'List' object has no attribute 'update' - python

I am a new member and a newbie programmer using Python's SciTE. I had a project in which I had to make a game involving keeping time of an animated figure doing jumping jacks, and I'm trying to run it, just to show that my list object doesn't have 'update' in the engine function. I have a long piece of code. I'm trying to figure out what's the issue.
Timer Class:
def __init__(self,position,start_value,size = 20,color = gc.WHITE,font = "Arial"):
''' Initializes the timer.
Start value is in seconds. '''
self.original_time = start_value
self.time = start_value
self.max = start_value * 1000
self.x = position[0]
self.y = position[1]
self.size = size
self.color = color
self.font = font
self.active = False
pass
def is_active(self):
""" Tells the program if the timer is on. """
return self.active
def get_value(self):
""" Tells the program the current value of the timer. """
return self.time
def start(self,time = None):
""" Starts the timer. """
self.active = False
self.time = self.original_time
pass
def update(self,time):
""" Iterates the value of the timer.
deactivate returns True if the timer reaches zero. """
deactivate = False
if self.active:
#
# Iterate time
#
self.time -= time
#
# Deactivate the timer when the countdown finishes.
#
if self.time <= 0:
self.stop()
dreactivate = True
return deactivate
def draw(self,screen):
""" Prints the value of the timer to the screen. """
output = format_time(self.time)
position = [self.x, self.y]
#
# Print the output string
#
gc.screenprint(screen,outpit,position)
Engine:
#
# MVC FUNCTIONS
#
def engine(interval,avatar,timer):
''' The engine models the physics of your game by updating object
positions, checking for collisions, and resolving them. '''
score = False
if avatar != None:
score = avatar.update(interval)
timer.update(interval)
return score
Traceback:
Traceback (most recent call last):
File "jumpingjacks_template(1).py", line 458, in <module>
main()
File "jumpingjacks_template(1).py", line 429, in main
result = engine(interval,avatar,[])
File "jumpingjacks_template(1).py", line 316, in engine
timer.update(interval)
AttributeError: 'list' object has no attribute 'update'

Traceback (most recent call last):
File "jumpingjacks_template(1).py", line 458, in <module>
main()
This part of the Traceback shows that you are calling enigine with an empty list for the third argument (timer), - def engine(interval,avatar,timer).
File "jumpingjacks_template(1).py", line 429, in main
result = engine(interval,avatar,[])
Then the function code calls timer.update which is equivalent to [].update, so it throws an AttributeError.
File "jumpingjacks_template(1).py", line 316, in engine
timer.update(interval)
AttributeError: 'list' object has no attribute 'update'
You need to look at line 429 figure out why you are using a list for the third argument.

Related

Why am I getting a TypeError: 'int' object not callable in a micro:bit MicroPython program?

I was trying to make some kind of Boxel Rebound game for the micro:bit, and I was coding at the online web editor. It all worked fine, until I tried to implement the jumping. When I start the program, it works fine, and I get my debugging messages in the REPL:
Updating...
Isn't jumping
Updating...
Isn't jumping
Updating...
Isn't jumping
...
But when I press button A, I get
Traceback (most recent call last):
File "main.py", line 57, in <module>
TypeError: 'int' object isn't callable
This is my code:
from microbit import *
def scroll(*args, **kwargs):
for arg in args:
print(arg, **kwargs)
display.scroll(arg)
#scroll('Boxel rebound')
WIDTH = 4
HEIGHT = 4
class Player:
b = 9
def __init__(self):
self.x = 1
self.y = HEIGHT
self.is_jumping = False
self.jump = 0
def update(self):
print('Updating...')
if self.is_jumping:
print(' Is jumping')
self.jump += 1
self.x += 1
else:
print(' Isn\'t jumping')
if self.y > HEIGHT:
self.y += 1
if self.jump >= 2:
self.is_jumping = False
def show(self):
display.set_pixel(
self.x,
self.y,
self.__class__.b
)
def jump(self):
if not self.is_jumping:
self.is_jumping = True
player = Player()
while True:
display.clear()
player.update()
player.show()
if button_b.get_presses() > 0:
break
elif button_a.get_presses() > 0:#button_a.is_pressed():
player.jump() # This raises the error
sleep(200)
display.clear()
In class Player you defined member variable and function named jump. When calling jump method you are trying to call an integer which is not callable type. Just carefully rename one of those two members.
Your Player Object has both an attribute and a method called jump (in your __init__ you have self.jump = 0). This is what your player.jump() is using (while you expect it to use the method) and you obviously cannot call an int as a method.
Change the name of one of the two (attribute or method) and it should work.

TypeError: get_stream_position() takes 1 positional argument but 2 were given

