/***
	Changes:

 GH 30.10.2006 AjaxMaintainer, Parameter added
 CP 00.00.2006 AjaxMaintainer created
 GH 03.10.2006 sendRequest(), Parameter return_xlm ist [optional] und async removed.
 GH 04.09.2006 created

 Functions PUBLIC:
 
	function sendRequest		( strSource, strData, intType, callback_function, return_xml)
	function sendRequestSync( strSource, strData, intType)
	function getValues		( xmlDocument, strTagName )
	function setEvent			( xmlNode, strName, strFunction )
	function hideElement		( strID, blnUseDisplay )
	function showElement		( strID, blnUseDisplay )
	
 Functions PRIVATE:
	function getXMLRequester( )

*/

// constants
var REQUEST_GET = 0;
var REQUEST_POST= 2;
var REQUEST_HEAD= 1;
var REQUEST_XML = 3;
var xmlHttp = false;

/**
 * instantiates a new xmlhttprequest object
 *
 * @return xmlhttprequest object or false
 */
function getXMLRequester( )
{
    // try to create a new instance of the xmlhttprequest object
    var xmlHttp = null;
    try
    {
        // Mozilla, Opera und Safari
        if( window.XMLHttpRequest )
          xmlHttp = new XMLHttpRequest();

        // Internet Explorer
        else if( window.ActiveXObject )
        {
            for( var i = 5; i; i-- )
            {
                try
                {
                    // loading of a newer version of msxml dll (msxml3 - msxml5) failed
                    // use fallback solution
                    // old style msxml version independent, deprecated
                    if( i == 2 )
                        xmlHttp = new ActiveXObject( "Microsoft.XMLHTTP" );
                    // try to use the latest msxml dll
                    else
                        xmlHttp = new ActiveXObject( "Msxml2.XMLHTTP." + i + ".0" );
                    break;
                } catch( excNotLoadable )
                {
                	xmlHttp = false;
                }
            }
        }                    
    } catch( excNotLoadable )
    { 	// loading of xmlhttp object failed
        xmlHttp = false;
    }

    return xmlHttp;
}

function AjaxMaintainer(elemWaiting,cb_finished)
{
  this.ajaxObjects = Array();
  this.anzObj = 0;
  this.objReady = 0;
  this.elemWaiting = "";  
  this.onFinished = null;
  
  if(elemWaiting)
    this.elemWaiting = elemWaiting;
  
  if (cb_finished)
  	this.onFinished = cb_finished;
  	
}

AjaxMaintainer.prototype.add = function( as_obj )
{
  this.ajaxObjects[this.anzObj++] = as_obj;
  as_obj.maintainer = this;
}

AjaxMaintainer.prototype.clear = function()
{
  foreach(as_obj in this.ajaxObjects)  
  {
    if(as_obj.xmlHttpRequest.readyState)
      as_obj.xmlHttpRequest.abort();
  }
  
  this.ajaxObjects = Array();
  this.anzObj = 0;
  this.objReady = 0;
  this.elemWaiting = "";
  this.onFinished = null;
}

AjaxMaintainer.prototype.ready = function(as_obj)
{
  this.objReady++;
  
  if(this.objReady == this.anzObj && this.elemWaiting.length > 0 && document.getElementById(this.elemWaiting))
  {
    hideElement(this.elemWaiting, true);

	 // Callback Function aufrufen, wenn alles fertig ist.
	 if (this.onFinished != null) 
	 	this.onFinished();
  }
    
  if(as_obj.nachfolger != null)
    as_obj.nachfolger.doRequest();  
    
//  alert("ready:" + this.objReady + "#Anz:" + this.anzObj + "#Elem:" + document.getElementById(this.elemWaiting));    
}

function AjaxObj()
{
  //Eigenschaften deklarieren und initialisieren
  this.url = "";
  this.params = "";
  this.onSuccess = null;
  this.onError = function (msg) { alert(msg); }
  this.xmlHttpRequest = false;
  this.nachfolger = null;
  this.maintainer = false;
  var _this = this;  
}

