// Test if the Browser is IE or not.
var ie = (navigator.appVersion.indexOf("MSIE") >= 0);

/**************************************************
 = The following are scripts which check for DOM
 = compliance and which try to do things the DOM
 = way first, but fall back on the old proprietary
 = methods if the browser doesn't support the DOM.
**************************************************/

var head = false;
var DOM = false;
var scripts = false;

if( document.createElement && document.getElementsByTagName )
{
	DOM = true;
	head = document.getElementsByTagName( "head" )[0];
	scripts = document.getElementsByTagName( "script" );
}


/*************************************************
 = Browser Compatibility Scripts
*************************************************/

function getElementById(id)
{
	if( document.getElementById ) return document.getElementById( id );
	if( document.all )
	{
		item = document.all.item( id );
		if( item && item.length )
			return item[0];
		return item;
	}

	return NULL;
}

// Hopefully we can attach this to a prototype sometime
function getElementsByTag( tag )
{
	if( ( "*" == tag ) && this.all )
		return this.all;

	if( this.getElementsByTagName )
		return this.getElementsByTagName( tag );

	return NULL;
}

document.getElementsByTag = getElementsByTag;

function createElement( type )
{
	if( document.createElement )
	{
		return document.createElement( type );
	}

	return false;
}

function clearElement( e )
{
	if( e )
	{
		if( e.hasChildNodes )
		{
			while( e.hasChildNodes() )
			{
				e.removeChild( e.firstChild );
			}
		}
	
		if( e.innerHTML ) e.innerHTML = "";
	}
}

function getActStyle( obj, styl )
{
	if( obj && obj.currentStyle )
	{
		if( eval( "true" ) )
			return eval( "obj.currentStyle." + transProperty( styl ) );
		else
			eval( "return obj.currentStyle." + transProperty( styl ) );
	}
	if( document.defaultView && document.defaultView.getComputedStyle )
	{
		return document.defaultView.getComputedStyle( obj, '' ).getPropertyValue( styl );
	}

	return "";
}



/**************************************************
 = These functions help include a script file
 = dynamically if you provide it with a
 = (relative/absolute) script file name, sort of
 = like include directives in C.
**************************************************/
function includeScript( scriptFileName ){
	if( !scriptIsIncluded( scriptFileName ) )
	{
		var s = createElement( "script" );
		if( head && s )
		{
			s.type = "text/javascript";
			s.src = scriptFileName;
			head.appendChild( s );
			scripts = document.getElementsByTagName( "script" );
		}
		else
		{
			document.write( '<script type="text/javascript" src="' + scriptFileName + '"></script>' );
		}
	}
}

// Tests if a script already exists in the document.
function scriptIsIncluded( scriptFileName )
{
	if( scripts )
	{
		for( var i = 0; i < scripts.length; i++ )
		{
			idx = scripts[i].src.lastIndexOf( scriptFileName );
			if( ( 0 == idx ) || ( ( idx > 0 ) && ( '/' == scripts[i].src.charAt( idx - 1 ) ) ) )
			{
				return true;
			}
		}
	}

	return false;
}

// getScriptDir returns the directory which contains
//  the script file whose name matches scriptFileName.
function getScriptDir(scriptFileName){
	if( scripts )
	{
		var idx = 0;
		for( var i = 0; i < scripts.length; i++ )
		{
			idx = scripts[i].src.lastIndexOf( scriptFileName );
			if( ( idx >= 0 ) && ( idx == ( scripts[i].src.lastIndexOf("/") + 1 ) ) )
			{
				return scripts[i].src.substring( 0, idx );
			}
		}
	}

	return "./";
}


var dir = getScriptDir( "scripts.js" );
includeScript( dir + "propmod.js" );


/**************************************************
 = Function for dynamic page updating.
**************************************************/
function GetXmlHttpObject()
{
	if (window.XMLHttpRequest)
	{
		return new XMLHttpRequest();
	}
	if (window.ActiveXObject)
	{
		try{ return new ActiveXObject("Microsoft.XMLHTTP"); }
		catch(e){ try{ return new ActiveXObject("Msxml2.XMLHTTP"); } catch(ex){} }
	}

	return null;
}


