是否从C ++向QML发出信号以读取Q_PROPERTY同步事件?

时间:2013-12-11 02:33:47

标签: c++ qt qml qtquick2

使用Qt 5.1我有:

Q_PROPERTY(float d1 MEMBER data1 NOTIFY datas_changed_signal)
Q_PROPERTY(float d2 MEMBER data2 NOTIFY datas_changed_signal)

....

void setOBJ(nobj){
        obj=nobj; //these are pointers to a data structure
        data1=nobj->data1(); //assign to member of this class
        data2=nobj->data2();

        emit datas_changed_signal();
    }

我的类收到指向某些数据的指针nobj,然后我希望我的QML能够访问这些数据。实际上nobj包含的不仅仅是2个数据项,但为了简单起见,我在此表达。

我想知道几件事。首先,快速调用setOBJ时会发生什么。在再次调用MEMBER之前,是否存在通知QML但未读取setOBJ(data1或data2)的风险?由于这个原因,QML会错过一些更新吗?例如,如果它是异步的,就会发生这种情况。或者,每次发出上面的信号时,我是否可以依靠QML获取数据?

其次,在我看来,在创建中间数据成员以存储来自传入对象nobj的数据时,存在一些不必要的开销。我尝试了这个:

    Q_PROPERTY(float d1 MEMBER obj->data1() NOTIFY datas_changed_signal)

但是MOC似乎不喜欢以这种方式使用Q_PROPERTY(不编译)。会有类似的选择吗?

更新:我发现this method (link)似乎是Q_PROPERTY的可行替代品,用于将数据从C ++发送到QML,我可以将我的数据作为参数发送到QML函数。这是一个很好的选择吗?

1 个答案:

答案 0 :(得分:3)

默认情况下,信号和插槽是同步实现的,并且即使在异步实现甚至跨线程边界传递时也始终按顺序处理。所以你不必担心你的QML会以错误的顺序获取信号。

事实上,默认情况下,信号实际上会立即触发所有绑定的目标代码。 IE,这个:

emit datas_changed_signal();

几乎就像打电话:

slotFunction1();
slotFunction2();
...

因此,任何附加的QML javascript(onDatas_changed_signal)都会立即被调用。

信号和插槽是向QML发送数据的首选方式,因为它为独立于C ++底层模型的QML提供了更大的支持,因此我坚持使用属性,信号和插槽。您的QML代码可能有一天需要扩展,并且在有意义的更改中会发生多种事情,如果您通过属性执行此操作而不是直接调用QML函数,那么这将简单易用。