AjaxObj.prototype.doRequest = function()
{
  //Ã¼berpruefen der Angaben
  if (!this.url)
  {
    this.onError("Es wurde keine URL angegeben. Der Request wird abgebrochen.");
		return false;
  }
  if (!this.method)
    this.method = REQUEST_POST;
    
  //XMLHttpRequest-Objekt erstellen
  this.xmlHttpRequest = getXMLRequester();
  
  if(!this.xmlHttpRequest)
  {
    this.onError("Es konnte kein XMLHttpRequest-Objekt erstellt werden.");
    return false;
  }
  
  //Zugriff auf Klasse für ReadyStateHandler ermöglichen
  var _this = this;  

  this.xmlHttpRequest.open("POST",this.url,true);
  this.xmlHttpRequest.onreadystatechange = readyStateHandler;
  this.xmlHttpRequest.setRequestHeader('Content-Type', 'application/x-www-form-urlencoded');
  this.xmlHttpRequest.setRequestHeader('Connection', 'close');
  this.xmlHttpRequest.send(this.params);
  showElement(_this.maintainer.elemWaiting, true);
  
  //Private Methode zur Verarbeitung der erhaltenen Daten
  function readyStateHandler()
  {
    //wenn readyState == 4, Verarbeitung fertig
    //0 = Nicht initialisiert
	//1 = Seite wird momentan geladen
	//2 = Seite ist fertig geladen
	//3 = interaktiv, downloading response
	//4 = Anforderung abgeschlossen
    if (_this.xmlHttpRequest.readyState < 4)
      return false;
    
    //Status = 200 || 304 -> Success
    if(_this.xmlHttpRequest.status == 200 || _this.xmlHttpRequest.status == 304)
    {
      if(_this.onSuccess)
      { 
//         alert(_this.onSuccess);
        _this.onSuccess(_this.xmlHttpRequest.responseText);
          
        if(_this.maintainer)
          _this.maintainer.ready(_this);  
      }  
    } 
    else
    {
      if(_this.onError)
        _this.onError("["+_this.xmlHttpRequest.status+" "+_this.xmlHttpRequest.statusText+"] Es trat ein Fehler bei der Datenuebertragung auf.");
     
      if(_this.maintainer)
        _this.maintainer.ready(_this);
    }
  } 
}    

function sendRequest(maintainer, strUrl, strParam, callback_function, istNachfolger, nachfolger)
{
   ajaxObj = new AjaxObj();

  //Ã¼berprÃ¼fen der Angaben
    if(typeof maintainer != "object")
    {
      alert("Es wurde kein gÃ¼ltiges Maintainer-Objekt angegeben!");
      return false;
    }
    else
      maintainer.add(ajaxObj);
   
    if( strParam )
        ajaxObj.params = strParam;   
        
    if( strUrl )
        ajaxObj.url = strUrl;            

    // parse query string
    if( ( ajaxObj.params && ajaxObj.params.substr( 0, 1 ) == '&' || ajaxObj.params.substr( 0, 1 ) == '?' ) )
        ajaxObj.params = ajaxObj.params.substring( 1, ajaxObj.params.length );
    
    if(callback_function)
      ajaxObj.onSuccess = callback_function;
/*
    else
    {
      alert("Es wurde keine Callback-Funktion angegeben!");
      return false;    
    }
*/      
    if(nachfolger != null)
      ajaxObj.nachfolger = nachfolger;  
      
    //kein Nachfolger -> wird gestartet
    if(istNachfolger == 0)
      ajaxObj.doRequest();
      
    return ajaxObj;        
} 



/**
 * sends a http request to server
 *
 * @param strSource, String, datasource on server, e.g. data.php
 * @param strData, String, data to send to server, optionally
 * @param intType, Integer,request type, possible values: REQUEST_GET, REQUEST_POST, REQUEST_XML, REQUEST_HEAD default REQUEST_GET
 * @param callback_function, function Funktion wird aufgerufen, wenn eine Antwort da ist.
 * @param return_xml, boolean, antwort in XML oder PlainText [optional]
 * @return String, request data or data source or false
 */
 /*
function sendRequest( strSource, strData, intType, callback_function, return_xml)
{
	if ((typeof return_xml) == "undefined")
		return_xml = false;

    if( !strData )
        strData = '';

    // default type (0 = GET, 1 = xml, 2 = POST )
    if( isNaN( intType ) )
        intType = 0; // GET

    // create a new instance of xmlhttprequest object
    // if it fails, return
    if( !xmlHttp )
    {
        xmlHttp = getXMLRequester( );
        if( !xmlHttp )
            return false;
    } else {
	    // previous request not finished yet, abort it before sending a new request
	    if( xmlHttp.readyState )
	        xmlHttp.abort( );
	}

    // parse query string
    if( intType != 1 && ( strData && strData.substr( 0, 1 ) == '&' || strData.substr( 0, 1 ) == '?' ) )
        strData = strData.substring( 1, strData.length );

    // data to send using POST
    var dataReturn = strData ? strData : strSource;

    switch( intType )
    {
        case 1:    // xml
            strData = "xml=" + strData;
        case 2: // POST
            // open the connection
            xmlHttp.open( "POST", strSource, true );
            xmlHttp.setRequestHeader( 'Content-Type', 'application/x-www-form-urlencoded' );
            xmlHttp.setRequestHeader( 'Content-length', strData.length );
            break;
        case 3: // HEAD
            // open the connection
            xmlHttp.open( "HEAD", strSource, true );
            strData = null;
            break;
        default: // GET
            // open the connection
            var strDataFile = strSource + (strData ? '?' + strData : '' );
            xmlHttp.open( "GET", strDataFile, true );
            strData = null;
    }

    // set onload data event-handler
    xmlHttp.onreadystatechange = function()
    {
 	   // status 0 UNINITIALIZED open() has not been called yet.
	    // status 1 LOADING send() has not been called yet.
	    // status 2 LOADED send() has been called, headers and status are available.
	    // status 3 INTERACTIVE Downloading, responseText holds the partial data.
	    // status 4 COMPLETED Finished with all operations.
	    if ( xmlHttp.readyState == 4)
        {
           // check http status
            if( xmlHttp.status == 200 )
            {  // success
                if (return_xml)
                  eval(callback_function + '(xmlHttp.responseXML)');
                else
                  eval(callback_function + '(xmlHttp.responseText)');
            } else
            	// loading not successfull, e.g. page not available
	             alert( "ERROR\n HTTP status = " + xmlHttp.status + "\n" + xmlHttp.statusText ) ;
       	}
    }

    // send request to server
    xmlHttp.send( strData );    // param = POST data

    return dataReturn;
}
*/

