PageSourceSearch

https://www.noinoi.kids/bundles/trhtechnishopd1atheme/jquery/spritespin.js?1791467626

js noinoi.kids collected 2026-10-09 22:54:22 UTC 76,875 bytes, 2,478 lines download raw bytes

vendor: 76,875 bytes, lines 1-2478
1(function (global, factory) {
2	typeof exports === 'object' && typeof module !== 'undefined' ? factory(exports) :
3	typeof define === 'function' && define.amd ? define(['exports'], factory) :
4	(factory((global.SpriteSpin = {})));
5}(this, (function (exports) { 'use strict';
6
7/**
8 * @internal
9 */
10var Api = /** @class */ (function () {
11    function Api(data) {
12        this.data = data;
13    }
14    return Api;
15}());
16/**
17 * Adds methods to the SpriteSpin api
18 *
19 * @public
20 */
21function extendApi(methods) {
22    var api = Api.prototype;
23    for (var key in methods) {
24        if (methods.hasOwnProperty(key)) {
25            if (api[key]) {
26                throw new Error('API method is already defined: ' + key);
27            }
28            else {
29                api[key] = methods[key];
30            }
31        }
32    }
33    return api;
34}
35
36var $$1 = window.jQuery || window.$;
37
38function getCursorPosition(event) {
39    var touches = event.touches;
40    var source = event;
41    // jQuery Event normalization does not preserve the 'event.touches'
42    // try to grab touches from the original event
43    if (event.touches === undefined && event.originalEvent !== undefined) {
44        touches = event.originalEvent.touches;
45    }
46    // get current touch or mouse position
47    if (touches !== undefined && touches.length > 0) {
48        source = touches[0];
49    }
50    return {
51        x: source.clientX || 0,
52        y: source.clientY || 0
53    };
54}
55
56var canvas;
57var context;
58function detectionContext() {
59    if (context) {
60        return context;
61    }
62    if (!canvas) {
63        canvas = document.createElement('canvas');
64    }
65    if (!canvas || !canvas.getContext) {
66        return null;
67    }
68    context = canvas.getContext('2d');
69    return context;
70}
71/**
72 * Idea taken from https://github.com/stomita/ios-imagefile-megapixel
73 * Detects whether the image has been sub sampled by the browser and does not have its original dimensions.
74 * This method unfortunately does not work for images that have transparent background.
75 */
76function detectSubsampling(img, width, height) {
77    if (!detectionContext()) {
78        return false;
79    }
80    // sub sampling happens on images above 1 megapixel
81    if (width * height <= 1024 * 1024) {
82        return false;
83    }
84    // set canvas to 1x1 pixel size and fill it with magenta color
85    canvas.width = canvas.height = 1;
86    context.fillStyle = '#FF00FF';
87    context.fillRect(0, 0, 1, 1);
88    // render the image with a negative offset to the left so that it would
89    // fill the canvas pixel with the top right pixel of the image.
90    context.drawImage(img, -width + 1, 0);
91    // check color value to confirm image is covering edge pixel or not.
92    // if color still magenta, the image is assumed to be sub sampled.
93    try {
94        var dat = context.getImageData(0, 0, 1, 1).data;
95        return (dat[0] === 255) && (dat[1] === 0) && (dat[2] === 255);
96    }
97    catch (err) {
98        // avoids cross origin exception for chrome when code runs without a server
99        return false;
100    }
101}
102
103/**
104 *
105 */
106function getOuterSize(data) {
107    var width = Math.floor(data.width || data.frameWidth || data.target.innerWidth());
108    var height = Math.floor(data.height || data.frameHeight || data.target.innerHeight());
109    return {
110        aspect: width / height,
111        height: height,
112        width: width
113    };
114}
115function getComputedSize(data) {
116    var size = getOuterSize(data);
117    if (typeof window.getComputedStyle !== 'function') {
118        return size;
119    }
120    var style = window.getComputedStyle(data.target[0]);
121    if (!style.width) {
122        return size;
123    }
124    size.width = Math.floor(Number(style.width.replace('px', '')));
125    size.height = Math.floor(size.width / size.aspect);
126    return size;
127}
128/**
129 *
130 */
131function getInnerSize(data) {
132    var width = Math.floor(data.frameWidth || data.width || data.target.innerWidth());
133    var height = Math.floor(data.frameHeight || data.height || data.target.innerHeight());
134    return {
135        aspect: width / height,
136        height: height,
137        width: width
138    };
139}
140/**
141 *
142 */
143function getInnerLayout(mode, inner, outer) {
144    // get mode
145    var isFit = mode === 'fit';
146    var isFill = mode === 'fill';
147    var isMatch = mode === 'stretch';
148    // resulting layout
149    var layout = {
150        width: '100%',
151        height: '100%',
152        top: 0,
153        left: 0,
154        bottom: 0,
155        right: 0,
156        position: 'absolute',
157        overflow: 'hidden'
158    };
159    // no calculation here
160    if (!mode || isMatch) {
161        return layout;
162    }
163    // get size and aspect
164    var aspectIsGreater = inner.aspect >= outer.aspect;
165    // mode == original
166    var width = inner.width;
167    var height = inner.height;
168    // keep aspect ratio but fit/fill into container
169    if (isFit && aspectIsGreater || isFill && !aspectIsGreater) {
170        width = outer.width;
171        height = outer.width / inner.aspect;
172    }
173    if (isFill && aspectIsGreater || isFit && !aspectIsGreater) {
174        height = outer.height;
175        width = outer.height * inner.aspect;
176    }
177    // floor the numbers
178    width = Math.floor(width);
179    height = Math.floor(height);
180    // position in center
181    layout.width = width;
182    layout.height = height;
183    layout.top = Math.floor((outer.height - height) / 2);
184    layout.left = Math.floor((outer.width - width) / 2);
185    layout.right = layout.left;
186    layout.bottom = layout.top;
187    return layout;
188}
189
190var img;
191/**
192 * gets the original width and height of an image element
193 */
194function naturalSize(image) {
195    // for browsers that support naturalWidth and naturalHeight properties
196    if (image.naturalWidth) {
197        return {
198            height: image.naturalHeight,
199            width: image.naturalWidth
200        };
201    }
202    // browsers that do not support naturalWidth and naturalHeight properties have to fall back to the width and
203    // height properties. However, the image might have a css style applied so width and height would return the
204    // css size. To avoid that create a new Image object that is free of css rules and grab width and height
205    // properties
206    //
207    // assume that the src has already been downloaded, so no onload callback is needed.
208    img = img || new Image();
209    img.crossOrigin = image.crossOrigin;
210    img.src = image.src;
211    return {
212        height: img.height,
213        width: img.width
214    };
215}
216
217/**
218 * Measures the image frames that are used in the given data object
219 */
220function measure(images, options) {
221    if (images.length === 1) {
222        return [measureSheet(images[0], options)];
223    }
224    else if (options.framesX && options.framesY) {
225        return measureMutipleSheets(images, options);
226    }
227    else {
228        return measureFrames(images, options);
229    }
230}
231function measureSheet(image, options) {
232    var result = { id: 0, sprites: [] };
233    measureImage(image, options, result);
234    var frames = options.frames;
235    var framesX = Number(options.framesX) || frames;
236    var framesY = Math.ceil(frames / framesX);
237    var frameWidth = Math.floor(result.width / framesX);
238    var frameHeight = Math.floor(result.height / framesY);
239    var divisor = result.isSubsampled ? 2 : 1;
240    for (var i = 0; i < frames; i++) {
241        var x = (i % framesX) * frameWidth;
242        var y = Math.floor(i / framesX) * frameHeight;
243        result.sprites.push({
244            id: i,
245            x: x, y: y,
246            width: frameWidth,
247            height: frameHeight,
248            sampledX: x / divisor,
249            sampledY: y / divisor,
250            sampledWidth: frameWidth / divisor,
251            sampledHeight: frameHeight / divisor
252        });
253    }
254    return result;
255}
256function measureFrames(images, options) {
257    var result = [];
258    for (var id = 0; id < images.length; id++) {
259        // TODO: optimize
260        // don't measure images with same size twice
261        var sheet = measureSheet(images[id], { frames: 1, framesX: 1, detectSubsampling: options.detectSubsampling });
262        sheet.id = id;
263        result.push(sheet);
264    }
265    return result;
266}
267function measureMutipleSheets(images, options) {
268    var result = [];
269    for (var id = 0; id < images.length; id++) {
270        // TODO: optimize
271        // don't measure images with same size twice
272        var sheet = measureSheet(images[id], {
273            frames: undefined,
274            framesX: options.framesX,
275            framesY: options.framesY,
276            detectSubsampling: options.detectSubsampling
277        });
278        sheet.id = id;
279        result.push(sheet);
280    }
281    return result;
282}
283function measureImage(image, options, result) {
284    var size = naturalSize(image);
285    result.isSubsampled = options.detectSubsampling && detectSubsampling(image, size.width, size.height);
286    result.width = size.width;
287    result.height = size.height;
288    result.sampledWidth = size.width / (result.isSubsampled ? 2 : 1);
289    result.sampledHeight = size.height / (result.isSubsampled ? 2 : 1);
290    return result;
291}
292function findSpecs(metrics, frames, frame, lane) {
293    var spriteId = lane * frames + frame;
294    var sheetId = 0;
295    var sprite = null;
296    var sheet = null;
297    while (true) {
298        sheet = metrics[sheetId];
299        if (!sheet) {
300            break;
301        }
302        if (spriteId >= sheet.sprites.length) {
303            spriteId -= sheet.sprites.length;
304            sheetId++;
305            continue;
306        }
307        sprite = sheet.sprites[spriteId];
308        break;
309    }
310    return { sprite: sprite, sheet: sheet };
311}
312
313function indexOf(element, arr) {
314    for (var i = 0; i < arr.length; i++) {
315        if (arr[i] === element) {
316            return i;
317        }
318    }
319}
320function noop() {
321    //
322}
323function preload(opts) {
324    var src;
325    var input = opts.source;
326    src = typeof input === 'string' ? [input] : input;
327    // const src: string[] =  ? [opts.source] : opts.source
328    var images = [];
329    var targetCount = (opts.preloadCount || src.length);
330    var onInitiated = opts.initiated || noop;
331    var onProgress = opts.progress || noop;
332    var onComplete = opts.complete || noop;
333    var count = 0;
334    var completed = false;
335    var firstLoaded = false;
336    var tick = function () {
337        count += 1;
338        onProgress({
339            index: indexOf(this, images),
340            loaded: count,
341            total: src.length,
342            percent: Math.round((count / src.length) * 100)
343        });
344        firstLoaded = firstLoaded || (this === images[0]);
345        if (firstLoaded && !completed && (count >= targetCount)) {
346            completed = true;
347            onComplete(images);
348        }
349    };
350    for (var _i = 0, src_1 = src; _i < src_1.length; _i++) {
351        var url = src_1[_i];
352        var img = new Image();
353        // push result
354        images.push(img);
355        // https://developer.mozilla.org/en-US/docs/Web/HTML/CORS_enabled_image
356        img.crossOrigin = opts.crossOrigin;
357        // bind logic, don't care about abort/errors
358        img.onload = img.onabort = img.onerror = tick;
359        // begin load
360        img.src = url;
361    }
362    onInitiated(images);
363}
364
365function padNumber(num, length, pad) {
366    var result = String(num);
367    while (result.length < length) {
368        result = String(pad) + result;
369    }
370    return result;
371}
372/**
373 * Generates an array of source strings
374 *
375 * @remarks
376 * Takes a template string and generates an array of strings by interpolating {lane} and {frame} placeholders.
377 *
378 * ```
379 * sourceArray('http://example.com/image_{frame}.jpg, { frame: [1, 3], digits: 2 })
380 * // gives:
381 * // [ 'http://example.com/image_01.jpg', 'http://example.com/image_02.jpg', 'http://example.com/image_03.jpg' ]
382 *
383 * sourceArray('http://example.com/image_FRAME.jpg, { frame: [1, 3], digits: 2, framePlacer: 'FRAME' })
384 * // gives:
385 * // [ 'http://example.com/image_01.jpg', 'http://example.com/image_02.jpg', 'http://example.com/image_03.jpg' ]
386 * ```
387 *
388 * @param template - The template string
389 * @param opts - Interpolation options
390 *
391 * @public
392 */
393function sourceArray(template, opts) {
394    var digits = opts.digits || 2;
395    var lPlacer = opts.lanePlacer || '{lane}';
396    var fPlacer = opts.framePlacer || '{frame}';
397    var fStart = 0;
398    var fEnd = 0;
399    if (opts.frame) {
400        fStart = opts.frame[0];
401        fEnd = opts.frame[1];
402    }
403    var lStart = 0;
404    var lEnd = 0;
405    if (opts.lane) {
406        lStart = opts.lane[0];
407        lEnd = opts.lane[1];
408    }
409    var result = [];
410    for (var lane = lStart; lane <= lEnd; lane += 1) {
411        for (var frame = fStart; frame <= fEnd; frame += 1) {
412            result.push(template
413                .replace(lPlacer, padNumber(lane, digits, '0'))
414                .replace(fPlacer, padNumber(frame, digits, '0')));
415        }
416    }
417    return result;
418}
419
420/**
421 * The namespace that is used to bind functions to DOM events and store the data object
422 */
423var namespace = 'spritespin';
424/**
425 * Event names that are recognized by SpriteSpin. A module can implement any of these and they will be bound
426 * to the target element on which the plugin is called.
427 */
428var eventNames = [
429    'mousedown',
430    'mousemove',
431    'mouseup',
432    'mouseenter',
433    'mouseover',
434    'mouseleave',
435    'mousewheel',
436    'wheel',
437    'click',
438    'dblclick',
439    'touchstart',
440    'touchmove',
441    'touchend',
442    'touchcancel',
443    'selectstart',
444    'gesturestart',
445    'gesturechange',
446    'gestureend'
447];
448/**
449 *
450 */
451var callbackNames = [
452    'onInit',
453    'onProgress',
454    'onLoad',
455    'onFrameChanged',
456    'onFrame',
457    'onDraw',
458    'onComplete',
459    'onDestroy'
460];
461/**
462 * Names of events for that the default behavior should be prevented.
463 */
464var eventsToPrevent = [
465    'dragstart'
466];
467/**
468 * Default set of SpriteSpin options. This also represents the majority of data attributes that are used during the
469 * lifetime of a SpriteSpin instance. The data is stored inside the target DOM element on which the plugin is called.
470 */
471var defaults = {
472    source: undefined,
473    width: undefined,
474    height: undefined,
475    frames: undefined,
476    framesX: undefined,
477    lanes: 1,
478    sizeMode: undefined,
479    renderer: 'canvas',
480    lane: 0,
481    frame: 0,
482    frameTime: 40,
483    animate: true,
484    retainAnimate: false,
485    reverse: false,
486    loop: true,
487    stopFrame: 0,
488    wrap: true,
489    wrapLane: false,
490    sense: 1,
491    senseLane: undefined,
492    orientation: 'horizontal',
493    detectSubsampling: true,
494    preloadCount: undefined,
495    touchScrollTimer: [200, 1500],
496    responsive: undefined,
497    plugins: undefined
498};
499
500function noop$1() {
501    // noop
502}
503function wrapConsole(type) {
504    return console && console[type] ? function () {
505        var args = [];
506        for (var _i = 0; _i < arguments.length; _i++) {
507            args[_i] = arguments[_i];
508        }
509        return console.log.apply(console, args);
510    } : noop$1;
511}
512var log = wrapConsole('log');
513var warn = wrapConsole('warn');
514var error = wrapConsole('error');
515function toArray(value) {
516    return Array.isArray(value) ? value : [value];
517}
518/**
519 * clamps the given value by the given min and max values
520 */
521function clamp(value, min, max) {
522    return (value > max ? max : (value < min ? min : value));
523}
524/**
525 *
526 */
527function wrap(value, min, max, size) {
528    while (value > max) {
529        value -= size;
530    }
531    while (value < min) {
532        value += size;
533    }
534    return value;
535}
536/**
537 * prevents default action on the given event
538 */
539function prevent(e) {
540    e.preventDefault();
541    return false;
542}
543/**
544 * Binds on the given target and event the given function.
545 * The SpriteSpin namespace is attached to the event name
546 */
547function bind(target, event, func) {
548    if (func) {
549        target.bind(event + '.' + namespace, function (e) {
550            func.apply(target, [e, target.spritespin('data')]);
551        });
552    }
553}
554/**
555 * Unbinds all SpriteSpin events from given target element
556 */
557function unbind(target) {
558    target.unbind('.' + namespace);
559}
560/**
561 * Checks if given object is a function
562 */
563function isFunction(fn) {
564    return typeof fn === 'function';
565}
566function pixelRatio(context) {
567    var devicePixelRatio = window.devicePixelRatio || 1;
568    var backingStoreRatio = context.webkitBackingStorePixelRatio ||
569        context.mozBackingStorePixelRatio ||
570        context.msBackingStorePixelRatio ||
571        context.oBackingStorePixelRatio ||
572        context.backingStorePixelRatio || 1;
573    return devicePixelRatio / backingStoreRatio;
574}
575
576/**
577 * Applies css attributes to layout the SpriteSpin containers.
578 *
579 * @internal
580 */
581function applyLayout(data) {
582    // disable selection
583    data.target
584        .attr('unselectable', 'on')
585        .css({
586        width: '',
587        height: '',
588        '-ms-user-select': 'none',
589        '-moz-user-select': 'none',
590        '-khtml-user-select': 'none',
591        '-webkit-user-select': 'none',
592        'user-select': 'none'
593    });
594    var size = data.responsive ? getComputedSize(data) : getOuterSize(data);
595    var layout = getInnerLayout(data.sizeMode, getInnerSize(data), size);
596    // apply layout on target
597    data.target.css({
598        width: size.width,
599        height: size.height,
600        position: 'relative',
601        overflow: 'hidden'
602    });
603    // apply layout on stage
604    data.stage
605        .css(layout)
606        .hide();
607    if (!data.canvas) {
608        return;
609    }
610    // apply layout on canvas
611    data.canvas.css(layout).hide();
612    // apply pixel ratio on canvas
613    data.canvasRatio = data.canvasRatio || pixelRatio(data.context);
614    if (typeof layout.width === 'number' && typeof layout.height === 'number') {
615        data.canvas[0].width = (layout.width * data.canvasRatio) || size.width;
616        data.canvas[0].height = (layout.height * data.canvasRatio) || size.height;
617    }
618    else {
619        data.canvas[0].width = (size.width * data.canvasRatio);
620        data.canvas[0].height = (size.height * data.canvasRatio);
621    }
622    // width and height must be set before calling scale
623    data.context.scale(data.canvasRatio, data.canvasRatio);
624}
625
626/**
627 * Gets a state object by name.
628 * @internal
629 * @param data - The SpriteSpin instance data
630 * @param name - The name of the state object
631 */
632function getState(data, name) {
633    data.state = data.state || {};
634    data.state[name] = data.state[name] || {};
635    return data.state[name];
636}
637/**
638 * Gets a plugin state object by name.
639 *
640 * @remarks
641 * Plugins should use this method to get or create a state object where they can
642 * store any instance variables.
643 *
644 * @public
645 * @param data - The SpriteSpin instance data
646 * @param name - The name of the plugin
647 */
648function getPluginState(data, name) {
649    var state = getState(data, 'plugin');
650    state[name] = state[name] || {};
651    return state[name];
652}
653/**
654 * Checks whether a flag is set. See {@link flag}.
655 *
656 * @public
657 * @param data - The SpriteSpin instance data
658 * @param key - The name of the flag
659 */
660function is(data, key) {
661    return !!getState(data, 'flags')[key];
662}
663/**
664 * Sets a flag value. See {@link is}.
665 *
666 * @public
667 * @param data - The SpriteSpin instance data
668 * @param key - The name of the flag
669 * @param value - The value to set
670 */
671function flag(data, key, value) {
672    getState(data, 'flags')[key] = !!value;
673}
674
675/**
676 * Gets the playback state
677 *
678 * @public
679 * @param data - The SpriteSpin instance data
680 */
681function getPlaybackState(data) {
682    return getState(data, 'playback');
683}
684function updateLane(data, lane) {
685    data.lane = data.wrapLane
686        ? wrap(lane, 0, data.lanes - 1, data.lanes)
687        : clamp(lane, 0, data.lanes - 1);
688}
689function updateAnimationFrame(data) {
690    data.frame += (data.reverse ? -1 : 1);
691    // wrap the frame value to fit in range [0, data.frames)
692    data.frame = wrap(data.frame, 0, data.frames - 1, data.frames);
693    // stop animation if loop is disabled and the stopFrame is reached
694    if (!data.loop && (data.frame === data.stopFrame)) {
695        stopAnimation(data);
696    }
697}
698function updateInputFrame(data, frame) {
699    data.frame = Number(frame);
700    data.frame = data.wrap
701        ? wrap(data.frame, 0, data.frames - 1, data.frames)
702        : clamp(data.frame, 0, data.frames - 1);
703}
704function updateAnimation(data) {
705    var state = getPlaybackState(data);
706    if (state.handler) {
707        updateBefore(data);
708        updateAnimationFrame(data);
709        updateAfter(data);
710    }
711}
712function updateBefore(data) {
713    var state = getPlaybackState(data);
714    state.lastFrame = data.frame;
715    state.lastLane = data.lane;
716}
717function updateAfter(data) {
718    var state = getPlaybackState(data);
719    if (state.lastFrame !== data.frame || state.lastLane !== data.lane) {
720        data.target.trigger('onFrameChanged.' + namespace, data);
721    }
722    data.target.trigger('onFrame.' + namespace, data);
723    data.target.trigger('onDraw.' + namespace, data);
724}
725/**
726 * Updates the frame or lane number of the SpriteSpin data.
727 *
728 * @public
729 * @param data - The SpriteSpin instance data
730 * @param frame - The frame number to set
731 * @param lane - The lane number to set
732 */
733function updateFrame(data, frame, lane) {
734    updateBefore(data);
735    if (frame != null) {
736        updateInputFrame(data, frame);
737    }
738    if (lane != null) {
739        updateLane(data, lane);
740    }
741    updateAfter(data);
742}
743/**
744 * Stops the running animation.
745 *
746 * @public
747 * @param data - The SpriteSpin instance data
748 */
749function stopAnimation(data) {
750    data.animate = false;
751    var state = getPlaybackState(data);
752    if (state.handler != null) {
753        window.clearInterval(state.handler);
754        state.handler = null;
755    }
756}
757/**
758 * Starts animation playback if needed.
759 *
760 * @remarks
761 * Starts animation playback if `animate` property is `true` and the animation is not yet running.
762 *
763 * @public
764 * @param data - The SpriteSpin instance data
765 */
766function applyAnimation(data) {
767    var state = getPlaybackState(data);
768    if (state.handler && (!data.animate || state.frameTime !== data.frameTime)) {
769        stopAnimation(data);
770    }
771    if (data.animate && !state.handler) {
772        state.frameTime = data.frameTime;
773        state.handler = window.setInterval(function () { return updateAnimation(data); }, state.frameTime);
774    }
775}
776/**
777 * Starts the animation playback
778 *
779 * @remarks
780 * Starts the animation playback and also sets the `animate` property to `true`
781 *
782 * @public
783 * @param data - The SpriteSpin instance data
784 */
785function startAnimation(data) {
786    data.animate = true;
787    applyAnimation(data);
788}
789
790var plugins = {};
791/**
792 * Registers a plugin.
793 *
794 * @remarks
795 * Use this to add custom Rendering or Updating modules that can be addressed with the 'module' option.
796 *
797 * @public
798 * @param name - The name of the plugin
799 * @param plugin - The plugin implementation
800 */
801function registerPlugin(name, plugin) {
802    if (plugins[name]) {
803        error("Plugin name \"" + name + "\" is already taken");
804        return;
805    }
806    plugin = plugin || {};
807    plugins[name] = plugin;
808    return plugin;
809}
810/**
811 * Registers a plugin.
812 *
813 * @public
814 * @deprecated Use {@link registerPlugin} instead
815 * @param name - The name of the plugin
816 * @param plugin - The plugin implementation
817 */
818function registerModule(name, plugin) {
819    warn('"registerModule" is deprecated, use "registerPlugin" instead');
820    registerPlugin(name, plugin);
821}
822/**
823 * Gets an active plugin by name
824 *
825 * @internal
826 * @param name - The name of the plugin
827 */
828function getPlugin(name) {
829    return plugins[name];
830}
831/**
832 * Replaces module names on given SpriteSpin data and replaces them with actual implementations.
833 * @internal
834 */
835function applyPlugins(data) {
836    fixPlugins(data);
837    for (var i = 0; i < data.plugins.length; i += 1) {
838        var name_1 = data.plugins[i];
839        if (typeof name_1 !== 'string') {
840            continue;
841        }
842        var plugin = getPlugin(name_1);
843        if (!plugin) {
844            error('No plugin found with name ' + name_1);
845            continue;
846        }
847        data.plugins[i] = plugin;
848    }
849}
850function fixPlugins(data) {
851    // tslint:disable no-string-literal
852    if (data['mods']) {
853        warn('"mods" option is deprecated, use "plugins" instead');
854        data.plugins = data['mods'];
855        delete data['mods'];
856    }
857    if (data['behavior']) {
858        warn('"behavior" option is deprecated, use "plugins" instead');
859        data.plugins.push(data['behavior']);
860        delete data['behavior'];
861    }
862    if (data['module']) {
863        warn('"module" option is deprecated, use "plugins" instead');
864        data.plugins.push(data['module']);
865        delete data['module'];
866    }
867}
868
869var $$2 = $$1;
870var counter = 0;
871/**
872 * Collection of all SpriteSpin instances
873 */
874var instances = {};
875function pushInstance(data) {
876    counter += 1;
877    data.id = String(counter);
878    instances[data.id] = data;
879}
880function popInstance(data) {
881    delete instances[data.id];
882}
883function eachInstance(cb) {
884    for (var id in instances) {
885        if (instances.hasOwnProperty(id)) {
886            cb(instances[id]);
887        }
888    }
889}
890var lazyinit = function () {
891    // replace function with a noop
892    // this logic must run only once
893    lazyinit = function () { };
894    function onEvent(eventName, e) {
895        eachInstance(function (data) {
896            for (var _i = 0, _a = data.plugins; _i < _a.length; _i++) {
897                var module_1 = _a[_i];
898                if (typeof module_1[eventName] === 'function') {
899                    module_1[eventName].apply(data.target, [e, data]);
900                }
901            }
902        });
903    }
904    function onResize() {
905        eachInstance(function (data) {
906            if (data.responsive) {
907                boot(data);
908            }
909        });
910    }
911    var _loop_1 = function (eventName) {
912        $$2(window.document).bind(eventName + '.' + namespace, function (e) {
913            onEvent('document' + eventName, e);
914        });
915    };
916    for (var _i = 0, eventNames_1 = eventNames; _i < eventNames_1.length; _i++) {
917        var eventName = eventNames_1[_i];
918        _loop_1(eventName);
919    }
920    var resizeTimeout = null;
921    $$2(window).on('resize', function () {
922        window.clearTimeout(resizeTimeout);
923        resizeTimeout = window.setTimeout(onResize, 100);
924    });
925};
926/**
927 * (re)binds all spritespin events on the target element
928 *
929 * @internal
930 */
931function applyEvents(data) {
932    var target = data.target;
933    // Clear all SpriteSpin events on the target element
934    unbind(target);
935    // disable all default browser behavior on the following events
936    // mainly prevents image drag operation
937    for (var _i = 0, eventsToPrevent_1 = eventsToPrevent; _i < eventsToPrevent_1.length; _i++) {
938        var eName = eventsToPrevent_1[_i];
939        bind(target, eName, prevent);
940    }
941    // Bind module functions to SpriteSpin events
942    for (var _a = 0, _b = data.plugins; _a < _b.length; _a++) {
943        var plugin = _b[_a];
944        for (var _c = 0, eventNames_2 = eventNames; _c < eventNames_2.length; _c++) {
945            var eName = eventNames_2[_c];
946            bind(target, eName, plugin[eName]);
947        }
948        for (var _d = 0, callbackNames_1 = callbackNames; _d < callbackNames_1.length; _d++) {
949            var eName = callbackNames_1[_d];
950            bind(target, eName, plugin[eName]);
951        }
952    }
953    // bind auto start function to load event.
954    bind(target, 'onLoad', function (e, d) {
955        applyAnimation(d);
956    });
957    // bind all user events that have been passed on initialization
958    for (var _e = 0, callbackNames_2 = callbackNames; _e < callbackNames_2.length; _e++) {
959        var eName = callbackNames_2[_e];
960        bind(target, eName, data[eName]);
961    }
962}
963function applyMetrics(data) {
964    if (!data.images) {
965        data.metrics = [];
966    }
967    data.metrics = measure(data.images, data);
968    var spec = findSpecs(data.metrics, data.frames, 0, 0);
969    if (spec.sprite) {
970        // TODO: try to remove frameWidth/frameHeight
971        data.frameWidth = spec.sprite.width;
972        data.frameHeight = spec.sprite.height;
973    }
974}
975/**
976 * Runs the boot process.
977 *
978 * @remarks
979 * (re)initializes plugins, (re)initializes the layout, (re)binds events and loads source images.
980 *
981 * @internal
982 */
983function boot(data) {
984    applyPlugins(data);
985    applyEvents(data);
986    applyLayout(data);
987    data.source = toArray(data.source);
988    data.loading = true;
989    data.target
990        .addClass('loading')
991        .trigger('onInit.' + namespace, data);
992    preload({
993        source: data.source,
994        crossOrigin: data.crossOrigin,
995        preloadCount: data.preloadCount,
996        progress: function (progress) {
997            data.progress = progress;
998            data.target.trigger('onProgress.' + namespace, data);
999        },
1000        complete: function (images) {
1001            data.images = images;
1002            data.loading = false;
1003            data.frames = data.frames || images.length;
1004            applyMetrics(data);
1005            applyLayout(data);
1006            data.stage.show();
1007            data.target
1008                .removeClass('loading')
1009                .trigger('onLoad.' + namespace, data)
1010                .trigger('onFrame.' + namespace, data)
1011                .trigger('onDraw.' + namespace, data)
1012                .trigger('onComplete.' + namespace, data);
1013        }
1014    });
1015}
1016/**
1017 * Creates a new SpriteSpin instance
1018 *
1019 * @public
1020 */
1021function create(options) {
1022    var _this = this;
1023    var target = options.target;
1024    // SpriteSpin is not initialized
1025    // Create default settings object and extend with given options
1026    var data = $$2.extend(true, {}, defaults, options);
1027    // ensure source is set
1028    data.source = data.source || [];
1029    // ensure plugins are set
1030    data.plugins = data.plugins || [
1031        '360',
1032        'drag'
1033    ];
1034    // if image tags are contained inside this DOM element
1035    // use these images as the source files
1036    target.find('img').each(function () {
1037        if (!Array.isArray(data.source)) {
1038            data.source = [];
1039        }
1040        data.source.push($$2(_this).attr('src'));
1041    });
1042    // build inner html
1043    // <div>
1044    //   <div class='spritespin-stage'></div>
1045    //   <canvas class='spritespin-canvas'></canvas>
1046    // </div>
1047    target
1048        .empty()
1049        .addClass('spritespin-instance')
1050        .append("<div class='spritespin-stage'></div>");
1051    // add the canvas element if canvas rendering is enabled and supported
1052    if (data.renderer === 'canvas') {
1053        var canvas = document.createElement('canvas');
1054        if (!!(canvas.getContext && canvas.getContext('2d'))) {
1055            data.canvas = $$2(canvas).addClass('spritespin-canvas');
1056            data.context = canvas.getContext('2d');
1057            target.append(data.canvas);
1058            target.addClass('with-canvas');
1059        }
1060        else {
1061            // fallback to image rendering mode
1062            data.renderer = 'image';
1063        }
1064    }
1065    // setup references to DOM elements
1066    data.target = target;
1067    data.stage = target.find('.spritespin-stage');
1068    // store the data
1069    target.data(namespace, data);
1070    pushInstance(data);
1071    return data;
1072}
1073/**
1074 * Creates a new SpriteSpin instance, or updates an existing one
1075 *
1076 * @public
1077 */
1078function createOrUpdate(options) {
1079    lazyinit();
1080    var data = options.target.data(namespace);
1081    if (!data) {
1082        data = create(options);
1083    }
1084    else {
1085        $$2.extend(data, options);
1086    }
1087    boot(data);
1088    return data;
1089}
1090/**
1091 * Destroys the SpriteSpin instance
1092 *
1093 * @remarks
1094 * - stops running animation
1095 * - unbinds all events
1096 * - deletes the data on the target element
1097 *
1098 * @public
1099 */
1100function destroy(data) {
1101    popInstance(data);
1102    stopAnimation(data);
1103    data.target
1104        .trigger('onDestroy', data)
1105        .html(null)
1106        .attr('style', null)
1107        .attr('unselectable', null)
1108        .removeClass(['spritespin-instance', 'with-canvas']);
1109    unbind(data.target);
1110    data.target.removeData(namespace);
1111}
1112
1113/**
1114 * Gets the current input state
1115 *
1116 * @public
1117 * @param data - The SpriteSpin instance data
1118 */
1119function getInputState(data) {
1120    return getState(data, 'input');
1121}
1122/**
1123 * Updates the input state using a mouse or touch event.
1124 *
1125 * @public
1126 * @param e - The input event
1127 * @param data - The SpriteSpin instance data
1128 */
1129function updateInput(e, data) {
1130    var cursor = getCursorPosition(e);
1131    var state = getInputState(data);
1132    // cache positions from previous frame
1133    state.oldX = state.currentX;
1134    state.oldY = state.currentY;
1135    state.currentX = cursor.x;
1136    state.currentY = cursor.y;
1137    // Fix old position.
1138    if (state.oldX === undefined || state.oldY === undefined) {
1139        state.oldX = state.currentX;
1140        state.oldY = state.currentY;
1141    }
1142    // Cache the initial click/touch position and store the frame number at which the click happened.
1143    // Useful for different behavior implementations. This must be restored when the click/touch is released.
1144    if (state.startX === undefined || state.startY === undefined) {
1145        state.startX = state.currentX;
1146        state.startY = state.currentY;
1147        state.clickframe = data.frame;
1148        state.clicklane = data.lane;
1149    }
1150    // Calculate the vector from start position to current pointer position.
1151    state.dX = state.currentX - state.startX;
1152    state.dY = state.currentY - state.startY;
1153    // Calculate the vector from last frame position to current pointer position.
1154    state.ddX = state.currentX - state.oldX;
1155    state.ddY = state.currentY - state.oldY;
1156    // Normalize vectors to range [-1:+1]
1157    state.ndX = state.dX / data.target.innerWidth();
1158    state.ndY = state.dY / data.target.innerHeight();
1159    state.nddX = state.ddX / data.target.innerWidth();
1160    state.nddY = state.ddY / data.target.innerHeight();
1161}
1162/**
1163 * Resets the input state.
1164 *
1165 * @public
1166 */
1167function resetInput(data) {
1168    var input = getInputState(data);
1169    input.startX = input.startY = undefined;
1170    input.currentX = input.currentY = undefined;
1171    input.oldX = input.oldY = undefined;
1172    input.dX = input.dY = 0;
1173    input.ddX = input.ddY = 0;
1174    input.ndX = input.ndY = 0;
1175    input.nddX = input.nddY = 0;
1176}
1177
1178function extension(option, value) {
1179    var $target = $$1(this);
1180    if (option === 'data') {
1181        return $target.data(namespace);
1182    }
1183    if (option === 'api') {
1184        var data = $target.data(namespace);
1185        data.api = data.api || new Api(data);
1186        return data.api;
1187    }
1188    if (option === 'destroy') {
1189        return $target.each(function () {
1190            var data = $target.data(namespace);
1191            if (data) {
1192                destroy(data);
1193            }
1194        });
1195    }
1196    if (arguments.length === 2 && typeof option === 'string') {
1197        option = (_a = {}, _a[option] = value, _a);
1198    }
1199    if (typeof option === 'object') {
1200        return createOrUpdate($$1.extend(true, { target: $target }, option)).target;
1201    }
1202    throw new Error('Invalid call to spritespin');
1203    var _a;
1204}
1205$$1.fn[namespace] = extension;
1206
1207// tslint:disable:object-literal-shorthand
1208// tslint:disable:only-arrow-functions
1209extendApi({
1210    // Gets a value indicating whether the animation is currently running.
1211    isPlaying: function () {
1212        return getPlaybackState(this.data).handler != null;
1213    },
1214    // Gets a value indicating whether the animation looping is enabled.
1215    isLooping: function () {
1216        return this.data.loop;
1217    },
1218    // Starts/Stops the animation playback
1219    toggleAnimation: function () {
1220        if (this.isPlaying()) {
1221            this.stopAnimation();
1222        }
1223        else {
1224            this.startAnimation();
1225        }
1226    },
1227    // Stops animation playback
1228    stopAnimation: function () {
1229        this.data.animate = false;
1230        stopAnimation(this.data);
1231    },
1232    // Starts animation playback
1233    startAnimation: function () {
1234        this.data.animate = true;
1235        applyAnimation(this.data);
1236    },
1237    // Sets a value indicating whether the animation should be looped or not.
1238    // This might start the animation (if the 'animate' data attribute is set to true)
1239    loop: function (value) {
1240        this.data.loop = value;
1241        applyAnimation(this.data);
1242        return this;
1243    },
1244    // Gets the current frame number
1245    currentFrame: function () {
1246        return this.data.frame;
1247    },
1248    // Updates SpriteSpin to the specified frame.
1249    updateFrame: function (frame) {
1250        updateFrame(this.data, frame);
1251        return this;
1252    },
1253    // Skips the given number of frames
1254    skipFrames: function (step) {
1255        var data = this.data;
1256        updateFrame(data, data.frame + (data.reverse ? -step : +step));
1257        return this;
1258    },
1259    // Updates SpriteSpin so that the next frame is shown
1260    nextFrame: function () {
1261        return this.skipFrames(1);
1262    },
1263    // Updates SpriteSpin so that the previous frame is shown
1264    prevFrame: function () {
1265        return this.skipFrames(-1);
1266    },
1267    // Starts the animations that will play until the given frame number is reached
1268    // options:
1269    //   force [boolean] starts the animation, even if current frame is the target frame
1270    //   nearest [boolean] animates to the direction with minimum distance to the target frame
1271    playTo: function (frame, options) {
1272        var data = this.data;
1273        options = options || {};
1274        if (!options.force && data.frame === frame) {
1275            return;
1276        }
1277        if (options.nearest) {
1278            // distance to the target frame
1279            var a = frame - data.frame;
1280            // distance to last frame and the to target frame
1281            var b = frame > data.frame ? a - data.frames : a + data.frames;
1282            // minimum distance
1283            var c = Math.abs(a) < Math.abs(b) ? a : b;
1284            data.reverse = c < 0;
1285        }
1286        data.animate = true;
1287        data.loop = false;
1288        data.stopFrame = frame;
1289        applyAnimation(data);
1290        return this;
1291    }
1292});
1293
1294function pick(target, names) {
1295    for (var _i = 0, names_1 = names; _i < names_1.length; _i++) {
1296        var name_1 = names_1[_i];
1297        if (target[name_1] || name_1 in target) {
1298            return name_1;
1299        }
1300    }
1301    return names[0];
1302}
1303var browser = {
1304    requestFullscreen: pick(document.documentElement, [
1305        'requestFullscreen',
1306        'webkitRequestFullScreen',
1307        'mozRequestFullScreen',
1308        'msRequestFullscreen'
1309    ]),
1310    exitFullscreen: pick(document, [
1311        'exitFullscreen',
1312        'webkitExitFullscreen',
1313        'webkitCancelFullScreen',
1314        'mozCancelFullScreen',
1315        'msExitFullscreen'
1316    ]),
1317    fullscreenElement: pick(document, [
1318        'fullscreenElement',
1319        'webkitFullscreenElement',
1320        'webkitCurrentFullScreenElement',
1321        'mozFullScreenElement',
1322        'msFullscreenElement'
1323    ]),
1324    fullscreenEnabled: pick(document, [
1325        'fullscreenEnabled',
1326        'webkitFullscreenEnabled',
1327        'mozFullScreenEnabled',
1328        'msFullscreenEnabled'
1329    ]),
1330    fullscreenchange: pick(document, [
1331        'onfullscreenchange',
1332        'onwebkitfullscreenchange',
1333        'onmozfullscreenchange',
1334        'onMSFullscreenChange'
1335    ]).replace(/^on/, ''),
1336    fullscreenerror: pick(document, [
1337        'onfullscreenerror',
1338        'onwebkitfullscreenerror',
1339        'onmozfullscreenerror',
1340        'onMSFullscreenError'
1341    ]).replace(/^on/, '')
1342};
1343var changeEvent = browser.fullscreenchange + '.' + namespace + '-fullscreen';
1344function unbindChangeEvent() {
1345    $$1(document).unbind(changeEvent);
1346}
1347function bindChangeEvent(callback) {
1348    unbindChangeEvent();
1349    $$1(document).bind(changeEvent, callback);
1350}
1351var orientationEvent = 'orientationchange.' + namespace + '-fullscreen';
1352function unbindOrientationEvent() {
1353    $$1(window).unbind(orientationEvent);
1354}
1355function bindOrientationEvent(callback) {
1356    unbindOrientationEvent();
1357    $$1(window).bind(orientationEvent, callback);
1358}
1359function requestFullscreenNative(e) {
1360    e = e || document.documentElement;
1361    e[browser.requestFullscreen]();
1362}
1363function exitFullscreen() {
1364    return document[browser.exitFullscreen]();
1365}
1366function fullscreenEnabled() {
1367    return document[browser.fullscreenEnabled];
1368}
1369function fullscreenElement() {
1370    return document[browser.fullscreenElement];
1371}
1372function isFullscreen() {
1373    return !!fullscreenElement();
1374}
1375function toggleFullscreen(data, opts) {
1376    if (isFullscreen()) {
1377        this.apiRequestFullscreen(opts);
1378    }
1379    else {
1380        this.exitFullscreen();
1381    }
1382}
1383function requestFullscreen(data, opts) {
1384    opts = opts || {};
1385    var oWidth = data.width;
1386    var oHeight = data.height;
1387    var oSource = data.source;
1388    var oSize = data.sizeMode;
1389    var oResponsive = data.responsive;
1390    var enter = function () {
1391        data.width = window.screen.width;
1392        data.height = window.screen.height;
1393        data.source = (opts.source || oSource);
1394        data.sizeMode = opts.sizeMode || 'fit';
1395        data.responsive = false;
1396        boot(data);
1397    };
1398    var exit = function () {
1399        data.width = oWidth;
1400        data.height = oHeight;
1401        data.source = oSource;
1402        data.sizeMode = oSize;
1403        data.responsive = oResponsive;
1404        boot(data);
1405    };
1406    bindChangeEvent(function () {
1407        if (isFullscreen()) {
1408            enter();
1409            bindOrientationEvent(enter);
1410        }
1411        else {
1412            unbindChangeEvent();
1413            unbindOrientationEvent();
1414            exit();
1415        }
1416    });
1417    requestFullscreenNative(data.target[0]);
1418}
1419extendApi({
1420    fullscreenEnabled: fullscreenEnabled,
1421    fullscreenElement: fullscreenElement,
1422    exitFullscreen: exitFullscreen,
1423    toggleFullscreen: function (opts) {
1424        toggleFullscreen(this.data, opts);
1425    },
1426    requestFullscreen: function (opts) {
1427        requestFullscreen(this.data, opts);
1428    }
1429});
1430
1431(function () {
1432    var NAME = 'click';
1433    function click(e, data) {
1434        if (data.loading || !data.stage.is(':visible')) {
1435            return;
1436        }
1437        updateInput(e, data);
1438        var input = getInputState(data);
1439        var half, pos;
1440        var target = data.target, offset = target.offset();
1441        if (data.orientation === 'horizontal') {
1442            half = target.innerWidth() / 2;
1443            pos = input.currentX - offset.left;
1444        }
1445        else {
1446            half = target.innerHeight() / 2;
1447            pos = input.currentY - offset.top;
1448        }
1449        updateFrame(data, data.frame + (pos > half ? 1 : -1));
1450    }
1451    registerPlugin(NAME, {
1452        name: NAME,
1453        mouseup: click,
1454        touchend: click
1455    });
1456})();
1457
1458(function () {
1459    var NAME = 'drag';
1460    function getState$$1(data) {
1461        return getPluginState(data, NAME);
1462    }
1463    function getAxis(data) {
1464        if (typeof data.orientation === 'number') {
1465            return data.orientation * Math.PI / 180;
1466        }
1467        if (data.orientation === 'horizontal') {
1468            return 0;
1469        }
1470        return Math.PI / 2;
1471    }
1472    function onInit(e, data) {
1473        var state = getState$$1(data);
1474        var d = [200, 1500];
1475        var t = data.touchScrollTimer || d;
1476        state.minTime = t[0] || d[0];
1477        state.maxTime = t[1] || d[1];
1478    }
1479    function dragStart(e, data) {
1480        var state = getState$$1(data);
1481        if (data.loading || is(data, 'dragging') || data['zoomPinFrame'] && !data.stage.is(':visible')) {
1482            return;
1483        }
1484        // Touch scroll can only be disabled by cancelling the 'touchstart' event.
1485        // If we would try to cancel the 'touchmove' event during a scroll
1486        // chrome browser raises an error
1487        //
1488        // When a user interacts with sprite spin, we don't know whether the intention
1489        // is to scroll the page or to roll the spin.
1490        //
1491        // On first interaction with SpriteSpin the scroll is not disabled
1492        // On double tap within 200ms the scroll is not disabled
1493        // Scroll is only disabled if there was an interaction with SpriteSpin in the past 1500ms
1494        var now = new Date().getTime();
1495        if (state.endAt && (now - state.endAt > state.maxTime)) {
1496            // reset timer if the user has no interaction with spritespin within 1500ms
1497            state.startAt = null;
1498            state.endAt = null;
1499        }
1500        if (state.startAt && (now - state.startAt > state.minTime)) {
1501            // disable scroll only if there was already an interaction with spritespin
1502            // however, allow scrolling on double tab within 200ms
1503            e.preventDefault();
1504        }
1505        state.startAt = now;
1506        state.wasPlaying = !!getPlaybackState(data).handler;
1507        state.frame = data.frame || 0;
1508        state.lane = data.lane || 0;
1509        flag(data, 'dragging', true);
1510        updateInput(e, data);
1511    }
1512    function dragEnd(e, data) {
1513        if (is(data, 'dragging')) {
1514            getState$$1(data).endAt = new Date().getTime();
1515            flag(data, 'dragging', false);
1516            resetInput(data);
1517            if (data.retainAnimate && getState$$1(data).wasPlaying) {
1518                startAnimation(data);
1519            }
1520        }
1521    }
1522    function drag(e, data) {
1523        var state = getState$$1(data);
1524        var input = getInputState(data);
1525        if (!is(data, 'dragging')) {
1526            return;
1527        }
1528        updateInput(e, data);
1529        var rad = getAxis(data);
1530        var sn = Math.sin(rad);
1531        var cs = Math.cos(rad);
1532        var x = ((input.nddX * cs - input.nddY * sn) * data.sense) || 0;
1533        var y = ((input.nddX * sn + input.nddY * cs) * (data.senseLane || data.sense)) || 0;
1534        // accumulate
1535        state.frame += data.frames * x;
1536        state.lane += data.lanes * y;
1537        // update spritespin
1538        var oldFrame = data.frame;
1539        var oldLane = data.lane;
1540        updateFrame(data, Math.floor(state.frame), Math.floor(state.lane));
1541        stopAnimation(data);
1542    }
1543    function mousemove(e, data) {
1544        dragStart(e, data);
1545        drag(e, data);
1546    }
1547    registerPlugin('drag', {
1548        name: 'drag',
1549        onInit: onInit,
1550        mousedown: dragStart,
1551        mousemove: drag,
1552        mouseup: dragEnd,
1553        documentmousemove: drag,
1554        documentmouseup: dragEnd,
1555        touchstart: dragStart,
1556        touchmove: drag,
1557        touchend: dragEnd,
1558        touchcancel: dragEnd
1559    });
1560    registerPlugin('move', {
1561        name: 'move',
1562        onInit: onInit,
1563        mousemove: mousemove,
1564        mouseleave: dragEnd,
1565        touchstart: dragStart,
1566        touchmove: drag,
1567        touchend: dragEnd,
1568        touchcancel: dragEnd
1569    });
1570})();
1571
1572(function () {
1573    var NAME = 'hold';
1574    function getState$$1(data) {
1575        return getPluginState(data, NAME);
1576    }
1577    function rememberOptions(data) {
1578        var state = getState$$1(data);
1579        state.frameTime = data.frameTime;
1580        state.animate = data.animate;
1581        state.reverse = data.reverse;
1582    }
1583    function restoreOptions(data) {
1584        var state = getState$$1(data);
1585        data.frameTime = state.frameTime;
1586        data.animate = state.animate;
1587        data.reverse = state.reverse;
1588    }
1589    function start(e, data) {
1590        if (is(data, 'loading') || is(data, 'dragging') || !data.stage.is(':visible')) {
1591            return;
1592        }
1593        rememberOptions(data);
1594        updateInput(e, data);
1595        flag(data, 'dragging', true);
1596        data.animate = true;
1597        applyAnimation(data);
1598    }
1599    function stop(e, data) {
1600        flag(data, 'dragging', false);
1601        resetInput(data);
1602        stopAnimation(data);
1603        restoreOptions(data);
1604        applyAnimation(data);
1605    }
1606    function update(e, data) {
1607        if (!is(data, 'dragging')) {
1608            return;
1609        }
1610        updateInput(e, data);
1611        var input = getInputState(data);
1612        var half, delta;
1613        var target = data.target, offset = target.offset();
1614        if (data.orientation === 'horizontal') {
1615            half = target.innerWidth() / 2;
1616            delta = (input.currentX - offset.left - half) / half;
1617        }
1618        else {
1619            half = (data.height / 2);
1620            delta = (input.currentY - offset.top - half) / half;
1621        }
1622        data.reverse = delta < 0;
1623        delta = delta < 0 ? -delta : delta;
1624        data.frameTime = 80 * (1 - delta) + 20;
1625        if (((data.orientation === 'horizontal') && (input.dX < input.dY)) ||
1626            ((data.orientation === 'vertical') && (input.dX < input.dY))) {
1627            e.preventDefault();
1628        }
1629    }
1630    function onFrame(e, data) {
1631        data.animate = true;
1632        applyAnimation(data);
1633    }
1634    registerPlugin(NAME, {
1635        name: NAME,
1636        mousedown: start,
1637        mousemove: update,
1638        mouseup: stop,
1639        mouseleave: stop,
1640        touchstart: start,
1641        touchmove: update,
1642        touchend: stop,
1643        touchcancel: stop,
1644        onFrame: onFrame
1645    });
1646})();
1647
1648(function () {
1649    var NAME = 'swipe';
1650    function getState$$1(data) {
1651        return getPluginState(data, NAME);
1652    }
1653    function getOption(data, name, fallback) {
1654        return data[name] || fallback;
1655    }
1656    function init(e, data) {
1657        var state = getState$$1(data);
1658        state.fling = getOption(data, 'swipeFling', 10);
1659        state.snap = getOption(data, 'swipeSnap', 0.50);
1660    }
1661    function start(e, data) {
1662        if (!data.loading && !is(data, 'dragging')) {
1663            updateInput(e, data);
1664            flag(data, 'dragging', true);
1665        }
1666    }
1667    function update(e, data) {
1668        if (!is(data, 'dragging')) {
1669            return;
1670        }
1671        updateInput(e, data);
1672        var frame = data.frame;
1673        var lane = data.lane;
1674        updateFrame(data, frame, lane);
1675    }
1676    function end(e, data) {
1677        if (!is(data, 'dragging')) {
1678            return;
1679        }
1680        flag(data, 'dragging', false);
1681        var state = getState$$1(data);
1682        var input = getInputState(data);
1683        var frame = data.frame;
1684        var lane = data.lane;
1685        var snap = state.snap;
1686        var fling = state.fling;
1687        var dS, dF;
1688        if (data.orientation === 'horizontal') {
1689            dS = input.ndX;
1690            dF = input.ddX;
1691        }
1692        else {
1693            dS = input.ndY;
1694            dF = input.ddY;
1695        }
1696        if (dS >= snap || dF >= fling) {
1697            frame = data.frame - 1;
1698        }
1699        else if (dS <= -snap || dF <= -fling) {
1700            frame = data.frame + 1;
1701        }
1702        resetInput(data);
1703        updateFrame(data, frame, lane);
1704        stopAnimation(data);
1705    }
1706    registerPlugin(NAME, {
1707        name: NAME,
1708        onLoad: init,
1709        mousedown: start,
1710        mousemove: update,
1711        mouseup: end,
1712        mouseleave: end,
1713        touchstart: start,
1714        touchmove: update,
1715        touchend: end,
1716        touchcancel: end
1717    });
1718})();
1719
1720(function () {
1721    var NAME = 'wheel';
1722    function wheel(e, data) {
1723        if (!data.loading && data.stage.is(':visible')) {
1724            e.preventDefault();
1725            var we = e.originalEvent;
1726            var signX = we.deltaX === 0 ? 0 : we.deltaX > 0 ? 1 : -1;
1727            var signY = we.deltaY === 0 ? 0 : we.deltaY > 0 ? 1 : -1;
1728            updateFrame(data, data.frame + signY, data.lane + signX);
1729        }
1730    }
1731    registerPlugin(NAME, {
1732        name: NAME,
1733        wheel: wheel
1734    });
1735})();
1736
1737(function () {
1738    var template = "\n<div class='spritespin-progress'>\n  <div class='spritespin-progress-label'></div>\n  <div class='spritespin-progress-bar'></div>\n</div>\n";
1739    function getState$$1(data) {
1740        return getPluginState(data, NAME);
1741    }
1742    var NAME = 'progress';
1743    function onInit(e, data) {
1744        var state = getState$$1(data);
1745        if (!state.stage) {
1746            state.stage = $$1(template);
1747            state.stage.appendTo(data.target);
1748        }
1749        state.stage.find('.spritespin-progress-label')
1750            .text("0%")
1751            .css({ 'text-align': 'center' });
1752        state.stage.find('.spritespin-progress-bar').css({
1753            width: "0%"
1754        });
1755        state.stage.hide().fadeIn();
1756    }
1757    function onProgress(e, data) {
1758        var state = getState$$1(data);
1759        state.stage.find('.spritespin-progress-label')
1760            .text(data.progress.percent + "%")
1761            .css({ 'text-align': 'center' });
1762        state.stage.find('.spritespin-progress-bar').css({
1763            width: data.progress.percent + "%"
1764        });
1765    }
1766    function onLoad(e, data) {
1767        $$1(getState$$1(data).stage).fadeOut();
1768    }
1769    function onDestroy(e, data) {
1770        $$1(getState$$1(data).stage).remove();
1771    }
1772    registerPlugin(NAME, {
1773        name: NAME,
1774        onInit: onInit,
1775        onProgress: onProgress,
1776        onLoad: onLoad,
1777        onDestroy: onDestroy
1778    });
1779})();
1780
1781(function () {
1782    var NAME = '360';
1783    function onLoad(e, data) {
1784        data.stage.find('.spritespin-frames').detach();
1785        if (data.renderer === 'image') {
1786            $(data.images).addClass('spritespin-frames').appendTo(data.stage);
1787        }
1788    }
1789    function onDraw(e, data) {
1790        var specs = findSpecs(data.metrics, data.frames, data.frame, data.lane);
1791        var sheet = specs.sheet;
1792        var sprite = specs.sprite;
1793        if (!sheet || !sprite) {
1794            return;
1795        }
1796        var src = data.source[sheet.id];
1797        var image = data.images[sheet.id];
1798        if (data.renderer === 'canvas') {
1799            data.canvas.show();
1800            var w = data.canvas[0].width / data.canvasRatio;
1801            var h = data.canvas[0].height / data.canvasRatio;
1802            data.context.clearRect(0, 0, w, h);
1803            data.context.drawImage(image, sprite.sampledX, sprite.sampledY, sprite.sampledWidth, sprite.sampledHeight, 0, 0, w, h);
1804            return;
1805        }
1806        var scaleX = data.stage.innerWidth() / sprite.sampledWidth;
1807        var scaleY = data.stage.innerHeight() / sprite.sampledHeight;
1808        var top = Math.floor(-sprite.sampledY * scaleY);
1809        var left = Math.floor(-sprite.sampledX * scaleX);
1810        var width = Math.floor(sheet.sampledWidth * scaleX);
1811        var height = Math.floor(sheet.sampledHeight * scaleY);
1812        if (data.renderer === 'background') {
1813            data.stage.css({
1814                'background-image': "url('" + src + "')",
1815                'background-position': left + "px " + top + "px",
1816                'background-repeat': 'no-repeat',
1817                // set custom background size to enable responsive rendering
1818                '-webkit-background-size': width + "px " + height + "px",
1819                '-moz-background-size': width + "px " + height + "px",
1820                '-o-background-size': width + "px " + height + "px",
1821                'background-size': width + "px " + height + "px" /* Chrome, Firefox 4+, IE 9+, Opera, Safari 5+ */
1822            });
1823            return;
1824        }
1825        $(data.images).hide();
1826        $(image).show().css({
1827            position: 'absolute',
1828            top: top,
1829            left: left,
1830            'max-width': 'initial',
1831            width: width,
1832            height: height
1833        });
1834    }
1835    registerPlugin(NAME, {
1836        name: NAME,
1837        onLoad: onLoad,
1838        onDraw: onDraw
1839    });
1840})();
1841
1842(function () {
1843    var NAME = 'blur';
1844    function getState$$1(data) {
1845        return getPluginState(data, NAME);
1846    }
1847    function getOption(data, name, fallback) {
1848        return data[name] || fallback;
1849    }
1850    function init(e, data) {
1851        var state = getState$$1(data);
1852        state.canvas = state.canvas || $$1("<canvas class='blur-layer'></canvas>");
1853        state.context = state.context || state.canvas[0].getContext('2d');
1854        state.steps = state.steps || [];
1855        state.fadeTime = Math.max(getOption(data, 'blurFadeTime', 200), 1);
1856        state.frameTime = Math.max(getOption(data, 'blurFrameTime', data.frameTime), 16);
1857        state.trackTime = null;
1858        state.cssBlur = !!getOption(data, 'blurCss', false);
1859        var inner = getInnerSize(data);
1860        var outer = data.responsive ? getComputedSize(data) : getOuterSize(data);
1861        var css = getInnerLayout(data.sizeMode, inner, outer);
1862        state.canvas[0].width = data.width * data.canvasRatio;
1863        state.canvas[0].height = data.height * data.canvasRatio;
1864        state.canvas.css(css).show();
1865        state.context.scale(data.canvasRatio, data.canvasRatio);
1866        data.target.append(state.canvas);
1867    }
1868    function onFrame(e, data) {
1869        var state = getState$$1(data);
1870        trackFrame(data);
1871        if (state.timeout == null) {
1872            loop(data);
1873        }
1874    }
1875    function trackFrame(data) {
1876        var state = getState$$1(data);
1877        var ani = getPlaybackState(data);
1878        // distance between frames
1879        var d = Math.abs(data.frame - ani.lastFrame);
1880        // shortest distance
1881        d = d >= data.frames / 2 ? data.frames - d : d;
1882        state.steps.unshift({
1883            frame: data.frame,
1884            lane: data.lane,
1885            live: 1,
1886            step: state.frameTime / state.fadeTime,
1887            d: d,
1888            alpha: 0
1889        });
1890    }
1891    var toRemove = [];
1892    function removeOldFrames(frames) {
1893        toRemove.length = 0;
1894        for (var i = 0; i < frames.length; i += 1) {
1895            if (frames[i].alpha <= 0) {
1896                toRemove.push(i);
1897            }
1898        }
1899        for (var _i = 0, toRemove_1 = toRemove; _i < toRemove_1.length; _i++) {
1900            var item = toRemove_1[_i];
1901            frames.splice(item, 1);
1902        }
1903    }
1904    function loop(data) {
1905        var state = getState$$1(data);
1906        state.timeout = window.setTimeout(function () { tick(data); }, state.frameTime);
1907    }
1908    function killLoop(data) {
1909        var state = getState$$1(data);
1910        window.clearTimeout(state.timeout);
1911        state.timeout = null;
1912    }
1913    function applyCssBlur(canvas, d) {
1914        var amount = Math.min(Math.max((d / 2) - 4, 0), 2.5);
1915        var blur = "blur(" + amount + "px)";
1916        canvas.css({
1917            '-webkit-filter': blur,
1918            filter: blur
1919        });
1920    }
1921    function clearFrame(data, state) {
1922        state.canvas.show();
1923        var w = state.canvas[0].width / data.canvasRatio;
1924        var h = state.canvas[0].height / data.canvasRatio;
1925        // state.context.clearRect(0, 0, w, h)
1926    }
1927    function drawFrame(data, state, step) {
1928        if (step.alpha <= 0) {
1929            return;
1930        }
1931        var specs = findSpecs(data.metrics, data.frames, step.frame, step.lane);
1932        var sheet = specs.sheet;
1933        var sprite = specs.sprite;
1934        if (!sheet || !sprite) {
1935            return;
1936        }
1937        var src = data.source[sheet.id];
1938        var image = data.images[sheet.id];
1939        if (image.complete === false) {
1940            return;
1941        }
1942        state.canvas.show();
1943        var w = state.canvas[0].width / data.canvasRatio;
1944        var h = state.canvas[0].height / data.canvasRatio;
1945        state.context.globalAlpha = step.alpha;
1946        state.context.drawImage(image, sprite.sampledX, sprite.sampledY, sprite.sampledWidth, sprite.sampledHeight, 0, 0, w, h);
1947    }
1948    function tick(data) {
1949        var state = getState$$1(data);
1950        killLoop(data);
1951        if (!state.context) {
1952            return;
1953        }
1954        var d = 0;
1955        clearFrame(data, state);
1956        state.context.clearRect(0, 0, data.width, data.height);
1957        for (var _i = 0, _a = state.steps; _i < _a.length; _i++) {
1958            var step = _a[_i];
1959            step.live = Math.max(step.live - step.step, 0);
1960            step.alpha = Math.max(step.live - 0.25, 0);
1961            drawFrame(data, state, step);
1962            d += step.alpha + step.d;
1963        }
1964        if (state.cssBlur) {
1965            applyCssBlur(state.canvas, d);
1966        }
1967        removeOldFrames(state.steps);
1968        if (state.steps.length) {
1969            loop(data);
1970        }
1971    }
1972    registerPlugin(NAME, {
1973        name: NAME,
1974        onLoad: init,
1975        onFrameChanged: onFrame
1976    });
1977})();
1978
1979(function () {
1980    var max = Math.max;
1981    var min = Math.min;
1982    var NAME = 'ease';
1983    function getState$$1(data) {
1984        return getPluginState(data, NAME);
1985    }
1986    function getOption(data, name, fallback) {
1987        return data[name] || fallback;
1988    }
1989    function init(e, data) {
1990        var state = getState$$1(data);
1991        state.maxSamples = max(getOption(data, 'easeMaxSamples', 5), 0);
1992        state.damping = max(min(getOption(data, 'easeDamping', 0.9), 0.999), 0);
1993        state.abortTime = max(getOption(data, 'easeAbortTime', 250), 16);
1994        state.updateTime = max(getOption(data, 'easeUpdateTime', data.frameTime), 16);
1995        state.samples = [];
1996        state.steps = [];
1997    }
1998    function update(e, data) {
1999        if (is(data, 'dragging')) {
2000            killLoop(data);
2001            sampleInput(data);
2002        }
2003    }
2004    function end(e, data) {
2005        var state = getState$$1(data);
2006        var samples = state.samples;
2007        var last;
2008        var lanes = 0;
2009        var frames = 0;
2010        var time = 0;
2011        for (var _i = 0, samples_1 = samples; _i < samples_1.length; _i++) {
2012            var sample = samples_1[_i];
2013            if (!last) {
2014                last = sample;
2015                continue;
2016            }
2017            var dt = sample.time - last.time;
2018            if (dt > state.abortTime) {
2019                lanes = frames = time = 0;
2020                return killLoop(data);
2021            }
2022            frames += sample.frame - last.frame;
2023            lanes += sample.lane - last.lane;
2024            time += dt;
2025            last = sample;
2026        }
2027        samples.length = 0;
2028        if (!time) {
2029            return;
2030        }
2031        state.lane = data.lane;
2032        state.lanes = 0;
2033        state.laneStep = lanes / time * state.updateTime;
2034        state.frame = data.frame;
2035        state.frames = 0;
2036        state.frameStep = frames / time * state.updateTime;
2037        loop(data);
2038    }
2039    function sampleInput(data) {
2040        var state = getState$$1(data);
2041        // add a new sample
2042        state.samples.push({
2043            time: new Date().getTime(),
2044            frame: data.frame,
2045            lane: data.lane
2046        });
2047        // drop old samples
2048        while (state.samples.length > state.maxSamples) {
2049            state.samples.shift();
2050        }
2051    }
2052    function killLoop(data) {
2053        var state = getState$$1(data);
2054        if (state.handler != null) {
2055            window.clearTimeout(state.handler);
2056            state.handler = null;
2057        }
2058    }
2059    function loop(data) {
2060        var state = getState$$1(data);
2061        state.handler = window.setTimeout(function () { tick(data); }, state.updateTime);
2062    }
2063    function tick(data) {
2064        var state = getState$$1(data);
2065        state.lanes += state.laneStep;
2066        state.frames += state.frameStep;
2067        state.laneStep *= state.damping;
2068        state.frameStep *= state.damping;
2069        var frame = Math.floor(state.frame + state.frames);
2070        var lane = Math.floor(state.lane + state.lanes);
2071        updateFrame(data, frame, lane);
2072        if (is(data, 'dragging')) {
2073            killLoop(data);
2074        }
2075        else if (Math.abs(state.frameStep) > 0.005 || Math.abs(state.laneStep) > 0.005) {
2076            loop(data);
2077        }
2078        else {
2079            killLoop(data);
2080        }
2081    }
2082    registerPlugin(NAME, {
2083        name: NAME,
2084        onLoad: init,
2085        mousemove: update,
2086        mouseup: end,
2087        mouseleave: end,
2088        touchmove: update,
2089        touchend: end,
2090        touchcancel: end
2091    });
2092})();
2093
2094(function () {
2095    var NAME = 'gallery';
2096    function getState$$1(data) {
2097        return getPluginState(data, NAME);
2098    }
2099    function getOption(data, name, fallback) {
2100        return data[name] || fallback;
2101    }
2102    function load(e, data) {
2103        var state = getState$$1(data);
2104        state.images = [];
2105        state.offsets = [];
2106        state.frame = data.frame;
2107        state.speed = getOption(data, 'gallerySpeed', 500);
2108        state.opacity = getOption(data, 'galleryOpacity', 0.25);
2109        state.stage = getOption(data, 'galleryStage', $$1('<div></div>'));
2110        state.stage.empty().addClass('gallery-stage').prependTo(data.stage);
2111        var size = 0;
2112        for (var _i = 0, _a = data.images; _i < _a.length; _i++) {
2113            var image = _a[_i];
2114            var naturalSize$$1 = naturalSize(image);
2115            var scale = data.height / naturalSize$$1.height;
2116            var img = $$1(image);
2117            state.stage.append(img);
2118            state.images.push(img);
2119            state.offsets.push(-size + (data.width - image.width * scale) / 2);
2120            size += data.width;
2121            img.css({
2122                'max-width': 'initial',
2123                opacity: state.opacity,
2124                width: data.width,
2125                height: data.height
2126            });
2127        }
2128        var innerSize = getInnerSize(data);
2129        var outerSize = data.responsive ? getComputedSize(data) : getOuterSize(data);
2130        var layout = getInnerLayout(data.sizeMode, innerSize, outerSize);
2131        state.stage.css(layout).css({ width: size, left: state.offsets[state.frame] });
2132        state.images[state.frame].animate({ opacity: 1 }, { duration: state.speed });
2133    }
2134    function draw(e, data) {
2135        var state = getState$$1(data);
2136        var input = getInputState(data);
2137        var isDragging = is(data, 'dragging');
2138        if (state.frame !== data.frame && !isDragging) {
2139            state.stage.stop(true, false).animate({ left: state.offsets[data.frame] }, { duration: state.speed });
2140            state.images[state.frame].animate({ opacity: state.opacity }, { duration: state.speed });
2141            state.frame = data.frame;
2142            state.images[state.frame].animate({ opacity: 1 }, { duration: state.speed });
2143            state.stage.animate({ left: state.offsets[state.frame] });
2144        }
2145        else if (isDragging || state.dX !== input.dX) {
2146            state.dX = input.dX;
2147            state.ddX = input.ddX;
2148            state.stage.stop(true, true).css({ left: state.offsets[state.frame] + state.dX });
2149        }
2150    }
2151    registerPlugin(NAME, {
2152        name: NAME,
2153        onLoad: load,
2154        onDraw: draw
2155    });
2156})();
2157
2158(function () {
2159    var NAME = 'panorama';
2160    function getState$$1(data) {
2161        return getPluginState(data, NAME);
2162    }
2163    function onLoad(e, data) {
2164        var state = getState$$1(data);
2165        var sprite = data.metrics[0];
2166        if (!sprite) {
2167            return;
2168        }
2169        if (data.orientation === 'horizontal') {
2170            state.scale = data.target.innerHeight() / sprite.sampledHeight;
2171            data.frames = sprite.sampledWidth;
2172        }
2173        else {
2174            state.scale = data.target.innerWidth() / sprite.sampledWidth;
2175            data.frames = sprite.sampledHeight;
2176        }
2177        var width = Math.floor(sprite.sampledWidth * state.scale);
2178        var height = Math.floor(sprite.sampledHeight * state.scale);
2179        data.stage.css({
2180            'background-image': "url(" + data.source[sprite.id] + ")",
2181            'background-repeat': 'repeat-both',
2182            // set custom background size to enable responsive rendering
2183            '-webkit-background-size': width + "px " + height + "px",
2184            '-moz-background-size': width + "px " + height + "px",
2185            '-o-background-size': width + "px " + height + "px",
2186            'background-size': width + "px " + height + "px" /* Chrome, Firefox 4+, IE 9+, Opera, Safari 5+ */
2187        });
2188    }
2189    function onDraw(e, data) {
2190        var state = getState$$1(data);
2191        var px = data.orientation === 'horizontal' ? 1 : 0;
2192        var py = px ? 0 : 1;
2193        var offset = data.frame % data.frames;
2194        var left = Math.round(px * offset * state.scale);
2195        var top = Math.round(py * offset * state.scale);
2196        data.stage.css({ 'background-position': left + "px " + top + "px" });
2197    }
2198    registerPlugin(NAME, {
2199        name: NAME,
2200        onLoad: onLoad,
2201        onDraw: onDraw
2202    });
2203})();
2204
2205(function () {
2206    var NAME = 'zoom';
2207    function getState$$1(data) {
2208        return getPluginState(data, NAME);
2209    }
2210    function getOption(data, name, fallback) {
2211        return name in data ? data[name] : fallback;
2212    }
2213    function onInit(e, data) {
2214        var state = getState$$1(data);
2215        state.source = getOption(data, 'zoomSource', data.source);
2216        state.useWheel = getOption(data, 'zoomUseWheel', false);
2217        state.useClick = getOption(data, 'zoomUseClick', true);
2218        state.pinFrame = getOption(data, 'zoomPinFrame', true);
2219        state.doubleClickTime = getOption(data, 'zoomDoubleClickTime', 500);
2220        state.stage = state.stage || $$1("<div class='zoom-stage'></div>");
2221        state.stage.css({
2222            width: '100%',
2223            height: '100%',
2224            top: 0,
2225            left: 0,
2226            bottom: 0,
2227            right: 0,
2228            position: 'absolute'
2229        })
2230            .appendTo(data.target)
2231            .hide();
2232    }
2233    function onDestroy(e, data) {
2234        var state = getState$$1(data);
2235        if (state.stage) {
2236            state.stage.remove();
2237            delete state.stage;
2238        }
2239    }
2240    function updateInput$$1(e, data) {
2241        var state = getState$$1(data);
2242        if (!state.stage.is(':visible')) {
2243            return;
2244        }
2245        e.preventDefault();
2246        if (state.pinFrame) {
2247            // hack into drag/move module and disable dragging
2248            // prevents frame change during zoom mode
2249            flag(data, 'dragging', false);
2250        }
2251        // grab touch/cursor position
2252        var cursor = getCursorPosition(e);
2253        // normalize cursor position into [0:1] range
2254        var x = cursor.x / data.width;
2255        var y = cursor.y / data.height;
2256        if (state.oldX == null) {
2257            state.oldX = x;
2258            state.oldY = y;
2259        }
2260        if (state.currentX == null) {
2261            state.currentX = x;
2262            state.currentY = y;
2263        }
2264        // calculate move delta since last frame and remember current position
2265        var dx = x - state.oldX;
2266        var dy = y - state.oldY;
2267        state.oldX = x;
2268        state.oldY = y;
2269        // invert drag direction for touch events to enable 'natural' scrolling
2270        if (e.type.match(/touch/)) {
2271            dx = -dx;
2272            dy = -dy;
2273        }
2274        // accumulate display coordinates
2275        state.currentX = clamp(state.currentX + dx, 0, 1);
2276        state.currentY = clamp(state.currentY + dy, 0, 1);
2277        updateFrame(data, data.frame, data.lane);
2278    }
2279    function onClick(e, data) {
2280        var state = getState$$1(data);
2281        if (!state.useClick) {
2282            return;
2283        }
2284        e.preventDefault();
2285        // simulate double click
2286        var clickTime = new Date().getTime();
2287        if (!state.clickTime) {
2288            // on first click
2289            state.clickTime = clickTime;
2290            return;
2291        }
2292        // on second click
2293        var timeDelta = clickTime - state.clickTime;
2294        if (timeDelta > state.doubleClickTime) {
2295            // took too long, back to first click
2296            state.clickTime = clickTime;
2297            return;
2298        }
2299        // on valid double click
2300        state.clickTime = undefined;
2301        if (toggleZoom(data)) {
2302            updateInput$$1(e, data);
2303        }
2304    }
2305    function onMove(e, data) {
2306        var state = getState$$1(data);
2307        if (state.stage.is(':visible')) {
2308            updateInput$$1(e, data);
2309        }
2310    }
2311    function onDraw(e, data) {
2312        var state = getState$$1(data);
2313        // calculate the frame index
2314        var index = data.lane * data.frames + data.frame;
2315        // get the zoom image. Use original frames as fallback. This won't work for sprite sheets
2316        var source = state.source[index];
2317        var spec = findSpecs(data.metrics, data.frames, data.frame, data.lane);
2318        // get display position
2319        var x = state.currentX;
2320        var y = state.currentY;
2321        // fallback to centered position
2322        if (x == null) {
2323            x = state.currentX = 0.5;
2324            y = state.currentY = 0.5;
2325        }
2326        if (source) {
2327            // scale up from [0:1] to [0:100] range
2328            x = Math.floor(x * 100);
2329            y = Math.floor(y * 100);
2330            // update background image and position
2331            state.stage.css({
2332                'background-repeat': 'no-repeat',
2333                'background-image': "url('" + source + "')",
2334                'background-position': x + "% " + y + "%"
2335            });
2336        }
2337        else if (spec.sheet && spec.sprite) {
2338            var sprite = spec.sprite;
2339            var sheet = spec.sheet;
2340            var src = data.source[sheet.id];
2341            var left = -Math.floor(sprite.sampledX + x * (sprite.sampledWidth - data.width));
2342            var top_1 = -Math.floor(sprite.sampledY + y * (sprite.sampledHeight - data.height));
2343            var width = sheet.sampledWidth;
2344            var height = sheet.sampledHeight;
2345            state.stage.css({
2346                'background-image': "url('" + src + "')",
2347                'background-position': left + "px " + top_1 + "px",
2348                'background-repeat': 'no-repeat',
2349                // set custom background size to enable responsive rendering
2350                '-webkit-background-size': width + "px " + height + "px",
2351                '-moz-background-size': width + "px " + height + "px",
2352                '-o-background-size': width + "px " + height + "px",
2353                'background-size': width + "px " + height + "px" /* Chrome, Firefox 4+, IE 9+, Opera, Safari 5+ */
2354            });
2355        }
2356    }
2357    function toggleZoom(data) {
2358        var state = getState$$1(data);
2359        if (!state.stage) {
2360            throw new Error('zoom module is not initialized or is not available.');
2361        }
2362        if (state.stage.is(':visible')) {
2363            showZoom(data);
2364        }
2365        else {
2366            hideZoom(data);
2367            return true;
2368        }
2369        return false;
2370    }
2371    function showZoom(data) {
2372        var state = getState$$1(data);
2373        state.stage.fadeOut();
2374        data.stage.fadeIn();
2375    }
2376    function hideZoom(data) {
2377        var state = getState$$1(data);
2378        state.stage.fadeIn();
2379        data.stage.fadeOut();
2380    }
2381    function wheel(e, data) {
2382        var state = getState$$1(data);
2383        if (!data.loading && state.useWheel) {
2384            var we = e.originalEvent;
2385            var signY = we.deltaY === 0 ? 0 : we.deltaY > 0 ? 1 : -1;
2386            if (typeof state.useWheel === 'number') {
2387                signY *= state.useWheel;
2388            }
2389            if (state.stage.is(':visible') && signY > 0) {
2390                e.preventDefault();
2391                showZoom(data);
2392            }
2393            if (!state.stage.is(':visible') && signY < 0) {
2394                e.preventDefault();
2395                hideZoom(data);
2396            }
2397        }
2398    }
2399    registerPlugin(NAME, {
2400        name: NAME,
2401        mousedown: onClick,
2402        touchstart: onClick,
2403        mousemove: onMove,
2404        touchmove: onMove,
2405        wheel: wheel,
2406        onInit: onInit,
2407        onDestroy: onDestroy,
2408        onDraw: onDraw
2409    });
2410    extendApi({
2411        toggleZoom: function () { toggleZoom(this.data); } // tslint:disable-line
2412    });
2413})();
2414
2415var Utils = {
2416    $: $$1,
2417    bind: bind,
2418    clamp: clamp,
2419    detectSubsampling: detectSubsampling,
2420    error: error,
2421    findSpecs: findSpecs,
2422    getComputedSize: getComputedSize,
2423    getCursorPosition: getCursorPosition,
2424    getInnerLayout: getInnerLayout,
2425    getInnerSize: getInnerSize,
2426    getOuterSize: getOuterSize,
2427    isFunction: isFunction,
2428    log: log,
2429    measure: measure,
2430    naturalSize: naturalSize,
2431    noop: noop$1,
2432    pixelRatio: pixelRatio,
2433    preload: preload,
2434    prevent: prevent,
2435    sourceArray: sourceArray,
2436    toArray: toArray,
2437    unbind: unbind,
2438    warn: warn,
2439    wrap: wrap
2440};
2441
2442exports.Utils = Utils;
2443exports.sourceArray = sourceArray;
2444exports.Api = Api;
2445exports.extendApi = extendApi;
2446exports.instances = instances;
2447exports.applyEvents = applyEvents;
2448exports.boot = boot;
2449exports.create = create;
2450exports.createOrUpdate = createOrUpdate;
2451exports.destroy = destroy;
2452exports.namespace = namespace;
2453exports.eventNames = eventNames;
2454exports.callbackNames = callbackNames;
2455exports.eventsToPrevent = eventsToPrevent;
2456exports.defaults = defaults;
2457exports.getInputState = getInputState;
2458exports.updateInput = updateInput;
2459exports.resetInput = resetInput;
2460exports.applyLayout = applyLayout;
2461exports.getPlaybackState = getPlaybackState;
2462exports.updateFrame = updateFrame;
2463exports.stopAnimation = stopAnimation;
2464exports.applyAnimation = applyAnimation;
2465exports.startAnimation = startAnimation;
2466exports.registerPlugin = registerPlugin;
2467exports.registerModule = registerModule;
2468exports.getPlugin = getPlugin;
2469exports.applyPlugins = applyPlugins;
2470exports.getState = getState;
2471exports.getPluginState = getPluginState;
2472exports.is = is;
2473exports.flag = flag;
2474
2475Object.defineProperty(exports, '__esModule', { value: true });
2476
2477})));
2478//# sourceMappingURL=spritespin.js.map

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.