为何调用tk.Toplevel会生成两个窗口?
Tkinter 子窗体弹出双窗口问题解决
问题现象
主程序(frmMain)调用createForm打开子窗体时,每次会弹出两个窗口:一个是正常的目标子窗体,另一个是空白且无法通过右上角关闭按钮关闭的异常窗口。
错误代码示例
frmMain=tk.Tk() def createForm(): lFrm = tk.Toplevel() # 创建新窗体 initForm(lFrm) # 初始化窗体并设置焦点事件冒泡 return lFrm def initForm(pFrm): tk.Toplevel.__init__(pFrm) # 手动调用父类初始化(未使用super) # super().__init__(master=pFrm) setWindowFocusEvent(pFrm) # 实现MDI应用的焦点联动:任意窗口获焦时,所有窗口按顺序前置
调用示例:
def listBands(): global frmMain frmMain.lListBandsFrm = createForm()
排查过程
- 确认代码中没有重复调用
tk.Tk(),每个窗体仅调用一次tk.Toplevel() - 尝试移除
tk.Toplevel.__init__(pFrm)调用,会导致功能异常(如无法使用.bind方法绑定事件)
问题根源
错误代码中,initForm函数接收的pFrm已经是tk.Toplevel的实例,此时再次调用tk.Toplevel.__init__(pFrm)相当于重复初始化Toplevel对象,额外创建了一个空白窗口。
正确解决方案:子类化Tk.Toplevel
通过子类化tk.Toplevel,在子类的__init__方法中正确调用父类初始化逻辑,避免重复创建窗口的同时保留所需功能:
class FrmMDI(tk.Toplevel): # 自定义MDI子窗体类,包含所需初始化逻辑 def __init__(self): # 实例化时自动调用 super().__init__() # 正确调用父类Toplevel的初始化方法 setWindowFocusEvent(self) # 设置MDI焦点联动逻辑,优化Windows下的多窗口体验 def createForm(): lFrm = FrmMDI() # 使用自定义子类创建子窗体 return lFrm
内容的提问来源于stack exchange,提问作者Vexen Crabtree
相关产品推荐
相关产品推荐

