// Slider:
/*
Usage:
 new Diaporama (target, boutton_back, boutton_forward, options)
 target = id de la zone contenant les diapo
 boutton_back = id du boutton pour revenir
 boutton_forward = id du boutton pour avancer
 options = {nom_1 : valeur_1 , nom_2_valeur_2 etc...}
 Listes des options:
 direction : vertical par dÃ©faut, si autre que 'vertical', le defilement sera horizontal
 moveAuto : si a true, alors le slider defillera automatiquement, les boutons accelerent ou inverse la vitesse
 loop : si a true, alors une boucle est crée
 speed : vitesse en pixel, 1 par dÃ©faut, 5 dans le cas d'un moveByStep
 moveByStep : si dÃ©init, sa valeur sera l'avancement par pas en pixel au clic de la souri, et non au passage sur le boutton.
*/

Slider = Class.create();
Object.extend(Slider.prototype,{
	contener:null,
	contener2:null,
	currentTimeout:null,
	autoTimeout:null,
	nextStep:null,
	direction:'top',
	totalSize:null,
	visibleSize:null,
	diferenceSize:null,

	initialize: function(target,btn_back,btn_fwd,options) {
		try{
	this.target = $(target);
    this.btn_back = $(btn_back);
    this.btn_fwd = $(btn_fwd);
	this.setOptions(options || {});
	this.direction = (this.options.direction == 'vertical') ? 'top' : 'left';
    this.createContener();
    this.totalSize = this.direction == 'top' ? this.contener.offsetHeight : this.contener.offsetWidth;
    this.visibleSize = this.direction == 'top' ? this.target.offsetHeight : this.target.offsetWidth;
    this.diferenceSize = this.visibleSize - this.totalSize;
    Element.setStyle(this.btn_back,{cursor:"pointer"});
    Element.setStyle(this.btn_fwd,{cursor:"pointer"});
    if(!this.options.moveByStep)
		{
		Event.observe(btn_fwd,"mouseover",this.moveFwd.bindAsEventListener(this));
	    Event.observe(btn_back,"mouseover",this.moveBack.bindAsEventListener(this));
	    Event.observe(btn_fwd,"mouseout",this.stopFwd.bindAsEventListener(this));
	    Event.observe(btn_back,"mouseout",this.stopBack.bindAsEventListener(this));
	    }
    else
    	{
    	this.options.speed = options.speed || 5;
		Event.observe(btn_fwd,"click",this.moveFwdByStep.bindAsEventListener(this));
	    Event.observe(btn_back,"click",this.moveBackByStep.bindAsEventListener(this));
		}
	if(this.options.moveAuto)
		{
		Event.observe(this.target,"mouseover",this.stopMoveAuto.bindAsEventListener(this));
		Event.observe(this.target,"mouseout",this.moveAuto.bindAsEventListener(this));
		Event.observe(btn_back,"mouseover",this.stopMoveAuto.bindAsEventListener(this));
		Event.observe(btn_back,"mouseout",this.moveAuto.bindAsEventListener(this));
		this.moveAuto();
		}
	}
	catch(e)
	{
		window.status = "Erreur dans la creation du slider : "+e;		
	}
	
  },
	  setOptions: function(options) {
	    this.options = Object.extend({
	      direction: options.direction || "vertical",
	      loop: options.loop || false,
	      speed: options.speed || 1,
	      moveByStep: options.moveByStep || false, //Si cette option est dÃ©finie, on avance par pas (chiffre dÃ©finit) en cliquant sur les bouttons
		  moveAuto: options.moveAuto || false //Si cette option est dÃ©finie, on avance par pas (chiffre dÃ©finit) en cliquant sur les bouttons
	    },options || {});
	  },

  	//Fonction creant le div intermediaire qui glissera dans le div "target" et contenant tous les element initiaux de "target"
  	createContener: function() {
  	this.contener = document.createElement('div');
  	Element.setStyle(this.contener,{position:'relative',top:'0px',left:'0px'});
  	/*on rattache tous les elements du bloc parent au slider*/
  	this.target.childElements().each(
		  function(node){
		  this.contener.appendChild(node);
		  }.bind(this));
  	this.target.appendChild(this.contener);
  	if(this.direction == 'left')
  		{
		  var contenerWidth = 0;
		  this.contener.childElements().each(
		  function(node){
		  contenerWidth += node.offsetWidth + parseInt(Element.getStyle(node,'marginLeft')) + parseInt(Element.getStyle(node,'marginRight'));
		  });
		  contenerWidth += 4;
		  Element.setStyle(this.contener,{width:contenerWidth+"px",cssFloat:'left'});
		}
	if(this.options.loop)
	{this.contener2 = this.contener.cloneNode(true);this.target.appendChild(this.contener2);}
	
	Element.setStyle(this.target,{overflow:'hidden',position:'relative'});
	  },

	//Fonction dÃ©finissant si le slide est dans les limites pour savoir si il est possible de glisser encore
	//(max = les plus bas = on voit la partie haute, min = le plus haut = on voit la partie basse)
	isInMinLimit: function() {
		var currPos = parseInt(Element.getStyle(this.contener,"margin-"+this.direction) || 0);
		return (currPos > this.diferenceSize)
	},
	isInMaxLimit: function() {
		var currPos = parseInt(Element.getStyle(this.contener,"margin-"+this.direction) || 0);
		return (currPos < 0)
	},
	//Fonctions fonctionnant par passage de la souri sur les bouton
	moveFwd:function(){
	if(this.options.loop) 
	 this.manageLoop();
	else if(!this.isInMinLimit())
		{return false;}
		this.manageLoop();
	 var nextPos = (parseInt(Element.getStyle(this.contener,"margin-"+this.direction) || 0)-this.options.speed)+"px";
	 var option = this.direction == "top" ? {marginTop:nextPos} : {marginLeft:nextPos};
	 Element.setStyle(this.contener,option);
	 this.currentTimeout = setTimeout(this.moveFwd.bindAsEventListener(this),40);
	 },
	moveBack:function(){
	if(this.options.loop) 
	 this.manageLoop();
	else if(!this.isInMaxLimit())
		{return false;}
		
	 var nextPos = parseInt(Element.getStyle(this.contener,"margin-"+this.direction) || 0)+this.options.speed+"px";
	 var option = this.direction == "top" ? {marginTop:nextPos} : {marginLeft:nextPos}
	 Element.setStyle(this.contener,option);
	 this.currentTimeout = setTimeout(this.moveBack.bindAsEventListener(this),40);
	 },
	stopFwd:function(){
	 clearTimeout(this.currentTimeout)
	 },
	stopBack:function(){
	 clearTimeout(this.currentTimeout)
	 },
	//Fonctions fonctionnant par clic de la souri sur les bouton, par pas dÃ©finit par l'option moveByStep
	moveFwdByStep:function(){
	if(this.options.loop) 
	 this.manageLoop();
	else if(!this.isInMinLimit() && this.nextStep == null)
		{return false;}
		this.manageLoop();
	 var currPos = parseInt(Element.getStyle(this.contener,"margin-"+this.direction) || 0);
	 if(this.nextStep == null)
	 	{this.nextStep = currPos - this.options.moveByStep;}
	 var nextPos = (currPos-this.options.speed)+"px";
	 var option = this.direction == "top" ? {marginTop:nextPos} : {marginLeft:nextPos}
	 Element.setStyle(this.contener,option);
	 if(currPos > this.nextStep && this.isInMinLimit())
	 	this.currentTimeout = setTimeout(this.moveFwdByStep.bindAsEventListener(this),10);
     else
     	{
		 this.nextStep = this.isInMinLimit() ? this.nextStep : this.diferenceSize;
		 option = this.direction=="top" ? {top:this.nextStep+"px"} : {left:this.nextStep+"px"};
		 Element.setStyle(this.contener,option);this.nextStep = null;
		 }
	 },
	moveBackByStep:function(){
	if(this.options.loop) 
	 this.manageLoop();
	else if(!this.isInMaxLimit() && this.nextStep == null)
		{return false;}
		this.manageLoop();
		 var currPos = parseInt(Element.getStyle(this.contener,"margin-"+this.direction) || 0);
	 if(this.nextStep == null)
	 	this.nextStep = currPos + this.options.moveByStep;
	 var nextPos = (currPos+this.options.speed)+"px";
	 var option = this.direction == "top" ? {marginTop:nextPos} : {marginLeft:nextPos}
	 Element.setStyle(this.contener,option);
	 if(currPos < this.nextStep && this.isInMaxLimit())
	 	this.currentTimeout = setTimeout(this.moveBackByStep.bindAsEventListener(this),10);
     else
     	{
     	this.nextStep = this.isInMaxLimit() ? this.nextStep : 0;
		 option = this.direction=="top" ? {top:this.nextStep+"px"} : {left:this.nextStep+"px"};
		 Element.setStyle(this.contener,option);this.nextStep = null;
		 }
	 },
	moveAuto:function(){
	if(this.options.loop) 
 		this.manageLoop();
	else if(!this.isInMinLimit())
		{return false;}
		 this.manageLoop();
	 var nextPos = (parseInt(Element.getStyle(this.contener,"margin-"+this.direction) || 0)-this.options.speed)+"px";
	 var option = this.direction == "top" ? {marginTop:nextPos} : {marginLeft:nextPos};
	 Element.setStyle(this.contener,option);
	 this.autoTimeout = setTimeout(this.moveAuto.bindAsEventListener(this),40);
	 },
	 stopMoveAuto:function(){
	 clearTimeout(this.autoTimeout);
	 },
	 manageLoop:function(){
		 var currPos = parseInt(Element.getStyle(this.contener,"margin-"+this.direction) || 0);
		 
		if(-currPos > this.totalSize)
			{
			_margin = Element.getStyle(this.contener,"margin-"+this.direction)			
			var option = this.direction == "top" ? {marginTop:0} : {marginLeft:0};
			var option2 = this.direction == "top" ? {marginTop:_margin} : {marginLeft:_margin};
			Element.setStyle(this.contener,option);		
			this.target.removeChild(this.contener);
			this.target.appendChild(this.contener);
			tempContener = this.contener;
			this.contener = this.contener2;
			this.contener2 = tempContener;
			}
		else if(currPos > 0)
			{
			_margin = parseInt(Element.getStyle(this.contener,"margin-"+this.direction) || 0);			
			/*var option2 = this.direction == "top" ? {marginTop:0} : {marginLeft:0};*/
			_margin = "-"+(this.totalSize-_margin)+"px";
			var option = this.direction == "top" ? {marginTop:_margin} : {marginLeft:_margin};
			Element.setStyle(this.contener2,option);
			this.target.removeChild(this.contener);	
			this.target.appendChild(this.contener);
			tempContener = this.contener;
			this.contener = this.contener2;
			this.contener2 = tempContener;
			}
	 }
});
