(function($) {
	$.widget('ui.photoviewer', {
		images: [],
		pload_images: [],
		container: null,
		overlay: null,
		viewers: [null, null],
		panel: null,
		viewer: 0,
		running: false,
		current_img: null,
		loaded: false,
		_init: function() {
			var self = this;

			$(window).keypress(function(event) {
				if ( event.keyCode == 27 ) {
					self.close();
				}
			});
			$(this.options.selector, this.element).each(function() {
				self.images.push(this.href);
				self.pload_images.push(false);
			}).click(function() {
				self._display(this.href);
				return false;
			});
			this._preloading();
			this._addelements();
			this._addevents();
		},
		_preloading: function() {
			var self = this;

			$.each(this.pload_images, function(k, v) {
				if ( ! v ) {
					var img = new Image();
					img.onload = function() {
						self.pload_images[k] = true;
						window.setTimeout(function() {
							self._preloading();
						}, 200);
					}
					img.src = self.images[k];
					return false;
				}
			});
		},
		_addelements: function() {
			var self = this;

			//append the viewers elements to the document
			this.container = $('<div class="ui-photoviewer-container"></div>').appendTo('body').hide();
			var overlay = null;
			if ( this.options.overlay ) {
				this.overlay = $('<div class="ui-widget-overlay"></div>').appendTo(this.container);
			}
			this.panel = $('<div/>').addClass('ui-widget-header ui-corner-all ui-photoviewer-panel');
			$('<ul class="ui-widget ui-helper-clearfix">'
				+'<li class="ui-state-default ui-corner-all" title="Prev">'
				+'	<span class="ui-icon ui-icon-seek-prev"></span>'
				+'</li>'
				+'<li class="ui-state-default ui-corner-all" title="Play">'
				+'	<span class="ui-icon ui-icon-play"></span>'
				+'</li>'
				+'<li class="ui-state-default ui-corner-all" title="Next">'
				+'	<span class="ui-icon ui-icon-seek-next"></span>'
				+'</li>'
				+'<li class="photo_counter ui-state-default ui-corner-all ui-state-active" title="Counter">'
				+'</li>'
				+'<li class="ui-state-default ui-corner-all" title="Close">'
				+'	<span class="ui-icon ui-icon-close"></span>'
				+'</li>'
			+'</ul>').appendTo(this.panel);
			this.panel.appendTo(this.container);

			//change apereance of the panel according to the options and number of images
			if ( this.options.autorun && this.images.length > 1) {
				$('.ui-icon-play', this.panel).removeClass('ui-icon-play').addClass('ui-icon-stop');
				$('li[title="Next"],li[title="Prev"]', this.panel).addClass('ui-state-disabled');
			} else if ( this.images.length <= 1 ) {
				$('li[title!="Close"]', this.panel).addClass('ui-state-disabled');			
			}
			//format panel
			$('li[title="Counter"]').css({
				cursor: 'default'
			});

			//append viewer containers
			this.viewers[0] = $('<div class="ui-dialog ui-widget ui-widget-content ui-corner-all ui-photoviewer-viewer" style="overflow:hidden;"><img style="position:relative;" /></div>')
				.appendTo(this.container).hide();

			this.viewers[1] = $('<div class="ui-dialog ui-widget ui-widget-content ui-corner-all ui-photoviewer-viewer" style="overflow:hidden;"><img style="position:relative;" /></div>')
				.appendTo(this.container).hide();
		},
		_addevents: function() {
			var self = this;

			//close on click at overlay
			this.overlay.add('.ui-icon-close', this.panel).click(function() {
				self.close();
			});

			//pic loaded handler
			this.viewers[0].find('img').load(function() {
				self._resize();
			});
			this.viewers[1].find('img').load(function() {
				self._resize();
			});

			//panel events
			$('.ui-icon-seek-prev', this.panel).click(function(){
				if ( ! $(this).closest('li').hasClass('ui-state-disabled') ) {
					self.prev();
				}
			});
			$('.ui-icon-seek-next', this.panel).click(function(){
				if ( ! $(this).closest('li').hasClass('ui-state-disabled') ) {
					self.next();
				} 
			});
			$('.ui-icon-play', this.panel).click(function(event){
				if ( ! $(this).closest('li').hasClass('ui-state-disabled') ) {
					if ( self.running ) {
						self._slides('stop');
					} else {
						self._slides('start');
					}
				}
			});
			$('li', this.panel).hover(function () {
				$(this).addClass('ui-state-hover');
			}, function () {
				$(this).removeClass('ui-state-hover');
			});
		},
		_display: function(start_img) {
			var self = this;

			var start_key = 0;
			$.each(this.images, function(k, v) {
				if ( v == start_img ) {
					start_key = k;
					return false;
				}
			});

			this.viewers[0].show();
			this.viewers[1].hide();
			this.container.fadeIn(500);
			this._loadimage(start_key, 0);
			if ( this.options.autorun && this.images.length > 1 || start_img == 'slide') {
				this._slides('start');
			}
		},
		_loadimage: function(key, viewer) {
			this.panel.find('.photo_counter').text((key+1)+'/'+this.images.length);
			this.viewer = viewer;
			this.current_img = key;
			this.viewers[viewer].find('img').attr('src', this.images[key]);
		},
		_resize: function() {
			var viewer = this.viewers[this.viewer];
			var img = $('img', viewer);
			img.stop().css({
				width: 'auto',
				height: 'auto'
			});
			var outerWidth = parseInt(img[0].width);
			var outerHeight = parseInt(img.height());

			ratio = Math.min(Math.min($(window).width() - 36, outerWidth) / outerWidth, Math.min($(window).height() - 100, outerHeight) / outerHeight);
			img.css({
				left: '0px',
				width: Math.round(ratio * outerWidth),
				height: Math.round(ratio * outerHeight)
			});

			var viewer_width = Math.round(ratio * outerWidth) - this.options.fadingSize;
			viewer.css({
				width: viewer_width,
				left: parseInt($(document).width()) / 2 - viewer_width / 2
			});
			this.panel.css({
				left: parseInt($(document).width()) / 2 - this.panel.width() / 2
			});
			this._animate(img);
		},
		_animate: function(img) {
			img.animate({
				left: (this.options.fadingSize * -1) 
			}, 4000);
		},
		_slides: function(action) {
			var self = this;
			if ( action == 'start' && ! this.runnig ) {
				this.running = window.setInterval(function(){
					self.next();
				}, this.options.slidedelay);
				$('li[title=Play] span', this.panel).removeClass('ui-icon-play').addClass('ui-icon-stop');
				self.panel.find('li[title="Next"],li[title="Prev"]').addClass('ui-state-disabled');
			} else if ( action == 'stop' ) {
				window.clearInterval(this.running);
				self.running = null;
				$('li[title=Play] span', this.panel).addClass('ui-icon-play').removeClass('ui-icon-stop');
				self.panel.find('li[title="Next"],li[title="Prev"]').removeClass('ui-state-disabled');
			}
		},
		_fadeto: function(key) {
			var hidden_viewer = this.viewer == 1 ? 0 : 1;
			var viewer = this.viewers[this.viewer];
			var viewer_new = this.viewers[hidden_viewer];

			
			
			viewer_new.fadeIn(500);
			viewer.fadeOut(500);
			this._loadimage(key, hidden_viewer);
		},
		next: function() {
			var next = this.current_img+1;
			if ( next == this.images.length ) {
				next = 0;
			}
			this._fadeto(next);
		},
		prev: function() {
			var prev = this.current_img-1;
			if ( prev < 0 ) {
				prev = this.images.length-1;
			}
			this._fadeto(prev);
		},
		close: function() {
			this._slides('stop');
			this.container.fadeOut(500);
		},
		open: function(pic) {
			this._display(pic);
		}
	});

	$.extend($.ui.photoviewer, {
		defaults: {
			slidedelay: 8000,
			loop: true,
			overlay: true,
			fadingSize: 25,
			autorun: false,
			selector: "a[href]:has(img[src])"
		}
	});
})(jQuery);

