python | Pygame | Sprite 碰撞

标签 python pygame sprite collision-detection collision

我们正在制作一款游戏,其中玩家沿着街道行走并射击多个敌人(机器人)。我们创建了一个子弹 Sprite ,每次按键时都会射击 <D><RIGHT_ARROW>被压。我们现在需要的只是子弹和敌人(已经创建的)之间的碰撞的一些帮助。

import pygame, os, sys, glob, random
from pygame.locals import *
pygame.init()

Still = pygame.image.load("Character\Stopped1.png")
Front = pygame.image.load("Terrain\Foreground2.png")
Back = pygame.image.load("Terrain\Background2.png")
VeryBack = pygame.image.load("terrain\VeryBack.jpg")
Middle = pygame.image.load("Terrain\shrub2.png")
RobotStill = pygame.image.load("Character\Robot\Robot Still.png")
RobotMove = pygame.image.load("Character\Robot\Robot.png")
Exclaim = pygame.image.load("pictures\Exclaim.png")

black = ( 0, 0, 0 )

#Defining player's health
HealthData = 100

#Player's X and Y coordinates
PLAYER_x = 0
PLAYER_Y = 0

#Backgrounds
Back_Movex = 0
Back_Movey = 0
Front_Movex = 0
Front_Movey = 0
Middle_Movex = 0
Middle_Movey = 0

#Robot
ROBOT_X = 0
Bot_Movex = 0



data = 0

Mx = 0
My = 0
Fx = 0
Fy = 0
Bx = 0
By = 0

#Setting a screen
H = 320
W = 800
screen = pygame.display.set_mode((W,H), RESIZABLE)
pygame.display.set_caption("Robot Game #0.002")
icon = pygame.image.load("Pictures\PCR(2).png")
icon = pygame.display.set_icon(icon)

#Define a Clock
clock = pygame.time.Clock()

#Bulet Class
class Bullet(pygame.sprite.Sprite):
def __init__(self):
    pygame.sprite.Sprite.__init__(self)  
    self.image = pygame.Surface([10,4])
    self.image.fill(black) 
    self.rect = self.image.get_rect()

all_sprites_list = pygame.sprite.Group()
bullet_list = pygame.sprite.Group()

#Player Class
class player(pygame.sprite.Sprite):
def __init__(self):
    pygame.sprite.Sprite.__init__(self)
    self.x = 25
    self.y = 210
    self.ani_speed_init = 5
    self.ani_speed = self.ani_speed_init 
    self.ani = glob.glob("Character\Walk\Walk*.png")
    self.aniBack = glob.glob("Character\WalkBack\Walk*.png")   
    self.ani.sort()
    self.ani_PLAYER_x = 0
    self.ani_max = len(self.ani)-1
    self.img = pygame.image.load(self.ani[0])
    self.rect = self.x
    self.update(0)

def update(self, PLAYER_x):  

    if Back_Movex == 0:
        screen.blit(Still,(self.x,self.y)),Still.get_rect()

    if Back_Movex < 0:
        self.ani_speed-=1
        self.x+=PLAYER_x
        if self.ani_speed == 0:
            self.img = pygame.image.load(self.ani[self.ani_PLAYER_x])
            self.ani_speed = self.ani_speed_init
            if self.ani_PLAYER_x == self.ani_max:
                self.ani_PLAYER_x = 0
            else:
                self.ani_PLAYER_x+=1
        screen.blit(self.img,(self.x,self.y))

    if Back_Movex > 0:
        self.ani_speed-=1
        self.x+=PLAYER_x
        if self.ani_speed == 0:
            self.img = pygame.image.load(self.aniBack[self.ani_PLAYER_x])
            self.ani_speed = self.ani_speed_init
            if self.ani_PLAYER_x == self.ani_max:
                self.ani_PLAYER_x = 0
            else:
                self.ani_PLAYER_x+=1
        screen.blit(self.img,(self.x,self.y))

#Robot Class
class Robot(pygame.sprite.Sprite):
    def __init__(Bot):
        pygame.sprite.Sprite.__init__(Bot)
        Bot.x = 750
        Bot.y = 197
        Bot.ani_speed_init = 5
        Bot.ani_speed = Bot.ani_speed_init 
        Bot.ani = glob.glob("Character\Robot\Robot Still*.png")  
        Bot.ani.sort()
        Bot.ani_Robot_x = 0
        Bot.ani_max = len(Bot.ani)-1
        Bot.img = pygame.image.load(Bot.ani[0])
        Bot.rect = pygame.image.load(Bot.ani[0])
        Bot.update(0)


