Flex 2.0 Tree with Spring Loaded Folders (Update)

January 25, 2007

I’ve decided to both update the sample on the original post, and explain the error in a new post for those that have already downloaded the example. Turns out it’s actually something to remember.

In today’s post Flex 2.0 Tree control with Spring Loaded Folders there was a nasty framework bug. The bug only happens sometimes so it was not detected right away. None the less it is a show stopper for those wishing to use the technique on the tree control.

The bug will surface when a folder has no children and you try to close it using the expandItem function. Which in the case of the sample I use extensively.

The bug is in my opinion a Flex bug within the tree.as when tweening animation. The tree.as function buildUpCollectionEvents makes an assignment to a collection view of a null value (first line below) the next line attempts to access this value without a test. If no children exist when a folder has no children for example, the createCursor call is being done on a null object. Hence the error #1009.

Code from the tree.as

var children:ICollectionView = getChildren(expandedItem, iterator.view);
var cursor:IViewCursor = children.createCursor();

So what can we do when this happens. Well lucky for me the function called just before the “buildUpCollectionEvents” on the error stack is marked as internal.

mx_internal function onTweenEnd(value:Object):void

Because it’s marked internal I was able to override this and add a error handler on the extended version of the tree in order to gracefully handle it.

In order to override a function marked as internal you need to add “use namespace mx_internal;” at the end of the imports. You can then override the “onTweenEnd” to control the error. The sample already contains the import “mx.core.mx_internal;”. The below code will handle the error.

override mx_internal function onTweenEnd(value:Object):void{
try{
  super.mx_internal::onTweenEnd(value);
 }
 catch(err:Error){
  //Tween failure a nasty flex bug.
  //trace(err.message);
 }
}

The bug seems after testing to be handled, and no adverse effects in doing this are noticeable.

Disclaimer : I stated in my opinion it is a Flex framework bug. The statement is based on my assumption that I’m doing everything correctly within the code. I want to say also that the folks at Adobe have done a bang up job on Flex. It truly is a fabulous product when you can get at the guts of it like we can with Flex. As we all know absolutely no products of the depth of Flex ever go to market bug free. It’s just a fact of software development.

I have already updated the sample and source. For those of you who have already downloaded the source please make the changes as above or download the code a second time.

Here is a link to the original post
Sample and Source: Spring Loaded Folders

My apologies for any inconvenience.

Jason Hawryluk

Advertisements

