2016-04-29 5 views
0

Dies ist ein Schlangen-Remake. Mein Ziel war es, den Apfel nach dem Zusammenstoß mit der Schlange zufällig wieder aufzutauchen. Aus irgendeinem Grund scheint die collide_rect-Funktion zu denken, dass sie ständig kollidieren, nachdem ich das Spiel gestartet habe.Warum kollidieren in diesem Szenario nicht kollidieren? Das Spiel druckt weiter "Collided!" auch wenn sich die beiden Sprites nicht berühren?

Alle anderen Spitzen sauber dieses Chaos zu helfen, sind auch willkommen:

import pygame 
import time 
import random 

pygame.init() 

WHITE = (pygame.Color("white")) 
BLACK = ( 0, 0, 0) 
RED = (245, 0, 0) 
TURQ = (pygame.Color("turquoise")) 
GREEN = ( 0, 155, 0) 
GREY = (90, 90, 90) 
SCREEN = (800, 600) 
gameDisplay = pygame.display.set_mode(SCREEN) 
#Set the window title and picture 
pygame.display.set_caption('Block Worm') 
ICON = pygame.image.load("apple10pix.png") 

pygame.display.set_icon(ICON) 
CLOCK = pygame.time.Clock() 
FPS = 20 
FONT = pygame.font.SysFont("arial", 25) 
APPLE_SIZE = 10 
TINY_FONT = pygame.font.SysFont("candara", 15) 
SMALL_FONT = pygame.font.SysFont("candara", 25) 
MED_FONT = pygame.font.SysFont("candara", 50) 
LARGE_FONT = pygame.font.SysFont("krabbypatty", 75) 
HUGE_FONT = pygame.font.SysFont("krabbypatty", 150) 
IMG = pygame.image.load("snakehead.png") 
APPLE_IMG = pygame.image.load("apple10pix.png") 
DIRECTION = "up"  

def pause(): 
    paused = True 
    message_to_screen("Paused", 
         BLACK, 
         Y_DISPLACE = -100, 
         size = "huge") 
    message_to_screen("Press C to continue or Q to quit.", 
         BLACK, 
         Y_DISPLACE = 25) 
    pygame.display.update() 
    while paused: 
     for event in pygame.event.get(): 
      if event.type == pygame.QUIT: 
       pygame.quit() 
       quit() 
      if event.type == pygame.KEYDOWN: 
       if event.key in (pygame.K_c, pygame.K_p): 
        paused = False 
       elif event.key in(pygame.K_q, pygame.K_ESCAPE): 
        pygame.quit() 
        quit() 
     CLOCK.tick(5) 

def score(score): 
    text = SMALL_FONT.render("Score: " + str(score), True, BLACK) 
    gameDisplay.blit(text, [0, 0]) 

def game_intro(): 
    intro = True 
    while intro: 
     for event in pygame.event.get(): 
      if event.type == pygame.QUIT: 
       pygame.quit() 
       quit() 
      if event.type == pygame.KEYDOWN: 
       if event.key == pygame.K_c: 
        intro = False 
       if event.key in (pygame.K_q, pygame.K_ESCAPE): 
        pygame.quit() 
        quit() 
     gameDisplay.fill(WHITE) 
     message_to_screen("Welcome to", 
          GREEN, 
          Y_DISPLACE = -170, 
          size = "large") 
     message_to_screen("Block Worm", 
          GREEN, 
          Y_DISPLACE = -50, 
          size = "huge") 
     message_to_screen("The objective of the game is to eat apples.", 
          BLACK, 
          Y_DISPLACE = 36, 
          size = "tiny") 
     message_to_screen("The more apples you eat the longer you get.", 
          BLACK, 
          Y_DISPLACE = 68, 
          size = "tiny") 
     message_to_screen("If you run into yourself or the edges, you die.", 
          BLACK, 
          Y_DISPLACE = 100, 
          size = "tiny") 
     message_to_screen("Press C to play or Q to quit.", 
          GREY, 
          Y_DISPLACE = 210,) 
     pygame.display.update() 
     CLOCK.tick(FPS) 

def text_objects(text, color, size): 
    if size == "tiny": 
     TEXT_SURFACE = TINY_FONT.render(text, True, color) 
    elif size == "small": 
     TEXT_SURFACE = SMALL_FONT.render(text, True, color) 
    elif size == "medium": 
     TEXT_SURFACE = MED_FONT.render(text, True, color) 
    elif size == "large": 
     TEXT_SURFACE = LARGE_FONT.render(text, True, color) 
    elif size == "huge": 
     TEXT_SURFACE = HUGE_FONT.render(text, True, color) 
    return TEXT_SURFACE, TEXT_SURFACE.get_rect() 

