高效的碰撞检测

时间:2012-09-17 09:11:08

标签: python collision-detection pyglet game-ai

我在2D游戏中使用python和pyglet,但我遇到了碰撞检测中的问题。我检查碰撞的代码如下所示:

def distance(self,target):
    return math.sqrt((self.x-target.x)**2 + (self.y-target.y)**2)
def check_collision(self):
    for i in list_of_mobs:
        if self.distance(i) < (self.width/2 + i.width/2):
            return True

它检查每个精灵的距离,其中“target”是另一个精灵。我不确定的是“我应该检查所有精灵之间的碰撞吗?”我有超过200个小怪(我希望在成品中更多)并且在检查碰撞时它变得无法播放。有没有办法只检查一定距离内的精灵而不会失去速度?

编辑:

我读了一下google,发现很多速度花在做同样的碰撞上。即用sprite2检查sprite1,用sprite1检查sprite2。所以我对检查碰撞功能进行了一些更改,现在运行速度更快,但仍然低于20 fps

def check_collision(self):
    global mobs_to_collide
    if mobs_to_collide == []:
        mobs_to_collide = list_of_mobs[:]
    if self in mobs_to_collide:
        mobs_to_collide.remove(self)
    for i in mobs_to_collide:
        if self.distance(i) < (self.width/2 + i.width/2):
            return True

(它可能包含一些低效的代码/无用的东西。我正在玩它一点)

EDIT2:

我决定使用rabbyt作为精灵库。碰撞快速而简单。我用以下代码替换了上面的代码:

rabbyt.collisions.collide(mobs_to_collide)

这将返回一个列表列表(我不确定这是否是正确的术语)与碰撞的对象。我还在研究如何将其翻译成“if collided:”类型语句,但我正在取得进展。如果有人处于类似情况,我会建议使用rabbyt。

2 个答案:

答案 0 :(得分:4)

提高速度的简单方法可能是删除平方根操作

def distancesq(self,target):
  return (self.x-target.x)**2 + (self.y-target.y)**2
def check_collision(self):
  for i in list_of_mobs:
    # Square this distance to compensate
    if self.distancesq(i) < (self.width/2 + i.width/2)**2: 
        return True

答案 1 :(得分:1)

可能已经太晚了,但我遇到了完全相同的问题。我设法通过仅计算可见对象的碰撞来解决它:

for object_ in objects:
    if not object_.visible: # pyglet.sprite.Sprite() provides this flag
        continue
    # rest of your collision detection