PDA

View Full Version : HOW-TO: Get rid of the expand for a tree node you know is empty



evant
18 Jun 2007, 12:10 AM
An issue I've had with an Ext app is that when loading a tree asynchronously, on the server side I already know that the node has no children, however as far as I can tell there is no easy way to communicate this back to Ext (please correct me if there is an easier way).

So, if you know beforehand that your node is empty, when sending the JSON back to the client, include:


{isLoaded: true}

for the appropriate nodes.

Then in your tree code, use:


tree.on('beforeload', function(node)
{
if (node.attributes['isLoaded'])
return false; //we know the node is empty, don't querying the server
}, this);

tree.on('load', function(node)
{
var children = node.childNodes;
for (var i = 0; i < children.length; i++)
{
var n = children[i];
if (n.attributes['isLoaded'])
n.expand(); //force the node to expand
}
}, this);


This technique is useful when there is not necessarily always a leaf node (a folder structure would be a good example of this).

GalaxySong
21 Jun 2007, 9:46 PM
Why not just use "leaf = true" instead of "isLoaded = true"?

evant
21 Jun 2007, 10:39 PM
Because the node might not always be a leaf (for example if you're creating a folder structure, it might be a leaf for the time being, however when you add a child folder it is no longer a leaf).

willydee
23 Jul 2007, 2:56 AM
evant,
this was very helpful, thanks for pointing out!

jack.slocum
23 Jul 2007, 6:01 AM
Actually, you can tell it it has no children when loading by returning an empty children array attribute:

children: []

Then, you can make it immediately "discover" that it has no children and remove the expand icon with:

expanded: true

A complete example:


{
id: 'my-id',
text: 'I have no children right now',
iconCls: 'foo-icon',
children: [],
expanded: true
}

willydee
24 Jul 2007, 7:31 AM
Perhaps the shortest way (assumed a numeric 'Children' property is supplied with the JSON data), otherwise almost the same as evant's solution:



loader.on('beforeload', function(loader, node) {
if (node.attributes.Children == 0) return false;
});
loader.on('load', function(loader, node) {
node.eachChild(function(child) {
if (child.attributes.Children == 0) child.expand();
});
});

GalaxySong
30 Jul 2007, 12:57 AM
I think Jack's way is convenient enough.