【问题标题】:Can't get Tkinter GUI to show using classes无法使用类显示 Tkinter GUI
【发布时间】:2020-05-29 19:38:13
【问题描述】:

我正在尝试制作一个 Tkinter GUI,它可以获取 Excel 文档、读取它们并将它们导出到窗口。问题是当我将代码更改为以下以合并类结构时,我无法再正确加载 GUI。

import tkinter as tk
from tkinter.filedialog import askopenfilename

def NewFile():
    print("New File!")
def OpenFile():
    name = askopenfilename()
    print(name)
def About():
    print("About works")
def deletelist():
    listbox.delete(0, END)

class MainApplication(tk.Frame):
    def __init__(self, master):
        tk.Frame.__init__(self, master)
        self.master = master
        self.frame = tk.Frame(self.master)

        self.load = tk.Button(self.frame, text = "Load XLSX File", command = OpenFile)
        self.load.grid(row = 0, column = 0, padx = 5, pady = 5, sticky = 'w')

        self.ckframe = tk.LabelFrame(self.frame, text="Currency Selections")
        self.ckframe.grid(row = 1, column = 0, padx = 5, pady = 5, stick = 'nesw')
        self.prochk = tk.Checkbutton(self.ckframe, text = '1 Currency').grid(row = 1, column = 0, columnspan = 2, sticky = 'w')
        self.msnchk = tk.Checkbutton(self.ckframe, text = '2 Currency').grid(row = 1, column = 2, columnspan = 2, sticky = 'w')
        self.nightschk = tk.Checkbutton(self.ckframe, text = '3 Currency').grid(row = 1, column = 4, columnspan = 2, sticky = 'w')
        self.semichk = tk.Checkbutton(self.ckframe, text = '4 Currency').grid(row = 2, column = 0, columnspan = 2, sticky = 'w')
        self.instqualCRchk = tk.Checkbutton(self.ckframe, text = '5 Currency').grid(row = 2, column = 2, columnspan = 2, sticky = 'w')
        self.msnCRchk = tk.Checkbutton(self.ckframe, text = '6 Currency').grid(row = 2, column = 4, columnspan = 2, sticky = 'w')

        self.listbox = tk.Listbox(self.frame, width = 83)
        self.listbox.grid(row = 3, column = 0, columnspan = 1, sticky = 'w') # Fix width size function
        self.listbox.insert(1, 'Test1')
        self.listbox.insert(0, 'Test2')
        self.save = tk.Button(self.frame, text = "Save").grid(row = 8, column = 0, padx = 5, pady = 5, stick = 'e')
        self.delete = tk.Button(self.frame, text = "Delete", command = deletelist).grid(row = 8, column = 0, padx = 45, pady = 5, stick = 'e')

if __name__ == '__main__':
    root = tk.Tk()
    MainApplication(root)
    root.mainloop()

我进行了很多搜索,试图找到使用 tkinter GUI 和网格系统的类的解决方案,但我主要找到了使用 pack() 解决方案制作 GUI 的方法。

【问题讨论】:

标签: python python-3.x user-interface tkinter


【解决方案1】:

MainApplication 的实例是一个框架。您永远不会在该实例上调用 packplacegrid,以便该框架及其所有子框架不可见。

此框架创建另一个框架,其中包含所有其他小部件self.frame。您也永远不会在其上调用 packplacegrid,因此它及其所有子项都将不可见。

由于小部件位于不可见的框架中,并且该框架本身是不可见的,因此其他小部件均不可见。

首先要做的是摆脱self.frame。删除创建它的行,在您引用self.frame 的任何地方,将其替换为self。由于self 在此上下文中已经是一个框架,因此在其中创建另一个框架是没有意义的。

接下来,您需要将MainApplication 的实例添加到窗口中。由于它是唯一直接在根窗口中的小部件,pack 是最简单的选择。

root = tk.Tk()
app = = MainApplication(root)
app.pack(fill="both", expand=True)

【讨论】:

  • 这行得通,但格式有点混乱。我确实发现我从未在MainApplication 中定义框架,所以我在self.frame = tk.Frame(self.master) 下添加了self.frame.grid(row=0, column=0, sticky='nsew'),效果也很好。与使用 pack() 相比,这将如何影响我的程序整体?
  • @MicahRutherford:只要您记得调用grid_rowconfiguregrid_columnconfigure 来适当地分配权重,grid 将与pack 一样有效。然而,如果self.frameself.master 作为它的父级,它就违背了MainApplicationFrame 继承的目的。对于像这样的类来说,将小部件放在父级而不是本身中是一种不好的做法。它破坏了封装。
  • 感谢您的快速回复!有道理,在对小部件中的行和列进行一些调整后,程序现在可以完美运行。实际上现在效果更好。
猜你喜欢
  • 2018-06-26
  • 2017-11-14
  • 2021-03-27
  • 2021-04-20
  • 1970-01-01
  • 1970-01-01
  • 2017-12-24
  • 2017-10-16
  • 2018-08-05
相关资源
最近更新 更多