2017-03-23 48 views
0

对不起,如果标题不是很明确。这里是例子,一个classA有几个孩子,childA1childA2等存储在classAlistQt - C++ - 通过父连接访问的子项的功能

QList<ClassA> listA; 
listA << childA1() << childA2(); 

childA1具有不中classA存在功能start()。所以,如果我尝试:

listA[0].start(); 

编译器说,classA没有成员start()start()被公槽,我做:

connect(this, SIGNAL(signalStart()), listA[0], SLOT(start())); 

,它的工作。所以我的问题是如何知道这个函数start()作为classA存储在列表中后?有没有办法知道“原始”类型?

回答

3

Qt的信号/插槽做工用内省(列出在运行任何QObject的方法和属性的能力)。

Qt利用Meta-Object Compiler工具在C++中具有内省功能。有关Qt信号/插槽内部的更多信息,您可以查看this blog post

您可以使用没有信号/插槽的内省。所以,在你的例子中,你不需要定义信号signalStart()只是为了能够调用start()方法。相反,你可以做这样的事情:

QMetaObject::invokeMethod(listA[0], "start"); 

这将查找在指定QObject(无论指针类型的)函数命名启动,并调用它。

下面是使用内省的工作的完整示例:

#include <QtCore> 

QTextStream& qOut(){static QTextStream out(stdout); return out;} 

class MyObject : public QObject{ 
    Q_OBJECT 
public: 
    explicit MyObject(QObject* parent= nullptr):QObject(parent){} 
    ~MyObject(){} 
    //Object has a slot named func 
    Q_SLOT void func(){ qOut() << "Hello func!\n"; } 
}; 

int main(int , char*[]){ 
    QObject* object = new MyObject(); 

    //print the object's class name (this is the real class name!) 
    qOut() << object->metaObject()->className() << "\n"; 

    //look for a function named func in the object, and invoke it 
    QMetaObject::invokeMethod(object, "func"); 

    return 0; 
} 

//run MOC on this CPP file 
#include "main.moc" 
0

首先,您应该在QList中存储对象的指针。

那么你可以使用dynamic_cast确定哪些孩子键入您的目标是:

A *obj = listA[0]; 

if (A1 *a1 = dynamic_cast<A1 *>(obj)) { 
    // This is an A1 object, you can call start() 
    a1->start(); 
} else if (A2 *a2 = dynamic_cast<A2 *>(obj)) { 
    // This is an A2 object 
}