/* ********************* */
if(!window.AddNamespace) {
	window.AddNamespace = function( ns ) 	{
		var nsParts = ns.split(".");
		var root = window;
		for( var i = 0; i < nsParts.length; i++ ) 		{
			if( typeof root[ nsParts[ i ] ] == 'undefined' ) {
				root[ nsParts[ i ] ] = new Object();
			}
			root = root[ nsParts[ i ] ];
		}
	}
}

// JavaScript objects wrappers
JSONObject = function( obj ) {
	this.obj = obj;
	this.toJSON = function() {
		if ( this.obj == null ) {
			return 'null';
		}
	//	debugger
		switch(this.obj.constructor) {
			case Array: return ArrayToJSON( this.obj ); break;
			case String: return StringToJSON( this.obj ); break;
			case Date: return DateToJSON( this.obj ); break;
			case Object: return ObjectToJSON( this.obj ); break;
			case Number:
			case Boolean: return String( this.obj ); break;
		}
	}
	
	function ObjectToJSON( obj ) {
		var v=[];
		for( attr in obj ) 	{
			if( typeof obj[ attr ] != "function" ) {
				var attribute = new JSONObject( obj[attr] );
				v.push('"' + attr + '": ' + ( obj[attr] != null ? attribute.toJSON() : 'null' ) );
			}
		}
		if( v.length > 0 ) {
			return "{" + v.join(", ") + "}";
		} else {
			return "{}";
		}
	
	}
	
	function StringToJSON( obj ) {
		var s = obj; // .encodeURI();
		s = '"' + s.replace(/(["\\])/g, '\\$1') + '"';
		s = s.replace(/\n/g,"\\n");
		s = s.replace(/\r/g,"\\r");
		s = s.replace(/\t/g,"\\t");
		return s;	
	}
	
	function DateToJSON( obj ) {
		var o = new Object();
		o.__type = "System.DateTime";
		o.Year = obj.getUTCFullYear();
		o.Month = obj.getUTCMonth() + 1;
		o.Day = obj.getUTCDate();
		o.Hour = obj.getUTCHours();
		o.Minute = obj.getUTCMinutes();
		o.Second = obj.getUTCSeconds();
		o.Millisecond = obj.getUTCMilliseconds();
		o.TimezoneOffset = obj.getTimezoneOffset();
		return new JSONObject( o ).toJSON();
	}
	
	function ArrayToJSON( obj ) {
		var v = [];

		for( var i = 0; i < obj.length; i++ ) {
			var elem = new JSONObject( obj[ i ] );
			v[v.length] = obj[ i ] != null ? elem.toJSON() : 'null';
		}
		return "[" + v.join(", ") + "]";
	}
}


JSONArray = function() {
	this.inherits = Array;
	this.inherits();
	
	this.push = function( o ) 	{
		this[ this.length ] = o;
	}
	
	this.getLast = function() 	{
		if( this.length == 0 ) {
			return null;
		}
		return this[ this.length -1 ];
	}
	
	this.getFirst = function() {
		if( this.length == 0 ) {
			return null;
		}
		return this[ 0 ];
	}
}


// .NET wrapper objects
AddNamespace( "System.Data" );

System.Data.DataSet = function( name ) {
	this.__type = "System.Data.DataSet, System.Data, Version=1.0.5000.0, Culture=neutral, PublicKeyToken=b77a5c561934e089";
	this.Name = name != null ? name : "";
	this.Tables = [];
}

System.Data.DataTable = function( name ) {
	this.__type = "System.Data.DataTable, System.Data, Version=1.0.5000.0, Culture=neutral, PublicKeyToken=b77a5c561934e089";
	this.Name = name != null ? name : "";
	this.Columns = [];
	this.Rows = [];
	
	this.addColumn = function( name, type ) {
		var c = new Object();
		c.Name = name;
		c.__type = type;
		this.Columns.push( c );
	}
}

// Browser related members
AddNamespace("MS.Browser" );

MS.Browser.isIE = (window.navigator.appName.toLowerCase().indexOf('explorer') != -1 || window.navigator.appName.toLowerCase().indexOf('msie') != -1 );
MS.Browser.isChrome = (window.navigator.appName.toLowerCase().indexOf('chrome') != -1 );

// Debug
AddNamespace( "MS.Debug" );

MS.Debug.enabled = false;
MS.Debug.trace = function(s) {}

AddNamespace( "SNAJAX" );

var ___tracerAvailable = -1;
SNAJAX.Trace = function( msg ) { return; } 
SNAJAX.LastRequestID = 0;

SNAJAX.NewRequestID = function() {
	return ++SNAJAX.LastRequestID;
}

SNAJAX.RequestCache = new Array();
SNAJAX.GetXmlRequestObject = function () {
	var xml = null
	var len = SNAJAX.RequestCache.length;
	for( var i = 0; i < len; i++ ) {
		if ( SNAJAX.RequestCache[i].readyState == 4 ) {
			SNAJAX.RequestCache[i].abort();
			SNAJAX.Trace( "SNAJAX RequestCache: Hit" );
			return SNAJAX.RequestCache[i];
		}
	}	
	
	if( ! window.XMLHttpRequest ) {
		try { 
			xml = new ActiveXObject( "Msxml2.XMLHTTP.4.0" ); 
		} catch( ex ) { xml = null; }
		try { 
			xml = new ActiveXObject( "MSXML2.XMLHTTP" ); 
		} catch( ex ){ xml = null; }
		try { 
			xml = new ActiveXObject( "Microsoft.XMLHTTP" ); 
		} catch( ex ){ xml = null; }
	} else {
		xml = new XMLHttpRequest();
	}
	
	if ( xml == null ) {
		alert("Fatal ERROR: Could not initialise an XMLHttpReuqest object");
		return
	}
	SNAJAX.RequestCache[SNAJAX.RequestCache.length] = xml;
	SNAJAX.Trace( "SNAJAX RequestCache: Created new request object" );
	SNAJAX.Trace( "SNAJAX RequestCache: Using " + SNAJAX.RequestCache.length + " requests" );
	return xml;
}

SNAJAX.PendingRequestCount = 0;
SNAJAX.RequestStarted = function() {
	SNAJAX.PendingRequestCount++;
	SNAJAX.CheckLoading();
}
SNAJAX.RequestFinished = function() {
	SNAJAX.PendingRequestCount--;
	SNAJAX.CheckLoading();
}
SNAJAX.CheckLoading = function() {
	if ( SNAJAX.PendingReuqestCount > 0 ) {
		if ( typeof( SNAJAX.ShowLoading ) == 'function' ) {
			SNAJAX.ShowLoading();
		}
	} else {
		if ( typeof( SNAJAX.HideLoading ) == 'function' ) {
			SNAJAX.HideLoading();
		}
	}
}
SNAJAX.ShowLoading = null;
SNAJAX.HideLoading = null;

SNAJAX.NoOperation = function() {}
SNAJAX.cryptProvider = null;
SNAJAX.token = "";
SNAJAX.Invoke = function(m, args, c, url) {
    if (typeof (url) == 'undefined') { alert('Url is invalid for the current request.'); return; }
    
    var xml = SNAJAX.GetXmlRequestObject();
    var requestData = new Object();
    requestData.method = m;
    requestData.args = args;
    requestData.callback = c[1].length > c[0] ? c[1][c[0]] : SNAJAX.NoOperation;
    requestData.context = c[1].length > c[0] + 1 ? c[1][c[0] + 1] : null;
    requestData.session = c[2];
    var data = "";
    var async = typeof requestData.callback == "function" && requestData.callback != SNAJAX.NoOperation;
    var requestID = SNAJAX.NewRequestID();

    SNAJAX.Trace("SNAJAX Request: " + requestID + " Invoke");

    for (attr in requestData.args) {
        if (typeof requestData.args[attr] != "function") {
            var attribute = new JSONObject(requestData.args[attr]);
            data += attr + "=" + (requestData.args[attr] != null ? attribute.toJSON() : 'null') + "\r\n";
        }
    }

    if (MS.Debug.enabled) {
        MS.Debug.trace("JSON string: " + data);
    }

    if (async) {
        xml.onreadystatechange = stateChanged;
    }
    var dataLength = 0;
    if (data.length != 0) {
        dataLength = data.length;
    } else {
        data = new Date().getTime();
        dataLength = String(new Date().getTime()).length;
    }

    xml.open("POST", url, async);
    xml.setRequestHeader("Content-type", "application/x-www-form-urlencoded");
    xml.setRequestHeader("Content-length", dataLength);
    xml.setRequestHeader("Ajax-method", requestData.method);
    xml.setRequestHeader("Ajax-session", requestData.session);
    // xml.setRequestHeader( "Ajax-token", SNAJAX.token );

    if (MS.Browser.isIE) {
        xml.setRequestHeader("Accept-Encoding", "gzip, deflate");
    } else if (!MS.Browser.isChrome) {
        xml.setRequestHeader("Connection", "close"); 	// Mozilla Bug #246651
    }

    if (SNAJAX.cryptProvider != null) {
        data = SNAJAX.cryptProvider.encrypt(data);
    }
    if (MS.Debug.enabled) {
        MS.Debug.trace("XMLHttpRequest: " + url + "\r\n  Method: " + requestData.method + "\r\n  Data: " + data);
    }
    SNAJAX.RequestStarted();

    try {
        xml.send(data);
        if (!async) {
            return createResponse();
        }
    } catch (e) {
        if (MS.Debug.enabled) {
            MS.Debug.trace("Send errored.");
        }
    }
    return true;


    function stateChanged() {
        if (typeof (SNAJAX) == 'undefined') return;
        if (!xml) {
            SNAJAX.RequestFinished();
            return;
        }

        // SNAJAX.Trace( "SNAJAX.Invoke: stateChanged()" );
        /*
        if ( xml.readyState == 1 ) { req.onLoadingInternal(req); }
        if ( xml.readyState == 2 ) { req.onLoadedInternal(req); }
        if ( xml.readyState == 3 ) { req.onInteractiveInternal(req); }
        */
        if (xml.readyState == 4) { doCallback(); }
    }

    function doCallback() {
        if (typeof (SNAJAX) == 'undefined') return;
        SNAJAX.Trace("SNAJAX Request: " + requestID + " doCallback()");

        if (xml.readyState != 4) {
            return;
        }

        if (typeof (xml.status) == 'undefined') {
            alert('xml.status == undefined');
            return;
        }

        if (xml.status == 200) {
            requestData.callback(createResponse());
        }
        xml = null; //TV-25.01.2006
    }

    function OnTimeout() {
        if (typeof (SNAJAX) == 'undefined') return;
        SNAJAX.Trace("SNAJAX.Invoke: OnTimeout()");
        if (typeof (SNAJAX.TimeOut) == 'function') {
            SNAJAX.TimeOut();
        }
    }

    function createResponse() {
        var responseData = new Object();
        responseData.url = url;
        responseData.error = null;
        responseData.request = requestData;
        responseData.value = null;
        responseData.responseText = xml.responseText;

        if (MS.Debug.enabled) {
            MS.Debug.trace("XMLHttpResponse: " + url + "\r\n  Method: " + requestData.method + "\r\n  Response: " + responseData.responseText);
        }
        if (SNAJAX.cryptProvider != null) {
            responseData.responseText = SNAJAX.cryptProvider.decrypt(responseData.responseText);
        }
        if (MS.Debug.enabled) {
            MS.Debug.trace("JSON string: " + responseData.responseText);
        }

        //alert( responseData.responseText );
        try {
            eval("responseData.value = " + responseData.responseText + ";");
        } catch (e) {
            //TODO:
        }

        SNAJAX.RequestFinished();
        return responseData;
    }
}

