编辑/更新:我现在最大的问题是步骤3的“ t = ...”等式是一个好主意还是有更好的方法来做到这一点。大多数其他问题已得到部分或完全解决,但没有任何评论或答案真正涉及此问题。同样,对于我可以想到的任何迭代/递归解决方案(下面的注释中有一些建议),可能都需要解析解决方案,速度和距离太大,对象也太小(尽管有一种特殊的迭代/递归解决方案,可以很好地处理此类情况,那么我肯定会接受)。到目前为止,非常感谢您的帮助,你们都很棒,我非常感谢您的想法和帮助!
我正在尝试检测小型高速物体之间的碰撞。在这种情况下,即使以相对较低的速度,也可能非常容易发生隧穿。
射线投射将不起作用,因为这将检测两个高速物体之间的碰撞,而不是一个物体与固定墙之间的碰撞。(除非我误解了射线投射?)性能是一个非常重要的考虑因素。如果可能的话,我想避免对性能造成重大影响。我已经实现了一个功能强大且非常有效的四叉树(http://en.wikipedia.org/wiki/Quadtree),因此,我将按如下所述对其进行修改和使用。
编辑:减少时间间隔将不起作用。此解决方案的速度太高,这意味着性能损失会太大,同时仍会丢失绝大多数隧道碰撞。(例如,我可能有一个大小约为1个单位的对象,其移动速度在每个时间间隔中以百万个单位为单位...)
建议的解决方案:
步骤1:
在每个对象的运动周围创建一个框,然后将这些框输入四叉树以生成可能发生碰撞的初始列表。参见下图(此图显示了一个圆形对象从一个位置移动到另一个位置,并且该移动生成一个矩形,该矩形将被馈送到四叉树中):
步骤2 :(可能要跳过此步骤吗?)
浏览四叉树可能产生的碰撞列表。查看矩形是否在每次可能的碰撞中相交。如果是这样,请继续执行步骤3。
编辑:在下面,肖恩·米德里奇(Sean Middleditch)建议使用扫掠体/胶囊的交点(如果对象是圆形的话)。剩下三个选项:1)完全跳过步骤2。2)按我的方式执行步骤2。3)按肖恩的方式做。肖恩的方法在计算上比我的盒子想法要昂贵,但是它会比我的方法消除更多的误报,从而阻止他们进入最后一步。
任何人都可以根据经验谈谈这三种选择中哪一种是最佳的吗?(我打算将此物理引擎用于其他一些事情,因此我正在寻找一种“一般最佳”的解决方案,该解决方案在各种各样的情况下都能最快地工作,而不仅仅是一个可以轻松衡量哪种解决方案的特定测试用例。是最快的)。
第三步:
使用下面的t =方程,如果判别式(即,平方根下的部分)为负或0,则无碰撞;如果为正,则将t值用作碰撞时间(在此之后,很容易相应地调整位置)。 ..如果两个对象在碰撞后仍继续存在)。方程:
t =(-1/2 sqrt((2 a w-2 a x + 2 b y-2 b z-2 c w + 2 c x-2 d y + 2 dz)^ 2-4(w ^ 2- 2 w x + x ^ 2 + y ^ 2-2 y z + z ^ 2)(a ^ 2-2 a c + b ^ 2-2 b d + c ^ 2 + d ^ 2-r ^ 2-2 r ss ^ 2))-a w + a xb y + b z + c wc x + d yd z)/(w ^ 2-2 w x + x ^ 2 + y ^ 2-2 y z + z ^ 2 )。
其中(1和2用于表示对象1和2):
t是介于0和-1之间的负时间值,其中0是当前帧,而-1是前一帧;
a = x位置1;
b = y位置1;
c = x位置2;
d = y位置2;
w = x速度1;
x = x速度2;
y = y速度1;
z = y速度2;
r =半径1;
s =半径2;
导数:(^ 2表示平方)
以对象运动的参数方程式为例(例如,newxpos1 = a + t w),并将其插入距离公式中(对边进行平方):距离公式的平方=(a + t w-(c + t x))^ 2 +(b + t y-(d + t * z))^ 2。请记住,t将为负。为了找到两个圆形物体的碰撞时间,我们将左侧设置为(r + s)^ 2。使用二次方程式(以及大量非常繁琐的代数)求解t,我们得到上面的“ t = ...”方程式。
我的问题:
1)这是一个好方法吗?会起作用吗?我会遇到任何无法预料的问题吗?(我知道当一次有两个以上的物体碰撞时我会遇到麻烦,但我不在乎,因为我真正反对的唯一情况是当它们的相对速度较低时(如果相对速度较高)那么算法给出的“愚蠢”解决方案将“足够好”,并且人类将不可能看到错误),并且如果在同一时间步长内有两个以上的碰撞且相对速度较低,大多数解决方案将无论如何都要足够近,因为我不打算发生一堆无弹性的碰撞)
2)我的表现会受到很大影响吗?我认为这不会,但是如果有的话,还有更好的方法吗?
3)我应该跳过第2步,直接从第1步转到第3步吗?显然,步骤2并不是至关重要的,但是它可能会提高性能(或者它可能花费比所节省的CPU时间更多的时间)。
所有其他评论,建议或批评都非常欢迎。谢谢您的帮助!