Python : comment appliquer un methode sur un groupe de sprit

kirito -  
yg_be Messages postés 23437 Date d'inscription   Statut Contributeur Dernière intervention   -

Bonjour,

Je suis un débutant, et j'essaye de coder un jeu de block breaker sans tutoriel.

Je code sur python avec pycharm et le module pygame.

Dans mon code, je crée un groupe de sprite, ce sont des blocks avec chacun une couleur, un nombre de point de vie ect...  Seulement j'ai une méthode pour generé automatiquement ces blocks, ils ne sont donc pas définit individuelement.

Dans une autre partie de mon code, j'ai crée un balle qui rebondit sur une plateforme que le joueur contrôle, et rebondit aussi sur les blocks.

Je n'arrive pas a appliqué une méthode au blocks touchés pour qu'il perdent 1 de vie.

Soit ma méthode ne s'applique pas du tout, soit elle s'applique sur tous les blocks.

Pouvez-vous m'expliquer comment faire que que cette méthode s'applique uniquement sur les blocks touchés par la balle.

Si vous avez besoins de partie de code ou de tout le code faite le moi savoir je vous le donnerais volontiers.

3 réponses

  1. yg_be Messages postés 23437 Date d'inscription   Statut Contributeur Dernière intervention   Ambassadeur 1 588
     

    bonjour,

    Il est en effet préférable de partager ton code, de préférence un code que nous puissions tester.  Tiens compte de ceci: https://codes-sources.commentcamarche.net/faq/11288-poster-un-extrait-de-code

    1
    1. kirito__38 Messages postés 4 Statut Membre
       

      Je suis la meme personne seulement entre temps j'ai creé un compte

      Mon code est diviser en plusieurs fichier 

      je vous envoie ces fichiers un par un.

      import pygame
      import random
      
      import block
      from game import Game
      from screen import screen
      pygame.init()
      pygame.display.set_caption('game of bounce')
      background = pygame.image.load('assets/background.jpg')
      background = pygame.transform.scale(background, (1300, 900))
      running = True
      game = Game()
      game.ball.rect.y += random.randint(500, 650)
      game.ball.rect.x += random.randint(9, 1020)
      game.ball.forward()
      if game.ball.rect.x < 500:
          game.ball.a = 1
      else:
          game.ball.a = 2
      
      game.last_rect_x = 155
      game.last_rect_y = 300
      
      while running:
      
          for blocks in game.all_blocks:
              blocks.print_health()
              print(blocks.health)
      
          if game.check_collide(game.ball, game.all_blocks):
              for blocks in game.all_blocks:
                  blocks.damage()
      
          if game.number_of_block < 13:
              game.block_color_number = random.randint(1, 6)
              game.new_blocks()
      
          if game.number_of_block == 13:
              game.last_rect_y += 55
              game.last_rect_x = 155
              game.block_color_number = random.randint(1, 6)
              game.new_blocks()
      
          if 13 < game.number_of_block < 26:
              game.block_color_number = random.randint(1, 6)
              game.new_blocks()
      
          if game.have_rebounce:
              if game.ball.rect.x < 500:
                  game.ball.a = 3
              else:
                  game.ball.a = 4
      
          if game.ball.rect.y > 450:
              game.have_rebounce = False
              game.ball.b = False
      
          if game.ball.rect.y >= 890:
              running = False
      
          screen.blit(background, (0, -50))
      
          for event in pygame.event.get():
              if event.type == pygame.QUIT:
                  running = False
                  pygame.quit()
              elif event.type == pygame.KEYDOWN:
                  game.pressed[event.key] = True
              elif event.type == pygame.KEYUP:
                  game.pressed[event.key] = False
      
          game.update()
          pygame.display.flip()

      ceci etait mon premier fichier "main"

      ensuite voila le fichier " game " :

      import pygame.sprite
      from Player import Player
      from screen import screen
      from ball import Ball
      from block import Block
      import random
      
      
      class Game:
          def __init__(self):
              self.player = Player(self)
              self.ball = Ball(self)
              # self.block = Block(10, 'yellow', self)
              self.all_blocks = pygame.sprite.Group()
              self.pressed = {}
              self.all_player = pygame.sprite.Group()
              self.all_balls = pygame.sprite.Group()
              self.player.add(self.all_player)
              self.have_rebounce = False
              self.have_rebounce_2 = 0
              self.score = 0
              self.number_of_block = 0
              self.block_color = 'null'
              self.block_health = 0
              self.block_color_number = 0
              self.last_rect_x = 0
              self.last_rect_y = 0
              self.font = pygame.font.SysFont("oriyamn", 33)
              self.score_text = self.font.render(f"Score : {self.score}", 1, (255, 0, 0))
      
          def update(self):
      
              screen.blit(self.ball.image, self.ball.rect)
              screen.blit(self.player.image, self.player.rect)
              self.all_blocks.draw(screen)
              if self.pressed.get(pygame.K_RIGHT) and self.player.rect.x < screen.get_width() - 156:
                  self.player.move_right()
              elif self.pressed.get(pygame.K_LEFT) and self.player.rect.x > 0:
                  self.player.move_left()
              self.ball.forward()
              if self.check_collide(self.player, self.all_balls) or self.check_collide(self.ball, self.all_player):
                  self.have_rebounce = True
                  self.have_rebounce = 1
                  self.ball.b = True
                  self.ball.b_2 = True
              if self.check_collide(self.ball, self.all_blocks):
                  self.score += 1
                  if self.ball.a == 1:
                      self.ball.a = 3
                  if self.ball.a == 2:
                      self.ball.a = 4
                  if self.ball.a == 3:
                      self.ball.a = 1
                  if self.ball.a == 4:
                      self.ball.a = 2
              for blocks in self.all_blocks:
                  blocks.forward()
      
              screen.blit(self.score_text, (90, 790))
      
              pygame.display.flip()
      
          def new_ball(self):
              self.all_balls.add(Ball(self))
      
          def new_blocks(self):
              if self.block_color_number == 1:
                  self.block_color = 'green'
                  self.block_health = 5
              if self.block_color_number == 2:
                  self.block_color = 'blue'
                  self.block_health = 10
              if self.block_color_number == 3:
                  self.block_color = 'yellow'
                  self.block_health = 15
              if self.block_color_number == 4:
                  self.block_color = 'orange'
                  self.block_health = 20
              if self.block_color_number == 5:
                  self.block_color = 'red'
                  self.block_health = 25
              if self.block_color_number == 6:
                  self.block_color = 'really_red'
                  self.block_health = 35
              self.all_blocks.add(Block(health=self.block_health, color=self.block_color, game=self))
              self.last_rect_x += 55
              self.number_of_block += 1
      
          def check_collide(self, sprite, group):
              return pygame.sprite.spritecollide(sprite, group, False, pygame.sprite.collide_mask)
      

       ensuite voici le fichier "ball" relatif a la balle :

      import pygame
      import random
      from Player import Player
      
      pygame.init()
      
      
      class Ball (pygame.sprite.Sprite):
          def __init__(self, game):
              super().__init__()
              self.velocity = 15
              self.game = game
              self.image = pygame.image.load('assets/ball.png')
              self.image = pygame.transform.scale(self.image, (25, 25))
              self.rect = self.image.get_rect()
              self.a = 0
              self.accelerate = 4.5
              self.b = False
              self.b_2 = False
      
          def forward(self):
              if self.rect.x >= 1055:
                  if self.a == 1:
                      self.a = 2
                  elif self.a == 3:
                      self.a = 4
              if self.rect.x <= 10:
                  if self.a == 2:
                      self.a = 1
                  elif self.a == 4:
                      self.a = 3
              if self.rect.y <= 35:
                  if self.a == 3:
                      self.a = 1
                  elif self.a == 4:
                      self.a = 2
              if self.a == 1:
                  if self.b_2:
                      self.rect.y += self.accelerate
                  self.rect.y += self.accelerate
                  self.rect.x += (self.accelerate * random.randint(1, 2))
                  self.accelerate += 1 / 1000
              elif self.a == 2:
                  if self.b_2:
                      self.rect.y += self.accelerate
                  self.rect.y += self.accelerate
                  self.rect.x -= (self.accelerate * random.randint(1, 2))
                  self.accelerate += 1 / 1000
              elif self.a == 3:
                  if self.b_2:
                      self.rect.y -= self.accelerate
                  self.rect.y -= self.accelerate
                  self.rect.x += (self.accelerate * random.randint(1, 2))
                  self.accelerate += 1 / 1000
              elif self.a == 4:
                  if self.b_2:
                      self.rect.y -= self.accelerate
                  self.rect.y -= self.accelerate
                  self.rect.x -= (self.accelerate * random.randint(1, 2))
                  self.accelerate += 1 / 1000
      

      enfin voici le fichier relatif aux blocks, nommée "block" : 

      import pygame
      
      import screen
      from ball import Ball
      
      
      class Block(pygame.sprite.Sprite):
          def __init__(self, health, color, game):
              super().__init__()
              self.health = health
              self.game = game
              self.color = color
              self.image = pygame.image.load(f'assets/blocks/{color}.png')
              self.image = pygame.transform.scale(self.image, (55, 55))
              self.rect = self.image.get_rect()
              self.pos_x = game.last_rect_x
              self.pos_y = game.last_rect_y
              self.rect.x += self.pos_x
              self.rect.y += self.pos_y
              self.font = pygame.font.SysFont("oriyamn", 30)
              self.score_health = self.font.render(f"{self.health}", 1, (255, 255, 255))
      
          def damage(self):
              self.health -= 1
      
          def print_health(self):
              screen.screen.blit(self.score_health, (self.rect.x + 13, self.rect.y))
      
          def forward(self):
              if self.game.check_collide(self, self.game.all_balls):
                  self.damage()
                  self.game.score += 1
              self.print_health()

      je vous remercie pour votre aide 

      0
      1. yg_be Messages postés 23437 Date d'inscription   Statut Contributeur Dernière intervention   1 588 > kirito__38 Messages postés 4 Statut Membre
         

        il demande aussi "screen" et "player"

        0
      2. yg_be Messages postés 23437 Date d'inscription   Statut Contributeur Dernière intervention   1 588 > kirito__38 Messages postés 4 Statut Membre
         

        qu'as-tu essayé pour tester qu'un bloc était touché?

        0
      3. kirito__38 Messages postés 4 Statut Membre > yg_be Messages postés 23437 Date d'inscription   Statut Contributeur Dernière intervention  
         

        je n'ai pas compris la question pardonnez moi

        0
  2. unoupoutou
     

    Salut, dans ton main tu fais
     

    if game.check_collide(game.ball, game.all_blocks):
        for blocks in game.all_blocks:
            blocks.damage()

    Ce qui n'est pas logique puisque que ta méthode Game.check_collide retourne la liste des sprites en collisions.

    Dons il faudrait faire un truc comme

    for block in game.check_collide(game.ball, game.all_blocks):
        block.damage()
    0
    1. kirito__38 Messages postés 4 Statut Membre
       

      merci beaucoup cependant ce la ne regle pas mon problème

      voici mon fichier "screen" :

      import pygame
      pygame.image
      
      
      screen = pygame.display.set_mode((1080, 900))

      et voila mon fichier "player":

      import pygame
      pygame.init()
      
      
      class Player(pygame.sprite.Sprite):
          def __init__(self, game):
              super().__init__()
              self.game = game
              self.image = pygame.image.load('assets/paddle.png')
              self.image = pygame.transform.scale(self.image, (150, 25))
              self.rect = self.image.get_rect()
              self.rect.y += 750
              self.rect.x += 300
              self.velocity = 15
              self.accelerate = 1.3
      
          def move_right(self):
              self.rect.x += self.velocity
      
          def move_left(self):
              self.rect.x -= self.velocity
      
      0
  3. yg_be Messages postés 23437 Date d'inscription   Statut Contributeur Dernière intervention   Ambassadeur 1 588
     

    D'où vient "pygame.sprite.collide_mask" dans la ligne 90 de game.py?

    0
    1. kirito__38 Messages postés 4 Statut Membre
       

      Cela sert a indiqué quelle sorte de collision on veut avoir, j'ai vu cela dans un tuto de graven sur pygame.J'ai reussi a crée le jeu ave le tuto, je voulais essayer d'en faire un moi meme

      0
      1. yg_be Messages postés 23437 Date d'inscription   Statut Contributeur Dernière intervention   1 588 > kirito__38 Messages postés 4 Statut Membre
         

        Peux-tu partager les images du jeu?
        Je suggère aussi que tu testes ton code.  Tu pourrais créer un petit exemple simple, statique, et l'utiliser pour tester check_collide(), en suivant la suggestion en #4.

        0