line 475, in draw self.spritedict[spr] = surface_blit(spr.image, spr.rect) - python-3.x

import pygame
import random
WIDTH = 360
HEIGHT = 480
FPS = 30
WHITE = (255, 255, 255)
BLACK = (0, 0, 0)
RED = (255, 0, 0)
GREEN = (0, 255, 0)
BLUE = (0, 0, 255)
pygame.init()
pygame.mixer.init()
screen = pygame.display.set_mode([WIDTH, HEIGHT])
pygame.display.set_caption("My Game")
clock = pygame.time.Clock()
class Player(pygame.sprite.Sprite):
def __init__(self):
pygame.sprite.Sprite.__init__(self)
self.image = pygame.Surface((10, 10))
self.image.fill(GREEN)
self.rect = self.image.get_rect()
self.rect.centerx = WIDTH / 2
self.rect = HEIGHT - 10
all_sprites = pygame.sprite.Group()
Player = Player()
all_sprites.add(Player)
running = True
while running:
clock.tick(FPS)
for event in pygame.event.get():
if event.type == pygame.QUIT:
running = False
all_sprites.update()
screen.fill(BLACK)
all_sprites.draw(screen)
pygame.display.flip()
pygame.quit()
Hello I am getting this error when i am trying to run this program File , line 54, in
all_sprites.draw(screen)
line 475, in draw
self.spritedict[spr] = surface_blit(spr.image, spr.rect)
TypeError: invalid destination position for blit. Plz help me.

Your rect attribute must be an Rect object but you're overriding it with an integer in the line self.rect = HEIGHT - 10. Since a single integer isn't a valid location to blit a sprite on you get "invalid destination position for blit".

Related

Pygame limiting collision targets [duplicate]

