| 1 |
/*! Lity - v1.6.6 - 2016-04-22 |
| 2 |
* http://sorgalla.com/lity/ |
| 3 |
* Copyright (c) 2016 Jan Sorgalla; Licensed MIT */ |
| 4 |
(function(window, factory) { |
| 5 |
if (typeof define === 'function' && define.amd) { |
| 6 |
define(['jquery'], function($) { |
| 7 |
return factory(window, $); |
| 8 |
}); |
| 9 |
} else if (typeof module === 'object' && typeof module.exports === 'object') { |
| 10 |
module.exports = factory(window, require('jquery')); |
| 11 |
} else { |
| 12 |
window.lity = factory(window, window.jQuery || window.Zepto); |
| 13 |
} |
| 14 |
}(typeof window !== "undefined" ? window : this, function(window, $) { |
| 15 |
'use strict'; |
| 16 |
|
| 17 |
var document = window.document; |
| 18 |
|
| 19 |
var _win = $(window); |
| 20 |
var _html = $('html'); |
| 21 |
var _instanceCount = 0; |
| 22 |
|
| 23 |
var _imageRegexp = /(^data:image\/)|(\.(png|jpe?g|gif|svg|webp|bmp|ico|tiff?)(\?\S*)?$)/i; |
| 24 |
var _youtubeRegex = /(youtube(-nocookie)?\.com|youtu\.be)\/(watch\?v=|v\/|u\/|embed\/?)?([\w-]{11})(.*)?/i; |
| 25 |
var _vimeoRegex = /(vimeo(pro)?.com)\/(?:[^\d]+)?(\d+)\??(.*)?$/; |
| 26 |
var _googlemapsRegex = /((maps|www)\.)?google\.([^\/\?]+)\/?((maps\/?)?\?)(.*)/i; |
| 27 |
|
| 28 |
var _defaultHandlers = { |
| 29 |
image: imageHandler, |
| 30 |
inline: inlineHandler, |
| 31 |
iframe: iframeHandler |
| 32 |
}; |
| 33 |
|
| 34 |
var _defaultOptions = { |
| 35 |
esc: true, |
| 36 |
handler: null, |
| 37 |
template: '<div class="lity" tabindex="-1"><div class="lity-wrap" data-lity-close><div class="lity-loader">Loading...</div><div class="lity-container"><div class="lity-content"></div><button class="lity-close" type="button" title="Close (Esc)" data-lity-close>×</button></div></div></div>' |
| 38 |
}; |
| 39 |
|
| 40 |
function globalToggle() { |
| 41 |
_html[_instanceCount > 0 ? 'addClass' : 'removeClass']('lity-active'); |
| 42 |
} |
| 43 |
|
| 44 |
var transitionEndEvent = (function() { |
| 45 |
var el = document.createElement('div'); |
| 46 |
|
| 47 |
var transEndEventNames = { |
| 48 |
WebkitTransition: 'webkitTransitionEnd', |
| 49 |
MozTransition: 'transitionend', |
| 50 |
OTransition: 'oTransitionEnd otransitionend', |
| 51 |
transition: 'transitionend' |
| 52 |
}; |
| 53 |
|
| 54 |
for (var name in transEndEventNames) { |
| 55 |
if (el.style[name] !== undefined) { |
| 56 |
return transEndEventNames[name]; |
| 57 |
} |
| 58 |
} |
| 59 |
|
| 60 |
return false; |
| 61 |
})(); |
| 62 |
|
| 63 |
function transitionEnd(element) { |
| 64 |
var deferred = $.Deferred(); |
| 65 |
|
| 66 |
if (!transitionEndEvent) { |
| 67 |
deferred.resolve(); |
| 68 |
} else { |
| 69 |
element.one(transitionEndEvent, deferred.resolve); |
| 70 |
setTimeout(deferred.resolve, 500); |
| 71 |
} |
| 72 |
|
| 73 |
return deferred.promise(); |
| 74 |
} |
| 75 |
|
| 76 |
function settings(currSettings, key, value) { |
| 77 |
if (arguments.length === 1) { |
| 78 |
return $.extend({}, currSettings); |
| 79 |
} |
| 80 |
|
| 81 |
if (typeof key === 'string') { |
| 82 |
if (typeof value === 'undefined') { |
| 83 |
return typeof currSettings[key] === 'undefined' ? |
| 84 |
null : |
| 85 |
currSettings[key]; |
| 86 |
} |
| 87 |
currSettings[key] = value; |
| 88 |
} else { |
| 89 |
$.extend(currSettings, key); |
| 90 |
} |
| 91 |
|
| 92 |
return this; |
| 93 |
} |
| 94 |
|
| 95 |
function parseQueryParams(params){ |
| 96 |
var pairs = decodeURI(params).split('&'); |
| 97 |
var obj = {}, p; |
| 98 |
|
| 99 |
for (var i = 0, n = pairs.length; i < n; i++) { |
| 100 |
if (!pairs[i]) { |
| 101 |
continue; |
| 102 |
} |
| 103 |
|
| 104 |
p = pairs[i].split('='); |
| 105 |
obj[p[0]] = p[1]; |
| 106 |
} |
| 107 |
|
| 108 |
return obj; |
| 109 |
} |
| 110 |
|
| 111 |
function appendQueryParams(url, params) { |
| 112 |
return url + (url.indexOf('?') > -1 ? '&' : '?') + $.param(params); |
| 113 |
} |
| 114 |
|
| 115 |
function error(msg) { |
| 116 |
return $('<span class="lity-error"/>').append(msg); |
| 117 |
} |
| 118 |
|
| 119 |
function imageHandler(target) { |
| 120 |
if (!_imageRegexp.test(target)) { |
| 121 |
return false; |
| 122 |
} |
| 123 |
|
| 124 |
var img = $('<img src="' + target + '">'); |
| 125 |
var deferred = $.Deferred(); |
| 126 |
var failed = function() { |
| 127 |
deferred.reject(error('Failed loading image')); |
| 128 |
}; |
| 129 |
|
| 130 |
img |
| 131 |
.on('load', function() { |
| 132 |
if (this.naturalWidth === 0) { |
| 133 |
return failed(); |
| 134 |
} |
| 135 |
|
| 136 |
deferred.resolve(img); |
| 137 |
}) |
| 138 |
.on('error', failed) |
| 139 |
; |
| 140 |
|
| 141 |
return deferred.promise(); |
| 142 |
} |
| 143 |
|
| 144 |
function inlineHandler(target) { |
| 145 |
var el; |
| 146 |
|
| 147 |
try { |
| 148 |
el = $(target); |
| 149 |
} catch (e) { |
| 150 |
return false; |
| 151 |
} |
| 152 |
|
| 153 |
if (!el.length) { |
| 154 |
return false; |
| 155 |
} |
| 156 |
|
| 157 |
var placeholder = $('<span style="display:none !important" class="lity-inline-placeholder"/>'); |
| 158 |
|
| 159 |
return el |
| 160 |
.after(placeholder) |
| 161 |
.on('lity:ready', function(e, instance) { |
| 162 |
instance.one('lity:remove', function() { |
| 163 |
placeholder |
| 164 |
.before(el.addClass('lity-hide')) |
| 165 |
.remove() |
| 166 |
; |
| 167 |
}); |
| 168 |
}) |
| 169 |
; |
| 170 |
} |
| 171 |
|
| 172 |
function iframeHandler(target) { |
| 173 |
var matches, url = target; |
| 174 |
|
| 175 |
matches = _youtubeRegex.exec(target); |
| 176 |
|
| 177 |
if (matches) { |
| 178 |
url = appendQueryParams( |
| 179 |
'https://www.youtube' + (matches[2] || '') + '.com/embed/' + matches[4], |
| 180 |
$.extend( |
| 181 |
{ |
| 182 |
autoplay: 1 |
| 183 |
}, |
| 184 |
parseQueryParams(matches[5] || '') |
| 185 |
) |
| 186 |
); |
| 187 |
} |
| 188 |
|
| 189 |
matches = _vimeoRegex.exec(target); |
| 190 |
|
| 191 |
if (matches) { |
| 192 |
url = appendQueryParams( |
| 193 |
'https://player.vimeo.com/video/' + matches[3], |
| 194 |
$.extend( |
| 195 |
{ |
| 196 |
autoplay: 1 |
| 197 |
}, |
| 198 |
parseQueryParams(matches[4] || '') |
| 199 |
) |
| 200 |
); |
| 201 |
} |
| 202 |
|
| 203 |
matches = _googlemapsRegex.exec(target); |
| 204 |
|
| 205 |
if (matches) { |
| 206 |
url = appendQueryParams( |
| 207 |
'https://www.google.' + matches[3] + '/maps?' + matches[6], |
| 208 |
{ |
| 209 |
output: matches[6].indexOf('layer=c') > 0 ? 'svembed' : 'embed' |
| 210 |
} |
| 211 |
); |
| 212 |
} |
| 213 |
|
| 214 |
return '<div class="lity-iframe-container"><iframe frameborder="0" allowfullscreen src="' + url + '"></iframe></div>'; |
| 215 |
} |
| 216 |
|
| 217 |
function lity(options) { |
| 218 |
var _options = {}, |
| 219 |
_handlers = {}, |
| 220 |
_instance, |
| 221 |
_content, |
| 222 |
_ready = $.Deferred().resolve(); |
| 223 |
|
| 224 |
function keyup(e) { |
| 225 |
if (e.keyCode === 27) { |
| 226 |
close(); |
| 227 |
} |
| 228 |
} |
| 229 |
|
| 230 |
function resize() { |
| 231 |
var height = document.documentElement.clientHeight ? document.documentElement.clientHeight : Math.round(_win.height()); |
| 232 |
|
| 233 |
_content |
| 234 |
.css('max-height', Math.floor(height) + 'px') |
| 235 |
.trigger('lity:resize', [_instance]) |
| 236 |
; |
| 237 |
} |
| 238 |
|
| 239 |
function ready(el, content) { |
| 240 |
if (!_instance) { |
| 241 |
return; |
| 242 |
} |
| 243 |
|
| 244 |
_content = $(content); |
| 245 |
|
| 246 |
_win.on('resize', resize); |
| 247 |
resize(); |
| 248 |
|
| 249 |
_instance |
| 250 |
.find('.lity-loader') |
| 251 |
.each(function() { |
| 252 |
var el = $(this); |
| 253 |
transitionEnd(el).always(function() { |
| 254 |
el.remove(); |
| 255 |
}); |
| 256 |
}) |
| 257 |
; |
| 258 |
|
| 259 |
_instance |
| 260 |
.removeClass('lity-loading') |
| 261 |
.find('.lity-content') |
| 262 |
.empty() |
| 263 |
.append(_content) |
| 264 |
; |
| 265 |
|
| 266 |
_content |
| 267 |
.removeClass('lity-hide') |
| 268 |
.trigger('lity:ready', [_instance, el]) |
| 269 |
; |
| 270 |
|
| 271 |
_ready.resolve(); |
| 272 |
} |
| 273 |
|
| 274 |
function init(handler, content, options, el) { |
| 275 |
_ready = $.Deferred(); |
| 276 |
|
| 277 |
_instanceCount++; |
| 278 |
globalToggle(); |
| 279 |
|
| 280 |
_instance = $(options.template) |
| 281 |
.addClass('lity-loading') |
| 282 |
.appendTo('body'); |
| 283 |
|
| 284 |
if (!!options.esc) { |
| 285 |
_win.on('keyup', keyup); |
| 286 |
} |
| 287 |
|
| 288 |
setTimeout(function() { |
| 289 |
_instance |
| 290 |
.addClass('lity-opened lity-' + handler) |
| 291 |
.on('click', '[data-lity-close]', function(e) { |
| 292 |
if ($(e.target).is('[data-lity-close]')) { |
| 293 |
close(); |
| 294 |
} |
| 295 |
}) |
| 296 |
.trigger('lity:open', [_instance, el]) |
| 297 |
; |
| 298 |
|
| 299 |
$.when(content).always($.proxy(ready, null, el)); |
| 300 |
}, 0); |
| 301 |
} |
| 302 |
|
| 303 |
function open(target, options, el) { |
| 304 |
var handler, content, handlers = $.extend({}, _defaultHandlers, _handlers); |
| 305 |
|
| 306 |
options = $.extend( |
| 307 |
{}, |
| 308 |
_defaultOptions, |
| 309 |
_options, |
| 310 |
options |
| 311 |
); |
| 312 |
|
| 313 |
if (options.handler && handlers[options.handler]) { |
| 314 |
content = handlers[options.handler](target, popup); |
| 315 |
handler = options.handler; |
| 316 |
} else { |
| 317 |
var lateHandlers = {}; |
| 318 |
|
| 319 |
// Run inline and iframe handlers after all other handlers |
| 320 |
$.each(['inline', 'iframe'], function(i, name) { |
| 321 |
if (handlers[name]) { |
| 322 |
lateHandlers[name] = handlers[name]; |
| 323 |
} |
| 324 |
|
| 325 |
delete handlers[name]; |
| 326 |
}); |
| 327 |
|
| 328 |
var call = function(name, callback) { |
| 329 |
// Handler might be "removed" by setting callback to null |
| 330 |
if (!callback) { |
| 331 |
return true; |
| 332 |
} |
| 333 |
|
| 334 |
content = callback(target, popup); |
| 335 |
|
| 336 |
if (!!content) { |
| 337 |
handler = name; |
| 338 |
return false; |
| 339 |
} |
| 340 |
}; |
| 341 |
|
| 342 |
$.each(handlers, call); |
| 343 |
|
| 344 |
if (!handler) { |
| 345 |
$.each(lateHandlers, call); |
| 346 |
} |
| 347 |
} |
| 348 |
|
| 349 |
if (content) { |
| 350 |
$.when(close()).done($.proxy(init, null, handler, content, options, el)); |
| 351 |
} |
| 352 |
|
| 353 |
return !!content; |
| 354 |
} |
| 355 |
|
| 356 |
function close() { |
| 357 |
if (!_instance) { |
| 358 |
return; |
| 359 |
} |
| 360 |
|
| 361 |
var deferred = $.Deferred(); |
| 362 |
|
| 363 |
_ready.done(function() { |
| 364 |
_instanceCount--; |
| 365 |
globalToggle(); |
| 366 |
|
| 367 |
_win |
| 368 |
.off('resize', resize) |
| 369 |
.off('keyup', keyup) |
| 370 |
; |
| 371 |
|
| 372 |
_content.trigger('lity:close', [_instance]); |
| 373 |
|
| 374 |
_instance |
| 375 |
.removeClass('lity-opened') |
| 376 |
.addClass('lity-closed') |
| 377 |
; |
| 378 |
|
| 379 |
var instance = _instance, content = _content; |
| 380 |
_instance = null; |
| 381 |
_content = null; |
| 382 |
|
| 383 |
transitionEnd(content.add(instance)).always(function() { |
| 384 |
content.trigger('lity:remove', [instance]); |
| 385 |
instance.remove(); |
| 386 |
deferred.resolve(); |
| 387 |
}); |
| 388 |
}); |
| 389 |
|
| 390 |
return deferred.promise(); |
| 391 |
} |
| 392 |
|
| 393 |
function popup(event) { |
| 394 |
// If not an event, act as alias of popup.open |
| 395 |
if (!event.preventDefault) { |
| 396 |
return popup.open(event); |
| 397 |
} |
| 398 |
|
| 399 |
var el = $(this); |
| 400 |
var target = el.data('lity-target') || el.attr('href') || el.attr('src'); |
| 401 |
|
| 402 |
if (!target) { |
| 403 |
return; |
| 404 |
} |
| 405 |
|
| 406 |
var options = el.data('lity-options') || el.data('lity'); |
| 407 |
|
| 408 |
if (open(target, options, el)) { |
| 409 |
el.blur(); |
| 410 |
event.preventDefault(); |
| 411 |
} |
| 412 |
} |
| 413 |
|
| 414 |
popup.handlers = $.proxy(settings, popup, _handlers); |
| 415 |
popup.options = $.proxy(settings, popup, _options); |
| 416 |
|
| 417 |
popup.open = function(target, options, el) { |
| 418 |
open(target, options, el); |
| 419 |
return popup; |
| 420 |
}; |
| 421 |
|
| 422 |
popup.close = function() { |
| 423 |
close(); |
| 424 |
return popup; |
| 425 |
}; |
| 426 |
|
| 427 |
return popup.options(options); |
| 428 |
} |
| 429 |
|
| 430 |
lity.version = '1.6.6'; |
| 431 |
lity.handlers = $.proxy(settings, lity, _defaultHandlers); |
| 432 |
lity.options = $.proxy(settings, lity, _defaultOptions); |
| 433 |
|
| 434 |
$(document).on('click', '[data-lity]', lity()); |
| 435 |
|
| 436 |
return lity; |
| 437 |
})); |
| 438 |
|