如何在tkinter中动态更新标签?

时间:2018-07-13 21:24:36

标签: python multithreading tkinter

我创建了这段代码,该代码每秒更新一次标签以指示正在加载某些内容(运行代码以了解我的意思)。我正在将线程模块与tkinter一起使用,但是我觉得必须有一种更有效的方法来实现此目的。

这是我的代码:

from typing import Union
def multi_value(para : Union[list, int]):
    return para[0] if len(para) == 1 else para

def fun(para : Union[list, int]):
    return para

print(type(multi_value([1,2,3]))) #--> [1,2,3]
print(type(multi_value(['1']))) #--> '1'
print(type(multi_value([1]))) #--> 1

此外,如果没有更好的方法来执行此操作,那么如何防止每次关闭根窗口时不断收到的错误?

谢谢!

2 个答案:

答案 0 :(得分:2)

这是一种不涉及线程的简单方法。

保留一个计数器,然后每秒调用一次该函数。在该函数中,只需将计数器的文本设置为列表中每个项目的索引即可。

更新:在评论中回答您的问题。

这不会陷入使我们无法到达mainloop()的某个循环中,因为此代码仅添加了一个命令,该命令以1秒的固定间隔在事件列表上运行。实际发生的是after()方法将添加一个新的偶数,使其运行不超过1秒(1000毫秒)。由于Tkinter是事件驱动的,因此Tkinter会处理mainloop()周期之后的列表中的每个事件。

import tkinter as tk

root = tk.Tk()
counter = 0

def change_text():
    global counter
    my_list = [".", "..", "...", ""]
    if counter != 3:
        l.config(text="Loading{}".format(my_list[counter]))
        counter += 1
        root.after(1000, change_text)
    else:
        l.config(text="Loading{}".format(my_list[counter]))
        counter = 0
        root.after(1000, change_text)

l = tk.Label(root, text = "")
l.pack()

change_text()
root.mainloop()

答案 1 :(得分:2)

这里的答案与@ Mike-SMT相同,但是使用循环功能使其更加整洁。

import tkinter as tk
from itertools import cycle

root = tk.Tk()
my_list = cycle([".", "..", "...", ""])

def change_text():
    l.config(text="Loading{}".format(next(my_list)))
    root.after(1000, change_text)

l = tk.Label(root)
l.pack()

change_text()
root.mainloop()