2013-04-18 151 views
2

我試圖打印出按鈕編號,當我點擊由循環創建的每個按鈕。以下是我所嘗試過的。Python Tkinter按鈕回調

import Tkinter as tk 
root=tk.Tk() 

def myfunction(a): 
     print a 

for i in range(10): 
    tk.Button(root,text='button'+str(i),command=lambda:myfunction(i)).place(x=10,y=(10+(25*i))) 
root.mainloop() 

但不是打印出每個按鈕的號碼,它實際上每次給我最後一個按鈕的號碼。有什麼我可以做,所以當我點擊按鈕1,它會打印1,2 2,等等?

回答

2

Blender的答案是一個聰明的解決方案,但如果你被函數抽象拋棄,這裏是另一種可能的方式來做到這一點。它真的只是創建一個映射,保存在buttons,從Button小部件保存到它們的正確數字。

import Tkinter as tk 
root = tk.Tk() 

def myfunction(event): 
    print buttons[event.widget] 

buttons = {} 
for i in range(10): 
    b = tk.Button(root, text='button' + str(i)) 
    buttons[b] = i # save button, index as key-value pair 
    b.bind("<Button-1>", myfunction) 
    b.place(x=10,y=(10+(25*i))) 
root.mainloop() 
0

這是因爲i在你的匿名函數是指計數器變量,而不是價值:

from __future__ import print_function 

x = [lambda: print(i) for i in range(10)] 

for f in x: 
    f() 

由此產生的10角連續9秒的輸出。

要解決這個問題,你必須使用兩個lambda S和與功能陰影i(產生你的第一個功能):

from __future__ import print_function 

x = [(lambda i: (lambda: print(i)))(i) for i in range(10)] 

for f in x: 
    f() 

雖然在這一點上,你會會更好只是讓一個名爲功能:

def my_command(i): 
    def inner_function(): 
     return my_function(i) 

    return inner_function 

,並用它是這樣的:

tk.Button(root, text='button' + str(i), command=my_command(i)) 
7

簡單的解決方法是每次創建lambda函數時用當前值i初始化lambda函數。這可以使用另一個虛擬變量j的Python默認值完成。

command = lambda j=i: myfunction(j) 
0

問題是tk中的Button命令忽略了任何像mycommand(data)這樣的數據被忽略的參數。

我使用的按鈕相當多,並決定繼承一個tk Button來包含數據。我稱它爲一個DataButton並添加了一個數據成員(在這種情況下是一個索引號)。這種方式點擊時,它會傳回其數據。 (索引號)現在我使用DataButton,只要我想要它像索引或甚至消息一樣保存信息。