-
Notifications
You must be signed in to change notification settings - Fork 0
/
breakout.py
225 lines (167 loc) · 6.61 KB
/
breakout.py
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
#!/usr/bin/env python3
# Import all the necessary
import math
import pygame
from breakout_variables import *
from breakout_graphics import *
# Creates surface and background and initializes all pygame modules
screen = pygame.display.set_mode([1280, 720], 0, 32)
background = pygame.Surface(screen.get_size())
pygame.init()
class Block(pygame.sprite.Sprite):
""" The objective to destroy in the game"""
def __init__(self, x, y):
""" The blocks consists of a position on coord (x,y)"""
super().__init__()
# Assigns the block attributes of custom graphics and location on screen
self.image = pygame.Surface([64, 64])
self.image = brick_img
self.rect = self.image.get_rect()
self.rect.x = x
self.rect.y = y
class Ball(pygame.sprite.Sprite):
""" The object used for destroying the blocks"""
# Properties of ball, valuables saved externally for simpler edits
x = ballX
y = ballY
velocity = ballVelocity
direction = ballDirection
radius = ballRadius
def __init__(self):
super().__init__()
# Assigns the ball attributes with custom graphics
# and get display values for boundingbox
self.image = pygame.Surface([self.radius, self.radius])
self.image = ball_img
self.rect = self.image.get_rect()
self.screenheight = pygame.display.get_surface().get_height()
self.screenwidth = pygame.display.get_surface().get_width()
def bounce(self, diff):
""" Updates the ball if it hits an object vertically """
self.direction = (180 - self.direction) % 360
self.direction -= diff
def update(self):
""" Update the ball if it hits the boundaries horisontally and vertically """
direction_radians = math.radians(self.direction)
self.x += self.velocity *math.sin(direction_radians)
self.y -= self.velocity *math.cos(direction_radians)
self.rect.x = self.x
self.rect.y = self.y
top_wall = self.y <= 0
left_wall = self.x <= 0
right_wall = self.x > self.screenwidth - self.radius
bottom = self.y > 720
if top_wall:
self.bounce(0)
self.y = 1
if left_wall:
self.direction = (360 - self.direction) % 360
self.x = 1
if right_wall:
self.direction = (360 - self.direction) % 360
self.x = self.screenwidth - self.radius - 1
if bottom:
return True
else:
return False
class Player(pygame.sprite.Sprite):
""" This class represents the platform at the bottom half that the player controls. """
def __init__(self):
super().__init__()
self.width = pad_width
self.height = pad_height
self.image = pygame.Surface([self.width, self.height])
self.image = paddle_img
self.rect = self.image.get_rect()
self.screenheight = pygame.display.get_surface().get_height()
self.screenwidth = pygame.display.get_surface().get_width()
self.rect.x = 0
self.rect.y = self.screenheight - self.height
def update(self):
""" Update the player position. """
key_pressed = pygame.key.get_pressed()
if key_pressed[pygame.K_RIGHT] | key_pressed[pygame.K_d]:
self.rect.x += 13
if self.rect.x > self.screenwidth - self.width:
self.rect.x = self.screenwidth - self.width
if key_pressed[pygame.K_LEFT] | key_pressed[pygame.K_a]:
self.rect.x -= 13
if self.rect.x < 0:
self.rect.x = 0
# Let the player exit the game by pressing escape
if key_pressed[pygame.K_ESCAPE]:
print("Game closed manually by ESCAPE")
exit()
# Initialise ready for game loop
# Hide cursor
pygame.mouse.set_visible(0)
# Import clock for frames per second configuration
clock = pygame.time.Clock()
# Name the game window
pygame.display.set_caption('Breakout made by Brage Røsberg | @bragerosberg')
# Make font ready for loss/win scenario
font = pygame.font.Font("./assets/arcade.ttf", 72)
# Assigns the different sprite classes their group classes
blocks = pygame.sprite.Group()
ball = pygame.sprite.Group()
player = pygame.sprite.Group()
allsprites = pygame.sprite.Group()
user = Player()
allsprites.add(user)
player.add(user)
firecharge = Ball()
allsprites.add(firecharge)
ball.add(firecharge)
# Loop for creating the blocks
for row in range(3):
for column in range(0, blockcount):
glowstone = Block(column * (64 + 16), block_top)
blocks.add(glowstone)
allsprites.add(glowstone)
block_top += 70
# Defeat is false
Defeat = False
# Main game loop
while True:
# 60 frames per second
clock.tick(60)
# Quit program if program is closed
for event in pygame.event.get():
if event.type == pygame.QUIT:
print("GAME PROPERLY CLOSED")
exit()
# As long as game is not lost or won
if not Defeat and len(blocks) > 0:
user.update()
Defeat = firecharge.update()
# If lost, print message
if Defeat:
text = font.render("You lost", True, (255, 0, 0))
textpos = text.get_rect(centerx=background.get_width()/2)
textpos.top = 300
screen.blit(text, textpos)
# If won, print message
if len(blocks) == 0:
text = font.render("You won", True, (0, 255, 0))
textpos = text.get_rect(centerx=background.get_width()/2)
textpos.top = 300
screen.blit(text, textpos)
# Bounce ball if collides with platform, dont remove object
if pygame.sprite.spritecollide(user, ball, False):
diff = (user.rect.x + user.width/2) - (firecharge.rect.x + firecharge.radius/2)
firecharge.rect.y = screen.get_height() - user.rect.height - firecharge.rect.height - 1
firecharge.bounce(diff)
# Remove block if ball hits, add one to score
block_hit = pygame.sprite.spritecollide(firecharge, blocks, True)
if block_hit:
score += 1
# if block_hit, prevent ball from going to the next block without bouncing back first
if len(block_hit) > 0:
firecharge.bounce(0)
# Draw everything
allsprites.draw(screen)
draw_text(screen, str(score), 36, 1250, 650)
pygame.display.flip()
screen.blit(background_img, [0, 0])
# Uninitializes all pygame modules
pygame.quit()