def update(Bot, Robot_x):

    Key = pygame.key.get_pressed()
    if Bot.x != -3 or Bot.x != 0:
        screen.blit(RobotStill,(Bot.x,Bot.y)),RobotStill.get_rect()

    if (Key[K_RIGHT]):
        Bot.x += -3
    if (Key[K_LEFT]):
        Bot.x += 3

        #Sending Robot in opposite direction after collision (DOES NOT WORK!...YET!)
    if Bot.x < 90:
        Bot.x += 10

        #Moving the Robot and displaying an exclimation mark (WORKS!)
    if Bot.x < 700 and Bot.x > 600:
        screen.blit(Exclaim,(Bot.x,130)),Exclaim.get_rect()
    if Bot.x < 700 and Bot.x > 120:
        Bot.x += -3.5

player1 = player()
Robot_x = Robot()

#Main Loop/Key Input
while True:
    clock.tick(60)

    for event in pygame.event.get():
        if event.type == pygame.QUIT:
            pygame.quit()

            #Check if a key is pressed
        elif event.type == KEYDOWN:
            if event.key == K_RIGHT:
                Front_Movex += -3
                Back_Movex += -1
                Middle_Movex += - 1.5
                data += 1
            if event.key == K_LEFT:
                Front_Movex += 3
                Back_Movex += 1
                Middle_Movex += 1.5
            if event.key == K_d and data ==1:
                bullet = Bullet()
                bullet.rect.x = 55
                bullet.rect.y = 262
                all_sprites_list.add(bullet)
                bullet_list.add(bullet)

        #Check if a key is un-pressed                                
    elif event.type == KEYUP:
        if event.key == K_RIGHT:
            Front_Movex = 0
            Back_Movex = 0
            Middle_Movex = 0
            data -= 1
        if event.key == K_LEFT:
            Front_Movex = 0
            Back_Movex = 0
            Middle_Movex = 0

        #Player's Health
    if pygame.font:
        pygame.font.init()
        font = pygame.font.Font(None,40)
        text = font.render("Health: "+str(HealthData),0, (255,255,255))
        screen.blit(text,(0,0))

        #Moving fired bullets
for bullet in bullet_list:
    bullet.rect.x += 14
    if bullet.rect.x > 810:
        bullet_list.remove(bullet)
        all_sprites_list.remove(bullet)




Bx+=Back_Movex
Fx+=Front_Movex
Fy+=Front_Movey
By+=Back_Movey
Mx+=Middle_Movex
My+=Middle_Movey

#Displaying to the screen
screen.blit(VeryBack,(0,0)),VeryBack.get_rect()
screen.blit(Back,(Bx,By)),Back.get_rect()
screen.blit(Middle,(Mx,My)),Middle.get_rect()
screen.blit(Front,(Fx,Fy)),Front.get_rect()
all_sprites_list.draw(screen)

player1.update(PLAYER_x)
Robot_x.update(Robot)

#Looping backgrounds
if Bx <= -1600.:
    Bx = 0.
if Fx <= -1600.:
    Fx = 0.
if Mx <= -1600.:
    Mx = 0.
if Bx >= 1.:
    Bx = -1600.
if Fx >= 1.:
    Fx = -1600.
if Mx >= 1.:
    Mx = -1600.

pygame.display.update()

最佳答案

pygame有几个api (pygame.Rect.colliderect)检测碰撞给出矩形。还有一些专门针对 Sprite 的( pygame.sprite.collide_rect)

最简单的方法可能是

bullet_hit_list = Robot_x.rect.collidelistall([b.rect for b in bulletlist])

关于 python | Pygame | Sprite 碰撞,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/16906984/

相关文章:

python - 在 cocos2d 中显示 Sprite 的问题

python - Python 中的正则表达式帮助有选择地从数学表达式中删除括号

python_pygame - 文件未找到错误 : No such file or directory

python - Pygame 如何检查第二次按下某个键

python - 试图查找某些文本是否存在

python - 主菜单帮助(pygame)

android - 使用 LibGDX 制作静态动画的有效方法?

java - 如何在 Libgdx 中调整 Sprite 的大小?

java - 如何通过处理java来减慢 Sprite 动画的速度

python - 如何与 Django 一起设置连续运行的进程?