﻿/*
	Net functions and classes.
	Dependencies: ??
*/
Util.ensureNamespacePath("Net");
/*=======================================================================*/

	Net.READY_STATE_UNINITIALIZED = 0;
	Net.READY_STATE_LOADING = 1;
	Net.READY_STATE_LOADED = 2;
	Net.READY_STATE_INTERACTIVE = 3;
	Net.READY_STATE_COMPLETE = 4;
	
/*=======================================================================*/
	
	Net.getXMLHttpRequest = function() {
		if (window.XMLHttpRequest) {
			return new XMLHttpRequest();
		}
		else if (window.ActiveXObject) {
			return new ActiveXObject("Microsoft.XMLHTTP");
		}
		
		return null;
	}
	
/*=======================================================================*/
/*
	constructor:
	aListener is either a function, in which case the context on load is this, or
	 an object with:
		* mSrcObj, mOnload, mOnerror (JSON: {mSrcObj:[srcobj], [mFunction]:[function], ...}
*/
	Net.cContentLoader = function(aURL, aListener, aOnerror) {
		this.mURL = aURL;
		this.mRequest = null;

		if (aListener.mSrcObj) {
			this.mSrcObj = aListener.mSrcObj;
			this.mOnload = aListener.mOnload;
			this.mOnerror = aListener.mOnerror;
		}
		else {
			this.mOnload = aListener;
			this.mOnerror = aOnerror;
		}
		
		this.mMethod = "GET";
		this.mDataToSend = null;
		this.mAsync = true;
		//auto load?
	}

/*=======================================================================*/

	Net.cContentLoader.prototype.loadData = function() {
		this.mRequest = Net.getXMLHttpRequest();
		if (this.mRequest == null) {
			return;
		}
		
		try {
			//a trick to be sure onReadyStateChange is called w/ this as context:
			var aThis = this;
			if (this.mAsync) {
				this.mRequest.onreadystatechange=function() {
					aThis.onReadyStateChange.call(aThis);
				}
			}
			this.mRequest.open(this.mMethod, this.mURL, this.mAsync);
			this.mRequest.send(this.mDataToSend);
			
			if (!this.mAsync) {
				this.onReadyStateChange();
			}
		}
		catch (aErr) {
			this.defaultError(aErr);
		}
	}
	
/*-----------------------------------------------------------------------*/

	Net.cContentLoader.prototype.onReadyStateChange = function() {
		var aReadyState = this.mRequest.readyState;
		
		if (aReadyState == Net.READY_STATE_COMPLETE) {
			var aHTTPStatus = this.mRequest.status;
			if (aHTTPStatus == 200 || aHTTPStatus == 0) {
				if (this.mSrcObj)
					this.mOnload.call(this.mSrcObj, this);
				else
					this.mOnload();
			}
			else {
				this.defaultError();
			}
		}
	}
	
/*-----------------------------------------------------------------------*/
/*
	aErr is optional
*/
	Net.cContentLoader.prototype.defaultError = function(aErr) {
		if (this.mOnerror) {
			if (this.mSrcObj)
				this.mOnerror.call(this.mSrcObj, aErr);
			else
				this.mOnerror(aErr);
			return;
		}
		
		if (aErr)
			alert("Error loading data (aErr):" + aErr);
		else
			alert("Error loading data: " +
					"\n\nreadyState: " + this.mRequest.readyState +
					"\nstatus: " + this.mRequest.status +
					"\nheaders: " + this.mRequest.getAllResponseHeaders());
	}
	
/*=======================================================================*/
/*
	Static method
*/
	Net.cContentLoader.addImage = function(aParEle, aSrc) {
		var aImage = document.createElement("img");
		if (aSrc.indexOf("/") == -1)
			aSrc = "../wwwLibs/Util_Web/Images/" + aSrc;
		aImage.border = "0";
		aImage.src = aSrc;
		aParEle.appendChild(aImage);
	}
	
/*-----------------------------------------------------------------------*/
/*
	Static method
	* Requires jQuery!
*/
	Net.cContentLoader.removeImage = function(aRefEle, aImgName, aGetParFlag) {
		if (aImgName.lastIndexOf("/") != -1)
			aImgName = aImgName.substr(aImgName.lastIndexOf("/")+1);
		if (aGetParFlag)
			aRefEle = $(aRefEle).parent()[0];
		if (aRefEle) {
			var aImg = $(aRefEle).find("img[src$='" + aImgName + "']")[0];
			if (aImg)
				aImg.parentNode.removeChild(aImg);
		}
	}
	
/*-----------------------------------------------------------------------*/
/*
	Static method
	* Requires jQuery!
	Inserts a span w/ the image specified as an immediate previous sibling of aRefEle
*/
	Net.cContentLoader.toggleElement = function(aRefEle, aImgName) {
		if ($(aRefEle).css("display") != "none") {
			//aRefEle is visible, add image and hide aRefEle
			var aSpan = $(aRefEle).before("<span></span>").prev()[0];
			Net.cContentLoader.addImage(aSpan,
					(aImgName == null || aImgName == "") ? "activityloader.gif" : aImgName);
			$(aRefEle).css("display", "none");
		}
		else {
			$(aRefEle).prev().remove();
			$(aRefEle).css("display", "inline");
		}
	}
	
/*-----------------------------------------------------------------------*/
/*
	Static method
	* Requires jQuery!
	Assumes aRootEle contains a single table.
	Toggles any rows with class aStatusRowClass/and all other rows
		- aStatusRowClass default: "id_ToggleLoadingStatusRow"
*/
	Net.cContentLoader.toggleTableRowsLoading = function(aRootEle, aStatusRowClass, aImageName) {
		if (!aRootEle)
			return;
		if (!aStatusRowClass)
			aStatusRowClass = "id_ToggleLoadingStatusRow";
		if (!aImageName)
			aImageName = "activityloader.gif";

		var aTbl = null;
		var aTRjq = $(aRootEle).find("tr." + aStatusRowClass);
		if (aTRjq.length > 0)
			aTbl = $(aTRjq[0]).closest("table");
		if (aTRjq.length > 0 && $(aTRjq[0]).css("display") == "none") {
			//toggle other rows hide, display status
			$(aTbl).find(">tbody>tr").css("display", "none");
			Net.cContentLoader.addImage(aTRjq[0].cells[0], aImageName);
			$(aTRjq[0]).css("display", "");
		}
		else {
			//toggle status hide, display others
			$(aTRjq[0]).css("display", "none");
			Net.cContentLoader.removeImage(aTRjq[0].cells[0], aImageName);
			//either works:
			$(aTbl).find("tbody>tr").not($(aTRjq[0])).css("display", "");
			//$(aRootEle).find("table.id_OutputTbl>tbody>tr").not($(aTRjq[0])).css("display", "");
			//$(aRootEle).find("table.id_OutputTbl>tbody>tr:not(table.id_OutputTbl>tbody>tr." + aStatusRowClass +")").css("display", "");
		}
	}

/*=======================================================================*/
//end Net.cContentLoader class
/*=======================================================================*/
//Namespace: Net

