Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/python/318.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Python 基于碰撞检测的Pygame停止运动_Python_Pygame_Rect - Fatal编程技术网

Python 基于碰撞检测的Pygame停止运动

Python 基于碰撞检测的Pygame停止运动,python,pygame,rect,Python,Pygame,Rect,我基本上是想用pygame制作一个“实体”对象。目标是在玩家接触时击退他们。我目前正在使用(但无法正常工作)的内容如下: keys_pressed = pygame.key.get_pressed() if 1 in keys_pressed: if keys_pressed[K_w]: self.player_l[1] += -2 if self.player_r.colliderect(self.tower_r): self.player_l[1] -

我基本上是想用pygame制作一个“实体”对象。目标是在玩家接触时击退他们。我目前正在使用(但无法正常工作)的内容如下:

keys_pressed = pygame.key.get_pressed()
if 1 in keys_pressed:
    if keys_pressed[K_w]:
        self.player_l[1] += -2
        if self.player_r.colliderect(self.tower_r): self.player_l[1] -= -2
    if keys_pressed[K_a]:
        self.player_l[0] += -2
        if self.player_r.colliderect(self.tower_r): self.player_l[0] -= -2
    if keys_pressed[K_s]:
        self.player_l[1] += 2
        if self.player_r.colliderect(self.tower_r): self.player_l[1] -= 2
    if keys_pressed[K_d]:
        self.player_l[0] += 2
        if self.player_r.colliderect(self.tower_r): self.player_l[0] -= 2

问题是玩家被卡在塔楼矩形内,尽管返回到碰撞开始前的位置,但玩家矩形将始终被拉回到塔楼,碰撞将继续触发。在最初接触到塔矩形后,玩家将无法向任何方向移动。

我在我的pygame游戏中也做了同样的事情。您要做的是创建一个所有对象都将使用的移动函数。这使得在名为“一切”的渲染更新组中不可能遍历任何精灵。如果精灵不是一切的一部分,它就不会碰撞。下面是函数。这会为碰撞产生一定量的阻力。基本上,当推一个物体时,它会向后推一定量。任何不调用move函数的对象即使被推上也不会移动,因此只有在第一个位置可以移动的对象才能被推,而墙之类的东西在推它们时不会滑过木板

    def moveRelative(self,other,speed):                                   #This function is a function the one you need uses, which you may find useful. It is designed to move towards or a way from another sprite. Other is the other sprite, speed is an integer, where a negative value specifies moving away from the sprite, which is how many pixels it will move away from the target. This returns coordinates for the move_ip function to move to or away from the sprite, as a tuple
            dx = other.rect.x - self.rect.x
            dy = other.rect.y - self.rect.y
            if abs(dx) > abs(dy):
                    # other is farther away in x than in y
                    if dx > 0:
                            return (+speed,0)
                    else:
                            return (-speed,0)
            else:
                    if dy > 0:
                            return (0,+speed)
                    else:
                            return (0,-speed)

    def move(self,dx,dy):
            screen.fill((COLOR),self.rect)                                 #covers over the sprite's rectangle with the background color, a constant in the program
            collisions = pygame.sprite.spritecollide(self, everything, False)
            for other in collisions:
                    if other != self:
                            (awayDx,awayDy) = self.moveRelative(other,-1)  #moves away from the object it is colliding with
                            dx = dx + 9*(awayDx)                           #the number 9 here represents the object's resistance. When you push on an object, it will push with a force of nine back. If you make it too low, players can walk right through other objects. If you make it too high, players will bounce back from other objects violently upon contact. In this, if a player moves in a direction faster than a speed of nine, they will push through the other object (or simply push the other object back if they are also in motion)
                            dy = dy + 9*(awayDy)
            self.rect.move_ip(dx,dy)                                       #this finally implements the movement, with the new calculations being used

它有很多代码,您可能想根据自己的目的对其进行更改,但这是一种非常好的方法。如果你想消除反弹的特性,你可以考虑将物体的任何运动设置为零,并且只允许移动。不过,我发现“反弹”功能对我的游戏更有用、更准确。

你能展示该方法的完整代码吗?这可能是一个输入错误。添加了整个移动代码:)一个想法是,如果你使用浮点数作为位置,舍入错误可能意味着你不会像被推入一样被挤出。你有没有试过使用调试器、打印语句或日志记录来跟踪位置的值。非常感谢,我设法修复了它,确保它圆满结束!