C ++中的Ray-mesh交集或AABB树实现,开销很小?

时间:2013-02-08 07:42:32

标签: c++ geometry intersection aabb

你能推荐我......

  • 是否是AABB树的经过验证的轻量级C / C ++实现?
  • ,或者,另一种有效的数据结构,加上轻量级的C / C ++实现,来解决大量光线与大量三角形相交的问题?

“大数字”表示光线和三角形都有几个100k。

我知道AABB树是CGAL库的一部分,可能是像Bullet这样的游戏物理库。但是,我不希望在我的项目中增加一个巨大的额外库。理想情况下,我想使用一个小型浮点型模板化头文件实现。只要它在我的项目中轻松集成,我也会选择一堆CPP文件。对boost的依赖是可以的。

是的,我用Google搜索,但没有成功。

我应该提一下,我的应用程序上下文是网格处理,而不是渲染。简而言之,我将参考网格的拓扑结构从3D扫描转移到网格的几何体。我正在从顶点和参考网格的法线向3D扫描拍摄光线,我需要通过扫描恢复这些光线的交叉点。

修改

几个答案/评论指向最近邻数据结构。我已经创建了一个关于使用最近邻方法逼近光线网格交叉点时出现的问题的小图。最近邻方法可以用作在许多情况下起作用的启发式方法,但我不相信它们实际上是系统地解决问题,就像AABB树一样。

enter image description here

3 个答案:

答案 0 :(得分:1)

如果没有实时要求,我首先尝试蛮力。

1M * 1M ray->三角测试运行时间不应超过几分钟(在CPU中)。

如果这是一个问题,那么要做的第二件事就是通过计算目标网格中三角形/多边形之间的邻接图/关系来限制搜索区域。在初始猜测失败后,可以尝试相邻的三角形。这当然依赖于缺乏自我遮挡/多个生命值。 (我认为这是“可见性不适用于这个问题”的一种解释)。

此外,根据拓扑结构的病理程度,可以尝试在单位立方体上对目标网格进行环境映射(每个像素将由投影在其上的三角形列表组成)并通过单个光线测试初始候选者 - > aabb test + lookup。

鉴于反馈,还有一个更简单的选择 - 空间划分为简单的3D网格,其中每个维度可以通过x / y / z位置的直方图进行细分,甚至可以定期进行细分。

  • 100x100x100网格非常可管理的1e6条目大小
  • 要访问的最大立方体数量与直径(最大300)
  • 成正比
  • 有大约60000个极端细胞,表明每个细胞有10个三角形

  • 警告:三角形必须放在它们占据的每个单元格上 - 保守算法将它们放置在它们不属于的单元格中;大三角形可能需要剪裁和重组。

答案 1 :(得分:1)

尝试ANN库: http://www.cs.umd.edu/~mount/ANN/

这是“近似最近邻居”。我知道,你正在寻找一些略有不同的东西,但是这里有你如何使用它来加速你的数据处理:

  1. 将要点纳入ANN。
  2. 在每个要进行光线投射的顶点周围查询用户可选择的(将其视为“每网格旋钮”)半径,并找出范围内的网格顶点。
  3. 仅选择该范围内的三角形,并沿法线进行光线追踪以找到所需的三角形。
  4. 通过明智地选择搜索半径,您肯定会在不影响准确性的情况下获得相当大的加速。

答案 2 :(得分:1)

虽然这段代码有点旧并且使用了3DS Max SDK,但它为C ++中的对象 - 对象碰撞变形提供了一个相当不错的树系统。无法一眼就看出它是四树,AABB树,还是OBB树(评论也有点吝啬)。

http://www.max3dstuff.com/max4/objectDeform/help.html

这需要从Max转换到您自己的系统,但这可能是值得的。