我有一个GUI应用程序,它有一个启动按钮,该按钮指向一个最终将启动qprocess的函数。这个qprocess在后台调用一个长时间运行的控制台程序,该程序输出一堆stdout。标准输出由信号和插槽捕获。当该qprocess在stdout上有新的内容时,它将通过该stdout行发出一个信号,并由GUI开槽并显示在文本浏览器小部件中。如果我只让分离的qprocess运行并自行退出,那就很好了。GUI保持响应,一切都很好。GUI上有一个停止按钮来停止它,如果需要,能够停止它是很重要的。我为停止按钮创建了一个插槽,它会终止Qprocess并将所有内容重置为1。如果我在qprocess被调用之前按下停止按钮,一切都会正常工作,GUI保持响应。
但是,如果我试图用停止按钮中断qprocess,它会向qprocess发送一个.kill()命令,如果我尝试单击太多的东西,它会严重减慢GUI的运行速度。
以下是qprocess的生成方式:
def launch_cmd(self): '''Look for the COM port number the uut/DUT is registered as.''' self.cli_process = QProcess() self.cli_process.readyReadStandardOutput.connect(self.handle_stdout) # self.cli_process.readyReadStandardError.connect(self.handle_stderr) self.cli_process.start("myprog.exe", ["run", "all", "--debug"])
这里是stop slot函数,它实际上在一个线程中。我还没有尝试在mainWindow代码中创建this.kill(),它在Thread类中。cliprocess由于某种原因被传递到线程类中。
def stop(self): '''Stops the thread and does some housekeeping''' print("Stop detected") self.abort_flag = True self.is_running = False try: self.cli_process.kill() #if self.cli_process.processId(): #os.kill(self.cli_process.processId(), signal.SIGINT) except: print(f"[{datetime.now()}]: Warning, cli process not killed...continuing headless.") else: pass
当qprocess被终止后按下停止按钮时,GUI仍然可以工作,这真的很慢。文本字段响应缓慢。即使是拖动GUI窗口,也会出现起伏和跳跃。如果我在这种情况下在GUI中做了太多的事情,它会使GUI崩溃;比如,如果我将鼠标放在菜单栏上,快速移动鼠标以拖动主窗口,然后单击某个文本字段,它将冻结整个GUI并使其变灰,就像它试图缓冲我的所有功能一样,它可能会执行最后一个操作,也可能只是崩溃并关闭。
我把范围缩小到被杀死的进程。
我编写了一个辅助程序来监控pid,并确认当我按下停止按钮时,进程确实被终止,GUI是唯一运行的pid。因此,一个被终止的qprocess会导致GUI阻塞。不知道如何克服这个问题。思想?