【问题标题】:Updating label upon getting message from queue从队列中获取消息时更新标签
【发布时间】:2019-07-26 04:06:01
【问题描述】:

我正在尝试更新标签以显示当它通过队列接收到数字时正在倒计时的数字。我可以看到它正在控制台中打印,但标签没有改变。任何帮助或建议都会有所帮助!

这是我的代码:

import tkinter as tk
import time
import threading
import queue

class GUIApp:
    def __init__(self):
        self.root = tk.Tk()
        self.buttonCountDown = tk.Button(text='Count Down', command=self.countDownAction)
        self.buttonCountDown.pack()
        self.label = tk.Label(text='default')
        self.label.pack()
        self.queue = queue.Queue()
        self.root.mainloop()

    def countDown(self, seconds):
        for i in range(seconds, 0, -1):
            self.queue.put(i)
            time.sleep(1)

    def listenToQueue(self):
        while True:
            try:
                if self.queue.empty() == False:
                    print(self.queue.get(0))
                    self.label['text'] = self.queue.get(0)
                elif self.queue.empty() == True:
                    pass
            except queue.Empty:
                pass

    def countDownAction(self):
        listenThread = threading.Thread(target=self.listenToQueue)
        listenThread.start()
        thread = threading.Thread(target=self.countDown, args=(5,))
        thread.start()
        thread.join()

app = GUIApp()

【问题讨论】:

    标签: python tkinter queue python-multithreading


    【解决方案1】:

    您需要知道的第一件事是Queue.get() 删除项目并将其返回,类似于dict.pop()。因此,当您执行print(self.queue.get(0)) 时,该项目已从队列中删除。如果你想打印和配置它,你必须先将它分配给一个变量:

    def listenToQueue(self):
        while True:
            try:
                if self.queue.empty() == False:
                    s = self.queue.get(0)
                    print (s)
                    self.label['text'] = s
                elif self.queue.empty() == True:
                    pass
            except queue.Empty:
                pass
    

    接下来,调用thread.join() 将等待线程终止。在当前设置中,您根本不需要调用此方法。

    def countDownAction(self):
        listenThread = threading.Thread(target=self.listenToQueue)
        listenThread.start()
        thread = threading.Thread(target=self.countDown, args=(5,))
        thread.start()
        #thread.join() #not required
    

    【讨论】:

    • 这样做我可以将标签更改为 1,但我没有看到它倒计时 5、4、3、2、1。我在 countDown 方法上做错了吗?
    • 你注释掉了thread.join吗?修改了以上两个,我可以看到倒计时到 1 就好了。
    • 抱歉,我没有评论它,是的,它现在完美运行。如果我想在线程完成后做某事怎么办?我必须使用 thread.join() 吗?
    • 我只想在你的倒计时函数的末尾添加任何需要做的事情。
    • 我明白了。有没有办法在 countDown 函数之外做到这一点?
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2018-07-10
    • 1970-01-01
    • 1970-01-01
    • 2015-09-17
    • 1970-01-01
    • 2013-12-13
    • 1970-01-01
    相关资源
    最近更新 更多