PDA

View Full Version : Qt Jambi: Thread and signal slot problem



newb_developer
18th December 2012, 16:51
Hello,
I develop application in Java using Qt Jambi 4.7.1.

I created the following GUI class (it seeems to be ok):


package org.margor.echoclient;

import com.trolltech.qt.gui.*;

public class MainWindow extends QMainWindow {
/*
* Objects / controls.
*/
Ui_MainWindow mainw = new Ui_MainWindow();
Client client = new Client();

/*
* Methods.
*/
public MainWindow() {
mainw.setupUi(this);
setWindowIcon(new QIcon("classpath:com/trolltech/images/qt-logo.png"));
set_signals_slots();
send_address.emit("127.0.0.1");
send_port.emit(8189);
client.c_connect();

}
protected void set_signals_slots()
{
// GUI settings
mainw.cleanButton.clicked.connect(this, "clean_server_message_box()");
// client settings
client.info.connect(this, "clean_server_message_box()");
client.error.connect(this, "get_error(String, String)");
send_address.connect(client, "recv_address(String)");
send_port.connect(client, "recv_port(Integer)");
// send message from client
mainw.sendButton.clicked.connect(this, "send_client_message()");
send_message.connect(client, "send_input_string(String)");
}
/*
* Signals.
*/
// send IP address
public Signal1<String> send_address = new Signal1<String>();
// send server port
public Signal1<Integer> send_port = new Signal1<Integer>();
// send message
public Signal1<String> send_message = new Signal1<String>();

/*
* Slots.
*/
protected void helloWorld() {
QMessageBox.information(this, tr("Hello"), tr("Hello World"));
}
protected void get_information(String title, String message) {
QMessageBox.information(this, tr(title), tr(message));
}
protected void get_error(String title, String message) {
QMessageBox.critical(this, tr(title), tr(message));
}
// clean chat box
protected void clean_server_message_box() {
mainw.display_textEdit.clear();
}
// send client message
protected void send_client_message() {
send_message.emit(mainw.message_lineEdit.text());
}
}


I have problem in my model class. I am unable to send signal to my GUI class.


package JambiTest;

import java.util.Observable;
import java.util.Observer;

import com.trolltech.qt.core.QObject;

public class Client extends QObject implements Observer {
/*
* Data.
*/
protected int number;
protected Thread t = null;
protected CounterThread counter = null;

/*
* Signals.
*/
Signal1<Integer> send_number = new Signal1<Integer>();
Signal2<String, String> send_info = new Signal2<String, String>();

Client() {
counter = new CounterThread();
counter.addObserver(this);
number = 0;
}

/*
* Slots.
*/
// runs counter thread
public void start_counter() {
t = new Thread(counter);
send_info.emit("Info", "Thread started");
t.start();
}

public class CounterThread extends Observable implements Runnable {
@Override
public void run() {
while(true) {
try {
Thread.sleep(10);
} catch (InterruptedException e) {
e.printStackTrace();
}
++number;
number %= 10;
setChanged();
notifyObservers(number);
}
}
}

@Override
public void update(Observable arg0, Object arg1)
{
if(arg1 instanceof Integer)
send_number.emit((Integer) arg1);
}
}


I get the exception:


Exception in thread "Thread-2" QObject used from outside its own thread, object=JambiTest::Client(0x5549a80) , objectThread=Thread[main,5,main], currentThread=Thread[Thread-2,5,main]
at com.trolltech.qt.GeneratorUtilities.threadCheck(Un known Source)
at com.trolltech.qt.core.QObject.signalsBlocked(Unkno wn Source)
at com.trolltech.qt.internal.QSignalEmitterInternal$A bstractSignalInternal.emit_helper(Unknown Source)
at com.trolltech.qt.QSignalEmitter$Signal1.emit(Unkno wn Source)
at JambiTest.Client.update(Client.java:59)
at java.util.Observable.notifyObservers(Unknown Source)
at JambiTest.Client$CounterThread.run(Client.java:50)
at java.lang.Thread.run(Unknown Source)


The problem is caused because update method is in other thread than GUI (the same thread as run), which is quite strange for me?

I tried to use only signal class, and rewritten model class:


package JambiTest;

import com.trolltech.qt.core.QObject;

public class Client extends QObject {
/*
* Data.
*/
protected int number;
protected Thread t = null;
protected CounterThread counter = null;

/*
* Signals.
*/
Signal1<Integer> send_number = new Signal1<Integer>();
Signal2<String, String> send_info = new Signal2<String, String>();

Client() {
counter = new CounterThread();
number = 0;
counter.send_thread_number.connect(this, "update(Integer)");
}

/*
* Slots.
*/
// runs counter thread
public void start_counter() {
t = new Thread(counter);
send_info.emit("Info", "Thread started");
t.start();
}

public class CounterThread extends QObject implements Runnable {
public Signal1<Integer> send_thread_number = new Signal1<Integer>();
@Override
public void run() {
while(true) {
try {
Thread.sleep(10);
} catch (InterruptedException e) {
e.printStackTrace();
}
++number;
number %= 10;
send_thread_number.emit(number);
}
}
}

public void update(Integer i)
{
send_number.emit(i);
}
}


However, I get exception:


Exception in thread "Thread-2" QObject used from outside its own thread, object=JambiTest::Client$CounterThread(0x56f9b20) , objectThread=Thread[main,5,main], currentThread=Thread[Thread-2,5,main]
at com.trolltech.qt.GeneratorUtilities.threadCheck(Un known Source)
at com.trolltech.qt.core.QObject.signalsBlocked(Unkno wn Source)
at com.trolltech.qt.internal.QSignalEmitterInternal$A bstractSignalInternal.emit_helper(Unknown Source)
at com.trolltech.qt.QSignalEmitter$Signal1.emit(Unkno wn Source)
at JambiTest.Client$CounterThread.run(Client.java:47)
at java.lang.Thread.run(Unknown Source)



Thanks for your attention,
Regards,

newb_developer
18th December 2012, 23:06
Please delete thread, put wrong code at first listing. Sorry!