 var Class = {
   create: function() {
     return function() {
       if (this.initialize) {
    	   var cmd = 'this.initialize(';
    	   if (arguments.length > 0){
	    	   var args = [];
	    	   for( var i = 0; i < arguments.length; i++ ) args.push("'" + arguments[i] + "'");
	   		   cmd += args.join(',');
    	   }
    	   cmd += ');';
    	   eval(cmd);
       }
     }
   }
 }
var AjaxDispatcher = {
	busy: false,
	queue: new Array(0),
	addWaitingEvent: function (request){
		this.queue.push(request);
	},
	executeWaitingEvent: function(){
		if (this.queue.length == 0) {
			this.busy = false;
			return;
		}
		this.busy = true;
		this.executedRequest = this.queue.shift();
		
		var data = this.executedRequest.options.data || this.executedRequest.options.postBody;
		
		var options = { 
			complete: AjaxDispatcher.onComplete, 
			success: AjaxDispatcher.onSuccess, 
			error: AjaxDispatcher.onFailure, 
			data:data
		};
		options.type = "POST";
		options.dataType = "json";
		
		options.url = this.executedRequest.method;
		
		if (this.executedRequest.options.onStart != undefined) this.executedRequest.options.onStart();
		if (this.executedRequest.options.silent != true)
			Loading.show();
		$.ajax(options);
	},
	executedRequest:null,
	request: function(method, options){
	    if (options == undefined) options = {};
		AjaxDispatcher.addWaitingEvent({method: method, options: options});
		if (!AjaxDispatcher.busy)
			AjaxDispatcher.executeWaitingEvent();
	},
	onComplete: function(){
		Loading.hide();
		AjaxDispatcher.executeWaitingEvent();
	},
	onFailure: function(obj, text, err){
		SMessages.error.show('System error: ' + text);
		Loading.hide();
		// ONCOMPLETE
		if (AjaxDispatcher.executedRequest.options.onComplete != undefined)
			AjaxDispatcher.executedRequest.options.onComplete();
	},
	onSuccess: function(json){
		response = json;
		if (response == null){
			if (AjaxDispatcher.executedRequest.onError != undefined)
				AjaxDispatcher.executedRequest.onError();
		    AjaxDispatcher.onFailure({status:"handling", statusText:"invalid response" + transport.responseText});
			return;
	    }
		var callSuccess = true;
		var callParam = null;
	// ONCOMPLETE
		if (AjaxDispatcher.executedRequest.options.onComplete != undefined)
			AjaxDispatcher.executedRequest.options.onComplete();
	// REDIRECT	
		if (response.redirect != undefined){
			callSuccess = false;
			var loc =  response.redirect;
			if (loc.substr(0,8) == '::reload') window.location.reload();
			else window.location = loc;
	    }
	// ERROR
		if (response.error != undefined){
			callSuccess = false;
			SMessages.error.show(unescape(response.error));
			if (AjaxDispatcher.executedRequest.onError != undefined){
				AjaxDispatcher.executedRequest.onError(unescape(response.error));
			}
	    }
	// RESPONSE	
		if (response.response != undefined){
		    if (typeof(response.response) == 'string'){
		        try{
	    		    callParam = unescape(response.response);
	        		if (AjaxDispatcher.executedRequest.updateElement != undefined){
	        			$(AjaxDispatcher.executedRequest.updateElement).update(callParam);
	                }
	                //callParam.evalScripts();
	        	}catch(e){
	                alert(e.message);
	        	}
			}else{
			    callParam = response.response;
		    }
		}
	// STATUS
		if (response.status != undefined){
			SMessages.status.show(unescape(response.status));
		}
	// SUCCESS
		if (callSuccess && (AjaxDispatcher.executedRequest.options.onSuccess != undefined) ) 
			AjaxDispatcher.executedRequest.options.onSuccess(callParam, AjaxDispatcher.executedRequest.extraParam);
	}
}
function ajaxUpdate (element, method, options){
    if (options == undefined) options = {};
	options.updateElement = element;
	return ajaxRequest(method, options);
}
function ajaxFormSubmit(form, onSuccess, options){
	if (options == undefined) options = {};
	options.postBody = $(form).serialize();
	options.onSuccess = onSuccess;
	ajaxRequest(form.action, options);	
	return false;
}
function ajaxRequest(method, options){return AjaxDispatcher.request(method,options);}