【问题标题】:Can't Show Tkinter Root Window Again After Using withdraw()使用撤消()后无法再次显示 Tkinter 根窗口
【发布时间】:2019-04-19 14:42:39
【问题描述】:

在我的程序中,我从我的根 tkinter 窗口创建一个窗口,并使用 .withdraw() 函数隐藏根。当我尝试通过调用根类再次显示根窗口时,它没有显示并且我的程序退出。这是我描述问题的代码的粗略轮廓:

 class MainGUI:
    def __init__(self, master):
        self.master = master
        #....Create and .grid() all GUI Widgets....

        # Button for switching to other window
        button = Button(text="CLICKME", command=lambda: self.other_window())

        # Call and define show function at the end of __init__
        self.show()
        def show(self):
            self.master.update()
            self.master.deiconify()

        # Create other window and withdraw self on button click
        def other_window(self):
            OtherGUI(self.master)
            self.master.withdraw()


class OtherGUI:
    def __init__(self, master):
        # Function for returning to main window, calls MainGUI class
        # to create window and withdraws self.
        def main_window():
            MainGUI(self.master)
            self.master.withdraw()

        master = self.master = Toplevel(master)
        #....Create and .grid() all GUI Widgets....

        # Button for switching back to main window
        button = Button(text="CLICKME", command=lambda: self.main_window())

使用 MainGUI 中的打印功能,我可以看到在尝试切换回主窗口时,实际上调用了 show(),并且似乎进入了整个类。

这让我很困惑,因为我只是从其他论坛帖子中真​​正学会了如何做到这一点,并且使用 root.update() 和 .deiconify() 似乎是大多数人的解决方案,但我不知道为什么会这样不工作。

有人知道我在哪里出错了吗?

【问题讨论】:

  • 我不确定您是否将 MainGui 方法缩进错误,或者您是否真的忘记将它们放在 __init__ 之外。但是在OtherGui 中,main_window 必须在 init 之外并且有 self 参数
  • 我认为构建一个分别从tktoplevel继承的类会更容易。我也确实在这里看到了缩进问题。通常在大多数 tkinter 应用程序中都不需要使用 update()

标签: python user-interface tkinter window show


【解决方案1】:

由于多种原因,您提供的示例无法正常工作。

#really you should build your gui as an inherited class as it makes things much easier to manage in tkinter.
class MainGUI:
    def __init__(self, master):
        self.master = master


        button = Button(text="CLICKME", command=lambda: self.other_window())
        # no need for lambda expressions here.
        # missing geometry layout... grid(), pack() or place()

        self.show()
        # self.show does nothing here because your show method is improperly indented.
        # your other_window method is also not properly indented.

        def show(self):
            self.master.update()
            self.master.deiconify()

        def other_window(self):
            OtherGUI(self.master)
            self.master.withdraw()


class OtherGUI:
    def __init__(self, master):
        # this function should be its own method.
        def main_window():
            MainGUI(self.master)
            self.master.withdraw()

        master = self.master = Toplevel(master)
        # this is not how you should be defining master.

        button = Button(text="CLICKME", command=lambda: self.main_window())
        # missing geometry layout... grid(), pack() or place()
        # your button command is using a lambda to call a class method but your define it as a function instead.

这是您正在尝试的一个更简单的版本:

import tkinter as tk


class MainGUI(tk.Tk):
    def __init__(self):
        super().__init__()
        tk.Button(self, text="Open Toplevel", command=self.open_toplevel_window).pack()

    def open_toplevel_window(self):
        OtherGUI(self)
        self.withdraw()


class OtherGUI(tk.Toplevel):
    def __init__(self, master):
        super().__init__()
        tk.Button(self, text="Close top and deiconify main", command=self.main_window).pack()

    def main_window(self):
        self.master.deiconify()
        self.destroy()


MainGUI().mainloop()

正如您在此处看到的,当您从控制主窗口和顶层窗口的 tkinter 类继承时,管理它们变得更容易,执行任务的代码更少。

【讨论】:

猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2019-06-30
  • 1970-01-01
  • 1970-01-01
  • 2020-11-18
相关资源
最近更新 更多