/*
Freeslider Jquery Plugin
Author: Jonathan Yarbor
License: Purchase liecense from Codecanyon.net. Please do not steal or share.
Version : 1.0
Release Date: 6/14/2010
*/

(function($){
    $.freeSlider = function(el, options){
        // To avoid scope issues, use 'base' instead of 'this'
        // to reference this class from internal events and functions.
        var base = this;
        
        // Access to jQuery and DOM versions of element
        base.$el = $(el);
        base.el = el;
        
        // Add a reverse reference to the DOM object
        base.$el.data("freeSlider", base);
        base.options = $.extend({},$.freeSlider.defaultOptions, options);
		var items = new Object;
		var totalItems = $(el).find('.fs_item').size();
		var auto = base.options.auto;
		var current = base.options.slide;
		
        base.init = function(){		
			// Set math variables
            var top_offset = $(el).offset().top;
			var left_offset = $(el).offset().left;
			var stretch_width = (Math.round(totalItems / base.options.rows) * (base.options.width + base.options.marginRight));
			var stretch_height = (base.options.rows * (base.options.height + base.options.marginBottom));
			var top_offset = $(el).offset().top; 
			var left_offset = $(el).offset().left;
			var c = 1;
			var elmid = $(el).attr('id');
				if(elmid==undefined || elmid == false || elmid ==''){
					var elmid = 'freeSlider';
				}
			// add the strecth element which will be the initial element with an id of <idname>_stretch this makes the rows work
			$(el).find('.fs_item').wrapAll('<div id="'+elmid+'_stretch" style="display:block; position:relative; width: '+stretch_width+'px; height: '+stretch_height+'px;">');
			// make sure all css is applied
			$(el).css({	'width'		:	base.options.width,
						'height'	:	base.options.height,
						'display'	:	'block',
						'overflow'	:	'hidden',
						'position'	:	'relative'
						});
			// lets make an array with the details of their coordinates
				$(el).find('.fs_item').each(function(){
					// make sure our slider elements work as well
					$(this).css({
								'width'		:	base.options.width,
								'height'	:	base.options.height,
								'display'	:	'block',
								'float'		:	'left',
								'position'	:	'relative',
								'margin-right'	:	base.options.marginRight,
								'margin-bottom'	:	base.options.marginBottom
					});
					$(this).attr('id','fs_'+c); 
					items['fs_'+c]= $(this).position();
					c++;
					if(c==totalItems){ // have completed our array
					base.setClicks(); // lets set any elements for triggers
					base.slideTo(base.options.slide,true);
						
					}
				});
        };
		
		// standard function intended to slide to given number
		// @item : id number to slide to
		// @snap : optional: to snap rather than animate
		 base.slideTo = function(item,snap){
		 if(item>totalItems){item = current=1;}
		 if(item<1){item = current= totalItems;}
		 current = item;
			 if(snap==true){
				base.snap(items['fs_'+item]['top'],items['fs_'+item]['left'],item);
			}else{
				base.slide(items['fs_'+item]['top'],items['fs_'+item]['left'],item);
			}
		}
		// simple function to move to the previous slide
		base.previous = function(){
			current--;
			base.slideTo(current);
		}
		
		// simple function to move to the next slide
		base.next = function(){
			current++;
			base.slideTo(current);
		}
		
		// simple function to move to the 1st slide
		base.first = function(){
			current=1;
			base.slideTo(current);
		}
		
		// simple function to move to the last slide
		base.last = function(){
			current=totalItems;
			base.slideTo(current);
		}
		
		// OOP method to help with the click triggers.
		base.clickTo = function(action,gotoitem){ 
			switch(action){
				case"previous":
					$(el).stop();
					base.previous();
				break;
				case"next":
					$(el).stop();
					base.next();
				break;
				case"first":
					$(el).stop();
					base.first();
				break;
				case"last":
					$(el).stop();
					base.last();
				break;
				case"number":
					$(el).stop();
					base.slideTo(gotoitem);
				break;
				case"stop":
					//do nothing, but have a fireback here if needed
				break;
			}
			auto = false; // stop the auto because the user has taken control
			return false; // this is so the link won't follow through
		}
		
		// init function to check if the click elements have been defiend, if they haven't then give them an event listener
		base.setClicks = function(){
			if(base.options.click.next!=false){$(base.options.click.next).bind('click',function(){base.clickTo('next');});}
			if(base.options.click.previous!=false){$(base.options.click.previous).bind('click',function(){base.clickTo('previous');});}
			if(base.options.click.last!=false){$(base.options.click.last).bind('click',function(){base.clickTo('last');});}
			if(base.options.click.first!=false){$(base.options.click.first).bind('click',function(){base.clickTo('first');});}
			if(base.options.click.stop!=false){$(base.options.click.stop).bind('click',function(){base.clickTo('stop');});}
			if(base.options.click.number!=false){$(base.options.click.number).bind('click',function(){
					gotonumber = $(this).attr('href'); //remove the # in the link
					gotonumber = gotonumber.slice(-1);
					base.clickTo('number',gotonumber);
				});				
			}
		}
		
		base.slide = function(top,left,item){
			$(el).stop().animate({
				scrollTop : top,
				scrollLeft : left
			},base.options.slideSpeed); 
			base.doAuto();
		}
		
		base.snap = function(top,left,item){ 
			$(el).scrollTop(top).scrollLeft(left);
			base.doAuto();
		}
		
		base.doAuto = function(){
			if(auto==true){ 
				if(current==totalItems){ //back to 1st
					setTimeout(function(){ if(auto==true){base.first();} },base.options.pauseTime);
				}else{ // keep going
					setTimeout(function(){  if(auto==true){base.next();} },base.options.pauseTime);
				}
			}else{ 
				return false;
			}
		}
        
        // Sample Function, Uncomment to use
        // base.functionName = function(paramaters){
        // 
        // };
        
        // Run initializer
        base.init();		
		return base;
    };
    
    $.freeSlider.defaultOptions = {
		//symatics
		rows : 2,
        slideSpeed: 300,
        pauseTime: 3000,
		auto: true,
		slide: 1,
		
		// click event elements. Set to false to disable
		click:	{
			next : false,
			previous : false,
			last : false,
			first : false,
			number : false,
			stop : false
		},	
		
		// design
		width : 650,
		height: 250,
		marginRight: 100,
		marginBottom: 100
    };
    
    $.fn.freeSlider = function(options){
		this.each(function(){
			 doit = new $.freeSlider(this, options);			 
        });
		return doit;
    };
    
})(jQuery);

