
//-----Begin LoadManager-----------------
function LoadManager() {	
	// obviously you have to write the specific implementation to define what 'loaded' means.  This is just a dummy implementation

	// Typically I think you'll want to keep track of a couple things; when your div's load, when your objects get initialized.  In the leakey prototype for instance, there were three seperate switches inside the loadManager, two for when main divs were finished loading, and one for  when the intro-motion was completed.  Only then was the global allIsLoaded switch flipped.   

	//  Bottom line is that in this code, the mouse eventHandlers are all wrapped in if (myLoadManager.allIsLoaded()) statements
	this.privateAllIsLoaded = true;
}

LoadManager.prototype.allIsLoaded = function() {
	return this.privateAllIsLoaded;
}

var myLoadManager = new LoadManager();
//-----End LoadManager-----------------

//-----Begin Browser-----------------
function Browser() {
	var b=navigator.appName;
	if (b=="Netscape") this.b="ns";
	else if ((b=="Opera") || (navigator.userAgent.indexOf("Opera")>0)) this.b = "opera";
	else if (b=="Microsoft Internet Explorer") this.b="ie";
	this.version=navigator.appVersion;
	this.v=parseInt(this.version);
	this.ns=(this.b=="ns" && this.v>=4);
	this.ns4=(this.b=="ns" && this.v==4);
	//this.ns6=(this.b=="ns" && this.v==5);
	this.ie=(this.b=="ie" && this.v>=4);
	this.ie4=(this.version.indexOf('MSIE 4')>0);
	this.ie5=(this.version.indexOf('MSIE 5')>0);
	this.ie55=(this.version.indexOf('MSIE 5.5')>0);
	this.ie6up = ((navigator.appVersion.indexOf("MSIE 6")!=-1)||(navigator.appVersion.indexOf("MSIE 7")!=-1));
	this.opera=(this.b=="opera");
	var ua=navigator.userAgent.toLowerCase();
	this.mac = (ua.indexOf("mac")!=-1);
}
//-----End Browser-----------------

var is = new Browser();  // this object is essentially global,static. 


//-----Begin LyrObj-----------------

function LyrObj(divId) {   
	this.name="";
	this.x = 0;
	this.y = 0;
	this.width=0;
	this.height=0;
}

LyrObj.prototype.px = (is.v>=5)?"px":"";
LyrObj.prototype.hideSyntax = (is.ns4)? "hide":"hidden";
LyrObj.prototype.showSyntax = "visible";

LyrObj.prototype.init = function(divId) {  
	this.name = divId;
	if (is.ns4) this.ob = eval("document." +divId);
	else if (is.ie4) this.ob = document.all(divId);
	else this.ob = document.getElementById(divId);
	// position should always be pushed to the dom for these objects, but width and height can be pulled from the dom safely
	this.width	=	this.getWidth();
	this.height	=	this.getHeight();
}

// these 2 functions will attempt to pull the positions of the object from an embedded location within a page. It will check the offsets with each parent and then check the parents offsets with its parents and so on and so forth.  In a typical page there can be quite a lot of parents. note: td, tr and table are accounted for seperately.
LyrObj.prototype.getInlineLeft = function() {
	if (is.ns4) return this.ob.pageX;
	else if ((is.ie) || (is.opera)) {
		var elem = this.ob;
		var xPos = 0;
		var yPos = 0;
		while (elem.offsetParent != null) {
			xPos += elem.offsetLeft;
			elem = elem.offsetParent;
		}
		return xPos;
	}	
	else return (this.ob.offsetLeft + document.body.offsetLeft);
}

LyrObj.prototype.getInlineTop = function() {
	if (is.ns4) return this.ob.pageY;
	else if ((is.ie) || (is.opera)) {
		var elem = this.ob;
		var yPos=0;
		while (elem.offsetParent != null) {
			yPos += elem.offsetTop;
			elem = elem.offsetParent;
		}
		return yPos;
	}
	else return (this.ob.offsetTop+ document.body.offsetTop);
}

LyrObj.prototype.getWidth = function () {	
	if (is.ns4) return this.ob.clip.width;
	else if (is.opera) return this.ob.style.pixelWidth;
	else return this.ob.offsetWidth;
}

LyrObj.prototype.getHeight = function () {
	if (is.ns4) return this.ob.clip.height;
	else if (is.opera) return this.ob.style.pixelHeight;
	else return this.ob.offsetHeight;
}

