/*
	nxSwapper v.1.1 by Gilles Cochez.
	Copyright (c) netXtra. All rights reserved.
*/

// closure
;(function($)
{	
	// plugin
	$.fn.nxSwapper = function(settings)
	{
		// private variables
		// old key, new key, old id, new id, new loaded, element displayed, link, container, container height, 
		// container width, current effect, new effect to use, fx direction, image array, image array size, link in new window
		var ok, nk, oid, nid, nl, e, url, self = this, sheight, swidth, cfx, nfx, fxdir, img, size, nwin;
		
		// default settings
		var defaults =
		{
			// amount of time an image will be displayed (used if no time is set per image)
			displayTime: 4000,			
			
			// swapped effect (default effect to use, effect can be set per image. supported: 'curtain', 'fade', 'slide' or 'toggle')
			effect: 'slide',
			
			// slow, normal, fast or time in ms
			effectSpeed: 'slow',

			// effect type ONLY for squeeze and slide ('horizontal' or 'vertical')
			effectDirection: 'vertical',

			// prefix (use if you need multiple swapper per page)
			prefix: 'nxSwapper',
			
			// url to the file that generate the JSON
			fileURL: '/assets/jsp/nxswapperimages.jsp',
			
			// open links in a new window
			linkInWindow: false,
			
			// randomely pick a record
			random: false,
			
			// used to pass directly the JSON instead of having the plugin load it
			data: false			
		};
		
		// merge defaults with given settings
		var o = $.extend({}, defaults, settings);		
		
		// data available?
		if (!o.data)
		{
			// get the JSON object
			$.getJSON(o.fileURL, function(d, s)
			{
				// loaded with success
				if (s == 'success')
				{
					// set data & run
					data = d;
					_init();
				}
				else alert(s);
			});
		}
		else
		{
			// set data & run
			data = o.data;
			_init();
		};		
		
		// initialize function
		function _init()
		{		
			// cache array length
			size = data.images.length;
			
			// cache array
			img = data.images;
			
			// cache container width
			swidth = $(self).innerWidth();
			
			// cache container height
			sheight = $(self).innerHeight();
			
			// check for elements
			if (size)
			{			
				// replace content with 2 images tag to the element and hide them
				$(self).html('<div id="'+o.prefix+'Img1"><img></div><div id="'+o.prefix+'Img2"><img></div>');
				
				// image tags css
				$(self).children('div').css(
				{
					position: 'absolute',
					top: 0,
					left: 0,
					zIndex: 800,
					display:'none'
				});
				
				// add div for the on mouse event text
				$(self).prepend('<div></div>').children('div').eq(0).css(
				{
					display: 'none',
					zIndex: 802,
					position: 'absolute'
				}).attr('id',o.prefix+'Text');
				
				// set first image in the first tag and switch z-index
				$('#'+o.prefix+'Img1 > img').attr('src', img[0].src);
				$('#'+o.prefix+'Img1').css('zIndex', 801).show();
				
				// make sure container overflow is hidden
				$(self).css('overflow','hidden');			
				
				// url?
				if (img[0].url)
				{				
					// save url
					url = img[0].url;
					
					// change element cursor
					$(self).css('cursor', 'pointer');
					
					// open link in new window
					if (img[0].linkInWindow) nwin = true;
					else nwin = o.linkInWindow;
					
					// set click event
					$(self).click(function() 
					{ 
						// make sure we have a url
						if (!url) return false;
						
						// new window?
						if (nwin)
						{
							// for new window return false
							window.open(url);
							return false;
						}
						else window.location = url; 
					});
				};
				
				// text?
				if (img[0].text) $('#'+o.prefix+'Text').text(img[0].text);
				
				// on mouse over / out effect
				$(self).hover(function() { if ($('#'+o.prefix+'Text').text()) $('#'+o.prefix+'Text').fadeIn(o.effectSpeed); }
				, function() { if ($('#'+o.prefix+'Text').text()) $('#'+o.prefix+'Text').fadeOut(o.effectSpeed); });

				// make sure we got more than one image before starting process
				// if not there is nothing else to do
				if (size > 1)
				{
					// Set src for second image (so it preload in background)
					$('#'+o.prefix+'Img2 > img').attr('src', img[1].src);
					
					// Set array key (old)
					ok = 0;

					// Set element displayed (1 or 2)
					e = 1;
					
					// Set time out swap
					if (img[0].time) setTimeout(_swap, img[0].time);
					else setTimeout(_swap, o.displayTime);
				};
			};
		};
		
		// swapping function (timed out)
		function _swap()
		{
			// Generate new array key
			if (o.random) nk = _random();
			else nk = ok+1;
			
			// reset needed?
			if (nk == size || ok == nk) nk = 0;
			
			if (e == 1)
			{
				oid = '#'+o.prefix+'Img1';
				nid = '#'+o.prefix+'Img2';
				e = 2;
			}
			else
			{
				oid = '#'+o.prefix+'Img2';
				nid = '#'+o.prefix+'Img1';
				e = 1;
			};
			
			// load image into tag
			$(nid).children('img').attr('src', img[nk].src).onload = _load();
		};
		
		function _load()
		{			
			// reset container
			_reset();
			
			// text?
			if (img[nk].text) $('#'+o.prefix+'Text').text(img[nk].text);
			
			// new effect?
			if (nfx) 
			{
				o.effect = nfx;
				nfx = false;
			};
			
			// specific image effect
			if (img[nk].effect) cfx = img[nk].effect;
			else cfx = o.effect;
			
			// Transition
			switch (cfx)
			{
				// fade
				case 'fade':
					_fade(oid, nid);
						break;
				// squeeze
				case 'curtain':
					_curtain(oid, nid);
						break;
				// slide
				case 'slide':
					_slide(oid, nid);
						break;
				// toggle
				default:
					_toggle(oid, nid);
			};
			
			// set old key
			ok = nk;			
		};
		
		// Generate a random key
		function _random()
		{
			// generate random key
			var rk = Math.floor(Math.random() * size); 
			
			// if random key equal old key just take next key
			if (rk == ok) rk = rk+1;
			
			// return key
			return rk;
		};
		
		// reset function
		function _reset()
		{
			// empty text holder and hide
			$('#'+o.prefix+'Text').text('').hide();
			
			// reset images tag
			$(self).children('div').css(
			{
				height: sheight,
				width: swidth,
				opacity:100,
				top:0,
				left:0
			})
			.show();
			
			// reset container cursor css
			$(self).css('cursor','auto');
			
			// reset url
			url = '';
		};
		
		// sliding function
		function _slide(oid, nid)
		{
			// image effect direction?
			if (img[nk].effectDirection) var fxd = img[nk].effectDirection;
			else var fxd = o.effectDirection;
			
			// effect direction
			if ('horizontal' == fxd)
			{
				// animation settings
				var osets = {left:'-'+swidth};
				var nsets = {left:0};
				
				// move nid to the right of oid
				$(nid).css('left', swidth);
			}
			else
			{
				// animation settings
				var osets = {top:'-'+sheight};
				var nsets = {top:0};
				
				// move nid to the bottom of oid
				$(nid).css('top', sheight);
			};
			
			// animate old out of the way
			$(oid).animate(osets, o.effectSpeed);
			
			// animate new one in
			$(nid).animate(nsets, o.effectSpeed, function()
			{
				_off(oid);
				_on(nid);
			});
		};
		
		// squeezing function
		function _curtain(oid, nid)
		{
			// image effect direction?
			if (img[nk].effectDirection) var fxd = img[nk].effectDirection;
			else var fxd = o.effectDirection;	
			
			// effect direction
			if ('horizontal' == fxd) var sets = {width:0, height:sheight};
			else var sets = {height:0, width:swidth};
			
			// animate
			$(oid).animate(sets, o.effectSpeed, function() 
			{ 
				// sort elements out
				_off(oid); 
				_on(nid);
			});
		};		
			
		// fading function
		function _fade(oid, nid)
		{
			$(oid).fadeTo(o.effectSpeed, 0, function() { _off(oid); });
			$(nid).fadeTo(o.effectSpeed, 100, function() { _on(nid); });
		};
		
		// toggle function
		function _toggle(oid, nid)
		{
			_off(oid);
			$(nid).show();
			_on(nid);
		};
		
		// off function (sort out element hidden)
		function _off(id)
		{
			// switch z-index
			$(id).css('zIndex', 800);
		};
		
		// on function (sort out element showed)
		function _on(id)
		{
			// switch z-index
			$(id).css('zIndex', 801);
			
			// on click url?
			if (img[nk].url)
			{				
				// save url
				url = img[nk].url;
				
				// change element cursor
				$(self).css('cursor','pointer');
				
				// new window settings
				nwin = img[nk].linkInWindow == true ? img[nk].linkInWindow : o.linkInWindow;
			};
			
			// text (used on mouseover)
			if (img[nk].text) $('#'+o.prefix+'Text').text(img[nk].text);
			
			// set time out for next swap
			if (img[nk].time) setTimeout(_swap, img[nk].time); 
			else setTimeout(_swap, o.displayTime);
		};
		
		// public method to allow property value change on the fly
		$.fn.nxSwapper.set = function(property, value)
		{
			// property exists
			if (o[property])
			{
				// if effect dont change straight away (avoid bug if animation in progress)
				if ('effect' == property) nfx = value;
				else o[property] = value;
				
				// success
				return true;
			}
			
			// failed
			else return false;
		};
		
		// public method to get property value
		$.fn.nxSwapper.get = function(property)
		{
			// return property value
			return o[property];
		};
	};
	
})(jQuery);
