2014-03-02 59 views
0

我試圖在python中爲我的小項目使用Tkinter庫。我創造了一個500平方的廣場,裏面有10000個小廣場。項目配置方法在Tkinter中不起作用

我想讓每個小方塊在用戶點擊時變黑。有人可以告訴我爲什麼,我真的很感激它。下面是圖形代碼:

from Tkinter import * 
from button import * 

class AppFrame(Frame): 




def __init__(self): 

    self.root = Tk() 
    self.root.geometry = ("1000x1000") 
    self.f = Frame(self.root, relief = 'sunken', width = 600, height = 600) 
    self.w = Canvas(self.f,width = 505, height =505) 

    ##get the x, y value whenever the user make a mouse click 
    self.w.bind("<Button-1>", self.xy) 
    self.bolist = [] 

    for k in range(1,101): 
     for i in range(1, 101): 

      button = Buttons(self.w, i * 5, k * 5, i * 5 + 5, k * 5 + 5) 
      self.bolist.append(button) 

    self.f.grid(column =0, columnspan = 4) 
    self.w.grid(column = 0) 

    self.root.mainloop() 


def xy (self, event): 
    self.x, self.y = event.x, event.y 
    print (self.x, self.y) 
    ##check each button if it's clicked 
    for hb in self.bolist: 
     if hb.clicked(self.x, self.y): 
      print ("hurry") 
      hb.activate() 

而且

##button.py 
from Tkinter import * 


class Buttons: 

def __init__(self,canvas,bx,by,tx,ty): 

    self.canvas = canvas 
    self.rec = canvas.create_rectangle((bx,by,tx,ty),fill = "lightgray", 
             activefill= 'black', outline = 'lightgray') 


    self.xmin = bx 
    self.xmax = tx 
    self.ymin = by 
    self.ymax = ty 
    ##print (bx, by, tx, ty) 
def clicked(self, px, py): 
    return (self.active and self.xmin <= px <= self.xmax and 
      self.ymin <= py <= self.ymax) 
def activate(self): 
    self.canvas.itemconfigure(slef.rec, fill = 'black') 
    self.active = True 
+0

你什麼錯誤? – Harvey

+0

您的代碼縮進是錯誤的。 –

回答

1

的問題是,你不初始化active屬性,所以它不存在,直到細胞變得活躍。要解決該問題,請在Buttons__init__方法內添加self.active = False

你也有一個錯字在這一行(請注意您使用slef而非self):

self.canvas.itemconfigure(slef.rec, fill = 'black') 

而不是在畫布上一個全球性的結合,這將是更有效地設定每個單獨的綁定長方形。然後,您可以使用綁定將Buttons類的實例傳遞給回調函數。通過這種方式,您不必遍歷數千個尋找被點擊的小部件。

爲此,請使用畫布的tag_bind方法。你可以這樣做,以便你的主程序傳入一個函數的引用,當矩形被點擊時調用,然後綁定可以調用該方法並將它傳遞給它自己。

例如:

class Buttons: 

    def __init__(self,canvas,bx,by,tx,ty, callback): 
     ... 
     self.rec = canvas.create_rectangle(...) 
     self.canvas.tag_bind(self.rec, "<1>", 
      lambda event: callback(self)) 
     ... 


class AppFrame(Frame): 
    def __init__(...): 
     ... 
      button = Buttons(..., self.callback) 
     ... 

    def callback(self, b): 
     b.activate() 
+0

非常感謝!我完全忘了我可以在Button類中綁定事件!它現在有效! – IsThatYou

0

在這裏,我看着你的代碼,調試它,並且做了一些調整。它現在有效。 只要保持這兩個腳本一個文件夾中,然後運行您的AppFrame腳本(第二個在這個答案)

##button.py 
from Tkinter import * 

class Buttons: 

    def __init__(self,canvas,bx,by,tx,ty): 

     self.canvas = canvas 
     self.rec = canvas.create_rectangle((bx,by,tx,ty),fill = "lightgray", activefill= 'black', outline = 'lightgray') 


     self.xmin = bx 
     self.xmax = tx 
     self.ymin = by 
     self.ymax = ty 
     ##print (bx, by, tx, ty) 
    def clicked(self, px, py): 
     return (self.xmin <= px <= self.xmax and 
       self.ymin <= py <= self.ymax) 
    def activate(self): 
     self.canvas.itemconfigure(self.rec, fill = 'black') 

from Tkinter import * 
from button import * 

class AppFrame(Frame): 

    def __init__(self): 

     self.root = Tk() 
     self.root.geometry = ("1000x1000") 
     self.f = Frame(self.root, relief = 'sunken', width = 600, height = 600) 
     self.w = Canvas(self.f,width = 505, height =505) 

     ##get the x, y value whenever the user make a mouse click 
     self.w.bind("<Button-1>", self.xy) 
     self.bolist = [] 

     for k in range(1,101): 
      for i in range(1, 101): 

       button = Buttons(self.w, i * 5, k * 5, i * 5 + 5, k * 5 + 5) 
       self.bolist.append(button) 

     self.f.grid(column =0, columnspan = 4) 
     self.w.grid(column = 0) 

     self.root.mainloop() 


    def xy (self, event): 
     self.x, self.y = event.x, event.y 
     print (self.x, self.y) 
     ##check each button if it's clicked 
     for hb in self.bolist: 
      if hb.clicked(self.x, self.y): 
       print ("hurry") 
       hb.activate() 

newApp = AppFrame() 
+1

如果你描述了你所做的工作,你的答案會更有用。嘗試將您的解決方案與原始的逐行比較非常困難,尋找您做得有什麼不同。請記住,作爲答案編寫者的目標是教授,而不僅僅是爲某人提供盲目剪切和粘貼的代碼。 –

+0

對不起。你是對的。我有點新鮮。 我所做的是我添加了'newApp = AppFrame()'到上面的第二個文件。這是因爲你實際上必須讓一個類的實例來使用它。 其次,我刪除了'self.active和'部分和'self.active = True'部分,因爲它不是按鈕的屬性。 這足以讓它工作。 @Bryan Oakley,我希望能夠解釋得很清楚。 – sshashank124

+0

謝謝你的耐心!我忘了寫self.active部分。這很有幫助! – IsThatYou