/**
 * sends a http request to server SYNC and return the data
 *
 * @param strSource, String, datasource on server, e.g. data.php
 * @param strData, String, data to send to server, optionally
 * @param intType, Integer,request type, possible values: REQUEST_GET, REQUEST_POST, REQUEST_XML, REQUEST_HEAD default REQUEST_GET
 * @return String, request data or data source or false
 */

function sendRequestSync( strSource, strData, intType)
{
    if( !strData )
        strData = '';

    // default type (0 = GET, 1 = xml, 2 = POST )
    if( isNaN( intType ) )
        intType = 0; // GET

    // create a new instance of xmlhttprequest object
    // if it fails, return
    if( !xmlHttp )
    {
        xmlHttp = getXMLRequester( );
        if( !xmlHttp )
            return false;
    } else {
	    // previous request not finished yet, abort it before sending a new request
	    if( xmlHttp.readyState )
	        xmlHttp.abort( );
	}

    // parse query string
    if( intType != 1 && ( strData && strData.substr( 0, 1 ) == '&' || strData.substr( 0, 1 ) == '?' ) )
        strData = strData.substring( 1, strData.length );

    // data to send using POST
    var dataReturn = strData ? strData : strSource;

    switch( intType )
    {
        case 1:    // xml
            strData = "xml=" + strData;
        case 2: // POST
            // open the connection
            xmlHttp.open( "POST", strSource, false );
            xmlHttp.setRequestHeader( 'Content-Type', 'application/x-www-form-urlencoded' );
            xmlHttp.setRequestHeader( 'Connection', 'close' );
            xmlHttp.setRequestHeader( 'Content-length', strData.length );
            break;
        case 3: // HEAD
            // open the connection
            xmlHttp.open( "HEAD", strSource, false );
            xmlHttp.setRequestHeader( 'Connection', 'close' );
            strData = null;
            break;
        default: // GET
            // open the connection
            var strDataFile = strSource + (strData ? '?' + strData : '' );
            xmlHttp.open( "GET", strDataFile, false );
            xmlHttp.setRequestHeader( 'Connection', 'close' );
            strData = null;
    }

  
    // send request to server
    xmlHttp.send( strData );    // param = POST data

    if ( xmlHttp.readyState == 4 && xmlHttp.status == 200 )
    {  // success
    	return xmlHttp.responseText;
    }
    alert( "ERROR\n HTTP status = " + xmlHttp.status + "\n" + xmlHttp.statusText ) ;
	return false;
}

// retrieve data from dom tree
function getValues( xmlDocument, strTagName )
{
    var xmlTags;
    if( strTagName )
        xmlTags =  xmlDocument.getElementsByTagName( strTagName );
    else
        xmlTags =  xmlDocument.childNodes;

    var intLen = xmlTags.length;
    if( !intLen )
        return null;
    else if( intLen == 1 )
    {
        return xmlTags[ 0 ].firstChild.nodeValue;
    }
    else
    {
        var arrValues = new Array( );
        for( var i = 0; i < intLen; i++ )
        {
            arrValues[ i ] = xmlTags[ i ].firstChild.nodeValue;
        }
        return arrValues;
    }
}

// register an event handler to an element
function setEvent( xmlNode, strName, strFunction )
{
    strName = strName.substr( 0, 2 ) == "on" ? strName.substr( 2, strName.length ) : strName;

    // w3c compatible style, not supported by internet explorer yet
    if( document.addEventListener )
        xmlNode.addEventListener( strName, new Function( "event", "event.preventDefault( ); " + strFunction ), true );
    // Internet Explorer
    else if( document.attachEvent )
        xmlNode.attachEvent( "on" + strName, new Function( "event", strFunction ) );
    // old style (tag.onclick)
    else
        xmlNode[ "on" + strName ] = new Function( "event", strFunction );
}


// hide an element
function hideElement( strID, blnUseDisplay )
{
    var xmlNode = document.getElementById( strID );
    if( xmlNode )
        blnUseDisplay ? xmlNode.style.display = "none" : xmlNode.style.visibility = "hidden";
}

// makes an element visible
function showElement( strID, blnUseDisplay )
{
    var xmlNode = document.getElementById( strID );
    if( xmlNode )
        blnUseDisplay ? xmlNode.style.display = "" : xmlNode.style.visibility = "visible";
}

