/* 
Constants to determine browser type / version
*/
var isOpera = navigator.userAgent.indexOf('Opera') > -1;
var isIE = navigator.userAgent.indexOf('MSIE') > 1 && !isOpera;
var isMoz = navigator.userAgent.indexOf('Mozilla/5.') == 0 && !isOpera;
var isMac = (navigator.appVersion.indexOf("Mac")!=-1) ? true : false;
var NS4 = (document.layers) ? true : false;
var IE4plus = (document.all) ? true : false;
var IE4 = ((document.all)&&(navigator.appVersion.indexOf("MSIE 4.")!=-1)) ? true : false;
var IE5 = ((document.all)&&(navigator.appVersion.indexOf("MSIE 5.")!=-1)) ? true : false;
var IE6 = ((document.all)&&(navigator.appVersion.indexOf("MSIE 6.")!=-1)) ? true : false;
var IE7 = ((document.all)&&(navigator.appVersion.indexOf("MSIE 7.")!=-1)) ? true : false;
var ver4 = (NS4 || IE4plus) ? true : false;
var NS6 = (!document.layers) && (navigator.userAgent.indexOf('Netscape')!=-1);
var isGecko = /gecko/i.test(navigator.userAgent); //added by dan-el
var docTitle = null;

/* 
Constants that enables/disables specific G2Page features
*/
var ENABLE_PROFILER = false;
var ENABLE_CLIENT_VALIDATION = true;
var ENABLE_POSTDATA_ONDEMAND = true;
var ENABLE_FAKE_POSTBACKS = false;
var NOTIFY_SERVER_HISTORY_CHANGE = false;
var CALLBACK_TIMEOUT = 5000; // the maximum time we will wait for a postback to return from server
// to enable this add in G2Page.PreRender:	TryRegisterG2ClientScriptFile("dhtmlHistory.js");

/*
Global window vars
*/
timings = [];
G2UseSyncCallbacks = false;
G2PartialPostDataElementIds = new Object();
G2InputChangedObservers = new Array();
var mainAdminTabControl = null;
G2AdminInputChangedObservers = new Object();
G2_EvalCache = {};

// a safty net for multiple post back all in the dame time.
var waitForCallback = null;


/*
Static methods that allows declaring various JS structures
*/


/*
G2_DeclareFunctions
Desc:
Methods declared with this function can be profiled
Usage:
regex to find function ggg(a, b, c)
function {.*}\({.*}\)
\1 : function(\2)
*/
G2_DeclareFunctions = function(json)
{
	1;
	for(var memberName in json)
	{
		var member = json[memberName];
		if(typeof(member)=="function")
		{
			member.name = memberName;
			eval(memberName+"=member;");
			if(ENABLE_PROFILER)
				Profiler.profile(member);
		}
	}
}

/*
G2_DeclareUtilInstance
Desc:
Allows declaring a static like instance in JS. Examples are: G2PopupManager, G2FrameManager, G2DOM
*/
G2_DeclareUtilInstance = function(instance)
{
	for(var memberName in instance)
	{
		var member = instance[memberName];
		if(typeof(member)=="function")
		{
			member.name = memberName;
			if(ENABLE_PROFILER)
				Profiler.profileUtilInstanceFunction(instance, member);
		}
	}
}

ImportInto = function(target, source)
{
	for(var memberName in source)
	{
		var member = source[memberName];
		target[memberName] = member;
		if(typeof(member)=="function")
		{
			member.name = memberName;
		}
	}
	if(source.toString!=Object.prototype.toString)
	{
		var member = source.toString;
		if(typeof(member)=="function")
			member.name = "toString";
		target.toString = member;
	}
}

G2_DeclareClass = function(type, name, baseType, json)
{
	type.name = name;
	if(baseType!=null)
		ImportInto(type.prototype, baseType.prototype);
	ImportInto(type.prototype, json);
	if(ENABLE_PROFILER)
	{
		for(var p in json)
		{
			var func = json[p];
			if(typeof(func)=="function")
				Profiler.profileTypeFunction(type, json[p]);
		}
	}

}

if(ENABLE_PROFILER)
{
	var Profiler = 
	{
		_pFuncs: [],
		profileUtilInstanceFunction : function(instance, func)
		{
			var pFunc = this._createProfilerFunction(func);
			if(pFunc==null)
				return;//cannot profile function
			instance[func.name] = pFunc;
		},
		profileTypeFunction : function(type, func)
		{
			var pFunc = this._createProfilerFunction(func);
			if(pFunc==null)
				return;//cannot profile function
			type.prototype[func.name] = pFunc;
		},
		profile : function(func)
		{
			var pFunc = this._createProfilerFunction(func);
			eval(func.name+"=pFunc;");
		},
		_createProfilerFunction : function(func)
		{
			if(func.name==null)
				return; //cannot profile function without a name
			var pFunc = function()
			{
				var pCallee = arguments.callee;
				pCallee.totalCalls++;
				var startInvoke = new Date().getTime();
				var result = pCallee.realFunc.apply(this, arguments);
				var endInvoke = new Date().getTime();
				var timeInvoke = endInvoke-startInvoke;
				pCallee.totalWithChildren += timeInvoke;
				var pCaller = pCallee.caller;
				var x = 0;
				while(pCaller!=null && pCaller.totalOfChildren==undefined && pCaller!=pCallee && x<5)
				{
					pCaller = pCaller.caller;
					x++;
				}
				if(pCaller!=null && pCaller.totalOfChildren!=undefined && pCaller!=pCallee)
				{
					pCaller.totalOfChildren+=timeInvoke;
				}
				return result;
			}
			pFunc.realFunc = func;
			pFunc.totalWithoutChildren = 0;
			pFunc.totalOfChildren = 0;
			pFunc.totalWithChildren = 0;
			pFunc.totalCalls = 0;
//			pFunc.totalOfChildrenWithProfiler = 0; //
			pFunc.name = func.name;
			this._pFuncs.push(pFunc);
			return pFunc;
		},
		clearData : function()
		{
			for(var i=0;i<this._pFuncs.length;i++)
			{
				var pFunc = this._pFuncs[i];
				pFunc.totalWithoutChildren = 0;
				pFunc.totalOfChildren = 0;
				pFunc.totalWithChildren = 0;
				pFunc.totalCalls = 0;
			}
		},
		takeSnapshot : function(sortBy)
		{
			if(sortBy==null)
				sortBy="totalCalls";
			var desc = sortBy!="name" ? -1 : 1;
			var arr = [];
			for(var i=0;i<this._pFuncs.length;i++)
			{
				var pFunc = this._pFuncs[i];
				pFunc.totalWithoutChildren = pFunc.totalWithChildren-pFunc.totalOfChildren;
				if(pFunc.totalCalls>0)
					arr.push(pFunc);
			}
			var array = arr.sort(function(x, y)
			{
				var valueX = x[sortBy];
				var valueY = y[sortBy];
				if(valueX==null || valueY==null)
				{
					if(valueX==valueY)
						return 0;
					return valueX==null ? 1*desc : -1*desc;
				}
				if(typeof(valueX)=="string" && typeof(valueY)=="string")
					return valueX.localeCompare(valueY)*desc;
				return (valueX.valueOf()-valueY.valueOf())*desc;
			});
			return array;
		},
		createDebugDiv : function()
		{
			if(Profiler.debugWindow==null)
			{
				if(window.opener!=null && window.opener.Profiler.debugWindow!=null)
				{
					Profiler.debugWindow = window.opener.Profiler.debugWindow;
				}
				else
				{
					var debugWindow = window.open(G2_MapPath('~/Client/Scripts/profiler.htm'), "debugWindow");
					Profiler.debugWindow = debugWindow;
				}
//				Profiler.debugWindow.registerWindow(window);
			}
		}
	}
	
}

/* 
Language extenstions
*/

String.prototype.endsWith = function String$endsWith(suffix) 
{
	return (this.substr(this.length - suffix.length) === suffix);
}

String.prototype.startsWith = function String$startsWith(prefix) 
{
  return (this.substr(0, prefix.length) === prefix);
}
String.prototype.contains = function(s)
{
	return this.indexOf(s)!=-1;
}


/* 
ASP.NET JS overrides
*/

if(typeof(WebForm_DoCallback)=="function")
{
	AspNet_WebForm_DoCallback = WebForm_DoCallback;
	AspNet_WebForm_CallbackComplete_Sync = WebForm_CallbackComplete;
}
window.net__doPostBack = window.__doPostBack;

window.__doPostBack = function(eventTarget, eventArgument,forcesilent) 
{
	// check lock to prevent multuple postbacks all in the same time
	if(waitForCallback)
	{
		// if we pass the the timeout value go on
		if(new Date() - waitForCallback <= CALLBACK_TIMEOUT)
		{
			// try again in 0.5 seconds
			window.setTimeout(function () { __doPostBack(eventTarget, eventArgument, forcesilent); }, 500);
			return;
		}
	}
	// lock this code
	waitForCallback = new Date();

  if (theForm==null || theForm.__EVENTTARGET == null) //This is sometimes caused when posting back from a popup that's closed.
		return;

	if (forcesilent == null)
		forcesilent = false;
	//Validation
	var targetEl = null;
	if(typeof(eventTarget)=="object")
	{
		targetEl = eventTarget;
		eventTarget = eventTarget.id;//String.Replace(eventTarget.id, "_", "$");
	}
	else
	{
		targetEl = G2_GetEventTargetElement(eventTarget);
	}
  if(targetEl!=null)
  {
		// 'CancelPostBackOnDisabled' attribute was added for canceling post back in case of disabled linkButton.
		// Any one can add this attribute in order to cancel postBack if the control is disabled.
		if (targetEl.cancelPostBackOnDisabled && targetEl.isDisabled)
			return;
			
		if (document.isPostingFromAClosedPopup) //Handle 'error 84' in IE when trying to postback from a closed popup.
			return;
    if(ENABLE_CLIENT_VALIDATION && (G2DOM.G2GetAttribute(targetEl,"causesvalidation")=="true" || (window.validateAll == "true" && G2DOM.G2GetAttribute(targetEl,"ignorevalidation") != "true"))) 
    {
      if(typeof(G2Validation_PerformValidation)=="function" && G2Validation_PerformValidation(targetEl)==false) 
        return;
      if(targetEl.onvalidatedclientclick!=null)
      {
     		var func = new Function(targetEl.onvalidatedclientclick);
				var res = func.call(targetEl);
				if (res == false)
					return;
      }
      if(targetEl.onbeforepostback!=null)
        window[targetEl.onbeforepostback](eventTarget, eventArgument);
    }
  }
  else
  {
    Debug.writeln("Could not find element " + eventTarget);
  }
  
 	if (theForm.onsubmit && (theForm.onsubmit() == false))
    return false;

  //Disable tooltips during silent postbacks.
  G2PopupManager.disableTooltips();
  //Display the processing image
  if (targetEl != null)
  {
    if (G2DOM.G2GetAttribute(targetEl,"showprocessingimage")=="true")
    {
      ShowProcessingImage(targetEl);
    }
    if (G2DOM.G2GetAttribute(targetEl,"showdisabler")=="true")
    {
      G2_ShowDisabler(true); 
    }
  }
  else
  {
    Debug.writeln("Could not find element " + eventTarget);
  }
  
  if(window.OnBeforePostbackClientFunction!=null)
  {
     window[window.OnBeforePostbackClientFunction]({eventTarget:eventTarget, eventArgument:eventArgument});
  }
  var doClassicPostBack = !G2IsSilent(eventTarget, eventArgument, targetEl) && !forcesilent;
  if(doClassicPostBack && !ENABLE_FAKE_POSTBACKS)
  {
 		for(var id in G2PartialPostDataElementIds)
		{
		  var element = G2PartialPostDataElementIds[id];
		  if(element==null || element.parentElement==null)
		  {
			  element = document.getElementById(id);
			}
			//isValueDirty might not be declared because it might've been updated dynamically, and lazy initialized.
			if(element!=null && typeof(element.isValueDirty)=="function" && !element.isValueDirty())
			{
				element.disabled = true;
			}
		}
 		for(var id in G2_PreventPostElementIds)
		{
			var element = document.getElementById(id);
			if(element!=null)
				element.disabled = true;
		}
		//we do not use the real __doPostback because it checks onsubmit again.
		theForm.__EVENTTARGET.value = eventTarget;
		theForm.__EVENTARGUMENT.value = eventArgument
		theForm.submit();

//		window.net__doPostBack(eventTarget, eventArgument);
		return;
  }
	var arg;
	if(ENABLE_FAKE_POSTBACKS && doClassicPostBack)
	{
		arg = "FakePostBack";
	}
	else
		arg = "SilentPostBack";
//		
  theForm.__EVENTTARGET.value = eventTarget;
  theForm.__EVENTARGUMENT.value = eventArgument;
	var arg = arg+"|" + eventTarget + "|" + eventArgument;
	G2_DoCallback('__Page', arg ,G2CallbackManager_HandleResult,{eventTarget:eventTarget,eventArgument:eventArgument},G2_OnCallbackError,false, false);
}

function WebForm_FireDefaultButton(event, target)
{
    if (event.keyCode == 13 && !(event.srcElement && (event.srcElement.tagName.toLowerCase() == "textarea"))) 
    {
			var defaultButton;
			if (__nonMSDOMBrowser) 
			{
				defaultButton = document.getElementById(target);
			}
    else 
    {
      defaultButton = document.all[target];
    }
    if (defaultButton && typeof(defaultButton.click) != "undefined") 
    {
			//added by dan-el - causes any other focused element to blur and fire the onchange event, #7457
			try
			{
				defaultButton.focus(); 
			}
			catch(err)
			{
				event.srcElement.blur();
			}
			defaultButton.click();
      event.cancelBubble = true;
      if (event.stopPropagation) 
				event.stopPropagation();
      return false;
    }
  }
  return true;
}
G2_onHistoryChange = function(newLocation, historyData)
{
	__doPostBack("__Page", "HistoryChange|"+newLocation, true);
}

/* 
G2 General Library Util Instance
*/

G2 = 
{
	AppendQueryString : function(url, qs)
	{
		if(url.search(/\?/)!=-1)
			return url+"&"+qs;
		return url+"?"+qs;
	},
	ArgumentsFrom : function(args, index)
	{
		var arr = [];
		for(var i=index;i<args.length;i++)
		{
			arr.push(args[i] || null);
		}
		return arr;
	},
	GetRelativeMouseX : function(e, relativeElement)
	{
		return e.clientX-G2_GetX(relativeElement)+relativeElement.scrollLeft;
	},
	GetRelativeMouseY : function(e, relativeElement)
	{
		return e.clientY-G2_GetY(relativeElement)+relativeElement.scrollTop;
	},
	Delegates : {},
	GetDelegate : function(target, func)
	{
		if(target==null)
			return func;
		if(typeof(func)=="string")
			func = target[func];
		var key = this.GetHashKey(func)+"$$"+this.GetHashKey(target);
		var delegate = this.Delegates[key];
		if(delegate==null)
		{
			delegate = function()
			{
				return arguments.callee.func.apply(arguments.callee.target, arguments);
			};
			delegate.func = func;
			delegate.target = target;
			delegate.isDelegate = true;
			this.Delegates[key] = delegate;
		}
		return delegate;
	},

	_hashIndex : 1,
	GetHashKey : function(obj)
	{
		if(obj===undefined)
			return "undefined";
		if(obj===null)
			return "null";
		var typeOf = typeof(obj);
		if(typeOf=="object" || typeOf=="function")
		{
			if(obj._hashKey==null)
			{
				obj._hashKey = typeOf+"$"+this._hashIndex;
				this._hashIndex++;
			}
			return obj._hashKey;
		}
		return obj.valueOf().toString();
	},
	historyIndex : 0,
	// check if any control was registered due to a change.
	ChangesWasMadeToControls : function()
	{
		if (this.changedInputs)
		{
			var i=0;
			for (var j in this.changedInputs)
				i++;
			if (i == 0)
				return false;
		}		
		return true
	},

	notifyInputPropertyChanged : function(e)
	{
	1;//value for textboxes, checked for checkboxes, selectedIndex for combos
		if(e.propertyName=="value" || e.propertyName=="checked" || e.propertyName=="selectedIndex") //checked is for checkbox and radiobutton
			this.notifyInputChanged(e.srcElement);
	},
	changedInputs : new Object(),
	notifyInputChangedFF_Watch : function(inputId, oldVal, newVal)
	{
		G2.notifyInputChanged(this);
		return newVal;
	},
	notifyInputChangedFF_Event : function(evnt)
	{
		G2.notifyInputChanged(evnt.target);
	},
	RegisterPropertyChangeWatch : function(elementID)
	{
		if (isMoz)
		{
			var e = document.getElementById(elementID);
			e.watch("value",this.notifyInputChangedFF_Watch	);
			e.watch("checked",this.notifyInputChangedFF_Watch);
			e.watch("selectedIndex",this.notifyInputChangedFF_Watch);
			e.addEventListener("change",this.notifyInputChangedFF_Event,false);
		}
	},	
	RegisterPropertyChangeWatchWithHandler : function(elementID,handler)
	{
		if (isMoz)
		{
			var e = document.getElementById(elementID);
			var watchHandler = function(){handler(this);};
			e.watch("value",watchHandler);
			e.watch("checked",watchHandler);
			e.watch("selectedIndex",watchHandler);
			var eventHandler = function(evnt){handler(evnt.target);};
			e.addEventListener("change",eventHandler,false);
		}
	},	
	notifyInputChanged : function(input)
	{
	   if(input.isInitializing)
	    return;
		this.changedInputs[input.id] = input;
		if(input.notifyobserver == null || input.notifyobserver == "true")		
			this.fireNotifyInputChangedEvent();
	},
	undoNotifyInputChanged : function(input)
	{
		if(this.changedInputs[input.id] != null)
		{
			delete this.changedInputs[input.id];
		}
	},	
	notifyCheckBoxPropertyChange : function(e)
	{
		if(e.propertyName=="value" || e.propertyName=="checked")
		{
			var checkbox = e.srcElement;
			this.notifyInputChanged(checkbox);
			if(typeof(checkbox.g2PerformUndo)=="undefined")
			{
				checkbox.originalValue = !checkbox.checked; //the value before the click
				checkbox.g2PerformUndo = G2.CheckBox_PerformUndo;
				checkbox.g2SetOriginalValue = G2.CheckBox_SetOriginalValue;
				checkbox.g2IsDirty = G2.CheckBox_IsDirty;
			}
		}
	},
	notifyCheckBoxClicked : function(checkbox)
	{
		this.notifyInputChanged(checkbox);
		if(typeof(checkbox.g2PerformUndo)=="undefined")
		{
			checkbox.originalValue = !checkbox.checked; //the value before the click
			checkbox.g2PerformUndo = G2.CheckBox_PerformUndo;
			checkbox.g2SetOriginalValue = G2.CheckBox_SetOriginalValue;
			checkbox.g2IsDirty = G2.CheckBox_IsDirty;
		}
	},
	CheckBox_PerformUndo : function(checkbox)
	{
		checkbox = checkbox || this;
		checkbox.checked = checkbox.originalValue;
	},
	CheckBox_SetOriginalValue : function(checkbox)
	{
		checkbox = checkbox || this;
		checkbox.originalValue = checkbox.checked;
	},
	CheckBox_IsDirty : function(checkbox)
	{
		checkbox = checkbox || this;
		return checkbox.checked != checkbox.originalValue;
	},
	getAdminToolsActiveTabId : function ()
	{
		if (mainAdminTabControl == null)
			mainAdminTabControl = $('adminTabControlDiv').firstChild;
		if (mainAdminTabControl.ActiveTab) //already initialized
			return mainAdminTabControl.ActiveTab.id;
		else //not yet initialized
			return mainAdminTabControl.activetabid;
	},
	getAdminToolsObserversInTab : function(tabId)
	{
		if (typeof(tabId) == 'undefined')
			tabId = this.getAdminToolsActiveTabId();
		if (typeof (G2AdminInputChangedObservers[tabId]) == 'undefined')
			G2AdminInputChangedObservers[tabId] = new Object();
		return G2AdminInputChangedObservers[tabId]; 
	},
	attachObserver : function (id, tabId)
	{		
		var observers = this.getAdminToolsObserversInTab(tabId);
		if (observers[id] == true) //Change by Adi Eduard
		  return;
		observers[id] = false; 
	},
	detachObserver : function (id, tabId)
	{		
		var observers = this.getAdminToolsObserversInTab(tabId);
		delete observers[id];
	},
	fireNotifyInputChangedEvent : function (tabId)
	{
	  if (window.IsAdminToolsMainPage != true) //this feature works only in the admin tools
			return; 
		var observers = this.getAdminToolsObserversInTab(tabId);
		for(var obs in observers)
		{
			observers[obs] = true;
		}
	},
	setObjectChanged : function (id, tabId)
	{
		var observers = this.getAdminToolsObserversInTab(tabId);
		observers[id] = true;
	},
	setObjectUnchanged : function (id, tabId)
	{
		var observers = this.getAdminToolsObserversInTab(tabId);
		(observers[id] != null)
			observers[id] = false;
	},
	IsObjectChanged : function (id, tabId)
	{
			var observers = this.getAdminToolsObserversInTab(tabId);
			return observers[id] == true;
	},
	AreThereAnyChanges : function ()
	{
		var allObservers = G2AdminInputChangedObservers;
		for (var tab in allObservers)
		{
			tabObservers = allObservers[tab];
			for (var obsId in tabObservers)
			{
				if (tabObservers[obsId] == true)
					return true;
			}
		}
		return false;
	}
	
};
G2_DeclareUtilInstance(G2);

G2_DeclareFunctions(
{
	G2InitParentControl : function(sender, e)
	{
		if(sender.g2HasInitedParentControl)
			return;
		sender.g2HasInitedParentControl = true;
		var control = sender;
		var controlType;
		while(control!=null)
		{
			controlType = G2DOM.G2GetAttribute(control, "g2control")
			if(controlType!=null)
				break;
			control = control.parentElement;
		}
		if(control.g2IsInited)
			return;
		if(control.isDisabled)
			return;
		window[controlType+"_Init"](control, e);
		if(!control.g2IsInited)
			control.g2IsInited = true;
	},
	G2_VerifyControlInitialized : function(control, e)
	{
		if(control.g2IsInited)
			return;
		var controlType = G2DOM.G2GetAttribute(control, "g2control");
		if(controlType==null)
			return;
		window[controlType+"_Init"](control, e);
		if(!control.g2IsInited)
			control.g2IsInited = true;
	},

	G2_DoCallback : function(eventTarget, eventArgument, eventCallback, context, errorCallback, useAsync, classicPostback)
	{
	  G2_OnBeforeCallback();
	  WebForm_DoCallback(eventTarget, eventArgument, eventCallback, context, errorCallback, useAsync, classicPostback);
	},
	G2_OnBeforeCallback : function()
	{
		document.body.style.cursor="wait";
	},

	G2_OnCallbackError : function(result, context)
	{
		var err = "Callback Error: "+result;
		alert(err);
		
		G2_OnCallbackFinally(result, context);
	},

	G2_OnCallbackFinally : function(result, context)
	{
 		document.body.style.cursor = "";
 		//Close and reebable tooltips (disabled during silent postbacks)
 		G2PopupManager.enableTooltips();
 		G2PopupManager.closeAllTooltips();
	},
	//taken from aspnet scripts - performed MAJOR optimizations (removed the foreach loop)
	G2_InitCallback : function() 
	{
 		var context = {postData:new Array(), postCollection:new Array()};
		G2_InitCallbackRecursive(context);
		return context;
//		__theFormPostData =context.postData.join("");
//		__theFormPostCollection = context.postCollection;
	},


	G2CallbackManager_HandleResult : function(result, aspNetContext)
	{
		// unlock dopostback
		waitForCallback = null;
		
		var r = result.split("%||%");
		var context = {resultArray:r, aspNetContext:aspNetContext};
//		//moved to start by dan-el  
//		var viewState = r[4];
//		G2CallbackManager_UpdateViewState(viewState);
		//Handle hidden fields


		var scriptIncludes = r[1].split("||||");
		var srcArray = new Array();
		for(var i=0; i<scriptIncludes.length; i++)
		{
			var src = scriptIncludes[i];
			if(src==null || src=="")
				continue;
			srcArray.push(src);
		}
		G2_RegisterScripts(srcArray, function(){G2_HandleCallbackResultPhase2(result, context);});
		
		
		
	},

	
	G2_HandleCallbackResult_UpdateDomElements : function(htmlData)
	{
		for(var i=0; i<htmlData.length; i++)
		{
			if(htmlData[i]=="" || htmlData[i]==null)
				break;
			var element=document.getElementById(htmlData[i]);
			i++;
			var newHtml = htmlData[i];
			if (element != null)
			{
				var controlElement = element;
				if(element.getcontrolelement!=null)
				{
					controlElement = G2_Eval(element.getcontrolelement, element);
					if(controlElement==null)
					{
						G2_Warn("G2_HandleCallbackResult_UpdateDomElements", "controlElement wasn't found for element "+element.id);
						continue;
					}
				}
				G2DOM.G2ReplaceOuterHTML(controlElement,newHtml);
			}
		}
	},
	
	G2_Eval : function(code, target)
	{
		var cache = G2_EvalCache;
		var func = cache[code];
		if(func==null)
		{
			func = new Function(code);
			cache[code] = func;
		}
		return func.call(target);
	},
	StartTiming : function()
	{
		timings.push(new Date().getTime());
	},
	EndTiming : function(name)
	{
		name = name || arguments.callee.caller.name;
		var end = new Date().getTime();
		var start = timings.pop();
		var span= end-start;
//		if(span>500)
//			alert(name+" took "+span+"ms!");
	},
	
	G2_HandleCallbackResult_AddRepeaterElement: function(htmlData)
	{
		for(var i=0; i<htmlData.length; i++)
		{
			if(htmlData[i]=="" || htmlData[i]==null)
				break;
			var element=document.getElementById(htmlData[i]);
			i++;
			if(element != null)
			{
				var tbody = element.firstChild.tBodies[0];
				var newElement = G2DOM.G2CreateElementFromHtml(htmlData[i]);
				tbody.appendChild(newElement);
			}
		}		
	},
	
	G2_HandleCallbackResult_RemoveElement: function(itemsToRemove)
	{
		for(var i=0; i<itemsToRemove.length; i++)
		{
			if(itemsToRemove[i]=="" || itemsToRemove[i]==null)
				break;
			var element = document.getElementById(itemsToRemove[i]);			
			if(element != null)
			{
				element.removeNode(true)				
			}
		}		
	},
	
	G2_HandleCallbackResult_UpdateHiddenFields : function(hfHtml)
	{
		var div=document.createElement("DIV");
		div.innerHTML = hfHtml;
		var divChildren = div.children;
		var addElements = new Array();
		for(var i=0;i<divChildren.length; i++)
		{
			var hf = divChildren[i];
			var curHf = document.getElementById(hf.id);
			if(curHf!=null)
				curHf.value = hf.value;
			else
				addElements.push(hf); //we don't appendChild now because the length will change.
		}
		for(var i=0;i<addElements.length;i++)
		{
			document.forms[0].appendChild(addElements[i]);
		}
	},
	G2_HandleCallbackResult_UpdateActiveElement : function(activeElementID, prevActiveElement)
	{
		var el = document.getElementById(activeElementID);
		if(el!=null && el.tagName!="A" && prevActiveElement!=el)
		{
			var f = function()
			{	
				//the following line handles focusing an element that was replaced during a callback
				if(el.parentElement==null) //Element is detached from the dom
					el = document.getElementById(el.id);//Find the new element in the dom
				try
				{
				  el.isFocusingAfterPostback = true;//Indicate to the element that this is autofocus 
					el.focus(); //This may fail if the control is hidden etc.
				} 
				catch(e)
				{
				}
			}
			window.setTimeout(f, 50);
		}
	},
	G2_HandleCallbackResult_EvalStartupStatements : function(scriptData)
	{
		StartTiming();
		eval(scriptData);
		EndTiming();
	},
	G2_ReplaceCssClass : function(element, addCss, removeCss, inverse)
	{
		if(inverse)
		{
			var temp = removeCss;
			removeCss = addCss;
			addCss = temp;
		}
		var classes = G2_ParseCssClasses(element);
		classes.remove(removeCss);
		classes.add(addCss);
		G2_SetCssClasses(element, classes);

  },
	G2_RemoveCssClass : function(element, className)
	{
		var index = G2_FindWholeWord(element.className, className);
		if(index!=-1)
		{
			var begin = element.className.substr(0, index-1);
			var end = element.className.substr(index+className.length+1);
			if(begin!="" && end!="")
				element.className = begin+" "+end;
			else
				element.className = begin+end;
		}
  },
	G2_ParseCssClasses : function(element)
	{
		var list = element.className.split(/ /g);
		var obj = new ListSet();
		if(list.length==1 && list[0]=="")
		{
		}
		else
		{
			obj.addRange(list);
		}
		return obj;
  },
	G2_SetCssClasses : function(element, listset)
	{
		element.className = listset.toString(" ");
  },

	G2_AddCssClass : function(element, className)
	{
    if (!G2_ContainsCssClass(element, className)) 
    {
      if (element.className === '') 
      {
        element.className = className;
      }
      else 
      {
        element.className += ' ' + className;
      }
    }
  },
	G2_ContainsCssClass : function(element, className)
	{
		return G2_FindWholeWord(element.className, className)!=-1;
	},
	G2_FindWholeWord : function(text, word, seperator)
	{
		if(seperator==null)
			seperator = " ";
		if(word==null || word=="" || word.indexOf(seperator)!=-1)
			throw new Error("error in word: "+word);
		if(text=="")
			return -1;
		var x = 0;
		for(var i=0;i<text.length;i++)
		{
			if(text.charAt(i)==seperator)
			{
				if(x==word.length)
					return i-x;
				x=0;
			}
			else if(text.charAt(i)==word.charAt(x))
				x++;
			else
				x=0;
		}
		if(x==word.length)
			return i-x;
		return -1;
  },

	G2_HandleCallbackResultPhase2 : function(result, context)
	{	
		var resultArray = context.resultArray;

		//Handle html repeater data
		var htmlRepeaterData = resultArray[5].split("||||");
		G2_HandleCallbackResult_AddRepeaterElement(htmlRepeaterData);
				
		//Handle removing items
		var itemsToRemove = resultArray[6].split("||||");
		G2_HandleCallbackResult_RemoveElement(itemsToRemove);
		
		//Handle html data
		var htmlData = resultArray[0].split("||||");
		var activeElementID = null;
		var activeElement = document.activeElement;
		if(activeElement && !String.IsNullOrEmpty(activeElement.id))
		{
			activeElementID = activeElement.id;
		}
		G2_HandleCallbackResult_UpdateDomElements(htmlData);				
		
		//aspnet holds a strong reference to the form element, (in a variable named theForm)
		//which might be updated dynamically, so we update that reference
		if(theForm.parentElement==null) 
			theForm = document.forms[0];
		var hfHtml = resultArray[2];
		if(hfHtml!=null && hfHtml!="")
		{
			G2_HandleCallbackResult_UpdateHiddenFields(hfHtml);
		}

		if(activeElementID!=null)
		{
			G2_HandleCallbackResult_UpdateActiveElement(activeElementID, activeElement);
		}
			
		//Handle scripts
		var scriptData = resultArray[3];
		if(scriptData!=null && scriptData!="")
		{
			G2_HandleCallbackResult_EvalStartupStatements(scriptData);
		}
		
 	  //Handle the processing image - AFTER the startup statements (since we might navigate, and in that case we don't want to hide the image)
		HideProcessingImage();
		
		G2_ShowDisabler(false);
		
		//Handle last scripts
		var lastScriptData = resultArray[4];
		if(lastScriptData!=null && lastScriptData!="")
		{
			window.setTimeout(function(){	G2_HandleCallbackResult_EvalStartupStatements(lastScriptData); }, 10);
		}
		
		if(window.OnAfterCallbackClientFunction!=null)
		{
			window[window.OnAfterCallbackClientFunction]();
		}
		
		
		if(NOTIFY_SERVER_HISTORY_CHANGE)
		{
			if(context.aspNetContext.eventTarget=="__Page" && context.aspNetContext.eventArgument.startsWith("HistoryChange"))
			{
			}
			else
			{
				G2.historyIndex++;
				dhtmlHistory.add(G2.historyIndex.toString(), "Hello World " + "Data")
			}
		}
		G2_OnCallbackFinally(result, context);

		//event validation - doesn't work
	//  var eventValidationFieldValue = r[3];
	//  var eventValidationField = document.getElementById("__EVENTVALIDATION");
	//  eventValidationField.value = eventValidationFieldValue;
	},



	G2CallbackManager_UpdateViewState : function(viewState)
	{
		var div = document.createElement("div");
		div.innerHTML = viewState;
		document.getElementById("__VIEWSTATE").value =div.firstChild.value;
	},


	G2_InitCallbackAddField : function(name, value, context) 
	{
	//	WebForm_InitCallbackAddField(name, value);
//			var nameValue = new Object();
//			nameValue.name = name;
//			nameValue.value = value;
//			context.postCollection.push(nameValue);
			context.postData.push(name);
			context.postData.push("=");
			context.postData.push(WebForm_EncodeCallback(value));
			context.postData.push("&");
	},

	EnableSupportForPartialPostData : function(element)
	{
		element.isValueDirty = EnableSupportForPartialPostData_IsValueDirty;
		element.setValueAsNotDirty = EnableSupportForPartialPostData_SetValueAsNotDirty;
		element._originalValue = element.value;
		G2PartialPostDataElementIds[element.id] = element;
		if(ENABLE_POSTDATA_ONDEMAND)
		{
			if (isIE)
			{
				if((element.tagName=="INPUT" && element.type=="text") || element.tagName=="SELECT" || element.tagName=="TEXTAREA")
				{
					G2_AttachEvent(element, "onchange", function()
					{
						G2.notifyInputChanged(this);
					});
				}
				else
				{
					G2_AttachEvent(element, "onpropertychange", function()
					{
						if(event.propertyName=="value")
							G2.notifyInputChanged(this);
					});
				}
			} 
			else if (isMoz)
			{
				G2.RegisterPropertyChangeWatch(element.id);
			}
		}
	},
	
	EnableSupportForPartialPostData_SetValueAsNotDirty : function()
	{
		this._originalValue = this.value;
	},
	
	EnableSupportForPartialPostData_IsValueDirty : function()
	{
		return !(this.value===this._originalValue);
	},
	G2_InitCallbackByIds : function(ids, context)
	{
		for(var i=0;i<ids.length;i++)
		{
			var element = $(ids[i]);
			if(element!=null)
			{
				G2_InitCallbackForElement(element, context);
			}
			else if(ids[i]=="__WINDOWID" && window.location.href.search("WindowID")==-1)
			{
				throw new Error("window id not found");
			}
		}
	},

	G2_InitCallbackRecursive : function(context)
	{
		if(ENABLE_POSTDATA_ONDEMAND)
		{
			G2_InitCallbackAddField("__PARTIALPOSTDATA", "true", context);
			G2_InitCallbackByIds(["__EVENTTARGET", "__EVENTARGUMENT",  "__EVENTVALIDATION", "__VIEWSTATE", "__WINDOWID"], context);
			var inputsToRemove = new Object();
			for(var id in G2.changedInputs)
			{
				var element = $(id)
				if (element) //the element may be detached from the DOM
				{
					G2_InitCallbackForElement(element, context);
					inputsToRemove[id] = id;
				}
			}
			for (var id in inputsToRemove)//remove sent inputs
			{
				delete G2.changedInputs[id];
			}
		}
		else
			G2_PerformRecursiveActionOnElement(theForm, G2_InitCallbackForElement, context);
	},

	G2_InitCallbackForElement : function(element, context)
	{
		if(element.doesNotContainInputs)
			return false;
		if(G2_PreventPostElementIds[element.id]==true)
			return false;
		var tagName = element.tagName.toLowerCase();
		if (tagName == "input") 
		{
			var type = element.type;
			if ((type == "text" || type == "hidden" || type == "password" ||
					((type == "checkbox" || type == "radio"))) && // && element.checked
					(element.id != "__EVENTVALIDATION")) 
			{
				var name = element.name;
				var value = element.value;
				if(type == "checkbox")
				{
					if(ENABLE_POSTDATA_ONDEMAND)
					{
						value = element.checked ? "on" : "off";
					}
					else if(!element.checked)
						return false;
				}
				else if(type == "radio")
				{
					if(ENABLE_POSTDATA_ONDEMAND)
					{
						if(type == "radio" && element.g2rb=="true")
						{
							name = element.id;
						  value = element.checked ? "on" : "off";
						}
						else
					  {
					    G2_InitCallbackAddField(name, value, context);
					    return false;
					  }
					}
					else if(!element.checked)
						return false;
				}

				if(typeof(element.isValueDirty)=="function")
				{
					if(element.isValueDirty())
					{
						element.setValueAsNotDirty();
					}
					else
						return false;
				}
				G2_InitCallbackAddField(name, value, context);
				return false;
			}
		}
		else if (tagName == "select") 
		{
			var selectCount = element.options.length;
			var selCount = 0;
			for (var j = 0; j < selectCount; j++) 
			{
				var selectChild = element.options[j];
				if (selectChild.selected == true) 
				{
					selCount++;
					G2_InitCallbackAddField(element.name, selectChild.value, context);
					if(!element.multiple)
						return false;
				}
			}
			//We send null value to the ListBox
			if(selCount==0 && element.multiple)
				G2_InitCallbackAddField(element.name, "__NULL__", context);
		}
		else if (tagName == "textarea") 
		{
			G2_InitCallbackAddField(element.name, element.value, context);
			return false;
		}
		return true;
	},





	G2_GetEventTargetID : function(eventTarget) 
	{
		var realId;
		if(eventTarget.indexOf("$")>-1)
			realId = eventTarget.replace(/\$/g, '_');
		else if(eventTarget.indexOf(":")>-1)
			realId = eventTarget.replace(/:/g, '_');
		else
			realId = eventTarget;
		return realId; 
	},

	G2_GetEventTargetElement : function(eventTarget)
	{
		var el = $(eventTarget);
		if(el==null)
		{
			if(eventTarget.indexOf("$")>-1)
				eventTarget = eventTarget.replace(/\$/g, '_');
			else if(eventTarget.indexOf(":")>-1)
				eventTarget = eventTarget.replace(/:/g, '_');
			else
				return null;
			el = $(eventTarget);
		}
		return el;
	},


	G2_RefreshElement : function(element)
	{
		element.outerHTML = element.outerHTML;
	},

	G2IsSilent : function(eventTarget, eventArgument, eventTargetElement) 
	{
		if(window.silentPostbacks==true)
			return true;
		if (window.DisableSilentPostBack==true)
			return false;
		if(eventTargetElement!=null && eventTargetElement.getAttribute("silentpostback")=="true")
			return true;
		return false;
		var targets = window.silentPostbacksTargets;
		if(targets==null)
			return false;
		var val = targets[eventTarget];
		//TODO: find what causes this
		if(val==null && eventTarget.indexOf("$")>-1)
		{
			eventTarget = eventTarget.replace(/\$/g, '_');
			val = targets[eventTarget];
		}
		if(val==null && eventTarget.indexOf(":")>-1)
		{
			eventTarget = eventTarget.replace(/:/g, '_');
			val = targets[eventTarget];
		}
		if(val==null)
			return false;
		if(!String.IsNullOrEmpty(eventArgument) && val.args!=null)
		{
			var childValue = val.args[eventArgument];
			if(childValue!=null)
				return childValue;
		}
		return val.silent;
	},

	G2SetSilentPostBacks : function(json) 
	{
		if(window.silentPostbacksTargets==null)
		{
			window.silentPostbacksTargets = json;
		}
		else
		{
			for(var p in json)
			{
				window.silentPostbacksTargets[p] = json[p];
			}
		}
	},


	G2SetSilentPostBacksAll : function(isSilent)
	{
		window.silentPostbacks = isSilent;
	},

	//*****************************************************************
	//*                      G2ScriptManager                          *
	//*****************************************************************
	G2_GetRegisteredScripts : function()
	{
		if(_registeredScripts==null)
		{
			var elements = document.getElementsByTagName("script");
			_registeredScripts = new Object();
			for(var i=0;i<elements.length;i++)
			{
				var element = elements[i];
				if(element.src!="")
					_registeredScripts[element.src] = true;
			}
		}
		return _registeredScripts;
	},

	G2_IsScriptRegistered : function(src)
	{
		return G2_GetRegisteredScripts()[src]==true;
	},

	G2_GetUnregisteredScripts : function(srcArray)
	{
		if(srcArray==null)
			return null;
		var sources = new Array();
		for(var i=0;i<srcArray.length;i++)
		{
			var src = srcArray[i];
			if(!G2_IsScriptRegistered(src))
			{
				sources.push(src);
			}
		}
		return sources;
	},
	//
	// Gets an array of src strings, and loads these scripts. returns a callback when all scripts are loaded
	//
	G2_RegisterScripts : function(srcArray, loadCompletedCallback)
	{
		var sources = G2_GetUnregisteredScripts(srcArray);
		if(sources!=null && sources.length>0)
		{
			var context = {total:sources.length, loadCompletedCallback:loadCompletedCallback, sources:sources};
			for(var i=0;i<sources.length;i++)
			{
				var src = sources[i];
//				didNothing = false;
				var element = document.createElement("SCRIPT");
				element.src = src;
				element.setAttribute("type","text/javascript"); //Check if really needed
				document.body.appendChild(element); //TODO: this is a problem - the included file takes time to load 
				
				if(loadCompletedCallback!=null)
				{
					G2_AttachEvent(element, isIE ? "onreadystatechange" : "onload", function(e){G2_WaitForScripts(e ? e : event,context);}	);
				}
			}
		}
		else if(loadCompletedCallback!=null)
		{
			loadCompletedCallback();
		}
	},
	//*****************************************************************
	//*               End of G2ScriptManager                          *
	//*****************************************************************

	G2_WaitForScripts : function(event,context)
	{
		var element = G2Event.element(event);
		if(element.readyState=="loaded" || element.readyState=="complete" || isMoz)
		{
			context.total--;
			//clean up
			G2_DetachEvent(element, isIE ? "onreadystatechange" : "onload", G2_WaitForScripts);
			//end 
			_registeredScripts[element.src] = true;
			if(context.total==0)
			{
				context.loadCompletedCallback();
			}
		}
	},
	
	G2_CreateXmlHttp : function()
	{
		var xmlRequest,e;
		try 
		{
			xmlRequest = new XMLHttpRequest();
		}
		catch(e) 
		{
			try 
			{
				xmlRequest = new ActiveXObject("Microsoft.XMLHTTP");
			}
			catch(e) {
			}
		}
		var setRequestHeaderMethodExists = true;
		try 
		{
			setRequestHeaderMethodExists = (xmlRequest && xmlRequest.setRequestHeader);
		}
		catch(e) {}
		if(!setRequestHeaderMethodExists)
			return null;
		return xmlRequest;
	},

	WebForm_DoCallback : function (eventTarget, eventArgument, eventCallback, context, errorCallback, useAsync, classicPostback, g2context) 
	{
		if(g2context==null) //this may happen when calling DoCallback directly (when using ClientScript.GetCallbackReference
		{
			g2context = G2_InitCallback();
		}

		g2context.postData.push("__CALLBACKID=");
		g2context.postData.push(WebForm_EncodeCallback(eventTarget));
		g2context.postData.push("&__CALLBACKPARAM=");
		g2context.postData.push(WebForm_EncodeCallback(eventArgument));
		if (theForm["__EVENTVALIDATION"]) 
		{
			g2context.postData.push("&__EVENTVALIDATION=");
			g2context.postData.push(WebForm_EncodeCallback(theForm["__EVENTVALIDATION"].value));
		}
		var postData = g2context.postData.join("");
		var xmlRequest = G2_CreateXmlHttp();
		
		var callback = new Object();
		callback.eventCallback = eventCallback;
		callback.context = context;
		callback.errorCallback = errorCallback;
		callback.async = useAsync;
		var callbackIndex = WebForm_FillFirstAvailableSlot(__pendingCallbacks, callback);
		if (!useAsync) 
		{
				if (__synchronousCallBackIndex != -1) {
						__pendingCallbacks[__synchronousCallBackIndex] = null;
				}
				__synchronousCallBackIndex = callbackIndex;
		}
		if (xmlRequest!=null) 
		{
			if(!G2UseSyncCallbacks)
				xmlRequest.onreadystatechange = WebForm_CallbackComplete;
			callback.xmlRequest = xmlRequest;
			xmlRequest.open("POST", theForm.action, !G2UseSyncCallbacks); //was hardcoded true - modified by Alon to force sync. calls to allow popups to be opened.
			xmlRequest.setRequestHeader("Content-Type", "application/x-www-form-urlencoded");
			xmlRequest.send(postData);
			if(G2UseSyncCallbacks)
				WebForm_CallbackComplete();
			return;
		}
		WebForm_DoCallback_WithIFrame();
	},
	//this code exists in asp.net callbacks code - and used when browser doesn't support xmlhttp.
	//removed for now.
	WebForm_DoCallback_WithIFrame : function()
	{
		throw new Error("not implemented");
	},


	WebForm_CallbackComplete : function() 
	{
			for (var i = 0; i < __pendingCallbacks.length; i++) 
			{
					callbackObject = __pendingCallbacks[i];
					if (callbackObject && callbackObject.xmlRequest && (callbackObject.xmlRequest.readyState == 4)) 
					{
							WebForm_ExecuteCallback(callbackObject);
							//TODO: HACK: added by dan-el - when closing popups the item is not there. probably related to registration to callbackreference
							if(__pendingCallbacks[i]!=null) 
							{
								if (!__pendingCallbacks[i].async) 
								{
										__synchronousCallBackIndex = -1;
								}
							}
							__pendingCallbacks[i] = null;
							var callbackFrameID = "__CALLBACKFRAME" + i;
							var xmlRequestFrame = document.getElementById(callbackFrameID);
							if (xmlRequestFrame) 
							{
									xmlRequestFrame.parentNode.removeChild(xmlRequestFrame);
							}
					}
			}
	},

	WebForm_ExecuteCallback : function(callbackObject) 
	{
		var response = callbackObject.xmlRequest.responseText;
		if (response.charAt(0) == "s") 
		{
			if ((typeof(callbackObject.eventCallback) != "undefined") && (callbackObject.eventCallback != null)) 
			{
				callbackObject.eventCallback(response.substring(1), callbackObject.context);
			}
		}
		else if (response.charAt(0) == "e") 
		{
			if ((typeof(callbackObject.errorCallback) != "undefined") && (callbackObject.errorCallback != null)) 
			{
				callbackObject.errorCallback(response.substring(1), callbackObject.context);
			}
		}
		else 
		{
			var separatorIndex = response.indexOf("|");
			if (separatorIndex != -1) 
			{
				var validationFieldLength = parseInt(response.substring(0, separatorIndex));
				if (!isNaN(validationFieldLength)) 
				{
					var validationField = response.substring(separatorIndex + 1, separatorIndex + validationFieldLength + 1);
					if (validationField != "") 
					{
						var validationFieldElement = theForm["__EVENTVALIDATION"];
						if (!validationFieldElement) 
						{
							validationFieldElement = document.createElement("INPUT");
							validationFieldElement.type = "hidden";
							validationFieldElement.name = "__EVENTVALIDATION";
							theForm.appendChild(validationFieldElement);
						}
						validationFieldElement.value = validationField;
					}
					if ((typeof(callbackObject.eventCallback) != "undefined") && (callbackObject.eventCallback != null)) 
					{
						callbackObject.eventCallback(response.substring(separatorIndex + validationFieldLength + 1), callbackObject.context);
					}
				}
			}
			else
			{
				var location = callbackObject.xmlRequest.getResponseHeader("location"); //if Response.RedirectLocation is used
				if(location!=null && location!="")
				{
					G2_Navigate(location);
				}
				else
				{
   				callbackObject.errorCallback(response, callbackObject.context);
   			}
			}
		}
	},

	G2_UseSyncCallbacks : function()
	{
		G2UseSyncCallbacks = true;
//		WebForm_DoCallback = WebForm_DoCallback_Sync;
//		WebForm_CallbackComplete = WebForm_CallbackComplete_Sync;
	},


	//
	//recursivle iterates on all child elements of a certain element,
	//and calls the specified action with the element and context, action(element, context)
	//if the action returns false, it will stop the recursive operation inside that element
	//
	G2_PerformRecursiveActionOnElement : function(element, action, context)
	{
		_G2_PerformRecursiveActionOnElement(element, action, context);
	},
	_G2_PerformRecursiveActionOnElement : function(element, action, context)
	{
		if(element.nodeType!=1) //textnode
			return;

		var result = action(element, context);
		if(result==false)
			return;
		var child = element.firstChild;
		while(child!=null)
		{
			_G2_PerformRecursiveActionOnElement(child, action, context);
			child = child.nextSibling;
		}
	},


	G2_SetFocus : function(elementId)
	{
		if(G2_SetFocus_ThreadId!=null)
		{
			window.clearTimeout(G2_SetFocus_ThreadId);
			G2_SetFocus_ThreadId = null;
		}
		G2_SetFocus_ThreadId = window.setTimeout(
			function()
			{
				G2_SetFocus_ThreadId = null;
				var success = G2_AutoFocus(elementId);
				if(success) //case 8578 - sometimes after the successful focus, the body is somehow focused. this hack fixes it.
				{
					if(document.activeElement==null || document.activeElement.id!=elementId)
					{
						success = G2_AutoFocus(elementId);
					}
				}
			}, 50);
	},


	///
	/// Finds a server control by server ID (using id.contains(id))
	///
	G2_FindServerControl : function(fromElement, id)
	{
		return _G2_FindServerControl(fromElement, id);
	},
	_G2_FindServerControl : function(fromElement, id)
	{
		if(fromElement.id!=null && fromElement.id.endsWith(id))
			return fromElement;

		if(fromElement.doesNotContainInputs || fromElement.tagName=="SELECT")
			return null;

		var element = fromElement.firstChild;
		while(element!=null)
		{
			var foundControl = _G2_FindServerControl(element, id)
			if(foundControl!=null)
				return foundControl;
			element = element.nextSibling;
		}
		return null;
	},



	G2ReturnValue : function(value)
	{
		this.value = value;
	},
	
	// Get current page theme
	G2_PageTheme : function()
	{
		return document.getElementById("G2_PageTheme").value;
	},


	G2_MapPath : function(virtualUrl)
	{
		var rootAppPath = document.getElementById("G2_RootAppPath").value;
		var path = virtualUrl.replace("~/", rootAppPath);
		return path;
	},
	G2_IsNavigating : function()
	{
	  return window.top.IsNavigating;
	},
	
	G2_Navigate : function(url, isInternalNavigation, targetFrame, navigateWithForms)
	{
	    var navigationWindow = null;
	    if (isInternalNavigation && isInternalNavigation != 'false')
		{
		      if(targetFrame!="" && targetFrame!=null) //navigate inside a frame
		      {
		        var f = document.getElementById(targetFrame);
		        f.contentWindow.document.location.href = url;
		        return;
		      }
		      else //navigate in this window
		         navigationWindow = window; 
		}
		else //navigate in the topmost window
		{
		      navigationWindow = window.top;
	    }
	    if (navigateWithForms && navigateWithForms != 'false') //naviage throught form submit
	        G2_FormNavigate(navigationWindow, url);
	     else //navigate through url change
	     {
	        navigationWindow.IsNavigating = true;
	        navigationWindow.window.location.href = url;
	        
	     }
	},
	
	G2_FormNavigate : function (windowObj, url)
	{
	    windowObj.IsNavigating = true;
	    var navForm = window.document.createElement("FORM");
	    navForm.method = "get";
	    var urlPair = url.toString().split('?');
	    var navUrl = urlPair[0];
	    if (urlPair.length > 1)
	    {
            var query = urlPair[1];
            queryStringKeys = new Array();	
            queryStringValues = new Array();
	        var pairs = query.split("&");
        	for (var i=0; i < pairs.length; i++)
            {
	            var pos = pairs[i].indexOf('=');
	            if (pos >= 0)
	            {
		            var argname = pairs[i].substring(0,pos);
		            var value = pairs[i].substring(pos+1);
		            var input = window.document.createElement('INPUT');
		            input.name = argname;
		            input.value = value;
		            input.type = 'hidden';
		            input.style.display = 'none';
		            navForm.appendChild(input);
	            }
             }
        }
    	windowObj.document.body.appendChild(navForm);
	    navForm.action = navUrl;
	    navForm.submit();
	},
	
	G2_Warn : function(sender, msg)
	{
		G2_Trace(sender, "************************************");
		G2_Trace(sender, msg);
		G2_Trace(sender, "************************************");
	},

	G2_Trace : function(sender, msg)
	{
		var id = null;
		if(sender!=null)
		{
			id = sender.id!=null ?  sender.id : sender.toString();
		}
		var now = new Date();
		var time = Date_ToString(now, "HH:mm:ss:ff");
		Debug.writeln(time+", "+id+": "+msg);
	},

	//New version by Alon.
	G2_GetData : function(url, callback, errorCallback)
	{
		url = encodeURI(url); //added by dan-el - when url has querystring arguments that contains chinese (for example) - will only work with encoding.
		if (isIE && window.ActiveXObject)
		{
			xmlhttp = new ActiveXObject("Microsoft.XMLHTTP");
			if (xmlhttp!=null)
			{
				xmlhttp.onreadystatechange=function()
				{
					var x = xmlhttp.readyState;
					var y = xmlhttp.readyState;
					if(x==y)
					{
					}
					// if xmlhttp shows "loaded"
					if (xmlhttp.readyState==4)
					{
						// if "OK"
						if (xmlhttp.status==200)
						{
							callback(xmlhttp);
						// ...some code here...
						}
						else
						{
							errorCallback(xmlhttp);
						}
					}
				}
				xmlhttp.open("GET",url,true);
				xmlhttp.send(null);
			}
		} 
		else if (window.XMLHttpRequest)
		{
			try
			{
				var xmlhttp=new XMLHttpRequest();
				xmlhttp.open("GET",url,false);
				xmlhttp.send(null);
				callback(xmlhttp);		
			} 
			catch(everything)
			{
			  if (G2_Trace!=null)
			  {
				  G2_Trace("G2_GetData", everything.description);
				}
				errorCallback(xmlhttp);
			}
		} 
		else
		{
			alert("Your browser does not support XMLHTTP.");
		}
	},

	//function G2Page_Wait()
	//{
	//  setTimeout("G2Page_Wait_Timeout();",150);
	//}

	//function G2Page_Wait_Timeout()
	//{
	//  if(!Page_IsValid)
	//   return;
	//  var hf = document.getElementById("G2_WaitingImage");
	//  if(hf.value!="")
	//  {
	//    var img = document.getElementById(hf.value);
	//    img.style.display = "block";
	//    var srcWas = img.src;
	//    img.src = "";
	//    img.src = srcWas;
	//  }
	//}

	G2_IsInPopup : function()
	{
		try
		{
			parentDoc = parent.document;
			return (parentDoc!=null && parentDoc!=document)
		} 
		catch(everything)
		{	
			G2_Trace("IsInPopup", everything.description);
			Debug.writeln("IsInPopup() FAILED");
			return false;
		}  
	},


	//now registered inline from g2page.cs
	//function G2Page_Init()
	//{
	//	G2_AttachEvent(window, "onload", G2Page_OnLoad);
	//}


	//Unless explicitly specified, resizing is DISABLED until page is loaded.
	//When the page is loaded, the auto-size feature is enabled
	G2Page_OnLoad : function()
	{
	//	G2_DetachEvent(window, "onload", G2Page_OnLoad);
		G2_PreventInputPost("G2_OnLoadStatement");
		var s = document.getElementById("G2_OnLoadStatement");
		enableResizing = true;
		if(s!=null)
		{
			eval(s.value);
		}	
		if (G2_IsInPopup())
		{
			G2Dialog_Init();
		}
	},

	G2_FirePopupClosed : function(popupID, popupResult, silent, uniqueId)
	{
		if (uniqueId!=null)
			popupID = popupID + "###"+uniqueId;
		var hf1 = document.getElementById('__PopupWindowID');
		var hf2 = document.getElementById('__PopupResult');
		hf1.value = popupID;
		hf2.value = popupResult;
		G2.notifyInputChanged(hf1);
		G2.notifyInputChanged(hf2);
		__doPostBack('__Page','G2PopupClosed',silent);  
	},

	G2HtmlFrame_Init : function(iframeId, targetElementId, tooltipKey, autoSize)
	{
		if(tooltipKey!=null && tooltipKey!="")
		{
			G2Tooltips[tooltipKey] = iframeId;
		}
		if(targetElementId!="")
		{
			var target = document.getElementById(targetElementId);
			var iframe = document.getElementById(iframeId);
			target._tooltipFrame = iframe;
			iframe.style.position="absolute";
	    
			target.onmouseover=function()
			{
				x = event.clientX + document.body.scrollLeft;
				y = event.clientY + document.body.scrollTop;
				this._tooltipFrame.style.pixelLeft = x;
				this._tooltipFrame.style.pixelTop = y;
				this._tooltipFrame.style.display = "block";
			}
			target.onmouseout=function()
			{
				this._tooltipFrame.style.display = "none";
			}
		}
		
		if(autoSize)
			window.setTimeout(function() { G2FrameManager.registerFrame(iframeId); }, 0);
	},

	G2ShowTooltip : function(target, tooltipKey,event)
	{
		var iframeId = G2Tooltips[tooltipKey];
		var iframe = document.getElementById(iframeId);
		if (!iframe)
			return;
		if (!event)
			event = window.event;
		G2ShowTooltipElement(target, iframe,event);
	},
	
  G2ShowTooltipElement : function(targetElement, tooltipElementOrId,e)
  {
	  if (!e)
		  e = window.event;
  		
	  if(typeof(tooltipElementOrId)=="string")
	   el = document.getElementById(tooltipElementOrId);
	  else
	   el = tooltipElementOrId;
  	 
	  G2PopupManager.showTooltipStart(targetElement, el,e);
  },  

	Date_Parse : function(strDate)
	{
		var date = new Date(strDate);
		if(isNaN(date))
			return null;
		return date;
	},



	//------- G2 Utils -----------------------------------------------------------
	//UNUSED
	G2SyncTables : function(tbl1ID,tbl2ID)
	{
		var table1 = document.getElementById(tbl1ID);
		var table2 = document.getElementById(tbl2ID);

		if(table1==null || table2==null)
			return;
		var tbl1AmoutOfRows= table1.rows.length;
		var tbl2AmoutOfRows= table2.rows.length;
		var minRowSize=0;


		if(tbl1AmoutOfRows>tbl2AmoutOfRows)
			minRowSize= tbl2AmoutOfRows;
		else 
			minRowSize= tbl1AmoutOfRows;
	    
		var i =0;
		var j =0;
		var minColSize=0;
		if(table1.rows[0].cells.length <table2.rows[0].cells.length)
			minColSize=table1.rows[0].cells.length;
		else 
			minColSize=table2.rows[0].cells.length;
	    
		while(i<minRowSize){
				j=0;
				while(j<minColSize){
									if(table1.rows[i].cells[j].style.width<table2.rows[i].cells[j].style.width)
										table1.rows[i].cells[j].style.width=table2.rows[i].cells[j].style.width;
									else
										table2.rows[i].cells[j].style.width=table1.rows[i].cells[j].style.width;
								 j=j+1;
				}
			i=i+1;
		}
	},

	String_ToInt : function(text)
	{
		if(text==null || text.length==0)
			return null;
		text = String_TrimLeft(text, "0");//because of js bug: parseInt('08') returns 0 as a result
		if(text.length==0)
			return 0;
		var x = parseInt(text);
		if(isNaN(x))
			return null;
		return x;
	},

	String_TrimLeft : function(text, trimChar)
	{
		while(text.length>0 && text.charAt(0)==trimChar)
		{
			text = text.substr(1, text.length-1);
		}
		return text;
	},

	Select_FindByValue : function(select, value)
	{
		for(var i=0;i<select.options.length;i++)
		{
			if(select.options[i].value==value)
				return select.options[i];
		}
		return null;
	},

	Select_IndexOfValue : function(select, value)
	{
		for(var i=0;i<select.options.length;i++)
		{
			if(select.options[i].value==value)
				return i;
		}
		return null;
	},
	Select_ContainsValue : function(select, value)
	{
		return Select_IndexOfValue(select, value)!=null;
	},

	//
	// returns the index of the first occurance of a specific item in an array
	//
	Array_IndexOf : function(array, value)
	{
		for(var i=0;i<array.length;i++)
		{
			if(array[i]==value)
				return i;
		}
		return -1;
	},
	G2_findPreviousControl : function(ctrl , tagName)
	{
		while (ctrl!=null && ctrl.tagName!=tagName)
		{
			if (ctrl.previousSibling==null)
				ctrl = ctrl.parentElement;
			else
				ctrl = ctrl.previousSibling;
		}
		return ctrl;

	},

	G2_getDayName : function(year , month , day)
	{
		var dDate = new Date();
		dDate.setFullYear(year,month-1,day);
		return weekDays[dDate.getDay()];
	},


	DateRange_GetDays : function(dateRange, hoursToAdd)
	{
		return DateRange_GetNights(dateRange, hoursToAdd)+1;
	},

	DateRange_GetNights : function(dateRange, hoursToAdd)
	{
		//case 7606: in case of date range over Summertime trnsition (start date in summertime 
		//and end date in regulare time or the other way around)
		dateRange = dateRange + hoursToAdd*1000*60*60;
		return Math.ceil(dateRange/(24*60*60*1000));
	},

	DateRange_GetYears : function(dateRange)
	{
		return dateRange/(365*24*60*60*1000);
	},

	Date_AddHours : function(date,hours) 
	{
		return new Date(date.getFullYear(), date.getMonth(), date.getDate(), date.getHours() + hours, date.getMinutes(), date.getSeconds());
	},

	Date_AddDays : function(date,days) 
	{
		return new Date(date.getFullYear(), date.getMonth(), date.getDate()+days, date.getHours(), date.getMinutes(), date.getSeconds());
	},

	Date_SubtractDays : function(date,days) 
	{
		return new Date(date.getFullYear(), date.getMonth(), date.getDate()-days, date.getHours(), date.getMinutes(), date.getSeconds());
	},

	Date_ToDotNetString : function(date) 
	{
		return Date_ToString(date, "MM-dd-yyyy");
	},

	Date_VerifyLeadingZero : function(str)
	{
		if(str.length==1)
			str = "0"+str;
		return str;
	},

	///Parses a string like 'Aug' or '8' or '08' into the month number (not javascript month)
	///and returns it - like 8 in this case
	Date_ParseMonth : function(text)
	{
		var month = Array_IndexOf(Date_ShortMonthNames, text);
		if(month!=-1)
		{
			return month+1;
		}
		
		month = String_ToInt(text);
		return month;
	},

	Number_Extension : function(str)
	{
			var lastDigit = str.charAt(str.length-1);
			var last = parseInt(lastDigit);
			var prev = 0;
			if (str.length >= 2) 
			{
				var prevDigit = str.charAt(str.length-2);
				prev = parseInt(prevDigit);
			}
			
			if (prev != 1) //When the number doesn't end with 11, 12 or 13, the extension is according the last digit
			{
				if (last == 1)
					return "st";
				else if (last == 2)
					return "nd";
				else if (last == 3)
					return "rd";
				else
				 return "th"; // 0, 4, 5, 6, 7, 8 and 9
			}
			else //When the number ends with 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, when the tenth digit is 1
				return "th"; 
			
	},

	Number_Format : function(number, format)
	{
		if(format=="#")
		{
			return number.toString();
		}
		else if(format=="##")
		{
			var s = number.toString();
			while(s.length<2)
			{
				s = "0"+s;
			}
			return s;
		}
		else if(format=="##xx")
		{
			var s = Number_Format(number, "##");
			var ext = Number_Extension(s);
			s += ext;
			return s;
		}
		else if(format=="#xx")
		{
			var s = Number_Format(number, "#");
			var ext = Number_Extension(s);
			s += ext;
			return s;
		}
		throw new Error("number format is not supported");
	},

	//
	// Formats a javascript Date object to string in a manner similar to .net framework.
	// currently supports: day, month, year, hour, minute,
	// seperators: '/', ':'
	//
	Date_ToString : function(date, format) 
	{
		if(date==null)
			return "";
			
		if(format=="H")
		{
			return date.getHours().toString();
		}
		else if(format=="HH")
		{
			return Date_VerifyLeadingZero(date.getHours().toString());
		}
		else if(format=="m")
		{
			return date.getMinutes().toString();
		}
		else if(format=="mm")
		{
			return Date_VerifyLeadingZero(date.getMinutes().toString());
		}
		else if(format=="s")
		{
			return date.getSeconds().toString();
		}
		else if(format=="ss")
		{
			return Date_VerifyLeadingZero(date.getSeconds().toString());
		}
		else if(format=="ff")
		{
			return Date_VerifyLeadingZero(date.getMilliseconds().toString());
		}
		else if(format=="d")
		{
			return date.getDate().toString();
		}
		else if(format=="dxx")
		{
			var day = date.getDate();
			var s = Number_Format(day, "#xx");
			return s;
		}
		else if(format=="dd")
		{
			return Date_VerifyLeadingZero(date.getDate().toString());
		}
		else if(format=="ddxx")
		{
			var day = date.getDate();
			var s = Number_Format(day, "##xx");
			return s;
		}
		else if(format=="M")
		{
			return (date.getMonth()+1).toString();
		}
		else if(format=="MM")
		{
			return Date_VerifyLeadingZero((date.getMonth()+1).toString());
		}
		else if(format=="MMM")
		{
			return Date_ShortMonthNames[date.getMonth()];
		}
		else if(format=="MMMM")
		{
			return Date_MonthNames[date.getMonth()];
		}
		else if(format=="y")
		{
			throw new Error("'y' is not a valid datetime format");
		}
		else if(format=="yy")
		{
			var str = date.getFullYear().toString();
			if(str.length==4)
				str = str.substr(2, 2);
			return str;
		}
		else if(format=="yyyy")
		{
			return date.getFullYear().toString();
		}
		else if(format.search(":")!=-1)
		{
			return _Date_ToString(date, format, ":");
		}
		else if(format.search("/")!=-1)
		{
			return _Date_ToString(date, format, "/");
		}
		else if(format.search("\\\\")!=-1)
		{
			return _Date_ToString(date, format, "\\");
		}
		else if(format.search("-")!=-1)
		{
			return _Date_ToString(date, format, "-");
		}
		else if(format.search(" ")!=-1)
		{
			return _Date_ToString(date, format, " ");
		}
		else if(format.search(".")!=-1)
		{
			return _Date_ToString(date, format, ".");
		}
		else
			throw new Error("date format is not supported");
	},

	//	var myDate = new Object();
	//	myDate.Day = date.getDate();
	//	myDate.Month = date.getMonth()+1;
	//	myDate.Year = date.getFullYear();
	//	myDate.ShortYear = date.getYear();

	//	if(format=="dd/MM/yy")
	//	{
	//		var s = (myDate.Day+"/"+myDate.Month+"/"+myDate.ShortYear);//.getDate()+"-" + date.getMonth()+1)+"-" + date.getFullYear();
	//		return s;
	//	}

	_Date_ToString : function(date, format, seperator)
	{
		var str="";
		var tokens = format.split(seperator);
		for(var i=0;i<tokens.length;i++)
		{
			var token = tokens[i];
			if(token!=null && token.length>0)
				str += Date_ToString(date, token);
			if(i!=tokens.length-1) //if not last, add seperator
				str += seperator;
		}
		return str;
	},


	// -------------------------------------------------------------------
	// autoComplete (text_input, select_input, ["text"|"value"], [true|false])
	//   Use this function when you have a SELECT box of values and a text
	//   input box with a fill-in value. Often, onChange of the SELECT box
	//   will fill in the selected value into the text input (working like
	//   a Windows combo box). Using this function, typing into the text
	//   box will auto-select the best match in the SELECT box and do
	//   auto-complete in supported browsers.
	//   Arguments:
	//      field = text input field object
	//      select = select list object containing valid values
	//      property = either "text" or "value". This chooses which of the
	//                 SELECT properties gets filled into the text box -
	//                 the 'value' or 'text' of the selected option
	//      forcematch = true or false. Set to 'true' to not allow any text
	//                 in the text box that does not match an option. Only
	//                 supported in IE (possible future Netscape).
	// -------------------------------------------------------------------
	G2DropDown_AutoComplete  : function(field, select, property, forcematch) 
	{
		var found = false;
		for (var i = 0; i < select.options.length; i++) {
		if (select.options[i][property].toUpperCase().indexOf(field.value.toUpperCase()) == 0) {
			found=true; break;
			}
		}
		if (found) { select.selectedIndex = i; }
		else { select.selectedIndex = -1; }
		if (field.createTextRange) 
		{
			if (forcematch && !found) 
			{
				field.value=field.value.substring(0,field.value.length-1); 
				return;
			}
			var cursorKeys ="8;46;37;38;39;40;33;34;35;36;45;";
			if (cursorKeys.indexOf(event.keyCode+";") == -1) 
			{
				var r1 = field.createTextRange();
				var oldValue = r1.text;
				var newValue = found ? select.options[i][property] : oldValue;
				if (newValue != field.value) 
				{
					field.value = newValue;
					var rNew = field.createTextRange();
					rNew.moveStart('character', oldValue.length) ;
					rNew.select();
				}
			}
		}
	},

	Select_SetValue : function(select, value, suppressOnChangeEvent)
	{
		select.value = value;
		if(!suppressOnChangeEvent)
			G2_FireEvent(select, "onchange");
	},

	String_PadEnd : function(src, count, paddingChar)
	{
		if(paddingChar==null)
			paddingChar=" ";
		var s="";	
		for(var i=0;i<count;i++)
		{
			s+=paddingChar;
		}
		return src+s;
	},


	String_InsertAt : function(src, index, value)
	{
		var s1 = src.substr(0, index);
		var s2 = src.substr(index, src.length-index);
		return s1+value+s2;
	},

	String_RemoveAt : function(src, index)
	{
		var s1 = src.substr(0, index);
		var s2 = src.substr(index+1, src.length-index+1);
		return s1+s2;
	},

	String_RemoveAll : function(src, search)
	{
		var tokens = src.split(search);
		var s = "";
		for(var i=0;i<tokens.length;i++)
		{
			s+=tokens[i];
		}
		return s;
	},
	
	String_StartsWith : function(text, start)
	{
		if(start.length>text.length)
			return false;
		for(var i=0;i<start.length;i++)
		{
			if(start.charAt(i)!=text.charAt(i))
				return false;
		}
		return true;
	},

	G2_CopyArray : function(sourceArray, startIndex)
	{
		if(startIndex==null)
			startIndex = 0;
		var array = new Array();
		array.length = sourceArray.length-startIndex;
		var j=0;
		for (var i=startIndex;i<sourceArray.length;i++)
		{
			array[j] = sourceArray[i];
			j++;
		}
		return array;
	},

	G2_ShowControl : function(control, useVisibility)
	{
		if(useVisibility)
		{
			control.style.visibility = "visible";
		}
		else
		{
			control.style.display = "";//FOLLOWUPDAN-EL

		}
		if(typeof(control.OnShow)!="undefined")
		{
			control.OnShow();
		}
		return true;
	},
	
	G2_IsElementVisible : function(element, checkParents)
  {
	  if(element.style && element.style.display=="none")
		  return false;
	  if(checkParents)
	  {
		  if(element.parentElement!=null)
			  return G2_IsElementVisible(element.parentElement, checkParents);
		  else
		      if (isMoz) //Moz has a parent for the documentElement (html tag)
		          return element instanceof Document;
		      else
			      return element==element.document.documentElement; //only when element reaches to the top doc element we can be (pretty) sure it's visible.
  			
	  }
	  return true;
  },

	G2_HideControl : function(control, useVisibility)
	{
 		if(useVisibility)
		{
			control.style.visibility = "hidden";
		}
		else
		{
			control.style.display = "none";
		}
		if(typeof(control.OnHide)!="undefined")
		{
			control.OnHide();
		}
		return false;
	},
	G2_ToggleElementVisibility : function(element)
	{
		if(element==null)
			return; //TODO: warn
		if(element.style.display=="none")
			G2_ShowControl(element);
		else
			G2_HideControl(element);
	},

	G2_ShowHideControl : function(control, show, useVisibility)
	{
		if(show)
		{
			return G2_ShowControl(control, useVisibility);
		}
		else
		{
			return G2_HideControl(control, useVisibility);
		}
	},

	G2Page_ErrorCallback : function(message)
	{
		alert('An error occurred on the server:\n' + message);
	},

	G2_RecursiveSetPropertyValue : function(rootElement, propertyName, value)
	{
		if(rootElement.nodeName!="#text" && rootElement[propertyName]!=value)
		{
			rootElement[propertyName] = value;
		}
		var rootElementChildren = rootElement.children;
		for(var i=0;i<rootElementChildren.length;i++)
		{
			var child = rootElementChildren[i];
			G2_RecursiveSetPropertyValue(child, propertyName, value);
		}
	},

	//----------------------------------------------------------------------	

	G2_GetY : function(element)
	{
		var y = 0;
		while( element != null ) 
		{
			y += parseInt(element.offsetTop);
			
			// taking into account scrooling with in overflow scroll elements
			if(element.tagName != 'HTML' && element.scrollTop != null)
				y -= element.scrollTop;
			if(element.tagName == 'IFRAME')
				y -= document.documentElement.scrollTop;
			
			element = element.offsetParent;
		}
		return y;
	},

	G2_GetX : function(element)
	{
		var x = 0;
		while( element != null ) 
		{
			x += parseInt(element.offsetLeft);
			element = element.offsetParent;
		}
		return x;
	},

	G2Validator_ValidateElementOnChange : function(element)
	{
		if(element!=null && element.Validators!=null)
		{
			var dummyEvent = new Object();
			dummyEvent.srcElement = element; //IE
			dummyEvent.target = element; //FF
			ValidatorOnChange(dummyEvent);
		}
	},

	//---------------------------------------------

	isFixedPositioned : function(elem)
	{
		while (elem!=null)
		{
			if (elem && elem.style && elem.currentStyle.position == "fixed")
				return true;
			elem = elem.parentElement;
		}
		return false;
	},

  G2_BringToFront : function(elementToFloat)
	{
	  //marked by dan-el elementToFloat.style.zIndex = G2_maxZ++;
	},
	
	G2_FloatElement : function(elementToFloat, positionElement, dir, useFrame,useFixedPositioning)
	{
		//G2_Trace("G2_FloatElement", "start");
		var parent = elementToFloat.parentElement;
		if(parent!=null)
		{
			parent.removeChild(elementToFloat);
		}
		document.body.appendChild(elementToFloat);
		elementToFloat.style.position = useFixedPositioning ? "fixed" : "absolute";
		G2_BringToFront(elementToFloat);
		//this.bringElementToFront(elementToFloat);
		var N=(dir.indexOf("N")>-1);
		var S=(dir.indexOf("S")>-1);
		var E=(dir.indexOf("E")>-1);
		var W=(dir.indexOf("W")>-1);
		if(!N && !S)
			S=true;
		if(!E && !W)
		{
			E=true;
		}
		
		var x = G2_GetX(positionElement);
		var y = G2_GetY(positionElement);

	  
		if (S)
			y += positionElement.offsetHeight;
		if (W)
			x += positionElement.offsetWidth;
		elementToFloat.style.pixelTop = y;
		elementToFloat.style.pixelLeft = x;
	  
		elementToFloat.style.display = "block";
	  
		//iframe is the only one that can hide select tags in IE
		if(useFrame) 
		{
			window.setTimeout(function(){G2_AttachFrame(elementToFloat,useFixedPositioning);}, 0);
		}
 		//G2_Trace("G2_FloatElement", "end");
	},

	G2_HideFloatingElement : function(targetElement)
	{
		G2_DetachFrame(targetElement);
		targetElement.style.display = "none";
	},
	G2_CreateIFrame : function(doc, frameBorder, scrolling)
	{
		doc = doc || document;
		var frame = doc.createElement("IFRAME");
		if(frameBorder==null)
			frameBorder = 0;
		frame.frameBorder = frameBorder.toString();
		if(scrolling!=null)
			frame.scrolling = scrolling ? "yes" : "no";
		
		// validate body exist
		var body = doc.body;
		if(body == null)
		  body = document.body;
		  
		body.appendChild(frame);
		var frameDoc = frame.contentWindow.document;
		frameDoc.open();
		frameDoc.write("<html><body></body></html>");
		frameDoc.close();
		body.removeChild(frame);
		return frame;
	},
	G2_AttachFrame : function(targetElement,useFixedPositioning)
	{
		if(!IE6)
			return;
		//G2_Trace("G2_AttachFrame", "start");

		if(G2_FixFrame==null)
		{
			G2_FixFrame = G2_CreateIFrame(targetElement.document, 0, false);
			G2_FixFrame.setAttribute("id", "fixFrame");
			targetElement.insertAdjacentElement("beforeBegin", G2_FixFrame);
		}
	  
		//TODO: some of the size properties causes performance overhead of about a second
		G2_FixFrame.style.position = useFixedPositioning ? "fixed" : "absolute";
		G2_FixFrame.style.width = targetElement.offsetWidth+"px";
		G2_FixFrame.style.height = targetElement.offsetHeight+"px";
		G2_FixFrame.style.top = G2_GetY(targetElement)+"px";
		G2_FixFrame.style.left = G2_GetX(targetElement)+"px";
		//G2_FixFrame.style.zIndex = targetElement.currentStyle.zIndex - 1;
		G2_FixFrame.style.display = "block";
		targetElement._popupFixFrame = G2_FixFrame;
		targetElement.onresize = function()
		{
			this._popupFixFrame.style.width = this.offsetWidth+"px";
			this._popupFixFrame.style.height = this.offsetHeight+"px";
		}
		targetElement.onmove = function()
		{
			this._popupFixFrame.style.pixelTop = this.offsetTop;
			this._popupFixFrame.style.pixelLeft = this.offsetLeft;
		}
 		//G2_Trace("G2_AttachFrame", "end");
	},
	G2_DetachFrame : function(targetElement)
	{
		if(!IE6)
			return;
		if(targetElement._popupFixFrame==null)
			return;
		targetElement._popupFixFrame.style.display = "none";
		targetElement._popupFixFrame = null;
		//G2_FixFrame.style.display = "none";
		targetElement.onresize = null;
		targetElement.onmove = null;
	},

	//added by rony - for validation control re evaluation.
	G2ReEvaluateValidationControl : function(validationControl) {
			Page_InvalidControlToBeFocused = null;
			if (typeof(Page_Validators) == "undefined") {
					return true;
			}
			validationControl.isvalid = true;
			if (typeof(validationControl.enabled) == "undefined" || validationControl.enabled != false) {
					if (typeof(validationControl.evaluationfunction) == "function") {
							validationControl.isvalid = validationControl.evaluationfunction(validationControl);
							if (!validationControl.isvalid && Page_InvalidControlToBeFocused == null &&
									typeof(validationControl.focusOnError) == "string" && validationControl.focusOnError == "t") {
									ValidatorSetFocus(validationControl, event);
							}
					}
			}
			ValidatorUpdateDisplay(validationControl);
	},

	/*
	resizing the hieght for the outer ifram element from a current page
	*/

	FixOuterIFramHight : function(){
		//FixIFrameHeight(window.frameElement.id);
		var iframe = window.frameElement;
		if (iframe.addEventListener)
		{
			iframe.addEventListener("load", readjustIframe, false);
		}
		else if (iframe.attachEvent)
		{
			iframe.attachEvent("onload", readjustIframe);
		}
		iframe.style.display = "";
	},
	/*
	Resizing IFrame dynamically
	Addaed by Arnon 21.10.06
	*/


	FixIFrameHeight : function(iframeId,doc,dontUseEvents)
	{
		if (doc==null)
			doc = document;			  
			
		if (dontUseEvents==null)
			dontUseEvents = false;

		var iframe = doc.getElementById(iframeId);
		
		if (iframe==null)
			return;
			
		if (iframe.addEventListener)
		{
			iframe.addEventListener("load", readjustIframe, false);
		}
		else if (iframe.attachEvent && !dontUseEvents)
		{
			iframe.attachEvent("onload", readjustIframe);
		} 
		else 
			readjustIframe({currentTarget:iframe});
		iframe.style.display = "";
	},

	readjustIframe : function(loadevt)
	{
		var crossevt=(window.event && window.event.type=="load" )? event : loadevt;
		var iframe=(crossevt.currentTarget)? crossevt.currentTarget : crossevt.srcElement;
		if (iframe)
		{
				iframe.style.height=iframe.Document.body.scrollHeight+"px";
				iframe.style.width=iframe.Document.body.scrollWidth+"px";
		}	
	},

	// Set the iframe flash elements transparent
	fixFlashInIframe : function(iframeId)
	{
		var iframe = document.getElementById(iframeId);
		fixFlashForIframe(iframe);
	},
	
	// Set the flash param wmode to transparent
	fixFlashForIframe : function(iframe)
	{
		G2DOM.SetFlashElementsTransparent(iframe);
		
		var iframes = iframe.Document.getElementsByTagName('iframe');
		for (var i = 0; i < iframes.length; i++) 
		{   
			  fixFlashForIframe(iframes[i]);
		}
	},
	
	// Fix the flash on iframe load
	FixIFrameFlash : function(iframeId)
	{
		var iframe = document.getElementById(iframeId);
		var fixFlash = function()
		{
			fixFlashInIframe(iframeId);
		}
		G2_AttachEvent(window, "onload", fixFlash,false);
	},
	
	FixIFrameSize : function(iframeId)
	{
		var iframe = document.getElementById(iframeId);
		iframe.style.border="0px";
		var onloaded = function()
		{
			readjustIframe({currentTarget:iframe});
		}
		if (iframe.addEventListener)
		{
			iframe.addEventListener("load", onloaded, false);
		}
		else if (iframe.attachEvent)
		{
			iframe.attachEvent("onload", onloaded);
		}
			
		iframe.style.display = "";
	},



	readjustIframeSize : function(loadevt)
	{
		var crossevt=(window.event)? event : loadevt;
		var iframe=(crossevt.currentTarget)? crossevt.currentTarget : crossevt.srcElement;
		if (iframe)
		{
			iframe.style.height=iframe.document.body.scrollHeight+"px";
		//	iframe.style.width=iframe.document.body.scrollWidth+"px";
			iframe.style.border="0px";
		}	
	},
	///*End of Resizing IFrame dynamically*/

	G2_AmntKeyPress : function()
	{
		var key = window.event.keyCode;
		if ((key < 48 || key > 57) && key != 46 && key != 45)
			window.event.keyCode = 0;
	},

	// TextBox: simulate [Tab] key press when number of characters reach maxLength
	G2_AutoSkip : function(thisEl, force,evnt)
	{
		if (force || (thisEl.value.length == thisEl.maxLength && evnt.keyCode != 9 && evnt.keyCode != 16)) 
		{
			nextEl = G2_GetNextElementToSkip(thisEl);
			if (nextEl != null) 
			{
				try {
					nextEl.focus();
					if (nextEl.select)
						nextEl.select();
				}
				catch (e) {}
			}
		}
	},

	// Get next element in tabIndex/creationOrder
	G2_GetNextElementToSkip : function(thisEl)
	{
		var currTabIndex = thisEl.tabIndex;
		var minDiffFromCurrTabIndex = 32767, minTabIndex = 32767;
		var nextCreateOrderEl = null, nextTabOrderEl = null, minTabOrderEl = null, nextEl = null;
		var getNextCreateOrder = false;
		for (var i = 0; i < thisEl.form.elements.length; i++) 
		{
			var element = thisEl.form.elements[i];
			if (element.type != "hidden" && !element.disabled && element.style.display != "none") 
			{
				if (element == thisEl) 
				{
					getNextCreateOrder = true;
				}
				else if (element.tabIndex >= 0)
				{
					// Find element with next creation order
					if (getNextCreateOrder) {
						nextCreateOrderEl = thisEl.form.elements[i];
						getNextCreateOrder = false;
						if (thisEl.tabIndex == 0)
							break;
					}
					if (element.tabIndex > 0) 
					{
						// Find element with next tabIndex
						var diff = element.tabIndex - currTabIndex;
						if (diff > 0) 
						{
							if (diff < minDiffFromCurrTabIndex) 
							{
								minDiffFromCurrTabIndex = diff;
								nextTabOrderEl = element;
							}
						}
					}
					// Find element with min tabIndex
					if (element.tabIndex < minTabIndex) 
					{
						minTabIndex = element.tabIndex;
						minTabOrderEl = element;
					}
				}
			}
		}
		if (thisEl.tabIndex == 0 && nextCreateOrderEl != null && nextCreateOrderEl.tabIndex == 0)
			nextEl = nextCreateOrderEl;
		else if (nextTabOrderEl != null)
			nextEl = nextTabOrderEl;
		else if (minTabOrderEl != null)
			nextEl = minTabOrderEl;
		else
			nextEl = nextCreateOrderEl;
		return nextEl;
	},

	G2Menu_ChangeMouseOver : function(parent)
	{	
		if (typeof(parent)=="string")
			parent = document.getElementById(parent);
		if (parent==null)
			return;
		var element = parent.firstChild;
		while(element!=null)
		{
			if(element.onmouseover!=null)
			{
				if(element.onmouseover!=null)
				{
					var func = element.onmouseover;
					element.onmouseover = null;	
					G2_AttachEvent(element, "onclick",function(e)
					{
						Menu_HoverStatic(this);
						e.cancelBubble = true;
					});
				}
			}
			if(element.style!=null && element.style.cursor!="hand")
			{
				element.style.cursor = "hand";
			}
			G2Menu_ChangeMouseOver(element);
			element = element.nextSibling;
		}
	},



	G2Menu_ChangeMouseOver_Old : function(targetElement) //new implementation by dan-el
	{
		var curEl = targetElement.firstChild;
		var firstLevelFound = false;
		while(curEl!=null)
		{
			if(!firstLevelFound && curEl.onmouseover!=null)
				firstLevelFound = true;
	      
			if(firstLevelFound)
			{
				curEl.onclick = function()
				{
					Menu_HoverStatic(this);
					event.cancelBubble = true;
					//return false;
				};
				//Yucki!
				var aa = curEl.getElementsByTagName("A");
				var a= null;
				if(aa.length>0)
					a = aa[0];
	      
				var nolink = "javascript:void(0)";
	        
				if(a!=null && a.href!=nolink)
				{
					if(a.href.indexOf("javascript:")>-1)
					{
						a.href = nolink;//Fix for case 4457. (nolink was: #)
					}
					else if(a.href.lastIndexOf("#") == a.href.length-1)
					{
						a.href = nolink; //Fix for case 4457. (nolink was: #)
					}
				}
	      
				curEl.onmouseover=null;
				curEl.ondeactivate = function(){Menu_Unhover(this);};
				curEl.onmouseout = null;
				//alert("before: " + curEl.style.cursor);
				curEl.style.cursor = "hand";
				if(a!=null)//TODO: Bug - Gilad
					a.style.cursor = "hand";
				//alert("after: " + curEl.style.cursor);
			}
			curEl = curEl.nextSibling;
		}
	  
		if(firstLevelFound)
			return true;
	  
		curEl = targetElement.firstChild;
		while(curEl!=null)
		{    
			//if (curEl.onmouseover!=null)
			//{
				G2Menu_ChangeMouseOver(curEl);
				curEl.onmouseover=null;    
			//}
			curEl = curEl.nextSibling;
		}
	},

	G2ConfirmBox_Show : function(text, eventTarget)
	{
		var eventArgument = confirm(text);
		__doPostBack(eventTarget, eventArgument);
	},

	//
	// findRel Usage:
	//
	// findRel( tag , "style.display == 'none'", G2GetParent )
	// This will find the nearest hidden tag in the hierarchy (moving up)
	// third parameter must be a function, like function(t){return t.nextSibling;} 
	findRel : function(node, predicate, nav)
	{
		if (typeof(predicate)=="string")
			eval("var compiledPredicate = function(){ return this."+predicate+";}");
		else
			compiledPredicate = predicate;

		try
		{
			while (node!=null)
			{			
				if (compiledPredicate.call(node))
					return node;
					
				node = nav(node);			
			}
		} 
		catch(e)
		{
		}
		return null;
	},

	$ : function( a )
	{
		return document.getElementById(a);
	},
		
	EventAttr : function(name)
	{
		if (event.srcElement.attributes[name] == null)
		{
			if (event.srcElement.parentElement.attributes[name] == null)
				return "";
				
			return event.srcElement.parentElement.attributes[name].nodeValue;
		}
			
		return event.srcElement.attributes[name].nodeValue;
	},

	G2Page_ShowWaiting : function()
	{
		//alert('waiting');
	},

	G2Page_ShowReady : function()
	{
		//alert('ready');
	},

	/**************************************************************************
	 *
	 * Popups and related functions
	 *
	 **************************************************************************/

	G2PopupWindow_ExtractParameter : function(features, paramname, defaultValue)
	{
		var poz = features.indexOf(paramname);
		if (poz==-1)
			return defaultValue;
		
		var f = features.substring(poz+paramname.length+1);
		poz = f.indexOf(';');
		var poz2 = f.indexOf(',');
		if (poz2!=-1 && poz ==-1)
			poz = poz2;
		if (poz!=-1)
			f = f.substring(0,poz);
		poz = f.indexOf('px');
		if (poz!=-1)
			f = f.substring(0,poz);
		return f;
		
	},

	// Modal Dialog Box  from http://www.eggheadcafe.com/articles/javascript_modal_dialog.asp
	/*
	var ModalDialogWindow;
	var ModalDialogInterval;
	var ModalDialog = new Object;

	ModalDialog.value = '';
	ModalDialog.eventhandler = '';

	function ModalDialogMaintainFocus()
	{
		try
		{
			if (ModalDialogWindow.closed)
			 {
					window.clearInterval(ModalDialogInterval);
					eval(ModalDialog.eventhandler);       
					return;
			 }
			ModalDialogWindow.focus(); 
		}
		catch (everything) {   }
	}

	function ModalDialogRemoveWatch()
	 {
			ModalDialog.value = '';
			ModalDialog.eventhandler = '';
	 }
	*/

	//This method is used to overcome google toolbar's popup blocker
	G2ExecuteSync : function(f)
	{
		var temporaryButton = G2DOM.G2CreateElement("<input type='Button' style='display:none'></input>");
			temporaryButton.id = temporaryButton.uniqueID;
			temporaryButton.onclick = f;
			document.body.appendChild(temporaryButton);
			temporaryButton.click();
			document.body.removeChild(temporaryButton);
	},

	ModalDialogShow : function(url,name,features,w,h,wndargs)
	{
		var me = window;
		var fullPath = G2_MapPath("~/Client/Dialog.aspx");
		if (IE6 && wndargs.title && wndargs.title!="")
		{
		fullPath += "?Title="+encodeURI(wndargs.title);
		wndargs.title=null;
		}
		//The following is a hack to run a function synchronously using a temporary hidden button   
		function ie_f()
		{
				return null!= window.showModalDialog(fullPath,wndargs,features);//{url:url,obj:me,width:w,height:h}, features);
		}
		function moz_f()
		{	
			var t =  window.open(fullPath,"G2POPUP","modal,"+features);//{url:url,obj:me,width:w,height:h}, features);				
			if (t!=null)
			{
				t.dialogArguments = wndargs;
				t.focus();
			}
			return null!=t;
		}
		if (isIE)
			G2ExecuteSync(ie_f);
		else
			moz_f();
	},


  G2_GetWindowId : function()
  {
    var el = document.getElementById('__WindowID');
    if(el==null)
      return null;
    return el.value
  },
  G2_CreateTable : function(rows, cols, onTopWindow, cellPadding, cellSpacing)
  {
    
		if (onTopWindow)
		{ 
			var win = GetTopAvailableWindow();
			var doc = win.document;
		}
		else
			var doc = document;
		
    
		cellPadding = cellPadding || 0;
		cellSpacing = cellSpacing || 0;
		var table = doc.createElement("table");
		table.cellPadding = cellPadding;
		table.cellSpacing = cellSpacing;
		for(var i=0;i<rows;i++)
		{
			var row = table.insertRow();
			for(var j=0;j<cols;j++)
			{
				var cell = row.insertCell();
			}
		}
		return table;
  },
  
	G2PopupWindow_Open : function(url, context, modal, name, features, title, uniqueID)
	{	
		if (features==null && context!=null)
		{
			//var h = document.getElementById(context);
			//if(h!=null)
			features = window[context];//h.value;
		}   
		if (modal==null)
			modal = features.indexOf('modal=0') == -1;
		url = url.replace(/\$quot\$/g,"'");		
							
		if(modal)
		{
			var wid = G2_GetWindowId();
			if(wid!=null)
			{
				if (url.indexOf('?') == -1)
					url += "?IsPopup=True";
				else
					url+="&IsPopup=True";
			}
	  	var h = parseInt(G2PopupWindow_ExtractParameter(features,"dialogHeight",""));
			var w = parseInt(G2PopupWindow_ExtractParameter(features,"dialogWidth",""));
			var minH = parseInt(G2PopupWindow_ExtractParameter(features,"dialogMinHeight","0"));
			var minW = parseInt(G2PopupWindow_ExtractParameter(features,"dialogMinWidth","0"));
			var autoSize = parseInt(G2PopupWindow_ExtractParameter(features,"autoSize","1"));
			var synthetic = G2PopupWindow_ExtractParameter(features,"SyntheticPopup","0");
			var fade = G2PopupWindow_ExtractParameter(features,"FadeSyntheticPopup","0");			
			var horzMargin = parseInt(G2PopupWindow_ExtractParameter(features,"HorizontalMargin","5"));
			var vertMargin = parseInt(G2PopupWindow_ExtractParameter(features,"VerticalMargin","5"));
			var scroll = G2PopupWindow_ExtractParameter(features,"scroll","0");
			var closeBtn = G2PopupWindow_ExtractParameter(features,"closeBtn","0");
			var closeClientFunction = G2PopupWindow_ExtractParameter(features,"OnCloseClientFunction","");
			var me = window;
			
			//If title was specified, but not name - copy title to name
			if (title && title!=null && title!="" && !name && (name==null||name==""))
				name=title;
			
			//If name was specified, but not title, copy name to title
			if (!title && (title==null||title=="") && name && name!=null && name!="")
				title=name;
			if (synthetic!="0")	
			{
				window.setTimeout(function(){		//This causes 'Operation Aborted' when showing popups in full postbacks
				var wnd = SyntheticModalDialogShow(url,name,features,h,w,{url:url,obj:me,width:w,height:h,title:title,autoSize:(autoSize=="1"),vertMargin:vertMargin,horzMargin:horzMargin, scroll : (scroll=="1"),closeBtn : (closeBtn=="1"), fade : (fade=="1"), minH : minH, minW : minW, uniqueID : uniqueID, closeClientFunction:closeClientFunction});
				},0);
			}
			else
			{	
				var wnd = ModalDialogShow(url,name,features,h,w,{url:url,obj:me,width:w,height:h,title:title,autoSize:autoSize});
			}
		}
		else
		{
			//Workaround for bug #3634: 
			// IE popup blocker blocked the popup, because it was not initiated by a user click.		
			
			//Note: The following is a workaround for IE popup blockers. It is not jiffacode.
			var temporaryButton = G2DOM.G2CreateElement("<input type='Button' style='display:none'></input>");
			temporaryButton.id = temporaryButton.uniqueID;
			temporaryButton.onclick = function()
			{
				var wnd = window.open(url, name, features);
				
				if (null == wnd)
				{
					alert('popup blocker detected!');
				} 
				else
				{
					if (features.indexOf('maximized=yes')!=-1)
						{
							wnd.moveTo( 0, 0 );
		
							wnd.resizeTo( screen.availWidth, screen.availHeight );
						}
				}
			}
			document.body.appendChild(temporaryButton);
			temporaryButton.click();
			document.body.removeChild(temporaryButton);
		}
	},

	updatePopupTitle : function(newTitle)
	{
		if (G2_IsInPopup() && window.top.document.popup!=null)
		{
			window.top.document.popup.setTitle(newTitle);
		}	
	},

	CreateModalContainer : function(contentid,h,w,title)
	{
			h = parseInt(h);
			w = parseInt(w);
			var marginHeight = (document.body.clientHeight - h) / 2;
			var marginWidth = (document.body.clientWidth - w) / 2;
			
			var containerTable = document.createElement("Table");
						
			//containerTable.id = id;
			containerTable.style.position="absolute";
			containerTable.style.pixelLeft=0;
			containerTable.style.pixelTop=0;
			containerTable.style.width=document.body.clientWidth+"px";
			containerTable.style.height=document.body.clientHeight+"px";
			G2_BringToFront(containerTable);
			containerTable.style.display="none"
			containerTable.style.background="transparent";
			containerTable.style.border="0px";
			containerTable.cellPadding = "0";
			containerTable.cellSpacing = "0";
			
			

			//Top Row
			var topRow = containerTable.insertRow();
			topRow.style.height=marginHeight+"px";
			var topRowCell = topRow.insertCell();
			topRowCell.colSpan = "3";
			topRowCell.className="MessageBoxContainer";
			topRowCell.innerHTML="<div style='background:#ccccee; width:300px'><b>"+title+"</b></div>";
			topRowCell.style.textAlign="center";
			topRowCell.style.verticalAlign="bottom";
			////////////////////////////////////////////////////////////////////////
			
			
			//Middle Row
			var middleRow = containerTable.insertRow();
			middleRow.style.height=w+"px";
			
			
			//Middle-Left
			var middleLeftCell = middleRow.insertCell();
			middleLeftCell.style.width=marginWidth+"px";
			middleLeftCell.style.height=h+"px";
			middleLeftCell.innerHTML="&nbsp;";
			middleLeftCell.className = "MessageBoxContainer";
			
			//Content cell
			var ContentCell = middleRow.insertCell();
			ContentCell.align="center";
			ContentCell.id = contentid;
			ContentCell.valign="middle";
			ContentCell.id = "modalContent";
			ContentCell.style.backgroundColor="white";
			ContentCell.style.width=w+"px";
			ContentCell.style.height=h+"px";
			
			//Middle-Right
			var middleRightCell = middleRow.insertCell();
			middleRightCell.style.width=marginWidth+"px";
			middleRightCell.style.height=h+"px";
			middleRightCell.innerHTML="&nbsp;";		
			middleRightCell.className = "MessageBoxContainer";
			
			////////////////////////////////////////////////////////////////////////
			//Bottom Row
			var bottomRow = containerTable.insertRow();
			bottomRow.style.height=marginHeight+"px";
			var bottomRowCell = bottomRow.insertCell();
			bottomRowCell.colSpan = "3";
			bottomRowCell.className="MessageBoxContainer";
			bottomRowCell.innerHTML="&nbsp;";
			
			return containerTable;
				
	},


	G2PopupWindow_CloseAndRedirect : function(url)
	{
		var parentWindow = window.opener; 
		G2_ClosePopupWindow();
		//window.close();
		parentWindow.location = url;
	},

	min : function(a,b)
	{
		return (a<b) ? a : b;
	},

	max : function(a,b)
	{
		return (a>b) ? a : b;
	},

	minInt : function(a,b)
	{
		var valA = parseInt(a);
		var valB = parseInt(b);
		
		if (isNaN(valA))
			return valB;
		if (isNaN(valB))
			return valA;
		return min(valA,valB);
	},

	maxInt : function(a,b)
	{
		var valA = parseInt(a);
		var valB = parseInt(b);
		
		if (isNaN(valA))
			return valB;
		if (isNaN(valB))
			return valA;
		return max(valA,valB);
	},

	// Removes leading whitespaces
	LTrim : function( value ) 
	{	
		var re = /\s*((\S+\s*)*)/;
		return value.replace(re, "$1");	
	},

	// Removes ending whitespaces
	RTrim : function( value ) 
	{	
		var re = /((\s*\S+)*)\s*/;
		return value.replace(re, "$1");	
	},

	// Removes leading and ending whitespaces
	trim : function( value ) 
	{	
		if (!value || value==null)
			value = this;
		return LTrim(RTrim(value));	
	},

	//----------------------------------------------------------------
	// Source: http://www.xs4all.nl/~zanstra/logs/jsLog.htm
	//----------------------------------------------------------------

	verifyObjectShown : function(obj)
	{
		var t=1;
		if (!InView(obj,5))
		{
			ScrollIntoView(obj,false,5);
			//obj.scrollIntoView(false); //align to bottom -- don't use unlesss previouse method fails (and it shouldn't)
		}
	},

	InView : function(element,margin) 
	{
		if(!margin) margin=0;
		var Top=GetTop(element), ScrollTop=GetScrollTop();
		return !(Top<ScrollTop+margin||
			Top>ScrollTop+GetWindowHeight()-element.offsetHeight-margin);
	},

	ScrollIntoView : function(element,bAlignTop,margin) 
	{
		if(!margin) margin=0;
		var posY = GetTop(element);
		if(bAlignTop) 
			posY -= margin;
		else 
			posY += element.offsetHeight+margin-GetWindowHeight();
		window.scrollTo(0, posY);
	},
	
	GetTopWindowHeight : function() 
	{
		return window.top.innerHeight ||
			window.top.document.documentElement&&window.top.document.documentElement.clientHeight ||
			window.top.document.body.clientHeight || 0;
	},

	GetWindowHeight : function() 
	{
		return window.innerHeight ||
			document.documentElement&&document.documentElement.clientHeight ||
			document.body.clientHeight || 0;
	},
	GetScrollTop : function() 
	{
		return window.pageYOffset ||
			document.documentElement && document.documentElement.scrollTop ||
			document.body.scrollTop || 0;
	},
	GetTop : function(element) 
	{
		var pos=0;
		do 
		{
			pos += element.offsetTop;
		}
		while(element=element.offsetParent);
		return pos;
	},


	////////////////////////////////////////////////////////////
	//        Range and selection relates functions           //
	////////////////////////////////////////////////////////////


	G2_SetSelectionRange : function(input, selectionStart, selectionEnd) 
	{
		if (input.setSelectionRange) 
		{
			input.focus();
			input.setSelectionRange(selectionStart, selectionEnd);
		}
		else if (input.createTextRange) 
		{
			var range = input.createTextRange();
			range.collapse(true);
			range.moveEnd('character', selectionEnd);
			range.moveStart('character', selectionStart);
			range.select();
		} else Debug.writeln('Cannot set selection');
	},

	G2_GetSelectionStartFromRange : function(range) 
	{
		var range = document.selection.createRange();
		var isCollapsed = range.compareEndPoints("StartToEnd", range) == 0;
		if (!isCollapsed)
			range.collapse(true);
		var b = range.getBookmark();
		return b.charCodeAt(2) - 2;
	},
	G2_GetSelectionStart : function(input) 
	{
		if (isGecko)
			return input.selectionStart;
		var range = document.selection.createRange();
		var isCollapsed = range.compareEndPoints("StartToEnd", range) == 0;
		if (!isCollapsed)
			range.collapse(true);
		var b = range.getBookmark();
		return b.charCodeAt(2) - 2;
	},

	G2_GetSelectionEnd : function(input) 
	{
		if (isGecko)
			return input.selectionEnd;
		var range = document.selection.createRange();
		var isCollapsed = range.compareEndPoints("StartToEnd", range) == 0;
		if (!isCollapsed)
			range.collapse(false);
		var b = range.getBookmark();
		return b.charCodeAt(2) - 2;
	},
	G2_SetCaretPosition : function(input, index)
	{
		G2_SetSelectionRange(input, index, 0);
	},

	G2_GetCaretPosition : function(input)
	{
		var range = input.document.selection.createRange();
		var pos = 0;
		while(range.move("character", -1)!=0)
			pos++;
		return pos;
	},



	Find : function(array, predicate, context)
	{
		for(var i=0;i<array.length;i++)
		{
			var item = array[i];
			if(predicate(item, context))
				return item;
		}
		return null;
	},

	//
	//iterates an array, and performs the specified action with the specified context.
	//
	ForEach : function(array, action, context)
	{
		if(array==null || action==null)
			return;
		for(var i=0;i<array.length;i++)
		{
			action(array[i], context);
		}
	},

	ForEachSibling : function(element, action, context, predicate)
	{
		if(element==null)
			return;
		action(element, context);
		var nextSibling = element.nextSibling;
		if (predicate != null)
		{
		    while (nextSibling != null && !predicate(nextSibling))
		        nextSibling = nextSibling.nextSibling;   
		}
		ForEachSibling(nextSibling, action, context, predicate);
	},

	G2_PlaceElementAbsolutlyBeside : function(element, parentElement , position)
	{ 
		element.style.position = "absolute";
		parentElement.document.body.appendChild(element);
		element.style.pixelLeft = G2_GetAbsoluteLeft(parentElement)+parentElement.scrollWidth;
		if(position == "Left")
			element.style.pixelLeft = G2_GetAbsoluteLeft(parentElement)-element.scrollWidth;
		
		element.style.pixelTop = (G2_GetAbsoluteTop(parentElement));
		
		// keep element from exiting screen limits
		G2_VerifyAbsoluteElementNotCropped(element);
	},
	G2_PlaceElementAbsolutlyAbove : function(element, parentElement, position, align)
	{
		element.style.position = "absolute";
		parentElement.document.body.appendChild(element);
		
		if(position == "Left")
			element.style.pixelLeft = G2_GetAbsoluteLeft(parentElement) - element.scrollWidth;
		else
			element.style.pixelLeft = (G2_GetAbsoluteLeft(parentElement));
			
		element.style.pixelTop = G2_GetAbsoluteTop(parentElement)-element.scrollHeight;
		
		// keep element from exiting screen limits
		G2_VerifyAbsoluteElementNotCropped(element);
	},

	G2_PlaceElementAbsolutlyBelow : function(element, parentElement, position)
	{
		element.style.position = "absolute";
		parentElement.document.body.appendChild(element);
		
		if(position == "Left")
			element.style.pixelLeft = G2_GetAbsoluteLeft(parentElement) - element.scrollWidth;
		else
			element.style.pixelLeft = G2_GetAbsoluteLeft(parentElement);
			
		element.style.pixelTop = G2_GetAbsoluteTop(parentElement)+parentElement.scrollHeight;
		
		// keep element from exiting screen limits
		G2_VerifyAbsoluteElementNotCropped(element);
	},
	//pos=T,B,R,L
	G2_GetAbsolute : function(element, pos, includeFrames, posInfo)
	{
		if(pos=="t")
			return G2_GetAbsoluteTop(element, includeFrames, posInfo);
		else if(pos=="l")
			return G2_GetAbsoluteLeft(element, includeFrames, posInfo);
		if(pos=="b")
			return G2_GetAbsoluteBottom(element, includeFrames, posInfo);
		else if(pos=="r")
			return G2_GetAbsoluteRight(element, includeFrames, posInfo);
		return null;
	},
	//pos=t,b,r,l
	G2_SetAbsolute : function(element, pos, value, ignoreCurrentTopAndLeft)
	{
		if(value==null)
			return;
		if(pos=="t")
			element.style.pixelTop = value;
		else if(pos=="l")
			element.style.pixelLeft = value;
		else if(pos=="b")
		{
			if(element.style.top=="" || ignoreCurrentTopAndLeft)
				element.style.top = (value-element.offsetHeight)+"px";
			else
				element.style.height=(value - element.style.pixelTop)+"px";
		}
		else if(pos=="r")
		{
			if(element.style.left==""  || ignoreCurrentTopAndLeft)
				element.style.left = (value-element.offsetWidth)+"px";
			else
				element.style.width=(value - element.style.pixelLeft)+"px";
		}
	},
	
	// this method returns true if a change was made, and false otherwise. case 11147
	G2_VerifyAbsoluteElementNotCropped : function(element)
	{
		var result = false;
		var elementOffsetWidth = element.offsetWidth;
		var offsetParent = element.offsetParent;
		if (offsetParent==null)
		  return false;
	  if (isIE)
	    element.style.display = "none";
	  if(element.offsetLeft+elementOffsetWidth>offsetParent.clientWidth)
	  {
		  element.style.pixelLeft-=element.offsetLeft+elementOffsetWidth-offsetParent.clientWidth;
		  result = true;
	  }
	  element.style.display = "";
	  
	   //locate the element in a proper place if it overflow the client screen	height  
	  var scrollTop =  window.top.document.documentElement.scrollTop;
	  var elementOffsetHeight = element.offsetHeight;
		var offsetParent = element.offsetParent;
		if (offsetParent==null)
		 return;
	 	
	 	if(G2_GetAbsoluteTop(element)+elementOffsetHeight > GetTopWindowHeight() + scrollTop)
	 	{
		  element.style.pixelTop -= G2_GetAbsoluteTop(element)+elementOffsetHeight-(GetTopWindowHeight() + scrollTop);
		  result = true;
	  }
	  
	  if(element.style.pixelTop < 0)
			element.style.pixelTop = 0;
			
		return result;
	},
	//places an element near another element - dock = string = "tl:bl,tr:br" etc... tl=TopLeft tl:br,
	G2_PlaceElementAbsolutlyNear : function(element, relativeElement, dock, onTopWindow, appendToElement)
	{
		var parent = onTopWindow ? window.top.document.body : relativeElement.document.body;
		
		if(appendToElement)
			parent = appendToElement;
			
		if(element.parentElement!=parent)
			parent.appendChild(element);
		if (isMoz)
		  element.style.display = "none";
		element.style.position = "absolute";
		var tokens = dock.split(",");
		var settings = {};
		for(var i=0;i<tokens.length;i++)
		{
			var token = tokens[i];
			var miniTokens = token.split(":");
			var relCorner = miniTokens[0];
			var absCorner = miniTokens[1];
			
			var rel1 = relCorner.charAt(0);
			var rel2 = relCorner.charAt(1);
			var abs1 = absCorner.charAt(0);
			var abs2 = absCorner.charAt(1);
			var posInfo = new Object();
			var rel1Val = G2_GetAbsolute(relativeElement, rel1, onTopWindow, posInfo);
			var rel2Val = G2_GetAbsolute(relativeElement, rel2, onTopWindow, posInfo);
			if(posInfo.offsetParent!=null && posInfo.offsetParent.currentStyle!=null)
			{
			  if(posInfo.offsetParent.currentStyle.position=="fixed")
			    element.style.position = "fixed";
			}
			settings[abs1] = rel1Val;
			settings[abs2] = rel2Val;
		}
		if (isMoz)
		  element.style.display = "";
		//the top and left MUST be set before the bottom and right
		G2_SetAbsolute(element, "t", settings["t"]); 
		G2_SetAbsolute(element, "l", settings["l"]); 
		G2_SetAbsolute(element, "b", settings["b"], settings["t"]==null); 
		G2_SetAbsolute(element, "r", settings["r"], settings["l"]==null); 
	},	
	G2_IsAbsolutlyPositioned : function(element)
	{
		if(element==null)
			return false;
		if(element.style.position=="absolute")
			return true;
		return G2_IsAbsolutlyPositioned(element.parentElement);
	},


	G2_GetElement : function(idOrElement)
	{
		if(typeof(idOrElement)=="string")
			return document.getElementById(idOrElement);
		return idOrElement;
	},
	
	G2_GetAbsoluteLeft : function(element, includeFrames, posInfo) 
	{
	  var x = 0;
    var originalElement = element;
    while( element != null ) 
    {
      x += element.offsetLeft;
      //bug in ie - when using 'relative right:50px' the offsetLeft is wrong //TODO: check in firefox  (dan-el)
 			if(element.style.position=="relative" && element.style.right.contains("px") && element.offsetParent!=element.parentElement)
			{
				x-=element.style.pixelRight;
			}
      if(posInfo!=null)
        posInfo.offsetParent = element;
      if (isMoz && element.currentStyle.position=="fixed")
        element = null;
      else
        element = element.offsetParent;
    }
    if (includeFrames && originalElement.document.parentWindow.frameElement!=null)
    {
      var f = originalElement.document.parentWindow.frameElement;
      var fb = 0;
      if(f.frameBorder == "1" || f.frameBorder == "yes")
        fb = 2;
      x += G2_GetAbsoluteLeft(f, includeFrames) + fb;
    }
    return x;
	},

	G2_GetAbsoluteTop : function(element, includeFrames, posInfo) 
	{
	  var y = 0;
    var originalElement = element;
    while( element != null ) 
    {
      y += element.offsetTop;

			// taking into account scrooling with in overflow scroll elements
      if(element.tagName != 'HTML' && element.scrollTop != null)
				y -= element.scrollTop;
			if(element.tagName == 'IFRAME')
				y -= document.documentElement.scrollTop;

      if(posInfo!=null)
        posInfo.offsetParent = element;
      if (isMoz && element.currentStyle.position=="fixed")
        element = null;
      else
        element = element.offsetParent;
    }
    if (includeFrames && originalElement.document.parentWindow.frameElement!=null)
    {
      var f = originalElement.document.parentWindow.frameElement;
      var fb = 0;
      if(f.frameBorder == "1" || f.frameBorder == "yes")
        fb = 2;
      y += G2_GetAbsoluteTop(f, includeFrames) + fb;
    }
    return y;
	},
	G2_GetAbsoluteBottom : function(element, includeFrames) 
	{
		return G2_GetAbsoluteTop(element, includeFrames)+element.offsetHeight;
	},
	G2_GetAbsoluteRight : function(element, includeFrames) 
	{
		return G2_GetAbsoluteLeft(element, includeFrames)+element.offsetWidth;
	},
	isInSyntheticPopup : function()
	{
		return (parent.document.body.closeSyntheticPopup!=null || document.body.closeSyntheticPopup!=null);
	},

	/**
			This method is called by G2Page.CloseWindow()


	**/
	 G2_ClosePopupWindow : function(openerFunctionScript_functionToCall,
										result,
										firePopupClosedOnOpener,
										fireCloseScript_functionToCall,
										fireCloseScript_windowID,
										fireCloseScript_forceSilentPopupClosedOnOpener)
	{
	  // The window parent should register G2PopupWindow2.js in order to 
	  // Get the popup window (the problem happens when the parent window
	  // of the popup is not the same as the window which open the popup)
		if(window.parent!=window && window.parent.G2PopupWindow2!=null)
		{
			var popup = window.parent.G2PopupWindow2.GetCurrentPopup(window);
			if(popup!=null)
			{
				var silent = fireCloseScript_forceSilentPopupClosedOnOpener ? true : null;
				popup.Close(firePopupClosedOnOpener, fireCloseScript_windowID, silent);
				return;
			}
		}
			if (isInSyntheticPopup())
				return G2_CloseSyntheticPopupWindow(openerFunctionScript_functionToCall,
										result,
										firePopupClosedOnOpener,
										fireCloseScript_functionToCall,
										fireCloseScript_windowID,
										fireCloseScript_forceSilentPopupClosedOnOpener);
				
			var op = window.top.opener;    
			if (op == null && window.dialogArguments == null)
			{
					//'Access Denied' detected.
					if (!String.IsNullOrEmpty(result))
							throw "Error - Result cannot be set with SSL Pages. To return a value from a popup to its opener, use the returnValue property on G2Page.";
					window.top.close();
					return;
			}
			else
			{            
					if (op == null)
						op = window.dialogArguments.obj;
						
					if (!String.IsNullOrEmpty(openerFunctionScript_functionToCall))
					{
									var openerFunction = op[openerFunctionScript_functionToCall];
									openerFunction(result);
					}
	        
					if (window.top.dialogArguments)
							window.top.dialogArguments.CloseEventFired = true;
					window.top.close();
	        
					if (firePopupClosedOnOpener)
					{
						try
						{
							var closeCallback = op.G2_FirePopupClosed;
							if (closeCallback!=null)
								closeCallback.call(op,fireCloseScript_windowID,result,fireCloseScript_forceSilentPopupClosedOnOpener);        
						}
						catch(accessDenied)
						{
							//This is a known limitation. SSL pages and non-SSL pages cannot communicate with each other
						}
							
					}       
			}
	},


	G2_FindElementById : function(element, id)
	{
		return _G2_FindElementById(element, id);
	},
	_G2_FindElementById : function(element, id)
	{
		if(element.id==id)
			return element;	
		if(element.doesNotContainInputs || element.tagName=="SELECT")
			return null;

		var child = element.firstChild;
		while(child!=null)
		{
			var el = _G2_FindElementById(child, id);
			if(el!=null)
				return el;
			child = child.nextSibling;
		}
		return null;
	},

	G2_FindParentElementByG2Tag : function(element, g2tag)
	{
		return _G2_FindParentElementByG2Tag(element, g2tag);
	},
	_G2_FindParentElementByG2Tag : function(element, g2tag)
	{
		if(element==null)
			return null;
		if(G2DOM.G2GetAttribute(element,'g2tag')==g2tag)
			return element;
		return _G2_FindParentElementByG2Tag(element.parentElement, g2tag);
	},

	G2_FindElementByTagName : function(element, tagName)
	{
		if(element.tagName==tagName)
			return element;	
		var child = element.firstChild;
		while(child!=null)
		{
			var el = G2_FindElementByTagName(child, tagName);
			if(el!=null)
				return el;
			child = child.nextSibling;
		}
		return null;
	},

	G2_FindNodeByNameValue : function(element, name, value)
	{
		if(element[name]==value)
			return element;	
		var child = element.firstChild;
		while(child!=null)
		{
			var el = G2_FindNodeByNameValue(child, name, value);
			if(el!=null)
				return el;
			child = child.nextSibling;
		}
		return null;
	},


	// When a page detects it is opened in a popup window, it calls this method
	G2Dialog_Init : function()
	{
		//Try accessing window.top.dialogArguments
		try
		{
			if (window.top.dialogArguments!=null)
			{
				//If that succeeds, we are in a non-SSL popup 
				//In that case, un-hook the onunload event handler
				window.top.document.getElementById('IFRM').contentWindow.onunload = null;		
				
			}
		} catch(bloodyerror)
		{
		}
	},
	G2_FireEventArray : function(owner, array)
	{
		for(var i=0;i<array.length;i++)
		{
			array[i](array.owner);
		}
	},

	G2_GetChildControlById : function(namingContainer, innerElementId)
	{
		return document.getElementById(namingContainer.id+"_"+innerElementId);
	},

	G2FindControlsById : function(controlIds)
	{
		var ret = [];
		if(controlIds==null)
			return ret;
		if (typeof(controlIds)=="string")
		{
			if (controlIds.length==0)
				return ret;			
			controlIds = controlIds.split(/,/g);	
		}
		for(var i=0,j=controlIds.length;i<j;i++)
		{
				var ctrl = document.getElementById(controlIds[i]);
				if (ctrl)
					ret.push(ctrl);
		}
		return ret;
	},

	G2ContextChange : function(func,context)
	{
		return function()
		{
			func.apply(context,arguments);
		}
	},
	
	//***********************************************************
	//                   Processing image                       *
	//***********************************************************
	
	getProcessingImageID : function()
	{
	  return window.ProcessingImageID;
	},
	
	setProcessingImageID : function(value)
	{
	  if(window.ProcessingImageID == value)
	    return;
	  window.ProcessingImageID = value;
	  window.ProcessingImage = null;
	},
	
	getProcessingImage : function()
	{
	  if(window.ProcessingImage==null && ProcessingImageID!=null)
	    window.ProcessingImage = document.getElementById(ProcessingImageID);
	  return window.ProcessingImage;
	},
	
	getElementsToHideWhileProcessing_Cache : function()
	{
	 if(window.ElementsToHideWhileProcessing_Cache == null)
	 {
	  window.ElementsToHideWhileProcessing_Cache = [];
	  
	  if(window.ElementsToHideWhileProcessing!=null)
	  {
	    var list = window.ElementsToHideWhileProcessing.split(',');
	    var eth = window.ElementsToHideWhileProcessing_Cache;
	    for (var i=0;i<list.length;i++)
		  {
			  var e = document.getElementById(list[i]);
			  if (e==null)
				  continue;
  			  
			  eth.push(e);
		  }
	   }
	 }
	 return window.ElementsToHideWhileProcessing_Cache;
	},
	
	getElementsToHideWhileProcessing : function()
	{
	  if(window.ElementsToHideWhileProcessing==null)
	    return "";
	  return window.ElementsToHideWhileProcessing;
	},
      
  setElementsToHideWhileProcessing : function(value)
	{
	  if(window.ElementsToHideWhileProcessing==value)
	    return;
	  window.ElementsToHideWhileProcessing = value;
	  window.ElementsToHideWhileProcessing_Cache = null;
	},
	  
	ShowProcessingImage : function(targetEl)
	{
		//flag that the processing image is activated
		window.ProcessingImageActive = true;
		var eventX = -1;
		var eventY = -1;
		if (!isMoz && event && event.type != "")
		{
			eventX = event.clientX;
			eventY = event.clientY;
		}
		window.setTimeout(function() {ShowProcessingImage_Timeout(targetEl, eventX, eventY);}, 100);
	},

	ShowProcessingImage_Timeout : function(targetEl, eventX, eventY)
	{
	//This function is running asynchronously, so we must check 
	//if the processing image is still required, and hasn't been switched off.
		if (window.ProcessingImageActive == false)
			return;
	    
		var processingImage = getProcessingImage();
		
		//Hide other elements
		var list = window.getElementsToHideWhileProcessing_Cache();
		for (var i=0;i<list.length;i++)
		{
			list[i].style.display='none';
		}
		
		//show processing image
		if (processingImage != null)
		{
			processingImage.style.display = '';
			if (processingImage.isDynamic == 'true')
			{   
					G2_ShowDisabler(true);
					processingImage.style.zIndex = 10001;
					
					if (eventX != -1 && eventY != -1)
					{
							processingImage.style.position = 'absolute';
							processingImage.style.left = Math.max(0, document.documentElement.scrollLeft + eventX - (processingImage.scrollWidth) / 2) + "px";
							processingImage.style.top = Math.max(0, document.documentElement.scrollTop + eventY - (processingImage.scrollHeight / 2)) + "px";
					}
					else
					{
						G2_PlaceElementAbsolutlyNear(processingImage, targetEl, "bl:bl", true);
						G2_VerifyAbsoluteElementNotCropped(processingImage);
					}
			}
		}
	},

	HideProcessingImage : function()
	{
		//switch flag off
		window.ProcessingImageActive = false;
		if (G2_IsNavigating())
		{
			return; //Keep the processing image until we are done navigating
		}	
		
		//hide processing image
		var processingImage = getProcessingImage();
		if (processingImage != null)
		{
			//Debug.writeln("hiding processing image: "+processingImage.id);
			processingImage.style.display = 'none';
		}
		
		//Show other elements
		var list = window.getElementsToHideWhileProcessing_Cache();
		for (var i=0;i<list.length;i++)
		{
			list[i].style.display='block';
		}
	},
	G2_PrintPopup : function(target)
	{
		if(G2_IsInPopup())
		{
			var win = window.open(target.location.href + "&HideButtons=true");
			if(win!=null)
			{
				G2_AttachEvent(win, "onload", function()
				{
					window.setTimeout(function(){	win.print();win.close();}, 500);
				});
			}
		}
		else
		{
			target.focus(); 
			target.print(); 
		}
	},
	// printing an html table
	Print : function(tableId)
	{
		window.focus();
		//Added by Arnon in case 5103
		var TableToPrintObj = document.getElementById(tableId)
		var TableToPrintWidth;
		if(TableToPrintObj && !(typeof document.body.style.maxHeight != "undefined"))//Not IE 7 and ID exist
		{
			// changeing width to fit printing sheet
			TableToPrintWidth = TableToPrintObj.style.pixelWidth;
			TableToPrintObj.style.width="640px";
		}
		window.print();
		if(TableToPrintObj && !(typeof document.body.style.maxHeight != "undefined")) //Not IE 7 and ID exist
		{
			// restore width
			TableToPrintObj.style.width=TableToPrintWidth+"px";
		}
	},
	G2_PreventInputPost : function(id)
	{
		if(typeof(id)=="string")
			G2_PreventPostElementIds[id] = true;
		else
			Debug.writeln("id is not a string");
		//input.disabled = true;
	},
	Select_SetAllSelected : function(select, selected)
	{
		if(select.tagName!="SELECT")
			throw new Error("Select Object expected "+select.tagName);
		//The visibility trick optimizes the selection performance
		var useVisiblityTrick = select.style.visibility=="";
		if(useVisiblityTrick)
			select.style.visibility = "hidden";
		var option = select.options[0];
		while(option!=null)
		{
			if(option.tagName=="OPTION")
				option.selected = selected;
			option = option.nextSibling;
		}
		G2.notifyInputChanged(select);
		if(useVisiblityTrick)
			select.style.visibility = "";
	},
	G2ListBox_SelectAll : function(id)
	{
		var select = $(id);
		if(select==null || select.disabled)
			return;
		Select_SetAllSelected(select, true);
	},
	G2ListBox_SelectNone : function(id)
	{
		var select = $(id);
		if(select==null || select.disabled)
			return;
		Select_SetAllSelected(select, false);	
	},
	G2_DisableBack : function()
	{
			if (window.backIsDisabled != true)
			{
				window.backIsDisabled = true;
				for(var i=0;i<2;i++)
				{
					window.location.hash = "#p"+i;
				}

				window.setInterval(function()
				{
				    if(docTitle!= null)
				    {
				        document.title = docTitle;
				    }
				    if(window.history.forward(1) != null)
						window.history.forward(1);
				}, 100);

			}
		},
		G2_ShowBeforeUnloadMessage : function (e, message, checkFunction)
		{
			if (window.allowUnloadMessage == false)
			{
				window.allowUnloadMessage = true;
			  return;
			}
			if (window[checkFunction] != null)
				if (!window[checkFunction]())
					return;
			return message;
		},
		
		// ------------------------- G2Alert ----------------------------
		//open alert Popup
		G2Alert : function(message, width)
		{
			if(width == null)
				width = 200;
				
			var doc = window.top.document;
			// build alert html
			var alertObj = doc.createElement("DIV");
			
			alertObj.innerHTML = '<TABLE style="width:' + width + '" class=modalPopup><TBODY>' +
			'<TR>' +
			'<TD style="PADDING-TOP: 5px" align="center">' +
			message + 
			'</TD></TR>' +
			'<TR>' +
			'<TD style="PADDING-TOP: 10px;cursor:pointer" align="center" onclick="G2CloseAlert();"><u>OK</u></TD>' +
			'</TR></TBODY></TABLE>';

			 // clone the Div and show the clone
			 alertObj.id = "AlertDiv";

			//return if already shown
			if (alertObj.style.display == 'block')
				return;
				
			// append messagePopup to the form and not to the body (case 11229)
			var container = doc.forms[0];
			
			// create a cover div 
			var coverDiv = G2_CreateModalCoverDiv();
			coverDiv.style.filter = "alpha(opacity=70)";

			// append cover div to form
			if(container != null)
				container.appendChild(coverDiv);
			else
				doc.getElementsByTagName("body")[0].appendChild(coverDiv);

			//set popup div position
			alertObj.style.position = 'absolute';
			
			alertObj.style.left = Math.max(0, doc.documentElement.scrollLeft + (doc.documentElement.clientWidth / 2) - (alertObj.scrollWidth / 2)) + "px";
			alertObj.style.top = Math.max(0, doc.documentElement.scrollTop + (doc.documentElement.clientHeight / 2) - (alertObj.scrollHeight / 2)) + "px";

			alertObj.style.zIndex = 1001;
			G2_AttachFrame(alertObj);

			// append element to form
			if(container != null)
				container.appendChild(alertObj);
			else
				doc.body.appendChild(alertObj);
			
			// verify that the popup is in the boreder of the screen
			G2_VerifyAbsoluteElementNotCropped(alertObj);
		},
		
		// close alert popup
		G2CloseAlert : function()
		{
			var doc = window.top.document;
			var alertObj = doc.getElementById("AlertDiv");
			// remove the cloned Div
			var container = alertObj.parentElement;
			if (alertObj != null && container !=  null)
				container.removeChild(alertObj);
			// remove the cover Div
			var coverDiv = doc.getElementById("CoverDiv");
			container = coverDiv.parentElement;
			if (coverDiv != null && container !=  null)
					container.removeChild(coverDiv);
			G2_DetachFrame(alertObj);
		},

		//create cover div for the modal effect
		G2_CreateModalCoverDiv : function(win)
		{
			var doc = window.top.document;
			if(win != null)
				doc = win.document;
				
			var coverDiv = doc.createElement('DIV');
			coverDiv.id = "CoverDiv";
			coverDiv.className = "CoverDiv";
			coverDiv.style.left = "0px";
			coverDiv.style.top = "0px";
			docHeight = Math.max (doc.documentElement.offsetHeight,doc.documentElement.scrollHeight);
			docWidth = Math.max ( doc.documentElement.offsetWidth, doc.documentElement.scrollWidth);
			coverDiv.style.height = docHeight+"px";
			coverDiv.style.width = docWidth+"px";
			coverDiv.style.zIndex="10";
			coverDiv.style.position="absolute";
			return coverDiv;
		},
		
		G2_VerifyScrollableElementHeight : function(pnlID, maxHeight)
		{
			var pnl = $(pnlID);
			if(pnl == null)
				return;
			if(maxHeight == null || maxHeight == 0)
				return;
				
			if(pnl.clientHeight > maxHeight)
			{
				pnl.style.overflowY = 'scroll';
				pnl.style.height = maxHeight;
			}
		},
		G2_VerifyScrollableElementWidth : function(pnlID, maxWidth)
		{
			var pnl = $(pnlID);
			if(pnl == null)
				return;
			if(maxWidth == null || maxWidth == 0)
				return;
				
			if(pnl.clientWidth > maxWidth)
			{
				pnl.style.overflowX = 'scroll';
				pnl.style.width = maxWidth;
			}
		}
	
});
G2_PreventPostElementIds = new Object();

//**************************************************************************************************

WebForm_InitCallback = function(){};//this is disabled in purpose. we use G2_InitCallback;
var G2_SetFocus_ThreadId = null;
//var G2_InitCallbackFirstTime = true;
var _registeredScripts;
var HtmlSelectEmptyValue = "_NULL_"; //empty strings causes problems with tabs and selectedIndex

if(typeof(Date_ShortMonthNames)=="undefined")
	Date_ShortMonthNames = new Array("Jan", "Feb", "Mar", "Apr", "May", "Jun", "Jul", "Aug", "Sep", "Oct", "Nov", "Dec");
if(typeof(Date_MonthNames)=="undefined")
	Date_MonthNames = new Array("January", "February", "March", "April", "May", "June", "July", "August", "September", "October", "November", "December");
if(typeof(G2_ShortDays)=="undefined")
	G2_ShortDays = ["Su","Mo","Tu","We","Th","Fr","Sa"];

var G2_maxZ=999;
var G2_FixFrame = null;
var enableResizing = false; 
var G2Tooltips = new Array();



G2_PreventInputPost("G2_RootAppPath");





String.IsNullOrEmpty = function(value)
{
	return value==null || value=="";
}

String.Format = function(format, args)
{
	for(var i=1;i<arguments.length;i++)
	{
		var arg = arguments[i];
		var exp = new RegExp("[{]"+(i-1)+"[}]", "g");
		format = format.replace(exp, arg);
	}
	return format;
}

String.Replace = function(s, search, replace)
{
	var exp = new RegExp(search, "g");
	return s.replace(exp, replace);
}








//**************************************************************************************************






function Stopper()
{
	this.laps = new Array();
	this.lapsInfos = new Array();
}

Stopper.prototype.start = function ()
{
	var now = new Date();
	this.laps.push(now);
}

Stopper.prototype.lap = function (name)
{
	var now = new Date();
	this.laps.push(now);
	if(name==null)
	  name="Lap";
	this.lapsInfos.push(name);
	return now-this.laps[this.laps.length-2];
}

Stopper.prototype.total = function ()
{
	var now = new Date();
	return now-this.laps[0];
}

Stopper.prototype.maxIndex = function ()
{
  var maxIndex = -1;
  var max=0;
	for(var i=1; i<this.laps.length; i++)
	{
	  var start = this.laps[i];
	  var end = this.laps[i-1];
	  var lap = start-end;
	  if(lap>max)
	  {
	    maxIndex = i;
	    max = lap;
	  }
  }
  return maxIndex;
}

Stopper.prototype.totalLaps = function ()
{
	var start = this.laps[0];
	var end = this.laps[this.laps.length-1];
	return end-start;
}

var StopperWinID = 0;
Stopper.prototype.report = function (title)
{
  var winID = "Stoper_"+StopperWinID;
  StopperWinID++;
	var win = window.open(null, winID, "height=300,width=300,status=no,toolbar=no, menubar=no, location=no, resizable=yes");
	var doc = win.document;
	doc.open();
	
	doc.write("<html><body>");
	//var now = new Date();
	doc.write("<div style='font-size:8px;'><b>"+title+"</b></div>");
	var maxIndex = this.maxIndex();
	doc.write("<table>");
	doc.write("<tbody>");
	for(var i=1; i<this.laps.length; i++)
	{
	  var start = this.laps[i];
	  var end = this.laps[i-1];
	  doc.write("<tr>");
	  doc.write("<td>");
	  doc.write("<div style='"); 
	  if(i==maxIndex)
	  {
	    doc.write("color:red;");
	  }
	  doc.write("'>"+i.toString());
	  doc.write("</div>");
	  doc.write("</td>");
	  doc.write("<td>");
	  doc.write(this.lapsInfos[i-1]);
	  doc.write("</td>");
	  doc.write("<td>");
	  doc.write((start-end)+"");
	  doc.write("</td>");
	  doc.write("</tr>");
	}
	doc.write("</tbody>");
	doc.write("</table>");
	doc.write("<hr />");
	doc.write("<div style='color:blue'>Total: <b>" + this.totalLaps()+ "</b>ms</div>"); 
	doc.write("</body></html>");
	doc.close();	
}


var specialCopyKey = 17; //ctrl + q 



Char = 
{
	Backspace : 8,
	Tab : 9,
	Enter : 13,
	Ctrl : 16,
	Alt : 17,
	Pause : 19,
	CapsLock : 20,
	Escape : 27,
	PageUp : 33,
	PageDown : 34,
	End : 35,
	Home : 36,
	ArrowLeft : 37,
	ArrowUp : 38,
	ArrowRight : 39,
	ArrowDown : 40,
	Insert : 45,
	Delete : 46,
	categories : {Digit:/[0-9]/, Upper:/[A-Z]/, Lower:/[a-z]/},
	IsDigit : function(charOrCode)
	{
		return this.IsInCategory(charOrCode, "Digit");
	},
	IsInCategory : function(charOrCode, categoryName)
	{
		if(charOrCode==null)
			return false;
		var s = typeof(charOrCode)=="number" ? String.fromCharCode(charOrCode) : charOrCode;
		return this.categories[categoryName].test(s);
	},
	IsUpper : function(charOrCode)
	{
		return this.IsInCategory(charOrCode, "Upper");
	},
	IsLower : function(charOrCode)
	{
		return this.IsInCategory(charOrCode, "Lower");
	},
	ToUpperKeyCode : function(keyCode)
	{
		return keyCode-32;
	},
	//
	// returns a value indicating whether the given charCode is a key that changes the cursor position
	//
	IsCursorPositionCharCode : function (charCode)
	{
		if
		(
			charCode==this.ArrowUp || 
			charCode==this.ArrowDown || 
			charCode==this.ArrowLeft || 
			charCode==this.ArrowRight || 
			charCode==this.Home || 
			charCode==this.End || 
			charCode==this.PageUp || 
			charCode==this.PageDown
		)
		{
			return true;
		}
		return false;
	}


}

//46 Delete 
//TODO:
//91 Left Windows 
//92 Right Windows 
//93 Context Menu 
//96 NumPad 0 
//97 NumPad 1 
//98 NumPad 2 
//99 NumPad 3 
//100 NumPad 4 
//101 NumPad 5 
//102 NumPad 6 
//103 NumPad 7 
//104 NumPad 8 
//105 NumPad 9 
//106 NumPad * 
//107 NumPad + 
//109 NumPad - 
//110 NumPad . 
//111 NumPad / 
//112 F1 
//113 F2 
//114 F3 
//115 F4 
//116 F5 
//117 F6 
//118 F7 
//119 F8 
//120 F9 
//121 F10 
//122 F11 
//123 F12 
//144 Num Lock 
//145 Scroll Lock 
//186 ; 
//187 = 
//188 , 
//189 - 
//190 . 
//191 / 
//192 ` 
//219 [ 
//220 \ 
//221 ] 
//222 ' 


function G2KeysClass()
{
  this.up = 38; //up arrow  
  this.down = 40; //down arrow
  this.left =  37; //left arrow
  this.right =  39; //right arrow
  this.pageUp =  33; //page up  
  this.pageDown =  34; //page down  
  this.home =  36; //home  
  this.end =  35; //end                  
  this.enter =  13; //enter  
  this.tab =  9; //tab  
  this.esc =  27; //esc  
  this.shift =  16; //shift  
  this.ctrl =  17; //ctrl  
  this.alt =  18; //alt  
  this.caps =  20; //caps lock
  this.backspace =  8; //backspace  
  this.del =  46; //delete
  
  this.controlKeys = new Array(this.up, this.down, this.left, this.right, this.pageUp, this.pageDown, this.home, this.end, this.enter, this.tab, this.shift, this.ctrl, this.alt, this.caps, this.backspace, this.del);
}
var G2Keys = new G2KeysClass();


G2EventArray = function(owner)
{
	this.owner = owner;
}
G2_DeclareClass(G2EventArray, "G2EventArray", Array,
{
	fire : function()
	{
		for(var i=0;i<this.length;i++)
		{
			this[i](this.owner);
		}
	}
});




//Add trim() to String.
String.prototype.trim = trim;
	/*
	function G2PopupWindow_Open2(url, context, modal, name, features)
	{	
		if (features==null && context!=null)
		{
			var h = document.all[context];
			if(h!=null)
				features = h.value;
		}   
		if (modal==null)
			modal=true;
			
		if(modal)
		{
			var h = G2PopupWindow_ExtractParameter(features,"dialogHeight");
			var w = G2PopupWindow_ExtractParameter(features,"dialogWidth");
					
			//Fix for callbacks on popup closed event
			var me = window;
			function f()
			{
				window.showModalDialog(G2_MapPath("~/Client/Dialog.aspx"),{url:url,obj:me,width:w,height:h}, features);
			}		
			f();
		}
		else
		{
	  
			//Workaround for bug #3634: 
			// IE popup blocker blocked the popup, because it was not initiated by a user click.		
			
			//Note: The following is a workaround for IE popup blockers. It is not jiffacode.
			var temporaryButton = G2DOM.G2CreateElement("<input type='Button' style='display:none'></input>");
			temporaryButton.id = temporaryButton.uniqueID;
			temporaryButton.onclick = function()
			{
				if (null == window.open(url, name, features))
				{
					alert('popup blocker detected!');
				}
			}
			document.body.appendChild(temporaryButton);
			temporaryButton.click();
			document.body.removeChild(temporaryButton);
		}
	}*/
if(ENABLE_PROFILER)
	Profiler.createDebugDiv();

ListSet = function()
{
	this._list = [];
	this._set = {};
}
G2_DeclareClass(ListSet, "ListSet", null, 
{
	addRange : function(array)
	{
		for(var i=0;i<array.length;i++)
		{
			this.add(array[i]);
		}
	},
	add : function(item)
	{
		if(this._set[item]!=null)
			return false;
		this._list.push(item);
		this._set[item] = this._list.length-1;
		return true;
	},
	remove : function(item)
	{
		if(this._set[item]==null)
			return false;
		var index = this._set[item];
		this._list.splice(index, 1); //removeAt
		this._set[item] = null;
		for(var i=index;i<this._list.length;i++) //perform reindexing
		{
			var item = this._list[index];
			this._set[item] = index;
		}
		return true;
	},
	toString : function(seperator)
	{
		return this._list.join(seperator);
	}
	
});

/* G2PopupManager
Manages all popups and tooltips within the application.
*/
G2PopupManager = 
{
//	popups : {},
//	tooltipTargets : [],
//	allowTooltips : true,
	
	init : function()
	{
		this.attachToOnClick(document, true);
		this.allowTooltips = true;
		if(window.top.G2PopupManager==this)
		{
		  this.popups = new Object();
		  this.tooltipTargets = new Array();
		}
		else
		{
		  var tm = window.top.G2PopupManager;
		  this.popups = tm.popups;
		  this.tooltipTargets = tm.tooltipTargets;
		}
	},
		
	attachToOnClick : function(doc, includeFrames)
	{
	  if(doc.attachEvent) //G2Dom is not available right now
		{
			doc.attachEvent("onmousedown", this.__document_onclick);
//			if(IE6) //memory leaks
//			  doc.parentWindow.attachEvent("onunload", this.window_onunload);
		}
		else if(document.addEventListener)
		{
			doc.addEventListener("mousedown", this.__document_onclick, false);
		}
//		if(!includeFrames || doc.parentWindow==null || doc.parentWindow.document==doc)
//		  return;
//		
//	  doc = doc.parentWindow.document;
//	  this.attachToOnClick(doc, includeFrames);
	},
	window_onunload : function(e)
	{
	  G2PopupManager.unload();
	},
	unload : function(e)
	{
	  for(var p in this.popups)
	  {
	    this.popups[p] = null;
	  }
	},
	__document_onclick : function(e)
	{
		G2PopupManager._document_onclick(e);
	},
	_document_onclick : function(e)
	{
		var element = e.srcElement;
		
		if(element!=null && element.tagName=="HTML")
		  return;//Clicked on scroll, ignore
		 
		while(element!=null)
		{
			var popup = this.popups[element.uniqueID];
			if(popup!=null)
				return;
			element = element.parentElement;
		}
		this.closeAllPopups(true);
		this.closeAllTooltips();
	},
	
	//Use this method to display a popup element relatively to a specific element
	//
	openPopup : function(element, relativeElement, dock, onTopWindow)
	{
		this.closeAllPopups();
		var popup = {element:element, relativeElement:relativeElement, dock:dock, isOpen:true, allowCloseOnDocumentClick:false};
		this.popups[element.uniqueID] = popup;
		if(relativeElement==null)
			throw new Error("relative element not found, cannot show popup");
		if(element.g2closepopup=="false")
			element.style.display = "";
		G2_PlaceElementAbsolutlyNear(element, relativeElement, dock, onTopWindow);
		if(dock==null || !dock.contains(","))
			G2_VerifyAbsoluteElementNotCropped(element);
		G2_BringToFront(element);
		G2_AttachFrame(element);
		
		window.setTimeout(
		function()
		{
			popup.allowCloseOnDocumentClick = true;
		}, 0);
		
	  if (element.onOpened!=null)
	    element.onOpened(element);			
	},
	
	//Closes all registered popups in the window
	closeAllPopups : function(isDocumentClick)
	{
		for(var p in this.popups)
		{
			var pp = this.popups[p];
			if(pp!=null && pp.isOpen)
			{
				if(isDocumentClick && !pp.allowCloseOnDocumentClick)
					continue;
				this.closePopup(pp.element);
			}
		}
	},
	isPopupOpened : function(element)
	{
		var popup = this.getPopup(element);
		if(popup!=null && popup.isOpen)
			return true;
		return false;
	},
	
	//Retrives a specific popup element
	getPopup : function(element)
	{
		return this.popups[element.uniqueID];
	},
	
	//Closes a given popup by its element
	closePopup : function(element)
	{
		var popup = this.getPopup(element);
		if(popup==null)
			return;
		if (popup.element.onBeforeClose!=null)
		  popup.element.onBeforeClose(popup.element);
		G2_DetachFrame(element);
		if(element.g2closepopup=="false")
		{
			element.style.display = "none";
		}
		else if(element.parentElement!=null)
		{
			element.parentElement.removeChild(element);
		}
		popup.isOpen = false;
		if(element.onPopupClosed)
		  element.onPopupClosed();
		 
		delete this.popups[element.uniqueID];
	},
	
	
	
	//Displayes the provided HTML as a tooltip
	//A typical use is to attach an onmouseenter handler to the target element such as
	//target.onomuseenter = "G2PopupManager.showTooltipHtml(this, '<b>Hello</b>', event);";
	showTooltipHtml : function(targetElement, html, e)
  {
	  if (!e)
		  e = window.event;
  	
	  var el = targetElement._tooltipElement;
	  if(el==null)
	  {
	    el = G2DOM.G2CreateElementFromHtml("<TABLE border='0' cellpadding='0' cellspacing='0'><TR><TD>"+html+"</TD></TR></TABLE>");
	    if(el.parentElement!=null)//TODO: Remove quick fix
	      el.parentElement.removeChild(el);
	  }
	  this.showTooltipStart(targetElement, el,e);
  },
  
  showTooltipText : function(targetElement, text, e)
  {
    if (!e)
		  e = window.event;
	  var html = "<div style='background-color: #fffacd;border-right: black 1px solid;border-top: black 1px solid;font-size: 8pt;border-left: black 1px solid;color: black;border-bottom: black 1px solid;font-family: Arial;padding:4px;'>"+text+"</div>";
	  this.showTooltipHtml(targetElement, html, e);
  },
  
  showTooltipStart : function(targetElement, el,e)
  {
    if(!this.allowTooltips)//Tooltips are disabled during postbacks
      return;
	  if (!e)
		  e = window.event;
	  
	  this.closeAllTooltips();
	  targetElement._tooltipElement = el;//Cache
	  
	  var posx = 0;
	  var posy = 0;
	  var winWidth = 1024;
	  var winHeight = 700;
  	 
  	if(el.parentElement == null)
  	  document.body.appendChild(el);
	  el.style.position="absolute";
	  offSet = 0
	  if (e.pageX || e.pageY)
	  {
		  winWidth = window.innerWidth;
		  winHeight = window.innerHeight;
		  posx = e.pageX;// + window.pageXOffset;
		  posy = e.pageY;// + window.pageYOffset;
	  }
	  else if (e.clientX || e.clientY)
	  {
		  winWidth = document.body.offsetWidth;
		  winHeight = document.body.offsetHeight;
		  posx = e.clientX + document.body.scrollLeft + document.documentElement.scrollLeft;
		  posy = e.clientY + document.body.scrollTop + document.documentElement.scrollTop;
	  }
	  
	  el.style.display = "block";
	  
	  //Fix flowing out of window
		var right = posx + el.offsetWidth;
	  if(right>winWidth)
	  {
	    var newPosx = (posx-el.offsetWidth);
	    if(newPosx>0)
	      posx = newPosx;
	  }
		var bottom = posy + el.offsetHeight;
	  if(bottom>winHeight)
	  {
	    newPosy = (posy-el.offsetHeight);
	    if(newPosy>0)
	      posy = newPosy; 
	  }
	  
	  posy++;		//Avoid some flickering in FireFox
	  el.style.pixelLeft = posx;
	  el.style.pixelTop = posy;
	  G2_VerifyAbsoluteElementNotCropped(el);
	  
	  targetElement.title = "";
	  this.tooltipTargets.push(targetElement);
	  
	  
	  
	  G2_BringToFront(el);
	  G2_AttachFrame(el);
	  el.enterToolTip = false;
	  	  
      if(targetElement.onmouseleave==null)
      {
          targetElement.onmouseleave=function(){
            setTimeout(function(){CloseIfNotInToolTip(targetElement, el)}, 500);
          };
          if (isMoz)
          {
            G2_AttachEvent(targetElement, "onmouseout",targetElement.onmouseleave); 
          }	    
	   }
	  if(el.onmouseenter==null)
      {
          el.onmouseenter=function(){el.enterToolTip = true;}; 
          if (isMoz)
          {
            G2_AttachEvent(el, "onmousein",el.onmouseenter); 
          }	      
	  }
	  if(el.onmouseleave==null)
      {
          el.onmouseleave=function(){
            G2PopupManager.closeTooltipFor(targetElement);
            el.enterToolTip = false;
          }; 
          if (isMoz)
          {
            G2_AttachEvent(el, "onmouseout",el.onmouseleave); 
          }	      
	  }
	  if(el.onmousedown==null)
      {
          el.onmousedown=function(){
           e.cancelBubble = true;
          };   
	  }
  },	
  closeAllTooltips : function()
  {
    while(this.tooltipTargets.length > 0)
    {
      var tt = this.tooltipTargets.pop();
      this.closeTooltipFor(tt);
    }
  },
  closeTooltipFor : function(targetElement)
	{
	  if(targetElement._tooltipElement !=null)
	    targetElement._tooltipElement.style.display="none";
	  G2_DetachFrame(targetElement._tooltipElement);
	},
	
	disableTooltips : function()
	{
	  this.allowTooltips = false;
	},
	
	enableTooltips : function()
	{
	  this.allowTooltips = true;
	}
	
};
G2_DeclareUtilInstance(G2PopupManager);
G2PopupManager.init();

G2FrameManager = 
{
	autoSizeThreadId : null,
	frames : {},
	registerFrame : function(frameOrId)
	{
		if(typeof(frameOrId)=="string")
			this.frames[frameOrId] = null;
		else
			this.frames[frameOrId.id] = frameOrId;
		if(this.autoSizeThreadId==null)
		{
			var caller = this;
			this.autoSizeThreadId = window.setInterval(
			function()
			{
				caller.autoSizeAllFrames();
			}, 300);
		}
	},
	unregisterFrame : function(frame)
	{
	    delete this.frames[frame.id];
	},
	autoSizeAllFrames : function()
	{
		for(var id in this.frames)
		{
			var frame = this.frames[id];
			if(frame==null)
			{
				frame = document.getElementById(id);
				this.frames[id] = frame;
			}
			frame.className = frame.className.replace("Hide", "");
			if(frame.autosize!="false" && frame.readyState=="complete")
			{
				try
				{
					if(frame.autosizeheight!="false")
					{
					  //  Following is the standard html page doctype definition as produced by Visual Studio with default settings
					  var doctypeString = '<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">';
					  var height, includesDTD = false;
					  //  Check if doctype is one of iframe document childs and retrieve the proper scrollHeight value
					  for(var i=0; i<frame.contentWindow.document.childNodes.length; i++)
					  {
					    if(frame.contentWindow.document.childNodes[i].text == doctypeString)
					    {
					      includesDTD = true;
					      break;
					    }
					  }
					  if(includesDTD) 
						  height = frame.contentWindow.document.documentElement.scrollHeight;
						else
						  height = frame.contentWindow.document.body.scrollHeight;
						if(frame.style.pixelHeight!=height)
							frame.style.height = height+"px";
					}
					if(frame.autosizewidth!="false")
					{
						var width = frame.contentWindow.document.documentElement.scrollWidth;
						if(frame.style.pixelWidth!=width)
							frame.style.width = width+"px";
					}
				}
				catch(err)
				{
					1;
					1;
				}
			}
		}
	}
}
G2_DeclareUtilInstance(G2FrameManager);



function G2_Print()
{
  window.print();
}


//
// Allows performing actions in the background
// action = function + arguments
// when the action occurs - 'this' keywork returns the background worker
//
G2BackgroundWorker = function(maxConcurrentActions)
{
	this.actions = [];
	this.concurrentActionsCount = 0;
	this.maxConcurrentActions = maxConcurrentActions || 1;
}

G2_DeclareClass(G2BackgroundWorker, "G2BackgroundWorker", null, 
{
	addAction : function(func, args, options)
	{
		this.actions.push({func:func,args:args,options:options});
		if(this.actions.length==1)
		{
			this._requestDoWorkIfNeeded();
		}
	},
	_requestDoWorkIfNeeded : function()
	{
		var caller = this;
		if(this.actions.length>0)
		{
			window.setTimeout(
			function()
			{
				caller.doWork();
			}, 0);
		}
		else if(this.concurrentActionsCount<=0)
		{
			this.onFinish();
		}
	},
	onActionStart : function(action)
	{
		this.concurrentActionsCount++;
	},
	onActionEnd : function()
	{
		if(this.concurrentActionsCount<=0)
			throw new Error("no current actions");
		this.concurrentActionsCount--;
		this._requestDoWorkIfNeeded();
	},
	doWork : function()
	{
		while(this.concurrentActionsCount<this.maxConcurrentActions && this.actions.length>0)
		{
			var action = this.actions.dequeue();
			this.onActionStart(action);
			this.currentAction = action;
			action.func.apply(this, action.args);
			if(action.options==null || !action.options.manualActionEndNotification)
				this.onActionEnd();
		}
	},
	onFinish : function()
	{
	}


});

//All (crappy) focus code taken from asp.net
function G2_FindFirstFocusableChild(control) 
{
  if (!control || !(control.tagName)) 
	{
    return null;
  }
  var tagName = control.tagName.toLowerCase();
  if (tagName == "undefined") 
	{
    return null;
  }
  var children = control.childNodes;
  if (children) 
	{
    for (var i = 0; i < children.length; i++) 
		{
      try 
			{
        if (WebForm_CanFocus(children[i])) 
				{
          return children[i];
        }
        else 
				{
          var focused = WebForm_FindFirstFocusableChild(children[i]);
          if (WebForm_CanFocus(focused)) 
					{
            return focused;
          }
				}
			} 
			catch (e) 
			{
			}
		}
	}
	return null;
}

function G2_AutoFocus(focusId) 
{
  var targetControl;
  if (__nonMSDOMBrowser) 
	{
    targetControl = document.getElementById(focusId);
  }
  else 
	{
    targetControl = document.all[focusId];
  }
  var focused = targetControl;
  if (targetControl && (!WebForm_CanFocus(targetControl)) ) 
	{
      focused = WebForm_FindFirstFocusableChild(targetControl);
  }
  if (focused) 
	{
    try 
		{
      focused.focus();
      if (__nonMSDOMBrowser) 
			{
        focused.scrollIntoView(false);
      }
      if (window.__smartNav) 
			{
        window.__smartNav.ae = focused.id;
      }
      return true;
    }
    catch (e) 
		{
			return false;
    }
  }
  else
		return false;
}
function G2_CanFocus(element) 
{
    if (!element || !(element.tagName)) return false;
    var tagName = element.tagName.toLowerCase();
    return (!(element.disabled) &&
            (!(element.type) || element.type.toLowerCase() != "hidden") &&
            WebForm_IsFocusableTag(tagName) &&
            WebForm_IsInVisibleContainer(element)
            );
}
function G2_IsFocusableTag(tagName) 
{
    return (tagName == "input" ||
            tagName == "textarea" ||
            tagName == "select" ||
            tagName == "button" ||
            tagName == "a");
}
function G2_IsInVisibleContainer(ctrl) 
{
  var current = ctrl;
  while((typeof(current) != "undefined") && (current != null)) 
	{
    if (current.disabled ||
        ( typeof(current.style) != "undefined" &&
        ( ( typeof(current.style.display) != "undefined" &&
            current.style.display == "none") ||
            ( typeof(current.style.visibility) != "undefined" &&
            current.style.visibility == "hidden") ) ) ) 
		{
      return false;
    }
    if (typeof(current.parentNode) != "undefined" &&
            current.parentNode != null &&
            current.parentNode != current &&
            current.parentNode.tagName.toLowerCase() != "body") 
		{
      current = current.parentNode;
    }
    else 
		{
      return true;
    }
  }
  return true;
}

function G2_ShowDisabler(show) 
{
  if(window.g2disabler == null)
  {
    if(show==false)
      return;
    var html = "<div id='g2disabler' class='g2Disabler' onclick='return false;' onmouseover='return false;' onmouseout='return false;'></div>";
    var disablerElement= G2DOM.G2CreateElementFromHtml(html, document);
    document.body.appendChild(disablerElement);
    window.g2disabler = disablerElement;
  }
  if(show)
  {
    window.g2disabler.style.pixelHeight = document.documentElement.scrollHeight;
		window.g2disabler.style.pixelWidth = Math.max(document.documentElement.offsetWidth-4, 0);
    window.g2disabler.style.display = '';
    window.g2disabler.lastDocumentOverflowX = document.documentElement.style.overflowX;
		document.documentElement.style.overflowX = 'hidden';
  }
  else
  {
	  window.setTimeout(function() {
    window.g2disabler.style.display = 'none';
    document.documentElement.style.overflowX = window.g2disabler.lastDocumentOverflowX;}, 1);
  }
}

function G2_DetectAcrobatReader() 
{
    var acrobat=new Object(); 
    acrobat.installed=false; 
    acrobat.version='0.0'; 
    if (navigator.plugins && navigator.plugins.length) { 
        for (x=0; x<navigator.plugins.length;x++) { 
              if (navigator.plugins[x].description.indexOf('Adobe Acrobat')!= -1) 
              { 
                    acrobat.version=parseFloat(navigator.plugins[x].description.split('Version ')[1]); 
                    if (acrobat.version.toString().length == 1) acrobat.version+='.0'; 
                          return acrobat; 
              } 
        } 
    } 
    else if (window.ActiveXObject) 
    { 
        for (x=2; x<10; x++) 
        { 
            try 
            { 
                oAcro=eval("new ActiveXObject('PDF.PdfCtrl."+x+"');"); 
                if (oAcro) 
                { 
                     acrobat.installed=true; 
                     acrobat.version=x+'.0'; 
                 } 
            } 
            catch(e) {} 
            } 
            try 
            { 
                oAcro4=new ActiveXObject('PDF.PdfCtrl.1'); 
                if (oAcro4) 
                { 
                      acrobat.installed=true; 
                      acrobat.version='4.0'; 
               } 
            } 
            catch(e) {} 
            try 
            { 
                oAcro7=new ActiveXObject('AcroPDF.PDF.1'); 
                if (oAcro7) 
                { 
                      acrobat.installed=true; 
                      acrobat.version='7.0'; 
                } 
            } 
            catch(e) {} 
        } 
        return acrobat; 
}
function CloseIfNotInToolTip(trgElm,curToolTip)
{
    if(!curToolTip.enterToolTip)
    {
        G2PopupManager.closeTooltipFor(trgElm);
    }
}
function SaveDocumentTitle(title)
{
    docTitle = title;
}

// Get the topest available window
function GetTopAvailableWindow()
{
	var win = window;
	var tmpElement;
	
	// For each window parent
	while((typeof(win.parent) != "undefined") && (win.parent != null) && (win != win.parent))
	{
	  // Try to access the window parent - else return the current window
		try
		{
			tmpElement = win.parent.document.createElement('DIV');
			win = win.parent;
		}
		catch(e)
		{
			return win;
		}
	}
	
	return win;
}

WebForm_FindFirstFocusableChild = G2_FindFirstFocusableChild;
WebForm_AutoFocus = G2_AutoFocus;
WebForm_CanFocus = G2_CanFocus;
WebForm_IsFocusableTag = G2_IsFocusableTag;
WebForm_IsInVisibleContainer = G2_IsInVisibleContainer;


/**********************************************************************
 *           G2 Cross-platform Javascript library                     *
 **********************************************************************/
Array.prototype.dequeue = function() {var r = this[0]; this.splice(0,1); return r;};
Array.prototype.FirstOrDefault = function(predicate)
{
	for(var i=0;i<this.length;i++)
	{
		var item = this[i];
		if(predicate(item))
			return item;
	}
	return null;
}
Array.prototype.ForEach = function(action)
{
	for(var i=0;i<this.length;i++)
	{
		var item = this[i];
		action(item);
	}
}
Array.prototype.RemoveItem = function(itemToRemove)
{
    for(var i=0;i<this.length;i++)
	{
		if (this[i] == itemToRemove)
		{
		    this.splice(i,1);
		    break;
		}
	}
}

var G2DOM = 
{
	GetChildElementById : function(element, id)
	{
		if(isIE)
		{
			var child = element.all[id];
			if(child==null)
				return null;
			if(child.length!=null)
				return child[0];
			return child;
		}
		else if(isMoz)
		{
			return this._GetChildElementById(element, id);
		}
		else
			throw new Error("not supported");
	},
	_GetChildElementById : function(element, id)
	{
		var child = element.firstChild;
		while(child!=null)
		{
			if(child.id==id)
				return child;
			var grandChild = this._GetChildElementById(child, id);
			if(grandChild!=null)
				return grandChild;
			child = child.nextSibling;
		}
		return null;
	},
	
	// This method gets a root element and a progid value and find the first child element with the progid specified
	// In case you got the whole progId path it is preffered to use the method 'findControl' below. It is much faster.
	// This method uses Depth-First-Search(DFS) recursively.
	GetChildByProgid_dfs : function(root, childProgid)
	{
		if (! root)
			return null;

		if (root.progid == childProgid)
			return root;

		var child = root.firstChild;
		while (child)
		{
			var res = this.GetChildByProgid(child, childProgid);
			if (res != null)
				return res;
			child = child.nextSibling;
		}
		
		return null;
	},
	

	// This method gets a root element and a progid value and find the first child element with the progid specified
	// This method uses Breadth-First-Search (BFS) instead of Depth-First-Search(DFS). It is therefore non-recursive.
	GetChildByProgid : function(root, childProgid)
	{
		if (! root)
			return null;
			
		if (root.progid == childProgid)
			return root;
			
		var queue = [root];		
		while (queue.length>0)
		{
			root = queue.dequeue();
			if (root.progid == childProgid)
				return root;
			var children = root.children;
			for (var i=0,j=children.length;i<j;i++)
				queue.push(children[i]);
		}	
				
		return null;
	},
	
	// This method gets a root element and a progid value and find the first parent element with the progid specified
	GetParentByProgid : function(root, childProgid)
	{
		while(root && root.progid != childProgid)
		{
			root = root.parentElement;
		}
		
		return root;
	},

	// gets the given object position	
	findPos : function(obj)
	{
		var curleft = 0;
		var curtop = 0;
		if (obj.offsetParent)
		{
			curleft = obj.offsetLeft;
			curtop = obj.offsetTop;
			while (obj = obj.offsetParent)
			{
				curleft += obj.offsetLeft;
				curtop += obj.offsetTop;
					
		    // taking into account scrooling with in overflow scroll elements
		    if(obj.tagName != 'HTML' && obj.scrollTop != null)
			    curtop -= obj.scrollTop;
			}
		}
		return [curleft,curtop];
	},
		
	// Create a covering DIV for a modal effect.
	// The input parameters:
	// side - left, top, right or bottom
	// tableId - the modal element or its id
	// errorMsg - message to shown when clicking on the div. optional
	CreateCoverDiv : function(side,tableId,errorMsg)
	{
		// validate modal element
		if(tableId == null)
			return;

		var tbl = tableId;
		if(typeof(tableId) == "string")
			tbl = $(tableId);

		var arr = this.findPos(tbl)	
		var docHeight,docWidth;
		var coverDiv = document.createElement('DIV');
		var div;
		if (side == "left")
		{
				div = $('leftCoverDiv');
			if (div!=null)
				return div;
			docHeight = document.documentElement.scrollHeight;		
			docWidth = arr[0];
			coverDiv.id = "leftCoverDiv";
		}
		else if (side == "top")
		{
				div = $('topCoverDiv');
			if (div!=null)
				return div;
			docWidth = document.documentElement.scrollWidth;
			docHeight = arr[1];	
			coverDiv.id = "topCoverDiv";
		}			
		else if (side == "right")
		{
				div = $('rightCoverDiv');
			if (div!=null)
				return div;
			docWidth = document.documentElement.scrollWidth-tbl.offsetWidth;
			docHeight = tbl.offsetHeight;
			coverDiv.id = "rightCoverDiv";
		}			
		else if(side == "bottom")
		{
				div = $('bottomCoverDiv');
			if (div!=null)
				return div;
			docWidth = document.documentElement.scrollWidth;
			docHeight = window.document.documentElement.scrollHeight-(arr[1]+tbl.offsetHeight);
			coverDiv.id = "bottomCoverDiv";
		}			
		coverDiv.className = "CoverDiv";
		if (side == "left" || side == "top")
		{
				coverDiv.style.left = "0px";
				coverDiv.style.top = "0px";
		}
		else if (side == "right")
		{
				coverDiv.style.left = arr[0]+tbl.offsetWidth+"px";
				coverDiv.style.top = arr[1]+"px";
		}
		else if (side == "bottom")
		{
				coverDiv.style.left = "0px";
				coverDiv.style.top = arr[1]+tbl.offsetHeight+2+"px";
		}
		coverDiv.style.height = docHeight+"px";
		coverDiv.style.width = docWidth+"px";	
		coverDiv.style.position="absolute";			
		coverDiv.onclick = function()
		{
			if(errorMsg)
				alert(errorMsg);
			else
				alert("You are in Edit Mode, Click Done to save or Cancel to exit");
		};
		return coverDiv;
	},

	//Transfers the custom attributes from the element to its properties (they are the same in IE, not in FF)
	G2TransferAttributes : function(elem)
	{
		if (isIE || elem==null || elem.attributesTransferred) //IE is nice enough
			return;
		elem.attributesTransferred = true;
		for (var atnum in elem.attributes)
		{
			var atNode = elem.attributes[atnum];
			var atname = atNode.nodeName;
			var atvalue = atNode.nodeValue;
			if (typeof(elem[atname])=="undefined")
				elem[atname] = atvalue;
		}	
	},

	G2GetSelection : function()
	{
		return (window.getSelection || (document.getSelection && document.getSelection()) || document.selection);
	},

	G2GetNextChild : function ( n )
	{
		if (isIE)
			return n.nextSibling;

		do
		{
			n	 = n.nextSibling;
		} 
		while (n!=null && n.nodeType == Node.TEXT_NODE);

		return n;
	},
	G2CreateElementFromHtml : function(html, doc)
	{
	  if(doc==null)
	    doc = document;
		var tagName = html.substr(html.search("<")+1, 2).toUpperCase();
		var div = doc.createElement('div');
		if(tagName=="TR")		
		{
			div.innerHTML = "<table><tbody>"+html+"</tbody></table>";
			var newRow = div.firstChild.firstChild.firstChild;
			newRow.parentElement.removeChild(newRow);
			return newRow;
		}
		else if(tagName=="TD")
		{
			var div = doc.createElement("div");
			div.innerHTML = "<table><tr>"+outerHTML+"</tr></table>";
			var cell = div.firstChild.firstChild.firstChild.firstChild;
			return cell;
		}
		else
		{
			div.innerHTML = html;
			return div.children[0]; //FF
		}
	},

	//Replaces a node's outerHTML (Already Implemented in IE, not in FF)
	//TODO: Check if this is needed or if the outerHTML setter works in FF 2.0
	G2ReplaceOuterHTML : function(obj,outerHTML)
	{
		if(isIE)
		{
			//added by dan-el - the simple method doesn't work for TR's.
			if(obj.tagName=="TR")
			{
				var tempDiv = document.createElement('div');
				tempDiv.innerHTML = "<table>"+outerHTML+"</table>";
				var newRow = tempDiv.firstChild.firstChild.firstChild;
				var row = obj;
				var table = obj.parentNode;
				table.replaceChild(newRow, row);
			}
			else if(obj.tagName=="TD")
			{
				var div = document.createElement("div");
				div.innerHTML = "<table><tr>"+outerHTML+"</tr></table>";
				var cell = div.firstChild.firstChild.firstChild.firstChild;
				obj.replaceNode(cell);
			}
			else
			{
				obj.outerHTML = outerHTML;
//				var div = document.createElement("div");
//				div.innerHTML = outerHTML;
//				if (div.firstChild)
//					obj.replaceNode(div.firstChild);
			}
		}
		else //this method caused problems with image caching in Explorer
		{
			obj.outerHTML = outerHTML; //Changed by Alon
			/*var tempDiv = document.createElement('div');
			tempDiv.innerHTML = outerHTML;
			obj.replaceNode(tempDiv.firstChild);*/
		}
	},

	//Firefox stores attributes in a different manner than IE
	G2GetAttribute : function (obj,attributeName)
	{	
		if (isIE)
			return obj[attributeName];
		else if (obj!=null && obj.hasAttribute!=null && obj.hasAttribute(attributeName.toLowerCase()))
			return obj.attributes[attributeName.toLowerCase()].nodeValue;
		else 
		{
			var t = obj.attributes[attributeName.toLowerCase()];
			if (t!=null)
				return t.nodeValue;				
			else
			t = obj[attributeName.toLowerCase()] || obj[attributeName];
			return t;
		}
	},

	G2SetAttribute : function (obj,attributeName,val)
	{
		if (isIE)
			obj[attributeName] = val;
		else
			obj.attributes[attributeName.toLowerCase()].nodeValue = val;
	},

	G2CreateElement : function(t)
	{
		if (isIE || t.charAt(0)!="<")
			return document.createElement(t); //  e.g. document.createElement("DIV")
			
		var tempDiv = document.createElement("DIV");
		tempDiv.innerHTML = t;
		return tempDiv.childNodes[0];
	},

	// This method return row.rowIndex
	GetRowIndex : function(row)
	{
		var body = row.parentElement;
		if (!body)
			return -1;
		var currRow = body.firstChild;
		var index = 0;
		while(currRow)
		{
			if (currRow == row)
				return index;
			index++;
			currRow = currRow.nextSibling;
		}
		return -1;
	},

	// This methods returns a row by its index by going throw the table rowafter row 
	// instead of using the table indexing
	GetRowByIndex : function(table, rowIndex)
	{	
		var row = table.firstChild;
		if (! row)
			return null;
			
		while (row && row.tagName != "TR")
			row = row.firstChild;
			
		if (! row)
			return null;
		
		if (rowIndex == 0)
			return row;
		
		for(var i = 0; i < rowIndex; i++)
		{
			row = row.nextSibling;
			if (!row)
				return null;
		}
		return row;
	},

	// Gets a table and return the number of rows
	GetRowsLength : function(table)
	{
		var row = table.firstChild;
		if (! row)
			return 0;
			
		while (row && row.tagName != "TR")
			row = row.firstChild;
		if (! row)
			return 0;
			
		var count = 0;
		while(row)
		{
			row = row.nextSibling;
			count++;
		}
		return count;
	},
	
	GetCellByIndex : function(row, cellIndex)
	{	
		var cell = row.firstChild;
		if (! cell)
			return null;
		
		if (cellIndex == 0)
			return cell;
		
		for(var i = 0; i < cellIndex; i++)
		{
			cell = cell.nextSibling;
			if (!cell)
				return null;
		}
		return cell;
	},
	
	// Gets a row and return the number of cells
	GetCellsLength : function(row)
	{
		var cell = row.firstChild;
		if (! cell)
			return 0;
			
		var count = 0;
		while(cell)
		{
			cell = cell.nextSibling;
			count++;
		}
		return count;
	},
    G2DisableSelects : function()
    {
         if (!IE6)
            return;
            
        selects = document.getElementsByTagName('SELECT');
        for (var i = 0; i < selects.length; i++)
        {
            sel = selects[i];
            if (sel.isDisabled == false)
            {
              sel.disabled = true;
              sel.wasGenerallyDisabled  = true; 
            }
         }
          
    },
    G2EnableSelects : function()
    {
       if (!IE6)
            return;
            
        selects = document.getElementsByTagName('SELECT');
        for (var i = 0; i < selects.length; i++)
        {
            sel = selects[i];
            if (sel.isDisabled && sel.wasGenerallyDisabled)
            {
                sel.disabled = false;
                sel.wasGenerallyDisabled = false;
             }
         }
    },
    G2InsertRowToTable : function(table, index)
    {
        if (index == null)
            index = table.rows.length;
        return table.insertRow(index);
    },
    
    G2InsertCellToRow : function (row, index)
    {
        if (index == null)
            index = row.cells.length;
        return row.insertCell(index);
    },
    
    G2RemoveNode : function (elem)
    {
        elem.parentNode.removeChild(elem);
    },
    
    G2Focus : function (elem)
    {
			try{
				elem.focus();
			}
			catch(e){
				//do nothing- error when pressing the widget of combo is unclear but cause no problem. 
				// the menu is displayed as usual.
			}
    },
    
    G2HTMLEncode : function (text)
    {
	    if ( !text )
		    return '' ;

	    text = text.replace( /&/g, '&amp;' ) ;
	    text = text.replace( /</g, '&lt;' ) ;
	    text = text.replace( />/g, '&gt;' ) ;
	    return text ;
    },
    
		// Set the flash elements in the iframe to transparent
		SetFlashElementsTransparent : function(iframe)
		{
			if(isMoz)
			{
				var objects = iframe.Document.getElementsByTagName('embed');  
				for (var i = 0; i < objects.length; i++) 
				{   
					var newObject = objects[i].cloneNode(true); 
					newObject.setAttribute('wmode', 'transparent');           
					objects[i].parentNode.replaceChild(newObject, objects[i]);    
				}
			}
			else
			{
				var elementToAppend = iframe.Document.createElement('param');    
				elementToAppend.setAttribute('name', 'wmode');    
				elementToAppend.setAttribute('value', 'transparent');    
				var objects = iframe.Document.getElementsByTagName('OBJECT');    
				for (var i = 0; i < objects.length; i++) 
				{        
					var newObject = objects[i].cloneNode(true);        
					elementToAppend = elementToAppend.cloneNode(true);        
					newObject.appendChild(elementToAppend);        
					objects[i].parentNode.replaceChild(newObject, objects[i]);    
				}
			}
    }
  
}

G2_DeclareUtilInstance(G2DOM);

//the following script adds document.getElementById if it is not present
if(document.all && !document.getElementById) 
{
	document.getElementById = function(id) 
	{
		return document.all[id];
	}
}


/**********************************************************************
 *           G2 Event handling                                        *
 *     portions taken from the Prototype library version 1.4.0        *
 **********************************************************************/

G2_DeclareFunctions(
{
	G2_AttachEventWithCaller : function(element, eventName, handler, caller)
	{
		element.attachEvent(eventName, G2.GetDelegate(caller, handler));
	},
	G2_DetachEventWithCaller : function(element, eventName, handler, caller)
	{
		element.detachEvent(eventName, G2.GetDelegate(caller, handler));
	},


	G2_FireEvent : function(target, eventName, eventArgs)
	{
		if(isIE)
		{
			return target.fireEvent(eventName, eventArgs);
		}
		else
		{
			var handler = target[eventName];
			if (handler!=null)
			{
				if (typeof(handler)=="function")
					handler();
				else eval(handler);
			}
			else
				throw new Error("not supported");
		}
	},

	// This method wraps an event handler, to achieve two goals:
	// 1. When the method executes, its 'this' context will be the actual object (who 'owns' the function)
	// 2. Cross-platform event handling:
	//    In IE, the current event that is being process is stored in window.event
	//    In Mozilla (and FireFox), the event object is passed as an argument to the event handler
	G2_PrepareEvent : function(newContext,method)
	{
		if (method.preparedEvent && method.preparedEvent!=null)
		{
			return method.preparedEvent;
		}
		method.preparedEvent = function(event)
		{
			if (event==null)
				event = window.event;
			return method.call(newContext,event);
		}
		
		return method.preparedEvent;
	},

	// Attaches an event handler to the target, as a response to that event
	// The handler should be a function that receives a single argument, named 'event'.
	// It should NOT use window.event, only the supplied event.
	G2_AttachEvent : function(target, eventName, handler, capture)
	{
		if (eventName.substr(0,2)=="on")
			eventName = eventName.substring(2);
		
		//Note: Capture is only supported in FireFox
		if (!capture)
			capture = false;
		
		if(isIE)
		{
			target.attachEvent('on'+eventName, G2_PrepareEvent(target,handler));
		}
		else if (target.addEventListener!=null)
		{		
				target.addEventListener(eventName,G2_PrepareEvent(target,handler),capture);
		} 
		else
			throw new Error("not supported");
	},


	G2_DetachEvent : function(target,eventName, handler, capture)
	{
		if (eventName.substr(0,2)=="on")
			eventName = eventName.substring(2);
		
		//Note: Capture is only supported in FireFox
		if (!capture)
			capture = false;
		
		if (isIE) 
		{
				target.detachEvent('on' + eventName, G2_PrepareEvent(target,handler));
		}
		else if (target.removeEventListener!=null)
		{
				target.removeEventListener(eventName, G2_PrepareEvent(target,handler), capture);
		} 
		else 
			throw new Error("not supported");
	},
	G2StopEvent : function(event)
	{
		G2Event.stop(event);
	},
		
	// Get child element in a given element by its id
	G2_FindChildControlById : function(element, id)
	{
		if(String.EndsWith(element.id, id))
			return element;
		var child = element.firstChild;
		while(child!=null)
		{
			var found = G2_FindChildControlById(child, id);
			if(found!=null)
				return found;
			child=child.nextSibling;
		}
		return null;
	},
	
	// Get the first child element in a given element with a specified tagName
	G2_FindChildControlByTagName : function(element, tagName)
	{
		if(! element)
			return null;
		if (element.tagName)
			if(element.tagName.toLowerCase() == tagName.toLowerCase())
				return element;
		var child = element.firstChild;
		while(child!=null)
		{
			var found = G2_FindChildControlByTagName(child, tagName);
			if(found!=null)
				return found;
			child=child.nextSibling;
		}
		return null;
	},

	///
	///Recursivly searches an element from the current control and up that has a certain tag name
	///
	G2_GetParentElementByTagName : function(control, tagName)
	{	
		tagName = tagName.toUpperCase();
		return _G2_GetParentElementByTagName(control, tagName);
	},
	_G2_GetParentElementByTagName : function(control, tagName)
	{	
		if(control==null)
			return null;
		if(control.tagName==tagName) //TODO: Compare case insensitive
			return control;
		control = control.parentElement;
		return _G2_GetParentElementByTagName(control, tagName);
	},

	//returns an array of all the nodes under node with progid=parentProgId that have the 
	//specified attribute name and value 
	findControlsByAttribute : function(node, parentProgId, attributeName, attributeValue)
	{
		
		var pred = function(el)
		{
			if(G2DOM.G2GetAttribute(el, "progid")==parentProgId)
					return el;
		}
		var testAttribute = function(node)
		{
			if(G2DOM.G2GetAttribute(node, attributeName)==attributeValue)
					return node;
		}
		var curNode = searchUp(node, pred);
		if(curNode == null)
			return null;

		var childrenArray = new Array();
		
		collectChildrenByAttribute(curNode, testAttribute, childrenArray);
		return childrenArray; 
	},
	
	collectChildrenByAttribute : function (obj, predicate, childrenArray)
	{
		if (obj==null)
			obj = this;
			
		if (obj.childNodes.length==0)
			return childrenArray;
			
		var c = obj.firstChild;
		
		while(c!=null)
		{
			collectChildrenByAttribute(c,predicate, childrenArray);
			if (c.nodeType == 1 && predicate(c))
				childrenArray.push(c);
			c = c.nextSibling;
		}
	},
	
		
	//Finds an element by progid
	//Usage: provide a start node and a path seperated by dots, i.e. findControl(el, 'div1.panel2.button3');
	//       in this example, a node with progid div will be searched UPWARDS from el
	//       Then a div1 child element with progid 'panel2'will be searched DOWN.
	//       Then a panel2 child element with progid 'button3'will be searched DOWN. 
	//Returns: the first element with the last progid in the path that matches
	findControl : function(node, progIdpath)
	{
		var tokens = progIdpath.split('.');
		if(tokens.length==0)
			return null;
		var progid=tokens[0];
		tokens.splice(0,1);//Remove first token
	  
		var pred = function(el)
		{
			if(G2DOM.G2GetAttribute(el, "progid")==progid)
					return el;
		}
		var curNode = searchUp(node, pred);
		if(curNode == null)
			return null;
		if(tokens.length==0)
			return curNode;
		var newPath = tokens.join('.');
		return _findChildControl(curNode, newPath); 
	},

	_findChildControl : function(node, progIdpath)
	{
		var curNode = node;
		var tokens = progIdpath.split('.');
		if(tokens.length==0)
			return curNode;
		
		var tokensLength = tokens.length;
		for(var i=0; i<tokensLength; i++)
		{
			var progid=tokens[i];
			var pred = function(el)
			{
				if(G2DOM.G2GetAttribute(el, "progid")==progid)
					return el;
			}
			curNode = searchDown(curNode, pred);  
			if(curNode==null)
				return null;
		}
		return curNode;
	},

	searchUp : function(node, predicate)
	{
		while(node!=null)
		{
			if(predicate(node))
				return node;
			node = node.parentElement;
		}  
		return null;
	},
	searchDown : function(node, predicate)
	{
		return _searchDown(node, predicate);
	},
	_searchDown : function(node, predicate)
	{
		if(predicate(node))
				return node;
		node = node.firstChild; 
		if (node!=null && node.nodeType != 1)
			node = G2DOM.G2GetNextChild(node);
		while(node!=null)
		{
			var n = _searchDown(node, predicate);
			if(n!=null)
				return n;
			node = G2DOM.G2GetNextChild(node);
		}  
		return null;
	}
	
});

var G2Event = {
  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_SPECIAL_COPY: 17,

	//Returns the target(FF)/source(IE) element - which is the event's context
	//Usage:  Event.element( e )
  element: function(event) {
		if (event==null)
			event = window.event;
    return event.target || event.srcElement;
  },

	//Returns true if the click was a left mouse click
	//Usage:  Event.isLeftClick( e )
  isLeftClick: function(event) {
		if (event==null)
			event = window.event;
    return (((event.which) && (event.which == 1)) ||
            ((event.button) && (event.button == 1)));
  },
	
	//Returns the cursor X coordinate (relative to the page)
	//Usage:  Event.pointerX( e )
  pointerX: function(event) {
		if (event==null)
			event = window.event;
    return event.pageX || (event.clientX +
      (document.documentElement.scrollLeft || document.body.scrollLeft));
  },

	//Returns the cursor Y coordinate (relative to the page)
	//Usage:  Event.pointerY( e )
  pointerY: function(event) {
		if (event==null)
			event = window.event;
    return event.pageY || (event.clientY +
      (document.documentElement.scrollTop || document.body.scrollTop));
  },

	//Stops the event propagation
	//Usage:  Event.stop( e )
  stop: function(event) {
		if (event==null)
			event = window.event;
    if (event.preventDefault) {
      event.preventDefault();
      event.stopPropagation();
    } else {
      event.returnValue = false;
      event.cancelBubble = true;
    }
  },

  // Finds the first node with the given tagName, starting from the
  // node the event was triggered on; traverses the DOM upwards
  findElement: function(event, tagName) {
		if (event==null)
			event = window.event;
    var element = Event.element(event);
    while (element.parentNode && (!element.tagName ||
        (element.tagName.toUpperCase() != tagName.toUpperCase())))
      element = element.parentNode;
    return element;
  }/*,

  observers: false,

  _observeAndCache: function(element, name, observer, useCapture) {
    if (!this.observers) this.observers = [];
    if (element.addEventListener) {
      this.observers.push([element, name, observer, useCapture]);
      element.addEventListener(name, observer, useCapture);
    } else if (element.attachEvent) {
      this.observers.push([element, name, observer, useCapture]);
      element.attachEvent('on' + name, observer);
    }
  },

  unloadCache: function() {
    if (!Event.observers) return;
    for (var i = 0; i < Event.observers.length; i++) {
      Event.stopObserving.apply(this, Event.observers[i]);
      Event.observers[i][0] = null;
    }
    Event.observers = false;
  },

  observe: function(element, name, observer, useCapture) {
    var element = $(element);
    useCapture = useCapture || false;

    if (name == 'keypress' &&
        (navigator.appVersion.match(/Konqueror|Safari|KHTML/)
        || element.attachEvent))
      name = 'keydown';

    this._observeAndCache(element, name, observer, useCapture);
  },

  stopObserving: function(element, name, observer, useCapture) {
    var element = $(element);
    useCapture = useCapture || false;

    if (name == 'keypress' &&
        (navigator.appVersion.match(/Konqueror|Safari|KHTML/)
        || element.detachEvent))
      name = 'keydown';

    if (element.removeEventListener) {
      element.removeEventListener(name, observer, useCapture);
    } else if (element.detachEvent) {
      element.detachEvent('on' + name, observer);
    }
  }*/
};




//Add Debug.writeln support for Firefox
//In order to enable logging:
// 1. open firefox
// 2. open about:config
// 3. right-click and New->String
// 4. Name the new entry "browser.dom.window.dump.enabled"
// 5. Set its value to true
// 6. Open firefox with the -console parameter (it might complain, but it works).
// For additional information, contact Alon.
// 
// Note: Console is disabled by default. On production systems no change needs to be done.
if (typeof(Debug)=="undefined")
	Debug = {writeln:function(txt){window.dump(txt+"\n");}};
	


/**********************************************************************
 *           G2 Firefox HTMLElement extension                         *
 **********************************************************************/

if(!document.documentElement.outerHTML)
{

    HTMLElement.prototype.getAttributes = function(){
       var attStr = "";
       if(this && this.attributes.length > 0){
          for(a = 0; a < this.attributes.length; a ++){
             attStr += " " + this.attributes.item(a).nodeName + "=\"";
             attStr += this.attributes.item(a).nodeValue + "\"";
          }
       }
       return attStr;
    }

    HTMLElement.prototype.getInsideNodes = function(){
       if(this){
          var cNodesStr = "", i = 0;
          var iEmpty = /^(img|embed|input|br|hr|bgsound)$/i;
          var cNodes = this.childNodes;
          for(i = 0; i < cNodes.length; i ++){
             switch(cNodes.item(i).nodeType){
                 case 1 :
                    cNodesStr += "<" + cNodes.item(i).nodeName.toLowerCase();
                    if(cNodes.item(i).attributes.length > 0){
                       cNodesStr += cNodes.item(i).getAttributes();
                    }
                    cNodesStr += (cNodes.item(i).nodeName.match(iEmpty))? "" : ">";
                    if(cNodes.item(i).childNodes.length > 0){
                       cNodesStr += cNodes.item(i).getInsideNodes();
                    }
                    if(cNodes.item(i).nodeName.match(iEmpty)){
                       cNodesStr += " />";
                    } else {
                       cNodesStr += "</" + cNodes.item(i).nodeName.toLowerCase() + ">";
                    }
                    break;
                 case 3 :
                    cNodesStr += cNodes.item(i).nodeValue;
                    break;
                 case 8 :
                    cNodesStr += "<!--" + cNodes.item(i).nodeValue + "-->";
                    break;
             }
          }
          return cNodesStr;
       }
    }

    G2MozGetOuterHTML = function(){
       var strOuter = "";
       var iEmpty = /^(img|embed|input|br|hr|bgsound)$/i;
       switch(this.nodeType){
          case 1 :
             strOuter += "<" + this.nodeName.toLowerCase();
             strOuter += this.getAttributes();
             if(this.nodeName.match(iEmpty)){
                 strOuter += " />";
             } else {
                 strOuter += ">" + this.getInsideNodes();
                 strOuter += "</" + this.nodeName.toLowerCase() + ">";
             }
             break;
          case 3 :
             strOuter += this.nodeValue;
             break;
          case 8 :
             cNodesStr += "<!--" + this.nodeValue + "-->";
             break;
       }
       return strOuter;
    }

    G2MozSetOuterHTML = function(str){
       var iRange = document.createRange();
       iRange.setStartBefore(this);
       var strFragment = iRange.createContextualFragment(str);
       var sRangeNode = iRange.startContainer;
       iRange.insertNode(strFragment);
       sRangeNode.removeChild(this);
    }
    
    //Returns the object's document
		G2GetDocument = function (obj)
		{
			if (obj == null)
				obj = this;
			return obj.ownerDocument;
		}

		// Artificially get the 'Children' array for the given node.
		// Added as a getter to the Node class in FF
		G2GetChildren = function (obj)
		{
			if (obj==null)
				obj = this;
				
			var childrenArray = new Array();
			if (obj.childNodes.length==0)
				return childrenArray;
				
			var c = obj.firstChild;
			while(c!=null)
			{
				if (c.nodeType != Node.TEXT_NODE)
					childrenArray.push(c);
				c = c.nextSibling;
			}
			
			childrenArray.namedItem = function(name)
			{
				for (var i=0;i<this.length;i++)
				{
					var node = this[i];
					if (node.id == name)
						return node;
				}
				return null;
			}
			
			return childrenArray;
		}
		
		G2GetTagName = function(obj)
		{
			if (obj==null)
				obj = this;
			return obj.nodeName;
		}

		function G2GetParent(obj)
		{	
			if (obj==null)
				obj = this;
			return obj.parentNode;
		}
		
		function G2GetCurrentStyle(obj)
		{
			if (obj==null)
				obj = this;
			return window.getComputedStyle(obj,null);
		}
		
		function G2GetInnerText(obj)
		{
			if (obj==null)
					obj = this;
			return obj.textContent;
		}
		
		function G2SetInnerText(txt)
		{
			this.innerHTML = txt;
		}
		
		function G2ContainsChild(c)
		{
			var chlrn = this.children;
			for (var i=0,j=chlrn.length;i<j;i++)
				if (chlrn[i]==c)
					return true;
			return false;
		}
		
		function G2GetContentDocument()
		{
			return this.contentDocument;
		}
		
		function G2MozGetParentWindow()
		{
			return this.defaultView;
		}
		
		HTMLElement.prototype.contains = G2ContainsChild;
		
		//Implement insertAdjacentElement, insertAdjacentText and insertAdjacentHTML
		HTMLElement.prototype.insertAdjacentElement = function(where,parsedNode)
		{
			switch (where)
			{
				case "beforeBegin":
					this.parentNode.insertBefore(parsedNode,this)
					break;
				case "afterBegin":
					this.insertBefore(parsedNode,this.firstChild);
					break;
				case "beforeEnd":
					this.appendChild(parsedNode);
					break;
				case "afterEnd":
					if (this.nextSibling)
						this.parentNode.insertBefore(parsedNode,this.nextSibling);
					else 
						this.parentNode.appendChild(parsedNode);
					break;
			}
		}
		
		HTMLElement.prototype.insertAdjacentHTML = function(where,htmlStr)
		{
			var r = this.ownerDocument.createRange();
			r.setStartBefore(this);
			var parsedHTML = r.createContextualFragment(htmlStr);
			this.insertAdjacentElement(where,parsedHTML)
		}
		
		HTMLElement.prototype.insertAdjacentText = function(where,txtStr)
		{
			var parsedText = document.createTextNode(txtStr)
			this.insertAdjacentElement(where,parsedText)
		}
		var lastGivenID = 1000;			
		function G2GetElementUniqueID ()
		{
			if (this._uniqueID) //already defined
				return this._uniqueID;
			//Generate using counter
			this._uniqueID = lastGivenID;
			lastGivenID++;
			return this._uniqueID;
		}	
		
		function G2GetEventSourceElement() 
		{
			var node = this.target;
			while (node.nodeType != 1) node = node.parentNode;
			return node;
		}
		
		function G2GetProgId()
		{
			if (this.hasAttribute("progid"))
				return this.attributes["progid"].nodeValue;
		}
		
		HTMLElement.prototype.attachEvent = function(eventName, handler, capture) //Simulate AttachEvent on Mozilla
	  {
	    if (eventName.substr(0,2)=="on")
		  	eventName = eventName.substring(2);		  
		  if (!capture)
		    capture = false;
	    this.addEventListener(eventName,handler,capture);
	  }
	  
	  HTMLElement.prototype.detachEvent = function(eventName, handler, capture) //Simulate DetachEvent on Mozilla
	  {
	    if (eventName.substr(0,2)=="on")
		  	eventName = eventName.substring(2);		  
		  if (!capture)
		    capture = false;
	    this.removeEventListener(eventName,handler,capture);
	  }
		
		function defineStyleProperties(names)
		{
			for(var i=0;i<names.length;i++)
			{
				var shortName = names[i];
				var pixelName = "pixel"+shortName.substring(0,1).toUpperCase()+shortName.substring(1);
				defineStyleProperty(shortName,pixelName);
			}
		}

		function defineStyleProperty(shortName,pixelName)
		{
			CSSStyleDeclaration.prototype.__defineGetter__(pixelName,function(){return parseInt(this[shortName])});
			CSSStyleDeclaration.prototype.__defineSetter__(pixelName,function(v){this[shortName]=v+"px";});
		}
		
		
		defineStyleProperties(["width","height","left","top"]);
		
		/*function Selection(doc)
		{		
		  this._doc = doc;
		}
		Selection.prototype.createRange = function(element)
		{
		  debugger;
		  var sel = window.getSelection();		  
		  var range = null;
		  if (sel.rangeCount==0)
		  {
		    if (element!=null)
		    {
 		      range = document.createRange();
 		      range.selectNodeContents(element);
 		      //range.setStart(element, 0);
 		      //var len = (element.nodeType==1 && element.tagName=="INPUT") ? element.value.length : element.innerText.length;
          //range.setEnd(element,0);
          //range.expand
		      sel.addRange(range);
		    }
		  }
		  else range = sel.getRangeAt(0);
		  var rng = new G2MozRange(range);
		  return rng;
		}
    function G2GetDocumentSelection()
		{
		  if (this._emulatedSelectionObject==null)
		    this._emulatedSelectionObject = new Selection(this);
		  return this._emulatedSelectionObject;
		}
		
		function G2MozRange(rng)
		{
		  this._range = rng;
		}
		function G2MozRange_GetText()
		{
		  return this._range.toString();
		}
		function G2MozRange_SetText(value)
		{
		  //this.commonAncestorContainer.innerText = value;
		  debugger;
		  var lastElement = this._range.endContainer;
		  if (lastElement==null)
		    debugger;
		  if (lastElement.nodeType==1)
		  {
		    if (lastElement.tagName=="INPUT")
		    {
		      lastElement.value += value;
		    }
		    else
		      lastElement.innerText += value;
		  }
		  else if (lastElement.nodeType==3)
		  {
		    lastElement.nodeValue += value;
		  }
		    
		}
		G2MozRange.prototype.__defineGetter__("text",G2MozRange_GetText);
		G2MozRange.prototype.__defineSetter__("text",G2MozRange_SetText);
		*/
		//Fix for firefox BACK
		window.addEventListener("pageshow",function(e){if(e.persisted) {window.location.href = window.location.href;}},false);
    
    HTMLDocument.prototype.__defineGetter__("parentWindow",G2MozGetParentWindow);
    //HTMLDocument.prototype.__defineGetter__("selection",G2GetDocumentSelection);
    HTMLElement.prototype.__defineGetter__("progid",G2GetProgId);
    HTMLElement.prototype.__defineGetter__("outerHTML",G2MozGetOuterHTML);
		HTMLElement.prototype.__defineSetter__("outerHTML",G2MozSetOuterHTML);
		HTMLElement.prototype.__defineGetter__("innerText",G2GetInnerText);
		HTMLElement.prototype.__defineSetter__("innerText",G2SetInnerText);
		HTMLElement.prototype.__defineGetter__("children",G2GetChildren);
		HTMLElement.prototype.__defineGetter__("document",G2GetDocument);
		HTMLElement.prototype.__defineGetter__("tagName",G2GetTagName);
		HTMLElement.prototype.__defineGetter__("parentElement",G2GetParent);
		HTMLElement.prototype.__defineGetter__("currentStyle",G2GetCurrentStyle);
		HTMLElement.prototype.__defineGetter__("uniqueID",G2GetElementUniqueID);
		HTMLIFrameElement.prototype.__defineGetter__("Document",G2GetContentDocument);
		Event.prototype.__defineGetter__("srcElement", G2GetEventSourceElement);
		
		
}
// returns true if the string 's' ends with the string 'endsWith'
String.EndsWith = function(s, endsWith)
{
	if(s==null)
		return endsWith==null;
	return s.substr(s.length-endsWith.length, endsWith.length)==endsWith;
}


//this function gets a control
//and disables/enables it and all its children recursively
SetControlDisability = function(control, disable)
{
	if(control == null)
		return;
	if (control.supportdisabledcss == "true")
	{
		control.disabled = disable;
		//we want the main css class to be standing alone
		//so when disabling, replace css class by disabled css class
		//when enabling if there are other classes, just remove disabled
		if (disable || control.className == control.disabledcssclass)
			G2_ReplaceCssClass(control, control.cssclass, control.disabledcssclass, disable);
		else
			G2_RemoveCssClass(control, control.disabledcssclass);
	}
	//we don't want to replace the initial css class but to add the disable css class
	else if (control.supportdefauldisabledtcss == "true") 
	{
		control.disabled = disable;
		if (disable)
			G2_AddCssClass(control, control.disabledcssclass);
		else
			G2_RemoveCssClass(control, control.disabledcssclass);
	}
	G2_VerifyControlInitialized(control);
	if(typeof(control.setEnabled)=="function")
		control.setEnabled(!disable);
	else
	{
		control.disabled = disable;
		SetControlChildrenDisability(control, disable);
	}
}

SetControlChildrenDisability = function(control, disable)
{
		if(control.children.length > 0)
		{
			var child = control.children[0];
			//lets be sure we are talking about html tag
			while(child != null)
			{
				if(child.nodeType == 1)
				{
					child.disabled = disable;
					SetControlDisability(child, disable);
				}
	
				child = child.nextSibling;
			}
		}
	}
	

/* 
Constants to determine browser type / version
*/
var isOpera = navigator.userAgent.indexOf('Opera') > -1;
var isIE = navigator.userAgent.indexOf('MSIE') > 1 && !isOpera;
var isMoz = navigator.userAgent.indexOf('Mozilla/5.') == 0 && !isOpera;
var isMac = (navigator.appVersion.indexOf("Mac")!=-1) ? true : false;
var NS4 = (document.layers) ? true : false;
var IE4plus = (document.all) ? true : false;
var IE4 = ((document.all)&&(navigator.appVersion.indexOf("MSIE 4.")!=-1)) ? true : false;
var IE5 = ((document.all)&&(navigator.appVersion.indexOf("MSIE 5.")!=-1)) ? true : false;
var IE6 = ((document.all)&&(navigator.appVersion.indexOf("MSIE 6.")!=-1)) ? true : false;
var IE7 = ((document.all)&&(navigator.appVersion.indexOf("MSIE 7.")!=-1)) ? true : false;
var ver4 = (NS4 || IE4plus) ? true : false;
var NS6 = (!document.layers) && (navigator.userAgent.indexOf('Netscape')!=-1);
var isGecko = /gecko/i.test(navigator.userAgent); //added by dan-el
var docTitle = null;

/* 
Constants that enables/disables specific G2Page features
*/
var ENABLE_PROFILER = false;
var ENABLE_CLIENT_VALIDATION = true;
var ENABLE_POSTDATA_ONDEMAND = true;
var ENABLE_FAKE_POSTBACKS = false;
var NOTIFY_SERVER_HISTORY_CHANGE = false;
var CALLBACK_TIMEOUT = 5000; // the maximum time we will wait for a postback to return from server
// to enable this add in G2Page.PreRender:	TryRegisterG2ClientScriptFile("dhtmlHistory.js");

/*
Global window vars
*/
timings = [];
G2UseSyncCallbacks = false;
G2PartialPostDataElementIds = new Object();
G2InputChangedObservers = new Array();
var mainAdminTabControl = null;
G2AdminInputChangedObservers = new Object();
G2_EvalCache = {};

// a safty net for multiple post back all in the dame time.
var waitForCallback = null;


/*
Static methods that allows declaring various JS structures
*/


/*
G2_DeclareFunctions
Desc:
Methods declared with this function can be profiled
Usage:
regex to find function ggg(a, b, c)
function {.*}\({.*}\)
\1 : function(\2)
*/
G2_DeclareFunctions = function(json)
{
	1;
	for(var memberName in json)
	{
		var member = json[memberName];
		if(typeof(member)=="function")
		{
			member.name = memberName;
			eval(memberName+"=member;");
			if(ENABLE_PROFILER)
				Profiler.profile(member);
		}
	}
}

/*
G2_DeclareUtilInstance
Desc:
Allows declaring a static like instance in JS. Examples are: G2PopupManager, G2FrameManager, G2DOM
*/
G2_DeclareUtilInstance = function(instance)
{
	for(var memberName in instance)
	{
		var member = instance[memberName];
		if(typeof(member)=="function")
		{
			member.name = memberName;
			if(ENABLE_PROFILER)
				Profiler.profileUtilInstanceFunction(instance, member);
		}
	}
}

ImportInto = function(target, source)
{
	for(var memberName in source)
	{
		var member = source[memberName];
		target[memberName] = member;
		if(typeof(member)=="function")
		{
			member.name = memberName;
		}
	}
	if(source.toString!=Object.prototype.toString)
	{
		var member = source.toString;
		if(typeof(member)=="function")
			member.name = "toString";
		target.toString = member;
	}
}

G2_DeclareClass = function(type, name, baseType, json)
{
	type.name = name;
	if(baseType!=null)
		ImportInto(type.prototype, baseType.prototype);
	ImportInto(type.prototype, json);
	if(ENABLE_PROFILER)
	{
		for(var p in json)
		{
			var func = json[p];
			if(typeof(func)=="function")
				Profiler.profileTypeFunction(type, json[p]);
		}
	}

}

if(ENABLE_PROFILER)
{
	var Profiler = 
	{
		_pFuncs: [],
		profileUtilInstanceFunction : function(instance, func)
		{
			var pFunc = this._createProfilerFunction(func);
			if(pFunc==null)
				return;//cannot profile function
			instance[func.name] = pFunc;
		},
		profileTypeFunction : function(type, func)
		{
			var pFunc = this._createProfilerFunction(func);
			if(pFunc==null)
				return;//cannot profile function
			type.prototype[func.name] = pFunc;
		},
		profile : function(func)
		{
			var pFunc = this._createProfilerFunction(func);
			eval(func.name+"=pFunc;");
		},
		_createProfilerFunction : function(func)
		{
			if(func.name==null)
				return; //cannot profile function without a name
			var pFunc = function()
			{
				var pCallee = arguments.callee;
				pCallee.totalCalls++;
				var startInvoke = new Date().getTime();
				var result = pCallee.realFunc.apply(this, arguments);
				var endInvoke = new Date().getTime();
				var timeInvoke = endInvoke-startInvoke;
				pCallee.totalWithChildren += timeInvoke;
				var pCaller = pCallee.caller;
				var x = 0;
				while(pCaller!=null && pCaller.totalOfChildren==undefined && pCaller!=pCallee && x<5)
				{
					pCaller = pCaller.caller;
					x++;
				}
				if(pCaller!=null && pCaller.totalOfChildren!=undefined && pCaller!=pCallee)
				{
					pCaller.totalOfChildren+=timeInvoke;
				}
				return result;
			}
			pFunc.realFunc = func;
			pFunc.totalWithoutChildren = 0;
			pFunc.totalOfChildren = 0;
			pFunc.totalWithChildren = 0;
			pFunc.totalCalls = 0;
//			pFunc.totalOfChildrenWithProfiler = 0; //
			pFunc.name = func.name;
			this._pFuncs.push(pFunc);
			return pFunc;
		},
		clearData : function()
		{
			for(var i=0;i<this._pFuncs.length;i++)
			{
				var pFunc = this._pFuncs[i];
				pFunc.totalWithoutChildren = 0;
				pFunc.totalOfChildren = 0;
				pFunc.totalWithChildren = 0;
				pFunc.totalCalls = 0;
			}
		},
		takeSnapshot : function(sortBy)
		{
			if(sortBy==null)
				sortBy="totalCalls";
			var desc = sortBy!="name" ? -1 : 1;
			var arr = [];
			for(var i=0;i<this._pFuncs.length;i++)
			{
				var pFunc = this._pFuncs[i];
				pFunc.totalWithoutChildren = pFunc.totalWithChildren-pFunc.totalOfChildren;
				if(pFunc.totalCalls>0)
					arr.push(pFunc);
			}
			var array = arr.sort(function(x, y)
			{
				var valueX = x[sortBy];
				var valueY = y[sortBy];
				if(valueX==null || valueY==null)
				{
					if(valueX==valueY)
						return 0;
					return valueX==null ? 1*desc : -1*desc;
				}
				if(typeof(valueX)=="string" && typeof(valueY)=="string")
					return valueX.localeCompare(valueY)*desc;
				return (valueX.valueOf()-valueY.valueOf())*desc;
			});
			return array;
		},
		createDebugDiv : function()
		{
			if(Profiler.debugWindow==null)
			{
				if(window.opener!=null && window.opener.Profiler.debugWindow!=null)
				{
					Profiler.debugWindow = window.opener.Profiler.debugWindow;
				}
				else
				{
					var debugWindow = window.open(G2_MapPath('~/Client/Scripts/profiler.htm'), "debugWindow");
					Profiler.debugWindow = debugWindow;
				}
//				Profiler.debugWindow.registerWindow(window);
			}
		}
	}
	
}

/* 
Language extenstions
*/

String.prototype.endsWith = function String$endsWith(suffix) 
{
	return (this.substr(this.length - suffix.length) === suffix);
}

String.prototype.startsWith = function String$startsWith(prefix) 
{
  return (this.substr(0, prefix.length) === prefix);
}
String.prototype.contains = function(s)
{
	return this.indexOf(s)!=-1;
}


/* 
ASP.NET JS overrides
*/

if(typeof(WebForm_DoCallback)=="function")
{
	AspNet_WebForm_DoCallback = WebForm_DoCallback;
	AspNet_WebForm_CallbackComplete_Sync = WebForm_CallbackComplete;
}
window.net__doPostBack = window.__doPostBack;

window.__doPostBack = function(eventTarget, eventArgument,forcesilent) 
{
	// check lock to prevent multuple postbacks all in the same time
	if(waitForCallback)
	{
		// if we pass the the timeout value go on
		if(new Date() - waitForCallback <= CALLBACK_TIMEOUT)
		{
			// try again in 0.5 seconds
			window.setTimeout(function () { __doPostBack(eventTarget, eventArgument, forcesilent); }, 500);
			return;
		}
	}
	// lock this code
	waitForCallback = new Date();

  if (theForm==null || theForm.__EVENTTARGET == null) //This is sometimes caused when posting back from a popup that's closed.
		return;

	if (forcesilent == null)
		forcesilent = false;
	//Validation
	var targetEl = null;
	if(typeof(eventTarget)=="object")
	{
		targetEl = eventTarget;
		eventTarget = eventTarget.id;//String.Replace(eventTarget.id, "_", "$");
	}
	else
	{
		targetEl = G2_GetEventTargetElement(eventTarget);
	}
  if(targetEl!=null)
  {
		// 'CancelPostBackOnDisabled' attribute was added for canceling post back in case of disabled linkButton.
		// Any one can add this attribute in order to cancel postBack if the control is disabled.
		if (targetEl.cancelPostBackOnDisabled && targetEl.isDisabled)
			return;
			
		if (document.isPostingFromAClosedPopup) //Handle 'error 84' in IE when trying to postback from a closed popup.
			return;
    if(ENABLE_CLIENT_VALIDATION && (G2DOM.G2GetAttribute(targetEl,"causesvalidation")=="true" || (window.validateAll == "true" && G2DOM.G2GetAttribute(targetEl,"ignorevalidation") != "true"))) 
    {
      if(typeof(G2Validation_PerformValidation)=="function" && G2Validation_PerformValidation(targetEl)==false) 
        return;
      if(targetEl.onvalidatedclientclick!=null)
      {
     		var func = new Function(targetEl.onvalidatedclientclick);
				var res = func.call(targetEl);
				if (res == false)
					return;
      }
      if(targetEl.onbeforepostback!=null)
        window[targetEl.onbeforepostback](eventTarget, eventArgument);
    }
  }
  else
  {
    Debug.writeln("Could not find element " + eventTarget);
  }
  
 	if (theForm.onsubmit && (theForm.onsubmit() == false))
    return false;

  //Disable tooltips during silent postbacks.
  G2PopupManager.disableTooltips();
  //Display the processing image
  if (targetEl != null)
  {
    if (G2DOM.G2GetAttribute(targetEl,"showprocessingimage")=="true")
    {
      ShowProcessingImage(targetEl);
    }
    if (G2DOM.G2GetAttribute(targetEl,"showdisabler")=="true")
    {
      G2_ShowDisabler(true); 
    }
  }
  else
  {
    Debug.writeln("Could not find element " + eventTarget);
  }
  
  if(window.OnBeforePostbackClientFunction!=null)
  {
     window[window.OnBeforePostbackClientFunction]({eventTarget:eventTarget, eventArgument:eventArgument});
  }
  var doClassicPostBack = !G2IsSilent(eventTarget, eventArgument, targetEl) && !forcesilent;
  if(doClassicPostBack && !ENABLE_FAKE_POSTBACKS)
  {
 		for(var id in G2PartialPostDataElementIds)
		{
		  var element = G2PartialPostDataElementIds[id];
		  if(element==null || element.parentElement==null)
		  {
			  element = document.getElementById(id);
			}
			//isValueDirty might not be declared because it might've been updated dynamically, and lazy initialized.
			if(element!=null && typeof(element.isValueDirty)=="function" && !element.isValueDirty())
			{
				element.disabled = true;
			}
		}
 		for(var id in G2_PreventPostElementIds)
		{
			var element = document.getElementById(id);
			if(element!=null)
				element.disabled = true;
		}
		//we do not use the real __doPostback because it checks onsubmit again.
		theForm.__EVENTTARGET.value = eventTarget;
		theForm.__EVENTARGUMENT.value = eventArgument
		theForm.submit();

//		window.net__doPostBack(eventTarget, eventArgument);
		return;
  }
	var arg;
	if(ENABLE_FAKE_POSTBACKS && doClassicPostBack)
	{
		arg = "FakePostBack";
	}
	else
		arg = "SilentPostBack";
//		
  theForm.__EVENTTARGET.value = eventTarget;
  theForm.__EVENTARGUMENT.value = eventArgument;
	var arg = arg+"|" + eventTarget + "|" + eventArgument;
	G2_DoCallback('__Page', arg ,G2CallbackManager_HandleResult,{eventTarget:eventTarget,eventArgument:eventArgument},G2_OnCallbackError,false, false);
}

function WebForm_FireDefaultButton(event, target)
{
    if (event.keyCode == 13 && !(event.srcElement && (event.srcElement.tagName.toLowerCase() == "textarea"))) 
    {
			var defaultButton;
			if (__nonMSDOMBrowser) 
			{
				defaultButton = document.getElementById(target);
			}
    else 
    {
      defaultButton = document.all[target];
    }
    if (defaultButton && typeof(defaultButton.click) != "undefined") 
    {
			//added by dan-el - causes any other focused element to blur and fire the onchange event, #7457
			try
			{
				defaultButton.focus(); 
			}
			catch(err)
			{
				event.srcElement.blur();
			}
			defaultButton.click();
      event.cancelBubble = true;
      if (event.stopPropagation) 
				event.stopPropagation();
      return false;
    }
  }
  return true;
}
G2_onHistoryChange = function(newLocation, historyData)
{
	__doPostBack("__Page", "HistoryChange|"+newLocation, true);
}

/* 
G2 General Library Util Instance
*/

G2 = 
{
	AppendQueryString : function(url, qs)
	{
		if(url.search(/\?/)!=-1)
			return url+"&"+qs;
		return url+"?"+qs;
	},
	ArgumentsFrom : function(args, index)
	{
		var arr = [];
		for(var i=index;i<args.length;i++)
		{
			arr.push(args[i] || null);
		}
		return arr;
	},
	GetRelativeMouseX : function(e, relativeElement)
	{
		return e.clientX-G2_GetX(relativeElement)+relativeElement.scrollLeft;
	},
	GetRelativeMouseY : function(e, relativeElement)
	{
		return e.clientY-G2_GetY(relativeElement)+relativeElement.scrollTop;
	},
	Delegates : {},
	GetDelegate : function(target, func)
	{
		if(target==null)
			return func;
		if(typeof(func)=="string")
			func = target[func];
		var key = this.GetHashKey(func)+"$$"+this.GetHashKey(target);
		var delegate = this.Delegates[key];
		if(delegate==null)
		{
			delegate = function()
			{
				return arguments.callee.func.apply(arguments.callee.target, arguments);
			};
			delegate.func = func;
			delegate.target = target;
			delegate.isDelegate = true;
			this.Delegates[key] = delegate;
		}
		return delegate;
	},

	_hashIndex : 1,
	GetHashKey : function(obj)
	{
		if(obj===undefined)
			return "undefined";
		if(obj===null)
			return "null";
		var typeOf = typeof(obj);
		if(typeOf=="object" || typeOf=="function")
		{
			if(obj._hashKey==null)
			{
				obj._hashKey = typeOf+"$"+this._hashIndex;
				this._hashIndex++;
			}
			return obj._hashKey;
		}
		return obj.valueOf().toString();
	},
	historyIndex : 0,
	// check if any control was registered due to a change.
	ChangesWasMadeToControls : function()
	{
		if (this.changedInputs)
		{
			var i=0;
			for (var j in this.changedInputs)
				i++;
			if (i == 0)
				return false;
		}		
		return true
	},

	notifyInputPropertyChanged : function(e)
	{
	1;//value for textboxes, checked for checkboxes, selectedIndex for combos
		if(e.propertyName=="value" || e.propertyName=="checked" || e.propertyName=="selectedIndex") //checked is for checkbox and radiobutton
			this.notifyInputChanged(e.srcElement);
	},
	changedInputs : new Object(),
	notifyInputChangedFF_Watch : function(inputId, oldVal, newVal)
	{
		G2.notifyInputChanged(this);
		return newVal;
	},
	notifyInputChangedFF_Event : function(evnt)
	{
		G2.notifyInputChanged(evnt.target);
	},
	RegisterPropertyChangeWatch : function(elementID)
	{
		if (isMoz)
		{
			var e = document.getElementById(elementID);
			e.watch("value",this.notifyInputChangedFF_Watch	);
			e.watch("checked",this.notifyInputChangedFF_Watch);
			e.watch("selectedIndex",this.notifyInputChangedFF_Watch);
			e.addEventListener("change",this.notifyInputChangedFF_Event,false);
		}
	},	
	RegisterPropertyChangeWatchWithHandler : function(elementID,handler)
	{
		if (isMoz)
		{
			var e = document.getElementById(elementID);
			var watchHandler = function(){handler(this);};
			e.watch("value",watchHandler);
			e.watch("checked",watchHandler);
			e.watch("selectedIndex",watchHandler);
			var eventHandler = function(evnt){handler(evnt.target);};
			e.addEventListener("change",eventHandler,false);
		}
	},	
	notifyInputChanged : function(input)
	{
	   if(input.isInitializing)
	    return;
		this.changedInputs[input.id] = input;
		if(input.notifyobserver == null || input.notifyobserver == "true")		
			this.fireNotifyInputChangedEvent();
	},
	undoNotifyInputChanged : function(input)
	{
		if(this.changedInputs[input.id] != null)
		{
			delete this.changedInputs[input.id];
		}
	},	
	notifyCheckBoxPropertyChange : function(e)
	{
		if(e.propertyName=="value" || e.propertyName=="checked")
		{
			var checkbox = e.srcElement;
			this.notifyInputChanged(checkbox);
			if(typeof(checkbox.g2PerformUndo)=="undefined")
			{
				checkbox.originalValue = !checkbox.checked; //the value before the click
				checkbox.g2PerformUndo = G2.CheckBox_PerformUndo;
				checkbox.g2SetOriginalValue = G2.CheckBox_SetOriginalValue;
				checkbox.g2IsDirty = G2.CheckBox_IsDirty;
			}
		}
	},
	notifyCheckBoxClicked : function(checkbox)
	{
		this.notifyInputChanged(checkbox);
		if(typeof(checkbox.g2PerformUndo)=="undefined")
		{
			checkbox.originalValue = !checkbox.checked; //the value before the click
			checkbox.g2PerformUndo = G2.CheckBox_PerformUndo;
			checkbox.g2SetOriginalValue = G2.CheckBox_SetOriginalValue;
			checkbox.g2IsDirty = G2.CheckBox_IsDirty;
		}
	},
	CheckBox_PerformUndo : function(checkbox)
	{
		checkbox = checkbox || this;
		checkbox.checked = checkbox.originalValue;
	},
	CheckBox_SetOriginalValue : function(checkbox)
	{
		checkbox = checkbox || this;
		checkbox.originalValue = checkbox.checked;
	},
	CheckBox_IsDirty : function(checkbox)
	{
		checkbox = checkbox || this;
		return checkbox.checked != checkbox.originalValue;
	},
	getAdminToolsActiveTabId : function ()
	{
		if (mainAdminTabControl == null)
			mainAdminTabControl = $('adminTabControlDiv').firstChild;
		if (mainAdminTabControl.ActiveTab) //already initialized
			return mainAdminTabControl.ActiveTab.id;
		else //not yet initialized
			return mainAdminTabControl.activetabid;
	},
	getAdminToolsObserversInTab : function(tabId)
	{
		if (typeof(tabId) == 'undefined')
			tabId = this.getAdminToolsActiveTabId();
		if (typeof (G2AdminInputChangedObservers[tabId]) == 'undefined')
			G2AdminInputChangedObservers[tabId] = new Object();
		return G2AdminInputChangedObservers[tabId]; 
	},
	attachObserver : function (id, tabId)
	{		
		var observers = this.getAdminToolsObserversInTab(tabId);
		if (observers[id] == true) //Change by Adi Eduard
		  return;
		observers[id] = false; 
	},
	detachObserver : function (id, tabId)
	{		
		var observers = this.getAdminToolsObserversInTab(tabId);
		delete observers[id];
	},
	fireNotifyInputChangedEvent : function (tabId)
	{
	  if (window.IsAdminToolsMainPage != true) //this feature works only in the admin tools
			return; 
		var observers = this.getAdminToolsObserversInTab(tabId);
		for(var obs in observers)
		{
			observers[obs] = true;
		}
	},
	setObjectChanged : function (id, tabId)
	{
		var observers = this.getAdminToolsObserversInTab(tabId);
		observers[id] = true;
	},
	setObjectUnchanged : function (id, tabId)
	{
		var observers = this.getAdminToolsObserversInTab(tabId);
		(observers[id] != null)
			observers[id] = false;
	},
	IsObjectChanged : function (id, tabId)
	{
			var observers = this.getAdminToolsObserversInTab(tabId);
			return observers[id] == true;
	},
	AreThereAnyChanges : function ()
	{
		var allObservers = G2AdminInputChangedObservers;
		for (var tab in allObservers)
		{
			tabObservers = allObservers[tab];
			for (var obsId in tabObservers)
			{
				if (tabObservers[obsId] == true)
					return true;
			}
		}
		return false;
	}
	
};
G2_DeclareUtilInstance(G2);

G2_DeclareFunctions(
{
	G2InitParentControl : function(sender, e)
	{
		if(sender.g2HasInitedParentControl)
			return;
		sender.g2HasInitedParentControl = true;
		var control = sender;
		var controlType;
		while(control!=null)
		{
			controlType = G2DOM.G2GetAttribute(control, "g2control")
			if(controlType!=null)
				break;
			control = control.parentElement;
		}
		if(control.g2IsInited)
			return;
		if(control.isDisabled)
			return;
		window[controlType+"_Init"](control, e);
		if(!control.g2IsInited)
			control.g2IsInited = true;
	},
	G2_VerifyControlInitialized : function(control, e)
	{
		if(control.g2IsInited)
			return;
		var controlType = G2DOM.G2GetAttribute(control, "g2control");
		if(controlType==null)
			return;
		window[controlType+"_Init"](control, e);
		if(!control.g2IsInited)
			control.g2IsInited = true;
	},

	G2_DoCallback : function(eventTarget, eventArgument, eventCallback, context, errorCallback, useAsync, classicPostback)
	{
	  G2_OnBeforeCallback();
	  WebForm_DoCallback(eventTarget, eventArgument, eventCallback, context, errorCallback, useAsync, classicPostback);
	},
	G2_OnBeforeCallback : function()
	{
		document.body.style.cursor="wait";
	},

	G2_OnCallbackError : function(result, context)
	{
		var err = "Callback Error: "+result;
		alert(err);
		
		G2_OnCallbackFinally(result, context);
	},

	G2_OnCallbackFinally : function(result, context)
	{
 		document.body.style.cursor = "";
 		//Close and reebable tooltips (disabled during silent postbacks)
 		G2PopupManager.enableTooltips();
 		G2PopupManager.closeAllTooltips();
	},
	//taken from aspnet scripts - performed MAJOR optimizations (removed the foreach loop)
	G2_InitCallback : function() 
	{
 		var context = {postData:new Array(), postCollection:new Array()};
		G2_InitCallbackRecursive(context);
		return context;
//		__theFormPostData =context.postData.join("");
//		__theFormPostCollection = context.postCollection;
	},


	G2CallbackManager_HandleResult : function(result, aspNetContext)
	{
		// unlock dopostback
		waitForCallback = null;
		
		var r = result.split("%||%");
		var context = {resultArray:r, aspNetContext:aspNetContext};
//		//moved to start by dan-el  
//		var viewState = r[4];
//		G2CallbackManager_UpdateViewState(viewState);
		//Handle hidden fields


		var scriptIncludes = r[1].split("||||");
		var srcArray = new Array();
		for(var i=0; i<scriptIncludes.length; i++)
		{
			var src = scriptIncludes[i];
			if(src==null || src=="")
				continue;
			srcArray.push(src);
		}
		G2_RegisterScripts(srcArray, function(){G2_HandleCallbackResultPhase2(result, context);});
		
		
		
	},

	
	G2_HandleCallbackResult_UpdateDomElements : function(htmlData)
	{
		for(var i=0; i<htmlData.length; i++)
		{
			if(htmlData[i]=="" || htmlData[i]==null)
				break;
			var element=document.getElementById(htmlData[i]);
			i++;
			var newHtml = htmlData[i];
			if (element != null)
			{
				var controlElement = element;
				if(element.getcontrolelement!=null)
				{
					controlElement = G2_Eval(element.getcontrolelement, element);
					if(controlElement==null)
					{
						G2_Warn("G2_HandleCallbackResult_UpdateDomElements", "controlElement wasn't found for element "+element.id);
						continue;
					}
				}
				G2DOM.G2ReplaceOuterHTML(controlElement,newHtml);
			}
		}
	},
	
	G2_Eval : function(code, target)
	{
		var cache = G2_EvalCache;
		var func = cache[code];
		if(func==null)
		{
			func = new Function(code);
			cache[code] = func;
		}
		return func.call(target);
	},
	StartTiming : function()
	{
		timings.push(new Date().getTime());
	},
	EndTiming : function(name)
	{
		name = name || arguments.callee.caller.name;
		var end = new Date().getTime();
		var start = timings.pop();
		var span= end-start;
//		if(span>500)
//			alert(name+" took "+span+"ms!");
	},
	
	G2_HandleCallbackResult_AddRepeaterElement: function(htmlData)
	{
		for(var i=0; i<htmlData.length; i++)
		{
			if(htmlData[i]=="" || htmlData[i]==null)
				break;
			var element=document.getElementById(htmlData[i]);
			i++;
			if(element != null)
			{
				var tbody = element.firstChild.tBodies[0];
				var newElement = G2DOM.G2CreateElementFromHtml(htmlData[i]);
				tbody.appendChild(newElement);
			}
		}		
	},
	
	G2_HandleCallbackResult_RemoveElement: function(itemsToRemove)
	{
		for(var i=0; i<itemsToRemove.length; i++)
		{
			if(itemsToRemove[i]=="" || itemsToRemove[i]==null)
				break;
			var element = document.getElementById(itemsToRemove[i]);			
			if(element != null)
			{
				element.removeNode(true)				
			}
		}		
	},
	
	G2_HandleCallbackResult_UpdateHiddenFields : function(hfHtml)
	{
		var div=document.createElement("DIV");
		div.innerHTML = hfHtml;
		var divChildren = div.children;
		var addElements = new Array();
		for(var i=0;i<divChildren.length; i++)
		{
			var hf = divChildren[i];
			var curHf = document.getElementById(hf.id);
			if(curHf!=null)
				curHf.value = hf.value;
			else
				addElements.push(hf); //we don't appendChild now because the length will change.
		}
		for(var i=0;i<addElements.length;i++)
		{
			document.forms[0].appendChild(addElements[i]);
		}
	},
	G2_HandleCallbackResult_UpdateActiveElement : function(activeElementID, prevActiveElement)
	{
		var el = document.getElementById(activeElementID);
		if(el!=null && el.tagName!="A" && prevActiveElement!=el)
		{
			var f = function()
			{	
				//the following line handles focusing an element that was replaced during a callback
				if(el.parentElement==null) //Element is detached from the dom
					el = document.getElementById(el.id);//Find the new element in the dom
				try
				{
				  el.isFocusingAfterPostback = true;//Indicate to the element that this is autofocus 
					el.focus(); //This may fail if the control is hidden etc.
				} 
				catch(e)
				{
				}
			}
			window.setTimeout(f, 50);
		}
	},
	G2_HandleCallbackResult_EvalStartupStatements : function(scriptData)
	{
		StartTiming();
		eval(scriptData);
		EndTiming();
	},
	G2_ReplaceCssClass : function(element, addCss, removeCss, inverse)
	{
		if(inverse)
		{
			var temp = removeCss;
			removeCss = addCss;
			addCss = temp;
		}
		var classes = G2_ParseCssClasses(element);
		classes.remove(removeCss);
		classes.add(addCss);
		G2_SetCssClasses(element, classes);

  },
	G2_RemoveCssClass : function(element, className)
	{
		var index = G2_FindWholeWord(element.className, className);
		if(index!=-1)
		{
			var begin = element.className.substr(0, index-1);
			var end = element.className.substr(index+className.length+1);
			if(begin!="" && end!="")
				element.className = begin+" "+end;
			else
				element.className = begin+end;
		}
  },
	G2_ParseCssClasses : function(element)
	{
		var list = element.className.split(/ /g);
		var obj = new ListSet();
		if(list.length==1 && list[0]=="")
		{
		}
		else
		{
			obj.addRange(list);
		}
		return obj;
  },
	G2_SetCssClasses : function(element, listset)
	{
		element.className = listset.toString(" ");
  },

	G2_AddCssClass : function(element, className)
	{
    if (!G2_ContainsCssClass(element, className)) 
    {
      if (element.className === '') 
      {
        element.className = className;
      }
      else 
      {
        element.className += ' ' + className;
      }
    }
  },
	G2_ContainsCssClass : function(element, className)
	{
		return G2_FindWholeWord(element.className, className)!=-1;
	},
	G2_FindWholeWord : function(text, word, seperator)
	{
		if(seperator==null)
			seperator = " ";
		if(word==null || word=="" || word.indexOf(seperator)!=-1)
			throw new Error("error in word: "+word);
		if(text=="")
			return -1;
		var x = 0;
		for(var i=0;i<text.length;i++)
		{
			if(text.charAt(i)==seperator)
			{
				if(x==word.length)
					return i-x;
				x=0;
			}
			else if(text.charAt(i)==word.charAt(x))
				x++;
			else
				x=0;
		}
		if(x==word.length)
			return i-x;
		return -1;
  },

	G2_HandleCallbackResultPhase2 : function(result, context)
	{	
		var resultArray = context.resultArray;

		//Handle html repeater data
		var htmlRepeaterData = resultArray[5].split("||||");
		G2_HandleCallbackResult_AddRepeaterElement(htmlRepeaterData);
				
		//Handle removing items
		var itemsToRemove = resultArray[6].split("||||");
		G2_HandleCallbackResult_RemoveElement(itemsToRemove);
		
		//Handle html data
		var htmlData = resultArray[0].split("||||");
		var activeElementID = null;
		var activeElement = document.activeElement;
		if(activeElement && !String.IsNullOrEmpty(activeElement.id))
		{
			activeElementID = activeElement.id;
		}
		G2_HandleCallbackResult_UpdateDomElements(htmlData);				
		
		//aspnet holds a strong reference to the form element, (in a variable named theForm)
		//which might be updated dynamically, so we update that reference
		if(theForm.parentElement==null) 
			theForm = document.forms[0];
		var hfHtml = resultArray[2];
		if(hfHtml!=null && hfHtml!="")
		{
			G2_HandleCallbackResult_UpdateHiddenFields(hfHtml);
		}

		if(activeElementID!=null)
		{
			G2_HandleCallbackResult_UpdateActiveElement(activeElementID, activeElement);
		}
			
		//Handle scripts
		var scriptData = resultArray[3];
		if(scriptData!=null && scriptData!="")
		{
			G2_HandleCallbackResult_EvalStartupStatements(scriptData);
		}
		
 	  //Handle the processing image - AFTER the startup statements (since we might navigate, and in that case we don't want to hide the image)
		HideProcessingImage();
		
		G2_ShowDisabler(false);
		
		//Handle last scripts
		var lastScriptData = resultArray[4];
		if(lastScriptData!=null && lastScriptData!="")
		{
			window.setTimeout(function(){	G2_HandleCallbackResult_EvalStartupStatements(lastScriptData); }, 10);
		}
		
		if(window.OnAfterCallbackClientFunction!=null)
		{
			window[window.OnAfterCallbackClientFunction]();
		}
		
		
		if(NOTIFY_SERVER_HISTORY_CHANGE)
		{
			if(context.aspNetContext.eventTarget=="__Page" && context.aspNetContext.eventArgument.startsWith("HistoryChange"))
			{
			}
			else
			{
				G2.historyIndex++;
				dhtmlHistory.add(G2.historyIndex.toString(), "Hello World " + "Data")
			}
		}
		G2_OnCallbackFinally(result, context);

		//event validation - doesn't work
	//  var eventValidationFieldValue = r[3];
	//  var eventValidationField = document.getElementById("__EVENTVALIDATION");
	//  eventValidationField.value = eventValidationFieldValue;
	},



	G2CallbackManager_UpdateViewState : function(viewState)
	{
		var div = document.createElement("div");
		div.innerHTML = viewState;
		document.getElementById("__VIEWSTATE").value =div.firstChild.value;
	},


	G2_InitCallbackAddField : function(name, value, context) 
	{
	//	WebForm_InitCallbackAddField(name, value);
//			var nameValue = new Object();
//			nameValue.name = name;
//			nameValue.value = value;
//			context.postCollection.push(nameValue);
			context.postData.push(name);
			context.postData.push("=");
			context.postData.push(WebForm_EncodeCallback(value));
			context.postData.push("&");
	},

	EnableSupportForPartialPostData : function(element)
	{
		element.isValueDirty = EnableSupportForPartialPostData_IsValueDirty;
		element.setValueAsNotDirty = EnableSupportForPartialPostData_SetValueAsNotDirty;
		element._originalValue = element.value;
		G2PartialPostDataElementIds[element.id] = element;
		if(ENABLE_POSTDATA_ONDEMAND)
		{
			if (isIE)
			{
				if((element.tagName=="INPUT" && element.type=="text") || element.tagName=="SELECT" || element.tagName=="TEXTAREA")
				{
					G2_AttachEvent(element, "onchange", function()
					{
						G2.notifyInputChanged(this);
					});
				}
				else
				{
					G2_AttachEvent(element, "onpropertychange", function()
					{
						if(event.propertyName=="value")
							G2.notifyInputChanged(this);
					});
				}
			} 
			else if (isMoz)
			{
				G2.RegisterPropertyChangeWatch(element.id);
			}
		}
	},
	
	EnableSupportForPartialPostData_SetValueAsNotDirty : function()
	{
		this._originalValue = this.value;
	},
	
	EnableSupportForPartialPostData_IsValueDirty : function()
	{
		return !(this.value===this._originalValue);
	},
	G2_InitCallbackByIds : function(ids, context)
	{
		for(var i=0;i<ids.length;i++)
		{
			var element = $(ids[i]);
			if(element!=null)
			{
				G2_InitCallbackForElement(element, context);
			}
			else if(ids[i]=="__WINDOWID" && window.location.href.search("WindowID")==-1)
			{
				throw new Error("window id not found");
			}
		}
	},

	G2_InitCallbackRecursive : function(context)
	{
		if(ENABLE_POSTDATA_ONDEMAND)
		{
			G2_InitCallbackAddField("__PARTIALPOSTDATA", "true", context);
			G2_InitCallbackByIds(["__EVENTTARGET", "__EVENTARGUMENT",  "__EVENTVALIDATION", "__VIEWSTATE", "__WINDOWID"], context);
			var inputsToRemove = new Object();
			for(var id in G2.changedInputs)
			{
				var element = $(id)
				if (element) //the element may be detached from the DOM
				{
					G2_InitCallbackForElement(element, context);
					inputsToRemove[id] = id;
				}
			}
			for (var id in inputsToRemove)//remove sent inputs
			{
				delete G2.changedInputs[id];
			}
		}
		else
			G2_PerformRecursiveActionOnElement(theForm, G2_InitCallbackForElement, context);
	},

	G2_InitCallbackForElement : function(element, context)
	{
		if(element.doesNotContainInputs)
			return false;
		if(G2_PreventPostElementIds[element.id]==true)
			return false;
		var tagName = element.tagName.toLowerCase();
		if (tagName == "input") 
		{
			var type = element.type;
			if ((type == "text" || type == "hidden" || type == "password" ||
					((type == "checkbox" || type == "radio"))) && // && element.checked
					(element.id != "__EVENTVALIDATION")) 
			{
				var name = element.name;
				var value = element.value;
				if(type == "checkbox")
				{
					if(ENABLE_POSTDATA_ONDEMAND)
					{
						value = element.checked ? "on" : "off";
					}
					else if(!element.checked)
						return false;
				}
				else if(type == "radio")
				{
					if(ENABLE_POSTDATA_ONDEMAND)
					{
						if(type == "radio" && element.g2rb=="true")
						{
							name = element.id;
						  value = element.checked ? "on" : "off";
						}
						else
					  {
					    G2_InitCallbackAddField(name, value, context);
					    return false;
					  }
					}
					else if(!element.checked)
						return false;
				}

				if(typeof(element.isValueDirty)=="function")
				{
					if(element.isValueDirty())
					{
						element.setValueAsNotDirty();
					}
					else
						return false;
				}
				G2_InitCallbackAddField(name, value, context);
				return false;
			}
		}
		else if (tagName == "select") 
		{
			var selectCount = element.options.length;
			var selCount = 0;
			for (var j = 0; j < selectCount; j++) 
			{
				var selectChild = element.options[j];
				if (selectChild.selected == true) 
				{
					selCount++;
					G2_InitCallbackAddField(element.name, selectChild.value, context);
					if(!element.multiple)
						return false;
				}
			}
			//We send null value to the ListBox
			if(selCount==0 && element.multiple)
				G2_InitCallbackAddField(element.name, "__NULL__", context);
		}
		else if (tagName == "textarea") 
		{
			G2_InitCallbackAddField(element.name, element.value, context);
			return false;
		}
		return true;
	},





	G2_GetEventTargetID : function(eventTarget) 
	{
		var realId;
		if(eventTarget.indexOf("$")>-1)
			realId = eventTarget.replace(/\$/g, '_');
		else if(eventTarget.indexOf(":")>-1)
			realId = eventTarget.replace(/:/g, '_');
		else
			realId = eventTarget;
		return realId; 
	},

	G2_GetEventTargetElement : function(eventTarget)
	{
		var el = $(eventTarget);
		if(el==null)
		{
			if(eventTarget.indexOf("$")>-1)
				eventTarget = eventTarget.replace(/\$/g, '_');
			else if(eventTarget.indexOf(":")>-1)
				eventTarget = eventTarget.replace(/:/g, '_');
			else
				return null;
			el = $(eventTarget);
		}
		return el;
	},


	G2_RefreshElement : function(element)
	{
		element.outerHTML = element.outerHTML;
	},

	G2IsSilent : function(eventTarget, eventArgument, eventTargetElement) 
	{
		if(window.silentPostbacks==true)
			return true;
		if (window.DisableSilentPostBack==true)
			return false;
		if(eventTargetElement!=null && eventTargetElement.getAttribute("silentpostback")=="true")
			return true;
		return false;
		var targets = window.silentPostbacksTargets;
		if(targets==null)
			return false;
		var val = targets[eventTarget];
		//TODO: find what causes this
		if(val==null && eventTarget.indexOf("$")>-1)
		{
			eventTarget = eventTarget.replace(/\$/g, '_');
			val = targets[eventTarget];
		}
		if(val==null && eventTarget.indexOf(":")>-1)
		{
			eventTarget = eventTarget.replace(/:/g, '_');
			val = targets[eventTarget];
		}
		if(val==null)
			return false;
		if(!String.IsNullOrEmpty(eventArgument) && val.args!=null)
		{
			var childValue = val.args[eventArgument];
			if(childValue!=null)
				return childValue;
		}
		return val.silent;
	},

	G2SetSilentPostBacks : function(json) 
	{
		if(window.silentPostbacksTargets==null)
		{
			window.silentPostbacksTargets = json;
		}
		else
		{
			for(var p in json)
			{
				window.silentPostbacksTargets[p] = json[p];
			}
		}
	},


	G2SetSilentPostBacksAll : function(isSilent)
	{
		window.silentPostbacks = isSilent;
	},

	//*****************************************************************
	//*                      G2ScriptManager                          *
	//*****************************************************************
	G2_GetRegisteredScripts : function()
	{
		if(_registeredScripts==null)
		{
			var elements = document.getElementsByTagName("script");
			_registeredScripts = new Object();
			for(var i=0;i<elements.length;i++)
			{
				var element = elements[i];
				if(element.src!="")
					_registeredScripts[element.src] = true;
			}
		}
		return _registeredScripts;
	},

	G2_IsScriptRegistered : function(src)
	{
		return G2_GetRegisteredScripts()[src]==true;
	},

	G2_GetUnregisteredScripts : function(srcArray)
	{
		if(srcArray==null)
			return null;
		var sources = new Array();
		for(var i=0;i<srcArray.length;i++)
		{
			var src = srcArray[i];
			if(!G2_IsScriptRegistered(src))
			{
				sources.push(src);
			}
		}
		return sources;
	},
	//
	// Gets an array of src strings, and loads these scripts. returns a callback when all scripts are loaded
	//
	G2_RegisterScripts : function(srcArray, loadCompletedCallback)
	{
		var sources = G2_GetUnregisteredScripts(srcArray);
		if(sources!=null && sources.length>0)
		{
			var context = {total:sources.length, loadCompletedCallback:loadCompletedCallback, sources:sources};
			for(var i=0;i<sources.length;i++)
			{
				var src = sources[i];
//				didNothing = false;
				var element = document.createElement("SCRIPT");
				element.src = src;
				element.setAttribute("type","text/javascript"); //Check if really needed
				document.body.appendChild(element); //TODO: this is a problem - the included file takes time to load 
				
				if(loadCompletedCallback!=null)
				{
					G2_AttachEvent(element, isIE ? "onreadystatechange" : "onload", function(e){G2_WaitForScripts(e ? e : event,context);}	);
				}
			}
		}
		else if(loadCompletedCallback!=null)
		{
			loadCompletedCallback();
		}
	},
	//*****************************************************************
	//*               End of G2ScriptManager                          *
	//*****************************************************************

	G2_WaitForScripts : function(event,context)
	{
		var element = G2Event.element(event);
		if(element.readyState=="loaded" || element.readyState=="complete" || isMoz)
		{
			context.total--;
			//clean up
			G2_DetachEvent(element, isIE ? "onreadystatechange" : "onload", G2_WaitForScripts);
			//end 
			_registeredScripts[element.src] = true;
			if(context.total==0)
			{
				context.loadCompletedCallback();
			}
		}
	},
	
	G2_CreateXmlHttp : function()
	{
		var xmlRequest,e;
		try 
		{
			xmlRequest = new XMLHttpRequest();
		}
		catch(e) 
		{
			try 
			{
				xmlRequest = new ActiveXObject("Microsoft.XMLHTTP");
			}
			catch(e) {
			}
		}
		var setRequestHeaderMethodExists = true;
		try 
		{
			setRequestHeaderMethodExists = (xmlRequest && xmlRequest.setRequestHeader);
		}
		catch(e) {}
		if(!setRequestHeaderMethodExists)
			return null;
		return xmlRequest;
	},

	WebForm_DoCallback : function (eventTarget, eventArgument, eventCallback, context, errorCallback, useAsync, classicPostback, g2context) 
	{
		if(g2context==null) //this may happen when calling DoCallback directly (when using ClientScript.GetCallbackReference
		{
			g2context = G2_InitCallback();
		}

		g2context.postData.push("__CALLBACKID=");
		g2context.postData.push(WebForm_EncodeCallback(eventTarget));
		g2context.postData.push("&__CALLBACKPARAM=");
		g2context.postData.push(WebForm_EncodeCallback(eventArgument));
		if (theForm["__EVENTVALIDATION"]) 
		{
			g2context.postData.push("&__EVENTVALIDATION=");
			g2context.postData.push(WebForm_EncodeCallback(theForm["__EVENTVALIDATION"].value));
		}
		var postData = g2context.postData.join("");
		var xmlRequest = G2_CreateXmlHttp();
		
		var callback = new Object();
		callback.eventCallback = eventCallback;
		callback.context = context;
		callback.errorCallback = errorCallback;
		callback.async = useAsync;
		var callbackIndex = WebForm_FillFirstAvailableSlot(__pendingCallbacks, callback);
		if (!useAsync) 
		{
				if (__synchronousCallBackIndex != -1) {
						__pendingCallbacks[__synchronousCallBackIndex] = null;
				}
				__synchronousCallBackIndex = callbackIndex;
		}
		if (xmlRequest!=null) 
		{
			if(!G2UseSyncCallbacks)
				xmlRequest.onreadystatechange = WebForm_CallbackComplete;
			callback.xmlRequest = xmlRequest;
			xmlRequest.open("POST", theForm.action, !G2UseSyncCallbacks); //was hardcoded true - modified by Alon to force sync. calls to allow popups to be opened.
			xmlRequest.setRequestHeader("Content-Type", "application/x-www-form-urlencoded");
			xmlRequest.send(postData);
			if(G2UseSyncCallbacks)
				WebForm_CallbackComplete();
			return;
		}
		WebForm_DoCallback_WithIFrame();
	},
	//this code exists in asp.net callbacks code - and used when browser doesn't support xmlhttp.
	//removed for now.
	WebForm_DoCallback_WithIFrame : function()
	{
		throw new Error("not implemented");
	},


	WebForm_CallbackComplete : function() 
	{
			for (var i = 0; i < __pendingCallbacks.length; i++) 
			{
					callbackObject = __pendingCallbacks[i];
					if (callbackObject && callbackObject.xmlRequest && (callbackObject.xmlRequest.readyState == 4)) 
					{
							WebForm_ExecuteCallback(callbackObject);
							//TODO: HACK: added by dan-el - when closing popups the item is not there. probably related to registration to callbackreference
							if(__pendingCallbacks[i]!=null) 
							{
								if (!__pendingCallbacks[i].async) 
								{
										__synchronousCallBackIndex = -1;
								}
							}
							__pendingCallbacks[i] = null;
							var callbackFrameID = "__CALLBACKFRAME" + i;
							var xmlRequestFrame = document.getElementById(callbackFrameID);
							if (xmlRequestFrame) 
							{
									xmlRequestFrame.parentNode.removeChild(xmlRequestFrame);
							}
					}
			}
	},

	WebForm_ExecuteCallback : function(callbackObject) 
	{
		var response = callbackObject.xmlRequest.responseText;
		if (response.charAt(0) == "s") 
		{
			if ((typeof(callbackObject.eventCallback) != "undefined") && (callbackObject.eventCallback != null)) 
			{
				callbackObject.eventCallback(response.substring(1), callbackObject.context);
			}
		}
		else if (response.charAt(0) == "e") 
		{
			if ((typeof(callbackObject.errorCallback) != "undefined") && (callbackObject.errorCallback != null)) 
			{
				callbackObject.errorCallback(response.substring(1), callbackObject.context);
			}
		}
		else 
		{
			var separatorIndex = response.indexOf("|");
			if (separatorIndex != -1) 
			{
				var validationFieldLength = parseInt(response.substring(0, separatorIndex));
				if (!isNaN(validationFieldLength)) 
				{
					var validationField = response.substring(separatorIndex + 1, separatorIndex + validationFieldLength + 1);
					if (validationField != "") 
					{
						var validationFieldElement = theForm["__EVENTVALIDATION"];
						if (!validationFieldElement) 
						{
							validationFieldElement = document.createElement("INPUT");
							validationFieldElement.type = "hidden";
							validationFieldElement.name = "__EVENTVALIDATION";
							theForm.appendChild(validationFieldElement);
						}
						validationFieldElement.value = validationField;
					}
					if ((typeof(callbackObject.eventCallback) != "undefined") && (callbackObject.eventCallback != null)) 
					{
						callbackObject.eventCallback(response.substring(separatorIndex + validationFieldLength + 1), callbackObject.context);
					}
				}
			}
			else
			{
				var location = callbackObject.xmlRequest.getResponseHeader("location"); //if Response.RedirectLocation is used
				if(location!=null && location!="")
				{
					G2_Navigate(location);
				}
				else
				{
   				callbackObject.errorCallback(response, callbackObject.context);
   			}
			}
		}
	},

	G2_UseSyncCallbacks : function()
	{
		G2UseSyncCallbacks = true;
//		WebForm_DoCallback = WebForm_DoCallback_Sync;
//		WebForm_CallbackComplete = WebForm_CallbackComplete_Sync;
	},


	//
	//recursivle iterates on all child elements of a certain element,
	//and calls the specified action with the element and context, action(element, context)
	//if the action returns false, it will stop the recursive operation inside that element
	//
	G2_PerformRecursiveActionOnElement : function(element, action, context)
	{
		_G2_PerformRecursiveActionOnElement(element, action, context);
	},
	_G2_PerformRecursiveActionOnElement : function(element, action, context)
	{
		if(element.nodeType!=1) //textnode
			return;

		var result = action(element, context);
		if(result==false)
			return;
		var child = element.firstChild;
		while(child!=null)
		{
			_G2_PerformRecursiveActionOnElement(child, action, context);
			child = child.nextSibling;
		}
	},


	G2_SetFocus : function(elementId)
	{
		if(G2_SetFocus_ThreadId!=null)
		{
			window.clearTimeout(G2_SetFocus_ThreadId);
			G2_SetFocus_ThreadId = null;
		}
		G2_SetFocus_ThreadId = window.setTimeout(
			function()
			{
				G2_SetFocus_ThreadId = null;
				var success = G2_AutoFocus(elementId);
				if(success) //case 8578 - sometimes after the successful focus, the body is somehow focused. this hack fixes it.
				{
					if(document.activeElement==null || document.activeElement.id!=elementId)
					{
						success = G2_AutoFocus(elementId);
					}
				}
			}, 50);
	},


	///
	/// Finds a server control by server ID (using id.contains(id))
	///
	G2_FindServerControl : function(fromElement, id)
	{
		return _G2_FindServerControl(fromElement, id);
	},
	_G2_FindServerControl : function(fromElement, id)
	{
		if(fromElement.id!=null && fromElement.id.endsWith(id))
			return fromElement;

		if(fromElement.doesNotContainInputs || fromElement.tagName=="SELECT")
			return null;

		var element = fromElement.firstChild;
		while(element!=null)
		{
			var foundControl = _G2_FindServerControl(element, id)
			if(foundControl!=null)
				return foundControl;
			element = element.nextSibling;
		}
		return null;
	},



	G2ReturnValue : function(value)
	{
		this.value = value;
	},
	
	// Get current page theme
	G2_PageTheme : function()
	{
		return document.getElementById("G2_PageTheme").value;
	},


	G2_MapPath : function(virtualUrl)
	{
		var rootAppPath = document.getElementById("G2_RootAppPath").value;
		var path = virtualUrl.replace("~/", rootAppPath);
		return path;
	},
	G2_IsNavigating : function()
	{
	  return window.top.IsNavigating;
	},
	
	G2_Navigate : function(url, isInternalNavigation, targetFrame, navigateWithForms)
	{
	    var navigationWindow = null;
	    if (isInternalNavigation && isInternalNavigation != 'false')
		{
		      if(targetFrame!="" && targetFrame!=null) //navigate inside a frame
		      {
		        var f = document.getElementById(targetFrame);
		        f.contentWindow.document.location.href = url;
		        return;
		      }
		      else //navigate in this window
		         navigationWindow = window; 
		}
		else //navigate in the topmost window
		{
		      navigationWindow = window.top;
	    }
	    if (navigateWithForms && navigateWithForms != 'false') //naviage throught form submit
	        G2_FormNavigate(navigationWindow, url);
	     else //navigate through url change
	     {
	        navigationWindow.IsNavigating = true;
	        navigationWindow.window.location.href = url;
	        
	     }
	},
	
	G2_FormNavigate : function (windowObj, url)
	{
	    windowObj.IsNavigating = true;
	    var navForm = window.document.createElement("FORM");
	    navForm.method = "get";
	    var urlPair = url.toString().split('?');
	    var navUrl = urlPair[0];
	    if (urlPair.length > 1)
	    {
            var query = urlPair[1];
            queryStringKeys = new Array();	
            queryStringValues = new Array();
	        var pairs = query.split("&");
        	for (var i=0; i < pairs.length; i++)
            {
	            var pos = pairs[i].indexOf('=');
	            if (pos >= 0)
	            {
		            var argname = pairs[i].substring(0,pos);
		            var value = pairs[i].substring(pos+1);
		            var input = window.document.createElement('INPUT');
		            input.name = argname;
		            input.value = value;
		            input.type = 'hidden';
		            input.style.display = 'none';
		            navForm.appendChild(input);
	            }
             }
        }
    	windowObj.document.body.appendChild(navForm);
	    navForm.action = navUrl;
	    navForm.submit();
	},
	
	G2_Warn : function(sender, msg)
	{
		G2_Trace(sender, "************************************");
		G2_Trace(sender, msg);
		G2_Trace(sender, "************************************");
	},

	G2_Trace : function(sender, msg)
	{
		var id = null;
		if(sender!=null)
		{
			id = sender.id!=null ?  sender.id : sender.toString();
		}
		var now = new Date();
		var time = Date_ToString(now, "HH:mm:ss:ff");
		Debug.writeln(time+", "+id+": "+msg);
	},

	//New version by Alon.
	G2_GetData : function(url, callback, errorCallback)
	{
		url = encodeURI(url); //added by dan-el - when url has querystring arguments that contains chinese (for example) - will only work with encoding.
		if (isIE && window.ActiveXObject)
		{
			xmlhttp = new ActiveXObject("Microsoft.XMLHTTP");
			if (xmlhttp!=null)
			{
				xmlhttp.onreadystatechange=function()
				{
					var x = xmlhttp.readyState;
					var y = xmlhttp.readyState;
					if(x==y)
					{
					}
					// if xmlhttp shows "loaded"
					if (xmlhttp.readyState==4)
					{
						// if "OK"
						if (xmlhttp.status==200)
						{
							callback(xmlhttp);
						// ...some code here...
						}
						else
						{
							errorCallback(xmlhttp);
						}
					}
				}
				xmlhttp.open("GET",url,true);
				xmlhttp.send(null);
			}
		} 
		else if (window.XMLHttpRequest)
		{
			try
			{
				var xmlhttp=new XMLHttpRequest();
				xmlhttp.open("GET",url,false);
				xmlhttp.send(null);
				callback(xmlhttp);		
			} 
			catch(everything)
			{
			  if (G2_Trace!=null)
			  {
				  G2_Trace("G2_GetData", everything.description);
				}
				errorCallback(xmlhttp);
			}
		} 
		else
		{
			alert("Your browser does not support XMLHTTP.");
		}
	},

	//function G2Page_Wait()
	//{
	//  setTimeout("G2Page_Wait_Timeout();",150);
	//}

	//function G2Page_Wait_Timeout()
	//{
	//  if(!Page_IsValid)
	//   return;
	//  var hf = document.getElementById("G2_WaitingImage");
	//  if(hf.value!="")
	//  {
	//    var img = document.getElementById(hf.value);
	//    img.style.display = "block";
	//    var srcWas = img.src;
	//    img.src = "";
	//    img.src = srcWas;
	//  }
	//}

	G2_IsInPopup : function()
	{
		try
		{
			parentDoc = parent.document;
			return (parentDoc!=null && parentDoc!=document)
		} 
		catch(everything)
		{	
			G2_Trace("IsInPopup", everything.description);
			Debug.writeln("IsInPopup() FAILED");
			return false;
		}  
	},


	//now registered inline from g2page.cs
	//function G2Page_Init()
	//{
	//	G2_AttachEvent(window, "onload", G2Page_OnLoad);
	//}


	//Unless explicitly specified, resizing is DISABLED until page is loaded.
	//When the page is loaded, the auto-size feature is enabled
	G2Page_OnLoad : function()
	{
	//	G2_DetachEvent(window, "onload", G2Page_OnLoad);
		G2_PreventInputPost("G2_OnLoadStatement");
		var s = document.getElementById("G2_OnLoadStatement");
		enableResizing = true;
		if(s!=null)
		{
			eval(s.value);
		}	
		if (G2_IsInPopup())
		{
			G2Dialog_Init();
		}
	},

	G2_FirePopupClosed : function(popupID, popupResult, silent, uniqueId)
	{
		if (uniqueId!=null)
			popupID = popupID + "###"+uniqueId;
		var hf1 = document.getElementById('__PopupWindowID');
		var hf2 = document.getElementById('__PopupResult');
		hf1.value = popupID;
		hf2.value = popupResult;
		G2.notifyInputChanged(hf1);
		G2.notifyInputChanged(hf2);
		__doPostBack('__Page','G2PopupClosed',silent);  
	},

	G2HtmlFrame_Init : function(iframeId, targetElementId, tooltipKey, autoSize)
	{
		if(tooltipKey!=null && tooltipKey!="")
		{
			G2Tooltips[tooltipKey] = iframeId;
		}
		if(targetElementId!="")
		{
			var target = document.getElementById(targetElementId);
			var iframe = document.getElementById(iframeId);
			target._tooltipFrame = iframe;
			iframe.style.position="absolute";
	    
			target.onmouseover=function()
			{
				x = event.clientX + document.body.scrollLeft;
				y = event.clientY + document.body.scrollTop;
				this._tooltipFrame.style.pixelLeft = x;
				this._tooltipFrame.style.pixelTop = y;
				this._tooltipFrame.style.display = "block";
			}
			target.onmouseout=function()
			{
				this._tooltipFrame.style.display = "none";
			}
		}
		
		if(autoSize)
			window.setTimeout(function() { G2FrameManager.registerFrame(iframeId); }, 0);
	},

	G2ShowTooltip : function(target, tooltipKey,event)
	{
		var iframeId = G2Tooltips[tooltipKey];
		var iframe = document.getElementById(iframeId);
		if (!iframe)
			return;
		if (!event)
			event = window.event;
		G2ShowTooltipElement(target, iframe,event);
	},
	
  G2ShowTooltipElement : function(targetElement, tooltipElementOrId,e)
  {
	  if (!e)
		  e = window.event;
  		
	  if(typeof(tooltipElementOrId)=="string")
	   el = document.getElementById(tooltipElementOrId);
	  else
	   el = tooltipElementOrId;
  	 
	  G2PopupManager.showTooltipStart(targetElement, el,e);
  },  

	Date_Parse : function(strDate)
	{
		var date = new Date(strDate);
		if(isNaN(date))
			return null;
		return date;
	},



	//------- G2 Utils -----------------------------------------------------------
	//UNUSED
	G2SyncTables : function(tbl1ID,tbl2ID)
	{
		var table1 = document.getElementById(tbl1ID);
		var table2 = document.getElementById(tbl2ID);

		if(table1==null || table2==null)
			return;
		var tbl1AmoutOfRows= table1.rows.length;
		var tbl2AmoutOfRows= table2.rows.length;
		var minRowSize=0;


		if(tbl1AmoutOfRows>tbl2AmoutOfRows)
			minRowSize= tbl2AmoutOfRows;
		else 
			minRowSize= tbl1AmoutOfRows;
	    
		var i =0;
		var j =0;
		var minColSize=0;
		if(table1.rows[0].cells.length <table2.rows[0].cells.length)
			minColSize=table1.rows[0].cells.length;
		else 
			minColSize=table2.rows[0].cells.length;
	    
		while(i<minRowSize){
				j=0;
				while(j<minColSize){
									if(table1.rows[i].cells[j].style.width<table2.rows[i].cells[j].style.width)
										table1.rows[i].cells[j].style.width=table2.rows[i].cells[j].style.width;
									else
										table2.rows[i].cells[j].style.width=table1.rows[i].cells[j].style.width;
								 j=j+1;
				}
			i=i+1;
		}
	},

	String_ToInt : function(text)
	{
		if(text==null || text.length==0)
			return null;
		text = String_TrimLeft(text, "0");//because of js bug: parseInt('08') returns 0 as a result
		if(text.length==0)
			return 0;
		var x = parseInt(text);
		if(isNaN(x))
			return null;
		return x;
	},

	String_TrimLeft : function(text, trimChar)
	{
		while(text.length>0 && text.charAt(0)==trimChar)
		{
			text = text.substr(1, text.length-1);
		}
		return text;
	},

	Select_FindByValue : function(select, value)
	{
		for(var i=0;i<select.options.length;i++)
		{
			if(select.options[i].value==value)
				return select.options[i];
		}
		return null;
	},

	Select_IndexOfValue : function(select, value)
	{
		for(var i=0;i<select.options.length;i++)
		{
			if(select.options[i].value==value)
				return i;
		}
		return null;
	},
	Select_ContainsValue : function(select, value)
	{
		return Select_IndexOfValue(select, value)!=null;
	},

	//
	// returns the index of the first occurance of a specific item in an array
	//
	Array_IndexOf : function(array, value)
	{
		for(var i=0;i<array.length;i++)
		{
			if(array[i]==value)
				return i;
		}
		return -1;
	},
	G2_findPreviousControl : function(ctrl , tagName)
	{
		while (ctrl!=null && ctrl.tagName!=tagName)
		{
			if (ctrl.previousSibling==null)
				ctrl = ctrl.parentElement;
			else
				ctrl = ctrl.previousSibling;
		}
		return ctrl;

	},

	G2_getDayName : function(year , month , day)
	{
		var dDate = new Date();
		dDate.setFullYear(year,month-1,day);
		return weekDays[dDate.getDay()];
	},


	DateRange_GetDays : function(dateRange, hoursToAdd)
	{
		return DateRange_GetNights(dateRange, hoursToAdd)+1;
	},

	DateRange_GetNights : function(dateRange, hoursToAdd)
	{
		//case 7606: in case of date range over Summertime trnsition (start date in summertime 
		//and end date in regulare time or the other way around)
		dateRange = dateRange + hoursToAdd*1000*60*60;
		return Math.ceil(dateRange/(24*60*60*1000));
	},

	DateRange_GetYears : function(dateRange)
	{
		return dateRange/(365*24*60*60*1000);
	},

	Date_AddHours : function(date,hours) 
	{
		return new Date(date.getFullYear(), date.getMonth(), date.getDate(), date.getHours() + hours, date.getMinutes(), date.getSeconds());
	},

	Date_AddDays : function(date,days) 
	{
		return new Date(date.getFullYear(), date.getMonth(), date.getDate()+days, date.getHours(), date.getMinutes(), date.getSeconds());
	},

	Date_SubtractDays : function(date,days) 
	{
		return new Date(date.getFullYear(), date.getMonth(), date.getDate()-days, date.getHours(), date.getMinutes(), date.getSeconds());
	},

	Date_ToDotNetString : function(date) 
	{
		return Date_ToString(date, "MM-dd-yyyy");
	},

	Date_VerifyLeadingZero : function(str)
	{
		if(str.length==1)
			str = "0"+str;
		return str;
	},

	///Parses a string like 'Aug' or '8' or '08' into the month number (not javascript month)
	///and returns it - like 8 in this case
	Date_ParseMonth : function(text)
	{
		var month = Array_IndexOf(Date_ShortMonthNames, text);
		if(month!=-1)
		{
			return month+1;
		}
		
		month = String_ToInt(text);
		return month;
	},

	Number_Extension : function(str)
	{
			var lastDigit = str.charAt(str.length-1);
			var last = parseInt(lastDigit);
			var prev = 0;
			if (str.length >= 2) 
			{
				var prevDigit = str.charAt(str.length-2);
				prev = parseInt(prevDigit);
			}
			
			if (prev != 1) //When the number doesn't end with 11, 12 or 13, the extension is according the last digit
			{
				if (last == 1)
					return "st";
				else if (last == 2)
					return "nd";
				else if (last == 3)
					return "rd";
				else
				 return "th"; // 0, 4, 5, 6, 7, 8 and 9
			}
			else //When the number ends with 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, when the tenth digit is 1
				return "th"; 
			
	},

	Number_Format : function(number, format)
	{
		if(format=="#")
		{
			return number.toString();
		}
		else if(format=="##")
		{
			var s = number.toString();
			while(s.length<2)
			{
				s = "0"+s;
			}
			return s;
		}
		else if(format=="##xx")
		{
			var s = Number_Format(number, "##");
			var ext = Number_Extension(s);
			s += ext;
			return s;
		}
		else if(format=="#xx")
		{
			var s = Number_Format(number, "#");
			var ext = Number_Extension(s);
			s += ext;
			return s;
		}
		throw new Error("number format is not supported");
	},

	//
	// Formats a javascript Date object to string in a manner similar to .net framework.
	// currently supports: day, month, year, hour, minute,
	// seperators: '/', ':'
	//
	Date_ToString : function(date, format) 
	{
		if(date==null)
			return "";
			
		if(format=="H")
		{
			return date.getHours().toString();
		}
		else if(format=="HH")
		{
			return Date_VerifyLeadingZero(date.getHours().toString());
		}
		else if(format=="m")
		{
			return date.getMinutes().toString();
		}
		else if(format=="mm")
		{
			return Date_VerifyLeadingZero(date.getMinutes().toString());
		}
		else if(format=="s")
		{
			return date.getSeconds().toString();
		}
		else if(format=="ss")
		{
			return Date_VerifyLeadingZero(date.getSeconds().toString());
		}
		else if(format=="ff")
		{
			return Date_VerifyLeadingZero(date.getMilliseconds().toString());
		}
		else if(format=="d")
		{
			return date.getDate().toString();
		}
		else if(format=="dxx")
		{
			var day = date.getDate();
			var s = Number_Format(day, "#xx");
			return s;
		}
		else if(format=="dd")
		{
			return Date_VerifyLeadingZero(date.getDate().toString());
		}
		else if(format=="ddxx")
		{
			var day = date.getDate();
			var s = Number_Format(day, "##xx");
			return s;
		}
		else if(format=="M")
		{
			return (date.getMonth()+1).toString();
		}
		else if(format=="MM")
		{
			return Date_VerifyLeadingZero((date.getMonth()+1).toString());
		}
		else if(format=="MMM")
		{
			return Date_ShortMonthNames[date.getMonth()];
		}
		else if(format=="MMMM")
		{
			return Date_MonthNames[date.getMonth()];
		}
		else if(format=="y")
		{
			throw new Error("'y' is not a valid datetime format");
		}
		else if(format=="yy")
		{
			var str = date.getFullYear().toString();
			if(str.length==4)
				str = str.substr(2, 2);
			return str;
		}
		else if(format=="yyyy")
		{
			return date.getFullYear().toString();
		}
		else if(format.search(":")!=-1)
		{
			return _Date_ToString(date, format, ":");
		}
		else if(format.search("/")!=-1)
		{
			return _Date_ToString(date, format, "/");
		}
		else if(format.search("\\\\")!=-1)
		{
			return _Date_ToString(date, format, "\\");
		}
		else if(format.search("-")!=-1)
		{
			return _Date_ToString(date, format, "-");
		}
		else if(format.search(" ")!=-1)
		{
			return _Date_ToString(date, format, " ");
		}
		else if(format.search(".")!=-1)
		{
			return _Date_ToString(date, format, ".");
		}
		else
			throw new Error("date format is not supported");
	},

	//	var myDate = new Object();
	//	myDate.Day = date.getDate();
	//	myDate.Month = date.getMonth()+1;
	//	myDate.Year = date.getFullYear();
	//	myDate.ShortYear = date.getYear();

	//	if(format=="dd/MM/yy")
	//	{
	//		var s = (myDate.Day+"/"+myDate.Month+"/"+myDate.ShortYear);//.getDate()+"-" + date.getMonth()+1)+"-" + date.getFullYear();
	//		return s;
	//	}

	_Date_ToString : function(date, format, seperator)
	{
		var str="";
		var tokens = format.split(seperator);
		for(var i=0;i<tokens.length;i++)
		{
			var token = tokens[i];
			if(token!=null && token.length>0)
				str += Date_ToString(date, token);
			if(i!=tokens.length-1) //if not last, add seperator
				str += seperator;
		}
		return str;
	},


	// -------------------------------------------------------------------
	// autoComplete (text_input, select_input, ["text"|"value"], [true|false])
	//   Use this function when you have a SELECT box of values and a text
	//   input box with a fill-in value. Often, onChange of the SELECT box
	//   will fill in the selected value into the text input (working like
	//   a Windows combo box). Using this function, typing into the text
	//   box will auto-select the best match in the SELECT box and do
	//   auto-complete in supported browsers.
	//   Arguments:
	//      field = text input field object
	//      select = select list object containing valid values
	//      property = either "text" or "value". This chooses which of the
	//                 SELECT properties gets filled into the text box -
	//                 the 'value' or 'text' of the selected option
	//      forcematch = true or false. Set to 'true' to not allow any text
	//                 in the text box that does not match an option. Only
	//                 supported in IE (possible future Netscape).
	// -------------------------------------------------------------------
	G2DropDown_AutoComplete  : function(field, select, property, forcematch) 
	{
		var found = false;
		for (var i = 0; i < select.options.length; i++) {
		if (select.options[i][property].toUpperCase().indexOf(field.value.toUpperCase()) == 0) {
			found=true; break;
			}
		}
		if (found) { select.selectedIndex = i; }
		else { select.selectedIndex = -1; }
		if (field.createTextRange) 
		{
			if (forcematch && !found) 
			{
				field.value=field.value.substring(0,field.value.length-1); 
				return;
			}
			var cursorKeys ="8;46;37;38;39;40;33;34;35;36;45;";
			if (cursorKeys.indexOf(event.keyCode+";") == -1) 
			{
				var r1 = field.createTextRange();
				var oldValue = r1.text;
				var newValue = found ? select.options[i][property] : oldValue;
				if (newValue != field.value) 
				{
					field.value = newValue;
					var rNew = field.createTextRange();
					rNew.moveStart('character', oldValue.length) ;
					rNew.select();
				}
			}
		}
	},

	Select_SetValue : function(select, value, suppressOnChangeEvent)
	{
		select.value = value;
		if(!suppressOnChangeEvent)
			G2_FireEvent(select, "onchange");
	},

	String_PadEnd : function(src, count, paddingChar)
	{
		if(paddingChar==null)
			paddingChar=" ";
		var s="";	
		for(var i=0;i<count;i++)
		{
			s+=paddingChar;
		}
		return src+s;
	},


	String_InsertAt : function(src, index, value)
	{
		var s1 = src.substr(0, index);
		var s2 = src.substr(index, src.length-index);
		return s1+value+s2;
	},

	String_RemoveAt : function(src, index)
	{
		var s1 = src.substr(0, index);
		var s2 = src.substr(index+1, src.length-index+1);
		return s1+s2;
	},

	String_RemoveAll : function(src, search)
	{
		var tokens = src.split(search);
		var s = "";
		for(var i=0;i<tokens.length;i++)
		{
			s+=tokens[i];
		}
		return s;
	},
	
	String_StartsWith : function(text, start)
	{
		if(start.length>text.length)
			return false;
		for(var i=0;i<start.length;i++)
		{
			if(start.charAt(i)!=text.charAt(i))
				return false;
		}
		return true;
	},

	G2_CopyArray : function(sourceArray, startIndex)
	{
		if(startIndex==null)
			startIndex = 0;
		var array = new Array();
		array.length = sourceArray.length-startIndex;
		var j=0;
		for (var i=startIndex;i<sourceArray.length;i++)
		{
			array[j] = sourceArray[i];
			j++;
		}
		return array;
	},

	G2_ShowControl : function(control, useVisibility)
	{
		if(useVisibility)
		{
			control.style.visibility = "visible";
		}
		else
		{
			control.style.display = "";//FOLLOWUPDAN-EL

		}
		if(typeof(control.OnShow)!="undefined")
		{
			control.OnShow();
		}
		return true;
	},
	
	G2_IsElementVisible : function(element, checkParents)
  {
	  if(element.style && element.style.display=="none")
		  return false;
	  if(checkParents)
	  {
		  if(element.parentElement!=null)
			  return G2_IsElementVisible(element.parentElement, checkParents);
		  else
		      if (isMoz) //Moz has a parent for the documentElement (html tag)
		          return element instanceof Document;
		      else
			      return element==element.document.documentElement; //only when element reaches to the top doc element we can be (pretty) sure it's visible.
  			
	  }
	  return true;
  },

	G2_HideControl : function(control, useVisibility)
	{
 		if(useVisibility)
		{
			control.style.visibility = "hidden";
		}
		else
		{
			control.style.display = "none";
		}
		if(typeof(control.OnHide)!="undefined")
		{
			control.OnHide();
		}
		return false;
	},
	G2_ToggleElementVisibility : function(element)
	{
		if(element==null)
			return; //TODO: warn
		if(element.style.display=="none")
			G2_ShowControl(element);
		else
			G2_HideControl(element);
	},

	G2_ShowHideControl : function(control, show, useVisibility)
	{
		if(show)
		{
			return G2_ShowControl(control, useVisibility);
		}
		else
		{
			return G2_HideControl(control, useVisibility);
		}
	},

	G2Page_ErrorCallback : function(message)
	{
		alert('An error occurred on the server:\n' + message);
	},

	G2_RecursiveSetPropertyValue : function(rootElement, propertyName, value)
	{
		if(rootElement.nodeName!="#text" && rootElement[propertyName]!=value)
		{
			rootElement[propertyName] = value;
		}
		var rootElementChildren = rootElement.children;
		for(var i=0;i<rootElementChildren.length;i++)
		{
			var child = rootElementChildren[i];
			G2_RecursiveSetPropertyValue(child, propertyName, value);
		}
	},

	//----------------------------------------------------------------------	

	G2_GetY : function(element)
	{
		var y = 0;
		while( element != null ) 
		{
			y += parseInt(element.offsetTop);
			
			// taking into account scrooling with in overflow scroll elements
			if(element.tagName != 'HTML' && element.scrollTop != null)
				y -= element.scrollTop;
			if(element.tagName == 'IFRAME')
				y -= document.documentElement.scrollTop;
			
			element = element.offsetParent;
		}
		return y;
	},

	G2_GetX : function(element)
	{
		var x = 0;
		while( element != null ) 
		{
			x += parseInt(element.offsetLeft);
			element = element.offsetParent;
		}
		return x;
	},

	G2Validator_ValidateElementOnChange : function(element)
	{
		if(element!=null && element.Validators!=null)
		{
			var dummyEvent = new Object();
			dummyEvent.srcElement = element; //IE
			dummyEvent.target = element; //FF
			ValidatorOnChange(dummyEvent);
		}
	},

	//---------------------------------------------

	isFixedPositioned : function(elem)
	{
		while (elem!=null)
		{
			if (elem && elem.style && elem.currentStyle.position == "fixed")
				return true;
			elem = elem.parentElement;
		}
		return false;
	},

  G2_BringToFront : function(elementToFloat)
	{
	  //marked by dan-el elementToFloat.style.zIndex = G2_maxZ++;
	},
	
	G2_FloatElement : function(elementToFloat, positionElement, dir, useFrame,useFixedPositioning)
	{
		//G2_Trace("G2_FloatElement", "start");
		var parent = elementToFloat.parentElement;
		if(parent!=null)
		{
			parent.removeChild(elementToFloat);
		}
		document.body.appendChild(elementToFloat);
		elementToFloat.style.position = useFixedPositioning ? "fixed" : "absolute";
		G2_BringToFront(elementToFloat);
		//this.bringElementToFront(elementToFloat);
		var N=(dir.indexOf("N")>-1);
		var S=(dir.indexOf("S")>-1);
		var E=(dir.indexOf("E")>-1);
		var W=(dir.indexOf("W")>-1);
		if(!N && !S)
			S=true;
		if(!E && !W)
		{
			E=true;
		}
		
		var x = G2_GetX(positionElement);
		var y = G2_GetY(positionElement);

	  
		if (S)
			y += positionElement.offsetHeight;
		if (W)
			x += positionElement.offsetWidth;
		elementToFloat.style.pixelTop = y;
		elementToFloat.style.pixelLeft = x;
	  
		elementToFloat.style.display = "block";
	  
		//iframe is the only one that can hide select tags in IE
		if(useFrame) 
		{
			window.setTimeout(function(){G2_AttachFrame(elementToFloat,useFixedPositioning);}, 0);
		}
 		//G2_Trace("G2_FloatElement", "end");
	},

	G2_HideFloatingElement : function(targetElement)
	{
		G2_DetachFrame(targetElement);
		targetElement.style.display = "none";
	},
	G2_CreateIFrame : function(doc, frameBorder, scrolling)
	{
		doc = doc || document;
		var frame = doc.createElement("IFRAME");
		if(frameBorder==null)
			frameBorder = 0;
		frame.frameBorder = frameBorder.toString();
		if(scrolling!=null)
			frame.scrolling = scrolling ? "yes" : "no";
		
		// validate body exist
		var body = doc.body;
		if(body == null)
		  body = document.body;
		  
		body.appendChild(frame);
		var frameDoc = frame.contentWindow.document;
		frameDoc.open();
		frameDoc.write("<html><body></body></html>");
		frameDoc.close();
		body.removeChild(frame);
		return frame;
	},
	G2_AttachFrame : function(targetElement,useFixedPositioning)
	{
		if(!IE6)
			return;
		//G2_Trace("G2_AttachFrame", "start");

		if(G2_FixFrame==null)
		{
			G2_FixFrame = G2_CreateIFrame(targetElement.document, 0, false);
			G2_FixFrame.setAttribute("id", "fixFrame");
			targetElement.insertAdjacentElement("beforeBegin", G2_FixFrame);
		}
	  
		//TODO: some of the size properties causes performance overhead of about a second
		G2_FixFrame.style.position = useFixedPositioning ? "fixed" : "absolute";
		G2_FixFrame.style.width = targetElement.offsetWidth+"px";
		G2_FixFrame.style.height = targetElement.offsetHeight+"px";
		G2_FixFrame.style.top = G2_GetY(targetElement)+"px";
		G2_FixFrame.style.left = G2_GetX(targetElement)+"px";
		//G2_FixFrame.style.zIndex = targetElement.currentStyle.zIndex - 1;
		G2_FixFrame.style.display = "block";
		targetElement._popupFixFrame = G2_FixFrame;
		targetElement.onresize = function()
		{
			this._popupFixFrame.style.width = this.offsetWidth+"px";
			this._popupFixFrame.style.height = this.offsetHeight+"px";
		}
		targetElement.onmove = function()
		{
			this._popupFixFrame.style.pixelTop = this.offsetTop;
			this._popupFixFrame.style.pixelLeft = this.offsetLeft;
		}
 		//G2_Trace("G2_AttachFrame", "end");
	},
	G2_DetachFrame : function(targetElement)
	{
		if(!IE6)
			return;
		if(targetElement._popupFixFrame==null)
			return;
		targetElement._popupFixFrame.style.display = "none";
		targetElement._popupFixFrame = null;
		//G2_FixFrame.style.display = "none";
		targetElement.onresize = null;
		targetElement.onmove = null;
	},

	//added by rony - for validation control re evaluation.
	G2ReEvaluateValidationControl : function(validationControl) {
			Page_InvalidControlToBeFocused = null;
			if (typeof(Page_Validators) == "undefined") {
					return true;
			}
			validationControl.isvalid = true;
			if (typeof(validationControl.enabled) == "undefined" || validationControl.enabled != false) {
					if (typeof(validationControl.evaluationfunction) == "function") {
							validationControl.isvalid = validationControl.evaluationfunction(validationControl);
							if (!validationControl.isvalid && Page_InvalidControlToBeFocused == null &&
									typeof(validationControl.focusOnError) == "string" && validationControl.focusOnError == "t") {
									ValidatorSetFocus(validationControl, event);
							}
					}
			}
			ValidatorUpdateDisplay(validationControl);
	},

	/*
	resizing the hieght for the outer ifram element from a current page
	*/

	FixOuterIFramHight : function(){
		//FixIFrameHeight(window.frameElement.id);
		var iframe = window.frameElement;
		if (iframe.addEventListener)
		{
			iframe.addEventListener("load", readjustIframe, false);
		}
		else if (iframe.attachEvent)
		{
			iframe.attachEvent("onload", readjustIframe);
		}
		iframe.style.display = "";
	},
	/*
	Resizing IFrame dynamically
	Addaed by Arnon 21.10.06
	*/


	FixIFrameHeight : function(iframeId,doc,dontUseEvents)
	{
		if (doc==null)
			doc = document;			  
			
		if (dontUseEvents==null)
			dontUseEvents = false;

		var iframe = doc.getElementById(iframeId);
		
		if (iframe==null)
			return;
			
		if (iframe.addEventListener)
		{
			iframe.addEventListener("load", readjustIframe, false);
		}
		else if (iframe.attachEvent && !dontUseEvents)
		{
			iframe.attachEvent("onload", readjustIframe);
		} 
		else 
			readjustIframe({currentTarget:iframe});
		iframe.style.display = "";
	},

	readjustIframe : function(loadevt)
	{
		var crossevt=(window.event && window.event.type=="load" )? event : loadevt;
		var iframe=(crossevt.currentTarget)? crossevt.currentTarget : crossevt.srcElement;
		if (iframe)
		{
				iframe.style.height=iframe.Document.body.scrollHeight+"px";
				iframe.style.width=iframe.Document.body.scrollWidth+"px";
		}	
	},

	// Set the iframe flash elements transparent
	fixFlashInIframe : function(iframeId)
	{
		var iframe = document.getElementById(iframeId);
		fixFlashForIframe(iframe);
	},
	
	// Set the flash param wmode to transparent
	fixFlashForIframe : function(iframe)
	{
		G2DOM.SetFlashElementsTransparent(iframe);
		
		var iframes = iframe.Document.getElementsByTagName('iframe');
		for (var i = 0; i < iframes.length; i++) 
		{   
			  fixFlashForIframe(iframes[i]);
		}
	},
	
	// Fix the flash on iframe load
	FixIFrameFlash : function(iframeId)
	{
		var iframe = document.getElementById(iframeId);
		var fixFlash = function()
		{
			fixFlashInIframe(iframeId);
		}
		G2_AttachEvent(window, "onload", fixFlash,false);
	},
	
	FixIFrameSize : function(iframeId)
	{
		var iframe = document.getElementById(iframeId);
		iframe.style.border="0px";
		var onloaded = function()
		{
			readjustIframe({currentTarget:iframe});
		}
		if (iframe.addEventListener)
		{
			iframe.addEventListener("load", onloaded, false);
		}
		else if (iframe.attachEvent)
		{
			iframe.attachEvent("onload", onloaded);
		}
			
		iframe.style.display = "";
	},



	readjustIframeSize : function(loadevt)
	{
		var crossevt=(window.event)? event : loadevt;
		var iframe=(crossevt.currentTarget)? crossevt.currentTarget : crossevt.srcElement;
		if (iframe)
		{
			iframe.style.height=iframe.document.body.scrollHeight+"px";
		//	iframe.style.width=iframe.document.body.scrollWidth+"px";
			iframe.style.border="0px";
		}	
	},
	///*End of Resizing IFrame dynamically*/

	G2_AmntKeyPress : function()
	{
		var key = window.event.keyCode;
		if ((key < 48 || key > 57) && key != 46 && key != 45)
			window.event.keyCode = 0;
	},

	// TextBox: simulate [Tab] key press when number of characters reach maxLength
	G2_AutoSkip : function(thisEl, force,evnt)
	{
		if (force || (thisEl.value.length == thisEl.maxLength && evnt.keyCode != 9 && evnt.keyCode != 16)) 
		{
			nextEl = G2_GetNextElementToSkip(thisEl);
			if (nextEl != null) 
			{
				try {
					nextEl.focus();
					if (nextEl.select)
						nextEl.select();
				}
				catch (e) {}
			}
		}
	},

	// Get next element in tabIndex/creationOrder
	G2_GetNextElementToSkip : function(thisEl)
	{
		var currTabIndex = thisEl.tabIndex;
		var minDiffFromCurrTabIndex = 32767, minTabIndex = 32767;
		var nextCreateOrderEl = null, nextTabOrderEl = null, minTabOrderEl = null, nextEl = null;
		var getNextCreateOrder = false;
		for (var i = 0; i < thisEl.form.elements.length; i++) 
		{
			var element = thisEl.form.elements[i];
			if (element.type != "hidden" && !element.disabled && element.style.display != "none") 
			{
				if (element == thisEl) 
				{
					getNextCreateOrder = true;
				}
				else if (element.tabIndex >= 0)
				{
					// Find element with next creation order
					if (getNextCreateOrder) {
						nextCreateOrderEl = thisEl.form.elements[i];
						getNextCreateOrder = false;
						if (thisEl.tabIndex == 0)
							break;
					}
					if (element.tabIndex > 0) 
					{
						// Find element with next tabIndex
						var diff = element.tabIndex - currTabIndex;
						if (diff > 0) 
						{
							if (diff < minDiffFromCurrTabIndex) 
							{
								minDiffFromCurrTabIndex = diff;
								nextTabOrderEl = element;
							}
						}
					}
					// Find element with min tabIndex
					if (element.tabIndex < minTabIndex) 
					{
						minTabIndex = element.tabIndex;
						minTabOrderEl = element;
					}
				}
			}
		}
		if (thisEl.tabIndex == 0 && nextCreateOrderEl != null && nextCreateOrderEl.tabIndex == 0)
			nextEl = nextCreateOrderEl;
		else if (nextTabOrderEl != null)
			nextEl = nextTabOrderEl;
		else if (minTabOrderEl != null)
			nextEl = minTabOrderEl;
		else
			nextEl = nextCreateOrderEl;
		return nextEl;
	},

	G2Menu_ChangeMouseOver : function(parent)
	{	
		if (typeof(parent)=="string")
			parent = document.getElementById(parent);
		if (parent==null)
			return;
		var element = parent.firstChild;
		while(element!=null)
		{
			if(element.onmouseover!=null)
			{
				if(element.onmouseover!=null)
				{
					var func = element.onmouseover;
					element.onmouseover = null;	
					G2_AttachEvent(element, "onclick",function(e)
					{
						Menu_HoverStatic(this);
						e.cancelBubble = true;
					});
				}
			}
			if(element.style!=null && element.style.cursor!="hand")
			{
				element.style.cursor = "hand";
			}
			G2Menu_ChangeMouseOver(element);
			element = element.nextSibling;
		}
	},



	G2Menu_ChangeMouseOver_Old : function(targetElement) //new implementation by dan-el
	{
		var curEl = targetElement.firstChild;
		var firstLevelFound = false;
		while(curEl!=null)
		{
			if(!firstLevelFound && curEl.onmouseover!=null)
				firstLevelFound = true;
	      
			if(firstLevelFound)
			{
				curEl.onclick = function()
				{
					Menu_HoverStatic(this);
					event.cancelBubble = true;
					//return false;
				};
				//Yucki!
				var aa = curEl.getElementsByTagName("A");
				var a= null;
				if(aa.length>0)
					a = aa[0];
	      
				var nolink = "javascript:void(0)";
	        
				if(a!=null && a.href!=nolink)
				{
					if(a.href.indexOf("javascript:")>-1)
					{
						a.href = nolink;//Fix for case 4457. (nolink was: #)
					}
					else if(a.href.lastIndexOf("#") == a.href.length-1)
					{
						a.href = nolink; //Fix for case 4457. (nolink was: #)
					}
				}
	      
				curEl.onmouseover=null;
				curEl.ondeactivate = function(){Menu_Unhover(this);};
				curEl.onmouseout = null;
				//alert("before: " + curEl.style.cursor);
				curEl.style.cursor = "hand";
				if(a!=null)//TODO: Bug - Gilad
					a.style.cursor = "hand";
				//alert("after: " + curEl.style.cursor);
			}
			curEl = curEl.nextSibling;
		}
	  
		if(firstLevelFound)
			return true;
	  
		curEl = targetElement.firstChild;
		while(curEl!=null)
		{    
			//if (curEl.onmouseover!=null)
			//{
				G2Menu_ChangeMouseOver(curEl);
				curEl.onmouseover=null;    
			//}
			curEl = curEl.nextSibling;
		}
	},

	G2ConfirmBox_Show : function(text, eventTarget)
	{
		var eventArgument = confirm(text);
		__doPostBack(eventTarget, eventArgument);
	},

	//
	// findRel Usage:
	//
	// findRel( tag , "style.display == 'none'", G2GetParent )
	// This will find the nearest hidden tag in the hierarchy (moving up)
	// third parameter must be a function, like function(t){return t.nextSibling;} 
	findRel : function(node, predicate, nav)
	{
		if (typeof(predicate)=="string")
			eval("var compiledPredicate = function(){ return this."+predicate+";}");
		else
			compiledPredicate = predicate;

		try
		{
			while (node!=null)
			{			
				if (compiledPredicate.call(node))
					return node;
					
				node = nav(node);			
			}
		} 
		catch(e)
		{
		}
		return null;
	},

	$ : function( a )
	{
		return document.getElementById(a);
	},
		
	EventAttr : function(name)
	{
		if (event.srcElement.attributes[name] == null)
		{
			if (event.srcElement.parentElement.attributes[name] == null)
				return "";
				
			return event.srcElement.parentElement.attributes[name].nodeValue;
		}
			
		return event.srcElement.attributes[name].nodeValue;
	},

	G2Page_ShowWaiting : function()
	{
		//alert('waiting');
	},

	G2Page_ShowReady : function()
	{
		//alert('ready');
	},

	/**************************************************************************
	 *
	 * Popups and related functions
	 *
	 **************************************************************************/

	G2PopupWindow_ExtractParameter : function(features, paramname, defaultValue)
	{
		var poz = features.indexOf(paramname);
		if (poz==-1)
			return defaultValue;
		
		var f = features.substring(poz+paramname.length+1);
		poz = f.indexOf(';');
		var poz2 = f.indexOf(',');
		if (poz2!=-1 && poz ==-1)
			poz = poz2;
		if (poz!=-1)
			f = f.substring(0,poz);
		poz = f.indexOf('px');
		if (poz!=-1)
			f = f.substring(0,poz);
		return f;
		
	},

	// Modal Dialog Box  from http://www.eggheadcafe.com/articles/javascript_modal_dialog.asp
	/*
	var ModalDialogWindow;
	var ModalDialogInterval;
	var ModalDialog = new Object;

	ModalDialog.value = '';
	ModalDialog.eventhandler = '';

	function ModalDialogMaintainFocus()
	{
		try
		{
			if (ModalDialogWindow.closed)
			 {
					window.clearInterval(ModalDialogInterval);
					eval(ModalDialog.eventhandler);       
					return;
			 }
			ModalDialogWindow.focus(); 
		}
		catch (everything) {   }
	}

	function ModalDialogRemoveWatch()
	 {
			ModalDialog.value = '';
			ModalDialog.eventhandler = '';
	 }
	*/

	//This method is used to overcome google toolbar's popup blocker
	G2ExecuteSync : function(f)
	{
		var temporaryButton = G2DOM.G2CreateElement("<input type='Button' style='display:none'></input>");
			temporaryButton.id = temporaryButton.uniqueID;
			temporaryButton.onclick = f;
			document.body.appendChild(temporaryButton);
			temporaryButton.click();
			document.body.removeChild(temporaryButton);
	},

	ModalDialogShow : function(url,name,features,w,h,wndargs)
	{
		var me = window;
		var fullPath = G2_MapPath("~/Client/Dialog.aspx");
		if (IE6 && wndargs.title && wndargs.title!="")
		{
		fullPath += "?Title="+encodeURI(wndargs.title);
		wndargs.title=null;
		}
		//The following is a hack to run a function synchronously using a temporary hidden button   
		function ie_f()
		{
				return null!= window.showModalDialog(fullPath,wndargs,features);//{url:url,obj:me,width:w,height:h}, features);
		}
		function moz_f()
		{	
			var t =  window.open(fullPath,"G2POPUP","modal,"+features);//{url:url,obj:me,width:w,height:h}, features);				
			if (t!=null)
			{
				t.dialogArguments = wndargs;
				t.focus();
			}
			return null!=t;
		}
		if (isIE)
			G2ExecuteSync(ie_f);
		else
			moz_f();
	},


  G2_GetWindowId : function()
  {
    var el = document.getElementById('__WindowID');
    if(el==null)
      return null;
    return el.value
  },
  G2_CreateTable : function(rows, cols, onTopWindow, cellPadding, cellSpacing)
  {
    
		if (onTopWindow)
		{ 
			var win = GetTopAvailableWindow();
			var doc = win.document;
		}
		else
			var doc = document;
		
    
		cellPadding = cellPadding || 0;
		cellSpacing = cellSpacing || 0;
		var table = doc.createElement("table");
		table.cellPadding = cellPadding;
		table.cellSpacing = cellSpacing;
		for(var i=0;i<rows;i++)
		{
			var row = table.insertRow();
			for(var j=0;j<cols;j++)
			{
				var cell = row.insertCell();
			}
		}
		return table;
  },
  
	G2PopupWindow_Open : function(url, context, modal, name, features, title, uniqueID)
	{	
		if (features==null && context!=null)
		{
			//var h = document.getElementById(context);
			//if(h!=null)
			features = window[context];//h.value;
		}   
		if (modal==null)
			modal = features.indexOf('modal=0') == -1;
		url = url.replace(/\$quot\$/g,"'");		
							
		if(modal)
		{
			var wid = G2_GetWindowId();
			if(wid!=null)
			{
				if (url.indexOf('?') == -1)
					url += "?IsPopup=True";
				else
					url+="&IsPopup=True";
			}
	  	var h = parseInt(G2PopupWindow_ExtractParameter(features,"dialogHeight",""));
			var w = parseInt(G2PopupWindow_ExtractParameter(features,"dialogWidth",""));
			var minH = parseInt(G2PopupWindow_ExtractParameter(features,"dialogMinHeight","0"));
			var minW = parseInt(G2PopupWindow_ExtractParameter(features,"dialogMinWidth","0"));
			var autoSize = parseInt(G2PopupWindow_ExtractParameter(features,"autoSize","1"));
			var synthetic = G2PopupWindow_ExtractParameter(features,"SyntheticPopup","0");
			var fade = G2PopupWindow_ExtractParameter(features,"FadeSyntheticPopup","0");			
			var horzMargin = parseInt(G2PopupWindow_ExtractParameter(features,"HorizontalMargin","5"));
			var vertMargin = parseInt(G2PopupWindow_ExtractParameter(features,"VerticalMargin","5"));
			var scroll = G2PopupWindow_ExtractParameter(features,"scroll","0");
			var closeBtn = G2PopupWindow_ExtractParameter(features,"closeBtn","0");
			var closeClientFunction = G2PopupWindow_ExtractParameter(features,"OnCloseClientFunction","");
			var me = window;
			
			//If title was specified, but not name - copy title to name
			if (title && title!=null && title!="" && !name && (name==null||name==""))
				name=title;
			
			//If name was specified, but not title, copy name to title
			if (!title && (title==null||title=="") && name && name!=null && name!="")
				title=name;
			if (synthetic!="0")	
			{
				window.setTimeout(function(){		//This causes 'Operation Aborted' when showing popups in full postbacks
				var wnd = SyntheticModalDialogShow(url,name,features,h,w,{url:url,obj:me,width:w,height:h,title:title,autoSize:(autoSize=="1"),vertMargin:vertMargin,horzMargin:horzMargin, scroll : (scroll=="1"),closeBtn : (closeBtn=="1"), fade : (fade=="1"), minH : minH, minW : minW, uniqueID : uniqueID, closeClientFunction:closeClientFunction});
				},0);
			}
			else
			{	
				var wnd = ModalDialogShow(url,name,features,h,w,{url:url,obj:me,width:w,height:h,title:title,autoSize:autoSize});
			}
		}
		else
		{
			//Workaround for bug #3634: 
			// IE popup blocker blocked the popup, because it was not initiated by a user click.		
			
			//Note: The following is a workaround for IE popup blockers. It is not jiffacode.
			var temporaryButton = G2DOM.G2CreateElement("<input type='Button' style='display:none'></input>");
			temporaryButton.id = temporaryButton.uniqueID;
			temporaryButton.onclick = function()
			{
				var wnd = window.open(url, name, features);
				
				if (null == wnd)
				{
					alert('popup blocker detected!');
				} 
				else
				{
					if (features.indexOf('maximized=yes')!=-1)
						{
							wnd.moveTo( 0, 0 );
		
							wnd.resizeTo( screen.availWidth, screen.availHeight );
						}
				}
			}
			document.body.appendChild(temporaryButton);
			temporaryButton.click();
			document.body.removeChild(temporaryButton);
		}
	},

	updatePopupTitle : function(newTitle)
	{
		if (G2_IsInPopup() && window.top.document.popup!=null)
		{
			window.top.document.popup.setTitle(newTitle);
		}	
	},

	CreateModalContainer : function(contentid,h,w,title)
	{
			h = parseInt(h);
			w = parseInt(w);
			var marginHeight = (document.body.clientHeight - h) / 2;
			var marginWidth = (document.body.clientWidth - w) / 2;
			
			var containerTable = document.createElement("Table");
						
			//containerTable.id = id;
			containerTable.style.position="absolute";
			containerTable.style.pixelLeft=0;
			containerTable.style.pixelTop=0;
			containerTable.style.width=document.body.clientWidth+"px";
			containerTable.style.height=document.body.clientHeight+"px";
			G2_BringToFront(containerTable);
			containerTable.style.display="none"
			containerTable.style.background="transparent";
			containerTable.style.border="0px";
			containerTable.cellPadding = "0";
			containerTable.cellSpacing = "0";
			
			

			//Top Row
			var topRow = containerTable.insertRow();
			topRow.style.height=marginHeight+"px";
			var topRowCell = topRow.insertCell();
			topRowCell.colSpan = "3";
			topRowCell.className="MessageBoxContainer";
			topRowCell.innerHTML="<div style='background:#ccccee; width:300px'><b>"+title+"</b></div>";
			topRowCell.style.textAlign="center";
			topRowCell.style.verticalAlign="bottom";
			////////////////////////////////////////////////////////////////////////
			
			
			//Middle Row
			var middleRow = containerTable.insertRow();
			middleRow.style.height=w+"px";
			
			
			//Middle-Left
			var middleLeftCell = middleRow.insertCell();
			middleLeftCell.style.width=marginWidth+"px";
			middleLeftCell.style.height=h+"px";
			middleLeftCell.innerHTML="&nbsp;";
			middleLeftCell.className = "MessageBoxContainer";
			
			//Content cell
			var ContentCell = middleRow.insertCell();
			ContentCell.align="center";
			ContentCell.id = contentid;
			ContentCell.valign="middle";
			ContentCell.id = "modalContent";
			ContentCell.style.backgroundColor="white";
			ContentCell.style.width=w+"px";
			ContentCell.style.height=h+"px";
			
			//Middle-Right
			var middleRightCell = middleRow.insertCell();
			middleRightCell.style.width=marginWidth+"px";
			middleRightCell.style.height=h+"px";
			middleRightCell.innerHTML="&nbsp;";		
			middleRightCell.className = "MessageBoxContainer";
			
			////////////////////////////////////////////////////////////////////////
			//Bottom Row
			var bottomRow = containerTable.insertRow();
			bottomRow.style.height=marginHeight+"px";
			var bottomRowCell = bottomRow.insertCell();
			bottomRowCell.colSpan = "3";
			bottomRowCell.className="MessageBoxContainer";
			bottomRowCell.innerHTML="&nbsp;";
			
			return containerTable;
				
	},


	G2PopupWindow_CloseAndRedirect : function(url)
	{
		var parentWindow = window.opener; 
		G2_ClosePopupWindow();
		//window.close();
		parentWindow.location = url;
	},

	min : function(a,b)
	{
		return (a<b) ? a : b;
	},

	max : function(a,b)
	{
		return (a>b) ? a : b;
	},

	minInt : function(a,b)
	{
		var valA = parseInt(a);
		var valB = parseInt(b);
		
		if (isNaN(valA))
			return valB;
		if (isNaN(valB))
			return valA;
		return min(valA,valB);
	},

	maxInt : function(a,b)
	{
		var valA = parseInt(a);
		var valB = parseInt(b);
		
		if (isNaN(valA))
			return valB;
		if (isNaN(valB))
			return valA;
		return max(valA,valB);
	},

	// Removes leading whitespaces
	LTrim : function( value ) 
	{	
		var re = /\s*((\S+\s*)*)/;
		return value.replace(re, "$1");	
	},

	// Removes ending whitespaces
	RTrim : function( value ) 
	{	
		var re = /((\s*\S+)*)\s*/;
		return value.replace(re, "$1");	
	},

	// Removes leading and ending whitespaces
	trim : function( value ) 
	{	
		if (!value || value==null)
			value = this;
		return LTrim(RTrim(value));	
	},

	//----------------------------------------------------------------
	// Source: http://www.xs4all.nl/~zanstra/logs/jsLog.htm
	//----------------------------------------------------------------

	verifyObjectShown : function(obj)
	{
		var t=1;
		if (!InView(obj,5))
		{
			ScrollIntoView(obj,false,5);
			//obj.scrollIntoView(false); //align to bottom -- don't use unlesss previouse method fails (and it shouldn't)
		}
	},

	InView : function(element,margin) 
	{
		if(!margin) margin=0;
		var Top=GetTop(element), ScrollTop=GetScrollTop();
		return !(Top<ScrollTop+margin||
			Top>ScrollTop+GetWindowHeight()-element.offsetHeight-margin);
	},

	ScrollIntoView : function(element,bAlignTop,margin) 
	{
		if(!margin) margin=0;
		var posY = GetTop(element);
		if(bAlignTop) 
			posY -= margin;
		else 
			posY += element.offsetHeight+margin-GetWindowHeight();
		window.scrollTo(0, posY);
	},
	
	GetTopWindowHeight : function() 
	{
		return window.top.innerHeight ||
			window.top.document.documentElement&&window.top.document.documentElement.clientHeight ||
			window.top.document.body.clientHeight || 0;
	},

	GetWindowHeight : function() 
	{
		return window.innerHeight ||
			document.documentElement&&document.documentElement.clientHeight ||
			document.body.clientHeight || 0;
	},
	GetScrollTop : function() 
	{
		return window.pageYOffset ||
			document.documentElement && document.documentElement.scrollTop ||
			document.body.scrollTop || 0;
	},
	GetTop : function(element) 
	{
		var pos=0;
		do 
		{
			pos += element.offsetTop;
		}
		while(element=element.offsetParent);
		return pos;
	},


	////////////////////////////////////////////////////////////
	//        Range and selection relates functions           //
	////////////////////////////////////////////////////////////


	G2_SetSelectionRange : function(input, selectionStart, selectionEnd) 
	{
		if (input.setSelectionRange) 
		{
			input.focus();
			input.setSelectionRange(selectionStart, selectionEnd);
		}
		else if (input.createTextRange) 
		{
			var range = input.createTextRange();
			range.collapse(true);
			range.moveEnd('character', selectionEnd);
			range.moveStart('character', selectionStart);
			range.select();
		} else Debug.writeln('Cannot set selection');
	},

	G2_GetSelectionStartFromRange : function(range) 
	{
		var range = document.selection.createRange();
		var isCollapsed = range.compareEndPoints("StartToEnd", range) == 0;
		if (!isCollapsed)
			range.collapse(true);
		var b = range.getBookmark();
		return b.charCodeAt(2) - 2;
	},
	G2_GetSelectionStart : function(input) 
	{
		if (isGecko)
			return input.selectionStart;
		var range = document.selection.createRange();
		var isCollapsed = range.compareEndPoints("StartToEnd", range) == 0;
		if (!isCollapsed)
			range.collapse(true);
		var b = range.getBookmark();
		return b.charCodeAt(2) - 2;
	},

	G2_GetSelectionEnd : function(input) 
	{
		if (isGecko)
			return input.selectionEnd;
		var range = document.selection.createRange();
		var isCollapsed = range.compareEndPoints("StartToEnd", range) == 0;
		if (!isCollapsed)
			range.collapse(false);
		var b = range.getBookmark();
		return b.charCodeAt(2) - 2;
	},
	G2_SetCaretPosition : function(input, index)
	{
		G2_SetSelectionRange(input, index, 0);
	},

	G2_GetCaretPosition : function(input)
	{
		var range = input.document.selection.createRange();
		var pos = 0;
		while(range.move("character", -1)!=0)
			pos++;
		return pos;
	},



	Find : function(array, predicate, context)
	{
		for(var i=0;i<array.length;i++)
		{
			var item = array[i];
			if(predicate(item, context))
				return item;
		}
		return null;
	},

	//
	//iterates an array, and performs the specified action with the specified context.
	//
	ForEach : function(array, action, context)
	{
		if(array==null || action==null)
			return;
		for(var i=0;i<array.length;i++)
		{
			action(array[i], context);
		}
	},

	ForEachSibling : function(element, action, context, predicate)
	{
		if(element==null)
			return;
		action(element, context);
		var nextSibling = element.nextSibling;
		if (predicate != null)
		{
		    while (nextSibling != null && !predicate(nextSibling))
		        nextSibling = nextSibling.nextSibling;   
		}
		ForEachSibling(nextSibling, action, context, predicate);
	},

	G2_PlaceElementAbsolutlyBeside : function(element, parentElement , position)
	{ 
		element.style.position = "absolute";
		parentElement.document.body.appendChild(element);
		element.style.pixelLeft = G2_GetAbsoluteLeft(parentElement)+parentElement.scrollWidth;
		if(position == "Left")
			element.style.pixelLeft = G2_GetAbsoluteLeft(parentElement)-element.scrollWidth;
		
		element.style.pixelTop = (G2_GetAbsoluteTop(parentElement));
		
		// keep element from exiting screen limits
		G2_VerifyAbsoluteElementNotCropped(element);
	},
	G2_PlaceElementAbsolutlyAbove : function(element, parentElement, position, align)
	{
		element.style.position = "absolute";
		parentElement.document.body.appendChild(element);
		
		if(position == "Left")
			element.style.pixelLeft = G2_GetAbsoluteLeft(parentElement) - element.scrollWidth;
		else
			element.style.pixelLeft = (G2_GetAbsoluteLeft(parentElement));
			
		element.style.pixelTop = G2_GetAbsoluteTop(parentElement)-element.scrollHeight;
		
		// keep element from exiting screen limits
		G2_VerifyAbsoluteElementNotCropped(element);
	},

	G2_PlaceElementAbsolutlyBelow : function(element, parentElement, position)
	{
		element.style.position = "absolute";
		parentElement.document.body.appendChild(element);
		
		if(position == "Left")
			element.style.pixelLeft = G2_GetAbsoluteLeft(parentElement) - element.scrollWidth;
		else
			element.style.pixelLeft = G2_GetAbsoluteLeft(parentElement);
			
		element.style.pixelTop = G2_GetAbsoluteTop(parentElement)+parentElement.scrollHeight;
		
		// keep element from exiting screen limits
		G2_VerifyAbsoluteElementNotCropped(element);
	},
	//pos=T,B,R,L
	G2_GetAbsolute : function(element, pos, includeFrames, posInfo)
	{
		if(pos=="t")
			return G2_GetAbsoluteTop(element, includeFrames, posInfo);
		else if(pos=="l")
			return G2_GetAbsoluteLeft(element, includeFrames, posInfo);
		if(pos=="b")
			return G2_GetAbsoluteBottom(element, includeFrames, posInfo);
		else if(pos=="r")
			return G2_GetAbsoluteRight(element, includeFrames, posInfo);
		return null;
	},
	//pos=t,b,r,l
	G2_SetAbsolute : function(element, pos, value, ignoreCurrentTopAndLeft)
	{
		if(value==null)
			return;
		if(pos=="t")
			element.style.pixelTop = value;
		else if(pos=="l")
			element.style.pixelLeft = value;
		else if(pos=="b")
		{
			if(element.style.top=="" || ignoreCurrentTopAndLeft)
				element.style.top = (value-element.offsetHeight)+"px";
			else
				element.style.height=(value - element.style.pixelTop)+"px";
		}
		else if(pos=="r")
		{
			if(element.style.left==""  || ignoreCurrentTopAndLeft)
				element.style.left = (value-element.offsetWidth)+"px";
			else
				element.style.width=(value - element.style.pixelLeft)+"px";
		}
	},
	
	// this method returns true if a change was made, and false otherwise. case 11147
	G2_VerifyAbsoluteElementNotCropped : function(element)
	{
		var result = false;
		var elementOffsetWidth = element.offsetWidth;
		var offsetParent = element.offsetParent;
		if (offsetParent==null)
		  return false;
	  if (isIE)
	    element.style.display = "none";
	  if(element.offsetLeft+elementOffsetWidth>offsetParent.clientWidth)
	  {
		  element.style.pixelLeft-=element.offsetLeft+elementOffsetWidth-offsetParent.clientWidth;
		  result = true;
	  }
	  element.style.display = "";
	  
	   //locate the element in a proper place if it overflow the client screen	height  
	  var scrollTop =  window.top.document.documentElement.scrollTop;
	  var elementOffsetHeight = element.offsetHeight;
		var offsetParent = element.offsetParent;
		if (offsetParent==null)
		 return;
	 	
	 	if(G2_GetAbsoluteTop(element)+elementOffsetHeight > GetTopWindowHeight() + scrollTop)
	 	{
		  element.style.pixelTop -= G2_GetAbsoluteTop(element)+elementOffsetHeight-(GetTopWindowHeight() + scrollTop);
		  result = true;
	  }
	  
	  if(element.style.pixelTop < 0)
			element.style.pixelTop = 0;
			
		return result;
	},
	//places an element near another element - dock = string = "tl:bl,tr:br" etc... tl=TopLeft tl:br,
	G2_PlaceElementAbsolutlyNear : function(element, relativeElement, dock, onTopWindow, appendToElement)
	{
		var parent = onTopWindow ? window.top.document.body : relativeElement.document.body;
		
		if(appendToElement)
			parent = appendToElement;
			
		if(element.parentElement!=parent)
			parent.appendChild(element);
		if (isMoz)
		  element.style.display = "none";
		element.style.position = "absolute";
		var tokens = dock.split(",");
		var settings = {};
		for(var i=0;i<tokens.length;i++)
		{
			var token = tokens[i];
			var miniTokens = token.split(":");
			var relCorner = miniTokens[0];
			var absCorner = miniTokens[1];
			
			var rel1 = relCorner.charAt(0);
			var rel2 = relCorner.charAt(1);
			var abs1 = absCorner.charAt(0);
			var abs2 = absCorner.charAt(1);
			var posInfo = new Object();
			var rel1Val = G2_GetAbsolute(relativeElement, rel1, onTopWindow, posInfo);
			var rel2Val = G2_GetAbsolute(relativeElement, rel2, onTopWindow, posInfo);
			if(posInfo.offsetParent!=null && posInfo.offsetParent.currentStyle!=null)
			{
			  if(posInfo.offsetParent.currentStyle.position=="fixed")
			    element.style.position = "fixed";
			}
			settings[abs1] = rel1Val;
			settings[abs2] = rel2Val;
		}
		if (isMoz)
		  element.style.display = "";
		//the top and left MUST be set before the bottom and right
		G2_SetAbsolute(element, "t", settings["t"]); 
		G2_SetAbsolute(element, "l", settings["l"]); 
		G2_SetAbsolute(element, "b", settings["b"], settings["t"]==null); 
		G2_SetAbsolute(element, "r", settings["r"], settings["l"]==null); 
	},	
	G2_IsAbsolutlyPositioned : function(element)
	{
		if(element==null)
			return false;
		if(element.style.position=="absolute")
			return true;
		return G2_IsAbsolutlyPositioned(element.parentElement);
	},


	G2_GetElement : function(idOrElement)
	{
		if(typeof(idOrElement)=="string")
			return document.getElementById(idOrElement);
		return idOrElement;
	},
	
	G2_GetAbsoluteLeft : function(element, includeFrames, posInfo) 
	{
	  var x = 0;
    var originalElement = element;
    while( element != null ) 
    {
      x += element.offsetLeft;
      //bug in ie - when using 'relative right:50px' the offsetLeft is wrong //TODO: check in firefox  (dan-el)
 			if(element.style.position=="relative" && element.style.right.contains("px") && element.offsetParent!=element.parentElement)
			{
				x-=element.style.pixelRight;
			}
      if(posInfo!=null)
        posInfo.offsetParent = element;
      if (isMoz && element.currentStyle.position=="fixed")
        element = null;
      else
        element = element.offsetParent;
    }
    if (includeFrames && originalElement.document.parentWindow.frameElement!=null)
    {
      var f = originalElement.document.parentWindow.frameElement;
      var fb = 0;
      if(f.frameBorder == "1" || f.frameBorder == "yes")
        fb = 2;
      x += G2_GetAbsoluteLeft(f, includeFrames) + fb;
    }
    return x;
	},

	G2_GetAbsoluteTop : function(element, includeFrames, posInfo) 
	{
	  var y = 0;
    var originalElement = element;
    while( element != null ) 
    {
      y += element.offsetTop;

			// taking into account scrooling with in overflow scroll elements
      if(element.tagName != 'HTML' && element.scrollTop != null)
				y -= element.scrollTop;
			if(element.tagName == 'IFRAME')
				y -= document.documentElement.scrollTop;

      if(posInfo!=null)
        posInfo.offsetParent = element;
      if (isMoz && element.currentStyle.position=="fixed")
        element = null;
      else
        element = element.offsetParent;
    }
    if (includeFrames && originalElement.document.parentWindow.frameElement!=null)
    {
      var f = originalElement.document.parentWindow.frameElement;
      var fb = 0;
      if(f.frameBorder == "1" || f.frameBorder == "yes")
        fb = 2;
      y += G2_GetAbsoluteTop(f, includeFrames) + fb;
    }
    return y;
	},
	G2_GetAbsoluteBottom : function(element, includeFrames) 
	{
		return G2_GetAbsoluteTop(element, includeFrames)+element.offsetHeight;
	},
	G2_GetAbsoluteRight : function(element, includeFrames) 
	{
		return G2_GetAbsoluteLeft(element, includeFrames)+element.offsetWidth;
	},
	isInSyntheticPopup : function()
	{
		return (parent.document.body.closeSyntheticPopup!=null || document.body.closeSyntheticPopup!=null);
	},

	/**
			This method is called by G2Page.CloseWindow()


	**/
	 G2_ClosePopupWindow : function(openerFunctionScript_functionToCall,
										result,
										firePopupClosedOnOpener,
										fireCloseScript_functionToCall,
										fireCloseScript_windowID,
										fireCloseScript_forceSilentPopupClosedOnOpener)
	{
	  // The window parent should register G2PopupWindow2.js in order to 
	  // Get the popup window (the problem happens when the parent window
	  // of the popup is not the same as the window which open the popup)
		if(window.parent!=window && window.parent.G2PopupWindow2!=null)
		{
			var popup = window.parent.G2PopupWindow2.GetCurrentPopup(window);
			if(popup!=null)
			{
				var silent = fireCloseScript_forceSilentPopupClosedOnOpener ? true : null;
				popup.Close(firePopupClosedOnOpener, fireCloseScript_windowID, silent);
				return;
			}
		}
			if (isInSyntheticPopup())
				return G2_CloseSyntheticPopupWindow(openerFunctionScript_functionToCall,
										result,
										firePopupClosedOnOpener,
										fireCloseScript_functionToCall,
										fireCloseScript_windowID,
										fireCloseScript_forceSilentPopupClosedOnOpener);
				
			var op = window.top.opener;    
			if (op == null && window.dialogArguments == null)
			{
					//'Access Denied' detected.
					if (!String.IsNullOrEmpty(result))
							throw "Error - Result cannot be set with SSL Pages. To return a value from a popup to its opener, use the returnValue property on G2Page.";
					window.top.close();
					return;
			}
			else
			{            
					if (op == null)
						op = window.dialogArguments.obj;
						
					if (!String.IsNullOrEmpty(openerFunctionScript_functionToCall))
					{
									var openerFunction = op[openerFunctionScript_functionToCall];
									openerFunction(result);
					}
	        
					if (window.top.dialogArguments)
							window.top.dialogArguments.CloseEventFired = true;
					window.top.close();
	        
					if (firePopupClosedOnOpener)
					{
						try
						{
							var closeCallback = op.G2_FirePopupClosed;
							if (closeCallback!=null)
								closeCallback.call(op,fireCloseScript_windowID,result,fireCloseScript_forceSilentPopupClosedOnOpener);        
						}
						catch(accessDenied)
						{
							//This is a known limitation. SSL pages and non-SSL pages cannot communicate with each other
						}
							
					}       
			}
	},


	G2_FindElementById : function(element, id)
	{
		return _G2_FindElementById(element, id);
	},
	_G2_FindElementById : function(element, id)
	{
		if(element.id==id)
			return element;	
		if(element.doesNotContainInputs || element.tagName=="SELECT")
			return null;

		var child = element.firstChild;
		while(child!=null)
		{
			var el = _G2_FindElementById(child, id);
			if(el!=null)
				return el;
			child = child.nextSibling;
		}
		return null;
	},

	G2_FindParentElementByG2Tag : function(element, g2tag)
	{
		return _G2_FindParentElementByG2Tag(element, g2tag);
	},
	_G2_FindParentElementByG2Tag : function(element, g2tag)
	{
		if(element==null)
			return null;
		if(G2DOM.G2GetAttribute(element,'g2tag')==g2tag)
			return element;
		return _G2_FindParentElementByG2Tag(element.parentElement, g2tag);
	},

	G2_FindElementByTagName : function(element, tagName)
	{
		if(element.tagName==tagName)
			return element;	
		var child = element.firstChild;
		while(child!=null)
		{
			var el = G2_FindElementByTagName(child, tagName);
			if(el!=null)
				return el;
			child = child.nextSibling;
		}
		return null;
	},

	G2_FindNodeByNameValue : function(element, name, value)
	{
		if(element[name]==value)
			return element;	
		var child = element.firstChild;
		while(child!=null)
		{
			var el = G2_FindNodeByNameValue(child, name, value);
			if(el!=null)
				return el;
			child = child.nextSibling;
		}
		return null;
	},


	// When a page detects it is opened in a popup window, it calls this method
	G2Dialog_Init : function()
	{
		//Try accessing window.top.dialogArguments
		try
		{
			if (window.top.dialogArguments!=null)
			{
				//If that succeeds, we are in a non-SSL popup 
				//In that case, un-hook the onunload event handler
				window.top.document.getElementById('IFRM').contentWindow.onunload = null;		
				
			}
		} catch(bloodyerror)
		{
		}
	},
	G2_FireEventArray : function(owner, array)
	{
		for(var i=0;i<array.length;i++)
		{
			array[i](array.owner);
		}
	},

	G2_GetChildControlById : function(namingContainer, innerElementId)
	{
		return document.getElementById(namingContainer.id+"_"+innerElementId);
	},

	G2FindControlsById : function(controlIds)
	{
		var ret = [];
		if(controlIds==null)
			return ret;
		if (typeof(controlIds)=="string")
		{
			if (controlIds.length==0)
				return ret;			
			controlIds = controlIds.split(/,/g);	
		}
		for(var i=0,j=controlIds.length;i<j;i++)
		{
				var ctrl = document.getElementById(controlIds[i]);
				if (ctrl)
					ret.push(ctrl);
		}
		return ret;
	},

	G2ContextChange : function(func,context)
	{
		return function()
		{
			func.apply(context,arguments);
		}
	},
	
	//***********************************************************
	//                   Processing image                       *
	//***********************************************************
	
	getProcessingImageID : function()
	{
	  return window.ProcessingImageID;
	},
	
	setProcessingImageID : function(value)
	{
	  if(window.ProcessingImageID == value)
	    return;
	  window.ProcessingImageID = value;
	  window.ProcessingImage = null;
	},
	
	getProcessingImage : function()
	{
	  if(window.ProcessingImage==null && ProcessingImageID!=null)
	    window.ProcessingImage = document.getElementById(ProcessingImageID);
	  return window.ProcessingImage;
	},
	
	getElementsToHideWhileProcessing_Cache : function()
	{
	 if(window.ElementsToHideWhileProcessing_Cache == null)
	 {
	  window.ElementsToHideWhileProcessing_Cache = [];
	  
	  if(window.ElementsToHideWhileProcessing!=null)
	  {
	    var list = window.ElementsToHideWhileProcessing.split(',');
	    var eth = window.ElementsToHideWhileProcessing_Cache;
	    for (var i=0;i<list.length;i++)
		  {
			  var e = document.getElementById(list[i]);
			  if (e==null)
				  continue;
  			  
			  eth.push(e);
		  }
	   }
	 }
	 return window.ElementsToHideWhileProcessing_Cache;
	},
	
	getElementsToHideWhileProcessing : function()
	{
	  if(window.ElementsToHideWhileProcessing==null)
	    return "";
	  return window.ElementsToHideWhileProcessing;
	},
      
  setElementsToHideWhileProcessing : function(value)
	{
	  if(window.ElementsToHideWhileProcessing==value)
	    return;
	  window.ElementsToHideWhileProcessing = value;
	  window.ElementsToHideWhileProcessing_Cache = null;
	},
	  
	ShowProcessingImage : function(targetEl)
	{
		//flag that the processing image is activated
		window.ProcessingImageActive = true;
		var eventX = -1;
		var eventY = -1;
		if (!isMoz && event && event.type != "")
		{
			eventX = event.clientX;
			eventY = event.clientY;
		}
		window.setTimeout(function() {ShowProcessingImage_Timeout(targetEl, eventX, eventY);}, 100);
	},

	ShowProcessingImage_Timeout : function(targetEl, eventX, eventY)
	{
	//This function is running asynchronously, so we must check 
	//if the processing image is still required, and hasn't been switched off.
		if (window.ProcessingImageActive == false)
			return;
	    
		var processingImage = getProcessingImage();
		
		//Hide other elements
		var list = window.getElementsToHideWhileProcessing_Cache();
		for (var i=0;i<list.length;i++)
		{
			list[i].style.display='none';
		}
		
		//show processing image
		if (processingImage != null)
		{
			processingImage.style.display = '';
			if (processingImage.isDynamic == 'true')
			{   
					G2_ShowDisabler(true);
					processingImage.style.zIndex = 10001;
					
					if (eventX != -1 && eventY != -1)
					{
							processingImage.style.position = 'absolute';
							processingImage.style.left = Math.max(0, document.documentElement.scrollLeft + eventX - (processingImage.scrollWidth) / 2) + "px";
							processingImage.style.top = Math.max(0, document.documentElement.scrollTop + eventY - (processingImage.scrollHeight / 2)) + "px";
					}
					else
					{
						G2_PlaceElementAbsolutlyNear(processingImage, targetEl, "bl:bl", true);
						G2_VerifyAbsoluteElementNotCropped(processingImage);
					}
			}
		}
	},

	HideProcessingImage : function()
	{
		//switch flag off
		window.ProcessingImageActive = false;
		if (G2_IsNavigating())
		{
			return; //Keep the processing image until we are done navigating
		}	
		
		//hide processing image
		var processingImage = getProcessingImage();
		if (processingImage != null)
		{
			//Debug.writeln("hiding processing image: "+processingImage.id);
			processingImage.style.display = 'none';
		}
		
		//Show other elements
		var list = window.getElementsToHideWhileProcessing_Cache();
		for (var i=0;i<list.length;i++)
		{
			list[i].style.display='block';
		}
	},
	G2_PrintPopup : function(target)
	{
		if(G2_IsInPopup())
		{
			var win = window.open(target.location.href + "&HideButtons=true");
			if(win!=null)
			{
				G2_AttachEvent(win, "onload", function()
				{
					window.setTimeout(function(){	win.print();win.close();}, 500);
				});
			}
		}
		else
		{
			target.focus(); 
			target.print(); 
		}
	},
	// printing an html table
	Print : function(tableId)
	{
		window.focus();
		//Added by Arnon in case 5103
		var TableToPrintObj = document.getElementById(tableId)
		var TableToPrintWidth;
		if(TableToPrintObj && !(typeof document.body.style.maxHeight != "undefined"))//Not IE 7 and ID exist
		{
			// changeing width to fit printing sheet
			TableToPrintWidth = TableToPrintObj.style.pixelWidth;
			TableToPrintObj.style.width="640px";
		}
		window.print();
		if(TableToPrintObj && !(typeof document.body.style.maxHeight != "undefined")) //Not IE 7 and ID exist
		{
			// restore width
			TableToPrintObj.style.width=TableToPrintWidth+"px";
		}
	},
	G2_PreventInputPost : function(id)
	{
		if(typeof(id)=="string")
			G2_PreventPostElementIds[id] = true;
		else
			Debug.writeln("id is not a string");
		//input.disabled = true;
	},
	Select_SetAllSelected : function(select, selected)
	{
		if(select.tagName!="SELECT")
			throw new Error("Select Object expected "+select.tagName);
		//The visibility trick optimizes the selection performance
		var useVisiblityTrick = select.style.visibility=="";
		if(useVisiblityTrick)
			select.style.visibility = "hidden";
		var option = select.options[0];
		while(option!=null)
		{
			if(option.tagName=="OPTION")
				option.selected = selected;
			option = option.nextSibling;
		}
		G2.notifyInputChanged(select);
		if(useVisiblityTrick)
			select.style.visibility = "";
	},
	G2ListBox_SelectAll : function(id)
	{
		var select = $(id);
		if(select==null || select.disabled)
			return;
		Select_SetAllSelected(select, true);
	},
	G2ListBox_SelectNone : function(id)
	{
		var select = $(id);
		if(select==null || select.disabled)
			return;
		Select_SetAllSelected(select, false);	
	},
	G2_DisableBack : function()
	{
			if (window.backIsDisabled != true)
			{
				window.backIsDisabled = true;
				for(var i=0;i<2;i++)
				{
					window.location.hash = "#p"+i;
				}

				window.setInterval(function()
				{
				    if(docTitle!= null)
				    {
				        document.title = docTitle;
				    }
				    if(window.history.forward(1) != null)
						window.history.forward(1);
				}, 100);

			}
		},
		G2_ShowBeforeUnloadMessage : function (e, message, checkFunction)
		{
			if (window.allowUnloadMessage == false)
			{
				window.allowUnloadMessage = true;
			  return;
			}
			if (window[checkFunction] != null)
				if (!window[checkFunction]())
					return;
			return message;
		},
		
		// ------------------------- G2Alert ----------------------------
		//open alert Popup
		G2Alert : function(message, width)
		{
			if(width == null)
				width = 200;
				
			var doc = window.top.document;
			// build alert html
			var alertObj = doc.createElement("DIV");
			
			alertObj.innerHTML = '<TABLE style="width:' + width + '" class=modalPopup><TBODY>' +
			'<TR>' +
			'<TD style="PADDING-TOP: 5px" align="center">' +
			message + 
			'</TD></TR>' +
			'<TR>' +
			'<TD style="PADDING-TOP: 10px;cursor:pointer" align="center" onclick="G2CloseAlert();"><u>OK</u></TD>' +
			'</TR></TBODY></TABLE>';

			 // clone the Div and show the clone
			 alertObj.id = "AlertDiv";

			//return if already shown
			if (alertObj.style.display == 'block')
				return;
				
			// append messagePopup to the form and not to the body (case 11229)
			var container = doc.forms[0];
			
			// create a cover div 
			var coverDiv = G2_CreateModalCoverDiv();
			coverDiv.style.filter = "alpha(opacity=70)";

			// append cover div to form
			if(container != null)
				container.appendChild(coverDiv);
			else
				doc.getElementsByTagName("body")[0].appendChild(coverDiv);

			//set popup div position
			alertObj.style.position = 'absolute';
			
			alertObj.style.left = Math.max(0, doc.documentElement.scrollLeft + (doc.documentElement.clientWidth / 2) - (alertObj.scrollWidth / 2)) + "px";
			alertObj.style.top = Math.max(0, doc.documentElement.scrollTop + (doc.documentElement.clientHeight / 2) - (alertObj.scrollHeight / 2)) + "px";

			alertObj.style.zIndex = 1001;
			G2_AttachFrame(alertObj);

			// append element to form
			if(container != null)
				container.appendChild(alertObj);
			else
				doc.body.appendChild(alertObj);
			
			// verify that the popup is in the boreder of the screen
			G2_VerifyAbsoluteElementNotCropped(alertObj);
		},
		
		// close alert popup
		G2CloseAlert : function()
		{
			var doc = window.top.document;
			var alertObj = doc.getElementById("AlertDiv");
			// remove the cloned Div
			var container = alertObj.parentElement;
			if (alertObj != null && container !=  null)
				container.removeChild(alertObj);
			// remove the cover Div
			var coverDiv = doc.getElementById("CoverDiv");
			container = coverDiv.parentElement;
			if (coverDiv != null && container !=  null)
					container.removeChild(coverDiv);
			G2_DetachFrame(alertObj);
		},

		//create cover div for the modal effect
		G2_CreateModalCoverDiv : function(win)
		{
			var doc = window.top.document;
			if(win != null)
				doc = win.document;
				
			var coverDiv = doc.createElement('DIV');
			coverDiv.id = "CoverDiv";
			coverDiv.className = "CoverDiv";
			coverDiv.style.left = "0px";
			coverDiv.style.top = "0px";
			docHeight = Math.max (doc.documentElement.offsetHeight,doc.documentElement.scrollHeight);
			docWidth = Math.max ( doc.documentElement.offsetWidth, doc.documentElement.scrollWidth);
			coverDiv.style.height = docHeight+"px";
			coverDiv.style.width = docWidth+"px";
			coverDiv.style.zIndex="10";
			coverDiv.style.position="absolute";
			return coverDiv;
		},
		
		G2_VerifyScrollableElementHeight : function(pnlID, maxHeight)
		{
			var pnl = $(pnlID);
			if(pnl == null)
				return;
			if(maxHeight == null || maxHeight == 0)
				return;
				
			if(pnl.clientHeight > maxHeight)
			{
				pnl.style.overflowY = 'scroll';
				pnl.style.height = maxHeight;
			}
		},
		G2_VerifyScrollableElementWidth : function(pnlID, maxWidth)
		{
			var pnl = $(pnlID);
			if(pnl == null)
				return;
			if(maxWidth == null || maxWidth == 0)
				return;
				
			if(pnl.clientWidth > maxWidth)
			{
				pnl.style.overflowX = 'scroll';
				pnl.style.width = maxWidth;
			}
		}
	
});
G2_PreventPostElementIds = new Object();

//**************************************************************************************************

WebForm_InitCallback = function(){};//this is disabled in purpose. we use G2_InitCallback;
var G2_SetFocus_ThreadId = null;
//var G2_InitCallbackFirstTime = true;
var _registeredScripts;
var HtmlSelectEmptyValue = "_NULL_"; //empty strings causes problems with tabs and selectedIndex

if(typeof(Date_ShortMonthNames)=="undefined")
	Date_ShortMonthNames = new Array("Jan", "Feb", "Mar", "Apr", "May", "Jun", "Jul", "Aug", "Sep", "Oct", "Nov", "Dec");
if(typeof(Date_MonthNames)=="undefined")
	Date_MonthNames = new Array("January", "February", "March", "April", "May", "June", "July", "August", "September", "October", "November", "December");
if(typeof(G2_ShortDays)=="undefined")
	G2_ShortDays = ["Su","Mo","Tu","We","Th","Fr","Sa"];

var G2_maxZ=999;
var G2_FixFrame = null;
var enableResizing = false; 
var G2Tooltips = new Array();



G2_PreventInputPost("G2_RootAppPath");





String.IsNullOrEmpty = function(value)
{
	return value==null || value=="";
}

String.Format = function(format, args)
{
	for(var i=1;i<arguments.length;i++)
	{
		var arg = arguments[i];
		var exp = new RegExp("[{]"+(i-1)+"[}]", "g");
		format = format.replace(exp, arg);
	}
	return format;
}

String.Replace = function(s, search, replace)
{
	var exp = new RegExp(search, "g");
	return s.replace(exp, replace);
}








//**************************************************************************************************






function Stopper()
{
	this.laps = new Array();
	this.lapsInfos = new Array();
}

Stopper.prototype.start = function ()
{
	var now = new Date();
	this.laps.push(now);
}

Stopper.prototype.lap = function (name)
{
	var now = new Date();
	this.laps.push(now);
	if(name==null)
	  name="Lap";
	this.lapsInfos.push(name);
	return now-this.laps[this.laps.length-2];
}

Stopper.prototype.total = function ()
{
	var now = new Date();
	return now-this.laps[0];
}

Stopper.prototype.maxIndex = function ()
{
  var maxIndex = -1;
  var max=0;
	for(var i=1; i<this.laps.length; i++)
	{
	  var start = this.laps[i];
	  var end = this.laps[i-1];
	  var lap = start-end;
	  if(lap>max)
	  {
	    maxIndex = i;
	    max = lap;
	  }
  }
  return maxIndex;
}

Stopper.prototype.totalLaps = function ()
{
	var start = this.laps[0];
	var end = this.laps[this.laps.length-1];
	return end-start;
}

var StopperWinID = 0;
Stopper.prototype.report = function (title)
{
  var winID = "Stoper_"+StopperWinID;
  StopperWinID++;
	var win = window.open(null, winID, "height=300,width=300,status=no,toolbar=no, menubar=no, location=no, resizable=yes");
	var doc = win.document;
	doc.open();
	
	doc.write("<html><body>");
	//var now = new Date();
	doc.write("<div style='font-size:8px;'><b>"+title+"</b></div>");
	var maxIndex = this.maxIndex();
	doc.write("<table>");
	doc.write("<tbody>");
	for(var i=1; i<this.laps.length; i++)
	{
	  var start = this.laps[i];
	  var end = this.laps[i-1];
	  doc.write("<tr>");
	  doc.write("<td>");
	  doc.write("<div style='"); 
	  if(i==maxIndex)
	  {
	    doc.write("color:red;");
	  }
	  doc.write("'>"+i.toString());
	  doc.write("</div>");
	  doc.write("</td>");
	  doc.write("<td>");
	  doc.write(this.lapsInfos[i-1]);
	  doc.write("</td>");
	  doc.write("<td>");
	  doc.write((start-end)+"");
	  doc.write("</td>");
	  doc.write("</tr>");
	}
	doc.write("</tbody>");
	doc.write("</table>");
	doc.write("<hr />");
	doc.write("<div style='color:blue'>Total: <b>" + this.totalLaps()+ "</b>ms</div>"); 
	doc.write("</body></html>");
	doc.close();	
}


var specialCopyKey = 17; //ctrl + q 



Char = 
{
	Backspace : 8,
	Tab : 9,
	Enter : 13,
	Ctrl : 16,
	Alt : 17,
	Pause : 19,
	CapsLock : 20,
	Escape : 27,
	PageUp : 33,
	PageDown : 34,
	End : 35,
	Home : 36,
	ArrowLeft : 37,
	ArrowUp : 38,
	ArrowRight : 39,
	ArrowDown : 40,
	Insert : 45,
	Delete : 46,
	categories : {Digit:/[0-9]/, Upper:/[A-Z]/, Lower:/[a-z]/},
	IsDigit : function(charOrCode)
	{
		return this.IsInCategory(charOrCode, "Digit");
	},
	IsInCategory : function(charOrCode, categoryName)
	{
		if(charOrCode==null)
			return false;
		var s = typeof(charOrCode)=="number" ? String.fromCharCode(charOrCode) : charOrCode;
		return this.categories[categoryName].test(s);
	},
	IsUpper : function(charOrCode)
	{
		return this.IsInCategory(charOrCode, "Upper");
	},
	IsLower : function(charOrCode)
	{
		return this.IsInCategory(charOrCode, "Lower");
	},
	ToUpperKeyCode : function(keyCode)
	{
		return keyCode-32;
	},
	//
	// returns a value indicating whether the given charCode is a key that changes the cursor position
	//
	IsCursorPositionCharCode : function (charCode)
	{
		if
		(
			charCode==this.ArrowUp || 
			charCode==this.ArrowDown || 
			charCode==this.ArrowLeft || 
			charCode==this.ArrowRight || 
			charCode==this.Home || 
			charCode==this.End || 
			charCode==this.PageUp || 
			charCode==this.PageDown
		)
		{
			return true;
		}
		return false;
	}


}

//46 Delete 
//TODO:
//91 Left Windows 
//92 Right Windows 
//93 Context Menu 
//96 NumPad 0 
//97 NumPad 1 
//98 NumPad 2 
//99 NumPad 3 
//100 NumPad 4 
//101 NumPad 5 
//102 NumPad 6 
//103 NumPad 7 
//104 NumPad 8 
//105 NumPad 9 
//106 NumPad * 
//107 NumPad + 
//109 NumPad - 
//110 NumPad . 
//111 NumPad / 
//112 F1 
//113 F2 
//114 F3 
//115 F4 
//116 F5 
//117 F6 
//118 F7 
//119 F8 
//120 F9 
//121 F10 
//122 F11 
//123 F12 
//144 Num Lock 
//145 Scroll Lock 
//186 ; 
//187 = 
//188 , 
//189 - 
//190 . 
//191 / 
//192 ` 
//219 [ 
//220 \ 
//221 ] 
//222 ' 


function G2KeysClass()
{
  this.up = 38; //up arrow  
  this.down = 40; //down arrow
  this.left =  37; //left arrow
  this.right =  39; //right arrow
  this.pageUp =  33; //page up  
  this.pageDown =  34; //page down  
  this.home =  36; //home  
  this.end =  35; //end                  
  this.enter =  13; //enter  
  this.tab =  9; //tab  
  this.esc =  27; //esc  
  this.shift =  16; //shift  
  this.ctrl =  17; //ctrl  
  this.alt =  18; //alt  
  this.caps =  20; //caps lock
  this.backspace =  8; //backspace  
  this.del =  46; //delete
  
  this.controlKeys = new Array(this.up, this.down, this.left, this.right, this.pageUp, this.pageDown, this.home, this.end, this.enter, this.tab, this.shift, this.ctrl, this.alt, this.caps, this.backspace, this.del);
}
var G2Keys = new G2KeysClass();


G2EventArray = function(owner)
{
	this.owner = owner;
}
G2_DeclareClass(G2EventArray, "G2EventArray", Array,
{
	fire : function()
	{
		for(var i=0;i<this.length;i++)
		{
			this[i](this.owner);
		}
	}
});




//Add trim() to String.
String.prototype.trim = trim;
	/*
	function G2PopupWindow_Open2(url, context, modal, name, features)
	{	
		if (features==null && context!=null)
		{
			var h = document.all[context];
			if(h!=null)
				features = h.value;
		}   
		if (modal==null)
			modal=true;
			
		if(modal)
		{
			var h = G2PopupWindow_ExtractParameter(features,"dialogHeight");
			var w = G2PopupWindow_ExtractParameter(features,"dialogWidth");
					
			//Fix for callbacks on popup closed event
			var me = window;
			function f()
			{
				window.showModalDialog(G2_MapPath("~/Client/Dialog.aspx"),{url:url,obj:me,width:w,height:h}, features);
			}		
			f();
		}
		else
		{
	  
			//Workaround for bug #3634: 
			// IE popup blocker blocked the popup, because it was not initiated by a user click.		
			
			//Note: The following is a workaround for IE popup blockers. It is not jiffacode.
			var temporaryButton = G2DOM.G2CreateElement("<input type='Button' style='display:none'></input>");
			temporaryButton.id = temporaryButton.uniqueID;
			temporaryButton.onclick = function()
			{
				if (null == window.open(url, name, features))
				{
					alert('popup blocker detected!');
				}
			}
			document.body.appendChild(temporaryButton);
			temporaryButton.click();
			document.body.removeChild(temporaryButton);
		}
	}*/
if(ENABLE_PROFILER)
	Profiler.createDebugDiv();

ListSet = function()
{
	this._list = [];
	this._set = {};
}
G2_DeclareClass(ListSet, "ListSet", null, 
{
	addRange : function(array)
	{
		for(var i=0;i<array.length;i++)
		{
			this.add(array[i]);
		}
	},
	add : function(item)
	{
		if(this._set[item]!=null)
			return false;
		this._list.push(item);
		this._set[item] = this._list.length-1;
		return true;
	},
	remove : function(item)
	{
		if(this._set[item]==null)
			return false;
		var index = this._set[item];
		this._list.splice(index, 1); //removeAt
		this._set[item] = null;
		for(var i=index;i<this._list.length;i++) //perform reindexing
		{
			var item = this._list[index];
			this._set[item] = index;
		}
		return true;
	},
	toString : function(seperator)
	{
		return this._list.join(seperator);
	}
	
});

/* G2PopupManager
Manages all popups and tooltips within the application.
*/
G2PopupManager = 
{
//	popups : {},
//	tooltipTargets : [],
//	allowTooltips : true,
	
	init : function()
	{
		this.attachToOnClick(document, true);
		this.allowTooltips = true;
		if(window.top.G2PopupManager==this)
		{
		  this.popups = new Object();
		  this.tooltipTargets = new Array();
		}
		else
		{
		  var tm = window.top.G2PopupManager;
		  this.popups = tm.popups;
		  this.tooltipTargets = tm.tooltipTargets;
		}
	},
		
	attachToOnClick : function(doc, includeFrames)
	{
	  if(doc.attachEvent) //G2Dom is not available right now
		{
			doc.attachEvent("onmousedown", this.__document_onclick);
//			if(IE6) //memory leaks
//			  doc.parentWindow.attachEvent("onunload", this.window_onunload);
		}
		else if(document.addEventListener)
		{
			doc.addEventListener("mousedown", this.__document_onclick, false);
		}
//		if(!includeFrames || doc.parentWindow==null || doc.parentWindow.document==doc)
//		  return;
//		
//	  doc = doc.parentWindow.document;
//	  this.attachToOnClick(doc, includeFrames);
	},
	window_onunload : function(e)
	{
	  G2PopupManager.unload();
	},
	unload : function(e)
	{
	  for(var p in this.popups)
	  {
	    this.popups[p] = null;
	  }
	},
	__document_onclick : function(e)
	{
		G2PopupManager._document_onclick(e);
	},
	_document_onclick : function(e)
	{
		var element = e.srcElement;
		
		if(element!=null && element.tagName=="HTML")
		  return;//Clicked on scroll, ignore
		 
		while(element!=null)
		{
			var popup = this.popups[element.uniqueID];
			if(popup!=null)
				return;
			element = element.parentElement;
		}
		this.closeAllPopups(true);
		this.closeAllTooltips();
	},
	
	//Use this method to display a popup element relatively to a specific element
	//
	openPopup : function(element, relativeElement, dock, onTopWindow)
	{
		this.closeAllPopups();
		var popup = {element:element, relativeElement:relativeElement, dock:dock, isOpen:true, allowCloseOnDocumentClick:false};
		this.popups[element.uniqueID] = popup;
		if(relativeElement==null)
			throw new Error("relative element not found, cannot show popup");
		if(element.g2closepopup=="false")
			element.style.display = "";
		G2_PlaceElementAbsolutlyNear(element, relativeElement, dock, onTopWindow);
		if(dock==null || !dock.contains(","))
			G2_VerifyAbsoluteElementNotCropped(element);
		G2_BringToFront(element);
		G2_AttachFrame(element);
		
		window.setTimeout(
		function()
		{
			popup.allowCloseOnDocumentClick = true;
		}, 0);
		
	  if (element.onOpened!=null)
	    element.onOpened(element);			
	},
	
	//Closes all registered popups in the window
	closeAllPopups : function(isDocumentClick)
	{
		for(var p in this.popups)
		{
			var pp = this.popups[p];
			if(pp!=null && pp.isOpen)
			{
				if(isDocumentClick && !pp.allowCloseOnDocumentClick)
					continue;
				this.closePopup(pp.element);
			}
		}
	},
	isPopupOpened : function(element)
	{
		var popup = this.getPopup(element);
		if(popup!=null && popup.isOpen)
			return true;
		return false;
	},
	
	//Retrives a specific popup element
	getPopup : function(element)
	{
		return this.popups[element.uniqueID];
	},
	
	//Closes a given popup by its element
	closePopup : function(element)
	{
		var popup = this.getPopup(element);
		if(popup==null)
			return;
		if (popup.element.onBeforeClose!=null)
		  popup.element.onBeforeClose(popup.element);
		G2_DetachFrame(element);
		if(element.g2closepopup=="false")
		{
			element.style.display = "none";
		}
		else if(element.parentElement!=null)
		{
			element.parentElement.removeChild(element);
		}
		popup.isOpen = false;
		if(element.onPopupClosed)
		  element.onPopupClosed();
		 
		delete this.popups[element.uniqueID];
	},
	
	
	
	//Displayes the provided HTML as a tooltip
	//A typical use is to attach an onmouseenter handler to the target element such as
	//target.onomuseenter = "G2PopupManager.showTooltipHtml(this, '<b>Hello</b>', event);";
	showTooltipHtml : function(targetElement, html, e)
  {
	  if (!e)
		  e = window.event;
  	
	  var el = targetElement._tooltipElement;
	  if(el==null)
	  {
	    el = G2DOM.G2CreateElementFromHtml("<TABLE border='0' cellpadding='0' cellspacing='0'><TR><TD>"+html+"</TD></TR></TABLE>");
	    if(el.parentElement!=null)//TODO: Remove quick fix
	      el.parentElement.removeChild(el);
	  }
	  this.showTooltipStart(targetElement, el,e);
  },
  
  showTooltipText : function(targetElement, text, e)
  {
    if (!e)
		  e = window.event;
	  var html = "<div style='background-color: #fffacd;border-right: black 1px solid;border-top: black 1px solid;font-size: 8pt;border-left: black 1px solid;color: black;border-bottom: black 1px solid;font-family: Arial;padding:4px;'>"+text+"</div>";
	  this.showTooltipHtml(targetElement, html, e);
  },
  
  showTooltipStart : function(targetElement, el,e)
  {
    if(!this.allowTooltips)//Tooltips are disabled during postbacks
      return;
	  if (!e)
		  e = window.event;
	  
	  this.closeAllTooltips();
	  targetElement._tooltipElement = el;//Cache
	  
	  var posx = 0;
	  var posy = 0;
	  var winWidth = 1024;
	  var winHeight = 700;
  	 
  	if(el.parentElement == null)
  	  document.body.appendChild(el);
	  el.style.position="absolute";
	  offSet = 0
	  if (e.pageX || e.pageY)
	  {
		  winWidth = window.innerWidth;
		  winHeight = window.innerHeight;
		  posx = e.pageX;// + window.pageXOffset;
		  posy = e.pageY;// + window.pageYOffset;
	  }
	  else if (e.clientX || e.clientY)
	  {
		  winWidth = document.body.offsetWidth;
		  winHeight = document.body.offsetHeight;
		  posx = e.clientX + document.body.scrollLeft + document.documentElement.scrollLeft;
		  posy = e.clientY + document.body.scrollTop + document.documentElement.scrollTop;
	  }
	  
	  el.style.display = "block";
	  
	  //Fix flowing out of window
		var right = posx + el.offsetWidth;
	  if(right>winWidth)
	  {
	    var newPosx = (posx-el.offsetWidth);
	    if(newPosx>0)
	      posx = newPosx;
	  }
		var bottom = posy + el.offsetHeight;
	  if(bottom>winHeight)
	  {
	    newPosy = (posy-el.offsetHeight);
	    if(newPosy>0)
	      posy = newPosy; 
	  }
	  
	  posy++;		//Avoid some flickering in FireFox
	  el.style.pixelLeft = posx;
	  el.style.pixelTop = posy;
	  G2_VerifyAbsoluteElementNotCropped(el);
	  
	  targetElement.title = "";
	  this.tooltipTargets.push(targetElement);
	  
	  
	  
	  G2_BringToFront(el);
	  G2_AttachFrame(el);
	  el.enterToolTip = false;
	  	  
      if(targetElement.onmouseleave==null)
      {
          targetElement.onmouseleave=function(){
            setTimeout(function(){CloseIfNotInToolTip(targetElement, el)}, 500);
          };
          if (isMoz)
          {
            G2_AttachEvent(targetElement, "onmouseout",targetElement.onmouseleave); 
          }	    
	   }
	  if(el.onmouseenter==null)
      {
          el.onmouseenter=function(){el.enterToolTip = true;}; 
          if (isMoz)
          {
            G2_AttachEvent(el, "onmousein",el.onmouseenter); 
          }	      
	  }
	  if(el.onmouseleave==null)
      {
          el.onmouseleave=function(){
            G2PopupManager.closeTooltipFor(targetElement);
            el.enterToolTip = false;
          }; 
          if (isMoz)
          {
            G2_AttachEvent(el, "onmouseout",el.onmouseleave); 
          }	      
	  }
	  if(el.onmousedown==null)
      {
          el.onmousedown=function(){
           e.cancelBubble = true;
          };   
	  }
  },	
  closeAllTooltips : function()
  {
    while(this.tooltipTargets.length > 0)
    {
      var tt = this.tooltipTargets.pop();
      this.closeTooltipFor(tt);
    }
  },
  closeTooltipFor : function(targetElement)
	{
	  if(targetElement._tooltipElement !=null)
	    targetElement._tooltipElement.style.display="none";
	  G2_DetachFrame(targetElement._tooltipElement);
	},
	
	disableTooltips : function()
	{
	  this.allowTooltips = false;
	},
	
	enableTooltips : function()
	{
	  this.allowTooltips = true;
	}
	
};
G2_DeclareUtilInstance(G2PopupManager);
G2PopupManager.init();

G2FrameManager = 
{
	autoSizeThreadId : null,
	frames : {},
	registerFrame : function(frameOrId)
	{
		if(typeof(frameOrId)=="string")
			this.frames[frameOrId] = null;
		else
			this.frames[frameOrId.id] = frameOrId;
		if(this.autoSizeThreadId==null)
		{
			var caller = this;
			this.autoSizeThreadId = window.setInterval(
			function()
			{
				caller.autoSizeAllFrames();
			}, 300);
		}
	},
	unregisterFrame : function(frame)
	{
	    delete this.frames[frame.id];
	},
	autoSizeAllFrames : function()
	{
		for(var id in this.frames)
		{
			var frame = this.frames[id];
			if(frame==null)
			{
				frame = document.getElementById(id);
				this.frames[id] = frame;
			}
			frame.className = frame.className.replace("Hide", "");
			if(frame.autosize!="false" && frame.readyState=="complete")
			{
				try
				{
					if(frame.autosizeheight!="false")
					{
					  //  Following is the standard html page doctype definition as produced by Visual Studio with default settings
					  var doctypeString = '<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">';
					  var height, includesDTD = false;
					  //  Check if doctype is one of iframe document childs and retrieve the proper scrollHeight value
					  for(var i=0; i<frame.contentWindow.document.childNodes.length; i++)
					  {
					    if(frame.contentWindow.document.childNodes[i].text == doctypeString)
					    {
					      includesDTD = true;
					      break;
					    }
					  }
					  if(includesDTD) 
						  height = frame.contentWindow.document.documentElement.scrollHeight;
						else
						  height = frame.contentWindow.document.body.scrollHeight;
						if(frame.style.pixelHeight!=height)
							frame.style.height = height+"px";
					}
					if(frame.autosizewidth!="false")
					{
						var width = frame.contentWindow.document.documentElement.scrollWidth;
						if(frame.style.pixelWidth!=width)
							frame.style.width = width+"px";
					}
				}
				catch(err)
				{
					1;
					1;
				}
			}
		}
	}
}
G2_DeclareUtilInstance(G2FrameManager);



function G2_Print()
{
  window.print();
}


//
// Allows performing actions in the background
// action = function + arguments
// when the action occurs - 'this' keywork returns the background worker
//
G2BackgroundWorker = function(maxConcurrentActions)
{
	this.actions = [];
	this.concurrentActionsCount = 0;
	this.maxConcurrentActions = maxConcurrentActions || 1;
}

G2_DeclareClass(G2BackgroundWorker, "G2BackgroundWorker", null, 
{
	addAction : function(func, args, options)
	{
		this.actions.push({func:func,args:args,options:options});
		if(this.actions.length==1)
		{
			this._requestDoWorkIfNeeded();
		}
	},
	_requestDoWorkIfNeeded : function()
	{
		var caller = this;
		if(this.actions.length>0)
		{
			window.setTimeout(
			function()
			{
				caller.doWork();
			}, 0);
		}
		else if(this.concurrentActionsCount<=0)
		{
			this.onFinish();
		}
	},
	onActionStart : function(action)
	{
		this.concurrentActionsCount++;
	},
	onActionEnd : function()
	{
		if(this.concurrentActionsCount<=0)
			throw new Error("no current actions");
		this.concurrentActionsCount--;
		this._requestDoWorkIfNeeded();
	},
	doWork : function()
	{
		while(this.concurrentActionsCount<this.maxConcurrentActions && this.actions.length>0)
		{
			var action = this.actions.dequeue();
			this.onActionStart(action);
			this.currentAction = action;
			action.func.apply(this, action.args);
			if(action.options==null || !action.options.manualActionEndNotification)
				this.onActionEnd();
		}
	},
	onFinish : function()
	{
	}


});

//All (crappy) focus code taken from asp.net
function G2_FindFirstFocusableChild(control) 
{
  if (!control || !(control.tagName)) 
	{
    return null;
  }
  var tagName = control.tagName.toLowerCase();
  if (tagName == "undefined") 
	{
    return null;
  }
  var children = control.childNodes;
  if (children) 
	{
    for (var i = 0; i < children.length; i++) 
		{
      try 
			{
        if (WebForm_CanFocus(children[i])) 
				{
          return children[i];
        }
        else 
				{
          var focused = WebForm_FindFirstFocusableChild(children[i]);
          if (WebForm_CanFocus(focused)) 
					{
            return focused;
          }
				}
			} 
			catch (e) 
			{
			}
		}
	}
	return null;
}

function G2_AutoFocus(focusId) 
{
  var targetControl;
  if (__nonMSDOMBrowser) 
	{
    targetControl = document.getElementById(focusId);
  }
  else 
	{
    targetControl = document.all[focusId];
  }
  var focused = targetControl;
  if (targetControl && (!WebForm_CanFocus(targetControl)) ) 
	{
      focused = WebForm_FindFirstFocusableChild(targetControl);
  }
  if (focused) 
	{
    try 
		{
      focused.focus();
      if (__nonMSDOMBrowser) 
			{
        focused.scrollIntoView(false);
      }
      if (window.__smartNav) 
			{
        window.__smartNav.ae = focused.id;
      }
      return true;
    }
    catch (e) 
		{
			return false;
    }
  }
  else
		return false;
}
function G2_CanFocus(element) 
{
    if (!element || !(element.tagName)) return false;
    var tagName = element.tagName.toLowerCase();
    return (!(element.disabled) &&
            (!(element.type) || element.type.toLowerCase() != "hidden") &&
            WebForm_IsFocusableTag(tagName) &&
            WebForm_IsInVisibleContainer(element)
            );
}
function G2_IsFocusableTag(tagName) 
{
    return (tagName == "input" ||
            tagName == "textarea" ||
            tagName == "select" ||
            tagName == "button" ||
            tagName == "a");
}
function G2_IsInVisibleContainer(ctrl) 
{
  var current = ctrl;
  while((typeof(current) != "undefined") && (current != null)) 
	{
    if (current.disabled ||
        ( typeof(current.style) != "undefined" &&
        ( ( typeof(current.style.display) != "undefined" &&
            current.style.display == "none") ||
            ( typeof(current.style.visibility) != "undefined" &&
            current.style.visibility == "hidden") ) ) ) 
		{
      return false;
    }
    if (typeof(current.parentNode) != "undefined" &&
            current.parentNode != null &&
            current.parentNode != current &&
            current.parentNode.tagName.toLowerCase() != "body") 
		{
      current = current.parentNode;
    }
    else 
		{
      return true;
    }
  }
  return true;
}

function G2_ShowDisabler(show) 
{
  if(window.g2disabler == null)
  {
    if(show==false)
      return;
    var html = "<div id='g2disabler' class='g2Disabler' onclick='return false;' onmouseover='return false;' onmouseout='return false;'></div>";
    var disablerElement= G2DOM.G2CreateElementFromHtml(html, document);
    document.body.appendChild(disablerElement);
    window.g2disabler = disablerElement;
  }
  if(show)
  {
    window.g2disabler.style.pixelHeight = document.documentElement.scrollHeight;
		window.g2disabler.style.pixelWidth = Math.max(document.documentElement.offsetWidth-4, 0);
    window.g2disabler.style.display = '';
    window.g2disabler.lastDocumentOverflowX = document.documentElement.style.overflowX;
		document.documentElement.style.overflowX = 'hidden';
  }
  else
  {
	  window.setTimeout(function() {
    window.g2disabler.style.display = 'none';
    document.documentElement.style.overflowX = window.g2disabler.lastDocumentOverflowX;}, 1);
  }
}

function G2_DetectAcrobatReader() 
{
    var acrobat=new Object(); 
    acrobat.installed=false; 
    acrobat.version='0.0'; 
    if (navigator.plugins && navigator.plugins.length) { 
        for (x=0; x<navigator.plugins.length;x++) { 
              if (navigator.plugins[x].description.indexOf('Adobe Acrobat')!= -1) 
              { 
                    acrobat.version=parseFloat(navigator.plugins[x].description.split('Version ')[1]); 
                    if (acrobat.version.toString().length == 1) acrobat.version+='.0'; 
                          return acrobat; 
              } 
        } 
    } 
    else if (window.ActiveXObject) 
    { 
        for (x=2; x<10; x++) 
        { 
            try 
            { 
                oAcro=eval("new ActiveXObject('PDF.PdfCtrl."+x+"');"); 
                if (oAcro) 
                { 
                     acrobat.installed=true; 
                     acrobat.version=x+'.0'; 
                 } 
            } 
            catch(e) {} 
            } 
            try 
            { 
                oAcro4=new ActiveXObject('PDF.PdfCtrl.1'); 
                if (oAcro4) 
                { 
                      acrobat.installed=true; 
                      acrobat.version='4.0'; 
               } 
            } 
            catch(e) {} 
            try 
            { 
                oAcro7=new ActiveXObject('AcroPDF.PDF.1'); 
                if (oAcro7) 
                { 
                      acrobat.installed=true; 
                      acrobat.version='7.0'; 
                } 
            } 
            catch(e) {} 
        } 
        return acrobat; 
}
function CloseIfNotInToolTip(trgElm,curToolTip)
{
    if(!curToolTip.enterToolTip)
    {
        G2PopupManager.closeTooltipFor(trgElm);
    }
}
function SaveDocumentTitle(title)
{
    docTitle = title;
}

// Get the topest available window
function GetTopAvailableWindow()
{
	var win = window;
	var tmpElement;
	
	// For each window parent
	while((typeof(win.parent) != "undefined") && (win.parent != null) && (win != win.parent))
	{
	  // Try to access the window parent - else return the current window
		try
		{
			tmpElement = win.parent.document.createElement('DIV');
			win = win.parent;
		}
		catch(e)
		{
			return win;
		}
	}
	
	return win;
}

WebForm_FindFirstFocusableChild = G2_FindFirstFocusableChild;
WebForm_AutoFocus = G2_AutoFocus;
WebForm_CanFocus = G2_CanFocus;
WebForm_IsFocusableTag = G2_IsFocusableTag;
WebForm_IsInVisibleContainer = G2_IsInVisibleContainer;


/**********************************************************************
 *           G2 Cross-platform Javascript library                     *
 **********************************************************************/
Array.prototype.dequeue = function() {var r = this[0]; this.splice(0,1); return r;};
Array.prototype.FirstOrDefault = function(predicate)
{
	for(var i=0;i<this.length;i++)
	{
		var item = this[i];
		if(predicate(item))
			return item;
	}
	return null;
}
Array.prototype.ForEach = function(action)
{
	for(var i=0;i<this.length;i++)
	{
		var item = this[i];
		action(item);
	}
}
Array.prototype.RemoveItem = function(itemToRemove)
{
    for(var i=0;i<this.length;i++)
	{
		if (this[i] == itemToRemove)
		{
		    this.splice(i,1);
		    break;
		}
	}
}

var G2DOM = 
{
	GetChildElementById : function(element, id)
	{
		if(isIE)
		{
			var child = element.all[id];
			if(child==null)
				return null;
			if(child.length!=null)
				return child[0];
			return child;
		}
		else if(isMoz)
		{
			return this._GetChildElementById(element, id);
		}
		else
			throw new Error("not supported");
	},
	_GetChildElementById : function(element, id)
	{
		var child = element.firstChild;
		while(child!=null)
		{
			if(child.id==id)
				return child;
			var grandChild = this._GetChildElementById(child, id);
			if(grandChild!=null)
				return grandChild;
			child = child.nextSibling;
		}
		return null;
	},
	
	// This method gets a root element and a progid value and find the first child element with the progid specified
	// In case you got the whole progId path it is preffered to use the method 'findControl' below. It is much faster.
	// This method uses Depth-First-Search(DFS) recursively.
	GetChildByProgid_dfs : function(root, childProgid)
	{
		if (! root)
			return null;

		if (root.progid == childProgid)
			return root;

		var child = root.firstChild;
		while (child)
		{
			var res = this.GetChildByProgid(child, childProgid);
			if (res != null)
				return res;
			child = child.nextSibling;
		}
		
		return null;
	},
	

	// This method gets a root element and a progid value and find the first child element with the progid specified
	// This method uses Breadth-First-Search (BFS) instead of Depth-First-Search(DFS). It is therefore non-recursive.
	GetChildByProgid : function(root, childProgid)
	{
		if (! root)
			return null;
			
		if (root.progid == childProgid)
			return root;
			
		var queue = [root];		
		while (queue.length>0)
		{
			root = queue.dequeue();
			if (root.progid == childProgid)
				return root;
			var children = root.children;
			for (var i=0,j=children.length;i<j;i++)
				queue.push(children[i]);
		}	
				
		return null;
	},
	
	// This method gets a root element and a progid value and find the first parent element with the progid specified
	GetParentByProgid : function(root, childProgid)
	{
		while(root && root.progid != childProgid)
		{
			root = root.parentElement;
		}
		
		return root;
	},

	// gets the given object position	
	findPos : function(obj)
	{
		var curleft = 0;
		var curtop = 0;
		if (obj.offsetParent)
		{
			curleft = obj.offsetLeft;
			curtop = obj.offsetTop;
			while (obj = obj.offsetParent)
			{
				curleft += obj.offsetLeft;
				curtop += obj.offsetTop;
					
		    // taking into account scrooling with in overflow scroll elements
		    if(obj.tagName != 'HTML' && obj.scrollTop != null)
			    curtop -= obj.scrollTop;
			}
		}
		return [curleft,curtop];
	},
		
	// Create a covering DIV for a modal effect.
	// The input parameters:
	// side - left, top, right or bottom
	// tableId - the modal element or its id
	// errorMsg - message to shown when clicking on the div. optional
	CreateCoverDiv : function(side,tableId,errorMsg)
	{
		// validate modal element
		if(tableId == null)
			return;

		var tbl = tableId;
		if(typeof(tableId) == "string")
			tbl = $(tableId);

		var arr = this.findPos(tbl)	
		var docHeight,docWidth;
		var coverDiv = document.createElement('DIV');
		var div;
		if (side == "left")
		{
				div = $('leftCoverDiv');
			if (div!=null)
				return div;
			docHeight = document.documentElement.scrollHeight;		
			docWidth = arr[0];
			coverDiv.id = "leftCoverDiv";
		}
		else if (side == "top")
		{
				div = $('topCoverDiv');
			if (div!=null)
				return div;
			docWidth = document.documentElement.scrollWidth;
			docHeight = arr[1];	
			coverDiv.id = "topCoverDiv";
		}			
		else if (side == "right")
		{
				div = $('rightCoverDiv');
			if (div!=null)
				return div;
			docWidth = document.documentElement.scrollWidth-tbl.offsetWidth;
			docHeight = tbl.offsetHeight;
			coverDiv.id = "rightCoverDiv";
		}			
		else if(side == "bottom")
		{
				div = $('bottomCoverDiv');
			if (div!=null)
				return div;
			docWidth = document.documentElement.scrollWidth;
			docHeight = window.document.documentElement.scrollHeight-(arr[1]+tbl.offsetHeight);
			coverDiv.id = "bottomCoverDiv";
		}			
		coverDiv.className = "CoverDiv";
		if (side == "left" || side == "top")
		{
				coverDiv.style.left = "0px";
				coverDiv.style.top = "0px";
		}
		else if (side == "right")
		{
				coverDiv.style.left = arr[0]+tbl.offsetWidth+"px";
				coverDiv.style.top = arr[1]+"px";
		}
		else if (side == "bottom")
		{
				coverDiv.style.left = "0px";
				coverDiv.style.top = arr[1]+tbl.offsetHeight+2+"px";
		}
		coverDiv.style.height = docHeight+"px";
		coverDiv.style.width = docWidth+"px";	
		coverDiv.style.position="absolute";			
		coverDiv.onclick = function()
		{
			if(errorMsg)
				alert(errorMsg);
			else
				alert("You are in Edit Mode, Click Done to save or Cancel to exit");
		};
		return coverDiv;
	},

	//Transfers the custom attributes from the element to its properties (they are the same in IE, not in FF)
	G2TransferAttributes : function(elem)
	{
		if (isIE || elem==null || elem.attributesTransferred) //IE is nice enough
			return;
		elem.attributesTransferred = true;
		for (var atnum in elem.attributes)
		{
			var atNode = elem.attributes[atnum];
			var atname = atNode.nodeName;
			var atvalue = atNode.nodeValue;
			if (typeof(elem[atname])=="undefined")
				elem[atname] = atvalue;
		}	
	},

	G2GetSelection : function()
	{
		return (window.getSelection || (document.getSelection && document.getSelection()) || document.selection);
	},

	G2GetNextChild : function ( n )
	{
		if (isIE)
			return n.nextSibling;

		do
		{
			n	 = n.nextSibling;
		} 
		while (n!=null && n.nodeType == Node.TEXT_NODE);

		return n;
	},
	G2CreateElementFromHtml : function(html, doc)
	{
	  if(doc==null)
	    doc = document;
		var tagName = html.substr(html.search("<")+1, 2).toUpperCase();
		var div = doc.createElement('div');
		if(tagName=="TR")		
		{
			div.innerHTML = "<table><tbody>"+html+"</tbody></table>";
			var newRow = div.firstChild.firstChild.firstChild;
			newRow.parentElement.removeChild(newRow);
			return newRow;
		}
		else if(tagName=="TD")
		{
			var div = doc.createElement("div");
			div.innerHTML = "<table><tr>"+outerHTML+"</tr></table>";
			var cell = div.firstChild.firstChild.firstChild.firstChild;
			return cell;
		}
		else
		{
			div.innerHTML = html;
			return div.children[0]; //FF
		}
	},

	//Replaces a node's outerHTML (Already Implemented in IE, not in FF)
	//TODO: Check if this is needed or if the outerHTML setter works in FF 2.0
	G2ReplaceOuterHTML : function(obj,outerHTML)
	{
		if(isIE)
		{
			//added by dan-el - the simple method doesn't work for TR's.
			if(obj.tagName=="TR")
			{
				var tempDiv = document.createElement('div');
				tempDiv.innerHTML = "<table>"+outerHTML+"</table>";
				var newRow = tempDiv.firstChild.firstChild.firstChild;
				var row = obj;
				var table = obj.parentNode;
				table.replaceChild(newRow, row);
			}
			else if(obj.tagName=="TD")
			{
				var div = document.createElement("div");
				div.innerHTML = "<table><tr>"+outerHTML+"</tr></table>";
				var cell = div.firstChild.firstChild.firstChild.firstChild;
				obj.replaceNode(cell);
			}
			else
			{
				obj.outerHTML = outerHTML;
//				var div = document.createElement("div");
//				div.innerHTML = outerHTML;
//				if (div.firstChild)
//					obj.replaceNode(div.firstChild);
			}
		}
		else //this method caused problems with image caching in Explorer
		{
			obj.outerHTML = outerHTML; //Changed by Alon
			/*var tempDiv = document.createElement('div');
			tempDiv.innerHTML = outerHTML;
			obj.replaceNode(tempDiv.firstChild);*/
		}
	},

	//Firefox stores attributes in a different manner than IE
	G2GetAttribute : function (obj,attributeName)
	{	
		if (isIE)
			return obj[attributeName];
		else if (obj!=null && obj.hasAttribute!=null && obj.hasAttribute(attributeName.toLowerCase()))
			return obj.attributes[attributeName.toLowerCase()].nodeValue;
		else 
		{
			var t = obj.attributes[attributeName.toLowerCase()];
			if (t!=null)
				return t.nodeValue;				
			else
			t = obj[attributeName.toLowerCase()] || obj[attributeName];
			return t;
		}
	},

	G2SetAttribute : function (obj,attributeName,val)
	{
		if (isIE)
			obj[attributeName] = val;
		else
			obj.attributes[attributeName.toLowerCase()].nodeValue = val;
	},

	G2CreateElement : function(t)
	{
		if (isIE || t.charAt(0)!="<")
			return document.createElement(t); //  e.g. document.createElement("DIV")
			
		var tempDiv = document.createElement("DIV");
		tempDiv.innerHTML = t;
		return tempDiv.childNodes[0];
	},

	// This method return row.rowIndex
	GetRowIndex : function(row)
	{
		var body = row.parentElement;
		if (!body)
			return -1;
		var currRow = body.firstChild;
		var index = 0;
		while(currRow)
		{
			if (currRow == row)
				return index;
			index++;
			currRow = currRow.nextSibling;
		}
		return -1;
	},

	// This methods returns a row by its index by going throw the table rowafter row 
	// instead of using the table indexing
	GetRowByIndex : function(table, rowIndex)
	{	
		var row = table.firstChild;
		if (! row)
			return null;
			
		while (row && row.tagName != "TR")
			row = row.firstChild;
			
		if (! row)
			return null;
		
		if (rowIndex == 0)
			return row;
		
		for(var i = 0; i < rowIndex; i++)
		{
			row = row.nextSibling;
			if (!row)
				return null;
		}
		return row;
	},

	// Gets a table and return the number of rows
	GetRowsLength : function(table)
	{
		var row = table.firstChild;
		if (! row)
			return 0;
			
		while (row && row.tagName != "TR")
			row = row.firstChild;
		if (! row)
			return 0;
			
		var count = 0;
		while(row)
		{
			row = row.nextSibling;
			count++;
		}
		return count;
	},
	
	GetCellByIndex : function(row, cellIndex)
	{	
		var cell = row.firstChild;
		if (! cell)
			return null;
		
		if (cellIndex == 0)
			return cell;
		
		for(var i = 0; i < cellIndex; i++)
		{
			cell = cell.nextSibling;
			if (!cell)
				return null;
		}
		return cell;
	},
	
	// Gets a row and return the number of cells
	GetCellsLength : function(row)
	{
		var cell = row.firstChild;
		if (! cell)
			return 0;
			
		var count = 0;
		while(cell)
		{
			cell = cell.nextSibling;
			count++;
		}
		return count;
	},
    G2DisableSelects : function()
    {
         if (!IE6)
            return;
            
        selects = document.getElementsByTagName('SELECT');
        for (var i = 0; i < selects.length; i++)
        {
            sel = selects[i];
            if (sel.isDisabled == false)
            {
              sel.disabled = true;
              sel.wasGenerallyDisabled  = true; 
            }
         }
          
    },
    G2EnableSelects : function()
    {
       if (!IE6)
            return;
            
        selects = document.getElementsByTagName('SELECT');
        for (var i = 0; i < selects.length; i++)
        {
            sel = selects[i];
            if (sel.isDisabled && sel.wasGenerallyDisabled)
            {
                sel.disabled = false;
                sel.wasGenerallyDisabled = false;
             }
         }
    },
    G2InsertRowToTable : function(table, index)
    {
        if (index == null)
            index = table.rows.length;
        return table.insertRow(index);
    },
    
    G2InsertCellToRow : function (row, index)
    {
        if (index == null)
            index = row.cells.length;
        return row.insertCell(index);
    },
    
    G2RemoveNode : function (elem)
    {
        elem.parentNode.removeChild(elem);
    },
    
    G2Focus : function (elem)
    {
			try{
				elem.focus();
			}
			catch(e){
				//do nothing- error when pressing the widget of combo is unclear but cause no problem. 
				// the menu is displayed as usual.
			}
    },
    
    G2HTMLEncode : function (text)
    {
	    if ( !text )
		    return '' ;

	    text = text.replace( /&/g, '&amp;' ) ;
	    text = text.replace( /</g, '&lt;' ) ;
	    text = text.replace( />/g, '&gt;' ) ;
	    return text ;
    },
    
		// Set the flash elements in the iframe to transparent
		SetFlashElementsTransparent : function(iframe)
		{
			if(isMoz)
			{
				var objects = iframe.Document.getElementsByTagName('embed');  
				for (var i = 0; i < objects.length; i++) 
				{   
					var newObject = objects[i].cloneNode(true); 
					newObject.setAttribute('wmode', 'transparent');           
					objects[i].parentNode.replaceChild(newObject, objects[i]);    
				}
			}
			else
			{
				var elementToAppend = iframe.Document.createElement('param');    
				elementToAppend.setAttribute('name', 'wmode');    
				elementToAppend.setAttribute('value', 'transparent');    
				var objects = iframe.Document.getElementsByTagName('OBJECT');    
				for (var i = 0; i < objects.length; i++) 
				{        
					var newObject = objects[i].cloneNode(true);        
					elementToAppend = elementToAppend.cloneNode(true);        
					newObject.appendChild(elementToAppend);        
					objects[i].parentNode.replaceChild(newObject, objects[i]);    
				}
			}
    }
  
}

G2_DeclareUtilInstance(G2DOM);

//the following script adds document.getElementById if it is not present
if(document.all && !document.getElementById) 
{
	document.getElementById = function(id) 
	{
		return document.all[id];
	}
}


/**********************************************************************
 *           G2 Event handling                                        *
 *     portions taken from the Prototype library version 1.4.0        *
 **********************************************************************/

G2_DeclareFunctions(
{
	G2_AttachEventWithCaller : function(element, eventName, handler, caller)
	{
		element.attachEvent(eventName, G2.GetDelegate(caller, handler));
	},
	G2_DetachEventWithCaller : function(element, eventName, handler, caller)
	{
		element.detachEvent(eventName, G2.GetDelegate(caller, handler));
	},


	G2_FireEvent : function(target, eventName, eventArgs)
	{
		if(isIE)
		{
			return target.fireEvent(eventName, eventArgs);
		}
		else
		{
			var handler = target[eventName];
			if (handler!=null)
			{
				if (typeof(handler)=="function")
					handler();
				else eval(handler);
			}
			else
				throw new Error("not supported");
		}
	},

	// This method wraps an event handler, to achieve two goals:
	// 1. When the method executes, its 'this' context will be the actual object (who 'owns' the function)
	// 2. Cross-platform event handling:
	//    In IE, the current event that is being process is stored in window.event
	//    In Mozilla (and FireFox), the event object is passed as an argument to the event handler
	G2_PrepareEvent : function(newContext,method)
	{
		if (method.preparedEvent && method.preparedEvent!=null)
		{
			return method.preparedEvent;
		}
		method.preparedEvent = function(event)
		{
			if (event==null)
				event = window.event;
			return method.call(newContext,event);
		}
		
		return method.preparedEvent;
	},

	// Attaches an event handler to the target, as a response to that event
	// The handler should be a function that receives a single argument, named 'event'.
	// It should NOT use window.event, only the supplied event.
	G2_AttachEvent : function(target, eventName, handler, capture)
	{
		if (eventName.substr(0,2)=="on")
			eventName = eventName.substring(2);
		
		//Note: Capture is only supported in FireFox
		if (!capture)
			capture = false;
		
		if(isIE)
		{
			target.attachEvent('on'+eventName, G2_PrepareEvent(target,handler));
		}
		else if (target.addEventListener!=null)
		{		
				target.addEventListener(eventName,G2_PrepareEvent(target,handler),capture);
		} 
		else
			throw new Error("not supported");
	},


	G2_DetachEvent : function(target,eventName, handler, capture)
	{
		if (eventName.substr(0,2)=="on")
			eventName = eventName.substring(2);
		
		//Note: Capture is only supported in FireFox
		if (!capture)
			capture = false;
		
		if (isIE) 
		{
				target.detachEvent('on' + eventName, G2_PrepareEvent(target,handler));
		}
		else if (target.removeEventListener!=null)
		{
				target.removeEventListener(eventName, G2_PrepareEvent(target,handler), capture);
		} 
		else 
			throw new Error("not supported");
	},
	G2StopEvent : function(event)
	{
		G2Event.stop(event);
	},
		
	// Get child element in a given element by its id
	G2_FindChildControlById : function(element, id)
	{
		if(String.EndsWith(element.id, id))
			return element;
		var child = element.firstChild;
		while(child!=null)
		{
			var found = G2_FindChildControlById(child, id);
			if(found!=null)
				return found;
			child=child.nextSibling;
		}
		return null;
	},
	
	// Get the first child element in a given element with a specified tagName
	G2_FindChildControlByTagName : function(element, tagName)
	{
		if(! element)
			return null;
		if (element.tagName)
			if(element.tagName.toLowerCase() == tagName.toLowerCase())
				return element;
		var child = element.firstChild;
		while(child!=null)
		{
			var found = G2_FindChildControlByTagName(child, tagName);
			if(found!=null)
				return found;
			child=child.nextSibling;
		}
		return null;
	},

	///
	///Recursivly searches an element from the current control and up that has a certain tag name
	///
	G2_GetParentElementByTagName : function(control, tagName)
	{	
		tagName = tagName.toUpperCase();
		return _G2_GetParentElementByTagName(control, tagName);
	},
	_G2_GetParentElementByTagName : function(control, tagName)
	{	
		if(control==null)
			return null;
		if(control.tagName==tagName) //TODO: Compare case insensitive
			return control;
		control = control.parentElement;
		return _G2_GetParentElementByTagName(control, tagName);
	},

	//returns an array of all the nodes under node with progid=parentProgId that have the 
	//specified attribute name and value 
	findControlsByAttribute : function(node, parentProgId, attributeName, attributeValue)
	{
		
		var pred = function(el)
		{
			if(G2DOM.G2GetAttribute(el, "progid")==parentProgId)
					return el;
		}
		var testAttribute = function(node)
		{
			if(G2DOM.G2GetAttribute(node, attributeName)==attributeValue)
					return node;
		}
		var curNode = searchUp(node, pred);
		if(curNode == null)
			return null;

		var childrenArray = new Array();
		
		collectChildrenByAttribute(curNode, testAttribute, childrenArray);
		return childrenArray; 
	},
	
	collectChildrenByAttribute : function (obj, predicate, childrenArray)
	{
		if (obj==null)
			obj = this;
			
		if (obj.childNodes.length==0)
			return childrenArray;
			
		var c = obj.firstChild;
		
		while(c!=null)
		{
			collectChildrenByAttribute(c,predicate, childrenArray);
			if (c.nodeType == 1 && predicate(c))
				childrenArray.push(c);
			c = c.nextSibling;
		}
	},
	
		
	//Finds an element by progid
	//Usage: provide a start node and a path seperated by dots, i.e. findControl(el, 'div1.panel2.button3');
	//       in this example, a node with progid div will be searched UPWARDS from el
	//       Then a div1 child element with progid 'panel2'will be searched DOWN.
	//       Then a panel2 child element with progid 'button3'will be searched DOWN. 
	//Returns: the first element with the last progid in the path that matches
	findControl : function(node, progIdpath)
	{
		var tokens = progIdpath.split('.');
		if(tokens.length==0)
			return null;
		var progid=tokens[0];
		tokens.splice(0,1);//Remove first token
	  
		var pred = function(el)
		{
			if(G2DOM.G2GetAttribute(el, "progid")==progid)
					return el;
		}
		var curNode = searchUp(node, pred);
		if(curNode == null)
			return null;
		if(tokens.length==0)
			return curNode;
		var newPath = tokens.join('.');
		return _findChildControl(curNode, newPath); 
	},

	_findChildControl : function(node, progIdpath)
	{
		var curNode = node;
		var tokens = progIdpath.split('.');
		if(tokens.length==0)
			return curNode;
		
		var tokensLength = tokens.length;
		for(var i=0; i<tokensLength; i++)
		{
			var progid=tokens[i];
			var pred = function(el)
			{
				if(G2DOM.G2GetAttribute(el, "progid")==progid)
					return el;
			}
			curNode = searchDown(curNode, pred);  
			if(curNode==null)
				return null;
		}
		return curNode;
	},

	searchUp : function(node, predicate)
	{
		while(node!=null)
		{
			if(predicate(node))
				return node;
			node = node.parentElement;
		}  
		return null;
	},
	searchDown : function(node, predicate)
	{
		return _searchDown(node, predicate);
	},
	_searchDown : function(node, predicate)
	{
		if(predicate(node))
				return node;
		node = node.firstChild; 
		if (node!=null && node.nodeType != 1)
			node = G2DOM.G2GetNextChild(node);
		while(node!=null)
		{
			var n = _searchDown(node, predicate);
			if(n!=null)
				return n;
			node = G2DOM.G2GetNextChild(node);
		}  
		return null;
	}
	
});

var G2Event = {
  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_SPECIAL_COPY: 17,

	//Returns the target(FF)/source(IE) element - which is the event's context
	//Usage:  Event.element( e )
  element: function(event) {
		if (event==null)
			event = window.event;
    return event.target || event.srcElement;
  },

	//Returns true if the click was a left mouse click
	//Usage:  Event.isLeftClick( e )
  isLeftClick: function(event) {
		if (event==null)
			event = window.event;
    return (((event.which) && (event.which == 1)) ||
            ((event.button) && (event.button == 1)));
  },
	
	//Returns the cursor X coordinate (relative to the page)
	//Usage:  Event.pointerX( e )
  pointerX: function(event) {
		if (event==null)
			event = window.event;
    return event.pageX || (event.clientX +
      (document.documentElement.scrollLeft || document.body.scrollLeft));
  },

	//Returns the cursor Y coordinate (relative to the page)
	//Usage:  Event.pointerY( e )
  pointerY: function(event) {
		if (event==null)
			event = window.event;
    return event.pageY || (event.clientY +
      (document.documentElement.scrollTop || document.body.scrollTop));
  },

	//Stops the event propagation
	//Usage:  Event.stop( e )
  stop: function(event) {
		if (event==null)
			event = window.event;
    if (event.preventDefault) {
      event.preventDefault();
      event.stopPropagation();
    } else {
      event.returnValue = false;
      event.cancelBubble = true;
    }
  },

  // Finds the first node with the given tagName, starting from the
  // node the event was triggered on; traverses the DOM upwards
  findElement: function(event, tagName) {
		if (event==null)
			event = window.event;
    var element = Event.element(event);
    while (element.parentNode && (!element.tagName ||
        (element.tagName.toUpperCase() != tagName.toUpperCase())))
      element = element.parentNode;
    return element;
  }/*,

  observers: false,

  _observeAndCache: function(element, name, observer, useCapture) {
    if (!this.observers) this.observers = [];
    if (element.addEventListener) {
      this.observers.push([element, name, observer, useCapture]);
      element.addEventListener(name, observer, useCapture);
    } else if (element.attachEvent) {
      this.observers.push([element, name, observer, useCapture]);
      element.attachEvent('on' + name, observer);
    }
  },

  unloadCache: function() {
    if (!Event.observers) return;
    for (var i = 0; i < Event.observers.length; i++) {
      Event.stopObserving.apply(this, Event.observers[i]);
      Event.observers[i][0] = null;
    }
    Event.observers = false;
  },

  observe: function(element, name, observer, useCapture) {
    var element = $(element);
    useCapture = useCapture || false;

    if (name == 'keypress' &&
        (navigator.appVersion.match(/Konqueror|Safari|KHTML/)
        || element.attachEvent))
      name = 'keydown';

    this._observeAndCache(element, name, observer, useCapture);
  },

  stopObserving: function(element, name, observer, useCapture) {
    var element = $(element);
    useCapture = useCapture || false;

    if (name == 'keypress' &&
        (navigator.appVersion.match(/Konqueror|Safari|KHTML/)
        || element.detachEvent))
      name = 'keydown';

    if (element.removeEventListener) {
      element.removeEventListener(name, observer, useCapture);
    } else if (element.detachEvent) {
      element.detachEvent('on' + name, observer);
    }
  }*/
};




//Add Debug.writeln support for Firefox
//In order to enable logging:
// 1. open firefox
// 2. open about:config
// 3. right-click and New->String
// 4. Name the new entry "browser.dom.window.dump.enabled"
// 5. Set its value to true
// 6. Open firefox with the -console parameter (it might complain, but it works).
// For additional information, contact Alon.
// 
// Note: Console is disabled by default. On production systems no change needs to be done.
if (typeof(Debug)=="undefined")
	Debug = {writeln:function(txt){window.dump(txt+"\n");}};
	


/**********************************************************************
 *           G2 Firefox HTMLElement extension                         *
 **********************************************************************/

if(!document.documentElement.outerHTML)
{

    HTMLElement.prototype.getAttributes = function(){
       var attStr = "";
       if(this && this.attributes.length > 0){
          for(a = 0; a < this.attributes.length; a ++){
             attStr += " " + this.attributes.item(a).nodeName + "=\"";
             attStr += this.attributes.item(a).nodeValue + "\"";
          }
       }
       return attStr;
    }

    HTMLElement.prototype.getInsideNodes = function(){
       if(this){
          var cNodesStr = "", i = 0;
          var iEmpty = /^(img|embed|input|br|hr|bgsound)$/i;
          var cNodes = this.childNodes;
          for(i = 0; i < cNodes.length; i ++){
             switch(cNodes.item(i).nodeType){
                 case 1 :
                    cNodesStr += "<" + cNodes.item(i).nodeName.toLowerCase();
                    if(cNodes.item(i).attributes.length > 0){
                       cNodesStr += cNodes.item(i).getAttributes();
                    }
                    cNodesStr += (cNodes.item(i).nodeName.match(iEmpty))? "" : ">";
                    if(cNodes.item(i).childNodes.length > 0){
                       cNodesStr += cNodes.item(i).getInsideNodes();
                    }
                    if(cNodes.item(i).nodeName.match(iEmpty)){
                       cNodesStr += " />";
                    } else {
                       cNodesStr += "</" + cNodes.item(i).nodeName.toLowerCase() + ">";
                    }
                    break;
                 case 3 :
                    cNodesStr += cNodes.item(i).nodeValue;
                    break;
                 case 8 :
                    cNodesStr += "<!--" + cNodes.item(i).nodeValue + "-->";
                    break;
             }
          }
          return cNodesStr;
       }
    }

    G2MozGetOuterHTML = function(){
       var strOuter = "";
       var iEmpty = /^(img|embed|input|br|hr|bgsound)$/i;
       switch(this.nodeType){
          case 1 :
             strOuter += "<" + this.nodeName.toLowerCase();
             strOuter += this.getAttributes();
             if(this.nodeName.match(iEmpty)){
                 strOuter += " />";
             } else {
                 strOuter += ">" + this.getInsideNodes();
                 strOuter += "</" + this.nodeName.toLowerCase() + ">";
             }
             break;
          case 3 :
             strOuter += this.nodeValue;
             break;
          case 8 :
             cNodesStr += "<!--" + this.nodeValue + "-->";
             break;
       }
       return strOuter;
    }

    G2MozSetOuterHTML = function(str){
       var iRange = document.createRange();
       iRange.setStartBefore(this);
       var strFragment = iRange.createContextualFragment(str);
       var sRangeNode = iRange.startContainer;
       iRange.insertNode(strFragment);
       sRangeNode.removeChild(this);
    }
    
    //Returns the object's document
		G2GetDocument = function (obj)
		{
			if (obj == null)
				obj = this;
			return obj.ownerDocument;
		}

		// Artificially get the 'Children' array for the given node.
		// Added as a getter to the Node class in FF
		G2GetChildren = function (obj)
		{
			if (obj==null)
				obj = this;
				
			var childrenArray = new Array();
			if (obj.childNodes.length==0)
				return childrenArray;
				
			var c = obj.firstChild;
			while(c!=null)
			{
				if (c.nodeType != Node.TEXT_NODE)
					childrenArray.push(c);
				c = c.nextSibling;
			}
			
			childrenArray.namedItem = function(name)
			{
				for (var i=0;i<this.length;i++)
				{
					var node = this[i];
					if (node.id == name)
						return node;
				}
				return null;
			}
			
			return childrenArray;
		}
		
		G2GetTagName = function(obj)
		{
			if (obj==null)
				obj = this;
			return obj.nodeName;
		}

		function G2GetParent(obj)
		{	
			if (obj==null)
				obj = this;
			return obj.parentNode;
		}
		
		function G2GetCurrentStyle(obj)
		{
			if (obj==null)
				obj = this;
			return window.getComputedStyle(obj,null);
		}
		
		function G2GetInnerText(obj)
		{
			if (obj==null)
					obj = this;
			return obj.textContent;
		}
		
		function G2SetInnerText(txt)
		{
			this.innerHTML = txt;
		}
		
		function G2ContainsChild(c)
		{
			var chlrn = this.children;
			for (var i=0,j=chlrn.length;i<j;i++)
				if (chlrn[i]==c)
					return true;
			return false;
		}
		
		function G2GetContentDocument()
		{
			return this.contentDocument;
		}
		
		function G2MozGetParentWindow()
		{
			return this.defaultView;
		}
		
		HTMLElement.prototype.contains = G2ContainsChild;
		
		//Implement insertAdjacentElement, insertAdjacentText and insertAdjacentHTML
		HTMLElement.prototype.insertAdjacentElement = function(where,parsedNode)
		{
			switch (where)
			{
				case "beforeBegin":
					this.parentNode.insertBefore(parsedNode,this)
					break;
				case "afterBegin":
					this.insertBefore(parsedNode,this.firstChild);
					break;
				case "beforeEnd":
					this.appendChild(parsedNode);
					break;
				case "afterEnd":
					if (this.nextSibling)
						this.parentNode.insertBefore(parsedNode,this.nextSibling);
					else 
						this.parentNode.appendChild(parsedNode);
					break;
			}
		}
		
		HTMLElement.prototype.insertAdjacentHTML = function(where,htmlStr)
		{
			var r = this.ownerDocument.createRange();
			r.setStartBefore(this);
			var parsedHTML = r.createContextualFragment(htmlStr);
			this.insertAdjacentElement(where,parsedHTML)
		}
		
		HTMLElement.prototype.insertAdjacentText = function(where,txtStr)
		{
			var parsedText = document.createTextNode(txtStr)
			this.insertAdjacentElement(where,parsedText)
		}
		var lastGivenID = 1000;			
		function G2GetElementUniqueID ()
		{
			if (this._uniqueID) //already defined
				return this._uniqueID;
			//Generate using counter
			this._uniqueID = lastGivenID;
			lastGivenID++;
			return this._uniqueID;
		}	
		
		function G2GetEventSourceElement() 
		{
			var node = this.target;
			while (node.nodeType != 1) node = node.parentNode;
			return node;
		}
		
		function G2GetProgId()
		{
			if (this.hasAttribute("progid"))
				return this.attributes["progid"].nodeValue;
		}
		
		HTMLElement.prototype.attachEvent = function(eventName, handler, capture) //Simulate AttachEvent on Mozilla
	  {
	    if (eventName.substr(0,2)=="on")
		  	eventName = eventName.substring(2);		  
		  if (!capture)
		    capture = false;
	    this.addEventListener(eventName,handler,capture);
	  }
	  
	  HTMLElement.prototype.detachEvent = function(eventName, handler, capture) //Simulate DetachEvent on Mozilla
	  {
	    if (eventName.substr(0,2)=="on")
		  	eventName = eventName.substring(2);		  
		  if (!capture)
		    capture = false;
	    this.removeEventListener(eventName,handler,capture);
	  }
		
		function defineStyleProperties(names)
		{
			for(var i=0;i<names.length;i++)
			{
				var shortName = names[i];
				var pixelName = "pixel"+shortName.substring(0,1).toUpperCase()+shortName.substring(1);
				defineStyleProperty(shortName,pixelName);
			}
		}

		function defineStyleProperty(shortName,pixelName)
		{
			CSSStyleDeclaration.prototype.__defineGetter__(pixelName,function(){return parseInt(this[shortName])});
			CSSStyleDeclaration.prototype.__defineSetter__(pixelName,function(v){this[shortName]=v+"px";});
		}
		
		
		defineStyleProperties(["width","height","left","top"]);
		
		/*function Selection(doc)
		{		
		  this._doc = doc;
		}
		Selection.prototype.createRange = function(element)
		{
		  debugger;
		  var sel = window.getSelection();		  
		  var range = null;
		  if (sel.rangeCount==0)
		  {
		    if (element!=null)
		    {
 		      range = document.createRange();
 		      range.selectNodeContents(element);
 		      //range.setStart(element, 0);
 		      //var len = (element.nodeType==1 && element.tagName=="INPUT") ? element.value.length : element.innerText.length;
          //range.setEnd(element,0);
          //range.expand
		      sel.addRange(range);
		    }
		  }
		  else range = sel.getRangeAt(0);
		  var rng = new G2MozRange(range);
		  return rng;
		}
    function G2GetDocumentSelection()
		{
		  if (this._emulatedSelectionObject==null)
		    this._emulatedSelectionObject = new Selection(this);
		  return this._emulatedSelectionObject;
		}
		
		function G2MozRange(rng)
		{
		  this._range = rng;
		}
		function G2MozRange_GetText()
		{
		  return this._range.toString();
		}
		function G2MozRange_SetText(value)
		{
		  //this.commonAncestorContainer.innerText = value;
		  debugger;
		  var lastElement = this._range.endContainer;
		  if (lastElement==null)
		    debugger;
		  if (lastElement.nodeType==1)
		  {
		    if (lastElement.tagName=="INPUT")
		    {
		      lastElement.value += value;
		    }
		    else
		      lastElement.innerText += value;
		  }
		  else if (lastElement.nodeType==3)
		  {
		    lastElement.nodeValue += value;
		  }
		    
		}
		G2MozRange.prototype.__defineGetter__("text",G2MozRange_GetText);
		G2MozRange.prototype.__defineSetter__("text",G2MozRange_SetText);
		*/
		//Fix for firefox BACK
		window.addEventListener("pageshow",function(e){if(e.persisted) {window.location.href = window.location.href;}},false);
    
    HTMLDocument.prototype.__defineGetter__("parentWindow",G2MozGetParentWindow);
    //HTMLDocument.prototype.__defineGetter__("selection",G2GetDocumentSelection);
    HTMLElement.prototype.__defineGetter__("progid",G2GetProgId);
    HTMLElement.prototype.__defineGetter__("outerHTML",G2MozGetOuterHTML);
		HTMLElement.prototype.__defineSetter__("outerHTML",G2MozSetOuterHTML);
		HTMLElement.prototype.__defineGetter__("innerText",G2GetInnerText);
		HTMLElement.prototype.__defineSetter__("innerText",G2SetInnerText);
		HTMLElement.prototype.__defineGetter__("children",G2GetChildren);
		HTMLElement.prototype.__defineGetter__("document",G2GetDocument);
		HTMLElement.prototype.__defineGetter__("tagName",G2GetTagName);
		HTMLElement.prototype.__defineGetter__("parentElement",G2GetParent);
		HTMLElement.prototype.__defineGetter__("currentStyle",G2GetCurrentStyle);
		HTMLElement.prototype.__defineGetter__("uniqueID",G2GetElementUniqueID);
		HTMLIFrameElement.prototype.__defineGetter__("Document",G2GetContentDocument);
		Event.prototype.__defineGetter__("srcElement", G2GetEventSourceElement);
		
		
}
// returns true if the string 's' ends with the string 'endsWith'
String.EndsWith = function(s, endsWith)
{
	if(s==null)
		return endsWith==null;
	return s.substr(s.length-endsWith.length, endsWith.length)==endsWith;
}


//this function gets a control
//and disables/enables it and all its children recursively
SetControlDisability = function(control, disable)
{
	if(control == null)
		return;
	if (control.supportdisabledcss == "true")
	{
		control.disabled = disable;
		//we want the main css class to be standing alone
		//so when disabling, replace css class by disabled css class
		//when enabling if there are other classes, just remove disabled
		if (disable || control.className == control.disabledcssclass)
			G2_ReplaceCssClass(control, control.cssclass, control.disabledcssclass, disable);
		else
			G2_RemoveCssClass(control, control.disabledcssclass);
	}
	//we don't want to replace the initial css class but to add the disable css class
	else if (control.supportdefauldisabledtcss == "true") 
	{
		control.disabled = disable;
		if (disable)
			G2_AddCssClass(control, control.disabledcssclass);
		else
			G2_RemoveCssClass(control, control.disabledcssclass);
	}
	G2_VerifyControlInitialized(control);
	if(typeof(control.setEnabled)=="function")
		control.setEnabled(!disable);
	else
	{
		control.disabled = disable;
		SetControlChildrenDisability(control, disable);
	}
}

SetControlChildrenDisability = function(control, disable)
{
		if(control.children.length > 0)
		{
			var child = control.children[0];
			//lets be sure we are talking about html tag
			while(child != null)
			{
				if(child.nodeType == 1)
				{
					child.disabled = disable;
					SetControlDisability(child, disable);
				}
	
				child = child.nextSibling;
			}
		}
	}
	

//Used in Dialog.aspx

var allowTitleUpdate = false;
var allowIframeResize = true;
var topdocument = document;
var PopupMinWidth = 250;
var PopupMinHeight = null;


// UpdateTitle is called to update the window's title
// Logic: When the WindowTitle attribute is set in G2PopupWindow, it is used
//        Otherwise, IE6 popups will have the default "Gilboa" title
//                   IE7 popups will use the content document's title
// (Related to case 4771)
UpdateTitle = function()
{
	if (!allowTitleUpdate)
		return;
	
	var ifrm = document.getElementById('IFRM');
	
	// Adi E: The try...catch was added due to a javaScript 'Permission denied' error in 'Use SSL' mode (case 4258) 
	try
	{
	    if (ifrm.Document!=null && ifrm.Document.title!=null)				
	    {
		    window.top.document.title = ifrm.Document.title;
	    }
	}
	catch(err)
  {
  }
}

// UpdateInnerFrameSize is called whenever the content is suspected to change its size
// The order of events should generally be:
//         1. Document content has changed
//         2. Document called G2Page_AutoSize  (common.js)
//         3. UpdateInnerFrameSize is called to update the IFRAME's size to match the content (shrink/expand)
//         4. G2Page_AutoSize is called to update the popup window's size to match the iframe
// If size was explicitly specified, use it. Otherwise, get from page
UpdateInnerFrameSize = function(doc)
{
	if (!allowIframeResize)
		return;
	if (!doc)
		doc = document;
	var ifrm = doc.getElementById('IFRM');		
	var innerDocument = ifrm.Document;				
		
	try
	{		
		if (innerDocument!=null && innerDocument.documentElement!=null && innerDocument.documentElement.scrollWidth)
		{	
			ifrm.style.width = maxInt(ifrm.style.width,parseInt(innerDocument.documentElement.scrollWidth)+10)+"px";	
			var prevW	= parseInt(innerDocument.documentElement.scrollWidth);			
			var prevH = parseInt(innerDocument.documentElement.scrollHeight);			
			Debug.writeln('Resizing popup. Initial estimated size: '+prevW+" x "+prevH);
			var initialWidth = prevW;
			do
			{
				prevW	= parseInt(innerDocument.documentElement.scrollWidth);
				ifrm.style.width = (parseInt(ifrm.style.width)-1)+"px";
			} while (parseInt(innerDocument.documentElement.scrollWidth)<prevW && parseInt(innerDocument.documentElement.scrollHeight)==prevH);
			
			//go back one step
			var newWidth = (parseInt(ifrm.style.width)+1);
			if (PopupMinWidth!=null)
				newWidth = maxInt(newWidth,PopupMinWidth);				
			ifrm.style.width = newWidth+"px";
		}
		
		if (innerDocument!=null && innerDocument.documentElement!=null && innerDocument.documentElement.scrollHeight)
		{
			var newHeight = parseInt(innerDocument.documentElement.scrollHeight+1);
			if (PopupMinHeight!=null)
				newHeight = maxInt(newHeight, PopupMinHeight);
			ifrm.style.height = newHeight+"px";
		}
	}
	catch(e)
	{
	}		
	ResizeDialogWindow(doc);
}



//Initializes the iframe and enables size updates (and title updates if title was not explicitly set)
InitIFrame = function()
{
	var ifrm = document.getElementById('IFRM');
	var popupWindowId = window.dialogArguments.url; //Extract WindowID parameter
	popupWindowId = popupWindowId.substring(popupWindowId.indexOf('&WindowID=')+10);
	popupWindowId = popupWindowId.substring(0,popupWindowId.indexOf('&'));
//	window.onunload = function() //Non-SSL Pages set dialogArguments.obj.CloseEventFired to true
//	{
//	    if (!dialogArguments.obj.CloseEventFired)
//	        dialogArguments.obj.G2_FirePopupClosed(popupWindowId,'',true);
//	}
	
	//If title was explicitly specified, use it
	if (window.dialogArguments.title!=null && window.dialogArguments.title!="")
	{
		window.top.document.title = window.dialogArguments.title;
	}
	else 
		allowTitleUpdate = true; //Allow updating the title when the page is loaded
	
  
	if (window.dialogArguments.width && ifrm.style.height)
	{		
		//TO DO:Fix G2PopupWindow_ExtractParameter in Common.js that will never return Nan.
	  var resized = false;  		
		if (!isNaN(window.dialogArguments.width))
		{
		  ifrm.style.width = window.dialogArguments.width+"px";
		  resized = true;
		}
		
		if (!isNaN(window.dialogArguments.height))
		{
		  ifrm.style.height = window.dialogArguments.height+"px";
		  resized = true;
		}
		
		if (resized)
			ResizeDialogWindow();//window.dialogArguments.width, window.dialogArguments.height);
	}
	
	if (window.dialogArguments.minWidth)
		PopupMinWidth = window.dialogArguments.minWidth;
	if (window.dialogArguments.minHeight)
		PopupMinHeight = window.dialogArguments.minHeight;
	
	allowIframeResize = window.dialogArguments.autoSize=="1";
		
	ifrm.src = window.dialogArguments.url; //Set IFrame source
}

//This method is calls UpdateInnerFrameSize with the top document as a context
G2Dialog_AutoSize = function ()
{
  pendingTimeout = -1;
	UpdateInnerFrameSize.apply(topdocument);	
}

var pendingTimeout = -1;
//This method schedules a call to G2Dialog_AutoSize in 300 mSec. if a call is already scheduled - it does nothing.
scheduleRefresh = function()
{	
	if (pendingTimeout!=-1)
	  return;
	
	pendingTimeout = window.setTimeout(G2Dialog_AutoSize,300);
}

//This method is called whenever a [new] image in the document has been loaded
contentImgReady = function(e)
{
	scheduleRefresh();			
	
	//Remove event handler to save some memory
	try
	{
		G2_DetachEvent(this,"onload",contentImgReady);
	} catch (e)
	{
		//An exception might be thrown when detaching events.
	}
}

//This method traverses the [new] images in the document, and subscribes to their Load event.
attachToImagesLoading = function()
{
	try
	{
		var ifrm = document.getElementById('IFRM');		
		var innerDocument = ifrm.Document;				
		var imgs = innerDocument.getElementsByTagName("IMG");
		for (var i=0;i<imgs.length;i++)
		{
			if (!imgs[i].scheduleRefreshAttached)
			{
				G2_AttachEvent(imgs[i],"onload",contentImgReady);
				imgs[i].scheduleRefreshAttached = true;
			}
		}
	} 
	catch(e) //Security violations etc.
	{
		G2_Trace("attachToImagesLoading", e.message);
	}
}

//The following line enables UpdateInnerFrameSize() calls. do not remove it
//This method is called by G2Page_AutoSize.
G2Dialog_NotifyContentChanged= function(noImages) 
{
	if (!noImages)
		attachToImagesLoading(); 		

	scheduleRefresh(); 
}

//Resizes the dialog window to be able to contain the IFRAME (use scrollbars as last resort)
function ResizeDialogWindow(/*windowWidth, windowHeight*/)
{
	if (G2_IsInPopup())
		return;
 
	var ifrm = document.getElementById('IFRM');	
	var ifrmWidth = parseInt(ifrm.style.width);
	var ifrmHeight = parseInt(ifrm.style.height);
	
  var sizeElement  = document.documentElement;
  var clientWidth  = ifrmWidth+25;
  var clientHeight = ifrmHeight;
		
  var screenHeight = screen.availHeight-50; //leave room for taskbar etc.
  var screenWidth  = screen.availWidth;
  
	if (IE6)
	{
		clientHeight += 75; //IE6 considers the window border to part of the height
	}
	
  var minWidth  = minInt(screenWidth,clientWidth);
	var minHeight = minInt(screenHeight,clientHeight);
	
	// Adi E: The try...catch was added due to a javaScript 'Permission denied' error in 'Use SSL' mode (case 4258)
	try
	{
		window.top.dialogWidth  = minWidth + "px";
		window.top.dialogHeight = minHeight + "px";		
		Debug.writeln('Dialog '+window.dialogArguments.url+' resized to '+minWidth+'(w) x'+minHeight+' (h)');
	}
	catch(err)
  {
  }
  
}

document.body.G2Dialog_NotifyContentChanged = G2Dialog_NotifyContentChanged;
// JScript File

//  function ExportToExcel2003(objToExport)
//  {
//        var sHTML;
//        var oExcel;
//        var oBook;
//        
//        sHTML = document.all.item(objToExport).outerHTML;
//        oExcel =  new ActiveXObject("Excel.Application");
//        
//        oBook.HTMLProject.HTMLProjectItems("Sheet1").Text = sHTML;
//        oBook.HTMLProject.RefreshDocument;
//        oExcel.Workbooks.Add(oBook);
//        oExcel.Visible = true;
//        oExcel.UserControl = true;
//  }
  
function ExportToExcel(tableID)
{
	// get the current table
	var curTable = $(tableID);
	
	// copy the table so the client wont see the removal of the icons
	// --------------------------------------------------------------
	var table = document.createElement('table');
	
	var oTBody = document.createElement('tbody');
	table.appendChild(oTBody);
	
	var rowNum = curTable.rows.length;
	var cellNum = curTable.rows[0].cells.length;
	for(var i = 0; i < rowNum; i++)
	{
		var curRow = document.createElement('tr');
		for(var j = 0; j < cellNum; j++)
		{
			if(curTable.rows[i].cells[j] != null)
			{
				var curCell = document.createElement('td');
				curCell.innerHTML = curTable.rows[i].cells[j].innerHTML;
				curRow.appendChild(curCell);
			}
		}
		
		oTBody.appendChild(curRow);
	}
	table.appendChild(oTBody);
	
	// Get rid of the image in the titles
	// ----------------------------------
	var cell;
	for(var k = 0; k < cellNum; k++)
	{
		cell = table.rows[0].cells[k];
		if(WebForm_GetElementByTagName(cell, 'span') != null)
			cell.innerHTML = WebForm_GetElementByTagName(cell, 'span').innerHTML;
		else if(WebForm_GetElementByTagName(cell, 'a') != null)
			cell.innerHTML = WebForm_GetElementByTagName(cell, 'a').innerText;
	}
	
	var frm = document.createElement("iframe");
	frm.style.display = "none";
	document.body.appendChild(frm);
	frm.Document.write(table.outerHTML);
	frm.Document.execCommand('SaveAs', false, 'ExcelReport.xls');
}
<!--
///////////////////////////////////////////////////////////////////////
//     This script was designed by Erik Arvidsson for WebFX          //
//                                                                   //
//     For more info and examples see: http://webfx.eae.net          //
//     or send mail to erik@eae.net                                  //
//                                                                   //
//     Feel free to use this code as lomg as this disclaimer is      //
//     intact.                                                       //
///////////////////////////////////////////////////////////////////////
//
// NOTE: This is not compatible with FF (Alon).
// Change document.all to document.getElementById
var checkZIndex = true;

var dragobject = null;
var tx;
var ty;

var ie5 = document.all != null && document.getElementsByTagName != null;

function getReal(el) {
	temp = el;

	while ((temp != null) && (temp.tagName != "BODY")) {
		if ((temp.className == "moveme") || (temp.className == "handle")){
			el = temp;
			return el;
		}
		temp = temp.parentElement;
	}
	return el;
}

function moveme_onmousedown() {
	el = getReal(G2Event.element(event))
	
	if (el.className == "moveme" || el.className == "handle") {
		if (el.className == "handle") {
			tmp = el.getAttribute("handlefor");
			if (tmp == null) {
				dragobject = null;
				return;
			}
			else
				dragobject = eval(tmp);
		}
		else 
			dragobject = el;
		
		if (checkZIndex) makeOnTop(dragobject);
		
		ty = window.event.clientY - getTopPos(dragobject);
		tx = window.event.clientX - getLeftPos(dragobject);
		
		window.event.returnValue = false;
		window.event.cancelBubble = true;
	}
	else {
		dragobject = null;
	}
}

function moveme_onmouseup() {
	if(dragobject) {
		dragobject = null;
	}
}

function moveme_onmousemove() {
	if (dragobject) {
		if (window.event.clientX >= 0 && window.event.clientY >= 0) {
			dragobject.style.left = window.event.clientX - tx;
			dragobject.style.top = window.event.clientY - ty;
		}
		window.event.returnValue = false;
		window.event.cancelBubble = true;
	}
}

function getLeftPos(el) {
	if (ie5) {
		if (el.currentStyle.left == "auto")
			return 0;
		else
			return parseInt(el.currentStyle.left);
	}
	else {
		return el.style.pixelLeft;
	}
}

function getTopPos(el) {
	if (ie5) {
		if (el.currentStyle.top == "auto")
			return 0;
		else
			return parseInt(el.currentStyle.top);
	}
	else {
		return el.style.pixelTop;
	}
}

function makeOnTop(el) {
	var daiz;
	var max = 0;
	var da = document.all;
	
	for (var i=0; i<da.length; i++) {
		daiz = da[i].style.zIndex;
		if (daiz != "" && daiz > max)
			max = daiz;
	}
	
	el.style.zIndex = max + 1;
}

if (document.all) { //This only works in IE4 or better
	document.onmousedown = moveme_onmousedown;
	document.onmouseup = moveme_onmouseup;
	document.onmousemove = moveme_onmousemove;
}

var msgbox;
function G2_Alert(title, message)
{
  msgbox = document.createElement("DIV");
  msgbox.id= "msgbox";
  theForm.appendChild(msgbox);
	msgbox.className="msgon"; 
	msgbox.innerHTML='<TABLE WIDTH="100%" CELLSPACING="0" CELLPADDING="3" BORDER="">'
	              + '<TR><TD BGCOLOR="#FF0000"><DIV CLASS="handle" HANDLEFOR="msgbox">'
				  + title 
				  + '</DIV></TD>'
				  + '<TD ALIGN="center" BGCOLOR="#000000" WIDTH="2%"><SPAN CLASS="msgbar" onMousedown="msgbox.className=\'msgoff\';">&nbsp;X&nbsp;</SPAN></TD></TR>'
				  + '<TR><TD BGCOLOR="#FFFFE1" COLSPAN=2><DIV CLASS="boxtext">' 
				  + message 
				  + '</DIV></TD></TR></TABLE>';
}

//-->

//Change this key to force reloading items from server between versions
var G2ComboBox_VERSION = "3_9";
var G2ComboBox_MIN_SIZE_FOR_BG_INIT = 10000;
var G2ComboBox_BG_INIT_BLOCK_SIZE = 100;
var G2ComboBox_IgnoreKeyUps;

G2_DeclareFunctions(
{
	G2ComboBox_Init : function(cb, e)
	{
		if(typeof(cb)=="string")
			cb = document.getElementById(cb);
		if(cb==null) //happen in multi-view
			return;
		if(cb.g2IsInited)
			return;
			
		cb.g2IsInited = true;
		
		var elementMap = G2ComboBox_FindElements(cb, ["TBText", "TBValue", "Widget"]);
		var tbText = elementMap["TBText"];
		
		if(e!=null)
		{
		  if(e.type=="focus" /*|| e.type=="mousedown" */)
		  {
		    if(tbText.isFocusingAfterPostback==true)
		    {
		      tbText.isFocusingAfterPostback=null;
		    }
		    else
		    {
			    cb.showPopupWhenLoaded = true;
			    G2StopEvent(e);
			  }
		  }
		}
		
		
   
		G2DOM.G2TransferAttributes(cb);

		cb.g2OnSelectedValueChanged = new Array();//event
		cb.AllowNull = cb.nullvalue != null || cb.nulldisplaytext != null;
		cb.alwaysshownullparentitems = cb.alwaysshownullparentitems=="true";
		cb.filterallwhenparentnull = cb.filterallwhenparentnull=="true";
		cb.showFixField = cb.showFixField=="true";

		var itemsPopup = window.top.document.createElement("DIV");

		var popup = window.top.document.createElement("DIV");
//		popup.style.display = "none";
		popup.g2closepopup = "false"; //to allow this popup to remain on the document
		popup.className = cb.popupcssclass || "G2ComboBox_Popup";
		popup.doesNotContainInputs = true; //optimization
		popup.appendChild(itemsPopup);
		
		if(cb.style.zIndex)
			popup.style.zIndex = cb.style.zIndex;

		if (cb.showFixField == true)
		{
			var fixField = window.top.document.createElement("DIV");
			fixField.className = "G2ComboBoxField";
			// build fix field
			fixField.innerText = cb.fixFieldDisplayText;
			fixField.onclick = function()
			{
				FixFieldClick(cb);
			};

			popup.appendChild(fixField);
		}
		popup.onBeforeClose = G2ComboBox_BeforeClose;
		popup.onOpened = G2ComboBox_Opened;
		cb.popup = popup;
		popup.combo = cb;
		popup.popupParentElement = cb;
		popup.onPopupClosed = function()
		{
		  G2ComboBox_VerifySelectedValue(cb);
		};
		
		window.onscroll=function()
		{
			G2ComboBox_HidePopup(cb);
		}
		
		G2_PreventInputPost(tbText.id);
		cb.tbText = tbText;
	 
		/// this is on purpose - to avoid the validators to attach to this event
		G2_AttachEvent(tbText,"onchange",function(){});
	
		G2_AttachEvent(tbText,"onkeydown",
		function(event)
		{
			switch(event.keyCode)
			{
		      
				case 13: //Enter
					if (cb.popup.style.display=="none")
					{												
						return true;
					}		
					//close PopUp
					G2ComboBox_HidePopup(cb);			
					//the last action will be the focus.
					window.setTimeout(function(){try {tbText.focus();}catch(e){}},10);					
					var item = cb.selectedItem;
					if (item!=null)					
							G2ComboBox_SetSelectedValue(cb, item.value, item);
					return true;
				case 27: //Esc
					G2Event.stop(event);					
				case 9: //Tab
					//close PopUp
					G2ComboBox_HidePopup(cb);			
					//the last action will be the focus.
					//window.setTimeout(function(){try {tbText.focus();}catch(e){}},10);					
					var item = cb.selectedItem;
					if (item!=null)					
							G2ComboBox_SetSelectedValue(cb, item.value, item);
					return true;		
			}	  
		});
		G2_AttachEvent(tbText,"onkeyup",
		function(event)
		{	
			//if(G2CKeys[event.keyCode]==null)
			G2ComboBox_OnKeyUp(cb,event);
		});
		
		
		G2_AttachEvent(tbText,"onfocus",
		function(event)
		{
			G2ComboBox_OnFocus(cb,event);
		});
		if(cb.onfocus)
		{
			G2_AttachEvent(tbText,"onfocus", 
			function(event)
			{
				eval(cb.onfocus);
			});
		}
		
		G2_AttachEvent(tbText,"onblur",
		function(event)
		{
			G2ComboBox_OnBlur(cb,event);
		});
		
		if(cb.onblur)
		{
			G2_AttachEvent(tbText,"onblur",
			function(event)
			{
				 eval(cb.onblur);
			});
		}
		
		G2_AttachEvent(tbText,"ondeactivate",
		function(event)
		{
			G2ComboBox_OnDeactivate(cb,event);
		});
		
		
		var tbValue = elementMap["TBValue"];
		if(tbValue==null)
		{
			throw new Error(String.Format("G2ComboBox's {0} hidden field {1} wasn't found", cb.id, cb.hfName));
		}
		EnableSupportForPartialPostData(tbValue);
		cb.tbValue = tbValue;
	  
		var widget = elementMap["Widget"];
		cb.widget = widget;
	  
	  
	  
		G2_AttachEvent(widget,"onmousedown",
		function(e)
		{
		  if(G2Event.element(e) != this)
			  return;
		  G2Event.stop(e);
		  G2ComboBox_OnWidgetMouseDown(e,cb);
		});
		//attach event - removed by dan-el - doesn't work.. 
		G2_AttachEvent(tbText,"onmousedown",
		function(event)
		{
			if(G2Event.element(event) != this)
				return;
			G2Event.stop(event);
			G2ComboBox_TogglePopup(cb, false,event);
			var tb = this;
			window.setTimeout(function(){try {tb.select();}catch(e){}},0);
		}
		);

		if (isMoz)
		{
			//Special Mozilla/FireFox ondeactivate replacement. Still does not work (Alon)
			cb.hideSelf = function()
			{
				G2ComboBox_HidePopup(cb);
			}
		}
		G2ComboBox_GetParentComboBox(cb);
	  
		if(cb.lazyloaditems!="true" || cb.showPopupWhenLoaded)
			G2ComboBox_LoadItems(cb);
	  
		//cb.originalValue = G2ComboBox_GetSelectedValue(cb);
		G2ComboBox_SetOriginalValue(cb);
		cb.g2PerformUndo = G2ComboBox_PerformUndo;
		cb.g2SetOriginalValue = G2ComboBox_SetOriginalValue;
		cb.g2IsDirty = G2ComboBox_IsDirty;
		
		if(cb.disabledcssclass!=null)
		{
			G2_AttachEvent(cb,"onpropertychange",
			function(e)
			{
				if(e.propertyName=="disabled")
					G2_ReplaceCssClass(cb, cb.cssclass, cb.disabledcssclass, cb.isDisabled);
			});
		}
		cb.setEnabled = function(value)
		{
			G2ComboBox_SetEnabled(cb, value);
		}
		
		if (isMoz)
		{
			if (e != null)
				G2ComboBox_OnWidgetMouseDown(e,cb);
		}
	},
	
	G2ComboBox_OnParentComboSelectedValueChanged : function(cbid)
	{
		G2ComboBox_Init(cbid);
	},
	
	G2ComboBox_OnWidgetMouseDown : function(e,cb)
	{
	   
	  //ensure focus if items should be loaded
	  G2DOM.G2Focus(cb.tbText);
	  cb._wasFocused = true;
		G2ComboBox_TogglePopup(cb, false,e);
    //ensure focus if items should not be loaded
	  G2ComboBox_Focus(cb);
	},
	
	G2ComboBox_SetEnabled : function(cb, value)
	{
		cb.disabled = !value;
		if(cb.disabledcssclass!=null)
			G2_ReplaceCssClass(cb, cb.cssclass, cb.disabledcssclass, cb.isDisabled);
		SetControlChildrenDisability(cb, !value);
	},
	G2ComboBox_IsDirty : function(cb)
	{
		cb = cb || this;
		return cb.originalValue!=G2ComboBox_GetSelectedValue(cb);
	},
	
		
	/*changing null value of combo box.
		in case the current value of the combo is null value, updating
		tbText with the new null value*/
	G2ComboBox_SetNullDisplayText : function(cb, text)
	{				
		if(!cb.g2IsInited)
		{
			G2ComboBox_Init(cb);
			if(cb.lazyloaditems=="true")
				G2ComboBox_LoadItems(cb);
		}
		var hasNullValue = (cb.tbText.value == cb.nulldisplaytext)
		var item = G2ComboBox_GetItemByValue(cb,cb.nullvalue);
		cb.nulldisplaytext = text;
		if (!item)
			return;
			
		item.text = text;
		if (text=="")
			item.innerHTML="&nbsp";
		else			
			item.innerText = text;
		if(hasNullValue)
			cb.tbText.value = cb.tbText.defaultValue = text;
	},
	

	G2ComboBox_PerformUndo : function(cb)
	{
		cb = cb || this;
		G2ComboBox_SetSelectedValue(cb, cb.originalValue);
		//G2.undoNotifyInputChanged(cb.tbValue);
	},
	G2ComboBox_SetOriginalValue : function(cb)
	{
		cb = cb || this;
		cb.originalValue = G2ComboBox_GetSelectedValue(cb);
		G2.undoNotifyInputChanged(cb.tbValue);
	},
	G2ComboBox_Focus : function(cb)
	{
		window.setTimeout(function()
		{
			try //temprary, ask Dan-El
			{
				cb.tbText.focus();
			}
			catch(e)
			{
			}
		}, 50);
	},

	G2ComboBox_EnsureItems : function(cb)
	{
		if(cb._itemsLoaded!=true)
		 G2ComboBox_LoadItems(cb); 
	},

	G2ComboBox_OnBlur : function(cb)
	{
		if (cb.ClientOnBlur)
			eval(cb.ClientOnBlur);
	},
	G2ComboBox_OnDeactivate : function(cb)
	{
	//case 8718
	//	document.selection.empty();
	},

	G2ComboBox_OnFocus : function(cb)
	{
		if (cb.ClientOnFocus)
			eval(cb.ClientOnFocus);
		
		cb.tbText.select();
		cb.previouslySelectedItem = cb.selectedItem;
	},

	G2ComboBox_ShouldIgnoreKeyUp : function(keyCode)
	{
		if(G2ComboBox_IgnoreKeyUps==null)
		{
			G2ComboBox_IgnoreKeyUps = [G2Keys.tab, G2Keys.left, G2Keys.right, G2Keys.home, G2Keys.end, G2Keys.shift, G2Keys.ctrl, G2Keys.alt];
		}
		for(var i=0;i<G2ComboBox_IgnoreKeyUps.length;i++)
		{
			if(G2ComboBox_IgnoreKeyUps[i]==keyCode)
				return true;
		}
		return false;
	},
	
	
	G2ComboBox_OnKeyUp : function(cb,event)
	{
		cb.keyCode = event.keyCode;
		if(G2ComboBox_ShouldIgnoreKeyUp(event.keyCode))
			return;

//    if(event.keyCode==G2Keys.backspace)
//		{
//		  if(cb.tbText.value=="")
//		    G2ComboBox_SelectFirstItem(cb);
//		}
		if(event.keyCode==G2Keys.esc)
		{
			return;
		}
		if(event.keyCode==G2Keys.down)
		{
			G2ComboBox_SelectNextItem(cb);
			return;
		}
		else if(event.keyCode==G2Keys.up)
		{
			G2ComboBox_SelectPrevItem(cb);
			return;
		}
		else if(event.keyCode==G2Keys.enter)
		{
			cb.tbText.blur();
			return;
		}
	  
		if(cb.FilterItemsByTextThreadId!=null)
		{
			window.clearTimeout(cb.FilterItemsByTextThreadId);
			cb.FilterItemsByTextThreadId = null;
		}
		var autoSelect = true;
	  
		if (event.keyCode == G2Keys.del)
			autoSelect = false;
			
		if(!G2ComboBox_IsPopupOpened(cb))
			G2ComboBox_ShowPopup(cb,null,event);

		cb.FilterItemsByTextThreadId = window.setTimeout
		(
			function(event)
			{
				G2ComboBox_FilterItems(cb, true, autoSelect);
			}
		, 100);
		
	},

	G2ComboBox_OnSelectedValueChanged : function(cb)
	{
		//The following line was removed - Combobox is now NOT validated when the selected value changes
		//G2Validator_ValidateElementOnChange(cb.tbValue);

		if(cb.UpdateValueOnControl!=null)
		{
			var value = G2ComboBox_GetSelectedValue(cb);
			G2ComboBox_SetSelectedValue(cb.UpdateValueOnControl, value);
		}
		if(cb.g2onselectedvaluechanged!=null)
		{
			if(cb.g2onselectedvaluechanged_Compiled==null)
				cb.g2onselectedvaluechanged_Compiled = new Function(cb.g2onselectedvaluechanged);
			cb.g2onselectedvaluechanged_Compiled();
		}
		for(var i=0;i<cb.g2OnSelectedValueChanged.length;i++)
		{
			cb.g2OnSelectedValueChanged[i](cb);
		}
		if(cb.OnClientChange!=null)
		{
			var value = G2ComboBox_GetSelectedValue(cb);
			window[cb.OnClientChange](cb, value);
		}
	},

	G2ComboBox_IsFocused : function(cb)
	{
		return cb.tbText==document.activeElement;
	},

	G2ComboBox_LoadItems : function(cb)
	{
	  if(cb._itemsLoaded==true)
	    return;
		cb._itemsLoaded = true;
		var stopper = new Stopper();
		stopper.start();
	 
		cb._wasFocused = G2ComboBox_IsFocused(cb);
		cb.disabled = true;
		var loadingtext = cb.loadingtext;
		if(loadingtext==null)
		  loadingtext = "Loading...";
		if(cb.tbText.value!="")
		{
		  cb.valueBeforeLoadStart = cb.tbText.value;
		}
		G2ComboBox_SetText(cb, loadingtext);
		
		var sb = new Array();
		sb.push(G2_MapPath("~/CachePage.ashx?"));
		G2ComboBox_WriteUrlNameValue(sb, "Version", G2ComboBox_VERSION);
		G2ComboBox_WriteUrlNameValue(sb, "CacheDataKey", cb.cachedatakey);
		G2ComboBox_WriteUrlNameValue(sb, "DataTextField", cb.datatextfield);
		G2ComboBox_WriteUrlNameValue(sb, "DataValueField", cb.datavaluefield);
		G2ComboBox_WriteUrlNameValue(sb, "ParentDataValueField", cb.parentdatavaluefield);
		G2ComboBox_WriteUrlNameValue(sb, "NullValue", cb.nullvalue);
		G2ComboBox_WriteUrlNameValue(sb, "NullDisplayText", cb.nulldisplaytext);
		G2ComboBox_WriteUrlNameValue(sb, "AllowNull", cb.AllowNull);
		G2ComboBox_WriteUrlNameValue(sb, "DataTextFormatString", cb.datatextformatstring);
		G2ComboBox_WriteUrlNameValue(sb, "CachingKey", cb.clientsidecachingkey);
		G2ComboBox_WriteUrlNameValue(sb, "Language", cb.language);
		G2ComboBox_WriteUrlNameValue(sb, "ItemColorMember", cb.itemcolormember);
		G2ComboBox_WriteUrlNameValue(sb, "CacheDataInStorage", cb.cachedatainstorage);
		G2ComboBox_WriteUrlNameValue(sb, "StateStorageID", cb.statestorageid);
		G2ComboBox_WriteUrlNameValue(sb,  "StateStorageKey", cb.statestoragekey);
				
		var url = sb.join("");
		G2_GetData
		(
			url, 
			function(xmlhttp)
			{
			  if (G2ComboBox_LoadItemsCallback) //FireFox may remember this callback from a previous page
			  {
				  G2ComboBox_LoadItemsCallback(cb, xmlhttp.responseText, stopper);
				}
			},
			function(xmlhttp)
			{
			    if (document.getElementById(cb.id) != null)
				    alert("could not load items for "+cb.id+" "+xmlhttp.statusText+", "+xmlhttp.responeText);
			}
		);
	},

	G2ComboBox_WriteUrlNameValue : function(sb, name, value)
	{
		if(value!=null)
			sb.push(name +"="+value+"&");
	},

	G2ComboBox_GetParentComboBox : function(cb)
	{
		if(cb.ParentComboBox==null)
		{
			if(cb.parentlistcontrolid!=null)
			{
				var parentComboBoxes = [];
				var sArr = cb.parentlistcontrolid.split(',');
				
				if(sArr.length > 1)
				{
					for(var i = 0, j = sArr.length; i < j; i++)
					{
						var pcb = document.getElementById(sArr[i]);
						
						// make sure that the parent comboBOx is intialized
						if(!pcb.g2IsInited)
							G2ComboBox_Init(pcb);
							
						parentComboBoxes.push(pcb);
					}
					cb.ParentComboBox = parentComboBoxes;
				}
				else
					cb.ParentComboBox = [document.getElementById(cb.parentlistcontrolid)];
			}
		}
		return cb.ParentComboBox;
	},

	G2ComboBox_IsLoaded : function(cb)
	{
		return cb.IsLoaded;
	},


//	G2ComboBox_CreateHtmlFromJson : function(items)
//	{
//		//G2_Trace("G2ComboBox", "G2ComboBox_CreateHtmlFromJson start");

//		var sb = new Array();
//		sb.push("<table><tbody>");
//		var lastItem;
//		for(var i=0;i<items.length;i++)
//		{
//			var item = items[i];
//			if(lastItem!=null)
//				lastItem.nextItem = item;
//			item.visible = true;
//			item.previousItem = lastItem;

//			sb.push("<tr id='");
//			sb.push(item.value);
//			sb.push("'>");
//			if(item.pdv!=null)
//			{
//				sb.push(" pdv='");
//				sb.push(item.pdv);
//			}
//			sb.push("<td>");
//			if(item.text==null || item.text=="")
//				sb.push("&nbsp;");
//			else
//				sb.push(item.text);
//			sb.push("</td></tr>");
//			lastItem = item;
//		}
//		sb.push("</tbody></table>");
//		var html = sb.join("");
//		return html;

//	},


 	G2ComboBox_FillItemsBackground : function(cb, itemElement, count)
 	{
 	  var c = 0;
 	  while(true)
 	  {
		  if (itemElement.nodeType==1) //FF adds textNodes with "\n", IE doesn't
		  {
			  G2DOM.G2TransferAttributes(itemElement);
			  cb.popup.items.push(itemElement);
			  itemElement.visible = true;
			  if (isMoz && itemElement.innerText=="")
			  {
			    itemElement.innerHTML = "&nbsp;"; //Firefox hides this element beacause it has no text
			  }
			  //index++;
			  //G2ComboBox_InitItem(cb, item);
			  c++;
			  if(count!=null && c==count)
		      break;
		  }
		  itemElement = itemElement.nextSibling;
		  
		  if(itemElement==null)
		    break;		  
		}
		if(count!=null && itemElement!=null)
		{
  	  //window.status = index+" "+item.text;
  	  window.setTimeout(function()
		  {
		    G2ComboBox_FillItemsBackground(cb, itemElement, count);
		  }, 0);
		}
//		else
//		{
//		  window.status = "FINISHED!!!";
//		  cb.ss.lap("Init Items");
//	    cb.ss.report("LoadItemsCallback for "+cb.id);
//		}
 	},


	G2ComboBox_LoadItemsCallback : function(cb, responseText, stopper)
	{
		var tokens = responseText.split("||||");
		var html = tokens[0];
		var items = [];//eval(tokens[1]);
		
		//cb.ss = new Stopper();
		//cb.ss.start();
		cb.popup.firstChild.innerHTML = html;
		//cb.ss.lap("InnerHTML");
		
		cb.popup.firstChild.onmouseover = G2ComboBox_PopupMouseOver;
		cb.popup.firstChild.onmouseout = G2ComboBox_PopupMouseOut;
		cb.popup.firstChild.onclick = G2ComboBox_PopupMouseClick;
			
		var tb = cb.popup.firstChild.firstChild;
		if(tb==null)
		{
		  G2ComboBox_SetText(cb, "No Data Found");
		  return;
		}
		var itemElement = tb.children[0];
		cb.popup.items = items;
		var index=0;
		if(itemElement!=null)
		{
			// Initialize first visible item
			G2DOM.G2TransferAttributes(itemElement);
			cb.firstVisibleItem = itemElement;
		  //Determine wether to init items async.
		  //Only when there is no parent combo (async screwes up sub-filtering) and items html is "big"
		  var shouldLoadAsync=(cb.parentlistcontrolid==null && html.length>G2ComboBox_MIN_SIZE_FOR_BG_INIT);
		  if(shouldLoadAsync)
		    G2ComboBox_FillItemsBackground(cb, itemElement,  G2ComboBox_BG_INIT_BLOCK_SIZE);
		  else
		    G2ComboBox_FillItemsBackground(cb, itemElement);
		}

		//var cbPopupChildren = cb.popup.firstChild;
		//if (cbPopupChildren!=null) //fixed by yaniv for cases that there is no items.
			//cbPopupChildren.className = "G2ComboBox_ItemsTable ScrollBarStyle";
		
		cb.disabled = false;
		if(cb.valueBeforeLoadStart!=null)
		{
		  G2ComboBox_SetText(cb, cb.valueBeforeLoadStart);
		  cb.valueBeforeLoadStart = null;
		}
		else
	  {
		  G2ComboBox_SetText(cb, "");
		}
		G2ComboBox_VerifySelectedValue(cb);
		
		if(cb._wasFocused)
		{
			G2ComboBox_Focus(cb);
			cb._wasFocused = undefined;
		}
		var parentCombo = G2ComboBox_GetParentComboBox(cb);
		
		if(parentCombo!=null)
		{
			for(var i = 0, j = parentCombo.length; i < j; i++)
			{
				pcb = parentCombo[i];
				if(pcb)
				{
					G2ComboBox_Init(pcb);
					pcb.g2OnSelectedValueChanged.push(
						function(sender)
						{
							G2ComboBox_FilterItems(cb);
							var selectedItem = G2ComboBox_GetSelectedItem(cb);
							if(typeof(selectedItem)!="undefined" && selectedItem.isItemDisabled)
							{
								var firstItem = G2ComboBox_GetFirstItem(cb);
								if(firstItem==null)
								{
									throw new Error("no items left for selection in "+cb.id);
								}
								G2ComboBox_SetSelectedValue(cb, firstItem.value, firstItem);
							}
						}
					);
				}
			}

			G2ComboBox_FilterItems(cb);
		}
		
		cb.IsLoaded = true;
		if(cb.setfocus=="true")
		{
			try //TODO: find a better way
			{  
				cb.tbText.focus();
				cb.tbText.select();
			}
			catch(e)
			{
			}
		}
		
		if(cb.updatevalueoncontrolid!=null)
		{
			cb.UpdateValueOnControl = document.getElementById(cb.updatevalueoncontrolid);
		}
		
		if(cb.showPopupWhenLoaded)
		{
		  cb.showPopupWhenLoaded = false;
			G2ComboBox_ShowPopup(cb);
			
		}
		
		

	},

	G2ComboBox_GetParentsDataValue : function(parentComboList)
	{
		var res = [];
		var parentCombo;
		var pdv;
		for(var i = 0, j=parentComboList.length; i < j; i++)
		{
			parentCombo = parentComboList[i];
			if(parentCombo)
			{
				pdv = G2ComboBox_GetSelectedValue(parentCombo);
				if(parentCombo.nullvalue == pdv) // null value will be signal by 'null' in the list of values
					pdv = null;
			}
			else
				pdv = null;
				
			res.push(pdv);
		}
		
		return res.join(',');
	},

	G2ComboBox_CompareFilterValues : function(itemPdv, parentPdvList, cb)
	{
		// validate parameters
		
		
		var iv;
		if(itemPdv)
			iv = itemPdv.split(',');
		else
		{
			iv = [];
			iv.push('');
		}
		
		// in case there is only one parent perform the original action
		if(parentPdvList.length == 1)
		{
			if(!parentPdvList[0])
				return  cb.filterallwhenparentnull ? false : true;
				
			return itemPdv==parentPdvList[0] || (cb.alwaysshownullparentitems && (itemPdv || "") == (cb.nullvalue || ""));
		}

		// if the length do not match there is a bug. its not a possible situation
		if(parentPdvList.length != iv.length)
			return false;
		var parentIsNull;
		for(var i = 0, j = parentPdvList.length; i < j; i++)
		{
			parentIsNull = false;
			if(!parentPdvList[i])
				parentIsNull = cb.filterallwhenparentnull ? false : true;
				
			var b = parentIsNull || // show item if the parent value is null value
				iv[i]==parentPdvList[i] ||	// show item if the values match
				(cb.alwaysshownullparentitems && (itemPdv || "") == (cb.nullvalue || "")); // show item if this is a null value

			if(!b)
				return false;
		}
		
		return true;
	},
	
	G2ComboBox_FilterItemsByParent : function(cb)
	{			 
		var filterByParent = (cb.ParentComboBox!=null);
		if (filterByParent == false)
			return;
		
		var parentCombo = G2ComboBox_GetParentComboBox(cb);
		
		var pdv = G2ComboBox_GetParentsDataValue(parentCombo);
		
		// get parent values as list
		var parentPdvList;
		if(pdv)
			parentPdvList = pdv.split(',');
		else
		{
			parentPdvList = [];
			parentPdvList.push('');
		}
		//var pdv = G2ComboBox_GetSelectedValue(parentCombo);
		//var pdvIsNull = (pdv==parentCombo.nullvalue);

		cb.firstVisibleItem = null;	
		
		var items = cb.popup.items;
		var itemCount = items.length;
		
		var showItems = new Array();
		var hideItems = new Array();
		var visibleCount = 0;	
		
		for (var i=0;i<itemCount;i++)
		{
			var item = items[i];
			var visible = true;
			if(filterByParent)
			{
				if(G2ComboBox_IsNullItem(cb, item)) //do not filter the null item
					visible = true;
				else
					visible = G2ComboBox_CompareFilterValues(item.pdv, parentPdvList, cb);

				item.isItemDisabled = !visible;
			}
			if (visible)
			{
				visibleCount++;
				if(!item.visible)
					showItems.push(item);
			}
			else
			{
				if(item.visible)
					hideItems.push(item);
			}
			if(cb.firstVisibleItem==null && visible && !item.isItemDisabled)
				cb.firstVisibleItem = item;
		}

		G2ComboBox_ShowAndHideItems(cb, showItems, hideItems);
	},

	G2ComboBox_FilterItemsByText : function(cb)
	{
		var text = cb.tbText.value;//.toLowerCase();
		var textRegExp = new RegExp("^"+text, "i");

//		cb.firstVisibleItem = null;	
		var items = cb.popup.items;
		var itemCount = items.length;
		
		var showItems = new Array();
		var hideItems = new Array();
		var visibleCount = 0;	
		
		var firstMatchingItem = null;
		
		for (var i=0;i<itemCount;i++)
		{
			var item = items[i];
			if(!item.visible)
				continue;			//Only search in visible items
				
			var visible = true;
			if (firstMatchingItem==null &&								//Take only the first item
					text!="" &&																//Never take action when the searched string is empty
					item.text.search(textRegExp)!=-1 &&				//Only accept items that match the searched string
					!G2ComboBox_IsNullItem(cb, item))					//Never select the null item
			{
				firstMatchingItem = item;
				break;
			}
//			if(cb.firstVisibleItem==null && visible && !item.isItemDisabled)
//				cb.firstVisibleItem = item;
		}
		
		if (firstMatchingItem!=null)
		{			
			G2ComboBox_SetSelectedValue(cb, firstMatchingItem.value, firstMatchingItem,false,true,true);
			G2ComboBox_ClearPreviouslySelectedItem(cb);
			G2ComboBox_ScrollIntoView(cb,firstMatchingItem);
			cb.selectedItem = firstMatchingItem;
		}
	},

	//TODO: optimize - filtering on js objects is MUCH FASTER!!!
	G2ComboBox_FilterItems : function(cb, filterByText, autoselect)
	{
		var filterByParent = (cb.ParentComboBox!=null);
		if (filterByParent)
		{
			var parentCombo = G2ComboBox_GetParentComboBox(cb);
			var pdv = G2ComboBox_GetParentsDataValue(parentCombo);
			//var pdv = G2ComboBox_GetSelectedValue(parentCombo);
			if (cb.prevPdv != pdv)
			{
				G2ComboBox_FilterItemsByParent(cb);
				cb.prevPdv = pdv;
			}
		}
		if (filterByText!=false)
				G2ComboBox_FilterItemsByText(cb);
		
		cb.FilterItemsByTextThreadId = null;
	},
	
	G2ComboBox_ShouldLoadItemsAsync : function(cb)
	{
	  if(cb.parentlistcontrolid!=null)
	    return false;
	  return true;
	},


	G2ComboBox_ShowAndHideItems : function(cb, showItems, hideItems)
	{
		var totalItemsToShowOrHide = showItems.length+hideItems.length;
		var optimizeByRemovingTable = totalItemsToShowOrHide>700;
		var tbl = null;
		if(optimizeByRemovingTable)
		{
			tbl = cb.popup.firstChild;
			cb.popup.removeChild(tbl);
		}
		G2ComboBox_ShowHideItems(showItems, true);
		G2ComboBox_ShowHideItems(hideItems, false);
		if(optimizeByRemovingTable)
		{
			cb.popup.appendChild(tbl);
		}
	},

	G2ComboBox_ShowHideItems : function(items, show)
	{
			var itemCount = items.length;
		for(var i=0; i < itemCount; i++)
		{
			G2ComboBox_ShowHideItem(items[i], show);
		}
	},

	G2ComboBox_ShowHideItem : function(item, show)
	{
		if(item.visible!=show)
		{
			item.visible = show;
			item.style.display = show ? "" : "none";			//FOLLOWUPDAN-EL
		}
	},

	G2ComboBox_IsNullItem : function(cb, item)
	{
		return cb.AllowNull && cb.nullvalue==item.value;
	},

	//TODO: Optimize
//	G2ComboBox_InitItem : function(cb, item)
//	{
//		var itemElement = item;
//		
//		itemElement.isItem = true;
//	  //moved to html render in server (faster)  itemElement.className = "G2ComboBox_Item";
//		//TODO: try using event bubbling and attach only once
//		itemElement.onmouseover = G2ComboBox_OnItemMouseOver;
//		itemElement.onmouseout = G2ComboBox_OnItemMouseOut;
//		itemElement.onclick = G2ComboBox_OnItemMouseClick;
//		itemElement.item = item;
//		//G2DOM.G2TransferAttributes(itemElement);
//	},
	
	G2ComboBox_GetEvent : function(e)
	{
	  if(e!=null)
	    return e;
	  if(event!=null)
	    return event;
	  return window.top.event;//When the combo opens in an iframe the event occurs on top window
	},
	
	G2ComboBox_PopupMouseOver : function(e)
	{
		e = G2ComboBox_GetEvent(e);
		if(e.srcElement.value!=null)
			G2ComboBox_OnItemMouseOver(e.srcElement);
	},
	
	G2ComboBox_PopupMouseOut : function(e)
	{
		e = G2ComboBox_GetEvent(e);
		if(e.srcElement.value!=null)
			G2ComboBox_OnItemMouseOut(e.srcElement);
	},
	
	G2ComboBox_PopupMouseClick : function(e)
	{
		e = G2ComboBox_GetEvent(e);
		if(e.srcElement.value!=null)
			G2ComboBox_OnItemMouseClick(e.srcElement);
	},
	
  G2ComboBox_OnItemMouseOver : function(itemElement)
	{
		//var itemElement = this;
		itemElement.className = "G2ComboBox_ItemMouseOver";
	},

	G2ComboBox_OnItemMouseOut : function(itemElement)
	{
		//var itemElement = this;
		//var item = itemElement.item;
		if(itemElement.isItemSelected)
			itemElement.className = "G2ComboBox_Item_Selected";
		else
			itemElement.className = "G2ComboBox_Item";
	},

	G2ComboBox_OnItemMouseClick : function(itemElement)
	{
		//var itemElement = this;
		var cb = G2ComboBox_GetComboForItemElement(itemElement);
		G2ComboBox_SetSelectedValue(cb, itemElement.value);
		G2ComboBox_HidePopup(cb);
		G2ComboBox_Focus(cb);
		//G2StopEvent(event);
	},

	G2ComboBox_TogglePopup : function(cb, filterItems,event)
	{
		if(G2ComboBox_IsPopupOpened(cb))
		{
			G2ComboBox_HidePopup(cb);
		}
		else
		{
			G2ComboBox_ShowPopup(cb, filterItems, event) ;
		}
	},

	G2ComboBox_IsPopupOpened : function(cb)
	{
		return G2PopupManager.isPopupOpened(cb.popup);
	},

	G2ComboBox_ShowPopup : function(cb, filterItems,event)
	{
		if (isMoz && event!=null)
			G2StopEvent(event);
			
		if(G2ComboBox_IsPopupOpened(cb))
			return;
	  
	  
	  //var ss = new Stopper();
		//ss.start();
		
		G2ComboBox_EnsureItems(cb);
		
		//ss.lap("EnsureItems");
		//fixedPos = isFixedPositioned(cb) && IE7;
		
		
		//G2_FloatElement(cb.popup, cb.tbText, "S", isIE,fixedPos);
//		cb.popup.style.display="";
		G2PopupManager.openPopup(cb.popup, cb, "bl:tl,br:tr", true);
		if(cb.listwidth)
			cb.popup.style.width = cb.listwidth;
		else
			cb.popup.style.pixelWidth -= 2;
		
		if(cb.selectedItem!=null)
		{
			//cb.selectedItem.scrollIntoView();
		}
 		// verify that the popup is in the boreder of the screen
		G2_VerifyAbsoluteElementNotCropped(cb.popup);
	},
	
	G2ComboBox_BeforeClose : function(popup)
	{
	  if (isMoz)
	  {	    
	    popup.lastScrollTop = popup.children[0].children[0].scrollTop;
	  }
	},
	
	G2ComboBox_Opened : function(popup)
	{
	  if (isMoz && popup.lastScrollTop)
	  {	    
	    popup.children[0].children[0].scrollTop = popup.lastScrollTop;
	  }
	},
  
	G2ComboBox_HidePopup : function(cb)
	{	  
	  G2PopupManager.closePopup(cb.popup);
	},

	G2ComboBox_FindElements : function(cb, childIds)
	{
		var map = new Object();
		var count = childIds.length;
		for(var i=0;i<count;i++)
		{
			map[childIds[i]] = null;
		}
		_G2ComboBox_FindElements(cb, {map:map, count:count});
		return map;
	},
	
	_G2ComboBox_FindElements : function(element, context)
	{
		var child = element.firstChild;
		while(child!=null && context.count>0)
		{
			if(child.id!="")
			{
				for(var p in context.map)
				{
					if(context.map[p]!=null)
						continue;
					if(String.EndsWith(child.id, p))
					{
						context.map[p] = child;
						context.count--;
					}
				}
			}
			_G2ComboBox_FindElements(child, context);
			child = child.nextSibling;
		}
	},

	G2ComboBox_SetText : function(cb, text)
	{
		cb.tbText.value = text.trim();
	},

	G2ComboBox_ClearPreviouslySelectedItem : function(cb)
	{
		cb.previouslySelectedItem = null;
	},

	G2ComboBox_SetSelectedValue : function(cb, value, item, notifyServer, suppressChangeEvent, hightlightOnly, ensureItems)
	{
		if(!cb.g2IsInited)
			G2ComboBox_Init(cb);
		if(ensureItems)
			G2ComboBox_EnsureItems(cb);
		if(notifyServer==null)
			notifyServer = true;
		if(cb.selectedItem!=null)
		{
			cb.selectedItem.className="G2ComboBox_Item";
			cb.selectedItem.isItemSelected = false;
			cb.selectedItem = null;
		}
	 
		if (cb.tbValue.value != value)
			cb.tbValue.value = value;
		//ASP.NET Validation stuff
		//Set initialvalue and value props to yield to RequiredFieldValidatorEvaluateIsValid MS function
		if(cb.initialvalue==null)
			cb.initialvalue = value;
		cb.value = value;
		//---
		if(item==null)
		{
			item = G2ComboBox_GetItemByValue(cb, value);
			if(item==null)
			{
				//TODO: Handle properly
				return;
				//throw new Error("item with value "+value+" was not found");
				
			}
		}
		// set items color;
		if(item.style.color && item.style.color != "")
			cb.tbText.style.color = item.style.color;
		else
			cb.tbText.style.color = "";
		
		cb.selectedItem = item;
		cb.selectedItem.isItemSelected = true;
		cb.selectedItem.className="G2ComboBox_Item_Selected";
		if(item.offsetTop > cb.popup.offsetHeight)
		{
			//cb.popup.doScroll("down");
		}
	  
	  if (!hightlightOnly)
			G2ComboBox_SetText(cb, item.text);
		if(cb.nullcssclass!=null)
		{
			G2_ReplaceCssClass(cb, cb.cssclass, cb.nullcssclass, value==cb.nullvalue);
		}
		if(!suppressChangeEvent)
		{
				window.setTimeout(function(){
						G2ComboBox_OnSelectedValueChanged(cb);}, 10);
 		}
		if(notifyServer && cb.autocallback=="true")
		{
  			__doPostBack(cb, null, true);
		}
	},

	G2ComboBox_GetSelectedItem : function(cb)
	{
		return cb.selectedItem;
	},

	G2ComboBox_SelectFirstItem : function(cb)
	{
		var item = G2ComboBox_GetFirstItem(cb);
		G2ComboBox_SetSelectedValue(cb, item.value, item);
	},

	G2ComboBox_GetFirstVisibleItem : function(cb)
	{
		return cb.firstVisibleItem;
	},

	G2ComboBox_SelectNextItem : function(cb)
	{
		var item = G2ComboBox_GetSelectedItem(cb);
	  
		if(item==null)
		{
			item = G2ComboBox_GetFirstVisibleItem(cb);// G2ComboBox_GetFirstItem(cb);
		}
		var nextItem = item.nextSibling;
		while(nextItem!=null && (!nextItem.visible || nextItem.isItemDisabled))
		{
			nextItem = nextItem.nextSibling;
		}
	  
		if(nextItem!=null)
		{
			G2ComboBox_SetSelectedValue(cb, nextItem.value, nextItem);
			cb.tbText.select();
			G2ComboBox_ClearPreviouslySelectedItem(cb);
		}
	},

	G2ComboBox_SelectPrevItem : function(cb)
	{
		var item = G2ComboBox_GetSelectedItem(cb);
		if(item==null)
			return;
	  
		var prevItem=null;
		while(true)
		{
			item = item.previousSibling;
			if(item==null)
				break;
			if(!item.isItemDisabled && item.visible)
			{
				prevItem = item;
				break;
			}
		}
	  
		if(prevItem!=null)
		{
			G2ComboBox_SetSelectedValue(cb, prevItem.value, prevItem);
			cb.tbText.select();      
			G2ComboBox_ClearPreviouslySelectedItem(cb);  
		}
	},

	G2ComboBox_GetSelectedValue : function(cb)
	{
		if(cb.tbValue)
			return cb.tbValue.value;
	
		return cb.value;
	},

	G2ComboBox_VerifySelectedValue : function(cb)
	{
		var value = G2ComboBox_GetSelectedValue(cb);
		if(value=="" && cb.nullvalue!=null)
			value = cb.nullvalue;
		G2ComboBox_SetSelectedValue(cb, value, null, false, true);
	},


	G2ComboBox_GetComboForItemElement : function(itemElement)
	{
		return itemElement.parentElement.parentElement.parentElement.combo;
	},
	
	G2ComboBox_GetItems : function(cb)
	{	
		return cb.popup.items;
	},

	G2ComboBox_GetFirstItem : function(cb)
	{
		return cb.popup.items[0];
	},

	G2ComboBox_GetItemByValue : function(cb, value)
	{	
		var items = G2ComboBox_GetItems(cb);
		if (items)
		{
			for(var i=0;i<items.length;i++)
			{
				var item = items[i];
				if(item.value==value) //TODO: hash
					return item;
			}
		}
	},

	G2ComboBox_CallbackReturned : function(result)
	{
	},

	G2ComboBox_Callback : function(sender)
	{
	  
	},
	
	FixFieldClick : function(cb)
	{
		G2ComboBox_HidePopup(cb);
		//run client side code 
		if(cb.fixFieldClientClick != null)
		{
			if(cb._fixFieldClientClickFunc == null)
			{
				cb._fixFieldClientClickFunc = new Function("cb", cb.fixFieldClientClick);
			}
			var result = cb._fixFieldClientClickFunc(cb);
			if (result == false)
				return;
				
		}
		__doPostBack(cb, 'FixedItemOnClick', true); //eventArgument
	},


	//Autocomplete ---------------------------------------------------

	textboxSelect  : function(oTextbox, iStart, iEnd) {

		 switch(arguments.length) {
				 case 1:
						 oTextbox.select();
						 break;

				 case 2:
						 iEnd = oTextbox.value.length;
						 /* falls through */
	           
				 case 3:        
						 G2_SetSelectionRange(oTextbox, iStart, iEnd);
		 }

		 oTextbox.focus();
	},
	
	G2ComboBox_ScrollIntoView : function (cb,item)
	{
		var margin = 10;
		var itemTop = item.offsetTop;
		item.parentElement.scrollTop = itemTop;
	}
});


/*
//TODO: optimize - filtering on js objects is MUCH FASTER!!!
	G2ComboBox_FilterItems : function(cb, filterByText, autoselect)
	{
		if (autoselect==null)
			 autoselect = true; //true by default
			 
		//G2_Trace(cb, "G2ComboBox_FilterItems start");
		var filterByParent = (cb.ParentComboBox!=null);
		if(filterByText==null)
			filterByText = false;
	  
		var text = null;
		var textRegExp = null;
		if(filterByText)
		{
			text = cb.tbText.value;//.toLowerCase();
			textRegExp = new RegExp("^"+text, "i");
		}
		var _filterByText = filterByText;
	  filterByText = false; 
		var parentCombo = null;
		var pdv = null;
		var pdvIsNull = false;
		if(filterByParent)
		{
			parentCombo = G2ComboBox_GetParentComboBox(cb);
			pdv = G2ComboBox_GetSelectedValue(parentCombo);
			pdvIsNull = (pdv==parentCombo.nullvalue);
		}
			
		cb.firstVisibleItem = null;	
		var items = cb.popup.items;
		var itemCount = items.length;
		
		var showItems = new Array();
		var hideItems = new Array();
		var visibleCount = 0;	
		
		var firstMatchingItem = null;
		
		for (var i=0;i<itemCount;i++)
		{
			var item = items[i];
			var visible = true;
			if(filterByParent)
			{
				if(G2ComboBox_IsNullItem(cb, item)) //do not filter the null item
					visible = true;
				else if(pdvIsNull)
					visible = cb.filterallwhenparentnull ? false : true;
				else
				{
					visible = item.pdv==pdv || (cb.alwaysshownullparentitems && item.pdv==cb.nullvalue);
				}
				item.isItemDisabled = !visible;
			}
			if(filterByText && !item.isItemDisabled)
			{
				visible = text=="" || item.text.search(textRegExp)!=-1;
			}
			if (_filterByText &&
					firstMatchingItem==null &&								//Take only the first item
					text!="" &&																//Never take action when the searched string is empty
					item.text.search(textRegExp)!=-1 &&				//Only accept items that match the searched string
					!G2ComboBox_IsNullItem(cb, item))					//Never select the null item
			{
				firstMatchingItem = item;
			}
			if (visible)
			{
				visibleCount++;
				if(!item.visible)
					showItems.push(item);
			}
			else
			{
				if(item.visible)
					hideItems.push(item);
			}
			if(cb.firstVisibleItem==null && visible && !item.isItemDisabled)
				cb.firstVisibleItem = item;
		}

		G2ComboBox_ShowAndHideItems(cb, showItems, hideItems);
		
		if (visibleCount==1 && autoselect)
		{
			var item = cb.firstVisibleItem;
			G2ComboBox_SetSelectedValue(cb, item.value, item);
			G2ComboBox_ClearPreviouslySelectedItem(cb);
			G2ComboBox_HidePopup(cb);
			cb.blur();
			if(text!=null) //TODO: FOLLOWUP
				G2_SetSelectionRange(cb.tbText,text.length,cb.tbText.value.length); 
		}
		else if (visibleCount == 0 && autoselect)
		{ 
			if (text)
			{
				G2ComboBox_SetText(cb, text.substr(0,text.length - 1)); // ignore the key if there is no match
				G2ComboBox_FilterItems(cb, filterByText, autoselect);
				
			}
		} else if (_filterByText && firstMatchingItem!=null)
		{			
			G2ComboBox_SetSelectedValue(cb, firstMatchingItem.value, firstMatchingItem,false,true,true);
			G2ComboBox_ClearPreviouslySelectedItem(cb);
			G2ComboBox_ScrollIntoView(cb,firstMatchingItem);
			cb.previouslySelectedItem = firstMatchingItem;
		}
		
		cb.FilterItemsByTextThreadId = null;
	},
	
	*/
function G2ControlSelector_SelectControl(option, control1ID, control2ID)
{
  var cToShow;
  var cToHide;
  if(option==0)
  {
    cToShow = document.getElementById(control1ID);
    cToHide = document.getElementById(control2ID);
  }
  else
  {
    cToShow = document.getElementById(control2ID);
    cToHide = document.getElementById(control1ID);
  }
    
  if(cToShow!=null)
    G2_ShowControl(cToShow);
  if(cToHide!=null)
    G2_HideControl(cToHide);
}

var USE_NEW_CALENDAR = true; //use new (client side) calendar
var ParsableDateTimeFormat = "MM/dd/yyyy HH:mm:ss";

///Creates some more functions for a G2DatePicker node.
function G2DatePicker_Init(datePickerId)
{
	var datePicker = document.getElementById(datePickerId);
	if(datePicker==null)
	{
		Debug.writeln("datepicker "+datePickerId+" was not found");
		return;
	}
	G2DatePicker_VerifyInit(datePicker);
}

function G2DatePicker_CompareValidatorEvaluateIsValid(val) 
{
	var datePicker = document.getElementById(val.controltovalidate);
	var date = G2DatePicker_GetDate(datePicker);
	var datePicker2 = document.getElementById(val.controltocompare);
	var date2 = G2DatePicker_GetDate(datePicker2);
  return G2_DateMatch(date, date2, val.operator);
}



function G2_DateMatch(op1, op2, operator)
{
	var x = op1-op2;
  switch (operator) 
  {
    case "NotEqual":
        return (x!=0);
    case "GreaterThan":
        return (x>0);
    case "GreaterThanEqual":
        return (x>=0);
    case "LessThan":
        return (x<0);
    case "LessThanEqual":
        return (x<=0);
    default:
        return (x==0);
  }
}



///Creates some more functions for a G2DatePicker node.
function G2DatePicker_VerifyInit(datePicker, forceFireOnChangeEvent)
{
	if(datePicker.IsInited)
		return;
		
//	G2_AttachEvent(datePicker, "onfocus", G2DatePicker_OnFocus);
	datePicker.IsInited = true;
	G2DOM.G2TransferAttributes(datePicker);

	var hf = G2DatePicker_GetDateTimeHiddenField(datePicker);
	EnableSupportForPartialPostData(hf);
	datePicker.popcalendarabove = datePicker.popcalendarabove=="true";
	datePicker.G2OnSelectedDateChanged = new Array();//event
	if(datePicker.ClientOnSelectedDateChanged!=null && datePicker.ClientOnSelectedDateChanged.length>0)
	{
		var script = datePicker.ClientOnSelectedDateChanged.replace(new RegExp("this", "g"), "datePicker");
		datePicker.G2OnSelectedDateChanged.push(function(){eval(script);});
	}
	
	datePicker.getValue = function()
	{
	  return G2DatePicker_GetDate(this);
	}
	
	if(datePicker.mode=="Label")
	{
	}
	else if(datePicker.mode=="TextBox")
	{
		var tb = G2DatePicker_GetDateTextBox(datePicker);
		tb.DatePicker = datePicker;
		G2_AttachEvent(tb, "onkeypress", G2DatePicker_TextBox_OnKeyPress);
		G2_AttachEvent(tb, "onblur", G2DatePicker_TextBox_OnBlur);
		G2_AttachEvent(tb, "onfocus", G2DatePicker_TextBox_OnFocus);
		G2_PreventInputPost(tb.id);
			
			
//		G2_AttachEvent(tb, "onchange", function(){G2DatePicker_Changed(datePicker, false);});
		if(!datePicker.disabled && datePicker.setfocus=="true")
		{
			tb.focus();
		}

	}
	else if(datePicker.mode=="DropDown")
	{
		var listDays = G2DatePicker_GetListDays(datePicker);
		datePicker.ShowDays = listDays!=null;
		if(listDays!=null)
		{
			G2NumericDropDown_VerifyInit(listDays);
			G2_PreventInputPost(listDays.id);
			G2_AttachEvent(listDays, "onchange", function(){G2DatePicker_Changed(datePicker, false);});
		}

		if(G2DatePicker_SeperateYearAndMonth(datePicker))
		{
			var listYears = G2DatePicker_GetListYears(datePicker);
			var listMonths = G2DatePicker_GetListMonths(datePicker);
			G2_PreventInputPost(listYears.id);
			G2_PreventInputPost(listMonths.id);

			G2NumericDropDown_VerifyInit(listYears);
			G2_AttachEvent(listMonths, "onchange", function(){G2DatePicker_Changed(datePicker, false);});
			G2_AttachEvent(listYears, "onchange", function(){G2DatePicker_Changed(datePicker, false);});
			if(datePicker.setfocus=="true")
			{
				listYears.focus();
			}
			if(datePicker.defaultyear!=null)
			{
				listYears.onclick = function()
				{
					if(listYears.value=="")
					{
						Select_SetValue(listYears, datePicker.defaultyear);
					}
				}
			}
		}
		else
		{
			var listMonthYear = G2DatePicker_GetListMonthYear(datePicker);
			G2_PreventInputPost(listMonthYear.id);
			G2_AttachEvent(listMonthYear, "onchange", function(){G2DatePicker_Changed(datePicker, false);});
//			listMonthYear.onchange=function(){G2DatePicker_Changed(datePicker, false);}
			if(datePicker.setfocus=="true")
			{
				try
				{
					listMonthYear.focus();	//This may cause an error if the item is hidden etc.
				}
				catch(e)
				{
				}
			}

		}
	}
	
	if(G2DatePicker_ShowTime(datePicker))
	{
		if(G2DatePicker_SeperateHourAndMinute(datePicker))
		{
			var ddlHours = G2DatePicker_GetHoursDropDown(datePicker);
//			G2DropDownList_VerifyInit(ddlHours);
			var ddlMinutes = G2DatePicker_GetMinutesDropDown(datePicker);
			G2_AttachEvent(ddlHours, "onchange", function(){G2DatePicker_Changed(datePicker, false);});
			G2_AttachEvent(ddlMinutes, "onchange", function(){G2DatePicker_Changed(datePicker, false);});
		}
		else
		{
			var ddlTime = G2DatePicker_GetTimeControl(datePicker);
			G2_AttachEvent(ddlTime, "onchange", function(){G2DatePicker_Changed(datePicker, false);});
		}
	}
	
	//TODO: cache related elements by ids.
	G2DatePicker_Changed(datePicker, true, forceFireOnChangeEvent);
	
	//datePicker.originalValue = G2DatePicker_GetDate(datePicker);
	G2DatePicker_SetOriginalValue(datePicker);
	datePicker.g2PerformUndo = G2DatePicker_PerformUndo;
	datePicker.g2SetOriginalValue = G2DatePicker_SetOriginalValue;
	datePicker.g2IsDirty = G2DatePicker_IsDirty;
	if(datePicker.disabledcssclass!=null)
	{
		G2_AttachEvent(datePicker,"onpropertychange",
		function(e)
		{
			if(e.propertyName=="disabled")
				G2_ReplaceCssClass(datePicker, datePicker.cssclass, datePicker.disabledcssclass, datePicker.isDisabled);
		});
	}
	datePicker.setEnabled = function(value)
	{
		G2DatePicker_SetEnabled(datePicker, value);
	}
}
	
function G2DatePicker_SetEnabled(dp, value)
{
	dp.disabled = !value;
	if(dp.disabledcssclass!=null)
		G2_ReplaceCssClass(dp, dp.cssclass, dp.disabledcssclass, !value);
	SetControlChildrenDisability(dp, !value);
}

function G2DatePicker_IsDirty(dp)
{
	dp = dp || this;
	return cb.originalValue!=G2DatePicker_GetDate(dp);
}

function G2DatePicker_PerformUndo(datePicker)
{
	datePicker = datePicker || this;
	G2DatePicker_SetDate(datePicker, datePicker.originalValue);
	//G2.undoNotifyInputChanged(datePicker);
}

function G2DatePicker_SetOriginalValue(datePicker)
{
	datePicker = datePicker || this;
	datePicker.originalValue = G2DatePicker_GetDate(datePicker);
	G2.undoNotifyInputChanged(datePicker);
}


//function G2DatePicker_OnFocus()
//{
//	var datePicker = event.srcElement;
//	datePicker.select();
//}
//
// returns the month value 
//
function G2DatePicker_GetMonth(datePicker)
{
	var month=null;
	if(datePicker.mode=="DropDown")
	{
		if(G2DatePicker_SeperateYearAndMonth(datePicker))
		{
 			var listMonth = G2DatePicker_GetListMonths(datePicker);
 			if(listMonth.value!="")
				month = String_ToInt(listMonth.value);
		}
		else
		{
			var listMonthYear = G2DatePicker_GetListMonthYear(datePicker);
			var monthYear = listMonthYear.value;
			if(monthYear!="")
			{
				var monthYearArray = monthYear.split(".");
				month = String_ToInt(monthYearArray[0]);
			}
		}
	}
	else if(datePicker.mode=="TextBox")
	{
		var tbDate = G2DatePicker_GetDateTextBox(datePicker);
		var strDate = tbDate.value;
		var tokens = strDate.split("/");
		if(tokens.length>=2)
		{
			month = Date_ParseMonth(tokens[1]);
		}
	}
	else if(datePicker.mode=="Label")
	{
		var date = G2DatePicker_GetHiddenFieldDate(datePicker);
		if(date!=null)
		{
			month = date.getMonth();
			month++;
		}
	}
	
	if(month!=null)
		month--;

	return month;
}


function G2DatePicker_GetHiddenFieldDate(datePicker)
{
	var hfDateTime = G2DatePicker_GetDateTimeHiddenField(datePicker);
	var date = Date_Parse(hfDateTime.value, ParsableDateTimeFormat);
	return date;
}

function G2DatePicker_GetYear(datePicker)
{
	var year;
 	if(datePicker.mode=="DropDown")
	{
		if(G2DatePicker_SeperateYearAndMonth(datePicker))
		{
			var listYears = G2DatePicker_GetListYears(datePicker);
			if(listYears.value!="")
				year = String_ToInt(listYears.value);
		}
		else
		{
			var listMonthYear = G2DatePicker_GetListMonthYear(datePicker);
			var monthYear = listMonthYear.value;
			if(monthYear!="")
			{
				var monthYearArray = monthYear.split(".");
				year = String_ToInt(monthYearArray[1]);
			}
		}
	}
	else if(datePicker.mode=="TextBox")
	{
		var tbDate = G2DatePicker_GetDateTextBox(datePicker);
		var strDate = tbDate.value;
		var tokens = strDate.split("/");
		var yearPos = 2;
		if (G2DatePicker_IsRtl(datePicker))
		    yearPos = 0;
		if(tokens.length>yearPos)
		{
			var yearPart = tokens[yearPos];
			if(yearPart.search(" ")==-1)
			{
				year = String_ToInt(yearPart);
				year = G2DatePicker_ResolveYear(datePicker, year);
			}
		}
	}
	else if(datePicker.mode=="Label")
	{
		var hfDateTime = G2DatePicker_GetDateTimeHiddenField(datePicker);
		var date = Date_Parse(hfDateTime.value, ParsableDateTimeFormat);
		if(date!=null)
			year = date.getFullYear();
	}
	return year;
}
//
// Resolves the correct year by checking the datepicker range.
//
function G2DatePicker_ResolveYear(datePicker, year)
{
	var minDate = G2DatePicker_GetMinDate(datePicker);
	if(minDate!=null)
	{
		var minYear = minDate.getFullYear();
		while(minYear>year)
		{
			year+=100;
		}
//		var maxDate = G2DatePicker_GetMaxDate(datePicker);
//		if(maxDate!=null && maxDate.getFullYear()<year)
//			return null; //invalid date. too big
		return year;
	}
	return year;
}

function G2DatePicker_GetMinDate(datePicker)
{
	if(datePicker.minDate==null && datePicker.mindate!=null)
	{
		datePicker.minDate = new Date(datePicker.mindate);
	}
	return datePicker.minDate;
}

function G2DatePicker_GetMaxDate(datePicker)
{
	if(datePicker.maxDate==null && datePicker.maxdate!=null)
	{
		datePicker.maxDate = new Date(datePicker.maxdate);
	}
	return datePicker.maxDate;
}


//text box edit mask
//01234567
//dd/mm/yy

function G2DatePicker_GetDay(datePicker)
{
	var day;
 	if(datePicker.mode=="DropDown")
	{
		if(datePicker.ShowDays)
		{
			var listDay = G2DatePicker_GetListDays(datePicker);
			if(listDay.value!="")
			{
				day = String_ToInt(listDay.value);
			}
		}
		else
		{
			day = 1;
		}
	}
	else if(datePicker.mode=="TextBox")
	{
		var tbDate = G2DatePicker_GetDateTextBox(datePicker);
		var strDate = tbDate.value;
		if(strDate.length>2)
		{
		    if (G2DatePicker_IsRtl(datePicker))
		        day = G2DatePicker_ParseNumber(strDate, strDate.length-2 , 2);
		    else		    
			    day = G2DatePicker_ParseNumber(strDate, 0, 2);
		}
	}
	else if(datePicker.mode=="Label")
	{
		var hfDateTime = G2DatePicker_GetDateTimeHiddenField(datePicker);
		var date = Date_Parse(hfDateTime.value, ParsableDateTimeFormat);
		if(date!=null)
		{
			day = date.getDate();
		}
	}
	return day;
}

function G2DatePicker_ParseNumber(str, startIndex, length)
{
	var s = str.substr(startIndex, length);
	var x = String_ToInt(s);
	if(isNaN(x))
		return null;
	return x;
}

function G2DatePicker_GetDateTextBox(datePicker)
{
	var tbDate = G2DatePicker_GetCachedProperty(datePicker, "tbdate");
	return tbDate;
}

function G2DatePicker_GetCachedProperty(element, propertyName)
{
	var cachedValue = G2DOM.G2GetAttribute(element,propertyName);
	if(cachedValue==null) //not found in cache - fetch it now
	{
		var elemID = G2DOM.G2GetAttribute(element,propertyName+"id");
		cachedValue = element.document.getElementById(elemID);
		element[propertyName] = cachedValue
	}
	return cachedValue;
}


function G2DatePicker_GetDate(datePicker, getDateWithoutTime)
{

  var day = G2DatePicker_GetDay(datePicker);
  var year = G2DatePicker_GetYear(datePicker);
  var month = G2DatePicker_GetMonth(datePicker);
  var hours=0;
  var minutes=0;
  var seconds=0;
  
	if(G2DatePicker_ShowTime(datePicker) && !getDateWithoutTime)
	{
		if(G2DatePicker_SeperateHourAndMinute(datePicker))
		{
			var ddlHours = G2DatePicker_GetHoursDropDown(datePicker);
			var ddlMinutes = G2DatePicker_GetMinutesDropDown(datePicker);
			hours = String_ToInt(ddlHours.value);
			minutes = String_ToInt(ddlMinutes.value);
		}
		else
		{
			var listTime = G2DatePicker_GetTimeControl(datePicker);
			if(listTime)
			{
				if(listTime.value && listTime.value!="__:__")
				{
					var timeArray = listTime.value.split(":");
					hours = String_ToInt(timeArray[0]);
					minutes = String_ToInt(timeArray[1]);
					
					// validate time is in range
					if(hours < 0 || hours > 23 || minutes < 0 || minutes > 59)
					{
						hours = 0;
						minutes = 0;
					}
				}
				
				listTime.parentElement.style['paddingLeft'] = '3px';
			}
		}
	}
	
	if(year==null || day==null || month==null)
		return null;
	if(!getDateWithoutTime  && (hours==null || minutes==null))
		return null;
	var date = Date_GetDateIfValid(year, month, day, hours, minutes, seconds)
	return date;
}

function G2DatePicker_Reset(datePicker)
{
	var defaultDate = G2DatePicker_GetHiddenFieldDate(datePicker);
//	if(!G2DatePicker_AllowNull(datePicker))
//	{
//		defaultDate = G2DatePicker_GetMinDate(datePicker);
//	}
	if(defaultDate)
		G2DatePicker_SetDate(datePicker, defaultDate);
}

function G2DatePicker_SetDate(datePicker, date, setDateWithoutTime)
{
	if(!G2DatePicker_IsDateInValidRange(datePicker, date))
	{
		alert("Date is not in valid range");
		G2DatePicker_Reset(datePicker);
		return;
	}
	if(datePicker.mode=="DropDown")
	{
		if(G2DatePicker_SeperateYearAndMonth(datePicker))
		{
 			var listYears = G2DatePicker_GetListYears(datePicker);
			listYears.value = Date_ToString(date, "yyyy");
 			var listMonths = G2DatePicker_GetListMonths(datePicker);
			listMonths.value =  Date_ToString(date, "M");
		}
		else
		{
			var monthYear = Date_ToString(date, "M.yyyy");//month+"."+year;
			var listMonthYear = G2DatePicker_GetListMonthYear(datePicker);
			listMonthYear.value = monthYear;
		}
		if(datePicker.ShowDays)
		{
			var listDay = G2DatePicker_GetListDays(datePicker);
			G2DatePicker_UpdateListDays(datePicker);
			listDay.value = date.getDate();
		}
		
	}
	else if(datePicker.mode=="TextBox")
	{
		G2DatePicker_SetTextBoxDate(datePicker, date);
	}
	else if(datePicker.mode=="Label")
	{
		var lblDate = G2DatePicker_GetDateLabel(datePicker);
		lblDate.innerText = Date_ToString(date, datePicker.dateformat);
	}
	if(G2DatePicker_ShowTime(datePicker) && !setDateWithoutTime)
	{
		if(G2DatePicker_SeperateHourAndMinute(datePicker))
		{
			var ddlHours = G2DatePicker_GetHoursDropDown(datePicker);
			var ddlMinutes = G2DatePicker_GetMinutesDropDown(datePicker);
			ddlHours.value = Date_ToString(date, "HH");//date.getHours();
			ddlMinutes.value = Date_ToString(date, "mm");//date.getMinutes();
//TODO?			ddlHours.onchange();
//TODO?			ddlMinutes.onchange();
		}
		else
		{
			var listTime = G2DatePicker_GetTimeControl(datePicker);
			listTime.value = Date_ToString(date, "HH:mm");
//TODO?			listTime.onchange();
		}
	}


	
	G2DatePicker_Changed(datePicker, false);
	//win.execScript(datePicker.onchange);
	
	UpdateDpToDate(date, datePicker.datepickertosynchronize);
	
	if(datePicker.autocallback=="true")
	{
		__doPostBack(datePicker, null, true);
	}
}


function G2DatePicker_SetTextBoxDate(datePicker, date)
{
	var tbDate = G2DatePicker_GetDateTextBox(datePicker);
	var s = "";
	if(date==null)
		s = datePicker.nulltext || "  /  /  ";
	else
	{
	    if (G2DatePicker_IsRtl(datePicker))
	        s = Date_ToString(date, "yy/MMM/dd");
	    else
		    s = Date_ToString(date, "dd/MMM/yy");
	}
	tbDate.value = s;
}

function G2DatePicker_OnPropertyChanged(datePicker)
{
	var datePickerChildren = datePicker.children;
	//KHEN: change below:
	//if(datePicker.disabled!=datePickerChildren[0].disabled)
	if(datePickerChildren.length>0 && datePicker.disabled!=datePickerChildren[0].disabled)
	{
		G2_RecursiveSetPropertyValue(datePicker, "disabled", datePicker.disabled);
		var hf = G2DatePicker_GetDateTimeHiddenField(datePicker);
		hf.disabled = false;
	}
}

//function G2DatePicker_Validate(validator, args)
//{
//	var datePicker = document.getElementById(validator.controltovalidate);
//	var date = G2DatePicker_GetDate(datePicker);
//	args.IsValid = G2DatePicker_IsDateInValidRange(datePicker, date);
//}

function G2DatePicker_VerifyCssClass(dp)
{
	if(dp.nullcssclass!=null)
	{
		var isNull = 	dp.SelectedDate==null;
		G2_ReplaceCssClass(dp, dp.cssclass, dp.nullcssclass, isNull);
	}
}
function G2DatePicker_Changed(datePicker, supressOnChangeEvent, forceFireOnChangeEvent)
{
	if(datePicker.mode=="DropDown")
	{
		if(datePicker.ShowDays)
		{
			G2DatePicker_UpdateListDays(datePicker);
		}
	}
	if(G2DatePicker_ShowDayOfWeek(datePicker))
		G2DatePicker_updateDayOfWeek(datePicker);

	var dateTime = G2DatePicker_GetDate(datePicker);
	
	// in case of non-valid week days
	if(datePicker.excludedweekdays != null)
	{
		// validate selected date
		if(!G2DatePicker_IsDateInValidRange(datePicker, dateTime))
		{
			alert("Date is not in valid range");
			G2DatePicker_Reset(datePicker);
			return;
		}
	}
	
	if(dateTime==null)
		datePicker.value = "";
	else
		datePicker.value = dateTime.toString();
	
	var oldDate = datePicker.SelectedDate;
	datePicker.SelectedDate = dateTime;
	G2DatePicker_VerifyCssClass(datePicker);
	if(!supressOnChangeEvent) //TODO: hotfix
	{
		G2DatePicker_SetDateTimeHiddenField(datePicker, dateTime);
	}

	if(!supressOnChangeEvent)
	{
		//TODO: deprecate
		if (isIE)
		{
			var win = datePicker.document.parentWindow;			
			win.execScript(datePicker.onchange);	
		}
		else
		{
			var evt = document.createEvent("HTMLEvents");
			evt.initEvent('change', false, true);
			datePicker.dispatchEvent(evt);
		}
		
		//-----------------------------
		for(var i=0;i<datePicker.G2OnSelectedDateChanged.length;i++)
		{
			datePicker.G2OnSelectedDateChanged[i]({oldValue:oldDate});
		}
	}
	
	if (forceFireOnChangeEvent)
	{
		if(datePicker.clientonchangedfunction!=null)
		{
			eval(datePicker.clientonchangedfunction);
		}
	}
	else if(!supressOnChangeEvent)
	{
		if(datePicker.clientonchangedfunction!=null)
		{
			eval(datePicker.clientonchangedfunction);
		}
	}
}

function G2DatePicker_GetDateLabel(datePicker)
{
	if(datePicker.lblDate==null)
	{
		datePicker.lblDate = G2_FindServerControl(datePicker, "lblDate");
	}
	return datePicker.lblDate;
}

function G2DatePicker_GetDateTimeHiddenField(datePicker)
{
	if(datePicker.hfDateTime==null)
	{
		//var array = document.getElementsByName(datePicker.hfname)[0];
		datePicker.hfDateTime = G2_GetChildControlById(datePicker, "hf");//document.getElementsByName(datePicker.hfname)[0];//document.get G2_FindServerControl(datePicker, "hfDateTime");
	}
	return datePicker.hfDateTime;
}

function G2DatePicker_SetDateTimeHiddenField(datePicker, date)
{
	if(!G2DatePicker_IsDateInValidRange(datePicker, date))
	{
		G2_Trace("date is not in valid range. "+datePicker.id+":"+date);
		//BUG
	}
	
	var hfDateTime = G2DatePicker_GetDateTimeHiddenField(datePicker);
	if(hfDateTime!=null)
	{
		hfDateTime.value = Date_ToString(date, ParsableDateTimeFormat);
	}
	else
	{
		throw new Error("datetime value field was not found");
	}
}

// Check if the selected day of week in the date picker is allowed
// according to the allowed week days - each char in the allowedWeekDays
// string represent the availability - "1" is available, and "0" is not.
function G2DatePicker_ValidateDay(datePicker, allowedWeekDays)
{
	var dateStart = G2DatePicker_GetDate(datePicker);

	if(dateStart != null && allowedWeekDays != null)
	{
		if(allowedWeekDays.substr(dateStart.getDay(),1)=="0")
				return false;		
	}
	return true;
}

function G2DatePicker_NextDate(dpClientID, weekDays)
{  
    var	msPerDay = 24*60*60*1000;
    var dp = document.getElementById(dpClientID);
    if (dp != null)
    {
        var maxDate = G2DatePicker_GetMaxDate(dp)
        var start_dt = G2DatePicker_GetDate(dp);
        do {
		    start_dt.setTime(start_dt.getTime()+msPerDay);
	    }
	    while (weekDays.substr(start_dt.getDay(),1)=="0" && start_dt <= maxDate);
	    if (start_dt <= maxDate && weekDays.substr(start_dt.getDay(),1)=="1")
            G2DatePicker_SetDate(dp, start_dt, true);
    }
}

function G2DatePicker_PreviousDate(dpClientID, weekDays)
{  
    var	msPerDay = 24*60*60*1000;
    var dp = document.getElementById(dpClientID);
    if (dp != null)
    {
        var minDate = G2DatePicker_GetMinDate(dp)
        var start_dt = G2DatePicker_GetDate(dp);
        do {
		    start_dt.setTime(start_dt.getTime()-msPerDay);
	    }
	    while (weekDays.substr(start_dt.getDay(),1)=="0" && start_dt >= minDate);
	    if (start_dt >= minDate && weekDays.substr(start_dt.getDay(),1)=="1")
            G2DatePicker_SetDate(dp, start_dt, true);
    }
}


function Date_GetHoursWithLeadingZero(date)
{
	var hours = date.getHours();
	if(hours<10)
		return "0"+hours.toString();
	return hours.toString();
}

function Date_GetMinutesWithLeadingZero(date)
{
	var minutes = date.getMinutes();
	if(minutes<10)
		return "0"+minutes.toString();
	return minutes.toString();
}

function G2DatePicker_IsDateInValidRange(datePicker, date)
{
	if(date==null)
	{
		var allowNull = G2DatePicker_AllowNull(datePicker);
//		if (!allowNull)
//		    alert('Date is null. returning allowNull: '+ allowNull);
		return allowNull;
	}
	
	// check the datePicker's excludedWeekDays
	if(datePicker.excludedweekdays != null &&
		datePicker.excludedweekdays.indexOf(date.getDay()) != -1)
		return false;
	
	var minDate = G2DatePicker_GetMinDate(datePicker);
	var maxDate = G2DatePicker_GetMaxDate(datePicker);
	
	if (maxDate == null || minDate == null)
		return true;
		
	if(datePicker.mode=="DropDown" && datePicker.ShowDays == false)
	{
		// in case we do not show days we do not regard them in the validation
		if (date.getFullYear() >= minDate.getFullYear() && date.getFullYear() <= maxDate.getFullYear() &&
			date.getMonth() <= minDate.getMonth() && date.getMonth() <= maxDate.getMonth())
			return true;
	}
	else
	{
		if(date>=minDate && date<=maxDate)
			return true;
	}
	return false;
}

// G2DatePicker functions
function G2DatePicker_UpdateListDays(datePicker)
{
	if(!datePicker.ShowDays)
		return;
		
	var listDays = G2DatePicker_GetListDays(datePicker);
//	var date = G2DatePicker_GetDate(datePicker);
//	if(date==null)
//		return;//TODO: reset the list to 1-31
		
	var month = G2DatePicker_GetMonth(datePicker);
	var year = G2DatePicker_GetYear(datePicker);
	if(month==null || year==null)
		return;

    // get the first value of the ddl
    var _newfirst;
    var _minmonth  = new Date(datePicker.mindate).getMonth();
    var _minyear = new Date(datePicker.mindate).getFullYear();
    if (_minmonth == month && _minyear == year)
        _newfirst = new Date(datePicker.mindate).getDate();
    else
        _newfirst = 1;
    
    // get the last value of the ddl
    var _newlast;
    var _maxmonth  = new Date(datePicker.maxdate).getMonth();
    var _maxyear = new Date(datePicker.maxdate).getFullYear();
    if (_maxmonth == month && _maxyear == year)
        _newlast = new Date(datePicker.maxdate).getDate();
    else
        _newlast = Date_GetNumOfDaysInMonth(year, month);
    
    // set the ddl range
    Select_SetRange(listDays, _newfirst, _newlast);
}

function G2_GetElement(idOrElement)
{
	if(typeof(idOrElement)=="string")
		return document.getElementById(idOrElement);
	return idOrElement;
}
//function G2_GetAbsoluteLeft(objectId) 
//{
//	// Get an object left position from the upper left viewport corner
//	// Tested with relative and nested objects
//	o = G2_GetElement(objectId)
//	oLeft = o.offsetLeft            // Get left position from the parent object
//	while(o.offsetParent!=null) {   // Parse the parent hierarchy up to the document element
//		oParent = o.offsetParent    // Get parent object reference
//		oLeft += oParent.offsetLeft // Add parent left position
//		o = oParent
//	}
//	// Return left postion
//	return oLeft
//}

//function G2_GetAbsoluteTop(objectId) 
//{
//	// Get an object top position from the upper left viewport corner
//	// Tested with relative and nested objects
//	o = G2_GetElement(objectId)
//	oTop = o.offsetTop            // Get top position from the parent object
//	while(o.offsetParent!=null) { // Parse the parent hierarchy up to the document element
//		oParent = o.offsetParent  // Get parent object reference
//		oTop += oParent.offsetTop // Add parent top position
//		o = oParent
//	}
//	// Return top position
//	return oTop
//}

function G2DatePicker_Calendar_SelectedDateChanged(sender)
{
	var cal = sender;
	
	// get DatePicker old date
	var datePickerDate = G2DatePicker_GetDate(cal.datePicker);
	var calenderDate = cal.getSelectedDate();
	
	// keep datePicker time instead of overiting it
	if(datePickerDate)
	{
		// get values from datePicker date
		var datePickerHours = datePickerDate.getHours();
		var datePickerMinutes = datePickerDate.getMinutes();
		var datePickerSeconds = datePickerDate.getSeconds();
		var datePickerMilliseconds = datePickerDate.getMilliseconds();
		// set values in calender date
		calenderDate.setHours(datePickerHours);
		calenderDate.setMinutes(datePickerMinutes);
		calenderDate.setSeconds(datePickerSeconds);
		calenderDate.setMilliseconds(datePickerMilliseconds);
	}
	
	// set the selected date
	G2DatePicker_SetDate(cal.datePicker, calenderDate);
	cal.closePopup();
}

//case 8725: if the fromDateDP is selected - the toDateDP is set accordingly
//this behavior occurs only if the 'ToDate' attribute of the fromDateDP is set to the ID of the toDateDP.
//in case the toDateDP is already set this update will not take place
function UpdateDpToDate(selectedDate, datePickerToSynchronize)
{
	if(datePickerToSynchronize != null && datePickerToSynchronize != "")
	{
		var dpToDate = $(datePickerToSynchronize);
		if(!dpToDate)
			return;

		var fixToDate = new Date(selectedDate) > new Date(dpToDate.value);
		if(dpToDate.value == "" || fixToDate)
			G2DatePicker_SetDate(dpToDate, selectedDate);
	}
}

function G2DatePicker_OpenCalendar(datePickerId,isModal)
{
	var datePicker = document.getElementById(datePickerId);
	if(datePicker.disabled)
		return;
	//Handle the case where the link was clicked twice (we already have a calendar opened so - close it)
	if(datePicker._g2calendar!=null)
	{
		G2DatePicker_CloseFloatingCalendar();
		return;
	}
	
	
	if (USE_NEW_CALENDAR)
	{
		var cal = datePicker._calendar;
		if(cal==null)
		{
			cal = new Calendar();
			cal.datePicker = datePicker;
			cal.setMinDate(G2DatePicker_GetMinDate(datePicker));
			cal.setMaxDate(G2DatePicker_GetMaxDate(datePicker));
			var selectedDate = G2DatePicker_GetDate(datePicker);
			cal.setSelectedDate(selectedDate);
			if(selectedDate!=null)
				cal.showDate(selectedDate);
			datePicker._calendar = cal;
			cal.element.style.zIndex = 10;
			cal.element.id = "floatingCalendarDiv";
			cal.setRelativeElement(datePicker);
			cal.setRelativeElementDock(datePicker.popcalendarabove ? "tl:bl" : "bl:tl");
			cal.attachEvent("SelectedDateChanged", G2DatePicker_Calendar_SelectedDateChanged);
			cal.render();
		}
		else
		{
			var selectedDate = G2DatePicker_GetDate(datePicker);
			cal.suspendLayout();
			
			if(selectedDate!=null)
			{
				cal.setSelectedDate(selectedDate);
				cal.showDate(selectedDate);
			}
			
			cal.resumeLayout();
		}
		cal.showPopup();
//		if(datePicker.popcalendarabove)
//			G2_PlaceElementAbsolutlyAbove(cal.element, datePicker);
//		else
//			G2_PlaceElementAbsolutlyBelow(cal.element, datePicker);
//		G2_AttachFrame(cal.element);
//		G2_AttachEvent(document, "onclick", G2DatePicker_CloseFloatingCalendar);
		return;
	}
	
	var minDate = Date_ToDotNetString(G2DatePicker_GetMinDate(datePicker));
	var maxDate = Date_ToDotNetString(G2DatePicker_GetMaxDate(datePicker));
	var selectedDate= Date_ToDotNetString(G2DatePicker_GetDate(datePicker));

	var path = G2_MapPath("~/Client/Controls/Calendar.aspx");
	var url = path+"?datePickerId=" + datePickerId+"&MinDate="+minDate+"&MaxDate="+maxDate+"&SelectedDate="+selectedDate;
	var windowparams = "width=200,height=230,left=270,top=180, location=false";
	var windowtitle = "cal";
	//window.open(rootUrl+"Client/Controls/Calendar.aspx?datePickerId=" + datePickerId+"&MinDate="+minDate+"&MaxDate="+maxDate+"&SelectedDate="+selectedDate, "cal", "width=200,height=230,left=270,top=180, location=false");
	if (isModal)
	{
		//Pop-up calendar
		G2PopupWindow_Open(url,null,false,windowtitle,windowparams);
	}
	else
	{	
		var locationStyle = "";
		if(datePicker.popcalendarabove)
		{
			var top = G2_GetAbsoluteTop(datePicker)-189;
			var left = G2_GetAbsoluteLeft(datePicker);
			
			if( IE7 && window.compactMode == true) //6651 - problem with the location of the calendare in IE7 in compact mode - diffrent calculation is needed
			{
				var top = G2_GetAbsoluteTop(datePicker)-345;
				var left = G2_GetAbsoluteLeft(datePicker)-90;				
			}
			locationStyle = String.Format("top:{0}px; left:{1}px; ", top, left);
		
		}
		
		var floatingDivHtml = String.Format('<DIV ID="floatingCalendarDiv" style="position:absolute; {0} width:184px; height:189px; margin:0px; background-color:transparent;z-index:1000;">', locationStyle);
		// Floating Calendar
		var floatingDiv = G2DOM.G2CreateElement(floatingDivHtml);//'<DIV ID="floatingCalendarDiv" style="position:absolute; left:'+(datePicker.left+225)+'px; top:'+(datePicker.top-15)+'px; width:184px; height:189px; margin:0px; background-color:transparent;z-index:1000;">');
		//Remove old calendar
		G2_DetachEvent(document,'onclick',G2DatePicker_CloseFloatingCalendar); //This will prevent closing the new calendar
		var oldCalendar = document.getElementById('floatingCalendarDiv');	
		var createNewCalendar = true;
		if (oldCalendar)
		{
			if (datePicker.contains(oldCalendar))
				createNewCalendar = false;
			oldCalendar.parentElement.removeChild(oldCalendar);			
		}
		
		if (createNewCalendar)
		{
			datePicker.appendChild(floatingDiv);
			datePicker._g2calendar = floatingDiv;
			//G2_AttachEvent(tb, "onkeyup", G2DatePicker_TextBox_OnKeyUp);
			//window.setTimeout("document.body.attachEvent('onclick',G2DatePicker_CloseFloatingCalendar);",0); //Will happen after the click event is processed.
			G2_DetachEvent(document,'onclick',G2DatePicker_CloseFloatingCalendar); //This will prevent closing the new calendar
			window.setTimeout("G2_AttachEvent(document,'onclick',G2DatePicker_CloseFloatingCalendar);",0); //Will happen after the click event is processed.
			var floatingDivIFrame = G2DOM.G2CreateElement('<IFRAME ID="floatingCalendarFrame" src="'+url+'" style="width:184px;height:189px;" FRAMEBORDER=0  SCROLLING=NO>');
			floatingDiv.appendChild(floatingDivIFrame);
			floatingDivIFrame.src = url //FIX for case 4468
			floatingDivIFrame.contentWindow.opener = window;
			floatingDivIFrame.contentWindow.g2opener = window; //FF refuses to set opener
			var wnd = window;			
			verifyObjectShown(floatingDiv);
			verifyObjectShown(floatingDivIFrame);
		}			
	}
}

function G2DatePicker_CloseFloatingCalendar()
{

	Debug.writeln('G2DatePicker_CloseFloatingCalendar');
	var oldCalendar = document.getElementById('floatingCalendarDiv');
	if (oldCalendar)
	{
		Debug.writeln('G2DatePicker_CloseFloatingCalendar - closed existing calendar.');
		if(oldCalendar.parentElement._g2calendar)
			oldCalendar.parentElement._g2calendar = null;
		oldCalendar.parentElement.removeChild(oldCalendar);	
		G2_DetachEvent(document,'onclick',G2DatePicker_CloseFloatingCalendar); //This will prevent closing the new calendar
		//Cacnel event bubbling so we wont get the click to open event
		if (event)
		{
			event.cancelBubble = true;
			event.returnValue = false;
		}
		return false;
		//document.body.detachEvent('onclick',G2DatePicker_CloseFloatingCalendar);
	}	
}



function G2DatePicker_updateDayOfWeek(sender)
{
    var lblDayOfWeekID = G2DatePicker_GetCachedProperty(sender, "lbldayofweekid");
    
    var lblDayOfWeek = sender.document.getElementById(lblDayOfWeekID);
	var date = G2DatePicker_GetDate(sender);//sender.getDate();
	if(date!=null)
	{
		//TODO: find this more accuratly.
		var iDay = date.getDay();
		var dayOfWeek = weekDays[iDay];
		lblDayOfWeek.innerText = dayOfWeek;
	}
	else
	{
		lblDayOfWeek.innerText = "";
	}
}

function G2DatePicker_SimulateValidation(datePicker)
{
	var targetElement;
	if(G2DatePicker_SeperateYearAndMonth(datePicker))
	{
		targetElement = G2DatePicker_GetListMonths(datePicker);
	}
	else
	{
		targetElement = G2DatePicker_GetListMonthYear(datePicker);
	}

	G2Validator_ValidateElementOnChange(targetElement);
}

//in rtl (hebrew) the date is reversed (when comes from the server or from calendar)
//when it is typed by the user it is already ok (thus disableRtl)
function G2DatePicker_IsRtl(datePicker)
{
    return (datePicker.isrtl == 'true' && datePicker.disableRtl != true);
}

function Calendar_UpdateDatePicker(datePickerId, strNewDate)
{
	//Parse the Date string
	var newDate = new Date(strNewDate);
	
	//Resolve the datePicker Control
	var datePicker = document.getElementById(datePickerId);
	
	//Set the date on the datePicker
	G2DatePicker_SetDate(datePicker, newDate, true);
	
	G2DatePicker_SimulateValidation(datePicker);
//	//Trigger the onchange event on the datePicker
//	window.opener.execScript(datePicker.onchange);
}



// Date functions
function Date_GetNumOfDaysInMonth(fullYear, month)
{
    if(!Date_IsValid(fullYear, month, 29))
        return 28
    if(!Date_IsValid(fullYear, month, 30))
        return 29
    if(!Date_IsValid(fullYear, month, 31))
        return 30;
        
    return 31;
}

function Date_IsValid(fullYear, month, day) 
{
	var test = new Date(fullYear,month,day);
	if ((test.getFullYear() == fullYear) && (month == test.getMonth()) &&  (day == test.getDate()))
		return true;
	else
		return false;
}



function Date_GetDateIfValid(fullYear, month, day, hours, minutes, seconds) 
{
	if(hours==null)
		hours = 0;
	if(minutes==null)
		minutes = 0;
	if(seconds==null)
		seconds = 0;
	var test = new Date(fullYear, month, day, hours, minutes, seconds);
	if (test.getFullYear() == fullYear && 
			month == test.getMonth() &&  
			day == test.getDate() &&
			hours == test.getHours() &&  
			minutes == test.getMinutes() &&  
			seconds == test.getSeconds() 
			)
		return test;
	else
		return null;
}


function Date_RemoveTime(date)
{
	var newDate = new Date(date.toDateString());
	return newDate;
}


function G2DatePicker_ShowDayOfWeek(datePicker)
{
	return G2DOM.G2GetAttribute(datePicker,"options").search("ShowDayOfWeek")!=-1;
}
function G2DatePicker_AllowNull(datePicker)
{
	return G2DOM.G2GetAttribute(datePicker,"options").search("AllowNull")!=-1;
}
function G2DatePicker_SeperateYearAndMonth(datePicker)
{
	return G2DOM.G2GetAttribute(datePicker,"options").search("SeperateYearAndMonth")!=-1;
}
function G2DatePicker_SeperateHourAndMinute(datePicker)
{
	return G2DOM.G2GetAttribute(datePicker,"options").search("SeperateHourAndMinute")!=-1;
}

function G2DatePicker_ShowTime(datePicker)
{
	return G2DOM.G2GetAttribute(datePicker,"options").search("ShowTime")!=-1;
}

function G2DatePicker_GetTimeControl(datePicker)
{
	return G2DatePicker_GetCachedProperty(datePicker, "listtime");
}

function G2DatePicker_GetHoursDropDown(datePicker)
{
	return G2DatePicker_GetCachedProperty(datePicker, "ddlhours");
}

function G2DatePicker_GetMinutesDropDown(datePicker)
{
	return G2DatePicker_GetCachedProperty(datePicker, "ddlminutes");
}

function G2DatePicker_GetListDays(datePicker)
{
	return G2DatePicker_GetCachedProperty(datePicker, "listdays");
}
function G2DatePicker_GetListMonthYear(datePicker)
{
	return G2DatePicker_GetCachedProperty(datePicker, "listmonthyear");
}
function G2DatePicker_GetListYears(datePicker)
{
	return G2DatePicker_GetCachedProperty(datePicker, "listyears");
}
function G2DatePicker_GetListMonths(datePicker)
{
	return G2DatePicker_GetCachedProperty(datePicker, "listmonths");
}

function G2_EmulateKeyPress(keyPressEvent)
{
	var e = keyPressEvent;
	var ch = String.fromCharCode(e.keyCode)
	if(ch=="")
		return;
	G2Event.stop(e);
	var range = document.selection.createRange();
	if(range.text.length>0)
	{
		document.selection.clear();
		range.text=ch;
	}
	else
	{
		range.text+=ch;
	}

}
function G2DatePicker_Mask(textbox, e)
{
	var oldText = textbox.value;
	G2_EmulateKeyPress(e);
	var text = textbox.value;
	if(text==oldText)
		return;
	var keyCode = e.keyCode;
//	var text = textbox.value;
//	var range = document.selection.createRange();
//	
	var pos = G2_GetCaretPosition(textbox);
//	var ch = String.fromCharCode(keyCode);
//	if(ch=="")
//		return;
//	G2Event.stop(e);
//	text = text.substr(0, pos)+ ch + text.substr(pos, text.length);
	text = String_RemoveAll(text, "/");
	for(var i=0;i<8;i++)
	{
		var ch = null;
		if(text.length>i)
			ch = text.charAt(i);
		if(i==2 || i==5)
		{
			if(ch!="/")
			{
				text = String_InsertAt(text, i, "/");
			}
		}
		else
		{
			if(ch==null)
				text = String_InsertAt(text, i, " ");
		}
	}
	text = text.substr(0, 8);
	
	var pos = G2_GetCaretPosition(textbox);
//	pos++;
	if(pos==2 || pos==5)
	{
		if(keyCode==Char.Backspace)
		{
			pos--;
			text = String_RemoveAt(text, pos);
			text = String_InsertAt(text, pos, " ");
		}
		else
		{
			pos++;
		}
	}
	else if(keyCode==Char.Tab)
	{
		pos = 0;
	}
	if(textbox.value!=text)
	{
		textbox.value = text;
		//Feature: blur when filled
	  if(pos==8)
	  {
	    G2_AutoSkip(textbox, true, e);
	  }
	  else
	  {
		  G2_SetCaretPosition (textbox, pos);
		}
		return true;
	}
	G2_SetCaretPosition (textbox, pos);
	window.status = textbox.value.length + ":["+textbox.value+"]";
	return false;
}


function G2DatePicker_TextBox_OnKeyPress(e)
{	
	var sender = G2Event.element(e);

	var keyCode = e.keyCode;
	if(keyCode==9 || keyCode==16) //tab, shift+tab
		return;
	var changed = false;
	changed = G2DatePicker_Mask(sender, e);
//	if(changed)
//	{
//		G2DatePicker_Changed(sender.DatePicker);
//	}
}

function G2DatePicker_TextBox_OnBlur(e)
{
	var sender = G2Event.element(e);
	var datePicker = sender.DatePicker;
	datePicker.disableRtl = true; 
	var date = G2DatePicker_GetDate(datePicker);
	datePicker.disableRtl = false;
	
	// if there was no change- return without ant action
	if(sender.currentDate == date)
		return;

	G2DatePicker_SetDate(datePicker, date);
}

function G2DatePicker_TextBox_OnFocus(e)
{
	
	var sender = G2Event.element(e);
	var datePicker = sender.DatePicker;
	var date = G2DatePicker_GetDate(datePicker);
	sender.currentDate = date;
	if(date!=null)
	{
		var format = "dd/MM/yy";
		sender.value = Date_ToString(date, format);
	}
	else
	{
		sender.value = "  /  /  ";
		if(datePicker.nullcssclass!=null)
			datePicker.className = datePicker.cssclass;
	}
	sender.select();
}









function getFirstDayOfWeek(year, month)
{
	if(typeof(year)=="object")
	{
		var date = year;
		var day = new Date(date.getFullYear(), date.getMonth(), 1).getDay();
		return day;
	}
	var day = new Date(year, month, 1).getDay();
	return day;
}

Calendar = function()
{
	this.suspendLayout();

	this.element = window.top.document.createElement("div");
	this.element._calendar = this;
	this.element.style.position = "absolute";
	this.element.className = "Calendar";
	G2_AttachEvent(this.element, "onselectstart", function(e)
	{
		G2Event.stop(e);
	});
	this.selectedDate = null;
	this._createTable();
	var caller = this;
	G2_AttachEvent(this.element, "onclick", function(e)
	{
		caller._element_onclick(e);
	});
	G2_AttachEvent(this.element, "ondblclick", function(e)
	{
		caller._element_onclick(e);
	});
	G2_AttachEvent(this.element, "onmouseover", function(e)
	{
		caller._element_onmouseover(e);
	});
	G2_AttachEvent(this.element, "onmouseout", function(e)
	{
		caller._element_onmouseout(e);
	});
	this.header = G2DOM.G2CreateElementFromHtml(Calendar._calendarHeaderTemplate, window.top.document);
	this.dateCaptionElement = G2DOM.GetChildElementById(this.header, "dateCaption");
	this.element.insertAdjacentElement("afterBegin", this.header);
	var now = new Date();
	this.today = new Date(now.getFullYear(), now.getMonth(), now.getDate());
	this.maxDate = null;
	this.minDate = null;
	this.showDate(this.today);
}

if(document.body.dir == "rtl")
{
    Calendar._calendarHeaderTemplate =	[
    '				<table class="calendarHeaderTemplate" cellspacing="0" cellpadding="0" border="0">',
    '						<tbody>',
    '							<tr>',
    '								<td style="width: 15px" class="CalendarTitleBackg">',
    '									<div title="Go to the previous month" class="CalendarNavigator_PreviousMonthRTL" style="color: #234b86" href="javascript:void(0);" onclick="Calendar._previousMonth(event);" ondblclick="Calendar._previousMonth(event);"></div></td>',
    '								<td style="width: 120px" class="CalendarTitleBackg" align="center"  id="dateCaption" nowrap></td>',
    '								<td style="width: 15px" align="right" class="CalendarTitleBackg">',
    '									<div title="Go to the next month" class="CalendarNavigator_NextMonthRTL" href="javascript:void(0);" onclick="Calendar._nextMonth(event);" ondblclick="Calendar._nextMonth(event);"></div></td>',
    '							</tr>',
    '						</tbody>',
    '					</table>'
    ].join("");
}
else
{
    Calendar._calendarHeaderTemplate =	[
    '				<table class="calendarHeaderTemplate" cellspacing="0" cellpadding="0" border="0">',
    '						<tbody>',
    '							<tr>',
    '								<td style="width: 15px" class="CalendarTitleBackg">',
    '									<div title="Go to the previous month" class="CalendarNavigator_PreviousMonth" style="color: #234b86" href="javascript:void(0);" onclick="Calendar._previousMonth(event);" ondblclick="Calendar._previousMonth(event);"></div></td>',
    '								<td style="width: 120px" class="CalendarTitleBackg" align="center"  id="dateCaption" nowrap></td>',
    '								<td style="width: 15px" align="right" class="CalendarTitleBackg">',
    '									<div title="Go to the next month" class="CalendarNavigator_NextMonth" href="javascript:void(0);" onclick="Calendar._nextMonth(event);" ondblclick="Calendar._nextMonth(event);"></div></td>',
    '							</tr>',
    '						</tbody>',
    '					</table>'
    ].join("");
}

Calendar.prototype.setRelativeElement = function(element)
{
	this._relativeElement = element;
}
Calendar.prototype.setRelativeElementDock = function(dock)
{
	this._relativeElementDock = dock;
}

Calendar.prototype.render = function()
{
	this.resumeLayout();
}
Calendar.prototype.closePopup = function()
{
	G2PopupManager.closePopup(this.element);
	return;
}


Calendar.prototype.showPopup = function(e)
{
	G2PopupManager.openPopup(this.element, this._relativeElement, this._relativeElementDock, true);
	var w = this._relativeElement.document.parentWindow;
	var tw = window.top;
	//  the marked lines caused 8646
  //	if(tw!=w)
  //	  tw.Calendar = Calendar;
	return;
}

Calendar._getCalendar = function(e)
{
	var element = e.srcElement;
	while(element!=null)
	{
		if(element._calendar!=null)
			return element._calendar;
		element = element.parentElement;
	}
	return null;
}

Calendar._previousMonth = function(e)
{
	var cal = this._getCalendar(e);
	cal.showPreviousMonth(e);
}
Calendar._nextMonth = function(e)
{
	var cal = this._getCalendar(e);
	cal.showNextMonth(e);
}

Calendar.prototype._element_onclick = function(e)
{
	var cell = e.srcElement;
	if(cell.tagName=="TD" && cell.date!=null && this._canSelectDate(cell.date))
	{
		if (this.selectedDate-cell.date==0) 
			this.closePopup();
		else
			this.setSelectedDate(cell.date);
				
	}
	else if(cell==this._btnNext)
	{
		this.showNextMonth();
	}
	else if(cell==this._btnPrevious)
	{
		this.showPreviousMonth();
	}
}


Calendar.prototype.setMinDate = function(date)
{
	this.minDate = date==null ? null : new Date(date.getFullYear(), date.getMonth(), date.getDate());
	this._redraw();
}

Calendar.prototype.setMaxDate = function(date)
{
	this.maxDate = date==null ? null : new Date(date.getFullYear(), date.getMonth(), date.getDate());
	this._redraw();
}

Calendar.prototype._element_onmouseover = function(e)
{
	var cell = e.srcElement;
	if(cell.tagName=="TD" && cell.date!=null)
	{
		if(this._canSelectDate(cell.date))
		{
			G2_AddCssClass(cell, "CalendarDay_MouseOver");
		}
		else
		{
			G2_AddCssClass(cell, "CalendarDay_MouseOver_Disabled");
		}
	}
}

Calendar.prototype._element_onmouseout = function(e)
{
	var cell = e.srcElement;
	if(cell.tagName=="TD" && cell.date!=null)
	{
		G2_RemoveCssClass(cell, "CalendarDay_MouseOver");
		G2_RemoveCssClass(cell, "CalendarDay_MouseOver_Disabled");
	}
}

Calendar.prototype.getSelectedDate = function(date)
{
	return this.selectedDate;
}

Calendar.prototype.setSelectedDate = function(date)
{
	if(date!=null)
		date = new Date(date.getFullYear(), date.getMonth(), date.getDate()); //strip time
	if(this.selectedDate==date || this.selectedDate-date==0)
		return;
	this.selectedDate = date;
	this._redraw();
	this.fireEvent("SelectedDateChanged");
}


Calendar.prototype.showNextMonth = function()
{
	var date= this._shownDate;
	this.showDate(new Date(date.getFullYear(), date.getMonth()+1, 1));
}
Calendar.prototype.showPreviousMonth = function()
{
	var date = this._shownDate;
	this.showDate(new Date(date.getFullYear(), date.getMonth()-1, 1));
}

Calendar.prototype.showDate = function(date)
{
	date = new Date(date.getFullYear(), date.getMonth(), 1); //strip time and day
	if(this._shownDate==date)
		return;
	this._shownDate = date;
	this._redraw();
}
Calendar.prototype.suspendLayout = function()
{
	this._suspendLayout = true;
	this._layoutChanged = false;
}
Calendar.prototype.resumeLayout = function()
{
	this._suspendLayout = false;
	if(this._layoutChanged)
		this._redraw();
}

Calendar.prototype._redraw = function()
{
	if(this._suspendLayout)
	{
		this._layoutChanged = true;
		return;
	}
	var table = this.table;
	var date = this._shownDate;
	this.dateCaptionElement.innerText = Date_ToString(date, "yyyy MMMM");

	var selectedDate = this.getSelectedDate();
	var firstDayOfWeek = getFirstDayOfWeek(date);
	var currentDate = new Date(date.getFullYear(), date.getMonth(), 1-firstDayOfWeek);
	var row = table.rows[0];
	row.className = "CalendarDaysOfWeek";
	for(var j=0;j<7;j++)
	{
		var cell = row.cells[j];
		cell.innerText = G2_ShortDays[j];
	}

	for(var i=1;i<7;i++)
	{
		var row = table.rows[i];
		for(var j=0;j<7;j++)
		{
			var cell = row.cells[j];
			var styles = G2_ParseCssClasses(cell);
			styles.add("CalendarDay");
			cell.innerText = currentDate.getDate().toString();
			if(!this._canSelectDate(currentDate))
			{
				styles.add("CalendarDay_Disabled");
			}
			else
			{
				styles.remove("CalendarDay_Disabled");
			}
			if(currentDate.getMonth()!=date.getMonth())
			{
				styles.add("CalendarDay_Dimmed");
			}
			else
			{
				styles.remove("CalendarDay_Dimmed");
			}
			// compare only the ate component of the dateTime value
			
			if(selectedDate && currentDate && selectedDate.getYear()== currentDate.getYear() && selectedDate.getMonth()== currentDate.getMonth() && selectedDate.getDate()== currentDate.getDate())
			{
				styles.add("CalendarDay_Selected");
				styles.remove("CalendarDay_Today");
			}
			else
			{
				styles.remove("CalendarDay_Selected");
				if(currentDate-this.today==0)
				{
					styles.add("CalendarDay_Today");
				}
				else
				{
					styles.remove("CalendarDay_Today");
				}
			}
			styles.remove("CalendarDay_MouseOver");
			styles.remove("CalendarDay_MouseOver_Disabled");
			G2_SetCssClasses(cell, styles);

			cell.date = currentDate;
			currentDate = Date_AddDays(currentDate, 1);
		}
	}
}

Calendar.prototype._canSelectDate = function(date)
{
	// check the datePicker's excludedWeekDays
	if(this.datePicker.excludedweekdays != null &&
		this.datePicker.excludedweekdays.indexOf(date.getDay()) != -1)
		return false;

	if(this.minDate!=null && date-this.minDate<0)
		return false;
	if(this.maxDate!=null && date-this.maxDate>0)
		return false;
	return true;
}

Calendar.prototype._createTable = function()
{
	var table = window.top.document.createElement("table");
	this.table = table;
	table.className = "Calendar_Table";
	table.cellPadding = 0;
	table.cellSpacing = 0;
	table.border = 0;
	for(var i=0;i<7;i++)
	{
		var row = table.insertRow(-1);
		for(var j=0;j<7;j++)
		{
			var cell = row.insertCell(-1);
		}
	}
	this.element.innerHTML = "";
	this.element.appendChild(table);
}


Calendar.prototype.attachEvent = function(eventName, handler)
{
	if(this.events==null)
	{
		this.events = new Object();
	}
	if(this.events[eventName]==null)
		this.events[eventName] = [handler];
	else
		this.events[eventName].push(handler);
}
Calendar.prototype.fireEvent = function(eventName)
{
	if(this.events==null)
		return;
	
	var handlers = this.events[eventName];
	if(handlers==null)
		return;
	for(var i=0;i<handlers.length;i++)
	{
		handlers[i](this);
	}
}

function G2DateRangePicker_GetStartDateControl(dateRangePicker)
{
	if(dateRangePicker.StartDateControl==null)
	{
		dateRangePicker.StartDateControl = document.getElementById(dateRangePicker.startdatecontrolid);
	}
	return dateRangePicker.StartDateControl;
}

function G2DateRangePicker_GetEndDateControl(dateRangePicker)
{
	if(dateRangePicker.EndDateControl==null)
	{
		dateRangePicker.EndDateControl = document.getElementById(dateRangePicker.enddatecontrolid);
	}
	return dateRangePicker.EndDateControl;
}

//This function is unused, but make sure to send the SenderID and not the sender itself
function G2DateRangePicker_VerifyInit(senderID)
{
	G2DateRangePicker_Init(senderID);
}

//Modified by Alon - sender is the ID of the sender, not the sender itself (FF compatibility)
function G2DateRangePicker_Init(senderID)
{
	var sender = document.getElementById(senderID);
	if(!sender || sender.IsInited)
		return;
	sender.IsInited = true;	
	G2DOM.G2TransferAttributes(sender);	
	var start = G2DateRangePicker_GetStartDateControl(sender);
	var end = G2DateRangePicker_GetEndDateControl(sender);
	if(start==null || end==null)
		return;
	
	//Force initialization of the datepickers
	G2DatePicker_VerifyInit(start, true);
	G2DatePicker_VerifyInit(end, true);
	sender.nightmode = sender.nightmode!="false";
	sender.includehours = sender.includehours!="false";

	if(sender.mode=="Invisible")
	{
		sender.maxdays = parseInt(sender.maxdays);
		sender.mindays = parseInt(sender.mindays);
	}
	else
	{
		var nddDays = G2DateRangePicker_GetDaysNumericDropDown(sender);
		G2NumericDropDown_VerifyInit(nddDays);
		nddDays.onchange=function(){G2DateRangePicker_DaysChanged(sender);};
	}
	
	
//	sender.onpropertychange = "G2DateRangePicker_OnPropertyChanged(this);";

	start.G2OnSelectedDateChanged.push
	(
		function(e)
		{
			G2DateRangePicker_StartDateChanged(sender, e);
		}
	);
	end.G2OnSelectedDateChanged.push
	(
		function(e)
		{
			G2DateRangePicker_EndDateChanged(sender, e);
		}
	);
	
	G2DateRangePicker_EndDateChanged(sender);
}

function G2DateRangePicker_OnPropertyChanged(dateRangePicker)
{
	if(dateRangePicker.mode!="Invisible")
	{
		var nddDays = G2DateRangePicker_GetDaysNumericDropDown(dateRangePicker);
		if(dateRangePicker.disabled!=nddDays.disabled)
		{
			G2_RecursiveSetPropertyValue(dateRangePicker, "disabled", dateRangePicker.disabled);
		}
	}
}


function G2DateRangePicker_GetDaysNumericDropDown(dateRangePicker)
{
	if(dateRangePicker.listDaysControl==null)
	{
		dateRangePicker.listDaysControl = document.getElementById(dateRangePicker.listdayscontrolid);
	}
	return dateRangePicker.listDaysControl;
}

///Occurs when the DateRangePicker changed its days
function G2DateRangePicker_DaysChanged(dateRangeControl)
{
	if(dateRangeControl.updating)
		return;
	dateRangeControl.updating = true;
	var startDateControl = G2DateRangePicker_GetStartDateControl(dateRangeControl);
	var endDateControl = G2DateRangePicker_GetEndDateControl(dateRangeControl);
	var startDate = G2DatePicker_GetDate(startDateControl, true);
	var sDays = parseInt(G2DateRangePicker_GetDaysNumericDropDown(dateRangeControl).value);
	if(sDays!="")
	{
		var days = parseInt(sDays);
	    //if day mode - we should subtract 1 day
		if(!dateRangeControl.nightmode)
			days--;
		var endDate = Date_AddDays(startDate, days);
		G2DatePicker_SetDate(endDateControl, endDate, true);
	}
	dateRangeControl.updating = false;
}

///Occurs when one of the date controls (start/end) changes its date
function G2DateRangePicker_StartDateChanged(dateRangeControl, e)
{
	if(dateRangeControl.updating)
		return;
	dateRangeControl.updating = true;
	var startDateControl = G2DateRangePicker_GetStartDateControl(dateRangeControl);
	var endDateControl = G2DateRangePicker_GetEndDateControl(dateRangeControl);
	var startDate = G2DatePicker_GetDate(startDateControl);
	if(startDate!=null)
	{
		var endDate = G2DatePicker_GetDate(endDateControl);
		var days = G2DateRangePicker_CalculateDays(dateRangeControl, startDate, endDate);
		if(dateRangeControl.mode=="Invisible")
		{
			if(days<dateRangeControl.mindays)
			{
				var newDate = Date_AddDays(startDate, dateRangeControl.mindays);
				G2DatePicker_SetDate(endDateControl, newDate, true);
			}
			else if(days>dateRangeControl.maxdays)
			{
				var newDate = Date_AddDays(startDate, dateRangeControl.maxdays);
				G2DatePicker_SetDate(endDateControl, newDate, true);
			}
		}
		else
		{
			if(Date_EqualsWithoutTime(startDate, e.oldValue)) //only time has changed
			{
			  //include the hours while calculating the range ( i.e. more the 24 hours range will cause addition of 1 day )
				if(dateRangeControl.includehours)
				{
					var currentDays = G2DateRangePicker_GetDays(dateRangeControl);
					if(currentDays!=days) //happens when just the time has changed
					{
						G2DateRangePicker_SetDays(dateRangeControl, days);
					}
				}
			}
			else
			{
				var currentDays = G2DateRangePicker_GetDays(dateRangeControl);
				if(currentDays == null)
				{
					currentDays = days;
					G2DateRangePicker_InternalSetDays(dateRangeControl,currentDays);
				}
				Date_RemoveTime(startDate);
				Date_RemoveTime(endDate);
				var newDate;
				//if day mode - we should subtract 1 day
                if(dateRangeControl.nightmode)
					newDate = Date_AddDays(startDate, currentDays);
				else
				    newDate = Date_AddDays(startDate, currentDays - 1);
				   
				G2DatePicker_SetDate(endDateControl, newDate, true);
			}
		}
	}
	dateRangeControl.updating = false;
}

//case 7606:
//this function is called in case the day light saving turn date (summer to winter or vise versa) 
//happens to occur between start date and end date
//these are the time formats: "00:00:00 UTC+0100" or "00:00:00 UTC-0100"
function AddHoursAtDateLightSavingSwitch(endDate, startDate)
{
	var hoursToAdd = 0
	if(startDate != null && startDate.toTimeString().indexOf('+') > -1)
		hoursToAdd -= ExtractMissingHours(startDate, '+');
	if(startDate != null && startDate.toTimeString().indexOf('-') > -1)
		hoursToAdd += ExtractMissingHours(startDate, '-');
	if(endDate != null && endDate.toTimeString().indexOf('+') > -1)
		hoursToAdd += ExtractMissingHours(endDate, '+');
	if(endDate != null && endDate.toTimeString().indexOf('-') > -1)
		hoursToAdd -= ExtractMissingHours(endDate, '-');
	return hoursToAdd;
}

function ExtractMissingHours(inPutDate, sign)
{
	var numInputDate = Number(inPutDate.toTimeString().split(sign)[1])/100;
	if(!isNaN(numInputDate))
		return Number(sign + numInputDate);
	else 
		return Number(sign + 1);
}

function G2DateRangePicker_CalculateDays(dateRangeControl, startDate, endDate)
{
	var hoursToAdd = AddHoursAtDateLightSavingSwitch(endDate, startDate);
	
	// If not include hours - remove time to calculate the days
	if(!dateRangeControl.includehours)
	{
	    Date_RemoveTime(startDate);
		Date_RemoveTime(endDate);
	}
	if(dateRangeControl.nightmode)
		return DateRange_GetNights(endDate-startDate, hoursToAdd);
    return DateRange_GetDays(endDate-startDate, hoursToAdd);

}

function G2DateRangePicker_GetDays(dateRangeControl)
{
	var ndd = G2DateRangePicker_GetDaysNumericDropDown(dateRangeControl);
	var days = String_ToInt(ndd.value);
	return days;
}

function Date_EqualsWithoutTime(date1, date2)
{
	if(date1==null || date2==null)
		return date1==date2;
	return (date1.getFullYear()==date2.getFullYear() && date1.getMonth()==date2.getMonth() && date1.getDate()==date2.getDate());
}

function Date_Equals(date1, date2)
{
	if(date1==null || date2==null)
		return date1==date2;
	return date1.valueOf()==date2.valueOf();
}

function Date_RemoveTime(date)
{
	if(date)
		date.setHours(0, 0, 0, 0);
}

function G2DateRangePicker_EndDateChanged(dateRangeControl, e)
{
	if(dateRangeControl.updating)
		return;
	dateRangeControl.updating = true;
	var startDateControl = G2DateRangePicker_GetStartDateControl(dateRangeControl);
	var endDateControl = G2DateRangePicker_GetEndDateControl(dateRangeControl);
	var startDate = G2DatePicker_GetDate(startDateControl);
	var endDate = G2DatePicker_GetDate(endDateControl);
	
	if(endDate!=null && startDate!=null)
	{
		var days = G2DateRangePicker_CalculateDays(dateRangeControl, startDate, endDate);
		if(dateRangeControl.mode=="Invisible")
		{ 
//			//TODO: remove this code - we don't wan't to update the startDatePicker
//			if(days<dateRangeControl.mindays)
//			{
//				var newDate = Date_SubtractDays(endDate, dateRangeControl.mindays);
//				G2DatePicker_SetDate(startDateControl, newDate);
//			}
//			else if(days>dateRangeControl.maxdays)
//			{
//				var newDate = Date_SubtractDays(endDate, dateRangeControl.maxdays);
//				G2DatePicker_SetDate(startDateControl, newDate);
//			}
		}
		else
		{
			var nddDays = G2DateRangePicker_GetDaysNumericDropDown(dateRangeControl);
			nddDays.value = days;
		}
	}
	dateRangeControl.updating = false;
}

function G2DateRangePicker_SetDays(dateRangePicker, days)
{
	G2DateRangePicker_InternalSetDays(dateRangePicker, days);
	G2DateRangePicker_DaysChanged(dateRangePicker);
}

function G2DateRangePicker_InternalSetDays(dateRangePicker, days)
{
	var nddDays = G2DateRangePicker_GetDaysNumericDropDown(dateRangePicker);
	nddDays.value = days;
}

// JScript File
G2Dragger = function(cell)
{
	this.Cell = cell;
	this.SetBackgroundImage("Dragger.gif");
	this.SurfaceElement = cell.parentElement.parentElement.parentElement;
	G2_AttachEventWithCaller(this.Cell, "onmousedown", this.DragHandleElement_mousedown, this);
	G2_AttachEventWithCaller(this.Cell,"onmouseover", this.DragHandleElement_mouseover, this);
	G2_AttachEventWithCaller(this.Cell,"onmouseout", this.DragHandleElement_mouseout, this);
}

G2Dragger.EnableDrag = function(cell)
{
	cell._dragger = new G2Dragger(cell);
}

G2_DeclareClass(G2Dragger, "G2Dragger", null, 
{
	DragHandleElement_mousedown : function(e)
	{
		if(this.isDragging)
			this._EndDrag(e);
		else
			this._StartDrag(e);
	},
	_StartDrag : function(e)
	{
		this.isDragging = true;
		var mouseX = e.clientX;
		this.offsetX = mouseX-this.Cell.offsetLeft;
		this.Cell.setCapture(true);
		G2_AttachEventWithCaller(this.Cell, "onmousemove", this.DragHandleElement_mousemove, this);
		G2_AttachEventWithCaller(this.Cell, "onmouseup", this.DragHandleElement_mouseup, this);
	},
	_EndDrag : function()
	{
		this.Cell.releaseCapture();
		G2_DetachEventWithCaller(this.Cell, "onmousemove", this.DragHandleElement_mousemove, this);
		G2_DetachEventWithCaller(this.Cell, "onmouseup", this.DragHandleElement_mouseup, this);
		this.isDragging = false;
	},
	DragHandleElement_mousemove : function(e)
	{
		var prevCell = this.Cell.previousSibling;
		var width = e.clientX - prevCell.offsetLeft - this.offsetX;
		if(width < 0)
			width = 0;
		prevCell.style.width = width;	
	},
	DragHandleElement_mouseup : function(e)
	{
		this.SetBackgroundImage("Dragger.gif");
		if(this.isDragging)
			this._EndDrag();
	},
	DragHandleElement_mouseover : function(e)
	{
		this.SetBackgroundImage("Dragger_Over.gif");
	},
	DragHandleElement_mouseout : function(e)
	{
		this.SetBackgroundImage("Dragger.gif");
	},
	SetBackgroundImage : function(ImageName)
	{
		var virtualUrl = "/App_Themes/Setup/Images/Icons/" + ImageName;
		var rootAppPath = document.getElementById("G2_RootAppPath").value;
		var url = G2_MapPath(rootAppPath + virtualUrl);
		this.Cell.style.backgroundImage = "url(" + url + ")";
	}
});



G2DropDownList_HtmlSelectEmptyValue = "_NULL_";

function G2DropDownList_VerifySubmit(ddlControlId)
{
	var ddlControl = document.getElementById(ddlControlId);
	if(ddlControl!=null && ddlControl.disabled)
		ddlControl.disabled = false;
}

function G2DropDownList_VerifyInit(ddlControl)
{
	if(ddlControl.IsInited)
		return;
	if (!ddlControl)
	{
		G2_Warn("G2DropDownList_VerifyInit","ddlControl is null!");
		return;
	}
	G2DOM.G2TransferAttributes(ddlControl);
	ddlControl.IsInited = true;
	
	ddlControl.g2onload = []; //events array
	var changeScripts = ddlControl.g2onchange;
	ddlControl.g2onchange = []; //events array
	if(changeScripts!=null)
	{
		var func = eval(changeScripts);
//		if(typeof(func)!="function")
//			throw new Error("g2onchage requires a function name");
		ddlControl.g2onchange.push(func);
	}
	
	if(G2DropDownList_EnableClientSideLoading(ddlControl))
	{		
		G2DropDownList_LoadItems(ddlControl);//asynchornous
	}
	else
	{
		G2DropDownList_InternalLoad(ddlControl);
	}
	EnableSupportForPartialPostData(ddlControl);
  ddlControl.getValue = function()
  {
    if(this.value == G2DropDownList_HtmlSelectEmptyValue)
      return "";
    return this.value;
  }
}

function G2DropDownList_Load(ddlControlId)
{
	var ddlControl = document.getElementById(ddlControlId);
	if(ddlControl==null) //TODO: this might happen when a visible control is found in an invisible gridColumn
		return;
	G2DropDownList_VerifyInit(ddlControl);
}

function G2DropDownList_GetParentListControl(ddlControl)
{
	if(ddlControl.parentlistcontrol==null && ddlControl.parentlistcontrolid!=null)
	{
		ddlControl.parentlistcontrol = document.getElementById(ddlControl.parentlistcontrolid);
	}
	return ddlControl.parentlistcontrol;
}

function G2DropDownList_IsLoaded(ddlControl)
{
	return ddlControl.IsLoaded;
}
function G2DropDownList_InternalLoad(ddlControl)
{
	var allowLoad=true;
	var parentListControl = G2DropDownList_GetParentListControl(ddlControl);
	if(parentListControl!=null)
	{
		if(G2DropDownList_IsLoaded(parentListControl))
		{
			G2DropDownList_ApplyFilter(parentListControl, ddlControl);
			G2DropDownList_AttachToParentListControl(ddlControl, parentListControl);
		}
		else
		{
			allowLoad	 = false;
			parentListControl.g2onload.push
			(
				function()
				{
					G2DropDownList_ApplyFilter(parentListControl, ddlControl);
					G2DropDownList_AttachToParentListControl(ddlControl, parentListControl);
					G2DropDownList_OnLoad(ddlControl);
				}
			);
		}
	}
	if(allowLoad)
		G2DropDownList_OnLoad(ddlControl);
}
	
function G2DropDownList_AttachToParentListControl(ddlControl, parentListControl)
{
	parentListControl.g2onchange.push(
		function()
		{
			G2DropDownList_ApplyFilter(parentListControl, ddlControl);
		});
}

//	if(ddlControl.ChildFilteredControlIds!=null)
//	{
//		ddlControl.ChildFilteredControls = new Array();
//		var tokens = ddlControl.ChildFilteredControlIds.split(",");
//		for(var i=0;i<tokens.length;i++)
//		{
//			var token = tokens[i];
//			if(token.length>0)
//				ddlControl.ChildFilteredControls.push(document.getElementById(token));
//		}
//		G2DropDownList_ApplyChildFiltering(ddlControl);
//	}



//	if(ddlControl.UpdateValueOnControlId!=null)
//	{
//		ddlControl.UpdateValueOnControl = document.getElementById(ddlControl.UpdateValueOnControlId);
//		G2DropDownList_ApplySync(ddlControl);
//	}
//	if(allowLoad)
//	{
//		G2DropDownList_OnLoad(ddlControl);
//	}
//}


function G2DropDownList_OnLoad(ddlControl)
{
	ddlControl.IsLoaded=true;
	for(var i=0;i<ddlControl.g2onload.length;i++)
	{
		ddlControl.g2onload[i](ddlControl);
	}
}





function G2DropDownList_LoadItems(ddlControl)
{
	var stopper = new Stopper();
	stopper.start();
	//G2_Trace(ddlControl, "G2DropDownList_LoadItems: "+stopper.lap()+"ms");

	ddlControl.disabled = true;
	ddlControl.options.add(new Option("Loading", "Loading"), 0);
	var url = G2_MapPath("~/CachePage.ashx");
	G2_GetData
	(
		url+"?CacheDataKey="+ddlControl.CacheDataKey+
			"&DataTextField="+ddlControl.DataTextField+
			"&DataValueField="+ddlControl.DataValueField+
			"&ParentDataValueField="+ddlControl.ParentDataValueField+
			"&DataTextFormatString="+ddlControl.DataTextFormatString, 
		function(xmlhttp)
		{
			G2DropDownList_LoadItemsCallback(ddlControl, xmlhttp.responseText, stopper);
		},
		function(xmlhttp)
		{
		    if (document.getElementById(ddlControl.id) != null)
			    alert("could not load items for "+ddlControl.id+" "+xmlhttp.statusText+", "+xmlhttp.responeText);
		}

	);
}

function G2DropDownList_LoadItemsCallback(ddlControl, responseText, stopper)
{
	//G2_Trace(ddlControl, "G2DropDownList_LoadItemsCallback start");
	//G2_Trace(ddlControl, "G2DropDownList_LoadItemsCallback Eval Start");
	eval(responseText);
	//G2_Trace(ddlControl, "G2DropDownList_LoadItemsCallback Eval End");
	ddlControl.options.remove(0);
	ddlControl.disabled = false;
	G2DropDownList_VerifyNullItem(ddlControl);
	ddlControl.value = ddlControl.selectedvvalue;
	G2DropDownList_InternalLoad(ddlControl);
	//G2_Trace(ddlControl, "G2DropDownList_LoadItemsCallback end: "+stopper.lap()+"ms");
}

function G2DropDownList_VerifyNullItem(ddlControl)
{
	if(G2DropDownList_AllowNull(ddlControl))
	{
		var option = new Option(ddlControl.nulldisplaytext, ddlControl.nullvalue);
		ddlControl.options.add(option, 0);
	}
}


function G2DropDownList_Changed(ddlControl)
{
	if(ddlControl.g2onchange!=null)
	{
		G2_FireEventArray(ddlControl, ddlControl.g2onchange);
	}
	

//  if(ddlControl.g2onchange!=null)
//  {
//    eval(ddlControl.g2onchange+"('"+ddlControl.id+"');");
//  }
//	G2DropDownList_ApplyChildFiltering(ddlControl);
	if(ddlControl.UpdateValueOnControl!=null)
		G2DropDownList_ApplySync(ddlControl);
}

//function G2DropDownList_ApplyChildFiltering(ddlControl)
//{
//	if(ddlControl.ChildFilteredControls!=null)
//	{
//		for(var i=0;i<ddlControl.ChildFilteredControls.length;i++)
//		{
//			var childControl = ddlControl.ChildFilteredControls[i]
//			G2DropDownList_ApplyFilter(ddlControl, childControl);
//		}
//	}
//}

function G2DropDownList_ApplySync(ddlControl)
{
	ddlControl.UpdateValueOnControl.value = ddlControl.value;
}

function G2DropDownList_ApplyFilter(parentListControl, ddlControl)
{
//	var start = new Date();
	var stopper = new Stopper();
	stopper.start();
	//G2_Trace(ddlControl, "G2DropDownList_ApplyFilter - start");
	var parentId = parentListControl.value;

	var startIndex = G2DropDownList_GetRelevantStartIndex(ddlControl);
  // backup the list, only the first time
  if (ddlControl.OriginalOptions==null)
  {
		ddlControl.OriginalOptions = G2_CopyArray(ddlControl.options, startIndex);
		G2DropDownList_GroupOptions(ddlControl);
	
  }
	//G2_Trace(ddlControl, "G2DropDownList_ApplyFilter - group options");
  
  //Backup the selected valkue
  var selectedValue = ddlControl.value;

	//Perform Unfilter if needed  
 	if(ddlControl.nullvalue==parentId)
	{
		//optimization - do not clear and refill the combo again
		if(ddlControl.options.length<ddlControl.OriginalOptions.length)
		{
			ddlControl.options.length = startIndex;
			G2DropDownList_AddItems(ddlControl, ddlControl.OriginalOptions, stopper);
//			ddlControl.options.length = 0;
//			for (n=0;n<ddlControl.OriginalOptions.length;n++)
//			{
//				ddlControl.options.add(ddlControl.OriginalOptions[n]);
//			}
		}
		//G2_Trace(ddlControl, "G2DropDownList_ApplyFilter - group options End");
	}
	else //Perform filter
	{
		G2DropDownList_FilterParentDataValue(ddlControl, parentId, selectedValue, stopper);
  }
  
  if(ddlControl.value!=selectedValue)
  {
		G2DropDownList_Changed(ddlControl);
	}
	
//	var end = new Date();
	//G2_Trace(ddlControl, "G2DropDownList_ApplyFilter end");
}

//function G2DropDownList_FilterParentDataValue2(ddlControl, parentId, selectedValue)
//{
////	var j=0;
//	for(var i=0;i<ddlControl.OriginalOptions.length;i++)
//	{
//		var originalOption = ddlControl.OriginalOptions[i];
//		if(originalOption.pdv==null || originalOption.pdv==parentId)
//		{
//			if(!ddlControl.options.contains(originalOption))
//				ddlControl.options.add(originalOption);
////			if(ddlControl.options[j]!=originalOption)
////				ddlControl.options[j] = originalOption;
//				
//			if(originalOption.value==selectedValue)
//				ddlControl.value = selectedValue;

////			j++;
//		}
//	}
//	if(ddlControl.options.length != j+1)
//		ddlControl.options.length = j+1;
//}

function G2DropDownList_AddItems(ddlControl, items, stopper)
{
	for (n=0;n<items.length;n++)
	{
		var option = items[n];
		ddlControl.options.add(option);
//		if(option.value==selectedValue)
//			ddlControl.value = selectedValue;
	}
}

function G2DropDownList_FilterParentDataValue(ddlControl, parentId, selectedValue, stopper)
{
	var startIndex = G2DropDownList_GetRelevantStartIndex(ddlControl);

  ddlControl.options.length = startIndex;
//	Debug.writeln("G2DropDownList_ApplyFilter - added ungrouped options, took: "+stopper.lap()+"ms");

  var relevantOptions = ddlControl.GroupedOptions[parentId];
 	//G2_Trace(ddlControl, "G2DropDownList_ApplyFilter - found grouped options");
 	if(relevantOptions==null || relevantOptions.length==0)
 	{
 		G2DropDownList_AddItems(ddlControl, ddlControl.OriginalOptions, selectedValue, stopper);
 	}
	else//if(relevantOptions!=null)
  {
		G2DropDownList_AddItems(ddlControl, relevantOptions, selectedValue, stopper);
	}
	ddlControl.value = selectedValue;
	if(ddlControl.selectedIndex==-1 && ddlControl.options.length>0)
		ddlControl.selectedIndex=0;
	//G2_Trace(ddlControl, "G2DropDownList_ApplyFilter - added grouped options");

}


function G2DropDownList_GroupOptions(ddlControl)
{
	var stopper = new Stopper();
	stopper.start();
	//G2_Trace(ddlControl, "entering G2DropDownList_GroupOptions");

	var hashtable = new Object();
	var ungroupedOptions = new Array();
	var startIndex = G2DropDownList_GetRelevantStartIndex(ddlControl);
	for (var i=startIndex;i<ddlControl.OriginalOptions.length;i++)
	{
		var option = ddlControl.OriginalOptions[i];
		if(option.pdv==null)
		{
			ungroupedOptions.push(option);
		}
		else
		{
			var options = hashtable[option.pdv];
			if(options==null)
			{
				options = new Array();
				hashtable[option.pdv] = options;
			}
			options.push(option);
		}
	}
	ddlControl.GroupedOptions = hashtable;
	ddlControl.UnGroupedOptions = ungroupedOptions;
	//G2_Trace(ddlControl, "G2DropDownList_GroupOptions End");
}

function G2DropDownList_GetRelevantStartIndex(ddlControl)
{
	return G2DropDownList_AllowNull(ddlControl) ? 1 : 0;
}

function G2DropDownList_AllowNull(ddlControl)
{
	return ddlControl.AllowNull=="true";
}
function G2DropDownList_EnableClientSideLoading(ddlControl)
{
	var settings = ddlControl.settings;
	//G2DOM.G2GetAttribute(ddlControl,"Settings");
	return settings.search("EnableClientSideLoading")!=-1;
}


//
// Autocomplete with delayed thinktime
//
function G2DropDownList_AutoComplete(sender,event)
{
	if (event==null)
		event = window.event;
	var eventKeyCode = event.keyCode;
	var keyCode = parseInt(eventKeyCode,10);
	if (keyCode==9)
		return true; //Firefox needs it
	var key = MakeUpper(String.fromCharCode(keyCode));

	var now = new Date();
	if(sender.autoCompleteLastTime==null || now-sender.autoCompleteLastTime>1500)
	{
		//G2_Trace(sender, "starting autocomplete session with letter: "+key);
		sender.autoCompleteText = key;
	}
	else
	{
		//G2_Trace(sender, "continuing autocomplete session with letter: "+key);
		sender.autoCompleteText += key;
	}
	sender.autoCompleteLastTime = now;

	if(sender.autoCompleteTimerID!=null)
	{
		window.clearTimeout(sender.autoCompleteTimerID);
	}
	sender.autoCompleteTimerID = window.setTimeout(function(){G2DropDownList_FindAutoCompleteText(sender);}, 300);
	return false;
}

function G2DropDownList_FindAutoCompleteText(sender)
{
	//G2_Trace(sender, "Performing autocomplete search on "+sender.autoCompleteText);
	sender.autoCompleteTimerID = null;
	var text = sender.autoCompleteText;

	var index = -1;
	var s;
	for (var i = 0; i < sender.length; i++) 
	{
		s = MakeUpper(sender.item(i).text);
		s = s.substr(0, text.length);
		if (s == text) 
		{
			index = i;
			break;
		}
	}
	if (index != -1) 
	{
		sender.selectedIndex = index;
		G2_FireEvent(sender, "onchange");
		//dan-el: removed this line - because this method happens asynchronously, followup:
		//window.event.returnValue = false;
		//changed instead of sender.onchange()
		//to support the stupid implementation of validators in asp.net
		//		var dummyEvent = new Object();
		//		dummyEvent.srcElement = sender;
		//		if(sender.Validators!=null)
		//		{
		//			ValidatorOnChange(dummyEvent);
		//		}
		//		G2DropDownList_Changed(sender);
		//reverted back to the old implementation - validators may not work
//TODO: TEST - this condition doesn't work
//		if (sender.onchange)
//		{
//			//HACK - Fix the validators stupid microsoft implementation
//			//they're looking for an event object which doesn't exist right now
//			var s = sender.onchange.toString();
//			if(s.search("(event)")!=-1)
//			{
//				var newFuncString = s.replace("function anonymous()", "var func = function(event)");
//				newFuncString+=";new G2ReturnValue(func);";
//				var result = eval(newFuncString);
//				var dummyEvent = new Object();
//				dummyEvent.srcElement = sender;
//				result.value(dummyEvent);
//			}
//			else
//			{
//				sender.onchange();
//			}
//		}
	}	
	//we always return false - so it's hardcoded somewhere else
	//	return false;
}


//// G2DropDownList functions
//function G2DropDownList_filterListControl(parentId, listControlId)
//{

//  var ddlControl = document.getElementById(listControlId);
//	//  alert("filterListControl: id="+parentId+", control="+listControlId + "items: "+list.options.length);
//	

//  // backup the list, only the first time
//  if (ddlControl.OriginalOptions==null)
//  {
//		ddlControl.OriginalOptions = G2_CopyArray(ddlControl.options);
//		G2DropDownList_GroupOptions(ddlControl);
//	
//  }
//  
//  //Backup the selected valkue
//  var selectedValue = ddlControl.value;


//	//Perform Unfilter if needed  
// 	if(ddlControl.NullValue==parentId)
//	{
//		//optimization - do not clear and refill the combo again
//		if(ddlControl.options.length<ddlControl.OriginalOptions.length)
//		{
//			ddlControl.options.length = 0;
//			for (n=0;n<ddlControl.OriginalOptions.length;n++)
//			{
//				ddlControl.options.add(ddlControl.OriginalOptions[n]);
//			}
//		}
//	}
//	else //Perform filter
//	{
//	  ddlControl.options.length = 0;
//	  var relevantOptions = ddlControl.GroupedOptions.get(parentId);
//	  if(relevantOptions!=null)
//	  {
//			for (n=0;n<relevantOptions.length;n++)
//			{
//				var option = relevantOptions[n];
//				ddlControl.options.add(option);
//				if(option.value==selectedValue)
//					ddlControl.value = selectedValue;
//			}
//		}
//		if(ddlControl.UnGroupedOptions!=null)
//		{
//			for (n=0;n<ddlControl.UnGroupedOptions.length;n++)
//			{
//				var option = ddlControl.UnGroupedOptions[n];
//				ddlControl.options.add(option);
//				if(option.value==selectedValue)
//					ddlControl.value = selectedValue;
//			}
//		}

//  }
//  if(ddlControl.value!=selectedValue)
//  {
//		if(ddlControl.onchange!=null)
//			ddlControl.onchange();
//	}
//}


//// DEPRECATED
//// SoftWeek for listbox/combobox
//function onSelectKeyPress()
//{
//	var now = new Date();
//	if (now.valueOf() > keybdTick.valueOf()+1500 || window.event.srcElement.name != keybdElementName)
//		keybdBuf = "";		
//	keybdTick = now;		
//	keybdElementName = window.event.srcElement.name;
//	var keyCode = parseInt(window.event.keyCode,10);
//	keybdBuf += MakeUpper(String.fromCharCode(keyCode));
//	var index = -1, s;
//	for (var i = 0; i < window.event.srcElement.length; i++) {
//		s = MakeUpper(window.event.srcElement.item(i).text);
//		s = s.substr(0, keybdBuf.length);
//		if (s == keybdBuf) {
//			index = i;
//			break;
//		}
//	}
//	if (index != -1) {
//		window.event.srcElement.selectedIndex = index;
//		window.event.returnValue = false;
//		if (window.event.srcElement.onchange)
//			window.event.srcElement.onchange();
//	}	
//	return false;
//}


////Autocomplete (Taken from Util.js)
//var keybdBuf = "";
//var keybdTick = 0;
//var keybdElementName = "";
//function onSortSelectKeyPress(firstIndex)
//{
//	if(firstIndex==null)
//		firstIndex = 1;
//		
//	var now = new Date();
//	if (now.valueOf() > keybdTick.valueOf()+1500 || window.event.srcElement.name != keybdElementName)
//		keybdBuf = "";		
//	keybdTick = now;		
//	keybdElementName = window.event.srcElement.name;
//	var keyCode = parseInt(window.event.keyCode,10);
//	keybdBuf += MakeUpper(String.fromCharCode(keyCode));
//	var index = -1, s;
//	var lower = firstIndex;
//    var upper = window.event.srcElement.length-1;
//    var middle;
//    while (lower <= upper) {
//        middle = parseInt((lower+upper)/2,10);
//		s = MakeUpper(window.event.srcElement.item(middle).text);
//		s = s.substr(0, keybdBuf.length);
//        if (s == keybdBuf) {
//			index = middle;
//            break;
//        }
//		else if (s < keybdBuf)
//            lower = middle+1;
//        else
//            upper = middle-1;
//	}
//	if (index != -1) {
//		// Find the first occurance of key, in case of duplicate keys
//		var prevIndex = index;
//		index--;
//		while (index >= firstIndex) {
//			s = MakeUpper(window.event.srcElement.item(index).text);
//			s = s.substr(0, keybdBuf.length);
//			if (s == keybdBuf) {
//				prevIndex = index;
//				index--;
//			}
//			else
//				break;
//		}
//		index = prevIndex;
//		window.event.srcElement.selectedIndex = index;
//		window.event.returnValue = false;
//		if (window.event.srcElement.onchange)
//			window.event.srcElement.onchange();
//	}	
//	return false;
//}

function MakeUpper(s)
{
	var outStr, c;
	outStr = "";
	for (var i = 0; i < s.length; i++) {
		c = s.charCodeAt(i);
		if (c >= 97 && c <= 122)
			c -= 32;
		outStr += String.fromCharCode(c);
	}
	return outStr;
}


function G2Expander_Init(controlId)
{
	//Required for FF Compatibility
	var control = document.getElementById(controlId);
	if (!control)
	{
		G2_Warn("G2Expander_Init","control "+controlId+" was not found!");
		return;
	}
	G2DOM.G2TransferAttributes(control);
	var func = function(e)
	{
		G2Expander_OnClick(control, e);
	};
	G2_AttachEvent(control, "onclick", func);
	G2_AttachEvent(control, "ondblclick", func);
}

function G2Expander_OnClick(sender, e)
{
	G2Event.stop(e);
	G2DOM.G2TransferAttributes(sender); //For FF
	if(sender.isDisabled)
		return;
	if(sender.targetislazy=="true")
	{
		sender.targetislazy="false";
		__doPostBack(sender, "WakeUpLazyTarget", true);
	}
	else
	{
	
		if(sender.allowclose=="false")
			G2Expander_ShowHideControl(sender.targetid, sender.stateid, sender.id, true);
		else
			G2Expander_ToggleControl(sender.targetid, sender.stateid, sender.id);
	}
}

//G2Expander functions

function G2Expander_ShowHideControl(controlId, stateControlID, expanderID, show)
{     
  var control = document.getElementById(controlId);
  var stateControl = document.getElementById(stateControlID);
  var expander = document.getElementById(expanderID);
  stateControl.value = G2_ShowHideControl(control, show).toString();
  
  var newHtml = "";
  //Handle image
  var expanderChildren = expander.children;
  if(expanderChildren.length>0)
  {
    if(show)
      expanderChildren[0].src = expander.g2expandedimageurl;
    else
      expanderChildren[0].src = expander.g2imageurl;
    
    //newHtml+=expanderChildren[0].outerHTML;
  }
  
  if(show)
    newHtml+=expander.g2expandedtext;
  else
    newHtml+=expander.g2text;
    
	var txtNode = G2_FindNodeByNameValue(expander, "nodeType", 3);
	if(txtNode!=null)
	{
		txtNode.nodeValue = newHtml;
  }
    
  //expander.innerHTML = newHtml;
	var element = expander;
	if(show && expander.onexpanded!=null)
  {
			eval(expander.onexpanded);
	}
	else if(!show && expander.oncollapsed!=null)
  {
			eval(expander.oncollapsed);
	}
	
	if(show && control.onexpanded!=null)
  {
			eval(control.onexpanded);
	}
	else if(!show && control.oncollapsed!=null)
  {		
			eval(control.oncollapsed);
	}
}

function G2Expander_ToggleControl(controlId, stateControlID, expanderID)
{
  var stateControl = document.getElementById(stateControlID);
  
  if(stateControl.value == "false")
  {
    G2Expander_ShowHideControl(controlId, stateControlID, expanderID, true);
  }
  else
  {
		G2Expander_ShowHideControl(controlId, stateControlID, expanderID, false);
  }
}

function G2_ShowHideElementById(elementId, show)
{
  var element = document.getElementById(elementId);
  if(element!=null)
  {
		G2_ShowHideControl(element, show).toString();
  }
}


function G2Expander_ToggleElementVisibilityById(elementId)
{
	var element = $(elementId);
	if(element!=null)
		G2_ToggleElementVisibility(element);
}

function G2Expander_ToggleElementVisibility(targetElementId)
{
	var targetElement = $targetElementId;
	if(targetElement!=null)
		G2_ToggleElementVisibility(targetElement);
}

function G2ExpanderHelper_ToggleControl(controlId, stateControlID)
{
  var control = document.getElementById(controlId);
  var stateControl = document.getElementById(stateControlID);
  
  if(stateControl.value == "false")
  {
    stateControl.value = G2_ShowControl(control);
  }
  else
  {
    stateControl.value = G2_HideControl(control);
  }
}

function G2CheckBoxExpander_ToggleControl(e, controlId, stateControlID)
{
	var sender = G2Event.element(e);
	if (sender==null || sender.nodeType!=1 || sender.tagName.toLowerCase()!="input")
		return;
	G2ExpanderHelper_ToggleControl(controlId, stateControlID);
}

//selects all the visible 
function G2ExtendedCheckBoxList_SelectAllVisibleLookups(senderid)
{
	var sender = document.getElementById(senderid);
	if(sender==null)
		return;//TODO: warn
	G2_PerformRecursiveActionOnElement(sender, G2ExtendedCheckBoxList_RecursiveCheck, {checked:true});
}

function G2ExtendedCheckBoxList_RecursiveCheck(element, context)
{
	if(element.type=="checkbox")
	{
		element.checked = context.checked;
	}
}

//select none of the visible lookups
function G2ExtendedCheckBoxList_SelectNoneVisibleLookups(senderid)
{
	var sender = document.getElementById(senderid);
	if(sender==null)
		return;//TODO: warn
	G2_PerformRecursiveActionOnElement(sender, G2ExtendedCheckBoxList_RecursiveCheck, {checked:false});
}


G2ExpanderGroupManager = 
{
  groups : [],
  
  getGroup : function(groupname)
  {
    return this.groups[groupname];
  },
  addToGroup : function(groupname, expander)
  {
    if(this.groups[groupname]==null)
    {
      this.groups[groupname] = new Array();
    }
    var group = this.groups[groupname];
    group.push(expander);
    
    //Show first in group, hide the rest
    if(group.length==1)
      G2ExternalExpander_SetExpanded(expander, true, false);
    else
      G2ExternalExpander_SetExpanded(expander, false, false);
  }
};

function G2ExternalExpander_Init(id)
{
	var expander = document.getElementById(id);
	if(expander==null)
		return;
	G2DOM.G2TransferAttributes(expander);
	expander.targetcontrol = document.getElementById(expander.targetcontrolid);
	expander.expandedcontrol = document.getElementById(expander.expandedcontrolid);
	expander.collapsedcontrol = document.getElementById(expander.collapsedcontrolid);	
	G2_AttachEvent(expander.expandedcontrol, "onclick", 
		function(e)
		{
			G2ExternalExpander_Toggle(expander, e);
		});
		
	G2_AttachEvent(expander.collapsedcontrol, "onclick", 
		function(e)
		{
			G2ExternalExpander_Toggle(expander, e);
		});
  
  if(expander.groupname!=null)
    G2ExpanderGroupManager.addToGroup(expander.groupname, expander);
}

function G2ExternalExpander_Toggle(expander)
{
	// notify changes
	G2.notifyInputChanged(expander);
	if(expander.targetislazy=="true")
	{
		expander.targetislazy="false";
		__doPostBack(expander, "WakeUpLazyTarget", true);
	}
	else
	{
		var expanded = G2ExternalExpander_GetExpanded(expander);
		G2ExternalExpander_SetExpanded(expander, !expanded)
	}
}

function G2ExternalExpander_GetExpanded(expander)
{
	return expander.value=="true";
}

function G2ExternalExpander_SetExpanded(expander, value, affectGroup)
{
  if(expander.groupname!=null && value && (affectGroup!=false))
  {
   var group = G2ExpanderGroupManager.getGroup(expander.groupname);
   for(var i =0; i<group.length; i++)
   {
     var exp = group[i];
     if(exp==expander)
       continue;
     G2ExternalExpander_SetExpanded(exp, false, false);
   }
  }
   
	if(value)
	{
		expander.value="true";
		G2_ShowControl(expander.targetcontrol);
		G2_ShowControl(expander.expandedcontrol);
		G2_HideControl(expander.collapsedcontrol);
	}
	else
	{
		expander.value="false";
		G2_HideControl(expander.targetcontrol);
		G2_HideControl(expander.expandedcontrol);
		G2_ShowControl(expander.collapsedcontrol);
	}
}


function G2ClientExpander_OnClick(exp, e)
{
	if(exp.elementCache==null)
	{
		exp.elementCache = {};
		exp.expanded = true;
		exp.visibilityClientElementsIds = exp.visiblityclientids.split(",");
		exp.displayClientElementsIds = exp.displayclientids.split(",");
	}
	var show = !exp.expanded;
	exp.src = show ? exp.expandedimagesrc : exp.collapsedimagesrc;
	var display = show ? "" : "none";	
	var border = show ? "true" : "false";	
	
	//build mutual reference between the expander and its parent row
	if (exp.ParentTr == null)
	{
		exp.ParentTr = findControl(exp, "TemplateRow");
		exp.ParentTr.Expander = exp;
	}
		
	G2ClientExpander_SetStyleProperty(exp, exp.displayClientElementsIds, "display", display);	
	G2ClientExpander_SetStyleProperty(exp, exp.visibilityClientElementsIds, "border", border);		
	exp.expanded = show;
}

/*there are 2 cases for this expander:
	1.list of id's to display or hide.
	2.list of id's to show their border or not.
		for these id's we save their border style on a backup variable that holds element.style.cssText information
		in case the element has left border style and bottom border style(a node in the diagram) we hide only
		the bottom border
	special case:
	when opening an expander that has child expander that is closed(expanded = false),
	we have to change visibilty of child expander visibilityClientElementsIds, open the expander and switch
	its image (all the child expanders should be open)  */
function G2ClientExpander_SetStyleProperty(exp, idList, propertyName, value)
{
	var cache = exp.elementCache;
	for(var i=0;i<idList.length;i++)
	{
		var id = idList[i];
		var element = cache[id];
		if(element===undefined)
		{
			element = document.getElementById(id);
			cache[id] = element;
		}
		if(element!=null)
		{		
			if(propertyName == "display")
			{
				element.style[propertyName] = value;
				if (value=="" && element.Expander != null && !element.Expander.expanded)
				{
					G2ClientExpander_SetStyleProperty(element.Exp