/**
 * Menu class and Effect library
 * @author Sjoerd Andringa (andringa-AT-quicknet.nl)
 * @copyright (c) 2007, Sjoerd Andringa
 * @license This code is distributed under the MIT license
 * @version 1.20070520
 * Depents on Prototype JavaScript framework, version 1.5.1
 */
	
var Menu = Class.create();
Menu.prototype = {
	initialize: function(properties){
		properties = properties || {};
		this._offsetX = properties.offsetX || 0;
		this._offsetY = properties.offsetY || 0;
		this._submenus = [];
		this._menuNode = $(document.createElement('div'));
		Object.extend(this._menuNode, properties.attributes);
		this._menuNode.setStyle({height: '0px', overflow: 'hidden', display: 'block', position: 'absolute'});		
		this._menuNode._fullHeight = 0;		
		/* register events */	
		var menu = this;
		Object.extend(this._menuNode, {
			onmouseover: function(){
				Effect.blindDown(this, this._fullHeight);
				this._mouseover = true;
			},
			onmouseout: function(){	
				window.setTimeout(function(){
					if(!menu._trigger._mouseover && !menu._menuNode._mouseover)
							Effect.blindUp(menu._menuNode);
				}, 200);
				this._mouseover = false;
			}
		});				
		/* add menu node to page */
		document.body.appendChild(this._menuNode);
	},
	addLink: function(text, url, attributes){
		attributes = attributes || {};
		var item = this._addItem('a', text, Object.extend(attributes, {href: url}));	
	},
	addMenu: function(text, new_menu, attributes){
		attributes = attributes || {};
		var item = this._addItem('div', text, attributes, {cursor: 'default'});	
		new Insertion.Top(item, "<div style=\"float: right\">&#187;</div>");		
		this._submenus.push(new_menu);
		new_menu.attachTo(item);
		parentMenu = this;
		/* make parent menu react to events on this menu */
		prevOmover = new_menu._menuNode.onmouseover;
		new_menu._menuNode.onmouseover = function(){
			if(typeof prevOmover == "function"){
				prevOmover.call(this);
			}
			parentMenu._menuNode.onmouseover();
		}
		prevOmout = new_menu._menuNode.onmouseout;
		new_menu._menuNode.onmouseout = function(){
			if(typeof prevOmout == "function"){
				prevOmout.call(this);
			}
			parentMenu._menuNode.onmouseout();
		}
	},
	_addItem: function(tag, text, attributes, css){
		var item = $(document.createElement(tag));
		Object.extend(item, attributes);
		item.setStyle(Object.extend({display: 'block'},css));
		item.update(text);
		this._menuNode.appendChild(item);
		/* update full height */
		this._menuNode._fullHeight += item.getHeight();		
		return item;
	},
	attachTo: function(trigger){
		this._trigger = $(trigger);
		this._trigger.menu = this;
		Object.extend(this._trigger, {
			onmouseover: function(){
				Effect.blindDown(this.menu._menuNode, this.menu._menuNode._fullHeight);
				this._mouseover = true;
			},
			onmouseout: function(){	
				menu = this.menu;
				trigger = this;
				window.setTimeout(function(){
					if(!menu._menuNode._mouseover && !trigger._mouseover)
						Effect.blindUp(menu._menuNode);
				}, 200);
				this._mouseover = false;
			}
		});
		this._putInPlace();
	},
	_putInPlace: function(){
		this._menuNode.setStyle({
			top:	(Position.cumulativeOffset(this._trigger)[1]+this._offsetY)+'px',
			left:   ((Position.cumulativeOffset(this._trigger)[0]+this._trigger.getWidth())+this._offsetX)+'px'
		});
		this._submenus.each(function(submenu){
			submenu._putInPlace();
		});
	}
}
/*----------------------------------------------------------------------------------------------------------*/
/**
 * Effect library
 */
var Effect = {
	_speed: 0.1,
	_interval: 20,
	blindDown: function(el, to){
		el = $(el);
		if(typeof el._iv == "number")
			window.clearInterval(el._iv);
		el.show();
		el._iv = window.setInterval(function(){
			curHeight = el.getHeight();
			if(curHeight >= to){
				window.clearInterval(el._iv);
			}else{				
				delta = to - curHeight;
				step = Math.ceil(delta * Effect._speed);
				el.style.height = (curHeight + step)+'px';
			}		
		}, Effect._interval);
	},
	blindUp: function(el){
		el = $(el);
		if(typeof el._iv == "number")
			window.clearInterval(el._iv)
		el._iv = window.setInterval(function(){			
			curHeight = el.getHeight();
			if(curHeight == 0){
				window.clearInterval(el._iv);
				el.hide();
			}else{				
				step = Math.ceil(curHeight * Effect._speed);
				el.style.height = (curHeight - step)+'px';
			}		
		}, Effect._interval);
	}
}
/*----------------------------------------------------------------------------------------------------------*/
/**
 * Debugging methods
 */
var debugger_enabled = false;

enableDebugger = function(){
	debugger_enabled = true;
}
debug = function(text){
	if(debugger_enabled){
		if($('debug') == null)
			new Insertion.Top(document.body, "<div style=\"float: right; font-family: courier; width: 300px\" id=\"debug\"></div>");
		new Insertion.Top($('debug'), "<div style=\"padding: 5px; border-left: 1px solid #bbb; border-bottom: 1px solid #bbb\">"+text+"</div>");
	}
};