如何将QML创建的组件指针传递给C++?实现方案有效性咨询
问题1:将QML组件指针传递给C++的最简单方式是什么?
你目前尝试的方案就是最简单的实现方式:
- 先将C++逻辑类实例注册为QML上下文属性
- 在QML组件的
Component.onCompleted信号回调中,直接将组件id作为参数传递给C++类的可调用方法
该方案完全规避了传统objectName查找方案的命名同步问题,代码更简洁,维护成本更低。
传统objectName查找的参考实现如下:
auto const root = engine.rootObjects(); if(!root.empty()) { auto const obj = root.first()->findChild<test_item*>("testItem"); if(obj) { c.setup_test(obj); } else { qDebug() << "Couldn't Cast"; } } else { qDebug() << "Empty root object list"; }
你采用的方案参考实现:
main.qml
TestItem { id: testItemId; Component.onCompleted: controller.setup_test(testItemId); }
main.cpp
class controller : public QObject { Q_OBJECT public slots: Q_INVOKABLE void setup_test(test_item* item) { item->f(); } }; #include "main.moc" int main(int argc, char* argv[]) { QGuiApplication app(argc, argv); QQmlApplicationEngine engine; controller c; qmlRegisterType<test_item>("qml.pass.id", 1, 0, "TestItem"); engine.rootContext()->setContextProperty("controller", &c); engine.load("qrc:/qml_pass_id_example/main.qml"); return app.exec(); }
问题2:将QML组件ID作为对应C类型指针传递给C函数的做法是否合法有效?
该做法完全合法有效,属于Qt元对象系统原生支持的特性:
- QML中的id本质就是当前组件实例的引用,当传递给C的
Q_INVOKABLE方法或者槽函数时,Qt会自动完成类型转换,只要你已经通过qmlRegisterType完成了QML类型和对应C类的绑定,且参数类型匹配,就不会出现类型转换错误 - 你测试的Qt 5.15.2、Qt 6.2.0版本,以及Windows、Linux平台均支持该特性,可以放心在生产环境使用
注意事项
- C++中不要长期持有QML组件的裸指针,若必须持有建议使用
QPointer包装,避免QML组件销毁后出现野指针访问问题 - 传递的组件类型必须是
QObject的派生类,普通自定义类型无法直接通过该方式传递
内容的提问来源于stack exchange,提问作者Ghasem Ramezani
相关产品推荐
相关产品推荐

