単一の QThread を使用して、異なる時間に 2 つ (またはそれ以上) の別々のメソッドを実行したい状況があります。たとえば、QThread をplay()
時々実行したいのですが、プレイが終わったら、QThread をこのメソッドから切断して、別の場所に接続できるようにしたいと考えています。本質的には、メイン プロセスと並行して実行したいものすべてのコンテナーとして QThread を機能させたいと考えています。
QThread を開始してすぐに切断すると、実行時に奇妙な動作が発生するという問題に遭遇しました。「競合状態」が何を意味するのかを発見する前 (またはマルチスレッドについて十分に理解する前)、切断される前にスレッドが完全に開始されていないのではないかという疑念をひそかに持っていました。これを克服するために、呼び出しと呼び出しの間に 5 ミリ秒のスリープを追加しましたstart()
。disconnect()
これは魅力的に機能します。それは魅力のように機能しますが、正しい方法ではありません。
への呼び出しを行わずに、1 つの QThread でこの機能を実装するにはどうすればよいsleep()
ですか?
問題のコード スニペット:
def play(self):
self.stateLabel.setText("Status: Playback initated ...")
self.myThread.started.connect(self.mouseRecorder.play)
self.myThread.start()
time.sleep(.005) #This is the line I'd like to eliminate
self.myThread.started.disconnect()
完全なスクリプト:
class MouseRecord(QtCore.QObject):
finished = QtCore.pyqtSignal()
def __init__(self):
super(MouseRecord, self).__init__()
self.isRecording = False
self.cursorPath = []
@QtCore.pyqtSlot()
def record(self):
self.isRecording = True
self.cursorPath = []
while(self.isRecording):
self.cursorPath.append(win32api.GetCursorPos())
time.sleep(.02)
self.finished.emit()
def stop(self):
self.isRecording = False
@QtCore.pyqtSlot()
def play(self):
for pos in self.cursorPath:
win32api.SetCursorPos(pos)
time.sleep(.02)
print "Playback complete!"
self.finished.emit()
class CursorCapture(QtGui.QWidget):
def __init__(self):
super(CursorCapture, self).__init__()
self.mouseRecorder = MouseRecord()
self.myThread = QtCore.QThread()
self.mouseRecorder.moveToThread(self.myThread)
self.mouseRecorder.finished.connect(self.myThread.quit)
self.initUI()
def initUI(self):
self.recordBtn = QtGui.QPushButton("Record")
self.stopBtn = QtGui.QPushButton("Stop")
self.playBtn = QtGui.QPushButton("Play")
self.recordBtn.clicked.connect(self.record)
self.stopBtn.clicked.connect(self.stop)
self.playBtn.clicked.connect(self.play)
self.stateLabel = QtGui.QLabel("Status: Stopped.")
#Bunch of other GUI initialization ...
def record(self):
self.stateLabel.setText("Status: Recording ...")
self.myThread.started.connect(self.mouseRecorder.record)
self.myThread.start()
time.sleep(.005)
self.myThread.started.disconnect()
def play(self):
self.stateLabel.setText("Status: Playback initated ...")
self.myThread.started.connect(self.mouseRecorder.play)
self.myThread.start()
time.sleep(.005)
self.myThread.started.disconnect()