// EffectChain, JQuery plugin
// v 1.0 
// Licensed under GPL licenses.
// Copyright (C) 2008 Nikos "DuMmWiaM" Kontis, info@dummwiam.com
// http://www.DuMmWiaM.com/EffectChain
// ----------------------------------------------------------------------------
// Permission is hereby granted, free of charge, to any person obtaining a copy
// of this software and associated documentation files (the "Software"), to deal
// in the Software without restriction, including without limitation the rights
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
// copies of the Software, and to permit persons to whom the Software is
// furnished to do so, subject to the following conditions:
// 
// The above copyright notice and this permission notice shall be included in
// all copies or substantial portions of the Software.
// 
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
// THE SOFTWARE.
// ----------------------------------------------------------------------------

(function($) 
{
	// plugin definition
	$.fn.EffectChain = function(options) 
	{
		// build main options before element iteration
		var opts = $.extend({}, $.fn.EffectChain.defaults, options);

		//parameters
		var $duration = opts.duration * 1000;
		var $effect = opts.effect;
		var $onComplete = opts.onComplete;
		var $onStep = opts.onStep;
		var $delay = opts.delay * 1000;
		var $order = String(opts.order).toLowerCase();
		var $animateParams = opts.animateParams;
		var $fadeToOpacity = opts.fadeToOpacity;
		//variables
		var $aItems = new Array();
		var $counter = 0;
		var $nItems = this.length;
		var $nInterval = 0;

	
		this.each(function() {
			var _this = $(this);			
			$aItems.push(_this);
		});//this.each

		switch ($order)
		{
			case "reverse":
				$aItems.reverse();
			break;
			
			case "random":
				$aItems = ArrayShuffler($aItems);
			break;
		}

		startNextStep();

		function startNextStep()
		{
			if ($delay) {clearInterval($nInterval);}
			
			switch ($effect)
			{
			case "animate":
				if (!$animateParams) {return false;}//if no parameters specified exit
				$aItems[$counter][$effect]($animateParams,$duration,validateNextStep);	
			break;
			
			case "fadeTo":
				$aItems[$counter][$effect]($duration,$fadeToOpacity,validateNextStep);	
			break;
			
			default:
				$aItems[$counter][$effect]($duration,validateNextStep);			
			break;
			}
			
		};
		
		function validateNextStep()
		{
			if ($onStep){ $onStep();}
			$counter++;
			if($counter < $nItems)
			{
				if ($delay)
				{
					$nInterval = setInterval(startNextStep,$delay);
				}
				else
				{
					startNextStep();
				}
			}
			else //final call here, end
			{
				if($onComplete)	{$onComplete();}
				$aItems = null;
			}
		};
		
		function ArrayShuffler(v){
			for(var j, x, i = v.length; i; j = parseInt(Math.random() * i), x = v[--i], v[i] = v[j], v[j] = x);
			return v;
		};
		
		return this;
		// plugin defaults
	}
	$.fn.EffectChain.defaults = {duration : 1,order:null,effect:"hide",animateParams:null,fadeToOpacity:0.1,delay:0,onStep:null,onComplete:null};
})(jQuery);
