/*\
 | Copyright (C) 2009-2010 Link Digital
 | http://www.linkdigital.com.au/
 | All rights reserved.
 | Unauthorised copying, distribution or derivation is prohibited.
\*/


/****************************** Helper Functions ******************************/

if (typeof (String.prototype.ltrim)	=== "undefined")	{ String.prototype.ltrim		= function (chars)	{ return this.replace (new RegExp ("^[" + (chars || "\\s") + "]+",  "g"), "");	}; }
if (typeof (String.prototype.rtrim)	=== "undefined")	{ String.prototype.rtrim		= function (chars)	{ return this.replace (new RegExp ( "[" + (chars || "\\s") + "]+$", "g"), "");	}; }
if (typeof (String.prototype.trim)	=== "undefined")	{ String.prototype.trim 		= function (chars)	{ return this.ltrim (chars).rtrim (chars);					}; }

Array.min												= function (array)	{ return Math.min.apply (Math, array); };
Array.max												= function (array)	{ return Math.max.apply (Math, array); };

/****************************** General Utility *******************************/

// Set all <a> tags with rel="ext" to open in new window
function a_init_ext (element)
{
	if (!(element = $ (element)))	return;

	element.observe ("click", function (event) { window.open (this.readAttribute ("href")); event.stop (); });
}

// Set all <a> tags with rel="rmv" to delete their parent element when clicked
function a_init_rmv (element)
{
	if (!(element = $ (element)))	return;

	element.observe ("click", function (event) { this.up ().hide (); if (this.readAttribute ("href") == "#") event.stop (); });
}

// Set the font size of the elements listed in ids (can be an array or a string)
// Uses cookies for persistance
function a_onclick_fsize (ids, size, unit)
{
	if (typeof (ids) == "string")
		ids = [ids];

	for (c = 0, x = ids.length; x--; )
	{
		CookieJar.set ("fontEl_" + c++, ids[x], 90);

		if (el = document.getElementById (ids[x]))
			el.style.fontSize = size + unit;
	}

	CookieJar.set ("fontSize", size, 90);
	CookieJar.set ("fontUnit", unit, 90);
	CookieJar.set ("fontNum",  c,    90);

	return false;
}

// Load persistant font sizes set with a_onclick_fsize
function onload_fsizes ()
{
	fontElem	= [];
	fontNum		= CookieJar.get ("fontNum");
	fontSize	= CookieJar.get ("fontSize");
	fontUnit	= CookieJar.get ("fontUnit");

	if (fontNum != null && fontSize != null && fontUnit != null)
	{
		for (x = parseInt (fontNum); x--; )
			if ((e = CookieJar.get ("fontEl_" + x)) != null)
				fontElem.push (e);

		a_onclick_fsize (fontElem, fontSize, fontUnit);
	}
}

// Set an input text box to clear its default text on focus
function input_init_srch (element)
{
	if (!(element = $ (element)))	return;

	var temp		= $F (element);

	element.setValue (element.readAttribute ("title"));
	element.defaultValue	= $F (element);

	element.observe ("focus", function ()
	{
		if ($F (this) === this.defaultValue)
		{
			this.clear ();
			this.removeClassName ("dflt");
		}
	});

	element.observe ("blur",  function ()
	{
		if (!this.present ())
		{
			this.setValue (this.defaultValue);
			this.addClassName ("dflt");
		}
	});

	if (temp)
		element.setValue (temp);
	else	element.addClassName ("dflt");
}

// Set an input password box to show plaintext until focus
function input_init_pass (element)
{
	if (!(element = $ (element)))	return;
	element.removeClassName ("lc_pass");
	element.setValue ("");

	//var newelem = element.clone (); 		// IE won't let us just change the type attribute, OR clone the element >:(
	var newelem = new Element ("input",
	{
		name:		"-1",
		type:		"text",
		value:		"Password",
		title:		"Password",
		tabindex:	parseInt (element.getAttribute ("tabindex")) + 1,
		className:	element.className
	});

	element.twin = newelem;
	newelem.twin = element;

	newelem.observe ("focus", function () { this.replace (this.twin); this.twin.activate (); });	// this.twin.focus doesn't work right in IE for some reason
	element.observe ("blur",  function () { if (!this.present ()) this.replace (this.twin); });

	element.focus ();
	element.blur ();
}


/********************************** Cookies ***********************************/

// Make cookies easier to deal with
var CookieJar =
{
	set: function (name, value, days)
	{
		var expires = "";

		if (days)
		{
			var date = new Date ();
			date.setTime (date.getTime () + (days * 86400000));
			expires = "; expires=" + date.toGMTString ();
		}

		document.cookie = name + "=" + value + expires + "; path=/";
	},

	get: function (name)
	{
		var ca		= document.cookie.split (";");

		for (var i = ca.length; i--; )
		{
			var c = ca[i].toString ().trim ().split ("=");
			if (c[0] == name) return c[1];
		}

		return null;
	},

	clr: function (name)
	{
		this.set (name, "", -1);
	}
};


/******************************* Image Rotator ********************************/

