界面卡死的一般解决方法
通过同步编程,设计Qt界面通常会由于某一步程序阻塞,导致原界面无法交互。
此时可以通过多线程编程等方式解决该问题。
可以参考文章:
pyqt5多线程,防止界面假死
Python解决PySide/PyQT等界面库的界面卡死问题
PyQt5 执行耗时操作导致界面卡死或未响应的解决办法
多线程编程界面卡死的可能原因
当采用多线程编程时,如果支线程访问了界面对象同样可能会导致界面卡死。
可以参考如下案例:
class Thread1(QThread):
Signal1 = Signal(str, str)
src: str
out: str
def __init__(self):
super().__init__()
def run(self):
self.Signal1.emit(self.src, self.out)
class Status:
thr1 = Thread1()
def __init__(self)
...
# 读取ui文件初始化界面对象
self.ui = QUiLoader().load(r'科研小助手_主窗口.ui')
# 自定义信号与槽函数连接
self.thr1.Signal1.connect(self.output)
...
def output(self, src, out)
if self.ui.CBox_OpenOrNot.isChecked() == True: # 此处支线程访问了界面对象
os.system(out + r"\out_" + os.path.basename(src))
def Finished(self, src, out):
QMessageBox.about(self.ui, '提示', '数据已处理并导出!')
# 如果“文件导出后打开”被勾选,则自动打开文件
self.thr1.src = src
self.thr1.out = out
self.thr1.start()
将支线程中访问界面对象的代码去除后,界面不再卡死,多线程正常运行。
修改后的代码如下:
class Thread1(QThread):
src: str
out: str
def __init__(self):
super().__init__()
def run(self): # 支线中移除界面对象的访问
os.system(self.out + r"\out_" + os.path.basename(self.src))
class Status:
thr1 = Thread1()
def Finished(self, src, out):
QMessageBox.about(self.ui, '提示', '数据已处理并导出!')
# 如果“文件导出后打开”被勾选,则自动打开文件
if self.ui.CBox_OpenOrNot.isChecked() == True:
self.thr1.src = src
self.thr1.out = out
self.thr1.start()