simple archery game in python - python

I'm just starting out with python and I'm trying to make a little archery game. However, it creates an error at this point: d = math.sqrt(x*x + y*y) (i.e. the distance between the new point and the original center of the cirlce) Any ideas on why this doesn't work?
def archery():
win = GraphWin("Archery Game", 500,500)
win.setCoords(-50, -50, 50, 50)
circle1 = Circle(Point(0,0), 40)
circle1.setFill("white")
circle1.draw(win)
circle2 = Circle(Point(0,0), 35)
circle2.setFill("black")
circle2.draw(win)
circle3 = Circle(Point(0,0), 30)
circle3.setFill("blue")
circle3.draw(win)
circle4 = Circle(Point(0,0), 25)
circle4.setFill("red")
circle4.draw(win)
circle5 = Circle(Point(0,0), 20)
circle5.setFill("yellow")
circle5.draw(win)
score = 0
for i in range(5):
p = win.getMouse()
p.draw(win)
x = p.getX
y = p.getY
d = math.sqrt(x*x + y*y)
if 40 >= d > 35:
score = score + 1
elif 35 >= d > 30:
score = score + 3
elif 30 >= d > 25:
score = score + 5
elif 25 >= d > 20:
score = score + 7
elif 20 >= d >= 0:
score = score + 9
else:
score = score + 0
print("Your current score is:", score)
win.getMouse()
win.close()

x = p.getX
y = p.getY
will return the function getX and getY instead of executing it. As Mike Steder said, try getX(), that should return a value.

First, you probably need to do:
x = p.getX()
y = p.getY()
i.e. call the functions and use the return value, instead of using the functions themselves.
Second, you can change the math.sqrt(x*x + y*y) call to:
d = math.hypot(x, y)

Related

Function not executing for every item (except last) in list while iterating through them

I have my update_entities function that is constantly updating my "entities' " states. The upward and downward functions activate the prototype movement for the entities.
The reason the function is in a for loop is because in each "round" in my game there are three entities / enemies, so the loop iterates through each of the entities and takes control of their states (positions and whether they shot their weapons).
The problem I'm running into is the shooting function, the function itself works just fine but only for the 3rd of the three entities. It's quite weird behavior and definitely unexpected, I don't understand why that's been happening because when iterating through each of the entities, each of them gets an opportunity to move in an oscillating behavior, but, again, the 3rd one is the only one that shoots.
Here is the code that could relate to the problem.
entity_bullet = None
ebullet_coordinates = [(0, 0), (0, 0)]
entity_bullets = []
def get_ebullet_coordinates(self):
for child in self.entity_bullets:
x1, y1 = child.pos
self.ebullet_coordinates[0] = (x1, y1)
x2, y2 = child.pos[0] + child.width, child.pos[1] + child.height
self.ebullet_coordinates[1] = (x2, y2)
def entity_shoot(self):
for child in self.entities:
self.get_entity_coordinates()
x = self.entity_coordinates[0][0]
y = self.entity_coordinates[0][1] - 20
if child.source == "images/evil_drone.png":
self.entity_bullet = Image(source="images/evil_drone_bullet2.png",
pos=(x, y))
elif child.source == "images/angry_cloud.png":
self.entity_bullet = Image(source="images/lightning_bullet2.png",
pos=(x, y))
elif child.source == "images/skullairballoon.png":
self.entity_bullet = Image(source="images/bomb.png",
pos=(x, y))
self.add_widget(self.entity_bullet)
self.entity_bullets.append(self.entity_bullet) # Add to list for them to move
def update_entity_bullets(self):
self.get_drone_coordinates()
self.get_entity_coordinates()
drone_xmin, drone_ymin = self.drone_coordinates[0][0], self.drone_coordinates[0][1]
drone_xmax, drone_ymax = self.drone_coordinates[1][0], self.drone_coordinates[1][1]
bullet_xmin, bullet_ymin = self.entity_coordinates[0][0], self.entity_coordinates[0][1] - 20
bullet_xmax, bullet_ymax = self.entity_coordinates[1][0], self.entity_coordinates[1][1]
xdistance = bullet_xmax - drone_xmin
ydistance = bullet_ymin - drone_ymax
final_xdistance = (xdistance / 60) + 1
final_ydistance = (ydistance / 60) + 1
for self.entity_bullet in self.entity_bullets:
for child in self.entity_bullets:
if child.pos[1] <= 0:
self.remove_widget(child)
elif child.pos[1] >= self.height - 10:
self.remove_widget(child)
if child.pos[0] <= -10:
self.remove_widget(child)
elif child.pos[0] >= self.width - 10:
self.remove_widget(child)
self.entity_bullet.pos[0] -= final_xdistance
self.entity_bullet.pos[1] -= final_ydistance
pass
def check_ebullet_collision(self, dt):
if self.game_ongoing:
self.get_drone_coordinates()
self.get_ebullet_coordinates()
drone_xmin, drone_ymin = self.drone_coordinates[0][0], self.drone_coordinates[0][1]
drone_xmax, drone_ymax = self.drone_coordinates[1][0], self.drone_coordinates[1][1]
bullet_xmin, bullet_ymin = self.ebullet_coordinates[0][0], self.ebullet_coordinates[0][1]
bullet_xmax, bullet_ymax = self.ebullet_coordinates[1][0], self.ebullet_coordinates[1][1]
if ((drone_xmax - 40) >= bullet_xmin >= (drone_xmin - 50)) and ((drone_ymax - 65) >= bullet_ymin >= (drone_ymin - 50)):
print("hit")
for self.entity_bullet in self.entity_bullets:
self.remove_widget(self.entity_bullet)
for ebullet in self.entity_bullets:
self.entity_bullets.remove(ebullet)
self.remove_widget(ebullet)
def update_entities(self):
for child in self.entities:
z = random.randint(1, 3000)
a = random.randint(1, 215)
def upward():
child.pos[1] += .1
def downward():
child.pos[1] -= .1
if z >= 2800 or z % 2 == 0:
for i in range(random.randint(1, 20)):
upward()
else:
for i in range(random.randint(1, 22)):
downward()
if a == 205:
self.entity_shoot()

