(function ($) {
	
    $.fn.slideshow = function (settings) {
    	var opts = $.extend({},$.fn.slideshow.defaults, settings);
    	var current_body = document.body || document.documentElement;
   		var current_body_style = current_body.style;
    	var is_css_transition_supported = ! jQuery.browser.mozilla && ( current_body_style.WebkitTransition !== undefined || current_body_style.MozTransition !== undefined || current_body_style.OTransition !== undefined || current_body_style.transition !== undefined );
		var has_3D = ('WebKitCSSMatrix' in window && 'm11' in new WebKitCSSMatrix());

    	var reset_css = {
			'-webkit-transform':'none',
			'-moz-transform':'none',
			'-o-transform':'none',
			'transform':'none',
			'-webkit-transition':'none',
			'-moz-transition':'none',
			'-o-transition':'none',
			'transition':'none'
		};
    	var list_items = {};
    	var dimension = 1;
    	var before;
    	var list_items = {};
    	var current_item;
    	var current_id = 0;
    	var width;
    	var height;
    	var startX;
    	var startY;
    	var query = false;
    	var num_items = opts.num_items;
    	var is_sliding = false;
    	var is_dragging = false;
    	var is_drag_sufficient_offset = false;
    	var last_drag_time = 0;
    	var drag_tread = 0;
    	var previous_offset = 0;
    	var real_time_drag = true;
        
    	var $this = this;
    	
    	var slide = function(id) {
    		if ( is_sliding ) {
    			return;
    		}
    		is_sliding = true;
    		if (typeof list_items[id] != 'undefined') {
    			animate(id);
    		}
    		else if (opts.on_fly_url && ! query ) {
				query = true;
    			$.get(opts.on_fly_url.replace('%id%',id), {}, function(data, status, request) {
    				display(id, data, status, request, true);
    				if ( opts.pre_load ) {
    					preLoad( data );
    				}
    				query = false;
    			}, 'html');
    		}
    	};
    	
    	var preLoad = function(html) {
    		var matches = html.match( /href="#[\d]+/ig );
			var ids = [];
			ids.push( parseInt( nextId() ) );
			ids.push( parseInt( previousId() ) );
			if ( matches ) {
				for( var i = 0; i < matches.length; i++ ) {
					var id = parseInt( matches[i].substring(7) );
					if ( $.inArray( id, ids ) == -1 ) {
						ids.push( id );
					}
				}
			}
    		$.each(ids,function(index, id) {
    			if ( id && ! list_items[id] ) {
		    		$.get(opts.on_fly_url.replace('%id%',id), {}, function(data, status, request) {
		    			list_item = $(data);
		        		list_item.css({
		        			width:width+'px',
		        			height:height+'px'
		        		});
		        		list_item.addClass('item');
		        		if ( ! list_items[id] ) {
			        		if ( before ) {
			        			before.before(list_item);
			        		}
			        		else {
			        			$this.append(list_item);
			        		}
			        		list_item.hide();
			    			bindEvents(list_item);
			        		list_items[id] = list_item;
		        		}
		    		});
    			}
    		});
    	};
    	
    	var firstId = function() {
    		var firstId = 1;
    		if ( typeof opts.pagination == 'object' ) {
				var p = opts.pagination.length ? opts.pagination[0] : opts.pagination ;
				for ( var key in p ) {
					firstId = p[key]['id'];
					break;
				}
    		}
    		return firstId;
    	};
    	
    	var lastId = function() {
    		var lastId = opts.num_items;
    		if ( typeof opts.pagination == 'object' ) {
				var p = opts.pagination.length ? opts.pagination[0] : opts.pagination ;
				for ( var key in p ) {
					lastId = p[key]['id'];
				}
    		}
    		return lastId;
    	};
    	
    	var adjacentIds = function(id) {
    		var ids = [];
    		if ( ! id ) {
    			return ids;
    		}
    		if ( typeof opts.pagination == 'object' ){
    			var found = 0;
    			if ( opts.pagination.length ) {
    				for ( var i = 0 ; i < opts.pagination.length ; i++ ) {
    					found = 0;
        				for ( var key in opts.pagination[i] ) {
        					if ( found || ( opts.pagination[i][key]['id'] == id ) ) {
        						ids.push(opts.pagination[i][key]['id']);
        						found++;
        						if ( found >= opts.displayed_items ) {
        							break;
        						}
        					}
        				}
        				if ( found ) {
     						break;
     					}
    				}
    			}
    			else {
    				for ( var key in opts.pagination ) {
    					if ( found || ( opts.pagination[key]['id'] == id ) ) {
    						ids.push(opts.pagination[key]['id']);
    						found++;
    						if ( found >= opts.displayed_items ) {
    							break;
    						}
    					}
    				}
    			}
    		}
    		else if ( opts.loop ) {
    			for ( var i = 0 ; i < opts.displayed_items ; i++ ) {
    				ids.push( ( id+i )%num_items + 1 );
    			}
    		}
    		else {
    			for ( var i = 0 ; i < opts.displayed_items ; i++ ) {
    				if ( ( id+i ) <= num_items ) {
    					ids.push( id+i+1 );
    				}
    			}
    		}
    		return ids;
    	};
    	
    	var nextId = function() {
    		var nextId = null;
    		if ( typeof opts.pagination == 'object' ){
    			var found = 0;
    			var firstId = null;
    			if ( opts.pagination.length ) {
    				for ( var i = 0 ; i < opts.pagination.length ; i++ ) {
    					found = 0;
        				for ( var key in opts.pagination[i] ) {
        					if ( ! firstId ) {
        						firstId = opts.pagination[i][key]['id'];
        					}
        					if ( ! found && opts.pagination[i][key]['id'] == current_id ) {
        						found++;
        					}
        					else if ( found ) {
        						if ( found >= opts.displayed_items ) {
        							nextId = opts.pagination[i][key]['id'];
        							break;
        						}
        						found++;
        					}
        				}
        				if ( found ) {
     						break;
     					}
    				}
    			}
    			else {
    				for ( var key in opts.pagination ) {
    					if ( ! firstId ) {
    						firstId = opts.pagination[key]['id'];
    					}
    					if ( ! found && opts.pagination[key]['id'] == current_id ) {
    						found++;
    					}
    					else if ( found ) {
    						if ( found >= opts.displayed_items ) {
    							nextId = opts.pagination[key]['id'];
    							break;
    						}
    						found++;
    					}
    				}
    			}
    			if ( ! found && firstId ) {
    				nextId = firstId;
    			}
    		}
    		else if ( ! current_id ) {
    			nextId = 1;
    		}
    		else {
    			nextId = current_id + opts.displayed_items;
    			if ( opts.loop ) {
    				nextId = (nextId-1+num_items)%num_items+1;
    			}
    			else if ( ( nextId <= 0 ) || ( nextId > num_items ) ) {
    				nextId = null;
    			} 
    		}
    		return nextId;
    	};
    	
    	var previousId = function() {
    		var previousId = null;
    		if ( typeof opts.pagination == 'object' ){
    			var previous = null;
    			var found = false;
    			if ( opts.pagination.length ) {
    				for ( var i = 0 ; i < opts.pagination.length ; i++ ) {
    					previous = null;
        				for ( var key in opts.pagination[i] ) {
        					if ( previous && ( opts.pagination[i][key]['id'] == current_id )) {
        						previousId = previous;
        						found = true;
        						break;
        					}
        					previous = opts.pagination[i][key]['id'];
        				}
        				if ( found ) {
     						break;
     					}
    				}
    			}
    			else {
    				for ( var key in opts.pagination ) {
    					if ( previous && ( opts.pagination[key]['id'] == current_id )) {
    						previousId = previous;
    						found = true;
    						break;
    					}
    					previous = opts.pagination[key]['id'];
    				}
    			}
    		}
    		else {
    			previousId = current_id-opts.displayed_items;
    			if ( opts.loop ) {
    				previousId = (previousId-1+num_items)%num_items+1;
    			}
    			else if ( ( previousId <= 0 ) || ( previousId >= num_items ) ) {
    				previousId = null;
    			}
    		}
    		return previousId;
    	};

    	var compareIds = function( a, b ) {
    		if ( a == b ) {
    			return 0;
    		}
    		if ( typeof opts.pagination == 'object' ){
    			if ( opts.pagination.length ) {
    				for ( var i = 0 ; i < opts.pagination.length ; i++ ) {
        				for ( var key in opts.pagination[i] ) {
        					if ( opts.pagination[i][key]['id'] == a ) {
        						return -1;
        					}
    						else if ( opts.pagination[i][key]['id'] == b ) {
        						return 1;
        					}
        				}
    				}
    			}
    			else {
    				for ( var key in opts.pagination ) {
    					if ( opts.pagination[key]['id'] == a ) {
    						return -1;
    					}
						else if ( opts.pagination[key]['id'] == b ) {
    						return 1;
    					}
    				}
    			}
    		}
    		return a - b;
    	}

    	var animate = function(id) {
    		var itemstoHide = adjacentIds( current_id );
    		var itemstoShow = adjacentIds( id );
    		current_id = id;
    		if ( itemstoHide.length == 0 ) {
    			var items = $this.children('.item');
    			for( var i = 0 ; i < opts.displayed_items ; i++ ) {
    				var offset = i * dimension / opts.displayed_items;
        			var show_item_id = itemstoShow[i];
        			var show_item = list_items[show_item_id];
        			if ( show_item ) {
    					show_item.css(opts.direction,offset).show();
    					items = items.not(show_item);
    				}
    			}
    			if ( ! opts.loop ) {
    				refreshNavigation();
    			}
    			items.hide();
        		is_sliding = false;
    		}
    		else {
    			var is = [];
    			for( var j = 0 ; j < opts.displayed_items ; j++ ) {
    				is.push(j);
    			}
    			jQuery.each(is,function(i,v) {
	    			var hide_item_id = itemstoHide[v];
	    			var show_item_id = itemstoShow[v];
	    			var hide_item = list_items[hide_item_id] ? list_items[hide_item_id] : jQuery('#none');
	    			var show_item = list_items[show_item_id] ? list_items[show_item_id] : jQuery('#none');
	    			var offset = i * dimension / opts.displayed_items;
	        		var hide_start_css = $.extend({},reset_css);
	        		var hide_end_css = $.extend({},reset_css);
	        		var show_start_css = $.extend({},reset_css);
	        		var show_end_css = $.extend({},reset_css);
	        		switch ( opts.direction ) {
	        			case 'left':
	        			case 'right':
	        			case 'top':
	        			case 'bottom':
	        				hide_start_css[opts.direction] = offset+'px';
	        				show_end_css[opts.direction] = offset+'px';
	        				var comparision = compareIds( hide_item_id,show_item_id );
	        				if ( comparision > 0 ) {
	        					hide_end_css[opts.direction] = (offset+dimension)+'px';
	        					show_start_css[opts.direction] = (offset-dimension)+'px';
	        				}
	        				else if ( comparision < 0 ) {
	        					hide_end_css[opts.direction] = (offset-dimension)+'px';
	        					show_start_css[opts.direction] = (offset+dimension)+'px';
	        				}
	        				break;
	        			case 'opacity':
	        				hide_start_css[opts.direction] = 1;
	        				show_end_css[opts.direction] = 1;
	        				hide_end_css[opts.direction] = 0;
	        				show_start_css[opts.direction] = 0;
	        				break;
	        		}
		    		if ( hide_item ) {
		    			hide_item.css(hide_start_css).show();
		    			show_item.css(show_start_css).show();
		    			if ( is_css_transition_supported ) {
		    				var transition = {
								'-webkit-transition':opts.direction+' '+opts.duration+'ms',
								'-moz-transition':opts.direction+' '+opts.duration+'ms',
								'-o-transition':opts.direction+' '+opts.duration+'ms',
								'transition':opts.direction+' '+opts.duration+'ms'
							};
		    				hide_end_css = jQuery.extend(hide_end_css, transition );
		    				show_end_css = jQuery.extend(show_end_css, transition );
		    				setTimeout(function() {
			    				hide_item.css(hide_end_css);
			    				show_item.css(show_end_css);
		    				},5);
		    			}
		    			else {
		    				hide_item.animate(hide_end_css, opts.duration, opts.easing);
		    				show_item.animate(show_end_css, opts.duration, opts.easing);
		    			}
		    			setTimeout(function() {
		    				hide_item.hide().css(reset_css);
		    				jQuery( 'audio,video', hide_item).each(function(){
								this.pause();
		    				});
		    				show_item.show().css(reset_css).css(opts.direction,offset);
		    				jQuery( 'audio,video', show_item).each(function(){
		    					if ( this.autoplay ) {
									this.play();
		    					}
		    				});
		    				if ( ! opts.loop ) {
		    					refreshNavigation();
		    				}
		    	    		is_sliding = false;
		    	    		if ( opts.pre_load ) {
		        				preLoad( show_item.html() );
		    				}
		    			}, opts.duration + 10);
		    		}
	    		});
    		}
    	};
    	
    	var refreshNavigation = function() {
    		if ( nextId() ) {
    			$this.children('.navigation-next').show();
    		}
    		else {
    			$this.children('.navigation-next').hide();			
    		}
    		if ( previousId() ) {
    			$this.children('.navigation-previous').show();
    		}
    		else {			
    			$this.children('.navigation-previous').hide();
    		}
    	};

    	var display = function(id, data, status, request, do_animate) {
    		var list_item = $(data);
    		list_item.css({
    			width:width+'px',
    			height:height+'px'
    		});
    		list_item.addClass('item');
    		if ( ! list_items[id] ) {
	    		if ( before ) {
	    			before.before(list_item);
	    		}
	    		else {
	    			$this.append(list_item);
	    		}
				bindEvents(list_item);
	    		list_items[id] = list_item;
    		}
	    	if ( do_animate ) {
	    		animate(id);
	    	}
    	};

    	var bindEvents = function(list_item) {
			if ( ! opts.prevent_click ) {
	    		var other = $('.navigation a,.navigation area', list_item);
				$('a,area', list_item).not(other).bind('click', clickAnchor);
			}
    		$('.slideshow-hover', list_item).addClass('slideshow-hover-collapsed').hover(function() {
				$(this).removeClass('slideshow-hover-collapsed').addClass('slideshow-hover-expanded');
			},function() {
				$(this).removeClass('slideshow-hover-expanded').addClass('slideshow-hover-collapsed');
			});
    		if ( opts.drag ) {
    			switch( opts.direction ) {
		        	case 'left':
		        	case 'right':
		        	case 'top':
		        	case 'bottom':
		        		if ( $.browserTouchSupport.touches ) {
		        			list_item.bind('touchstart',startDrag);
		        		}
		        		else {
		        			list_item.bind('mousedown',startDrag);
		        		}
		        		break;
	        	}
    		}
    	};

    	var clickAnchor = function() {
    		var href = $(this).attr('href');
    		if ( href && href.lastIndexOf('#') ) {
    			href = href.substring(href.lastIndexOf('#'));
    		}
    		switch( href ) {
    			case '#next':
    				var id = nextId();
    				if ( id ) {
    					slide(id);
    				}
    				if ( opts.passthru ) {
    					window.location.hash = id;
    				}
        			return false;
        			break;
    			case '#previous':
    				var id = previousId()
    				if ( id ) {
    					slide(id);
    				}
    				if ( opts.passthru ) {
    					window.location.hash = id;
    				}
        			return false;
        			break;
    			case '#home':
    				slide(firstId());
    				if ( opts.passthru ) {
    					window.location.hash = '';
    				}
        			return false;
        			break;
				case '':
					return false;
					break;
    			default:
    				if ( href && href.indexOf('#') == 0 ) {
    	    			var id = parseInt(href.substring(1));
    	    			if ( current_id != id ) {
    	    				slide(id);
    	    				if ( ! opts.passthru ) {
    	    					return false;
    	    				}
    	    			}
    	    		}
    				break;
    		}
    	};
    	
    	var getOffset = function(e) {
    		var offset = 0;
    		var pageX = 0;
    		var pageY = 0;
    		if ( ( typeof e.originalEvent.changedTouches != 'undefined' ) && e.originalEvent.changedTouches.length ) {
    			var t = e.originalEvent.changedTouches[0];
        		pageX = t.pageX;
        		pageY = t.pageY;
    		}
    		else {
        		pageX = e.pageX;
        		pageY = e.pageY;
    		}
    		switch( opts.direction ) {
	        	case 'left':
	        		offset = startX - pageX;
	        		break;
	        	case 'right':
	        		offset = pageX - startX;
	        		break;
	        	case 'top':
	        		offset = startY - pageY;
	        		break;
	        	case 'bottom':
	        		offset = pageY - startY;
	        		break;
    		}
    		return offset;
    	};
    	
    	var startDrag = function(e) {
    		if ( is_sliding ) {
    			return;
    		}
    		if ( is_dragging ) {
    			return;
    		}
    		if ( e.target.nodeName.toLowerCase() == 'a' ) {
    			return;
    		}
    		is_dragging = true;
    		is_drag_sufficient_offset = false;
    		if ( ( typeof e.originalEvent.changedTouches != 'undefined' ) && e.originalEvent.changedTouches.length ) {
    			var t = e.originalEvent.changedTouches[0];
        		startX = t.pageX;
        		startY = t.pageY;
    		}
    		else {
        		startX = e.pageX;
        		startY = e.pageY;
    		}
    		if ( $.browserTouchSupport.touches ) {
    			$this.bind('touchmove',drag);
    			$this.bind('touchend',endDrag);
    			$this.bind('touchcancel',endDrag);
    		}
    		else {
    			$this.bind('mousemove',drag);
    			$this.bind('mouseleave',endDrag);
    			$this.bind('mouseup',endDrag);
    		}
    	};

    	var drag = function(e) {
    		var offset = getOffset(e);
    		var final_css = $.extend({}, reset_css);
    		final_css[opts.direction] = 0;
    		var current_item = list_items[current_id];
    		var last_id = lastId();
    		var first_id = firstId();
    		if (
    			opts.loop || (
	    			( current_id > first_id || offset > 0 ) &&
	    			( current_id < last_id || offset < 0 )
	    		)
    		) {
    			var id = 0;
    			if ( offset > 0 ) {
    				id  = nextId();
    			}
    			else {
    				id  = previousId();
    			}
    			var itemstoHide = adjacentIds( current_id );
        		var itemstoShow = adjacentIds( id );
        		if ( ( Math.abs( offset ) < dimension / 5 ) && ! is_drag_sufficient_offset ) {
        			return false;
        		}
        		is_drag_sufficient_offset = true;
    			var current_css = {};
    			var next_css = {};
    			var transform;
    			if ( is_css_transition_supported ) {
    				if ( has_3D ) {
    					switch( opts.direction ) {
	    					case 'left':
	    						transform = 'translate3d('+(-offset)+'px,0,0)';
	    						break;
	    					case 'right':
	    						transform = 'translate3d('+(offset)+'px,0,0)';
	    						break;
	    					case 'top':
	    						transform = 'translate3d(0,'+(-offset)+'px,0)';
	    						break;
	    					case 'bottom':
	    						transform = 'translate3d(0,'+(offset)+'px,0)';
	    						break;
    					}
    				}
    				else {
    					switch( opts.direction ) {
	    					case 'left':
	    						transform = 'translate('+(-offset)+'px,0)';
	    						break;
	    					case 'right':
	    						transform = 'translate('+(offset)+'px,0)';
	    						break;
	    					case 'top':
	    						transform = 'translate(0,'+(-offset)+'px)';
	    						break;
	    					case 'bottom':
	    						transform = 'translate(0,'+(offset)+'px)';
	    						break;
    					}
    				}
    				current_css[opts.direction] = 0;
    				current_css['-webkit-transform'] = transform;
    				current_css['-moz-transform'] = transform;
    				current_css['-o-transform'] = transform;
    				current_css['transform'] = transform;
    				next_css[opts.direction] = ( offset > 0 ) ? dimension : -dimension;
    				next_css['-webkit-transform'] = transform;
    				next_css['-moz-transform'] = transform;
    				next_css['-o-transform'] = transform;
    				next_css['transform'] = transform;
    			}
    			else {
    				current_css[opts.direction] = -offset;
    				next_css[opts.direction] = -offset+( ( offset > 0 ) ? dimension : -dimension );
    			}
    			if ( typeof list_items[id] != 'undefined' ) {
    				var list_item = list_items[id];
					current_item.css(current_css);
					list_item.show().css(next_css);
    			}
    			else if ( opts.on_fly_url && ! query ) {
    				query = true;
        			$.get(opts.on_fly_url.replace('%id%',id), {}, function(data, status, request) {
        				display(id, data, status, request, false);
        				query = false;
        			}, 'html');
        		}
    		}
    		else {
    			current_item.css(final_css);
    			$this.children('.item').not(current_item).hide();
    		}
    	};
    	
    	var endDrag = function(e) {
    		if ( $.browserTouchSupport.touches ) {
	    		$this.unbind('touchmove',drag);
	    		$this.unbind('touchend',endDrag);
	    		$this.unbind('touchcancel',endDrag);
    		}
    		else {    			
    			$this.unbind('mousemove',drag);
    			$this.unbind('mouseleave',endDrag);
    			$this.unbind('mouseup',endDrag);
    		}
    		var offset = getOffset(e);
    		var current_item = list_items[current_id];
    		var last_id = lastId();
    		var first_id = firstId();
    		if ( ! is_drag_sufficient_offset ) {
    			is_dragging = false;
    			return false;
    		}
    		if (
    			opts.loop || (
	    			( current_id > first_id || offset > 0 ) &&
	    			( current_id < last_id || offset < 0 )
	    		)
    		) {
	    		var next_css = $.extend({}, reset_css);
	    		var current_css = $.extend({}, reset_css);
	    		
	    		var id = 0;
    			if ( offset > 0 ) {
    				id  = nextId();
    			}
    			else {
    				id  = previousId();
    			}
    			var itemstoHide = adjacentIds( current_id );
        		var itemstoShow = adjacentIds( id );
        		
	    		var virtual_offset = offset;
	    		if ( ! real_time_drag ) {
	    			virtual_offset = 0;
	    		}
				var list_item = list_items[id];
				current_css[opts.direction] = - virtual_offset;
				next_css[opts.direction] = - virtual_offset + ( ( offset > 0 ) ? dimension : -dimension );
				current_item.css(current_css).show();
				list_item.css(next_css).show();
				var previous_item = current_item;
				var next_item = list_item;
				var next_id = id;
				current_css = {};
				next_css = {};
				current_css[opts.direction] = ( offset > 0 ) ? - dimension : dimension;
				next_css[opts.direction] = 0;
	    		if ( Math.abs( 3 * offset ) < dimension ) {
	    			current_css[opts.direction] = - current_css[opts.direction];
	    			previous_item = list_item;
	    			next_item = current_item;
	    			next_id = current_id;
	    		}
	    		var rest_duration = Math.round( opts.duration * ( dimension - Math.abs(virtual_offset) ) / dimension );
    			if ( is_css_transition_supported ) {
    				var transition = {
						'-webkit-transition':opts.direction+' '+rest_duration+'ms',
						'-moz-transition':opts.direction+' '+rest_duration+'ms',
						'-o-transition':opts.direction+' '+rest_duration+'ms',
						'transition':opts.direction+' '+rest_duration+'ms'
					};
    				current_css = $.extend(current_css, transition );
    				next_css = $.extend(next_css, transition );
    				setTimeout(function() {
    					previous_item.css(current_css);
    					next_item.css(next_css);
    				},5);
    			}
    			else {
    				previous_item.animate(current_css, rest_duration, opts.easing);
    				next_item.animate(next_css, rest_duration, opts.easing);
    			}
    			setTimeout(function() {
    				previous_item.hide().css(reset_css);
    				current_item = next_item;
    				current_id = next_id;
    				next_item.show().css(reset_css);
    				if ( ! opts.loop ) {
    					refreshNavigation();
    				}
    				is_dragging = false;
    			}, opts.duration + 10);
    		}
    		else {
    			$this.children('.item').css(reset_css);
    			is_dragging = false;
    		}
    	};
		
		//CONSTRUCT		
        $this.addClass('slideshow-'+opts.direction);
        
        width = $this.width();
    	height = $this.height();
    	var orientation = null; 
    	switch ( opts.direction ) {
    		case 'left':
    		case 'right':
    			dimension = width;
    			reset_css[opts.direction] = 0;
    			orientation = 'horizontal'; 
    			break;
    		case 'top':
    		case 'bottom':
    			dimension = height;
    			reset_css[opts.direction] = 0;
    			orientation = 'vertical';
    			break;
    		case 'opacity':
    			reset_css[opts.direction] = 1;
    			break;
    	}
    	var i = 1;
    	$this.children('.item').css({
			width:(width/(orientation=='horizontal'?opts.displayed_items:1))+'px',
			height:(height/(orientation=='vertical'?opts.displayed_items:1))+'px'
		}).each(function() {
    		list_items[i] = $(this);
    		bindEvents(list_items[i]);
    		i++;
    	});
    	if ( ! opts.on_fly_url ) {
    		num_items = $this.children().size();
    	}
    	if ( ! before && $this.children(':not(.item):first').size() ) {
    		before = $this.children(':not(.item):first');
    	}
    	if ( ! opts.prevent_click ) {
    		var other = $(opts.markup+':not(.item) .navigation a,'+opts.markup+':not(.item) .navigation area', $this);
			$(opts.markup+':not(.item) a,'+opts.markup+':not(.item) area',$this).not(other).bind('click', clickAnchor);
		}
    	if ( opts.pagination ) {
    		var html = [];
    		if ( typeof opts.pagination == 'object' ) {
    			if ( opts.pagination.length ) {
    				for ( var i = 0 ; i < opts.pagination.length ; i++ ) {
    					var menu = [];
        				for ( var key in opts.pagination[i] ) {
        					menu.push('<a href="#'+opts.pagination[i][key]['id']+'">'+opts.pagination[i][key]['img']+'</a>');
        				}
        				html.push('<'+opts.markup+' class="menu menu-'+i+' '+( opts.hide_pagination?'menu-collapsed':'menu-expanded')+'">'+menu.join('')+'</'+opts.markup+'>');
    				}
    			}
    			else {
            		var menu = [];	
    				for ( var key in opts.pagination ) {
    					menu.push('<a href="#'+opts.pagination[key]['id']+'">'+opts.pagination[key]['img']+'</a>');
    				}
    				html.push('<'+opts.markup+' class="menu '+( opts.hide_pagination?'menu-collapsed':'menu-expanded')+'">'+menu.join('')+'</'+opts.markup+'>');
    			}
    		}
    		else {
        		var menu = [];
    			for ( var i = 1 ; i <= num_items ; i++ ) {
    				menu.push('<a href="#'+i+'">'+i+'</a>');
        		}
        		html.push('<'+opts.markup+' class="menu '+( opts.hide_pagination?'menu-collapsed':'menu-expanded')+'">'+menu.join('')+'</'+opts.markup+'>');
    		}
    		var menu = $(html.join(''));
    		$this.append(menu);
    		$('a,area',menu).bind('click', clickAnchor);
    		if ( ! before ) {
    			before = $( menu[0] );
    		}
    		if ( opts.hide_pagination ) {
    			menu.each(function() {
    				$(this).hover(function() {
	    				$(this).removeClass('menu-collapsed').addClass('menu-expanded');
	    			},function() {
	    				$(this).removeClass('menu-expanded').addClass('menu-collapsed');
	    			});
    			});
    		}
    	}
    	
        if ( opts.navigation ) {
    		var navigation = $('<'+opts.markup+' class="navigation navigation-previous"><a class="previous" href="#previous">'+opts.previous_label+'</a></'+opts.markup+'><'+opts.markup+' class="navigation navigation-next"><a class="next" href="#next">'+opts.next_label+'</a></'+opts.markup+'>');
    		try {
	    		$this.append(navigation);
	    		$('a',navigation).bind('click', clickAnchor);
	    		if ( ! before ) {
	    			before = $( navigation[0] );
	    		}
    		}
    		catch( e ) {
    			
    		}
    	}

        var jump_to = null;
        if ( opts.use_hash && window.location.hash ) {
        	jump_to = window.location.hash;
        	jump_to = parseInt( jump_to.substring( 1 ) );
        }
        if ( ! jump_to ) {
        	jump_to = nextId();
        }
    	slide( jump_to );
    	
    	if ( opts.auto ) {
    		var autoSlide = function() {slide( nextId() );};
    		var thread = setInterval(autoSlide, opts.auto );
			$(this).hover(function(){
				clearInterval( thread );
			},function(){
				thread = setInterval(autoSlide, opts.auto );
			});
    	}
        
        $this.extend({
        	slideTo: function(id) {
        		slide(id);
    		},
    		startSlide: function() {
    		},
    		stopSlide: function() {
    		}
        });
    	
    	return $this;
    };
    
	$.fn.slideshow.defaults = {
        displayed_items: 1,
        num_items: 1,
        navigation: true,
        previous_label: 'Previous',
        next_label: 'Next',
        pagination: true,
        loop: false,
        drag: true,
        auto: false,
        effect: 'slide',
        duration: 1000,
        direction: 'left',
		easing: 'swing',
		hide_pagination: false,
		hide_navigation: false,
		prevent_click: false,
		pre_load: true,
		markup: 'li',
		passthru: true,
		use_hash: true
    };
	
	var support = {};
	
	var events = [
		'touchstart',
		'touchmove',
		'touchend',
		'gesturestart',
		'gesturechange',
		'gestureend'
	];

	var el = document.createElement('div');

	for( i in events ) {
		var eventName = events[i];
		eventName = 'on' + eventName;
		var isSupported = (eventName in el);
		if (!isSupported) {
			el.setAttribute(eventName, 'return;');
			isSupported = typeof el[eventName] == 'function';
		}
		support[events[i]] = isSupported;
	}

	support.touches = 
		support.touchstart 
		&& support.touchend 
		&& support.touchmove;
	
	support.gestures = 
		support.gesturestart && 
		support.gesturechange && 
		support.gestureend;
	
	$.browserTouchSupport = support;
	
})(jQuery);

