(function() {

var Event = YAHOO.util.Event,
	Sel = YAHOO.util.Selector,
	Dom = YAHOO.util.Dom,
	extensionRegExp = new RegExp('(.+)(\\.[a-z0-9]+)$', 'i'),
	urlRegExp = new RegExp('url\\([\'"]?(.*?)[\'"]?\\)');

/**
 * For best IE compatibility wait for the window object's load event before creating ImageSwitchers
 */
IRIS.widget.ImageSwitcher = function( el, cfg ) {
	this.cfg = {};
	if( typeof el == 'string' ) {
		el = Dom.get(el);
	}
	this.el = el;
	cfg = (cfg ? cfg : {});
	if( cfg.suffixes ) {
		this.suffixes = cfg.suffixes;
	}
	if( cfg.states ) {
		this.states = cfg.states;
	}
	if( cfg.on ) {
		for( var event in cfg.on ) {
			Event.on(this.el, event, cfg.on[event], this);
		}
	}
	IRIS.widget.ImageSwitcher.instances[el.id] = this;
};

IRIS.widget.ImageSwitcher.instances = {};
IRIS.widget.ImageSwitcher.getInstance = function( id ) {
	return IRIS.widget.ImageSwitcher.instances[id];
};

IRIS.widget.ImageSwitcher.prototype = {
	el: null,
	imageUri: null,
	useBackground: false,
	suffixes: {},
	defaultState: false,
	preLoaded: [],
	updateImageUri: function( uri ) {
		uri = (uri ? uri : this.getImageUri());
		if( uri && (matches = extensionRegExp.exec(uri)) ) {
			this.imageUri = [matches[1], matches[2]];
		}
	},
	setState: function( state ) {
		this.setImageUri(this.getStateUri(state));
	},
	getImageUri: function( el ) {
		var rv, matches, bg;
		if( !el ) {
			el = this.el;
		}
		if( el.tagName && ((el.tagName.toLowerCase() == 'img')
				|| (el.tagName.toLowerCase() == 'input' && el.type == 'image') ) ) {
			rv = el.src;
		}
		else if( bg = Dom.getStyle(el, 'backgroundImage') ) {
			if( matches = urlRegExp.exec(bg) ) {
				this.useBackground = true;
				rv = matches[1];
			}
		}
		if( rv ) {
			this.preLoaded.push(rv);
		}
		return rv;
	},
	getStateUri: function( state ) {
		if( this.imageUri === null ) {
			this.updateImageUri();
		}
		if( !this.imageUri ) {
			return;
		}
		if( !state ) {
			state = this.defaultState;
		}
		if( state ) {
			var suffix = (this.suffixes[state] ? this.suffixes[state] : state)
			return this.imageUri[0] + '_' + suffix + this.imageUri[1];
		}
		else {
			return this.imageUri[0] + this.imageUri[1];
		}
	},
	setDefaultState: function( state ) {
		this.defaultState = state;
	},
	setImageUri: function( uri, dontPreload ) {
		if( !dontPreload && (this.preLoaded.indexOf(uri) == -1) ) {
			this.preLoadImage(uri, function() {
				this.setImageUri(uri);
			}, this, true);
		}
		else {
			if( this.useBackground ) {
				this.el.style.backgroundImage = 'url(' + uri + ')';
			}
			else {
				this.el.src = uri;
			}
		}
	},
	preLoadImages: function( callback, scope, setScope ) {
		for( var i = 0; i < this.states.length; i++ ) {
			this.preLoadImage(this.getStateUri(this.states[i]), callback, scope, setScope);
		}
	},
	preLoadState: function( state, callback, scope, setScope ) {
		this.preLoadImage(this.getStateUri(state), callback, scope, setScope);
	},
	preLoadImage: function( uri, callback, scope, setScope ) {
		if( !uri ) {
			return;
		}
		if( !Event.DOMReady ) {
			Event.onDOMReady(function() {
				this.preLoadImage(uri, callback, scope, setScope);
			}, this, true);
		}
		else if( this.preLoaded.indexOf(uri) != -1 ) {
			if( callback ) {
				callback.call(setScope ? scope : this);
			}
		}
		else {
			this.preLoaded.push(uri);
			new IRIS.widget.ImageLoader(uri, callback, scope, setScope);
		}
	}
};

IRIS.widget.ImageLoader = function( uri, callback, scope ) {
	var image = new Image();
	image.src = uri;
	image.style.position = 'absolute';
	image.style.visibility = 'hidden';
	image.style.top = '0px';
	image.style.left = '0px';
	IRIS.getBody().appendChild(image);
	if( callback ) {
		if( YAHOO.env.ua.ie ) {
			var pollImage = function() {
				if( image.width ) {
					callback.call(scope);
				}
				else {
					setTimeout(pollImage, 100);
				}
			};
			pollImage.call();
		}
		else {
			Event.on(image, 'load', callback, scope, true);
		}
	}
};

IRIS.widget.RolloverImage = function( el, cfg ) {
	IRIS.widget.RolloverImage.superclass.constructor.call(this, el, cfg);
	this.updateImageUri(cfg ? cfg.uri : null);
};
YAHOO.extend(IRIS.widget.RolloverImage, IRIS.widget.ImageSwitcher, {
	states: ['over'],
	init: function() {
		this.preLoadImages(function() {
				Event.on(this.el, 'mouseover', this.mouseOver, this, true);
				Event.on(this.el, 'mouseout', this.mouseOut, this, true);
		}, this, true);
	},
	mouseOver: function() {
		this.setState('over');
	},
	mouseOut: function() {
		this.setState();
	}
});

IRIS.widget.PreLoadImage = function( el, cfg ) {
	IRIS.widget.PreLoadImage.superclass.constructor.call(this, el, cfg);
	this.updateImageUri(cfg ? cfg.uri : null);
};
YAHOO.extend(IRIS.widget.PreLoadImage, IRIS.widget.ImageSwitcher, {
	states: ['over'],
	init: function() {
		this.preLoadImages();
	}
});

IRIS.widget.SlideShow = function( el, cfg ) {
	var i, j;
	this.images = [];
	this.pos = 0;
	this.cfg = {
		delay: 1000,
		random: false
	};
	this.displayed = [];
	IRIS.widget.SlideShow.superclass.constructor.call(this, el, cfg);
	if( cfg.images ) {
		this.images = cfg.images;
		for( i in this.cfg ) {
			if( cfg[i] ) {
				this.cfg[i] = cfg[i];
			}
		}
		if( cfg.baseUri ) {
			if( cfg.baseUri.substring(cfg.baseUri.length - 1) != '/' ) {
				cfg.baseUri += '/';
			}
			for( var i = 0; i < this.images.length; i++ ) {
				this.images[i] = cfg.baseUri + this.images[i];
			}
		}
		if( this.cfg.random ) {
			var images = [];
			for( i = 0; i < this.images.length; i++ ) {
				do {
					j = Math.round(Math.random() * (this.images.length - 1));
				}
				while( !YAHOO.util.Lang.isUndefined(images[j]) );
				images[j] = this.images[i];
			}
			this.images = images;
		}
		this.showNextImage();
	}
};
YAHOO.extend(IRIS.widget.SlideShow, IRIS.widget.ImageSwitcher, {
	showNextImage: function() {
		this.pos += 1;
		if( this.pos > (this.images.length - 1) ) {
			this.pos = 0;
		}
		this.showImage();
	},
	showImage: function() {
		this.setImageUri(this.images[this.pos]);
		var obj = this;
		setTimeout(function() {
			obj.showNextImage();
		}, this.cfg.delay);
	}
});

IRIS.widget.MapSwitcher = function( el, cfg ) {
	IRIS.widget.MapSwitcher.superclass.constructor.call(this, el, cfg);
	if( cfg.map ) {
		this.map = (typeof cfg.map == 'string' ? Dom.get(cfg.map) : cfg.map);
	}
};

YAHOO.extend(IRIS.widget.MapSwitcher, IRIS.widget.ImageSwitcher, {
	init: function() {
		var areas = Dom.getChildren(this.map), i;
		this.states = [];
		for( i = 0; i < areas.length; i++ ) {
			if( areas[i].id ) {
				this.states[i] = areas[i].id;
				Event.on(areas[i], 'mouseover', function(e) {
					this.setState(Event.getTarget(e).id);
				}, this, true);
				Event.on(areas[i], 'mouseout', function(e) {
					this.setState(null);
				}, this, true);
			}
		};
		this.preLoadImages();
	}
});

IRIS.widget.ImageSwitcher.init = function( elements, cfg ) {
	if( !YAHOO.lang.isArray(elements) ) {
		elements = Sel.query(elements ? elements : '.rollover');
	}
	if( elements && elements.length ) {
		for( var i = 0; i < elements.length; i++ ) {
			new IRIS.widget.RolloverImage(elements[i], cfg).init();
		}
	}
};

IRIS.widget.ImageSwitcher.preLoadImages = function( selector ) {
	var elements = Sel.query(selector), i;
	for( i = 0; i < elements.length; i++ ) {
		new IRIS.widget.PreLoadImage(elements[i]).init();
	}
};

IRIS.widget.ImageSwitcher.handleSelected = function() {
	var body = IRIS.getBody(), matches, selected, switcher;
	if( matches = new RegExp('page_(.+?)( |$)').exec(body.className) ) {
		if( matches[1] == 'index' ) {
			if( body.id != 'page_index' ) {
				matches[1] = false;
			}
			else {
				matches[1] = 'home';
			}
		}
		if( matches[1] && (selected = Sel.query('#' + matches[1], null, true)) ) {
			Dom.addClass(selected, 'selected');
			if( switcher = IRIS.widget.ImageSwitcher.getInstance(matches[1]) ) {
				switcher.setDefaultState('over');
				switcher.setState('over');
			}
		}
	}
};

Event.on(window, 'load', function() { IRIS.widget.ImageSwitcher.init() });

}());