2D Platformer的碰撞检测

时间:2020-03-01 16:10:50

标签: python pygame

我正在开发平台游戏,我想与平台进行基本碰撞,可惜仍然无法正确完成。玩家移动的计算方法如下:

                if(a[i]=='H'){
                    a[i] = 'T';
                }
                if(a[i]=='T'){
                    a[i] = 'H';
                }

所有变量都是具有a[]'H'值的向量。这按预期工作,冲突的问题。我的规则是:

  • 停在平台上时停止下落。
  • 从平台运行时开始下降。
  • 在跳跃过程中撞到平台时,停止向上移动。
  • 撞到墙壁时停止向一侧移动,但是可以向相反方向移动。

检查底部是否与平台发生碰撞非常简单,但要检测出棘手的部分,即哪一侧与平台发生碰撞并能够为玩家设置合适的位置。

我试图从每个侧面检测角和中间,但是由于我的速度不是每帧1px,所以有时玩家会掉下来很快并且也被检测为侧面。

什么是检测哪一侧发生碰撞的好方法?

2 个答案:

答案 0 :(得分:0)

我在JavaScript中有几个类似平台游戏的游戏,这就是我实现碰撞的方式:

1。降落在平台上时停止下落: 您可以为子画面提供一个矩形作为边界区域,然后使用Pygames内置的Rect类检测交点。当您的精灵点击框(矩形)和平台矩形(另一个矩形)之间发生这种相交时,您可以将玩家的Y速度设置为0。

2。在跨平台运行时开始下降。 我通常有一个专门用于重力的变量,并且简单地将其不断应用于精灵,以将其向下推。这样,当您不再与平台相交后,它将向下掉落。

3。在跳跃过程中撞到平台时,停止向上移动: 与交点之前的操作相同,只是在矩形碰撞后将Y速度设置为0,并且由于恒定的重力而让玩家跌倒。

4。碰到墙时停止向一侧移动,但可以向相反方向移动: 同样,但这次将X速度设置为0。 (如果您被困在墙上,则可以始终将X设置为大于0的值来推动自己回到游戏中)

还有一点要注意,如果您只想在Sprite到达平台的某个边缘时执行某些操作,则可以仅创建一个与Sprite侧面对齐的矩形。例如,如果我想查看某个东西是否与精灵的左侧相交,则可以使用 -高度:相同高度 宽度:1 -x:x +宽度 -y:相同y

关于矩形的文档: https://www.pygame.org/docs/ref/rect.html

答案 1 :(得分:0)

下面是代码,可以帮助您检测何时可以从平台跳出:

self.rect.y += 2
platform_hit_list = pygame.sprite.spritecollide(self, self.level.platform_list, False)
self.rect.y -= 2

# If it is ok to jump, set our speed upwards
if len(platform_hit_list) > 0:
    velocity += acceleration
    position += velocity + 0.5 * acceleration

然后提供用于检测何时落入平台的代码:

if self.rect.y >= constants.SCREEN_HEIGHT and self.change_y >= 0:
    self.change_y = 0
    self.rect.y = constants.SCREEN_HEIGHT

最后是碰撞代码:

block_hit_list = pygame.sprite.spritecollide(self, self.level.platform_list, False)
for block in block_hit_list:
    # If we are moving right,
    # set our right side to the left side of the item we hit
    if self.change_x > 0:
        self.rect.right = block.rect.left
    elif self.change_x < 0:
        # Otherwise if we are moving left, do the opposite.
        self.rect.left = block.rect.right

# Move up/down
velocity += acceleration
position += velocity + 0.5 * acceleration

# Check and see if we hit anything
block_hit_list = pygame.sprite.spritecollide(self, self.level.platform_list, False)
for block in block_hit_list:

    # Reset our position based on the top/bottom of the object.
    if self.change_y > 0:
        self.rect.bottom = block.rect.top
    elif self.change_y < 0:
        self.rect.top = block.rect.bottom

    # Stop our vertical movement
    self.change_y = 0

希望这一切都会以某种方式帮助您提供所需的答案。请注意,这些块是指平台,并且将检查给定列表中的每个平台,而我使用rects是因为它是检查冲突的最佳方法之一。至于change_x和change_y,它们只是存储玩家将移动多少的变量。

相关问题