/**
 * Add support for function object binding
 * @param {Object} context
 */
Function.prototype.bindObject = function(context) {
    if(typeof(context) == null) {
        return this;
    }
	
    var __method = this;
    return function() {
        return __method.apply(context);
    }
}

/**
 * Horizontal menu class constructor
 * 
 * @param string element
 * @param string submenuClass
 * @param string hoverClass
 */
var HorizontalMenu = function(menuContainer, submenuClass, hoverClass) {
    if ($(menuContainer)){
        this.items = [];
        this.container = document.getElementById(menuContainer);
        if(!this.container) {
            throw('Cannot find menu container object in DOM! (debug: menuContainer = ' + menuContainer + ')');
        }
        this.submenuClass = submenuClass || 'submenu';
        this.hoverClass = hoverClass || 'HM-hover';
	
        this.active = false;
        this.activeItem = null;
        this.inTimeOut = null;
        this.outTimeOut = null;
	
        for(var i=0; i<this.container.childNodes.length; i++) {
            if("LI" == this.container.childNodes[i].tagName) {
                this.addItem(this.container.childNodes[i]);
            }
        }
    }
};
HorizontalMenu.prototype.addItem = function(item) {
    var menuItem = new HorizontalMenu.Item(item, this);
    this.items.push(menuItem);
}

/**
 * Menu item constructor
 * 
 * @param Element element
 * @param HorizontalMenu menu
 */
HorizontalMenu.Item = function(element, menu) {
    this.menu = menu;
    this.element = element;
    this.hasSubmenu = (this.element.className.indexOf(this.menu.submenuClass) != -1 ? true : false);
	
    this.element.onmouseover = function() {
        if(this.menu.active) {
            this.mouseOver();
        }
        else {
            this.menu.inTimeOut = setTimeout(this.mouseOver.bindObject(this), 100);
        }
    }.bindObject(this);
    this.element.onmouseout = function() {
        if(!this.hasSubmenu) {
            this.mouseOut();
        }
        else {
            this.menu.outTimeOut = setTimeout(this.mouseOut.bindObject(this), 500);
        }
        clearTimeout(this.menu.inTimeOut);
    }.bindObject(this);
}
HorizontalMenu.Item.prototype.mouseOver = function() {
    if(this.menu.active && (this.menu.activeItem == this)) {
        clearTimeout(this.menu.outTimeOut);
        return;
    }
	
    for(i=0; i<this.menu.items.length; i++) {
        this.menu.items[i].hide();
    }
    /*
	if(this.menu.activeItem) {
		this.menu.activeItem.hide();
	}
	*/
	
    this.show();
    this.menu.active = true;
    this.menu.activeItem = this;
    clearTimeout(this.menu.outTimeOut);
}
HorizontalMenu.Item.prototype.mouseOut = function() {
    this.hide();
    this.menu.active = false;
    this.menu.activeItem = null;
}
HorizontalMenu.Item.prototype.show = function() {
    if(this.element.className.indexOf(this.menu.hoverClass) != -1) {
        return;
    }
	
    var newClasses = [];
    var elementClasses = this.element.className.split(' ');
    for(i=0; i<elementClasses.length; i++) {
        if(!elementClasses[i].length) {
            continue;
        }
        newClasses.push(elementClasses[i]);
    }
    newClasses.push(this.menu.hoverClass);
	
    this.element.className = newClasses.join(' ');
}
HorizontalMenu.Item.prototype.hide = function() {
    if(this.element.className.indexOf(this.menu.hoverClass) == -1) {
        return;
    }
	
    var newClasses = [];
    var elementClasses = this.element.className.split(' ');
    for(i=0; i<elementClasses.length; i++) {
        if(!elementClasses[i].length || elementClasses[i] == this.menu.hoverClass) {
            continue;
        }
        newClasses.push(elementClasses[i]);
    }
	
    this.element.className = newClasses.join(' ');
}

