本文介绍了如何在pygame中检测碰撞?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我使用下面的类制作了子弹列表和子画面列表.如何检测子弹是否与精灵碰撞,然后删除该精灵和子弹?

  #Define Sprite类类精灵:def __init __(self,x,y,name):自我.x = xself.y = yself.image = pygame.image.load(name)self.rect = self.image.get_rect()def render():window.blit(self.image,(self.x,self.y))#定义项目符号类以创建项目符号子弹类:def __init __(self,x,y):self.x = x + 23self.y = yself.bullet = pygame.image.load("user_bullet.BMP")self.rect = self.bullet.get_rect()def render():window.blit(self.bullet,(self.x,self.y)) 
解决方案

在PyGame中,可以使用

  import pygamepygame.init()窗口= pygame.display.set_mode((250,250))rect = pygame.Rect(* window.get_rect().center,0,0).inflate(100,100)运行=真运行时:对于pygame.event.get()中的事件:如果event.type == pygame.QUIT:运行=错误点= pygame.mouse.get_pos()碰撞= rect.collidepoint(point)color =(255,0,0)如果碰撞否则(255,255,255)window.fill(0)pygame.draw.rect(窗口,颜色,矩形)pygame.display.flip()pygame.quit()出口() 

  •   import pygamepygame.init()窗口= pygame.display.set_mode((250,250))rect1 = pygame.Rect(* window.get_rect().center,0,0).inflate(75,75)rect2 = pygame.Rect(0,0,75,75)运行=真运行时:对于pygame.event.get()中的事件:如果event.type == pygame.QUIT:运行=错误rect2.center = pygame.mouse.get_pos()碰撞= rect1.colliderect(rect2)color =(255,0,0)如果碰撞否则(255,255,255)window.fill(0)pygame.draw.rect(窗口,颜色,rect1)pygame.draw.rect(窗口,(0,255,0),rect2,6,1)pygame.display.flip()pygame.quit()出口() 

  • 此外

      import pygamepygame.init()窗口= pygame.display.set_mode((250,250))sprite1 = pygame.sprite.Sprite()sprite1.image = pygame.Surface((75,75))sprite1.image.fill((255,0,0))sprite1.rect = pygame.Rect(* window.get_rect().center,0,0).inflate(75,75)sprite2 = pygame.sprite.Sprite()sprite2.image = pygame.Surface((75,75))sprite2.image.fill((0,255,0))sprite2.rect = pygame.Rect(* window.get_rect().center,0,0).inflate(75,75)all_group = pygame.sprite.Group([sprite2,sprite1])test_group = pygame.sprite.Group(sprite2)运行=真运行时:对于pygame.event.get()中的事件:如果event.type == pygame.QUIT:运行=错误sprite1.rect.center = pygame.mouse.get_pos()碰撞= pygame.sprite.spritecollide(sprite1,test_group,False)window.fill(0)all_group.draw(窗口)对于s发生碰撞:pygame.draw.rect(窗口,(255,255,255),s.rect,5,1)pygame.display.flip()pygame.quit()出口() 

    有关与口罩的碰撞,请参见

      import pygamepygame.init()窗口= pygame.display.set_mode((250,250))sprite1 = pygame.sprite.Sprite()sprite1.image = pygame.Surface((80,80),pygame.SRCALPHA)pygame.draw.circle(sprite1.image,(255,0,0),(40,40),40)sprite1.rect = pygame.Rect(* window.get_rect().center,0,0).inflate(40,40)sprite2 = pygame.sprite.Sprite()sprite2.image = pygame.Surface((80,89),pygame.SRCALPHA)pygame.draw.circle(sprite2.image,(0,255,0),(40,40),40)sprite2.rect = pygame.Rect(* window.get_rect().center,0,0).inflate(80,80)all_group = pygame.sprite.Group([sprite2,sprite1])test_group = pygame.sprite.Group(sprite2)运行=真运行时:对于pygame.event.get()中的事件:如果event.type == pygame.QUIT:运行=错误sprite1.rect.center = pygame.mouse.get_pos()碰撞= pygame.sprite.spritecollide(sprite1,test_group,False,pygame.sprite.collide_circle)window.fill(0)all_group.draw(窗口)对于s发生碰撞:pygame.draw.circle(窗口,(255,255,255),矩形中心,矩形宽度//2,5)pygame.display.flip()pygame.quit()出口() 


    这对您的代码意味着什么?

    pygame.Surface.get_rect.get_rect() 返回具有 Surface 对象大小的矩形,由于 Surface 对象没有位置,因此该矩形始终以(0,0)开始.矩形的位置可以通过关键字参数指定.例如,可以使用关键字参数 center 指定矩形的中心.这些关键字参数应用于 pygame.Rect ,然后再返回(请参见 pygame.Rect 以获得关键字参数的完整列表).
    请参阅* 为什么我的碰撞测试总是返回"true",为什么?图像矩形的位置是否总是错误(0,0)?

    您根本不需要 Sprite Bullet x y 属性.请使用 rect 属性的位置代替:

     #定义sprite类类精灵:def __init __(self,x,y,name):self.image = pygame.image.load(name)self.rect = self.image.get_rect(topleft =(x,y))def render():window.blit(self.image,self.rect)#定义项目符号类以创建项目符号子弹类:def __init __(self,x,y):self.bullet = pygame.image.load("user_bullet.BMP")self.rect = self.bullet.get_rect(topleft =(x + 23,y))def render():window.blit(self.bullet,self.rect) 

    使用 pygame.Rect.colliderect() 来检测 Sprite Bullet 实例之间的冲突.
    请参阅如何检测两个矩形对象之间的碰撞或pygame中的图片:

      my_sprite = Sprite(sx,sy,name)my_bullet =项目符号(by,by) 
     为True时:#[...]如果my_sprite.rect.colliderect(my_bullet.rect):printe(命中") 

    I have made a list of bullets and a list of sprites using the classes below. How do I detect if a bullet collides with a sprite and then delete that sprite and the bullet?

    #Define the sprite class
    class Sprite:
    
        def __init__(self,x,y, name):
            self.x=x
    
            self.y=y
    
            self.image = pygame.image.load(name)
    
            self.rect = self.image.get_rect()
    
        def render(self):
            window.blit(self.image, (self.x,self.y))
    
    
    # Define the bullet class to create bullets
    class Bullet:
    
        def __init__(self,x,y):
            self.x = x + 23
            self.y = y
            self.bullet = pygame.image.load("user_bullet.BMP")
            self.rect = self.bullet.get_rect()
    
        def render(self):
            window.blit(self.bullet, (self.x, self.y))
    
    解决方案

    In PyGame, basic collision detection can be done using pygame.Rect objects. The Rect object offers various methods for detecting collisions between objects. Note that even the collision of a rectangular object with a circular object such as a paddle and a ball in Pong game can be roughly detected by a collision between two rectangular objects, the paddle and the bounding rectangle of the ball.

    Some examples:

    • pygame.Rect.collidepoint:

      import pygame
      
      pygame.init()
      window = pygame.display.set_mode((250, 250))
      rect = pygame.Rect(*window.get_rect().center, 0, 0).inflate(100, 100)
      
      run = True
      while run:
          for event in pygame.event.get():
              if event.type == pygame.QUIT:
                  run = False
      
          point = pygame.mouse.get_pos()
          collide = rect.collidepoint(point)
          color = (255, 0, 0) if collide else (255, 255, 255)
      
          window.fill(0)
          pygame.draw.rect(window, color, rect)
          pygame.display.flip()
      
      pygame.quit()
      exit()
      

    • pygame.Rect.colliderect

      See also How to detect collisions between two rectangular objects or images in pygame

      import pygame
      
      pygame.init()
      window = pygame.display.set_mode((250, 250))
      rect1 = pygame.Rect(*window.get_rect().center, 0, 0).inflate(75, 75)
      rect2 = pygame.Rect(0, 0, 75, 75)
      
      run = True
      while run:
          for event in pygame.event.get():
              if event.type == pygame.QUIT:
                  run = False
      
          rect2.center = pygame.mouse.get_pos()
          collide = rect1.colliderect(rect2)
          color = (255, 0, 0) if collide else (255, 255, 255)
      
          window.fill(0)
          pygame.draw.rect(window, color, rect1)
          pygame.draw.rect(window, (0, 255, 0), rect2, 6, 1)
          pygame.display.flip()
      
      pygame.quit()
      exit()
      

    Furthermore pygame.Rect.collidelist and pygame.Rect.collidelistall can be used for the collision test between a rectangle and a list of rectangles. pygame.Rect.collidedict and pygame.Rect.collidedictall can be used for the collision collision test between a rectangle and a dictionary of rectangles.

    The collision of pygame.sprite.Sprite and pygame.sprite.Group objects, can be detected by pygame.sprite.spritecollide(), pygame.sprite.groupcollide() or pygame.sprite.spritecollideany(). When using these methods, the collision detection algorithm can be specified by the collided argument:

    Possible collided callables are collide_rect, collide_rect_ratio, collide_circle, collide_circle_ratio, collide_mask

    Some examples:

    • pygame.sprite.spritecollide()

      import pygame
      
      pygame.init()
      window = pygame.display.set_mode((250, 250))
      
      sprite1 = pygame.sprite.Sprite()
      sprite1.image = pygame.Surface((75, 75))
      sprite1.image.fill((255, 0, 0))
      sprite1.rect = pygame.Rect(*window.get_rect().center, 0, 0).inflate(75, 75)
      sprite2 = pygame.sprite.Sprite()
      sprite2.image = pygame.Surface((75, 75))
      sprite2.image.fill((0, 255, 0))
      sprite2.rect = pygame.Rect(*window.get_rect().center, 0, 0).inflate(75, 75)
      
      all_group = pygame.sprite.Group([sprite2, sprite1])
      test_group = pygame.sprite.Group(sprite2)
      
      run = True
      while run:
          for event in pygame.event.get():
              if event.type == pygame.QUIT:
                  run = False
      
          sprite1.rect.center = pygame.mouse.get_pos()
          collide = pygame.sprite.spritecollide(sprite1, test_group, False)
      
          window.fill(0)
          all_group.draw(window)
          for s in collide:
              pygame.draw.rect(window, (255, 255, 255), s.rect, 5, 1)
          pygame.display.flip()
      
      pygame.quit()
      exit()
      

    For a collision with masks see How can I made a collision mask? or Pygame mask collision

    See also Collision and Intersection

    • pygame.sprite.spritecollide() / collide_circle

      import pygame
      
      pygame.init()
      window = pygame.display.set_mode((250, 250))
      
      sprite1 = pygame.sprite.Sprite()
      sprite1.image = pygame.Surface((80, 80), pygame.SRCALPHA)
      pygame.draw.circle(sprite1.image, (255, 0, 0), (40, 40), 40)
      sprite1.rect = pygame.Rect(*window.get_rect().center, 0, 0).inflate(40, 40)
      sprite2 = pygame.sprite.Sprite()
      sprite2.image = pygame.Surface((80, 89), pygame.SRCALPHA)
      pygame.draw.circle(sprite2.image, (0, 255, 0), (40, 40), 40)
      sprite2.rect = pygame.Rect(*window.get_rect().center, 0, 0).inflate(80, 80)
      
      all_group = pygame.sprite.Group([sprite2, sprite1])
      test_group = pygame.sprite.Group(sprite2)
      
      run = True
      while run:
          for event in pygame.event.get():
              if event.type == pygame.QUIT:
                  run = False
      
          sprite1.rect.center = pygame.mouse.get_pos()
          collide = pygame.sprite.spritecollide(sprite1, test_group, False, pygame.sprite.collide_circle)
      
          window.fill(0)
          all_group.draw(window)
          for s in collide:
              pygame.draw.circle(window, (255, 255, 255), s.rect.center, s.rect.width // 2, 5)
          pygame.display.flip()
      
      pygame.quit()
      exit()
      


    What does this all mean for your code?

    pygame.Surface.get_rect.get_rect() returns a rectangle with the size of the Surface object, that always starts at (0, 0) since a Surface object has no position. The position of the rectangle can be specified by a keyword argument. For example, the center of the rectangle can be specified with the keyword argument center. These keyword argument are applied to the attributes of the pygame.Rect before it is returned (see pygame.Rect for a full list of the keyword arguments).
    See *Why is my collision test always returning 'true' and why is the position of the rectangle of the image always wrong (0, 0)?

    You don't need the x and y attributes of Sprite and Bullet at all. Use the position of the rect attribute instead:

    #Define the sprite class
    class Sprite:
        def __init__(self, x, y, name):
            self.image = pygame.image.load(name)
            self.rect = self.image.get_rect(topleft = (x, y))
    
        def render(self):
            window.blit(self.image, self.rect)
    
    # Define the bullet class to create bullets
    class Bullet:
        def __init__(self, x, y):
            self.bullet = pygame.image.load("user_bullet.BMP")
            self.rect = self.bullet.get_rect(topleft = (x + 23, y))
    
        def render(self):
            window.blit(self.bullet, self.rect)
    

    Use pygame.Rect.colliderect() to detect collisions between instances of Sprite and Bullet.
    See How to detect collisions between two rectangular objects or images in pygame:

    my_sprite = Sprite(sx, sy, name)
    my_bullet = Bullet(by, by)
    
    while True:
        # [...]
    
        if my_sprite.rect.colliderect(my_bullet.rect):
            printe("hit")
    

    这篇关于如何在pygame中检测碰撞?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!

    08-31 09:51