patternpythonMinor
Pong game in Python
Viewed 0 times
pythongamepong
Problem
I'm writing a pong game in Python and I created classes for the game objects.
The top level class is
```
# classes.py
# 3/19/2013
import pygame
import random
# Paddle properties
PADDLE_WIDTH = 25
PADDLE_HEIGHT = 100
PADDLE_COLOR = (0, 0, 0)
PADDLE_SPEED = 6
# Ball properties
BALL_RADIUS = 20
BALL_COLOR = (0, 0, 0)
BALL_INITIAL_VX = -5
BALL_INITIAL_VY = -5
# Base object class
class Object:
# Initializes the object with coordinates, size and color
def __init__(self, x, y, w, h, color):
self.x = x
self.y = y
self.w = w
self.h = h
self.vx = 0
self.vy = 0
self.color = color
# Updates object by moving it and checking if it's in screen range
def update(self, screenWidth, screenHeight):
self.x += self.vx
self.y += self.vy
if self.x screenWidth - self.w: self.x = screenWidth - self.w
if self.y > screenHeight - self.h: self.y = screenHeight - self.h
# Must be implemented by child classes
def draw(self, surface):
pass
# Returns whether object collides with another object (rectangular collision detection)
def collides(self, obj):
return self.y obj.y and self.x obj.x
# Called when object collides with anoher object, must be implemented by child classes
def onCollide(self, obj):
pass
# Paddle class
class Paddle(Object):
# Initializes Paddle object
def __init__(self, x, y):
super(Paddle, self).__init__(x, y, PADDLE_WIDTH, PADDLE_HEIGHT, PADDLE_COLOR)
# Draws paddle with a rectangle
def draw(self, surface):
pygame.draw.rect(surface, self.color, (self.x, self.y, self.w, self.h))
# Moves paddle up
def moveUp(self):
self.vy -= PADDLE_SPEED
# Moves paddle down
def moveDown(self):
self.vy = PADDLE_SPEED
# Stops moving the paddle
def stopMovin
The top level class is
Object, and Ball and Paddle inherit from it. And ComputerPaddle is a child class of Paddle. ```
# classes.py
# 3/19/2013
import pygame
import random
# Paddle properties
PADDLE_WIDTH = 25
PADDLE_HEIGHT = 100
PADDLE_COLOR = (0, 0, 0)
PADDLE_SPEED = 6
# Ball properties
BALL_RADIUS = 20
BALL_COLOR = (0, 0, 0)
BALL_INITIAL_VX = -5
BALL_INITIAL_VY = -5
# Base object class
class Object:
# Initializes the object with coordinates, size and color
def __init__(self, x, y, w, h, color):
self.x = x
self.y = y
self.w = w
self.h = h
self.vx = 0
self.vy = 0
self.color = color
# Updates object by moving it and checking if it's in screen range
def update(self, screenWidth, screenHeight):
self.x += self.vx
self.y += self.vy
if self.x screenWidth - self.w: self.x = screenWidth - self.w
if self.y > screenHeight - self.h: self.y = screenHeight - self.h
# Must be implemented by child classes
def draw(self, surface):
pass
# Returns whether object collides with another object (rectangular collision detection)
def collides(self, obj):
return self.y obj.y and self.x obj.x
# Called when object collides with anoher object, must be implemented by child classes
def onCollide(self, obj):
pass
# Paddle class
class Paddle(Object):
# Initializes Paddle object
def __init__(self, x, y):
super(Paddle, self).__init__(x, y, PADDLE_WIDTH, PADDLE_HEIGHT, PADDLE_COLOR)
# Draws paddle with a rectangle
def draw(self, surface):
pygame.draw.rect(surface, self.color, (self.x, self.y, self.w, self.h))
# Moves paddle up
def moveUp(self):
self.vy -= PADDLE_SPEED
# Moves paddle down
def moveDown(self):
self.vy = PADDLE_SPEED
# Stops moving the paddle
def stopMovin
Solution
Instead of using 4 different fields to keep track of your object's position and size, I suggest you just use a
This way, you can simplify your code a lot.
Example: Collision detection
just becomes:
Example: movement and bounds checking
can be rewritten as:
Example: drawing
becomes
Also, I probably wouldn't name a class
Otherwise, I think your code is fine so far.
Rect:def __init__(self, x, y, w, h, color):
self.rect = Rect(x, y, w, h)
self.vx = 0
self.vy = 0
self.color = colorThis way, you can simplify your code a lot.
Example: Collision detection
def collides(self, obj):
return self.y obj.y and self.x obj.xjust becomes:
def collides(self, obj):
return self.rect.colliderect(obj.rect)Example: movement and bounds checking
def update(self, screenWidth, screenHeight):
self.x += self.vx
self.y += self.vy
if self.x screenWidth - self.w: self.x = screenWidth - self.w
if self.y > screenHeight - self.h: self.y = screenHeight - self.hcan be rewritten as:
def update(self, screenWidth, screenHeight):
self.rect.move_ip(self.vx, self.vy)
self.rect.clamp_ip(Rect(0, 0, screenWidth, screenHeight)Example: drawing
def draw(self, surface):
pygame.draw.rect(surface, self.color, (self.x, self.y, self.w, self.h))becomes
def draw(self, surface):
pygame.draw.rect(surface, self.color, self.rect)Also, I probably wouldn't name a class
Object, since there's already the object class.Otherwise, I think your code is fine so far.
Code Snippets
def __init__(self, x, y, w, h, color):
self.rect = Rect(x, y, w, h)
self.vx = 0
self.vy = 0
self.color = colordef collides(self, obj):
return self.y < obj.y + obj.h and self.y + self.h > obj.y and self.x < obj.x + obj.w and self.x + self.w > obj.xdef collides(self, obj):
return self.rect.colliderect(obj.rect)def update(self, screenWidth, screenHeight):
self.x += self.vx
self.y += self.vy
if self.x < 0: self.x = 0
if self.y < 0: self.y = 0
if self.x > screenWidth - self.w: self.x = screenWidth - self.w
if self.y > screenHeight - self.h: self.y = screenHeight - self.hdef update(self, screenWidth, screenHeight):
self.rect.move_ip(self.vx, self.vy)
self.rect.clamp_ip(Rect(0, 0, screenWidth, screenHeight)Context
StackExchange Code Review Q#24167, answer score: 6
Revisions (0)
No revisions yet.