QTJambi - QNetworkManager из потока не излучает сигналы - PullRequest
0 голосов
/ 14 апреля 2010

Я новичок в QT (Джамби). У меня очень простое приложение QTJambi (4.5.2). Я пытаюсь выяснить, почему это не будет работать (DoResponseReady никогда не вызывается) в потоке. Переключите статическую переменную между threadaded = true / false для воспроизведения.


import com.trolltech.qt.core.QByteArray;
import com.trolltech.qt.core.QUrl;
import com.trolltech.qt.gui.QApplication;
import com.trolltech.qt.gui.QPushButton;
import com.trolltech.qt.network.QNetworkAccessManager;
import com.trolltech.qt.network.QNetworkReply;
import com.trolltech.qt.network.QNetworkRequest;


public class Main {
 static boolean threaded = false;
 static Main main;

 public static void main(String[] args) {
  QApplication.initialize(args);
  main = new Main();  
  main.doit();
 }

 void DoResponseReady(QNetworkReply reply) {
  System.out.println("Response Ready");
 }

 void testnetwork_thread()
 {
  new Thread(new Runnable() {
   @Override
   public void run() {
    testnetwork();    
   }
  }).start();  
 }

 void testnetwork()
 {
  QNetworkAccessManager qnam = new QNetworkAccessManager();
  QNetworkRequest req = new QNetworkRequest(new QUrl("http://junkurl.neverwillwork.ok"));  
  QByteArray data = new QByteArray();
  qnam.finished.connect(main, "DoResponseReady(QNetworkReply)");
  qnam.post(req, data);    
 }

 void NetworkTest()
 {
  if (threaded)   
   testnetwork_thread();
  else
   testnetwork();
 }

 public void doit() {
        QPushButton quit = new QPushButton("Test");
        quit.clicked.connect(this, "NetworkTest()");
        quit.show();
        QApplication.exec();
 } 
}

1 Ответ

1 голос
/ 15 апреля 2010

Ваш поток не имеет цикла событий QT, поэтому ничего не произойдет.

Я работал не с QT в Java, а с c ++, поэтому не могу привести пример кода, но эта страница должна помочь:

http://qt.nokia.com/doc/qtjambi-4.5.2_01/com/trolltech/qt/qtjambi-threads.html

С этим сказанным ... попробуйте это:

void testnetwork_thread()
 {
  new Thread(new Runnable() {
   @Override
   public void run() {
    QEventLoop loop = new QEventLoop();
    testnetwork();    
    loop.exec();
   }
  }).start();  
 }

Обратите внимание, что это должно просто указать вам правильное направление, вам необходимо решить проблемы с синхронизацией и т. Д. Также обратите внимание на абзац, в котором говорится о владении QObject и потоках (сходство потоков).

В C ++ я создал класс, расширяющий QThread, и абстрактный интерфейс под названием «Рабочий». Производный класс QThread принимает объект Worker в качестве аргумента в конструкторе и изменяет сродство так, что он «принадлежит» этому потоку (см .: moveToThread ()). Затем в переопределенном методе run () он вызывает метод Worker :: init (), после чего запускает цикл обработки событий. Я запускаю все начальные вещи, которые необходимо обработать в методе init (), такие как таймеры или сетевые запросы.

...