Skip to content
  • Categories
  • Recent
  • Tags
  • Popular
  • Users
  • Groups
  • Search
  • Get Qt
  • Unsolved
Collapse
Brand Logo
  1. Home
  2. Qt Development
  3. General and Desktop
  4. QThread example to run a function in MainWindow on button click
Qt 6.12 LTS is out! See what's new in the release blog

QThread example to run a function in MainWindow on button click

Scheduled Pinned Locked Moved Unsolved General and Desktop
13 Posts 5 Posters 7.2k Views 1 Watching
  • Oldest to Newest
  • Newest to Oldest
  • Most Votes
Reply
  • Reply as topic
Log in to reply
This topic has been deleted. Only users with topic management privileges can see it.
  • J Offline
    J Offline
    JSher
    wrote on last edited by
    #3

    @JonB

    So I created a big elaborate function that runs based off user input from the ui and in order to change it to a thread I have to write it all in the run() function and pass signals back and forth to get the information from the ui?

    Hmm this does not make sense to me.

    Is it possible to have the thread emit a signal to then run the function I have created?

    --James

    jsulmJ 1 Reply Last reply
    0
    • J JSher

      @JonB

      So I created a big elaborate function that runs based off user input from the ui and in order to change it to a thread I have to write it all in the run() function and pass signals back and forth to get the information from the ui?

      Hmm this does not make sense to me.

      Is it possible to have the thread emit a signal to then run the function I have created?

      --James

      jsulmJ Offline
      jsulmJ Offline
      jsulm
      Lifetime Qt Champion
      wrote on last edited by
      #4

      @JSher Do you have to pass user input all the time to your function?
      Usually you would do it once when starting the function. So, I don't see how it does not make sense. To my knowledge most GUI frameworks do not allow changes to GUI from other threads than main (GUI) thread, not only Qt.

      Yes, threads can emit signals too.

      https://forum.qt.io/topic/113070/qt-code-of-conduct

      1 Reply Last reply
      3
      • J Offline
        J Offline
        JSher
        wrote on last edited by
        #5

        No I do not pass user input other than the initial start but I get paramaters from the ui such as ui->comboBox->currentText() all through the function

        --James

        1 Reply Last reply
        0
        • J Offline
          J Offline
          JSher
          wrote on last edited by
          #6

          For instance in Java using Swing I just create a class in my MainGUI class like this:

          class MASummaryTask extends SwingWorker<Void, Void> {
          }
          

          It has full access to the GUI members etc. I just start it from the push button method like this:

          summaryTask = new MASummaryTask();
          summaryTask.addPropertyChangeListener(this);
          summaryTask.execute();
          

          So when I needed to go multithreaded I just run that function from the doInBackground() method of the thread class
          --James

          jsulmJ 1 Reply Last reply
          0
          • J JSher

            For instance in Java using Swing I just create a class in my MainGUI class like this:

            class MASummaryTask extends SwingWorker<Void, Void> {
            }
            

            It has full access to the GUI members etc. I just start it from the push button method like this:

            summaryTask = new MASummaryTask();
            summaryTask.addPropertyChangeListener(this);
            summaryTask.execute();
            

            So when I needed to go multithreaded I just run that function from the doInBackground() method of the thread class
            --James

            jsulmJ Offline
            jsulmJ Offline
            jsulm
            Lifetime Qt Champion
            wrote on last edited by
            #7

            @JSher I still don't see the problem. Before starting this function collect all needed information from the UI elements and pass it as parameters to your function.

            https://forum.qt.io/topic/113070/qt-code-of-conduct

            1 Reply Last reply
            0
            • J Offline
              J Offline
              JSher
              wrote on last edited by
              #8

              I was hoping to avoid this as it is a great deal of clean up as there is 30+ paramaters mostly pulled from the UI. Was hoping to just be able to run that function in a thread:)

              Thanks,
              --James

              1 Reply Last reply
              0
              • J Offline
                J Offline
                JSher
                wrote on last edited by
                #9

                Ok so I can create threads and emit information back to the main GUI that can then use that information to update a vector or something of that nature to keep track of the work the threads are doing.

                What I cannot figure out is how to pass the information to the worker thread IE

                mThread = new MyThread(this);
                connect(mThread, SIGNAL(runThread()),this,SLOT(onRunThread()));
                mThread->start();
                

                In this code if I put paramaters for runThread(thread class) and same paramaters in onRunThread(gui class), the paramaters will be available to the main gui.

                So how do I pass paramaters to the thread worker? Here is the thread header:

                #ifndef MYTHREAD_H
                #define MYTHREAD_H
                
                #include <QThread>
                
                class MyThread : public QThread
                {
                    Q_OBJECT
                public:
                    explicit MyThread(QObject *parent = 0);
                    void run();
                signals:
                    void runThread();
                
                public slots:
                
                };
                
                #endif // MYTHREAD_H
                

                Thanks,
                --James

                1 Reply Last reply
                0
                • VRoninV Offline
                  VRoninV Offline
                  VRonin
                  wrote on last edited by VRonin
                  #10
                  1. What was said above about ui in a secondary thread is correct and it's a limitation of some OSs, not of Qt. Having said that, however, getters like ui->comboBox->currentText() do not change the UI so they can be called in a secondary thread. The problem remains, however, of how do you prevent race conditions if you access the ui directly (what stops the user to change the index of ui->comboBox while the code is running?)
                  2. if you just need to run a function in a different thread you don't need anything fancy coming from Qt, std::async does that
                  3. QThread is not the thread, it's a container of the actual thread that lives on the tread that spawns it. this means emitting a signal of MyThread in the secondary thread is a race condition and slots of MyThread will be executed in the main thread, not the one it spawns. See this article for an explanation on how to use signals and slots in a secondary thread

                  "La mort n'est rien, mais vivre vaincu et sans gloire, c'est mourir tous les jours"
                  ~Napoleon Bonaparte

                  On a crusade to banish setIndexWidget() from the holy land of Qt

                  1 Reply Last reply
                  2
                  • J Offline
                    J Offline
                    JSher
                    wrote on last edited by
                    #11

                    @VRonin I want to run the function in another thread because I want to run the function across several threads(concurrently) and return a results vector to then be used to produce a spreadsheet once all the threads have finished.

                    I can find no examples of pushing a button in a GUI, sending information to a thread function to run and then returning that information to the main thread.....

                    Thanks,
                    --James

                    VRoninV 1 Reply Last reply
                    0
                    • J JSher

                      @VRonin I want to run the function in another thread because I want to run the function across several threads(concurrently) and return a results vector to then be used to produce a spreadsheet once all the threads have finished.

                      I can find no examples of pushing a button in a GUI, sending information to a thread function to run and then returning that information to the main thread.....

                      Thanks,
                      --James

                      VRoninV Offline
                      VRoninV Offline
                      VRonin
                      wrote on last edited by
                      #12

                      @JSher said in QThread example to run a function in MainWindow on button click:

                      sending information to a thread function to run and then returning that information to the main thread

                      This is literally what std::async of vanilla C++ does, otherwise you can use QtConcurrent. You can just google examples of std::async

                      "La mort n'est rien, mais vivre vaincu et sans gloire, c'est mourir tous les jours"
                      ~Napoleon Bonaparte

                      On a crusade to banish setIndexWidget() from the holy land of Qt

                      1 Reply Last reply
                      1
                      • S Offline
                        S Offline
                        SimonSchroeder
                        wrote on last edited by
                        #13

                        @JSher said in QThread example to run a function in MainWindow on button click:

                        @VRonin I want to run the function in another thread because I want to run the function across several threads(concurrently) and return a results vector to then be used to produce a spreadsheet once all the threads have finished.

                        This sounds like you want something like the functions in QtConcurrent. There is a difference between launching a single thread to do work asynchronously and using multiple threads to split the work. For the latter it makes sense to use a thread pool so you don't have to manage the number of threads yourself. QtConcurrent will use a thread pool internally which automatically adapts to the number of cores available. Probably, you want something like QtConcurrent::map or QtConcurrent::filter. These will give back a QFuture object. Which in turn can be handed to a QFutureWatcher so that you can connect signals from QFutureWatcher to update your GUI once the work is finished.

                        1 Reply Last reply
                        0

                        • Login

                        • Login or register to search.
                        • First post
                          Last post
                        0
                        • Categories
                        • Recent
                        • Tags
                        • Popular
                        • Users
                        • Groups
                        • Search
                        • Get Qt
                        • Unsolved