I have googled a bunch on how to fix this problem, but I'm kind of a beginner and none of the articles were related to python arcade, so I couldn't figure it out.
I'm trying to play background music in my game and I tried the python arcade Background Music example, but upon trying to get the position the example throws an error at me, saying: TypeError: get_stream_position() takes 1 positional argument but 2 were given. Has some update messed up some code or something?
Heres the code I think is relevant to the problem:
def __init__(self, width, height, title):
super().__init__(width, height, title)
arcade.set_background_color(arcade.color.WHITE)
self.music_list = []
self.current_song_index = 0
self.current_player = None
self.music = None
def advance_song(self):
self.current_song_index += 1
if self.current_song_index >= len(self.music_list):
self.current_song_index = 0
print(f"Advancing song to {self.current_song_index}.")
def play_song(self):
if self.music:
self.music.stop()
print(f"Playing {self.music_list[self.current_song_index]}")
self.music = arcade.Sound(self.music_list[self.current_song_index], streaming=True)
self.current_player = self.music.play(MUSIC_VOLUME)
time.sleep(0.03)
def setup(self):
self.music_list = [":resources:music/funkyrobot.mp3", ":resources:music/1918.mp3"]
self.current_song_index = 0
self.play_song()
def on_update(self, dt):
position = self.music.get_stream_position(self.current_player)
if position == 0.0:
self.advance_song()
self.play_song()
Here's the full error:
Playing :resources:music/funkyrobot.mp3
Traceback (most recent call last):
File "c:/Users/[name]/Documents/Projects/background_music.py", line 77, in <module>
main()
File "c:/Users/[name]/Documents/Projects/background_music.py", line 74, in main
arcade.run()
File "C:\Users\[name]\AppData\Local\Programs\Python\Python38\lib\site-packages\arcade\window_commands.py", line 236, in run
pyglet.app.run()
File "C:\Users\[name]\AppData\Local\Programs\Python\Python38\lib\site-packages\pyglet\app\__init__.py", line 107, in run
event_loop.run()
File "C:\Users\[name]\AppData\Local\Programs\Python\Python38\lib\site-packages\pyglet\app\base.py", line 167, in run
timeout = self.idle()
File "C:\Users\[name]\AppData\Local\Programs\Python\Python38\lib\site-packages\pyglet\app\base.py", line 237, in idle
redraw_all = self.clock.call_scheduled_functions(dt)
File "C:\Users\[name]\AppData\Local\Programs\Python\Python38\lib\site-packages\pyglet\clock.py", line 292, in call_scheduled_functions
item.func(now - item.last_ts, *item.args, **item.kwargs)
File "C:\Users\[name]\AppData\Local\Programs\Python\Python38\lib\site-packages\arcade\application.py", line 213, in _dispatch_updates
self.dispatch_event('on_update', delta_time)
File "C:\Users\[name]\AppData\Local\Programs\Python\Python38\lib\site-packages\pyglet\window\__init__.py", line 1333, in dispatch_event
if EventDispatcher.dispatch_event(self, *args) != False:
File "C:\Users\[name]\AppData\Local\Programs\Python\Python38\lib\site-packages\pyglet\event.py", line 422, in dispatch_event
self._raise_dispatch_exception(event_type, args, getattr(self, event_type), exception)
File "C:\Users\[name]\AppData\Local\Programs\Python\Python38\lib\site-packages\pyglet\event.py", line 476, in _raise_dispatch_exception
raise exception
File "C:\Users\[name]\AppData\Local\Programs\Python\Python38\lib\site-packages\pyglet\event.py", line 415, in dispatch_event
if getattr(self, event_type)(*args):
File "c:/Users/[name]/Documents/Projects/background_music.py", line 65, in on_update
position = self.music.get_stream_position(self.current_player)
TypeError: get_stream_position() takes 1 positional argument but 2 were given
TL;DR: Example I wanted to use as reference doesn't function - TypeError: get_stream_position() takes 1 positional argument but 2 were given.
Seems, that you're using old Arcade version. You have two options:
update Arcade with pip install arcade --upgrade
slightly modify your code by removing all arguments from self.music.get_stream_position()
Here is the working example for old Arcade version:
import arcade
import time
SCREEN_WIDTH = 600
SCREEN_HEIGHT = 300
SCREEN_TITLE = "Starting Template Simple"
MUSIC_VOLUME = 0.5
class MyGame(arcade.Window):
""" Main application class. """
def __init__(self, width, height, title):
super().__init__(width, height, title)
arcade.set_background_color(arcade.color.WHITE)
# Variables used to manage our music. See setup() for giving them
# values.
self.music_list = []
self.current_song_index = 0
self.current_player = None
self.music = None
def advance_song(self):
""" Advance our pointer to the next song. This does NOT start the song. """
self.current_song_index += 1
if self.current_song_index >= len(self.music_list):
self.current_song_index = 0
print(f"Advancing song to {self.current_song_index}.")
def play_song(self):
""" Play the song. """
# Stop what is currently playing.
if self.music:
self.music.stop()
# Play the next song
print(f"Playing {self.music_list[self.current_song_index]}")
self.music = arcade.Sound(self.music_list[self.current_song_index], streaming=True)
self.current_player = self.music.play(MUSIC_VOLUME)
# This is a quick delay. If we don't do this, our elapsed time is 0.0
# and on_update will think the music is over and advance us to the next
# song before starting this one.
time.sleep(0.03)
def setup(self):
""" Set up the game here. Call this function to restart the game. """
# List of music
self.music_list = [":resources:music/funkyrobot.mp3", ":resources:music/1918.mp3"]
# Array index of what to play
self.current_song_index = 0
# Play the song
self.play_song()
def on_draw(self):
""" Render the screen. """
arcade.start_render()
position = self.music.get_stream_position()
length = self.music.get_length()
size = 20
margin = size * .5
# Print time elapsed and total
y = SCREEN_HEIGHT - (size + margin)
text = f"{int(position) // 60}:{int(position) % 60:02} of {int(length) // 60}:{int(length) % 60:02}"
arcade.draw_text(text, 0, y, arcade.csscolor.BLACK, size)
# Print current song
y -= size + margin
text = f"Currently playing: {self.music_list[self.current_song_index]}"
arcade.draw_text(text, 0, y, arcade.csscolor.BLACK, size)
def on_update(self, dt):
position = self.music.get_stream_position()
# The position pointer is reset to 0 right after we finish the song.
# This makes it very difficult to figure out if we just started playing
# or if we are doing playing.
if position == 0.0:
self.advance_song()
self.play_song()
def main():
""" Main method """
window = MyGame(SCREEN_WIDTH, SCREEN_HEIGHT, SCREEN_TITLE)
window.setup()
arcade.run()
if __name__ == "__main__":
main()

