2017-01-13 100 views
0

我想知道爲什麼我通過按鈕調用方法時未定義方法SavePVParmsCloseApplyGraph。我知道,如果我把它們放在__init__裏面,它們就會起作用,我的問題就解決了,但我不明白爲什麼它不能如此。我試圖尋找這個問題,發現這個Python Class: Global/Local variable name not defined和這個Python says global name not defined,但如果我不明白答案,請原諒我。你能幫我理解爲什麼嗎? 背景:這個類是頂級窗口,當我在根窗口中按下按鈕時彈出窗口(這裏我只是直接向大家展示頂層窗口)。它應該在我保存時傳遞所有條目的字典(尚未實現)。 **另外(但不需要回答,如果你不想)在OOP中這是一種適當的編碼風格? (不到1周的時間學習tkinter,並從predural python移到OOP python)。tkinter回調方法未定義全局名稱未定義

import Tkinter as tk 
import ttk 
class PVDialog(tk.Toplevel): 

    def SavePVParms(self): 
     print "saved" 
     self.destroy() 

    def Close(self): 
     self.destroy() 

    def ApplyGraph(self): 
     print 'applied' 

    def __init__(self, parent): 
     tk.Toplevel.__init__(self, parent) 
     print parent 
     self.title('PV Parameters Configuration') 
     self.geometry('800x480') 
     self.resizable(width=False, height=False) 
     self.columnconfigure(0, weight=1) 
     self.columnconfigure(1, weight=8) 
     self.rowconfigure(0, weight=1) 
     self.rowconfigure(1, weight=2) 

    # ====== FRAMES ======= 

     lb1Frame = tk.LabelFrame(self, text='Electric Properties') 
     lb1Frame.grid(row=0, column=0, sticky='ewns', pady=(15, 2), padx=(30,10)) 

     AdvFrame = tk.LabelFrame(self, text='Thermal Properties') 
     AdvFrame.grid(row=1, column=0, sticky='ewns', pady=5, padx=(30,10)) 

     pcurveFrame = tk.LabelFrame(self, text='PV Curves') 
     pcurveFrame.grid(row=0, column=1, sticky='ewns', padx=(0,30), pady=(15,5),rowspan=2) 

     ctrlFrame = tk.Frame(self) 
     ctrlFrame.grid(row=2, column=0, columnspan=2, sticky='ens', padx=20, pady=(2, 20)) 

    # ======== PARAMETER INPUT DATA FRAME ============= # 

     labelName = tk.Label(lb1Frame, text='Name', anchor='w') 
     labelCellType = tk.Label(lb1Frame, text='Cell Type', anchor='w') 
     labelPower = tk.Label(lb1Frame, text='Rated Power [W]', anchor='w') 
     labelOV = tk.Label(lb1Frame, text='Open Voltage [V]', anchor='w') 
     labelSCC = tk.Label(lb1Frame, text='Short-circuit Current [A]', anchor='w') 
     labelMPC = tk.Label(lb1Frame, text='Maximum Point Current [I]', anchor='w') 
     labelMPV = tk.Label(lb1Frame, text="Maximum point Voltage [V]", anchor='w') 
     labelSeries = tk.Label(lb1Frame, text='Cells in series', anchor='w') 
     labelPallel = tk.Label(lb1Frame, text='Cells in parallel', anchor='w') 
     labelNOCT = tk.Label(AdvFrame, text='NOCT', anchor='w') 
     labelThC = tk.Label(AdvFrame, text='Current T factor [%/K]', anchor='w') 
     labelThV = tk.Label(AdvFrame, text='Voltage T factor [%/K]', anchor='w') 
     labelThP = tk.Label(AdvFrame, text='Power T factor [%/K]', anchor='w') 

     labelName.grid(row=0, sticky='ew', padx=10, pady=2) 
     labelCellType.grid(row=1, sticky='ew', padx=10, pady=2) 
     labelPower.grid(row=2, sticky='ew', padx=10, pady=2) 
     labelOV.grid(row=3, sticky='ew', padx=10, pady=2) 
     labelSCC.grid(row=4, sticky='ew', padx=10, pady=2) 
     labelMPC.grid(row=5, sticky='ew', padx=10, pady=2) 
     labelMPV.grid(row=6, sticky='ew', padx=10, pady=2) 
     labelSeries.grid(row=7, sticky='ew', padx=10, pady=2) 
     labelPallel.grid(row=8, sticky='ew', padx=10, pady=2) 
     labelNOCT.grid(row=9 , sticky='ew', padx=10, pady=2) 
     labelThC.grid(row=10, sticky='ew', padx=10, pady=2) 
     labelThV.grid(row=11, sticky='ew', padx=10, pady=2) 
     labelThP.grid(row=12, sticky='ew', padx=10, pady=2) 

     entryName = ttk.Entry(lb1Frame, show='Default') 
     entryCellType = ttk.Combobox(lb1Frame) 
     entryPower = ttk.Entry(lb1Frame) 
     entryOV = ttk.Entry(lb1Frame) 
     entrySCC = ttk.Entry(lb1Frame) 
     entryMPC = ttk.Entry(lb1Frame) 
     entryMPV = ttk.Entry(lb1Frame) 
     entrySeries = ttk.Entry(lb1Frame) 
     entryPallel = ttk.Entry(lb1Frame) 
     entryNOCT = ttk.Entry(AdvFrame, width=23) 
     entryThC = ttk.Entry(AdvFrame, width=23) 
     entryThV = ttk.Entry(AdvFrame, width=23) 
     entryThP = ttk.Entry(AdvFrame, width=23) 

     entryName.grid(row=0, column=1, sticky='ew') 
     entryCellType.grid(row=1, column=1, sticky='ew') 
     entryPower.grid(row=2, column=1, sticky='ew') 
     entryOV.grid(row=3, column=1, sticky='ew') 
     entrySCC.grid(row=4, column=1, sticky='ew') 
     entryMPC.grid(row=5, column=1, sticky='ew') 
     entryMPV.grid(row=6, column=1, sticky='ew') 
     entrySeries.grid(row=7, column=1, sticky='ew') 
     entryPallel.grid(row=8, column=1, sticky='ew') 
     entryNOCT.grid(row=9, column=1, sticky='w', padx=(26,0)) 
     entryThC.grid(row=10, column=1, sticky='w', padx=(26,0)) 
     entryThV.grid(row=11, column=1, sticky='w', padx=(26,0)) 
     entryThP.grid(row=12, column=1, sticky='w', padx=(26,0)) 

    # ==== BUTTON COMANDS ====== 
     saveBttn = ttk.Button(ctrlFrame, text='Save', command=SavePVParms) 
     closBttn = ttk.Button(ctrlFrame, text='Cancel', command=Close) 
     applyBttn = ttk.Button(ctrlFrame, text='Apply', command=ApplyGraph) 
     saveBttn.grid() 
     closBttn.grid(row=0, column=1, padx=10) 
     applyBttn.grid(row=0, column=2, padx=(0, 10)) 

