Q_PROPERTY NOTIFY signal and its argument
binding, c++, data-binding, qml, qt
Solution
Passing the values of the changed properties in the `onPropertyChanged`-signal is, though possible, most surely not the QML style.
Would it be, then you should expect that at least for the basic types it is implemented, which is easily shown, it's not.
basictypes.qml
import QtQuick 2.7
import QtQuick.Controls 2.0
ApplicationWindow {
id: root
visible: true
width: 400; height: 450
property int num: 5
Button {
text: num
onClicked: num += 1
}
onNumChanged: console.log(JSON.stringify(arguments), arguments.length)
}
As you can see in the output, that there are no arguments passed, when you change even one of the most basic types, such as `int`.
If now QML would use the optional, but rarely implemented passed value this would create overhead, as you would always need to check the existence of the argument before using it. Though a simple check is not to expensive, if it usually evaluates to `false`, and then you use the workaround, why do it beforehand?
Though I might not rule out, that there are any passed values in any `onPropertyChanged`-signals in the official realse, there are none for properties added in QML with `property [type] [name]`. There also none for most inherited properties (tested the Button: `text`, `width`, `height`).
Problem
I have the habit of writing my "propertyChanged" `signal`s with an argument, such that the receiving end doesn't need to call the `Q_PROPERTY`'s `READ` function explicitly. I do this out of clarity and the assumption that in a QML data binding situation, no "expensive" call to the getter needs to be done to actually fetch the value, as it's already passed to QML as a signal argument. My colleagues disagreed and said it was against "QML style", to which I responded the documentation clearly states it may have an argument that will take the new value of the underlying member: `NOTIFY` signals for `MEMBER` variables must take zero or one parameter, which must be of the same type as the property. The parameter will take the new value of the property. Nowhere in the documentation is it stated that the QML binding system uses this parameter to prevent an additional function call to the getter when handling the signal. I understand this call will probably be made from C++, so no "expensive" QML to C++ call will be made, but it still is an extra function call, which in principle could result in a visible performance penalty in case of many updates. I tried inspecting the QML binding source code, but couldn't infer anything from it. I wonder if someone knows what the deal is: is the signal argument used or not?