PDA

View Full Version : Thread shall emit signals with "complex" argument



Boron
17th June 2010, 14:21
Hello,

I want to pass some data from a sub thread to the main thread (GUI).
So I decided to emit a signal from the thread. The signal shall have an object containing the data as argument.
The main thread has a slot with the identical signature (means: expects an object as argument).


// The signal declarationin of the sub thread class:
signals:
void newLineConstructed( MyTableWidgetRow );

// The slot definition in the main thread class:
public slots:
void AddNewElementsLine( MyTableWidgetRow newRow );

// The "connect" statement used:
connect( m_updateElementsThread, SIGNAL(newLineConstructed(MyTableWidgetRow)),
this, SLOT(AddNewElementsLine(MyTableWidgetRow)) );
"MyTableWidgetRow" is a class.
m_updateElementsThread is an instance of a class derived from QThread that declares the above described signal.
"this" is the main thread. The connecting code is therefore in the constructor of the main thread.

The slot is never called when the signal is emited (and yes, it is emited in my code).
When I change the aguments type from MyTableWidgetRow to int, the slot is called, but not with my class as argument.

Any ideas what could be wrong?
What more information do you need th "analyze" what could be wrong?

chris_helloworld
17th June 2010, 14:34
You don't really want to be using SIGNALs and SLOTs between threads. What you need to do is within your thread create an event and post it to the GUI thread using,

MyCustomEvent *someevent = new MyCustomEvent(); // This should be a subclass of QCustomEvent and could contain your data.
QApplication::postEvent(targetWidget, someevent);

In the GUI thread, you need to implement,

void customEvent(QCustomEvent *event);

to recieve your event.

Have a read up on these.
Hope it helps,
Chris.

chris_helloworld
17th June 2010, 14:38
Have a read of "C++ GUI Programming with Qt 3" which can be downloaded from http://www.informit.com/store/product.aspx?isbn=0131240722 in pdf for free. Chaper 17 has a section on multithreading in Qt.

Chris

Boron
17th June 2010, 14:46
Why shouldn't I want signals and slots between thread?

You are talking of Qt 3, aren't you?
My Qt 4.6 docs say that signals and slots between threads work very well.

The QCustomEvent is part of the Qt 3 support library, according to the documentation.
I will give QEvent as base class for my event containing data a try.
But I still believe signals and slots should work.

chris_helloworld
17th June 2010, 14:54
I was just suggesting using the custom event mechanism because I know for certain it works properly. I've posted messages between threads this way in Qt4 applications.

I don't know whether signalling between threads is valid or otherwise.

chris_helloworld
17th June 2010, 14:57
Yes you can - http://doc.qt.nokia.com/4.6/threads-qobject.html#signals-and-slots-across-threads

numbat
17th June 2010, 15:06
Docs say:


To use the type T in queued signal and slot connections, qRegisterMetaType<T>() must be called before the first connection is established.

Note that connections across threads are queued by default.

Boron
17th June 2010, 15:53
Thanks a lot. numbats' post helped.

Declaring a new metatype right after the class definition in the header file:
Q_DECLARE_METATYPE(MyTableWidgetRow)
and a
qRegisterMetaType<MyTableWidgetRow>();right before the first usage in a connection did it.

borisbn
17th June 2010, 18:22
For the future: look in "output" window of your debugger, when you run your application. In your case it had a string:
"use qRegisterMetaType to send "MyTableWidgetRow" in signals/slots"
or something like this