// ===================================================================
// Author: Matt Kruse <matt@ajaxtoolbox.com>
// WWW: http://www.AjaxToolbox.com/
//
// NOTICE: You may use this code for any purpose, commercial or
// private, without any further permission from the author. You may
// remove this notice from your final code if you wish, however it is
// appreciated by the author if at least my web site address is kept.
//
// You may *NOT* re-distribute this code in any way except through its
// use. That means, you can include it in your product, or your web
// site, or any other form where the code is actually being used. You
// may not put the plain javascript up on your site for download or
// include it in your javascript libraries for download. 
// If you wish to share this code with others, please just point them
// to the URL instead.
// Please DO NOT link directly to my .js files from your site. Copy
// the files to your server and use them there. Thank you.
// ===================================================================

function AjaxRequest(){
	var req =new Object();
	req.timeout =null;
	req.generateUniqueUrl =false;
	req.url =window.location.href;
	req.method ="GET";
	req.async =true;
	req.username =null;
	req.password =null;
	req.parameters =new Object();
	req.requestIndex =AjaxRequest.numAjaxRequests++;
	req.responseReceived =false;
	req.groupName =null;
	req.queryString ="";
	req.responseText =null;
	req.responseXML =null;
	req.status =null;
	req.statusText =null;
	req.aborted =false;
	req.xmlHttpRequest =null;
	req.onTimeout=null;
	req.onLoading=null;
	req.onLoaded=null;
	req.onInteractive=null;
	req.onComplete=null;
	req.onSuccess=null;
	req.onError=null;
	req.onGroupBegin=null;
	req.onGroupEnd=null;
	req.xmlHttpRequest =AjaxRequest.getXmlHttpRequest();
	if(req.xmlHttpRequest==null){return null;}

	req.xmlHttpRequest.onreadystatechange = function(){
		if(req==null || req.xmlHttpRequest==null){return;}
		if(req.xmlHttpRequest.readyState==1){
			req.onLoadingInternal(req);
		}
		if(req.xmlHttpRequest.readyState==2){
			req.onLoadedInternal(req);
		}
		if(req.xmlHttpRequest.readyState==3){
			req.onInteractiveInternal(req);
		}
		if(req.xmlHttpRequest.readyState==4){
			req.onCompleteInternal(req);
		}
	};
	req.onLoadingInternalHandled=false;
	req.onLoadedInternalHandled=false;
	req.onInteractiveInternalHandled=false;
	req.onCompleteInternalHandled=false;
	req.onLoadingInternal=function(){
		if(req.onLoadingInternalHandled){return;}
		AjaxRequest.numActiveAjaxRequests++;
		if(AjaxRequest.numActiveAjaxRequests==1 && typeof(window['AjaxRequestBegin'])=="function"){
			AjaxRequestBegin();
		}
		if(req.groupName!=null){
			if(typeof(AjaxRequest.numActiveAjaxGroupRequests[req.groupName])=="undefined"){
				AjaxRequest.numActiveAjaxGroupRequests[req.groupName] =0;
			}
			AjaxRequest.numActiveAjaxGroupRequests[req.groupName]++;
			if(AjaxRequest.numActiveAjaxGroupRequests[req.groupName]==1 && typeof(req.onGroupBegin)=="function"){
				req.onGroupBegin(req.groupName);
			}
		}
		if(typeof(req.onLoading)=="function"){req.onLoading(req);}
		req.onLoadingInternalHandled=true;
	};
	req.onLoadedInternal=function(){
		if(req.onLoadedInternalHandled){return;}
		if(typeof(req.onLoaded)=="function"){req.onLoaded(req);}
		req.onLoadedInternalHandled=true;
	};
	req.onInteractiveInternal=function(){
		if(req.onInteractiveInternalHandled){return;}
		if(typeof(req.onInteractive)=="function"){req.onInteractive(req);}
		req.onInteractiveInternalHandled=true;
	};
	req.onCompleteInternal=function(){
		if(req.onCompleteInternalHandled || req.aborted){return;}
		req.onCompleteInternalHandled=true;
		AjaxRequest.numActiveAjaxRequests--;
		if(AjaxRequest.numActiveAjaxRequests==0 && typeof(window['AjaxRequestEnd'])=="function"){AjaxRequestEnd(req.groupName);}
		if(req.groupName!=null){
			AjaxRequest.numActiveAjaxGroupRequests[req.groupName]--;
			if(AjaxRequest.numActiveAjaxGroupRequests[req.groupName]==0 && typeof(req.onGroupEnd)=="function"){req.onGroupEnd(req.groupName);}
		}
		req.responseReceived =true;
		req.status =req.xmlHttpRequest.status;
		req.statusText =req.xmlHttpRequest.statusText;
		req.responseText =req.xmlHttpRequest.responseText;
		req.responseXML =req.xmlHttpRequest.responseXML;
		if(typeof(req.onComplete)=="function"){req.onComplete(req);}
		if(req.xmlHttpRequest.status==200 && typeof(req.onSuccess)=="function"){req.onSuccess(req);}
		else if(typeof(req.onError)=="function"){req.onError(req);}
		delete req.xmlHttpRequest['onreadystatechange'];
		req.xmlHttpRequest =null;
	};
	req.onTimeoutInternal=function(){if(req!=null && req.xmlHttpRequest!=null && !req.onCompleteInternalHandled){req.aborted =true;
	req.xmlHttpRequest.abort();
		AjaxRequest.numActiveAjaxRequests--;
		if(AjaxRequest.numActiveAjaxRequests==0 && typeof(window['AjaxRequestEnd'])=="function"){AjaxRequestEnd(req.groupName);}if(req.groupName!=null){AjaxRequest.numActiveAjaxGroupRequests[req.groupName]--;
		if(AjaxRequest.numActiveAjaxGroupRequests[req.groupName]==0 && typeof(req.onGroupEnd)=="function"){req.onGroupEnd(req.groupName);}}if(typeof(req.onTimeout)=="function"){req.onTimeout(req);}delete req.xmlHttpRequest['onreadystatechange'];
		req.xmlHttpRequest =null;}
	};
	req.process=function(){
		if(req.xmlHttpRequest!=null){
			if(req.generateUniqueUrl && req.method=="GET"){req.parameters["AjaxRequestUniqueId"] =new Date().getTime() + "" + req.requestIndex;}
			var content =null;
			for(var i in req.parameters){
				if(req.queryString.length>0){	req.queryString +="&";	}
					req.queryString +=encodeURIComponent(i) + "=" + encodeURIComponent(req.parameters[i]);
				}
				if(req.method=="GET"){
					if(req.queryString.length>0){req.url +=((req.url.indexOf("?")>-1)?"&":"?") + req.queryString;
				}
			}
			req.xmlHttpRequest.open(req.method,req.url,req.async,req.username,req.password);
			if(req.method=="POST"){
				if(typeof(req.xmlHttpRequest.setRequestHeader)!="undefined"){req.xmlHttpRequest.setRequestHeader('Content-type', 'application/x-www-form-urlencoded');}content =req.queryString;
			}
			if(req.timeout>0){setTimeout(req.onTimeoutInternal,req.timeout);}
			req.xmlHttpRequest.send(content);
		}
	};
	req.handleArguments=function(args){
		for(var i in args){
			if(typeof(req[i])=="undefined"){req.parameters[i] =args[i];}
			else{req[i] =args[i];}
		}
	};
	req.getAllResponseHeaders =function(){
		if(req.xmlHttpRequest!=null){if(req.responseReceived){return req.xmlHttpRequest.getAllResponseHeaders();}alert("Cannot getAllResponseHeaders because a response has not yet been received");}
	};
	req.getResponseHeader =function(headerName){
		if(req.xmlHttpRequest!=null){if(req.responseReceived){return req.xmlHttpRequest.getResponseHeader(headerName);}alert("Cannot getResponseHeader because a response has not yet been received");}
	};
	return req;
}
AjaxRequest.getXmlHttpRequest =function(){
	if(window.XMLHttpRequest){
		return new XMLHttpRequest();}else if(window.ActiveXObject){/*@cc_on @*/
		/*@if(@_jscript_version >=5)
		try{return new ActiveXObject("Msxml2.XMLHTTP");}catch(e){try{return new ActiveXObject("Microsoft.XMLHTTP");}catch(E){return null;}}@end @*/
	}else{return null;}
};
AjaxRequest.isActive =function(){return(AjaxRequest.numActiveAjaxRequests>0);};
AjaxRequest.get =function(args){AjaxRequest.doRequest("GET",args);};
AjaxRequest.post =function(args){AjaxRequest.doRequest("POST",args);};
AjaxRequest.doRequest =function(method,args){
	if(typeof(args)!="undefined" && args!=null){
		var myRequest =new AjaxRequest();
		myRequest.method =method;
		myRequest.handleArguments(args);
		myRequest.process();
	}
};
AjaxRequest.submit =function(theform, args){
	var myRequest =new AjaxRequest();
	if(myRequest==null){return false;}var serializedForm =AjaxRequest.serializeForm(theform);
	myRequest.method =theform.method.toUpperCase();
	myRequest.url =theform.action;
	myRequest.handleArguments(args);
	myRequest.queryString =serializedForm;
	myRequest.process();
	return true;
};
AjaxRequest.serializeForm =function(theform){
	var els =theform.elements;
	var len =els.length;
	var queryString ="";
	this.addField =	function(name,value){if(queryString.length>0){queryString +="&";}queryString +=encodeURIComponent(name) + "=" + encodeURIComponent(value);};
	for(var i=0;i<len;i++){var el =els[i];
		if(!el.disabled){
		switch(el.type){
			case 'text': 
			case 'password': 
			case 'hidden': 
			case 'textarea':
				this.addField(el.name,el.value);
				break;
			case 'select-one':
				if(el.selectedIndex>=0){this.addField(el.name,el.options[el.selectedIndex].value);}break;
			case 'select-multiple':
				for(var j=0;j<el.options.length;j++){if(el.options[j].selected){this.addField(el.name,el.options[j].value);}}break;
			case 'checkbox': case 'radio':
				if(el.checked){this.addField(el.name,el.value);}break;}
		}
	}
	return queryString;
};
AjaxRequest.numActiveAjaxRequests =0;
AjaxRequest.numActiveAjaxGroupRequests =new Object();
AjaxRequest.numAjaxRequests =0;


