I have a custom struct
which I use as a Q_PROPERTY
type in a QMediaPlayer
derived class. But here's the code:
struct VideoMeta
{
Q_GADGET
Q_PROPERTY(int width MEMBER width)
Q_PROPERTY(...)
....
public:
int width;
...
};
Q_DECLARE_METATYPE(VideoMeta)
class FrameProvider : public QMediaPlayer
{
Q_OBJECT
Q_PROPERTY(VideoMeta videoMeta READ getVideoMeta WRITE setVideoMeta NOTIFY videoLoaded)
VideoMeta m_videoMeta;
...
}
And I use it in a Label
:
Label {
text: "Cached frames: " + cacheLoaded + " / " + frameProvider.videoMeta.framecount
}
This works like charm but here comes the twist:
If I copy and paste the declaration of the struct
into a separate header file (and obviously included it) with the Q_DECLARE_METATYPE
macro, I get the following error:
QMetaProperty::read: Unable to handle unregistered datatype 'VideoMeta' for property 'FrameProvider::videoMeta'
So I have two questions:
Q_DECLARE_METATYPE
macro, if the documentation says that I don't need it with the Q_GADGET
macro because it automatically registers the type?Thanks in advance!
EDIT:
This might be relevant: I use Qt v5.15 in a Visual Studio (MSVC v142) project. (Not in Qt Creator.)
Q_GADGET
main usage is to allow a non QObject type to have introspection.
The Q_GADGET macro is a lighter version of the Q_OBJECT macro for classes that do not inherit from QObject but still want to use some of the reflection capabilities offered by QMetaObject. Just like the Q_OBJECT macro, it must appear in the private section of a class definition.
Q_GADGETs can have Q_ENUM, Q_PROPERTY and Q_INVOKABLE, but they cannot have signals or slots.
Q_GADGET makes a class member, staticMetaObject, available. staticMetaObject is of type QMetaObject and provides access to the enums declared with Q_ENUMS.
It does not say anything about registering the type.
Also Q_DECLARE_METATYPE
does not register a type, but declares it.
To register VideoMeta
you need to call qRegisterMetaType<VideoMeta>()
.
Qt documentation specifically states that qRegisterMetaType<T>()
must be called for a type to work in the Qt property system.
Also, to use type T with the QObject::property() API, qRegisterMetaType() must be called before it is used, typically in the constructor of the class that uses T, or in the main() function.
See https://doc.qt.io/qt-5/qmetatype.html#qRegisterMetaType-1