2016-02-15 2 views
-1

было бы действительно удивительно, если бы вы могли помочь нам с этой проблемой. В настоящее время мы работаем над игровым проектом в школе, и мы хотим создать игру в лабиринте, подобную Bomberman.Pygame Collision с переменной скоростью

Проблема заключается в следующем: положение и скорость бомб зависят от мыши, которая отслеживается с использованием значений поплавка, но слишком высоко, если вы нажимаете далеко, чтобы она могла пропустить обнаружение столкновения, потому что она просто идет слишком быстро. Теперь есть некоторые другие странные ошибки, когда вы выстраиваете бомбу с нижней частью блока и другими столкновениями.

Является ли метод коллапсом ошибки? Нужно ли нам проверять каждый сайт или какие-либо более эффективные решения этой проблемы. Мы также думали о том, чтобы использовать только 4 направления, но даже это не получилось.

Я действительно надеюсь, что кто-то там может помочь.

class Block(pygame.sprite.Sprite): 

    def __init__(self,color = SCHWARZ, width = 40, height = 40, movable = 0): 

     super().__init__() 

     self.width = width 
     self.height = height 

     self.color = color 

     self.movable = movable 

     self.image = pygame.Surface((width,height)) 
     self.image.fill(color) 

     self.properties() 

    def properties(self): 

     self.rect = self.image.get_rect() 

     self.origin_x = self.rect.centerx 
     self.origin_y = self.rect.centery 

    def set_pos(self, x, y): 
     self.rect.x = x 
     self.rect.y = y 

    def render(self,window): 
     pygame.draw.rect(window,self.color,(self.rect.x,self.rect.y,self.width,self.height)) 

class Bomb(Block): 

    def __init__(self,player, target_x, target_y,countdown,zeit,color = BLAU): 

     super().__init__(color, width = 20, height = 20) 
     self.target_x = round(target_x) 
     self.target_y = round(target_y) 

     self.countdown = countdown 
     self.zeit = zeit 

     self.player_x = player.rect.left + player.width/2 
     self.player_y = player.rect.top + player.height/2 

     self.set_pos(player.rect.center[0]-self.width/2,player.rect.center[1]-self.height/2) 
     self.truepos = list(self.rect.center) 

     self.setspeed(3) 

    def setspeed(self,factor): 

     self.speed_x = (self.target_x - self.player_x)/100 
     self.speed_y = (self.target_y - self.player_y)/100 




     """self.direction = [0,0] 

     if self.target_x - self.player_x < 0: 
      self.direction[0] = -1 
     elif self.target_x - self.player_x > 0: 
      self.direction[0] = 1 
     if self.target_y - self.player_y > 0: 
      self.direction[1] = 1 
     elif self.target_y - self.player_y < 0: 
      self.direction[1] = -1 

     self.speed_x = self.direction[0]* factor 
     self.speed_y = self.direction[1]* factor 

     print(self.speed_x) 
     print(self.speed_y)""" 

    def move(self): 

     if self.speed_x != 0: 
      self.collision() 
     if self.speed_y != 0: 
      self.collision() 

    def update(self): 

     self.move() 

     if self.countdown > 0: 
      self.countdown -= self.zeit 

     elif self.countdown <= 0: 
      bomblist_list.remove(self) 

    def collision(self): 
     for block in block_list: 
      if block.movable != 1: 
       if self.rect.colliderect(block.rect): 
        self.distance = [abs(block.rect.centerx - (self.truepos[0] + self.speed_x)), abs(block.rect.centery - (self.truepos[1] + self.speed_y))] 
        if self.distance[0] > self.distance[1]: 
         if self.speed_x < 0: 
          self.rect.left = block.rect.right - self.speed_x 
         elif self.speed_x > 0: 
          self.rect.right = block.rect.left -self.speed_x 
         self.speed_x = -self.speed_x 
        elif self.distance[0] < self.distance[1]: 
         if self.speed_y < 0: 
          self.rect.top = block.rect.bottom - self.speed_y 
         elif self.speed_y > 0: 
          self.rect.bottom = block.rect.top - self.speed_y 
         self.speed_y = -self.speed_y 



     self.truepos[0] += self.speed_x 
     self.truepos[1] += self.speed_y 
     self.rect.center = self.truepos 

# -------- Main Program Loop ----------- 
while not done: 
    clock.tick(fps) 
    millisekunde = float(clock.tick(fps)) 
    zeit = millisekunde /500 
    vergangen += zeit 

    # --- Main event loop 
    for event in pygame.event.get(): # User macht irgendwas 

     if event.type == pygame.QUIT: # Wenn der User Quit klickt 
      done = True # Verlässt die Schleife 

     elif event.type == pygame.KEYDOWN: 
      pass 



      #if event.key == pygame.K_UP: 
       #if e 


     elif event.type == pygame.MOUSEBUTTONDOWN: 
      if event.button == 1: 
       mx,my = pygame.mouse.get_pos() 
       bomb = Bomb(player,mx,my,3,zeit) 
       bomblist_list.append(bomb) 
       planted = True 

    keys = pygame.key.get_pressed() 

    if keys[pygame.K_RIGHT]: 
      player.move(speedx,0) 
    if keys[pygame.K_LEFT]: 
      player.move(-speedx,0) 
    if keys[pygame.K_DOWN]: 
      player.move(0,speedy) 
    if keys[pygame.K_UP]: 
      player.move(0,-speedy) 

    if planted: 
     for bomb in bomblist_list: 
      bomb.update() 

    screen.fill(SCHWARZ) 

    for block in block_list: 
     block.render(screen) 

    if planted: 
     for bomb in bomblist_list: 
      bomb.render(screen) 

    pygame.draw.rect(screen,red,player.rect) 

    pygame.display.update() 

pygame.quit() 
+2

Добро пожаловать в StackOverflow. Прочтите и следуйте инструкциям по отправке в справочной документации. [Минимальный, полный, проверяемый пример] (http://stackoverflow.com/help/mcve) применим здесь. Мы не можем эффективно помочь вам, пока вы не опубликуете свой код и не сможете точно описать проблему. «Слишком высокий уровень» и «некоторые другие странные ошибки» не представляют собой описание проблемы. – Prune

ответ

0

При проверке столкновения на быстро движущихся предметов, которые могут передать объект в одном кадре, то, что вы хотите сделать, это сохранить это положение на последнем кадре и получить его положение на текущем кадре. С помощью этого вы можете проверить, не столкнулось ли оно с чем-либо между последним и текущим фреймом.

Затем вы можете изменить его положение, вернув его туда, где он должен был остановиться и впоследствии нарисовать объект.