This question is asked a lot, but unfortunately I found no answer fitting my problem. If possible, I prefer a generic answer, since I'm a novice trying to learn Python. Thank you in advance.
This is the code I got by following a tutorial on the basics of python using the pygame library:
import pygame
background_colour = (255, 255, 255)
(width, height) = (300, 200)
class Particle:
def __init__(self, x, y, size):
self.x = x
self.y = y
self.size = size
self.colour = (0, 0, 255)
self.thickness = 1
screen = pygame.display.set_mode((width, height))
def display(self):
pygame.draw.circle(screen, self.colour, (self.x, self.y), self.size, self.thickness)
pygame.display.set_caption('Agar')
screen.fill(background_colour)
pygame.display.flip()
running = True
my_first_particle = Particle(150, 50, 15)
my_first_particle.display()
while running:
for event in pygame.event.get():
if event.type == pygame.QUIT:
running = False
It is used to create a window for gaming, with a circle in it. The circle is defined as a class to be used multiple times in a similar way later on.
I got the following error:
Traceback (most recent call last):
File "C:/Users/20172542/PycharmProjects/agarTryout/Agar.py", line 29, in <module>
my_first_particle.display()
AttributeError: 'Particle' object has no attribute 'display'
What principle am I not understanding, and what is the specific solution for this error?
Thank you for your time and effort.
The display function defined is not inside Particle, instead at the global (not sure if this name is right) level of your script. Indentation is significant in python, as it does not have brackets. Move the function after your __init__ function, with the same indentation.
Also, I guess you should move screen above your Particle definition.
By your definition of the Particle class, my_first_particle (an instance of Particle) has no display attribute.
It looks like the definition of the display function should be part of the Particle class definition.
Check out the Python Classes tutorial.
Related
I am trying to code a game with Python, but it keeps showing the error "TypeError: update() takes 1 positional argument but 2 were given". I have checked multiple forums including stackoverflow multiple times, but all of them were saying that the error occurs when we forget a 'self' argument. However, that is not my case.
Below, you can see my tiles.py file. It shows the Tile class.
import pygame
class Tile(pygame.sprite.Sprite):
def __init__(self,pos,size):
super().__init__()
self.image = pygame.Surface((size,size))
self.image.fill('grey')
self.rect = self.image.get_rect(topleft = pos)
def update(self,x_shift):
self.rect.x += x_shift
As you can see, both the __init__() and the update() functions has the self argument. When I run the update part in level.py:
import pygame
from tiles import Tile
from settings import tile_size
from player import Player
class Level:
def __init__(self,level_data,surface):
self.display_surface = surface
self.setup_level(level_data)
self.world_shift = 0
def setup_level(self,layout):
self.tiles = pygame.sprite.Group()
self.player = pygame.sprite.GroupSingle()
for row_index,row in enumerate(layout):
for col_index,cell in enumerate(row):
x = col_index * tile_size
y = row_index * tile_size
if cell == 'X':
tile = Tile((x,y),tile_size)
self.tiles.add(tile)
if cell == 'P':
player_sprite = Player((x,y))
self.tiles.add(player_sprite)
def run(self):
#level tiles
self.tiles.update(self.world_shift)
self.tiles.draw(self.display_surface)
#player
self.player.update()
self.player.draw(self.display_surface)
The run function's self.tiles.update(self.world_shift), as you can see, also has an argument in it, which is the x_shift argument. However, when I run the run function in my main.py file:
import pygame, sys
from settings import *
from level import Level
#Setup
pygame.init()
screen = pygame.display.set_mode((screen_width,screen_height))
clock = pygame.time.Clock()
level = Level(level_map,screen)
pygame.display.set_caption('Pirates Run')
while True:
for event in pygame.event.get():
if event.type == pygame.QUIT:
pygame.quit()
sys.exit()
screen.fill('black')
level.run()
pygame.display.update()
clock.tick(60)
When I have run the code, the only output I get is a black screen that appears for less than a second and then closes, and then an error that looks like this:
Traceback (most recent call last):
File "c:\Users\User\OneDrive\Desktop\Blazel\Pirates Run\code\main.py", line 19, in <module>
level.run()
File "c:\Users\User\OneDrive\Desktop\Blazel\Pirates Run\code\level.py", line 26, in run
self.tiles.update(self.world_shift)
File "C:\Users\User\AppData\Local\Programs\Python\Python39\lib\site-
packages\pygame\sprite.py", line 531, in update
sprite.update(*args, **kwargs)
TypeError: update() takes 1 positional argument but 2 were given
Please help me solve this problem! Thanks!
First some basics:
pygame.sprite.Group.draw() and pygame.sprite.Group.update() are methods which are provided by pygame.sprite.Group.
The latter delegates to the update method of the contained pygame.sprite.Sprites — you have to implement the method. See pygame.sprite.Group.update():
Calls the update() method on all Sprites in the Group. [...]
The former uses the image and rect attributes of the contained pygame.sprite.Sprites to draw the objects — you have to ensure that the pygame.sprite.Sprites have the required attributes. See pygame.sprite.Group.draw():
Draws the contained Sprites to the Surface argument. This uses the Sprite.image attribute for the source surface, and Sprite.rect. [...]
You add player_sprite to the self.tiles Group.
self.tiles.add(player_sprite)
The Tile object has an update methode:
def update(self,x_shift):
The Player object has an update method with a different argument list. This causes the error.
Do not add player_sprite to tiles, but create a separate Group for the player to solve the issue (e.g. pygame.sprite.GroupSingle).
This question already has answers here:
Pygame Drawing a Rectangle
(6 answers)
Closed 1 year ago.
I am making a snake game in pygame. However, I ran into a TypeError problem inside my Snake class object. To be specific it threw an error inside the draw() (class) and blit() (non-class) functions, telling me that "an integer is required" (got type tuple).
import pygame
import random
pygame.init()
screen = pygame.display.set_mode((640, 480))
class Snake(object):
def __init__(self, x, y, height, width, color):
self.x = x
self.y = y
self.height = height
self.width = width
self.color = color
self.vel = 3
def draw(self): # The problem happened here
pygame.draw.rect(screen, self.color, (self.x, self.y), (self.height, self.width))
def auto_move(self):
pass
def blit(): # The problem also happened here
snake.draw()
snake = Snake(300, 300, 64, 64, (0, 255, 0))
run = True
while run:
screen.fill((0, 0, 0))
for event in pygame.event.get():
if event.type == pygame.QUIT:
run = False
blit()
pygame.display.update()
The game is far from finish as I quickly ran to said error. Thanks in advance.
To use pygame.draw.rect, the documentation says that you must pass as arguments:
surface: in your case, surface is screen.
color: pygame.Color, int or tuple of length 3. In your case self.color.
rect: pygame.Rect()
The rect argument can be as following:
pygame.Rect(left, top, width, height)
pygame.Rect((left, top), (width, height))
pygame.Rect(object)
So, you must type
def draw(self, screen): # The problem no longer happen here
rect = pygame.Rect(self.x, self.y, self.height, self.width)
pygame.draw.rect(screen, self.color, rect)
Second error
def blit(): # The problem also happened here
snack.draw(screen) >>> ?????
Of course! Why are you typing this line ? There is no "snack" class...
-- Edit --
Your question has been edited to do a minimal reproducible example and the person who edited didn't remove this line - I'll do it
I am just started getting into classes and understand the basic concept however I don't understand why it gives me this error.
My code:
import pygame
pygame.init()
screen = pygame.display.set_mode((400, 300))
done = False
while not done:
for event in pygame.event.get():
if event.type == pygame.QUIT:
done = True
class shape():
def __init__(self, place, colour, x, y):
self.place = place
self.colour = colour
self.x = x
self.y = y
class rectangle(shape):
def __init__(self, place, colour, x, y, length, width):
super().__init__(self, place, colour, x, y)
self.length = length
self.width = width
pygame.draw.rect(screen, colour, pygame.Rect(x, y, lenght, width))
Rectangle = rectangle(screen, (0, 128, 255), 30, 30, 60, 60)
pygame.display.flip()
The error I receive:
Traceback (most recent call last):
File "Pygame.py", line 34, in <module>
Rectangle = rectangle(screen, (0, 128, 255), 30, 30, 60, 60)
File "Pygame.py", line 23, in __init__
super().__init__(self, place, colour, x, y)
TypeError: __init__() takes 5 positional arguments but 6 were given
I am not sure why it gives an error as I am creating a "rectangle" object. I found some examples and they seemed to be the same as mine.
The issue is in super().__init__(self, place, colour, x, y).
You are trying to call the initializer of a class you extends, but your rectangle class is not extending any class, this means that the super() is looking for something builtin class you don't have control over it.
Since you said you took this from an example, my guess is that you are missing to extend a class.
To make the script working you can remove the call to super().__init__...
I faced same issue , iam using python 2.7.x. I resolved it using classname directly. Here is the explination Python extending with - using super() Python 3 vs Python 2
Try this
shape.__init_(self,place, colour, x, y)
super() returns a proxy object that delegates method calls to a parent.
So it has to be:
super().__init__(self, place, colour, x, y)
super().__init__(place, colour, x, y)
The call is like calling an instance method .
So I'm trying to get into using Pygame, but all of the tutorials I can find online utilize only one file. I played around with ideas on how I can load all of the images in a single function. and decided on saving them in a Dictionary. Problem is, when I try to paste the image from the dictionary, I get the following error:
Traceback (most recent call last):
File "J:\Growth of Deities\Main.py", line 32, in <module>
pygame.Surface.blit(Sprites["TileWastelandBasic"], (0, 0))
TypeError: argument 1 must be pygame.Surface, not tuple
So I played around with the code a bit and googled it for an hour or so, but I can't figure out why I'm getting an error. I assume it's because I can't save images in dictionaries, but I'm not certain. Does anyone have any ideas on how to fix it?
My Main File:
import pygame
from Startup import LoadTextures
pygame.init()
#Sets the color White
WHITE = (255, 255, 255)
#Sets screen size Variable
size = (900, 900)
#Sets Screen Size
screen = pygame.display.set_mode(size)
#Sets name of Game
pygame.display.set_caption("Growth of Deities")
closeWindow = False
clock = pygame.time.Clock()
Sprites = LoadTextures.Load()
while not closeWindow:
#Repeat while game is playing
for event in pygame.event.get():
#Close Window if you close the window
if event.type == pygame.QUIT:
closeWindow = True
#Logic Code
#Rendering Code
pygame.Surface.blit(Sprites["TileWastelandBasic"], (0, 0))
#Clear Screen
screen.fill(WHITE)
#Update Screen
pygame.display.flip()
#Set Tick Rate
clock.tick(60)
#Closes Game
pygame.quit()
My Image Loading File:
import pygame
import os, sys
def Load():
Sprites = {}
WastelandSprites = 'Assets\Textures\Tile Sprites\Wasteland'
Sprites["TileWastelandBasic"] = pygame.image.load(os.path.join(WastelandSprites + "\WastelandBasic.png")).convert_alpha()
Sprites["TileWastelandBasic"] = pygame.transform.scale(Sprites["TileWastelandBasic"], (50, 50)).convert_alpha()
return Sprites
The problem is not because of your dictionary. The signature of blit is
blit(source, dest, area=None, special_flags = 0) -> Rect
where source must be a surface. However, this assumes that blit is being invoked with a pygame.Surface instance as the receiver. Instead, you're calling the blit function from its class, which means that its signature is effectively
blit(self, source, dest, area=None, special_flags = 0) -> Rect
where self must also be a surface. You could fix your problem by changing the call to
pygame.Surface.blit(screen, Sprites["TileWastelandBasic"], (0, 0))
but I would recommend the more idiomatic
screen.blit(Sprites["TimeWastelandBasic"], (0, 0))
instead.
See: http://www.pygame.org/docs/ref/surface.html#pygame.Surface.blit
hello im new to python/pygame and tried to make a basic project. it did not turn out as planned as i don't understand this error if you can tell my why my image is not loading it will very much appreciated. Traceback (most recent call last):
File "C:\Users\Nicolas\Desktop\template\templat.py", line 15, in <module>
screen.fill(background_colour)
NameError: name 'background_colour' is not defined
this is the error i was speaking of however i have fixed now. how ever now the screen opens displayes the background and crashes.
import pygame, sys
pygame.init()
def game():
background_colour = (255,255,255)
(width, height) = (800, 600)
screen = pygame.display.set_mode((width, height))
pygame.display.set_caption('Tutorial 1')
pygame.display.set_icon(pygame.image.load('baller.jpg'))
background=pygame.image.load('path.png')
target = pygame.image.load('Player.png')
targetpos =target.get_rect()
screen.blit(target,targetpos)
screen.blit(background,(0,0))
pygame.display.update()
while True:
screen.blit(background,(0,0))
screen.blit(target,targetpos)
running = True
while running:
for event in pygame.event.get():
if event.type == pygame.QUIT:
running = False
if__name__==('__main__')
game()
You missed the __init__ definition!
While your code does run, it is not what you want. There's an infinite loop inside the definition of the class, which means, however you are running this, there's something missing. You should put this code (most of it at least) inside the __init__ function, and then create an instance of the class.
This is what I assume you want:
import pygame, sys
class game():
width, height = 600,400
def __init__(self):
ball_filename = "Ball.png"
path_filename = "path.png"
self.screen = pygame.display.set_mode((self.width, self.height))
pygame.display.set_caption('Star catcher')
self.background = pygame.image.load(path_filename)
self.screen.blit(self.background,(0,0))
self.target = pygame.image.load(ball_filename)
def run(self):
while True:
self.screen.blit(self.background, (0,0))
targetpos = self.target.get_rect()
for event in pygame.event.get():
if event.type == pygame.QUIT:
pygame.quit()
if __name__ == "__main__":
# To run this
pygame.init()
g = game()
g.run()
UPDATE:
I made more modifications than what you must do, but they could be useful. I did not test this, but it should be fine.
The error of width and height not being defined is because they are not local/global variables, but bound to the class and/or the instance of the class, therefore in their namespace. So you need to access these either via game.width (per class) or self.width (per instance, only inside a method defined in the class) or g.width (per instance, if you are outside the class definition and g is an instance of game class).
I hope I'm clear. :)