【问题标题】:Opinions on collision detection objects with a moving scene关于运动场景碰撞检测对象的意见
【发布时间】:2010-03-27 15:24:21
【问题描述】:

所以我的问题很简单,我想这可以归结为您对碰撞检测的期望。为简单起见,假设我们正在讨论由边界框定义的 2D 精灵。另外,假设我的精灵对象有一个检测碰撞的功能,如下所示:S.collidesWith(other);最终场景在移动,场景中的“墙”可以移动,对象可能不会碰到墙。

所以一个简单的实现可能看起来像这样(伪代码):

moveWalls();
moveSprite();
foreach(wall as w) {
    if(s.collidesWith(w)) { 
        gameover();
    }
}

这样做的问题是,如果精灵和墙相互移动,取决于情况(例如对角力矩)。它们可能会相互穿过(不太可能但可能发生)。

所以我可以这样做。

moveWalls();
foreach(wall as w) {
    if(s.collidesWith(w)) { 
        gameover();
    }
}
moveSprite();
foreach(wall as w) {
    if(s.collidesWith(w)) { 
        gameover();
    }
}

这解决了互相传递的问题,但出现了另一个罕见的问题。如果它们彼此相邻(字面意思是下一个像素)并且墙壁和精灵都向左移动,那么我将得到一个无效的碰撞,因为墙壁移动,检查碰撞(命中)然后精灵被移动。这似乎不公平。此外,冗余碰撞检测感觉非常低效。我可以给予玩家移动优先权来缓解第一个问题,但它仍在检查两次。

moveSprite();
foreach(wall as w) {
    if(s.collidesWith(w)) { 
        gameover();
    }
}
moveWalls();
foreach(wall as w) {
    if(s.collidesWith(w)) { 
        gameover();
    }
}

我是否只是在思考这个问题,是否应该将其归结为“它会发生得非常罕见,以至于没人会关心”?当然,在查看基于精灵的旧游戏时,我经常会发现碰撞检测存在细微缺陷的情况,但我认为现在我们可以做得更好:-P。人们的想法是什么?

【问题讨论】:

    标签: language-agnostic collision-detection


    【解决方案1】:

    我们无法告诉您是否值得提高准确性,但应该在游戏测试期间变得明显。至于提高碰撞检测的可靠性,您有多种选择:

    1. 减小模拟步长。如果 stepsize * (player max velocity + wall max velocity)
    2. 还要检查模拟步骤前后玩家是否在墙的同一侧。
    3. 不是只在每个模拟步骤结束时检查碰撞,而是推导出一个公式,计算在给定当前速度的情况下墙壁和玩家发生碰撞的时间,如果该时间在当前模拟范围内,则标记碰撞步。如果在您的情况下这可能有点过分,但在建模诸如从墙壁反弹之类的东西时很有用。

    【讨论】:

      【解决方案2】:

      这在很大程度上取决于您用来检查碰撞的频率(以及玩家的输入设备)。当您经常检查时,两者“同时”移动的情况将变得不太可能。如果是回合制策略游戏,那就另当别论了。

      也就是说,我不知道您详细使用的是哪个模型,但如果您有一个线程来检查玩家输入,一个线程负责移动计算和碰撞检测,那么两者都必须是无论如何同步(读/写锁)。在那种情况下,很明显,首先发生了什么。同样的事情,如果你只使用一个线程。

      根据物理模型,输入可以控制加速度,这将决定速度,进而决定位置。如果对象从前一个位置到(可能的)下一个位置的移动线与当时的墙壁位置相交,那么您就会发生碰撞(考虑到可能发生碰撞的整个轮廓)。

      可能更困难的是计算反弹的效果。当我编写一个基于 OpenGL 的游戏时,我发现这是真的,墙壁不能移动,但地板可以倾斜:当弹跳强度不足以抵消对墙壁的加速度时,你仍然会碰撞后的墙内。经过一番努力,我认为效果很好(包括沿墙滚动,这是另一个问题),但是移动墙壁,就更难了。

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 2018-02-15
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2018-11-07
        • 2015-12-04
        相关资源
        最近更新 更多