/**************************************************
 = Miscellaneous helper functions.
**************************************************/

function min(val1, val2){
	if(val1 < val2) return val1;
	else return val2;
}

function minpos(val1, val2){
	if( val2 < 0 || val1 < val2 ) return val1;
	else return val2;
}

function max(val1, val2){
	if(val1 > val2) return val1;
	else return val2;
}

function stripLink(str){
	var apos = str.toUpperCase().indexOf("<A ");
	if(apos == -1) return str;

	var aend = apos + str.substring(apos).indexOf(">") + 1;
	var aclose = aend + str.substring(aend).toUpperCase().indexOf("</A>");

	str = str.substring(0, apos) + str.substring(aend, aclose) +
		str.substring(aclose + ("</a>").length);

	return str;
}

// Translates a dash-separated property name into a
//   first-letter-uppercase string.
function transProperty( prop )
{
	var dArray = prop.split( '-' );
	prop = dArray[0];
	for( var i = 1; i < dArray.length; i++ )
	{
		prop += dArray[i].charAt(0).toUpperCase() +
		        dArray[i].substring( 1, dArray[i].length );
	}

	return prop;
}

// Adds a name/value pair to a server-side GET-method string
function addGetData( reqstr, varname, val )
{
	var varstr = varname;
	if( val ) varstr += "=" + val;

	if( 0 <= reqstr.indexOf( "?" ) )
		return reqstr + "&" + varstr;

	return reqstr + "?" + varstr;
}

function getInt( str )
{
	var i = 0;
	while(i < str.length && (str.charAt(i) < '0' || str.charAt(i) > '9')){ i++; }
	var j = i;
	while(j < str.length && str.charAt(j) >= '0' && str.charAt(j) <= '9'){ j++; }
	return parseInt(str.substring(i, j));
}

function expandPosAbbr( pos )
{
	switch( pos )
	{
	case "tl": return "left top";
	case "bl": return "left bottom";
	case "tr": return "right top";
	case "br": return "right bottom";
	}
	return "";
}

function replaceAll( str, findStr, replaceStr )
{
	var index = str.indexOf( findStr );
	var newStr = "";
	if( index == -1 ) return str;
	while( ( str.length > 0 ) && ( index > -1 ) )
	{
		newStr += str.substring( 0, index ) + replaceStr;
		str = str.substring( index + findStr.length, str.length );
		index = str.indexOf( findStr );
	}
	return newStr;
}

// Takes a string and changes all double-quote characters to "&quot;"
//  and all single-quote characters to "&apos;"
function makeSafeString( str ){
	str = replaceAll( str, '"', "&quot;" );
	str = replaceAll( str, "'", "&apos;" );
	return str;
}


/********************************************************************/
/*    The following script I took from MySpace.com                  */
/*      (I have modified it a bit for robustness's sake.)           */
/********************************************************************/


//////////////////////////////////////////////////////////////////////
// registerEvent function
//////////////////////////////////////////////////////////////////////
// Allows you to attach an event to an HTML object (without 
// overwriting any existing events).
// Parameters:
//		object: 
// 		The name of the HTML element you wish to append an event
//		to, such as "window" or "document.form.myElement".
//		event:
//		The event handler you would like to modify, such as 
//		"onload" or "onclick".  Event handlers are all lowercase.
//		cmd:
//		The javascript statement(s) you would like to put into the 
//		event handler, such as "alert("test");", or 
//		"var s = 1; s++;".  AS ALWAYS, ALL JAVASCRIPT COMMANDS MUST
//		END WITH A SEMICOLON.
//		append:
//		This is a boolean value which determines whether the cmd you
//		are attaching should go at the end of the handler or the 
//		beginning.  true = at the end.  false = at the beginning.
//////////////////////////////////////////////////////////////////////
function registerEvent(object, event, cmd, append)
{
	if(arguments.length < 3) return alert("Invalid arguments. Please use the format \nregisterEvent(object, event, command, [append]).");
	if (typeof append != "boolean") append = true;

	var event = "" + event;
	if( typeof object == "string" )
		event = object + "." + event.toLowerCase();
	else
		event = "object." + event.toLowerCase();

	eval( "var objEvent = " + event );

	var strEvent = (objEvent) ? objEvent.toString() : "";
	strEvent = strEvent.substring(strEvent.indexOf("{")+1, strEvent.lastIndexOf("}"));
	strEvent = (append) ? (strEvent + cmd) : (cmd + strEvent);
	strEvent += "\n";
	eval( event + " = new Function( strEvent )" );
	return true;
}