18 Responses to “Flex 2.0 Tree with Spring Loaded Folders (Update)”

  1. JabbyPanda Says:

    Dear Jason,

    I want to clarify for the rest of the folks that this Spring Loaded Folders Tree component works correctly only with *Flex 2.0.1 SDK*, just released by Adobe at January 2007.
    http://www.adobe.com/support/flex/downloads_updaters.html

    If you are still using Flex 2.0 SDK, you will receive the following error in Flex Builder why compiling Spring Loaded Folders Tree:
    ———
    1178: Attempted access of inaccessible property _dropData through a reference with static type mx.controls:Tree. AudiooFileBrowser/src/com SpringLoadedTree.as
    ———

    In Flex 2 SDK the Tree.as the property _dropData was declared as private.

    ps
    Jason, it is nice to see this new great effort from you targeting at the new useful developments at Flash sphere. I remember your efforts to build RTE in Flex 1.5, it was also a good try 🙂


  2. JabbyPanda,

    Oops. I’d not thought about that at all. Just assumed everyone had/would have upgraded.

    Appreciate the heads up and the nice comment.

    I had actually used that originally for getting at the drop location, and then decide to go back the old way. Even worse it’s not used in the sample at all. You can safely remove that property and it’ll work.

    Warning I’ve not tried it on Flex 2.0

    My posts will from now on have the Flex 2.0.1 in the title.

    That said I’ll update the code online immediately.

    Thanks again.

    EDIT: Code updated. I don’t see a real need for yet another update post.

  3. JabbyPanda Says:

    No problem Jason, it was a minor nuisance with your component.

    BTW, the enginner of Adobe had made a promise at November 2006 at Flexcoders to upgrade access to _dropData property to public 🙂
    http://www.mail-archive.com/flexcoders@yahoogroups.com/msg46023.html

    ps..
    I am currently fighting with myTree.calculateDropIndex method, if you are interested in my adventures with Flex 2 Tree, I can provide you with the link to my demo app.


  4. […] example, if I came across a nice component, such as this spring loaded tree, it would be great if all I had to do to add it to my projects is crack open a command line and […]

  5. Serdar Badem Says:

    It looks like what you are suggesting at least suppresses the error messages however my tree still shows half rendered with some areas not repainted when this exception occurs. In my case I am doing an async data call (HttpService) in onItemOpening event and based on the timing of the call back I am getting this nasty error.


  6. Serdar,

    I not sure about your case. Couple suggestions you could try.

    Sometimes a callLater() in the right spot can do wonders.

    Perhaps test for a bool variable that signified the data loading, if data is loading then try a preventDefault() in the events itemOpen or itemClose combined with a callLater to give the data time to properly load, the call could perhaps be on the same event i.e.

    callLater(yourItemCloseHandler,[event]);

    Or perhaps test when you open the folder. If data is not already loaded for that folder then don’t use animation.

    expandItem(_lastNodeOver.data,true,false);

    Keeping in mind these suggestions are without knowing any details about your specific implementation.

    Jason

  7. Serdar Badem Says:

    I think whats going on is if the data loading (appending chilren through HTTPService) takes a little bit longer than the openduration (which is 250ms by default) I get this exception. What I end up doing was to override the expandItem method in my extended tree and actually call the super.expandItem in my result handler method. So in summary, you need to have the children ready before itemOpening.

  8. Sinan Says:

    I’ve experienced this BUG!
    Bug solved : thanks, jason!
    Thanks for your article.. 🙂


  9. […] : A nasty framework bug was discovered and corrected. Sample and source have been updated. I’ve created a new post describing the bug. Turns out it’s a good one to […]

  10. diamondtearz Says:

    I just lost 4 hours of my life that I will never get back battling this bug and the DataDescriptor last night!

  11. Mark Says:

    Dark gray on black is very hard to read. Might want to pick some different colors.

  12. Jimmy Choi Says:

    Thanks Jason. I’d like to mention that another (possibly more robust) way to get around the problem is to disable the open animation by setting openDuration to 0.

    I say that this is possibly more robust because although your solution gets around the crash, I almost always get an incorrectly-rendered tree as someone above has also mentioned.

    Hope this helps!


  13. I have been reading your articles now for a while and it looks very nice. Thanks Jason

    Cheers

    Vincent

  14. Arivu Says:

    Hi,
    I am using Flex 3, even then i am getting this error

    1178: Attempted access of inaccessible property _dropData through a reference with static type mx.controls:Tree.

  15. lingpri Says:

    I’m loading the XML document using the URLLoader class and providing the dataProvider of the tree as an XMLList.The whole XML document appears as a tree node.Please advise on what i’m doing wrong.

    Thanks..

    var loader:URLLoader = new URLLoader();
    loader.addEventListener( Event.COMPLETE, handleComplete );
    loader.load(new URLRequest(“sampleData.xml”));

    private function handleComplete( event:Event ):void {
    var example:XML = new XML( event.target.data );
    Model.instance.opAreaXMLList = example.children();

  16. Teacher Says:

    If human demand to share/stay at home so certain have occasion to.But if increase all a certain it,quiet one thousand language within reason death.

  17. Good Laptops Says:

    I am using Flex 3, even then i am getting this error


Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out / Change )

Twitter picture

You are commenting using your Twitter account. Log Out / Change )

Facebook photo

You are commenting using your Facebook account. Log Out / Change )

Google+ photo

You are commenting using your Google+ account. Log Out / Change )

Connecting to %s

%d bloggers like this: