/*
* Slides, A Slideshow Plugin for jQuery
* Intructions: http://slidesjs.com
* By: Nathan Searles, http://nathansearles.com
* Version: 1.1.9
* Updated: September 5th, 2011
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
(function($){
	$.fn.sliderInit = function( constructor, op ) {
		var elem = $(this);
		var home = parseInt(elem.attr('iuid'));
		if(!home){
			home = $.slider.hash.length;
			elem.attr('iuid',home);
		}
		
		if($.slider.hash[home])return this;
		
		var h = {
			jqObject: elem,
			items: [],
			itemConst: function(d){this.data=d},
			sliderSettings: {
				preload: false, // boolean, Set true to preload images in an image based slideshow
				preloadImage: '/img/loading.gif', // string, Name and location of loading image for preloader. Default is "/img/loading.gif"
				container: 'slides_container', // string, Class name for slides container. Default is "slides_container"
				generateNextPrev: false, // boolean, Auto generate next/prev buttons
				next: 'next', // string, Class name for next button
				prev: 'prev', // string, Class name for previous button
				pagination: true, // boolean, If you're not using pagination you can set to false, but don't have to
				generatePagination: true, // boolean, Auto generate pagination
				prependPagination: false, // boolean, prepend pagination
				paginationClass: 'pagination', // string, Class name for pagination
				currentClass: 'current', // string, Class name for current class
				fadeSpeed: 350, // number, Set the speed of the fading animation in milliseconds
				fadeEasing: '', // string, must load jQuery's easing plugin before http://gsgd.co.uk/sandbox/jquery/easing/
				slideSpeed: 350, // number, Set the speed of the sliding animation in milliseconds
				slideEasing: '', // string, must load jQuery's easing plugin before http://gsgd.co.uk/sandbox/jquery/easing/
				start: 1, // number, Set the speed of the sliding animation in milliseconds
				effect: 'slide', // string, '[next/prev], [pagination]', e.g. 'slide, fade' or simply 'fade' for both
				crossfade: false, // boolean, Crossfade images in a image based slideshow
				randomize: false, // boolean, Set to true to randomize slides
				play: 0, // number, Autoplay slideshow, a positive number will set to true and be the time between slide animation in milliseconds
				pause: 0, // number, Pause slideshow on click of next/prev or pagination. A positive number will set to true and be the time of pause in milliseconds
				hoverPause: false, // boolean, Set to true and hovering over slideshow will pause it
				autoHeight: false, // boolean, Set to true to auto adjust height
				autoHeightSpeed: 350, // number, Set auto height animation time in milliseconds
				bigTarget: false, // boolean, Set to true and the whole slide will link to next slide on click
				animationStart: function(){}, // Function called at the start of animation
				animationComplete: function(){}, // Function called at the completion of animation
				slidesLoaded: null, // Function is called when slides is fully loaded
				datasource: null,
				loadOnInit: true,
				on_load_complete: null,
				showEmptySlider: false,
				emptyImg: null,
				imgPath: '',
				dopHTML: '',
				eventName: null
			},
			totalCount: 0,
			home: home,
			state: 0
		};
		
		if(typeof constructor == 'function')h.itemConst = constructor;
		if(typeof constructor == 'object')op = constructor;
		
		// override defaults with specified op
		h.sliderSettings = $.extend(h.sliderSettings,op);
		elem.html(h.sliderSettings.dopHTML+'<div class="slides_container"><div class="slides_control"/></div>');
		h.control = $('.slides_control',elem);
		
		
		
		if(!$.slider.hash[home]){
			$.slider.hash[home] = h;
			if(h.sliderSettings.datasource && h.gridSettings.loadOnInit){
				this.sliderLoad();
			}else{
				//$.slider.render(this);
			}
		}
		return this;
	};
	$.fn.sliderLoad=function(ds,clear,callback){
		var t = this;
		var h = t.sliderHash();
		if(!h){		
			console.log(t);
			console.log(t.gridHash());
			alert('Error! Press F5.');
			return false;
		}
		$.slider.stop(t);
		
		if(typeof ds == 'function'){
			callback = ds;
			clear = true;
			ds = h.sliderSettings.datasource;
		}else if(typeof ds == 'boolean'){
			callback = clear;
			clear = ds;
			ds = h.sliderSettings.datasource;
		}else if(typeof ds == 'undefined'){
			ds = h.sliderSettings.datasource;
			clear = true;
		}
		
		if(h.sliderSettings)
			h.sliderSettings.datasource = ds;
		else{
			console.log(h);
			alert('Error! Press F5.');
			return false;
		}
		
		if(typeof clear=='undefined')clear = false;
		
		$.getJSON(ds+'&time='+escape(Date()),function(data){
			if(data.errcode && data.errcode!=0)return false;
			t.sliderAdd(data,clear);
			if(typeof h.sliderSettings.on_load_complete == 'function')
				h.sliderSettings.on_load_complete(h);
			if(typeof callback == 'function')callback(h,data);
		});
		return this;
		/* }}} */
	};	
	$.fn.sliderAdd=function(x,clear){
		/* 
		**	@description	Добавляет данные в слайдер
		**	@param 			x: object - данные, полученные от сервера
		**	Структура данных:
		**	x = [{
		**		'Path': 	'',	путь к картинке
		**		'ID':		0,	или номер к картинке
		**		'Title':	'',	заголовок
		**		'Content':	''	описани
		**	},....
		**	]		
		**
		**	@param 			clear: boolean - флаг необходимости очистки кэша данных
		**	@return 		jquery
		*/
		
		// Проверка параметров 
		if(typeof x !='object')return this;
		if(typeof clear =='undefined')clear = false;
				
		var exist = true;
		var h = 	this.sliderHash();
		
		// Очистка , если clear
		if(h && clear){
			delete h.items;
			h.items = x;//[];
			h.totalCount = x.length;//0;
		}else{
			for(var i=0;i<x.length;i++){
				h.items[h.items.length] = x[i];
			}
			h.totalCount+=x.length;
		};
		
		$.slider.render(h.jqObject);
		return this;
	};
	// Randomize slide order on load
	/* $.fn.sliderRandomize = function(callback) {
		function randomizeOrder() { return(Math.round(Math.random())-0.5); }
			return($(this).each(function() {
			var $this = $(this);
			var $children = $this.children();
			var childCount = $children.length;
			if (childCount > 1) {
				$children.hide();
				var indices = [];
				for (i=0;i<childCount;i++) { indices[indices.length] = i; }
				indices = indices.sort(randomizeOrder);
				$.each(indices,function(j,k) { 
					var $child = $children.eq(k);
					var $clone = $child.clone(true);
					$clone.show().appendTo($this);
					if (callback !== undefined) {
						callback($child, $clone);
					}
				$child.remove();
			});
			}
		}));
	}; */
	$.fn.sliderHash=function(){
		var id = parseInt(this.attr('iuid'));
		if(!id && this.parent().size()==0)return false;
		if($.slider.hash[id])return $.slider.hash[id];
		return this.parent().sliderHash();
	};
	$.slider={
		hash:[
		],
		render: function(elem,init){
			if(typeof init == 'undefined') init = false;
			var h = 	elem.sliderHash();
			var total = 	h.totalCount;
			var it = 	h.items;
			var con = 	h.control;
			var gs =	h.sliderSettings;
			var url =	gs.imgPath;
			var sf = 	gs.selectFirst;
			var ds = 	gs.datasource;
			var home =	elem.attr('iuid');
			var out = '';
			var event = typeof gs.eventName == "function";
			
			for(var i in it)out += '<div class="slide" '+(event?'onclick="$.slider.sliderAction(this,'+it[i].ID+');"':'')+' id="tab-news-'+i+'" style="background: url('+url+it[i].ID+') no-repeat"> <a style="display:'+(it[i].Title.length<=10||it[i].ShortContent<=10?'none':'block')+'"><div class="slider-text-area"><h3>'+it[i].Title+'</h3><p>'+it[i].ShortContent+'</p></div></a></div>';
			
			con.html(out);
			
			var width = con.children().outerWidth(),
				height = con.children().outerHeight(),
				start = gs.start - 1,
				effect = gs.effect.indexOf(',') < 0 ? gs.effect : gs.effect.replace(' ', '').split(',')[0],
				paginationEffect = gs.effect.indexOf(',') < 0 ? effect : gs.effect.replace(' ', '').split(',')[1],
				next = 0, prev = 0, number = 0, current = 0, loaded, active, clicked, position, direction, imageParent, pauseTimeout, playInterval;
			
			// is there only one slide?
			if (total < 2) {
				// Fade in .slides_container
				$('.' + gs.container, elem).fadeIn(gs.fadeSpeed, gs.fadeEasing, function(){
					// let the script know everything is loaded
					loaded = true;
					// call the loaded funciton
					if(typeof(gs.slidesLoaded)=="function")gs.slidesLoaded(this);
				});
				// Hide the next/previous buttons
				$('.' + gs.next + ', .' + gs.prev,elem).fadeOut(0);
				return elem;
			}

			
				
			// 2 or more slides required
			if (total < 2) {
				return elem;
			}
			
			// error corection for start slide
			if (start < 0) {
				start = 0;
			}
			
			if (start > total) {
				start = total - 1;
			}
					
			// change current based on start op number
			if (gs.start) {
				h.current = start;
			}
			
			// randomizes slide order
			/* if (gs.randomize) {
				con.sliderRandomize();
			} */
			
			// make sure overflow is hidden, width is set
			$('.' + gs.container, elem).css({
				overflow: 'hidden',
				// fix for ie
				position: 'relative'
			});
			
			// set css for slides
			con.children().css({
				position: 'absolute',
				top: 0, 
				left: width,
				zIndex: 0,
				display: 'none'
			 });
			
			// set css for control div
			con.css({
				position: 'relative',
				// size of control 3 x slide width
				width: (width * 3),
				// set height to slide height
				height: height,
				// center control to slide
				left: -width
			});
			
			// show slides
			$('.' + gs.container, elem).css({
				display: 'block'
			});

			// if autoHeight true, get and set height of first slide
			if (gs.autoHeight) {
				con.children().css({
					height: 'auto'
				});
				con.animate({
					height: con.children(':eq('+ start +')').outerHeight()
				},gs.autoHeightSpeed);
			}
			
			// checks if image is loaded
			if (gs.preload && con.find('img:eq(' + start + ')').length) {
				// adds preload image
				$('.' + gs.container, elem).css({
					background: 'url(' + gs.preloadImage + ') no-repeat 50% 50%'
				});
				
				// gets image src, with cache buster
				var img = con.find('img:eq(' + start + ')').attr('src') + '?' + (new Date()).getTime();
				
				// check if the image has a parent
				if ($('img', elem).parent().attr('class') != 'slides_control') {
					// If image has parent, get tag name
					imageParent = con.children(':eq(0)')[0].tagName.toLowerCase();
				} else {
					// Image doesn't have parent, use image tag name
					imageParent = con.find('img:eq(' + start + ')');
				}

				// checks if image is loaded
				con.find('img:eq(' + start + ')').attr('src', img).load(function() {
					// once image is fully loaded, fade in
					con.find(imageParent + ':eq(' + start + ')').fadeIn(gs.fadeSpeed, gs.fadeEasing, function(){
						$(this).css({
							zIndex: 5
						});
						// removes preload image
						$('.' + gs.container, elem).css({
							background: ''
						});
						// let the script know everything is loaded
						loaded = true;
						// call the loaded funciton
						if(typeof(gs.slidesLoaded)=="function")gs.slidesLoaded(elem);
					});
				});
			} else {
				// if no preloader fade in start slide
				con.children(':eq(' + start + ')').fadeIn(gs.fadeSpeed, gs.fadeEasing, function(){
					// let the script know everything is loaded
					loaded = true;
					// call the loaded funciton
					if(typeof(gs.slidesLoaded)=="function")gs.slidesLoaded(elem);
				});
			}
			
			// click slide for next
			if (gs.bigTarget) {
				// set cursor to pointer
				con.children().css({
					cursor: 'pointer'
				});
				// click handler
				con.children().click(function(){
					// animate to next on slide click
					animate('next', effect);
					return false;
				});									
			}
			
			// pause on mouseover
			if (gs.hoverPause && gs.play) {
				con.bind('mouseover',function(){
					// on mouse over stop
					$.slider.stop(elem);
				});
				con.bind('mouseleave',function(){
					// on mouse leave start pause timeout
					$.slider.pause(elem);
				});
			}
			
			// generate next/prev buttons
			if (gs.generateNextPrev) {
				$('.' + gs.container, elem).after('<a class="'+ gs.prev +'">&laquo;</a>');
				$('.' + gs.prev, elem).after('<a class="'+ gs.next +'">&raquo;</a>');
			}
			
			// next button
			$('.' + gs.next ,elem).click(function(e){				
				e.preventDefault();
				if (gs.play) {
					$.slider.pause(elem);
				}
				$.slider.animate(elem,'next', effect);
			});
			
			// previous button
			$('.' + gs.prev, elem).click(function(e){
				e.preventDefault();
				if (gs.play) {
					 $.slider.pause(elem);
				}
				$.slider.animate(elem,'prev', effect);
			});
			
			// generate pagination
			if (gs.generatePagination) {
				if(!$('.' + gs.paginationClass, elem).length){
				// create unordered list
				if (gs.prependPagination) {
					elem.prepend('<ul class='+ gs.paginationClass +'></ul>');
				} else {
					elem.append('<ul class='+ gs.paginationClass +'></ul>');
				}}
				// for each slide create a list item and link
				var nav = $('.' + gs.paginationClass, elem)
				nav.html('');
				con.children().each(function(){
					nav.append('<li><a href="#'+ number +'">'+ (number+1) +'</a></li>');
					number++;
				});
			} else {
				// if pagination exists, add href w/ value of item number to links
				$('.' + gs.paginationClass + ' li a', elem).each(function(){
					$(this).attr('href', '#' + number);
					number++;
				});
			}
			
			// add current class to start slide pagination
			$('.' + gs.paginationClass + ' li:eq('+ start +')', elem).addClass(gs.currentClass);
			
			// click handling 
			$('.' + gs.paginationClass + ' li a', elem ).click(function(){
				// pause slideshow
				if (gs.play) {
					 $.slider.pause(elem);
				}
				// get clicked, pass to animate function					
				clicked = $(this).attr('href').match('[^#/]+$');
				// if current slide equals clicked, don't do anything
				if (h.current != clicked) {
					$.slider.animate(elem,'pagination', paginationEffect, clicked);
				}
				return false;
			});
			
			// click handling 
			$('a.link', elem).click(function(){
				// pause slideshow
				if (gs.play) {
					 $.slider.pause(elem);
				}
				// get clicked, pass to animate function					
				clicked = $(this).attr('href').match('[^#/]+$') - 1;
				// if current slide equals clicked, don't do anything
				if (h.current != clicked) {
					$.slider.animate(elem,'pagination', paginationEffect, clicked);
				}
				return false;
			});
		
			if (gs.play) {
				// set interval
				if(!h.state){
					h.state = 1;
					h.playInterval = setInterval(function() {
						$.slider.animate(elem,'next', effect);
					}, gs.play);
				}
			}
		},
		animate: function(elem,direction, effect, clicked) {
			var h =		elem.sliderHash();
			var gs = 	h.sliderSettings;
			var con = 	h.control;
			//console.log(Date()-h.time,Date());
			//h.time= Date();
			//temp
			var active = false;
			var loaded = true;
			var total = h.totalCount;
			var width = con.children().outerWidth();
			var	height = con.children().outerHeight();
			
			/* width = con.children().outerWidth(),
				height = con.children().outerHeight(),*/
			var	start = gs.start - 1,
				effect = gs.effect.indexOf(',') < 0 ? gs.effect : gs.effect.replace(' ', '').split(',')[0],
				paginationEffect = gs.effect.indexOf(',') < 0 ? effect : gs.effect.replace(' ', '').split(',')[1], 
			 	next = 0, prev = 0, number = 0, loaded, active, clicked, position, imageParent, pauseTimeout, playInterval;
			
			if (!active && loaded) {
				active = true;
				// start of animation
				gs.animationStart(h.current + 1);
				switch(direction) {
					case 'next':{
						// change current slide to previous
						prev = h.current;
						// get next from current + 1
						next = h.current + 1;
						// if last slide, set next to first slide
						next = total === next ? 0 : next;						
						// set position of next slide to right of previous
						position = width*2;
						// distance to slide based on width of slides
						direction = -width*2;
						// store new current slide
						h.current = next;
					}break;
					case 'prev':{
						// change current slide to previous
						prev = h.current;
						// get next from current - 1
						next = h.current - 1;
						// if first slide, set next to last slide
						next = next === -1 ? total-1 : next;								
						// set position of next slide to left of previous
						position = 0;								
						// distance to slide based on width of slides
						direction = 0;		
						// store new current slide
						h.current = next;
					}break;
					case 'pagination':{
						// get next from pagination item clicked, convert to number
						next = parseInt(clicked,10);
						// get previous from pagination item with class of current
						prev = $('.' + gs.paginationClass + ' li.'+ gs.currentClass +' a', elem).attr('href').match('[^#/]+$');
						// if next is greater then previous set position of next slide to right of previous
						if (next > prev) {
							position = width*2;
							direction = -width*2;
						} else {
						// if next is less then previous set position of next slide to left of previous
							position = 0;
							direction = 0;
						}
						// store new current slide
						h.current = next;
					}break;
				}

				// fade animation
				if (effect === 'fade') {
					// fade animation with crossfade
					if (gs.crossfade) {
						// put hidden next above current
						con.children(':eq('+ next +')', elem).css({
							zIndex: 10
						// fade in next
						}).fadeIn(gs.fadeSpeed, gs.fadeEasing, function(){
							if (gs.autoHeight) {
								// animate container to height of next
								con.animate({
									height: con.children(':eq('+ next +')', elem).outerHeight()
								}, gs.autoHeightSpeed, function(){
									// hide previous
									con.children(':eq('+ prev +')', elem).css({
										display: 'none',
										zIndex: 0
									});								
									// reset z index
									con.children(':eq('+ next +')', elem).css({
										zIndex: 0
									});									
									// end of animation
									gs.animationComplete(next + 1);
									active = false;
								});
							} else {
								// hide previous
								con.children(':eq('+ prev +')', elem).css({
									display: 'none',
									zIndex: 0
								});									
								// reset zindex
								con.children(':eq('+ next +')', elem).css({
									zIndex: 0
								});									
								// end of animation
								gs.animationComplete(next + 1);
								active = false;
							}
						});
					} else {
						// fade animation with no crossfade
						con.children(':eq('+ prev +')', elem).fadeOut(gs.fadeSpeed,  gs.fadeEasing, function(){
							// animate to new height
							if (gs.autoHeight) {
								con.animate({
									// animate container to height of next
									height: con.children(':eq('+ next +')', elem).outerHeight()
								}, gs.autoHeightSpeed,
								// fade in next slide
								function(){
									con.children(':eq('+ next +')', elem).fadeIn(gs.fadeSpeed, gs.fadeEasing);
								});
							} else {
							// if fixed height
								con.children(':eq('+ next +')', elem).fadeIn(gs.fadeSpeed, gs.fadeEasing, function(){
									// fix font rendering in ie, lame
									if($.browser.msie) {
										$(this).get(0).style.removeAttribute('filter');
									}
								});
							}									
							// end of animation
							gs.animationComplete(next + 1);
							active = false;
						});
					}
				// slide animation
				} else {
					// move next slide to right of previous
					con.children(':eq('+ next +')').css({
						left: position,
						display: 'block'
					});
					// animate to new height
					if (gs.autoHeight) {
						con.animate({
							left: direction,
							height: con.children(':eq('+ next +')').outerHeight()
						},gs.slideSpeed, gs.slideEasing, function(){
							con.css({
								left: -width
							});
							con.children(':eq('+ next +')').css({
								left: width,
								zIndex: 5
							});
							// reset previous slide
							con.children(':eq('+ prev +')').css({
								left: width,
								display: 'none',
								zIndex: 0
							});
							// end of animation
							gs.animationComplete(next + 1);
							active = false;
						});
						// if fixed height
					} else {
						// animate control
						con.animate({
							left: direction
						},gs.slideSpeed, gs.slideEasing, function(){
							// after animation reset control position
							con.css({
								left: -width
							});
							// reset and show next
							con.children(':eq('+ next +')').css({
								left: width,
								zIndex: 5
							});
							// reset previous slide
							con.children(':eq('+ prev +')').css({
								left: width,
								display: 'none',
								zIndex: 0
							});
							// end of animation
							gs.animationComplete(next + 1);
							active = false;
						});
					}
				}
				
				// set current state for pagination
				if (gs.pagination) {
					// remove current class from all
					$('.'+ gs.paginationClass +' li.' + gs.currentClass, elem).removeClass(gs.currentClass);
					// add current class to next
					$('.' + gs.paginationClass + ' li:eq('+ next +')', elem).addClass(gs.currentClass);
				}
			}
		},		
		stop: function(elem) {
			// clear interval from stored id
			var h = elem.sliderHash();
			if(h.state){
				h.state = 0;
				clearInterval(h.playInterval);
			};
		},
		pause: function(elem) {
			var h =	elem.sliderHash();
			var gs = h.sliderSettings;
			var effect = gs.effect.indexOf(',') < 0 ? gs.effect : gs.effect.replace(' ', '').split(',')[0];
			if (gs.pause) {
				// clear timeout and interval
				clearTimeout(h.pauseTimeout);
				if(h.state){
					h.state = 0;
					clearInterval(h.playInterval);
				};
				// pause slide show for gs.pause amount
				h.pauseTimeout = setTimeout(function() {
					// clear pause timeout
					clearTimeout(h.pauseTimeout);
					// start play interval after pause
					
					if(!h.state){
						h.state = 1;
						h.playInterval = setInterval(	function(){
							$.slider.animate(elem,"next", effect);
						},gs.play);
					}
				},gs.pause);
			} else {
				// if no pause, just stop
				$.slider.stop(elem);
			}
		},
		sliderAction: function(t, id){
			var th = $(t).parent().parent().parent();
			var h = th.sliderHash();
			h.sliderSettings.eventName(id);
		}
	};
})(jQuery);
