1

This has stumped me for over a week. As the title asks, how can I get TK button commands to take in a parameter with a variable?

Here is the exact code I'm using:

i=0

# Make a Staff list button
staffButton = Button(masterFrame,
                        text='Staff List',
                        width=20,
                        justify=LEFT,
                        #command=lambda:self.openTabHere(isLeft,STAFF_LIST_TAB))
                        command=lambda:self.openTabHere(isLeft,i))
staffButton.grid(column=0, row=1)

# Make a course list button
courseButton = Button(masterFrame,
                        text='Course List',
                        width=20,
                        justify=LEFT,
                        #command=lambda:self.openTabHere(isLeft,COURSE_LIST_TAB))
                        command=lambda:self.openTabHere(isLeft,i))
courseButton.grid(column=0, row=0)

i=1

Note that if I use the commented (hardcoded) command, it works as intended. However, if I use the code not commented, with the variable i, both buttons end up with the command for i=1.

Is it that the command gets the variable i at runtime? If so, or for some other reason, what can I do to accomplish what I'm trying to do?

This is because I do something similar for every staff member; a for loop intending to have buttons that open up a tab with a staff ID that is in the parameter as a variable that can't be hardcoded.

Thanks ahead of time.

3
  • I just tried it and found this isn't the solution. I get an invalid syntax when I try to run that. Commented Oct 29, 2012 at 0:59
  • Yes, I just noticed it was python instead of tcl, and deleted my stupid comment. Note, if you post a self-contained program instead of just the above extract others might be able to try it out and find the problem Commented Oct 29, 2012 at 1:01
  • Thanks for the tip; the main issue was that I didn't want to make a self-contained program that didn't fully represent my problem. I was worried I'd leave out some detail that doesn't convey the underlying problem :S Commented Nov 1, 2012 at 13:45

1 Answer 1

1

You need to bind the value of i at the time you create the widget:

staffButton = Button(..., command=lambda btn=i:self.openTabHere(isLeft,btn))

You probably need to do the same thing for isLeft, unless that's a static value.

Sign up to request clarification or add additional context in comments.

2 Comments

IT WORKS!!!!!! My week of hell is over (sort of). staffButton = Button(..., command=lambda i=i : self.openTabHere(isLeft,i)) This does the trick. Followup Question: As you said, I'll need to do this with isLeft, but what would be the appropriate syntax?
@narutoreplicate: The syntax would look something like lambda A=isLeft, B=i: self.openTabHere(A,B) Notice the pattern? Think of a lambda as a function without a name. The part after lambda and before the :is a list of arguments and their default values, as if you had done def some_func(A="abc", B="123").

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.