前言
提示:图形界面启动、点击运行如果执行的代码需要长时间才能够执行完成,会导致图形界面卡死状态,这种情况下需要采用线程或者进程处理。
当前demo引用线程后台运行模块进行维护。
示例、更多功能请“PyQt快速开发框架”专栏,或下载demo测试
一、公共子界面基类
class WDTBaseQWidget(QWidget):
isBackRun= False
backRunData= {}
def toClose(self) -> bool:
if self.isBackRun:
pass #弹出窗口 提示后台线程运行...
def openBackRun(self):
self.isBackRun = True
def closeBackRun(self):
self.isBackRun = False
def getBackRunStatus(self):
return self.isBackRun
def backRun(self,func, inData,outData, callbackFunc):
# 创建线程、关联启动函数、回调函数、启动线程
self.thread = BackThread(func,inData,outData)
self.thread.signalStart.connect(self.openBackRun)
self.thread.signalCallBackup.connect(callbackFunc)
self.thread.start()
class BackThread(QtCore.QThread):
signalStart = QtCore.pyqtSignal(str)
signalCallBackup = QtCore.pyqtSignal(str)
def __init__(self,func,inData,backData,parent=None):
super(BackThread, self).__init__(parent)
#传入后台执行的函数、函数接受两个参数:inData(dict类型、None)、outData(dict类型)
self.func = func
self.inData = inData
self.backData = backData
def run(self):
self.signalStart.emit('start')
try:
self.func(self.inData,self.backData)
self.signalCallBackup.emit('runOk')
except:
self.signalCallBackup.emit('runError')
二、子页面使用线程、以及线程回调函数
子界面继承界面基类
class WDT**Widget(WDTBaseQWidget, Ui.Ui_Form):
def __init__(self,parent=None):
self.btn.clicked.connect(callThread)
def callThread(self):
def threadRun(in,out):
pass
# 线程逻辑
# 设置out返回信息
out['aaa'] =''
self.backRun(func=threadRun,inData=None, outData=self.backRunData, callbackFunc=self.callback)
else:
def callback(self):
pass# 把out值回写到界面上
三、子页面关闭检查后台线程
本项目用的子页面容器为QMdiSubWindow,重载QMdiSubWindow,重写closeEvent函数,在这个函数中检查
class WDTQMdiSubWindow(QMdiSubWindow):
def __init__(self,widgetName, parent=None):
super(WDTQMdiSubWindow, self).__init__(parent)
self.parentObj=parent
self.widgetName = widgetName
def closeEvent(self, closeEvent: QtGui.QCloseEvent) -> None:
wdt = self.widget()
if hasattr(wdt,'toClose') :
if not wdt.toClose():
closeEvent.ignore()
return
四、 主页面关闭检查后台线程
遍历sub容器中的widget的getBackRunStatus()返回值作为判断是否可以关闭主页面。
这部分逻辑也是在主页面的close事件中实现。