To start the QBasicTimer and execute the timerEvent() within a thread.



  • Hi everyone,

    I am working on a multi-threaded GUI application, where I create three threads. These three threads will run continuously and update main thread (GUI thread). One of the thread will start the timer with 10msec as time interval. timerEvent() method will extract the image from camera (every 10ms) and send QImage to GUI thread for updating video widget (using signal and slot mechanism).

    Whenever the timer is timed out, main thread is executing timerEvent() method instead of other thread which started the timer. Because of this GUI is becoming less interactive and slow.

    Is it possible to make the thread (other than main thread) which starts timer to execute the timerEvent() method?

    Thank you in advance.


  • Lifetime Qt Champion

    Hi,

    You share the code of your thread, it will allow to understand how it is currently working.



  • main.cpp

    int main (int argc, char *argv[])
    {
          QApplication a (argc, argv);
          Viewer *w = new Viewer();
    
          w->show();
          a.exec ();
          return 0;
    }
    

    viewer.cpp

    Viewer::Viewer (QWidget *parent) :
      QMainWindow (parent),
      ui (new Ui::Viewer)
    {
          ....
          Thread1 = new work1(this)
          Thread2 = new work2(this)
          Thread3 = new video(this)
         
         connect(Thread3, SIGNAL(imageReady(QImage ), this, SLOT(setImage(QImage ));
          Thread3 -> start();
      }
    
    void setImage(QImage image)
    {
        //updates the image in Qlabel widget
    }
    
    

    video.cpp

    void video::run()
    {
        timer.start(10,this);   //timer is of QBasicTimer type
    }
    
    void video::timerEvent(QTimerEvent *)
    {
        //code for extarcting the image from camera
           ....
         emit imageReady(image);
    }
    

  • Qt Champions 2016

    @kole said in To start the QBasicTimer and execute the timerEvent() within a thread.:

    void video::run()
    {
        timer.start(10,this);   //timer is of QBasicTimer type
    }
    

    The thread object (Thread3) is living in the main thread and you pass it as receiver of the timer events. The main thread receiving the timer events is for all intents and purposes correct and expected behavior.


  • Lifetime Qt Champion

    Hi,

    To add to @kshegunov, you thread doesn't run its own event loop since you didn't started it.



  • @kshegunov , @SGaist Thank you for replying. I found this material helpful for understanding the event loop.

    But is it possible to make Thread3 process the timerEvent() method? I am thinking to start the thread without parent (in main.cpp along with viewer object) and then process its own events by calling exec() in run() method. Is it right way to do?

    main.cpp

    int main (int argc, char *argv[])
    {
          QApplication a (argc, argv);
          Viewer *w = new Viewer();
          video *Thread3 = new video();
          connect(Thread3, SIGNAL(imageReady(QImage ), w, SLOT(setImage(QImage ));
          Thread3 -> start();
    
          w->show();
          a.exec ();
          Thread3->quit();
          Thread3->wait();
          return 0;
    }
    

    video.cpp

    void video::run()
    {
        timer.start(10,this);   //timer is of QBasicTimer type
        exec();
    }
    
    void video::timerEvent(QTimerEvent *)
    {
        //code for extarcting the image from camera
           ....
         emit imageReady(image);
    }
    
    

  • Qt Champions 2016

    My advice is to not derive from QThread in this case, but use the worker object approach. See here.


Log in to reply
 

Looks like your connection to Qt Forum was lost, please wait while we try to reconnect.