Hello Martin,

I'm close to committing changes that will enable the propagation of value
changes between trees, using something similar like qx.data.Array. In fact,
I did not want to rewrite the whole TreeVirtual, using qx.data.Array,
because a) I'd rather extend Derrell's excellent codebase, and b) I think
that qx.data.Array doesn't scale well when you deal with a tree that has
10.000 nodes. Of course, there aren't very many use cases for trees that
big, but I want to be sure not to slow the UI down. I therefore kept the
native array that is the basis of Derrell's tree data model, and simulate
change events whenever something changes in the tree. These changes will
then be propagated to the controller and synchronized through property
binding with the jsonrpc store, which, in turn, will propagate the change
further to the server. 

I hope to have the stuff ready by tonight and will keep you posted. Haven't
thought about editable cells, but TreeVirtual somewhat different from the
Table. I'll see into that.

Thanks,

Christian 


Martin Wittemann wrote:
> 
> Hello Christian,
> 
> the sample application looks really good. I like the fact that the  
> tree is filled in the background. I did also take a look at the source  
> code of the store and the controller. If i did get it right, you are  
> using a default virtaul tree model as model for the data binding? Do  
> you already have a plan how to handle editable cells in the tree?
> You are also using native javascript arrays as container for the  
> nodes, right? How do you plan to handle a change in the structure of  
> the tree data during the runtime?
> 
> Best,
> Martin
> 
> 
> Am 13.05.2009 um 21:32 schrieb panyasan:
> 
>>
>> Hello,
>>
>> I committed a first version of a databinding feature for
>> qx.ui.treevirtual.TreeVirtual, using a jsonrpc store, in the  
>> contrib://qcl
>> in the qcl namespace. You can have a look at the code here:
>>
>> https://qooxdoo-contrib.svn.sourceforge.net/svnroot/qooxdoo-contrib/trunk/qooxdoo-contrib/qcl/trunk/frontend/source/class/qcl/databinding/event/
>>
>> It is currently in the qcl.databinding.event namespace, because I am  
>> working
>> on a client-server bidirectional databinding that works with events  
>> that are
>> sent between the client and the server. But that still needs to be
>> implemented.
>>
>> I have created a sample application that shows how the tree works  
>> with huge
>> datasets (up to 10.000 nodes):
>>
>> https://qooxdoo-contrib.svn.sourceforge.net/svnroot/qooxdoo-contrib/trunk/qooxdoo-contrib/qcl/trunk/application/databinding/
>>
>> A live instance of it is here:
>>
>> http://m53s12.vlinux.de/cboulanger/databinding/build/
>>
>> When you click on the "Get data from jsonrpc" button, you can see  
>> how the
>> tree starts loading the first couple of nodes and then continues  
>> loading in
>> the background. The ui stays responsive at the whole time, because the
>> massive tree is divided into smaller chunks which are loaded one  
>> after the
>> other. You can even add new nodes manually without interfering with  
>> the
>> process.
>>
>> The php json-rpc backend service creates a random tree with  
>> 1000-9000 nodes.
>> There is a small bug - sometimes the loading stops after the first  
>> request -
>> just press the button again.
>>
>> The source code of the sample application is heavily documented so  
>> you can
>> see how the API currently is designed:
>>
>> https://qooxdoo-contrib.svn.sourceforge.net/svnroot/qooxdoo-contrib/trunk/qooxdoo-contrib/qcl/trunk/application/databinding/source/class/databinding/Application.js
>>
>> Here is how the loading of the tree is implemented:
>>
>>      /*
>>       * Get data from JSON-RPC backend
>>       */
>>      var store = new qcl.databinding.event.store.JsonRpc(
>>        /* url */ "../services/index.php",
>>        /* service */ "qcl.Databinding",
>>        /* method */ null,
>>        /* marshaler */ new qcl.databinding.event.marshal.TreeVirtual
>>      );
>>
>>      var controller = new
>> qcl.databinding.event.controller.TreeVirtual(null, this.treeWidget);
>>      store.bind("model", controller, "model");
>> [...]
>>        /*
>>         * get some local variable references for the closure
>>         */
>>        var tree = this.treeWidget;
>>        var cancelButton = this.buttonCancelAddJsonRpcData;
>>        var startButton = this.buttonAddJsonRpcData;
>>
>>        /*
>>         * clear the tree
>>         */
>>        tree.getDataModel().clearData();
>>
>>        /*
>>         * calling getNodeCount() method on server with no
>>         * parameters. it returns the number of nodes on the
>>         * server.
>>         */
>>        store.load("getNodeCount", [], function(data)
>>        {
>>          var nodeCount = data.nodeCount;
>>
>>          var counter = 0;
>>          abortJsonRpcLoad = false;  // global flag
>>
>>          /*
>>           * Create a function that can recursively call itself
>>           * in order to load folder children, as long as there
>>           * are some left on the server.
>>           */
>>          (function loadTree(data)
>>          {
>>
>>            /*
>>             * if the function is called with boolean 'true', this
>>             * is interpreted as the start of the loading process.
>>             */
>>            if (data === true)
>>            {
>>
>>              /*
>>               * do some nice ui stuff
>>               */
>>              tree.setAdditionalStatusBarText(" | Tree has " +  
>> nodeCount + "
>> nodes ...");
>>              cancelButton.setEnabled(true);
>>              startButton.setEnabled(false);
>>
>>              /*
>>               * call the load method with no arguments which means  
>> that
>>               * the top level nodes are requested.
>>               */
>>              store.load("getNodeData", [], loadTree);
>>            }
>>
>>            /*
>>             * After the data has returned from the server, the  
>> function is
>>             * called again, and the data passed to the function.
>>             * We use a global flag to signal if the loading process  
>> should
>>             * be aborted. The data passed from the server has a  
>> 'nodes' and
>> a
>>             * 'queue' property. The 'nodes' property will be used by  
>> the
>>             * controller to build the tree in the tree model. The  
>> 'queue'
>> property
>>             * is an array of child ids which still have to be  
>> retrieved. If
>> this
>>             * array is empty, we're done loading.
>>             */
>>            else if ( ! abortJsonRpcLoad && data && typeof data ==  
>> "object"
>>                      && data.queue instanceof Array &&  
>> data.queue.length )
>>            {
>>              /*
>>               * display loading progress
>>               */
>>              counter += data.nodes.length;
>>              var parentNodeId = data.parentNodeId;
>>              tree.setAdditionalStatusBarText(" | Loaded " + counter  
>> + " of
>> " + nodeCount + " nodes...");
>>
>>              /*
>>               * now call the load method of the store with the queue  
>> of
>> node ids that
>>               * still have to be retrieved. It will pull no more than
>>               * 10 folders (plus children) at a time to avoid  
>> timeouts.
>>               * You can play with the value of 10 to see whatever
>>               * works best, given the bandwith and server speed. When
>>               * done loading, call the loadTree function again with
>>               * the result.
>>               */
>>              store.load("getNodeData", [ data.queue, 10 ], loadTree );
>>            }
>>
>>            /*
>>             * if no data, an error occurred
>>             */
>>            else if (data === null)
>>            {
>>              tree.setAdditionalStatusBarText(" | *** An error occurred
>> ***");
>>              cancelButton.setEnabled(false);
>>              startButton.setEnabled(true);
>>            }
>>
>>            /*
>>             * else, we're done.
>>             */
>>            else
>>            {
>>              tree.setAdditionalStatusBarText(" | Finished loading " +
>> nodeCount + " nodes.");
>>              cancelButton.setEnabled(false);
>>              startButton.setEnabled(true);
>>            }
>>          })(true);
>>        });
>>
>> The data sent by the server is not converted by the json marshaler,  
>> because
>> that would be too expensive and would actually complicate things.  
>> Instead, a
>> special TreeVirtual marshaler converts it into a simple model with a  
>> few
>> properties. The controller then adds data from this model to the
>> TreeVirtual's own internal data model.
>>
>> I would be interested in feedback at this early stage, especially  
>> concerning
>> the databinding design.
>>
>> Thanks,
>>
>> Christian
>> -- 
>> View this message in context:
>> http://www.nabble.com/Databinding-for-TreeVirtual-tp23528458p23528458.html
>> Sent from the qooxdoo-devel mailing list archive at Nabble.com.
>>
>>
>> ------------------------------------------------------------------------------
>> The NEW KODAK i700 Series Scanners deliver under ANY circumstances!  
>> Your
>> production scanning environment may not be a perfect world - but  
>> thanks to
>> Kodak, there's a perfect scanner to get the job done! With the NEW  
>> KODAK i700
>> Series Scanner you'll get full speed at 300 dpi even with all image
>> processing features enabled. http://p.sf.net/sfu/kodak-com
>> _______________________________________________
>> qooxdoo-devel mailing list
>> [email protected]
>> https://lists.sourceforge.net/lists/listinfo/qooxdoo-devel
>>
>>
> 
> 
> ------------------------------------------------------------------------------
> The NEW KODAK i700 Series Scanners deliver under ANY circumstances! Your
> production scanning environment may not be a perfect world - but thanks to
> Kodak, there's a perfect scanner to get the job done! With the NEW KODAK
> i700
> Series Scanner you'll get full speed at 300 dpi even with all image 
> processing features enabled. http://p.sf.net/sfu/kodak-com
> _______________________________________________
> qooxdoo-devel mailing list
> [email protected]
> https://lists.sourceforge.net/lists/listinfo/qooxdoo-devel
> 
> 

-- 
View this message in context: 
http://www.nabble.com/Databinding-for-TreeVirtual-tp23528458p23540433.html
Sent from the qooxdoo-devel mailing list archive at Nabble.com.


------------------------------------------------------------------------------
The NEW KODAK i700 Series Scanners deliver under ANY circumstances! Your
production scanning environment may not be a perfect world - but thanks to
Kodak, there's a perfect scanner to get the job done! With the NEW KODAK i700
Series Scanner you'll get full speed at 300 dpi even with all image 
processing features enabled. http://p.sf.net/sfu/kodak-com
_______________________________________________
qooxdoo-devel mailing list
[email protected]
https://lists.sourceforge.net/lists/listinfo/qooxdoo-devel

Reply via email to