
	HG_LocalDebug = false;
	HG_AJaxError  = ':::: AJAX Called Errored Out ::::';
	HG_GlobalObj  = '';

	//
	//	HG_LoadIFrame :: Display as Currency Number with Thousand and Decimal Format
	//
	//	: URL		--
	//	: Target  	--
	//	: HGTID		--
	//	: PRC 		--
	//
	HG_LoadIFrame = function(LoadOptions) {
		
		if (GetID(LoadOptions.Target).innerHTML == '' || LoadOptions.Reload == true) {
			LoadOptions.URL = ReplaceStr(LoadOptions.URL, '%26', '&');
			GetID(LoadOptions.Target).innerHTML = '<iframe src="' + LoadOptions.URL + '" allowtransparency="true" frameborder="0" style="width:100%; height:100%; z-index:0;"></iframe>';
		}
	}

	//
	//	HG_CurrencyFormat :: Display as Currency Number with Thousand and Decimal Format
	//
	//	: Amount	-- Formatted Amount
	//	: ThouDel  	-- Thousand Delimiter
	//	: DecDel	-- Decimal Delimiter
	//	: US 		-- Is Value Starting In US
	//
	HG_CurrencyFormat = function(Amount, ThouDel, DecDel, US) {

		
		if (ThouDel == undefined) {
			ThouDel = HG_ThouDel;
			DecDel 	= HG_DecDel;
		}

		/*
			Amount = Number('0.00');	
		*/
		//alert(Amount + ' : ' + ThouDel +' : ' + DecDel);

		//
		// Convert to US Number
		Amount = Number(HG_CurrencyToNumber(Amount, ThouDel, DecDel));

		
		if (isNaN(Amount) == true) {
			Amount = Number('0.00');	
		}
		
		Amount = Amount.toFixed(2);
		var Thou = ReplaceStr(GetToken(Amount, 1, '.'), ',', '');
		var Dec  = GetToken(Amount, 2, '.');

		/*
		if (US == true) {
			Amount = Amount.toFixed(2);
			var Thou = ReplaceStr(GetToken(Amount, 1, '.'), ',', '');
			var Dec  = Number(GetToken(Amount, 2, '.'));
		} else {
			alert(ThouDel + ' - ' + DecDel);
			var Thou = ReplaceStr(GetToken(String(Amount), 1, DecDel), ThouDel, '');
			var Dec  = GetToken(String(Amount), 2, DecDel);
			alert(Thou + ' - ' + Dec);
		}
		*/
		
		if (DecDel != '' && Dec == '') {
			Dec = '00';	
		}
		
		var NewStr = '';
		var Counter = 0;

		if (Math.abs(Thou).toString().length >= 4) { 
			for (var t=Thou.length;t>=0;t--) {
				if (Counter==4) {
					NewStr = ThouDel + NewStr;
					Counter=1
				}
		
				NewStr = Thou.charAt(t) + NewStr;
				Counter++;
			}
		} else {
			NewStr = Thou;
		}
		return NewStr + DecDel + String(Dec);
	}
		
		
	//
	//	HG_CurrencyNumberFormat :: Display as Currency Number with Decimal Format
	//
	//	: Amount	-- Formatted Amount
	//	: ThouDel  	-- Thousand Delimiter
	//	: DecDel	-- Decimal Delimiter
	//	: US 		-- Is Value Starting In US
	//
	HG_CurrencyNumberFormat = function(Amount, ThouDel, DecDel, US, DecPlaces) {
		
		Amount = Number(Amount);
		
		if (isNaN(Amount) == true) {
			Amount = Number('0.00');	
		}
		
		if (ThouDel == undefined) {
			ThouDel = HG_ThouDel;
			DecDel 	= HG_DecDel;
		}
		
		if (DecPlaces == undefined) {
			DecPlaces = 2;
		}
		
		if (isNaN(Number(DecPlaces)) == true) {
			DecPlaces = 2;
		}
		
		if (US == true) {
			Amount = HG_RoundNumber(Amount, DecPlaces);
			
			var Thou = ReplaceStr(GetToken(Amount, 1, '.'), ',', '');
			var Dec  = GetToken(Amount, 2, '.');
		} else {
			var Thou = ReplaceStr(GetToken(Amount, 1, DecDel), ThouDel, '');
			var Dec  = GetToken(Amount, 2, DecDel);
		}
	
	
		if (DecDel != '' && Dec == '') {
			Dec = '00';	
		}
		
		return Thou + DecDel + Dec;
		
	}
	
	
	//
	//	HG_CurrencyToNumber :: Convert to a USA number for Math
	//
	//	: Amount	-- Formatted Amount
	//	: ThouDel  	-- Thousand Delimiter
	//	: DecDel	-- Decimal Delimiter
	//
	HG_CurrencyToNumber = function(Amount, ThouDel, DecDel, Reset) {
		
		
		if (Amount.toString().indexOf(DecDel) == 0) {
			Amount = '0' + Amount;
		}
		
		// ERA 1/12/2010
		if (ThouDel == ' ') {
			ThouDel = '#'
			Amount = ReplaceStr(Amount, ' ', '#');
		}
		
		if (DecDel == ' ') {
			DecDel = '~'
			Amount = ReplaceStr(Amount, ' ', '~');
		}
		
		var Thou = ReplaceStr(GetToken(Amount, 1, DecDel), ThouDel, '');
		
		if (Thou == Amount) {
			var Thou = ReplaceStr(GetToken(Amount, 1, '.'), ThouDel, '');
		}

		var Dec  = GetToken(Amount, 2, DecDel);

		if (Dec == '') {
			var Dec  = GetToken(Amount, 2, '.');
		}

		Amount = Number(Thou + '.' + Dec);
		
		if (isNaN(Amount) == true && (Reset == undefined || Reset == true)) {
			Amount = Number('0.00');	
		}
		
		return HG_RoundNumber(Amount, 2);
		
	}
	
	
	//
	//	HG_RoundNumber :: Round Number
	//
	//	: original_number	
	//	: decimals  		
	//
	HG_RoundNumber = function(original_number, decimals) {
		
		var result1 = original_number * Math.pow(10, decimals)
		var result2 = Math.round(result1)
		var result3 = result2 / Math.pow(10, decimals)
		return Number(HG_PadWithZeros(result3, decimals));
	}


	//
	//	HG_PadWithZeros :: Round Number
	//
	//	: rounded_value		
	//	: decimal_places  	
	//
	HG_PadWithZeros = function (rounded_value, decimal_places) {
	
		// Convert the number to a string
		var value_string = rounded_value.toString()
		
		// Locate the decimal point
		var decimal_location = value_string.indexOf(".")
	
		// Is there a decimal point?
		if (decimal_location == -1) {
			
			// If no, then all decimal places will be padded with 0s
			decimal_part_length = 0
			
			// If decimal_places is greater than zero, tack on a decimal point
			value_string += decimal_places > 0 ? "." : ""
		}
		else {
	
			// If yes, then only the extra decimal places will be padded with 0s
			decimal_part_length = value_string.length - decimal_location - 1
		}
		
		// Calculate the number of decimal places that need to be padded with 0s
		var pad_total = decimal_places - decimal_part_length
		
		if (pad_total > 0) {
			
			// Pad the string with 0s
			for (var counter = 1; counter <= pad_total; counter++) 
				value_string += "0"
			}
		return value_string
	}
	
	
	//
	//	HG_JSONToObject :: Converts a coldfusion JSON Var to 
	//
	//	: JSONObj -- A JSON Object		
	//
	//
	HG_JSONToObject = function (JSONObj) { 
		var o = JSONObj;
		if (typeof(JSONObj) == 'string') {
			JSONObj = HG_ToObject(JSONObj);
		}
		if (HG_IsArray(JSONObj)) {
			return JSONObj;
		}
		
		for (var name in JSONObj) {
			try {

				if (JSONObj[name].substring(0, 2) == '//') {
					var Val = JSONObj[name].substring(2, JSONObj[name].length);
					JSONObj[name] = Val.evalJSON();
				} else {
					if (JSONObj[name] != '') {
						JSONObj[name] = JSONObj[name].evalJSON();	
					}
				}
								
			} catch(err) {
				Dump(err, 'Invalid (HG_JSONToObject) name: ' + name);
				//alert(' JSONObj: ' + JSONObj[name]);
				//DumpObjectValue(err);	
				return false;
			}
		}

		
		return JSONObj;
	}
	HG_ConvertJSONtoJSObj = function (JSONObj) {
		return HG_JSONToObject(JSONObj);
	}


	//
	//	HG_ObjectToJSON :: 
	//
	//	: JSONObj -- A JS Object
	//	: Make sure 	.js is used
	//
	HG_ObjectToJSON = function (JSObj) {
		
	if (typeof(JSObj) == 'string') {
		try {
			JSObj = HG_ToObject(JSObj, true);
		} catch(e) {
			// Possible Error
			return JSObj;
		}
	} 
	 return JSON2.stringify(GetID(JSObj));
	}
	HG_ConvertJSObjtoJSONStr = function (JSObj) {
		return HG_ObjectToJSON(JSObj);
	}
	
	
	
	//
	//	HG_CreateJSON :: 
	//
	//	: JSONObj -- A JS Object
	//	: Make sure json2.js is used
	//
	HG_CreateJSON = function (Name, JSObj) {
		
	  return '{"' + Name + '":' + JSON2.stringify(GetID(JSObj)) +'}';
	  
	}
	HG_CreateJSObjtoJSONStr = function (Name, JSObj) {
		return HG_CreateJSObjtoJSONStr(Name, JSObj);
	}
	
/*


	//
	// 	HG_JSON_Escape
	//
	// 	If the string contains no control characters, no quote characters, and no
	// 	backslash characters, then we can safely slap some quotes around it.
	// 	Otherwise we must also replace the offending characters with safe escape
	//	sequences.
	//
	HG_JSON_Escape = function (string) {
		
		var escapable = /[\\\"\x00-\x1f\x7f-\x9f\u00ad\u0600-\u0604\u070f\u17b4\u17b5\u200c-\u200f\u2028-\u202f\u2060-\u206f\ufeff\ufff0-\uffff]/g,
			 meta = {    // table of character substitutions
				'\b': '\\b',
				'\t': '\\t',
				'\n': '\\n',
				'\f': '\\f',
				'\r': '\\r',
				'"' : '\\"',
				'\\': '\\\\'
			}
        escapable.lastIndex = 0;
        return escapable.test(string) ?
            '"' + string.replace(escapable, function (a) {
                var c = meta[a];
                return typeof c === 'string' ? c :
                    '\\u' + ('0000' + a.charCodeAt(0).toString(16)).slice(-4);
            }) + '"' :
            '"' + string + '"';
    }
			
	*/
	
	//
	//	HG_FormatCurrencyWithValue
	//
	//	: FormField	-- 
	//	: Value		-- If Undefined, pull from FormField
	//	: US		-- true or false
	//
	HG_FormatCurrencyWithValue = function(FormField, Value, US) {

		if (Value == undefined) {
			GetID(FormField).value 		= HG_CurrencyNumberFormat(GetID(FormField).value, '#vtThouDel#', '#vtDecDel#', US);
		} else {
			GetID(FormField).innerHTML 	= HG_CurrencyFormat(Value, '#vtThouDel#', '#vtDecDel#', US);
		}
		
	}
	
	
	
	//
	//	HG_ToString
	//
	//	: TheObject	-- 
	//
	HG_ToString = function(TheObject) {
		return JSON2.stringify(TheObject);
	}
	
	
	
	//
	//	HG_Escape
	//
	//	: TheObject	-- 
	//
	HG_Escape = function(TheString) {
		var str = JSON2.stringify(TheString);
		str = str.substring(1, str.length);
		str = str.substring(0, str.length-1);
		return str;
	}
	
	
	
	
	//
	//	HG_ToObject
	//
	//	: TheString	-- 
	//
	HG_ToObject = function(TheString, NoError) {
		
		if (TheString == '') {
			return {}	
		}
		
		if (typeof TheString == 'object') {
			return TheString;	
		}

		if (TheString.substring(0, 2) == '//') {
			TheString = TheString.substring(2, TheString.length);
		}

		if (TheString.substring(0, 1) != '(') {
			TheString = '(' + Trim(TheString) + ')';
	   	}
		//alert(TheString);
		try {
			return eval(TheString);
		} catch(e) {
			if (NoError == undefined) {
				Dump(e, 'Developer: HG_ToObject ' + TheString); // :: String->' + unescape(TheString));
			} else {
				return TheString;	
			}
		}
	}
	
	
	
	//
	//	HG_CopyObject
	//
	//	: TheObject	-- 
	//
	HG_CopyObject = function(TheObject) {
		
		return HG_ToObject(HG_ToString(TheObject))

	}
	
	
	
	//
	// Search Key was Press
	//
	HG_EnterKey = function(Event, FunctionCall, KeyNum) {

		var keynum = (Event.which) ? Event.which : Event.keyCode;
		
		if (KeyNum == undefined) {
			KeyNum = 13;
		}
		if (keynum == KeyNum) {		// enter
			FunctionCall();
		}
	
	}
	
	


	//
	// HG_DefaultFormatter
	//	
	HG_DefaultFormatter = function(Value) {
		return Value
	}
	
	//
	// HG_DefaultCleaner
	//	
	HG_DefaultCleaner = function(Value) {
		return Value
	}
	
	
	//
	// HG_DefaultValidator
	//	
	HG_DefaultValidator = function(Value) {
		return true
	}
		
		
	
	

	/***
	//
	//   Name: HG_MergeObjects - Recursively merge properties of two objects 
	//	
	//	Parameters:
	//		
	//		
	*/
	function HG_MergeObjects(obj1, obj2) {
		
	  for (var p in obj2) {
		try {
		  // Property in destination object set; update its value.
		  if ( obj2[p].constructor==Object ) {
			obj1[p] = HG_MergeObjects(obj1[p], obj2[p]);
	
		  } else {
			obj1[p] = obj2[p];
	
		  }
	
		} catch(e) {
		  // Property in destination object not set; create it and set its value.
		  obj1[p] = obj2[p];
	
		}
	  }
	
	  return obj1;
	}
	
	
	
	/***
	//
	//   Name: ArrayInsert
	//	
	//	Parameters:
	//		OriginalArray
	//		TheObject
	//		InsertAt
	*/
	function HG_ArrayInsert(OriginalArray, TheObject, InsertAt) {
		
		var Top 	= OriginalArray.slice(0, InsertAt);
		var Bottom  = OriginalArray.slice(InsertAt, OriginalArray.length);
		
		if (OriginalArray.length == 0 && TheObject.length == 0) {
			return OriginalArray;
		}
		
		if (TheObject.length > 1) {
			TheObject = TheObject.slice();
			for (var ind = 0; ind<TheObject.length;ind++) {
				Top.push(TheObject[ind]);	
			}
		} else {
			Top.push(TheObject[0]);
		}
		
		return Top.concat(Bottom);
	
	}
	
	/***
	//
	//   Name: HG_IsArray
	//	
	//	Parameters:
	//		OriginalArray
	//		TheObject
	//		InsertAt
	*/
	function HG_IsArray(AnArray) {
	  return AnArray != null && typeof AnArray == "object" &&
		  'splice' in AnArray && 'join' in AnArray;
	}
	
	
	
	
	/***
	//
	//   Name: HG_CreateObject
	//	
	//	Parameters:
	//		ObjectPath - 
	//		ex. HGO_Test.Guest.First.SSN
	//	    	Make sure that each node exist and the last node set = ''
	//		
	*/
	HG_CreateObject = function(ObjectPath, Value) {
				
		//
		//	Note this function MAY destory value in between up to the last node
		//
		
		try {
			var test = GetID(ObjectPath);
			if (typeof test != "undefined") { return true }
		} catch(e) {};
		
		
		ObjectPath 	 = ReplaceStr(ObjectPath, '[', '.');
		ObjectPath 	 = ReplaceStr(ObjectPath, ']', '.');
		ObjectPath 	 = ReplaceStr(ObjectPath, '..', '.');
		
		
		
		var Root 	 = GetToken(ObjectPath, 1, '.');
		var Path 	 = GetToken(ObjectPath, 1, '.');
		var Dots 	 = ListLen(ObjectPath, '.');
		var LastNode = GetToken(ObjectPath, Dots, '.');
		var Node 	 = '';
		var Pos  	 = '';
		var PrevNode = '';
		var PrevPath = Path;
		//var Limb 	 = ObjectPath.substring(0, ObjectPath.length - LastNode.length - 1);
		
		
		if (Value != undefined) {
			Dots--;
		}
		
		
		if (typeof window[Path] == "undefined") {
			window[Path] = new Object();
		};
			
		
		for (var t=2;t<=Dots;t++) {
			PrevNode = Node;
			Node 	 = GetToken(ObjectPath, t, '.');

			try {
				HG_NewObj  = eval(Path);
				HG_PrevObj = eval(PrevPath);
			} catch(e) {
				Dump(e, 'Developer: Invalid Object Path (HG_CreateObject) ' + Path);
				return false;
			}
			
		
		  	if (typeof HG_NewObj[Node] == "undefined") {
				if (!isNaN(Number(Node))) {
					
					HG_PrevObj[PrevNode]	= new Array();
					HG_NewObj  				= eval(Path);
					HG_NewObj[Node]			= new Object();
					PrevPath 				= Path;
					Path 	  			   += '[' + Node + ']';
				} else { 
					HG_NewObj[Node]  = new Object();
					PrevPath = Path;
					Path 			+= '.' + Node;
				} 
			} else {
				if (isNaN(Number(Node))) {
					Path += '.' + Node;
				} else {
					Path += '[' + Node + ']';
				}
			}
		}

		try {
			HG_NewObj = eval(Path);
		} catch(e) {
			Dump(e, 'Developer: Invalid Object Path (HG_CreateObject) ' + Path);
			return false;
		}
			
		if (Value != undefined) {
			HG_NewObj 		= eval(Path);
			HG_NewObj[LastNode] = Value;
		}

		return true;
		
	}
	
	
	
	
	/***
	//
	//   Name: HG_SetObject
	//	
	//	Parameters:
	//		ObjectPath - 
	//		ex. HGO_Test.Guest.First.SSN
	//	    	Make sure that each node exist and the last node set = ''
	//		
	*/
	HG_SetObject = function(ObjectPath, Value) {

		if (typeof GetID(ObjectPath) == "undefined") {
			HG_CreateObject(ObjectPath);
		}
		
		
		
		var Path    = HG_ReverseString(ObjectPath);
		var Dot 	= Path.indexOf('.');
		var Brc 	= Path.indexOf('[');
									 
		if (Dot > -1 && (Dot < Brc || Brc == -1)) {
			Path = Path.substring(Dot + 1, Path.length);
		} else if (Brc > -1 && (Dot == -1 || Brc < Dot)) {
			Path = Path.substring(Brc + 1, Path.length);
		}

		Path = HG_ReverseString(Path);
		var LastNode = ReplaceStr(ReplaceStr(ReplaceStr(ReplaceStr(ObjectPath, Path, ''), '.', ''), '[', ''), ']', '');

		HG_NewObj = eval(Path);
		HG_NewObj[LastNode] = Value;

	}
	
	
	
	
	/***
	//
	//   Name: HG_GetToken - Get a Value at the Position Index of the Delimiter
	//	
	//	Parameters:
	//		Str
	//		Position		
	//		Delimiter
	*/	
	function HG_GetToken(Str, Position, Delimiter) {

		var	u 	= 0;
		var c   = 0;
		var s   = 0;
		var e   = 0;
		
		Str 		= String(Str);
		Delimiter 	= String(Delimiter);
		
		for (var t=0;t<Str.length;t++) {
			c++;
			u = Str.indexOf(Delimiter, u + 1);
			if (u == -1) {	// EOL
				e = Str.length - u;
				if (c < Position) {
					Str = '';
					break;
				}
			} else {
				e = u - s;
			}
		
			if (c == Position) {
				Str  = Str.substr(s, e);
				break;
			}
			s = u + 1;
		}
		
		
		return String(Str);
	}
	
	
	/* ----------------------------------------------------------------------------
	//
	//   Name: HG_TokenCount - Return the number count of values delimited by delimiter
	//	
	//	Parameters:
	//		Text
	//		Delimiter
	*/
	function HG_TokenCount(Text, Delimiter) {
		if (Text==undefined) {
			return -1;
		}
		var c = Text.split(Delimiter);
		return c.length;
	}
	
	
	
	
	/* ----------------------------------------------------------------------------
	// 	HasClassName
	//
	// 	Description : returns boolean indicating whether the object has the class name
	//    built with the understanding that there may be multiple classes
	//
	// 	Arguments:
	//    objElement              - element to manipulate
	//    strClass                - class name to add
	*/
	function HG_HasClassName(objElement, strClass)
	   {
	
	   // if there is a class
	   if ( objElement.className )
		  {
	
		  // the classes are just a space separated list, so first get the list
		  var arrList = objElement.className.split(' ');
	
		  // get uppercase class for comparison purposes
		  var strClassUpper = strClass.toUpperCase();
	
		  // find all instances and remove them
		  for ( var i = 0; i < arrList.length; i++ )
			 {
	
			 // if class found
			 if ( arrList[i].toUpperCase() == strClassUpper )
				{
	
				// we found it
				return true;
	
				}
	
			 }
	
		  }
	
	   // if we got here then the class name is not there
	   return false;
	
	   }
	
	
	/* ----------------------------------------------------------------------------
	// AddClassName
	//
	// Description : adds a class to the class attribute of a DOM element
	//    built with the understanding that there may be multiple classes
	//
	// Arguments:
	//    objElement              - element to manipulate
	//    strClass                - class name to add
	*/
	function HG_AddClassName(objElement, strClass, blnMayAlreadyExist)
	   {
	
	   // if there is a class
	   if ( objElement.className )
		  {
	
		  // the classes are just a space separated list, so first get the list
		  var arrList = objElement.className.split(' ');
	
		  // if the new class name may already exist in list
		  if ( blnMayAlreadyExist )
			 {
	
			 // get uppercase class for comparison purposes
			 var strClassUpper = strClass.toUpperCase();
	
			 // find all instances and remove them
			 for ( var i = 0; i < arrList.length; i++ )
				{
	
				// if class found
				if ( arrList[i].toUpperCase() == strClassUpper )
				   {
	
				   // remove array item
				   arrList.splice(i, 1);
	
				   // decrement loop counter as we have adjusted the array's contents
				   i--;
	
				   }
	
				}
	
			 }
	
		  // add the new class to end of list
		  arrList[arrList.length] = strClass;
	
		  // add the new class to beginning of list
		  //arrList.splice(0, 0, strClass);
		  
		  // assign modified class name attribute
		  objElement.className = arrList.join(' ');
	
		  }
	   // if there was no class
	   else
		  {
	
		  // assign modified class name attribute      
		  objElement.className = strClass;
	   
		  }
	
	   }
	
	
	/* ----------------------------------------------------------------------------
	// RemoveClassName
	//
	// Description : removes a class from the class attribute of a DOM element
	//    built with the understanding that there may be multiple classes
	//
	// Arguments:
	//    objElement              - element to manipulate
	//    strClass                - class name to remove
	*/
	function HG_RemoveClassName(objElement, strClass)
	   {
	
	   // if there is a class
	   if ( objElement.className )
		  {
	
		  // the classes are just a space separated list, so first get the list
		  var arrList = objElement.className.split(' ');
	
		  // get uppercase class for comparison purposes
		  var strClassUpper = strClass.toUpperCase();
	
		  // find all instances and remove them
		  for ( var i = 0; i < arrList.length; i++ )
			 {
	
			 // if class found
			 if ( arrList[i].toUpperCase() == strClassUpper )
				{
	
				// remove array item
				arrList.splice(i, 1);
	
				// decrement loop counter as we have adjusted the array's contents
				i--;
	
				}
	
			 }
	
		  // assign modified class name attribute
		  objElement.className = arrList.join(' ');
	
		  }
	   // if there was no class
	   // there is nothing to remove
	
	   }



	HG_AJAX_InError = false;

	/* ----------------------------------------------------------------------------
	//
	//   Name: HG_AJAX
	//	
	//	Parameters:
			Parameters.Container	= WindowName;
			Parameters.URL			= URL;
			Parameters.OnSuccess	= OnSuccess;
			Parameters.Message		= Message;
			Parameters.PostText		= PostText;
			Parameters.Fetch		= true | false -- Don't output just fetch
			Parameters.Left			= 0;
			Parameters.Top			= 0;
	//		
	//		
	*/
	HG_AJAX = function(Parameters) {

		
		if (Parameters==undefined) {
			alert('Developer: Your WindowName ID Object has not been Defined :: ' + window.location.hostname + window.location.pathname + window.location.search + ' :: ' + HTTP);
			return false;
		}
		
		
	
		if (Parameters.Message=='') {
			var myElement = '';
		} else {
			if (typeof Parameters.Message == 'undefined' || typeof(Parameters.Message) != 'string') {
				Parameters.Message = 'Loading...';
			}
			var myElement = document.createElement('div');
			
			if (typeof Parameters.Container == 'undefined' || Parameters.Container == '') {
				var ContProvided = false;
				Parameters.Container = myElement;
				var a = myElement;
				if (!Parameters.Fetch) {
					document.body.appendChild(myElement);
				}
				var conWidth  = GetWindowWidth();
				var conHeight = GetWindowHeight()
				var conTL     = 'top:0;left:0;';
			} else {
				var ContProvided = true;
				Parameters.Container = GetID(Parameters.Container);
				var a = Parameters.Container.insertBefore(myElement, Parameters.Container.firstChild); 
				var conWidth  = Parameters.Container.offsetWidth;
				var conHeight = Parameters.Container.offsetHeight;
				var conTL     = '';
			}

 			var tid = 'DIV' + CreateUUID(10);
			
			
			a.innerHTML = '<div id="' + tid + '" style="float:left"><div style="position:absolute; z-index:10000; float:left">' + Parameters.Message + '</div><div>' +
						  '<div id="' + tid + 'PW"  class="AJAXPleaseWait" style="position:absolute; background-color:#FFFFFF; z-index:9999; ' +
						  'width:' + conWidth + 'px; ' +
						  'height:' + conHeight + 'px; '+
						  '" onclick="return false";>&nbsp;</div>';
						  
			if (!ContProvided && GetID(tid) != undefined) {
				if (Parameters.Top == undefined) {
					Parameters.Top = parseInt((GetWindowHeight() / 2)) - parseInt((GetID(tid).offsetHeight / 2));
				}
				if (Parameters.Left == undefined) {
					Parameters.Left = parseInt((GetWindowWidth() / 2)) - parseInt((GetID(tid).offsetWidth / 2));
				}

				myElement.style.position 		= 'absolute';
				myElement.style.zIndex 			= 10000;
				myElement.style.top  			= Parameters.Top;
				myElement.style.left 			= Parameters.Left;
				GetID(tid + 'PW').style.left 	= Parameters.Left *-1;
				GetID(tid + 'PW').style.top 	= Parameters.Top *-1;
				GetID(tid).style.float = 'none';
			}
			
			
		}
		
		
		Parameters.OnFailure = function (request, dump) {
			return
			
			if (HG_AJAX_InError == true) {
				return
			}
			
			HG_AJAX_InError = true;

			// If CF Debug Show That Portion Only
			if (request.responseText.indexOf('Debugging Information') > -1) {
				request.responseText = request.responseText.substring(request.responseText.indexOf('Debugging Information'), 700000);
			}
			
			//
			//	Open Window
			//
			window['HGAJAX_Popup'] = dhtmlwindow.open(   "HGAJAX_Popup"
													, "inline"
													, request.responseText
													, 'Request Error :: ' + GetToken(Parameters.URL, 1, '?')
													, "width=" + (GetWindowWidth() - 100) +"px,height=" + (GetWindowHeight() - 100) +"px,resize=1,scrolling=1,center=1"
													, "recal"
													);	
	
			//
			//	Close Window
			//
			GetID("HGAJAX_Popup").onclose = function() {
				HG_AJAX_InError = false;
				return true;
			}
			
			//alert('Background Load Error: ID > ' + Parameters.Container.id + '\n' + URL + ' \n[ ' + request.status +' ]');
			if (!Parameters.Fetch && dump == undefined) {
				document.body.removeChild(myElement);
			}
		}

		
		Parameters.DoOnSuccess = function(request) {
			
			if (request.status != 200) {
				Parameters.OnFailure(request);
				myElement.innerHTML = HG_AJaxError;
			}
			
			if (request.responseText.indexOf('table.cfdump_wddx') > -1 || request.responseText.indexOf('Debugging Information') > -1) {
				Parameters.OnFailure(request, true);
			}
			
			if (Parameters.OnSuccess != undefined) {
				if (Parameters.Fetch) {
					Parameters.OnSuccess(myElement.innerHTML);
				} else {
					Parameters.OnSuccess();
					document.body.removeChild(myElement);
				}
			}
			
		}
		
		Parameters.DoDefaultOnSuccess = function(request) {
			
			if (request.responseText.indexOf('table.cfdump_wddx') > -1 || request.responseText.indexOf('Debugging Information') > -1) {
				Parameters.OnFailure(request, true);
			}
			
		}
		
		
		var me = 'get';
		var ct = undefined;
		
		if (Parameters.PostText != undefined || typeof HG_GlobalObj == 'object') {
			me = 'post';
			ct = 'application/x-www-form-urlencoded';
			if (Parameters.PostText == undefined) {
				Parameters.PostText = '';
			}
		}
		
		 if (typeof HG_GlobalObj == 'object') {
			 Parameters.PostText = 'GlobalAJax=' + HG_ToString(HG_GlobalObj) + '&' + Parameters.PostText;
		 }
		 
		
		//
		//  Forces NO Caching
		//
		if (Parameters.URL.indexOf('?') > -1) {
			Parameters.URL += '&zzzdatetime=' + String(new Date());
		 } else {
			Parameters.URL += '?zzzdatetime=' + String(new Date());
		 }
		 
		 if (Parameters.Fetch) {
			 Parameters.URL += '&_NDB=1';
		 }
		 
		
		 

		if (Parameters.OnSuccess != undefined) {
			new Ajax.Updater(Parameters.Container, 
							 Parameters.URL, 
							 {asynchronous	: true, 
							  evalScripts	: true, 
						   	  method		: me, 
							  onFailure		: Parameters.OnFailure, 
							  onComplete	: Parameters.DoOnSuccess, 
							  parameters	: Parameters.PostText, 
							  contentType	: ct
							 });
		} else {
			new Ajax.Updater(Parameters.Container, 
							 Parameters.URL, 
							 {asynchronous	: true, 
							  evalScripts	: true, 
						   	  method		: me, 
							  onFailure		: Parameters.OnFailure, 
							  onComplete	: Parameters.DoDefaultOnSuccess,
							  parameters	: Parameters.PostText, 
							  contentType	: ct
							 });
		}
		
	}
	
	
	HG_ReverseString = function(Str) {
		var splitext = Str.split("");
		splitext = splitext.reverse();
		splitext = splitext.join("");
		return splitext;
	}
	
	
	HG_VariableLIST = '';
	
	HG_VariableList = function(HGTID, Exact) {
		
		HG_VariableLIST = ''
		var Obj = window;
		if (typeof Exact == 'undefined' || Exact == undefined) {
			Exact = false;	
		} else {
			return HGTID;
		}
		
		for (var ThisObj in Obj) {
			var TO = String(ThisObj);
			if (Exact == false) {
				if (TO.indexOf(HGTID) > -1) {
					HG_VariableLIST += TO + ',';
				}
			} else {
				if (TO == HGTID) {
					HG_VariableLIST += TO + ',';
					break;
				}
			}
		}
		
		return HG_VariableLIST.substring(HG_VariableLIST, HG_VariableLIST.length-1);
	
	}
	
	
	/* ----------------------------------------------------------------------------
	//	Remove an HG Tag and all related varibles
	//
	*/
	HG_Delete = function(HGTID, Exact) {
		
		if (isIE) {
			__DELETEval = window[HGTID];
			delete __DELETEval;
			return
		}
		

		var List = HG_VariableList(HGTID, Exact);
		var DeleteCount = ListLen(List, ',');

		for (var Item =1; Item <= DeleteCount; Item++) {
			ResizeRemoveFunction(GetToken(List, Item, ','));
			if (!isIE) {
				window[GetToken(List, Item, ',')] = new Object();
				delete window[GetToken(List, Item, ',')];
			} else {
				__DELETEval = window[GetToken(List, Item, ',')];
				delete __DELETEval;
			}
							
			
		}
	}
	
	
	
	/* ----------------------------------------------------------------------------
	//
	//   Name:HG_ToArray
	//	
	//	Parameters:
			
	//		
	//		
	*/
	HG_ToArray = function(Obj) {
	
		if (Obj == undefined) {
			return new Array();
		}
		
		if (HG_IsArray(Obj) == false) {
			Obj = Obj.split(',');
		}
		
		return Obj;
	}
	
	
	/* ----------------------------------------------------------------------------
	//
	//   Name:HG_ArrayConcat
	//	
	//	Parameters:
			
	//		
	//		
	*/
	HG_ArrayConcat = function(Arr1, Arr2) {
	
		if (Arr1 == undefined) {
			return new Array();
		}

		if (Arr1.length == 0 && Arr2.length > 0) {
			return Arr2;
		}


		if (Arr2 == undefined || Arr2.length == 0) {
			return Arr1;
		}

		
		return Arr1.concat(Arr2);
	}
	
	
	
	
	/* ----------------------------------------------------------------------------
	//
	//   Name:HG_GetStyle
	//	
	//	Parameters:
			
	//		
	//		
	*/
	HG_GetStyle = function(el,styleProp,Default)
	{
		var x = GetID(el);
		if (x.currentStyle)
			var y = x.currentStyle[styleProp];
		else
			var y = window.getComputedStyle(x,null).getPropertyValue(styleProp);
			
		if ((y=='' || y == undefined) && Default != undefined) {
			y =Default;
		}
		return parseInt(y);
	}
	
	
		/***
	//
	//   Name: HG_GetCSS
	//	
	//
	//		
	//		
	*/
	HG_GetCSS = function(theClass, element) {

		var cssRules;
		
		var added = false;
		for (var S = 0; S < document.styleSheets.length; S++){
			
			if (document.styleSheets[S]['rules']) {
				cssRules = 'rules';
			} else if (document.styleSheets[S]['cssRules']) {
				cssRules = 'cssRules';
			} else {
				//no rules found... browser unknown
			}
			
			for (var R = 0; R < document.styleSheets[S][cssRules].length; R++) {
				if (document.styleSheets[S][cssRules][R].selectorText != undefined && document.styleSheets[S][cssRules][R].selectorText.toLowerCase() == theClass.toLowerCase()) {
					if(document.styleSheets[S][cssRules][R].style[element]){
						return document.styleSheets[S][cssRules][R].style[element];
					}
				}
			}
			
		}
		
		return '';
	}
	
	
	
	
	/***
	//
	//   Name: HG_ChangeCSS
	//	
	//
	//		
	//		
	*/
	HG_ChangeCSS = function(theClass, element, value) {

		var cssRules;
		
		var added = false;
		for (var S = 0; S < document.styleSheets.length; S++){
			
			if (document.styleSheets[S]['rules']) {
				cssRules = 'rules';
			} else if (document.styleSheets[S]['cssRules']) {
				cssRules = 'cssRules';
			} else {
				//no rules found... browser unknown
			}
			
			for (var R = 0; R < document.styleSheets[S][cssRules].length; R++) {
				if (document.styleSheets[S][cssRules][R].selectorText != undefined && document.styleSheets[S][cssRules][R].selectorText.toLowerCase() == theClass.toLowerCase()) {
					
					if (value == '!REMOVE') {
						document.styleSheets[S][cssRules][R].style[element] = '';
						added=true;
						break;
					}

					if(document.styleSheets[S][cssRules][R].style[element]){
						document.styleSheets[S][cssRules][R].style[element] = value;
						added=true;
						break;
					}
				}
			}
			
			if(!added){
				if(document.styleSheets[S].insertRule){
				  document.styleSheets[S].insertRule(theClass+' { '+element+': '+value+'; }',document.styleSheets[S][cssRules].length);
				} else if (document.styleSheets[S].addRule) {
					document.styleSheets[S].addRule(theClass,element+': '+value+';');
				}
			}
		}
	}

/*  Prototype JavaScript framework, version 1.6.0.2
 *  (c) 2005-2008 Sam Stephenson
 *
 *  Prototype is freely distributable under the terms of an MIT-style license.
 *  For details, see the Prototype web site: http://www.prototypejs.org/
 *
 *--------------------------------------------------------------------------*/


//CompleteJavaScript('/javascript/prototype.js');

var Prototype = {
  Version: '1.6.0.2',

  Browser: {
    IE:     !!(window.attachEvent && !window.opera),
    Opera:  !!window.opera,
    WebKit: navigator.userAgent.indexOf('AppleWebKit/') > -1,
    Gecko:  navigator.userAgent.indexOf('Gecko') > -1 && navigator.userAgent.indexOf('KHTML') == -1,
    MobileSafari: !!navigator.userAgent.match(/Apple.*Mobile.*Safari/)
  },

  BrowserFeatures: {
    XPath: !!document.evaluate,
    ElementExtensions: !!window.HTMLElement,
    SpecificElementExtensions:
      document.createElement('div').__proto__ &&
      document.createElement('div').__proto__ !==
        document.createElement('form').__proto__
  },

  ScriptFragment: '<script[^>]*>([\\S\\s]*?)<\/script>',
  JSONFilter: /^\/\*-secure-([\s\S]*)\*\/\s*$/,

  emptyFunction: function() { },
  K: function(x) { return x }
};

if (Prototype.Browser.MobileSafari)
  Prototype.BrowserFeatures.SpecificElementExtensions = false;


/* Based on Alex Arnell's inheritance implementation. */
var Class = {
  create: function() {
    var parent = null, properties = $A(arguments);
    if (Object.isFunction(properties[0]))
      parent = properties.shift();

    function klass() {
      this.initialize.apply(this, arguments);
    }

    Object.extend(klass, Class.Methods);
    klass.superclass = parent;
    klass.subclasses = [];

    if (parent) {
      var subclass = function() { };
      subclass.prototype = parent.prototype;
      klass.prototype = new subclass;
      parent.subclasses.push(klass);
    }

    for (var i = 0; i < properties.length; i++)
      klass.addMethods(properties[i]);

    if (!klass.prototype.initialize)
      klass.prototype.initialize = Prototype.emptyFunction;

    klass.prototype.constructor = klass;

    return klass;
  }
};

Class.Methods = {
  addMethods: function(source) {
    var ancestor   = this.superclass && this.superclass.prototype;
    var properties = Object.keys(source);

    if (!Object.keys({ toString: true }).length)
      properties.push("toString", "valueOf");

    for (var i = 0, length = properties.length; i < length; i++) {
      var property = properties[i], value = source[property];
      if (ancestor && Object.isFunction(value) &&
          value.argumentNames().first() == "$super") {
        var method = value, value = Object.extend((function(m) {
          return function() { return ancestor[m].apply(this, arguments) };
        })(property).wrap(method), {
          valueOf:  function() { return method },
          toString: function() { return method.toString() }
        });
      }
      this.prototype[property] = value;
    }

    return this;
  }
};

var Abstract = { };

Object.extend = function(destination, source) {
  for (var property in source)
    destination[property] = source[property];
  return destination;
};

Object.extend(Object, {
  inspect: function(object) {
    try {
      if (Object.isUndefined(object)) return 'undefined';
      if (object === null) return 'null';
      return object.inspect ? object.inspect() : String(object);
    } catch (e) {
      if (e instanceof RangeError) return '...';
      throw e;
    }
  },

  toJSON: function(object) {
    var type = typeof object;
    switch (type) {
      case 'undefined':
      case 'function':
      case 'unknown': return;
      case 'boolean': return object.toString();
    }

    if (object === null) return 'null';
    if (object.toJSON) return object.toJSON();
    if (Object.isElement(object)) return;

    var results = [];
    for (var property in object) {
      var value = Object.toJSON(object[property]);
      if (!Object.isUndefined(value))
        results.push(property.toJSON() + ': ' + value);
    }

    return '{' + results.join(', ') + '}';
  },

  toQueryString: function(object) {
    return $H(object).toQueryString();
  },

  toHTML: function(object) {
    return object && object.toHTML ? object.toHTML() : String.interpret(object);
  },

  keys: function(object) {
    var keys = [];
    for (var property in object)
      keys.push(property);
    return keys;
  },

  values: function(object) {
    var values = [];
    for (var property in object)
      values.push(object[property]);
    return values;
  },

  clone: function(object) {
    return Object.extend({ }, object);
  },

  isElement: function(object) {
    return object && object.nodeType == 1;
  },

  isArray: function(object) {
    return object != null && typeof object == "object" &&
      'splice' in object && 'join' in object;
  },

  isHash: function(object) {
    return object instanceof Hash;
  },

  isFunction: function(object) {
    return typeof object == "function";
  },

  isString: function(object) {
    return typeof object == "string";
  },

  isNumber: function(object) {
    return typeof object == "number";
  },

  isUndefined: function(object) {
    return typeof object == "undefined";
  }
});

Object.extend(Function.prototype, {
  argumentNames: function() {
    var names = this.toString().match(/^[\s\(]*function[^(]*\((.*?)\)/)[1].split(",").invoke("strip");
    return names.length == 1 && !names[0] ? [] : names;
  },

  bind: function() {
    if (arguments.length < 2 && Object.isUndefined(arguments[0])) return this;
    var __method = this, args = $A(arguments), object = args.shift();
    return function() {
      return __method.apply(object, args.concat($A(arguments)));
    }
  },

  bindAsEventListener: function() {
    var __method = this, args = $A(arguments), object = args.shift();
    return function(event) {
      return __method.apply(object, [event || window.event].concat(args));
    }
  },

  curry: function() {
    if (!arguments.length) return this;
    var __method = this, args = $A(arguments);
    return function() {
      return __method.apply(this, args.concat($A(arguments)));
    }
  },

  delay: function() {
    var __method = this, args = $A(arguments), timeout = args.shift() * 1000;
    return window.setTimeout(function() {
      return __method.apply(__method, args);
    }, timeout);
  },

  wrap: function(wrapper) {
    var __method = this;
    return function() {
      return wrapper.apply(this, [__method.bind(this)].concat($A(arguments)));
    }
  },

  methodize: function() {
    if (this._methodized) return this._methodized;
    var __method = this;
    return this._methodized = function() {
      return __method.apply(null, [this].concat($A(arguments)));
    };
  }
});

Function.prototype.defer = Function.prototype.delay.curry(0.01);

Date.prototype.toJSON = function() {
  return '"' + this.getUTCFullYear() + '-' +
    (this.getUTCMonth() + 1).toPaddedString(2) + '-' +
    this.getUTCDate().toPaddedString(2) + 'T' +
    this.getUTCHours().toPaddedString(2) + ':' +
    this.getUTCMinutes().toPaddedString(2) + ':' +
    this.getUTCSeconds().toPaddedString(2) + 'Z"';
};

var Try = {
  these: function() {
    var returnValue;

    for (var i = 0, length = arguments.length; i < length; i++) {
      var lambda = arguments[i];
      try {
        returnValue = lambda();
        break;
      } catch (e) { }
    }

    return returnValue;
  }
};

RegExp.prototype.match = RegExp.prototype.test;

RegExp.escape = function(str) {
  return String(str).replace(/([.*+?^=!:${}()|[\]\/\\])/g, '\\$1');
};

/*--------------------------------------------------------------------------*/

var PeriodicalExecuter = Class.create({
  initialize: function(callback, frequency) {
    this.callback = callback;
    this.frequency = frequency;
    this.currentlyExecuting = false;

    this.registerCallback();
  },

  registerCallback: function() {
    this.timer = setInterval(this.onTimerEvent.bind(this), this.frequency * 1000);
  },

  execute: function() {
    this.callback(this);
  },

  stop: function() {
    if (!this.timer) return;
    clearInterval(this.timer);
    this.timer = null;
  },

  onTimerEvent: function() {
    if (!this.currentlyExecuting) {
      try {
        this.currentlyExecuting = true;
        this.execute();
      } finally {
        this.currentlyExecuting = false;
      }
    }
  }
});
Object.extend(String, {
  interpret: function(value) {
    return value == null ? '' : String(value);
  },
  specialChar: {
    '\b': '\\b',
    '\t': '\\t',
    '\n': '\\n',
    '\f': '\\f',
    '\r': '\\r',
    '\\': '\\\\'
  }
});

Object.extend(String.prototype, {
  gsub: function(pattern, replacement) {
    var result = '', source = this, match;
    replacement = arguments.callee.prepareReplacement(replacement);

    while (source.length > 0) {
      if (match = source.match(pattern)) {
        result += source.slice(0, match.index);
        result += String.interpret(replacement(match));
        source  = source.slice(match.index + match[0].length);
      } else {
        result += source, source = '';
      }
    }
    return result;
  },

  sub: function(pattern, replacement, count) {
    replacement = this.gsub.prepareReplacement(replacement);
    count = Object.isUndefined(count) ? 1 : count;

    return this.gsub(pattern, function(match) {
      if (--count < 0) return match[0];
      return replacement(match);
    });
  },

  scan: function(pattern, iterator) {
    this.gsub(pattern, iterator);
    return String(this);
  },

  truncate: function(length, truncation) {
    length = length || 30;
    truncation = Object.isUndefined(truncation) ? '...' : truncation;
    return this.length > length ?
      this.slice(0, length - truncation.length) + truncation : String(this);
  },

  strip: function() {
    return this.replace(/^\s+/, '').replace(/\s+$/, '');
  },

  stripTags: function() {
    return this.replace(/<\/?[^>]+>/gi, '');
  },

  stripScripts: function() {
    return this.replace(new RegExp(Prototype.ScriptFragment, 'img'), '');
  },

  extractScripts: function() {
    var matchAll = new RegExp(Prototype.ScriptFragment, 'img');
    var matchOne = new RegExp(Prototype.ScriptFragment, 'im');
    return (this.match(matchAll) || []).map(function(scriptTag) {
      return (scriptTag.match(matchOne) || ['', ''])[1];
    });
  },

  evalScripts: function() {
    return this.extractScripts().map(function(script) { return eval(script) });
  },

  escapeHTML: function() {
    var self = arguments.callee;
    self.text.data = this;
    return self.div.innerHTML;
  },

  unescapeHTML: function() {
    var div = new Element('div');
    div.innerHTML = this.stripTags();
    return div.childNodes[0] ? (div.childNodes.length > 1 ?
      $A(div.childNodes).inject('', function(memo, node) { return memo+node.nodeValue }) :
      div.childNodes[0].nodeValue) : '';
  },

  toQueryParams: function(separator) {
    var match = this.strip().match(/([^?#]*)(#.*)?$/);
    if (!match) return { };

    return match[1].split(separator || '&').inject({ }, function(hash, pair) {
      if ((pair = pair.split('='))[0]) {
        var key = decodeURIComponent(pair.shift());
        var value = pair.length > 1 ? pair.join('=') : pair[0];
        if (value != undefined) value = decodeURIComponent(value);

        if (key in hash) {
          if (!Object.isArray(hash[key])) hash[key] = [hash[key]];
          hash[key].push(value);
        }
        else hash[key] = value;
      }
      return hash;
    });
  },

  toArray: function() {
    return this.split('');
  },

  succ: function() {
    return this.slice(0, this.length - 1) +
      String.fromCharCode(this.charCodeAt(this.length - 1) + 1);
  },

  times: function(count) {
    return count < 1 ? '' : new Array(count + 1).join(this);
  },

  camelize: function() {
    var parts = this.split('-'), len = parts.length;
    if (len == 1) return parts[0];

    var camelized = this.charAt(0) == '-'
      ? parts[0].charAt(0).toUpperCase() + parts[0].substring(1)
      : parts[0];

    for (var i = 1; i < len; i++)
      camelized += parts[i].charAt(0).toUpperCase() + parts[i].substring(1);

    return camelized;
  },

  capitalize: function() {
    return this.charAt(0).toUpperCase() + this.substring(1).toLowerCase();
  },

  underscore: function() {
    return this.gsub(/::/, '/').gsub(/([A-Z]+)([A-Z][a-z])/,'#{1}_#{2}').gsub(/([a-z\d])([A-Z])/,'#{1}_#{2}').gsub(/-/,'_').toLowerCase();
  },

  dasherize: function() {
    return this.gsub(/_/,'-');
  },

  inspect: function(useDoubleQuotes) {
    var escapedString = this.gsub(/[\x00-\x1f\\]/, function(match) {
      var character = String.specialChar[match[0]];
      return character ? character : '\\u00' + match[0].charCodeAt().toPaddedString(2, 16);
    });
    if (useDoubleQuotes) return '"' + escapedString.replace(/"/g, '\\"') + '"';
    return "'" + escapedString.replace(/'/g, '\\\'') + "'";
  },

  toJSON: function() {
    return this.inspect(true);
  },

  unfilterJSON: function(filter) {
    return this.sub(filter || Prototype.JSONFilter, '#{1}');
  },

  isJSON: function() {
    var str = this;
    if (str.blank()) return false;
    str = this.replace(/\\./g, '@').replace(/"[^"\\\n\r]*"/g, '');
    return (/^[,:{}\[\]0-9.\-+Eaeflnr-u \n\r\t]*$/).test(str);
  },

  evalJSON: function(sanitize) {
    var json = this.unfilterJSON();
    try {
      if (!sanitize || json.isJSON()) return eval('(' + json + ')');
    } catch (e) { }
    throw new SyntaxError('Badly formed JSON string: ' + this.inspect());
  },

  include: function(pattern) {
    return this.indexOf(pattern) > -1;
  },

  startsWith: function(pattern) {
    return this.indexOf(pattern) === 0;
  },

  endsWith: function(pattern) {
    var d = this.length - pattern.length;
    return d >= 0 && this.lastIndexOf(pattern) === d;
  },

  empty: function() {
    return this == '';
  },

  blank: function() {
    return /^\s*$/.test(this);
  },

  interpolate: function(object, pattern) {
    return new Template(this, pattern).evaluate(object);
  }
});

if (Prototype.Browser.WebKit || Prototype.Browser.IE) Object.extend(String.prototype, {
  escapeHTML: function() {
    return this.replace(/&/g,'&amp;').replace(/</g,'&lt;').replace(/>/g,'&gt;');
  },
  unescapeHTML: function() {
    return this.replace(/&amp;/g,'&').replace(/&lt;/g,'<').replace(/&gt;/g,'>');
  }
});

String.prototype.gsub.prepareReplacement = function(replacement) {
  if (Object.isFunction(replacement)) return replacement;
  var template = new Template(replacement);
  return function(match) { return template.evaluate(match) };
};

String.prototype.parseQuery = String.prototype.toQueryParams;

Object.extend(String.prototype.escapeHTML, {
  div:  document.createElement('div'),
  text: document.createTextNode('')
});

with (String.prototype.escapeHTML) div.appendChild(text);

var Template = Class.create({
  initialize: function(template, pattern) {
    this.template = template.toString();
    this.pattern = pattern || Template.Pattern;
  },

  evaluate: function(object) {
    if (Object.isFunction(object.toTemplateReplacements))
      object = object.toTemplateReplacements();

    return this.template.gsub(this.pattern, function(match) {
      if (object == null) return '';

      var before = match[1] || '';
      if (before == '\\') return match[2];

      var ctx = object, expr = match[3];
      var pattern = /^([^.[]+|\[((?:.*?[^\\])?)\])(\.|\[|$)/;
      match = pattern.exec(expr);
      if (match == null) return before;

      while (match != null) {
        var comp = match[1].startsWith('[') ? match[2].gsub('\\\\]', ']') : match[1];
        ctx = ctx[comp];
        if (null == ctx || '' == match[3]) break;
        expr = expr.substring('[' == match[3] ? match[1].length : match[0].length);
        match = pattern.exec(expr);
      }

      return before + String.interpret(ctx);
    });
  }
});
Template.Pattern = /(^|.|\r|\n)(#\{(.*?)\})/;

var $break = { };

var Enumerable = {
  each: function(iterator, context) {
    var index = 0;
    iterator = iterator.bind(context);
    try {
      this._each(function(value) {
        iterator(value, index++);
      });
    } catch (e) {
      if (e != $break) throw e;
    }
    return this;
  },

  eachSlice: function(number, iterator, context) {
    iterator = iterator ? iterator.bind(context) : Prototype.K;
    var index = -number, slices = [], array = this.toArray();
    while ((index += number) < array.length)
      slices.push(array.slice(index, index+number));
    return slices.collect(iterator, context);
  },

  all: function(iterator, context) {
    iterator = iterator ? iterator.bind(context) : Prototype.K;
    var result = true;
    this.each(function(value, index) {
      result = result && !!iterator(value, index);
      if (!result) throw $break;
    });
    return result;
  },

  any: function(iterator, context) {
    iterator = iterator ? iterator.bind(context) : Prototype.K;
    var result = false;
    this.each(function(value, index) {
      if (result = !!iterator(value, index))
        throw $break;
    });
    return result;
  },

  collect: function(iterator, context) {
    iterator = iterator ? iterator.bind(context) : Prototype.K;
    var results = [];
    this.each(function(value, index) {
      results.push(iterator(value, index));
    });
    return results;
  },

  detect: function(iterator, context) {
    iterator = iterator.bind(context);
    var result;
    this.each(function(value, index) {
      if (iterator(value, index)) {
        result = value;
        throw $break;
      }
    });
    return result;
  },

  findAll: function(iterator, context) {
    iterator = iterator.bind(context);
    var results = [];
    this.each(function(value, index) {
      if (iterator(value, index))
        results.push(value);
    });
    return results;
  },

  grep: function(filter, iterator, context) {
    iterator = iterator ? iterator.bind(context) : Prototype.K;
    var results = [];

    if (Object.isString(filter))
      filter = new RegExp(filter);

    this.each(function(value, index) {
      if (filter.match(value))
        results.push(iterator(value, index));
    });
    return results;
  },

  include: function(object) {
    if (Object.isFunction(this.indexOf))
      if (this.indexOf(object) != -1) return true;

    var found = false;
    this.each(function(value) {
      if (value == object) {
        found = true;
        throw $break;
      }
    });
    return found;
  },

  inGroupsOf: function(number, fillWith) {
    fillWith = Object.isUndefined(fillWith) ? null : fillWith;
    return this.eachSlice(number, function(slice) {
      while(slice.length < number) slice.push(fillWith);
      return slice;
    });
  },

  inject: function(memo, iterator, context) {
    iterator = iterator.bind(context);
    this.each(function(value, index) {
      memo = iterator(memo, value, index);
    });
    return memo;
  },

  invoke: function(method) {
    var args = $A(arguments).slice(1);
    return this.map(function(value) {
      return value[method].apply(value, args);
    });
  },

  max: function(iterator, context) {
    iterator = iterator ? iterator.bind(context) : Prototype.K;
    var result;
    this.each(function(value, index) {
      value = iterator(value, index);
      if (result == null || value >= result)
        result = value;
    });
    return result;
  },

  min: function(iterator, context) {
    iterator = iterator ? iterator.bind(context) : Prototype.K;
    var result;
    this.each(function(value, index) {
      value = iterator(value, index);
      if (result == null || value < result)
        result = value;
    });
    return result;
  },

  partition: function(iterator, context) {
    iterator = iterator ? iterator.bind(context) : Prototype.K;
    var trues = [], falses = [];
    this.each(function(value, index) {
      (iterator(value, index) ?
        trues : falses).push(value);
    });
    return [trues, falses];
  },

  pluck: function(property) {
    var results = [];
    this.each(function(value) {
      results.push(value[property]);
    });
    return results;
  },

  reject: function(iterator, context) {
    iterator = iterator.bind(context);
    var results = [];
    this.each(function(value, index) {
      if (!iterator(value, index))
        results.push(value);
    });
    return results;
  },

  sortBy: function(iterator, context) {
    iterator = iterator.bind(context);
    return this.map(function(value, index) {
      return {value: value, criteria: iterator(value, index)};
    }).sort(function(left, right) {
      var a = left.criteria, b = right.criteria;
      return a < b ? -1 : a > b ? 1 : 0;
    }).pluck('value');
  },

  toArray: function() {
    return this.map();
  },

  zip: function() {
    var iterator = Prototype.K, args = $A(arguments);
    if (Object.isFunction(args.last()))
      iterator = args.pop();

    var collections = [this].concat(args).map($A);
    return this.map(function(value, index) {
      return iterator(collections.pluck(index));
    });
  },

  size: function() {
    return this.toArray().length;
  },

  inspect: function() {
    return '#<Enumerable:' + this.toArray().inspect() + '>';
  }
};

Object.extend(Enumerable, {
  map:     Enumerable.collect,
  find:    Enumerable.detect,
  select:  Enumerable.findAll,
  filter:  Enumerable.findAll,
  member:  Enumerable.include,
  entries: Enumerable.toArray,
  every:   Enumerable.all,
  some:    Enumerable.any
});
function $A(iterable) {
  if (!iterable) return [];
  if (iterable.toArray) return iterable.toArray();
  var length = iterable.length || 0, results = new Array(length);
  while (length--) results[length] = iterable[length];
  return results;
}

if (Prototype.Browser.WebKit) {
  $A = function(iterable) {
    if (!iterable) return [];
    if (!(Object.isFunction(iterable) && iterable == '[object NodeList]') &&
        iterable.toArray) return iterable.toArray();
    var length = iterable.length || 0, results = new Array(length);
    while (length--) results[length] = iterable[length];
    return results;
  };
}

Array.from = $A;

Object.extend(Array.prototype, Enumerable);

if (!Array.prototype._reverse) Array.prototype._reverse = Array.prototype.reverse;

Object.extend(Array.prototype, {
  _each: function(iterator) {
    for (var i = 0, length = this.length; i < length; i++)
      iterator(this[i]);
  },

  clear: function() {
    this.length = 0;
    return this;
  },

  first: function() {
    return this[0];
  },

  last: function() {
    return this[this.length - 1];
  },

  compact: function() {
    return this.select(function(value) {
      return value != null;
    });
  },

  flatten: function() {
    return this.inject([], function(array, value) {
      return array.concat(Object.isArray(value) ?
        value.flatten() : [value]);
    });
  },

  without: function() {
    var values = $A(arguments);
    return this.select(function(value) {
      return !values.include(value);
    });
  },

  reverse: function(inline) {
    return (inline !== false ? this : this.toArray())._reverse();
  },

  reduce: function() {
    return this.length > 1 ? this : this[0];
  },

  uniq: function(sorted) {
    return this.inject([], function(array, value, index) {
      if (0 == index || (sorted ? array.last() != value : !array.include(value)))
        array.push(value);
      return array;
    });
  },

  intersect: function(array) {
    return this.uniq().findAll(function(item) {
      return array.detect(function(value) { return item === value });
    });
  },

  clone: function() {
    return [].concat(this);
  },

  size: function() {
    return this.length;
  },

  inspect: function() {
    return '[' + this.map(Object.inspect).join(', ') + ']';
  },

  toJSON: function() {
    var results = [];
    this.each(function(object) {
      var value = Object.toJSON(object);
      if (!Object.isUndefined(value)) results.push(value);
    });
    return '[' + results.join(', ') + ']';
  }
});

// use native browser JS 1.6 implementation if available
if (Object.isFunction(Array.prototype.forEach))
  Array.prototype._each = Array.prototype.forEach;

if (!Array.prototype.indexOf) Array.prototype.indexOf = function(item, i) {
  i || (i = 0);
  var length = this.length;
  if (i < 0) i = length + i;
  for (; i < length; i++)
    if (this[i] === item) return i;
  return -1;
};

if (!Array.prototype.lastIndexOf) Array.prototype.lastIndexOf = function(item, i) {
  i = isNaN(i) ? this.length : (i < 0 ? this.length + i : i) + 1;
  var n = this.slice(0, i).reverse().indexOf(item);
  return (n < 0) ? n : i - n - 1;
};

Array.prototype.toArray = Array.prototype.clone;

function $w(string) {
  if (!Object.isString(string)) return [];
  string = string.strip();
  return string ? string.split(/\s+/) : [];
}

if (Prototype.Browser.Opera){
  Array.prototype.concat = function() {
    var array = [];
    for (var i = 0, length = this.length; i < length; i++) array.push(this[i]);
    for (var i = 0, length = arguments.length; i < length; i++) {
      if (Object.isArray(arguments[i])) {
        for (var j = 0, arrayLength = arguments[i].length; j < arrayLength; j++)
          array.push(arguments[i][j]);
      } else {
        array.push(arguments[i]);
      }
    }
    return array;
  };
}
Object.extend(Number.prototype, {
  toColorPart: function() {
    return this.toPaddedString(2, 16);
  },

  succ: function() {
    return this + 1;
  },

  times: function(iterator) {
    $R(0, this, true).each(iterator);
    return this;
  },

  toPaddedString: function(length, radix) {
    var string = this.toString(radix || 10);
    return '0'.times(length - string.length) + string;
  },

  toJSON: function() {
    return isFinite(this) ? this.toString() : 'null';
  }
});

$w('abs round ceil floor').each(function(method){
  Number.prototype[method] = Math[method].methodize();
});
function $H(object) {
  return new Hash(object);
};

var Hash = Class.create(Enumerable, (function() {

  function toQueryPair(key, value) {
    if (Object.isUndefined(value)) return key;
    return key + '=' + encodeURIComponent(String.interpret(value));
  }

  return {
    initialize: function(object) {
      this._object = Object.isHash(object) ? object.toObject() : Object.clone(object);
    },

    _each: function(iterator) {
      for (var key in this._object) {
        var value = this._object[key], pair = [key, value];
        pair.key = key;
        pair.value = value;
        iterator(pair);
      }
    },

    set: function(key, value) {
      return this._object[key] = value;
    },

    get: function(key) {
      return this._object[key];
    },

    unset: function(key) {
      var value = this._object[key];
      delete this._object[key];
      return value;
    },

    toObject: function() {
      return Object.clone(this._object);
    },

    keys: function() {
      return this.pluck('key');
    },

    values: function() {
      return this.pluck('value');
    },

    index: function(value) {
      var match = this.detect(function(pair) {
        return pair.value === value;
      });
      return match && match.key;
    },

    merge: function(object) {
      return this.clone().update(object);
    },

    update: function(object) {
      return new Hash(object).inject(this, function(result, pair) {
        result.set(pair.key, pair.value);
        return result;
      });
    },

    toQueryString: function() {
      return this.map(function(pair) {
        var key = encodeURIComponent(pair.key), values = pair.value;

        if (values && typeof values == 'object') {
          if (Object.isArray(values))
            return values.map(toQueryPair.curry(key)).join('&');
        }
        return toQueryPair(key, values);
      }).join('&');
    },

    inspect: function() {
      return '#<Hash:{' + this.map(function(pair) {
        return pair.map(Object.inspect).join(': ');
      }).join(', ') + '}>';
    },

    toJSON: function() {
      return Object.toJSON(this.toObject());
    },

    clone: function() {
      return new Hash(this);
    }
  }
})());

Hash.prototype.toTemplateReplacements = Hash.prototype.toObject;
Hash.from = $H;
var ObjectRange = Class.create(Enumerable, {
  initialize: function(start, end, exclusive) {
    this.start = start;
    this.end = end;
    this.exclusive = exclusive;
  },

  _each: function(iterator) {
    var value = this.start;
    while (this.include(value)) {
      iterator(value);
      value = value.succ();
    }
  },

  include: function(value) {
    if (value < this.start)
      return false;
    if (this.exclusive)
      return value < this.end;
    return value <= this.end;
  }
});

var $R = function(start, end, exclusive) {
  return new ObjectRange(start, end, exclusive);
};

var Ajax = {
  getTransport: function() {
    return Try.these(
      function() {return new XMLHttpRequest()},
      function() {return new ActiveXObject('Msxml2.XMLHTTP')},
      function() {return new ActiveXObject('Microsoft.XMLHTTP')}
    ) || false;
  },

  activeRequestCount: 0
};

Ajax.Responders = {
  responders: [],

  _each: function(iterator) {
    this.responders._each(iterator);
  },

  register: function(responder) {
    if (!this.include(responder))
      this.responders.push(responder);
  },

  unregister: function(responder) {
    this.responders = this.responders.without(responder);
  },

  dispatch: function(callback, request, transport, json) {
    this.each(function(responder) {
      if (Object.isFunction(responder[callback])) {
        try {
          responder[callback].apply(responder, [request, transport, json]);
        } catch (e) { }
      }
    });
  }
};

Object.extend(Ajax.Responders, Enumerable);

Ajax.Responders.register({
  onCreate:   function() { Ajax.activeRequestCount++ },
  onComplete: function() { Ajax.activeRequestCount-- }
});

Ajax.Base = Class.create({
  initialize: function(options) {
    this.options = {
      method:       'post',
      asynchronous: true,
      contentType:  'application/x-www-form-urlencoded',
      encoding:     'UTF-8',
      parameters:   '',
      evalJSON:     true,
      evalJS:       true
    };
    Object.extend(this.options, options || { });

    this.options.method = this.options.method.toLowerCase();

    if (Object.isString(this.options.parameters))
      this.options.parameters = this.options.parameters.toQueryParams();
    else if (Object.isHash(this.options.parameters))
      this.options.parameters = this.options.parameters.toObject();
  }
});

Ajax.Request = Class.create(Ajax.Base, {
  _complete: false,

  initialize: function($super, url, options) {
    $super(options);
    this.transport = Ajax.getTransport();
    this.request(url);
  },

  request: function(url) {
    this.url = url;
    this.method = this.options.method;
    var params = Object.clone(this.options.parameters);

    if (!['get', 'post'].include(this.method)) {
      // simulate other verbs over post
      params['_method'] = this.method;
      this.method = 'post';
    }

    this.parameters = params;

    if (params = Object.toQueryString(params)) {
      // when GET, append parameters to URL
      if (this.method == 'get')
        this.url += (this.url.include('?') ? '&' : '?') + params;
      else if (/Konqueror|Safari|KHTML/.test(navigator.userAgent))
        params += '&_=';
    }

    try {
      var response = new Ajax.Response(this);
      if (this.options.onCreate) this.options.onCreate(response);
      Ajax.Responders.dispatch('onCreate', this, response);

      this.transport.open(this.method.toUpperCase(), this.url,
        this.options.asynchronous);

      if (this.options.asynchronous) this.respondToReadyState.bind(this).defer(1);

      this.transport.onreadystatechange = this.onStateChange.bind(this);
      this.setRequestHeaders();

      this.body = this.method == 'post' ? (this.options.postBody || params) : null;
      this.transport.send(this.body);

      /* Force Firefox to handle ready state 4 for synchronous requests */
      if (!this.options.asynchronous && this.transport.overrideMimeType)
        this.onStateChange();

    }
    catch (e) {
      this.dispatchException(e);
    }
  },

  onStateChange: function() {
    var readyState = this.transport.readyState;
    if (readyState > 1 && !((readyState == 4) && this._complete))
      this.respondToReadyState(this.transport.readyState);
  },

  setRequestHeaders: function() {
    var headers = {
      'X-Requested-With': 'XMLHttpRequest',
      'X-Prototype-Version': Prototype.Version,
      'Accept': 'text/javascript, text/html, application/xml, text/xml, */*'
    };

    if (this.method == 'post') {
      headers['Content-type'] = this.options.contentType +
        (this.options.encoding ? '; charset=' + this.options.encoding : '');

      /* Force "Connection: close" for older Mozilla browsers to work
       * around a bug where XMLHttpRequest sends an incorrect
       * Content-length header. See Mozilla Bugzilla #246651.
       */
      if (this.transport.overrideMimeType &&
          (navigator.userAgent.match(/Gecko\/(\d{4})/) || [0,2005])[1] < 2005)
            headers['Connection'] = 'close';
    }

    // user-defined headers
    if (typeof this.options.requestHeaders == 'object') {
      var extras = this.options.requestHeaders;

      if (Object.isFunction(extras.push))
        for (var i = 0, length = extras.length; i < length; i += 2)
          headers[extras[i]] = extras[i+1];
      else
        $H(extras).each(function(pair) { headers[pair.key] = pair.value });
    }

    for (var name in headers)
      this.transport.setRequestHeader(name, headers[name]);
  },

  success: function() {
    var status = this.getStatus();
    return !status || (status >= 200 && status < 300);
  },

  getStatus: function() {
    try {
      return this.transport.status || 0;
    } catch (e) { return 0 }
  },

  respondToReadyState: function(readyState) {
    var state = Ajax.Request.Events[readyState], response = new Ajax.Response(this);

    if (state == 'Complete') {
      try {
        this._complete = true;
        (this.options['on' + response.status]
         || this.options['on' + (this.success() ? 'Success' : 'Failure')]
         || Prototype.emptyFunction)(response, response.headerJSON);
      } catch (e) {
        this.dispatchException(e);
      }

      var contentType = response.getHeader('Content-type');
      if (this.options.evalJS == 'force'
          || (this.options.evalJS && this.isSameOrigin() && contentType
          && contentType.match(/^\s*(text|application)\/(x-)?(java|ecma)script(;.*)?\s*$/i)))
        this.evalResponse();
    }

    try {
      (this.options['on' + state] || Prototype.emptyFunction)(response, response.headerJSON);
      Ajax.Responders.dispatch('on' + state, this, response, response.headerJSON);
    } catch (e) {
      this.dispatchException(e);
    }

    if (state == 'Complete') {
      // avoid memory leak in MSIE: clean up
      this.transport.onreadystatechange = Prototype.emptyFunction;
    }
  },

  isSameOrigin: function() {
    var m = this.url.match(/^\s*https?:\/\/[^\/]*/);
    return !m || (m[0] == '#{protocol}//#{domain}#{port}'.interpolate({
      protocol: location.protocol,
      domain: document.domain,
      port: location.port ? ':' + location.port : ''
    }));
  },

  getHeader: function(name) {
    try {
      return this.transport.getResponseHeader(name) || null;
    } catch (e) { return null }
  },

  evalResponse: function() {
    try {
      return eval((this.transport.responseText || '').unfilterJSON());
    } catch (e) {
      this.dispatchException(e);
    }
  },

  dispatchException: function(exception) {
    (this.options.onException || Prototype.emptyFunction)(this, exception);
    Ajax.Responders.dispatch('onException', this, exception);
  }
});

Ajax.Request.Events =
  ['Uninitialized', 'Loading', 'Loaded', 'Interactive', 'Complete'];

Ajax.Response = Class.create({
  initialize: function(request){
    this.request = request;
    var transport  = this.transport  = request.transport,
        readyState = this.readyState = transport.readyState;

    if((readyState > 2 && !Prototype.Browser.IE) || readyState == 4) {
      this.status       = this.getStatus();
      this.statusText   = this.getStatusText();
      this.responseText = String.interpret(transport.responseText);
      this.headerJSON   = this._getHeaderJSON();
    }

    if(readyState == 4) {
      var xml = transport.responseXML;
      this.responseXML  = Object.isUndefined(xml) ? null : xml;
      this.responseJSON = this._getResponseJSON();
    }
  },

  status:      0,
  statusText: '',

  getStatus: Ajax.Request.prototype.getStatus,

  getStatusText: function() {
    try {
      return this.transport.statusText || '';
    } catch (e) { return '' }
  },

  getHeader: Ajax.Request.prototype.getHeader,

  getAllHeaders: function() {
    try {
      return this.getAllResponseHeaders();
    } catch (e) { return null }
  },

  getResponseHeader: function(name) {
    return this.transport.getResponseHeader(name);
  },

  getAllResponseHeaders: function() {
    return this.transport.getAllResponseHeaders();
  },

  _getHeaderJSON: function() {
    var json = this.getHeader('X-JSON');
    if (!json) return null;
    json = decodeURIComponent(escape(json));
    try {
      return json.evalJSON(this.request.options.sanitizeJSON ||
        !this.request.isSameOrigin());
    } catch (e) {
      this.request.dispatchException(e);
    }
  },

  _getResponseJSON: function() {
    var options = this.request.options;
    if (!options.evalJSON || (options.evalJSON != 'force' &&
      !(this.getHeader('Content-type') || '').include('application/json')) ||
        this.responseText.blank())
          return null;
    try {
      return this.responseText.evalJSON(options.sanitizeJSON ||
        !this.request.isSameOrigin());
    } catch (e) {
      this.request.dispatchException(e);
    }
  }
});

Ajax.Updater = Class.create(Ajax.Request, {
  initialize: function($super, container, url, options) {
    this.container = {
      success: (container.success || container),
      failure: (container.failure || (container.success ? null : container))
    };

    options = Object.clone(options);
    var onComplete = options.onComplete;
    options.onComplete = (function(response, json) {
      this.updateContent(response.responseText);
      if (Object.isFunction(onComplete)) onComplete(response, json);
    }).bind(this);

    $super(url, options);
  },

  updateContent: function(responseText) {
    var receiver = this.container[this.success() ? 'success' : 'failure'],
        options = this.options;

    if (!options.evalScripts) responseText = responseText.stripScripts();

    if (receiver = $(receiver)) {
      if (options.insertion) {
        if (Object.isString(options.insertion)) {
          var insertion = { }; insertion[options.insertion] = responseText;
          receiver.insert(insertion);
        }
        else options.insertion(receiver, responseText);
      }
      else receiver.update(responseText);
    }
  }
});

Ajax.PeriodicalUpdater = Class.create(Ajax.Base, {
  initialize: function($super, container, url, options) {
    $super(options);
    this.onComplete = this.options.onComplete;

    this.frequency = (this.options.frequency || 2);
    this.decay = (this.options.decay || 1);

    this.updater = { };
    this.container = container;
    this.url = url;

    this.start();
  },

  start: function() {
    this.options.onComplete = this.updateComplete.bind(this);
    this.onTimerEvent();
  },

  stop: function() {
    this.updater.options.onComplete = undefined;
    clearTimeout(this.timer);
    (this.onComplete || Prototype.emptyFunction).apply(this, arguments);
  },

  updateComplete: function(response) {
    if (this.options.decay) {
      this.decay = (response.responseText == this.lastText ?
        this.decay * this.options.decay : 1);

      this.lastText = response.responseText;
    }
    this.timer = this.onTimerEvent.bind(this).delay(this.decay * this.frequency);
  },

  onTimerEvent: function() {
    this.updater = new Ajax.Updater(this.container, this.url, this.options);
  }
});
function $(element) {
  if (arguments.length > 1) {
    for (var i = 0, elements = [], length = arguments.length; i < length; i++)
      elements.push($(arguments[i]));
    return elements;
  }
  if (Object.isString(element))
    element = document.getElementById(element);
  return Element.extend(element);
}

if (Prototype.BrowserFeatures.XPath) {
  document._getElementsByXPath = function(expression, parentElement) {
    var results = [];
    var query = document.evaluate(expression, $(parentElement) || document,
      null, XPathResult.ORDERED_NODE_SNAPSHOT_TYPE, null);
    for (var i = 0, length = query.snapshotLength; i < length; i++)
      results.push(Element.extend(query.snapshotItem(i)));
    return results;
  };
}

/*--------------------------------------------------------------------------*/

if (!window.Node) var Node = { };

if (!Node.ELEMENT_NODE) {
  // DOM level 2 ECMAScript Language Binding
  Object.extend(Node, {
    ELEMENT_NODE: 1,
    ATTRIBUTE_NODE: 2,
    TEXT_NODE: 3,
    CDATA_SECTION_NODE: 4,
    ENTITY_REFERENCE_NODE: 5,
    ENTITY_NODE: 6,
    PROCESSING_INSTRUCTION_NODE: 7,
    COMMENT_NODE: 8,
    DOCUMENT_NODE: 9,
    DOCUMENT_TYPE_NODE: 10,
    DOCUMENT_FRAGMENT_NODE: 11,
    NOTATION_NODE: 12
  });
}

(function() {
  var element = this.Element;
  this.Element = function(tagName, attributes) {
    attributes = attributes || { };
    tagName = tagName.toLowerCase();
    var cache = Element.cache;
    if (Prototype.Browser.IE && attributes.name) {
      tagName = '<' + tagName + ' name="' + attributes.name + '">';
      delete attributes.name;
      return Element.writeAttribute(document.createElement(tagName), attributes);
    }
    if (!cache[tagName]) cache[tagName] = Element.extend(document.createElement(tagName));
    return Element.writeAttribute(cache[tagName].cloneNode(false), attributes);
  };
  Object.extend(this.Element, element || { });
}).call(window);

Element.cache = { };

Element.Methods = {
  visible: function(element) {
    return $(element).style.display != 'none';
  },

  toggle: function(element) {
    element = $(element);
    Element[Element.visible(element) ? 'hide' : 'show'](element);
    return element;
  },

  hide: function(element) {
    $(element).style.display = 'none';
    return element;
  },

  show: function(element) {
    $(element).style.display = '';
    return element;
  },

  remove: function(element) {
    element = $(element);
    element.parentNode.removeChild(element);
    return element;
  },

  update: function(element, content) {
    element = $(element);
    if (content && content.toElement) content = content.toElement();
    if (Object.isElement(content)) return element.update().insert(content);
    content = Object.toHTML(content);
    element.innerHTML = content.stripScripts();
    content.evalScripts.bind(content).defer();
    return element;
  },

  replace: function(element, content) {
    element = $(element);
    if (content && content.toElement) content = content.toElement();
    else if (!Object.isElement(content)) {
      content = Object.toHTML(content);
      var range = element.ownerDocument.createRange();
      range.selectNode(element);
      content.evalScripts.bind(content).defer();
      content = range.createContextualFragment(content.stripScripts());
    }
    element.parentNode.replaceChild(content, element);
    return element;
  },

  insert: function(element, insertions) {
    element = $(element);

    if (Object.isString(insertions) || Object.isNumber(insertions) ||
        Object.isElement(insertions) || (insertions && (insertions.toElement || insertions.toHTML)))
          insertions = {bottom:insertions};

    var content, insert, tagName, childNodes;

    for (var position in insertions) {
      content  = insertions[position];
      position = position.toLowerCase();
      insert = Element._insertionTranslations[position];

      if (content && content.toElement) content = content.toElement();
      if (Object.isElement(content)) {
        insert(element, content);
        continue;
      }

      content = Object.toHTML(content);

      tagName = ((position == 'before' || position == 'after')
        ? element.parentNode : element).tagName.toUpperCase();

      childNodes = Element._getContentFromAnonymousElement(tagName, content.stripScripts());

      if (position == 'top' || position == 'after') childNodes.reverse();
      childNodes.each(insert.curry(element));

      content.evalScripts.bind(content).defer();
    }

    return element;
  },

  wrap: function(element, wrapper, attributes) {
    element = $(element);
    if (Object.isElement(wrapper))
      $(wrapper).writeAttribute(attributes || { });
    else if (Object.isString(wrapper)) wrapper = new Element(wrapper, attributes);
    else wrapper = new Element('div', wrapper);
    if (element.parentNode)
      element.parentNode.replaceChild(wrapper, element);
    wrapper.appendChild(element);
    return wrapper;
  },

  inspect: function(element) {
    element = $(element);
    var result = '<' + element.tagName.toLowerCase();
    $H({'id': 'id', 'className': 'class'}).each(function(pair) {
      var property = pair.first(), attribute = pair.last();
      var value = (element[property] || '').toString();
      if (value) result += ' ' + attribute + '=' + value.inspect(true);
    });
    return result + '>';
  },

  recursivelyCollect: function(element, property) {
    element = $(element);
    var elements = [];
    while (element = element[property])
      if (element.nodeType == 1)
        elements.push(Element.extend(element));
    return elements;
  },

  ancestors: function(element) {
    return $(element).recursivelyCollect('parentNode');
  },

  descendants: function(element) {
    return $(element).select("*");
  },

  firstDescendant: function(element) {
    element = $(element).firstChild;
    while (element && element.nodeType != 1) element = element.nextSibling;
    return $(element);
  },

  immediateDescendants: function(element) {
    if (!(element = $(element).firstChild)) return [];
    while (element && element.nodeType != 1) element = element.nextSibling;
    if (element) return [element].concat($(element).nextSiblings());
    return [];
  },

  previousSiblings: function(element) {
    return $(element).recursivelyCollect('previousSibling');
  },

  nextSiblings: function(element) {
    return $(element).recursivelyCollect('nextSibling');
  },

  siblings: function(element) {
    element = $(element);
    return element.previousSiblings().reverse().concat(element.nextSiblings());
  },

  match: function(element, selector) {
    if (Object.isString(selector))
      selector = new Selector(selector);
    return selector.match($(element));
  },

  up: function(element, expression, index) {
    element = $(element);
    if (arguments.length == 1) return $(element.parentNode);
    var ancestors = element.ancestors();
    return Object.isNumber(expression) ? ancestors[expression] :
      Selector.findElement(ancestors, expression, index);
  },


  down: function(element, expression, index) {
    element = $(element);
    if (arguments.length == 1) return element.firstDescendant();
    return Object.isNumber(expression) ? element.descendants()[expression] :
      element.select(expression)[index || 0];
  },

  previous: function(element, expression, index) {
    element = $(element);
    if (arguments.length == 1) return $(Selector.handlers.previousElementSibling(element));
    var previousSiblings = element.previousSiblings();
    return Object.isNumber(expression) ? previousSiblings[expression] :
      Selector.findElement(previousSiblings, expression, index);
  },

  next: function(element, expression, index) {
    element = $(element);
    if (arguments.length == 1) return $(Selector.handlers.nextElementSibling(element));
    var nextSiblings = element.nextSiblings();
    return Object.isNumber(expression) ? nextSiblings[expression] :
      Selector.findElement(nextSiblings, expression, index);
  },

  select: function() {
    var args = $A(arguments), element = $(args.shift());
    return Selector.findChildElements(element, args);
  },

  adjacent: function() {
    var args = $A(arguments), element = $(args.shift());
    return Selector.findChildElements(element.parentNode, args).without(element);
  },

  identify: function(element) {
    element = $(element);
    var id = element.readAttribute('id'), self = arguments.callee;
    if (id) return id;
    do { id = 'anonymous_element_' + self.counter++ } while ($(id));
    element.writeAttribute('id', id);
    return id;
  },

  readAttribute: function(element, name) {
    element = $(element);
    if (Prototype.Browser.IE) {
      var t = Element._attributeTranslations.read;
      if (t.values[name]) return t.values[name](element, name);
      if (t.names[name]) name = t.names[name];
      if (name.include(':')) {
        return (!element.attributes || !element.attributes[name]) ? null :
         element.attributes[name].value;
      }
    }
    return element.getAttribute(name);
  },

  writeAttribute: function(element, name, value) {
    element = $(element);
    var attributes = { }, t = Element._attributeTranslations.write;

    if (typeof name == 'object') attributes = name;
    else attributes[name] = Object.isUndefined(value) ? true : value;

    for (var attr in attributes) {
      name = t.names[attr] || attr;
      value = attributes[attr];
      if (t.values[attr]) name = t.values[attr](element, value);
      if (value === false || value === null)
        element.removeAttribute(name);
      else if (value === true)
        element.setAttribute(name, name);
      else element.setAttribute(name, value);
    }
    return element;
  },

  getHeight: function(element) {
    return $(element).getDimensions().height;
  },

  getWidth: function(element) {
    return $(element).getDimensions().width;
  },

  classNames: function(element) {
    return new Element.ClassNames(element);
  },

  hasClassName: function(element, className) {
    if (!(element = $(element))) return;
    var elementClassName = element.className;
    return (elementClassName.length > 0 && (elementClassName == className ||
      new RegExp("(^|\\s)" + className + "(\\s|$)").test(elementClassName)));
  },

  addClassName: function(element, className) {
    if (!(element = $(element))) return;
    if (!element.hasClassName(className))
      element.className += (element.className ? ' ' : '') + className;
    return element;
  },

  removeClassName: function(element, className) {
    if (!(element = $(element))) return;
    element.className = element.className.replace(
      new RegExp("(^|\\s+)" + className + "(\\s+|$)"), ' ').strip();
    return element;
  },

  toggleClassName: function(element, className) {
    if (!(element = $(element))) return;
    return element[element.hasClassName(className) ?
      'removeClassName' : 'addClassName'](className);
  },

  // removes whitespace-only text node children
  cleanWhitespace: function(element) {
    element = $(element);
    var node = element.firstChild;
    while (node) {
      var nextNode = node.nextSibling;
      if (node.nodeType == 3 && !/\S/.test(node.nodeValue))
        element.removeChild(node);
      node = nextNode;
    }
    return element;
  },

  empty: function(element) {
    return $(element).innerHTML.blank();
  },

  descendantOf: function(element, ancestor) {
    element = $(element), ancestor = $(ancestor);
    var originalAncestor = ancestor;

    if (element.compareDocumentPosition)
      return (element.compareDocumentPosition(ancestor) & 8) === 8;

    if (element.sourceIndex && !Prototype.Browser.Opera) {
      var e = element.sourceIndex, a = ancestor.sourceIndex,
       nextAncestor = ancestor.nextSibling;
      if (!nextAncestor) {
        do { ancestor = ancestor.parentNode; }
        while (!(nextAncestor = ancestor.nextSibling) && ancestor.parentNode);
      }
      if (nextAncestor && nextAncestor.sourceIndex)
       return (e > a && e < nextAncestor.sourceIndex);
    }

    while (element = element.parentNode)
      if (element == originalAncestor) return true;
    return false;
  },

  scrollTo: function(element) {
    element = $(element);
    var pos = element.cumulativeOffset();
    window.scrollTo(pos[0], pos[1]);
    return element;
  },

  getStyle: function(element, style) {
    element = $(element);
    style = style == 'float' ? 'cssFloat' : style.camelize();
    var value = element.style[style];
    if (!value) {
      var css = document.defaultView.getComputedStyle(element, null);
      value = css ? css[style] : null;
    }
    if (style == 'opacity') return value ? parseFloat(value) : 1.0;
    return value == 'auto' ? null : value;
  },

  getOpacity: function(element) {
    return $(element).getStyle('opacity');
  },

  setStyle: function(element, styles) {
    element = $(element);
    var elementStyle = element.style, match;
    if (Object.isString(styles)) {
      element.style.cssText += ';' + styles;
      return styles.include('opacity') ?
        element.setOpacity(styles.match(/opacity:\s*(\d?\.?\d*)/)[1]) : element;
    }
    for (var property in styles)
      if (property == 'opacity') element.setOpacity(styles[property]);
      else
        elementStyle[(property == 'float' || property == 'cssFloat') ?
          (Object.isUndefined(elementStyle.styleFloat) ? 'cssFloat' : 'styleFloat') :
            property] = styles[property];

    return element;
  },

  setOpacity: function(element, value) {
    element = $(element);
    element.style.opacity = (value == 1 || value === '') ? '' :
      (value < 0.00001) ? 0 : value;
    return element;
  },

  getDimensions: function(element) {
    element = $(element);
    var display = $(element).getStyle('display');
    if (display != 'none' && display != null) // Safari bug
      return {width: element.offsetWidth, height: element.offsetHeight};

    // All *Width and *Height properties give 0 on elements with display none,
    // so enable the element temporarily
    var els = element.style;
    var originalVisibility = els.visibility;
    var originalPosition = els.position;
    var originalDisplay = els.display;
    els.visibility = 'hidden';
    els.position = 'absolute';
    els.display = 'block';
    var originalWidth = element.clientWidth;
    var originalHeight = element.clientHeight;
    els.display = originalDisplay;
    els.position = originalPosition;
    els.visibility = originalVisibility;
    return {width: originalWidth, height: originalHeight};
  },

  makePositioned: function(element) {
    element = $(element);
    var pos = Element.getStyle(element, 'position');
    if (pos == 'static' || !pos) {
      element._madePositioned = true;
      element.style.position = 'relative';
      // Opera returns the offset relative to the positioning context, when an
      // element is position relative but top and left have not been defined
      if (window.opera) {
        element.style.top = 0;
        element.style.left = 0;
      }
    }
    return element;
  },

  undoPositioned: function(element) {
    element = $(element);
    if (element._madePositioned) {
      element._madePositioned = undefined;
      element.style.position =
        element.style.top =
        element.style.left =
        element.style.bottom =
        element.style.right = '';
    }
    return element;
  },

  makeClipping: function(element) {
    element = $(element);
    if (element._overflow) return element;
    element._overflow = Element.getStyle(element, 'overflow') || 'auto';
    if (element._overflow !== 'hidden')
      element.style.overflow = 'hidden';
    return element;
  },

  undoClipping: function(element) {
    element = $(element);
    if (!element._overflow) return element;
    element.style.overflow = element._overflow == 'auto' ? '' : element._overflow;
    element._overflow = null;
    return element;
  },

  cumulativeOffset: function(element) {
    var valueT = 0, valueL = 0;
    do {
      valueT += element.offsetTop  || 0;
      valueL += element.offsetLeft || 0;
      element = element.offsetParent;
    } while (element);
    return Element._returnOffset(valueL, valueT);
  },

  positionedOffset: function(element) {
    var valueT = 0, valueL = 0;
    do {
      valueT += element.offsetTop  || 0;
      valueL += element.offsetLeft || 0;
      element = element.offsetParent;
      if (element) {
        if (element.tagName == 'BODY') break;
        var p = Element.getStyle(element, 'position');
        if (p !== 'static') break;
      }
    } while (element);
    return Element._returnOffset(valueL, valueT);
  },

  absolutize: function(element) {
    element = $(element);
    if (element.getStyle('position') == 'absolute') return;
    // Position.prepare(); // To be done manually by Scripty when it needs it.

    var offsets = element.positionedOffset();
    var top     = offsets[1];
    var left    = offsets[0];
    var width   = element.clientWidth;
    var height  = element.clientHeight;

    element._originalLeft   = left - parseFloat(element.style.left  || 0);
    element._originalTop    = top  - parseFloat(element.style.top || 0);
    element._originalWidth  = element.style.width;
    element._originalHeight = element.style.height;

    element.style.position = 'absolute';
    element.style.top    = top + 'px';
    element.style.left   = left + 'px';
    element.style.width  = width + 'px';
    element.style.height = height + 'px';
    return element;
  },

  relativize: function(element) {
    element = $(element);
    if (element.getStyle('position') == 'relative') return;
    // Position.prepare(); // To be done manually by Scripty when it needs it.

    element.style.position = 'relative';
    var top  = parseFloat(element.style.top  || 0) - (element._originalTop || 0);
    var left = parseFloat(element.style.left || 0) - (element._originalLeft || 0);

    element.style.top    = top + 'px';
    element.style.left   = left + 'px';
    element.style.height = element._originalHeight;
    element.style.width  = element._originalWidth;
    return element;
  },

  cumulativeScrollOffset: function(element) {
    var valueT = 0, valueL = 0;
    do {
      valueT += element.scrollTop  || 0;
      valueL += element.scrollLeft || 0;
      element = element.parentNode;
    } while (element);
    return Element._returnOffset(valueL, valueT);
  },

  getOffsetParent: function(element) {
    if (element.offsetParent) return $(element.offsetParent);
    if (element == document.body) return $(element);

    while ((element = element.parentNode) && element != document.body)
      if (Element.getStyle(element, 'position') != 'static')
        return $(element);

    return $(document.body);
  },

  viewportOffset: function(forElement) {
    var valueT = 0, valueL = 0;

    var element = forElement;
    do {
      valueT += element.offsetTop  || 0;
      valueL += element.offsetLeft || 0;

      // Safari fix
      if (element.offsetParent == document.body &&
        Element.getStyle(element, 'position') == 'absolute') break;

    } while (element = element.offsetParent);

    element = forElement;
    do {
      if (!Prototype.Browser.Opera || element.tagName == 'BODY') {
        valueT -= element.scrollTop  || 0;
        valueL -= element.scrollLeft || 0;
      }
    } while (element = element.parentNode);

    return Element._returnOffset(valueL, valueT);
  },

  clonePosition: function(element, source) {
    var options = Object.extend({
      setLeft:    true,
      setTop:     true,
      setWidth:   true,
      setHeight:  true,
      offsetTop:  0,
      offsetLeft: 0
    }, arguments[2] || { });

    // find page position of source
    source = $(source);
    var p = source.viewportOffset();

    // find coordinate system to use
    element = $(element);
    var delta = [0, 0];
    var parent = null;
    // delta [0,0] will do fine with position: fixed elements,
    // position:absolute needs offsetParent deltas
    if (Element.getStyle(element, 'position') == 'absolute') {
      parent = element.getOffsetParent();
      delta = parent.viewportOffset();
    }

    // correct by body offsets (fixes Safari)
    if (parent == document.body) {
      delta[0] -= document.body.offsetLeft;
      delta[1] -= document.body.offsetTop;
    }

    // set position
    if (options.setLeft)   element.style.left  = (p[0] - delta[0] + options.offsetLeft) + 'px';
    if (options.setTop)    element.style.top   = (p[1] - delta[1] + options.offsetTop) + 'px';
    if (options.setWidth)  element.style.width = source.offsetWidth + 'px';
    if (options.setHeight) element.style.height = source.offsetHeight + 'px';
    return element;
  }
};

Element.Methods.identify.counter = 1;

Object.extend(Element.Methods, {
  getElementsBySelector: Element.Methods.select,
  childElements: Element.Methods.immediateDescendants
});

Element._attributeTranslations = {
  write: {
    names: {
      className: 'class',
      htmlFor:   'for'
    },
    values: { }
  }
};

if (Prototype.Browser.Opera) {
  Element.Methods.getStyle = Element.Methods.getStyle.wrap(
    function(proceed, element, style) {
      switch (style) {
        case 'left': case 'top': case 'right': case 'bottom':
          if (proceed(element, 'position') === 'static') return null;
        case 'height': case 'width':
          // returns '0px' for hidden elements; we want it to return null
          if (!Element.visible(element)) return null;

          // returns the border-box dimensions rather than the content-box
          // dimensions, so we subtract padding and borders from the value
          var dim = parseInt(proceed(element, style), 10);

          if (dim !== element['offset' + style.capitalize()])
            return dim + 'px';

          var properties;
          if (style === 'height') {
            properties = ['border-top-width', 'padding-top',
             'padding-bottom', 'border-bottom-width'];
          }
          else {
            properties = ['border-left-width', 'padding-left',
             'padding-right', 'border-right-width'];
          }
          return properties.inject(dim, function(memo, property) {
            var val = proceed(element, property);
            return val === null ? memo : memo - parseInt(val, 10);
          }) + 'px';
        default: return proceed(element, style);
      }
    }
  );

  Element.Methods.readAttribute = Element.Methods.readAttribute.wrap(
    function(proceed, element, attribute) {
      if (attribute === 'title') return element.title;
      return proceed(element, attribute);
    }
  );
}

else if (Prototype.Browser.IE) {
  // IE doesn't report offsets correctly for static elements, so we change them
  // to "relative" to get the values, then change them back.
  Element.Methods.getOffsetParent = Element.Methods.getOffsetParent.wrap(
    function(proceed, element) {
      element = $(element);
      var position = element.getStyle('position');
      if (position !== 'static') return proceed(element);
      element.setStyle({ position: 'relative' });
      var value = proceed(element);
      element.setStyle({ position: position });
      return value;
    }
  );

  $w('positionedOffset viewportOffset').each(function(method) {
    Element.Methods[method] = Element.Methods[method].wrap(
      function(proceed, element) {
        element = $(element);
        var position = element.getStyle('position');
        if (position !== 'static') return proceed(element);
        // Trigger hasLayout on the offset parent so that IE6 reports
        // accurate offsetTop and offsetLeft values for position: fixed.
        var offsetParent = element.getOffsetParent();
        if (offsetParent && offsetParent.getStyle('position') === 'fixed')
          offsetParent.setStyle({ zoom: 1 });
        element.setStyle({ position: 'relative' });
        var value = proceed(element);
        element.setStyle({ position: position });
        return value;
      }
    );
  });

  Element.Methods.getStyle = function(element, style) {
    element = $(element);
    style = (style == 'float' || style == 'cssFloat') ? 'styleFloat' : style.camelize();
    var value = element.style[style];
    if (!value && element.currentStyle) value = element.currentStyle[style];

    if (style == 'opacity') {
      if (value = (element.getStyle('filter') || '').match(/alpha\(opacity=(.*)\)/))
        if (value[1]) return parseFloat(value[1]) / 100;
      return 1.0;
    }

    if (value == 'auto') {
      if ((style == 'width' || style == 'height') && (element.getStyle('display') != 'none'))
        return element['offset' + style.capitalize()] + 'px';
      return null;
    }
    return value;
  };

  Element.Methods.setOpacity = function(element, value) {
    function stripAlpha(filter){
      return filter.replace(/alpha\([^\)]*\)/gi,'');
    }
    element = $(element);
    var currentStyle = element.currentStyle;
    if ((currentStyle && !currentStyle.hasLayout) ||
      (!currentStyle && element.style.zoom == 'normal'))
        element.style.zoom = 1;

    var filter = element.getStyle('filter'), style = element.style;
    if (value == 1 || value === '') {
      (filter = stripAlpha(filter)) ?
        style.filter = filter : style.removeAttribute('filter');
      return element;
    } else if (value < 0.00001) value = 0;
    style.filter = stripAlpha(filter) +
      'alpha(opacity=' + (value * 100) + ')';
    return element;
  };

  Element._attributeTranslations = {
    read: {
      names: {
        'class': 'className',
        'for':   'htmlFor'
      },
      values: {
        _getAttr: function(element, attribute) {
          return element.getAttribute(attribute, 2);
        },
        _getAttrNode: function(element, attribute) {
          var node = element.getAttributeNode(attribute);
          return node ? node.value : "";
        },
        _getEv: function(element, attribute) {
          attribute = element.getAttribute(attribute);
          return attribute ? attribute.toString().slice(23, -2) : null;
        },
        _flag: function(element, attribute) {
          return $(element).hasAttribute(attribute) ? attribute : null;
        },
        style: function(element) {
          return element.style.cssText.toLowerCase();
        },
        title: function(element) {
          return element.title;
        }
      }
    }
  };

  Element._attributeTranslations.write = {
    names: Object.extend({
      cellpadding: 'cellPadding',
      cellspacing: 'cellSpacing'
    }, Element._attributeTranslations.read.names),
    values: {
      checked: function(element, value) {
        element.checked = !!value;
      },

      style: function(element, value) {
        element.style.cssText = value ? value : '';
      }
    }
  };

  Element._attributeTranslations.has = {};

  $w('colSpan rowSpan vAlign dateTime accessKey tabIndex ' +
      'encType maxLength readOnly longDesc').each(function(attr) {
    Element._attributeTranslations.write.names[attr.toLowerCase()] = attr;
    Element._attributeTranslations.has[attr.toLowerCase()] = attr;
  });

  (function(v) {
    Object.extend(v, {
      href:        v._getAttr,
      src:         v._getAttr,
      type:        v._getAttr,
      action:      v._getAttrNode,
      disabled:    v._flag,
      checked:     v._flag,
      readonly:    v._flag,
      multiple:    v._flag,
      onload:      v._getEv,
      onunload:    v._getEv,
      onclick:     v._getEv,
      ondblclick:  v._getEv,
      onmousedown: v._getEv,
      onmouseup:   v._getEv,
      onmouseover: v._getEv,
      onmousemove: v._getEv,
      onmouseout:  v._getEv,
      onfocus:     v._getEv,
      onblur:      v._getEv,
      onkeypress:  v._getEv,
      onkeydown:   v._getEv,
      onkeyup:     v._getEv,
      onsubmit:    v._getEv,
      onreset:     v._getEv,
      onselect:    v._getEv,
      onchange:    v._getEv
    });
  })(Element._attributeTranslations.read.values);
}

else if (Prototype.Browser.Gecko && /rv:1\.8\.0/.test(navigator.userAgent)) {
  Element.Methods.setOpacity = function(element, value) {
    element = $(element);
    element.style.opacity = (value == 1) ? 0.999999 :
      (value === '') ? '' : (value < 0.00001) ? 0 : value;
    return element;
  };
}

else if (Prototype.Browser.WebKit) {
  Element.Methods.setOpacity = function(element, value) {
    element = $(element);
    element.style.opacity = (value == 1 || value === '') ? '' :
      (value < 0.00001) ? 0 : value;

    if (value == 1)
      if(element.tagName == 'IMG' && element.width) {
        element.width++; element.width--;
      } else try {
        var n = document.createTextNode(' ');
        element.appendChild(n);
        element.removeChild(n);
      } catch (e) { }

    return element;
  };

  // Safari returns margins on body which is incorrect if the child is absolutely
  // positioned.  For performance reasons, redefine Element#cumulativeOffset for
  // KHTML/WebKit only.
  Element.Methods.cumulativeOffset = function(element) {
    var valueT = 0, valueL = 0;
    do {
      valueT += element.offsetTop  || 0;
      valueL += element.offsetLeft || 0;
      if (element.offsetParent == document.body)
        if (Element.getStyle(element, 'position') == 'absolute') break;

      element = element.offsetParent;
    } while (element);

    return Element._returnOffset(valueL, valueT);
  };
}

if (Prototype.Browser.IE || Prototype.Browser.Opera) {
  // IE and Opera are missing .innerHTML support for TABLE-related and SELECT elements
  Element.Methods.update = function(element, content) {
    element = $(element);

    if (content && content.toElement) content = content.toElement();
    if (Object.isElement(content)) return element.update().insert(content);

    content = Object.toHTML(content);
    var tagName = element.tagName.toUpperCase();

    if (tagName in Element._insertionTranslations.tags) {
      $A(element.childNodes).each(function(node) { element.removeChild(node) });
      Element._getContentFromAnonymousElement(tagName, content.stripScripts())
        .each(function(node) { element.appendChild(node) });
    }
    else element.innerHTML = content.stripScripts();

    content.evalScripts.bind(content).defer();
    return element;
  };
}

if ('outerHTML' in document.createElement('div')) {
  Element.Methods.replace = function(element, content) {
    element = $(element);

    if (content && content.toElement) content = content.toElement();
    if (Object.isElement(content)) {
      element.parentNode.replaceChild(content, element);
      return element;
    }

    content = Object.toHTML(content);
    var parent = element.parentNode, tagName = parent.tagName.toUpperCase();

    if (Element._insertionTranslations.tags[tagName]) {
      var nextSibling = element.next();
      var fragments = Element._getContentFromAnonymousElement(tagName, content.stripScripts());
      parent.removeChild(element);
      if (nextSibling)
        fragments.each(function(node) { parent.insertBefore(node, nextSibling) });
      else
        fragments.each(function(node) { parent.appendChild(node) });
    }
    else element.outerHTML = content.stripScripts();

    content.evalScripts.bind(content).defer();
    return element;
  };
}

Element._returnOffset = function(l, t) {
  var result = [l, t];
  result.left = l;
  result.top = t;
  return result;
};

Element._getContentFromAnonymousElement = function(tagName, html) {
  var div = new Element('div'), t = Element._insertionTranslations.tags[tagName];
  if (t) {
    div.innerHTML = t[0] + html + t[1];
    t[2].times(function() { div = div.firstChild });
  } else div.innerHTML = html;
  return $A(div.childNodes);
};

Element._insertionTranslations = {
  before: function(element, node) {
    element.parentNode.insertBefore(node, element);
  },
  top: function(element, node) {
    element.insertBefore(node, element.firstChild);
  },
  bottom: function(element, node) {
    element.appendChild(node);
  },
  after: function(element, node) {
    element.parentNode.insertBefore(node, element.nextSibling);
  },
  tags: {
    TABLE:  ['<table>',                '</table>',                   1],
    TBODY:  ['<table><tbody>',         '</tbody></table>',           2],
    TR:     ['<table><tbody><tr>',     '</tr></tbody></table>',      3],
    TD:     ['<table><tbody><tr><td>', '</td></tr></tbody></table>', 4],
    SELECT: ['<select>',               '</select>',                  1]
  }
};

(function() {
  Object.extend(this.tags, {
    THEAD: this.tags.TBODY,
    TFOOT: this.tags.TBODY,
    TH:    this.tags.TD
  });
}).call(Element._insertionTranslations);

Element.Methods.Simulated = {
  hasAttribute: function(element, attribute) {
    attribute = Element._attributeTranslations.has[attribute] || attribute;
    var node = $(element).getAttributeNode(attribute);
    return node && node.specified;
  }
};

Element.Methods.ByTag = { };

Object.extend(Element, Element.Methods);

if (!Prototype.BrowserFeatures.ElementExtensions &&
    document.createElement('div').__proto__) {
  window.HTMLElement = { };
  window.HTMLElement.prototype = document.createElement('div').__proto__;
  Prototype.BrowserFeatures.ElementExtensions = true;
}

Element.extend = (function() {
  if (Prototype.BrowserFeatures.SpecificElementExtensions)
    return Prototype.K;

  var Methods = { }, ByTag = Element.Methods.ByTag;

  var extend = Object.extend(function(element) {
    if (!element || element._extendedByPrototype ||
        element.nodeType != 1 || element == window) return element;

    var methods = Object.clone(Methods),
      tagName = element.tagName, property, value;

    // extend methods for specific tags
    if (ByTag[tagName]) Object.extend(methods, ByTag[tagName]);

    for (property in methods) {
      value = methods[property];
      if (Object.isFunction(value) && !(property in element))
        element[property] = value.methodize();
    }

    element._extendedByPrototype = Prototype.emptyFunction;
    return element;

  }, {
    refresh: function() {
      // extend methods for all tags (Safari doesn't need this)
      if (!Prototype.BrowserFeatures.ElementExtensions) {
        Object.extend(Methods, Element.Methods);
        Object.extend(Methods, Element.Methods.Simulated);
      }
    }
  });

  extend.refresh();
  return extend;
})();

Element.hasAttribute = function(element, attribute) {
  if (element.hasAttribute) return element.hasAttribute(attribute);
  return Element.Methods.Simulated.hasAttribute(element, attribute);
};

Element.addMethods = function(methods) {
  var F = Prototype.BrowserFeatures, T = Element.Methods.ByTag;

  if (!methods) {
    Object.extend(Form, Form.Methods);
    Object.extend(Form.Element, Form.Element.Methods);
    Object.extend(Element.Methods.ByTag, {
      "FORM":     Object.clone(Form.Methods),
      "INPUT":    Object.clone(Form.Element.Methods),
      "SELECT":   Object.clone(Form.Element.Methods),
      "TEXTAREA": Object.clone(Form.Element.Methods)
    });
  }

  if (arguments.length == 2) {
    var tagName = methods;
    methods = arguments[1];
  }

  if (!tagName) Object.extend(Element.Methods, methods || { });
  else {
    if (Object.isArray(tagName)) tagName.each(extend);
    else extend(tagName);
  }

  function extend(tagName) {
    tagName = tagName.toUpperCase();
    if (!Element.Methods.ByTag[tagName])
      Element.Methods.ByTag[tagName] = { };
    Object.extend(Element.Methods.ByTag[tagName], methods);
  }

  function copy(methods, destination, onlyIfAbsent) {
    onlyIfAbsent = onlyIfAbsent || false;
    for (var property in methods) {
      var value = methods[property];
      if (!Object.isFunction(value)) continue;
      if (!onlyIfAbsent || !(property in destination))
        destination[property] = value.methodize();
    }
  }

  function findDOMClass(tagName) {
    var klass;
    var trans = {
      "OPTGROUP": "OptGroup", "TEXTAREA": "TextArea", "P": "Paragraph",
      "FIELDSET": "FieldSet", "UL": "UList", "OL": "OList", "DL": "DList",
      "DIR": "Directory", "H1": "Heading", "H2": "Heading", "H3": "Heading",
      "H4": "Heading", "H5": "Heading", "H6": "Heading", "Q": "Quote",
      "INS": "Mod", "DEL": "Mod", "A": "Anchor", "IMG": "Image", "CAPTION":
      "TableCaption", "COL": "TableCol", "COLGROUP": "TableCol", "THEAD":
      "TableSection", "TFOOT": "TableSection", "TBODY": "TableSection", "TR":
      "TableRow", "TH": "TableCell", "TD": "TableCell", "FRAMESET":
      "FrameSet", "IFRAME": "IFrame"
    };
    if (trans[tagName]) klass = 'HTML' + trans[tagName] + 'Element';
    if (window[klass]) return window[klass];
    klass = 'HTML' + tagName + 'Element';
    if (window[klass]) return window[klass];
    klass = 'HTML' + tagName.capitalize() + 'Element';
    if (window[klass]) return window[klass];

    window[klass] = { };
    window[klass].prototype = document.createElement(tagName).__proto__;
    return window[klass];
  }

  if (F.ElementExtensions) {
    copy(Element.Methods, HTMLElement.prototype);
    copy(Element.Methods.Simulated, HTMLElement.prototype, true);
  }

  if (F.SpecificElementExtensions) {
    for (var tag in Element.Methods.ByTag) {
      var klass = findDOMClass(tag);
      if (Object.isUndefined(klass)) continue;
      copy(T[tag], klass.prototype);
    }
  }

  Object.extend(Element, Element.Methods);
  delete Element.ByTag;

  if (Element.extend.refresh) Element.extend.refresh();
  Element.cache = { };
};

document.viewport = {
  getDimensions: function() {
    var dimensions = { };
    var B = Prototype.Browser;
    $w('width height').each(function(d) {
      var D = d.capitalize();
      dimensions[d] = (B.WebKit && !document.evaluate) ? self['inner' + D] :
        (B.Opera) ? document.body['client' + D] : document.documentElement['client' + D];
    });
    return dimensions;
  },

  getWidth: function() {
    return this.getDimensions().width;
  },

  getHeight: function() {
    return this.getDimensions().height;
  },

  getScrollOffsets: function() {
    return Element._returnOffset(
      window.pageXOffset || document.documentElement.scrollLeft || document.body.scrollLeft,
      window.pageYOffset || document.documentElement.scrollTop || document.body.scrollTop);
  }
};
/* Portions of the Selector class are derived from Jack SlocumÃ¢â?¬â?¢s DomQuery,
 * part of YUI-Ext version 0.40, distributed under the terms of an MIT-style
 * license.  Please see http://www.yui-ext.com/ for more information. */

var Selector = Class.create({
  initialize: function(expression) {
    this.expression = expression.strip();
    this.compileMatcher();
  },

  shouldUseXPath: function() {
    if (!Prototype.BrowserFeatures.XPath) return false;

    var e = this.expression;

    // Safari 3 chokes on :*-of-type and :empty
    if (Prototype.Browser.WebKit &&
     (e.include("-of-type") || e.include(":empty")))
      return false;

    // XPath can't do namespaced attributes, nor can it read
    // the "checked" property from DOM nodes
    if ((/(\[[\w-]*?:|:checked)/).test(this.expression))
      return false;

    return true;
  },

  compileMatcher: function() {
    if (this.shouldUseXPath())
      return this.compileXPathMatcher();

    var e = this.expression, ps = Selector.patterns, h = Selector.handlers,
        c = Selector.criteria, le, p, m;

    if (Selector._cache[e]) {
      this.matcher = Selector._cache[e];
      return;
    }

    this.matcher = ["this.matcher = function(root) {",
                    "var r = root, h = Selector.handlers, c = false, n;"];

    while (e && le != e && (/\S/).test(e)) {
      le = e;
      for (var i in ps) {
        p = ps[i];
        if (m = e.match(p)) {
          this.matcher.push(Object.isFunction(c[i]) ? c[i](m) :
    	      new Template(c[i]).evaluate(m));
          e = e.replace(m[0], '');
          break;
        }
      }
    }

    this.matcher.push("return h.unique(n);\n}");
    eval(this.matcher.join('\n'));
    Selector._cache[this.expression] = this.matcher;
  },

  compileXPathMatcher: function() {
    var e = this.expression, ps = Selector.patterns,
        x = Selector.xpath, le, m;

    if (Selector._cache[e]) {
      this.xpath = Selector._cache[e]; return;
    }

    this.matcher = ['.//*'];
    while (e && le != e && (/\S/).test(e)) {
      le = e;
      for (var i in ps) {
        if (m = e.match(ps[i])) {
          this.matcher.push(Object.isFunction(x[i]) ? x[i](m) :
            new Template(x[i]).evaluate(m));
          e = e.replace(m[0], '');
          break;
        }
      }
    }

    this.xpath = this.matcher.join('');
    Selector._cache[this.expression] = this.xpath;
  },

  findElements: function(root) {
    root = root || document;
    if (this.xpath) return document._getElementsByXPath(this.xpath, root);
    return this.matcher(root);
  },

  match: function(element) {
    this.tokens = [];

    var e = this.expression, ps = Selector.patterns, as = Selector.assertions;
    var le, p, m;

    while (e && le !== e && (/\S/).test(e)) {
      le = e;
      for (var i in ps) {
        p = ps[i];
        if (m = e.match(p)) {
          // use the Selector.assertions methods unless the selector
          // is too complex.
          if (as[i]) {
            this.tokens.push([i, Object.clone(m)]);
            e = e.replace(m[0], '');
          } else {
            // reluctantly do a document-wide search
            // and look for a match in the array
            return this.findElements(document).include(element);
          }
        }
      }
    }

    var match = true, name, matches;
    for (var i = 0, token; token = this.tokens[i]; i++) {
      name = token[0], matches = token[1];
      if (!Selector.assertions[name](element, matches)) {
        match = false; break;
      }
    }

    return match;
  },

  toString: function() {
    return this.expression;
  },

  inspect: function() {
    return "#<Selector:" + this.expression.inspect() + ">";
  }
});

Object.extend(Selector, {
  _cache: { },

  xpath: {
    descendant:   "//*",
    child:        "/*",
    adjacent:     "/following-sibling::*[1]",
    laterSibling: '/following-sibling::*',
    tagName:      function(m) {
      if (m[1] == '*') return '';
      return "[local-name()='" + m[1].toLowerCase() +
             "' or local-name()='" + m[1].toUpperCase() + "']";
    },
    className:    "[contains(concat(' ', @class, ' '), ' #{1} ')]",
    id:           "[@id='#{1}']",
    attrPresence: function(m) {
      m[1] = m[1].toLowerCase();
      return new Template("[@#{1}]").evaluate(m);
    },
    attr: function(m) {
      m[1] = m[1].toLowerCase();
      m[3] = m[5] || m[6];
      return new Template(Selector.xpath.operators[m[2]]).evaluate(m);
    },
    pseudo: function(m) {
      var h = Selector.xpath.pseudos[m[1]];
      if (!h) return '';
      if (Object.isFunction(h)) return h(m);
      return new Template(Selector.xpath.pseudos[m[1]]).evaluate(m);
    },
    operators: {
      '=':  "[@#{1}='#{3}']",
      '!=': "[@#{1}!='#{3}']",
      '^=': "[starts-with(@#{1}, '#{3}')]",
      '$=': "[substring(@#{1}, (string-length(@#{1}) - string-length('#{3}') + 1))='#{3}']",
      '*=': "[contains(@#{1}, '#{3}')]",
      '~=': "[contains(concat(' ', @#{1}, ' '), ' #{3} ')]",
      '|=': "[contains(concat('-', @#{1}, '-'), '-#{3}-')]"
    },
    pseudos: {
      'first-child': '[not(preceding-sibling::*)]',
      'last-child':  '[not(following-sibling::*)]',
      'only-child':  '[not(preceding-sibling::* or following-sibling::*)]',
      'empty':       "[count(*) = 0 and (count(text()) = 0 or translate(text(), ' \t\r\n', '') = '')]",
      'checked':     "[@checked]",
      'disabled':    "[@disabled]",
      'enabled':     "[not(@disabled)]",
      'not': function(m) {
        var e = m[6], p = Selector.patterns,
            x = Selector.xpath, le, v;

        var exclusion = [];
        while (e && le != e && (/\S/).test(e)) {
          le = e;
          for (var i in p) {
            if (m = e.match(p[i])) {
              v = Object.isFunction(x[i]) ? x[i](m) : new Template(x[i]).evaluate(m);
              exclusion.push("(" + v.substring(1, v.length - 1) + ")");
              e = e.replace(m[0], '');
              break;
            }
          }
        }
        return "[not(" + exclusion.join(" and ") + ")]";
      },
      'nth-child':      function(m) {
        return Selector.xpath.pseudos.nth("(count(./preceding-sibling::*) + 1) ", m);
      },
      'nth-last-child': function(m) {
        return Selector.xpath.pseudos.nth("(count(./following-sibling::*) + 1) ", m);
      },
      'nth-of-type':    function(m) {
        return Selector.xpath.pseudos.nth("position() ", m);
      },
      'nth-last-of-type': function(m) {
        return Selector.xpath.pseudos.nth("(last() + 1 - position()) ", m);
      },
      'first-of-type':  function(m) {
        m[6] = "1"; return Selector.xpath.pseudos['nth-of-type'](m);
      },
      'last-of-type':   function(m) {
        m[6] = "1"; return Selector.xpath.pseudos['nth-last-of-type'](m);
      },
      'only-of-type':   function(m) {
        var p = Selector.xpath.pseudos; return p['first-of-type'](m) + p['last-of-type'](m);
      },
      nth: function(fragment, m) {
        var mm, formula = m[6], predicate;
        if (formula == 'even') formula = '2n+0';
        if (formula == 'odd')  formula = '2n+1';
        if (mm = formula.match(/^(\d+)$/)) // digit only
          return '[' + fragment + "= " + mm[1] + ']';
        if (mm = formula.match(/^(-?\d*)?n(([+-])(\d+))?/)) { // an+b
          if (mm[1] == "-") mm[1] = -1;
          var a = mm[1] ? Number(mm[1]) : 1;
          var b = mm[2] ? Number(mm[2]) : 0;
          predicate = "[((#{fragment} - #{b}) mod #{a} = 0) and " +
          "((#{fragment} - #{b}) div #{a} >= 0)]";
          return new Template(predicate).evaluate({
            fragment: fragment, a: a, b: b });
        }
      }
    }
  },

  criteria: {
    tagName:      'n = h.tagName(n, r, "#{1}", c);      c = false;',
    className:    'n = h.className(n, r, "#{1}", c);    c = false;',
    id:           'n = h.id(n, r, "#{1}", c);           c = false;',
    attrPresence: 'n = h.attrPresence(n, r, "#{1}", c); c = false;',
    attr: function(m) {
      m[3] = (m[5] || m[6]);
      return new Template('n = h.attr(n, r, "#{1}", "#{3}", "#{2}", c); c = false;').evaluate(m);
    },
    pseudo: function(m) {
      if (m[6]) m[6] = m[6].replace(/"/g, '\\"');
      return new Template('n = h.pseudo(n, "#{1}", "#{6}", r, c); c = false;').evaluate(m);
    },
    descendant:   'c = "descendant";',
    child:        'c = "child";',
    adjacent:     'c = "adjacent";',
    laterSibling: 'c = "laterSibling";'
  },

  patterns: {
    // combinators must be listed first
    // (and descendant needs to be last combinator)
    laterSibling: /^\s*~\s*/,
    child:        /^\s*>\s*/,
    adjacent:     /^\s*\+\s*/,
    descendant:   /^\s/,

    // selectors follow
    tagName:      /^\s*(\*|[\w\-]+)(\b|$)?/,
    id:           /^#([\w\-\*]+)(\b|$)/,
    className:    /^\.([\w\-\*]+)(\b|$)/,
    pseudo:
/^:((first|last|nth|nth-last|only)(-child|-of-type)|empty|checked|(en|dis)abled|not)(\((.*?)\))?(\b|$|(?=\s|[:+~>]))/,
    attrPresence: /^\[([\w]+)\]/,
    attr:         /\[((?:[\w-]*:)?[\w-]+)\s*(?:([!^$*~|]?=)\s*((['"])([^\4]*?)\4|([^'"][^\]]*?)))?\]/
  },

  // for Selector.match and Element#match
  assertions: {
    tagName: function(element, matches) {
      return matches[1].toUpperCase() == element.tagName.toUpperCase();
    },

    className: function(element, matches) {
      return Element.hasClassName(element, matches[1]);
    },

    id: function(element, matches) {
      return element.id === matches[1];
    },

    attrPresence: function(element, matches) {
      return Element.hasAttribute(element, matches[1]);
    },

    attr: function(element, matches) {
      var nodeValue = Element.readAttribute(element, matches[1]);
      return nodeValue && Selector.operators[matches[2]](nodeValue, matches[5] || matches[6]);
    }
  },

  handlers: {
    // UTILITY FUNCTIONS
    // joins two collections
    concat: function(a, b) {
      for (var i = 0, node; node = b[i]; i++)
        a.push(node);
      return a;
    },

    // marks an array of nodes for counting
    mark: function(nodes) {
      var _true = Prototype.emptyFunction;
      for (var i = 0, node; node = nodes[i]; i++)
        node._countedByPrototype = _true;
      return nodes;
    },

    unmark: function(nodes) {
      for (var i = 0, node; node = nodes[i]; i++)
        node._countedByPrototype = undefined;
      return nodes;
    },

    // mark each child node with its position (for nth calls)
    // "ofType" flag indicates whether we're indexing for nth-of-type
    // rather than nth-child
    index: function(parentNode, reverse, ofType) {
      parentNode._countedByPrototype = Prototype.emptyFunction;
      if (reverse) {
        for (var nodes = parentNode.childNodes, i = nodes.length - 1, j = 1; i >= 0; i--) {
          var node = nodes[i];
          if (node.nodeType == 1 && (!ofType || node._countedByPrototype)) node.nodeIndex = j++;
        }
      } else {
        for (var i = 0, j = 1, nodes = parentNode.childNodes; node = nodes[i]; i++)
          if (node.nodeType == 1 && (!ofType || node._countedByPrototype)) node.nodeIndex = j++;
      }
    },

    // filters out duplicates and extends all nodes
    unique: function(nodes) {
      if (nodes.length == 0) return nodes;
      var results = [], n;
      for (var i = 0, l = nodes.length; i < l; i++)
        if (!(n = nodes[i])._countedByPrototype) {
          n._countedByPrototype = Prototype.emptyFunction;
          results.push(Element.extend(n));
        }
      return Selector.handlers.unmark(results);
    },

    // COMBINATOR FUNCTIONS
    descendant: function(nodes) {
      var h = Selector.handlers;
      for (var i = 0, results = [], node; node = nodes[i]; i++)
        h.concat(results, node.getElementsByTagName('*'));
      return results;
    },

    child: function(nodes) {
      var h = Selector.handlers;
      for (var i = 0, results = [], node; node = nodes[i]; i++) {
        for (var j = 0, child; child = node.childNodes[j]; j++)
          if (child.nodeType == 1 && child.tagName != '!') results.push(child);
      }
      return results;
    },

    adjacent: function(nodes) {
      for (var i = 0, results = [], node; node = nodes[i]; i++) {
        var next = this.nextElementSibling(node);
        if (next) results.push(next);
      }
      return results;
    },

    laterSibling: function(nodes) {
      var h = Selector.handlers;
      for (var i = 0, results = [], node; node = nodes[i]; i++)
        h.concat(results, Element.nextSiblings(node));
      return results;
    },

    nextElementSibling: function(node) {
      while (node = node.nextSibling)
	      if (node.nodeType == 1) return node;
      return null;
    },

    previousElementSibling: function(node) {
      while (node = node.previousSibling)
        if (node.nodeType == 1) return node;
      return null;
    },

    // TOKEN FUNCTIONS
    tagName: function(nodes, root, tagName, combinator) {
      var uTagName = tagName.toUpperCase();
      var results = [], h = Selector.handlers;
      if (nodes) {
        if (combinator) {
          // fastlane for ordinary descendant combinators
          if (combinator == "descendant") {
            for (var i = 0, node; node = nodes[i]; i++)
              h.concat(results, node.getElementsByTagName(tagName));
            return results;
          } else nodes = this[combinator](nodes);
          if (tagName == "*") return nodes;
        }
        for (var i = 0, node; node = nodes[i]; i++)
          if (node.tagName.toUpperCase() === uTagName) results.push(node);
        return results;
      } else return root.getElementsByTagName(tagName);
    },

    id: function(nodes, root, id, combinator) {
      var targetNode = $(id), h = Selector.handlers;
      if (!targetNode) return [];
      if (!nodes && root == document) return [targetNode];
      if (nodes) {
        if (combinator) {
          if (combinator == 'child') {
            for (var i = 0, node; node = nodes[i]; i++)
              if (targetNode.parentNode == node) return [targetNode];
          } else if (combinator == 'descendant') {
            for (var i = 0, node; node = nodes[i]; i++)
              if (Element.descendantOf(targetNode, node)) return [targetNode];
          } else if (combinator == 'adjacent') {
            for (var i = 0, node; node = nodes[i]; i++)
              if (Selector.handlers.previousElementSibling(targetNode) == node)
                return [targetNode];
          } else nodes = h[combinator](nodes);
        }
        for (var i = 0, node; node = nodes[i]; i++)
          if (node == targetNode) return [targetNode];
        return [];
      }
      return (targetNode && Element.descendantOf(targetNode, root)) ? [targetNode] : [];
    },

    className: function(nodes, root, className, combinator) {
      if (nodes && combinator) nodes = this[combinator](nodes);
      return Selector.handlers.byClassName(nodes, root, className);
    },

    byClassName: function(nodes, root, className) {
      if (!nodes) nodes = Selector.handlers.descendant([root]);
      var needle = ' ' + className + ' ';
      for (var i = 0, results = [], node, nodeClassName; node = nodes[i]; i++) {
        nodeClassName = node.className;
        if (nodeClassName.length == 0) continue;
        if (nodeClassName == className || (' ' + nodeClassName + ' ').include(needle))
          results.push(node);
      }
      return results;
    },

    attrPresence: function(nodes, root, attr, combinator) {
      if (!nodes) nodes = root.getElementsByTagName("*");
      if (nodes && combinator) nodes = this[combinator](nodes);
      var results = [];
      for (var i = 0, node; node = nodes[i]; i++)
        if (Element.hasAttribute(node, attr)) results.push(node);
      return results;
    },

    attr: function(nodes, root, attr, value, operator, combinator) {
      if (!nodes) nodes = root.getElementsByTagName("*");
      if (nodes && combinator) nodes = this[combinator](nodes);
      var handler = Selector.operators[operator], results = [];
      for (var i = 0, node; node = nodes[i]; i++) {
        var nodeValue = Element.readAttribute(node, attr);
        if (nodeValue === null) continue;
        if (handler(nodeValue, value)) results.push(node);
      }
      return results;
    },

    pseudo: function(nodes, name, value, root, combinator) {
      if (nodes && combinator) nodes = this[combinator](nodes);
      if (!nodes) nodes = root.getElementsByTagName("*");
      return Selector.pseudos[name](nodes, value, root);
    }
  },

  pseudos: {
    'first-child': function(nodes, value, root) {
      for (var i = 0, results = [], node; node = nodes[i]; i++) {
        if (Selector.handlers.previousElementSibling(node)) continue;
          results.push(node);
      }
      return results;
    },
    'last-child': function(nodes, value, root) {
      for (var i = 0, results = [], node; node = nodes[i]; i++) {
        if (Selector.handlers.nextElementSibling(node)) continue;
          results.push(node);
      }
      return results;
    },
    'only-child': function(nodes, value, root) {
      var h = Selector.handlers;
      for (var i = 0, results = [], node; node = nodes[i]; i++)
        if (!h.previousElementSibling(node) && !h.nextElementSibling(node))
          results.push(node);
      return results;
    },
    'nth-child':        function(nodes, formula, root) {
      return Selector.pseudos.nth(nodes, formula, root);
    },
    'nth-last-child':   function(nodes, formula, root) {
      return Selector.pseudos.nth(nodes, formula, root, true);
    },
    'nth-of-type':      function(nodes, formula, root) {
      return Selector.pseudos.nth(nodes, formula, root, false, true);
    },
    'nth-last-of-type': function(nodes, formula, root) {
      return Selector.pseudos.nth(nodes, formula, root, true, true);
    },
    'first-of-type':    function(nodes, formula, root) {
      return Selector.pseudos.nth(nodes, "1", root, false, true);
    },
    'last-of-type':     function(nodes, formula, root) {
      return Selector.pseudos.nth(nodes, "1", root, true, true);
    },
    'only-of-type':     function(nodes, formula, root) {
      var p = Selector.pseudos;
      return p['last-of-type'](p['first-of-type'](nodes, formula, root), formula, root);
    },

    // handles the an+b logic
    getIndices: function(a, b, total) {
      if (a == 0) return b > 0 ? [b] : [];
      return $R(1, total).inject([], function(memo, i) {
        if (0 == (i - b) % a && (i - b) / a >= 0) memo.push(i);
        return memo;
      });
    },

    // handles nth(-last)-child, nth(-last)-of-type, and (first|last)-of-type
    nth: function(nodes, formula, root, reverse, ofType) {
      if (nodes.length == 0) return [];
      if (formula == 'even') formula = '2n+0';
      if (formula == 'odd')  formula = '2n+1';
      var h = Selector.handlers, results = [], indexed = [], m;
      h.mark(nodes);
      for (var i = 0, node; node = nodes[i]; i++) {
        if (!node.parentNode._countedByPrototype) {
          h.index(node.parentNode, reverse, ofType);
          indexed.push(node.parentNode);
        }
      }
      if (formula.match(/^\d+$/)) { // just a number
        formula = Number(formula);
        for (var i = 0, node; node = nodes[i]; i++)
          if (node.nodeIndex == formula) results.push(node);
      } else if (m = formula.match(/^(-?\d*)?n(([+-])(\d+))?/)) { // an+b
        if (m[1] == "-") m[1] = -1;
        var a = m[1] ? Number(m[1]) : 1;
        var b = m[2] ? Number(m[2]) : 0;
        var indices = Selector.pseudos.getIndices(a, b, nodes.length);
        for (var i = 0, node, l = indices.length; node = nodes[i]; i++) {
          for (var j = 0; j < l; j++)
            if (node.nodeIndex == indices[j]) results.push(node);
        }
      }
      h.unmark(nodes);
      h.unmark(indexed);
      return results;
    },

    'empty': function(nodes, value, root) {
      for (var i = 0, results = [], node; node = nodes[i]; i++) {
        // IE treats comments as element nodes
        if (node.tagName == '!' || (node.firstChild && !node.innerHTML.match(/^\s*$/))) continue;
        results.push(node);
      }
      return results;
    },

    'not': function(nodes, selector, root) {
      var h = Selector.handlers, selectorType, m;
      var exclusions = new Selector(selector).findElements(root);
      h.mark(exclusions);
      for (var i = 0, results = [], node; node = nodes[i]; i++)
        if (!node._countedByPrototype) results.push(node);
      h.unmark(exclusions);
      return results;
    },

    'enabled': function(nodes, value, root) {
      for (var i = 0, results = [], node; node = nodes[i]; i++)
        if (!node.disabled) results.push(node);
      return results;
    },

    'disabled': function(nodes, value, root) {
      for (var i = 0, results = [], node; node = nodes[i]; i++)
        if (node.disabled) results.push(node);
      return results;
    },

    'checked': function(nodes, value, root) {
      for (var i = 0, results = [], node; node = nodes[i]; i++)
        if (node.checked) results.push(node);
      return results;
    }
  },

  operators: {
    '=':  function(nv, v) { return nv == v; },
    '!=': function(nv, v) { return nv != v; },
    '^=': function(nv, v) { return nv.startsWith(v); },
    '$=': function(nv, v) { return nv.endsWith(v); },
    '*=': function(nv, v) { return nv.include(v); },
    '~=': function(nv, v) { return (' ' + nv + ' ').include(' ' + v + ' '); },
    '|=': function(nv, v) { return ('-' + nv.toUpperCase() + '-').include('-' + v.toUpperCase() + '-'); }
  },

  split: function(expression) {
    var expressions = [];
    expression.scan(/(([\w#:.~>+()\s-]+|\*|\[.*?\])+)\s*(,|$)/, function(m) {
      expressions.push(m[1].strip());
    });
    return expressions;
  },

  matchElements: function(elements, expression) {
    var matches = $$(expression), h = Selector.handlers;
    h.mark(matches);
    for (var i = 0, results = [], element; element = elements[i]; i++)
      if (element._countedByPrototype) results.push(element);
    h.unmark(matches);
    return results;
  },

  findElement: function(elements, expression, index) {
    if (Object.isNumber(expression)) {
      index = expression; expression = false;
    }
    return Selector.matchElements(elements, expression || '*')[index || 0];
  },

  findChildElements: function(element, expressions) {
    expressions = Selector.split(expressions.join(','));
    var results = [], h = Selector.handlers;
    for (var i = 0, l = expressions.length, selector; i < l; i++) {
      selector = new Selector(expressions[i].strip());
      h.concat(results, selector.findElements(element));
    }
    return (l > 1) ? h.unique(results) : results;
  }
});

if (Prototype.Browser.IE) {
  Object.extend(Selector.handlers, {
    // IE returns comment nodes on getElementsByTagName("*").
    // Filter them out.
    concat: function(a, b) {
      for (var i = 0, node; node = b[i]; i++)
        if (node.tagName !== "!") a.push(node);
      return a;
    },

    // IE improperly serializes _countedByPrototype in (inner|outer)HTML.
    unmark: function(nodes) {
      for (var i = 0, node; node = nodes[i]; i++)
        node.removeAttribute('_countedByPrototype');
      return nodes;
    }
  });
}

function $$() {
  return Selector.findChildElements(document, $A(arguments));
}
var Form = {
  reset: function(form) {
    $(form).reset();
    return form;
  },

  serializeElements: function(elements, options) {
    if (typeof options != 'object') options = { hash: !!options };
    else if (Object.isUndefined(options.hash)) options.hash = true;
    var key, value, submitted = false, submit = options.submit;

    var data = elements.inject({ }, function(result, element) {
      if (!element.disabled && element.name) {
        key = element.name; value = $(element).getValue();
        if (value != null && (element.type != 'submit' || (!submitted &&
            submit !== false && (!submit || key == submit) && (submitted = true)))) {
          if (key in result) {
            // a key is already present; construct an array of values
            if (!Object.isArray(result[key])) result[key] = [result[key]];
            result[key].push(value);
          }
          else result[key] = value;
        }
      }
      return result;
    });

    return options.hash ? data : Object.toQueryString(data);
  }
};

Form.Methods = {
  serialize: function(form, options) {
    return Form.serializeElements(Form.getElements(form), options);
  },

  getElements: function(form) {
    return $A($(form).getElementsByTagName('*')).inject([],
      function(elements, child) {
        if (Form.Element.Serializers[child.tagName.toLowerCase()])
          elements.push(Element.extend(child));
        return elements;
      }
    );
  },

  getInputs: function(form, typeName, name) {
    form = $(form);
    var inputs = form.getElementsByTagName('input');

    if (!typeName && !name) return $A(inputs).map(Element.extend);

    for (var i = 0, matchingInputs = [], length = inputs.length; i < length; i++) {
      var input = inputs[i];
      if ((typeName && input.type != typeName) || (name && input.name != name))
        continue;
      matchingInputs.push(Element.extend(input));
    }

    return matchingInputs;
  },

  disable: function(form) {
    form = $(form);
    Form.getElements(form).invoke('disable');
    return form;
  },

  enable: function(form) {
    form = $(form);
    Form.getElements(form).invoke('enable');
    return form;
  },

  findFirstElement: function(form) {
    var elements = $(form).getElements().findAll(function(element) {
      return 'hidden' != element.type && !element.disabled;
    });
    var firstByIndex = elements.findAll(function(element) {
      return element.hasAttribute('tabIndex') && element.tabIndex >= 0;
    }).sortBy(function(element) { return element.tabIndex }).first();

    return firstByIndex ? firstByIndex : elements.find(function(element) {
      return ['input', 'select', 'textarea'].include(element.tagName.toLowerCase());
    });
  },

  focusFirstElement: function(form) {
    form = $(form);
    form.findFirstElement().activate();
    return form;
  },

  request: function(form, options) {
    form = $(form), options = Object.clone(options || { });

    var params = options.parameters, action = form.readAttribute('action') || '';
    if (action.blank()) action = window.location.href;
    options.parameters = form.serialize(true);

    if (params) {
      if (Object.isString(params)) params = params.toQueryParams();
      Object.extend(options.parameters, params);
    }

    if (form.hasAttribute('method') && !options.method)
      options.method = form.method;

    return new Ajax.Request(action, options);
  }
};

/*--------------------------------------------------------------------------*/

Form.Element = {
  focus: function(element) {
    $(element).focus();
    return element;
  },

  select: function(element) {
    $(element).select();
    return element;
  }
};

Form.Element.Methods = {
  serialize: function(element) {
    element = $(element);
    if (!element.disabled && element.name) {
      var value = element.getValue();
      if (value != undefined) {
        var pair = { };
        pair[element.name] = value;
        return Object.toQueryString(pair);
      }
    }
    return '';
  },

  getValue: function(element) {
    element = $(element);
    var method = element.tagName.toLowerCase();
    return Form.Element.Serializers[method](element);
  },

  setValue: function(element, value) {
    element = $(element);
    var method = element.tagName.toLowerCase();
    Form.Element.Serializers[method](element, value);
    return element;
  },

  clear: function(element) {
    $(element).value = '';
    return element;
  },

  present: function(element) {
    return $(element).value != '';
  },

  activate: function(element) {
    element = $(element);
    try {
      element.focus();
      if (element.select && (element.tagName.toLowerCase() != 'input' ||
          !['button', 'reset', 'submit'].include(element.type)))
        element.select();
    } catch (e) { }
    return element;
  },

  disable: function(element) {
    element = $(element);
    element.blur();
    element.disabled = true;
    return element;
  },

  enable: function(element) {
    element = $(element);
    element.disabled = false;
    return element;
  }
};

/*--------------------------------------------------------------------------*/

var Field = Form.Element;
var $F = Form.Element.Methods.getValue;

/*--------------------------------------------------------------------------*/

Form.Element.Serializers = {
  input: function(element, value) {
    switch (element.type.toLowerCase()) {
      case 'checkbox':
      case 'radio':
        return Form.Element.Serializers.inputSelector(element, value);
      default:
        return Form.Element.Serializers.textarea(element, value);
    }
  },

  inputSelector: function(element, value) {
    if (Object.isUndefined(value)) return element.checked ? element.value : null;
    else element.checked = !!value;
  },

  textarea: function(element, value) {
    if (Object.isUndefined(value)) return element.value;
    else element.value = value;
  },

  select: function(element, index) {
    if (Object.isUndefined(index))
      return this[element.type == 'select-one' ?
        'selectOne' : 'selectMany'](element);
    else {
      var opt, value, single = !Object.isArray(index);
      for (var i = 0, length = element.length; i < length; i++) {
        opt = element.options[i];
        value = this.optionValue(opt);
        if (single) {
          if (value == index) {
            opt.selected = true;
            return;
          }
        }
        else opt.selected = index.include(value);
      }
    }
  },

  selectOne: function(element) {
    var index = element.selectedIndex;
    return index >= 0 ? this.optionValue(element.options[index]) : null;
  },

  selectMany: function(element) {
    var values, length = element.length;
    if (!length) return null;

    for (var i = 0, values = []; i < length; i++) {
      var opt = element.options[i];
      if (opt.selected) values.push(this.optionValue(opt));
    }
    return values;
  },

  optionValue: function(opt) {
    // extend element because hasAttribute may not be native
    return Element.extend(opt).hasAttribute('value') ? opt.value : opt.text;
  }
};

/*--------------------------------------------------------------------------*/

Abstract.TimedObserver = Class.create(PeriodicalExecuter, {
  initialize: function($super, element, frequency, callback) {
    $super(callback, frequency);
    this.element   = $(element);
    this.lastValue = this.getValue();
  },

  execute: function() {
    var value = this.getValue();
    if (Object.isString(this.lastValue) && Object.isString(value) ?
        this.lastValue != value : String(this.lastValue) != String(value)) {
      this.callback(this.element, value);
      this.lastValue = value;
    }
  }
});

Form.Element.Observer = Class.create(Abstract.TimedObserver, {
  getValue: function() {
    return Form.Element.getValue(this.element);
  }
});

Form.Observer = Class.create(Abstract.TimedObserver, {
  getValue: function() {
    return Form.serialize(this.element);
  }
});

/*--------------------------------------------------------------------------*/

Abstract.EventObserver = Class.create({
  initialize: function(element, callback) {
    this.element  = $(element);
    this.callback = callback;

    this.lastValue = this.getValue();
    if (this.element.tagName.toLowerCase() == 'form')
      this.registerFormCallbacks();
    else
      this.registerCallback(this.element);
  },

  onElementEvent: function() {
    var value = this.getValue();
    if (this.lastValue != value) {
      this.callback(this.element, value);
      this.lastValue = value;
    }
  },

  registerFormCallbacks: function() {
    Form.getElements(this.element).each(this.registerCallback, this);
  },

  registerCallback: function(element) {
    if (element.type) {
      switch (element.type.toLowerCase()) {
        case 'checkbox':
        case 'radio':
          Event.observe(element, 'click', this.onElementEvent.bind(this));
          break;
        default:
          Event.observe(element, 'change', this.onElementEvent.bind(this));
          break;
      }
    }
  }
});

Form.Element.EventObserver = Class.create(Abstract.EventObserver, {
  getValue: function() {
    return Form.Element.getValue(this.element);
  }
});

Form.EventObserver = Class.create(Abstract.EventObserver, {
  getValue: function() {
    return Form.serialize(this.element);
  }
});
if (!window.Event) var Event = { };

Object.extend(Event, {
  KEY_BACKSPACE: 8,
  KEY_TAB:       9,
  KEY_RETURN:   13,
  KEY_ESC:      27,
  KEY_LEFT:     37,
  KEY_UP:       38,
  KEY_RIGHT:    39,
  KEY_DOWN:     40,
  KEY_DELETE:   46,
  KEY_HOME:     36,
  KEY_END:      35,
  KEY_PAGEUP:   33,
  KEY_PAGEDOWN: 34,
  KEY_INSERT:   45,

  cache: { },

  relatedTarget: function(event) {
    var element;
    switch(event.type) {
      case 'mouseover': element = event.fromElement; break;
      case 'mouseout':  element = event.toElement;   break;
      default: return null;
    }
    return Element.extend(element);
  }
});

Event.Methods = (function() {
  var isButton;

  if (Prototype.Browser.IE) {
    var buttonMap = { 0: 1, 1: 4, 2: 2 };
    isButton = function(event, code) {
      return event.button == buttonMap[code];
    };

  } else if (Prototype.Browser.WebKit) {
    isButton = function(event, code) {
      switch (code) {
        case 0: return event.which == 1 && !event.metaKey;
        case 1: return event.which == 1 && event.metaKey;
        default: return false;
      }
    };

  } else {
    isButton = function(event, code) {
      return event.which ? (event.which === code + 1) : (event.button === code);
    };
  }

  return {
    isLeftClick:   function(event) { return isButton(event, 0) },
    isMiddleClick: function(event) { return isButton(event, 1) },
    isRightClick:  function(event) { return isButton(event, 2) },

    element: function(event) {
      var node = Event.extend(event).target;
      return Element.extend(node.nodeType == Node.TEXT_NODE ? node.parentNode : node);
    },

    findElement: function(event, expression) {
      var element = Event.element(event);
      if (!expression) return element;
      var elements = [element].concat(element.ancestors());
      return Selector.findElement(elements, expression, 0);
    },

    pointer: function(event) {
      return {
        x: event.pageX || (event.clientX +
          (document.documentElement.scrollLeft || document.body.scrollLeft)),
        y: event.pageY || (event.clientY +
          (document.documentElement.scrollTop || document.body.scrollTop))
      };
    },

    pointerX: function(event) { return Event.pointer(event).x },
    pointerY: function(event) { return Event.pointer(event).y },

    stop: function(event) {
      Event.extend(event);
      event.preventDefault();
      event.stopPropagation();
      event.stopped = true;
    }
  };
})();

Event.extend = (function() {
  var methods = Object.keys(Event.Methods).inject({ }, function(m, name) {
    m[name] = Event.Methods[name].methodize();
    return m;
  });

  if (Prototype.Browser.IE) {
    Object.extend(methods, {
      stopPropagation: function() { this.cancelBubble = true },
      preventDefault:  function() { this.returnValue = false },
      inspect: function() { return "[object Event]" }
    });

    return function(event) {
      if (!event) return false;
      if (event._extendedByPrototype) return event;

      event._extendedByPrototype = Prototype.emptyFunction;
      var pointer = Event.pointer(event);
      Object.extend(event, {
        target: event.srcElement,
        relatedTarget: Event.relatedTarget(event),
        pageX:  pointer.x,
        pageY:  pointer.y
      });
      return Object.extend(event, methods);
    };

  } else {
    Event.prototype = Event.prototype || document.createEvent("HTMLEvents").__proto__;
    Object.extend(Event.prototype, methods);
    return Prototype.K;
  }
})();

Object.extend(Event, (function() {
  var cache = Event.cache;

  function getEventID(element) {
    if (element._prototypeEventID) return element._prototypeEventID[0];
    arguments.callee.id = arguments.callee.id || 1;
    return element._prototypeEventID = [++arguments.callee.id];
  }

  function getDOMEventName(eventName) {
    if (eventName && eventName.include(':')) return "dataavailable";
    return eventName;
  }

  function getCacheForID(id) {
    return cache[id] = cache[id] || { };
  }

  function getWrappersForEventName(id, eventName) {
    var c = getCacheForID(id);
    return c[eventName] = c[eventName] || [];
  }

  function createWrapper(element, eventName, handler) {
    var id = getEventID(element);
    var c = getWrappersForEventName(id, eventName);
    if (c.pluck("handler").include(handler)) return false;

    var wrapper = function(event) {
      if (!Event || !Event.extend ||
        (event.eventName && event.eventName != eventName))
          return false;

      Event.extend(event);
      handler.call(element, event);
    };

    wrapper.handler = handler;
    c.push(wrapper);
    return wrapper;
  }

  function findWrapper(id, eventName, handler) {
    var c = getWrappersForEventName(id, eventName);
    return c.find(function(wrapper) { return wrapper.handler == handler });
  }

  function destroyWrapper(id, eventName, handler) {
    var c = getCacheForID(id);
    if (!c[eventName]) return false;
    c[eventName] = c[eventName].without(findWrapper(id, eventName, handler));
  }

  function destroyCache() {
    for (var id in cache)
      for (var eventName in cache[id])
        cache[id][eventName] = null;
  }

  if (window.attachEvent) {
    window.attachEvent("onunload", destroyCache);
  }

  return {
    observe: function(element, eventName, handler) {
      element = $(element);
      var name = getDOMEventName(eventName);

      var wrapper = createWrapper(element, eventName, handler);
      if (!wrapper) return element;

      if (element.addEventListener) {
        element.addEventListener(name, wrapper, false);
      } else {
        element.attachEvent("on" + name, wrapper);
      }

      return element;
    },

    stopObserving: function(element, eventName, handler) {
      element = $(element);
      var id = getEventID(element), name = getDOMEventName(eventName);

      if (!handler && eventName) {
        getWrappersForEventName(id, eventName).each(function(wrapper) {
          element.stopObserving(eventName, wrapper.handler);
        });
        return element;

      } else if (!eventName) {
        Object.keys(getCacheForID(id)).each(function(eventName) {
          element.stopObserving(eventName);
        });
        return element;
      }

      var wrapper = findWrapper(id, eventName, handler);
      if (!wrapper) return element;

      if (element.removeEventListener) {
        element.removeEventListener(name, wrapper, false);
      } else {
        element.detachEvent("on" + name, wrapper);
      }

      destroyWrapper(id, eventName, handler);

      return element;
    },

    fire: function(element, eventName, memo) {
      element = $(element);
      if (element == document && document.createEvent && !element.dispatchEvent)
        element = document.documentElement;

      var event;
      if (document.createEvent) {
        event = document.createEvent("HTMLEvents");
        event.initEvent("dataavailable", true, true);
      } else {
        event = document.createEventObject();
        event.eventType = "ondataavailable";
      }

      event.eventName = eventName;
      event.memo = memo || { };

      if (document.createEvent) {
        element.dispatchEvent(event);
      } else {
        element.fireEvent(event.eventType, event);
      }

      return Event.extend(event);
    }
  };
})());

Object.extend(Event, Event.Methods);

Element.addMethods({
  fire:          Event.fire,
  observe:       Event.observe,
  stopObserving: Event.stopObserving
});

Object.extend(document, {
  fire:          Element.Methods.fire.methodize(),
  observe:       Element.Methods.observe.methodize(),
  stopObserving: Element.Methods.stopObserving.methodize(),
  loaded:        false
});

(function() {
  /* Support for the DOMContentLoaded event is based on work by Dan Webb,
     Matthias Miller, Dean Edwards and John Resig. */

  var timer;

  function fireContentLoadedEvent() {
    if (document.loaded) return;
    if (timer) window.clearInterval(timer);
    document.fire("dom:loaded");
    document.loaded = true;
  }

  if (document.addEventListener) {
    if (Prototype.Browser.WebKit) {
      timer = window.setInterval(function() {
        if (/loaded|complete/.test(document.readyState))
          fireContentLoadedEvent();
      }, 0);

      Event.observe(window, "load", fireContentLoadedEvent);

    } else {
      document.addEventListener("DOMContentLoaded",
        fireContentLoadedEvent, false);
    }

  } else {
    document.write("<script id=__onDOMContentLoaded defer src=//:><\/script>");
    $("__onDOMContentLoaded").onreadystatechange = function() {
      if (this.readyState == "complete") {
        this.onreadystatechange = null;
        fireContentLoadedEvent();
      }
    };
  }
})();
/*------------------------------- DEPRECATED -------------------------------*/

Hash.toQueryString = Object.toQueryString;

var Toggle = { display: Element.toggle };

Element.Methods.childOf = Element.Methods.descendantOf;

var Insertion = {
  Before: function(element, content) {
    return Element.insert(element, {before:content});
  },

  Top: function(element, content) {
    return Element.insert(element, {top:content});
  },

  Bottom: function(element, content) {
    return Element.insert(element, {bottom:content});
  },

  After: function(element, content) {
    return Element.insert(element, {after:content});
  }
};

var $continue = new Error('"throw $continue" is deprecated, use "return" instead');

// This should be moved to script.aculo.us; notice the deprecated methods
// further below, that map to the newer Element methods.
var Position = {
  // set to true if needed, warning: firefox performance problems
  // NOT neeeded for page scrolling, only if draggable contained in
  // scrollable elements
  includeScrollOffsets: false,

  // must be called before calling withinIncludingScrolloffset, every time the
  // page is scrolled
  prepare: function() {
    this.deltaX =  window.pageXOffset
                || document.documentElement.scrollLeft
                || document.body.scrollLeft
                || 0;
    this.deltaY =  window.pageYOffset
                || document.documentElement.scrollTop
                || document.body.scrollTop
                || 0;
  },

  // caches x/y coordinate pair to use with overlap
  within: function(element, x, y) {
    if (this.includeScrollOffsets)
      return this.withinIncludingScrolloffsets(element, x, y);
    this.xcomp = x;
    this.ycomp = y;
    this.offset = Element.cumulativeOffset(element);

    return (y >= this.offset[1] &&
            y <  this.offset[1] + element.offsetHeight &&
            x >= this.offset[0] &&
            x <  this.offset[0] + element.offsetWidth);
  },

  withinIncludingScrolloffsets: function(element, x, y) {
    var offsetcache = Element.cumulativeScrollOffset(element);

    this.xcomp = x + offsetcache[0] - this.deltaX;
    this.ycomp = y + offsetcache[1] - this.deltaY;
    this.offset = Element.cumulativeOffset(element);

    return (this.ycomp >= this.offset[1] &&
            this.ycomp <  this.offset[1] + element.offsetHeight &&
            this.xcomp >= this.offset[0] &&
            this.xcomp <  this.offset[0] + element.offsetWidth);
  },

  // within must be called directly before
  overlap: function(mode, element) {
    if (!mode) return 0;
    if (mode == 'vertical')
      return ((this.offset[1] + element.offsetHeight) - this.ycomp) /
        element.offsetHeight;
    if (mode == 'horizontal')
      return ((this.offset[0] + element.offsetWidth) - this.xcomp) /
        element.offsetWidth;
  },

  // Deprecation layer -- use newer Element methods now (1.5.2).

  cumulativeOffset: Element.Methods.cumulativeOffset,

  positionedOffset: Element.Methods.positionedOffset,

  absolutize: function(element) {
    Position.prepare();
    return Element.absolutize(element);
  },

  relativize: function(element) {
    Position.prepare();
    return Element.relativize(element);
  },

  realOffset: Element.Methods.cumulativeScrollOffset,

  offsetParent: Element.Methods.getOffsetParent,

  page: Element.Methods.viewportOffset,

  clone: function(source, target, options) {
    options = options || { };
    return Element.clonePosition(target, source, options);
  }
};

/*--------------------------------------------------------------------------*/

if (!document.getElementsByClassName) document.getElementsByClassName = function(instanceMethods){
  function iter(name) {
    return name.blank() ? null : "[contains(concat(' ', @class, ' '), ' " + name + " ')]";
  }

  instanceMethods.getElementsByClassName = Prototype.BrowserFeatures.XPath ?
  function(element, className) {
    className = className.toString().strip();
    var cond = /\s/.test(className) ? $w(className).map(iter).join('') : iter(className);
    return cond ? document._getElementsByXPath('.//*' + cond, element) : [];
  } : function(element, className) {
    className = className.toString().strip();
    var elements = [], classNames = (/\s/.test(className) ? $w(className) : null);
    if (!classNames && !className) return elements;

    var nodes = $(element).getElementsByTagName('*');
    className = ' ' + className + ' ';

    for (var i = 0, child, cn; child = nodes[i]; i++) {
      if (child.className && (cn = ' ' + child.className + ' ') && (cn.include(className) ||
          (classNames && classNames.all(function(name) {
            return !name.toString().blank() && cn.include(' ' + name + ' ');
          }))))
        elements.push(Element.extend(child));
    }
    return elements;
  };

  return function(className, parentElement) {
    return $(parentElement || document.body).getElementsByClassName(className);
  };
}(Element.Methods);

/*--------------------------------------------------------------------------*/

Element.ClassNames = Class.create();
Element.ClassNames.prototype = {
  initialize: function(element) {
    this.element = $(element);
  },

  _each: function(iterator) {
    this.element.className.split(/\s+/).select(function(name) {
      return name.length > 0;
    })._each(iterator);
  },

  set: function(className) {
    this.element.className = className;
  },

  add: function(classNameToAdd) {
    if (this.include(classNameToAdd)) return;
    this.set($A(this).concat(classNameToAdd).join(' '));
  },

  remove: function(classNameToRemove) {
    if (!this.include(classNameToRemove)) return;
    this.set($A(this).without(classNameToRemove).join(' '));
  },

  toString: function() {
    return $A(this).join(' ');
  }
};

Object.extend(Element.ClassNames.prototype, Enumerable);

/*--------------------------------------------------------------------------*/

Element.addMethods();
/*
    http://www.JSON2.org/json2.js
    2008-11-19

    Public Domain.

    NO WARRANTY EXPRESSED OR IMPLIED. USE AT YOUR OWN RISK.

    See http://www.JSON2.org/js.html

    This file creates a global JSON2 object containing two methods: stringify
    and parse.

        JSON2.stringify(value, replacer, space)
            value       any JavaScript value, usually an object or array.

            replacer    an optional parameter that determines how object
                        values are stringified for objects. It can be a
                        function or an array of strings.

            space       an optional parameter that specifies the indentation
                        of nested structures. If it is omitted, the text will
                        be packed without extra whitespace. If it is a number,
                        it will specify the number of spaces to indent at each
                        level. If it is a string (such as '\t' or '&nbsp;'),
                        it contains the characters used to indent at each level.

            This method produces a JSON2 text from a JavaScript value.

            When an object value is found, if the object contains a toJSON
            method, its toJSON method will be called and the result will be
            stringified. A toJSON method does not serialize: it returns the
            value represented by the name/value pair that should be serialized,
            or undefined if nothing should be serialized. The toJSON method
            will be passed the key associated with the value, and this will be
            bound to the object holding the key.

            For example, this would serialize Dates as ISO strings.

                Date.prototype.toJSON = function (key) {
                    function f(n) {
                                        // Format integers to have at least two digits.
                        return n < 10 ? '0' + n : n;
                    }

                    return this.getUTCFullYear()   + '-' +
                         f(this.getUTCMonth() + 1) + '-' +
                         f(this.getUTCDate())      + 'T' +
                         f(this.getUTCHours())     + ':' +
                         f(this.getUTCMinutes())   + ':' +
                         f(this.getUTCSeconds())   + 'Z';
                };

            You can provide an optional replacer method. It will be passed the
            key and value of each member, with this bound to the containing
            object. The value that is returned from your method will be
            serialized. If your method returns undefined, then the member will
            be excluded from the serialization.

            If the replacer parameter is an array of strings, then it will be
            used to select the members to be serialized. It filters the results
            such that only members with keys listed in the replacer array are
            stringified.

            Values that do not have JSON2 representations, such as undefined or
            functions, will not be serialized. Such values in objects will be
            dropped; in arrays they will be replaced with null. You can use
            a replacer function to replace those with JSON2 values.
            JSON2.stringify(undefined) returns undefined.

            The optional space parameter produces a stringification of the
            value that is filled with line breaks and indentation to make it
            easier to read.

            If the space parameter is a non-empty string, then that string will
            be used for indentation. If the space parameter is a number, then
            the indentation will be that many spaces.

            Example:

            text = JSON2.stringify(['e', {pluribus: 'unum'}]);
                            // text is '["e",{"pluribus":"unum"}]'


            text = JSON2.stringify(['e', {pluribus: 'unum'}], null, '\t');
                            // text is '[\n\t"e",\n\t{\n\t\t"pluribus":"unum"\n\t}\n]'

            text = JSON2.stringify([new Date()], function (key, value) {
                return this[key] instanceof Date ?
                    'Date(' + this[key] + ')' : value;
            });
                            // text is '["Date(---current time---)"]'


        JSON2.parse(text, reviver)
            This method parses a JSON2 text to produce an object or array.
            It can throw a SyntaxError exception.

            The optional reviver parameter is a function that can filter and
            transform the results. It receives each of the keys and values,
            and its return value is used instead of the original value.
            If it returns what it received, then the structure is not modified.
            If it returns undefined then the member is deleted.

            Example:

                            // Parse the text. Values that look like ISO date strings will
                            // be converted to Date objects.

            myData = JSON2.parse(text, function (key, value) {
                var a;
                if (typeof value === 'string') {
                    a =
/^(\d{4})-(\d{2})-(\d{2})T(\d{2}):(\d{2}):(\d{2}(?:\.\d*)?)Z$/.exec(value);
                    if (a) {
                        return new Date(Date.UTC(+a[1], +a[2] - 1, +a[3], +a[4],
                            +a[5], +a[6]));
                    }
                }
                return value;
            });

            myData = JSON2.parse('["Date(09/09/2001)"]', function (key, value) {
                var d;
                if (typeof value === 'string' &&
                        value.slice(0, 5) === 'Date(' &&
                        value.slice(-1) === ')') {
                    d = new Date(value.slice(5, -1));
                    if (d) {
                        return d;
                    }
                }
                return value;
            });


    This is a reference implementation. You are free to copy, modify, or
    redistribute.

    This code should be minified before deployment.
    See http://javascript.crockford.com/jsmin.html

    USE YOUR OWN COPY. IT IS EXTREMELY UNWISE TO LOAD CODE FROM SERVERS YOU DO
    NOT CONTROL.
*/

/*jslint evil: true */

/*global JSON2 */

/*members "", "\b", "\t", "\n", "\f", "\r", "\"", JSON, "\\", apply,
    call, charCodeAt, getUTCDate, getUTCFullYear, getUTCHours,
    getUTCMinutes, getUTCMonth, getUTCSeconds, hasOwnProperty, join,
    lastIndex, length, parse, prototype, push, replace, slice, stringify,
    test, toJSON, toString, valueOf
*/

                // Create a JSON2 object only if one does not already exist. We create the
                // methods in a closure to avoid creating global variables.

if (!this.JSON2) {
    JSON2 = {};
}
(function () {

    function f(n) {
                        // Format integers to have at least two digits.
        return n < 10 ? '0' + n : n;
    }

    if (typeof Date.prototype.toJSON !== 'function') {

        Date.prototype.toJSON = function (key) {

            return this.getUTCFullYear()   + '-' +
                 f(this.getUTCMonth() + 1) + '-' +
                 f(this.getUTCDate())      + 'T' +
                 f(this.getUTCHours())     + ':' +
                 f(this.getUTCMinutes())   + ':' +
                 f(this.getUTCSeconds())   + 'Z';
        };

        String.prototype.toJSON =
        Number.prototype.toJSON =
        Boolean.prototype.toJSON = function (key) {
            return this.valueOf();
        };
    }
	
     var cx = /[\u0000\u00ad\u0600-\u0604\u070f\u17b4\u17b5\u200c-\u200f\u2028-\u202f\u2060-\u206f\ufeff\ufff0-\uffff]/g,
        escapable = /[\\\"\'\?\\>\<{\}\&\%\#\+\x00-\x1f\x7f-\x9f\u00ad\u0600-\u0604\u070f\u17b4\u17b5\u200c-\u200f\u2028-\u202f\u2060-\u206f\ufeff\ufff0-\uffff]/g,
        gap,
        indent,
        meta = {                    // table of character substitutions
            '\b': '\\b',
            '\t': '\\t',
            '\n': '\\n',
            '\f': '\\f',
            '\r': '\\r',
            '"' : '\\"',
            '\\': '\\\\', // \\\\%5c%5c
			'&' : '%26',
			'#' : '%23',
			'+' : '%7F', // 127 // Cf will undo
			'%' : '%25',
			"'" : '%27',
			"}" : '%7d',
			"{" : '%7b',
			"<" : '%3c',
			"?" : '%3f',
			">" : '%3e'
        },
        rep;
	
	//' //This is for color correction 
	
    function quote(string) {

                // If the string contains no control characters, no quote characters, and no
                // backslash characters, then we can safely slap some quotes around it.
                // Otherwise we must also replace the offending characters with safe escape
                // sequences.

        escapable.lastIndex = 0;
        return escapable.test(string) ?
            '"' + string.replace(escapable, function (a) {
                var c = meta[a];
                return typeof c === 'string' ? c : '\\u' + ('0000' + a.charCodeAt(0).toString(16)).slice(-4);
            }) + '"' :
            '"' + string + '"';
    }


    function str(key, holder) {

                // Produce a string from holder[key].

        var i,                          // The loop counter.
            k,                          // The member key.
            v,                          // The member value.
            length,
            mind = gap,
            partial,
            value = holder[key];

                // If the value has a toJSON method, call it to obtain a replacement value.
        if (value && typeof value === 'object' &&
                typeof value.toJSON === 'function') {
            value = value.toJSON(key);
        }

                // If we were called with a replacer function, then call the replacer to
                // obtain a replacement value.

        if (typeof rep === 'function') {
            value = rep.call(holder, key, value);
        }

                // What happens next depends on the value's type.

        switch (typeof value) {
        case 'string':

            return quote(value);

        case 'number':

                // JSON2 numbers must be finite. Encode non-finite numbers as null.

            return isFinite(value) ? String(value) : 'null';

        case 'boolean':
        case 'null':

                // If the value is a boolean or null, convert it to a string. Note:
                // typeof null does not produce 'null'. The case is included here in
                // the remote chance that this gets fixed someday.

            return String(value);

                // If the type is 'object', we might be dealing with an object or an array or
                // null.

        case 'object':

                // Due to a specification blunder in ECMAScript, typeof null is 'object',
                // so watch out for that case.

            if (!value) {
                return 'null';
            }

                // Make an array to hold the partial results of stringifying this object value.

            gap += indent;
            partial = [];

                // Is the value an array?
		
           if (Object.prototype.toString.apply(value) === '[object Array]') {
                // The value is an array. Stringify every element. Use null as a placeholder
                // for non-JSON2 values.
                length = value.length;
                for (i = 0; i < length; i += 1) {
                    partial[i] = str(i, value) || 'null';
                }

                // Join all of the elements together, separated with commas, and wrap them in
                // brackets.

                v = partial.length === 0 ? '[]' :
                    gap ? '[\n' + gap +
                            partial.join(',\n' + gap) + '\n' +
                                mind + ']' :
                          '[' + partial.join(',') + ']';
                gap = mind;
                return v;
            }

                // If the replacer is an array, use it to select the members to be stringified.
		
            if (rep && typeof rep === 'object') {
                length = rep.length;
                for (i = 0; i < length; i += 1) {
                    k = rep[i];
                    if (typeof k === 'string') {
                        v = str(k, value);
                        if (v) {
                            partial.push(quote(k) + (gap ? ': ' : ':') + v);
                        }
                    }
					
                }
            } else {

                // Otherwise, iterate through all of the keys in the object.

                for (k in value) {
                    if (Object.hasOwnProperty.call(value, k)) {
                        v = str(k, value);
                        if (v) {
                            partial.push(quote(k) + (gap ? ': ' : ':') + v);
                        }
                    }
                }
            }

                // Join all of the member texts together, separated with commas,
                // and wrap them in braces.

            v = partial.length === 0 ? '{}' :
                gap ? '{\n' + gap + partial.join(',\n' + gap) + '\n' +
                        mind + '}' : '{' + partial.join(',') + '}';
            gap = mind;
			

            return v;
        }
    }

                // If the JSON2 object does not yet have a stringify method, give it one.

    if (typeof JSON2.stringify !== 'function') {
        JSON2.stringify = function (value, replacer, space) {

                // The stringify method takes a value and an optional replacer, and an optional
                // space parameter, and returns a JSON2 text. The replacer can be a function
                // that can replace values, or an array of strings that will select the keys.
                // A default replacer method can be provided. Use of the space parameter can
                // produce text that is more easily readable.
            var i;
            gap = '';
            indent = '';

                // If the space parameter is a number, make an indent string containing that
                // many spaces.

            if (typeof space === 'number') {
                for (i = 0; i < space; i += 1) {
                    indent += ' ';
                }

                // If the space parameter is a string, it will be used as the indent string.

            } else if (typeof space === 'string') {
                indent = space;
            }

                // If there is a replacer, it must be a function or an array.
                // Otherwise, throw an error.

            rep = replacer;
            if (replacer && typeof replacer !== 'function' &&
                    (typeof replacer !== 'object' ||
                     typeof replacer.length !== 'number')) {
                throw new Error('JSON2.stringify');
            }

                // Make a fake root object containing our value under the key of ''.
                // Return the result of stringifying the value.
            return str('', {'': value});
        };
    }


                // If the JSON2 object does not yet have a parse method, give it one.

    if (typeof JSON2.parse !== 'function') {
        JSON2.parse = function (text, reviver) {

                // The parse method takes a text and an optional reviver function, and returns
                // a JavaScript value if the text is a valid JSON2 text.

            var j;

            function walk(holder, key) {

                // The walk method is used to recursively walk the resulting structure so
                // that modifications can be made.

                var k, v, value = holder[key];
                if (value && typeof value === 'object') {
                    for (k in value) {
                        if (Object.hasOwnProperty.call(value, k)) {
                            v = walk(value, k);
                            if (v !== undefined) {
                                value[k] = v;
                            } else {
                                delete value[k];
                            }
                        }
                    }
                }
                return reviver.call(holder, key, value);
            }


                // Parsing happens in four stages. In the first stage, we replace certain
                // Unicode characters with escape sequences. JavaScript handles many characters
                // incorrectly, either silently deleting them, or treating them as line endings.

            cx.lastIndex = 0;
            if (cx.test(text)) {
                text = text.replace(cx, function (a) {
                    return '\\u' +
                        ('0000' + a.charCodeAt(0).toString(16)).slice(-4);
                });
            }

                // In the second stage, we run the text against regular expressions that look
                // for non-JSON2 patterns. We are especially concerned with '()' and 'new'
                // because they can cause invocation, and '=' because it can cause mutation.
                // But just to be safe, we want to reject all unexpected forms.

                // We split the second stage into 4 regexp operations in order to work around
                // crippling inefficiencies in IE's and Safari's regexp engines. First we
                // replace the JSON2 backslash pairs with '@' (a non-JSON2 character). Second, we
                // replace all simple value tokens with ']' characters. Third, we delete all
                // open brackets that follow a colon or comma or that begin the text. Finally,
                // we look to see that the remaining characters are only whitespace or ']' or
                // ',' or ':' or '{' or '}'. If that is so, then the text is safe for eval.

            if (/^[\],:{}\s]*$/.
test(text.replace(/\\(?:["\\\/bfnrt]|u[0-9a-fA-F]{4})/g, '@').
replace(/"[^"\\\n\r]*"|true|false|null|-?\d+(?:\.\d*)?(?:[eE][+\-]?\d+)?/g, ']').
replace(/(?:^|:|,)(?:\s*\[)+/g, ''))) {

                // In the third stage we use the eval function to compile the text into a
                // JavaScript structure. The '{' operator is subject to a syntactic ambiguity
                // in JavaScript: it can begin a block or an object literal. We wrap the text
                // in parens to eliminate the ambiguity.

                j = eval('(' + text + ')');

                // In the optional fourth stage, we recursively walk the new structure, passing
                // each name/value pair to a reviver function for possible transformation.

                return typeof reviver === 'function' ?
                    walk({'': j}, '') : j;
            }

                // If the text is not JSON2 parseable, then a SyntaxError is thrown.

            throw new SyntaxError('JSON2.parse');
        };
    }
})();


	//
	//	Global IFrame Resize Code
	//
	
		//
		//	Input the IDs of the IFRAMES you wish to dynamically resize to match its content height:
		//	Separate each ID with a comma. Examples: ["myframe1", "myframe2"] or ["myframe"] or [] for none:
		//
		var iframeids=["WinBody"]
		
		//Should script hide iframe from browsers that don't support this script (non IE5+/NS6+ browsers. Recommended):
		var iframehide="no"
		
		//	Set this onload of Iframe if display is cut off bottom - ERA
		var iFrameExtra=0;
	

	//
	//	Global Flash Vars :: Defined by Adobe
	//
	var getFFVersion=navigator.userAgent.substring(navigator.userAgent.indexOf("Firefox")).split("/")[1]
	var FFextraHeight=parseFloat(getFFVersion)>=0.1? 16 : 0 //extra height in px to add to iframe in FireFox 1.0+ browsers


	//
	//	Used for highlight functions
	//
	var HL = new Object;
	
	
	//
	//	Global Use for Mouse Positions
	//
	var GetMouseX = 0;
	var GetMouseY = 0;
		
	//
	//	Global for GalaxyNet Menus
	//
	GN_Menu 	 = new Object();		
	GN_Menu.Page = new Object();
	

	//
	//	Global  Used by Drag Drop Functions
	//
	var mouseover = true; 
	var DragDropObject;
	
	
	//
	//	Browser Check
	//
	var isIE 		= false;
	var isOpera 	= false;
	var isFirefox 	= false;
	var isChrome 	= false;
	var isSafari 	= false;
		
	DetectBrowserType = function() {
	
		isIE 		= (navigator.userAgent.indexOf("MSIE") != -1) ? true : false;
		isOpera 	= (navigator.userAgent.indexOf("Opera") != -1) ? true : false;
		isChrome 	= (navigator.userAgent.indexOf("Chrome") != -1) ? true : false;
		if (!isChrome) {
			isSafari 	= (navigator.userAgent.indexOf("Apple") != -1) ? true : false;
			if (!isSafari && !isOpera && !isIE) {
				isFirefox =	true;
			}
		} 
		
	}	
	
	DetectBrowserType();
	
	
	//
	//	Get Object Value from an ID
	//
	function GetID(ObjStr, DefaultValue, Parent) {
		
		if (typeof(ObjStr) == 'object') {
			return 	ObjStr;
		}
		
		try {
			if (Parent != undefined) {
				Obj = Parent.document.getElementById(ObjStr);
			} else {
				Obj = document.getElementById(ObjStr);
			}
			if (Obj == null) {
				try {
					Obj = eval(ObjStr)
					
					if (Obj == null) {
						Obj = undefined;
					}
				} catch(e) {
					Obj = undefined;
				}
			}
			return Obj
		} catch(e) {
			
			try {
				return eval(ObjStr)
				if (Obj == null) {
					return DefaultValue;
				}
			
			} catch(e) {
				return DefaultValue;
			}
		}
	}


	//
	//	SafeSize Make value 0 if non zeroor neg
	//
	function SafeSize(IntValue) {
		
		if (parseInt(IntValue) < 0) {
			IntValue = 0;
		}
		
		return IntValue;
		
	}


	//
	//	Get Object Value from an ID
	//
	function IfVarExists(ObjStr) {
		
		try {
			var t = document.getElementById(ObjStr);
			return true;
		} catch(e) {
			return false;
		}
	}
	
		
	
	//
	//
	//
	var LastWaitDiv;
	var LastModalDiv;
	

	//
	//	Get Object Value from an ID
	//
	function GetNode(ParentObject, ObjStr) {
		
		return ParentObject.getAttributeNode(ObjStr);
		
	}

	


	function LTrim(s) {
		try {
	        return s.replace( /^\s*/, "" );
		} catch(e) {
			return s;
		}
    }

    function RTrim(s) {
		try {
	        return s.replace( /\s*$/, "" );
		} catch(e) {
			return s;
		}
    }

    function Trim(s){
        return RTrim(LTrim(s));
    }

	
	
	//_____________________________________________________________________________
	//
	//  GET TOKEN: Get a value in a delimited str
	//
	function GetToken(Str, Position, FindStr) {

		var	u 	= 0;
		var c   = 0;
		var s   = 0;
		var e   = 0;
		
		Str 	= String(Str);
		FindStr = String(FindStr);
		
		for (var t=0;t<Str.length;t++) {
			c++;
			u = Str.indexOf(FindStr, u + 1);
			if (u == -1) {	// EOL
				e = Str.length - u;
				if (c < Position) {
					Str = '';
					break;
				}
			} else {
				e = u - s;
			}
		
			if (c == Position) {
				Str  = Str.substr(s, e);
				break;
			}
			s = u + 1;
		}
		
		
		return String(Str);
	}
	
	
	//_____________________________________________________________________________
	//
	//	Return the Number Of Items in a String Listy
	//
	function ListLen(Str, DelStr) {
		if (Str==undefined) {
			return -1;
		}
		var c = Str.split(DelStr);
		return c.length;
	}


	
	function WriteHTML(WindowName, HTML) {
	
		GetID(WindowName).innerHTML = HTML;
	}
	
	
	//
	//
	//
	function LoadFlashMovieStr(WindowName, SWFFile, Width, Height, Version, Secure, SWFName, Transparent) {

		if (Width == undefined) {
			Width = '100%';
		}
		if (Height == undefined) {
			Height = '100%';
		}

		if (Version == undefined) {
			Version = '10';
		}
		
		if (Secure == undefined) {
			Secure = 's';
		}
		
		if (SWFName == undefined) {
			SWFName = 'ABC';
		}
		
		if (Transparent == undefined) {
			Transparent = 'transparent'
		}
		
		var Str = '<object classid="clsid:D27CDB6E-AE6D-11cf-96B8-444553540000" codebase="http' + Secure + '://download.macromedia.com/pub/shockwave/cabs/flash/swflash.cab#version=' + Version + '"';
			Str = Str + '	width="' + Width + '" height="' + Height + '" id="' + SWFName + '">';
			Str = Str + '	<param name="movie" value="' + SWFFile + '">';
			Str = Str + '	<param name="quality" value="high">';
			Str = Str + '	<param name="wmode" value="' + Transparent + '">';
			Str = Str + '	<embed ';
			Str = Str + '		src="' + SWFFile + '" ';
			Str = Str + '		quality="high" ';
			Str = Str + '		pluginspage="http' + Secure + '://www.macromedia.com/go/getflashplayer" ';
			Str = Str + '		type="application/x-shockwave-flash" ';
			Str = Str + '		width="' + Width + '" ';
			Str = Str + '		height="' + Height + '"';
			Str = Str + '		wmode="' + Transparent + '">';
			Str = Str + '	</embed>';
			Str = Str + '</object>';
		
		return Str;

	}
	
	//
	//
	//
	function LoadFlashMovie(WindowName, SWFFile, Width, Height, Version, Secure, SWFName,Transparent) {

		WriteHTML(WindowName, LoadFlashMovieStr(WindowName, SWFFile, Width, Height, Version, Secure, SWFName,Transparent));
		
	}

	//
	//
	//
	function LoadPDFStr(PDFile, Width, Height, ID) {
		var Str = '<object classid="clsid:CA8A9780-280D-11CF-A24D-444553540000" width="' + Width + '" height="' + Height + '" id="' + ID +'" >';
			Str = Str + '	<param name="SRC" value="' + PDFile + '">';
			Str = Str + '	<embed  ';
			Str = Str + '		id="' + ID + '" ';
			Str = Str + '		src="' + PDFile + '" ';
			Str = Str + '		width="' + Width + '" ';
			Str = Str + '		height="' + Height + '"';
			Str = Str + '		 >';
			Str = Str + '	</embed>';
			Str = Str + '</object>';
		
		return Str;
	}
	
	
		
	//
	//
	//
	function LoadPDF(WindowName, PDFile, Width, Height, ID) {
		WriteHTML(WindowName, LoadPDFStr(PDFile, Width, Height, ID));
	}


	//
	//
	//
	function LoadXLS(WindowName, File, Width, Height) {
		CreateIFrame(WindowName, 'Excel', File);
		//WriteHTML(WindowName, LoadXLSStr(File, Width, Height));
	}


	//
	//
	//
	function LoadDOC(WindowName, File, Width, Height) {
		CreateIFrame(WindowName, 'Doc', File);
		//WriteHTML(WindowName, LoadXLSStr(File, Width, Height));
	}


	//
	//	Create an HTML Element and Fetch a URL
	//
	function GetHTTPNewWindow(Owner, ElementID, ElementType, Style, HTTP, LoadingMSG ) {
		GetHTTP(CreateElement(Owner, ElementID, ElementType, Style), HTTP, LoadingMSG);
	}
	

	//
	//	Fetch a URL and Insert Content into Window Name
	//	If WindowName = '' Just Return Content
	//
	function GetHTTP(WindowName, HTTP, LoadingMSG, onComplete, Append) {

		var xmlhttp;

		if (!xmlhttp && typeof XMLHttpRequest != 'undefined') {
			try {
				xmlhttp = new XMLHttpRequest();
			}	 
			catch (e) {
				alert("Your browser is not supporting XMLHTTPRequest");
				return false;
			}
		} else {
			xmlhttp = (window.XMLHttpRequest)? new XMLHttpRequest(): new ActiveXObject("Microsoft.XMLHTTP");
				//new ActiveXObject("Microsoft.XMLHTTP");
		}
	

		var request = xmlhttp;
		request.open("GET", HTTP); 
		
		request.onreadystatechange = function() {

			if(request.readyState == 1) {
				if (!Append) {
					if (LoadingMSG == undefined) {
						WindowName.innerHTML = 'Loading...';
					} else {
						WindowName.innerHTML = LoadingMSG;
					}
				}
			}
			if(request.readyState == 4) {
				if (request.status == 200) { 

					if (WindowName!='') {
						if (Append==true) {
							AppendHTML(WindowName, request.responseText);
						} else {
							WriteHTML(WindowName, request.responseText);
						}
					}

					if (onComplete!=undefined) {
						onComplete(request.responseText);
					} 
					
					request = undefined;
					
					//} else {
					///	var ret = request.status;
					//	request = undefined
					//	return ret;
					//}
				} else {
					alert('Background Load Error: ' + HTTP + ' [ ' + request.status +' ]');
				}
				request = undefined;
			}
			
		} 
		
		request.send(null); 
	}
	
	//
	//
	//
	CloneObject = function(what) {
		for (i in what) {
			this[i] = what[i];
		}
	}

	
	//
	//	Design to Support new way and old way
	//	-- For the New Way Pass Just An Object :: The Old Way Will Pass All Parameters	
	//
	GetHTTPAJAX = function(Parameters, HTTP, OnSuccess, Message, PostText) {
		
		
		if (Parameters==undefined) {
			alert('Developer: Your WindowName ID Object (' + String(Parameters)+ ') has not been Defined :: ' + 
				  window.location.hostname + window.location.pathname + window.location.search + ' :: Trying to call ' + HTTP);
			return false;
		}
		
		
		
		if (HTTP == undefined) { 

			Parameters.Fetch  = false;
			Parameters.URL	  = Parameters.HTTP;
			HG_AJAX(Parameters);
		} else {
		
			var	Parameter 				= {}
				Parameter.Container		= Parameters;
				Parameter.URL			= HTTP;
				Parameter.OnSuccess		= OnSuccess;
				Parameter.Message		= Message;
				Parameter.PostText		= PostText;
				Parameter.Fetch			= false;
			HG_AJAX(Parameter);
		}
		
		
		return;
		
		
		//	Create Object if Parameters Used
		if (HTTP != undefined) { 
			var WindowName 			= Parameters;
			Parameters 				= new Object();
			Parameters.Container	= WindowName;
			Parameters.HTTP			= HTTP;
			Parameters.OnSuccess	= OnSuccess;
			Parameters.Message		= Message;
			Parameters.PostText		= PostText;
			Parameters.Left			= 0;
			Parameters.Top			= 0;
		}
		
	
		if (Parameters.Message=='') {
			var myElement = '';
		} else {
			if (typeof(Parameters.Message) != 'string' && eval(Parameters.Message) == undefined) {
				Parameters.Message = 'Loading...';
			}
			var myElement = document.createElement('div');
			
			if (Parameters.Container == '') {
				Parameters.Container = myElement;
				var a = myElement;
				document.body.appendChild(myElement);
			} else {
				Parameters.Container = GetID(Parameters.Container);
				var a = Parameters.Container.insertBefore(myElement, Parameters.Container.firstChild); 
			}

 			
			a.innerHTML = '<div style="position:absolute; z-index:1000;">' + Parameters.Message + '</div>' +
						  '<div class="AJAXPleaseWait" style="position:absolute; background-color:FFFFFF; z-index:999; width:' + Parameters.Container.offsetWidth + 
						  'px; height:' + Parameters.Container.offsetHeight + 'px;" '+
						  'onclick="return false";>&nbsp;</div>';
		}
		
		
		Parameters.OnFailure = function (request) {
			try {
				document.body.removeChild(myElement);
			} catch(e){};
			alert('Background Load Error: ID > ' + Parameters.Container.id + '\n' + HTTP + ' \n[ ' + request.status +' ]');
		}

		
		Parameters.DoOnSuccess = function() {
			try {
				document.body.removeChild(myElement);
			} catch(e){};
			if (Parameters.OnSuccess != undefined) {
				Parameters.OnSuccess();
			}
		}
		
		
		var me = 'get';
		var ct = undefined;
		
		if (Parameters.PostText != undefined) {
			me = 'post';
			ct = 'application/x-www-form-urlencoded';
		}
		
		//
		//  Forces NO Caching
		//
		if (Parameters.HTTP.indexOf('?') > -1) {
			Parameters.HTTP += '&' + String(new Date());
		 } else {
			Parameters.HTTP += '?' + String(new Date());
		 }
		 
		 
		if (Parameters.OnSuccess != undefined) {
			new Ajax.Updater(Parameters.Container, 
							 Parameters.HTTP, 
							 {asynchronous	: true, 
							  evalScripts	: true, 
						   	  method		: me, 
							  onFailure		: Parameters.OnFailure, 
							  onComplete	: Parameters.DoOnSuccess, 
							  parameters	: Parameters.PostText, 
							  contentType	: ct
							 });
		} else {
			new Ajax.Updater(Parameters.Container, 
							 Parameters.HTTP, 
							 {asynchronous	: true, 
							  evalScripts	: true, 
						   	  method		: me, 
							  onFailure		: Parameters.OnFailure, 
							  parameters	: Parameters.PostText, 
							  contentType	: ct
							 });
		}
		
	}
	
	//
	//
	//
	function GetHTTPAJAXNewWindow(Owner, ElementID, ElementType, Style, HTTP, onAJaxSuccess, LoadingMSG) {
		
		GetHTTPAJAX(CreateElement(Owner, ElementID, ElementType, Style), HTTP, onAJaxSuccess, LoadingMSG);
		
	}

	
	
	//
	//
	//
	function ToggleDisplay(ObjID, Set) {
			
		if (typeof(ObjID) == 'string') {
			ObjID = GetID(ObjID);	
		}
		
		if (ObjID.style.display.toUpperCase() == 'NONE') {
			var NSet = '';
		} else {
			var NSet = 'none';
		}
		
		if (Set == undefined) {
			Set = NSet;	
		}
											
		ObjID.style.display = Set;
	}

	
	//
	//
	//
	function GetObject(Name) {
		return document.all? document.all[Name] : document.getElementById(Name);
	}

	//
	//	New Window
	//
	function NewWindow(Url, WindowName, w, h, WindowParams) {
		
		if (WindowParams==undefined) {
			WindowParams = 'resizable=1,menubar=0,scrollbars=1,toolbar=0';
		}
		
		cal = window.open(Url, WindowName, WindowParams);
		
		//cal.window.resizeTo(parent.document.body.clientWidth - 10, parent.document.body.clientHeight - 10);
		if (w!=undefined && h!= undefined) {
			cal.window.resizeTo(w, h);
		}
		
		cal.window.focus();
		
		if (cal != null) {
			if (cal.opener == null) {
				cal.opener = self;
			}
		}
		
		//cal.window.moveTo((cal.window.screen.availWidth / 2) - (cal.document.body.clientWidth / 2), (cal.window.screen.availHeight / 2) - (cal.document.body.clientHeight / 2));
	}
	
	//
	//	Resize Window - SELF
	//
	function ResizeThisWindow(w, h) {
		
		if (w.indexOf('%') > 0) {
			w = GetToken(w, 1, '%') * 0.01;
			w = self.window.screen.availWidth * w;
		}
		
		if (h.indexOf('%') > 0) {
			h = GetToken(h, 1, '%') * 0.01;
			h = self.window.screen.availHeight * h;
		}
		
		
		
		self.window.resizeTo(w, h);
		self.window.moveTo((self.window.screen.availWidth / 2) - (w / 2), (self.window.screen.availHeight / 2) - (h / 2));
		 
	}

	
	
	//
	// Retrive a specific URL parameter
	// else return all URL parameters
	//
	function GetURLParameterVal(param) {
		
		var val 	= "";
		var qs 		= window.location.search;
		var start 	= qs.indexOf(param);
		
		if (start != -1) {
			
			start += param.length + 1;
			var end = qs.indexOf("&", start);
			
			if (end == -1) {
				end = qs.length
			}
			val = qs.substring(start,end);
			
		}
		
		//alert(val);
		return val;
	}
	
	
	//
	// Retrive a specific COOKIE parameter
	// else return all COOKIE parameters
	//
	function GetCookieParameterVal(param) {
	
		var val = "";
		var qs = document.cookie;
		var start = qs.indexOf(param);
		
		if (start != -1) {
			
			start += param.length + 1;
			var end = qs.indexOf(";", start);
			if (end == -1) {
				end = qs.length
			}
			
			val = qs.substring(start,end);
		}
		
		//alert(val);
		return unescape(val);
	}
	

	
	//
	// This will check the size of the window and return
	// the width and height in a comma delimited value
	// which can then either be used with an Array or
	// GetToken(Str, POS, FindStr) which in this case is
	// GetToken(val, 1, ",") for width or
	// GetToken(val, 2, ",") for height
	//
	function GetWindowSize() {

		var myWidth = 0, myHeight = 0, val = '';
		if ( typeof( window.innerWidth ) == 'number' ) {
			//Non-IE
			myWidth = window.innerWidth;
			myHeight = window.innerHeight;
		} else if ( document.documentElement && ( document.documentElement.clientWidth || document.documentElement.clientHeight ) ) {
			//IE 6+ in 'standards compliant mode'
			myWidth = document.documentElement.clientWidth;
			myHeight = document.documentElement.clientHeight;
		} else if ( document.body && ( document.body.clientWidth || document.body.clientHeight ) ) {
			//IE 4 compatible
			myWidth = document.body.clientWidth;
			myHeight = document.body.clientHeight;
		}
		
		val = myWidth + "," + myHeight;
		return unescape(val);
	}
	


	function GetWindowHeight() {

		var myWidth = 0, myHeight = 0, val = '';
		if ( typeof( window.innerWidth ) == 'number' ) {
			//Non-IE
			myWidth = window.innerWidth;
			myHeight = window.innerHeight;
		} else if ( document.documentElement && ( document.documentElement.clientWidth || document.documentElement.clientHeight ) ) {
			//IE 6+ in 'standards compliant mode'
			myWidth = document.documentElement.clientWidth;
			myHeight = document.documentElement.clientHeight;
		} else if ( document.body && ( document.body.clientWidth || document.body.clientHeight ) ) {
			//IE 4 compatible
			myWidth = document.body.clientWidth;
			myHeight = document.body.clientHeight;
		}
		
		return unescape(myHeight);
	}

	function GetWindowWidth() {
		var myWidth = 0, myHeight = 0, val = '';
		if ( typeof( window.innerWidth ) == 'number' ) {
			//Non-IE
			myWidth = window.innerWidth;
			myHeight = window.innerHeight;
		} else if ( document.documentElement && ( document.documentElement.clientWidth || document.documentElement.clientHeight ) ) {
			//IE 6+ in 'standards compliant mode'
			myWidth = document.documentElement.clientWidth;
			myHeight = document.documentElement.clientHeight;
		} else if ( document.body && ( document.body.clientWidth || document.body.clientHeight ) ) {
			//IE 4 compatible
			myWidth = document.body.clientWidth;
			myHeight = document.body.clientHeight;
		}
		
		return unescape(myWidth);
	}
	
	
	function GetObjectHeight(Obj, OrHeight) {

	if (Obj.style.height!=undefined) {
			
			return Obj.style.height
			
		} else {
		
			return OrHeight;
			
		}
	}

	function GetObjectWidth(Obj, OrWidth) {
		
		if (Obj.style.width!=undefined) {
			
			return Obj.style.width
			
		} else {
		
			return OrWidth;
			
		}


	}
	

	

	
	//=====================================
	// REPLACE STR: Replace Str function
	//=====================================
	function ReplaceStr(Str, FindStr, ReStr) {

		if (Str == undefined) {
			return '';	
		}
		
		Str = String(Str);
		var UStr = String(Str).toUpperCase();
		var u = 0;
		
		FindStr = String(FindStr).toUpperCase();
		ReStr	= String(ReStr);
	
		u = 0;
		for (var t=0;t<Str.length;t++) {
			
			if (u==0) {
				u = UStr.indexOf(FindStr);
			} else {
				u = UStr.indexOf(FindStr, u - FindStr.length);
			}
			if (u == -1) {
				break;
			}
			UStr = UStr.substr(0, u) + ReStr + UStr.substr(u + FindStr.length, UStr.length);
			Str = Str.substr(0, u) + ReStr + Str.substr(u + FindStr.length, Str.length);
			t += ReStr.length;
		}
		return String(Str);
	}
	
	//===================================
	// This will encode or unencode HTML
	//===================================
	function EUhtml(type, str) {
		if (type == 'E') {
			return escape(str);
		}
		if (type == 'U') {
			return unescape(str);
		}
	}
	
	
	
	//
	//	Target Content
	//	Takes innerHTML Content from one ID to Another ID Tag
	//
	function TargetContent(FromID, ToID, Method) {
		var Str;

		Str = FromID.innerHTML;
		
		if (Method.toUpperCase()==undefined) {
			Method = "APPEND";
		}
		
		if (Method.toUpperCase()=="OVERWRITE") {
			FromID.innerHTML = '';
			try {
				FromID.style.display = 'none';
			} catch(e) {}
			ToID.innerHTML 	 = Str;
		}
		
		if (Method.toUpperCase()=="MOVE") {
			FromID.innerHTML = '';
			ToID.innerHTML 	 = Str;
		}
		
		if (Method.toUpperCase()=="OVERWRITEONLY") {
			ToID.innerHTML 	 = Str;
		}
		
		if (Method.toUpperCase()=="APPEND") {
			FromID.outerHTML = '';
			try {
				FromID.style.display = 'none';
			} catch(e) {}
			ToID.innerHTML 	 = ToID.innerHTML + Str;
		}
		
		if (Method.toUpperCase()=="APPENDOUT") {
			Str = FromID.outerHTML;
			FromID.outerHTML = '';
			try {
				FromID.style.display = 'none';
			} catch(e) {}
			ToID.innerHTML 	 = ToID.innerHTML + Str;
		}
		if (Method.toUpperCase()=="APPENDONLY") {
			ToID.innerHTML 	 = ToID.innerHTML + Str;
		}
		

	}
	
	
	

	function StripCharacter(words,character) {
		//documentation for this script at http://www.shawnolson.net/a/499/
		var spaces = words.length;
		for(var x = 1; x<spaces; ++x){
			words = words.replace(character, "");   
		}
		return words;
	}
	
	

	function ChangeClassValue(theClass,element,value) {
		var cssRules;
		
		if (document.all) {
			cssRules = 'rules';
		} else if (document.getElementById) {
			cssRules = 'cssRules';
		}
		for (var S = 0; S < document.styleSheets.length; S++){
			for (var R = 0; R < document.styleSheets[S][cssRules].length; R++) {
				if (document.styleSheets[S][cssRules][R].selectorText == theClass) {
					document.styleSheets[S][cssRules][R].style[element] = value;
				}
			}
		}	
	}



	function CheckUncheckAll(theElement) {
		var theForm = theElement.form, z = 0;
			for(z=0; z<the.length;z++){
				if(theForm[z].type == 'checkbox' && theForm[z].name != 'checkall') {
					theForm[z].checked = theElement.checked;
				}
			}
	}
	
	
	
	function checkUncheckSome(controller,theElements) {
	
		// theElements is an array of objects designated as a comma separated list of their IDs
		// If an element in theElements is not a checkbox, then it is assumed
		// that the function is recursive for that object and will check/uncheck
		// all checkboxes contained in that element
		
		
		var formElements = theElements.split(',');
		var theController = document.getElementById(controller);
		
		for(var z=0; z<formElements.length;z++){
			theItem = document.getElementById(formElements[z]);
			if(theItem){
				
				if(theItem.type){
					if(theItem.type == 'checkbox' && theItem.id != theController.id){
						theItem.checked = theController.checked;
					}
				} else {
					
					var nextArray = '';
					
					for(var x=0;x <theItem.childNodes.length;x++){
						if(theItem.childNodes[x]){
							if (theItem.childNodes[x].id){
						  		nextArray += theItem.childNodes[x].id+',';
							}
					  	}
					 }
					 
					 checkUncheckSome(controller,nextArray);
				}
			}
		}
	}

	
	
			
	//
	//
	//	
	function GetMouseCoords(e)	{
		
		 if (!e) e = window.event; // works on IE, but not NS (we rely on NS passing us the event)

		  if (e)
		  { 
			if (e.pageX || e.pageY)
			{ // this doesn't work on IE6!! (works on FF,Moz,Opera7)
			  GetMouseX = e.pageX;
			  GetMouseY = e.pageY;
			  algor = '[e.pageX]';
			
			  if (e.clientX || e.clientY) algor += ' [e.clientX] '
			}
			else if (e.clientX || e.clientY)
			{ // works on IE6,FF,Moz,Opera7
			  GetMouseX = e.clientX + document.body.scrollLeft;
			  GetMouseY = e.clientY + document.body.scrollTop;
			  algor = '[e.clientX]';
			  if (e.pageX || e.pageY) algor += ' [e.pageX] '
			}  
		  }

	}
	
	
	//
	//
	//
	MoveObjectToMouse = function(DivObj, BottomOffSet) {
			
		xHeightVal 			= GetWindowHeight();
		xDiffVal   			= xHeightVal - GetMouseY;
		DivObj.style.left	= GetMouseX;
		
		if (BottomOffSet==undefined) {
			BottomOffSet = 100;
		}
		
		if (xDiffVal <= BottomOffSet) {
			// This will move the popup div from disappearing off the page
			// The popup will appear above the mouse
			DivObj.style.top				= GetMouseY - BottomOffSet;
			
		} else {
			// The popup will appear below the mouse
			DivObj.style.top				= GetMouseY;
			
		}
		
	
	}
	
	
	
	
	
	
	
	DumpObject = function(Obj) {
		
		if (typeof(Obj) == 'string') {
			alert(Obj);
			return;
		}
		
		var gg = '';
		for (var i in Obj) {
			gg = gg + String(i) + ' | ';
		}
		alert(gg);
		
		return gg;
	}
	
	
	DumpObjectValue = function(Obj, HTML, ExcludeNull, ExcludeObject, ObjectsOnly, IncludeFunction) {
		var gg = '';

		for (var i in Obj) {
			var Show = true;
			try {
				if (eval('Obj.' + i)!='') {
				
					if (ExcludeNull!=undefined &&  eval('Obj.' + i) == null) {
						Show = false;
					}
					if (ExcludeObject!=undefined && typeof(eval('Obj.' + i)) == 'object') {
						Show = false;
					}
					if (HTML!=undefined && String(i) == 'innerHTML') {
						Show = false;
					}
					if (HTML!=undefined && String(i) == 'outerHTML') {
						Show = false;
					}
				
					if (ObjectsOnly==true && typeof(eval('Obj.' + i)) != 'object') {
						Show = false;
					}
					if (typeof(eval('Obj.' + i)) == 'function') {
						Show = IncludeFunction;
					}
					
					if (Show==true) {
						gg = gg + String(i) + '=' + eval('Obj.' + i) + ' | ';
					}
				} 
			} catch(e) {}
		}
		alert(gg);
		
		return gg;
	}
	
	
	_DumpCount     = 0;
	_DumpSameCount = 0;
	_MaxDump	   = 1000;
	_DumpLevel	   = 0;
	_DumpLevelMax  = 0;
	_LastDumpObj   = null;
	Dump = function(Obj, Alert, Target, cr, level, Sub, LastName) {

		if (Obj == _LastDumpObj) return '';

		_LastDumpObj = Obj;
		
		var gg = '\n';

		if (cr == undefined) {
			cr = '\n'; 
		}

		if (level == undefined) {
			level = ''; 
		} else {
			level += _DumpLevel + ' ';
		}
		
		_DumpLevel++;
			
		if (_DumpLevel > _DumpLevelMax) {
			_DumpLevelMax = _DumpLevel;
		}
		
		
		if (typeof(Obj) == 'string') {
			alert(Obj);
			return;
		} else {
		
			if (_DumpCount > _MaxDump) {
				_DumpLevel--;
				return '';
			}
			
			var count   = 0;
			var brCount = 0;
			var FirstValue = false;
			var Funcs = '';
			for (var i in Obj) {
				count ++;
				if (count>50) break;
				_DumpCount++;
				if (typeof(Obj[i]) != 'function') {
					if ((typeof(Obj[i]) == 'object' || typeof(Obj[i]) == 'array')
						&& i != 'parentNode' 
						&& i.indexOf('Sibling') == -1 
						&& i.indexOf('Child') == -1 
						&& i.indexOf('Nodes') == -1
						&& i.indexOf('owner') == -1
						) {
						
							if (gg.substring(gg.length-2, 2) != '\n') {
								gg = gg +  '\n';
							}
							gg = gg +  '[' + Trim(level) + ']   ' + String(i) + ': ' + typeof(Obj[i]);
												
							var NextLevel = Dump(Obj[i], undefined, Target, cr, level, 1, i);
							
							gg = gg + NextLevel;
							FirstValue = false;
							
						} else {
							
							if (!FirstValue || Target != undefined) {
								if (Target != undefined) {
									gg += '\n';
								} 
								gg = gg + '[' + Trim(level) + ']   ';

								FirstValue = true;
							}
								
							if (Obj[i] != '' || Number(Obj[i]) == 0) {
								gg = gg + String(i) + '=' + Obj[i] + ' | ';
							} else {
								gg = gg + String(i) + '= (blank)' + Obj[i] + ' | ';
							}
							
							
							
							if (brCount == 4) {
								brCount  = 0;
								gg = gg + cr + '[' + Trim(level) + ']   ';
							}
						}
		
					
			   } else {
				   //	Function
				  if (Target != undefined) {
					 Funcs += '\n[' + Trim(level) + ']  ';
				  }
				  Funcs = Funcs +  ' ' + String(i) + '() ';   
			   }
			}
			
			if (Funcs != '') {
				gg = gg + Funcs;
			}

			
			
			if (brCount > 0) {
				gg = gg + cr;
			}
	
	
			if (Alert != undefined) {
				gg = Alert + '\n' + gg;
			}
	
			/*
			if (Sub==undefined) {
				
				if (Target == undefined) {
					alert(gg);
				} else {
					gg = ReplaceStr(gg, '\n', '<br>');
					if (GetID(Target)) {
						GetID(Target).innerHTML = ReplaceStr(gg, ' ', '&nbsp;');
					}
				}
			}*/
		
		}
		
		_DumpLevel--;
			
		if (_DumpCount>1) {
			level = level.substring(0, (level.length-3));
		}
		
		if (_DumpLevel == 0) {
			if (Target == undefined) {
				alert(gg);
			} else {
				
				gg = ReplaceStr(gg, '[]', 				'   <hr size=\"1\">');
				gg = ReplaceStr(gg, '[1]', 				'\t');
				gg = ReplaceStr(gg, '[1 2]', 			'\t\t');
				gg = ReplaceStr(gg, '[1 2 3]', 			'\t\t\t');
				gg = ReplaceStr(gg, '[1 2 3 4]', 		'\t\t\t\t');
				gg = ReplaceStr(gg, '[1 2 3 4 5]', 		'\t\t\t\t\t');
				gg = ReplaceStr(gg, '[1 2 3 4 5 6]', 	'\t\t\t\t\t\t');
				
				GetID(Target).innerHTML = '<pre>' + gg;	
			}
			
			_DumpCount     = 0;
			_DumpSameCount = 0;
			_MaxDump	   = 1000;
			_DumpLevel	   = 0;
			_DumpLevelMax  = 0;
			_LastDumpObj   = null;
		}

		
		return gg;
	}
	
	Dump1 = function(Obj, Alert, Target, cr, level, Sub, LastName) {


		var gg = level==undefined ? '' : level;

		if (cr == undefined) {
			cr = '\n'; 
		}

		if (level == undefined) {
			level = ''; 
		} else {
			level += '   ';
		}
		
		if (typeof(Obj) == 'string') {
			alert(Obj);
			return;
		}
		
		if (_DumpCount > _MaxDump) {
			return '';
		}
		
		var count = 0;
		var brCount = 0;
		for (var i in Obj) {
			count ++;
			_DumpCount++;
			if (typeof(Obj[i]) != 'function') {
				try {
					if ((typeof(Obj[i]) == 'object' || typeof(Obj[i]) == 'array')
					    && i != 'parentNode' 
						&& i.indexOf('Sibling') == -1 
						&& i.indexOf('Child') == -1 
						&& i.indexOf('Nodes') == -1
						&& i.indexOf('owner') == -1
						) {
						
						
						if (count> 1) {
							//gg = gg + '\n';
						}
						gg = gg + level + String(i) + ': ' + typeof(Obj[i]) + '\n';

						
						
											
						var NextLevel = Dump(Obj[i], undefined, undefined, cr, level, 1, i);
						
						gg = gg + NextLevel;
						
						if (_DumpCount>1) {
							level = level.substring(0, (level.length-3));
						}
						
						if (_DumpCount > _MaxDump) {
							_DumpCount--;
							break;
						}
						
												
					} else {
						if (Obj[i] != '' || Number(Obj[i]) == 0) {
							gg = gg + String(i) + '=' + Obj[i] + ' | ';
						} else {
							gg = gg + String(i) + '= (blank)' + Obj[i] + ' | ';
						}
						if (brCount == 4) {
							brCount  = 0;
							gg = gg + cr + level;
						}
					}
	
				} catch(e) {
					gg = gg + String(i) + ' ! Error ' + e.message + ' | ';
				}
		   } else {
				gg = gg + '(' + String(i) + ') ';   
		   }
		}
		
		if (brCount > 0) {
			gg = gg + cr;
		}


		if (Alert != undefined) {
			gg = Alert + '\n' + gg;
		}

		
		if (Sub==undefined) {
			
			if (Target == undefined) {
				alert(gg);
			} else {
				gg = ReplaceStr(gg, '\n', '<br>');
				if (GetID(Target)) {
					GetID(Target).innerHTML = ReplaceStr(gg, ' ', '&nbsp;');
				}
			}
		}

		return gg;
	}
	
	
	MultiSelectToStringList = function(Obj, Field, Delimiter) {

		var gg = '';
		for (var i=0; i< Obj.options.length; i++) {
			gg = gg + Obj.options(i)[Field] + Delimiter;
		}
		
		gg = gg.substring(0, gg.length-1);
		
		return gg;
	}
	
	
	
		
	
	PrintHTML = function(DivObj, HTML) {

		DivObj.innerHTML = DivObj.innerHTML + '<iframe id="PRINTframe" style="position:absolute; left:-5000"></iframe>';
		PRINTframe.onload = function () {
											PRINTframe.document.body.innerHTML = HTML;
											PRINTframe.focus();
											PRINTframe.print();
										};
					
	}
	
	
	var vClockDiv;
	var vClockStyle;
	
	function StartClock(DivObj)	{
		
		if (DivObj != undefined) {
			vClockDiv = DivObj;
		}
		
		var today=new Date()
		var h=today.getHours()
		var m=today.getMinutes()
		var s=today.getSeconds()
		// add a zero in front of numbers<10
		//m=checkTime(m)
		//s=checkTime(s)
		//DivObj.innerHTML=h+":"+m+":"+s;
		vClockDiv.innerHTML=new Date();
		t=setTimeout('StartClock()',500)
	}
	
	//
	// Prefix 1-9 with a 0
	//
	function checkTime(i) {
		if (i < 10) { i = "0" + i }
		return i
	}
	
	// ************************************
	// This is similar ot he StartClock, only formatted
	// ds = Date Style, options are dfull, dshort, dshorter
	// ts = Time Style, options are t24 or t12
	// by: Jennifer Stephens, 1/31/2008
	// ************************************
	function StartClock2(DivObj, ds, ts)	{
		
		if (DivObj != undefined) {
			vClockDiv = DivObj;
		};
		
		
		if (ds == undefined) {
			vDateStyle = 'dfull';
		} else {
			vDateStyle = ds;
		};
		
		if (ts == undefined) {
			vTimeStyle = 't24';
		} else {
			vTimeStyle = ts;
		};
		
		var vClock = new Date();
		var s=vClock.getSeconds()
		
		vClockDiv.innerHTML = FormatDate(vClock, vDateStyle) + " " + FormatTime(vClock, vTimeStyle);
		t=setTimeout(
					 	function() {
								  		StartClock2(GetID(DivObj), ds, ts, 500);
								   }
					);
	}

	// ************************************
	// Date Properties
	// by: Jennifer Stephens, 1/31/2008
	// ************************************
	function FormatDate(ThisDate, DateStyle) {

		if (DateStyle == undefined) {
			DateStyle = 'dshorter';
		}
		
		wd = ShowDayOfWeekString(ThisDate.getDay());
		mv = ShowMonthAsString(ThisDate.getMonth());
		mn = ThisDate.getMonth() + 1
		mn = checkTime(mn);
		dv = ThisDate.getDate();
		dn = checkTime(dv);
		yv = ThisDate.getFullYear();
		
		if (DateStyle == 'dfull') {
			OutputVal = wd + ", " + mv + " " + ThisDate.getDate() + ", " + ThisDate.getFullYear();
		} else if (DateStyle == 'dshort') {
			OutputVal = wd.substring(0, 3) + ", " + mv.substring(0, 3) + " " + dv + ", " + yv;
		} else if (DateStyle == 'dshorter') {
			wd = ShowDayOfWeekString(ThisDate.getDay());
			OutputVal = mn + "/" + dn + "/" + yv;
		}
			
		
		return OutputVal;
	}
	
	// ************************************
	// Time Properties
	// by: Jennifer Stephens, 1/31/2008
	// ************************************
	function FormatTime(ThisDate, TimeStyle) {

		if (TimeStyle == undefined) {
			TimeStyle = 't24';
		}
		
		hv = checkTime(ThisDate.getHours());
		mv = checkTime(ThisDate.getMinutes());
		sv = checkTime(ThisDate.getSeconds());
		
		if (TimeStyle == 't24') {
			OutputVal = hv + ":" + mv + ":" + sv;
		} else {
			OutputVal = ShowTimeAs12(hv, mv, sv);
		}
		
		return OutputVal;
	}
	
	// ************************************
	// Convert the numeric value of the 
	// weekday to its string representation
	// by: Jennifer Stephens, 1/31/2008
	// ************************************
	function ShowDayOfWeekString(w) {
		if (w == 0) { w = 'Sunday'; } 
		else if (w == 1) { w = 'Monday'; } 
		else if (w == 2) { w = 'Tuesday'; } 
		else if (w == 3) { w = 'Wednesday'; } 
		else if (w == 4) { w = 'Thursday'; } 
		else if (w == 5) { w = 'Friday'; } 
		else if (w == 6) { w = 'Saturday'; }
		
		return w;
	}
	
	// ************************************
	// Convert the numeric value of the
	// month to its string representation
	// by: Jennifer Stephens, 1/31/2008
	// ************************************
	function ShowMonthAsString(m) {
		if (m == 0) { m = 'January'; }
		else if (m == 1) { m = 'February'; }
		else if (m == 2) { m = 'March'; }
		else if (m == 3) { m = 'April'; }
		else if (m == 4) { m = 'May'; }
		else if (m == 5) { m = 'June'; }
		else if (m == 6) { m = 'July'; }
		else if (m == 7) { m = 'August'; }
		else if (m == 8) { m = 'September'; }
		else if (m == 9) { m = 'October'; }
		else if (m == 10) { m = 'November'; }
		else if (m == 11) { m = 'December'; }
		
		return m;
	}
	
	// ************************************
	// This will take the 24 hour and make it 12
	// by: Jennifer Stephens, 1/31/2008
	// ************************************
	function ShowTimeAs12(h, m, s) {
		if (h <= 12) {
			t = 'AM';
		} else {
			t = 'PM';
			h = checkTime(h - 12);
		}
		
		return h + ":" + m + ":" + s + " " + t;
	}
	
	//
	//	Show / Hide Table Column
	//
	function ShowTableColumn(tableid, colno, show) {

		var stl;
		
		if (show) 
				stl = ''
		else    stl = 'none';
	
		var tbl  = document.getElementById(tableid);
		var rows = tbl.getElementsByTagName('tr');
	
		for (var row=0; row<rows.length;row++) {
		  var cels = rows[row].getElementsByTagName('td')
		  cels[colno].style.display=stl;
		}
		
	  }
	  
	 

	
	//________________________________________________________________________________
	//
	//	EXECUTE A FUNCTION AFTER MILISECS
	//
	function ExecuteFunctionAfter(func, timing, Param1, Param2, Param3, Param4) {
		Obj = new Object();
		Obj.Interval= setInterval(func, timing, Obj, Param1, Param2, Param3, Param4);
		return Obj;
	}
	
	
	
	//________________________________________________________________________________
	//
	//	EXECUTE A FUNCTION AFTER MILISECS
	//
	function ExecuteFunctionOnceAfterCall(func, Obj, Param1, Param2, Param3, Param4) {

		clearInterval(Obj.Interval);
		func(Param1, Param2, Param3, Param4);
		Obj = undefined;
	}
	
	
	
	//________________________________________________________________________________
	//
	//	EXECUTE A FUNCTION AFTER MILISECS
	//
	function ExecuteFunctionOnceAfter(func, timing, Param1, Param2, Param3, Param4) {
		var Obj = new Object();
		Obj.func   = func;
		Obj.Param1 = Param1;
		Obj.Param2 = Param2;
		Obj.Param3 = Param3;
		Obj.Param4 = Param4;
		

		var TempFunc = function() {
			ExecuteFunctionOnceAfterCall(Obj.func, Obj, Obj.Param1, Obj.Param2, Obj.Param3, Obj.Param4);
		}
		
		Obj.Interval = setInterval(TempFunc, timing);
		return Obj;
	}
	
	
	//________________________________________________________________________________
	//
	//	EXECUTE A FUNCTION AFTER MILISECS USING THE PASSED IN OBJ
	//
	function ExecuteFunctionOnceAfterUsing(Obj, func, timing, Param1, Param2, Param3, Param4) {
	
		if (Obj != undefined) {
			clearInterval(Obj.Interval);
		} else {
			Obj = new Object();
		}
		

		Obj.func   = func;
		Obj.Param1 = Param1;
		Obj.Param2 = Param2;
		Obj.Param3 = Param3;
		Obj.Param4 = Param4;
		

		var TempFunc = function() {
			ExecuteFunctionOnceAfterCall(Obj.func, Obj, Obj.Param1, Obj.Param2, Obj.Param3, Obj.Param4);
		}

		Obj.Interval = setInterval(TempFunc, timing);
		return Obj;
	}
	
	
	
	
	function DragDropCoordinates() {
		
		if (!DragDropObject) {
			return
		}

		
		if (event.srcElement==DragDropSelect)	{
			mouseover	 =true;
			DragDropLeft =DragDropObject.style.pixelLeft;
			DragDropTop	 =DragDropObject.style.pixelTop;
			DragDropX	 =event.clientX;
			DragDropY	 =event.clientY;
			//DragDropObject.style.filter = "alpha(opacity=20)";
			document.onmousemove=DragObject;
		}
	}
	
	function DragObject() {
		
		if (mouseover&&event.button==1)	{

			DragDropObject.style.pixelLeft	=DragDropLeft+event.clientX-DragDropX
			DragDropObject.style.pixelTop	=DragDropTop+event.clientY-DragDropY
			return false
		}
	}
	
	function StopDragDrop() {
	
		mouseover=false;
		document.onmousedown=function() {};
		//DragDropObject.style.filter = "";
	}

	function StartDragDrop(SelectObject, DragObject) {

		DragDropObject = DragObject;
		DragDropSelect = SelectObject;
		document.onmousedown=DragDropCoordinates;
		document.onmouseup=StopDragDrop;

	}

	
	
	function NumbersOnly(e)	{
		var keynum
		var keychar
		var numcheck
		if(window.event) { // IE	
			keynum = e.keyCode
		} else if(e.which) { // Netscape/Firefox/Opera
			keynum = e.which
		}
		keychar = String.fromCharCode(keynum)
		numcheck = /\d/;
		
		return numcheck.test(keychar)
	}
	
	
	
	function NumberTypes(e)	{
		var keynum
		var keychar
		var numcheck
		if(window.event) { // IE	
			keynum = e.keyCode
		} else if(e.which) { // Netscape/Firefox/Opera
			keynum = e.which
		}
		keychar = String.fromCharCode(keynum);
		
		var validletters = '0123456789%.$\/\\';
		//alert(validletters.indexOf(keychar) + " : " + keychar + " : " + keynum + " : " + e.type);
		return (validletters.indexOf(keychar) > -1)
	}
	
	//
	// This is different from above because this
	// allows for the num key pad to be used
	// where the above thinks the num key pad
	// is a lower case letter.
	// PrevNum is used to determine if someone has pressed the shift key
	//
	
	
	function AlwaysAllowed(e) {
		var keynum
		var RetVal = false;
		
		//which :: Netscape/Firefox/Opera
		//keyCode :: IE
		var keynum = (e.which) ? e.which : e.keyCode
		
		IsAllowed = IsAllowedWith(e);
		
		if (
			keynum == 13 ||		// enter
			keynum == 9 ||		// tab
			keynum == 8 ||		// backspace
			keynum == 46 || 	// delete
			keynum == 16 || 	// shift
			keynum == 17 || 	// ctrl
			keynum == 18 || 	// alt
			keynum == 45 || 	// insert
			keynum == 36 || 	// home
			keynum == 35 || 	// end
			keynum == 33 || 	// page up
			keynum == 34 || 	// page down
			keynum == 27 || 	// esc
			keynum == 20 || 	// caps lock
			keynum == 144 ||	// num lock
			(keynum >= 112 && keynum <= 123) ||	// F1-F12
			(keynum >= 37 && keynum <= 40) ||	// arrow keys
			(keynum == 65 && IsAllowed) ||	// select all CTRL A
			(keynum == 90 && IsAllowed) ||	// undo CTRL Z
			(keynum == 67 && IsAllowed) ||	// copy CTRL C
			(keynum == 86 && IsAllowed) ||	// paste CTRL V
			(keynum == 88 && IsAllowed) 	// cut CTRL X
		) {
			RetVal = true; 
		} else {
			RetVal = false; 
		}

		return RetVal;
		
	}
	
	//
	// These keys return false because they are not allowed to be true
	// when another key is pressed
	//
	function NotAllowedWith(e) {
		
		if (e.shiftKey || e.ctrlKey || e.altKey) {
			return false;
		} else {
			return true;
		}
	}
	
	//
	// These keys return true because they are allowed to be true
	// when another key is pressed
	//
	function IsAllowedWith(e) {
		
		if (e.shiftKey || e.ctrlKey || e.altKey) {
			return true;
		} else {
			return false;
		}
	}
	
	
	function CheckNumericOnly(e) { 
		var keynum
		var RetVal = false;
		
		
		//which :: Netscape/Firefox/Opera
		//keyCode :: IE
		var keynum = (e.which) ? e.which : e.keyCode
		
		IsNotAllowed = NotAllowedWith(e);
			
		// 48 - 57 are the number keys at the top of a keyboard
		// 96 - 105 are the numbers on the numpad
		if (
			((keynum >= 48 && keynum <= 57) && IsNotAllowed) || 
			(keynum >= 96 && keynum <= 105)
		) {
			RetVal = true; 
		} else { 
			RetVal = false; 
		}
		
		if (RetVal == false) {
			RetVal = AlwaysAllowed(e);
		}
		
		return RetVal; 
	}
	
//
	//	Letter, Numbers and Some Punctuation
	//
	function CheckAllowedPunctuation(e) { 
		var keynum
		var RetVal = false;
		
		
		//which :: Netscape/Firefox/Opera
		//keyCode :: IE
		var keynum = (e.which) ? e.which : e.keyCode
		
		var IsAllowed = IsAllowedWith(e);
			
		// 48 - 57 are the number keys at the top of a keyboard
		// 96 - 105 are the numbers on the numpad
		if (
			keynum == 190 || 	// .
			keynum == 188 ||	// , 
			keynum == 189 || 	//	- _	
			//keynum == 222 || 	// '
			(keynum == 57 && IsAllowed) || // (
			(keynum == 48 && IsAllowed)   // )

		) {
			RetVal = true; 
		} else { 
			RetVal = false; 
		}
		
		if (RetVal == false) {
			RetVal =  LettersAndNumberOnly(e);
		}
		
		if (RetVal == false) {
			RetVal = AlwaysAllowed(e);
		}
		
		return RetVal; 
	}
	
	function CheckLettersOnly(e) { 
		var keynum
		var RetVal = false;
		
		
		//which :: Netscape/Firefox/Opera
		//keyCode :: IE
		var keynum = (e.which) ? e.which : e.keyCode
		
			
		// 48 - 57 are the number keys at the top of a keyboard
		// 96 - 105 are the numbers on the numpad
		if (
			keynum >= 65 && keynum <= 90
		) {
			RetVal = true; 
		} else { 
			RetVal = false; 
		} 
		
		if (RetVal == false) {
			RetVal = AlwaysAllowed(e);
		}
		
		return RetVal; 
	}
	
	
	//
	//
	//
	function CheckNumericKeyInfo(e) { 
		var keynum
		var RetVal = false;
		
		
		//which :: Netscape/Firefox/Opera
		//keyCode :: IE
		var keynum = (e.which) ? e.which : e.keyCode
		
		IsNotAllowed = NotAllowedWith(e);
		IsNumericValue = CheckNumericOnly(e);
		
		// 190 is the . on the keyboard
		// 189 is the - on the keyboard
		// 109 is the - on the number pad
		// 110 is the . on the number pad
		
		if (
			IsNumericValue || 
			(keynum == 190 && IsNotAllowed) || 
			(keynum == 189 && IsNotAllowed)  ||
			keynum == 109 || keynum == 110
		) {
			RetVal = true; 
		} else { 
			RetVal = false; 
		} 
		
		if (RetVal == false) {
			RetVal = AlwaysAllowed(e);
		}
		
		return RetVal; 
	}
	
	
	//
	//
	//
	function CheckNumericMinMax(value, minval, maxval, id, allowblank) { 
		var keynum
		var RetVal = false;
		
		//alert(value + ' : ' + minval + ' : ' + maxval);
		
		//
		// Allow blank value
		// 
		if (allowblank && value == '') {
			return true
		}
		
		//
		// Blank value is not allowed
		// Evaluate number provided based on minval and maxval
		//
		if (minval == '' || minval == undefined) {
			RetVal = true;
		} else if (Number(value) < minval) {
			alert('Value provided is less than allowed min of ' + minval);
			if (id != undefined) {
				id.focus();
			}
			return false;
		}
		
		
		if (maxval == '' || maxval == undefined) {
			RetVal = true;
		} else if (Number(value) > maxval) {
			alert('Value provided is greater than allowed max of ' + maxval);
			if (id != undefined) {
				id.focus();
			}
			return false;
		}
		
		return RetVal; 
	}
	
	
	//
	// This allows A-Z, a-z and 0-9 and a space only
	//
	function LettersAndNumberOnly(e) { 
		var keynum
		var RetVal = false;
		
		
		//which :: Netscape/Firefox/Opera
		//keyCode :: IE
		var keynum = (e.which) ? e.which : e.keyCode
		
		IsNotAllowed = NotAllowedWith(e);
		IsNumericValue = CheckNumericOnly(e);
		IsAlphaValue = CheckLettersOnly(e);
		
		// 32 is the space bar on the keyboard

		
		if (
			IsNumericValue ||
			IsAlphaValue ||
			keynum == 32
		) {
			RetVal = true; 
		} else { 
			RetVal = false; 
		} 
		
		if (RetVal == false) {
			RetVal = AlwaysAllowed(e);
		}
		
		return RetVal; 
	} 
	
	
	//
	// This allows A-Z, a-z and 0-9 and a space only and $ and *
	//
	function AllowedClientGroupCode(e) { 
		var keynum
		var RetVal = false;
		
		
		//which :: Netscape/Firefox/Opera
		//keyCode :: IE
		var keynum = (e.which) ? e.which : e.keyCode
		
		IsNotAllowed = NotAllowedWith(e);
		IsNumericValue = CheckNumericOnly(e);
		IsAlphaValue = CheckLettersOnly(e);
		
		// 32 is the space bar on the keyboard

		
		if (
			IsNumericValue ||
			IsAlphaValue ||
			keynum == 32 ||	// space
			keynum == 56 ||	// *
			keynum == 52	// $
		) {
			RetVal = true; 
		} else { 
			RetVal = false; 
		} 
		
		if (RetVal == false) {
			RetVal = AlwaysAllowed(e);
		}
		
		return RetVal; 
	}
	
	//
	// Letters and Numbers only
	//
	function AlphaNumericOnly(e) { 
		var keynum
		var RetVal = false;
		
		
		//which :: Netscape/Firefox/Opera
		//keyCode :: IE
		var keynum = (e.which) ? e.which : e.keyCode
		
		IsNotAllowed = NotAllowedWith(e);
		IsNumericValue = CheckNumericOnly(e);
		IsAlphaValue = CheckLettersOnly(e);
		
		// 190 is the . on the keyboard
		// 189 is the - on the keyboard
		// 109 is the - on the number pad
		// 110 is the . on the number pad
		// 32 is space
		
		//alert(keynum);
		
		if (
			IsNumericValue ||
			IsAlphaValue ||
			(keynum == 190 && IsNotAllowed) || 
			(keynum == 189 && IsNotAllowed) ||
			keynum == 109 || 
			keynum == 110 ||
			keynum == 32
		) {
			RetVal = true; 
		} else { 
			RetVal = false;
		} 
		
		if (RetVal == false) {
			RetVal = AlwaysAllowed(e);
		}
		
		return RetVal; 
	} 

	
	//
	// HTML Color Key codes
	//
	function HexColor(e) {
		var keynum
		var RetVal = false;
		
		
		//which :: Netscape/Firefox/Opera
		//keyCode :: IE
		var keynum = (e.which) ? e.which : e.keyCode
		
		IsNumericValue = CheckNumericOnly(e);
		
		// 65 - 71 are upper case A-F
		
		if(
			IsNumericValue || 
			(keynum >= 65 && keynum <= 70)
		) {
			RetVal = true; 
		} else { 
			RetVal = false;
		} 
		
		if (RetVal == false) {
			RetVal = AlwaysAllowed(e);
		}
		
		
		return RetVal; 
	}

	
	//
	// Old Hex function
	//
	function HexOnly(e)	{
		var keynum
		var keychar
		var numcheck
		
		//which :: Netscape/Firefox/Opera
		//keyCode :: IE
		var keynum = (e.which) ? e.which : e.keyCode
		
		IsNotAllowed = NotAllowedWith(e);
		
		keychar = String.fromCharCode(keynum);
		var validletters = '0123456789ABCDEFabcdef';
		return (validletters.indexOf(keychar) > -1)
	}
	
	//
	//
	//
	function LettersAndNumber(e)	{
		var keynum
		var keychar
		var numcheck
		
		//which :: Netscape/Firefox/Opera
		//keyCode :: IE
		var keynum = (e.which) ? e.which : e.keyCode
		
		IsNotAllowed = NotAllowedWith(e);
		
		keychar = String.fromCharCode(keynum);
		var validletters = '0123456789 ABCDEFGHIJKLMNOPQRSTUVWXYZ-.*() abcdefghijklmnopqrstuvwxyz';
		return (validletters.indexOf(keychar) > -1)
	}


	function GetPixelPosition(Obj, PosObj) {
		
		if (typeof Obj == 'String') {
			Obj = GetID(Obj);
		}
			
		//
		//	Recursive Function to Determine Left and Top Actual Position
		//
		
		if (PosObj == undefined) {
			PosObj 			= new Object;
			PosObj.Left 	= 0;
			PosObj.Top 		= 0;
			PosObj.Parents 	= 0;
		}
		
		var blw = 0;
		var btw = 0;
		var plw = 0;
		var ptw = 0;
		
		try {
			if (isNaN(parseInt(Obj.currentStyle.borderTopWidth)) == false) {
				btw = parseInt(Obj.currentStyle.borderTopWidth);
			}
		} catch(e) {}

		try {
			if (isNaN(parseInt(Obj.currentStyle.paddingTop)) == false) {
				ptw = parseInt(Obj.currentStyle.paddingTop);
			}
		} catch(e) {}


		try {
			if (isNaN(parseInt(Obj.currentStyle.borderLeftWidth)) == false) {
				blw = parseInt(Obj.currentStyle.borderLeftWidth);
			}
		} catch(e) {}


		try {
			if (isNaN(parseInt(Obj.currentStyle.paddingLeft)) == false) {
				plw = parseInt(Obj.currentStyle.paddingLeft);
			}
		} catch(e) {}

			
		PosObj.Left 	= PosObj.Left + Obj.offsetLeft + blw + plw;
		PosObj.Top 		= PosObj.Top  + Obj.offsetTop + btw + ptw;

		// Test for Parent
		try {
			var test = Obj.offsetParent;
			// If Still here Parent exist
			if (String(Obj.offsetParent) != null ) {
				PosObj.Parents	= PosObj.Parents + 1;
				PosObj = GetPixelPosition(Obj.offsetParent, PosObj);
			}
		} catch(e) {
		}
		
		return PosObj;
		
	}


	//
	//
	//	
	function ArrayAdd(TheArray, Value) {
		
		TheArray[TheArray.length ] = Value;
		
		return TheArray;
		
	}


	//
	//
	//
	function ArrayRemove(TheArray, Value) {
		
		var t;
		var NA = new Array();
		
		for (t=0;t<TheArray.length; t++) {
			if (TheArray[t] != Value) {
				NA[NA.length] = TheArray[t];
			}
		}
		
		return NA;
		
	}


	//
	//
	//
	function ShowPopup(TargetID, PopupDiv, Content, x, y, w, h)	{
		
		
		if (typeof(Content) == 'object') {
			var c = Content.innerHTML;
		} else {
			var c = Content;
		}
		
		var p		= window.createPopup();
		var pbody	= p.document.body;

		if (w==undefined) { w = 0 };
		if (h==undefined) { h = 0 };
		
		
		PopupDiv.innerHTML = c;		
	  	w  				   = PopupDiv.offsetWidth  + w;
		h  				   = PopupDiv.offsetHeight + h;

		
		var t = '<div style="font-family:arial; font-size:12px;padding:10; background-Color:lightyellow; border:solid #999999 1px; ' + 
					'border-Left:solid #CCCCCC 1px; border-Top:solid #CCCCCC 1px; ' +
					'filter:progid:DXImageTransform.Microsoft.Shadow(color=#BBBBBB, Direction=135, Strength=2); ' +
					'width:' + (w-2) +  ';' + 
					'height:' + (h-2) + 
					'">' + c + '</div>';

		pbody.innerHTML = t;

		p.show(x,y,w,h,TargetID);
		
		return pbody;
	}
	
	
	//
	//
	//
	function CreatePopup(x, y, w, h, Content, RelativeID)	{
		
		if (typeof(Content) == 'object') {
			var c = Content.innerHTML;
		} else {
			var c = Content;
		}
		

		var p		= window.createPopup();
		var pbody	= p.document.body;
		
		pbody.innerHTML = c;
		p.show(x,y,w,h, RelativeID);
		
		return pbody;
	}




	var Div_To_Refresh_Obj = new Object();
	
	RefreshDivAfterScroll = function(DivToRefresh) {
		Div_To_Refresh_Obj = ExecuteFunctionOnceAfterUsing(Div_To_Refresh_Obj,  
															function() { 
																DivToRefresh.style.visibility = 'hidden'; 
																ExecuteFunctionOnceAfter( function() { DivToRefresh.style.visibility = 'visible'; }, 100);
															},
															200);
	}
	
	
	
	
	function SelectAll(FieldName) {
		
	
		
		if (typeof(FieldName) == 'object') {
			var tempval = FieldName;	   
		} else {
			var tempval = GetID(FieldName);
		}
		
		try {
			ExecuteFunctionOnceAfter(
					function() {
						tempval.focus()
						tempval.select();
					},
					300);
			
		} catch(e){}
	}
	
	
	function UnSelectAll() {
		
		ExecuteFunctionOnceAfter(
				function() {
					try {
						document.selection.empty();
						
					} catch(e){}
					try {		
						window.getSelection().removeAllRanges();
						
					} catch(e){}
				},
				100
		)
	}
	
	
	LoadStyleSheet = function(DIV, URL) {
		document.body.innerHTML = document.body.innerHTML +  '<link rel=stylesheet href="' + URL + '">';
	}
	
	
	var PleaseWaitCounter;
	PleaseWaitCounter = 0;

	
	
	
	var StyleSheetCache = new Object;
	

	//
	//
	//
	GetStyleValue = function(StyleObj, Style) {
		StyleObj = GetID(StyleObj);
		
		if (StyleObj == undefined) {
			return 0;	
		}
		
		var Value = 0;
		
		//
		//	Use Inline Style If Found
		//
		if (GetID(StyleObj.style) != undefined) {
			try {
				var Value = ReplaceStr(StyleObj.style[Style], 'px', '');
			} catch(e) {
			}
		}
		
		
		
		//
		//	Use Style Sheet Value If Found :: ClassName Argument Must be Passed
		//
		if (StyleObj['className'] != '' && Value == 0) {

			var cssRules;
			
			if (document.all) {
				cssRules = 'rules';
			} else if (document.getElementById) {
				cssRules = 'cssRules';
			}


			//
			//	If Cached
			//

				if (StyleSheetCache[StyleObj.className] != undefined){
					Value = parseInt(StyleSheetCache[StyleObj.className][Style]);
					//DIV_RecentInfo.innerHTML += '**' + StyleObj.className +' '+Style + ' ' + Value + '<br>';
				}
				try{
			} catch(e){}
			
			if (Value == '') {

				for (var S = 0; S < document.styleSheets.length; S++){
					for (var R = 0; R < document.styleSheets[S][cssRules].length; R++) {
					
						var ClassStr = ReplaceStr(document.styleSheets[S][cssRules][R].selectorText, '#', ' ');
						ClassStr = ReplaceStr(ClassStr, '.', ' ');
						ClassStr = ReplaceStr(ClassStr, ',', ' ');
						ClassStr = ' ' + ClassStr + ' ';
						if (ClassStr.indexOf(StyleObj.className) > -1  && document.styleSheets[S][cssRules][R]['style'] != undefined) {
							Value = Number(parseInt(document.styleSheets[S][cssRules][R].style[Style]));
							if (Value > 0) {
								StyleSheetCache[StyleObj.className] = document.styleSheets[S][cssRules][R].style;
								break;
							}
						}
					}

					if (Value > 0) {

						break;
					}
				}
			}
		}

	  
		if (Value > 0) {
			return Value;	
		} else {
			return 0;
		}

		
	}

	
	//
	//
	//
	GetWidth = function(ObjectID, Width) {
	
		ObjectID = GetID(ObjectID);
		
		var SizeObj = new Object();
		SizeObj.OffsetWidth  	= Number(ObjectID.offsetWidth);
				
			
		if (isIE || isChrome || isSafari) {
			
			return SizeObj.OffsetWidth;

		} else {
			
			SizeObj.Border	 		= Number(GetStyleValue(ObjectID, 'borderWidth'));
			SizeObj.BorderLeft 		= Number(GetStyleValue(ObjectID, 'borderLeftWidth'));
			SizeObj.BorderRight		= Number(GetStyleValue(ObjectID, 'borderRightWidth'));
			SizeObj.PaddingLeft		= Number(GetStyleValue(ObjectID, 'paddingLeft'));
			SizeObj.PaddingRight	= Number(GetStyleValue(ObjectID, 'paddingRight'));
			SizeObj.Padding			= Number(GetStyleValue(ObjectID, 'padding'));
			SizeObj.MarginLeft		= Number(GetStyleValue(ObjectID, 'marginLeft'));
			SizeObj.MarginRight		= Number(GetStyleValue(ObjectID, 'marginRight'));
			SizeObj.Margin			= Number(GetStyleValue(ObjectID, 'margin'));
			SizeObj.OutlineLeft		= Number(0);
			SizeObj.OutlineRight	= Number(0);
	
	
			if (SizeObj.Padding != 0) {
				if (SizeObj.PaddingRight==0) {
					SizeObj.PaddingRight = SizeObj.Padding;
				}
				if (SizeObj.PaddingLeft==0) {
					SizeObj.PaddingLeft = SizeObj.Padding;
				}
				
				//SizeObj.Padding = 0;
			}
			
			if (SizeObj.Border != 0) {
				if (SizeObj.BorderRight==0) {
					SizeObj.BorderRight = SizeObj.Border;
				}
				if (SizeObj.BorderLeft==0) {
					SizeObj.BorderLeft = SizeObj.Border;
				}
				//SizeObj.Border = 0;
			}
			
		
			SizeObj.OuterWidth 		= 	SizeObj.Border			+
										SizeObj.BorderLeft  	+	 
										SizeObj.BorderRight 	+
										SizeObj.PaddingLeft 	+ 
										SizeObj.PaddingRight 	+
										SizeObj.MarginLeft 		+ 
										SizeObj.MarginRight 	+ 
										SizeObj.OutlineLeft 	+ 
										SizeObj.OutlineRight; 
												
			if (Width == undefined) {
				Width = ObjectID.offsetWidth;	
			}
		

			return Width - SizeObj.OuterWidth;
		}
		
	}
		
	
	
	CreateUUID = function(len, radix) {
		 // Private array of chars to use
		var CHARS = '0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz'.split(''); 
	
	 
		var chars = CHARS, uuid = [], rnd = Math.random;
		radix = radix || chars.length;
	
		if (len) {
		  // Compact form
		  for (var i = 0; i < len; i++) uuid[i] = chars[0 | rnd()*radix];
		} else {
		  // rfc4122, version 4 form
		  var r;
	
		  // rfc4122 requires these characters
		  uuid[8] = uuid[13] = uuid[18] = uuid[23] = '-';
		  uuid[14] = '4';
	
		  // Fill in random data.  At i==19 set the high bits of clock sequence as
		  // per rfc4122, sec. 4.1.5
		  for (var i = 0; i < 36; i++) {
			if (!uuid[i]) {
			  r = 0 | rnd()*16;
			  uuid[i] = chars[(i == 19) ? (r & 0x3) | 0x8 : r & 0xf];
			}
		  }
		}
	
		return uuid.join('');
	
	}

// -------------------------------------------------------------------
// DHTML Window Widget- By Dynamic Drive, available at: http://www.dynamicdrive.com
// v1.0: Script created Feb 15th, 07'
// v1.01: Feb 21th, 07' (see changelog.txt)
// v1.02: March 26th, 07' (see changelog.txt)
// v1.03: May 5th, 07' (see changelog.txt)
// v1.1:  Oct 29th, 07' (see changelog.txt)
// -------------------------------------------------------------------


// ** HELP: http://www.dynamicdrive.com/dynamicindex8/dhtmlwindow/index.htm

var dhtmlwindow={
	
	imagefiles:['/Images/DHTMLWindow/min.png', '/Images/DHTMLWindow/close.png', '/Images/DHTMLWindow/restore.png', '/Images/DHTMLWindow/resize.gif'], //Path to 4 images used by script, in that order
	ajaxbustcache: true, //Bust caching when fetching a file via Ajax?
	ajaxloadinghtml: '<b>Loading Page. Please wait...</b>', //HTML to show while window fetches Ajax Content?
	
	minimizeorder: 0,
	zIndexvalue:100,
	tobjects: [], //object to contain references to dhtml window divs, for cleanup purposes
	lastactivet: {}, //reference to last active DHTML window
	
	
	// ERA modal Count
	ModalCount:0,
	ModalHideBars:'',

init:function(t){
	var domwindow=document.createElement("div") //create dhtml window div
	domwindow.id=t
	domwindow.className="dhtmlwindow"

	UUID = CreateUUID(5);
		
	var domwindowdata='';
	domwindowdata+='<div id="Shadow_Window_Left' + UUID + '" class="drag-shadow"><img id="Shadow_Window_Left_Img' + UUID + '" src="/Images/WindowShadow_Left.png"/></div>';
	domwindowdata+='<div id="Shadow_Window_Right' + UUID + '" class="drag-shadow"><img id="Shadow_Window_Right_Img' + UUID + '" src="/Images/WindowShadow_Right.png"/></div>';
	domwindowdata+='<div id="Shadow_Window_Top' + UUID + '" class="drag-shadow"><img id="Shadow_Window_Top_Img' + UUID + '" src="/Images/WindowShadow_Top.png"/></div>';
	domwindowdata+='<div id="Shadow_Window_Bottom' + UUID + '" class="drag-shadow"><img id="Shadow_Window_Bottom_Img' + UUID + '" src="/Images/WindowShadow_Bottom.png"/></div>';
	domwindowdata+='<div id="DHTML_' + UUID + '"><div><div id="Handle_' + UUID + '" class="drag-handle">Window</div>'
	domwindowdata+='<div class="drag-controls"><img src="'+this.imagefiles[0]+'" title="Minimize" /><img src="'+this.imagefiles[1]+'" title="Close" /></div>'
	domwindowdata+='</div>'
	domwindowdata+='<div class="drag-contentarea"></div>'
	domwindowdata+='<div id="Resizer_' + UUID + '" class="drag-statusarea"><div class="drag-resizearea" style="background: transparent url('+this.imagefiles[3]+') top right no-repeat;"></div></div>'
	domwindowdata+='</div>'
	domwindow.innerHTML=domwindowdata
	document.getElementById("dhtmlwindowholder").appendChild(domwindow)
	domwindow = null;
	//this.zIndexvalue=(this.zIndexvalue)? this.zIndexvalue+1 : 100 //z-index value for DHTML window: starts at 0, increments whenever a window has focus
	
	
	
	var t=document.getElementById(t)
	t.UUID = UUID;
	var divs=t.getElementsByTagName("div")
	for (var i=0; i<divs.length; i++){ //go through divs inside dhtml window and extract all those with class="drag-" prefix
		if (/drag-/.test(divs[i].className))
			t[divs[i].className.replace(/drag-/, "")]=divs[i] //take out the "drag-" prefix for shorter access by name
	}
	
	
	
	//t.style.zIndex=this.zIndexvalue //set z-index of this dhtml window
	t.handle._parent=t //store back reference to dhtml window
	t.resizearea._parent=t //same
	t.controls._parent=t //same
	t.onclose=function(){return true} //custom event handler "onclose"
	t.onmousedown=function(){dhtmlwindow.setfocus(this)} //Increase z-index of window when focus is on it
	t.handle.onmousedown=dhtmlwindow.setupdrag //set up drag behavior when mouse down on handle div
	t.resizearea.onmousedown=dhtmlwindow.setupdrag //set up drag behavior when mouse down on resize div
	t.controls.onclick=dhtmlwindow.enablecontrols
	t.show=function(){dhtmlwindow.show(this)} //public function for showing dhtml window
	t.restore=function(){dhtmlwindow.restore(this, t)} //public function for showing dhtml window
	t.hide=function(){dhtmlwindow.hide(this)} //public function for hiding dhtml window
	t.close=function(){dhtmlwindow.close(this)} //public function for closing dhtml window (also empties DHTML window content)
	t.setSize=function(w, h){dhtmlwindow.setSize(this, w, h)} //public function for setting window dimensions
	t.moveTo=function(x, y){dhtmlwindow.moveTo(this, x, y)} //public function for moving dhtml window (relative to viewpoint)
	t.isResize=function(bol){dhtmlwindow.isResize(this, bol)} //public function for specifying if window is resizable
	t.isScrolling=function(bol){dhtmlwindow.isScrolling(this, bol)} //public function for specifying if window content contains scrollbars
	t.load=function(contenttype, contentsource, title){dhtmlwindow.load(this, contenttype, contentsource, title)} //public function for loading content into window
	
	// ERA
	t.TitleDIV = GetID("Handle_" + t.UUID);
	t.refreshShadow=function(){dhtmlwindow.refreshShadow(t)}
	
	ExecuteFunctionOnceAfter( function() { t.refreshShadow() }, 5000) ;
	ExecuteFunctionOnceAfter( function() { t.refreshShadow() }, 7000) ;
	 
	this.tobjects[this.tobjects.length]=t;
	
	return t //return reference to dhtml window div
},

open:function(t, contenttype, contentsource, title, attr, recalonload){
	var d=dhtmlwindow //reference dhtml window object
	function getValue(Name){
		var config=new RegExp(Name+"=([^,]+)", "i") //get name/value config pair (ie: width=400px,)
		return (config.test(attr))? parseInt(RegExp.$1) : 0 //return value portion (int), or 0 (false) if none found
	}
	if (document.getElementById(t)==null) //if window doesn't exist yet, create it
		t=this.init(t) //return reference to dhtml window div
	else
		t=document.getElementById(t)
	this.setfocus(t)
	t.setSize(getValue(("width")), (getValue("height"))) //Set dimensions of window
	var xpos=getValue("center")? "middle" : getValue("left") //Get x coord of window
	var ypos=getValue("center")? "middle" : getValue("top") //Get y coord of window
	xpos=getValue("centerX")? "middle" : xpos //Get x coord of window
	ypos=getValue("centerY")? "middle" : ypos //Get y coord of window

	//t.moveTo(xpos, ypos) //Position window
	if (typeof recalonload!="undefined" && recalonload=="recal" && this.scroll_top==0){ //reposition window when page fully loads with updated window viewpoints?
		if (window.attachEvent && !window.opera) //In IE, add another 400 milisecs on page load (viewpoint properties may return 0 b4 then)
			this.addEvent(window, function(){setTimeout(function(){t.moveTo(xpos, ypos)}, 400)}, "load")
		else
			this.addEvent(window, function(){t.moveTo(xpos, ypos)}, "load")
	}
	t.isResize(getValue("resize")) //Set whether window is resizable
	t.isScrolling(getValue("scrolling")) //Set whether window should contain scrollbars
	t.style.visibility="visible"
	t.style.display="block"
	t.contentarea.style.display="block"
	t.moveTo(xpos, ypos) //Position window
	t.load(contenttype, contentsource, title)
	if (t.state=="minimized" && t.controls.firstChild.title=="Restore"){ //If window exists and is currently minimized?
		t.controls.firstChild.setAttribute("src", dhtmlwindow.imagefiles[0]) //Change "restore" icon within window interface to "minimize" icon
		t.controls.firstChild.setAttribute("title", "Minimize")
		t.state="fullview" //indicate the state of the window as being "fullview"
	}
	
		
	// ERA
	/*
	this.ModalCount++;
	if (this.ModalCount<2) {
		document.getElementById("dhtmlmodal").style.display = '';
		this.ModalHideBars = document.body.style.overflow;
		if (this.ModalHideBars == '') {
			this.ModalHideBars = 'scroll';
		}
		var st = document.body.scrollTop;
		document.body.style.overflow = 'hidden';
		document.getElementById("dhtmlmodal").style.top = st;
		document.body.scrollTop = st;
	}*/
	
	t.refreshShadow(t);

	return t
},

setSize:function(t, w, h){ //set window size (min is 150px wide by 100px tall)
	
	if (w + 20  > GetWindowWidth()) { // ERA
		w = GetWindowWidth() - 50;
	}

	t.style.width=Math.max(parseInt(w), 150)+"px"
	
	
	if (h + 75 > GetWindowHeight()) { // ERA
		h = GetWindowHeight() - 85;
	}
	
	t.contentarea.style.height=Math.max(parseInt(h), 100)+"px"
	// ERA
	t.refreshShadow(t);
}, 


// ERA 
refreshShadow:function(t){ //set window size (min is 150px wide by 100px tall)

	var ShadowWidthSpan = 10;
	var Height = GetID('DHTML_' + t.UUID).offsetHeight;
	var Width  = GetID('DHTML_' + t.UUID).offsetWidth;
	
	GetID('Shadow_Window_Left' + t.UUID).style.left 		= (ShadowWidthSpan * -1) + 1;	
	GetID('Shadow_Window_Left' + t.UUID).style.top 			= 0;
	GetID('Shadow_Window_Left_Img' + t.UUID).style.width	= 20;
	GetID('Shadow_Window_Left_Img' + t.UUID).style.height	= Height;
	
	GetID('Shadow_Window_Right' + t.UUID).style.left 		= Width - 1;	
	GetID('Shadow_Window_Right' + t.UUID).style.top 		= 0;	
	GetID('Shadow_Window_Right_Img' + t.UUID).style.width	= 20;
	GetID('Shadow_Window_Right_Img' + t.UUID).style.height	= Height;

	GetID('Shadow_Window_Top' + t.UUID).style.left 			= 0;	
	GetID('Shadow_Window_Top' + t.UUID).style.top 			= (ShadowWidthSpan * -1) + 2;	
	GetID('Shadow_Window_Top_Img' + t.UUID).style.width		= Width;
	GetID('Shadow_Window_Top_Img' + t.UUID).style.height	= 20;

	GetID('Shadow_Window_Bottom' + t.UUID).style.left 		= 0;	
	GetID('Shadow_Window_Bottom' + t.UUID).style.top 		= Height;
	GetID('Shadow_Window_Bottom_Img' + t.UUID).style.width	= Width;
	GetID('Shadow_Window_Bottom_Img' + t.UUID).style.height	= 20;
	
	if (!isIE) {
		GetID('Resizer_' + t.UUID).style.top  = Height - GetID('Resizer_' + t.UUID).offsetHeight - 3;
	} else {
		GetID('Resizer_' + t.UUID).style.top  = Height - GetID('Resizer_' + t.UUID).offsetHeight;
	}
	GetID('Resizer_' + t.UUID).style.left = Width - 13;
	
	if (t.offsetTop < -10) { t.moveTo(undefined, -10) }
	if (t.offsetTop > GetWindowHeight()-10) { t.moveTo(undefined, GetWindowHeight()-10) }
	if (t.offsetLeft < -150) { t.moveTo(-150) }
	if (t.offsetLeft > GetWindowWidth()-50) { t.moveTo(GetWindowWidth()-50) }
	
}, 

moveTo:function(t, x, y){ //move window. Position includes current viewpoint of document
	this.getviewpoint() //Get current viewpoint numbers
	
	if (x != undefined) {
		t.style.left=(x=="middle")? this.scroll_left+((this.docwidth-t.offsetWidth)/2)+"px" : this.scroll_left+parseInt(x)+"px"
	}
	
	if (y != undefined) {
		t.style.top=(y=="middle")? this.scroll_top+((this.docheight-t.offsetHeight)/2)+"px" : this.scroll_top+parseInt(y)+"px"
	}
	
	t.refreshShadow(t);
},

isResize:function(t, bol){ //show or hide resize inteface (part of the status bar)
	t.statusarea.style.display=(bol)? "block" : "none"
	t.resizeBool=(bol)? 1 : 0
},

isScrolling:function(t, bol){ //set whether loaded content contains scrollbars
	t.contentarea.style.overflow=(bol)? "auto" : "hidden"
},

load:function(t, contenttype, contentsource, title){ //loads content into window plus set its title (3 content types: "inline", "iframe", or "ajax")
	if (t.isClosed){
		alert("DHTML Window has been closed, so no window to load contents into. Open/Create the window again.")
		return
	}
	var contenttype=contenttype.toLowerCase() //convert string to lower case
	if (typeof title!="undefined")
		t.handle.firstChild.nodeValue=title
	if (contenttype=="inline")
		t.contentarea.innerHTML=contentsource
	else if (contenttype=="div"){
		var inlinedivref=document.getElementById(contentsource)
		t.contentarea.innerHTML=(inlinedivref.defaultHTML || inlinedivref.innerHTML) //Populate window with contents of inline div on page
		if (!inlinedivref.defaultHTML)
			inlinedivref.defaultHTML=inlinedivref.innerHTML //save HTML within inline DIV
		inlinedivref.innerHTML="" //then, remove HTML within inline DIV (to prevent duplicate IDs, NAME attributes etc in contents of DHTML window
		inlinedivref.style.display="none" //hide that div
	}
	else if (contenttype=="iframe"){
		t.contentarea.style.overflow="hidden" //disable window scrollbars, as iframe already contains scrollbars
		if (!t.contentarea.firstChild || t.contentarea.firstChild.tagName!="IFRAME") //If iframe tag doesn't exist already, create it first
			t.contentarea.innerHTML='<iframe src="" style="margin:0; padding:0; width:100%; height: 100%" name="_iframe-'+t.id+'" frameborder="0"></iframe>'
		window.frames["_iframe-"+t.id].location.replace(contentsource) //set location of iframe window to specified URL
		}
	else if (contenttype=="ajax"){
		//this.ajax_connect(contentsource, t) //populate window with external contents fetched via Ajax
		t.contentarea.innerHTML = "";
		GetHTTPAJAX(t.contentarea, contentsource);
	}
	t.contentarea.datatype=contenttype //store contenttype of current window for future reference
},



setupdrag:function(e){
	var d=dhtmlwindow //reference dhtml window object
	var t=this._parent //reference dhtml window div
	d.etarget=this //remember div mouse is currently held down on ("handle" or "resize" div)
	var e=window.event || e
	d.initmousex=e.clientX //store x position of mouse onmousedown
	d.initmousey=e.clientY
	d.initx=parseInt(t.offsetLeft) //store offset x of window div onmousedown
	d.inity=parseInt(t.offsetTop)
	d.width=parseInt(t.offsetWidth) //store width of window div
	d.contentheight=parseInt(t.contentarea.offsetHeight) //store height of window div's content div
	if (t.contentarea.datatype=="iframe"){ //if content of this window div is "iframe"
		t.style.backgroundColor="#F8F8F8" //colorize and hide content div (while window is being dragged)
		t.contentarea.style.visibility="hidden"
	}
	document.onmousemove=d.getdistance //get distance travelled by mouse as it moves
	document.onmouseup=function(){
		if (t.contentarea.datatype=="iframe"){ //restore color and visibility of content div onmouseup
			t.contentarea.style.backgroundColor="white"
			t.contentarea.style.visibility="visible"
		}
		d.stop()
	}
	
	
	return false
},

getdistance:function(e){
	var d=dhtmlwindow
	var etarget=d.etarget
	var e=window.event || e
	d.distancex=e.clientX-d.initmousex //horizontal distance travelled relative to starting point
	d.distancey=e.clientY-d.initmousey
	if (etarget.className.indexOf("drag-handle") > -1) //if target element is "handle" div
		d.move(etarget._parent, e)
	else if (etarget.className=="drag-resizearea") //if target element is "resize" div
		d.resize(etarget._parent, e)
	return false //cancel default dragging behavior
},

getviewpoint:function(){ //get window viewpoint numbers
	var ie=document.all && !window.opera
	var domclientWidth=document.documentElement && parseInt(document.documentElement.clientWidth) || 100000 //Preliminary doc width in non IE browsers
	this.standardbody=(document.compatMode=="CSS1Compat")? document.documentElement : document.body //create reference to common "body" across doctypes
	this.scroll_top=(ie)? this.standardbody.scrollTop : window.pageYOffset
	this.scroll_left=(ie)? this.standardbody.scrollLeft : window.pageXOffset
	this.docwidth=(ie)? this.standardbody.clientWidth : (/Safari/i.test(navigator.userAgent))? window.innerWidth : Math.min(domclientWidth, window.innerWidth-16)
	this.docheight=(ie)? this.standardbody.clientHeight: window.innerHeight
},

rememberattrs:function(t){ //remember certain attributes of the window when it's minimized or closed, such as dimensions, position on page
	this.getviewpoint() //Get current window viewpoint numbers
	t.lastx=parseInt((t.style.left || t.offsetLeft))-dhtmlwindow.scroll_left //store last known x coord of window just before minimizing
	t.lasty=parseInt((t.style.top || t.offsetTop))-dhtmlwindow.scroll_top
	t.lastwidth=parseInt(t.style.width) //store last known width of window just before minimizing/ closing
},

move:function(t, e){
	t.style.left=dhtmlwindow.distancex+dhtmlwindow.initx+"px"
	t.style.top=dhtmlwindow.distancey+dhtmlwindow.inity+"px"
	t.refreshShadow(t);
},

resize:function(t, e){
	t.style.width=Math.max(dhtmlwindow.width+dhtmlwindow.distancex, 150)+"px"
	t.contentarea.style.height=Math.max(dhtmlwindow.contentheight+dhtmlwindow.distancey, 100)+"px"
	t.refreshShadow(t);
	
	try { // ERA
		ResizeExecuteAll();
		ResizeExecuteAllDelay() 
	} catch(e) {}
},

enablecontrols:function(e){
	var d=dhtmlwindow
	var sourceobj=window.event? window.event.srcElement : e.target //Get element within "handle" div mouse is currently on (the controls)
	if (/Minimize/i.test(sourceobj.getAttribute("title"))) //if this is the "minimize" control
		d.minimize(sourceobj, this._parent)
	else if (/Restore/i.test(sourceobj.getAttribute("title"))) //if this is the "restore" control
		d.restore(sourceobj, this._parent)
	else if (/Close/i.test(sourceobj.getAttribute("title"))) //if this is the "close" control
		d.close(this._parent)
		
	this._parent.refreshShadow(this._parent);
	
	return false
},

minimize:function(button, t){
	dhtmlwindow.rememberattrs(t)
	button.setAttribute("src", dhtmlwindow.imagefiles[2])
	button.setAttribute("title", "Restore")
	t.state="minimized" //indicate the state of the window as being "minimized"
	t.contentarea.style.display="none"
	t.statusarea.style.display="none"
	if (typeof t.minimizeorder=="undefined"){ //stack order of minmized window on screen relative to any other minimized windows
		dhtmlwindow.minimizeorder++ //increment order
		t.minimizeorder=dhtmlwindow.minimizeorder
	}
	t.style.left="10px" //left coord of minmized window
	t.style.width="200px"
	var windowspacing=t.minimizeorder*10 //spacing (gap) between each minmized window(s)
	t.style.top=dhtmlwindow.scroll_top+dhtmlwindow.docheight-(t.handle.offsetHeight*t.minimizeorder)-windowspacing+"px"
},

restore:function(button, t){
	dhtmlwindow.getviewpoint()
	button.setAttribute("src", dhtmlwindow.imagefiles[0])
	button.setAttribute("title", "Minimize")
	t.state="fullview" //indicate the state of the window as being "fullview"
	t.style.display="block"
	t.contentarea.style.display="block"
	if (t.resizeBool) //if this window is resizable, enable the resize icon
		t.statusarea.style.display="block"
	t.style.left=parseInt(t.lastx)+dhtmlwindow.scroll_left+"px" //position window to last known x coord just before minimizing
	t.style.top=parseInt(t.lasty)+dhtmlwindow.scroll_top+"px"
	t.style.width=parseInt(t.lastwidth)+"px"
},


close:function(t){
	try{
		var closewinbol=t.onclose()
	}
	catch(err){ //In non IE browsers, all errors are caught, so just run the below
		var closewinbol=true
 }
	finally{ //In IE, not all errors are caught, so check if variable isn't defined in IE in those cases
		if (typeof closewinbol=="undefined"){
			alert("An error has occured somwhere inside your \"onclose\" event handler")
			var closewinbol=true
		}
	}
	if (closewinbol){ //if custom event handler function returns true
		if (t.state!="minimized") //if this window isn't currently minimized
			dhtmlwindow.rememberattrs(t) //remember window's dimensions/position on the page before closing
		if (window.frames["_iframe-"+t.id]) //if this is an IFRAME DHTML window
			window.frames["_iframe-"+t.id].location.replace("about:blank")
		else {
			t.contentarea.innerHTML=""
		}
		t.style.display="none"
		
		//Effect.Shrink('t');
		
		t.isClosed=true //tell script this window is closed (for detection in t.show())
		

			//ERA
		/*this.ModalCount--;
		if (this.ModalCount<1) {
			//document.getElementById("dhtmlmodal").style.display = 'none';
			document.body.style.overflow = this.ModalHideBars;
		}
		if (this.ModalCount<0) {
			this.ModalCount = 0;
		}*/
		
	}
	return closewinbol
},


setopacity:function(targetobject, value){ //Sets the opacity of targetobject based on the passed in value setting (0 to 1 and in between)

//ERA 4/21/2008
return


if (!targetobject)
		return
	if (targetobject.filters && targetobject.filters[0]){ //IE syntax
		if (typeof targetobject.filters[0].opacity=="number") //IE6
			targetobject.filters[0].opacity=value*100
		else //IE 5.5
			targetobject.style.filter="alpha(opacity="+value*100+")"
		}
	else if (typeof targetobject.style.MozOpacity!="undefined") //Old Mozilla syntax
		targetobject.style.MozOpacity=value
	else if (typeof targetobject.style.opacity!="undefined") //Standard opacity syntax
		targetobject.style.opacity=value
},

setfocus:function(t){ //Sets focus to the currently active window
	this.zIndexvalue++
	t.style.zIndex=this.zIndexvalue
	t.isClosed=false //tell script this window isn't closed (for detection in t.show())
	this.setopacity(this.lastactivet.handle, 0.5) //unfocus last active window
	this.setopacity(t.handle, 1) //focus currently active window
	this.lastactivet=t //remember last active window
},


show:function(t){
	if (t.isClosed){
		alert("DHTML Window has been closed, so nothing to show. Open/Create the window again.")
		return
	}
	if (t.lastx) //If there exists previously stored information such as last x position on window attributes (meaning it's been minimized or closed)
		dhtmlwindow.restore(t.controls.firstChild, t) //restore the window using that info
	else
		t.style.display="block"
	this.setfocus(t)
	t.state="fullview" //indicate the state of the window as being "fullview"
	
	t.refreshShadow(t);
},

hide:function(t){
	t.style.display="none"
},

ajax_connect:function(url, t){
	var page_request = false
	var bustcacheparameter=""
	if (window.XMLHttpRequest) // if Mozilla, IE7, Safari etc
		page_request = new XMLHttpRequest()
	else if (window.ActiveXObject){ // if IE6 or below
		try { 
		page_request = new ActiveXObject("Msxml2.XMLHTTP")
		} 
		catch (e){
			try{
			page_request = new ActiveXObject("Microsoft.XMLHTTP")
			}
			catch (e){}
		}
	}
	else
		return false
	t.contentarea.innerHTML=this.ajaxloadinghtml
	page_request.onreadystatechange=function(){dhtmlwindow.ajax_loadpage(page_request, t)}
	if (this.ajaxbustcache) //if bust caching of external page
		bustcacheparameter=(url.indexOf("?")!=-1)? "&"+new Date().getTime() : "?"+new Date().getTime()
	page_request.open('GET', url+bustcacheparameter, true)
	page_request.send(null)
},

ajax_loadpage:function(page_request, t){
	if (page_request.readyState == 4 && (page_request.status==200 || window.location.href.indexOf("http")==-1)){
	t.contentarea.innerHTML=page_request.responseText
	}
},


stop:function(){
	dhtmlwindow.etarget=null //clean up
	document.onmousemove=null
	document.onmouseup=null
},

addEvent:function(target, functionref, tasktype){ //assign a function to execute to an event handler (ie: onunload)
	var tasktype=(window.addEventListener)? tasktype : "on"+tasktype
	if (target.addEventListener)
		target.addEventListener(tasktype, functionref, false)
	else if (target.attachEvent)
		target.attachEvent(tasktype, functionref)
},

cleanup:function(){
	for (var i=0; i<dhtmlwindow.tobjects.length; i++){
		dhtmlwindow.tobjects[i].handle._parent=dhtmlwindow.tobjects[i].resizearea._parent=dhtmlwindow.tobjects[i].controls._parent=null
	}
	window.onload=null
}

} //End dhtmlwindow object



//ERA
//document.write('<div id="dhtmlmodal" class="modalwindow" style="display:none" onclick=""></div>'); // Modal BG

// NOT ERA
document.write('<div id="dhtmlwindowholder"><span style="display:none">.</span></div>'); 
	





	/***
	//
	//   Name: FormatPhone
	//	
	//	Parameters:
	//		
	//		
	*/	
	function FormatPhone (Field) {
		//field.value = Trim(field.value);
		Field = String(Field);
		
		var ov = CleanPhone(Field);
		var v = "";
		var Pre = "";
		var Start = -1;
		

		if (ov.charAt(0) == '1') {
			ov = ov.substring(1, ov.length);
		} else if (ov.charAt(0) == '+') { // Inter
			if (ov.charAt(3) =='0') {
				Pre = ov.substring(0, 4);
				ov = ov.substring(4, ov.length);
			} else {
				Pre = ov.substring(0, 3);
				ov = ov.substring(3, ov.length);
			}
		} else if (ov.charAt(0) == '0') { // Inter
			if (ov.charAt(2) =='0') {
				Pre = ov.substring(0, 3);
				ov = ov.substring(3, ov.length);
			} else {
				Pre = ov.substring(0, 2);
				ov = ov.substring(2, ov.length);
			}
		}


		// count number of digits
		var n = 0;
		for (i = 0; i < ov.length; i++) {
			var ch = ov.charAt(i);

			// build up formatted number
			if (ch >= '0' && ch <= '9' && ov.length >= 10) {
				if (n == 0) v += "(";
				else if (n == 3) v += ") ";
				else if (n == 6) v += "-";
				v += ch;
				n++;
			}

			if (ch >= '0' && ch <= '9' && ov.length < 10) {
				if (n == 3) v += "-";
				v += ch;
				n++;
			}
		}
		v += '                                                 ';
		if (ov.length >= 10) { 
			v =  Trim(v.substring(0, 14) + " x" + v.substring(14, 50));
		} else {
			v = Trim(v.substring(0, 8) + " x" + v.substring(8, 50));
		}
		
		if (v.charAt(v.length-1) == 'x') {
			v = Trim(v.substring(0, v.length-1));
		}
		
		return Trim(Pre + ' ' + v);
			
	}
	
	
	/***
	//
	//   Name: CleanPhone
	//	
	//	Parameters:
	//		
	//		
	*/
	function CleanPhone(Field) {
		Field = String(Field);
		var v = '';
		for (var i = 0; i < Field.length; i++) {
			var ch = Field.charAt(i);
			if (ch >= '0' && ch <= '9' || ch == '+') {
				v += ch;
			}
		}
		return v
	}


	/***
	//
	//   Name: CleanDate
	//	
	//	Parameters:
	//		
	//		
	*/
	function CleanDate(Field) {
		
		Field = String(Field);
		var v = '';
		for (var i = 0; i < Field.length; i++) {
			var ch = Field.charAt(i);
			if (ch >= '0' && ch <= '9' || ch == '/' || ch == '-') {
				v += ch;
			}
		}
		
		v = ReplaceStr(v, ' ', '');
		v = ReplaceStr(v, '-', '/');
		
		if (v.length == 6) {
			v = v.substr(0, 2) + '/' + v.substr(2, 2) + '/20' + v.substr(4, 2) 	
		}
		
		v = new Date(v);
		return v
	}
	
	
	

	/***
	//
	//   Name: ToProperCase
	//	
	//	Parameters:
	//		
	//		
	*/
	function ToProperCase(s)
	{
  	  s = String(s);
	  return s.toLowerCase().replace(/^(.)|\s(.)/g
							        , function($1) { return $1.toUpperCase(); });
	}
	
	
	/***
	//
	//   Name: EscapeUTF
	//	
	//	Parameters:
	//		
	//		
	*/
	function EscapeUTF(src) {
		var ret = "";
		for (i = 0; i < src.length; i++) {
			var ch = src.charCodeAt(i);
			if (ch <= 0x7F) {
				ret += escape(src.charAt(i));
			} else if (ch <= 0x07FF) {
				ret += '%' + ((ch >> 6) | 0xC0).toString(16) + '%' + ((ch & 0x3F) | 0x80).toString(16);
			} else if (ch >= 0x0800) {
				ret += '%' + ((ch >> 12) | 0xE0).toString(16) +
					   '%' + (((ch >> 6) & 0x3F) | 0x80).toString(16) + '%' + ((ch & 0x3F) | 0x80).toString(16);
			}
		}
		return ret;
	}


	/*
	 * Date Format 1.2.3
	 * (c) 2007-2009 Steven Levithan <stevenlevithan.com>
	 * MIT license
	 *
	 * Includes enhancements by Scott Trenda <scott.trenda.net>
	 * and Kris Kowal <cixar.com/~kris.kowal/>
	 *
	 * Accepts a date, a mask, or a date and a mask.
	 * Returns a formatted version of the given date.
	 * The date defaults to the current date/time.
	 * The mask defaults to dateFormat.masks.default.
	 
		 http://blog.stevenlevithan.com/archives/date-time-format
		 d	Day of the month as digits; no leading zero for single-digit days.
		dd	Day of the month as digits; leading zero for single-digit days.
		ddd	Day of the week as a three-letter abbreviation.
		dddd	Day of the week as its full name.
		m	Month as digits; no leading zero for single-digit months.
		mm	Month as digits; leading zero for single-digit months.
		mmm	Month as a three-letter abbreviation.
		mmmm	Month as its full name.
		yy	Year as last two digits; leading zero for years less than 10.
		yyyy	Year represented by four digits.
		h	Hours; no leading zero for single-digit hours (12-hour clock).
		hh	Hours; leading zero for single-digit hours (12-hour clock).
		H	Hours; no leading zero for single-digit hours (24-hour clock).
		HH	Hours; leading zero for single-digit hours (24-hour clock).
		M	Minutes; no leading zero for single-digit minutes.
		Uppercase M unlike CF timeFormat's m to avoid conflict with months.
		MM	Minutes; leading zero for single-digit minutes.
		Uppercase MM unlike CF timeFormat's mm to avoid conflict with months.
		s	Seconds; no leading zero for single-digit seconds.
		ss	Seconds; leading zero for single-digit seconds.
		l or L	Milliseconds. l gives 3 digits. L gives 2 digits.
		t	Lowercase, single-character time marker string: a or p.
		No equivalent in CF.
		tt	Lowercase, two-character time marker string: am or pm.
		No equivalent in CF.
		T	Uppercase, single-character time marker string: A or P.
		Uppercase T unlike CF's t to allow for user-specified casing.
		TT	Uppercase, two-character time marker string: AM or PM.
		Uppercase TT unlike CF's tt to allow for user-specified casing.
		Z	US timezone abbreviation, e.g. EST or MDT. With non-US timezones or in the Opera browser, the GMT/UTC offset is returned, e.g. GMT-0500
		No equivalent in CF.
		o	GMT/UTC timezone offset, e.g. -0500 or +0230.
		No equivalent in CF.
		S	The date's ordinal suffix (st, nd, rd, or th). Works well with d.
		No equivalent in CF.
		'…' or "…"	Literal character sequence. Surrounding quotes are removed.
		No equivalent in CF.
		UTC:	Must be the first four characters of the mask. Converts the date from local time to UTC/GMT/Zulu time before applying the mask. The "UTC:" prefix is removed.
		No equivalent in CF.
	 
	 */
	var dateFormat = function () {
		var	token = /d{1,4}|m{1,4}|yy(?:yy)?|([HhMsTt])\1?|[LloSZ]|"[^"]*"|'[^']*'/g,
			timezone = /\b(?:[PMCEA][SDP]T|(?:Pacific|Mountain|Central|Eastern|Atlantic) (?:Standard|Daylight|Prevailing) Time|(?:GMT|UTC)(?:[-+]\d{4})?)\b/g,
			timezoneClip = /[^-+\dA-Z]/g,
			pad = function (val, len) {
				val = String(val);
				len = len || 2;
				while (val.length < len) val = "0" + val;
				return val;
   			};

		// Regexes and supporting functions are cached through closure
		return function (date, mask, utc) {
			
			var dF = dateFormat;
			
			if (date.length == 6) {
				date = CleanDate(date);	
			}
			
	
			// You can't provide utc if you skip other args (use the "UTC:" mask prefix)
			if (arguments.length == 1 && Object.prototype.toString.call(date) == "[object String]" && !/\d/.test(date)) {
				mask = date;
				date = undefined;
			}
			
			var oDate = date;
	
			// Passing date through Date applies Date.parse, if necessary
			date = date ? new Date(date) : new Date;
			if (isNaN(date)) return oDate;
	
			mask = String(dF.masks[mask] || mask || dF.masks["default"]);
	
			// Allow setting the utc argument via the mask
			if (mask.slice(0, 4) == "UTC:") {
				mask = mask.slice(4);
				utc = true;
			}
	
			var	_ = utc ? "getUTC" : "get",
				d = date[_ + "Date"](),
				D = date[_ + "Day"](),
				m = date[_ + "Month"](),
				y = date[_ + "FullYear"](),
				H = date[_ + "Hours"](),
				M = date[_ + "Minutes"](),
				s = date[_ + "Seconds"](),
				L = date[_ + "Milliseconds"](),
				o = utc ? 0 : date.getTimezoneOffset(),
				flags = {
					d:    d,
					dd:   pad(d),
					ddd:  dF.i18n.dayNames[D],
					dddd: dF.i18n.dayNames[D + 7],
					m:    m + 1,
					mm:   pad(m + 1),
					mmm:  dF.i18n.monthNames[m],
					mmmm: dF.i18n.monthNames[m + 12],
					yy:   String(y).slice(2),
					yyyy: y,
					h:    H % 12 || 12,
					hh:   pad(H % 12 || 12),
					H:    H,
					HH:   pad(H),
					M:    M,
					MM:   pad(M),
					s:    s,
					ss:   pad(s),
					l:    pad(L, 3),
					L:    pad(L > 99 ? Math.round(L / 10) : L),
					t:    H < 12 ? "a"  : "p",
					tt:   H < 12 ? "am" : "pm",
					T:    H < 12 ? "A"  : "P",
					TT:   H < 12 ? "AM" : "PM",
					Z:    utc ? "UTC" : (String(date).match(timezone) || [""]).pop().replace(timezoneClip, ""),
					o:    (o > 0 ? "-" : "+") + pad(Math.floor(Math.abs(o) / 60) * 100 + Math.abs(o) % 60, 4),
					S:    ["th", "st", "nd", "rd"][d % 10 > 3 ? 0 : (d % 100 - d % 10 != 10) * d % 10]
				};
	
			return mask.replace(token, function ($0) {
				return $0 in flags ? flags[$0] : $0.slice(1, $0.length - 1);
			});
		};
	}();
	
	// Some common format strings
	dateFormat.masks = {
		"default":      "ddd mmm dd yyyy HH:MM:ss",
		shortDate:      "m/d/yy",
		mediumDate:     "mmm d, yyyy",
		longDate:       "mmmm d, yyyy",
		fullDate:       "dddd, mmmm d, yyyy",
		shortTime:      "h:MM TT",
		mediumTime:     "h:MM:ss TT",
		longTime:       "h:MM:ss TT Z",
		isoDate:        "yyyy-mm-dd",
		isoTime:        "HH:MM:ss",
		isoDateTime:    "yyyy-mm-dd'T'HH:MM:ss",
		isoUtcDateTime: "UTC:yyyy-mm-dd'T'HH:MM:ss'Z'"
	};
	
	// Internationalization strings
	dateFormat.i18n = {
		dayNames: [
			"Sun", "Mon", "Tue", "Wed", "Thu", "Fri", "Sat",
			"Sunday", "Monday", "Tuesday", "Wednesday", "Thursday", "Friday", "Saturday"
		],
		monthNames: [
			"Jan", "Feb", "Mar", "Apr", "May", "Jun", "Jul", "Aug", "Sep", "Oct", "Nov", "Dec",
			"January", "February", "March", "April", "May", "June", "July", "August", "September", "October", "November", "December"
		]
	};
	
	// For convenience...
	Date.prototype.format = function (mask, utc) {
		return dateFormat(this, mask, utc);
	};

	Date.prototype.TIFormat = function() {
		return dateFormat(this, 'mm/dd/yyyy');
	}
	
	TIDateFormat = function(value) {
		if (value != '') {
			return IsValidDate(value) ? dateFormat(value, 'mm/dd/yyyy') : value;
		} else {
			return ''
		}
	}
	
	StdDateFormat = function(value) {

		if (value != '') {
			return IsValidDate(value) ? dateFormat(value, HG_DateFormat) : value;
		} else {
			return ''
		}
	}
	
	StdDateDayFormat = function(value) {

		if (value != '') {
			return IsValidDate(value) ? dateFormat(value, HG_DateDayFormat) : value;
		} else {
			return ''
		}
	}
	
	StdDateTimeFormat = function(value) {
		
		
		if (value != '') {
			return IsValidDate(value) ? dateFormat(value, HG_DateTimeFormat) : value;
		} else {
			return ''
		}
	}
	
	StdDateTimeFormatDay = function(value) {
		
		
		if (value != '') {
			return IsValidDate(value) ? dateFormat(value, HG_DateTimeFormatDay) : value;
		} else {
			return ''
		}
	}

	/***
	//
	//   Name: FormatTextFieldForHTML
	//	
	//	Parameters:
	//		
	//		
	*/
	FormatTextFieldForHTML = function(Value, BindObject, crlf) {
		if (crlf == undefined) {
			crlf = 10;
		}
		return ReplaceStr(Value, String.fromCharCode(crlf), '<br>');
	}
	
	
	
	/***
	//
	//   Name: FormatTextFieldForInput
	//	
	//	Parameters:
	//		
	//		
	*/
	FormatTextFieldForInput = function(Value, BindObject, BR) {
		
		if (BR == undefined) {
			BR = '<br>';
		}
		
		return ReplaceStr(Value, BR, String.fromCharCode(10));
	}
	
	
	/***
	//
	//   Name: FormatCurrency - Format Number as Currency In Users Language Format
	//	
	//	Parameters:
	//		
	//		
	*/
	FormatCurrency = function(Value) {
		return HG_CurrencyFormat(Value, HG_ThouDel, HG_DecDel, (HG_LangID=='en'));
	}
	
	
	/***
	//
	//   Name: FormatCurrencyABS - Format Number as Currency In Users Language Format
	//	
	//	Parameters:
	//		
	//		
	*/
	FormatCurrencyABS = function(Value) {
		return FormatCurrency(ReplaceStr(Value, '-', ''));
	}
	
	
	/***
	//
	//   Name: FormatCurrencyToUS - Format Currency Back To USD Format
	//	
	//	Parameters:
	//		
	//		
	*/
	FormatCurrencyToUS = function(Value) {
		return HG_CurrencyToNumber(Value, HG_ThouDel, HG_DecDel, (HG_LangID=='en'));
	}
	
	/***
	//
	//   Name: FormatCurrencyToUSABS - Format Currency Back To USD Format
	//	
	//	Parameters:
	//		
	//		
	*/
	FormatCurrencyToUSABS = function(Value) {
		return FormatCurrencyToUS(ReplaceStr(Value, '-', ''));
	}
		
	
	
	
	
	/***
	//
	//   Name: FormatWithTab - Add A Tab To Text if The Tab Key pressed
	//	
	//	Parameters:
	//		
	//		
	*/
	// Set desired tab- defaults to four space softtab
	var _FormatTabSize = "    ";
       
	function FormatWithTab(evt) {
		var t = evt.target;
		var ss = t.selectionStart;
		var se = t.selectionEnd;
	 
		// Tab key - insert _FormatTabSize expansion
		if (evt.keyCode == 9) {
			//evt.preventDefault();
				   
			// Special case of multi line selection
			if (ss != se && t.value.slice(ss,se).indexOf("\n") != -1) {
				// In case selection was not of entire lines (e.g. selection begins in the middle of a line)
				// we ought to _FormatTabSize at the beginning as well as at the start of every following line.
				var pre = t.value.slice(0,ss);
				var sel = t.value.slice(ss,se).replace(/\n/g,"\n"+_FormatTabSize);
				var post = t.value.slice(se,t.value.length);
				t.value = pre.concat(_FormatTabSize).concat(sel).concat(post);
					   
				t.selectionStart = ss + _FormatTabSize.length;
				t.selectionEnd = se + _FormatTabSize.length;
			}
				   
			// "Normal" case (no selection or selection on one line only)
			else {
				t.value = t.value.slice(0,ss).concat(_FormatTabSize).concat(t.value.slice(ss,t.value.length));
				if (ss == se) {
					t.selectionStart = t.selectionEnd = ss + _FormatTabSize.length;
				}
				else {
					t.selectionStart = ss + _FormatTabSize.length;
					t.selectionEnd = se + _FormatTabSize.length;
				}
			}
			return StopEvent(evt);
		}
			   
		// Backspace key - delete preceding _FormatTabSize expansion, if exists
	   else if (evt.keyCode==8 && t.value.slice(ss - 4,ss) == _FormatTabSize) {
			//evt.preventDefault();
				   
			t.value = t.value.slice(0,ss - 4).concat(t.value.slice(ss,t.value.length));
			t.selectionStart = t.selectionEnd = ss - _FormatTabSize.length;
			
			return StopEvent(evt);
		}
			   
		// Delete key - delete following _FormatTabSize expansion, if exists
		else if (evt.keyCode==46 && t.value.slice(se,se + 4) == _FormatTabSize) {
			//evt.preventDefault();
				 
			t.value = t.value.slice(0,ss).concat(t.value.slice(ss + 4,t.value.length));
			t.selectionStart = t.selectionEnd = ss;
			return StopEvent(evt);
		}
		// Left/right arrow keys - move across the _FormatTabSize in one go
		else if (evt.keyCode == 37 && t.value.slice(ss - 4,ss) == _FormatTabSize) {
			//evt.preventDefault();
			t.selectionStart = t.selectionEnd = ss - 4;
			
			return StopEvent(evt);
		}
		else if (evt.keyCode == 39 && t.value.slice(ss,ss + 4) == _FormatTabSize) {
			//evt.preventDefault();
			t.selectionStart = t.selectionEnd = ss + 4;
			
			return StopEvent(evt);
		}
		
		
		
		
	}


	/***
	//
	//   Name: FormatJSEscaped
	//		Escape Javascript Code before sending to JSON
	//	Parameters:
	//		
	//		
	*/
	FormatJSEscaped = function(JSScript) {
		
		JSScript = escape(JSScript);
		
		return JSScript;
			
	}
	
	
	
	/***
	//
	//   Name: ToNumber
	//		Return typeof Number Value or 0
	//	Parameters:
	//		
	//		
	*/
	ToNumber = function(Value) {
		
		if (IsNumber(Value) == true) {
			return Number(Value);
		} else {
			return 0;
		}
	}
	
	
	/***
	//
	//   Name: ToABSNumber
	//		Return typeof Number Value or 0
	//	Parameters:
	//		
	//		
	*/
	ToABSNumber = function(Value) {
		
		if (IsNumber(Value) == true) {
			return Math.abs(Number(Value));
		} else {
			return 0;
		}
	}
	
	
	/***
	//
	//   Name: ToNumber
	//		Return typeof Number Value or 0
	//	Parameters:
	//		
	//		
	*/
	FormatNumberOr = function(Value, Eq, Replace) {
		
		if (IsNumber(Value) == true) {
			if (Number(Value) == Eq) { 
				return Replace 
			} else {
				return Value
			}
		} else {
			return Value;
		}
	}
	
		/***
	//
	//   Name: ToNumber
	//		Return typeof Number Value or 0
	//	Parameters:
	//		
	//		
	*/
	FormatNumberOrSpace = function(Value) {
		
		return FormatNumberOr(Value, 0, '&nbsp;');

	}
	
	
	
	
	

function StopEvent(e){
	
	 var evt=window.event || e
	 if (evt.preventDefault) //supports preventDefault?
	  evt.preventDefault()
	 else //IE browser
	  return false
	  
}




KeyDown_Enter = function(e) {
	
	var keynum = (e.which) ? e.which : e.keyCode
	
	if (keynum == 13) {		// enter
		return true
	} 
	return false

}


	/***
	//
	//   Name: CalculateDays
	//	
	//	Parameters:
	//		date1
	//		date2
	//		part	-- [(D)ay], (H)our, (M)in, (S)ec
	*/
	function Calculate_DateDiff(date1, date2, part){ 
	
		if (part == undefined) {
			part = 'D';
		}
		
		part = part.toUpperCase();
		var time1 = GetToken(date1, 2, ' ');
		var time2 = GetToken(date2, 2, ' ');
		date1 = GetToken(date1, 1, ' ');
		date2 = GetToken(date2, 1, ' ');

		
	   if (date1.indexOf("-") != -1) { date1 = date1.split("-"); } else if (date1.indexOf("/") != -1) { date1 = date1.split("/"); } else { return 0; } 
	   if (date2.indexOf("-") != -1) { date2 = date2.split("-"); } else if (date2.indexOf("/") != -1) { date2 = date2.split("/"); } else { return 0; } 
	   
	   if (parseInt(date1[0], 10) >= 1000) { 
		   var sDate = new Date(date1[0]+"/"+date1[1]+"/"+date1[2] + ' ' + time1); 
	   } else if (parseInt(date1[2], 10) >= 1000) { 
		   var sDate = new Date(date1[2]+"/"+date1[0]+"/"+date1[1] + ' ' + time1); 
	   } else { 
		   return 0; 
	   } 
	   
	   if (parseInt(date2[0], 10) >= 1000) { 
		   var eDate = new Date(date2[0]+"/"+date2[1]+"/"+date2[2] + ' ' + time2); 
	   } else if (parseInt(date2[2], 10) >= 1000) { 
		   var eDate = new Date(date2[2]+"/"+date2[0]+"/"+date2[1] + ' ' + time2); 
	   } else { 
		   return 0; 
	   } 
	   
	   if (part == 'D') {
		   var one_day = 1000*60*60*24; 
	   } else if (part == 'H') {
		   var one_day = 1000*60*60; 
	   } else if (part == 'M') {
		   var one_day = 1000*60; 
	   } else if (part == 'S') {
		   var one_day = 1000; 
	   }
	

	   
	   var daysApart = HG_RoundNumber((eDate.getTime()-sDate.getTime())/one_day, 0); 

	   if (sDate.getTime() > eDate.getTime()) {
			daysApart = daysApart * -1;
	   };
	   
	   return daysApart; 
	} 




	/***
	//
	//   Name: Calculate_DateAdd
	//	
	//	Parameters:
	//		date1
	//		Days
	*/
	function Calculate_DateAdd(date1, Days){ 
		//
		// Parse into an array
		//
		if (date1.indexOf("-") != -1) { 
			date1 = date1.split("-"); 
		} else if (date1.indexOf("/") != -1) { 
			date1 = date1.split("/"); 
		} else { return 0; } 
		
		Days        = Number(Days);
		var one_day = 1000*60*60*24;

		// Is Year 1st
		if (parseInt(date1[0], 10) >= 1000) { 
		   var sDate = new Date(date1[0]+"/"+date1[1]+"/"+date1[2]); 
		} else if (parseInt(date1[2], 10) >= 1000) { 
		   var sDate = new Date(date1[2]+"/"+date1[0]+"/"+date1[1]); 
		} else { 
		   return 0; 
		} 
		
		sDate = Date.UTC(sDate.getFullYear(), sDate.getMonth(), sDate.getDate());

		return StdDateFormat(sDate + (one_day * (Days + 1))); 
	   
	}
	

	/***
	//
	//   Name: Calculate_DateMonthAdd
	//	
	//	Parameters:
	//		date1
	//		Months
	*/
	function Calculate_DateMonthAdd(date1, Months){ 

		t = new Date (d);
		 t.setMonth(d.getMonth()+ Months) ;
		 if (t.getDate() < d.getDate())
		{
		   t.setDate(0);
		 }
		 return StdDateFormat(t);
	
	} 
	
	

 	/***
	//
	//   Name: Calculate_NaturalSort -- Called be Array.sort(Calculate_NaturalSort);
			If sort Objects Use Calculate_NaturalSortObject
	//	
	//	Parameters:
	//		a
	//		b
	*/
	function Calculate_NaturalSort (a, b) {
			// setup temp-scope variables for comparison evauluation
			var x = a.toString().toLowerCase() || '', y = b.toString().toLowerCase() || '',
					nC = String.fromCharCode(0),
					xN = x.replace(/([-]{0,1}[0-9.]{1,})/g, nC + '$1' + nC).split(nC),
					yN = y.replace(/([-]{0,1}[0-9.]{1,})/g, nC + '$1' + nC).split(nC),
					xD = (new Date(x)).getTime(), yD = (new Date(y)).getTime();

			// natural sorting of dates
			if ( xD && yD && xD < yD )
					return -1;
			else if ( xD && yD && xD > yD )
					return 1;
			
			// natural sorting through split numeric strings and default strings
			for ( var cLoc=0, numS = Math.max( xN.length, yN.length ); cLoc < numS; cLoc++ )
					if ( ( parseFloat( xN[cLoc] ) || xN[cLoc] ) < ( parseFloat( yN[cLoc] ) || yN[cLoc] ) )
							return -1;
					else if ( ( parseFloat( xN[cLoc] ) || xN[cLoc] ) > ( parseFloat( yN[cLoc] ) || yN[cLoc] ) )
							return 1;
			return 0;
			
	}
	
	
 	/***
	//
	//   Name: Calculate_NaturalSortObject -- Called be Array.sort(Calculate_NaturalSort);
	//	
	//	Parameters:
	//		Value1
	//		Value1
	//		Name	- Object Ref Name
	//		Direction - 1 or -1=(DESC)
	*/
	function Calculate_NaturalSortObject(Value1, Value2, Name, Direction) {
		var Res = Calculate_NaturalSort(Value1[Name], Value2[Name]);
		return Res * Direction;
	}
	
	
	



	/***
	//
	//   Name: FormatLoyaltyRatingWithIcon
	//	
	//	Parameters:
	//		
	//		
	*/	
	function FormatLoyaltyRatingWithIcon (Value) {

		var Str = '<img src="/Images/GuestLoyaltyRating16x16.png" align="absmiddle">&nbsp;' + Value;
		return Str;
	}
	
	
	/***
	//
	//   Name: FormatDNRStatusWithIcon
	//	
	//	Parameters:
	//		
	//		
	*/	
	function FormatDNRStatusWithIcon (Value) {

		var Str = '<img src="/Images/DNRNetwork16x16.png" align="absmiddle">&nbsp;' + Value;
		return Str;
	}

	/***
	//
	//   Name: 
	//	
	//	Parameters:
	//		
	//		
	*/
	function IsValidEmail(email) {
        if (!email) return false;
        email = email.toLowerCase();
        var components = email.split('@');
        if (components.length != 2) return false;
		if (components[0].length == 0) return false;
        if (components[1].indexOf('.') < 0) return false;
		var domain = components[1].split('.');
		if (domain[1].length == 0) return false;
		if (domain[0].length == 0) return false;
		
        return true;
    }
	
	
	
	/***
	//
	//   Name: 
	//	
	//	Parameters:
	//		
	//		
	*/
	 function IsValidEmailList(email,list) {
        if (!email) return false;
        email = email.toLowerCase();
        var components = email.split('@');
        if (components.length != 2) return false;
		if (components[0].length == 0) return false;
        if (components[1].indexOf('.') < 0) return false;
		var domain = components[1].split('.');
		if (domain[1].length == 0) return false;
		if (domain[0].length == 0) return false;
		
        if (list) {
            var items = list.split(',');
            for (var i = 0; i < items.length; i++) {
                var domain = items[i];
                if (components[1] == domain) return true;
                if ((components[1].indexOf(domain, components[1].length - domain.length) > 0) &&
                    (components[1].charAt(components[1].length - domain.length - 1) == '.')) return true;
            }
            return false;
        }
        return true;
    }
	
	/***
	//
	//   Name: IsValidDate
	//	
	//	Parameters:
	//		TheDate - String Date
	//		
	*/
	function IsValidDate(TheDate) {

		if (TheDate.length == 6) {
			TheDate = CleanDate(TheDate);	
		}

		// Passing date through Date applies Date.parse, if necessary
		TheDate = TheDate ? new Date(TheDate) : new Date;
		if (isNaN(TheDate)) 
			return false
		else return true

		
	}
	


	/***
	//
	//   Name: IsLength
	//	
	//	Parameters:
	//		TheDate - String Date
	//		
	*/
	function IsLength(Value, Length, Message) {

		try {
			var Ret = (String(Value).length >= Number(Length))
		} catch(e) {
			var Ret = false	
		}
		if (!Ret && String(Message).length > 0 && Message != undefined) {
			alert(Message + ' (' + Value +')');
			return -1;
		}
		
		return Ret;
		
	}
	
	
	
	
	/***
	//
	//   Name: IsNumber
	//	
	//	Parameters:
	//		Value -- Number
	//		
	*/
	function IsNumber(Value) {
	
		return !isNaN(Number(Value));
	
	}
		
		
	/***
	//
	//   Name: IsPositiveNumber
	//	
	//	Parameters:
	//		Value -- Number
	//		Min -- Has to be greater than equal to
	//		
	*/
	function IsPositiveNumber(Value, Min) {
		
		if (Min == undefined ) {
			Min = 0;	
		}

		if (IsNumber(Value) == false) {
			return false	
		}

		if (Value < Min) {
			return false;	
		} else {
			return true
		}
		
	}
	

	
	
	function events() {
	
		this.Events = new Object();

	}
	
	
	
	//
	//
	//
	events.prototype.Add = function(Event) {
	
		if (Event['toArray'] != undefined) {
			for (var Index = 0; Index<Event.toArray().length;Index++) {
				this.AddOne(Event[Index]);
			} 
		} else {
			this.AddOne(Event);
		}
		
	}

	//
	//
	//
	events.prototype.AddOne = function(Event) {
		
		var EventID = Event.id;
		
		if (Event.Function == undefined) {
			alert('Developer: Event [' + Event.Event + '] Does Not Have A Function Assigned');
			return;
		}
		
		if (!Event.Suspended) {
			if (this.Events[EventID] == undefined) {
				this.Events[EventID] = new Object;
			}
			if (this.Events[EventID][Event.Event] == undefined) {
				this.Events[EventID][Event.Event] = new Object;
			}
			if (this.Events[EventID][Event.Event][Event.Function] == undefined) {
				this.Events[EventID][Event.Event][Event.Function] = Event;
			} else {
				this.Remove(EventID, Event.Event, Event.Function);
			}
		}
		
		if (EventID == 'window') {
			var EventObj = window;	
		} else {
			var EventObj = GetID(EventID);
		}
		
		try {
		if (isIE || isOpera) {
			EventObj.attachEvent("on" + Event.Event.toLowerCase(), Event.Function);
		} else {
			EventObj.addEventListener(Event.Event.toLowerCase(), Event.Function, true);
		}	
		} catch(e) { Dump(Event, 'Event.js Error') }
		
		Event.Suspend   = false;
		Event.Suspended = false;
	}

	
	//
	//
	//
	events.prototype.Remove = function(EventID, Event, Function) {
		
		var TheEvent = this.Events[EventID][Event][Function];
		
		if (TheEvent == undefined || TheEvent.Suspended == true) {
			return;
		}
		
		if (EventID == 'window') {
			var EventObj = window;	
		} else {
			var EventObj = GetID(EventID);
		}

		if (isIE) {
			EventObj.detachEvent("on" + Event.toLowerCase(), TheEvent.Function);
		} else {
			EventObj.removeEventListener(Event.toLowerCase(), TheEvent.Function, true);
		}
		
		if (!TheEvent.Suspend) {
			delete TheEvent;
		} else {
			TheEvent.Suspended = true;
		}
		
	}
	
	//
	//
	//
	events.prototype.RemoveAll = function(EventID) {
		
		var TheEvent = this.Events[EventID];
		if (TheEvent == undefined) { return false }
		
		//  Add All to Bind
		for (var Eve in TheEvent) {
			for (var Func in TheEvent[Eve]) {
				this.Remove(EventID, Eve, Func);
			}
		}
		
	}
	
	//
	//
	//
	events.prototype.Suspend = function(EventID, Event) {
		
		var TheEvent = this.Events[EventID][Event];
		
		if (TheEvent == undefined) { return false }
		
		TheEvent.Suspend = true;
		this.Remove(EventID, Event);
	}
	
	//
	//
	//
	events.prototype.Resume = function(EventID, Event) {
		
		var TheEvent = this.Events[EventID][Event];
		
		if (TheEvent == undefined) { return false }
		
		TheEvent.Suspend = false;
		this.Add(TheEvent);
	}
	
	
	//
	//
	//
	events.prototype.Destroy = function() {
		//  Remove All to Bind
		for (var Eve in this.Events) {
			this.RemoveAll(Eve);
			delete this.Events[Eve];
		}
	}
	
	//
	//
	//
	events.prototype._UnloadDestroy = function() {
		//  Remove All to Bind
		for (var Eve in this.Events.Events) {
			this.Events.RemoveAll(Eve);
			delete this.Events.Events[Eve];
		}
	}
	
	//
	//
	//
	Events = new events();
	Events.Add({id:'window', Event:'unload', Function:Events._UnloadDestroy});

	
	
	

	/***
	//
	//   Name: _GlobalBindings - Object Array of all Binding Objects in use
	//	
	*/
	var _GlobalBindings = new Object();
	var BindDebug = false;

	
	/***
	//
	//   Name: Bind - Initializer for Binding
	//		Usage: MyBind = new Bind('MyBind');
	//				MyBind.Add({...}) -- See Add
	//	
	//	Parameters:
	//		BindName	  -- Unique Name for Above Array
	//		ClearPrevious -- Not Implementated
	*/
	function Bind (BindName, ClearPrevious) {
	
	
		//
		//	If Bind New Create
		//
		if (_GlobalBindings[BindName] == undefined || ClearPrevious == false) {
			this.Bindings 	= new Object();
			this.Events 	= new events();
		} else {
			//
			//	Exists? Remove and 
			//
			//this.RemoveAll();	// NOT DONE******
			this.Bindings 	= new Object();
			this.Events 	= new events();
		}
		
		//
		//	Defaults
		//
		this.FieldClass 		= 'AppInputCell';
		this.FieldStyle 		= '';
		this.PreviewClass 		= 'AppPreviewCell';
		this.PreviewStyle 		= '';
		this.LabelClass 		= 'AppInputLabel';
		this.LabelStyle 		= '';
		this.BlankFieldClass	= 'AppBlankFormInput';
		this.RequiredFieldClass	= ' AppRequired ';
		this.InvalidClass		= ' AppInvalidValue ';
		this.AllRequired		= false;
		this.AllValidated		= false;
		this.Modified 			= false;
		this.id					= BindName;
			
		//
		// Add to Global
		//
		_GlobalBindings[BindName] = this;
		
	}
	
	
	
	/***
	//
	//   Name: Add - Add Binding fields from provided Object
	//		Usage: MyBind.Add(BindObject);
	//	
	//	Parameters:
	//		BindObject	  -- In Any Order
			[{	id			- Unique Field ID
			 ,	Target		- Container ID || Target Label/Field Container Will Become {Target}_Label, {Target}_Field, {Target}_View, {Target}_Format
			 ,	Value		- Sets Inital Value
			 ,	Type 		- Any HTML Input/TextArea Type
			 ,  Label		- The label of the field
 			 ,  LabelContainer - The Parent ContainerID holding the Label Container
			 ,  FieldContainer - The Parent ContainerID holding the Field Container
			 ,	FieldStyle	- string of HTML style || ex. width:10px; font-size:11px;
			 ,	FieldClass	- Class String
			 ,	LabelStyle	- string of HTML style || ex. width:10px; font-size:11px;
			 ,	LabelClass	- Class String
			 ,	Required	- 1 | 0
			 ,  Locked		- 1 | 0 
			 ,  Invisible	- 1 | 0 
			 ,	InputFormat	- Display Format
			 ,	BlankText	- Tool Tip and Text Displayed in field when it is blank
			 , 	BindField	- String Pointer to a JSON Object
			 ,	Elements	- Any support HTML Element/Attrib for the given {Type}
			 ,	Cleaner		- A Function that will clean the data before updating data bind source || This Value and this BindObject will be passed to function
			 ,	Changer 	- A Function that will fire when the value changes
			 ,	Validator	- A Function that will Validate the data before updating data bind source. If Validation failes no update to data bind source will occur
			 					|| This Value and this BindObject will be passed to function
			 ,  Focuser		- A Function that will fire when entering the the field for editing.
			 ,  Keyer		- A Function that will fire when Key Down is done
			 ,  ValidatorMessage - Alert Message if invalid
			 ,	Formatter	- A Function that will format the data before updating data bind source || This Value and this BindObject will be passed to function
			 ,  Previewer	- A Function that will fire before the display of the preview value
		    }]
			
	*/
	Bind.prototype.Add = function(BindObject) {

		if (BindObject['toArray'] != undefined) {
			
			//
			//   Loop over an array if user provided an array of fields to add
			//
			for (var Index = 0; Index<BindObject.toArray().length;Index++) {
				this.Bindings[BindObject[Index].id] = BindObject[Index];
				BindObject[Index].Initialized = false;
				BindObject[Index].Validated   = 1;
				
				//
				//   Create the Field
				//
				this.ConstructField(BindObject[Index].id);
				
				BindObject[Index].Initialized = true;
			}
		} else {
			//
			//   Create A Single Field
			//
			this.Bindings[BindObject.id] = BindObject;
			BindObject.Initialized 	= false;
			BindObject.Validated   	= 1;

			//
			//   Create the Field
			//
			this.ConstructField(BindObject.id);
			BindObject.Initialized = true;
		}
		
	}



	/***
	//
	//   Name: ConstructField - Actually creates the dynamic HTML for the input field
	//			Usually called by Add
	//	Parameters:
	//		BindID	  -- Unique Name for Above Array
	//		
	*/
	Bind.prototype.ConstructField = function(BindID) {
		
		var BindObject = this.Bindings[BindID];
		if (BindObject == undefined) { return false; }


		if (BindObject['Value'] == undefined) { 
			BindObject.Value = ''
		}


		if (BindObject.Type.toUpperCase() == 'TEXTAREA') {
			var ElementType = 'textarea';
			var EndElement  = '</textarea>';
		} else if (BindObject.Type.toUpperCase() == 'SELECT') {
			var ElementType = 'select';
			var EndElement  = '</select>';
		} else if (BindObject.Type.toUpperCase() == 'DIV') {
			var ElementType = 'div';
			var EndElement  = '</div>';
		} else if (BindObject.Type.toUpperCase() == 'DIVSHOW') {
			var ElementType = 'div';
			var EndElement  = '</div>';
			BindObject.Type = 'div';
			BindObject.Locked = 2;
		} else if (BindObject.Type.toUpperCase() == 'AJAX') {
			var ElementType = 'div';
			var EndElement  = '</div>';
		} else if (BindObject.Type.toUpperCase() == 'SPAN') {
			var ElementType = 'span';
			var EndElement  = '</span>';
		} else if (BindObject.Type.toUpperCase() == 'IFRAME') {
			var ElementType = 'iframe';
			var EndElement  = '</iframe>';
		} else if (BindObject.Type.toUpperCase() == 'BUTTON') {
			var ElementType = 'button';
			var EndElement  = '</button>';
		} else if (BindObject.Type.toUpperCase() == 'IMG') {
			var ElementType = 'img';
			var EndElement  = '';
		} else { 
			var ElementType = 'input type="' + BindObject.Type + '" ';
			var EndElement  = '';
		}
		
		// Construct HTML Tag
		var Input = '<' + ElementType + ' id="' + Trim(BindObject.id) + '" style="' + BindObject.FieldStyle + '; display:none; " ';
			
		//  Add Any Passed Html Elements
		if (typeof(BindObject.Elements) == 'object') {
			for (var Element in BindObject.Elements) {
				Input += Element + '="' + BindObject.Elements[Element]+ '" ';
			}
		} else {
			if (BindObject.Elements != undefined) {
				Input += BindObject.Elements;
			}
		}
		Input += '>' + EndElement;

		if (BindObject.PreviewTag == undefined) {
			BindObject.PreviewTag = 'span';
		}
		
		
		if (BindObject.PreviewValue == undefined) {
			BindObject.PreviewValue = ''
		}
		
		if (BindObject.Type.toUpperCase() != 'IMG') {
			//  Create the Reaonly View container
			Input += '<' + BindObject.PreviewTag + ' id="' + Trim(BindObject.Target) + '_View" style="display:none;">' + BindObject.PreviewValue + '</' + BindObject.PreviewTag + '>';
		} else {
			// Convert Img Tag to Div but move Original Img Tag to Preview
			var OrgInput = Input;
			Input = ReplaceStr(ReplaceStr(Input, '<' + ElementType, '<div'), BindObject.id, BindObject.id + '_ImgInput')+'</div>'
				  + '<' + BindObject.PreviewTag + '  id="' + Trim(BindObject.Target) + '_View" style="display:none;">' + OrgInput + '</' + BindObject.PreviewTag + '>';
				  
			BindObject.ImgInput = BindObject.id + '_ImgInput';
		}
		
		
		if (BindObject.BlankText == undefined) {
			BindObject.BlankText = '';
		}
		
		
		if (BindObject.BindField == undefined) {
			BindObject.BindField = '';
		}
		
		//  Create Pointer References
		BindObject.LabelContainerID	= BindObject.LabelContainer;
		BindObject.FieldContainerID	= BindObject.FieldContainer;
		BindObject.LabelID 			= BindObject.Target + '_Label';
		BindObject.FieldID 			= BindObject.Target + '_Field';
		BindObject.ViewID  			= BindObject.Target + '_View';
		BindObject.DataObject 	 	= eval(GetToken(BindObject.BindField, 1, '.'));
		BindObject.DataObjectID 	= GetToken(BindObject.BindField, 1, '.');
		BindObject.HasLabel 		= true;
		BindObject.HasField 		= true;
		BindObject.HasScript 		= false;
		
		if (BindObject.ValidatorMessage == undefined) {
			BindObject.ValidatorMessage = 'Invalid Value';
		}
		
		if (BindObject.BindField == undefined) {
			BindObject.FieldName = '';
			BindObject.FieldPath = '';

		} else {
			BindObject.FieldName = GetToken(BindObject.BindField, ListLen(BindObject.BindField, '.'), '.');
			BindObject.FieldPath = ReplaceStr(BindObject.BindField + '~', '.' + BindObject.FieldName + '~', '');
			if (BindObject.FieldPath == '~') { BindObject.FieldPath = ''; }
		}

		if (BindObject.Label == undefined || GetID(BindObject.LabelID) == undefined) {
			BindObject.HasLabel = false;
		}


		if (Bind.HasLabel) {
			BindObject.LabelID = BindObject.Target;
		}
		
		
		if (GetID(BindObject.Target + '_Field') == undefined) {
			BindObject.FieldID = BindObject.Target;
		}
		if (BindObject.ViewMode == undefined) {
			BindObject.ViewMode = 'Edit';
		}
		if (BindObject.Locked == undefined) {
			BindObject.Locked = 0;
		}
		if (BindObject.InputFormat == undefined) {
			BindObject.InputFormat = '';
		}
		
		if (BindObject.Invisible == undefined) {
			BindObject.Invisible = 0;
		}
		BindObject.IsInvisible = -1;

		if (GetID(BindObject.FieldID)==undefined || GetID(BindObject.FieldID)=='') {
			if (BindDebug == true) {
				alert('Developer Bind Field ID: [' + BindObject.FieldID + '] Does Not Exist');
			}
			BindObject.HasField = false;
		} else {
			BindObject.HasField = true;
			// Clear container
			GetID(BindObject.FieldID).innerHTML = '';
		}
		
		//
		// Display HTML Input field
		//
		if (BindObject.HasField) {
			if (BindObject.Type == '') {
				GetID(BindObject.FieldID).innerHTML = '<span id="' + Trim(BindObject.id) + '"><span id="' + Trim(BindObject.Target) + '_View"></span></span>';
			} else {
				//
				//	Set HTML Input with Field/Object
				//
				GetID(BindObject.FieldID).innerHTML += Input;
			}
			// Now create reference to Actual Field || id is the string ref and Object is the pointer ref
			BindObject.Object = GetID(Trim(BindObject.id));
			if (BindObject.Invisible == 0)	{ BindObject.Object.style.visibility = '' }
		}
	
		
		// Display Label if provided
		if (BindObject.HasLabel) {
			GetID(BindObject.LabelID).innerHTML = BindObject.Label + '<br>';
		}
		
		
		
		//
		//	LoadJavascript
		//
		if (BindObject.LoadJavaScript != undefined && BindObject.LoadJavaScript != '') {
			
			try {
				eval(BindObject.LoadJavaScript);
			} catch(e) {};
		}
		
		
		//
		//	AJAX
		//
		if (BindObject.Type.toUpperCase() == 'AJAX') {
			
			BindObject.DoAJAX = function() {
				ExecuteFunctionOnceAfter(function() {
											GetHTTPAJAX(HG_ToObject(BindObject.DefaultValue));
										 }
										 , 100);
			}
			
			BindObject.DoAJAX();
		}
		
		
		
		//
		//	Lets Make sure the BindField Existing in the Data Object
		//	If the JSON Datasource does not existing in memory, this will create it
		//
		BindObject.CreatedField = this.CreateObject(BindID);
		
		if (BindObject.CreatedField && BindObject.DefaultValue != undefined) {
			this.Modified = true;
			this.SetValue(BindID, BindObject.DefaultValue, '');
		}

		//
		//	When dealing with "SELECT" inputs, if the "Options" are provided
		//
		if (BindObject.Type.toUpperCase() == 'SELECT') {
			var HadSelect = true;
			if (BindObject.SelectOptions == undefined) {
				BindObject.SelectOptions = {};
				HadSelect = false;
			}
			if (BindObject.SelectOptions.ID == undefined) {
				BindObject.SelectOptions.ID = BindObject.id
			}
			
			BindObject.SelectOptions.Selected = eval(BindObject.BindField);
			// 12/13/09 ERA Passed Default was not setting dropdown
			if (BindObject.SelectOptions.Selected == '' && typeof BindObject.DefaultValue != 'undefined' && this.GetValue(BindID) == '') {
				BindObject.SelectOptions.Selected = BindObject.DefaultValue;
				this.SetValue(BindID, BindObject.DefaultValue);
			}
			
			//
			//	Try Loading Select if URL provides
			//
			this.RefreshSelect(BindID);

			// For Selects SET Bind By Default -- because of dropdown's default value
			if (BindObject.SelectOptions.URL == undefined && HadSelect==true) {
				this.SetValue(BindID, this.GetHTMLValue(BindID));
			}
		}
		
		//
		//	When dealing with "NON" inputs
		//
		if ( BindObject.Type.toUpperCase() == 'BUTTON' || BindObject.Type.toUpperCase() == 'DIV' || BindObject.Type.toUpperCase() == 'SPAN' || BindObject.Type.toUpperCase() == 'IFRAME') {
			this.SetHTMLValue(BindID, BindObject.DefaultValue);
		}


		this.SetEvents(BindID);
		
		if (BindObject.Type.toUpperCase() != 'SELECT' && BindObject.Type.toUpperCase() != 'BUTTON' && BindObject.Type.toUpperCase() != 'DIV' 
			&& BindObject.Type.toUpperCase() != 'SPAN' && BindObject.Type.toUpperCase() != 'IFRAME') {
			this.SetHTMLValue(BindID, this.GetBindValue(BindID));
		}
		
		this.ShowBind(this.ViewMode, BindObject.Invisible);
		this.ChangeMode(this.ViewMode, BindID);
		this.SetClasses(BindID);
		
		
		//	Save Original Values
		this.SealValue(BindID);
		
		
	}
	
	
	
	/***
	//
	//   Name: SetLabel - Set the HTML Label Field
	//	
	//	Parameters:
	//		BindName	  -- Unique Name for Above Array
	//		Value		  -- Value to set
	*/
	Bind.prototype.SetLabel = function(BindID, Value) {
		
		var BindObject = this.Bindings[BindID];
		if (BindObject == undefined) { return false; }

		if (!BindObject.HasLabel) {
			return false;
		}
			
			
		//	All values must be in string format
		Value = String(Value);
		
		if (Value == undefined || Value == 'undefined') {
			Value = '';
		}
		//alert(Value + ' - ' + BindObject.LabelID);
		GetID(BindObject.LabelID).innerHTML	= Value;
	}
	
	
	
	/***
	//
	//   Name: SetValue - Takes the "Value" and updates the HTML Input Field 
				And Sets the JSON Datasource field. For IMG Tags, the SRC value is set.
				If the Value is BLANK on non SRC tag the this.BlankValue is displayed in the field
				and the Bind Datasource field is cleared
	//	
	//	Parameters:
	//		BindName	  -- Unique Name for Above Array
	//		Value		  -- Value to set
	//		Event		  -- Optional: Passed when an event fires :: developers will not pass the parameter
	*/
	Bind.prototype.SetValue = function(BindID, Value, Event) {
		
		var BindObject = this.Bindings[BindID];
		if (BindObject == undefined) { 
			alert('Developer: ' + BindID + ' not found in SetValue');
			return false; 
		}

		if (!BindObject.HasField) {
			return false;
		}
			
			
		//	All values must be in string format
		//Value = String(Value);
		
		if (Value == undefined || Value == 'undefined') {
			Value = '';
		}
		
		if (BindObject.FieldPath == '') {
			Value = '';
		} else {
			try {
				eval(BindObject.FieldPath)[BindObject.FieldName] = Value;
			} catch(e) {
				//HG_CreateObject(BindObject.FieldPath + '.' + BindObject.FieldName);
				Dump(indObject.FieldPath + '.' + BindObject.FieldName, 'SetValue Issue');
				//eval(BindObject.FieldPath)[BindObject.FieldName] = Value;
				//alert(BindObject.FieldPath + ' ' +  BindObject.FieldName
			}
		}
		
		if (Event == undefined) {
			if (BindObject.Type.toUpperCase() != 'BUTTON' && BindObject.Type.toUpperCase() != 'DIV' && BindObject.Type.toUpperCase() != 'SPAN') {
				this.SetHTMLValue(BindID, Value);
			}
		}
	}
	
	
	/***
	//
	//   Name: SetHTMLValue -- Set the HTML display value || Multi selects and src are also set based on HTML type
	//	
	//	Parameters: Object ID and Value
	//		
	//		
	*/
	Bind.prototype.SetHTMLValue = function(BindID, Value, Event, NoFormat) {
		
		var BindObject = this.Bindings[BindID];
		if (BindObject == undefined) { alert('Developer: (SetHTMLValue) Bind Missing ' + BindID); return false; }

		if (!BindObject.HasField) {
			return false;
		}


		var ObjectID = BindObject.Object;
			
		try {
			if (GetID(ObjectID).type != 'select-one' && GetID(ObjectID).type != 'select-multiple') {
				if (Value == '{_Refresh_}') {
					Value = this.GetBindValue(BindID);	
				}
				
				if (NoFormat == true) {
					GetID(ObjectID).value = String(Value);	
				} else {
					GetID(ObjectID).value = BindObject._Formatter(String(Value));
				}
			}
		} catch(e) {}

		if (GetID(ObjectID).type == 'select-one' || GetID(ObjectID).type == 'select-multiple') {
			
			if (ObjectID.selectedIndex > -1 && Value != ObjectID.options[ObjectID.selectedIndex].value) {
			
				ObjectID.selectedIndex = 0;
				for (var t = 0; t<ObjectID.options.length;t++) {
					if (ObjectID.options[t].value == Value) {
						ObjectID.selectedIndex = t;
						break;
					}
				}

				//GetID(ObjectID).value = ObjectID.options[ObjectID.selectedIndex].value;
				
			}
			
		} else if (GetID(ObjectID).type == 'checkbox') {

			if (   Value 			   == undefined
				|| Value.toLowerCase() == 'no' 
				|| Value.toLowerCase() == 'false' 
				|| Value			   == false
				|| Value.toLowerCase() == '0' 
				|| Value.toLowerCase() == 'off'
				|| Value.toLowerCase() == 'unchecked'
				|| Value.toLowerCase() == ''
			   ) {
				GetID(ObjectID).checked  = false;
			} else {
				GetID(ObjectID).checked  = true;
			}
			
		} else {
		
			if (BindObject.Type.toUpperCase() == 'BUTTON' || BindObject.Type.toLowerCase() == 'div' || BindObject.Type.toLowerCase() == 'span') {
				GetID(ObjectID).innerHTML = String(Value);

			} else if (BindObject.Type.toLowerCase() == 'ajax') { 

				// Do Nothing for now
				
			} else if (BindObject.Type.toLowerCase() == 'image' || BindObject.Type.toLowerCase() == 'iframe') {
				 
				if (BindObject.Type.toLowerCase() == 'iframe') {
						GetID(ObjectID).src = String(Value); 
				} else if (GetID(ObjectID).src != undefined) {
						GetID(ObjectID).src = String(Value); 
					}
			}
		
			//
			//	If Blank or equal to Default BlankText :: Clear Value and Object Value
			//
			if (BindObject.BlankText != '') {
				if (Value == '' || String(Value).toUpperCase() == BindObject.BlankText.toUpperCase()) {
					///eval(BindObject.FieldPath)[BindObject.FieldName] = '';
					//this.SetHTMLValue(BindObject.Object, BindObject.BlankText);
					try {
						GetID(ObjectID).value = BindObject.BlankText;
					} catch(e) {}
				}
			}
		}
		   //   alert(GetID(ObjectID).value);
		if (BindObject.Title == undefined) {
			GetID(ObjectID).title = Trim(BindObject.BlankText + ' ' + BindObject.InputFormat);
		} else {
			GetID(ObjectID).title = Trim(BindObject.Title + ' ' + BindObject.InputFormat);
		}
	
		this.SetClasses(BindID);
		
		if (BindObject.ViewMode == 'View') {
			this.SwapFieldViewTo(BindObject.ViewMode, BindID);
		}
	}
	
	

	/***
	//
	//   Name: GetHTMLValue -- Returns the Value from the HTML  Object
	//	
	//	Parameters:
	//		BindID	  		-- Unique Name for Above Array
	//		GetText			-- True | False - For "Select"s return the display text instead of the value
	//		FromDataSource  -- True | False - Get the value from the Bind Datasource field
	*/
	Bind.prototype.GetHTMLValue = function(BindID, GetText, FromDataSource) {
		
		var BindObject = this.Bindings[BindID];
		if (BindObject == undefined) { alert('Field ' + BindID + ' was not found'); return false; }
		
		if (!BindObject.HasField) {
			this.SetClasses(BindID);
			return '';
		}
		
		if (FromDataSource == true) {
		
			var Value = this.GetBindValue(BindID);
	
		} else {
			try {
				if (GetID(BindObject.id).type == 'select-one') {
					if (GetText == true) {
						try {
							var Value = GetID(BindObject.id).options[GetID(BindObject.id).selectedIndex].text;
						} catch(e) {}
					} else {
						
					try {
							var Value =	GetID(BindObject.id).options[GetID(BindObject.id).selectedIndex].value; //GetID(BindObject.id).value;
							//alert(Value);
						
					} catch(e) {
							var Value =	GetID(BindObject.id).value;
						}
					}
					
				} else if (GetID(BindObject.id).type == 'select-multiple') {
					
					var Value = new Array();
					for (var loop=0;loop < GetID(BindObject.id).length;loop++) {
						if (GetID(BindObject.id).options[loop].selected) {
							var Obj = new Object();
							Obj.Value = GetID(BindObject.id).options[loop].value;
							Value.push(Obj);
						}
					}

				} else if (GetID(BindObject.id).type == 'checkbox') {
					var Value = (GetID(BindObject.id).checked == false) ? 'No' : 'Yes';
				} else if (BindObject.Type.toUpperCase() == 'IMG' || BindObject.Type.toUpperCase() == 'IFRAME') {
					var Value = GetID(BindObject.id).src;
				} else {
					var Value =	GetID(BindObject.id).value;
				}
			} catch(e) {
				Dump(e, BindID);
			}

		}
		
		this.SetClasses(BindID);
		return Value;
	
	}
	
	
	/***
	//
	//   Name: GetBindValue - Get the value of the actual Bind Object 
	//	
	//	Parameters:
	//		BindID	  		-- Unique Name for Above Array
	//		
	*/	
	Bind.prototype.GetBindValue = function(BindID) {
		
		var BindObject = this.Bindings[BindID];
		if (BindObject == undefined) { return false; }
		
		//
		//	Make sure the Bind Data Storage (FIELD PATH) is available or create it
		//
		
		if (BindObject.BindField == '') {
			Value = '';
		} else {
		
			try {		
				var Value = String(eval(BindObject.BindField));
				if (Value==undefined) { Value = '' };
			} catch(e) {
				try {		
					this.CreateObject(BindID);
					var Value = String(eval(BindObject.BindField));
					if (Value==undefined) { Value = '' };
				} catch(err) {
					Value = '';
				}
			}
			
		}

		if (Value == '[object Object]') {
			return '';	
		}
	
		return Value;

	}
	Bind.prototype.GetValue = function(BindID) {
		return this.GetBindValue(BindID);
	}
	
	
	
	/***
	//
	//   Name: RefreshSelect - Refreshes Select
	//	
	//	Parameters:
	//		BindID	  		-- Unique Name for Above Array
	//		
	*/
	Bind.prototype.RefreshSelect = function(BindID) {
		var BindObject = this.Bindings[BindID];
		
		//
		//	After the URL Call is made to fetch data the URL is clear but retained in OriginalURL
		//	Reset this before call is made
		//
		if (typeof BindObject.SelectOptions.OriginalURL != 'undefined') {
			BindObject.SelectOptions.URL  = BindObject.SelectOptions.OriginalURL;
			BindObject.SelectOptions.Addt = BindObject.SelectOptions.OriginalAddt
			BindObject.SelectOptions.Selected = this.GetValue(BindID);
		}
		
		DHE_SetSelectOptions(BindObject.SelectOptions);
	}
	
	
	
	/***
	//
	//   Name: UpdateBindValue - Updates Bind Value From HTML Value
	//	
	//	Parameters:
	//		BindID	  		-- Unique Name for Above Array
	//		
	*/
	Bind.prototype.UpdateBindValue = function(BindID) {
		this.SetValue(BindID, this.GetHTMLValue(BindID));
	}
	
	
	
	/***
	//
	//   Name: SetClasses - Set the Classes and Style based on whether there is a value in the Input Field or NOT
	//	
	//	Parameters:
	//		BindID	  		-- Unique Name for Above Array
	//		
	*/
	Bind.prototype.SetClasses = function(BindID) {
	
		var BindObject = this.Bindings[BindID];
		if (BindObject == undefined) { return false; }
		
		
		if (BindObject.FieldClass == undefined || BindObject.FieldClass == '') {
			BindObject.FieldClass = this.FieldClass; 
		}
		if (BindObject.FieldStyle == undefined || BindObject.FieldStyle == '') {
			BindObject.FieldStyle = this.FieldStyle; 
		}
		
		
		if (BindObject.LabelClass == undefined || BindObject.LabelClass == '') {
			BindObject.LabelClass = this.LabelClass; 
		}
		if (BindObject.LabelStyle == undefined || BindObject.LabelStyle == '') {
			BindObject.LabelStyle = this.LabelStyle; 
		}
		

		if (BindObject.PreviewClass == undefined) {
			BindObject.PreviewClass = this.PreviewClass; 
		}
		if (BindObject.PreviewStyle == undefined) {
			BindObject.PreviewStyle = this.PreviewStyle; 
		}

		if (BindObject.PreviewStyle == '') {
			BindObject.PreviewStyle = BindObject.FieldStyle; 
		}

		if (BindObject.PreviewClass == '') {
			BindObject.PreviewClass = BindObject.FieldClass; 
		}


		if ((BindObject.Type.toUpperCase() == 'INPUT' || BindObject.Type.toUpperCase() == 'TEXTAREA') && this.IsBlankText(BindID) == true) {
			var vFieldClass = this.BlankFieldClass; 
		} else {
			var vFieldClass = BindObject.FieldClass;
		}
		
		
		
		if (BindObject.Required == 1) {
			vFieldClass += ' ' + this.RequiredFieldClass + ' ';
		}
		
		if ((!BindObject.Validated == 1 || BindObject.Validated == -1) && this.InvalidClass != undefined) {
			vFieldClass += ' ' + this.InvalidClass + ' ';
		}
		
	
		
		if (BindObject.HasLabel) {
			GetID(BindObject.LabelID).className 	= BindObject.LabelClass;
			GetID(BindObject.LabelID).style.cssText = BindObject.LabelStyle;
		}

		
		if (BindObject.HasField && BindObject.Locked == '0') {
			GetID(BindObject.Object).className 		= vFieldClass;
			GetID(BindObject.Object).style.cssText  = BindObject.FieldStyle;	
		}


	}



	/***
	//
	//   Name: IsBlankText - Return true or false of whether the "BlankText" is displayed
	//	
	//	Parameters:
	//		BindID	  		-- Unique Name for Above Array
	//		
	*/
	Bind.prototype.IsBlankText = function(BindID) {
		var BindObject = this.Bindings[BindID];
		if (BindObject == undefined) { return false; }

		if (!BindObject.HasField) {
			return true;
		}
		
		var Val = GetID(BindObject.Object).value;
		
		if (typeof Val == 'object' || Val == undefined || (Val != '' && Val.toUpperCase() == BindObject.BlankText.toUpperCase())) {
			return true;
		} else {
			return false;
		}
	}
		
		
		
	/***
	//
	//   Name: SetEvents - Setup the Events for the Input Field
	//	
	//	Parameters:
	//		BindID	  		-- Unique Name for Above Array
	//		EventOpt		-- Overide this.Events
	*/	
	Bind.prototype.SetEvents = function(BindID, EventOpt) {
	
		var BindObject = this.Bindings[BindID];
		if (BindObject == undefined) { return false; }
		
		if (EventOpt != undefined) {
			BindObject.Events = EventOpt;
		}
		
		if (!BindObject.HasField || BindObject.Type.toLowerCase() == 'iframe' 
			|| BindObject.Type.toLowerCase() == 'div' || BindObject.Type.toLowerCase() == 'span'
			|| BindObject.Type.toUpperCase() == 'BUTTON') {
			return false;
		} 
		

		//
		//	Use This so when used inside a sub function, the scope reference will work correctly
		//
		var This = this;
		
		//
		//	Default Events
		//
		if (BindObject.Formatter == undefined) {
			BindObject._Formatter  = Bind_Formatter;
		} else {
			BindObject._Formatter = BindObject.Formatter
		}
		if (BindObject.Cleaner == undefined) {
			BindObject._Cleaner  = Bind_Cleaner;
		}else {
			BindObject._Cleaner = BindObject.Cleaner
		}
		if (BindObject.Validator == undefined) {
			BindObject._Validator  = Bind_Validator;
		}else {
			BindObject._Validator = BindObject.Validator
		}
		if (BindObject.Changer == undefined) {
			BindObject._Changer  = Bind_Changer;
		}else {
			BindObject._Changer = BindObject.Changer
		}
		if (BindObject.Previewer == undefined) {
			BindObject._Previewer  = Bind_Previewer;
		}else {
			BindObject._Previewer = BindObject.Previewer
		}
		if (BindObject.KeyUpper == undefined) {
			BindObject._KeyUpper  = Bind_KeyUpper;
		}else {
			BindObject._KeyUpper = BindObject.KeyUpper
		}
		if (BindObject.KeyDowner == undefined) {
			BindObject._KeyDowner  = Bind_KeyDowner;
		}else {
			BindObject._KeyDowner = BindObject.KeyDowner
		}
		if (BindObject.Focuser == undefined) {
			BindObject._Focuser  = Bind_Focuser;
		}else {
			BindObject._Focuser = BindObject.Focuser
		}
		
		
		//
		//	Event Functions that can be called by the developer
		//
		
			//
			//	Called When the Input field is ENTERED or Direct
			//
			BindObject.Focus = function(Event) { // Event Passed if Event Fires
			try {
									if (This.IsBlankText(BindID) == true || GetID(BindObject.id).type == 'checkbox' || GetID(BindObject.id).type == 'select-one' || BindObject.BlankText == '') {
										if (BindObject.BlankText != '') {
											GetID(_GlobalBindings[This.id].Bindings[BindID].id).value = '';
										}
										BindObject._Focuser('', This)
										This.SetClasses(BindID);
									} else {
										_GlobalBindings[This.id].SetHTMLValue( BindID
																			 , BindObject._Focuser(GetID(_GlobalBindings[This.id].Bindings[BindID].id).value, BindObject)
																			 , Event
																			 , true);  
										This.SetClasses(BindID);
									}
			} catch(e) { Dump(e, BindID); }
								} ;
	
								
			//
			//	Called When the Input field is EXITED by Format or Direct
			//
			BindObject.Validate = function(Event) { // Event Passed if Event Fires
									if (BindObject.Type.toUpperCase() == 'BUTTON' || BindObject.Type.toLowerCase() == 'div'|| BindObject.Type.toLowerCase() == 'span') {
										return
									}
									
									if (Event == undefined) { Event = {}}
									if (Event.type == 'focus') { return }
									

									var Val = This.GetHTMLValue(BindID);//GetID(_GlobalBindings[This.id].Bindings[BindID].id).value;
									BindObject.Validated = 0;

									if (typeof Val == "undefined"){
										alert('Developer: (Validate) ' + BindID + ' Is Missing');
									} else {
										if (BindObject.Type.toLowerCase() == 'select' && GetID(_GlobalBindings[This.id].Bindings[BindID].id).type == 'select-multiple') {
											if (Val.length == 0) {
												BindObject.Validated = 1;
												This.SetClasses(BindID);
												return BindObject.Validated;
											}
										} else  if (Val == '' || Val.toUpperCase() == _GlobalBindings[This.id].Bindings[BindID].BlankText.toUpperCase()) {
											BindObject.Validated = 1;
											This.SetClasses(BindID);
											return BindObject.Validated;
										}
										BindObject.Validated = BindObject._Validator(Val, BindObject);

										if (BindObject.Validated==true || BindObject.Validated=='true') {
											BindObject.Validated = 1;
										} else if (BindObject.Validated==false) {
											BindObject.Validated = 0;
										}

									}
								
									This.SetClasses(BindID);

									if (BindObject.ValidatorMessage != undefined && BindObject.Validated == 0 && BindObject.Initialized && BindObject.ValidatorMessage.toLowerCase() != 'noalert') {
										alert(BindObject.ValidatorMessage + ' (' + GetID(_GlobalBindings[This.id].Bindings[BindID].id).value + ')');
									}
									
									if (BindObject.Validated == -1) {
										BindObject.Validated = 0;
									}
									
									
									 return BindObject.Validated; //BindObject.Validated;
								} ;					
	
	
			//
			//	Called When the Input field is EXITED or Direct
			//
			BindObject.Format = function(Event) { // Event Passed if Event Fires
									if (Event == undefined) { 
										Event = {}
									}
									if (!BindObject.Initialized || BindObject.Validate(Event)==1) {
										if (BindObject._Formatter != Bind_Formatter) {
											This.SetHTMLValue( BindID
															 , BindObject._Formatter(This.GetHTMLValue(BindID), BindObject, Event)
															 , Event
															 , true);  
										}
									}
								} ;
								
			//
			//	Call Direct to Clean the Bind Value
			//
			BindObject.Clean = function(Event) { // Event Passed if Event Fires
									if (Event == undefined) { Event = {}}
									_GlobalBindings[This.id].SetValue( BindID
																	 , BindObject._Cleaner(This.GetHTMLValue(BindID), BindObject)
																	 , Event);  

								} ;
	
	
			//
			//	Define the wrapper for the "Change" Function
			//
			BindObject.Change = function(Event) { // Event Passed if Event Fires
									if (Event == undefined) { Event = {}}
									
									if (BindObject.Initialized) {
										This.Modified = true;
									}
									BindObject.Clean(Event);

									BindObject._Changer(This.GetHTMLValue(BindID), BindObject);  
								} ;
	
		
			//
			//	Define the Preview Function
			//
			BindObject.Preview = function() { 
									return BindObject._Previewer(This.GetHTMLValue(BindID), BindObject);  
								} ;


			//
			//	Define the Key Function
			//
			BindObject.KeyDown = function(KeyEvent) { 
									return BindObject._KeyDowner(KeyEvent, This.GetHTMLValue(BindID), BindObject);  
								} ;
								
			//
			//	Define the Key Function
			//
			BindObject.KeyUp = function(KeyEvent) {
									return BindObject._KeyUpper(KeyEvent, This.GetHTMLValue(BindID), BindObject);  
								} ;


		//
		//	Create Events using the "Events.js" Object functions || Bindings (this) has an Events Object Define by Default
		//	
		this.Events.Add([{ id:		BindObject.Object.id
						, Event:	'blur'
						, Function:	function(Event) {  
										_GlobalBindings[This.id].Bindings[BindID].Format(Event); 
									}
						},
						{ id:		BindObject.Object.id
						, Event:	'focus'
						, Function:	function(Event) {  
										_GlobalBindings[This.id].Bindings[BindID].Focus(Event); 
									}
						},
						{ id:		BindObject.Object.id
						, Event:	'change'
						, Function:	function(Event) {  
										_GlobalBindings[This.id].Bindings[BindID].Change(Event); 
									}
						},
						{ id:		BindObject.Object.id
						, Event:	'keydown'
						, Function:	function(Event) {  
										_GlobalBindings[This.id].Bindings[BindID].KeyDown(Event); 
									}
						},
						{ id:		BindObject.Object.id
						, Event:	'keyup'
						, Function:	function(Event) {  
										_GlobalBindings[This.id].Bindings[BindID].KeyUp(Event); 
									}
						}
						]);
			
		
		
		//
		//  New and Overide the above events -- Setup User Defined Events Which Can overide the above
		//
		for (var AnEvent in BindObject.Events) {

			this.Events.Add({ id:		BindObject.Object.id
							, Event:	AnEvent
							, Function:	function(Event) {  
											_GlobalBindings[This.id].Bindings[BindID].Events[AnEvent](Event); 
										}
							});
		}
	
	}
	
	
	
	/**
	//
	// 	Convert BindField to a available Object if it does not exists
	//	
	//		ex. HGO_Test.Guest.First.SSN
	//	    	Make sure that each node exist and the last node set = ''
	//
	*/
	Bind.prototype.CreateObject = function(BindID) {
		
		var BindObject = this.Bindings[BindID];
		if (BindObject == undefined) { return false; }
		
		var Path = BindObject.BindField;
			
		try {
			if (eval(Path) != undefined) {
				return false
			}
		} catch(e){}
		
		if (Path == '') {
			return false;
		}

		HG_CreateObject(Path);
		//BindObject.DataObject = HG_MergeObjects(BindObject.DataObject, eval(Path));
		
		return true;
		
		var Dots = ListLen(Path, '.');
		
		Dots += ListLen(Path, '[') - 1;
		Path = ReplaceStr(Path, '].', '":\"');
		Path = ReplaceStr(Path, '.', '\":{\"');
	    Path = ReplaceStr(Path, '[', '\":{"');
	    Path = ReplaceStr(Path, "'", '"');
 	    Path = ReplaceStr(Path, '"]', '');
		Path = ReplaceStr(Path, ']', '}');
		Path = '{"' + Path + '":""';
		for (var t = 1; t <= Dots; t++) {
			Path += '}';
	    }
		Path = ReplaceStr(Path, '"', '\"');

		var JSO               = new Object();
		JSO		  = "//" + Path;
		
		if (BindObject.DataObjectID != undefined && BindObject.DataObjectID != '') {
			JSO 				  = HG_JSONToObject(JSO)[BindObject.DataObjectID];
			BindObject.DataObject = HG_MergeObjects(BindObject.DataObject, JSO);
		}

		return true;
		
	}
	
	

	/***
	//
	//   Name: ParsePath -Parse the Bind Path
	//	
	//	Parameters:
	//		BindID 	- Field Bind ID String	
	//		
	*/
	Bind.prototype.ParsePath = function(BindID) {
		
		var BindObject = this.Bindings[BindID];
		if (BindObject == undefined) { return false; }
		
		Path = BindObject.BindField;
		
		var SPArray = Path.split('.');
		
		if (eval(SPArray[0]) == undefined) {
			alert('Developer :: ' + SPArray[0] + ' :: Object does not exists');
		}
		BindObject.FieldName = SPArray[SPArray.length-1];
		SPArray.splice(SPArray.length-1, 1);
		BindObject.FieldPath = ReplaceStr(SPArray.toString(), ',', '.');
	}
	
	/***
	//
	//   Name: Change -Change the Bind Path
	//	
	//	Parameters:
	//		BindID 	- Field Bind ID String	
	//		
	*/
	Bind.prototype.Change = function(BindID) {
		
		var BindObject = this.Bindings[BindID];
		if (BindObject == undefined) { return false; }
		
		BindObject.Change();
	}
	
	
	/***
	//
	//   Name: ShowBind -- 
	//	
	//	Parameters:
	//		BindID 	- Field Bind ID String	
	//		Show    - 0 | 1
	*/
	Bind.prototype.ShowBind = function(BindID, Show) {
		
		var BindObject = this.Bindings[BindID];
		if (BindObject == undefined) { return false; }
		
		if (Show != undefined) {
			BindObject.Invisible = Show;
		}
		
		/*if (BindObject.Invisible == BindObject.IsInvisible) {
			return false;
		}*/

		if (BindObject.Invisible == 1) {
			var ShowValue = 'none';
			BindObject.IsInvisible = BindObject.Invisible;
		} else {
			var ShowValue = '';
			BindObject.IsInvisible = BindObject.Invisible;
		}
		
		
		if (BindObject.LabelContainerID != undefined) {	
			try {
				GetID(BindObject.LabelContainerID).style.display 	= ShowValue;
			} catch(e){}
		} else {
			if (Bind.HasLabel) {
				GetID(BindObject.LabelID).style.display 			= ShowValue;	
			}
		}
		
		if (BindObject.FieldContainerID != undefined) {		
			try {
				GetID(BindObject.FieldContainerID).style.display 	= ShowValue;
			} catch(e){}
		} else {
			if (BindObject.HasField) {
				GetID(BindObject.id).style.display 				= ShowValue;
				GetID(BindObject.ViewID).style.display 			= ShowValue;	
			}
			if (Bind.HasLabel) {
				GetID(BindObject.LabelID).style.display 			= ShowValue;	
			}
		}
		
			
		return true;
			
	}
	
		
	
	/***
	//
	//   Name: SwapFieldViewTo -- Do Not Call Directly, Call ChangeMode
	//	
	//	Parameters:
	//		Mode 	- View|Edit
	//		BindID 	- Field Bind ID String	
	*/
	Bind.prototype.SwapFieldViewTo = function(Mode, BindID) {
	
		var BindObject = this.Bindings[BindID];
		if (BindObject == undefined) { return false; }
		

		if (BindObject.Invisible != BindObject.IsInvisible) {
			this.ShowBind(BindID);
		}
		
		
		if (!BindObject.HasField) {
			return false;
		}
		
		if (Mode == undefined) { Mode = BindObject.ViewMode; }
			
		if (BindObject.Locked == 2) {
			GetID(BindObject.id).style.display 		= '';
		} else if (Mode == 'View' || BindObject.Locked == 1) {
			
			//GetID(BindObject.ViewID).style.cssText 	= BindObject.FieldStyle;
			
			if (GetID(BindObject.ViewID).style.display == undefined) {
				GetID(BindObject.ViewID).style.display 	= '';
			}
			
			if (BindObject.Type == 'img') {
				//	Pass Bind Value, Bind Object, Current HTML to function
				var pv = BindObject._Previewer(this.GetBindValue(BindID), BindObject, GetID(BindObject.ViewID).innerHTML);
				if (pv != undefined) {
					GetID(BindObject.ViewID).innerHTML 	= pv;
				}
				GetID(BindObject.ImgInput).style.display = 'none';
			} else if (BindObject.Type.toLowerCase() == 'iframe') {
				// Do Nothing
			} else {
				if (BindObject.PreviewValue == '' && typeof BindObject._Previewer == 'function') {
					if (this.IsBlankText(BindID) == true) {
						GetID(BindObject.ViewID).innerHTML 	= BindObject._Previewer('&nbsp', BindObject);
					} else {
						GetID(BindObject.ViewID).innerHTML 	= BindObject._Previewer(this.GetHTMLValue(BindID, true), BindObject);
					}
				}
				if (BindObject.Title == undefined) {
					GetID(BindObject.ViewID).title		= BindObject.BlankText;
				} else {
					(BindObject.ViewID).title			= BindObject.Title;
				}
				if (BindObject.HasField) {
					GetID(BindObject.id).style.display 		= 'none';
				}
				GetID(BindObject.ViewID).className 		= BindObject.PreviewClass;
				GetID(BindObject.ViewID).style.cssText 	= BindObject.PreviewStyle;
			}
			
			BindObject.ViewMode 					= 'View';

		} else {
			GetID(BindObject.ViewID).style.display 	= 'none';
			if (BindObject.Type != 'img') {
				if (BindObject.PreviewValue == '') {
					GetID(BindObject.ViewID).innerHTML 		= '';
				}
				GetID(BindObject.id).style.display 		= '';
			} else {
				GetID(BindObject.ImgInput).style.display = '';
			}
			BindObject.ViewMode = 'Edit';
		}
			
	}
		
		
		
	/***
	//
	//   Name: ChangeMode - Show in View Mode
	//	
	//	Parameters:
	//		Mode 	- View|Edit
	//		BindID 	- Field Bind ID String
	*/
	Bind.prototype.ChangeMode = function(Mode, BindID) {
		
		var BindObject = this.Bindings[BindID];
		
		if (BindObject != undefined) {
			this.SwapFieldViewTo(Mode, BindID);
			return;
		}
		
		for (var BindObject in this.Bindings) {
			this.SwapFieldViewTo(Mode, BindObject);
		}
	
	}
	
	
	Bind.prototype.SetViewTo = function(BindID, Mode) {
		
		this.ChangeMode(Mode, BindID);
	
	}
	
	
	/***
	//
	//   Name: Lock - Change Locked Mode || When Changed, SwapFieldViewTo will be called
	//	
	//	Parameters:
	//		BindID 	- Field Bind ID String
	//		Lock 	- 1 | 0 :: Optionally -- if not passed then toggle between 0 and 1
	*/
	Bind.prototype.Lock = function(BindID, Lock) {
		
		var BindObject = this.Bindings[BindID];
		
		if (BindObject == undefined) {
			return;
		}
		
		if (Lock == undefined) {
			if (BindObject.Locked == '1' || BindObject.Locked == '2') {
				BindObject.Locked = '0';
			} else {
				BindObject.Locked = '1';
			}
		} else {
			BindObject.Locked = Lock;
		}

		this.SwapFieldViewTo('Edit', BindID);
	
	}
	
	
	
	/***
	//
	//   Name: SealValue - Remember Original value until reset
	//	
	//	Parameters:
	//		BindID 	- Field Bind ID String
	*/
	Bind.prototype.SealValue = function(BindID) {
		if (BindID == undefined) {
			for (var BindID in this.Bindings) {
				var BindObject = this.Bindings[BindID];
				BindObject.SealedValue = this.GetHTMLValue(BindID, undefined, true);
			}
			
			this.Modified = false;
			
		} else {
			var BindObject = this.Bindings[BindID];
			BindObject.SealedValue = this.GetHTMLValue(BindID, undefined, true);
		}
	}
	
	
	
	/***
	//
	//   Name: ResetValue - Reset to Original value 
	//	
	//	Parameters:
	//		BindID 	- Field Bind ID String
	*/
	Bind.prototype.ResetValue = function(BindID) {
		if (BindID == undefined) {
			for (var BindID in this.Bindings) {
				var BindObject = this.Bindings[BindID];
				this.SetValue(BindID, BindObject.SealedValue);
			}
		} else {
			var BindObject = this.Bindings[BindID];
			this.SetValue(BindID, BindObject.SealedValue);
		}
	}
	
	
	
	/***
	//
	//   Name: ResetValue - Reset to Original value 
	//	
	//	Parameters:
	//		BindID 	- Field Bind ID String
	*/
	Bind.prototype.HasChanged = function(BindID) {
		
		var BindObject = this.Bindings[BindID];
		if (BindObject == undefined) { return undefined; }
		
		return (this.GetHTMLValue(BindID) != BindObject.SealedValue);
	}
	
	
	
	/***
	//
	//   Name: Refresh - Reset to Original value 
	//	
	//	Parameters:
	//		BindID 	- Field Bind ID String
	*/
	Bind.prototype.Refresh = function(BindID) {
		if (BindID == undefined) {
			for (var BindID in this.Bindings) {
				var BindObject = this.Bindings[BindID];
				if (BindObject.HasField) {
					try { BindObject._Cleaner(); } catch(e) {}
					this.SetValue(BindID, this.GetValue(BindID));
					this.SealValue(BindID);
				}
			}
		} else {
			var BindObject = this.Bindings[BindID];
			if (BindObject.HasField) {
				try { BindObject._Cleaner(); } catch(e) {}
				this.SetValue(BindID, this.GetValue(BindID));
				this.SealValue(BindID);
			}
		}
	}
	
	
	/***
	//
	//   Name: FilterSelect - 
	//	
	//	Parameters:
	//		BindID 	- Field Bind ID String
	*/
	Bind.prototype.FilterSelect = function(BindID, FilterBy) {

		var BindObject = this.Bindings[BindID];
		
		if (!BindObject.HasField) {
			return false;
		}
		
		if (BindObject.Type.toUpperCase() != 'SELECT') {
			return false
		} 

		BindObject.SelectOptions.FilterBy = FilterBy;
		DHE_SetSelectOptions(BindObject.SelectOptions);
		
		this.SetValue( BindID, BindObject._Cleaner(this.GetHTMLValue(BindID), BindObject));

		
		return true
		
	}
	
	
	
	/***
	//
	//   Name: SetSelect - Sets the Value of select field
	//	
	//	Parameters:
	//		BindID 	- Field Bind ID String
	*/
	Bind.prototype.SetSelect = function(BindID, Options, Selected, NoCleaner) {

		var BindObject = this.Bindings[BindID];

		if (!BindObject.HasField) {
			return false;
		}
		
		if (BindObject.Type.toUpperCase() != 'SELECT') {
			return false
		} 

		if (BindObject.SelectOptions == undefined) {
			return false;
		}


		if (BindObject.SelectOptions.URL != undefined) {
			BindObject.SelectOptions.OriginalURL  = BindObject.SelectOptions.URL;
			BindObject.SelectOptions.OriginalAddt = BindObject.SelectOptions.Addt;
			//	Now that we have static data clear URL
			BindObject.SelectOptions.URL		= undefined;

		};


		BindObject.SelectOptions.Options	= Options;
		BindObject.SelectOptions.ID 		= BindObject.id;
		if ((NoCleaner == undefined || NoCleaner == false) && Selected.substring(0, 2) != '//')  {
			BindObject.SelectOptions.Selected 	= BindObject._Cleaner(Selected, BindObject);
		} else {
			BindObject.SelectOptions.Selected 	= Selected;
		}
		
		DHE_SetSelectOptions(BindObject.SelectOptions);
		
		BindObject._Changer(Selected, BindObject);
		this.SetValue(BindID, BindObject._Cleaner(this.GetHTMLValue(BindID)), false);
		
		this.SwapFieldViewTo(undefined, BindID);
		
		return true
		
	}


	/***
	//
	//   Name: isSubmitReady - If you are wanting to check to see if
				the data is good to save call this function
	//	
	//	Parameters:
	//		RequiredMessage 	- This message you want to display when not ready
	//		ValidationMessage	- Display Message when validation has failed
	//		
	*/	
	Bind.prototype.isSubmitReady = function(RequiredMessage, ValidationMessage) {
				
		this.AllRequired  = true;
		this.AllValidated = true;
		
		var ProblemFields  = '';
		var InvalidFields  = '';

		//  Add All to Bind
		for (var BindObject in this.Bindings) {
			
			if (this.Bindings[BindObject].HasField && this.Bindings[BindObject].Type != 'hidden') {
		
				if (  (this.GetHTMLValue(BindObject) == '' 
				   ||  this.GetHTMLValue(BindObject) == this.Bindings[BindObject].DenyValue
				   ||	(!isNaN(Number(this.GetHTMLValue(BindObject))) && Number(this.GetHTMLValue(BindObject)) == Number(this.Bindings[BindObject].DenyValue))
				   )
					&& this.Bindings[BindObject].Required  == 1 
					&& this.Bindings[BindObject].Invisible == 0 
					&& this.Bindings[BindObject].Locked    != 1
				) {
					this.AllRequired = false;
					//ProblemFields += ' ' + BindObject;
					if (this.Bindings[BindObject].HasLabel) {
						ProblemFields += '- ' + this.Bindings[BindObject].Label + '\n';
					}
				}
			

				if (typeof this.Bindings[BindObject].Validate  == 'function') {
					this.Bindings[BindObject].Initialized = false; // This will disable alert
					this.Bindings[BindObject].Validate();
					this.Bindings[BindObject].Initialized = true;
				};
	
				if (this.Bindings[BindObject].Validated == 0) {
					if (this.Bindings[BindObject].HasLabel) {
						InvalidFields += '- ' + this.Bindings[BindObject].Label + '\n';
					}
					this.AllValidated = false;	
				}
			}
			
		}

		var Alert = '';
		
		if (RequiredMessage != undefined && !this.AllRequired) {
			Alert = RequiredMessage + '\n' + ProblemFields + '\n';
		}

		if (ValidationMessage != undefined && !this.AllValidated) {
			Alert += ValidationMessage + '\n ' + InvalidFields;
		}
		
		if (Alert != '' && ValidationMessage != '' && RequiredMessage != '') {
			alert(Alert);
		}

		return (this.AllRequired == true && this.AllValidated == true);
	}	

	Bind.prototype.IsSubmitReady = function(RequiredMessage, ValidationMessage) {
		return this.isSubmitReady(RequiredMessage, ValidationMessage);
	}
	
	

	/***
	//
	//   Name: Destroy - Destroy the Bind Object and All Associated with it
	//	
	//	Parameters:
	//		
	//		
	*/
	Bind.prototype.Destroy = function() {
		
		this.Events.Destroy();
		
		//  Add All to Bind
		for (var BindObject in this.Bindings) {
			GetID(this.Bindings[BindObject].Target).innerHTML = '';
			delete this.Bindings[BindObject];
		}
	}	
	
	
	
	/***
	//
	//   Name: Default Bind_Formatter - Returns same value
			Pass your own function and this one will be overwritten	
	//	
	//	Parameters:
	//		Value - 
	//		
	*/	
	Bind_Formatter = function(Value) {
		return Value;
	}
	
	
	
	/***
	//
	//   Name: Default Bind_Cleaner - Returns same value
			Pass your own function and this one will be overwritten	
	//	
	//	Parameters:
	//		Value - 
	//		
	*/	
	Bind_Cleaner = function(Value) {
		return Value
	}
	
	
	/***
	//
	//   Name: Default Bind_Validator - Returns true	
			Pass your own function and this one will be overwritten
	//	
	//	Parameters:
	//		Value - 
	//		
	*/	
	Bind_Validator = function(Value) {
		return 1
	}
	
	
	
	/***
	//
	//   Name: Default Bind_Change - Returns void
			Pass your own function and this one will be overwritten
	//	
	//	Parameters:
	//		Value - 
	//		
	*/	
	Bind_Changer = function(Events) {
		return true
	}
	
	/***
	//
	//   Name: Default Bind_Previewer - Returns void
			Pass your own function and this one will be overwritten
	//	
	//	Parameters:
	//		Value - 
	//		
	*/	
	Bind_Previewer = function(Value) {
		return Value
	}
	
	
	/***
	//
	//   Name: Default Bind_Keyer - Returns void
			Pass your own function and this one will be overwritten
	//	
	//	Parameters:
	//		Value - 
	//		
	*/	
	Bind_KeyUpper = function(Events) {
		return true
	}
	
	
	/***
	//
	//   Name: Default Bind_Keyer - Returns void
			Pass your own function and this one will be overwritten
	//	
	//	Parameters:
	//		Value - 
	//		
	*/	
	Bind_KeyDowner = function(Events) {
		return true
	}
	
	
	/***
	//
	//   Name: Default Bind_Focuser - Returns void
			Pass your own function and this one will be overwritten
	//	
	//	Parameters:
	//		Value - 
	//		
	*/	
	Bind_Focuser = function(Value) {
		return Value
	}
	
	
	
	/***
	//
	//   Name: Bind_SetSelect
	//	
	//	Parameters:
	//		BindObjID - 
	//		BindID
	//		Options
	//		Selected
	//		
	*/	
	Bind_SetSelect = function(BindObjID, BindID, Options, Selected) {
		_GlobalBindings[BindObjID].SetSelect(BindID, Options, Selected);
		/*Dump(Options, '', GetID(DB)); */
		/* Put this at botton of a CF Page 
		<div id="DB" style="position:absolute; top:500px; height:300; width:1000px; overflow:auto">23423</div>
		*/
	}
	
	
	
	var _DataGrids = new Object();
	


	/***
	//
	//   Name: DataGrid - Object
	//	
	//	Parameters:
	//		  Formatters:{StartDate:TIDateFormat, Phone:FormatPhone}  -- DataSet Field : Function Name
	//		
	*/
	
	
	
	//
	// 
	//
	DataGrid = function(DGObject) {

		this.id = DGObject.id;
		
		this.Destory(); // In Case Already Defined
		
	
		for (var Item in DGObject) {
			this[Item] = DGObject[Item];
		}
			
		if (this.HeaderContainer == undefined) {
			alert('Developer: Missing HeaderContainer for DataGrid: ' + DGObject.id);
			return false;
		}
		if (this.BodyContainer == undefined) {
			alert('Developer: Missing BodyContainer for DataGrid: ' + DGObject.id);
			return false;
		}
		
			
		//
		// Add to master
		//
		_DataGrids[DGObject.id] = this;

		this.SetupMainContainer();
		this.Init(this);
	}
	
	
	//
	//
	//
	DataGrid.prototype.Init = function(DGObject){

		if (DGObject.HeaderContainer.Columns == undefined) {
			alert('Developer: Missing Header Columns for ' + this.id);
			return false
		}


		if (this.ShowRowCounter == undefined) {
			this.ShowRowCounter = true;
		}

		this.StartColumns = 1;
		this.SortObjects = new Object();
				
		if (this.Columns == undefined) {
			if (DGObject.HeaderContainer.Columns.toArray()[0].toArray != undefined) {
				//  Multi Header Lines Used
				this.Columns = DGObject.HeaderContainer.Columns.toArray()[0].toArray().length; 
			} else {
				// Single Header Line Used
				this.Columns = DGObject.HeaderContainer.Columns.toArray().length; 
			}
		}
		
		if (this.ShowRowCounter == true) {
			this.StartColumns++;
		};
		
		this.Columns += this.StartColumns;
		
		GetID(this.Container.id).innerHTML = this.GetContainerHTML('Header', DGObject.HeaderContainer)
										   + '\n'
		 								   + this.GetContainerHTML('Body',   DGObject.BodyContainer)
										   + '\n';
										   
		this.Container = GetID(this.Container.id);

		this.Body   	 	= GetID('Container_Body_' + this.id);
		this.Header 	 	= GetID('Container_Header_' + this.id);
		this.TableBody   	= GetID('TBL_Body_' + this.id);
		this.TableHeader 	= GetID('TBL_Header_' + this.id);
		this.Data		 	= new Object();
		this.DisplayData 	= new Array();
		this.LastSortField 	= '';
		this.LastSelectedRow = -1;

		if (this.Formatters== undefined) {
			this.Formatters = new Object();
		}

		this.DataIndex   = 0;
		if (this.PageSize == undefined) {
			this.PageSize 	 = 49;
		}
		
		if (this.BodyOffsetHeight == undefined ) {
			this.BodyOffsetHeight = 0;
		}
		if (this.BodyOffsetWidth == undefined ) {
			this.BodyOffsetWidth = 0;
		}		
		
		this.DefaultPageSize = this.PageSize;
		
		if (this.ShowRowCounter &&  this.SortObjects['_Counter'] != undefined) {
			this.Sort('_Counter', -2);
		}
		
		if (this.OverClass == undefined) {
			this.OverClass = 'DGMouseOver'
		}
		if (this.UpClass == undefined) {
			this.UpClass = 'DGMouseClick'
		}
		
		this.OverClass += ' Clickable'
		this.UpClass += '  Clickable'
		
		//
		// Setup Room List
		//
		ListInit({ Init:			true
				 , ListName:		'TBL_Body_' + this.id
				 , Type:			'Row'
				 , MonitorObject:	GetID('TBL_Body_' + this.id)
				 , UpClass:			this.UpClass
				 , OverClass:		this.OverClass
				 });
		
		
		this.InitResize();
			
	}
	
	//
	//	Set Elements on the Main Container DIV
	//
	DataGrid.prototype.SetupMainContainer = function() {
		// this.Container is the Main Container
		for (var Element in this.Container.Elements) {
			GetID(this.Container.id)[Element] = this.ContainerElements[Element];
		}
	}
	
	
		
	//
	//	Build DIV Container for passed in Container
	//
	DataGrid.prototype.GetContainerHTML = function(ContainerStrType, Container) {  // ContainerStrType = Header| Body

		if (Container.Elements == undefined) {
			Container.Elements             = new Object();
		}
		
		if (Container.Elements['style'] == undefined) {
			Container.Elements['style']    = '';
		}
		if (Container.Elements['onscroll'] == undefined) {
			Container.Elements['onscroll'] = '';
		}

		if (ContainerStrType == 'Header') {
			Container.Elements['style'] += "; overflow:hidden;";
		}

		if (ContainerStrType == 'Body') {
			Container.Elements['style'] 	+= "; overflow:auto;";

			Container.Elements['onscroll'] 	=  "ListScrollHeader(this, GetID('Container_Header_" +  this.id + "'));" + Container.Elements['onscroll'];
		}

		var Str = '<div id="Container_' + ContainerStrType + '_' + this.id + '" ';
		
		for (var Element in Container.Elements) {
			Str += ReplaceStr(Element, "className", "class") + '="' + Container.Elements[Element] + '" '
		}
		
		Str += '>';
		Str += this.GetTableHTML(ContainerStrType, Container);
		Str += '</div>';
		
		return Str;
	}
	
	
	//
	//	Build TABLE Container for passed in Container
	//
	DataGrid.prototype.GetTableHTML = function(TableStrType, Container) {  // TableStrType = Header | Body
		
		var Str = '<table id="TBL_' + TableStrType + '_' + this.id +'" border="0" cellpadding="0" cellspacing="0">\n';
		var DefaultColumnElements = '';
		
			//	Elements for All Columns
		for (var Column in Container.DefaultColumnElements) {
			DefaultColumnElements += ReplaceStr(Column, "className", "class") + '="' + Container.DefaultColumnElements[Column] + '" '
		}
	
		
		var Rows = 0;
		var Row  = 0;
		if (TableStrType=='Header' && Container.Columns.toArray()[0].toArray != undefined) {
			Rows = Container.Columns.toArray().length;
		} else {
			Row = -1;
			
		}
		var SRow = Row;
		if (Container.Columns != undefined && TableStrType=='Header') { // Body Cells will get done when AddData is Called
		
			/*
			Str += '\n<tr>\n'; //  class="" style="padding-top:0; padding-bottom:0; overflow:hidden; height:0px;"
			for (var Column =0;Column<this.Columns-1; Column++) { 
				Str  += '<td><div  ' + DefaultColumnElements + ' style="padding-top:0px; padding-bottom:0px; overflow:hidden; height:0px; max-height:0px; background-image:url(/UI/Images/Blank.gif); visibility:hidden  " ';
				Str  += '>2</td>\n';
			}
			Str  += '</tr>\n';
			*/
			
			
			for (Row=SRow;Row<Rows;Row++) {
				Str += '\n<tr>\n';
				for (var Column =0;Column<this.Columns; Column++) { 
					if (Rows > 0) {
						var DataRow = Container.Columns.toArray()[Row][Column];
					} else {
						var DataRow = Container.Columns[Column];
					}
					if (DataRow != undefined) {
						
						Str 		+= '<td><div ' + DefaultColumnElements + ' title="' + DataRow.Text + '"';
						//
						//	Class & Style
						//
						if (DataRow.Elements != undefined) {
							
							for (var Element in DataRow.Elements) {
								Str 		+= ReplaceStr(Element, "className", "class") + '="' + DataRow.Elements[Element] + '" '
							}
						} else {
							//	Force Overview hidden
							Str 		+= ' style="overflow:hidden" ';
						}
						
						//
						//	Click
						//
						if (DataRow.SortBy != undefined && DataRow.SortBy != '') {
						  Str 		+= ' onclick="_DataGrids[\'' + this.id +'\'].Sort(\'' + DataRow.SortBy + '\')" '
						  this.SortObjects[DataRow.SortBy] = -1;
						}
						
						Str += '>'
						//
						// Cell Value
						//
						if ( DataRow.Text != undefined) {
							Str += DataRow.Text;
						}
						//
						//	Sort Arrow
						//
						if (DataRow.SortBy != undefined && DataRow.SortBy != '') {
							Str += '&nbsp;<span id="' + this.id + '_S_' + DataRow.SortBy + '"></span>';
						}
						Str += '</div></td>\n';
					}
				}
				Str += '</tr>\n';
			}
		}
		Str += '</table>\n';

		return Str;
	}
	
	//
	//	Add Resize to Global Resize List
	//
	DataGrid.prototype.InitResize = function() {

		var ID = this.id;
		this.DoResize = function() { _DataGrids[ID].Resize(ID) };
		//
		//	Add to Global Resize
		//				
		ResizeAddFunction( this.id
						 , true
						 , undefined
						 , undefined
						 , this.DoResize
						 );
		
	}
	
	
	//
	//	Build Resize Javascript
	//
	DataGrid.prototype.Resize = function(DGID) {
	
		
		ListResize(_DataGrids[DGID].TableHeader, _DataGrids[DGID].TableBody);
		
		ExecuteFunctionOnceAfter( function() {
										
			if (DGID == undefined) { 
				DGID = this.ID;
			}
	
			if (DGID == undefined) { 
				 alert('Developer: DataGrid.prototype.Resize was not provided the ID of the DataGrid');
				 return
			}
			
			var DG = _DataGrids[DGID];
			
			if (GetID(DG.Container.id) == undefined) {
				ResizeRemoveFunction('_DataGrids[ID].DoResize');
				return
			}
			
	
			DG.Body.style.height  = SafeSize(GetID(DG.Container.id).offsetHeight - (DG.TableHeader.offsetHeight + (DG.BodyOffsetHeight * -1)));
	
			DG.Body.style.width   = SafeSize(GetID(DG.Container.id).offsetWidth + DG.BodyOffsetWidth -2);
			
			DG.Header.style.width = SafeSize(DG.Body.offsetWidth -1);
			ListResize(DG.TableHeader, DG.TableBody);

			
		}, 200) 
		
	}
	
	
	//
	//	Apply Alt Row Colors
	//
	DataGrid.prototype.ApplyAltColors = function() {
	
		var Counter = 0;

		var Rows = this.ViewableRows;
		
		if (Rows > this.TableBody.rows.length) {
			Rows = this.TableBody.rows.length;
		}
		if (Rows > 0) {
			if (this.AltClassList != undefined) {
				var Colors  = ListLen(this.AltClassList, ',');
				for (var Row = 0; Row<Rows; Row++) {
					Counter++;
					if (Counter > Colors) { Counter = 1 }
					this.TableBody.rows[Row].className = GetToken(this.AltClassList, Counter, ',');
				}
			}
	
			if (this.AltColorList != undefined) {
				var Colors  = ListLen(this.AltColorList, ',');
				for (var Row = 0; Row<Rows; Row++) {
					Counter++;
					if (Counter > Colors) { Counter = 1 }
					this.TableBody.rows[Row].style.backgroundColor = GetToken(this.AltColorList, Counter, ',');
				}
			}
		}
	}
	
	
	
	
	//
	//	Apply Row Counter
	//
	DataGrid.prototype.ApplyRowCounter = function(StartRow) {
	
		if (!this.ShowRowCounter) { return }
	
		var Counter = 0;


		var Rows = this.ViewableRows;
		
		if (Rows > this.TableBody.rows.length) {
			Rows = this.TableBody.rows.length;
		}
		if (Rows > 0) {
			for (var Row = 0; Row<Rows; Row++) {
				this.TableBody.rows[Row].cells[1].innerHTML = Row + 1 + StartRow;
			}
		}
	}
	
	
	
	//
	//	@SetElements
	//	
	// 	Target HTML Object
	//  HTML Elements as {Object}
	//
	DataGrid.prototype.SetElements = function(Target, ElementObject) {
		if (ElementObject == undefined) { return false }
		for (var Element in ElementObject) {
			
			if (typeof(ElementObject[Element]) == 'string') {
				try {
					Target[Element] = ElementObject[Element];
				} catch(e) {
					Dump(e, 'Element ' + Element + ' Should Be Formatted As ' + Element + ':{} not ' + Element + '=""');
					return false;
				}
			} else {
				for (var Obj in ElementObject[Element]) {
					Target[Element][Obj] = ElementObject[Element][Obj];
				}
			}
		}
		
		return true;
	}
	
	
	
	
	/***
	//
	//   Name: Rows - Get Actual Row Count of Data
	//	
	//	Parameters:
	//		
	//		
	*/
	DataGrid.prototype.Rows = function() {
		
		if (this.DataObject.Data.toArray != undefined) {
			var Rows = this.DataObject.Data.toArray().length;
		} else {
			var Rows = 0;
		}
		
		return Number(Rows);
	}
	
	
	
	/***
	//
	//   Name: Rows - Get Actual Row Count for Data being display
	//	
	//	Parameters:
	//		
	//		
	*/
	DataGrid.prototype.DisplayRows = function() {
		
		if (this.DisplayData.toArray != undefined) {
			var Rows = this.DisplayData.toArray().length;
		} else {
			var Rows = 0;
		}
		
		return Rows;
	}
	
	
	
	
	/***
	//
	//   Name: CreateDisplayData - This is the data that used to be display or used for sorting so orginal data does not change
	//	
	//	Parameters:
	//	DataObject = {
	// 		Data:Data As {}
	//  	StartRow:
	//  	EndRow:
	//		FieldList: 'Col1,Room,GN,LK'

	//		Action:{Action:''}
	//	},
	//	Refresh: true | false
	//		
	*/
	DataGrid.prototype.CreateDisplayData = function(DataObject) {

		//
		//	Filter Requested
		//
		if (DataObject.FilterField != undefined) {
			if (DataObject.FilterField == undefined || Trim(DataObject.FilterField) == '') {
				alert('Developer: No FilterField Provided');
				return
			}
			if (DataObject.FilterBy == undefined || Trim(DataObject.FilterBy) == '') {
				//alert('Developer: No FilterBy Provided');
				return
			}
			
			if (DataObject.FilterBy != this.LastFilterBy) {
				this.ResetLastSelected();
			}
			this.LastFilterBy = DataObject.FilterBy;
		
			DataObject.Data     = DataObject.Data.slice();
			DataObject.FilterBy = DataObject.FilterBy.toLowerCase();
			for (var ind = DataObject.Data.length-1; ind>=0;ind--) {
				DataObject.Data[ind]['_SourceRef'] = DataObject.DataID +'[' + ind + ']';
				if (DataObject.Data[ind][DataObject.FilterField].toLowerCase().indexOf(DataObject.FilterBy) == -1) {
					DataObject.Data.splice(ind, 1);
				}
			}
			
		}
		
		
		this.Data[DataObject.DataID] = DataObject;
		this.DataObject 			 = DataObject;
		
		this.ValidateRange();

		//
		//	Build Display Array
		//
		this.DisplayData = [];
		
		var Row  	 = DataObject.StartRow;
		var Rows 	 = DataObject.EndRow;

		var AddedRows = -1;
		if (Rows > 0 || this.DisplayData['toArray'] != undefined) {
			
			this.DisplayData = HG_ArrayInsert(this.DisplayData, DataObject.Data, Row);
						
			///this.DisplayData = DataObject.Data;
			for (Row;Row<Rows;Row++) {
				AddedRows++;
				
				if (this.ShowRowCounter == true) {
					this.DisplayData[Row]['_Counter'] = Row;
				}
				if (DataObject.FilterField == undefined) {
					this.DisplayData[Row]['_SourceRef'] = DataObject.DataID +'[' + Row + ']';
				}
				this.DisplayData[Row]['_Index'] = AddedRows;
			}
			/*
			if (Rows==1) {
				if (this.ShowRowCounter == true) {
					this.DisplayData[0][0]['_Counter'] = Row;
				}
				if (this.DisplayData[0][0] == undefined) {
					//this.DisplayData[0][0]['_SourceRef'] = DataObject.DataID +'[0]';
				}
				this.DisplayData[0][0]['_Index'] = 0;
			}*/
			
			// Trim the DisplayData Array to only what you can see -- Makes sorting possible
			this.DisplayData.splice(Rows, Rows - DataObject.StartRow);
			if (DataObject.StartRow > 0) {
				this.DisplayData.splice(0, DataObject.StartRow);
			}
			
		} else {
				var DObject = HG_CopyObject(DataObject.Data);
				DObject._SourceRef = '_DataGrids["' + this.id +'"].Data["' + DataObject.DataID +'"].Data';
				this.DisplayData.push(DObject);
		}
	
	}
	
	
	//
	//	@AddData
	//
	//	DataObject = {
	// 		Data:Data As {}
	//  	StartRow:
	//  	EndRow:
	//		FieldList: 'Col1,Room,GN,LK'
	//		RemoveRows: {Index, Rows}
	//		Action:{Action:''}
	//	},
	//	Refresh: true | false
	//
	DataGrid.prototype.AddData = function(DataObject, Refreshing) {
		
		if (DataObject == undefined ) {
			alert('Developer: (AddData) DataGrid - DataObject was not provided');
			return false;
		}
		
		
		if (DataObject.Data == undefined || DataObject.DataID == undefined) {
			alert('Developer: (AddData) DataGrid - Data or DataID was not provided');
			return false;
		}
		
		if (DataObject.Action == undefined) { 
			DataObject.Action  = 'Up|alert("Developer: (AddData) DataGrid  - Action was not provided for ' + DataObject.DataID + '")';
		}
		
		this.DataSource = DataObject.Data;
		

		//
		//	Call this to remember the last selected row. Just incase we want to know.
		//
		this.GetLastSelected();
		
		//
		//	If Remove Option Exists -- Execute Removal which will manage this.DisplayData also
		//
		if (DataObject.RemoveRows != undefined) {
			this.RemoveRows(DataObject.RemoveRows);
		}
		
		//
		// Create/Update Display Data
		//
		this.CreateDisplayData(DataObject);
		

		//var RowsToAdd = (this.DisplayRows() > this.PageSize) ? this.PageSize : (this.DisplayRows() > this.TableBody.rows.length) ? this.DisplayRows() - this.TableBody.rows.length : 0;
		var RowsToAdd = this.ViewableRows;

		//
		//	Create/Update  DataGrid Output Table
		//
	 	ListInsertRow( this.TableBody
					  , { Index: DataObject.Index
						, Cells: this.Columns
						, Rows:  RowsToAdd
						}
					  );

	
		//
		//	Display
		//
		this.DisplayDataGrid();

		return true;
			
	}
	
	
	
	/***
	//
	//   Name: 
	//	
	//	Parameters:
	//		
	//		
	*/
	DataGrid.prototype.DisplayDataGrid = function() {

		var DataObject = this.DataObject;
		
		var Row  	 = 0;
		var Rows 	 = this.ViewableRows;
		var Selected = '';
		
		if (Rows == 0) {
			return;
		}


		this.ApplyAltColors();


		_DataGrids[this.id].DisplayData = this.DisplayData;

		var TblRow = -1;
		for (Row;Row<Rows;Row++) {

			TblRow++;
			var DataColumn   = 0;
			var FormatColumn = -1;
			
			
			//
			//	Get Row based on Array of Data or Single Object
			//
			//if (Rows > 1) {
				//
				//	Get Value for Output
				//
				Selected = this.DisplayData.toArray()[Row];
				var SelectedStr = '_DataGrids["' + this.id +'"].DisplayData.toArray()[' + Row + ']';
			/*} else {
				//
				//	Get Value for Output
				//
				Selected = this.DisplayData[0][0];
				var SelectedStr = '_DataGrids["' + this.id +'"].DisplayData[0][0]';
			}*/
			
			if (Selected == undefined) {
				alert('Developer: DataGrid ' + this.id + ', Row ' + Row + ' has no data');
				return
			}

			for (var Column=0; Column<this.Columns; Column++) { 

				if (Column > 0) { // Column 0 is always the action whether used or not
				
					FormatColumn++;
					//
					//	Default Column Level Formatting
					//
					this.SetElements( this.TableBody.rows[TblRow].cells[Column]
									, this.BodyContainer['DefaultColumnElements']
									);
	
					//
					//	Column By Column Formatting
					//
					if (this.BodyContainer.Columns && this.BodyContainer.Columns[FormatColumn]) {
						this.SetElements( this.TableBody.rows[TblRow].cells[Column]
										, this.BodyContainer.Columns[FormatColumn].Elements);
					}
				}
				
			
				//
				//	Column Level Formatting
				//
				if (this.StartColumns > 0 && Column < this.StartColumns) {
					
					var CurField = '&nbsp;';
					var CurFieldName = '__NONE';

				} else {
					DataColumn++;

					var CurFieldName= GetToken(DataObject.FieldList, DataColumn, ',')
					var CurField 	= Selected[CurFieldName];

					if (CurField != undefined) {
						if (CurField.Elements != undefined) {
							
							this.SetElements( this.TableBody.rows[TblRow].cells[Column]
											, CurField.Elements);
							CurField = CurField.Value;
	
						}
					} else {
						CurField = '';
					}
				}

				this.TableBody.rows[TblRow].cells[Column].innerHTML = (String(CurField)=='') ? '&nbsp;' : this.Formatters[CurFieldName] != undefined ? this.Formatters[CurFieldName](CurField, Selected) : CurField;
				
			}

			//
			//	Set Value
			//
			this.TableBody.rows[TblRow].cells[0].className = "Action";
			this.TableBody.rows[TblRow].cells[0].noWrap    = null;
			if (DataObject.Action != undefined) { 
				this.TableBody.rows[TblRow].cells[0].innerHTML = ReplaceStr(DataObject.Action.Action, '_Selected_', SelectedStr) + '/*' + Selected[this.SortKeyField] + '*/';
			}


			//
			//	Row Level Formatting
			//

			if (Selected[DataObject.RowFormatField] != undefined) {
				
				this.SetElements( this.TableBody.rows[TblRow]
								, Selected[DataObject.RowFormatField]
								);
				
			}
		}
		
		if (DataObject != undefined) {
			this.ApplyRowCounter(DataObject.StartRow);
		}
		
		ResizeExecuteAll();

	}
	
	
	/***
	//
	//   Name: RemoveRows
	//	
	//	Parameters:
	//		RemoveRowObject { Index, Rows, Source(true||false) }
	//		
	*/
	DataGrid.prototype.RemoveRows = function(RemoveRowObject) {
		
		ListRemoveRow(this.TableBody, RemoveRowObject);

		if (RemoveRowObject.Index > -1)  {
			if (RemoveRowObject.Source == true && RemoveRowObject.Rows == 1) {
				var SRow = GetToken(GetToken(this.DisplayData[RemoveRowObject.Index]._SourceRef, 2, '['), 1, ']');
				this.DataSource.splice(SRow, 1);
			}
			this.DisplayData.splice(RemoveRowObject.Index, RemoveRowObject.Rows);
		} else {
			// Remove All
			this.DisplayData.length = 0;
			if (RemoveRowObject.Source == true) {
				this.DataSource.length = 0;
			}
		}

		this.ApplyAltColors();
		this.ApplyRowCounter();
		
	}
	
	
	
	/***
	//
	//   Name: 
	//	
	//	Parameters:
	//		
	//		
	*/	
	DataGrid.prototype.Bottom = function() {
		this.Body.scrollTop = 100000;
	}



	/***
	//
	//   Name: 
	//	
	//	Parameters:
	//		
	//		
	*/
	DataGrid.prototype.Top = function() {
		this.Body.scrollTop = 0;
	}
	
	
	
	/***
	//
	//   Name: 	
	//	
	//	Parameters:
	//		
	//		
	*/
	DataGrid.prototype.Next = function() {
		this.NextPage(1);
	}
	
	
	
	/***
	//
	//   Name: 
	//	
	//	Parameters:
	//		
	//		
	*/	
	DataGrid.prototype.Previous = function() {
		this.NextPage(-1);
	}


	
	/***
	//
	//   Name: 
	//	
	//	Parameters:
	//		
	//		
	*/
	DataGrid.prototype.NextPage = function(PageDir) { // 1 || -1
	
		this.DataIndex += (this.PageSize * PageDir);
		this.DataObject.StartRow   = this.DataIndex;
		this.DataObject.EndRow     = this.DataIndex + this.PageSize;
		this.ValidateRange();
		this.DataObject.RemoveRows = {Rows:-1};
		this.AddData(this.DataObject);
		
		if (this.LastSortField != undefined) {
			this.Sort(this.LastSortField, this.SortObjects[this.LastSortField]);
		}
	
	}



	/***
	//
	//   Name: 
	//	
	//	Parameters:
	//		
	//		
	*/
	DataGrid.prototype.ValidateRange = function() {

		if (this.Rows() < this.PageSize) {
			this.PageSize = this.Rows()
		} else {
			this.PageSize = this.DefaultPageSize;
		}
		
		if (this.DataObject.Index == undefined) {
			this.DataObject.Index = -1;
		}
		
	
		if (this.DataObject.StartRow == undefined || this.DataObject.StartRow == '') {
			this.DataObject.StartRow = 0;
		}

		if (this.DataObject.EndRow == undefined || this.DataObject.EndRow == '') {
			if (this.Rows==0) {
				this.DataObject.EndRow = 0;	
			} else {
				this.DataObject.EndRow = this.PageSize;	
			}
		}


		if (this.DataObject.StartRow < 0) {
			this.DataObject.StartRow = 0;
			this.DataObject.EndRow   = this.PageSize;
			this.DataIndex 			 = 0;
		}
		
		if (this.DataObject.EndRow >= this.Rows()) {
			this.DataObject.StartRow = Number(this.Rows() - Number(this.PageSize));
			if (this.DataObject.StartRow < 0) { 
			this.DataObject.StartRow = 0;
			}
			this.DataObject.EndRow   = this.Rows();
			this.DataIndex 			 = this.DataObject.StartRow;
		}
		
		if (this.DataObject.EndRow - this.DataObject.StartRow > this.PageSize + 1) {
			this.DataObject.EndRow = this.DataObject.StartRow + this.PageSize;	
		}

		this.ViewableRows = Number(this.DataObject.EndRow) - Number(this.DataObject.StartRow);
	}

	
	/***
	//
	//   Name: Sort -- Sort the DisplayData and Redraw Datagrid
	//	
	//	Parameters:
	//		Field
	//		Direction: 1 Asc | -1 Desc
	*/	
	DataGrid.prototype.Sort = function(Field, Direction) {

		var DataObject = this.DataObject;
		
		var Setup = Direction;
		
		if (Field == undefined && Direction == undefined) {
			Field     = this.LastSortField;
			Direction = -3;
		}
		
		if (Direction==-2) {
			Direction=1;	
		}

		if (Direction==-3 && this.LastSortField != '') {
			Direction=this.SortObjects[Field];	
		}

		if (this.GetLastSelected() != -1) {
			this.LastSelectedActionKey = this.TableBody.rows[this.GetLastSelected()].cells[0].innerHTML;
		}


		//
		//	If Remove Option Exists -- Execute Removal which will manage this.DisplayData also
		//
		ListRemoveRow(this.TableBody, {Rows:-1});
		
	
		var RowsToAdd = (this.DisplayRows() > this.PageSize) ? this.PageSize : (this.DisplayRows() > this.TableBody.rows.length) ? this.DisplayRows() - this.TableBody.rows.length : 0;
		
		//
		//	Create/Update  DataGrid Output Table
		//
	 	ListInsertRow( this.TableBody
					  , { Index: 0
						, Cells: this.Columns
						, Rows:  this.ViewableRows
						}
					  );

		
		if (Direction == undefined && this.SortObjects[Field] == undefined) { 
			Direction = 1 
		} else if (this.SortObjects[Field] != undefined && (Direction == undefined || Direction == 0)) {
			Direction = this.SortObjects[Field] * -1;
		}

		this.SortObjects[Field] = Direction;
		
		if (this.LastSortField != '') {
			GetID(this.id + '_S_' + this.LastSortField).innerHTML = '';
		}
		
		if (Direction == 1) {
			GetID(this.id + '_S_' + Field).innerHTML = '<img src="/Images/SortArrowDown.png">';	
		} else {
			GetID(this.id + '_S_' + Field).innerHTML = '<img src="/Images/SortArrowUp.png">';	
		}
		
		this.LastSortField = Field;

		if (Setup > -2 || Setup == undefined) {
			this.DisplayData.sort(function(a,b) { return Calculate_NaturalSortObject(a,b,Field, Direction)});
			this.DisplayDataGrid();
		}
		
		
		if (this.GetLastSelected() != -1) {
			this.SelectRowByValue(GetToken(this.LastSelectedActionKey, 2, '/*'), 0, true, true);
		}
		
	}
	
	
	
	/***
	//
	//   Name: SelectRow
	//	
	//	Parameters:
	//		Index - Row Index
	//		CancelAction - Do not execute the click just highlight
	*/
	DataGrid.prototype.SelectRow = function(Index, CancelAction) {

		if (Index == undefined) {
			Index = this.GetLastSelected();
		}

		if (Index == -1) {
			return false;
		}
		
		if (!isNaN(Number(Index))) {
			ListSelectRow('TBL_Body_' + this.id, Index, CancelAction);
		 } else {
			this.SelectRowByValue(Index, 0, CancelAction, true); 
		 }
		
		return true;
		
	}
	
	
	/***
	//
	//   Name: SelectRowByValue
	//	
	//	Parameters:
	//		ValueToMatch - 
	//		ColumnIndex	 - Column to Check
	//		CancelAction - Do not execute the click just highlight
	*/
	DataGrid.prototype.SelectRowByValue = function(ValueToMatch, ColumnIndex, CancelAction, IndexSearch) {

		if (ValueToMatch == undefined) {
			return false;
		}
		
		if (ColumnIndex == undefined) {
			ColumnIndex = 0;
		}
		
		ListSelectRowByValue('TBL_Body_' + this.id, undefined, ColumnIndex, ValueToMatch, CancelAction, IndexSearch);
	
		return true;
		
	}
	
	
	
	/***
	//
	//   Name: GetLastSelected
	//	
	//	Parameters:
	//		
	//		
	*/
	DataGrid.prototype.GetLastSelected = function() {

		if (ListGroup['TBL_Body_' + this.id] == undefined || ListGroup['TBL_Body_' + this.id].LastSelectedRow == -1 && this.LastSelectedRow == -1) {
			var Index =  -1;
		} else if (ListGroup['TBL_Body_' + this.id].LastSelectedRow != -1) {
			var Index = ListGroup['TBL_Body_' + this.id].LastSelectedRow;
			this.LastSelectedRow = Index;
		} else {
			var Index = this.LastSelectedRow;
		}
		
		return Index;
	}
	
	
	
	/***
	//
	//   Name: ResetLastSelected
	//	
	//	Parameters:
	//		
	//		
	*/
	DataGrid.prototype.ResetLastSelected = function() {

		if (ListGroup['TBL_Body_' + this.id] != undefined) {
			ListGroup['TBL_Body_' + this.id].LastSelectedRow = -1;
		}
		this.LastSelectedRow = -1;
	}
	
	
	/***
	//
	//   Name: Filter
	//	
	//	Parameters:
	//		Parameters  - FilterData
	//					- FilterField
	//					- FilterBy
	//					- FilterMessage
	//					- + Parameters that would be passed to DHE_SelectOptions
	*/
	DataGrid.prototype.Filter = function(Parameters) {
		
	
		if (Parameters.FilterData == undefined) { 
			return []
		}
		
		
		if (Parameters.FilterField == undefined || Parameters.FilterField == '') { 
			Parameters.FilterField = 'Value'
		}
		
		if (Parameters.FilterBy == undefined || Parameters.FilterBy == '' || Parameters.FilterBy == Parameters.FilterDefault) { 
			if (Parameters.FilterMessage == undefined) {
				return Parameters.FilterData
			} else {
				var NewArr = new Array();
				NewArr[0] = {};
				NewArr[0][Parameters.DisplayField] = Parameters.FilterMessage;
				NewArr[0][Parameters.ValueField]   = '';
				return NewArr; 
			}
		}
		
		
	
		//
		//	Options provided as a Object (Display, Value)
		//
		if (typeof(Parameters.FilterData) == 'object') {
		
			//
			//	Array Object 
			//
			if (Parameters.FilterData['toArray'] == undefined) {
				var NewObj = new Object();
				for (var t in Parameters.FilterData) {
					var str = unescapeXML(Parameters.FilterData[t][Parameters.FilterField]);
					if (str.indexOf(Parameters.FilterBy) > -1) {
						NewObj[t] = Parameters.FilterData[t];
					}
				}
			}
			
			//
			//	Array
			//
			if (Parameters.FilterData['toArray'] != undefined) {
				var NewObj = new Array();
				var Count = 0;
				for (var t = 0; t<Parameters.FilterData.toArray().length;t++) {
					var str = unescapeXML(Parameters.FilterData[t][Parameters.FilterField]);
					if (str.indexOf(Parameters.FilterBy) > -1) {
						NewObj[Count++] = Parameters.FilterData[t];
					}
				}
			}
		
			return NewObj;
		
		} else {
			
			return Parameters.FilterData;
		}
		
	
	}
	
	
	/***
	//
	//   Name: 
	//	
	//	Parameters:
	//		
	//		
	*/	
	DataGrid.prototype.Destory = function() {

		if (_DataGrids[this.id] == undefined) {
			return false
		}
		
		ListRemove('TBL_Body_' + this.id);

		GetID(_DataGrids[this.id].Container.id).innerHTML = '';
		delete _DataGrids[this.id];

		return true;
	}

	
	
	/***
	//
	//   Name: memory (CLASS)
	//	
	//		
	*/
	function memory() {
	
		this.MemoryBlocks  = new Object();	// Object with Arrays
		this.Index  	   = 0;
		
		this.AddBlock({BlockID:'_MemoryRoot', ParentID:'', CellID: ''});
	}
	
	
	
	/***
	//
	//   Name: Add
	//
	//	
	//	Parameters:
	//		- MemoryOptions
	//			- BlockID
	//			- CellID
	//			- ParentID
	//			- ObjectRef
	//			- DestoryFunc
	//		
	*/
	memory.prototype.Add = function(Memory) {
		
		
		var MemoryBlock = this.AddBlock(Memory);
		
		if (Memory.CellID == undefined) { 
			return false;
		}

		if (Memory.ObjectRef == undefined) { 
			alert('No Ref');
			return false;
		}


		Memory.Index 						= this.IncIndex();
		MemoryBlock.Cells[Memory.CellID]	= Memory;
		
	}
	
	
	
	/***
	//
	//   Name: AddBlock
	//
	//	
	//	Parameters:
	//		- Memory{}
	//			- BlockID
	//			- MemoryID
	*/
	memory.prototype.AddBlock = function(Memory) {
		
		var BlockID = Memory.BlockID;
		
		if (BlockID == undefined) { 
			BlockID        = '_MemoryRoot';
			Memory.BlockID = BlockID;
		}
		
		if (this.MemoryBlocks[BlockID] == undefined) {
			//
			//	Create Block
			//
			this.MemoryBlocks[BlockID] 			= new Object();
			this.MemoryBlocks[BlockID].Index 	= this.IncIndex();
			this.MemoryBlocks[BlockID].BlockID 	= BlockID;
			this.MemoryBlocks[BlockID].Cells 	= new Object;
			
			
		}
		
		
		if (this.MemoryBlocks[Memory.ParentID] == undefined || Memory.ParentID == undefined) {
			Memory.ParentID ='_MemoryRoot';
		}
		this.MemoryBlocks[BlockID].ParentID = Memory.ParentID;

		return this.MemoryBlocks[BlockID];
		
	}
	
	
	/***
	//
	//   Name: IncIndex
	//	
	//	Parameters:
	//		- MemoryOptions
	//			- GroupID
	//			- VarRef
	//		
	*/
	memory.prototype.IncIndex = function() {
		this.Index++;	
		return Number(this.Index);
	}
	
		
	/***
	//
	//   Name: GetIndex
	//	
	//	Parameters:
	//		- MemoryOptions
	//			- GroupID
	//			- VarRef
	//		
	*/
	memory.prototype.GetIndex = function() {
		return this.Index;
	}
	
	
	
	/***
	//
	//   Name: Free
	//	
	//	Parameters:
	//		- MemoryOptions
	//			- GroupID
	//			- VarRef
	//		
	*/
	MemoryFree = function(BlockID, Obj, Node) {
		
		if (BlockID==undefined || BlockID == '') {
			for (var BlockID in Memory.MemoryBlocks) {
				MemoryFree(BlockID);
				delete MemoryFree[BlockID];
			}
			return
		}
		
		if (Obj == undefined) {
			for (var Cell in Memory.MemoryBlocks[BlockID].Cells) {
				MemoryFree(BlockID, Memory.MemoryBlocks[BlockID].Cells, Cell);
				delete Memory.MemoryBlocks[BlockID].Cells[Cell];
			}
			delete Memory.MemoryBlocks[BlockID].Cells;
			delete Memory.MemoryBlocks[BlockID];
		} else {
			for (var Item in Obj[Node]) {
			
				if (typeof(Obj[Node][Item]) == 'object') {
					MemoryFree(BlockID, Obj[Node], Item);
				} else {

					if (typeof(Obj[Node][Item]) == 'string') {
						if (Item == 'CellID') {
							if (!isIE) {
								delete window[Obj[Node][Item]];
							} else {
								val = window[Obj[Node][Item]];
								delete val;
							}
						}
						delete Obj[Node][Item];
						
					} else {
						delete Obj[Node][Item];
					}
				}
			}
			delete Obj[Node];
		}
	
	}

			
	
	//
	//
	//
	Memory = new memory();


	
	
	

	App = function () {
	

	}

	
	
	App.Data = function () {
	
		this.id = CreateUUID(5);
		this.Data 		= new Object();
		this.DataObject = new Object();
		this.InProgress = false;
		Memory.Add({BlockID:this.id, CellID: 'Data',       ObjectRef: this});
	}
	
	
	
	/***
	//
	//   Name: GetHGON - Get Data
	//	
	//	Parameters:
	//	@DataObject - 	URL			 -- URL
	//					Target		 -- Target Varible to place Data In. If Not Provided This Will Create One
	//					Data		 -- JSON Data To Send
	//					CallBack	 -- CallBack Function
	//					Delay		 -- Milisec to wait before execution
	//					DelayCallBack -- Milisec to wait before execution
	*/
	App.Data.prototype.GetHGON = function(DataObject, Refresh) {

		if (this.IsDestroyed()) { return }

		if (this.InProgress) { return false }
		this.InProgress = true;




		if (Refresh == undefined) {
			var RequestDO = DataObject;
			this.DataObject = DataObject;
		} else {
			var RequestDO	= this.DataObject
		}
		
		var This = this;
		
		if (RequestDO.DelayCallBack == undefined) { 
			this.DataObject.DelayCallBack = 0
		}

		if (RequestDO.DelayCallBack == undefined) { 
			this.DataObject.Delay = 0
		}

		if (RequestDO.Data != undefined && typeof RequestDO.Data == 'object') {
			var RData = 'HGO=' +  HG_ObjectToJSON(RequestDO.Data) ;
		} else {
			var RData  = undefined;
		}

		HG_AJAX({  URL:		  RequestDO.URL
				 , OnSuccess: function(Content) { 
				 		This.SetData(Content) 
					}
				 , Fetch:     true
				 , PostText:  RData 
				});
		
	}


	/***
	//
	//   Name: Data - Access Target Object
	//	
	//	Parameters:
	//		
	//		
	*/
	App.Data.prototype.SetData = function(Content) {

		if (this.IsDestroyed()) { return }

		this.InProgress = false;
		
		
		if (Content == HG_AJaxError) {
			return false;	
		}


		if (typeof  this.DataObject.Target != 'undefined' && this.DataObject.Target.indexOf(',')>-1) {
			
			var GroupData = HG_JSONToObject(Content);

			for (var t = 0; t<GroupData.length; t++) {
				this.SetDataSet(GroupData[t], GetToken(this.DataObject.Target, t+1, ','));
			}

			if (this.DataObject.CallBack != undefined) {
				this.DataObject.CallBack();
			}
		
	   } else {
			this.SetDataSet(Content);
			if (this.DataObject.CallBack != undefined) {
				this.DataObject.CallBack(this.Data);
			}
	   }
	   
	}
	
	
	/***
	//
	//   Name: Data - Access Target Object
	//	
	//	Parameters:
	//		
	//		
	*/
	App.Data.prototype.SetDataSet = function(Content, Target) {

		if (this.IsDestroyed()) { return }


		if (Target != undefined) {
			HG_SetObject(Target, HG_JSONToObject(Content));
		} else {
			this.Data = HG_JSONToObject(Content);
		}

	}
	

	
	
	/***
	//
	//   Name: Refresh
	//	
	//	Parameters:
	//		
	//		
	*/
	App.Data.prototype.Refresh = function() {

		if (this.IsDestroyed()) { return }
		
		this.GetHGON(this.DataObject);

	}



	/***
	//
	//   Name: IsDestroyed
	//	
	//	Parameters:
	//		
	//		
	*/
	App.Data.prototype.IsDestroyed = function() {
		
		if (this.id != undefined) {
			return false;
		}
		
		alert('Developer: App Data Object no longer exist.');
		return true;

	}

	
	//
	// NOT DONE with IncludeTargetData
	//
	App.Data.prototype.Destroy = function(IncludeTargetData) {
		
		if (this.IsDestroyed()) { return }
		
		
		
		MemoryFree(this.id);
	}
	

	
	
	

