I have encountered quite freaky bug - QAction::trigger
caused blocking dialog to appear, which caused my server which called trigger
to go stuck (eg. n
You can separate that into a function QueuedInvoke
like this:
//overload for methods/slots
//the slot gets invoked in the thread where the QObject lives
template <typename Object, typename T>
void QueuedInvoke(Object* object, T (Object::* f)()){
QObject signalSource;
QObject::connect(&signalSource, &QObject::destroyed,
object, f, Qt::QueuedConnection);
}
//overload for functors
//the functor gets invoked in the thread where the contextObject lives
//or in the current thread if no contextObject is provided
template <typename Func>
void QueuedInvoke(Func&& f, QObject* contextObject = QAbstractEventDispatcher::instance()){
QObject signalSource;
QObject::connect(&signalSource, &QObject::destroyed,
contextObject, std::forward<Func>(f), Qt::QueuedConnection);
}
This will leverage the destroyed()
signal emitted from the temporary QObject
to post a queued event into the event loop. The slot/functor is actually invoked when the event loop processes that event.
So, Instead of the 3 lines you posted, You can use the above function like this:
QueuedInvoke(targetAction_.data(), &QAction::trigger);
My answer is based on this great answer about executing a functor in a given QThread
. You can refer to it for more details.