如何使标签的文本自动更改?

How to make the text of a Label change automatically?

我在选择新的 Combobox 选项时自动更新 ttk.Label(frame, text=value).grid(column=1, row=2) 时遇到问题。我知道这与我的处理程序函数有关,但就我的生活而言,我一直无法弄清楚。

import tkinter as tk
from tkinter import ttk
from tkinter import *
from time import *

vegetable_needs = {
    'Tomato': {'ph': '6', 'moisture': '60', 'humidity': '70'},
    'Bell pepper': {'ph': '9', 'moisture': '61', 'humidity': '71'},
    'Cucumber': {'ph': '2', 'moisture': '62', 'humidity': '72'},
    'Broccoli': {'ph': '4', 'moisture': '63', 'humidity': '73'},
    'Green Bean': {'ph': '1', 'moisture': '64', 'humidity': '74'},
    'Zucchini': {'ph': '5', 'moisture': '65', 'humidity': '75'},
    'Sweet potatoe': {'ph': '0', 'moisture': '66', 'humidity': '76'}
}

#Create Frame
def create_input_frame(container):
    #declare string variables
    vegetable = tk.StringVar()

    frame = tk.Frame(container, borderwidth=1, relief=RIDGE, padx=15, pady=10)
    
    options = ttk.Combobox(frame, width = 20, textvariable = vegetable)
    #list of veggies
    options['values'] = (
    "Tomato",
    "Bell pepper",
    "Cucumber",
    "Broccoli",
    "Green Bean",
    "Zucchini",
    "Sweet potatoe"
    )
    options['state'] = 'readonly'

    ttk.Label(frame, text = "Select a veggie: ", font = ("Times New Roman", 10)).grid(column=0, row=0, padx=5, pady=0)
    options.grid(column = 1, row = 0)
    options.current()
    

    def handler(event):
        current = options.current()
        if current != -1:
            ph_level = vegetable_needs[vegetable.get()]['ph']
            value = ph_level
            print(value)
    
    
    options.bind('<<ComboboxSelected>>', handler)
    
    ttk.Label(frame, text=value).grid(column=1, row=2)
    ttk.Label(frame, text='PH Level').grid(column=0, row=2)
  
    return frame

#Create the main window
def create_main_window():
    root = tk.Tk()
    root.title('Growing Veggies')
    root.attributes('-toolwindow', False)
    r1=0
    r2=0
    r3=0
    
    #Create zones 1-5 row 0
    if number_of_zones >= 1 and number_of_zones <= 5:
        for r1 in range(number_of_zones):
            input_frame = create_input_frame(root)
            input_frame.grid(column=r1, row=0)
            r1+=1
    #Create zones 6-10 rows 0-1
    elif number_of_zones > 5 and number_of_zones <=10:
        for r1 in range(5):
            input_frame = create_input_frame(root)
            input_frame.grid(column=r1, row=0)
            r1+=1
        for r2 in range(number_of_zones - 5):
            input_frame = create_input_frame(root)
            input_frame.grid(column=r2, row=1)
            r2+=1
    #Create zones 11-15 rows 0-2
    elif number_of_zones > 10 and number_of_zones <=15:
        for r1 in range(5):
            input_frame = create_input_frame(root)
            input_frame.grid(column=r1, row=0)
            r1+=1
        for r2 in range(5):
            input_frame = create_input_frame(root)
            input_frame.grid(column=r2, row=1)
            r2+=1
        for r2 in range(number_of_zones - 10):
            input_frame = create_input_frame(root)
            input_frame.grid(column=r2, row=2)
            r3+=1

    #Output an error
    else:
        root.title('ERROR')
        ttk.Label(root, text = "Please enter a valid number between 1 and 15").grid(column=1, row=1, padx=15, pady=5)
        ttk.Button(root, text = "Acknowledge", command=quit).grid(column=1, row=2, padx=5, pady=5)
    
    root.mainloop()

if __name__ == "__main__":

    value = "?"
    number_of_zones = int(input("How many zones should be made? "))
    create_main_window()
