且构网

分享程序员开发的那些事...
且构网 - 分享程序员编程开发的那些事

python:将值附加到类外的列表中,在类外也有附加的函数,但在类内调用函数

更新时间:2022-12-16 16:40:42

Frame ReceiptPage 是在开始时创建的,在你按下任何按钮甚至看到窗口之前,所以 Labels从空列表中获取信息.您必须在 ReceiptPage 中添加更新 Labels 的功能,并在您取消 Check Out

Frame ReceiptPage is create at start, before you press any button or even see window, so Labels get information from empty lists. You have to add function which updates Labels in ReceiptPage and execute it when you pless Check Out

您还必须将 self. 用于标签,以便您可以访问其他功能中的标签.

You will have to also use self. for labels so you have access to labels in other functions.

ReceiptPage 具有更新标签的功能.标签使用self.

ReceiptPage has function which update labels. Labels uses self.

class ReceiptPage(tk.Frame):

    def update_labels(self):
        self.fullreceipt['text'] = '\n'.join(map(str, Receipt))
        self.sumprice['text'] = sum(prices)

OrderPage 具有改变页面和运行update_labels 的功能.controler 也使用 self.

OrderPage has function which change page and run update_labels. controler also uses self.

def show_check_out(self):
    self.controller.show_frame(ReceiptPage)
    self.controller.frames[ReceiptPage].update_labels()

和按钮执行此功能

    checkout = tk.Button(self, text="Check Out", command=self.show_check_out)

完整代码:


Full code:

import tkinter as tk
from threading import Thread
from queue import Queue
import time
from tkinter import messagebox

LARGE_FONT = ("Verdana", 12)


Receipt = []
prices = []
job_queue = Queue()
Orders = []

class SushiMenuApp(tk.Tk):

    def __init__(self, *args, **kwargs):
        tk.Tk.__init__(self, *args, **kwargs)
        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 (OrderPage, ReceiptPage):
            frame = F(container, self)

            self.frames[F] = frame

            frame.grid(row=0, column=0, sticky="nsew")

        self.show_frame(OrderPage)

    def show_frame(self, cont):
        frame = self.frames[cont]
        frame.tkraise()

def sushichef(job_queue):
    while True:
        a = job_queue.get()
        if a is None:
            print("There are no more orders")
            break        
        messagebox.showinfo("Message", "Sushi Chef started doing you order")
        time.sleep(a)
        print("Your order will be coming to you now")
        job_queue.task_done()


class OrderPage(tk.Frame):

    def __init__(self, parent, controller):
        tk.Frame.__init__(self, parent)
        self.controller = controller

        label = tk.Label(self, text="Sushi Selections", font=LARGE_FONT)
        label.grid(row=0, column=0, columnspan=4)

        checkout = tk.Button(self, text="Check Out", command=self.show_check_out)
        checkout.grid(row=0, column=4)

        for _ in range(4):  # 4 Sushi Chefs
            thread = Thread(target=sushichef, args=(job_queue,))
            thread.start()
            Orders.append(thread)

        shrimptempura = tk.Button(self, text="Shrimp Tempura", command=staction)
        shrimptempura.grid(row=1, column=0)

    def show_check_out(self):
        self.controller.show_frame(ReceiptPage)
        self.controller.frames[ReceiptPage].update_labels()

def staction():
    for item in [6]:
        job_queue.put(item)
    prices.append(69)
    Receipt.append("Shrimp Tempura")

class ReceiptPage(tk.Frame):

    def __init__(self, parent, controller):

        tk.Frame.__init__(self, parent)

        self.label = tk.Label(self, text="Receipt", font=LARGE_FONT)
        self.label.grid(row=0, columnspan=4, sticky="nsew")

        self.fullreceipt= tk.Label(self, text='\n'.join(map(str, Receipt)))
        self.fullreceipt.grid(row=1, columnspan=4, rowspan=48)

        self.sumprice= tk.Label(self, text=sum(prices))
        self.sumprice.grid(row=49, column=1, columnspan=2)

    def update_labels(self):
        self.fullreceipt['text'] = '\n'.join(map(str, Receipt))
        self.sumprice['text'] = sum(prices)


app = SushiMenuApp()
app.mainloop()

为了让它更通用,你可以在每个框架函数中创建update_frame(甚至是空函数),然后你可以在show_frame


To make it more universal you can create in every frame function update_frame (even empty function) and then you can execute it in show_frame

def show_frame(self, cont):
    frame = self.frames[cont]
    frame.tkraise()
    frame.update_frame()

不要使用名称 update() 因为它被 tkinter 使用.