PageSourceSearch

https://www.varsity.com/wp-content/themes/Varsity-Theme/js/lightcase.js?ver=7.0.5

js varsity.com collected 2026-10-01 11:32:39 UTC 51,118 bytes, 1,860 lines download raw bytes

1/*
2 * Lightcase - jQuery Plugin
3 * The smart and flexible Lightbox Plugin.
4 *
5 * @author		Cornel Boppart <[email protected]>
6 * @copyright	Author
7 *
8 * @version		2.4.2 (24/11/2017)
9 * @version modified the The Creative Momentum Team 
10 */
11
12;(function ($) {
13
14	'use strict';
15
16	var _self = {
17		cache: {},
18
19		support: {},
20
21		objects: {},
22
23		/**
24		 * Initializes the plugin
25		 *
26		 * @param	{object}	options
27		 * @return	{object}
28		 */
29		init: function (options) {
30			return this.each(function () {
31				$(this).unbind('click.lightcase').bind('click.lightcase', function (event) {
32					event.preventDefault();
33					$(this).lightcase('start', options);
34				});
35			});
36		},
37
38		/**
39		 * Starts the plugin
40		 *
41		 * @param	{object}	options
42		 * @return	{void}
43		 */
44		start: function (options) {
45			_self.origin = lightcase.origin = this;
46
47			_self.settings = lightcase.settings = $.extend(true, {
48				idPrefix: 'lightcase-',
49				classPrefix: 'lightcase-',
50				attrPrefix: 'lc-',
51				transition: 'elastic',
52				transitionOpen: null,
53				transitionClose: null,
54				transitionIn: null,
55				transitionOut: null,
56				cssTransitions: true,
57				speedIn: 250,
58				speedOut: 250,
59				width: null,
60				height: null,
61				maxWidth: 800,
62				maxHeight: 500,
63				forceWidth: false,
64				forceHeight: false,
65				liveResize: true,
66				fullScreenModeForMobile: true,
67				mobileMatchExpression: /(iphone|ipod|ipad|android|blackberry|symbian)/,
68				disableShrink: false,
69				fixedRatio: true,
70				shrinkFactor: .75,
71				overlayOpacity: .9,
72				slideshow: false,
73				slideshowAutoStart: true,
74				timeout: 5000,
75				swipe: true,
76				useKeys: true,
77				useCategories: true,
78				useAsCollection: false,
79				navigateEndless: true,
80				closeOnOverlayClick: true,
81				title: null,
82				caption: null,
83				showTitle: true,
84				showCaption: true,
85				showSequenceInfo: true,
86				inline: {
87					width: 'auto',
88					height: 'auto'
89				},
90				ajax: {
91					width: 'auto',
92					height: 'auto',
93					type: 'get',
94					dataType: 'html',
95					data: {}
96				},
97				iframe: {
98					width: 800,
99					height: 500,
100					frameborder: 0
101				},
102				flash: {
103					width: 400,
104					height: 205,
105					wmode: 'transparent'
106				},
107				video: {
108					width: 400,
109					height: 225,
110					poster: '',
111					preload: 'auto',
112					controls: true,
113					autobuffer: true,
114					autoplay: true,
115					loop: false
116				},
117				attr: 'data-rel',
118				href: null,
119				type: null,
120				typeMapping: {
121					'image': 'jpg,jpeg,gif,png,bmp',
122					'flash': 'swf',
123					'video': 'mp4,mov,ogv,ogg,webm',
124					'iframe': 'html,php',
125					'ajax': 'json,txt',
126					'inline': '#'
127				},
128				errorMessage: function () {
129					return '<p class="' + _self.settings.classPrefix + 'error">' + _self.settings.labels['errorMessage'] + '</p>';
130				},
131				labels: {
132					'errorMessage': 'Source could not be found...',
133					'sequenceInfo.of': ' of ',
134					'close': 'Close',
135					'navigator.prev': 'Prev',
136					'navigator.next': 'Next',
137 					'navigator.play': 'Play',
138					'navigator.pause': 'Pause'
139				},
140				markup: function () {
141					_self.objects.body.append(
142						_self.objects.overlay = $('<div id="' + _self.settings.idPrefix + 'overlay"></div>'),
143						_self.objects.loading = $('<div id="' + _self.settings.idPrefix + 'loading" class="' + _self.settings.classPrefix + 'icon-spin"></div>'),
144						_self.objects.case = $('<div id="' + _self.settings.idPrefix + 'case" aria-hidden="true" role="dialog"></div>')
145					);
146					_self.objects.case.append(
147						_self.objects.close = $('<a href="#" class="' + _self.settings.classPrefix + 'icon-close"><span>' + _self.settings.labels['close'] + '</span></a>'),
148						_self.objects.nav = $('<div id="' + _self.settings.idPrefix + 'nav"></div>')
149					);
150					_self.objects.nav.append(
151						_self.objects.prev = $('<a href="#" class="' + _self.settings.classPrefix + 'icon-prev"><span>' + _self.settings.labels['navigator.prev'] + '</span></a>').hide(),
152						_self.objects.next = $('<a href="#" class="' + _self.settings.classPrefix + 'icon-next"><span>' + _self.settings.labels['navigator.next'] + '</span></a>').hide(),
153						_self.objects.play = $('<a href="#" class="' + _self.settings.classPrefix + 'icon-play"><span>' + _self.settings.labels['navigator.play'] + '</span></a>').hide(),
154						_self.objects.pause = $('<a href="#" class="' + _self.settings.classPrefix + 'icon-pause"><span>' + _self.settings.labels['navigator.pause'] + '</span></a>').hide()
155					);
156					_self.objects.case.append(
157						_self.objects.content = $('<div id="' + _self.settings.idPrefix + 'content"></div>'),
158						_self.objects.info = $('<div id="' + _self.settings.idPrefix + 'info"></div>')
159					);
160					_self.objects.content.append(
161						_self.objects.contentInner = $('<div class="' + _self.settings.classPrefix + 'contentInner"></div>')
162					);
163					_self.objects.info.append(
164						_self.objects.sequenceInfo = $('<div id="' + _self.settings.idPrefix + 'sequenceInfo"></div>'),
165						_self.objects.title = $('<h4 id="' + _self.settings.idPrefix + 'title"></h4>'),
166						_self.objects.caption = $('<p id="' + _self.settings.idPrefix + 'caption"></p>')
167					);
168				},
169				onInit: {},
170				onStart: {},
171				onCalculateDimensions: {},
172				onFinish: {},
173				onResize: {},
174				onClose: {},
175				onCleanup: {}
176			}, 
177			options,
178			// Load options from data-lc-options attribute
179			_self.origin.data ? _self.origin.data('lc-options') : {});
180
181			_self.objects.document = $('html');
182			_self.objects.body = $('body');
183
184			// Call onInit hook functions
185			_self._callHooks(_self.settings.onInit);
186
187			_self.objectData = _self._setObjectData(this);
188
189			_self._addElements();
190			_self._open();
191
192			_self.dimensions = _self.getViewportDimensions();
193		},
194
195		/**
196		 * Getter method for objects
197		 *
198		 * @param	{string}	name
199		 * @return	{object}
200		 */
201		get: function (name) {
202			return _self.objects[name];
203		},
204
205		/**
206		 * Getter method for objectData
207		 *
208		 * @return	{object}
209		 */
210		getObjectData: function () {
211			return _self.objectData;
212		},
213
214		/**
215		 * Sets the object data
216		 *
217		 * @param	{object}	object
218		 * @return	{object}	objectData
219		 */
220		_setObjectData: function (object) {
221		 	var $object = $(object),
222				objectData = {
223				this: $(object),
224				title: _self.settings.title || $object.attr(_self._prefixAttributeName('title')) || $object.attr('title'),
225				caption: _self.settings.caption || $object.attr(_self._prefixAttributeName('caption')) || $object.children('img').attr('alt'),
226				url: _self._determineUrl(),
227				requestType: _self.settings.ajax.type,
228				requestData: _self.settings.ajax.data,
229				requestDataType: _self.settings.ajax.dataType,
230				rel: $object.attr(_self._determineAttributeSelector()),
231				type: _self.settings.type || _self._verifyDataType(_self._determineUrl()),
232				isPartOfSequence: _self.settings.useAsCollection || _self._isPartOfSequence($object.attr(_self.settings.attr), ':'),
233				isPartOfSequenceWithSlideshow: _self._isPartOfSequence($object.attr(_self.settings.attr), ':slideshow'),
234				currentIndex: $(_self._determineAttributeSelector()).index($object),
235				sequenceLength: $(_self._determineAttributeSelector()).length
236			};
237
238			// Add sequence info to objectData
239			objectData.sequenceInfo = (objectData.currentIndex + 1) + _self.settings.labels['sequenceInfo.of'] + objectData.sequenceLength;
240
241			// Add next/prev index
242			objectData.prevIndex = objectData.currentIndex - 1;
243			objectData.nextIndex = objectData.currentIndex + 1;
244
245			return objectData;
246		},
247
248		/**
249		 * Prefixes a data attribute name with defined name from 'settings.attrPrefix'
250		 * to ensure more uniqueness for all lightcase related/used attributes.
251		 *
252		 * @param	{string}	name
253		 * @return	{string}
254		 */
255		_prefixAttributeName: function (name) {
256			return 'data-' + _self.settings.attrPrefix + name;
257		},
258
259		/**
260		 * Determines the link target considering 'settings.href' and data attributes
261		 * but also with a fallback to the default 'href' value.
262		 *
263		 * @return	{string}
264		 */
265		_determineLinkTarget: function () {
266			return _self.settings.href || $(_self.origin).attr(_self._prefixAttributeName('href')) || $(_self.origin).attr('href');
267		},
268
269		/**
270		 * Determines the attribute selector to use, depending on
271		 * whether categorized collections are beeing used or not.
272		 *
273		 * @return	{string}	selector
274		 */
275		_determineAttributeSelector: function () {
276			var	$origin = $(_self.origin),
277				selector = '';
278
279			if (typeof _self.cache.selector !== 'undefined') {
280				selector = _self.cache.selector;
281			} else if (_self.settings.useCategories === true && $origin.attr(_self._prefixAttributeName('categories'))) {
282				var	categories = $origin.attr(_self._prefixAttributeName('categories')).split(' ');
283
284				$.each(categories, function (index, category) {
285					if (index > 0) {
286						selector += ',';
287					}
288					selector += '[' + _self._prefixAttributeName('categories') + '~="' + category + '"]';
289				});
290			} else {
291				selector = '[' + _self.settings.attr + '="' + $origin.attr(_self.settings.attr) + '"]';
292			}
293
294			_self.cache.selector = selector;
295
296			return selector;
297		},
298
299		/**
300		 * Determines the correct resource according to the
301		 * current viewport and density.
302		 *
303		 * @return	{string}	url
304		 */
305		_determineUrl: function () {
306			var	dataUrl = _self._verifyDataUrl(_self._determineLinkTarget()),
307				width = 0,
308				density = 0,
309				supportLevel = '',
310				url;
311
312			$.each(dataUrl, function (index, src) {
313				switch (_self._verifyDataType(src.url)) {
314					case 'video':
315						var	video = document.createElement('video'),
316							videoType = _self._verifyDataType(src.url) + '/' + _self._getFileUrlSuffix(src.url);
317
318						// Check if browser can play this type of video format
319						if (supportLevel !== 'probably' && supportLevel !== video.canPlayType(videoType) && video.canPlayType(videoType) !== '') {
320							supportLevel = video.canPlayType(videoType);
321							url = src.url;
322						}
323						break;
324					default:
325						if (
326							// Check density
327							_self._devicePixelRatio() >= src.density &&
328							src.density >= density &&
329							// Check viewport width
330							_self._matchMedia()('screen and (min-width:' + src.width + 'px)').matches &&
331							src.width >= width
332						) {
333							width = src.width;
334							density = src.density;
335							url = src.url;
336						}
337						break;
338				}
339			});
340
341			return url;
342		},
343
344		/**
345		 * Normalizes an url and returns information about the resource path,
346		 * the viewport width as well as density if defined.
347		 *
348		 * @param	{string}	url	Path to resource in format of an url or srcset
349		 * @return	{object}
350		 */
351		_normalizeUrl: function (url) {
352			var srcExp = /^\d+$/;
353
354			return url.split(',').map(function (str) {
355				var src = {
356					width: 0,
357					density: 0
358				};
359
360				str.trim().split(/\s+/).forEach(function (url, i) {
361					if (i === 0) {
362						return src.url = url;
363					}
364
365					var value = url.substring(0, url.length - 1),
366						lastChar = url[url.length - 1],
367						intVal = parseInt(value, 10),
368						floatVal = parseFloat(value);
369					if (lastChar === 'w' && srcExp.test(value)) {
370						src.width = intVal;
371					} else if (lastChar === 'h' && srcExp.test(value)) {
372						src.height = intVal;
373					} else if (lastChar === 'x' && !isNaN(floatVal)) {
374						src.density = floatVal;
375					}
376				});
377
378				return src;
379			});
380		},
381
382		/**
383		 * Verifies if the link is part of a sequence
384		 *
385		 * @param	{string}	rel
386		 * @param	{string}	expression
387		 * @return	{boolean}
388		 */
389		_isPartOfSequence: function (rel, expression) {
390			var getSimilarLinks = $('[' + _self.settings.attr + '="' + rel + '"]'),
391				regexp = new RegExp(expression);
392
393			return (regexp.test(rel) && getSimilarLinks.length > 1);
394		},
395
396		/**
397		 * Verifies if the slideshow should be enabled
398		 *
399		 * @return	{boolean}
400		 */
401		isSlideshowEnabled: function () {
402			return (_self.objectData.isPartOfSequence && (_self.settings.slideshow === true || _self.objectData.isPartOfSequenceWithSlideshow === true));
403		},
404
405		/**
406		 * Loads the new content to show
407		 *
408		 * @return	{void}
409		 */
410		_loadContent: function () {
411			if (_self.cache.originalObject) {
412				_self._restoreObject();
413			}
414
415			_self._createObject();
416		},
417
418		/**
419		 * Creates a new object
420		 *
421		 * @return	{void}
422		 */
423		_createObject: function () {
424			var $object;
425
426			// Create object
427			switch (_self.objectData.type) {
428				case 'image':
429					$object = $(new Image());
430					$object.attr({
431						// The time expression is required to prevent the binding of an image load
432						'src': _self.objectData.url,
433						'alt': _self.objectData.title
434					});
435					break;
436				case 'inline':
437					$object = $('<div class="' + _self.settings.classPrefix + 'inlineWrap"></div>');
438					$object.html(_self._cloneObject($(_self.objectData.url)));
439
440					// Add custom attributes from _self.settings
441					$.each(_self.settings.inline, function (name, value) {
442						$object.attr(_self._prefixAttributeName(name), value);
443					});
444					break;
445				case 'ajax':
446					$object = $('<div class="' + _self.settings.classPrefix + 'inlineWrap"></div>');
447
448					// Add custom attributes from _self.settings
449					$.each(_self.settings.ajax, function (name, value) {
450						if (name !== 'data') {
451							$object.attr(_self._prefixAttributeName(name), value);
452						}
453					});
454					break;
455				case 'flash':
456					$object = $('<embed src="' + _self.objectData.url + '" type="application/x-shockwave-flash"></embed>');
457
458					// Add custom attributes from _self.settings
459					$.each(_self.settings.flash, function (name, value) {
460						$object.attr(name, value);
461					});
462					break;
463				case 'video':
464					$object = $('<video></video>');
465					$object.attr('src', _self.objectData.url);
466
467					// Add custom attributes from _self.settings
468					$.each(_self.settings.video, function (name, value) {
469						$object.attr(name, value);
470					});
471					break;
472				default:
473					$object = $('<iframe></iframe>');
474					$object.attr({
475						'src': _self.objectData.url
476					});
477
478					// Add custom attributes from _self.settings
479					$.each(_self.settings.iframe, function (name, value) {
480						$object.attr(name, value);
481					});
482					break;
483			}
484
485			_self._addObject($object);
486			_self._loadObject($object);
487		},
488
489		/**
490		 * Adds the new object to the markup
491		 *
492		 * @param	{object}	$object
493		 * @return	{void}
494		 */
495		_addObject: function ($object) {
496			// Add object to content holder
497			_self.objects.contentInner.html($object);
498
499			// Start loading
500			_self._loading('start');
501
502			// Call onStart hook functions
503			_self._callHooks(_self.settings.onStart);
504
505			// Add sequenceInfo to the content holder or hide if its empty
506			if (_self.settings.showSequenceInfo === true && _self.objectData.isPartOfSequence) {
507				_self.objects.sequenceInfo.html(_self.objectData.sequenceInfo);
508				_self.objects.sequenceInfo.show();
509			} else {
510				_self.objects.sequenceInfo.empty();
511				_self.objects.sequenceInfo.hide();
512			}
513			// Add title to the content holder or hide if its empty
514			if (_self.settings.showTitle === true && _self.objectData.title !== undefined && _self.objectData.title !== '') {
515				_self.objects.title.html(_self.objectData.title);
516				_self.objects.title.show();
517			} else {
518				_self.objects.title.empty();
519				_self.objects.title.hide();
520			}
521			// Add caption to the content holder or hide if its empty
522			if (_self.settings.showCaption === true && _self.objectData.caption !== undefined && _self.objectData.caption !== '') {
523				_self.objects.caption.html(_self.objectData.caption);
524				_self.objects.caption.show();
525			} else {
526				_self.objects.caption.empty();
527				_self.objects.caption.hide();
528			}
529		},
530
531		/**
532		 * Loads the new object
533		 *
534		 * @param	{object}	$object
535		 * @return	{void}
536		 */
537		_loadObject: function ($object) {
538			// Load the object
539			switch (_self.objectData.type) {
540				case 'inline':
541					if ($(_self.objectData.url)) {
542						_self._showContent($object);
543					} else {
544						_self.error();
545					}
546					break;
547				case 'ajax':
548					$.ajax(
549						$.extend({}, _self.settings.ajax, {
550							url: _self.objectData.url,
551							type: _self.objectData.requestType,
552							dataType: _self.objectData.requestDataType,
553							data: _self.objectData.requestData,
554							success: function (data, textStatus, jqXHR) {
555								// Check for X-Ajax-Location
556								if (jqXHR.getResponseHeader('X-Ajax-Location')) {
557									_self.objectData.url = jqXHR.getResponseHeader('X-Ajax-Location');
558									_self._loadObject($object);
559								}
560								else {
561									// Unserialize if data is transferred as json
562									if (_self.objectData.requestDataType === 'json') {
563										_self.objectData.data = data;
564									} else {
565										$object.html(data);
566									}
567									_self._showContent($object);
568								}
569							},
570							error: function (jqXHR, textStatus, errorThrown) {
571								_self.error();
572							}
573						})
574					);
575					break;
576				case 'flash':
577					_self._showContent($object);
578					break;
579				case 'video':
580					if (typeof($object.get(0).canPlayType) === 'function' || _self.objects.case.find('video').length === 0) {
581						_self._showContent($object);
582					} else {
583						_self.error();
584					}
585					break;
586				default:
587					if (_self.objectData.url) {
588						$object.on('load', function () {
589							_self._showContent($object);
590						});
591						$object.on('error', function () {
592							_self.error();
593						});
594					} else {
595						_self.error();
596					}
597					break;
598			}
599		},
600
601		/**
602		 * Throws an error message if something went wrong
603		 *
604		 * @return	{void}
605		 */
606		error: function () {
607			_self.objectData.type = 'error';
608			var $object = $('<div class="' + _self.settings.classPrefix + 'inlineWrap"></div>');
609
610			$object.html(_self.settings.errorMessage);
611			_self.objects.contentInner.html($object);
612
613			_self._showContent(_self.objects.contentInner);
614		},
615
616		/**
617		 * Calculates the dimensions to fit content
618		 *
619		 * @param	{object}	$object
620		 * @return	{void}
621		 */
622		_calculateDimensions: function ($object) {
623			_self._cleanupDimensions();
624
625			if (!$object) return;
626
627			// Set default dimensions
628			var dimensions = {
629				ratio: 1,
630				objectWidth: $object.attr('width') ? $object.attr('width') : $object.attr(_self._prefixAttributeName('width')),
631				objectHeight: $object.attr('height') ? $object.attr('height') : $object.attr(_self._prefixAttributeName('height'))
632			};
633
634			if (!_self.settings.disableShrink) {
635				// Add calculated maximum width/height to dimensions
636				dimensions.maxWidth = parseInt(_self.dimensions.windowWidth * _self.settings.shrinkFactor);
637				dimensions.maxHeight = parseInt(_self.dimensions.windowHeight * _self.settings.shrinkFactor);
638
639				// If the auto calculated maxWidth/maxHeight greather than the user-defined one, use that.
640				if (dimensions.maxWidth > _self.settings.maxWidth) {
641					dimensions.maxWidth = _self.settings.maxWidth;
642				}
643				if (dimensions.maxHeight > _self.settings.maxHeight) {
644					dimensions.maxHeight = _self.settings.maxHeight;
645				}
646
647				// Calculate the difference between screen width/height and image width/height
648				dimensions.differenceWidthAsPercent = parseInt(100 / dimensions.maxWidth * dimensions.objectWidth);
649				dimensions.differenceHeightAsPercent = parseInt(100 / dimensions.maxHeight * dimensions.objectHeight);
650
651				switch (_self.objectData.type) {
652					case 'image':
653					case 'flash':
654					case 'video':
655					case 'iframe':
656					case 'ajax':
657					case 'inline':
658						if (_self.objectData.type === 'image' || _self.settings.fixedRatio === true) {
659							if (dimensions.differenceWidthAsPercent > 100 && dimensions.differenceWidthAsPercent > dimensions.differenceHeightAsPercent) {
660								dimensions.objectWidth = dimensions.maxWidth;
661								dimensions.objectHeight = parseInt(dimensions.objectHeight / dimensions.differenceWidthAsPercent * 100);
662							}
663							if (dimensions.differenceHeightAsPercent > 100 && dimensions.differenceHeightAsPercent > dimensions.differenceWidthAsPercent) {
664								dimensions.objectWidth = parseInt(dimensions.objectWidth / dimensions.differenceHeightAsPercent * 100);
665								dimensions.objectHeight = dimensions.maxHeight;
666							}
667							if (dimensions.differenceHeightAsPercent > 100 && dimensions.differenceWidthAsPercent < dimensions.differenceHeightAsPercent) {
668								dimensions.objectWidth = parseInt(dimensions.maxWidth / dimensions.differenceHeightAsPercent * dimensions.differenceWidthAsPercent);
669								dimensions.objectHeight = dimensions.maxHeight;
670							}
671							break;
672						}
673					case 'error':
674						if (!isNaN(dimensions.objectWidth) && dimensions.objectWidth > dimensions.maxWidth) {
675							dimensions.objectWidth = dimensions.maxWidth;
676						}
677						break;
678					default:
679						if ((isNaN(dimensions.objectWidth) || dimensions.objectWidth > dimensions.maxWidth) && !_self.settings.forceWidth) {
680							dimensions.objectWidth = dimensions.maxWidth;
681						}
682						if (((isNaN(dimensions.objectHeight) && dimensions.objectHeight !== 'auto') || dimensions.objectHeight > dimensions.maxHeight) && !_self.settings.forceHeight) {
683							dimensions.objectHeight = dimensions.maxHeight;
684						}
685						break;
686				}
687			}
688
689			if (_self.settings.forceWidth) {
690				try {
691					dimensions.objectWidth = _self.settings[_self.objectData.type].width;
692				} catch (e) {
693					dimensions.objectWidth = _self.settings.width || dimensions.objectWidth;
694				}
695
696				dimensions.maxWidth = null;
697			}
698			if ($object.attr(_self._prefixAttributeName('max-width'))) {
699				dimensions.maxWidth = $object.attr(_self._prefixAttributeName('max-width'));
700			}
701
702			if (_self.settings.forceHeight) {
703				try {
704					dimensions.objectHeight = _self.settings[_self.objectData.type].height;
705				} catch (e) {
706					dimensions.objectHeight = _self.settings.height || dimensions.objectHeight;
707				}
708
709				dimensions.maxHeight = null;
710			}
711			if ($object.attr(_self._prefixAttributeName('max-height'))) {
712				dimensions.maxHeight = $object.attr(_self._prefixAttributeName('max-height'));
713			}
714			_self._adjustDimensions($object, dimensions);
715		},
716
717		/**
718		 * Adjusts the dimensions
719		 *
720		 * @param	{object}	$object
721		 * @param	{object}	dimensions
722		 * @return	{void}
723		 */
724		_adjustDimensions: function ($object, dimensions) {
725			// Adjust width and height
726			$object.css({
727				'width': dimensions.objectWidth,
728				'height': dimensions.objectHeight,
729				'max-width': dimensions.maxWidth,
730				'max-height': dimensions.maxHeight
731			});
732
733			_self.objects.contentInner.css({
734				'width': $object.outerWidth(),
735				'height': $object.outerHeight(),
736				'max-width': '100%'
737			});
738
739			_self.objects.case.css({
740				'width': _self.objects.contentInner.outerWidth(),
741				'max-width': '100%'
742			});
743
744			// Adjust margin
745			_self.objects.case.css({
746				'margin-top': parseInt(-(_self.objects.case.outerHeight() / 2)),
747				'margin-left': parseInt(-(_self.objects.case.outerWidth() / 2))
748			});
749		},
750
751		/**
752		 * Handles the _loading
753		 *
754		 * @param	{string}	process
755		 * @return	{void}
756		 */
757		_loading: function (process) {
758			if (process === 'start') {
759				_self.objects.case.addClass(_self.settings.classPrefix + 'loading');
760				_self.objects.loading.show();
761			} else if (process === 'end') {
762				_self.objects.case.removeClass(_self.settings.classPrefix + 'loading');
763				_self.objects.loading.hide();
764			}
765		},
766
767
768		/**
769		 * Gets the client screen dimensions
770		 *
771		 * @return	{object}	dimensions
772		 */
773		getViewportDimensions: function () {
774			return {
775				windowWidth: $(window).innerWidth(),
776				windowHeight: $(window).innerHeight()
777			};
778		},
779
780		/**
781		 * Verifies the url
782		 *
783		 * @param	{string}	dataUrl
784		 * @return	{object}	dataUrl	Clean url for processing content
785		 */
786		_verifyDataUrl: function (dataUrl) {
787			if (!dataUrl || dataUrl === undefined || dataUrl === '') {
788				return false;
789			}
790
791			if (dataUrl.indexOf('#') > -1) {
792				dataUrl = dataUrl.split('#');
793				dataUrl = '#' + dataUrl[dataUrl.length - 1];
794			}
795
796			return _self._normalizeUrl(dataUrl.toString());
797		},
798
799			// 
800		/**
801		 * Tries to get the (file) suffix of an url
802		 *
803		 * @param	{string}	url
804		 * @return	{string}
805		 */
806		_getFileUrlSuffix: function (url) {
807			var re = /(?:\.([^.]+))?$/;
808			return re.exec(url.toLowerCase())[1]; 
809		},
810
811		/**
812		 * Verifies the data type of the content to load
813		 *
814		 * @param	{string}			url
815		 * @return	{string|boolean}	Array key if expression matched, else false
816		 */
817		_verifyDataType: function (url) {
818			var typeMapping = _self.settings.typeMapping;
819
820			// Early abort if dataUrl couldn't be verified
821			if (!url) {
822				return false;
823			}
824
825			// Verify the dataType of url according to typeMapping which
826			// has been defined in settings.
827			for (var key in typeMapping) {
828				if (typeMapping.hasOwnProperty(key)) {
829					var suffixArr = typeMapping[key].split(',');
830
831					for (var i = 0; i < suffixArr.length; i++) {
832						var suffix = suffixArr[i].toLowerCase(),
833							regexp = new RegExp('\.(' + suffix + ')$', 'i'),
834							str = url.toLowerCase().split('?')[0].substr(-5);
835
836						if (regexp.test(str) === true || (key === 'inline' && (url.indexOf(suffix) > -1))) {
837							return key;
838						}
839					}
840				}
841			}
842
843			// If no expression matched, return 'iframe'.
844			return 'iframe';
845		},
846
847		/**
848		 * Extends html markup with the essential tags
849		 *
850		 * @return	{void}
851		 */
852		_addElements: function () {
853			if (typeof _self.objects.case !== 'undefined' && $('#' + _self.objects.case.attr('id')).length) {
854				return;
855			}
856
857			_self.settings.markup();
858		},
859
860		/**
861		 * Shows the loaded content
862		 *
863		 * @param	{object}	$object
864		 * @return	{void}
865		 */
866		_showContent: function ($object) {
867			// Add data attribute with the object type
868			_self.objects.document.attr(_self._prefixAttributeName('type'), _self.objectData.type);
869
870			_self.cache.object = $object;
871
872			// Call onCalculateDimensions hook functions
873			_self._callHooks(_self.settings.onCalculateDimensions);
874
875			_self._calculateDimensions($object);
876
877			// Call onFinish hook functions
878			_self._callHooks(_self.settings.onFinish);
879
880			_self._startInTransition();
881		},
882
883		/**
884		 * Starts the 'inTransition'
885		 * @return	{void}
886		 */
887		_startInTransition: function () {
888			switch (_self.transition.in()) {
889				case 'scrollTop':
890				case 'scrollRight':
891				case 'scrollBottom':
892				case 'scrollLeft':
893				case 'scrollHorizontal':
894				case 'scrollVertical':
895					_self.transition.scroll(_self.objects.case, 'in', _self.settings.speedIn);
896					_self.transition.fade(_self.objects.contentInner, 'in', _self.settings.speedIn);
897					break;
898				case 'elastic':
899					if (_self.objects.case.css('opacity') < 1) {
900						_self.transition.zoom(_self.objects.case, 'in', _self.settings.speedIn);
901						_self.transition.fade(_self.objects.contentInner, 'in', _self.settings.speedIn);
902				}
903				case 'fade':
904				case 'fadeInline':
905					_self.transition.fade(_self.objects.case, 'in', _self.settings.speedIn);
906					_self.transition.fade(_self.objects.contentInner, 'in', _self.settings.speedIn);
907					break;
908				default:
909					_self.transition.fade(_self.objects.case, 'in', 0);
910					break;
911			}
912 
913			// End loading.
914			_self._loading('end');
915			_self.isBusy = false;
916
917			// Set index of the first item opened
918			if (!_self.cache.firstOpened) {
919				_self.cache.firstOpened = _self.objectData.this;
920			}
921 
922			// Fade in the info with delay
923			_self.objects.info.hide();
924			setTimeout(function () {
925				 _self.transition.fade(_self.objects.info, 'in', _self.settings.speedIn);
926			}, _self.settings.speedIn);
927		},
928
929		/**
930		 * Processes the content to show
931		 *
932		 * @return	{void}
933		 */
934		_processContent: function () {
935			_self.isBusy = true;
936
937			// Fade out the info at first
938			_self.transition.fade(_self.objects.info, 'out', 0);
939
940			switch (_self.settings.transitionOut) {
941				case 'scrollTop':
942				case 'scrollRight':
943				case 'scrollBottom':
944				case 'scrollLeft':
945				case 'scrollVertical':
946				case 'scrollHorizontal':
947					if (_self.objects.case.is(':hidden')) {
948						_self.transition.fade(_self.objects.contentInner, 'out', 0);
949						_self.transition.fade(_self.objects.case, 'out', 0, 0, function () {
950							_self._loadContent();
951						});
952					} else {
953						_self.transition.scroll(_self.objects.case, 'out', _self.settings.speedOut, function () {
954							_self._loadContent();
955						});
956					}
957					break;
958				case 'fade':
959					if (_self.objects.case.is(':hidden')) {
960						_self.transition.fade(_self.objects.case, 'out', 0, 0, function () {
961							_self._loadContent();
962						});
963					} else {
964						_self.transition.fade(_self.objects.case, 'out', _self.settings.speedOut, 0, function () {
965							_self._loadContent();
966						});
967					}
968					break;
969				case 'fadeInline':
970				case 'elastic':
971					if (_self.objects.case.is(':hidden')) {
972						_self.transition.fade(_self.objects.case, 'out', 0, 0, function () {
973							_self._loadContent();
974						});
975					} else {
976						_self.transition.fade(_self.objects.contentInner, 'out', _self.settings.speedOut, 0, function () {
977							_self._loadContent();
978						});
979					}
980					break;
981				default:
982					_self.transition.fade(_self.objects.case, 'out', 0, 0, function () {
983						_self._loadContent();
984					});
985					break;
986			}
987		},
988
989		/**
990		 * Handles events for gallery buttons
991		 *
992		 * @return	{void}
993		 */
994		_handleEvents: function () {
995			_self._unbindEvents();
996
997			_self.objects.nav.children().not(_self.objects.close).hide();
998
999			// If slideshow is enabled, show play/pause and start timeout.
1000			if (_self.isSlideshowEnabled()) {
1001				// Only start the timeout if slideshow autostart is enabled and slideshow is not pausing
1002				if (
1003					(_self.settings.slideshowAutoStart === true || _self.isSlideshowStarted) &&
1004					!_self.objects.nav.hasClass(_self.settings.classPrefix + 'paused')
1005				) {
1006					_self._startTimeout();
1007				} else {
1008					_self._stopTimeout();
1009				}
1010			}
1011
1012			if (_self.settings.liveResize) {
1013				_self._watchResizeInteraction();
1014			}
1015
1016			_self.objects.close.click(function (event) {
1017				event.preventDefault();
1018				_self.close();
1019			});
1020
1021			if (_self.settings.closeOnOverlayClick === true) {
1022				_self.objects.overlay.css('cursor', 'pointer').click(function (event) {
1023					event.preventDefault();
1024
1025					_self.close();
1026				});
1027			}
1028
1029			if (_self.settings.useKeys === true) {
1030				_self._addKeyEvents();
1031			}
1032
1033			if (_self.objectData.isPartOfSequence) {
1034				_self.objects.nav.attr(_self._prefixAttributeName('ispartofsequence'), true);
1035				_self.objects.nav.data('items', _self._setNavigation());
1036
1037				_self.objects.prev.click(function (event) {
1038					event.preventDefault();
1039
1040					if (_self.settings.navigateEndless === true || !_self.item.isFirst()) {
1041						_self.objects.prev.unbind('click');
1042						_self.cache.action = 'prev';
1043						_self.objects.nav.data('items').prev.click();
1044
1045						if (_self.isSlideshowEnabled()) {
1046							_self._stopTimeout();
1047						}
1048					}
1049				});
1050
1051				_self.objects.next.click(function (event) {
1052					event.preventDefault();
1053
1054					if (_self.settings.navigateEndless === true || !_self.item.isLast()) {
1055						_self.objects.next.unbind('click');
1056						_self.cache.action = 'next';
1057						_self.objects.nav.data('items').next.click();
1058
1059						if (_self.isSlideshowEnabled()) {
1060							_self._stopTimeout();
1061						}
1062					}
1063				});
1064
1065				if (_self.isSlideshowEnabled()) {
1066					_self.objects.play.click(function (event) {
1067						event.preventDefault();
1068						_self._startTimeout();
1069					});
1070					_self.objects.pause.click(function (event) {
1071						event.preventDefault();
1072						_self._stopTimeout();
1073					});
1074				}
1075
1076				// Enable swiping if activated
1077				if (_self.settings.swipe === true) {
1078					if ($.isPlainObject($.event.special.swipeleft)) {
1079						_self.objects.case.on('swipeleft', function (event) {
1080							event.preventDefault();
1081							_self.objects.next.click();
1082							if (_self.isSlideshowEnabled()) {
1083								_self._stopTimeout();
1084							}
1085						});
1086					}
1087					if ($.isPlainObject($.event.special.swiperight)) {
1088						_self.objects.case.on('swiperight', function (event) {
1089							event.preventDefault();
1090							_self.objects.prev.click();
1091							if (_self.isSlideshowEnabled()) {
1092								_self._stopTimeout();
1093							}
1094						});
1095					}
1096				}
1097			}
1098		},
1099
1100		/**
1101		 * Adds the key events
1102		 *
1103		 * @return	{void}
1104		 */
1105		_addKeyEvents: function () {
1106			$(document).bind('keyup.lightcase', function (event) {
1107				// Do nothing if lightcase is in process
1108				if (_self.isBusy) {
1109					return;
1110				}
1111
1112				switch (event.keyCode) {
1113					// Escape key
1114					case 27:
1115						_self.objects.close.click();
1116						break;
1117					// Backward key
1118					case 37:
1119						if (_self.objectData.isPartOfSequence) {
1120							_self.objects.prev.click();
1121						}
1122						break;
1123					// Forward key
1124					case 39:
1125						if (_self.objectData.isPartOfSequence) {
1126							_self.objects.next.click();
1127						}
1128						break;
1129				}
1130			});
1131		},
1132
1133		/**
1134		 * Starts the slideshow timeout
1135		 *
1136		 * @return	{void}
1137		 */
1138		_startTimeout: function () {
1139			_self.isSlideshowStarted = true;
1140
1141			_self.objects.play.hide();
1142			_self.objects.pause.show();
1143
1144			_self.cache.action = 'next';
1145			_self.objects.nav.removeClass(_self.settings.classPrefix + 'paused');
1146
1147			_self.timeout = setTimeout(function () {
1148				_self.objects.nav.data('items').next.click();
1149			}, _self.settings.timeout);
1150		},
1151
1152		/**
1153		 * Stops the slideshow timeout
1154		 *
1155		 * @return	{void}
1156		 */
1157		_stopTimeout: function () {
1158			_self.objects.play.show();
1159			_self.objects.pause.hide();
1160
1161			_self.objects.nav.addClass(_self.settings.classPrefix + 'paused');
1162
1163			clearTimeout(_self.timeout);
1164		},
1165
1166		/**
1167		 * Sets the navigator buttons (prev/next)
1168		 *
1169		 * @return	{object}	items
1170		 */
1171		_setNavigation: function () {
1172			var $links = $((_self.cache.selector || _self.settings.attr)),
1173				sequenceLength = _self.objectData.sequenceLength - 1,
1174				items = {
1175					prev: $links.eq(_self.objectData.prevIndex),
1176					next: $links.eq(_self.objectData.nextIndex)
1177				};
1178
1179			if (_self.objectData.currentIndex > 0) {
1180				_self.objects.prev.show();
1181			} else {
1182				items.prevItem = $links.eq(sequenceLength);
1183			}
1184			if (_self.objectData.nextIndex <= sequenceLength) {
1185				_self.objects.next.show();
1186			} else {
1187				items.next = $links.eq(0);
1188			}
1189
1190			if (_self.settings.navigateEndless === true) {
1191				_self.objects.prev.show();
1192				_self.objects.next.show();
1193			}
1194
1195			return items;
1196		},
1197
1198		/**
1199		 * Item information/status
1200		 *
1201		 */
1202		item: {
1203			/**
1204			 * Verifies if the current item is first item.
1205			 *
1206			 * @return	{boolean}
1207			 */
1208			isFirst: function () {
1209				return (_self.objectData.currentIndex === 0);
1210			},
1211
1212			/**
1213			 * Verifies if the current item is first item opened.
1214			 *
1215			 * @return	{boolean}
1216			 */
1217			isFirstOpened: function () {
1218				return _self.objectData.this.is(_self.cache.firstOpened);
1219			},
1220
1221			/**
1222			 * Verifies if the current item is last item.
1223			 *
1224			 * @return	{boolean}
1225			 */
1226			isLast: function () {
1227				return (_self.objectData.currentIndex === (_self.objectData.sequenceLength - 1));
1228			}
1229		},
1230
1231		/**
1232		 * Clones the object for inline elements
1233		 *
1234		 * @param	{object}	$object
1235		 * @return	{object}	$clone
1236		 */
1237		_cloneObject: function ($object) {
1238			var $clone = $object.clone(),
1239				objectId = $object.attr('id');
1240
1241			// If element is hidden, cache the object and remove
1242			if ($object.is(':hidden')) {
1243				_self._cacheObjectData($object);
1244				$object.attr('id', _self.settings.idPrefix + 'temp-' + objectId).empty();
1245			} else {
1246				// Prevent duplicated id's
1247				$clone.removeAttr('id');
1248			}
1249
1250			return $clone.show();
1251		},
1252
1253		/**
1254		 * Verifies if it is a mobile device
1255		 *
1256		 * @return	{boolean}
1257		 */
1258		isMobileDevice: function () {
1259			var deviceAgent = navigator.userAgent.toLowerCase(),
1260				agentId = deviceAgent.match(_self.settings.mobileMatchExpression);
1261
1262			return agentId ? true : false;
1263		},
1264
1265		/**
1266		 * Verifies if css transitions are supported
1267		 *
1268		 * @return	{string|boolean}	The transition prefix if supported, else false.
1269		 */
1270		isTransitionSupported: function () {
1271			var body = _self.objects.body.get(0),
1272				isTransitionSupported = false,
1273				transitionMapping = {
1274					'transition': '',
1275					'WebkitTransition': '-webkit-',
1276					'MozTransition': '-moz-',
1277					'OTransition': '-o-',
1278					'MsTransition': '-ms-'
1279				};
1280
1281			for (var key in transitionMapping) {
1282				if (transitionMapping.hasOwnProperty(key) && key in body.style) {
1283					_self.support.transition = transitionMapping[key];
1284					isTransitionSupported = true;
1285				}
1286			}
1287
1288			return isTransitionSupported;
1289		},
1290
1291		/**
1292		 * Transition types
1293		 *
1294		 */
1295		transition: {
1296			/**
1297			 * Returns the correct transition type according to the status of interaction.
1298			 *
1299			 * @return	{string}	Transition type
1300			 */
1301			in: function () {
1302				if (_self.settings.transitionOpen && !_self.cache.firstOpened) {
1303					return _self.settings.transitionOpen;
1304				}
1305				return _self.settings.transitionIn;
1306			},
1307
1308			/**
1309			 * Fades in/out the object
1310			 *
1311			 * @param	{object}	$object
1312			 * @param	{string}	type
1313			 * @param	{number}	speed
1314			 * @param	{number}	opacity
1315			 * @param	{function}	callback
1316			 * @return	{void}		Animates an object
1317			 */
1318			fade: function ($object, type, speed, opacity, callback) {
1319				var isInTransition = type === 'in',
1320					startTransition = {},
1321					startOpacity = $object.css('opacity'),
1322					endTransition = {},
1323					endOpacity = opacity ? opacity: isInTransition ? 1 : 0;
1324
1325				if (!_self.isOpen && isInTransition) return;
1326
1327				startTransition['opacity'] = startOpacity;
1328				endTransition['opacity'] = endOpacity;
1329
1330				$object.css(_self.support.transition + 'transition', 'none');
1331				$object.css(startTransition).show();
1332
1333				// Css transition
1334				if (_self.support.transitions) {
1335					endTransition[_self.support.transition + 'transition'] = speed + 'ms ease';
1336
1337					setTimeout(function () {
1338						$object.css(endTransition);
1339
1340						setTimeout(function () {
1341							$object.css(_self.support.transition + 'transition', '');
1342
1343							if (callback && (_self.isOpen || !isInTransition)) {
1344								callback();
1345							}
1346						}, speed);
1347					}, 15);
1348				} else {
1349					// Fallback to js transition
1350					$object.stop();
1351					$object.animate(endTransition, speed, callback);
1352				}
1353			},
1354
1355			/**
1356			 * Scrolls in/out the object
1357			 *
1358			 * @param	{object}	$object
1359			 * @param	{string}	type
1360			 * @param	{number}	speed
1361			 * @param	{function}	callback
1362			 * @return	{void}		Animates an object
1363			 */
1364			scroll: function ($object, type, speed, callback) {
1365				var isInTransition = type === 'in',
1366					transition = isInTransition ? _self.settings.transitionIn : _self.settings.transitionOut,
1367					direction = 'left',
1368					startTransition = {},
1369					startOpacity = isInTransition ? 0 : 1,
1370					startOffset = isInTransition ? '-50%' : '50%',
1371					endTransition = {},
1372					endOpacity = isInTransition ? 1 : 0,
1373					endOffset = isInTransition ? '50%' : '-50%';
1374
1375				if (!_self.isOpen && isInTransition) return;
1376
1377				switch (transition) {
1378					case 'scrollTop':
1379						direction = 'top';
1380						break;
1381					case 'scrollRight':
1382						startOffset = isInTransition ? '150%' : '50%';
1383						endOffset = isInTransition ? '50%' : '150%';
1384						break;
1385					case 'scrollBottom':
1386						direction = 'top';
1387						startOffset = isInTransition ? '150%' : '50%';
1388						endOffset = isInTransition ? '50%' : '150%';
1389						break;
1390					case 'scrollHorizontal':
1391						startOffset = isInTransition ? '150%' : '50%';
1392						endOffset = isInTransition ? '50%' : '-50%';
1393						break;
1394					case 'scrollVertical':
1395						direction = 'top';
1396						startOffset = isInTransition ? '-50%' : '50%';
1397						endOffset = isInTransition ? '50%' : '150%';
1398						break;
1399				}
1400
1401				if (_self.cache.action === 'prev') {
1402					switch (transition) {
1403						case 'scrollHorizontal':
1404							startOffset = isInTransition ? '-50%' : '50%';
1405							endOffset = isInTransition ? '50%' : '150%';
1406							break;
1407						case 'scrollVertical':
1408							startOffset = isInTransition ? '150%' : '50%';
1409							endOffset = isInTransition ? '50%' : '-50%';
1410							break;
1411					}
1412				}
1413
1414				startTransition['opacity'] = startOpacity;
1415				startTransition[direction] = startOffset;
1416
1417				endTransition['opacity'] = endOpacity;
1418				endTransition[direction] = endOffset;
1419
1420				$object.css(_self.support.transition + 'transition', 'none');
1421				$object.css(startTransition).show();
1422
1423				// Css transition
1424				if (_self.support.transitions) {
1425					endTransition[_self.support.transition + 'transition'] = speed + 'ms ease';
1426
1427					setTimeout(function () {
1428						$object.css(endTransition);
1429
1430						setTimeout(function () {
1431							$object.css(_self.support.transition + 'transition', '');
1432
1433							if (callback && (_self.isOpen || !isInTransition)) {
1434								callback();
1435							}
1436						}, speed);
1437					}, 15);
1438				} else {
1439					// Fallback to js transition
1440					$object.stop();
1441					$object.animate(endTransition, speed, callback);
1442				}
1443			},
1444
1445			/**
1446			 * Zooms in/out the object
1447			 *
1448			 * @param	{object}	$object
1449			 * @param	{string}	type
1450			 * @param	{number}	speed
1451			 * @param	{function}	callback
1452			 * @return	{void}		Animates an object
1453			 */
1454			zoom: function ($object, type, speed, callback) {
1455				var isInTransition = type === 'in',
1456					startTransition = {},
1457					startOpacity = $object.css('opacity'),
1458					startScale = isInTransition ? 'scale(0.75)' : 'scale(1)',
1459					endTransition = {},
1460					endOpacity = isInTransition ? 1 : 0,
1461					endScale = isInTransition ? 'scale(1)' : 'scale(0.75)';
1462
1463				if (!_self.isOpen && isInTransition) return;
1464
1465				startTransition['opacity'] = startOpacity;
1466				startTransition[_self.support.transition + 'transform'] = startScale;
1467
1468				endTransition['opacity'] = endOpacity;
1469
1470				$object.css(_self.support.transition + 'transition', 'none');
1471				$object.css(startTransition).show();
1472
1473				// Css transition
1474				if (_self.support.transitions) {
1475					endTransition[_self.support.transition + 'transform'] = endScale;
1476					endTransition[_self.support.transition + 'transition'] = speed + 'ms ease';
1477
1478					setTimeout(function () {
1479						$object.css(endTransition);
1480
1481						setTimeout(function () {
1482							$object.css(_self.support.transition + 'transform', '');
1483							$object.css(_self.support.transition + 'transition', '');
1484
1485							if (callback && (_self.isOpen || !isInTransition)) {
1486								callback();
1487							}
1488						}, speed);
1489					}, 15);
1490				} else {
1491					// Fallback to js transition
1492					$object.stop();
1493					$object.animate(endTransition, speed, callback);
1494				}
1495			}
1496		},
1497
1498		/**
1499		 * Calls all the registered functions of a specific hook
1500		 *
1501		 * @param	{object}	hooks
1502		 * @return	{void}
1503		 */
1504		_callHooks: function (hooks) {
1505			if (typeof(hooks) === 'object') {
1506				$.each(hooks, function(index, hook) {
1507					if (typeof(hook) === 'function') {
1508						hook.call(_self.origin);
1509					}
1510				});
1511			}
1512		},
1513
1514		/**
1515		 * Caches the object data
1516		 *
1517		 * @param	{object}	$object
1518		 * @return	{void}
1519		 */
1520		_cacheObjectData: function ($object) {
1521			$.data($object, 'cache', {
1522				id: $object.attr('id'),
1523				content: $object.html()
1524			});
1525
1526			_self.cache.originalObject = $object;
1527		},
1528
1529		/**
1530		 * Restores the object from cache
1531		 *
1532		 * @return	void
1533		 */
1534		_restoreObject: function () {
1535			var $object = $('[id^="' + _self.settings.idPrefix + 'temp-"]');
1536
1537			$object.attr('id', $.data(_self.cache.originalObject, 'cache').id);
1538			$object.html($.data(_self.cache.originalObject, 'cache').content);
1539		},
1540
1541		/**
1542		 * Executes functions for a window resize.
1543		 * It stops an eventual timeout and recalculates dimenstions.
1544		 *
1545		 * @param	{boolean}	startInTransition
1546		 * @return	{void}
1547		 */
1548		resize: function (event, startInTransition) {
1549			if (!_self.isOpen) return;
1550
1551			if (_self.isSlideshowEnabled()) {
1552				_self._stopTimeout();
1553			}
1554
1555			_self.dimensions = _self.getViewportDimensions();
1556			_self._calculateDimensions(_self.cache.object);
1557
1558			// Call onResize hook functions
1559			_self._callHooks(_self.settings.onResize);
1560
1561			if (startInTransition) {
1562				_self._startInTransition(_self.cache.object);
1563			}
1564		},
1565
1566		/**
1567		 * Watches for any resize interaction and caches the new sizes.
1568		 *
1569		 * @return	{void}
1570		 */
1571		_watchResizeInteraction: function () {
1572			$(window).resize(_self.resize);
1573		},
1574
1575		/**
1576		 * Stop watching any resize interaction related to _self.
1577		 *
1578		 * @return	{void}
1579		 */
1580		_unwatchResizeInteraction: function () {
1581			$(window).off('resize', _self.resize);
1582		},
1583
1584		/**
1585		 * Switches to the fullscreen mode
1586		 *
1587		 * @return	{void}
1588		 */
1589		_switchToFullScreenMode: function () {
1590			_self.settings.shrinkFactor = 1;
1591			_self.settings.overlayOpacity = 1;
1592
1593			$('html').addClass(_self.settings.classPrefix + 'fullScreenMode');
1594		},
1595
1596		/**
1597		 * Enters into the lightcase view
1598		 *
1599		 * @return	{void}
1600		 */
1601		_open: function () {
1602			_self.isOpen = true;
1603
1604			_self.support.transitions = _self.settings.cssTransitions ? _self.isTransitionSupported() : false;
1605			_self.support.mobileDevice = _self.isMobileDevice();
1606
1607			if (_self.support.mobileDevice) {
1608				$('html').addClass(_self.settings.classPrefix + 'isMobileDevice');
1609
1610				if (_self.settings.fullScreenModeForMobile) {
1611					_self._switchToFullScreenMode();
1612				}
1613			}
1614
1615			if (!_self.settings.transitionIn) {
1616				_self.settings.transitionIn = _self.settings.transition;
1617			}
1618			if (!_self.settings.transitionOut) {
1619				_self.settings.transitionOut = _self.settings.transition;
1620			}
1621
1622			switch (_self.transition.in()) {
1623				case 'fade':
1624				case 'fadeInline':
1625				case 'elastic':
1626				case 'scrollTop':
1627				case 'scrollRight':
1628				case 'scrollBottom':
1629				case 'scrollLeft':
1630				case 'scrollVertical':
1631				case 'scrollHorizontal':
1632					if (_self.objects.case.is(':hidden')) {
1633						_self.objects.close.css('opacity', 0);
1634						_self.objects.overlay.css('opacity', 0);
1635						_self.objects.case.css('opacity', 0);
1636						_self.objects.contentInner.css('opacity', 0);
1637					}
1638					_self.transition.fade(_self.objects.overlay, 'in', _self.settings.speedIn, _self.settings.overlayOpacity, function () {
1639						_self.transition.fade(_self.objects.close, 'in', _self.settings.speedIn);
1640						_self._handleEvents();
1641						_self._processContent();
1642					});
1643					break;
1644				default:
1645					_self.transition.fade(_self.objects.overlay, 'in', 0, _self.settings.overlayOpacity, function () {
1646						_self.transition.fade(_self.objects.close, 'in', 0);
1647						_self._handleEvents();
1648						_self._processContent();
1649					});
1650					break;
1651			}
1652
1653			_self.objects.document.addClass(_self.settings.classPrefix + 'open');
1654			_self.objects.case.attr('aria-hidden', 'false');
1655		},
1656
1657		/**
1658		 * Escapes from the lightcase view
1659		 *
1660		 * @return	{void}
1661		 */
1662		close: function () {
1663			_self.isOpen = false;
1664
1665			if (_self.isSlideshowEnabled()) {
1666				_self._stopTimeout();
1667				_self.isSlideshowStarted = false;
1668				_self.objects.nav.removeClass(_self.settings.classPrefix + 'paused');
1669			}
1670
1671			_self.objects.loading.hide();
1672
1673			_self._unbindEvents();
1674
1675			_self._unwatchResizeInteraction();
1676
1677			$('html').removeClass(_self.settings.classPrefix + 'open');
1678			_self.objects.case.attr('aria-hidden', 'true');
1679
1680			_self.objects.nav.children().hide();
1681			_self.objects.close.hide();
1682
1683			// Call onClose hook functions
1684			_self._callHooks(_self.settings.onClose);
1685
1686			// Fade out the info at first
1687			_self.transition.fade(_self.objects.info, 'out', 0);
1688
1689			switch (_self.settings.transitionClose || _self.settings.transitionOut) {
1690				case 'fade':
1691				case 'fadeInline':
1692				case 'scrollTop':
1693				case 'scrollRight':
1694				case 'scrollBottom':
1695				case 'scrollLeft':
1696				case 'scrollHorizontal':
1697				case 'scrollVertical':
1698					_self.transition.fade(_self.objects.case, 'out', _self.settings.speedOut, 0, function () {
1699						_self.transition.fade(_self.objects.overlay, 'out', _self.settings.speedOut, 0, function () {
1700							_self.cleanup();
1701						});
1702					});
1703					break;
1704				case 'elastic':
1705					_self.transition.zoom(_self.objects.case, 'out', _self.settings.speedOut, function () {
1706						_self.transition.fade(_self.objects.overlay, 'out', _self.settings.speedOut, 0, function () {
1707							_self.cleanup();
1708						});
1709					});
1710					break;
1711				default:
1712					_self.cleanup();
1713					break;
1714			}
1715		},
1716
1717		/**
1718		 * Unbinds all given events
1719		 *
1720		 * @return	{void}
1721		 */
1722		_unbindEvents: function () {
1723			// Unbind overlay event
1724			_self.objects.overlay.unbind('click');
1725
1726			// Unbind key events
1727			$(document).unbind('keyup.lightcase');
1728
1729			// Unbind swipe events
1730			_self.objects.case.unbind('swipeleft').unbind('swiperight');
1731
1732			// Unbind navigator events
1733			_self.objects.prev.unbind('click');
1734			_self.objects.next.unbind('click');
1735			_self.objects.play.unbind('click');
1736			_self.objects.pause.unbind('click');
1737
1738			// Unbind close event
1739			_self.objects.close.unbind('click');
1740		},
1741
1742		/**
1743		 * Cleans up the dimensions
1744		 *
1745		 * @return	{void}
1746		 */
1747		_cleanupDimensions: function () {
1748			var opacity = _self.objects.contentInner.css('opacity');
1749
1750			_self.objects.case.css({
1751				'width': '',
1752				'height': '',
1753				'top': '',
1754				'left': '',
1755				'margin-top': '',
1756				'margin-left': ''
1757			});
1758
1759			_self.objects.contentInner.removeAttr('style').css('opacity', opacity);
1760			_self.objects.contentInner.children().removeAttr('style');
1761		},
1762
1763		/**
1764		 * Cleanup after aborting lightcase
1765		 *
1766		 * @return	{void}
1767		 */
1768		cleanup: function () {
1769			_self._cleanupDimensions();
1770
1771			_self.objects.loading.hide();
1772			_self.objects.overlay.hide();
1773			_self.objects.case.hide();
1774			_self.objects.prev.hide();
1775			_self.objects.next.hide();
1776			_self.objects.play.hide();
1777			_self.objects.pause.hide();
1778
1779			_self.objects.document.removeAttr(_self._prefixAttributeName('type'));
1780			_self.objects.nav.removeAttr(_self._prefixAttributeName('ispartofsequence'));
1781
1782			_self.objects.contentInner.empty().hide();
1783			_self.objects.info.children().empty();
1784
1785			if (_self.cache.originalObject) {
1786				_self._restoreObject();
1787			}
1788
1789			// Call onCleanup hook functions
1790			_self._callHooks(_self.settings.onCleanup);
1791
1792			// Restore cache
1793			_self.cache = {};
1794		},
1795
1796		/**
1797		 * Returns the supported match media or undefined if the browser
1798		 * doesn't support match media.
1799		 *
1800		 * @return	{mixed}
1801		 */
1802		_matchMedia: function () {
1803			return window.matchMedia || window.msMatchMedia;
1804		},
1805
1806		/**
1807		 * Returns the devicePixelRatio if supported. Else, it simply returns
1808		 * 1 as the default.
1809		 *
1810		 * @return	{number}
1811		 */
1812		_devicePixelRatio: function () {
1813			return window.devicePixelRatio || 1;
1814		},
1815
1816		/**
1817		 * Checks if method is public
1818		 *
1819		 * @return	{boolean}
1820		 */
1821		_isPublicMethod: function (method) {
1822			return (typeof _self[method] === 'function' && method.charAt(0) !== '_');
1823		},
1824
1825		/**
1826		 * Exports all public methods to be accessible, callable
1827		 * from global scope.
1828		 *
1829		 * @return	{void}
1830		 */
1831		_export: function () {
1832			window.lightcase = {};
1833
1834			$.each(_self, function (property) {
1835				if (_self._isPublicMethod(property)) {
1836					lightcase[property] = _self[property];
1837				}
1838			});
1839		}
1840	};
1841
1842	_self._export();
1843
1844	$.fn.lightcase = function (method) {
1845		// Method calling logic (only public methods are applied)
1846		if (_self._isPublicMethod(method)) {
1847			return _self[method].apply(this, Array.prototype.slice.call(arguments, 1));
1848		} else if (typeof method === 'object' || !method) {
1849			return _self.init.apply(this, arguments);
1850		} else {
1851			$.error('Method ' + method + ' does not exist on jQuery.lightcase');
1852		}
1853	};
1854})(jQuery);
1855
1856
1857
1858
1859
1860

Line numbers count LF bytes from the start of the resource, as the search results do. Vendor segments are library code the classifier recognised; they are stored but not indexed. Bytes are shown as Latin1 characters, one per byte.