Tree = Class.create();

Tree.prototype = {
   initialize: function( element, options ) {
      this.ul = $( element );
      this.lis = new Array();

      this.options = { 
         element: Tree.Node
      }
      Object.extend( this.options, options );

      this.setup();
   },

   setup: function() {
      var name = "";
      var children = this.ul.immediateDescendants();

      children.each( function( child ) {
         name = child.tagName || "";
         if( name != "LI" )
            return;

         this.lis.push( new this.options.element( child, this.options ) );
      }.bind( this ) );

   }
}

/**********************************************************************/

Tree.Node = Class.create();
Tree.Node.prototype = {
   initialize: function( element, options ) {
      this.li = $( element );
      this.uls = new Array();
      this.root = false;

      this.options = { 
         more: '/images/plus.png',
         less: '/images/minus.png'
      }
      Object.extend( this.options, options );

      this.setup();
   },

   setup: function() {
      var name = "";
      var children = this.li.immediateDescendants();

      children.each( function( child ) {
         name = child.tagName || "";
         if( name != "UL" )
            return;

         this.uls.push( new Tree( child, this.options ) );
      }.bind( this ) );

      this.checkRoot();
   },

   checkRoot: function( ) {
      if( this.uls.length == 0 )
         return;

      this.root = true;
      Element.addClassName( this.li, 'root' );
      this.tog = Builder.node( 'img', 
         { className: 'toggle', src: this.options.less } );

      this.li.insertBefore( this.tog, this.li.childNodes[0] );
      this.tog.onclick = this.closeChildren.bindAsEventListener( this );
   },

   closeChildren: function( event ) {
      var node;
      this.uls.each( function( ul ) { 
         node = ul.ul;
         if( node.visible() ) {
            Effect.BlindUp( node );
            this.tog.src = this.options.more;
         }
         else {
            Effect.BlindDown( node );
            this.tog.src = this.options.less;
         }
      }.bind( this ) );
   }

}
