簡體   English   中英

Python 3:Tkinter框架和意外行為

[英]Python 3: Tkinter frames and unexpected behaviour

我目前正在嘗試在tkinter中創建一個具有多個屏幕的程序,但是我遇到了一個奇怪的問題:當我嘗試將特定屏幕提升到前面時,它沒有出現。 我用來創建不同屏幕的代碼是這樣的:

class PokemonDecklistCreatorApp(tk.Tk):

    def __init__(self, *args, **kwargs):
        tk.Tk.__init__(self, *args, **kwargs)
        container = tk.Frame(self)
        container.pack(side='top', fill='both', expand=True)
        container.grid_rowconfigure(0, weight=1)
        container.grid_columnconfigure(0, weight=1)

        self.frames = {}

        for F in (MainMenu, DecksMenu, DeckEditor, CardViewerDeckEditor,DeckNotes,SearchMenu, StandardSearch, AdvancedSearch, RandomSearch, SearchResults,CardViewerSearchResults, ExtrasMenu, CardExplanationGuide, AboutProgram):
            try:
                frame = F(parent=container, controller=self)
                pageName = F.__name__
                self.frames[pageName] = frame
                frame.grid(row=0, column=0, sticky='nsew')
            except Exception as e:
                print(e)
        self.show_frame('MainMenu')

    def show_frame(self, page):
        frame = self.frames[page]
        frame.tkraise()

然后,用戶可以使用“搜索屏幕”指定要搜索的條件,然后調用doSearch函數,該函數應該破壞舊的SearchResults屏幕(通過從self.frames dict和垃圾回收中彈出)。

class RandomSearch(tk.Frame):

    def __init__(self, parent, controller):
        tk.Frame.__init__(self, parent)
        self.controller = controller
        self.parent = parent
        [some widgety code here]
        self.btnSearch = tk.Button(self, text='Gotta Search \'em All!', command=self.doSearch, font=('Lucida Grande',24))
        self.btnSearch.place(x=450, y=670, width=500, height=40)

    def doSearch(self,* args,** kwargs):
        self.controller.frames.pop('SearchResults')
        frame=SearchResults(parent=self.parent,controller=self.controller,searchTerms=[])
        pageName = SearchResults.__name__
        self.controller.frames[pageName]=frame
        self.controller.show_frame('SearchResults')


class SearchResults(tk.Frame):

    def __init__(self, parent, controller,searchTerms=None):
        tk.Frame.__init__(self, parent)
        self.controller = controller
        [more widgety stuff]

但是,問題在於,當我嘗試運行doSearch函數時,它將創建新對象,但不顯示它。 它保留在同一屏幕上,我仍然可以像往常一樣與它進行交互,就好像它根本沒有改變屏幕一樣!

我已經通過將print(id(self.frames['SearchResults']))放在show_frame函數中來檢查是否創建了新對象,每次按下按鈕時,它都會顯示一個不同的ID。

我也知道問題不在於self.controller.show_frame('SearchResults')行,因為我嘗試了self.controller.show_frame('MainMenu')並且按預期工作。

我做錯了什么?

考慮以下代碼:

def doSearch(self,* args,** kwargs):
    ...
    frame=SearchResults...)
    pageName = SearchResults.__name__
    self.controller.frames[pageName]=frame
    self.controller.show_frame('SearchResults')

永遠不要通過調用grid將框架添加到控制器中。 您可能需要添加以下語句:

    frame.grid(row=0, column=0, sticky='nsew')

我看不出有任何理由需要從列表中刪除一個框架(而不破壞它!)並放置一個新的框架。 您創建了內存泄漏。 Intead,您只需在SearchResults中添加一個方法即可在現有SearchResults頁面內重新創建或重置小部件。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM