如何从 QML 访问在 C++ class 中声明的 Q_ENUM?
How to access a Q_ENUM declared in C++ class from QML?
我在 MyClass
中声明了一个 Q_ENUM
,如下所示:
class MyClass {
public:
enum Enum_Test {
eTestA,
eTestB
}
Q_ENUM(Enum_Test)
Q_OBJECT
Q_PROPERTY(MyClass::Enum_Test enumTest READ GetEnumTest WRITE SetEnumTest )
}
我已经 MyClass
像下面这样在 QML 端注册并且能够访问它。
auto my_class = std::make_shared<MyClass>();
qmlRegisterUncreatableType<MyClass>("MyClass", 1,0, "MyClass","Cannot create type MyClass in QML");
rootContext()->setContextProperty("my_class", my_class.get());
如何从 QML 访问 Q_ENUM Enum_Test
?
您的 class 需要进行两次调整。
正如JarMan所指出的,它需要一个metaObject,可以通过从QObject派生并添加Q_OBJECT:
来获得
class MyClass : public QObject
{
Q_Object
...
}
其实用Q_GADGET
也是可以的,不过你好像已经倾向于Q_OBJECT
了。但是,按照要求,我们开始吧:
class 我的班级
{
Q_GADGET
public:
enum Enum_Test {
ETestA,
ETestB
}
Q_ENUM(Enum_Test)
};
请记住 Q_GADGET cannot have signals,所以我省略了 属性,只有这个 class 作为“枚举占位符”。
枚举值名称需要大写:
enum Enum_Test {
ETestA,
ETestB
}
Q_ENUM(Enum_Test)
然后您可以在 QML 中将其用作:
QtObject {
property int myEnumVal: MyClass.ETestA
}
请注意,由于与 JavaScript 的混合,对枚举的支持有些有限。这些值将被转换为整数。此外,当在 JavaScript 开关语句中使用时,QtCreator(假设版本 4.14)不会警告拼写错误
@Amfasis 提供的答案已经很好了。因为我经常这样做,所以我写了一个小快捷方式来定义枚举,其中包含 Qt 提供的所有功能,包括 QML 中的可用性:https://github.com/carlonluca/lqtutils#lqtutils_enumh.
您只需要包含 header,定义您的枚举值,例如:
L_DECLARE_ENUM(Enum_Test,
ETestA,
ETestB
)
并在您喜欢的地方注册:
Enum_Test::qmlRegisterMySharedEnum("some.uri", 1, 0);
此外,这使用简单的名称空间,比使用 QObject 或小工具更轻便。
实际上,当我使用 Qt 时,我习惯了总是这样声明我的枚举,因为我也可以从 QMetaEnum 中受益。例如,我真的很喜欢这样记录:
qDebug() << "Value:" << Enum_Test::ETestA;
得到:
Value: Enum_Test::ETestA
而不是简单的整数。
我在 MyClass
中声明了一个 Q_ENUM
,如下所示:
class MyClass {
public:
enum Enum_Test {
eTestA,
eTestB
}
Q_ENUM(Enum_Test)
Q_OBJECT
Q_PROPERTY(MyClass::Enum_Test enumTest READ GetEnumTest WRITE SetEnumTest )
}
我已经 MyClass
像下面这样在 QML 端注册并且能够访问它。
auto my_class = std::make_shared<MyClass>();
qmlRegisterUncreatableType<MyClass>("MyClass", 1,0, "MyClass","Cannot create type MyClass in QML");
rootContext()->setContextProperty("my_class", my_class.get());
如何从 QML 访问 Q_ENUM Enum_Test
?
您的 class 需要进行两次调整。
正如JarMan所指出的,它需要一个metaObject,可以通过从QObject派生并添加Q_OBJECT:
来获得class MyClass : public QObject { Q_Object ... }
其实用
Q_GADGET
也是可以的,不过你好像已经倾向于Q_OBJECT
了。但是,按照要求,我们开始吧:class 我的班级 { Q_GADGET
public: enum Enum_Test { ETestA, ETestB } Q_ENUM(Enum_Test)
};
请记住 Q_GADGET cannot have signals,所以我省略了 属性,只有这个 class 作为“枚举占位符”。
枚举值名称需要大写:
enum Enum_Test { ETestA, ETestB } Q_ENUM(Enum_Test)
然后您可以在 QML 中将其用作:
QtObject {
property int myEnumVal: MyClass.ETestA
}
请注意,由于与 JavaScript 的混合,对枚举的支持有些有限。这些值将被转换为整数。此外,当在 JavaScript 开关语句中使用时,QtCreator(假设版本 4.14)不会警告拼写错误
@Amfasis 提供的答案已经很好了。因为我经常这样做,所以我写了一个小快捷方式来定义枚举,其中包含 Qt 提供的所有功能,包括 QML 中的可用性:https://github.com/carlonluca/lqtutils#lqtutils_enumh.
您只需要包含 header,定义您的枚举值,例如:
L_DECLARE_ENUM(Enum_Test,
ETestA,
ETestB
)
并在您喜欢的地方注册:
Enum_Test::qmlRegisterMySharedEnum("some.uri", 1, 0);
此外,这使用简单的名称空间,比使用 QObject 或小工具更轻便。
实际上,当我使用 Qt 时,我习惯了总是这样声明我的枚举,因为我也可以从 QMetaEnum 中受益。例如,我真的很喜欢这样记录:
qDebug() << "Value:" << Enum_Test::ETestA;
得到:
Value: Enum_Test::ETestA
而不是简单的整数。