/**
 * Slideshow controller that accomodates with options for a prev/next togger, multiple togglers, or a combination of both
 * @alias SlideShow
 * @param {string} initial This is the index of the inital slide to appear on page load
 * @param {string} container This is the parent HTML element
 * @param {array} contents This is an array of slides
 * @param {integer} delay This is the delay between each slide transition
 * @param {array} options This is a set of options that can be passed such as prev/next togglers, multiple togglers
 */
 
 /*
if ($('slideshow')) {
	show = new SlideShow(0, $('slideshow'), $$('#slideshow .slide'), 8);
}
*/
 
var SlideShow = Class.create({
	initialize : function (initial, container, contents, delay, options) {
		this.initial = initial;
		this.container = container;
		this.contents = contents;
		this.delay = delay;
		this.fadeDuration = 0.5;
		this.showOnly(this.contents[this.initial]);
		this.current = initial;
		this.show = null;
		this.hide = null;
		
		this.options = Object.extend({
			prevToggler: '.prev',
			nextToggler: '.next',
			btnToggler: '.controls li'
		}, options || {});
		
		if (this.container.select(this.options.prevToggler).length > 0 && this.container.select(this.options.nextToggler).length > 0) {
			this.prevBtn = this.container.select('.prev')[0].addClassName('active');
			this.nextBtn = this.container.select('.next')[0].addClassName('active');
			this.prevBtn.observe('click', this.back.bindAsEventListener(this));
			this.nextBtn.observe('click', this.forward.bindAsEventListener(this));
			
			//handle ie6's lack of hover support on non-anchor elements
			if (Prototype.Browser.IE6) {
				this.prevBtn.observe('mouseenter', function () {
					this.addClassName('hover_prev');
				});
				this.prevBtn.observe('mouseleave', function () {
					this.removeClassName('hover_prev');
				});
			}
		}
		else if (this.container.select(this.options.btnToggler).length > 0) {
			this.buttons = this.container.select(this.options.btnToggler);
			this.buttons.each(function (el, i) {
				el.observe('click', function (ev) {
					ev.stop();
					this.pause();
					this.goTo(i, 0.5);
				}.bind(this));
			}.bind(this));
			
			this.buttons[this.current].addClassName('active');
			
		}
		else { 
			return;
		}
		
		document.observe('pop:active',  this.pause.bind(this));
		document.observe('pop:inactive',  this.start.bind(this));
		
		this.start();
	},
	start : function () {
		if (this.timer) { 
			return;
		}
		this.timer = setTimeout(this.next.bind(this), this.delay * 1000);
	},
	showOnly : function (el) {
		this.contents.invoke('hide');
		el.show();
	},
	pause : function () {
		if (this.timer) {
			clearTimeout(this.timer);
			this.timer = false;
		}
		if (this.hide) {
			this.hide.cancel();
		}
		else {
			return;
		}
	},
	back: function (ev) {
		if (this.show) {
			this.show.cancel();
			return;
		}	
		if (this.hide) {
			this.hide.cancel();
			return;
		}	

		this.pause(); 
		if (this.current === 0) {
			this.goTo(this.contents.length - 1);
		}
		else {
			this.goTo(this.current - 1);
		}
		ev.stop(); 
	},
	forward: function (ev) {
		if (this.show) {
			this.show.cancel();
			return;
		}	
		if (this.hide) {
			this.hide.cancel();
			return;
		}	
		
		this.pause();
		this.next();
		ev.stop(); 
	}, 
	next: function () {
		this.timer = false;
		if (this.current === this.contents.length - 1) {
			this.goTo(0);
		}
		else {
			this.goTo(this.current + 1);
		}
		this.start();
	},	
	goTo: function (idx, dur) {
		if (idx === this.current) { 
			return;
		}
		this.hide = new Effect.Fade(this.contents[this.current], { duration: this.fadeDuration || 2, afterFinish: function () {
			this.hide = null;
		}.bind(this)});
		
		if (this.buttons) {
			this.buttons[this.current].removeClassName('active');
		}
		
		this.current = idx;
		this.show = new Effect.Appear(this.contents[this.current], { duration: this.fadeDuration || 2, afterFinish: function () {
			this.show = null; 
		}.bind(this)});
		
		if (this.buttons) {
			this.buttons[this.current].addClassName('active');
			this.start();
		}
	}
});

/**
 * Input prompt controller 
 * @alias Prompt
 * @param {string} field The parent html element
 */
var Prompt = Class.create({
	initialize: function (field) {
		this.field = $(field);
		this.label = this.field.down('label'); // the <label>
		this.input = this.field.down('input.prompt'); // the <input>
		this.setup();
	},
	setup: function () {
		this.label.observe('click', this.focus.bind(this));
		this.input.observe('focus', this.focus.bind(this));
		this.input.observe('blur', this.blur.bind(this));
	},
	focus: function () {
		this.field.addClassName('active');
		this.input.addClassName('active');
	},
	blur: function () {
		this.input.removeClassName('active');
		this.field.removeClassName('active');
	}
});


/**
 * Input prompt controller that toggles a <label>'s visibility over a textbox
 * Upon focus or click, the <label> is hidden
 * If no text is entered and the user loses focus to the input, the <label> reappears
 * @alias PromptLabel
 * @param {string} field The parent html element
 */
var PromptLabel = Class.create({
	initialize: function (field) {
		this.field = $(field);
		this.label = this.field.down('label'); // the <label>
		this.input = this.field.down('input.prompt'); // the <input>
		this.setup();
	},
	setup: function () {
		if (this.input.value !== '') {
			this.focus();
		}
		this.label.observe('click', this.focus.bind(this));
		this.input.observe('focus', this.focus.bind(this));
		this.input.observe('blur', this.blur.bind(this));
	},
	focus: function () {
		this.label.hide();
		this.field.addClassName('active');
		this.input.addClassName('active');
	},
	blur: function () {
		if (this.input.value === '') {
			this.label.show();
		}
		this.field.removeClassName('active');
	}
});



/**
 * dom:loaded function calls
 */
document.observe('dom:loaded', function () {
	if ($('slideshow')) {
		show = new SlideShow(0, $('slideshow'), $$('#slideshow .slide'), 8);
	}
	
	/* affiliate log in tout */
	$$('#quick_quote .field').each(function(el) {
		new PromptLabel(el);										  
	});

});


