Tkinter中嵌入Frame的PanedWindow无法拉伸且不显示窗扇问题求解
问题成因分析
- PanedWindow子组件未使用
add()方法添加
PanedWindow为专属布局容器,仅支持通过自带的
add()方法注册子控件,不能使用grid()/pack()/place()管理子组件。原代码中顶层PanedWindow容器container通过grid()添加两个页面,导致PanedWindow无法识别子组件,无法生成窗扇,自然无法实现拖拽拉伸效果。
- PanedWindow自身布局未配置拉伸属性
顶层
container调用grid()方法时未添加sticky="nsew"参数,导致PanedWindow本身无法跟随主窗口缩放。
- 容器类Frame未配置行列权重
MainPage、PlottingPage等作为容器的Frame实例,未给自身的行、列设置weight参数,导致内部嵌套的PanedWindow和控件无法跟随父容器拉伸。
- 子组件重复布局冲突
代码中多处先对Frame调用
grid(),后又将其添加到PanedWindow的操作,add()方法会自动接管子组件的布局控制,重复的布局声明会导致逻辑冲突,窗扇样式、拉伸逻辑均会失效。
修正后可运行代码
import tkinter as tk from tkinter import ttk class Main(tk.Tk): def __init__(self, *args, **kwargs): tk.Tk.__init__(self, *args, **kwargs) tk.Tk.wm_title(self, "Program") self.columnconfigure(0, weight=1) self.rowconfigure(0, weight=1) container = tk.PanedWindow(self, bg='bisque',orient=tk.HORIZONTAL, relief='groove', borderwidth=2, sashwidth=3) # 增加sticky让PanedWindow跟随主窗口拉伸 container.grid(row=0, column=0, sticky="nsew") self.frames = {} main_page = MainPage(container, self) self.frames[0] = main_page # 用add方法添加子组件,不要用grid container.add(main_page, stretch="always") plotting_page = PlottingPage(container, self) self.frames[1] = plotting_page container.add(plotting_page, stretch="always") class MainPage(tk.Frame): def __init__(self, parent, controller): tk.Frame.__init__(self, parent) # 配置当前Frame的行列权重,让内部组件可以拉伸 self.columnconfigure(0, weight=1) self.rowconfigure(1, weight=3) self.rowconfigure(2, weight=1) # Paned Windows top_pane = tk.PanedWindow(self, orient=tk.HORIZONTAL, relief='groove', borderwidth=2, sashwidth=3) top_pane.grid(column=0, row=1, sticky="nsew") bottom_pane = tk.PanedWindow(self, orient=tk.VERTICAL, relief='groove', borderwidth=2, sashwidth=50) bottom_pane.grid(column=0, row=2, sticky="nsew") # Frames top_frame = ttk.LabelFrame(self, text="Top frame") bottom_frame = ttk.LabelFrame(self, text="Bottom frame") # 去掉Frame的grid调用,由PanedWindow接管布局 top_frame.columnconfigure(0, weight=1) top_frame.rowconfigure(0, weight=1) top_pane.add(top_frame, stretch="always") bottom_frame.columnconfigure(0, weight=1) bottom_frame.rowconfigure(0, weight=1) bottom_pane.add(bottom_frame, stretch="always") top = tk.Label(top_frame, text="top pane") top.grid(column=0, row=0, sticky="nsew") bottom = tk.Label(bottom_frame, text="bottom pane") bottom.grid(column=0, row=0, sticky="nsew") class PlottingPage(tk.Frame): def __init__(self, parent, controller): tk.Frame.__init__(self, parent) # 配置当前Frame的行列权重 self.columnconfigure(0, weight=1) self.rowconfigure(0, weight=1) # Paned Windows right_pane = tk.PanedWindow(self, orient=tk.HORIZONTAL, relief='groove', borderwidth=2, sashwidth=3) right_pane.grid(column=0, row=0, sticky="nsew") # Frames right_frame = ttk.LabelFrame(self, text="Right frame") right_frame.columnconfigure(0, weight=1) right_frame.rowconfigure(0, weight=1) right_pane.add(right_frame, stretch="always") # Widgets right = tk.Label(right_frame, text="right pane") right.grid(column=0, row=0, sticky="nsew") def main(): app = Main() app.geometry("800x600") app.mainloop() if __name__ == '__main__': main()
内容的提问来源于stack exchange,提问作者user10575420
相关产品推荐
相关产品推荐

