/*****************************************************
* Slideshow
*
* TODO: add caption and navigation, show slide number
******************************************************/

var Slide = Class.create({
	initialize: function(src) {
		this.src = src;
		this.image = new Image(); // preload image
		this.image.src = src;
		this.width = this.image.width;
		this.height = this.image.height;
	},

	setCaption: function(caption) {
		this.caption = caption;
	},
	
	setAlt: function(alt) {
		this.alt = alt;
	}
	
});

var Slideshow = Class.create({
	initialize: function(slides, holderelm) {
		this.elm = $(holderelm);
		this.elm.setStyle({backgroundColor: "#000"});
		this.slide = document.createElement("img");
		this.slideDuration = 3;
		this.transitionDuration = .5;
		this.currentSlide = 0;
		this.slides = slides;
		this.isPlaying = false; 
		this.width = 0;
		this.height = 0;

		// check if holder elment contains an image (this will be replaced by the slideshow)
		if (this.elm.getElementsByTagName("IMG").length >0) {
			this.elm.replaceChild(this.slide,this.elm.getElementsByTagName("IMG")[0]);
			this.slide.src = this.slides[this.currentSlide].src;
			this.setSize();
		} else {
			// insert a new child element
			this.elm.appendChild(this.slide);
			this.show();
		}
	},
	
	addSlide: function(slide) {
		this.slides.push(slide);
		this.currentSlide++;
	},
	
	getSlide: function() {
		return this.currentSlide;
	},
	
	setWidth: function(w) {
		this.width = w;
	},
	
	setHeight: function(h) {
		this.height = h;
	},
	
	/* navigation */
	setSlideDuration: function(duration) {
		this.slideDuration = duration;
	},
	
	setTransitionDuration: function(duration) {
		this.transitionDuration = duration;
	},
	
	forward: function() {
		this.currentSlide>=(this.slides.size()-1)?this.currentSlide = 0:this.currentSlide++;
	},
	
	back: function() {
		this.currentSlide==0?this.currentSlide = this.slides.size()-1:this.currentSlide--;
	},
	
	show: function() {
		Effect.Fade(this.slide,{duration:this.transitionDuration/2,to:.01});
		this.transition = new PeriodicalExecuter(this.appear.bind(this), this.transitionDuration/2);
	},
	
	appear: function() {
		this.slide.src = this.slides[this.currentSlide].src;
		this.setSize();
		Effect.Appear(this.slide,{duration:this.transitionDuration/2, from:.01});
		this.transition.stop();
	},
	
	showNextSlide: function() {
		this.forward();
		this.show();
	},

	showPreviousSlide: function() {
		this.back();
		this.show();
	},
	
	showSlide: function(slideNr) {
		if (slideNr >0  && slideNr <= this.slides.length) {
			this.currentSlide = slideNr - 1;
		}
		this.show();
	},
	
	startShow: function() {
		this.slideshow = new PeriodicalExecuter(this.showNextSlide.bind(this), this.slideDuration);
		this.isPlaying = true; 
	},
	
	stopShow: function() {
		this.slideshow.stop();
		this.isPlaying = false; 
	},
	
	fadeTo: function(color) {
		this.elm.setStyle({backgroundColor: color});
	},
	/* utitility methods */
	/* make order of slides random */
	randomize: function() {
		this.slides.sort(randomOrder);
	},
	/* return sources of slides as one string */
	toString: function() {
		var str = "";
		this.slides.each(function(s, index) {
			str += index + ": " + s.src + "\n";
		});
		return str;
	},
	
	/* find sizes for slide when width or height are set */
	setSize: function() {
		if (this.width > 0 || this.height > 0) {
			// find smallest factor
			var factW = 1;
			var factH = 1;
			if (this.width > 0 && this.width/this.slides[this.currentSlide].width < 1) {
				factW = this.width/this.slides[this.currentSlide].width;
			}
			if (this.height > 0 && this.height/this.slides[this.currentSlide].height < 1) {
				factH = this.height/this.slides[this.currentSlide].height;
			}
			var factor = factW>factH?factH:factW;
			//alert(this.slide.inspect());
			//alert("setting width: " + this.slides[this.currentSlide].width + " * " + factor);
			this.elm.setStyle({"width": (this.slides[this.currentSlide].width * factor) + "px", "height": (this.slides[this.currentSlide].height * factor) + "px"});
			this.slide.setStyle({"width": (this.slides[this.currentSlide].width * factor) + "px", "height": (this.slides[this.currentSlide].height * factor) + "px"});
		} else {
			return;
		}
	}
});

// Utitlity function for random ordering of an array
var randomOrder = function (){
	return (Math.round(Math.random())-0.5);
}
