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. Opening a Qt dialog from within a plugin (a general-type shared library)
Qt 6.11 is out! See what's new in the release blog

Opening a Qt dialog from within a plugin (a general-type shared library)

Scheduled Pinned Locked Moved General and Desktop
13 Posts 3 Posters 5.4k 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.
  • F Offline
    F Offline
    floatingWoods
    wrote on last edited by
    #1

    Hello,

    I am having difficulties displaying a Qt dialog from within a plugin (a dll dynamically loaded by another application). The other application is also based on Qt and constructs a QApplication object. In the main application, I open a main window (QMainWindow) and several dialogs. Then I send the handle of the main window ( void* mainWindowHandle=myMainWindow->winId() ) to the plugin (during plugin initialization).

    The plugin then tries to open (non-modally) one of its own dialog with following instructions:

    @
    pluginDialog=new CPluginDialog((QWidget*)mainWindowHandle);
    pluginDialog->setVisible(true);
    @

    Trying to make the plugin dialog visible crashes the plugin and application. This also happens when I create the plugin dialog with a NULL argument like this:

    @
    pluginDialog=new CPluginDialog(NULL);
    pluginDialog->setVisible(true);
    @

    What am I doing wrong? How can I tell the plugin that it should use the same messaging loop for its dialogs as the main application? (everything is using the same thread)

    [EDIT: code formatting, please use @-tags, Volker]

    1 Reply Last reply
    0
    • F Offline
      F Offline
      floatingWoods
      wrote on last edited by
      #2

      Might it be a problem with the project file?

      Following is what I have in the project file:

      TEMPLATE = lib
      CONFIG += shared
      QT += gui

      I also tried to create a second QApplication or QCoreApplication object, but that didn't help..

      1 Reply Last reply
      0
      • L Offline
        L Offline
        lgeyer
        wrote on last edited by
        #3

        You cannot pass a value returned by <code>QWidget::winId()</code> as a parent. The one is a native window handle of type <code>WId</code> (not <code>void*</code>), the other is a <code>QWidget*</code>. If you want your main window to be the parent of your widget, you will have to pass a pointer to the main window, not its window id.
        @void MainWindow::initializePlugin()
        {
        plugin->initialize(this);
        }
        ...
        void Plugin::initialize(QWidget* mainWindow)
        {
        Dialog* dialog = new Dialog(mainWindow);
        dialog->show();
        }@

        You should always prefer C++ style casts (<code>static_cast</code> and <code>dynamic_cast</code>) over C style casts and <code>reinterpret_cast</code>. They won't allow you to do such horrible things as:
        [quote author="floatingWoods" date="1325597152"]
        @
        void* mainWindowHandle = myMainWindow->winId();
        pluginDialog = new CPluginDialog((QWidget*) mainWindowHandle); // WRONGEST
        @
        [/quote]

        1 Reply Last reply
        0
        • F Offline
          F Offline
          floatingWoods
          wrote on last edited by
          #4

          Thanks Lukas,

          You are right, and I corrected for that. However, I still have the same problem. I also have that problem when I create the plugin dialog with a NULL argument. The plugin initializes fine but then crashes when I call "setVisible(true)" on the created dialog.

          1 Reply Last reply
          0
          • F Offline
            F Offline
            floatingWoods
            wrote on last edited by
            #5

            Actually I noticed that the main application sometimes has the same problem (at least it appears same). Still, always using the same thread (the main thread), sometimes following works, sometimes it crashes in msg.exec():

            @
            QMessageBox msg(NULL);
            msg.setWindowTitle(title.c_str());
            msg.setText(message.c_str());
            msg.addButton(QMessageBox::Ok);
            int result=msg.exec();
            @

            is there some restriction when exec() can be called?

            [EDIT: code formatting, Volker]

            1 Reply Last reply
            0
            • L Offline
              L Offline
              lgeyer
              wrote on last edited by
              #6

              Can you provide a small compileable example that reproduces your problem?

              1 Reply Last reply
              0
              • F Offline
                F Offline
                floatingWoods
                wrote on last edited by
                #7

                The application is very big and it would take days to simplify it to provide a small compilable example...
                But I think I found the source of the problem:

                I manage the "main application loop" myself, i.e. I call on a regular basis "myQApplication->processEvents". This is important for that application that is not purely event based. The main thread should never be blocked or trapped in "myQApplication->exec()" or similar.

                When a dialog is opened or shown indirectly by a call to "myQApplication->processEvents", which is 99% of the cases, there is no problem at all. In that case a user action triggers an event, that is processed by that call, and that opens a dialog.

                However, when I open or show a dialog somewhere else (e.g. just before or after calling "myQApplication->processEvents"), then the application crashes.

                What am I doing wrong here?

                EDIT: actually, the whole application was ported to Qt from a MSVC application. Under MSVC, above method (i.e. "a non-blocking main application loop") doesn't cause any crash or strange behaviour

                1 Reply Last reply
                0
                • G Offline
                  G Offline
                  goetz
                  wrote on last edited by
                  #8

                  The firsthand solution would be to use Qt programming patterns for Qt programs, and MSVC programming patterns for MSVC native programs. In other words: call application.exec(). The usual flow of control in a Qt program is that after application.exec() returns, the program shuts down. There's at maximum a few lines of clean up code after that and before returning from main().

                  This way you save yourself from calling processEvents, etc.

                  The Qt event loop is non blocking in the sense that the rest of your program logic is pretty much unblocked. And something in main() must block until the user quits the program, otherwise the program would quit immediately. So you will have something similar and blocking in your main method (probably a loop watching over a flag or the like).

                  Additionally, make sure you always link against the same library versions and build flavors, especially make sure to not mix debug and release versions!

                  http://www.catb.org/~esr/faqs/smart-questions.html

                  1 Reply Last reply
                  0
                  • F Offline
                    F Offline
                    floatingWoods
                    wrote on last edited by
                    #9

                    Thanks Volker!

                    I will gradually shift to a "more conventional" way of handling the application, but the first priority is to keep "relative" similarity/compatibility with the old framework so that old users don't get upset.

                    I noticed something strange right now:

                    When I prepare my Qt application at start-up (allocating resources, creating a QMainWindow with toolbars+menu bar), I can display message boxes without any problem any time... until I call myQMainWindow->showMaximized(). After that, message boxes work fine only when called from within processEvents(). Is that a normal behaviour?

                    1 Reply Last reply
                    0
                    • G Offline
                      G Offline
                      goetz
                      wrote on last edited by
                      #10

                      Are you talking about users of your application? Those do not care about internal implementations. If you're talking about users in the sense of co-developers, switching frameworks causes the need to switch habits too. There's no gain in conserving old habits in a new framework if it is "the wrong way" to do it.

                      Message boxes carry their own event loop. That's why they work even if the main event loop hasn't started yet. For your main window to work you need the main event loop, it doesn't provide its own incarnation. If you do not start application.exec(), you're pretty much on your own. That's the way a Qt application is supposed to be run and you will have a hard time finding someone giving you advice on doing otherwise. It's just too much that depends on the main event loop running.

                      You will run into further serious issues. So do yourself (and your users) a favor and to it "the right way" from the beginning! Learning Qt by ignoring it's rules is much like learning English from dadaistic poems - you will gain almost nothing.

                      http://www.catb.org/~esr/faqs/smart-questions.html

                      1 Reply Last reply
                      0
                      • F Offline
                        F Offline
                        floatingWoods
                        wrote on last edited by
                        #11

                        That makes sense.

                        When I am talking about users, those are also writing plugins for my application. Until now there was only one single thread that would talk to those plugins. If I switch to the "correct Qt" way, I will have to split the application into:

                        • Qt thread and UI handling (rendering an openGl scene, handling the dialogs, etc.). This may block if there is another thread (see next item):
                        • Working thread (doing simulation calculations). I guess message boxes can be started from there without problems?
                        1 Reply Last reply
                        0
                        • G Offline
                          G Offline
                          goetz
                          wrote on last edited by
                          #12

                          No, you must not start any GUI related code from a worker thread. This must be done in the GUI thread. The good side is: you can connect a signal of the worker thread to your GUI classes and request a message box this way.

                          As threaded programming is quite tricky, don't forget to read further on this topic in Qt context. At least, read an understand pepes wonderful wiki article about "Threads, Events and QObjects":/wiki/Threads_Events_QObjects.

                          http://www.catb.org/~esr/faqs/smart-questions.html

                          1 Reply Last reply
                          0
                          • F Offline
                            F Offline
                            floatingWoods
                            wrote on last edited by
                            #13

                            Thanks a lot Volker. I will look into that article.

                            Best regards and thanks again!

                            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 Extensions
                            • Unsolved