Best way to create new window (QWidget) and interactions between QWidgets



  • I am pretty noob to QT development, started yesterday, so keep it calm and simple if possible.

    I have a main window, from class MainWindow which inherits QWidget, from it I want to click a button "Register", a slot named new_register() is called and creates an instance of a class Register that inherits QWidget and on its constructor sets all layout.

    Now from the MainWindow class which I called this "new Register()" I want to verify when it gets destroyed, when it happens I call a function update_list() but I do not know how to do it and not sure if the way I am creating this new window (QWidget) is the best practice way.

    Would love any kind of help, thanks.


  • Qt Champions 2016

    Hi
    Can you show the new_register() ?
    Also how do you want Register to work?
    It be modal and block the mainwindow until user click ok or cancel
    or it can be open and non modal and user can still interact with mainwindow.

    If your use case is that Register should block, maybe you can just use exec() to show it and it wait there until
    user close dialog.
    For this to work, Register should inherits QDialog.
    then in
    mainwindow::new_register() {
    Register dia;
    if ( dia.exec() == QDialog::Accepted) // It waits here till user selects ok or cancel and is OK, then call update_list
    update_list();
    }



  • Sure, here it is, a lot of code but I thought that this was the best way of doing it:

    Register::Register(QWidget *parent) : QWidget(parent)
    {
        this->setLayout();
        this->setConnections();
    }
    
    void Register::setLayout(){
        auto vertical = new QVBoxLayout(this);
        auto horizontal_buttons = new QHBoxLayout(NULL);
        register_new.setText("Register");
        cancel.setText("Cancel");
    
        move(QApplication::desktop()->screen()->rect().center() - this->rect().center());
    
        auto info_list = new QList<QString>({"Name", "Age", "Mass", "Height", "Sport"});
        auto list_it = info_list->begin();
    
        for (list_it = info_list->begin(); list_it != info_list->end(); list_it++) {
            auto horiz = new QHBoxLayout();
            auto label = new QLabel(*list_it);
            auto lineedit = new QLineEdit();
    
            label->setMinimumWidth(60);
            lineedit->setMaximumWidth(200);
    
            vertical->addLayout(horiz);
            horiz->addWidget(label);
            horiz->addWidget(lineedit);
    
            label_list.push_back(lineedit);
        }
    
        vertical->addLayout(horizontal_buttons);
    
        vertical->setAlignment(Qt::AlignTop);
        horizontal_buttons->setAlignment(Qt::AlignRight);
    
        horizontal_buttons->addWidget(&cancel);
        horizontal_buttons->addWidget(&register_new);
    
        register_new.resize(60, 20);
        register_new.setMaximumWidth(100);
        cancel.setMaximumWidth(100);
        cancel.resize(60, 20);
    
        setMaximumWidth(300);
        setMaximumHeight(400);
        setWindowTitle("Register");
    
        show();
    }
    
    void Register::setConnections(){
        connect(&cancel, &QPushButton::clicked, this, &Register::cancel_clicked);
        connect(&register_new, &QPushButton::clicked, this, &Register::register_clicked);
    }
    

    About how I want it to work, I would prefer learning how to do both ways. In Register QWidget if the button "Register" is clicked I want to run the update_list() from MainWidget else if cancel or "x" button clicked just close it. I did not get well the difference between exec() and show(), would you mind explaining? Also is there any good link to learn when to use QObject, QWidget, QFrame (not remembering if this is the right name), QDialog, etc?

    In this case: if ( dia.exec() == QDialog::Accepted) do I have to set anything inside Register, for example, when clicking the Register button, equivalent for an ok button, make the state mode as Accepted?

    Appreciate the patience!


  • Qt Champions 2016

    • difference between exec() and show(),
      Only QDialog have exec() Qwidgets have show.
      When you call show on a Dialog, it becomes visible but do not
      wait for input.
      example
    mainw::func() {
    MyDialog *dia=new MyDialog(this);
    dia->show();
    int a=0; // this code is run the moment dialog is shown on screen,
    }
    
    using exec()
    mainw::func() {
    MyDialog dia;
    dia.exec();
    int a=0; // this code is run only after dialog is dismissed.
    }
    

    The version of dialog where u call show() could be called floating so when user click ok
    it should emit signal that something should happen. ( to maiwindow )

    The exec() version will report back the result ok/cancel/closed at once.

    • learn when to use QObject, QWidget, QFrame
      QWidget is often used if making own widget. QFrame is used if you just need something to draw
      a frame. If you use Designer you can check out the Widgets that are available.
      QDialog is useful for any type of windows that pop ups up or open via a menu.

    • I have to set anything inside Register.
      Yes, Register should be able to give the data back.
      the widgets inside are private so you need a function to return the data.
      You might also need to call
      http://doc.qt.io/qt-5/qdialog.html#accept
      in your Register buttons clicked slot.



Looks like your connection to Qt Forum was lost, please wait while we try to reconnect.