15

I am calling from my thread the following:

QMetaObject::invokeMethod(pProcessor,
                          "doTask",
                          Qt::QueuedConnection,
                          Q_RETURN_ARG(quint32, taskId),
                          Q_ARG(quint64,   objId),
                          Q_ARG(quint8,    intId),
                          Q_ARG(QString,   name),
                          Q_ARG(QString,   comment)
                          );

but it just fails, no matter what I do. If I take out Q_RETURN_ARG(quint32, taskId), the method is invoked, but I need the taskId, which I cannot get. Any help is much appreciated.

Amy
  • 1,814
  • 2
  • 23
  • 38

3 Answers3

29

I'm assuming you want to call a method of an object from non owner thread & wants to get the return value. In order to do that use "Qt::BlockingQueuedConnection" as a connection type.

quint32 taskId; // Declare taskId.
qRegisterMetaType<quint32>("quint32");
QMetaObject::invokeMethod(pProcessor,
                      "doTask",
                      Qt::BlockingQueuedConnection,
                      Q_RETURN_ARG(quint32, taskId),
                      Q_ARG(quint64,   objId),
                      Q_ARG(quint8,    intId),
                      Q_ARG(QString,   name),
                      Q_ARG(QString,   comment)
                      );

Incase your method returns non standard return type you have to register your type before calling QMetaObject::invokeMethod(...). Refer http://qt-project.org/doc/qt-5.0/qtcore/qmetatype.html#qRegisterMetaType.

Arunprasad Rajkumar
  • 1,374
  • 1
  • 15
  • 31
1

The documentation for invokeMethod states that

The return value of the member function call is placed in ret. If the invocation is asynchronous, the return value cannot be evaluated.

I guess this happens because the code below this function call is continued to be executed, while your doTask method may not yet be called. Try using Qt::DirectConnection therefore.

Oleg Pyzhcov
  • 7,323
  • 1
  • 18
  • 30
0

from docs: If the invocation is asynchronous, the return value cannot be evaluated.

Then you should switch to Qt::DirectConnection, or change your design. QFuture, of course, could help.

I blogged here about a different solution, using C++ lambda facility to issue calls from background threads to GUI thread (see the text after 'My Solution' label).

CapelliC
  • 59,646
  • 5
  • 47
  • 90