Python Tkinter类式多页面间变量传递后标签显示PY_VAR0的问题求助
Let's break down what's going wrong here and fix it step by step!
Key Problems in Your Code
- You're replacing the StringVar object instead of updating its value: In your
pageturnmethod,self.controller.shared_data["variable"] = 'string i wanna pass'overwrites the originaltk.StringVar()instance with a plain string. That's why.get()throws errors later (strings don't have this method) and why you sawPY_VAR0initially (that's the default string representation of an unmodified StringVar). - Labels use static text instead of dynamic binding: Your page2 labels are created with fixed text at initialization. Even if you fixed the variable update, they wouldn't refresh unless you explicitly update them or use Tkinter's built-in variable binding.
Corrected Code with Explanations
import tkinter as tk from tkinter import ttk class example(tk.Tk): def __init__(self, *args, **kwargs): tk.Tk.__init__(self, *args, **kwargs) # Keep the StringVar instance intact — we'll update its value later, not replace it self.shared_data = { "variable": tk.StringVar() } container = tk.Frame(self) container.pack(side="top", fill="both", expand=True) container.grid_rowconfigure(0, weight=1) container.grid_columnconfigure(0, weight=1) self.frames = {} for F in (page1, page2): frame = F(container, self) self.frames[F] = frame frame.grid(row=0, column=0, sticky="nsew") self.show_frame(page1) def get_page(self, page_class): return self.frames[page_class] def show_frame(self, cont): frame = self.frames[cont] # Trigger content update when switching to the frame (for static widgets) if hasattr(frame, "update_content"): frame.update_content() frame.tkraise() class page1(tk.Frame): def __init__(self, parent, controller): tk.Frame.__init__(self, parent) self.controller = controller label = ttk.Label(self, text="first page") label.grid(row=0, column=4, padx=10, pady=10) button1 = ttk.Button(self, text="turn page", command=lambda: self.pageturn()) button1.grid(row=3, column=1, padx=10, pady=10) def pageturn(self): # Use .set() to update the StringVar's value — don't replace the object itself self.controller.shared_data["variable"].set('string i wanna pass') print("variable set here: ", self.controller.shared_data["variable"].get()) self.controller.show_frame(page2) class page2(tk.Frame): def __init__(self, parent, controller): tk.Frame.__init__(self, parent) self.controller = controller self.var = self.controller.shared_data["variable"] # Use textvariable to bind the Label directly to the StringVar # This auto-updates the label whenever the variable changes self.dynamic_label = ttk.Label(self, textvariable=self.var) self.dynamic_label.grid(row=0, column=4, padx=10, pady=10) # For static labels that need manual updates, initialize with empty text self.static_label = ttk.Label(self, text="") self.static_label.grid(row=1, column=4, padx=10, pady=10) # Buttons can also use textvariable for dynamic text updates self.dynamic_button = ttk.Button(self, textvariable=self.var, command=lambda: print(self.var.get())) self.dynamic_button.grid(row=8, column=10, padx=10, pady=10) button2 = ttk.Button(self, text="Check variable value", command=lambda: self.ifok()) button2.grid(row=9, column=10, padx=10, pady=10) def update_content(self): # Manually refresh static widgets when the page is shown self.static_label.config(text=self.var.get()) def ifok(self): # Always use .get() to retrieve the actual string value from the StringVar if self.var.get() == 'string i wanna pass': print("Variable value is correct!") app = example() app.mainloop()
What We Fixed
Proper StringVar updates:
We use.set()to modify the value of the existing StringVar instead of replacing the object. This keeps the variable intact so.get()works as expected.Dynamic widget binding:
Thetextvariableparameter binds widgets directly to the StringVar. Any change to the variable automatically updates the widget's display, no manual refreshes needed.Page switch content refresh:
Theshow_framemethod now calls anupdate_contentmethod on the frame (if it exists) when switching pages. This ensures static widgets (like the second label) show the latest variable value when the page becomes visible.Correct value retrieval:
We consistently use.get()to fetch the actual string value from the StringVar, whether in print statements, condition checks, or manual widget updates.
This should resolve both the PY_VAR0 display issue and the variable passing/updating problems you were facing.
内容的提问来源于stack exchange,提问作者Andreasz