def message_to_screen(msg, color, Y_DISPLACE = 0, size = "small"): 
    TEXT_SURF, TEXT_RECT = text_objects(msg, color, size) 
    TEXT_RECT.center = (SCREEN[0]/2), (SCREEN[1]/2) + Y_DISPLACE 
    gameDisplay.blit(TEXT_SURF, TEXT_RECT) 

class Snake(pygame.sprite.Sprite): 
    def __init__(self, image, size, trail, start_size): 
     pygame.sprite.Sprite.__init__(self) 
     self.image = image 
     self.size = size 
     self.trail = trail 
     self.start_size = start_size 
     self.rect = self.image.get_rect() 
     if DIRECTION == "right": 
      HEAD = pygame.transform.rotate(self.image, 270) 
     elif DIRECTION == "left": 
      HEAD = pygame.transform.rotate(self.image, 90) 
     elif DIRECTION == "down": 
      HEAD = pygame.transform.rotate(self.image, 180) 
     else: 
      HEAD = image 
     gameDisplay.blit(HEAD, (self.trail[-1][0], self.trail[-1][1])) 
     for XnY in self.trail[:-1]: 
      pygame.draw.rect(gameDisplay, GREEN, [XnY[0], XnY[1], self.size, self.size]) 

class Apple(pygame.sprite.Sprite): 
    def __init__(self, image): 
     pygame.sprite.Sprite.__init__(self) 
     self.image = image 
     self.rect = self.image.get_rect() 
     self.size = self.rect.width 
     gameDisplay.blit(self.image, (100, 100)) 

    def random_location(self): 
     self.rect.x = random.randrange(0, (SCREEN[0] - 10), 10) 
     self.rect.y = random.randrange(0, (SCREEN[1]- 10), 10) 
     gameDisplay.blit(self.image, (self.rect.x, self.rect.y)) 





def gameLoop(): 
    global DIRECTION 
    DIRECTION = "up" 
    gameExit = False 
    gameOver = False 
    SCORE = 0 

    player_snake_trail = [] # Where the snake head has been. 
    enemy_snake_trail = [] # If I create an AI snake. 
    start_length = 1 

    lead_x = (SCREEN[0]/2) 
    lead_y = (SCREEN[1] - (SCREEN[1]/5)) 
    move_speed = 10 
    move_speed_neg = move_speed * -1 
    lead_x_change = 0 
    lead_y_change = -move_speed 

    while not gameExit: 
     if gameOver == True: 
      message_to_screen("Game over", 
           RED, 
           Y_DISPLACE = -50, 
           size = "huge") 
      message_to_screen("Press C to play again or Q to quit.", 
           BLACK, 
           Y_DISPLACE = 50, 
           size = "small") 
      pygame.display.update() 
     while gameOver == True: 
      for event in pygame.event.get(): 
       if event.type == pygame.QUIT: 
        gameExit = True 
        gameOver = False 
       elif event.type == pygame.KEYDOWN: 
        if event.key == pygame.K_q: 
         gameOver = False 
         gameExit = True 
        elif event.key == pygame.K_c: 
         gameLoop() 

     for event in pygame.event.get(): 
      if event.type == pygame.QUIT: 
       gameExit = True 
      elif event.type == pygame.KEYDOWN: 
       if event.key in (pygame.K_LEFT, pygame.K_a): 
        lead_x_change = move_speed_neg 
        lead_y_change = 0 
        DIRECTION = "left" 
       elif event.key in (pygame.K_RIGHT, pygame.K_d): 
        lead_x_change = move_speed 
        lead_y_change = 0 
        DIRECTION = "right" 
       elif event.key in (pygame.K_UP, pygame.K_w): 
        lead_y_change = move_speed_neg 
        lead_x_change = 0 
        DIRECTION = "up" 
       elif event.key in (pygame.K_DOWN, pygame.K_s): 
        lead_y_change = move_speed 
        lead_x_change = 0 
        DIRECTION = "down" 
       elif event.key in (pygame.K_p, pygame.K_ESCAPE): 
        pause() 

     # If the snake goes beyond the screen borders the game will end. 
     if lead_x >= SCREEN[0] or lead_x < 0 or lead_y >= SCREEN[1] or lead_y <0: 
      gameOver = True 

     lead_x += lead_x_change 
     lead_y += lead_y_change 

     gameDisplay.fill(WHITE) 

     # Draw the apple on screen 
     red_apple = Apple(APPLE_IMG) 

     # Draw the snake on screen 
     SNAKE_HEAD = [] 
     SNAKE_HEAD.append(lead_x) 
     SNAKE_HEAD.append(lead_y) 
     player_snake_trail.append(SNAKE_HEAD) 
     # If you hit yourself, game over. 
     if SNAKE_HEAD in player_snake_trail[:-1]: 
      gameOver = True 
     if len(player_snake_trail) > start_length: 
      del player_snake_trail[0] 

     player_snake = Snake(IMG, 10, player_snake_trail, start_length) 
     if pygame.sprite.collide_rect(player_snake, red_apple) == True: 
      print("Collided!") 