LyrObj.prototype.hide = function() {
	if (is.ns4) this.ob.visibility = this.hideSyntax;
	else this.ob.style.visibility = this.hideSyntax;
}

LyrObj.prototype.show = function() {	
	if (is.ns4) this.ob.visibility = this.showSyntax;
	else this.ob.style.visibility = this.showSyntax;
}

LyrObj.prototype.moveLayerTo = function(toX, toY) {
	this.x = toX;
	this.y = toY;
}

LyrObj.prototype.moveLayerBy = function(dX, dY) {
	this.x += dX;
	this.y += dY;
}

LyrObj.prototype.clipTo = function(x1,x2,y1,y2) {
	if (is.ns4){
		this.ob.clip.left   = x1;
		this.ob.clip.right  = x2;
		this.ob.clip.top	= y1;
		this.ob.clip.bottom = y2;
	}
	else {
		this.ob.style.clip = "rect("+y1+"px "+x2+"px "+y2+"px "+x1+"px)";
	}
}

LyrObj.prototype.updateLayer =  function() {
	if (is.ns4) {
		this.ob.left = Math.round(this.x) + this.px;
		this.ob.top = Math.round(this.y)+ this.px ;
	}
	else {
		this.ob.style.left = Math.round(this.x) + this.px;
		this.ob.style.top = Math.round(this.y)  + this.px;
	}
}

//----------End LyrObj---------------------


//----------Begin MenuManager-----------------

function MenuManager(menuNames, subMenuNames, selectedImageNumber, hasGraphicalTextTriggers) {
	this.isNavReady = false;
	this.isSubNavReady = false;
	this.isNewlyLoaded = true;
	this.isSubNewlyLoaded = true;
	this.hasGraphicalTextTriggers = hasGraphicalTextTriggers;
	this.selectedImageNumber = selectedImageNumber;
	this.selectedSubImageNumber = -1;
	this.mNames = new Array();
	this.smNames = new Array();
	this.menus = new Array();
	this.subMenus = new Array();
	this.numberOfMenus = menuNames.length;
	this.numberOfSubMenus = subMenuNames.length;
	for (i=0; i<this.numberOfMenus; i++ ) {
		this.mNames[i] = menuNames[i]
		this.menus[i] = new LyrObj();
		this.menus[i].init(this.mNames[i]+ "_menu");
	}
	for (n=0; n<this.numberOfSubMenus; n++ ) {
		this.smNames[n] = subMenuNames[n]
		this.subMenus[n] = new LyrObj();
		this.subMenus[n].init(this.smNames[n]+ "_submenu");
	}
	if ((this.hasGraphicalTextTriggers) && (this.selectedImageNumber >-1)) roll(-1,this.mNames[this.selectedImageNumber],"on");
	this.setupMenuPositions();
	this.activeMenu = -1;
	this.activeSubMenu = -1;
	this.specificallyOverTheParentElement = false;
	this.specificallyOverTheSubParentElement = false;
	this.mouseX = 0;
	this.mouseY = 0;
	this.peskyFormFields = false;
}


MenuManager.prototype.setupMovableFormFields = function(originalX, originalY) {
	if (is.ns4) {
		this.peskyFormFields = new LyrObj("movableformfielddiv");
		this.peskyFormFields.originalX = originalX;
		this.peskyFormFields.originalY = originalY;
	}
}


MenuManager.prototype.mouseIsOverSubnav = function() {
	//	if activeMenu indicates that mouse has activated a menu recently (activeMenu!=-1) , AND the mouseOut from the parent Element HAS been fired (!this.specificallyOverTheParentElement ) 
	if ((this.activeMenu!=-1) && (!this.specificallyOverTheParentElement )) {
		//  if mouse is actually outside of the 'active' subnav.
		if ((this.mouseX<this.menus[this.activeMenu].x) || (this.mouseX>this.menus[this.activeMenu].x + this.menus[this.activeMenu].width) || (this.mouseY<this.menus[this.activeMenu].y) || (this.mouseY>this.menus[this.activeMenu].y + this.menus[this.activeMenu].height)) return false;
		else return true;
	}
	// and if activeMenu was already -1, or we're still over the parent Element (menuMouseOut has not yet fired) just return false
	else return false;
}


