【问题标题】:How to prevent newer Collisions bypassing old collisions? (2D)如何防止新碰撞绕过旧碰撞? (2D)
【发布时间】:2020-03-24 13:25:03
【问题描述】:

我想用 C++ 中的多边形制作我自己的碰撞系统。有静态碰撞器(从不移动,不能被推动)和动态碰撞器(可以移动,永远不能在静态碰撞器中。)。 我目前的做法是:

for (auto &dyn : dynamicColliders) {
    for (auto &stat : staticColliders) {
        // "how deep" is any vertex of dyn inside of stat? Store that in t.
        //    Is dyn inside stat (0 <= t <= 1)? -> push dyn outside by t
        // not inside? -> next 2 lines
        // "how deep" is any vertex of stat inside of dyn? Store that in r.
        //    Is stat inside dyn (0 <= r <= 1)? -> push dyn outside by r.
    }
}

这是发生的事情的一个例子:

https://youtu.be/XeGga98ZtUY

基本上,正方形是静态对象。六边形是动态的。 现在,当六边形碰撞底部正方形时,它会被推入顶部正方形。然而,顶部正方形将六边形推回底部正方形。 (现在,物理步骤结束了。不再考虑假底部碰撞。这个顺序发生的原因是顶部正方形是“最新”的碰撞对象)

我尝试了什么:

  1. 对所有“推送”向量求和并在末尾添加它们
  2. 如果在被推到方块外后发生碰撞,则完全取消当前物理步骤中的移动。
  3. (以上方法)

结果:

  1. 不起作用:六边形被推入下方的正方形,之前没有碰撞。
  2. 确实有效,但非常有问题。我无法沿着正方形滑行,因为它已被取消。
  3. (见上面的视频)

如何避免绕过这种类型的碰撞?非常感谢!

【问题讨论】:

    标签: c++ 2d collision-detection game-physics


    【解决方案1】:

    这种单点的碰撞检测方法(很遗憾)行不通。由于它在发生碰撞的单个点对每个对象进行建模,因此它没有考虑到对象也可能在其他地方发生碰撞,因此无法在它试图推动它的方向上移动或反弹。

    您需要使用您正在使用的任何检测系统检查它碰撞的所有点,然后让您的碰撞处理逻辑根据它可以进入的有效方向做出反应。

    如果您还在构建检测系统(听起来像是您的问题),那么您将需要一种有效的算法来映射二维空间中可能的碰撞点,您可能需要实现 最近邻搜索 带有kd-tree。您可以找到许多 C++ 库来为您执行此操作。

    (请注意,kd-tree 在每次插入和删除时都会失去平衡,因此您应该为您的移动点创建一个动态树,并定期重新平衡,并为您的静态点创建一个静态树,可以单独放置)

    【讨论】:

    • 感谢您的回答!我将尝试实施该系统。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2015-07-26
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多