打印 Qt 属性 枚举值作为键字符串
Printing a Qt property enum value as a key string
我有一个 QML Loader
,在某些情况下我想打印它的 status
属性,但我在控制台上得到 0
,即使我使用 toString()
。所以我需要始终参考 qquickloader_p.h 中枚举值的顺序以了解发生了什么。
还有其他方法吗?
唯一的其他方法是从使用 moc 生成的元数据查找枚举名称的 C++ 助手访问 属性。另见 。
与使用整数相比,使用 ENUM 可以使代码更具可读性,但比使用字符串更快。
他们的目的主要是比较。
如果你想要它的名字,你需要创建额外的结构(例如数组)来查找它们。通常这不是必须的,所以效率更高,不做。
如果你查看 console.log(typeof(Loader.Ready))
你会发现,ENUM
确实只不过是一个 number
- 也许还有一些元对象信息。
由于 MetaObject,有一种方法,即使不舒服...问题是,您需要知道 ENUM
的名称
enumspy.h
#ifndef ENUMSPY_H
#define ENUMSPY_H
#include <QObject>
class EnumSpy: public QObject
{
Q_OBJECT
public:
EnumSpy(QObject* parent = nullptr);
public slots:
QString getEnumName(QObject* object, QString name, int index) const;
};
#endif // ENUMSPY_H
enumspy.cpp
#include <QMetaObject>
#include <QMetaEnum>
#include <QDebug>
#include "enumspy.h"
EnumSpy::EnumSpy(QObject* parent)
: QObject(parent)
{
}
QString EnumSpy::getEnumName(QObject *object, QString name, int index) const
{
const QMetaObject* meta = object->metaObject();
QMetaEnum enm = meta->enumerator(meta->indexOfEnumerator(&name.toStdString()[0]));
qDebug() << meta;
return QString(enm.key(index));
}
注册,创建对象,调用方法
Note: The name for the ENUMs of the Loader is Status
myEnumSpy.getEnumName(myLoaderInstance, 'Status', 1) => "Ready"
实际上有一种方法可以在不知道甚至不传递枚举名称的情况下获取枚举密钥,如果以下语法满足您的需要:
Info.print(loader, "status")
你可以通过这个获取:
#include <QMetaType>
#include <QMetaProperty>
#include <QMetaEnum>
#include <QObject>
#include <QDebug>
class EnumInfo : public QObject {
Q_OBJECT
public slots:
void print(QObject * obj, QString prop) {
const QMetaObject * meta = obj->metaObject();
int i = meta->indexOfProperty(qUtf8Printable(prop));
if (i > -1) {
QMetaProperty p = meta->property(i);
if (p.isEnumType()) {
QMetaEnum en = p.enumerator();
qDebug() << en.name() << ":" << en.key(obj->property(p.name()).toInt());
}
}
}
};
该对象最好作为单例暴露给 QML,尽管对于更随意的使用,上下文 属性 不会有太多开销。
我有一个 QML Loader
,在某些情况下我想打印它的 status
属性,但我在控制台上得到 0
,即使我使用 toString()
。所以我需要始终参考 qquickloader_p.h 中枚举值的顺序以了解发生了什么。
还有其他方法吗?
唯一的其他方法是从使用 moc 生成的元数据查找枚举名称的 C++ 助手访问 属性。另见
与使用整数相比,使用 ENUM 可以使代码更具可读性,但比使用字符串更快。
他们的目的主要是比较。
如果你想要它的名字,你需要创建额外的结构(例如数组)来查找它们。通常这不是必须的,所以效率更高,不做。
如果你查看 console.log(typeof(Loader.Ready))
你会发现,ENUM
确实只不过是一个 number
- 也许还有一些元对象信息。
由于 MetaObject,有一种方法,即使不舒服...问题是,您需要知道 ENUM
enumspy.h
#ifndef ENUMSPY_H
#define ENUMSPY_H
#include <QObject>
class EnumSpy: public QObject
{
Q_OBJECT
public:
EnumSpy(QObject* parent = nullptr);
public slots:
QString getEnumName(QObject* object, QString name, int index) const;
};
#endif // ENUMSPY_H
enumspy.cpp
#include <QMetaObject>
#include <QMetaEnum>
#include <QDebug>
#include "enumspy.h"
EnumSpy::EnumSpy(QObject* parent)
: QObject(parent)
{
}
QString EnumSpy::getEnumName(QObject *object, QString name, int index) const
{
const QMetaObject* meta = object->metaObject();
QMetaEnum enm = meta->enumerator(meta->indexOfEnumerator(&name.toStdString()[0]));
qDebug() << meta;
return QString(enm.key(index));
}
注册,创建对象,调用方法
Note: The name for the ENUMs of the Loader is
Status
myEnumSpy.getEnumName(myLoaderInstance, 'Status', 1) => "Ready"
实际上有一种方法可以在不知道甚至不传递枚举名称的情况下获取枚举密钥,如果以下语法满足您的需要:
Info.print(loader, "status")
你可以通过这个获取:
#include <QMetaType>
#include <QMetaProperty>
#include <QMetaEnum>
#include <QObject>
#include <QDebug>
class EnumInfo : public QObject {
Q_OBJECT
public slots:
void print(QObject * obj, QString prop) {
const QMetaObject * meta = obj->metaObject();
int i = meta->indexOfProperty(qUtf8Printable(prop));
if (i > -1) {
QMetaProperty p = meta->property(i);
if (p.isEnumType()) {
QMetaEnum en = p.enumerator();
qDebug() << en.name() << ":" << en.key(obj->property(p.name()).toInt());
}
}
}
};
该对象最好作为单例暴露给 QML,尽管对于更随意的使用,上下文 属性 不会有太多开销。