function linkCMS_Snippet (snipID, xmlPath)
{
	var snipX		= 0;
	var snipZ		= 0;
	var snipM		= 0;
	var snipL		= $ (snipID + "_ctl");
	var snip1;
	var snip2;

	if (!(snipID = $ (snipID + "_ctr"))) return 0;

	new Ajax.Request (xmlPath,
	{
		method: 	"get",
		onSuccess:	snip_Init,
		onFailure:	function (response) { alert ("FAIL: " + response); }
	});


	function snip_Init (response)
	{
		var xml 	= response.responseXML;

		var imgs	= xml.getElementsByTagName ("image");
		var tFade	= xml.getElementsByTagName ("fadeInTime")[0].getAttribute ("val");
		var tHold	= xml.getElementsByTagName ("holdTime"  )[0].getAttribute ("val");

		snipM		= imgs.length;

		snipID.store ("tFade",	tFade);
		snipID.store ("tHold",	tHold);

		$R (0, snipM, true).each (function (x)
		{
			var src			= imgs[x].getAttribute ("uri");
			var rel 		= imgs[x].getAttribute ("rel");
			var alt 		= imgs[x].getAttribute ("alt");
			var ttl 		= imgs[x].getAttribute ("title");
			var desc 		= imgs[x].getAttribute ("desc");
			var href		= imgs[x].getAttribute ("link");

			var img			= new Image (); 				// Helps ensure the image loads properly
			img.src 		= src;

			var elD 		= new Element ("div",
			{
				id:		"snipDiv" + x
			});

			var elI 		= new Element ("img",
			{
				//id:		"snipDiv" + x,
				alt:		ttl,
				src:		src
			});

			elD.store ("prev", "snipDiv" + ((x - 1 + snipM) % snipM));		// Because Modulo doesn't work on negative numbers
			elD.store ("next", "snipDiv" + ((x + 1 + snipM) % snipM));

			if (x)	elD.hide ();

			elD.insert (new Element ("h2").update (ttl));
			elD.insert (new Element ("p").update (desc));

			if (href !== "")							// If we have an associated link, add that too
			{
				var elA 	= new Element ("a");
				if (href)	elA.setAttribute ("href", href);
				if (rel)	elA.setAttribute ("rel",  rel);

				elD.insert (elA);
				elA.insert (elI);
			}
			else	elD.insert (elI);						// No link, just add the image

			snipID.insert (elD);

			if (snipL)
			{
				var elL 		= new Element ("a",
				{
					id:		"snipLnk" + x,
					title:		ttl,
					href:		"#"
				});

				elL.update (x + 1);
				elL.store ("jump", x);
				elL.observe ("click", function (event) { snip_Jump (this.retrieve ("jump")); event.stop (); });

				if (!x) elL.addClassName ("at");

				snipL.insert (elL);
			}
		});

		if (snipM > 1) snip_Next ();
	}


	function snip_Next ()
	{
		var elI 		= $ ("snipDiv" + snipX);
		var elP 		= $ (elI.retrieve ("prev"));
		var elN 		= $ (elI.retrieve ("next"));

		snipX			= ++snipX % snipM;

		elP.hide ();
		elN.hide ();

		elI.setStyle ({zIndex:	 0});
		elN.setStyle ({zIndex:	 1});

		snip1			= new Effect.Appear (elN.id,
		{
			from:		0,
			to:		1,
			duration:	snipID.retrieve ("tFade"),
			delay:		snipID.retrieve ("tHold"),
			afterFinish:	snip_Next,
			afterSetup:	function ()
			{
				snipL.childElements ().invoke ("removeClassName", "at");
				$  ("snipLnk" + snipX).addClassName ("at");
			}
		});
	}


	function snip_Jump (jumpTo)
	{
		jumpTo			= jumpTo % snipM;

		var elI 		= $ ("snipDiv" + snipX);
		var elN 		= $ ("snipDiv" + jumpTo);

		snipX			= jumpTo;

		elN.hide ();

		elI.setStyle ({zIndex:	 0});
		elN.setStyle ({zIndex:	 1});

		snip1.cancel ();

		snip1			= new Effect.Appear (elN.id,
		{
			from:		0,
			to:		1,
			duration:	snipID.retrieve ("tFade"),
			afterFinish:	snip_Next,
			afterSetup:	function ()
			{
				snipL.childElements ().invoke ("removeClassName", "at");
				$  ("snipLnk" + snipX).addClassName ("at");
			}
		});
	}

	return 1;
}


/******************************** Load Things *********************************/

// Load everything
document.observe ("dom:loaded", function ()
{
	// Count AJAX objects
	var complex	= 0;
	var ajax	= 0;

	Ajax.Responders.register
	({
		onCreate:	function () { ++ajax; },
		onComplete:	function () { if (!--ajax) linkCMS_Load (); }			// Load normal stuff once AJAX has finished
	});


	// Complex stuff - uncomment as needed
	complex		+= linkCMS_Snippet ("snippet", "/userfiles/linkCMS/xml/snippet.xml");	// Snippet Rotator


	// Normal stuff
	if (!complex)	   linkCMS_Load ();
});


// Normal stuff
function linkCMS_Load ()
{
	$$ ("a[rel~=ext]").each 		(a_init_ext);		// Anchor OnClicks
	$$ ("a[rel~=rmv]").each 		(a_init_rmv);		// Anchor OnClicks

	$$ ("input.lc_srch").each		(input_init_srch);	// Search field niceness
	$$ ("input.lc_pass").each		(input_init_pass);	// Password field niceness

	$$ (".lc_hide").invoke			('hide');		// Hide stuff that can't be put in <noscript> tags.
	$$ (".lc_show").invoke			('show');		// Show stuff that is only of use to people with scripts enabled.
/*
	$  ("fonts_sml").observe		("click", function (event)
	{
		a_onclick_fsize (["cnav", "qnav"],				0.9,  "em");
		a_onclick_fsize (["lnav", "rnav", "rcol", "main", "snippet"],	1.0,  "em");
		a_onclick_fsize (["intro"],					1.15, "em");
		event.stop ();
	});

	$  ("fonts_lrg").observe		("click", function (event)
	{
		a_onclick_fsize (["cnav", "qnav"],				1.1,  "em");
		a_onclick_fsize (["lnav", "rnav", "rcol", "main", "snippet"],	1.2,  "em");
		a_onclick_fsize (["intro"],					1.3,  "em");
		event.stop ();
	});

	onload_fsizes ();
*/
}


