Dennis Kellly
|
Re: Calling an event function in a QT thread from a QNX thread.
|
Dennis Kellly
05/23/2012 7:59 AM
post93255
|
Re: Calling an event function in a QT thread from a QNX thread.
Magnus-
This example has a thread which "signals" back to the UI...
http://community.qnx.com/sf/discussion/do/listPosts/projects.qt/discussion.general.topc20365
Note that the thread is created as a Qt object (not pthread_create) but thread execution is the same. Here the thread
is waiting to be notified by pps, but it could be waiting for a CAN message.
If you don't want your CAN logic in a Qt thread, you could wait for a pulse in the Qt thread, and send the pulse from a
standard (non-Qt) C program with CAN knowledge. This way, you can easier debug the more complex non-Qt portion, and
your UI remains simple.
|
|
|
Dennis Kellly
|
Re: Calling an event function in a QT thread from a QNX thread.
|
Dennis Kellly
05/23/2012 10:56 AM
post93261
|
Re: Calling an event function in a QT thread from a QNX thread.
Yes, I realize you are not using QML... why, I don't know since that is the current Qt-preferred method.
Still, from what I have read, signals and slots existed prior to QML. So you need to find such an example. Some of the
signal/slot packaging of qTstat will likely still apply.
|
|
|
Rafael Roquetto(deleted)
|
Re: Calling an event function in a QT thread from a QNX thread.
|
Rafael Roquetto(deleted)
05/24/2012 8:57 AM
post93286
|
Re: Calling an event function in a QT thread from a QNX thread.
Hello Magnus,
> I have an issue that I don’t know how to call event/message functions inside
> the “QT thread” from a QNX thread in my QNX application.
>
> In main I create a thread for receiving can messages. When I have received a
> can message I would like to send an event/message/signal to my “myqtclass”
> event function or another function inside the object. I end up in the function
> myqtcalss::event but I still execute in the “qnx function thread” not the
> “QT thread”. Because of this I receive an error message from QT. I would
> like to send an event/message/signal so the “QT thread” execute it. Do you
> have any suggestion how to do this?
>
This is because QCoreApplication::sendEvent() will call QObject::event()
directly, as if it were a simple function call, and therefore it will run on the
caller's thread context (i.e. the QNX thread in your program). Qt has a rule
that events can obly be sent to objects in the current thread, i.e. sending
events directly accross threads, using QCoreApplication::sendEvent() is
forbidden.
The easiest way to solve your problem is to use QCoreApplication::postEvent()
(or QApplication, in your case). Unlike QCoreApplication::sendEvent(),
QCoreApplication::postEvent() will push the event to the receiver thread's event
equeue, and the event will be processed only when the control returns to the
receiver's thread main loop. This ensures that the event will be processed on
the context of the receiver's thread, which is the behavior you are expecting.
Please note that the event must be allocated on the heap, since the post event
queue will take ownership of the event and delete it once it has been posted.
In practice, your code should look like:
void QNX_thread_function( void *pvParameters )
{
// Code that executes when a can message is received
QEvent *event = new QEvent(static_cast<QEvent::Type>(QEvent::UserType + 1));
QApplication::postEvent(myqtclass, event);
}
However, if all you would like to do is signalizing your Qt class that a CAN
message has arrived, you can instead take advantage of the Qt MetaObject system
instead of reimplementing QObject::event().
class myqtclass : public QObject
{
Q_OBJECT
public:
/* ... */
Q_INVOKABLE void canMessageArrived();
};
and then:
void QNX_thread_function( void *pvParameters )
{
// Code that executs when a can message is received
QMetaObject::invokeMethod(myqtclass, "canMessageArrived", Qt::QueuedConnection);
}
In a nutshell, the Q_INVOKABLE macro tells the Qt MetaObject system that canMessageArrived can be invoked using
QMetaObject::invokeMethod - it is a bit more complicated than that under the hood, but let's leave it like this for the
sake of simplicity. The caveat then is passing Qt::QueuedConnection to QMetaObject::invokeMethod. This means that,
instead of invoking the method directly (akin to QApplication::sendEvent()), the method is invoked when control returns
to the event loop of the receiver's thread and is executed in the context of the receiver's thread (akin to QApplication
::postEvent()). You can also use Qt::BlockingQueuedConnection - the difference is that, while QMetaObject::
invokeMethod() will return immediately with the former, when using the latter it will only return after the method has
been executed.
I hope that helps.
Cheers,
Rafael
---
Rafael Roquetto | rafael.roquetto@kdab.com | Software Engineer
Klarälvdalens Datakonsult AB, a KDAB Group company
Tel. Sweden (HQ) +46-563-540090, USA +1-866-777-KDAB(5322)
KDAB - Qt Experts - Platform-independent software solutions
|
|
|