Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/python/357.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/7/user-interface/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Python 使用Tkinter使用'after'设置工作流_Python_User Interface_Tkinter_Tkinter Canvas - Fatal编程技术网

Python 使用Tkinter使用'after'设置工作流

Python 使用Tkinter使用'after'设置工作流,python,user-interface,tkinter,tkinter-canvas,Python,User Interface,Tkinter,Tkinter Canvas,我试图使用Tkinter的after方法创建预定义的GUI工作流(即管道),但它不起作用,我感到困惑 作为一个简单的示例,我创建了以下简单的GUI: from tkinter import * class example: global frame, rect, text def __init__(self): self.root = Tk() self.initialize() self.workflow()

我试图使用Tkinter的
after
方法创建预定义的GUI工作流(即管道),但它不起作用,我感到困惑

作为一个简单的示例,我创建了以下简单的GUI:

from tkinter import *

class example:

    global frame, rect, text

    def __init__(self):
        self.root = Tk()
        self.initialize()
        self.workflow()
        self.root.mainloop()

    def initialize(self):
        global frame, rect, text
        # frame
        frame = Canvas(self.root, width=500, height=500, bd=0, highlightthickness=0, relief='ridge')
        frame.grid(row=0, column=0)
        # rectangle
        rect = frame.create_rectangle(20, 20, 400, 350, fill='blue')
        # text
        text = frame.create_text(250, 250, text='FIRST...', fill='#ffff00', font=("Purisa", 20, "bold"))

    def change_message(self, new_message):
        global frame, text
        frame.itemconfig(text, text=new_message)

    def workflow(self):
        global frame, rect, text
        self.root.after(2000, self.change_message("SECOND..."))
        self.root.after(4000, self.change_message("END"))

myExample = example()
目的是遵循
工作流
方法中指定的管道,即:

  • 第一:当应用程序运行时,消息显示文本“FIRST…”
  • 第二:2秒后,文本更改并显示“第二…”
  • 第三:4秒后,文本再次更改并显示“结束”
但是,当我运行这个示例时,GUI等待4秒显示,并显示最终的“结束”消息,而不绘制以前的更改

我做错了什么

提前感谢

更换:

self.root.after(2000, self.change_message("SECOND..."))
self.root.after(4000, self.change_message("END"))
与以下任何一项:

self.root.after(2000, lambda : self.change_message("SECOND..."))
self.root.after(4000, lambda : self.change_message("END"))
或者,如中所述:


.after(ms,callback,*args)
要求
callback
作为引用,而不是实际调用
callback
函数。基本上,将
()
callback()
中删除,使其具有
回调

当传递
callback()
而不是
callback
时,如下所示:

widget.after(ms, callback(), *args)
python的作用大致相当于:

callback(*args)
time.sleep(ms / 1000)
这会延迟执行
mainloop()
行,因此GUI显示延迟



这与在每次调用之间添加
self.root.update()
有些相似。您不需要在
之后使用
lambda
。您可以在不使用它的情况下传递其他参数:
self.root.after(2000,self.change_message,“SECOND”)
@BryanOakley再次感谢,希望我能记住这一点。您的解决方案是可行的,但它增加了不必要的复杂性。Tkinter初学者似乎认为
lambda
是万灵丹。在我看来,它只应该在绝对必要的时候使用,因为它会使调试变得更加困难。@BryanOakley好吧,我发现使用
lambda
更容易,因为我可以将点连接起来,以便回调与
bind
trace\u add
命令
等选项一起使用。再说一次,我也是初学者。
callback(*args)
time.sleep(ms / 1000)