var XmlHttp = false;

if ( window.XMLHttpRequest ) 
{
	XmlHttp = new XMLHttpRequest();

} else if ( window.ActiveXObject )
{
	XmlHttp = new ActiveXObject( 'Microsoft.XMLHTTP' );
}


// ---

function GSInstance( aReference, aControlID )
{
	this.reference = aReference;
	this.controlID = aControlID;
}

var Instances = new Array( 0 );

// ---

function GSClass( aControlID, aLink, aContentID )
{
	this.m_ControlID    = aControlID;
	this.m_Link         = aLink;
	this.m_ContentID    = aContentID;
	this.m_SearchText   = "";

	//

	this.m_Data = new Array();
	this.m_NumberOfRecords = 0;

	this.m_IsContentVisible = false;
	this.m_IsCursorEnabled  = false;
	this.m_CursorIndex      = 0;

	//

	this.MoveCursorUp   = GSMoveCursorUp;
	this.MoveCursorDown = GSMoveCursorDown;

	// methods

	this.ShowContent    = GSShowContent;
	this.WriteContent   = GSWriteContent;
	this.InitValues     = GSInitValues;
	this.Attach         = GSAttach;
	this.Clear          = GSClear;

	this.doMyKeyUp    = GSOnKeyUp;
	this.doMyKeyDown  = GSOnKeyDown;
	this.doMyBlur     = GSOnBlur;
	this.doMyFocus    = GSOnFocus;

	// onload
	this.Clear();
	this.Attach();

	// register ourselves in the instances array for the static functions
	Instances.splice( Instances.length, 0, new GSInstance( this, this.m_ControlID ) );
}


function GSClear()
{
	this.ShowContent( false );

	this.m_IsCursorEnabled  = false;
	this.m_CursorIndex      = 0;
	this.m_SearchText       = "";
}



function GSMoveCursorUp()
{
	this.m_CursorIndex --;
	if ( this.m_CursorIndex < 0 )
	{
		this.m_IsCursorEnabled = false;
		this.m_CursorIndex     = 0;
	} 

	this.WriteContent();
}



function GSMoveCursorDown()
{
	if ( !this.m_IsCursorEnabled )
	{
		this.m_IsCursorEnabled = true;
		this.m_CursorIndex = 0;

	} else
	{
		this.m_CursorIndex ++;
		if ( this.m_CursorIndex >= this.m_NumberOfRecords ) this.m_CursorIndex = this.m_NumberOfRecords - 1;
	}

	this.WriteContent();
}


function GSOnKeyUp( e )
{
	var theKey = 0;
	anObject = GetObjectByID( this.m_ControlID );
	if ( !e ) var e = window.event;
	theKey = e["keyCode"];

	if ( theKey == 40 ) return;
	if ( theKey == 38 ) return;
	if ( theKey == 27 ) return;

	if ( anObject.value.length < 1 )
	{
		this.ShowContent( false );

	} else
	{

		if ( !this.m_IsContentVisible )
		{
			this.WriteContent();
			this.ShowContent( true );
		}

		if ( this.m_SearchText != anObject.value )
		{
			this.m_SearchText = anObject.value;
			var theLink = this.m_Link + this.m_SearchText + "&anticache=" + Math.random();

			this.m_CursorIndex = 0;

			this.InitValues( GetFileContent( theLink ) );
			this.WriteContent();

			if ( !this.m_IsContentVisible ) this.ShowContent( true );
		}

	} // end of if anobject.value.length < 1

}


function GSOnKeyDown( e )
{
	var theKey = 0;
	anObject = GetObjectByID( this.m_ControlID );
	if ( !e ) var e = window.event;
	theKey = e["keyCode"];

	// down
	if ( theKey == 40 && this.m_IsContentVisible )
	{
		this.MoveCursorDown();
		anObject.value = this.m_Data[ this.m_CursorIndex ];
	}

	// up
	if ( theKey == 38 && this.m_IsContentVisible )
	{
		this.MoveCursorUp();	
		anObject.value = this.m_Data[ this.m_CursorIndex ];
	}

	// escape pressed ?
	if ( theKey == 27 && this.m_IsContentVisible )
	{
		anObject.value = "";

		this.Clear();
	}
}



function GSOnBlur()
{
	SetObjectVisibility( this.m_ContentID, false );
}


function GSOnFocus()
{
	if ( this.m_IsContentVisible ) SetObjectVisibility( this.m_ContentID, true );
}



function GSAttach()
{
	var theObject = GetObjectByID( this.m_ControlID );

	// position teh content div under the control

	x = GetObjectLeft( this.m_ControlID );
	y = GetObjectTop( this.m_ControlID );
	height = GetObjectHeight( this.m_ControlID );

	SetObjectPosition( this.m_ContentID, x, y + height );

	// hook the control events we need. events need to be attached to "this" before hooking the control

	theObject.onkeydown = GSOnKeyDownStatic;
	theObject.onkeyup   = GSOnKeyUpStatic;
	theObject.onblur    = GSOnBlurStatic;
	theObject.onfocus   = GSOnFocusStatic;
}



function GSInitValues( aString )
{
	if ( !aString || aString == "" )
	{
		this.m_Data = new Array();
		this.m_NumberOfRecords = 0;
		this.ShowContent( false );

	} else
	{
		this.m_Data = String( aString ).split( "|" );
		this.m_NumberOfRecords = this.m_Data.length;

		this.WriteContent();
		this.ShowContent( true );
	}
}



function GSShowContent( aState )
{
	this.m_IsContentVisible = aState;
	SetObjectVisibility( this.m_ContentID, aState );
}



function GSWriteContent()
{
	var theObject = GetObjectByID( this.m_ContentID );
	var theContent = new String();
	theContent = "<table cellspacing=\"1\" cellpadding=\"1\" class=\"suggest\" width=\"250px\">";

	for ( var i = 0; i < this.m_NumberOfRecords; i++ )
	{
		var theTDClass = ( this.m_IsCursorEnabled && i == this.m_CursorIndex ) ? "over" : "";
		theContent += "<tr><td class=\"" +  theTDClass + "\">" + this.m_Data[i] + "</td></tr>";
	}

	theContent += "</table>";
	theObject.innerHTML = theContent;
}



function GetFileContent( url )
{
	XmlHttp.open( "GET", url, false ); // sync request
	XmlHttp.send( null );
	return ( XmlHttp.responseText );
}

function GSOnKeyDownStatic( e )
{
	// look for our instance and route the event
	for ( var i = 0; i < Instances.length; i++ )
	{
		if ( Instances[i].controlID == this.id )
		{
			Instances[i].reference.doMyKeyDown( e );
			break;
		}
	}
}

function GSOnKeyUpStatic( e )
{
	// look for our instance and route the event
	for ( var i = 0; i < Instances.length; i++ )
	{
		if ( Instances[i].controlID == this.id )
		{
			Instances[i].reference.doMyKeyUp( e );
			break;
		}
	}
}

function GSOnBlurStatic()
{
	// look for our instance and route the event
	for ( var i = 0; i < Instances.length; i++ )
	{
		if ( Instances[i].controlID == this.id )
		{
			Instances[i].reference.doMyBlur();
			break;
		}
	}
}

function GSOnFocusStatic()
{
	// look for our instance and route the event
	for ( var i = 0; i < Instances.length; i++ )
	{
		if ( Instances[i].controlID == this.id )
		{
			Instances[i].reference.doMyFocus();
			break;
		}
	}
}