How to solve unsupported operand type(s) for +: 'dict_items' and 'dict_items' in Python

I'm trying to do Schelling’s Segregation Model in Python which takes 6 parameters: the width and height of the city, the ratio of empty houses in the city, the similarity threshold, the number of iterations, and the number of races.
There are 4 methods within the Schelling class: populate, is_unsatisfied, update, move_to_empty, and plot.
This is the code:
class Schelling:
def __init__(self, width, height, empty_ratio, similarity_threshold, n_iterations, races = 2):
self.width = width
self.height = height
self.races = races
self.empty_ratio = empty_ratio
self.similarity_threshold = similarity_threshold
self.n_iterations = n_iterations
self.empty_houses = []
self.agents = {}
def populate(self):
self.all_houses = list(itertools.product(range(self.width),range(self.height)))
random.shuffle(self.all_houses)
self.n_empty = int( self.empty_ratio * len(self.all_houses) )
self.empty_houses = self.all_houses[:self.n_empty]
self.remaining_houses = self.all_houses[self.n_empty:]
houses_by_race = [self.remaining_houses[i::self.races] for i in range(self.races)]
for i in range(self.races):
#create agents for each race
self.agents = dict(
self.agents.items() +
dict(zip(houses_by_race[i], [i+1]*len(houses_by_race[i]))).items()
)
def is_unsatisfied(self, x, y):
race = self.agents[(x,y)]
count_similar = 0
count_different = 0
if x > 0 and y > 0 and (x-1, y-1) not in self.empty_houses:
if self.agents[(x-1, y-1)] == race:
count_similar += 1
else:
count_different += 1
if y > 0 and (x,y-1) not in self.empty_houses:
if self.agents[(x,y-1)] == race:
count_similar += 1
else:
count_different += 1
if x < (self.width-1) and y > 0 and (x+1,y-1) not in self.empty_houses:
if self.agents[(x+1,y-1)] == race:
count_similar += 1
else:
count_different += 1
if x > 0 and (x-1,y) not in self.empty_houses:
if self.agents[(x-1,y)] == race:
count_similar += 1
else:
count_different += 1
if x < (self.width-1) and (x+1,y) not in self.empty_houses:
if self.agents[(x+1,y)] == race:
count_similar += 1
else:
count_different += 1
if x > 0 and y < (self.height-1) and (x-1,y+1) not in self.empty_houses:
if self.agents[(x-1,y+1)] == race:
count_similar += 1
else:
count_different += 1
if x > 0 and y < (self.height-1) and (x,y+1) not in self.empty_houses:
if self.agents[(x,y+1)] == race:
count_similar += 1
else:
count_different += 1
if x < (self.width-1) and y < (self.height-1) and (x+1,y+1) not in self.empty_houses:
if self.agents[(x+1,y+1)] == race:
count_similar += 1
else:
count_different += 1
if (count_similar+count_different) == 0:
return False
else:
return float(count_similar)/(count_similar+count_different) < self.happy_threshold
def update(self):
for i in range(self.n_iterations):
self.old_agents = copy.deepcopy(self.agents)
n_changes = 0
for agent in self.old_agents:
if self.is_unhappy(agent[0], agent[1]):
agent_race = self.agents[agent]
empty_house = random.choice(self.empty_houses)
self.agents[empty_house] = agent_race
del self.agents[agent]
self.empty_houses.remove(empty_house)
self.empty_houses.append(agent)
n_changes += 1
print (n_changes)
if n_changes == 0:
break
def move_to_empty(self, x, y):
race = self.agents[(x,y)]
empty_house = random.choice(self.empty_houses)
self.updated_agents[empty_house] = race
del self.updated_agents[(x, y)]
self.empty_houses.remove(empty_house)
self.empty_houses.append((x, y))
def plot(self, title, file_name):
fig, ax = plt.subplots()
#If you want to run the simulation with more than 7 colors, you should set agent_colors accordingly
agent_colors = {1:'b', 2:'r', 3:'g', 4:'c', 5:'m', 6:'y', 7:'k'}
for agent in self.agents:
ax.scatter(agent[0]+0.5, agent[1]+0.5, color=agent_colors[self.agents[agent]])
ax.set_title(title, fontsize=10, fontweight='bold')
ax.set_xlim([0, self.width])
ax.set_ylim([0, self.height])
ax.set_xticks([])
ax.set_yticks([])
plt.savefig(file_name)
Now that has an implementation of the Schelling class, can run different simulations and plot the results.
Build three simulations with the following characteristics:
width = 50, and height = 50 (2500 houses)
30% of empty houses
Similarity Threshold = 30% (for Simulation 1), Similarity Threshold = 50% (for Simulation 2), and Similarity Threshold = 80% (for Simulation 3)
Maximum number of iterations = 500
Number of races = 2
Start by creating and populating the cities.
schelling_1 = Schelling(50, 50, 0.3, 0.3, 500, 2)
schelling_1.populate()
schelling_2 = Schelling(50, 50, 0.3, 0.5, 500, 2)
schelling_2.populate()
schelling_3 = Schelling(50, 50, 0.3, 0.8, 500, 2)
schelling_3.populate()
After I run schelling_1.populate(), there is an error occurs.
The error is unsupported operand type(s) for +: 'dict_items' and 'dict_items' on
self.agents = dict(
self.agents.items() +
dict(zip(houses_by_race[i], [i+1]*len(houses_by_race[i]))).items()
)
How to make this error solve ?
Thank you

