
/*--------------------------------------------------------------
 
	This library performs a dynamic lookup and returns an XML
	string to the specified place in your HTML document.
    
	Example Usage:
    
	<script type="text/javascript">
        campaign_search = new liveRequest ('results_div', '/xml/request.php');
        campaign_search.addListenerOnLoad('test_form_field', 'keypress');
        campaign_search.setEmptySearchText('<br />');
	</script>
	
	<input type="text" id="test_form_field" name="test_form_field" value="" />
	
	<div id="results_div" style="border: 1px solid black; height: 80px;">
	
	</div>	
	
--------------------------------------------------------------*/

if (browserEngine == null)
{
    if (!browserEngine)
    {
        var browserEngine = "";
        if (navigator.userAgent.indexOf("Safari") > 0) 
        {
        	browserEngine = "safari";	
        }
        else if (navigator.product == "Gecko") 
        {
        	browserEngine = "gecko";
        } 
        else 
        {
        	browserEngine = "ie";
        }
    }


    if (window.ActiveXObject && !window.XMLHttpRequest)
    {
        window.XMLHttpRequest = function() 
        {
            return new ActiveXObject((navigator.userAgent.toLowerCase().indexOf('msie 5') != -1) ? 'Microsoft.XMLHTTP' : 'Msxml2.XMLHTTP');
        };
    }
    
    var liveRequestObjects = new Array();

    function liveRequestInit ()
    {
        if (liveRequestObjects.length > 0)
        {
            for (var i=0; i<liveRequestObjects.length; i++)
            {
                liveRequestObjects[i].init();
            }
        }
    }

    function addLoadEvent(func)
    {
      var oldonload = window.onload;
      if (typeof window.onload != 'function')
      {
        window.onload = func;
      }
      else
      {
        window.onload = function()
        {
          oldonload();
          func();
        }
      }
    }

    addLoadEvent(liveRequestInit);
    
    function getTimestamp ()
    {
        var d = new Date();
        return d.getTime();
    }
    
    function liveRequest (resultId, xmlUrl)
    {
        this.requestObject = "";
        this.resultId = resultId;
        this.xmlUrl = xmlUrl;
        this.evalResult = false; // do we eval() result or display it
        this.eventListeners = new Array(); // array of ids to monitor
        this.monitoredIds = new Array(); // array of items being successfully monitored
        this.monitorTimeout = null; // holds the timeout parameter when monitoring a change
        this.showLoadingText = false; // if set will show loading text whilst loading
        this.liveDropdown = null;
        liveRequestObjects[liveRequestObjects.length] = this;
        this.liveRequestObjectsId = liveRequestObjects.length-1;
		this.changeEvents = new Array();
		this.allowEmptySearch = false;
		this.debugId = null;
    
        // methods
        this.fetchRequestObject = function ()
        {
           	this.requestObject = new XMLHttpRequest();
        }

        if (browserEngine != "ie") // gecko browser only load browsers once
        {
        	this.fetchRequestObject();
        }
        
        this.getEvent = function (ev)
        {
        	if (ev == "change") {
        		switch (browserEngine) 
        		{
                    case "safari":
                    case "gecko":
                        return "change";break;
           			case "ie":
                        return "onchange";break;
        		}
        	}
        	else /*(ev == "keypress")*/ 
        	{
        		switch (browserEngine) 
        		{
        			case "safari":
                        return "keydown";break;
           			case "gecko":
                        return "keypress";break;
        			case "ie":
                        return "onkeydown";break;
        		}
        	}
        }
		
        this.showLoading = function (text)
        {
            if (text == true)
            {
                text = '<div align="center"><img src="/images/icons/loading.gif" /></div>';
            }
			else
			{
				text = text+'<br />';
			}
			
            this.showLoadingText = text;
        }

        this.setEmptySearchText = function (text)
        {
            this.emptySearchText = text;
        }

        this.setAllowEmptySearch = function (w)
        {
            this.allowEmptySearch = w;
        }

        this.changeResultsText = function (text, apply_events)
        {
    		if (this.evalResult)
    		{
    			eval(text);
    		} 
    		else 
    		{
    			document.getElementById(this.resultId).innerHTML = text;
            }
			
			if (apply_events) {
				this.applyChangeEvents();
			}
        }
        
        this.processResults = function ()
        {
        	if (this.requestObject.readyState == 4) 
        	{
        		this.changeResultsText(this.requestObject.responseText, true);
        	}
        }

        this.setLiveDropdown = function (livedd)
        {
            this.liveDropdown = livedd;
            this.liveDropdown.liveRequestObjectsId = this.liveRequestObjectsId;
        }
        
        this.addListenerOnLoad = function (item_id, item_action, evalResult)
        {
            this.evalResult = evalResult;
            this.eventListeners[this.eventListeners.length] = new Array(item_id, this.getEvent(item_action));
        }

        this.addListener = function (item_id, item_action, evalResult)
        {
            this.evalResult = evalResult;
            this.addEventListener(new Array(item_id, this.getEvent(item_action)));
            this.addMonitorId(item_id);
        }

        this.abortRequest = function ()
        {
            if (this.requestObject) this.requestObject.abort();
        }
        
        this.process = function (debug) 
        {
            if (this.liveDropdown!=null)
            {
                this.liveDropdown.hideResults();
            }

    		if (this.requestObject && this.requestObject.readyState < 4) 
    		{
    			this.abortRequest();
    		}

            var url_params = new Array();
            if (this.monitoredIds.length > 0)
            {
                var found_non_empty = false;
    
            	for (var i=0; i < this.monitoredIds.length; i++)
            	{
            		var monitoredId = this.monitoredIds[i];
            		if (document.getElementById(monitoredId).value)
            		{
            		    found_non_empty = true;
            		}
            		url_params[url_params.length] = monitoredId+"="+escape(document.getElementById(monitoredId).value);
            	}
    
            	if (!found_non_empty)
            	{
            	    if (this.emptySearchText)
            	    {
            	       this.changeResultsText(this.emptySearchText);
            	    }
					if (!this.allowEmptySearch)
					{
						return;
					}
            	}
            }

        	if (this.showLoadingText != false) 
        	{
        		this.changeResultsText(this.showLoadingText, false);
        	}
            
    		if (browserEngine == "ie")
    		{
    			this.fetchRequestObject();
    		}
    		
    		this.requestObject.onreadystatechange = new Function ("liveRequestObjects["+this.liveRequestObjectsId+"].processResults();");
    		var qmark = (this.xmlUrl.indexOf('?') == -1) ? '?' : '&';
    		var url = this.xmlUrl + qmark;
            
    		url_params[url_params.length] = '_ts='+escape(getTimestamp());
    		if (url_params.length > 0)
    		{
    		    url = url + url_params.join('&');
    		}

			if (this.debugId)
			{
				document.getElementById(this.debugId).value += url+'; ';
			}
				
    		this.requestObject.open("GET", url);
    		this.requestObject.send(null);
        }
    
        this.registerChange = function (evt)
        {
            var key = (evt.which || evt.charCode || evt.keyCode);

    		// only process if key pressed is not up, down, left, right, pg_up, pg_down, end, home, tab, escape, return
    		if (key != 40 && key != 39 && key != 38 && key != 37 && key != 36 
    		      && key != 35 && key != 34 && key != 33 && key != 9 && key != 27 && key != 13)
    		{
            	if (this.monitorTimeout) 
            	{
            		window.clearTimeout(this.monitorTimeout);
            	}
    	      	this.monitorTimeout = window.setTimeout("liveRequestObjects["+this.liveRequestObjectsId+"].process()",400);
    		}

    		// and for certain keys we clear the timeout (escape, tab)
    		if (key == 27 | key == 9)
    		{
            	if (this.monitorTimeout)
            	{
            		window.clearTimeout(this.monitorTimeout);
            	}
    		}
        }

        this.init = function ()
        {
            if (this.eventListeners.length > 0)
            {
            	for (var i=0; i < this.eventListeners.length; i++)
            	{
            		var listener = this.eventListeners[i];
            		if (!document.getElementById(listener[0]))
            		{
            		    alert ("id not found: document.getElementById("+listener[0]+");");
            		    continue;
            		}
            		this.addEventListener(listener)
            		this.monitoredIds[this.monitoredIds.length] = listener[0];
            	}
            }
        }
        
        this.addEventListener = function (listener)
        {
			if (listener.length < 2) return;

    		switch (browserEngine)
    		{
    			case "safari":
    			case "gecko":
    				document.getElementById(listener[0]).addEventListener(listener[1], new Function ("evt", "liveRequestObjects["+this.liveRequestObjectsId+"].registerChange(evt);"), false);
    				break;
    
    			case "ie":
    				document.getElementById(listener[0]).attachEvent(listener[1], new Function ("evt", "liveRequestObjects["+this.liveRequestObjectsId+"].registerChange(evt);"));
    				break;
    		}
        }
        
        this.addMonitorId = function (id)
        {
    		this.monitoredIds[this.monitoredIds.length] = id;
        }

		this.addChangeEvent = function (str)
		{
			this.changeEvents[this.changeEvents.length] = str;
		}

		this.applyChangeEvents = function ()
		{
			for(var i=0; i < this.changeEvents.length; i++)
			{
				eval(this.changeEvents[i]);
			}
		}

        this.setDebugId = function (id)
        {
                this.debugId = id;
        }
    }
}
