/*	Script: simple.slideshow.js
 Makes a very, very simple slideshow gallery with a collection of dom elements and previous and next buttons.
 
 Author:
 Aaron Newton
 
 Dependencies:
 mootools - 	<Moo.js>, <Utility.js>, <Common.js>, <Function.js>, <Array.js>, <String.js>, <Element.js>, <Fx.Base.js>, <Dom.js>, <Cookie.js>
 Class: SimpleSlideShow
 Makes a very, very simple slideshow gallery with a collection of dom elements and previous and next buttons.
 
 Arguments:
 options - an object with key/value settings.
 
 Options:
 startIndex - (integer) the first image to show
 slides - (array) a collection of elements already in the dom.
 currentSlideClass - (string; optional) class to assign the currently visible slide; defaults to "currentSlide"
 currentIndexContainer - (dom element or id) container to display the the currently shown slide index
 (i.e. "showing *2* of 3"); optional
 maxContainer - (dom element or id) container to display the maximum number of slides available; optional
 nextImg - (dom element or id) image to capture clicks to show the next image; optional, but if
 not supplied you'll have to execute <cycleForward> yourself.
 prevImg - (dom element or id) image to capture clicks to show the next image; optional, but if
 not supplied you'll have to execute <cycleBack> yourself.
 wrap - (boolean) when the user clicks next at the end of a set, go back to the start
 (and if they click prev at the begining, go to the end); defaults to true
 disabledLinkClass - (string) class to add to next/prev links when there are no next or prev slides;
 defaults to "disabled"
 onNext - (function) callback for when the user clicks next; optional
 onPrev - (function) callback for when the user clicks prev; optional
 onSlideClick - (function) callback for when the user clicks a slide, this function will
 be passed the slide clicked and the index of the slide. optional
 crossFadeOptions - (object) options object to be passed to the opacity effects.
 
 Example:
 (start code)
 new SimpleSlideShow({
 startIndex: 0,
 slides: $$('.slide'),
 currentIndexContainer: 'slideNow', //an element or it's id
 maxContainer: 'slideMax',
 nextLink: 'nextImg',
 prevLink: 'prevImg'
 });
 (end)
 */
