// Retina module for Slider Pro.
// 
// Adds the possibility to load a different image when the slider is
// viewed on a retina screen.
;(function( window, $ ) {

	"use strict";
	
	var NS = 'Retina.' + $.SliderPro.namespace;

	var Retina = {

		initRetina: function() {
			var that = this;

			// Return if it's not a retina screen
			if ( this._isRetina() === false ) {
				return;
			}
			
			this.on( 'sliderResize.' + NS, $.proxy( this._checkRetinaImages, this ) );

			if ( this.$slider.find( '.sp-thumbnail' ).length !== 0 ) {
				this.on( 'update.Thumbnails.' + NS, $.proxy( this._checkRetinaThumbnailImages, this ) );
			}
		},

		// Checks if the current display supports high PPI
		_isRetina: function() {
			if ( window.devicePixelRatio >= 2 ) {
				return true;
			}

			if ( window.matchMedia && ( window.matchMedia( "(-webkit-min-device-pixel-ratio: 2),(min-resolution: 2dppx)" ).matches ) ) {
				return true;
			}

			return false;
		},

		// Loop through the slides and replace the images with their retina version
		_checkRetinaImages: function() {
			var that = this;

			$.each( this.slides, function( index, element ) {
				var $slide = element.$slide;

				if ( typeof $slide.attr( 'data-retina-loaded' ) === 'undefined' ) {
					$slide.attr( 'data-retina-loaded', true );

					$slide.find( 'img[data-retina]' ).each(function() {
						var $image = $( this );

						if ( typeof $image.attr( 'data-src' ) !== 'undefined' ) {
							$image.attr( 'data-src', $image.attr( 'data-retina' ) );
						} else {
							that._loadRetinaImage( $image, function( newImage ) {
								if ( newImage.hasClass( 'sp-image' ) ) {
									element.$mainImage = newImage;
									element.resizeMainImage( true );
								}
							});
						}
					});
				}
			});
		},

		// Loop through the thumbnails and replace the images with their retina version
		_checkRetinaThumbnailImages: function() {
			var that = this;

			$.each( this.thumbnails, function( index, element ) {
				var $thumbnail = element.$thumbnailContainer;

				if ( typeof $thumbnail.attr( 'data-retina-loaded' ) === 'undefined' ) {
					$thumbnail.attr( 'data-retina-loaded', true );

					$thumbnail.find( 'img[data-retina]' ).each(function() {
						var $image = $( this );

						if ( typeof $image.attr( 'data-src' ) !== 'undefined' ) {
							$image.attr( 'data-src', $image.attr( 'data-retina' ) );
						} else {
							that._loadRetinaImage( $image, function( newImage ) {
								if ( newImage.hasClass( 'sp-thumbnail' ) ) {
									element.resizeImage();
								}
							});
						}
					});
				}
			});
		},

		// Load the retina image
		_loadRetinaImage: function( image, callback ) {
			var retinaFound = false,
				newImagePath = '';

			// Check if there is a retina image specified
			if ( typeof image.attr( 'data-retina' ) !== 'undefined' ) {
				retinaFound = true;

				newImagePath = image.attr( 'data-retina' );
			}

			// Check if there is a lazy loaded, non-retina, image specified
			if ( typeof image.attr( 'data-src' ) !== 'undefined' ) {
				if ( retinaFound === false ) {
					newImagePath = image.attr( 'data-src') ;
				}

				image.removeAttr('data-src');
			}

			// Return if there isn't a retina or lazy loaded image
			if ( newImagePath === '' ) {
				return;
			}

			// Create a new image element
			var newImage = $( new Image() );

			// Copy the class(es) and inline style
			newImage.attr( 'class', image.attr('class') );
			newImage.attr( 'style', image.attr('style') );

			// Copy the data attributes
			$.each( image.data(), function( name, value ) {
				newImage.attr( 'data-' + name, value );
			});

			// Copy the width and height attributes if they exist
			if ( typeof image.attr( 'width' ) !== 'undefined' ) {
				newImage.attr( 'width', image.attr( 'width' ) );
			}

			if ( typeof image.attr( 'height' ) !== 'undefined' ) {
				newImage.attr( 'height', image.attr( 'height' ) );
			}

			if ( typeof image.attr( 'alt' ) !== 'undefined' ) {
				newImage.attr( 'alt', image.attr( 'alt' ) );
			}

			if ( typeof image.attr( 'title' ) !== 'undefined' ) {
				newImage.attr( 'title', image.attr( 'title' ) );
			}

			// Add the new image in the same container and remove the older image
			newImage.insertAfter( image );
			image.remove();
			image = null;

			// Assign the source of the image
			newImage.attr( 'src', newImagePath );

			if ( typeof callback === 'function' ) {
				callback( newImage );
			}
		},

		// Destroy the module
		destroyRetina: function() {
			this.off( 'update.' + NS );
			this.off( 'update.Thumbnails.' + NS );
		}
	};

	$.SliderPro.addModule( 'Retina', Retina );
	
})( window, jQuery );