##   start_length += 1 
##   SCORE += 1 
##   red_apple.random_location() 

     # If the snake eats the apple 
     # Old code below, needs to be rewritten. Disregard. 
##  if APPLE_RECT.collidepoint(lead_x, lead_y) == True: 
##   randAppleX, randAppleY = randAppleGen() 
##   start_length += 1 
##   SCORE += 1 

     score(SCORE) 

     pygame.display.update() 
     CLOCK.tick(FPS) 
    pygame.quit() 
    quit() 

game_intro() 
gameLoop() 
+0

Warum zeichnen Sie die Sprites in den Init-Methoden? Ich denke, du musst schauen, wie man Sprites richtig benutzt. Erstelle sie einmal und benutze die 'update()' Funktion, um sie herum zu bewegen und das draw() um sie zu blitten. – xthestreams

+0

Sollten Sie random_location() im Apple-Konstruktor aufrufen? Auch das ist eine Menge Code. Sie sollten weniger posten, wenn Sie erwarten, dass Menschen Ihnen tatsächlich helfen können. – Falmarri

+0

Sie sollten Ihren Code vereinfachen, damit es Ihnen leichter fällt, Ihnen zu helfen. Wenn Sie Ihren Code vereinfachen, können Sie möglicherweise auch nachvollziehen, wo der Fehler aufgetreten ist. Haben Sie versucht, die Koordinaten der Objekte auszudrucken, wenn Sie eine Kollision feststellen? Das sollte dein erster Debugging-Schritt sein. –

Antwort

0

Wenn Sie die Rects in der Konstrukteurs für den Apfel und Schlange den Kopf gesetzt, sie haben x und y-Koordinaten von 0. Sie müssen die Retrakte einstellen und sie aktualisieren, wenn sich die Schlange bewegt. Ich habe ihnen eine set_rect-Methode hinzugefügt. Ich habe auch die Auslosung von apple.random_location zu einer eigenen Methode verschoben. Der Code sollte wie folgt aussehen:

init() 
run() 

und in Lauf:

check_events() 
update_snake() 
collision_check() 
draw_things() 
clock.tick(FPS) 

Hier wird der veränderte Code ist, versuchen Sie es, wie oben in Abschnitte aufzuteilen.

import pygame 
import time 
import random 

pygame.init() 

WHITE = (pygame.Color("white")) 
BLACK = ( 0, 0, 0) 
RED = (245, 0, 0) 
TURQ = (pygame.Color("turquoise")) 
GREEN = ( 0, 155, 0) 
GREY = (90, 90, 90) 
SCREEN = (800, 600) 
gameDisplay = pygame.display.set_mode(SCREEN) 
#Set the window title and picture 
pygame.display.set_caption('Block Worm') 
ICON = pygame.Surface((10,10)) #pygame.image.load("apple10pix.png") 

pygame.display.set_icon(ICON) 
CLOCK = pygame.time.Clock() 
FPS = 20 
FONT = pygame.font.SysFont("arial", 25) 
APPLE_SIZE = 10 
TINY_FONT = pygame.font.SysFont("candara", 15) 
SMALL_FONT = pygame.font.SysFont("candara", 25) 
MED_FONT = pygame.font.SysFont("candara", 50) 
LARGE_FONT = pygame.font.SysFont("krabbypatty", 75) 
HUGE_FONT = pygame.font.SysFont("krabbypatty", 150) 
IMG = pygame.Surface((10,10)) #pygame.image.load("snakehead.png") 
APPLE_IMG = pygame.Surface((10,10)) #pygame.image.load("apple10pix.png") 
DIRECTION = "up"  

