Source

Snakes / python.py

import pygame
from random import randint
from myobjects.snake import snake
from myobjects.food import food

# Settings
SCREENSIZE = (1024,768)
BGCOLOR = (0xff, 0xa5, 0x00)
FRAMERATE = 30

def playGame():
    # define the arrow keys
    arrow_keys = (pygame.K_UP, pygame.K_DOWN, pygame.K_LEFT, pygame.K_RIGHT)

    # init pygame
    pygame.init()
    game_surface = pygame.display.set_mode(SCREENSIZE)
    # set the key repeat speed
    pygame.key.set_repeat(10, 25)
    # set the caption
    pygame.display.set_caption('SNAKES!!!! - Press <Esc> to Quit, <R> to Restart')

    replay = True
    while replay:
        replay = False
        # create our snake
        python = snake(pygame.Color('purple'), 
                [randint(0,SCREENSIZE[0]), randint(0,SCREENSIZE[1])])
        python.update(game_surface)
       
        # create the bad snake
        rattle = snake(pygame.Color('grey'), 
                [randint(0,SCREENSIZE[0]), randint(0,SCREENSIZE[1])])
        rattle.update(game_surface)
        rattle_num_frames_in_dir = 0
        rattle_max_frames_in_dir = 50
        rattle_dir = arrow_keys[randint(0,3)]

        # create some food
        food_items = []
        def create_food():
            while len(food_items) < 2:
                food_items.append(food(game_surface))

        game_clock = pygame.time.Clock()
        playing = True
        while playing:
            game_clock.tick(FRAMERATE)

            # reset surface to the background color
            game_surface.fill(BGCOLOR)

            # handle events
            for e in pygame.event.get():
                if e.type == pygame.QUIT:
                    playing = False
                elif e.type == pygame.KEYDOWN:
                    if e.key == pygame.K_ESCAPE:
                        playing = False
                        replay = False
                    if e.key == pygame.K_r:
                        playing = False
                        replay = True
                    if e.key in arrow_keys:
                        python.move(e.key,game_surface)

            # always move the bad snake
            rattle_num_frames_in_dir = rattle_num_frames_in_dir + 1
            moved_rattle = rattle_num_frames_in_dir % 2 == 0
            while not moved_rattle:
                if rattle_num_frames_in_dir > rattle_max_frames_in_dir:
                    curr_dir = rattle_dir
                    while curr_dir == rattle_dir:
                        rattle_dir = arrow_keys[randint(0,3)]
                    rattle_max_frames_in_dir = randint(25,50)
                    rattle_num_frames_in_dir = 0
                moved_rattle = rattle.move(rattle_dir,game_surface)
                if not moved_rattle:
                    rattle_num_frames_in_dir = rattle_max_frames_in_dir+1

            # detect collisions with the bad snake
            for r1,r2 in ((r1,r2)
                    for r1 in python.get_rects()
                    for r2 in rattle.get_rects()):
                if r1.colliderect(r2):
                    playing = False
                    replay = gameOver(game_surface)
                    break

            # detect collisions with ourself
            if python.head_hit_body():
                playing = False
                replay = gameOver(game_surface)
                break

            # eat
            python.try_eat(food_items)
            rattle.try_eat(food_items)
            
            # replace food
            create_food()

            # update display & objects
            python.update(game_surface)
            rattle.update(game_surface)
            for f in food_items:
                f.update(game_surface)
            pygame.display.update()

    pygame.quit()

def gameOver(game_surface):
    """ Displays the game over screen. 
        Returns True if the game should restart """

    text = 'GAME OVER'
    font = pygame.font.SysFont('Tahoma', 128)
    line = font.render(text, True, (20, 20, 220))

    x_center = (SCREENSIZE[0] / 2) - (line.get_width() / 2)
    waiting = True
    while waiting:
        # reset surface to the background color
        game_surface.fill(BGCOLOR)
        game_surface.blit(line, line.get_rect().move((x_center,20)))

        # handle events
        for e in pygame.event.get():
            if e.type == pygame.QUIT:
                waiting = False
                return False
            elif e.type == pygame.KEYDOWN:
                if e.key == pygame.K_ESCAPE:
                    waiting = False
                    return False
                elif e.key == pygame.K_r:
                    waiting = False
                    return True

        pygame.display.update()

if __name__ == '__main__':
    playGame()