Inheriting subclasses can not use Q_OBJECT

3.1k views Asked by At

I have a big problem with my classes: I will use the Q_OBJECT macro in my subclasses. But if I define Q_OBJECT in my subclasses, it throws an exception. This is the exception:

undefined reference to `vtable for SubClassOne'
undefined reference to `vtable for SubClassTwo'

My SubClassOne and SubClassTwo inherits from BaseClass.

Here some Code: (All #includes are correct)

\\baseclass.h
class BaseClass
{
public:
BaseClass(QWidget *widget=0);
QHBoxLayout *mainLayout;
};

\\subclassone.h
class SubClassOne : public BaseClass, public QWidget
{
 Q_OBJECT
public:
   explicit SubClassOne(QWidget *widget=0);
};

\\subclasstwo.h
class SubClassTwo : public BaseClass, public QDialog
{
 Q_OBJECT
public:
    explicit SubClassTwo(QWidget *dialog=0);
};

Here comes the .cpp Files

//baseclass.cpp
BaseClass::BaseClass(QWidget *widget)
{
 mainLayout = new QHBoxLayout();
}

//subclassone.cpp
SubClassOne::SubClassOne(QWidget *widget):BaseClass(widget)
{
 setWindowTitle("Widget");
}

//subclasstwo.cpp
SubClassTwo::SubClassTwo(QWidget *dialog):BaseClass(dialog)
{
setWindowTitle("Dialog");

QPushButton *btn = new QPushButton();
QObject::connect(btn,SIGNAL(clicked()),SLOT(close()));
mainLayout->addWidget(btn);
setLayout(mainLayout);
}

main.cpp

int main(int argc, char *argv[])
{
QApplication a(argc, argv);
SubClassTwo *s = new SubClassTwo();
s->show();
return a.exec();
}

How can I use Q_OBJECT in my subclasses?

2

There are 2 answers

7
László Papp On BEST ANSWER

Your Q_OBJECT placement is fine in your code.

What you are hitting is that you forgot to include the generated moc file in your source such as:

baseclass.cpp (at the end of the file)

#include "baseclass.moc"

subclassone.cpp (at the end of the file)

#include "subclassone.moc"

subclasstwo.cpp (at the end of the file)

#include "subclasstwo.moc"

You need to make sure moc is generating these files for you though. You have not shown your buildsystem yet.

Also, please make sure to have one header and source file per "Q_OBJECT" classes. It is not strictly necessary, but it is a good practice.

You can of course resolve that at link time as well, but you will need to do either of those.

Moreover, once you have multiple inheritance, at least with Qt 4, you will need to inherit from the QObject subclass first, which is QWidget in your case. You can find the correct inheritance below.

subclassone.h

class SubClassOne : public QWidget, public BaseClass

subclasstwo.h

class SubClassTwo : public QDialog, public BaseClass

etc. Hope it helps.

0
ratchet freak On

Q_OBJECT must be the firs declaration in your class and any class inheriting QObject must be first in the list

class SubClassOne : public QWidget, public BaseClass
{
Q_OBJECT
public:
   explicit SubClassOne(QWidget *widget=0);
};

\\subclasstwo.h
class SubClassTwo : public QDialog, public BaseClass
{
Q_OBJECT
public:
    explicit SubClassTwo(QWidget *dialog=0);
};

you also need to run the moc on the header to generate the code needed to implement the slots and signals