سؤال

أنا أكتب DLL يتم استخدامه كمكون إضافي من خلال تطبيق آخر وأرغب في الاستفادة من قدرات QT.
لديّ جميع الفصول التي تم إعدادها وتجميعها وتشغيلها ، ولكن لا يتم تنبعث أي إشارات. لذلك يبدو كما لو أنه لا يوجد QeventLoop.

محاولة 1:
لقد قمت بتعديل الفصل الرئيسي الخاص بي إلى QTHread الفرعي بدلاً من QOBject ، وفي Run () قم بإنشاء QeventLoop ، وتوصيل جميع الإشارات/الفتحات ، و EXEC.
لكنه فشل في القول إنه لا يمكن أن يكون لديك QeventLoop بدون Qaplication.

محاولة 2:
لقد قمت بتعديل الفئة الرئيسية (التي لا تزال تصنيف QTHRAED) لإقامة إنشاء QCOREApplication بدلاً من ذلك ، وتوصيل جميع الإشارات/الفتحات ، ثم تنفيذ التطبيق.
يحذر من أنه لم يتم إنشاء Qapplication في الخيط الرئيسي () ، ولا يزال لا ينبعث منه إشارات.

لست متأكدًا حقًا مما يجب فعله هنا. من الواضح أنه لا يمكنني إنشاء QCoreApplication في التطبيق الذي سيستخدم المكون الإضافي الخاص بي ، ولا يمكنني إصدار إشارات بدون واحدة.

لقد قمت بتضمين تطبيق اختبار بسيط (مكتوب بشكل فظيع) والذي يجب أن يوضح مشكلتي:

سيكون موضع تقدير أي مساعدة!

main.cpp:

#include <iostream>
#include "ThreadThing.h"
using namespace std;
int main(int argc, char *argv[])
{
    cout << "Main: " << 1 << endl;
    ThreadThing thing1;
    cout << "Main: " << 2 << endl;
    thing1.testStart();
    cout << "Main: " << 3 << endl;
    thing1.testEnd();
    cout << "Main: " << 4 << endl;
    thing1.wait(-1);
    cout << "Main: " << 5 << endl;
    return 0;
}

Threadthing.H:

#ifndef THREADTHING_H
#define THREADTHING_H
#include <QThread>
class ThreadThing : public QThread
{
    Q_OBJECT
public:
    ThreadThing();
    virtual void run();
    void testStart();
    void testEnd();
public slots:
    void testSlot();
signals:
    void testSignal();
};
#endif//THREADTHING_H

Threadthing.cpp:

#include "ThreadThing.h"
#include <iostream>
#include <QCoreApplication>

using namespace std;

ThreadThing::ThreadThing()
{
    cout << "Constructor: " << 1 << endl;
    this->start();
    cout << "Constructor: " << 2 << endl;
}

void ThreadThing::run()
{
    cout << "Run: " << 1 << endl;
    int i = 0;
    cout << "Run: " << 2 << endl;
    QCoreApplication* t = new QCoreApplication(i, 0);
    cout << "Run: " << 3 << endl;
    connect(this, SIGNAL(testSignal()), this, SLOT(testSlot()), Qt::QueuedConnection);
    cout << "Run: " << 4 << endl;
    t->exec();
    cout << "Run: " << 5 << endl;
}

void ThreadThing::testStart()
{
    cout << "TestStart: " << 1 << endl;
    emit testSignal();
    cout << "TestStart: " << 2 << endl;
}

void ThreadThing::testEnd()
{
    cout << "TestEnd: " << 1 << endl;
    this->quit();
    cout << "TestEnd: " << 1 << endl;
}

void ThreadThing::testSlot()
{
    cout << "TEST WORKED" << endl;
}

انتاج:

Main: 1
Constructor: 1
Constructor: 2
Main: 2
TestStart: 1
TestStart: 2
Main: 3
TestEnd: 1
TestEnd: 1
Main: 4
Run: 1
Run: 2
WARNING: QApplication was not created in the main() thread.
Run: 3
Run: 4
هل كانت مفيدة؟

المحلول

أنت لديك لإنشاء qcoreapplication أو qapplication وأنت لديك للقيام بذلك في الموضوع الرئيسي.

هذا لا يعني أنه لا يمكنك وضع الرمز لذلك في البرنامج المساعد الخاص بك ... ما لم يكن التطبيق دائمًا تشغيل كل مكون إضافي في موضوعه الخاص.

إذا كان التطبيق هو القيام بذلك ، ثم يمكنك محاولة التثبيت في أي حلقة حدث أصلية يستخدمها التطبيق ، وترتيبها للاتصال ببعض الوظائف في البرنامج المساعد في الخيط الرئيسي.

نصائح أخرى

لقد نجحت في إنشاء QCoreApplication وتشغيله على موضوع خلفية. هذا هو ليس تطبيق قياسي ولكن يمكن أن يعمل من أجل وظيفة الإشارة/الفتحة البسيطة. لقد فعلت ذلك لتطبيق iOS الأصلي مع قاعدة كود QT Legacy كبيرة.

//I really don't do anything but run on a background thread
class MyQtAppForBackgroundThread : public QCoreApplication 
{
    Q_OBJECT
    ...
}

 //iOS specific code here...
 dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_LOW, 0), ^(void){
        // This spawns a QCoreApplication on a background thread in an attempt to create something that can
        // queue signals across threads
        qtApp = new MyQtAppForBackgroundThread(smArgc, smArgv);
        qtApp->exec();

    });

الإشارات التي تم إطلاقها على نفس الخيط حيث تم توصيلها سيتم القبض عليها. للقبض على إشارات على مؤشرات ترابط مختلفة ، يجب عليك إنشاء واستطلاع QeventLoop على الخيط حيث تم إنشاء الإشارات.

//Fire me periodically on the thread the signals and slots were connected
QEventLoop loop;
loop.processEvents( QEventLoop::ExcludeUserInputEvents, 500 );
مرخصة بموجب: CC-BY-SA مع الإسناد
لا تنتمي إلى StackOverflow
scroll top