长距离无缝过渡(3D渲染)

时间:2009-12-18 20:11:33

标签: math opengl graphics 3d directx

处理大型结构和场景的最佳机制是什么?

例如具有规模城市和地理的大陆,或无限宇宙风格的行星过渡。

3 个答案:

答案 0 :(得分:3)

使用大规模位置浮点表示的最大问题是,当您越来越远离原点时,您会迅速失去精度。

要解决此问题,您需要将所有位置表示为相对于原点以外的其他位置。最简单的方法是将世界划分为网格并存储所有实体的位置,如下所示:

struct Position {
    int kilometers[3]; // x, y and z offset in kilometers
    float offset[3]; //x, y and z offset in meters
};

相机的位置也是这样存储的,当你需要渲染时,你可以这样做:

void
getRelativePosition(float& x, float& y, float& z, const Position& origin, const Position& object) {
    x = (object.kilometers[0] - origin.kilometers[0]) * 1000.0f +
        (object.offset[0] - origin.offset[0]);
    //Ditto for y and z
}

//Somewhere later
float x, y, z;
getRelativePosition(x, y, z, camera.position(), object.position());
renderMesh(x, y, z, object.mesh());

(为简单起见,我忽略了本例中相机和物体的方向,因为没有与此相关的特殊问题)。

如果您正在使用银河系上的连续世界,您可以用kilometers(64位)替换long long参数,为您提供180万光年的有效范围。

编辑:要将此用于连续几何体(如地形等),您必须将地形拆分为大小为一平方公里的块,地形块中顶点的坐标应位于范围[0,1000]。

同样在上面的getRelativePosition函数中,您可以更改它,以便返回bool并返回false,如果公里数的差异大于某个阈值(例如距离远处的距离)剪辑平面)。

答案 1 :(得分:1)

取自http://www.gamedev.net/reference/business/features/spotlightFB/

  

问:空间。它很大。这真的很棒。它   在如此巨大的代码中必须令人生畏   尺度 - 你怎么去做这样的   事情?你使用任何特殊数据吗?   结构或测量单位   帮助

     

答:正如你可以想象的那样,与...合作   单一类型的单位不起作用。一世   使用单元的分层系统。在   银河系,光年(LY)   单位被利用。在星系统   等级,公里是基本单位,   和坐标用   双精度浮点   数字。在渲染时,顶点是   生成为单精度浮点数,   但翻译成相机空间   最大限度地减少由于的精度损失   大数字。

答案 2 :(得分:0)

可能值得研究Bing Maps Deep Zoom

背后的技术

Google地球使用了类似的技术,它可以让您从行星视图一直到街景非常顺利。放大和缩小时,很明显会有很多分辨率交换。