如何为具有多个 类 的应用程序创建保存功能?

How do I create a save function for an application that has multiple classes?

我正在为我的 GUI 使用 Tkinter 开发一个程序。现在我正在概念化整个项目,所以我将提供的代码非常简单。

本质上,我想创建一个主要的 window,它有几个小部件,每个小部件都是用自己的 classes 编写的。其中一个小部件是导航栏,其中 "File" -> "Save As" 将存在。

我的问题是,如果我将导航栏作为单独的 class 在主 class 中实例化,则在导航栏中编写的保存函数将无法查看其他 classes.

我已经想到了可能的两种解决方案,但我不确定其中任何一种是否一定是最佳软件工程实践的正确选择。

可能的解决方案 1:创建一个单独的线程,不断等待用户单击保存。单击保存后,它会更改一个事件标志,这会导致主 class 调用一些保存函数来保存所有变量。我的问题是这是一种持续的资源浪费。线程将不断浪费资源,等待保存按钮被点击。

可能的解决方案 2:在单独的 class 中创建导航栏,但在实例化它的主 class 中定义导航栏函数。我对此的问题是,它使主要的 class 与我希望在其他地方定义的无关功能串通起来以获得更好的实践。此外,我不完全确定我将如何做到这一点,但我确信如果我花时间研究它,可以通过某种方式完成它。

class Main:
    def __init__(self, rt):
        self.rt = rt
        self.navbar = navbar.NavBar(rt)
        self.rt.mainloop()

class NavBar(tkinter.Frame):
    def __init__(self, master):
        tkinter.Frame.__init__(self, master)
        self.master = master
        self.bg='red'
        self.text = tkinter.Text(self, height=1, width=30)
        self.text.insert(tkinter.END, "File")
        self.text.pack()
        self.grid(row=0, column=0)

if __name__ == "__main__":
    root = tkinter.Tk()
    root.title('Automation')
    main = Main(root)

在这里,Navbar 将有一个名为 File 的按钮,如果您滚动它会生成其他按钮的列表,其中之一是 "Save As"。如果单击此另存为按钮,我希望能够保存属于 Main 的所有变量。

TLDR:我想找出创建保存文件功能的最佳方法,能够保存来自不同 classes 的变量,这些变量都在主伞 class 下实例化.

通常我会将Main class设置为所有Frames的控制器,让Main直接继承自Tk。下面是有关如何使用此方法从其他 class 访问属性的示例:

import tkinter as tk

class Main(tk.Tk):
    def __init__(self):
        tk.Tk.__init__(self)
        self.navbar = NavBar(self)
        self.another_frame = AnotherFrame(self)
        self.navbar.grid(row=0, column=0)
        self.another_frame.grid(row=1, column=0)

class NavBar(tk.Frame):
    def __init__(self, master):
        tk.Frame.__init__(self, master)
        self.master = master
        tk.Button(self,text="Button of first frame",command=self.print_other_frame).pack()

    def print_other_frame(self):
        print (self.master.another_frame.entry.get()) #access master attributes

class AnotherFrame(tk.Frame):
    def __init__(self,master):
        tk.Frame.__init__(self, master)
        self.entry = tk.Entry(self)
        self.entry.pack()
        self.entry.insert(0,"Test from 2nd frame")

if __name__ == "__main__":
    root = Main()
    root.title('Automation')
    root.mainloop()