[Qt-qml] Managing declarative/imperative "order of operations"
michael.brasser at nokia.com
michael.brasser at nokia.com
Thu Nov 11 02:22:38 CET 2010
Hi Charley,
On 07/11/2010, at 5:45 AM, ext Charley Bay wrote:
> Using QML/Javascript, quite a few options exist to *either* be declarative (e.g., "myAnimation.paused = true") or imperative (e.g., "myAnimation.pause();")
>
> IMHO, when possible, one should be declarative (long discussion for a different thread). However, we all probably agree that we *sometimes* must do both. I'm now scratching-my-head a little to understand how to handle this marriage as it relates to order-of-operations.
>
> For example, I'm writing a "MyLayout" element that contains "MyBucket" for transient children:
>
> //MyBucket.qml
> Item {
> onChildrenChanged: {
> // ...do stuff with children, including set properties
> }
> };
>
> //MyLayout.qml
> Item {
> id: myLayout
>
> MyBucket {
> id: myBucket
> }
>
> onChildrenChanged: {
> // Push "transient" children to our bucket.
> var i = myLayout.children.length;
> while(i--) {
> if( ...<test-if-"myLayout.children[i]"-is-transient-child>...) {
> myLayout.children[i].parent = myBucket;
> }
> }
> }
> };
>
> The above works fine. HOWEVER, there is TONS of "supporting" code that both declarative and imperative that triggers "behind-the-scenes" (for example, Javascript functions get called when properties like "parent" changed, and similarly Javascript handlers get triggered when "children" change.)
>
> I've been using "console.log()" to trace what's going on, but it's triggered some questions:
>
> (1) Does console.log("My message") *guarantee* the displayed order is the order the calls are made? (I assume "yes" -- this is very important).
Yes, it should.
> (2) Does console.log() "flush" after each message, or is there an option to trigger flushing? (Would be nice to have an option, but I can live without it.)
Internally console.log() just calls qDebug("%s",msg.constData()), which I believe should flush.
> (3) I'm getting some seriously weird order-of-operations that may possibly force me to re-think my design. However, since we are "declarative", by definition I suppose there's no such thing as a "weird" order of operation. Is there any "general guidance" on understanding order-of-operations within the QML engine? (For example, I'd *assume* a general preference would be made to perform "Declarative First!", but I concede that it's probably often quite indeterminate.)
>
> In short, I have bound properties that are changing, that are reflected in other bound properties. Then, these bound properties are "used" in imperative code (e.g., computing placement for items). In my particular case, the "layout" logic is being executed *before* the bound properties are updated (so the layout incorrectly reflects the "old" values before the properties are updated). (The properties correctly get updated later.)
>
> Of course, I have *tons* of design options, including manually forcing updates, setting up hooks like "onLoadCompleted()", etc.
>
> However, I'm now wondering if I'm thinking about the problem wrong, and I'm interested in opinions: How do you balance declarative and imperative? For example, if you have a problem where much of it *must* be imperative, my current assumption is that it is *?best practice?* if you do one of the following:
>
> (a) When significant portions of your implementation must be imperative, you should consider implementing (as much logic as possible) that couples to that imperative implementation as *also* imperative (so order-of-operations is deterministic).
>
> (b) When significant portions of your implementation must be imperative, you should consider *forcing* that to a single "clean execution point" that is fired ONLY at discrete times where you can "trust" the property inputs (e.g., onLoadCompleted(), at specific well-understood call points) (so you have no coupling to "unknown/stale" property values).
>
> My problem is that until I do either of the two, I think I can't trust my properties from within my imperative calls. This is an interesting design challenge which is new to me.
This reminds me a bit of http://bugreports.qt.nokia.com/browse/QTBUG-11712 -- do you think this may be related to what you are seeing? Do you have any small examples of strange out-of-order behaviors you could share (I'd like to understand the problem better)?
Regards,
Michael
More information about the Qt-qml
mailing list