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. How to change my GUI Base Class (QWidget => QMainWindow) ?
Forum Updated to NodeBB v4.3 + New Features

How to change my GUI Base Class (QWidget => QMainWindow) ?

Scheduled Pinned Locked Moved General and Desktop
14 Posts 3 Posters 23.5k 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.
  • sierdzioS Offline
    sierdzioS Offline
    sierdzio
    Moderators
    wrote on last edited by
    #2

    Just change it in c++ header...
    @
    class MyWidget : public QWidget
    // should now become
    class MyWidget : public QMainWindow
    @

    And then update the constructors, too. Last step would be to do a full rebuild. Details depend on what your code actually looks like, though.

    (Z(:^

    1 Reply Last reply
    0
    • U Offline
      U Offline
      u2gilles
      wrote on last edited by
      #3

      That's what i did. it compiled. But my QWidget GUI designed with Qt Designer is lost. When I open xxx.ui (generated by Qt Designer in XML), it still contain tens of QWidget and in QT Creator/Designer, my parent object is still QWidget.

      PS: As far as my other post about clone project is concerned, it worked. I just had to rename the .pro file too (and the TARGET inside). Thanks .

      1 Reply Last reply
      0
      • sierdzioS Offline
        sierdzioS Offline
        sierdzio
        Moderators
        wrote on last edited by
        #4

        You're welcome.

        OK, so your setup is probably not a standard one. It would be really helpful if we could see some code here (your new QMainWindow class declaration, at least a part of the .ui file).

        (Z(:^

        1 Reply Last reply
        0
        • U Offline
          U Offline
          u2gilles
          wrote on last edited by
          #5

          ok. Here you are. This is a simple calculator (i am new in Qt)

          calculator.h
          @
          #ifndef CALC1_H
          #define CALC1_H

          #include <QMainWindow>

          namespace Ui {
          class calc1;
          }

          class StateCal;

          class Calculator : public QMainWindow {
          Q_OBJECT
          public:
          explicit Calculator(QMainWindow *parent = 0);
          ~Calculator();
          void setCurrentState(StateCal *);
          void displayScreen();

          private slots:
          void on_pushButCE_clicked();
          void on_pushButC_clicked();
          void on_pushButDot_clicked();
          void on_pushBut0_clicked();
          void on_pushBut1_clicked();
          void on_pushBut2_clicked();
          void on_pushBut3_clicked();
          void on_pushBut5_clicked();
          void on_pushBut4_clicked();
          void on_pushBut6_clicked();
          void on_pushBut7_clicked();
          void on_pushBut8_clicked();
          void on_pushBut9_clicked();
          void on_pushButTimes_clicked();
          void on_pushButDivide_clicked();
          void on_pushButPlus_clicked();
          void on_pushButMinus_clicked();
          void on_pushButEqual_clicked();

          private:
          Ui::calc1 *ui;
          StateCal *currentState;
          };

          #endif // CALC1_H

          @

          but it does not change anything in calculator.ui which still contains QWidget.

          @
          <?xml version="1.0" encoding="UTF-8"?>
          <ui version="4.0">
          <class>calc1</class>
          <widget class="QWidget" name="calc1">
          <property name="geometry">
          <rect>
          <x>0</x>
          <y>0</y>
          <width>338</width>
          <height>206</height>
          </rect>
          </property>
          <property name="windowTitle">
          <string>calc1</string>
          </property>
          <layout class="QVBoxLayout" name="verticalLayout">
          <item>
          <widget class="QLCDNumber" name="lcdResult">
          <property name="midLineWidth">
          <number>1</number>
          </property>
          <property name="smallDecimalPoint">
          <bool>false</bool>
          </property>
          <property name="numDigits">
          <number>8</number>
          </property>
          <property name="mode">
          <enum>QLCDNumber::Dec</enum>
          </property>
          <property name="value" stdset="0">
          <double>0.000000000000000</double>
          </property>
          </widget>
          </item>
          <item>
          <layout class="QGridLayout" name="gridLayout">
          <item row="0" column="0">
          <widget class="QPushButton" name="pushButCE">
          <property name="text">
          <string>CE</string>
          </property>
          </widget>
          </item>

          .....

          @

          This GUI contains only pushButton , label and LCD.

          The main :

          @
          #include <QtGui/QApplication>
          #include "calculator.h"

          int main(int argc, char *argv[])
          {
          QApplication a(argc, argv);
          Calculator w1;
          w1.show();

          return a.exec&#40;&#41;;
          

          }
          @

          and calcu2.pro :
          @
          QT += core gui
          TARGET = calcu2
          TEMPLATE = app
          SOURCES += main.cpp calculator.cpp statecal.cpp
          HEADERS += calculator.h statecal.h
          FORMS += calculator.ui
          @

          1 Reply Last reply
          0
          • sierdzioS Offline
            sierdzioS Offline
            sierdzio
            Moderators
            wrote on last edited by
            #6

            Just change QWidget from line 4 of the .ui file into a QMainWindow.

            (Z(:^

            1 Reply Last reply
            0
            • U Offline
              U Offline
              u2gilles
              wrote on last edited by
              #7

              Sierdzio, just hold on a moment.
              I just realized that when i renamed calc1->calculator, some calc1 remain like in
              @
              namespace Ui {
              class calc1;
              }
              @
              i will try your method on a new project with just a pushbutton.

              1 Reply Last reply
              0
              • sierdzioS Offline
                sierdzioS Offline
                sierdzio
                Moderators
                wrote on last edited by
                #8

                Sure, take your time.

                (Z(:^

                1 Reply Last reply
                0
                • U Offline
                  U Offline
                  u2gilles
                  wrote on last edited by
                  #9

                  So, forget about my project. I just would like to validate your method now. So I created a QWidget with just one pushbutton. Then i tried to switch to a QMainWindow by renaming every i could but i can't even compile now. Below are all my files and the compile errors.
                  As you can see, the errors comes from the UIC generated file ui_mainwindow.h which i can't control because Qt Designer does not let me change QWidget to QMainWindow.

                  bid3.pro :
                  @
                  QT += core gui

                  TARGET = bid3
                  TEMPLATE = app

                  SOURCES += main.cpp
                  mainwindow.cpp

                  HEADERS +=
                  mainwindow.h

                  FORMS +=
                  mainwindow.ui
                  @

                  mainwindow.h :
                  @
                  #ifndef MAINWINDOW_H
                  #define MAINWINDOW_H

                  #include <QMainWindow>

                  namespace Ui {
                  class MainWindow;
                  }

                  class MainWindow : public QMainWindow
                  {
                  Q_OBJECT

                  public:
                  explicit MainWindow(QMainWindow *parent = 0);
                  ~MainWindow();

                  private:
                  Ui::MainWindow *ui;
                  };

                  #endif // MAINWINDOW_H

                  @

                  mainwindow.cpp :
                  @
                  #include "mainwindow.h"
                  #include "ui_mainwindow.h"

                  MainWindow::MainWindow(QMainWindow *parent) :
                  QMainWindow(parent),
                  ui(new Ui::MainWindow)
                  {
                  ui->setupUi(this);
                  }

                  MainWindow::~MainWindow()
                  {
                  delete ui;
                  }
                  @

                  main.cpp :
                  @
                  #include <QtGui/QApplication>
                  #include "mainwindow.h"

                  int main(int argc, char *argv[])
                  {
                  QApplication a(argc, argv);
                  MainWindow w;
                  w.show();

                  return a.exec&#40;&#41;;
                  

                  }

                  @

                  mainwindow.ui :
                  @
                  <?xml version="1.0" encoding="UTF-8"?>
                  <ui version="4.0">
                  <class>Widget</class>
                  <widget class="QWidget" name="Widget">
                  <property name="geometry">
                  <rect>
                  <x>0</x>
                  <y>0</y>
                  <width>400</width>
                  <height>300</height>
                  </rect>
                  </property>
                  <property name="windowTitle">
                  <string>Widget</string>
                  </property>
                  <widget class="QPushButton" name="pushButton">
                  <property name="geometry">
                  <rect>
                  <x>160</x>
                  <y>150</y>
                  <width>75</width>
                  <height>23</height>
                  </rect>
                  </property>
                  <property name="text">
                  <string>PushButton</string>
                  </property>
                  </widget>
                  </widget>
                  <layoutdefault spacing="6" margin="11"/>
                  <resources/>
                  <connections/>
                  </ui>

                  @

                  The generated ui_mainwindow.h :
                  @
                  /********************************************************************************
                  ** Form generated from reading UI file 'mainwindow.ui'
                  **
                  ** Created: Fri Oct 19 14:27:11 2012
                  ** by: Qt User Interface Compiler version 4.8.1
                  **
                  ** WARNING! All changes made in this file will be lost when recompiling UI file!
                  ********************************************************************************/

                  #ifndef UI_MAINWINDOW_H
                  #define UI_MAINWINDOW_H

                  #include <QtCore/QVariant>
                  #include <QtGui/QAction>
                  #include <QtGui/QApplication>
                  #include <QtGui/QButtonGroup>
                  #include <QtGui/QHeaderView>
                  #include <QtGui/QPushButton>
                  #include <QtGui/QWidget>

                  QT_BEGIN_NAMESPACE

                  class Ui_Widget
                  {
                  public:
                  QPushButton *pushButton;

                  void setupUi(QWidget *Widget)
                  {
                      if (Widget->objectName().isEmpty())
                          Widget->setObjectName(QString::fromUtf8("Widget"));
                      Widget->resize(400, 300);
                      pushButton = new QPushButton(Widget);
                      pushButton->setObjectName(QString::fromUtf8("pushButton"));
                      pushButton->setGeometry(QRect(160, 150, 75, 23));
                  
                      retranslateUi(Widget);
                  
                      QMetaObject::connectSlotsByName(Widget);
                  } // setupUi
                  
                  void retranslateUi(QWidget *Widget)
                  {
                      Widget->setWindowTitle(QApplication::translate("Widget", "Widget", 0, QApplication::UnicodeUTF8));
                      pushButton->setText(QApplication::translate("Widget", "PushButton", 0, QApplication::UnicodeUTF8));
                  } // retranslateUi
                  

                  };

                  namespace Ui {
                  class Widget: public Ui_Widget {};
                  } // namespace Ui

                  QT_END_NAMESPACE

                  #endif // UI_MAINWINDOW_H
                  @

                  compilation errors :
                  @
                  14:30:26: Running build steps for project bid3...
                  14:30:26: Configuration unchanged, skipping qmake step.
                  14:30:26: Starting: "C:\dev\Qt\mingw\bin\mingw32-make.exe"
                  C:/dev/Qt/mingw/bin/mingw32-make.exe -f Makefile.Debug
                  mingw32-make.exe[1]: Entering directory D:/Source/Cpp/qt5/bid3-build-desktop-Qt_4_8_1_for_Desktop_-_MinGW__Qt_SDK__Debug' g++ -c -g -frtti -fexceptions -mthreads -Wall -DUNICODE -DQT_LARGEFILE_SUPPORT -DQT_DLL -DQT_GUI_LIB -DQT_CORE_LIB -DQT_HAVE_MMX -DQT_HAVE_3DNOW -DQT_HAVE_SSE -DQT_HAVE_MMXEXT -DQT_HAVE_SSE2 -DQT_THREAD_SUPPORT -DQT_NEEDS_QMAIN -I"c:\dev\Qt\Desktop\Qt\4.8.1\mingw\include\QtCore" -I"c:\dev\Qt\Desktop\Qt\4.8.1\mingw\include\QtGui" -I"c:\dev\Qt\Desktop\Qt\4.8.1\mingw\include" -I"c:\dev\Qt\Desktop\Qt\4.8.1\mingw\include\ActiveQt" -I"debug" -I"." -I"..\bid3" -I"." -I"c:\dev\Qt\Desktop\Qt\4.8.1\mingw\mkspecs\win32-g++" -o debug\mainwindow.o ..\bid3\mainwindow.cpp ..\bid3\mainwindow.cpp: In constructor 'MainWindow::MainWindow(QMainWindow*)': ..\bid3\mainwindow.cpp:6: error: invalid use of incomplete type 'struct Ui::MainWindow' ..\bid3\/mainwindow.h:7: error: forward declaration of 'struct Ui::MainWindow' ..\bid3\mainwindow.cpp:8: error: invalid use of incomplete type 'struct Ui::MainWindow' ..\bid3\/mainwindow.h:7: error: forward declaration of 'struct Ui::MainWindow' ..\bid3\mainwindow.cpp: In destructor 'virtual MainWindow::~MainWindow()': ..\bid3\mainwindow.cpp:13: warning: possible problem detected in invocation of delete operator: ..\bid3\mainwindow.cpp:13: warning: invalid use of incomplete type 'struct Ui::MainWindow' ..\bid3\/mainwindow.h:7: warning: forward declaration of 'struct Ui::MainWindow' ..\bid3\mainwindow.cpp:13: note: neither the destructor nor the class-specific operator delete will be called, even if they are declared when the class is defined. mingw32-make.exe[1]: Leaving directory D:/Source/Cpp/qt5/bid3-build-desktop-Qt_4_8_1_for_Desktop_-_MinGW__Qt_SDK__Debug'
                  mingw32-make.exe[1]: *** [debug/mainwindow.o] Error 1
                  mingw32-make.exe: *** [debug] Error 2
                  14:30:28: The process "C:\dev\Qt\mingw\bin\mingw32-make.exe" exited with code 2.
                  Error while building project bid3 (target: Desktop)
                  When executing build step 'Make'
                  @

                  1 Reply Last reply
                  0
                  • sierdzioS Offline
                    sierdzioS Offline
                    sierdzio
                    Moderators
                    wrote on last edited by
                    #10

                    Something is amiss, but sadly my Friday-afternoon brain is not helping :) I will have to investigate myself when I'm more fresh.

                    (Z(:^

                    1 Reply Last reply
                    0
                    • U Offline
                      U Offline
                      u2gilles
                      wrote on last edited by
                      #11

                      Sure. If you want to reproduce it on your computer just :

                      • Create a new Qt Gui Application with base class QWidget
                      • add a push button with Qt Designer
                      • try to switch from QWidget to QMainWindow without deleting the push button.
                        Have a nice week-end and let me know if you see a solution .
                        Thanks again,
                        Gilles
                      1 Reply Last reply
                      0
                      • A Offline
                        A Offline
                        andre
                        wrote on last edited by
                        #12

                        Easiest seems to be a copy-paste operation between two Creator forms. Just create a new form with the base class you want, switch to the class you want to change, select and copy everything, and past into the empty form.

                        Yes, it would be nice to have the option to change the base class for a .ui form, but I never found one.

                        1 Reply Last reply
                        0
                        • sierdzioS Offline
                          sierdzioS Offline
                          sierdzio
                          Moderators
                          wrote on last edited by
                          #13

                          OK, my brain power seems to be restored. I have tried doing this myself as you suggested. I have managed to successfully run the default app after changing it from QWidget to QMainWindow. It works well after steps outlined above (change class inheritance to QMainWindow, change QWidget into QMainWindow in the .ui file), after a full rebuild (and restart of the file in the Designer so that it can pick up those changes). But this results in a bare QMW, different from default you get when creating a new QMW-based project in Qt Creator (status bar and tool bar are missing).

                          In general, I think Andre's suggestion is better here. I have tried this in some of my projects before and it is a pretty good solution. Sometimes it fails, as .ui file parser is quite sensitive, but it produces better results than simple renaming.

                          (Z(:^

                          1 Reply Last reply
                          1
                          • U Offline
                            U Offline
                            u2gilles
                            wrote on last edited by
                            #14

                            Ok, Thanks guys. Andre's method worked (with some more work to copy past the code from my QWidget to the new QMainWindow)

                            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