Why is my loop still running? (Python Zelle Graphics)

I'm trying to figure out why the while loop in one of my functions is still running even after the points in my graphics are equal, which is when I set it to stop. Is there anything I'm doing wrong? I've tried to switch other things around to get it to work but no luck.
It's for a game--when the character reaches the endbox the loop needs to break, but it isn't doing that after I explicitly coded it to. It's in the second function I have:
from graphics import *
def field():
#creating the window
win = GraphWin('The Field',400,400)
win.setBackground('white')
#drawing the grid
boxlist = []
for i in range(0,400,40):
for j in range(0,400,40):
box = Rectangle(Point(i,j),Point(i+40,j+40))
box.setOutline('light gray')
box.draw(win)
boxlist.append(box)
#creating other boxes
startbox = Rectangle(Point(0,0),Point(40,40))
startbox.setFill('lime')
startbox.setOutline('light gray')
startbox.draw(win)
endbox = Rectangle(Point(360,360),Point(400,400))
endbox.setFill('red')
endbox.setOutline('light gray')
endbox.draw(win)
boxlist.append(startbox)
boxlist.append(endbox)
#creating Pete
pete = Rectangle(Point(2,2),Point(38,38))
pete.setFill('gold')
pete.draw(win)
return win,boxlist,pete
def move(win2,boxlist,pete,endbox):
peteloc = pete.getCenter()
#creating loop to move pete
while peteloc != endbox.getCenter():
click = win2.getMouse()
x = click.getX()
y = click.getY()
peteloc = pete.getCenter()
petex = peteloc.getX()
petey = peteloc.getY()
#moving pete
if x>=petex+20 and y<=petey+20 and y>=petey-20:
pete.move(40,0)
elif x<=petex-20 and y<=petey+20 and y>=petey-20:
pete.move(-40,0)
elif y>=petey+20 and x<=petex+20 and x>=petex-20:
pete.move(0,40)
elif y<=petey-20 and x<=petex+20 and x>=petex-20:
pete.move(0,-40)
peteloc = pete.getCenter()
# The main function
def main():
win2,boxlist,pete = field()
endbox = boxlist[len(boxlist)-1]
move(win2,boxlist,pete,endbox)
main()
I think maybe it is caused by precision of float. I guess pete.getCenter() and endbox.getCenter() are something like [float, float], you should avoid using != between float, such as 1.0000001 is not equal to 1.
So even if the character reaches the endbox, the position will still get a little float bias.
So you can change a != b to abs(a - b) > acceptable_error when the error is acceptable. Sample code is like:
# while peteloc != endbox.getCenter():
while abs(peteloc.getX() - endbox.getCenter().getX()) > 0.01 and abs(peteloc.getY() - endbox.getCenter().getY()) > 0.01:
Hope that will help you.
Zelle graphics Point objects don't appear to ever compare as equal:
>>> from graphics import *
>>> a = Point(100, 100)
>>> b = Point(100, 100)
>>> a == b
False
>>>
We have to extract coordinates and do our own comparison. Although #recnac provides a workable solution (+1), I'm going to suggest a more general one. We'll create a distance() method that's valid for any object that inherits from _BBox, which includes Rectangle, Oval, Circle and Line:
def distance(bbox1, bbox2):
c1 = bbox1.getCenter()
c2 = bbox2.getCenter()
return ((c2.getX() - c1.getX()) ** 2 + (c2.getY() - c1.getY()) ** 2) ** 0.5
We can now measure the distance between objects, horizontally, vertically and diagonally. Since your boxes are moving twenty pixels at a time, we can assume that if they are withing 1 pixel of each other, they are in the same location. Your code rewritten to use the distance() method and other tweaks:
from graphics import *
def field(win):
# drawing the grid
boxlist = []
for i in range(0, 400, 40):
for j in range(0, 400, 40):
box = Rectangle(Point(i, j), Point(i + 40, j + 40))
box.setOutline('light gray')
box.draw(win)
boxlist.append(box)
# creating other boxes
startbox = Rectangle(Point(0, 0), Point(40, 40))
startbox.setFill('lime')
startbox.setOutline('light gray')
startbox.draw(win)
boxlist.append(startbox)
endbox = Rectangle(Point(360, 360), Point(400, 400))
endbox.setFill('red')
endbox.setOutline('light gray')
endbox.draw(win)
boxlist.append(endbox)
# creating Pete
pete = Rectangle(Point(2, 2), Point(38, 38))
pete.setFill('gold')
pete.draw(win)
return boxlist, pete
def distance(bbox1, bbox2):
c1 = bbox1.getCenter()
c2 = bbox2.getCenter()
return ((c2.getX() - c1.getX()) ** 2 + (c2.getY() - c1.getY()) ** 2) ** 0.5
def move(win, pete, endbox):
# creating loop to move pete
while distance(pete, endbox) > 1:
click = win.getMouse()
x, y = click.getX(), click.getY()
peteloc = pete.getCenter()
petex, petey = peteloc.getX(), peteloc.getY()
# moving pete
if x >= petex + 20 and petey - 20 <= y <= petey + 20:
pete.move(40, 0)
elif x <= petex - 20 and petey - 20 <= y <= petey + 20:
pete.move(-40, 0)
elif y >= petey + 20 and petex - 20 <= x <= petex + 20:
pete.move(0, 40)
elif y <= petey - 20 and petex - 20 <= x <= petex + 20:
pete.move(0, -40)
# The main function
def main():
# creating the window
win = GraphWin('The Field', 400, 400)
win.setBackground('white')
boxlist, pete = field(win)
endbox = boxlist[-1]
move(win, pete, endbox)
main()

