function push(value, stack)
{
	stack[stack.length] = value;
}

function pop(stack)
{
	if (stack.length == 0)
		return false;

	var ret = stack[stack.length - 1];
	stack.length--;
	return ret;
}

function menu_SetBgColor(nodenum)
{
	this.overnode = nodenum;
	var curnode = GetById('tr_' + this.instance + '_' + nodenum);
	curnode.style.background = this.overBgColor;
}

function menu_RestoreBgColor(nodenum)
{
	this.overnode = -1;
	var curnode = GetById('tr_' + this.instance + '_' + nodenum);
	curnode.style.background = this.outBgColor;
}

function menu_GetNode(nodenum)
{
	var struct =  (menu_GetNode.arguments.length == 1) ? this.struct : menu_GetNode.arguments[1];
	var result = false;
	
	for (var i = 0; i < struct.length; i++)
	{
		if (struct[i]['nodenum'] == nodenum)
			return struct[i];

		if (struct[i]['child'] != null)
		{
			result = this.GetNode(nodenum, struct[i]['child']);
			if (result != false)
				return result;
		}
	}
	
	return result;
}

function menu_Hide()
{
	var stacklength = this.stack.length;
	
	for (var i = 0; i < stacklength; i++)
	{
		var curmenu = pop(this.stack);
		var struct = this.GetNode(this.overnode);

		if ((curmenu != this.overnode) && (struct['menunum'] != curmenu))
		{
			GetById('table_' + this.instance + '_' + curmenu).style.visibility = 'hidden';
			this.lefttoright = true;
		}
		else
		{
			push(curmenu, this.stack);
			return;
		}
	}
}

function countOffset(element)
{
	var offset = element.offsetLeft;
	while (element.parentNode)
	{
		element = element.parentNode;
		offset += element.offsetLeft;
	}
	return offset;
}

function menu_Show(nodenum)
{
	if (!this.run)
		return false;

	this.SetBgColor(nodenum);
	this.Hide();

	for (var i = 0; i < this.stack.length; i++)
	{
  	if (this.stack[i] == nodenum)
			return;
	}
	
	this.overnode = nodenum;

	var showmenu = GetById('table_' + this.instance + '_' + nodenum);

	if (!showmenu)
		return;

	push(nodenum, this.stack);

	var struct = this.GetNode(nodenum);
	var curmenu = GetById('table_' + this.instance + '_' + struct['menunum']);
	var curnode = GetById('tr_' + this.instance + '_' + nodenum, curmenu.document);

	var parentMenu = GetById(menu_Show.arguments[1]);
	var x = parentMenu.offsetLeft - 1 + (this.isIe ? GetById('wrapper').offsetLeft : 0);
	var y = parentMenu.clientHeight + GetById('header').clientHeight + 1;

	showmenu.style.left = x + 'px';
	showmenu.style.top = y + 'px';
	var width = GetById(menu_Show.arguments[1]).clientWidth;

	if (!this.isIe)
		width++;

	showmenu.style.width = width + 'px';
	showmenu.style.visibility = 'visible';
}

function menu_Out(nodenum)
{
	if (!this.run)
		return false;
	
	this.RestoreBgColor(nodenum);
	clearTimeout(this.timeout);
	this.timeout = setTimeout(this.instance + '.Hide()', this.overTimeout);
}

function menu_Run()
{
	this.run = true;
	var firstlevel = (menu_Run.arguments.length == 0);
	var struct =  firstlevel ? this.struct : menu_Run.arguments[0];
	var tableid = firstlevel ? -1 : menu_Run.arguments[1];
	this.tmpcreatemenu[this.menucounter] = '<div id="table_' + this.instance + '_' + tableid + '" style="position: absolute; z-index:' + this.menucounter + '; visibility: hidden;">';

	for (var i = 0; i < struct.length; i++)
	{
		this.tmpcreatemenu[this.menucounter] += '<div style="background: ' + this.outBgColor + '" onmouseover="' + this.instance + '.Show(' + struct[i]['nodenum'] + ')" onmouseout="' + this.instance + '.Out(' + struct[i]['nodenum'] + ')">';
		this.tmpcreatemenu[this.menucounter] += '<div class="hoverMenulist"><a href="' + struct[i]['link'] + '"><div class="hoverMenu';

		switch (navigator.appName)
		{
			case "Netscape":
			case "Gecko":
			case "Mozilla":
			case "Safari":
				this.tmpcreatemenu[this.menucounter] += 'FF';
				break;
			default:
			break;
		}

		this.tmpcreatemenu[this.menucounter] += '" id="tr_' + this.instance + '_' + struct[i]['nodenum'] + '">' + struct[i]['text'] + '</div></a></div>';
		struct[i]['menunum'] = tableid;
		if (struct[i]['child'] != null)
		{
			this.menucounter++;
			this.Run(struct[i]['child'], struct[i]['nodenum']);
		}

		this.tmpcreatemenu[this.menucounter] += '</div>';
	}

	this.tmpcreatemenu[this.menucounter] += '</div>';

	WriteHtml(this.tmpcreatemenu[this.menucounter]);
	this.menucounter--;
}

function menu_AddNode(text, link, parnum)
{
	if (parnum == null)
	{
		var rootlength = this.struct.length;
		this.struct[rootlength] = new Array(5);
		this.struct[rootlength]['text'] = text;
		this.struct[rootlength]['nodenum'] = this.curnode;
		this.struct[rootlength]['child'] = null;
		this.struct[rootlength]['menunum'] = -1;
		this.struct[rootlength]['link'] = link;
	}
	else
	{
		var struct = this.GetNode(parnum);
		var tmparr = new Array(5);
		tmparr['text'] = text;
		tmparr['nodenum'] = this.curnode;
		tmparr['child'] = null;
		tmparr['menunum'] = -1;
		tmparr['link'] = link;

		if (struct['child'] == null)
			struct['child'] = new Array();

		curlength =  struct['child'].length;
		struct['child'][curlength] = tmparr;
	}
	
	return this.curnode++;
}

function Menu(instance)
{
	this.instance = instance;

	// Private
	this.isIe = navigator.appName == "Microsoft Internet Explorer";
	this.struct = new Array();
	this.tmpcreatemenu = new Array();
	this.menucounter = 0;
	this.curnode = 0;
	this.lefttoright = true;
	this.stack = new Array();
	this.overnode = -1;
	this.timeout = 0;
	this.overTimeout = 500;

	this.overBgColor = '#E1001A';
	this.outBgColor = '#666666';
	this.run = false;

	// Private
	this.Hide = menu_Hide;
	this.GetNode = menu_GetNode;
	this.SetBgColor = menu_SetBgColor;
	this.RestoreBgColor = menu_RestoreBgColor;

	// Public
	this.AddNode = menu_AddNode;
	this.Run = menu_Run;
	this.Show = menu_Show;
	this.Out = menu_Out;
}