[Tutor] command in menu and button
John Fouhy
john at fouhy.net
Tue Nov 22 23:00:27 CET 2005
Apologies to Double Six for getting this twice; I forgot to cc: tutor..
On 23/11/05, Double Six <doublesix at ureach.com> wrote:
> menu.add_command(label="Open Viewer", command=os.system("Open my
> viewer &"))
Hi Joe,
This is a fairly common gotcha.
Think about what happens when python executes a function call:
Firstly, it evaluates each of the arguments to the function. Then, it
calls the function.
So, with your line above, here's what python does:
1. Evaluate "Open Viewer". This is easy; it just produces a string.
2. Evaluate os.system("Open my viewer &"). Since this is a function
call, in order to evaluate it, python calls the function to get its
return value.
3. Call menu.add_command with the arguments it has just evaluated.
Do you see what is happening now? What python wants is a _callable_
--- this is like a function that hasn't been called yet.
Functions are first-class objects in python. That means you can do
things like this:
>>> def hello():
... print 'hello world!'
...
>>> hello()
hello world!
>>> f = hello # assign to f the function hello.
>>> f() # f is now a function, so we can call it.
hello world!
Or, I could make a quit button like this:
b = Button(self, text='Quit program', command=self.quit)
# assuming 'self' is a Frame or Tk or something.
Note the lack of () after self.quit: We're passing a reference to the
method itself.
So, to your specific problem:
menu.add_command(label="Open Viewer", command=os.system("Open my viewer &"))
It's a bit more difficult, because you want to pass an argument to
os.system. And when Tkinter calls a menu callback, it doesn't give it
any arguments.
But, that's OK. You can just define a new function:
def callback():
os.system("Open my viewer &")
menu.add_command(label="Open Viewer", command=callback)
Does this help?
--
John.
More information about the Tutor
mailing list