Variable keeps its value

I need some help once again. The problem is, when I call a function that should add to a variable, the variable stays at its original value.
Code:
import random
def christncombat(x,y,z):
x += 1
if x > 26:
x = 1
y += 1
if y > 26:
y = 1
z += 1
if z > 26:
z = 1
x = 1
y = 1
encrypt = {65:90, 66:90, 67:72, 68:78, 69:77, 70:83, 71:87, 72:67, 73:73, 74:89, 75:84,
76:81, 77:69, 78:68, 79:79, 80:66, 81:76, 82:82, 83:70, 84:75, 85:85, 86:86,
87:71, 88:88, 89:74, 90:65}
encrypted = []
r1 = random.randint(1,26)
r2 = random.randint(1,26)
r3 = random.randint(1,26)
security = str(r1) + "a" + "-" + str(r2) + "b" + "-" + str(r3) + "c"
input_en = input("Zadejte text, ktery chcete zasifrovat (pouzivejte velka pismena): ")
for i in range(0,len(input_en)):
coded = input_en[i]
coded = ord(coded)
coded = encrypt[coded]
full = r1 + r2 + r3
coded += full
while(coded > 90):
rekt = coded - 90
coded = 65 + rekt
christncombat(r1,r2,r3)
full1 = r1 + r2 + r3
coded += full1
while(coded > 90):
rekt = coded - 90
coded = 65 + rekt
done = chr(coded)
encrypted.append(done)
print(encrypted)
print("Bezpecnostni kod je",security)
Although the issue is probably in this part:
def christncombat(x,y,z):
x += 1
if x > 26:
x = 1
y += 1
if y > 26:
y = 1
z += 1
if z > 26:
z = 1
x = 1
y = 1
You need to return the modified values from the function, like this:
def christncombat(x,y,z):
x += 1
if x > 26:
x = 1
y += 1
if y > 26:
y = 1
z += 1
if z > 26:
z = 1
x = 1
y = 1
return x, y, z
Then in the calling code you can capture those returned values like this:
r1, r2, r3 = christncombat(r1, r2, r3)
Perhaps you want to return values from your function? You could put the values in a list and return the list:
def christncombat(x,y,z):
x += 1
if x > 26:
x = 1
y += 1
if y > 26:
y = 1
z += 1
if z > 26:
z = 1
x = 1
y = 1
value_list = [x, y, z]
return value_list
now, you can call the function in the main part of your code:
new_value_list = christncombat(r1,r2,r3)
now, in your new_value_list, you have r1, r2, and r3 all changed to what you want them to be. Now, you can access all the variables:
new_r1 = new_value_list[0]
new_r2 = new_value_list[1]
new_r3 = new_value_list[2]

