Python Tkinter GUI只能工作一次

时间:2014-02-04 11:07:44

标签: python user-interface tkinter

Hello所有Python人员,我对Tkinter相对较新,我目前正在开发一个GUI,允许用户从给定列表中选择元素,然后按任何给定顺序放置它们并添加任何可选的前缀/后缀。该程序第一次调用时工作正常,但是当我第二次调用它时,它将无法正确更新。

我的代码如下所示为创建的类(我在底部放置了一个可执行部件,以便让您了解我的问题,列表0是任何给定的列表,列表1是我们从第一个获得的呼叫和列表第二应该是从第二次呼叫获得的,如果没有显示此问题):

import Tkinter as TK
class SelecParamOrdered(TK.Frame):
    def __init__(self,master, listInit=[], listFinal=[], TITLE="Parameter selection", TEXTE="Here, specific instructions", number = 5):
        TK.Frame.__init__(self,master)
        self.master = master
        self.TEXTE = TEXTE
        self.TITLE = TITLE
        listInit.sort()
        listFinal.sort()
    #
        listTemp=[]
        for elt in listInit:
            if elt.replace(' ','')=='':
                pass
            elif not elt in listTemp:
                listTemp.append(elt)
        listInit=listTemp
    #
        listTemp=[]
        for elt in listFinal:
            if (not elt in listTemp) and (elt in listInit):
                listTemp.append(elt)
        listFinal=listTemp
    #
        listTemp=[]
        for elt in listInit:
            if not elt in listFinal:
                listTemp.append(elt)
        listInit=listTemp
        self.listInit=listInit
        self.listFinal=listFinal
        self.indexI=0
        self.indexF=0
        self.number = number
        self.initUI()

    def initUI(self):
        self.master.title(self.TITLE)
        self.grid()        
        self.columnconfigure(0, pad=3)
        self.columnconfigure(1, pad=3)
        self.columnconfigure(2, pad=3)
        self.columnconfigure(3, pad=3)
        self.columnconfigure(4, pad=3)
        self.columnconfigure(5, pad=3)
        self.columnconfigure(6, pad=3)       
        self.rowconfigure(0, pad=3)
        self.rowconfigure(1, pad=3)
        self.rowconfigure(2, pad=3)
        self.rowconfigure(3, pad=3)
        self.rowconfigure(4, pad=3)
        self.rowconfigure(5, pad=3)
        self.rowconfigure(6, pad=3)
    # Labels texte
        text_param = TK.Label(self,text='Parametre')
        text_param.grid(column=0, row=8, sticky='W')
        text_order = TK.Label(self,text='Ordre')
        text_order.grid(column=1, row=8, columnspan = 3)
        text_prefix = TK.Label(self,text='Prefixe')
        text_prefix.grid(column=5,row=8)
        text_suffix = TK.Label(self,text='Suffixe')
        text_suffix.grid(column=6, row=8)
        txt = TK.Label(self, text=self.TEXTE)
        txt.grid(row=0, column=0, columnspan=7, sticky=TK.W+TK.E)
        t1= TK.Label(self, text="Liste initiale")
        t1.grid(row=1, column=1, columnspan=2, sticky=TK.W+TK.E)
        t2 = TK.Label(self, text="Liste finale")
        t2.grid(row=1, column=4, columnspan=2, sticky=TK.W+TK.E)
    #
        self.listboxInit=TK.Listbox(self, selectmode=TK.EXTENDED)
        self.listboxInit.grid(row=2, column=1, columnspan=2, rowspan=4, sticky=TK.N+TK.W+TK.E+TK.S)
        self.listboxInit.bind('<Double-1>', self.listInit_event)
        self.sbInit = TK.Scrollbar(self)
        self.sbInit.config(command=self.listboxInit.yview)
        self.listboxInit.config(yscrollcommand=self.sbInit.set)
        self.sbInit.grid(row=2, column=0, rowspan=4, sticky=TK.N+TK.S)
    #
        self.listboxFinal = TK.Listbox(self, selectmode=TK.EXTENDED)
        self.listboxFinal.grid(row=2, column=4, columnspan=2, rowspan=4, sticky=TK.N+TK.W+TK.E+TK.S)
        self.listboxFinal.bind('<Double-1>', self.listFinal_event)
        self.sbFinal = TK.Scrollbar(self)
        self.sbFinal.config(command=self.listboxFinal.yview)
        self.listboxFinal.config(yscrollcommand=self.sbFinal.set)
        self.sbFinal.grid(row=2, column=6, rowspan=4, sticky=TK.N+TK.S)
        self.fillListboxes()
        add = TK.Button(self, text="==>", command=self.addParam)
        add.grid(row=2, column=3, sticky=TK.W+TK.E)
        rem = TK.Button(self, text="<==", command=self.removeParam)
        rem.grid(row=4, column=3, sticky=TK.W+TK.E)
        addT = TK.Button(self, text=">>>", command=self.addAllParam)
        addT.grid(row=3, column=3, sticky=TK.W+TK.E)
        remT = TK.Button(self, text="<<<", command=self.removeAllParam)
        remT.grid(row=5, column=3, sticky=TK.W+TK.E)
        send = TK.Button(self, text="OK", command=self.sendList)
        send.grid(row=6, column=0, columnspan=7, sticky=TK.W+TK.E)
        sendall = TK.Button(self,text='OK',command=self.sendAll)
        sendall.grid(column=0, row=self.number+9, columnspan=7, sticky='WE')
    # Une boucle par label/parametre
        liste_options = range(1,self.number+1)        
        for i in range(self.number):
        # Label Ordre
            exec('self.text_var_'+str(i+1)+' = TK.StringVar()')
            exec('self.text_param_'+str(i+1)+' = TK.Label(self,text=\'\', textvariable=self.text_var_'+str(i+1)+')')
            exec('self.text_param_'+str(i+1)+'.grid(column=0, row='+str(i+9)+')')

        # Liste deroulante
            exec('self.v_'+str(i+1)+' = TK.IntVar()')
            exec('self.v_'+str(i+1)+'.set(None)')
            exec('om_'+str(i+1)+' = TK.OptionMenu(self,self.v_'+str(i+1)+',*liste_options)')
            exec('om_'+str(i+1)+'.grid(column=1,row='+str(i+9)+',sticky=\'WE\')')

        # Entree prefixe
            exec('self.p_'+str(i+1)+' = TK.StringVar()')
            exec('self.entry_prefix_'+str(i+1)+' = TK.Entry(self,textvariable=self.p_'+str(i+1)+',width=10)')
            exec('self.entry_prefix_'+str(i+1)+'.grid(column=5,row='+str(i+9)+')')

        # Entree suffixe
            exec('self.s_'+str(i+1)+' = TK.StringVar()')
            exec('self.entry_suffix_'+str(i+1)+' = TK.Entry(self,textvariable=self.s_'+str(i+1)+',width=10)')
            exec('self.entry_suffix_'+str(i+1)+'.grid(column=6,row='+str(i+9)+')')

    def fillInit(self,list):
        list2=[]
        for elt in list:
            if (not elt in list2) and (not elt in self.listFinal):
                list2.append(elt)
        list2.sort()
        self.listInit=list2
        self.fillListboxes()
    def fillFinal(self,list):
        for elt in list:
            if not elt in self.listFinal:
                self.listFinal.append(elt)
                if elt in self.listInit:
                    self.listInit.remove(elt)
        self.listFinal.sort()
        self.fillListboxes()

    def fillListboxes(self):
        self.listboxInit.delete(0,TK.END)
        for p in self.listInit:
            self.listboxInit.insert(TK.END,p)
        self.listboxFinal.delete(0,TK.END)
        for p in self.listFinal:
            self.listboxFinal.insert(TK.END,p)
        self.listboxInit.see(self.indexI)
        self.listboxFinal.see(self.indexF)

    def addParam(self):
        index = self.listboxInit.curselection()
        for i in index:
            self.listInit.remove(self.listboxInit.get(i))
            if not self.listboxInit.get(i) in self.listFinal:
                self.listFinal.append(self.listboxInit.get(i))
        if len(index)>0:
        if index[0]>0:
            self.indexI=int(index[0])-1
    else:
        self.indexI=0
        self.listFinal.sort()
        self.fillListboxes()

    def removeParam(self):
        index = self.listboxFinal.curselection()
        for i in index:
            self.listFinal.remove(self.listboxFinal.get(i))
        if not self.listboxFinal.get(i) in self.listInit:
                self.listInit.append(self.listboxFinal.get(i))
    if len(index)>0:
        if index[0]>0:
            self.indexF=int(index[0])-1
    else:
        self.indexF=0
        self.listInit.sort()
        self.fillListboxes()

    def addAllParam(self):
        for elt in self.listInit:
        if not elt in self.listFinal:
                self.listFinal.append(elt)
        self.listFinal.sort()
        self.listInit=[]
    self.indexI=0
        self.fillListboxes()

    def removeAllParam(self):
        for elt in self.listFinal:
        if not elt in self.listInit:
                self.listInit.append(elt)
        self.listInit.sort()
        self.listFinal=[]
    self.indexF=0
        self.fillListboxes()

    def listInit_event(self, event):
        self.addParam()

    def listFinal_event(self, event):
        self.removeParam()

    def sendList(self):
        for i in range(len(self.listFinal)):
            exec('self.text_var_'+str(i+1)+'.set(self.listFinal[i])')
        self.master.update_idletasks()

    def sendAll(self):
        listOut = []
        pOut = []
        sOut = []
        for i in range(len(self.listFinal)):
            exec('num = self.v_'+str(i+1)+'.get()')
        #print 'Num is: ',num
            for j in range(len(self.listFinal)):
            #print '  Index is: ',j+1
                if num == j+1:
                #print '  Condition OK'
                    exec('listOut.append(self.text_var_'+str(j+1)+'.get())')
                    exec('pOut.append(self.p_'+str(j+1)+'.get())')
                    exec('sOut.append(self.s_'+str(j+1)+'.get())')
        self.quit()
        return listOut, pOut, sOut

