【问题标题】:Creating a new qwidget on exception using a thread使用线程在异常上创建新的 qwidget
【发布时间】:2015-09-18 19:44:26
【问题描述】:
from PyQt4 import QtGui
import threading
import sys

class Window(QtGui.QWidget):
    def __init__(self):
        super().__init__()
        self.button = QtGui.QPushButton('click', self)
        self.button.clicked.connect(self.mythread)

    def mythread(self):
        self.t=threading.Thread(target=self.action)
        self.t.start()

    def action(self):
        try:
            raise FileExistsError

        except FileExistsError:
            self.errorwindow = QtGui.QWidget()
            self.errorwindow.setGeometry(200, 200, 200, 100)
            self.errortext = QtGui.QLabel('error', self.errorwindow)
            self.errorwindow.show()
            print('1')

def main():
    program = QtGui.QApplication(sys.argv)
    a=Window()
    a.setGeometry(300, 300, 200, 100)
    a.show()
    sys.exit(program.exec_())

if __name__=='__main__':
    main()

正如在这里很容易看到的那样,我正在尝试制作一个“哎呀!发生错误”类型的窗口,该窗口将由线程在异常时创建。这是一个示例代码,展示了我是如何尝试这样做的,当你运行它时,你会看到一个窗口显示了一会儿然后消失了。使用我的实际程序,它甚至会导致崩溃。 print('1') 是为了查看解释器是否到达该行,是的,它会打印“1”。所以这并不是说它根本不运行异常块,它确实运行了,但它只是不会创建一个 qwidget。我做错了什么?

【问题讨论】:

    标签: python multithreading exception pyqt


    【解决方案1】:

    您不应该从任何线程执行 GUI 操作,除了创建的线程 QApplication。因此,您的异常处理程序必须在主线程中运行并通过信号槽机制调用:

    from PyQt4 import QtGui, QtCore
    from PyQt4.QtCore import pyqtSignal
    
    class MyThread(QtCore.QThread):
        somethingIsWrong = pyqtSignal(Exception)
    
        def run(self):
            try:
                raise FileExistsError
            except FileExistsError as e:
                self.somethingIsWrong.emit(e)
    
    class Window(QtGui.QWidget):
        def __init__(self):
            super(QtGui.QWidget, self).__init__()
            self.button = QtGui.QPushButton('click', self)
            self.button.clicked.connect(self.mythread)
    
        def mythread(self):
            self.t = MyThread()
            self.t.somethingIsWrong.connect(self.handleException)
            self.t.start()
    
        def handleException(self, exception):
            self.errorwindow = QtGui.QWidget()
            self.errorwindow.setGeometry(200, 200, 200, 100)
            self.errortext = QtGui.QLabel('error', self.errorwindow)
            self.errorwindow.show()
            print(exception.__class__)
    

    【讨论】:

    • 我需要学习pyqtSignalQThread 才能完全理解这个解决方案。尽管如此,我对此进行了测试,并且可以正常工作,谢谢。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2020-11-01
    • 1970-01-01
    • 2020-11-09
    • 2020-01-28
    相关资源
    最近更新 更多