I have made a list of bullets and a list of sprites using the classes below. How do I detect if a bullet collides with a sprite and then delete that sprite and the bullet?
#Define the sprite class
class Sprite:
def __init__(self,x,y, name):
self.x=x
self.y=y
self.image = pygame.image.load(name)
self.rect = self.image.get_rect()
def render(self):
window.blit(self.image, (self.x,self.y))
# Define the bullet class to create bullets
class Bullet:
def __init__(self,x,y):
self.x = x + 23
self.y = y
self.bullet = pygame.image.load("user_bullet.BMP")
self.rect = self.bullet.get_rect()
def render(self):
window.blit(self.bullet, (self.x, self.y))
In PyGame, collision detection is done using pygame.Rect objects. The Rect object offers various methods for detecting collisions between objects. Even the collision between a rectangular and circular object such as a paddle and a ball can be detected by a collision between two rectangular objects, the paddle and the bounding rectangle of the ball.
Some examples:
pygame.Rect.collidepoint:
Test if a point is inside a rectangle
repl.it/#Rabbid76/PyGame-collidepoint
import pygame
pygame.init()
window = pygame.display.set_mode((250, 250))
rect = pygame.Rect(*window.get_rect().center, 0, 0).inflate(100, 100)
run = True
while run:
for event in pygame.event.get():
if event.type == pygame.QUIT:
run = False
point = pygame.mouse.get_pos()
collide = rect.collidepoint(point)
color = (255, 0, 0) if collide else (255, 255, 255)
window.fill(0)
pygame.draw.rect(window, color, rect)
pygame.display.flip()
pygame.quit()
exit()
pygame.Rect.colliderect
Test if two rectangles overlap
See also How to detect collisions between two rectangular objects or images in pygame
repl.it/#Rabbid76/PyGame-colliderect
import pygame
pygame.init()
window = pygame.display.set_mode((250, 250))
rect1 = pygame.Rect(*window.get_rect().center, 0, 0).inflate(75, 75)
rect2 = pygame.Rect(0, 0, 75, 75)
run = True
while run:
for event in pygame.event.get():
if event.type == pygame.QUIT:
run = False
rect2.center = pygame.mouse.get_pos()
collide = rect1.colliderect(rect2)
color = (255, 0, 0) if collide else (255, 255, 255)
window.fill(0)
pygame.draw.rect(window, color, rect1)
pygame.draw.rect(window, (0, 255, 0), rect2, 6, 1)
pygame.display.flip()
pygame.quit()
exit()
Furthermore, pygame.Rect.collidelist and pygame.Rect.collidelistall can be used for the collision test between a rectangle and a list of rectangles. pygame.Rect.collidedict and pygame.Rect.collidedictall can be used for the collision test between a rectangle and a dictionary of rectangles.
The collision of pygame.sprite.Sprite and pygame.sprite.Group objects, can be detected by pygame.sprite.spritecollide(), pygame.sprite.groupcollide() or pygame.sprite.spritecollideany(). When using these methods, the collision detection algorithm can be specified by the collided argument:
The collided argument is a callback function used to calculate if two sprites are colliding.
Possible collided callables are collide_rect, collide_rect_ratio, collide_circle, collide_circle_ratio, collide_mask
Some examples:
pygame.sprite.spritecollide()
repl.it/#Rabbid76/PyGame-spritecollide
import pygame
pygame.init()
window = pygame.display.set_mode((250, 250))
sprite1 = pygame.sprite.Sprite()
sprite1.image = pygame.Surface((75, 75))
sprite1.image.fill((255, 0, 0))
sprite1.rect = pygame.Rect(*window.get_rect().center, 0, 0).inflate(75, 75)
sprite2 = pygame.sprite.Sprite()
sprite2.image = pygame.Surface((75, 75))
sprite2.image.fill((0, 255, 0))
sprite2.rect = pygame.Rect(*window.get_rect().center, 0, 0).inflate(75, 75)
all_group = pygame.sprite.Group([sprite2, sprite1])
test_group = pygame.sprite.Group(sprite2)
run = True
while run:
for event in pygame.event.get():
if event.type == pygame.QUIT:
run = False
sprite1.rect.center = pygame.mouse.get_pos()
collide = pygame.sprite.spritecollide(sprite1, test_group, False)
window.fill(0)
all_group.draw(window)
for s in collide:
pygame.draw.rect(window, (255, 255, 255), s.rect, 5, 1)
pygame.display.flip()
pygame.quit()
exit()
For a collision with masks, see How can I make a collision mask? or Pygame mask collision
See also Collision and Intersection
pygame.sprite.spritecollide() / collide_circle
repl.it/#Rabbid76/PyGame-spritecollidecollidecircle
import pygame
pygame.init()
window = pygame.display.set_mode((250, 250))
sprite1 = pygame.sprite.Sprite()
sprite1.image = pygame.Surface((80, 80), pygame.SRCALPHA)
pygame.draw.circle(sprite1.image, (255, 0, 0), (40, 40), 40)
sprite1.rect = pygame.Rect(*window.get_rect().center, 0, 0).inflate(80, 80)
sprite1.radius = 40
sprite2 = pygame.sprite.Sprite()
sprite2.image = pygame.Surface((80, 89), pygame.SRCALPHA)
pygame.draw.circle(sprite2.image, (0, 255, 0), (40, 40), 40)
sprite2.rect = pygame.Rect(*window.get_rect().center, 0, 0).inflate(80, 80)
sprite2.radius = 40
all_group = pygame.sprite.Group([sprite2, sprite1])
test_group = pygame.sprite.Group(sprite2)
run = True
while run:
for event in pygame.event.get():
if event.type == pygame.QUIT:
run = False
sprite1.rect.center = pygame.mouse.get_pos()
collide = pygame.sprite.spritecollide(sprite1, test_group, False, pygame.sprite.collide_circle)
window.fill(0)
all_group.draw(window)
for s in collide:
pygame.draw.circle(window, (255, 255, 255), s.rect.center, s.rect.width // 2, 5)
pygame.display.flip()
pygame.quit()
exit()
What does this all mean for your code?
pygame.Surface.get_rect.get_rect() returns a rectangle with the size of the Surface object, that always starts at (0, 0) since a Surface object has no position. The position of the rectangle can be specified by a keyword argument. For example, the centre of the rectangle can be specified with the keyword argument center. These keyword arguments are applied to the attributes of the pygame.Rect before it is returned (see pygame.Rect for a list of the keyword arguments).
See *Why is my collision test always returning 'true' and why is the position of the rectangle of the image always wrong (0, 0)?
You do not need the x and y attributes of Sprite and Bullet at all. Use the position of the rect attribute instead:
#Define the sprite class
class Sprite:
def __init__(self, x, y, name):
self.image = pygame.image.load(name)
self.rect = self.image.get_rect(topleft = (x, y))
def render(self):
window.blit(self.image, self.rect)
# Define the bullet class to create bullets
class Bullet:
def __init__(self, x, y):
self.bullet = pygame.image.load("user_bullet.BMP")
self.rect = self.bullet.get_rect(topleft = (x + 23, y))
def render(self):
window.blit(self.bullet, self.rect)
Use pygame.Rect.colliderect() to detect collisions between instances of Sprite and Bullet.
See How to detect collisions between two rectangular objects or images in pygame:
my_sprite = Sprite(sx, sy, name)
my_bullet = Bullet(by, by)
while True:
# [...]
if my_sprite.rect.colliderect(my_bullet.rect):
printe("hit")
From what I understand of pygame you just need to check if the two rectangles overlap using the colliderect method. One way to do it is to have a method in your Bullet class that checks for collisions:
def is_collided_with(self, sprite):
return self.rect.colliderect(sprite.rect)
Then you can call it like:
sprite = Sprite(10, 10, 'my_sprite')
bullet = Bullet(20, 10)
if bullet.is_collided_with(sprite):
print('collision!')
bullet.kill()
sprite.kill()
There is a very simple method for what you are trying to do using built in methods.
here is an example.
import pygame
import sys
class Sprite(pygame.sprite.Sprite):
def __init__(self, pos):
pygame.sprite.Sprite.__init__(self)
self.image = pygame.Surface([20, 20])
self.image.fill((255, 0, 0))
self.rect = self.image.get_rect()
self.rect.center = pos
def main():
pygame.init()
clock = pygame.time.Clock()
fps = 50
bg = [255, 255, 255]
size =[200, 200]
screen = pygame.display.set_mode(size)
player = Sprite([40, 50])
player.move = [pygame.K_LEFT, pygame.K_RIGHT, pygame.K_UP, pygame.K_DOWN]
player.vx = 5
player.vy = 5
wall = Sprite([100, 60])
wall_group = pygame.sprite.Group()
wall_group.add(wall)
player_group = pygame.sprite.Group()
player_group.add(player)
# I added loop for a better exit from the game
loop = 1
while loop:
for event in pygame.event.get():
if event.type == pygame.QUIT:
loop = 0
key = pygame.key.get_pressed()
for i in range(2):
if key[player.move[i]]:
player.rect.x += player.vx * [-1, 1][i]
for i in range(2):
if key[player.move[2:4][i]]:
player.rect.y += player.vy * [-1, 1][i]
screen.fill(bg)
# first parameter takes a single sprite
# second parameter takes sprite groups
# third parameter is a do kill command if true
# all group objects colliding with the first parameter object will be
# destroyed. The first parameter could be bullets and the second one
# targets although the bullet is not destroyed but can be done with
# simple trick bellow
hit = pygame.sprite.spritecollide(player, wall_group, True)
if hit:
# if collision is detected call a function in your case destroy
# bullet
player.image.fill((255, 255, 255))
player_group.draw(screen)
wall_group.draw(screen)
pygame.display.update()
clock.tick(fps)
pygame.quit()
# sys.exit
if __name__ == '__main__':
main()
Make a group for the bullets, and then add the bullets to the group.
What I would do is this:
In the class for the player:
def collideWithBullet(self):
if pygame.sprite.spritecollideany(self, 'groupName'):
print("CollideWithBullet!!")
return True
And in the main loop somewhere:
def run(self):
if self.player.collideWithBullet():
print("Game Over")
Hopefully that works for you!!!
Inside the Sprite class, try adding a self.mask attribute with
self.mask = pygame.mask.from_surface(self.image)
and a collide_mask function inside of the Sprite class with this code:
def collide_mask(self, mask):
collided = False
mask_outline = mask.outline()
self.mask_outline = self.mask.outline()
for point in range(len(mask_outline)):
mask_outline[point] = list(mask_outline[point])
mask_outline[point][0] += bullet.x
mask_outline[point][1] += bullet.y
for point in range(len(self.mask_outline)):
self.mask_outline[point] = list(mask_outline[point])
self.mask_outline[point][0] += self.x
self.mask_outline[point][1] += self.y
for point in mask_outline:
for self_mask_point in self.mask_outline:
if point = self_mask_point:
collided = True
return collided

How to completely clear pygame window with button

I made this program:
import pygame
pygame.init()
WIDTH = 600
HEIGHT = 700
RED = (255, 0, 0)
BLACK = (0, 0, 0)
GREY = (211, 211, 211)
GREEN = (0, 255, 0)
win = pygame.display.set_mode((WIDTH, HEIGHT))
win.fill(GREY)
def buttons(buttonx, buttony, buttonw, buttonh, color, msg, size): # left, top, width, height, color, message, font size
pos = pygame.mouse.get_pos()
fontb = pygame.font.SysFont("arial", size)
text = fontb.render(msg, True, BLACK)
outline = pygame.Rect(buttonx - 2, buttony - 2, buttonw + 4, buttonh + 4)
win.fill(BLACK, outline)
button = pygame.Rect(buttonx, buttony, buttonw, buttonh)
win.fill(color, button)
textplace = text.get_rect(center=(buttonx + buttonw/2, buttony + buttonh/2))
win.blit(text, textplace)
if button.collidepoint(pos):
win.fill(GREEN, button)
win.blit(text, textplace)
for event in pygame.event.get():
if event.type == pygame.MOUSEBUTTONDOWN:
pass
# this block of code should make window grey
def main_menu():
font1 = pygame.font.SysFont("arial", 45)
welcoming = font1.render("Welcome!", True, BLACK, GREY)
wRect = welcoming.get_rect(center=(WIDTH / 2, 75))
win.blit(welcoming, wRect)
buttons(100, 150, 400, 100, RED, "Play", 60)
buttons(100, 300, 175, 100, RED, "Options", 40)
buttons(325, 300, 175, 100, RED, "Instructions", 30)
buttons(100, 450, 175, 100, RED, "Leaderboard", 30)# left, top, width, height, color, message
buttons(325, 450, 175, 100, RED, "Quit", 60)
main = True
while main:
main_menu()
for event in pygame.event.get():
if event.type == pygame.QUIT:
main = False
pygame.display.update()
If any of the buttons is pressed, the window should turn completely grey (all buttons and texts should disappear). I have tried to put
win.fill(GREY)
pygame.display.update()
in place of
pass
# this block of code should make window grey
in lines 34 and 35, but it does not work. I have also tried to make some kind of functions that return grey window which is same size as the original window and then blit it on the main menu, but it doesn't work either. Can anyone help?
The code you are trying succeeds in filling the window with grey. However, the blank grey screen then has the menu drawn on top of it immediately by your main loop.
Using an additional global variable, current_screen, it is possible to prevent this from happening. The main loop now checks current_screen to see which screen it should draw before doing so, ensuring that the menu will not be drawn when it is not supposed to be shown.
This following code worked for me, but let me know if you have any problems with it.
import pygame
pygame.init()
# declare final variables
WIDTH = 600
HEIGHT = 700
RED = (255, 0, 0)
BLACK = (0, 0, 0)
GREY = (211, 211, 211)
GREEN = (0, 255, 0)
# create window
win = pygame.display.set_mode((WIDTH, HEIGHT))
win.fill(GREY)
# left, top, width, height, color, message, font size
def buttons(buttonx, buttony, buttonw, buttonh, color, msg, size):
global win, current_screen
pos = pygame.mouse.get_pos()
fontb = pygame.font.SysFont("arial", size)
text = fontb.render(msg, True, BLACK)
# draw button outline and fill
outline = pygame.Rect(buttonx - 2, buttony - 2, buttonw + 4, buttonh + 4)
win.fill(BLACK, outline)
button = pygame.Rect(buttonx, buttony, buttonw, buttonh)
win.fill(color, button)
# draw button text
textplace = text.get_rect(
center=(buttonx + buttonw/2, buttony + buttonh/2))
win.blit(text, textplace)
if button.collidepoint(pos): # button mouse-hover
win.fill(GREEN, button)
win.blit(text, textplace)
for event in pygame.event.get():
if event.type == pygame.MOUSEBUTTONDOWN: # button pressed
current_screen = "blank"
def main_menu():
# draw welcome message
font1 = pygame.font.SysFont("arial", 45)
welcoming = font1.render("Welcome!", True, BLACK, GREY)
wRect = welcoming.get_rect(center=(WIDTH / 2, 75))
win.blit(welcoming, wRect)
# draw buttons
buttons(100, 150, 400, 100, RED, "Play", 60)
buttons(100, 300, 175, 100, RED, "Options", 40)
buttons(325, 300, 175, 100, RED, "Instructions", 30)
# left, top, width, height, color, message
buttons(100, 450, 175, 100, RED, "Leaderboard", 30)
buttons(325, 450, 175, 100, RED, "Quit", 60)
main = True
current_screen = "main menu"
while main:
# draw the current screen
if current_screen == "main menu":
main_menu()
elif current_screen == "blank":
win.fill(GREY)
else:
raise NotImplementedError("There is no behavior defined for the current screen, "+current_screen+", in the main loop!")
# end main loop on window close
for event in pygame.event.get():
if event.type == pygame.QUIT:
main = False
pygame.display.update()

Return a sprite to its original position?

So I have a very basic PyGame Python program which is a 'car' that the user controls and one which comes down he road towards it. How can I get the NPC car to return to its original position once it leaves the screen? My current code is shown below, thanks for any help you can provide!
import pygame, random
from car import Car
from car import AutoCar
pygame.init()
play = True
clock = pygame.time.Clock()
screen = pygame.display.set_mode((700, 750))
pygame.display.set_caption("Car Game")
# Define a bunch of colours
GREEN = (20, 255, 100)
GREY = (210, 210, 210)
WHITE = (255, 255, 255)
RED = (255, 0, 0)
PURPLE = (255, 0, 255)
BLUE = (0, 0, 255)
all_sprites = pygame.sprite.Group() # Creates a list of all sprites in the game
playerCar = Car(RED, 20, 30) # Defines the car, its colour, and its
size
playerCar.rect.x = 200
playerCar.rect.y = 300
AutoCar1 = AutoCar(BLUE, 20, 30)
AutoCar1.rect.x = 200
AutoCar1.rect.y = 20
all_sprites.add(playerCar) # Adds the playerCar to the list of sprites
all_sprites.add(AutoCar1) # Adds an automated 'enemy' car which you must avoid
while play:
for event in pygame.event.get():
if event.type == pygame.QUIT: # If the detected event is clicking the exit button, stop the program.
play = False
elif event.type == pygame.KEYDOWN: # If a key is pressed and the key is 'x', quit the game.
if event.key == pygame.K_x:
play = False
keys = pygame.key.get_pressed() # Defines a variable keys that consists of whatever event is happening in the game
if keys[pygame.K_LEFT]:
playerCar.move_left(5)
if keys[pygame.K_RIGHT]:
playerCar.move_right(5)
if keys[pygame.K_DOWN]:
playerCar.move_backward(5)
if keys[pygame.K_UP]:
playerCar.move_forward(5)
all_sprites.update() # Draws in all sprites
AutoCar1.auto_move_forward(3) # Makes the 'enemy' move forward automatically.
# Create the background
screen.fill(GREEN)
# Create the road
pygame.draw.rect(screen, GREY, [100, 0, 500, 750])
# Draw the lines on the road
pygame.draw.line(screen, WHITE, [340, 0], [340, 750], 5)
# Draw in all the sprites
all_sprites.draw(screen)
pygame.display.flip()
clock.tick(60) # Cap limit at 60FPS
pygame.quit()
I also have a file defining the class Car and Autocar:
import pygame
WHITE = (255, 255, 255)
class Car(pygame.sprite.Sprite): # Creates a class representing a car, derived from the sprite class
def __init__(self, color, width, height):
# Call the parent class (i.e. Sprite) constructor
super().__init__()
self.image = pygame.Surface([width,height])
self.image.fill(WHITE)
self.image.set_colorkey(WHITE) # Sets white as transparent for this class
# alternatively load a proper car picture:
# self.image = pygame.image.load("car.png").convert_alpha()
pygame.draw.rect(self.image, color, [0, 0, width, height])
self.rect = self.image.get_rect() # Fetches the rectangle with the dimensions of the image
def move_right(self, pixels): # Adds to the x value of the car the desired amount of pixels
self.rect.x += pixels
def move_left(self, pixels): # Same as move_right()
self.rect.x -= pixels
def move_forward(self, pixels):
self.rect.y -= pixels
def move_backward(self, pixels):
self.rect.y += pixels
class AutoCar(pygame.sprite.Sprite):
def __init__(self, color, width, height):
super().__init__()
self.image = pygame.Surface([width, height])
self.image.fill(WHITE)
self.image.set_colorkey(WHITE)
pygame.draw.rect(self.image, color, [0, 0, width, height])
self.rect = self.image.get_rect()
def auto_move_forward(self, pixels):
self.rect.y += pixels
def return_to_top(self):
Just store the start position as an attribute of the AutoCar, check in the update method if the sprite is below the screen and then set the self.rect.topleft (or one of the other rect attributes) to the self.start_position.
class AutoCar(pygame.sprite.Sprite):
def __init__(self, color, width, height):
super().__init__()
self.image = pygame.Surface([width, height])
self.image.fill(WHITE)
self.image.set_colorkey(WHITE)
pygame.draw.rect(self.image, color, [0, 0, width, height])
self.rect = self.image.get_rect()
self.start_position = (200, -50)
self.rect.topleft = self.start_position
def auto_move_forward(self, pixels):
self.rect.y += pixels
def return_to_top(self):
self.rect.topleft = self.start_position
def update(self):
if self.rect.top > 750: # Screen height.
self.rect.topleft = self.start_position

How do I pass a rect into pygame.display.update() to update a specific area of the window?

On the documentation page for pygame.display.update(), it says you can pass a rect into the method to update part of the screen. However, all of the examples I see just pass an existing rect from an image or shape in the program. How can I tell it to update an area on the screen directly? For example, when drawing a rectangle, I could use a rect argument of (100,200,30,40). This would draw a rectangle with a top at 200, a left at 100, a width of 30, and a height of 40. How can I pass a similar argument into pygame.display.update()? I tried pygame.display.update((100,200,30,40)), but this updates the entire window.
Just define a rect and pass it to pygame.display.update() to update only this specific region of the display. You can also pass a list of rects.
import random
import pygame as pg
from pygame.math import Vector2
# A simple sprite, just to have something moving on the screen.
class Ball(pg.sprite.Sprite):
def __init__(self, screen_rect):
super().__init__()
radius = random.randrange(5, 31)
self.image = pg.Surface((radius*2, radius*2), pg.SRCALPHA)
pg.draw.circle(self.image, pg.Color('dodgerblue1'), (radius, radius), radius)
pg.draw.circle(self.image, pg.Color('dodgerblue3'), (radius, radius), radius-2)
self.rect = self.image.get_rect(center=screen_rect.center)
self.vel = Vector2(random.uniform(-2, 2), random.uniform(-2, 2))
self.pos = Vector2(self.rect.center)
self.screen_rect = screen_rect
self.lifetime = 350
def update(self):
self.pos += self.vel
self.rect.center = self.pos
self.lifetime -= 1
if not self.screen_rect.contains(self.rect) or self.lifetime <= 0:
self.kill()
def main():
screen = pg.display.set_mode((800, 600))
screen.fill((20, 40, 70))
pg.display.update()
screen_rect = screen.get_rect()
clock = pg.time.Clock()
all_sprites = pg.sprite.Group()
# Pass this rect to `pg.display.update` to update only this area.
update_rect = pg.Rect(50, 50, 500, 400)
done = False
while not done:
for event in pg.event.get():
if event.type == pg.QUIT:
done = True
all_sprites.add(Ball(screen_rect))
all_sprites.update()
screen.fill((20, 50, 90))
all_sprites.draw(screen)
# Update only the area that we specified with the `update_rect`.
pg.display.update(update_rect)
clock.tick(60)
if __name__ == '__main__':
pg.init()
main()
pg.quit()

Rect error in Python 3.6.2, Pygame 1.9.3

I have recently been learning python and I just found out about sprites. They seem really useful and I have been trying to make a game where you have to eat all the red apples (healthy), and not the blue apples (mouldy). An error occurred when I tried to run it and it said:
line 32, in <module>
apples.rect.y = random.randrange(displayHeight - 20)
AttributeError: type object 'apples' has no attribute 'rect'
Sorry if I have made a really nooby error but I have been looking for an answer elsewhere and I couldn't find one. Here is my entire main code:
import pygame
import random
pygame.init()
displayWidth = 800
displayHeight = 600
black = (0, 0, 0)
white = (255, 255, 255)
red = (255, 0, 0)
green = (0, 255, 0)
blue = (0, 0, 255)
gameDisplay = pygame.display.set_mode((displayWidth, displayHeight))
gameCaption = pygame.display.set_caption("Eat The Apples")
gameClock = pygame.time.Clock()
class apples(pygame.sprite.Sprite):
def __init__(self, colour, width, height):
pygame.sprite.Sprite.__init__(self)
self.image = pygame.Surface([20, 10])
self.image.fill(red)
self.rect = self.image.get_rect()
applesList = pygame.sprite.Group()
allSpriteList = pygame.sprite.Group()
for i in range(50):
apple = apples(red, 20 , 20)
apples.rect.y = random.randrange(displayHeight - 20)
apples.rect.x = random.randrange(displayWidth - 20)
applesList.add(apple)
allSpriteList.add(apple)
player = apples(green, 20, 20)
def gameLoop():
gameExit = False
while not gameExit:
for event in pygame.event.get():
if event.type == pygame.QUIT:
gameExit = True
pygame.display.update()
gameClock.tick(60)
gameLoop()
pygame.quit()
quit()
Thank you for reading and I look forward to a response!
(P.S. This code isn't completely finished if you were wondering)
You're trying to change the rect attribute of the class here not the rect of the instance, and since the class doesn't have a rect, the AttributeError is raised.
apples.rect.y = random.randrange(displayHeight - 20)
apples.rect.x = random.randrange(displayWidth - 20)
Just change apples to apple (the instance) and it should work correctly.
apple.rect.y = random.randrange(displayHeight - 20)
apple.rect.x = random.randrange(displayWidth - 20)
Yes, like skrx said. you just have to single one out.
for apple in apples:
should work.

Resources