MenuManager.prototype.mouseIsOverSubSubnav = function() {
	//	if activeMenu indicates that mouse has activated a menu recently (activeMenu!=-1) , AND the mouseOut from the parent Element HAS been fired (!this.specificallyOverTheParentElement ) 
	if ((this.activeSubMenu!=-1) && (!this.specificallyOverTheSubParentElement )) {
		//  if mouse is actually outside of the 'active' subnav.
	//alert("mouseX="+this.mouseX+"\nX="+this.subMenus[this.activeSubMenu].x+"\nmouseY="+this.mouseY+"\nY="+this.subMenus[this.activeSubMenu].y+"\nHeight="+this.subMenus[this.activeSubMenu].height+"\nWidth="+this.subMenus[this.activeSubMenu].width);
		if ((this.mouseX<this.subMenus[this.activeSubMenu].x) || (this.mouseX>this.subMenus[this.activeSubMenu].x + this.subMenus[this.activeSubMenu].width) || (this.mouseY<this.subMenus[this.activeSubMenu].y) || (this.mouseY>this.subMenus[this.activeSubMenu].y + this.subMenus[this.activeSubMenu].height)) return false;
		else return true;
	}
	// and if activeMenu was already -1, or we're still over the parent Element (menuMouseOut has not yet fired) just return false
	else return false;
}


MenuManager.prototype.setupMenuPositions = function () {
	for (i=0; i<this.numberOfMenus; i++) {
		var imgX=0;
		var imgY=0;
		var imgWidth = 0;
		var imgHeight = 0;
		var elem=null;
		if (is.ns4) {
			elem = eval(document.images[this.mNames[i]+"_image"])
			imgX = elem.x;
			imgY = elem.y;
			imgWidth = elem.width;
			imgHeight = elem.height;
		}
		else {
			if (is.ie4 && is.mac) elem = document.all[this.mNames[i]+"_image"];
			else if (is.ie4) elem = eval(this.mNames[i]+"_image");
			else elem = document.getElementById(this.mNames[i]+"_image");
			imgWidth = elem.offsetWidth;
			imgHeight = elem.offsetHeight;
			// more complicated than the ns4 method; we have to add up offsets to get actual pixel location of default image
			do {
				imgX += elem.offsetLeft;
				imgY += elem.offsetTop;
				elem = elem.offsetParent;
			}
			while (elem.offsetParent != null);
		}
		if (is.ns) {
			this.menus[i].x = imgX + imgWidth + 1;
		} else {
			this.menus[i].x = imgX + imgWidth;
		}
		this.menus[i].y = imgY - 1;
		this.menus[i].width = this.menus[i].getWidth();
		this.menus[i].height= this.menus[i].getHeight();
		this.menus[i].updateLayer();
	}
	if (this.numberOfMenus>0) this.isNavReady = true;
	
	for (i=0; i<this.numberOfSubMenus; i++) {
		var imgX=0;
		var imgY=0;
		var imgWidth = 0;
		var imgHeight = 0;
		var elem=null;
		if (is.ns4) {
			elem = eval(document.images[this.smNames[i]+"_arrow"])
			imgX = elem.x;
			imgY = elem.y;
			imgWidth = elem.width;
			imgHeight = elem.height;
		}
		else {
			if (is.ie4 && is.mac) elem = document.all[this.smNames[i]+"_arrow"];
			else if (is.ie4) elem = eval(this.smNames[i]+"_arrow");
			else elem = document.getElementById(this.smNames[i]+"_arrow");
			imgWidth = elem.offsetWidth;
			imgHeight = elem.offsetHeight;
			// more complicated than the ns4 method; we have to add up offsets to get actual pixel location of default image
			do {
				imgX += elem.offsetLeft;
				imgY += elem.offsetTop;
				elem = elem.offsetParent;
			}
			while (elem.offsetParent != null);
		}
		if (is.ns) {
			this.subMenus[i].x = imgX + imgWidth + 8;
		} else {
			this.subMenus[i].x = imgX + imgWidth + 12;
		}
		if (is.ns) {
			this.subMenus[i].y = imgY - 1;
		} else {
			this.subMenus[i].y = imgY - (0*i) - 1;
		}
		this.subMenus[i].width = this.subMenus[i].getWidth();
		this.subMenus[i].height= this.subMenus[i].getHeight();
		this.subMenus[i].updateLayer();
	}
	if (this.numberOfSubMenus>0) this.isSubNavReady = true;
}


