スレッドセーフな方法を使用して GUI を更新します。wxPython には、次の 3 つがあります。
- wx.CallAfter
- wx.CallLater
- wx.PostEvent
wxPython とスレッド化に関する情報については、wxPython wiki も参照してください。
このトピックに関するチュートリアルも書きました。
更新:これは、40 個のスレッドを作成し、40 個の構成ファイルを「処理」する簡単な例です。各スレッドが完了すると、表示が更新されます。しかし、私はあなたが話している問題を見ていません。
import random
import time
import wx
from threading import Thread
from wx.lib.pubsub import Publisher
########################################################################
class TestThread(Thread):
"""Test Worker Thread Class."""
#----------------------------------------------------------------------
def __init__(self, fname, sleepAmt):
"""Init Worker Thread Class."""
Thread.__init__(self)
self.fname = fname
self.sleepAmt = sleepAmt
self.start() # start the thread
#----------------------------------------------------------------------
def run(self):
"""Run Worker Thread."""
# This is the code executing in the new thread.
time.sleep(self.sleepAmt)
msg = "%s finished in %s seconds!" % (self.fname, self.sleepAmt)
wx.CallAfter(Publisher().sendMessage, "update", msg)
########################################################################
class MyForm(wx.Frame):
#----------------------------------------------------------------------
def __init__(self):
wx.Frame.__init__(self, None, wx.ID_ANY, "Tutorial")
panel = wx.Panel(self, wx.ID_ANY)
self.updateText = wx.TextCtrl(panel, style=wx.TE_MULTILINE)
self.btn = btn = wx.Button(panel, label="Start Thread")
btn.Bind(wx.EVT_BUTTON, self.onButton)
sizer = wx.BoxSizer(wx.VERTICAL)
sizer.Add(self.updateText, 1, wx.ALL|wx.EXPAND, 5)
sizer.Add(btn, 0, wx.ALL|wx.CENTER, 5)
panel.SetSizer(sizer)
# create a pubsub receiver
Publisher().subscribe(self.updateDisplay, "update")
#----------------------------------------------------------------------
def onButton(self, event):
"""
Runs the thread
"""
for i in range(40):
fname = "test%s.txt" % i
secs = random.choice(range(3, 15))
TestThread(fname, secs)
#----------------------------------------------------------------------
def updateDisplay(self, msg):
"""
Receives data from thread and updates the display
"""
data = msg.data + "\n"
self.updateText.WriteText(data)
#----------------------------------------------------------------------
# Run the program
if __name__ == "__main__":
app = wx.PySimpleApp()
frame = MyForm().Show()
app.MainLoop()
wxPython 2.8.12.1でPython 2.6を使用してWindows 7で実行しています