我用来调用它的函数以及main函数如下:

def getchosenlist(listInit=[],listFinal=[], TITLE="Parameter selection", TEXTE="Here, specific instructions"):
    root = TK.Tk()
    app = SelecParamOrdered(root,listInit,listFinal,TITLE,TEXTE)
    root.mainloop()
    return app.sendAll()

if __name__ == '__main__':
    liste_param = []
    for i in range(10):
        liste_param.append('Parameter'+str(i+1))
    print ' List 0:\n',liste_param
    list1 = getchosenlist(liste_param)
    print ' List 1st:\n',list1
    list2 = getchosenlist(liste_param)
    print ' List 2nd:\n',list2

谢谢!

1 个答案:

答案 0 :(得分:0)

也许不是唯一的问题,因为正如评论所提到的,您的示例代码对于此站点的约定来说太长了(请参阅例如Code Review SE以获取有关重要代码段的反馈)。

您的代码在python的新手中表现出一个常见错误,即使用空列表作为关键字参数的默认值(至少在getchosenlistSelecParamOrdered.__init__中)。这个空列表在您的方法的每次调用之间共享,因此,随着时间的推移会累积结果。您可以在effbot.org上阅读详细说明。

您可能想要实现的目标可以与模式一起使用:

def foo(arg = None):
    if arg is None:
        arg = []
    (...)