text: /******/ (function(modules) { // webpackBootstrap
  /******/ 	// The module cache
  /******/ 	var installedModules = {};
  /******/
  /******/ 	// The require function
  /******/ 	function __webpack_require__(moduleId) {
  /******/
  /******/ 		// Check if module is in cache
  /******/ 		if(installedModules[moduleId]) {
  /******/ 			return installedModules[moduleId].exports;
  /******/ 		}
  /******/ 		// Create a new module (and put it into the cache)
  /******/ 		var module = installedModules[moduleId] = {
  /******/ 			i: moduleId,
  /******/ 			l: false,
  /******/ 			exports: {}
  /******/ 		};
  /******/
  /******/ 		// Execute the module function
  /******/ 		modules[moduleId].call(module.exports, module, module.exports, __webpack_require__);
  /******/
  /******/ 		// Flag the module as loaded
  /******/ 		module.l = true;
  /******/
  /******/ 		// Return the exports of the module
  /******/ 		return module.exports;
  /******/ 	}
  /******/
  /******/
  /******/ 	// expose the modules object (__webpack_modules__)
  /******/ 	__webpack_require__.m = modules;
  /******/
  /******/ 	// expose the module cache
  /******/ 	__webpack_require__.c = installedModules;
  /******/
  /******/ 	// define getter function for harmony exports
  /******/ 	__webpack_require__.d = function(exports, name, getter) {
  /******/ 		if(!__webpack_require__.o(exports, name)) {
  /******/ 			Object.defineProperty(exports, name, { enumerable: true, get: getter });
  /******/ 		}
  /******/ 	};
  /******/
  /******/ 	// define __esModule on exports
  /******/ 	__webpack_require__.r = function(exports) {
  /******/ 		if(typeof Symbol !== 'undefined' && Symbol.toStringTag) {
  /******/ 			Object.defineProperty(exports, Symbol.toStringTag, { value: 'Module' });
  /******/ 		}
  /******/ 		Object.defineProperty(exports, '__esModule', { value: true });
  /******/ 	};
  /******/
  /******/ 	// create a fake namespace object
  /******/ 	// mode & 1: value is a module id, require it
  /******/ 	// mode & 2: merge all properties of value into the ns
  /******/ 	// mode & 4: return value when already ns object
  /******/ 	// mode & 8|1: behave like require
  /******/ 	__webpack_require__.t = function(value, mode) {
  /******/ 		if(mode & 1) value = __webpack_require__(value);
  /******/ 		if(mode & 8) return value;
  /******/ 		if((mode & 4) && typeof value === 'object' && value && value.__esModule) return value;
  /******/ 		var ns = Object.create(null);
  /******/ 		__webpack_require__.r(ns);
  /******/ 		Object.defineProperty(ns, 'default', { enumerable: true, value: value });
  /******/ 		if(mode & 2 && typeof value != 'string') for(var key in value) __webpack_require__.d(ns, key, function(key) { return value[key]; }.bind(null, key));
  /******/ 		return ns;
  /******/ 	};
  /******/
  /******/ 	// getDefaultExport function for compatibility with non-harmony modules
  /******/ 	__webpack_require__.n = function(module) {
  /******/ 		var getter = module && module.__esModule ?
  /******/ 			function getDefault() { return module['default']; } :
  /******/ 			function getModuleExports() { return module; };
  /******/ 		__webpack_require__.d(getter, 'a', getter);
  /******/ 		return getter;
  /******/ 	};
  /******/
  /******/ 	// Object.prototype.hasOwnProperty.call
  /******/ 	__webpack_require__.o = function(object, property) { return Object.prototype.hasOwnProperty.call(object, property); };
  /******/
  /******/ 	// __webpack_public_path__
  /******/ 	__webpack_require__.p = "";
  /******/
  /******/
  /******/ 	// Load entry module and return exports
  /******/ 	return __webpack_require__(__webpack_require__.s = "./public/assets/src/js/index.js");
  /******/ })
  /************************************************************************/
  /******/ ({
  
  /***/ "./node_modules/@glidejs/glide/dist/glide.esm.js":
  /*!*******************************************************!*\
    !*** ./node_modules/@glidejs/glide/dist/glide.esm.js ***!
    \*******************************************************/
  /*! exports provided: default */
  /***/ (function(module, __webpack_exports__, __webpack_require__) {
  
  "use strict";
  eval("__webpack_require__.r(__webpack_exports__);\n/*!\n * Glide.js v3.3.0\n * (c) 2013-2019 Jędrzej Chałubek <jedrzej.chalubek@gmail.com> (http://jedrzejchalubek.com/)\n * Released under the MIT License.\n */\n\nvar defaults = {\n  /**\n   * Type of the movement.\n   *\n   * Available types:\n   * `slider` - Rewinds slider to the start/end when it reaches the first or last slide.\n   * `carousel` - Changes slides without starting over when it reaches the first or last slide.\n   *\n   * @type {String}\n   */\n  type: 'slider',\n\n  /**\n   * Start at specific slide number defined with zero-based index.\n   *\n   * @type {Number}\n   */\n  startAt: 0,\n\n  /**\n   * A number of slides visible on the single viewport.\n   *\n   * @type {Number}\n   */\n  perView: 1,\n\n  /**\n   * Focus currently active slide at a specified position in the track.\n   *\n   * Available inputs:\n   * `center` - Current slide will be always focused at the center of a track.\n   * `0,1,2,3...` - Current slide will be focused on the specified zero-based index.\n   *\n   * @type {String|Number}\n   */\n  focusAt: 0,\n\n  /**\n   * A size of the gap added between slides.\n   *\n   * @type {Number}\n   */\n  gap: 10,\n\n  /**\n   * Change slides after a specified interval. Use `false` for turning off autoplay.\n   *\n   * @type {Number|Boolean}\n   */\n  autoplay: false,\n\n  /**\n   * Stop autoplay on mouseover event.\n   *\n   * @type {Boolean}\n   */\n  hoverpause: true,\n\n  /**\n   * Allow for changing slides with left and right keyboard arrows.\n   *\n   * @type {Boolean}\n   */\n  keyboard: true,\n\n  /**\n   * Stop running `perView` number of slides from the end. Use this\n   * option if you don't want to have an empty space after\n   * a slider. Works only with `slider` type and a\n   * non-centered `focusAt` setting.\n   *\n   * @type {Boolean}\n   */\n  bound: false,\n\n  /**\n   * Minimal swipe distance needed to change the slide. Use `false` for turning off a swiping.\n   *\n   * @type {Number|Boolean}\n   */\n  swipeThreshold: 80,\n\n  /**\n   * Minimal mouse drag distance needed to change the slide. Use `false` for turning off a dragging.\n   *\n   * @type {Number|Boolean}\n   */\n  dragThreshold: 120,\n\n  /**\n   * A maximum number of slides to which movement will be made on swiping or dragging. Use `false` for unlimited.\n   *\n   * @type {Number|Boolean}\n   */\n  perTouch: false,\n\n  /**\n   * Moving distance ratio of the slides on a swiping and dragging.\n   *\n   * @type {Number}\n   */\n  touchRatio: 0.5,\n\n  /**\n   * Angle required to activate slides moving on swiping or dragging.\n   *\n   * @type {Number}\n   */\n  touchAngle: 45,\n\n  /**\n   * Duration of the animation in milliseconds.\n   *\n   * @type {Number}\n   */\n  animationDuration: 400,\n\n  /**\n   * Allows looping the `slider` type. Slider will rewind to the first/last slide when it's at the start/end.\n   *\n   * @type {Boolean}\n   */\n  rewind: true,\n\n  /**\n   * Duration of the rewinding animation of the `slider` type in milliseconds.\n   *\n   * @type {Number}\n   */\n  rewindDuration: 800,\n\n  /**\n   * Easing function for the animation.\n   *\n   * @type {String}\n   */\n  animationTimingFunc: 'cubic-bezier(.165, .840, .440, 1)',\n\n  /**\n   * Throttle costly events at most once per every wait milliseconds.\n   *\n   * @type {Number}\n   */\n  throttle: 10,\n\n  /**\n   * Moving direction mode.\n   *\n   * Available inputs:\n   * - 'ltr' - left to right movement,\n   * - 'rtl' - right to left movement.\n   *\n   * @type {String}\n   */\n  direction: 'ltr',\n\n  /**\n   * The distance value of the next and previous viewports which\n   * have to peek in the current view. Accepts number and\n   * pixels as a string. Left and right peeking can be\n   * set up separately with a directions object.\n   *\n   * For example:\n   * `100` - Peek 100px on the both sides.\n   * { before: 100, after: 50 }` - Peek 100px on the left side and 50px on the right side.\n   *\n   * @type {Number|String|Object}\n   */\n  peek: 0,\n\n  /**\n   * Collection of options applied at specified media breakpoints.\n   * For example: display two slides per view under 800px.\n   * `{\n   *   '800px': {\n   *     perView: 2\n   *   }\n   * }`\n   */\n  breakpoints: {},\n\n  /**\n   * Collection of internally used HTML classes.\n   *\n   * @todo Refactor `slider` and `carousel` properties to single `type: { slider: '', carousel: '' }` object\n   * @type {Object}\n   */\n  classes: {\n    direction: {\n      ltr: 'glide--ltr',\n      rtl: 'glide--rtl'\n    },\n    slider: 'glide--slider',\n    carousel: 'glide--carousel',\n    swipeable: 'glide--swipeable',\n    dragging: 'glide--dragging',\n    cloneSlide: 'glide__slide--clone',\n    activeNav: 'glide__bullet--active',\n    activeSlide: 'glide__slide--active',\n    disabledArrow: 'glide__arrow--disabled'\n  }\n};\n\n/**\n * Outputs warning message to the bowser console.\n *\n * @param  {String} msg\n * @return {Void}\n */\nfunction warn(msg) {\n  console.error(\"[Glide warn]: \" + msg);\n}\n\nvar _typeof = typeof Symbol === \"function\" && typeof Symbol.iterator === \"symbol\" ? function (obj) {\n  return typeof obj;\n} : function (obj) {\n  return obj && typeof Symbol === \"function\" && obj.constructor === Symbol && obj !== Symbol.prototype ? \"symbol\" : typeof obj;\n};\n\nvar classCallCheck = function (instance, Constructor) {\n  if (!(instance instanceof Constructor)) {\n    throw new TypeError(\"Cannot call a class as a function\");\n  }\n};\n\nvar createClass = function () {\n  function defineProperties(target, props) {\n    for (var i = 0; i < props.length; i++) {\n      var descriptor = props[i];\n      descriptor.enumerable = descriptor.enumerable || false;\n      descriptor.configurable = true;\n      if (\"value\" in descriptor) descriptor.writable = true;\n      Object.defineProperty(target, descriptor.key, descriptor);\n    }\n  }\n\n  return function (Constructor, protoProps, staticProps) {\n    if (protoProps) defineProperties(Constructor.prototype, protoProps);\n    if (staticProps) defineProperties(Constructor, staticProps);\n    return Constructor;\n  };\n}();\n\nvar _extends = Object.assign || function (target) {\n  for (var i = 1; i < arguments.length; i++) {\n    var source = arguments[i];\n\n    for (var key in source) {\n      if (Object.prototype.hasOwnProperty.call(source, key)) {\n        target[key] = source[key];\n      }\n    }\n  }\n\n  return target;\n};\n\nvar get = function get(object, property, receiver) {\n  if (object === null) object = Function.prototype;\n  var desc = Object.getOwnPropertyDescriptor(object, property);\n\n  if (desc === undefined) {\n    var parent = Object.getPrototypeOf(object);\n\n    if (parent === null) {\n      return undefined;\n    } else {\n      return get(parent, property, receiver);\n    }\n  } else if (\"value\" in desc) {\n    return desc.value;\n  } else {\n    var getter = desc.get;\n\n    if (getter === undefined) {\n      return undefined;\n    }\n\n    return getter.call(receiver);\n  }\n};\n\nvar inherits = function (subClass, superClass) {\n  if (typeof superClass !== \"function\" && superClass !== null) {\n    throw new TypeError(\"Super expression must either be null or a function, not \" + typeof superClass);\n  }\n\n  subClass.prototype = Object.create(superClass && superClass.prototype, {\n    constructor: {\n      value: subClass,\n      enumerable: false,\n      writable: true,\n      configurable: true\n    }\n  });\n  if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass;\n};\n\nvar possibleConstructorReturn = function (self, call) {\n  if (!self) {\n    throw new ReferenceError(\"this hasn't been initialised - super() hasn't been called\");\n  }\n\n  return call && (typeof call === \"object\" || typeof call === \"function\") ? call : self;\n};\n\n/**\n * Converts value entered as number\n * or string to integer value.\n *\n * @param {String} value\n * @returns {Number}\n */\nfunction toInt(value) {\n  return parseInt(value);\n}\n\n/**\n * Converts value entered as number\n * or string to flat value.\n *\n * @param {String} value\n * @returns {Number}\n */\nfunction toFloat(value) {\n  return parseFloat(value);\n}\n\n/**\n * Indicates whether the specified value is a string.\n *\n * @param  {*}   value\n * @return {Boolean}\n */\nfunction isString(value) {\n  return typeof value === 'string';\n}\n\n/**\n * Indicates whether the specified value is an object.\n *\n * @param  {*} value\n * @return {Boolean}\n *\n * @see https://github.com/jashkenas/underscore\n */\nfunction isObject(value) {\n  var type = typeof value === 'undefined' ? 'undefined' : _typeof(value);\n\n  return type === 'function' || type === 'object' && !!value; // eslint-disable-line no-mixed-operators\n}\n\n/**\n * Indicates whether the specified value is a number.\n *\n * @param  {*} value\n * @return {Boolean}\n */\nfunction isNumber(value) {\n  return typeof value === 'number';\n}\n\n/**\n * Indicates whether the specified value is a function.\n *\n * @param  {*} value\n * @return {Boolean}\n */\nfunction isFunction(value) {\n  return typeof value === 'function';\n}\n\n/**\n * Indicates whether the specified value is undefined.\n *\n * @param  {*} value\n * @return {Boolean}\n */\nfunction isUndefined(value) {\n  return typeof value === 'undefined';\n}\n\n/**\n * Indicates whether the specified value is an array.\n *\n * @param  {*} value\n * @return {Boolean}\n */\nfunction isArray(value) {\n  return value.constructor === Array;\n}\n\n/**\n * Creates and initializes specified collection of extensions.\n * Each extension receives access to instance of glide and rest of components.\n *\n * @param {Object} glide\n * @param {Object} extensions\n *\n * @returns {Object}\n */\nfunction mount(glide, extensions, events) {\n  var components = {};\n\n  for (var name in extensions) {\n    if (isFunction(extensions[name])) {\n      components[name] = extensions[name](glide, components, events);\n    } else {\n      warn('Extension must be a function');\n    }\n  }\n\n  for (var _name in components) {\n    if (isFunction(components[_name].mount)) {\n      components[_name].mount();\n    }\n  }\n\n  return components;\n}\n\n/**\n * Defines getter and setter property on the specified object.\n *\n * @param  {Object} obj         Object where property has to be defined.\n * @param  {String} prop        Name of the defined property.\n * @param  {Object} definition  Get and set definitions for the property.\n * @return {Void}\n */\nfunction define(obj, prop, definition) {\n  Object.defineProperty(obj, prop, definition);\n}\n\n/**\n * Sorts aphabetically object keys.\n *\n * @param  {Object} obj\n * @return {Object}\n */\nfunction sortKeys(obj) {\n  return Object.keys(obj).sort().reduce(function (r, k) {\n    r[k] = obj[k];\n\n    return r[k], r;\n  }, {});\n}\n\n/**\n * Merges passed settings object with default options.\n *\n * @param  {Object} defaults\n * @param  {Object} settings\n * @return {Object}\n */\nfunction mergeOptions(defaults, settings) {\n  var options = _extends({}, defaults, settings);\n\n  // `Object.assign` do not deeply merge objects, so we\n  // have to do it manually for every nested object\n  // in options. Although it does not look smart,\n  // it's smaller and faster than some fancy\n  // merging deep-merge algorithm script.\n  if (settings.hasOwnProperty('classes')) {\n    options.classes = _extends({}, defaults.classes, settings.classes);\n\n    if (settings.classes.hasOwnProperty('direction')) {\n      options.classes.direction = _extends({}, defaults.classes.direction, settings.classes.direction);\n    }\n  }\n\n  if (settings.hasOwnProperty('breakpoints')) {\n    options.breakpoints = _extends({}, defaults.breakpoints, settings.breakpoints);\n  }\n\n  return options;\n}\n\nvar EventsBus = function () {\n  /**\n   * Construct a EventBus instance.\n   *\n   * @param {Object} events\n   */\n  function EventsBus() {\n    var events = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : {};\n    classCallCheck(this, EventsBus);\n\n    this.events = events;\n    this.hop = events.hasOwnProperty;\n  }\n\n  /**\n   * Adds listener to the specifed event.\n   *\n   * @param {String|Array} event\n   * @param {Function} handler\n   */\n\n\n  createClass(EventsBus, [{\n    key: 'on',\n    value: function on(event, handler) {\n      if (isArray(event)) {\n        for (var i = 0; i < event.length; i++) {\n          this.on(event[i], handler);\n        }\n      }\n\n      // Create the event's object if not yet created\n      if (!this.hop.call(this.events, event)) {\n        this.events[event] = [];\n      }\n\n      // Add the handler to queue\n      var index = this.events[event].push(handler) - 1;\n\n      // Provide handle back for removal of event\n      return {\n        remove: function remove() {\n          delete this.events[event][index];\n        }\n      };\n    }\n\n    /**\n     * Runs registered handlers for specified event.\n     *\n     * @param {String|Array} event\n     * @param {Object=} context\n     */\n\n  }, {\n    key: 'emit',\n    value: function emit(event, context) {\n      if (isArray(event)) {\n        for (var i = 0; i < event.length; i++) {\n          this.emit(event[i], context);\n        }\n      }\n\n      // If the event doesn't exist, or there's no handlers in queue, just leave\n      if (!this.hop.call(this.events, event)) {\n        return;\n      }\n\n      // Cycle through events queue, fire!\n      this.events[event].forEach(function (item) {\n        item(context || {});\n      });\n    }\n  }]);\n  return EventsBus;\n}();\n\nvar Glide = function () {\n  /**\r\n   * Construct glide.\r\n   *\r\n   * @param  {String} selector\r\n   * @param  {Object} options\r\n   */\n  function Glide(selector) {\n    var options = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : {};\n    classCallCheck(this, Glide);\n\n    this._c = {};\n    this._t = [];\n    this._e = new EventsBus();\n\n    this.disabled = false;\n    this.selector = selector;\n    this.settings = mergeOptions(defaults, options);\n    this.index = this.settings.startAt;\n  }\n\n  /**\r\n   * Initializes glide.\r\n   *\r\n   * @param {Object} extensions Collection of extensions to initialize.\r\n   * @return {Glide}\r\n   */\n\n\n  createClass(Glide, [{\n    key: 'mount',\n    value: function mount$$1() {\n      var extensions = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : {};\n\n      this._e.emit('mount.before');\n\n      if (isObject(extensions)) {\n        this._c = mount(this, extensions, this._e);\n      } else {\n        warn('You need to provide a object on `mount()`');\n      }\n\n      this._e.emit('mount.after');\n\n      return this;\n    }\n\n    /**\r\n     * Collects an instance `translate` transformers.\r\n     *\r\n     * @param  {Array} transformers Collection of transformers.\r\n     * @return {Void}\r\n     */\n\n  }, {\n    key: 'mutate',\n    value: function mutate() {\n      var transformers = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : [];\n\n      if (isArray(transformers)) {\n        this._t = transformers;\n      } else {\n        warn('You need to provide a array on `mutate()`');\n      }\n\n      return this;\n    }\n\n    /**\r\n     * Updates glide with specified settings.\r\n     *\r\n     * @param {Object} settings\r\n     * @return {Glide}\r\n     */\n\n  }, {\n    key: 'update',\n    value: function update() {\n      var settings = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : {};\n\n      this.settings = mergeOptions(this.settings, settings);\n\n      if (settings.hasOwnProperty('startAt')) {\n        this.index = settings.startAt;\n      }\n\n      this._e.emit('update');\n\n      return this;\n    }\n\n    /**\r\n     * Change slide with specified pattern. A pattern must be in the special format:\r\n     * `>` - Move one forward\r\n     * `<` - Move one backward\r\n     * `={i}` - Go to {i} zero-based slide (eq. '=1', will go to second slide)\r\n     * `>>` - Rewinds to end (last slide)\r\n     * `<<` - Rewinds to start (first slide)\r\n     *\r\n     * @param {String} pattern\r\n     * @return {Glide}\r\n     */\n\n  }, {\n    key: 'go',\n    value: function go(pattern) {\n      this._c.Run.make(pattern);\n\n      return this;\n    }\n\n    /**\r\n     * Move track by specified distance.\r\n     *\r\n     * @param {String} distance\r\n     * @return {Glide}\r\n     */\n\n  }, {\n    key: 'move',\n    value: function move(distance) {\n      this._c.Transition.disable();\n      this._c.Move.make(distance);\n\n      return this;\n    }\n\n    /**\r\n     * Destroy instance and revert all changes done by this._c.\r\n     *\r\n     * @return {Glide}\r\n     */\n\n  }, {\n    key: 'destroy',\n    value: function destroy() {\n      this._e.emit('destroy');\n\n      return this;\n    }\n\n    /**\r\n     * Start instance autoplaying.\r\n     *\r\n     * @param {Boolean|Number} interval Run autoplaying with passed interval regardless of `autoplay` settings\r\n     * @return {Glide}\r\n     */\n\n  }, {\n    key: 'play',\n    value: function play() {\n      var interval = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : false;\n\n      if (interval) {\n        this.settings.autoplay = interval;\n      }\n\n      this._e.emit('play');\n\n      return this;\n    }\n\n    /**\r\n     * Stop instance autoplaying.\r\n     *\r\n     * @return {Glide}\r\n     */\n\n  }, {\n    key: 'pause',\n    value: function pause() {\n      this._e.emit('pause');\n\n      return this;\n    }\n\n    /**\r\n     * Sets glide into a idle status.\r\n     *\r\n     * @return {Glide}\r\n     */\n\n  }, {\n    key: 'disable',\n    value: function disable() {\n      this.disabled = true;\n\n      return this;\n    }\n\n    /**\r\n     * Sets glide into a active status.\r\n     *\r\n     * @return {Glide}\r\n     */\n\n  }, {\n    key: 'enable',\n    value: function enable() {\n      this.disabled = false;\n\n      return this;\n    }\n\n    /**\r\n     * Adds cuutom event listener with handler.\r\n     *\r\n     * @param  {String|Array} event\r\n     * @param  {Function} handler\r\n     * @return {Glide}\r\n     */\n\n  }, {\n    key: 'on',\n    value: function on(event, handler) {\n      this._e.on(event, handler);\n\n      return this;\n    }\n\n    /**\r\n     * Checks if glide is a precised type.\r\n     *\r\n     * @param  {String} name\r\n     * @return {Boolean}\r\n     */\n\n  }, {\n    key: 'isType',\n    value: function isType(name) {\n      return this.settings.type === name;\n    }\n\n    /**\r\n     * Gets value of the core options.\r\n     *\r\n     * @return {Object}\r\n     */\n\n  }, {\n    key: 'settings',\n    get: function get$$1() {\n      return this._o;\n    }\n\n    /**\r\n     * Sets value of the core options.\r\n     *\r\n     * @param  {Object} o\r\n     * @return {Void}\r\n     */\n    ,\n    set: function set$$1(o) {\n      if (isObject(o)) {\n        this._o = o;\n      } else {\n        warn('Options must be an `object` instance.');\n      }\n    }\n\n    /**\r\n     * Gets current index of the slider.\r\n     *\r\n     * @return {Object}\r\n     */\n\n  }, {\n    key: 'index',\n    get: function get$$1() {\n      return this._i;\n    }\n\n    /**\r\n     * Sets current index a slider.\r\n     *\r\n     * @return {Object}\r\n     */\n    ,\n    set: function set$$1(i) {\n      this._i = toInt(i);\n    }\n\n    /**\r\n     * Gets type name of the slider.\r\n     *\r\n     * @return {String}\r\n     */\n\n  }, {\n    key: 'type',\n    get: function get$$1() {\n      return this.settings.type;\n    }\n\n    /**\r\n     * Gets value of the idle status.\r\n     *\r\n     * @return {Boolean}\r\n     */\n\n  }, {\n    key: 'disabled',\n    get: function get$$1() {\n      return this._d;\n    }\n\n    /**\r\n     * Sets value of the idle status.\r\n     *\r\n     * @return {Boolean}\r\n     */\n    ,\n    set: function set$$1(status) {\n      this._d = !!status;\n    }\n  }]);\n  return Glide;\n}();\n\nfunction Run (Glide, Components, Events) {\n  var Run = {\n    /**\n     * Initializes autorunning of the glide.\n     *\n     * @return {Void}\n     */\n    mount: function mount() {\n      this._o = false;\n    },\n\n\n    /**\n     * Makes glides running based on the passed moving schema.\n     *\n     * @param {String} move\n     */\n    make: function make(move) {\n      var _this = this;\n\n      if (!Glide.disabled) {\n        Glide.disable();\n\n        this.move = move;\n\n        Events.emit('run.before', this.move);\n\n        this.calculate();\n\n        Events.emit('run', this.move);\n\n        Components.Transition.after(function () {\n          if (_this.isStart()) {\n            Events.emit('run.start', _this.move);\n          }\n\n          if (_this.isEnd()) {\n            Events.emit('run.end', _this.move);\n          }\n\n          if (_this.isOffset('<') || _this.isOffset('>')) {\n            _this._o = false;\n\n            Events.emit('run.offset', _this.move);\n          }\n\n          Events.emit('run.after', _this.move);\n\n          Glide.enable();\n        });\n      }\n    },\n\n\n    /**\n     * Calculates current index based on defined move.\n     *\n     * @return {Void}\n     */\n    calculate: function calculate() {\n      var move = this.move,\n          length = this.length;\n      var steps = move.steps,\n          direction = move.direction;\n\n\n      var countableSteps = isNumber(toInt(steps)) && toInt(steps) !== 0;\n\n      switch (direction) {\n        case '>':\n          if (steps === '>') {\n            Glide.index = length;\n          } else if (this.isEnd()) {\n            if (!(Glide.isType('slider') && !Glide.settings.rewind)) {\n              this._o = true;\n\n              Glide.index = 0;\n            }\n          } else if (countableSteps) {\n            Glide.index += Math.min(length - Glide.index, -toInt(steps));\n          } else {\n            Glide.index++;\n          }\n          break;\n\n        case '<':\n          if (steps === '<') {\n            Glide.index = 0;\n          } else if (this.isStart()) {\n            if (!(Glide.isType('slider') && !Glide.settings.rewind)) {\n              this._o = true;\n\n              Glide.index = length;\n            }\n          } else if (countableSteps) {\n            Glide.index -= Math.min(Glide.index, toInt(steps));\n          } else {\n            Glide.index--;\n          }\n          break;\n\n        case '=':\n          Glide.index = steps;\n          break;\n\n        default:\n          warn('Invalid direction pattern [' + direction + steps + '] has been used');\n          break;\n      }\n    },\n\n\n    /**\n     * Checks if we are on the first slide.\n     *\n     * @return {Boolean}\n     */\n    isStart: function isStart() {\n      return Glide.index === 0;\n    },\n\n\n    /**\n     * Checks if we are on the last slide.\n     *\n     * @return {Boolean}\n     */\n    isEnd: function isEnd() {\n      return Glide.index === this.length;\n    },\n\n\n    /**\n     * Checks if we are making a offset run.\n     *\n     * @param {String} direction\n     * @return {Boolean}\n     */\n    isOffset: function isOffset(direction) {\n      return this._o && this.move.direction === direction;\n    }\n  };\n\n  define(Run, 'move', {\n    /**\n     * Gets value of the move schema.\n     *\n     * @returns {Object}\n     */\n    get: function get() {\n      return this._m;\n    },\n\n\n    /**\n     * Sets value of the move schema.\n     *\n     * @returns {Object}\n     */\n    set: function set(value) {\n      var step = value.substr(1);\n\n      this._m = {\n        direction: value.substr(0, 1),\n        steps: step ? toInt(step) ? toInt(step) : step : 0\n      };\n    }\n  });\n\n  define(Run, 'length', {\n    /**\n     * Gets value of the running distance based\n     * on zero-indexing number of slides.\n     *\n     * @return {Number}\n     */\n    get: function get() {\n      var settings = Glide.settings;\n      var length = Components.Html.slides.length;\n\n      // If the `bound` option is acitve, a maximum running distance should be\n      // reduced by `perView` and `focusAt` settings. Running distance\n      // should end before creating an empty space after instance.\n\n      if (Glide.isType('slider') && settings.focusAt !== 'center' && settings.bound) {\n        return length - 1 - (toInt(settings.perView) - 1) + toInt(settings.focusAt);\n      }\n\n      return length - 1;\n    }\n  });\n\n  define(Run, 'offset', {\n    /**\n     * Gets status of the offsetting flag.\n     *\n     * @return {Boolean}\n     */\n    get: function get() {\n      return this._o;\n    }\n  });\n\n  return Run;\n}\n\n/**\n * Returns a current time.\n *\n * @return {Number}\n */\nfunction now() {\n  return new Date().getTime();\n}\n\n/**\n * Returns a function, that, when invoked, will only be triggered\n * at most once during a given window of time.\n *\n * @param {Function} func\n * @param {Number} wait\n * @param {Object=} options\n * @return {Function}\n *\n * @see https://github.com/jashkenas/underscore\n */\nfunction throttle(func, wait, options) {\n  var timeout = void 0,\n      context = void 0,\n      args = void 0,\n      result = void 0;\n  var previous = 0;\n  if (!options) options = {};\n\n  var later = function later() {\n    previous = options.leading === false ? 0 : now();\n    timeout = null;\n    result = func.apply(context, args);\n    if (!timeout) context = args = null;\n  };\n\n  var throttled = function throttled() {\n    var at = now();\n    if (!previous && options.leading === false) previous = at;\n    var remaining = wait - (at - previous);\n    context = this;\n    args = arguments;\n    if (remaining <= 0 || remaining > wait) {\n      if (timeout) {\n        clearTimeout(timeout);\n        timeout = null;\n      }\n      previous = at;\n      result = func.apply(context, args);\n      if (!timeout) context = args = null;\n    } else if (!timeout && options.trailing !== false) {\n      timeout = setTimeout(later, remaining);\n    }\n    return result;\n  };\n\n  throttled.cancel = function () {\n    clearTimeout(timeout);\n    previous = 0;\n    timeout = context = args = null;\n  };\n\n  return throttled;\n}\n\nvar MARGIN_TYPE = {\n  ltr: ['marginLeft', 'marginRight'],\n  rtl: ['marginRight', 'marginLeft']\n};\n\nfunction Gaps (Glide, Components, Events) {\n  var Gaps = {\n    /**\n     * Applies gaps between slides. First and last\n     * slides do not receive it's edge margins.\n     *\n     * @param {HTMLCollection} slides\n     * @return {Void}\n     */\n    apply: function apply(slides) {\n      for (var i = 0, len = slides.length; i < len; i++) {\n        var style = slides[i].style;\n        var direction = Components.Direction.value;\n\n        if (i !== 0) {\n          style[MARGIN_TYPE[direction][0]] = this.value / 2 + 'px';\n        } else {\n          style[MARGIN_TYPE[direction][0]] = '';\n        }\n\n        if (i !== slides.length - 1) {\n          style[MARGIN_TYPE[direction][1]] = this.value / 2 + 'px';\n        } else {\n          style[MARGIN_TYPE[direction][1]] = '';\n        }\n      }\n    },\n\n\n    /**\n     * Removes gaps from the slides.\n     *\n     * @param {HTMLCollection} slides\n     * @returns {Void}\n    */\n    remove: function remove(slides) {\n      for (var i = 0, len = slides.length; i < len; i++) {\n        var style = slides[i].style;\n\n        style.marginLeft = '';\n        style.marginRight = '';\n      }\n    }\n  };\n\n  define(Gaps, 'value', {\n    /**\n     * Gets value of the gap.\n     *\n     * @returns {Number}\n     */\n    get: function get() {\n      return toInt(Glide.settings.gap);\n    }\n  });\n\n  define(Gaps, 'grow', {\n    /**\n     * Gets additional dimentions value caused by gaps.\n     * Used to increase width of the slides wrapper.\n     *\n     * @returns {Number}\n     */\n    get: function get() {\n      return Gaps.value * (Components.Sizes.length - 1);\n    }\n  });\n\n  define(Gaps, 'reductor', {\n    /**\n     * Gets reduction value caused by gaps.\n     * Used to subtract width of the slides.\n     *\n     * @returns {Number}\n     */\n    get: function get() {\n      var perView = Glide.settings.perView;\n\n      return Gaps.value * (perView - 1) / perView;\n    }\n  });\n\n  /**\n   * Apply calculated gaps:\n   * - after building, so slides (including clones) will receive proper margins\n   * - on updating via API, to recalculate gaps with new options\n   */\n  Events.on(['build.after', 'update'], throttle(function () {\n    Gaps.apply(Components.Html.wrapper.children);\n  }, 30));\n\n  /**\n   * Remove gaps:\n   * - on destroying to bring markup to its inital state\n   */\n  Events.on('destroy', function () {\n    Gaps.remove(Components.Html.wrapper.children);\n  });\n\n  return Gaps;\n}\n\n/**\n * Finds siblings nodes of the passed node.\n *\n * @param  {Element} node\n * @return {Array}\n */\nfunction siblings(node) {\n  if (node && node.parentNode) {\n    var n = node.parentNode.firstChild;\n    var matched = [];\n\n    for (; n; n = n.nextSibling) {\n      if (n.nodeType === 1 && n !== node) {\n        matched.push(n);\n      }\n    }\n\n    return matched;\n  }\n\n  return [];\n}\n\n/**\n * Checks if passed node exist and is a valid element.\n *\n * @param  {Element} node\n * @return {Boolean}\n */\nfunction exist(node) {\n  if (node && node instanceof window.HTMLElement) {\n    return true;\n  }\n\n  return false;\n}\n\nvar TRACK_SELECTOR = '[data-glide-el=\"track\"]';\n\nfunction Html (Glide, Components) {\n  var Html = {\n    /**\n     * Setup slider HTML nodes.\n     *\n     * @param {Glide} glide\n     */\n    mount: function mount() {\n      this.root = Glide.selector;\n      this.track = this.root.querySelector(TRACK_SELECTOR);\n      this.slides = Array.prototype.slice.call(this.wrapper.children).filter(function (slide) {\n        return !slide.classList.contains(Glide.settings.classes.cloneSlide);\n      });\n    }\n  };\n\n  define(Html, 'root', {\n    /**\n     * Gets node of the glide main element.\n     *\n     * @return {Object}\n     */\n    get: function get() {\n      return Html._r;\n    },\n\n\n    /**\n     * Sets node of the glide main element.\n     *\n     * @return {Object}\n     */\n    set: function set(r) {\n      if (isString(r)) {\n        r = document.querySelector(r);\n      }\n\n      if (exist(r)) {\n        Html._r = r;\n      } else {\n        warn('Root element must be a existing Html node');\n      }\n    }\n  });\n\n  define(Html, 'track', {\n    /**\n     * Gets node of the glide track with slides.\n     *\n     * @return {Object}\n     */\n    get: function get() {\n      return Html._t;\n    },\n\n\n    /**\n     * Sets node of the glide track with slides.\n     *\n     * @return {Object}\n     */\n    set: function set(t) {\n      if (exist(t)) {\n        Html._t = t;\n      } else {\n        warn('Could not find track element. Please use ' + TRACK_SELECTOR + ' attribute.');\n      }\n    }\n  });\n\n  define(Html, 'wrapper', {\n    /**\n     * Gets node of the slides wrapper.\n     *\n     * @return {Object}\n     */\n    get: function get() {\n      return Html.track.children[0];\n    }\n  });\n\n  return Html;\n}\n\nfunction Peek (Glide, Components, Events) {\n  var Peek = {\n    /**\n     * Setups how much to peek based on settings.\n     *\n     * @return {Void}\n     */\n    mount: function mount() {\n      this.value = Glide.settings.peek;\n    }\n  };\n\n  define(Peek, 'value', {\n    /**\n     * Gets value of the peek.\n     *\n     * @returns {Number|Object}\n     */\n    get: function get() {\n      return Peek._v;\n    },\n\n\n    /**\n     * Sets value of the peek.\n     *\n     * @param {Number|Object} value\n     * @return {Void}\n     */\n    set: function set(value) {\n      if (isObject(value)) {\n        value.before = toInt(value.before);\n        value.after = toInt(value.after);\n      } else {\n        value = toInt(value);\n      }\n\n      Peek._v = value;\n    }\n  });\n\n  define(Peek, 'reductor', {\n    /**\n     * Gets reduction value caused by peek.\n     *\n     * @returns {Number}\n     */\n    get: function get() {\n      var value = Peek.value;\n      var perView = Glide.settings.perView;\n\n      if (isObject(value)) {\n        return value.before / perView + value.after / perView;\n      }\n\n      return value * 2 / perView;\n    }\n  });\n\n  /**\n   * Recalculate peeking sizes on:\n   * - when resizing window to update to proper percents\n   */\n  Events.on(['resize', 'update'], function () {\n    Peek.mount();\n  });\n\n  return Peek;\n}\n\nfunction Move (Glide, Components, Events) {\n  var Move = {\n    /**\n     * Constructs move component.\n     *\n     * @returns {Void}\n     */\n    mount: function mount() {\n      this._o = 0;\n    },\n\n\n    /**\n     * Calculates a movement value based on passed offset and currently active index.\n     *\n     * @param  {Number} offset\n     * @return {Void}\n     */\n    make: function make() {\n      var _this = this;\n\n      var offset = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : 0;\n\n      this.offset = offset;\n\n      Events.emit('move', {\n        movement: this.value\n      });\n\n      Components.Transition.after(function () {\n        Events.emit('move.after', {\n          movement: _this.value\n        });\n      });\n    }\n  };\n\n  define(Move, 'offset', {\n    /**\n     * Gets an offset value used to modify current translate.\n     *\n     * @return {Object}\n     */\n    get: function get() {\n      return Move._o;\n    },\n\n\n    /**\n     * Sets an offset value used to modify current translate.\n     *\n     * @return {Object}\n     */\n    set: function set(value) {\n      Move._o = !isUndefined(value) ? toInt(value) : 0;\n    }\n  });\n\n  define(Move, 'translate', {\n    /**\n     * Gets a raw movement value.\n     *\n     * @return {Number}\n     */\n    get: function get() {\n      return Components.Sizes.slideWidth * Glide.index;\n    }\n  });\n\n  define(Move, 'value', {\n    /**\n     * Gets an actual movement value corrected by offset.\n     *\n     * @return {Number}\n     */\n    get: function get() {\n      var offset = this.offset;\n      var translate = this.translate;\n\n      if (Components.Direction.is('rtl')) {\n        return translate + offset;\n      }\n\n      return translate - offset;\n    }\n  });\n\n  /**\n   * Make movement to proper slide on:\n   * - before build, so glide will start at `startAt` index\n   * - on each standard run to move to newly calculated index\n   */\n  Events.on(['build.before', 'run'], function () {\n    Move.make();\n  });\n\n  return Move;\n}\n\nfunction Sizes (Glide, Components, Events) {\n  var Sizes = {\n    /**\n     * Setups dimentions of slides.\n     *\n     * @return {Void}\n     */\n    setupSlides: function setupSlides() {\n      var width = this.slideWidth + 'px';\n      var slides = Components.Html.slides;\n\n      for (var i = 0; i < slides.length; i++) {\n        slides[i].style.width = width;\n      }\n    },\n\n\n    /**\n     * Setups dimentions of slides wrapper.\n     *\n     * @return {Void}\n     */\n    setupWrapper: function setupWrapper(dimention) {\n      Components.Html.wrapper.style.width = this.wrapperSize + 'px';\n    },\n\n\n    /**\n     * Removes applied styles from HTML elements.\n     *\n     * @returns {Void}\n     */\n    remove: function remove() {\n      var slides = Components.Html.slides;\n\n      for (var i = 0; i < slides.length; i++) {\n        slides[i].style.width = '';\n      }\n\n      Components.Html.wrapper.style.width = '';\n    }\n  };\n\n  define(Sizes, 'length', {\n    /**\n     * Gets count number of the slides.\n     *\n     * @return {Number}\n     */\n    get: function get() {\n      return Components.Html.slides.length;\n    }\n  });\n\n  define(Sizes, 'width', {\n    /**\n     * Gets width value of the glide.\n     *\n     * @return {Number}\n     */\n    get: function get() {\n      return Components.Html.root.offsetWidth;\n    }\n  });\n\n  define(Sizes, 'wrapperSize', {\n    /**\n     * Gets size of the slides wrapper.\n     *\n     * @return {Number}\n     */\n    get: function get() {\n      return Sizes.slideWidth * Sizes.length + Components.Gaps.grow + Components.Clones.grow;\n    }\n  });\n\n  define(Sizes, 'slideWidth', {\n    /**\n     * Gets width value of the single slide.\n     *\n     * @return {Number}\n     */\n    get: function get() {\n      return Sizes.width / Glide.settings.perView - Components.Peek.reductor - Components.Gaps.reductor;\n    }\n  });\n\n  /**\n   * Apply calculated glide's dimensions:\n   * - before building, so other dimentions (e.g. translate) will be calculated propertly\n   * - when resizing window to recalculate sildes dimensions\n   * - on updating via API, to calculate dimensions based on new options\n   */\n  Events.on(['build.before', 'resize', 'update'], function () {\n    Sizes.setupSlides();\n    Sizes.setupWrapper();\n  });\n\n  /**\n   * Remove calculated glide's dimensions:\n   * - on destoting to bring markup to its inital state\n   */\n  Events.on('destroy', function () {\n    Sizes.remove();\n  });\n\n  return Sizes;\n}\n\nfunction Build (Glide, Components, Events) {\n  var Build = {\n    /**\n     * Init glide building. Adds classes, sets\n     * dimensions and setups initial state.\n     *\n     * @return {Void}\n     */\n    mount: function mount() {\n      Events.emit('build.before');\n\n      this.typeClass();\n      this.activeClass();\n\n      Events.emit('build.after');\n    },\n\n\n    /**\n     * Adds `type` class to the glide element.\n     *\n     * @return {Void}\n     */\n    typeClass: function typeClass() {\n      Components.Html.root.classList.add(Glide.settings.classes[Glide.settings.type]);\n    },\n\n\n    /**\n     * Sets active class to current slide.\n     *\n     * @return {Void}\n     */\n    activeClass: function activeClass() {\n      var classes = Glide.settings.classes;\n      var slide = Components.Html.slides[Glide.index];\n\n      if (slide) {\n        slide.classList.add(classes.activeSlide);\n\n        siblings(slide).forEach(function (sibling) {\n          sibling.classList.remove(classes.activeSlide);\n        });\n      }\n    },\n\n\n    /**\n     * Removes HTML classes applied at building.\n     *\n     * @return {Void}\n     */\n    removeClasses: function removeClasses() {\n      var classes = Glide.settings.classes;\n\n      Components.Html.root.classList.remove(classes[Glide.settings.type]);\n\n      Components.Html.slides.forEach(function (sibling) {\n        sibling.classList.remove(classes.activeSlide);\n      });\n    }\n  };\n\n  /**\n   * Clear building classes:\n   * - on destroying to bring HTML to its initial state\n   * - on updating to remove classes before remounting component\n   */\n  Events.on(['destroy', 'update'], function () {\n    Build.removeClasses();\n  });\n\n  /**\n   * Remount component:\n   * - on resizing of the window to calculate new dimentions\n   * - on updating settings via API\n   */\n  Events.on(['resize', 'update'], function () {\n    Build.mount();\n  });\n\n  /**\n   * Swap active class of current slide:\n   * - after each move to the new index\n   */\n  Events.on('move.after', function () {\n    Build.activeClass();\n  });\n\n  return Build;\n}\n\nfunction Clones (Glide, Components, Events) {\n  var Clones = {\n    /**\n     * Create pattern map and collect slides to be cloned.\n     */\n    mount: function mount() {\n      this.items = [];\n\n      if (Glide.isType('carousel')) {\n        this.items = this.collect();\n      }\n    },\n\n\n    /**\n     * Collect clones with pattern.\n     *\n     * @return {Void}\n     */\n    collect: function collect() {\n      var items = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : [];\n      var slides = Components.Html.slides;\n      var _Glide$settings = Glide.settings,\n          perView = _Glide$settings.perView,\n          classes = _Glide$settings.classes;\n\n\n      var peekIncrementer = +!!Glide.settings.peek;\n      var part = perView + peekIncrementer;\n      var start = slides.slice(0, part);\n      var end = slides.slice(-part);\n\n      for (var r = 0; r < Math.max(1, Math.floor(perView / slides.length)); r++) {\n        for (var i = 0; i < start.length; i++) {\n          var clone = start[i].cloneNode(true);\n\n          clone.classList.add(classes.cloneSlide);\n\n          items.push(clone);\n        }\n\n        for (var _i = 0; _i < end.length; _i++) {\n          var _clone = end[_i].cloneNode(true);\n\n          _clone.classList.add(classes.cloneSlide);\n\n          items.unshift(_clone);\n        }\n      }\n\n      return items;\n    },\n\n\n    /**\n     * Append cloned slides with generated pattern.\n     *\n     * @return {Void}\n     */\n    append: function append() {\n      var items = this.items;\n      var _Components$Html = Components.Html,\n          wrapper = _Components$Html.wrapper,\n          slides = _Components$Html.slides;\n\n\n      var half = Math.floor(items.length / 2);\n      var prepend = items.slice(0, half).reverse();\n      var append = items.slice(half, items.length);\n      var width = Components.Sizes.slideWidth + 'px';\n\n      for (var i = 0; i < append.length; i++) {\n        wrapper.appendChild(append[i]);\n      }\n\n      for (var _i2 = 0; _i2 < prepend.length; _i2++) {\n        wrapper.insertBefore(prepend[_i2], slides[0]);\n      }\n\n      for (var _i3 = 0; _i3 < items.length; _i3++) {\n        items[_i3].style.width = width;\n      }\n    },\n\n\n    /**\n     * Remove all cloned slides.\n     *\n     * @return {Void}\n     */\n    remove: function remove() {\n      var items = this.items;\n\n\n      for (var i = 0; i < items.length; i++) {\n        Components.Html.wrapper.removeChild(items[i]);\n      }\n    }\n  };\n\n  define(Clones, 'grow', {\n    /**\n     * Gets additional dimentions value caused by clones.\n     *\n     * @return {Number}\n     */\n    get: function get() {\n      return (Components.Sizes.slideWidth + Components.Gaps.value) * Clones.items.length;\n    }\n  });\n\n  /**\n   * Append additional slide's clones:\n   * - while glide's type is `carousel`\n   */\n  Events.on('update', function () {\n    Clones.remove();\n    Clones.mount();\n    Clones.append();\n  });\n\n  /**\n   * Append additional slide's clones:\n   * - while glide's type is `carousel`\n   */\n  Events.on('build.before', function () {\n    if (Glide.isType('carousel')) {\n      Clones.append();\n    }\n  });\n\n  /**\n   * Remove clones HTMLElements:\n   * - on destroying, to bring HTML to its initial state\n   */\n  Events.on('destroy', function () {\n    Clones.remove();\n  });\n\n  return Clones;\n}\n\nvar EventsBinder = function () {\n  /**\n   * Construct a EventsBinder instance.\n   */\n  function EventsBinder() {\n    var listeners = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : {};\n    classCallCheck(this, EventsBinder);\n\n    this.listeners = listeners;\n  }\n\n  /**\n   * Adds events listeners to arrows HTML elements.\n   *\n   * @param  {String|Array} events\n   * @param  {Element|Window|Document} el\n   * @param  {Function} closure\n   * @param  {Boolean|Object} capture\n   * @return {Void}\n   */\n\n\n  createClass(EventsBinder, [{\n    key: 'on',\n    value: function on(events, el, closure) {\n      var capture = arguments.length > 3 && arguments[3] !== undefined ? arguments[3] : false;\n\n      if (isString(events)) {\n        events = [events];\n      }\n\n      for (var i = 0; i < events.length; i++) {\n        this.listeners[events[i]] = closure;\n\n        el.addEventListener(events[i], this.listeners[events[i]], capture);\n      }\n    }\n\n    /**\n     * Removes event listeners from arrows HTML elements.\n     *\n     * @param  {String|Array} events\n     * @param  {Element|Window|Document} el\n     * @param  {Boolean|Object} capture\n     * @return {Void}\n     */\n\n  }, {\n    key: 'off',\n    value: function off(events, el) {\n      var capture = arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : false;\n\n      if (isString(events)) {\n        events = [events];\n      }\n\n      for (var i = 0; i < events.length; i++) {\n        el.removeEventListener(events[i], this.listeners[events[i]], capture);\n      }\n    }\n\n    /**\n     * Destroy collected listeners.\n     *\n     * @returns {Void}\n     */\n\n  }, {\n    key: 'destroy',\n    value: function destroy() {\n      delete this.listeners;\n    }\n  }]);\n  return EventsBinder;\n}();\n\nfunction Resize (Glide, Components, Events) {\n  /**\n   * Instance of the binder for DOM Events.\n   *\n   * @type {EventsBinder}\n   */\n  var Binder = new EventsBinder();\n\n  var Resize = {\n    /**\n     * Initializes window bindings.\n     */\n    mount: function mount() {\n      this.bind();\n    },\n\n\n    /**\n     * Binds `rezsize` listener to the window.\n     * It's a costly event, so we are debouncing it.\n     *\n     * @return {Void}\n     */\n    bind: function bind() {\n      Binder.on('resize', window, throttle(function () {\n        Events.emit('resize');\n      }, Glide.settings.throttle));\n    },\n\n\n    /**\n     * Unbinds listeners from the window.\n     *\n     * @return {Void}\n     */\n    unbind: function unbind() {\n      Binder.off('resize', window);\n    }\n  };\n\n  /**\n   * Remove bindings from window:\n   * - on destroying, to remove added EventListener\n   */\n  Events.on('destroy', function () {\n    Resize.unbind();\n    Binder.destroy();\n  });\n\n  return Resize;\n}\n\nvar VALID_DIRECTIONS = ['ltr', 'rtl'];\nvar FLIPED_MOVEMENTS = {\n  '>': '<',\n  '<': '>',\n  '=': '='\n};\n\nfunction Direction (Glide, Components, Events) {\n  var Direction = {\n    /**\n     * Setups gap value based on settings.\n     *\n     * @return {Void}\n     */\n    mount: function mount() {\n      this.value = Glide.settings.direction;\n    },\n\n\n    /**\n     * Resolves pattern based on direction value\n     *\n     * @param {String} pattern\n     * @returns {String}\n     */\n    resolve: function resolve(pattern) {\n      var token = pattern.slice(0, 1);\n\n      if (this.is('rtl')) {\n        return pattern.split(token).join(FLIPED_MOVEMENTS[token]);\n      }\n\n      return pattern;\n    },\n\n\n    /**\n     * Checks value of direction mode.\n     *\n     * @param {String} direction\n     * @returns {Boolean}\n     */\n    is: function is(direction) {\n      return this.value === direction;\n    },\n\n\n    /**\n     * Applies direction class to the root HTML element.\n     *\n     * @return {Void}\n     */\n    addClass: function addClass() {\n      Components.Html.root.classList.add(Glide.settings.classes.direction[this.value]);\n    },\n\n\n    /**\n     * Removes direction class from the root HTML element.\n     *\n     * @return {Void}\n     */\n    removeClass: function removeClass() {\n      Components.Html.root.classList.remove(Glide.settings.classes.direction[this.value]);\n    }\n  };\n\n  define(Direction, 'value', {\n    /**\n     * Gets value of the direction.\n     *\n     * @returns {Number}\n     */\n    get: function get() {\n      return Direction._v;\n    },\n\n\n    /**\n     * Sets value of the direction.\n     *\n     * @param {String} value\n     * @return {Void}\n     */\n    set: function set(value) {\n      if (VALID_DIRECTIONS.indexOf(value) > -1) {\n        Direction._v = value;\n      } else {\n        warn('Direction value must be `ltr` or `rtl`');\n      }\n    }\n  });\n\n  /**\n   * Clear direction class:\n   * - on destroy to bring HTML to its initial state\n   * - on update to remove class before reappling bellow\n   */\n  Events.on(['destroy', 'update'], function () {\n    Direction.removeClass();\n  });\n\n  /**\n   * Remount component:\n   * - on update to reflect changes in direction value\n   */\n  Events.on('update', function () {\n    Direction.mount();\n  });\n\n  /**\n   * Apply direction class:\n   * - before building to apply class for the first time\n   * - on updating to reapply direction class that may changed\n   */\n  Events.on(['build.before', 'update'], function () {\n    Direction.addClass();\n  });\n\n  return Direction;\n}\n\n/**\n * Reflects value of glide movement.\n *\n * @param  {Object} Glide\n * @param  {Object} Components\n * @return {Object}\n */\nfunction Rtl (Glide, Components) {\n  return {\n    /**\n     * Negates the passed translate if glide is in RTL option.\n     *\n     * @param  {Number} translate\n     * @return {Number}\n     */\n    modify: function modify(translate) {\n      if (Components.Direction.is('rtl')) {\n        return -translate;\n      }\n\n      return translate;\n    }\n  };\n}\n\n/**\n * Updates glide movement with a `gap` settings.\n *\n * @param  {Object} Glide\n * @param  {Object} Components\n * @return {Object}\n */\nfunction Gap (Glide, Components) {\n  return {\n    /**\n     * Modifies passed translate value with number in the `gap` settings.\n     *\n     * @param  {Number} translate\n     * @return {Number}\n     */\n    modify: function modify(translate) {\n      return translate + Components.Gaps.value * Glide.index;\n    }\n  };\n}\n\n/**\n * Updates glide movement with width of additional clones width.\n *\n * @param  {Object} Glide\n * @param  {Object} Components\n * @return {Object}\n */\nfunction Grow (Glide, Components) {\n  return {\n    /**\n     * Adds to the passed translate width of the half of clones.\n     *\n     * @param  {Number} translate\n     * @return {Number}\n     */\n    modify: function modify(translate) {\n      return translate + Components.Clones.grow / 2;\n    }\n  };\n}\n\n/**\n * Updates glide movement with a `peek` settings.\n *\n * @param  {Object} Glide\n * @param  {Object} Components\n * @return {Object}\n */\nfunction Peeking (Glide, Components) {\n  return {\n    /**\n     * Modifies passed translate value with a `peek` setting.\n     *\n     * @param  {Number} translate\n     * @return {Number}\n     */\n    modify: function modify(translate) {\n      if (Glide.settings.focusAt >= 0) {\n        var peek = Components.Peek.value;\n\n        if (isObject(peek)) {\n          return translate - peek.before;\n        }\n\n        return translate - peek;\n      }\n\n      return translate;\n    }\n  };\n}\n\n/**\n * Updates glide movement with a `focusAt` settings.\n *\n * @param  {Object} Glide\n * @param  {Object} Components\n * @return {Object}\n */\nfunction Focusing (Glide, Components) {\n  return {\n    /**\n     * Modifies passed translate value with index in the `focusAt` setting.\n     *\n     * @param  {Number} translate\n     * @return {Number}\n     */\n    modify: function modify(translate) {\n      var gap = Components.Gaps.value;\n      var width = Components.Sizes.width;\n      var focusAt = Glide.settings.focusAt;\n      var slideWidth = Components.Sizes.slideWidth;\n\n      if (focusAt === 'center') {\n        return translate - (width / 2 - slideWidth / 2);\n      }\n\n      return translate - slideWidth * focusAt - gap * focusAt;\n    }\n  };\n}\n\n/**\n * Applies diffrent transformers on translate value.\n *\n * @param  {Object} Glide\n * @param  {Object} Components\n * @return {Object}\n */\nfunction mutator (Glide, Components, Events) {\n  /**\n   * Merge instance transformers with collection of default transformers.\n   * It's important that the Rtl component be last on the list,\n   * so it reflects all previous transformations.\n   *\n   * @type {Array}\n   */\n  var TRANSFORMERS = [Gap, Grow, Peeking, Focusing].concat(Glide._t, [Rtl]);\n\n  return {\n    /**\n     * Piplines translate value with registered transformers.\n     *\n     * @param  {Number} translate\n     * @return {Number}\n     */\n    mutate: function mutate(translate) {\n      for (var i = 0; i < TRANSFORMERS.length; i++) {\n        var transformer = TRANSFORMERS[i];\n\n        if (isFunction(transformer) && isFunction(transformer().modify)) {\n          translate = transformer(Glide, Components, Events).modify(translate);\n        } else {\n          warn('Transformer should be a function that returns an object with `modify()` method');\n        }\n      }\n\n      return translate;\n    }\n  };\n}\n\nfunction Translate (Glide, Components, Events) {\n  var Translate = {\n    /**\n     * Sets value of translate on HTML element.\n     *\n     * @param {Number} value\n     * @return {Void}\n     */\n    set: function set(value) {\n      var transform = mutator(Glide, Components).mutate(value);\n\n      Components.Html.wrapper.style.transform = 'translate3d(' + -1 * transform + 'px, 0px, 0px)';\n    },\n\n\n    /**\n     * Removes value of translate from HTML element.\n     *\n     * @return {Void}\n     */\n    remove: function remove() {\n      Components.Html.wrapper.style.transform = '';\n    }\n  };\n\n  /**\n   * Set new translate value:\n   * - on move to reflect index change\n   * - on updating via API to reflect possible changes in options\n   */\n  Events.on('move', function (context) {\n    var gap = Components.Gaps.value;\n    var length = Components.Sizes.length;\n    var width = Components.Sizes.slideWidth;\n\n    if (Glide.isType('carousel') && Components.Run.isOffset('<')) {\n      Components.Transition.after(function () {\n        Events.emit('translate.jump');\n\n        Translate.set(width * (length - 1));\n      });\n\n      return Translate.set(-width - gap * length);\n    }\n\n    if (Glide.isType('carousel') && Components.Run.isOffset('>')) {\n      Components.Transition.after(function () {\n        Events.emit('translate.jump');\n\n        Translate.set(0);\n      });\n\n      return Translate.set(width * length + gap * length);\n    }\n\n    return Translate.set(context.movement);\n  });\n\n  /**\n   * Remove translate:\n   * - on destroying to bring markup to its inital state\n   */\n  Events.on('destroy', function () {\n    Translate.remove();\n  });\n\n  return Translate;\n}\n\nfunction Transition (Glide, Components, Events) {\n  /**\n   * Holds inactivity status of transition.\n   * When true transition is not applied.\n   *\n   * @type {Boolean}\n   */\n  var disabled = false;\n\n  var Transition = {\n    /**\n     * Composes string of the CSS transition.\n     *\n     * @param {String} property\n     * @return {String}\n     */\n    compose: function compose(property) {\n      var settings = Glide.settings;\n\n      if (!disabled) {\n        return property + ' ' + this.duration + 'ms ' + settings.animationTimingFunc;\n      }\n\n      return property + ' 0ms ' + settings.animationTimingFunc;\n    },\n\n\n    /**\n     * Sets value of transition on HTML element.\n     *\n     * @param {String=} property\n     * @return {Void}\n     */\n    set: function set() {\n      var property = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : 'transform';\n\n      Components.Html.wrapper.style.transition = this.compose(property);\n    },\n\n\n    /**\n     * Removes value of transition from HTML element.\n     *\n     * @return {Void}\n     */\n    remove: function remove() {\n      Components.Html.wrapper.style.transition = '';\n    },\n\n\n    /**\n     * Runs callback after animation.\n     *\n     * @param  {Function} callback\n     * @return {Void}\n     */\n    after: function after(callback) {\n      setTimeout(function () {\n        callback();\n      }, this.duration);\n    },\n\n\n    /**\n     * Enable transition.\n     *\n     * @return {Void}\n     */\n    enable: function enable() {\n      disabled = false;\n\n      this.set();\n    },\n\n\n    /**\n     * Disable transition.\n     *\n     * @return {Void}\n     */\n    disable: function disable() {\n      disabled = true;\n\n      this.set();\n    }\n  };\n\n  define(Transition, 'duration', {\n    /**\n     * Gets duration of the transition based\n     * on currently running animation type.\n     *\n     * @return {Number}\n     */\n    get: function get() {\n      var settings = Glide.settings;\n\n      if (Glide.isType('slider') && Components.Run.offset) {\n        return settings.rewindDuration;\n      }\n\n      return settings.animationDuration;\n    }\n  });\n\n  /**\n   * Set transition `style` value:\n   * - on each moving, because it may be cleared by offset move\n   */\n  Events.on('move', function () {\n    Transition.set();\n  });\n\n  /**\n   * Disable transition:\n   * - before initial build to avoid transitioning from `0` to `startAt` index\n   * - while resizing window and recalculating dimentions\n   * - on jumping from offset transition at start and end edges in `carousel` type\n   */\n  Events.on(['build.before', 'resize', 'translate.jump'], function () {\n    Transition.disable();\n  });\n\n  /**\n   * Enable transition:\n   * - on each running, because it may be disabled by offset move\n   */\n  Events.on('run', function () {\n    Transition.enable();\n  });\n\n  /**\n   * Remove transition:\n   * - on destroying to bring markup to its inital state\n   */\n  Events.on('destroy', function () {\n    Transition.remove();\n  });\n\n  return Transition;\n}\n\n/**\n * Test via a getter in the options object to see\n * if the passive property is accessed.\n *\n * @see https://github.com/WICG/EventListenerOptions/blob/gh-pages/explainer.md#feature-detection\n */\n\nvar supportsPassive = false;\n\ntry {\n  var opts = Object.defineProperty({}, 'passive', {\n    get: function get() {\n      supportsPassive = true;\n    }\n  });\n\n  window.addEventListener('testPassive', null, opts);\n  window.removeEventListener('testPassive', null, opts);\n} catch (e) {}\n\nvar supportsPassive$1 = supportsPassive;\n\nvar START_EVENTS = ['touchstart', 'mousedown'];\nvar MOVE_EVENTS = ['touchmove', 'mousemove'];\nvar END_EVENTS = ['touchend', 'touchcancel', 'mouseup', 'mouseleave'];\nvar MOUSE_EVENTS = ['mousedown', 'mousemove', 'mouseup', 'mouseleave'];\n\nfunction Swipe (Glide, Components, Events) {\n  /**\n   * Instance of the binder for DOM Events.\n   *\n   * @type {EventsBinder}\n   */\n  var Binder = new EventsBinder();\n\n  var swipeSin = 0;\n  var swipeStartX = 0;\n  var swipeStartY = 0;\n  var disabled = false;\n  var capture = supportsPassive$1 ? { passive: true } : false;\n\n  var Swipe = {\n    /**\n     * Initializes swipe bindings.\n     *\n     * @return {Void}\n     */\n    mount: function mount() {\n      this.bindSwipeStart();\n    },\n\n\n    /**\n     * Handler for `swipestart` event. Calculates entry points of the user's tap.\n     *\n     * @param {Object} event\n     * @return {Void}\n     */\n    start: function start(event) {\n      if (!disabled && !Glide.disabled) {\n        this.disable();\n\n        var swipe = this.touches(event);\n\n        swipeSin = null;\n        swipeStartX = toInt(swipe.pageX);\n        swipeStartY = toInt(swipe.pageY);\n\n        this.bindSwipeMove();\n        this.bindSwipeEnd();\n\n        Events.emit('swipe.start');\n      }\n    },\n\n\n    /**\n     * Handler for `swipemove` event. Calculates user's tap angle and distance.\n     *\n     * @param {Object} event\n     */\n    move: function move(event) {\n      if (!Glide.disabled) {\n        var _Glide$settings = Glide.settings,\n            touchAngle = _Glide$settings.touchAngle,\n            touchRatio = _Glide$settings.touchRatio,\n            classes = _Glide$settings.classes;\n\n\n        var swipe = this.touches(event);\n\n        var subExSx = toInt(swipe.pageX) - swipeStartX;\n        var subEySy = toInt(swipe.pageY) - swipeStartY;\n        var powEX = Math.abs(subExSx << 2);\n        var powEY = Math.abs(subEySy << 2);\n        var swipeHypotenuse = Math.sqrt(powEX + powEY);\n        var swipeCathetus = Math.sqrt(powEY);\n\n        swipeSin = Math.asin(swipeCathetus / swipeHypotenuse);\n\n        if (swipeSin * 180 / Math.PI < touchAngle) {\n          event.stopPropagation();\n\n          Components.Move.make(subExSx * toFloat(touchRatio));\n\n          Components.Html.root.classList.add(classes.dragging);\n\n          Events.emit('swipe.move');\n        } else {\n          return false;\n        }\n      }\n    },\n\n\n    /**\n     * Handler for `swipeend` event. Finitializes user's tap and decides about glide move.\n     *\n     * @param {Object} event\n     * @return {Void}\n     */\n    end: function end(event) {\n      if (!Glide.disabled) {\n        var settings = Glide.settings;\n\n        var swipe = this.touches(event);\n        var threshold = this.threshold(event);\n\n        var swipeDistance = swipe.pageX - swipeStartX;\n        var swipeDeg = swipeSin * 180 / Math.PI;\n        var steps = Math.round(swipeDistance / Components.Sizes.slideWidth);\n\n        this.enable();\n\n        if (swipeDistance > threshold && swipeDeg < settings.touchAngle) {\n          // While swipe is positive and greater than threshold move backward.\n          if (settings.perTouch) {\n            steps = Math.min(steps, toInt(settings.perTouch));\n          }\n\n          if (Components.Direction.is('rtl')) {\n            steps = -steps;\n          }\n\n          Components.Run.make(Components.Direction.resolve('<' + steps));\n        } else if (swipeDistance < -threshold && swipeDeg < settings.touchAngle) {\n          // While swipe is negative and lower than negative threshold move forward.\n          if (settings.perTouch) {\n            steps = Math.max(steps, -toInt(settings.perTouch));\n          }\n\n          if (Components.Direction.is('rtl')) {\n            steps = -steps;\n          }\n\n          Components.Run.make(Components.Direction.resolve('>' + steps));\n        } else {\n          // While swipe don't reach distance apply previous transform.\n          Components.Move.make();\n        }\n\n        Components.Html.root.classList.remove(settings.classes.dragging);\n\n        this.unbindSwipeMove();\n        this.unbindSwipeEnd();\n\n        Events.emit('swipe.end');\n      }\n    },\n\n\n    /**\n     * Binds swipe's starting event.\n     *\n     * @return {Void}\n     */\n    bindSwipeStart: function bindSwipeStart() {\n      var _this = this;\n\n      var settings = Glide.settings;\n\n      if (settings.swipeThreshold) {\n        Binder.on(START_EVENTS[0], Components.Html.wrapper, function (event) {\n          _this.start(event);\n        }, capture);\n      }\n\n      if (settings.dragThreshold) {\n        Binder.on(START_EVENTS[1], Components.Html.wrapper, function (event) {\n          _this.start(event);\n        }, capture);\n      }\n    },\n\n\n    /**\n     * Unbinds swipe's starting event.\n     *\n     * @return {Void}\n     */\n    unbindSwipeStart: function unbindSwipeStart() {\n      Binder.off(START_EVENTS[0], Components.Html.wrapper, capture);\n      Binder.off(START_EVENTS[1], Components.Html.wrapper, capture);\n    },\n\n\n    /**\n     * Binds swipe's moving event.\n     *\n     * @return {Void}\n     */\n    bindSwipeMove: function bindSwipeMove() {\n      var _this2 = this;\n\n      Binder.on(MOVE_EVENTS, Components.Html.wrapper, throttle(function (event) {\n        _this2.move(event);\n      }, Glide.settings.throttle), capture);\n    },\n\n\n    /**\n     * Unbinds swipe's moving event.\n     *\n     * @return {Void}\n     */\n    unbindSwipeMove: function unbindSwipeMove() {\n      Binder.off(MOVE_EVENTS, Components.Html.wrapper, capture);\n    },\n\n\n    /**\n     * Binds swipe's ending event.\n     *\n     * @return {Void}\n     */\n    bindSwipeEnd: function bindSwipeEnd() {\n      var _this3 = this;\n\n      Binder.on(END_EVENTS, Components.Html.wrapper, function (event) {\n        _this3.end(event);\n      });\n    },\n\n\n    /**\n     * Unbinds swipe's ending event.\n     *\n     * @return {Void}\n     */\n    unbindSwipeEnd: function unbindSwipeEnd() {\n      Binder.off(END_EVENTS, Components.Html.wrapper);\n    },\n\n\n    /**\n     * Normalizes event touches points accorting to different types.\n     *\n     * @param {Object} event\n     */\n    touches: function touches(event) {\n      if (MOUSE_EVENTS.indexOf(event.type) > -1) {\n        return event;\n      }\n\n      return event.touches[0] || event.changedTouches[0];\n    },\n\n\n    /**\n     * Gets value of minimum swipe distance settings based on event type.\n     *\n     * @return {Number}\n     */\n    threshold: function threshold(event) {\n      var settings = Glide.settings;\n\n      if (MOUSE_EVENTS.indexOf(event.type) > -1) {\n        return settings.dragThreshold;\n      }\n\n      return settings.swipeThreshold;\n    },\n\n\n    /**\n     * Enables swipe event.\n     *\n     * @return {self}\n     */\n    enable: function enable() {\n      disabled = false;\n\n      Components.Transition.enable();\n\n      return this;\n    },\n\n\n    /**\n     * Disables swipe event.\n     *\n     * @return {self}\n     */\n    disable: function disable() {\n      disabled = true;\n\n      Components.Transition.disable();\n\n      return this;\n    }\n  };\n\n  /**\n   * Add component class:\n   * - after initial building\n   */\n  Events.on('build.after', function () {\n    Components.Html.root.classList.add(Glide.settings.classes.swipeable);\n  });\n\n  /**\n   * Remove swiping bindings:\n   * - on destroying, to remove added EventListeners\n   */\n  Events.on('destroy', function () {\n    Swipe.unbindSwipeStart();\n    Swipe.unbindSwipeMove();\n    Swipe.unbindSwipeEnd();\n    Binder.destroy();\n  });\n\n  return Swipe;\n}\n\nfunction Images (Glide, Components, Events) {\n  /**\n   * Instance of the binder for DOM Events.\n   *\n   * @type {EventsBinder}\n   */\n  var Binder = new EventsBinder();\n\n  var Images = {\n    /**\n     * Binds listener to glide wrapper.\n     *\n     * @return {Void}\n     */\n    mount: function mount() {\n      this.bind();\n    },\n\n\n    /**\n     * Binds `dragstart` event on wrapper to prevent dragging images.\n     *\n     * @return {Void}\n     */\n    bind: function bind() {\n      Binder.on('dragstart', Components.Html.wrapper, this.dragstart);\n    },\n\n\n    /**\n     * Unbinds `dragstart` event on wrapper.\n     *\n     * @return {Void}\n     */\n    unbind: function unbind() {\n      Binder.off('dragstart', Components.Html.wrapper);\n    },\n\n\n    /**\n     * Event handler. Prevents dragging.\n     *\n     * @return {Void}\n     */\n    dragstart: function dragstart(event) {\n      event.preventDefault();\n    }\n  };\n\n  /**\n   * Remove bindings from images:\n   * - on destroying, to remove added EventListeners\n   */\n  Events.on('destroy', function () {\n    Images.unbind();\n    Binder.destroy();\n  });\n\n  return Images;\n}\n\nfunction Anchors (Glide, Components, Events) {\n  /**\n   * Instance of the binder for DOM Events.\n   *\n   * @type {EventsBinder}\n   */\n  var Binder = new EventsBinder();\n\n  /**\n   * Holds detaching status of anchors.\n   * Prevents detaching of already detached anchors.\n   *\n   * @private\n   * @type {Boolean}\n   */\n  var detached = false;\n\n  /**\n   * Holds preventing status of anchors.\n   * If `true` redirection after click will be disabled.\n   *\n   * @private\n   * @type {Boolean}\n   */\n  var prevented = false;\n\n  var Anchors = {\n    /**\n     * Setups a initial state of anchors component.\n     *\n     * @returns {Void}\n     */\n    mount: function mount() {\n      /**\n       * Holds collection of anchors elements.\n       *\n       * @private\n       * @type {HTMLCollection}\n       */\n      this._a = Components.Html.wrapper.querySelectorAll('a');\n\n      this.bind();\n    },\n\n\n    /**\n     * Binds events to anchors inside a track.\n     *\n     * @return {Void}\n     */\n    bind: function bind() {\n      Binder.on('click', Components.Html.wrapper, this.click);\n    },\n\n\n    /**\n     * Unbinds events attached to anchors inside a track.\n     *\n     * @return {Void}\n     */\n    unbind: function unbind() {\n      Binder.off('click', Components.Html.wrapper);\n    },\n\n\n    /**\n     * Handler for click event. Prevents clicks when glide is in `prevent` status.\n     *\n     * @param  {Object} event\n     * @return {Void}\n     */\n    click: function click(event) {\n      if (prevented) {\n        event.stopPropagation();\n        event.preventDefault();\n      }\n    },\n\n\n    /**\n     * Detaches anchors click event inside glide.\n     *\n     * @return {self}\n     */\n    detach: function detach() {\n      prevented = true;\n\n      if (!detached) {\n        for (var i = 0; i < this.items.length; i++) {\n          this.items[i].draggable = false;\n\n          this.items[i].setAttribute('data-href', this.items[i].getAttribute('href'));\n\n          this.items[i].removeAttribute('href');\n        }\n\n        detached = true;\n      }\n\n      return this;\n    },\n\n\n    /**\n     * Attaches anchors click events inside glide.\n     *\n     * @return {self}\n     */\n    attach: function attach() {\n      prevented = false;\n\n      if (detached) {\n        for (var i = 0; i < this.items.length; i++) {\n          this.items[i].draggable = true;\n\n          this.items[i].setAttribute('href', this.items[i].getAttribute('data-href'));\n        }\n\n        detached = false;\n      }\n\n      return this;\n    }\n  };\n\n  define(Anchors, 'items', {\n    /**\n     * Gets collection of the arrows HTML elements.\n     *\n     * @return {HTMLElement[]}\n     */\n    get: function get() {\n      return Anchors._a;\n    }\n  });\n\n  /**\n   * Detach anchors inside slides:\n   * - on swiping, so they won't redirect to its `href` attributes\n   */\n  Events.on('swipe.move', function () {\n    Anchors.detach();\n  });\n\n  /**\n   * Attach anchors inside slides:\n   * - after swiping and transitions ends, so they can redirect after click again\n   */\n  Events.on('swipe.end', function () {\n    Components.Transition.after(function () {\n      Anchors.attach();\n    });\n  });\n\n  /**\n   * Unbind anchors inside slides:\n   * - on destroying, to bring anchors to its initial state\n   */\n  Events.on('destroy', function () {\n    Anchors.attach();\n    Anchors.unbind();\n    Binder.destroy();\n  });\n\n  return Anchors;\n}\n\nvar NAV_SELECTOR = '[data-glide-el=\"controls[nav]\"]';\nvar CONTROLS_SELECTOR = '[data-glide-el^=\"controls\"]';\n\nfunction Controls (Glide, Components, Events) {\n  /**\n   * Instance of the binder for DOM Events.\n   *\n   * @type {EventsBinder}\n   */\n  var Binder = new EventsBinder();\n\n  var capture = supportsPassive$1 ? { passive: true } : false;\n\n  var Controls = {\n    /**\n     * Inits arrows. Binds events listeners\n     * to the arrows HTML elements.\n     *\n     * @return {Void}\n     */\n    mount: function mount() {\n      /**\n       * Collection of navigation HTML elements.\n       *\n       * @private\n       * @type {HTMLCollection}\n       */\n      this._n = Components.Html.root.querySelectorAll(NAV_SELECTOR);\n\n      /**\n       * Collection of controls HTML elements.\n       *\n       * @private\n       * @type {HTMLCollection}\n       */\n      this._c = Components.Html.root.querySelectorAll(CONTROLS_SELECTOR);\n\n      this.addBindings();\n    },\n\n\n    /**\n     * Sets active class to current slide.\n     *\n     * @return {Void}\n     */\n    setActive: function setActive() {\n      for (var i = 0; i < this._n.length; i++) {\n        this.addClass(this._n[i].children);\n      }\n    },\n\n\n    /**\n     * Removes active class to current slide.\n     *\n     * @return {Void}\n     */\n    removeActive: function removeActive() {\n      for (var i = 0; i < this._n.length; i++) {\n        this.removeClass(this._n[i].children);\n      }\n    },\n\n\n    /**\n     * Toggles active class on items inside navigation.\n     *\n     * @param  {HTMLElement} controls\n     * @return {Void}\n     */\n    addClass: function addClass(controls) {\n      var settings = Glide.settings;\n      var item = controls[Glide.index];\n\n      if (item) {\n        item.classList.add(settings.classes.activeNav);\n\n        siblings(item).forEach(function (sibling) {\n          sibling.classList.remove(settings.classes.activeNav);\n        });\n      }\n    },\n\n\n    /**\n     * Removes active class from active control.\n     *\n     * @param  {HTMLElement} controls\n     * @return {Void}\n     */\n    removeClass: function removeClass(controls) {\n      var item = controls[Glide.index];\n\n      if (item) {\n        item.classList.remove(Glide.settings.classes.activeNav);\n      }\n    },\n\n\n    /**\n     * Adds handles to the each group of controls.\n     *\n     * @return {Void}\n     */\n    addBindings: function addBindings() {\n      for (var i = 0; i < this._c.length; i++) {\n        this.bind(this._c[i].children);\n      }\n    },\n\n\n    /**\n     * Removes handles from the each group of controls.\n     *\n     * @return {Void}\n     */\n    removeBindings: function removeBindings() {\n      for (var i = 0; i < this._c.length; i++) {\n        this.unbind(this._c[i].children);\n      }\n    },\n\n\n    /**\n     * Binds events to arrows HTML elements.\n     *\n     * @param {HTMLCollection} elements\n     * @return {Void}\n     */\n    bind: function bind(elements) {\n      for (var i = 0; i < elements.length; i++) {\n        Binder.on('click', elements[i], this.click);\n        Binder.on('touchstart', elements[i], this.click, capture);\n      }\n    },\n\n\n    /**\n     * Unbinds events binded to the arrows HTML elements.\n     *\n     * @param {HTMLCollection} elements\n     * @return {Void}\n     */\n    unbind: function unbind(elements) {\n      for (var i = 0; i < elements.length; i++) {\n        Binder.off(['click', 'touchstart'], elements[i]);\n      }\n    },\n\n\n    /**\n     * Handles `click` event on the arrows HTML elements.\n     * Moves slider in driection precised in\n     * `data-glide-dir` attribute.\n     *\n     * @param {Object} event\n     * @return {Void}\n     */\n    click: function click(event) {\n      event.preventDefault();\n\n      Components.Run.make(Components.Direction.resolve(event.currentTarget.getAttribute('data-glide-dir')));\n    }\n  };\n\n  define(Controls, 'items', {\n    /**\n     * Gets collection of the controls HTML elements.\n     *\n     * @return {HTMLElement[]}\n     */\n    get: function get() {\n      return Controls._c;\n    }\n  });\n\n  /**\n   * Swap active class of current navigation item:\n   * - after mounting to set it to initial index\n   * - after each move to the new index\n   */\n  Events.on(['mount.after', 'move.after'], function () {\n    Controls.setActive();\n  });\n\n  /**\n   * Remove bindings and HTML Classes:\n   * - on destroying, to bring markup to its initial state\n   */\n  Events.on('destroy', function () {\n    Controls.removeBindings();\n    Controls.removeActive();\n    Binder.destroy();\n  });\n\n  return Controls;\n}\n\nfunction Keyboard (Glide, Components, Events) {\n  /**\n   * Instance of the binder for DOM Events.\n   *\n   * @type {EventsBinder}\n   */\n  var Binder = new EventsBinder();\n\n  var Keyboard = {\n    /**\n     * Binds keyboard events on component mount.\n     *\n     * @return {Void}\n     */\n    mount: function mount() {\n      if (Glide.settings.keyboard) {\n        this.bind();\n      }\n    },\n\n\n    /**\n     * Adds keyboard press events.\n     *\n     * @return {Void}\n     */\n    bind: function bind() {\n      Binder.on('keyup', document, this.press);\n    },\n\n\n    /**\n     * Removes keyboard press events.\n     *\n     * @return {Void}\n     */\n    unbind: function unbind() {\n      Binder.off('keyup', document);\n    },\n\n\n    /**\n     * Handles keyboard's arrows press and moving glide foward and backward.\n     *\n     * @param  {Object} event\n     * @return {Void}\n     */\n    press: function press(event) {\n      if (event.keyCode === 39) {\n        Components.Run.make(Components.Direction.resolve('>'));\n      }\n\n      if (event.keyCode === 37) {\n        Components.Run.make(Components.Direction.resolve('<'));\n      }\n    }\n  };\n\n  /**\n   * Remove bindings from keyboard:\n   * - on destroying to remove added events\n   * - on updating to remove events before remounting\n   */\n  Events.on(['destroy', 'update'], function () {\n    Keyboard.unbind();\n  });\n\n  /**\n   * Remount component\n   * - on updating to reflect potential changes in settings\n   */\n  Events.on('update', function () {\n    Keyboard.mount();\n  });\n\n  /**\n   * Destroy binder:\n   * - on destroying to remove listeners\n   */\n  Events.on('destroy', function () {\n    Binder.destroy();\n  });\n\n  return Keyboard;\n}\n\nfunction Autoplay (Glide, Components, Events) {\n  /**\n   * Instance of the binder for DOM Events.\n   *\n   * @type {EventsBinder}\n   */\n  var Binder = new EventsBinder();\n\n  var Autoplay = {\n    /**\n     * Initializes autoplaying and events.\n     *\n     * @return {Void}\n     */\n    mount: function mount() {\n      this.start();\n\n      if (Glide.settings.hoverpause) {\n        this.bind();\n      }\n    },\n\n\n    /**\n     * Starts autoplaying in configured interval.\n     *\n     * @param {Boolean|Number} force Run autoplaying with passed interval regardless of `autoplay` settings\n     * @return {Void}\n     */\n    start: function start() {\n      var _this = this;\n\n      if (Glide.settings.autoplay) {\n        if (isUndefined(this._i)) {\n          this._i = setInterval(function () {\n            _this.stop();\n\n            Components.Run.make('>');\n\n            _this.start();\n          }, this.time);\n        }\n      }\n    },\n\n\n    /**\n     * Stops autorunning of the glide.\n     *\n     * @return {Void}\n     */\n    stop: function stop() {\n      this._i = clearInterval(this._i);\n    },\n\n\n    /**\n     * Stops autoplaying while mouse is over glide's area.\n     *\n     * @return {Void}\n     */\n    bind: function bind() {\n      var _this2 = this;\n\n      Binder.on('mouseover', Components.Html.root, function () {\n        _this2.stop();\n      });\n\n      Binder.on('mouseout', Components.Html.root, function () {\n        _this2.start();\n      });\n    },\n\n\n    /**\n     * Unbind mouseover events.\n     *\n     * @returns {Void}\n     */\n    unbind: function unbind() {\n      Binder.off(['mouseover', 'mouseout'], Components.Html.root);\n    }\n  };\n\n  define(Autoplay, 'time', {\n    /**\n     * Gets time period value for the autoplay interval. Prioritizes\n     * times in `data-glide-autoplay` attrubutes over options.\n     *\n     * @return {Number}\n     */\n    get: function get() {\n      var autoplay = Components.Html.slides[Glide.index].getAttribute('data-glide-autoplay');\n\n      if (autoplay) {\n        return toInt(autoplay);\n      }\n\n      return toInt(Glide.settings.autoplay);\n    }\n  });\n\n  /**\n   * Stop autoplaying and unbind events:\n   * - on destroying, to clear defined interval\n   * - on updating via API to reset interval that may changed\n   */\n  Events.on(['destroy', 'update'], function () {\n    Autoplay.unbind();\n  });\n\n  /**\n   * Stop autoplaying:\n   * - before each run, to restart autoplaying\n   * - on pausing via API\n   * - on destroying, to clear defined interval\n   * - while starting a swipe\n   * - on updating via API to reset interval that may changed\n   */\n  Events.on(['run.before', 'pause', 'destroy', 'swipe.start', 'update'], function () {\n    Autoplay.stop();\n  });\n\n  /**\n   * Start autoplaying:\n   * - after each run, to restart autoplaying\n   * - on playing via API\n   * - while ending a swipe\n   */\n  Events.on(['run.after', 'play', 'swipe.end'], function () {\n    Autoplay.start();\n  });\n\n  /**\n   * Remount autoplaying:\n   * - on updating via API to reset interval that may changed\n   */\n  Events.on('update', function () {\n    Autoplay.mount();\n  });\n\n  /**\n   * Destroy a binder:\n   * - on destroying glide instance to clearup listeners\n   */\n  Events.on('destroy', function () {\n    Binder.destroy();\n  });\n\n  return Autoplay;\n}\n\n/**\n * Sorts keys of breakpoint object so they will be ordered from lower to bigger.\n *\n * @param {Object} points\n * @returns {Object}\n */\nfunction sortBreakpoints(points) {\n  if (isObject(points)) {\n    return sortKeys(points);\n  } else {\n    warn('Breakpoints option must be an object');\n  }\n\n  return {};\n}\n\nfunction Breakpoints (Glide, Components, Events) {\n  /**\n   * Instance of the binder for DOM Events.\n   *\n   * @type {EventsBinder}\n   */\n  var Binder = new EventsBinder();\n\n  /**\n   * Holds reference to settings.\n   *\n   * @type {Object}\n   */\n  var settings = Glide.settings;\n\n  /**\n   * Holds reference to breakpoints object in settings. Sorts breakpoints\n   * from smaller to larger. It is required in order to proper\n   * matching currently active breakpoint settings.\n   *\n   * @type {Object}\n   */\n  var points = sortBreakpoints(settings.breakpoints);\n\n  /**\n   * Cache initial settings before overwritting.\n   *\n   * @type {Object}\n   */\n  var defaults = _extends({}, settings);\n\n  var Breakpoints = {\n    /**\n     * Matches settings for currectly matching media breakpoint.\n     *\n     * @param {Object} points\n     * @returns {Object}\n     */\n    match: function match(points) {\n      if (typeof window.matchMedia !== 'undefined') {\n        for (var point in points) {\n          if (points.hasOwnProperty(point)) {\n            if (window.matchMedia('(max-width: ' + point + 'px)').matches) {\n              return points[point];\n            }\n          }\n        }\n      }\n\n      return defaults;\n    }\n  };\n\n  /**\n   * Overwrite instance settings with currently matching breakpoint settings.\n   * This happens right after component initialization.\n   */\n  _extends(settings, Breakpoints.match(points));\n\n  /**\n   * Update glide with settings of matched brekpoint:\n   * - window resize to update slider\n   */\n  Binder.on('resize', window, throttle(function () {\n    Glide.settings = mergeOptions(settings, Breakpoints.match(points));\n  }, Glide.settings.throttle));\n\n  /**\n   * Resort and update default settings:\n   * - on reinit via API, so breakpoint matching will be performed with options\n   */\n  Events.on('update', function () {\n    points = sortBreakpoints(points);\n\n    defaults = _extends({}, settings);\n  });\n\n  /**\n   * Unbind resize listener:\n   * - on destroying, to bring markup to its initial state\n   */\n  Events.on('destroy', function () {\n    Binder.off('resize', window);\n  });\n\n  return Breakpoints;\n}\n\nvar COMPONENTS = {\n  // Required\n  Html: Html,\n  Translate: Translate,\n  Transition: Transition,\n  Direction: Direction,\n  Peek: Peek,\n  Sizes: Sizes,\n  Gaps: Gaps,\n  Move: Move,\n  Clones: Clones,\n  Resize: Resize,\n  Build: Build,\n  Run: Run,\n\n  // Optional\n  Swipe: Swipe,\n  Images: Images,\n  Anchors: Anchors,\n  Controls: Controls,\n  Keyboard: Keyboard,\n  Autoplay: Autoplay,\n  Breakpoints: Breakpoints\n};\n\nvar Glide$1 = function (_Core) {\n  inherits(Glide$$1, _Core);\n\n  function Glide$$1() {\n    classCallCheck(this, Glide$$1);\n    return possibleConstructorReturn(this, (Glide$$1.__proto__ || Object.getPrototypeOf(Glide$$1)).apply(this, arguments));\n  }\n\n  createClass(Glide$$1, [{\n    key: 'mount',\n    value: function mount() {\n      var extensions = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : {};\n\n      return get(Glide$$1.prototype.__proto__ || Object.getPrototypeOf(Glide$$1.prototype), 'mount', this).call(this, _extends({}, COMPONENTS, extensions));\n    }\n  }]);\n  return Glide$$1;\n}(Glide);\n\n/* harmony default export */ __webpack_exports__[\"default\"] = (Glide$1);\n\n\n//# sourceURL=webpack:///./node_modules/@glidejs/glide/dist/glide.esm.js?");
  
  /***/ }),
  
  /***/ "./node_modules/aos/dist/aos.js":
  /*!**************************************!*\
    !*** ./node_modules/aos/dist/aos.js ***!
    \**************************************/
  /*! no static exports found */
  /***/ (function(module, exports, __webpack_require__) {
  
  eval("!function(e,t){ true?module.exports=t():undefined}(this,function(){return function(e){function t(o){if(n[o])return n[o].exports;var i=n[o]={exports:{},id:o,loaded:!1};return e[o].call(i.exports,i,i.exports,t),i.loaded=!0,i.exports}var n={};return t.m=e,t.c=n,t.p=\"dist/\",t(0)}([function(e,t,n){\"use strict\";function o(e){return e&&e.__esModule?e:{default:e}}var i=Object.assign||function(e){for(var t=1;t<arguments.length;t++){var n=arguments[t];for(var o in n)Object.prototype.hasOwnProperty.call(n,o)&&(e[o]=n[o])}return e},r=n(1),a=(o(r),n(6)),u=o(a),c=n(7),s=o(c),f=n(8),d=o(f),l=n(9),p=o(l),m=n(10),b=o(m),v=n(11),y=o(v),g=n(14),h=o(g),w=[],k=!1,x={offset:120,delay:0,easing:\"ease\",duration:400,disable:!1,once:!1,startEvent:\"DOMContentLoaded\",throttleDelay:99,debounceDelay:50,disableMutationObserver:!1},j=function(){var e=arguments.length>0&&void 0!==arguments[0]&&arguments[0];if(e&&(k=!0),k)return w=(0,y.default)(w,x),(0,b.default)(w,x.once),w},O=function(){w=(0,h.default)(),j()},M=function(){w.forEach(function(e,t){e.node.removeAttribute(\"data-aos\"),e.node.removeAttribute(\"data-aos-easing\"),e.node.removeAttribute(\"data-aos-duration\"),e.node.removeAttribute(\"data-aos-delay\")})},S=function(e){return e===!0||\"mobile\"===e&&p.default.mobile()||\"phone\"===e&&p.default.phone()||\"tablet\"===e&&p.default.tablet()||\"function\"==typeof e&&e()===!0},_=function(e){x=i(x,e),w=(0,h.default)();var t=document.all&&!window.atob;return S(x.disable)||t?M():(x.disableMutationObserver||d.default.isSupported()||(console.info('\\n      aos: MutationObserver is not supported on this browser,\\n      code mutations observing has been disabled.\\n      You may have to call \"refreshHard()\" by yourself.\\n    '),x.disableMutationObserver=!0),document.querySelector(\"body\").setAttribute(\"data-aos-easing\",x.easing),document.querySelector(\"body\").setAttribute(\"data-aos-duration\",x.duration),document.querySelector(\"body\").setAttribute(\"data-aos-delay\",x.delay),\"DOMContentLoaded\"===x.startEvent&&[\"complete\",\"interactive\"].indexOf(document.readyState)>-1?j(!0):\"load\"===x.startEvent?window.addEventListener(x.startEvent,function(){j(!0)}):document.addEventListener(x.startEvent,function(){j(!0)}),window.addEventListener(\"resize\",(0,s.default)(j,x.debounceDelay,!0)),window.addEventListener(\"orientationchange\",(0,s.default)(j,x.debounceDelay,!0)),window.addEventListener(\"scroll\",(0,u.default)(function(){(0,b.default)(w,x.once)},x.throttleDelay)),x.disableMutationObserver||d.default.ready(\"[data-aos]\",O),w)};e.exports={init:_,refresh:j,refreshHard:O}},function(e,t){},,,,,function(e,t){(function(t){\"use strict\";function n(e,t,n){function o(t){var n=b,o=v;return b=v=void 0,k=t,g=e.apply(o,n)}function r(e){return k=e,h=setTimeout(f,t),M?o(e):g}function a(e){var n=e-w,o=e-k,i=t-n;return S?j(i,y-o):i}function c(e){var n=e-w,o=e-k;return void 0===w||n>=t||n<0||S&&o>=y}function f(){var e=O();return c(e)?d(e):void(h=setTimeout(f,a(e)))}function d(e){return h=void 0,_&&b?o(e):(b=v=void 0,g)}function l(){void 0!==h&&clearTimeout(h),k=0,b=w=v=h=void 0}function p(){return void 0===h?g:d(O())}function m(){var e=O(),n=c(e);if(b=arguments,v=this,w=e,n){if(void 0===h)return r(w);if(S)return h=setTimeout(f,t),o(w)}return void 0===h&&(h=setTimeout(f,t)),g}var b,v,y,g,h,w,k=0,M=!1,S=!1,_=!0;if(\"function\"!=typeof e)throw new TypeError(s);return t=u(t)||0,i(n)&&(M=!!n.leading,S=\"maxWait\"in n,y=S?x(u(n.maxWait)||0,t):y,_=\"trailing\"in n?!!n.trailing:_),m.cancel=l,m.flush=p,m}function o(e,t,o){var r=!0,a=!0;if(\"function\"!=typeof e)throw new TypeError(s);return i(o)&&(r=\"leading\"in o?!!o.leading:r,a=\"trailing\"in o?!!o.trailing:a),n(e,t,{leading:r,maxWait:t,trailing:a})}function i(e){var t=\"undefined\"==typeof e?\"undefined\":c(e);return!!e&&(\"object\"==t||\"function\"==t)}function r(e){return!!e&&\"object\"==(\"undefined\"==typeof e?\"undefined\":c(e))}function a(e){return\"symbol\"==(\"undefined\"==typeof e?\"undefined\":c(e))||r(e)&&k.call(e)==d}function u(e){if(\"number\"==typeof e)return e;if(a(e))return f;if(i(e)){var t=\"function\"==typeof e.valueOf?e.valueOf():e;e=i(t)?t+\"\":t}if(\"string\"!=typeof e)return 0===e?e:+e;e=e.replace(l,\"\");var n=m.test(e);return n||b.test(e)?v(e.slice(2),n?2:8):p.test(e)?f:+e}var c=\"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},s=\"Expected a function\",f=NaN,d=\"[object Symbol]\",l=/^\\s+|\\s+$/g,p=/^[-+]0x[0-9a-f]+$/i,m=/^0b[01]+$/i,b=/^0o[0-7]+$/i,v=parseInt,y=\"object\"==(\"undefined\"==typeof t?\"undefined\":c(t))&&t&&t.Object===Object&&t,g=\"object\"==(\"undefined\"==typeof self?\"undefined\":c(self))&&self&&self.Object===Object&&self,h=y||g||Function(\"return this\")(),w=Object.prototype,k=w.toString,x=Math.max,j=Math.min,O=function(){return h.Date.now()};e.exports=o}).call(t,function(){return this}())},function(e,t){(function(t){\"use strict\";function n(e,t,n){function i(t){var n=b,o=v;return b=v=void 0,O=t,g=e.apply(o,n)}function r(e){return O=e,h=setTimeout(f,t),M?i(e):g}function u(e){var n=e-w,o=e-O,i=t-n;return S?x(i,y-o):i}function s(e){var n=e-w,o=e-O;return void 0===w||n>=t||n<0||S&&o>=y}function f(){var e=j();return s(e)?d(e):void(h=setTimeout(f,u(e)))}function d(e){return h=void 0,_&&b?i(e):(b=v=void 0,g)}function l(){void 0!==h&&clearTimeout(h),O=0,b=w=v=h=void 0}function p(){return void 0===h?g:d(j())}function m(){var e=j(),n=s(e);if(b=arguments,v=this,w=e,n){if(void 0===h)return r(w);if(S)return h=setTimeout(f,t),i(w)}return void 0===h&&(h=setTimeout(f,t)),g}var b,v,y,g,h,w,O=0,M=!1,S=!1,_=!0;if(\"function\"!=typeof e)throw new TypeError(c);return t=a(t)||0,o(n)&&(M=!!n.leading,S=\"maxWait\"in n,y=S?k(a(n.maxWait)||0,t):y,_=\"trailing\"in n?!!n.trailing:_),m.cancel=l,m.flush=p,m}function o(e){var t=\"undefined\"==typeof e?\"undefined\":u(e);return!!e&&(\"object\"==t||\"function\"==t)}function i(e){return!!e&&\"object\"==(\"undefined\"==typeof e?\"undefined\":u(e))}function r(e){return\"symbol\"==(\"undefined\"==typeof e?\"undefined\":u(e))||i(e)&&w.call(e)==f}function a(e){if(\"number\"==typeof e)return e;if(r(e))return s;if(o(e)){var t=\"function\"==typeof e.valueOf?e.valueOf():e;e=o(t)?t+\"\":t}if(\"string\"!=typeof e)return 0===e?e:+e;e=e.replace(d,\"\");var n=p.test(e);return n||m.test(e)?b(e.slice(2),n?2:8):l.test(e)?s:+e}var u=\"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=\"Expected a function\",s=NaN,f=\"[object Symbol]\",d=/^\\s+|\\s+$/g,l=/^[-+]0x[0-9a-f]+$/i,p=/^0b[01]+$/i,m=/^0o[0-7]+$/i,b=parseInt,v=\"object\"==(\"undefined\"==typeof t?\"undefined\":u(t))&&t&&t.Object===Object&&t,y=\"object\"==(\"undefined\"==typeof self?\"undefined\":u(self))&&self&&self.Object===Object&&self,g=v||y||Function(\"return this\")(),h=Object.prototype,w=h.toString,k=Math.max,x=Math.min,j=function(){return g.Date.now()};e.exports=n}).call(t,function(){return this}())},function(e,t){\"use strict\";function n(e){var t=void 0,o=void 0,i=void 0;for(t=0;t<e.length;t+=1){if(o=e[t],o.dataset&&o.dataset.aos)return!0;if(i=o.children&&n(o.children))return!0}return!1}function o(){return window.MutationObserver||window.WebKitMutationObserver||window.MozMutationObserver}function i(){return!!o()}function r(e,t){var n=window.document,i=o(),r=new i(a);u=t,r.observe(n.documentElement,{childList:!0,subtree:!0,removedNodes:!0})}function a(e){e&&e.forEach(function(e){var t=Array.prototype.slice.call(e.addedNodes),o=Array.prototype.slice.call(e.removedNodes),i=t.concat(o);if(n(i))return u()})}Object.defineProperty(t,\"__esModule\",{value:!0});var u=function(){};t.default={isSupported:i,ready:r}},function(e,t){\"use strict\";function n(e,t){if(!(e instanceof t))throw new TypeError(\"Cannot call a class as a function\")}function o(){return navigator.userAgent||navigator.vendor||window.opera||\"\"}Object.defineProperty(t,\"__esModule\",{value:!0});var i=function(){function e(e,t){for(var n=0;n<t.length;n++){var o=t[n];o.enumerable=o.enumerable||!1,o.configurable=!0,\"value\"in o&&(o.writable=!0),Object.defineProperty(e,o.key,o)}}return function(t,n,o){return n&&e(t.prototype,n),o&&e(t,o),t}}(),r=/(android|bb\\d+|meego).+mobile|avantgo|bada\\/|blackberry|blazer|compal|elaine|fennec|hiptop|iemobile|ip(hone|od)|iris|kindle|lge |maemo|midp|mmp|mobile.+firefox|netfront|opera m(ob|in)i|palm( os)?|phone|p(ixi|re)\\/|plucker|pocket|psp|series(4|6)0|symbian|treo|up\\.(browser|link)|vodafone|wap|windows ce|xda|xiino/i,a=/1207|6310|6590|3gso|4thp|50[1-6]i|770s|802s|a wa|abac|ac(er|oo|s\\-)|ai(ko|rn)|al(av|ca|co)|amoi|an(ex|ny|yw)|aptu|ar(ch|go)|as(te|us)|attw|au(di|\\-m|r |s )|avan|be(ck|ll|nq)|bi(lb|rd)|bl(ac|az)|br(e|v)w|bumb|bw\\-(n|u)|c55\\/|capi|ccwa|cdm\\-|cell|chtm|cldc|cmd\\-|co(mp|nd)|craw|da(it|ll|ng)|dbte|dc\\-s|devi|dica|dmob|do(c|p)o|ds(12|\\-d)|el(49|ai)|em(l2|ul)|er(ic|k0)|esl8|ez([4-7]0|os|wa|ze)|fetc|fly(\\-|_)|g1 u|g560|gene|gf\\-5|g\\-mo|go(\\.w|od)|gr(ad|un)|haie|hcit|hd\\-(m|p|t)|hei\\-|hi(pt|ta)|hp( i|ip)|hs\\-c|ht(c(\\-| |_|a|g|p|s|t)|tp)|hu(aw|tc)|i\\-(20|go|ma)|i230|iac( |\\-|\\/)|ibro|idea|ig01|ikom|im1k|inno|ipaq|iris|ja(t|v)a|jbro|jemu|jigs|kddi|keji|kgt( |\\/)|klon|kpt |kwc\\-|kyo(c|k)|le(no|xi)|lg( g|\\/(k|l|u)|50|54|\\-[a-w])|libw|lynx|m1\\-w|m3ga|m50\\/|ma(te|ui|xo)|mc(01|21|ca)|m\\-cr|me(rc|ri)|mi(o8|oa|ts)|mmef|mo(01|02|bi|de|do|t(\\-| |o|v)|zz)|mt(50|p1|v )|mwbp|mywa|n10[0-2]|n20[2-3]|n30(0|2)|n50(0|2|5)|n7(0(0|1)|10)|ne((c|m)\\-|on|tf|wf|wg|wt)|nok(6|i)|nzph|o2im|op(ti|wv)|oran|owg1|p800|pan(a|d|t)|pdxg|pg(13|\\-([1-8]|c))|phil|pire|pl(ay|uc)|pn\\-2|po(ck|rt|se)|prox|psio|pt\\-g|qa\\-a|qc(07|12|21|32|60|\\-[2-7]|i\\-)|qtek|r380|r600|raks|rim9|ro(ve|zo)|s55\\/|sa(ge|ma|mm|ms|ny|va)|sc(01|h\\-|oo|p\\-)|sdk\\/|se(c(\\-|0|1)|47|mc|nd|ri)|sgh\\-|shar|sie(\\-|m)|sk\\-0|sl(45|id)|sm(al|ar|b3|it|t5)|so(ft|ny)|sp(01|h\\-|v\\-|v )|sy(01|mb)|t2(18|50)|t6(00|10|18)|ta(gt|lk)|tcl\\-|tdg\\-|tel(i|m)|tim\\-|t\\-mo|to(pl|sh)|ts(70|m\\-|m3|m5)|tx\\-9|up(\\.b|g1|si)|utst|v400|v750|veri|vi(rg|te)|vk(40|5[0-3]|\\-v)|vm40|voda|vulc|vx(52|53|60|61|70|80|81|83|85|98)|w3c(\\-| )|webc|whit|wi(g |nc|nw)|wmlb|wonu|x700|yas\\-|your|zeto|zte\\-/i,u=/(android|bb\\d+|meego).+mobile|avantgo|bada\\/|blackberry|blazer|compal|elaine|fennec|hiptop|iemobile|ip(hone|od)|iris|kindle|lge |maemo|midp|mmp|mobile.+firefox|netfront|opera m(ob|in)i|palm( os)?|phone|p(ixi|re)\\/|plucker|pocket|psp|series(4|6)0|symbian|treo|up\\.(browser|link)|vodafone|wap|windows ce|xda|xiino|android|ipad|playbook|silk/i,c=/1207|6310|6590|3gso|4thp|50[1-6]i|770s|802s|a wa|abac|ac(er|oo|s\\-)|ai(ko|rn)|al(av|ca|co)|amoi|an(ex|ny|yw)|aptu|ar(ch|go)|as(te|us)|attw|au(di|\\-m|r |s )|avan|be(ck|ll|nq)|bi(lb|rd)|bl(ac|az)|br(e|v)w|bumb|bw\\-(n|u)|c55\\/|capi|ccwa|cdm\\-|cell|chtm|cldc|cmd\\-|co(mp|nd)|craw|da(it|ll|ng)|dbte|dc\\-s|devi|dica|dmob|do(c|p)o|ds(12|\\-d)|el(49|ai)|em(l2|ul)|er(ic|k0)|esl8|ez([4-7]0|os|wa|ze)|fetc|fly(\\-|_)|g1 u|g560|gene|gf\\-5|g\\-mo|go(\\.w|od)|gr(ad|un)|haie|hcit|hd\\-(m|p|t)|hei\\-|hi(pt|ta)|hp( i|ip)|hs\\-c|ht(c(\\-| |_|a|g|p|s|t)|tp)|hu(aw|tc)|i\\-(20|go|ma)|i230|iac( |\\-|\\/)|ibro|idea|ig01|ikom|im1k|inno|ipaq|iris|ja(t|v)a|jbro|jemu|jigs|kddi|keji|kgt( |\\/)|klon|kpt |kwc\\-|kyo(c|k)|le(no|xi)|lg( g|\\/(k|l|u)|50|54|\\-[a-w])|libw|lynx|m1\\-w|m3ga|m50\\/|ma(te|ui|xo)|mc(01|21|ca)|m\\-cr|me(rc|ri)|mi(o8|oa|ts)|mmef|mo(01|02|bi|de|do|t(\\-| |o|v)|zz)|mt(50|p1|v )|mwbp|mywa|n10[0-2]|n20[2-3]|n30(0|2)|n50(0|2|5)|n7(0(0|1)|10)|ne((c|m)\\-|on|tf|wf|wg|wt)|nok(6|i)|nzph|o2im|op(ti|wv)|oran|owg1|p800|pan(a|d|t)|pdxg|pg(13|\\-([1-8]|c))|phil|pire|pl(ay|uc)|pn\\-2|po(ck|rt|se)|prox|psio|pt\\-g|qa\\-a|qc(07|12|21|32|60|\\-[2-7]|i\\-)|qtek|r380|r600|raks|rim9|ro(ve|zo)|s55\\/|sa(ge|ma|mm|ms|ny|va)|sc(01|h\\-|oo|p\\-)|sdk\\/|se(c(\\-|0|1)|47|mc|nd|ri)|sgh\\-|shar|sie(\\-|m)|sk\\-0|sl(45|id)|sm(al|ar|b3|it|t5)|so(ft|ny)|sp(01|h\\-|v\\-|v )|sy(01|mb)|t2(18|50)|t6(00|10|18)|ta(gt|lk)|tcl\\-|tdg\\-|tel(i|m)|tim\\-|t\\-mo|to(pl|sh)|ts(70|m\\-|m3|m5)|tx\\-9|up(\\.b|g1|si)|utst|v400|v750|veri|vi(rg|te)|vk(40|5[0-3]|\\-v)|vm40|voda|vulc|vx(52|53|60|61|70|80|81|83|85|98)|w3c(\\-| )|webc|whit|wi(g |nc|nw)|wmlb|wonu|x700|yas\\-|your|zeto|zte\\-/i,s=function(){function e(){n(this,e)}return i(e,[{key:\"phone\",value:function(){var e=o();return!(!r.test(e)&&!a.test(e.substr(0,4)))}},{key:\"mobile\",value:function(){var e=o();return!(!u.test(e)&&!c.test(e.substr(0,4)))}},{key:\"tablet\",value:function(){return this.mobile()&&!this.phone()}}]),e}();t.default=new s},function(e,t){\"use strict\";Object.defineProperty(t,\"__esModule\",{value:!0});var n=function(e,t,n){var o=e.node.getAttribute(\"data-aos-once\");t>e.position?e.node.classList.add(\"aos-animate\"):\"undefined\"!=typeof o&&(\"false\"===o||!n&&\"true\"!==o)&&e.node.classList.remove(\"aos-animate\")},o=function(e,t){var o=window.pageYOffset,i=window.innerHeight;e.forEach(function(e,r){n(e,i+o,t)})};t.default=o},function(e,t,n){\"use strict\";function o(e){return e&&e.__esModule?e:{default:e}}Object.defineProperty(t,\"__esModule\",{value:!0});var i=n(12),r=o(i),a=function(e,t){return e.forEach(function(e,n){e.node.classList.add(\"aos-init\"),e.position=(0,r.default)(e.node,t.offset)}),e};t.default=a},function(e,t,n){\"use strict\";function o(e){return e&&e.__esModule?e:{default:e}}Object.defineProperty(t,\"__esModule\",{value:!0});var i=n(13),r=o(i),a=function(e,t){var n=0,o=0,i=window.innerHeight,a={offset:e.getAttribute(\"data-aos-offset\"),anchor:e.getAttribute(\"data-aos-anchor\"),anchorPlacement:e.getAttribute(\"data-aos-anchor-placement\")};switch(a.offset&&!isNaN(a.offset)&&(o=parseInt(a.offset)),a.anchor&&document.querySelectorAll(a.anchor)&&(e=document.querySelectorAll(a.anchor)[0]),n=(0,r.default)(e).top,a.anchorPlacement){case\"top-bottom\":break;case\"center-bottom\":n+=e.offsetHeight/2;break;case\"bottom-bottom\":n+=e.offsetHeight;break;case\"top-center\":n+=i/2;break;case\"bottom-center\":n+=i/2+e.offsetHeight;break;case\"center-center\":n+=i/2+e.offsetHeight/2;break;case\"top-top\":n+=i;break;case\"bottom-top\":n+=e.offsetHeight+i;break;case\"center-top\":n+=e.offsetHeight/2+i}return a.anchorPlacement||a.offset||isNaN(t)||(o=t),n+o};t.default=a},function(e,t){\"use strict\";Object.defineProperty(t,\"__esModule\",{value:!0});var n=function(e){for(var t=0,n=0;e&&!isNaN(e.offsetLeft)&&!isNaN(e.offsetTop);)t+=e.offsetLeft-(\"BODY\"!=e.tagName?e.scrollLeft:0),n+=e.offsetTop-(\"BODY\"!=e.tagName?e.scrollTop:0),e=e.offsetParent;return{top:n,left:t}};t.default=n},function(e,t){\"use strict\";Object.defineProperty(t,\"__esModule\",{value:!0});var n=function(e){return e=e||document.querySelectorAll(\"[data-aos]\"),Array.prototype.map.call(e,function(e){return{node:e}})};t.default=n}])});\n\n//# sourceURL=webpack:///./node_modules/aos/dist/aos.js?");
  
  /***/ }),
  
  /***/ "./node_modules/desandro-matches-selector/matches-selector.js":
  /*!********************************************************************!*\
    !*** ./node_modules/desandro-matches-selector/matches-selector.js ***!
    \********************************************************************/
  /*! no static exports found */
  /***/ (function(module, exports, __webpack_require__) {
  
  eval("var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_RESULT__;/**\n * matchesSelector v2.0.2\n * matchesSelector( element, '.selector' )\n * MIT license\n */\n\n/*jshint browser: true, strict: true, undef: true, unused: true */\n\n( function( window, factory ) {\n  /*global define: false, module: false */\n  'use strict';\n  // universal module definition\n  if ( true ) {\n    // AMD\n    !(__WEBPACK_AMD_DEFINE_FACTORY__ = (factory),\n\t\t\t\t__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?\n\t\t\t\t(__WEBPACK_AMD_DEFINE_FACTORY__.call(exports, __webpack_require__, exports, module)) :\n\t\t\t\t__WEBPACK_AMD_DEFINE_FACTORY__),\n\t\t\t\t__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));\n  } else {}\n\n}( window, function factory() {\n  'use strict';\n\n  var matchesMethod = ( function() {\n    var ElemProto = window.Element.prototype;\n    // check for the standard method name first\n    if ( ElemProto.matches ) {\n      return 'matches';\n    }\n    // check un-prefixed\n    if ( ElemProto.matchesSelector ) {\n      return 'matchesSelector';\n    }\n    // check vendor prefixes\n    var prefixes = [ 'webkit', 'moz', 'ms', 'o' ];\n\n    for ( var i=0; i < prefixes.length; i++ ) {\n      var prefix = prefixes[i];\n      var method = prefix + 'MatchesSelector';\n      if ( ElemProto[ method ] ) {\n        return method;\n      }\n    }\n  })();\n\n  return function matchesSelector( elem, selector ) {\n    return elem[ matchesMethod ]( selector );\n  };\n\n}));\n\n\n//# sourceURL=webpack:///./node_modules/desandro-matches-selector/matches-selector.js?");
  
  /***/ }),
  
  /***/ "./node_modules/ev-emitter/ev-emitter.js":
  /*!***********************************************!*\
    !*** ./node_modules/ev-emitter/ev-emitter.js ***!
    \***********************************************/
  /*! no static exports found */
  /***/ (function(module, exports, __webpack_require__) {
  
  eval("var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_RESULT__;/**\n * EvEmitter v1.1.0\n * Lil' event emitter\n * MIT License\n */\n\n/* jshint unused: true, undef: true, strict: true */\n\n( function( global, factory ) {\n  // universal module definition\n  /* jshint strict: false */ /* globals define, module, window */\n  if ( true ) {\n    // AMD - RequireJS\n    !(__WEBPACK_AMD_DEFINE_FACTORY__ = (factory),\n\t\t\t\t__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?\n\t\t\t\t(__WEBPACK_AMD_DEFINE_FACTORY__.call(exports, __webpack_require__, exports, module)) :\n\t\t\t\t__WEBPACK_AMD_DEFINE_FACTORY__),\n\t\t\t\t__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));\n  } else {}\n\n}( typeof window != 'undefined' ? window : this, function() {\n\n\"use strict\";\n\nfunction EvEmitter() {}\n\nvar proto = EvEmitter.prototype;\n\nproto.on = function( eventName, listener ) {\n  if ( !eventName || !listener ) {\n    return;\n  }\n  // set events hash\n  var events = this._events = this._events || {};\n  // set listeners array\n  var listeners = events[ eventName ] = events[ eventName ] || [];\n  // only add once\n  if ( listeners.indexOf( listener ) == -1 ) {\n    listeners.push( listener );\n  }\n\n  return this;\n};\n\nproto.once = function( eventName, listener ) {\n  if ( !eventName || !listener ) {\n    return;\n  }\n  // add event\n  this.on( eventName, listener );\n  // set once flag\n  // set onceEvents hash\n  var onceEvents = this._onceEvents = this._onceEvents || {};\n  // set onceListeners object\n  var onceListeners = onceEvents[ eventName ] = onceEvents[ eventName ] || {};\n  // set flag\n  onceListeners[ listener ] = true;\n\n  return this;\n};\n\nproto.off = function( eventName, listener ) {\n  var listeners = this._events && this._events[ eventName ];\n  if ( !listeners || !listeners.length ) {\n    return;\n  }\n  var index = listeners.indexOf( listener );\n  if ( index != -1 ) {\n    listeners.splice( index, 1 );\n  }\n\n  return this;\n};\n\nproto.emitEvent = function( eventName, args ) {\n  var listeners = this._events && this._events[ eventName ];\n  if ( !listeners || !listeners.length ) {\n    return;\n  }\n  // copy over to avoid interference if .off() in listener\n  listeners = listeners.slice(0);\n  args = args || [];\n  // once stuff\n  var onceListeners = this._onceEvents && this._onceEvents[ eventName ];\n\n  for ( var i=0; i < listeners.length; i++ ) {\n    var listener = listeners[i]\n    var isOnce = onceListeners && onceListeners[ listener ];\n    if ( isOnce ) {\n      // remove listener\n      // remove before trigger to prevent recursion\n      this.off( eventName, listener );\n      // unset once flag\n      delete onceListeners[ listener ];\n    }\n    // trigger listener\n    listener.apply( this, args );\n  }\n\n  return this;\n};\n\nproto.allOff = function() {\n  delete this._events;\n  delete this._onceEvents;\n};\n\nreturn EvEmitter;\n\n}));\n\n\n//# sourceURL=webpack:///./node_modules/ev-emitter/ev-emitter.js?");
  
  /***/ }),
  
  /***/ "./node_modules/fizzy-ui-utils/utils.js":
  /*!**********************************************!*\
    !*** ./node_modules/fizzy-ui-utils/utils.js ***!
    \**********************************************/
  /*! no static exports found */
  /***/ (function(module, exports, __webpack_require__) {
  
  eval("var __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/**\n * Fizzy UI utils v2.0.7\n * MIT license\n */\n\n/*jshint browser: true, undef: true, unused: true, strict: true */\n\n( function( window, factory ) {\n  // universal module definition\n  /*jshint strict: false */ /*globals define, module, require */\n\n  if ( true ) {\n    // AMD\n    !(__WEBPACK_AMD_DEFINE_ARRAY__ = [\n      __webpack_require__(/*! desandro-matches-selector/matches-selector */ \"./node_modules/desandro-matches-selector/matches-selector.js\")\n    ], __WEBPACK_AMD_DEFINE_RESULT__ = (function( matchesSelector ) {\n      return factory( window, matchesSelector );\n    }).apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__),\n\t\t\t\t__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));\n  } else {}\n\n}( window, function factory( window, matchesSelector ) {\n\n'use strict';\n\nvar utils = {};\n\n// ----- extend ----- //\n\n// extends objects\nutils.extend = function( a, b ) {\n  for ( var prop in b ) {\n    a[ prop ] = b[ prop ];\n  }\n  return a;\n};\n\n// ----- modulo ----- //\n\nutils.modulo = function( num, div ) {\n  return ( ( num % div ) + div ) % div;\n};\n\n// ----- makeArray ----- //\n\nvar arraySlice = Array.prototype.slice;\n\n// turn element or nodeList into an array\nutils.makeArray = function( obj ) {\n  if ( Array.isArray( obj ) ) {\n    // use object if already an array\n    return obj;\n  }\n  // return empty array if undefined or null. #6\n  if ( obj === null || obj === undefined ) {\n    return [];\n  }\n\n  var isArrayLike = typeof obj == 'object' && typeof obj.length == 'number';\n  if ( isArrayLike ) {\n    // convert nodeList to array\n    return arraySlice.call( obj );\n  }\n\n  // array of single index\n  return [ obj ];\n};\n\n// ----- removeFrom ----- //\n\nutils.removeFrom = function( ary, obj ) {\n  var index = ary.indexOf( obj );\n  if ( index != -1 ) {\n    ary.splice( index, 1 );\n  }\n};\n\n// ----- getParent ----- //\n\nutils.getParent = function( elem, selector ) {\n  while ( elem.parentNode && elem != document.body ) {\n    elem = elem.parentNode;\n    if ( matchesSelector( elem, selector ) ) {\n      return elem;\n    }\n  }\n};\n\n// ----- getQueryElement ----- //\n\n// use element as selector string\nutils.getQueryElement = function( elem ) {\n  if ( typeof elem == 'string' ) {\n    return document.querySelector( elem );\n  }\n  return elem;\n};\n\n// ----- handleEvent ----- //\n\n// enable .ontype to trigger from .addEventListener( elem, 'type' )\nutils.handleEvent = function( event ) {\n  var method = 'on' + event.type;\n  if ( this[ method ] ) {\n    this[ method ]( event );\n  }\n};\n\n// ----- filterFindElements ----- //\n\nutils.filterFindElements = function( elems, selector ) {\n  // make array of elems\n  elems = utils.makeArray( elems );\n  var ffElems = [];\n\n  elems.forEach( function( elem ) {\n    // check that elem is an actual element\n    if ( !( elem instanceof HTMLElement ) ) {\n      return;\n    }\n    // add elem if no selector\n    if ( !selector ) {\n      ffElems.push( elem );\n      return;\n    }\n    // filter & find items if we have a selector\n    // filter\n    if ( matchesSelector( elem, selector ) ) {\n      ffElems.push( elem );\n    }\n    // find children\n    var childElems = elem.querySelectorAll( selector );\n    // concat childElems to filterFound array\n    for ( var i=0; i < childElems.length; i++ ) {\n      ffElems.push( childElems[i] );\n    }\n  });\n\n  return ffElems;\n};\n\n// ----- debounceMethod ----- //\n\nutils.debounceMethod = function( _class, methodName, threshold ) {\n  threshold = threshold || 100;\n  // original method\n  var method = _class.prototype[ methodName ];\n  var timeoutName = methodName + 'Timeout';\n\n  _class.prototype[ methodName ] = function() {\n    var timeout = this[ timeoutName ];\n    clearTimeout( timeout );\n\n    var args = arguments;\n    var _this = this;\n    this[ timeoutName ] = setTimeout( function() {\n      method.apply( _this, args );\n      delete _this[ timeoutName ];\n    }, threshold );\n  };\n};\n\n// ----- docReady ----- //\n\nutils.docReady = function( callback ) {\n  var readyState = document.readyState;\n  if ( readyState == 'complete' || readyState == 'interactive' ) {\n    // do async to allow for other scripts to run. metafizzy/flickity#441\n    setTimeout( callback );\n  } else {\n    document.addEventListener( 'DOMContentLoaded', callback );\n  }\n};\n\n// ----- htmlInit ----- //\n\n// http://jamesroberts.name/blog/2010/02/22/string-functions-for-javascript-trim-to-camel-case-to-dashed-and-to-underscore/\nutils.toDashed = function( str ) {\n  return str.replace( /(.)([A-Z])/g, function( match, $1, $2 ) {\n    return $1 + '-' + $2;\n  }).toLowerCase();\n};\n\nvar console = window.console;\n/**\n * allow user to initialize classes via [data-namespace] or .js-namespace class\n * htmlInit( Widget, 'widgetName' )\n * options are parsed from data-namespace-options\n */\nutils.htmlInit = function( WidgetClass, namespace ) {\n  utils.docReady( function() {\n    var dashedNamespace = utils.toDashed( namespace );\n    var dataAttr = 'data-' + dashedNamespace;\n    var dataAttrElems = document.querySelectorAll( '[' + dataAttr + ']' );\n    var jsDashElems = document.querySelectorAll( '.js-' + dashedNamespace );\n    var elems = utils.makeArray( dataAttrElems )\n      .concat( utils.makeArray( jsDashElems ) );\n    var dataOptionsAttr = dataAttr + '-options';\n    var jQuery = window.jQuery;\n\n    elems.forEach( function( elem ) {\n      var attr = elem.getAttribute( dataAttr ) ||\n        elem.getAttribute( dataOptionsAttr );\n      var options;\n      try {\n        options = attr && JSON.parse( attr );\n      } catch ( error ) {\n        // log error, do not initialize\n        if ( console ) {\n          console.error( 'Error parsing ' + dataAttr + ' on ' + elem.className +\n          ': ' + error );\n        }\n        return;\n      }\n      // initialize\n      var instance = new WidgetClass( elem, options );\n      // make available via $().data('namespace')\n      if ( jQuery ) {\n        jQuery.data( elem, namespace, instance );\n      }\n    });\n\n  });\n};\n\n// -----  ----- //\n\nreturn utils;\n\n}));\n\n\n//# sourceURL=webpack:///./node_modules/fizzy-ui-utils/utils.js?");
  
  /***/ }),
  
  /***/ "./node_modules/get-size/get-size.js":
  /*!*******************************************!*\
    !*** ./node_modules/get-size/get-size.js ***!
    \*******************************************/
  /*! no static exports found */
  /***/ (function(module, exports, __webpack_require__) {
  
  eval("var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_RESULT__;/*!\n * getSize v2.0.3\n * measure size of elements\n * MIT license\n */\n\n/* jshint browser: true, strict: true, undef: true, unused: true */\n/* globals console: false */\n\n( function( window, factory ) {\n  /* jshint strict: false */ /* globals define, module */\n  if ( true ) {\n    // AMD\n    !(__WEBPACK_AMD_DEFINE_FACTORY__ = (factory),\n\t\t\t\t__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?\n\t\t\t\t(__WEBPACK_AMD_DEFINE_FACTORY__.call(exports, __webpack_require__, exports, module)) :\n\t\t\t\t__WEBPACK_AMD_DEFINE_FACTORY__),\n\t\t\t\t__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));\n  } else {}\n\n})( window, function factory() {\n'use strict';\n\n// -------------------------- helpers -------------------------- //\n\n// get a number from a string, not a percentage\nfunction getStyleSize( value ) {\n  var num = parseFloat( value );\n  // not a percent like '100%', and a number\n  var isValid = value.indexOf('%') == -1 && !isNaN( num );\n  return isValid && num;\n}\n\nfunction noop() {}\n\nvar logError = typeof console == 'undefined' ? noop :\n  function( message ) {\n    console.error( message );\n  };\n\n// -------------------------- measurements -------------------------- //\n\nvar measurements = [\n  'paddingLeft',\n  'paddingRight',\n  'paddingTop',\n  'paddingBottom',\n  'marginLeft',\n  'marginRight',\n  'marginTop',\n  'marginBottom',\n  'borderLeftWidth',\n  'borderRightWidth',\n  'borderTopWidth',\n  'borderBottomWidth'\n];\n\nvar measurementsLength = measurements.length;\n\nfunction getZeroSize() {\n  var size = {\n    width: 0,\n    height: 0,\n    innerWidth: 0,\n    innerHeight: 0,\n    outerWidth: 0,\n    outerHeight: 0\n  };\n  for ( var i=0; i < measurementsLength; i++ ) {\n    var measurement = measurements[i];\n    size[ measurement ] = 0;\n  }\n  return size;\n}\n\n// -------------------------- getStyle -------------------------- //\n\n/**\n * getStyle, get style of element, check for Firefox bug\n * https://bugzilla.mozilla.org/show_bug.cgi?id=548397\n */\nfunction getStyle( elem ) {\n  var style = getComputedStyle( elem );\n  if ( !style ) {\n    logError( 'Style returned ' + style +\n      '. Are you running this code in a hidden iframe on Firefox? ' +\n      'See https://bit.ly/getsizebug1' );\n  }\n  return style;\n}\n\n// -------------------------- setup -------------------------- //\n\nvar isSetup = false;\n\nvar isBoxSizeOuter;\n\n/**\n * setup\n * check isBoxSizerOuter\n * do on first getSize() rather than on page load for Firefox bug\n */\nfunction setup() {\n  // setup once\n  if ( isSetup ) {\n    return;\n  }\n  isSetup = true;\n\n  // -------------------------- box sizing -------------------------- //\n\n  /**\n   * Chrome & Safari measure the outer-width on style.width on border-box elems\n   * IE11 & Firefox<29 measures the inner-width\n   */\n  var div = document.createElement('div');\n  div.style.width = '200px';\n  div.style.padding = '1px 2px 3px 4px';\n  div.style.borderStyle = 'solid';\n  div.style.borderWidth = '1px 2px 3px 4px';\n  div.style.boxSizing = 'border-box';\n\n  var body = document.body || document.documentElement;\n  body.appendChild( div );\n  var style = getStyle( div );\n  // round value for browser zoom. desandro/masonry#928\n  isBoxSizeOuter = Math.round( getStyleSize( style.width ) ) == 200;\n  getSize.isBoxSizeOuter = isBoxSizeOuter;\n\n  body.removeChild( div );\n}\n\n// -------------------------- getSize -------------------------- //\n\nfunction getSize( elem ) {\n  setup();\n\n  // use querySeletor if elem is string\n  if ( typeof elem == 'string' ) {\n    elem = document.querySelector( elem );\n  }\n\n  // do not proceed on non-objects\n  if ( !elem || typeof elem != 'object' || !elem.nodeType ) {\n    return;\n  }\n\n  var style = getStyle( elem );\n\n  // if hidden, everything is 0\n  if ( style.display == 'none' ) {\n    return getZeroSize();\n  }\n\n  var size = {};\n  size.width = elem.offsetWidth;\n  size.height = elem.offsetHeight;\n\n  var isBorderBox = size.isBorderBox = style.boxSizing == 'border-box';\n\n  // get all measurements\n  for ( var i=0; i < measurementsLength; i++ ) {\n    var measurement = measurements[i];\n    var value = style[ measurement ];\n    var num = parseFloat( value );\n    // any 'auto', 'medium' value will be 0\n    size[ measurement ] = !isNaN( num ) ? num : 0;\n  }\n\n  var paddingWidth = size.paddingLeft + size.paddingRight;\n  var paddingHeight = size.paddingTop + size.paddingBottom;\n  var marginWidth = size.marginLeft + size.marginRight;\n  var marginHeight = size.marginTop + size.marginBottom;\n  var borderWidth = size.borderLeftWidth + size.borderRightWidth;\n  var borderHeight = size.borderTopWidth + size.borderBottomWidth;\n\n  var isBorderBoxSizeOuter = isBorderBox && isBoxSizeOuter;\n\n  // overwrite width and height if we can get it from style\n  var styleWidth = getStyleSize( style.width );\n  if ( styleWidth !== false ) {\n    size.width = styleWidth +\n      // add padding and border unless it's already including it\n      ( isBorderBoxSizeOuter ? 0 : paddingWidth + borderWidth );\n  }\n\n  var styleHeight = getStyleSize( style.height );\n  if ( styleHeight !== false ) {\n    size.height = styleHeight +\n      // add padding and border unless it's already including it\n      ( isBorderBoxSizeOuter ? 0 : paddingHeight + borderHeight );\n  }\n\n  size.innerWidth = size.width - ( paddingWidth + borderWidth );\n  size.innerHeight = size.height - ( paddingHeight + borderHeight );\n\n  size.outerWidth = size.width + marginWidth;\n  size.outerHeight = size.height + marginHeight;\n\n  return size;\n}\n\nreturn getSize;\n\n});\n\n\n//# sourceURL=webpack:///./node_modules/get-size/get-size.js?");
  
  /***/ }),
  
  /***/ "./node_modules/imagesloaded/imagesloaded.js":
  /*!***************************************************!*\
    !*** ./node_modules/imagesloaded/imagesloaded.js ***!
    \***************************************************/
  /*! no static exports found */
  /***/ (function(module, exports, __webpack_require__) {
  
  eval("var __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/*!\n * imagesLoaded v4.1.4\n * JavaScript is all like \"You images are done yet or what?\"\n * MIT License\n */\n\n( function( window, factory ) { 'use strict';\n  // universal module definition\n\n  /*global define: false, module: false, require: false */\n\n  if ( true ) {\n    // AMD\n    !(__WEBPACK_AMD_DEFINE_ARRAY__ = [\n      __webpack_require__(/*! ev-emitter/ev-emitter */ \"./node_modules/ev-emitter/ev-emitter.js\")\n    ], __WEBPACK_AMD_DEFINE_RESULT__ = (function( EvEmitter ) {\n      return factory( window, EvEmitter );\n    }).apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__),\n\t\t\t\t__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));\n  } else {}\n\n})( typeof window !== 'undefined' ? window : this,\n\n// --------------------------  factory -------------------------- //\n\nfunction factory( window, EvEmitter ) {\n\n'use strict';\n\nvar $ = window.jQuery;\nvar console = window.console;\n\n// -------------------------- helpers -------------------------- //\n\n// extend objects\nfunction extend( a, b ) {\n  for ( var prop in b ) {\n    a[ prop ] = b[ prop ];\n  }\n  return a;\n}\n\nvar arraySlice = Array.prototype.slice;\n\n// turn element or nodeList into an array\nfunction makeArray( obj ) {\n  if ( Array.isArray( obj ) ) {\n    // use object if already an array\n    return obj;\n  }\n\n  var isArrayLike = typeof obj == 'object' && typeof obj.length == 'number';\n  if ( isArrayLike ) {\n    // convert nodeList to array\n    return arraySlice.call( obj );\n  }\n\n  // array of single index\n  return [ obj ];\n}\n\n// -------------------------- imagesLoaded -------------------------- //\n\n/**\n * @param {Array, Element, NodeList, String} elem\n * @param {Object or Function} options - if function, use as callback\n * @param {Function} onAlways - callback function\n */\nfunction ImagesLoaded( elem, options, onAlways ) {\n  // coerce ImagesLoaded() without new, to be new ImagesLoaded()\n  if ( !( this instanceof ImagesLoaded ) ) {\n    return new ImagesLoaded( elem, options, onAlways );\n  }\n  // use elem as selector string\n  var queryElem = elem;\n  if ( typeof elem == 'string' ) {\n    queryElem = document.querySelectorAll( elem );\n  }\n  // bail if bad element\n  if ( !queryElem ) {\n    console.error( 'Bad element for imagesLoaded ' + ( queryElem || elem ) );\n    return;\n  }\n\n  this.elements = makeArray( queryElem );\n  this.options = extend( {}, this.options );\n  // shift arguments if no options set\n  if ( typeof options == 'function' ) {\n    onAlways = options;\n  } else {\n    extend( this.options, options );\n  }\n\n  if ( onAlways ) {\n    this.on( 'always', onAlways );\n  }\n\n  this.getImages();\n\n  if ( $ ) {\n    // add jQuery Deferred object\n    this.jqDeferred = new $.Deferred();\n  }\n\n  // HACK check async to allow time to bind listeners\n  setTimeout( this.check.bind( this ) );\n}\n\nImagesLoaded.prototype = Object.create( EvEmitter.prototype );\n\nImagesLoaded.prototype.options = {};\n\nImagesLoaded.prototype.getImages = function() {\n  this.images = [];\n\n  // filter & find items if we have an item selector\n  this.elements.forEach( this.addElementImages, this );\n};\n\n/**\n * @param {Node} element\n */\nImagesLoaded.prototype.addElementImages = function( elem ) {\n  // filter siblings\n  if ( elem.nodeName == 'IMG' ) {\n    this.addImage( elem );\n  }\n  // get background image on element\n  if ( this.options.background === true ) {\n    this.addElementBackgroundImages( elem );\n  }\n\n  // find children\n  // no non-element nodes, #143\n  var nodeType = elem.nodeType;\n  if ( !nodeType || !elementNodeTypes[ nodeType ] ) {\n    return;\n  }\n  var childImgs = elem.querySelectorAll('img');\n  // concat childElems to filterFound array\n  for ( var i=0; i < childImgs.length; i++ ) {\n    var img = childImgs[i];\n    this.addImage( img );\n  }\n\n  // get child background images\n  if ( typeof this.options.background == 'string' ) {\n    var children = elem.querySelectorAll( this.options.background );\n    for ( i=0; i < children.length; i++ ) {\n      var child = children[i];\n      this.addElementBackgroundImages( child );\n    }\n  }\n};\n\nvar elementNodeTypes = {\n  1: true,\n  9: true,\n  11: true\n};\n\nImagesLoaded.prototype.addElementBackgroundImages = function( elem ) {\n  var style = getComputedStyle( elem );\n  if ( !style ) {\n    // Firefox returns null if in a hidden iframe https://bugzil.la/548397\n    return;\n  }\n  // get url inside url(\"...\")\n  var reURL = /url\\((['\"])?(.*?)\\1\\)/gi;\n  var matches = reURL.exec( style.backgroundImage );\n  while ( matches !== null ) {\n    var url = matches && matches[2];\n    if ( url ) {\n      this.addBackground( url, elem );\n    }\n    matches = reURL.exec( style.backgroundImage );\n  }\n};\n\n/**\n * @param {Image} img\n */\nImagesLoaded.prototype.addImage = function( img ) {\n  var loadingImage = new LoadingImage( img );\n  this.images.push( loadingImage );\n};\n\nImagesLoaded.prototype.addBackground = function( url, elem ) {\n  var background = new Background( url, elem );\n  this.images.push( background );\n};\n\nImagesLoaded.prototype.check = function() {\n  var _this = this;\n  this.progressedCount = 0;\n  this.hasAnyBroken = false;\n  // complete if no images\n  if ( !this.images.length ) {\n    this.complete();\n    return;\n  }\n\n  function onProgress( image, elem, message ) {\n    // HACK - Chrome triggers event before object properties have changed. #83\n    setTimeout( function() {\n      _this.progress( image, elem, message );\n    });\n  }\n\n  this.images.forEach( function( loadingImage ) {\n    loadingImage.once( 'progress', onProgress );\n    loadingImage.check();\n  });\n};\n\nImagesLoaded.prototype.progress = function( image, elem, message ) {\n  this.progressedCount++;\n  this.hasAnyBroken = this.hasAnyBroken || !image.isLoaded;\n  // progress event\n  this.emitEvent( 'progress', [ this, image, elem ] );\n  if ( this.jqDeferred && this.jqDeferred.notify ) {\n    this.jqDeferred.notify( this, image );\n  }\n  // check if completed\n  if ( this.progressedCount == this.images.length ) {\n    this.complete();\n  }\n\n  if ( this.options.debug && console ) {\n    console.log( 'progress: ' + message, image, elem );\n  }\n};\n\nImagesLoaded.prototype.complete = function() {\n  var eventName = this.hasAnyBroken ? 'fail' : 'done';\n  this.isComplete = true;\n  this.emitEvent( eventName, [ this ] );\n  this.emitEvent( 'always', [ this ] );\n  if ( this.jqDeferred ) {\n    var jqMethod = this.hasAnyBroken ? 'reject' : 'resolve';\n    this.jqDeferred[ jqMethod ]( this );\n  }\n};\n\n// --------------------------  -------------------------- //\n\nfunction LoadingImage( img ) {\n  this.img = img;\n}\n\nLoadingImage.prototype = Object.create( EvEmitter.prototype );\n\nLoadingImage.prototype.check = function() {\n  // If complete is true and browser supports natural sizes,\n  // try to check for image status manually.\n  var isComplete = this.getIsImageComplete();\n  if ( isComplete ) {\n    // report based on naturalWidth\n    this.confirm( this.img.naturalWidth !== 0, 'naturalWidth' );\n    return;\n  }\n\n  // If none of the checks above matched, simulate loading on detached element.\n  this.proxyImage = new Image();\n  this.proxyImage.addEventListener( 'load', this );\n  this.proxyImage.addEventListener( 'error', this );\n  // bind to image as well for Firefox. #191\n  this.img.addEventListener( 'load', this );\n  this.img.addEventListener( 'error', this );\n  this.proxyImage.src = this.img.src;\n};\n\nLoadingImage.prototype.getIsImageComplete = function() {\n  // check for non-zero, non-undefined naturalWidth\n  // fixes Safari+InfiniteScroll+Masonry bug infinite-scroll#671\n  return this.img.complete && this.img.naturalWidth;\n};\n\nLoadingImage.prototype.confirm = function( isLoaded, message ) {\n  this.isLoaded = isLoaded;\n  this.emitEvent( 'progress', [ this, this.img, message ] );\n};\n\n// ----- events ----- //\n\n// trigger specified handler for event type\nLoadingImage.prototype.handleEvent = function( event ) {\n  var method = 'on' + event.type;\n  if ( this[ method ] ) {\n    this[ method ]( event );\n  }\n};\n\nLoadingImage.prototype.onload = function() {\n  this.confirm( true, 'onload' );\n  this.unbindEvents();\n};\n\nLoadingImage.prototype.onerror = function() {\n  this.confirm( false, 'onerror' );\n  this.unbindEvents();\n};\n\nLoadingImage.prototype.unbindEvents = function() {\n  this.proxyImage.removeEventListener( 'load', this );\n  this.proxyImage.removeEventListener( 'error', this );\n  this.img.removeEventListener( 'load', this );\n  this.img.removeEventListener( 'error', this );\n};\n\n// -------------------------- Background -------------------------- //\n\nfunction Background( url, element ) {\n  this.url = url;\n  this.element = element;\n  this.img = new Image();\n}\n\n// inherit LoadingImage prototype\nBackground.prototype = Object.create( LoadingImage.prototype );\n\nBackground.prototype.check = function() {\n  this.img.addEventListener( 'load', this );\n  this.img.addEventListener( 'error', this );\n  this.img.src = this.url;\n  // check if image is already complete\n  var isComplete = this.getIsImageComplete();\n  if ( isComplete ) {\n    this.confirm( this.img.naturalWidth !== 0, 'naturalWidth' );\n    this.unbindEvents();\n  }\n};\n\nBackground.prototype.unbindEvents = function() {\n  this.img.removeEventListener( 'load', this );\n  this.img.removeEventListener( 'error', this );\n};\n\nBackground.prototype.confirm = function( isLoaded, message ) {\n  this.isLoaded = isLoaded;\n  this.emitEvent( 'progress', [ this, this.element, message ] );\n};\n\n// -------------------------- jQuery -------------------------- //\n\nImagesLoaded.makeJQueryPlugin = function( jQuery ) {\n  jQuery = jQuery || window.jQuery;\n  if ( !jQuery ) {\n    return;\n  }\n  // set local variable\n  $ = jQuery;\n  // $().imagesLoaded()\n  $.fn.imagesLoaded = function( options, callback ) {\n    var instance = new ImagesLoaded( this, options, callback );\n    return instance.jqDeferred.promise( $(this) );\n  };\n};\n// try making plugin\nImagesLoaded.makeJQueryPlugin();\n\n// --------------------------  -------------------------- //\n\nreturn ImagesLoaded;\n\n});\n\n\n//# sourceURL=webpack:///./node_modules/imagesloaded/imagesloaded.js?");
  
  /***/ }),
  
  /***/ "./node_modules/masonry-layout/masonry.js":
  /*!************************************************!*\
    !*** ./node_modules/masonry-layout/masonry.js ***!
    \************************************************/
  /*! no static exports found */
  /***/ (function(module, exports, __webpack_require__) {
  
  eval("var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/*!\n * Masonry v4.2.2\n * Cascading grid layout library\n * https://masonry.desandro.com\n * MIT License\n * by David DeSandro\n */\n\n( function( window, factory ) {\n  // universal module definition\n  /* jshint strict: false */ /*globals define, module, require */\n  if ( true ) {\n    // AMD\n    !(__WEBPACK_AMD_DEFINE_ARRAY__ = [\n        __webpack_require__(/*! outlayer/outlayer */ \"./node_modules/outlayer/outlayer.js\"),\n        __webpack_require__(/*! get-size/get-size */ \"./node_modules/get-size/get-size.js\")\n      ], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),\n\t\t\t\t__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?\n\t\t\t\t(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),\n\t\t\t\t__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));\n  } else {}\n\n}( window, function factory( Outlayer, getSize ) {\n\n'use strict';\n\n// -------------------------- masonryDefinition -------------------------- //\n\n  // create an Outlayer layout class\n  var Masonry = Outlayer.create('masonry');\n  // isFitWidth -> fitWidth\n  Masonry.compatOptions.fitWidth = 'isFitWidth';\n\n  var proto = Masonry.prototype;\n\n  proto._resetLayout = function() {\n    this.getSize();\n    this._getMeasurement( 'columnWidth', 'outerWidth' );\n    this._getMeasurement( 'gutter', 'outerWidth' );\n    this.measureColumns();\n\n    // reset column Y\n    this.colYs = [];\n    for ( var i=0; i < this.cols; i++ ) {\n      this.colYs.push( 0 );\n    }\n\n    this.maxY = 0;\n    this.horizontalColIndex = 0;\n  };\n\n  proto.measureColumns = function() {\n    this.getContainerWidth();\n    // if columnWidth is 0, default to outerWidth of first item\n    if ( !this.columnWidth ) {\n      var firstItem = this.items[0];\n      var firstItemElem = firstItem && firstItem.element;\n      // columnWidth fall back to item of first element\n      this.columnWidth = firstItemElem && getSize( firstItemElem ).outerWidth ||\n        // if first elem has no width, default to size of container\n        this.containerWidth;\n    }\n\n    var columnWidth = this.columnWidth += this.gutter;\n\n    // calculate columns\n    var containerWidth = this.containerWidth + this.gutter;\n    var cols = containerWidth / columnWidth;\n    // fix rounding errors, typically with gutters\n    var excess = columnWidth - containerWidth % columnWidth;\n    // if overshoot is less than a pixel, round up, otherwise floor it\n    var mathMethod = excess && excess < 1 ? 'round' : 'floor';\n    cols = Math[ mathMethod ]( cols );\n    this.cols = Math.max( cols, 1 );\n  };\n\n  proto.getContainerWidth = function() {\n    // container is parent if fit width\n    var isFitWidth = this._getOption('fitWidth');\n    var container = isFitWidth ? this.element.parentNode : this.element;\n    // check that this.size and size are there\n    // IE8 triggers resize on body size change, so they might not be\n    var size = getSize( container );\n    this.containerWidth = size && size.innerWidth;\n  };\n\n  proto._getItemLayoutPosition = function( item ) {\n    item.getSize();\n    // how many columns does this brick span\n    var remainder = item.size.outerWidth % this.columnWidth;\n    var mathMethod = remainder && remainder < 1 ? 'round' : 'ceil';\n    // round if off by 1 pixel, otherwise use ceil\n    var colSpan = Math[ mathMethod ]( item.size.outerWidth / this.columnWidth );\n    colSpan = Math.min( colSpan, this.cols );\n    // use horizontal or top column position\n    var colPosMethod = this.options.horizontalOrder ?\n      '_getHorizontalColPosition' : '_getTopColPosition';\n    var colPosition = this[ colPosMethod ]( colSpan, item );\n    // position the brick\n    var position = {\n      x: this.columnWidth * colPosition.col,\n      y: colPosition.y\n    };\n    // apply setHeight to necessary columns\n    var setHeight = colPosition.y + item.size.outerHeight;\n    var setMax = colSpan + colPosition.col;\n    for ( var i = colPosition.col; i < setMax; i++ ) {\n      this.colYs[i] = setHeight;\n    }\n\n    return position;\n  };\n\n  proto._getTopColPosition = function( colSpan ) {\n    var colGroup = this._getTopColGroup( colSpan );\n    // get the minimum Y value from the columns\n    var minimumY = Math.min.apply( Math, colGroup );\n\n    return {\n      col: colGroup.indexOf( minimumY ),\n      y: minimumY,\n    };\n  };\n\n  /**\n   * @param {Number} colSpan - number of columns the element spans\n   * @returns {Array} colGroup\n   */\n  proto._getTopColGroup = function( colSpan ) {\n    if ( colSpan < 2 ) {\n      // if brick spans only one column, use all the column Ys\n      return this.colYs;\n    }\n\n    var colGroup = [];\n    // how many different places could this brick fit horizontally\n    var groupCount = this.cols + 1 - colSpan;\n    // for each group potential horizontal position\n    for ( var i = 0; i < groupCount; i++ ) {\n      colGroup[i] = this._getColGroupY( i, colSpan );\n    }\n    return colGroup;\n  };\n\n  proto._getColGroupY = function( col, colSpan ) {\n    if ( colSpan < 2 ) {\n      return this.colYs[ col ];\n    }\n    // make an array of colY values for that one group\n    var groupColYs = this.colYs.slice( col, col + colSpan );\n    // and get the max value of the array\n    return Math.max.apply( Math, groupColYs );\n  };\n\n  // get column position based on horizontal index. #873\n  proto._getHorizontalColPosition = function( colSpan, item ) {\n    var col = this.horizontalColIndex % this.cols;\n    var isOver = colSpan > 1 && col + colSpan > this.cols;\n    // shift to next row if item can't fit on current row\n    col = isOver ? 0 : col;\n    // don't let zero-size items take up space\n    var hasSize = item.size.outerWidth && item.size.outerHeight;\n    this.horizontalColIndex = hasSize ? col + colSpan : this.horizontalColIndex;\n\n    return {\n      col: col,\n      y: this._getColGroupY( col, colSpan ),\n    };\n  };\n\n  proto._manageStamp = function( stamp ) {\n    var stampSize = getSize( stamp );\n    var offset = this._getElementOffset( stamp );\n    // get the columns that this stamp affects\n    var isOriginLeft = this._getOption('originLeft');\n    var firstX = isOriginLeft ? offset.left : offset.right;\n    var lastX = firstX + stampSize.outerWidth;\n    var firstCol = Math.floor( firstX / this.columnWidth );\n    firstCol = Math.max( 0, firstCol );\n    var lastCol = Math.floor( lastX / this.columnWidth );\n    // lastCol should not go over if multiple of columnWidth #425\n    lastCol -= lastX % this.columnWidth ? 0 : 1;\n    lastCol = Math.min( this.cols - 1, lastCol );\n    // set colYs to bottom of the stamp\n\n    var isOriginTop = this._getOption('originTop');\n    var stampMaxY = ( isOriginTop ? offset.top : offset.bottom ) +\n      stampSize.outerHeight;\n    for ( var i = firstCol; i <= lastCol; i++ ) {\n      this.colYs[i] = Math.max( stampMaxY, this.colYs[i] );\n    }\n  };\n\n  proto._getContainerSize = function() {\n    this.maxY = Math.max.apply( Math, this.colYs );\n    var size = {\n      height: this.maxY\n    };\n\n    if ( this._getOption('fitWidth') ) {\n      size.width = this._getContainerFitWidth();\n    }\n\n    return size;\n  };\n\n  proto._getContainerFitWidth = function() {\n    var unusedCols = 0;\n    // count unused columns\n    var i = this.cols;\n    while ( --i ) {\n      if ( this.colYs[i] !== 0 ) {\n        break;\n      }\n      unusedCols++;\n    }\n    // fit container to columns that have been used\n    return ( this.cols - unusedCols ) * this.columnWidth - this.gutter;\n  };\n\n  proto.needsResizeLayout = function() {\n    var previousWidth = this.containerWidth;\n    this.getContainerWidth();\n    return previousWidth != this.containerWidth;\n  };\n\n  return Masonry;\n\n}));\n\n\n//# sourceURL=webpack:///./node_modules/masonry-layout/masonry.js?");
  
  /***/ }),
  
  /***/ "./node_modules/outlayer/item.js":
  /*!***************************************!*\
    !*** ./node_modules/outlayer/item.js ***!
    \***************************************/
  /*! no static exports found */
  /***/ (function(module, exports, __webpack_require__) {
  
  eval("var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/**\n * Outlayer Item\n */\n\n( function( window, factory ) {\n  // universal module definition\n  /* jshint strict: false */ /* globals define, module, require */\n  if ( true ) {\n    // AMD - RequireJS\n    !(__WEBPACK_AMD_DEFINE_ARRAY__ = [\n        __webpack_require__(/*! ev-emitter/ev-emitter */ \"./node_modules/ev-emitter/ev-emitter.js\"),\n        __webpack_require__(/*! get-size/get-size */ \"./node_modules/get-size/get-size.js\")\n      ], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),\n\t\t\t\t__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?\n\t\t\t\t(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),\n\t\t\t\t__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));\n  } else {}\n\n}( window, function factory( EvEmitter, getSize ) {\n'use strict';\n\n// ----- helpers ----- //\n\nfunction isEmptyObj( obj ) {\n  for ( var prop in obj ) {\n    return false;\n  }\n  prop = null;\n  return true;\n}\n\n// -------------------------- CSS3 support -------------------------- //\n\n\nvar docElemStyle = document.documentElement.style;\n\nvar transitionProperty = typeof docElemStyle.transition == 'string' ?\n  'transition' : 'WebkitTransition';\nvar transformProperty = typeof docElemStyle.transform == 'string' ?\n  'transform' : 'WebkitTransform';\n\nvar transitionEndEvent = {\n  WebkitTransition: 'webkitTransitionEnd',\n  transition: 'transitionend'\n}[ transitionProperty ];\n\n// cache all vendor properties that could have vendor prefix\nvar vendorProperties = {\n  transform: transformProperty,\n  transition: transitionProperty,\n  transitionDuration: transitionProperty + 'Duration',\n  transitionProperty: transitionProperty + 'Property',\n  transitionDelay: transitionProperty + 'Delay'\n};\n\n// -------------------------- Item -------------------------- //\n\nfunction Item( element, layout ) {\n  if ( !element ) {\n    return;\n  }\n\n  this.element = element;\n  // parent layout class, i.e. Masonry, Isotope, or Packery\n  this.layout = layout;\n  this.position = {\n    x: 0,\n    y: 0\n  };\n\n  this._create();\n}\n\n// inherit EvEmitter\nvar proto = Item.prototype = Object.create( EvEmitter.prototype );\nproto.constructor = Item;\n\nproto._create = function() {\n  // transition objects\n  this._transn = {\n    ingProperties: {},\n    clean: {},\n    onEnd: {}\n  };\n\n  this.css({\n    position: 'absolute'\n  });\n};\n\n// trigger specified handler for event type\nproto.handleEvent = function( event ) {\n  var method = 'on' + event.type;\n  if ( this[ method ] ) {\n    this[ method ]( event );\n  }\n};\n\nproto.getSize = function() {\n  this.size = getSize( this.element );\n};\n\n/**\n * apply CSS styles to element\n * @param {Object} style\n */\nproto.css = function( style ) {\n  var elemStyle = this.element.style;\n\n  for ( var prop in style ) {\n    // use vendor property if available\n    var supportedProp = vendorProperties[ prop ] || prop;\n    elemStyle[ supportedProp ] = style[ prop ];\n  }\n};\n\n // measure position, and sets it\nproto.getPosition = function() {\n  var style = getComputedStyle( this.element );\n  var isOriginLeft = this.layout._getOption('originLeft');\n  var isOriginTop = this.layout._getOption('originTop');\n  var xValue = style[ isOriginLeft ? 'left' : 'right' ];\n  var yValue = style[ isOriginTop ? 'top' : 'bottom' ];\n  var x = parseFloat( xValue );\n  var y = parseFloat( yValue );\n  // convert percent to pixels\n  var layoutSize = this.layout.size;\n  if ( xValue.indexOf('%') != -1 ) {\n    x = ( x / 100 ) * layoutSize.width;\n  }\n  if ( yValue.indexOf('%') != -1 ) {\n    y = ( y / 100 ) * layoutSize.height;\n  }\n  // clean up 'auto' or other non-integer values\n  x = isNaN( x ) ? 0 : x;\n  y = isNaN( y ) ? 0 : y;\n  // remove padding from measurement\n  x -= isOriginLeft ? layoutSize.paddingLeft : layoutSize.paddingRight;\n  y -= isOriginTop ? layoutSize.paddingTop : layoutSize.paddingBottom;\n\n  this.position.x = x;\n  this.position.y = y;\n};\n\n// set settled position, apply padding\nproto.layoutPosition = function() {\n  var layoutSize = this.layout.size;\n  var style = {};\n  var isOriginLeft = this.layout._getOption('originLeft');\n  var isOriginTop = this.layout._getOption('originTop');\n\n  // x\n  var xPadding = isOriginLeft ? 'paddingLeft' : 'paddingRight';\n  var xProperty = isOriginLeft ? 'left' : 'right';\n  var xResetProperty = isOriginLeft ? 'right' : 'left';\n\n  var x = this.position.x + layoutSize[ xPadding ];\n  // set in percentage or pixels\n  style[ xProperty ] = this.getXValue( x );\n  // reset other property\n  style[ xResetProperty ] = '';\n\n  // y\n  var yPadding = isOriginTop ? 'paddingTop' : 'paddingBottom';\n  var yProperty = isOriginTop ? 'top' : 'bottom';\n  var yResetProperty = isOriginTop ? 'bottom' : 'top';\n\n  var y = this.position.y + layoutSize[ yPadding ];\n  // set in percentage or pixels\n  style[ yProperty ] = this.getYValue( y );\n  // reset other property\n  style[ yResetProperty ] = '';\n\n  this.css( style );\n  this.emitEvent( 'layout', [ this ] );\n};\n\nproto.getXValue = function( x ) {\n  var isHorizontal = this.layout._getOption('horizontal');\n  return this.layout.options.percentPosition && !isHorizontal ?\n    ( ( x / this.layout.size.width ) * 100 ) + '%' : x + 'px';\n};\n\nproto.getYValue = function( y ) {\n  var isHorizontal = this.layout._getOption('horizontal');\n  return this.layout.options.percentPosition && isHorizontal ?\n    ( ( y / this.layout.size.height ) * 100 ) + '%' : y + 'px';\n};\n\nproto._transitionTo = function( x, y ) {\n  this.getPosition();\n  // get current x & y from top/left\n  var curX = this.position.x;\n  var curY = this.position.y;\n\n  var didNotMove = x == this.position.x && y == this.position.y;\n\n  // save end position\n  this.setPosition( x, y );\n\n  // if did not move and not transitioning, just go to layout\n  if ( didNotMove && !this.isTransitioning ) {\n    this.layoutPosition();\n    return;\n  }\n\n  var transX = x - curX;\n  var transY = y - curY;\n  var transitionStyle = {};\n  transitionStyle.transform = this.getTranslate( transX, transY );\n\n  this.transition({\n    to: transitionStyle,\n    onTransitionEnd: {\n      transform: this.layoutPosition\n    },\n    isCleaning: true\n  });\n};\n\nproto.getTranslate = function( x, y ) {\n  // flip cooridinates if origin on right or bottom\n  var isOriginLeft = this.layout._getOption('originLeft');\n  var isOriginTop = this.layout._getOption('originTop');\n  x = isOriginLeft ? x : -x;\n  y = isOriginTop ? y : -y;\n  return 'translate3d(' + x + 'px, ' + y + 'px, 0)';\n};\n\n// non transition + transform support\nproto.goTo = function( x, y ) {\n  this.setPosition( x, y );\n  this.layoutPosition();\n};\n\nproto.moveTo = proto._transitionTo;\n\nproto.setPosition = function( x, y ) {\n  this.position.x = parseFloat( x );\n  this.position.y = parseFloat( y );\n};\n\n// ----- transition ----- //\n\n/**\n * @param {Object} style - CSS\n * @param {Function} onTransitionEnd\n */\n\n// non transition, just trigger callback\nproto._nonTransition = function( args ) {\n  this.css( args.to );\n  if ( args.isCleaning ) {\n    this._removeStyles( args.to );\n  }\n  for ( var prop in args.onTransitionEnd ) {\n    args.onTransitionEnd[ prop ].call( this );\n  }\n};\n\n/**\n * proper transition\n * @param {Object} args - arguments\n *   @param {Object} to - style to transition to\n *   @param {Object} from - style to start transition from\n *   @param {Boolean} isCleaning - removes transition styles after transition\n *   @param {Function} onTransitionEnd - callback\n */\nproto.transition = function( args ) {\n  // redirect to nonTransition if no transition duration\n  if ( !parseFloat( this.layout.options.transitionDuration ) ) {\n    this._nonTransition( args );\n    return;\n  }\n\n  var _transition = this._transn;\n  // keep track of onTransitionEnd callback by css property\n  for ( var prop in args.onTransitionEnd ) {\n    _transition.onEnd[ prop ] = args.onTransitionEnd[ prop ];\n  }\n  // keep track of properties that are transitioning\n  for ( prop in args.to ) {\n    _transition.ingProperties[ prop ] = true;\n    // keep track of properties to clean up when transition is done\n    if ( args.isCleaning ) {\n      _transition.clean[ prop ] = true;\n    }\n  }\n\n  // set from styles\n  if ( args.from ) {\n    this.css( args.from );\n    // force redraw. http://blog.alexmaccaw.com/css-transitions\n    var h = this.element.offsetHeight;\n    // hack for JSHint to hush about unused var\n    h = null;\n  }\n  // enable transition\n  this.enableTransition( args.to );\n  // set styles that are transitioning\n  this.css( args.to );\n\n  this.isTransitioning = true;\n\n};\n\n// dash before all cap letters, including first for\n// WebkitTransform => -webkit-transform\nfunction toDashedAll( str ) {\n  return str.replace( /([A-Z])/g, function( $1 ) {\n    return '-' + $1.toLowerCase();\n  });\n}\n\nvar transitionProps = 'opacity,' + toDashedAll( transformProperty );\n\nproto.enableTransition = function(/* style */) {\n  // HACK changing transitionProperty during a transition\n  // will cause transition to jump\n  if ( this.isTransitioning ) {\n    return;\n  }\n\n  // make `transition: foo, bar, baz` from style object\n  // HACK un-comment this when enableTransition can work\n  // while a transition is happening\n  // var transitionValues = [];\n  // for ( var prop in style ) {\n  //   // dash-ify camelCased properties like WebkitTransition\n  //   prop = vendorProperties[ prop ] || prop;\n  //   transitionValues.push( toDashedAll( prop ) );\n  // }\n  // munge number to millisecond, to match stagger\n  var duration = this.layout.options.transitionDuration;\n  duration = typeof duration == 'number' ? duration + 'ms' : duration;\n  // enable transition styles\n  this.css({\n    transitionProperty: transitionProps,\n    transitionDuration: duration,\n    transitionDelay: this.staggerDelay || 0\n  });\n  // listen for transition end event\n  this.element.addEventListener( transitionEndEvent, this, false );\n};\n\n// ----- events ----- //\n\nproto.onwebkitTransitionEnd = function( event ) {\n  this.ontransitionend( event );\n};\n\nproto.onotransitionend = function( event ) {\n  this.ontransitionend( event );\n};\n\n// properties that I munge to make my life easier\nvar dashedVendorProperties = {\n  '-webkit-transform': 'transform'\n};\n\nproto.ontransitionend = function( event ) {\n  // disregard bubbled events from children\n  if ( event.target !== this.element ) {\n    return;\n  }\n  var _transition = this._transn;\n  // get property name of transitioned property, convert to prefix-free\n  var propertyName = dashedVendorProperties[ event.propertyName ] || event.propertyName;\n\n  // remove property that has completed transitioning\n  delete _transition.ingProperties[ propertyName ];\n  // check if any properties are still transitioning\n  if ( isEmptyObj( _transition.ingProperties ) ) {\n    // all properties have completed transitioning\n    this.disableTransition();\n  }\n  // clean style\n  if ( propertyName in _transition.clean ) {\n    // clean up style\n    this.element.style[ event.propertyName ] = '';\n    delete _transition.clean[ propertyName ];\n  }\n  // trigger onTransitionEnd callback\n  if ( propertyName in _transition.onEnd ) {\n    var onTransitionEnd = _transition.onEnd[ propertyName ];\n    onTransitionEnd.call( this );\n    delete _transition.onEnd[ propertyName ];\n  }\n\n  this.emitEvent( 'transitionEnd', [ this ] );\n};\n\nproto.disableTransition = function() {\n  this.removeTransitionStyles();\n  this.element.removeEventListener( transitionEndEvent, this, false );\n  this.isTransitioning = false;\n};\n\n/**\n * removes style property from element\n * @param {Object} style\n**/\nproto._removeStyles = function( style ) {\n  // clean up transition styles\n  var cleanStyle = {};\n  for ( var prop in style ) {\n    cleanStyle[ prop ] = '';\n  }\n  this.css( cleanStyle );\n};\n\nvar cleanTransitionStyle = {\n  transitionProperty: '',\n  transitionDuration: '',\n  transitionDelay: ''\n};\n\nproto.removeTransitionStyles = function() {\n  // remove transition\n  this.css( cleanTransitionStyle );\n};\n\n// ----- stagger ----- //\n\nproto.stagger = function( delay ) {\n  delay = isNaN( delay ) ? 0 : delay;\n  this.staggerDelay = delay + 'ms';\n};\n\n// ----- show/hide/remove ----- //\n\n// remove element from DOM\nproto.removeElem = function() {\n  this.element.parentNode.removeChild( this.element );\n  // remove display: none\n  this.css({ display: '' });\n  this.emitEvent( 'remove', [ this ] );\n};\n\nproto.remove = function() {\n  // just remove element if no transition support or no transition\n  if ( !transitionProperty || !parseFloat( this.layout.options.transitionDuration ) ) {\n    this.removeElem();\n    return;\n  }\n\n  // start transition\n  this.once( 'transitionEnd', function() {\n    this.removeElem();\n  });\n  this.hide();\n};\n\nproto.reveal = function() {\n  delete this.isHidden;\n  // remove display: none\n  this.css({ display: '' });\n\n  var options = this.layout.options;\n\n  var onTransitionEnd = {};\n  var transitionEndProperty = this.getHideRevealTransitionEndProperty('visibleStyle');\n  onTransitionEnd[ transitionEndProperty ] = this.onRevealTransitionEnd;\n\n  this.transition({\n    from: options.hiddenStyle,\n    to: options.visibleStyle,\n    isCleaning: true,\n    onTransitionEnd: onTransitionEnd\n  });\n};\n\nproto.onRevealTransitionEnd = function() {\n  // check if still visible\n  // during transition, item may have been hidden\n  if ( !this.isHidden ) {\n    this.emitEvent('reveal');\n  }\n};\n\n/**\n * get style property use for hide/reveal transition end\n * @param {String} styleProperty - hiddenStyle/visibleStyle\n * @returns {String}\n */\nproto.getHideRevealTransitionEndProperty = function( styleProperty ) {\n  var optionStyle = this.layout.options[ styleProperty ];\n  // use opacity\n  if ( optionStyle.opacity ) {\n    return 'opacity';\n  }\n  // get first property\n  for ( var prop in optionStyle ) {\n    return prop;\n  }\n};\n\nproto.hide = function() {\n  // set flag\n  this.isHidden = true;\n  // remove display: none\n  this.css({ display: '' });\n\n  var options = this.layout.options;\n\n  var onTransitionEnd = {};\n  var transitionEndProperty = this.getHideRevealTransitionEndProperty('hiddenStyle');\n  onTransitionEnd[ transitionEndProperty ] = this.onHideTransitionEnd;\n\n  this.transition({\n    from: options.visibleStyle,\n    to: options.hiddenStyle,\n    // keep hidden stuff hidden\n    isCleaning: true,\n    onTransitionEnd: onTransitionEnd\n  });\n};\n\nproto.onHideTransitionEnd = function() {\n  // check if still hidden\n  // during transition, item may have been un-hidden\n  if ( this.isHidden ) {\n    this.css({ display: 'none' });\n    this.emitEvent('hide');\n  }\n};\n\nproto.destroy = function() {\n  this.css({\n    position: '',\n    left: '',\n    right: '',\n    top: '',\n    bottom: '',\n    transition: '',\n    transform: ''\n  });\n};\n\nreturn Item;\n\n}));\n\n\n//# sourceURL=webpack:///./node_modules/outlayer/item.js?");
  
  /***/ }),
  
  /***/ "./node_modules/outlayer/outlayer.js":
  /*!*******************************************!*\
    !*** ./node_modules/outlayer/outlayer.js ***!
    \*******************************************/
  /*! no static exports found */
  /***/ (function(module, exports, __webpack_require__) {
  
  eval("var __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/*!\n * Outlayer v2.1.1\n * the brains and guts of a layout library\n * MIT license\n */\n\n( function( window, factory ) {\n  'use strict';\n  // universal module definition\n  /* jshint strict: false */ /* globals define, module, require */\n  if ( true ) {\n    // AMD - RequireJS\n    !(__WEBPACK_AMD_DEFINE_ARRAY__ = [\n        __webpack_require__(/*! ev-emitter/ev-emitter */ \"./node_modules/ev-emitter/ev-emitter.js\"),\n        __webpack_require__(/*! get-size/get-size */ \"./node_modules/get-size/get-size.js\"),\n        __webpack_require__(/*! fizzy-ui-utils/utils */ \"./node_modules/fizzy-ui-utils/utils.js\"),\n        __webpack_require__(/*! ./item */ \"./node_modules/outlayer/item.js\")\n      ], __WEBPACK_AMD_DEFINE_RESULT__ = (function( EvEmitter, getSize, utils, Item ) {\n        return factory( window, EvEmitter, getSize, utils, Item);\n      }).apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__),\n\t\t\t\t__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));\n  } else {}\n\n}( window, function factory( window, EvEmitter, getSize, utils, Item ) {\n'use strict';\n\n// ----- vars ----- //\n\nvar console = window.console;\nvar jQuery = window.jQuery;\nvar noop = function() {};\n\n// -------------------------- Outlayer -------------------------- //\n\n// globally unique identifiers\nvar GUID = 0;\n// internal store of all Outlayer intances\nvar instances = {};\n\n\n/**\n * @param {Element, String} element\n * @param {Object} options\n * @constructor\n */\nfunction Outlayer( element, options ) {\n  var queryElement = utils.getQueryElement( element );\n  if ( !queryElement ) {\n    if ( console ) {\n      console.error( 'Bad element for ' + this.constructor.namespace +\n        ': ' + ( queryElement || element ) );\n    }\n    return;\n  }\n  this.element = queryElement;\n  // add jQuery\n  if ( jQuery ) {\n    this.$element = jQuery( this.element );\n  }\n\n  // options\n  this.options = utils.extend( {}, this.constructor.defaults );\n  this.option( options );\n\n  // add id for Outlayer.getFromElement\n  var id = ++GUID;\n  this.element.outlayerGUID = id; // expando\n  instances[ id ] = this; // associate via id\n\n  // kick it off\n  this._create();\n\n  var isInitLayout = this._getOption('initLayout');\n  if ( isInitLayout ) {\n    this.layout();\n  }\n}\n\n// settings are for internal use only\nOutlayer.namespace = 'outlayer';\nOutlayer.Item = Item;\n\n// default options\nOutlayer.defaults = {\n  containerStyle: {\n    position: 'relative'\n  },\n  initLayout: true,\n  originLeft: true,\n  originTop: true,\n  resize: true,\n  resizeContainer: true,\n  // item options\n  transitionDuration: '0.4s',\n  hiddenStyle: {\n    opacity: 0,\n    transform: 'scale(0.001)'\n  },\n  visibleStyle: {\n    opacity: 1,\n    transform: 'scale(1)'\n  }\n};\n\nvar proto = Outlayer.prototype;\n// inherit EvEmitter\nutils.extend( proto, EvEmitter.prototype );\n\n/**\n * set options\n * @param {Object} opts\n */\nproto.option = function( opts ) {\n  utils.extend( this.options, opts );\n};\n\n/**\n * get backwards compatible option value, check old name\n */\nproto._getOption = function( option ) {\n  var oldOption = this.constructor.compatOptions[ option ];\n  return oldOption && this.options[ oldOption ] !== undefined ?\n    this.options[ oldOption ] : this.options[ option ];\n};\n\nOutlayer.compatOptions = {\n  // currentName: oldName\n  initLayout: 'isInitLayout',\n  horizontal: 'isHorizontal',\n  layoutInstant: 'isLayoutInstant',\n  originLeft: 'isOriginLeft',\n  originTop: 'isOriginTop',\n  resize: 'isResizeBound',\n  resizeContainer: 'isResizingContainer'\n};\n\nproto._create = function() {\n  // get items from children\n  this.reloadItems();\n  // elements that affect layout, but are not laid out\n  this.stamps = [];\n  this.stamp( this.options.stamp );\n  // set container style\n  utils.extend( this.element.style, this.options.containerStyle );\n\n  // bind resize method\n  var canBindResize = this._getOption('resize');\n  if ( canBindResize ) {\n    this.bindResize();\n  }\n};\n\n// goes through all children again and gets bricks in proper order\nproto.reloadItems = function() {\n  // collection of item elements\n  this.items = this._itemize( this.element.children );\n};\n\n\n/**\n * turn elements into Outlayer.Items to be used in layout\n * @param {Array or NodeList or HTMLElement} elems\n * @returns {Array} items - collection of new Outlayer Items\n */\nproto._itemize = function( elems ) {\n\n  var itemElems = this._filterFindItemElements( elems );\n  var Item = this.constructor.Item;\n\n  // create new Outlayer Items for collection\n  var items = [];\n  for ( var i=0; i < itemElems.length; i++ ) {\n    var elem = itemElems[i];\n    var item = new Item( elem, this );\n    items.push( item );\n  }\n\n  return items;\n};\n\n/**\n * get item elements to be used in layout\n * @param {Array or NodeList or HTMLElement} elems\n * @returns {Array} items - item elements\n */\nproto._filterFindItemElements = function( elems ) {\n  return utils.filterFindElements( elems, this.options.itemSelector );\n};\n\n/**\n * getter method for getting item elements\n * @returns {Array} elems - collection of item elements\n */\nproto.getItemElements = function() {\n  return this.items.map( function( item ) {\n    return item.element;\n  });\n};\n\n// ----- init & layout ----- //\n\n/**\n * lays out all items\n */\nproto.layout = function() {\n  this._resetLayout();\n  this._manageStamps();\n\n  // don't animate first layout\n  var layoutInstant = this._getOption('layoutInstant');\n  var isInstant = layoutInstant !== undefined ?\n    layoutInstant : !this._isLayoutInited;\n  this.layoutItems( this.items, isInstant );\n\n  // flag for initalized\n  this._isLayoutInited = true;\n};\n\n// _init is alias for layout\nproto._init = proto.layout;\n\n/**\n * logic before any new layout\n */\nproto._resetLayout = function() {\n  this.getSize();\n};\n\n\nproto.getSize = function() {\n  this.size = getSize( this.element );\n};\n\n/**\n * get measurement from option, for columnWidth, rowHeight, gutter\n * if option is String -> get element from selector string, & get size of element\n * if option is Element -> get size of element\n * else use option as a number\n *\n * @param {String} measurement\n * @param {String} size - width or height\n * @private\n */\nproto._getMeasurement = function( measurement, size ) {\n  var option = this.options[ measurement ];\n  var elem;\n  if ( !option ) {\n    // default to 0\n    this[ measurement ] = 0;\n  } else {\n    // use option as an element\n    if ( typeof option == 'string' ) {\n      elem = this.element.querySelector( option );\n    } else if ( option instanceof HTMLElement ) {\n      elem = option;\n    }\n    // use size of element, if element\n    this[ measurement ] = elem ? getSize( elem )[ size ] : option;\n  }\n};\n\n/**\n * layout a collection of item elements\n * @api public\n */\nproto.layoutItems = function( items, isInstant ) {\n  items = this._getItemsForLayout( items );\n\n  this._layoutItems( items, isInstant );\n\n  this._postLayout();\n};\n\n/**\n * get the items to be laid out\n * you may want to skip over some items\n * @param {Array} items\n * @returns {Array} items\n */\nproto._getItemsForLayout = function( items ) {\n  return items.filter( function( item ) {\n    return !item.isIgnored;\n  });\n};\n\n/**\n * layout items\n * @param {Array} items\n * @param {Boolean} isInstant\n */\nproto._layoutItems = function( items, isInstant ) {\n  this._emitCompleteOnItems( 'layout', items );\n\n  if ( !items || !items.length ) {\n    // no items, emit event with empty array\n    return;\n  }\n\n  var queue = [];\n\n  items.forEach( function( item ) {\n    // get x/y object from method\n    var position = this._getItemLayoutPosition( item );\n    // enqueue\n    position.item = item;\n    position.isInstant = isInstant || item.isLayoutInstant;\n    queue.push( position );\n  }, this );\n\n  this._processLayoutQueue( queue );\n};\n\n/**\n * get item layout position\n * @param {Outlayer.Item} item\n * @returns {Object} x and y position\n */\nproto._getItemLayoutPosition = function( /* item */ ) {\n  return {\n    x: 0,\n    y: 0\n  };\n};\n\n/**\n * iterate over array and position each item\n * Reason being - separating this logic prevents 'layout invalidation'\n * thx @paul_irish\n * @param {Array} queue\n */\nproto._processLayoutQueue = function( queue ) {\n  this.updateStagger();\n  queue.forEach( function( obj, i ) {\n    this._positionItem( obj.item, obj.x, obj.y, obj.isInstant, i );\n  }, this );\n};\n\n// set stagger from option in milliseconds number\nproto.updateStagger = function() {\n  var stagger = this.options.stagger;\n  if ( stagger === null || stagger === undefined ) {\n    this.stagger = 0;\n    return;\n  }\n  this.stagger = getMilliseconds( stagger );\n  return this.stagger;\n};\n\n/**\n * Sets position of item in DOM\n * @param {Outlayer.Item} item\n * @param {Number} x - horizontal position\n * @param {Number} y - vertical position\n * @param {Boolean} isInstant - disables transitions\n */\nproto._positionItem = function( item, x, y, isInstant, i ) {\n  if ( isInstant ) {\n    // if not transition, just set CSS\n    item.goTo( x, y );\n  } else {\n    item.stagger( i * this.stagger );\n    item.moveTo( x, y );\n  }\n};\n\n/**\n * Any logic you want to do after each layout,\n * i.e. size the container\n */\nproto._postLayout = function() {\n  this.resizeContainer();\n};\n\nproto.resizeContainer = function() {\n  var isResizingContainer = this._getOption('resizeContainer');\n  if ( !isResizingContainer ) {\n    return;\n  }\n  var size = this._getContainerSize();\n  if ( size ) {\n    this._setContainerMeasure( size.width, true );\n    this._setContainerMeasure( size.height, false );\n  }\n};\n\n/**\n * Sets width or height of container if returned\n * @returns {Object} size\n *   @param {Number} width\n *   @param {Number} height\n */\nproto._getContainerSize = noop;\n\n/**\n * @param {Number} measure - size of width or height\n * @param {Boolean} isWidth\n */\nproto._setContainerMeasure = function( measure, isWidth ) {\n  if ( measure === undefined ) {\n    return;\n  }\n\n  var elemSize = this.size;\n  // add padding and border width if border box\n  if ( elemSize.isBorderBox ) {\n    measure += isWidth ? elemSize.paddingLeft + elemSize.paddingRight +\n      elemSize.borderLeftWidth + elemSize.borderRightWidth :\n      elemSize.paddingBottom + elemSize.paddingTop +\n      elemSize.borderTopWidth + elemSize.borderBottomWidth;\n  }\n\n  measure = Math.max( measure, 0 );\n  this.element.style[ isWidth ? 'width' : 'height' ] = measure + 'px';\n};\n\n/**\n * emit eventComplete on a collection of items events\n * @param {String} eventName\n * @param {Array} items - Outlayer.Items\n */\nproto._emitCompleteOnItems = function( eventName, items ) {\n  var _this = this;\n  function onComplete() {\n    _this.dispatchEvent( eventName + 'Complete', null, [ items ] );\n  }\n\n  var count = items.length;\n  if ( !items || !count ) {\n    onComplete();\n    return;\n  }\n\n  var doneCount = 0;\n  function tick() {\n    doneCount++;\n    if ( doneCount == count ) {\n      onComplete();\n    }\n  }\n\n  // bind callback\n  items.forEach( function( item ) {\n    item.once( eventName, tick );\n  });\n};\n\n/**\n * emits events via EvEmitter and jQuery events\n * @param {String} type - name of event\n * @param {Event} event - original event\n * @param {Array} args - extra arguments\n */\nproto.dispatchEvent = function( type, event, args ) {\n  // add original event to arguments\n  var emitArgs = event ? [ event ].concat( args ) : args;\n  this.emitEvent( type, emitArgs );\n\n  if ( jQuery ) {\n    // set this.$element\n    this.$element = this.$element || jQuery( this.element );\n    if ( event ) {\n      // create jQuery event\n      var $event = jQuery.Event( event );\n      $event.type = type;\n      this.$element.trigger( $event, args );\n    } else {\n      // just trigger with type if no event available\n      this.$element.trigger( type, args );\n    }\n  }\n};\n\n// -------------------------- ignore & stamps -------------------------- //\n\n\n/**\n * keep item in collection, but do not lay it out\n * ignored items do not get skipped in layout\n * @param {Element} elem\n */\nproto.ignore = function( elem ) {\n  var item = this.getItem( elem );\n  if ( item ) {\n    item.isIgnored = true;\n  }\n};\n\n/**\n * return item to layout collection\n * @param {Element} elem\n */\nproto.unignore = function( elem ) {\n  var item = this.getItem( elem );\n  if ( item ) {\n    delete item.isIgnored;\n  }\n};\n\n/**\n * adds elements to stamps\n * @param {NodeList, Array, Element, or String} elems\n */\nproto.stamp = function( elems ) {\n  elems = this._find( elems );\n  if ( !elems ) {\n    return;\n  }\n\n  this.stamps = this.stamps.concat( elems );\n  // ignore\n  elems.forEach( this.ignore, this );\n};\n\n/**\n * removes elements to stamps\n * @param {NodeList, Array, or Element} elems\n */\nproto.unstamp = function( elems ) {\n  elems = this._find( elems );\n  if ( !elems ){\n    return;\n  }\n\n  elems.forEach( function( elem ) {\n    // filter out removed stamp elements\n    utils.removeFrom( this.stamps, elem );\n    this.unignore( elem );\n  }, this );\n};\n\n/**\n * finds child elements\n * @param {NodeList, Array, Element, or String} elems\n * @returns {Array} elems\n */\nproto._find = function( elems ) {\n  if ( !elems ) {\n    return;\n  }\n  // if string, use argument as selector string\n  if ( typeof elems == 'string' ) {\n    elems = this.element.querySelectorAll( elems );\n  }\n  elems = utils.makeArray( elems );\n  return elems;\n};\n\nproto._manageStamps = function() {\n  if ( !this.stamps || !this.stamps.length ) {\n    return;\n  }\n\n  this._getBoundingRect();\n\n  this.stamps.forEach( this._manageStamp, this );\n};\n\n// update boundingLeft / Top\nproto._getBoundingRect = function() {\n  // get bounding rect for container element\n  var boundingRect = this.element.getBoundingClientRect();\n  var size = this.size;\n  this._boundingRect = {\n    left: boundingRect.left + size.paddingLeft + size.borderLeftWidth,\n    top: boundingRect.top + size.paddingTop + size.borderTopWidth,\n    right: boundingRect.right - ( size.paddingRight + size.borderRightWidth ),\n    bottom: boundingRect.bottom - ( size.paddingBottom + size.borderBottomWidth )\n  };\n};\n\n/**\n * @param {Element} stamp\n**/\nproto._manageStamp = noop;\n\n/**\n * get x/y position of element relative to container element\n * @param {Element} elem\n * @returns {Object} offset - has left, top, right, bottom\n */\nproto._getElementOffset = function( elem ) {\n  var boundingRect = elem.getBoundingClientRect();\n  var thisRect = this._boundingRect;\n  var size = getSize( elem );\n  var offset = {\n    left: boundingRect.left - thisRect.left - size.marginLeft,\n    top: boundingRect.top - thisRect.top - size.marginTop,\n    right: thisRect.right - boundingRect.right - size.marginRight,\n    bottom: thisRect.bottom - boundingRect.bottom - size.marginBottom\n  };\n  return offset;\n};\n\n// -------------------------- resize -------------------------- //\n\n// enable event handlers for listeners\n// i.e. resize -> onresize\nproto.handleEvent = utils.handleEvent;\n\n/**\n * Bind layout to window resizing\n */\nproto.bindResize = function() {\n  window.addEventListener( 'resize', this );\n  this.isResizeBound = true;\n};\n\n/**\n * Unbind layout to window resizing\n */\nproto.unbindResize = function() {\n  window.removeEventListener( 'resize', this );\n  this.isResizeBound = false;\n};\n\nproto.onresize = function() {\n  this.resize();\n};\n\nutils.debounceMethod( Outlayer, 'onresize', 100 );\n\nproto.resize = function() {\n  // don't trigger if size did not change\n  // or if resize was unbound. See #9\n  if ( !this.isResizeBound || !this.needsResizeLayout() ) {\n    return;\n  }\n\n  this.layout();\n};\n\n/**\n * check if layout is needed post layout\n * @returns Boolean\n */\nproto.needsResizeLayout = function() {\n  var size = getSize( this.element );\n  // check that this.size and size are there\n  // IE8 triggers resize on body size change, so they might not be\n  var hasSizes = this.size && size;\n  return hasSizes && size.innerWidth !== this.size.innerWidth;\n};\n\n// -------------------------- methods -------------------------- //\n\n/**\n * add items to Outlayer instance\n * @param {Array or NodeList or Element} elems\n * @returns {Array} items - Outlayer.Items\n**/\nproto.addItems = function( elems ) {\n  var items = this._itemize( elems );\n  // add items to collection\n  if ( items.length ) {\n    this.items = this.items.concat( items );\n  }\n  return items;\n};\n\n/**\n * Layout newly-appended item elements\n * @param {Array or NodeList or Element} elems\n */\nproto.appended = function( elems ) {\n  var items = this.addItems( elems );\n  if ( !items.length ) {\n    return;\n  }\n  // layout and reveal just the new items\n  this.layoutItems( items, true );\n  this.reveal( items );\n};\n\n/**\n * Layout prepended elements\n * @param {Array or NodeList or Element} elems\n */\nproto.prepended = function( elems ) {\n  var items = this._itemize( elems );\n  if ( !items.length ) {\n    return;\n  }\n  // add items to beginning of collection\n  var previousItems = this.items.slice(0);\n  this.items = items.concat( previousItems );\n  // start new layout\n  this._resetLayout();\n  this._manageStamps();\n  // layout new stuff without transition\n  this.layoutItems( items, true );\n  this.reveal( items );\n  // layout previous items\n  this.layoutItems( previousItems );\n};\n\n/**\n * reveal a collection of items\n * @param {Array of Outlayer.Items} items\n */\nproto.reveal = function( items ) {\n  this._emitCompleteOnItems( 'reveal', items );\n  if ( !items || !items.length ) {\n    return;\n  }\n  var stagger = this.updateStagger();\n  items.forEach( function( item, i ) {\n    item.stagger( i * stagger );\n    item.reveal();\n  });\n};\n\n/**\n * hide a collection of items\n * @param {Array of Outlayer.Items} items\n */\nproto.hide = function( items ) {\n  this._emitCompleteOnItems( 'hide', items );\n  if ( !items || !items.length ) {\n    return;\n  }\n  var stagger = this.updateStagger();\n  items.forEach( function( item, i ) {\n    item.stagger( i * stagger );\n    item.hide();\n  });\n};\n\n/**\n * reveal item elements\n * @param {Array}, {Element}, {NodeList} items\n */\nproto.revealItemElements = function( elems ) {\n  var items = this.getItems( elems );\n  this.reveal( items );\n};\n\n/**\n * hide item elements\n * @param {Array}, {Element}, {NodeList} items\n */\nproto.hideItemElements = function( elems ) {\n  var items = this.getItems( elems );\n  this.hide( items );\n};\n\n/**\n * get Outlayer.Item, given an Element\n * @param {Element} elem\n * @param {Function} callback\n * @returns {Outlayer.Item} item\n */\nproto.getItem = function( elem ) {\n  // loop through items to get the one that matches\n  for ( var i=0; i < this.items.length; i++ ) {\n    var item = this.items[i];\n    if ( item.element == elem ) {\n      // return item\n      return item;\n    }\n  }\n};\n\n/**\n * get collection of Outlayer.Items, given Elements\n * @param {Array} elems\n * @returns {Array} items - Outlayer.Items\n */\nproto.getItems = function( elems ) {\n  elems = utils.makeArray( elems );\n  var items = [];\n  elems.forEach( function( elem ) {\n    var item = this.getItem( elem );\n    if ( item ) {\n      items.push( item );\n    }\n  }, this );\n\n  return items;\n};\n\n/**\n * remove element(s) from instance and DOM\n * @param {Array or NodeList or Element} elems\n */\nproto.remove = function( elems ) {\n  var removeItems = this.getItems( elems );\n\n  this._emitCompleteOnItems( 'remove', removeItems );\n\n  // bail if no items to remove\n  if ( !removeItems || !removeItems.length ) {\n    return;\n  }\n\n  removeItems.forEach( function( item ) {\n    item.remove();\n    // remove item from collection\n    utils.removeFrom( this.items, item );\n  }, this );\n};\n\n// ----- destroy ----- //\n\n// remove and disable Outlayer instance\nproto.destroy = function() {\n  // clean up dynamic styles\n  var style = this.element.style;\n  style.height = '';\n  style.position = '';\n  style.width = '';\n  // destroy items\n  this.items.forEach( function( item ) {\n    item.destroy();\n  });\n\n  this.unbindResize();\n\n  var id = this.element.outlayerGUID;\n  delete instances[ id ]; // remove reference to instance by id\n  delete this.element.outlayerGUID;\n  // remove data for jQuery\n  if ( jQuery ) {\n    jQuery.removeData( this.element, this.constructor.namespace );\n  }\n\n};\n\n// -------------------------- data -------------------------- //\n\n/**\n * get Outlayer instance from element\n * @param {Element} elem\n * @returns {Outlayer}\n */\nOutlayer.data = function( elem ) {\n  elem = utils.getQueryElement( elem );\n  var id = elem && elem.outlayerGUID;\n  return id && instances[ id ];\n};\n\n\n// -------------------------- create Outlayer class -------------------------- //\n\n/**\n * create a layout class\n * @param {String} namespace\n */\nOutlayer.create = function( namespace, options ) {\n  // sub-class Outlayer\n  var Layout = subclass( Outlayer );\n  // apply new options and compatOptions\n  Layout.defaults = utils.extend( {}, Outlayer.defaults );\n  utils.extend( Layout.defaults, options );\n  Layout.compatOptions = utils.extend( {}, Outlayer.compatOptions  );\n\n  Layout.namespace = namespace;\n\n  Layout.data = Outlayer.data;\n\n  // sub-class Item\n  Layout.Item = subclass( Item );\n\n  // -------------------------- declarative -------------------------- //\n\n  utils.htmlInit( Layout, namespace );\n\n  // -------------------------- jQuery bridge -------------------------- //\n\n  // make into jQuery plugin\n  if ( jQuery && jQuery.bridget ) {\n    jQuery.bridget( namespace, Layout );\n  }\n\n  return Layout;\n};\n\nfunction subclass( Parent ) {\n  function SubClass() {\n    Parent.apply( this, arguments );\n  }\n\n  SubClass.prototype = Object.create( Parent.prototype );\n  SubClass.prototype.constructor = SubClass;\n\n  return SubClass;\n}\n\n// ----- helpers ----- //\n\n// how many milliseconds are in each unit\nvar msUnits = {\n  ms: 1,\n  s: 1000\n};\n\n// munge time-like parameter into millisecond number\n// '0.4s' -> 40\nfunction getMilliseconds( time ) {\n  if ( typeof time == 'number' ) {\n    return time;\n  }\n  var matches = time.match( /(^\\d*\\.?\\d*)(\\w*)/ );\n  var num = matches && matches[1];\n  var unit = matches && matches[2];\n  if ( !num.length ) {\n    return 0;\n  }\n  num = parseFloat( num );\n  var mult = msUnits[ unit ] || 1;\n  return num * mult;\n}\n\n// ----- fin ----- //\n\n// back in global\nOutlayer.Item = Item;\n\nreturn Outlayer;\n\n}));\n\n\n//# sourceURL=webpack:///./node_modules/outlayer/outlayer.js?");
  
  /***/ }),
  
  /***/ "./node_modules/overlayscrollbars/js/OverlayScrollbars.js":
  /*!****************************************************************!*\
    !*** ./node_modules/overlayscrollbars/js/OverlayScrollbars.js ***!
    \****************************************************************/
  /*! no static exports found */
  /***/ (function(module, exports, __webpack_require__) {
  
  eval("var __WEBPACK_AMD_DEFINE_RESULT__;/*!\n * OverlayScrollbars\n * https://github.com/KingSora/OverlayScrollbars\n *\n * Version: 1.8.0\n *\n * Copyright KingSora | Rene Haas.\n * https://github.com/KingSora\n *\n * Released under the MIT license.\n * Date: 08.07.2019\n */\n\n(function (global, factory) {\n    if (true)\n        !(__WEBPACK_AMD_DEFINE_RESULT__ = (function() { return factory(global, global.document, undefined); }).call(exports, __webpack_require__, exports, module),\n\t\t\t\t__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));\n    else {}\n}(typeof window !== 'undefined' ? window : this,\n    function(window, document, undefined) {\n        'use strict';\n        var PLUGINNAME = 'OverlayScrollbars';\n        var TYPES = {\n            o : 'object',\n            f : 'function',\n            a : 'array',\n            s : 'string',\n            b : 'boolean',\n            n : 'number',\n            u : 'undefined',\n            z : 'null'\n            //d : 'date',\n            //e : 'error',\n            //r : 'regexp',\n            //y : 'symbol'\n        };\n        var LEXICON = {\n            c : 'class',\n            s : 'style',\n            i : 'id',\n            l : 'length',\n            p : 'prototype',\n            oH : 'offsetHeight',\n            cH : 'clientHeight',\n            sH : 'scrollHeight',\n            oW : 'offsetWidth',\n            cW : 'clientWidth',\n            sW : 'scrollWidth',\n            hOP : 'hasOwnProperty'\n        };\n        var VENDORS = {\n            //https://developer.mozilla.org/en-US/docs/Glossary/Vendor_Prefix\n            _jsCache : { },\n            _cssCache : { },\n            _cssPrefixes : ['-webkit-', '-moz-', '-o-', '-ms-'],\n            _jsPrefixes : ['WebKit', 'Moz', 'O', 'MS'],\n            _cssProperty : function(name) {\n                var cache = this._cssCache;\n\n                if(cache[name])\n                    return cache[name];\n\n                var prefixes = this._cssPrefixes;\n                var uppercasedName = this._firstLetterToUpper(name);\n                var elmStyle = document.createElement('div')[LEXICON.s];\n                var resultPossibilities;\n                var i = 0;\n                var v = 0;\n                var currVendorWithoutDashes;\n\n                for (; i < prefixes.length; i++) {\n                    currVendorWithoutDashes = prefixes[i].replace(/-/g, '');\n                    resultPossibilities = [\n                        name, //transition\n                        prefixes[i] + name, //-webkit-transition\n                        currVendorWithoutDashes + uppercasedName, //webkitTransition\n                        this._firstLetterToUpper(currVendorWithoutDashes) + uppercasedName //WebkitTransition\n                    ];\n                    for(v = 0; v < resultPossibilities[LEXICON.l]; v++) {\n                        if(elmStyle[resultPossibilities[v]] !== undefined) {\n                            cache[name] = resultPossibilities[v];\n                            return resultPossibilities[v];\n                        }\n                    }\n                }\n\n                return null;\n            },\n            _jsAPI : function(name, isInterface, fallback) {\n                var prefixes = this._jsPrefixes;\n                var cache = this._jsCache;\n                var i = 0;\n                var result = cache[name];\n                if(!result) {\n                    result = window[name];\n                    for(; i < prefixes[LEXICON.l]; i++)\n                        result = result || window[(isInterface ? prefixes[i] : prefixes[i].toLowerCase()) + this._firstLetterToUpper(name)];\n                    cache[name] = result;\n                }\n                return result || fallback;\n            },\n            _firstLetterToUpper : function(str) {\n                return str.charAt(0).toUpperCase() + str.slice(1);\n            }\n        };\n        var COMPATIBILITY = {\n            /**\n             * Gets the current window width.\n             * @returns {Number|number} The current window width in pixel.\n             */\n            wW: function() {\n                return window.innerWidth || document.documentElement[LEXICON.cW] || document.body[LEXICON.cW];\n            },\n\n            /**\n             * Gets the current window height.\n             * @returns {Number|number} The current window height in pixel.\n             */\n            wH: function() {\n                return window.innerHeight || document.documentElement[LEXICON.cH] || document.body[LEXICON.cH];\n            },\n\n            /**\n             * Gets the MutationObserver Object or undefined if not supported.\n             * @returns {MutationObserver|*|undefined} The MutationsObserver Object or undefined.\n             */\n            mO: function() {\n                return VENDORS._jsAPI('MutationObserver', true);\n            },\n\n            /**\n             * Gets the ResizeObserver Object or undefined if not supported.\n             * @returns {MutationObserver|*|undefined} The ResizeObserver Object or undefined.\n             */\n            rO: function() {\n                return VENDORS._jsAPI('ResizeObserver', true);\n            },\n\n            /**\n             * Gets the RequestAnimationFrame method or it's corresponding polyfill.\n             * @returns {*|Function} The RequestAnimationFrame method or it's corresponding polyfill.\n             */\n            rAF: function() {\n                return VENDORS._jsAPI('requestAnimationFrame', false, function (func) { return window.setTimeout(func, 1000 / 60); });\n            },\n\n            /**\n             * Gets the CancelAnimationFrame method or it's corresponding polyfill.\n             * @returns {*|Function} The CancelAnimationFrame method or it's corresponding polyfill.\n             */\n            cAF: function() {\n                return VENDORS._jsAPI('cancelAnimationFrame', false, function (id) { return window.clearTimeout(id); });\n            },\n\n            /**\n             * Gets the current time.\n             * @returns {number} The current time.\n             */\n            now: function() {\n                return Date.now && Date.now() || new Date().getTime();\n            },\n\n            /**\n             * Stops the propagation of the given event.\n             * @param event The event of which the propagation shall be stoped.\n             */\n            stpP: function(event) {\n                if(event.stopPropagation)\n                    event.stopPropagation();\n                else\n                    event.cancelBubble = true;\n            },\n\n            /**\n             * Prevents the default action of the given event.\n             * @param event The event of which the default action shall be prevented.\n             */\n            prvD: function(event) {\n                if(event.preventDefault && event.cancelable)\n                    event.preventDefault();\n                else\n                    event.returnValue = false;\n            },\n\n            /**\n             * Gets the pageX and pageY values of the given mouse event.\n             * @param event The mouse event of which the pageX and pageX shall be got.\n             * @returns {{x: number, y: number}} x = pageX value, y = pageY value.\n             */\n            page: function(event) {\n                event = event.originalEvent || event;\n\n                var strPage = 'page';\n                var strClient = 'client';\n                var strX = 'X';\n                var strY = 'Y';\n                var target = event.target || event.srcElement || document;\n                var eventDoc = target.ownerDocument || document;\n                var doc = eventDoc.documentElement;\n                var body = eventDoc.body;\n\n                //if touch event return return pageX/Y of it\n                if(event.touches !== undefined) {\n                    var touch = event.touches[0];\n                    return {\n                        x : touch[strPage + strX],\n                        y : touch[strPage + strY]\n                    }\n                }\n\n                // Calculate pageX/Y if not native supported\n                if (!event[strPage + strX] && event[strClient + strX] && event[strClient + strX] != null) {\n\n                    return {\n                        x : event[strClient + strX] +\n                        (doc && doc.scrollLeft || body && body.scrollLeft || 0) -\n                        (doc && doc.clientLeft || body && body.clientLeft || 0),\n                        y : event[strClient + strY] +\n                        (doc && doc.scrollTop || body && body.scrollTop || 0) -\n                        (doc && doc.clientTop || body && body.clientTop || 0)\n                    }\n                }\n                return {\n                    x : event[strPage + strX],\n                    y : event[strPage + strY]\n                };\n            },\n\n            /**\n             * Gets the clicked mouse button of the given mouse event.\n             * @param event The mouse event of which the clicked button shal be got.\n             * @returns {number} The number of the clicked mouse button. (0 : none | 1 : leftButton | 2 : middleButton | 3 : rightButton)\n             */\n            mBtn: function(event) {\n                var button = event.button;\n                if (!event.which && button !== undefined)\n                    return (button & 1 ? 1 : (button & 2 ? 3 : (button & 4 ? 2 : 0)));\n                else\n                    return event.which;\n            },\n\n            /**\n             * Checks whether a item is in the given array and returns its index.\n             * @param item The item of which the position in the array shall be determined.\n             * @param arr The array.\n             * @returns {number} The zero based index of the item or -1 if the item isn't in the array.\n             */\n            inA : function(item, arr) {\n                for (var i = 0; i < arr[LEXICON.l]; i++)\n                    //Sometiems in IE a \"SCRIPT70\" Permission denied error occurs if HTML elements in a iFrame are compared\n                    try {\n                        if (arr[i] === item)\n                            return i;\n                    }\n                    catch(e) { }\n                return -1;\n            },\n\n            /**\n             * Returns true if the given value is a array.\n             * @param arr The potential array.\n             * @returns {boolean} True if the given value is a array, false otherwise.\n             */\n            isA: function(arr) {\n                var def = Array.isArray;\n                return def ? def(arr) : this.type(arr) == TYPES.a;\n            },\n\n            /**\n             * Determine the internal JavaScript [[Class]] of the given object.\n             * @param obj The object of which the type shall be determined.\n             * @returns {string} The type of the given object.\n             */\n            type: function(obj) {\n                if (obj === undefined)\n                    return obj + \"\";\n                if (obj === null)\n                    return obj + \"\";\n                return Object[LEXICON.p].toString.call(obj).replace(/^\\[object (.+)\\]$/, '$1').toLowerCase();\n            },\n\n\n            bind: function(func, thisObj) {\n                if (typeof func != TYPES.f) {\n                    throw \"Can't bind function!\";\n                    // closest thing possible to the ECMAScript 5\n                    // internal IsCallable function\n                    //throw new TypeError('Function.prototype.bind - what is trying to be bound is not callable');\n                }\n                var proto     = LEXICON.p;\n                var aArgs   = Array[proto].slice.call(arguments, 2);\n                var fNOP    = function() {};\n                var fBound  = function() { return func.apply(this instanceof fNOP ? this : thisObj, aArgs.concat(Array[proto].slice.call(arguments))); };\n\n                if (func[proto])\n                    fNOP[proto] = func[proto]; // Function.prototype doesn't have a prototype property\n                fBound[proto] = new fNOP();\n\n                return fBound;\n            }\n\n            /**\n             * Gets the vendor-prefixed CSS property by the given name.\n             * For example the given name is \"transform\" and you're using a old Firefox browser then the returned value would be \"-moz-transform\".\n             * If the browser doesn't need a vendor-prefix, then the returned string is the given name.\n             * If the browser doesn't support the given property name at all (not even with a vendor-prefix) the returned value is null.\n             * @param propName The unprefixed CSS property name.\n             * @returns {string|null} The vendor-prefixed CSS property or null if the browser doesn't support the given CSS property.\n\n            cssProp : function(propName) {\n                return VENDORS._cssProperty(propName);\n            }\n            */\n        };\n\n        var MATH = Math;\n        var JQUERY = window.jQuery;\n        var EASING = (function() {\n            var _easingsMath = {\n                p : MATH.PI,\n                c : MATH.cos,\n                s : MATH.sin,\n                w : MATH.pow,\n                t : MATH.sqrt,\n                n : MATH.asin,\n                a : MATH.abs,\n                o : 1.70158\n            };\n            \n            /*\n             x : current percent (0 - 1),\n             t : current time (duration * percent),\n             b : start value (from),\n             c : end value (to),\n             d : duration\n\n             easingName : function(x, t, b, c, d) { return easedValue; }\n             */\n\n            return {\n                swing: function (x, t, b, c, d) {\n                    return 0.5 - _easingsMath.c(x * _easingsMath.p) / 2;\n                },\n                linear: function(x, t, b, c, d) {\n                    return x;\n                },\n                easeInQuad: function (x, t, b, c, d) {\n                    return c*(t/=d)*t + b;\n                },\n                easeOutQuad: function (x, t, b, c, d) {\n                    return -c *(t/=d)*(t-2) + b;\n                },\n                easeInOutQuad: function (x, t, b, c, d) {\n                    return ((t/=d/2) < 1) ? c/2*t*t + b : -c/2 * ((--t)*(t-2) - 1) + b;\n                },\n                easeInCubic: function (x, t, b, c, d) {\n                    return c*(t/=d)*t*t + b;\n                },\n                easeOutCubic: function (x, t, b, c, d) {\n                    return c*((t=t/d-1)*t*t + 1) + b;\n                },\n                easeInOutCubic: function (x, t, b, c, d) {\n                    return ((t/=d/2) < 1) ? c/2*t*t*t + b : c/2*((t-=2)*t*t + 2) + b;\n                },\n                easeInQuart: function (x, t, b, c, d) {\n                    return c*(t/=d)*t*t*t + b;\n                },\n                easeOutQuart: function (x, t, b, c, d) {\n                    return -c * ((t=t/d-1)*t*t*t - 1) + b;\n                },\n                easeInOutQuart: function (x, t, b, c, d) {\n                    return ((t/=d/2) < 1) ? c/2*t*t*t*t + b : -c/2 * ((t-=2)*t*t*t - 2) + b;\n                },\n                easeInQuint: function (x, t, b, c, d) {\n                    return c*(t/=d)*t*t*t*t + b;\n                },\n                easeOutQuint: function (x, t, b, c, d) {\n                    return c*((t=t/d-1)*t*t*t*t + 1) + b;\n                },\n                easeInOutQuint: function (x, t, b, c, d) {\n                    return ((t/=d/2) < 1) ? c/2*t*t*t*t*t + b : c/2*((t-=2)*t*t*t*t + 2) + b;\n                },\n                easeInSine: function (x, t, b, c, d) {\n                    return -c * _easingsMath.c(t/d * (_easingsMath.p/2)) + c + b;\n                },\n                easeOutSine: function (x, t, b, c, d) {\n                    return c * _easingsMath.s(t/d * (_easingsMath.p/2)) + b;\n                },\n                easeInOutSine: function (x, t, b, c, d) {\n                    return -c/2 * (_easingsMath.c(_easingsMath.p*t/d) - 1) + b;\n                },\n                easeInExpo: function (x, t, b, c, d) {\n                    return (t==0) ? b : c * _easingsMath.w(2, 10 * (t/d - 1)) + b;\n                },\n                easeOutExpo: function (x, t, b, c, d) {\n                    return (t==d) ? b+c : c * (-_easingsMath.w(2, -10 * t/d) + 1) + b;\n                },\n                easeInOutExpo: function (x, t, b, c, d) {\n                    if (t==0) return b;\n                    if (t==d) return b+c;\n                    if ((t/=d/2) < 1) return c/2 * _easingsMath.w(2, 10 * (t - 1)) + b;\n                    return c/2 * (-_easingsMath.w(2, -10 * --t) + 2) + b;\n                },\n                easeInCirc: function (x, t, b, c, d) {\n                    return -c * (_easingsMath.t(1 - (t/=d)*t) - 1) + b;\n                },\n                easeOutCirc: function (x, t, b, c, d) {\n                    return c * _easingsMath.t(1 - (t=t/d-1)*t) + b;\n                },\n                easeInOutCirc: function (x, t, b, c, d) {\n                    return ((t/=d/2) < 1) ? -c/2 * (_easingsMath.t(1 - t*t) - 1) + b : c/2 * (_easingsMath.t(1 - (t-=2)*t) + 1) + b;\n                },\n                easeInElastic: function (x, t, b, c, d) {\n                    var s=_easingsMath.o;var p=0;var a=c;\n                    if (t==0) return b;  if ((t/=d)==1) return b+c;  if (!p) p=d*.3;\n                    if (a < _easingsMath.a(c)) { a=c; s=p/4; }\n                    else s = p/(2*_easingsMath.p) * _easingsMath.n (c/a);\n                    return -(a*_easingsMath.w(2,10*(t-=1)) * _easingsMath.s( (t*d-s)*(2*_easingsMath.p)/p )) + b;\n                },\n                easeOutElastic: function (x, t, b, c, d) {\n                    var s=_easingsMath.o;var p=0;var a=c;\n                    if (t==0) return b;  \n                    if ((t/=d)==1) return b+c;  \n                    if (!p) p=d*.3;\n                    if (a < _easingsMath.a(c)) { a=c; s=p/4; }\n                    else s = p/(2*_easingsMath.p) * _easingsMath.n (c/a);\n                    return a*_easingsMath.w(2,-10*t) * _easingsMath.s( (t*d-s)*(2*_easingsMath.p)/p ) + c + b;\n                },\n                easeInOutElastic: function (x, t, b, c, d) {\n                    var s=_easingsMath.o;var p=0;var a=c;\n                    if (t==0) return b;  \n                    if ((t/=d/2)==2) return b+c;  \n                    if (!p) p=d*(.3*1.5);\n                    if (a < _easingsMath.a(c)) { a=c; s=p/4; }\n                    else s = p/(2*_easingsMath.p) * _easingsMath.n (c/a);\n                    if (t < 1) return -.5*(a*_easingsMath.w(2,10*(t-=1)) * _easingsMath.s( (t*d-s)*(2*_easingsMath.p)/p )) + b;\n                    return a*_easingsMath.w(2,-10*(t-=1)) * _easingsMath.s( (t*d-s)*(2*_easingsMath.p)/p )*.5 + c + b;\n                },\n                easeInBack: function (x, t, b, c, d, s) {\n                    s = s || _easingsMath.o;\n                    return c*(t/=d)*t*((s+1)*t - s) + b;\n                },\n                easeOutBack: function (x, t, b, c, d, s) {\n                    s = s || _easingsMath.o;\n                    return c*((t=t/d-1)*t*((s+1)*t + s) + 1) + b;\n                },\n                easeInOutBack: function (x, t, b, c, d, s) {\n                    s = s || _easingsMath.o;\n                    return ((t/=d/2) < 1) ? c/2*(t*t*(((s*=(1.525))+1)*t - s)) + b : c/2*((t-=2)*t*(((s*=(1.525))+1)*t + s) + 2) + b;\n                },\n                easeInBounce: function (x, t, b, c, d) {\n                    return c - this.easeOutBounce (x, d-t, 0, c, d) + b;\n                },\n                easeOutBounce: function (x, t, b, c, d) {\n                    var o = 7.5625;\n                    if ((t/=d) < (1/2.75)) {\n                        return c*(o*t*t) + b;\n                    } else if (t < (2/2.75)) {\n                        return c*(o*(t-=(1.5/2.75))*t + .75) + b;\n                    } else if (t < (2.5/2.75)) {\n                        return c*(o*(t-=(2.25/2.75))*t + .9375) + b;\n                    } else {\n                        return c*(o*(t-=(2.625/2.75))*t + .984375) + b;\n                    }\n                },\n                easeInOutBounce: function (x, t, b, c, d) {\n                    return (t < d/2) ? this.easeInBounce (x, t*2, 0, c, d) * .5 + b : this.easeOutBounce (x, t*2-d, 0, c, d) * .5 + c*.5 + b;\n                }\n            };\n            /*\n             *\n             * TERMS OF USE - EASING EQUATIONS\n             * \n             * Open source under the BSD License. \n             * \n             * Copyright Â© 2001 Robert Penner\n             * All rights reserved.\n             * \n             * Redistribution and use in source and binary forms, with or without modification, \n             * are permitted provided that the following conditions are met:\n             * \n             * Redistributions of source code must retain the above copyright notice, this list of \n             * conditions and the following disclaimer.\n             * Redistributions in binary form must reproduce the above copyright notice, this list \n             * of conditions and the following disclaimer in the documentation and/or other materials \n             * provided with the distribution.\n             * \n             * Neither the name of the author nor the names of contributors may be used to endorse \n             * or promote products derived from this software without specific prior written permission.\n             * \n             * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS \"AS IS\" AND ANY \n             * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF\n             * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n             *  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,\n             *  EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE\n             *  GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED \n             * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING\n             *  NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED \n             * OF THE POSSIBILITY OF SUCH DAMAGE. \n             *\n             */\n        })();\n        var FRAMEWORK = (function() {\n            var _rnothtmlwhite = ( /[^\\x20\\t\\r\\n\\f]+/g );\n            var _strSpace = ' ';\n            var _strEmpty = '';\n            var _strScrollLeft = 'scrollLeft';\n            var _strScrollTop = 'scrollTop';\n            var _animations = [ ];\n            var _type = COMPATIBILITY.type;\n            var _cssNumber = {\n                \"animationIterationCount\": true,\n                \"columnCount\": true,\n                \"fillOpacity\": true,\n                \"flexGrow\": true,\n                \"flexShrink\": true,\n                \"fontWeight\": true,\n                \"lineHeight\": true,\n                \"opacity\": true,\n                \"order\": true,\n                \"orphans\": true,\n                \"widows\": true,\n                \"zIndex\": true,\n                \"zoom\": true\n            };\n\n            var extend = function() {\n                var src, copyIsArray, copy, name, options, clone, target = arguments[0] || {},\n                    i = 1,\n                    length = arguments[LEXICON.l],\n                    deep = false;\n\n                // Handle a deep copy situation\n                if (_type(target) == TYPES.b) {\n                    deep = target;\n                    target = arguments[1] || {};\n                    // skip the boolean and the target\n                    i = 2;\n                }\n\n                // Handle case when target is a string or something (possible in deep copy)\n                if (_type(target) != TYPES.o && !_type(target) == TYPES.f) {\n                    target = {};\n                }\n\n                // extend jQuery itself if only one argument is passed\n                if (length === i) {\n                    target = FakejQuery;\n                    --i;\n                }\n\n                for (; i < length; i++) {\n                    // Only deal with non-null/undefined values\n                    if ((options = arguments[i]) != null) {\n                        // Extend the base object\n                        for (name in options) {\n                            src = target[name];\n                            copy = options[name];\n\n                            // Prevent never-ending loop\n                            if (target === copy) {\n                                continue;\n                            }\n\n                            // Recurse if we're merging plain objects or arrays\n                            if (deep && copy && (isPlainObject(copy) || (copyIsArray = COMPATIBILITY.isA(copy)))) {\n                                if (copyIsArray) {\n                                    copyIsArray = false;\n                                    clone = src && COMPATIBILITY.isA(src) ? src : [];\n\n                                } else {\n                                    clone = src && isPlainObject(src) ? src : {};\n                                }\n\n                                // Never move original objects, clone them\n                                target[name] = extend(deep, clone, copy);\n\n                                // Don't bring in undefined values\n                            } else if (copy !== undefined) {\n                                target[name] = copy;\n                            }\n                        }\n                    }\n                }\n\n                // Return the modified object\n                return target;\n            };\n\n            var inArray = function(item, arr, fromIndex) {\n                for (var i = fromIndex || 0; i < arr[LEXICON.l]; i++)\n                    if (arr[i] === item)\n                        return i;\n                return -1;\n            }\n            \n            var isFunction = function(obj) {\n                return _type(obj) == TYPES.f;\n            };\n\n            var isEmptyObject = function(obj) {\n                for (var name in obj )\n                    return false;\n                return true;\n            };\n\n            var isPlainObject = function(obj) {\n                if (!obj || _type(obj) != TYPES.o)\n                    return false;\n\n                var key;\n                var proto = LEXICON.p;\n                var hasOwnProperty = Object[proto].hasOwnProperty;\n                var hasOwnConstructor = hasOwnProperty.call(obj, 'constructor');\n                var hasIsPrototypeOf = obj.constructor && obj.constructor[proto] && hasOwnProperty.call(obj.constructor[proto], 'isPrototypeOf');\n\n                if (obj.constructor && !hasOwnConstructor && !hasIsPrototypeOf) {\n                    return false;\n                }\n\n\n                for (key in obj) { /**/ }\n\n                return _type(key) == TYPES.u || hasOwnProperty.call(obj, key);\n            };\n\n            var each = function(obj, callback) {\n                var i = 0;\n\n                if (isArrayLike(obj)) {\n                    for (; i < obj[LEXICON.l]; i++) {\n                        if (callback.call(obj[i], i, obj[i]) === false)\n                            break;\n                    }\n                }\n                else {\n                    for (i in obj) {\n                        if (callback.call(obj[i], i, obj[i]) === false)\n                            break;\n                    }\n                }\n\n                return obj;\n            };\n\n            var FakejQuery = function (selector) {\n                if(arguments[LEXICON.l] === 0)\n                    return this;\n\n                var base = new FakejQuery();\n                var elements = selector;\n                var i = 0;\n                var elms;\n                var el;\n\n                if(_type(selector) == TYPES.s) {\n                    elements = [ ];\n                    if(selector.charAt(0) === '<') {\n                        el = document.createElement('div');\n                        el.innerHTML = selector;\n                        elms = el.children;\n                    }\n                    else {\n                        elms = document.querySelectorAll(selector);\n                    }\n\n                    for(; i < elms[LEXICON.l]; i++)\n                        elements.push(elms[i]);\n                }\n\n                if(elements) {\n                    if(_type(elements) != TYPES.s && (!isArrayLike(elements) || elements === window || elements === elements.self))\n                        elements = [ elements ];\n\n                    for(i = 0; i < elements[LEXICON.l]; i++)\n                        base[i] = elements[i];\n\n                    base[LEXICON.l] = elements[LEXICON.l];\n                }\n\n                return base;\n            };\n\n            function isArrayLike(obj) {\n                var length = !!obj && [LEXICON.l] in obj && obj[LEXICON.l];\n                var t = _type(obj);\n                return isFunction(t) ? false : (t == TYPES.a || length === 0 || _type(length) == TYPES.n && length > 0 && (length - 1) in obj);\n            }\n\n            function stripAndCollapse(value) {\n                var tokens = value.match(_rnothtmlwhite) || [];\n                return tokens.join(_strSpace);\n            }\n\n            function matches(elem, selector) {\n                var nodeList = (elem.parentNode || document).querySelectorAll(selector) || [];\n                var i = nodeList[LEXICON.l];\n\n                while (i--)\n                    if (nodeList[i] == elem)\n                        return true;\n\n                return false;\n            }\n\n            function insertAdjacentElement(el, strategy, child) {\n                if(_type(child) == TYPES.a) {\n                    for(var i = 0; i < child[LEXICON.l]; i++)\n                        insertAdjacentElement(el, strategy, child[i]);\n                }\n                else if(_type(child) == TYPES.s)\n                    el.insertAdjacentHTML(strategy, child);\n                else\n                    el.insertAdjacentElement(strategy, child.nodeType ? child : child[0]);\n            }\n\n            function setCSSVal(el, prop, val) {\n                try {\n                    if(el[LEXICON.s][prop] !== undefined)\n                        el[LEXICON.s][prop] = parseCSSVal(prop, val);\n                } catch(e) { }\n            }\n\n            function parseCSSVal(prop, val) {\n                if(!_cssNumber[prop.toLowerCase()] && _type(val) == TYPES.n)\n                    val += 'px';\n                return val;\n            }\n\n            function startNextAnimationInQ(animObj, removeFromQ) {\n                var index;\n                var nextAnim;\n                if(removeFromQ !== false)\n                    animObj.q.splice(0, 1);\n                if(animObj.q[LEXICON.l] > 0) {\n                    nextAnim = animObj.q[0];\n                    animate(animObj.el, nextAnim.props, nextAnim.duration, nextAnim.easing, nextAnim.complete, true);\n                }\n                else {\n                    index = inArray(animObj, _animations);\n                    if(index > -1)\n                        _animations.splice(index, 1);\n                }\n            }\n\n            function setAnimationValue(el, prop, value) {\n                if(prop === _strScrollLeft || prop === _strScrollTop)\n                    el[prop] = value;\n                else\n                    setCSSVal(el, prop, value);\n            }\n\n            function animate(el, props, options, easing, complete, guaranteedNext) {\n                var hasOptions = isPlainObject(options);\n                var from = { };\n                var to = { };\n                var i = 0;\n                var key;\n                var animObj;\n                var start;\n                var progress;\n                var step;\n                var specialEasing;\n                var duration;\n                if(hasOptions) {\n                    easing = options.easing;\n                    start = options.start;\n                    progress = options.progress;\n                    step = options.step;\n                    specialEasing = options.specialEasing;\n                    complete = options.complete;\n                    duration = options.duration;\n                }\n                else\n                    duration = options;\n                specialEasing = specialEasing || { };\n                duration = duration || 400;\n                easing = easing || 'swing';\n                guaranteedNext = guaranteedNext || false;\n\n                for(; i < _animations[LEXICON.l]; i++) {\n                    if(_animations[i].el === el) {\n                        animObj = _animations[i];\n                        break;\n                    }\n                }\n\n                if(!animObj) {\n                    animObj = {\n                        el : el,\n                        q : []\n                    };\n                    _animations.push(animObj);\n                }\n\n                for (key in props) {\n                    if(key === _strScrollLeft || key === _strScrollTop)\n                        from[key] = el[key];\n                    else\n                        from[key] = FakejQuery(el).css(key);\n                }\n\n                for (key in from) {\n                    if(from[key] !== props[key] && props[key] !== undefined)\n                        to[key] = props[key];\n                }\n\n                if(!isEmptyObject(to)) {\n                    var timeNow;\n                    var end;\n                    var percent;\n                    var fromVal;\n                    var toVal;\n                    var easedVal;\n                    var timeStart;\n                    var frame;\n                    var elapsed;\n                    var qPos = guaranteedNext ? 0 : inArray(qObj, animObj.q);\n                    var qObj = {\n                        props : to,\n                        duration : hasOptions ? options : duration,\n                        easing : easing,\n                        complete : complete\n                    };\n                    if (qPos === -1) {\n                        qPos = animObj.q[LEXICON.l];\n                        animObj.q.push(qObj);\n                    }\n\n                    if(qPos === 0) {\n                        if(duration > 0) {\n                            timeStart = COMPATIBILITY.now();\n                            frame = function() {\n                                timeNow = COMPATIBILITY.now();\n                                elapsed = (timeNow - timeStart);\n                                end = qObj.stop || elapsed >= duration;\n                                percent = 1 - ((MATH.max(0, timeStart + duration - timeNow) / duration) || 0);\n\n                                for(key in to) {\n                                    fromVal = parseFloat(from[key]);\n                                    toVal = parseFloat(to[key]);\n                                    easedVal = (toVal - fromVal) * EASING[specialEasing[key] || easing](percent, percent * duration, 0, 1, duration) + fromVal;\n                                    setAnimationValue(el, key, easedVal);\n                                    if(isFunction(step)) {\n                                        step(easedVal, {\n                                            elem : el,\n                                            prop : key,\n                                            start : fromVal,\n                                            now : easedVal,\n                                            end : toVal,\n                                            pos : percent,\n                                            options : {\n                                                easing : easing,\n                                                speacialEasing : specialEasing,\n                                                duration : duration,\n                                                complete : complete,\n                                                step : step\n                                            },\n                                            startTime : timeStart\n                                        });\n                                    }\n                                }\n\n                                if(isFunction(progress))\n                                    progress({ }, percent, MATH.max(0, duration - elapsed));\n\n                                if (end) {\n                                    startNextAnimationInQ(animObj);\n                                    if(isFunction(complete))\n                                        complete();\n                                }\n                                else\n                                    qObj.frame = COMPATIBILITY.rAF()(frame);\n                            };\n                            qObj.frame = COMPATIBILITY.rAF()(frame);\n                        }\n                        else {\n                            for(key in to)\n                                setAnimationValue(el, key, to[key]);\n                            startNextAnimationInQ(animObj);\n                        }\n                    }\n                }\n                else if(guaranteedNext)\n                    startNextAnimationInQ(animObj);\n            }\n\n            function stop(el, clearQ, jumpToEnd) {\n                var animObj;\n                var qObj;\n                var key;\n                var i = 0;\n                for(; i < _animations[LEXICON.l]; i++) {\n                    animObj = _animations[i];\n                    if(animObj.el === el) {\n                        if(animObj.q[LEXICON.l] > 0) {\n                            qObj = animObj.q[0];\n                            qObj.stop = true;\n                            COMPATIBILITY.cAF()(qObj.frame);\n                            animObj.q.splice(0, 1);\n\n                            if(jumpToEnd)\n                                for(key in qObj.props)\n                                    setAnimationValue(el, key, qObj.props[key]);\n\n                            if(clearQ)\n                                animObj.q = [ ];\n                            else\n                                startNextAnimationInQ(animObj, false);\n                        }\n                        break;\n                    }\n                }\n            }\n\n            FakejQuery[LEXICON.p] = {\n\n                //EVENTS:\n\n                on : function(eventName, handler) {\n                    eventName = (eventName || _strEmpty).match(_rnothtmlwhite) || [_strEmpty];\n\n                    var eventNameLength = eventName[LEXICON.l];\n                    var i = 0;\n                    var el;\n                    return this.each(function() {\n                        el = this;\n                        try {\n                            if (el.addEventListener) {\n                                for (; i < eventNameLength; i++)\n                                    el.addEventListener(eventName[i], handler);\n                            }\n                            else if(el.detachEvent) {\n                                for (; i < eventNameLength; i++)\n                                    el.attachEvent('on' + eventName[i], handler);\n                            }\n                        } catch (e) { }\n                    });\n                },\n\n                off : function(eventName, handler) {\n                    eventName = (eventName || _strEmpty).match(_rnothtmlwhite) || [_strEmpty];\n\n                    var eventNameLength = eventName[LEXICON.l];\n                    var i = 0;\n                    var el;\n                    return this.each(function() {\n                        el = this;\n                        try {\n                            if (el.removeEventListener) {\n                                for (; i < eventNameLength; i++)\n                                    el.removeEventListener(eventName[i], handler);\n                            }\n                            else if(el.detachEvent) {\n                                for (; i < eventNameLength; i++)\n                                    el.detachEvent('on' + eventName[i], handler);\n                            }\n                        } catch (e) { }\n                    });\n                },\n\n                one : function (eventName, handler) {\n                    eventName = (eventName || _strEmpty).match(_rnothtmlwhite) || [_strEmpty];\n                    return this.each(function() {\n                        var el = FakejQuery(this);\n                        FakejQuery.each(eventName, function(i, oneEventName) {\n                            var oneHandler = function(e) {\n                                handler.call(this, e);\n                                el.off(oneEventName, oneHandler);\n                            };\n                            el.on(oneEventName, oneHandler);\n                        });\n                    });\n                },\n\n                trigger : function(eventName) {\n                    var el;\n                    var event;\n                    return this.each(function() {\n                        el = this;\n                        if (document.createEvent) {\n                            event = document.createEvent('HTMLEvents');\n                            event.initEvent(eventName, true, false);\n                            el.dispatchEvent(event);\n                        }\n                        else {\n                            el.fireEvent(\"on\" + eventName);\n                        }\n                    });\n                },\n\n                //DOM NODE INSERTING / REMOVING:\n\n                append : function(child) {\n                    return this.each(function() { insertAdjacentElement(this, 'beforeend', child); });\n                },\n\n                prepend : function(child) {\n                    return this.each(function() { insertAdjacentElement(this, 'afterbegin', child); });\n                },\n\n                before : function(child) {\n                    return this.each(function() { insertAdjacentElement(this, 'beforebegin', child); });\n                },\n\n                after : function(child) {\n                    return this.each(function() { insertAdjacentElement(this, 'afterend', child); });\n                },\n\n                remove : function() {\n                    return this.each(function() {\n                        var el = this;\n                        var parentNode = el.parentNode;\n                        if(parentNode != null)\n                            parentNode.removeChild(el);\n                    });\n                },\n\n                unwrap : function() {\n                    var parents = [ ];\n                    var i;\n                    var el;\n                    var parent;\n\n                    this.each(function() {\n                        parent = this.parentNode;\n                        if(inArray(parent, parents) === - 1)\n                            parents.push(parent);\n                    });\n\n                    for(i = 0; i < parents[LEXICON.l]; i++) {\n                        el = parents[i];\n                        parent = el.parentNode;\n                        while (el.firstChild)\n                            parent.insertBefore(el.firstChild, el);\n                        parent.removeChild(el);\n                    }\n\n                    return this;\n                },\n\n                wrapAll : function(wrapperHTML) {\n                    var i;\n                    var nodes = this;\n                    var wrapper = FakejQuery(wrapperHTML)[0];\n                    var deepest = wrapper;\n                    var parent = nodes[0].parentNode;\n                    var previousSibling = nodes[0].previousSibling;\n                    while(deepest.childNodes[LEXICON.l] > 0)\n                        deepest = deepest.childNodes[0];\n\n                    for (i = 0; nodes[LEXICON.l] - i; deepest.firstChild === nodes[0] && i++)\n                        deepest.appendChild(nodes[i]);\n\n                    var nextSibling = previousSibling ? previousSibling.nextSibling : parent.firstChild;\n                    parent.insertBefore(wrapper, nextSibling);\n\n                    return this;\n                },\n\n                wrapInner : function(wrapperHTML) {\n                    return this.each(function() {\n                        var el = FakejQuery(this);\n                        var contents = el.contents();\n\n                        if (contents[LEXICON.l])\n                            contents.wrapAll(wrapperHTML);\n                        else\n                            el.append(wrapperHTML);\n                    });\n                },\n\n                wrap : function(wrapperHTML) {\n                    return this.each(function() { FakejQuery(this).wrapAll(wrapperHTML); });\n                },\n\n\n                //DOM NODE MANIPULATION / INFORMATION:\n\n                css : function(styles, val) {\n                    var el;\n                    var key;\n                    var cptStyle;\n                    var getCptStyle = window.getComputedStyle;\n                    if(_type(styles) == TYPES.s) {\n                        if(val === undefined) {\n                            el = this[0];\n                            cptStyle = getCptStyle ? getCptStyle(el, null) : el.currentStyle[styles];\n\n                            //https://bugzilla.mozilla.org/show_bug.cgi?id=548397 can be null sometimes if iframe with display: none (firefox only!)\n                            return getCptStyle ? cptStyle != null ? cptStyle.getPropertyValue(styles) : el[LEXICON.s][styles] : cptStyle;\n                        }\n                        else {\n                            return this.each(function() {\n                                setCSSVal(this, styles, val);\n                            });\n                        }\n                    }\n                    else {\n                        return this.each(function() {\n                            for(key in styles)\n                                setCSSVal(this, key, styles[key]);\n                        });\n                    }\n                },\n\n                hasClass : function(className) {\n                    var elem, i = 0;\n                    var classNamePrepared = _strSpace + className + _strSpace;\n                    var classList;\n\n                    while ((elem = this[ i++ ])) {\n                        classList = elem.classList;\n                        if(classList && classList.contains(className))\n                            return true;\n                        else if (elem.nodeType === 1 && (_strSpace + stripAndCollapse(elem.className + _strEmpty) + _strSpace).indexOf(classNamePrepared) > -1)\n                            return true;\n                    }\n\n                    return false;\n                },\n\n                addClass : function(className) {\n                    var classes;\n                    var elem;\n                    var cur;\n                    var curValue;\n                    var clazz;\n                    var finalValue;\n                    var supportClassList;\n                    var elmClassList;\n                    var i = 0;\n                    var v = 0;\n\n                    if (className) {\n                        classes = className.match( _rnothtmlwhite ) || [];\n\n                        while ((elem = this[i++])) {\n                            elmClassList = elem.classList;\n                            if(supportClassList === undefined)\n                                supportClassList = elmClassList !== undefined;\n\n                            if(supportClassList) {\n                                while ((clazz = classes[v++]))\n                                    elmClassList.add(clazz);\n                            }\n                            else {\n                                curValue = elem.className + _strEmpty;\n                                cur = elem.nodeType === 1 && (_strSpace + stripAndCollapse(curValue) + _strSpace);\n\n                                if (cur) {\n                                    while ((clazz = classes[v++]))\n                                        if (cur.indexOf(_strSpace + clazz + _strSpace) < 0)\n                                            cur += clazz + _strSpace;\n\n                                    finalValue = stripAndCollapse(cur);\n                                    if (curValue !== finalValue)\n                                        elem.className = finalValue;\n                                }\n                            }\n                        }\n                    }\n\n                    return this;\n                },\n\n                removeClass : function(className) {\n                    var classes;\n                    var elem;\n                    var cur;\n                    var curValue;\n                    var clazz;\n                    var finalValue;\n                    var supportClassList;\n                    var elmClassList;\n                    var i = 0;\n                    var v = 0;\n\n                    if (className) {\n                        classes = className.match(_rnothtmlwhite) || [];\n\n                        while ((elem = this[i++])) {\n                            elmClassList = elem.classList;\n                            if(supportClassList === undefined)\n                                supportClassList = elmClassList !== undefined;\n\n                            if(supportClassList) {\n                                while ((clazz = classes[v++]))\n                                    elmClassList.remove(clazz);\n                            }\n                            else {\n                                curValue = elem.className + _strEmpty;\n                                cur = elem.nodeType === 1 && (_strSpace + stripAndCollapse(curValue) + _strSpace);\n\n                                if (cur) {\n                                    while ((clazz = classes[v++]))\n                                        while (cur.indexOf(_strSpace + clazz + _strSpace) > -1)\n                                            cur = cur.replace(_strSpace + clazz + _strSpace, _strSpace);\n\n                                    finalValue = stripAndCollapse(cur);\n                                    if (curValue !== finalValue)\n                                        elem.className = finalValue;\n                                }\n                            }\n                        }\n                    }\n\n                    return this;\n                },\n\n                hide : function() {\n                    return this.each(function() { this[LEXICON.s].display = 'none'; });\n                },\n\n                show : function() {\n                    return this.each(function() { this[LEXICON.s].display = 'block'; });\n                },\n\n                attr : function(attrName, value) {\n                    var i = 0;\n                    var el;\n                    while (el = this[i++]) {\n                        if(value === undefined)\n                            return el.getAttribute(attrName);\n                        el.setAttribute(attrName, value);\n                    }\n                    return this;\n                },\n\n                removeAttr : function(attrName) {\n                    return this.each(function() { this.removeAttribute(attrName); });\n                },\n\n                offset : function() {\n                    var el = this[0];\n                    var rect = el.getBoundingClientRect();\n                    var scrollLeft = window.pageXOffset || document.documentElement[_strScrollLeft];\n                    var scrollTop = window.pageYOffset || document.documentElement[_strScrollTop];\n                    return {\n                        top: rect.top + scrollTop,\n                        left: rect.left + scrollLeft\n                    };\n                },\n\n                position : function() {\n                    var el = this[0];\n                    return {\n                        top: el.offsetTop,\n                        left: el.offsetLeft\n                    };\n                },\n\n                scrollLeft : function(value) {\n                    var i = 0;\n                    var el;\n                    while (el = this[i++]) {\n                        if(value === undefined)\n                            return el[_strScrollLeft];\n                        el[_strScrollLeft] = value;\n                    }\n                    return this;\n                },\n\n                scrollTop : function(value) {\n                    var i = 0;\n                    var el;\n                    while (el = this[i++]) {\n                        if(value === undefined)\n                            return el[_strScrollTop];\n                        el[_strScrollTop] = value;\n                    }\n                    return this;\n                },\n\n                val : function(value) {\n                    var el = this[0];\n                    if(!value)\n                        return el.value;\n                    el.value = value;\n                    return this;\n                },\n\n\n                //DOM TRAVERSAL / FILTERING:\n\n                first : function() {\n                    return this.eq(0);\n                },\n\n                last : function() {\n                    return this.eq(-1);\n                },\n\n                eq : function(index) {\n                    return FakejQuery(this[index >= 0 ? index : this[LEXICON.l] + index]);\n                },\n\n                find : function(selector) {\n                    var children = [ ];\n                    var i;\n                    this.each(function() {\n                        var el = this;\n                        var ch = el.querySelectorAll(selector);\n                        for(i = 0; i < ch[LEXICON.l]; i++)\n                            children.push(ch[i]);\n                    });\n                    return FakejQuery(children);\n                },\n\n                children : function(selector) {\n                    var children = [ ];\n                    var el;\n                    var ch;\n                    var i;\n\n                    this.each(function() {\n                        ch = this.children;\n                        for(i = 0; i < ch[LEXICON.l]; i++) {\n                            el = ch[i];\n                            if(selector) {\n                                if((el.matches && el.matches(selector)) || matches(el, selector))\n                                    children.push(el);\n                            }\n                            else\n                                children.push(el);\n                        }\n                    });\n                    return FakejQuery(children);\n                },\n\n                parent : function(selector) {\n                    var parents = [ ];\n                    var parent;\n                    this.each(function() {\n                        parent = this.parentNode;\n                        if(selector ? FakejQuery(parent).is(selector) : true)\n                            parents.push(parent);\n                    });\n                    return FakejQuery(parents);\n                },\n\n                is : function(selector) {\n                    var el;\n                    var i;\n                    for(i = 0; i < this[LEXICON.l]; i++) {\n                        el = this[i];\n                        if(selector === \":visible\")\n                            return !!(el[LEXICON.oW] || el[LEXICON.oH] || el.getClientRects()[LEXICON.l]);\n                        if(selector === \":hidden\")\n                            return !!!(el[LEXICON.oW] || el[LEXICON.oH] || el.getClientRects()[LEXICON.l]);\n                        if((el.matches && el.matches(selector)) || matches(el, selector))\n                            return true;\n                    }\n                    return false;\n                },\n\n                contents : function() {\n                    var contents = [ ];\n                    var childs;\n                    var i;\n\n                    this.each(function() {\n                        childs = this.childNodes;\n                        for(i = 0; i < childs[LEXICON.l]; i++)\n                            contents.push(childs[i]);\n                    });\n\n                    return FakejQuery(contents);\n                },\n\n                each : function(callback) {\n                    return each(this, callback);\n                },\n\n\n                //ANIMATION:\n\n                animate : function(props, duration, easing, complete) {\n                    return this.each(function() { animate(this, props, duration, easing, complete); });\n                },\n\n                stop : function(clearQ, jump) {\n                    return this.each(function() { stop(this, clearQ, jump); });\n                }\n            };\n\n            extend(FakejQuery, {\n                extend : extend,\n                inArray : inArray,\n                isEmptyObject : isEmptyObject,\n                isPlainObject : isPlainObject,\n                each : each\n            });\n\n            return FakejQuery;\n        })();\n        var INSTANCES = (function() {\n            var _targets = [ ];\n            var _instancePropertyString = '__overlayScrollbars__';\n\n            /**\n             * Register, unregister or get a certain (or all) instances.\n             * Register: Pass the target and the instance.\n             * Unregister: Pass the target and null.\n             * Get Instance: Pass the target from which the instance shall be got.\n             * Get Targets: Pass no arguments.\n             * @param target The target to which the instance shall be registered / from which the instance shall be unregistered / the instance shall be got\n             * @param instance The instance.\n             * @returns {*|void} Returns the instance from the given target.\n             */\n            return function (target, instance) {\n                var argLen = arguments[LEXICON.l];\n                if(argLen < 1) {\n                    //return all targets\n                    return _targets;\n                }\n                else {\n                    if(instance) {\n                        //register instance\n                        target[_instancePropertyString] = instance;\n                        _targets.push(target);\n                    }\n                    else {\n                        var index = COMPATIBILITY.inA(target, _targets);\n                        if (index > -1) {\n                            if(argLen > 1) {\n                                //unregister instance\n                                delete target[_instancePropertyString];\n                                _targets.splice(index, 1);\n                            }\n                            else {\n                                //get instance from target\n                                return _targets[index][_instancePropertyString];\n                            }\n                        }\n                    }\n                }\n            }\n        })();\n        var PLUGIN = (function() {\n            var _pluginsGlobals;\n            var _pluginsAutoUpdateLoop;\n            var _pluginsExtensions = [ ];\n            var _pluginsOptions = (function() {\n                var type = COMPATIBILITY.type;\n                var possibleTemplateTypes = [\n                    TYPES.b, //boolean\n                    TYPES.n, //number\n                    TYPES.s, //string\n                    TYPES.a, //array\n                    TYPES.o, //object\n                    TYPES.f, //function\n                    TYPES.z  //null\n                ];\n                var restrictedStringsSplit = ' ';\n                var restrictedStringsPossibilitiesSplit = ':';\n                var classNameAllowedValues = [TYPES.z, TYPES.s];\n                var numberAllowedValues = TYPES.n;\n                var booleanNullAllowedValues = [TYPES.z, TYPES.b];\n                var booleanTrueTemplate = [true, TYPES.b];\n                var booleanFalseTemplate = [false, TYPES.b];\n                var callbackTemplate = [null,  [TYPES.z, TYPES.f]];\n                var inheritedAttrsTemplate = [['style', 'class'], [TYPES.s, TYPES.a, TYPES.z]];\n                var resizeAllowedValues = 'n:none b:both h:horizontal v:vertical';\n                var overflowBehaviorAllowedValues = 'v-h:visible-hidden v-s:visible-scroll s:scroll h:hidden';\n                var scrollbarsVisibilityAllowedValues = 'v:visible h:hidden a:auto';\n                var scrollbarsAutoHideAllowedValues = 'n:never s:scroll l:leave m:move';\n                var optionsDefaultsAndTemplate = {\n                    className: ['os-theme-dark', classNameAllowedValues],                //null || string\n                    resize: ['none', resizeAllowedValues],                               //none || both  || horizontal || vertical || n || b || h || v\n                    sizeAutoCapable: booleanTrueTemplate,                                //true || false\n                    clipAlways: booleanTrueTemplate,                                     //true || false\n                    normalizeRTL: booleanTrueTemplate,                                   //true || false\n                    paddingAbsolute: booleanFalseTemplate,                               //true || false\n                    autoUpdate: [null, booleanNullAllowedValues],                        //true || false || null\n                    autoUpdateInterval: [33, numberAllowedValues],                       //number\n                    nativeScrollbarsOverlaid: {\n                        showNativeScrollbars: booleanFalseTemplate,                      //true || false\n                        initialize: booleanTrueTemplate                                  //true || false\n                    },\n                    overflowBehavior: {\n                        x: ['scroll', overflowBehaviorAllowedValues],                    //visible-hidden  || visible-scroll || hidden || scroll || v-h || v-s || h || s\n                        y: ['scroll', overflowBehaviorAllowedValues]                     //visible-hidden  || visible-scroll || hidden || scroll || v-h || v-s || h || s\n                    },\n                    scrollbars: {\n                        visibility: ['auto', scrollbarsVisibilityAllowedValues],         //visible || hidden || auto || v || h || a\n                        autoHide: ['never', scrollbarsAutoHideAllowedValues],            //never || scroll || leave || move || n || s || l || m\n                        autoHideDelay: [800, numberAllowedValues],                       //number\n                        dragScrolling: booleanTrueTemplate,                              //true || false\n                        clickScrolling: booleanFalseTemplate,                            //true || false\n                        touchSupport: booleanTrueTemplate,                               //true || false\n                        snapHandle: booleanFalseTemplate                                 //true || false\n                    },\n                    textarea: {\n                        dynWidth: booleanFalseTemplate,                                  //true || false\n                        dynHeight: booleanFalseTemplate,                                 //true || false\n                        inheritedAttrs : inheritedAttrsTemplate                          //string || array || null\n                    },\n                    callbacks: {\n                        onInitialized: callbackTemplate,                                 //null || function\n                        onInitializationWithdrawn: callbackTemplate,                     //null || function\n                        onDestroyed: callbackTemplate,                                   //null || function\n                        onScrollStart: callbackTemplate,                                 //null || function\n                        onScroll: callbackTemplate,                                      //null || function\n                        onScrollStop: callbackTemplate,                                  //null || function\n                        onOverflowChanged: callbackTemplate,                             //null || function\n                        onOverflowAmountChanged: callbackTemplate,                       //null || function\n                        onDirectionChanged: callbackTemplate,                            //null || function\n                        onContentSizeChanged: callbackTemplate,                          //null || function\n                        onHostSizeChanged: callbackTemplate,                             //null || function\n                        onUpdated: callbackTemplate                                      //null || function\n                    }\n                };\n                var convert = function(template) {\n                    var recursive = function(obj) {\n                        var key;\n                        var val;\n                        var valType;\n                        for(key in obj) {\n                            if(!obj[LEXICON.hOP](key))\n                                continue;\n                            val = obj[key];\n                            valType = type(val);\n                            if(valType == TYPES.a)\n                                obj[key] = val[template ? 1 : 0];\n                            else if(valType == TYPES.o)\n                                obj[key] = recursive(val);\n                        }\n                        return obj;\n                    };\n                    return recursive(FRAMEWORK.extend(true, { }, optionsDefaultsAndTemplate));\n                };\n\n                return {\n                    _defaults : convert(),\n\n                    _template : convert(true),\n\n                    /**\n                     * Validates the passed object by the passed template.\n                     * @param obj The object which shall be validated.\n                     * @param template The template which defines the allowed values and types.\n                     * @param writeErrors True if errors shall be logged to the console.\n                     * @param diffObj If a object is passed then only valid differences to this object will be returned.\n                     * @returns {{}} A object which contains two objects called \"default\" and \"prepared\" which contains only the valid properties of the passed original object and discards not different values compared to the passed diffObj.\n                     */\n                    _validate : function (obj, template, writeErrors, diffObj) {\n                        var validatedOptions = { };\n                        var validatedOptionsPrepared = { };\n                        var objectCopy = FRAMEWORK.extend(true, { }, obj);\n                        var inArray = FRAMEWORK.inArray;\n                        var isEmptyObj = FRAMEWORK.isEmptyObject;\n                        var checkObjectProps = function(data, template, diffData, validatedOptions, validatedOptionsPrepared, prevPropName) {\n                            for (var prop in template) {\n                                if (template[LEXICON.hOP](prop) && data[LEXICON.hOP](prop)) {\n                                    var isValid = false;\n                                    var isDiff = false;\n                                    var templateValue = template[prop];\n                                    var templateValueType = type(templateValue);\n                                    var templateIsComplex = templateValueType == TYPES.o;\n                                    var templateTypes = type(templateValue) != TYPES.a ? [ templateValue ] : templateValue;\n                                    var dataDiffValue = diffData[prop];\n                                    var dataValue = data[prop];\n                                    var dataValueType = type(dataValue);\n                                    var propPrefix = prevPropName ? prevPropName + \".\" : \"\";\n                                    var error = \"The option \\\"\" + propPrefix + prop + \"\\\" wasn't set, because\";\n                                    var errorPossibleTypes = [ ];\n                                    var errorRestrictedStrings = [ ];\n                                    var restrictedStringValuesSplit;\n                                    var restrictedStringValuesPossibilitiesSplit;\n                                    var isRestrictedValue;\n                                    var mainPossibility;\n                                    var currType;\n                                    var i;\n                                    var v;\n                                    var j;\n\n                                    dataDiffValue = dataDiffValue === undefined ? { } : dataDiffValue;\n                                    \n                                    //if the template has a object as value, it means that the options are complex (verschachtelt)\n                                    if(templateIsComplex && dataValueType == TYPES.o) {\n                                        validatedOptions[prop] = validatedOptionsPrepared[prop] = { };\n                                        checkObjectProps(dataValue, templateValue, dataDiffValue, validatedOptions[prop], validatedOptionsPrepared[prop], propPrefix + prop);\n                                        if(isEmptyObj(dataValue))\n                                            delete data[prop];\n                                    }\n                                    else if(!templateIsComplex) {\n                                        for(i = 0; i < templateTypes[LEXICON.l]; i++) {\n                                            currType = templateTypes[i];\n                                            templateValueType = type(currType);\n                                            //if currtype is string and starts with restrictedStringPrefix and end with restrictedStringSuffix\n                                            isRestrictedValue = templateValueType == TYPES.s && inArray(currType, possibleTemplateTypes) === -1;\n                                            if(isRestrictedValue) {\n                                                errorPossibleTypes.push(TYPES.s);\n\n                                                //split it into a array which contains all possible values for example: [\"y:yes\", \"n:no\", \"m:maybe\"]\n                                                restrictedStringValuesSplit = currType.split(restrictedStringsSplit);\n                                                errorRestrictedStrings = errorRestrictedStrings.concat(restrictedStringValuesSplit);\n                                                for(v = 0; v < restrictedStringValuesSplit[LEXICON.l]; v++) {\n                                                    //split the possible values into their possibiliteis for example: [\"y\", \"yes\"] -> the first is always the mainPossibility\n                                                    restrictedStringValuesPossibilitiesSplit = restrictedStringValuesSplit[v].split(restrictedStringsPossibilitiesSplit);\n                                                    mainPossibility = restrictedStringValuesPossibilitiesSplit[0];\n                                                    for(j = 0; j < restrictedStringValuesPossibilitiesSplit[LEXICON.l]; j++) {\n                                                        //if any possibility matches with the dataValue, its valid\n                                                        if(dataValue === restrictedStringValuesPossibilitiesSplit[j]) {\n                                                            isValid = true;\n                                                            break;\n                                                        }\n                                                    }\n                                                    if(isValid)\n                                                        break;\n                                                }\n                                            }\n                                            else {\n                                                errorPossibleTypes.push(currType);\n\n                                                if(dataValueType === currType) {\n                                                    isValid = true;\n                                                    break;\n                                                }\n                                            }\n                                        }\n\n                                        if(isValid) {\n                                            isDiff = dataValue !== dataDiffValue;\n                                            \n                                            if(isDiff)\n                                                validatedOptions[prop] = dataValue;\n                                            \n                                            if(isRestrictedValue ? inArray(dataDiffValue, restrictedStringValuesPossibilitiesSplit) < 0 : isDiff)\n                                                validatedOptionsPrepared[prop] = isRestrictedValue ? mainPossibility : dataValue;\n                                        }\n                                        else if(writeErrors) {\n                                            console.warn(error + \" it doesn't accept the type [ \" + dataValueType.toUpperCase() + \" ] with the value of \\\"\" + dataValue + \"\\\".\\r\\n\" +\n                                                \"Accepted types are: [ \" + errorPossibleTypes.join(\", \").toUpperCase() + \" ].\" +\n                                                (errorRestrictedStrings[length] > 0 ? \"\\r\\nValid strings are: [ \" + errorRestrictedStrings.join(\", \").split(restrictedStringsPossibilitiesSplit).join(\", \") + \" ].\" : \"\"));\n                                        }\n                                        delete data[prop];\n                                    }\n                                }\n                            }\n                        };\n                        checkObjectProps(objectCopy, template, diffObj || { }, validatedOptions, validatedOptionsPrepared);\n\n                        //add values which aren't specified in the template to the finished validated object to prevent them from being discarded\n                        /*\n                        if(keepForeignProps) {\n                            FRAMEWORK.extend(true, validatedOptions, objectCopy);\n                            FRAMEWORK.extend(true, validatedOptionsPrepared, objectCopy);\n                        }\n                        */\n                        \n                        if(!isEmptyObj(objectCopy) && writeErrors)\n                            console.warn(\"The following options are discarded due to invalidity:\\r\\n\" + window.JSON.stringify(objectCopy, null, 2));\n\n                        return {\n                            _default : validatedOptions,\n                            _prepared : validatedOptionsPrepared\n                        };\n                    }\n                }\n            }());\n\n            /**\n             * Initializes the object which contains global information about the plugin and each instance of it.\n             */\n            function initOverlayScrollbarsStatics() {\n                if(!_pluginsGlobals)\n                    _pluginsGlobals = new OverlayScrollbarsGlobals(_pluginsOptions._defaults);\n                if(!_pluginsAutoUpdateLoop)\n                    _pluginsAutoUpdateLoop = new OverlayScrollbarsAutoUpdateLoop(_pluginsGlobals);\n            }\n\n            /**\n             * The global object for the OverlayScrollbars objects. It contains resources which every OverlayScrollbars object needs. This object is initialized only once: if the first OverlayScrollbars object gets initialized.\n             * @param defaultOptions\n             * @constructor\n             */\n            function OverlayScrollbarsGlobals(defaultOptions) {\n                var _base = this;\n                var strOverflow = 'overflow';\n                var strHidden = 'hidden';\n                var strScroll = 'scroll';\n                var bodyElement = FRAMEWORK('body');\n                var scrollbarDummyElement = FRAMEWORK('<div id=\"os-dummy-scrollbar-size\"><div></div></div>');\n                var scrollbarDummyElement0 = scrollbarDummyElement[0];\n                var dummyContainerChild = FRAMEWORK(scrollbarDummyElement.children('div').eq(0));\n\n                bodyElement.append(scrollbarDummyElement);\n                scrollbarDummyElement.hide().show(); //fix IE8 bug (incorrect measuring)\n\n                var nativeScrollbarSize = calcNativeScrollbarSize(scrollbarDummyElement0);\n                var nativeScrollbarIsOverlaid = {\n                    x: nativeScrollbarSize.x === 0,\n                    y: nativeScrollbarSize.y === 0\n                };\n\n                FRAMEWORK.extend(_base, {\n                    defaultOptions : defaultOptions,\n                    autoUpdateLoop : false,\n                    autoUpdateRecommended : !COMPATIBILITY.mO(),\n                    nativeScrollbarSize : nativeScrollbarSize,\n                    nativeScrollbarIsOverlaid : nativeScrollbarIsOverlaid,\n                    nativeScrollbarStyling : (function() {\n                        var result = false;\n                        scrollbarDummyElement.addClass('os-viewport-native-scrollbars-invisible');\n                        try {\n                            result = scrollbarDummyElement.css('scrollbar-width') === 'none' || window.getComputedStyle(scrollbarDummyElement0, '::-webkit-scrollbar').getPropertyValue('display') === 'none';\n                        } catch (ex) { }\n                        \n                        //fix opera bug: scrollbar styles will only appear if overflow value is scroll or auto during the activation of the style.\n                        //and set overflow to scroll\n                        //scrollbarDummyElement.css(strOverflow, strHidden).hide().css(strOverflow, strScroll).show();\n                        //return (scrollbarDummyElement0[LEXICON.oH] - scrollbarDummyElement0[LEXICON.cH]) === 0 && (scrollbarDummyElement0[LEXICON.oW] - scrollbarDummyElement0[LEXICON.cW]) === 0;\n                        \n                        return result;\n                    })(),\n                    overlayScrollbarDummySize : { x: 30, y: 30 },\n                    msie : (function() {\n                        var ua = window.navigator.userAgent;\n                        var strIndexOf = 'indexOf';\n                        var strSubString = 'substring';\n                        var msie = ua[strIndexOf]('MSIE ');\n                        var trident = ua[strIndexOf]('Trident/');\n                        var edge = ua[strIndexOf]('Edge/');\n                        var rv = ua[strIndexOf]('rv:');\n                        var result;\n                        var parseIntFunc = parseInt;\n\n                        // IE 10 or older => return version number\n                        if (msie > 0)\n                            result = parseIntFunc(ua[strSubString](msie + 5, ua[strIndexOf]('.', msie)), 10);\n\n                        // IE 11 => return version number\n                        else if (trident > 0)\n                            result = parseIntFunc(ua[strSubString](rv + 3, ua[strIndexOf]('.', rv)), 10);\n\n                        // Edge (IE 12+) => return version number\n                        else if (edge > 0)\n                            result = parseIntFunc(ua[strSubString](edge + 5, ua[strIndexOf]('.', edge)), 10);\n\n                        // other browser\n                        return result;\n                    })(),\n                    cssCalc : (function() {\n                        var dummyStyle = document.createElement('div')[LEXICON.s];\n                        var strCalc = 'calc';\n                        var i = -1;\n                        var prop;\n\n                        for(; i < VENDORS._cssPrefixes[LEXICON.l]; i++) {\n                            prop = i < 0 ? strCalc : VENDORS._cssPrefixes[i] + strCalc;\n                            dummyStyle.cssText = 'width:' + prop + '(1px);';\n                            if (dummyStyle[LEXICON.l])\n                                return prop;\n                        }\n                        return null;\n                    })(),\n                    restrictedMeasuring : (function() {\n                        //https://bugzilla.mozilla.org/show_bug.cgi?id=1439305\n                        scrollbarDummyElement.css(strOverflow, strHidden);\n                        var scrollSize = {\n                            w : scrollbarDummyElement0[LEXICON.sW],\n                            h : scrollbarDummyElement0[LEXICON.sH]\n                        };\n                        scrollbarDummyElement.css(strOverflow, 'visible');\n                        var scrollSize2 = {\n                            w : scrollbarDummyElement0[LEXICON.sW],\n                            h : scrollbarDummyElement0[LEXICON.sH]\n                        };\n                        return (scrollSize.w - scrollSize2.w) !== 0 || (scrollSize.h - scrollSize2.h) !== 0;\n                    })(),\n                    rtlScrollBehavior : (function() {\n                        scrollbarDummyElement.css({ 'overflow-y' : strHidden, 'overflow-x' : strScroll, 'direction' : 'rtl' }).scrollLeft(0);\n                        var dummyContainerOffset = scrollbarDummyElement.offset();\n                        var dummyContainerChildOffset = dummyContainerChild.offset();\n                        scrollbarDummyElement.scrollLeft(999);\n                        var dummyContainerScrollOffsetAfterScroll = dummyContainerChild.offset();\n                        return {\n                            //origin direction = determines if the zero scroll position is on the left or right side\n                            //'i' means 'invert' (i === true means that the axis must be inverted to be correct)\n                            //true = on the left side\n                            //false = on the right side\n                            i : dummyContainerOffset.left === dummyContainerChildOffset.left,\n                            //negative = determines if the maximum scroll is positive or negative\n                            //'n' means 'negate' (n === true means that the axis must be negated to be correct)\n                            //true = negative\n                            //false = positive\n                            n : dummyContainerChildOffset.left - dummyContainerScrollOffsetAfterScroll.left === 0\n                        };\n                    })(),\n                    supportTransform : VENDORS._cssProperty('transform') !== null,\n                    supportTransition : VENDORS._cssProperty('transition') !== null,\n                    supportPassiveEvents : (function() {\n                        var supportsPassive = false;\n                        try {\n                            window.addEventListener('test', null, Object.defineProperty({ }, 'passive', {\n                                get: function() {\n                                    supportsPassive = true;\n                                }\n                            }));\n                        } catch (e) { }\n                        return supportsPassive;\n                    })(),\n                    supportResizeObserver : !!COMPATIBILITY.rO(),\n                    supportMutationObserver : !!COMPATIBILITY.mO()\n                });\n\n                scrollbarDummyElement.removeAttr(LEXICON.s).remove();\n\n                //Catch zoom event:\n                (function () {\n                    if(nativeScrollbarIsOverlaid.x && nativeScrollbarIsOverlaid.y)\n                        return;\n\n                    var abs = MATH.abs;\n                    var windowWidth = COMPATIBILITY.wW();\n                    var windowHeight = COMPATIBILITY.wH();\n                    var windowDpr = getWindowDPR();\n                    var onResize = function() {\n                        if(INSTANCES().length > 0) {\n                            var newW = COMPATIBILITY.wW();\n                            var newH = COMPATIBILITY.wH();\n                            var deltaW = newW - windowWidth;\n                            var deltaH = newH - windowHeight;\n\n                            if (deltaW === 0 && deltaH === 0)\n                                return;\n\n                            var deltaWRatio = MATH.round(newW / (windowWidth / 100.0));\n                            var deltaHRatio = MATH.round(newH / (windowHeight / 100.0));\n                            var absDeltaW = abs(deltaW);\n                            var absDeltaH = abs(deltaH);\n                            var absDeltaWRatio = abs(deltaWRatio);\n                            var absDeltaHRatio = abs(deltaHRatio);\n                            var newDPR = getWindowDPR();\n\n                            var deltaIsBigger = absDeltaW > 2 && absDeltaH > 2;\n                            var difference = !differenceIsBiggerThanOne(absDeltaWRatio, absDeltaHRatio);\n                            var dprChanged = newDPR !== windowDpr && windowDpr > 0;\n                            var isZoom = deltaIsBigger && difference && dprChanged;\n                            var oldScrollbarSize = _base.nativeScrollbarSize;\n                            var newScrollbarSize;\n\n                            if (isZoom) {\n                                bodyElement.append(scrollbarDummyElement);\n                                newScrollbarSize = _base.nativeScrollbarSize = calcNativeScrollbarSize(scrollbarDummyElement[0]);\n                                scrollbarDummyElement.remove();\n                                if(oldScrollbarSize.x !== newScrollbarSize.x || oldScrollbarSize.y !== newScrollbarSize.y) {\n                                    FRAMEWORK.each(INSTANCES(), function () {\n                                        if(INSTANCES(this))\n                                            INSTANCES(this).update('zoom');\n                                    });\n                                }\n                            }\n\n                            windowWidth = newW;\n                            windowHeight = newH;\n                            windowDpr = newDPR;\n                        }\n                    };\n\n                    function differenceIsBiggerThanOne(valOne, valTwo) {\n                        var absValOne = abs(valOne);\n                        var absValTwo = abs(valTwo);\n                        return !(absValOne === absValTwo || absValOne + 1 === absValTwo || absValOne - 1 === absValTwo);\n                    }\n\n                    function getWindowDPR() {\n                        var dDPI = window.screen.deviceXDPI || 0;\n                        var sDPI = window.screen.logicalXDPI || 1;\n                        return window.devicePixelRatio || (dDPI / sDPI);\n                    }\n\n                    FRAMEWORK(window).on('resize', onResize);\n                })();\n\n                function calcNativeScrollbarSize(measureElement) {\n                    return {\n                        x: measureElement[LEXICON.oH] - measureElement[LEXICON.cH],\n                        y: measureElement[LEXICON.oW] - measureElement[LEXICON.cW]\n                    };\n                }\n            }\n\n            /**\n             * The object which manages the auto update loop for all OverlayScrollbars objects. This object is initialized only once: if the first OverlayScrollbars object gets initialized.\n             * @constructor\n             */\n            function OverlayScrollbarsAutoUpdateLoop(globals) {\n                var _base = this;\n                var _inArray = FRAMEWORK.inArray;\n                var _getNow = COMPATIBILITY.now;\n                var _strAutoUpdate = 'autoUpdate';\n                var _strAutoUpdateInterval = _strAutoUpdate + 'Interval';\n                var _strLength = LEXICON.l;\n                var _loopingInstances = [ ];\n                var _loopingInstancesIntervalCache = [ ];\n                var _loopIsActive = false;\n                var _loopIntervalDefault = 33;\n                var _loopInterval = _loopIntervalDefault;\n                var _loopTimeOld = _getNow();\n                var _loopID;\n                \n\n                /**\n                 * The auto update loop which will run every 50 milliseconds or less if the update interval of a instance is lower than 50 milliseconds.\n                 */\n                var loop = function() {\n                    if(_loopingInstances[_strLength] > 0 && _loopIsActive) {\n                        _loopID = COMPATIBILITY.rAF()(function () {\n                            loop();\n                        });\n                        var timeNew = _getNow();\n                        var timeDelta = timeNew - _loopTimeOld;\n                        var lowestInterval;\n                        var instance;\n                        var instanceOptions;\n                        var instanceAutoUpdateAllowed;\n                        var instanceAutoUpdateInterval;\n                        var now;\n\n                        if (timeDelta > _loopInterval) {\n                            _loopTimeOld = timeNew - (timeDelta % _loopInterval);\n                            lowestInterval = _loopIntervalDefault;\n                            for(var i = 0; i < _loopingInstances[_strLength]; i++) {\n                                instance = _loopingInstances[i];\n                                if (instance !== undefined) {\n                                    instanceOptions = instance.options();\n                                    instanceAutoUpdateAllowed = instanceOptions[_strAutoUpdate];\n                                    instanceAutoUpdateInterval = MATH.max(1, instanceOptions[_strAutoUpdateInterval]);\n                                    now = _getNow();\n\n                                    if ((instanceAutoUpdateAllowed === true || instanceAutoUpdateAllowed === null) && (now - _loopingInstancesIntervalCache[i]) > instanceAutoUpdateInterval) {\n                                        instance.update('auto');\n                                        _loopingInstancesIntervalCache[i] = new Date(now += instanceAutoUpdateInterval);\n                                    }\n\n                                    lowestInterval = MATH.max(1, MATH.min(lowestInterval, instanceAutoUpdateInterval));\n                                }\n                            }\n                            _loopInterval = lowestInterval;\n                        }\n                    } else {\n                        _loopInterval = _loopIntervalDefault;\n                    }\n                };\n\n                /**\n                 * Add OverlayScrollbars instance to the auto update loop. Only successful if the instance isn't already added.\n                 * @param instance The instance which shall be updated in a loop automatically.\n                 */\n                _base.add = function(instance) {\n                    if(_inArray(instance, _loopingInstances) === -1) {\n                        _loopingInstances.push(instance);\n                        _loopingInstancesIntervalCache.push(_getNow());\n                        if (_loopingInstances[_strLength] > 0 && !_loopIsActive) {\n                            _loopIsActive = true;\n                            globals.autoUpdateLoop = _loopIsActive;\n                            loop();\n                        }\n                    }\n                };\n\n                /**\n                 * Remove OverlayScrollbars instance from the auto update loop. Only successful if the instance was added before.\n                 * @param instance The instance which shall be updated in a loop automatically.\n                 */\n                _base.remove = function(instance) {\n                    var index = _inArray(instance, _loopingInstances);\n                    if(index > -1) {\n                        //remove from loopingInstances list\n                        _loopingInstancesIntervalCache.splice(index, 1);\n                        _loopingInstances.splice(index, 1);\n\n                        //correct update loop behavior\n                        if (_loopingInstances[_strLength] === 0 && _loopIsActive) {\n                            _loopIsActive = false;\n                            globals.autoUpdateLoop = _loopIsActive;\n                            if(_loopID !== undefined) {\n                                COMPATIBILITY.cAF()(_loopID);\n                                _loopID = -1;\n                            }\n                        }\n                    }\n                };\n            }\n\n            /**\n             * A object which manages the scrollbars visibility of the target element.\n             * @param pluginTargetElement The element from which the scrollbars shall be hidden.\n             * @param options The custom options.\n             * @param extensions The custom extensions.\n             * @param globals\n             * @param autoUpdateLoop\n             * @returns {*}\n             * @constructor\n             */\n            function OverlayScrollbarsInstance(pluginTargetElement, options, extensions, globals, autoUpdateLoop) {\n                //shortcuts\n                var type = COMPATIBILITY.type;\n                var inArray = FRAMEWORK.inArray;\n                var each = FRAMEWORK.each;\n                \n                //make correct instanceof\n                var _base = new window[PLUGINNAME]();\n                var _frameworkProto = FRAMEWORK[LEXICON.p];\n                \n                //if passed element is no HTML element: skip and return\n                if(!isHTMLElement(pluginTargetElement))\n                    return;\n                \n                //if passed element is already initialized: set passed options if there are any and return its instance\n                if(INSTANCES(pluginTargetElement)) {\n                    var inst = INSTANCES(pluginTargetElement);\n                    inst.options(options);\n                    return inst;\n                }\n\n                //globals:\n                var _nativeScrollbarIsOverlaid;\n                var _overlayScrollbarDummySize;\n                var _rtlScrollBehavior;\n                var _autoUpdateRecommended;\n                var _msieVersion;\n                var _nativeScrollbarStyling;\n                var _cssCalc;\n                var _nativeScrollbarSize;\n                var _supportTransition;\n                var _supportTransform;\n                var _supportPassiveEvents;\n                var _supportResizeObserver;\n                var _supportMutationObserver;\n                var _restrictedMeasuring;\n\n                //general readonly:\n                var _initialized;\n                var _destroyed;\n                var _isTextarea;\n                var _isBody;\n                var _documentMixed;\n                var _isTextareaHostGenerated;\n\n                //general:\n                var _isBorderBox;\n                var _sizeAutoObserverAdded;\n                var _paddingX;\n                var _paddingY;\n                var _borderX;\n                var _borderY;\n                var _marginX;\n                var _marginY;\n                var _isRTL;\n                var _sleeping;\n                var _contentBorderSize = { };\n                var _scrollHorizontalInfo = { };\n                var _scrollVerticalInfo = { };\n                var _viewportSize = { };\n                var _nativeScrollbarMinSize = { };\n\n                //naming:\n                var _strMinusHidden = '-hidden';\n                var _strMarginMinus = 'margin-';\n                var _strPaddingMinus = 'padding-';\n                var _strBorderMinus = 'border-';\n                var _strTop = 'top';\n                var _strRight = 'right';\n                var _strBottom = 'bottom';\n                var _strLeft = 'left';\n                var _strMinMinus = 'min-';\n                var _strMaxMinus = 'max-';\n                var _strWidth = 'width';\n                var _strHeight = 'height';\n                var _strFloat = 'float';\n                var _strEmpty = '';\n                var _strAuto = 'auto';\n                var _strSync = 'sync';\n                var _strScroll = 'scroll';\n                var _strHundredPercent = '100%';\n                var _strX = 'x';\n                var _strY = 'y';\n                var _strDot = '.';\n                var _strSpace = ' ';\n                var _strScrollbar = 'scrollbar';\n                var _strMinusHorizontal = '-horizontal';\n                var _strMinusVertical = '-vertical';\n                var _strScrollLeft = _strScroll + 'Left';\n                var _strScrollTop = _strScroll + 'Top';\n                var _strMouseTouchDownEvent = 'mousedown touchstart';\n                var _strMouseTouchUpEvent = 'mouseup touchend touchcancel';\n                var _strMouseTouchMoveEvent = 'mousemove touchmove';\n                var _strMouseTouchEnter = 'mouseenter';\n                var _strMouseTouchLeave = 'mouseleave';\n                var _strKeyDownEvent = 'keydown';\n                var _strKeyUpEvent = 'keyup';\n                var _strSelectStartEvent = 'selectstart';\n                var _strTransitionEndEvent = 'transitionend webkitTransitionEnd oTransitionEnd';\n                var _strResizeObserverProperty = '__overlayScrollbarsRO__';\n\n                //class names:\n                var _cassNamesPrefix = 'os-';\n                var _classNameHTMLElement = _cassNamesPrefix + 'html';\n                var _classNameHostElement = _cassNamesPrefix + 'host';\n                var _classNameHostTextareaElement = _classNameHostElement + '-textarea';\n                var _classNameHostScrollbarHorizontalHidden = _classNameHostElement + '-' + _strScrollbar + _strMinusHorizontal + _strMinusHidden;\n                var _classNameHostScrollbarVerticalHidden = _classNameHostElement + '-' + _strScrollbar + _strMinusVertical + _strMinusHidden;\n                var _classNameHostTransition = _classNameHostElement + '-transition';\n                var _classNameHostRTL = _classNameHostElement + '-rtl';\n                var _classNameHostResizeDisabled = _classNameHostElement + '-resize-disabled';\n                var _classNameHostScrolling = _classNameHostElement + '-scrolling';\n                var _classNameHostOverflow = _classNameHostElement + '-overflow';\n                var _classNameHostOverflowX = _classNameHostOverflow + '-x';\n                var _classNameHostOverflowY = _classNameHostOverflow + '-y';\n                var _classNameTextareaElement = _cassNamesPrefix + 'textarea';\n                var _classNameTextareaCoverElement = _classNameTextareaElement + '-cover';\n                var _classNamePaddingElement = _cassNamesPrefix + 'padding';\n                var _classNameViewportElement = _cassNamesPrefix + 'viewport';\n                var _classNameViewportNativeScrollbarsInvisible = _classNameViewportElement + '-native-scrollbars-invisible';\n                var _classNameViewportNativeScrollbarsOverlaid = _classNameViewportElement + '-native-scrollbars-overlaid';\n                var _classNameContentElement = _cassNamesPrefix + 'content';\n                var _classNameContentArrangeElement = _cassNamesPrefix + 'content-arrange';\n                var _classNameContentGlueElement = _cassNamesPrefix + 'content-glue';\n                var _classNameSizeAutoObserverElement = _cassNamesPrefix + 'size-auto-observer';\n                var _classNameResizeObserverElement = _cassNamesPrefix + 'resize-observer';\n                var _classNameResizeObserverItemElement = _cassNamesPrefix + 'resize-observer-item';\n                var _classNameResizeObserverItemFinalElement = _classNameResizeObserverItemElement + '-final';\n                var _classNameTextInherit = _cassNamesPrefix + 'text-inherit';\n                var _classNameScrollbar = _cassNamesPrefix + _strScrollbar;\n                var _classNameScrollbarTrack = _classNameScrollbar + '-track';\n                var _classNameScrollbarTrackOff = _classNameScrollbarTrack + '-off';\n                var _classNameScrollbarHandle = _classNameScrollbar + '-handle';\n                var _classNameScrollbarHandleOff = _classNameScrollbarHandle + '-off';\n                var _classNameScrollbarUnusable = _classNameScrollbar + '-unusable';\n                var _classNameScrollbarAutoHidden = _classNameScrollbar + '-' + _strAuto + _strMinusHidden;\n                var _classNameScrollbarCorner = _classNameScrollbar + '-corner';\n                var _classNameScrollbarCornerResize = _classNameScrollbarCorner + '-resize';\n                var _classNameScrollbarCornerResizeB = _classNameScrollbarCornerResize + '-both';\n                var _classNameScrollbarCornerResizeH = _classNameScrollbarCornerResize + _strMinusHorizontal;\n                var _classNameScrollbarCornerResizeV = _classNameScrollbarCornerResize + _strMinusVertical;\n                var _classNameScrollbarHorizontal = _classNameScrollbar + _strMinusHorizontal;\n                var _classNameScrollbarVertical = _classNameScrollbar + _strMinusVertical;\n                var _classNameDragging = _cassNamesPrefix + 'dragging';\n                var _classNameThemeNone = _cassNamesPrefix + 'theme-none';\n\n                //callbacks:\n                var _callbacksInitQeueue = [ ];\n\n                //options:\n                var _defaultOptions;\n                var _currentOptions;\n                var _currentPreparedOptions;\n\n                //extensions:\n                var _extensions = { };\n                var _extensionsPrivateMethods = 'added removed on contract';\n\n                //update\n                var _lastUpdateTime;\n                var _swallowedUpdateHints = { };\n                var _swallowedUpdateTimeout;\n                var _swallowUpdateLag = 42;\n                var _imgs = [ ];\n\n                //DOM elements:\n                var _windowElement;\n                var _documentElement;\n                var _htmlElement;\n                var _bodyElement;\n                var _targetElement;                     //the target element of this OverlayScrollbars object\n                var _hostElement;                       //the host element of this OverlayScrollbars object -> may be the same as targetElement\n                var _sizeAutoObserverElement;           //observes size auto changes\n                var _sizeObserverElement;               //observes size and padding changes\n                var _paddingElement;                    //manages the padding\n                var _viewportElement;                   //is the viewport of our scrollbar model\n                var _contentElement;                    //the element which holds the content\n                var _contentArrangeElement;             //is needed for correct sizing of the content element (only if native scrollbars are overlays)\n                var _contentGlueElement;                //has always the size of the content element\n                var _textareaCoverElement;              //only applied if target is a textarea element. Used for correct size calculation and for prevention of uncontrolled scrolling\n                var _scrollbarCornerElement;\n                var _scrollbarHorizontalElement;\n                var _scrollbarHorizontalTrackElement;\n                var _scrollbarHorizontalHandleElement;\n                var _scrollbarVerticalElement;\n                var _scrollbarVerticalTrackElement;\n                var _scrollbarVerticalHandleElement;\n                var _windowElementNative;\n                var _documentElementNative;\n                var _targetElementNative;\n                var _hostElementNative;\n                var _sizeAutoObserverElementNative;\n                var _sizeObserverElementNative;\n                var _paddingElementNative;\n                var _viewportElementNative;\n                var _contentElementNative;\n\n                //Cache:\n                var _hostSizeCache;\n                var _contentScrollSizeCache;\n                var _arrangeContentSizeCache;\n                var _hasOverflowCache;\n                var _hideOverflowCache;\n                var _widthAutoCache;\n                var _heightAutoCache;\n                var _cssMaxValueCache;\n                var _cssBoxSizingCache;\n                var _cssPaddingCache;\n                var _cssBorderCache;\n                var _cssMarginCache;\n                var _cssDirectionCache;\n                var _cssDirectionDetectedCache;\n                var _paddingAbsoluteCache;\n                var _clipAlwaysCache;\n                var _contentGlueSizeCache;\n                var _overflowBehaviorCache;\n                var _overflowAmountCache;\n                var _ignoreOverlayScrollbarHidingCache;\n                var _autoUpdateCache;\n                var _sizeAutoCapableCache;\n                var _textareaAutoWrappingCache;\n                var _textareaInfoCache;\n                var _contentElementScrollSizeChangeDetectedCache;\n                var _hostElementSizeChangeDetectedCache;\n                var _scrollbarsVisibilityCache;\n                var _scrollbarsAutoHideCache;\n                var _scrollbarsClickScrollingCache;\n                var _scrollbarsDragScrollingCache;\n                var _resizeCache;\n                var _normalizeRTLCache;\n                var _classNameCache;\n                var _oldClassName;\n                var _textareaDynHeightCache;\n                var _textareaDynWidthCache;\n                var _bodyMinSizeCache;\n                var _viewportScrollSizeCache;\n                var _displayIsHiddenCache;\n                var _updateAutoCache = { };\n\n                //MutationObserver:\n                var _mutationObserverHost;\n                var _mutationObserverContent;\n                var _mutationObserverHostCallback;\n                var _mutationObserverContentCallback;\n                var _mutationObserversConnected;\n                var _mutationObserverAttrsTextarea = ['wrap', 'cols', 'rows'];\n                var _mutationObserverAttrsHost = [LEXICON.i, LEXICON.c, LEXICON.s, 'open'];\n\n                //textarea:\n                var _textareaEvents;\n                var _textareaHasFocus;\n\n                //scrollbars:\n                var _scrollbarsAutoHideTimeoutId;\n                var _scrollbarsAutoHideMoveTimeoutId;\n                var _scrollbarsAutoHideDelay;\n                var _scrollbarsAutoHideNever;\n                var _scrollbarsAutoHideScroll;\n                var _scrollbarsAutoHideMove;\n                var _scrollbarsAutoHideLeave;\n                var _scrollbarsHandleHovered;\n                var _scrollbarsHandlesDefineScrollPos;\n\n                //resize\n                var _resizeReconnectMutationObserver;\n                var _resizeNone;\n                var _resizeBoth;\n                var _resizeHorizontal;\n                var _resizeVertical;\n                var _resizeOnMouseTouchDown;\n                \n                \n                //==== Passive Event Listener ====//\n\n                /**\n                 * Adds or removes a passive event listener from the given element.\n                 * @param element The element to which the event listener shall be applied or removed.\n                 * @param eventNames The name(s) of the events.\n                 * @param listener The method which shall be called.\n                 * @param remove True if the handler shall be removed, false or undefined if the handler shall be added.\n                 */\n                function setupPassiveEventListener(element, eventNames, listener, remove, notPassive) {\n                    var method = remove ? 'removeEventListener' : 'addEventListener';\n                    var events = eventNames.split(_strSpace);\n                    var i = 0;\n\n                    for (; i < events[LEXICON.l]; i++) {\n                        element[0][method](events[i], listener, { passive: !notPassive });\n                    }\n                }\n\n\n                //==== Resize Observer ====//\n\n                /**\n                 * Adds or removes a resize observer from the given element.\n                 * @param targetElement The element to which the resize observer shall be added or removed.\n                 * @param onElementResizedCallback The callback which is fired every time the resize observer registers a size change or false / undefined if the resizeObserver shall be removed.\n                 */\n                function setupResizeObserver(targetElement, onElementResizedCallback) {\n                    if(targetElement) {\n                        //add resize observer:\n                        if(onElementResizedCallback) {\n                            var constMaximum = 3333333;\n                            var resizeObserver = COMPATIBILITY.rO();\n                            var strAnimationStartEvent = 'animationstart mozAnimationStart webkitAnimationStart MSAnimationStart';\n                            var strChildNodes = 'childNodes';\n                            var callback = function () {\n                                targetElement[_strScrollTop](constMaximum)[_strScrollLeft](_isRTL ? _rtlScrollBehavior.n ? -constMaximum : _rtlScrollBehavior.i ? 0 : constMaximum : constMaximum);\n                                onElementResizedCallback();\n                            };\n                            if (_supportResizeObserver) {\n                                var element = targetElement.append(generateDiv(_classNameResizeObserverElement + ' observed')).contents()[0];\n                                var observer = element[_strResizeObserverProperty] = new resizeObserver(callback);\n                                observer.observe(element);\n                            }\n                            else {\n                                if (_msieVersion > 9 || !_autoUpdateRecommended) {\n                                    targetElement.prepend(\n                                        generateDiv(_classNameResizeObserverElement,\n                                            generateDiv({ className : _classNameResizeObserverItemElement, dir : \"ltr\" },\n                                                generateDiv(_classNameResizeObserverItemElement,\n                                                    generateDiv(_classNameResizeObserverItemFinalElement)\n                                                ) +\n                                                generateDiv(_classNameResizeObserverItemElement,\n                                                    generateDiv({ className : _classNameResizeObserverItemFinalElement, style : 'width: 200%; height: 200%' })\n                                                )\n                                            )\n                                        )\n                                    );\n\n                                    var observerElement = targetElement[0][strChildNodes][0][strChildNodes][0];\n                                    var shrinkElement = FRAMEWORK(observerElement[strChildNodes][1]);\n                                    var expandElement = FRAMEWORK(observerElement[strChildNodes][0]);\n                                    var expandElementChild = FRAMEWORK(expandElement[0][strChildNodes][0]);\n                                    var widthCache = observerElement[LEXICON.oW];\n                                    var heightCache = observerElement[LEXICON.oH];\n                                    var isDirty;\n                                    var rAFId;\n                                    var currWidth;\n                                    var currHeight;\n                                    var factor = 2;\n                                    var nativeScrollbarSize = globals.nativeScrollbarSize; //care don't make changes to this object!!!\n                                    var reset = function () {\n                                        /*\n                                         var sizeResetWidth = observerElement[LEXICON.oW] + nativeScrollbarSize.x * factor + nativeScrollbarSize.y * factor + _overlayScrollbarDummySize.x + _overlayScrollbarDummySize.y;\n                                         var sizeResetHeight = observerElement[LEXICON.oH] + nativeScrollbarSize.x * factor + nativeScrollbarSize.y * factor + _overlayScrollbarDummySize.x + _overlayScrollbarDummySize.y;\n                                         var expandChildCSS = {};\n                                         expandChildCSS[_strWidth] = sizeResetWidth;\n                                         expandChildCSS[_strHeight] = sizeResetHeight;\n                                         expandElementChild.css(expandChildCSS);\n\n\n                                         expandElement[_strScrollLeft](sizeResetWidth)[_strScrollTop](sizeResetHeight);\n                                         shrinkElement[_strScrollLeft](sizeResetWidth)[_strScrollTop](sizeResetHeight);\n                                         */\n                                        expandElement[_strScrollLeft](constMaximum)[_strScrollTop](constMaximum);\n                                        shrinkElement[_strScrollLeft](constMaximum)[_strScrollTop](constMaximum);\n                                    };\n                                    var onResized = function () {\n                                        rAFId = 0;\n                                        if (!isDirty)\n                                            return;\n\n                                        widthCache = currWidth;\n                                        heightCache = currHeight;\n                                        callback();\n                                    };\n                                    var onScroll = function (event) {\n                                        currWidth = observerElement[LEXICON.oW];\n                                        currHeight = observerElement[LEXICON.oH];\n                                        isDirty = currWidth != widthCache || currHeight != heightCache;\n\n                                        if (event && isDirty && !rAFId) {\n                                            COMPATIBILITY.cAF()(rAFId);\n                                            rAFId = COMPATIBILITY.rAF()(onResized);\n                                        }\n                                        else if(!event)\n                                            onResized();\n\n                                        reset();\n                                        if (event) {\n                                            COMPATIBILITY.prvD(event);\n                                            COMPATIBILITY.stpP(event);\n                                        }\n                                        return false;\n                                    };\n                                    var expandChildCSS = {};\n                                    var observerElementCSS = {};\n\n                                    setTopRightBottomLeft(observerElementCSS, _strEmpty, [\n                                        -((nativeScrollbarSize.y + 1) * factor),\n                                        nativeScrollbarSize.x * -factor,\n                                        nativeScrollbarSize.y * -factor,\n                                        -((nativeScrollbarSize.x + 1) * factor)\n                                    ]);\n\n                                    FRAMEWORK(observerElement).css(observerElementCSS);\n                                    expandElement.on(_strScroll, onScroll);\n                                    shrinkElement.on(_strScroll, onScroll);\n                                    targetElement.on(strAnimationStartEvent, function () {\n                                        onScroll(false);\n                                    });\n                                    //lets assume that the divs will never be that large and a constant value is enough\n                                    expandChildCSS[_strWidth] = constMaximum;\n                                    expandChildCSS[_strHeight] = constMaximum;\n                                    expandElementChild.css(expandChildCSS);\n\n                                    reset();\n                                }\n                                else {\n                                    var attachEvent = _documentElementNative.attachEvent;\n                                    var isIE = _msieVersion !== undefined;\n                                    if (attachEvent) {\n                                        targetElement.prepend(generateDiv(_classNameResizeObserverElement));\n                                        findFirst(targetElement, _strDot + _classNameResizeObserverElement)[0].attachEvent('onresize', callback);\n                                    }\n                                    else {\n                                        var obj = _documentElementNative.createElement(TYPES.o);\n                                        obj.setAttribute('tabindex', '-1');\n                                        obj.setAttribute(LEXICON.c, _classNameResizeObserverElement);\n                                        obj.onload = function () {\n                                            var wnd = this.contentDocument.defaultView;\n                                            wnd.addEventListener('resize', callback);\n                                            wnd.document.documentElement.style.display = 'none';\n                                        };\n                                        obj.type = 'text/html';\n                                        if (isIE)\n                                            targetElement.prepend(obj);\n                                        obj.data = 'about:blank';\n                                        if (!isIE)\n                                            targetElement.prepend(obj);\n                                        targetElement.on(strAnimationStartEvent, callback);\n                                    }\n                                }\n                            }\n\n                            //direction change detection:\n                            if (targetElement[0] === _sizeObserverElementNative) {\n                                var directionChanged = function () {\n                                    var dir = _hostElement.css('direction');\n                                    var css = {};\n                                    var scrollLeftValue = 0;\n                                    var result = false;\n                                    if (dir !== _cssDirectionDetectedCache) {\n                                        if (dir === 'ltr') {\n                                            css[_strLeft] = 0;\n                                            css[_strRight] = _strAuto;\n                                            scrollLeftValue = constMaximum;\n                                        }\n                                        else {\n                                            css[_strLeft] = _strAuto;\n                                            css[_strRight] = 0;\n                                            scrollLeftValue = _rtlScrollBehavior.n ? -constMaximum : _rtlScrollBehavior.i ? 0 : constMaximum;\n                                        }\n                                        _sizeObserverElement.children().eq(0).css(css);\n                                        targetElement[_strScrollLeft](scrollLeftValue)[_strScrollTop](constMaximum);\n                                        _cssDirectionDetectedCache = dir;\n                                        result = true;\n                                    }\n                                    return result;\n                                };\n                                directionChanged();\n                                targetElement.on(_strScroll, function (event) {\n                                    if (directionChanged())\n                                        update();\n                                    COMPATIBILITY.prvD(event);\n                                    COMPATIBILITY.stpP(event);\n                                    return false;\n                                });\n                            }\n                        }\n                        //remove resize observer:\n                        else {\n                            if (_supportResizeObserver) {\n                                var element = targetElement.contents()[0];\n                                var resizeObserverObj = element[_strResizeObserverProperty];\n                                if(resizeObserverObj) {\n                                    resizeObserverObj.disconnect();\n                                    delete element[_strResizeObserverProperty];\n                                }\n                            }\n                            else {\n                                remove(targetElement.children(_strDot + _classNameResizeObserverElement).eq(0));\n                            }\n                        }\n                    }\n                }\n\n                /**\n                 * Freezes or unfreezes the given resize observer.\n                 * @param targetElement The element to which the target resize observer is applied.\n                 * @param freeze True if the resize observer shall be frozen, false otherwise.\n                 \n                function freezeResizeObserver(targetElement, freeze) {\n                    if (targetElement !== undefined) {\n                        if(freeze) {\n                            if (_supportResizeObserver) {\n                                var element = targetElement.contents()[0];\n                                element[_strResizeObserverProperty].unobserve(element);\n                            }\n                            else {\n                                targetElement = targetElement.children(_strDot + _classNameResizeObserverElement).eq(0);\n                                var w = targetElement.css(_strWidth);\n                                var h = targetElement.css(_strHeight);\n                                var css = {};\n                                css[_strWidth] = w;\n                                css[_strHeight] = h;\n                                targetElement.css(css);\n                            }\n                        }\n                        else {\n                            if (_supportResizeObserver) {\n                                var element = targetElement.contents()[0];\n                                element[_strResizeObserverProperty].observe(element);\n                            }\n                            else {\n                                var css = { };\n                                css[_strHeight] = _strEmpty;\n                                css[_strWidth] = _strEmpty;\n                                targetElement.children(_strDot + _classNameResizeObserverElement).eq(0).css(css);\n                            }\n                        }\n                    }\n                }\n                */\n\n\n                //==== Mutation Observers ====//\n\n                /**\n                 * Creates MutationObservers for the host and content Element if they are supported.\n                 */\n                function createMutationObservers() {\n                    if (_supportMutationObserver) {\n                        var mutationObserverContentLag = 11;\n                        var mutationObserver = COMPATIBILITY.mO();\n                        var contentLastUpdate = COMPATIBILITY.now();\n                        var mutationTarget;\n                        var mutationAttrName;\n                        var contentTimeout;\n                        var now;\n                        var sizeAuto;\n                        var action;\n\n                        _mutationObserverHostCallback = function(mutations) {\n                            var doUpdate = false;\n                            var mutation;\n                                \n                            if (_initialized && !_sleeping) {\n                                each(mutations, function () {\n                                    mutation = this;\n                                    mutationTarget = mutation.target;\n                                    mutationAttrName = mutation.attributeName;\n\n                                    if (mutationAttrName === LEXICON.c)\n                                        doUpdate = hostClassNamesChanged(mutation.oldValue, mutationTarget.className);\n                                    else if (mutationAttrName === LEXICON.s)\n                                        doUpdate = mutation.oldValue !== mutationTarget[LEXICON.s].cssText;\n                                    else\n                                        doUpdate = true;\n\n                                    if (doUpdate)\n                                        return false;\n                                });\n\n                                if (doUpdate)\n                                    _base.update(_strAuto);\n                            }\n                            return doUpdate;\n                        };\n                        _mutationObserverContentCallback = function (mutations) {\n                            var doUpdate = false;\n                            var mutation;\n                            \n                            if (_initialized && !_sleeping) {\n                                each(mutations, function () {\n                                    mutation = this;\n                                    doUpdate = isUnknownMutation(mutation);\n                                    return !doUpdate;\n                                });\n\n                                if (doUpdate) {\n                                    now = COMPATIBILITY.now();\n                                    sizeAuto = (_heightAutoCache || _widthAutoCache);\n                                    action = function () {\n                                        if(!_destroyed) {\n                                            contentLastUpdate = now;\n\n                                            //if cols, rows or wrap attr was changed\n                                            if (_isTextarea)\n                                                textareaUpdate();\n\n                                            if (sizeAuto)\n                                                update();\n                                            else\n                                                _base.update(_strAuto);\n                                        }\n                                    };\n                                    clearTimeout(contentTimeout);\n                                    if (mutationObserverContentLag <= 0 || now - contentLastUpdate > mutationObserverContentLag || !sizeAuto)\n                                        action();\n                                    else\n                                        contentTimeout = setTimeout(action, mutationObserverContentLag);\n                                }\n                            }\n                            return doUpdate;\n                        }\n\n                        _mutationObserverHost = new mutationObserver(_mutationObserverHostCallback);\n                        _mutationObserverContent = new mutationObserver(_mutationObserverContentCallback);\n                    }\n                }\n\n                /**\n                 * Connects the MutationObservers if they are supported.\n                 */\n                function connectMutationObservers() {\n                    if (_supportMutationObserver && !_mutationObserversConnected) {\n                        _mutationObserverHost.observe(_hostElementNative, {\n                            attributes: true,\n                            attributeOldValue: true,\n                            attributeFilter: _mutationObserverAttrsHost\n                        });\n\n                        _mutationObserverContent.observe(_isTextarea ? _targetElementNative : _contentElementNative, {\n                            attributes: true,\n                            attributeOldValue: true,\n                            subtree: !_isTextarea,\n                            childList: !_isTextarea,\n                            characterData: !_isTextarea,\n                            attributeFilter: _isTextarea ? _mutationObserverAttrsTextarea : _mutationObserverAttrsHost\n                        });\n\n                        _mutationObserversConnected = true;\n                    }\n                }\n\n                /**\n                 * Disconnects the MutationObservers if they are supported.\n                 */\n                function disconnectMutationObservers() {\n                    if (_supportMutationObserver && _mutationObserversConnected) {\n                        _mutationObserverHost.disconnect();\n                        _mutationObserverContent.disconnect();\n\n                        _mutationObserversConnected = false;\n                    }\n                }\n\n               \n               //==== Events of elements ====//\n\n                /**\n                 * This method gets called every time the host element gets resized. IMPORTANT: Padding changes are detected too!!\n                 * It refreshes the hostResizedEventArgs and the hostSizeResizeCache.\n                 * If there are any size changes, the update method gets called.\n                 */\n                function hostOnResized() {\n                    if (!_sleeping) {\n                        var changed;\n                        var hostSize = {\n                            w: _sizeObserverElementNative[LEXICON.sW],\n                            h: _sizeObserverElementNative[LEXICON.sH]\n                        };\n                        \n                        changed = checkCache(hostSize, _hostElementSizeChangeDetectedCache);\n                        _hostElementSizeChangeDetectedCache = hostSize;\n                        if (changed)\n                            update({ _hostSizeChanged : true });\n                    }\n                }\n\n                /**\n                 * The mouse enter event of the host element. This event is only needed for the autoHide feature.\n                 */\n                function hostOnMouseEnter() {\n                    if (_scrollbarsAutoHideLeave)\n                        refreshScrollbarsAutoHide(true);\n                }\n\n                /**\n                 * The mouse leave event of the host element. This event is only needed for the autoHide feature.\n                 */\n                function hostOnMouseLeave() {\n                    if (_scrollbarsAutoHideLeave && !_bodyElement.hasClass(_classNameDragging))\n                        refreshScrollbarsAutoHide(false);\n                }\n\n                /**\n                 * The mouse move event of the host element. This event is only needed for the autoHide \"move\" feature.\n                 */\n                function hostOnMouseMove() {\n                    if (_scrollbarsAutoHideMove) {\n                        refreshScrollbarsAutoHide(true);\n                        clearTimeout(_scrollbarsAutoHideMoveTimeoutId);\n                        _scrollbarsAutoHideMoveTimeoutId = setTimeout(function () {\n                            if (_scrollbarsAutoHideMove && !_destroyed)\n                                refreshScrollbarsAutoHide(false);\n                        }, 100);\n                    }\n                }\n\n                 /**\n                 * Adds or removes mouse & touch events of the host element. (for handling auto-hiding of the scrollbars)\n                 * @param destroy Indicates whether the events shall be added or removed.\n                 */\n                function setupHostMouseTouchEvents(destroy) {\n                    var strOnOff = destroy ? 'off' : 'on';\n                    var setupEvent = function(target, name, listener) {\n                        if(_supportPassiveEvents)\n                            setupPassiveEventListener(target, name, listener, destroy);\n                        else\n                            target[strOnOff](name, listener);\n                    };\n\n                    if(_scrollbarsAutoHideMove && !destroy)\n                        setupEvent(_hostElement, _strMouseTouchMoveEvent, hostOnMouseMove);\n                    else {\n                        if(destroy)\n                            setupEvent(_hostElement, _strMouseTouchMoveEvent, hostOnMouseMove);\n                        setupEvent(_hostElement, _strMouseTouchEnter, hostOnMouseEnter);\n                        setupEvent(_hostElement, _strMouseTouchLeave, hostOnMouseLeave);\n                    }\n\n                    //if the plugin is initialized and the mouse is over the host element, make the scrollbars visible\n                    if(!_initialized && !destroy)\n                        _hostElement.one(\"mouseover\", hostOnMouseEnter);\n                }\n\n                /**\n                 * Prevents text from deselection if attached to the document element on the mousedown event of a DOM element.\n                 * @param event The select start event.\n                 */\n                function documentOnSelectStart(event) {\n                    COMPATIBILITY.prvD(event);\n                    return false;\n                }\n\n                /**\n                 * A callback which will be called after a img element has downloaded its src asynchronous.\n                 */\n                function imgOnLoad() {\n                    update({ _contentSizeChanged : true });\n                }\n\n\n                //==== Update Detection ====//\n\n                /**\n                 * Measures the min width and min height of the body element and refreshes the related cache.\n                 * @returns {boolean} True if the min width or min height has changed, false otherwise.\n                 */\n                function bodyMinSizeChanged() {\n                    var bodyMinSize = {};\n                    if (_isBody && _contentArrangeElement) {\n                        bodyMinSize.w = parseToZeroOrNumber(_contentArrangeElement.css(_strMinMinus + _strWidth));\n                        bodyMinSize.h = parseToZeroOrNumber(_contentArrangeElement.css(_strMinMinus + _strHeight));\n                        bodyMinSize.c = checkCache(bodyMinSize, _bodyMinSizeCache);\n                        bodyMinSize.f = true; //flag for \"measured at least once\"\n                    }\n                    _bodyMinSizeCache = bodyMinSize;\n                    return !!bodyMinSize.c;\n                }\n\n                /**\n                 * Returns true if the class names really changed (new class without plugin host prefix)\n                 * @param oldCassNames The old ClassName string.\n                 * @param newClassNames The new ClassName string.\n                 * @returns {boolean} True if the class names has really changed, false otherwise.\n                 */\n                function hostClassNamesChanged(oldCassNames, newClassNames) {\n                    var currClasses = (newClassNames !== undefined && newClassNames !== null) ? newClassNames.split(_strSpace) : _strEmpty;\n                    var oldClasses = (oldCassNames !== undefined && oldCassNames !== null) ? oldCassNames.split(_strSpace) : _strEmpty;\n                    if (currClasses === _strEmpty && oldClasses === _strEmpty)\n                        return false;\n                    var diff = getArrayDifferences(oldClasses, currClasses);\n                    var changed = false;\n                    var oldClassNames = _oldClassName !== undefined && _oldClassName !== null ? _oldClassName.split(_strSpace) : [_strEmpty];\n                    var currClassNames = _classNameCache !== undefined && _classNameCache !== null ? _classNameCache.split(_strSpace) : [_strEmpty];\n\n                    //remove none theme from diff list to prevent update\n                    var idx = inArray(_classNameThemeNone, diff);\n                    var curr;\n                    var i;\n                    var v;\n                    var o;\n                    var c;\n\n                    if (idx > -1)\n                        diff.splice(idx, 1);\n\n                    for (i = 0; i < diff.length; i++) {\n                        curr = diff[i];\n                        if (curr.indexOf(_classNameHostElement) !== 0) {\n                            o = true;\n                            c = true;\n                            for (v = 0; v < oldClassNames.length; v++) {\n                                if (curr === oldClassNames[v]) {\n                                    o = false;\n                                    break;\n                                }\n                            }\n                            for (v = 0; v < currClassNames.length; v++) {\n                                if (curr === currClassNames[v]) {\n                                    c = false;\n                                    break;\n                                }\n                            }\n                            if (o && c) {\n                                changed = true;\n                                break;\n                            }\n                        }\n\n                    }\n                    return changed;\n                }\n\n                /**\n                 * Returns true if the given mutation is not from a from the plugin generated element. If the target element is a textarea the mutation is always unknown.\n                 * @param mutation The mutation which shall be checked.\n                 * @returns {boolean} True if the mutation is from a unknown element, false otherwise.\n                 */\n                function isUnknownMutation(mutation) {\n                    var attributeName = mutation.attributeName;\n                    var mutationTarget = mutation.target;\n                    var mutationType = mutation.type;\n                    var strClosest = 'closest';\n\n                    if (mutationTarget === _contentElementNative)\n                        return attributeName === null;\n                    if (mutationType === 'attributes' && (attributeName === LEXICON.c || attributeName === LEXICON.s) && !_isTextarea) {\n                        //ignore className changes by the plugin\n                        if (attributeName === LEXICON.c && FRAMEWORK(mutationTarget).hasClass(_classNameHostElement))\n                            return hostClassNamesChanged(mutation.oldValue, mutationTarget.getAttribute(LEXICON.c));\n\n                        //only do it of browser support it natively\n                        if (typeof mutationTarget[strClosest] != TYPES.f)\n                            return true;\n                        if (mutationTarget[strClosest](_strDot + _classNameResizeObserverElement) !== null ||\n                            mutationTarget[strClosest](_strDot + _classNameScrollbar) !== null ||\n                            mutationTarget[strClosest](_strDot + _classNameScrollbarCorner) !== null)\n                            return false;\n                    }\n                    return true;\n                }\n\n                /**\n                 * Returns true if the content size was changed since the last time this method was called.\n                 * @returns {boolean} True if the content size was changed, false otherwise.\n                 */\n                function updateAutoContentSizeChanged() {\n                    if (_sleeping)\n                        return false;\n                    \n                    var contentMeasureElement = getContentMeasureElement();\n                    var textareaValueLength = _isTextarea && _widthAutoCache && !_textareaAutoWrappingCache ? _targetElement.val().length : 0;\n                    var setCSS = !_mutationObserversConnected && _widthAutoCache && !_isTextarea;\n                    var viewportScrollSize = { };\n                    var css = { };\n                    var float;\n                    var bodyMinSizeC;\n                    var changed;\n                    var viewportScrollSizeChanged;\n                    var contentElementScrollSize;\n\n                    //fix for https://bugzilla.mozilla.org/show_bug.cgi?id=1439305, it only works with \"clipAlways : true\"\n                    //it can work with \"clipAlways : false\" too, but I had to set the overflow of the viewportElement to hidden every time before measuring\n                    if(_restrictedMeasuring) {\n                        viewportScrollSize = {\n                            x : _viewportElementNative[LEXICON.sW],\n                            y : _viewportElementNative[LEXICON.sH]\n                        }\n                    }\n                    if (setCSS) {\n                        float = _contentElement.css(_strFloat);\n                        css[_strFloat] = _isRTL ? _strRight : _strLeft;\n                        css[_strWidth] = _strAuto;\n                        _contentElement.css(css);\n                    }\n                    contentElementScrollSize = {\n                        w: contentMeasureElement[LEXICON.sW] + textareaValueLength,\n                        h: contentMeasureElement[LEXICON.sH] + textareaValueLength\n                    };\n                    if (setCSS) {\n                        css[_strFloat] = float;\n                        css[_strWidth] = _strHundredPercent;\n                        _contentElement.css(css);\n                    }\n\n                    bodyMinSizeC = bodyMinSizeChanged();\n                    changed = checkCache(contentElementScrollSize, _contentElementScrollSizeChangeDetectedCache);\n                    viewportScrollSizeChanged = checkCache(viewportScrollSize, _viewportScrollSizeCache);\n\n                    _contentElementScrollSizeChangeDetectedCache = contentElementScrollSize;\n                    _viewportScrollSizeCache = viewportScrollSize;\n\n                    return changed || bodyMinSizeC || viewportScrollSizeChanged;\n                }\n\n                /**\n                 * Returns true when a attribute which the MutationObserver would observe has changed.  \n                 * @returns {boolean} True if one of the attributes which a MutationObserver would observe has changed, false or undefined otherwise.\n                 */\n                function meaningfulAttrsChanged() {\n                    if (_sleeping || _mutationObserversConnected)\n                        return;\n                    \n                    var changed;\n                    var elem;\n                    var curr;\n                    var cache;\n                    var checks = [\n                        {\n                            _elem: _hostElement, \n                            _props : _mutationObserverAttrsHost.concat(':visible')\n                        },\n                        {\n                            _elem: _isTextarea ? _targetElement : undefined, \n                            _props : _mutationObserverAttrsTextarea\n                        }\n                    ];\n                    \n                    each(checks, function(index, check) { \n                        elem = check._elem;\n                        if(elem) {\n                            each(check._props, function(index, prop) { \n                                curr = prop.charAt(0) === ':' ? elem.is(prop) : elem.attr(prop);\n                                cache = _updateAutoCache[prop];\n                                \n                                changed = changed || checkCache(curr, cache);\n                                \n                                _updateAutoCache[prop] = curr;\n                            });\n                        }\n                    });\n                    \n                    return changed;\n                }\n\n                /**\n                 * Checks is a CSS Property of a child element is affecting the scroll size of the content.\n                 * @param propertyName The CSS property name.\n                 * @returns {boolean} True if the property is affecting the content scroll size, false otherwise.\n                 */\n                function isSizeAffectingCSSProperty(propertyName) {\n                    if (!_initialized)\n                        return true;\n                    var flexGrow = 'flex-grow';\n                    var flexShrink = 'flex-shrink';\n                    var flexBasis = 'flex-basis';\n                    var affectingPropsX = [\n                        _strWidth,\n                        _strMinMinus + _strWidth,\n                        _strMaxMinus + _strWidth,\n                        _strMarginMinus + _strLeft,\n                        _strMarginMinus + _strRight,\n                        _strLeft,\n                        _strRight,\n                        'font-weight',\n                        'word-spacing',\n                        flexGrow,\n                        flexShrink,\n                        flexBasis\n                    ];\n                    var affectingPropsXContentBox = [\n                        _strPaddingMinus + _strLeft,\n                        _strPaddingMinus + _strRight,\n                        _strBorderMinus + _strLeft + _strWidth,\n                        _strBorderMinus + _strRight + _strWidth\n                    ];\n                    var affectingPropsY = [\n                        _strHeight,\n                        _strMinMinus + _strHeight,\n                        _strMaxMinus + _strHeight,\n                        _strMarginMinus + _strTop,\n                        _strMarginMinus + _strBottom,\n                        _strTop,\n                        _strBottom,\n                        'line-height',\n                        flexGrow,\n                        flexShrink,\n                        flexBasis\n                    ];\n                    var affectingPropsYContentBox = [\n                        _strPaddingMinus + _strTop,\n                        _strPaddingMinus + _strBottom,\n                        _strBorderMinus + _strTop + _strWidth,\n                        _strBorderMinus + _strBottom + _strWidth\n                    ];\n                    var _strS = 's';\n                    var _strVS = 'v-s';\n                    var checkX = _overflowBehaviorCache.x === _strS || _overflowBehaviorCache.x === _strVS;\n                    var checkY = _overflowBehaviorCache.y === _strS || _overflowBehaviorCache.y === _strVS;\n                    var sizeIsAffected = false;\n                    var checkPropertyName = function (arr, name) {\n                        for (var i = 0; i < arr[LEXICON.l]; i++) {\n                            if (arr[i] === name)\n                                return true;\n                        }\n                        return false;\n                    };\n\n                    if (checkY) {\n                        sizeIsAffected = checkPropertyName(affectingPropsY, propertyName);\n                        if (!sizeIsAffected && !_isBorderBox)\n                            sizeIsAffected = checkPropertyName(affectingPropsYContentBox, propertyName);\n                    }\n                    if (checkX && !sizeIsAffected) {\n                        sizeIsAffected = checkPropertyName(affectingPropsX, propertyName);\n                        if (!sizeIsAffected && !_isBorderBox)\n                            sizeIsAffected = checkPropertyName(affectingPropsXContentBox, propertyName);\n                    }\n                    return sizeIsAffected;\n                }\n\n                \n                //==== Update ====//\n\n                /**\n                 * Updates the variables and size of the textarea element, and manages the scroll on new line or new character.\n                 */\n                function textareaUpdate() {\n                    if (!_sleeping) {\n                        var wrapAttrOff = !_textareaAutoWrappingCache;\n                        var minWidth = _viewportSize.w;\n                        var minHeight = _viewportSize.h;\n                        var css = { };\n                        var doMeasure = _widthAutoCache || wrapAttrOff;\n                        var origWidth;\n                        var width;\n                        var origHeight;\n                        var height;\n\n                        //reset min size\n                        css[_strMinMinus + _strWidth] = _strEmpty;\n                        css[_strMinMinus + _strHeight] = _strEmpty;\n\n                        //set width auto\n                        css[_strWidth] = _strAuto;\n                        _targetElement.css(css);\n\n                        //measure width\n                        origWidth = _targetElementNative[LEXICON.oW];\n                        width = doMeasure ? MATH.max(origWidth, _targetElementNative[LEXICON.sW] - 1) : 1;\n                        /*width += (_widthAutoCache ? _marginX + (!_isBorderBox ? wrapAttrOff ? 0 : _paddingX + _borderX : 0) : 0);*/\n\n                        //set measured width\n                        css[_strWidth] = _widthAutoCache ? _strAuto /*width*/ : _strHundredPercent;\n                        css[_strMinMinus + _strWidth] = _strHundredPercent;\n\n                        //set height auto\n                        css[_strHeight] = _strAuto;\n                        _targetElement.css(css);\n\n                        //measure height\n                        origHeight = _targetElementNative[LEXICON.oH];\n                        height = MATH.max(origHeight, _targetElementNative[LEXICON.sH] - 1);\n\n                        //append correct size values\n                        css[_strWidth] = width;\n                        css[_strHeight] = height;\n                        _textareaCoverElement.css(css);\n\n                        //apply min width / min height to prevent textarea collapsing\n                        css[_strMinMinus + _strWidth] = minWidth /*+ (!_isBorderBox && _widthAutoCache ? _paddingX + _borderX : 0)*/;\n                        css[_strMinMinus + _strHeight] = minHeight /*+ (!_isBorderBox && _heightAutoCache ? _paddingY + _borderY : 0)*/;\n                        _targetElement.css(css);\n\n                        return {\n                            _originalWidth: origWidth,\n                            _originalHeight: origHeight,\n                            _dynamicWidth: width,\n                            _dynamicHeight: height\n                        };\n                    }\n                }\n\n                /**\n                 * Updates the plugin and DOM to the current options.\n                 * This method should only be called if a update is 100% required.\n                 * @param updateHints A objects which contains hints for this update:\n                 * {\n                 *   _hostSizeChanged : boolean,\n                 *   _contentSizeChanged : boolean,\n                 *   _force : boolean,                             == preventSwallowing\n                 *   _changedOptions : { },                        == preventSwallowing && preventSleep\n                *  }\n                 */\n                function update(updateHints) {\n                    clearTimeout(_swallowedUpdateTimeout);\n                    updateHints = updateHints || { };\n                    _swallowedUpdateHints._hostSizeChanged |= updateHints._hostSizeChanged;\n                    _swallowedUpdateHints._contentSizeChanged |= updateHints._contentSizeChanged;\n                    _swallowedUpdateHints._force |= updateHints._force;\n                    \n                    var now = COMPATIBILITY.now();\n                    var hostSizeChanged = !!_swallowedUpdateHints._hostSizeChanged;\n                    var contentSizeChanged = !!_swallowedUpdateHints._contentSizeChanged;\n                    var force = !!_swallowedUpdateHints._force;\n                    var changedOptions = updateHints._changedOptions;    \n                    var swallow = _swallowUpdateLag > 0 && _initialized && !_destroyed && !force && !changedOptions && (now - _lastUpdateTime) < _swallowUpdateLag && (!_heightAutoCache && !_widthAutoCache);                    \n                    var displayIsHidden;\n\n                    if(swallow)\n                        _swallowedUpdateTimeout = setTimeout(update, _swallowUpdateLag);\n\n                    //abort update due to:\n                    //destroyed\n                    //swallowing\n                    //sleeping\n                    //host is hidden or has false display\n                    if (_destroyed || swallow || (_sleeping && !changedOptions) || (_initialized && !force && (displayIsHidden = _hostElement.is(':hidden'))) || _hostElement.css('display') === 'inline')\n                        return;\n\n                    _lastUpdateTime = now;\n                    _swallowedUpdateHints = { };\n                    \n                    //if scrollbar styling is possible and native scrollbars aren't overlaid the scrollbar styling will be applied which hides the native scrollbars completely.\n                    if (_nativeScrollbarStyling && !(_nativeScrollbarIsOverlaid.x && _nativeScrollbarIsOverlaid.y)) {\n                        //native scrollbars are hidden, so change the values to zero\n                        _nativeScrollbarSize.x = 0;\n                        _nativeScrollbarSize.y = 0;\n                    }\n                    else {\n                        //refresh native scrollbar size (in case of zoom)\n                        _nativeScrollbarSize = extendDeep({}, globals.nativeScrollbarSize);\n                    }\n\n                    // Scrollbar padding is needed for firefox, because firefox hides scrollbar automatically if the size of the div is too small.\n                    // The calculation: [scrollbar size +3 *3]\n                    // (+3 because of possible decoration e.g. borders, margins etc., but only if native scrollbar is NOT a overlaid scrollbar)\n                    // (*3 because (1)increase / (2)decrease -button and (3)resize handle)\n                    _nativeScrollbarMinSize = {\n                        x: (_nativeScrollbarSize.x + (_nativeScrollbarIsOverlaid.x ? 0 : 3)) * 3,\n                        y: (_nativeScrollbarSize.y + (_nativeScrollbarIsOverlaid.y ? 0 : 3)) * 3\n                    };\n                    \n                    //changedOptions = changedOptions || { };\n                    //freezeResizeObserver(_sizeObserverElement, true);\n                    //freezeResizeObserver(_sizeAutoObserverElement, true);\n                    \n                    var checkCacheAutoForce = function () {\n                        return checkCache.apply(this, [].slice.call(arguments).concat([ force ]));\n                    };\n                    \n                    //save current scroll offset\n                    var currScroll = {\n                        x: _viewportElement[_strScrollLeft](),\n                        y: _viewportElement[_strScrollTop]()\n                    };\n\n                    var currentPreparedOptionsScrollbars = _currentPreparedOptions.scrollbars;\n                    var currentPreparedOptionsTextarea = _currentPreparedOptions.textarea;\n\n                    //scrollbars visibility:\n                    var scrollbarsVisibility = currentPreparedOptionsScrollbars.visibility;\n                    var scrollbarsVisibilityChanged = checkCacheAutoForce(scrollbarsVisibility, _scrollbarsVisibilityCache);\n\n                    //scrollbars autoHide:\n                    var scrollbarsAutoHide = currentPreparedOptionsScrollbars.autoHide;\n                    var scrollbarsAutoHideChanged = checkCacheAutoForce(scrollbarsAutoHide, _scrollbarsAutoHideCache);\n\n                    //scrollbars click scrolling\n                    var scrollbarsClickScrolling = currentPreparedOptionsScrollbars.clickScrolling;\n                    var scrollbarsClickScrollingChanged = checkCacheAutoForce(scrollbarsClickScrolling, _scrollbarsClickScrollingCache);\n\n                    //scrollbars drag scrolling\n                    var scrollbarsDragScrolling = currentPreparedOptionsScrollbars.dragScrolling;\n                    var scrollbarsDragScrollingChanged = checkCacheAutoForce(scrollbarsDragScrolling, _scrollbarsDragScrollingCache);\n\n                    //className\n                    var className = _currentPreparedOptions.className;\n                    var classNameChanged = checkCacheAutoForce(className, _classNameCache);\n\n                    //resize\n                    var resize = _currentPreparedOptions.resize;\n                    var resizeChanged = checkCacheAutoForce(resize, _resizeCache) && !_isBody; //body can't be resized since the window itself acts as resize possibility.\n\n                    //paddingAbsolute\n                    var paddingAbsolute = _currentPreparedOptions.paddingAbsolute;\n                    var paddingAbsoluteChanged = checkCacheAutoForce(paddingAbsolute, _paddingAbsoluteCache);\n\n                    //clipAlways\n                    var clipAlways = _currentPreparedOptions.clipAlways;\n                    var clipAlwaysChanged = checkCacheAutoForce(clipAlways, _clipAlwaysCache);\n\n                    //sizeAutoCapable\n                    var sizeAutoCapable = _currentPreparedOptions.sizeAutoCapable && !_isBody; //body can never be size auto, because it shall be always as big as the viewport.\n                    var sizeAutoCapableChanged = checkCacheAutoForce(sizeAutoCapable, _sizeAutoCapableCache);\n\n                    //showNativeScrollbars\n                    var ignoreOverlayScrollbarHiding = _currentPreparedOptions.nativeScrollbarsOverlaid.showNativeScrollbars;\n                    var ignoreOverlayScrollbarHidingChanged = checkCacheAutoForce(ignoreOverlayScrollbarHiding, _ignoreOverlayScrollbarHidingCache);\n\n                    //autoUpdate\n                    var autoUpdate = _currentPreparedOptions.autoUpdate;\n                    var autoUpdateChanged = checkCacheAutoForce(autoUpdate, _autoUpdateCache);\n\n                    //overflowBehavior\n                    var overflowBehavior = _currentPreparedOptions.overflowBehavior;\n                    var overflowBehaviorChanged = checkCacheAutoForce(overflowBehavior, _overflowBehaviorCache, force);\n\n                    //dynWidth:\n                    var textareaDynWidth = currentPreparedOptionsTextarea.dynWidth;\n                    var textareaDynWidthChanged = checkCacheAutoForce(_textareaDynWidthCache, textareaDynWidth);\n\n                    //dynHeight:\n                    var textareaDynHeight = currentPreparedOptionsTextarea.dynHeight;\n                    var textareaDynHeightChanged = checkCacheAutoForce(_textareaDynHeightCache, textareaDynHeight);\n\n                    //scrollbars visibility\n                    _scrollbarsAutoHideNever = scrollbarsAutoHide === 'n';\n                    _scrollbarsAutoHideScroll = scrollbarsAutoHide === 's';\n                    _scrollbarsAutoHideMove = scrollbarsAutoHide === 'm';\n                    _scrollbarsAutoHideLeave = scrollbarsAutoHide === 'l';\n\n                    //scrollbars autoHideDelay\n                    _scrollbarsAutoHideDelay = currentPreparedOptionsScrollbars.autoHideDelay;\n\n                    //old className\n                    _oldClassName = _classNameCache;\n\n                    //resize\n                    _resizeNone = resize === 'n';\n                    _resizeBoth = resize === 'b';\n                    _resizeHorizontal = resize === 'h';\n                    _resizeVertical = resize === 'v';\n\n                    //normalizeRTL\n                    _normalizeRTLCache = _currentPreparedOptions.normalizeRTL;\n\n                    //ignore overlay scrollbar hiding\n                    ignoreOverlayScrollbarHiding = ignoreOverlayScrollbarHiding && (_nativeScrollbarIsOverlaid.x && _nativeScrollbarIsOverlaid.y);\n\n                    //refresh options cache\n                    _scrollbarsVisibilityCache = scrollbarsVisibility;\n                    _scrollbarsAutoHideCache = scrollbarsAutoHide;\n                    _scrollbarsClickScrollingCache = scrollbarsClickScrolling;\n                    _scrollbarsDragScrollingCache = scrollbarsDragScrolling;\n                    _classNameCache = className;\n                    _resizeCache = resize;\n                    _paddingAbsoluteCache = paddingAbsolute;\n                    _clipAlwaysCache = clipAlways;\n                    _sizeAutoCapableCache = sizeAutoCapable;\n                    _ignoreOverlayScrollbarHidingCache = ignoreOverlayScrollbarHiding;\n                    _autoUpdateCache = autoUpdate;\n                    _overflowBehaviorCache = extendDeep({}, overflowBehavior);\n                    _textareaDynWidthCache = textareaDynWidth;\n                    _textareaDynHeightCache = textareaDynHeight;\n                    _hasOverflowCache = _hasOverflowCache || { x: false, y: false };\n\n                    //set correct class name to the host element\n                    if (classNameChanged) {\n                        removeClass(_hostElement, _oldClassName + _strSpace + _classNameThemeNone);\n                        addClass(_hostElement, className !== undefined && className !== null && className.length > 0 ? className : _classNameThemeNone);\n                    }\n\n                    //set correct auto Update\n                    if (autoUpdateChanged) {\n                        if (autoUpdate === true) {\n                            disconnectMutationObservers();\n                            autoUpdateLoop.add(_base);\n                        }\n                        else if (autoUpdate === null) {\n                            if (_autoUpdateRecommended) {\n                                disconnectMutationObservers();\n                                autoUpdateLoop.add(_base);\n                            }\n                            else {\n                                autoUpdateLoop.remove(_base);\n                                connectMutationObservers();\n                            }\n                        }\n                        else {\n                            autoUpdateLoop.remove(_base);\n                            connectMutationObservers();\n                        }\n                    }\n\n                    //activate or deactivate size auto capability\n                    if (sizeAutoCapableChanged) {\n                        if (sizeAutoCapable) {\n                            if (!_contentGlueElement) {\n                                _contentGlueElement = FRAMEWORK(generateDiv(_classNameContentGlueElement));\n                                _paddingElement.before(_contentGlueElement);\n                            }\n                            else {\n                                _contentGlueElement.show();\n                            }\n                            if (_sizeAutoObserverAdded) {\n                                _sizeAutoObserverElement.show();\n                            }\n                            else {\n                                _sizeAutoObserverElement = FRAMEWORK(generateDiv(_classNameSizeAutoObserverElement));\n                                _sizeAutoObserverElementNative = _sizeAutoObserverElement[0];\n\n                                _contentGlueElement.before(_sizeAutoObserverElement);\n                                var oldSize = {w: -1, h: -1};\n                                setupResizeObserver(_sizeAutoObserverElement, function () {\n                                    var newSize = {\n                                        w: _sizeAutoObserverElementNative[LEXICON.oW],\n                                        h: _sizeAutoObserverElementNative[LEXICON.oH]\n                                    };\n                                    if (checkCache(newSize, oldSize)) {\n                                        if (_initialized && (_heightAutoCache && newSize.h > 0) || (_widthAutoCache && newSize.w > 0)) {\n                                            update();\n                                        }\n                                        else if (_initialized && (!_heightAutoCache && newSize.h === 0) || (!_widthAutoCache && newSize.w === 0)) {\n                                            update();\n                                        }\n                                    }\n                                    oldSize = newSize;\n                                });\n                                _sizeAutoObserverAdded = true;\n                                //fix heightAuto detector bug if height is fixed but contentHeight is 0.\n                                //the probability this bug will ever happen is very very low, thats why its ok if we use calc which isn't supported in IE8.\n                                if (_cssCalc !== null)\n                                    _sizeAutoObserverElement.css(_strHeight, _cssCalc + '(100% + 1px)');\n                            }\n                        }\n                        else {\n                            if (_sizeAutoObserverAdded)\n                                _sizeAutoObserverElement.hide();\n                            if (_contentGlueElement)\n                                _contentGlueElement.hide();\n                        }\n                    }\n\n                    //if force, update all resizeObservers too\n                    if (force) {\n                        _sizeObserverElement.find('*').trigger(_strScroll);\n                        if (_sizeAutoObserverAdded)\n                            _sizeAutoObserverElement.find('*').trigger(_strScroll);\n                    }\n\n                    //display hidden:\n                    displayIsHidden = displayIsHidden === undefined ? _hostElement.is(':hidden') : displayIsHidden;\n                    var displayIsHiddenChanged = checkCacheAutoForce(displayIsHidden, _displayIsHiddenCache);\n\n                    //textarea AutoWrapping:\n                    var textareaAutoWrapping = _isTextarea ? _targetElement.attr('wrap') !== 'off' : false;\n                    var textareaAutoWrappingChanged = checkCacheAutoForce(textareaAutoWrapping, _textareaAutoWrappingCache);\n\n                    //detect direction:\n                    var cssDirection = _hostElement.css('direction');\n                    var cssDirectionChanged = checkCacheAutoForce(cssDirection, _cssDirectionCache);\n\n                    //detect box-sizing:\n                    var boxSizing = _hostElement.css('box-sizing');\n                    var boxSizingChanged = checkCacheAutoForce(boxSizing, _cssBoxSizingCache);\n\n                    //detect padding:\n                    var padding = {\n                        c: force,\n                        t: parseToZeroOrNumber(_hostElement.css(_strPaddingMinus + _strTop)),\n                        r: parseToZeroOrNumber(_hostElement.css(_strPaddingMinus + _strRight)),\n                        b: parseToZeroOrNumber(_hostElement.css(_strPaddingMinus + _strBottom)),\n                        l: parseToZeroOrNumber(_hostElement.css(_strPaddingMinus + _strLeft))\n                    };\n                    \n                    //width + height auto detecting var:\n                    var sizeAutoObserverElementBCRect;\n                    //exception occurs in IE8 sometimes (unknown exception)\n                    try {\n                        sizeAutoObserverElementBCRect = _sizeAutoObserverAdded ? _sizeAutoObserverElementNative.getBoundingClientRect() : null;\n                    } catch (ex) {\n                        return;\n                    }\n\n                    _isRTL = cssDirection === 'rtl';\n                    _isBorderBox = (boxSizing === 'border-box');\n                    var isRTLLeft = _isRTL ? _strLeft : _strRight;\n                    var isRTLRight = _isRTL ? _strRight : _strLeft;\n\n                    //detect width auto:\n                    var widthAutoResizeDetection = false;\n                    var widthAutoObserverDetection = (_sizeAutoObserverAdded && (_hostElement.css(_strFloat) !== 'none' /*|| _isTextarea */)) ? (MATH.round(sizeAutoObserverElementBCRect.right - sizeAutoObserverElementBCRect.left) === 0) && (!paddingAbsolute ? (_hostElementNative[LEXICON.cW] - _paddingX) > 0 : true) : false;\n                    if (sizeAutoCapable && !widthAutoObserverDetection) {\n                        var tmpCurrHostWidth = _hostElementNative[LEXICON.oW];\n                        var tmpCurrContentGlueWidth = _contentGlueElement.css(_strWidth);\n                        _contentGlueElement.css(_strWidth, _strAuto);\n\n                        var tmpNewHostWidth = _hostElementNative[LEXICON.oW];\n                        _contentGlueElement.css(_strWidth, tmpCurrContentGlueWidth);\n                        widthAutoResizeDetection = tmpCurrHostWidth !== tmpNewHostWidth;\n                        if (!widthAutoResizeDetection) {\n                            _contentGlueElement.css(_strWidth, tmpCurrHostWidth + 1);\n                            tmpNewHostWidth = _hostElementNative[LEXICON.oW];\n                            _contentGlueElement.css(_strWidth, tmpCurrContentGlueWidth);\n                            widthAutoResizeDetection = tmpCurrHostWidth !== tmpNewHostWidth;\n                        }\n                    }\n                    var widthAuto = (widthAutoObserverDetection || widthAutoResizeDetection) && sizeAutoCapable && !displayIsHidden;\n                    var widthAutoChanged = checkCacheAutoForce(widthAuto, _widthAutoCache);\n                    var wasWidthAuto = !widthAuto && _widthAutoCache;\n\n                    //detect height auto:\n                    var heightAuto = _sizeAutoObserverAdded && sizeAutoCapable && !displayIsHidden ? (MATH.round(sizeAutoObserverElementBCRect.bottom - sizeAutoObserverElementBCRect.top) === 0) /* && (!paddingAbsolute && (_msieVersion > 9 || !_msieVersion) ? true : true) */ : false;\n                    var heightAutoChanged = checkCacheAutoForce(heightAuto, _heightAutoCache);\n                    var wasHeightAuto = !heightAuto && _heightAutoCache;\n\n                    //detect border:\n                    //we need the border only if border box and auto size\n                    var strMinusWidth = '-' + _strWidth;\n                    var updateBorderX = (widthAuto && _isBorderBox) || !_isBorderBox;\n                    var updateBorderY = (heightAuto && _isBorderBox) || !_isBorderBox;\n                    var border = {\n                        c: force,\n                        t: updateBorderY ? parseToZeroOrNumber(_hostElement.css(_strBorderMinus + _strTop + strMinusWidth), true) : 0,\n                        r: updateBorderX ? parseToZeroOrNumber(_hostElement.css(_strBorderMinus + _strRight + strMinusWidth), true) : 0,\n                        b: updateBorderY ? parseToZeroOrNumber(_hostElement.css(_strBorderMinus + _strBottom + strMinusWidth), true) : 0,\n                        l: updateBorderX ? parseToZeroOrNumber(_hostElement.css(_strBorderMinus + _strLeft + strMinusWidth), true) : 0\n                    };\n\n                    //detect margin:\n                    var margin = {\n                        c: force,\n                        t: parseToZeroOrNumber(_hostElement.css(_strMarginMinus + _strTop)),\n                        r: parseToZeroOrNumber(_hostElement.css(_strMarginMinus + _strRight)),\n                        b: parseToZeroOrNumber(_hostElement.css(_strMarginMinus + _strBottom)),\n                        l: parseToZeroOrNumber(_hostElement.css(_strMarginMinus + _strLeft))\n                    };\n\n                    //detect css max width & height:\n                    var cssMaxValue = {\n                        h: String(_hostElement.css(_strMaxMinus + _strHeight)),\n                        w: String(_hostElement.css(_strMaxMinus + _strWidth))\n                    };\n\n                    //vars to apply correct css\n                    var contentElementCSS = { };\n                    var contentGlueElementCSS = { };\n\n                    //funcs\n                    var getHostSize = function() {\n                        //has to be clientSize because offsetSize respect borders\n                        return {\n                            w: _hostElementNative[LEXICON.cW],\n                            h: _hostElementNative[LEXICON.cH]\n                        };\n                    };\n                    var getViewportSize = function() {\n                        //viewport size is padding container because it never has padding, margin and a border\n                        //determine zoom rounding error -> sometimes scrollWidth/Height is smaller than clientWidth/Height\n                        //if this happens add the difference to the viewportSize to compensate the rounding error\n                        return {\n                            w: _paddingElementNative[LEXICON.oW] + MATH.max(0, _contentElementNative[LEXICON.cW] - _contentElementNative[LEXICON.sW]),\n                            h: _paddingElementNative[LEXICON.oH] + MATH.max(0, _contentElementNative[LEXICON.cH] - _contentElementNative[LEXICON.sH])\n                        };\n                    };\n\n                    //set info for padding\n                    var paddingAbsoluteX = _paddingX = padding.l + padding.r;\n                    var paddingAbsoluteY = _paddingY = padding.t + padding.b;\n                    paddingAbsoluteX *= paddingAbsolute ? 1 : 0;\n                    paddingAbsoluteY *= paddingAbsolute ? 1 : 0;\n                    padding.c = checkCacheAutoForce(padding, _cssPaddingCache);\n\n                    //set info for border\n                    _borderX = border.l + border.r;\n                    _borderY = border.t + border.b;\n                    border.c = checkCacheAutoForce(border, _cssBorderCache);\n\n                    //set info for margin\n                    _marginX = margin.l + margin.r;\n                    _marginY = margin.t + margin.b;\n                    margin.c = checkCacheAutoForce(margin, _cssMarginCache);\n\n                    //set info for css max value\n                    cssMaxValue.ih = parseToZeroOrNumber(cssMaxValue.h); //ih = integer height\n                    cssMaxValue.iw = parseToZeroOrNumber(cssMaxValue.w); //iw = integer width\n                    cssMaxValue.ch = cssMaxValue.h.indexOf('px') > -1; //ch = correct height\n                    cssMaxValue.cw = cssMaxValue.w.indexOf('px') > -1; //cw = correct width\n                    cssMaxValue.c = checkCacheAutoForce(cssMaxValue, _cssMaxValueCache);\n\n                    //refresh cache\n                    _displayIsHiddenCache = displayIsHidden;\n                    _textareaAutoWrappingCache = textareaAutoWrapping;\n                    _cssDirectionCache = cssDirection;\n                    _cssBoxSizingCache = boxSizing;\n                    _widthAutoCache = widthAuto;\n                    _heightAutoCache = heightAuto;\n                    _cssPaddingCache = padding;\n                    _cssBorderCache = border;\n                    _cssMarginCache = margin;\n                    _cssMaxValueCache = cssMaxValue;\n                        \n                    //IEFix direction changed\n                    if (cssDirectionChanged && _sizeAutoObserverAdded)\n                        _sizeAutoObserverElement.css(_strFloat, isRTLRight);\n\n                    //apply padding:\n                    if (padding.c || cssDirectionChanged || paddingAbsoluteChanged || widthAutoChanged || heightAutoChanged || boxSizingChanged || sizeAutoCapableChanged) {\n                        var paddingElementCSS = {};\n                        var textareaCSS = {};\n                        setTopRightBottomLeft(contentGlueElementCSS, _strMarginMinus, [-padding.t, -padding.r, -padding.b, -padding.l]);\n                        if (paddingAbsolute) {\n                            setTopRightBottomLeft(paddingElementCSS, _strEmpty, [padding.t, padding.r, padding.b, padding.l]);\n                            if (_isTextarea)\n                                setTopRightBottomLeft(textareaCSS, _strPaddingMinus);\n                            else\n                                setTopRightBottomLeft(contentElementCSS, _strPaddingMinus);\n                        }\n                        else {\n                            setTopRightBottomLeft(paddingElementCSS, _strEmpty);\n                            if (_isTextarea)\n                                setTopRightBottomLeft(textareaCSS, _strPaddingMinus, [padding.t, padding.r, padding.b, padding.l]);\n                            else\n                                setTopRightBottomLeft(contentElementCSS, _strPaddingMinus, [padding.t, padding.r, padding.b, padding.l]);\n                        }\n                        _paddingElement.css(paddingElementCSS);\n                        _targetElement.css(textareaCSS);\n                    }\n\n                    //viewport size is padding container because it never has padding, margin and a border.\n                    _viewportSize = getViewportSize();\n\n                    //update Textarea\n                    var textareaSize = _isTextarea ? textareaUpdate() : false;\n                    var textareaDynOrigSize = _isTextarea && textareaSize ? {\n                        w : textareaDynWidth ? textareaSize._dynamicWidth : textareaSize._originalWidth,\n                        h : textareaDynHeight ? textareaSize._dynamicHeight : textareaSize._originalHeight\n                    } : { };\n                    \n                    //fix height auto / width auto in cooperation with current padding & boxSizing behavior:\n                    if (heightAuto && (heightAutoChanged || paddingAbsoluteChanged || boxSizingChanged || cssMaxValue.c || padding.c || border.c)) {\n                        //if (cssMaxValue.ch)\n                        contentElementCSS[_strMaxMinus + _strHeight] =\n                            (cssMaxValue.ch ? (cssMaxValue.ih - paddingAbsoluteY + (_isBorderBox ? -_borderY : _paddingY))\n                            : _strEmpty);\n                        contentElementCSS[_strHeight] = _strAuto;\n                    }\n                    else if (heightAutoChanged || paddingAbsoluteChanged) {\n                        contentElementCSS[_strMaxMinus + _strHeight] = _strEmpty;\n                        contentElementCSS[_strHeight] = _strHundredPercent;\n                    }\n                    if (widthAuto && (widthAutoChanged || paddingAbsoluteChanged || boxSizingChanged || cssMaxValue.c || padding.c || border.c || cssDirectionChanged)) {\n                        //if (cssMaxValue.cw)\n                        contentElementCSS[_strMaxMinus + _strWidth] =\n                            (cssMaxValue.cw ? (cssMaxValue.iw - paddingAbsoluteX + (_isBorderBox ? -_borderX : _paddingX)) +\n                            (_nativeScrollbarIsOverlaid.y /*&& _hasOverflowCache.y && widthAuto */ ? _overlayScrollbarDummySize.y : 0)\n                            : _strEmpty);\n                        contentElementCSS[_strWidth] = _strAuto;\n                        contentGlueElementCSS[_strMaxMinus + _strWidth] = _strHundredPercent; //IE Fix\n                    }\n                    else if (widthAutoChanged || paddingAbsoluteChanged) {\n                        contentElementCSS[_strMaxMinus + _strWidth] = _strEmpty;\n                        contentElementCSS[_strWidth] = _strHundredPercent;\n                        contentElementCSS[_strFloat] = _strEmpty;\n                        contentGlueElementCSS[_strMaxMinus + _strWidth] = _strEmpty; //IE Fix\n                    }\n                    if (widthAuto) {\n                        if (!cssMaxValue.cw)\n                            contentElementCSS[_strMaxMinus + _strWidth] = _strEmpty;\n                        //textareaDynOrigSize.w || _strAuto :: doesnt works because applied margin will shift width\n                        contentGlueElementCSS[_strWidth] = _strAuto;\n\n                        contentElementCSS[_strWidth] = _strAuto;\n                        contentElementCSS[_strFloat] = isRTLRight;\n                    }\n                    else {\n                        contentGlueElementCSS[_strWidth] = _strEmpty;\n                    }\n                    if (heightAuto) {\n                        if (!cssMaxValue.ch)\n                            contentElementCSS[_strMaxMinus + _strHeight] = _strEmpty;\n                        //textareaDynOrigSize.h || _contentElementNative[LEXICON.cH] :: use for anti scroll jumping\n                        contentGlueElementCSS[_strHeight] = textareaDynOrigSize.h || _contentElementNative[LEXICON.cH];\n                    }\n                    else {\n                        contentGlueElementCSS[_strHeight] = _strEmpty;\n                    }\n                    if (sizeAutoCapable)\n                        _contentGlueElement.css(contentGlueElementCSS);\n                    _contentElement.css(contentElementCSS);\n\n                    //CHECKPOINT HERE ~\n                    contentElementCSS = {};\n                    contentGlueElementCSS = {};\n\n                    //if [content(host) client / scroll size, or target element direction, or content(host) max-sizes] changed, or force is true\n                    if (hostSizeChanged || contentSizeChanged || cssDirectionChanged || boxSizingChanged || paddingAbsoluteChanged || widthAutoChanged || widthAuto || heightAutoChanged || heightAuto || cssMaxValue.c || ignoreOverlayScrollbarHidingChanged || overflowBehaviorChanged || clipAlwaysChanged || resizeChanged || scrollbarsVisibilityChanged || scrollbarsAutoHideChanged || scrollbarsDragScrollingChanged || scrollbarsClickScrollingChanged || textareaDynWidthChanged || textareaDynHeightChanged || textareaAutoWrappingChanged) {\n                        var strOverflow = 'overflow';\n                        var strOverflowX = strOverflow + '-x';\n                        var strOverflowY = strOverflow + '-y';\n                        var strHidden = 'hidden';\n                        var strVisible = 'visible';\n                        //decide whether the content overflow must get hidden for correct overflow measuring, it !MUST! be always hidden if the height is auto\n                        var hideOverflow4CorrectMeasuring = _restrictedMeasuring ?\n                        (_nativeScrollbarIsOverlaid.x || _nativeScrollbarIsOverlaid.y) || //it must be hidden if native scrollbars are overlaid\n                        (_viewportSize.w < _nativeScrollbarMinSize.y || _viewportSize.h < _nativeScrollbarMinSize.x) || //it must be hidden if host-element is too small\n                        heightAuto || displayIsHiddenChanged //it must be hidden if height is auto or display was changed\n                            : heightAuto; //if there is not the restricted Measuring bug, it must be hidden if the height is auto\n\n                        //Reset the viewport (very important for natively overlaid scrollbars and zoom change\n                        //don't change the overflow prop as it is very expensive and affects performance !A LOT!\n                        var viewportElementResetCSS = { };\n                        var resetXTmp = _hasOverflowCache.y && _hideOverflowCache.ys && !ignoreOverlayScrollbarHiding ? (_nativeScrollbarIsOverlaid.y ? _viewportElement.css(isRTLLeft) : -_nativeScrollbarSize.y) : 0;\n                        var resetBottomTmp = _hasOverflowCache.x && _hideOverflowCache.xs && !ignoreOverlayScrollbarHiding ? (_nativeScrollbarIsOverlaid.x ? _viewportElement.css(_strBottom) : -_nativeScrollbarSize.x) : 0;\n                        setTopRightBottomLeft(viewportElementResetCSS, _strEmpty);\n                        _viewportElement.css(viewportElementResetCSS);\n                        if(hideOverflow4CorrectMeasuring)\n                            _contentElement.css(strOverflow, strHidden);\n\n                        //measure several sizes:\n                        var contentMeasureElement = getContentMeasureElement();\n                        //in Firefox content element has to have overflow hidden, else element margins aren't calculated properly, this element prevents this bug, but only if scrollbars aren't overlaid\n                        var contentMeasureElementGuaranty = _restrictedMeasuring && !hideOverflow4CorrectMeasuring ? _viewportElementNative : contentMeasureElement;\n                        var contentSize = {\n                            //use clientSize because natively overlaidScrollbars add borders\n                            w: textareaDynOrigSize.w || contentMeasureElement[LEXICON.cW],\n                            h: textareaDynOrigSize.h || contentMeasureElement[LEXICON.cH]\n                        };\n                        var scrollSize = {\n                            w: MATH.max(contentMeasureElement[LEXICON.sW], contentMeasureElementGuaranty[LEXICON.sW]),\n                            h: MATH.max(contentMeasureElement[LEXICON.sH], contentMeasureElementGuaranty[LEXICON.sH])\n                        };\n\n                        //apply the correct viewport style and measure viewport size\n                        viewportElementResetCSS[_strBottom] = wasHeightAuto ? _strEmpty : resetBottomTmp;\n                        viewportElementResetCSS[isRTLLeft] = wasWidthAuto ? _strEmpty : resetXTmp;\n                        _viewportElement.css(viewportElementResetCSS);\n                        _viewportSize = getViewportSize();\n\n                        //measure and correct several sizes\n                        var hostSize = getHostSize();\n                        var contentGlueSize = {\n                            //client/scrollSize + AbsolutePadding -> because padding is only applied to the paddingElement if its absolute, so you have to add it manually\n                            //hostSize is clientSize -> so padding should be added manually, right? FALSE! Because content glue is inside hostElement, so we don't have to worry about padding\n                            w: MATH.max((widthAuto ? contentSize.w : scrollSize.w) + paddingAbsoluteX, hostSize.w),\n                            h: MATH.max((heightAuto ? contentSize.h : scrollSize.h) + paddingAbsoluteY, hostSize.h)\n                        };\n                        contentGlueSize.c = checkCacheAutoForce(contentGlueSize, _contentGlueSizeCache);\n                        _contentGlueSizeCache = contentGlueSize;\n\n                        //apply correct contentGlue size\n                        if (sizeAutoCapable) {\n                            //size contentGlue correctly to make sure the element has correct size if the sizing switches to auto\n                            if (contentGlueSize.c || (heightAuto || widthAuto)) {\n                                contentGlueElementCSS[_strWidth] = contentGlueSize.w;\n                                contentGlueElementCSS[_strHeight] = contentGlueSize.h;\n\n                                //textarea-sizes are already calculated correctly at this point\n                                if(!_isTextarea) {\n                                    contentSize = {\n                                        //use clientSize because natively overlaidScrollbars add borders\n                                        w: contentMeasureElement[LEXICON.cW],\n                                        h: contentMeasureElement[LEXICON.cH]\n                                    };\n                                }\n                            }\n                            var textareaCoverCSS = {};\n                            var setContentGlueElementCSSfunction = function(horizontal) {\n                                var scrollbarVars = getScrollbarVars(horizontal);\n                                var wh = scrollbarVars._w_h;\n                                var strWH = scrollbarVars._width_height;\n                                var autoSize = horizontal ? widthAuto : heightAuto;\n                                var borderSize = horizontal ? _borderX : _borderY;\n                                var paddingSize = horizontal ? _paddingX : _paddingY;\n                                var marginSize = horizontal ? _marginX : _marginY;\n                                var maxSize = contentGlueElementCSS[strWH] + (_isBorderBox ? borderSize : -paddingSize);\n\n                                //make contentGlue size -1 if element is not auto sized, to make sure that a resize event happens when the element shrinks\n                                if (!autoSize || (!autoSize && border.c))\n                                    contentGlueElementCSS[strWH] = hostSize[wh] - (_isBorderBox ? 0 : paddingSize + borderSize) - 1 - marginSize;\n\n                                //if size is auto and host is same size as max size, make content glue size +1 to make sure size changes will be detected\n                                if (autoSize && cssMaxValue['c' + wh] && cssMaxValue['i' + wh] === maxSize)\n                                    contentGlueElementCSS[strWH] = maxSize + (_isBorderBox ? 0 : paddingSize) + 1;\n\n                                //if size is auto and host is smaller than size as min size, make content glue size -1 to make sure size changes will be detected (this is only needed if padding is 0)\n                                if (autoSize && (contentSize[wh] < _viewportSize[wh]) && (horizontal ? (_isTextarea ? !textareaAutoWrapping : false) : true)) {\n                                    if (_isTextarea)\n                                        textareaCoverCSS[strWH] = parseToZeroOrNumber(_textareaCoverElement.css(strWH)) - 1;\n                                    contentGlueElementCSS[strWH] -= 1;\n                                }\n\n                                //make sure content glue size is at least 1\n                                if (contentSize[wh] > 0)\n                                    contentGlueElementCSS[strWH] = MATH.max(1, contentGlueElementCSS[strWH]);\n                            };\n                            setContentGlueElementCSSfunction(true);\n                            setContentGlueElementCSSfunction(false);\n\n                            if (_isTextarea)\n                                _textareaCoverElement.css(textareaCoverCSS);\n                            _contentGlueElement.css(contentGlueElementCSS);\n                        }\n                        if (widthAuto)\n                            contentElementCSS[_strWidth] = _strHundredPercent;\n                        if (widthAuto && !_isBorderBox && !_mutationObserversConnected)\n                            contentElementCSS[_strFloat] = 'none';\n\n                        //apply and reset content style\n                        _contentElement.css(contentElementCSS);\n                        contentElementCSS = {};\n\n                        //measure again, but this time all correct sizes:\n                        var contentScrollSize = {\n                            w: MATH.max(contentMeasureElement[LEXICON.sW], contentMeasureElementGuaranty[LEXICON.sW]),\n                            h: MATH.max(contentMeasureElement[LEXICON.sH], contentMeasureElementGuaranty[LEXICON.sH])\n                        };\n                        contentScrollSize.c = contentSizeChanged = checkCacheAutoForce(contentScrollSize, _contentScrollSizeCache);\n                        _contentScrollSizeCache = contentScrollSize;\n\n                        //remove overflow hidden to restore overflow\n                        if(hideOverflow4CorrectMeasuring)\n                            _contentElement.css(strOverflow, _strEmpty);\n                        \n                        //refresh viewport size after correct measuring\n                        _viewportSize = getViewportSize();\n\n                        hostSize = getHostSize();\n                        hostSizeChanged = checkCacheAutoForce(hostSize, _hostSizeCache);\n                        _hostSizeCache = hostSize;\n\n                        var hideOverflowForceTextarea = _isTextarea && (_viewportSize.w === 0 || _viewportSize.h === 0);\n                        var previousOverflow = _overflowAmountCache;\n                        var overflowBehaviorIsVS = { };\n                        var overflowBehaviorIsVH = { };\n                        var overflowBehaviorIsS = { };\n                        var overflowAmount = { };\n                        var hasOverflow = { };\n                        var hideOverflow = { };\n                        var canScroll = { };\n                        var viewportRect = _paddingElementNative.getBoundingClientRect();\n                        var setOverflowVariables = function(horizontal) {\n                            var scrollbarVars = getScrollbarVars(horizontal);\n                            var scrollbarVarsInverted = getScrollbarVars(!horizontal);\n                            var xyI = scrollbarVarsInverted._x_y;\n                            var xy = scrollbarVars._x_y;\n                            var wh = scrollbarVars._w_h;\n                            var widthHeight = scrollbarVars._width_height;\n                            var scrollMax = _strScroll + scrollbarVars._Left_Top + 'Max';\n                            var fractionalOverflowAmount = viewportRect[widthHeight] ? MATH.abs(viewportRect[widthHeight] - _viewportSize[wh]) : 0;\n                            overflowBehaviorIsVS[xy] = overflowBehavior[xy] === 'v-s';\n                            overflowBehaviorIsVH[xy] = overflowBehavior[xy] === 'v-h';\n                            overflowBehaviorIsS[xy] = overflowBehavior[xy] === 's';\n                            overflowAmount[xy] = MATH.max(0, MATH.round((contentScrollSize[wh] - _viewportSize[wh]) * 100) / 100);\n                            overflowAmount[xy] *= (hideOverflowForceTextarea || (_viewportElementNative[scrollMax] === 0 && fractionalOverflowAmount > 0 && fractionalOverflowAmount < 1)) ? 0 : 1;\n                            hasOverflow[xy] = overflowAmount[xy] > 0;\n\n                            //hideOverflow:\n                            //x || y : true === overflow is hidden by \"overflow: scroll\" OR \"overflow: hidden\"\n                            //xs || ys : true === overflow is hidden by \"overflow: scroll\"\n                            hideOverflow[xy] = overflowBehaviorIsVS[xy] || overflowBehaviorIsVH[xy] ? (hasOverflow[xyI] && !overflowBehaviorIsVS[xyI] && !overflowBehaviorIsVH[xyI]) : hasOverflow[xy];\n                            hideOverflow[xy + 's'] = hideOverflow[xy] ? (overflowBehaviorIsS[xy] || overflowBehaviorIsVS[xy]) : false;\n\n                            canScroll[xy] = hasOverflow[xy] && hideOverflow[xy + 's'];\n                        };\n                        setOverflowVariables(true);\n                        setOverflowVariables(false);\n\n                        overflowAmount.c = checkCacheAutoForce(overflowAmount, _overflowAmountCache);\n                        _overflowAmountCache = overflowAmount;\n                        hasOverflow.c = checkCacheAutoForce(hasOverflow, _hasOverflowCache);\n                        _hasOverflowCache = hasOverflow;\n                        hideOverflow.c = checkCacheAutoForce(hideOverflow, _hideOverflowCache);\n                        _hideOverflowCache = hideOverflow;\n\n                        //if native scrollbar is overlay at x OR y axis, prepare DOM\n                        if (_nativeScrollbarIsOverlaid.x || _nativeScrollbarIsOverlaid.y) {\n                            var borderDesign = 'px solid transparent';\n                            var contentArrangeElementCSS = { };\n                            var arrangeContent = { };\n                            var arrangeChanged = force;\n                            var setContentElementCSS;\n\n                            if (hasOverflow.x || hasOverflow.y) {\n                                arrangeContent.w = _nativeScrollbarIsOverlaid.y && hasOverflow.y ? contentScrollSize.w + _overlayScrollbarDummySize.y : _strEmpty;\n                                arrangeContent.h = _nativeScrollbarIsOverlaid.x && hasOverflow.x ? contentScrollSize.h + _overlayScrollbarDummySize.x : _strEmpty;\n                                arrangeChanged = checkCacheAutoForce(arrangeContent, _arrangeContentSizeCache);\n                                _arrangeContentSizeCache = arrangeContent;\n                            }\n\n                            if (hasOverflow.c || hideOverflow.c || contentScrollSize.c || cssDirectionChanged || widthAutoChanged || heightAutoChanged || widthAuto || heightAuto || ignoreOverlayScrollbarHidingChanged) {\n                                contentElementCSS[_strMarginMinus + isRTLRight] = contentElementCSS[_strBorderMinus + isRTLRight] = _strEmpty;\n                                setContentElementCSS = function(horizontal) {\n                                    var scrollbarVars = getScrollbarVars(horizontal);\n                                    var scrollbarVarsInverted = getScrollbarVars(!horizontal);\n                                    var xy = scrollbarVars._x_y;\n                                    var strDirection = horizontal ? _strBottom : isRTLLeft;\n                                    var invertedAutoSize = horizontal ? heightAuto : widthAuto;\n\n                                    if (_nativeScrollbarIsOverlaid[xy] && hasOverflow[xy] && hideOverflow[xy + 's']) {\n                                        contentElementCSS[_strMarginMinus + strDirection] = invertedAutoSize ? (ignoreOverlayScrollbarHiding ? _strEmpty : _overlayScrollbarDummySize[xy]) : _strEmpty;\n                                        contentElementCSS[_strBorderMinus + strDirection] = ((horizontal ? !invertedAutoSize : true) && !ignoreOverlayScrollbarHiding) ? (_overlayScrollbarDummySize[xy] + borderDesign) : _strEmpty;\n                                    }\n                                    else {\n                                        arrangeContent[scrollbarVarsInverted._w_h] =\n                                        contentElementCSS[_strMarginMinus + strDirection] =\n                                        contentElementCSS[_strBorderMinus + strDirection] = _strEmpty;\n                                        arrangeChanged = true;\n                                    }\n                                };\n\n                                if (_nativeScrollbarStyling) {\n                                    if (ignoreOverlayScrollbarHiding) \n                                        removeClass(_viewportElement, _classNameViewportNativeScrollbarsInvisible);\n                                    else\n                                        addClass(_viewportElement, _classNameViewportNativeScrollbarsInvisible);\n                                }\n                                else {\n                                    setContentElementCSS(true);\n                                    setContentElementCSS(false);\n                                }\n                            }\n                            if (ignoreOverlayScrollbarHiding) {\n                                arrangeContent.w = arrangeContent.h = _strEmpty;\n                                arrangeChanged = true;\n                            }\n                            if (arrangeChanged && !_nativeScrollbarStyling) {\n                                contentArrangeElementCSS[_strWidth] = hideOverflow.y ? arrangeContent.w : _strEmpty;\n                                contentArrangeElementCSS[_strHeight] = hideOverflow.x ? arrangeContent.h : _strEmpty;\n\n                                if (!_contentArrangeElement) {\n                                    _contentArrangeElement = FRAMEWORK(generateDiv(_classNameContentArrangeElement));\n                                    _viewportElement.prepend(_contentArrangeElement);\n                                }\n                                _contentArrangeElement.css(contentArrangeElementCSS);\n                            }\n                            _contentElement.css(contentElementCSS);\n                        }\n\n                        var viewportElementCSS = {};\n                        var paddingElementCSS = {};\n                        var setViewportCSS;\n                        if (hostSizeChanged || hasOverflow.c || hideOverflow.c || contentScrollSize.c || overflowBehaviorChanged || boxSizingChanged || ignoreOverlayScrollbarHidingChanged || cssDirectionChanged || clipAlwaysChanged || heightAutoChanged) {\n                            viewportElementCSS[isRTLRight] = _strEmpty;\n                            setViewportCSS = function(horizontal) {\n                                var scrollbarVars = getScrollbarVars(horizontal);\n                                var scrollbarVarsInverted = getScrollbarVars(!horizontal);\n                                var xy = scrollbarVars._x_y;\n                                var XY = scrollbarVars._X_Y;\n                                var strDirection = horizontal ? _strBottom : isRTLLeft;\n\n                                var reset = function () {\n                                    viewportElementCSS[strDirection] = _strEmpty;\n                                    _contentBorderSize[scrollbarVarsInverted._w_h] = 0;\n                                };\n                                if (hasOverflow[xy] && hideOverflow[xy + 's']) {\n                                    viewportElementCSS[strOverflow + XY] = _strScroll;\n                                    if (ignoreOverlayScrollbarHiding || _nativeScrollbarStyling) {\n                                        reset();\n                                    }\n                                    else {\n                                        viewportElementCSS[strDirection] =  -(_nativeScrollbarIsOverlaid[xy] ? _overlayScrollbarDummySize[xy] : _nativeScrollbarSize[xy]);\n                                        _contentBorderSize[scrollbarVarsInverted._w_h] = _nativeScrollbarIsOverlaid[xy] ? _overlayScrollbarDummySize[scrollbarVarsInverted._x_y] : 0;\n                                    }\n                                } else {\n                                    viewportElementCSS[strOverflow + XY] = _strEmpty;\n                                    reset();\n                                }\n                            };\n                            setViewportCSS(true);\n                            setViewportCSS(false);\n                            \n                            // if the scroll container is too small and if there is any overflow with no overlay scrollbar (and scrollbar styling isn't possible), \n                            // make viewport element greater in size (Firefox hide Scrollbars fix)\n                            // because firefox starts hiding scrollbars on too small elements\n                            // with this behavior the overflow calculation may be incorrect or the scrollbars would appear suddenly\n                            // https://bugzilla.mozilla.org/show_bug.cgi?id=292284\n                            if (!_nativeScrollbarStyling \n                                && (_viewportSize.h < _nativeScrollbarMinSize.x || _viewportSize.w < _nativeScrollbarMinSize.y)\n                                && ((hasOverflow.x && hideOverflow.x && !_nativeScrollbarIsOverlaid.x) || (hasOverflow.y && hideOverflow.y && !_nativeScrollbarIsOverlaid.y))) {\n                                viewportElementCSS[_strPaddingMinus + _strTop] = _nativeScrollbarMinSize.x;\n                                viewportElementCSS[_strMarginMinus + _strTop] = -_nativeScrollbarMinSize.x;\n\n                                viewportElementCSS[_strPaddingMinus + isRTLRight] = _nativeScrollbarMinSize.y;\n                                viewportElementCSS[_strMarginMinus + isRTLRight] = -_nativeScrollbarMinSize.y;\n                            }\n                            else {\n                                viewportElementCSS[_strPaddingMinus + _strTop] =\n                                viewportElementCSS[_strMarginMinus + _strTop] =\n                                viewportElementCSS[_strPaddingMinus + isRTLRight] =\n                                viewportElementCSS[_strMarginMinus + isRTLRight] = _strEmpty;\n                            }\n                            viewportElementCSS[_strPaddingMinus + isRTLLeft] =\n                            viewportElementCSS[_strMarginMinus + isRTLLeft] = _strEmpty;\n\n                            //if there is any overflow (x OR y axis) and this overflow shall be hidden, make overflow hidden, else overflow visible\n                            if ((hasOverflow.x && hideOverflow.x) || (hasOverflow.y && hideOverflow.y) || hideOverflowForceTextarea) {\n                                //only hide if is Textarea\n                                if (_isTextarea && hideOverflowForceTextarea) {\n                                    paddingElementCSS[strOverflowX] =\n                                    paddingElementCSS[strOverflowY] = strHidden;\n                                }\n                            }\n                            else {\n                                if (!clipAlways || (overflowBehaviorIsVH.x || overflowBehaviorIsVS.x || overflowBehaviorIsVH.y || overflowBehaviorIsVS.y)) {\n                                    //only un-hide if Textarea\n                                    if (_isTextarea) {\n                                        paddingElementCSS[strOverflowX] =\n                                        paddingElementCSS[strOverflowY] = _strEmpty;\n                                    }\n                                    viewportElementCSS[strOverflowX] =\n                                    viewportElementCSS[strOverflowY] = strVisible;\n                                }\n                            }\n\n                            _paddingElement.css(paddingElementCSS);\n                            _viewportElement.css(viewportElementCSS);\n                            viewportElementCSS = { };\n\n                            //force soft redraw in webkit because without the scrollbars will may appear because DOM wont be redrawn under special conditions\n                            if ((hasOverflow.c || boxSizingChanged || widthAutoChanged || heightAutoChanged) && !(_nativeScrollbarIsOverlaid.x && _nativeScrollbarIsOverlaid.y)) {\n                                var elementStyle = _contentElementNative[LEXICON.s];\n                                var dump;\n                                elementStyle.webkitTransform = 'scale(1)';\n                                elementStyle.display = 'run-in';\n                                dump = _contentElementNative[LEXICON.oH];\n                                elementStyle.display = _strEmpty; //|| dump; //use dump to prevent it from deletion if minify\n                                elementStyle.webkitTransform = _strEmpty;\n                            }\n                            /*\n                            //force hard redraw in webkit if native overlaid scrollbars shall appear\n                            if (ignoreOverlayScrollbarHidingChanged && ignoreOverlayScrollbarHiding) {\n                                _hostElement.hide();\n                                var dump = _hostElementNative[LEXICON.oH];\n                                _hostElement.show();\n                            }\n                            */\n                        }\n\n                        //change to direction RTL and width auto Bugfix in Webkit\n                        //without this fix, the DOM still thinks the scrollbar is LTR and thus the content is shifted to the left\n                        contentElementCSS = {};\n                        if (cssDirectionChanged || widthAutoChanged || heightAutoChanged) {\n                            if (_isRTL && widthAuto) {\n                                var floatTmp = _contentElement.css(_strFloat);\n                                var posLeftWithoutFloat = MATH.round(_contentElement.css(_strFloat, _strEmpty).css(_strLeft, _strEmpty).position().left);\n                                _contentElement.css(_strFloat, floatTmp);\n                                var posLeftWithFloat = MATH.round(_contentElement.position().left);\n\n                                if (posLeftWithoutFloat !== posLeftWithFloat)\n                                    contentElementCSS[_strLeft] = posLeftWithoutFloat;\n                            }\n                            else {\n                                contentElementCSS[_strLeft] = _strEmpty;\n                            }\n                        }\n                        _contentElement.css(contentElementCSS);\n\n                        //handle scroll position\n                        if (_isTextarea && contentSizeChanged) {\n                            var textareaInfo = getTextareaInfo();\n                            if (textareaInfo) {\n                                var textareaRowsChanged = _textareaInfoCache === undefined ? true : textareaInfo._rows !== _textareaInfoCache._rows;\n                                var cursorRow = textareaInfo._cursorRow;\n                                var cursorCol = textareaInfo._cursorColumn;\n                                var widestRow = textareaInfo._widestRow;\n                                var lastRow = textareaInfo._rows;\n                                var lastCol = textareaInfo._columns;\n                                var cursorPos = textareaInfo._cursorPosition;\n                                var cursorMax = textareaInfo._cursorMax;\n                                var cursorIsLastPosition = (cursorPos >= cursorMax && _textareaHasFocus);\n                                var textareaScrollAmount = {\n                                    x: (!textareaAutoWrapping && (cursorCol === lastCol && cursorRow === widestRow)) ? _overflowAmountCache.x : -1,\n                                    y: (textareaAutoWrapping ? cursorIsLastPosition || textareaRowsChanged && (previousOverflow !== undefined ? (currScroll.y === previousOverflow.y) : false) : (cursorIsLastPosition || textareaRowsChanged) && cursorRow === lastRow) ? _overflowAmountCache.y : -1\n                                };\n                                currScroll.x = textareaScrollAmount.x > -1 ? (_isRTL && _normalizeRTLCache && _rtlScrollBehavior.i ? 0 : textareaScrollAmount.x) : currScroll.x; //if inverted, scroll to 0 -> normalized this means to max scroll offset.\n                                currScroll.y = textareaScrollAmount.y > -1 ? textareaScrollAmount.y : currScroll.y;\n                            }\n                            _textareaInfoCache = textareaInfo;\n                        }\n                        if (_isRTL && _rtlScrollBehavior.i && _nativeScrollbarIsOverlaid.y && hasOverflow.x && _normalizeRTLCache)\n                            currScroll.x += _contentBorderSize.w || 0;\n                        if(widthAuto)\n                            _hostElement[_strScrollLeft](0);\n                        if(heightAuto)\n                            _hostElement[_strScrollTop](0);\n                        _viewportElement[_strScrollLeft](currScroll.x)[_strScrollTop](currScroll.y);\n\n                        //scrollbars management:\n                        var scrollbarsVisibilityVisible = scrollbarsVisibility === 'v';\n                        var scrollbarsVisibilityHidden = scrollbarsVisibility === 'h';\n                        var scrollbarsVisibilityAuto = scrollbarsVisibility === 'a';\n\n                        var showScrollbarH = COMPATIBILITY.bind(refreshScrollbarAppearance, 0, true, true, canScroll.x);\n                        var showScrollbarV = COMPATIBILITY.bind(refreshScrollbarAppearance, 0, false, true, canScroll.y);\n                        var hideScrollbarH = COMPATIBILITY.bind(refreshScrollbarAppearance, 0, true, false, canScroll.x);\n                        var hideScrollbarV = COMPATIBILITY.bind(refreshScrollbarAppearance, 0, false, false, canScroll.y);\n\n                        //manage class name which indicates scrollable overflow\n                        if (hideOverflow.x || hideOverflow.y)\n                            addClass(_hostElement, _classNameHostOverflow);\n                        else\n                            removeClass(_hostElement, _classNameHostOverflow);\n                        if (hideOverflow.x)\n                            addClass(_hostElement, _classNameHostOverflowX);\n                        else\n                            removeClass(_hostElement, _classNameHostOverflowX);\n                        if (hideOverflow.y)\n                            addClass(_hostElement, _classNameHostOverflowY);\n                        else\n                            removeClass(_hostElement, _classNameHostOverflowY);\n\n                        //add or remove rtl class name for styling purposes\n                        if (cssDirectionChanged) {\n                            if (_isRTL)\n                                addClass(_hostElement, _classNameHostRTL);\n                            else\n                                removeClass(_hostElement, _classNameHostRTL);\n                        }\n\n                        //manage the resize feature (CSS3 resize \"polyfill\" for this plugin)\n                        if (_isBody)\n                            addClass(_hostElement, _classNameHostResizeDisabled);\n                        if (resizeChanged) {\n                            var setupCornerEvents = function(remove) {\n                                if(_supportPassiveEvents)\n                                    setupPassiveEventListener(_scrollbarCornerElement, _strMouseTouchDownEvent, _resizeOnMouseTouchDown, remove, true);\n                                else\n                                    _scrollbarCornerElement[remove ? 'off' : 'on'](_strMouseTouchDownEvent, _resizeOnMouseTouchDown);\n                            };\n                            removeClass(_scrollbarCornerElement, [\n                                    _classNameHostResizeDisabled,\n                                    _classNameScrollbarCornerResize,\n                                    _classNameScrollbarCornerResizeB,\n                                    _classNameScrollbarCornerResizeH,\n                                    _classNameScrollbarCornerResizeV].join(_strSpace));\n                            if (_resizeNone) {\n                                addClass(_hostElement, _classNameHostResizeDisabled);\n                                setupCornerEvents(true);\n                            }\n                            else {\n                                addClass(_scrollbarCornerElement, _classNameScrollbarCornerResize);\n                                if (_resizeBoth)\n                                    addClass(_scrollbarCornerElement, _classNameScrollbarCornerResizeB);\n                                else if (_resizeHorizontal)\n                                    addClass(_scrollbarCornerElement, _classNameScrollbarCornerResizeH);\n                                else if (_resizeVertical)\n                                    addClass(_scrollbarCornerElement, _classNameScrollbarCornerResizeV);\n\n                                setupCornerEvents(true);\n                                setupCornerEvents();\n                            }\n                        }\n\n                        //manage the scrollbars general visibility + the scrollbar interactivity (unusable class name)\n                        if (scrollbarsVisibilityChanged || overflowBehaviorChanged || hideOverflow.c || hasOverflow.c || ignoreOverlayScrollbarHidingChanged) {\n                            if (ignoreOverlayScrollbarHiding) {\n                                if (ignoreOverlayScrollbarHidingChanged) {\n                                    removeClass(_hostElement, _classNameHostScrolling);\n                                    if (ignoreOverlayScrollbarHiding) {\n                                        hideScrollbarH();\n                                        hideScrollbarV();\n                                    }\n                                }\n                            }\n                            else if (scrollbarsVisibilityAuto) {\n                                if (canScroll.x)\n                                    showScrollbarH();\n                                else\n                                    hideScrollbarH();\n\n                                if (canScroll.y)\n                                    showScrollbarV();\n                                else\n                                    hideScrollbarV();\n                            }\n                            else if (scrollbarsVisibilityVisible) {\n                                showScrollbarH();\n                                showScrollbarV();\n                            }\n                            else if (scrollbarsVisibilityHidden) {\n                                hideScrollbarH();\n                                hideScrollbarV();\n                            }\n                        }\n\n                        //manage the scrollbars auto hide feature (auto hide them after specific actions)\n                        if (scrollbarsAutoHideChanged || ignoreOverlayScrollbarHidingChanged) {\n                            if (_scrollbarsAutoHideLeave || _scrollbarsAutoHideMove) {\n                                setupHostMouseTouchEvents(true);\n                                setupHostMouseTouchEvents();\n                            }\n                            else {\n                                setupHostMouseTouchEvents(true);\n                            }\n\n                            if (_scrollbarsAutoHideNever)\n                                refreshScrollbarsAutoHide(true);\n                            else\n                                refreshScrollbarsAutoHide(false, true);\n                        }\n\n                        //manage scrollbars handle length & offset - don't remove!\n                        if (hostSizeChanged || overflowAmount.c || heightAutoChanged || widthAutoChanged || resizeChanged || boxSizingChanged || paddingAbsoluteChanged || ignoreOverlayScrollbarHidingChanged || cssDirectionChanged) {\n                            refreshScrollbarHandleLength(true);\n                            refreshScrollbarHandleOffset(true);\n                            refreshScrollbarHandleLength(false);\n                            refreshScrollbarHandleOffset(false);\n                        }\n\n                        //manage interactivity\n                        if (scrollbarsClickScrollingChanged)\n                            refreshScrollbarsInteractive(true, scrollbarsClickScrolling);\n                        if (scrollbarsDragScrollingChanged)\n                            refreshScrollbarsInteractive(false, scrollbarsDragScrolling);\n\n                        //callbacks:\n                        if (cssDirectionChanged) {\n                            dispatchCallback(\"onDirectionChanged\", {\n                                isRTL: _isRTL,\n                                dir: cssDirection\n                            });\n                        }\n                        if (hostSizeChanged) {\n                            dispatchCallback(\"onHostSizeChanged\", {\n                                width: _hostSizeCache.w,\n                                height: _hostSizeCache.h\n                            });\n                        }\n                        if (contentSizeChanged) {\n                            dispatchCallback(\"onContentSizeChanged\", {\n                                width: _contentScrollSizeCache.w,\n                                height: _contentScrollSizeCache.h\n                            });\n                        }\n                        if (hasOverflow.c || hideOverflow.c) {\n                            dispatchCallback(\"onOverflowChanged\", {\n                                x: hasOverflow.x,\n                                y: hasOverflow.y,\n                                xScrollable: hideOverflow.xs,\n                                yScrollable: hideOverflow.ys,\n                                clipped: hideOverflow.x || hideOverflow.y\n                            });\n                        }\n                        if (overflowAmount.c) {\n                            dispatchCallback(\"onOverflowAmountChanged\", {\n                                x: overflowAmount.x,\n                                y: overflowAmount.y\n                            });\n                        }\n                    }\n\n                    //fix body min size\n                    if (_isBody && _bodyMinSizeCache && (_hasOverflowCache.c || _bodyMinSizeCache.c)) {\n                        //its possible that no min size was measured until now, because the content arrange element was just added now, in this case, measure now the min size.\n                        if (!_bodyMinSizeCache.f)\n                            bodyMinSizeChanged();\n                        if (_nativeScrollbarIsOverlaid.y && _hasOverflowCache.x)\n                            _contentElement.css(_strMinMinus + _strWidth, _bodyMinSizeCache.w + _overlayScrollbarDummySize.y);\n                        if (_nativeScrollbarIsOverlaid.x && _hasOverflowCache.y)\n                            _contentElement.css(_strMinMinus + _strHeight, _bodyMinSizeCache.h + _overlayScrollbarDummySize.x);\n                        _bodyMinSizeCache.c = false;\n                    }\n\n                    //freezeResizeObserver(_sizeObserverElement, false);\n                    //freezeResizeObserver(_sizeAutoObserverElement, false);\n\n                    dispatchCallback(\"onUpdated\", { forced: force });\n                }\n\n                \n                //==== Options ====//\n\n                /**\n                 * Sets new options but doesn't call the update method.\n                 * @param newOptions The object which contains the new options.\n                 * @returns {*} A object which contains the changed options.\n                 */\n                function setOptions(newOptions) {\n                    var validatedOpts = _pluginsOptions._validate(newOptions, _pluginsOptions._template, true, _currentOptions)\n\n                    _currentOptions = extendDeep({}, _currentOptions, validatedOpts._default);\n                    _currentPreparedOptions = extendDeep({}, _currentPreparedOptions, validatedOpts._prepared);\n                    \n                    return validatedOpts._prepared;\n                }\n\n\n                //==== Structure ====//\n\n                /**\n                 * Builds or destroys the wrapper and helper DOM elements.\n                 * @param destroy Indicates whether the DOM shall be build or destroyed.\n                 */\n                function setupStructureDOM(destroy) {\n                    var adoptAttrs = _currentPreparedOptions.textarea.inheritedAttrs;\n                    var adoptAttrsMap = { };\n                    var applyAdoptedAttrs = function() {\n                        var applyAdoptedAttrsElm = destroy ? _targetElement : _hostElement;\n                        each(adoptAttrsMap, function(k, v) {\n                            if(type(v) == TYPES.s) {\n                                if(k == LEXICON.c)\n                                    applyAdoptedAttrsElm.addClass(v);\n                                else\n                                    applyAdoptedAttrsElm.attr(k, v);\n                            }\n                        });\n                    };\n                    var hostElementClassNames = [\n                        _classNameHostElement,\n                        _classNameHostTextareaElement,\n                        _classNameHostResizeDisabled,\n                        _classNameHostRTL,\n                        _classNameHostScrollbarHorizontalHidden,\n                        _classNameHostScrollbarVerticalHidden,\n                        _classNameHostTransition,\n                        _classNameHostScrolling,\n                        _classNameHostOverflow,\n                        _classNameHostOverflowX,\n                        _classNameHostOverflowY,\n                        _classNameThemeNone,\n                        _classNameTextareaElement,\n                        _classNameTextInherit,\n                        _classNameCache].join(_strSpace);\n                    adoptAttrs = type(adoptAttrs) == TYPES.s ? adoptAttrs.split(' ') : adoptAttrs;\n                    if(type(adoptAttrs) == TYPES.a) {\n                        each(adoptAttrs, function(i, v) {\n                            if(type(v) == TYPES.s)\n                                adoptAttrsMap[v] = destroy ? _hostElement.attr(v) : _targetElement.attr(v);\n                        });\n                    }\n\n                    if(!destroy) {\n                        if (_isTextarea) {\n                            var hostElementCSS = {};\n                            var parent = _targetElement.parent();\n                            _isTextareaHostGenerated = !(parent.hasClass(_classNameHostTextareaElement) && parent.children()[LEXICON.l] === 1);\n\n                            if (!_currentPreparedOptions.sizeAutoCapable) {\n                                hostElementCSS[_strWidth] = _targetElement.css(_strWidth);\n                                hostElementCSS[_strHeight] = _targetElement.css(_strHeight);\n                            }\n                            if(_isTextareaHostGenerated)\n                                _targetElement.wrap(generateDiv(_classNameHostTextareaElement));\n\n                            _hostElement = _targetElement.parent();\n                            _hostElement.css(hostElementCSS)\n                                .wrapInner(generateDiv(_classNameContentElement + _strSpace + _classNameTextInherit))\n                                .wrapInner(generateDiv(_classNameViewportElement + _strSpace + _classNameTextInherit))\n                                .wrapInner(generateDiv(_classNamePaddingElement + _strSpace + _classNameTextInherit));\n                            _contentElement = findFirst(_hostElement, _strDot + _classNameContentElement);\n                            _viewportElement = findFirst(_hostElement, _strDot + _classNameViewportElement);\n                            _paddingElement = findFirst(_hostElement, _strDot + _classNamePaddingElement);\n                            _textareaCoverElement = FRAMEWORK(generateDiv(_classNameTextareaCoverElement));\n                            _contentElement.prepend(_textareaCoverElement);\n\n                            addClass(_targetElement, _classNameTextareaElement + _strSpace + _classNameTextInherit);\n\n                            if(_isTextareaHostGenerated)\n                                applyAdoptedAttrs();\n                        }\n                        else {\n                            _hostElement = _targetElement;\n                            _hostElement.wrapInner(generateDiv(_classNameContentElement))\n                                .wrapInner(generateDiv(_classNameViewportElement))\n                                .wrapInner(generateDiv(_classNamePaddingElement));\n                            _contentElement = findFirst(_hostElement, _strDot + _classNameContentElement);\n                            _viewportElement = findFirst(_hostElement, _strDot + _classNameViewportElement);\n                            _paddingElement = findFirst(_hostElement, _strDot + _classNamePaddingElement);\n\n                            addClass(_targetElement, _classNameHostElement);\n                        }\n                        \n                        if (_nativeScrollbarStyling)\n                            addClass(_viewportElement, _classNameViewportNativeScrollbarsInvisible);\n                        if(_nativeScrollbarIsOverlaid.x && _nativeScrollbarIsOverlaid.y)\n                            addClass(_viewportElement, _classNameViewportNativeScrollbarsOverlaid);\n                        if (_isBody)\n                            addClass(_htmlElement, _classNameHTMLElement);\n\n                        _sizeObserverElement = FRAMEWORK(generateDiv('os-resize-observer-host'));\n                        _hostElement.prepend(_sizeObserverElement);\n\n                        _sizeObserverElementNative = _sizeObserverElement[0];\n                        _hostElementNative = _hostElement[0];\n                        _paddingElementNative = _paddingElement[0];\n                        _viewportElementNative = _viewportElement[0];\n                        _contentElementNative = _contentElement[0];\n                    }\n                    else {\n                        _contentElement.contents()\n                            .unwrap()\n                            .unwrap()\n                            .unwrap();\n\n                        removeClass(_hostElement, hostElementClassNames);\n                        if (_isTextarea) {\n                            _targetElement.removeAttr(LEXICON.s);\n\n                            if(_isTextareaHostGenerated)\n                                applyAdoptedAttrs();\n\n                            removeClass(_targetElement, hostElementClassNames);\n                            remove(_textareaCoverElement);\n\n                            if(_isTextareaHostGenerated) {\n                                _targetElement.unwrap();\n                                remove(_hostElement);\n                            }\n                            else {\n                                addClass(_hostElement, _classNameHostTextareaElement);\n                            }\n                        }\n                        else {\n                            removeClass(_targetElement, _classNameHostElement);\n                        }\n\n                        if (_isBody)\n                            removeClass(_htmlElement, _classNameHTMLElement);\n\n                        remove(_sizeObserverElement);\n                    }\n                }\n\n                /**\n                 * Adds or removes all wrapper elements interactivity events.\n                 * @param destroy Indicates whether the Events shall be added or removed.\n                 */\n                function setupStructureEvents(destroy) {\n                    var textareaKeyDownRestrictedKeyCodes = [\n                        112, 113, 114, 115, 116, 117, 118, 119, 120, 121, 123,    //F1 to F12\n                        33, 34,                                                   //page up, page down\n                        37, 38, 39, 40,                                           //left, up, right, down arrows\n                        16, 17, 18, 19, 20, 144                                   //Shift, Ctrl, Alt, Pause, CapsLock, NumLock\n                    ];\n                    var textareaKeyDownKeyCodesList = [ ];\n                    var textareaUpdateIntervalID;\n                    var scrollStopDelay = 175;\n                    var scrollStopTimeoutId;\n                    var strOnOff = destroy ? 'off' : 'on';\n                    var updateTextarea;\n                    var viewportOnScroll;\n\n                    if(!destroy && _isTextarea) {\n                        _textareaEvents = { };\n                        updateTextarea = function(doClearInterval) {\n                            textareaUpdate();\n                            _base.update(_strAuto);\n                            if(doClearInterval)\n                                clearInterval(textareaUpdateIntervalID);\n                        };\n                        _textareaEvents[_strScroll] = function(event) {\n                            _targetElement[_strScrollLeft](_rtlScrollBehavior.i && _normalizeRTLCache ? 9999999 : 0);\n                            _targetElement[_strScrollTop](0);\n                            COMPATIBILITY.prvD(event);\n                            COMPATIBILITY.stpP(event);\n                            return false;\n                        };\n                        _textareaEvents['drop'] = function() {\n                            setTimeout(function () {\n                                if(!_destroyed)\n                                    updateTextarea();\n                            }, 50);\n                        };\n                        _textareaEvents['focus'] = function() {\n                            _textareaHasFocus = true;\n                        };\n                        _textareaEvents['focusout'] = function() {\n                            _textareaHasFocus = false;\n                            textareaKeyDownKeyCodesList = [ ];\n                            updateTextarea(true);\n                        };\n                        if (_msieVersion > 9 || !_autoUpdateRecommended) {\n                            _textareaEvents['input'] = function textareaOnInput() {\n                                updateTextarea();\n                            }\n                        }\n                        else {\n                            _textareaEvents[_strKeyDownEvent] = function textareaOnKeyDown(event) {\n                                var keyCode = event.keyCode;\n                                if (inArray(keyCode, textareaKeyDownRestrictedKeyCodes) > -1)\n                                    return;\n                                if (!textareaKeyDownKeyCodesList.length) {\n                                    updateTextarea();\n                                    textareaUpdateIntervalID = setInterval(updateTextarea, 1000 / 60);\n                                }\n                                if (inArray(keyCode, textareaKeyDownKeyCodesList) === -1)\n                                    textareaKeyDownKeyCodesList.push(keyCode);\n                            };\n                            _textareaEvents[_strKeyUpEvent] = function(event) {\n                                var keyCode = event.keyCode;\n                                var index = inArray(keyCode, textareaKeyDownKeyCodesList);\n\n                                if (inArray(keyCode, textareaKeyDownRestrictedKeyCodes) > -1)\n                                    return;\n                                if (index > -1)\n                                    textareaKeyDownKeyCodesList.splice(index, 1);\n                                if (!textareaKeyDownKeyCodesList.length)\n                                    updateTextarea(true);\n                            };\n                        }\n                    }\n\n                    if (_isTextarea) {\n                        each(_textareaEvents, function(key, value) {\n                            _targetElement[strOnOff](key, value);\n                        });\n                    }\n                    else {\n                        _contentElement[strOnOff](_strTransitionEndEvent, function (event) {\n                            if (_autoUpdateCache === true)\n                                return;\n                            event = event.originalEvent || event;\n                            if (isSizeAffectingCSSProperty(event.propertyName))\n                                _base.update(_strAuto);\n                        });\n                    }\n\n                    if(!destroy) {\n                        viewportOnScroll = function(event) {\n                            if (!_sleeping) {\n                                if (scrollStopTimeoutId !== undefined)\n                                    clearTimeout(scrollStopTimeoutId);\n                                else {\n                                    if (_scrollbarsAutoHideScroll || _scrollbarsAutoHideMove)\n                                        refreshScrollbarsAutoHide(true);\n\n                                    if (!nativeOverlayScrollbarsAreActive())\n                                        addClass(_hostElement, _classNameHostScrolling);\n\n                                    dispatchCallback(\"onScrollStart\", event);\n                                }\n\n                                //if a scrollbars handle gets dragged, the mousemove event is responsible for refreshing the handle offset\n                                //because if CSS scroll-snap is used, the handle offset gets only refreshed on every snap point\n                                //this looks laggy & clunky, it looks much better if the offset refreshes with the mousemove\n                                if(!_scrollbarsHandlesDefineScrollPos) {\n                                    refreshScrollbarHandleOffset(true);\n                                    refreshScrollbarHandleOffset(false);\n                                }\n                                dispatchCallback(\"onScroll\", event);\n\n                                scrollStopTimeoutId = setTimeout(function () {\n                                    if(!_destroyed) {\n                                        //OnScrollStop:\n                                        clearTimeout(scrollStopTimeoutId);\n                                        scrollStopTimeoutId = undefined;\n\n                                        if (_scrollbarsAutoHideScroll || _scrollbarsAutoHideMove)\n                                            refreshScrollbarsAutoHide(false);\n\n                                        if (!nativeOverlayScrollbarsAreActive())\n                                            removeClass(_hostElement, _classNameHostScrolling);\n\n                                        dispatchCallback(\"onScrollStop\", event);\n                                    }\n                                }, scrollStopDelay);\n                            }\n                        };\n\n                        if (_supportPassiveEvents)\n                            setupPassiveEventListener(_viewportElement, _strScroll, viewportOnScroll);\n                        else\n                            _viewportElement.on(_strScroll, viewportOnScroll);\n                    }\n                }\n\n\n\n                //==== Scrollbars ====//\n\n                /**\n                 * Builds or destroys all scrollbar DOM elements (scrollbar, track, handle)\n                 * @param destroy Indicates whether the DOM shall be build or destroyed.\n                 */\n                function setupScrollbarsDOM(destroy) {\n                    if(!destroy) {\n                        _scrollbarHorizontalElement = FRAMEWORK(generateDiv(_classNameScrollbar + _strSpace + _classNameScrollbarHorizontal));\n                        _scrollbarHorizontalTrackElement = FRAMEWORK(generateDiv(_classNameScrollbarTrack));\n                        _scrollbarHorizontalHandleElement = FRAMEWORK(generateDiv(_classNameScrollbarHandle));\n                        _scrollbarVerticalElement = FRAMEWORK(generateDiv(_classNameScrollbar + _strSpace + _classNameScrollbarVertical));\n                        _scrollbarVerticalTrackElement = FRAMEWORK(generateDiv(_classNameScrollbarTrack));\n                        _scrollbarVerticalHandleElement = FRAMEWORK(generateDiv(_classNameScrollbarHandle));\n\n                        _scrollbarHorizontalElement.append(_scrollbarHorizontalTrackElement);\n                        _scrollbarHorizontalTrackElement.append(_scrollbarHorizontalHandleElement);\n                        _scrollbarVerticalElement.append(_scrollbarVerticalTrackElement);\n                        _scrollbarVerticalTrackElement.append(_scrollbarVerticalHandleElement);\n\n                        _paddingElement.after(_scrollbarVerticalElement);\n                        _paddingElement.after(_scrollbarHorizontalElement);\n                    }\n                    else {\n                        remove(_scrollbarHorizontalElement);\n                        remove(_scrollbarVerticalElement);\n                    }\n                }\n\n                /**\n                 * Initializes all scrollbar interactivity events. (track and handle dragging, clicking, scrolling)\n                 * @param isHorizontal True if the target scrollbar is the horizontal scrollbar, false if the target scrollbar is the vertical scrollbar.\n                 */\n                function setupScrollbarEvents(isHorizontal) {\n                    var scrollbarVars = getScrollbarVars(isHorizontal);\n                    var scrollbarVarsInfo = scrollbarVars._info;\n                    var insideIFrame = _windowElementNative.top !== _windowElementNative;\n                    var xy = scrollbarVars._x_y;\n                    var XY = scrollbarVars._X_Y;\n                    var scroll = _strScroll + scrollbarVars._Left_Top;\n                    var strActive = 'active';\n                    var strSnapHandle = 'snapHandle';\n                    var scrollDurationFactor = 1;\n                    var increaseDecreaseScrollAmountKeyCodes = [ 16, 17 ]; //shift, ctrl\n                    var trackTimeout;\n                    var mouseDownScroll;\n                    var mouseDownOffset;\n                    var mouseDownInvertedScale;\n                    \n                    function setupEvent(element, eventNames, listener) {\n                        var collected = type(eventNames) == TYPES.a && type(listener) == TYPES.a;\n                        var i = 0;\n                        \n                        if(collected) {\n                            for (; i < eventNames[LEXICON.l]; i++)\n                                setupEvent(element, eventNames[i], listener[i]);\n                        }\n                        else {\n                            if(_supportPassiveEvents)\n                                setupPassiveEventListener(element, eventNames, listener, false, true);\n                            else\n                                element.on(eventNames, listener);\n                        }\n                    }\n                    function getPointerPosition(event) {\n                        return _msieVersion && insideIFrame ? event['screen' + XY] : COMPATIBILITY.page(event)[xy]; //use screen coordinates in EDGE & IE because the page values are incorrect in frames.\n                    }\n                    function getPreparedScrollbarsOption(name) {\n                        return _currentPreparedOptions.scrollbars[name];\n                    }\n                    function increaseTrackScrollAmount() {\n                        scrollDurationFactor = 0.5;\n                    }\n                    function decreaseTrackScrollAmount() {\n                        scrollDurationFactor = 1;\n                    }\n                    function documentKeyDown(event) {\n                        if (inArray(event.keyCode, increaseDecreaseScrollAmountKeyCodes) > -1)\n                            increaseTrackScrollAmount();\n                    }\n                    function documentKeyUp(event) {\n                        if (inArray(event.keyCode, increaseDecreaseScrollAmountKeyCodes) > -1)\n                            decreaseTrackScrollAmount();\n                    }\n                    function onMouseTouchDownContinue(event) {\n                        var originalEvent = event.originalEvent || event;\n                        var isTouchEvent = originalEvent.touches !== undefined;\n                        return _sleeping || _destroyed || nativeOverlayScrollbarsAreActive() || !_scrollbarsDragScrollingCache || (isTouchEvent && !getPreparedScrollbarsOption('touchSupport')) ? false : COMPATIBILITY.mBtn(event) === 1 || isTouchEvent;\n                    }\n                    function documentDragMove(event) {\n                        if(onMouseTouchDownContinue(event)) {\n                            var trackLength = scrollbarVarsInfo._trackLength;\n                            var handleLength = scrollbarVarsInfo._handleLength;\n                            var scrollRange = scrollbarVarsInfo._maxScroll;\n                            var scrollRaw = (getPointerPosition(event) - mouseDownOffset) * mouseDownInvertedScale;\n                            var scrollDeltaPercent = scrollRaw / (trackLength - handleLength);\n                            var scrollDelta = (scrollRange * scrollDeltaPercent);\n                            scrollDelta = isFinite(scrollDelta) ? scrollDelta : 0;\n                            if (_isRTL && isHorizontal && !_rtlScrollBehavior.i)\n                                scrollDelta *= -1;\n\n                            _viewportElement[scroll](MATH.round(mouseDownScroll + scrollDelta));\n\n                            if(_scrollbarsHandlesDefineScrollPos)\n                                refreshScrollbarHandleOffset(isHorizontal, mouseDownScroll + scrollDelta);\n\n                            if (!_supportPassiveEvents)\n                                COMPATIBILITY.prvD(event);\n                        }\n                        else\n                            documentMouseTouchUp(event);\n                    }\n                    function documentMouseTouchUp(event) {\n                        event = event || event.originalEvent;\n\n                        _documentElement.off(_strMouseTouchMoveEvent, documentDragMove)\n                            .off(_strMouseTouchUpEvent, documentMouseTouchUp)\n                            .off(_strKeyDownEvent, documentKeyDown)\n                            .off(_strKeyUpEvent, documentKeyUp)\n                            .off(_strSelectStartEvent, documentOnSelectStart);\n\n                        if(_scrollbarsHandlesDefineScrollPos)\n                            refreshScrollbarHandleOffset(isHorizontal, true);\n\n                        _scrollbarsHandlesDefineScrollPos = false;\n                        removeClass(_bodyElement, _classNameDragging);\n                        removeClass(scrollbarVars._handle, strActive);\n                        removeClass(scrollbarVars._track, strActive);\n                        removeClass(scrollbarVars._scrollbar, strActive);\n\n                        mouseDownScroll = undefined;\n                        mouseDownOffset = undefined;\n                        mouseDownInvertedScale = 1;\n\n                        decreaseTrackScrollAmount();\n\n                        if (trackTimeout !== undefined) {\n                            _base.scrollStop();\n                            clearTimeout(trackTimeout);\n                            trackTimeout = undefined;\n                        }\n\n                        if(event) {\n                            var rect = _hostElementNative.getBoundingClientRect();\n                            var mouseInsideHost = event.clientX >= rect.left && event.clientX <= rect.right && event.clientY >= rect.top && event.clientY <= rect.bottom;\n\n                            //if mouse is outside host element\n                            if (!mouseInsideHost)\n                                hostOnMouseLeave();\n\n                            if (_scrollbarsAutoHideScroll || _scrollbarsAutoHideMove)\n                                refreshScrollbarsAutoHide(false);\n                        }\n                    }\n                    function onHandleMouseTouchDown(event) {\n                        if (onMouseTouchDownContinue(event))\n                            onHandleMouseTouchDownAction(event);\n                    }\n                    function onHandleMouseTouchDownAction(event) {\n                        mouseDownScroll = _viewportElement[scroll]();\n                        mouseDownScroll = isNaN(mouseDownScroll) ? 0 : mouseDownScroll;\n                        if (_isRTL && isHorizontal && !_rtlScrollBehavior.n || !_isRTL)\n                            mouseDownScroll = mouseDownScroll < 0 ? 0 : mouseDownScroll;\n\n                        mouseDownInvertedScale = getHostElementInvertedScale()[xy];\n                        mouseDownOffset = getPointerPosition(event);\n\n                        _scrollbarsHandlesDefineScrollPos = !getPreparedScrollbarsOption(strSnapHandle);\n                        addClass(_bodyElement, _classNameDragging);\n                        addClass(scrollbarVars._handle, strActive);\n                        addClass(scrollbarVars._scrollbar, strActive);\n\n                        _documentElement.on(_strMouseTouchMoveEvent, documentDragMove)\n                            .on(_strMouseTouchUpEvent, documentMouseTouchUp)\n                            .on(_strSelectStartEvent, documentOnSelectStart);\n\n                        if(_msieVersion || !_documentMixed)\n                            COMPATIBILITY.prvD(event);\n                        COMPATIBILITY.stpP(event);\n                    }\n                    function onTrackMouseTouchDown(event) {\n                        if (onMouseTouchDownContinue(event)) {\n                            var scrollDistance = MATH.round(_viewportSize[scrollbarVars._w_h]);\n                            var trackOffset = scrollbarVars._track.offset()[scrollbarVars._left_top];\n                            var ctrlKey = event.ctrlKey;\n                            var instantScroll = event.shiftKey;\n                            var instantScrollTransition = instantScroll && ctrlKey;\n                            var isFirstIteration = true;\n                            var easing = 'linear';\n                            var decreaseScroll;\n                            var finishedCondition;\n                            var scrollActionFinsished = function(transition) {\n                                if(_scrollbarsHandlesDefineScrollPos)\n                                    refreshScrollbarHandleOffset(isHorizontal, transition);\n                            };\n                            var scrollActionInstantFinished = function() {\n                                scrollActionFinsished();\n                                onHandleMouseTouchDownAction(event);\n                            };\n                            var scrollAction = function () {\n                                if(!_destroyed) {\n                                    var mouseOffset = (mouseDownOffset - trackOffset) * mouseDownInvertedScale;\n                                    var handleOffset = scrollbarVarsInfo._handleOffset;\n                                    var trackLength = scrollbarVarsInfo._trackLength;\n                                    var handleLength = scrollbarVarsInfo._handleLength;\n                                    var scrollRange = scrollbarVarsInfo._maxScroll;\n                                    var currScroll = scrollbarVarsInfo._currentScroll;\n                                    var scrollDuration = 270 * scrollDurationFactor;\n                                    var timeoutDelay = isFirstIteration ? MATH.max(400, scrollDuration) : scrollDuration;\n                                    var instantScrollPosition = scrollRange * ((mouseOffset - (handleLength / 2)) / (trackLength - handleLength)); // 100% * positionPercent\n                                    var rtlIsNormal = _isRTL && isHorizontal && ((!_rtlScrollBehavior.i && !_rtlScrollBehavior.n) || _normalizeRTLCache);\n                                    var decreaseScrollCondition = rtlIsNormal ? handleOffset < mouseOffset : handleOffset > mouseOffset;\n                                    var scrollObj = { };\n                                    var animationObj = {\n                                        easing : easing,\n                                        step : function(now) {\n                                            if(_scrollbarsHandlesDefineScrollPos) {\n                                                _viewportElement[scroll](now); //https://github.com/jquery/jquery/issues/4340\n                                                refreshScrollbarHandleOffset(isHorizontal, now);\n                                            }\n                                        }\n                                    };\n                                    instantScrollPosition = isFinite(instantScrollPosition) ? instantScrollPosition : 0;\n                                    instantScrollPosition = _isRTL && isHorizontal && !_rtlScrollBehavior.i ? (scrollRange - instantScrollPosition) : instantScrollPosition;\n\n                                    //_base.scrollStop();\n\n                                    if(instantScroll) {\n                                        _viewportElement[scroll](instantScrollPosition); //scroll instantly to new position\n                                        if(instantScrollTransition) {\n                                            //get the scroll position after instant scroll (in case CSS Snap Points are used) to get the correct snapped scroll position\n                                            //and the animation stops at the correct point\n                                            instantScrollPosition = _viewportElement[scroll]();\n                                            //scroll back to the position before instant scrolling so animation can be performed\n                                            _viewportElement[scroll](currScroll);\n\n                                            instantScrollPosition = rtlIsNormal && _rtlScrollBehavior.i ? (scrollRange - instantScrollPosition) : instantScrollPosition;\n                                            instantScrollPosition = rtlIsNormal && _rtlScrollBehavior.n ? -instantScrollPosition : instantScrollPosition;\n\n                                            scrollObj[xy] = instantScrollPosition;\n                                            _base.scroll(scrollObj, extendDeep(animationObj, {\n                                                duration : 130,\n                                                complete : scrollActionInstantFinished\n                                            }));\n                                        }\n                                        else\n                                            scrollActionInstantFinished();\n                                    }\n                                    else {\n                                        decreaseScroll = isFirstIteration ? decreaseScrollCondition : decreaseScroll;\n                                        finishedCondition = rtlIsNormal\n                                            ? (decreaseScroll ? handleOffset + handleLength >= mouseOffset : handleOffset <= mouseOffset)\n                                            : (decreaseScroll ? handleOffset <= mouseOffset : handleOffset + handleLength >= mouseOffset);\n\n                                        if (finishedCondition) {\n                                            clearTimeout(trackTimeout);\n                                            _base.scrollStop();\n                                            trackTimeout = undefined;\n                                            scrollActionFinsished(true);\n                                        }\n                                        else {\n                                            trackTimeout = setTimeout(scrollAction, timeoutDelay);\n\n                                            scrollObj[xy] = (decreaseScroll ? '-=' : '+=') + scrollDistance;\n                                            _base.scroll(scrollObj, extendDeep(animationObj, {\n                                                duration: scrollDuration\n                                            }));\n                                        }\n                                        isFirstIteration = false;\n                                    }\n                                }\n                            };\n                            if (ctrlKey)\n                                increaseTrackScrollAmount();\n\n                            mouseDownInvertedScale = getHostElementInvertedScale()[xy];\n                            mouseDownOffset = COMPATIBILITY.page(event)[xy];\n\n                            _scrollbarsHandlesDefineScrollPos = !getPreparedScrollbarsOption(strSnapHandle);\n                            addClass(_bodyElement, _classNameDragging);\n                            addClass(scrollbarVars._track, strActive);\n                            addClass(scrollbarVars._scrollbar, strActive);\n\n                            _documentElement.on(_strMouseTouchUpEvent, documentMouseTouchUp)\n                                .on(_strKeyDownEvent, documentKeyDown)\n                                .on(_strKeyUpEvent, documentKeyUp)\n                                .on(_strSelectStartEvent, documentOnSelectStart);\n\n                            scrollAction();\n                            COMPATIBILITY.prvD(event);\n                            COMPATIBILITY.stpP(event);\n                        }\n                    }\n                    function onTrackMouseTouchEnter(event) {\n                        //make sure both scrollbars will stay visible if one scrollbar is hovered if autoHide is \"scroll\" or \"move\".\n                        _scrollbarsHandleHovered = true;\n                        if (_scrollbarsAutoHideScroll || _scrollbarsAutoHideMove)\n                            refreshScrollbarsAutoHide(true);\n                    }\n                    function onTrackMouseTouchLeave(event) {\n                        _scrollbarsHandleHovered = false;\n                        if (_scrollbarsAutoHideScroll || _scrollbarsAutoHideMove)\n                            refreshScrollbarsAutoHide(false);\n                    }\n                    function onScrollbarMouseTouchDown(event) {\n                        COMPATIBILITY.stpP(event);\n                    }\n                    \n                    setupEvent(scrollbarVars._handle, \n                        _strMouseTouchDownEvent, \n                        onHandleMouseTouchDown);\n                    setupEvent(scrollbarVars._track,\n                        [_strMouseTouchDownEvent, _strMouseTouchEnter, _strMouseTouchLeave], \n                        [onTrackMouseTouchDown, onTrackMouseTouchEnter, onTrackMouseTouchLeave]);\n                    setupEvent(scrollbarVars._scrollbar, \n                        _strMouseTouchDownEvent, \n                        onScrollbarMouseTouchDown);\n\n                    if (_supportTransition) {\n                        scrollbarVars._scrollbar.on(_strTransitionEndEvent, function(event) {\n                            if (event.target !== scrollbarVars._scrollbar[0])\n                                return;\n                            refreshScrollbarHandleLength(isHorizontal);\n                            refreshScrollbarHandleOffset(isHorizontal);\n                        });\n                    }\n                }\n\n                /**\n                 * Shows or hides the given scrollbar and applied a class name which indicates if the scrollbar is scrollable or not.\n                 * @param isHorizontal True if the horizontal scrollbar is the target, false if the vertical scrollbar is the target.\n                 * @param shallBeVisible True if the scrollbar shall be shown, false if hidden.\n                 * @param canScroll True if the scrollbar is scrollable, false otherwise.\n                 */\n                function refreshScrollbarAppearance(isHorizontal, shallBeVisible, canScroll) {\n                    var scrollbarClassName = isHorizontal ? _classNameHostScrollbarHorizontalHidden : _classNameHostScrollbarVerticalHidden;\n                    var scrollbarElement = isHorizontal ? _scrollbarHorizontalElement : _scrollbarVerticalElement;\n\n                    if (shallBeVisible)\n                        removeClass(_hostElement, scrollbarClassName);\n                    else\n                        addClass(_hostElement, scrollbarClassName);\n\n                    if (canScroll)\n                        removeClass(scrollbarElement, _classNameScrollbarUnusable);\n                    else\n                        addClass(scrollbarElement, _classNameScrollbarUnusable);\n                }\n\n                /**\n                 * Autoshows / autohides both scrollbars with.\n                 * @param shallBeVisible True if the scrollbars shall be autoshown (only the case if they are hidden by a autohide), false if the shall be auto hidden.\n                 * @param delayfree True if the scrollbars shall be hidden without a delay, false or undefined otherwise.\n                 */\n                function refreshScrollbarsAutoHide(shallBeVisible, delayfree) {\n                    clearTimeout(_scrollbarsAutoHideTimeoutId);\n                    if (shallBeVisible) {\n                        //if(_hasOverflowCache.x && _hideOverflowCache.xs)\n                        removeClass(_scrollbarHorizontalElement, _classNameScrollbarAutoHidden);\n                        //if(_hasOverflowCache.y && _hideOverflowCache.ys)\n                        removeClass(_scrollbarVerticalElement, _classNameScrollbarAutoHidden);\n                    }\n                    else {\n                        var anyActive;\n                        var strActive = 'active';\n                        var hide = function () {\n                            if (!_scrollbarsHandleHovered && !_destroyed) {\n                                anyActive = _scrollbarHorizontalHandleElement.hasClass(strActive) || _scrollbarVerticalHandleElement.hasClass(strActive);\n                                if (!anyActive && (_scrollbarsAutoHideScroll || _scrollbarsAutoHideMove || _scrollbarsAutoHideLeave))\n                                    addClass(_scrollbarHorizontalElement, _classNameScrollbarAutoHidden);\n                                if (!anyActive && (_scrollbarsAutoHideScroll || _scrollbarsAutoHideMove || _scrollbarsAutoHideLeave))\n                                    addClass(_scrollbarVerticalElement, _classNameScrollbarAutoHidden);\n                            }\n                        };\n                        if (_scrollbarsAutoHideDelay > 0 && delayfree !== true)\n                            _scrollbarsAutoHideTimeoutId = setTimeout(hide, _scrollbarsAutoHideDelay);\n                        else\n                            hide();\n                    }\n                }\n\n                /**\n                 * Refreshes the handle length of the given scrollbar.\n                 * @param isHorizontal True if the horizontal scrollbar handle shall be refreshed, false if the vertical one shall be refreshed.\n                 */\n                function refreshScrollbarHandleLength(isHorizontal) {\n                    var handleCSS = {};\n                    var scrollbarVars = getScrollbarVars(isHorizontal);\n                    var scrollbarVarsInfo = scrollbarVars._info;\n                    var digit = 1000000;\n                    //get and apply intended handle length\n                    var handleRatio = MATH.min(1, (_hostSizeCache[scrollbarVars._w_h] - (_paddingAbsoluteCache ? (isHorizontal ? _paddingX : _paddingY) : 0)) / _contentScrollSizeCache[scrollbarVars._w_h]);\n                    handleCSS[scrollbarVars._width_height] = (MATH.floor(handleRatio * 100 * digit) / digit) + \"%\"; //the last * digit / digit is for flooring to the 4th digit\n\n                    if (!nativeOverlayScrollbarsAreActive())\n                        scrollbarVars._handle.css(handleCSS);\n\n                    //measure the handle length to respect min & max length\n                    scrollbarVarsInfo._handleLength = scrollbarVars._handle[0]['offset' + scrollbarVars._Width_Height];\n                    scrollbarVarsInfo._handleLengthRatio = handleRatio;\n                }\n\n                /**\n                 * Refreshes the handle offset of the given scrollbar.\n                 * @param isHorizontal True if the horizontal scrollbar handle shall be refreshed, false if the vertical one shall be refreshed.\n                 * @param scrollOrTransition The scroll position of the given scrollbar axis to which the handle shall be moved or a boolean which indicates whether a transition shall be applied. If undefined or boolean if the current scroll-offset is taken. (if isHorizontal ? scrollLeft : scrollTop)\n                 */\n                function refreshScrollbarHandleOffset(isHorizontal, scrollOrTransition) {\n                    var transition = type(scrollOrTransition) == TYPES.b;\n                    var transitionDuration = 250;\n                    var isRTLisHorizontal = _isRTL && isHorizontal;\n                    var scrollbarVars = getScrollbarVars(isHorizontal);\n                    var scrollbarVarsInfo = scrollbarVars._info;\n                    var strTranslateBrace = 'translate(';\n                    var strTransform = VENDORS._cssProperty('transform');\n                    var strTransition = VENDORS._cssProperty('transition');\n                    var nativeScroll = isHorizontal ? _viewportElement[_strScrollLeft]() : _viewportElement[_strScrollTop]();\n                    var currentScroll = scrollOrTransition === undefined || transition ? nativeScroll : scrollOrTransition;\n\n                    //measure the handle length to respect min & max length\n                    var handleLength = scrollbarVarsInfo._handleLength;\n                    var trackLength = scrollbarVars._track[0]['offset' + scrollbarVars._Width_Height];\n                    var handleTrackDiff = trackLength - handleLength;\n                    var handleCSS = {};\n                    var transformOffset;\n                    var translateValue;\n\n                    //DONT use the variable '_contentScrollSizeCache[scrollbarVars._w_h]' instead of '_viewportElement[0]['scroll' + scrollbarVars._Width_Height]'\n                    // because its a bit behind during the small delay when content size updates\n                    //(delay = mutationObserverContentLag, if its 0 then this var could be used)\n                    var maxScroll = (_viewportElementNative[_strScroll + scrollbarVars._Width_Height] - _viewportElementNative['client' + scrollbarVars._Width_Height]) * (_rtlScrollBehavior.n && isRTLisHorizontal ? -1 : 1); //* -1 if rtl scroll max is negative\n                    var getScrollRatio = function(base) {\n                        return isNaN(base / maxScroll) ? 0 : MATH.max(0, MATH.min(1, base / maxScroll));\n                    };\n                    var getHandleOffset = function(scrollRatio) {\n                        var offset = handleTrackDiff * scrollRatio;\n                        offset = isNaN(offset) ? 0 : offset;\n                        offset = (isRTLisHorizontal && !_rtlScrollBehavior.i) ? (trackLength - handleLength - offset) : offset;\n                        offset = MATH.max(0, offset);\n                        return offset;\n                    };\n                    var scrollRatio = getScrollRatio(nativeScroll);\n                    var unsnappedScrollRatio = getScrollRatio(currentScroll);\n                    var handleOffset = getHandleOffset(unsnappedScrollRatio);\n                    var snappedHandleOffset = getHandleOffset(scrollRatio);\n\n                    scrollbarVarsInfo._maxScroll = maxScroll;\n                    scrollbarVarsInfo._currentScroll = nativeScroll;\n                    scrollbarVarsInfo._currentScrollRatio = scrollRatio;\n\n                    if (_supportTransform) {\n                        transformOffset = isRTLisHorizontal ? -(trackLength - handleLength - handleOffset) : handleOffset; //in px\n                        //transformOffset = (transformOffset / trackLength * 100) * (trackLength / handleLength); //in %\n                        translateValue = isHorizontal ? strTranslateBrace + transformOffset + 'px, 0)' : strTranslateBrace + '0, ' + transformOffset + 'px)';\n\n                        handleCSS[strTransform] = translateValue;\n\n                        //apply or clear up transition\n                        if(_supportTransition)\n                            handleCSS[strTransition] = transition && MATH.abs(handleOffset - scrollbarVarsInfo._handleOffset) > 1 ? getCSSTransitionString(scrollbarVars._handle) + ', ' +  (strTransform + _strSpace + transitionDuration + 'ms') : _strEmpty;\n                    }\n                    else\n                        handleCSS[scrollbarVars._left_top] = handleOffset;\n\n\n                    //only apply css if offset has changed and overflow exists.\n                    if (!nativeOverlayScrollbarsAreActive()) {\n                        scrollbarVars._handle.css(handleCSS);\n\n                        //clear up transition\n                        if(_supportTransform && _supportTransition && transition) {\n                            scrollbarVars._handle.one(_strTransitionEndEvent, function() {\n                                if(!_destroyed)\n                                    scrollbarVars._handle.css(strTransition, _strEmpty);\n                            });\n                        }\n                    }\n\n                    scrollbarVarsInfo._handleOffset = handleOffset;\n                    scrollbarVarsInfo._snappedHandleOffset = snappedHandleOffset;\n                    scrollbarVarsInfo._trackLength = trackLength;\n                }\n\n                /**\n                 * Refreshes the interactivity of the given scrollbar element.\n                 * @param isTrack True if the track element is the target, false if the handle element is the target.\n                 * @param value True for interactivity false for no interactivity.\n                 */\n                function refreshScrollbarsInteractive(isTrack, value) {\n                    var action = value ? 'removeClass' : 'addClass';\n                    var element1 = isTrack ? _scrollbarHorizontalTrackElement : _scrollbarHorizontalHandleElement;\n                    var element2 = isTrack ? _scrollbarVerticalTrackElement : _scrollbarVerticalHandleElement;\n                    var className = isTrack ? _classNameScrollbarTrackOff : _classNameScrollbarHandleOff;\n\n                    element1[action](className);\n                    element2[action](className);\n                }\n\n                /**\n                 * Returns a object which is used for fast access for specific variables.\n                 * @param isHorizontal True if the horizontal scrollbar vars shall be accessed, false if the vertical scrollbar vars shall be accessed.\n                 * @returns {{wh: string, WH: string, lt: string, _wh: string, _lt: string, t: *, h: *, c: {}, s: *}}\n                 */\n                function getScrollbarVars(isHorizontal) {\n                    return {\n                        _width_height: isHorizontal ? _strWidth : _strHeight,\n                        _Width_Height: isHorizontal ? 'Width' : 'Height',\n                        _left_top: isHorizontal ? _strLeft : _strTop,\n                        _Left_Top: isHorizontal ? 'Left' : 'Top',\n                        _x_y: isHorizontal ? _strX : _strY,\n                        _X_Y: isHorizontal ? 'X' : 'Y',\n                        _w_h: isHorizontal ? 'w' : 'h',\n                        _l_t: isHorizontal ? 'l' : 't',\n                        _track: isHorizontal ? _scrollbarHorizontalTrackElement : _scrollbarVerticalTrackElement,\n                        _handle: isHorizontal ? _scrollbarHorizontalHandleElement : _scrollbarVerticalHandleElement,\n                        _scrollbar: isHorizontal ? _scrollbarHorizontalElement : _scrollbarVerticalElement,\n                        _info: isHorizontal ? _scrollHorizontalInfo : _scrollVerticalInfo\n                    };\n                }\n\n\n                //==== Scrollbar Corner ====//\n\n                /**\n                 * Builds or destroys the scrollbar corner DOM element.\n                 * @param destroy Indicates whether the DOM shall be build or destroyed.\n                 */\n                function setupScrollbarCornerDOM(destroy) {\n                    if(!destroy) {\n                         _scrollbarCornerElement = FRAMEWORK(generateDiv(_classNameScrollbarCorner));\n                        _hostElement.append(_scrollbarCornerElement);\n                    }\n                    else {\n                        remove(_scrollbarCornerElement);\n                    }\n                 }\n\n                /**\n                 * Initializes all scrollbar corner interactivity events.\n                 */\n                function setupScrollbarCornerEvents() {\n                    var insideIFrame = _windowElementNative.top !== _windowElementNative;\n                    var mouseDownPosition = { };\n                    var mouseDownSize = { };\n                    var mouseDownInvertedScale = { };\n\n                    _resizeOnMouseTouchDown = function(event) {\n                        if (onMouseTouchDownContinue(event)) {\n                            if (_mutationObserversConnected) {\n                                _resizeReconnectMutationObserver = true;\n                                disconnectMutationObservers();\n                            }\n\n                            mouseDownPosition = getCoordinates(event);\n\n                            mouseDownSize.w = _hostElementNative[LEXICON.oW] - (!_isBorderBox ? _paddingX : 0);\n                            mouseDownSize.h = _hostElementNative[LEXICON.oH] - (!_isBorderBox ? _paddingY : 0);\n                            mouseDownInvertedScale = getHostElementInvertedScale();\n\n                            _documentElement.on(_strSelectStartEvent, documentOnSelectStart)\n                                .on(_strMouseTouchMoveEvent, documentDragMove)\n                                .on(_strMouseTouchUpEvent, documentMouseTouchUp);\n\n                            addClass(_bodyElement, _classNameDragging);\n                            if (_scrollbarCornerElement.setCapture)\n                                _scrollbarCornerElement.setCapture();\n\n                            COMPATIBILITY.prvD(event);\n                            COMPATIBILITY.stpP(event);\n                        }\n                    };\n                    function documentDragMove(event) {\n                        if (onMouseTouchDownContinue(event)) {\n                            var pageOffset = getCoordinates(event);\n                            var hostElementCSS = { };\n                            if (_resizeHorizontal || _resizeBoth)\n                                hostElementCSS[_strWidth] = (mouseDownSize.w + (pageOffset.x - mouseDownPosition.x) * mouseDownInvertedScale.x);\n                            if (_resizeVertical || _resizeBoth)\n                                hostElementCSS[_strHeight] = (mouseDownSize.h + (pageOffset.y - mouseDownPosition.y) * mouseDownInvertedScale.y);\n                            _hostElement.css(hostElementCSS);\n                            COMPATIBILITY.stpP(event);\n                        }\n                        else {\n                            documentMouseTouchUp(event);\n                        }\n                    }\n                    function documentMouseTouchUp(event) {\n                        var eventIsTrusted = event !== undefined;\n\n                        _documentElement.off(_strSelectStartEvent, documentOnSelectStart)\n                            .off(_strMouseTouchMoveEvent, documentDragMove)\n                            .off(_strMouseTouchUpEvent, documentMouseTouchUp);\n\n                        removeClass(_bodyElement, _classNameDragging);\n                        if (_scrollbarCornerElement.releaseCapture)\n                            _scrollbarCornerElement.releaseCapture();\n\n                        if (eventIsTrusted) {\n                            if (_resizeReconnectMutationObserver)\n                                connectMutationObservers();\n                            _base.update(_strAuto);\n                        }\n                        _resizeReconnectMutationObserver = false;\n                    }\n                    function onMouseTouchDownContinue(event) {\n                        var originalEvent = event.originalEvent || event;\n                        var isTouchEvent = originalEvent.touches !== undefined;\n                        return _sleeping || _destroyed ? false : COMPATIBILITY.mBtn(event) === 1 || isTouchEvent;\n                    }\n                    function getCoordinates(event) {\n                        return _msieVersion && insideIFrame ? { x : event.screenX , y : event.screenY } : COMPATIBILITY.page(event);\n                    }\n                }\n\n\n                //==== Utils ====//\n\n                /**\n                 * Calls the callback with the given name. The Context of this callback is always _base (this).\n                 * @param name The name of the target which shall be called.\n                 * @param args The args with which the callback shall be called.\n                 */\n                function dispatchCallback(name, args) {\n                    if(_initialized) {\n                        var callback = _currentPreparedOptions.callbacks[name];\n                        var extensionOnName = name;\n                        var ext;\n\n                        if(extensionOnName.substr(0, 2) === 'on')\n                            extensionOnName = extensionOnName.substr(2, 1).toLowerCase() + extensionOnName.substr(3);\n\n                        if(type(callback) == TYPES.f)\n                            callback.call(_base, args);\n\n                        each(_extensions, function() {\n                            ext = this;\n                            if(type(ext.on) == TYPES.f)\n                                ext.on(extensionOnName, args);\n                        });\n                    }\n                    else if(!_destroyed)\n                        _callbacksInitQeueue.push({ n : name, a : args });\n                }\n\n                /**\n                 * Sets the \"top, right, bottom, left\" properties, with a given prefix, of the given css object.\n                 * @param targetCSSObject The css object to which the values shall be applied.\n                 * @param prefix The prefix of the \"top, right, bottom, left\" css properties. (example: 'padding-' is a valid prefix)\n                 * @param values A array of values which shall be applied to the \"top, right, bottom, left\" -properties. The array order is [top, right, bottom, left].\n                 * If this argument is undefined the value '' (empty string) will be applied to all properties.\n                 */\n                function setTopRightBottomLeft(targetCSSObject, prefix, values) {\n                    if (values === undefined)\n                        values = [_strEmpty, _strEmpty, _strEmpty, _strEmpty];\n\n                    targetCSSObject[prefix + _strTop] = values[0];\n                    targetCSSObject[prefix + _strRight] = values[1];\n                    targetCSSObject[prefix + _strBottom] = values[2];\n                    targetCSSObject[prefix + _strLeft] = values[3];\n                }\n\n                /**\n                 * Returns the computed CSS transition string from the given element.\n                 * @param element The element from which the transition string shall be returned.\n                 * @returns {string} The CSS transition string from the given element.\n                 */\n                function getCSSTransitionString(element) {\n                    var transitionStr = VENDORS._cssProperty('transition');\n                    var assembledValue = element.css(transitionStr);\n                    if(assembledValue)\n                        return assembledValue;\n                    var regExpString = '\\\\s*(' + '([^,(]+(\\\\(.+?\\\\))?)+' + ')[\\\\s,]*';\n                    var regExpMain = new RegExp(regExpString);\n                    var regExpValidate = new RegExp('^(' + regExpString + ')+$');\n                    var properties = 'property duration timing-function delay'.split(' ');\n                    var result = [ ];\n                    var strResult;\n                    var valueArray;\n                    var i = 0;\n                    var j;\n                    var splitCssStyleByComma = function(str) {\n                        strResult = [ ];\n                        if (!str.match(regExpValidate))\n                            return str;\n                        while (str.match(regExpMain)) {\n                            strResult.push(RegExp.$1);\n                            str = str.replace(regExpMain, _strEmpty);\n                        }\n\n                        return strResult;\n                    };\n                    for (; i < properties[LEXICON.l]; i++) {\n                        valueArray = splitCssStyleByComma(element.css(transitionStr + '-' + properties[i]));\n                        for (j = 0; j < valueArray[LEXICON.l]; j++)\n                            result[j] = (result[j] ? result[j] + _strSpace : _strEmpty) + valueArray[j];\n                    }\n                    return result.join(', ');\n                }\n\n                /**\n                 * Calculates the host-elements inverted scale. (invertedScale = 1 / scale)\n                 * @returns {{x: number, y: number}} The scale of the host-element.\n                 */\n                function getHostElementInvertedScale() {\n                    var rect = _paddingElementNative.getBoundingClientRect();\n                    return {\n                        x :  _supportTransform ? 1 / (MATH.round(rect.width) / _paddingElementNative[LEXICON.oW]) || 1 : 1,\n                        y :  _supportTransform ? 1 / (MATH.round(rect.height) / _paddingElementNative[LEXICON.oH]) || 1 : 1\n                    };\n                }\n\n                /**\n                 * Checks whether the given object is a HTMLElement.\n                 * @param o The object which shall be checked.\n                 * @returns {boolean} True the given object is a HTMLElement, false otherwise.\n                 */\n                function isHTMLElement(o) {\n                    var strOwnerDocument = 'ownerDocument';\n                    var strHTMLElement = 'HTMLElement';\n                    var wnd = o && o[strOwnerDocument] ? (o[strOwnerDocument].parentWindow || window) : window;\n                    return (\n                        typeof wnd[strHTMLElement] == TYPES.o ? o instanceof wnd[strHTMLElement] : //DOM2\n                        o && typeof o == TYPES.o && o !== null && o.nodeType === 1 && typeof o.nodeName == TYPES.s\n                    );\n                }\n\n                /**\n                 * Compares 2 arrays and returns the differences between them as a array.\n                 * @param a1 The first array which shall be compared.\n                 * @param a2 The second array which shall be compared.\n                 * @returns {Array} The differences between the two arrays.\n                 */\n                function getArrayDifferences(a1, a2) {\n                    var a = [ ];\n                    var diff = [ ];\n                    var i;\n                    var k;\n                    for (i = 0; i < a1.length; i++)\n                        a[a1[i]] = true;\n                    for (i = 0; i < a2.length; i++) {\n                        if (a[a2[i]])\n                            delete a[a2[i]];\n                        else\n                            a[a2[i]] = true;\n                    }\n                    for (k in a)\n                        diff.push(k);\n                    return diff;\n                }\n\n                /**\n                 * Returns Zero or the number to which the value can be parsed.\n                 * @param value The value which shall be parsed.\n                 * @param toFloat Indicates whether the number shall be parsed to a float.\n                 */\n                function parseToZeroOrNumber(value, toFloat) {\n                    var num = toFloat ? parseFloat(value) : parseInt(value, 10);\n                    return isNaN(num) ? 0 : num;\n                }\n\n                /**\n                 * Gets several information of the textarea and returns them as a object or undefined if the browser doesn't support it.\n                 * @returns {{cursorRow: Number, cursorCol, rows: Number, cols: number, wRow: number, pos: number, max : number}} or undefined if not supported.\n                 */\n                function getTextareaInfo() {\n                    //read needed values\n                    var textareaCursorPosition = _targetElementNative.selectionStart;\n                    if (textareaCursorPosition === undefined)\n                        return;\n\n                    var textareaValue = _targetElement.val();\n                    var textareaLength = textareaValue[LEXICON.l];\n                    var textareaRowSplit = textareaValue.split('\\n');\n                    var textareaLastRow = textareaRowSplit[LEXICON.l];\n                    var textareaCurrentCursorRowSplit = textareaValue.substr(0, textareaCursorPosition).split('\\n');\n                    var widestRow = 0;\n                    var textareaLastCol = 0;\n                    var cursorRow = textareaCurrentCursorRowSplit[LEXICON.l];\n                    var cursorCol = textareaCurrentCursorRowSplit[textareaCurrentCursorRowSplit[LEXICON.l] - 1][LEXICON.l];\n                    var rowCols;\n                    var i;\n\n                    //get widest Row and the last column of the textarea\n                    for (i = 0; i < textareaRowSplit[LEXICON.l]; i++) {\n                        rowCols = textareaRowSplit[i][LEXICON.l];\n                        if (rowCols > textareaLastCol) {\n                            widestRow = i + 1;\n                            textareaLastCol = rowCols;\n                        }\n                    }\n\n                    return {\n                        _cursorRow: cursorRow, //cursorRow\n                        _cursorColumn: cursorCol, //cursorCol\n                        _rows: textareaLastRow, //rows\n                        _columns: textareaLastCol, //cols\n                        _widestRow: widestRow, //wRow\n                        _cursorPosition: textareaCursorPosition, //pos\n                        _cursorMax: textareaLength //max\n                    };\n                }\n\n                /**\n                 * Determines whether native overlay scrollbars are active.\n                 * @returns {boolean} True if native overlay scrollbars are active, false otherwise.\n                 */\n                function nativeOverlayScrollbarsAreActive() {\n                    return (_ignoreOverlayScrollbarHidingCache && (_nativeScrollbarIsOverlaid.x && _nativeScrollbarIsOverlaid.y));\n                }\n\n                /**\n                 * Gets the element which is used to measure the content size.\n                 * @returns {*} TextareaCover if target element is textarea else the ContentElement.\n                 */\n                function getContentMeasureElement() {\n                    return _isTextarea ? _textareaCoverElement[0] : _contentElementNative;\n                }\n\n                /**\n                 * Generates a string which represents a HTML div with the given classes or attributes.\n                 * @param classesOrAttrs The class of the div as string or a object which represents the attributes of the div. (The class attribute can also be written as \"className\".)\n                 * @param content The content of the div as string.\n                 * @returns {string} The concated string which represents a HTML div and its content.\n                 */\n                function generateDiv(classesOrAttrs, content) {\n                    return '<div ' + (classesOrAttrs ? type(classesOrAttrs) == TYPES.s ?\n                        'class=\"' + classesOrAttrs + '\"' :\n                            (function() {\n                                var key;\n                                var attrs = '';\n                                if(FRAMEWORK.isPlainObject(classesOrAttrs)) {\n                                    for (key in classesOrAttrs)\n                                        attrs += (key === 'className' ? 'class' : key) + '=\"' + classesOrAttrs[key] + '\" ';\n                                }\n                                return attrs;\n                            })() :\n                            _strEmpty) +\n                        '>' +\n                        (content ? content : _strEmpty) +\n                        '</div>';\n                }\n\n                /**\n                 * Gets the value of the given property from the given object.\n                 * @param obj The object from which the property value shall be got.\n                 * @param path The property of which the value shall be got.\n                 * @returns {*} Returns the value of the searched property or undefined of the property wasn't found.\n                 */\n                function getObjectPropVal(obj, path) {\n                    var splits = path.split(_strDot);\n                    var i = 0;\n                    var val;\n                    for(; i < splits.length; i++) {\n                        if(!obj[LEXICON.hOP](splits[i]))\n                            return;\n                        val = obj[splits[i]];\n                        if(i < splits.length && type(val) == TYPES.o)\n                            obj = val;\n                    }\n                    return val;\n                }\n\n                /**\n                 * Sets the value of the given property from the given object.\n                 * @param obj The object from which the property value shall be set.\n                 * @param path The property of which the value shall be set.\n                 * @param val The value of the property which shall be set.\n                 */\n                function setObjectPropVal(obj, path, val) {\n                    var splits = path.split(_strDot);\n                    var splitsLength = splits.length;\n                    var i = 0;\n                    var extendObj = { };\n                    var extendObjRoot = extendObj;\n                    for(; i < splitsLength; i++)\n                        extendObj = extendObj[splits[i]] = i + 1 < splitsLength ? { } : val;\n                    FRAMEWORK.extend(obj, extendObjRoot, true);\n                }\n\n\n                //==== Utils Cache ====//\n\n                /**\n                 * Compares two values or objects and returns true if they aren't equal.\n                 * @param current The first value or object which shall be compared.\n                 * @param cache The second value or object which shall be compared.\n                 * @param force If true the returned value is always true.\n                 * @returns {boolean} True if both values or objects aren't equal or force is true, false otherwise.\n                 */\n                function checkCache(current, cache, force) {\n                    if (force)\n                        return force;\n                    if(type(current) == TYPES.o && type(cache) == TYPES.o) {\n                        for (var prop in current) {\n                            if(prop !== 'c') {\n                                if (current[LEXICON.hOP](prop) && cache[LEXICON.hOP](prop)) {\n                                    if(checkCache(current[prop], cache[prop]))\n                                        return true;\n                                }\n                                else {\n                                    return true;\n                                }\n                            }\n                        }\n                    }\n                    else {\n                        return current !== cache;\n                    }\n                    return false;\n                }\n\n\n                //==== Shortcuts ====//\n\n                /**\n                 * jQuery extend method shortcut with a appended \"true\" as first argument.\n                 */\n                function extendDeep() {\n                    return FRAMEWORK.extend.apply(this, [ true ].concat([].slice.call(arguments)));\n                }\n\n                /**\n                 * jQuery addClass method shortcut.\n                 */\n                function addClass(el, classes) {\n                    return _frameworkProto.addClass.call(el, classes);\n                }\n\n                /**\n                 * jQuery removeClass method shortcut.\n                 */\n                function removeClass(el, classes) {\n                    return _frameworkProto.removeClass.call(el, classes);\n                }\n\n                /**\n                 * jQuery remove method shortcut.\n                 */\n                function remove(el) {\n                    return _frameworkProto.remove.call(el);\n                }\n\n                /**\n                 * Finds the first child element with the given selector of the given element.\n                 * @param el The root element from which the selector shall be valid.\n                 * @param selector The selector of the searched element.\n                 * @returns {*} The first element which is a child of the given element and matches the givens selector.\n                 */\n                function findFirst(el, selector) {\n                    return _frameworkProto.find.call(el, selector).eq(0);\n                }\n\n\n                //==== API ====//\n\n                /**\n                 * Puts the instance to sleep. It wont respond to any changes in the DOM and won't update. Scrollbar Interactivity is also disabled as well as the resize handle.\n                 * This behavior can be reset by calling the update method.\n                 */\n                _base.sleep = function () {\n                    _sleeping = true;\n                };\n\n                /**\n                 * Updates the plugin and DOM to the current options.\n                 * This method should only be called if a update is 100% required.\n                 * @param force True if every property shall be updated and the cache shall be ignored.\n                 * !INTERNAL USAGE! : force can be a string \"auto\", \"sync\" or \"zoom\" too\n                 * if \"auto\" then before a real update the content size and host element attributes gets checked, and if they changed only then the update method will be called.\n                 * if \"sync\" then the async update process (MutationObserver or UpdateLoop) gets synchronized and a corresponding update takes place if one was needed due to pending changes.\n                 * if \"zoom\" then a update takes place where it's assumed that content and host size changed\n                 * @returns {boolean|undefined} \n                 * If force is \"sync\" then a boolean is returned which indicates whether a update was needed due to pending changes.\n                 * If force is \"auto\" then a boolean is returned whether a update was needed due to attribute or size changes.\n                 * undefined otherwise.\n                 */\n                _base.update = function (force) {\n                    var attrsChanged;\n                    var contentSizeC;\n                    var isString = type(force) == TYPES.s;\n                    var imgElementSelector = 'img';\n                    var imgElementLoadEvent = 'load';\n                    var doUpdateAuto;\n                    var mutHost;\n                    var mutContent;\n                    if(isString) {\n                        if (force === _strAuto) {\n                            attrsChanged = meaningfulAttrsChanged();\n                            contentSizeC = updateAutoContentSizeChanged();\n                            doUpdateAuto = attrsChanged || contentSizeC;\n                            if (doUpdateAuto) {\n                                update({\n                                    _contentSizeChanged : contentSizeC,\n                                    _changedOptions : _initialized ? undefined : _currentPreparedOptions\n                                });\n                            }\n                        }\n                        else if (force === _strSync) {\n                            if(_mutationObserversConnected) {\n                                mutHost = _mutationObserverHostCallback(_mutationObserverHost.takeRecords());\n                                mutContent = _mutationObserverContentCallback(_mutationObserverContent.takeRecords());\n                            }\n                            else {\n                                mutHost = _base.update(_strAuto);\n                            }\n                        }\n                        else if (force === 'zoom') {\n                            update({\n                                _hostSizeChanged : true,\n                                _contentSizeChanged : true\n                            });\n                        }\n                    }\n                    else {\n                        force = _sleeping || force;\n                        _sleeping = false;\n                        if(!_base.update(_strSync) || force)\n                            update({ _force : force });\n                    }\n                    if(!_isTextarea) {\n                        _contentElement.find(imgElementSelector).each(function(i, el) {\n                            var index = COMPATIBILITY.inA(el, _imgs);\n                            if (index === -1)\n                                FRAMEWORK(el).off(imgElementLoadEvent, imgOnLoad).on(imgElementLoadEvent, imgOnLoad);\n                        });\n                    }\n                    return doUpdateAuto || mutHost || mutContent;\n                };\n\n                /**\n                 Gets or sets the current options. The update method will be called automatically if new options were set.\n                 * @param newOptions If new options are given, then the new options will be set, if new options aren't given (undefined or a not a plain object) then the current options will be returned.\n                 * @param value If new options is a property path string, then this value will be used to set the option to which the property path string leads.\n                 * @returns {*}\n                 */\n                _base.options = function (newOptions, value) {\n                    var option = { };\n                    var changedOps;\n                    \n                    //return current options if newOptions are undefined or empty\n                    if (FRAMEWORK.isEmptyObject(newOptions) || !FRAMEWORK.isPlainObject(newOptions)) {\n                        if (type(newOptions) == TYPES.s) {\n                            if (arguments.length > 1) {\n                                setObjectPropVal(option, newOptions, value);\n                                changedOps = setOptions(option);\n                            }\n                            else\n                                return getObjectPropVal(_currentOptions, newOptions);\n                        }\n                        else\n                            return _currentOptions;\n                    }\n                    else {\n                        changedOps = setOptions(newOptions);\n                    }\n                    \n                    if(!FRAMEWORK.isEmptyObject(changedOps)) {\n                        update({ _changedOptions : changedOps });\n                    }    \n                };\n\n                /**\n                 * Restore the DOM, disconnects all observers, remove all resize observers and put the instance to sleep.\n                 */\n                _base.destroy = function () {\n                    //remove this instance from auto update loop\n                    autoUpdateLoop.remove(_base);\n\n                    //disconnect all mutation observers\n                    disconnectMutationObservers();\n\n                    //remove all resize observers\n                    setupResizeObserver(_sizeObserverElement);\n                    setupResizeObserver(_sizeAutoObserverElement);\n\n                    //remove all extensions\n                    for(var extName in _extensions)\n                        _base.removeExt(extName);\n\n                    //remove all events from host element\n                    setupHostMouseTouchEvents(true);\n\n                    //remove all events from structure\n                    setupStructureEvents(true);\n\n                    //remove all helper / detection elements\n                    if (_contentGlueElement)\n                        remove(_contentGlueElement);\n                    if (_contentArrangeElement)\n                        remove(_contentArrangeElement);\n                    if (_sizeAutoObserverAdded)\n                        remove(_sizeAutoObserverElement);\n\n                    //remove all generated DOM\n                    setupScrollbarsDOM(true);\n                    setupScrollbarCornerDOM(true);\n                    setupStructureDOM(true);\n\n                    //remove all generated image load events\n                    for(var i = 0; i < _imgs[LEXICON.l]; i++)\n                        FRAMEWORK(_imgs[i]).off('load', imgOnLoad);\n                    _imgs = undefined;\n\n                    _destroyed = true;\n                    _sleeping = true;\n\n                    //remove this instance from the instances list\n                    INSTANCES(pluginTargetElement, 0);\n                    dispatchCallback(\"onDestroyed\");\n\n                    //remove all properties and methods\n                    //for (var property in _base)\n                    //    delete _base[property];\n                    //_base = undefined;\n                };\n\n                /**\n                 * Scrolls to a given position or element.\n                 * @param coordinates\n                 * 1. Can be \"coordinates\" which looks like:\n                 *    { x : ?, y : ? } OR          Object with x and y properties\n                 *    { left : ?, top : ? } OR     Object with left and top properties\n                 *    { l : ?, t : ? } OR          Object with l and t properties\n                 *    [ ?, ? ] OR                  Array where the first two element are the coordinates (first is x, second is y)\n                 *    ?                            A single value which stays for both axis\n                 *    A value can be a number, a string or a calculation.\n                 *\n                 *    Operators:\n                 *    [NONE]  The current scroll will be overwritten by the value.\n                 *    '+='    The value will be added to the current scroll offset\n                 *    '-='    The value will be subtracted from the current scroll offset\n                 *    '*='    The current scroll wil be multiplicated by the value.\n                 *    '/='    The current scroll wil be divided by the value.\n                 *\n                 *    Units:\n                 *    [NONE]  The value is the final scroll amount.                   final = (value * 1)\n                 *    'px'    Same as none\n                 *    '%'     The value is dependent on the current scroll value.     final = ((currentScrollValue / 100) * value)\n                 *    'vw'    The value is multiplicated by the viewport width.       final = (value * viewportWidth)\n                 *    'vh'    The value is multiplicated by the viewport height.      final = (value * viewportHeight)\n                 *\n                 *    example final values:\n                 *    200, '200px', '50%', '1vw', '1vh', '+=200', '/=1vw', '*=2px', '-=5vh', '+=33%', '+= 50% - 2px', '-= 1vw - 50%'\n                 *\n                 * 2. Can be a HTML or jQuery element:\n                 *    The final scroll offset is the offset (without margin) of the given HTML / jQuery element.\n                 *\n                 * 3. Can be a object with a HTML or jQuery element with additional settings:\n                 *    {\n                 *      el : [HTMLElement, jQuery element],             MUST be specified, else this object isn't valid.\n                 *      scroll : [string, array, object],               Default value is 'always'.\n                 *      block : [string, array, object],                Default value is 'begin'.\n                 *      margin : [number, boolean, array, object]       Default value is false.\n                 *    }\n                 *\n                 *    Possible scroll settings are:\n                 *    'always'      Scrolls always.\n                 *    'ifneeded'    Scrolls only if the element isnt fully in view.\n                 *    'never'       Scrolls never.\n                 *\n                 *    Possible block settings are:\n                 *    'begin'   Both axis shall be docked to the \"begin\" edge. - The element will be docked to the top and left edge of the viewport.\n                 *    'end'     Both axis shall be docked to the \"end\" edge. - The element will be docked to the bottom and right edge of the viewport. (If direction is RTL to the bottom and left edge.)\n                 *    'center'  Both axis shall be docked to \"center\". - The element will be centered in the viewport.\n                 *    'nearest' The element will be docked to the nearest edge(s).\n                 *\n                 *    Possible margin settings are: -- The actual margin of the element wont be affect, this option affects only the final scroll offset.\n                 *    [BOOLEAN]                                         If true the css margin of the element will be used, if false no margin will be used.\n                 *    [NUMBER]                                          The margin will be used for all edges.\n                 *\n                 * @param duration The duration of the scroll animation, OR a jQuery animation configuration object.\n                 * @param easing The animation easing.\n                 * @param complete The animation complete callback.\n                 * @returns {{\n                 *   position: {x: number, y: number},\n                 *   ratio: {x: number, y: number},\n                 *   max: {x: number, y: number},\n                 *   handleOffset: {x: number, y: number},\n                 *   handleLength: {x: number, y: number},\n                 *   handleLengthRatio: {x: number, y: number}, t\n                 *   rackLength: {x: number, y: number},\n                 *   isRTL: boolean,\n                 *   isRTLNormalized: boolean\n                 *  }}\n                 */\n                _base.scroll = function (coordinates, duration, easing, complete) {\n                    if (arguments.length === 0 || coordinates === undefined) {\n                        var infoX = _scrollHorizontalInfo;\n                        var infoY = _scrollVerticalInfo;\n                        var normalizeInvert = _normalizeRTLCache && _isRTL && _rtlScrollBehavior.i;\n                        var normalizeNegate = _normalizeRTLCache && _isRTL && _rtlScrollBehavior.n;\n                        var scrollX = infoX._currentScroll;\n                        var scrollXRatio = infoX._currentScrollRatio;\n                        var maxScrollX = infoX._maxScroll;\n                        scrollXRatio = normalizeInvert ? 1 - scrollXRatio : scrollXRatio;\n                        scrollX = normalizeInvert ? maxScrollX - scrollX : scrollX;\n                        scrollX *= normalizeNegate ? -1 : 1;\n                        maxScrollX *= normalizeNegate ? -1 : 1;\n\n                        return {\n                            position : {\n                                x : scrollX,\n                                y : infoY._currentScroll\n                            },\n                            ratio : {\n                                x : scrollXRatio,\n                                y : infoY._currentScrollRatio\n                            },\n                            max : {\n                                x : maxScrollX,\n                                y : infoY._maxScroll\n                            },\n                            handleOffset : {\n                                x : infoX._handleOffset,\n                                y : infoY._handleOffset\n                            },\n                            handleLength : {\n                                x : infoX._handleLength,\n                                y : infoY._handleLength\n                            },\n                            handleLengthRatio : {\n                                x : infoX._handleLengthRatio,\n                                y : infoY._handleLengthRatio\n                            },\n                            trackLength : {\n                                x : infoX._trackLength,\n                                y : infoY._trackLength\n                            },\n                            snappedHandleOffset : {\n                                x : infoX._snappedHandleOffset,\n                                y : infoY._snappedHandleOffset\n                            },\n                            isRTL: _isRTL,\n                            isRTLNormalized: _normalizeRTLCache\n                        };\n                    }\n                    \n                    _base.update(_strSync);\n                    \n                    var normalizeRTL = _normalizeRTLCache;\n                    var coordinatesXAxisProps = [_strX, _strLeft, 'l'];\n                    var coordinatesYAxisProps = [_strY, _strTop, 't'];\n                    var coordinatesOperators = ['+=', '-=', '*=', '/='];\n                    var durationIsObject = type(duration) == TYPES.o;\n                    var completeCallback = durationIsObject ? duration.complete : complete;\n                    var i;\n                    var finalScroll = { };\n                    var specialEasing = {};\n                    var doScrollLeft;\n                    var doScrollTop;\n                    var animationOptions;\n                    var strEnd = 'end';\n                    var strBegin = 'begin';\n                    var strCenter = 'center';\n                    var strNearest = 'nearest';\n                    var strAlways = 'always';\n                    var strNever = 'never';\n                    var strIfNeeded = 'ifneeded';\n                    var strLength = LEXICON.l;\n                    var settingsAxis;\n                    var settingsScroll;\n                    var settingsBlock;\n                    var settingsMargin;\n                    var finalElement;\n                    var elementObjSettingsAxisValues = [_strX, _strY, 'xy', 'yx'];\n                    var elementObjSettingsBlockValues = [strBegin, strEnd, strCenter, strNearest];\n                    var elementObjSettingsScrollValues = [strAlways, strNever, strIfNeeded];\n                    var coordinatesIsElementObj = coordinates[LEXICON.hOP]('el');\n                    var possibleElement = coordinatesIsElementObj ? coordinates.el : coordinates;\n                    var possibleElementIsJQuery = possibleElement instanceof FRAMEWORK || JQUERY ? possibleElement instanceof JQUERY : false;\n                    var possibleElementIsHTMLElement = possibleElementIsJQuery ? false : isHTMLElement(possibleElement);\n                    var proxyCompleteCallback = type(completeCallback) != TYPES.f ? undefined : function() {\n                        if(doScrollLeft)\n                            refreshScrollbarHandleOffset(true);\n                        if(doScrollTop)\n                            refreshScrollbarHandleOffset(false);\n                        completeCallback();\n                    };\n                    var checkSettingsStringValue = function (currValue, allowedValues) {\n                        for (i = 0; i < allowedValues[strLength]; i++) {\n                            if (currValue === allowedValues[i])\n                                return true;\n                        }\n                        return false;\n                    };\n                    var getRawScroll = function (isX, coordinates) {\n                        var coordinateProps = isX ? coordinatesXAxisProps : coordinatesYAxisProps;\n                        coordinates = type(coordinates) == TYPES.s || type(coordinates) == TYPES.n ? [ coordinates, coordinates ] : coordinates;\n\n                        if (type(coordinates) == TYPES.a)\n                            return isX ? coordinates[0] : coordinates[1];\n                        else if (type(coordinates) == TYPES.o) {\n                            //decides RTL normalization \"hack\" with .n\n                            //normalizeRTL = type(coordinates.n) == TYPES.b ? coordinates.n : normalizeRTL; \n                            for (i = 0; i < coordinateProps[strLength]; i++)\n                                if (coordinateProps[i] in coordinates)\n                                    return coordinates[coordinateProps[i]];\n                        }\n                    };\n                    var getFinalScroll = function (isX, rawScroll) {\n                        var isString = type(rawScroll) == TYPES.s;\n                        var operator;\n                        var amount;\n                        var scrollInfo = isX ? _scrollHorizontalInfo : _scrollVerticalInfo;\n                        var currScroll = scrollInfo._currentScroll;\n                        var maxScroll = scrollInfo._maxScroll;\n                        var mult = ' * ';\n                        var finalValue;\n                        var isRTLisX = _isRTL && isX;\n                        var normalizeShortcuts = isRTLisX && _rtlScrollBehavior.n && !normalizeRTL;\n                        var strReplace = 'replace';\n                        var evalFunc = eval;\n                        var possibleOperator;\n                        if (isString) {\n                            //check operator\n                            if (rawScroll[strLength] > 2) {\n                                possibleOperator = rawScroll.substr(0, 2);\n                                if(inArray(possibleOperator, coordinatesOperators) > -1)\n                                    operator = possibleOperator;\n                            }\n\n                            //calculate units and shortcuts\n                            rawScroll = operator ? rawScroll.substr(2) : rawScroll;\n                            rawScroll = rawScroll\n                            [strReplace](/min/g, 0) //'min' = 0%\n                            [strReplace](/</g, 0)   //'<'   = 0%\n                            [strReplace](/max/g, (normalizeShortcuts ? '-' : _strEmpty) + _strHundredPercent)    //'max' = 100%\n                            [strReplace](/>/g, (normalizeShortcuts ? '-' : _strEmpty) + _strHundredPercent)      //'>'   = 100%\n                            [strReplace](/px/g, _strEmpty)\n                            [strReplace](/%/g, mult + (maxScroll * (isRTLisX && _rtlScrollBehavior.n ? -1 : 1) / 100.0))\n                            [strReplace](/vw/g, mult + _viewportSize.w)\n                            [strReplace](/vh/g, mult + _viewportSize.h);\n                            amount = parseToZeroOrNumber(isNaN(rawScroll) ? parseToZeroOrNumber(evalFunc(rawScroll), true).toFixed() : rawScroll);\n                        }\n                        else {\n                            amount = rawScroll;\n                        }\n\n                        if (amount !== undefined && !isNaN(amount) && type(amount) == TYPES.n) {\n                            var normalizeIsRTLisX = normalizeRTL && isRTLisX;\n                            var operatorCurrScroll = currScroll * (normalizeIsRTLisX && _rtlScrollBehavior.n ? -1 : 1);\n                            var invert = normalizeIsRTLisX && _rtlScrollBehavior.i;\n                            var negate = normalizeIsRTLisX && _rtlScrollBehavior.n;\n                            operatorCurrScroll = invert ? (maxScroll - operatorCurrScroll) : operatorCurrScroll;\n                            switch (operator) {\n                                case '+=':\n                                    finalValue = operatorCurrScroll + amount;\n                                    break;\n                                case '-=':\n                                    finalValue = operatorCurrScroll - amount;\n                                    break;\n                                case '*=':\n                                    finalValue = operatorCurrScroll * amount;\n                                    break;\n                                case '/=':\n                                    finalValue = operatorCurrScroll / amount;\n                                    break;\n                                default:\n                                    finalValue = amount;\n                                    break;\n                            }\n                            finalValue = invert ? maxScroll - finalValue : finalValue;\n                            finalValue *= negate ? -1 : 1;\n                            finalValue = isRTLisX && _rtlScrollBehavior.n ? MATH.min(0, MATH.max(maxScroll, finalValue)) : MATH.max(0, MATH.min(maxScroll, finalValue));\n                        }\n                        return finalValue === currScroll ? undefined : finalValue;\n                    };\n                    var getPerAxisValue = function (value, valueInternalType, defaultValue, allowedValues) {\n                        var resultDefault = [ defaultValue, defaultValue ];\n                        var valueType = type(value);\n                        var valueArrLength;\n                        var valueArrItem;\n\n                        //value can be [ string, or array of two strings ]\n                        if (valueType == valueInternalType) {\n                            value = [value, value];\n                        }\n                        else if (valueType == TYPES.a) {\n                            valueArrLength = value[strLength];\n                            if (valueArrLength > 2 || valueArrLength < 1)\n                                value = resultDefault;\n                            else {\n                                if (valueArrLength === 1)\n                                    value[1] = defaultValue;\n                                for (i = 0; i < valueArrLength; i++) {\n                                    valueArrItem = value[i];\n                                    if (type(valueArrItem) != valueInternalType || !checkSettingsStringValue(valueArrItem, allowedValues)) {\n                                        value = resultDefault;\n                                        break;\n                                    }\n                                }\n                            }\n                        }\n                        else if (valueType == TYPES.o)\n                            value = [ value[_strX]|| defaultValue, value[_strY] || defaultValue];\n                        else\n                            value = resultDefault;\n                        return { x : value[0], y : value[1] };\n                    };\n                    var generateMargin = function (marginTopRightBottomLeftArray) {\n                        var result = [ ];\n                        var currValue;\n                        var currValueType;\n                        var valueDirections = [ _strTop, _strRight, _strBottom, _strLeft ];\n                        for(i = 0; i < marginTopRightBottomLeftArray[strLength]; i++) {\n                            if(i === valueDirections[strLength])\n                                break;\n                            currValue = marginTopRightBottomLeftArray[i];\n                            currValueType = type(currValue);\n                            if(currValueType == TYPES.b)\n                                result.push(currValue ? parseToZeroOrNumber(finalElement.css(_strMarginMinus + valueDirections[i])) : 0);\n                            else\n                                result.push(currValueType == TYPES.n ? currValue : 0);\n                        }\n                        return result;\n                    };\n\n                    if (possibleElementIsJQuery || possibleElementIsHTMLElement) {\n                        //get settings\n                        var margin = coordinatesIsElementObj ? coordinates.margin : 0;\n                        var axis = coordinatesIsElementObj ? coordinates.axis : 0;\n                        var scroll = coordinatesIsElementObj ? coordinates.scroll : 0;\n                        var block = coordinatesIsElementObj ? coordinates.block : 0;\n                        var marginDefault = [ 0, 0, 0, 0 ];\n                        var marginType = type(margin);\n                        var marginLength;\n                        finalElement = possibleElementIsJQuery ? possibleElement : FRAMEWORK(possibleElement);\n                        if (finalElement[strLength] === 0)\n                            return;\n\n                        //margin can be [ boolean, number, array of 2, array of 4, object ]\n                        if (marginType == TYPES.n || marginType == TYPES.b)\n                            margin = generateMargin([margin, margin, margin, margin]);\n                        else if (marginType == TYPES.a) {\n                            marginLength = margin[strLength];\n                            if(marginLength === 2)\n                                margin = generateMargin([margin[0], margin[1], margin[0], margin[1]]);\n                            else if(marginLength >= 4)\n                                margin = generateMargin(margin);\n                            else\n                                margin = marginDefault;\n                        }\n                        else if (marginType == TYPES.o)\n                            margin = generateMargin([margin[_strTop], margin[_strRight], margin[_strBottom], margin[_strLeft]]);\n                        else\n                            margin = marginDefault;\n\n                        //block = type(block) === TYPES.b ? block ? [ strNearest, strBegin ] : [ strNearest, strEnd ] : block;\n                        settingsAxis = checkSettingsStringValue(axis, elementObjSettingsAxisValues) ? axis : 'xy';\n                        settingsScroll = getPerAxisValue(scroll, TYPES.s, strAlways, elementObjSettingsScrollValues);\n                        settingsBlock = getPerAxisValue(block, TYPES.s, strBegin, elementObjSettingsBlockValues);\n                        settingsMargin = margin;\n\n                        var viewportScroll = {\n                            l: _scrollHorizontalInfo._currentScroll,\n                            t: _scrollVerticalInfo._currentScroll\n                        };\n                        // use padding element instead of viewport element because padding element has never padding, margin or position applied.\n                        var viewportOffset = _paddingElement.offset();\n\n                        //get coordinates\n                        var elementOffset = finalElement.offset();\n                        var doNotScroll = {\n                            x : settingsScroll.x == strNever || settingsAxis == _strY,\n                            y : settingsScroll.y == strNever || settingsAxis == _strX\n                        };\n                        elementOffset[_strTop] -= settingsMargin[0];\n                        elementOffset[_strLeft] -= settingsMargin[3];\n                        var elementScrollCoordinates = {\n                            x: MATH.round(elementOffset[_strLeft] - viewportOffset[_strLeft] + viewportScroll.l),\n                            y: MATH.round(elementOffset[_strTop] - viewportOffset[_strTop] + viewportScroll.t)\n                        };\n                        if (_isRTL) {\n                            if (!_rtlScrollBehavior.n && !_rtlScrollBehavior.i)\n                                elementScrollCoordinates.x = MATH.round(viewportOffset[_strLeft] - elementOffset[_strLeft] + viewportScroll.l);\n                            if (_rtlScrollBehavior.n && normalizeRTL)\n                                elementScrollCoordinates.x *= -1;\n                            if (_rtlScrollBehavior.i && normalizeRTL)\n                                elementScrollCoordinates.x = MATH.round(viewportOffset[_strLeft] - elementOffset[_strLeft] + (_scrollHorizontalInfo._maxScroll - viewportScroll.l));\n                        }\n\n                        //measuring is required\n                        if (settingsBlock.x != strBegin || settingsBlock.y != strBegin || settingsScroll.x == strIfNeeded || settingsScroll.y == strIfNeeded || _isRTL) {\n                            var measuringElm = finalElement[0];\n                            var rawElementSize = _supportTransform ? measuringElm.getBoundingClientRect() : {\n                                width : measuringElm[LEXICON.oW],\n                                height : measuringElm[LEXICON.oH]\n                            };\n                            var elementSize = {\n                                w: rawElementSize[_strWidth] + settingsMargin[3] + settingsMargin[1],\n                                h: rawElementSize[_strHeight] + settingsMargin[0] + settingsMargin[2]\n                            };\n                            var finalizeBlock = function(isX) {\n                                var vars = getScrollbarVars(isX);\n                                var wh = vars._w_h;\n                                var lt = vars._left_top;\n                                var xy = vars._x_y;\n                                var blockIsEnd = settingsBlock[xy] == (isX ? _isRTL ? strBegin : strEnd : strEnd);\n                                var blockIsCenter = settingsBlock[xy] == strCenter;\n                                var blockIsNearest = settingsBlock[xy] == strNearest;\n                                var scrollNever = settingsScroll[xy] == strNever;\n                                var scrollIfNeeded = settingsScroll[xy] == strIfNeeded;\n                                var vpSize = _viewportSize[wh];\n                                var vpOffset = viewportOffset[lt];\n                                var elSize = elementSize[wh];\n                                var elOffset = elementOffset[lt];\n                                var divide = blockIsCenter ? 2 : 1;\n                                var elementCenterOffset = elOffset + (elSize / 2);\n                                var viewportCenterOffset = vpOffset + (vpSize / 2);\n                                var isInView =\n                                    elSize <= vpSize\n                                    && elOffset >= vpOffset\n                                    && elOffset + elSize <= vpOffset + vpSize;\n\n                                if(scrollNever)\n                                    doNotScroll[xy] = true;\n                                else if(!doNotScroll[xy]) {\n                                    if (blockIsNearest || scrollIfNeeded) {\n                                        doNotScroll[xy] = scrollIfNeeded ? isInView : false;\n                                        blockIsEnd = elSize < vpSize ? elementCenterOffset > viewportCenterOffset : elementCenterOffset < viewportCenterOffset;\n                                    }\n                                    elementScrollCoordinates[xy] -= blockIsEnd || blockIsCenter ? ((vpSize / divide) - (elSize / divide)) * (isX && _isRTL && normalizeRTL ? -1 : 1) : 0;\n                                }\n                            };\n                            finalizeBlock(true);\n                            finalizeBlock(false);\n                        }\n\n                        if (doNotScroll.y)\n                            delete elementScrollCoordinates.y;\n                        if (doNotScroll.x)\n                            delete elementScrollCoordinates.x;\n\n                        coordinates = elementScrollCoordinates;\n                    }\n\n                    finalScroll[_strScrollLeft] = getFinalScroll(true, getRawScroll(true, coordinates));\n                    finalScroll[_strScrollTop] = getFinalScroll(false, getRawScroll(false, coordinates));\n                    doScrollLeft = finalScroll[_strScrollLeft] !== undefined;\n                    doScrollTop = finalScroll[_strScrollTop] !== undefined;\n\n                    if ((doScrollLeft || doScrollTop) && (duration > 0 || durationIsObject)) {\n                        if (durationIsObject) {\n                            duration.complete = proxyCompleteCallback;\n                            _viewportElement.animate(finalScroll, duration);\n                        }\n                        else {\n                            animationOptions = {\n                                duration: duration,\n                                complete: proxyCompleteCallback\n                            };\n                            if (type(easing) == TYPES.a || FRAMEWORK.isPlainObject(easing)) {\n                                specialEasing[_strScrollLeft] = easing[0] || easing.x;\n                                specialEasing[_strScrollTop] = easing[1] || easing.y;\n                                animationOptions.specialEasing = specialEasing;\n                            }\n                            else {\n                                animationOptions.easing = easing;\n                            }\n                            _viewportElement.animate(finalScroll, animationOptions);\n                        }\n                    }\n                    else {\n                        if (doScrollLeft)\n                            _viewportElement[_strScrollLeft](finalScroll[_strScrollLeft]);\n                        if (doScrollTop)\n                            _viewportElement[_strScrollTop](finalScroll[_strScrollTop]);\n                    }\n                };\n\n                /**\n                 * Stops all scroll animations.\n                 * @returns {*} The current OverlayScrollbars instance (for chaining).\n                 */\n                _base.scrollStop = function (param1, param2, param3) {\n                    _viewportElement.stop(param1, param2, param3);\n                    return _base;\n                };\n\n                /**\n                 * Returns all relevant elements.\n                 * @param elementName The name of the element which shall be returned.\n                 * @returns {{target: *, host: *, padding: *, viewport: *, content: *, scrollbarHorizontal: {scrollbar: *, track: *, handle: *}, scrollbarVertical: {scrollbar: *, track: *, handle: *}, scrollbarCorner: *} | *}\n                 */\n                _base.getElements = function (elementName) {\n                    var obj = {\n                        target: _targetElementNative,\n                        host: _hostElementNative,\n                        padding: _paddingElementNative,\n                        viewport: _viewportElementNative,\n                        content: _contentElementNative,\n                        scrollbarHorizontal: {\n                            scrollbar: _scrollbarHorizontalElement[0],\n                            track: _scrollbarHorizontalTrackElement[0],\n                            handle: _scrollbarHorizontalHandleElement[0]\n                        },\n                        scrollbarVertical: {\n                            scrollbar: _scrollbarVerticalElement[0],\n                            track: _scrollbarVerticalTrackElement[0],\n                            handle: _scrollbarVerticalHandleElement[0]\n                        },\n                        scrollbarCorner: _scrollbarCornerElement[0]\n                    };\n                    return type(elementName) == TYPES.s ? getObjectPropVal(obj, elementName) : obj;\n                };\n\n                /**\n                 * Returns a object which describes the current state of this instance.\n                 * @param stateProperty A specific property from the state object which shall be returned.\n                 * @returns {{widthAuto, heightAuto, overflowAmount, hideOverflow, hasOverflow, contentScrollSize, viewportSize, hostSize, autoUpdate} | *}\n                 */\n                _base.getState = function (stateProperty) {\n                    function prepare(obj) {\n                        if (!FRAMEWORK.isPlainObject(obj))\n                            return obj;\n                        var extended = extendDeep({}, obj);\n                        var changePropertyName = function (from, to) {\n                            if (extended[LEXICON.hOP](from)) {\n                                extended[to] = extended[from];\n                                delete extended[from];\n                            }\n                        };\n                        changePropertyName('w', _strWidth); //change w to width\n                        changePropertyName('h', _strHeight); //change h to height\n                        delete extended.c; //delete c (the 'changed' prop)\n                        return extended;\n                    };\n                    var obj = {\n                        destroyed: !!prepare(_destroyed),\n                        sleeping: !!prepare(_sleeping),\n                        autoUpdate: prepare(!_mutationObserversConnected),\n                        widthAuto: prepare(_widthAutoCache),\n                        heightAuto: prepare(_heightAutoCache),\n                        padding: prepare(_cssPaddingCache),\n                        overflowAmount: prepare(_overflowAmountCache),\n                        hideOverflow: prepare(_hideOverflowCache),\n                        hasOverflow: prepare(_hasOverflowCache),\n                        contentScrollSize: prepare(_contentScrollSizeCache),\n                        viewportSize: prepare(_viewportSize),\n                        hostSize: prepare(_hostSizeCache),\n                        documentMixed : prepare(_documentMixed)\n                    };\n                    return type(stateProperty) == TYPES.s ? getObjectPropVal(obj, stateProperty) : obj;\n                };\n\n                /**\n                 * Gets all or specific extension instance.\n                 * @param extName The name of the extension from which the instance shall be got.\n                 * @returns {{}} The instance of the extension with the given name or undefined if the instance couldn't be found.\n                 */\n                _base.ext = function(extName) {\n                    var result;\n                    var privateMethods = _extensionsPrivateMethods.split(' ');\n                    var i = 0;\n                    if(type(extName) == TYPES.s) {\n                        if(_extensions[LEXICON.hOP](extName)) {\n                            result = extendDeep({}, _extensions[extName]);\n                            for (; i < privateMethods.length; i++)\n                                delete result[privateMethods[i]];\n                        }\n                    }\n                    else {\n                        result = { };\n                        for(i in _extensions)\n                            result[i] = extendDeep({ }, _base.ext(i));\n                    }\n                    return result;\n                };\n\n                /**\n                 * Adds a extension to this instance.\n                 * @param extName The name of the extension which shall be added.\n                 * @param extensionOptions The extension options which shall be used.\n                 * @returns {{}} The instance of the added extension or undefined if the extension couldn't be added properly.\n                 */\n                _base.addExt = function(extName, extensionOptions) {\n                    var registeredExtensionObj = window[PLUGINNAME].extension(extName);\n                    var instance;\n                    var instanceAdded;\n                    var instanceContract;\n                    var contractResult;\n                    var contractFulfilled = true;\n                    if(registeredExtensionObj) {\n                        if(!_extensions[LEXICON.hOP](extName)) {\n                            instance = registeredExtensionObj.extensionFactory.call(_base,\n                                extendDeep({ }, registeredExtensionObj.defaultOptions),\n                                FRAMEWORK,\n                                COMPATIBILITY);\n\n                            if (instance) {\n                                instanceContract = instance.contract;\n                                if (type(instanceContract) == TYPES.f) {\n                                    contractResult = instanceContract(window);\n                                    contractFulfilled = type(contractResult) == TYPES.b ? contractResult : contractFulfilled;\n                                }\n                                if(contractFulfilled) {\n                                    _extensions[extName] = instance;\n                                    instanceAdded = instance.added;\n                                    if(type(instanceAdded) == TYPES.f)\n                                        instanceAdded(extensionOptions);\n\n                                    return _base.ext(extName);\n                                }\n                            }\n                        }\n                        else\n                            return _base.ext(extName);\n                    }\n                    else\n                        console.warn(\"A extension with the name \\\"\" + extName + \"\\\" isn't registered.\");\n                };\n\n                /**\n                 * Removes a extension from this instance.\n                 * @param extName The name of the extension which shall be removed.\n                 * @returns {boolean} True if the extension was removed, false otherwise e.g. if the extension wasn't added before.\n                 */\n                _base.removeExt = function(extName) {\n                    var instance = _extensions[extName];\n                    var instanceRemoved;\n                    if(instance) {\n                        delete _extensions[extName];\n\n                        instanceRemoved = instance.removed;\n                        if(type(instanceRemoved) == TYPES.f)\n                            instanceRemoved();\n\n                        return true;\n                    }\n                    return false;\n                };\n\n                /**\n                 * Constructs the plugin.\n                 * @param targetElement The element to which the plugin shall be applied.\n                 * @param options The initial options of the plugin.\n                 * @param extensions The extension(s) which shall be added right after the initialization.\n                 * @returns {boolean} True if the plugin was successfully initialized, false otherwise.\n                 */\n                function construct(targetElement, options, extensions) {\n                    _defaultOptions = globals.defaultOptions;\n                    _nativeScrollbarStyling = globals.nativeScrollbarStyling;\n                    _nativeScrollbarSize = extendDeep({}, globals.nativeScrollbarSize);\n                    _nativeScrollbarIsOverlaid = extendDeep({}, globals.nativeScrollbarIsOverlaid);\n                    _overlayScrollbarDummySize = extendDeep({}, globals.overlayScrollbarDummySize);\n                    _rtlScrollBehavior = extendDeep({}, globals.rtlScrollBehavior);\n\n                    //parse & set options but don't update\n                    setOptions(extendDeep({ }, _defaultOptions, options));\n\n                    //check if the plugin hasn't to be initialized\n                    if (_nativeScrollbarIsOverlaid.x && _nativeScrollbarIsOverlaid.x && !_currentPreparedOptions.nativeScrollbarsOverlaid.initialize) {\n                        dispatchCallback(\"onInitializationWithdrawn\");\n                        return false;\n                    }\n\n                    _cssCalc = globals.cssCalc;\n                    _msieVersion = globals.msie;\n                    _autoUpdateRecommended = globals.autoUpdateRecommended;\n                    _supportTransition = globals.supportTransition;\n                    _supportTransform = globals.supportTransform;\n                    _supportPassiveEvents = globals.supportPassiveEvents;\n                    _supportResizeObserver = globals.supportResizeObserver;\n                    _supportMutationObserver = globals.supportMutationObserver;\n                    _restrictedMeasuring = globals.restrictedMeasuring;\n                    _documentElement = FRAMEWORK(targetElement.ownerDocument);\n                    _documentElementNative = _documentElement[0];\n                    _windowElement = FRAMEWORK(_documentElementNative.defaultView || _documentElementNative.parentWindow);\n                    _windowElementNative = _windowElement[0];\n                    _htmlElement = findFirst(_documentElement, 'html');\n                    _bodyElement =  findFirst(_htmlElement, 'body');\n                    _targetElement = FRAMEWORK(targetElement);\n                    _targetElementNative = _targetElement[0];\n                    _isTextarea = _targetElement.is('textarea');\n                    _isBody = _targetElement.is('body');\n                    _documentMixed = _documentElementNative !== document;\n\n                    var initBodyScroll;\n                    if (_isBody) {\n                        initBodyScroll = {};\n                        initBodyScroll.l = MATH.max(_targetElement[_strScrollLeft](), _htmlElement[_strScrollLeft](), _windowElement[_strScrollLeft]());\n                        initBodyScroll.t = MATH.max(_targetElement[_strScrollTop](), _htmlElement[_strScrollTop](), _windowElement[_strScrollTop]());\n                    }\n\n                    //build OverlayScrollbars DOM and Events\n                    setupStructureDOM();\n                    setupStructureEvents();\n\n                    //build Scrollbars DOM and Events\n                    setupScrollbarsDOM();\n                    setupScrollbarEvents(true);\n                    setupScrollbarEvents(false);\n\n                    //build Scrollbar Corner DOM and Events\n                    setupScrollbarCornerDOM();\n                    setupScrollbarCornerEvents();\n\n                    //create mutation observers\n                    createMutationObservers();\n\n                    if(_isBody) {\n                        //apply the body scroll to handle it right in the update method\n                        _viewportElement[_strScrollLeft](initBodyScroll.l)[_strScrollTop](initBodyScroll.t);\n\n                        //set the focus on the viewport element so you dont have to click on the page to use keyboard keys (up / down / space) for scrolling\n                        if(document.activeElement == targetElement && _viewportElementNative.focus) {\n                            //set a tabindex to make the viewportElement focusable\n                            _viewportElement.attr('tabindex', '-1');\n                            _viewportElementNative.focus();\n                            /* the tabindex has to be removed due to;\n                             * If you set the tabindex attribute on an <div>, then its child content cannot be scrolled with the arrow keys unless you set tabindex on the content, too\n                             * https://developer.mozilla.org/en-US/docs/Web/HTML/Global_attributes/tabindex\n                             */\n                            _viewportElement.one(_strMouseTouchDownEvent, function() {\n                                _viewportElement.removeAttr('tabindex');\n                            });\n                        }\n                    }\n\n                    //build resize observer for the host element\n                    setupResizeObserver(_sizeObserverElement, hostOnResized);\n\n                    //update for the first time & initialize cache\n                    _base.update(_strAuto);\n\n                    //the plugin is initialized now!\n                    _initialized = true;\n                    dispatchCallback(\"onInitialized\");\n\n                    //call all callbacks which would fire before the initialized was complete\n                    each(_callbacksInitQeueue, function(index, value) { dispatchCallback(value.n, value.a); });\n                    _callbacksInitQeueue = [ ];\n\n                    //add extensions\n                    if(type(extensions) == TYPES.s)\n                        extensions = [ extensions ];\n                    if(COMPATIBILITY.isA(extensions))\n                        each(extensions, function (index, value) {_base.addExt(value); });\n                    else if(FRAMEWORK.isPlainObject(extensions))\n                        each(extensions, function (key, value) { _base.addExt(key, value); });\n\n                    //add the transition class for transitions AFTER the first update & AFTER the applied extensions (for preventing unwanted transitions)\n                    setTimeout(function () {\n                        if (_supportTransition && !_destroyed)\n                            addClass(_hostElement, _classNameHostTransition);\n                    }, 333);\n\n                    return _initialized;\n                }\n\n                if (construct(pluginTargetElement, options, extensions)) {\n                    INSTANCES(pluginTargetElement, _base);\n                    return _base;\n                }\n                _base = undefined;\n            }\n\n            /**\n             * Initializes a new OverlayScrollbarsInstance object or changes options if already initialized or returns the current instance.\n             * @param pluginTargetElements The elements to which the Plugin shall be initialized.\n             * @param options The custom options with which the plugin shall be initialized.\n             * @param extensions The extension(s) which shall be added right after initialization.\n             * @returns {*}\n             */\n            window[PLUGINNAME] = function(pluginTargetElements, options, extensions) {\n                if(arguments[LEXICON.l] === 0)\n                    return this;\n\n                var arr = [ ];\n                var optsIsPlainObj = FRAMEWORK.isPlainObject(options);\n                var inst;\n                var result;\n\n                //pluginTargetElements is null or undefined\n                if(!pluginTargetElements)\n                    return optsIsPlainObj || !options ? result : arr;\n\n                /*\n                   pluginTargetElements will be converted to:\n                   1. A jQueryElement Array\n                   2. A HTMLElement Array\n                   3. A Array with a single HTML Element\n                   so pluginTargetElements is always a array.\n                */\n                pluginTargetElements = pluginTargetElements[LEXICON.l] != undefined ? pluginTargetElements : [ pluginTargetElements[0] || pluginTargetElements ];\n                initOverlayScrollbarsStatics();\n\n                if(pluginTargetElements[LEXICON.l] > 0) {\n                    if(optsIsPlainObj) {\n                        FRAMEWORK.each(pluginTargetElements, function (i, v) {\n                            inst = v;\n                            if(inst !== undefined)\n                                arr.push(OverlayScrollbarsInstance(inst, options, extensions, _pluginsGlobals, _pluginsAutoUpdateLoop));\n                        });\n                    }\n                    else {\n                        FRAMEWORK.each(pluginTargetElements, function(i, v) {\n                            inst = INSTANCES(v);\n                            if((options === '!' && inst instanceof window[PLUGINNAME]) || (COMPATIBILITY.type(options) == TYPES.f && options(v, inst)))\n                                arr.push(inst);\n                            else if(options === undefined)\n                                arr.push(inst);\n                        });\n                    }\n                    result = arr[LEXICON.l] === 1 ? arr[0] : arr;\n                }\n                return result;\n            };\n\n            /**\n             * Returns a object which contains global information about the plugin and each instance of it.\n             * The returned object is just a copy, that means that changes to the returned object won't have any effect to the original object.\n             */\n            window[PLUGINNAME].globals = function () {\n                initOverlayScrollbarsStatics();\n                var globals = FRAMEWORK.extend(true, { }, _pluginsGlobals);\n                delete globals['msie'];\n                return globals;\n            };\n\n            /**\n             * Gets or Sets the default options for each new plugin initialization.\n             * @param newDefaultOptions The object with which the default options shall be extended.\n             */\n            window[PLUGINNAME].defaultOptions = function(newDefaultOptions) {\n                initOverlayScrollbarsStatics();\n                var currDefaultOptions = _pluginsGlobals.defaultOptions;\n                if(newDefaultOptions === undefined)\n                    return FRAMEWORK.extend(true, { }, currDefaultOptions);\n\n                //set the new default options\n                _pluginsGlobals.defaultOptions = FRAMEWORK.extend(true, { }, currDefaultOptions , _pluginsOptions._validate(newDefaultOptions, _pluginsOptions._template, true, currDefaultOptions)._default);\n            };\n\n            /**\n             * Registers, Unregisters or returns a extension.\n             * Register: Pass the name and the extension. (defaultOptions is optional)\n             * Unregister: Pass the name and anything except a function as extension parameter.\n             * Get extension: Pass the name of the extension which shall be got.\n             * Get all extensions: Pass no arguments.\n             * @param extensionName The name of the extension which shall be registered, unregistered or returned.\n             * @param extension A function which generates the instance of the extension or anything other to remove a already registered extension.\n             * @param defaultOptions The default options which shall be used for the registered extension.\n             */\n            window[PLUGINNAME].extension = function(extensionName, extension, defaultOptions) {\n                var extNameTypeString = COMPATIBILITY.type(extensionName) == TYPES.s;\n                var argLen = arguments[LEXICON.l];\n                var i = 0;\n                if(argLen < 1 || !extNameTypeString) {\n                    //return a copy of all extension objects\n                    return FRAMEWORK.extend(true, { length : _pluginsExtensions[LEXICON.l] }, _pluginsExtensions);\n                }\n                else if(extNameTypeString) {\n                    if(COMPATIBILITY.type(extension) == TYPES.f) {\n                        //register extension\n                        _pluginsExtensions.push({\n                            name : extensionName,\n                            extensionFactory : extension,\n                            defaultOptions : defaultOptions\n                        });\n                    }\n                    else {\n                        for(; i < _pluginsExtensions[LEXICON.l]; i++) {\n                            if (_pluginsExtensions[i].name === extensionName) {\n                                if(argLen > 1)\n                                    _pluginsExtensions.splice(i, 1); //remove extension\n                                else\n                                    return FRAMEWORK.extend(true, { }, _pluginsExtensions[i]); //return extension with the given name\n                            }\n                        }\n                    }\n                }\n            };\n\n            return window[PLUGINNAME];\n        })();\n\n        if(JQUERY && JQUERY.fn) {\n            /**\n             * The jQuery initialization interface.\n             * @param options The initial options for the construction of the plugin. To initialize the plugin, this option has to be a object! If it isn't a object, the instance(s) are returned and the plugin wont be initialized.\n             * @param extensions The extension(s) which shall be added right after initialization.\n             * @returns {*} After initialization it returns the jQuery element array, else it returns the instance(s) of the elements which are selected.\n             */\n            JQUERY.fn.overlayScrollbars = function (options, extensions) {\n                var _elements = this;\n                if(JQUERY.isPlainObject(options)) {\n                    JQUERY.each(_elements, function() { PLUGIN(this, options, extensions); });\n                    return _elements;\n                }\n                else\n                    return PLUGIN(_elements, options);\n            };\n        }\n        return PLUGIN;\n    }\n));\n\n//# sourceURL=webpack:///./node_modules/overlayscrollbars/js/OverlayScrollbars.js?");
  
  /***/ }),
  
  /***/ "./node_modules/rellax/rellax.js":
  /*!***************************************!*\
    !*** ./node_modules/rellax/rellax.js ***!
    \***************************************/
  /*! no static exports found */
  /***/ (function(module, exports, __webpack_require__) {
  
  eval("/* WEBPACK VAR INJECTION */(function(global) {var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;\n// ------------------------------------------\n// Rellax.js\n// Buttery smooth parallax library\n// Copyright (c) 2016 Moe Amaya (@moeamaya)\n// MIT license\n//\n// Thanks to Paraxify.js and Jaime Cabllero\n// for parallax concepts\n// ------------------------------------------\n\n(function (root, factory) {\n  if (true) {\n    // AMD. Register as an anonymous module.\n    !(__WEBPACK_AMD_DEFINE_ARRAY__ = [], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),\n\t\t\t\t__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?\n\t\t\t\t(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),\n\t\t\t\t__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));\n  } else {}\n}(typeof window !== \"undefined\" ? window : global, function () {\n  var Rellax = function(el, options){\n    \"use strict\";\n\n    var self = Object.create(Rellax.prototype);\n\n    var posY = 0;\n    var screenY = 0;\n    var posX = 0;\n    var screenX = 0;\n    var blocks = [];\n    var pause = true;\n\n    // check what requestAnimationFrame to use, and if\n    // it's not supported, use the onscroll event\n    var loop = window.requestAnimationFrame ||\n      window.webkitRequestAnimationFrame ||\n      window.mozRequestAnimationFrame ||\n      window.msRequestAnimationFrame ||\n      window.oRequestAnimationFrame ||\n      function(callback){ return setTimeout(callback, 1000 / 60); };\n\n    // store the id for later use\n    var loopId = null;\n\n    // Test via a getter in the options object to see if the passive property is accessed\n    var supportsPassive = false;\n    try {\n      var opts = Object.defineProperty({}, 'passive', {\n        get: function() {\n          supportsPassive = true;\n        }\n      });\n      window.addEventListener(\"testPassive\", null, opts);\n      window.removeEventListener(\"testPassive\", null, opts);\n    } catch (e) {}\n\n    // check what cancelAnimation method to use\n    var clearLoop = window.cancelAnimationFrame || window.mozCancelAnimationFrame || clearTimeout;\n\n    // check which transform property to use\n    var transformProp = window.transformProp || (function(){\n        var testEl = document.createElement('div');\n        if (testEl.style.transform === null) {\n          var vendors = ['Webkit', 'Moz', 'ms'];\n          for (var vendor in vendors) {\n            if (testEl.style[ vendors[vendor] + 'Transform' ] !== undefined) {\n              return vendors[vendor] + 'Transform';\n            }\n          }\n        }\n        return 'transform';\n      })();\n\n    // Default Settings\n    self.options = {\n      speed: -2,\n      center: false,\n      wrapper: null,\n      relativeToWrapper: false,\n      round: true,\n      vertical: true,\n      horizontal: false,\n      callback: function() {},\n    };\n\n    // User defined options (might have more in the future)\n    if (options){\n      Object.keys(options).forEach(function(key){\n        self.options[key] = options[key];\n      });\n    }\n\n    // By default, rellax class\n    if (!el) {\n      el = '.rellax';\n    }\n\n    // check if el is a className or a node\n    var elements = typeof el === 'string' ? document.querySelectorAll(el) : [el];\n\n    // Now query selector\n    if (elements.length > 0) {\n      self.elems = elements;\n    }\n\n    // The elements don't exist\n    else {\n      console.warn(\"Rellax: The elements you're trying to select don't exist.\");\n      return;\n    }\n\n    // Has a wrapper and it exists\n    if (self.options.wrapper) {\n      if (!self.options.wrapper.nodeType) {\n        var wrapper = document.querySelector(self.options.wrapper);\n\n        if (wrapper) {\n          self.options.wrapper = wrapper;\n        } else {\n          console.warn(\"Rellax: The wrapper you're trying to use doesn't exist.\");\n          return;\n        }\n      }\n    }\n\n\n    // Get and cache initial position of all elements\n    var cacheBlocks = function() {\n      for (var i = 0; i < self.elems.length; i++){\n        var block = createBlock(self.elems[i]);\n        blocks.push(block);\n      }\n    };\n\n\n    // Let's kick this script off\n    // Build array for cached element values\n    var init = function() {\n      for (var i = 0; i < blocks.length; i++){\n        self.elems[i].style.cssText = blocks[i].style;\n      }\n\n      blocks = [];\n\n      screenY = window.innerHeight;\n      screenX = window.innerWidth;\n      setPosition();\n\n      cacheBlocks();\n\n      animate();\n\n      // If paused, unpause and set listener for window resizing events\n      if (pause) {\n        window.addEventListener('resize', init);\n        pause = false;\n        // Start the loop\n        update();\n      }\n    };\n\n    // We want to cache the parallax blocks'\n    // values: base, top, height, speed\n    // el: is dom object, return: el cache values\n    var createBlock = function(el) {\n      var dataPercentage = el.getAttribute( 'data-rellax-percentage' );\n      var dataSpeed = el.getAttribute( 'data-rellax-speed' );\n      var dataZindex = el.getAttribute( 'data-rellax-zindex' ) || 0;\n      var dataMin = el.getAttribute( 'data-rellax-min' );\n      var dataMax = el.getAttribute( 'data-rellax-max' );\n\n      // initializing at scrollY = 0 (top of browser), scrollX = 0 (left of browser)\n      // ensures elements are positioned based on HTML layout.\n      //\n      // If the element has the percentage attribute, the posY and posX needs to be\n      // the current scroll position's value, so that the elements are still positioned based on HTML layout\n      var wrapperPosY = self.options.wrapper ? self.options.wrapper.scrollTop : (window.pageYOffset || document.documentElement.scrollTop || document.body.scrollTop);\n      // If the option relativeToWrapper is true, use the wrappers offset to top, subtracted from the current page scroll.\n      if (self.options.relativeToWrapper) {\n        var scrollPosY = (window.pageYOffset || document.documentElement.scrollTop || document.body.scrollTop);\n        wrapperPosY = scrollPosY - self.options.wrapper.offsetTop;\n      }\n      var posY = self.options.vertical ? ( dataPercentage || self.options.center ? wrapperPosY : 0 ) : 0;\n      var posX = self.options.horizontal ? ( dataPercentage || self.options.center ? self.options.wrapper ? self.options.wrapper.scrollLeft : (window.pageXOffset || document.documentElement.scrollLeft || document.body.scrollLeft) : 0 ) : 0;\n\n      var blockTop = posY + el.getBoundingClientRect().top;\n      var blockHeight = el.clientHeight || el.offsetHeight || el.scrollHeight;\n\n      var blockLeft = posX + el.getBoundingClientRect().left;\n      var blockWidth = el.clientWidth || el.offsetWidth || el.scrollWidth;\n\n      // apparently parallax equation everyone uses\n      var percentageY = dataPercentage ? dataPercentage : (posY - blockTop + screenY) / (blockHeight + screenY);\n      var percentageX = dataPercentage ? dataPercentage : (posX - blockLeft + screenX) / (blockWidth + screenX);\n      if(self.options.center){ percentageX = 0.5; percentageY = 0.5; }\n\n      // Optional individual block speed as data attr, otherwise global speed\n      var speed = dataSpeed ? dataSpeed : self.options.speed;\n\n      var bases = updatePosition(percentageX, percentageY, speed);\n\n      // ~~Store non-translate3d transforms~~\n      // Store inline styles and extract transforms\n      var style = el.style.cssText;\n      var transform = '';\n\n      // Check if there's an inline styled transform\n      var searchResult = /transform\\s*:/i.exec(style);\n      if (searchResult) {\n        // Get the index of the transform\n        var index = searchResult.index;\n\n        // Trim the style to the transform point and get the following semi-colon index\n        var trimmedStyle = style.slice(index);\n        var delimiter = trimmedStyle.indexOf(';');\n\n        // Remove \"transform\" string and save the attribute\n        if (delimiter) {\n          transform = \" \" + trimmedStyle.slice(11, delimiter).replace(/\\s/g,'');\n        } else {\n          transform = \" \" + trimmedStyle.slice(11).replace(/\\s/g,'');\n        }\n      }\n\n      return {\n        baseX: bases.x,\n        baseY: bases.y,\n        top: blockTop,\n        left: blockLeft,\n        height: blockHeight,\n        width: blockWidth,\n        speed: speed,\n        style: style,\n        transform: transform,\n        zindex: dataZindex,\n        min: dataMin,\n        max: dataMax\n      };\n    };\n\n    // set scroll position (posY, posX)\n    // side effect method is not ideal, but okay for now\n    // returns true if the scroll changed, false if nothing happened\n    var setPosition = function() {\n      var oldY = posY;\n      var oldX = posX;\n\n      posY = self.options.wrapper ? self.options.wrapper.scrollTop : (document.documentElement || document.body.parentNode || document.body).scrollTop || window.pageYOffset;\n      posX = self.options.wrapper ? self.options.wrapper.scrollLeft : (document.documentElement || document.body.parentNode || document.body).scrollLeft || window.pageXOffset;\n      // If option relativeToWrapper is true, use relative wrapper value instead.\n      if (self.options.relativeToWrapper) {\n        var scrollPosY = (document.documentElement || document.body.parentNode || document.body).scrollTop || window.pageYOffset;\n        posY = scrollPosY - self.options.wrapper.offsetTop;\n      }\n\n\n      if (oldY != posY && self.options.vertical) {\n        // scroll changed, return true\n        return true;\n      }\n\n      if (oldX != posX && self.options.horizontal) {\n        // scroll changed, return true\n        return true;\n      }\n\n      // scroll did not change\n      return false;\n    };\n\n    // Ahh a pure function, gets new transform value\n    // based on scrollPosition and speed\n    // Allow for decimal pixel values\n    var updatePosition = function(percentageX, percentageY, speed) {\n      var result = {};\n      var valueX = (speed * (100 * (1 - percentageX)));\n      var valueY = (speed * (100 * (1 - percentageY)));\n\n      result.x = self.options.round ? Math.round(valueX) : Math.round(valueX * 100) / 100;\n      result.y = self.options.round ? Math.round(valueY) : Math.round(valueY * 100) / 100;\n\n      return result;\n    };\n\n    // Remove event listeners and loop again\n    var deferredUpdate = function() {\n      window.removeEventListener('resize', deferredUpdate);\n      window.removeEventListener('orientationchange', deferredUpdate);\n      (self.options.wrapper ? self.options.wrapper : window).removeEventListener('scroll', deferredUpdate);\n      (self.options.wrapper ? self.options.wrapper : document).removeEventListener('touchmove', deferredUpdate);\n\n      // loop again\n      loopId = loop(update);\n    };\n\n    // Loop\n    var update = function() {\n      if (setPosition() && pause === false) {\n        animate();\n\n        // loop again\n        loopId = loop(update);\n      } else {\n        loopId = null;\n\n        // Don't animate until we get a position updating event\n        window.addEventListener('resize', deferredUpdate);\n        window.addEventListener('orientationchange', deferredUpdate);\n        (self.options.wrapper ? self.options.wrapper : window).addEventListener('scroll', deferredUpdate, supportsPassive ? { passive: true } : false);\n        (self.options.wrapper ? self.options.wrapper : document).addEventListener('touchmove', deferredUpdate, supportsPassive ? { passive: true } : false);\n      }\n    };\n\n    // Transform3d on parallax element\n    var animate = function() {\n      var positions;\n      for (var i = 0; i < self.elems.length; i++){\n        var percentageY = ((posY - blocks[i].top + screenY) / (blocks[i].height + screenY));\n        var percentageX = ((posX - blocks[i].left + screenX) / (blocks[i].width + screenX));\n\n        // Subtracting initialize value, so element stays in same spot as HTML\n        positions = updatePosition(percentageX, percentageY, blocks[i].speed);// - blocks[i].baseX;\n        var positionY = positions.y - blocks[i].baseY;\n        var positionX = positions.x - blocks[i].baseX;\n\n        // The next two \"if\" blocks go like this:\n        // Check if a limit is defined (first \"min\", then \"max\");\n        // Check if we need to change the Y or the X\n        // (Currently working only if just one of the axes is enabled)\n        // Then, check if the new position is inside the allowed limit\n        // If so, use new position. If not, set position to limit.\n\n        // Check if a min limit is defined\n        if (blocks[i].min !== null) {\n          if (self.options.vertical && !self.options.horizontal) {\n            positionY = positionY <= blocks[i].min ? blocks[i].min : positionY;\n          }\n          if (self.options.horizontal && !self.options.vertical) {\n            positionX = positionX <= blocks[i].min ? blocks[i].min : positionX;\n          }\n        }\n\n        // Check if a max limit is defined\n        if (blocks[i].max !== null) {\n          if (self.options.vertical && !self.options.horizontal) {\n            positionY = positionY >= blocks[i].max ? blocks[i].max : positionY;\n          }\n          if (self.options.horizontal && !self.options.vertical) {\n            positionX = positionX >= blocks[i].max ? blocks[i].max : positionX;\n          }\n        }\n\n        var zindex = blocks[i].zindex;\n\n        // Move that element\n        // (Set the new translation and append initial inline transforms.)\n        var translate = 'translate3d(' + (self.options.horizontal ? positionX : '0') + 'px,' + (self.options.vertical ? positionY : '0') + 'px,' + zindex + 'px) ' + blocks[i].transform;\n        self.elems[i].style[transformProp] = translate;\n      }\n      self.options.callback(positions);\n    };\n\n    self.destroy = function() {\n      for (var i = 0; i < self.elems.length; i++){\n        self.elems[i].style.cssText = blocks[i].style;\n      }\n\n      // Remove resize event listener if not pause, and pause\n      if (!pause) {\n        window.removeEventListener('resize', init);\n        pause = true;\n      }\n\n      // Clear the animation loop to prevent possible memory leak\n      clearLoop(loopId);\n      loopId = null;\n    };\n\n    // Init\n    init();\n\n    // Allow to recalculate the initial values whenever we want\n    self.refresh = init;\n\n    return self;\n  };\n  return Rellax;\n}));\n\n/* WEBPACK VAR INJECTION */}.call(this, __webpack_require__(/*! ./../webpack/buildin/global.js */ \"./node_modules/webpack/buildin/global.js\")))\n\n//# sourceURL=webpack:///./node_modules/rellax/rellax.js?");
  
  /***/ }),
  
  /***/ "./node_modules/webpack/buildin/global.js":
  /*!***********************************!*\
    !*** (webpack)/buildin/global.js ***!
    \***********************************/
  /*! no static exports found */
  /***/ (function(module, exports) {
  
  eval("var g;\n\n// This works in non-strict mode\ng = (function() {\n\treturn this;\n})();\n\ntry {\n\t// This works if eval is allowed (see CSP)\n\tg = g || new Function(\"return this\")();\n} catch (e) {\n\t// This works if the window reference is available\n\tif (typeof window === \"object\") g = window;\n}\n\n// g can still be undefined, but nothing to do about it...\n// We return undefined, instead of nothing here, so it's\n// easier to handle this case. if(!global) { ...}\n\nmodule.exports = g;\n\n\n//# sourceURL=webpack:///(webpack)/buildin/global.js?");
  
  /***/ }),
  
  /***/ "./public/assets/src/js/Views/base.js":
  /*!********************************************!*\
    !*** ./public/assets/src/js/Views/base.js ***!
    \********************************************/
  /*! exports provided: selectors, elements */
  /***/ (function(module, __webpack_exports__, __webpack_require__) {
  
  "use strict";
  eval("__webpack_require__.r(__webpack_exports__);\n/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, \"selectors\", function() { return selectors; });\n/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, \"elements\", function() { return elements; });\nconst selectors = {\n  frontPage: {\n    testimonials: \".glide\",\n    testimonialContent: '.testimonial-content',\n    // testimonialContent: '.scroller',\n    gallery: \".gallery\",\n    header: {\n      base: \"#page-header\",\n      bgImg: \"#page-header__background-image\",\n      logo: \"#intro\"\n    }\n  }\n};\nconst elements = {\n  frontPage: {\n    testimonials: document.querySelector(selectors.frontPage.testimonials),\n    gallery: document.querySelector(selectors.frontPage.gallery),\n    header: document.querySelector(selectors.frontPage.header.base),\n    headerBackground: document.querySelector(selectors.frontPage.header.bgImg),\n    headerLogo: document.querySelector(selectors.frontPage.header.logo),\n    testimonialContent: document.querySelectorAll(selectors.frontPage.testimonialContent)\n  }\n};\n\n//# sourceURL=webpack:///./public/assets/src/js/Views/base.js?");
  
  /***/ }),
  
  /***/ "./public/assets/src/js/Views/parallax.js":
  /*!************************************************!*\
    !*** ./public/assets/src/js/Views/parallax.js ***!
    \************************************************/
  /*! exports provided: rellaxers */
  /***/ (function(module, __webpack_exports__, __webpack_require__) {
  
  "use strict";
  eval("__webpack_require__.r(__webpack_exports__);\n/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, \"rellaxers\", function() { return rellaxers; });\n/* harmony import */ var _base__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! ./base */ \"./public/assets/src/js/Views/base.js\");\n/**\n *\n */\n\n/**\n *\n */\n\nvar rellaxers = {\n  frontPage: [{\n    // hero background\n    element: _base__WEBPACK_IMPORTED_MODULE_0__[\"elements\"].frontPage.headerBackground,\n    speed: -8\n  }, {\n    // hero logo\n    element: _base__WEBPACK_IMPORTED_MODULE_0__[\"elements\"].frontPage.headerLogo,\n    speed: 3\n  }]\n};\n\n//# sourceURL=webpack:///./public/assets/src/js/Views/parallax.js?");
  
  /***/ }),
  
  /***/ "./public/assets/src/js/Views/rearrangeView.js":
  /*!*****************************************************!*\
    !*** ./public/assets/src/js/Views/rearrangeView.js ***!
    \*****************************************************/
  /*! exports provided: initParallax, initMasonry, initSlider, initSimpleBar */
  /***/ (function(module, __webpack_exports__, __webpack_require__) {
  
  "use strict";
  eval("__webpack_require__.r(__webpack_exports__);\n/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, \"initParallax\", function() { return initParallax; });\n/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, \"initMasonry\", function() { return initMasonry; });\n/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, \"initSlider\", function() { return initSlider; });\n/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, \"initSimpleBar\", function() { return initSimpleBar; });\n/* harmony import */ var rellax__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! rellax */ \"./node_modules/rellax/rellax.js\");\n/* harmony import */ var rellax__WEBPACK_IMPORTED_MODULE_0___default = /*#__PURE__*/__webpack_require__.n(rellax__WEBPACK_IMPORTED_MODULE_0__);\n/* harmony import */ var _glidejs_glide__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! @glidejs/glide */ \"./node_modules/@glidejs/glide/dist/glide.esm.js\");\n/* harmony import */ var masonry_layout__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__(/*! masonry-layout */ \"./node_modules/masonry-layout/masonry.js\");\n/* harmony import */ var masonry_layout__WEBPACK_IMPORTED_MODULE_2___default = /*#__PURE__*/__webpack_require__.n(masonry_layout__WEBPACK_IMPORTED_MODULE_2__);\n/* harmony import */ var overlayscrollbars__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__(/*! overlayscrollbars */ \"./node_modules/overlayscrollbars/js/OverlayScrollbars.js\");\n/* harmony import */ var overlayscrollbars__WEBPACK_IMPORTED_MODULE_3___default = /*#__PURE__*/__webpack_require__.n(overlayscrollbars__WEBPACK_IMPORTED_MODULE_3__);\n/* harmony import */ var _base__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__(/*! ./base */ \"./public/assets/src/js/Views/base.js\");\n/* harmony import */ var _parallax__WEBPACK_IMPORTED_MODULE_5__ = __webpack_require__(/*! ./parallax */ \"./public/assets/src/js/Views/parallax.js\");\n/**\n * dependencies\n */\n // import SimpleBar from 'simplebar';\n\n\n\n\n/**\n * stuffs\n */\n\n\n\n/**\n * parallax scrolling\n */\n\nfunction initParallax() {\n  const selector = 'rellax';\n  const base = 'data-rellax-';\n  const options = ['speed', 'percentage', 'zindex'];\n  var rellax = _parallax__WEBPACK_IMPORTED_MODULE_5__[\"rellaxers\"].frontPage;\n  rellax.forEach(rellaxer => {\n    const element = rellaxer.element;\n    element.classList.add(selector);\n    options.forEach(option => {\n      if (rellaxer.hasOwnProperty(option)) {\n        element.setAttribute(base + option, rellaxer[option]);\n      }\n    });\n  });\n  rellax = new rellax__WEBPACK_IMPORTED_MODULE_0___default.a(`.${selector}`, {\n    round: false\n  });\n}\n/**\n * masonry\n */\n\nfunction initMasonry(instance) {\n  new masonry_layout__WEBPACK_IMPORTED_MODULE_2___default.a(_base__WEBPACK_IMPORTED_MODULE_4__[\"elements\"].frontPage.gallery, {\n    itemSelector: '[class^=gallery__item-]',\n    columnWidth: '.cornerstone',\n    percentPosition: true\n  });\n}\n/**\n * sliders\n */\n\nfunction initSlider(ImagesLoaded) {\n  let slider = _base__WEBPACK_IMPORTED_MODULE_4__[\"elements\"].frontPage.testimonials;\n  const slides = slider.querySelector('[data-glide-el=\"track\"]>ul');\n  const count = slides.childElementCount;\n  const maxSlides = 1;\n  slider = new _glidejs_glide__WEBPACK_IMPORTED_MODULE_1__[\"default\"](slider, {\n    type: 'carousel',\n    perView: count < maxSlides ? count : maxSlides,\n    // autoplay: (count <= maxSlides) ? false : 5000\n    autoplay: false\n  });\n  slider.mount();\n}\n/**\n * scrollbars\n */\n\nfunction initSimpleBar(e) {\n  const scrollElements = _base__WEBPACK_IMPORTED_MODULE_4__[\"elements\"].frontPage.testimonialContent;\n  const instances = overlayscrollbars__WEBPACK_IMPORTED_MODULE_3___default()(scrollElements, {\n    className: \"os-theme-thin-light\",\n    paddingAbsolute: true,\n    overflowBehavior: {\n      x: 'hidden',\n      y: 'visible-hidden'\n    },\n    scrollbars: {\n      visibility: 'auto',\n      autoHide: \"leave\",\n      autoHideDelay: 300\n    }\n  }); // instances.forEach(instance => {\n  //   let overflow = instance.getState('hasOverflow').y;\n  //   if (true === overflow) {\n  //     instance.getElements('target').querySelector('.os-content').classList.add('fix-os-scroll');\n  //   }\n  // })\n  // Array.from(scrollElements).forEach(el => el = new SimpleBar(el, {\n  //   autoHide: false\n  // }));\n}\n\n//# sourceURL=webpack:///./public/assets/src/js/Views/rearrangeView.js?");
  
  /***/ }),
  
  /***/ "./public/assets/src/js/index.js":
  /*!***************************************!*\
    !*** ./public/assets/src/js/index.js ***!
    \***************************************/
  /*! no exports provided */
  /***/ (function(module, __webpack_exports__, __webpack_require__) {
  
  "use strict";
  eval("__webpack_require__.r(__webpack_exports__);\n/* harmony import */ var imagesloaded__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! imagesloaded */ \"./node_modules/imagesloaded/imagesloaded.js\");\n/* harmony import */ var imagesloaded__WEBPACK_IMPORTED_MODULE_0___default = /*#__PURE__*/__webpack_require__.n(imagesloaded__WEBPACK_IMPORTED_MODULE_0__);\n/* harmony import */ var aos__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! aos */ \"./node_modules/aos/dist/aos.js\");\n/* harmony import */ var aos__WEBPACK_IMPORTED_MODULE_1___default = /*#__PURE__*/__webpack_require__.n(aos__WEBPACK_IMPORTED_MODULE_1__);\n/* harmony import */ var _Views_rearrangeView__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__(/*! ./Views/rearrangeView */ \"./public/assets/src/js/Views/rearrangeView.js\");\n/* harmony import */ var _Views_base__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__(/*! ./Views/base */ \"./public/assets/src/js/Views/base.js\");\n/**\n * dependencies\n */\n\n\n/**\n * stuffs\n */\n\n\n\n/**\n * init if you gotta\n */\n\naos__WEBPACK_IMPORTED_MODULE_1___default.a.init();\n/**\n * testimonials\n */\n\nimagesloaded__WEBPACK_IMPORTED_MODULE_0___default()(_Views_base__WEBPACK_IMPORTED_MODULE_3__[\"elements\"].frontPage.testimonials, _Views_rearrangeView__WEBPACK_IMPORTED_MODULE_2__[\"initSlider\"]); // document.addEventListener('DOMContentLoaded', rearrangeView.initSlider);\n\n/**\n * gallery\n */\n// ImagesLoaded(elements.frontPage.gallery, rearrangeView.initMasonry);\n\n/**\n * parallax\n */\n// document.addEventListener('DOMContentLoaded', rearrangeView.initParallax);\n\nimagesloaded__WEBPACK_IMPORTED_MODULE_0___default()(_Views_base__WEBPACK_IMPORTED_MODULE_3__[\"elements\"].frontPage.headerBackground, _Views_rearrangeView__WEBPACK_IMPORTED_MODULE_2__[\"initParallax\"]);\n/**\n * scrollbars\n */\n\ndocument.addEventListener('DOMContentLoaded', _Views_rearrangeView__WEBPACK_IMPORTED_MODULE_2__[\"initSimpleBar\"]);\n\n//# sourceURL=webpack:///./public/assets/src/js/index.js?");
  
  /***/ })
  
  /******/ });