How do I properly use a Callback in this code? (Kivy)

Why does this code not work? I think it's something to do with x1 being already defined because I get the error "UnboundLocalError: local variable 'x1' referenced before assignment" whenever I click b1. Please I've searched the entire Internet with no luck.... Sorry I'm relatively new to Python and programming.
import calendar
import datetime
from kivy.app import App
from kivy.uix.label import Label
from kivy.uix.button import Button
from kivy.uix.gridlayout import GridLayout
from kivy.uix.label import Label
now = datetime.datetime.now()
h = now.hour
m = now.minute
s = now.second
year = now.year
month = now.month
day = now.day
home = 'home.'
weekday1 = calendar.weekday(year, month, day)
if len(str(m)) == 1:
zero = '0'
else:
zero = ''
if len(str(s)) == 1:
zero1 = '0'
else:
zero1 = ''
if weekday1 == 0:
day = 'Monday'
time = '''Period 1/2/3/4 = History
Period 5/6 = Japanese'''
if h == 8 and m >= 40:
current = 'Homeroom.'
elif h == 9 or (h == 10 and m <= 40):
current = 'History.'
elif h == 10 and m > 40:
current = 'recess.'
elif h == 11 or (h == 12 and m <= 40):
current = 'History.'
elif (h == 12 and m > 40) or (h == 13 and m <= 20):
current = 'lunch.'
elif (h == 13 and m > 20) or h == 14:
current = 'Japanese.'
else:
current = home
elif weekday1 == 1:
day = 'Tuesday'
time = '''Period 1 = English
Period 2 = Maths
Period 3/4 = English
Period 5/6 = ICT'''
if h == 8 and m>= 40:
current = 'Homeroom.'
elif h == 9 and m <= 50:
current = 'English.'
elif (h == 9 and m > 50) or (h == 10 and m <= 40):
current = 'Maths.'
elif h == 10 and m > 40:
current = 'recess.'
elif h == 11 or (h == 12 and m <= 40):
current = 'English.'
elif (h == 12 and m > 40) or (h == 13 and m <= 20):
current = 'lunch.'
elif (h == 13 and m > 20) or h == 14:
current = 'ICT.'
else:
current = home
elif weekday1 == 2:
day = 'Wednesday'
time = '''Period 1/2 = Science Extended
Period 3 = English
Period 4 = Maths
Period 5/6 = Science'''
if h == 8 and m >= 40:
current = 'Homeroom.'
elif h == 9 or (h == 10 and m <= 40):
current = 'Science Extended.'
elif h == 10 and m > 40:
current = 'recess.'
elif h == 11 and m <= 50:
current = 'English.'
elif (h== 11 and m > 50) or (h == 12 and m <= 40):
current = 'Maths.'
elif (h == 12 and m > 40) or (h == 13 and m <= 20):
current = 'lunch.'
elif (h == 13 and m > 20) or h == 14:
current = 'Science.'
else:
current = home
elif weekday1 == 3:
day = 'Thursday'
time = '''Period 1/2 = Art
Period 3 = Science
Period 4 = Wellbeing
Period 5 = English
Period 6 = Maths'''
if h == 8 and m >= 40:
current = 'Homeroom.'
elif (h == 10 and m <= 40) or h == 9:
current = 'Art.'
elif h == 10 and m > 40:
current = 'recess.'
elif h == 11 and m <= 50:
current = 'Science.'
elif (h == 11 and m > 50) or (h == 12 and m <= 40):
current = 'Wellbeing.'
elif (h == 12 and m > 40) or (h == 13 and m < 20):
current = 'lunch.'
elif (h == 13 and m >= 20) or (h == 14 and m <= 10):
current = 'English.'
elif h == 14 and m > 10:
current = 'Maths.'
else:
current = home
elif weekday1 == 4:
day = 'Friday'
time = '''Period 1/2 = PE
Period 3 = English
Period 4 = Maths
Period 5/6 = Music'''
if h == 8 and m >= 40:
current = 'Homeroom.'
elif h == 9 or (h == 10 and m <= 40):
current = 'PE.'
elif h == 10 and m > 40:
current = 'recess.'
elif h == 11 and m <= 50:
current = 'English.'
elif (h == 11 and m > 50) or (h == 12 and m <= 40):
current = 'Maths.'
elif (h == 12 and m > 40) or (h == 13 and m < 20):
current = 'lunch.'
elif (h == 13 and m >= 20) or h == 14:
current = 'Music.'
else:
current = home
else:
day = 'a weekend'
time = 'You have none.'
if day == 'a weekend':
a = "You don't have to be anywhere."
else:
a = ('You should be at ' + current)
a1 = ('Today is ' + day + '.')
a2 = ('''Today your timetable is:
''' + time)
a3 = ('The current time is ' + str(h) + ':' + zero + str(m) + ':' + zero1 + str(s) + '.')
t1 = 'What is the day today?'
t2 = 'What is the current time?'
t3 = 'What is my timetable today?'
t4 = 'Where should I be?'
x1, x2, x3, x4 = '', '', '', ''
def callback1(object):
del x1
x1 = a1
def callback2(object):
x2 = a3
def callback3(object):
x3 = a2
def callback4(object):
x4 = a
b1 = Button(text = t1)
b1.bind(on_press = callback1)
layout = GridLayout(cols = 2)
layout.add_widget(b1)
layout.add_widget(Label(text = x1))
layout.add_widget(Button(text = t2))
layout.add_widget(Label(text = x2))
layout.add_widget(Button(text = t3))
layout.add_widget(Label(text = x3))
layout.add_widget(Button(text = t4))
layout.add_widget(Label(text = x4))
class TimeTable(App):
def build(self):
return layout
if __name__ == '__main__':
TimeTable().run()
Your error is because you try to delete a global variable (x1) in a local context (callback1), without declaring it as global before.
You could do:
global x1
del x1
But there is a more general issue with what you are trying to accomplish, when you say text = x1, it just passes the current value of x1 to the text property of the Label you create, and changing the value of x1 later has no effect on this, what you want is to change widget.text to the new value (and you should rename object to widget in these callbacks, object is the name of the base class in python, so you shouldn't use it as a parameter or anything).
Also, the way you structure your code won't work well in the long term, you should do more things in methods of your class (most of what you do before could be done in build).

Categories