Results 1 to 6 of 6

Thread: GUI Updates from separate Thread

  1. #1
    Join Date
    Jun 2012
    Posts
    13
    Thanks
    1
    Qt products
    Qt4
    Platforms
    Unix/X11 Windows

    Default GUI Updates from separate Thread

    I have a GUI containing a QTableWidget whose rows contain strings. The strings are processed in a separate thread in order to keep the GUI free for providing status by selecting each row as the string in that row is being processed and also to abort the overall processing if desired. My problem is that the GUI's QTableWidget does not show/update row selection for each row until after all the rows have already been processed even though the GUI slot that performs the selectRow is called correctly at the right time. It looks as if the QTableWidget selectRow is queued for later execution after the thread is finished.

    I did see one comment which suggested that the problem might be the thread wait executed after the thread start, but without the wait the program crashes with the error that the thread was terminated before processing was complete. What do I need to do to get the GUI to update the row selection on the QTableWidget when I execute the emit from the separate thread?

    Qt Code:
    1. mainwindow.cpp
    2. ***************************************
    3. #include "mainwindow.h"
    4. #include "ui_mainwindow.h"
    5. #include <stdexcept>
    6.  
    7. MainWindow::MainWindow(QWidget *parent) :
    8. QMainWindow(parent),
    9. ui(new Ui::MainWindow)
    10. {
    11. ui->setupUi(this);
    12. }
    13.  
    14. MainWindow::~MainWindow()
    15. {
    16. delete ui;
    17. }
    18.  
    19. void MainWindow::on_btnRun_clicked()
    20. {
    21. TestThread testThread(this);
    22. testThread.TestCmds(_testCmds);
    23. testThread.SetStartIndex(0);
    24. connect(&testThread, SIGNAL(stepChanged(int)), this, SLOT(testThreadStepChanged(int)));
    25. connect(&testThread, SIGNAL(finished()), this, SLOT(testThreadFinished()));
    26. testThread.start();
    27. testThread.wait();
    28. }
    29.  
    30. void MainWindow::testThreadStepChanged(int step)
    31. {
    32. // tblCmds is a QTableWidget with rows of strings
    33. ui->tblCmds->selectRow(step);
    34. ui->tblCmds->repaint();
    35. }
    36.  
    37. void MainWindow::testThreadFinished()
    38. {
    39. qDebug("Received Thread Finished Signal");
    40. }
    41.  
    42. mainwindow.h
    43. ***************************************
    44. #ifndef MAINWINDOW_H
    45. #define MAINWINDOW_H
    46.  
    47. #include <QMainWindow>
    48. #include "qthread.h"
    49. #include "qtablewidget.h"
    50. #include "testthread.h"
    51.  
    52. namespace Ui {
    53. class MainWindow;
    54. }
    55.  
    56. class MainWindow : public QMainWindow
    57. {
    58. Q_OBJECT
    59.  
    60. public:
    61. explicit MainWindow(QWidget *parent = 0);
    62. ~MainWindow();
    63.  
    64. private slots:
    65. void on_btnRun_clicked();
    66. void testThreadStepChanged(int step);
    67. void testThreadFinished();
    68.  
    69. private:
    70. Ui::MainWindow *ui;
    71. QStringList _testCmds;
    72. };
    73.  
    74. #endif // MAINWINDOW_H
    75.  
    76.  
    77. testthread.cpp
    78. ***************************************
    79. #include "testthread.h"
    80.  
    81. TestThread::TestThread(QObject *parent) :
    82. QThread(parent)
    83. {
    84. }
    85.  
    86. void TestThread::run()
    87. {
    88. for(int si=_startIndex; si < _testCmds.count(); si++)
    89. {
    90. if(_stopFlag) return;
    91. emit stepChanged(si);
    92. }
    93. }
    94.  
    95. testthread.h
    96. ***************************************
    97. #ifndef TESTTHREAD_H
    98. #define TESTTHREAD_H
    99.  
    100. #include <QThread>
    101.  
    102. class TestThread : public QThread
    103. {
    104. Q_OBJECT
    105. public:
    106. explicit TestThread(QObject *parent = 0);
    107.  
    108. void SetStartIndex(int startIndex);
    109. void TestCmds(QStringList testCmds);
    110. void Stop();
    111.  
    112. signals:
    113. void stepChanged(int step);
    114.  
    115. public slots:
    116.  
    117. private:
    118. void run();
    119.  
    120. QStringList _testCmds;
    121. int _startIndex;
    122. bool _stopFlag;
    123. };
    124.  
    125. #endif // TESTTHREAD_H
    To copy to clipboard, switch view to plain text mode 

  2. #2
    Join Date
    Jan 2006
    Location
    Warsaw, Poland
    Posts
    33,358
    Thanks
    3
    Thanked 5,015 Times in 4,792 Posts
    Qt products
    Qt3 Qt4 Qt5 Qt/Embedded
    Platforms
    Unix/X11 Windows Android Maemo/MeeGo
    Wiki edits
    10

    Default Re: GUI Updates from separate Thread

    Creating an object on a stack will destroy that object when the scope where the object was created ends. Create the object on the heap instead.
    Your biological and technological distinctiveness will be added to our own. Resistance is futile.

    Please ask Qt related questions on the forum and not using private messages or visitor messages.


  3. #3
    Join Date
    Mar 2008
    Location
    Kraków, Poland
    Posts
    1,533
    Thanked 282 Times in 277 Posts
    Qt products
    Qt4
    Platforms
    Unix/X11 Windows

    Default Re: GUI Updates from separate Thread

    1. You ARE blocking GUI thread beacuse second thread is created in slot on_btnRun_clicked() and You are waiting in this slot for finishing this thread.
    2. In worker thread You are NOT starting event loop. So signals from worker thread are NOT provided to main thread.

  4. #4
    Join Date
    Jan 2006
    Location
    Warsaw, Poland
    Posts
    33,358
    Thanks
    3
    Thanked 5,015 Times in 4,792 Posts
    Qt products
    Qt3 Qt4 Qt5 Qt/Embedded
    Platforms
    Unix/X11 Windows Android Maemo/MeeGo
    Wiki edits
    10

    Default Re: GUI Updates from separate Thread

    Quote Originally Posted by Lesiok View Post
    2. In worker thread You are NOT starting event loop. So signals from worker thread are NOT provided to main thread.
    This is actually false. Signals don't need an event loop, only slots do.
    Your biological and technological distinctiveness will be added to our own. Resistance is futile.

    Please ask Qt related questions on the forum and not using private messages or visitor messages.


  5. #5
    Join Date
    Mar 2008
    Location
    Kraków, Poland
    Posts
    1,533
    Thanked 282 Times in 277 Posts
    Qt products
    Qt4
    Platforms
    Unix/X11 Windows

    Default Re: GUI Updates from separate Thread

    Quote Originally Posted by wysota View Post
    This is actually false. Signals don't need an event loop, only slots do.
    My mistake. Thank you for correcting Wysota.

  6. #6
    Join Date
    Jun 2012
    Posts
    13
    Thanks
    1
    Qt products
    Qt4
    Platforms
    Unix/X11 Windows

    Default Re: GUI Updates from separate Thread

    Auggh, that should have been obvious to me now that you point it out. Made the necessary changes and it now works like a charm. Thanks.

Similar Threads

  1. Replies: 5
    Last Post: 17th July 2011, 06:27
  2. Thread updates progress bar
    By GianMarco in forum Qt Programming
    Replies: 7
    Last Post: 12th October 2009, 14:29
  3. update widget from separate thread
    By method in forum Qt Programming
    Replies: 5
    Last Post: 10th July 2009, 15:33
  4. new QWidget in separate thread
    By magland in forum Qt Programming
    Replies: 15
    Last Post: 7th February 2008, 13:32
  5. handling paintGL in a separate thread
    By al101 in forum Qt Programming
    Replies: 1
    Last Post: 15th May 2007, 18:04

Bookmarks

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts
  •  
Digia, Qt and their respective logos are trademarks of Digia Plc in Finland and/or other countries worldwide.