I have been writing an annual data verification program and need a bit of user input with it and decided to go the tkinter route. I have created the interface for one of the user input screen, and will have to make others, but I'm having some issues with the destruction of the windows after a selection is made, and the globalization of the variable.
So ideally the program is run, the window pops up, an appropriate attribute selection is made, the text on that button is passed to the "assign" function, which creates a global variable to be used in my program, and the window disappears.
As it stands now, the running of this code results in an error: "TclError: can't invoke "button" command: application has been destroyed".
If I comment out the "mGui.destroy()" line, I can select a button and close the window manually, but the "DRN" variable is passed to variable "x" no matter what!
import sys
from Tkinter import *
def assign(value):
global x
x = value
mGui.destroy()
mGui = Tk()
mGui.geometry("500x100+500+300")
mGui.title("Attribute Selection Window")
mLabel = Label(mGui, text = "Please select one of the following attributes to assign to the selected Convwks feature:").pack()
mButton = Button(mGui, text = "CON", command = assign("CON")).pack()
mButton = Button(mGui, text = "MS", command = assign("MS")).pack()
mButton = Button(mGui, text = "DRN", command = assign("DRN")).pack()
mGui.mainloop() #FOR WINDOWS ONLY
Bonus problem: Putting all of the buttons on the same row with spaces in between them, while keeping them centered.
The problem with your code is that you can't call functions when adding button commands. You can't write Button(command=function())
, you have to write Button(command=function)
. If you want to pass an argument into a function, you'll have to do it like this:
Instead of:
mButton = Button(mGui, text = "CON", command = assign("CON")).pack()
mButton = Button(mGui, text = "MS", command = assign("MS")).pack()
mButton = Button(mGui, text = "DRN", command = assign("DRN")).pack()
You have to write:
mButton = Button(mGui, text = "CON", command = lambda: assign("CON")).pack()
mButton = Button(mGui, text = "MS", command = lambda: assign("MS")).pack()
mButton = Button(mGui, text = "DRN", command = lambda: assign("DRN")).pack()
If you want to put all the buttons on the same row, you could use this code:
import sys
from Tkinter import *
def assign(value):
global x
x = value
mGui.destroy()
mGui = Tk()
mGui.geometry("500x100+500+300")
mGui.title("Attribute Selection Window")
frame1 = Frame(mGui)
frame1.pack()
mLabel = Label(frame1, text = "Please select one of the following attributes to assign to the selected Convwks feature:").grid(row=0, column=0)
frame2 = Frame(mGui)
frame2.pack()
mButton = Button(frame2, text = "CON", command = lambda: assign("CON")).grid(row=0, column=0, padx=10)
mButton = Button(frame2, text = "MS", command = lambda: assign("MS")).grid(row=0, column=1, padx=10)
mButton = Button(frame2, text = "DRN", command = lambda: assign("DRN")).grid(row=0, column=2, padx=10)
mGui.mainloop() #FOR WINDOWS ONLY