我有一个继承自 QObject 并具有 Q_OBJECT 宏的类:
class SomeClass: public QObject
{
Q_OBJECT
public:
SomeClass(QObject *parent = 0);
void method1();
void method2();
...
};
在同一 header 的另一个类中,我创建了该类的一个实例,然后我尝试从“SomeClass”获取所有方法并将其存储在 QMap 中:
this->someclass = new SomeClass(); // in constructor.
...
cout<<"init some class methods"<<endl;
const QMetaObject *metaobj = dynamic_cast<QObject*>(this->someclass)->metaObject();
cout<<"offset "<<metaobj->methodOffset()<<endl;
for(int i = metaobj->methodOffset();i < metaobj->methodCount();i++){
QMetaMethod metamethod = metaobj->method(i);
//if(metamethod.methodType() == QMetaMethod::Method){
QString methodname = QString(metamethod.signature());
methodname = methodname.replace(QRegExp("\\(.*\\)"),"");
controlmethods.insert(methodname,metamethod);
cout<<"added method: "<<metamethod.signature()<<" as "<<methodname.toAscii().data()<<endl;
//}
}
但是这并没有显示我添加了任何方法,因为方法偏移量等于方法计数,为什么可以呢?我不明白原因,谢谢任何帮助。
最佳答案
您需要为希望在 QMetaObject
中看到的每个方法使用 Q_INVOKABLE
宏。
Q_INVOKABLE
Apply this macro to declarations of member functions to allow them to be invoked via the meta-object system. The macro is written before the return type, as shown in the following example:
class Window : public QWidget { Q_OBJECT public: Window(); void normalMethod(); Q_INVOKABLE void invokableMethod(); };
The invokableMethod() function is marked up using Q_INVOKABLE, causing it to be registered with the meta-object system and enabling it to be invoked using QMetaObject::invokeMethod(). Since normalMethod() function is not registered in this way, it cannot be invoked using QMetaObject::invokeMethod().
您还可以使用 slots
宏。不过,我认为 Q_INVOKABLE
可能更小。
QMetaObject 只知道信号、槽、属性和其他可调用的成员函数,有时作为一个组称为“元方法”。
此外,对于示例的第一行,您应该(可能)只调用
const QMetaObject *metaobj = someClass->metaObject();
这不仅仅是装饰性的。 dynamic_cast
会将类型检查转移到运行时,如果您在编译时知道 someClass
是指向 QObject
的指针,则不需要这样做-派生类。 (dynamic_cast
ing 到 QObject*
会起作用,并且由于虚拟继承会为您提供正确的 QMetaObject,但这是不必要的、不太安全且不清楚。)
您实际上不需要类的实例来获取元对象:
const QMetaObject *metaobj = SomeClass::staticMetaObject();
这是可能的,因为每个类都有一个 QMetaObject,而不是每个对象。
对于任何想了解更多关于元对象系统的人,我推荐咖啡和 documentation .通常您不需要直接处理 QMetaObject 实例,除非您正在编写脚本引擎或类似“元”的东西。很容易无意中复制 Qt 已经提供的功能。
此外,Q_DECLARE_METATYPE
不是您想要的。
关于c++ - 我无法从 QMetaObject 获取方法,方法偏移量和计数相等,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/14576078/