I have a slot that is triggered by a QFutureWatcher. I'm trying to cast the sender to get the results
QFutureWatcher<QPair<QImage,QString>>* QFW = qobject_cast<QFutureWatcher<QPair<QImage,QString>>*>(sender());
but keep getting
error: static assertion failed: qobject_cast requires the type to have a Q_OBJECT macro
I'm not really sure what's wrong here, these are all Qt built-in types, so what am I doing wrong?
You have to put Q_OBJECT in the Class Definition, like this:
class MyClass : public QObject
{
Q_OBJECT
// ^^^^^^^^^^
public:
MyClass();
/*...*/
}
Related
Hey guys I know there are already some threads for this question but I think I made none of the mistakes others did which led to the problem. So here is my code:
#include "consolerender.h"
consoleRender::consoleRender(QObject *parent) :
QObject(parent) {
connect(Enviroment::instance, &Enviroment::enviromentChanged,
this, &consoleRender::renderField);
}
And the header:
class consoleRender : public QObject
{
Q_OBJECT
public:
explicit consoleRender(QObject *parent = 0);
public slots:
void renderField();
};
And the Enviroment.h
class Enviroment : public QObject
{
Q_OBJECT
public:
static Enviroment& instance();
virtual ~Enviroment();
//stuff...
signals:
void enviromentChanged();
I already tried to do the connect in a separate class, I tried to use the old connect syntax (SIGNAL/SLOT(function)) and tried it with >>all<< my classes inheriting from QObject but it showed the same error. Also it says something that the function expects 3 arguments but gets 4. and seems to point at the connect(...renderField). I heard of a solution to just do all of that in the MainWindow class but that is not an option for me.
You have to pass the instance pointer:
connect(&Enviroment::instance(), &Enviroment::enviromentChanged,
this, &consoleRender::renderField);
I have a class MyClass with:
- private:
pushButton *button;
void connectSignalAndSlot();
- private slot:
void buttonAction();
I want to connect these in MyClass using connectSignalAndSlot(), like so:
void MyClass::connectSignalAndSlot()
{
QObject::connect(button,SIGNAL(clicked()),this,SLOT(buttonAction()));
}
This gives me an error of
no matching function for call to 'QObject::connect(QPushButton*&, const char*, MyClass* const, const char*)';
If I inherit QObject with MyClass, the program compiles and starts, but then I get the following issues displayed in my Application Output pane:
QObject::connect: No such slot QObject::buttonAction() in ..\MyProject\myclass.cpp:48
Do I have to make the button and slot public and use them in the MainWindow class only? Is there no way to keep this at the MyClass level?
Thanks for your help!
You must have MyClass inherit from QObject AND add Q_OBJECT macro in your MyClass definition (header file) to have slots/signals work.
class MyClass : public QObject
{
Q_OBJECT
public:
....
};
Inheriting QObject is the right way, but your still missing Qt-Meta Object Code. Your header-file for your class should look like this:
#ifndef MYCLASS_H
#define MYCLASS_H
class MyClass : public QObject {
Q_OBJECT
// your methods, variables, slots and signals
}
#endif
Don't forget to create the moc file, the easiest way is to use qmake or the QtCreator IDE.
This class no problem:
#include <QThread>
class LiveImageItem : public QThread
{
Q_OBJECT
public:
LiveImageItem(QPixmap pimg);
signals:
public slots:
};
BUT this class get problem associated with "Q_OBJECT" macro defined in header file
#include <QGraphicsPixmapItem>
class LiveImageItem : public QGraphicsPixmapItem
{
Q_OBJECT //this line will generate many errors in compiling
public:
LiveImageItem(QPixmap pimg);
signals:
public slots:
};
both their cpp file is the same:
#include "LiveImageItem.h"
LiveImageItem::LiveImageItem(QPixmap pimg)
{
}
I thought every QT object essentially inherited from QObject so if I inherit any of the subclass of QObject, I could have all the magics QObject offers. The 2nd version of the above (which is inherited from, say, QGraphicsPixmapItem) seems proved I was wrong. It turns out to be having lots of errors while compiling, all from moc files(automatically generated by QT). What happens?
Some of these errors are:
[qobject.h] error: 'QScopedPointer QObject::d_ptr' is
protected
[moc_LiveImageItem.cpp] error: within this context
...
According to the documentation QGraphicsPixmapItem is not a QObject, thus you cannot treat it as if it is. I would try to extend your class inheritance and do:
class LiveImageItem : public QObject, public QGraphicsPixmapItem
{
Q_OBJECT //this line will generate many errors in compiling
[..]
As #vahancho said, QGraphicsPixmapItem is not a QObject. In fact, that can be said of most of the QGraphics*Item classes.
However, if you want to use signals and slots with QGraphicsSystem classes, you can inherit from QGraphicsObject: -
class LiveImageItem : public QGraphicsObject
{
Q_OBJECT
public:
private:
QPixmap m_pixmap;
};
You would then override the paint function in this class and draw the pixmap from there.
Here is my sample code:
class hoho : public QObject
{
Q_OBJECT
public:
hoho()
{
httpFetch = new HttpFetch(QUrl("http://www.google.com/"));
connect(httpFetch, SIGNAL(Fetched()), this, SLOT(PrintData(QByteArray)));
}
void PrintData(QByteArray http)
{
qDebug()<<http;
}
HttpFetch *httpFetch;
};
When I try to compile this, following error pops up
1>main.cpp(15): error C2243: 'type cast' : conversion from 'HttpFetch *' to 'const QObject *' exists, but is inaccessible
This error comes as the class is derived from QObject (which is necessary for signal and slot mechanism).
Can anyone tell me how to fix this?
You probably did not derive HttpFetch publicly, but privately from QObject. So just change
class HttpFetch : QObject { // ...
to
class HttpFetch : public QObject { // ...
and it should work.
If your design requires to make the inheritance non-public (I had this requirement because I inherited from a QWidget for a multithreading purpose and didn't want to expose all functions to the user), you can do this:
class FilesQueueQList : protected QWidget
{
Q_OBJECT
public:
using QWidget::QObject; //This is the solution!
//...
}
Now the members of QWidget are private/protected, but QObject is accessible as public.
Did you forget the Q_OBJECT macro in your class HttpFetch ?
Can I see your class HttpFetch ?
g++ is reporting a parse error with the code below:
class Sy_timeLineDelegateScene : public QGraphicsScene
{
Q_OBJECT
public:
Sy_timeLineDelegateScene( Sy_animPropertyTimeLine* timeline,
Sy_animClock* clock,
QObject* parent = nullptr );
virtual ~Sy_timeLineDelegateScene() {}
protected slots: // Parse error at ":"
typedef QMap< Sy::Frame, Sy_timeLineDelegateKey* > DelegateTimeLine;
...
My class is derived from QObject and I have declared the Q_OBJECT macro before the error, but if I comment out the slots part, it compiles fine. I have used Qt for years and never seen this before, it must be something stupid, but I can't see what's causing the problem.
The "slots" and "signals" sections in a class definition should only contain functions; neither types nor member variables.
You should move the typedef in a public, protected or private section:
class Sy_timeLineDelegateScene : public QGraphicsScene
{
Q_OBJECT
public:
Sy_timeLineDelegateScene( Sy_animPropertyTimeLine* timeline,
Sy_animClock* clock,
QObject* parent = nullptr );
virtual ~Sy_timeLineDelegateScene() {}
typedef QMap< Sy::Frame, Sy_timeLineDelegateKey* > DelegateTimeLine;
protected slots:
...