MenuManager.prototype.mouseMoveHandler = function(e) {
	var scrollOffsetX = ((is.ie5)||(is.ie6up))?(document.body.scrollLeft):0;
	var scrollOffsetY = ((is.ie5)||(is.ie6up))?(document.body.scrollTop):0;
	this.mouseX = (is.ns)?e.pageX:event.x + scrollOffsetX;
	this.mouseY = (is.ns)?e.pageY:event.y + scrollOffsetY;
	this.potentiallyCloseSubnav();
	this.potentiallyCloseSubSubnav();
	// not sure if this helps keep netscape4's event queue from getting gummed up, but it doesnt hurt. 
	return true;
}


// function closes the active subnav if the mouse is not over it. 
// 2 ways this function can be called.  Either from a mouseout from a parentElement, of by mouseMoveHandler
MenuManager.prototype.potentiallyCloseSubnav = function() {
	// this function is the only way to set this.activeMenu to -1, so if (activeMenu==-1), this will do nothing. 
	// the other two conditions abort the hide operation, and are essentially (isOverParent), and (isOverSubnav). 
	//	alert(this.activeMenu +", " + this.specificallyOverTheParentElement  +", " +  this.mouseIsOverSubnav());
	if ((this.activeSubMenu!= -1) || (this.specificallyOverTheParentElement) || (this.mouseIsOverSubSubnav())) {
		this.menus[this.activeMenu].show();
		this.menus[this.activeMenu].updateLayer();
		if ((this.hasGraphicalTextTriggers) && (this.activeMenu != this.selectedImageNumber)&& (!this.isNewlyLoaded)) roll(-1,this.mNames[this.activeMenu],"over");
	} else if ((this.activeMenu!= -1) && (!this.specificallyOverTheParentElement) && (!this.mouseIsOverSubnav())) {
		this.menus[this.activeMenu].hide();
		this.menus[this.activeMenu].updateLayer();
		// if the system thinks the mouse is not over the selected Global Nav parent, and menuTrigger has never run since the page loaded, switch off the active image. 
		if ((this.hasGraphicalTextTriggers) && (this.activeMenu != this.selectedImageNumber)&& (!this.isNewlyLoaded)) roll(-1,this.mNames[this.activeMenu],"off");
		this.activeMenu=-1;
		if (this.peskyFormFields) {
			this.peskyFormFields.moveLayerTo(this.peskyFormFields.originalX, this.peskyFormFields.originalY);
			this.peskyFormFields.updateLayer();
		}
	}
}


MenuManager.prototype.potentiallyCloseSubSubnav = function() {
	if ((this.activeSubMenu!= -1) && (!this.specificallyOverTheSubParentElement) && (!this.mouseIsOverSubSubnav())) {
		this.subMenus[this.activeSubMenu].hide();
		this.subMenus[this.activeSubMenu].updateLayer();
		//if ((this.activeMenu != this.selectedImageNumber)&& (!this.isNewlyLoaded)) roll(-1,this.mNames[this.activeMenu],"off");
		this.activeSubMenu=-1;
		if (this.peskyFormFields) {
			this.peskyFormFields.moveLayerTo(this.peskyFormFields.originalX, this.peskyFormFields.originalY);
			this.peskyFormFields.updateLayer();
		}
	}
}


//  shows the menu defined by the integer argument.  hides all other menus.  Flips an internal boolean to indicate that the mouse is over a parentElement, and sets an integer to hold which menu is active
MenuManager.prototype.menuTrigger = function(which) {
	if (this.isNavReady) {
	this.specificallyOverTheParentElement = true;
		this.activeMenu = which;
		if ((this.hasGraphicalTextTriggers) && (which != this.selectedImageNumber)) roll(-1,this.mNames[which],"over");
		for (i= 0; i<this.numberOfMenus; i++) {
			if (i==which) {
				this.menus[i].show();
				this.menus[i].updateLayer();
				if ((this.hasGraphicalTextTriggers) && (i != this.selectedImageNumber)&& (!this.isNewlyLoaded)) roll(-1,this.mNames[i],"over");
			}	
			else {
				this.menus[i].hide();
				this.menus[i].updateLayer();
				if ((this.hasGraphicalTextTriggers) && (i != this.selectedImageNumber)&& (!this.isNewlyLoaded)) roll(-1,this.mNames[i],"off");
			}
		}
		if (this.isNewlyLoaded) this.isNewlyLoaded = false;
		if (this.peskyFormFields) {
			this.peskyFormFields.moveLayerTo(-500,0);
			this.peskyFormFields.updateLayer();
		}
	}
}