'''

您需要创建变量来引用您的标签。此外,您需要在 PH 更改时更新它们。代码应该是这样的,更改标记为 ### EDITED LINE### ADDED LINE:

import tkinter as tk
from tkinter import ttk
from tkinter.constants import *

vegetable_needs = {
    'Tomato': {'ph': '6', 'moisture': '60', 'humidity': '70'},
    'Bell pepper': {'ph': '9', 'moisture': '61', 'humidity': '71'},
    'Cucumber': {'ph': '2', 'moisture': '62', 'humidity': '72'},
    'Broccoli': {'ph': '4', 'moisture': '63', 'humidity': '73'},
    'Green Bean': {'ph': '1', 'moisture': '64', 'humidity': '74'},
    'Zucchini': {'ph': '5', 'moisture': '65', 'humidity': '75'},
    'Sweet potatoe': {'ph': '0', 'moisture': '66', 'humidity': '76'}
}

#Create Frame
def create_input_frame(container):
    #declare string variables
    vegetable = tk.StringVar()

    frame = tk.Frame(container, borderwidth=1, relief=RIDGE, padx=15, pady=10)
    
    options = ttk.Combobox(frame, width = 20, textvariable = vegetable)
    #list of veggies
    options['values'] = (
    "Tomato",
    "Bell pepper",
    "Cucumber",
    "Broccoli",
    "Green Bean",
    "Zucchini",
    "Sweet potatoe"
    )
    options['state'] = 'readonly'

    veggie_label = ttk.Label(frame, text = "Select a veggie: ", font = ("Times New Roman", 10)) ### EDITED LINE
    veggie_label.grid(column=0, row=0, padx=5, pady=0) ### ADDED LINE
    options.grid(column = 1, row = 0)
    options.current()
    

    def handler(event):
        current = options.current()
        if current != -1:
            ph_level = vegetable_needs[vegetable.get()]['ph']
            value = ph_level
            value_label.config(text=value) ### ADDED LINE
            print(value)
    
    
    options.bind('<<ComboboxSelected>>', handler)
    
    value_label = ttk.Label(frame, text=value) ### EDITED LINE
    value_label.grid(column=1, row=2) ### ADDED LINE
    ph_label = ttk.Label(frame, text='PH Level') ### EDITED LINE
    ph_label.grid(column=0, row=2) ### ADDED LINE
    
    return frame

#Create the main window
def create_main_window():
    root = tk.Tk()
    root.title('Growing Veggies')
    # root.attributes('-toolwindow', False)
    r1=0
    r2=0
    r3=0
    
    #Create zones 1-5 row 0
    if number_of_zones >= 1 and number_of_zones <= 5:
        for r1 in range(number_of_zones):
            input_frame = create_input_frame(root)
            input_frame.grid(column=r1, row=0)
            r1+=1
    #Create zones 6-10 rows 0-1
    elif number_of_zones > 5 and number_of_zones <=10:
        for r1 in range(5):
            input_frame = create_input_frame(root)
            input_frame.grid(column=r1, row=0)
            r1+=1
        for r2 in range(number_of_zones - 5):
            input_frame = create_input_frame(root)
            input_frame.grid(column=r2, row=1)
            r2+=1
    #Create zones 11-15 rows 0-2
    elif number_of_zones > 10 and number_of_zones <=15:
        for r1 in range(5):
            input_frame = create_input_frame(root)
            input_frame.grid(column=r1, row=0)
            r1+=1
        for r2 in range(5):
            input_frame = create_input_frame(root)
            input_frame.grid(column=r2, row=1)
            r2+=1
        for r2 in range(number_of_zones - 10):
            input_frame = create_input_frame(root)
            input_frame.grid(column=r2, row=2)
            r3+=1

    #Output an error
    else:
        root.title('ERROR')
        error_label = ttk.Label(root, text = "Please enter a valid number between 1 and 15")
        error_label.grid(column=1, row=1, padx=15, pady=5)
        ttk.Button(root, text = "Acknowledge", command=quit).grid(column=1, row=2, padx=5, pady=5)
    
    root.mainloop()

if __name__ == "__main__":

    value = "?"
    number_of_zones = int(input("How many zones should be made? "))
    create_main_window()

注意我将标签定义为变量:value_labelph_labelerror_label。这使得标签可以在整个程序中被引用。还要注意我如何在 handler 函数中调用 value_label.config(text=value)。这会将 value_label 的文本设置为 PH 级别。

很简单,只需在创建 ttk.Label 时使用 textvariable= 选项而不是 text= 选项,然后每次 [=15] 时 Label 都会自动更新=] StringVar 的值已更改。

#    ttk.Label(frame, text=value).grid(column=1, row=2)
    ttk.Label(frame, textvariable=vegetable).grid(column=1, row=2)
    ttk.Label(frame, text='PH Level').grid(column=0, row=2)