Thursday, March 14, 2013

$w(css,parentNode) as WidgetList (NodeList on steroids)

Story in development, the post will be modified as ongoing design changed.

The CSS selector for widget's content has been used for a while by dojoplay2012/lib/TemplatedWidget. It allows the query to scope by widget's content and handy for group operations given by NodeList:

this.$(".classInChild").html("");

This interface has been extended to get sub-child widget

this.$w(".classInChild").resize();


At the moment $w() returns only first widget but it would be handy to operate with all widgets with same call. So the expression above will resize() all matching children rather first only.

Following the NodeList chaining concept, would be nice to have calls chained.

this.$w(".classInChild").update().resize();

WidgetList will be returned on each call to support the chainig. That could be achieved by wrapping returned widgets into object which will simulate each method call invoking each widget one and returning WidgetList.

To access results of last call :
this.$w(".classInChild")
    .resize(maxDimentions)
    .getSize()
    .forEachResult(function(sz){ total.x+=s.x; });

COST

When WidgetList is created there is no way to define ahead which method will be called as a first in the chain. Which will have an overhead of wrapper creation for each method name in each returned object.
Each call could potentially change widget set and it's  interface and as result WidgetList and methods map need to be updated. While API changing of widgets could be ignored assuming no changes during WidgetList existence, DOM changes are little trickier to guess.

WAYS AROUND
The chaining by member method name could be substituted with explicitly set function name set in first parameter:

this.$w(".classInChild")
    .call( "resize", maxDimentions )
    .call(  "getSize"  )
    .forEachResult( function(sz){ total.x+=s.x; } );

Another short version of above using return the function instead of object:

this.$w(".classInChild")
    ( "resize", maxDimentions )
    (  "getSize"  )
    .forEachResult( function(sz){ total.x+=s.x; } );


Such call convention will prevent creation of mappings hence could help with extra memory and CPU during execution. But it makes code less elegant and readable. The simple string substitution during compilation could convert original "nice" syntax to "efficient" one.

Comments and suggestions are welcome.

No comments:

Post a Comment