Can an object living in one thread emit a signal from another thread?
-
I have an object
a
created in the main thread, where its signals are connected to slots of other object,b
, that also lives in the main thread.Then I create an object
c
and move it to aworker
thread, where it will periodically access objecta
through a pointer, change its state and emit its signals.Here is the code:
(Note: some lines were purposely ignored to keep the example short)
class A : public QObject { Q_OBJECT friend class C; signals: void sigA(); private: quint8 _m1; quint8 _m2; }; class B : public QObject { Q_OBJECT public slots: void slotB(); }; class C : public QObject { Q_OBJECT public: C(A* a) : _a{a}, _timer{new QTimer{this}} { _timer->setInterval(5); connect(_timer, &QTimer::timeout, this, &C::doSomeWork); } public slots: void start() { _timer->start(); } private slots: void doSomeWork() { // update members of `a` emit _a->sigA(); // ... } private: A* _a; QTimer* _timer; }; int main(int argc, char* argv[]) { QApplication app(argc, argv); A* a {new A}; B* b {new B}; QObject::connect(a, &A::sigA, b, &B::slotB); QThread* worker {new QThread}; C* c {new C{a}}; c->moveToThread(worker); QObject::connect(worker, &QThread::started, c, &C::start); worker->start(); return app.exec(); }
I hope
a
signals, emitted from threadworker
, will triggerb
slots in main thread. And I hope I'll have no concurrency problems becausea
members are 8-bit sized.But
c
, that lives in threadworker
, will be posting events in the main thread event queue. I'm not using any synchronization primitive, so I'm afraid I may run into problems.May I use the signal/slot mechanism the way I'm using in the code example? Am I doing something wrong?
-
@rrd0 said in Can an object living in Thread A emit a signal from Thread B?:
Then I create an object C and move it to a worker thread W, where it will access object A through a pointer, change its state and emit its signals.
I think that is asking for trouble. Use the signal/slot mechanism exclusively. have C emit signals to slots in A. Don't access A members directly via its object pointer.
-
@rrd0
I principle, there should be no reason for problems.Connecting signals to signals is an established feature of Qt's Signal/Slot mechanism the fact that it in the end, will cross 3 different threads does't matter much.
As long, as you do not force a DirectConnection at least. Also keep in mind, that your original signal will pass through 3 different event loops, so the execution of the final slot may very well be delayed by significant amount of time.
-
@J.Hilk said in Can an object living in Thread A emit a signal from Thread B?:
@rrd0
I principle, there should be no reason for problems.Connecting signals to signals is an established feature of Qt's Signal/Slot mechanism the fact that it in the end, will cross 3 different threads does't matter much.
But what about concurrent issues? I updated my question and added a code example. Can you please have a look?
-
@KroMignon said in Can an object living in one thread emit a signal from another thread?:
@rrd0 I don't understand the meaning of this construct... why not move
a
in the worker thread?I'm actually trying to do that, but the problem I have is a little more complex than the example I wrote here. If a could keep
a
in the main thread it would be a lot easier for me. -
Hi,
Why exactly are you trying to emit a signal from an instance of class A in C ? That doesn't look clean and it's not the correct way to emit a signal. The purpose of a signal is to notify the outside that something has changed inside an object.