]> _ Git - fluidbook-html5.git/commitdiff
#812
authorVincent Vanwaelscappel <vincent@cubedesigners.com>
Fri, 6 Oct 2017 15:30:36 +0000 (17:30 +0200)
committerVincent Vanwaelscappel <vincent@cubedesigners.com>
Fri, 6 Oct 2017 15:30:36 +0000 (17:30 +0200)
js/libs/flashdetect.js [deleted file]
js/libs/hammer.js [deleted file]
js/libs/hammer.min.js [new file with mode: 0644]
js/libs/modernizr/modernizr.js [deleted file]
js/libs/modernizr/modernizr.min.js [new file with mode: 0644]
js/libs/print.min.js [new file with mode: 0644]
js/libs/screenfull.js [deleted file]
js/libs/screenfull.min.js [new file with mode: 0644]

diff --git a/js/libs/flashdetect.js b/js/libs/flashdetect.js
deleted file mode 100644 (file)
index 689a6e3..0000000
+++ /dev/null
@@ -1,200 +0,0 @@
-/*
-Copyright (c) Copyright (c) 2007, Carl S. Yestrau All rights reserved.
-Code licensed under the BSD License: http://www.featureblend.com/license.txt
-Version: 1.0.4
-*/
-var FlashDetect = new function(){
-    var self = this;
-    self.installed = false;
-    self.raw = "";
-    self.major = -1;
-    self.minor = -1;
-    self.revision = -1;
-    self.revisionStr = "";
-    var activeXDetectRules = [
-        {
-            "name":"ShockwaveFlash.ShockwaveFlash.7",
-            "version":function(obj){
-                return getActiveXVersion(obj);
-            }
-        },
-        {
-            "name":"ShockwaveFlash.ShockwaveFlash.6",
-            "version":function(obj){
-                var version = "6,0,21";
-                try{
-                    obj.AllowScriptAccess = "always";
-                    version = getActiveXVersion(obj);
-                }catch(err){}
-                return version;
-            }
-        },
-        {
-            "name":"ShockwaveFlash.ShockwaveFlash",
-            "version":function(obj){
-                return getActiveXVersion(obj);
-            }
-        }
-    ];
-    /**
-     * Extract the ActiveX version of the plugin.
-     * 
-     * @param {Object} The flash ActiveX object.
-     * @type String
-     */
-    var getActiveXVersion = function(activeXObj){
-        var version = -1;
-        try{
-            version = activeXObj.GetVariable("$version");
-        }catch(err){}
-        return version;
-    };
-    /**
-     * Try and retrieve an ActiveX object having a specified name.
-     * 
-     * @param {String} name The ActiveX object name lookup.
-     * @return One of ActiveX object or a simple object having an attribute of activeXError with a value of true.
-     * @type Object
-     */
-    var getActiveXObject = function(name){
-        var obj = -1;
-        try{
-            obj = new ActiveXObject(name);
-        }catch(err){
-            obj = {activeXError:true};
-        }
-        return obj;
-    };
-    /**
-     * Parse an ActiveX $version string into an object.
-     * 
-     * @param {String} str The ActiveX Object GetVariable($version) return value. 
-     * @return An object having raw, major, minor, revision and revisionStr attributes.
-     * @type Object
-     */
-    var parseActiveXVersion = function(str){
-        var versionArray = str.split(",");//replace with regex
-        return {
-            "raw":str,
-            "major":parseInt(versionArray[0].split(" ")[1], 10),
-            "minor":parseInt(versionArray[1], 10),
-            "revision":parseInt(versionArray[2], 10),
-            "revisionStr":versionArray[2]
-        };
-    };
-    /**
-     * Parse a standard enabledPlugin.description into an object.
-     * 
-     * @param {String} str The enabledPlugin.description value.
-     * @return An object having raw, major, minor, revision and revisionStr attributes.
-     * @type Object
-     */
-    var parseStandardVersion = function(str){
-        var descParts = str.split(/ +/);
-        var majorMinor = descParts[2].split(/\./);
-        var revisionStr = descParts[3];
-        return {
-            "raw":str,
-            "major":parseInt(majorMinor[0], 10),
-            "minor":parseInt(majorMinor[1], 10), 
-            "revisionStr":revisionStr,
-            "revision":parseRevisionStrToInt(revisionStr)
-        };
-    };
-    /**
-     * Parse the plugin revision string into an integer.
-     * 
-     * @param {String} The revision in string format.
-     * @type Number
-     */
-    var parseRevisionStrToInt = function(str){
-        return parseInt(str.replace(/[a-zA-Z]/g, ""), 10) || self.revision;
-    };
-    /**
-     * Is the major version greater than or equal to a specified version.
-     * 
-     * @param {Number} version The minimum required major version.
-     * @type Boolean
-     */
-    self.majorAtLeast = function(version){
-        return self.major >= version;
-    };
-    /**
-     * Is the minor version greater than or equal to a specified version.
-     * 
-     * @param {Number} version The minimum required minor version.
-     * @type Boolean
-     */
-    self.minorAtLeast = function(version){
-        return self.minor >= version;
-    };
-    /**
-     * Is the revision version greater than or equal to a specified version.
-     * 
-     * @param {Number} version The minimum required revision version.
-     * @type Boolean
-     */
-    self.revisionAtLeast = function(version){
-        return self.revision >= version;
-    };
-    /**
-     * Is the version greater than or equal to a specified major, minor and revision.
-     * 
-     * @param {Number} major The minimum required major version.
-     * @param {Number} (Optional) minor The minimum required minor version.
-     * @param {Number} (Optional) revision The minimum required revision version.
-     * @type Boolean
-     */
-    self.versionAtLeast = function(major){
-        var properties = [self.major, self.minor, self.revision];
-        var len = Math.min(properties.length, arguments.length);
-        for(i=0; i<len; i++){
-            if(properties[i]>=arguments[i]){
-                if(i+1<len && properties[i]==arguments[i]){
-                    continue;
-                }else{
-                    return true;
-                }
-            }else{
-                return false;
-            }
-        }
-    };
-    /**
-     * Constructor, sets raw, major, minor, revisionStr, revision and installed public properties.
-     */
-    self.FlashDetect = function(){
-        if(navigator.plugins && navigator.plugins.length>0){
-            var type = 'application/x-shockwave-flash';
-            var mimeTypes = navigator.mimeTypes;
-            if(mimeTypes && mimeTypes[type] && mimeTypes[type].enabledPlugin && mimeTypes[type].enabledPlugin.description){
-                var version = mimeTypes[type].enabledPlugin.description;
-                var versionObj = parseStandardVersion(version);
-                self.raw = versionObj.raw;
-                self.major = versionObj.major;
-                self.minor = versionObj.minor; 
-                self.revisionStr = versionObj.revisionStr;
-                self.revision = versionObj.revision;
-                self.installed = true;
-            }
-        }else if(navigator.appVersion.indexOf("Mac")==-1 && window.execScript){
-            var version = -1;
-            for(var i=0; i<activeXDetectRules.length && version==-1; i++){
-                var obj = getActiveXObject(activeXDetectRules[i].name);
-                if(!obj.activeXError){
-                    self.installed = true;
-                    version = activeXDetectRules[i].version(obj);
-                    if(version!=-1){
-                        var versionObj = parseActiveXVersion(version);
-                        self.raw = versionObj.raw;
-                        self.major = versionObj.major;
-                        self.minor = versionObj.minor; 
-                        self.revision = versionObj.revision;
-                        self.revisionStr = versionObj.revisionStr;
-                    }
-                }
-            }
-        }
-    }();
-};
-FlashDetect.JS_RELEASE = "1.0.4";
\ No newline at end of file
diff --git a/js/libs/hammer.js b/js/libs/hammer.js
deleted file mode 100644 (file)
index 0b8febe..0000000
+++ /dev/null
@@ -1,2643 +0,0 @@
-/*! Hammer.JS - v2.0.8 - 2016-04-23
- * http://hammerjs.github.io/
- *
- * Copyright (c) 2016 Jorik Tangelder;
- * Licensed under the MIT license */
-(function(window, document, exportName, undefined) {
-    'use strict';
-
-    var VENDOR_PREFIXES = ['', 'webkit', 'Moz', 'MS', 'ms', 'o'];
-    var TEST_ELEMENT = document.createElement('div');
-
-    var TYPE_FUNCTION = 'function';
-
-    var round = Math.round;
-    var abs = Math.abs;
-    var now = Date.now;
-
-    /**
-     * set a timeout with a given scope
-     * @param {Function} fn
-     * @param {Number} timeout
-     * @param {Object} context
-     * @returns {number}
-     */
-    function setTimeoutContext(fn, timeout, context) {
-        return setTimeout(bindFn(fn, context), timeout);
-    }
-
-    /**
-     * if the argument is an array, we want to execute the fn on each entry
-     * if it aint an array we don't want to do a thing.
-     * this is used by all the methods that accept a single and array argument.
-     * @param {*|Array} arg
-     * @param {String} fn
-     * @param {Object} [context]
-     * @returns {Boolean}
-     */
-    function invokeArrayArg(arg, fn, context) {
-        if (Array.isArray(arg)) {
-            each(arg, context[fn], context);
-            return true;
-        }
-        return false;
-    }
-
-    /**
-     * walk objects and arrays
-     * @param {Object} obj
-     * @param {Function} iterator
-     * @param {Object} context
-     */
-    function each(obj, iterator, context) {
-        var i;
-
-        if (!obj) {
-            return;
-        }
-
-        if (obj.forEach) {
-            obj.forEach(iterator, context);
-        } else if (obj.length !== undefined) {
-            i = 0;
-            while (i < obj.length) {
-                iterator.call(context, obj[i], i, obj);
-                i++;
-            }
-        } else {
-            for (i in obj) {
-                obj.hasOwnProperty(i) && iterator.call(context, obj[i], i, obj);
-            }
-        }
-    }
-
-    /**
-     * wrap a method with a deprecation warning and stack trace
-     * @param {Function} method
-     * @param {String} name
-     * @param {String} message
-     * @returns {Function} A new function wrapping the supplied method.
-     */
-    function deprecate(method, name, message) {
-        var deprecationMessage = 'DEPRECATED METHOD: ' + name + '\n' + message + ' AT \n';
-        return function() {
-            var e = new Error('get-stack-trace');
-            var stack = e && e.stack ? e.stack.replace(/^[^\(]+?[\n$]/gm, '')
-                .replace(/^\s+at\s+/gm, '')
-                .replace(/^Object.<anonymous>\s*\(/gm, '{anonymous}()@') : 'Unknown Stack Trace';
-
-            var log = window.console && (window.console.warn || window.console.log);
-            if (log) {
-                log.call(window.console, deprecationMessage, stack);
-            }
-            return method.apply(this, arguments);
-        };
-    }
-
-    /**
-     * extend object.
-     * means that properties in dest will be overwritten by the ones in src.
-     * @param {Object} target
-     * @param {...Object} objects_to_assign
-     * @returns {Object} target
-     */
-    var assign;
-    if (typeof Object.assign !== 'function') {
-        assign = function assign(target) {
-            if (target === undefined || target === null) {
-                throw new TypeError('Cannot convert undefined or null to object');
-            }
-
-            var output = Object(target);
-            for (var index = 1; index < arguments.length; index++) {
-                var source = arguments[index];
-                if (source !== undefined && source !== null) {
-                    for (var nextKey in source) {
-                        if (source.hasOwnProperty(nextKey)) {
-                            output[nextKey] = source[nextKey];
-                        }
-                    }
-                }
-            }
-            return output;
-        };
-    } else {
-        assign = Object.assign;
-    }
-
-    /**
-     * extend object.
-     * means that properties in dest will be overwritten by the ones in src.
-     * @param {Object} dest
-     * @param {Object} src
-     * @param {Boolean} [merge=false]
-     * @returns {Object} dest
-     */
-    var extend = deprecate(function extend(dest, src, merge) {
-        var keys = Object.keys(src);
-        var i = 0;
-        while (i < keys.length) {
-            if (!merge || (merge && dest[keys[i]] === undefined)) {
-                dest[keys[i]] = src[keys[i]];
-            }
-            i++;
-        }
-        return dest;
-    }, 'extend', 'Use `assign`.');
-
-    /**
-     * merge the values from src in the dest.
-     * means that properties that exist in dest will not be overwritten by src
-     * @param {Object} dest
-     * @param {Object} src
-     * @returns {Object} dest
-     */
-    var merge = deprecate(function merge(dest, src) {
-        return extend(dest, src, true);
-    }, 'merge', 'Use `assign`.');
-
-    /**
-     * simple class inheritance
-     * @param {Function} child
-     * @param {Function} base
-     * @param {Object} [properties]
-     */
-    function inherit(child, base, properties) {
-        var baseP = base.prototype,
-            childP;
-
-        childP = child.prototype = Object.create(baseP);
-        childP.constructor = child;
-        childP._super = baseP;
-
-        if (properties) {
-            assign(childP, properties);
-        }
-    }
-
-    /**
-     * simple function bind
-     * @param {Function} fn
-     * @param {Object} context
-     * @returns {Function}
-     */
-    function bindFn(fn, context) {
-        return function boundFn() {
-            return fn.apply(context, arguments);
-        };
-    }
-
-    /**
-     * let a boolean value also be a function that must return a boolean
-     * this first item in args will be used as the context
-     * @param {Boolean|Function} val
-     * @param {Array} [args]
-     * @returns {Boolean}
-     */
-    function boolOrFn(val, args) {
-        if (typeof val == TYPE_FUNCTION) {
-            return val.apply(args ? args[0] || undefined : undefined, args);
-        }
-        return val;
-    }
-
-    /**
-     * use the val2 when val1 is undefined
-     * @param {*} val1
-     * @param {*} val2
-     * @returns {*}
-     */
-    function ifUndefined(val1, val2) {
-        return (val1 === undefined) ? val2 : val1;
-    }
-
-    /**
-     * addEventListener with multiple events at once
-     * @param {EventTarget} target
-     * @param {String} types
-     * @param {Function} handler
-     */
-    function addEventListeners(target, types, handler) {
-        each(splitStr(types), function(type) {
-            target.addEventListener(type, handler, false);
-        });
-    }
-
-    /**
-     * removeEventListener with multiple events at once
-     * @param {EventTarget} target
-     * @param {String} types
-     * @param {Function} handler
-     */
-    function removeEventListeners(target, types, handler) {
-        each(splitStr(types), function(type) {
-            target.removeEventListener(type, handler, false);
-        });
-    }
-
-    /**
-     * find if a node is in the given parent
-     * @method hasParent
-     * @param {HTMLElement} node
-     * @param {HTMLElement} parent
-     * @return {Boolean} found
-     */
-    function hasParent(node, parent) {
-        while (node) {
-            if (node == parent) {
-                return true;
-            }
-            node = node.parentNode;
-        }
-        return false;
-    }
-
-    /**
-     * small indexOf wrapper
-     * @param {String} str
-     * @param {String} find
-     * @returns {Boolean} found
-     */
-    function inStr(str, find) {
-        return str.indexOf(find) > -1;
-    }
-
-    /**
-     * split string on whitespace
-     * @param {String} str
-     * @returns {Array} words
-     */
-    function splitStr(str) {
-        return str.trim().split(/\s+/g);
-    }
-
-    /**
-     * find if a array contains the object using indexOf or a simple polyFill
-     * @param {Array} src
-     * @param {String} find
-     * @param {String} [findByKey]
-     * @return {Boolean|Number} false when not found, or the index
-     */
-    function inArray(src, find, findByKey) {
-        if (src.indexOf && !findByKey) {
-            return src.indexOf(find);
-        } else {
-            var i = 0;
-            while (i < src.length) {
-                if ((findByKey && src[i][findByKey] == find) || (!findByKey && src[i] === find)) {
-                    return i;
-                }
-                i++;
-            }
-            return -1;
-        }
-    }
-
-    /**
-     * convert array-like objects to real arrays
-     * @param {Object} obj
-     * @returns {Array}
-     */
-    function toArray(obj) {
-        return Array.prototype.slice.call(obj, 0);
-    }
-
-    /**
-     * unique array with objects based on a key (like 'id') or just by the array's value
-     * @param {Array} src [{id:1},{id:2},{id:1}]
-     * @param {String} [key]
-     * @param {Boolean} [sort=False]
-     * @returns {Array} [{id:1},{id:2}]
-     */
-    function uniqueArray(src, key, sort) {
-        var results = [];
-        var values = [];
-        var i = 0;
-
-        while (i < src.length) {
-            var val = key ? src[i][key] : src[i];
-            if (inArray(values, val) < 0) {
-                results.push(src[i]);
-            }
-            values[i] = val;
-            i++;
-        }
-
-        if (sort) {
-            if (!key) {
-                results = results.sort();
-            } else {
-                results = results.sort(function sortUniqueArray(a, b) {
-                    return a[key] > b[key];
-                });
-            }
-        }
-
-        return results;
-    }
-
-    /**
-     * get the prefixed property
-     * @param {Object} obj
-     * @param {String} property
-     * @returns {String|Undefined} prefixed
-     */
-    function prefixed(obj, property) {
-        var prefix, prop;
-        var camelProp = property[0].toUpperCase() + property.slice(1);
-
-        var i = 0;
-        while (i < VENDOR_PREFIXES.length) {
-            prefix = VENDOR_PREFIXES[i];
-            prop = (prefix) ? prefix + camelProp : property;
-
-            if (prop in obj) {
-                return prop;
-            }
-            i++;
-        }
-        return undefined;
-    }
-
-    /**
-     * get a unique id
-     * @returns {number} uniqueId
-     */
-    var _uniqueId = 1;
-    function uniqueId() {
-        return _uniqueId++;
-    }
-
-    /**
-     * get the window object of an element
-     * @param {HTMLElement} element
-     * @returns {DocumentView|Window}
-     */
-    function getWindowForElement(element) {
-        var doc = element.ownerDocument || element;
-        return (doc.defaultView || doc.parentWindow || window);
-    }
-
-    var MOBILE_REGEX = /mobile|tablet|ip(ad|hone|od)|android/i;
-
-    var SUPPORT_TOUCH = ('ontouchstart' in window);
-    var SUPPORT_POINTER_EVENTS = prefixed(window, 'PointerEvent') !== undefined;
-    var SUPPORT_ONLY_TOUCH = SUPPORT_TOUCH && MOBILE_REGEX.test(navigator.userAgent);
-
-    var INPUT_TYPE_TOUCH = 'touch';
-    var INPUT_TYPE_PEN = 'pen';
-    var INPUT_TYPE_MOUSE = 'mouse';
-    var INPUT_TYPE_KINECT = 'kinect';
-
-    var COMPUTE_INTERVAL = 25;
-
-    var INPUT_START = 1;
-    var INPUT_MOVE = 2;
-    var INPUT_END = 4;
-    var INPUT_CANCEL = 8;
-
-    var DIRECTION_NONE = 1;
-    var DIRECTION_LEFT = 2;
-    var DIRECTION_RIGHT = 4;
-    var DIRECTION_UP = 8;
-    var DIRECTION_DOWN = 16;
-
-    var DIRECTION_HORIZONTAL = DIRECTION_LEFT | DIRECTION_RIGHT;
-    var DIRECTION_VERTICAL = DIRECTION_UP | DIRECTION_DOWN;
-    var DIRECTION_ALL = DIRECTION_HORIZONTAL | DIRECTION_VERTICAL;
-
-    var PROPS_XY = ['x', 'y'];
-    var PROPS_CLIENT_XY = ['clientX', 'clientY'];
-
-    /**
-     * create new input type manager
-     * @param {Manager} manager
-     * @param {Function} callback
-     * @returns {Input}
-     * @constructor
-     */
-    function Input(manager, callback) {
-        var self = this;
-        this.manager = manager;
-        this.callback = callback;
-        this.element = manager.element;
-        this.target = manager.options.inputTarget;
-
-        // smaller wrapper around the handler, for the scope and the enabled state of the manager,
-        // so when disabled the input events are completely bypassed.
-        this.domHandler = function(ev) {
-            if (boolOrFn(manager.options.enable, [manager])) {
-                self.handler(ev);
-            }
-        };
-
-        this.init();
-
-    }
-
-    Input.prototype = {
-        /**
-         * should handle the inputEvent data and trigger the callback
-         * @virtual
-         */
-        handler: function() { },
-
-        /**
-         * bind the events
-         */
-        init: function() {
-            this.evEl && addEventListeners(this.element, this.evEl, this.domHandler);
-            this.evTarget && addEventListeners(this.target, this.evTarget, this.domHandler);
-            this.evWin && addEventListeners(getWindowForElement(this.element), this.evWin, this.domHandler);
-        },
-
-        /**
-         * unbind the events
-         */
-        destroy: function() {
-            this.evEl && removeEventListeners(this.element, this.evEl, this.domHandler);
-            this.evTarget && removeEventListeners(this.target, this.evTarget, this.domHandler);
-            this.evWin && removeEventListeners(getWindowForElement(this.element), this.evWin, this.domHandler);
-        }
-    };
-
-    /**
-     * create new input type manager
-     * called by the Manager constructor
-     * @param {Hammer} manager
-     * @returns {Input}
-     */
-    function createInputInstance(manager) {
-        var Type;
-        var inputClass = manager.options.inputClass;
-
-        if (inputClass) {
-            Type = inputClass;
-        } else if (SUPPORT_POINTER_EVENTS) {
-            Type = PointerEventInput;
-        } else if (SUPPORT_ONLY_TOUCH) {
-            Type = TouchInput;
-        } else if (!SUPPORT_TOUCH) {
-            Type = MouseInput;
-        } else {
-            Type = TouchMouseInput;
-        }
-        return new (Type)(manager, inputHandler);
-    }
-
-    /**
-     * handle input events
-     * @param {Manager} manager
-     * @param {String} eventType
-     * @param {Object} input
-     */
-    function inputHandler(manager, eventType, input) {
-        var pointersLen = input.pointers.length;
-        var changedPointersLen = input.changedPointers.length;
-        var isFirst = (eventType & INPUT_START && (pointersLen - changedPointersLen === 0));
-        var isFinal = (eventType & (INPUT_END | INPUT_CANCEL) && (pointersLen - changedPointersLen === 0));
-
-        input.isFirst = !!isFirst;
-        input.isFinal = !!isFinal;
-
-        if (isFirst) {
-            manager.session = {};
-        }
-
-        // source event is the normalized value of the domEvents
-        // like 'touchstart, mouseup, pointerdown'
-        input.eventType = eventType;
-
-        // compute scale, rotation etc
-        computeInputData(manager, input);
-
-        // emit secret event
-        manager.emit('hammer.input', input);
-
-        manager.recognize(input);
-        manager.session.prevInput = input;
-    }
-
-    /**
-     * extend the data with some usable properties like scale, rotate, velocity etc
-     * @param {Object} manager
-     * @param {Object} input
-     */
-    function computeInputData(manager, input) {
-        var session = manager.session;
-        var pointers = input.pointers;
-        var pointersLength = pointers.length;
-
-        // store the first input to calculate the distance and direction
-        if (!session.firstInput) {
-            session.firstInput = simpleCloneInputData(input);
-        }
-
-        // to compute scale and rotation we need to store the multiple touches
-        if (pointersLength > 1 && !session.firstMultiple) {
-            session.firstMultiple = simpleCloneInputData(input);
-        } else if (pointersLength === 1) {
-            session.firstMultiple = false;
-        }
-
-        var firstInput = session.firstInput;
-        var firstMultiple = session.firstMultiple;
-        var offsetCenter = firstMultiple ? firstMultiple.center : firstInput.center;
-
-        var center = input.center = getCenter(pointers);
-        input.timeStamp = now();
-        input.deltaTime = input.timeStamp - firstInput.timeStamp;
-
-        input.angle = getAngle(offsetCenter, center);
-        input.distance = getDistance(offsetCenter, center);
-
-        computeDeltaXY(session, input);
-        input.offsetDirection = getDirection(input.deltaX, input.deltaY);
-
-        var overallVelocity = getVelocity(input.deltaTime, input.deltaX, input.deltaY);
-        input.overallVelocityX = overallVelocity.x;
-        input.overallVelocityY = overallVelocity.y;
-        input.overallVelocity = (abs(overallVelocity.x) > abs(overallVelocity.y)) ? overallVelocity.x : overallVelocity.y;
-
-        input.scale = firstMultiple ? getScale(firstMultiple.pointers, pointers) : 1;
-        input.rotation = firstMultiple ? getRotation(firstMultiple.pointers, pointers) : 0;
-
-        input.maxPointers = !session.prevInput ? input.pointers.length : ((input.pointers.length >
-        session.prevInput.maxPointers) ? input.pointers.length : session.prevInput.maxPointers);
-
-        computeIntervalInputData(session, input);
-
-        // find the correct target
-        var target = manager.element;
-        if (hasParent(input.srcEvent.target, target)) {
-            target = input.srcEvent.target;
-        }
-        input.target = target;
-    }
-
-    function computeDeltaXY(session, input) {
-        var center = input.center;
-        var offset = session.offsetDelta || {};
-        var prevDelta = session.prevDelta || {};
-        var prevInput = session.prevInput || {};
-
-        if (input.eventType === INPUT_START || prevInput.eventType === INPUT_END) {
-            prevDelta = session.prevDelta = {
-                x: prevInput.deltaX || 0,
-                y: prevInput.deltaY || 0
-            };
-
-            offset = session.offsetDelta = {
-                x: center.x,
-                y: center.y
-            };
-        }
-
-        input.deltaX = prevDelta.x + (center.x - offset.x);
-        input.deltaY = prevDelta.y + (center.y - offset.y);
-    }
-
-    /**
-     * velocity is calculated every x ms
-     * @param {Object} session
-     * @param {Object} input
-     */
-    function computeIntervalInputData(session, input) {
-        var last = session.lastInterval || input,
-            deltaTime = input.timeStamp - last.timeStamp,
-            velocity, velocityX, velocityY, direction;
-
-        if (input.eventType != INPUT_CANCEL && (deltaTime > COMPUTE_INTERVAL || last.velocity === undefined)) {
-            var deltaX = input.deltaX - last.deltaX;
-            var deltaY = input.deltaY - last.deltaY;
-
-            var v = getVelocity(deltaTime, deltaX, deltaY);
-            velocityX = v.x;
-            velocityY = v.y;
-            velocity = (abs(v.x) > abs(v.y)) ? v.x : v.y;
-            direction = getDirection(deltaX, deltaY);
-
-            session.lastInterval = input;
-        } else {
-            // use latest velocity info if it doesn't overtake a minimum period
-            velocity = last.velocity;
-            velocityX = last.velocityX;
-            velocityY = last.velocityY;
-            direction = last.direction;
-        }
-
-        input.velocity = velocity;
-        input.velocityX = velocityX;
-        input.velocityY = velocityY;
-        input.direction = direction;
-    }
-
-    /**
-     * create a simple clone from the input used for storage of firstInput and firstMultiple
-     * @param {Object} input
-     * @returns {Object} clonedInputData
-     */
-    function simpleCloneInputData(input) {
-        // make a simple copy of the pointers because we will get a reference if we don't
-        // we only need clientXY for the calculations
-        var pointers = [];
-        var i = 0;
-        while (i < input.pointers.length) {
-            pointers[i] = {
-                clientX: round(input.pointers[i].clientX),
-                clientY: round(input.pointers[i].clientY)
-            };
-            i++;
-        }
-
-        return {
-            timeStamp: now(),
-            pointers: pointers,
-            center: getCenter(pointers),
-            deltaX: input.deltaX,
-            deltaY: input.deltaY
-        };
-    }
-
-    /**
-     * get the center of all the pointers
-     * @param {Array} pointers
-     * @return {Object} center contains `x` and `y` properties
-     */
-    function getCenter(pointers) {
-        var pointersLength = pointers.length;
-
-        // no need to loop when only one touch
-        if (pointersLength === 1) {
-            return {
-                x: round(pointers[0].clientX),
-                y: round(pointers[0].clientY)
-            };
-        }
-
-        var x = 0, y = 0, i = 0;
-        while (i < pointersLength) {
-            x += pointers[i].clientX;
-            y += pointers[i].clientY;
-            i++;
-        }
-
-        return {
-            x: round(x / pointersLength),
-            y: round(y / pointersLength)
-        };
-    }
-
-    /**
-     * calculate the velocity between two points. unit is in px per ms.
-     * @param {Number} deltaTime
-     * @param {Number} x
-     * @param {Number} y
-     * @return {Object} velocity `x` and `y`
-     */
-    function getVelocity(deltaTime, x, y) {
-        return {
-            x: x / deltaTime || 0,
-            y: y / deltaTime || 0
-        };
-    }
-
-    /**
-     * get the direction between two points
-     * @param {Number} x
-     * @param {Number} y
-     * @return {Number} direction
-     */
-    function getDirection(x, y) {
-        if (x === y) {
-            return DIRECTION_NONE;
-        }
-
-        if (abs(x) >= abs(y)) {
-            return x < 0 ? DIRECTION_LEFT : DIRECTION_RIGHT;
-        }
-        return y < 0 ? DIRECTION_UP : DIRECTION_DOWN;
-    }
-
-    /**
-     * calculate the absolute distance between two points
-     * @param {Object} p1 {x, y}
-     * @param {Object} p2 {x, y}
-     * @param {Array} [props] containing x and y keys
-     * @return {Number} distance
-     */
-    function getDistance(p1, p2, props) {
-        if (!props) {
-            props = PROPS_XY;
-        }
-        var x = p2[props[0]] - p1[props[0]],
-            y = p2[props[1]] - p1[props[1]];
-
-        return Math.sqrt((x * x) + (y * y));
-    }
-
-    /**
-     * calculate the angle between two coordinates
-     * @param {Object} p1
-     * @param {Object} p2
-     * @param {Array} [props] containing x and y keys
-     * @return {Number} angle
-     */
-    function getAngle(p1, p2, props) {
-        if (!props) {
-            props = PROPS_XY;
-        }
-        var x = p2[props[0]] - p1[props[0]],
-            y = p2[props[1]] - p1[props[1]];
-        return Math.atan2(y, x) * 180 / Math.PI;
-    }
-
-    /**
-     * calculate the rotation degrees between two pointersets
-     * @param {Array} start array of pointers
-     * @param {Array} end array of pointers
-     * @return {Number} rotation
-     */
-    function getRotation(start, end) {
-        return getAngle(end[1], end[0], PROPS_CLIENT_XY) + getAngle(start[1], start[0], PROPS_CLIENT_XY);
-    }
-
-    /**
-     * calculate the scale factor between two pointersets
-     * no scale is 1, and goes down to 0 when pinched together, and bigger when pinched out
-     * @param {Array} start array of pointers
-     * @param {Array} end array of pointers
-     * @return {Number} scale
-     */
-    function getScale(start, end) {
-        return getDistance(end[0], end[1], PROPS_CLIENT_XY) / getDistance(start[0], start[1], PROPS_CLIENT_XY);
-    }
-
-    var MOUSE_INPUT_MAP = {
-        mousedown: INPUT_START,
-        mousemove: INPUT_MOVE,
-        mouseup: INPUT_END
-    };
-
-    var MOUSE_ELEMENT_EVENTS = 'mousedown';
-    var MOUSE_WINDOW_EVENTS = 'mousemove mouseup';
-
-    /**
-     * Mouse events input
-     * @constructor
-     * @extends Input
-     */
-    function MouseInput() {
-        this.evEl = MOUSE_ELEMENT_EVENTS;
-        this.evWin = MOUSE_WINDOW_EVENTS;
-
-        this.pressed = false; // mousedown state
-
-        Input.apply(this, arguments);
-    }
-
-    inherit(MouseInput, Input, {
-        /**
-         * handle mouse events
-         * @param {Object} ev
-         */
-        handler: function MEhandler(ev) {
-            var eventType = MOUSE_INPUT_MAP[ev.type];
-
-            // on start we want to have the left mouse button down
-            if (eventType & INPUT_START && ev.button === 0) {
-                this.pressed = true;
-            }
-
-            if (eventType & INPUT_MOVE && ev.which !== 1) {
-                eventType = INPUT_END;
-            }
-
-            // mouse must be down
-            if (!this.pressed) {
-                return;
-            }
-
-            if (eventType & INPUT_END) {
-                this.pressed = false;
-            }
-
-            this.callback(this.manager, eventType, {
-                pointers: [ev],
-                changedPointers: [ev],
-                pointerType: INPUT_TYPE_MOUSE,
-                srcEvent: ev
-            });
-        }
-    });
-
-    var POINTER_INPUT_MAP = {
-        pointerdown: INPUT_START,
-        pointermove: INPUT_MOVE,
-        pointerup: INPUT_END,
-        pointercancel: INPUT_CANCEL,
-        pointerout: INPUT_CANCEL
-    };
-
-// in IE10 the pointer types is defined as an enum
-    var IE10_POINTER_TYPE_ENUM = {
-        2: INPUT_TYPE_TOUCH,
-        3: INPUT_TYPE_PEN,
-        4: INPUT_TYPE_MOUSE,
-        5: INPUT_TYPE_KINECT // see https://twitter.com/jacobrossi/status/480596438489890816
-    };
-
-    var POINTER_ELEMENT_EVENTS = 'pointerdown';
-    var POINTER_WINDOW_EVENTS = 'pointermove pointerup pointercancel';
-
-// IE10 has prefixed support, and case-sensitive
-    if (window.MSPointerEvent && !window.PointerEvent) {
-        POINTER_ELEMENT_EVENTS = 'MSPointerDown';
-        POINTER_WINDOW_EVENTS = 'MSPointerMove MSPointerUp MSPointerCancel';
-    }
-
-    /**
-     * Pointer events input
-     * @constructor
-     * @extends Input
-     */
-    function PointerEventInput() {
-        this.evEl = POINTER_ELEMENT_EVENTS;
-        this.evWin = POINTER_WINDOW_EVENTS;
-
-        Input.apply(this, arguments);
-
-        this.store = (this.manager.session.pointerEvents = []);
-    }
-
-    inherit(PointerEventInput, Input, {
-        /**
-         * handle mouse events
-         * @param {Object} ev
-         */
-        handler: function PEhandler(ev) {
-            var store = this.store;
-            var removePointer = false;
-
-            var eventTypeNormalized = ev.type.toLowerCase().replace('ms', '');
-            var eventType = POINTER_INPUT_MAP[eventTypeNormalized];
-            var pointerType = IE10_POINTER_TYPE_ENUM[ev.pointerType] || ev.pointerType;
-
-            var isTouch = (pointerType == INPUT_TYPE_TOUCH);
-
-            // get index of the event in the store
-            var storeIndex = inArray(store, ev.pointerId, 'pointerId');
-
-            // start and mouse must be down
-            if (eventType & INPUT_START && (ev.button === 0 || isTouch)) {
-                if (storeIndex < 0) {
-                    store.push(ev);
-                    storeIndex = store.length - 1;
-                }
-            } else if (eventType & (INPUT_END | INPUT_CANCEL)) {
-                removePointer = true;
-            }
-
-            // it not found, so the pointer hasn't been down (so it's probably a hover)
-            if (storeIndex < 0) {
-                return;
-            }
-
-            // update the event in the store
-            store[storeIndex] = ev;
-
-            this.callback(this.manager, eventType, {
-                pointers: store,
-                changedPointers: [ev],
-                pointerType: pointerType,
-                srcEvent: ev
-            });
-
-            if (removePointer) {
-                // remove from the store
-                store.splice(storeIndex, 1);
-            }
-        }
-    });
-
-    var SINGLE_TOUCH_INPUT_MAP = {
-        touchstart: INPUT_START,
-        touchmove: INPUT_MOVE,
-        touchend: INPUT_END,
-        touchcancel: INPUT_CANCEL
-    };
-
-    var SINGLE_TOUCH_TARGET_EVENTS = 'touchstart';
-    var SINGLE_TOUCH_WINDOW_EVENTS = 'touchstart touchmove touchend touchcancel';
-
-    /**
-     * Touch events input
-     * @constructor
-     * @extends Input
-     */
-    function SingleTouchInput() {
-        this.evTarget = SINGLE_TOUCH_TARGET_EVENTS;
-        this.evWin = SINGLE_TOUCH_WINDOW_EVENTS;
-        this.started = false;
-
-        Input.apply(this, arguments);
-    }
-
-    inherit(SingleTouchInput, Input, {
-        handler: function TEhandler(ev) {
-            var type = SINGLE_TOUCH_INPUT_MAP[ev.type];
-
-            // should we handle the touch events?
-            if (type === INPUT_START) {
-                this.started = true;
-            }
-
-            if (!this.started) {
-                return;
-            }
-
-            var touches = normalizeSingleTouches.call(this, ev, type);
-
-            // when done, reset the started state
-            if (type & (INPUT_END | INPUT_CANCEL) && touches[0].length - touches[1].length === 0) {
-                this.started = false;
-            }
-
-            this.callback(this.manager, type, {
-                pointers: touches[0],
-                changedPointers: touches[1],
-                pointerType: INPUT_TYPE_TOUCH,
-                srcEvent: ev
-            });
-        }
-    });
-
-    /**
-     * @this {TouchInput}
-     * @param {Object} ev
-     * @param {Number} type flag
-     * @returns {undefined|Array} [all, changed]
-     */
-    function normalizeSingleTouches(ev, type) {
-        var all = toArray(ev.touches);
-        var changed = toArray(ev.changedTouches);
-
-        if (type & (INPUT_END | INPUT_CANCEL)) {
-            all = uniqueArray(all.concat(changed), 'identifier', true);
-        }
-
-        return [all, changed];
-    }
-
-    var TOUCH_INPUT_MAP = {
-        touchstart: INPUT_START,
-        touchmove: INPUT_MOVE,
-        touchend: INPUT_END,
-        touchcancel: INPUT_CANCEL
-    };
-
-    var TOUCH_TARGET_EVENTS = 'touchstart touchmove touchend touchcancel';
-
-    /**
-     * Multi-user touch events input
-     * @constructor
-     * @extends Input
-     */
-    function TouchInput() {
-        this.evTarget = TOUCH_TARGET_EVENTS;
-        this.targetIds = {};
-
-        Input.apply(this, arguments);
-    }
-
-    inherit(TouchInput, Input, {
-        handler: function MTEhandler(ev) {
-            var type = TOUCH_INPUT_MAP[ev.type];
-            var touches = getTouches.call(this, ev, type);
-            if (!touches) {
-                return;
-            }
-
-            this.callback(this.manager, type, {
-                pointers: touches[0],
-                changedPointers: touches[1],
-                pointerType: INPUT_TYPE_TOUCH,
-                srcEvent: ev
-            });
-        }
-    });
-
-    /**
-     * @this {TouchInput}
-     * @param {Object} ev
-     * @param {Number} type flag
-     * @returns {undefined|Array} [all, changed]
-     */
-    function getTouches(ev, type) {
-        var allTouches = toArray(ev.touches);
-        var targetIds = this.targetIds;
-
-        // when there is only one touch, the process can be simplified
-        if (type & (INPUT_START | INPUT_MOVE) && allTouches.length === 1) {
-            targetIds[allTouches[0].identifier] = true;
-            return [allTouches, allTouches];
-        }
-
-        var i,
-            targetTouches,
-            changedTouches = toArray(ev.changedTouches),
-            changedTargetTouches = [],
-            target = this.target;
-
-        // get target touches from touches
-        targetTouches = allTouches.filter(function(touch) {
-            return hasParent(touch.target, target);
-        });
-
-        // collect touches
-        if (type === INPUT_START) {
-            i = 0;
-            while (i < targetTouches.length) {
-                targetIds[targetTouches[i].identifier] = true;
-                i++;
-            }
-        }
-
-        // filter changed touches to only contain touches that exist in the collected target ids
-        i = 0;
-        while (i < changedTouches.length) {
-            if (targetIds[changedTouches[i].identifier]) {
-                changedTargetTouches.push(changedTouches[i]);
-            }
-
-            // cleanup removed touches
-            if (type & (INPUT_END | INPUT_CANCEL)) {
-                delete targetIds[changedTouches[i].identifier];
-            }
-            i++;
-        }
-
-        if (!changedTargetTouches.length) {
-            return;
-        }
-
-        return [
-            // merge targetTouches with changedTargetTouches so it contains ALL touches, including 'end' and 'cancel'
-            uniqueArray(targetTouches.concat(changedTargetTouches), 'identifier', true),
-            changedTargetTouches
-        ];
-    }
-
-    /**
-     * Combined touch and mouse input
-     *
-     * Touch has a higher priority then mouse, and while touching no mouse events are allowed.
-     * This because touch devices also emit mouse events while doing a touch.
-     *
-     * @constructor
-     * @extends Input
-     */
-
-    var DEDUP_TIMEOUT = 2500;
-    var DEDUP_DISTANCE = 25;
-
-    function TouchMouseInput() {
-        Input.apply(this, arguments);
-
-        var handler = bindFn(this.handler, this);
-        this.touch = new TouchInput(this.manager, handler);
-        this.mouse = new MouseInput(this.manager, handler);
-
-        this.primaryTouch = null;
-        this.lastTouches = [];
-    }
-
-    inherit(TouchMouseInput, Input, {
-        /**
-         * handle mouse and touch events
-         * @param {Hammer} manager
-         * @param {String} inputEvent
-         * @param {Object} inputData
-         */
-        handler: function TMEhandler(manager, inputEvent, inputData) {
-            var isTouch = (inputData.pointerType == INPUT_TYPE_TOUCH),
-                isMouse = (inputData.pointerType == INPUT_TYPE_MOUSE);
-
-            if (isMouse && inputData.sourceCapabilities && inputData.sourceCapabilities.firesTouchEvents) {
-                return;
-            }
-
-            // when we're in a touch event, record touches to  de-dupe synthetic mouse event
-            if (isTouch) {
-                recordTouches.call(this, inputEvent, inputData);
-            } else if (isMouse && isSyntheticEvent.call(this, inputData)) {
-                return;
-            }
-
-            this.callback(manager, inputEvent, inputData);
-        },
-
-        /**
-         * remove the event listeners
-         */
-        destroy: function destroy() {
-            this.touch.destroy();
-            this.mouse.destroy();
-        }
-    });
-
-    function recordTouches(eventType, eventData) {
-        if (eventType & INPUT_START) {
-            this.primaryTouch = eventData.changedPointers[0].identifier;
-            setLastTouch.call(this, eventData);
-        } else if (eventType & (INPUT_END | INPUT_CANCEL)) {
-            setLastTouch.call(this, eventData);
-        }
-    }
-
-    function setLastTouch(eventData) {
-        var touch = eventData.changedPointers[0];
-
-        if (touch.identifier === this.primaryTouch) {
-            var lastTouch = {x: touch.clientX, y: touch.clientY};
-            this.lastTouches.push(lastTouch);
-            var lts = this.lastTouches;
-            var removeLastTouch = function() {
-                var i = lts.indexOf(lastTouch);
-                if (i > -1) {
-                    lts.splice(i, 1);
-                }
-            };
-            setTimeout(removeLastTouch, DEDUP_TIMEOUT);
-        }
-    }
-
-    function isSyntheticEvent(eventData) {
-        var x = eventData.srcEvent.clientX, y = eventData.srcEvent.clientY;
-        for (var i = 0; i < this.lastTouches.length; i++) {
-            var t = this.lastTouches[i];
-            var dx = Math.abs(x - t.x), dy = Math.abs(y - t.y);
-            if (dx <= DEDUP_DISTANCE && dy <= DEDUP_DISTANCE) {
-                return true;
-            }
-        }
-        return false;
-    }
-
-    var PREFIXED_TOUCH_ACTION = prefixed(TEST_ELEMENT.style, 'touchAction');
-    var NATIVE_TOUCH_ACTION = PREFIXED_TOUCH_ACTION !== undefined;
-
-// magical touchAction value
-    var TOUCH_ACTION_COMPUTE = 'compute';
-    var TOUCH_ACTION_AUTO = 'auto';
-    var TOUCH_ACTION_MANIPULATION = 'manipulation'; // not implemented
-    var TOUCH_ACTION_NONE = 'none';
-    var TOUCH_ACTION_PAN_X = 'pan-x';
-    var TOUCH_ACTION_PAN_Y = 'pan-y';
-    var TOUCH_ACTION_MAP = getTouchActionProps();
-
-    /**
-     * Touch Action
-     * sets the touchAction property or uses the js alternative
-     * @param {Manager} manager
-     * @param {String} value
-     * @constructor
-     */
-    function TouchAction(manager, value) {
-        this.manager = manager;
-        this.set(value);
-    }
-
-    TouchAction.prototype = {
-        /**
-         * set the touchAction value on the element or enable the polyfill
-         * @param {String} value
-         */
-        set: function(value) {
-            // find out the touch-action by the event handlers
-            if (value == TOUCH_ACTION_COMPUTE) {
-                value = this.compute();
-            }
-
-            if (NATIVE_TOUCH_ACTION && this.manager.element.style && TOUCH_ACTION_MAP[value]) {
-                this.manager.element.style[PREFIXED_TOUCH_ACTION] = value;
-            }
-            this.actions = value.toLowerCase().trim();
-        },
-
-        /**
-         * just re-set the touchAction value
-         */
-        update: function() {
-            this.set(this.manager.options.touchAction);
-        },
-
-        /**
-         * compute the value for the touchAction property based on the recognizer's settings
-         * @returns {String} value
-         */
-        compute: function() {
-            var actions = [];
-            each(this.manager.recognizers, function(recognizer) {
-                if (boolOrFn(recognizer.options.enable, [recognizer])) {
-                    actions = actions.concat(recognizer.getTouchAction());
-                }
-            });
-            return cleanTouchActions(actions.join(' '));
-        },
-
-        /**
-         * this method is called on each input cycle and provides the preventing of the browser behavior
-         * @param {Object} input
-         */
-        preventDefaults: function(input) {
-            var srcEvent = input.srcEvent;
-            var direction = input.offsetDirection;
-
-            // if the touch action did prevented once this session
-            if (this.manager.session.prevented) {
-                srcEvent.preventDefault();
-                return;
-            }
-
-            var actions = this.actions;
-            var hasNone = inStr(actions, TOUCH_ACTION_NONE) && !TOUCH_ACTION_MAP[TOUCH_ACTION_NONE];
-            var hasPanY = inStr(actions, TOUCH_ACTION_PAN_Y) && !TOUCH_ACTION_MAP[TOUCH_ACTION_PAN_Y];
-            var hasPanX = inStr(actions, TOUCH_ACTION_PAN_X) && !TOUCH_ACTION_MAP[TOUCH_ACTION_PAN_X];
-
-            if (hasNone) {
-                //do not prevent defaults if this is a tap gesture
-
-                var isTapPointer = input.pointers.length === 1;
-                var isTapMovement = input.distance < 2;
-                var isTapTouchTime = input.deltaTime < 250;
-
-                if (isTapPointer && isTapMovement && isTapTouchTime) {
-                    return;
-                }
-            }
-
-            if (hasPanX && hasPanY) {
-                // `pan-x pan-y` means browser handles all scrolling/panning, do not prevent
-                return;
-            }
-
-            if (hasNone ||
-                (hasPanY && direction & DIRECTION_HORIZONTAL) ||
-                (hasPanX && direction & DIRECTION_VERTICAL)) {
-                return this.preventSrc(srcEvent);
-            }
-        },
-
-        /**
-         * call preventDefault to prevent the browser's default behavior (scrolling in most cases)
-         * @param {Object} srcEvent
-         */
-        preventSrc: function(srcEvent) {
-            this.manager.session.prevented = true;
-            srcEvent.preventDefault();
-        }
-    };
-
-    /**
-     * when the touchActions are collected they are not a valid value, so we need to clean things up. *
-     * @param {String} actions
-     * @returns {*}
-     */
-    function cleanTouchActions(actions) {
-        // none
-        if (inStr(actions, TOUCH_ACTION_NONE)) {
-            return TOUCH_ACTION_NONE;
-        }
-
-        var hasPanX = inStr(actions, TOUCH_ACTION_PAN_X);
-        var hasPanY = inStr(actions, TOUCH_ACTION_PAN_Y);
-
-        // if both pan-x and pan-y are set (different recognizers
-        // for different directions, e.g. horizontal pan but vertical swipe?)
-        // we need none (as otherwise with pan-x pan-y combined none of these
-        // recognizers will work, since the browser would handle all panning
-        if (hasPanX && hasPanY) {
-            return TOUCH_ACTION_NONE;
-        }
-
-        // pan-x OR pan-y
-        if (hasPanX || hasPanY) {
-            return hasPanX ? TOUCH_ACTION_PAN_X : TOUCH_ACTION_PAN_Y;
-        }
-
-        // manipulation
-        if (inStr(actions, TOUCH_ACTION_MANIPULATION)) {
-            return TOUCH_ACTION_MANIPULATION;
-        }
-
-        return TOUCH_ACTION_AUTO;
-    }
-
-    function getTouchActionProps() {
-        if (!NATIVE_TOUCH_ACTION) {
-            return false;
-        }
-        var touchMap = {};
-        var cssSupports = window.CSS && window.CSS.supports;
-        ['auto', 'manipulation', 'pan-y', 'pan-x', 'pan-x pan-y', 'none'].forEach(function(val) {
-
-            // If css.supports is not supported but there is native touch-action assume it supports
-            // all values. This is the case for IE 10 and 11.
-            touchMap[val] = cssSupports ? window.CSS.supports('touch-action', val) : true;
-        });
-        return touchMap;
-    }
-
-    /**
-     * Recognizer flow explained; *
-     * All recognizers have the initial state of POSSIBLE when a input session starts.
-     * The definition of a input session is from the first input until the last input, with all it's movement in it. *
-     * Example session for mouse-input: mousedown -> mousemove -> mouseup
-     *
-     * On each recognizing cycle (see Manager.recognize) the .recognize() method is executed
-     * which determines with state it should be.
-     *
-     * If the recognizer has the state FAILED, CANCELLED or RECOGNIZED (equals ENDED), it is reset to
-     * POSSIBLE to give it another change on the next cycle.
-     *
-     *               Possible
-     *                  |
-     *            +-----+---------------+
-     *            |                     |
-     *      +-----+-----+               |
-     *      |           |               |
-     *   Failed      Cancelled          |
-     *                          +-------+------+
-     *                          |              |
-     *                      Recognized       Began
-     *                                         |
-     *                                      Changed
-     *                                         |
-     *                                  Ended/Recognized
-     */
-    var STATE_POSSIBLE = 1;
-    var STATE_BEGAN = 2;
-    var STATE_CHANGED = 4;
-    var STATE_ENDED = 8;
-    var STATE_RECOGNIZED = STATE_ENDED;
-    var STATE_CANCELLED = 16;
-    var STATE_FAILED = 32;
-
-    /**
-     * Recognizer
-     * Every recognizer needs to extend from this class.
-     * @constructor
-     * @param {Object} options
-     */
-    function Recognizer(options) {
-        this.options = assign({}, this.defaults, options || {});
-
-        this.id = uniqueId();
-
-        this.manager = null;
-
-        // default is enable true
-        this.options.enable = ifUndefined(this.options.enable, true);
-
-        this.state = STATE_POSSIBLE;
-
-        this.simultaneous = {};
-        this.requireFail = [];
-    }
-
-    Recognizer.prototype = {
-        /**
-         * @virtual
-         * @type {Object}
-         */
-        defaults: {},
-
-        /**
-         * set options
-         * @param {Object} options
-         * @return {Recognizer}
-         */
-        set: function(options) {
-            assign(this.options, options);
-
-            // also update the touchAction, in case something changed about the directions/enabled state
-            this.manager && this.manager.touchAction.update();
-            return this;
-        },
-
-        /**
-         * recognize simultaneous with an other recognizer.
-         * @param {Recognizer} otherRecognizer
-         * @returns {Recognizer} this
-         */
-        recognizeWith: function(otherRecognizer) {
-            if (invokeArrayArg(otherRecognizer, 'recognizeWith', this)) {
-                return this;
-            }
-
-            var simultaneous = this.simultaneous;
-            otherRecognizer = getRecognizerByNameIfManager(otherRecognizer, this);
-            if (!simultaneous[otherRecognizer.id]) {
-                simultaneous[otherRecognizer.id] = otherRecognizer;
-                otherRecognizer.recognizeWith(this);
-            }
-            return this;
-        },
-
-        /**
-         * drop the simultaneous link. it doesnt remove the link on the other recognizer.
-         * @param {Recognizer} otherRecognizer
-         * @returns {Recognizer} this
-         */
-        dropRecognizeWith: function(otherRecognizer) {
-            if (invokeArrayArg(otherRecognizer, 'dropRecognizeWith', this)) {
-                return this;
-            }
-
-            otherRecognizer = getRecognizerByNameIfManager(otherRecognizer, this);
-            delete this.simultaneous[otherRecognizer.id];
-            return this;
-        },
-
-        /**
-         * recognizer can only run when an other is failing
-         * @param {Recognizer} otherRecognizer
-         * @returns {Recognizer} this
-         */
-        requireFailure: function(otherRecognizer) {
-            if (invokeArrayArg(otherRecognizer, 'requireFailure', this)) {
-                return this;
-            }
-
-            var requireFail = this.requireFail;
-            otherRecognizer = getRecognizerByNameIfManager(otherRecognizer, this);
-            if (inArray(requireFail, otherRecognizer) === -1) {
-                requireFail.push(otherRecognizer);
-                otherRecognizer.requireFailure(this);
-            }
-            return this;
-        },
-
-        /**
-         * drop the requireFailure link. it does not remove the link on the other recognizer.
-         * @param {Recognizer} otherRecognizer
-         * @returns {Recognizer} this
-         */
-        dropRequireFailure: function(otherRecognizer) {
-            if (invokeArrayArg(otherRecognizer, 'dropRequireFailure', this)) {
-                return this;
-            }
-
-            otherRecognizer = getRecognizerByNameIfManager(otherRecognizer, this);
-            var index = inArray(this.requireFail, otherRecognizer);
-            if (index > -1) {
-                this.requireFail.splice(index, 1);
-            }
-            return this;
-        },
-
-        /**
-         * has require failures boolean
-         * @returns {boolean}
-         */
-        hasRequireFailures: function() {
-            return this.requireFail.length > 0;
-        },
-
-        /**
-         * if the recognizer can recognize simultaneous with an other recognizer
-         * @param {Recognizer} otherRecognizer
-         * @returns {Boolean}
-         */
-        canRecognizeWith: function(otherRecognizer) {
-            return !!this.simultaneous[otherRecognizer.id];
-        },
-
-        /**
-         * You should use `tryEmit` instead of `emit` directly to check
-         * that all the needed recognizers has failed before emitting.
-         * @param {Object} input
-         */
-        emit: function(input) {
-            var self = this;
-            var state = this.state;
-
-            function emit(event) {
-                self.manager.emit(event, input);
-            }
-
-            // 'panstart' and 'panmove'
-            if (state < STATE_ENDED) {
-                emit(self.options.event + stateStr(state));
-            }
-
-            emit(self.options.event); // simple 'eventName' events
-
-            if (input.additionalEvent) { // additional event(panleft, panright, pinchin, pinchout...)
-                emit(input.additionalEvent);
-            }
-
-            // panend and pancancel
-            if (state >= STATE_ENDED) {
-                emit(self.options.event + stateStr(state));
-            }
-        },
-
-        /**
-         * Check that all the require failure recognizers has failed,
-         * if true, it emits a gesture event,
-         * otherwise, setup the state to FAILED.
-         * @param {Object} input
-         */
-        tryEmit: function(input) {
-            if (this.canEmit()) {
-                return this.emit(input);
-            }
-            // it's failing anyway
-            this.state = STATE_FAILED;
-        },
-
-        /**
-         * can we emit?
-         * @returns {boolean}
-         */
-        canEmit: function() {
-            var i = 0;
-            while (i < this.requireFail.length) {
-                if (!(this.requireFail[i].state & (STATE_FAILED | STATE_POSSIBLE))) {
-                    return false;
-                }
-                i++;
-            }
-            return true;
-        },
-
-        /**
-         * update the recognizer
-         * @param {Object} inputData
-         */
-        recognize: function(inputData) {
-            // make a new copy of the inputData
-            // so we can change the inputData without messing up the other recognizers
-            var inputDataClone = assign({}, inputData);
-
-            // is is enabled and allow recognizing?
-            if (!boolOrFn(this.options.enable, [this, inputDataClone])) {
-                this.reset();
-                this.state = STATE_FAILED;
-                return;
-            }
-
-            // reset when we've reached the end
-            if (this.state & (STATE_RECOGNIZED | STATE_CANCELLED | STATE_FAILED)) {
-                this.state = STATE_POSSIBLE;
-            }
-
-            this.state = this.process(inputDataClone);
-
-            // the recognizer has recognized a gesture
-            // so trigger an event
-            if (this.state & (STATE_BEGAN | STATE_CHANGED | STATE_ENDED | STATE_CANCELLED)) {
-                this.tryEmit(inputDataClone);
-            }
-        },
-
-        /**
-         * return the state of the recognizer
-         * the actual recognizing happens in this method
-         * @virtual
-         * @param {Object} inputData
-         * @returns {Const} STATE
-         */
-        process: function(inputData) { }, // jshint ignore:line
-
-        /**
-         * return the preferred touch-action
-         * @virtual
-         * @returns {Array}
-         */
-        getTouchAction: function() { },
-
-        /**
-         * called when the gesture isn't allowed to recognize
-         * like when another is being recognized or it is disabled
-         * @virtual
-         */
-        reset: function() { }
-    };
-
-    /**
-     * get a usable string, used as event postfix
-     * @param {Const} state
-     * @returns {String} state
-     */
-    function stateStr(state) {
-        if (state & STATE_CANCELLED) {
-            return 'cancel';
-        } else if (state & STATE_ENDED) {
-            return 'end';
-        } else if (state & STATE_CHANGED) {
-            return 'move';
-        } else if (state & STATE_BEGAN) {
-            return 'start';
-        }
-        return '';
-    }
-
-    /**
-     * direction cons to string
-     * @param {Const} direction
-     * @returns {String}
-     */
-    function directionStr(direction) {
-        if (direction == DIRECTION_DOWN) {
-            return 'down';
-        } else if (direction == DIRECTION_UP) {
-            return 'up';
-        } else if (direction == DIRECTION_LEFT) {
-            return 'left';
-        } else if (direction == DIRECTION_RIGHT) {
-            return 'right';
-        }
-        return '';
-    }
-
-    /**
-     * get a recognizer by name if it is bound to a manager
-     * @param {Recognizer|String} otherRecognizer
-     * @param {Recognizer} recognizer
-     * @returns {Recognizer}
-     */
-    function getRecognizerByNameIfManager(otherRecognizer, recognizer) {
-        var manager = recognizer.manager;
-        if (manager) {
-            return manager.get(otherRecognizer);
-        }
-        return otherRecognizer;
-    }
-
-    /**
-     * This recognizer is just used as a base for the simple attribute recognizers.
-     * @constructor
-     * @extends Recognizer
-     */
-    function AttrRecognizer() {
-        Recognizer.apply(this, arguments);
-    }
-
-    inherit(AttrRecognizer, Recognizer, {
-        /**
-         * @namespace
-         * @memberof AttrRecognizer
-         */
-        defaults: {
-            /**
-             * @type {Number}
-             * @default 1
-             */
-            pointers: 1
-        },
-
-        /**
-         * Used to check if it the recognizer receives valid input, like input.distance > 10.
-         * @memberof AttrRecognizer
-         * @param {Object} input
-         * @returns {Boolean} recognized
-         */
-        attrTest: function(input) {
-            var optionPointers = this.options.pointers;
-            return optionPointers === 0 || input.pointers.length === optionPointers;
-        },
-
-        /**
-         * Process the input and return the state for the recognizer
-         * @memberof AttrRecognizer
-         * @param {Object} input
-         * @returns {*} State
-         */
-        process: function(input) {
-            var state = this.state;
-            var eventType = input.eventType;
-
-            var isRecognized = state & (STATE_BEGAN | STATE_CHANGED);
-            var isValid = this.attrTest(input);
-
-            // on cancel input and we've recognized before, return STATE_CANCELLED
-            if (isRecognized && (eventType & INPUT_CANCEL || !isValid)) {
-                return state | STATE_CANCELLED;
-            } else if (isRecognized || isValid) {
-                if (eventType & INPUT_END) {
-                    return state | STATE_ENDED;
-                } else if (!(state & STATE_BEGAN)) {
-                    return STATE_BEGAN;
-                }
-                return state | STATE_CHANGED;
-            }
-            return STATE_FAILED;
-        }
-    });
-
-    /**
-     * Pan
-     * Recognized when the pointer is down and moved in the allowed direction.
-     * @constructor
-     * @extends AttrRecognizer
-     */
-    function PanRecognizer() {
-        AttrRecognizer.apply(this, arguments);
-
-        this.pX = null;
-        this.pY = null;
-    }
-
-    inherit(PanRecognizer, AttrRecognizer, {
-        /**
-         * @namespace
-         * @memberof PanRecognizer
-         */
-        defaults: {
-            event: 'pan',
-            threshold: 10,
-            pointers: 1,
-            direction: DIRECTION_ALL
-        },
-
-        getTouchAction: function() {
-            var direction = this.options.direction;
-            var actions = [];
-            if (direction & DIRECTION_HORIZONTAL) {
-                actions.push(TOUCH_ACTION_PAN_Y);
-            }
-            if (direction & DIRECTION_VERTICAL) {
-                actions.push(TOUCH_ACTION_PAN_X);
-            }
-            return actions;
-        },
-
-        directionTest: function(input) {
-            var options = this.options;
-            var hasMoved = true;
-            var distance = input.distance;
-            var direction = input.direction;
-            var x = input.deltaX;
-            var y = input.deltaY;
-
-            // lock to axis?
-            if (!(direction & options.direction)) {
-                if (options.direction & DIRECTION_HORIZONTAL) {
-                    direction = (x === 0) ? DIRECTION_NONE : (x < 0) ? DIRECTION_LEFT : DIRECTION_RIGHT;
-                    hasMoved = x != this.pX;
-                    distance = Math.abs(input.deltaX);
-                } else {
-                    direction = (y === 0) ? DIRECTION_NONE : (y < 0) ? DIRECTION_UP : DIRECTION_DOWN;
-                    hasMoved = y != this.pY;
-                    distance = Math.abs(input.deltaY);
-                }
-            }
-            input.direction = direction;
-            return hasMoved && distance > options.threshold && direction & options.direction;
-        },
-
-        attrTest: function(input) {
-            return AttrRecognizer.prototype.attrTest.call(this, input) &&
-                (this.state & STATE_BEGAN || (!(this.state & STATE_BEGAN) && this.directionTest(input)));
-        },
-
-        emit: function(input) {
-
-            this.pX = input.deltaX;
-            this.pY = input.deltaY;
-
-            var direction = directionStr(input.direction);
-
-            if (direction) {
-                input.additionalEvent = this.options.event + direction;
-            }
-            this._super.emit.call(this, input);
-        }
-    });
-
-    /**
-     * Pinch
-     * Recognized when two or more pointers are moving toward (zoom-in) or away from each other (zoom-out).
-     * @constructor
-     * @extends AttrRecognizer
-     */
-    function PinchRecognizer() {
-        AttrRecognizer.apply(this, arguments);
-    }
-
-    inherit(PinchRecognizer, AttrRecognizer, {
-        /**
-         * @namespace
-         * @memberof PinchRecognizer
-         */
-        defaults: {
-            event: 'pinch',
-            threshold: 0,
-            pointers: 2
-        },
-
-        getTouchAction: function() {
-            return [TOUCH_ACTION_NONE];
-        },
-
-        attrTest: function(input) {
-            return this._super.attrTest.call(this, input) &&
-                (Math.abs(input.scale - 1) > this.options.threshold || this.state & STATE_BEGAN);
-        },
-
-        emit: function(input) {
-            if (input.scale !== 1) {
-                var inOut = input.scale < 1 ? 'in' : 'out';
-                input.additionalEvent = this.options.event + inOut;
-            }
-            this._super.emit.call(this, input);
-        }
-    });
-
-    /**
-     * Press
-     * Recognized when the pointer is down for x ms without any movement.
-     * @constructor
-     * @extends Recognizer
-     */
-    function PressRecognizer() {
-        Recognizer.apply(this, arguments);
-
-        this._timer = null;
-        this._input = null;
-    }
-
-    inherit(PressRecognizer, Recognizer, {
-        /**
-         * @namespace
-         * @memberof PressRecognizer
-         */
-        defaults: {
-            event: 'press',
-            pointers: 1,
-            time: 251, // minimal time of the pointer to be pressed
-            threshold: 9 // a minimal movement is ok, but keep it low
-        },
-
-        getTouchAction: function() {
-            return [TOUCH_ACTION_AUTO];
-        },
-
-        process: function(input) {
-            var options = this.options;
-            var validPointers = input.pointers.length === options.pointers;
-            var validMovement = input.distance < options.threshold;
-            var validTime = input.deltaTime > options.time;
-
-            this._input = input;
-
-            // we only allow little movement
-            // and we've reached an end event, so a tap is possible
-            if (!validMovement || !validPointers || (input.eventType & (INPUT_END | INPUT_CANCEL) && !validTime)) {
-                this.reset();
-            } else if (input.eventType & INPUT_START) {
-                this.reset();
-                this._timer = setTimeoutContext(function() {
-                    this.state = STATE_RECOGNIZED;
-                    this.tryEmit();
-                }, options.time, this);
-            } else if (input.eventType & INPUT_END) {
-                return STATE_RECOGNIZED;
-            }
-            return STATE_FAILED;
-        },
-
-        reset: function() {
-            clearTimeout(this._timer);
-        },
-
-        emit: function(input) {
-            if (this.state !== STATE_RECOGNIZED) {
-                return;
-            }
-
-            if (input && (input.eventType & INPUT_END)) {
-                this.manager.emit(this.options.event + 'up', input);
-            } else {
-                this._input.timeStamp = now();
-                this.manager.emit(this.options.event, this._input);
-            }
-        }
-    });
-
-    /**
-     * Rotate
-     * Recognized when two or more pointer are moving in a circular motion.
-     * @constructor
-     * @extends AttrRecognizer
-     */
-    function RotateRecognizer() {
-        AttrRecognizer.apply(this, arguments);
-    }
-
-    inherit(RotateRecognizer, AttrRecognizer, {
-        /**
-         * @namespace
-         * @memberof RotateRecognizer
-         */
-        defaults: {
-            event: 'rotate',
-            threshold: 0,
-            pointers: 2
-        },
-
-        getTouchAction: function() {
-            return [TOUCH_ACTION_NONE];
-        },
-
-        attrTest: function(input) {
-            return this._super.attrTest.call(this, input) &&
-                (Math.abs(input.rotation) > this.options.threshold || this.state & STATE_BEGAN);
-        }
-    });
-
-    /**
-     * Swipe
-     * Recognized when the pointer is moving fast (velocity), with enough distance in the allowed direction.
-     * @constructor
-     * @extends AttrRecognizer
-     */
-    function SwipeRecognizer() {
-        AttrRecognizer.apply(this, arguments);
-    }
-
-    inherit(SwipeRecognizer, AttrRecognizer, {
-        /**
-         * @namespace
-         * @memberof SwipeRecognizer
-         */
-        defaults: {
-            event: 'swipe',
-            threshold: 10,
-            velocity: 0.3,
-            direction: DIRECTION_HORIZONTAL | DIRECTION_VERTICAL,
-            pointers: 1
-        },
-
-        getTouchAction: function() {
-            return PanRecognizer.prototype.getTouchAction.call(this);
-        },
-
-        attrTest: function(input) {
-            var direction = this.options.direction;
-            var velocity;
-
-            if (direction & (DIRECTION_HORIZONTAL | DIRECTION_VERTICAL)) {
-                velocity = input.overallVelocity;
-            } else if (direction & DIRECTION_HORIZONTAL) {
-                velocity = input.overallVelocityX;
-            } else if (direction & DIRECTION_VERTICAL) {
-                velocity = input.overallVelocityY;
-            }
-
-            return this._super.attrTest.call(this, input) &&
-                direction & input.offsetDirection &&
-                input.distance > this.options.threshold &&
-                input.maxPointers == this.options.pointers &&
-                abs(velocity) > this.options.velocity && input.eventType & INPUT_END;
-        },
-
-        emit: function(input) {
-            var direction = directionStr(input.offsetDirection);
-            if (direction) {
-                this.manager.emit(this.options.event + direction, input);
-            }
-
-            this.manager.emit(this.options.event, input);
-        }
-    });
-
-    /**
-     * A tap is ecognized when the pointer is doing a small tap/click. Multiple taps are recognized if they occur
-     * between the given interval and position. The delay option can be used to recognize multi-taps without firing
-     * a single tap.
-     *
-     * The eventData from the emitted event contains the property `tapCount`, which contains the amount of
-     * multi-taps being recognized.
-     * @constructor
-     * @extends Recognizer
-     */
-    function TapRecognizer() {
-        Recognizer.apply(this, arguments);
-
-        // previous time and center,
-        // used for tap counting
-        this.pTime = false;
-        this.pCenter = false;
-
-        this._timer = null;
-        this._input = null;
-        this.count = 0;
-    }
-
-    inherit(TapRecognizer, Recognizer, {
-        /**
-         * @namespace
-         * @memberof PinchRecognizer
-         */
-        defaults: {
-            event: 'tap',
-            pointers: 1,
-            taps: 1,
-            interval: 300, // max time between the multi-tap taps
-            time: 250, // max time of the pointer to be down (like finger on the screen)
-            threshold: 9, // a minimal movement is ok, but keep it low
-            posThreshold: 10 // a multi-tap can be a bit off the initial position
-        },
-
-        getTouchAction: function() {
-            return [TOUCH_ACTION_MANIPULATION];
-        },
-
-        process: function(input) {
-            var options = this.options;
-
-            var validPointers = input.pointers.length === options.pointers;
-            var validMovement = input.distance < options.threshold;
-            var validTouchTime = input.deltaTime < options.time;
-
-            this.reset();
-
-            if ((input.eventType & INPUT_START) && (this.count === 0)) {
-                return this.failTimeout();
-            }
-
-            // we only allow little movement
-            // and we've reached an end event, so a tap is possible
-            if (validMovement && validTouchTime && validPointers) {
-                if (input.eventType != INPUT_END) {
-                    return this.failTimeout();
-                }
-
-                var validInterval = this.pTime ? (input.timeStamp - this.pTime < options.interval) : true;
-                var validMultiTap = !this.pCenter || getDistance(this.pCenter, input.center) < options.posThreshold;
-
-                this.pTime = input.timeStamp;
-                this.pCenter = input.center;
-
-                if (!validMultiTap || !validInterval) {
-                    this.count = 1;
-                } else {
-                    this.count += 1;
-                }
-
-                this._input = input;
-
-                // if tap count matches we have recognized it,
-                // else it has began recognizing...
-                var tapCount = this.count % options.taps;
-                if (tapCount === 0) {
-                    // no failing requirements, immediately trigger the tap event
-                    // or wait as long as the multitap interval to trigger
-                    if (!this.hasRequireFailures()) {
-                        return STATE_RECOGNIZED;
-                    } else {
-                        this._timer = setTimeoutContext(function() {
-                            this.state = STATE_RECOGNIZED;
-                            this.tryEmit();
-                        }, options.interval, this);
-                        return STATE_BEGAN;
-                    }
-                }
-            }
-            return STATE_FAILED;
-        },
-
-        failTimeout: function() {
-            this._timer = setTimeoutContext(function() {
-                this.state = STATE_FAILED;
-            }, this.options.interval, this);
-            return STATE_FAILED;
-        },
-
-        reset: function() {
-            clearTimeout(this._timer);
-        },
-
-        emit: function() {
-            if (this.state == STATE_RECOGNIZED) {
-                this._input.tapCount = this.count;
-                this.manager.emit(this.options.event, this._input);
-            }
-        }
-    });
-
-    /**
-     * Simple way to create a manager with a default set of recognizers.
-     * @param {HTMLElement} element
-     * @param {Object} [options]
-     * @constructor
-     */
-    function Hammer(element, options) {
-        options = options || {};
-        options.recognizers = ifUndefined(options.recognizers, Hammer.defaults.preset);
-        return new Manager(element, options);
-    }
-
-    /**
-     * @const {string}
-     */
-    Hammer.VERSION = '2.0.8';
-
-    /**
-     * default settings
-     * @namespace
-     */
-    Hammer.defaults = {
-        /**
-         * set if DOM events are being triggered.
-         * But this is slower and unused by simple implementations, so disabled by default.
-         * @type {Boolean}
-         * @default false
-         */
-        domEvents: false,
-
-        /**
-         * The value for the touchAction property/fallback.
-         * When set to `compute` it will magically set the correct value based on the added recognizers.
-         * @type {String}
-         * @default compute
-         */
-        touchAction: TOUCH_ACTION_COMPUTE,
-
-        /**
-         * @type {Boolean}
-         * @default true
-         */
-        enable: true,
-
-        /**
-         * EXPERIMENTAL FEATURE -- can be removed/changed
-         * Change the parent input target element.
-         * If Null, then it is being set the to main element.
-         * @type {Null|EventTarget}
-         * @default null
-         */
-        inputTarget: null,
-
-        /**
-         * force an input class
-         * @type {Null|Function}
-         * @default null
-         */
-        inputClass: null,
-
-        /**
-         * Default recognizer setup when calling `Hammer()`
-         * When creating a new Manager these will be skipped.
-         * @type {Array}
-         */
-        preset: [
-            // RecognizerClass, options, [recognizeWith, ...], [requireFailure, ...]
-            [RotateRecognizer, {enable: false}],
-            [PinchRecognizer, {enable: false}, ['rotate']],
-            [SwipeRecognizer, {direction: DIRECTION_HORIZONTAL}],
-            [PanRecognizer, {direction: DIRECTION_HORIZONTAL}, ['swipe']],
-            [TapRecognizer],
-            [TapRecognizer, {event: 'doubletap', taps: 2}, ['tap']],
-            [PressRecognizer]
-        ],
-
-        /**
-         * Some CSS properties can be used to improve the working of Hammer.
-         * Add them to this method and they will be set when creating a new Manager.
-         * @namespace
-         */
-        cssProps: {
-            /**
-             * Disables text selection to improve the dragging gesture. Mainly for desktop browsers.
-             * @type {String}
-             * @default 'none'
-             */
-            userSelect: 'none',
-
-            /**
-             * Disable the Windows Phone grippers when pressing an element.
-             * @type {String}
-             * @default 'none'
-             */
-            touchSelect: 'none',
-
-            /**
-             * Disables the default callout shown when you touch and hold a touch target.
-             * On iOS, when you touch and hold a touch target such as a link, Safari displays
-             * a callout containing information about the link. This property allows you to disable that callout.
-             * @type {String}
-             * @default 'none'
-             */
-            touchCallout: 'none',
-
-            /**
-             * Specifies whether zooming is enabled. Used by IE10>
-             * @type {String}
-             * @default 'none'
-             */
-            contentZooming: 'none',
-
-            /**
-             * Specifies that an entire element should be draggable instead of its contents. Mainly for desktop browsers.
-             * @type {String}
-             * @default 'none'
-             */
-            userDrag: 'none',
-
-            /**
-             * Overrides the highlight color shown when the user taps a link or a JavaScript
-             * clickable element in iOS. This property obeys the alpha value, if specified.
-             * @type {String}
-             * @default 'rgba(0,0,0,0)'
-             */
-            tapHighlightColor: 'rgba(0,0,0,0)'
-        }
-    };
-
-    var STOP = 1;
-    var FORCED_STOP = 2;
-
-    /**
-     * Manager
-     * @param {HTMLElement} element
-     * @param {Object} [options]
-     * @constructor
-     */
-    function Manager(element, options) {
-        this.options = assign({}, Hammer.defaults, options || {});
-
-        this.options.inputTarget = this.options.inputTarget || element;
-
-        this.handlers = {};
-        this.session = {};
-        this.recognizers = [];
-        this.oldCssProps = {};
-
-        this.element = element;
-        this.input = createInputInstance(this);
-        this.touchAction = new TouchAction(this, this.options.touchAction);
-
-        toggleCssProps(this, true);
-
-        each(this.options.recognizers, function(item) {
-            var recognizer = this.add(new (item[0])(item[1]));
-            item[2] && recognizer.recognizeWith(item[2]);
-            item[3] && recognizer.requireFailure(item[3]);
-        }, this);
-    }
-
-    Manager.prototype = {
-        /**
-         * set options
-         * @param {Object} options
-         * @returns {Manager}
-         */
-        set: function(options) {
-            assign(this.options, options);
-
-            // Options that need a little more setup
-            if (options.touchAction) {
-                this.touchAction.update();
-            }
-            if (options.inputTarget) {
-                // Clean up existing event listeners and reinitialize
-                this.input.destroy();
-                this.input.target = options.inputTarget;
-                this.input.init();
-            }
-            return this;
-        },
-
-        /**
-         * stop recognizing for this session.
-         * This session will be discarded, when a new [input]start event is fired.
-         * When forced, the recognizer cycle is stopped immediately.
-         * @param {Boolean} [force]
-         */
-        stop: function(force) {
-            this.session.stopped = force ? FORCED_STOP : STOP;
-        },
-
-        /**
-         * run the recognizers!
-         * called by the inputHandler function on every movement of the pointers (touches)
-         * it walks through all the recognizers and tries to detect the gesture that is being made
-         * @param {Object} inputData
-         */
-        recognize: function(inputData) {
-            var session = this.session;
-            if (session.stopped) {
-                return;
-            }
-
-            // run the touch-action polyfill
-            this.touchAction.preventDefaults(inputData);
-
-            var recognizer;
-            var recognizers = this.recognizers;
-
-            // this holds the recognizer that is being recognized.
-            // so the recognizer's state needs to be BEGAN, CHANGED, ENDED or RECOGNIZED
-            // if no recognizer is detecting a thing, it is set to `null`
-            var curRecognizer = session.curRecognizer;
-
-            // reset when the last recognizer is recognized
-            // or when we're in a new session
-            if (!curRecognizer || (curRecognizer && curRecognizer.state & STATE_RECOGNIZED)) {
-                curRecognizer = session.curRecognizer = null;
-            }
-
-            var i = 0;
-            while (i < recognizers.length) {
-                recognizer = recognizers[i];
-
-                // find out if we are allowed try to recognize the input for this one.
-                // 1.   allow if the session is NOT forced stopped (see the .stop() method)
-                // 2.   allow if we still haven't recognized a gesture in this session, or the this recognizer is the one
-                //      that is being recognized.
-                // 3.   allow if the recognizer is allowed to run simultaneous with the current recognized recognizer.
-                //      this can be setup with the `recognizeWith()` method on the recognizer.
-                if (session.stopped !== FORCED_STOP && ( // 1
-                    !curRecognizer || recognizer == curRecognizer || // 2
-                    recognizer.canRecognizeWith(curRecognizer))) { // 3
-                    recognizer.recognize(inputData);
-                } else {
-                    recognizer.reset();
-                }
-
-                // if the recognizer has been recognizing the input as a valid gesture, we want to store this one as the
-                // current active recognizer. but only if we don't already have an active recognizer
-                if (!curRecognizer && recognizer.state & (STATE_BEGAN | STATE_CHANGED | STATE_ENDED)) {
-                    curRecognizer = session.curRecognizer = recognizer;
-                }
-                i++;
-            }
-        },
-
-        /**
-         * get a recognizer by its event name.
-         * @param {Recognizer|String} recognizer
-         * @returns {Recognizer|Null}
-         */
-        get: function(recognizer) {
-            if (recognizer instanceof Recognizer) {
-                return recognizer;
-            }
-
-            var recognizers = this.recognizers;
-            for (var i = 0; i < recognizers.length; i++) {
-                if (recognizers[i].options.event == recognizer) {
-                    return recognizers[i];
-                }
-            }
-            return null;
-        },
-
-        /**
-         * add a recognizer to the manager
-         * existing recognizers with the same event name will be removed
-         * @param {Recognizer} recognizer
-         * @returns {Recognizer|Manager}
-         */
-        add: function(recognizer) {
-            if (invokeArrayArg(recognizer, 'add', this)) {
-                return this;
-            }
-
-            // remove existing
-            var existing = this.get(recognizer.options.event);
-            if (existing) {
-                this.remove(existing);
-            }
-
-            this.recognizers.push(recognizer);
-            recognizer.manager = this;
-
-            this.touchAction.update();
-            return recognizer;
-        },
-
-        /**
-         * remove a recognizer by name or instance
-         * @param {Recognizer|String} recognizer
-         * @returns {Manager}
-         */
-        remove: function(recognizer) {
-            if (invokeArrayArg(recognizer, 'remove', this)) {
-                return this;
-            }
-
-            recognizer = this.get(recognizer);
-
-            // let's make sure this recognizer exists
-            if (recognizer) {
-                var recognizers = this.recognizers;
-                var index = inArray(recognizers, recognizer);
-
-                if (index !== -1) {
-                    recognizers.splice(index, 1);
-                    this.touchAction.update();
-                }
-            }
-
-            return this;
-        },
-
-        /**
-         * bind event
-         * @param {String} events
-         * @param {Function} handler
-         * @returns {EventEmitter} this
-         */
-        on: function(events, handler) {
-            if (events === undefined) {
-                return;
-            }
-            if (handler === undefined) {
-                return;
-            }
-
-            var handlers = this.handlers;
-            each(splitStr(events), function(event) {
-                handlers[event] = handlers[event] || [];
-                handlers[event].push(handler);
-            });
-            return this;
-        },
-
-        /**
-         * unbind event, leave emit blank to remove all handlers
-         * @param {String} events
-         * @param {Function} [handler]
-         * @returns {EventEmitter} this
-         */
-        off: function(events, handler) {
-            if (events === undefined) {
-                return;
-            }
-
-            var handlers = this.handlers;
-            each(splitStr(events), function(event) {
-                if (!handler) {
-                    delete handlers[event];
-                } else {
-                    handlers[event] && handlers[event].splice(inArray(handlers[event], handler), 1);
-                }
-            });
-            return this;
-        },
-
-        /**
-         * emit event to the listeners
-         * @param {String} event
-         * @param {Object} data
-         */
-        emit: function(event, data) {
-            // we also want to trigger dom events
-            if (this.options.domEvents) {
-                triggerDomEvent(event, data);
-            }
-
-            // no handlers, so skip it all
-            var handlers = this.handlers[event] && this.handlers[event].slice();
-            if (!handlers || !handlers.length) {
-                return;
-            }
-
-            data.type = event;
-            data.preventDefault = function() {
-                data.srcEvent.preventDefault();
-            };
-
-            var i = 0;
-            while (i < handlers.length) {
-                handlers[i](data);
-                i++;
-            }
-        },
-
-        /**
-         * destroy the manager and unbinds all events
-         * it doesn't unbind dom events, that is the user own responsibility
-         */
-        destroy: function() {
-            this.element && toggleCssProps(this, false);
-
-            this.handlers = {};
-            this.session = {};
-            this.input.destroy();
-            this.element = null;
-        }
-    };
-
-    /**
-     * add/remove the css properties as defined in manager.options.cssProps
-     * @param {Manager} manager
-     * @param {Boolean} add
-     */
-    function toggleCssProps(manager, add) {
-        var element = manager.element;
-        if (!element.style) {
-            return;
-        }
-        var prop;
-        each(manager.options.cssProps, function(value, name) {
-            prop = prefixed(element.style, name);
-            if (add) {
-                manager.oldCssProps[prop] = element.style[prop];
-                element.style[prop] = value;
-            } else {
-                element.style[prop] = manager.oldCssProps[prop] || '';
-            }
-        });
-        if (!add) {
-            manager.oldCssProps = {};
-        }
-    }
-
-    /**
-     * trigger dom event
-     * @param {String} event
-     * @param {Object} data
-     */
-    function triggerDomEvent(event, data) {
-        var gestureEvent = document.createEvent('Event');
-        gestureEvent.initEvent(event, true, true);
-        gestureEvent.gesture = data;
-        data.target.dispatchEvent(gestureEvent);
-    }
-
-    assign(Hammer, {
-        INPUT_START: INPUT_START,
-        INPUT_MOVE: INPUT_MOVE,
-        INPUT_END: INPUT_END,
-        INPUT_CANCEL: INPUT_CANCEL,
-
-        STATE_POSSIBLE: STATE_POSSIBLE,
-        STATE_BEGAN: STATE_BEGAN,
-        STATE_CHANGED: STATE_CHANGED,
-        STATE_ENDED: STATE_ENDED,
-        STATE_RECOGNIZED: STATE_RECOGNIZED,
-        STATE_CANCELLED: STATE_CANCELLED,
-        STATE_FAILED: STATE_FAILED,
-
-        DIRECTION_NONE: DIRECTION_NONE,
-        DIRECTION_LEFT: DIRECTION_LEFT,
-        DIRECTION_RIGHT: DIRECTION_RIGHT,
-        DIRECTION_UP: DIRECTION_UP,
-        DIRECTION_DOWN: DIRECTION_DOWN,
-        DIRECTION_HORIZONTAL: DIRECTION_HORIZONTAL,
-        DIRECTION_VERTICAL: DIRECTION_VERTICAL,
-        DIRECTION_ALL: DIRECTION_ALL,
-
-        Manager: Manager,
-        Input: Input,
-        TouchAction: TouchAction,
-
-        TouchInput: TouchInput,
-        MouseInput: MouseInput,
-        PointerEventInput: PointerEventInput,
-        TouchMouseInput: TouchMouseInput,
-        SingleTouchInput: SingleTouchInput,
-
-        Recognizer: Recognizer,
-        AttrRecognizer: AttrRecognizer,
-        Tap: TapRecognizer,
-        Pan: PanRecognizer,
-        Swipe: SwipeRecognizer,
-        Pinch: PinchRecognizer,
-        Rotate: RotateRecognizer,
-        Press: PressRecognizer,
-
-        on: addEventListeners,
-        off: removeEventListeners,
-        each: each,
-        merge: merge,
-        extend: extend,
-        assign: assign,
-        inherit: inherit,
-        bindFn: bindFn,
-        prefixed: prefixed
-    });
-
-// this prevents errors when Hammer is loaded in the presence of an AMD
-//  style loader but by script tag, not by the loader.
-    var freeGlobal = (typeof window !== 'undefined' ? window : (typeof self !== 'undefined' ? self : {})); // jshint ignore:line
-    freeGlobal.Hammer = Hammer;
-
-    if (typeof define === 'function' && define.amd) {
-        define(function() {
-            return Hammer;
-        });
-    } else if (typeof module != 'undefined' && module.exports) {
-        module.exports = Hammer;
-    } else {
-        window[exportName] = Hammer;
-    }
-
-})(window, document, 'Hammer');
diff --git a/js/libs/hammer.min.js b/js/libs/hammer.min.js
new file mode 100644 (file)
index 0000000..edadee1
--- /dev/null
@@ -0,0 +1,7 @@
+/*! Hammer.JS - v2.0.8 - 2016-04-23
+ * http://hammerjs.github.io/
+ *
+ * Copyright (c) 2016 Jorik Tangelder;
+ * Licensed under the MIT license */
+!function(a,b,c,d){"use strict";function e(a,b,c){return setTimeout(j(a,c),b)}function f(a,b,c){return Array.isArray(a)?(g(a,c[b],c),!0):!1}function g(a,b,c){var e;if(a)if(a.forEach)a.forEach(b,c);else if(a.length!==d)for(e=0;e<a.length;)b.call(c,a[e],e,a),e++;else for(e in a)a.hasOwnProperty(e)&&b.call(c,a[e],e,a)}function h(b,c,d){var e="DEPRECATED METHOD: "+c+"\n"+d+" AT \n";return function(){var c=new Error("get-stack-trace"),d=c&&c.stack?c.stack.replace(/^[^\(]+?[\n$]/gm,"").replace(/^\s+at\s+/gm,"").replace(/^Object.<anonymous>\s*\(/gm,"{anonymous}()@"):"Unknown Stack Trace",f=a.console&&(a.console.warn||a.console.log);return f&&f.call(a.console,e,d),b.apply(this,arguments)}}function i(a,b,c){var d,e=b.prototype;d=a.prototype=Object.create(e),d.constructor=a,d._super=e,c&&la(d,c)}function j(a,b){return function(){return a.apply(b,arguments)}}function k(a,b){return typeof a==oa?a.apply(b?b[0]||d:d,b):a}function l(a,b){return a===d?b:a}function m(a,b,c){g(q(b),function(b){a.addEventListener(b,c,!1)})}function n(a,b,c){g(q(b),function(b){a.removeEventListener(b,c,!1)})}function o(a,b){for(;a;){if(a==b)return!0;a=a.parentNode}return!1}function p(a,b){return a.indexOf(b)>-1}function q(a){return a.trim().split(/\s+/g)}function r(a,b,c){if(a.indexOf&&!c)return a.indexOf(b);for(var d=0;d<a.length;){if(c&&a[d][c]==b||!c&&a[d]===b)return d;d++}return-1}function s(a){return Array.prototype.slice.call(a,0)}function t(a,b,c){for(var d=[],e=[],f=0;f<a.length;){var g=b?a[f][b]:a[f];r(e,g)<0&&d.push(a[f]),e[f]=g,f++}return c&&(d=b?d.sort(function(a,c){return a[b]>c[b]}):d.sort()),d}function u(a,b){for(var c,e,f=b[0].toUpperCase()+b.slice(1),g=0;g<ma.length;){if(c=ma[g],e=c?c+f:b,e in a)return e;g++}return d}function v(){return ua++}function w(b){var c=b.ownerDocument||b;return c.defaultView||c.parentWindow||a}function x(a,b){var c=this;this.manager=a,this.callback=b,this.element=a.element,this.target=a.options.inputTarget,this.domHandler=function(b){k(a.options.enable,[a])&&c.handler(b)},this.init()}function y(a){var b,c=a.options.inputClass;return new(b=c?c:xa?M:ya?P:wa?R:L)(a,z)}function z(a,b,c){var d=c.pointers.length,e=c.changedPointers.length,f=b&Ea&&d-e===0,g=b&(Ga|Ha)&&d-e===0;c.isFirst=!!f,c.isFinal=!!g,f&&(a.session={}),c.eventType=b,A(a,c),a.emit("hammer.input",c),a.recognize(c),a.session.prevInput=c}function A(a,b){var c=a.session,d=b.pointers,e=d.length;c.firstInput||(c.firstInput=D(b)),e>1&&!c.firstMultiple?c.firstMultiple=D(b):1===e&&(c.firstMultiple=!1);var f=c.firstInput,g=c.firstMultiple,h=g?g.center:f.center,i=b.center=E(d);b.timeStamp=ra(),b.deltaTime=b.timeStamp-f.timeStamp,b.angle=I(h,i),b.distance=H(h,i),B(c,b),b.offsetDirection=G(b.deltaX,b.deltaY);var j=F(b.deltaTime,b.deltaX,b.deltaY);b.overallVelocityX=j.x,b.overallVelocityY=j.y,b.overallVelocity=qa(j.x)>qa(j.y)?j.x:j.y,b.scale=g?K(g.pointers,d):1,b.rotation=g?J(g.pointers,d):0,b.maxPointers=c.prevInput?b.pointers.length>c.prevInput.maxPointers?b.pointers.length:c.prevInput.maxPointers:b.pointers.length,C(c,b);var k=a.element;o(b.srcEvent.target,k)&&(k=b.srcEvent.target),b.target=k}function B(a,b){var c=b.center,d=a.offsetDelta||{},e=a.prevDelta||{},f=a.prevInput||{};b.eventType!==Ea&&f.eventType!==Ga||(e=a.prevDelta={x:f.deltaX||0,y:f.deltaY||0},d=a.offsetDelta={x:c.x,y:c.y}),b.deltaX=e.x+(c.x-d.x),b.deltaY=e.y+(c.y-d.y)}function C(a,b){var c,e,f,g,h=a.lastInterval||b,i=b.timeStamp-h.timeStamp;if(b.eventType!=Ha&&(i>Da||h.velocity===d)){var j=b.deltaX-h.deltaX,k=b.deltaY-h.deltaY,l=F(i,j,k);e=l.x,f=l.y,c=qa(l.x)>qa(l.y)?l.x:l.y,g=G(j,k),a.lastInterval=b}else c=h.velocity,e=h.velocityX,f=h.velocityY,g=h.direction;b.velocity=c,b.velocityX=e,b.velocityY=f,b.direction=g}function D(a){for(var b=[],c=0;c<a.pointers.length;)b[c]={clientX:pa(a.pointers[c].clientX),clientY:pa(a.pointers[c].clientY)},c++;return{timeStamp:ra(),pointers:b,center:E(b),deltaX:a.deltaX,deltaY:a.deltaY}}function E(a){var b=a.length;if(1===b)return{x:pa(a[0].clientX),y:pa(a[0].clientY)};for(var c=0,d=0,e=0;b>e;)c+=a[e].clientX,d+=a[e].clientY,e++;return{x:pa(c/b),y:pa(d/b)}}function F(a,b,c){return{x:b/a||0,y:c/a||0}}function G(a,b){return a===b?Ia:qa(a)>=qa(b)?0>a?Ja:Ka:0>b?La:Ma}function H(a,b,c){c||(c=Qa);var d=b[c[0]]-a[c[0]],e=b[c[1]]-a[c[1]];return Math.sqrt(d*d+e*e)}function I(a,b,c){c||(c=Qa);var d=b[c[0]]-a[c[0]],e=b[c[1]]-a[c[1]];return 180*Math.atan2(e,d)/Math.PI}function J(a,b){return I(b[1],b[0],Ra)+I(a[1],a[0],Ra)}function K(a,b){return H(b[0],b[1],Ra)/H(a[0],a[1],Ra)}function L(){this.evEl=Ta,this.evWin=Ua,this.pressed=!1,x.apply(this,arguments)}function M(){this.evEl=Xa,this.evWin=Ya,x.apply(this,arguments),this.store=this.manager.session.pointerEvents=[]}function N(){this.evTarget=$a,this.evWin=_a,this.started=!1,x.apply(this,arguments)}function O(a,b){var c=s(a.touches),d=s(a.changedTouches);return b&(Ga|Ha)&&(c=t(c.concat(d),"identifier",!0)),[c,d]}function P(){this.evTarget=bb,this.targetIds={},x.apply(this,arguments)}function Q(a,b){var c=s(a.touches),d=this.targetIds;if(b&(Ea|Fa)&&1===c.length)return d[c[0].identifier]=!0,[c,c];var e,f,g=s(a.changedTouches),h=[],i=this.target;if(f=c.filter(function(a){return o(a.target,i)}),b===Ea)for(e=0;e<f.length;)d[f[e].identifier]=!0,e++;for(e=0;e<g.length;)d[g[e].identifier]&&h.push(g[e]),b&(Ga|Ha)&&delete d[g[e].identifier],e++;return h.length?[t(f.concat(h),"identifier",!0),h]:void 0}function R(){x.apply(this,arguments);var a=j(this.handler,this);this.touch=new P(this.manager,a),this.mouse=new L(this.manager,a),this.primaryTouch=null,this.lastTouches=[]}function S(a,b){a&Ea?(this.primaryTouch=b.changedPointers[0].identifier,T.call(this,b)):a&(Ga|Ha)&&T.call(this,b)}function T(a){var b=a.changedPointers[0];if(b.identifier===this.primaryTouch){var c={x:b.clientX,y:b.clientY};this.lastTouches.push(c);var d=this.lastTouches,e=function(){var a=d.indexOf(c);a>-1&&d.splice(a,1)};setTimeout(e,cb)}}function U(a){for(var b=a.srcEvent.clientX,c=a.srcEvent.clientY,d=0;d<this.lastTouches.length;d++){var e=this.lastTouches[d],f=Math.abs(b-e.x),g=Math.abs(c-e.y);if(db>=f&&db>=g)return!0}return!1}function V(a,b){this.manager=a,this.set(b)}function W(a){if(p(a,jb))return jb;var b=p(a,kb),c=p(a,lb);return b&&c?jb:b||c?b?kb:lb:p(a,ib)?ib:hb}function X(){if(!fb)return!1;var b={},c=a.CSS&&a.CSS.supports;return["auto","manipulation","pan-y","pan-x","pan-x pan-y","none"].forEach(function(d){b[d]=c?a.CSS.supports("touch-action",d):!0}),b}function Y(a){this.options=la({},this.defaults,a||{}),this.id=v(),this.manager=null,this.options.enable=l(this.options.enable,!0),this.state=nb,this.simultaneous={},this.requireFail=[]}function Z(a){return a&sb?"cancel":a&qb?"end":a&pb?"move":a&ob?"start":""}function $(a){return a==Ma?"down":a==La?"up":a==Ja?"left":a==Ka?"right":""}function _(a,b){var c=b.manager;return c?c.get(a):a}function aa(){Y.apply(this,arguments)}function ba(){aa.apply(this,arguments),this.pX=null,this.pY=null}function ca(){aa.apply(this,arguments)}function da(){Y.apply(this,arguments),this._timer=null,this._input=null}function ea(){aa.apply(this,arguments)}function fa(){aa.apply(this,arguments)}function ga(){Y.apply(this,arguments),this.pTime=!1,this.pCenter=!1,this._timer=null,this._input=null,this.count=0}function ha(a,b){return b=b||{},b.recognizers=l(b.recognizers,ha.defaults.preset),new ia(a,b)}function ia(a,b){this.options=la({},ha.defaults,b||{}),this.options.inputTarget=this.options.inputTarget||a,this.handlers={},this.session={},this.recognizers=[],this.oldCssProps={},this.element=a,this.input=y(this),this.touchAction=new V(this,this.options.touchAction),ja(this,!0),g(this.options.recognizers,function(a){var b=this.add(new a[0](a[1]));a[2]&&b.recognizeWith(a[2]),a[3]&&b.requireFailure(a[3])},this)}function ja(a,b){var c=a.element;if(c.style){var d;g(a.options.cssProps,function(e,f){d=u(c.style,f),b?(a.oldCssProps[d]=c.style[d],c.style[d]=e):c.style[d]=a.oldCssProps[d]||""}),b||(a.oldCssProps={})}}function ka(a,c){var d=b.createEvent("Event");d.initEvent(a,!0,!0),d.gesture=c,c.target.dispatchEvent(d)}var la,ma=["","webkit","Moz","MS","ms","o"],na=b.createElement("div"),oa="function",pa=Math.round,qa=Math.abs,ra=Date.now;la="function"!=typeof Object.assign?function(a){if(a===d||null===a)throw new TypeError("Cannot convert undefined or null to object");for(var b=Object(a),c=1;c<arguments.length;c++){var e=arguments[c];if(e!==d&&null!==e)for(var f in e)e.hasOwnProperty(f)&&(b[f]=e[f])}return b}:Object.assign;var sa=h(function(a,b,c){for(var e=Object.keys(b),f=0;f<e.length;)(!c||c&&a[e[f]]===d)&&(a[e[f]]=b[e[f]]),f++;return a},"extend","Use `assign`."),ta=h(function(a,b){return sa(a,b,!0)},"merge","Use `assign`."),ua=1,va=/mobile|tablet|ip(ad|hone|od)|android/i,wa="ontouchstart"in a,xa=u(a,"PointerEvent")!==d,ya=wa&&va.test(navigator.userAgent),za="touch",Aa="pen",Ba="mouse",Ca="kinect",Da=25,Ea=1,Fa=2,Ga=4,Ha=8,Ia=1,Ja=2,Ka=4,La=8,Ma=16,Na=Ja|Ka,Oa=La|Ma,Pa=Na|Oa,Qa=["x","y"],Ra=["clientX","clientY"];x.prototype={handler:function(){},init:function(){this.evEl&&m(this.element,this.evEl,this.domHandler),this.evTarget&&m(this.target,this.evTarget,this.domHandler),this.evWin&&m(w(this.element),this.evWin,this.domHandler)},destroy:function(){this.evEl&&n(this.element,this.evEl,this.domHandler),this.evTarget&&n(this.target,this.evTarget,this.domHandler),this.evWin&&n(w(this.element),this.evWin,this.domHandler)}};var Sa={mousedown:Ea,mousemove:Fa,mouseup:Ga},Ta="mousedown",Ua="mousemove mouseup";i(L,x,{handler:function(a){var b=Sa[a.type];b&Ea&&0===a.button&&(this.pressed=!0),b&Fa&&1!==a.which&&(b=Ga),this.pressed&&(b&Ga&&(this.pressed=!1),this.callback(this.manager,b,{pointers:[a],changedPointers:[a],pointerType:Ba,srcEvent:a}))}});var Va={pointerdown:Ea,pointermove:Fa,pointerup:Ga,pointercancel:Ha,pointerout:Ha},Wa={2:za,3:Aa,4:Ba,5:Ca},Xa="pointerdown",Ya="pointermove pointerup pointercancel";a.MSPointerEvent&&!a.PointerEvent&&(Xa="MSPointerDown",Ya="MSPointerMove MSPointerUp MSPointerCancel"),i(M,x,{handler:function(a){var b=this.store,c=!1,d=a.type.toLowerCase().replace("ms",""),e=Va[d],f=Wa[a.pointerType]||a.pointerType,g=f==za,h=r(b,a.pointerId,"pointerId");e&Ea&&(0===a.button||g)?0>h&&(b.push(a),h=b.length-1):e&(Ga|Ha)&&(c=!0),0>h||(b[h]=a,this.callback(this.manager,e,{pointers:b,changedPointers:[a],pointerType:f,srcEvent:a}),c&&b.splice(h,1))}});var Za={touchstart:Ea,touchmove:Fa,touchend:Ga,touchcancel:Ha},$a="touchstart",_a="touchstart touchmove touchend touchcancel";i(N,x,{handler:function(a){var b=Za[a.type];if(b===Ea&&(this.started=!0),this.started){var c=O.call(this,a,b);b&(Ga|Ha)&&c[0].length-c[1].length===0&&(this.started=!1),this.callback(this.manager,b,{pointers:c[0],changedPointers:c[1],pointerType:za,srcEvent:a})}}});var ab={touchstart:Ea,touchmove:Fa,touchend:Ga,touchcancel:Ha},bb="touchstart touchmove touchend touchcancel";i(P,x,{handler:function(a){var b=ab[a.type],c=Q.call(this,a,b);c&&this.callback(this.manager,b,{pointers:c[0],changedPointers:c[1],pointerType:za,srcEvent:a})}});var cb=2500,db=25;i(R,x,{handler:function(a,b,c){var d=c.pointerType==za,e=c.pointerType==Ba;if(!(e&&c.sourceCapabilities&&c.sourceCapabilities.firesTouchEvents)){if(d)S.call(this,b,c);else if(e&&U.call(this,c))return;this.callback(a,b,c)}},destroy:function(){this.touch.destroy(),this.mouse.destroy()}});var eb=u(na.style,"touchAction"),fb=eb!==d,gb="compute",hb="auto",ib="manipulation",jb="none",kb="pan-x",lb="pan-y",mb=X();V.prototype={set:function(a){a==gb&&(a=this.compute()),fb&&this.manager.element.style&&mb[a]&&(this.manager.element.style[eb]=a),this.actions=a.toLowerCase().trim()},update:function(){this.set(this.manager.options.touchAction)},compute:function(){var a=[];return g(this.manager.recognizers,function(b){k(b.options.enable,[b])&&(a=a.concat(b.getTouchAction()))}),W(a.join(" "))},preventDefaults:function(a){var b=a.srcEvent,c=a.offsetDirection;if(this.manager.session.prevented)return void b.preventDefault();var d=this.actions,e=p(d,jb)&&!mb[jb],f=p(d,lb)&&!mb[lb],g=p(d,kb)&&!mb[kb];if(e){var h=1===a.pointers.length,i=a.distance<2,j=a.deltaTime<250;if(h&&i&&j)return}return g&&f?void 0:e||f&&c&Na||g&&c&Oa?this.preventSrc(b):void 0},preventSrc:function(a){this.manager.session.prevented=!0,a.preventDefault()}};var nb=1,ob=2,pb=4,qb=8,rb=qb,sb=16,tb=32;Y.prototype={defaults:{},set:function(a){return la(this.options,a),this.manager&&this.manager.touchAction.update(),this},recognizeWith:function(a){if(f(a,"recognizeWith",this))return this;var b=this.simultaneous;return a=_(a,this),b[a.id]||(b[a.id]=a,a.recognizeWith(this)),this},dropRecognizeWith:function(a){return f(a,"dropRecognizeWith",this)?this:(a=_(a,this),delete this.simultaneous[a.id],this)},requireFailure:function(a){if(f(a,"requireFailure",this))return this;var b=this.requireFail;return a=_(a,this),-1===r(b,a)&&(b.push(a),a.requireFailure(this)),this},dropRequireFailure:function(a){if(f(a,"dropRequireFailure",this))return this;a=_(a,this);var b=r(this.requireFail,a);return b>-1&&this.requireFail.splice(b,1),this},hasRequireFailures:function(){return this.requireFail.length>0},canRecognizeWith:function(a){return!!this.simultaneous[a.id]},emit:function(a){function b(b){c.manager.emit(b,a)}var c=this,d=this.state;qb>d&&b(c.options.event+Z(d)),b(c.options.event),a.additionalEvent&&b(a.additionalEvent),d>=qb&&b(c.options.event+Z(d))},tryEmit:function(a){return this.canEmit()?this.emit(a):void(this.state=tb)},canEmit:function(){for(var a=0;a<this.requireFail.length;){if(!(this.requireFail[a].state&(tb|nb)))return!1;a++}return!0},recognize:function(a){var b=la({},a);return k(this.options.enable,[this,b])?(this.state&(rb|sb|tb)&&(this.state=nb),this.state=this.process(b),void(this.state&(ob|pb|qb|sb)&&this.tryEmit(b))):(this.reset(),void(this.state=tb))},process:function(a){},getTouchAction:function(){},reset:function(){}},i(aa,Y,{defaults:{pointers:1},attrTest:function(a){var b=this.options.pointers;return 0===b||a.pointers.length===b},process:function(a){var b=this.state,c=a.eventType,d=b&(ob|pb),e=this.attrTest(a);return d&&(c&Ha||!e)?b|sb:d||e?c&Ga?b|qb:b&ob?b|pb:ob:tb}}),i(ba,aa,{defaults:{event:"pan",threshold:10,pointers:1,direction:Pa},getTouchAction:function(){var a=this.options.direction,b=[];return a&Na&&b.push(lb),a&Oa&&b.push(kb),b},directionTest:function(a){var b=this.options,c=!0,d=a.distance,e=a.direction,f=a.deltaX,g=a.deltaY;return e&b.direction||(b.direction&Na?(e=0===f?Ia:0>f?Ja:Ka,c=f!=this.pX,d=Math.abs(a.deltaX)):(e=0===g?Ia:0>g?La:Ma,c=g!=this.pY,d=Math.abs(a.deltaY))),a.direction=e,c&&d>b.threshold&&e&b.direction},attrTest:function(a){return aa.prototype.attrTest.call(this,a)&&(this.state&ob||!(this.state&ob)&&this.directionTest(a))},emit:function(a){this.pX=a.deltaX,this.pY=a.deltaY;var b=$(a.direction);b&&(a.additionalEvent=this.options.event+b),this._super.emit.call(this,a)}}),i(ca,aa,{defaults:{event:"pinch",threshold:0,pointers:2},getTouchAction:function(){return[jb]},attrTest:function(a){return this._super.attrTest.call(this,a)&&(Math.abs(a.scale-1)>this.options.threshold||this.state&ob)},emit:function(a){if(1!==a.scale){var b=a.scale<1?"in":"out";a.additionalEvent=this.options.event+b}this._super.emit.call(this,a)}}),i(da,Y,{defaults:{event:"press",pointers:1,time:251,threshold:9},getTouchAction:function(){return[hb]},process:function(a){var b=this.options,c=a.pointers.length===b.pointers,d=a.distance<b.threshold,f=a.deltaTime>b.time;if(this._input=a,!d||!c||a.eventType&(Ga|Ha)&&!f)this.reset();else if(a.eventType&Ea)this.reset(),this._timer=e(function(){this.state=rb,this.tryEmit()},b.time,this);else if(a.eventType&Ga)return rb;return tb},reset:function(){clearTimeout(this._timer)},emit:function(a){this.state===rb&&(a&&a.eventType&Ga?this.manager.emit(this.options.event+"up",a):(this._input.timeStamp=ra(),this.manager.emit(this.options.event,this._input)))}}),i(ea,aa,{defaults:{event:"rotate",threshold:0,pointers:2},getTouchAction:function(){return[jb]},attrTest:function(a){return this._super.attrTest.call(this,a)&&(Math.abs(a.rotation)>this.options.threshold||this.state&ob)}}),i(fa,aa,{defaults:{event:"swipe",threshold:10,velocity:.3,direction:Na|Oa,pointers:1},getTouchAction:function(){return ba.prototype.getTouchAction.call(this)},attrTest:function(a){var b,c=this.options.direction;return c&(Na|Oa)?b=a.overallVelocity:c&Na?b=a.overallVelocityX:c&Oa&&(b=a.overallVelocityY),this._super.attrTest.call(this,a)&&c&a.offsetDirection&&a.distance>this.options.threshold&&a.maxPointers==this.options.pointers&&qa(b)>this.options.velocity&&a.eventType&Ga},emit:function(a){var b=$(a.offsetDirection);b&&this.manager.emit(this.options.event+b,a),this.manager.emit(this.options.event,a)}}),i(ga,Y,{defaults:{event:"tap",pointers:1,taps:1,interval:300,time:250,threshold:9,posThreshold:10},getTouchAction:function(){return[ib]},process:function(a){var b=this.options,c=a.pointers.length===b.pointers,d=a.distance<b.threshold,f=a.deltaTime<b.time;if(this.reset(),a.eventType&Ea&&0===this.count)return this.failTimeout();if(d&&f&&c){if(a.eventType!=Ga)return this.failTimeout();var g=this.pTime?a.timeStamp-this.pTime<b.interval:!0,h=!this.pCenter||H(this.pCenter,a.center)<b.posThreshold;this.pTime=a.timeStamp,this.pCenter=a.center,h&&g?this.count+=1:this.count=1,this._input=a;var i=this.count%b.taps;if(0===i)return this.hasRequireFailures()?(this._timer=e(function(){this.state=rb,this.tryEmit()},b.interval,this),ob):rb}return tb},failTimeout:function(){return this._timer=e(function(){this.state=tb},this.options.interval,this),tb},reset:function(){clearTimeout(this._timer)},emit:function(){this.state==rb&&(this._input.tapCount=this.count,this.manager.emit(this.options.event,this._input))}}),ha.VERSION="2.0.8",ha.defaults={domEvents:!1,touchAction:gb,enable:!0,inputTarget:null,inputClass:null,preset:[[ea,{enable:!1}],[ca,{enable:!1},["rotate"]],[fa,{direction:Na}],[ba,{direction:Na},["swipe"]],[ga],[ga,{event:"doubletap",taps:2},["tap"]],[da]],cssProps:{userSelect:"none",touchSelect:"none",touchCallout:"none",contentZooming:"none",userDrag:"none",tapHighlightColor:"rgba(0,0,0,0)"}};var ub=1,vb=2;ia.prototype={set:function(a){return la(this.options,a),a.touchAction&&this.touchAction.update(),a.inputTarget&&(this.input.destroy(),this.input.target=a.inputTarget,this.input.init()),this},stop:function(a){this.session.stopped=a?vb:ub},recognize:function(a){var b=this.session;if(!b.stopped){this.touchAction.preventDefaults(a);var c,d=this.recognizers,e=b.curRecognizer;(!e||e&&e.state&rb)&&(e=b.curRecognizer=null);for(var f=0;f<d.length;)c=d[f],b.stopped===vb||e&&c!=e&&!c.canRecognizeWith(e)?c.reset():c.recognize(a),!e&&c.state&(ob|pb|qb)&&(e=b.curRecognizer=c),f++}},get:function(a){if(a instanceof Y)return a;for(var b=this.recognizers,c=0;c<b.length;c++)if(b[c].options.event==a)return b[c];return null},add:function(a){if(f(a,"add",this))return this;var b=this.get(a.options.event);return b&&this.remove(b),this.recognizers.push(a),a.manager=this,this.touchAction.update(),a},remove:function(a){if(f(a,"remove",this))return this;if(a=this.get(a)){var b=this.recognizers,c=r(b,a);-1!==c&&(b.splice(c,1),this.touchAction.update())}return this},on:function(a,b){if(a!==d&&b!==d){var c=this.handlers;return g(q(a),function(a){c[a]=c[a]||[],c[a].push(b)}),this}},off:function(a,b){if(a!==d){var c=this.handlers;return g(q(a),function(a){b?c[a]&&c[a].splice(r(c[a],b),1):delete c[a]}),this}},emit:function(a,b){this.options.domEvents&&ka(a,b);var c=this.handlers[a]&&this.handlers[a].slice();if(c&&c.length){b.type=a,b.preventDefault=function(){b.srcEvent.preventDefault()};for(var d=0;d<c.length;)c[d](b),d++}},destroy:function(){this.element&&ja(this,!1),this.handlers={},this.session={},this.input.destroy(),this.element=null}},la(ha,{INPUT_START:Ea,INPUT_MOVE:Fa,INPUT_END:Ga,INPUT_CANCEL:Ha,STATE_POSSIBLE:nb,STATE_BEGAN:ob,STATE_CHANGED:pb,STATE_ENDED:qb,STATE_RECOGNIZED:rb,STATE_CANCELLED:sb,STATE_FAILED:tb,DIRECTION_NONE:Ia,DIRECTION_LEFT:Ja,DIRECTION_RIGHT:Ka,DIRECTION_UP:La,DIRECTION_DOWN:Ma,DIRECTION_HORIZONTAL:Na,DIRECTION_VERTICAL:Oa,DIRECTION_ALL:Pa,Manager:ia,Input:x,TouchAction:V,TouchInput:P,MouseInput:L,PointerEventInput:M,TouchMouseInput:R,SingleTouchInput:N,Recognizer:Y,AttrRecognizer:aa,Tap:ga,Pan:ba,Swipe:fa,Pinch:ca,Rotate:ea,Press:da,on:m,off:n,each:g,merge:ta,extend:sa,assign:la,inherit:i,bindFn:j,prefixed:u});var wb="undefined"!=typeof a?a:"undefined"!=typeof self?self:{};wb.Hammer=ha,"function"==typeof define&&define.amd?define(function(){return ha}):"undefined"!=typeof module&&module.exports?module.exports=ha:a[c]=ha}(window,document,"Hammer");
+//# sourceMappingURL=hammer.min.js.map
\ No newline at end of file
diff --git a/js/libs/modernizr/modernizr.js b/js/libs/modernizr/modernizr.js
deleted file mode 100644 (file)
index cc85e67..0000000
+++ /dev/null
@@ -1,3 +0,0 @@
-/*! modernizr 3.3.1 (Custom Build) | MIT *
- * https://modernizr.com/download/?-applicationcache-audio-csstransforms-csstransforms3d-csstransitions-fullscreen-localstorage-preserve3d-sessionstorage-svg-touchevents-video-addtest-atrule-domprefixes-hasevent-mq-prefixed-prefixedcss-prefixedcssvalue-prefixes-setclasses-testallprops-testprop-teststyles !*/
-!function(e,n,t){function r(e,n){return typeof e===n}function o(){var e,n,t,o,i,a,s;for(var c in T)if(T.hasOwnProperty(c)){if(e=[],n=T[c],n.name&&(e.push(n.name.toLowerCase()),n.options&&n.options.aliases&&n.options.aliases.length))for(t=0;t<n.options.aliases.length;t++)e.push(n.options.aliases[t].toLowerCase());for(o=r(n.fn,"function")?n.fn():n.fn,i=0;i<e.length;i++)a=e[i],s=a.split("."),1===s.length?Modernizr[s[0]]=o:(!Modernizr[s[0]]||Modernizr[s[0]]instanceof Boolean||(Modernizr[s[0]]=new Boolean(Modernizr[s[0]])),Modernizr[s[0]][s[1]]=o),w.push((o?"":"no-")+s.join("-"))}}function i(e){var n=_.className,t=Modernizr._config.classPrefix||"";if(b&&(n=n.baseVal),Modernizr._config.enableJSClass){var r=new RegExp("(^|\\s)"+t+"no-js(\\s|$)");n=n.replace(r,"$1"+t+"js$2")}Modernizr._config.enableClasses&&(n+=" "+t+e.join(" "+t),b?_.className.baseVal=n:_.className=n)}function a(e,n){if("object"==typeof e)for(var t in e)x(e,t)&&a(t,e[t]);else{e=e.toLowerCase();var r=e.split("."),o=Modernizr[r[0]];if(2==r.length&&(o=o[r[1]]),"undefined"!=typeof o)return Modernizr;n="function"==typeof n?n():n,1==r.length?Modernizr[r[0]]=n:(!Modernizr[r[0]]||Modernizr[r[0]]instanceof Boolean||(Modernizr[r[0]]=new Boolean(Modernizr[r[0]])),Modernizr[r[0]][r[1]]=n),i([(n&&0!=n?"":"no-")+r.join("-")]),Modernizr._trigger(e,n)}return Modernizr}function s(){return"function"!=typeof n.createElement?n.createElement(arguments[0]):b?n.createElementNS.call(n,"http://www.w3.org/2000/svg",arguments[0]):n.createElement.apply(n,arguments)}function c(e){return e.replace(/([a-z])-([a-z])/g,function(e,n,t){return n+t.toUpperCase()}).replace(/^-/,"")}function u(e){return e.replace(/([A-Z])/g,function(e,n){return"-"+n.toLowerCase()}).replace(/^ms-/,"-ms-")}function l(e,n){return!!~(""+e).indexOf(n)}function f(){var e=n.body;return e||(e=s(b?"svg":"body"),e.fake=!0),e}function d(e,t,r,o){var i,a,c,u,l="modernizr",d=s("div"),p=f();if(parseInt(r,10))for(;r--;)c=s("div"),c.id=o?o[r]:l+(r+1),d.appendChild(c);return i=s("style"),i.type="text/css",i.id="s"+l,(p.fake?p:d).appendChild(i),p.appendChild(d),i.styleSheet?i.styleSheet.cssText=e:i.appendChild(n.createTextNode(e)),d.id=l,p.fake&&(p.style.background="",p.style.overflow="hidden",u=_.style.overflow,_.style.overflow="hidden",_.appendChild(p)),a=t(d,e),p.fake?(p.parentNode.removeChild(p),_.style.overflow=u,_.offsetHeight):d.parentNode.removeChild(d),!!a}function p(n,r){var o=n.length;if("CSS"in e&&"supports"in e.CSS){for(;o--;)if(e.CSS.supports(u(n[o]),r))return!0;return!1}if("CSSSupportsRule"in e){for(var i=[];o--;)i.push("("+u(n[o])+":"+r+")");return i=i.join(" or "),d("@supports ("+i+") { #modernizr { position: absolute; } }",function(e){return"absolute"==getComputedStyle(e,null).position})}return t}function v(e,n,o,i){function a(){f&&(delete q.style,delete q.modElem)}if(i=r(i,"undefined")?!1:i,!r(o,"undefined")){var u=p(e,o);if(!r(u,"undefined"))return u}for(var f,d,v,m,h,g=["modernizr","tspan","samp"];!q.style&&g.length;)f=!0,q.modElem=s(g.shift()),q.style=q.modElem.style;for(v=e.length,d=0;v>d;d++)if(m=e[d],h=q.style[m],l(m,"-")&&(m=c(m)),q.style[m]!==t){if(i||r(o,"undefined"))return a(),"pfx"==n?m:!0;try{q.style[m]=o}catch(y){}if(q.style[m]!=h)return a(),"pfx"==n?m:!0}return a(),!1}function m(e,n){return function(){return e.apply(n,arguments)}}function h(e,n,t){var o;for(var i in e)if(e[i]in n)return t===!1?e[i]:(o=n[e[i]],r(o,"function")?m(o,t||n):o);return!1}function g(e,n,t,o,i){var a=e.charAt(0).toUpperCase()+e.slice(1),s=(e+" "+z.join(a+" ")+a).split(" ");return r(n,"string")||r(n,"undefined")?v(s,n,o,i):(s=(e+" "+E.join(a+" ")+a).split(" "),h(s,n,t))}function y(e,n,r){return g(e,t,t,n,r)}var w=[],T=[],C={_version:"3.3.1",_config:{classPrefix:"",enableClasses:!0,enableJSClass:!0,usePrefixes:!0},_q:[],on:function(e,n){var t=this;setTimeout(function(){n(t[e])},0)},addTest:function(e,n,t){T.push({name:e,fn:n,options:t})},addAsyncTest:function(e){T.push({name:null,fn:e})}},Modernizr=function(){};Modernizr.prototype=C,Modernizr=new Modernizr,Modernizr.addTest("applicationcache","applicationCache"in e),Modernizr.addTest("svg",!!n.createElementNS&&!!n.createElementNS("http://www.w3.org/2000/svg","svg").createSVGRect),Modernizr.addTest("localstorage",function(){var e="modernizr";try{return localStorage.setItem(e,e),localStorage.removeItem(e),!0}catch(n){return!1}}),Modernizr.addTest("sessionstorage",function(){var e="modernizr";try{return sessionStorage.setItem(e,e),sessionStorage.removeItem(e),!0}catch(n){return!1}});var S=C._config.usePrefixes?" -webkit- -moz- -o- -ms- ".split(" "):["",""];C._prefixes=S;var x;!function(){var e={}.hasOwnProperty;x=r(e,"undefined")||r(e.call,"undefined")?function(e,n){return n in e&&r(e.constructor.prototype[n],"undefined")}:function(n,t){return e.call(n,t)}}();var _=n.documentElement,b="svg"===_.nodeName.toLowerCase();C._l={},C.on=function(e,n){this._l[e]||(this._l[e]=[]),this._l[e].push(n),Modernizr.hasOwnProperty(e)&&setTimeout(function(){Modernizr._trigger(e,Modernizr[e])},0)},C._trigger=function(e,n){if(this._l[e]){var t=this._l[e];setTimeout(function(){var e,r;for(e=0;e<t.length;e++)(r=t[e])(n)},0),delete this._l[e]}},Modernizr._q.push(function(){C.addTest=a});var P="Moz O ms Webkit",E=C._config.usePrefixes?P.toLowerCase().split(" "):[];C._domPrefixes=E;var z=C._config.usePrefixes?P.split(" "):[];C._cssomPrefixes=z;var $=function(n){var r,o=S.length,i=e.CSSRule;if("undefined"==typeof i)return t;if(!n)return!1;if(n=n.replace(/^@/,""),r=n.replace(/-/g,"_").toUpperCase()+"_RULE",r in i)return"@"+n;for(var a=0;o>a;a++){var s=S[a],c=s.toUpperCase()+"_"+r;if(c in i)return"@-"+s.toLowerCase()+"-"+n}return!1};C.atRule=$;var k=function(){function e(e,n){var o;return e?(n&&"string"!=typeof n||(n=s(n||"div")),e="on"+e,o=e in n,!o&&r&&(n.setAttribute||(n=s("div")),n.setAttribute(e,""),o="function"==typeof n[e],n[e]!==t&&(n[e]=t),n.removeAttribute(e)),o):!1}var r=!("onblur"in n.documentElement);return e}();C.hasEvent=k;var j=function(e,n){var t=!1,r=s("div"),o=r.style;if(e in o){var i=E.length;for(o[e]=n,t=o[e];i--&&!t;)o[e]="-"+E[i]+"-"+n,t=o[e]}return""===t&&(t=!1),t};C.prefixedCSSValue=j,Modernizr.addTest("audio",function(){var e=s("audio"),n=!1;try{(n=!!e.canPlayType)&&(n=new Boolean(n),n.ogg=e.canPlayType('audio/ogg; codecs="vorbis"').replace(/^no$/,""),n.mp3=e.canPlayType('audio/mpeg; codecs="mp3"').replace(/^no$/,""),n.opus=e.canPlayType('audio/ogg; codecs="opus"')||e.canPlayType('audio/webm; codecs="opus"').replace(/^no$/,""),n.wav=e.canPlayType('audio/wav; codecs="1"').replace(/^no$/,""),n.m4a=(e.canPlayType("audio/x-m4a;")||e.canPlayType("audio/aac;")).replace(/^no$/,""))}catch(t){}return n}),Modernizr.addTest("video",function(){var e=s("video"),n=!1;try{(n=!!e.canPlayType)&&(n=new Boolean(n),n.ogg=e.canPlayType('video/ogg; codecs="theora"').replace(/^no$/,""),n.h264=e.canPlayType('video/mp4; codecs="avc1.42E01E"').replace(/^no$/,""),n.webm=e.canPlayType('video/webm; codecs="vp8, vorbis"').replace(/^no$/,""),n.vp9=e.canPlayType('video/webm; codecs="vp9"').replace(/^no$/,""),n.hls=e.canPlayType('application/x-mpegURL; codecs="avc1.42E01E"').replace(/^no$/,""))}catch(t){}return n}),Modernizr.addTest("preserve3d",function(){var e=s("a"),n=s("a");e.style.cssText="display: block; transform-style: preserve-3d; transform-origin: right; transform: rotateY(40deg);",n.style.cssText="display: block; width: 9px; height: 1px; background: #000; transform-origin: right; transform: rotateY(40deg);",e.appendChild(n),_.appendChild(e);var t=n.getBoundingClientRect();return _.removeChild(e),t.width&&t.width<4});var A="CSS"in e&&"supports"in e.CSS,N="supportsCSS"in e;Modernizr.addTest("supports",A||N);var L=function(){var n=e.matchMedia||e.msMatchMedia;return n?function(e){var t=n(e);return t&&t.matches||!1}:function(n){var t=!1;return d("@media "+n+" { #modernizr { position: absolute; } }",function(n){t="absolute"==(e.getComputedStyle?e.getComputedStyle(n,null):n.currentStyle).position}),t}}();C.mq=L;var O=C.testStyles=d;Modernizr.addTest("touchevents",function(){var t;if("ontouchstart"in e||e.DocumentTouch&&n instanceof DocumentTouch)t=!0;else{var r=["@media (",S.join("touch-enabled),("),"heartz",")","{#modernizr{top:9px;position:absolute}}"].join("");O(r,function(e){t=9===e.offsetTop})}return t});var R={elem:s("modernizr")};Modernizr._q.push(function(){delete R.elem});var q={style:R.elem.style};Modernizr._q.unshift(function(){delete q.style});C.testProp=function(e,n,r){return v([e],t,n,r)};C.testAllProps=g;var B=C.prefixed=function(e,n,t){return 0===e.indexOf("@")?$(e):(-1!=e.indexOf("-")&&(e=c(e)),n?g(e,n,t):g(e,"pfx"))};C.prefixedCSS=function(e){var n=B(e);return n&&u(n)};Modernizr.addTest("fullscreen",!(!B("exitFullscreen",n,!1)&&!B("cancelFullScreen",n,!1))),C.testAllProps=y,Modernizr.addTest("csstransforms",function(){return-1===navigator.userAgent.indexOf("Android 2.")&&y("transform","scale(1)",!0)}),Modernizr.addTest("csstransforms3d",function(){var e=!!y("perspective","1px",!0),n=Modernizr._config.usePrefixes;if(e&&(!n||"webkitPerspective"in _.style)){var t,r="#modernizr{width:0;height:0}";Modernizr.supports?t="@supports (perspective: 1px)":(t="@media (transform-3d)",n&&(t+=",(-webkit-transform-3d)")),t+="{#modernizr{width:7px;height:18px;margin:0;padding:0;border:0}}",O(r+t,function(n){e=7===n.offsetWidth&&18===n.offsetHeight})}return e}),Modernizr.addTest("csstransitions",y("transition","all",!0)),o(),i(w),delete C.addTest,delete C.addAsyncTest;for(var I=0;I<Modernizr._q.length;I++)Modernizr._q[I]();e.Modernizr=Modernizr}(window,document);
\ No newline at end of file
diff --git a/js/libs/modernizr/modernizr.min.js b/js/libs/modernizr/modernizr.min.js
new file mode 100644 (file)
index 0000000..cc85e67
--- /dev/null
@@ -0,0 +1,3 @@
+/*! modernizr 3.3.1 (Custom Build) | MIT *
+ * https://modernizr.com/download/?-applicationcache-audio-csstransforms-csstransforms3d-csstransitions-fullscreen-localstorage-preserve3d-sessionstorage-svg-touchevents-video-addtest-atrule-domprefixes-hasevent-mq-prefixed-prefixedcss-prefixedcssvalue-prefixes-setclasses-testallprops-testprop-teststyles !*/
+!function(e,n,t){function r(e,n){return typeof e===n}function o(){var e,n,t,o,i,a,s;for(var c in T)if(T.hasOwnProperty(c)){if(e=[],n=T[c],n.name&&(e.push(n.name.toLowerCase()),n.options&&n.options.aliases&&n.options.aliases.length))for(t=0;t<n.options.aliases.length;t++)e.push(n.options.aliases[t].toLowerCase());for(o=r(n.fn,"function")?n.fn():n.fn,i=0;i<e.length;i++)a=e[i],s=a.split("."),1===s.length?Modernizr[s[0]]=o:(!Modernizr[s[0]]||Modernizr[s[0]]instanceof Boolean||(Modernizr[s[0]]=new Boolean(Modernizr[s[0]])),Modernizr[s[0]][s[1]]=o),w.push((o?"":"no-")+s.join("-"))}}function i(e){var n=_.className,t=Modernizr._config.classPrefix||"";if(b&&(n=n.baseVal),Modernizr._config.enableJSClass){var r=new RegExp("(^|\\s)"+t+"no-js(\\s|$)");n=n.replace(r,"$1"+t+"js$2")}Modernizr._config.enableClasses&&(n+=" "+t+e.join(" "+t),b?_.className.baseVal=n:_.className=n)}function a(e,n){if("object"==typeof e)for(var t in e)x(e,t)&&a(t,e[t]);else{e=e.toLowerCase();var r=e.split("."),o=Modernizr[r[0]];if(2==r.length&&(o=o[r[1]]),"undefined"!=typeof o)return Modernizr;n="function"==typeof n?n():n,1==r.length?Modernizr[r[0]]=n:(!Modernizr[r[0]]||Modernizr[r[0]]instanceof Boolean||(Modernizr[r[0]]=new Boolean(Modernizr[r[0]])),Modernizr[r[0]][r[1]]=n),i([(n&&0!=n?"":"no-")+r.join("-")]),Modernizr._trigger(e,n)}return Modernizr}function s(){return"function"!=typeof n.createElement?n.createElement(arguments[0]):b?n.createElementNS.call(n,"http://www.w3.org/2000/svg",arguments[0]):n.createElement.apply(n,arguments)}function c(e){return e.replace(/([a-z])-([a-z])/g,function(e,n,t){return n+t.toUpperCase()}).replace(/^-/,"")}function u(e){return e.replace(/([A-Z])/g,function(e,n){return"-"+n.toLowerCase()}).replace(/^ms-/,"-ms-")}function l(e,n){return!!~(""+e).indexOf(n)}function f(){var e=n.body;return e||(e=s(b?"svg":"body"),e.fake=!0),e}function d(e,t,r,o){var i,a,c,u,l="modernizr",d=s("div"),p=f();if(parseInt(r,10))for(;r--;)c=s("div"),c.id=o?o[r]:l+(r+1),d.appendChild(c);return i=s("style"),i.type="text/css",i.id="s"+l,(p.fake?p:d).appendChild(i),p.appendChild(d),i.styleSheet?i.styleSheet.cssText=e:i.appendChild(n.createTextNode(e)),d.id=l,p.fake&&(p.style.background="",p.style.overflow="hidden",u=_.style.overflow,_.style.overflow="hidden",_.appendChild(p)),a=t(d,e),p.fake?(p.parentNode.removeChild(p),_.style.overflow=u,_.offsetHeight):d.parentNode.removeChild(d),!!a}function p(n,r){var o=n.length;if("CSS"in e&&"supports"in e.CSS){for(;o--;)if(e.CSS.supports(u(n[o]),r))return!0;return!1}if("CSSSupportsRule"in e){for(var i=[];o--;)i.push("("+u(n[o])+":"+r+")");return i=i.join(" or "),d("@supports ("+i+") { #modernizr { position: absolute; } }",function(e){return"absolute"==getComputedStyle(e,null).position})}return t}function v(e,n,o,i){function a(){f&&(delete q.style,delete q.modElem)}if(i=r(i,"undefined")?!1:i,!r(o,"undefined")){var u=p(e,o);if(!r(u,"undefined"))return u}for(var f,d,v,m,h,g=["modernizr","tspan","samp"];!q.style&&g.length;)f=!0,q.modElem=s(g.shift()),q.style=q.modElem.style;for(v=e.length,d=0;v>d;d++)if(m=e[d],h=q.style[m],l(m,"-")&&(m=c(m)),q.style[m]!==t){if(i||r(o,"undefined"))return a(),"pfx"==n?m:!0;try{q.style[m]=o}catch(y){}if(q.style[m]!=h)return a(),"pfx"==n?m:!0}return a(),!1}function m(e,n){return function(){return e.apply(n,arguments)}}function h(e,n,t){var o;for(var i in e)if(e[i]in n)return t===!1?e[i]:(o=n[e[i]],r(o,"function")?m(o,t||n):o);return!1}function g(e,n,t,o,i){var a=e.charAt(0).toUpperCase()+e.slice(1),s=(e+" "+z.join(a+" ")+a).split(" ");return r(n,"string")||r(n,"undefined")?v(s,n,o,i):(s=(e+" "+E.join(a+" ")+a).split(" "),h(s,n,t))}function y(e,n,r){return g(e,t,t,n,r)}var w=[],T=[],C={_version:"3.3.1",_config:{classPrefix:"",enableClasses:!0,enableJSClass:!0,usePrefixes:!0},_q:[],on:function(e,n){var t=this;setTimeout(function(){n(t[e])},0)},addTest:function(e,n,t){T.push({name:e,fn:n,options:t})},addAsyncTest:function(e){T.push({name:null,fn:e})}},Modernizr=function(){};Modernizr.prototype=C,Modernizr=new Modernizr,Modernizr.addTest("applicationcache","applicationCache"in e),Modernizr.addTest("svg",!!n.createElementNS&&!!n.createElementNS("http://www.w3.org/2000/svg","svg").createSVGRect),Modernizr.addTest("localstorage",function(){var e="modernizr";try{return localStorage.setItem(e,e),localStorage.removeItem(e),!0}catch(n){return!1}}),Modernizr.addTest("sessionstorage",function(){var e="modernizr";try{return sessionStorage.setItem(e,e),sessionStorage.removeItem(e),!0}catch(n){return!1}});var S=C._config.usePrefixes?" -webkit- -moz- -o- -ms- ".split(" "):["",""];C._prefixes=S;var x;!function(){var e={}.hasOwnProperty;x=r(e,"undefined")||r(e.call,"undefined")?function(e,n){return n in e&&r(e.constructor.prototype[n],"undefined")}:function(n,t){return e.call(n,t)}}();var _=n.documentElement,b="svg"===_.nodeName.toLowerCase();C._l={},C.on=function(e,n){this._l[e]||(this._l[e]=[]),this._l[e].push(n),Modernizr.hasOwnProperty(e)&&setTimeout(function(){Modernizr._trigger(e,Modernizr[e])},0)},C._trigger=function(e,n){if(this._l[e]){var t=this._l[e];setTimeout(function(){var e,r;for(e=0;e<t.length;e++)(r=t[e])(n)},0),delete this._l[e]}},Modernizr._q.push(function(){C.addTest=a});var P="Moz O ms Webkit",E=C._config.usePrefixes?P.toLowerCase().split(" "):[];C._domPrefixes=E;var z=C._config.usePrefixes?P.split(" "):[];C._cssomPrefixes=z;var $=function(n){var r,o=S.length,i=e.CSSRule;if("undefined"==typeof i)return t;if(!n)return!1;if(n=n.replace(/^@/,""),r=n.replace(/-/g,"_").toUpperCase()+"_RULE",r in i)return"@"+n;for(var a=0;o>a;a++){var s=S[a],c=s.toUpperCase()+"_"+r;if(c in i)return"@-"+s.toLowerCase()+"-"+n}return!1};C.atRule=$;var k=function(){function e(e,n){var o;return e?(n&&"string"!=typeof n||(n=s(n||"div")),e="on"+e,o=e in n,!o&&r&&(n.setAttribute||(n=s("div")),n.setAttribute(e,""),o="function"==typeof n[e],n[e]!==t&&(n[e]=t),n.removeAttribute(e)),o):!1}var r=!("onblur"in n.documentElement);return e}();C.hasEvent=k;var j=function(e,n){var t=!1,r=s("div"),o=r.style;if(e in o){var i=E.length;for(o[e]=n,t=o[e];i--&&!t;)o[e]="-"+E[i]+"-"+n,t=o[e]}return""===t&&(t=!1),t};C.prefixedCSSValue=j,Modernizr.addTest("audio",function(){var e=s("audio"),n=!1;try{(n=!!e.canPlayType)&&(n=new Boolean(n),n.ogg=e.canPlayType('audio/ogg; codecs="vorbis"').replace(/^no$/,""),n.mp3=e.canPlayType('audio/mpeg; codecs="mp3"').replace(/^no$/,""),n.opus=e.canPlayType('audio/ogg; codecs="opus"')||e.canPlayType('audio/webm; codecs="opus"').replace(/^no$/,""),n.wav=e.canPlayType('audio/wav; codecs="1"').replace(/^no$/,""),n.m4a=(e.canPlayType("audio/x-m4a;")||e.canPlayType("audio/aac;")).replace(/^no$/,""))}catch(t){}return n}),Modernizr.addTest("video",function(){var e=s("video"),n=!1;try{(n=!!e.canPlayType)&&(n=new Boolean(n),n.ogg=e.canPlayType('video/ogg; codecs="theora"').replace(/^no$/,""),n.h264=e.canPlayType('video/mp4; codecs="avc1.42E01E"').replace(/^no$/,""),n.webm=e.canPlayType('video/webm; codecs="vp8, vorbis"').replace(/^no$/,""),n.vp9=e.canPlayType('video/webm; codecs="vp9"').replace(/^no$/,""),n.hls=e.canPlayType('application/x-mpegURL; codecs="avc1.42E01E"').replace(/^no$/,""))}catch(t){}return n}),Modernizr.addTest("preserve3d",function(){var e=s("a"),n=s("a");e.style.cssText="display: block; transform-style: preserve-3d; transform-origin: right; transform: rotateY(40deg);",n.style.cssText="display: block; width: 9px; height: 1px; background: #000; transform-origin: right; transform: rotateY(40deg);",e.appendChild(n),_.appendChild(e);var t=n.getBoundingClientRect();return _.removeChild(e),t.width&&t.width<4});var A="CSS"in e&&"supports"in e.CSS,N="supportsCSS"in e;Modernizr.addTest("supports",A||N);var L=function(){var n=e.matchMedia||e.msMatchMedia;return n?function(e){var t=n(e);return t&&t.matches||!1}:function(n){var t=!1;return d("@media "+n+" { #modernizr { position: absolute; } }",function(n){t="absolute"==(e.getComputedStyle?e.getComputedStyle(n,null):n.currentStyle).position}),t}}();C.mq=L;var O=C.testStyles=d;Modernizr.addTest("touchevents",function(){var t;if("ontouchstart"in e||e.DocumentTouch&&n instanceof DocumentTouch)t=!0;else{var r=["@media (",S.join("touch-enabled),("),"heartz",")","{#modernizr{top:9px;position:absolute}}"].join("");O(r,function(e){t=9===e.offsetTop})}return t});var R={elem:s("modernizr")};Modernizr._q.push(function(){delete R.elem});var q={style:R.elem.style};Modernizr._q.unshift(function(){delete q.style});C.testProp=function(e,n,r){return v([e],t,n,r)};C.testAllProps=g;var B=C.prefixed=function(e,n,t){return 0===e.indexOf("@")?$(e):(-1!=e.indexOf("-")&&(e=c(e)),n?g(e,n,t):g(e,"pfx"))};C.prefixedCSS=function(e){var n=B(e);return n&&u(n)};Modernizr.addTest("fullscreen",!(!B("exitFullscreen",n,!1)&&!B("cancelFullScreen",n,!1))),C.testAllProps=y,Modernizr.addTest("csstransforms",function(){return-1===navigator.userAgent.indexOf("Android 2.")&&y("transform","scale(1)",!0)}),Modernizr.addTest("csstransforms3d",function(){var e=!!y("perspective","1px",!0),n=Modernizr._config.usePrefixes;if(e&&(!n||"webkitPerspective"in _.style)){var t,r="#modernizr{width:0;height:0}";Modernizr.supports?t="@supports (perspective: 1px)":(t="@media (transform-3d)",n&&(t+=",(-webkit-transform-3d)")),t+="{#modernizr{width:7px;height:18px;margin:0;padding:0;border:0}}",O(r+t,function(n){e=7===n.offsetWidth&&18===n.offsetHeight})}return e}),Modernizr.addTest("csstransitions",y("transition","all",!0)),o(),i(w),delete C.addTest,delete C.addAsyncTest;for(var I=0;I<Modernizr._q.length;I++)Modernizr._q[I]();e.Modernizr=Modernizr}(window,document);
\ No newline at end of file
diff --git a/js/libs/print.min.js b/js/libs/print.min.js
new file mode 100644 (file)
index 0000000..79f552f
--- /dev/null
@@ -0,0 +1 @@
+!function(e){function t(i){if(n[i])return n[i].exports;var o=n[i]={i:i,l:!1,exports:{}};return e[i].call(o.exports,o,o.exports,t),o.l=!0,o.exports}var n={};t.m=e,t.c=n,t.i=function(e){return e},t.d=function(e,n,i){t.o(e,n)||Object.defineProperty(e,n,{configurable:!1,enumerable:!0,get:i})},t.n=function(e){var n=e&&e.__esModule?function(){return e.default}:function(){return e};return t.d(n,"a",n),n},t.o=function(e,t){return Object.prototype.hasOwnProperty.call(e,t)},t.p="./",t(t.s=10)}([function(e,t,n){"use strict";function i(e,t){if(e.focus(),a.a.isIE()||a.a.isEdge())try{e.contentWindow.document.execCommand("print",!1,null)}catch(t){e.contentWindow.print()}else e.contentWindow.print();t.showModal&&d.a.close()}function o(e){void 0===e.print?setTimeout(function(){o()},1e3):(l.send(),setTimeout(function(){e.parentNode.removeChild(e)},2e3))}function r(e,t,n){void 0===e.naturalWidth||0===e.naturalWidth?setTimeout(function(){r(e,t,n)},500):i(t,n)}var a=n(1),d=n(3),l={send:function(e,t){document.getElementsByTagName("body")[0].appendChild(t);var n=document.getElementById(e.frameId);a.a.isIE()&&"pdf"===e.type?o(n):t.onload=function(){if("pdf"===e.type)i(n,e);else{var t=n.contentWindow||n.contentDocument;t.document&&(t=t.document),t.body.innerHTML=e.htmlData,"image"===e.type?r(t.getElementById("printableImage"),n,e):i(n,e)}}}};t.a=l},function(e,t,n){"use strict";var i={isFirefox:function(){return"undefined"!=typeof InstallTrigger},isIE:function(){return!!document.documentMode},isEdge:function(){return!i.isIE()&&!!window.StyleMedia},isChrome:function(){return!!window.chrome&&!!window.chrome.webstore},isSafari:function(){return Object.prototype.toString.call(window.HTMLElement).indexOf("Constructor")>0||-1!==navigator.userAgent.toLowerCase().indexOf("safari")}};t.a=i},function(e,t,n){"use strict";function i(e,t){return'<div style="font-family:'+t.font+" !important; font-size: "+t.font_size+' !important; width:100%;">'+e+"</div>"}function o(e){return e.charAt(0).toUpperCase()+e.slice(1)}function r(e,t){var n=document.defaultView||window,i=[],o="";if(n.getComputedStyle){i=n.getComputedStyle(e,"");var r=["border","float","box","break","text-decoration"],a=["clear","display","width","min-width","height","min-height","max-height"];t.honorMarginPadding&&r.push("margin","padding"),t.honorColor&&r.push("color");for(var d=0;d<i.length;d++)for(var l=0;l<a.length;l++)-1===i[d].indexOf(r[l])&&0!==i[d].indexOf(a[l])||(o+=i[d]+":"+i.getPropertyValue(i[d])+";")}else if(e.currentStyle){i=e.currentStyle;for(var s in i)-1!==i.indexOf("border")&&-1!==i.indexOf("color")&&(o+=s+":"+i[s]+";")}return o+="max-width: "+t.maxWidth+"px !important;"+t.font_size+" !important;"}function a(e,t){for(var n=0;n<e.length;n++){var i=e[n],o=i.tagName;if("INPUT"===o||"TEXTAREA"===o||"SELECT"===o){var d=r(i,t),l=i.parentNode,s="SELECT"===o?document.createTextNode(i.options[i.selectedIndex].text):document.createTextNode(i.value),c=document.createElement("div");c.appendChild(s),c.setAttribute("style",d),l.appendChild(c),l.removeChild(i)}else i.setAttribute("style",r(i,t));var p=i.children;p&&p.length&&a(p,t)}}function d(e,t){var n=document.createElement("h1"),i=document.createTextNode(t);n.appendChild(i),n.setAttribute("style","font-weight:300;"),e.insertBefore(n,e.childNodes[0])}t.a=i,t.b=o,t.c=r,t.d=a,t.e=d},function(e,t,n){"use strict";var i={show:function(e){var t=document.createElement("div");t.setAttribute("style","font-family:sans-serif; display:table; text-align:center; font-weight:300; font-size:30px; left:0; top:0;position:fixed; z-index: 9990;color: #0460B5; width: 100%; height: 100%; background-color:rgba(255,255,255,.9);transition: opacity .3s ease;"),t.setAttribute("id","printJS-Modal");var n=document.createElement("div");n.setAttribute("style","display:table-cell; vertical-align:middle; padding-bottom:100px;");var o=document.createElement("div");o.setAttribute("class","printClose"),o.setAttribute("id","printClose"),n.appendChild(o);var r=document.createElement("span");r.setAttribute("class","printSpinner"),n.appendChild(r);var a=document.createTextNode(e.modalMessage);n.appendChild(a),t.appendChild(n),document.getElementsByTagName("body")[0].appendChild(t),document.getElementById("printClose").addEventListener("click",function(){i.close()})},close:function(){var e=document.getElementById("printJS-Modal");e.parentNode.removeChild(e)}};t.a=i},function(e,t,n){"use strict";Object.defineProperty(t,"__esModule",{value:!0});var i=n(7),o=i.a.init;"undefined"!=typeof window&&(window.printJS=o),t.default=o},function(e,t,n){"use strict";var i=n(2),o=n(0);t.a={print:function(e,t){var r=document.getElementById(e.printable);if(!r)return window.console.error("Invalid HTML element id: "+e.printable),!1;var a=document.createElement("div");a.appendChild(r.cloneNode(!0)),a.setAttribute("style","display:none;"),a.setAttribute("id","printJS-html"),r.parentNode.appendChild(a),a=document.getElementById("printJS-html"),a.setAttribute("style",n.i(i.c)(a,e)+"margin:0 !important;");var d=a.children;n.i(i.d)(d,e),e.header&&n.i(i.e)(a,e.header),a.parentNode.removeChild(a),e.htmlData=n.i(i.a)(a.innerHTML,e),o.a.send(e,t)}}},function(e,t,n){"use strict";var i=n(2),o=n(0);t.a={print:function(e,t){var r=document.createElement("img");r.src=e.printable,r.onload=function(){r.setAttribute("style","width:100%;"),r.setAttribute("id","printableImage");var a=document.createElement("div");a.setAttribute("style","width:100%"),a.appendChild(r),e.header&&n.i(i.e)(a),e.htmlData=a.outerHTML,o.a.send(e,t)}}}},function(e,t,n){"use strict";var i=n(1),o=n(3),r=n(9),a=n(5),d=n(6),l=n(8),s="function"==typeof Symbol&&"symbol"==typeof Symbol.iterator?function(e){return typeof e}:function(e){return e&&"function"==typeof Symbol&&e.constructor===Symbol&&e!==Symbol.prototype?"symbol":typeof e},c=["pdf","html","image","json"];t.a={init:function(){var e={printable:null,type:"pdf",header:null,maxWidth:800,font:"TimesNewRoman",font_size:"12pt",honorMarginPadding:!0,honorColor:!1,properties:null,showModal:!1,modalMessage:"Retrieving Document...",frameId:"printJS",border:!0,htmlData:""},t=arguments[0];if(void 0===t)throw new Error("printJS expects at least 1 attribute.");switch(void 0===t?"undefined":s(t)){case"string":e.printable=encodeURI(t),e.type=arguments[1]||e.type;break;case"object":e.printable=t.printable,e.type=void 0!==t.type?t.type:e.type,e.frameId=void 0!==t.frameId?t.frameId:e.frameId,e.header=void 0!==t.header?t.header:e.header,e.maxWidth=void 0!==t.maxWidth?t.maxWidth:e.maxWidth,e.font=void 0!==t.font?t.font:e.font,e.font_size=void 0!==t.font_size?t.font_size:e.font_size,e.honorMarginPadding=void 0!==t.honorMarginPadding?t.honorMarginPadding:e.honorMarginPadding,e.properties=void 0!==t.properties?t.properties:e.properties,e.showModal=void 0!==t.showModal?t.showModal:e.showModal,e.modalMessage=void 0!==t.modalMessage?t.modalMessage:e.modalMessage;break;default:throw new Error('Unexpected argument type! Expected "string" or "object", got '+(void 0===t?"undefined":s(t)))}if(!e.printable)throw new Error("Missing printable information.");if(!e.type||"string"!=typeof e.type||-1===c.indexOf(e.type.toLowerCase()))throw new Error("Invalid print type. Available types are: pdf, html, image and json.");e.showModal&&o.a.show(e);var n=document.getElementById(e.frameId);n&&n.parentNode.removeChild(n);var p=void 0;switch(i.a.isIE()&&"pdf"===e.type?(p=document.createElement("embed"),p.setAttribute("type","application/pdf"),p.setAttribute("style","width:0px;height:0px;")):(p=document.createElement("iframe"),p.setAttribute("style","display:none;")),p.setAttribute("id",e.frameId),"pdf"!==e.type&&(i.a.isChrome()||i.a.isSafari())&&(p.srcdoc="<html><head></head><body></body></html>"),e.type){case"pdf":if(i.a.isFirefox()||i.a.isIE()||i.a.isEdge()){window.open(e.printable,"_blank").focus(),e.showModal&&o.a.close()}else r.a.print(e,p);break;case"image":d.a.print(e,p);break;case"html":a.a.print(e,p);break;case"json":l.a.print(e,p);break;default:throw new Error("Invalid print type. Available types are: pdf, html, image and json.")}}}},function(e,t,n){"use strict";function i(e){var t=e.printable,i=e.properties,r='<div style="display:flex; flex-direction: column;">';r+='<div style="flex:1; display:flex;">';for(var a=0;a<i.length;a++)r+='<div style="flex:1; padding:5px;">'+n.i(o.b)(i[a].displayName||i[a])+"</div>";r+="</div>";for(var d=0;d<t.length;d++){r+='<div style="flex:1; display:flex;',r+=e.border?"border:1px solid lightgray;":"",r+='">';for(var l=0;l<i.length;l++)r+='<div style="flex:1; padding:5px;">'+t[d][i[l].field||i[l]]+"</div>";r+="</div>"}return r+="</div>"}var o=n(2),r=n(0),a="function"==typeof Symbol&&"symbol"==typeof Symbol.iterator?function(e){return typeof e}:function(e){return e&&"function"==typeof Symbol&&e.constructor===Symbol&&e!==Symbol.prototype?"symbol":typeof e};t.a={print:function(e,t){if("object"!==a(e.printable))throw new Error("Invalid javascript data object (JSON).");if(!e.properties||"object"!==a(e.properties))throw new Error("Invalid properties array for your JSON data.");var d="";e.header&&(d+='<h1 style="font-weight:300;">'+e.header+"</h1>"),d+=i(e),e.htmlData=n.i(o.a)(d,e),r.a.send(e,t)}}},function(e,t,n){"use strict";function i(e,t){t.setAttribute("src",e.printable),r.a.send(e,t)}var o=n(1),r=n(0);t.a={print:function(e,t){if(e.showModal&&!o.a.isIE()){var n=document.createElement("img");n.src=e.printable;new Promise(function(e,t){function i(){n.complete&&(window.clearInterval(o),e("PrintJS: PDF loaded."))}var o=setInterval(i,100)}).then(function(n){i(e,t)})}else i(e,t)}}},function(e,t,n){e.exports=n(4)}]);
\ No newline at end of file
diff --git a/js/libs/screenfull.js b/js/libs/screenfull.js
deleted file mode 100644 (file)
index ff82f25..0000000
+++ /dev/null
@@ -1,168 +0,0 @@
-/*!
- * screenfull
- * v3.3.1 - 2017-07-07
- * (c) Sindre Sorhus; MIT License
- */
-(function () {
-       'use strict';
-
-       var document = typeof window !== 'undefined' && typeof window.document !== 'undefined' ? window.document : {};
-       var isCommonjs = typeof module !== 'undefined' && module.exports;
-       var keyboardAllowed = typeof Element !== 'undefined' && 'ALLOW_KEYBOARD_INPUT' in Element;
-
-       var fn = (function () {
-               var val;
-
-               var fnMap = [
-                       [
-                               'requestFullscreen',
-                               'exitFullscreen',
-                               'fullscreenElement',
-                               'fullscreenEnabled',
-                               'fullscreenchange',
-                               'fullscreenerror'
-                       ],
-                       // New WebKit
-                       [
-                               'webkitRequestFullscreen',
-                               'webkitExitFullscreen',
-                               'webkitFullscreenElement',
-                               'webkitFullscreenEnabled',
-                               'webkitfullscreenchange',
-                               'webkitfullscreenerror'
-
-                       ],
-                       // Old WebKit (Safari 5.1)
-                       [
-                               'webkitRequestFullScreen',
-                               'webkitCancelFullScreen',
-                               'webkitCurrentFullScreenElement',
-                               'webkitCancelFullScreen',
-                               'webkitfullscreenchange',
-                               'webkitfullscreenerror'
-
-                       ],
-                       [
-                               'mozRequestFullScreen',
-                               'mozCancelFullScreen',
-                               'mozFullScreenElement',
-                               'mozFullScreenEnabled',
-                               'mozfullscreenchange',
-                               'mozfullscreenerror'
-                       ],
-                       [
-                               'msRequestFullscreen',
-                               'msExitFullscreen',
-                               'msFullscreenElement',
-                               'msFullscreenEnabled',
-                               'MSFullscreenChange',
-                               'MSFullscreenError'
-                       ]
-               ];
-
-               var i = 0;
-               var l = fnMap.length;
-               var ret = {};
-
-               for (; i < l; i++) {
-                       val = fnMap[i];
-                       if (val && val[1] in document) {
-                               for (i = 0; i < val.length; i++) {
-                                       ret[fnMap[0][i]] = val[i];
-                               }
-                               return ret;
-                       }
-               }
-
-               return false;
-       })();
-
-       var eventNameMap = {
-               change: fn.fullscreenchange,
-               error: fn.fullscreenerror
-       };
-
-       var screenfull = {
-               request: function (elem) {
-                       var request = fn.requestFullscreen;
-
-                       elem = elem || document.documentElement;
-
-                       // Work around Safari 5.1 bug: reports support for
-                       // keyboard in fullscreen even though it doesn't.
-                       // Browser sniffing, since the alternative with
-                       // setTimeout is even worse.
-                       if (/5\.1[.\d]* Safari/.test(navigator.userAgent)) {
-                               elem[request]();
-                       } else {
-                               elem[request](keyboardAllowed && Element.ALLOW_KEYBOARD_INPUT);
-                       }
-               },
-               exit: function () {
-                       document[fn.exitFullscreen]();
-               },
-               toggle: function (elem) {
-                       if (this.isFullscreen) {
-                               this.exit();
-                       } else {
-                               this.request(elem);
-                       }
-               },
-               onchange: function (callback) {
-                       this.on('change', callback);
-               },
-               onerror: function (callback) {
-                       this.on('error', callback);
-               },
-               on: function (event, callback) {
-                       var eventName = eventNameMap[event];
-                       if (eventName) {
-                               document.addEventListener(eventName, callback, false);
-                       }
-               },
-               off: function (event, callback) {
-                       var eventName = eventNameMap[event];
-                       if (eventName) {
-                               document.removeEventListener(eventName, callback, false);
-                       }
-               },
-               raw: fn
-       };
-
-       if (!fn) {
-               if (isCommonjs) {
-                       module.exports = false;
-               } else {
-                       window.screenfull = false;
-               }
-
-               return;
-       }
-
-       Object.defineProperties(screenfull, {
-               isFullscreen: {
-                       get: function () {
-                               return Boolean(document[fn.fullscreenElement]);
-                       }
-               },
-               element: {
-                       enumerable: true,
-                       get: function () {
-                               return document[fn.fullscreenElement];
-                       }
-               },
-               enabled: {
-                       enumerable: true,
-                       get: function () {
-                               // Coerce to boolean in case of old WebKit
-                               return Boolean(document[fn.fullscreenEnabled]);
-                       }
-               }
-       });
-
-       if (isCommonjs) {
-               module.exports = screenfull;
-       } else {
-               window.screenfull = screenfull;
-       }
-})();
\ No newline at end of file
diff --git a/js/libs/screenfull.min.js b/js/libs/screenfull.min.js
new file mode 100644 (file)
index 0000000..d02dc81
--- /dev/null
@@ -0,0 +1,7 @@
+/*!
+* screenfull
+* v3.3.1 - 2017-07-07
+* (c) Sindre Sorhus; MIT License
+*/
+
+!function(){"use strict";var a="undefined"!=typeof window&&void 0!==window.document?window.document:{},b="undefined"!=typeof module&&module.exports,c="undefined"!=typeof Element&&"ALLOW_KEYBOARD_INPUT"in Element,d=function(){for(var b,c=[["requestFullscreen","exitFullscreen","fullscreenElement","fullscreenEnabled","fullscreenchange","fullscreenerror"],["webkitRequestFullscreen","webkitExitFullscreen","webkitFullscreenElement","webkitFullscreenEnabled","webkitfullscreenchange","webkitfullscreenerror"],["webkitRequestFullScreen","webkitCancelFullScreen","webkitCurrentFullScreenElement","webkitCancelFullScreen","webkitfullscreenchange","webkitfullscreenerror"],["mozRequestFullScreen","mozCancelFullScreen","mozFullScreenElement","mozFullScreenEnabled","mozfullscreenchange","mozfullscreenerror"],["msRequestFullscreen","msExitFullscreen","msFullscreenElement","msFullscreenEnabled","MSFullscreenChange","MSFullscreenError"]],d=0,e=c.length,f={};d<e;d++)if((b=c[d])&&b[1]in a){for(d=0;d<b.length;d++)f[c[0][d]]=b[d];return f}return!1}(),e={change:d.fullscreenchange,error:d.fullscreenerror},f={request:function(b){var e=d.requestFullscreen;b=b||a.documentElement,/5\.1[.\d]* Safari/.test(navigator.userAgent)?b[e]():b[e](c&&Element.ALLOW_KEYBOARD_INPUT)},exit:function(){a[d.exitFullscreen]()},toggle:function(a){this.isFullscreen?this.exit():this.request(a)},onchange:function(a){this.on("change",a)},onerror:function(a){this.on("error",a)},on:function(b,c){var d=e[b];d&&a.addEventListener(d,c,!1)},off:function(b,c){var d=e[b];d&&a.removeEventListener(d,c,!1)},raw:d};if(!d)return void(b?module.exports=!1:window.screenfull=!1);Object.defineProperties(f,{isFullscreen:{get:function(){return Boolean(a[d.fullscreenElement])}},element:{enumerable:!0,get:function(){return a[d.fullscreenElement]}},enabled:{enumerable:!0,get:function(){return Boolean(a[d.fullscreenEnabled])}}}),b?module.exports=f:window.screenfull=f}();
\ No newline at end of file