(function($){
	
	$.ezbox = function(){
		
		var ie7 = jQuery.browser.msie && parseInt(jQuery.browser.version) < 8;
		var ie8 = jQuery.browser.msie && parseInt(jQuery.browser.version) < 9;
		var album;
		var current;
		var markup;
		var galleryLength;
		var galleryItems;
		
		var settings    = {
							counter: '%index sur %length',
							gallery: '<li rel="%index">%thumbnail</li>',
							pdf: '<iframe src="http://docs.google.com/viewer?url=%url&embedded=true" width="754" height="424" frameborder="0"></iframe>',
							vimeo: '<iframe src="http://player.vimeo.com/video/%url?title=0&byline=0&portrait=0&autoplay=1" width="754" height="424" frameborder="0"></iframe>',
							audio: '<object classid="clsid:d27cdb6e-ae6d-11cf-96b8-444553540000" codebase="http://download.macromedia.com/pub/shockwave/cabs/flash/swflash.cab#version=10,0,0,0" width="754" height="424" id="audio" align="middle">\
										<param name="allowScriptAccess" value="sameDomain" />\
										<param name="allowFullScreen" value="false" />\
										<param name="movie" value="%root/wp-content/themes/nte/swf/audio.swf?url=%url" />\
										<param name="quality" value="high" />\
										<param name="scale" value="noscale" />\
										<param name="salign" value="lt" />\
										<param name="wmode" value="opaque" />\
										<param name="bgcolor" value="#000000" />\
										<embed src="%root/wp-content/themes/nte/swf/audio.swf?url=%url" quality="high" scale="noscale" salign="lt" wmode="opaque" bgcolor="#000000" width="754" height="424" name="audio" align="middle" allowScriptAccess="sameDomain" allowFullScreen="false" type="application/x-shockwave-flash" pluginspage="http://www.adobe.com/go/getflashplayer" />\
									</object>'
						  };
						
		var loadMarkup  = '<p id="ez_loader">Téléchargement en cours</p>';
		var pageMarkup  = '<div id="ez_wrapper" class="page clearfix" style="display:none;">%data</div>';
		var pdfMarkup 	= '<div id="ez_wrapper" class="pdf clearfix" style="display:none;">%data</div>';
		var albumMarkup = '<div id="ez_wrapper" class="album clearfix" style="display:none;">\
								<div id="ez_gallery">\
									<div id="ez_gallery_holder">\
										<ul class="clearfix"></ul>\
									</div>\
									<a class="gallery-previous disabled">Précédent</a>\
									<a class="gallery-next disabled">Suivant</a>\
								</div>\
								<div id="ez_display" class="clearfix">\
									<div id="ez_display_holder"></div>\
									<a href="#" id="ez_previous">Précédent</a>\
									<a href="#" id="ez_next">Suivant</a>\
								</div>\
								<div id="ez_details">\
									<p id="ez_counter"></p>\
									<div id="ez_description"></div>\
								</div>\
						   </div>';
		
		// jquery Objects
		var overlay = $('<div id="ez_overlay"></div>').css('opacity', 0.75).click( function(){ $.ezbox.close(); } );
		var ezbox 	= $('<div id="ezbox"> \
							<a id="ez_close">Fermer</a> \
							<div id="ez_content"></div> \
						</div>');
		var content = ezbox.find('#ez_content');
		
		
		
		
		// events handling
		content.mouseenter(function(e){ $('#ez_next, #ez_previous').fadeIn('fast'); })
			   .mouseleave(function(e){ $('#ez_next, #ez_previous').fadeOut('fast'); });
		
		ezbox.delegate('#ez_close', 'click', function(e){ $.ezbox.close(); return false; } );
		ezbox.delegate('#ez_next', 'click', function(e){ $.ezbox.next(); return false; });
		ezbox.delegate('#ez_previous', 'click', function(e){ $.ezbox.previous(); return false; });
		ezbox.delegate('#ez_gallery li', 'click', function(e){ $.ezbox.to( parseInt($(this).attr('rel')) ); return false; });
		ezbox.delegate('#ez_gallery .gallery-next', 'click', function(e){
			
			if( $(this).hasClass('disabled') ) return;
			
			$('#ez_gallery a.gallery-previous').removeClass('disabled');
			
			var item = getLastGalleryItem();
			var left = parseInt(item.position().left) * -1;
			
			if( galleryLength + left < $('#ez_gallery_holder').width() )
			{
				left = $('#ez_gallery_holder').width() - galleryLength;
				$(this).addClass('disabled');
			};
			
			$('#ez_gallery ul').stop().animate({'left': left + "px"}, 'fast');
			return false;
		});
		ezbox.delegate('#ez_gallery .gallery-previous', 'click', function(e){
			
			if( $(this).hasClass('disabled') ) return;
			
			$('#ez_gallery a.gallery-next').removeClass('disabled');
			
			var item = getFirstGalleryItem();
			var left = parseInt(item.position().left) * -1;
			
			if( left == 0 ) $(this).addClass('disabled');
			$('#ez_gallery ul').animate({'left': left + "px"}, 'fast');
			
			return false;
		});
		
		
		
		
		// public API
		$.ezbox.album = function( id, index ){
			
			// stop cascade and grigoux for smooth animation
			cascade.stop();
			grigoux.stop();
			
			// reset content box
			reset('album');
			animateIn();
						
			
			// load album
			$.get($.admin_ajax, {action: "album", id: id}, function(data){
				
				album 		 = data;
				galleryItems = [];
				
				// create markup
				markup = $(albumMarkup);
				
				
				// gallery building
				var items = '', li, ul = markup.find('#ez_gallery ul'), i = 0, n = data.length, w;
				for(; i<n; i++)
				{
					li = $(settings.gallery.replace(/\%thumbnail/, data[i].thumbnail).replace(/\%index/, data[i].index));
					li.data('left', galleryLength );
					
					if( data[i].src.match(/vimeo\.com/i) ) vimeo_thumbnail(data[i].src, li);
					
					galleryItems.push( li );
					ul.append( li );
					
					w = ie8 ? parseInt(li.find('img').css('width')) : li.find('img').attr('width');
					galleryLength += w + 14;
				};
				
				ul.css('width', galleryLength + 'px').append( $(li) );
				galleryLength -= 14;
				
				
				
				
				// append markup
				content.append(markup);
				
				// load current item
				$.ezbox.to( index );
				
			}, 'json');
		};
		$.ezbox.cascade = function( id ){
			
			// stop cascade and grigoux for smooth animation
			cascade.stop();
			grigoux.stop();
			
			// reset and animate in
			reset('cascade');
			animateIn();
				
			$.get($.admin_ajax, {action: "cascade", cascade: id}, function(data){

				markup = $(pageMarkup.replace(/\%data/, data));
				content.append(markup);
				
				// viewport
				ezbox.find('#ez_loader').fadeOut(150, function(){ ezbox.find('#ez_loader').remove(); });
				
				var w  = 500; //markup.outerWidth();
				var h  = markup.outerHeight();
				var ww = $(window).width();
				var wh = $(window).height();
				
				var lrpadding = parseInt(content.css('paddingLeft')) + parseInt(content.css('paddingRight'));
				var tbpadding = parseInt(content.css('paddingTop')) + parseInt(content.css('paddingBottom')) + 30;
				
				var ow = w + lrpadding;
				var oh = h + tbpadding;
				
				if( ow > ww )
				{
					ow = ww - 10;
					w  = ow - lrpadding;
					
					markup.css('overflow-x', 'auto');
				};
				
				if( oh > wh )
				{
					oh = wh - 10;
					h  = oh - tbpadding;
					
					markup.css('overflow-y', 'auto');
				};
				
				ezbox.delay(150).animate({
											width: ow + "px", 
											height: oh + "px",
											marginLeft: ( -ow >> 1 ) + "px",
											marginTop: ( -oh >> 1 ) + "px"
							  			 }, 400);

				content.delay(150).animate({width: w+"px", height: h+'px'}, 400);
				markup.delay(550).fadeIn();
			});
		};
		$.ezbox.page = function( url ){
			
			// stop cascade and grigoux for smooth animation
			cascade.stop();
			grigoux.stop();
			
			// reset and animate in
			reset('page');
			animateIn();
				
			$.get($.admin_ajax, {action: "page", page: url}, function(data){

				markup = $(pageMarkup.replace(/\%data/, data));
				content.append(markup);
				
				// viewport
				ezbox.find('#ez_loader').fadeOut(150, function(){ ezbox.find('#ez_loader').remove(); });
				
				var w  = 500; //markup.outerWidth();
				var h  = markup.outerHeight();
				var ww = $(window).width();
				var wh = $(window).height();
				
				var lrpadding = parseInt(content.css('paddingLeft')) + parseInt(content.css('paddingRight'));
				var tbpadding = parseInt(content.css('paddingTop')) + parseInt(content.css('paddingBottom')) + 30;
				
				var ow = w + lrpadding;
				var oh = h + tbpadding;
				
				if( ow > ww )
				{
					ow = ww - 10;
					w  = ow - lrpadding;
					
					markup.css('overflow-x', 'auto');
				};
				
				if( oh > wh )
				{
					oh = wh - 10;
					h  = oh - tbpadding;
					
					markup.css('overflow-y', 'auto');
				};
				
				ezbox.delay(150).animate({
											width: ow + "px", 
											height: oh + "px",
											marginLeft: ( -ow >> 1 ) + "px",
											marginTop: ( -oh >> 1 ) + "px"
							  			 }, 400);

				content.delay(150).animate({width: w+"px", height: h+'px'}, 400);
				markup.delay(550).fadeIn();
			});
		};
		$.ezbox.pdf = function( url ){
			
			// stop cascade and grigoux for smooth animation
			cascade.stop();
			grigoux.stop();
			
			// reset and animate in
			reset('pdf');
			animateIn();
			
			markup = $(pdfMarkup.replace(/\%data/, settings.pdf.replace(/\%url/, url)));
			content.append(markup);
			
			// viewport
			ezbox.find('#ez_loader').fadeOut(150, function(){ ezbox.find('#ez_loader').remove(); });
			
			var w  = markup.outerWidth();
			var h  = markup.outerHeight();
			var ow = w + parseInt(content.css('paddingLeft')) + parseInt(content.css('paddingRight'));
			var oh = h + parseInt(content.css('paddingTop')) + parseInt(content.css('paddingBottom')) + 30;
			
			ezbox.delay(150).animate({
										width: ow + "px", 
										height: oh + "px",
										marginLeft: ( -ow >> 1 ) + "px",
										marginTop: ( -oh >> 1 ) + "px"
						  			 }, 400);

			content.delay(150).animate({width: w+"px", height: h+'px'}, 400);		
			markup.delay(550).fadeIn();
		};
		
		
		
		
		$.ezbox.close = function(){
			ezbox.detach();
			
			ezbox.width('auto').height('auto');
			ezbox.find('#ez_content').height('auto');
			
			$(overlay).fadeOut('fast', remove);
		};
		$.ezbox.next = function(){
			
			var index = current + 1;
			if( index == album.length ) index = 0;
			
			$.ezbox.to( index );
		};
		$.ezbox.previous = function(){
			
			var index = current - 1;
			if( index < 0 ) index = album.length - 1;
			
			$.ezbox.to( index );
		};
		$.ezbox.to = function( index ){
			
			// set current index
			if( current == index || index < 0 || index > album.length - 1 ) return;
			current = index;
			
			// select current item
			var item = album[current];
			
			// update description
			content.find('#ez_counter').empty().append( settings.counter.replace(/\%index/, current+1).replace(/\%length/, album.length));
			content.find('#ez_description').empty().append( item.content );
			
			// gallery navigation
			$('#ez_gallery li.selected').removeClass('selected');
			$('#ez_gallery li:eq('+current+')').addClass('selected');
			
			// add loader
			if( content.find('#ez_loader').length == 0 )
			{
				var holder = markup.find('#ez_display_holder')
					holder.css({width: holder.css('width'), height: holder.css('height')});
					holder.animate({opacity: 0}, 150, function(){
						markup.find('#ez_display').append(loadMarkup);
						load();
					});	
			}
			else load();
		};
		
		
		
		
		// private methods
		function animateIn(){
			$('body').append(overlay, ezbox);
			
			overlay.fadeIn('fast');
			ezbox.css({ marginLeft: -ezbox.outerWidth() >> 1, marginTop: -ezbox.outerHeight() >> 1 });
		};
		function fitToView(){
			
			// remove loader
			ezbox.find('#ez_loader').fadeOut(150, function(){ ezbox.find('#ez_loader').remove(); });
			
			
			// resize holder
			var holder = markup.find('#ez_display_holder');
			var file   = holder.find(':first-child');
			var old    = {width: holder.css('width'), height: holder.css('height')};
			var update = {width: file.css('width'), height: file.css('height')};
			
			holder.css(update);
			
			
			// calculate actual size
			var w  = markup.outerWidth();
			var h  = markup.outerHeight();
			
			var lrpadding = parseInt(content.css('paddingLeft')) + parseInt(content.css('paddingRight'));
			var tbpadding = parseInt(content.css('paddingTop')) + parseInt(content.css('paddingBottom')) + 30;
			
			var ow = w + lrpadding;
			var oh = h + tbpadding;
			
			if( ie7 )
			{
				ow = $(window).width() - 20;
				oh = $(window).height() - 20;
				
				w = ow - lrpadding;
				h = oh - tbpadding;
			};
			
			holder.css(old);
			
			
			
			// gallery navigation
			if( w < galleryLength )
			{
				var limit = -$('#ez_gallery_holder ul').position().left, i = 0, n = galleryItems.length, item;
				for(; i<n; i++)
				{
					item = galleryItems[i];
					if( item.data('left') >= limit ) break;
				};
				
				var left = parseInt(item.position().left) * -1;
				
				if( galleryLength + left < w ){ left = w - galleryLength; $('#ez_gallery a.gallery-next').addClass('disabled'); }
				else $('#ez_gallery a.gallery-next').removeClass('disabled');
				
				if( left == 0 ) $('#ez_gallery a.gallery-previous').addClass('disabled');
				else $('#ez_gallery a.gallery-previous').removeClass('disabled');
				
				$('#ez_gallery ul').delay(150).animate({'left': left + "px"}, 400);
			}
			else
			{
				$('#ez_gallery a.gallery-next, #ez_gallery a.galley-previous').addClass('disabled');
				$('#ez_gallery ul').delay(150).animate({left: '0px'}, 400);
			};
			
			
			
			// tween dimensions
			ezbox.delay(150).animate({
										width: ow + "px", 
										height: oh + "px",
										marginLeft: ( -ow >> 1 ) + "px",
										marginTop: ( -oh >> 1 ) + "px"
						  			 }, 400);
			
			content.delay(150).animate({width: w+"px", height: h+'px'}, 400);
			holder.delay(150).animate(update, 400).animate({opacity: 1}, 200)		
			markup.delay(550).fadeIn(200);
		};
		function getFirstGalleryItem(){
			
			var limit = -$('#ez_gallery_holder ul').position().left - $('#ez_gallery_holder').width(),
				i = 0, n = galleryItems.length, item;
			for(; i<n; i++)
			{
				item = galleryItems[i];
				if( item.data('left') >= limit ) break;
			};
			
			return galleryItems[i];
		};
		function getLastGalleryItem(){
			
			var limit = $('#ez_gallery_holder').width() - $('#ez_gallery_holder ul').position().left,
				n = galleryItems.length, item;
			
			while( --n >= 0 )
			{
				item = galleryItems[n];
				if( item.data('left') <= limit ) break;
			};
			
			return galleryItems[n];
		};
		function load(){
			
			var item = album[current];
			var mime = item.mime.split("/");
			
			if( item.src.match(/vimeo\.com/i) )
			{
				var match = item.src.match(/http:\/\/(www\.)?vimeo.com\/(\d+)/);
				
				content.find('#ez_display_holder').empty().append( $(settings.vimeo.replace(/\%url/, match[2])) );
				fitToView();
			}
			else if( mime[0] == "image" )
			{
				var img = $(item.src).load(function(){ 
					
					content.find('#ez_display_holder').empty().append( $(this) );	
					fitToView();
				});
			}
			else if( mime[1] == "pdf" )
			{			
				content.find('#ez_display_holder').empty().append( $(settings.pdf.replace(/\%url/, item.src)) );
				fitToView();
			}
			else if( mime[0] == "audio" )
			{
				content.find('#ez_display_holder')
					   .empty()
					   .append( settings.audio.replace(/\%url/g, item.src).replace(/\%root/g, $.application) );
					
				fitToView();
			}
		};
		function reset(type){
			
			album = null;
			current = null;
			markup = null;
			galleryLength = null;
			galleryItems = null;
			
			content.removeClass()
				   .addClass(type)
				   .empty()
				   .css({width: '32px', height: '32px'})
				   .append(loadMarkup);
		};
		function remove(){
			
			album = null;
			current = null;
			markup = null;
			galleryLength = null;
			galleryItems = null;
			
			overlay.detach();
			
			// restart cascade and grigoux
			cascade.start();
			grigoux.start();
		};
		function vimeo_thumbnail( src, el ){
			
			$.getJSON($.admin_ajax, {action: "proxy", id: src.split("/").pop()}, function(data){
				
				var item = data[0], css = {};

				if( $.browser.msie && $.browser.version < 9 ) css.filter = "progid:DXImageTransform.Microsoft.AlphaImageLoader(src='"+item.thumbnail_small+"', sizingMethod='scale')";
				else css.backgroundImage = 'url('+item.thumbnail_small+')';

				el.css(css);
			});
		}
		
	};
	
	$.ezbox();
	
})(jQuery);
