// Start with Semicolon to block
; (function ($) {

	// Enable Strict Mode
	'use strict';

	// Create Panels Array
	var panels = [];

	// Has done CSS3 browser support check?
	var browserSupportTest = false;
	var has3d = false;
	var hasTransitions = false;

	// Plugin Default Settings
	var defaults = {

		// General Config
		containerSelector: 'body',
		type: 'html', // html, iframe, video, image

		// Styles
		direction: 'top', // top, left, right, bottom
		duration: 300, // ms
		transition: 'ease', // linear, ease, ease-in, ease-out, ease-in-out, cubic-bezier(P1x,P1y,P2x,P2y)

		// Browser Support
		easingPluginTransition: 'easeInCirc',
		useCSS: true,   // Consider not using if have Fixed Elements
		useEasingPlugin: false, // http://gsgd.co.uk/sandbox/jquery/easing/ only for browser support

		// Image Options
		imageURL: false,

		// Iframe Options
		iframeURL: false,

		// Video Options
		autoPlayVideo: true,
		youtubeID: false,
		youTubeTheme: 'light',

		// TranslateX Options
		distanceX: '70%',

		// TranslateY Options
		forceMinHeight: false,
		minHeight: '200px',

		// Triggers
		closeAfter: 0, // ms
		startOpened: false,
		startOpenedDelay: 0, // ms

		// Event Helpers
		clickSelector: false,
		enableEscapeKey: true,
		hoverSelector: false,
		touchSelector: false,

		// Callbacks
		beforePanelOpen: function () { },
		afterPanelOpen: function () { },
		beforePanelClose: function () { },
		afterPanelClose: function () { }
	};


	$.fn.scotchPanel = function (options) {

		// Check to see if Default Options are Set
		if (typeof options === 'undefined') {
			options = {};
		}

		// Check to see if an element is even selected
		if (this.length === 0) return this;

		// Support selecting Panels
		if (this.length > 1) {

			// Loop through all selected scotch panels
			this.each(function () {
				// Add panel to array
				panels.push($(this).scotchPanel(options));
			});

			// Public Functions Functionality for all at once
			panels.open = function () {
				for (var i = 0; i < panels.length; i++) {
					panels[i].open();
				}
			};
			panels.close = function () {
				for (var i = 0; i < panels.length; i++) {
					panels[i].close();
				}
			};
			panels.toggle = function () {
				for (var i = 0; i < panels.length; i++) {
					panels[i].toggle();
				}
			};

			// Return the Scotch Panels
			return panels;
		}

		// Create Current Scotch Panel Object
		var panel = {};
		panel = this;


        /*=========================================
        =            PRIVATE FUNCTIONS            =
        =========================================*/
		// Prep everything
		var init = function () {

			// Do CSS3 Check!
			if (!browserSupportTest) {
				browserSupportTest = true;
				has3d = browserSupport.transition();
				hasTransitions = browserSupport.translate3d();
			}

			// Check for HTML5 data attributes instead
			for (var key in defaults) {
				if (defaults.hasOwnProperty(key)) {
					if (panel.attr('data-' + key.toLowerCase())) {
						options[key] = panel.data(key.toLowerCase());
					}
				}
			}

			// Merge Custom Plugin Settings with Default
			panel.settings = $.extend({}, defaults, options);

			// Start DOM and CSS Modifications
			setup();
		};


		// DOM / CSS Changes / Make Things Happen
		var setup = function () {

			// Wrap the panel!
			var container = $(panel.settings.containerSelector);
			if (!container.hasClass('scotchified')) {
				container.wrapInner('<div class="scotch-panel-wrapper"><div class="scotch-panel-canvas"></div></div>').addClass('scotchified');
			}

			// Scotch Panel Wrapper CSS
			$('.scotch-panel-wrapper').css({
				'position': 'relative',
				'overflow': 'hidden',
				'width': '100%'
			});
			// Scotch Panel Canvas CSS
			$('.scotch-panel-canvas').css({
				'position': 'relative',
				'height': '100%',
				'width': '100%'
			});
			// Do 3D Stuff separate
			if (panel.settings.useCSS) {
				$('.scotch-panel-canvas').css({
					'-moz-transform': 'translate3d(0, 0, 0)',
					'-ms-transform': 'translate3d(0, 0, 0)',
					'-o-transform': 'translate3d(0, 0, 0)',
					'-webkit-transform': 'translate3d(0, 0, 0)',
					'transform': 'translate3d(0, 0, 0)',
					'-moz-backface-visibility': 'hidden',
					'-ms-backface-visibility': 'hidden',
					'-o-backface-visibility': 'hidden',
					'-webkit-backface-visibility': 'hidden',
					'backface-visibility': 'hidden'
				});
			}

			// Figure out which off canvas style is used (left, top, right)
			if (panel.settings.direction == 'top') {
				panel.height = panel.height();
				panel.addClass('scotch-panel-top');

				panel.css({
					'bottom': '100%',
					'left': '0',
					'width': '100%',
					'position': 'absolute',
					'z-index': '888888',
					'overflow': 'hidden'
				});
			}
			if (panel.settings.direction == 'bottom') {
				panel.height = panel.height();
				panel.addClass('scotch-panel-bottom');

				panel.css({
					'top': '100%',
					'left': '0',
					'width': '100%',
					'position': 'absolute',
					'z-index': '888888',
					'overflow': 'hidden'
				});
			}
			if (panel.settings.direction == 'left') {
				panel.addClass('scotch-panel-left');

				panel.css({
					'top': '0',
					'left': '-' + panel.settings.distanceX,
					'width': panel.settings.distanceX,
					'height': '100%',
					'position': 'absolute',
					'z-index': '888888',
					'overflow': 'hidden'
				});
			}
			if (panel.settings.direction == 'right') {
				panel.addClass('scotch-panel-right');

				panel.css({
					'top': '0',
					'right': '-' + panel.settings.distanceX,
					'width': panel.settings.distanceX,
					'height': '100%',
					'position': 'absolute',
					'z-index': '888888',
					'overflow': 'hidden'
				});
			}
			panel.css({
				'-moz-backface-visibility': 'hidden',
				'-ms-backface-visibility': 'hidden',
				'-o-backface-visibility': 'hidden',
				'-webkit-backface-visibility': 'hidden',
				'backface-visibility': 'hidden'
			});

			// Photo Logic
			if (panel.settings.type == 'image' && panel.settings.imageURL) {
				panel.css({
					'-o-background-size': 'cover',
					'-ms-background-size': 'cover',
					'-moz-background-size': 'cover',
					'-webkit-background-size': 'cover',
					'background-size': 'cover',
					'background-position': '50% 0',
					'background-repeat': 'no-repeat',
					'background-image': 'url(' + panel.settings.imageURL + ')'
				});

				// Update Panel Height if top or bottom
				if (panel.settings.direction == 'top' || panel.settings.direction == 'bottom') {
					panel.css('min-height', panel.settings.minHeight);
					panel.height = $(panel).height();
				}
			}

			// Iframe Logic
			if (panel.settings.type == 'iframe' && panel.settings.iframeURL) {
				panel.iframeIsLoaded = false;
				panel.append('<iframe frameborder="0" style="width: 100%; height: 100%; display: block; position: relative; min-height: ' + panel.settings.minHeight + '" allowfullscreen></iframe>');

				// Update Panel Height if top or bottom
				if (panel.settings.direction == 'top' || panel.settings.direction == 'bottom') {
					panel.height = $(panel).height();
				}
			}

			// YouTube Logic
			if (panel.settings.type == 'video' && panel.settings.youtubeID) {
				panel.append('<div id="video-id-' + panel.settings.youtubeID + '" style="min-height: ' + panel.settings.minHeight + '; display: block !important;"><iframe src="//www.youtube.com/embed/' + panel.settings.youtubeID + '?enablejsapi=1&theme=' + panel.settings.youTubeTheme + '" frameborder="0" style="width: 100%; height: 100%; display: block; position: absolute; left: 0; top: 0;" allowfullscreen></iframe></div>');

				// Update Panel Height if top or bottom
				if (panel.settings.direction == 'top' || panel.settings.direction == 'bottom') {
					panel.height = $(panel).height();
				}
			}

			// Apply CSS3 Transitions if modern browser
			if (has3d && hasTransitions) {
				applyTransition(panel.settings.transition, panel.settings.duration);
			}

			// Open on Start?
			if (panel.settings.startOpened) {
				setTimeout(function () {
					panel.open();
				}, panel.settings.startOpenedDelay);
			}

			// Close after X milliseconds?
			if (panel.settings.closeAfter != 0) {
				setTimeout(function () {
					panel.close();
				}, panel.settings.closeAfter);
			}
		};


		// Browser Support Object
		var browserSupport = {
			transition: function () {
				// IE 7 + 8 Sucks
				if (!window.getComputedStyle) {
					return false;
				}

				var b = document.body || document.documentElement,
					s = b.style,
					p = 'transition';

				if (typeof s[p] == 'string') { return true; }

				// Tests for vendor specific prop
				var v = ['Moz', 'webkit', 'Webkit', 'Khtml', 'O', 'ms'];
				p = p.charAt(0).toUpperCase() + p.substr(1);

				for (var i = 0; i < v.length; i++) {
					if (typeof s[v[i] + p] == 'string') { return true; }
				}

				return false;
			},
			translate3d: function () {
				// IE 7 + 8 Sucks
				if (!window.getComputedStyle) {
					return false;
				}

				var el, has3d;

				el = document.createElement('p');
				el.style['transform'] = 'matrix3d(1, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1)';
				el.style['margin'] = '0';
				document.body.insertBefore(el, document.body.lastChild);
				has3d = window.getComputedStyle(el).getPropertyValue('transform');

				if (has3d !== undefined) {
					return has3d !== 'none';
				} else {
					return false;
				}
			}
		};

		// Toggle YouTube State (Play / Pause)
		var toggleVideoState = function (element, state) {
			var div = document.getElementById(element);
			var iframe = div.getElementsByTagName('iframe')[0].contentWindow;
			div.style.display = state == 'hide' ? 'none' : '';
			var func = state == 'hide' ? 'pauseVideo' : 'playVideo';
			iframe.postMessage('{"event":"command","func":"' + func + '","args":""}', '*');
			div.style['display'] = 'block';
		};

		// Apply CSS Transitions
		var applyTransition = function (transition, duration) {
			panel.parents('.scotch-panel-canvas:first').css({
				'-ms-transition': 'all ' + duration + 'ms ' + transition,
				'-moz-transition': 'all ' + duration + 'ms ' + transition,
				'-o-transition': 'all ' + duration + 'ms ' + transition,
				'-webkit-transition': 'all ' + duration + 'ms ' + transition,
				'transition': 'all ' + duration + 'ms ' + transition
			});
		};

		// Toggle Translate Y
		var translateY = function (distanceY) {

			// Auto adapt height if unknown and enabled
			if (panel.settings.forceMinHeight) {
				panel.parents('.scotch-panel-canvas:first').css('min-height', distanceY);
			}

			if (has3d && hasTransitions && panel.settings.useCSS) {

				// Open/Close Before Callbacks (CSS)
				if (panel.parents('.scotch-panel-canvas:first').hasClass('scotch-is-showing')) {
					panel.settings.beforePanelOpen();
				} else {
					panel.settings.beforePanelClose();
				}

				panel.parents('.scotch-panel-canvas:first').css({
					'-ms-transform': 'translate3d(0, ' + distanceY + 'px, 0)',
					'-moz-transform': 'translate3d(0, ' + distanceY + 'px, 0)',
					'-o-transform': 'translate3d(0, ' + distanceY + 'px, 0)',
					'-webkit-transform': 'translate3d(0, ' + distanceY + 'px, 0)',
					'transform': 'translate3d(0, ' + distanceY + 'px, 0)'
				});

				setTimeout(function () {

					// Open/Close After Callbacks (CSS)
					if (panel.parents('.scotch-panel-canvas:first').hasClass('scotch-is-showing')) {
						panel.settings.afterPanelOpen();
					} else {
						panel.settings.afterPanelClose();
					}

				}, panel.settings.duration);


			} else {

				// Open/Close Before Callbacks (JS)
				if (panel.parents('.scotch-panel-canvas:first').hasClass('scotch-is-showing')) {
					panel.settings.beforePanelOpen();
				} else {
					panel.settings.beforePanelClose();
				}

				if (panel.settings.useEasingPlugin) {

					panel.parents('.scotch-panel-canvas:first').animate({
						top: distanceY + 'px'
					}, {
							duration: panel.settings.duration,
							easing: panel.settings.easingPluginTransition,
							complete: function () {

								// Open/Close After Callbacks (JS EASE)
								if (panel.parents('.scotch-panel-canvas:first').hasClass('scotch-is-showing')) {
									panel.settings.afterPanelOpen();
								} else {
									panel.settings.afterPanelClose();
								}

							}
						});

				} else {

					panel.parents('.scotch-panel-canvas:first').animate({
						top: distanceY + 'px'
					}, panel.settings.duration, function () {

						// Open/Close After Callbacks (JS NO EASE)
						if (panel.parents('.scotch-panel-canvas:first').hasClass('scotch-is-showing')) {
							panel.settings.afterPanelOpen();
						} else {
							panel.settings.afterPanelClose();
						}

					});

				}
			}
		};

		// Toggle Translate X
		var translateX = function (distanceX) {

			if (has3d && hasTransitions && panel.settings.useCSS) {

				// Open/Close Before Callbacks (CSS)
				if (panel.parents('.scotch-panel-canvas:first').hasClass('scotch-is-showing')) {
					panel.settings.beforePanelOpen();
				} else {
					panel.settings.beforePanelClose();
				}

				panel.parents('.scotch-panel-canvas:first').css({
					'-ms-transform': 'translate3d(' + distanceX + ', 0, 0)',
					'-moz-transform': 'translate3d(' + distanceX + ', 0, 0)',
					'-o-transform': 'translate3d(' + distanceX + ', 0, 0)',
					'-webkit-transform': 'translate3d(' + distanceX + ', 0, 0)',
					'transform': 'translate3d(' + distanceX + ', 0, 0)'
				});

				setTimeout(function () {

					// Open/Close After Callbacks (CSS)
					if (panel.parents('.scotch-panel-canvas:first').hasClass('scotch-is-showing')) {
						panel.settings.afterPanelOpen();
					} else {
						panel.settings.afterPanelClose();
					}

				}, panel.settings.duration);

			} else {

				// Open/Close Before Callbacks (JS)
				if (panel.parents('.scotch-panel-canvas:first').hasClass('scotch-is-showing')) {
					panel.settings.beforePanelOpen();
				} else {
					panel.settings.beforePanelClose();
				}

				if (panel.settings.useEasingPlugin) {

					panel.parents('.scotch-panel-canvas:first').animate({
						left: distanceX
					}, {
							duration: panel.settings.duration,
							easing: panel.settings.easingPluginTransition,
							complete: function () {

								// Open/Close After Callbacks (JS EASE)
								if (panel.parents('.scotch-panel-canvas:first').hasClass('scotch-is-showing')) {
									panel.settings.afterPanelOpen();
								} else {
									panel.settings.afterPanelClose();
								}

							}
						});

				} else {

					panel.parents('.scotch-panel-canvas:first').animate({
						left: distanceX
					}, panel.settings.duration, function () {

						// Open/Close After Callbacks (JS NO EASE)
						if (panel.parents('.scotch-panel-canvas:first').hasClass('scotch-is-showing')) {
							panel.settings.afterPanelOpen();
						} else {
							panel.settings.afterPanelClose();
						}

					});

				}
			}
		};


        /*========================================
        =            PUBLIC FUNCTIONS            =
        ========================================*/
		// Open the Scotch Panel
		panel.open = function () {
			panel.parents('.scotch-panel-canvas:first').addClass('scotch-is-showing');

			// Load iframe if not loaded
			if (panel.settings.type == 'iframe' && panel.settings.iframeURL && !panel.iframeIsLoaded) {
				panel.iframeIsLoaded = true;
				panel.find('iframe').attr('src', panel.settings.iframeURL);
			}

			// Play YouTube Video
			if (panel.settings.type == 'video' && panel.settings.youtubeID && panel.settings.autoPlayVideo) {
				toggleVideoState('video-id-' + panel.settings.youtubeID, '');
			}

			if (panel.settings.direction == 'top') {
				translateY(panel.height);
			}

			if (panel.settings.direction == 'bottom') {
				translateY('-' + panel.height);
			}

			if (panel.settings.direction == 'left') {
				translateX(panel.settings.distanceX);
			}

			if (panel.settings.direction == 'right') {
				translateX('-' + panel.settings.distanceX);
			}
		};

		// Close ScotchPanel
		panel.close = function () {
			panel.parents('.scotch-panel-canvas:first').removeClass('scotch-is-showing');

			// Pause YouTube Video (after close...)
			setTimeout(function () {
				if (panel.settings.type == 'video' && panel.settings.youtubeID && panel.settings.autoPlayVideo) {
					toggleVideoState('video-id-' + panel.settings.youtubeID, 'hide');
				}
			}, panel.settings.duration);

			if (panel.settings.direction == 'top' || panel.settings.direction == 'bottom') {
				translateY(0);
			}

			if (panel.settings.direction == 'left' || panel.settings.direction == 'right') {
				translateX(0);
			}
		};

		// Toggle ScotchPanel
		panel.toggle = function () {
			if (panel.parents('.scotch-panel-canvas:first').hasClass('scotch-is-showing')) {
				panel.close();
			} else {
				panel.open();
			}
		};




        /*=========================================
        =            MAKE MAGIC HAPPEN            =
        =========================================*/
		init();




        /*===============================
        =            HELEPRS            =
        ===============================*/
		// Escape Key to Close
		$(document).keyup(function (e) {
			if (e.keyCode == 27 && panel.settings.enableEscapeKey) {
				panel.close();
			}
		});

		// Hover Helper
		if (panel.settings.hoverSelector) {
			$(panel.settings.hoverSelector).hover(function () {
				panel.open();
			},
				function () {
					panel.close();
				});
		}

		// Click Helper
		if (panel.settings.clickSelector) {
			$(panel.settings.clickSelector).click(function () {
				panel.toggle();

				return false;
			});
		}

		// Touch Helper
		if (panel.settings.touchSelector) {
			$(panel.settings.touchSelector).on('touchstart', function () {
				panel.toggle();

				return false;
			});
		}

		// Return the Scotch Panel Object so Devs can do cool things with it
		return panel;
	};

}(jQuery));