var SimpleSlideShow = new Class({
	Implements: [Options, Events],
	options: {
		startIndex: 0,
		slides: [],
		currentSlideClass: 'currentSlide',
		currentIndexContainer: false,
		maxContainer: false,
		nextLink: false,
		prevLink: false,
		wrap: true,
		disabledLinkClass: 'disabled',
		onNext: Class.empty,
		onPrev: Class.empty,
		onSlideClick: Class.empty,
		crossFadeOptions: {}
	},
	initialize: function(options){
		this.setOptions(options);
		this.slides = [];
		this.now = this.options.startIndex;
		this.makeSlides(this.options.slides);
		this.setCounters();
		this.setUpNav();
		if (this.slides.length > 0) this.showSlide(this.now);
	},
	setCounters: function(){
		if ($(this.options.currentIndexContainer)) $(this.options.currentIndexContainer).setHTML(this.now + 1);
		if ($(this.options.maxContainer)) $(this.options.maxContainer).setHTML(this.slides.length);
	},
	makeSlides: function(slides){
		//hide them all
		slides.each(function(slide, index){
			if (index != this.now) slide.fade('hide');
			this.makeSlide(slide);
		}, this);
		
	},
	makeSlide: function(slide){
		this.slides.push(slide);
		slide.addEvent('click', function(){
			this.fireEvent('onSlideClick');
		}.bind(this));
		this.setCounters();
	},
	setUpNav: function(){
		if ($(this.options.nextLink)) $(this.options.nextLink).addEvent('click', function(){
			this.cycleForward();
		} .bind(this));
		if ($(this.options.prevLink)) $(this.options.prevLink).addEvent('click', function(){
			this.cycleBack();
		}.bind(this));
	},
	/*	Property: cycleForward
	 Shows the next slide.
	 */
	cycleForward: function() {
		if (this.now < this.slides.length - 1) {
			this.showSlide(this.now + 1);
		}
		else if (this.slides.length > 1 && this.options.wrap) {
			this.showSlide(0);
		}
		else return;
		this.fireEvent('onNext');
		if (this.now == this.slides.length && !this.options.wrap && $(this.options.nextLink)) {
			$(this.options.nextLink).addClass(this.options.disabledLinkClass);
		}
		else if ($(this.options.nextLink)) {
			$(this.options.nextLink).removeClass(this.options.disabledLinkClass);
		}
	},
	/*	Property: cycleBack
	 Shows the prev slide.
	 */
	cycleBack: function(){
		if (this.now > 0) {
			this.showSlide(this.now - 1);
			this.fireEvent('onPrev');
		}
		else if (this.options.wrap && this.slides.length > 1) {
			this.showSlide(this.slides.length - 1);
			this.fireEvent('onPrev');
		}
		if (this.now == 0 && !this.options.wrap && $(this.options.prevSlide)) $(this.options.prevSlide).addClass(this.options.disabledLinkClass);
		else if ($(this.options.prevSlide)) $(this.options.prevSlide).removeClass(this.options.disabledLinkClass);
	},
	/*	Property: showSlide
	 Shows a specific slide.
	 
	 Arguments:
	 iToShow - (integer) index of the slide to show.
	 */
	fadeIn: function(s){
//		s.addClass(this.options.currentSlideClass).effect('opacity', this.options.crossFadeOptions).start(1);
		s.addClass(this.options.currentSlideClass).get('tween', {property: 'opacity', duration: 'long'}).start(1);
	},
	fadeOut: function(s){
//		s.removeClass(this.options.currentSlideClass).effect('opacity', this.options.crossFadeOptions).start(0);
		s.removeClass(this.options.currentSlideClass).get('tween', {property: 'opacity', duration: 'long'}).start(0);
	},
	showSlide: function(iToShow){
		var cur = this.slides[this.now];
		var s = this.slides[iToShow];
		if (s) {
			if (this.now != iToShow) {
				this.fadeOut(cur);
				this.fadeIn(s);
			}
			else this.fadeIn(s);
			this.now = iToShow;
			this.setCounters();
		}
	},
	slideClick: function(){
		this.fireEvent('onSlideClick', [this.slides[this.now], this.now]);
	}
});
/*	Class: SimpleImageSlideShow
 Extends <SimpleSlideShow> to make a slideshow of images.
 
 Arguments:
 options - a key/value options object; inherits options from <SimpleSlideShow>.
 
 Options:
 imgUrls - (array; optional) an array of image urls to add to the dom and to the slideshow
 imgClass - (string; optional) a class to add to the images that get created on the fly
 container - (element; optional) if you are adding images to the dom either using <addImg> or
 the imgUrls array above, then "container" is required to know where to put them.
 */
var SimpleImageSlideShow = SimpleSlideShow.extend({
	options: {
		imgUrls: [],
		imgClass: 'screenshot',
		container: false
	},
	initialize: function(options){
		this.parent(options);
		var self = this;
		var cSize = $(this.options.container).getSize();
		new Asset.images(this.options.imgUrls, {
			onProgress: function(i){
				this.set({
					styles: {
						'position': 'absolute',
						'left': (cSize.x / 2) - (this.width / 2),
						'top': (cSize.y / 2) - (this.height / 2)
					},
					'opacity': 0,
					'id': self.options.imgClass + i,
					'class': self.options.imgClass
				}).inject(self.options.container);
				self.slides[i] = this;
				self.makeSlide(this);
			}
		})
	},
	/* Property: addImg 
	 * Adds a new image to the group
	 */
	addImg: function(url){
		if ($(this.options.container)) {
			var self = this;
			var img = new Asset.image(url, {
				'id': this.options.imgClass + this.slides.length,
				'class': this.options.imgClass,
				'onload': function(){
					var cSize = $(self.options.container).getSize();
					var pSize = this.getSize();
					this.set('styles', {
						'left': (cSize.x - pSize.x) / 2 + 'px',
						'top': (cSize.y - pSize.y) / 2 + 'px'
					});
				}
			}).setOpacity(0).inject($(this.options.container));
			this.makeSlide(img);
		}
	}
});


