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. Connect ui files from different classes

Connect ui files from different classes

Scheduled Pinned Locked Moved Unsolved General and Desktop
12 Posts 4 Posters 2.0k Views 2 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.
  • D Offline
    D Offline
    DeadSo0ul
    wrote on last edited by
    #1

    Hello!
    I was wondering if I am able to change widgets from any class.

    If I use a MainWindow class I can simply use setCentralWidget function. But I want to use multiple .ui files with multiple classes and be able to load different .ui files for example when a button is clicked.
    The idea is to make things more organized in stead of using QStackedWidget and a single MainWindow class.

    Thanks!

    M 1 Reply Last reply
    0
    • D DeadSo0ul

      Hello!
      I was wondering if I am able to change widgets from any class.

      If I use a MainWindow class I can simply use setCentralWidget function. But I want to use multiple .ui files with multiple classes and be able to load different .ui files for example when a button is clicked.
      The idea is to make things more organized in stead of using QStackedWidget and a single MainWindow class.

      Thanks!

      M Offline
      M Offline
      mpergand
      wrote on last edited by
      #2

      Hi @DeadSo0ul

      You can use QUILoader

      D 1 Reply Last reply
      0
      • M mpergand

        Hi @DeadSo0ul

        You can use QUILoader

        D Offline
        D Offline
        DeadSo0ul
        wrote on last edited by
        #3

        Hi @mpergand
        Thanks for your advice about using QUiLoader. I tried following their documentation but got into an error.

        I wrote a simple code whenever a button is pressed

        void MainMenu::on_LogIn_menu_PB_clicked()
        {
            QUiLoader loader;
            QFile file(":/forms/logInPage.ui");
            file.open(QFile::ReadOnly);
            QWidget *myWidget = loader.load(&file, this);
            file.close();
        
            QVBoxLayout *layout = new QVBoxLayout;
            layout->addWidget(myWidget);
            setLayout(layout);
        }
        

        but I get an error:
        QWidget::setLayout: Attempting to set QLayout "" on MainMenu "MainMenu", which already has a layout

        With some AI help I managed to change the code to

        void MainMenu::on_LogIn_menu_PB_clicked()
        {
            QUiLoader loader;
            QFile file(":/forms/logInPage.ui");
            file.open(QFile::ReadOnly);
            QWidget *myWidget = loader.load(&file, this);
            file.close();
        
            QLayout *existingLayout = centralWidget()->layout();
        
           if (existingLayout)
                delete existingLayout;
        
            QVBoxLayout *layout = new QVBoxLayout(centralWidget());
            layout->addWidget(myWidget);
        
            myWidget->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding);
        }
        

        However that just loaded both .ui files at once.
        I want to ask if I am mistaken and if so how can I make it appear a single ui file (by ui file I mean all the design inside)

        D 1 Reply Last reply
        0
        • D DeadSo0ul

          Hi @mpergand
          Thanks for your advice about using QUiLoader. I tried following their documentation but got into an error.

          I wrote a simple code whenever a button is pressed

          void MainMenu::on_LogIn_menu_PB_clicked()
          {
              QUiLoader loader;
              QFile file(":/forms/logInPage.ui");
              file.open(QFile::ReadOnly);
              QWidget *myWidget = loader.load(&file, this);
              file.close();
          
              QVBoxLayout *layout = new QVBoxLayout;
              layout->addWidget(myWidget);
              setLayout(layout);
          }
          

          but I get an error:
          QWidget::setLayout: Attempting to set QLayout "" on MainMenu "MainMenu", which already has a layout

          With some AI help I managed to change the code to

          void MainMenu::on_LogIn_menu_PB_clicked()
          {
              QUiLoader loader;
              QFile file(":/forms/logInPage.ui");
              file.open(QFile::ReadOnly);
              QWidget *myWidget = loader.load(&file, this);
              file.close();
          
              QLayout *existingLayout = centralWidget()->layout();
          
             if (existingLayout)
                  delete existingLayout;
          
              QVBoxLayout *layout = new QVBoxLayout(centralWidget());
              layout->addWidget(myWidget);
          
              myWidget->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding);
          }
          

          However that just loaded both .ui files at once.
          I want to ask if I am mistaken and if so how can I make it appear a single ui file (by ui file I mean all the design inside)

          D Offline
          D Offline
          DeadSo0ul
          wrote on last edited by
          #4

          I tried using setCentralWidget:

          void MainMenu::on_LogIn_menu_PB_clicked()
          {
              QUiLoader loader;
              QFile file(":/forms/logInPage.ui");
          
              if (!file.open(QFile::ReadOnly)) {
                  qDebug() << "Cannot open file:" << file.errorString();
                  return;
              }
          
              QWidget *myWidget = loader.load(&file, this);
              file.close();
          
              if (!myWidget) {
                  qDebug() << "Failed to load UI file";
                  return;
              }
          
              // Set the loaded widget as the central widget
              setCentralWidget(myWidget);
          }
          

          Which gave me the wanted result however setCentralWidget is a function that can only be used from MainWindow class or from inheritance.

          Is there any other way I can get that result without using setCentralWidget function

          M Pl45m4P 2 Replies Last reply
          0
          • D DeadSo0ul

            I tried using setCentralWidget:

            void MainMenu::on_LogIn_menu_PB_clicked()
            {
                QUiLoader loader;
                QFile file(":/forms/logInPage.ui");
            
                if (!file.open(QFile::ReadOnly)) {
                    qDebug() << "Cannot open file:" << file.errorString();
                    return;
                }
            
                QWidget *myWidget = loader.load(&file, this);
                file.close();
            
                if (!myWidget) {
                    qDebug() << "Failed to load UI file";
                    return;
                }
            
                // Set the loaded widget as the central widget
                setCentralWidget(myWidget);
            }
            

            Which gave me the wanted result however setCentralWidget is a function that can only be used from MainWindow class or from inheritance.

            Is there any other way I can get that result without using setCentralWidget function

            M Offline
            M Offline
            mpergand
            wrote on last edited by mpergand
            #5

            @DeadSo0ul said in Connect ui files from different classes:

            Which gave me the wanted result however setCentralWidget is a function that can only be used from MainWindow class or from inheritance.

            If you need to access the central widget from other classes, there's an ui design error somewhere.

            I suspect you should use signal & slots instead.
            Without further details, it's hard to say.

            1 Reply Last reply
            2
            • D DeadSo0ul

              I tried using setCentralWidget:

              void MainMenu::on_LogIn_menu_PB_clicked()
              {
                  QUiLoader loader;
                  QFile file(":/forms/logInPage.ui");
              
                  if (!file.open(QFile::ReadOnly)) {
                      qDebug() << "Cannot open file:" << file.errorString();
                      return;
                  }
              
                  QWidget *myWidget = loader.load(&file, this);
                  file.close();
              
                  if (!myWidget) {
                      qDebug() << "Failed to load UI file";
                      return;
                  }
              
                  // Set the loaded widget as the central widget
                  setCentralWidget(myWidget);
              }
              

              Which gave me the wanted result however setCentralWidget is a function that can only be used from MainWindow class or from inheritance.

              Is there any other way I can get that result without using setCentralWidget function

              Pl45m4P Offline
              Pl45m4P Offline
              Pl45m4
              wrote on last edited by
              #6

              @DeadSo0ul said in Connect ui files from different classes:

              Is there any other way I can get that result without using setCentralWidget function

              Show the custom built widgets directly. Nobody forces you to show your UI content as centralwidget.
              But as @mpergand said, without further information it's hard to say what fits best in your case.


              If debugging is the process of removing software bugs, then programming must be the process of putting them in.

              ~E. W. Dijkstra

              D 1 Reply Last reply
              0
              • Pl45m4P Pl45m4

                @DeadSo0ul said in Connect ui files from different classes:

                Is there any other way I can get that result without using setCentralWidget function

                Show the custom built widgets directly. Nobody forces you to show your UI content as centralwidget.
                But as @mpergand said, without further information it's hard to say what fits best in your case.

                D Offline
                D Offline
                DeadSo0ul
                wrote on last edited by
                #7

                @Pl45m4
                It was a stupid mistake. I managed to make it work by simply making a new widget and hiding the current one

                    logInWindow = new logIn(nullptr);
                    this->hide();
                    logInWindow->show();
                

                Thanks!

                JonBJ 1 Reply Last reply
                0
                • D DeadSo0ul

                  @Pl45m4
                  It was a stupid mistake. I managed to make it work by simply making a new widget and hiding the current one

                      logInWindow = new logIn(nullptr);
                      this->hide();
                      logInWindow->show();
                  

                  Thanks!

                  JonBJ Offline
                  JonBJ Offline
                  JonB
                  wrote on last edited by JonB
                  #8

                  @DeadSo0ul
                  Qt provides QStackedWidget as a convenient way to switch between showing one of a number of widgets.

                  D 1 Reply Last reply
                  0
                  • JonBJ JonB

                    @DeadSo0ul
                    Qt provides QStackedWidget as a convenient way to switch between showing one of a number of widgets.

                    D Offline
                    D Offline
                    DeadSo0ul
                    wrote on last edited by
                    #9

                    @JonB
                    I do know and have used it before but I decided to do every single widget with it's own c++ class and .ui file to keep things more organized. As far as I have read I haven't find any way to connect stacked widgets with multiple classes.

                    JonBJ 1 Reply Last reply
                    0
                    • D DeadSo0ul

                      @JonB
                      I do know and have used it before but I decided to do every single widget with it's own c++ class and .ui file to keep things more organized. As far as I have read I haven't find any way to connect stacked widgets with multiple classes.

                      JonBJ Offline
                      JonBJ Offline
                      JonB
                      wrote on last edited by
                      #10

                      @DeadSo0ul
                      Sorry, I do not know you mean. QStackedWidget holds any number of QWidget instances of any classes. Whatever you are doing with "it's own c++ class and .ui file to keep things more organized" can be done just as well with a QSW as whatever you are doing presently with individual widgets and showing/hiding them yourself.

                      QStackedWidget *sw = new QStackedWidget;
                      sw->addWidget(new QWidget);
                      sw->addWidget(new YourOwnWidgetClassCreatedViaUiFileOrAnyOtherWay);
                      
                      D 1 Reply Last reply
                      1
                      • JonBJ JonB

                        @DeadSo0ul
                        Sorry, I do not know you mean. QStackedWidget holds any number of QWidget instances of any classes. Whatever you are doing with "it's own c++ class and .ui file to keep things more organized" can be done just as well with a QSW as whatever you are doing presently with individual widgets and showing/hiding them yourself.

                        QStackedWidget *sw = new QStackedWidget;
                        sw->addWidget(new QWidget);
                        sw->addWidget(new YourOwnWidgetClassCreatedViaUiFileOrAnyOtherWay);
                        
                        D Offline
                        D Offline
                        DeadSo0ul
                        wrote on last edited by DeadSo0ul
                        #11

                        @JonB
                        I think I understood you but didn't manage to make it work.
                        I made a public variable in my class of type QStackedWidget:

                        public:
                            explicit logIn(QWidget *parent = nullptr);
                            ~logIn();
                            QStackedWidget *sw = new QStackedWidget;
                        

                        Then I created the widget I want the application to redirect to:

                        LogIn::logIn(QWidget *parent) : QWidget(parent), ui(new Ui::logIn)
                                    
                                    {
                                    
                                        ui->setupUi(this);
                                    
                                        ui->password_LE->setEchoMode(QLineEdit::Password);
                                    
                                        this->setWindowTitle("Log In");
                                    
                                    
                                    
                                        databaseManager = std::make_unique<DatabaseManager>();
                                    
                                        databaseManager->openConnection();
                                    
                                        db = databaseManager->getDatabase();
                                    
                                    
                                    
                                        sw->addWidget(this);
                                    
                                    
                                    
                                    }
                        

                        And finally tried to change the index of the QStackedWidget

                        void MainMenu::on_LogIn_PB_clicked()
                        {
                            logInWindow = new logIn(nullptr);
                        
                            logInWindow->sw->setCurrentIndex(0);
                        }
                        

                        Did I do anything wrong?
                        Please let me know.
                        Thanks!

                        JonBJ 1 Reply Last reply
                        0
                        • D DeadSo0ul

                          @JonB
                          I think I understood you but didn't manage to make it work.
                          I made a public variable in my class of type QStackedWidget:

                          public:
                              explicit logIn(QWidget *parent = nullptr);
                              ~logIn();
                              QStackedWidget *sw = new QStackedWidget;
                          

                          Then I created the widget I want the application to redirect to:

                          LogIn::logIn(QWidget *parent) : QWidget(parent), ui(new Ui::logIn)
                                      
                                      {
                                      
                                          ui->setupUi(this);
                                      
                                          ui->password_LE->setEchoMode(QLineEdit::Password);
                                      
                                          this->setWindowTitle("Log In");
                                      
                                      
                                      
                                          databaseManager = std::make_unique<DatabaseManager>();
                                      
                                          databaseManager->openConnection();
                                      
                                          db = databaseManager->getDatabase();
                                      
                                      
                                      
                                          sw->addWidget(this);
                                      
                                      
                                      
                                      }
                          

                          And finally tried to change the index of the QStackedWidget

                          void MainMenu::on_LogIn_PB_clicked()
                          {
                              logInWindow = new logIn(nullptr);
                          
                              logInWindow->sw->setCurrentIndex(0);
                          }
                          

                          Did I do anything wrong?
                          Please let me know.
                          Thanks!

                          JonBJ Offline
                          JonBJ Offline
                          JonB
                          wrote on last edited by JonB
                          #12

                          @DeadSo0ul
                          Your code for adding "pages" to a QSW look correct. But you don't seem to have actually added the QSW itself anywhere onto the UI to be visible, just like you would need to for any QWidget! QSW itself is a QWidget, it just happens to show one of its child widgets at any one time So I would expect nothing to show in your code.

                          The QSW does not belong in your LogIn class. It belongs on whatever widget you want to show the (choice of) widget instances, exactly where you would place the widgets and use show/hide() if you were doing that yourself. Let's say that is the central widget on a QMainWindow. Then over in your derived main window class you would have something like:

                          #include <QWidget>
                          #include "logIn.h"
                          #include "someotherofyouruiclass.h"
                          
                          class MyMainWindow : QMainWindow;
                          MyMainWindow::MyMainWindow(QWidget *parent /* = nullptr */)
                              : QMainWindow(parent)
                          {
                              QStackedWidget *sw = new QStackedWidget(this);
                              this->setCentralWidget(sw);
                              sw->addWidget(new QTextEdit);    // arbitrary, just to show what's possible
                              sw->addWidget(new Login);    // instance of your UI designed class
                              sw->addWidget(new SomeOtherOfYourUiClass);    // instance of a different UI designed class
                              
                              // you can do the following line here or e.g. in a main window button click slot
                              sw->setCurrentIndex(1);    // show your `Login` instead of the default one at index 0
                          };
                          

                          If you are not attempting to show one of a choice of a widgets in the same place as each other then QSW is not your buddy. But I thought that is what you are wanting to do.

                          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