/*
---
name: Animate
description: Animate stuff.
license: MIT license
authors: [Tim Wienk]
requires: [Core/*]
provides: bbAnimate
...
*/

var bbAnimate = new Class({
	Implements: [Events, Options],
	options: {
		'container':  'animation',           // ID of container
		'objects':    '.animate',            // Selector for animating objects
		'animation':  'fade',                // Type of animation [fade, scroll]
		'direction':  'left',                // Direction (for scroll animation only) [left, right, top, bottom]
		'transition': Fx.Transitions.linear, // Transition to use for the animation
		'interval':   5000,                  // Interval between animations (milliseconds)
		'duration':   1000,                  // Animation duration (milliseconds)
		'autoPlay':   true,                  // Automatically animate
		'paging':     false                  // Element containing paging elements
	},
	initialize: function(options) {
		this.setOptions(options);
		this.con = $(this.options.container);
		this.obj = $(this.options.container).getElements(this.options.objects);
		this.cur = 0;
		this.fx = new Array();
		if (this.con.getStyle('position') == 'static') this.con.setStyle('position', 'relative');

		switch(this.options.animation) {
			case 'scroll':
				this.scroll();
				break;

			default:
				this.fade();
		}

		if (this.options.autoPlay) {
			this.play();
		}

		this.prevBtns = $(this.options.container+'_prev') || $$('.'+this.options.container+'_prev');
		if (this.prevBtns) {
			this.prevBtns.addEvent('click', this.prev.bind(this));
		}

		this.nextBtns = $(this.options.container+'_next') || $$('.'+this.options.container+'_next');
		if (this.nextBtns) {
			this.nextBtns.addEvent('click', this.next.bind(this));
		}

		if (this.options.paging) {
			this.pagers = $(this.options.paging).getElements('a');
			if (this.pagers) {
				this.pagers.each(function(a) {
					a.addEvent('click', function(e) {
						this.show(a, e);
					}.bind(this));
				}, this);
			}
		}
	},
	fade: function() {
		this.obj.each(function(o,i) {
			o.setStyle('position', 'absolute');
			this.fx[i] = new Fx.Tween(o, {property: 'opacity', duration: this.options.duration, transition: this.options.transition});
			if (i === 0) {
				this.fx[i].set(1);
			} else {
				this.fx[i].set(0);
			}
		}, this);

		this.doAnimate = function(toObj, backwards) {
			this.fx[this.cur].start(0);
			this.fx[toObj].start(1);
		};
	},
	scroll: function() {
		var mod = 1;
		if (this.options.direction == 'right' || this.options.direction == 'bottom') mod = -1;
		var scrollTo = this.con.getSize().x;
		if (this.options.direction == 'top' || this.options.direction == 'bottom') scrollTo = this.con.getSize().y;

		this.con.setStyles({
			'height': this.con.getSize().y,
			'width': this.con.getSize().x,
			'overflow': 'hidden'
		});
		this.obj.each(function(o,i) {
			o.setStyle('position', 'absolute');
			this.fx[i] = new Fx.Tween(o, {property: this.options.direction, duration: this.options.duration, transition: this.options.transition});
			if (i === 0) {
				this.fx[i].set(0);
			} else {
				this.fx[i].set(scrollTo);
			}
		}, this);

		this.doAnimate = function(toObj, backwards) {
			if (!backwards) var backwards = 1;
			this.fx[this.cur].start(-scrollTo*backwards);
			this.fx[toObj].set(scrollTo*backwards);
			this.fx[toObj].start(0);
		};
	},
	animate: function(to) {
		if (this.cur !== to) {
			if (this.prevBtns) {
				this.prevBtns.removeEvents('click');
				this.prevBtns.addEvent('click', function(e){if(e)e.stop()});
			}
			if (this.nextBtns) {
				this.nextBtns.removeEvents('click');
				this.nextBtns.addEvent('click', function(e){if(e)e.stop()});
			}
			if (this.pagers) {
				this.pagers.removeEvents('click');
				this.pagers.addEvent('click', function(e){if(e)e.stop();});
			}

			var toObj = this.cur+1;
			var backwards = 1;
			if (typeof(to) == 'number') {
				toObj = to;
				if (toObj < this.cur) {
					backwards = -1;
				}
			}
			if (toObj > this.fx.length-1) {
				toObj = 0;
			} else if (toObj < 0) {
				toObj = this.fx.length-1;
			}

			if (this.fx[toObj]) {
				if (this.pagers) {
					this.pagers[this.cur].removeClass('active');
					this.pagers[toObj].addClass('active');
				}
				this.doAnimate(toObj, backwards);
				this.cur = toObj;
			}

			(function() {
				if (this.prevBtns) {
					this.prevBtns.removeEvents('click');
					this.prevBtns.addEvent('click', this.prev.bind(this));
				}
				if (this.nextBtns) {
					this.nextBtns.removeEvents('click');
					this.nextBtns.addEvent('click', this.next.bind(this));
				}
				if (this.pagers) {
					this.pagers.removeEvents('click');
					this.pagers.each(function(a) {
						a.addEvent('click', function(e) {
							this.show(a, e);
						}.bind(this));
					}, this);
				}
			}).delay(this.options.duration+100, this);
		}
	},
	play: function(e) {
		if (e) e.stop();
		if (this.animation) {
			$clear(this.animation);
		}
		this.animation = this.animate.periodical(this.options.interval, this);
	},
	pause: function(e) {
		if (e) e.stop();
		if (this.animation) {
			$clear(this.animation);
		}
	},
	prev: function(e) {
		if (e) e.stop();
		if (this.animation) {
			$clear(this.animation);
			this.animate(this.cur-1);
			this.animation = this.animate.periodical(this.options.interval, this);
		} else {
			this.animate(this.cur-1);
		}
	},
	next: function(e) {
		if (e) e.stop();
		if (this.animation) {
			$clear(this.animation);
			this.animate();
			this.animation = this.animate.periodical(this.options.interval, this);
		} else {
			this.animate(this.cur+1);
		}
	},
	show: function(a, e) {
		if (e) e.stop();
		if (this.animation) {
			$clear(this.animation);
			this.animate(a.getProperty('href').replace(/[^0-9]/gi,'').toInt());
			this.animation = this.animate.periodical(this.options.interval, this);
		} else {
			this.animate(a.getProperty('href').replace(/[^0-9]/gi,'').toInt());
		}
	}
});