/********************************************************************/
/*    These scripts are to make dynamically adding event handlers   */
/*      modular and easy in script.                                 */
/********************************************************************/

// Using the newfangled event registration methods doesn't currently
//   work well for events which depend on return values (e.g. onclick)
//   I've found it's best to stick to simple assignment there, because
//   an onclick (and the like) generally should only have one action
//   to take on the event.

// usenew is whether the scripter wants to even attempt to use the new
//   event methods.

function attachEvt( obj, evt, func, usenew )
{
	if( false !== usenew ) usenew = true;

	if( obj.addEventListener && usenew )
	{
		obj.addEventListener( evt, getFPtr( func ), false )
	}
	else if( obj.attachEvent && usenew )
	{
		obj.attachEvent( "on" + evt, getFPtr( func ) )
	}
	else
	{
		registerEvent( obj, "on" + evt, getFString( func ) );
	}
}

// Returns a function pointer - either a new function if "func" is
//   a string or just "func"'s value.
function getFPtr( func )
{
	if( typeof func == "string" )
		return new Function( func );
	else
		return func;
}

// Returns the representation of "func" as a string - an object
//   string if "func" is anything but a string or just "func"
function getFString( func )
{
	if( typeof func == "string" )
		return func;

	var fstr = String( func );
	fstr = fstr.substring( fstr.indexOf( "{" ) + 1, fstr.lastIndexOf( "}" ) );
	return fstr;
}


function testReady( iptr, func )
{
	if( document.readyState && ( "complete" == document.readyState ) )
	{
		clearInterval( iptr );
		getFPtr( func )();
	}
}


function addLoadEvent( func )
{
	if( document.addEventListener )
	{
		document.addEventListener( "DOMContentLoaded", func, false );
	}
	else if( document.readyState && setInterval )
	{
		var loadtest = setInterval( function(){ testReady( loadtest, func ); }, 10 );
	}
	else
	{
		attachEvt( window, "load", func );
	}
}


/**************************************************
 = These functions add rounded corners to an
 = element.
**************************************************/

function roundOff(elem, allcorners, formatting)
{
	var all4 = true;
	if( allcorners ) all4 = allcorners;

	var formt = "";
	if( formatting ) formt = formatting;

	var imgstr = getActStyle( elem, "background-image" );
	var imgext = imgstr.substring(imgstr.indexOf("tl.") + 2, imgstr.length - 1);
	imgstr = imgstr.substring(4, imgstr.indexOf("tl."));

	var origElem = elem;

	var i = 0;

	if( all4 )
	{
		elem = addRoundOff(elem, imgstr + "tr" + imgext, "top right", "");
		elem = addRoundOff(elem, imgstr + "br" + imgext, "bottom right", "");
	}

	elem = addRoundOff(elem, imgstr + "bl" + imgext, "bottom left", formt);
}

function addRoundOff(elem, img, align, formatting)
{
	if( DOM )
	{
		container = document.createElement("div");
		container.style.backgroundImage = "url(" + img + ")";
		container.style.backgroundRepeat = "no-repeat";
		container.style.backgroundPosition = align;

		addStyles( container, formatting );

		container.style.width = "100%";
		container.style.height = "100%";

		while(elem.childNodes.length > 0)
			container.appendChild(elem.removeChild(elem.childNodes.item(0)));
		elem.appendChild(container);


		return container;
	}
	else
	{
		elem.innerHTML = "<div style='width:100%; height:100%; background-image:url(" + img +
			"); background-repeat:no-repeat; background-position:" + align + "; " +
			formatting + ";'>" + elem.innerHTML + "</div>";

		return elem;
	}
}

