代码之家  ›  专栏  ›  技术社区  ›  Dirk Groeneveld

QThread工作类发出的信号不会到达

  •  0
  • Dirk Groeneveld  · 技术社区  · 4 年前

    class MyCustomObject {
    };
    
    class DeviceConnection : public QObject {
        Q_OBJECT
    
        public:
            explicit DeviceConnection(QObject* const parent = nullptr);
    
        signals:
            void readFinished(MyCustomObject result);
    
        public slots:
            void readFromDevice();
    };
    
    DeviceConnection::readFromDevice() {
        /* ... */
        emit readFinished(MyCustomObject());
    }
    
    void MainWindow::on_actionRead_triggered() {
        QThread* const thread = new QThread(this);
        DeviceConnection* const connection = new DeviceConnection();
        connection->moveToThread(thread);
        thread->start();
    
        connect(connection, &DeviceConnection::readFinished, this, [=](MyCustomObject data) {
            /* This never runs. */
            connection->deleteLater();
            thread->quit();
        });
    
        QTimer::singleShot(0, connection, &DeviceConnection::readFromDevice);
    }
    

    开始读起来还不错。我可以在调试器中看到我正在到达 emit 线,我就要到了。但是我也可以在调试器和代码的行为中看到 readFinished

    Edit:当我不使用额外的线程时,这个代码运行得很好,但是当然它会在运行时阻塞主线程 readFromDevice()

    0 回复  |  直到 4 年前
        1
  •  1
  •   Dirk Groeneveld    4 年前

    我想出来了。不幸的是,当我第一次问这个问题时,我把重要的部分简化了,但我只是把它编辑了回来。

    问题是 MyCustomObject 无法在Qt消息队列中排队。为此,需要运行以下命令:

    qRegisterMetaType<MyCustomObject>("MyCustomObject");
    

    // ideally just after the definition for MyCustomObject
    Q_DECLARE_METATYPE(MyCustomObject);
    
    // any time before you want to enqueue one of these objects
    qRegisterMetaType<MyCustomObject>();
    
        2
  •  0
  •   Mosi    4 年前