def pause(): 
    paused = True 
    message_to_screen("Paused", 
         BLACK, 
         Y_DISPLACE = -100, 
         size = "huge") 
    message_to_screen("Press C to continue or Q to quit.", 
         BLACK, 
         Y_DISPLACE = 25) 
    pygame.display.update() 
    while paused: 
     for event in pygame.event.get(): 
      if event.type == pygame.QUIT: 
       pygame.quit() 
       quit() 
      if event.type == pygame.KEYDOWN: 
       if event.key in (pygame.K_c, pygame.K_p): 
        paused = False 
       elif event.key in(pygame.K_q, pygame.K_ESCAPE): 
        pygame.quit() 
        quit() 
     CLOCK.tick(5) 

def score(score): 
    text = SMALL_FONT.render("Score: " + str(score), True, BLACK) 
    gameDisplay.blit(text, [0, 0]) 

def game_intro(): 
    intro = True 
    while intro: 
     for event in pygame.event.get(): 
      if event.type == pygame.QUIT: 
       pygame.quit() 
       quit() 
      if event.type == pygame.KEYDOWN: 
       if event.key == pygame.K_c: 
        intro = False 
       if event.key in (pygame.K_q, pygame.K_ESCAPE): 
        pygame.quit() 
        quit() 
     gameDisplay.fill(WHITE) 
     message_to_screen("Welcome to", 
          GREEN, 
          Y_DISPLACE = -170, 
          size = "large") 
     message_to_screen("Block Worm", 
          GREEN, 
          Y_DISPLACE = -50, 
          size = "huge") 
     message_to_screen("The objective of the game is to eat apples.", 
          BLACK, 
          Y_DISPLACE = 36, 
          size = "tiny") 
     message_to_screen("The more apples you eat the longer you get.", 
          BLACK, 
          Y_DISPLACE = 68, 
          size = "tiny") 
     message_to_screen("If you run into yourself or the edges, you die.", 
          BLACK, 
          Y_DISPLACE = 100, 
          size = "tiny") 
     message_to_screen("Press C to play or Q to quit.", 
          GREY, 
          Y_DISPLACE = 210,) 
     pygame.display.update() 
     CLOCK.tick(FPS) 

def text_objects(text, color, size): 
    if size == "tiny": 
     TEXT_SURFACE = TINY_FONT.render(text, True, color) 
    elif size == "small": 
     TEXT_SURFACE = SMALL_FONT.render(text, True, color) 
    elif size == "medium": 
     TEXT_SURFACE = MED_FONT.render(text, True, color) 
    elif size == "large": 
     TEXT_SURFACE = LARGE_FONT.render(text, True, color) 
    elif size == "huge": 
     TEXT_SURFACE = HUGE_FONT.render(text, True, color) 
    return TEXT_SURFACE, TEXT_SURFACE.get_rect() 

def message_to_screen(msg, color, Y_DISPLACE = 0, size = "small"): 
    TEXT_SURF, TEXT_RECT = text_objects(msg, color, size) 
    TEXT_RECT.center = (SCREEN[0]/2), (SCREEN[1]/2) + Y_DISPLACE 
    gameDisplay.blit(TEXT_SURF, TEXT_RECT) 

class Snake(pygame.sprite.Sprite): 
    def __init__(self, image, size, trail, start_size): 
     pygame.sprite.Sprite.__init__(self) 
     self.image = image 
     self.size = size 
     self.trail = trail 
     self.start_size = start_size 
     self.rect = self.image.get_rect() 
     if DIRECTION == "right": 
      HEAD = pygame.transform.rotate(self.image, 270) 
     elif DIRECTION == "left": 
      HEAD = pygame.transform.rotate(self.image, 90) 
     elif DIRECTION == "down": 
      HEAD = pygame.transform.rotate(self.image, 180) 
     else: 
      HEAD = image 
     gameDisplay.blit(HEAD, (self.trail[-1][0], self.trail[-1][1])) 
     for XnY in self.trail[:-1]: 
      pygame.draw.rect(gameDisplay, GREEN, [XnY[0], XnY[1], self.size, self.size]) 

    def set_rect(self, rect): 
     self.rect = rect 

