Skip to content
  • Categories
  • Recent
  • Tags
  • Popular
  • Users
  • Groups
  • Search
  • Get Qt Extensions
  • Unsolved
Collapse
Brand Logo
  1. Home
  2. Qt Development
  3. General and Desktop
  4. Qt 6: can't create working local QEventLoop while handling aboutToQuit()
Forum Updated to NodeBB v4.3 + New Features

Qt 6: can't create working local QEventLoop while handling aboutToQuit()

Scheduled Pinned Locked Moved Solved General and Desktop
3 Posts 2 Posters 73 Views
  • 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.
  • B Offline
    B Offline
    barbicels
    wrote last edited by barbicels
    #1

    My application needs to respond to the QCoreApplication::aboutToQuit() signal by chatting with some background worker threads. It's not just waiting for them to finish — they need to "chat" back and forth with the main thread, the way it's written.

    My understanding has been that I should program the main thread's aboutToQuit() handler so that it doesn't return until all threads are ready to be killed.

    Under Qt 5.15.2, I was able to do that in my handler by spinning a local QEventLoop or calling processEvents() repeatedly (as documented) until all background threads are finished chatting with the main thread using the signal/slot connections they have built.

    Under Qt 6.5.3, apparently due to changes in the way aboutToQuit() is administered in qcoreapplication.cpp, this no longer works. The local QEventLoop's exec() call returns immediately because the main thread's quitNow flag has already been set, where previously it was not set at the time of this signal.

    What is the "new" correct way to forestall the app shutdown if my app still needs to pass events between threads?

    PS edit: This is a QML application.

    1 Reply Last reply
    0
    • hskoglundH hskoglund

      Hi, maybe try QWindow's closeEvent and set accepted to false, or on the C++ side the closeEvent()?

      In C++, say like this:

      ...
      void MainWindow::closeEvent(QCloseEvent *event)
      {
          static bool bThreadsDone = false;
          if (!bThreadsDone)
          {
              event->ignore();
      
              QTimer::singleShot(1234,[&bThreadsDone]
              {
              // check if threads are done (assuming yes :-)
                  bThreadsDone = true;
                  qApp->quit();
              });
          }
      ...
      }
      

      When the user quits the app, in the above example, there will be a delay of 1234 milliseconds before the app exits.

      B Offline
      B Offline
      barbicels
      wrote last edited by
      #3

      @hskoglund I think this may be the only way to go, especially if the result of the thread interaction requires any sort of GUI (posting error messages, etc.). It does seem that aboutToQuit() is too late in the sequence.

      Evidence, after some exploration:

      • My problem was caused by a change in Qt 6.5.0 (link) that moved the signaling point from QCoreApplication::execCleanup() (which explicitly turns off the quitNow flag) to exit() (which doesn't). That flag is what prevents a local QEventLoop in my slot handler from spinning up. It's not clear if they meant to do that, but...
      • That change refers to a bug report (link). A comment by the maintainer says, "The docs for aboutToQuit specify 'Note that no user interaction is possible in this state.'"
      • And indeed they do (link).
      1 Reply Last reply
      1
      • hskoglundH Offline
        hskoglundH Offline
        hskoglund
        wrote last edited by hskoglund
        #2

        Hi, maybe try QWindow's closeEvent and set accepted to false, or on the C++ side the closeEvent()?

        In C++, say like this:

        ...
        void MainWindow::closeEvent(QCloseEvent *event)
        {
            static bool bThreadsDone = false;
            if (!bThreadsDone)
            {
                event->ignore();
        
                QTimer::singleShot(1234,[&bThreadsDone]
                {
                // check if threads are done (assuming yes :-)
                    bThreadsDone = true;
                    qApp->quit();
                });
            }
        ...
        }
        

        When the user quits the app, in the above example, there will be a delay of 1234 milliseconds before the app exits.

        B 1 Reply Last reply
        0
        • hskoglundH hskoglund

          Hi, maybe try QWindow's closeEvent and set accepted to false, or on the C++ side the closeEvent()?

          In C++, say like this:

          ...
          void MainWindow::closeEvent(QCloseEvent *event)
          {
              static bool bThreadsDone = false;
              if (!bThreadsDone)
              {
                  event->ignore();
          
                  QTimer::singleShot(1234,[&bThreadsDone]
                  {
                  // check if threads are done (assuming yes :-)
                      bThreadsDone = true;
                      qApp->quit();
                  });
              }
          ...
          }
          

          When the user quits the app, in the above example, there will be a delay of 1234 milliseconds before the app exits.

          B Offline
          B Offline
          barbicels
          wrote last edited by
          #3

          @hskoglund I think this may be the only way to go, especially if the result of the thread interaction requires any sort of GUI (posting error messages, etc.). It does seem that aboutToQuit() is too late in the sequence.

          Evidence, after some exploration:

          • My problem was caused by a change in Qt 6.5.0 (link) that moved the signaling point from QCoreApplication::execCleanup() (which explicitly turns off the quitNow flag) to exit() (which doesn't). That flag is what prevents a local QEventLoop in my slot handler from spinning up. It's not clear if they meant to do that, but...
          • That change refers to a bug report (link). A comment by the maintainer says, "The docs for aboutToQuit specify 'Note that no user interaction is possible in this state.'"
          • And indeed they do (link).
          1 Reply Last reply
          1
          • B barbicels has marked this topic as solved

          • Login

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