
if (typeof Effect.ScrollHorizontal == 'undefined') {
	throw("gallery.js requires including script.aculo.us' elementscroller.js library!");
}

if(!myUtils) {
	var myUtils	= {
	
		swapClass:	function(element, class1, class2) {
			element.removeClassName(class1);
			element.addClassName(class2);
		}
	
	}
}

Element.addMethods(myUtils);

var slideShow = Class.create();
slideShow.prototype = {

	oldItem			: null,
	options 		: null,
	listItem		: [],
	listToggle		: [],
	currentIndex	: 0,
	auto			: null ,

	initialize: function(container, options) {

		if (!$(container)) {
			throw(container+" doesn't exist!");
			return false;
		}

		this.containerName	= $(container).readAttribute('id');

		this.options = Object.extend({
			container		: false,
			delay			: 0,
			duration		: 0.20,
			toggle			: false,
			toggleOff		: false,
			previous		: false,
			next			: false,
			justCallBack	: false,
			item			: 'slideshow',
			onEvent 		: 'click',
			move			: 'horizontal',
			defaultView		: 0,
			auto			: false,
			delayAuto		: 3,
			direction		: 1,
			onStop			: 'mouseover',
			onRestart		: 'mouseout',
			callBack		: null,
			nbItemsVisible  : 4,
			step			: 1,
			offsetMarginX	: 0,
			height			: 0

		}, options || {});

		
		if(this.options.container == false) {
			this.options.container	= container;
		}

		if(this.options.height == 0) {
			var	listHeight	= new Array();

			listHeight[0]	= $(container).getHeight();
			listHeight[1]	= $(this.options.container).getHeight();
			listHeight[2]	= $(this.options.container).firstDescendant().getHeight();

			for(i=0; i<3; i++) {
				if(listHeight[i] > this.options.height) {
					this.options.height	= listHeight[i];
				}
			}
		}



		$(this.options.container).firstDescendant().setStyle({height: this.options.height + 'px', position: 'absolute'});

		this.listItem	= $$('#' + this.options.container + ' .' + this.options.item);

		if(this.listItem.size() == 0) {
			return false;
		}

		if(this.options.toggle) {
			this.listToggle	= $$('#' + container + ' .' + this.options.toggle);

			if(this.listToggle.length != this.listItem.length) {
				throw Error('Number of toggle/item does not match! toggle : ' + this.listToggle.length + ' - item : ' + this.listItem.length);
				return false;
			}
			for(var i = 0; i < this.listToggle.length; i++) {
				Event.observe(this.listToggle[i], this.options.onEvent, this.moveTo.bind(this, i));
				this.listToggle[i].style.cursor = 'pointer';
				this.listToggle[i].swapClass(this.options.toggle, this.options.toggleOff);

				if (this.options.onEvent == 'click') {
				  this.listToggle[i].onclick	= function() {return false;};
				}
			}

		} else if(this.options.previous && this.options.next) {

			this.options.previous	= $$('#' + container + ' .' + this.options.previous)[0];
			this.options.next		= $$('#' + container + ' .' + this.options.next)[0];

			if ( this.listItem.length > this.options.nbItemsVisible){	
				this.options.previous.setStyle({cursor: 'pointer'});
				this.options.next.setStyle({cursor: 'pointer'});
				
				Event.observe(this.options.previous, this.options.onEvent, this.moveTo.bind(this, (0 - this.options.step)));
				Event.observe(this.options.next, this.options.onEvent, this.moveTo.bind(this, this.options.step));
	
				if (this.options.onEvent == 'click') {
					this.options.previous.onclick	= function() {return false;};
					this.options.next.onclick 		= function() {return false;};
				}
			} 

		} else if(this.options.justCallBack) {
			
			this.listToggle	= $$('#' + container + ' .' + this.options.justCallBack);

			if(this.listToggle.length != this.listItem.length) {
				throw Error('Number of toggle/item does not match! toggle : ' + this.listToggle.length + ' - item : ' + this.listItem.length);
				return false;
			}
			
			for(var i = 0; i < this.listToggle.length; i++) {
				Event.observe(this.listToggle[i], this.options.onEvent, this.sendCallBack.bind(this, i));
				this.listToggle[i].style.cursor = 'pointer';
				this.listToggle[i].swapClass(this.options.toggle, this.options.toggleOff);

				if (this.options.onEvent == 'click') {
				  this.listToggle[i].onclick	= function() {return false;};
				}
			}


		}
		
		if(this.options.auto == true) {
			Event.observe(container, this.options.onStop, this.stop.bind(this));
			Event.observe(container, this.options.onRestart, this.start.bind(this));
		}

//		this.moveTo(this.options.defaultView);
		this.currentIndex	= this.options.defaultView;
		this.oldItem		= this.options.defaultView;

		this.listItem.each(
			function(el, index) {
				if((index != this.currentIndex && index > (this.options.nbItemsVisible + this.currentIndex) || index < this.currentIndex)) {
					el.hide();
				}
			}.bind(this)
		);

		if(this.options.previous && this.options.next) {			
			if ( this.listItem.length <= this.options.nbItemsVisible) {
				this.cacher(this.options.previous);
				this.cacher(this.options.next);
				this.options.previous	= false;
				this.options.next		= false;				
			}
		}
	
		if(this.options.auto == true) {
			this.auto	= new PeriodicalExecuter(this.autoMove.bind(this), this.options.delayAuto);
		}

		if(this.options.previous && this.options.next) {
			this.togglePrevNext(this.currentIndex);
		}

		if(!this.options.justCallBack) {
			this.sendCallBack(-1);
		}

	},

	start: function() {
		if(this.options.auto == true) {

			if(this.auto !== null) {
				this.auto.stop();
			}
			
			this.auto	= new PeriodicalExecuter(this.autoMove.bind(this), this.options.delayAuto);
		}
	},

	stop: function() {
		if(this.options.auto == true) {
			this.auto.stop();
		}
	},

	autoMove: function() {
		var	index	= this.currentIndex + (this.options.direction * this.options.step)

		var	step	= this.options.direction;

		if(this.options.direction == 0 ) {
			this.options.direction = 1;
		}

		if(index < 0) {
			this.options.direction	= 1;
		} else if(index > this.listItem.length-1) {
			this.options.direction	= -1;
		}

//		alert(index + ' ' + this.options.direction);

		index	= this.currentIndex + (step * this.options.step);

		if(index > this.listItem.length- (this.options.nbItemsVisible) ) {
//			index = this.listItem.length - (this.options.nbItemsVisible) - 1;
			index = this.listItem.length - (this.options.nbItemsVisible);
		}

		if(index < 0) {
			index	= 0;

//			if(this.listItem.length > 0) {
//				index	= 1;
//			}
		}

		this.move(index);

	},

	afficher: function(el) {
		el.setStyle({visibility: 'visible'});
	},
	
	cacher: function(el) {
		el.setStyle({visibility: 'hidden'});
	},

	sendCallBack:	function(step) {
		if (this.options.callBack){
			this.index	= step;
			this.options.callBack(this);
		}
	},

	moveTo: function(step) {
		
		var index	= step;

		if(this.options.previous && this.options.next) {

			index	= this.currentIndex + step;

			if((index + this.options.nbItemsVisible) > (Math.ceil((this.listItem.length/this.options.nbItemsVisible)) * this.options.nbItemsVisible) )  { // ajout d'une nbItemsVisible-1 qui d�finit l'arr�t du scroll
				index	=  0;
			}
			
			if(index > this.listItem.length- (this.options.nbItemsVisible) ) {				
				index = this.listItem.length - (this.options.nbItemsVisible);
			}

			if(index < 0){
				index	= 0;
			}

			this.options.direction	= step;
		
		}

		this.move(index);
	},

	move:	function(index) {

		for(var i = index; i<(index + this.options.nbItemsVisible); i++) {
			this.listItem[i].show();
		}

		$(this.options.container).scrollLeft	= this.listItem[this.currentIndex].positionedOffset().left-this.options.offsetMarginX;

		if(this.listItem[index].positionedOffset().left-this.options.offsetMarginX < this.listItem[this.currentIndex].positionedOffset().left-this.options.offsetMarginX) {
			new Effect.ScrollHorizontal(this.options.container, {
				queue: {position : 'end', scope: this.containerName}, duration: this.options.duration, from: (this.listItem[this.currentIndex].positionedOffset().left-this.options.offsetMarginX), to: (this.listItem[index].positionedOffset().left-this.options.offsetMarginX) ,
				afterFinish	:	function() {

					this.listItem.each(
						function(el, index) {
							if((index != this.currentIndex && index > (this.options.nbItemsVisible + this.currentIndex) || index < this.currentIndex)) {
								el.hide();
							}
						}.bind(this)
					);

					$(this.options.container).scrollLeft	= 0-this.options.offsetMarginX;
					
				}.bind(this)

			});
		} else {
			new Effect.ScrollHorizontal(this.options.container, {
				queue: {position : 'end', scope: this.containerName}, duration: this.options.duration, from: this.listItem[this.currentIndex].positionedOffset().left-this.options.offsetMarginX, to: this.listItem[index].positionedOffset().left-this.options.offsetMarginX,
				afterFinish	:	function() {

					this.listItem.each(
						function(el, index) {
							if((index != this.currentIndex && index > (this.options.nbItemsVisible + this.currentIndex) || index < this.currentIndex)) {
								el.hide();
							}
						}.bind(this)
					);

					$(this.options.container).scrollLeft	= 0-this.options.offsetMarginX;
					
				}.bind(this)

			});
		}

		if(this.options.toggle && this.options.toggleOff) {
			this.listToggle[this.currentIndex].swapClass(this.options.toggle, this.options.toggleOff);
			this.listToggle[index].swapClass(this.options.toggleOff, this.options.toggle);
		}

		if(this.options.auto == false) {
			if(this.currentIndex < index) {
				this.options.direction	= 1;
			} else {
				this.options.direction	= -1;
			}
		}

		if(this.currentIndex != index || this.oldItem == null) {
			this.oldItem	= this.currentIndex;
		}

		this.currentIndex	= index;

		if(!this.options.justCallBack) {
			this.sendCallBack(index);
		}

		if(this.options.previous && this.options.next) {
			this.togglePrevNext(index);
		}

	},

	togglePrevNext:	function(index) {

		if (index == 0 ){
			this.cacher(this.options.previous);
		} else {
			this.afficher(this.options.previous);
		}

		if ( index == (this.listItem.length - this.options.nbItemsVisible)){
			this.cacher(this.options.next);
		}else{
			this.afficher(this.options.next);
		}
	}

}