class Apple(pygame.sprite.Sprite): 
    def __init__(self, image): 
     pygame.sprite.Sprite.__init__(self) 
     self.image = image 
     self.random_location() 
     self.size = self.rect.width 
     gameDisplay.blit(self.image, (100, 100)) 

    def random_location(self): 

     x = random.randrange(0, (SCREEN[0] - 10), 10) 
     y = random.randrange(0, (SCREEN[1]- 10), 10) 
     self.rect = pygame.Rect(x,y, 10, 10) 
     print "apple rect =", 
     print self.rect 

    def draw(self): 
     gameDisplay.blit(self.image, (self.rect.x, self.rect.y)) 




def gameLoop(): 
    global DIRECTION 
    DIRECTION = "up" 
    gameExit = False 
    gameOver = False 
    SCORE = 0 

    player_snake_trail = [] # Where the snake head has been. 
    enemy_snake_trail = [] # If I create an AI snake. 
    start_length = 1 

    lead_x = (SCREEN[0]/2) 
    lead_y = (SCREEN[1] - (SCREEN[1]/5)) 
    move_speed = 10 
    move_speed_neg = move_speed * -1 
    lead_x_change = 0 
    lead_y_change = -move_speed 


    red_apple = Apple(APPLE_IMG) 

    while not gameExit: 
     if gameOver == True: 
      message_to_screen("Game over", 
           RED, 
           Y_DISPLACE = -50, 
           size = "huge") 
      message_to_screen("Press C to play again or Q to quit.", 
           BLACK, 
           Y_DISPLACE = 50, 
           size = "small") 
      pygame.display.update() 
     while gameOver == True: 
      for event in pygame.event.get(): 
       if event.type == pygame.QUIT: 
        gameExit = True 
        gameOver = False 
       elif event.type == pygame.KEYDOWN: 
        if event.key == pygame.K_q: 
         gameOver = False 
         gameExit = True 
        elif event.key == pygame.K_c: 
         gameLoop() 

     for event in pygame.event.get(): 
      if event.type == pygame.QUIT: 
       gameExit = True 
      elif event.type == pygame.KEYDOWN: 
       if event.key in (pygame.K_LEFT, pygame.K_a): 
        lead_x_change = move_speed_neg 
        lead_y_change = 0 
        DIRECTION = "left" 
       elif event.key in (pygame.K_RIGHT, pygame.K_d): 
        lead_x_change = move_speed 
        lead_y_change = 0 
        DIRECTION = "right" 
       elif event.key in (pygame.K_UP, pygame.K_w): 
        lead_y_change = move_speed_neg 
        lead_x_change = 0 
        DIRECTION = "up" 
       elif event.key in (pygame.K_DOWN, pygame.K_s): 
        lead_y_change = move_speed 
        lead_x_change = 0 
        DIRECTION = "down" 
       elif event.key in (pygame.K_p, pygame.K_ESCAPE): 
        pause() 

     # If the snake goes beyond the screen borders the game will end. 
     if lead_x >= SCREEN[0] or lead_x < 0 or lead_y >= SCREEN[1] or lead_y <0: 
      gameOver = True 

     lead_x += lead_x_change 
     lead_y += lead_y_change 

     gameDisplay.fill(WHITE) 

     # Draw the snake on screen 
     SNAKE_HEAD = [] 
     SNAKE_HEAD.append(lead_x) 
     SNAKE_HEAD.append(lead_y) 
     player_snake_trail.append(SNAKE_HEAD) 

     # draw the apple on the screen 
     red_apple.draw() 

     # If you hit yourself, game over. 
     if SNAKE_HEAD in player_snake_trail[:-1]: 
      gameOver = True 
     if len(player_snake_trail) > start_length: 
      del player_snake_trail[0] 

     player_snake = Snake(IMG, 10, player_snake_trail, start_length) 
     player_snake.set_rect(pygame.Rect(lead_x, lead_y, 10, 10)) 

     if pygame.sprite.collide_rect(player_snake, red_apple) == True: 
      print("Collided!") 

      start_length += 1 
      SCORE += 1 
      red_apple.random_location() 

     # If the snake eats the apple 
     # Old code below, needs to be rewritten. Disregard. 
##  if APPLE_RECT.collidepoint(lead_x, lead_y) == True: 
##   randAppleX, randAppleY = randAppleGen() 
##   start_length += 1 
##   SCORE += 1 

     score(SCORE) 

     pygame.display.update() 
     CLOCK.tick(FPS) 
    pygame.quit() 
    quit() 

game_intro() 
gameLoop() 
Verwandte Themen