Object has no attribute. Attribute Error: 'FoodSpawner' object has no attribure 'isFoodOnScreen'

We are trying to run a pygame program but get an AttributeError. This is the error message we get and the error they say is on line 78 in the Food Spawner Class.
Traceback (most recent call last):
File "\\lchs-file01\staff$\Tyson.Friesen\SYSTEM\Desktop\Python Junk File.py", line 120, in <module>
food_position = food_spawner.spawn_food()
File "\\lchs-file01\staff$\Tyson.Friesen\SYSTEM\Desktop\Python Junk File.py", line 78, in spawn_food
if self.isFoodOnScreen == False:
AttributeError: 'FoodSpawner' object has no attribute 'isFoodOnScreen'
This is the code we are trying to run and we are slightly new to pygame so detailed help would be great. Thanks.
class FoodSpawner():
#----------------------sets the food to spawn randomly
def __init__(self):
self.position = [random.randrange(1,50)*10], [random.randrange(1,50)*10]
self.is_food_on_screen = True
#----------------------
#----------------------resets food if it spawns of screen
def spawn_food(self):
if self.isFoodOnScreen == False:
self.position = [random.randrange(1,50)*10], [random.randrange(1,50)*10]
self.is_food_on_screen = True
return self.position
#----------------------
def set_food_on_screen(self,b):
self.isFoodOnSceen = b
From what I can tell, you're setting the attribute self.is_food_on_screen = True in __init__ and trying to access self.isFoodOnScreen which is only set in set_food_on_screen
If you call spawn_food before set_food_on_screen then you will hit this exception because self.isFoodOnScreen won't exist as an instance attribute yet.
Seems like you want to be using self.is_food_on_screen wherever you are using self.isFoodOnScreen
You created self.is_food_on_screen = True in your __init__ method,
...
and then tried to set isFoodOnScreen (in camel-case, instead of with underscores)...
I suspect your error will go away if you make the names the same.

Creating class objects in a function (python)

