1

我试图通过按下 Tkinter GUI 中的按钮来调用外部函数;函数“插入”到文本元素中。这完美地工作;只要 time.sleep() 没有紧随其后。如果不遵循,则文本正确更新;如果是,则文本不会更新,尽管该函数似乎仍在循环运行,因为它会愉快地将文本打印到控制台。

这是我的示例脚本:

from Tkinter import *
from time import sleep

def test_function(gui_self):
    while True:
        print "Debug message"
        gui_self.main_.insert(END, "Test")


class GUI:
    def __init__(self, master):
        frame = Frame(master, width=300, height=500)
        frame.pack()
        self.main_ = Entry(frame, width=80, justify=CENTER)
        self.main_.pack()

        test_function(self)

root = Tk()
application = GUI(root)
root.mainloop()

这很好用。但是,将 test_function 更改为以下内容似乎会使事情变得混乱:

def test_function(gui_self):
    while True:
        print "Debug message"
        gui_self.main_.insert(END, "Test")
        sleep(5)

有什么建议可以解决我在这里做错的任何事情吗?我确信这只是一个问题,我作为一个相当基本的用户,没有使用正确的语法。

作为旁注,“睡眠”命令似乎也完全冻结了程序,我觉得这很烦人而且没有吸引力。除了“管道”线程之外​​,是否有一种方法可以将循环暂停可变设置(例如,var = 1(秒))的时间量,这将是有效的并且更......干净?

谢谢。

4

2 回答 2

3

一般来说,不要调用time.sleep单线程 GUI,否则你会发现它会阻塞。

处理睡眠的正确方法是使用 GUI 事件。

请参阅另一个 Stack Overflow问题中的此示例,该问题显示如何使用after所有 TK 根窗口都有的方法。

于 2012-05-12T13:56:58.553 回答
3

我完全同意尼克克雷格伍德的回答——不要让你的 gui 的主线程进入睡眠状态。通常,您希望调用afterwhich 注册要在(大约)X 毫秒后调用的函数。test_function这是一个每 5 秒调用一次的示例。每次调用 test_function 时,它都会重新注册自己以在 5 秒后调用。

def test_function(gui_self):
    print "Debug message"
    gui_self.main_.insert(END, "Test")
    gui_self.after(5000,test_function,gui_self)
    #the line below also should work.  As long as the item is a Tkinter widget
    #gui_self.main_.after(5000,test_function,gui_self) 

另外,完全不相关,(但就风格而言)-您使用main_inGUI而不是 just有什么原因main吗?通常,尾随下划线会附加到带有 python 关键字的 aviod 名称冲突中。据我所知,main不是关键字。

于 2012-05-12T14:37:37.963 回答