Python 'Breakout!' code

Week 5

Here's all the code for the platform game, as it should be at the start of Week 4. Your code may not look exactly the same: maybe you used different variable names, put things in a different order, or missed out the comment tags.

Things written in green are the first things to complete today, getting the score to go up, and the lives to go down.

The bits in red will let you display a game over/start screen, which dramatically improves the way the game feels.


# Screen related variables and constants SCREEN_WIDTH = 400 SCREEN_HEIGHT = 400 # Game related variables and constants score = 0 lives = 3 game_state = 'ready' # Variables for the start button start_X = 150 start_y = 100 start_w = 100 start_h = 30 # Bat related variables and constants bat_x = 120 bat_y = 0 bat_vel_x = 0 BAT_W = 60 BAT_H = 15 # Ball related variables and constants ball_x = 180 ball_y = 50 ball_vel_x = 2 ball_vel_y = 2 BALL_D = 15 # Wall related variables and constants BRICK_W = 40 BRICK_H = 15 NUM_BRICKS_IN_ROW = 9 NUM_BRICK_ROWS = 4 bricks = [] BRICK_COLOURS = ['red','green','yellow','blue'] BRICK_SCORES = [1, 2, 3, 4] def setup(): global SCREEN_WIDTH, SCREEN_HEIGHT global NUM_BRICKS_IN_ROW, NUM_BRICK_ROWS global bricks # Create the screen canvas at the specified width and height createCanvas(SCREEN_WIDTH,SCREEN_HEIGHT) # Set the frame refresh rate frameRate(60) create_wall() def draw(): global SCREEN_WIDTH, SCREEN_HEIGHT, score, lives, game_state global start_button_X, start_button_y, start_button_w, start_button_h global ball_x, ball_y, ball_vel_x, ball_vel_y, BALL_D global bat_x, bat_y, BAT_W, BAT_H, bat_vel_x global BRICK_H,BRICK_H, BRICK_COLOURS, BRICK_SCORES # Set the background colour background("black") # Show score and lives textSize(20); fill(255); text('Score: '+str(score), 10, 374); text('Lives: '+str(lives), 320, 374); if game_state == 'ready': show_start() else: if bricks == []: create_wall() #--------------- CHECK COLLISIONS ----------------# # Check if the BALL has HIT a BRICK in the wall for row_index, row in enumerate(bricks): for brick_index, brick in enumerate(row): x = 4+brick_index*(BRICK_W+4) y = 300+row_index*(BRICK_H+2) if ball_x > x - BALL_D/2 and ball_x < x + BRICK_W + BALL_D/2: if ball_y > y - BALL_D/2 and ball_y < y + BRICK_H + BALL_D/2: if brick == 'B': bricks[row_index][brick_index] = 'X' ball_vel_y = -ball_vel_y score += BRICK_SCORES[row_index] # Check if the BALL has HIT the BAT # Check if the ball is within the width of the bat if ball_x >= bat_x and ball_x <= (bat_x + BAT_W): # Check if the ball has reached the bat if ball_y <= BAT_H + BALL_D/2: # Send the ball back up the screen ball_vel_y = -ball_vel_y # Otherwise, check if the ball is below the bat elif ball_y < BAT_H: # Reset the bat to the starting values bat_x = 120 bat_y = 0 bat_vel_x = 0 # Reset the ball to the starting values ball_x = 180 ball_y = 50 ball_vel_x = 2 ball_vel_y = 2 lives -=1 if lives == 0: bricks = [] game_state = 'ready' # Check if the BALL has gone off the LEFT or RIGHT of the SCREEN if ball_x >= SCREEN_WIDTH - BALL_D/2: ball_vel_x = -ball_vel_x elif ball_x < BALL_D: ball_vel_x = -ball_vel_x # Check if the BALL has gone off the TOP of the SCREEN if ball_y >= SCREEN_HEIGHT - BALL_D/2: ball_vel_y = -ball_vel_y # Check if the BAT is going off the SCREEN if bat_x > SCREEN_WIDTH - BAT_W: bat_x = SCREEN_WIDTH - BAT_W elif bat_x < 0: bat_x = 0 #--------------- MOVE OBJECTS ----------------# # Move the bat bat_x = bat_x + bat_vel_x # Move the ball ball_x = ball_x + ball_vel_x ball_y = ball_y + ball_vel_y #----------------- DRAW OBJECTS ---------------------# # Draw the bat on the screen fill('white') rect(bat_x, bat_y, BAT_W, BAT_H) # Draw the ball on the screen fill('white') circle(ball_x,ball_y,BALL_D) # Draw the bricks on the screen if they are a 'B' for row_index, row in enumerate(bricks): fill(BRICK_COLOURS[row_index]) for brick_index, brick in enumerate(row): if brick == 'B': rect(4+brick_index*(BRICK_W+4),300+row_index*(BRICK_H+2),BRICK_W,BRICK_H) def show_start(): # This function displays a start screen with a clickable button global start_X, start_y, start_w, start_h, game_state, score, lives fill('white') textSize(64); text('Game Over', 30, 240); fill('purple') rect(start_X, start_y, start_w, start_h) fill('white') textSize(20); text('Start', start_X+25, start_y+9); if mouseIsPressed: print(mouseX, start_X) if mouseX>start_X and mouseX < start_X + start_w: if mouseY > start_y and mouseY < start_y + start_h: game_state = 'play' score = 0 lives = 3 def create_wall(): # Create the wall as a list of lists of bricks (ie. 2D array of bricks) named 'B' global NUM_BRICKS_IN_ROW, NUM_BRICK_ROWS, bricks for j in range(NUM_BRICK_ROWS): row = [] for i in range(NUM_BRICKS_IN_ROW): row.append('B') bricks.append(row) def keyPressed(): global bat_vel_x # Check if the player is moving the bat to the left if key == "ArrowLeft": # set the velocity of the bat to the left bat_vel_x = -2 # Otherwise check if the player is moving the bat to the right elif key == "ArrowRight": # set the velocity of the bat of the right bat_vel_x = 2