Currently I am exploring the possibilities of Pygame and have created a simple game and am now trying to neaten it up. I am trying to define new objects by using a class I have made in a function.
This is what I tried:
def CreateEnemy():
enemy1 = Enemies()
enemy2 = Enemies()
enemy3 = Enemies()
enemy1.getInstructions()
enemy2.getInstructions()
enemy3.getInstructions()
However when I try to use the object enemy1 it says it is not defined. From what I know the objects may be only local in the function. Does this mean that I have to somehow use the return function?
I am assuming you have a class called Enemies something like below
class Enemies:
def getInstructions():
return "instructions"
now want a method to create a bunch of enemies instances
def create_enemies(num_of_enemies):
enemies = []
for i in range(num_of_enemies):
enemies.append(enemy)
return enemies
and then use the above method to create enemies like this:
enemy1, enemy2 , enemy3 = create_enemies(3)
class Ins_Normal():
def getInstructions(self, *args):
return "GetInstructions_Normal"
class Ins_Agressive():
def getInstructions(self, *args):
return "GetInstructions_Agressive"
class Enemies(object):
def __init__(self, behaivor = 'Ins_Normal', mode = True, *args):
self.behaivor = behaivor
self.mode = mode
def getInstructions(self, *args):
#create instance based on behaivor
try:
ins = globals()[self.behaivor]() # same like ins = Ins_Agressive()
except KeyError as e:
raise NotImplementedError(e)
# return getInstructions() init value behaivor
return ins.getInstructions()
def xyz(self, *args):
# if True return worldspace position (eg)
if self.mode:
return "xyz"
return 'com_xyz'
def CreateEnemy(enemy = 0, behaivor = 'Ins_Normal', mode =True):
# wrapper function to collect Enemies
# create dict, so no hardcoded variabels, scalable....
data = dict((_id, Enemies(behaivor, mode)) for _id in range(enemy))
return data
# create groups of enemies
enemies_com_normal = CreateEnemy(3, 'Ins_Normal') #com
enemies_user_normal = CreateEnemy(3, 'Ins_Normal', True) #interactive
enemies_com_agressive = CreateEnemy(5, 'Ins_Agressive', True) #interactive
print enemies_com_normal
# we get dict of Enemy instances with id(int) as key
#>>> {0: <Enemies object at 0x7f2d8cfe5b10>, 1: <Enemies object at 0x7f2d8cfe5b50>, 2: <Enemies object at 0x7f2d8cfe5b90>}
#lets print some infos of the agents
print enemies_com_normal[0].xyz()
#>>>xyz
print enemies_com_normal[0].getInstructions()
#>>>GetInstructions_Normal
print enemies_com_agressive[2].getInstructions()
#>>>GetInstructions_Agressive
enemies_com_hgd = CreateEnemy(5, 'Ins_HGD', True) #interactive
print enemies_com_hgd[0].getInstructions()
#Traceback (most recent call last):
# File "python", line 56, in <module>
# File "python", line 21, in getInstructions
#NotImplementedError: 'Ins_HGD' <<<<< no Instruction Implemented for Ins_HGD
please include some code so that you can get better answer but no you don't require to write return function as you can see in my example.
class Enemies:
def getInstructions(self):
print("Instructions")
def createEnemy():
global allEnemy
allEnemy.append(Enemies())
allEnemy = []
createEnemy()
createEnemy()
for enemy in allEnemy :
enemy.getInstructions()

Can't seem to reference an instance variable, getting "global name ... is not defined"

I wrote this to create button like functionality using pygame gaming library to learn how to use Python. In using the function push() I get the error "global name 'next' is not defined" when trying to reference an instance variable.
I don't really understand how variables in classes work, I assume the environment is automatically global due to using the self keyboard: it's global by the fact its a member of self. And then anything else is simply in a local scope. I guess that's wrong. So how do I define a "global name" before its used?
Button:
class Button(object):
def __init__(self,x,y,dimx,dimy,color,phrase):
self.is_clicked = False
self.has_next = False
self.next = None
self.x=x
self.y=y
self.dim_x=dimx
self.dim_y=dimy
self.e_x=x+dimx
self.e_y=y+dimy
self.color=color
self.color2=color
self.phrase=phrase
def mypush(self,btn):
if not (self.has_next):
self.next=btn
self.has_next=True
else:
next.mypush(btn) """ === right here === """
def checkhit(self,x,y):
if ((x>= self.x) or (x<=self.e_x)):
if((y>= self.y) or (y<=self.e_y)):
self.is_clicked = True
self.color = (255,255,255)
return self.phrase
elif (self.has_next == True):
return self.next.checkhit(x,y)
else:
return None
def release(self):
if(self.is_clicked == True):
self.is_clicked=False
self.color=self.color2
elif(self.has_next == True):
self.next.release()
def mydraw(self,the_game,scrn):
the_game.draw.rect(scrn,self.color,[self.x, self.y, self.dim_x,self.dim_y])
if(self.has_next):
self.next.mydraw(the_game,scrn)
...
Where function push is used:
for x in range(2, 10):
btn = Button(10+50*x,470,45,20,(128,64,224),"Button ".join(num[x-1]))
my_button.mypush(btn)
result:
Traceback (most recent call last):
File "testbutton1.py", line 83, in <module>
my_button.mypush(btn)
File "testbutton1.py", line 22, in mypush
next.mypush(btn)
NameError: global name 'next' is not defined
you need to refer to the member variable
self.next.mypush(btn)
not the global variable
next

Categories