这是我在Mac上面对wxpython的奇怪问题。虽然这在Windows7上使用wxpython完全正常。我正试图在time.sleep()之前和之后更新wx.StaticText标签:
self.lblStatus = wx.StaticText(self, label="", pos=(180, 80))
self.lblStatus.SetLabel("Processing....")
time.sleep(10)
在上面的代码中,标签“Processing ...”在time.sleep()完成10秒后才会显示。即SetLabel在10秒后生效。
在Windows7 / wxpython上按预期工作,但在Mac上我遇到了问题。
答案 0 :(得分:1)
我从未见过time.sleep()不阻止Windows上的GUI。睡眠功能阻止wx的主循环,简单明了。正如JHolta所提到的,假设您使用线程安全方法,例如wx.CallAfter,wx.CallLater或wx.PostEvent,您可以将睡眠放入线程并从那里更新GUI。
但是,如果你只想偶尔任意重置一个标签,我认为使用wx.Timer()要简单得多。
答案 1 :(得分:0)
wxPython gui是一个循环,让代码的一部分进入睡眠状态而不会导致gui睡眠,需要多线程。
我会写一个调用线程函数的函数,现在这是一个肮脏的例子,但应该告诉你需要做什么:
import wx
from threading import Thread
import time
from wx.lib.pubsub import setuparg1
from wx.lib.pubsub import pub as Publisher
class Example(wx.Frame):
def __init__(self, *args, **kw):
super(Example, self).__init__(*args, **kw)
self.SetTitle('This is a threaded thing')
self.st1 = wx.StaticText(self, label='', pos=(30, 10))
self.SetSize((250, 180))
self.Centre()
self.Show(True)
self.Bind(wx.EVT_MOVE, self.OnMove)
# call updateUI when the thread returns something
Publisher.subscribe(self.updateUI, "update")
def OnMove(self, evt):
''' On frame movement call thread '''
x, y = evt.GetPosition()
C = SomeClass()
C.runthread(x, y)
def updateUI(self, evt):
''' Update label '''
data = evt.data
self.st1.SetLabel(data)
class SomeClass:
def runthread(self, x,y):
''' Start a new thread '''
t = Thread(target=self._runthread, args=(x,y,))
t.start()
def _runthread(self, x,y):
''' this is a threaded function '''
wx.CallAfter(Publisher.sendMessage, "update", "processing...")
time.sleep(3)
wx.CallAfter(Publisher.sendMessage, "update", "%d, %d" % (x, y))
def main():
ex = wx.App()
Example(None)
ex.MainLoop()
if __name__ == '__main__':
main()
现在,一旦您尝试移动“框架”/窗口,线程就会被初始化,并且将返回窗口的当前位置。
wx.CallAfter()是对GUI线程的线程安全调用,仅在GUI线程准备好接收时才发送数据。 Publisher-module简化了将数据发送到我们的线程的任务。
我建议您阅读:http://www.blog.pythonlibrary.org/2010/05/22/wxpython-and-threads/