I have an|Item|with a property. This property contains an array of JavaScript objects which in turn contain other properties. When I set binding for one of object's properties to some variable and its (variable) value changes triggering the binding then all properties in the array are reset to their initial values. I've created a small demo to show the problem.

C++ code:

|// main.cpp
#include <QGuiApplication>
#include <QQuickWindow>
#include <QQmlApplicationEngine>
#include <QQmlContext>

class Test : public QObject
{

    Q_OBJECT
        Q_PROPERTY(QString emptyString READ getEmptyString NOTIFY valueChanged)
        QString getEmptyString(){ return ""; }

public:
    Test(QObject* parent = 0) : QObject(parent) {}

    Q_INVOKABLE void triggerNotify()
    {
        valueChanged();
    }

signals:
    void valueChanged();
};

int main(int argc, char *argv[])
{
    QGuiApplication app(argc, argv);
QQmlApplicationEngine engine;
    Test* test = new Test(&engine);
    engine.rootContext()->setContextProperty("__test__", (QObject*)test);
    QObject::connect(&engine, &QQmlApplicationEngine::objectCreated, 
[](QObject* rootObject) {
        QQuickWindow *appWindow = qobject_cast<QQuickWindow *>(rootObject);
        appWindow->show();
    });

    engine.load(QUrl(QStringLiteral("qrc:/ui/main.qml")));
    return app.exec();
}|

QML code:

|// main.qml
import  QtQuick  2.4
import  QtQuick.Controls  1.3

ApplicationWindow  {
    id:  container
    visible:  true

    width:  640
    height:  480

    property  int  clicksCounter:  0

    Item  {
        id:  testObject
        property  var myArray:  [{
            name:  "CustomName"  +  __test__.value,
            boolFlag:  false
        }]
    }

    Rectangle  {
        x:  10
        y:  10

        width:  100
        height:  100
        color:  "red"

        MouseArea  {
            anchors.fill:  parent
            onClicked:  {
                container.clicksCounter++

                console.log("CLICK #"  +  container.clicksCounter+  "[RED SQUARE] : 
Set testObject.myArray[0] to TRUE\n")
                testObject.myArray[0].boolFlag=  true
                console.log("CLICK #"  +  container.clicksCounter+  "[RED SQUARE] : 
DONE\n")
            }
        }
    }

    Rectangle  {
        x:  120
        y:  10

        width:  100
        height:  100
        color:  "blue"

        MouseArea  {
            anchors.fill:  parent
            onClicked:  {
                container.clicksCounter++

                console.log("CLICK #"  +  container.clicksCounter+  "[BLUE SQUARE] : 
Triggering notify by calling C++ <Test::valueChanged> method \n")
                console.log("CLICK #"  +  container.clicksCounter+  "[BLUE SQUARE] : 
[BEFORE] testObject.myArray[0].name:"  +  testObject.myArray[0].name+  ', 
testObject.myArray[0].boolFlag:'  +  testObject.myArray[0].boolFlag)
                __test__.valueChanged()
                console.log("CLICK #"  +  container.clicksCounter+  "[BLUE SQUARE] : 
[AFTER] testObject.myArray[0].name:"  +  testObject.myArray[0].name+  ', 
testObject.myArray[0].boolFlag:'  +  testObject.myArray[0].boolFlag)
            }
        }
    }
}|


Here is what I get:

qml: CLICK #1[RED SQUARE] : Set testObject.myArray[0] to TRUE
qml: CLICK #1[RED SQUARE] : DONE

qml: CLICK #2[BLUE SQUARE] : Triggering notify by calling C++ <Test::triggerNotify> method

qml: CLICK #2[BLUE SQUARE] : [BEFORE] testObject.myArray[0].name: CustomName, testObject.myArray[0].boolFlag: true qml: CLICK #2[BLUE SQUARE] : [AFTER] testObject.myArray[0].name: CustomName, testObject.myArray[0].boolFlag: false

So what happens here is that after I set testObject.myArray[0].boolFlag from FALSE to TRUE and call test.triggerNotify() method my flag automatically resets to its initial value. Same goes if any other type used - int, string, etc. Why does this happen?

[UPDATE] QT 5.5 is used, Visual Studio 2013 Update 4 x32.

_______________________________________________
Interest mailing list
Interest@qt-project.org
http://lists.qt-project.org/mailman/listinfo/interest

Reply via email to