MenuManager.prototype.subMenuTrigger = function(which) {
	if (this.isSubNavReady) {
	this.specificallyOverTheSubParentElement = true;
		this.activeSubMenu = which;
		//if ((which != this.selectedSubImageNumber)) document.getElementById(this.mNames[which]+"_menu").childNodes[this.selectedSubImageNumber].style.backgroundColor='#F6F8FA';
		for (i= 0; i<this.numberOfSubMenus; i++) {
			if (i==which) {
				this.subMenus[i].show();
				this.subMenus[i].updateLayer();
				//if ((i != this.selectedSubImageNumber)&& (!this.isSubNewlyLoaded)) document.getElementById(this.mNames[which]+"_menu").childNodes[this.selectedSubImageNumber].style.backgroundColor='#F6F8FA';
			}	
			else {
				this.subMenus[i].hide();
				this.subMenus[i].updateLayer();
				//if ((i != this.selectedSubImageNumber)&& (!this.isSubNewlyLoaded)) document.getElementById(this.mNames[which]+"_menu").childNodes[this.selectedSubImageNumber].style.backgroundColor='#ffffff';
			}
		}
		this.menus[this.activeMenu].show();
		this.menus[this.activeMenu].updateLayer();
		if (this.isSubNewlyLoaded) this.isSubNewlyLoaded = false;
		if (this.peskyFormFields) {
			this.peskyFormFields.moveLayerTo(-500,0);
			this.peskyFormFields.updateLayer();
		}
	}
}


MenuManager.prototype.attachEventHandlers = function() {
	var trigger, image, menu, subtrigger, submenu, subarea;
	for (i=0; i<this.numberOfMenus; i++) {
		trigger = document.getElementById(this.mNames[i]+"_trigger");
		image = document.getElementById(this.mNames[i]+"_image");
		menu = document.getElementById(this.mNames[i]+"_menu");
		eval("trigger.onmouseover = function() {menuTrigger("+i+");}");
		eval("trigger.onmouseout = function() {menuMouseOut();}");
		// now to attach the little onmouseovers to the subnav items. 
		for (j=0;j<menu.childNodes.length;j++ ) {
			var node = menu.childNodes[j];
			//if (node.nodeType==1){
				eval("node.onmouseover = function() {this.style.backgroundColor='#F6F8FA';}");
				eval("node.onmouseout = function() {this.style.backgroundColor='#ffffff';}");
				if (is.ie) node.style.width="170px";
				eval("node.onclick = function() {document.location = this.childNodes[0].getAttribute('href');}");
			//}
		}
	}
	for (i=0; i<this.numberOfSubMenus; i++) {
		subtrigger = document.getElementById(this.smNames[i]+"_subtrigger");
		submenu = document.getElementById(this.smNames[i]+"_submenu");
		subarea = document.getElementById(this.smNames[i]+"_subarea");
		eval("subtrigger.onmouseover = function() {subMenuTrigger("+i+");}");
		eval("subtrigger.onmouseout = function() {subMenuMouseOut();}");
		// now to attach the little onmouseovers to the subnav items. 
		for (j=0;j<submenu.childNodes.length;j++ ) {
			var subnode = submenu.childNodes[j];
			if (subnode.nodeType==1){
				eval("subnode.onmouseover = function() {this.style.backgroundColor='#F6F8FA';}");
				eval("subnode.onmouseout = function() {this.style.backgroundColor='#ffffff';}");
				if (is.ie) node.style.width="170px";
				eval("subnode.onclick = function() {document.location = this.childNodes[0].getAttribute('href');}");
			}
		}
	}
}


// all this does is flip off the boolean, so the mouse is no longer over a parent Element. 
MenuManager.prototype.menuMouseOut = function () {
	if (this.isNavReady) {
		this.specificallyOverTheParentElement = false;
		// set a timeout to potentially deactivate the menus.
		setTimeout("potentiallyCloseSubnav()", 200);
	}
}


MenuManager.prototype.subMenuMouseOut = function () {
	if (this.isSubNavReady) {
		this.specificallyOverTheSubParentElement = false;
		// set a timeout to potentially deactivate the menus.
		setTimeout("potentiallyCloseSubSubnav()", 200);
	}
}

// END MenuManager
