﻿/* 
 * v0.x
 * Author: Martin Veith
*/
(function($) {
	$.fn.XQSlide = function(options) {
		// init XQ 
		$.XQ = $.XQ || {};
		
		$.XQ.Slide = $.XQ.Slide || {};
		
		// default settings
		var settings = {
			// FINAL (unordered)
			autoplay : true,
			carousel : true,
			interval : 3000,
			clickable : true,
			startIndex: 1,
			onPlay : null,
			onPause : null,
			onStop : null,
			onPrevious : null,
			onNext : null,
			onRotateBefore : null,
			onRotate : null,
			onRotateAfter : null,
			ContainerSelector : ".xqslide-container",
			NavigationSelector : ".xqslide-navigation",
			ToolbarSelector : ".xqslide-toolbar",
			ItemSelector : ".xqslide-item",
			pauseOnHover : false,
			transition : "default",
			KeyboardNav : 250,
			preloading : 0,
			preloadingBehaviour : "wait"
		};

		$.XQ.IsUndefined = function(type)
		{
			return typeof type == "undefined" | type === null;	
		}
		
		$.XQ.IsFunction = function(type)
		{
			return typeof type == "function";	
		}

		$.XQ.Slide.Transitions = {
			transitions : {
				"default" : function(transition) {
					this.getCurrentPane().hide();       
					this.getActivePane().show();
					this.finish();	
				},			
				
				"fade" : function(transition) {
					var toptions = $.extend({fadeInSpeed : 444, fadeOutSpeed : 444}, transition),
						t = this,
						
						$active_pane = t.getActivePane(),
						webkit = false & $.browser.webkit; // & window.location.href.indexOf("jstest") > -1;
					
					if(webkit)
					{
						//fade out 
						this.getCurrentPane().show().css({"-webkit-transition" : "opacity " + (Math.min(toptions.fadeInSpeed, toptions.fadeOutSpeed) / 1000) + "s linear"});  
						this.getCurrentPane().css({"opacity" : 0});
						
						//fade in
						$active_pane.animate({opacity : 0}, 100, function() { 
							$active_pane.show().css({"opacity" : 0}).css({"-webkit-transition" : "opacity " + (toptions.fadeInSpeed / 1000) + "s linear"});
							$active_pane.css({"opacity" : 1}).animate({textIndent : 0}, toptions.fadeInSpeed, function() {	
								t.finish();			
							});
						});
					}
					else
					{
						//fade out 
						this.getCurrentPane().show().fadeOut(Math.min(toptions.fadeInSpeed, toptions.fadeOutSpeed));  
						
						//fade in
						this.getActivePane().stop(true, true).fadeIn(toptions.fadeInSpeed, function() { t.finish(); });
					}
				},
				
				"slide" : function(transition) {
					var toptions = $.extend({Speed : 1000, Direction : "horizontal", easing : "linear"}, transition),
						t = this,
					
						xclass = "xqslider",
						$panes = this.getPanes(),
						$container = this.getContainer(),
						$slider = $($container.find(".xqslider")[0]),
						
						Index = this.getIndex(),
						CurrentIndex = this.getCurrentIndex(),
						
						horizontal = (toptions.Direction == "horizontal" || (toptions.Direction == "random" & Math.round(Math.random()))) || (toptions.Direction != "vertical" & toptions.Direction != "random"),
						container_size = horizontal ? $container.innerWidth() : $container.innerHeight(),
						full_size = container_size * $panes.length,
						to_slide = container_size * Index * -1,
						margin = CurrentIndex * container_size * -1,
						cross = false,
						cross_size = full_size * -1,
						
						webkit = $.browser.webkit && (navigator.userAgent.match(/iPad/i) || navigator.userAgent.match(/iPhone/i) || navigator.userAgent.match(/iPod/i) || navigator.userAgent.match(/Android/i)), // & window.location.href.indexOf("jstest") > -1;
						webkit_plugin = false, //window.location.href.indexOf("noplugin") > -1;
						webkit_cache = true; //window.location.href.indexOf("cache") > -1;

					$panes.css({position: "relative", "float" : "left"}).show();
					if(!$panes.parent("." + xclass).length)
					{
						$panes.wrapAll('<div class="' + xclass + '"></div>');
					}
					
					$slider = $($container.find("." + xclass)[0]).css("position", "relative");
					$panes.css({height: $container.innerHeight()});
									





					var action = t.log[t.log.length - 1]; 
								
					to_slide_cross = to_slide;			
					if(settings.carousel & action != "show")
					{
						if(Index == $panes.length - 1 & CurrentIndex == 0)
						{
							to_slide = container_size;
							if(action == "next") { cross_size = 0; to_slide = container_size * ($panes.length - 1) * -1; }
							//if (webkit && !webkit_plugin) to_slide = container_size * ($panes.length - 1) * -1;
							cross = true;
							
							to_slide_cross = 0;
						}
						else if(Index == 0 & CurrentIndex == $panes.length - 1)
						{	
							margin = container_size; 	
							to_slide_cross = container_size;
							if(action == "previous") { cross_size = 0; margin = container_size * -1; if($panes.length <= 2) to_slide_cross = container_size * -1; }
							
							cross = true;
						}	
					}
					
					var $pane = t.getCurrentPane(),
						$cache_pane = $pane.next();
					
					if(action == "next")
					{
						if(cross & $panes.length > 2) {
							$cache_pane = $panes.first();
						}
						else
							$cache_pane = $pane.next();
					}
					
					if(action == "previous")
					{
						if(cross)
							$cache_pane = $panes.last();
						else
							$cache_pane = $pane.prev();
					}
					
					if(action == "show")
					{
						$cache_pane = $($panes[Index]);	
					}

					if(webkit && webkit_cache && (navigator.userAgent.match(/iPad/i) || navigator.userAgent.match(/iPhone/i) || navigator.userAgent.match(/iPod/i) || navigator.userAgent.match(/Android/i)))
					{ 
						if($panes.length > 2)
							$panes.not($pane).not($cache_pane).find("img").css({"-webkit-transform-style" : "", "-webkit-transform": ""});

						$cache_pane.find("img").css({"-webkit-transform": "translate3d(0, 0, 0)"});
						$pane.find("img").css({"-webkit-transform": "translate3d(0, 0, 0)"});
					}
					
					t.log = [];
			
					if(horizontal)
					{
						if(webkit && !webkit_plugin)
						{
							$slider.stop(true, true).css({width : full_size}); 
							$slider[0].style.webkitTransform = "translate3d(" + margin + "px, 0, 0)";
							$slider[0].style.webkitTransitionDuration = "";
						}
						
						if(webkit)
							$slider.stop(true, true).css({width : full_size});
						else
							$slider.stop(true, true).css({width : full_size, left : margin});
				
						if(cross)
						{ 
							$panes.last().stop(true, true).css({left : cross_size});
						
							if(webkit)
							{
								to_slide_i = {"-webkit-transform" : "translate3d(" + to_slide_cross + "px, 0, 0)", "-webkit-transition-duration" : ""};	

								//$slider.css(to_slide_i);
								$slider[0].style.webkitTransitionDuration = "";
								$slider[0].style.webkitTransform= "translate3d(" + to_slide_cross + "px, 0, 0)";
						
								if($panes.length > 2)
								{
									if(to_slide_cross == 0)
										to_slide = container_size;	
									else
										to_slide = 0;
								}
							}
						}
						
						if(webkit)
						{
							to_slide_new = to_slide;
							to_slide = {webkitTransform : "translate(" + to_slide + ",0)"};
						}
						else
							to_slide = {left : to_slide};
					}
					else
					{
						$slider.stop(true, true).css({width : container_size, height : full_size, marginTop : margin});
						if(cross)
							$panes.last().stop(true, true).css({top : cross_size});
						to_slide = {marginTop : to_slide};
					}
		
					if(webkit && !webkit_plugin)
					{ 
						var time = new Date().getTime();
						
						//$panes.css({"-webkit-transform": "translate3d(0, 0, 0)"});

						//to_slide = {"-webkit-transform" : "translate3d(" + to_slide_new + "px, 0, 0)", "-webkit-transition-delay" : "now", "-webkit-transition-duration" : (toptions.Speed / 1000) + "s"};
				
						$slider.animate({opacity : 1}, 100, function() { 
							$slider[0].style.webkitTransitionDuration = (toptions.Speed / 1000) + "s";
							$slider[0].style.webkitTransform= "translate3d(" + to_slide_new + "px, 0, 0)";
							
							$slider.animate({opacity : 1}, toptions.Speed, function() {	
																								  
								$panes.last().css({left : 0});
								
								//$slider.css({"-webkit-transform" : "translate3d(" + container_size * Index * -1 + "px, 0, 0)", "-webkit-transition-duration" : ""});	
								$slider[0].style.webkitTransitionDuration = "";
								$slider[0].style.webkitTransform= "";
								
								t.setPaneStyles(Index);	
								$slider.css("left", 0);
								
								t.finish();			
							});
						});
					}
					else	
					{
						$slider.stop(true, true).animate(to_slide, toptions.Speed, toptions.easing, function() { 
							/*if(horizontal)
								$slider.css({width: container_size, left : 0});
							else
								$slider.css({height: container_size, top : 0});*/
							
							/*if(webkit && webkit_cache > -1)
							{
								$panes.find("img").css({"-webkit-transform-style" : "", "-webkit-transform": ""});
							}*/
							
							//reset panes
							if(!webkit)
								t.setPaneStyles(Index);	
								
							$slider.css("left", 0);
							
							t.finish();
						});
					}
				}
			},
			
			addTransition : function(name, fn)
			{
				$.XQ.Slide.Transitions.transitions[name] = fn;
			},
			
			doTransition : function(obj, transitions)
			{
				var transition = $.XQ.Slide.Transitions.validateTransition(obj, transitions, obj.getIndex());			
				$.XQ.Slide.Transitions.transitions[transition.name].call(obj, transition);


			},
			
			validateTransition : function(obj, transitions, index)
			{
				var transition = transitions;
				
				if(typeof transition == "object")
				{

					if(transitions[index] != undefined)
						transition = transitions[index];
				}

				if(transition.name == undefined)
					if(typeof transition == "string")
						transition = {
							name : transition
						};
					else
						transition.name = "default";

				if(transition.name == "random")
				{
					var transitions_length = 0;
					for(var random_transition in $.XQ.Slide.Transitions.transitions)
					{
						transitions_length++;	
					}
					
					var random_transition_index = Math.floor(Math.random() * transitions_length),
						i = 0;
					
					for(random_transition in $.XQ.Slide.Transitions.transitions)
					{
						if(i == random_transition_index)
						{
							transition = {
								name : random_transition
							};
							break;
						}
						i++;
					} 			
				}

				if($.XQ.Slide.Transitions.transitions[transition.name] == undefined)
					transition.name = "default";
					
				return transition;
			}
		};
		
		var SlideShow = function($slideshow, options)
		{
			var $slideshow = $slideshow, 
				$panes, $container, $navigation = [],
		   
				Timeout = "",
			
				Index, CurrentIndex = 0,
		   
		   		images = [],
				randoms = [],

				init = false,
				obj = this,
				
				States = {
					Started : false,
					Stopped : false,
					RotationStopped : false,
					Paused : false,
					Rotation : false
				};
				
			this.log = [];
		
			$.extend(this, {
				getSlideShow : function()
				{
					return $slideshow;
				},
				
				getContainer : function()
				{
					return $container;
				},
				
				getIndex : function()
				{
					return Index;
				},
			   
				getCurrentIndex : function()
				{
					return CurrentIndex;
				},
				
				getStates : function()
				{
					return States;
				},
				
				getTabs : function(index)
				{   
					if(typeof index == "number")
						return $($("a", $navigation).not(".next, .previous")[index]);
						
					return $("a", $navigation).not(".next, .previous");
				},
			   
				getActiveTab : function()
				{   
					return this.getTabs(Index);
				},
		
				getCurrentTab : function()
				{   
					return this.getTabs(CurrentIndex);
				},
				
				getInactiveTabs : function()
				{
					return this.getTabs().not(this.getActiveTab());
				},
			   
				getPanes : function()
				{
					return $panes;
				},
			   

				getActivePane : function()
				{
					return $($panes[Index]);
				},
		
				getCurrentPane : function()
				{
					return $($panes[CurrentIndex]);
				},
				
				getInactivePanes : function()
				{
					return $panes.not(this.getActivePane());
				},
				
				getImages : function()
				{
					return images;
				},
				
				setSettings : function(options)
				{
					var startIndex = settings.startIndex;
					$.extend(settings, options || {});	
					
					$slideshow.add(obj);
					$panes = $(settings.ItemSelector, $slideshow); 
					$container = $panes.parents(settings.ContainerSelector); 
					$navigation = $(settings.NavigationSelector, $slideshow);
					$toolbar = $(settings.ToolbarSelector, $slideshow);
	
					if(typeof options.startIndex != undefined)
						settings.startIndex = getRotationIndex(settings.startIndex - 1);
					else
						settings.startIndex = startIndex;
		
					//clickable
					if(settings.clickable)
					{
						$panes.click(function() {
							obj.next(true);	
							return false;
						});
					}
					
					setStates({Started : settings.autoplay, Paused : !settings.autoplay, Stopped : !settings.autoplay});
				
					//pause slideshow on hover
					if(settings.pauseOnHover)
					{
						$container.hover(this.pause, function() { if(!States.Rotation & !States.Stopped & !States.RotationStopped) { obj.play(); } });
					}
				},
				
				getSettings : function()
				{
					return settings;
				},
				
				getInterval : function() 
				{
					if(typeof settings.interval != "number")
						return settings.interval[Index];
					
					return settings.interval;
				},
		   
				play : function()
				{	 
					window.clearTimeout(Timeout);
					setStates({Started : false, RotationStopped : false, Stopped : false, Paused : false});
					if($.isFunction(settings.onPlay)) settings.onPlay.call(this);
					rotate();
				},
			
				stop : function()
				{
					window.clearTimeout(Timeout);
					if(States.Stopped)
						return;
						
					setStates({Stopped : true, RotationStopped : false, Paused : false});
					
					if($.isFunction(settings.onStop)) settings.onStop.call(this);
					randoms = []; 
					rotate({index : settings.startIndex, random : false});
					setStates({Started : false});
				},
			   
				pause : function()
				{
					setStates({Paused : true});
					if($.isFunction(settings.onPause)) settings.onPause.call(this);
					window.clearTimeout(Timeout);
				},
			   
				show : function(index, stop)
				{
					if(index == Index | States.Rotation) 
						return; 
					window.clearTimeout(Timeout);
					setStates({Started : true, RotationStopped : stop, Stopped : false, Paused : false}); 
					obj.log.push("show");
					if($.isFunction(settings.onShow)) settings.onShow.call(this); 
					rotate({index : index, random : false});   
				},
			   
				previous : function(stop)
				{
					if(States.Rotation) return; 
					setStates({Started : true, RotationStopped : stop, Stopped : false, Paused : false});
					obj.log.push("previous");
					if($.isFunction(settings.onPrevious)) settings.onPrevious.call(this);
					rotate({index : Index - 1});
				},  
			   
				next : function(stop)
				{ 
					if(States.Rotation) return;  
					setStates({Started : true, RotationStopped : stop, Stopped : false, Paused : false});
					obj.log.push("next");
					if($.isFunction(settings.onNext)) settings.onNext.call(this);
					rotate({index : Index + 1});
				},
			
				setPaneStyles : function(index)
				{
					var count = $panes.length,
						$pane = $($panes[index]);
					
					//style panes
					$panes.not($pane).hide();
					
					$panes.stop(true, true).each(function(index) {
						if(!$(this).find("object").length)
							$(this).css({position : "absolute"});
						$(this).css({zIndex : count * 10 - index, top : 0, left : 0, margin : "auto"});
					});
				},
				
				finish : function() { 
					setStates({Rotation : false}); 	 
					if($.isFunction(settings.onRotateAfter)) settings.onRotateAfter.call(obj);
					
					if(!States.Stopped & !States.Paused & !States.RotationStopped & obj.getInterval() > 0)
					{	
						Timeout = window.setTimeout(function() { 
							obj.next();	
						}, this.getInterval());
					}
					else
						$(".xqslide-progress").stop(true, true).css({width : 0});
				}
			});
							   
			var rotate = function(rotation) { 
				window.clearTimeout(Timeout);
				if(States.Paused)
					return;
				
				if(!States.Stopped)
				{
					setStates({Rotation : true});
			
					if(States.Started)
					{	
						setRotationSettings(rotation); 
						if($.isFunction(settings.onRotateBefore)) settings.onRotateBefore.call(obj);
						setToolbar();

						//onImagesLoaded();
						$.XQ.Slide.Transitions.doTransition(obj, settings.transition); 
						$slideshow.bind(Index + "onImagesLoaded", onImagesLoaded);		
						loadImages(Index);	

						//$.XQ.Slide.Transitions.doTransition(obj, settings.transition); 
					}
					else
					{ 
						obj.finish();
						setStates({Started : true});
					} 
				}
			};
			
			var onImagesLoaded = function() { 
				if($.isFunction(settings.onRotate)) settings.onRotate.call(obj);
			
				$slideshow.unbind(Index + "onImagesLoaded", onImagesLoaded);	
				
				//$.XQ.Slide.Transitions.doTransition(obj, settings.transition); 
			};
			
			var setIndex = function(index, random)
			{
				var final_index, random_index = 0;
		
				if(random)
				{  
					if(randoms.length == $panes.length)
					{ 
						randoms = []; 
						if(!settings.carousel)
						{
							obj.stop();
							final_index = settings.startIndex;
						}
					}
		
					while(final_index == undefined)
					{
						random_index = Math.floor(Math.random() * $panes.length);
						if(settings.carousel)
							random_index = getRotationIndex(random_index);
							
						if(random_index == Index & randoms.length + 1 < $panes.length) {
							continue;
						}
		
						for(var i = 0; i < randoms.length; i++)
						{
							if(random_index == randoms[i])
							{
								break; 
							}
						}
						
						if(random_index == randoms[i]) {
							continue;
						}
						
						final_index = random_index;
					} 
				}
				else
				{
					final_index = getRotationIndex(index);    
				}
				
				randoms.push(final_index);
		
				setCurrentIndex(Index);
					
				Index = final_index;  
				setNavigationStyles();
			};	
				
			var setCurrentIndex = function(index)
			{
				CurrentIndex = index;
			};
			
			var setStates = function(states)
			{		
				$.extend(States, states);
				setToolbar();
			};
			
			var getRotationIndex = function(index)
			{
				if(settings.carousel)
				{
					if(index > $panes.length - 1)
					{
						index = 0;
					}
					else if(index < 0) 
					{
						index = $panes.length - 1;
					}
				}
				else
				{
					if(index > $panes.length - 1)
					{
						obj.stop();
						index = settings.startIndex;
					}
					else if(index < 0) 
					{
						index = 0;
					}
				}
				
				return index;
			};
			
			var setRotationSettings = function(rotation)
			{
				var default_rotation = {
						index : Index,
						random : settings.random
					},
					i_random = false;
				
				if(typeof rotation != "undefined" && typeof rotation.random != "undefined")
				{
					i_random = rotation.random;
					rotation.random = i_random;
				}
		
				$.extend(default_rotation, rotation);
				rotation = default_rotation;
			   
				rotation.index = getRotationIndex(rotation.index);
					
				setIndex(rotation.index, rotation.random);
			 
				return rotation;
			};
			
			var setPanes = function(index)
			{
				setIndex(settings.startIndex);
				setCurrentIndex(settings.startIndex);
		
				obj.setPaneStyles(settings.startIndex);
				
				if(settings.preloading != 0)
					obj.getPanes().not($($panes[settings.startIndex])).addClass("item-loading");
			};
			
			var setToolbar = function(index)
			{
				$("li", $toolbar).show();
				var $pause = $(".pause", $toolbar),
					$play = $(".play", $toolbar),
					$stop = $(".stop", $toolbar);
					
				$stop.find("a").removeClass("disabled");
							
				if(States.Started & !States.RotationStopped)
				{
					$play.hide();
					$pause.show();
				}
				
				if(States.Paused | States.RotationStopped)
				{
					$pause.hide();
					$play.show();
				}
		
				if(States.Stopped)
				{
					$pause.hide();
					$play.show();
					$stop.find("a").addClass("disabled");
				}
			};
		   
			var initNavigation = function()
			{
				var $tabs = obj.getTabs().show(),
					$previous = $(".previous", $slideshow),
					$next = $(".next", $slideshow);
		
				$previous.click(function() {   
						if(!$(this).parents(".disabled").length & !$(this).hasClass("disabled"))
							obj.previous(true);
							
						return false;
					});
		
				$next.click(function() {    
						if(!$(this).parents(".disabled").length && !$(this).hasClass("disabled"))
							obj.next(true);

						return false;
					});
		
				$tabs.each(function(index) {
					$(this)
						.click(function() { 
							if(!$(this).parents(".disabled").length && !$(this).hasClass("disabled"))
								obj.show(index, true);
						
							return false;
						});
				});
		
				setNavigationStyles();
			};
			
			var initKeyboardNav = function() 
			{
				var keyboard_nav = obj.getSettings().KeyboardNav;
				if(!keyboard_nav)
					return;
				
				if(keyboard_nav != -1)
				{
					$(document).bind("mousemove", function(e) {
						var offset = $slideshow.offset();
			
						obj.hovered = e.pageX >= offset.left - keyboard_nav & e.pageX <= offset.left + $slideshow.width() + keyboard_nav
							& e.pageY >= offset.top - keyboard_nav & e.pageY <= offset.top + $slideshow.height() + keyboard_nav;
					});
				}
				
				$(document).bind("keydown", function(e) { 
					if(!obj.hovered & keyboard_nav != -1)
						return;
						
					if (e.which == 37 | e.which == 38) {
						e.preventDefault();
						obj.previous(1);
					} else if (e.which == 39 | e.which == 40) {
						e.preventDefault();
						obj.next(1);
					}
				});
			};
			
			var setNavigationStyles = function()
			{
				var $tabs = obj.getTabs().show(),
					$previous = $(".previous", $slideshow),
					$next = $(".next", $slideshow),
					index = Index,
					length = $panes.length;
				
				if(!settings.carousel & !settings.random)
				{
					if(index == 0)

					{
						$previous.addClass("disabled");
						$previous.find("a").addClass("disabled");
					}
					else
					{
						$previous.removeClass("disabled");
						$previous.find("a").removeClass("disabled");
					}
					
					if(index == length - 1)
					{
						$next.addClass("disabled");
						$next.find("a").addClass("disabled");
					}
					else
					{
						$next.removeClass("disabled");
						$next.find("a").removeClass("disabled");
					}
				}
			};
			
			var checkImagesToLoad = function(indexes, index) {
				var $loader = $slideshow.find(".loader");
			
				images[indexes[index]].$images_to_load.not(".loaded").each(function(image_index) { 
					var $img = $(images[indexes[index]].$images_to_load[image_index]),
						img = null;
						
					if($img.length == 0)
						return;
					
					if($.XQ.IsUndefined($img.data("img"))) {
						img = new Image();
						
						if($.XQ.IsUndefined($img.data("loaded")))
						{
							$img.data("loaded", false); 
							$(img).load(function() {
								$img.data("loaded", true);	
							});
						}
						
						if($.XQ.IsUndefined($img.data("error"))) {
							$img.data("error", false);	
							$(img).error(function() {  
								$img.data("error", true);
							});		
						}
						
						img.src = $.XQ.IsUndefined($img.attr("data-src")) ? $img.attr("src") : $img.attr("data-src");
						
						$img.data("img", img);
					}
					else 
						img = $img.data("img");

					if(img.readyState == 4 | img.readyState == "complete")
						$(img).trigger("load");
	
					if($img.data("error") | $img.data("loaded"))
					{ 
						images[indexes[index]].to_load--;
						
						$img.attr("src", img.src);
						$img.removeClass("loading").addClass("loaded");

						images[indexes[index]].$images_to_load = images[indexes[index]].$images_to_load.not($img);
					
						if(images[indexes[index]].to_load <= 0)
						{  		
							clearTimeout(images[indexes[index]].loader_timeout);
							clearInterval(images[indexes[index]].interval);	
					
							if(Index == indexes[index])
							{
								$(obj.getPanes()[Index]).removeClass("item-loading").find(".item-content").fadeIn(400);
								$loader.stop().fadeOut(250);
								
								$slideshow.trigger(indexes[index] + "onImagesLoaded");
							}
							
							if(indexes.length && index < indexes.length - 1)
							{
								prepareImageLoad(indexes, index + 1);	
							}
						}
					}
				});
				
				return images[indexes[index]];
			};
			
			var prepareImageLoad = function(indexes, index)
			{
				var $loader = $slideshow.find(".loader").hide(),
					$pane = $($panes[indexes[index]]),
					$images = $pane.filter("img").add($pane.find("img"));

				if($.XQ.IsUndefined(images[indexes[index]])) { 
					images[indexes[index]] = {
						$images : $images,
						$images_to_load : $images,
						loading : false,
						to_load : $images.length,
						interval : "",
						loader_timeout : ""
					}; 
				}

				if(images[indexes[index]].to_load)
				{
					$slideshow.stop(true, true);

					if(Index == indexes[index])
					{
						$(obj.getPanes()[Index]).find(".item-content").hide();
						images[indexes[index]].loader_timeout = setTimeout(function() { if(images[indexes[index]].to_load > 0 && Index == indexes[index]) { $(obj.getPanes()[Index]).addClass("item-loading"); $loader.show(); } }, 100);
					}
					
					checkImagesToLoad(indexes, index);									
				
					if(images[indexes[index]].to_load)
					{							
						images[indexes[index]].loading = true;

						images[indexes[index]].interval = setInterval(function() {    
							checkImagesToLoad(indexes, index); 
						}, 1);
					}
				}
				
				if(images[indexes[index]].to_load <= 0 & Index == indexes[index]) { 
					$(obj.getPanes()[Index]).removeClass("item-loading").find(".item-content").fadeIn(400);
				
					$slideshow.trigger(indexes[index] + "onImagesLoaded");		
					
					if(indexes.length && index < indexes.length - 1)
					{
						prepareImageLoad(indexes, index + 1);	
					}
				}
			}
			
			var loadImages = function(index, init) { 			
				if(settings.preloading == 0)
				{
					$slideshow.trigger(index + "onImagesLoaded");
					return;	
				}
				
				//var $loader = $slideshow.find(".loader").hide();
				
				if(!init)
				{
					//$container.after('<div class="loader"></div>');
				}

				/*if(!$.XQ.IsUndefined(images[index]))
				{
					if(Index == index)
						$slideshow.trigger(index + "onImagesLoaded");	
					
					return images[index];
				}*/

				var $panes = obj.getPanes(),
					indexes = [index],
					max_preload = settings.preloading == -1 ? $panes.length - 1 : Math.min($panes.length - 1, settings.preloading),
					new_index = index;
					
				for(var i = 0; i < max_preload; i++)
				{
					new_index++;
					
					if(new_index > $panes.length - 1)
					{					
						new_index = 0;
					}
					
					indexes.push(new_index);
				}
		
				//if(!init)
				//	indexes.push(getRotationIndex(index + 1));
				
				var i = 0;
				//for(var i = 0; i < indexes.length; i++) {
				//	(function(i){
						prepareImageLoad(indexes, i);
					//})(i);
				//}
									 
				return images[index];
			};
			
			var onScrollVisibleArea = function() {
				if((obj.slideshow_height + $slideshow.offset().top) < $(document).scrollTop())
				{
					if(!States.Paused)
						obj.pause();	
				}
				else if(!States.Stopped & States.Paused & !States.Rotation & !States.RotationStopped)
					obj.play();
			};
			
			(function() {
				obj.setSettings(options);

				setPanes();
				setToolbar();
				if(false && $.browser.webkit && (navigator.userAgent.match(/iPad/i) || navigator.userAgent.match(/iPhone/i) || navigator.userAgent.match(/iPod/i) || navigator.userAgent.match(/Android/i)))
					$panes.each(function() { $(this)[0].style.webkitTransform = "translate3d(0, 0, 0)"; });
				
				obj.slideshow_height = $slideshow.height();
			
				initNavigation();
				
				if(true)
				{
					$slideshow.bind(settings.startIndex + "onImagesLoaded", function() { 	 
						$slideshow.unbind(settings.startIndex + "onImagesLoaded");
									
						if($.isFunction(settings.onInit)) settings.onInit.call(obj);
						
						if($panes.length > 1)
						{
							initKeyboardNav();
							
							if(settings.autoplay)
								obj.play();
							else
								setStates({Started : true});
						
							onScrollVisibleArea();
							$(window).bind("scroll", onScrollVisibleArea);
						}
						
						init = true;
					});		
					loadImages(settings.startIndex, true);
				}
				else
				{
					if($.isFunction(settings.onInit)) settings.onInit.call(obj);
					
					if(settings.autoplay)
						obj.play();
					else
						setStates({Started : true});
				
					onScrollVisibleArea();
					$(window).bind("scroll", onScrollVisibleArea);
				}
			})();
		};
		
		return this.each(function()
       	{
        	var $this = $(this);

			if($this.data('SlideShow')) 
				return;
				
			SlideShow = new SlideShow($(this), options);
				
			$this.data('SlideShow', SlideShow);		
       });	
	};
})(jQuery);
