从本质上讲,你的问题有一个简单的答案。“如何从对象X获取值?” 对于任何对象,答案都是相同的:你可以通过询问对象X来获得答案。为此,你所需要做的就是获取对该对象的引用,然后直接访问该属性。
从其他页面访问数据
在你的情况下,中的代码
PageTwo需要引用,
PageOne以便你可以获取
v变量。
那么,你如何获得参考?代码(从教程复制或从教程复制的stackoverflow答案复制)旨在简化此过程。每个页面都有对控制器的引用,该控制器也具有对每个页面的引用。因此,你可以要求控制器为你提供对页面的引用。
第一步是将引用保存到每个类中的控制器。有趣的是,你已经在中执行了此操作PageOne,但是你应该在所有页面中都执行此操作。确保添加
self.controller = controller每种
__init__方法,如下所示:
class PageTwo(tk.frame): def __init__(self, parent, controller): ... self.controller=controller ...
接下来,我们需要在控制器类中添加一个方法,该方法将返回对该页面的引用。将以下功能添加到
SampleApp:
class SampleApp(tk.Tk): ... def get_page(self, page_class): return self.frames[page_class] ...
现在,你可以从任何“页面”中访问任何其他“页面”的对象。例如,
PageTwo你可以像这样访问v变量PageOne:
page1 = self.controller.get_page(PageOne)page1.v.set("Hello, world")使用共享数据
更好的解决方案是让你的
SampleApp类创建一组所有页面共享的变量。你可以在该类中创建字典,然后使用控制器授予每个页面访问权限。例如:
class SampleApp(tk.Tk): def __init__(self, *args, **kwargs): tk.Tk.__init__(self, *args, **kwargs) self.shared_data = { "username": tk.StringVar(), "password": tk.StringVar(), ... )然后,可以从任何类中访问如下数据:
entry1 = tk.Entry(self, textvariable=self.controller.shared_data["username"])...username = self.controller.shared_data["username"].get()
之所以是更好的解决方案,是因为你的页面不必知道其他页面的实现方式。当页面依赖于另一页面的确切实现时,这称为紧密耦合。如果页面不需要知道其他页面的实现方式,则称为松耦合。
松耦合使你更具灵活性。它们不是将每个页面都紧密地耦合到其他页面,而是都紧密地耦合到一个对象:控制器。只要每个页面只知道控制器,每个页面都可以随时更改,而不会影响程序的其余部分。
当然,如果要更改控制器,则必须更改所有页面,但是如果设计得好,则不太可能出现该控制器,并且在出现时更易于管理。



