finiteloop
finiteloop

Reputation: 4496

Why is the Q_OBJECT macro causing issues (Qt)?

I am running QtCreator in OSX Lion, and anytime I create a class that requires the Q_OBJECT macro, I get an error when I try to build my application. The code for that class is below, as is the error I am recieving. Any clue what may be going on?

Note: I have already tried cleaning, running qmake and re-building to no avail.

#ifndef TASKLIST_H
#define TASKLIST_H

#include <QObject>

class TaskList : public QObject
{
    Q_OBJECT
public:
    explicit TaskList(QObject *parent = 0 );

public slots:
    void addTask();
    void displayTasks();
};

#endif // TASKLIST_H

And the error:

:-1: error: symbol(s) not found for architecture x86_64

:-1: error: collect2: ld returned 1 exit status

Upvotes: 4

Views: 3041

Answers (2)

vsz
vsz

Reputation: 4893

There still seems to be a bug in Qt Creator.

I have a large project with a number of classes all having Q_OBJECT and another number of classes not having Q_OBJECT. It works fine. However, if I add Q_OBJECT to one of the classes which didn't have it, I get this "collect2: ld returned 1 exit status" error when trying to build it.

Checking the build directory, I see that the moc file for this class is missing. Qt just does not create the moc files for it! However, if I remove the header and cpp files from the project and add them again, it works, the moc files are generated and the project is built successfully.

This problem seems to happen only if I have a class which did not have Q_OBJECT and it was built succesfully in the past. A fresh class with Q_OBJECT that was never compiled before adding "Q_OBJECT" always works fine.

So, if this problem happens and you are sure you included everything correctly (and commenting out Q_OBJECT lets the project to be built correctly), do the following:

  • remove the .h and .cpp files (where you just added the Q_OBJECT) from the project.
  • add them to the project again
  • clean project
  • build it again.

EDIT

In some cases running qmake (Build/Run qmake) followed by a Clean All is enough.

Upvotes: 6

Dmitriy Kachko
Dmitriy Kachko

Reputation: 2914

tasklist.h file

   #ifndef TASKLIST_H
    #define TASKLIST_H

    #include <QObject>

    class TaskList : public QObject
    {
        Q_OBJECT
    public:
        explicit TaskList(QObject *parent = 0 );

    public slots:
        void addTask(){};
        void displayTasks(){};
    };

    #endif // TASKLIST_H

tasklist.cpp

   #include "tasklist.h"

    TaskList::TaskList(QObject *parent) :
        QObject(parent)
    {
    }

main.cpp

#include <QtCore/QCoreApplication>
#include "tasklist.h"


int main(int argc, char *argv[])
{
    QCoreApplication a(argc, argv);
    TaskList t;
    return a.exec();
}

works fine, but it should be in separate files

Upvotes: 0

Related Questions