从C ++中与Repeater中的委托QML组件交互

时间:2015-08-21 07:15:24

标签: c++ qt qml repeater qqmlcomponent

我无法从C ++访问Repeater中的委托QML组件。请在下面找到代码。感谢。

的main.cpp

#include <QApplication>
#include <QDebug>
#include <QQuickView>
#include <QQuickItem>

int main(int argc, char *argv[]) {
    QApplication app(argc, argv);
    QQuickView view;
    view.setSource(QUrl(QStringLiteral("qrc:/Main.qml")));
    view.show();
    QQuickItem *object = view.rootObject();
    QObject *rectangle = object->findChild<QObject*>("rect1");

    if (!rectangle)
    qDebug() << "MyError: rectangle was not found";

    app.exec();
}

Main.qml

import QtQuick 2.4

Row {
    Repeater {
        model: 3
        Rectangle {
            width: 50; height: 50
            color: index %2 ? "black" : "white"
            objectName: "rect" + index
        }
    }
}

控制台输出:

MyError: rectangle was not found

2 个答案:

答案 0 :(得分:3)

我已经实现了自己的递归函数模板&#39; findChild&#39;用C ++编写的函数。“

QQuickItem *object = view.rootObject();
QQuickItem *rectangle = findChild<QQuickItem*>(object, "rect1");

if (rectangle)
{
    qDebug() << rectangle;
    qDebug() << rectangle->objectName();
} 

并将其称为默认函数。

QQuickRectangle(0x2222b40, name="rect1", parent=0x22245b0, geometry=50,0 50x50)
"rect1"

获得输出:

       <div id="logo_container">
       <span class="logo_name"> James Mitchell</span>
       <span class="logo_title"> Consultant ENT Surgeon</span>
       <span class="logo_website"> enthealth.co.uk</span>
       </div>

答案 1 :(得分:0)

如果您调用object->dumpObjectTree(),您将看到类似以下控制台输出的内容:

QQuickRow:: 
QQuickRepeater:: 
    QQmlComponent::

如您所见,对象树不包含矩形作为专用qobjects。在我对QML方面的有限理解中,有另一个树包含所有可见的qml项目/组件。这些您至少可以通过qml中的&#39; children&property -property访问。为了表明这一点,我将你的qml文件更改为:

Main.qml:

Row {
    id: row
    Repeater {
        model: 3
        Rectangle {
            width: 50; height: 50
            color: index %2 ? "black" : "white"
            objectName: "rect" + index
        }

    }
    Component.onCompleted: {
        console.log(row.children[0].objectName);
        console.log(row.children[1].objectName);
        console.log(row.children[2].objectName);
    }

}

得到以下结果:

qml: rect0
qml: rect1
qml: rect2
MyError: rectangle was not found

当然,直接可访问性和索引取决于您的其他项目/组件。从这里开始,你可以编写自己的递归&#39; findChild&#39;函数并将结果对象公开给C ++。以下是如何:http://doc.qt.io/qt-5/qtqml-cppintegration-interactqmlfromcpp.html

例如,您可以实施一个&#39; findChild&#39;在qml中像这样:

function findChild(propertyName, propertyValue) {
    return findChildRecursivly(row, propertyName, propertyValue)
}

您可以从C ++调用此qml函数,如

QVariant result;
QMetaObject::invokeMethod(object, "findChild",
                          Q_RETURN_ARG(QVariant, result),
                          Q_ARG(QVariant, "objectName"),
                          Q_ARG(QVariant, "rect1"));
rectangle = result.value<QObject *>();

使用以下附加代码行:

if (!rectangle)
{
    qDebug() << "MyError: rectangle was not found";
}
else
{
    qDebug() << rectangle;
    qDebug() << rectangle->objectName();
}

你得到以下输出:

QQuickRectangle(0x1c1beef, name = "rect1")
"rect1"