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. Get user input from QDialog
Forum Updated to NodeBB v4.3 + New Features

Get user input from QDialog

Scheduled Pinned Locked Moved Unsolved General and Desktop
12 Posts 5 Posters 4.1k 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.
  • E Essentialfloss7-111XfacF
    13 Mar 2019, 14:38

    Hi,
    How can I grab "send" data input from user from QDialog using signal/slots?

    Right now I've got something like this:

    connect(ui.okButton, &QPushButton::clicked, this, &DialogInput::buttonClicked);
    
    void DialogInput::buttonClicked() {
    	setSite();
    }
    
    void DialogInput::setSite() {
    	const QString siteQString = ui.lineEdit->text();
    	site_text = siteQString.toLocal8Bit().constData();
    }
    

    Right after okButton is been clicked values are saved in private fields of "DialogInput" class. How can I "send" those values to functions in other classes? In DialogInput other objects and they're methods are inaccessible.

    Dialog is invoking this way:

    dialog = new DialogInput();
    dialog->exec();
    
    J Offline
    J Offline
    JonB
    wrote on 13 Mar 2019, 15:41 last edited by JonB
    #2

    @Essentialfloss7-111XfacF
    The usual way is to emit() a signal from the dialog which outside world can connect slots to. That's the Qt way of doing things, and does not require your dialog to know who the listeners are, nor to expose methods for outside world to call.

    1 Reply Last reply
    0
    • V Offline
      V Offline
      VRonin
      wrote on 13 Mar 2019, 16:14 last edited by VRonin
      #3

      It happens rarely but I disagree with @JonB
      The usual way (for dialogs, for other widgets Jon's suggestion is 100% correct) is just to have a getter for the property you want. Add in the public: section of DialogInput something like QString getSite() const {return ui.lineEdit->text();}.
      Then you just call

      DialogInput dialog;
      if(dialog.exec()){
      qDebug() << dialog.getSite();
      }
      

      "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

      J 1 Reply Last reply 13 Mar 2019, 18:11
      2
      • E Offline
        E Offline
        Essentialfloss7-111XfacF
        wrote on 13 Mar 2019, 17:02 last edited by Essentialfloss7-111XfacF
        #4

        I've got "working" solution that look like @VRonin solution. But I think there's something wrong with that. I think in my solution data are passed and saved to db after closing Dialog (I want to save into db after clicked -okButton in DialogInput window :

        In MainWindow constructor I've got initialization of database class (db) and connect to pushButton which is invoking DialogInput window

        db = new Database();
        connect(ui.insertBtn, &QPushButton::clicked, this, &MainWindow::runUserInputDialog);
        
        void MainWindow::runUserInputDialog() {
        	dialog = new DialogInput();
        	dialog->exec();
        	getters();
        	setters();
        	db->insertValues();
        }
        
        void MainWindow::getters() {
        	site_text = dialog->getSite();
        	login_text = dialog->getLogin();
        	pass_text = dialog->getPass();
        }
        
        void MainWindow::setters() {
        	db->setSite(site_text);
        	db->setLogin(login_text);
        	db->setPasswd(pass_text);
        }
        
        J 1 Reply Last reply 14 Mar 2019, 05:23
        0
        • V VRonin
          13 Mar 2019, 16:14

          It happens rarely but I disagree with @JonB
          The usual way (for dialogs, for other widgets Jon's suggestion is 100% correct) is just to have a getter for the property you want. Add in the public: section of DialogInput something like QString getSite() const {return ui.lineEdit->text();}.
          Then you just call

          DialogInput dialog;
          if(dialog.exec()){
          qDebug() << dialog.getSite();
          }
          
          J Offline
          J Offline
          JonB
          wrote on 13 Mar 2019, 18:11 last edited by JonB
          #5

          @VRonin , @Essentialfloss7-111XfacF

          It happens rarely but I disagree with @JonB

          :) I read the OP's question as

          How can I grab "send" data input from user from QDialog using signal/slots?
          How can I "send" those values to functions in other classes?

          I thought he actively wanted to "post" data out from his dialog.

          Re-reading, maybe OP is only asking to access data in fields on the dialog, I don't know?

          One thing about the approach you two are using now, just to be aware of. I have all my dialogs default to Qt::WA_DeleteOnClose (https://doc-snapshots.qt.io/qt5-5.9/qt.html#WidgetAttribute-enum). After QDialog.exec() the dialog has closed & gone, you cannot access its members, so this approach won't work. This may not affect the OP (so long as he deletes the dialog himself), it may be because I use Python/PyQt.

          1 Reply Last reply
          0
          • S Offline
            S Offline
            SGaist
            Lifetime Qt Champion
            wrote on 13 Mar 2019, 20:16 last edited by
            #6

            Hi,

            An additional note, you are leaking dialogs object with your implementation.

            You create a new dialog each time your function is called.

            Interested in AI ? www.idiap.ch
            Please read the Qt Code of Conduct - https://forum.qt.io/topic/113070/qt-code-of-conduct

            1 Reply Last reply
            2
            • E Essentialfloss7-111XfacF
              13 Mar 2019, 17:02

              I've got "working" solution that look like @VRonin solution. But I think there's something wrong with that. I think in my solution data are passed and saved to db after closing Dialog (I want to save into db after clicked -okButton in DialogInput window :

              In MainWindow constructor I've got initialization of database class (db) and connect to pushButton which is invoking DialogInput window

              db = new Database();
              connect(ui.insertBtn, &QPushButton::clicked, this, &MainWindow::runUserInputDialog);
              
              void MainWindow::runUserInputDialog() {
              	dialog = new DialogInput();
              	dialog->exec();
              	getters();
              	setters();
              	db->insertValues();
              }
              
              void MainWindow::getters() {
              	site_text = dialog->getSite();
              	login_text = dialog->getLogin();
              	pass_text = dialog->getPass();
              }
              
              void MainWindow::setters() {
              	db->setSite(site_text);
              	db->setLogin(login_text);
              	db->setPasswd(pass_text);
              }
              
              J Offline
              J Offline
              jsulm
              Lifetime Qt Champion
              wrote on 14 Mar 2019, 05:23 last edited by
              #7

              @Essentialfloss7-111XfacF said in Get user input from QDialog:

              data are passed and saved to db after closing Dialog (I want to save into db after clicked -okButton

              Isn't the dialog closed when you click on Ok button? So, what is would be the difference?
              If your dialog is not closed when Ok button is clicked, then you will need to go for the solution suggested by @JonB

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

              1 Reply Last reply
              0
              • V Offline
                V Offline
                VRonin
                wrote on 14 Mar 2019, 08:29 last edited by
                #8

                The normal approach with ok/cancel buttons is to connect them to the QDialog::accept/QDialog::reject slots

                I have all my dialogs default to Qt::WA_DeleteOnClose

                If you want to go down this rabbit hole: https://blogs.kde.org/2009/03/26/how-crash-almost-every-qtkde-application-and-how-fix-it-0

                "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

                J 1 Reply Last reply 14 Mar 2019, 09:57
                0
                • V VRonin
                  14 Mar 2019, 08:29

                  The normal approach with ok/cancel buttons is to connect them to the QDialog::accept/QDialog::reject slots

                  I have all my dialogs default to Qt::WA_DeleteOnClose

                  If you want to go down this rabbit hole: https://blogs.kde.org/2009/03/26/how-crash-almost-every-qtkde-application-and-how-fix-it-0

                  J Offline
                  J Offline
                  JonB
                  wrote on 14 Mar 2019, 09:57 last edited by JonB
                  #9

                  @VRonin
                  I'm not sure what your KDE link is saying about my situation. My problem (not the OP's/yours/C++) is Python/PyQt. We cannot delete a dialog. Python does that for us --- or not --- behind the scenes. I cannot recall all the ins and outs, but I found that setting Qt::WA_DeleteOnClose was the best way to ensure the dialog actually gets deleted.

                  95% of my dialogs do not have extra buttons/fields/callbacks, and do not need to be accessed after the user closes. For the few that do require post-close access, my code explicitly removes that flag and handles clear up itself. It's just my default. I just wanted to make OP aware of potential pitfall when trying to access widgets on dialog after it has been exec()ed.

                  J 1 Reply Last reply 14 Mar 2019, 10:10
                  0
                  • J JonB
                    14 Mar 2019, 09:57

                    @VRonin
                    I'm not sure what your KDE link is saying about my situation. My problem (not the OP's/yours/C++) is Python/PyQt. We cannot delete a dialog. Python does that for us --- or not --- behind the scenes. I cannot recall all the ins and outs, but I found that setting Qt::WA_DeleteOnClose was the best way to ensure the dialog actually gets deleted.

                    95% of my dialogs do not have extra buttons/fields/callbacks, and do not need to be accessed after the user closes. For the few that do require post-close access, my code explicitly removes that flag and handles clear up itself. It's just my default. I just wanted to make OP aware of potential pitfall when trying to access widgets on dialog after it has been exec()ed.

                    J Offline
                    J Offline
                    jsulm
                    Lifetime Qt Champion
                    wrote on 14 Mar 2019, 10:10 last edited by
                    #10

                    @JonB said in Get user input from QDialog:

                    We cannot delete a dialog

                    Isn't that happening automatically as soon as the dialog instance goes out of scope?

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

                    V J 2 Replies Last reply 14 Mar 2019, 10:24
                    0
                    • J jsulm
                      14 Mar 2019, 10:10

                      @JonB said in Get user input from QDialog:

                      We cannot delete a dialog

                      Isn't that happening automatically as soon as the dialog instance goes out of scope?

                      V Offline
                      V Offline
                      VRonin
                      wrote on 14 Mar 2019, 10:24 last edited by
                      #11

                      @jsulm said in Get user input from QDialog:

                      @JonB said in Get user input from QDialog:

                      We cannot delete a dialog

                      Isn't that happening automatically as soon as the dialog instance goes out of scope?

                      In Python I don't think that's the case if you pass a parent to the dialog (I'm not sure though)

                      "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
                      0
                      • J jsulm
                        14 Mar 2019, 10:10

                        @JonB said in Get user input from QDialog:

                        We cannot delete a dialog

                        Isn't that happening automatically as soon as the dialog instance goes out of scope?

                        J Offline
                        J Offline
                        JonB
                        wrote on 14 Mar 2019, 10:42 last edited by JonB
                        #12

                        @jsulm , @VRonin

                        Isn't that happening automatically as soon as the dialog instance goes out of scope?

                        Ohhh, noooo ! Welcome to my Python hell :( Don't be fooled by claims that Python "just works". :) I don't know whether you/others are Pythonistas, this should be relevant not just to PyQt but also to new Qt for Python/PySide2, but briefly....

                        Python automatically reference counts objects. Object is not freed if there are any existing references to it, till reference count reaches 0. Even trying to go Python del, which you might think would behave as C++ delete, does not delete --- it only decrements reference count by 1.

                        "Normally" this works well. However, there are cases where you have reference counts you don't even know about, which prevent disposal! :( I did say I did not recall all the ins & outs, but the most obvious & horrible one is if you have lambdas in the dialog code which reference self (this) in its parameters. I'm not a great fan of lambdas, but there are a lot in the code I have inherited. Many are innocuous-looking:

                        self.widget.signal.connect(lambda: method(self.something))
                        

                        This creates a lambda which references self (via self.something). That is effectively an anonymous function (called a "closure", I think) which references self and so increments the dialog's reference count. Python is not clever enough to understand that it is local to the dialog and so does not need to increment to prevent disposal. As a consequence, Python is never going to dispose this dialog, because its count will never reach 0! :( [This issue does not apply only to e.g. Qt, it's a general Python issue with lambdas.]

                        I tested by walking QtWidgets.QApplication.allWidgets() and sure enough such dialogs (together with all their widgets) never get freed via out-of-scope once opened, till application closure. They do get freed if you explicitly close the dialog via Qt::WA_DeleteOnClose. Hence my decision on advisable default behaviour for me/Python.....

                        1 Reply Last reply
                        4

                        11/12

                        14 Mar 2019, 10:24

                        • Login

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