Python GUI Tk : Event
Capturing destroy events
from Tkinter import * import tkMessageBox def callback(): if tkMessageBox.askokcancel("Quit", "Do you really wish to quit?"): root.destroy() root = Tk() root.protocol("WM_DELETE_WINDOW", callback) root.mainloop()
Binding an event with an event handler
from Tkinter import * class Application(Frame): def __init__(self, master): Frame.__init__(self, master) self.grid() self.bttn_clicks = 0 self.create_widget() def create_widget(self): self.bttn = Button(self) self.bttn["text"]= "Total Clicks: 0" self.bttn["command"] = self.update_count self.bttn.grid() def update_count(self): self.bttn_clicks += 1 self.bttn["text"] = "Total Clicks: " + str(self.bttn_clicks) root = Tk() root.geometry("200x50") app = Application(root) root.mainloop()
Associating arguments to an event-handler function
from Tkinter import * class curry: """from Scott David Daniels'recipe "curry -- associating parameters with a function" in the "Python Cookbook" http://aspn.activestate.com/ASPN/Python/Cookbook/ """ def __init__(self, fun, *args, **kwargs): self.fun = fun self.pending = args[:] self.kwargs = kwargs.copy() def __call__(self, *args, **kwargs): if kwargs and self.kwargs: kw = self.kwargs.copy() kw.update(kwargs) else: kw = kwargs or self.kwargs return self.fun(*(self.pending + args), **kw) def event_lambda(f, *args, **kwds ): """A helper function that wraps lambda in a prettier interface. Thanks to Chad Netzer for the code.""" return lambda event, f=f, args=args, kwds=kwds : f( *args, **kwds ) # ---------- code for function: event_lambda (end) ----------- class MyApp: def __init__(self, parent): self.myParent = parent self.myContainer1 = Frame(parent) self.myContainer1.pack() button_name = "OK" # command binding -- using curry self.button1 = Button(self.myContainer1, command = curry(self.buttonHandler, button_name, 1, "Good stuff!")) # event binding -- using the event_lambda helper function self.button1.bind("<Return>", event_lambda( self.buttonHandler, button_name, 1, "Good stuff!" ) ) self.button1.configure(text=button_name, background="green") self.button1.pack(side=LEFT) self.button1.focus_force() # Put keyboard focus on button1 button_name = "Cancel" # command binding -- using curry self.button2 = Button(self.myContainer1, command = curry(self.buttonHandler, button_name, 2, "Bad stuff!")) # event binding -- using the event_lambda helper function in two steps event_handler = event_lambda( self.buttonHandler, button_name, 2, "Bad stuff!" ) self.button2.bind("<Return>", event_handler ) self.button2.configure(text=button_name, background="red") self.button2.pack(side=LEFT) def buttonHandler(self, argument1, argument2, argument3): print " buttonHandler routine received arguments:", \ argument1.ljust(8), argument2, argument3 def buttonHandler_a(self, event, argument1, argument2, argument3): print "buttonHandler_a received event", event self.buttonHandler(argument1, argument2, argument3) root = Tk() myapp = MyApp(root) root.mainloop()
Sharing Information Between Event-Handler Functions
from Tkinter import * class MyApp: def __init__(self, parent): self.myLastButtonInvoked = None self.myParent = parent self.myContainer1 = Frame(parent) self.myContainer1.pack() self.yellowButton = Button(self.myContainer1, command=self.yellowButtonClick) self.yellowButton.configure(text="YELLOW") self.yellowButton.pack(side=LEFT) self.redButton = Button(self.myContainer1, command=self.redButtonClick) self.redButton.configure(text="RED") self.redButton.pack(side=LEFT) self.whiteButton = Button(self.myContainer1, command=self.whiteButtonClick) self.whiteButton.configure(text="WHITE") self.whiteButton.pack(side=LEFT) def redButtonClick(self): print "RED button clicked. Previous button invoked was", self.myLastButtonInvoked ### 2 self.myLastButtonInvoked = "RED" def yellowButtonClick(self): print "YELLOW button clicked. Previous button invoked was", self.myLastButtonInvoked ### 2 self.myLastButtonInvoked = "YELLOW" def whiteButtonClick(self): print "WHITE button clicked. Previous button invoked was", self.myLastButtonInvoked ### 2 self.myLastButtonInvoked = "WHITE" root = Tk() myapp = MyApp(root) root.mainloop()
What Events Does 'Command' Bind To?
from Tkinter import * class MyApp: def __init__(self, parent): self.myParent = parent self.myContainer1 = Frame(parent) self.myContainer1.pack() self.button1 = Button(self.myContainer1, command=self.button1Click) self.button1.bind("<Return>", self.button1Click_a) self.button1.configure(text="OK") self.button1.pack(side=LEFT) self.button1.focus_force() self.button2 = Button(self.myContainer1, command=self.button2Click) self.button2.bind("<Return>", self.button2Click_a) self.button2.configure(text="Cancel") self.button2.pack(side=RIGHT) def button1Click(self): print "button1Click event handler" if self.button1["background"] == "green": self.button1["background"] = "yellow" else: self.button1["background"] = "green" def button2Click(self): print "button2Click event handler" self.myParent.destroy() def button1Click_a(self, event): print "button 1 Click event" self.button1Click() def button2Click_a(self, event): print "button 2 Click event" self.button2Click() root = Tk() myapp = MyApp(root) root.mainloop()
adds callbacks function to a button
import sys from Tkinter import * widget = Button(None, text='Hello', command=sys.exit) widget.pack() widget.mainloop()
Add system exit action to a button
from Tkinter import * root = Tk() Button(root, text='press', command=root.quit).pack(side=LEFT) root.mainloop()
Update Label in action event
#!/usr/bin/env python from Tkinter import * import math root = Tk() top = Frame(root) top.pack(side='top') hwframe = Frame(top) hwframe.pack(side='top') font = 'times 18 bold' hwtext = Label(hwframe, text='Hello, World!', font=font) hwtext.pack(side='top', pady=20) rframe = Frame(top) rframe.pack(side='top', padx=10, pady=20) r_label = Label(rframe, text='The sine of') r_label.pack(side='left') r_entry = Entry(rframe, width=6) r_entry.pack(side='left') r_entry.insert('end', '1.2') def comp_s(event=None): r = float(r_entry.get()) s = math.sin(r) s_label.configure(text='%g' % s) r_entry.bind('<Return>', comp_s) compute = Button(rframe, text=' equals ', command=comp_s, relief='flat') compute.pack(side='left') s_label = Label(rframe, width=12) s_label.pack(side='left') def quit(event=None): root.destroy() quit_button = Button(top, text='Goodbye, GUI World!', command=quit, background='yellow', foreground='blue') quit_button.pack(side='top', pady=5, fill='x') root.bind('<q>', quit) root.mainloop()
Class wrapper for GUI
from Tkinter import * import math class HelloWorld: def __init__(self, parent): self.master = parent top = Frame(parent) top.pack(side='top') hwframe = Frame(top) hwframe.pack(side='top') font = 'times 18 bold' hwtext = Label(hwframe, text='Hello, World!', font=font) hwtext.pack(side='top', pady=20) rframe = Frame(top) rframe.pack(side='top', padx=10, pady=20) r_label = Label(rframe, text='The sine of') r_label.pack(side='left') self.r = StringVar() self.r.set('1.2') r_entry = Entry(rframe, width=6, textvariable=self.r) r_entry.pack(side='left') r_entry.bind('<Return>', self.comp_s) compute = Button(rframe, text=' equals ', command=self.comp_s, relief='flat') compute.pack(side='left') self.s = StringVar() s_label = Label(rframe, textvariable=self.s, width=12) s_label.pack(side='left') quit_button = Button(top, text='Goodbye, GUI World!', command=self.quit, background='yellow',foreground='blue') quit_button.pack(side='top', pady=5, fill='x') self.master.bind('<q>', self.quit) def quit(self, event=None): self.master.quit() def comp_s(self, event=None): self.s.set('%g' % math.sin(float(self.r.get()))) root = Tk() hello = HelloWorld(root) root.mainloop()
Use lambda to generate a call back function for a button
from Tkinter import * from sys import stdout, exit widget = Button(None, text='Hello event world', command=(lambda: stdout.write('Hello lambda world\n') or exit()) ) widget.pack() widget.mainloop()