|
|
我现在需要判断一个*.3ds模型的各个顶点在当前视角下是否可见?
我的想法是:
1. 计算出模型中某一点的世界坐标 => Vworld(顶点世界坐标(齐次向量))
2. glGetDoublev(GL_MODELVIEW_MATRIX, Mmodelview); => Mmodelview(模型视图矩阵)
3. glGetDoublev(GL_PROJECTION_MATRIX, Mproj); => Mproj(投影矩阵)
4. glGetIntegerv(GL_VIEWPORT, ViewPort); => ViewPort(视口)
5. glReadBuffer(GL_BACK);
glReadPixels(ViewPort[0], ViewPort[1], ViewPort[2], ViewPort[3], GL_DEPTH_COMPONENT, GL_FLOAT, pBuffer); => pBuffer中是深度信息(倒置存放)
6. 计算出Vproj(投影体内的齐次坐标) = Vworld * Mmodelview * Mproj;
7. 计算出屏幕坐标以及深度信息:
nScreenX = int((Vproj.x/Vproj.w + 1) * ViewPort[2] / 2 + ViewPort[0]);
nScreenY = int((-Vproj.y/Vproj.w + 1) * ViewPort[3] / 2 + ViewPort[1]);
dDepth = (Vproj.z/Vproj.w + 1) / 2;
这样得到了顶点的深度信息,然后dDepth与pBuffer[(ViewPort[3]-1-nScreenY)*ViewPort[2] + nScreenX](由于pBuffer倒置存放深度信息)比较,看它们差的绝对值是否足够小,来判断该顶点是否可见。
但是问题:
1. 结果不正确,很明显看不到的结果是能看到,也有很明显看到的结果看不到。
2. pBuffer中得到的深度值应该是归约到[0, 1]之间吧,所以我计算dDepth也归约到[0, 1],不知道对不对?
3. 我google,baidu查找原因,有种说法说得到的深度值精度不够,当两个面相邻很近时会发生所谓Z-fighting?
4. 我曾尝试用其他方法,比如,对于一个顶点,遍历每个三角面判断是否有被遮挡,但是效率和效果都很差。
请问大侠,顶点可见性判断有什么好方法没?谢谢! |
|