私のプロジェクトで同様の問題が発生し、作業者の結果を表示してプログレスバーを更新するタイミングをメインGUIスレッドに伝えるために信号を使用しました。
PyQt reference guideにオブジェクトと信号を接続する例がいくつかあります。これらのすべてがPythonには適用されません(これを実現するにはしばらく時間がかかりました)。
ここでは、Pythonの信号をPython関数に接続するための例を示します。
QtCore.QObject.connect(a, QtCore.SIGNAL("PySig"), pyFunction)
a.emit(QtCore.SIGNAL("pySig"), "Hello", "World")
さらに、__pyqtSignals__ = ("PySig",)
をワーカークラスに追加することを忘れないでください。ここで
は私がやったことのストリップダウンバージョンです:
class MyGui(QtGui.QMainWindow):
def __init__(self, parent=None):
QtGui.QMainWindow.__init__(self, parent)
self.worker = None
def makeWorker(self):
#create new thread
self.worker = Worker(work_to_do)
#connect thread to GUI function
QtCore.QObject.connect(self.worker, QtCore.SIGNAL('progressUpdated'), self.updateWorkerProgress)
QtCore.QObject.connect(self.worker, QtCore.SIGNAL('resultsReady'), self.updateResults)
#start thread
self.worker.start()
def updateResults(self):
results = self.worker.results
#display results in the GUI
def updateWorkerProgress(self, msg)
progress = self.worker.progress
#update progress bar and display msg in status bar
class Worker(QtCore.QThread):
__pyqtSignals__ = ("resultsReady",
"progressUpdated")
def __init__(self, work_queue):
self.progress = 0
self.results = []
self.work_queue = work_queue
QtCore.QThread.__init__(self, None)
def run(self):
#do whatever work
num_work_items = len(self.work_queue)
for i, work_item in enumerate(self.work_queue):
new_progress = int((float(i)/num_work_items)*100)
#emit signal only if progress has changed
if self.progress != new_progress:
self.progress = new_progress
self.emit(QtCore.SIGNAL("progressUpdated"), 'Working...')
#process work item and update results
result = processWorkItem(work_item)
self.results.append(result)
self.emit(QtCore.SIGNAL("resultsReady"))