使用视锥体检查边界框交叉点/碰撞

时间:2011-03-18 04:39:43

标签: python collision-detection bounding-box frustum

我想检查某些对象的轴对齐边界框的视锥体,以粗略地检查这些对象是否在视野中。速度不是什么大问题。

2 个答案:

答案 0 :(得分:3)

我发现构建视锥体的世界空间模型并检查bbox与它的碰撞是错误的方法。

一个更简单的方法是以相反的方式将给定bbox的每个顶点转换为屏幕空间,如果bbox的任何顶点在屏幕边界内,则将该bbox计为可见。我通过乘以相机矩阵得到屏幕空间位置,然后根据相机的视野计算透视。

以下是代码:

vertexMatrix = matrix([vertex.x,vertex.y,vertex.z,1]) 
productMatrix = (vertexMatrix * camMatrix)
pVectSS = vector(prodMatrix[0][0],prodMatrix[0][1],prodMatrix[0][2])

pointX = ((pVectSS.x/(-pVectSS.z))/tan(radians(hFOV/2)))/2.0+.5
pointY = ((pVectSS.y/(-pVectSS.z))/tan(radians(vFOV/2)))/2.0+.5

键:

 camMatrix = camera inverse world-space matrix
 pVectSS = position vector screen-space
 hFOV = horizontal field of view
 vFOV = vertical field of view

答案 1 :(得分:2)

那会有效。然而,通常人们宁愿提取平截头体平面并计算到它们的距离。你说“速度不是什么大不了的事”,但最终你可能会发现速度并不是什么大问题。毕竟,为了让事情变得更快,人们会挫败剔除。

将顶点与矩阵相乘需要相当于4个点的乘积,因此您需要相当于32个点的乘积来检查所有8个角。计算一个点到一个平面的距离需要一个点积和一个加法,这在最坏的情况下更有效,而在一般情况下更有效(因为你经常可以在一个或两个平面之后剪掉一个物体,并且从不超过三个)。利用临时一致性的剪辑平面有很多优化,我不会详细介绍。

此外,您可以通过计算中心点到平面的距离来预先进行一些粗略剔除,并检查它是否大于边界框的半径。这将非常便宜地剔除明显“进入”或“出去”的物体。或者,您也可以将视图矢量的点积与视场值的余弦值加上一些“填充”(或者只是看它是否为正)作为第一次超粗略检查。你会记得,两个向量的点积告诉你它们指向同一个方向的程度。与您的视图向量具有负点积的东西肯定是您可以放弃的东西,因为它在您身后。