# ======== RUNNIG THE CLIENT ============ 
root = tk.Tk() 
dialog = PVDialog(root) 
root.mainloop() 

更新:由於我是在對提交這個問題,我記得__init__是讀取和類執行的第一件事情,所以這就是爲什麼如果我把它們放在__init__的定義。我仍然不明白爲什麼python不能打電話給他們,如果他們不在外__init__不是python讀全班的?那麼我怎樣才能撥打self.method__init__呢?謝謝!

+0

此代碼是否準確反映您的實際代碼?縮進看起來不正確。 –

+0

用正確的壓痕固定! –

回答

0

SavePVParmsCloseApplyGraph方法是屬於你的類,所以你需要使用self.告訴,你要使用的方法在類的解釋。

saveBttn = ttk.Button(..., command=self.SavePVParms) 

對於編碼standarts,你應該檢查PEP 8但只要你和你的風格相一致,它不應該管那麼多了。

+0

將這些方法作爲類方法還是作爲實例方法會有什麼優勢或不同?目前我把它們作爲__init__實例方法,只是因爲;因爲我不知道。 @Lafexlos –

+0

我認爲你應該閱讀[這個問題和它的答案](http://stackoverflow.com/questions/17134653/difference-between-class-and-instance-methods)。它解釋得比我的好得多。 – Lafexlos