As I try to make a mini calculator using a Tkinter class, the interpreter returns the "NameError: name 'evaluate' is not defined" error code. I've also tried to define my function evaluate before the "def init" but it still doesn't work.
from tkinter import *
class App(Tk):
def __init__(self):
Tk.__init__(self)
self.entree = Entry(self)
self.chaine = Label(self)
self.entree.bind("<Return>", evaluate)
self.entree.pack()
self.chaine.pack()
def evaluate(self, event):
self.chaine.configure(text="Result = " + str(eval(self.entree.get())))
app = App()
app.mainloop()
thanks for your help!
evaluate is a method inside your App class. The method is accessible anywhere inside the class using its self member. self is the initial class object itself and you cannot access anything(methods, variables etc..) inside the class without this member. Therefore, you should use:
#<---code---->
self.entree.bind("<Return>", self.evaluate)
#<---code---->
Related
For a couple of days I've been attempting to pass an instance of a variable from one of my classes to another, and until recently I have not been able to get it to work. I've read this document regarding classes and instances, I've searched online and stackoverflow and I couldn't get an answer until I tried a solution from a previous asked question and it solved my problem. However, I'm not exactly sure on the why and the how it works.
My code goes as follows, :
from tkinter import *
def main():
main_window = Tk()
app = First(main_window)
main_window.mainloop()
class First:
def __init__(self, root):
self.root = root
self.root.title('First Window')
self.entry1 = Entry(self.root)
self.entry1.pack()
btn = Button(self.root, text="click", command=self.clicked)
btn.pack()
def clicked(self):
writeDoc(First=self)
class writeDoc:
def __init__(self, First):
self.First = First
txt = self.First.entry1.get()
print(txt)
if __name__ == '__main__'
main()
Under the class writeDoc whenever I hover over the parameter First it is not a reference to the Class First, so I am unsure how it has access to entry1. The same goes for the First within writeDoc(First=self). Addtionally, why does writeDoc(First=self) work but not writeDoc(self.First)?
I assumed when I want to reference to another class and want to pass its instances over I would need to do
class First:
....
def clicked(self):
writeDoc(First)
....
class writeDoc(First):
def __init__(self, First):
super().__init__(First):
...
But, this didn't work for me at all.
I hope this isn't a loaded/jumbled question. I want to understand how this works to create better code and avoid misunderstanding how python classes works.
Inside the clicked() method, self refers to an instance of the First class. It then does
writeDoc(First=self)
which passes that instance to the writeDoc class's __init__() method, as the value of its First parameter. This is no different from passing any other object as a method parameter.
writeDoc(self.First) doesn't work because there's no First attribute in the self instance. First is the name of the class, not an attribute.
I want to change a labeltext from outside of the class through a setter method in the class. Im just getting
AttributeError: type object 'gui' has no attribute 'label'. I tried changing the text through label['text']; label.config(text = 'X')
from tkinter import *
class gui:
def __init__(self):
self.root = Tk()
self.label = Label(self.root, text='Y')
self.label.pack()
self.button = Button(self.root, text='Click', command=self.__btnClick)
self.button.pack()
mainloop()
def __btnClick(self):
changeText()
def setLabelText(self):
self.label['text']= 'X'
def changeText():
gui.setLabelText(gui)
if __name__ == '__main__':
window = gui()
I dont know if it helps but heres my full code
https://pastebin.com/bT43NgpH
Thank you for your help!
You have to call setLabelText on an instance of gui not on the class itself. When you call setLabelText in __btnClick you have to give the instance of gui as a parameter to this function. You've got the instance in the parameter self.
So __btnClick should be altered to:
def __btnClick(self):
changeText(self)
And changeText should be altered to:
def changeText(the_window):
the_window.setLabelText()
I'd like to add a link to the Style Guide for Python Code. Your code is hard to read for an experienced programmer (OK, not that hard, but harder than necessary) because you don't follow the naming conventions.
I am writing a Tkinter application that requires parts of the user display to exist in two different class, both imported from another file. I need to take a piece of user input and pass it from one class to another. In the toy example below, the user is supposed to type something into my_entry_input which later the class PullVariable is supposed to access.
Code is below. I had a few thoughts, such as somehow using globals or creating a function within the original class to get the variables and then pass them back. In all cases, I get:
AttributeError: type object 'Application' has no attribute 'my_entry'
The best solution I can think of is to create a function that responds to the binding, then pass the .get() to the other class from that function. My feeling is that tkinter doesn't like .get() in between classes.
Thanks to the community for your help.
MAIN
from import_test1 import *
root=Tk()
ui = Application(root)
ui.hello_world()
ui.entry()
pv = PullVariable()
if __name__ == '__main__':
root.mainloop()
IMPORTED CODE
from tkinter import *
from tkinter import ttk
class Application(Frame):
def __init__(self, parent, *args, **kwargs):
print('Application init')
Frame.__init__(self, parent, *args, **kwargs)
self.parent=parent
self.parent.grid()
def entry(self):
self.my_entry = StringVar(self.parent)
my_entry_input = Entry(self.parent, textvariable=self.my_entry,
width=16)
my_entry_input.bind('<FocusOut>', self.show_entry)
my_entry_input.grid(column=0, row=1)
self.show_label = Label(self.parent, text = '')
self.show_label.grid(column=0, row=2)
def hello_world(self):
print('hello world')
self.hw = Label(self.parent, text='Hello World!')
self.hw.grid(column=0, row=0)
def show_entry(self, event):
PullVariable(Application).find_entry()
class PullVariable:
def __init__(self, app):
self.app = app
print('Pull initiated')
def find_entry(self, event=None):
self.pulled_entry = self.app.my_entry.get()
self.app.show_label['text'] = self.pulled_entry
my_entry is not a attribute of Application class, so you can't do Application.my_entry, by it is an attribute of instance of Application class, so you can do Application().my_entry. You can probably add either instance of Application or my_entry to the __init__ method of PullVariable. I'll use the former.
# ...
class PullVariable:
def __init__(self, app): # add app here
self.pulled_entry = app.my_entry.get() # use app here
print(self.pulled_entry)
# and then
root=Tk()
ui = Application(root)
ui.hello_world()
ui.entry()
pv = PullVariable(ui) # supply PullVariable with instance of Application
I'm sorry for my bad English.
I get an error when I try to get() the Entry named entry from outside the class.
Error:
AttributeError: 'function' object has no attribute 'entry' ""
Example Code:
class asd:
def gui(self, guiwindow, labelplacex, labelplacey, textx, texty, entryx, entryy):
self.root = tk
self.image = tk.PhotoImage(file=aimage_path)
self.label = tk.Label(image=self.image)
self.label.pack()
self.label.place(x=labelplacex , y=labelplacey)
self.text = Label(guiawindow, text="Code:")
self.text.pack()
self.text.place(x = textx,y = texty)
self.entry = Entry(guiwindow)
self.entry.pack()
self.entry.place(x = entryx,y = entryy)
self.button = Button(Tk(), text="Back Menu", command=self.asdfg)
self.button.pack()
self.root.mainloop()
asd.gui.entry.get()
How to do this??
You have two problems. First, you need to create an instance of asd, and second, you need to call the gui method.
For example, something like this:
asd_instance = asd()
asd_instance.gui(...)
asd_instance.entry.get()
Not: ... represents all the parameters that you need to pass to gui, which are irrelevant to the problem. The point being, you must first create an instance of the class before you can get an attribute of the instance. In this case the attribute you want won't exist until you call the gui method. Thus, you must first create an instance, then call the gui method, and only then can you access the attribute.
Try asd.entry.get() instead.
Assuming self.entry has already been defined, you should be able to access it by calling the class itself and then the variable, since the word 'self' means the class itself.
gui in this case is just a function and self.entry belongs to the class asd, not the function gui.
I am still pretty new to Python, so I'm sorry if my question is trivial or even stupid. I am trying to build a little module that reacts on a callback of a Button (which isn't in the code). The callback is simulated in the main()-function. Now my problem is that I can't figure out how to get rid of the global name error. It says that drink0_ingred is not defined as global name. I need this as text for the label called self.l0. This is what I have so far:
import tkinter
from tkinter import ttk
def main():
root = tkinter.Tk()
callback = callbackkb0()
drink0 = Drink0(root)
root.mainloop()
def callbackkb0():
with open(file="drink0_ingred.txt") as ingred0:
drink0_ingred = ingred0.read()
print(drink0_ingred)
return drink0_ingred
class Drink0(ttk.Frame):
def __init__(self, root):
ttk.Frame.__init__(self, root)
self.grid()
self.widgets_create()
def widgets_create(self):
self.l0 = ttk.Label(self, text=drink0_ingred)
self.l0.grid()
main()
How do I define drink0_ingred as global name and make it accessable for other functions?
Thanks for helping me!
Two things you can do:
Globalise drink0_ingred:
with open(file="drink0_ingred.txt") as ingred0:
global drink0_ingred
drink0_ingred = ingred0.read()
Call the function instead of calling the variable:
self.l0 = ttk.Label(self, text=callbackkb0()) # Notice how I called the function
# because it returned drink0_ingred