error: allocation of incomplete type ....
-
I am asking somebody to help me to identify the SOURCE of my error.
This is a second time I am trying to modify QT example "simple terminal" to include in my sub project.
I am unable to FIND the source of my error.I have loaded the example and RENAMED the .cpp,.h.ui files and changed the class name , and redirected the necessary .h and .ui files.
I just cannot see what I have missed...
I do realize I need to POST the actual source BUT I do not want to do that until I receive a positive reply to this initial post !
/mnt/A_BT_DEC10/BT__PROGRAMS/A_MAR7_MAR15/A_BT_LIBRARY/CCC_SOURCE/BT_TERMINAL/terminal/mainwindow_TERMINAL_ORIGINAL.cpp:67: error: allocation of incomplete type 'Ui::MainWindow_TERMINAL_ORIGINAL'
mainwindow_TERMINAL_ORIGINAL.cpp:67:14: error: allocation of incomplete type 'Ui::MainWindow_TERMINAL_ORIGINAL'
m_ui(new Ui::MainWindow_TERMINAL_ORIGINAL),
^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
./mainwindow_TERMINAL_ORIGINAL.h:66:7: note: forward declaration of 'Ui::MainWindow_TERMINAL_ORIGINAL'
class MainWindow_TERMINAL_ORIGINAL;
^OK, just as a gesture of good will
here is my header file
#ifndef MAINWINDOW_TERMINAL_ORIGINAL_H_ #define MAINWINDOW_TERMINAL_ORIGINAL_H_ // ?? #include "ui_mainwindow_TERMINAL_ORIGINAL.h" #include "./ui_mainwindow_TERMINAL_ORIGINAL.h" #include <QMainWindow> #include <QSerialPort> QT_BEGIN_NAMESPACE class QLabel; namespace Ui { class MainWindow_TERMINAL_ORIGINAL; } QT_END_NAMESPACE class Console; class SettingsDialog; class MainWindow_TERMINAL_ORIGINAL : public QMainWindow { Q_OBJECT public: explicit MainWindow_TERMINAL_ORIGINAL(QWidget *parent = nullptr); ~MainWindow_TERMINAL_ORIGINAL(); private slots: void openSerialPort(); void closeSerialPort(); void about(); void writeData(const QByteArray &data); void readData(); void handleError(QSerialPort::SerialPortError error); private: void initActionsConnections(); private: void showStatusMessage(const QString &message); Ui::MainWindow_TERMINAL_ORIGINAL *m_ui = nullptr; QLabel *m_status = nullptr; Console *m_console = nullptr; SettingsDialog *m_settings = nullptr; QSerialPort *m_serial = nullptr; }; #endif // MAINWINDOW_H
Thanks
-
@AnneRanch
The file you show is presumablymainwindow_TERMINAL_ORIGINAL.h
--- or is it some other file? But error message./mainwindow_TERMINAL_ORIGINAL.h:66:7: note: forward declaration of 'Ui::MainWindow_TERMINAL_ORIGINAL'
says that file has 66 lines, and I make what you posted have at most 56 lines. So is the file you show actually the one being read?
-
The error is raised at line 67 of
mainwindow_TERMINAL_ORIGINAL.cpp
. Please show all lines up to & including that line from that.cpp
file. -
The file
ui_mainwindow_TERMINAL_ORIGINAL.h
whichmainwindow_TERMINAL_ORIGINAL.h
includes is supposed to be generated and located in the build output directory, not the source directory (e.g. where you havemainwindow_TERMINAL_ORIGINAL.h
). If you have a file namedui_mainwindow_TERMINAL_ORIGINAL.h
in that source directory it will go wrong. Do you have such a file there, it has happened to you before? And in the file you show you have
#include "ui_mainwindow_TERMINAL_ORIGINAL.h" #include "./ui_mainwindow_TERMINAL_ORIGINAL.h"
I do not recognise where the second of those lines comes from, or why you would have two.
- Whichever
ui_mainwindow_TERMINAL_ORIGINAL.h
it is actually including, can you go look at at least the start of it. If you did correct renaming it will define a class namedMainWindow_TERMINAL_ORIGINAL
now. However, if you did not do the full job it will probably be left defining a class namedMainWindow_TERMINAL
, and that would give rise to such an error.
-
-
Renaming a Qt Widget class with its own ui file is never a trivial task. There's a lot of magic code generating happening on Qt/uic side that is easily broken because not everything is always regenerated on each compile. An imperfect system for sure.
That said, did you add the renamed ui file to the FORMS inside you pro file, assuming you're using qmake and not cmake?
FORMS += \ MainWindow_TERMINAL_ORIGINAL.ui //presumably. Case shouldn't matter on windows, but does on linux
without it, the compiler won't generate obj files for your gui-header
ui_mainwindow_TERMINAL_ORIGINAL.h
and you will get anincomplete type
type error -
@J-Hilk
Thanks for all replies.Here is my modified .pro
QT += widgets serialport requires(qtConfig(combobox)) TARGET = terminal TEMPLATE = lib SOURCES += \ main.cpp \ mainwindow_TERMINAL_ORIGINAL.cpp \ settingsdialog.cpp \ console.cpp HEADERS += \ mainwindow_TERMINAL_ORIGINAL.h \ settingsdialog.h \ console.h FORMS += \ mainwindow_TERMINAL_ORIGINAL.ui \ settingsdialog.ui RESOURCES += \ terminal.qrc target.path = $$[QT_INSTALL_EXAMPLES]/serialport/terminal INSTALLS += target message(" add Mar19 original simple terminal code ") message(" changed to lib ")
-
@AnneRanch Thanks. So did you look at my third point?
-
@JonB Here is .cpp - minus the "credit lines"
One of the errors gives " note forward declaration" which just enforces " incomplete type" errors...
It is still unclear where is this "missing type"....
//#include "mainwindow.h" // renamed #include "mainwindow_TERMINAL_ORIGINAL.h" #include "ui_mainwindow_TERMINAL_ORIGINAL.h" //#include "ui_mainwindow.h" #include "console.h" #include "settingsdialog.h" #include <QLabel> #include <QMessageBox> //! [0] MainWindow_TERMINAL_ORIGINAL::MainWindow_TERMINAL_ORIGINAL(QWidget *parent) : QMainWindow(parent), m_ui(new Ui::MainWindow_TERMINAL_ORIGINAL), m_status(new QLabel), m_console(new Console), m_settings(new SettingsDialog), //! [1] m_serial(new QSerialPort(this)) //! [1] { //! [0] m_ui->setupUi(this); m_console->setEnabled(false); setCentralWidget(m_console); m_ui->actionConnect->setEnabled(true); m_ui->actionDisconnect->setEnabled(false); m_ui->actionQuit->setEnabled(true); m_ui->actionConfigure->setEnabled(true); m_ui->statusBar->addWidget(m_status); initActionsConnections(); connect(m_serial, &QSerialPort::errorOccurred, this, &MainWindow_TERMINAL_ORIGINAL::handleError); //! [2] connect(m_serial, &QSerialPort::readyRead, this, &MainWindow_TERMINAL_ORIGINAL::readData); //! [2] connect(m_console, &Console::getData, this, &MainWindow_TERMINAL_ORIGINAL::writeData); //! [3] } //! [3] MainWindow_TERMINAL_ORIGINAL::~MainWindow_TERMINAL_ORIGINAL() { delete m_settings; delete m_ui; } //! [4] void MainWindow_TERMINAL_ORIGINAL::openSerialPort() { const SettingsDialog::Settings p = m_settings->settings(); m_serial->setPortName(p.name); m_serial->setBaudRate(p.baudRate); m_serial->setDataBits(p.dataBits); m_serial->setParity(p.parity); m_serial->setStopBits(p.stopBits); m_serial->setFlowControl(p.flowControl); if (m_serial->open(QIODevice::ReadWrite)) { m_console->setEnabled(true); m_console->setLocalEchoEnabled(p.localEchoEnabled); m_ui->actionConnect->setEnabled(false); m_ui->actionDisconnect->setEnabled(true); m_ui->actionConfigure->setEnabled(false); showStatusMessage(tr("Connected to %1 : %2, %3, %4, %5, %6") .arg(p.name).arg(p.stringBaudRate).arg(p.stringDataBits) .arg(p.stringParity).arg(p.stringStopBits).arg(p.stringFlowControl)); } else { QMessageBox::critical(this, tr("Error"), m_serial->errorString()); showStatusMessage(tr("Open error")); } } //! [4] //! [5] void MainWindow_TERMINAL_ORIGINAL::closeSerialPort() { if (m_serial->isOpen()) m_serial->close(); m_console->setEnabled(false); m_ui->actionConnect->setEnabled(true); m_ui->actionDisconnect->setEnabled(false); m_ui->actionConfigure->setEnabled(true); showStatusMessage(tr("Disconnected")); } //! [5] void MainWindow_TERMINAL_ORIGINAL::about() { QMessageBox::about(this, tr("About Simple Terminal"), tr("The <b>Simple Terminal</b> example demonstrates how to " "use the Qt Serial Port module in modern GUI applications " "using Qt, with a menu bar, toolbars, and a status bar.")); } //! [6] void MainWindow_TERMINAL_ORIGINAL::writeData(const QByteArray &data) { m_serial->write(data); } //! [6] //! [7] void MainWindow_TERMINAL_ORIGINAL::readData() { const QByteArray data = m_serial->readAll(); m_console->putData(data); } //! [7] //! [8] void MainWindow_TERMINAL_ORIGINAL::handleError(QSerialPort::SerialPortError error) { if (error == QSerialPort::ResourceError) { QMessageBox::critical(this, tr("Critical Error"), m_serial->errorString()); closeSerialPort(); } } //! [8] void MainWindow_TERMINAL_ORIGINAL::initActionsConnections() { connect(m_ui->actionConnect, &QAction::triggered, this, &MainWindow_TERMINAL_ORIGINAL::openSerialPort); connect(m_ui->actionDisconnect, &QAction::triggered, this, &MainWindow_TERMINAL_ORIGINAL::closeSerialPort); connect(m_ui->actionQuit, &QAction::triggered, this, &MainWindow_TERMINAL_ORIGINAL::close); connect(m_ui->actionConfigure, &QAction::triggered, m_settings, &SettingsDialog::show); connect(m_ui->actionClear, &QAction::triggered, m_console, &Console::clear); connect(m_ui->actionAbout, &QAction::triggered, this, &MainWindow_TERMINAL_ORIGINAL::about); connect(m_ui->actionAboutQt, &QAction::triggered, qApp, &QApplication::aboutQt); } void MainWindow_TERMINAL_ORIGINAL::showStatusMessage(const QString &message) { m_status->setText(message); }
-
@AnneRanch
I still suggest it's likely to be the 3rd (or 2nd) point. When you renamed, did you go not just rename the.ui
file but also go into editing it and change the class name inside it? -
@JonB OK. it is back to "how is "ui_...h " created / build and where .
My next logical step will be to let Qt build "QDialog " project and add it to my sub project. From scratch and see how it actually builds "ui_.h" header AND WHERE .
That may resolve my missing step...
-
@AnneRanch
This is a guess, but your behaviour would be explained if: you look at the top few lines (about line #20) of theui_mainwindow_TERMINAL_ORIGINAL.h
file, wherever you are including it from. If that still showsclass Ui_mainwindow_TERMINAL
instead of the intendedclass Ui_mainwindow_TERMINAL_ORIGINAL
that should cause the error message you showed.BTW: The build process always places the generated
ui_....h
file in the build output directory, like../build-yourprojectname-Desktop-Debug
. If you copy it into your source directory, or somehow a file of that name ends up there, it will go wrong as you update the.ui
file. -
@AnneRanch UPDATE / GOTCHA
When reusing (C++ "feature") project in subproject one better change / rename "MainWindow" class name. .I start with renaming the existing class header file. QtCreator gives an option to rename both .cpp and .ui
BUT you must start with renaming the header file FIRST.Then you can rename the MainWindow class and that will change the "object" name in .ui file! l
Another "GOTCHA" - the #include ui_ file , generated from .ui file MUST be changed manually !
Good luck...