/************************************************/
/* IPB3 Javascript								*/
/* -------------------------------------------- */
/* ips.slideshow.js - Gallery slideshow code	*/
/* (c) IPS, Inc 2009							*/
/* -------------------------------------------- */
/* Author: Rikki Tissier						*/
/************************************************/

var _ss = window.IPBoard;

_ss.prototype.slideshow = {
	
	/* Current ID */
	currentImage: 0,
	/* Paused? */
	paused: false,
	/* Length of fade transition */
	transitionLen: 0.6,
	/* Time between images */
	speed: 4,
	/* Size of the window */
	holderSize: [],
	/* Size of the thumbnails */
	thumbSize: 0,
	/* Have we stopped auto-scrolling the thumbbar for now? */
	stopAutoScroll: false,
	/* Timer for autoscroll */
	autoScrollTimer: null,
	
	/*------------------------------*/
	/* Constructor 					*/
	init: function()
	{
		Debug.write("Initializing ips.slideshow.js");
		
		document.observe("dom:loaded", function(){
			
			// Set up button events
			$( 'c_PREV' ).observe('click', ipb.slideshow.buttonPrevious);
			$( 'c_PAUSE_PLAY' ).observe('click', ipb.slideshow.buttonPause);
			$( 'c_NEXT' ).observe('click', ipb.slideshow.buttonNext);
			$( 'button_left' ).observe('click', ipb.slideshow.thumbPrev);
			$( 'button_right' ).observe('click', ipb.slideshow.thumbNext);
			
			
			// Preload first image
			var firstImage = IMAGES.first();			
			ipb.slideshow.loadImage( firstImage, IMAGE_DATA.get( firstImage )['filename'] );
			
			// While that's going, get holder size
			ipb.slideshow.holderSize = $('image_holder').getDimensions();
			Event.observe( window, 'resize', ipb.slideshow.resizeWindow );
			
			// Build thumbnails
			ipb.slideshow.buildThumbnails();
			ipb.delegate.register('.thumb', ipb.slideshow.thumbnailClick);
			
			// Get width of thumbnail wrapper
			Debug.write( "Viewport width: " + ipb.slideshow.holderSize['width'] );
			Debug.write( "Thumbnail wrapper: " + $('thumbnail_wrap').getDimensions()['width'] );
			
			// Kick the slideshow off
			Debug.write("Starting slideshow...");
			ipb.slideshow.play();
			
		});
	},
	
	/*------------------------------*/
	/* scrolls the thumb bar left 	*/
	thumbPrev: function(e)
	{
		if( !$('button_left').hasClassName('active') || $('button_left').hasClassName('disabled') ){
			return;
		}
		
		var barLeft = parseInt( $('thumbnail_wrap').getStyle('left') );
		var moveX = ipb.slideshow.thumbSize;
		
		if( ( barLeft + ipb.slideshow.thumbSize ) > 30 ){
			moveX = barLeft - 30;
		}
		 		
		new Effect.Move( $('thumbnail_wrap'), { x: moveX, y: 0, duration: 0.2, mode: 'relative', afterFinish: function(){ ipb.slideshow.recalculateThumbnailButtons(); } } );
		
		// Wait for more user input
		ipb.slideshow.stopAutoScroll = true;		
		clearTimeout( ipb.slideshow.autoScrollTimer );
		ipb.slideshow.autoScrollTimer = setTimeout( ipb.slideshow.clearAutoScrollWait, 8000 );				
	},
	
	/*------------------------------*/
	/* scrolls the thumb bar right	*/
	thumbNext: function(e)
	{
		if( !$('button_right').hasClassName('active') || $('button_right').hasClassName('disabled') ){
			return;
		} 
		
		new Effect.Move( $('thumbnail_wrap'), { x: ( -1 * ipb.slideshow.thumbSize ), y: 0, duration: 0.2, mode: 'relative', afterFinish: function(){ ipb.slideshow.recalculateThumbnailButtons(); } } );

		// Wait for more user input
		ipb.slideshow.stopAutoScroll = true;		
		clearTimeout( ipb.slideshow.autoScrollTimer );
		ipb.slideshow.autoScrollTimer = setTimeout( ipb.slideshow.clearAutoScrollWait, 8000 );		
	},
	
	/*-------------------------------*/
	/* Callback to resume autoscroll */
	clearAutoScrollWait: function()
	{
		ipb.slideshow.stopAutoScroll = false;
		return;		
	},	
	
	/*------------------------------*/
	/* User is jumping to an image  */
	thumbnailClick: function(e, elem)
	{
		Event.stop(e);
		
		var thumbID = $( elem ).id.replace('thumb_', '');
		
		// Are we paused? If not, do so
		if( !ipb.slideshow.paused ){
			ipb.slideshow.pause();
		}
		
		ipb.slideshow.loadImage( thumbID, IMAGE_DATA.get( thumbID )['filename'] );
		ipb.slideshow.update( thumbID );
	},	
	
	/*------------------------*/
	/* Plays the slideshow 	  */
	play: function()
	{
		var mainLoop = function()
		{
			var nextImage = ipb.slideshow.getNextID();
			ipb.slideshow.update( nextImage );
			
			// Get the next image ready
			var oneAfter = ipb.slideshow.getNextID( nextImage );
			ipb.slideshow.loadImage( oneAfter, IMAGE_DATA.get( oneAfter )['filename'] );
			
			// Continue slideshow
			ipb.slideshow.mainLoop = setTimeout( mainLoop, ( ipb.slideshow.speed * 1000 ) );
		};
		
		mainLoop();					
	},
	
	/*------------------------*/
	/* Pause button	          */
	buttonPause: function(e)
	{
		Event.stop(e);
		
		if( !ipb.slideshow.paused ){
			ipb.slideshow.pause();
		} else {
			ipb.slideshow.unpause();
		}		
	},
	
	/*-------------------------*/
	/* Next image button  	   */
	buttonNext: function(e)
	{
		Event.stop(e);
		
		// Are we paused? If not, do so
		if( !ipb.slideshow.paused ){
			ipb.slideshow.pause();
		}
		
		// Go to the next image
		var nextImage = ipb.slideshow.getNextID();
		ipb.slideshow.loadImage( nextImage, IMAGE_DATA.get( nextImage )['filename'] );
		ipb.slideshow.update( nextImage );		
	},
	
	/*-------------------------*/
	/* Next image button  	   */
	buttonPrevious: function(e)
	{
		Event.stop(e);
		
		// Are we paused? If not, do so
		if( !ipb.slideshow.paused ){
			ipb.slideshow.pause();
		}
		
		// Go to the next image
		var prevImage = ipb.slideshow.getPrevID();
		ipb.slideshow.loadImage( prevImage, IMAGE_DATA.get( prevImage )['filename'] );
		ipb.slideshow.update( prevImage );		
	},
	
	/*-------------------------*/
	/* Pauses				   */
	pause: function()
	{
		clearTimeout( ipb.slideshow.mainLoop );
		ipb.slideshow.paused = 1;
		$('c_PAUSE_PLAY').addClassName('paused');
		Debug.write("Slideshow is paused.");
	},
	
	/*-------------------------*/
	/* Unpauses				   */
	unpause: function()
	{
		ipb.slideshow.play();
		ipb.slideshow.paused = 0;
		$('c_PAUSE_PLAY').removeClassName('paused');
		Debug.write("Slideshow is playing.");
	},
	
	/*-----------------------------------*/
	/* Readies the next image to display */
	update: function( nextImage )
	{
		if( ipb.slideshow.currentImage == nextImage ){ return; }
		
		if( !$('img_' + nextImage) ){
			ipb.slideshow.loadImage( nextImage, IMAGE_DATA.get( nextImage )['filename'] );
		}
		
		// If the image hasn't finished loading, then go into a loop and wait
		if( $('img_' + nextImage).complete != true ){
			Debug.write("Loading image...");
			ipb.slideshow.loading(true);
			ipb.slideshow.update.delay( .1, nextImage );
			return;
		} else { 
			ipb.slideshow.loading(false);
			Debug.write("Image loaded.");
		}
		
		// See if we need to resize & position
		ipb.slideshow.checkSizing( nextImage );
		ipb.slideshow.positionImage( nextImage );
		
		// Build info box
		ipb.slideshow.buildImageInfo( nextImage );
		
		// Now transition
		if( ipb.slideshow.currentImage != 0 )
		{
			new Effect.Parallel([
				new Effect.Fade( $('img_' + ipb.slideshow.currentImage) ),
				new Effect.Appear( $('img_' + nextImage ) )
			], { duration: ipb.slideshow.transitionLen });
			
			//if( IMAGE_DATA.get( ipb.slideshow.currentImage )['author']['id'] != IMAGE_DATA.get( nextImage )['author']['id'] )
			//{
				new Effect.Parallel([
					new Effect.Fade( $('info_' + IMAGE_DATA.get( ipb.slideshow.currentImage )['author']['id'] + '_' + ipb.slideshow.currentImage) ),
					new Effect.Appear( $('info_' + IMAGE_DATA.get( nextImage )['author']['id'] + '_' + nextImage ) )
				], { duration: ipb.slideshow.transitionLen });
			//}
		}
		else
		{
			new Effect.Appear( $('img_' + nextImage ), { duration: ipb.slideshow.transitionLen } );
			new Effect.Appear( $('info_' + IMAGE_DATA.get( nextImage )['author']['id'] + '_' + nextImage ), { duration: ipb.slideshow.transitionLen } );
		}
		
		// Thumbnail stuff
		if( $('thumb_' + nextImage) )
		{		
			ipb.slideshow.positionThumbnailBar( nextImage );			
			
			if( ipb.slideshow.currentImage ){
				$('thumb_' + ipb.slideshow.currentImage).removeClassName('active');
			}
			$('thumb_' + nextImage).addClassName('active');
		}
		
		// Set the current ID
		ipb.slideshow.currentImage = nextImage;
	},
	
	/*----------------------------------*/
	/* Activates/deactivates buttons    */
	recalculateThumbnailButtons: function()
	{
		var thumbWrapLeft = parseInt( $('thumbnail_wrap').getStyle('left') );
		var barWidth = $('thumbnail_wrap').getWidth();
		var viewportWidth = document.viewport.getWidth();
		
		if( thumbWrapLeft >= 30 ){
			$('button_left').removeClassName('active').addClassName('disabled');
		} else {
			$('button_left').addClassName('active').removeClassName('disabled');
		}
		
		if( $('thumbnail_wrap').getWidth() < $('thumbnail_bar').getWidth() ){
			$('button_right').removeClassName('active').addClassName('disabled');
		}
		
		if( ( thumbWrapLeft + barWidth ) > ( viewportWidth - 30 ) ){
			$('button_right').removeClassName('disabled').addClassName('active');
		} else {
			$('button_right').removeClassName('active').addClassName('disabled');
		}
		
	},
	
	/*---------------------------------*/
	/* Positions the thumbnail bar	   */
	positionThumbnailBar: function( thumbID )
	{
		// We're not autoscrolling right now
		if( ipb.slideshow.stopAutoScroll ){
			ipb.slideshow.recalculateThumbnailButtons();
			return;
		}
		
		var barWidth = $('thumbnail_bar').getWidth();
		var thumbPosition = $('thumb_' + thumbID).viewportOffset();
		var positionedOffset = $('thumb_' + thumbID).positionedOffset();
		
		var rightPos = barWidth - 150;
		
		var afterFinish = function()
		{
			ipb.slideshow.recalculateThumbnailButtons();
		};
		
		// Is the thumbnail off to the left?
		if( thumbPosition['left'] < 30 )
		{
			if( positionedOffset['left'] > rightPos ){
				new Effect.Move( $('thumbnail_wrap'), { x: ( rightPos - thumbPosition['left'] ), y: 0, mode: 'relative', duration: 0.2, afterFinish: afterFinish } );
			} else {
				new Effect.Move( $('thumbnail_wrap'), { x: 30, y: 0, mode: 'absolute', duration: 0.2, afterFinish: afterFinish } );
			}
		}
		else if( thumbPosition['left'] > rightPos )
		{			
			new Effect.Move( $('thumbnail_wrap'), { x: (rightPos - thumbPosition['left']), y: 0, mode: 'relative', duration: 0.2, afterFinish: afterFinish } );
		}
		else
		{
			ipb.slideshow.recalculateThumbnailButtons();
		}
		
	},
	
	/*---------------------------------*/
	/* Builds the thumbnail bar		   */
	buildThumbnails: function()
	{
		var thumbCount = 0;
		
		IMAGES.each( function( imageID ){
			var content = ipb.slideshow.thumbnail.evaluate({ 'id': imageID });
			$('thumbnail_wrap').insert( content );
			$('thumb_' + imageID).setStyle( { backgroundImage: "url(" + ipb.slideshow.imageURL + IMAGE_DATA.get( imageID )['thumb'] + ")" } );
			
			if( ipb.slideshow.thumbSize == 0 )
			{
				ipb.slideshow.thumbSize = $('thumb_' + imageID).getWidth();
				
				if( $('thumb_' + imageID).getStyle('margin-right') )
				{
					ipb.slideshow.thumbSize += parseInt( $('thumb_' + imageID).getStyle('margin-right') );
				}
			}
			
			thumbCount++;
		});	
		
		$('thumbnail_wrap').setStyle( { width: ( thumbCount * ipb.slideshow.thumbSize ) + 'px' } );	
		$('thumbnail_wrap').writeAttribute('unselectable', 'on');
		$('thumbnail_bar').writeAttribute('unselectable', 'on');		
	},
	
	/*---------------------------------*/
	/* Build the info box for an image */
	buildImageInfo: function( imageID )
	{
		var authorInfo = IMAGE_DATA.get( imageID )['author'];
		var authorID = authorInfo['id'];
		
		if( $('info_' + authorID + '_' + imageID ) ){ return true; }
		
		var contents = ipb.slideshow.userInfo.evaluate( { 
				'id': authorID + '_' + imageID,
				'name': authorInfo['name'],
				'photo': ipb.slideshow.userPhotoURL + authorInfo['photo'],
				'title': IMAGE_DATA.get( imageID )['title'],
				'width': authorInfo['width'],
				'height': authorInfo['height']
	 	});
		
		$('image_info').insert( contents );
	},
	
	/*------------------------------*/
	/* Preloads an image			*/
	loadImage: function( id, filename )
	{
		if( $( 'img_' + id ) ){ return true; }
		
		var img = new Element('img', { 'id': 'img_' + id, 'src': ipb.slideshow.imageURL + filename }).hide();
		$('image_holder').insert( img );
	},
	
	/*------------------------------*/
	/* Checks the image will fit	*/
	checkSizing: function( imageID )
	{
		var img = $('img_' + imageID);
		
		if( !img.readAttribute('origWidth') || !img.readAttribute('origHeight') )
		{
			var dims = img.getDimensions();
			img.writeAttribute('origWidth', dims['width']).writeAttribute('origHeight', dims['height']);
		}
		
		//Debug.write("Holder size: " +  ipb.slideshow.holderSize['width'] + ", Image size: " + img.readAttribute('origWidth'));
		
		var newWidth = img.readAttribute('origWidth');
		var newHeight = img.readAttribute('origHeight');
		var aspect = img.readAttribute('origWidth') / img.readAttribute('origHeight');
		
		if( newWidth > ipb.slideshow.holderSize['width'] ){
			newWidth = ipb.slideshow.holderSize['width'];
			newHeight = ( newWidth / aspect );
		}
		
		if( newHeight > ipb.slideshow.holderSize['height'] ){
			newHeight = ipb.slideshow.holderSize['height'];
			newWidth = ( newHeight * aspect );
		}
		
		// Resize image
		img.width = newWidth;
		img.height = newHeight;
		
	},
	
	/*----------------------------------*/
	/* Positions an image in the middle */
	positionImage: function( imageID )
	{
		var img = $('img_' + imageID).getDimensions();
		
		var left = Math.ceil( ( ipb.slideshow.holderSize['width'] - img['width'] ) / 2 );
		var top = Math.ceil( ( ipb.slideshow.holderSize['height'] - img['height'] ) / 2 );
		
		// Border
		if( $('img_' + imageID).getStyle('border-top-width') )
		{
			var border = $('img_' + imageID).getStyle('border-top-width').replace('px', '');
			left = left - parseInt( border );
			top = top - parseInt( border );
		}
		
		//Debug.write( "Left: " + left + ", " + "top: " + top );
		// Position
		$('img_' + imageID).setStyle( { left: left + "px", top: top + "px" } );		
	},
	
	/*-------------------------------*/
	/* Returns the next ID in line   */
	getNextID: function( curID )
	{
		// If no ID or currentImage is specified, return first image
		if( Object.isUndefined( curID ) && ipb.slideshow.currentImage == 0 ){
			return IMAGES.first();
		}
		
		var curID = ( Object.isUndefined( curID ) ) ? ipb.slideshow.currentImage : curID;	
		var pos = IMAGES.indexOf( parseInt(curID) );
		
		// Last item?
		if( pos == ( IMAGES.length - 1 ) ){
			return IMAGES.first();
		} else {
			return IMAGES[ pos + 1 ];
		}		
	},
	
	/*-------------------------------*/
	/* Returns the next ID in line   */
	getPrevID: function( curID )
	{
		// If no ID or currentImage is specified, return first image
		if( Object.isUndefined( curID ) && ipb.slideshow.currentImage == 0 ){
			return IMAGES.first();
		}
		
		var curID = ( Object.isUndefined( curID ) ) ? ipb.slideshow.currentImage : curID;	
		var pos = IMAGES.indexOf( parseInt(curID) );
		
		// Last item?
		if( pos === 0 ){
			return IMAGES.last();
		} else {
			return IMAGES[ pos - 1 ];
		}		
	},
	
	/*------------------------------*/
	/* Show loading throbber        */
	loading: function( loading )
	{
		if( loading ){
			$('loading').show();
		} else {
			$('loading').hide();
		}
	},
	
	/*-------------------------------------*/
	/* Resize event to get new holder size */
	resizeWindow: function()
	{
		ipb.slideshow.holderSize = $('image_holder').getDimensions();
		ipb.slideshow.recalculateThumbnailButtons();
	}
};

ipb.slideshow.init();
