PageSourceSearch

https://closertotruth.com/wp-content/themes/closer-to-truth/dist/scripts/main.js?ver=1790742401

js closertotruth.com collected 2026-10-01 10:34:07 UTC 801,813 bytes, 24,908 lines download raw bytes

1/******/ (function(modules) { // webpackBootstrap
2/******/ 	// The module cache
3/******/ 	var installedModules = {};
4/******/
5/******/ 	// The require function
6/******/ 	function __webpack_require__(moduleId) {
7/******/
8/******/ 		// Check if module is in cache
9/******/ 		if(installedModules[moduleId]) {
10/******/ 			return installedModules[moduleId].exports;
11/******/ 		}
12/******/ 		// Create a new module (and put it into the cache)
13/******/ 		var module = installedModules[moduleId] = {
14/******/ 			i: moduleId,
15/******/ 			l: false,
16/******/ 			exports: {}
17/******/ 		};
18/******/
19/******/ 		// Execute the module function
20/******/ 		modules[moduleId].call(module.exports, module, module.exports, __webpack_require__);
21/******/
22/******/ 		// Flag the module as loaded
23/******/ 		module.l = true;
24/******/
25/******/ 		// Return the exports of the module
26/******/ 		return module.exports;
27/******/ 	}
28/******/
29/******/
30/******/ 	// expose the modules object (__webpack_modules__)
31/******/ 	__webpack_require__.m = modules;
32/******/
33/******/ 	// expose the module cache
34/******/ 	__webpack_require__.c = installedModules;
35/******/
36/******/ 	// define getter function for harmony exports
37/******/ 	__webpack_require__.d = function(exports, name, getter) {
38/******/ 		if(!__webpack_require__.o(exports, name)) {
39/******/ 			Object.defineProperty(exports, name, {
40/******/ 				configurable: false,
41/******/ 				enumerable: true,
42/******/ 				get: getter
43/******/ 			});
44/******/ 		}
45/******/ 	};
46/******/
47/******/ 	// getDefaultExport function for compatibility with non-harmony modules
48/******/ 	__webpack_require__.n = function(module) {
49/******/ 		var getter = module && module.__esModule ?
50/******/ 			function getDefault() { return module['default']; } :
51/******/ 			function getModuleExports() { return module; };
52/******/ 		__webpack_require__.d(getter, 'a', getter);
53/******/ 		return getter;
54/******/ 	};
55/******/
56/******/ 	// Object.prototype.hasOwnProperty.call
57/******/ 	__webpack_require__.o = function(object, property) { return Object.prototype.hasOwnProperty.call(object, property); };
58/******/
59/******/ 	// __webpack_public_path__
60/******/ 	__webpack_require__.p = "/wp-content/themes/closer-to-truth/dist/";
61/******/
62/******/ 	// Load entry module and return exports
63/******/ 	return __webpack_require__(__webpack_require__.s = 13);
64/******/ })
65/************************************************************************/
66/******/ ([
67/* 0 */
68/***/ (function(module, exports) {
69
70module.exports = jQuery;
71
72/***/ }),
73/* 1 */
74/***/ (function(module, exports, __webpack_require__) {
75
76var __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/**
77 * Fizzy UI utils v2.0.7
78 * MIT license
79 */
80
81/*jshint browser: true, undef: true, unused: true, strict: true */
82
83( function( window, factory ) {
84  // universal module definition
85  /*jshint strict: false */ /*globals define, module, require */
86
87  if ( true ) {
88    // AMD
89    !(__WEBPACK_AMD_DEFINE_ARRAY__ = [
90      __webpack_require__(12)
91    ], __WEBPACK_AMD_DEFINE_RESULT__ = (function( matchesSelector ) {
92      return factory( window, matchesSelector );
93    }).apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__),
94				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
95  } else if ( typeof module == 'object' && module.exports ) {
96    // CommonJS
97    module.exports = factory(
98      window,
99      require('desandro-matches-selector')
100    );
101  } else {
102    // browser global
103    window.fizzyUIUtils = factory(
104      window,
105      window.matchesSelector
106    );
107  }
108
109}( window, function factory( window, matchesSelector ) {
110
111'use strict';
112
113var utils = {};
114
115// ----- extend ----- //
116
117// extends objects
118utils.extend = function( a, b ) {
119  for ( var prop in b ) {
120    a[ prop ] = b[ prop ];
121  }
122  return a;
123};
124
125// ----- modulo ----- //
126
127utils.modulo = function( num, div ) {
128  return ( ( num % div ) + div ) % div;
129};
130
131// ----- makeArray ----- //
132
133var arraySlice = Array.prototype.slice;
134
135// turn element or nodeList into an array
136utils.makeArray = function( obj ) {
137  if ( Array.isArray( obj ) ) {
138    // use object if already an array
139    return obj;
140  }
141  // return empty array if undefined or null. #6
142  if ( obj === null || obj === undefined ) {
143    return [];
144  }
145
146  var isArrayLike = typeof obj == 'object' && typeof obj.length == 'number';
147  if ( isArrayLike ) {
148    // convert nodeList to array
149    return arraySlice.call( obj );
150  }
151
152  // array of single index
153  return [ obj ];
154};
155
156// ----- removeFrom ----- //
157
158utils.removeFrom = function( ary, obj ) {
159  var index = ary.indexOf( obj );
160  if ( index != -1 ) {
161    ary.splice( index, 1 );
162  }
163};
164
165// ----- getParent ----- //
166
167utils.getParent = function( elem, selector ) {
168  while ( elem.parentNode && elem != document.body ) {
169    elem = elem.parentNode;
170    if ( matchesSelector( elem, selector ) ) {
171      return elem;
172    }
173  }
174};
175
176// ----- getQueryElement ----- //
177
178// use element as selector string
179utils.getQueryElement = function( elem ) {
180  if ( typeof elem == 'string' ) {
181    return document.querySelector( elem );
182  }
183  return elem;
184};
185
186// ----- handleEvent ----- //
187
188// enable .ontype to trigger from .addEventListener( elem, 'type' )
189utils.handleEvent = function( event ) {
190  var method = 'on' + event.type;
191  if ( this[ method ] ) {
192    this[ method ]( event );
193  }
194};
195
196// ----- filterFindElements ----- //
197
198utils.filterFindElements = function( elems, selector ) {
199  // make array of elems
200  elems = utils.makeArray( elems );
201  var ffElems = [];
202
203  elems.forEach( function( elem ) {
204    // check that elem is an actual element
205    if ( !( elem instanceof HTMLElement ) ) {
206      return;
207    }
208    // add elem if no selector
209    if ( !selector ) {
210      ffElems.push( elem );
211      return;
212    }
213    // filter & find items if we have a selector
214    // filter
215    if ( matchesSelector( elem, selector ) ) {
216      ffElems.push( elem );
217    }
218    // find children
219    var childElems = elem.querySelectorAll( selector );
220    // concat childElems to filterFound array
221    for ( var i=0; i < childElems.length; i++ ) {
222      ffElems.push( childElems[i] );
223    }
224  });
225
226  return ffElems;
227};
228
229// ----- debounceMethod ----- //
230
231utils.debounceMethod = function( _class, methodName, threshold ) {
232  threshold = threshold || 100;
233  // original method
234  var method = _class.prototype[ methodName ];
235  var timeoutName = methodName + 'Timeout';
236
237  _class.prototype[ methodName ] = function() {
238    var timeout = this[ timeoutName ];
239    clearTimeout( timeout );
240
241    var args = arguments;
242    var _this = this;
243    this[ timeoutName ] = setTimeout( function() {
244      method.apply( _this, args );
245      delete _this[ timeoutName ];
246    }, threshold );
247  };
248};
249
250// ----- docReady ----- //
251
252utils.docReady = function( callback ) {
253  var readyState = document.readyState;
254  if ( readyState == 'complete' || readyState == 'interactive' ) {
255    // do async to allow for other scripts to run. metafizzy/flickity#441
256    setTimeout( callback );
257  } else {
258    document.addEventListener( 'DOMContentLoaded', callback );
259  }
260};
261
262// ----- htmlInit ----- //
263
264// http://jamesroberts.name/blog/2010/02/22/string-functions-for-javascript-trim-to-camel-case-to-dashed-and-to-underscore/
265utils.toDashed = function( str ) {
266  return str.replace( /(.)([A-Z])/g, function( match, $1, $2 ) {
267    return $1 + '-' + $2;
268  }).toLowerCase();
269};
270
271var console = window.console;
272/**
273 * allow user to initialize classes via [data-namespace] or .js-namespace class
274 * htmlInit( Widget, 'widgetName' )
275 * options are parsed from data-namespace-options
276 */
277utils.htmlInit = function( WidgetClass, namespace ) {
278  utils.docReady( function() {
279    var dashedNamespace = utils.toDashed( namespace );
280    var dataAttr = 'data-' + dashedNamespace;
281    var dataAttrElems = document.querySelectorAll( '[' + dataAttr + ']' );
282    var jsDashElems = document.querySelectorAll( '.js-' + dashedNamespace );
283    var elems = utils.makeArray( dataAttrElems )
284      .concat( utils.makeArray( jsDashElems ) );
285    var dataOptionsAttr = dataAttr + '-options';
286    var jQuery = window.jQuery;
287
288    elems.forEach( function( elem ) {
289      var attr = elem.getAttribute( dataAttr ) ||
290        elem.getAttribute( dataOptionsAttr );
291      var options;
292      try {
293        options = attr && JSON.parse( attr );
294      } catch ( error ) {
295        // log error, do not initialize
296        if ( console ) {
297          console.error( 'Error parsing ' + dataAttr + ' on ' + elem.className +
298          ': ' + error );
299        }
300        return;
301      }
302      // initialize
303      var instance = new WidgetClass( elem, options );
304      // make available via $().data('namespace')
305      if ( jQuery ) {
306        jQuery.data( elem, namespace, instance );
307      }
308    });
309
310  });
311};
312
313// -----  ----- //
314
315return utils;
316
317}));
318
319
320/***/ }),
321/* 2 */
322/***/ (function(module, exports, __webpack_require__) {
323
324var __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;// core
325( function( window, factory ) {
326  // universal module definition
327  /* globals define, module, require */
328  if ( true ) {
329    // AMD
330    !(__WEBPACK_AMD_DEFINE_ARRAY__ = [
331      __webpack_require__(31),
332      __webpack_require__(1),
333    ], __WEBPACK_AMD_DEFINE_RESULT__ = (function( EvEmitter, utils) {
334      return factory( window, EvEmitter, utils );
335    }).apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__),
336				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
337  } else if ( typeof module == 'object' && module.exports ) {
338    // CommonJS
339    module.exports = factory(
340      window,
341      require('ev-emitter'),
342      require('fizzy-ui-utils')
343    );
344  } else {
345    // browser global
346    window.InfiniteScroll = factory(
347      window,
348      window.EvEmitter,
349      window.fizzyUIUtils
350    );
351  }
352
353}( window, function factory( window, EvEmitter, utils ) {
354
355var jQuery = window.jQuery;
356// internal store of all InfiniteScroll intances
357var instances = {};
358
359function InfiniteScroll( element, options ) {
360  var queryElem = utils.getQueryElement( element );
361
362  if ( !queryElem ) {
363    console.error( 'Bad element for InfiniteScroll: ' + ( queryElem || element ) );
364    return;
365  }
366  element = queryElem;
367  // do not initialize twice on same element
368  if ( element.infiniteScrollGUID ) {
369    var instance = instances[ element.infiniteScrollGUID ];
370    instance.option( options );
371    return instance;
372  }
373
374  this.element = element;
375  // options
376  this.options = utils.extend( {}, InfiniteScroll.defaults );
377  this.option( options );
378  // add jQuery
379  if ( jQuery ) {
380    this.$element = jQuery( this.element );
381  }
382
383  this.create();
384}
385
386// defaults
387InfiniteScroll.defaults = {
388  // path: null,
389  // hideNav: null,
390  // debug: false,
391};
392
393// create & destroy methods
394InfiniteScroll.create = {};
395InfiniteScroll.destroy = {};
396
397var proto = InfiniteScroll.prototype;
398// inherit EvEmitter
399utils.extend( proto, EvEmitter.prototype );
400
401// --------------------------  -------------------------- //
402
403// globally unique identifiers
404var GUID = 0;
405
406proto.create = function() {
407  // create core
408  // add id for InfiniteScroll.data
409  var id = this.guid = ++GUID;
410  this.element.infiniteScrollGUID = id; // expando
411  instances[ id ] = this; // associate via id
412  // properties
413  this.pageIndex = 1; // default to first page
414  this.loadCount = 0;
415  this.updateGetPath();
416  // bail if getPath not set
417  if ( !this.getPath ) {
418    console.error('Disabling InfiniteScroll');
419    return;
420  }
421  this.updateGetAbsolutePath();
422  this.log( 'initialized', [ this.element.className ] );
423  this.callOnInit();
424  // create features
425  for ( var method in InfiniteScroll.create ) {
426    InfiniteScroll.create[ method ].call( this );
427  }
428};
429
430proto.option = function( opts ) {
431  utils.extend( this.options, opts );
432};
433
434// call onInit option, used for binding events on init
435proto.callOnInit = function() {
436  var onInit = this.options.onInit;
437  if ( onInit ) {
438    onInit.call( this, this );
439  }
440};
441
442// ----- events ----- //
443
444proto.dispatchEvent = function( type, event, args ) {
445  this.log( type, args );
446  var emitArgs = event ? [ event ].concat( args ) : args;
447  this.emitEvent( type, emitArgs );
448  // trigger jQuery event
449  if ( !jQuery || !this.$element ) {
450    return;
451  }
452  // namespace jQuery event
453  type += '.infiniteScroll';
454  var $event = type;
455  if ( event ) {
456    // create jQuery event
457    var jQEvent = jQuery.Event( event );
458    jQEvent.type = type;
459    $event = jQEvent;
460  }
461  this.$element.trigger( $event, args );
462};
463
464var loggers = {
465  initialized: function( className ) {
466    return 'on ' + className;
467  },
468  request: function( path ) {
469    return 'URL: ' + path;
470  },
471  load: function( response, path ) {
472    return ( response.title || '' ) + '. URL: ' + path;
473  },
474  error: function( error, path ) {
475    return error + '. URL: ' + path;
476  },
477  append: function( response, path, items ) {
478    return items.length + ' items. URL: ' + path;
479  },
480  last: function( response, path ) {
481    return 'URL: ' + path;
482  },
483  history: function( title, path ) {
484    return 'URL: ' + path;
485  },
486  pageIndex: function( index, origin ) {
487    return 'current page determined to be: ' + index + ' from ' + origin;
488  },
489};
490
491// log events
492proto.log = function( type, args ) {
493  if ( !this.options.debug ) {
494    return;
495  }
496  var message = '[InfiniteScroll] ' + type;
497  var logger = loggers[ type ];
498  if ( logger ) {
499    message += '. ' + logger.apply( this, args );
500  }
501  console.log( message );
502};
503
504// -------------------------- methods used amoung features -------------------------- //
505
506proto.updateMeasurements = function() {
507  this.windowHeight = window.innerHeight;
508  var rect = this.element.getBoundingClientRect();
509  this.top = rect.top + window.pageYOffset;
510};
511
512proto.updateScroller = function() {
513  var elementScroll = this.options.elementScroll;
514  if ( !elementScroll ) {
515    // default, use window
516    this.scroller = window;
517    return;
518  }
519  // if true, set to element, otherwise use option
520  this.scroller = elementScroll === true ? this.element :
521    utils.getQueryElement( elementScroll );
522  if ( !this.scroller ) {
523    throw 'Unable to find elementScroll: ' + elementScroll;
524  }
525};
526
527// -------------------------- page path -------------------------- //
528
529proto.updateGetPath = function() {
530  var optPath = this.options.path;
531  if ( !optPath ) {
532    console.error( 'InfiniteScroll path option required. Set as: ' + optPath );
533    return;
534  }
535  // function
536  var type = typeof optPath;
537  if ( type == 'function' ) {
538    this.getPath = optPath;
539    return;
540  }
541  // template string: '/pages/{{#}}.html'
542  var templateMatch = type == 'string' && optPath.match('{{#}}');
543  if ( templateMatch ) {
544    this.updateGetPathTemplate( optPath );
545    return;
546  }
547  // selector: '.next-page-selector'
548  this.updateGetPathSelector( optPath );
549};
550
551proto.updateGetPathTemplate = function( optPath ) {
552  // set getPath with template string
553  this.getPath = function() {
554    var nextIndex = this.pageIndex + 1;
555    return optPath.replace( '{{#}}', nextIndex );
556  }.bind( this );
557  // get pageIndex from location
558  // convert path option into regex to look for pattern in location
559  var regexString = optPath.replace( '{{#}}', '(\\d\\d?\\d?)' );
560  var templateRe = new RegExp( regexString );
561  var match = location.href.match( templateRe );
562  if ( match ) {
563    this.pageIndex = parseInt( match[1], 10 );
564    this.log( 'pageIndex', this.pageIndex, 'template string' );
565  }
566};
567
568var pathRegexes = [
569  // WordPress & Tumblr - example.com/page/2
570  // Jekyll - example.com/page2
571  /^(.*?\/?page\/?)(\d\d?\d?)(.*?$)/,
572  // Drupal - example.com/?page=1
573  /^(.*?\/?\?page=)(\d\d?\d?)(.*?$)/,
574  // catch all, last occurence of a number
575  /(.*?)(\d\d?\d?)(?!.*\d)(.*?$)/,
576];
577
578proto.updateGetPathSelector = function( optPath ) {
579  // parse href of link: '.next-page-link'
580  var hrefElem = document.querySelector( optPath );
581  if ( !hrefElem ) {
582    console.error( 'Bad InfiniteScroll path option. Next link not found: ' +
583      optPath );
584    return;
585  }
586  var href = hrefElem.getAttribute('href');
587  // try matching href to pathRegexes patterns
588  var pathParts, regex;
589  for ( var i=0; href && i < pathRegexes.length; i++ ) {
590    regex = pathRegexes[i];
591    var match = href.match( regex );
592    if ( match ) {
593      pathParts = match.slice(1); // remove first part
594      break;
595    }
596  }
597  if ( !pathParts ) {
598    console.error( 'InfiniteScroll unable to parse next link href: ' + href );
599    return;
600  }
601  this.isPathSelector = true; // flag for checkLastPage()
602  this.getPath = function() {
603    var nextIndex = this.pageIndex + 1;
604    return pathParts[0] + nextIndex + pathParts[2];
605  }.bind( this );
606  // get pageIndex from href
607  this.pageIndex = parseInt( pathParts[1], 10 ) - 1;
608  this.log( 'pageIndex', [ this.pageIndex, 'next link' ] );
609};
610
611proto.updateGetAbsolutePath = function() {
612  var path = this.getPath();
613  // path doesn't start with http or /
614  var isAbsolute = path.match( /^http/ ) || path.match( /^\// );
615  if ( isAbsolute ) {
616    this.getAbsolutePath = this.getPath;
617    return;
618  }
619
620  var pathname = location.pathname;
621  // /foo/bar/index.html => /foo/bar
622  var directory = pathname.substring( 0, pathname.lastIndexOf('/') );
623
624  this.getAbsolutePath = function() {
625    return directory + '/' + this.getPath();
626  };
627};
628
629// -------------------------- nav -------------------------- //
630
631// hide navigation
632InfiniteScroll.create.hideNav = function() {
633  var nav = utils.getQueryElement( this.options.hideNav );
634  if ( !nav ) {
635    return;
636  }
637  nav.style.display = 'none';
638  this.nav = nav;
639};
640
641InfiniteScroll.destroy.hideNav = function() {
642  if ( this.nav ) {
643    this.nav.style.display = '';
644  }
645};
646
647// -------------------------- destroy -------------------------- //
648
649proto.destroy = function() {
650  this.allOff(); // remove all event listeners
651  // call destroy methods
652  for ( var method in InfiniteScroll.destroy ) {
653    InfiniteScroll.destroy[ method ].call( this );
654  }
655
656  delete this.element.infiniteScrollGUID;
657  delete instances[ this.guid ];
658};
659
660// -------------------------- utilities -------------------------- //
661
662// https://remysharp.com/2010/07/21/throttling-function-calls
663InfiniteScroll.throttle = function( fn, threshold ) {
664  threshold = threshold || 200;
665  var last, timeout;
666
667  return function() {
668    var now = +new Date();
669    var args = arguments;
670    var trigger = function() {
671      last = now;
672      fn.apply( this, args );
673    }.bind( this );
674    if ( last && now < last + threshold ) {
675      // hold on to it
676      clearTimeout( timeout );
677      timeout = setTimeout( trigger, threshold );
678    } else {
679      trigger();
680    }
681  };
682};
683
684InfiniteScroll.data = function( elem ) {
685  elem = utils.getQueryElement( elem );
686  var id = elem && elem.infiniteScrollGUID;
687  return id && instances[ id ];
688};
689
690// set internal jQuery, for Webpack + jQuery v3
vendor: 5,988 bytes, lines 691-913
691InfiniteScroll.setJQuery = function( $ ) {
692  jQuery = $;
693};
694
695// -------------------------- setup -------------------------- //
696
697utils.htmlInit( InfiniteScroll, 'infinite-scroll' );
698
699if ( jQuery && jQuery.bridget ) {
700  jQuery.bridget( 'infiniteScroll', InfiniteScroll );
701}
702
703// --------------------------  -------------------------- //
704
705return InfiniteScroll;
706
707}));
708
709
710/***/ }),
711/* 3 */
712/***/ (function(module, exports, __webpack_require__) {
713
714var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_RESULT__;/*!
715 * getSize v2.0.3
716 * measure size of elements
717 * MIT license
718 */
719
720/* jshint browser: true, strict: true, undef: true, unused: true */
721/* globals console: false */
722
723( function( window, factory ) {
724  /* jshint strict: false */ /* globals define, module */
725  if ( true ) {
726    // AMD
727    !(__WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
728				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
729				(__WEBPACK_AMD_DEFINE_FACTORY__.call(exports, __webpack_require__, exports, module)) :
730				__WEBPACK_AMD_DEFINE_FACTORY__),
731				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
732  } else if ( typeof module == 'object' && module.exports ) {
733    // CommonJS
734    module.exports = factory();
735  } else {
736    // browser global
737    window.getSize = factory();
738  }
739
740})( window, function factory() {
741'use strict';
742
743// -------------------------- helpers -------------------------- //
744
745// get a number from a string, not a percentage
746function getStyleSize( value ) {
747  var num = parseFloat( value );
748  // not a percent like '100%', and a number
749  var isValid = value.indexOf('%') == -1 && !isNaN( num );
750  return isValid && num;
751}
752
753function noop() {}
754
755var logError = typeof console == 'undefined' ? noop :
756  function( message ) {
757    console.error( message );
758  };
759
760// -------------------------- measurements -------------------------- //
761
762var measurements = [
763  'paddingLeft',
764  'paddingRight',
765  'paddingTop',
766  'paddingBottom',
767  'marginLeft',
768  'marginRight',
769  'marginTop',
770  'marginBottom',
771  'borderLeftWidth',
772  'borderRightWidth',
773  'borderTopWidth',
774  'borderBottomWidth'
775];
776
777var measurementsLength = measurements.length;
778
779function getZeroSize() {
780  var size = {
781    width: 0,
782    height: 0,
783    innerWidth: 0,
784    innerHeight: 0,
785    outerWidth: 0,
786    outerHeight: 0
787  };
788  for ( var i=0; i < measurementsLength; i++ ) {
789    var measurement = measurements[i];
790    size[ measurement ] = 0;
791  }
792  return size;
793}
794
795// -------------------------- getStyle -------------------------- //
796
797/**
798 * getStyle, get style of element, check for Firefox bug
799 * https://bugzilla.mozilla.org/show_bug.cgi?id=548397
800 */
801function getStyle( elem ) {
802  var style = getComputedStyle( elem );
803  if ( !style ) {
804    logError( 'Style returned ' + style +
805      '. Are you running this code in a hidden iframe on Firefox? ' +
806      'See https://bit.ly/getsizebug1' );
807  }
808  return style;
809}
810
811// -------------------------- setup -------------------------- //
812
813var isSetup = false;
814
815var isBoxSizeOuter;
816
817/**
818 * setup
819 * check isBoxSizerOuter
820 * do on first getSize() rather than on page load for Firefox bug
821 */
822function setup() {
823  // setup once
824  if ( isSetup ) {
825    return;
826  }
827  isSetup = true;
828
829  // -------------------------- box sizing -------------------------- //
830
831  /**
832   * Chrome & Safari measure the outer-width on style.width on border-box elems
833   * IE11 & Firefox<29 measures the inner-width
834   */
835  var div = document.createElement('div');
836  div.style.width = '200px';
837  div.style.padding = '1px 2px 3px 4px';
838  div.style.borderStyle = 'solid';
839  div.style.borderWidth = '1px 2px 3px 4px';
840  div.style.boxSizing = 'border-box';
841
842  var body = document.body || document.documentElement;
843  body.appendChild( div );
844  var style = getStyle( div );
845  // round value for browser zoom. desandro/masonry#928
846  isBoxSizeOuter = Math.round( getStyleSize( style.width ) ) == 200;
847  getSize.isBoxSizeOuter = isBoxSizeOuter;
848
849  body.removeChild( div );
850}
851
852// -------------------------- getSize -------------------------- //
853
854function getSize( elem ) {
855  setup();
856
857  // use querySeletor if elem is string
858  if ( typeof elem == 'string' ) {
859    elem = document.querySelector( elem );
860  }
861
862  // do not proceed on non-objects
863  if ( !elem || typeof elem != 'object' || !elem.nodeType ) {
864    return;
865  }
866
867  var style = getStyle( elem );
868
869  // if hidden, everything is 0
870  if ( style.display == 'none' ) {
871    return getZeroSize();
872  }
873
874  var size = {};
875  size.width = elem.offsetWidth;
876  size.height = elem.offsetHeight;
877
878  var isBorderBox = size.isBorderBox = style.boxSizing == 'border-box';
879
880  // get all measurements
881  for ( var i=0; i < measurementsLength; i++ ) {
882    var measurement = measurements[i];
883    var value = style[ measurement ];
884    var num = parseFloat( value );
885    // any 'auto', 'medium' value will be 0
886    size[ measurement ] = !isNaN( num ) ? num : 0;
887  }
888
889  var paddingWidth = size.paddingLeft + size.paddingRight;
890  var paddingHeight = size.paddingTop + size.paddingBottom;
891  var marginWidth = size.marginLeft + size.marginRight;
892  var marginHeight = size.marginTop + size.marginBottom;
893  var borderWidth = size.borderLeftWidth + size.borderRightWidth;
894  var borderHeight = size.borderTopWidth + size.borderBottomWidth;
895
896  var isBorderBoxSizeOuter = isBorderBox && isBoxSizeOuter;
897
898  // overwrite width and height if we can get it from style
899  var styleWidth = getStyleSize( style.width );
900  if ( styleWidth !== false ) {
901    size.width = styleWidth +
902      // add padding and border unless it's already including it
903      ( isBorderBoxSizeOuter ? 0 : paddingWidth + borderWidth );
904  }
905
906  var styleHeight = getStyleSize( style.height );
907  if ( styleHeight !== false ) {
908    size.height = styleHeight +
909      // add padding and border unless it's already including it
910      ( isBorderBoxSizeOuter ? 0 : paddingHeight + borderHeight );
911  }
912
913  size.innerWidth = size.width - ( paddingWidth + borderWidth );
914  size.innerHeight = size.height - ( paddingHeight + borderHeight );
915
916  size.outerWidth = size.width + marginWidth;
917  size.outerHeight = size.height + marginHeight;
918
919  return size;
920}
921
922return getSize;
923
924});
925
926
927/***/ }),
928/* 4 */
929/***/ (function(module, __webpack_exports__, __webpack_require__) {
930
931"use strict";
932/* unused harmony export bunnyIframeUrl */
933/* harmony export (immutable) */ __webpack_exports__["a"] = loadBunnyPlayer;
934/* harmony export (immutable) */ __webpack_exports__["b"] = swapBunnyVideo;
935/**
936 * Bunny Stream player loader — shared across video routes.
937 *
938 * The theme renders a placeholder element with `data-video` (the source id/url)
939 * and `data-source` (youtube|bunny|kaltura). YouTube and Kaltura keep their
940 * existing per-route logic; this util provides the Bunny branch so it lives in
941 * one place. Background players add `data-background="true"` for muted/looping
942 * autoplay.
943 *
944 * Bunny config (library id + pull zone) is localized to `window.CTT_BUNNY`.
945 */
946
947var bunnyCounter = 0;
948
949/**
950 * Build a Bunny Stream iframe embed URL.
951 */
952function bunnyIframeUrl(videoGuid, ref) {
953    if ( ref === void 0 ) ref = {};
954    var background = ref.background; if ( background === void 0 ) background = false;
955    var autoplay = ref.autoplay; if ( autoplay === void 0 ) autoplay = true;
956    var start = ref.start; if ( start === void 0 ) start = 0;
957
958    var cfg = window.CTT_BUNNY || {};
959    var libraryId = cfg.libraryId || '';
960    var params = new URLSearchParams({
961        autoplay: autoplay ? 'true' : 'false',
962        loop: background ? 'true' : 'false',
963        muted: background ? 'true' : 'false',
964    });
965    if (start > 0) {
966        params.set('t', String(Math.floor(start)));
967    }
968    return ("https://iframe.mediadelivery.net/embed/" + libraryId + "/" + videoGuid + "?" + (params.toString()));
969}
970
971/**
972 * Render a Bunny iframe into a placeholder element and (optionally) wire
973 * Player.js events for progress tracking.
974 *
975 * @param {HTMLElement} playerEl   The placeholder element (has data-video).
976 * @param {Object}      opts
977 * @param {boolean}     opts.background  Muted/looping autoplay for mastheads.
978 * @param {boolean}     opts.autoplay    Defaults to `background`. Set false for
979 *                       overlay-driven single-video playback.
980 * @param {Function}    opts.onTimeUpdate  (data) => {} where data.seconds/.duration.
981 *                       NOTE: fires very frequently (~4x/sec) — use only to cache
982 *                       the latest position, never to make network calls.
983 * @param {Function}    opts.onPause       () => {} — coarse, for progress writes.
984 * @param {Function}    opts.onEnded       () => {} — coarse, for progress writes.
985 * @returns {Object|null} The Player.js instance, if created.
986 */
987function loadBunnyPlayer(playerEl, ref) {
988    if ( ref === void 0 ) ref = {};
989    var background = ref.background; if ( background === void 0 ) background = false;
990    var autoplay = ref.autoplay; if ( autoplay === void 0 ) autoplay = background;
991    var start = ref.start; if ( start === void 0 ) start = 0;
992    var onTimeUpdate = ref.onTimeUpdate; if ( onTimeUpdate === void 0 ) onTimeUpdate = null;
993    var onPause = ref.onPause; if ( onPause === void 0 ) onPause = null;
994    var onEnded = ref.onEnded; if ( onEnded === void 0 ) onEnded = null;
995
996    var videoGuid = playerEl.dataset.video;
997    if (!videoGuid) {
998        return null;
999    }
1000
1001    var iframe = document.createElement('iframe');
1002    iframe.id = (playerEl.id || 'bunny-player') + '-bunny-' + (++bunnyCounter);
1003    iframe.src = bunnyIframeUrl(videoGuid, { background: background, autoplay: autoplay, start: start });
1004    iframe.setAttribute('allow', 'autoplay; fullscreen; encrypted-media; picture-in-picture');
1005    iframe.setAttribute('allowfullscreen', '');
1006    iframe.style.cssText = 'width:100%;height:100%;border:0;';
1007    playerEl.innerHTML = '';
1008    playerEl.appendChild(iframe);
1009
1010    // Player.js (loaded via the `bunny-playerjs` handle) exposes standard
1011    // events. Progress writes should be driven by the coarse pause/ended events
1012    // (matching the YouTube/Kaltura paths), not by the high-frequency timeupdate.
1013    if (window.playerjs && (onTimeUpdate || onPause || onEnded)) {
1014        try {
1015            var player = new window.playerjs.Player(iframe);
1016            player.on('ready', function () {
1017                if (onTimeUpdate) {
1018                    player.on('timeupdate', onTimeUpdate);
1019                }
1020                if (onPause) {
1021                    player.on('pause', onPause);
1022                }
1023                if (onEnded) {
1024                    player.on('ended', onEnded);
1025                }
1026            });
1027            return player;
1028        } catch (e) {
1029            console.error('Bunny Player.js init failed:', e.message); // eslint-disable-line no-console
1030        }
1031    }
1032    return null;
1033}
1034
1035/**
1036 * Swap an existing Bunny player's iframe to a different video GUID
1037 * (used by the Short/Long format toggle).
1038 */
1039function swapBunnyVideo(playerEl, videoGuid, ref) {
1040    if ( ref === void 0 ) ref = {};
1041    var background = ref.background; if ( background === void 0 ) background = false;
1042
1043    // Keep the element's data-video in sync with the requested GUID so any
1044    // re-render uses the selected target (not the originally-loaded clip).
1045    playerEl.dataset.video = videoGuid;
1046    // Only reuse the existing iframe if it's already a Bunny embed — its
1047    // Player.js instance (and the tracking handlers bound to it) survive a
1048    // src swap. A foreign iframe (e.g. a YouTube player) must be replaced so
1049    // Bunny's Player.js events actually attach.
1050    var iframe = playerEl.querySelector('iframe');
1051    if (iframe && iframe.src.indexOf('mediadelivery.net') > -1) {
1052        iframe.src = bunnyIframeUrl(videoGuid, { background: background });
1053    } else {
1054        loadBunnyPlayer(playerEl, { background: background });
1055    }
1056}
1057
1058
1059/***/ }),
1060/* 5 */
1061/***/ (function(module, exports, __webpack_require__) {
1062
1063var __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/*!
1064 * Outlayer v2.1.1
1065 * the brains and guts of a layout library
1066 * MIT license
1067 */
1068
1069( function( window, factory ) {
1070  'use strict';
1071  // universal module definition
1072  /* jshint strict: false */ /* globals define, module, require */
1073  if ( true ) {
1074    // AMD - RequireJS
1075    !(__WEBPACK_AMD_DEFINE_ARRAY__ = [
1076        __webpack_require__(11),
1077        __webpack_require__(3),
1078        __webpack_require__(1),
1079        __webpack_require__(25)
1080      ], __WEBPACK_AMD_DEFINE_RESULT__ = (function( EvEmitter, getSize, utils, Item ) {
1081        return factory( window, EvEmitter, getSize, utils, Item);
1082      }).apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__),
1083				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__)
vendor: 21,459 bytes, lines 1083-2001
1083);
1084  } else if ( typeof module == 'object' && module.exports ) {
1085    // CommonJS - Browserify, Webpack
1086    module.exports = factory(
1087      window,
1088      require('ev-emitter'),
1089      require('get-size'),
1090      require('fizzy-ui-utils'),
1091      require('./item')
1092    );
1093  } else {
1094    // browser global
1095    window.Outlayer = factory(
1096      window,
1097      window.EvEmitter,
1098      window.getSize,
1099      window.fizzyUIUtils,
1100      window.Outlayer.Item
1101    );
1102  }
1103
1104}( window, function factory( window, EvEmitter, getSize, utils, Item ) {
1105'use strict';
1106
1107// ----- vars ----- //
1108
1109var console = window.console;
1110var jQuery = window.jQuery;
1111var noop = function() {};
1112
1113// -------------------------- Outlayer -------------------------- //
1114
1115// globally unique identifiers
1116var GUID = 0;
1117// internal store of all Outlayer intances
1118var instances = {};
1119
1120
1121/**
1122 * @param {Element, String} element
1123 * @param {Object} options
1124 * @constructor
1125 */
1126function Outlayer( element, options ) {
1127  var queryElement = utils.getQueryElement( element );
1128  if ( !queryElement ) {
1129    if ( console ) {
1130      console.error( 'Bad element for ' + this.constructor.namespace +
1131        ': ' + ( queryElement || element ) );
1132    }
1133    return;
1134  }
1135  this.element = queryElement;
1136  // add jQuery
1137  if ( jQuery ) {
1138    this.$element = jQuery( this.element );
1139  }
1140
1141  // options
1142  this.options = utils.extend( {}, this.constructor.defaults );
1143  this.option( options );
1144
1145  // add id for Outlayer.getFromElement
1146  var id = ++GUID;
1147  this.element.outlayerGUID = id; // expando
1148  instances[ id ] = this; // associate via id
1149
1150  // kick it off
1151  this._create();
1152
1153  var isInitLayout = this._getOption('initLayout');
1154  if ( isInitLayout ) {
1155    this.layout();
1156  }
1157}
1158
1159// settings are for internal use only
1160Outlayer.namespace = 'outlayer';
1161Outlayer.Item = Item;
1162
1163// default options
1164Outlayer.defaults = {
1165  containerStyle: {
1166    position: 'relative'
1167  },
1168  initLayout: true,
1169  originLeft: true,
1170  originTop: true,
1171  resize: true,
1172  resizeContainer: true,
1173  // item options
1174  transitionDuration: '0.4s',
1175  hiddenStyle: {
1176    opacity: 0,
1177    transform: 'scale(0.001)'
1178  },
1179  visibleStyle: {
1180    opacity: 1,
1181    transform: 'scale(1)'
1182  }
1183};
1184
1185var proto = Outlayer.prototype;
1186// inherit EvEmitter
1187utils.extend( proto, EvEmitter.prototype );
1188
1189/**
1190 * set options
1191 * @param {Object} opts
1192 */
1193proto.option = function( opts ) {
1194  utils.extend( this.options, opts );
1195};
1196
1197/**
1198 * get backwards compatible option value, check old name
1199 */
1200proto._getOption = function( option ) {
1201  var oldOption = this.constructor.compatOptions[ option ];
1202  return oldOption && this.options[ oldOption ] !== undefined ?
1203    this.options[ oldOption ] : this.options[ option ];
1204};
1205
1206Outlayer.compatOptions = {
1207  // currentName: oldName
1208  initLayout: 'isInitLayout',
1209  horizontal: 'isHorizontal',
1210  layoutInstant: 'isLayoutInstant',
1211  originLeft: 'isOriginLeft',
1212  originTop: 'isOriginTop',
1213  resize: 'isResizeBound',
1214  resizeContainer: 'isResizingContainer'
1215};
1216
1217proto._create = function() {
1218  // get items from children
1219  this.reloadItems();
1220  // elements that affect layout, but are not laid out
1221  this.stamps = [];
1222  this.stamp( this.options.stamp );
1223  // set container style
1224  utils.extend( this.element.style, this.options.containerStyle );
1225
1226  // bind resize method
1227  var canBindResize = this._getOption('resize');
1228  if ( canBindResize ) {
1229    this.bindResize();
1230  }
1231};
1232
1233// goes through all children again and gets bricks in proper order
1234proto.reloadItems = function() {
1235  // collection of item elements
1236  this.items = this._itemize( this.element.children );
1237};
1238
1239
1240/**
1241 * turn elements into Outlayer.Items to be used in layout
1242 * @param {Array or NodeList or HTMLElement} elems
1243 * @returns {Array} items - collection of new Outlayer Items
1244 */
1245proto._itemize = function( elems ) {
1246
1247  var itemElems = this._filterFindItemElements( elems );
1248  var Item = this.constructor.Item;
1249
1250  // create new Outlayer Items for collection
1251  var items = [];
1252  for ( var i=0; i < itemElems.length; i++ ) {
1253    var elem = itemElems[i];
1254    var item = new Item( elem, this );
1255    items.push( item );
1256  }
1257
1258  return items;
1259};
1260
1261/**
1262 * get item elements to be used in layout
1263 * @param {Array or NodeList or HTMLElement} elems
1264 * @returns {Array} items - item elements
1265 */
1266proto._filterFindItemElements = function( elems ) {
1267  return utils.filterFindElements( elems, this.options.itemSelector );
1268};
1269
1270/**
1271 * getter method for getting item elements
1272 * @returns {Array} elems - collection of item elements
1273 */
1274proto.getItemElements = function() {
1275  return this.items.map( function( item ) {
1276    return item.element;
1277  });
1278};
1279
1280// ----- init & layout ----- //
1281
1282/**
1283 * lays out all items
1284 */
1285proto.layout = function() {
1286  this._resetLayout();
1287  this._manageStamps();
1288
1289  // don't animate first layout
1290  var layoutInstant = this._getOption('layoutInstant');
1291  var isInstant = layoutInstant !== undefined ?
1292    layoutInstant : !this._isLayoutInited;
1293  this.layoutItems( this.items, isInstant );
1294
1295  // flag for initalized
1296  this._isLayoutInited = true;
1297};
1298
1299// _init is alias for layout
1300proto._init = proto.layout;
1301
1302/**
1303 * logic before any new layout
1304 */
1305proto._resetLayout = function() {
1306  this.getSize();
1307};
1308
1309
1310proto.getSize = function() {
1311  this.size = getSize( this.element );
1312};
1313
1314/**
1315 * get measurement from option, for columnWidth, rowHeight, gutter
1316 * if option is String -> get element from selector string, & get size of element
1317 * if option is Element -> get size of element
1318 * else use option as a number
1319 *
1320 * @param {String} measurement
1321 * @param {String} size - width or height
1322 * @private
1323 */
1324proto._getMeasurement = function( measurement, size ) {
1325  var option = this.options[ measurement ];
1326  var elem;
1327  if ( !option ) {
1328    // default to 0
1329    this[ measurement ] = 0;
1330  } else {
1331    // use option as an element
1332    if ( typeof option == 'string' ) {
1333      elem = this.element.querySelector( option );
1334    } else if ( option instanceof HTMLElement ) {
1335      elem = option;
1336    }
1337    // use size of element, if element
1338    this[ measurement ] = elem ? getSize( elem )[ size ] : option;
1339  }
1340};
1341
1342/**
1343 * layout a collection of item elements
1344 * @api public
1345 */
1346proto.layoutItems = function( items, isInstant ) {
1347  items = this._getItemsForLayout( items );
1348
1349  this._layoutItems( items, isInstant );
1350
1351  this._postLayout();
1352};
1353
1354/**
1355 * get the items to be laid out
1356 * you may want to skip over some items
1357 * @param {Array} items
1358 * @returns {Array} items
1359 */
1360proto._getItemsForLayout = function( items ) {
1361  return items.filter( function( item ) {
1362    return !item.isIgnored;
1363  });
1364};
1365
1366/**
1367 * layout items
1368 * @param {Array} items
1369 * @param {Boolean} isInstant
1370 */
1371proto._layoutItems = function( items, isInstant ) {
1372  this._emitCompleteOnItems( 'layout', items );
1373
1374  if ( !items || !items.length ) {
1375    // no items, emit event with empty array
1376    return;
1377  }
1378
1379  var queue = [];
1380
1381  items.forEach( function( item ) {
1382    // get x/y object from method
1383    var position = this._getItemLayoutPosition( item );
1384    // enqueue
1385    position.item = item;
1386    position.isInstant = isInstant || item.isLayoutInstant;
1387    queue.push( position );
1388  }, this );
1389
1390  this._processLayoutQueue( queue );
1391};
1392
1393/**
1394 * get item layout position
1395 * @param {Outlayer.Item} item
1396 * @returns {Object} x and y position
1397 */
1398proto._getItemLayoutPosition = function( /* item */ ) {
1399  return {
1400    x: 0,
1401    y: 0
1402  };
1403};
1404
1405/**
1406 * iterate over array and position each item
1407 * Reason being - separating this logic prevents 'layout invalidation'
1408 * thx @paul_irish
1409 * @param {Array} queue
1410 */
1411proto._processLayoutQueue = function( queue ) {
1412  this.updateStagger();
1413  queue.forEach( function( obj, i ) {
1414    this._positionItem( obj.item, obj.x, obj.y, obj.isInstant, i );
1415  }, this );
1416};
1417
1418// set stagger from option in milliseconds number
1419proto.updateStagger = function() {
1420  var stagger = this.options.stagger;
1421  if ( stagger === null || stagger === undefined ) {
1422    this.stagger = 0;
1423    return;
1424  }
1425  this.stagger = getMilliseconds( stagger );
1426  return this.stagger;
1427};
1428
1429/**
1430 * Sets position of item in DOM
1431 * @param {Outlayer.Item} item
1432 * @param {Number} x - horizontal position
1433 * @param {Number} y - vertical position
1434 * @param {Boolean} isInstant - disables transitions
1435 */
1436proto._positionItem = function( item, x, y, isInstant, i ) {
1437  if ( isInstant ) {
1438    // if not transition, just set CSS
1439    item.goTo( x, y );
1440  } else {
1441    item.stagger( i * this.stagger );
1442    item.moveTo( x, y );
1443  }
1444};
1445
1446/**
1447 * Any logic you want to do after each layout,
1448 * i.e. size the container
1449 */
1450proto._postLayout = function() {
1451  this.resizeContainer();
1452};
1453
1454proto.resizeContainer = function() {
1455  var isResizingContainer = this._getOption('resizeContainer');
1456  if ( !isResizingContainer ) {
1457    return;
1458  }
1459  var size = this._getContainerSize();
1460  if ( size ) {
1461    this._setContainerMeasure( size.width, true );
1462    this._setContainerMeasure( size.height, false );
1463  }
1464};
1465
1466/**
1467 * Sets width or height of container if returned
1468 * @returns {Object} size
1469 *   @param {Number} width
1470 *   @param {Number} height
1471 */
1472proto._getContainerSize = noop;
1473
1474/**
1475 * @param {Number} measure - size of width or height
1476 * @param {Boolean} isWidth
1477 */
1478proto._setContainerMeasure = function( measure, isWidth ) {
1479  if ( measure === undefined ) {
1480    return;
1481  }
1482
1483  var elemSize = this.size;
1484  // add padding and border width if border box
1485  if ( elemSize.isBorderBox ) {
1486    measure += isWidth ? elemSize.paddingLeft + elemSize.paddingRight +
1487      elemSize.borderLeftWidth + elemSize.borderRightWidth :
1488      elemSize.paddingBottom + elemSize.paddingTop +
1489      elemSize.borderTopWidth + elemSize.borderBottomWidth;
1490  }
1491
1492  measure = Math.max( measure, 0 );
1493  this.element.style[ isWidth ? 'width' : 'height' ] = measure + 'px';
1494};
1495
1496/**
1497 * emit eventComplete on a collection of items events
1498 * @param {String} eventName
1499 * @param {Array} items - Outlayer.Items
1500 */
1501proto._emitCompleteOnItems = function( eventName, items ) {
1502  var _this = this;
1503  function onComplete() {
1504    _this.dispatchEvent( eventName + 'Complete', null, [ items ] );
1505  }
1506
1507  var count = items.length;
1508  if ( !items || !count ) {
1509    onComplete();
1510    return;
1511  }
1512
1513  var doneCount = 0;
1514  function tick() {
1515    doneCount++;
1516    if ( doneCount == count ) {
1517      onComplete();
1518    }
1519  }
1520
1521  // bind callback
1522  items.forEach( function( item ) {
1523    item.once( eventName, tick );
1524  });
1525};
1526
1527/**
1528 * emits events via EvEmitter and jQuery events
1529 * @param {String} type - name of event
1530 * @param {Event} event - original event
1531 * @param {Array} args - extra arguments
1532 */
1533proto.dispatchEvent = function( type, event, args ) {
1534  // add original event to arguments
1535  var emitArgs = event ? [ event ].concat( args ) : args;
1536  this.emitEvent( type, emitArgs );
1537
1538  if ( jQuery ) {
1539    // set this.$element
1540    this.$element = this.$element || jQuery( this.element );
1541    if ( event ) {
1542      // create jQuery event
1543      var $event = jQuery.Event( event );
1544      $event.type = type;
1545      this.$element.trigger( $event, args );
1546    } else {
1547      // just trigger with type if no event available
1548      this.$element.trigger( type, args );
1549    }
1550  }
1551};
1552
1553// -------------------------- ignore & stamps -------------------------- //
1554
1555
1556/**
1557 * keep item in collection, but do not lay it out
1558 * ignored items do not get skipped in layout
1559 * @param {Element} elem
1560 */
1561proto.ignore = function( elem ) {
1562  var item = this.getItem( elem );
1563  if ( item ) {
1564    item.isIgnored = true;
1565  }
1566};
1567
1568/**
1569 * return item to layout collection
1570 * @param {Element} elem
1571 */
1572proto.unignore = function( elem ) {
1573  var item = this.getItem( elem );
1574  if ( item ) {
1575    delete item.isIgnored;
1576  }
1577};
1578
1579/**
1580 * adds elements to stamps
1581 * @param {NodeList, Array, Element, or String} elems
1582 */
1583proto.stamp = function( elems ) {
1584  elems = this._find( elems );
1585  if ( !elems ) {
1586    return;
1587  }
1588
1589  this.stamps = this.stamps.concat( elems );
1590  // ignore
1591  elems.forEach( this.ignore, this );
1592};
1593
1594/**
1595 * removes elements to stamps
1596 * @param {NodeList, Array, or Element} elems
1597 */
1598proto.unstamp = function( elems ) {
1599  elems = this._find( elems );
1600  if ( !elems ){
1601    return;
1602  }
1603
1604  elems.forEach( function( elem ) {
1605    // filter out removed stamp elements
1606    utils.removeFrom( this.stamps, elem );
1607    this.unignore( elem );
1608  }, this );
1609};
1610
1611/**
1612 * finds child elements
1613 * @param {NodeList, Array, Element, or String} elems
1614 * @returns {Array} elems
1615 */
1616proto._find = function( elems ) {
1617  if ( !elems ) {
1618    return;
1619  }
1620  // if string, use argument as selector string
1621  if ( typeof elems == 'string' ) {
1622    elems = this.element.querySelectorAll( elems );
1623  }
1624  elems = utils.makeArray( elems );
1625  return elems;
1626};
1627
1628proto._manageStamps = function() {
1629  if ( !this.stamps || !this.stamps.length ) {
1630    return;
1631  }
1632
1633  this._getBoundingRect();
1634
1635  this.stamps.forEach( this._manageStamp, this );
1636};
1637
1638// update boundingLeft / Top
1639proto._getBoundingRect = function() {
1640  // get bounding rect for container element
1641  var boundingRect = this.element.getBoundingClientRect();
1642  var size = this.size;
1643  this._boundingRect = {
1644    left: boundingRect.left + size.paddingLeft + size.borderLeftWidth,
1645    top: boundingRect.top + size.paddingTop + size.borderTopWidth,
1646    right: boundingRect.right - ( size.paddingRight + size.borderRightWidth ),
1647    bottom: boundingRect.bottom - ( size.paddingBottom + size.borderBottomWidth )
1648  };
1649};
1650
1651/**
1652 * @param {Element} stamp
1653**/
1654proto._manageStamp = noop;
1655
1656/**
1657 * get x/y position of element relative to container element
1658 * @param {Element} elem
1659 * @returns {Object} offset - has left, top, right, bottom
1660 */
1661proto._getElementOffset = function( elem ) {
1662  var boundingRect = elem.getBoundingClientRect();
1663  var thisRect = this._boundingRect;
1664  var size = getSize( elem );
1665  var offset = {
1666    left: boundingRect.left - thisRect.left - size.marginLeft,
1667    top: boundingRect.top - thisRect.top - size.marginTop,
1668    right: thisRect.right - boundingRect.right - size.marginRight,
1669    bottom: thisRect.bottom - boundingRect.bottom - size.marginBottom
1670  };
1671  return offset;
1672};
1673
1674// -------------------------- resize -------------------------- //
1675
1676// enable event handlers for listeners
1677// i.e. resize -> onresize
1678proto.handleEvent = utils.handleEvent;
1679
1680/**
1681 * Bind layout to window resizing
1682 */
1683proto.bindResize = function() {
1684  window.addEventListener( 'resize', this );
1685  this.isResizeBound = true;
1686};
1687
1688/**
1689 * Unbind layout to window resizing
1690 */
1691proto.unbindResize = function() {
1692  window.removeEventListener( 'resize', this );
1693  this.isResizeBound = false;
1694};
1695
1696proto.onresize = function() {
1697  this.resize();
1698};
1699
1700utils.debounceMethod( Outlayer, 'onresize', 100 );
1701
1702proto.resize = function() {
1703  // don't trigger if size did not change
1704  // or if resize was unbound. See #9
1705  if ( !this.isResizeBound || !this.needsResizeLayout() ) {
1706    return;
1707  }
1708
1709  this.layout();
1710};
1711
1712/**
1713 * check if layout is needed post layout
1714 * @returns Boolean
1715 */
1716proto.needsResizeLayout = function() {
1717  var size = getSize( this.element );
1718  // check that this.size and size are there
1719  // IE8 triggers resize on body size change, so they might not be
1720  var hasSizes = this.size && size;
1721  return hasSizes && size.innerWidth !== this.size.innerWidth;
1722};
1723
1724// -------------------------- methods -------------------------- //
1725
1726/**
1727 * add items to Outlayer instance
1728 * @param {Array or NodeList or Element} elems
1729 * @returns {Array} items - Outlayer.Items
1730**/
1731proto.addItems = function( elems ) {
1732  var items = this._itemize( elems );
1733  // add items to collection
1734  if ( items.length ) {
1735    this.items = this.items.concat( items );
1736  }
1737  return items;
1738};
1739
1740/**
1741 * Layout newly-appended item elements
1742 * @param {Array or NodeList or Element} elems
1743 */
1744proto.appended = function( elems ) {
1745  var items = this.addItems( elems );
1746  if ( !items.length ) {
1747    return;
1748  }
1749  // layout and reveal just the new items
1750  this.layoutItems( items, true );
1751  this.reveal( items );
1752};
1753
1754/**
1755 * Layout prepended elements
1756 * @param {Array or NodeList or Element} elems
1757 */
1758proto.prepended = function( elems ) {
1759  var items = this._itemize( elems );
1760  if ( !items.length ) {
1761    return;
1762  }
1763  // add items to beginning of collection
1764  var previousItems = this.items.slice(0);
1765  this.items = items.concat( previousItems );
1766  // start new layout
1767  this._resetLayout();
1768  this._manageStamps();
1769  // layout new stuff without transition
1770  this.layoutItems( items, true );
1771  this.reveal( items );
1772  // layout previous items
1773  this.layoutItems( previousItems );
1774};
1775
1776/**
1777 * reveal a collection of items
1778 * @param {Array of Outlayer.Items} items
1779 */
1780proto.reveal = function( items ) {
1781  this._emitCompleteOnItems( 'reveal', items );
1782  if ( !items || !items.length ) {
1783    return;
1784  }
1785  var stagger = this.updateStagger();
1786  items.forEach( function( item, i ) {
1787    item.stagger( i * stagger );
1788    item.reveal();
1789  });
1790};
1791
1792/**
1793 * hide a collection of items
1794 * @param {Array of Outlayer.Items} items
1795 */
1796proto.hide = function( items ) {
1797  this._emitCompleteOnItems( 'hide', items );
1798  if ( !items || !items.length ) {
1799    return;
1800  }
1801  var stagger = this.updateStagger();
1802  items.forEach( function( item, i ) {
1803    item.stagger( i * stagger );
1804    item.hide();
1805  });
1806};
1807
1808/**
1809 * reveal item elements
1810 * @param {Array}, {Element}, {NodeList} items
1811 */
1812proto.revealItemElements = function( elems ) {
1813  var items = this.getItems( elems );
1814  this.reveal( items );
1815};
1816
1817/**
1818 * hide item elements
1819 * @param {Array}, {Element}, {NodeList} items
1820 */
1821proto.hideItemElements = function( elems ) {
1822  var items = this.getItems( elems );
1823  this.hide( items );
1824};
1825
1826/**
1827 * get Outlayer.Item, given an Element
1828 * @param {Element} elem
1829 * @param {Function} callback
1830 * @returns {Outlayer.Item} item
1831 */
1832proto.getItem = function( elem ) {
1833  // loop through items to get the one that matches
1834  for ( var i=0; i < this.items.length; i++ ) {
1835    var item = this.items[i];
1836    if ( item.element == elem ) {
1837      // return item
1838      return item;
1839    }
1840  }
1841};
1842
1843/**
1844 * get collection of Outlayer.Items, given Elements
1845 * @param {Array} elems
1846 * @returns {Array} items - Outlayer.Items
1847 */
1848proto.getItems = function( elems ) {
1849  elems = utils.makeArray( elems );
1850  var items = [];
1851  elems.forEach( function( elem ) {
1852    var item = this.getItem( elem );
1853    if ( item ) {
1854      items.push( item );
1855    }
1856  }, this );
1857
1858  return items;
1859};
1860
1861/**
1862 * remove element(s) from instance and DOM
1863 * @param {Array or NodeList or Element} elems
1864 */
1865proto.remove = function( elems ) {
1866  var removeItems = this.getItems( elems );
1867
1868  this._emitCompleteOnItems( 'remove', removeItems );
1869
1870  // bail if no items to remove
1871  if ( !removeItems || !removeItems.length ) {
1872    return;
1873  }
1874
1875  removeItems.forEach( function( item ) {
1876    item.remove();
1877    // remove item from collection
1878    utils.removeFrom( this.items, item );
1879  }, this );
1880};
1881
1882// ----- destroy ----- //
1883
1884// remove and disable Outlayer instance
1885proto.destroy = function() {
1886  // clean up dynamic styles
1887  var style = this.element.style;
1888  style.height = '';
1889  style.position = '';
1890  style.width = '';
1891  // destroy items
1892  this.items.forEach( function( item ) {
1893    item.destroy();
1894  });
1895
1896  this.unbindResize();
1897
1898  var id = this.element.outlayerGUID;
1899  delete instances[ id ]; // remove reference to instance by id
1900  delete this.element.outlayerGUID;
1901  // remove data for jQuery
1902  if ( jQuery ) {
1903    jQuery.removeData( this.element, this.constructor.namespace );
1904  }
1905
1906};
1907
1908// -------------------------- data -------------------------- //
1909
1910/**
1911 * get Outlayer instance from element
1912 * @param {Element} elem
1913 * @returns {Outlayer}
1914 */
1915Outlayer.data = function( elem ) {
1916  elem = utils.getQueryElement( elem );
1917  var id = elem && elem.outlayerGUID;
1918  return id && instances[ id ];
1919};
1920
1921
1922// -------------------------- create Outlayer class -------------------------- //
1923
1924/**
1925 * create a layout class
1926 * @param {String} namespace
1927 */
1928Outlayer.create = function( namespace, options ) {
1929  // sub-class Outlayer
1930  var Layout = subclass( Outlayer );
1931  // apply new options and compatOptions
1932  Layout.defaults = utils.extend( {}, Outlayer.defaults );
1933  utils.extend( Layout.defaults, options );
1934  Layout.compatOptions = utils.extend( {}, Outlayer.compatOptions  );
1935
1936  Layout.namespace = namespace;
1937
1938  Layout.data = Outlayer.data;
1939
1940  // sub-class Item
1941  Layout.Item = subclass( Item );
1942
1943  // -------------------------- declarative -------------------------- //
1944
1945  utils.htmlInit( Layout, namespace );
1946
1947  // -------------------------- jQuery bridge -------------------------- //
1948
1949  // make into jQuery plugin
1950  if ( jQuery && jQuery.bridget ) {
1951    jQuery.bridget( namespace, Layout );
1952  }
1953
1954  return Layout;
1955};
1956
1957function subclass( Parent ) {
1958  function SubClass() {
1959    Parent.apply( this, arguments );
1960  }
1961
1962  SubClass.prototype = Object.create( Parent.prototype );
1963  SubClass.prototype.constructor = SubClass;
1964
1965  return SubClass;
1966}
1967
1968// ----- helpers ----- //
1969
1970// how many milliseconds are in each unit
1971var msUnits = {
1972  ms: 1,
1973  s: 1000
1974};
1975
1976// munge time-like parameter into millisecond number
1977// '0.4s' -> 40
1978function getMilliseconds( time ) {
1979  if ( typeof time == 'number' ) {
1980    return time;
1981  }
1982  var matches = time.match( /(^\d*\.?\d*)(\w*)/ );
1983  var num = matches && matches[1];
1984  var unit = matches && matches[2];
1985  if ( !num.length ) {
1986    return 0;
1987  }
1988  num = parseFloat( num );
1989  var mult = msUnits[ unit ] || 1;
1990  return num * mult;
1991}
1992
1993// ----- fin ----- //
1994
1995// back in global
1996Outlayer.Item = Item;
1997
1998return Outlayer;
1999
2000}));
2001
2002
2003/***/ }),
2004/* 6 */
2005/***/ (function(module, exports, __webpack_require__) {
2006
2007var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/**
2008 * Isotope LayoutMode
2009 */
2010
2011( function( window, factory ) {
2012  // universal module definition
2013  /* jshint strict: false */ /*globals define, module, require */
2014  if ( true ) {
2015    // AMD
2016    !(__WEBPACK_AMD_DEFINE_ARRAY__ = [
2017        __webpack_require__(3),
2018        __webpack_require__(5)
2019      ], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
2020				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
2021				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
2022				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
2023  } else if ( typeof module == 'object' && module.exports ) {
2024    // CommonJS
2025    module.exports = factory(
2026      require('get-size'),
2027      require('outlayer')
2028    );
2029  } else {
2030    // browser global
2031    window.Isotope = window.Isotope || {};
2032    window.Isotope.LayoutMode = factory(
2033      window.getSize,
2034      window.Outlayer
2035    );
2036  }
2037
2038}( window, function factory( getSize, Outlayer ) {
2039  'use strict';
2040
2041  // layout mode class
2042  function LayoutMode( isotope ) {
2043    this.isotope = isotope;
2044    // link properties
2045    if ( isotope ) {
2046      this.options = isotope.options[ this.namespace ];
2047      this.element = isotope.element;
2048      this.items = isotope.filteredItems;
2049      this.size = isotope.size;
2050    }
2051  }
2052
2053  var proto = LayoutMode.prototype;
2054
2055  /**
2056   * some methods should just defer to default Outlayer method
2057   * and reference the Isotope instance as `this`
2058  **/
2059  var facadeMethods = [
2060    '_resetLayout',
2061    '_getItemLayoutPosition',
2062    '_manageStamp',
2063    '_getContainerSize',
2064    '_getElementOffset',
2065    'needsResizeLayout',
2066    '_getOption'
2067  ];
2068
2069  facadeMethods.forEach( function( methodName ) {
2070    proto[ methodName ] = function() {
2071      return Outlayer.prototype[ methodName ].apply( this.isotope, arguments );
2072    };
2073  });
2074
2075  // -----  ----- //
2076
2077  // for horizontal layout modes, check vertical size
2078  proto.needsVerticalResizeLayout = function() {
vendor: 2,698 bytes, lines 2079-2182
2079    // don't trigger if size did not change
2080    var size = getSize( this.isotope.element );
2081    // check that this.size and size are there
2082    // IE8 triggers resize on body size change, so they might not be
2083    var hasSizes = this.isotope.size && size;
2084    return hasSizes && size.innerHeight != this.isotope.size.innerHeight;
2085  };
2086
2087  // ----- measurements ----- //
2088
2089  proto._getMeasurement = function() {
2090    this.isotope._getMeasurement.apply( this, arguments );
2091  };
2092
2093  proto.getColumnWidth = function() {
2094    this.getSegmentSize( 'column', 'Width' );
2095  };
2096
2097  proto.getRowHeight = function() {
2098    this.getSegmentSize( 'row', 'Height' );
2099  };
2100
2101  /**
2102   * get columnWidth or rowHeight
2103   * segment: 'column' or 'row'
2104   * size 'Width' or 'Height'
2105  **/
2106  proto.getSegmentSize = function( segment, size ) {
2107    var segmentName = segment + size;
2108    var outerSize = 'outer' + size;
2109    // columnWidth / outerWidth // rowHeight / outerHeight
2110    this._getMeasurement( segmentName, outerSize );
2111    // got rowHeight or columnWidth, we can chill
2112    if ( this[ segmentName ] ) {
2113      return;
2114    }
2115    // fall back to item of first element
2116    var firstItemSize = this.getFirstItemSize();
2117    this[ segmentName ] = firstItemSize && firstItemSize[ outerSize ] ||
2118      // or size of container
2119      this.isotope.size[ 'inner' + size ];
2120  };
2121
2122  proto.getFirstItemSize = function() {
2123    var firstItem = this.isotope.filteredItems[0];
2124    return firstItem && firstItem.element && getSize( firstItem.element );
2125  };
2126
2127  // ----- methods that should reference isotope ----- //
2128
2129  proto.layout = function() {
2130    this.isotope.layout.apply( this.isotope, arguments );
2131  };
2132
2133  proto.getSize = function() {
2134    this.isotope.getSize();
2135    this.size = this.isotope.size;
2136  };
2137
2138  // -------------------------- create -------------------------- //
2139
2140  LayoutMode.modes = {};
2141
2142  LayoutMode.create = function( namespace, options ) {
2143
2144    function Mode() {
2145      LayoutMode.apply( this, arguments );
2146    }
2147
2148    Mode.prototype = Object.create( proto );
2149    Mode.prototype.constructor = Mode;
2150
2151    // default options
2152    if ( options ) {
2153      Mode.options = options;
2154    }
2155
2156    Mode.prototype.namespace = namespace;
2157    // register in Isotope
2158    LayoutMode.modes[ namespace ] = Mode;
2159
2160    return Mode;
2161  };
2162
2163  return LayoutMode;
2164
2165}));
2166
2167
2168/***/ }),
2169/* 7 */
2170/***/ (function(module, exports, __webpack_require__) {
2171
2172/*!
2173 * imagesLoaded v5.0.0
2174 * JavaScript is all like "You images are done yet or what?"
2175 * MIT License
2176 */
2177
2178( function( window, factory ) {
2179  // universal module definition
2180  if ( typeof module == 'object' && module.exports ) {
2181    // CommonJS
2182    module.exports = factory( window, __webpack_require__(24
vendor: 9,235 bytes, lines 2182-2506
2182) );
2183  } else {
2184    // browser global
2185    window.imagesLoaded = factory( window, window.EvEmitter );
2186  }
2187
2188} )( typeof window !== 'undefined' ? window : this,
2189    function factory( window, EvEmitter ) {
2190
2191let $ = window.jQuery;
2192let console = window.console;
2193
2194// -------------------------- helpers -------------------------- //
2195
2196// turn element or nodeList into an array
2197function makeArray( obj ) {
2198  // use object if already an array
2199  if ( Array.isArray( obj ) ) return obj;
2200
2201  let isArrayLike = typeof obj == 'object' && typeof obj.length == 'number';
2202  // convert nodeList to array
2203  if ( isArrayLike ) return [ ...obj ];
2204
2205  // array of single index
2206  return [ obj ];
2207}
2208
2209// -------------------------- imagesLoaded -------------------------- //
2210
2211/**
2212 * @param {[Array, Element, NodeList, String]} elem
2213 * @param {[Object, Function]} options - if function, use as callback
2214 * @param {Function} onAlways - callback function
2215 * @returns {ImagesLoaded}
2216 */
2217function ImagesLoaded( elem, options, onAlways ) {
2218  // coerce ImagesLoaded() without new, to be new ImagesLoaded()
2219  if ( !( this instanceof ImagesLoaded ) ) {
2220    return new ImagesLoaded( elem, options, onAlways );
2221  }
2222  // use elem as selector string
2223  let queryElem = elem;
2224  if ( typeof elem == 'string' ) {
2225    queryElem = document.querySelectorAll( elem );
2226  }
2227  // bail if bad element
2228  if ( !queryElem ) {
2229    console.error(`Bad element for imagesLoaded ${queryElem || elem}`);
2230    return;
2231  }
2232
2233  this.elements = makeArray( queryElem );
2234  this.options = {};
2235  // shift arguments if no options set
2236  if ( typeof options == 'function' ) {
2237    onAlways = options;
2238  } else {
2239    Object.assign( this.options, options );
2240  }
2241
2242  if ( onAlways ) this.on( 'always', onAlways );
2243
2244  this.getImages();
2245  // add jQuery Deferred object
2246  if ( $ ) this.jqDeferred = new $.Deferred();
2247
2248  // HACK check async to allow time to bind listeners
2249  setTimeout( this.check.bind( this ) );
2250}
2251
2252ImagesLoaded.prototype = Object.create( EvEmitter.prototype );
2253
2254ImagesLoaded.prototype.getImages = function() {
2255  this.images = [];
2256
2257  // filter & find items if we have an item selector
2258  this.elements.forEach( this.addElementImages, this );
2259};
2260
2261const elementNodeTypes = [ 1, 9, 11 ];
2262
2263/**
2264 * @param {Node} elem
2265 */
2266ImagesLoaded.prototype.addElementImages = function( elem ) {
2267  // filter siblings
2268  if ( elem.nodeName === 'IMG' ) {
2269    this.addImage( elem );
2270  }
2271  // get background image on element
2272  if ( this.options.background === true ) {
2273    this.addElementBackgroundImages( elem );
2274  }
2275
2276  // find children
2277  // no non-element nodes, #143
2278  let { nodeType } = elem;
2279  if ( !nodeType || !elementNodeTypes.includes( nodeType ) ) return;
2280
2281  let childImgs = elem.querySelectorAll('img');
2282  // concat childElems to filterFound array
2283  for ( let img of childImgs ) {
2284    this.addImage( img );
2285  }
2286
2287  // get child background images
2288  if ( typeof this.options.background == 'string' ) {
2289    let children = elem.querySelectorAll( this.options.background );
2290    for ( let child of children ) {
2291      this.addElementBackgroundImages( child );
2292    }
2293  }
2294};
2295
2296const reURL = /url\((['"])?(.*?)\1\)/gi;
2297
2298ImagesLoaded.prototype.addElementBackgroundImages = function( elem ) {
2299  let style = getComputedStyle( elem );
2300  // Firefox returns null if in a hidden iframe https://bugzil.la/548397
2301  if ( !style ) return;
2302
2303  // get url inside url("...")
2304  let matches = reURL.exec( style.backgroundImage );
2305  while ( matches !== null ) {
2306    let url = matches && matches[2];
2307    if ( url ) {
2308      this.addBackground( url, elem );
2309    }
2310    matches = reURL.exec( style.backgroundImage );
2311  }
2312};
2313
2314/**
2315 * @param {Image} img
2316 */
2317ImagesLoaded.prototype.addImage = function( img ) {
2318  let loadingImage = new LoadingImage( img );
2319  this.images.push( loadingImage );
2320};
2321
2322ImagesLoaded.prototype.addBackground = function( url, elem ) {
2323  let background = new Background( url, elem );
2324  this.images.push( background );
2325};
2326
2327ImagesLoaded.prototype.check = function() {
2328  this.progressedCount = 0;
2329  this.hasAnyBroken = false;
2330  // complete if no images
2331  if ( !this.images.length ) {
2332    this.complete();
2333    return;
2334  }
2335
2336  /* eslint-disable-next-line func-style */
2337  let onProgress = ( image, elem, message ) => {
2338    // HACK - Chrome triggers event before object properties have changed. #83
2339    setTimeout( () => {
2340      this.progress( image, elem, message );
2341    } );
2342  };
2343
2344  this.images.forEach( function( loadingImage ) {
2345    loadingImage.once( 'progress', onProgress );
2346    loadingImage.check();
2347  } );
2348};
2349
2350ImagesLoaded.prototype.progress = function( image, elem, message ) {
2351  this.progressedCount++;
2352  this.hasAnyBroken = this.hasAnyBroken || !image.isLoaded;
2353  // progress event
2354  this.emitEvent( 'progress', [ this, image, elem ] );
2355  if ( this.jqDeferred && this.jqDeferred.notify ) {
2356    this.jqDeferred.notify( this, image );
2357  }
2358  // check if completed
2359  if ( this.progressedCount === this.images.length ) {
2360    this.complete();
2361  }
2362
2363  if ( this.options.debug && console ) {
2364    console.log( `progress: ${message}`, image, elem );
2365  }
2366};
2367
2368ImagesLoaded.prototype.complete = function() {
2369  let eventName = this.hasAnyBroken ? 'fail' : 'done';
2370  this.isComplete = true;
2371  this.emitEvent( eventName, [ this ] );
2372  this.emitEvent( 'always', [ this ] );
2373  if ( this.jqDeferred ) {
2374    let jqMethod = this.hasAnyBroken ? 'reject' : 'resolve';
2375    this.jqDeferred[ jqMethod ]( this );
2376  }
2377};
2378
2379// --------------------------  -------------------------- //
2380
2381function LoadingImage( img ) {
2382  this.img = img;
2383}
2384
2385LoadingImage.prototype = Object.create( EvEmitter.prototype );
2386
2387LoadingImage.prototype.check = function() {
2388  // If complete is true and browser supports natural sizes,
2389  // try to check for image status manually.
2390  let isComplete = this.getIsImageComplete();
2391  if ( isComplete ) {
2392    // report based on naturalWidth
2393    this.confirm( this.img.naturalWidth !== 0, 'naturalWidth' );
2394    return;
2395  }
2396
2397  // If none of the checks above matched, simulate loading on detached element.
2398  this.proxyImage = new Image();
2399  // add crossOrigin attribute. #204
2400  if ( this.img.crossOrigin ) {
2401    this.proxyImage.crossOrigin = this.img.crossOrigin;
2402  }
2403  this.proxyImage.addEventListener( 'load', this );
2404  this.proxyImage.addEventListener( 'error', this );
2405  // bind to image as well for Firefox. #191
2406  this.img.addEventListener( 'load', this );
2407  this.img.addEventListener( 'error', this );
2408  this.proxyImage.src = this.img.currentSrc || this.img.src;
2409};
2410
2411LoadingImage.prototype.getIsImageComplete = function() {
2412  // check for non-zero, non-undefined naturalWidth
2413  // fixes Safari+InfiniteScroll+Masonry bug infinite-scroll#671
2414  return this.img.complete && this.img.naturalWidth;
2415};
2416
2417LoadingImage.prototype.confirm = function( isLoaded, message ) {
2418  this.isLoaded = isLoaded;
2419  let { parentNode } = this.img;
2420  // emit progress with parent <picture> or self <img>
2421  let elem = parentNode.nodeName === 'PICTURE' ? parentNode : this.img;
2422  this.emitEvent( 'progress', [ this, elem, message ] );
2423};
2424
2425// ----- events ----- //
2426
2427// trigger specified handler for event type
2428LoadingImage.prototype.handleEvent = function( event ) {
2429  let method = 'on' + event.type;
2430  if ( this[ method ] ) {
2431    this[ method ]( event );
2432  }
2433};
2434
2435LoadingImage.prototype.onload = function() {
2436  this.confirm( true, 'onload' );
2437  this.unbindEvents();
2438};
2439
2440LoadingImage.prototype.onerror = function() {
2441  this.confirm( false, 'onerror' );
2442  this.unbindEvents();
2443};
2444
2445LoadingImage.prototype.unbindEvents = function() {
2446  this.proxyImage.removeEventListener( 'load', this );
2447  this.proxyImage.removeEventListener( 'error', this );
2448  this.img.removeEventListener( 'load', this );
2449  this.img.removeEventListener( 'error', this );
2450};
2451
2452// -------------------------- Background -------------------------- //
2453
2454function Background( url, element ) {
2455  this.url = url;
2456  this.element = element;
2457  this.img = new Image();
2458}
2459
2460// inherit LoadingImage prototype
2461Background.prototype = Object.create( LoadingImage.prototype );
2462
2463Background.prototype.check = function() {
2464  this.img.addEventListener( 'load', this );
2465  this.img.addEventListener( 'error', this );
2466  this.img.src = this.url;
2467  // check if image is already complete
2468  let isComplete = this.getIsImageComplete();
2469  if ( isComplete ) {
2470    this.confirm( this.img.naturalWidth !== 0, 'naturalWidth' );
2471    this.unbindEvents();
2472  }
2473};
2474
2475Background.prototype.unbindEvents = function() {
2476  this.img.removeEventListener( 'load', this );
2477  this.img.removeEventListener( 'error', this );
2478};
2479
2480Background.prototype.confirm = function( isLoaded, message ) {
2481  this.isLoaded = isLoaded;
2482  this.emitEvent( 'progress', [ this, this.element, message ] );
2483};
2484
2485// -------------------------- jQuery -------------------------- //
2486
2487ImagesLoaded.makeJQueryPlugin = function( jQuery ) {
2488  jQuery = jQuery || window.jQuery;
2489  if ( !jQuery ) return;
2490
2491  // set local variable
2492  $ = jQuery;
2493  // $().imagesLoaded()
2494  $.fn.imagesLoaded = function( options, onAlways ) {
2495    let instance = new ImagesLoaded( this, options, onAlways );
2496    return instance.jqDeferred.promise( $( this ) );
2497  };
2498};
2499// try making plugin
2500ImagesLoaded.makeJQueryPlugin();
2501
2502// --------------------------  -------------------------- //
2503
2504return ImagesLoaded;
2505
2506} );
2507
2508
2509/***/ }),
2510/* 8 */
2511/***/ (function(module, exports, __webpack_require__) {
2512
2513var __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/*!
2514 * Isotope v3.0.6
2515 *
2516 * Licensed GPLv3 for open source use
2517 * or Isotope Commercial License for commercial use
2518 *
2519 * https://isotope.metafizzy.co
2520 * Copyright 2010-2018 Metafizzy
2521 */
2522
2523( function( window, factory ) {
2524  // universal module definition
2525  /* jshint strict: false */ /*globals define, module, require */
2526  if ( true ) {
2527    // AMD
2528    !(__WEBPACK_AMD_DEFINE_ARRAY__ = [
2529        __webpack_require__(5),
2530        __webpack_require__(3),
2531        __webpack_require__(12),
2532        __webpack_require__(1),
2533        __webpack_require__(26),
2534        __webpack_require__(6),
2535        // include default layout modes
2536        __webpack_require__(27),
2537        __webpack_require__(29),
2538        __webpack_require__(30)
2539      ], __WEBPACK_AMD_DEFINE_RESULT__ = (function( Outlayer, getSize, matchesSelector, utils, Item, LayoutMode ) {
2540        return factory( window, Outlayer, getSize, matchesSelector, utils, Item, LayoutMode );
2541      }).apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__),
2542				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
2543  } else if ( typeof module == 'object' && module.exports ) {
2544    // CommonJS
2545    module.exports = factory(
2546      window,
2547      require('outlayer'),
2548      require('get-size'),
2549      require('desandro-matches-selector'),
2550      require('fizzy-ui-utils'),
2551      require('./item'),
2552      require('./layout-mode'),
2553      // include default layout modes
2554      require('./layout-modes/masonry'),
2555      require('./layout-modes/fit-rows'),
2556      require('./layout-modes/vertical')
2557    );
2558  } else {
2559    // browser global
2560    window.Isotope = factory(
2561      window,
2562      window.Outlayer,
2563      window.getSize,
2564      window.matchesSelector,
2565      window.fizzyUIUtils,
2566      window.Isotope.Item,
2567      window.Isotope.LayoutMode
2568    );
2569  }
2570
2571}( window, function factory( window, Outlayer, getSize, matchesSelector, utils,
2572  Item, LayoutMode ) {
2573
2574'use strict';
vendor: 15,771 bytes, lines 2574-3134
2574
2575
2576// -------------------------- vars -------------------------- //
2577
2578var jQuery = window.jQuery;
2579
2580// -------------------------- helpers -------------------------- //
2581
2582var trim = String.prototype.trim ?
2583  function( str ) {
2584    return str.trim();
2585  } :
2586  function( str ) {
2587    return str.replace( /^\s+|\s+$/g, '' );
2588  };
2589
2590// -------------------------- isotopeDefinition -------------------------- //
2591
2592  // create an Outlayer layout class
2593  var Isotope = Outlayer.create( 'isotope', {
2594    layoutMode: 'masonry',
2595    isJQueryFiltering: true,
2596    sortAscending: true
2597  });
2598
2599  Isotope.Item = Item;
2600  Isotope.LayoutMode = LayoutMode;
2601
2602  var proto = Isotope.prototype;
2603
2604  proto._create = function() {
2605    this.itemGUID = 0;
2606    // functions that sort items
2607    this._sorters = {};
2608    this._getSorters();
2609    // call super
2610    Outlayer.prototype._create.call( this );
2611
2612    // create layout modes
2613    this.modes = {};
2614    // start filteredItems with all items
2615    this.filteredItems = this.items;
2616    // keep of track of sortBys
2617    this.sortHistory = [ 'original-order' ];
2618    // create from registered layout modes
2619    for ( var name in LayoutMode.modes ) {
2620      this._initLayoutMode( name );
2621    }
2622  };
2623
2624  proto.reloadItems = function() {
2625    // reset item ID counter
2626    this.itemGUID = 0;
2627    // call super
2628    Outlayer.prototype.reloadItems.call( this );
2629  };
2630
2631  proto._itemize = function() {
2632    var items = Outlayer.prototype._itemize.apply( this, arguments );
2633    // assign ID for original-order
2634    for ( var i=0; i < items.length; i++ ) {
2635      var item = items[i];
2636      item.id = this.itemGUID++;
2637    }
2638    this._updateItemsSortData( items );
2639    return items;
2640  };
2641
2642
2643  // -------------------------- layout -------------------------- //
2644
2645  proto._initLayoutMode = function( name ) {
2646    var Mode = LayoutMode.modes[ name ];
2647    // set mode options
2648    // HACK extend initial options, back-fill in default options
2649    var initialOpts = this.options[ name ] || {};
2650    this.options[ name ] = Mode.options ?
2651      utils.extend( Mode.options, initialOpts ) : initialOpts;
2652    // init layout mode instance
2653    this.modes[ name ] = new Mode( this );
2654  };
2655
2656
2657  proto.layout = function() {
2658    // if first time doing layout, do all magic
2659    if ( !this._isLayoutInited && this._getOption('initLayout') ) {
2660      this.arrange();
2661      return;
2662    }
2663    this._layout();
2664  };
2665
2666  // private method to be used in layout() & magic()
2667  proto._layout = function() {
2668    // don't animate first layout
2669    var isInstant = this._getIsInstant();
2670    // layout flow
2671    this._resetLayout();
2672    this._manageStamps();
2673    this.layoutItems( this.filteredItems, isInstant );
2674
2675    // flag for initalized
2676    this._isLayoutInited = true;
2677  };
2678
2679  // filter + sort + layout
2680  proto.arrange = function( opts ) {
2681    // set any options pass
2682    this.option( opts );
2683    this._getIsInstant();
2684    // filter, sort, and layout
2685
2686    // filter
2687    var filtered = this._filter( this.items );
2688    this.filteredItems = filtered.matches;
2689
2690    this._bindArrangeComplete();
2691
2692    if ( this._isInstant ) {
2693      this._noTransition( this._hideReveal, [ filtered ] );
2694    } else {
2695      this._hideReveal( filtered );
2696    }
2697
2698    this._sort();
2699    this._layout();
2700  };
2701  // alias to _init for main plugin method
2702  proto._init = proto.arrange;
2703
2704  proto._hideReveal = function( filtered ) {
2705    this.reveal( filtered.needReveal );
2706    this.hide( filtered.needHide );
2707  };
2708
2709  // HACK
2710  // Don't animate/transition first layout
2711  // Or don't animate/transition other layouts
2712  proto._getIsInstant = function() {
2713    var isLayoutInstant = this._getOption('layoutInstant');
2714    var isInstant = isLayoutInstant !== undefined ? isLayoutInstant :
2715      !this._isLayoutInited;
2716    this._isInstant = isInstant;
2717    return isInstant;
2718  };
2719
2720  // listen for layoutComplete, hideComplete and revealComplete
2721  // to trigger arrangeComplete
2722  proto._bindArrangeComplete = function() {
2723    // listen for 3 events to trigger arrangeComplete
2724    var isLayoutComplete, isHideComplete, isRevealComplete;
2725    var _this = this;
2726    function arrangeParallelCallback() {
2727      if ( isLayoutComplete && isHideComplete && isRevealComplete ) {
2728        _this.dispatchEvent( 'arrangeComplete', null, [ _this.filteredItems ] );
2729      }
2730    }
2731    this.once( 'layoutComplete', function() {
2732      isLayoutComplete = true;
2733      arrangeParallelCallback();
2734    });
2735    this.once( 'hideComplete', function() {
2736      isHideComplete = true;
2737      arrangeParallelCallback();
2738    });
2739    this.once( 'revealComplete', function() {
2740      isRevealComplete = true;
2741      arrangeParallelCallback();
2742    });
2743  };
2744
2745  // -------------------------- filter -------------------------- //
2746
2747  proto._filter = function( items ) {
2748    var filter = this.options.filter;
2749    filter = filter || '*';
2750    var matches = [];
2751    var hiddenMatched = [];
2752    var visibleUnmatched = [];
2753
2754    var test = this._getFilterTest( filter );
2755
2756    // test each item
2757    for ( var i=0; i < items.length; i++ ) {
2758      var item = items[i];
2759      if ( item.isIgnored ) {
2760        continue;
2761      }
2762      // add item to either matched or unmatched group
2763      var isMatched = test( item );
2764      // item.isFilterMatched = isMatched;
2765      // add to matches if its a match
2766      if ( isMatched ) {
2767        matches.push( item );
2768      }
2769      // add to additional group if item needs to be hidden or revealed
2770      if ( isMatched && item.isHidden ) {
2771        hiddenMatched.push( item );
2772      } else if ( !isMatched && !item.isHidden ) {
2773        visibleUnmatched.push( item );
2774      }
2775    }
2776
2777    // return collections of items to be manipulated
2778    return {
2779      matches: matches,
2780      needReveal: hiddenMatched,
2781      needHide: visibleUnmatched
2782    };
2783  };
2784
2785  // get a jQuery, function, or a matchesSelector test given the filter
2786  proto._getFilterTest = function( filter ) {
2787    if ( jQuery && this.options.isJQueryFiltering ) {
2788      // use jQuery
2789      return function( item ) {
2790        return jQuery( item.element ).is( filter );
2791      };
2792    }
2793    if ( typeof filter == 'function' ) {
2794      // use filter as function
2795      return function( item ) {
2796        return filter( item.element );
2797      };
2798    }
2799    // default, use filter as selector string
2800    return function( item ) {
2801      return matchesSelector( item.element, filter );
2802    };
2803  };
2804
2805  // -------------------------- sorting -------------------------- //
2806
2807  /**
2808   * @params {Array} elems
2809   * @public
2810   */
2811  proto.updateSortData = function( elems ) {
2812    // get items
2813    var items;
2814    if ( elems ) {
2815      elems = utils.makeArray( elems );
2816      items = this.getItems( elems );
2817    } else {
2818      // update all items if no elems provided
2819      items = this.items;
2820    }
2821
2822    this._getSorters();
2823    this._updateItemsSortData( items );
2824  };
2825
2826  proto._getSorters = function() {
2827    var getSortData = this.options.getSortData;
2828    for ( var key in getSortData ) {
2829      var sorter = getSortData[ key ];
2830      this._sorters[ key ] = mungeSorter( sorter );
2831    }
2832  };
2833
2834  /**
2835   * @params {Array} items - of Isotope.Items
2836   * @private
2837   */
2838  proto._updateItemsSortData = function( items ) {
2839    // do not update if no items
2840    var len = items && items.length;
2841
2842    for ( var i=0; len && i < len; i++ ) {
2843      var item = items[i];
2844      item.updateSortData();
2845    }
2846  };
2847
2848  // ----- munge sorter ----- //
2849
2850  // encapsulate this, as we just need mungeSorter
2851  // other functions in here are just for munging
2852  var mungeSorter = ( function() {
2853    // add a magic layer to sorters for convienent shorthands
2854    // `.foo-bar` will use the text of .foo-bar querySelector
2855    // `[foo-bar]` will use attribute
2856    // you can also add parser
2857    // `.foo-bar parseInt` will parse that as a number
2858    function mungeSorter( sorter ) {
2859      // if not a string, return function or whatever it is
2860      if ( typeof sorter != 'string' ) {
2861        return sorter;
2862      }
2863      // parse the sorter string
2864      var args = trim( sorter ).split(' ');
2865      var query = args[0];
2866      // check if query looks like [an-attribute]
2867      var attrMatch = query.match( /^\[(.+)\]$/ );
2868      var attr = attrMatch && attrMatch[1];
2869      var getValue = getValueGetter( attr, query );
2870      // use second argument as a parser
2871      var parser = Isotope.sortDataParsers[ args[1] ];
2872      // parse the value, if there was a parser
2873      sorter = parser ? function( elem ) {
2874        return elem && parser( getValue( elem ) );
2875      } :
2876      // otherwise just return value
2877      function( elem ) {
2878        return elem && getValue( elem );
2879      };
2880
2881      return sorter;
2882    }
2883
2884    // get an attribute getter, or get text of the querySelector
2885    function getValueGetter( attr, query ) {
2886      // if query looks like [foo-bar], get attribute
2887      if ( attr ) {
2888        return function getAttribute( elem ) {
2889          return elem.getAttribute( attr );
2890        };
2891      }
2892
2893      // otherwise, assume its a querySelector, and get its text
2894      return function getChildText( elem ) {
2895        var child = elem.querySelector( query );
2896        return child && child.textContent;
2897      };
2898    }
2899
2900    return mungeSorter;
2901  })();
2902
2903  // parsers used in getSortData shortcut strings
2904  Isotope.sortDataParsers = {
2905    'parseInt': function( val ) {
2906      return parseInt( val, 10 );
2907    },
2908    'parseFloat': function( val ) {
2909      return parseFloat( val );
2910    }
2911  };
2912
2913  // ----- sort method ----- //
2914
2915  // sort filteredItem order
2916  proto._sort = function() {
2917    if ( !this.options.sortBy ) {
2918      return;
2919    }
2920    // keep track of sortBy History
2921    var sortBys = utils.makeArray( this.options.sortBy );
2922    if ( !this._getIsSameSortBy( sortBys ) ) {
2923      // concat all sortBy and sortHistory, add to front, oldest goes in last
2924      this.sortHistory = sortBys.concat( this.sortHistory );
2925    }
2926    // sort magic
2927    var itemSorter = getItemSorter( this.sortHistory, this.options.sortAscending );
2928    this.filteredItems.sort( itemSorter );
2929  };
2930
2931  // check if sortBys is same as start of sortHistory
2932  proto._getIsSameSortBy = function( sortBys ) {
2933    for ( var i=0; i < sortBys.length; i++ ) {
2934      if ( sortBys[i] != this.sortHistory[i] ) {
2935        return false;
2936      }
2937    }
2938    return true;
2939  };
2940
2941  // returns a function used for sorting
2942  function getItemSorter( sortBys, sortAsc ) {
2943    return function sorter( itemA, itemB ) {
2944      // cycle through all sortKeys
2945      for ( var i = 0; i < sortBys.length; i++ ) {
2946        var sortBy = sortBys[i];
2947        var a = itemA.sortData[ sortBy ];
2948        var b = itemB.sortData[ sortBy ];
2949        if ( a > b || a < b ) {
2950          // if sortAsc is an object, use the value given the sortBy key
2951          var isAscending = sortAsc[ sortBy ] !== undefined ? sortAsc[ sortBy ] : sortAsc;
2952          var direction = isAscending ? 1 : -1;
2953          return ( a > b ? 1 : -1 ) * direction;
2954        }
2955      }
2956      return 0;
2957    };
2958  }
2959
2960  // -------------------------- methods -------------------------- //
2961
2962  // get layout mode
2963  proto._mode = function() {
2964    var layoutMode = this.options.layoutMode;
2965    var mode = this.modes[ layoutMode ];
2966    if ( !mode ) {
2967      // TODO console.error
2968      throw new Error( 'No layout mode: ' + layoutMode );
2969    }
2970    // HACK sync mode's options
2971    // any options set after init for layout mode need to be synced
2972    mode.options = this.options[ layoutMode ];
2973    return mode;
2974  };
2975
2976  proto._resetLayout = function() {
2977    // trigger original reset layout
2978    Outlayer.prototype._resetLayout.call( this );
2979    this._mode()._resetLayout();
2980  };
2981
2982  proto._getItemLayoutPosition = function( item  ) {
2983    return this._mode()._getItemLayoutPosition( item );
2984  };
2985
2986  proto._manageStamp = function( stamp ) {
2987    this._mode()._manageStamp( stamp );
2988  };
2989
2990  proto._getContainerSize = function() {
2991    return this._mode()._getContainerSize();
2992  };
2993
2994  proto.needsResizeLayout = function() {
2995    return this._mode().needsResizeLayout();
2996  };
2997
2998  // -------------------------- adding & removing -------------------------- //
2999
3000  // HEADS UP overwrites default Outlayer appended
3001  proto.appended = function( elems ) {
3002    var items = this.addItems( elems );
3003    if ( !items.length ) {
3004      return;
3005    }
3006    // filter, layout, reveal new items
3007    var filteredItems = this._filterRevealAdded( items );
3008    // add to filteredItems
3009    this.filteredItems = this.filteredItems.concat( filteredItems );
3010  };
3011
3012  // HEADS UP overwrites default Outlayer prepended
3013  proto.prepended = function( elems ) {
3014    var items = this._itemize( elems );
3015    if ( !items.length ) {
3016      return;
3017    }
3018    // start new layout
3019    this._resetLayout();
3020    this._manageStamps();
3021    // filter, layout, reveal new items
3022    var filteredItems = this._filterRevealAdded( items );
3023    // layout previous items
3024    this.layoutItems( this.filteredItems );
3025    // add to items and filteredItems
3026    this.filteredItems = filteredItems.concat( this.filteredItems );
3027    this.items = items.concat( this.items );
3028  };
3029
3030  proto._filterRevealAdded = function( items ) {
3031    var filtered = this._filter( items );
3032    this.hide( filtered.needHide );
3033    // reveal all new items
3034    this.reveal( filtered.matches );
3035    // layout new items, no transition
3036    this.layoutItems( filtered.matches, true );
3037    return filtered.matches;
3038  };
3039
3040  /**
3041   * Filter, sort, and layout newly-appended item elements
3042   * @param {Array or NodeList or Element} elems
3043   */
3044  proto.insert = function( elems ) {
3045    var items = this.addItems( elems );
3046    if ( !items.length ) {
3047      return;
3048    }
3049    // append item elements
3050    var i, item;
3051    var len = items.length;
3052    for ( i=0; i < len; i++ ) {
3053      item = items[i];
3054      this.element.appendChild( item.element );
3055    }
3056    // filter new stuff
3057    var filteredInsertItems = this._filter( items ).matches;
3058    // set flag
3059    for ( i=0; i < len; i++ ) {
3060      items[i].isLayoutInstant = true;
3061    }
3062    this.arrange();
3063    // reset flag
3064    for ( i=0; i < len; i++ ) {
3065      delete items[i].isLayoutInstant;
3066    }
3067    this.reveal( filteredInsertItems );
3068  };
3069
3070  var _remove = proto.remove;
3071  proto.remove = function( elems ) {
3072    elems = utils.makeArray( elems );
3073    var removeItems = this.getItems( elems );
3074    // do regular thing
3075    _remove.call( this, elems );
3076    // bail if no items to remove
3077    var len = removeItems && removeItems.length;
3078    // remove elems from filteredItems
3079    for ( var i=0; len && i < len; i++ ) {
3080      var item = removeItems[i];
3081      // remove item from collection
3082      utils.removeFrom( this.filteredItems, item );
3083    }
3084  };
3085
3086  proto.shuffle = function() {
3087    // update random sortData
3088    for ( var i=0; i < this.items.length; i++ ) {
3089      var item = this.items[i];
3090      item.sortData.random = Math.random();
3091    }
3092    this.options.sortBy = 'random';
3093    this._sort();
3094    this._layout();
3095  };
3096
3097  /**
3098   * trigger fn without transition
3099   * kind of hacky to have this in the first place
3100   * @param {Function} fn
3101   * @param {Array} args
3102   * @returns ret
3103   * @private
3104   */
3105  proto._noTransition = function( fn, args ) {
3106    // save transitionDuration before disabling
3107    var transitionDuration = this.options.transitionDuration;
3108    // disable transition
3109    this.options.transitionDuration = 0;
3110    // do it
3111    var returnValue = fn.apply( this, args );
3112    // re-enable transition for reveal
3113    this.options.transitionDuration = transitionDuration;
3114    return returnValue;
3115  };
3116
3117  // ----- helper methods ----- //
3118
3119  /**
3120   * getter method for getting filtered item elements
3121   * @returns {Array} elems - collection of item elements
3122   */
3123  proto.getFilteredItemElements = function() {
3124    return this.filteredItems.map( function( item ) {
3125      return item.element;
3126    });
3127  };
3128
3129  // -----  ----- //
3130
3131  return Isotope;
3132
3133}));
3134
3135
3136/***/ }),
3137/* 9 */
3138/***/ (function(module, exports, __webpack_require__) {
3139
3140var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/*!
3141 * Infinite Scroll v3.0.3
3142 * Automatically add next page
3143 *
3144 * Licensed GPLv3 for open source use
3145 * or Infinite Scroll Commercial License for commercial use
3146 *
3147 * https://infinite-scroll.com
3148 * Copyright 2018 Metafizzy
3149 */
3150
3151( function( window, factory ) {
3152  // universal module definition
3153  /* globals define, module, require */
3154  if ( true ) {
3155    // AMD
3156    !(__WEBPACK_AMD_DEFINE_ARRAY__ = [
3157      __webpack_require__(2),
3158      __webpack_require__(32),
3159      __webpack_require__(33),
3160      __webpack_require__(34),
3161      __webpack_require__(35),
3162      __webpack_require__(36),
3163    ], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
3164				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
3165				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
3166				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
3167  } else if ( typeof module == 'object' && module.exports ) {
3168    // CommonJS
3169    module.exports = factory(
3170      require('./core'),
3171      require('./page-load'),
3172      require('./scroll-watch'),
3173      require('./history'),
3174      require('./button'),
3175      require('./status')
3176    );
3177  }
3178
3179})( window, function factory( InfiniteScroll ) {
3180  return InfiniteScroll;
3181});
3182
3183
3184/***/ }),
3185/* 10 */
3186/***/ (function(module, __webpack_exports__, __webpack_require__) {
3187
3188"use strict";
3189/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return GSCache; });
3190/* unused harmony export Animation */
3191/* unused harmony export Timeline */
3192/* unused harmony export Tween */
3193/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "b", function() { return PropTween; });
3194/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "w", function() { return gsap; });
3195/* unused harmony export Power0 */
3196/* unused harmony export Power1 */
3197/* unused harmony export Power2 */
3198/* unused harmony export Power3 */
3199/* unused harmony export Power4 */
3200/* unused harmony export Linear */
3201/* unused harmony export Quad */
3202/* unused harmony export Cubic */
3203/* unused harmony export Quart */
3204/* unused harmony export Quint */
3205/* unused harmony export Strong */
3206/* unused harmony export Elastic */
3207/* unused harmony export Back */
3208/* unused harmony export SteppedEase */
3209/* unused harmony export Bounce */
3210/* unused harmony export Sine */
3211/* unused harmony export Expo */
3212/* unused harmony export Circ */
3213/* unused harmony export TweenMax */
3214/* unused harmony export TweenLite */
3215/* unused harmony export TimelineMax */
3216/* unused harmony export TimelineLite */
3217/* unused harmony export default */
3218/* unused harmony export wrap */
3219/* unused harmony export wrapYoyo */
3220/* unused harmony export distribute */
3221/* unused harmony export random */
3222/* unused harmony export snap */
3223/* unused harmony export normalize */
3224/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "v", function() { return getUnit; });
3225/* unused harmony export clamp */
3226/* unused harmony export splitColor */
3227/* unused harmony export toArray */
3228/* unused harmony export mapRange */
3229/* unused harmony export pipe */
3230/* unused harmony export unitize */
3231/* unused harmony export interpolate */
3232/* unused harmony export shuffle */
3233/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "h", function() { return _getProperty; });
3234/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "m", function() { return _numExp; });
3235/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "n", function() { return _numWithUnitExp; });
3236/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "j", function() { return _isString; });
3237/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "k", function() { return _isUndefined; });
3238/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "q", function() { return _renderComplexString; });
3239/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "p", function() { return _relExp; });
3240/* unused harmony export _setDefaults */
3241/* unused harmony export _removeLinkedListItem */
3242/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "f", function() { return _forEachName; });
3243/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "t", function() { return _sortPropTweensByPriority; });
3244/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "d", function() { return _colorStringFilter; });
3245/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "r", function() { return _replaceRandom; });
3246/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "c", function() { return _checkPlugin; });
3247/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "o", function() { return _plugins; });
3248/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "u", function() { return _ticker; });
3249/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "e", function() { return _config; });
3250/* unused harmony export _roundModifier */
3251/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "s", function() { return _round; });
3252/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "l", function() { return _missingPlugin; });
3253/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "i", function() { return _getSetter; });
3254/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "g", function() { return _getCache; });
3255function _assertThisInitialized(self) { if (self === void 0) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return self; }
3256
3257function _inheritsLoose(subClass, superClass) { subClass.prototype = Object.create(superClass.prototype); subClass.prototype.constructor = subClass; subClass.__proto__ = superClass; }
3258
3259/*!
3260 * GSAP 3.6.0
3261 * https://greensock.com
3262 *
3263 * @license Copyright 2008-2021, GreenSock. All rights reserved.
3264 * Subject to the terms at https://greensock.com/standard-license or for
3265 * Club GreenSock members, the agreement issued with that membership.
3266 * @author: Jack Doyle, [email protected]
3267*/
3268
3269/* eslint-disable */
3270var _config = {
3271  autoSleep: 120,
3272  force3D: "auto",
3273  nullTargetWarn: 1,
3274  units: {
3275    lineHeight: ""
3276  }
3277},
3278    _defaults = {
3279  duration: .5,
3280  overwrite: false,
3281  delay: 0
3282},
3283    _suppressOverwrites,
3284    _bigNum = 1e8,
3285    _tinyNum = 1 / _bigNum,
3286    _2PI = Math.PI * 2,
3287    _HALF_PI = _2PI / 4,
3288    _gsID = 0,
3289    _sqrt = Math.sqrt,
3290    _cos = Math.cos,
3291    _sin = Math.sin,
3292    _isString = function _isString(value) {
3293  return typeof value === "string";
3294},
3295    _isFunction = function _isFunction(value) {
3296  return typeof value === "function";
3297},
3298    _isNumber = function _isNumber(value) {
3299  return typeof value === "number";
3300},
3301    _isUndefined = function _isUndefined(value) {
3302  return typeof value === "undefined";
3303},
3304    _isObject = function _isObject(value) {
3305  return typeof value === "object";
3306},
3307    _isNotFalse = function _isNotFalse(value) {
3308  return value !== false;
3309},
3310    _windowExists = function _windowExists() {
3311  return typeof window !== "undefined";
3312},
3313    _isFuncOrString = function _isFuncOrString(value) {
3314  return _isFunction(value) || _isString(value);
3315},
3316    _isTypedArray = typeof ArrayBuffer === "function" && ArrayBuffer.isView || function () {},
3317    // note: IE10 has ArrayBuffer, but NOT ArrayBuffer.isView().
3318_isArray = Array.isArray,
vendor: 13,896 bytes, lines 3319-3673
3319    _strictNumExp = /(?:-?\.?\d|\.)+/gi,
3320    //only numbers (including negatives and decimals) but NOT relative values.
3321_numExp = /[-+=.]*\d+[.e\-+]*\d*[e\-+]*\d*/g,
3322    //finds any numbers, including ones that start with += or -=, negative numbers, and ones in scientific notation like 1e-8.
3323_numWithUnitExp = /[-+=.]*\d+[.e-]*\d*[a-z%]*/g,
3324    _complexStringNumExp = /[-+=.]*\d+\.?\d*(?:e-|e\+)?\d*/gi,
3325    //duplicate so that while we're looping through matches from exec(), it doesn't contaminate the lastIndex of _numExp which we use to search for colors too.
3326_relExp = /[+-]=-?[.\d]+/,
3327    _delimitedValueExp = /[#\-+.]*\b[a-z\d-=+%.]+/gi,
3328    _unitExp = /[\d.+\-=]+(?:e[-+]\d*)*/i,
3329    _globalTimeline,
3330    _win,
3331    _coreInitted,
3332    _doc,
3333    _globals = {},
3334    _installScope = {},
3335    _coreReady,
3336    _install = function _install(scope) {
3337  return (_installScope = _merge(scope, _globals)) && gsap;
3338},
3339    _missingPlugin = function _missingPlugin(property, value) {
3340  return console.warn("Invalid property", property, "set to", value, "Missing plugin? gsap.registerPlugin()");
3341},
3342    _warn = function _warn(message, suppress) {
3343  return !suppress && console.warn(message);
3344},
3345    _addGlobal = function _addGlobal(name, obj) {
3346  return name && (_globals[name] = obj) && _installScope && (_installScope[name] = obj) || _globals;
3347},
3348    _emptyFunc = function _emptyFunc() {
3349  return 0;
3350},
3351    _reservedProps = {},
3352    _lazyTweens = [],
3353    _lazyLookup = {},
3354    _lastRenderedFrame,
3355    _plugins = {},
3356    _effects = {},
3357    _nextGCFrame = 30,
3358    _harnessPlugins = [],
3359    _callbackNames = "",
3360    _harness = function _harness(targets) {
3361  var target = targets[0],
3362      harnessPlugin,
3363      i;
3364  _isObject(target) || _isFunction(target) || (targets = [targets]);
3365
3366  if (!(harnessPlugin = (target._gsap || {}).harness)) {
3367    // find the first target with a harness. We assume targets passed into an animation will be of similar type, meaning the same kind of harness can be used for them all (performance optimization)
3368    i = _harnessPlugins.length;
3369
3370    while (i-- && !_harnessPlugins[i].targetTest(target)) {}
3371
3372    harnessPlugin = _harnessPlugins[i];
3373  }
3374
3375  i = targets.length;
3376
3377  while (i--) {
3378    targets[i] && (targets[i]._gsap || (targets[i]._gsap = new GSCache(targets[i], harnessPlugin))) || targets.splice(i, 1);
3379  }
3380
3381  return targets;
3382},
3383    _getCache = function _getCache(target) {
3384  return target._gsap || _harness(toArray(target))[0]._gsap;
3385},
3386    _getProperty = function _getProperty(target, property, v) {
3387  return (v = target[property]) && _isFunction(v) ? target[property]() : _isUndefined(v) && target.getAttribute && target.getAttribute(property) || v;
3388},
3389    _forEachName = function _forEachName(names, func) {
3390  return (names = names.split(",")).forEach(func) || names;
3391},
3392    //split a comma-delimited list of names into an array, then run a forEach() function and return the split array (this is just a way to consolidate/shorten some code).
3393_round = function _round(value) {
3394  return Math.round(value * 100000) / 100000 || 0;
3395},
3396    _arrayContainsAny = function _arrayContainsAny(toSearch, toFind) {
3397  //searches one array to find matches for any of the items in the toFind array. As soon as one is found, it returns true. It does NOT return all the matches; it's simply a boolean search.
3398  var l = toFind.length,
3399      i = 0;
3400
3401  for (; toSearch.indexOf(toFind[i]) < 0 && ++i < l;) {}
3402
3403  return i < l;
3404},
3405    _parseVars = function _parseVars(params, type, parent) {
3406  //reads the arguments passed to one of the key methods and figures out if the user is defining things with the OLD/legacy syntax where the duration is the 2nd parameter, and then it adjusts things accordingly and spits back the corrected vars object (with the duration added if necessary, as well as runBackwards or startAt or immediateRender). type 0 = to()/staggerTo(), 1 = from()/staggerFrom(), 2 = fromTo()/staggerFromTo()
3407  var isLegacy = _isNumber(params[1]),
3408      varsIndex = (isLegacy ? 2 : 1) + (type < 2 ? 0 : 1),
3409      vars = params[varsIndex],
3410      irVars;
3411
3412  isLegacy && (vars.duration = params[1]);
3413  vars.parent = parent;
3414
3415  if (type) {
3416    irVars = vars;
3417
3418    while (parent && !("immediateRender" in irVars)) {
3419      // inheritance hasn't happened yet, but someone may have set a default in an ancestor timeline. We could do vars.immediateRender = _isNotFalse(_inheritDefaults(vars).immediateRender) but that'd exact a slight performance penalty because _inheritDefaults() also runs in the Tween constructor. We're paying a small kb price here to gain speed.
3420      irVars = parent.vars.defaults || {};
3421      parent = _isNotFalse(parent.vars.inherit) && parent.parent;
3422    }
3423
3424    vars.immediateRender = _isNotFalse(irVars.immediateRender);
3425    type < 2 ? vars.runBackwards = 1 : vars.startAt = params[varsIndex - 1]; // "from" vars
3426  }
3427
3428  return vars;
3429},
3430    _lazyRender = function _lazyRender() {
3431  var l = _lazyTweens.length,
3432      a = _lazyTweens.slice(0),
3433      i,
3434      tween;
3435
3436  _lazyLookup = {};
3437  _lazyTweens.length = 0;
3438
3439  for (i = 0; i < l; i++) {
3440    tween = a[i];
3441    tween && tween._lazy && (tween.render(tween._lazy[0], tween._lazy[1], true)._lazy = 0);
3442  }
3443},
3444    _lazySafeRender = function _lazySafeRender(animation, time, suppressEvents, force) {
3445  _lazyTweens.length && _lazyRender();
3446  animation.render(time, suppressEvents, force);
3447  _lazyTweens.length && _lazyRender(); //in case rendering caused any tweens to lazy-init, we should render them because typically when someone calls seek() or time() or progress(), they expect an immediate render.
3448},
3449    _numericIfPossible = function _numericIfPossible(value) {
3450  var n = parseFloat(value);
3451  return (n || n === 0) && (value + "").match(_delimitedValueExp).length < 2 ? n : _isString(value) ? value.trim() : value;
3452},
3453    _passThrough = function _passThrough(p) {
3454  return p;
3455},
3456    _setDefaults = function _setDefaults(obj, defaults) {
3457  for (var p in defaults) {
3458    p in obj || (obj[p] = defaults[p]);
3459  }
3460
3461  return obj;
3462},
3463    _setKeyframeDefaults = function _setKeyframeDefaults(obj, defaults) {
3464  for (var p in defaults) {
3465    p in obj || p === "duration" || p === "ease" || (obj[p] = defaults[p]);
3466  }
3467},
3468    _merge = function _merge(base, toMerge) {
3469  for (var p in toMerge) {
3470    base[p] = toMerge[p];
3471  }
3472
3473  return base;
3474},
3475    _mergeDeep = function _mergeDeep(base, toMerge) {
3476  for (var p in toMerge) {
3477    p !== "__proto__" && p !== "constructor" && p !== "prototype" && (base[p] = _isObject(toMerge[p]) ? _mergeDeep(base[p] || (base[p] = {}), toMerge[p]) : toMerge[p]);
3478  }
3479
3480  return base;
3481},
3482    _copyExcluding = function _copyExcluding(obj, excluding) {
3483  var copy = {},
3484      p;
3485
3486  for (p in obj) {
3487    p in excluding || (copy[p] = obj[p]);
3488  }
3489
3490  return copy;
3491},
3492    _inheritDefaults = function _inheritDefaults(vars) {
3493  var parent = vars.parent || _globalTimeline,
3494      func = vars.keyframes ? _setKeyframeDefaults : _setDefaults;
3495
3496  if (_isNotFalse(vars.inherit)) {
3497    while (parent) {
3498      func(vars, parent.vars.defaults);
3499      parent = parent.parent || parent._dp;
3500    }
3501  }
3502
3503  return vars;
3504},
3505    _arraysMatch = function _arraysMatch(a1, a2) {
3506  var i = a1.length,
3507      match = i === a2.length;
3508
3509  while (match && i-- && a1[i] === a2[i]) {}
3510
3511  return i < 0;
3512},
3513    _addLinkedListItem = function _addLinkedListItem(parent, child, firstProp, lastProp, sortBy) {
3514  if (firstProp === void 0) {
3515    firstProp = "_first";
3516  }
3517
3518  if (lastProp === void 0) {
3519    lastProp = "_last";
3520  }
3521
3522  var prev = parent[lastProp],
3523      t;
3524
3525  if (sortBy) {
3526    t = child[sortBy];
3527
3528    while (prev && prev[sortBy] > t) {
3529      prev = prev._prev;
3530    }
3531  }
3532
3533  if (prev) {
3534    child._next = prev._next;
3535    prev._next = child;
3536  } else {
3537    child._next = parent[firstProp];
3538    parent[firstProp] = child;
3539  }
3540
3541  if (child._next) {
3542    child._next._prev = child;
3543  } else {
3544    parent[lastProp] = child;
3545  }
3546
3547  child._prev = prev;
3548  child.parent = child._dp = parent;
3549  return child;
3550},
3551    _removeLinkedListItem = function _removeLinkedListItem(parent, child, firstProp, lastProp) {
3552  if (firstProp === void 0) {
3553    firstProp = "_first";
3554  }
3555
3556  if (lastProp === void 0) {
3557    lastProp = "_last";
3558  }
3559
3560  var prev = child._prev,
3561      next = child._next;
3562
3563  if (prev) {
3564    prev._next = next;
3565  } else if (parent[firstProp] === child) {
3566    parent[firstProp] = next;
3567  }
3568
3569  if (next) {
3570    next._prev = prev;
3571  } else if (parent[lastProp] === child) {
3572    parent[lastProp] = prev;
3573  }
3574
3575  child._next = child._prev = child.parent = null; // don't delete the _dp just so we can revert if necessary. But parent should be null to indicate the item isn't in a linked list.
3576},
3577    _removeFromParent = function _removeFromParent(child, onlyIfParentHasAutoRemove) {
3578  child.parent && (!onlyIfParentHasAutoRemove || child.parent.autoRemoveChildren) && child.parent.remove(child);
3579  child._act = 0;
3580},
3581    _uncache = function _uncache(animation, child) {
3582  if (animation && (!child || child._end > animation._dur || child._start < 0)) {
3583    // performance optimization: if a child animation is passed in we should only uncache if that child EXTENDS the animation (its end time is beyond the end)
3584    var a = animation;
3585
3586    while (a) {
3587      a._dirty = 1;
3588      a = a.parent;
3589    }
3590  }
3591
3592  return animation;
3593},
3594    _recacheAncestors = function _recacheAncestors(animation) {
3595  var parent = animation.parent;
3596
3597  while (parent && parent.parent) {
3598    //sometimes we must force a re-sort of all children and update the duration/totalDuration of all ancestor timelines immediately in case, for example, in the middle of a render loop, one tween alters another tween's timeScale which shoves its startTime before 0, forcing the parent timeline to shift around and shiftChildren() which could affect that next tween's render (startTime). Doesn't matter for the root timeline though.
3599    parent._dirty = 1;
3600    parent.totalDuration();
3601    parent = parent.parent;
3602  }
3603
3604  return animation;
3605},
3606    _hasNoPausedAncestors = function _hasNoPausedAncestors(animation) {
3607  return !animation || animation._ts && _hasNoPausedAncestors(animation.parent);
3608},
3609    _elapsedCycleDuration = function _elapsedCycleDuration(animation) {
3610  return animation._repeat ? _animationCycle(animation._tTime, animation = animation.duration() + animation._rDelay) * animation : 0;
3611},
3612    // feed in the totalTime and cycleDuration and it'll return the cycle (iteration minus 1) and if the playhead is exactly at the very END, it will NOT bump up to the next cycle.
3613_animationCycle = function _animationCycle(tTime, cycleDuration) {
3614  var whole = Math.floor(tTime /= cycleDuration);
3615  return tTime && whole === tTime ? whole - 1 : whole;
3616},
3617    _parentToChildTotalTime = function _parentToChildTotalTime(parentTime, child) {
3618  return (parentTime - child._start) * child._ts + (child._ts >= 0 ? 0 : child._dirty ? child.totalDuration() : child._tDur);
3619},
3620    _setEnd = function _setEnd(animation) {
3621  return animation._end = _round(animation._start + (animation._tDur / Math.abs(animation._ts || animation._rts || _tinyNum) || 0));
3622},
3623    _alignPlayhead = function _alignPlayhead(animation, totalTime) {
3624  // adjusts the animation's _start and _end according to the provided totalTime (only if the parent's smoothChildTiming is true and the animation isn't paused). It doesn't do any rendering or forcing things back into parent timelines, etc. - that's what totalTime() is for.
3625  var parent = animation._dp;
3626
3627  if (parent && parent.smoothChildTiming && animation._ts) {
3628    animation._start = _round(parent._time - (animation._ts > 0 ? totalTime / animation._ts : ((animation._dirty ? animation.totalDuration() : animation._tDur) - totalTime) / -animation._ts));
3629
3630    _setEnd(animation);
3631
3632    parent._dirty || _uncache(parent, animation); //for performance improvement. If the parent's cache is already dirty, it already took care of marking the ancestors as dirty too, so skip the function call here.
3633  }
3634
3635  return animation;
3636},
3637
3638/*
3639_totalTimeToTime = (clampedTotalTime, duration, repeat, repeatDelay, yoyo) => {
3640	let cycleDuration = duration + repeatDelay,
3641		time = _round(clampedTotalTime % cycleDuration);
3642	if (time > duration) {
3643		time = duration;
3644	}
3645	return (yoyo && (~~(clampedTotalTime / cycleDuration) & 1)) ? duration - time : time;
3646},
3647*/
3648_postAddChecks = function _postAddChecks(timeline, child) {
3649  var t;
3650
3651  if (child._time || child._initted && !child._dur) {
3652    //in case, for example, the _start is moved on a tween that has already rendered. Imagine it's at its end state, then the startTime is moved WAY later (after the end of this timeline), it should render at its beginning.
3653    t = _parentToChildTotalTime(timeline.rawTime(), child);
3654
3655    if (!child._dur || _clamp(0, child.totalDuration(), t) - child._tTime > _tinyNum) {
3656      child.render(t, true);
3657    }
3658  } //if the timeline has already ended but the inserted tween/timeline extends the duration, we should enable this timeline again so that it renders properly. We should also align the playhead with the parent timeline's when appropriate.
3659
3660
3661  if (_uncache(timeline, child)._dp && timeline._initted && timeline._time >= timeline._dur && timeline._ts) {
3662    //in case any of the ancestors had completed but should now be enabled...
3663    if (timeline._dur < timeline.duration()) {
3664      t = timeline;
3665
3666      while (t._dp) {
3667        t.rawTime() >= 0 && t.totalTime(t._tTime); //moves the timeline (shifts its startTime) if necessary, and also enables it. If it's currently zero, though, it may not be scheduled to render until later so there's no need to force it to align with the current playhead position. Only move to catch up with the playhead.
3668
3669        t = t._dp;
3670      }
3671    }
3672
3673    timeline._zTime = -_tinyNum; // helps ensure that the next render() will be forced (crossingStart = true in render()), even if the duration hasn't changed (we're adding a child which w
3673ould need to get rendered). Definitely an edge case. Note: we MUST do this AFTER the loop above where the totalTime() might trigger a render() because this _addToTimeline() method gets called from the Animation constructor, BEFORE tweens even record their targets, etc. so we wouldn't want things to get triggered in the wrong order.
3674  }
3675},
3676    _addToTimeline = function _addToTimeline(timeline, child, position, skipChecks) {
3677  child.parent && _removeFromParent(child);
3678  child._start = _round(position + child._delay);
3679  child._end = _round(child._start + (child.totalDuration() / Math.abs(child.timeScale()) || 0));
3680
3681  _addLinkedListItem(timeline, child, "_first", "_last", timeline._sort ? "_start" : 0);
3682
3683  timeline._recent = child;
3684  skipChecks || _postAddChecks(timeline, child);
3685  return timeline;
3686},
3687    _scrollTrigger = function _scrollTrigger(animation, trigger) {
3688  return (_globals.ScrollTrigger || _missingPlugin("scrollTrigger", trigger)) && _globals.ScrollTrigger.create(trigger, animation);
3689},
3690    _attemptInitTween = function _attemptInitTween(tween, totalTime, force, suppressEvents) {
3691  _initTween(tween, totalTime);
3692
3693  if (!tween._initted) {
3694    return 1;
3695  }
3696
3697  if (!force && tween._pt && (tween._dur && tween.vars.lazy !== false || !tween._dur && tween.vars.lazy) && _lastRenderedFrame !== _ticker.frame) {
3698    _lazyTweens.push(tween);
3699
3700    tween._lazy = [totalTime, suppressEvents];
3701    return 1;
3702  }
3703},
3704    _parentPlayheadIsBeforeStart = function _parentPlayheadIsBeforeStart(_ref) {
3705  var parent = _ref.parent;
3706  return parent && parent._ts && parent._initted && !parent._lock && (parent.rawTime() < 0 || _parentPlayheadIsBeforeStart(parent));
3707},
3708    // check parent's _lock because when a timeline repeats/yoyos and does its artificial wrapping, we shouldn't force the ratio back to 0
3709_renderZeroDurationTween = function _renderZeroDurationTween(tween, totalTime, suppressEvents, force) {
3710  var prevRatio = tween.ratio,
3711      ratio = totalTime < 0 || !totalTime && (!tween._start && _parentPlayheadIsBeforeStart(tween) || (tween._ts < 0 || tween._dp._ts < 0) && tween.data !== "isFromStart" && tween.data !== "isStart") ? 0 : 1,
3712      // if the tween or its parent is reversed and the totalTime is 0, we should go to a ratio of 0.
3713  repeatDelay = tween._rDelay,
3714      tTime = 0,
3715      pt,
3716      iteration,
3717      prevIteration;
3718
3719  if (repeatDelay && tween._repeat) {
3720    // in case there's a zero-duration tween that has a repeat with a repeatDelay
3721    tTime = _clamp(0, tween._tDur, totalTime);
3722    iteration = _animationCycle(tTime, repeatDelay);
3723    prevIteration = _animationCycle(tween._tTime, repeatDelay);
3724    tween._yoyo && iteration & 1 && (ratio = 1 - ratio);
3725
3726    if (iteration !== prevIteration) {
3727      prevRatio = 1 - ratio;
3728      tween.vars.repeatRefresh && tween._initted && tween.invalidate();
3729    }
3730  }
3731
3732  if (ratio !== prevRatio || force || tween._zTime === _tinyNum || !totalTime && tween._zTime) {
3733    if (!tween._initted && _attemptInitTween(tween, totalTime, force, suppressEvents)) {
3734      // if we render the very beginning (time == 0) of a fromTo(), we must force the render (normal tweens wouldn't need to render at a time of 0 when the prevTime was also 0). This is also mandatory to make sure overwriting kicks in immediately.
3735      return;
3736    }
3737
3738    prevIteration = tween._zTime;
3739    tween._zTime = totalTime || (suppressEvents ? _tinyNum : 0); // when the playhead arrives at EXACTLY time 0 (right on top) of a zero-duration tween, we need to discern if events are suppressed so that when the playhead moves again (next time), it'll trigger the callback. If events are NOT suppressed, obviously the callback would be triggered in this render. Basically, the callback should fire either when the playhead ARRIVES or LEAVES this exact spot, not both. Imagine doing a timeline.seek(0) and there's a callback that sits at 0. Since events are suppressed on that seek() by default, nothing will fire, but when the playhead moves off of that position, the callback should fire. This behavior is what people intuitively expect.
3740
3741    suppressEvents || (suppressEvents = totalTime && !prevIteration); // if it was rendered previously at exactly 0 (_zTime) and now the playhead is moving away, DON'T fire c
vendor: 11,087 bytes, lines 3741-4034
3741allbacks otherwise they'll seem like duplicates.
3742
3743    tween.ratio = ratio;
3744    tween._from && (ratio = 1 - ratio);
3745    tween._time = 0;
3746    tween._tTime = tTime;
3747    suppressEvents || _callback(tween, "onStart");
3748    pt = tween._pt;
3749
3750    while (pt) {
3751      pt.r(ratio, pt.d);
3752      pt = pt._next;
3753    }
3754
3755    tween._startAt && totalTime < 0 && tween._startAt.render(totalTime, true, true);
3756    tween._onUpdate && !suppressEvents && _callback(tween, "onUpdate");
3757    tTime && tween._repeat && !suppressEvents && tween.parent && _callback(tween, "onRepeat");
3758
3759    if ((totalTime >= tween._tDur || totalTime < 0) && tween.ratio === ratio) {
3760      ratio && _removeFromParent(tween, 1);
3761
3762      if (!suppressEvents) {
3763        _callback(tween, ratio ? "onComplete" : "onReverseComplete", true);
3764
3765        tween._prom && tween._prom();
3766      }
3767    }
3768  } else if (!tween._zTime) {
3769    tween._zTime = totalTime;
3770  }
3771},
3772    _findNextPauseTween = function _findNextPauseTween(animation, prevTime, time) {
3773  var child;
3774
3775  if (time > prevTime) {
3776    child = animation._first;
3777
3778    while (child && child._start <= time) {
3779      if (!child._dur && child.data === "isPause" && child._start > prevTime) {
3780        return child;
3781      }
3782
3783      child = child._next;
3784    }
3785  } else {
3786    child = animation._last;
3787
3788    while (child && child._start >= time) {
3789      if (!child._dur && child.data === "isPause" && child._start < prevTime) {
3790        return child;
3791      }
3792
3793      child = child._prev;
3794    }
3795  }
3796},
3797    _setDuration = function _setDuration(animation, duration, skipUncache, leavePlayhead) {
3798  var repeat = animation._repeat,
3799      dur = _round(duration) || 0,
3800      totalProgress = animation._tTime / animation._tDur;
3801  totalProgress && !leavePlayhead && (animation._time *= dur / animation._dur);
3802  animation._dur = dur;
3803  animation._tDur = !repeat ? dur : repeat < 0 ? 1e10 : _round(dur * (repeat + 1) + animation._rDelay * repeat);
3804  totalProgress && !leavePlayhead ? _alignPlayhead(animation, animation._tTime = animation._tDur * totalProgress) : animation.parent && _setEnd(animation);
3805  skipUncache || _uncache(animation.parent, animation);
3806  return animation;
3807},
3808    _onUpdateTotalDuration = function _onUpdateTotalDuration(animation) {
3809  return animation instanceof Timeline ? _uncache(animation) : _setDuration(animation, animation._dur);
3810},
3811    _zeroPosition = {
3812  _start: 0,
3813  endTime: _emptyFunc
3814},
3815    _parsePosition = function _parsePosition(animation, position) {
3816  var labels = animation.labels,
3817      recent = animation._recent || _zeroPosition,
3818      clippedDuration = animation.duration() >= _bigNum ? recent.endTime(false) : animation._dur,
3819      //in case there's a child that infinitely repeats, users almost never intend for the insertion point of a new child to be based on a SUPER long value like that so we clip it and assume the most recently-added child's endTime should be used instead.
3820  i,
3821      offset;
3822
3823  if (_isString(position) && (isNaN(position) || position in labels)) {
3824    //if the string is a number like "1", check to see if there's a label with that name, otherwise interpret it as a number (absolute value).
3825    i = position.charAt(0);
3826
3827    if (i === "<" || i === ">") {
3828      return (i === "<" ? recent._start : recent.endTime(recent._repeat >= 0)) + (parseFloat(position.substr(1)) || 0);
3829    }
3830
3831    i = position.indexOf("=");
3832
3833    if (i < 0) {
3834      position in labels || (labels[position] = clippedDuration);
3835      return labels[position];
3836    }
3837
3838    offset = +(position.charAt(i - 1) + position.substr(i + 1));
3839    return i > 1 ? _parsePosition(animation, position.substr(0, i - 1)) + offset : clippedDuration + offset;
3840  }
3841
3842  return position == null ? clippedDuration : +position;
3843},
3844    _conditionalReturn = function _conditionalReturn(value, func) {
3845  return value || value === 0 ? func(value) : func;
3846},
3847    _clamp = function _clamp(min, max, value) {
3848  return value < min ? min : value > max ? max : value;
3849},
3850    getUnit = function getUnit(value) {
3851  if (typeof value !== "string") {
3852    return "";
3853  }
3854
3855  var v = _unitExp.exec(value);
3856
3857  return v ? value.substr(v.index + v[0].length) : "";
3858},
3859    // note: protect against padded numbers as strings, like "100.100". That shouldn't return "00" as the unit. If it's numeric, return no unit.
3860clamp = function clamp(min, max, value) {
3861  return _conditionalReturn(value, function (v) {
3862    return _clamp(min, max, v);
3863  });
3864},
3865    _slice = [].slice,
3866    _isArrayLike = function _isArrayLike(value, nonEmpty) {
3867  return value && _isObject(value) && "length" in value && (!nonEmpty && !value.length || value.length - 1 in value && _isObject(value[0])) && !value.nodeType && value !== _win;
3868},
3869    _flatten = function _flatten(ar, leaveStrings, accumulator) {
3870  if (accumulator === void 0) {
3871    accumulator = [];
3872  }
3873
3874  return ar.forEach(function (value) {
3875    var _accumulator;
3876
3877    return _isString(value) && !leaveStrings || _isArrayLike(value, 1) ? (_accumulator = accumulator).push.apply(_accumulator, toArray(value)) : accumulator.push(value);
3878  }) || accumulator;
3879},
3880    //takes any value and returns an array. If it's a string (and leaveStrings isn't true), it'll use document.querySelectorAll() and convert that to an array. It'll also accept iterables like jQuery objects.
3881toArray = function toArray(value, leaveStrings) {
3882  return _isString(value) && !leaveStrings && (_coreInitted || !_wake()) ? _slice.call(_doc.querySelectorAll(value), 0) : _isArray(value) ? _flatten(value, leaveStrings) : _isArrayLike(value) ? _slice.call(value, 0) : value ? [value] : [];
3883},
3884    shuffle = function shuffle(a) {
3885  return a.sort(function () {
3886    return .5 - Math.random();
3887  });
3888},
3889    // alternative that's a bit faster and more reliably diverse but bigger:   for (let j, v, i = a.length; i; j = Math.floor(Math.random() * i), v = a[--i], a[i] = a[j], a[j] = v); return a;
3890//for distributing values across an array. Can accept a number, a function or (most commonly) a function which can contain the following properties: {base, amount, from, ease, grid, axis, length, each}. Returns a function that expects the following parameters: index, target, array. Recognizes the following
3891distribute = function distribute(v) {
3892  if (_isFunction(v)) {
3893    return v;
3894  }
3895
3896  var vars = _isObject(v) ? v : {
3897    each: v
3898  },
3899      //n:1 is just to indicate v was a number; we leverage that later to set v according to the length we get. If a number is passed in, we treat it like the old stagger value where 0.1, for example, would mean that things would be distributed with 0.1 between each element in the array rather than a total "amount" that's chunked out among them all.
3900  ease = _parseEase(vars.ease),
3901      from = vars.from || 0,
3902      base = parseFloat(vars.base) || 0,
3903      cache = {},
3904      isDecimal = from > 0 && from < 1,
3905      ratios = isNaN(from) || isDecimal,
3906      axis = vars.axis,
3907      ratioX = from,
3908      ratioY = from;
3909
3910  if (_isString(from)) {
3911    ratioX = ratioY = {
3912      center: .5,
3913      edges: .5,
3914      end: 1
3915    }[from] || 0;
3916  } else if (!isDecimal && ratios) {
3917    ratioX = from[0];
3918    ratioY = from[1];
3919  }
3920
3921  return function (i, target, a) {
3922    var l = (a || vars).length,
3923        distances = cache[l],
3924        originX,
3925        originY,
3926        x,
3927        y,
3928        d,
3929        j,
3930        max,
3931        min,
3932        wrapAt;
3933
3934    if (!distances) {
3935      wrapAt = vars.grid === "auto" ? 0 : (vars.grid || [1, _bigNum])[1];
3936
3937      if (!wrapAt) {
3938        max = -_bigNum;
3939
3940        while (max < (max = a[wrapAt++].getBoundingClientRect().left) && wrapAt < l) {}
3941
3942        wrapAt--;
3943      }
3944
3945      distances = cache[l] = [];
3946      originX = ratios ? Math.min(wrapAt, l) * ratioX - .5 : from % wrapAt;
3947      originY = ratios ? l * ratioY / wrapAt - .5 : from / wrapAt | 0;
3948      max = 0;
3949      min = _bigNum;
3950
3951      for (j = 0; j < l; j++) {
3952        x = j % wrapAt - originX;
3953        y = originY - (j / wrapAt | 0);
3954        distances[j] = d = !axis ? _sqrt(x * x + y * y) : Math.abs(axis === "y" ? y : x);
3955        d > max && (max = d);
3956        d < min && (min = d);
3957      }
3958
3959      from === "random" && shuffle(distances);
3960      distances.max = max - min;
3961      distances.min = min;
3962      distances.v = l = (parseFloat(vars.amount) || parseFloat(vars.each) * (wrapAt > l ? l - 1 : !axis ? Math.max(wrapAt, l / wrapAt) : axis === "y" ? l / wrapAt : wrapAt) || 0) * (from === "edges" ? -1 : 1);
3963      distances.b = l < 0 ? base - l : base;
3964      distances.u = getUnit(vars.amount || vars.each) || 0; //unit
3965
3966      ease = ease && l < 0 ? _invertEase(ease) : ease;
3967    }
3968
3969    l = (distances[i] - distances.min) / distances.max || 0;
3970    return _round(distances.b + (ease ? ease(l) : l) * distances.v) + distances.u; //round in order to work around floating point errors
3971  };
3972},
3973    _roundModifier = function _roundModifier(v) {
3974  //pass in 0.1 get a function that'll round to the nearest tenth, or 5 to round to the closest 5, or 0.001 to the closest 1000th, etc.
3975  var p = v < 1 ? Math.pow(10, (v + "").length - 2) : 1; //to avoid floating point math errors (like 24 * 0.1 == 2.4000000000000004), we chop off at a specific number of decimal places (much faster than toFixed()
3976
3977  return function (raw) {
3978    var n = Math.round(parseFloat(raw) / v) * v * p;
3979    return (n - n % 1) / p + (_isNumber(raw) ? 0 : getUnit(raw)); // n - n % 1 replaces Math.floor() in order to handle negative values properly. For example, Math.floor(-150.00000000000003) is 151!
3980  };
3981},
3982    snap = function snap(snapTo, value) {
3983  var isArray = _isArray(snapTo),
3984      radius,
3985      is2D;
3986
3987  if (!isArray && _isObject(snapTo)) {
3988    radius = isArray = snapTo.radius || _bigNum;
3989
3990    if (snapTo.values) {
3991      snapTo = toArray(snapTo.values);
3992
3993      if (is2D = !_isNumber(snapTo[0])) {
3994        radius *= radius; //performance optimization so we don't have to Math.sqrt() in the loop.
3995      }
3996    } else {
3997      snapTo = _roundModifier(snapTo.increment);
3998    }
3999  }
4000
4001  return _conditionalReturn(value, !isArray ? _roundModifier(snapTo) : _isFunction(snapTo) ? function (raw) {
4002    is2D = snapTo(raw);
4003    return Math.abs(is2D - raw) <= radius ? is2D : raw;
4004  } : function (raw) {
4005    var x = parseFloat(is2D ? raw.x : raw),
4006        y = parseFloat(is2D ? raw.y : 0),
4007        min = _bigNum,
4008        closest = 0,
4009        i = snapTo.length,
4010        dx,
4011        dy;
4012
4013    while (i--) {
4014      if (is2D) {
4015        dx = snapTo[i].x - x;
4016        dy = snapTo[i].y - y;
4017        dx = dx * dx + dy * dy;
4018      } else {
4019        dx = Math.abs(snapTo[i] - x);
4020      }
4021
4022      if (dx < min) {
4023        min = dx;
4024        closest = i;
4025      }
4026    }
4027
4028    closest = !radius || min <= radius ? snapTo[closest] : raw;
4029    return is2D || closest === raw || _isNumber(raw) ? closest : closest + getUnit(raw);
4030  });
4031},
4032    random = function random(min, max, roundingIncrement, returnFunction) {
4033  return _conditionalReturn(_isArray(min) ? !max : roundingIncrement === true ? !!(roundingIncrement = 0) : !returnFunction, function () {
4034    return _isArray(min) ? min[~~(Math.random() * min.length)] : (roundingIncrement = roundingIncrement || 1e
vendor: 5,141 bytes, lines 4034-4194
4034-5) && (returnFunction = roundingIncrement < 1 ? Math.pow(10, (roundingIncrement + "").length - 2) : 1) && Math.floor(Math.round((min - roundingIncrement / 2 + Math.random() * (max - min + roundingIncrement * .99)) / roundingIncrement) * roundingIncrement * returnFunction) / returnFunction;
4035  });
4036},
4037    pipe = function pipe() {
4038  for (var _len = arguments.length, functions = new Array(_len), _key = 0; _key < _len; _key++) {
4039    functions[_key] = arguments[_key];
4040  }
4041
4042  return function (value) {
4043    return functions.reduce(function (v, f) {
4044      return f(v);
4045    }, value);
4046  };
4047},
4048    unitize = function unitize(func, unit) {
4049  return function (value) {
4050    return func(parseFloat(value)) + (unit || getUnit(value));
4051  };
4052},
4053    normalize = function normalize(min, max, value) {
4054  return mapRange(min, max, 0, 1, value);
4055},
4056    _wrapArray = function _wrapArray(a, wrapper, value) {
4057  return _conditionalReturn(value, function (index) {
4058    return a[~~wrapper(index)];
4059  });
4060},
4061    wrap = function wrap(min, max, value) {
4062  // NOTE: wrap() CANNOT be an arrow function! A very odd compiling bug causes problems (unrelated to GSAP).
4063  var range = max - min;
4064  return _isArray(min) ? _wrapArray(min, wrap(0, min.length), max) : _conditionalReturn(value, function (value) {
4065    return (range + (value - min) % range) % range + min;
4066  });
4067},
4068    wrapYoyo = function wrapYoyo(min, max, value) {
4069  var range = max - min,
4070      total = range * 2;
4071  return _isArray(min) ? _wrapArray(min, wrapYoyo(0, min.length - 1), max) : _conditionalReturn(value, function (value) {
4072    value = (total + (value - min) % total) % total || 0;
4073    return min + (value > range ? total - value : value);
4074  });
4075},
4076    _replaceRandom = function _replaceRandom(value) {
4077  //replaces all occurrences of random(...) in a string with the calculated random value. can be a range like random(-100, 100, 5) or an array like random([0, 100, 500])
4078  var prev = 0,
4079      s = "",
4080      i,
4081      nums,
4082      end,
4083      isArray;
4084
4085  while (~(i = value.indexOf("random(", prev))) {
4086    end = value.indexOf(")", i);
4087    isArray = value.charAt(i + 7) === "[";
4088    nums = value.substr(i + 7, end - i - 7).match(isArray ? _delimitedValueExp : _strictNumExp);
4089    s += value.substr(prev, i - prev) + random(isArray ? nums : +nums[0], isArray ? 0 : +nums[1], +nums[2] || 1e-5);
4090    prev = end + 1;
4091  }
4092
4093  return s + value.substr(prev, value.length - prev);
4094},
4095    mapRange = function mapRange(inMin, inMax, outMin, outMax, value) {
4096  var inRange = inMax - inMin,
4097      outRange = outMax - outMin;
4098  return _conditionalReturn(value, function (value) {
4099    return outMin + ((value - inMin) / inRange * outRange || 0);
4100  });
4101},
4102    interpolate = function interpolate(start, end, progress, mutate) {
4103  var func = isNaN(start + end) ? 0 : function (p) {
4104    return (1 - p) * start + p * end;
4105  };
4106
4107  if (!func) {
4108    var isString = _isString(start),
4109        master = {},
4110        p,
4111        i,
4112        interpolators,
4113        l,
4114        il;
4115
4116    progress === true && (mutate = 1) && (progress = null);
4117
4118    if (isString) {
4119      start = {
4120        p: start
4121      };
4122      end = {
4123        p: end
4124      };
4125    } else if (_isArray(start) && !_isArray(end)) {
4126      interpolators = [];
4127      l = start.length;
4128      il = l - 2;
4129
4130      for (i = 1; i < l; i++) {
4131        interpolators.push(interpolate(start[i - 1], start[i])); //build the interpolators up front as a performance optimization so that when the function is called many times, it can just reuse them.
4132      }
4133
4134      l--;
4135
4136      func = function func(p) {
4137        p *= l;
4138        var i = Math.min(il, ~~p);
4139        return interpolators[i](p - i);
4140      };
4141
4142      progress = end;
4143    } else if (!mutate) {
4144      start = _merge(_isArray(start) ? [] : {}, start);
4145    }
4146
4147    if (!interpolators) {
4148      for (p in end) {
4149        _addPropTween.call(master, start, p, "get", end[p]);
4150      }
4151
4152      func = function func(p) {
4153        return _renderPropTweens(p, master) || (isString ? start.p : start);
4154      };
4155    }
4156  }
4157
4158  return _conditionalReturn(progress, func);
4159},
4160    _getLabelInDirection = function _getLabelInDirection(timeline, fromTime, backward) {
4161  //used for nextLabel() and previousLabel()
4162  var labels = timeline.labels,
4163      min = _bigNum,
4164      p,
4165      distance,
4166      label;
4167
4168  for (p in labels) {
4169    distance = labels[p] - fromTime;
4170
4171    if (distance < 0 === !!backward && distance && min > (distance = Math.abs(distance))) {
4172      label = p;
4173      min = distance;
4174    }
4175  }
4176
4177  return label;
4178},
4179    _callback = function _callback(animation, type, executeLazyFirst) {
4180  var v = animation.vars,
4181      callback = v[type],
4182      params,
4183      scope;
4184
4185  if (!callback) {
4186    return;
4187  }
4188
4189  params = v[type + "Params"];
4190  scope = v.callbackScope || animation;
4191  executeLazyFirst && _lazyTweens.length && _lazyRender(); //in case rendering caused any tweens to lazy-init, we should render them because typically when a timeline finishes, users expect things to have rendered fully. Imagine an onUpdate on a timeline that reports/checks tweened values.
4192
4193  return params ? callback.apply(scope, params) : callback.call(scope);
4194},
vendor: 2,477 bytes, lines 4195-4284
4195    _interrupt = function _interrupt(animation) {
4196  _removeFromParent(animation);
4197
4198  animation.progress() < 1 && _callback(animation, "onInterrupt");
4199  return animation;
4200},
4201    _quickTween,
4202    _createPlugin = function _createPlugin(config) {
4203  config = !config.name && config["default"] || config; //UMD packaging wraps things oddly, so for example MotionPathHelper becomes {MotionPathHelper:MotionPathHelper, default:MotionPathHelper}.
4204
4205  var name = config.name,
4206      isFunc = _isFunction(config),
4207      Plugin = name && !isFunc && config.init ? function () {
4208    this._props = [];
4209  } : config,
4210      //in case someone passes in an object that's not a plugin, like CustomEase
4211  instanceDefaults = {
4212    init: _emptyFunc,
4213    render: _renderPropTweens,
4214    add: _addPropTween,
4215    kill: _killPropTweensOf,
4216    modifier: _addPluginModifier,
4217    rawVars: 0
4218  },
4219      statics = {
4220    targetTest: 0,
4221    get: 0,
4222    getSetter: _getSetter,
4223    aliases: {},
4224    register: 0
4225  };
4226
4227  _wake();
4228
4229  if (config !== Plugin) {
4230    if (_plugins[name]) {
4231      return;
4232    }
4233
4234    _setDefaults(Plugin, _setDefaults(_copyExcluding(config, instanceDefaults), statics)); //static methods
4235
4236
4237    _merge(Plugin.prototype, _merge(instanceDefaults, _copyExcluding(config, statics))); //instance methods
4238
4239
4240    _plugins[Plugin.prop = name] = Plugin;
4241
4242    if (config.targetTest) {
4243      _harnessPlugins.push(Plugin);
4244
4245      _reservedProps[name] = 1;
4246    }
4247
4248    name = (name === "css" ? "CSS" : name.charAt(0).toUpperCase() + name.substr(1)) + "Plugin"; //for the global name. "motionPath" should become MotionPathPlugin
4249  }
4250
4251  _addGlobal(name, Plugin);
4252
4253  config.register && config.register(gsap, Plugin, PropTween);
4254},
4255
4256/*
4257 * --------------------------------------------------------------------------------------
4258 * COLORS
4259 * --------------------------------------------------------------------------------------
4260 */
4261_255 = 255,
4262    _colorLookup = {
4263  aqua: [0, _255, _255],
4264  lime: [0, _255, 0],
4265  silver: [192, 192, 192],
4266  black: [0, 0, 0],
4267  maroon: [128, 0, 0],
4268  teal: [0, 128, 128],
4269  blue: [0, 0, _255],
4270  navy: [0, 0, 128],
4271  white: [_255, _255, _255],
4272  olive: [128, 128, 0],
4273  yellow: [_255, _255, 0],
4274  orange: [_255, 165, 0],
4275  gray: [128, 128, 128],
4276  purple: [128, 0, 128],
4277  green: [0, 128, 0],
4278  red: [_255, 0, 0],
4279  pink: [_255, 192, 203],
4280  cyan: [0, _255, _255],
4281  transparent: [_255, _255, _255, 0]
4282},
4283    _hue = function _hue(h, m1, m2) {
4284  h = h < 0 ? h + 1 : h > 1 ? h - 1 : h
vendor: 6,261 bytes, lines 4284-4488
4284;
4285  return (h * 6 < 1 ? m1 + (m2 - m1) * h * 6 : h < .5 ? m2 : h * 3 < 2 ? m1 + (m2 - m1) * (2 / 3 - h) * 6 : m1) * _255 + .5 | 0;
4286},
4287    splitColor = function splitColor(v, toHSL, forceAlpha) {
4288  var a = !v ? _colorLookup.black : _isNumber(v) ? [v >> 16, v >> 8 & _255, v & _255] : 0,
4289      r,
4290      g,
4291      b,
4292      h,
4293      s,
4294      l,
4295      max,
4296      min,
4297      d,
4298      wasHSL;
4299
4300  if (!a) {
4301    if (v.substr(-1) === ",") {
4302      //sometimes a trailing comma is included and we should chop it off (typically from a comma-delimited list of values like a textShadow:"2px 2px 2px blue, 5px 5px 5px rgb(255,0,0)" - in this example "blue," has a trailing comma. We could strip it out inside parseComplex() but we'd need to do it to the beginning and ending values plus it wouldn't provide protection from other potential scenarios like if the user passes in a similar value.
4303      v = v.substr(0, v.length - 1);
4304    }
4305
4306    if (_colorLookup[v]) {
4307      a = _colorLookup[v];
4308    } else if (v.charAt(0) === "#") {
4309      if (v.length < 6) {
4310        //for shorthand like #9F0 or #9F0F (could have alpha)
4311        r = v.charAt(1);
4312        g = v.charAt(2);
4313        b = v.charAt(3);
4314        v = "#" + r + r + g + g + b + b + (v.length === 5 ? v.charAt(4) + v.charAt(4) : "");
4315      }
4316
4317      if (v.length === 9) {
4318        // hex with alpha, like #fd5e53ff
4319        a = parseInt(v.substr(1, 6), 16);
4320        return [a >> 16, a >> 8 & _255, a & _255, parseInt(v.substr(7), 16) / 255];
4321      }
4322
4323      v = parseInt(v.substr(1), 16);
4324      a = [v >> 16, v >> 8 & _255, v & _255];
4325    } else if (v.substr(0, 3) === "hsl") {
4326      a = wasHSL = v.match(_strictNumExp);
4327
4328      if (!toHSL) {
4329        h = +a[0] % 360 / 360;
4330        s = +a[1] / 100;
4331        l = +a[2] / 100;
4332        g = l <= .5 ? l * (s + 1) : l + s - l * s;
4333        r = l * 2 - g;
4334        a.length > 3 && (a[3] *= 1); //cast as number
4335
4336        a[0] = _hue(h + 1 / 3, r, g);
4337        a[1] = _hue(h, r, g);
4338        a[2] = _hue(h - 1 / 3, r, g);
4339      } else if (~v.indexOf("=")) {
4340        //if relative values are found, just return the raw strings with the relative prefixes in place.
4341        a = v.match(_numExp);
4342        forceAlpha && a.length < 4 && (a[3] = 1);
4343        return a;
4344      }
4345    } else {
4346      a = v.match(_strictNumExp) || _colorLookup.transparent;
4347    }
4348
4349    a = a.map(Number);
4350  }
4351
4352  if (toHSL && !wasHSL) {
4353    r = a[0] / _255;
4354    g = a[1] / _255;
4355    b = a[2] / _255;
4356    max = Math.max(r, g, b);
4357    min = Math.min(r, g, b);
4358    l = (max + min) / 2;
4359
4360    if (max === min) {
4361      h = s = 0;
4362    } else {
4363      d = max - min;
4364      s = l > 0.5 ? d / (2 - max - min) : d / (max + min);
4365      h = max === r ? (g - b) / d + (g < b ? 6 : 0) : max === g ? (b - r) / d + 2 : (r - g) / d + 4;
4366      h *= 60;
4367    }
4368
4369    a[0] = ~~(h + .5);
4370    a[1] = ~~(s * 100 + .5);
4371    a[2] = ~~(l * 100 + .5);
4372  }
4373
4374  forceAlpha && a.length < 4 && (a[3] = 1);
4375  return a;
4376},
4377    _colorOrderData = function _colorOrderData(v) {
4378  // strips out the colors from the string, finds all the numeric slots (with units) and returns an array of those. The Array also has a "c" property which is an Array of the index values where the colors belong. This is to help work around issues where there's a mis-matched order of color/numeric data like drop-shadow(#f00 0px 1px 2px) and drop-shadow(0x 1px 2px #f00). This is basically a helper function used in _formatColors()
4379  var values = [],
4380      c = [],
4381      i = -1;
4382  v.split(_colorExp).forEach(function (v) {
4383    var a = v.match(_numWithUnitExp) || [];
4384    values.push.apply(values, a);
4385    c.push(i += a.length + 1);
4386  });
4387  values.c = c;
4388  return values;
4389},
4390    _formatColors = function _formatColors(s, toHSL, orderMatchData) {
4391  var result = "",
4392      colors = (s + result).match(_colorExp),
4393      type = toHSL ? "hsla(" : "rgba(",
4394      i = 0,
4395      c,
4396      shell,
4397      d,
4398      l;
4399
4400  if (!colors) {
4401    return s;
4402  }
4403
4404  colors = colors.map(function (color) {
4405    return (color = splitColor(color, toHSL, 1)) && type + (toHSL ? color[0] + "," + color[1] + "%," + color[2] + "%," + color[3] : color.join(",")) + ")";
4406  });
4407
4408  if (orderMatchData) {
4409    d = _colorOrderData(s);
4410    c = orderMatchData.c;
4411
4412    if (c.join(result) !== d.c.join(result)) {
4413      shell = s.replace(_colorExp, "1").split(_numWithUnitExp);
4414      l = shell.length - 1;
4415
4416      for (; i < l; i++) {
4417        result += shell[i] + (~c.indexOf(i) ? colors.shift() || type + "0,0,0,0)" : (d.length ? d : colors.length ? colors : orderMatchData).shift());
4418      }
4419    }
4420  }
4421
4422  if (!shell) {
4423    shell = s.split(_colorExp);
4424    l = shell.length - 1;
4425
4426    for (; i < l; i++) {
4427      result += shell[i] + colors[i];
4428    }
4429  }
4430
4431  return result + shell[l];
4432},
4433    _colorExp = function () {
4434  var s = "(?:\\b(?:(?:rgb|rgba|hsl|hsla)\\(.+?\\))|\\B#(?:[0-9a-f]{3,4}){1,2}\\b",
4435      //we'll dynamically build this Regular Expression to conserve file size. After building it, it will be able to find rgb(), rgba(), # (hexadecimal), and named color values like red, blue, purple, etc.,
4436  p;
4437
4438  for (p in _colorLookup) {
4439    s += "|" + p + "\\b";
4440  }
4441
4442  return new RegExp(s + ")", "gi");
4443}(),
4444    _hslExp = /hsl[a]?\(/,
4445    _colorStringFilter = function _colorStringFilter(a) {
4446  var combined = a.join(" "),
4447      toHSL;
4448  _colorExp.lastIndex = 0;
4449
4450  if (_colorExp.test(combined)) {
4451    toHSL = _hslExp.test(combined);
4452    a[1] = _formatColors(a[1], toHSL);
4453    a[0] = _formatColors(a[0], toHSL, _colorOrderData(a[1])); // make sure the order of numbers/colors match with the END value.
4454
4455    return true;
4456  }
4457},
4458
4459/*
4460 * --------------------------------------------------------------------------------------
4461 * TICKER
4462 * --------------------------------------------------------------------------------------
4463 */
4464_tickerActive,
4465    _ticker = function () {
4466  var _getTime = Date.now,
4467      _lagThreshold = 500,
4468      _adjustedLag = 33,
4469      _startTime = _getTime(),
4470      _lastUpdate = _startTime,
4471      _gap = 1000 / 240,
4472      _nextTime = _gap,
4473      _listeners = [],
4474      _id,
4475      _req,
4476      _raf,
4477      _self,
4478      _delta,
4479      _i,
4480      _tick = function _tick(v) {
4481    var elapsed = _getTime() - _lastUpdate,
4482        manual = v === true,
4483        overlap,
4484        dispatch,
4485        time,
4486        frame;
4487
4488    
vendor: 4,012 bytes, lines 4488-4607
4488elapsed > _lagThreshold && (_startTime += elapsed - _adjustedLag);
4489    _lastUpdate += elapsed;
4490    time = _lastUpdate - _startTime;
4491    overlap = time - _nextTime;
4492
4493    if (overlap > 0 || manual) {
4494      frame = ++_self.frame;
4495      _delta = time - _self.time * 1000;
4496      _self.time = time = time / 1000;
4497      _nextTime += overlap + (overlap >= _gap ? 4 : _gap - overlap);
4498      dispatch = 1;
4499    }
4500
4501    manual || (_id = _req(_tick)); //make sure the request is made before we dispatch the "tick" event so that timing is maintained. Otherwise, if processing the "tick" requires a bunch of time (like 15ms) and we're using a setTimeout() that's based on 16.7ms, it'd technically take 31.7ms between frames otherwise.
4502
4503    if (dispatch) {
4504      for (_i = 0; _i < _listeners.length; _i++) {
4505        // use _i and check _listeners.length instead of a variable because a listener could get removed during the loop, and if that happens to an element less than the current index, it'd throw things off in the loop.
4506        _listeners[_i](time, _delta, frame, v);
4507      }
4508    }
4509  };
4510
4511  _self = {
4512    time: 0,
4513    frame: 0,
4514    tick: function tick() {
4515      _tick(true);
4516    },
4517    deltaRatio: function deltaRatio(fps) {
4518      return _delta / (1000 / (fps || 60));
4519    },
4520    wake: function wake() {
4521      if (_coreReady) {
4522        if (!_coreInitted && _windowExists()) {
4523          _win = _coreInitted = window;
4524          _doc = _win.document || {};
4525          _globals.gsap = gsap;
4526          (_win.gsapVersions || (_win.gsapVersions = [])).push(gsap.version);
4527
4528          _install(_installScope || _win.GreenSockGlobals || !_win.gsap && _win || {});
4529
4530          _raf = _win.requestAnimationFrame;
4531        }
4532
4533        _id && _self.sleep();
4534
4535        _req = _raf || function (f) {
4536          return setTimeout(f, _nextTime - _self.time * 1000 + 1 | 0);
4537        };
4538
4539        _tickerActive = 1;
4540
4541        _tick(2);
4542      }
4543    },
4544    sleep: function sleep() {
4545      (_raf ? _win.cancelAnimationFrame : clearTimeout)(_id);
4546      _tickerActive = 0;
4547      _req = _emptyFunc;
4548    },
4549    lagSmoothing: function lagSmoothing(threshold, adjustedLag) {
4550      _lagThreshold = threshold || 1 / _tinyNum; //zero should be interpreted as basically unlimited
4551
4552      _adjustedLag = Math.min(adjustedLag, _lagThreshold, 0);
4553    },
4554    fps: function fps(_fps) {
4555      _gap = 1000 / (_fps || 240);
4556      _nextTime = _self.time * 1000 + _gap;
4557    },
4558    add: function add(callback) {
4559      _listeners.indexOf(callback) < 0 && _listeners.push(callback);
4560
4561      _wake();
4562    },
4563    remove: function remove(callback) {
4564      var i;
4565      ~(i = _listeners.indexOf(callback)) && _listeners.splice(i, 1) && _i >= i && _i--;
4566    },
4567    _listeners: _listeners
4568  };
4569  return _self;
4570}(),
4571    _wake = function _wake() {
4572  return !_tickerActive && _ticker.wake();
4573},
4574    //also ensures the core classes are initialized.
4575
4576/*
4577* -------------------------------------------------
4578* EASING
4579* -------------------------------------------------
4580*/
4581_easeMap = {},
4582    _customEaseExp = /^[\d.\-M][\d.\-,\s]/,
4583    _quotesExp = /["']/g,
4584    _parseObjectInString = function _parseObjectInString(value) {
4585  //takes a string like "{wiggles:10, type:anticipate})" and turns it into a real object. Notice it ends in ")" and includes the {} wrappers. This is because we only use this function for parsing ease configs and prioritized optimization rather than reusability.
4586  var obj = {},
4587      split = value.substr(1, value.length - 3).split(":"),
4588      key = split[0],
4589      i = 1,
4590      l = split.length,
4591      index,
4592      val,
4593      parsedVal;
4594
4595  for (; i < l; i++) {
4596    val = split[i];
4597    index = i !== l - 1 ? val.lastIndexOf(",") : val.length;
4598    parsedVal = val.substr(0, index);
4599    obj[key] = isNaN(parsedVal) ? parsedVal.replace(_quotesExp, "").trim() : +parsedVal;
4600    key = val.substr(index + 1).trim();
4601  }
4602
4603  return obj;
4604},
4605    _valueInParentheses = function _valueInParentheses(value) {
4606  var open = value.indexOf("(") + 1,
4607      close = value.indexOf(")"),
vendor: 5,237 bytes, lines 4608-4750
4608      nested = value.indexOf("(", open);
4609  return value.substring(open, ~nested && nested < close ? value.indexOf(")", close + 1) : close);
4610},
4611    _configEaseFromString = function _configEaseFromString(name) {
4612  //name can be a string like "elastic.out(1,0.5)", and pass in _easeMap as obj and it'll parse it out and call the actual function like _easeMap.Elastic.easeOut.config(1,0.5). It will also parse custom ease strings as long as CustomEase is loaded and registered (internally as _easeMap._CE).
4613  var split = (name + "").split("("),
4614      ease = _easeMap[split[0]];
4615  return ease && split.length > 1 && ease.config ? ease.config.apply(null, ~name.indexOf("{") ? [_parseObjectInString(split[1])] : _valueInParentheses(name).split(",").map(_numericIfPossible)) : _easeMap._CE && _customEaseExp.test(name) ? _easeMap._CE("", name) : ease;
4616},
4617    _invertEase = function _invertEase(ease) {
4618  return function (p) {
4619    return 1 - ease(1 - p);
4620  };
4621},
4622    // allow yoyoEase to be set in children and have those affected when the parent/ancestor timeline yoyos.
4623_propagateYoyoEase = function _propagateYoyoEase(timeline, isYoyo) {
4624  var child = timeline._first,
4625      ease;
4626
4627  while (child) {
4628    if (child instanceof Timeline) {
4629      _propagateYoyoEase(child, isYoyo);
4630    } else if (child.vars.yoyoEase && (!child._yoyo || !child._repeat) && child._yoyo !== isYoyo) {
4631      if (child.timeline) {
4632        _propagateYoyoEase(child.timeline, isYoyo);
4633      } else {
4634        ease = child._ease;
4635        child._ease = child._yEase;
4636        child._yEase = ease;
4637        child._yoyo = isYoyo;
4638      }
4639    }
4640
4641    child = child._next;
4642  }
4643},
4644    _parseEase = function _parseEase(ease, defaultEase) {
4645  return !ease ? defaultEase : (_isFunction(ease) ? ease : _easeMap[ease] || _configEaseFromString(ease)) || defaultEase;
4646},
4647    _insertEase = function _insertEase(names, easeIn, easeOut, easeInOut) {
4648  if (easeOut === void 0) {
4649    easeOut = function easeOut(p) {
4650      return 1 - easeIn(1 - p);
4651    };
4652  }
4653
4654  if (easeInOut === void 0) {
4655    easeInOut = function easeInOut(p) {
4656      return p < .5 ? easeIn(p * 2) / 2 : 1 - easeIn((1 - p) * 2) / 2;
4657    };
4658  }
4659
4660  var ease = {
4661    easeIn: easeIn,
4662    easeOut: easeOut,
4663    easeInOut: easeInOut
4664  },
4665      lowercaseName;
4666
4667  _forEachName(names, function (name) {
4668    _easeMap[name] = _globals[name] = ease;
4669    _easeMap[lowercaseName = name.toLowerCase()] = easeOut;
4670
4671    for (var p in ease) {
4672      _easeMap[lowercaseName + (p === "easeIn" ? ".in" : p === "easeOut" ? ".out" : ".inOut")] = _easeMap[name + "." + p] = ease[p];
4673    }
4674  });
4675
4676  return ease;
4677},
4678    _easeInOutFromOut = function _easeInOutFromOut(easeOut) {
4679  return function (p) {
4680    return p < .5 ? (1 - easeOut(1 - p * 2)) / 2 : .5 + easeOut((p - .5) * 2) / 2;
4681  };
4682},
4683    _configElastic = function _configElastic(type, amplitude, period) {
4684  var p1 = amplitude >= 1 ? amplitude : 1,
4685      //note: if amplitude is < 1, we simply adjust the period for a more natural feel. Otherwise the math doesn't work right and the curve starts at 1.
4686  p2 = (period || (type ? .3 : .45)) / (amplitude < 1 ? amplitude : 1),
4687      p3 = p2 / _2PI * (Math.asin(1 / p1) || 0),
4688      easeOut = function easeOut(p) {
4689    return p === 1 ? 1 : p1 * Math.pow(2, -10 * p) * _sin((p - p3) * p2) + 1;
4690  },
4691      ease = type === "out" ? easeOut : type === "in" ? function (p) {
4692    return 1 - easeOut(1 - p);
4693  } : _easeInOutFromOut(easeOut);
4694
4695  p2 = _2PI / p2; //precalculate to optimize
4696
4697  ease.config = function (amplitude, period) {
4698    return _configElastic(type, amplitude, period);
4699  };
4700
4701  return ease;
4702},
4703    _configBack = function _configBack(type, overshoot) {
4704  if (overshoot === void 0) {
4705    overshoot = 1.70158;
4706  }
4707
4708  var easeOut = function easeOut(p) {
4709    return p ? --p * p * ((overshoot + 1) * p + overshoot) + 1 : 0;
4710  },
4711      ease = type === "out" ? easeOut : type === "in" ? function (p) {
4712    return 1 - easeOut(1 - p);
4713  } : _easeInOutFromOut(easeOut);
4714
4715  ease.config = function (overshoot) {
4716    return _configBack(type, overshoot);
4717  };
4718
4719  return ease;
4720}; // a cheaper (kb and cpu) but more mild way to get a parameterized weighted ease by feeding in a value between -1 (easeIn) and 1 (easeOut) where 0 is linear.
4721// _weightedEase = ratio => {
4722// 	let y = 0.5 + ratio / 2;
4723// 	return p => (2 * (1 - p) * p * y + p * p);
4724// },
4725// a stronger (but more expensive kb/cpu) parameterized weighted ease that lets you feed in a value between -1 (easeIn) and 1 (easeOut) where 0 is linear.
4726// _weightedEaseStrong = ratio => {
4727// 	ratio = .5 + ratio / 2;
4728// 	let o = 1 / 3 * (ratio < .5 ? ratio : 1 - ratio),
4729// 		b = ratio - o,
4730// 		c = ratio + o;
4731// 	return p => p === 1 ? p : 3 * b * (1 - p) * (1 - p) * p + 3 * c * (1 - p) * p * p + p * p * p;
4732// };
4733
4734
4735_forEachName("Linear,Quad,Cubic,Quart,Quint,Strong", function (name, i) {
4736  var power = i < 5 ? i + 1 : i;
4737
4738  _insertEase(name + ",Power" + (power - 1), i ? function (p) {
4739    return Math.pow(p, power);
4740  } : function (p) {
4741    return p;
4742  }, function (p) {
4743    return 1 - Math.pow(1 - p, power);
4744  }, function (p) {
4745    return p < .5 ? Math.pow(p * 2, power) / 2 : 1 - Math.pow((1 - p) * 2, power) / 2;
4746  });
4747});
4748
4749_easeMap.Linear.easeNone = _easeMap.none = _easeMap.Linear.easeIn;
4750
vendor: 4,245 bytes, lines 4751-4882
4751_insertEase("Elastic", _configElastic("in"), _configElastic("out"), _configElastic());
4752
4753(function (n, c) {
4754  var n1 = 1 / c,
4755      n2 = 2 * n1,
4756      n3 = 2.5 * n1,
4757      easeOut = function easeOut(p) {
4758    return p < n1 ? n * p * p : p < n2 ? n * Math.pow(p - 1.5 / c, 2) + .75 : p < n3 ? n * (p -= 2.25 / c) * p + .9375 : n * Math.pow(p - 2.625 / c, 2) + .984375;
4759  };
4760
4761  _insertEase("Bounce", function (p) {
4762    return 1 - easeOut(1 - p);
4763  }, easeOut);
4764})(7.5625, 2.75);
4765
4766_insertEase("Expo", function (p) {
4767  return p ? Math.pow(2, 10 * (p - 1)) : 0;
4768});
4769
4770_insertEase("Circ", function (p) {
4771  return -(_sqrt(1 - p * p) - 1);
4772});
4773
4774_insertEase("Sine", function (p) {
4775  return p === 1 ? 1 : -_cos(p * _HALF_PI) + 1;
4776});
4777
4778_insertEase("Back", _configBack("in"), _configBack("out"), _configBack());
4779
4780_easeMap.SteppedEase = _easeMap.steps = _globals.SteppedEase = {
4781  config: function config(steps, immediateStart) {
4782    if (steps === void 0) {
4783      steps = 1;
4784    }
4785
4786    var p1 = 1 / steps,
4787        p2 = steps + (immediateStart ? 0 : 1),
4788        p3 = immediateStart ? 1 : 0,
4789        max = 1 - _tinyNum;
4790    return function (p) {
4791      return ((p2 * _clamp(0, max, p) | 0) + p3) * p1;
4792    };
4793  }
4794};
4795_defaults.ease = _easeMap["quad.out"];
4796
4797_forEachName("onComplete,onUpdate,onStart,onRepeat,onReverseComplete,onInterrupt", function (name) {
4798  return _callbackNames += name + "," + name + "Params,";
4799});
4800/*
4801 * --------------------------------------------------------------------------------------
4802 * CACHE
4803 * --------------------------------------------------------------------------------------
4804 */
4805
4806
4807var GSCache = function GSCache(target, harness) {
4808  this.id = _gsID++;
4809  target._gsap = this;
4810  this.target = target;
4811  this.harness = harness;
4812  this.get = harness ? harness.get : _getProperty;
4813  this.set = harness ? harness.getSetter : _getSetter;
4814};
4815/*
4816 * --------------------------------------------------------------------------------------
4817 * ANIMATION
4818 * --------------------------------------------------------------------------------------
4819 */
4820
4821var Animation = /*#__PURE__*/function () {
4822  function Animation(vars, time) {
4823    var parent = vars.parent || _globalTimeline;
4824    this.vars = vars;
4825    this._delay = +vars.delay || 0;
4826
4827    if (this._repeat = vars.repeat === Infinity ? -2 : vars.repeat || 0) {
4828      // TODO: repeat: Infinity on a timeline's children must flag that timeline internally and affect its totalDuration, otherwise it'll stop in the negative direction when reaching the start.
4829      this._rDelay = vars.repeatDelay || 0;
4830      this._yoyo = !!vars.yoyo || !!vars.yoyoEase;
4831    }
4832
4833    this._ts = 1;
4834
4835    _setDuration(this, +vars.duration, 1, 1);
4836
4837    this.data = vars.data;
4838    _tickerActive || _ticker.wake();
4839    parent && _addToTimeline(parent, this, time || time === 0 ? time : parent._time, 1);
4840    vars.reversed && this.reverse();
4841    vars.paused && this.paused(true);
4842  }
4843
4844  var _proto = Animation.prototype;
4845
4846  _proto.delay = function delay(value) {
4847    if (value || value === 0) {
4848      this.parent && this.parent.smoothChildTiming && this.startTime(this._start + value - this._delay);
4849      this._delay = value;
4850      return this;
4851    }
4852
4853    return this._delay;
4854  };
4855
4856  _proto.duration = function duration(value) {
4857    return arguments.length ? this.totalDuration(this._repeat > 0 ? value + (value + this._rDelay) * this._repeat : value) : this.totalDuration() && this._dur;
4858  };
4859
4860  _proto.totalDuration = function totalDuration(value) {
4861    if (!arguments.length) {
4862      return this._tDur;
4863    }
4864
4865    this._dirty = 0;
4866    return _setDuration(this, this._repeat < 0 ? value : (value - this._repeat * this._rDelay) / (this._repeat + 1));
4867  };
4868
4869  _proto.totalTime = function totalTime(_totalTime, suppressEvents) {
4870    _wake();
4871
4872    if (!arguments.length) {
4873      return this._tTime;
4874    }
4875
4876    var parent = this._dp;
4877
4878    if (parent && parent.smoothChildTiming && this._ts) {
4879      _alignPlayhead(this, _totalTime);
4880
4881      !parent._dp || parent.parent || _postAddChecks(parent, this); // edge case: if this is a child of a timeline that already completed, for example, we must re-activate the parent.
4882      //in case any of the ancestor timelines had completed but should now be enabled, we should reset the
vendor: 5,599 bytes, lines 4882-4967
4882ir totalTime() which will also ensure that they're lined up properly and enabled. Skip for animations that are on the root (wasteful). Example: a TimelineLite.exportRoot() is performed when there's a paused tween on the root, the export will not complete until that tween is unpaused, but imagine a child gets restarted later, after all [unpaused] tweens have completed. The start of that child would get pushed out, but one of the ancestors may have completed.
4883
4884      while (parent.parent) {
4885        if (parent.parent._time !== parent._start + (parent._ts >= 0 ? parent._tTime / parent._ts : (parent.totalDuration() - parent._tTime) / -parent._ts)) {
4886          parent.totalTime(parent._tTime, true);
4887        }
4888
4889        parent = parent.parent;
4890      }
4891
4892      if (!this.parent && this._dp.autoRemoveChildren && (this._ts > 0 && _totalTime < this._tDur || this._ts < 0 && _totalTime > 0 || !this._tDur && !_totalTime)) {
4893        //if the animation doesn't have a parent, put it back into its last parent (recorded as _dp for exactly cases like this). Limit to parents with autoRemoveChildren (like globalTimeline) so that if the user manually removes an animation from a timeline and then alters its playhead, it doesn't get added back in.
4894        _addToTimeline(this._dp, this, this._start - this._delay);
4895      }
4896    }
4897
4898    if (this._tTime !== _totalTime || !this._dur && !suppressEvents || this._initted && Math.abs(this._zTime) === _tinyNum || !_totalTime && !this._initted && (this.add || this._ptLookup)) {
4899      // check for _ptLookup on a Tween instance to ensure it has actually finished being instantiated, otherwise if this.reverse() gets called in the Animation constructor, it could trigger a render() here even though the _targets weren't populated, thus when _init() is called there won't be any PropTweens (it'll act like the tween is non-functional)
4900      this._ts || (this._pTime = _totalTime); // otherwise, if an animation is paused, then the playhead is moved back to zero, then resumed, it'd revert back to the original time at the pause
4901      //if (!this._lock) { // avoid endless recursion (not sure we need this yet or if it's worth the performance hit)
4902      //   this._lock = 1;
4903
4904      _lazySafeRender(this, _totalTime, suppressEvents); //   this._lock = 0;
4905      //}
4906
4907    }
4908
4909    return this;
4910  };
4911
4912  _proto.time = function time(value, suppressEvents) {
4913    return arguments.length ? this.totalTime(Math.min(this.totalDuration(), value + _elapsedCycleDuration(this)) % this._dur || (value ? this._dur : 0), suppressEvents) : this._time; // note: if the modulus results in 0, the playhead could be exactly at the end or the beginning, and we always defer to the END with a non-zero value, otherwise if you set the time() to the very end (duration()), it would render at the START!
4914  };
4915
4916  _proto.totalProgress = function totalProgress(value, suppressEvents) {
4917    return arguments.length ? this.totalTime(this.totalDuration() * value, suppressEvents) : this.totalDuration() ? Math.min(1, this._tTime / this._tDur) : this.ratio;
4918  };
4919
4920  _proto.progress = function progress(value, suppressEvents) {
4921    return arguments.length ? this.totalTime(this.duration() * (this._yoyo && !(this.iteration() & 1) ? 1 - value : value) + _elapsedCycleDuration(this), suppressEvents) : this.duration() ? Math.min(1, this._time / this._dur) : this.ratio;
4922  };
4923
4924  _proto.iteration = function iteration(value, suppressEvents) {
4925    var cycleDuration = this.duration() + this._rDelay;
4926
4927    return arguments.length ? this.totalTime(this._time + (value - 1) * cycleDuration, suppressEvents) : this._repeat ? _animationCycle(this._tTime, cycleDuration) + 1 : 1;
4928  } // potential future addition:
4929  // isPlayingBackwards() {
4930  // 	let animation = this,
4931  // 		orientation = 1; // 1 = forward, -1 = backward
4932  // 	while (animation) {
4933  // 		orientation *= animation.reversed() || (animation.repeat() && !(animation.iteration() & 1)) ? -1 : 1;
4934  // 		animation = animation.parent;
4935  // 	}
4936  // 	return orientation < 0;
4937  // }
4938  ;
4939
4940  _proto.timeScale = function timeScale(value) {
4941    if (!arguments.length) {
4942      return this._rts === -_tinyNum ? 0 : this._rts; // recorded timeScale. Special case: if someone calls reverse() on an animation with timeScale of 0, we assign it -_tinyNum to remember it's reversed.
4943    }
4944
4945    if (this._rts === value) {
4946      return this;
4947    }
4948
4949    var tTime = this.parent && this._ts ? _parentToChildTotalTime(this.parent._time, this) : this._tTime; // make sure to do the parentToChildTotalTime() BEFORE setting the new _ts because the old one must be used in that calculation.
4950    // prioritize rendering where the parent's playhead lines up instead of this._tTime because there could be a tween that's animating another tween's timeScale in the same rendering loop (same parent), thus if the timeScale tween renders first, it would alter _start BEFORE _tTime was set on that tick (in the rendering loop), effectively freezing it until the timeScale tween finishes.
4951
4952    this._rts = +value || 0;
4953    this._ts = this._ps || value === -_tinyNum ? 0 : this._rts; // _ts is the functional timeScale which would be 0 if the animation is paused.
4954
4955    return _recacheAncestors(this.totalTime(_clamp(-this._delay, this._tDur, tTime), true));
4956  };
4957
4958  _proto.paused = function paused(value) {
4959    if (!arguments.length) {
4960      return this._ps;
4961    }
4962
4963    if (this._ps !== value) {
4964      this._ps = value;
4965
4966      if (value) {
4967        this._pTime = this._tTime || Math.max(-this._delay, this.rawTime()); // if the pause occurs during the delay phase, make sure that's factored 
vendor: 4,401 bytes, lines 4967-5078
4967in when resuming.
4968
4969        this._ts = this._act = 0; // _ts is the functional timeScale, so a paused tween would effectively have a timeScale of 0. We record the "real" timeScale as _rts (recorded time scale)
4970      } else {
4971        _wake();
4972
4973        this._ts = this._rts; //only defer to _pTime (pauseTime) if tTime is zero. Remember, someone could pause() an animation, then scrub the playhead and resume(). If the parent doesn't have smoothChildTiming, we render at the rawTime() because the startTime won't get updated.
4974
4975        this.totalTime(this.parent && !this.parent.smoothChildTiming ? this.rawTime() : this._tTime || this._pTime, this.progress() === 1 && (this._tTime -= _tinyNum) && Math.abs(this._zTime) !== _tinyNum); // edge case: animation.progress(1).pause().play() wouldn't render again because the playhead is already at the end, but the call to totalTime() below will add it back to its parent...and not remove it again (since removing only happens upon rendering at a new time). Offsetting the _tTime slightly is done simply to cause the final render in totalTime() that'll pop it off its timeline (if autoRemoveChildren is true, of course). Check to make sure _zTime isn't -_tinyNum to avoid an edge case where the playhead is pushed to the end but INSIDE a tween/callback, the timeline itself is paused thus halting rendering and leaving a few unrendered. When resuming, it wouldn't render those otherwise.
4976      }
4977    }
4978
4979    return this;
4980  };
4981
4982  _proto.startTime = function startTime(value) {
4983    if (arguments.length) {
4984      this._start = value;
4985      var parent = this.parent || this._dp;
4986      parent && (parent._sort || !this.parent) && _addToTimeline(parent, this, value - this._delay);
4987      return this;
4988    }
4989
4990    return this._start;
4991  };
4992
4993  _proto.endTime = function endTime(includeRepeats) {
4994    return this._start + (_isNotFalse(includeRepeats) ? this.totalDuration() : this.duration()) / Math.abs(this._ts);
4995  };
4996
4997  _proto.rawTime = function rawTime(wrapRepeats) {
4998    var parent = this.parent || this._dp; // _dp = detatched parent
4999
5000    return !parent ? this._tTime : wrapRepeats && (!this._ts || this._repeat && this._time && this.totalProgress() < 1) ? this._tTime % (this._dur + this._rDelay) : !this._ts ? this._tTime : _parentToChildTotalTime(parent.rawTime(wrapRepeats), this);
5001  };
5002
5003  _proto.globalTime = function globalTime(rawTime) {
5004    var animation = this,
5005        time = arguments.length ? rawTime : animation.rawTime();
5006
5007    while (animation) {
5008      time = animation._start + time / (animation._ts || 1);
5009      animation = animation._dp;
5010    }
5011
5012    return time;
5013  };
5014
5015  _proto.repeat = function repeat(value) {
5016    if (arguments.length) {
5017      this._repeat = value === Infinity ? -2 : value;
5018      return _onUpdateTotalDuration(this);
5019    }
5020
5021    return this._repeat === -2 ? Infinity : this._repeat;
5022  };
5023
5024  _proto.repeatDelay = function repeatDelay(value) {
5025    if (arguments.length) {
5026      this._rDelay = value;
5027      return _onUpdateTotalDuration(this);
5028    }
5029
5030    return this._rDelay;
5031  };
5032
5033  _proto.yoyo = function yoyo(value) {
5034    if (arguments.length) {
5035      this._yoyo = value;
5036      return this;
5037    }
5038
5039    return this._yoyo;
5040  };
5041
5042  _proto.seek = function seek(position, suppressEvents) {
5043    return this.totalTime(_parsePosition(this, position), _isNotFalse(suppressEvents));
5044  };
5045
5046  _proto.restart = function restart(includeDelay, suppressEvents) {
5047    return this.play().totalTime(includeDelay ? -this._delay : 0, _isNotFalse(suppressEvents));
5048  };
5049
5050  _proto.play = function play(from, suppressEvents) {
5051    from != null && this.seek(from, suppressEvents);
5052    return this.reversed(false).paused(false);
5053  };
5054
5055  _proto.reverse = function reverse(from, suppressEvents) {
5056    from != null && this.seek(from || this.totalDuration(), suppressEvents);
5057    return this.reversed(true).paused(false);
5058  };
5059
5060  _proto.pause = function pause(atTime, suppressEvents) {
5061    atTime != null && this.seek(atTime, suppressEvents);
5062    return this.paused(true);
5063  };
5064
5065  _proto.resume = function resume() {
5066    return this.paused(false);
5067  };
5068
5069  _proto.reversed = function reversed(value) {
5070    if (arguments.length) {
5071      !!value !== this.reversed() && this.timeScale(-this._rts || (value ? -_tinyNum : 0)); // in case timeScale is zero, reversing would have no effect so we use _tinyNum.
5072
5073      return this;
5074    }
5075
5076    return this._rts < 0;
5077  };
5078
vendor: 9,032 bytes, lines 5079-5310
5079  _proto.invalidate = function invalidate() {
5080    this._initted = this._act = 0;
5081    this._zTime = -_tinyNum;
5082    return this;
5083  };
5084
5085  _proto.isActive = function isActive() {
5086    var parent = this.parent || this._dp,
5087        start = this._start,
5088        rawTime;
5089    return !!(!parent || this._ts && this._initted && parent.isActive() && (rawTime = parent.rawTime(true)) >= start && rawTime < this.endTime(true) - _tinyNum);
5090  };
5091
5092  _proto.eventCallback = function eventCallback(type, callback, params) {
5093    var vars = this.vars;
5094
5095    if (arguments.length > 1) {
5096      if (!callback) {
5097        delete vars[type];
5098      } else {
5099        vars[type] = callback;
5100        params && (vars[type + "Params"] = params);
5101        type === "onUpdate" && (this._onUpdate = callback);
5102      }
5103
5104      return this;
5105    }
5106
5107    return vars[type];
5108  };
5109
5110  _proto.then = function then(onFulfilled) {
5111    var self = this;
5112    return new Promise(function (resolve) {
5113      var f = _isFunction(onFulfilled) ? onFulfilled : _passThrough,
5114          _resolve = function _resolve() {
5115        var _then = self.then;
5116        self.then = null; // temporarily null the then() method to avoid an infinite loop (see https://github.com/greensock/GSAP/issues/322)
5117
5118        _isFunction(f) && (f = f(self)) && (f.then || f === self) && (self.then = _then);
5119        resolve(f);
5120        self.then = _then;
5121      };
5122
5123      if (self._initted && self.totalProgress() === 1 && self._ts >= 0 || !self._tTime && self._ts < 0) {
5124        _resolve();
5125      } else {
5126        self._prom = _resolve;
5127      }
5128    });
5129  };
5130
5131  _proto.kill = function kill() {
5132    _interrupt(this);
5133  };
5134
5135  return Animation;
5136}();
5137
5138_setDefaults(Animation.prototype, {
5139  _time: 0,
5140  _start: 0,
5141  _end: 0,
5142  _tTime: 0,
5143  _tDur: 0,
5144  _dirty: 0,
5145  _repeat: 0,
5146  _yoyo: false,
5147  parent: null,
5148  _initted: false,
5149  _rDelay: 0,
5150  _ts: 1,
5151  _dp: 0,
5152  ratio: 0,
5153  _zTime: -_tinyNum,
5154  _prom: 0,
5155  _ps: false,
5156  _rts: 1
5157});
5158/*
5159 * -------------------------------------------------
5160 * TIMELINE
5161 * -------------------------------------------------
5162 */
5163
5164
5165var Timeline = /*#__PURE__*/function (_Animation) {
5166  _inheritsLoose(Timeline, _Animation);
5167
5168  function Timeline(vars, time) {
5169    var _this;
5170
5171    if (vars === void 0) {
5172      vars = {};
5173    }
5174
5175    _this = _Animation.call(this, vars, time) || this;
5176    _this.labels = {};
5177    _this.smoothChildTiming = !!vars.smoothChildTiming;
5178    _this.autoRemoveChildren = !!vars.autoRemoveChildren;
5179    _this._sort = _isNotFalse(vars.sortChildren);
5180    _this.parent && _postAddChecks(_this.parent, _assertThisInitialized(_this));
5181    vars.scrollTrigger && _scrollTrigger(_assertThisInitialized(_this), vars.scrollTrigger);
5182    return _this;
5183  }
5184
5185  var _proto2 = Timeline.prototype;
5186
5187  _proto2.to = function to(targets, vars, position) {
5188    new Tween(targets, _parseVars(arguments, 0, this), _parsePosition(this, _isNumber(vars) ? arguments[3] : position));
5189    return this;
5190  };
5191
5192  _proto2.from = function from(targets, vars, position) {
5193    new Tween(targets, _parseVars(arguments, 1, this), _parsePosition(this, _isNumber(vars) ? arguments[3] : position));
5194    return this;
5195  };
5196
5197  _proto2.fromTo = function fromTo(targets, fromVars, toVars, position) {
5198    new Tween(targets, _parseVars(arguments, 2, this), _parsePosition(this, _isNumber(fromVars) ? arguments[4] : position));
5199    return this;
5200  };
5201
5202  _proto2.set = function set(targets, vars, position) {
5203    vars.duration = 0;
5204    vars.parent = this;
5205    _inheritDefaults(vars).repeatDelay || (vars.repeat = 0);
5206    vars.immediateRender = !!vars.immediateRender;
5207    new Tween(targets, vars, _parsePosition(this, position), 1);
5208    return this;
5209  };
5210
5211  _proto2.call = function call(callback, params, position) {
5212    return _addToTimeline(this, Tween.delayedCall(0, callback, params), _parsePosition(this, position));
5213  } //ONLY for backward compatibility! Maybe delete?
5214  ;
5215
5216  _proto2.staggerTo = function staggerTo(targets, duration, vars, stagger, position, onCompleteAll, onCompleteAllParams) {
5217    vars.duration = duration;
5218    vars.stagger = vars.stagger || stagger;
5219    vars.onComplete = onCompleteAll;
5220    vars.onCompleteParams = onCompleteAllParams;
5221    vars.parent = this;
5222    new Tween(targets, vars, _parsePosition(this, position));
5223    return this;
5224  };
5225
5226  _proto2.staggerFrom = function staggerFrom(targets, duration, vars, stagger, position, onCompleteAll, onCompleteAllParams) {
5227    vars.runBackwards = 1;
5228    _inheritDefaults(vars).immediateRender = _isNotFalse(vars.immediateRender);
5229    return this.staggerTo(targets, duration, vars, stagger, position, onCompleteAll, onCompleteAllParams);
5230  };
5231
5232  _proto2.staggerFromTo = function staggerFromTo(targets, duration, fromVars, toVars, stagger, position, onCompleteAll, onCompleteAllParams) {
5233    toVars.startAt = fromVars;
5234    _inheritDefaults(toVars).immediateRender = _isNotFalse(toVars.immediateRender);
5235    return this.staggerTo(targets, duration, toVars, stagger, position, onCompleteAll, onCompleteAllParams);
5236  };
5237
5238  _proto2.render = function render(totalTime, suppressEvents, force) {
5239    var prevTime = this._time,
5240        tDur = this._dirty ? this.totalDuration() : this._tDur,
5241        dur = this._dur,
5242        tTime = this !== _globalTimeline && totalTime > tDur - _tinyNum && totalTime >= 0 ? tDur : totalTime < _tinyNum ? 0 : totalTime,
5243        crossingStart = this._zTime < 0 !== totalTime < 0 && (this._initted || !dur),
5244        time,
5245        child,
5246        next,
5247        iteration,
5248        cycleDuration,
5249        prevPaused,
5250        pauseTween,
5251        timeScale,
5252        prevStart,
5253        prevIteration,
5254        yoyo,
5255        isYoyo;
5256
5257    if (tTime !== this._tTime || force || crossingStart) {
5258      if (prevTime !== this._time && dur) {
5259        //if totalDuration() finds a child with a negative startTime and smoothChildTiming is true, things get shifted around internally so we need to adjust the time accordingly. For example, if a tween starts at -30 we must shift EVERYTHING forward 30 seconds and move this timeline's startTime backward by 30 seconds so that things align with the playhead (no jump).
5260        tTime += this._time - prevTime;
5261        totalTime += this._time - prevTime;
5262      }
5263
5264      time = tTime;
5265      prevStart = this._start;
5266      timeScale = this._ts;
5267      prevPaused = !timeScale;
5268
5269      if (crossingStart) {
5270        dur || (prevTime = this._zTime); //when the playhead arrives at EXACTLY time 0 (right on top) of a zero-duration timeline, we need to discern if events are suppressed so that when the playhead moves again (next time), it'll trigger the callback. If events are NOT suppressed, obviously the callback would be triggered in this render. Basically, the callback should fire either when the playhead ARRIVES or LEAVES this exact spot, not both. Imagine doing a timeline.seek(0) and there's a callback that sits at 0. Since events are suppressed on that seek() by default, nothing will fire, but when the playhead moves off of that position, the callback should fire. This behavior is what people intuitively expect.
5271
5272        (totalTime || !suppressEvents) && (this._zTime = totalTime);
5273      }
5274
5275      if (this._repeat) {
5276        //adjust the time for repeats and yoyos
5277        yoyo = this._yoyo;
5278        cycleDuration = dur + this._rDelay;
5279
5280        if (this._repeat < -1 && totalTime < 0) {
5281          return this.totalTime(cycleDuration * 100 + totalTime, suppressEvents, force);
5282        }
5283
5284        time = _round(tTime % cycleDuration); //round to avoid floating point errors. (4 % 0.8 should be 0 but some browsers report it as 0.79999999!)
5285
5286        if (tTime === tDur) {
5287          // the tDur === tTime is for edge cases where there's a lengthy decimal on the duration and it may reach the very end but the time is rendered as not-quite-there (remember, tDur is rounded to 4 decimals whereas dur isn't)
5288          iteration = this._repeat;
5289          time = dur;
5290        } else {
5291          iteration = ~~(tTime / cycleDuration);
5292
5293          if (iteration && iteration === tTime / cycleDuration) {
5294            time = dur;
5295            iteration--;
5296          }
5297
5298          time > dur && (time = dur);
5299        }
5300
5301        prevIteration = _animationCycle(this._tTime, cycleDuration);
5302        !prevTime && this._tTime && prevIteration !== iteration && (prevIteration = iteration); // edge case - if someone does addPause() at the very beginning of a repeating timeline, that pause is technically at the same spot as the end which causes this._time to get set to 0 when the totalTime would normally place the playhead at the end. See https://greensock.com/forums/topic/23823-closing-nav-animation-not-working-on-ie-and-iphone-6-maybe-other-older-browser/?tab=comments#comment-113005
5303
5304        if (yoyo && iteration & 1) {
5305          time = dur - time;
5306          isYoyo = 1;
5307        }
5308        /*
5309        make sure children at the end/beginning of the timeline are rendered properly. If, for example,
5310        a 3-second long timeline rendered at 2.9 seconds previously, and now renders at 3.2 seconds (which
5311        would get translated to 2.8 seconds if the timeline yoyos or 0.2 seconds if it just repeats), there
5312        could be a callback or a short tween that's at 2.95 or 3 seconds in which wouldn't render. So
5313        we need to push the timeline to the end (and/or beginning depending on its yoyo value). Also we must
5314        ensure that zero-duration tweens at the very beginning or end of the Timeline work.
5315        */
5316
5317
5318        if (iteration !== prevIteration && !this._lock) {
5319          var rewinding = yoyo && prevIteration & 1,
5320              doesWrap = rewinding === (yoyo && iteration & 1);
5321          iteration < prevIteration && (rewinding = !rewinding);
5322          prevTime = rewinding ? 0 : dur;
5323          this._lock = 1;
5324          this.render(prevTime || (isYoyo ? 0 : _round(iteration * cycleDuration)), suppressEvents, !dur)._lock = 0;
5325          !suppressEvents && this.parent && _callback(this, "onRepeat");
5326          this.vars.repeatRefresh && !isYoyo && (this.invalidate()._lock = 1);
5327
5328          if (prevTime !== this._time || prevPaused !== !this._ts) {
5329            return this;
5330          }
5331
5332          dur = this._dur; // in case the duration changed in the onRepeat
5333
5334          tDur = this._tDur;
5335
5336          if (doesWrap) {
5337            this._lock = 2;
5338            prevTime = rewinding ? dur : -0.0001;
5339            this.render(prevTime, true);
5340            this.vars.repeatRefresh && !isYoyo && this.invalidate();
5341          }
5342
5343          this._lock = 0;
5344
5345          if (!this._ts && !prevPaused) {
5346            return this;
5347          } //in order for yoyoEase to work properly when there's a stagger, we must swap out the ease in each sub-tween.
5348
5349
5350          _propagateYoyoEase(this, isYoyo);
5351        }
5352      }
5353
5354      if (this._hasPause && !this._forcing && this._lock < 2) {
5355        pauseTween = _findNextPauseTween(this, _round(prevTime), _round(time));
5356
5357        if (pauseTween) {
5358          tTime -= time - (time = pauseTween._start);
5359        }
5360      }
5361
5362      this._tTime = tTime;
5363      this._time = time;
5364      this._act = !timeScale; //as long as it's not paused, force it to be active so that if the user renders independent of the parent timeline, it'll be forced to re-render on the next tick.
5365
5366      if (!this._initted) {
5367        this._onUpdate = this.vars.onUpdate;
5368        this._initted = 1;
5369        this._zTime = totalTime;
5370        prevTime = 0; // upon init, the playhead should always go forward;
5370 someone could invalidate() a completed timeline and then if they restart(), that would make child tweens render in reverse order which could lock in the wrong starting values if they build on each other, like tl.to(obj, {x: 100}).to(obj, {x: 0}).
5371      }
5372
5373      !prevTime && (time || !dur && totalTime >= 0) && !suppressEvents && _callback(this, "onStart");
5374
5375      if (time >= prevTime && totalTime >= 0) {
5376        child = this._first;
5377
5378        while (child) {
5379          next = child._next;
5380
5381          if ((child._act || time >= child._start) && child._ts && pauseTween !== child) {
5382            if (child.parent !== this) {
5383              // an extreme edge case - the child's render could do something like kill() the "next" one in the linked list, or reparent it. In that case we must re-initiate the whole render to be safe.
5384              return this.render(totalTime, suppressEvents, force);
5385            }
5386
5387            child.render(child._ts > 0 ? (time - child._start) * child._ts : (child._dirty ? child.totalDuration() : child._tDur) + (time - child._start) * child._ts, suppressEvents, force);
5388
5389            if (time !== this._time || !this._ts && !prevPaused) {
5390              //in case a tween pauses or seeks the timeline when rendering, like inside of an onUpdate/onComplete
5391              pauseTween = 0;
5392              next && (tTime += this._zTime = -_tinyNum); // it didn't finish rendering, so flag zTime as negative so that so that the next time render() is called it'll be forced (to render any remaining children)
5393
5394              break;
5395            }
5396          }
5397
5398          child = next;
5399        }
5400      } else {
5401        child = this._last;
5402        var adjustedTime = totalTime < 0 ? totalTime : time; //when the playhead goes backward beyond the start of this timeline, we must pass that information down to the child animations so that zero-duration tweens know whether to render their starting or ending values.
5403
5404        while (child) {
5405          next = child._prev;
5406
5407          if ((child._act || adjustedTime <= child._end) && child._ts && pauseTween !== child) {
5408            if (child.parent !== this) {
5409              // an extreme edge case - the child's render could do something like kill() the "next" one in the linked list, or reparent it. In that case we must re-initiate the whole render to be safe.
5410              return this.render(totalTime, suppressEvents, force);
5411            }
5412
5413            child.render(child._ts > 0 ? (adjustedTime - child._start) * child._ts : (child._dirty ? child.totalDuration() : child._tDur) + (adjustedTime - child._start) * child._ts, suppressEvents, force);
5414
5415            if (time !== this._time || !this._ts && !prevPaused) {
5416              //in case a tween pauses or seeks the timeline when rendering, like inside of an onUpdate/onComplete
5417              pauseTween = 0;
5418              next && (tTime += this._zTime = adjustedTime ? -_tinyNum : _tinyNum); // it didn't finish rendering, so adjust zTime so that so that the next time render() is called it'll be forced (to render any remaining children)
5419
5420              break;
5421            }
5422          }
5423
5424          child = next;
5425        }
5426      }
5427
5428      if (pauseTween && !suppressEvents) {
5429        this.pause();
5430        pauseTween.render(time >= prevTime ? 0 : -_tinyNum)._zTime = time >= prevTime ? 1 : -1;
5431
5432        if (this._ts) {
5433          //the callback resumed playback! So since we may have held back the playhead due to where the pause is positioned, go ahead and jump to where it's SUPPOSED to be (if no pause happened).
5434          this._start = prevStart; //if the pause was at an earlier time and the user resumed in the callback, it could reposition the timeline (changing its startTime), throwing things off slightly, so we make sure the _start doesn't shift.
5435
5436          _setEnd(this);
5437
5438          return this.render(totalTime, suppressEvents, force);
5439        }
5440      }
5441
vendor: 17,787 bytes, lines 5442-5987
5442      this._onUpdate && !suppressEvents && _callback(this, "onUpdate", true);
5443      if (tTime === tDur && tDur >= this.totalDuration() || !tTime && prevTime) if (prevStart === this._start || Math.abs(timeScale) !== Math.abs(this._ts)) if (!this._lock) {
5444        (totalTime || !dur) && (tTime === tDur && this._ts > 0 || !tTime && this._ts < 0) && _removeFromParent(this, 1); // don't remove if the timeline is reversed and the playhead isn't at 0, otherwise tl.progress(1).reverse() won't work. Only remove if the playhead is at the end and timeScale is positive, or if the playhead is at 0 and the timeScale is negative.
5445
5446        if (!suppressEvents && !(totalTime < 0 && !prevTime) && (tTime || prevTime)) {
5447          _callback(this, tTime === tDur ? "onComplete" : "onReverseComplete", true);
5448
5449          this._prom && !(tTime < tDur && this.timeScale() > 0) && this._prom();
5450        }
5451      }
5452    }
5453
5454    return this;
5455  };
5456
5457  _proto2.add = function add(child, position) {
5458    var _this2 = this;
5459
5460    _isNumber(position) || (position = _parsePosition(this, position));
5461
5462    if (!(child instanceof Animation)) {
5463      if (_isArray(child)) {
5464        child.forEach(function (obj) {
5465          return _this2.add(obj, position);
5466        });
5467        return this;
5468      }
5469
5470      if (_isString(child)) {
5471        return this.addLabel(child, position);
5472      }
5473
5474      if (_isFunction(child)) {
5475        child = Tween.delayedCall(0, child);
5476      } else {
5477        return this;
5478      }
5479    }
5480
5481    return this !== child ? _addToTimeline(this, child, position) : this; //don't allow a timeline to be added to itself as a child!
5482  };
5483
5484  _proto2.getChildren = function getChildren(nested, tweens, timelines, ignoreBeforeTime) {
5485    if (nested === void 0) {
5486      nested = true;
5487    }
5488
5489    if (tweens === void 0) {
5490      tweens = true;
5491    }
5492
5493    if (timelines === void 0) {
5494      timelines = true;
5495    }
5496
5497    if (ignoreBeforeTime === void 0) {
5498      ignoreBeforeTime = -_bigNum;
5499    }
5500
5501    var a = [],
5502        child = this._first;
5503
5504    while (child) {
5505      if (child._start >= ignoreBeforeTime) {
5506        if (child instanceof Tween) {
5507          tweens && a.push(child);
5508        } else {
5509          timelines && a.push(child);
5510          nested && a.push.apply(a, child.getChildren(true, tweens, timelines));
5511        }
5512      }
5513
5514      child = child._next;
5515    }
5516
5517    return a;
5518  };
5519
5520  _proto2.getById = function getById(id) {
5521    var animations = this.getChildren(1, 1, 1),
5522        i = animations.length;
5523
5524    while (i--) {
5525      if (animations[i].vars.id === id) {
5526        return animations[i];
5527      }
5528    }
5529  };
5530
5531  _proto2.remove = function remove(child) {
5532    if (_isString(child)) {
5533      return this.removeLabel(child);
5534    }
5535
5536    if (_isFunction(child)) {
5537      return this.killTweensOf(child);
5538    }
5539
5540    _removeLinkedListItem(this, child);
5541
5542    if (child === this._recent) {
5543      this._recent = this._last;
5544    }
5545
5546    return _uncache(this);
5547  };
5548
5549  _proto2.totalTime = function totalTime(_totalTime2, suppressEvents) {
5550    if (!arguments.length) {
5551      return this._tTime;
5552    }
5553
5554    this._forcing = 1;
5555
5556    if (!this._dp && this._ts) {
5557      //special case for the global timeline (or any other that has no parent or detached parent).
5558      this._start = _round(_ticker.time - (this._ts > 0 ? _totalTime2 / this._ts : (this.totalDuration() - _totalTime2) / -this._ts));
5559    }
5560
5561    _Animation.prototype.totalTime.call(this, _totalTime2, suppressEvents);
5562
5563    this._forcing = 0;
5564    return this;
5565  };
5566
5567  _proto2.addLabel = function addLabel(label, position) {
5568    this.labels[label] = _parsePosition(this, position);
5569    return this;
5570  };
5571
5572  _proto2.removeLabel = function removeLabel(label) {
5573    delete this.labels[label];
5574    return this;
5575  };
5576
5577  _proto2.addPause = function addPause(position, callback, params) {
5578    var t = Tween.delayedCall(0, callback || _emptyFunc, params);
5579    t.data = "isPause";
5580    this._hasPause = 1;
5581    return _addToTimeline(this, t, _parsePosition(this, position));
5582  };
5583
5584  _proto2.removePause = function removePause(position) {
5585    var child = this._first;
5586    position = _parsePosition(this, position);
5587
5588    while (child) {
5589      if (child._start === position && child.data === "isPause") {
5590        _removeFromParent(child);
5591      }
5592
5593      child = child._next;
5594    }
5595  };
5596
5597  _proto2.killTweensOf = function killTweensOf(targets, props, onlyActive) {
5598    var tweens = this.getTweensOf(targets, onlyActive),
5599        i = tweens.length;
5600
5601    while (i--) {
5602      _overwritingTween !== tweens[i] && tweens[i].kill(targets, props);
5603    }
5604
5605    return this;
5606  };
5607
5608  _proto2.getTweensOf = function getTweensOf(targets, onlyActive) {
5609    var a = [],
5610        parsedTargets = toArray(targets),
5611        child = this._first,
5612        isGlobalTime = _isNumber(onlyActive),
5613        // a number is interpreted as a global time. If the animation spans
5614    children;
5615
5616    while (child) {
5617      if (child instanceof Tween) {
5618        if (_arrayContainsAny(child._targets, parsedTargets) && (isGlobalTime ? (!_overwritingTween || child._initted && child._ts) && child.globalTime(0) <= onlyActive && child.globalTime(child.totalDuration()) > onlyActive : !onlyActive || child.isActive())) {
5619          // note: if this is for overwriting, it should only be for tweens that aren't paused and are initted.
5620          a.push(child);
5621        }
5622      } else if ((children = child.getTweensOf(parsedTargets, onlyActive)).length) {
5623        a.push.apply(a, children);
5624      }
5625
5626      child = child._next;
5627    }
5628
5629    return a;
5630  } // potential future feature - targets() on timelines
5631  // targets() {
5632  // 	let result = [];
5633  // 	this.getChildren(true, true, false).forEach(t => result.push(...t.targets()));
5634  // 	return result;
5635  // }
5636  ;
5637
5638  _proto2.tweenTo = function tweenTo(position, vars) {
5639    vars = vars || {};
5640
5641    var tl = this,
5642        endTime = _parsePosition(tl, position),
5643        _vars = vars,
5644        startAt = _vars.startAt,
5645        _onStart = _vars.onStart,
5646        onStartParams = _vars.onStartParams,
5647        immediateRender = _vars.immediateRender,
5648        tween = Tween.to(tl, _setDefaults({
5649      ease: "none",
5650      lazy: false,
5651      immediateRender: false,
5652      time: endTime,
5653      overwrite: "auto",
5654      duration: vars.duration || Math.abs((endTime - (startAt && "time" in startAt ? startAt.time : tl._time)) / tl.timeScale()) || _tinyNum,
5655      onStart: function onStart() {
5656        tl.pause();
5657        var duration = vars.duration || Math.abs((endTime - tl._time) / tl.timeScale());
5658        tween._dur !== duration && _setDuration(tween, duration, 0, 1).render(tween._time, true, true);
5659        _onStart && _onStart.apply(tween, onStartParams || []); //in case the user had an onStart in the vars - we don't want to overwrite it.
5660      }
5661    }, vars));
5662
5663    return immediateRender ? tween.render(0) : tween;
5664  };
5665
5666  _proto2.tweenFromTo = function tweenFromTo(fromPosition, toPosition, vars) {
5667    return this.tweenTo(toPosition, _setDefaults({
5668      startAt: {
5669        time: _parsePosition(this, fromPosition)
5670      }
5671    }, vars));
5672  };
5673
5674  _proto2.recent = function recent() {
5675    return this._recent;
5676  };
5677
5678  _proto2.nextLabel = function nextLabel(afterTime) {
5679    if (afterTime === void 0) {
5680      afterTime = this._time;
5681    }
5682
5683    return _getLabelInDirection(this, _parsePosition(this, afterTime));
5684  };
5685
5686  _proto2.previousLabel = function previousLabel(beforeTime) {
5687    if (beforeTime === void 0) {
5688      beforeTime = this._time;
5689    }
5690
5691    return _getLabelInDirection(this, _parsePosition(this, beforeTime), 1);
5692  };
5693
5694  _proto2.currentLabel = function currentLabel(value) {
5695    return arguments.length ? this.seek(value, true) : this.previousLabel(this._time + _tinyNum);
5696  };
5697
5698  _proto2.shiftChildren = function shiftChildren(amount, adjustLabels, ignoreBeforeTime) {
5699    if (ignoreBeforeTime === void 0) {
5700      ignoreBeforeTime = 0;
5701    }
5702
5703    var child = this._first,
5704        labels = this.labels,
5705        p;
5706
5707    while (child) {
5708      if (child._start >= ignoreBeforeTime) {
5709        child._start += amount;
5710        child._end += amount;
5711      }
5712
5713      child = child._next;
5714    }
5715
5716    if (adjustLabels) {
5717      for (p in labels) {
5718        if (labels[p] >= ignoreBeforeTime) {
5719          labels[p] += amount;
5720        }
5721      }
5722    }
5723
5724    return _uncache(this);
5725  };
5726
5727  _proto2.invalidate = function invalidate() {
5728    var child = this._first;
5729    this._lock = 0;
5730
5731    while (child) {
5732      child.invalidate();
5733      child = child._next;
5734    }
5735
5736    return _Animation.prototype.invalidate.call(this);
5737  };
5738
5739  _proto2.clear = function clear(includeLabels) {
5740    if (includeLabels === void 0) {
5741      includeLabels = true;
5742    }
5743
5744    var child = this._first,
5745        next;
5746
5747    while (child) {
5748      next = child._next;
5749      this.remove(child);
5750      child = next;
5751    }
5752
5753    this._dp && (this._time = this._tTime = this._pTime = 0);
5754    includeLabels && (this.labels = {});
5755    return _uncache(this);
5756  };
5757
5758  _proto2.totalDuration = function totalDuration(value) {
5759    var max = 0,
5760        self = this,
5761        child = self._last,
5762        prevStart = _bigNum,
5763        prev,
5764        start,
5765        parent;
5766
5767    if (arguments.length) {
5768      return self.timeScale((self._repeat < 0 ? self.duration() : self.totalDuration()) / (self.reversed() ? -value : value));
5769    }
5770
5771    if (self._dirty) {
5772      parent = self.parent;
5773
5774      while (child) {
5775        prev = child._prev; //record it here in case the tween changes position in the sequence...
5776
5777        child._dirty && child.totalDuration(); //could change the tween._startTime, so make sure the animation's cache is clean before analyzing it.
5778
5779        start = child._start;
5780
5781        if (start > prevStart && self._sort && child._ts && !self._lock) {
5782          //in case one of the tweens shifted out of order, it needs to be re-inserted into the correct position in the sequence
5783          self._lock = 1; //prevent endless recursive calls - there are methods that get triggered that check duration/totalDuration when we add().
5784
5785          _addToTimeline(self, child, start - child._delay, 1)._lock = 0;
5786        } else {
5787          prevStart = start;
5788        }
5789
5790        if (start < 0 && child._ts) {
5791          //children aren't allowed to have negative startTimes unless smoothChildTiming is true, so adjust here if one is found.
5792          max -= start;
5793
5794          if (!parent && !self._dp || parent && parent.smoothChildTiming) {
5795            self._start += start / self._ts;
5796            self._time -= start;
5797            self._tTime -= start;
5798          }
5799
5800          self.shiftChildren(-start, false, -1e999);
5801          prevStart = 0;
5802        }
5803
5804        child._end > max && child._ts && (max = child._end);
5805        child = prev;
5806      }
5807
5808      _setDuration(self, self === _globalTimeline && self._time > max ? self._time : max, 1, 1);
5809
5810      self._dirty = 0;
5811    }
5812
5813    return self._tDur;
5814  };
5815
5816  Timeline.updateRoot = function updateRoot(time) {
5817    if (_globalTimeline._ts) {
5818      _lazySafeRender(_globalTimeline, _parentToChildTotalTime(time, _globalTimeline));
5819
5820      _lastRenderedFrame = _ticker.frame;
5821    }
5822
5823    if (_ticker.frame >= _nextGCFrame) {
5824      _nextGCFrame += _config.autoSleep || 120;
5825      var child = _globalTimeline._first;
5826      if (!child || !child._ts) if (_config.autoSleep && _ticker._listeners.length < 2) {
5827        while (child && !child._ts) {
5828          child = child._next;
5829        }
5830
5831        child || _ticker.sleep();
5832      }
5833    }
5834  };
5835
5836  return Timeline;
5837}(Animation);
5838
5839_setDefaults(Timeline.prototype, {
5840  _lock: 0,
5841  _hasPause: 0,
5842  _forcing: 0
5843});
5844
5845var _addComplexStringPropTween = function _addComplexStringPropTween(target, prop, start, end, setter, stringFilter, funcParam) {
5846  //note: we call _addComplexStringPropTween.call(tweenInstance...) to ensure that it's scoped properly. We may call it from within a plugin too, thus "this" would refer to the plugin.
5847  var pt = new PropTween(this._pt, target, prop, 0, 1, _renderComplexString, null, setter),
5848      index = 0,
5849      matchIndex = 0,
5850      result,
5851      startNums,
5852      color,
5853      endNum,
5854      chunk,
5855      startNum,
5856      hasRandom,
5857      a;
5858  pt.b = start;
5859  pt.e = end;
5860  start += ""; //ensure values are strings
5861
5862  end += "";
5863
5864  if (hasRandom = ~end.indexOf("random(")) {
5865    end = _replaceRandom(end);
5866  }
5867
5868  if (stringFilter) {
5869    a = [start, end];
5870    stringFilter(a, target, prop); //pass an array with the starting and ending values and let the filter do whatever it needs to the values.
5871
5872    start = a[0];
5873    end = a[1];
5874  }
5875
5876  startNums = start.match(_complexStringNumExp) || [];
5877
5878  while (result = _complexStringNumExp.exec(end)) {
5879    endNum = result[0];
5880    chunk = end.substring(index, result.index);
5881
5882    if (color) {
5883      color = (color + 1) % 5;
5884    } else if (chunk.substr(-5) === "rgba(") {
5885      color = 1;
5886    }
5887
5888    if (endNum !== startNums[matchIndex++]) {
5889      startNum = parseFloat(startNums[matchIndex - 1]) || 0; //these nested PropTweens are handled in a special way - we'll never actually call a render or setter method on them. We'll just loop through them in the parent complex string PropTween's render method.
5890
5891      pt._pt = {
5892        _next: pt._pt,
5893        p: chunk || matchIndex === 1 ? chunk : ",",
5894        //note: SVG spec allows omission of comma/space when a negative sign is wedged between two numbers, like 2.5-5.3 instead of 2.5,-5.3 but when tweening, the negative value may switch to positive, so we insert the comma just in case.
5895        s: startNum,
5896        c: endNum.charAt(1) === "=" ? parseFloat(endNum.substr(2)) * (endNum.charAt(0) === "-" ? -1 : 1) : parseFloat(endNum) - startNum,
5897        m: color && color < 4 ? Math.round : 0
5898      };
5899      index = _complexStringNumExp.lastIndex;
5900    }
5901  }
5902
5903  pt.c = index < end.length ? end.substring(index, end.length) : ""; //we use the "c" of the PropTween to store the final part of the string (after the last number)
5904
5905  pt.fp = funcParam;
5906
5907  if (_relExp.test(end) || hasRandom) {
5908    pt.e = 0; //if the end string contains relative values or dynamic random(...) values, delete the end it so that on the final render we don't actually set it to the string with += or -= characters (forces it to use the calculated value).
5909  }
5910
5911  this._pt = pt; //start the linked list with this new PropTween. Remember, we call _addComplexStringPropTween.call(tweenInstance...) to ensure that it's scoped properly. We may call it from within a plugin too, thus "this" would refer to the plugin.
5912
5913  return pt;
5914},
5915    _addPropTween = function _addPropTween(target, prop, start, end, index, targets, modifier, stringFilter, funcParam) {
5916  _isFunction(end) && (end = end(index || 0, target, targets));
5917  var currentValue = target[prop],
5918      parsedStart = start !== "get" ? start : !_isFunction(currentValue) ? currentValue : funcParam ? target[prop.indexOf("set") || !_isFunction(target["get" + prop.substr(3)]) ? prop : "get" + prop.substr(3)](funcParam) : target[prop](),
5919      setter = !_isFunction(currentValue) ? _setterPlain : funcParam ? _setterFuncWithParam : _setterFunc,
5920      pt;
5921
5922  if (_isString(end)) {
5923    if (~end.indexOf("random(")) {
5924      end = _replaceRandom(end);
5925    }
5926
5927    if (end.charAt(1) === "=") {
5928      end = parseFloat(parsedStart) + parseFloat(end.substr(2)) * (end.charAt(0) === "-" ? -1 : 1) + (getUnit(parsedStart) || 0);
5929    }
5930  }
5931
5932  if (parsedStart !== end) {
5933    if (!isNaN(parsedStart * end)) {
5934      pt = new PropTween(this._pt, target, prop, +parsedStart || 0, end - (parsedStart || 0), typeof currentValue === "boolean" ? _renderBoolean : _renderPlain, 0, setter);
5935      funcParam && (pt.fp = funcParam);
5936      modifier && pt.modifier(modifier, this, target);
5937      return this._pt = pt;
5938    }
5939
5940    !currentValue && !(prop in target) && _missingPlugin(prop, end);
5941    return _addComplexStringPropTween.call(this, target, prop, parsedStart, end, setter, stringFilter || _config.stringFilter, funcParam);
5942  }
5943},
5944    //creates a copy of the vars object and processes any function-based values (putting the resulting values directly into the copy) as well as strings with "random()" in them. It does NOT process relative values.
5945_processVars = function _processVars(vars, index, target, targets, tween) {
5946  _isFunction(vars) && (vars = _parseFuncOrString(vars, tween, index, target, targets));
5947
5948  if (!_isObject(vars) || vars.style && vars.nodeType || _isArray(vars) || _isTypedArray(vars)) {
5949    return _isString(vars) ? _parseFuncOrString(vars, tween, index, target, targets) : vars;
5950  }
5951
5952  var copy = {},
5953      p;
5954
5955  for (p in vars) {
5956    copy[p] = _parseFuncOrString(vars[p], tween, index, target, targets);
5957  }
5958
5959  return copy;
5960},
5961    _checkPlugin = function _checkPlugin(property, vars, tween, index, target, targets) {
5962  var plugin, pt, ptLookup, i;
5963
5964  if (_plugins[property] && (plugin = new _plugins[property]()).init(target, plugin.rawVars ? vars[property] : _processVars(vars[property], index, target, targets, tween), tween, index, targets) !== false) {
5965    tween._pt = pt = new PropTween(tween._pt, target, property, 0, 1, plugin.render, plugin, 0, plugin.priority);
5966
5967    if (tween !== _quickTween) {
5968      ptLookup = tween._ptLookup[tween._targets.indexOf(target)]; //note: we can't use tween._ptLookup[index] because for staggered tweens, the index from the fullTargets array won't match what it is in each individual tween that spawns from the stagger.
5969
5970      i = plugin._props.length;
5971
5972      while (i--) {
5973        ptLookup[plugin._props[i]] = pt;
5974      }
5975    }
5976  }
5977
5978  return plugin;
5979},
5980    _overwritingTween,
5981    //store a reference temporarily so we can avoid overwriting itself.
5982_initTween = function _initTween(tween, time) {
5983  var vars = tween.vars,
5984      ease = vars.ease,
5985      startAt = vars.startAt,
5986      immediateRender = vars.immediateRender,
5987      lazy = vars.lazy,
5988      onUpdate = vars.onUpdate,
5989      onUpdateParams = vars.onUpdateParams,
5990      callbackScope = vars.callbackScope,
5991      runBackwards = vars.runBackwards,
5992      yoyoEase = vars.yoyoEase,
5993      keyframes = vars.keyframes,
5994      autoRevert = vars.autoRevert,
5995      dur = tween._dur,
5996      prevStartAt = tween._startAt,
5997      targets = tween._targets,
5998      parent = tween.parent,
5999      fullTargets = parent && parent.data === "nested" ? parent.parent._targets : targets,
6000      autoOverwrite = tween._overwrite === "auto" && !_suppressOverwrites,
6001      tl = tween.timeline,
6002      cleanVars,
6003      i,
6004      p,
6005      pt,
6006      target,
6007      hasPriority,
6008      gsData,
6009      harness,
6010      plugin,
6011      ptLookup,
6012      index,
6013      harnessVars,
6014      overwritten;
6015  tl && (!keyframes || !ease) && (ease = "none");
6016  tween._ease = _parseEase(ease, _defaults.ease);
6017  tween._yEase = yoyoEase ? _invertEase(_parseEase(yoyoEase === true ? ease : yoyoEase, _defaults.ease)) : 0;
6018
6019  if (yoyoEase && tween._yoyo && !tween._repeat) {
6020    //there must have been a parent timeline with yoyo:true that is currently in its yoyo phase, so flip the eases.
6021    yoyoEase = tween._yEase;
6022    tween._yEase = tween._ease;
6023    tween._ease = yoyoEase;
6024  }
6025
6026  if (!tl) {
6027    //if there's an internal timeline, skip all the parsing because we passed that task down the chain.
6028    harness = targets[0] ? _getCache(targets[0]).harness : 0;
6029    harnessVars = harness && vars[harness.prop]; //someone may need to specify CSS-specific values AND non-CSS values, like if the element has an "x" property plus it's a standard DOM element. We allow people to distinguish by wrapping plugin-specific stuff in a css:{} object for example.
6030
6031    cleanVars = _copyExcluding(vars, _reservedProps);
6032    prevStartAt && prevStartAt.render(-1, true).kill();
6033
6034    if (startAt) {
6035      _removeFromParent(tween._startAt = Tween.set(targets, _setDefaults({
6036        data: "isStart",
6037        overwrite: false,
6038        parent: parent,
6039        immediateRender: true,
6040        lazy: _isNotFalse(lazy),
6041        startAt: null,
6042        delay: 0,
6043        onUpdate: onUpdate,
6044        onUpdateParams: onUpdateParams,
6045        callbackScope: callbackScope,
6046        stagger: 0
6047      }, startAt))); //copy the properties/values into a new object to avoid collisions, like var to = {x:0}, from = {x:500}; timeline.fromTo(e, from, to).fromTo(e, to, from);
6048
6049
6050      if (immediateRender) {
6051        if (time > 0) {
6052          autoRevert || (tween._startAt = 0); //tweens that render immediately (like most from() and fromTo() tweens) shouldn't revert when their parent timeline's playhead goes backward past the startTime because the initial render could have happened anytime and it shouldn't be directly correlated to this tween's startTime. Imagine setting up a complex animation where the beginning states of various objects are rendered immediately but the tween doesn't happen for quite some time - if we revert to the starting values as soon as the playhead goes backward past the tween's startTime, it will throw things off visually. Reversion should only happen in Timeline instances where immediateRender was false or when autoRevert is explicitly set to true.
6053        } else if (dur && !(time < 0 && prevStartAt)) {
6054          time && (tween._zTime = time);
6055          return; //we skip initialization here so that overwriting doesn't occur until the tween actually begins. Otherwise, if you create several immediateRender:true tweens of the same target/properties to drop into a Timeline, the last one created would overwrite the first ones because they didn't get placed into the timeline yet before the first render occurs and kicks in overwriting.
6056        }
6057      }
6058    } else if (runBackwards && dur) {
6059      //from() tweens must be handled uniquely: their beginning values must be rendered but we don't want overwriting to occur yet (when time is still 0). Wait until the tween actually begins before doing all the routines like overwriting. At that time, we should render at the END of the tween to ensure that things initialize correctly (remember, from() tweens go backwards)
6060      if (prevStartAt) {
6061        !autoRevert && (tween._startAt = 0);
6062      } else {
6063        time && (immediateRender = false); //in rare cases (like if a from() tween runs and then is invali
6063date()-ed), immediateRender could be true but the initial forced-render gets skipped, so there's no need to force the render in this context when the _time is greater than 0
6064
6065        p = _setDefaults({
6066          overwrite: false,
6067          data: "isFromStart",
6068          //we tag the tween with as "isFromStart" so that if [inside a plugin] we need to only do something at the very END of a tween, we have a way of identifying this tween as merely the one that's setting the beginning values for a "from()" tween. For example, clearProps in CSSPlugin should only get applied at the very END of a tween and without this tag, from(...{height:100, clearProps:"height", delay:1}) would wipe the height at the beginning of the tween and after 1 second, it'd kick back in.
6069          lazy: immediateRender && _isNotFalse(lazy),
6070          immediateRender: immediateRender,
6071          //zero-duration tweens render immediately by default, but if we're not specifically instructed to render this tween immediately, we should skip this and merely _init() to record the starting values (rendering them immediately would push them to completion which is wasteful in that case - we'd have to render(-1) immediately after)
6072          stagger: 0,
6073          parent: parent //ensures that nested tweens that had a stagger are handled properly, like gsap.from(".class", {y:gsap.utils.wrap([-100,100])})
6074
6075        }, cleanVars);
6076        harnessVars && (p[harness.prop] = harnessVars); // in case someone does something like .from(..., {css:{}})
6077
6078        _removeFromParent(tween._startAt = Tween.set(targets, p));
6079
6080        if (!immediateRender) {
6081          _initTween(tween._startAt, _tinyNum); //ensures that the initial values are recorded
6082
6083        } else if (!time) {
6084          return;
6085        }
6086      }
6087    }
6088
6089    tween._pt = 0;
6090    lazy = dur && _isNotFalse(lazy) || lazy && !dur;
6091
6092    for (i = 0; i < targets.length; i++) {
6093      target = targets[i];
6094      gsData = target._gsap || _harness(targets)[i]._gsap;
6095      tween._ptLookup[i] = ptLookup = {};
6096      _lazyLookup[gsData.id] && _lazyTweens.length && _lazyRender(); //if other tweens of the same target have recently initted but haven't rendered yet, we've got to force the render so that the starting values are correct (imagine populating a timeline with a bunch of sequential tweens and then jumping to the end)
6097
6098      index = fullTargets === targets ? i : fullTargets.indexOf(target);
6099
6100      if (harness && (plugin = new harness()).init(target, harnessVars || cleanVars, tween, index, fullTargets) !== false) {
6101        tween._pt = pt = new PropTween(tween._pt, target, plugin.name, 0, 1, plugin.render, plugin, 0, plugin.priority);
6102
6103        plugin._props.forEach(function (name) {
6104          ptLookup[name] = pt;
6105        });
6106
6107        plugin.priority && (hasPriority = 1);
6108      }
6109
6110      if (!harness || harnessVars) {
6111        for (p in cleanVars) {
6112          if (_plugins[p] && (plugin = _checkPlugin(p, cleanVars, tween, index, target, fullTargets))) {
6113            plugin.priority && (hasPriority = 1);
6114          } else {
6115            ptLookup[p] = pt = _addPropTween.call(tween, target, p, "get", cleanVars[p], index, fullTargets, 0, vars.stringFilter);
6116          }
6117        }
6118      }
6119
6120      tween._op && tween._op[i] && tween.kill(target, tween._op[i]);
6121
6122      if (autoOverwrite && tween._pt) {
6123        _overwritingTween = tween;
6124
6125        _globalTimeline.killTweensOf(target, ptLookup, tween.globalTime(0)); //Also make sure the overwriting doesn't overwrite THIS tween!!!
6126
6127
6128        overwritten = !tween.parent;
6129        _overwritingTween = 0;
6130      }
6131
6132      tween._pt && lazy && (_lazyLookup[gsData.id] = 1);
6133    }
6134
6135    hasPriority && _sortPropTweensByPriority(tween);
6136    tween._onInit && tween._onInit(tween); //plugins like RoundProps must wait until ALL of the PropTweens are instantiated. In the plugin's init() function, it sets the _onInit on the tween instance. May not be pretty/intuitive, but it's fast and keeps file size down.
6137  }
6138
6139  tween._from = !tl && !!vars.runBackwards; //nested timelines should never run backwards - the backwards-ness is in the child tweens.
6140
6141  tween._onUpdate = onUpdate;
6142  tween._initted = (!tween._op || tween._pt) && !overwritten;
6142 // if overwrittenProps resulted in the entire tween being killed, do NOT flag it as initted or else it may render for one tick.
6143},
6144    _addAliasesToVars = function _addAliasesToVars(targets, vars) {
6145  var harness = targets[0] ? _getCache(targets[0]).harness : 0,
6146      propertyAliases = harness && harness.aliases,
6147      copy,
6148      p,
6149      i,
6150      aliases;
6151
6152  if (!propertyAliases) {
6153    return vars;
6154  }
6155
6156  copy = _merge({}, vars);
6157
6158  for (p in propertyAliases) {
6159    if (p in copy) {
6160      aliases = propertyAliases[p].split(",");
6161      i = aliases.length;
6162
6163      while (i--) {
6164        copy[aliases[i]] = copy[p];
6165      }
6166    }
6167  }
6168
6169  return copy;
6170},
6171    _parseFuncOrString = function _parseFuncOrString(value, tween, i, target, targets) {
6172  return _isFunction(value) ? value.call(tween, i, target, targets) : _isString(value) && ~value.indexOf("random(") ? _replaceRandom(value) : value;
6173},
6174    _staggerTweenProps = _callbackNames + "repeat,repeatDelay,yoyo,repeatRefresh,yoyoEase",
6175    _staggerPropsToSkip = (_staggerTweenProps + ",id,stagger,delay,duration,paused,scrollTrigger").split(",");
6176/*
6177 * --------------------------------------------------------------------------------------
6178 * TWEEN
6179 * --------------------------------------------------------------------------------------
6180 */
6181
6182
6183var Tween = /*#__PURE__*/function (_Animation2) {
6184  _inheritsLoose(Tween, _Animation2);
6185
6186  function Tween(targets, vars, time, skipInherit) {
6187    var _this3;
6188
6189    if (typeof vars === "number") {
6190      time.duration = vars;
6191      vars = time;
6192      time = null;
6193    }
6194
6195    _this3 = _Animation2.call(this, skipInherit ? vars : _inheritDefaults(vars), time) || this;
6196    var _this3$vars = _this3.vars,
6197        duration = _this3$vars.duration,
6198        delay = _this3$vars.delay,
6199        immediateRender = _this3$vars.immediateRender,
6200        stagger = _this3$vars.stagger,
6201        overwrite = _this3$vars.overwrite,
6202        keyframes = _this3$vars.keyframes,
6203        defaults = _this3$vars.defaults,
6204        scrollTrigger = _this3$vars.scrollTrigger,
6205        yoyoEase = _this3$vars.yoyoEase,
6206        parent = _this3.parent,
6207        parsedTargets = (_isArray(targets) || _isTypedArray(targets) ? _isNumber(targets[0]) : "length" in vars) ? [targets] : toArray(targets),
6208        tl,
6209        i,
6210        copy,
6211        l,
6212        p,
6213        curTarget,
6214        staggerFunc,
6215        staggerVarsToMerge;
6216    _this3._targets = parsedTargets.length ? _harness(parsedTargets) : _warn("GSAP target " + targets + " not found. https://greensock.com", !_config.nullTargetWarn) || [];
6217    _this3._ptLookup = []; //PropTween lookup. An array containing an object for each target, having keys for each tweening property
6218
6219    _this3._overwrite = overwrite;
6220
6221    if (keyframes || stagger || _isFuncOrString(duration) || _isFuncOrString(delay)) {
6222      vars = _this3.vars;
6223      tl = _this3.timeline = new Timeline({
6224        data: "nested",
6225        defaults: defaults || {}
6226      });
6227      tl.kill();
6228      tl.parent = tl._dp = _assertThisInitialized(_this3);
6229      tl._start = 0;
6230
6231      if (keyframes) {
6232        _setDefaults(tl.vars.defaults, {
6233          ease: "none"
6234        });
6235
6236        keyframes.forEach(function (frame) {
6237          return tl.to(parsedTargets, frame, ">");
6238        });
6239      } else {
6240        l = parsedTargets.length;
6241        staggerFunc = stagger ? distribute(stagger) : _emptyFunc;
6242
6243        if (_isObject(stagger)) {
6244          //users can pass in callbacks like onStart/onComplete in the stagger object. These should fire with each individual tween.
6245          for (p in stagger) {
6246            if (~_staggerTweenProps.indexOf(p)) {
6247              staggerVarsToMerge || (staggerVarsToMerge = {});
6248              staggerVarsToMerge[p] = stagger[p];
6249            }
6250          }
6251        }
6252
6253        for (i = 0; i < l; i++) {
6254          copy = {};
6255
6256          for (p in vars) {
6257            if (_staggerPropsToSkip.indexOf(p) < 0) {
6258              copy[p] = vars[p];
6259            }
6260          }
6261
6262          copy.stagger = 0;
6263          yoyoEase && (copy.yoyoEase = yoyoEase);
6264          staggerVarsToMerge && _merge(copy, staggerVarsToMerge);
6265          curTarget = parsedTargets[i]; //don't just copy duration or delay because if they're a string or function, we'd end up in an infinite loop because _isFuncOrString() would evaluate as true in the child tweens, entering this loop, etc. So we parse the value straight from vars and default to 0.
6266
6267          copy.duration = +_parseFuncOrString(duration, _assertThisInitialized(_this3), i, curTarget, parsedTargets);
6268          copy.delay = (+_parseFuncOrString(delay, _assertThisInitialized(_this3), i, curTarget, parsedTargets) || 0) - _this3._delay;
6269
6270          if (!stagger && l === 1 && copy.delay) {
6271            // if someone does delay:"random(1, 5)", repeat:-1, for example, the delay 
6271shouldn't be inside the repeat.
6272            _this3._delay = delay = copy.delay;
6273            _this3._start += delay;
6274            copy.delay = 0;
6275          }
6276
6277          tl.to(curTarget, copy, staggerFunc(i, curTarget, parsedTargets));
6278        }
6279
6280        tl.duration() ? duration = delay = 0 : _this3.timeline = 0; // if the timeline's duration is 0, we don't need a timeline internally!
6281      }
6282
6283      duration || _this3.duration(duration = tl.duration());
6284    } else {
6285      _this3.timeline = 0; //speed optimization, faster lookups (no going up the prototype chain)
6286    }
6287
6288    if (overwrite === true && !_suppressOverwrites) {
6289      _overwritingTween = _assertThisInitialized(_this3);
6290
6291      _globalTimeline.killTweensOf(parsedTargets);
6292
6293      _overwritingTween = 0;
6294    }
6295
6296    parent && _postAddChecks(parent, _assertThisInitialized(_this3));
6297
6298    if (immediateRender || !duration && !keyframes && _this3._start === _round(parent._time) && _isNotFalse(immediateRender) && _hasNoPausedAncestors(_assertThisInitialized(_this3)) && parent.data !== "nested") {
6299      _this3._tTime = -_tinyNum; //forces a render without having to set the render() "force" parameter to true because we want to allow lazying by default (using the "force" parameter always forces an immediate full render)
6300
6301      _this3.render(Math.max(0, -delay)); //in case delay is negative
6302
6303    }
6304
6305    scrollTrigger && _scrollTrigger(_assertThisInitialized(_this3), scrollTrigger);
6306    return _this3;
6307  }
6308
6309  var _proto3 = Tween.prototype;
6310
6311  _proto3.render = function render(totalTime, suppressEvents, force) {
6312    var prevTime = this._time,
6313        tDur = this._tDur,
6314        dur = this._dur,
6315        tTime = totalTime > tDur - _tinyNum && totalTime >= 0 ? tDur : totalTime < _tinyNum ? 0 : totalTime,
6316        time,
6317        pt,
6318        iteration,
6319        cycleDuration,
6320        prevIteration,
6321        isYoyo,
6322        ratio,
6323        timeline,
6324        yoyoEase;
6325
6326    if (!dur) {
6327      _renderZeroDurationTween(this, totalTime, suppressEvents, force);
6328    } else if (tTime !== this._tTime || !totalTime || force || !this._initted && this._tTime || this._startAt && this._zTime < 0 !== totalTime < 0) {
6329      //this senses if we're crossing over the start time, in which case we must record _zTime and force the render, but we do it in this lengthy conditional way for performance reasons (usually we can skip the calculations): this._initted && (this._zTime < 0) !== (totalTime < 0)
6330      time = tTime;
6331      timeline = this.timeline;
6332
6333      if (this._repeat) {
6334        //adjust the time for repeats and yoyos
6335        cycleDuration = dur + this._rDelay;
6336
6337        if (this._repeat < -1 && totalTime < 0) {
6338          return this.totalTime(cycleDuration * 100 + totalTime, suppressEvents, force);
6339        }
6340
6341        time = _round(tTime % cycleDuration); //round to avoid floating point errors. (4 % 0.8 should be 0 but some browsers report it as 0.79999999!)
6342
6343        if (tTime === tDur) {
6344          // the tDur === tTime is for edge cases where there's a lengthy decimal on the duration and it may reach the very end but the time is rendered as not-quite-there (remember, tDur is rounded to 4 decimals whereas dur isn't)
6345          iteration = this._repeat;
6346          time = dur;
6347        } else {
6348          iteration = ~~(tTime / cycleDuration);
6349
6350          if (iteration && iteration === tTime / cycleDuration) {
6351            time = dur;
6352            iteration--;
6353          }
6354
6355          time > dur && (time = dur);
6356        }
6357
6358        isYoyo = this._yoyo && iteration & 1;
6359
6360        if (isYoyo) {
6361          yoyoEase = this._yEase;
6362          time = dur - time;
6363        }
6364
6365        prevIteration = _animationCycle(this._tTime, cycleDuration);
6366
6367        if (time === prevTime && !force && this._initted) {
6368          //could be during the repeatDelay part. No need to render and fire callbacks.
6369          return this;
6370        }
6371
6372        if (iteration !== prevIteration) {
6373          timeline && this._yEase && _propagateYoyoEase(timeline, isYoyo); //repeatRefresh functionality
6374
6375          if (this.vars.repeatRefresh && !isYoyo && !this._lock) {
6376            this._lock = force = 1; //force, otherwise if lazy is true, the _attemptInitTween() will return and we'll jump out and get caught bouncing on each tick.
6377
6378            this.render(_round(cycleDuration * iteration), true).invalidate()._lock = 0;
6379          }
6380        }
6381      }
6382
6383      if (!this._initted) {
6384        if (_attemptInitTween(this, totalTime < 0 ? totalTime : time, force, suppressEvents)) {
6385          this._tTime = 0; // in constructor if immediateRender is true, we set _tTime to -_tinyNum to have the playhead cross the starting point but we can't leave _tTime as a negative number.
6386
6387          return this;
6388        }
6389
6390        if (dur !== this._dur) {
6391          // while initting, a plugin like InertiaPlugin might alter the duration, so rerun from the start to ensure everything renders as it should.
6392          return this.render(totalTime, suppressEvents, force);
6393        }
6394      }
6395
6396      this._tTime = tTime;
6397      this._time = time;
6398
6399      if (!this._act && this._ts) {
6400        this._act = 1; //as long as it's not paused, force it to be active so that if the user renders independent of the parent timeline, it'll be forced to re-render on the next tick.
6401
6402        this._lazy = 0;
6403      }
6404
6405      this.ratio = ratio = (yoyoEase || this._ease)(time / dur);
6406
6407      if (this._from) {
6408        this.ratio = ratio = 1 - ratio;
6409      }
6410
6411      time && !prevTime && !suppressEvents && _callback(this, "onStart");
6412      pt = this._pt;
6413
6414      while (pt) {
6415        pt.r(ratio, pt.d);
6416        pt = pt._next;
6417      }
6418
6419      timeline && timeline.render(totalTime < 0 ? totalTime : !time && isYoyo ? -_tinyNum : timeline._dur * ratio, suppressEvents, force) || this._startAt && (this._zTime = totalTime);
6420
6421      if (this._onUpdate && !suppressEvents) {
6422        totalTime < 0 && this._startAt && this._startAt.render(totalTime, true, force); //note: for performance reasons, we tuck this conditional logic inside less traveled areas (most tweens don't have an onUpdate). We'd just have it at the end before the onComplete, but the values should be updated before any onUpdate is called, so we ALSO put it here and then if it's not called, we do so later near the onComplete.
6423
6424        _callback(this, "onUpdate");
6425      }
6426
6427      this._repeat && iteration !== prevIteration && this.vars.onRepeat && !suppressEvents && this.parent && _callback(this, "onRepeat");
6428
6429      if ((tTime === this._tDur || !tTime) && this._tTime === tTime) {
6430        totalTime < 0 && this._startAt && !this._onUpdate && this._startAt.render(totalTime, true, true);
6431        (totalTime || !dur) && (tTime === this._tDur && this._ts > 0 || !tTime && this._ts < 0) && _removeFromParent(this, 1); // don't remove if we're rendering at exactly a time of 0, as there could be autoRevert values that should get set on the next tick (if the playhead goes backward beyond the startTime, negative totalTime). Don't remove if the timeline is reversed and the playhead isn't at 0, otherwise tl.progress(1).reverse() won't work. Only remove if the playhead is at the end and timeScale is positive, or if the playhead is at 0 and the timeScale is negative.
6432
6433        if (!suppressEvents && !(totalTime < 0 && !prevTime) && (tTime || prevTime)) {
6434          // if prevTime and tTime are zero, we shouldn't fire the onReverseComplete. This could happen if you gsap.to(... {paused:true}).play();
6435          _callback(this, tTime === tDur ? "onComplete" : "onReverseComplete", true);
6436
6437          this._prom && !(tTime < tDur && this.timeScale() > 0) && this._prom();
6438        }
6439      }
6440    }
6441
6442    return this;
6443  };
6444
6445  _proto3.targets = function targets() {
6446    return this._targets;
6447  };
6448
vendor: 16,343 bytes, lines 6449-6966
6449  _proto3.invalidate = function invalidate() {
6450    this._pt = this._op = this._startAt = this._onUpdate = this._lazy = this.ratio = 0;
6451    this._ptLookup = [];
6452    this.timeline && this.timeline.invalidate();
6453    return _Animation2.prototype.invalidate.call(this);
6454  };
6455
6456  _proto3.kill = function kill(targets, vars) {
6457    if (vars === void 0) {
6458      vars = "all";
6459    }
6460
6461    if (!targets && (!vars || vars === "all")) {
6462      this._lazy = this._pt = 0;
6463      return this.parent ? _interrupt(this) : this;
6464    }
6465
6466    if (this.timeline) {
6467      var tDur = this.timeline.totalDuration();
6468      this.timeline.killTweensOf(targets, vars, _overwritingTween && _overwritingTween.vars.overwrite !== true)._first || _interrupt(this); // if nothing is left tweening, interrupt.
6469
6470      this.parent && tDur !== this.timeline.totalDuration() && _setDuration(this, this._dur * this.timeline._tDur / tDur, 0, 1); // if a nested tween is killed that changes the duration, it should affect this tween's duration. We must use the ratio, though, because sometimes the internal timeline is stretched like for keyframes where they don't all add up to whatever the parent tween's duration was set to.
6471
6472      return this;
6473    }
6474
6475    var parsedTargets = this._targets,
6476        killingTargets = targets ? toArray(targets) : parsedTargets,
6477        propTweenLookup = this._ptLookup,
6478        firstPT = this._pt,
6479        overwrittenProps,
6480        curLookup,
6481        curOverwriteProps,
6482        props,
6483        p,
6484        pt,
6485        i;
6486
6487    if ((!vars || vars === "all") && _arraysMatch(parsedTargets, killingTargets)) {
6488      vars === "all" && (this._pt = 0);
6489      return _interrupt(this);
6490    }
6491
6492    overwrittenProps = this._op = this._op || [];
6493
6494    if (vars !== "all") {
6495      //so people can pass in a comma-delimited list of property names
6496      if (_isString(vars)) {
6497        p = {};
6498
6499        _forEachName(vars, function (name) {
6500          return p[name] = 1;
6501        });
6502
6503        vars = p;
6504      }
6505
6506      vars = _addAliasesToVars(parsedTargets, vars);
6507    }
6508
6509    i = parsedTargets.length;
6510
6511    while (i--) {
6512      if (~killingTargets.indexOf(parsedTargets[i])) {
6513        curLookup = propTweenLookup[i];
6514
6515        if (vars === "all") {
6516          overwrittenProps[i] = vars;
6517          props = curLookup;
6518          curOverwriteProps = {};
6519        } else {
6520          curOverwriteProps = overwrittenProps[i] = overwrittenProps[i] || {};
6521          props = vars;
6522        }
6523
6524        for (p in props) {
6525          pt = curLookup && curLookup[p];
6526
6527          if (pt) {
6528            if (!("kill" in pt.d) || pt.d.kill(p) === true) {
6529              _removeLinkedListItem(this, pt, "_pt");
6530            }
6531
6532            delete curLookup[p];
6533          }
6534
6535          if (curOverwriteProps !== "all") {
6536            curOverwriteProps[p] = 1;
6537          }
6538        }
6539      }
6540    }
6541
6542    this._initted && !this._pt && firstPT && _interrupt(this); //if all tweening properties are killed, kill the tween. Without this line, if there's a tween with multiple targets and then you killTweensOf() each target individually, the tween would technically still remain active and fire its onComplete even though there aren't any more properties tweening.
6543
6544    return this;
6545  };
6546
6547  Tween.to = function to(targets, vars) {
6548    return new Tween(targets, vars, arguments[2]);
6549  };
6550
6551  Tween.from = function from(targets, vars) {
6552    return new Tween(targets, _parseVars(arguments, 1));
6553  };
6554
6555  Tween.delayedCall = function delayedCall(delay, callback, params, scope) {
6556    return new Tween(callback, 0, {
6557      immediateRender: false,
6558      lazy: false,
6559      overwrite: false,
6560      delay: delay,
6561      onComplete: callback,
6562      onReverseComplete: callback,
6563      onCompleteParams: params,
6564      onReverseCompleteParams: params,
6565      callbackScope: scope
6566    });
6567  };
6568
6569  Tween.fromTo = function fromTo(targets, fromVars, toVars) {
6570    return new Tween(targets, _parseVars(arguments, 2));
6571  };
6572
6573  Tween.set = function set(targets, vars) {
6574    vars.duration = 0;
6575    vars.repeatDelay || (vars.repeat = 0);
6576    return new Tween(targets, vars);
6577  };
6578
6579  Tween.killTweensOf = function killTweensOf(targets, props, onlyActive) {
6580    return _globalTimeline.killTweensOf(targets, props, onlyActive);
6581  };
6582
6583  return Tween;
6584}(Animation);
6585
6586_setDefaults(Tween.prototype, {
6587  _targets: [],
6588  _lazy: 0,
6589  _startAt: 0,
6590  _op: 0,
6591  _onInit: 0
6592}); //add the pertinent timeline methods to Tween instances so that users can chain conveniently and create a timeline automatically. (removed due to concerns that it'd ultimately add to more confusion especially for beginners)
6593// _forEachName("to,from,fromTo,set,call,add,addLabel,addPause", name => {
6594// 	Tween.prototype[name] = function() {
6595// 		let tl = new Timeline();
6596// 		return _addToTimeline(tl, this)[name].apply(tl, toArray(arguments));
6597// 	}
6598// });
6599//for backward compatibility. Leverage the timeline calls.
6600
6601
6602_forEachName("staggerTo,staggerFrom,staggerFromTo", function (name) {
6603  Tween[name] = function () {
6604    var tl = new Timeline(),
6605        params = _slice.call(arguments, 0);
6606
6607    params.splice(name === "staggerFromTo" ? 5 : 4, 0, 0);
6608    return tl[name].apply(tl, params);
6609  };
6610});
6611/*
6612 * --------------------------------------------------------------------------------------
6613 * PROPTWEEN
6614 * --------------------------------------------------------------------------------------
6615 */
6616
6617
6618var _setterPlain = function _setterPlain(target, property, value) {
6619  return target[property] = value;
6620},
6621    _setterFunc = function _setterFunc(target, property, value) {
6622  return target[property](value);
6623},
6624    _setterFuncWithParam = function _setterFuncWithParam(target, property, value, data) {
6625  return target[property](data.fp, value);
6626},
6627    _setterAttribute = function _setterAttribute(target, property, value) {
6628  return target.setAttribute(property, value);
6629},
6630    _getSetter = function _getSetter(target, property) {
6631  return _isFunction(target[property]) ? _setterFunc : _isUndefined(target[property]) && target.setAttribute ? _setterAttribute : _setterPlain;
6632},
6633    _renderPlain = function _renderPlain(ratio, data) {
6634  return data.set(data.t, data.p, Math.round((data.s + data.c * ratio) * 10000) / 10000, data);
6635},
6636    _renderBoolean = function _renderBoolean(ratio, data) {
6637  return data.set(data.t, data.p, !!(data.s + data.c * ratio), data);
6638},
6639    _renderComplexString = function _renderComplexString(ratio, data) {
6640  var pt = data._pt,
6641      s = "";
6642
6643  if (!ratio && data.b) {
6644    //b = beginning string
6645    s = data.b;
6646  } else if (ratio === 1 && data.e) {
6647    //e = ending string
6648    s = data.e;
6649  } else {
6650    while (pt) {
6651      s = pt.p + (pt.m ? pt.m(pt.s + pt.c * ratio) : Math.round((pt.s + pt.c * ratio) * 10000) / 10000) + s; //we use the "p" property for the text inbetween (like a suffix). And in the context of a complex string, the modifier (m) is typically just Math.round(), like for RGB colors.
6652
6653      pt = pt._next;
6654    }
6655
6656    s += data.c; //we use the "c" of the PropTween to store the final chunk of non-numeric text.
6657  }
6658
6659  data.set(data.t, data.p, s, data);
6660},
6661    _renderPropTweens = function _renderPropTweens(ratio, data) {
6662  var pt = data._pt;
6663
6664  while (pt) {
6665    pt.r(ratio, pt.d);
6666    pt = pt._next;
6667  }
6668},
6669    _addPluginModifier = function _addPluginModifier(modifier, tween, target, property) {
6670  var pt = this._pt,
6671      next;
6672
6673  while (pt) {
6674    next = pt._next;
6675    pt.p === property && pt.modifier(modifier, tween, target);
6676    pt = next;
6677  }
6678},
6679    _killPropTweensOf = function _killPropTweensOf(property) {
6680  var pt = this._pt,
6681      hasNonDependentRemaining,
6682      next;
6683
6684  while (pt) {
6685    next = pt._next;
6686
6687    if (pt.p === property && !pt.op || pt.op === property) {
6688      _removeLinkedListItem(this, pt, "_pt");
6689    } else if (!pt.dep) {
6690      hasNonDependentRemaining = 1;
6691    }
6692
6693    pt = next;
6694  }
6695
6696  return !hasNonDependentRemaining;
6697},
6698    _setterWithModifier = function _setterWithModifier(target, property, value, data) {
6699  data.mSet(target, property, data.m.call(data.tween, value, data.mt), data);
6700},
6701    _sortPropTweensByPriority = function _sortPropTweensByPriority(parent) {
6702  var pt = parent._pt,
6703      next,
6704      pt2,
6705      first,
6706      last; //sorts the PropTween linked list in order of priority because some plugins need to do their work after ALL of the PropTweens were created (like RoundPropsPlugin and ModifiersPlugin)
6707
6708  while (pt) {
6709    next = pt._next;
6710    pt2 = first;
6711
6712    while (pt2 && pt2.pr > pt.pr) {
6713      pt2 = pt2._next;
6714    }
6715
6716    if (pt._prev = pt2 ? pt2._prev : last) {
6717      pt._prev._next = pt;
6718    } else {
6719      first = pt;
6720    }
6721
6722    if (pt._next = pt2) {
6723      pt2._prev = pt;
6724    } else {
6725      last = pt;
6726    }
6727
6728    pt = next;
6729  }
6730
6731  parent._pt = first;
6732}; //PropTween key: t = target, p = prop, r = renderer, d = data, s = start, c = change, op = overwriteProperty (ONLY populated when it's different than p), pr = priority, _next/_prev for the linked list siblings, set = setter, m = modifier, mSet = modifierSetter (the original setter, before a modifier was added)
6733
6734
6735var PropTween = /*#__PURE__*/function () {
6736  function PropTween(next, target, prop, start, change, renderer, data, setter, priority) {
6737    this.t = target;
6738    this.s = start;
6739    this.c = change;
6740    this.p = prop;
6741    this.r = renderer || _renderPlain;
6742    this.d = data || this;
6743    this.set = setter || _setterPlain;
6744    this.pr = priority || 0;
6745    this._next = next;
6746
6747    if (next) {
6748      next._prev = this;
6749    }
6750  }
6751
6752  var _proto4 = PropTween.prototype;
6753
6754  _proto4.modifier = function modifier(func, tween, target) {
6755    this.mSet = this.mSet || this.set; //in case it was already set (a PropTween can only have one modifier)
6756
6757    this.set = _setterWithModifier;
6758    this.m = func;
6759    this.mt = target; //modifier target
6760
6761    this.tween = tween;
6762  };
6763
6764  return PropTween;
6765}(); //Initialization tasks
6766
6767_forEachName(_callbackNames + "parent,duration,ease,delay,overwrite,runBackwards,startAt,yoyo,immediateRender,repeat,repeatDelay,data,paused,reversed,lazy,callbackScope,stringFilter,id,yoyoEase,stagger,inherit,repeatRefresh,keyframes,autoRevert,scrollTrigger", function (name) {
6768  return _reservedProps[name] = 1;
6769});
6770
6771_globals.TweenMax = _globals.TweenLite = Tween;
6772_globals.TimelineLite = _globals.TimelineMax = Timeline;
6773_globalTimeline = new Timeline({
6774  sortChildren: false,
6775  defaults: _defaults,
6776  autoRemoveChildren: true,
6777  id: "root",
6778  smoothChildTiming: true
6779});
6780_config.stringFilter = _colorStringFilter;
6781/*
6782 * --------------------------------------------------------------------------------------
6783 * GSAP
6784 * --------------------------------------------------------------------------------------
6785 */
6786
6787var _gsap = {
6788  registerPlugin: function registerPlugin() {
6789    for (var _len2 = arguments.length, args = new Array(_len2), _key2 = 0; _key2 < _len2; _key2++) {
6790      args[_key2] = arguments[_key2];
6791    }
6792
6793    args.forEach(function (config) {
6794      return _createPlugin(config);
6795    });
6796  },
6797  timeline: function timeline(vars) {
6798    return new Timeline(vars);
6799  },
6800  getTweensOf: function getTweensOf(targets, onlyActive) {
6801    return _globalTimeline.getTweensOf(targets, onlyActive);
6802  },
6803  getProperty: function getProperty(target, property, unit, uncache) {
6804    _isString(target) && (target = toArray(target)[0]); //in case selector text or an array is passed in
6805
6806    var getter = _getCache(target || {}).get,
6807        format = unit ? _passThrough : _numericIfPossible;
6808
6809    unit === "native" && (unit = "");
6810    return !target ? target : !property ? function (property, unit, uncache) {
6811      return format((_plugins[property] && _plugins[property].get || getter)(target, property, unit, uncache));
6812    } : format((_plugins[property] && _plugins[property].get || getter)(target, property, unit, uncache));
6813  },
6814  quickSetter: function quickSetter(target, property, unit) {
6815    target = toArray(target);
6816
6817    if (target.length > 1) {
6818      var setters = target.map(function (t) {
6819        return gsap.quickSetter(t, property, unit);
6820      }),
6821          l = setters.length;
6822      return function (value) {
6823        var i = l;
6824
6825        while (i--) {
6826          setters[i](value);
6827        }
6828      };
6829    }
6830
6831    target = target[0] || {};
6832
6833    var Plugin = _plugins[property],
6834        cache = _getCache(target),
6835        p = cache.harness && (cache.harness.aliases || {})[property] || property,
6836        // in case it's an alias, like "rotate" for "rotation".
6837    setter = Plugin ? function (value) {
6838      var p = new Plugin();
6839      _quickTween._pt = 0;
6840      p.init(target, unit ? value + unit : value, _quickTween, 0, [target]);
6841      p.render(1, p);
6842      _quickTween._pt && _renderPropTweens(1, _quickTween);
6843    } : cache.set(target, p);
6844
6845    return Plugin ? setter : function (value) {
6846      return setter(target, p, unit ? value + unit : value, cache, 1);
6847    };
6848  },
6849  isTweening: function isTweening(targets) {
6850    return _globalTimeline.getTweensOf(targets, true).length > 0;
6851  },
6852  defaults: function defaults(value) {
6853    value && value.ease && (value.ease = _parseEase(value.ease, _defaults.ease));
6854    return _mergeDeep(_defaults, value || {});
6855  },
6856  config: function config(value) {
6857    return _mergeDeep(_config, value || {});
6858  },
6859  registerEffect: function registerEffect(_ref2) {
6860    var name = _ref2.name,
6861        effect = _ref2.effect,
6862        plugins = _ref2.plugins,
6863        defaults = _ref2.defaults,
6864        extendTimeline = _ref2.extendTimeline;
6865    (plugins || "").split(",").forEach(function (pluginName) {
6866      return pluginName && !_plugins[pluginName] && !_globals[pluginName] && _warn(name + " effect requires " + pluginName + " plugin.");
6867    });
6868
6869    _effects[name] = function (targets, vars, tl) {
6870      return effect(toArray(targets), _setDefaults(vars || {}, defaults), tl);
6871    };
6872
6873    if (extendTimeline) {
6874      Timeline.prototype[name] = function (targets, vars, position) {
6875        return this.add(_effects[name](targets, _isObject(vars) ? vars : (position = vars) && {}, this), position);
6876      };
6877    }
6878  },
6879  registerEase: function registerEase(name, ease) {
6880    _easeMap[name] = _parseEase(ease);
6881  },
6882  parseEase: function parseEase(ease, defaultEase) {
6883    return arguments.length ? _parseEase(ease, defaultEase) : _easeMap;
6884  },
6885  getById: function getById(id) {
6886    return _globalTimeline.getById(id);
6887  },
6888  exportRoot: function exportRoot(vars, includeDelayedCalls) {
6889    if (vars === void 0) {
6890      vars = {};
6891    }
6892
6893    var tl = new Timeline(vars),
6894        child,
6895        next;
6896    tl.smoothChildTiming = _isNotFalse(vars.smoothChildTiming);
6897
6898    _globalTimeline.remove(tl);
6899
6900    tl._dp = 0; //otherwise it'll get re-activated when adding children and be re-introduced into _globalTimeline's linked list (then added to itself).
6901
6902    tl._time = tl._tTime = _globalTimeline._time;
6903    child = _globalTimeline._first;
6904
6905    while (child) {
6906      next = child._next;
6907
6908      if (includeDelayedCalls || !(!child._dur && child instanceof Tween && child.vars.onComplete === child._targets[0])) {
6909        _addToTimeline(tl, child, child._start - child._delay);
6910      }
6911
6912      child = next;
6913    }
6914
6915    _addToTimeline(_globalTimeline, tl, 0);
6916
6917    return tl;
6918  },
6919  utils: {
6920    wrap: wrap,
6921    wrapYoyo: wrapYoyo,
6922    distribute: distribute,
6923    random: random,
6924    snap: snap,
6925    normalize: normalize,
6926    getUnit: getUnit,
6927    clamp: clamp,
6928    splitColor: splitColor,
6929    toArray: toArray,
6930    mapRange: mapRange,
6931    pipe: pipe,
6932    unitize: unitize,
6933    interpolate: interpolate,
6934    shuffle: shuffle
6935  },
6936  install: _install,
6937  effects: _effects,
6938  ticker: _ticker,
6939  updateRoot: Timeline.updateRoot,
6940  plugins: _plugins,
6941  globalTimeline: _globalTimeline,
6942  core: {
6943    PropTween: PropTween,
6944    globals: _addGlobal,
6945    Tween: Tween,
6946    Timeline: Timeline,
6947    Animation: Animation,
6948    getCache: _getCache,
6949    _removeLinkedListItem: _removeLinkedListItem,
6950    suppressOverwrites: function suppressOverwrites(value) {
6951      return _suppressOverwrites = value;
6952    }
6953  }
6954};
6955
6956_forEachName("to,from,fromTo,delayedCall,set,killTweensOf", function (name) {
6957  return _gsap[name] = Tween[name];
6958});
6959
6960_ticker.add(Timeline.updateRoot);
6961
6962_quickTween = _gsap.to({}, {
6963  duration: 0
6964}); // ---- EXTRA PLUGINS --------------------------------------------------------
6965
6966var _getPluginPropTween = function _getPluginPropTween(plugin, prop
6966) {
6967  var pt = plugin._pt;
6968
6969  while (pt && pt.p !== prop && pt.op !== prop && pt.fp !== prop) {
6970    pt = pt._next;
6971  }
6972
6973  return pt;
6974},
6975    _addModifiers = function _addModifiers(tween, modifiers) {
6976  var targets = tween._targets,
6977      p,
6978      i,
6979      pt;
6980
6981  for (p in modifiers) {
6982    i = targets.length;
6983
6984    while (i--) {
6985      pt = tween._ptLookup[i][p];
6986
6987      if (pt && (pt = pt.d)) {
6988        if (pt._pt) {
6989          // is a plugin
6990          pt = _getPluginPropTween(pt, p);
6991        }
6992
6993        pt && pt.modifier && pt.modifier(modifiers[p], tween, targets[i], p);
6994      }
6995    }
6996  }
6997},
6998    _buildModifierPlugin = function _buildModifierPlugin(name, modifier) {
6999  return {
7000    name: name,
7001    rawVars: 1,
7002    //don't pre-process function-based values or "random()" strings.
7003    init: function init(target, vars, tween) {
7004      tween._onInit = function (tween) {
7005        var temp, p;
7006
7007        if (_isString(vars)) {
7008          temp = {};
7009
7010          _forEachName(vars, function (name) {
7011            return temp[name] = 1;
7012          }); //if the user passes in a comma-delimited list of property names to roundProps, like "x,y", we round to whole numbers.
7013
7014
7015          vars = temp;
7016        }
7017
7018        if (modifier) {
7019          temp = {};
7020
7021          for (p in vars) {
7022            temp[p] = modifier(vars[p]);
7023          }
7024
7025          vars = temp;
7026        }
7027
7028        _addModifiers(tween, vars);
7029      };
7030    }
7031  };
7032}; //register core plugins
7033
7034
7035var gsap = _gsap.registerPlugin({
7036  name: "attr",
7037  init: function init(target, vars, tween, index, targets) {
7038    var p, pt;
7039
7040    for (p in vars) {
7041      pt = this.add(target, "setAttribute", (target.getAttribute(p) || 0) + "", vars[p], index, targets, 0, 0, p);
7042      pt && (pt.op = p);
7043
7044      this._props.push(p);
7045    }
7046  }
7047}, {
7048  name: "endArray",
7049  init: function init(target, value) {
7050    var i = value.length;
7051
7052    while (i--) {
7053      this.add(target, i, target[i] || 0, value[i]);
7054    }
7055  }
7056}, _buildModifierPlugin("roundProps", _roundModifier), _buildModifierPlugin("modifiers"), _buildModifierPlugin("snap", snap)) || _gsap; //to prevent the core plugins from being dropped via aggressive tree shaking, we must include them in the variable declaration in this way.
7057
7058Tween.version = Timeline.version = gsap.version = "3.6.0";
7059_coreReady = 1;
7060
7061if (_windowExists()) {
7062  _wake();
7063}
7064
7065var Power0 = _easeMap.Power0,
7066    Power1 = _easeMap.Power1,
7067    Power2 = _easeMap.Power2,
7068    Power3 = _easeMap.Power3,
7069    Power4 = _easeMap.Power4,
7070    Linear = _easeMap.Linear,
7071    Quad = _easeMap.Quad,
7072    Cubic = _easeMap.Cubic,
7073    Quart = _easeMap.Quart,
7074    Quint = _easeMap.Quint,
7075    Strong = _easeMap.Strong,
7076    Elastic = _easeMap.Elastic,
7077    Back = _easeMap.Back,
7078    SteppedEase = _easeMap.SteppedEase,
7079    Bounce = _easeMap.Bounce,
7080    Sine = _easeMap.Sine,
7081    Expo = _easeMap.Expo,
7082    Circ = _easeMap.Circ;
7083
7084 //export some internal methods/orojects for use in CSSPlugin so that we can externalize that file and allow custom builds that exclude it.
7085
7086
7087
7088/***/ }),
7089/* 11 */
7090/***/ (function(module, exports, __webpack_require__) {
7091
7092var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_RESULT__;/**
7093 * EvEmitter v1.1.0
7094 * Lil' event emitter
7095 * MIT License
7096 */
7097
7098/* jshint unused: true, undef: true, strict: true */
7099
7100( function( global, factory ) {
7101  // universal module definition
7102  /* jshint strict: false */ /* globals define, module, window */
7103  if ( true ) {
7104    // AMD - RequireJS
7105    !(__WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
7106				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
7107				(__WEBPACK_AMD_DEFINE_FACTORY__.call(exports, __webpack_require__, exports, module)) :
7108				__WEBPACK_AMD_DEFINE_FACTORY__),
7109				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
7110  } else if ( typeof module == 'object' && module.exports ) {
7111    // CommonJS - Browserify, Webpack
7112    module.exports = factory();
7113  } else {
7114    // Browser globals
7115    global.EvEmitter = factory();
7116  }
7117
7118}( typeof window != 'undefined' ? window : this, function() {
7119
7120"use strict";
7121
7122function EvEmitter() {}
7123
7124var proto = EvEmitter.prototype;
7125
7126proto.on = function( eventName, listener ) {
7127  if ( !eventName || !listener ) {
7128    return;
7129  }
7130  // set events hash
7131  var events = this._events = this._events || {};
7132  // set listeners array
7133  var listeners = events[ eventName ] = events[ eventName ] || [];
7134  // only add once
7135  if ( listeners.indexOf( listener ) == -1 ) {
7136    listeners.push( listener );
7137  }
7138
7139  return this;
7140};
7141
7142proto.once = function( eventName, listener ) {
7143  if ( !eventName || !listener ) {
7144    return;
7145  }
7146  // add event
7147  this.on( eventName, listener );
7148  // set once flag
7149  // set onceEvents hash
7150  var onceEvents = this._onceEvents = this._onceEvents || {};
7151  // set onceListeners object
7152  var onceListeners = onceEvents[ eventName ] = onceEvents[ eventName ] || {};
7153  // set flag
7154  onceListeners[ listener ] = true;
7155
7156  return this;
7157};
7158
7159proto.off = function( eventName, listener ) {
7160  var listeners = this._events && this._events[ eventName ];
7161  if ( !listeners || !listeners.length ) {
7162    return;
7163  }
7164  var index = listeners.indexOf( listener );
7165  if ( index != -1 ) {
7166    listeners.splice( index, 1 );
7167  }
7168
7169  return this;
7170};
7171
7172proto.emitEvent = function( eventName, args ) {
7173  var listeners = this._events && this._events[ eventName ];
7174  if ( !listeners || !listeners.length ) {
7175    return;
7176  }
7177  // copy over to avoid interference if .off() in listener
7178  listeners = listeners.slice(0);
7179  args = args || [];
7180  // once stuff
7181  var onceListeners = this._onceEvents && this._onceEvents[ eventName ];
7182
7183  for ( var i=0; i < listeners.length; i++ ) {
7184    var listener = listeners[i]
7185    var isOnce = onceListeners && onceListeners[ listener ];
7186    if ( isOnce ) {
7187      // remove listener
7188      // remove before trigger to prevent recursion
7189      this.off( eventName, listener );
7190      // unset once flag
7191      delete onceListeners[ listener ];
7192    }
7193    // trigger listener
7194    listener.apply( this, args );
7195  }
7196
7197  return this;
7198};
7199
7200proto.allOff = function() {
7201  delete this._events;
7202  delete this._onceEvents;
7203};
7204
7205return EvEmitter;
7206
7207}));
7208
7209
7210/***/ }),
7211/* 12 */
7212/***/ (function(module, exports, __webpack_require__) {
7213
7214var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_RESULT__;/**
7215 * matchesSelector v2.0.2
7216 * matchesSelector( element, '.selector' )
7217 * MIT license
7218 */
7219
7220/*jshint browser: true, strict: true, undef: true, unused: true */
7221
7222( function( window, factory ) {
7223  /*global define: false, module: false */
7224  'use strict';
7225  // universal module definition
7226  if ( true ) {
7227    // AMD
7228    !(__WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
7229				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
7230				(__WEBPACK_AMD_DEFINE_FACTORY__.call(exports, __webpack_require__, exports, module)) :
7231				__WEBPACK_AMD_DEFINE_FACTORY__),
7232				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
7233  } else if ( typeof module == 'object' && module.exports ) {
7234    // CommonJS
7235    module.exports = factory();
7236  } else {
7237    // browser global
7238    window.matchesSelector = factory();
7239  }
7240
7241}( window, function factory() {
7242  'use strict';
7243
7244  var matchesMethod = ( function() {
7245    var ElemProto = window.Element.prototype;
7246    // check for the standard method name first
7247    if ( ElemProto.matches ) {
7248      return 'matches';
7249    }
7250    // check un-prefixed
7251    if ( ElemProto.matchesSelector ) {
7252      return 'matchesSelector';
7253    }
7254    // check vendor prefixes
7255    var prefixes = [ 'webkit', 'moz', 'ms', 'o' ];
7256
7257    for ( var i=0; i < prefixes.length; i++ ) {
7258      var prefix = prefixes[i];
7259      var method = prefix + 'MatchesSelector';
7260      if ( ElemProto[ method ] ) {
7261        return method;
7262      }
7263    }
7264  })();
7265
7266  return function matchesSelector( elem, selector ) {
7267    return elem[ matchesMethod ]( selector );
7268  };
7269
7270}));
7271
7272
7273/***/ }),
7274/* 13 */
7275/***/ (function(module, exports, __webpack_require__) {
7276
7277__webpack_require__(14);
7278module.exports = __webpack_require__(47);
7279
7280
7281/***/ }),
7282/* 14 */
7283/***/ (function(module, __webpack_exports__, __webpack_require__) {
7284
7285"use strict";
7286Object.defineProperty(__webpack_exports__, "__esModule", { value: true });
7287/* WEBPACK VAR INJECTION */(function(jQuery) {/* harmony import */ var __WEBPACK_IMPORTED_MODULE_0_jquery__ = __webpack_require__(0);
7288/* harmony import */ var __WEBPACK_IMPORTED_MODULE_0_jquery___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_0_jquery__);
7289/* harmony import */ var __WEBPACK_IMPORTED_MODULE_1_focus_visible__ = __webpack_require__(15);
7290/* harmony import */ var __WEBPACK_IMPORTED_MODULE_1_focus_visible___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_1_focus_visible__);
7291/* harmony import */ var __WEBPACK_IMPORTED_MODULE_2__util_Router__ = __webpack_require__(16);
7292/* harmony import */ var __WEBPACK_IMPORTED_MODULE_3__routes_common__ = __webpack_require__(18);
7293/* harmony import */ var __WEBPACK_IMPORTED_MODULE_4__routes_home__ = __webpack_require__(40);
7294/* harmony import */ var __WEBPACK_IMPORTED_MODULE_5__routes_about__ = __webpack_require__(41);
7295/* harmony import */ var __WEBPACK_IMPORTED_MODULE_6__routes_contributors__ = __webpack_require__(42);
7296/* harmony import */ var __WEBPACK_IMPORTED_MODULE_7__routes_topicGuide__ = __webpack_require__(43);
7297/* harmony import */ var __WEBPACK_IMPORTED_MODULE_8__routes_episodes__ = __webpack_require__(44);
7298/* harmony import */ var __WEBPACK_IMPORTED_MODULE_9__routes_singleVideo__ = __webpack_require__(45);
7299/* harmony import */ var __WEBPACK_IMPORTED_MODULE_10__routes_singlePlaylist__ = __webpack_require__(46);
7300// import external dependencies
7301
7302
7303
7304// Import everything from autoload
7305//;
7306
7307// import local dependencies
7308
7309
7310
7311
7312
7313
7314
7315
7316
7317// import archive from './routes/taxonomyTopic';
7318
7319/** Populate Router instance with DOM routes */
7320var routes = new __WEBPACK_IMPORTED_MODULE_2__util_Router__["a" /* default */]({
7321    // All pages 
7322    common: __WEBPACK_IMPORTED_MODULE_3__routes_common__["a" /* default */],
7323    // Home page
7324    home: __WEBPACK_IMPORTED_MODULE_4__routes_home__["a" /* default */],
7325    // About Us page, note the change from about-us to aboutUs.
7326    aboutUs: __WEBPACK_IMPORTED_MODULE_5__routes_about__["a" /* default */],
7327    contributors: __WEBPACK_IMPORTED_MODULE_6__routes_contributors__["a" /* default */],
7328    singleVideo: __WEBPACK_IMPORTED_MODULE_9__routes_singleVideo__["a" /* default */],
7329    singlePlaylist: __WEBPACK_IMPORTED_MODULE_10__routes_singlePlaylist__["a" /* default */],
7330    episodes: __WEBPACK_IMPORTED_MODULE_8__routes_episodes__["a" /* default */],
7331    topicGuide: __WEBPACK_IMPORTED_MODULE_7__routes_topicGuide__["a" /* default */],
7332    // archive,
7333});
7334
7335// Load Events
7336jQuery(document).ready(function () { return routes.loadEvents(); });
7337
7338/* WEBPACK VAR INJECTION */}.call(__webpack_exports__, __webpack_require__(0)))
7339
7340/***/ }),
7341/* 15 */
7342/***/ (function(module, exports, __webpack_require__) {
7343
7344(function (global, factory) {
7345   true ? factory() :
7346  typeof define === 'function' && define.amd ? define(factory) :
7347  (factory());
7348}(this, (function () { 'use strict';
7349
7350  /**
7351   * Applies the :focus-visible polyfill at the given scope.
7352   * A scope in this case is either the top-level Document or a Shadow Root.
7353   *
7354   * @param {(Document|ShadowRoot)} scope
7355   * @see https://github.com/WICG/focus-visible
7356   */
7357  function applyFocusVisiblePolyfill(scope) {
7358    var hadKeyboardEvent = true;
7359    var hadFocusVisibleRecently = false;
vendor: 4,705 bytes, lines 7360-7519
7360    var hadFocusVisibleRecentlyTimeout = null;
7361
7362    var inputTypesAllowlist = {
7363      text: true,
7364      search: true,
7365      url: true,
7366      tel: true,
7367      email: true,
7368      password: true,
7369      number: true,
7370      date: true,
7371      month: true,
7372      week: true,
7373      time: true,
7374      datetime: true,
7375      'datetime-local': true
7376    };
7377
7378    /**
7379     * Helper function for legacy browsers and iframes which sometimes focus
7380     * elements like document, body, and non-interactive SVG.
7381     * @param {Element} el
7382     */
7383    function isValidFocusTarget(el) {
7384      if (
7385        el &&
7386        el !== document &&
7387        el.nodeName !== 'HTML' &&
7388        el.nodeName !== 'BODY' &&
7389        'classList' in el &&
7390        'contains' in el.classList
7391      ) {
7392        return true;
7393      }
7394      return false;
7395    }
7396
7397    /**
7398     * Computes whether the given element should automatically trigger the
7399     * `focus-visible` class being added, i.e. whether it should always match
7400     * `:focus-visible` when focused.
7401     * @param {Element} el
7402     * @return {boolean}
7403     */
7404    function focusTriggersKeyboardModality(el) {
7405      var type = el.type;
7406      var tagName = el.tagName;
7407
7408      if (tagName === 'INPUT' && inputTypesAllowlist[type] && !el.readOnly) {
7409        return true;
7410      }
7411
7412      if (tagName === 'TEXTAREA' && !el.readOnly) {
7413        return true;
7414      }
7415
7416      if (el.isContentEditable) {
7417        return true;
7418      }
7419
7420      return false;
7421    }
7422
7423    /**
7424     * Add the `focus-visible` class to the given element if it was not added by
7425     * the author.
7426     * @param {Element} el
7427     */
7428    function addFocusVisibleClass(el) {
7429      if (el.classList.contains('focus-visible')) {
7430        return;
7431      }
7432      el.classList.add('focus-visible');
7433      el.setAttribute('data-focus-visible-added', '');
7434    }
7435
7436    /**
7437     * Remove the `focus-visible` class from the given element if it was not
7438     * originally added by the author.
7439     * @param {Element} el
7440     */
7441    function removeFocusVisibleClass(el) {
7442      if (!el.hasAttribute('data-focus-visible-added')) {
7443        return;
7444      }
7445      el.classList.remove('focus-visible');
7446      el.removeAttribute('data-focus-visible-added');
7447    }
7448
7449    /**
7450     * If the most recent user interaction was via the keyboard;
7451     * and the key press did not include a meta, alt/option, or control key;
7452     * then the modality is keyboard. Otherwise, the modality is not keyboard.
7453     * Apply `focus-visible` to any current active element and keep track
7454     * of our keyboard modality state with `hadKeyboardEvent`.
7455     * @param {KeyboardEvent} e
7456     */
7457    function onKeyDown(e) {
7458      if (e.metaKey || e.altKey || e.ctrlKey) {
7459        return;
7460      }
7461
7462      if (isValidFocusTarget(scope.activeElement)) {
7463        addFocusVisibleClass(scope.activeElement);
7464      }
7465
7466      hadKeyboardEvent = true;
7467    }
7468
7469    /**
7470     * If at any point a user clicks with a pointing device, ensure that we change
7471     * the modality away from keyboard.
7472     * This avoids the situation where a user presses a key on an already focused
7473     * element, and then clicks on a different element, focusing it with a
7474     * pointing device, while we still think we're in keyboard modality.
7475     * @param {Event} e
7476     */
7477    function onPointerDown(e) {
7478      hadKeyboardEvent = false;
7479    }
7480
7481    /**
7482     * On `focus`, add the `focus-visible` class to the target if:
7483     * - the target received focus as a result of keyboard navigation, or
7484     * - the event target is an element that will likely require interaction
7485     *   via the keyboard (e.g. a text box)
7486     * @param {Event} e
7487     */
7488    function onFocus(e) {
7489      // Prevent IE from focusing the document or HTML element.
7490      if (!isValidFocusTarget(e.target)) {
7491        return;
7492      }
7493
7494      if (hadKeyboardEvent || focusTriggersKeyboardModality(e.target)) {
7495        addFocusVisibleClass(e.target);
7496      }
7497    }
7498
7499    /**
7500     * On `blur`, remove the `focus-visible` class from the target.
7501     * @param {Event} e
7502     */
7503    function onBlur(e) {
7504      if (!isValidFocusTarget(e.target)) {
7505        return;
7506      }
7507
7508      if (
7509        e.target.classList.contains('focus-visible') ||
7510        e.target.hasAttribute('data-focus-visible-added')
7511      ) {
7512        // To detect a tab/window switch, we look for a blur event followed
7513        // rapidly by a visibility change.
7514        // If we don't see a visibility change within 100ms, it's probably a
7515        // regular focus change.
7516        hadFocusVisibleRecently = true;
7517        window.clearTimeout(hadFocusVisibleRecentlyTimeout);
7518        hadFocusVisibleRecentlyTimeout = window.setTimeout(function() {
7519          hadFocusVisibleRecently = false;
7520        }, 100);
7521        removeFocusVisibleClass(e.target);
7522      }
7523    }
7524
7525    /**
7526     * If the user changes tabs, keep track of whether or not the previously
7527     * focused element had .focus-visible.
7528     * @param {Event} e
7529     */
7530    function onVisibilityChange(e) {
7531      if (document.visibilityState === 'hidden') {
7532        // If the tab becomes active again, the browser will handle calling focus
7533        // on the element (Safari actually calls it twice).
7534        // If this tab change caused a blur on an element with focus-visible,
7535        // re-apply the class when the user switches back to the tab.
7536        if (hadFocusVisibleRecently) {
7537          hadKeyboardEvent = true;
7538        }
7539        addInitialPointerMoveListeners();
7540      }
7541    }
7542
7543    /**
7544     * Add a group of listeners to detect usage of any pointing devices.
7545     * These listeners will be added when the polyfill first loads, and anytime
7546     * the window is blurred, so that they are active when the window regains
7547     * focus.
7548     */
7549    function addInitialPointerMoveListeners() {
7550      document.addEventListener('mousemove', onInitialPointerMove);
7551      document.addEventListener('mousedown', onInitialPointerMove);
7552      document.addEventListener('mouseup', onInitialPointerMove);
7553      document.addEventListener('pointermove', onInitialPointerMove);
7554      document.addEventListener('pointerdown', onInitialPointerMove);
7555      document.addEventListener('pointerup', onInitialPointerMove);
7556      document.addEventListener('touchmove', onInitialPointerMove);
7557      document.addEventListener('touchstart', onInitialPointerMove);
7558      document.addEventListener('touchend', onInitialPointerMove);
7559    }
7560
7561    function removeInitialPointerMoveListeners() {
7562      document.removeEventListener('mousemove', onInitialPointerMove);
7563      document.removeEventListener('mousedown', onInitialPointerMove);
7564      document.removeEventListener('mouseup', onInitialPointerMove);
7565      document.removeEventListener('pointermove', onInitialPointerMove);
7566      document.removeEventListener('pointerdown', onInitialPointerMove);
7567      document.removeEventListener('pointerup', onInitialPointerMove);
7568      document.removeEventListener('touchmove', onInitialPointerMove);
7569      document.removeEventListener('touchstart', onInitialPointerMove);
7570      document.removeEventListener('touchend', onInitialPointerMove);
7571    }
7572
7573    /**
7574     * When the polfyill first loads, assume the user is in keyboard modality.
7575     * If any event is received from a pointing device (e.g. mouse, pointer,
7576     * touch), turn off keyboard modality.
7577     * This accounts for situations where focus enters the page from the URL bar.
7578     * @param {Event} e
7579     */
7580    function onInitialPointerMove(e) {
7581      // Work around a Safari quirk that fires a mousemove on <html> whenever the
7582      // window blurs, even if you're tabbing out of the page. ¯\_(ツ)_/¯
7583      if (e.target.nodeName && e.target.nodeName.toLowerCase() === 'html') {
7584        return;
7585      }
7586
7587      hadKeyboardEvent = false;
7588      removeInitialPointerMoveListeners();
7589    }
7590
7591    // For some kinds of state, we are interested in changes at the global scope
7592    // only. For example, global pointer input, global key presses and global
7593    // visibility change should affect the state at every scope:
7594    document.addEventListener('keydown', onKeyDown, true);
7595    document.addEventListener('mousedown', onPointerDown, true);
7596    document.addEventListener('pointerdown', onPointerDown, true);
7597    document.addEventListener('touchstart', onPointerDown, true);
7598    document.addEventListener('visibilitychange', onVisibilityChange, true);
7599
7600    addInitialPointerMoveListeners();
7601
7602    // For focus and blur, we specifically care about state changes in the local
7603    // scope. This is because focus / blur events that originate from within a
7604    // shadow root are not re-dispatched from the host element if it was already
7605    // the active element in its own scope:
7606    scope.addEventListener('focus', onFocus, true);
7607    scope.addEventListener('blur', onBlur, true);
7608
7609    // We detect that a node is a ShadowRoot by ensuring that it is a
7610    // DocumentFragment and also has a host property. This check covers native
7611    // implementation and polyfill implementation transparently. If we only cared
7612    // about the native implementation, we could just check if the scope was
7613    // an instance of a ShadowRoot.
7614    if (scope.nodeType === Node.DOCUMENT_FRAGMENT_NODE && scope.host) {
7615      // Since a ShadowRoot is a special kind of DocumentFragment, it does not
7616      // have a root element to add a class to. So, we add this attribute to the
7617      // host element instead:
7618      scope.host.setAttribute('data-js-focus-visible', '');
7619    } else if (scope.nodeType === Node.DOCUMENT_NODE) {
7620      document.documentElement.classList.add('js-focus-visible');
7621      document.documentElement.setAttribute('data-js-focus-visible', '');
7622    }
7623  }
7624
7625  // It is important to wrap all references to global window and document in
7626  // these checks to support server-side rendering use cases
7627  // @see https://github.com/WICG/focus-visible/issues/199
7628  if (typeof window !== 'undefined' && typeof document !== 'undefined') {
7629    // Make the polyfill helper globally available. This can be used as a signal
7630    // to interested libraries that wish to coordinate with the polyfill for e.g.,
7631    // applying the polyfill to a shadow root:
7632    window.applyFocusVisiblePolyfill = applyFocusVisiblePolyfill;
7633
7634    // Notify interested libraries of the polyfill's presence, in case the
7635    // polyfill was loaded lazily:
7636    var event;
7637
7638    try {
7639      event = new CustomEvent('focus-visible-polyfill-ready');
7640    } catch (error) {
7641      // IE11 does not support using CustomEvent as a constructor directly:
7642      event = document.createEvent('CustomEvent');
7643      event.initCustomEvent('focus-visible-polyfill-ready', false, false, {});
7644    }
7645
7646    window.dispatchEvent(event);
7647  }
7648
7649  if (typeof document !== 'undefined') {
7650    // Apply the polyfill to the global document, so that no JavaScript
7651    // coordination is required to use the polyfill in the top-level document:
7652    applyFocusVisiblePolyfill(document);
7653  }
7654
7655})));
7656
7657
7658/***/ }),
7659/* 16 */
7660/***/ (function(module, __webpack_exports__, __webpack_require__) {
7661
7662"use strict";
7663/* harmony import */ var __WEBPACK_IMPORTED_MODULE_0__camelCase__ = __webpack_require__(17);
7664
7665
7666/**
7667 * DOM-based Routing
7668 *
7669 * Based on {@link http://goo.gl/EUTi53|Markup-based Unobtrusive Comprehensive DOM-ready Execution} by Paul Irish
7670 *
7671 * The routing fires all common scripts, followed by the page specific scripts.
7672 * Add additional events for more control over timing e.g. a finalize event
7673 */
7674var Router = function Router(routes) {
7675  this.routes = routes;
7676};
7677
7678/**
7679 * Fire Router events
7680 * @param {string} route DOM-based route derived from body classes (`<body class="...">`)
7681 * @param {string} [event] Events on the route. By default, `init` and `finalize` events are called.
7682 * @param {string} [arg] Any custom argument to be passed to the event.
7683 */
7684Router.prototype.fire = function fire (route, event, arg) {
7685    if ( event === void 0 ) event = 'init';
7686
7687  document.dispatchEvent(new CustomEvent('routed', {
7688    bubbles: true,
7689    detail: {
7690      route: route,
7691      fn: event,
7692    },
7693  }));
7694    
7695  var fire = route !== '' && this.routes[route] && typeof this.routes[route][event] === 'function';
7696  if (fire) {
7697    this.routes[route][event](arg);
7698  }
7699};
7700
7701/**
7702 * Automatically load and fire Router events
7703 *
7704 * Events are fired in the following order:
7705 ** common init
7706 ** page-specific init
7707 ** page-specific finalize
7708 ** common finalize
7709 */
7710Router.prototype.loadEvents = function loadEvents () {
7711    var this$1 = this;
7712
7713  // Fire common init JS
7714  this.fire('common');
7715
7716  // Fire page-specific init JS, and then finalize JS
7717  document.body.className
7718    .toLowerCase()
7719    .replace(/-/g, '_')
7720    .split(/\s+/)
7721    .map(__WEBPACK_IMPORTED_MODULE_0__camelCase__["a" /* default */])
7722    .forEach(function (className) {
7723      this$1.fire(className);
7724      this$1.fire(className, 'finalize');
7725    });
7726
7727  // Fire common finalize JS
7728  this.fire('common', 'finalize');
7729};
7730
7731/* harmony default export */ __webpack_exports__["a"] = (Router);
7732
7733
7734/***/ }),
7735/* 17 */
7736/***/ (function(module, __webpack_exports__, __webpack_require__) {
7737
7738"use strict";
7739/**
7740 * the most terrible camelizer on the internet, guaranteed!
7741 * @param {string} str String that isn't camel-case, e.g., CAMeL_CaSEiS-harD
7742 * @return {string} String converted to camel-case, e.g., camelCaseIsHard
7743 */
7744/* harmony default export */ __webpack_exports__["a"] = (function (str) { return ("" + (str.charAt(0).toLowerCase()) + (str.replace(/[\W_]/g, '|').split('|')
7745  .map(function (part) { return ("" + (part.charAt(0).toUpperCase()) + (part.slice(1))); })
7746  .join('')
7747  .slice(1))); });;
7748
7749
7750/***/ }),
7751/* 18 */
7752/***/ (function(module, __webpack_exports__, __webpack_require__) {
7753
7754"use strict";
7755/* WEBPACK VAR INJECTION */(function($, jQuery) {/* harmony import */ var __WEBPACK_IMPORTED_MODULE_0_gsap__ = __webpack_require__(19);
7756/* harmony import */ var __WEBPACK_IMPORTED_MODULE_1_gsap_ScrollTrigger__ = __webpack_require__(21);
7757/* harmony import */ var __WEBPACK_IMPORTED_MODULE_2_slick_carousel__ = __webpack_require__(22);
7758/* harmony import */ var __WEBPACK_IMPORTED_MODULE_2_slick_carousel___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_2_slick_carousel__);
7759/* harmony import */ var __WEBPACK_IMPORTED_MODULE_3__util_playerLoader__ = __webpack_require__(4);
7760/* harmony import */ var __WEBPACK_IMPORTED_MODULE_4_magnific_popup__ = __webpack_require__(23);
7761/* harmony import */ var __WEBPACK_IMPORTED_MODULE_4_magnific_popup___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_4_magnific_popup__);
7762/* harmony import */ var __WEBPACK_IMPORTED_MODULE_5_imagesloaded__ = __webpack_require__(7);
7763/* harmony import */ var __WEBPACK_IMPORTED_MODULE_5_imagesloaded___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_5_imagesloaded__);
7764/* harmony import */ var __WEBPACK_IMPORTED_MODULE_6_isotope_layout__ = __webpack_require__(8);
7765/* harmony import */ var __WEBPACK_IMPORTED_MODULE_6_isotope_layout___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_6_isotope_layout__);
7766/* harmony import */ var __WEBPACK_IMPORTED_MODULE_7_infinite_scroll__ = __webpack_require__(9);
7767/* harmony import */ var __WEBPACK_IMPORTED_MODULE_7_infinite_scroll___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_7_infinite_scroll__);
7768/* harmony import */ var __WEBPACK_IMPORTED_MODULE_8__selectize_selectize__ = __webpack_require__(37);
7769/* harmony import */ var __WEBPACK_IMPORTED_MODULE_8__selectize_selectize___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_8__selectize_selectize__);
7770
7771
7772
7773
7774
7775
7776
7777
7778
7779
7780/* harmony default export */ __webpack_exports__["a"] = ({
7781    ajaxLoadMore: function ajaxLoadMore() {
7782        // AJAX Load More
7783        function visc_load_more() {
7784            // eslint-disable-next-line no-undef
7785            if (visceral_vars !== undefined) {
7786                var data = {
7787                    action: 'visc_load_more',
7788                    // eslint-disable-next-line no-undef
7789                    query: visceral_vars.query,
7790                    // eslint-disable-next-line no-undef
7791                    paged: visceral_vars.current_page,
7792                    // eslint-disable-next-line no-undef
7793                    security: visceral_vars.security,
7794                };
7795
7796                var $button = $('.btn--load-more');
7797
7798                $.ajax({
7799                    // eslint-disable-next-line no-undef
7800                    url: visceral_vars.ajaxurl, // AJAX handler
7801                    data: data,
7802                    type: 'POST',
7803                    beforeSend: function () {
7804                        $button.find('span').text('Loading...'); // change the button text, you can also add a preloader image
7805                    },
7806                    complete: function () {
7807                        this.itemReveal();
7808                    },
7809                    success: function (data) {
7810                        $button.blur();
7811                        if (data) {
7812                            $button.find('span').text('Load More');
7813
7814                            var $postsContainer = $(
7815                                '.posts-list-container > div'
7816                            );
7817                            $postsContainer.append(data);
7818                            // eslint-disable-next-line no-undef
7819                            visceral_vars.current_page++;
7820                            // eslint-disable-next-line no-undef
7821                            if (
7822                                // eslint-disable-next-line no-undef
7823                                visceral_vars.current_page ==
7824                                // eslint-disable-next-line no-undef
7825                                visceral_vars.max_page
7826                            ) {
7827                                $button.remove(); // if last page, remove the button
7828                            }
7829                        } else {
7830                            $button.remove(); // if last page, remove the button
7831                        }
7832                    },
7833                });
7834            }
7835        }
7836
7837        $('.btn--load-more').on('click', function () {
7838            visc_load_more();
7839        });
7840    },
7841    buttons: function buttons() {
7842        var btnPulse = document.querySelectorAll('.btn-pulse');
7843
7844        if (btnPulse) {
7845            btnPulse.forEach(function (btn) {
7846                btn.innerHTML = '<span class="btn-pulse__outer" aria-hidden="true"><span class="btn-pulse__inner"></span></span>' + btn.innerHTML;
7847            });
7848        }
7849    },
7850    header: function header() {
7851        /** FIXED HEADER ANIMATION **/
7852        var didScroll = false,
7853            scrollOffset = 100;
7854
7855        function scrollY() {
7856            return window.pageYOffset || document.documentElement.scrollTop;
7857        }
7858
7859        function scrollPage() {
7860            var sy = scrollY();
7861            if (sy > scrollOffset) {
7862                $('.site-header--fixed').addClass(
7863                    'site-header--scroll-triggered'
7864                );
7865            } else {
7866                $('.site-header--fixed').removeClass(
7867                    'site-header--scroll-triggered'
7868                );
7869            }
7870            didScroll = false;
7871        }
7872
7873        window.addEventListener('load', scrollPage);
7874        window.addEventListener(
7875            'scroll',
7876            function () {
7877                // eslint-disable-line no-unused-vars
7878                if (!didScroll) {
7879                    didScroll = true;
7880                    setTimeout(scrollPage, 100);
7881                }
7882            },
7883            false
7884        );
7885        /** END FIXED HEADER ANIMATION **/
7886
7887        /**  SEARCH OVERLAY **/
7888        var body = document.querySelector('body');
7889        var siteSearch = document.querySelector('.site-search');
7890        var searchWrap = document.querySelector('.site-header__search-wrap');
7891        var searchIcon = document.querySelector('.site-header__search-icon');
7892
7893        if (searchIcon) {
7894            searchIcon.addEventListener('click', function (e) {
7895                e.preventDefault();
7896            });
7897        }
7898
7899        // Fade in/out site search on hover of search icon
7900        if (searchWrap) {
7901            searchWrap.addEventListener('mouseenter', function () {
7902                body.classList.add('menu-active');
7903                siteSearch.classList.add('site-search--active');
7904                setTimeout(function () {
7905                    document.querySelector('.site-search__form input[type="text"]').focus();
7906                }, 800);
7907            });
7908
7909            searchWrap.addEventListener('mouseleave', function () {
7910                body.classList.remove('menu-active');
7911                siteSearch.classList.remove('site-search--active');
7912            });
7913        }
7914        /**  END SEARCH OVERLAY **/
7915
7916        // Mobile Icon
7917        $('.mobile-nav-icon').on('click', function () {
7918            $(this).toggleClass('mobile-nav-icon--active');
7919            $('.site-header').toggleClass('site-header--mobile-nav-active');
7920            $('body').toggleClass('mobile-nav-active');
7921        });
7922
7923        // Disable click on mobile
7924        $('.mobile-menu__item--parent .sub-menu-toggle').on(
7925            'click',
7926            function () {
7927                $(this)
7928                    .parent('.mobile-menu__item')
7929                    .toggleClass('mobile-menu__item--opened');
7930            }
7931        );
7932    },
7933    infScroll: function infScroll() {
7934        var grid = document.querySelector('.listing--inf-scroll');
7935
7936        if (grid) {
7937            var select = document.querySelector('.input-iso-select');
7938            var iso;
7939
7940            // Instantiate selectize to use in conjunction
7941            if (select) {
7942                var $selectize = $('.input-iso-select').selectize({
7943                    create: true,
7944                    sortField: 'text',
7945                });
7946            }
7947
7948            __WEBPACK_IMPORTED_MODULE_5_imagesloaded___default()(grid, function () {
7949                if (select) {
7950                    // images have loaded
7951                    iso = new __WEBPACK_IMPORTED_MODULE_6_isotope_layout___default.a(grid, {
7952                        itemSelector: '.col',
7953                        layoutMode: 'fitRows',
7954                        percentPosition: true,
7955                        stagger: 100,
7956                        fitRows: {
7957                            // set to the element
7958                            gutter: 16,
7959                            columnWidth: '.col',
7960                        },
7961                        hiddenStyle: {
7962                            opacity: 0,
7963                            transform: 'translateY(10px)',
7964                        },
7965                        visibleStyle: {
7966                            opacity: 1,
7967                            transform: 'translateY(0px)',
7968                        },
7969                    });
7970
7971                    // Filter on selection
7972                    // check if selectize is active, and use that as a trigger if so
7973                    if ($selectize) {
7974                        // fetch the instance
7975                        var selectize = $selectize[0].selectize;
7976
7977                        selectize.on('change', function (e) {
7978                            console.log(e);
7979                            iso.arrange({
7980                                filter: e,
7981                            });
7982
7983                            location.hash = 'filter=' + encodeURIComponent(e);
7984                        });
7985                    } else { // otherwise, use the <select>
7986                        // bind filter on select change
7987                        select.addEventListener('change', function () {
7988                            // get filter value from option value
7989                            var filterValue = this.value;
7990                            // console.log(filterValue);
7991
7992                            iso.arrange({
7993                                filter: filterValue,
7994                            });
7995
7996                            location.hash = 'filter=' + encodeURIComponent(filterValue);
7997                        });
7998                    }
7999
8000                    function getHashFilter() { // eslint-disable-line no-inner-declarations
8001                        var hash = location.hash; // eslint-disable-line no-unused-vars
8002                        // get filter=filterName
8003                        var matches = location.hash.match(/filter=([^&]+)/i);
8004                        var hashFilter = matches && matches[1];
8005                        return hashFilter && decodeURIComponent(hashFilter);
8006                    }
8007
8008                    var isIsotopeInit = false;
8009
8010                    function onHashchange() { // eslint-disable-line no-inner-declarations
8011                        var hashFilter = getHashFilter();
8012                        if (!hashFilter && isIsotopeInit) {
8013                            return;
8014                        }
8015                        isIsotopeInit = true;
8016                        // filter isotope
8017                        iso.arrange({
8018                            filter: hashFilter,
8019                        });
8020
8021                        // set selected class on button
8022                        // if (hashFilter) {
8023                        //     $filters.find('.is-checked').removeClass('is-checked');
8024                        //     $filters.find('[data-filter="' + hashFilter + '"]').addClass('is-checked');
8025                        // }
8026                    }
8027
8028                    $(window).on('hashchange', onHashchange);
8029                    // trigger event handler to init Isotope
8030                    onHashchange();
8031                }
8032
8033                // make imagesLoaded available for InfiniteScroll
8034                // InfiniteScroll.imagesLoaded = imagesLoaded;
8035
8036                // Infinite scroll
8037                var infScroll = new __WEBPACK_IMPORTED_MODULE_7_infinite_scroll___default.a(grid, {  // eslint-disable-line no-unused-vars
8038                    path: '.next',
8039                    append: '.inf-post',
8040                    history: 'push',
8041                    outlayer: iso,
8042                    // debug: true,
8043                    scrollThreshold: 450,
8044                    hideNav: '.pagination',
8045                    status: '.page-load-status',
8046                });
8047            });
8048        }
8049    },
8050    interestForm: function interestForm() {
8051        var form = document.querySelector('#register-interests');
8052        if (form) {
8053            var nextBtn = document.querySelector('.register-interests__next');
8054            var stepOne = document.querySelector('.register-interests__topics');
8055            var stepTwo = document.querySelector('.register-interests__formats');
8056
8057            // On click of Next, hide Step 1 and show Step 2
8058            nextBtn.addEventListener('click', function (e) {
8059                e.preventDefault();
8060                stepOne.classList.add('register-interests__topics--hide');
8061                stepTwo.classList.add('register-interests__formats--show');
8062            });
8063
8064            // For each choice, on click of the wrapper, check the corresponding checkbox
8065            var choices = document.querySelectorAll('.register-interests__choice');
8066            choices.forEach(function (choice) {
8067                choice.addEventListener('click', function () {
8068                    var checkbox = choice.querySelector('input[type="checkbox"]');
8069                    checkbox.checked = !checkbox.checked;
8070                    choice.classList.toggle('register-interests__choice--checked');
8071                });
8072            });
8073        }
8074    },
8075    itemReveal: function itemReveal() {
8076        // eslint-disable-next-line no-unused-vars
8077        // var $itemReveals = $('.reveal').waypoint({
8078        //   handler: function () {
8079        //     $(this)[0].element.classList.add('revealed');
8080        //   },
8081        //   offset: '85%',
8082        // });
8083
8084        // Use gsap and ScrollTrigger
8085        __WEBPACK_IMPORTED_MODULE_0_gsap__["a" /* default */].registerPlugin(__WEBPACK_IMPORTED_MODULE_1_gsap_ScrollTrigger__["a" /* default */]);
8086        var reveals = __WEBPACK_IMPORTED_MODULE_0_gsap__["a" /* default */].utils.toArray('.reveal');
8087        reveals.forEach(function (reveal) {
8088            __WEBPACK_IMPORTED_MODULE_1_gsap_ScrollTrigger__["a" /* default */].create({
8089                trigger: reveal,
8090                start: 'top 75%', // when the top of the element is 75% from the top of the viewport
8091                toggleClass: 'revealed',
8092                // toggleActions: 'play pause resume none',
8093                once: true, // only trigger the toggle once. we can control repeat behavior using toggleActions
8094            });
8095        });
8096
8097        // Stagger reveals with a gsap.timeline() + ScrollTrigger
8098        var staggers = __WEBPACK_IMPORTED_MODULE_0_gsap__["a" /* default */].utils.toArray('.reveal--staggered');
8099        staggers.forEach(function (stagger) {
8100            var tl = __WEBPACK_IMPORTED_MODULE_0_gsap__["a" /* default */].timeline({
8101                scrollTrigger: {
8102                    trigger: stagger,
8103                    start: 'top 75%',
8104                },
8105            });
8106
8107            var children = stagger.children; // the immediate children elements of the current target
8108
8109            tl.to(children, {
8110                duration: 1,
8111                y: 0,
8112                opacity: 1,
8113                stagger: 0.15,
8114            });
8115        });
8116    },
8117    kalturaSession: function kalturaSession() {
8118        var partnerId = '1529571';
8119        var playerId = '49927973';
8120        var videoPlayer = document.getElementById('bg-video-player');
8121        var videoId = videoPlayer.dataset.video;
8122        var body = document.querySelector('body');
8123
8124        // https://github.com/kaltura/kaltura-player-js
8125        // config options: https://developer.kaltura.com/player/web/configuration-web
8126        try {
8127            var kalturaPlayer = KalturaPlayer.setup({ // eslint-disable-line no-undef
8128                targetId: 'bg-video-player',
8129                provider: {
8130                    partnerId: partnerId,
8131                    uiConfId: playerId,
8132                },
8133                playback: {
8134                    autoplay: true,
8135                    loop: true,
8136                    muted: true,
8137                },
8138                // plugins: {
8139                //     googleTagManager: {
8140                //         containerId: 'GTM-MF367DD',                      // formatted as GTM-XXXXXX
8141                //         customEventsTracking: {
8142                //             preset: {
8143                //                 coreEvents: true,                                   // Default = false
8144                //                 UIEvents: true,                                     // Default = false
8145                //                 playlistEvents: false,                               // Default = false
8146                //                 castEvents: false,                                    // Default = false
8147                //             },
8148                //         },
8149                //     },
8150                // },
8151            });
8152            kalturaPlayer.loadMedia({
8153                entryId: videoId,
8154            });
8155
8156            // player events: https://github.com/kaltura/playkit-js/blob/master/src/event/event-type.js
8157            kalturaPlayer.ready().then(function () {
8158                setTimeout(function () {
8159                    body.classList.add('loaded');
8160                }, 500);
8161            });
8162
8163        } catch (e) {
8164            console.error(e.message)
8165        }
8166    },
8167    likeButton: function likeButton() {
8168        var button = document.querySelectorAll('.ctt-like-button-link');
8169
8170        if (button) {
8171            button.forEach(function (element) {
8172                var postId = element.dataset.post_id;
8173                var userId = element.dataset.user_id;
8174                element.addEventListener('click', function (e) {
8175                    e.preventDefault();
8176                    var process = element.dataset.process; // process changes on each click
8177
8178                    jQuery.ajax({
8179                        type: 'POST',
8180                        dataType: 'json',
8181                        url: ajax_obj.ajax_url, // eslint-disable-line no-undef
8182                        data: {
8183                            action: 'like_button',
8184                            post_id: postId,
8185                            user_id: userId,
8186                            process: process,
8187                            _ajax_nonce: ajax_obj.like_nonce, // eslint-disable-line no-undef
8188                        },
8189                        success: function (response) {
8190                            if (response.type == 'success') {
8191                                var params = new Proxy(new URLSearchParams(window.location.search), {
8192                                    get: function (searchParams, prop) { return searchParams.get(prop); },
8193                                });
8194                                if (params.profiletab == 'likes') {
8195                                    $(element.closest('.list-item--video-member')).fadeOut();
8196                                } else {
8197                                    element.dataset.process = response.process;
8198
8199                                    var type = '';
8200                                    if (element.innerHTML.includes('video')) { type = 'video'; }
8201                                    if (element.innerHTML.includes('playlist')) { type = 'playlist'; }
8202
8203                                    element.innerHTML = '<i class="icon-heart"></i> ' + response.process + ' ' + type;
8204                                }
8205                            } else {
8206                                console.log(response);
8207                            }
8208                        },
8209                    });
8210                });
8211            });
8212        }
8213    },
8214    links: function links() {
8215        /** SKIP LINK NAVIGATION */
8216        $('#skip-to-content').click(function () {
8217            // strip the leading hash and declare
8218            // the content we're skipping to
8219            var skipTo = '#' + this.href.split('#')[1];
8220            // Setting 'tabindex' to -1 takes an element out of normal
8221            // tab flow but allows it to be focused via javascript
8222            $(skipTo)
8223                .attr('tabindex', -1)
8224                .on('blur focusout', function () {
8225                    // when focus leaves this element,
8226                    // remove the tabindex attribute
8227                    $(this).removeAttr('tabindex');
8228                })
8229                .focus(); // focus on the content container
8230        });
8231        /** END SKIP LINK NAVIGATION */
8232
8233        /** ANIMATED ANCHOR LINKS **/
8234        $('a[href*="#"]:not([href="#"])').click(function (e) {
8235            // Doesn't do it on page builder tabs
8236            if (!$(this).hasClass('tab-toggle__link')) {
8237                if (
8238                    location.pathname.replace(/^\//, '') ===
8239                    this.pathname.replace(/^\//, '') &&
8240                    location.hostname === this.hostname
8241                ) {
8242                    var target = $(this.hash);
8243                    var $this = this;
8244                    var header = $('header.site-header');
8245                    var wpAdminBar = $('#wpadminbar');
8246                    var fixedHeaderOffset =
8247                        parseInt(header.outerHeight()) -
8248                        parseInt(
8249                            header.css('padding-top').replace('px', '')
8250                        );
8251                    // If we're logged in and WP ADmin Bar exists, add it to the offset
8252                    if (wpAdminBar.length) {
8253                        fixedHeaderOffset += parseInt(
8254                            wpAdminBar.outerHeight()
8255                        );
8256                    }
8257                    target = target.length
8258                        ? target
8259                        : $('[name=' + this.hash.slice(1) + ']');
8260                    if (target.length) {
8261                        $('html,body').animate(
8262                            {
8263                                scrollTop:
8264                                    target.offset().top - fixedHeaderOffset,
8265                            },
8266                            500,
8267                            function () {
8268                                if (history.pushState) {
8269                                    history.pushState(
8270                                        null,
8271                                        null,
8272                                        $this.hash
8273                                    );
8274                                } else {
8275                                    location.hash = $this.hash;
8276                                }
8277                            }
8278                        );
8279                        e.preventDefault();
8280                    }
8281                }
8282            }
8283        });
8284        /** END ANIMATED ANCHOR LINKS **/
8285
8286        /** Break link text to new line when link text is a URL **/
8287        $(document).ready(function () {
8288            $('a').each(function () {
8289                var $this = $(this);
8290                var innerLink = $this.text();
8291                if (innerLink.startsWith('http')) {
8292                    $this.css('word-break', 'break-all');
8293                }
8294            });
8295        });
8296        /** End Break link text to new line when link text is a URL **/
8297
8298        /** Back link */
8299        var backLink = document.querySelector('.back-link a');
8300
8301        if (backLink) {
8302            backLink.addEventListener('click', function (e) {
8303                e.preventDefault();
8304                history.back();
8305            })
8306        }
8307    },
8308    loadScript: function loadScript(src, callback) {
8309        var loaded = false;
8310        var tag = document.createElement('script');
8311        var firstScriptTag = document.getElementsByTagName('script')[0];
8312        if (!firstScriptTag) {
8313            // when loaded in jest without jsdom setup it doesn't get any element.
8314            // In jest it doesn't really make sense to do anything, because no one is watching youtube in jest
8315            return;
8316        }
8317        firstScriptTag.parentNode.insertBefore(tag, firstScriptTag);
8318        tag.onload = function () {
8319            if (!loaded) {
8320                loaded = true;
8321                callback();
8322            }
8323        };
8324        tag.onreadystatechange = function () {
8325            if (!loaded && (this.readyState === 'complete' || this.readyState === 'loaded')) {
8326                loaded = true;
8327                callback();
8328            }
8329        };
8330        tag.src = src;
8331    },
8332    magnificPopup: function magnificPopup() {
8333        var videoLink = $('.modal-link-video');
8334        if (videoLink) {
8335            videoLink.magnificPopup({
8336                // disableOn: 700,
8337                type: 'iframe',
8338                mainClass: 'mfp-fade',
8339                // removalDelay: 160,
8340                preloader: false,
8341                fixedContentPos: false,
8342                closeOnBgClick: true,
8343                enableEscapeKey: true,
8344                iframe: {
8345                    markup: '<div class="mfp-iframe-scaler">' +
8346                        '<div class="mfp-close"></div>' +
8347                        '<iframe class="mfp-iframe" frameborder="0" allow="autoplay"></iframe>' +
8348                        '</div>',
8349                    patterns: {
8350                        youtube: {
8351                            index: 'youtube.com',
8352                            id: 'v=',
8353                            src: 'https://www.youtube.com/embed/%id%?rel=0&autoplay=1',
8354                        },
8355                    },
8356                },
8357                srcAction: 'iframe_src',
8358            });
8359        }
8360
8361        var htmlLink = $('.modal-link-html');
8362        if (htmlLink) {
8363            htmlLink.magnificPopup({
8364                // disableOn: 700,
8365                type: 'inline',
8366                midClick: true,
8367                mainClass: 'mfp-fade',
8368                // removalDelay: 160,
8369                // preloader: false,
8370                // fixedContentPos: false,
8371                closeBtnInside: true,
8372            });
8373        }
8374    },
8375    mainMenu: function mainMenu() {
8376        var body = document.querySelector('body');
8377        var itemParent = document.querySelectorAll('.main-menu__item');
8378        // let menu = document.querySelector('.main-menu');
8379
8380        // On mouseover of a menu item with dropdown, fade in overlay
8381        if (itemParent) {
8382            itemParent.forEach(function (item) {
8383                item.addEventListener('mouseenter', function () {
8384                    body.classList.add('menu-active');
8385                });
8386
8387                item.addEventListener('mouseleave', function () {
8388                    body.classList.remove('menu-active');
8389                });
8390            });
8391        }
8392
8393        // Sliding menu
8394        // ref: https://codyhouse.co/ds/components/app/drop-menu
8395        var topicMenuWrap = document.querySelector('.main-menu__item--topic-menu .main-menu__sub-menu');
8396
8397        if (topicMenuWrap) {
8398            var topicMenu = topicMenuWrap.querySelector('.main-menu__item--parent');
8399            if (topicMenu) {
8400                var parentLinks = topicMenu.querySelectorAll('.main-menu__sub-menu--2__item > .main-menu__sub-menu__link');
8401                parentLinks.forEach(function (link) {
8402                    var subMenu = link.nextElementSibling; // Shift in child topic menu
8403                    link.addEventListener('click', function (e) {
8404                        e.preventDefault();
8405                        topicMenu.classList.toggle('shifted');
8406                        subMenu.classList.toggle('in');
8407                    });
8408                });
8409
8410                var gParentLinks = topicMenu.querySelectorAll('.sub-menu__item--parent > .sub-menu__link');
8411                gParentLinks.forEach(function (link) {
8412                    var parentMenu = link.closest('.sub-menu'); // parent submenu
8413                    var subMenu = link.nextElementSibling; // Shift in child topic menu
8414                    link.addEventListener('click', function (e) {
8415                        e.preventDefault();
8416                        parentMenu.classList.toggle('shifted');
8417                        subMenu.classList.toggle('in');
8418                    });
8419                });
8420
8421                // On Back link click, toggle class of parent menu and topicMenu
8422                var backLink = topicMenu.querySelectorAll('.sub-menu--topics-child > .sub-menu__item > .sub-menu__link--back');
8423                backLink.forEach(function (link) {
8424                    var parentMenu = link.closest('.sub-menu'); // parent submenu
8425                    var topicMenu = link.closest('.main-menu__item--parent');
8426
8427                    link.addEventListener('click', function (e) {
8428                        e.preventDefault();
8429                        parentMenu.classList.toggle('in');
8430                        topicMenu.classList.toggle('shifted');
8431                    })
8432                })
8433
8434                var gBackLink = topicMenu.querySelectorAll('.sub-menu
8434--topics-gchild > .sub-menu__item > .sub-menu__link--back');
8435                gBackLink.forEach(function (link) {
8436                    var parentMenu = link.closest('.sub-menu--topics-gchild'); // parent submenu
8437                    var topicMenu = link.closest('.sub-menu--topics-child');
8438
8439                    link.addEventListener('click', function (e) {
8440                        e.preventDefault();
8441                        parentMenu.classList.toggle('in');
8442                        topicMenu.classList.toggle('shifted');
8443                    })
8444                })
8445            }
8446        }
8447    },
8448    mainNavAccessibility: function mainNavAccessibility() {
8449        var $mainNavigationTopLevelItemLinks = $(
8450            '.site-header .main-menu > .main-menu__item--parent > button'
8451        );
8452
8453        if ($mainNavigationTopLevelItemLinks.length) {
8454            $mainNavigationTopLevelItemLinks.each(function () {
8455                $(this).prev('a').attr('aria-haspopup', 'true');
8456                $(this).on('click', function () {
8457                    $(this).closest('li').toggleClass('sub-menu-open');
8458                    $(this).attr('aria-expanded', 'true');
8459                });
8460            });
8461        }
8462    },
8463    masthead: function masthead() {
8464        /** MASTHEAD PRGRESSIVE IMAGES **/
8465        var masthead = document.querySelector('.bg-img-load'),
8466            placeholderOverlay = document.querySelector('.masthead__overlay');
8467
8468        if (masthead && placeholderOverlay) {
8469            // Load full size image. When loaded, fade our placeholder add it as bg to masthead
8470            var img = new Image();
8471            img.src = masthead.dataset.imageSrc;
8472            img.onload = function () {
8473                placeholderOverlay.classList.add('fade-out');
8474                masthead.style.backgroundImage = 'url(' + img.src + ')';
8475            };
8476        }
8477        /** END MASTHEAD PRGRESSIVE IMAGES **/
8478    },
8479    mastheadFade: function mastheadFade() {
8480        var mastheadMedia = document.querySelector('.masthead__media');
8481
8482        if (mastheadMedia) {
8483            // Use gsap and ScrollTrigger
8484            __WEBPACK_IMPORTED_MODULE_0_gsap__["a" /* default */].registerPlugin(__WEBPACK_IMPORTED_MODULE_1_gsap_ScrollTrigger__["a" /* default */]);
8485
8486            __WEBPACK_IMPORTED_MODULE_0_gsap__["a" /* default */].to('.masthead__media', {
8487                opacity: 0,
8488                scrollTrigger: {
8489                    trigger: '.masthead',
8490                    scrub: true,
8491                    start: 'top top',
8492                    end: '+=50%',
8493                    // markers: true,
8494                },
8495            });
8496        }
8497    },
8498    onYouTubeIframeAPIReady: function onYouTubeIframeAPIReady() {
8499        // This function creates an <iframe> (and YouTube player) after the API code downloads.
8500
8501        // Video player output
8502        var player;
8503        var videoPlayer = document.getElementById('bg-video-player');
8504        var videoUrl = videoPlayer.dataset.video;
8505        var body = document.querySelector('body');
8506
8507        // Get the video ID
8508        var regex = /(https?:\/\/)?((www\.)?(youtube(-nocookie)?|youtube.googleapis)\.com.*(v\/|v=|vi=|vi\/|e\/|embed\/|user\/.*\/u\/\d+\/)|youtu\.be\/)([_0-9a-z-]+)/i;
8509        var videoId = videoUrl.match(regex);
8510
8511        window.YT.ready(function () {
8512            player = new window.YT.Player(videoPlayer, { // eslint-disable-line no-undef
8513                height: '390',
8514                width: '640',
8515                videoId: videoId[7],
8516                playerVars: {
8517                    'playsinline': 1,
8518                    'autoplay': 1,
8519                    'controls': 0,
8520                    'disablekb': 1,
8521                    'enablejsapi': 1,
8522                    'fs': 0,
8523                    'loop': 1,
8524                    'rel': 0,
8525                    'modestbranding': 1,
8526                },
8527                events: {
8528                    'onReady': onPlayerReady,
8529                    onStateChange:
8530                        function (e) {
8531                            if (e.data === window.YT.PlayerState.CUED || e.data === window.YT.PlayerState.UNSTARTED || e.data === window.YT.PlayerState.ENDED || e.data === window.YT.PlayerState.PAUSED) {
8532                                player.playVideo();
8533                            }
8534
8535                            // Add loaded state only once video is playing
8536                            if (e.data === window.YT.PlayerState.PLAYING) {
8537                                setTimeout(function () {
8538                                    body.classList.add('loaded');
8539                                }, 500);
8540                            }
8541                        },
8542                },
8543            });
8544
8545            document.addEventListener('visibilitychange', function () {
8546                if (document.hidden) {
8547                    console.log('not visible');
8548                } else {
8549                    console.log('is visible');
8550                    player.playVideo();
8551                }
8552            });
8553        });
8554
8555        // Called when the player's state changes
8556        // Available states: buffering, unstarted, cued, playing, paused, ended
8557        function onPlayerReady() {
8558            player.playVideo();
8559            player.mute();
8560        }
8561    },
8562    pageLoad: function pageLoad() {
8563        // Note that this is also fired on additional media events sitewide:
8564        // - Background YouTube videos: onYouTubeIframeAPIReady()
8565        // - Background Kaltura videos: kalturaSession()
8566        // - Homepage carousel: home.js
8567
8568        // Check if masthead background image
8569        var masthead = document.querySelector('.bg-img-load'),
8570            body = document.querySelector('body');
8571
8572        if (masthead) {
8573            // Load full size image. When loaded, set body class to trigger page animations
8574            var img = new Image();
8575            img.src = masthead.dataset.imageSrc;
8576            img.onload = function () {
8577                setTimeout(function () {
8578                    body.classList.add('loaded');
8579                }, 500);
8580            };
8581        } else {
8582            // Default if no masthead media set
8583            setTimeout(function () {
8584                body.classList.add('loaded');
8585            }, 500);
8586        }
8587    },
8588    removeButton: function removeButton() {
8589        var button = document.querySelectorAll('.ctt-remove-button-link');
8590
8591        if (button) {
8592            button.forEach(function (element) {
8593                var postId = element.dataset.post_id;
8594                var userId = element.dataset.user_id;
8595                element.addEventListener('click', function (e) {
8596                    e.preventDefault();
8597                    var process = element.dataset.process; // process changes on each click
8598
8599                    jQuery.ajax({
8600                        type: 'POST',
8601                        dataType: 'json',
8602                        url: ajax_obj.ajax_url, // eslint-disable-line no-undef
8603                        data: {
8604                            action: 'remove_button',
8605                            post_id: postId,
8606                            user_id: userId,
8607                            process: process,
8608                            _ajax_nonce: ajax_obj.remove_nonce, // eslint-disable-line no-undef
8609                        },
8610                        success: function (response) {
8611                            if (response.type == 'success') {
8612                                var params = new Proxy(new URLSearchParams(window.location.search), {
8613                                    get: function (searchParams, prop) { return searchParams.get(prop); },
8614                                });
8615                                if (params.profiletab == 'history') {
8616                                    $(element.closest('.list-item--video-member')).fadeOut();
8617                                } else {
8618                                    console.log(response);
8619                                }
8620                            }
8621                        },
8622                    });
8623                });
8624            });
8625        }
8626    },
8627    selectize: function selectize() {
8628        var selectize = $('.input--alt');
8629        if (selectize) {
8630            $('.input--alt').selectize({
8631                create: true,
8632                sortField: 'text',
8633            });
8634        }
8635    },
8636    slider: function slider() {
8637        // Include .visc-posts-list which is output from visceral-addons (elementor block)
8638        var visceralSlider = $('.visceral-slider');
8639
8640        if (visceralSlider) {
8641            visceralSlider.each(function () {
8642                var slider = $(this);
8643                var slidesToShow = slider.attr('data-slides-to-show') ? slider.attr('data-slides-to-show') : 3;
8644
8645                slider.slick({
8646                    autoplay: false,
8647                    fade: false,
8648                    speed: 600,
8649                    infinite: false,
8650                    cssEase: 'ease',
8651                    centerMode: false,
8652                    slidesToShow: 1,
8653                    slidesToScroll: 1,
8654                    swipeToSlide: true,
8655                    dots: true,
8656                    arrows: true,
8657                    mobileFirst: true,
8658                    rows: 0,
8659                    nextArrow:
8660                        '<button type="button" class="slick-next"><span class="screen-reader-text">Next</span><i class="icon-chevron-right"></i></button>',
8661                    prevArrow:
8662                        '<button type="button" class="slick-prev"><span class="screen-reader-text">Previous</span><i class="icon-chevron-left"></i></button>',
8663                    responsive: [
8664                        {
8665                            breakpoint: 280,
8666                            settings: {
8667                                slidesToShow: 1,
8668                            },
8669                        },
8670                        {
8671                            breakpoint: 560, // min-width
8672                            settings: {
8673                                slidesToShow: 2,
8674                            },
8675                        },
8676                        {
8677                            breakpoint: 992, // min-width
8678                            settings: {
8679                                slidesToShow: parseInt(slidesToShow),
8680                            },
8681                        } ],
8682                });
8683
8684                // Counter
8685                var sliderItemsNum = slider.find('.slick-slide').not('.slick-cloned').length;
8686                if (sliderItemsNum > parseInt(slidesToShow)) {
8687                    var counter = $('<div class="slick-counter"><span>' + sliderItemsNum + ' items</span></div>');
8688                    counter.insertBefore(slider);
8689                }
8690            });
8691        }
8692    },
8693    socialShare: function socialShare() {
8694        /**  SOCIAL SHARE OVERLAY **/
8695        var body = document.querySelector('body');
8696        var shareLinks = document.querySelectorAll('.visc-social-share-btn');
8697        var socialShare = document.querySelector('.visc-social-share');
8698        var socialShareClose = document.querySelector('.visc-social-share__close');
8699
8700        if (shareLinks && socialShare) {
8701            shareLinks.forEach(function (link) {
8702                link.addEventListener('click', function () {
8703                    socialShare.classList.add('visc-social-share--active');
8704                    body.classList.toggle('menu-active');
8705                });
8706                socialShareClose.addEventListener('click', function () {
8707                    socialShare.classList.remove('visc-social-share--active');
8708                    body.classList.remove('menu-active');
8709                });
8710            })
8711        }
8712        /**  END SOCIAL SHARE OVERLAY **/
8713    },
8714    subNavigation: function subNavigation() {
8715        var toggle = document.querySelectorAll('.sub-nav__list--toggle');
8716
8717        if (toggle) {
8718            toggle.forEach(function (item) {
8719                var toggleLink = item.querySelectorAll('.sub-nav__link');
8720
8721                toggleLink.forEach(function (link) {
8722                    link.addEventListener('click', function (e) {
8723                        e.preventDefault();
8724
8725                        [].forEach.call(toggleLink, function (el) {
8726                            el.classList.remove('active');
8727                        });
8728
8729                        link.classList.add('active');
8730                    });
8731                });
8732            });
8733        }
8734    },
8735    subNavigationAjax: function subNavigationAjax() {
8736        var $contentContainer = $('.post-content');
8737        var $subNavigation = $('.list--sub-page-menu');
8738
8739        if ($subNavigation.length) {
8740            $subNavigation.each(function () {
8741                var $subNavigationItems = $(this).find('li');
8742                var $activeSubNavigationLinks = $(this).find('li a');
8743                $activeSubNavigationLinks.on('click', function (e) {
8744                    e.preventDefault();
8745                    $subNavigationItems.removeClass('current-menu-item');
8746                    $(this).parent('li').addClass('current-menu-item');
8747                    var url = e.target.href;
8748                    console.log(e);
8749                    $.ajax({
8750                        url: url,
8751                        dataType: 'html',
8752                        beforeSend: function () {
8753                            // Show the user something is happening
8754                            //   $postsListLoader.addClass("visc-posts-list__loader--active");
8755                        },
8756                        success: function (data) {
8757                            // Get all the new content inside of the container
8758                            var updatedContent = $(data).find('.post-content > *');
8759
8760                            // Display the new data in the container
8761                            $contentContainer.empty();
8762                            $contentContainer.append(updatedContent);
8763
8764                            // Scroll to the top of the list container
8765                            // contentContainer.scrollIntoView({
8766                            //     behavior: 'smooth',
8767                            //     block: 'start',
8768                            //     inline: 'nearest',
8769                            // });
8770                            // Show the user the request is comlete
8771                            // $postsListLoader.removeClass(
8772                            //     'visc-posts-list__loader--active'
8773                            // );
8774                            // Need to re-run this after each complete AJAX too
8775                            // postsListPaginationAJAXHandler();
8776                            history.pushState('', document.title, url);
8777                            // Create custom JS event to listen to for custom JS after AJAX is complete
8778                            // $(document).trigger('visceralPage:ajaxSuccess');
8779                            // window.elementorFrontend.init();
8780                        },
8781                    });
8782                });
8783            });
8784        }
8785    },
8786    viewCounter: function viewCounter() {
8787        jQuery(document).ready(function () {
8788            jQuery.ajax({
8789                type: 'post',
8790                dataType: 'json',
8791                url: ajax_obj.ajax_url, // eslint-disable-line no-undef
8792                data: {
8793                    action: 'view_counter',
8794                    post_id: ajax_obj.post_id, // eslint-disable-line no-undef
8795                },
8796                success: function (response) {
8797                    if (response.type != 'success') {
8798                        //alert('Sorry, an error occured. Please try again.');
8799                    } else {
8800                        //alert('Yay!');
8801                    }
8802                },
8803            });
8804        });
8805    },
8806    zendesk: function zendesk() {
8807        var footerLink = document.querySelector('.footer-menu__item--contact a');
8808        var contactLink = document.querySelector('.contact-trigger');
8809
8810        if (footerLink) {
8811            footerLink.addEventListener('click', function (e) {
8812                e.preventDefault();
8813
8814                // Show the Zendesk widget
8815                zE('webWidget', 'open'); // eslint-disable-line no-undef
8816            });
8817        }
8818
8819        if (contactLink) {
8820            contactLink.addEventListener('click', function (e) {
8821                e.preventDefault();
8822
8823                // Show the Zendesk widget
8824                zE('webWidget', 'open'); // eslint-disable-line no-undef
8825            });
8826        }
8827    },
8828    init: function init() {
8829        // JavaScript to be fired on all pages
8830
8831        /** GLOBAL VARIABLES */
8832        // var body = document.querySelector('body');
8833        /** END GLOBAL VARIABLES */
8834
8835        // Load more
8836        this.ajaxLoadMore();
8837
8838        this.buttons();
8839
8840        // Header
8841        this.header();
8842
8843        // Footer
8844        this.zendesk();
8845
8846        // Global reveal animations (consider commenting out this and 'gsap' and 'ScrollTrigger' import if not in use)
8847        this.itemReveal();
8848
8849        // infinite scroll
8850        this.infScroll();
8851
8852        // Interest form
8853        this.interestForm();
8854
8855        // Like button
8856        this.likeButton();
8857
8858        // Remove button
8859        this.removeButton();
8860
8861        // Misc. link behaviors
8862        this.links();
8863
8864        // Modals (consider comment out this and 'magnific-popup' import if not in use)
8865        this.magnificPopup();
8866
8867        this.mainMenu();
8868
8869        // Main Nav Accessibility
8870        this.mainNavAccessibility();
8871
8872        // Masthead
8873        this.masthead();
8874        this.mastheadFade();
8875
8876        // Page load
8877        this.pageLoad();
8878
8879        this.selectize();
8880
8881        // Social share
8882        this.socialShare();
8883
8884        // Slider (consider commenting out this and 'slick-carousel' import if not in use)
8885        this.slider();
8886
8887        // Sub-nav linking
8888        this.subNavigation();
8889
8890        // View Counter
8891        this.viewCounter();
8892
8893        // Video player for background videos (masthead only)
8894        // See singleVideo.js for user initiated videos
8895        var videoPlayer = document.getElementById('bg-video-player');
8896        if (videoPlayer) {
8897            var videoId = videoPlayer.dataset.video;
8898            var source = videoPlayer.dataset.source;
8899            // data-source resolves the platform; fall back to legacy detection.
8900            if (source === 'youtube' || (!source && videoId.indexOf('youtube') > -1)) {
8901                // Loads the IFrame Player API code asynchronously.
8902                this.loadScript('https://www.youtube.com/iframe_api', this.onYouTubeIframeAPIReady);
8903            } else if (source === 'bunny') {
8904                // Bunny Stream background video (muted, looping autoplay)
8905                Object(__WEBPACK_IMPORTED_MODULE_3__util_playerLoader__["a" /* loadBunnyPlayer */])(videoPlayer, { background: true });
8906            } else {
8907                // Kaltura Web Player
8908                // Utilizes the TV Studio Player (V7) in Kaltura Management Console (KMC)
8909                // https://developer.kaltura.com/player/web/getting-started-web
8910                var partnerId = '1529571';
8911                var playerId = '49927973';
8912                this.loadScript('https://cdnapisec.kaltura.com/p/' + partnerId + '/embedPlaykitJs/uiconf_id/' + playerId, this.kalturaSession);
8913            }
8914        }
8915    },
8916    finalize: function finalize() {
8917        // JavaScript to be fired on all pages, after page specific JS is fired
8918    },
8919});
8920
8921/* WEBPACK VAR INJECTION */}.call(__webpack_exports__, __webpack_require__(0), __webpack_require__(0)))
8922
8923/***/ }),
8924/* 19 */
8925/***/ (function(module, __webpack_exports__, __webpack_require__) {
8926
8927"use strict";
8928/* unused harmony export gsap */
8929/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return gsapWithCSS; });
8930/* unused harmony export TweenMax */
8931/* harmony import */ var __WEBPACK_IMPORTED_MODULE_0__gsap_core_js__ = __webpack_require__(10);
8932/* harmony import */ var __WEBPACK_IMPORTED_MODULE_1__CSSPlugin_js__ = __webpack_require__(20);
8933/* unused harmony reexport CSSPlugin */
8934/* unused harmony reexport TweenLite */
8935/* unused harmony reexport TimelineMax */
8936/* unused harmony reexport TimelineLite */
8937/* unused harmony reexport Power0 */
8938/* unused harmony reexport Power1 */
8939/* unused harmony reexport Power2 */
8940/* unused harmony reexport Power3 */
8941/* unused harmony reexport Power4 */
8942/* unused harmony reexport Linear */
8943/* unused harmony reexport Quad */
8944/* unused harmony reexport Cubic */
8945/* unused harmony reexport Quart */
8946/* unused harmony reexport Quint */
8947/* unused harmony reexport Strong */
8948/* unused harmony reexport Elastic */
8949/* unused harmony reexport Back */
8950/* unused harmony reexport SteppedEase */
8951/* unused harmony reexport Bounce */
8952/* unused harmony reexport Sine */
8953/* unused harmony reexport Expo */
8954/* unused harmony reexport Circ */
8955
8956
8957var gsapWithCSS = __WEBPACK_IMPORTED_MODULE_0__gsap_core_js__["w" /* gsap */].registerPlugin(__WEBPACK_IMPORTED_MODULE_1__CSSPlugin_js__["a" /* CSSPlugin */]) || __WEBPACK_IMPORTED_MODULE_0__gsap_core_js__["w" /* gsap */],
8958    // to protect from tree shaking
8959TweenMaxWithCSS = gsapWithCSS.core.Tween;
8960
8961
8962/***/ }),
8963/* 20 */
8964/***/ (function(module, __webpack_exports__, __webpack_require__) {
8965
8966"use strict";
8967/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return CSSPlugin; });
8968/* unused harmony export default */
8969/* unused harmony export _getBBox */
8970/* unused harmony export _createElement */
8971/* unused harmony export checkPrefix */
8972/* harmony import */ var __WEBPACK_IMPORTED_MODULE_0__gsap_core_js__ = __webpack_require__(10);
8973/*!
8974 * CSSPlugin 3.6.0
8975 * https://greensock.com
8976 *
8977 * Copyright 2008-2021, GreenSock. All rights reserved.
8978 * Subject to the terms at https://greensock.com/standard-license or for
8979 * Club GreenSock members, the agreement issued with that membership.
8980 * @author: Jack Doyle, [email protected]
8981*/
8982
8983/* eslint-disable */
8984
8985
8986var _win,
8987    _doc,
8988    _docElement,
8989    _pluginInitted,
8990    _tempDiv,
8991    _tempDivStyler,
8992    _recentSetterPlugin,
8993    _windowExists = function _windowExists() {
8994  return typeof window !== "undefined";
8995},
8996    _transformProps = {},
8997    _RAD2DEG = 180 / Math.PI,
8998    _DEG2RAD = Math.PI / 180,
8999    _atan2 = Math.atan2,
9000    _bigNum = 1e8,
9001    _capsExp = /([A-Z])/g,
9002    _horizontalExp = /(?:left|right|width|margin|padding|x)/i,
vendor: 11,308 bytes, lines 9003-9246
9003    _complexExp = /[\s,\(]\S/,
9004    _propertyAliases = {
9005  autoAlpha: "opacity,visibility",
9006  scale: "scaleX,scaleY",
9007  alpha: "opacity"
9008},
9009    _renderCSSProp = function _renderCSSProp(ratio, data) {
9010  return data.set(data.t, data.p, Math.round((data.s + data.c * ratio) * 10000) / 10000 + data.u, data);
9011},
9012    _renderPropWithEnd = function _renderPropWithEnd(ratio, data) {
9013  return data.set(data.t, data.p, ratio === 1 ? data.e : Math.round((data.s + data.c * ratio) * 10000) / 10000 + data.u, data);
9014},
9015    _renderCSSPropWithBeginning = function _renderCSSPropWithBeginning(ratio, data) {
9016  return data.set(data.t, data.p, ratio ? Math.round((data.s + data.c * ratio) * 10000) / 10000 + data.u : data.b, data);
9017},
9018    //if units change, we need a way to render the original unit/value when the tween goes all the way back to the beginning (ratio:0)
9019_renderRoundedCSSProp = function _renderRoundedCSSProp(ratio, data) {
9020  var value = data.s + data.c * ratio;
9021  data.set(data.t, data.p, ~~(value + (value < 0 ? -.5 : .5)) + data.u, data);
9022},
9023    _renderNonTweeningValue = function _renderNonTweeningValue(ratio, data) {
9024  return data.set(data.t, data.p, ratio ? data.e : data.b, data);
9025},
9026    _renderNonTweeningValueOnlyAtEnd = function _renderNonTweeningValueOnlyAtEnd(ratio, data) {
9027  return data.set(data.t, data.p, ratio !== 1 ? data.b : data.e, data);
9028},
9029    _setterCSSStyle = function _setterCSSStyle(target, property, value) {
9030  return target.style[property] = value;
9031},
9032    _setterCSSProp = function _setterCSSProp(target, property, value) {
9033  return target.style.setProperty(property, value);
9034},
9035    _setterTransform = function _setterTransform(target, property, value) {
9036  return target._gsap[property] = value;
9037},
9038    _setterScale = function _setterScale(target, property, value) {
9039  return target._gsap.scaleX = target._gsap.scaleY = value;
9040},
9041    _setterScaleWithRender = function _setterScaleWithRender(target, property, value, data, ratio) {
9042  var cache = target._gsap;
9043  cache.scaleX = cache.scaleY = value;
9044  cache.renderTransform(ratio, cache);
9045},
9046    _setterTransformWithRender = function _setterTransformWithRender(target, property, value, data, ratio) {
9047  var cache = target._gsap;
9048  cache[property] = value;
9049  cache.renderTransform(ratio, cache);
9050},
9051    _transformProp = "transform",
9052    _transformOriginProp = _transformProp + "Origin",
9053    _supports3D,
9054    _createElement = function _createElement(type, ns) {
9055  var e = _doc.createElementNS ? _doc.createElementNS((ns || "http://www.w3.org/1999/xhtml").replace(/^https/, "http"), type) : _doc.createElement(type); //some servers swap in https for http in the namespace which can break things, making "style" inaccessible.
9056
9057  return e.style ? e : _doc.createElement(type); //some environments won't allow access to the element's style when created with a namespace in which case we default to the standard createElement() to work around the issue. Also note that when GSAP is embedded directly inside an SVG file, createElement() won't allow access to the style object in Firefox (see https://greensock.com/forums/topic/20215-problem-using-tweenmax-in-standalone-self-containing-svg-file-err-cannot-set-property-csstext-of-undefined/).
9058},
9059    _getComputedProperty = function _getComputedProperty(target, property, skipPrefixFallback) {
9060  var cs = getComputedStyle(target);
9061  return cs[property] || cs.getPropertyValue(property.replace(_capsExp, "-$1").toLowerCase()) || cs.getPropertyValue(property) || !skipPrefixFallback && _getComputedProperty(target, _checkPropPrefix(property) || property, 1) || ""; //css variables may not need caps swapped out for dashes and lowercase.
9062},
9063    _prefixes = "O,Moz,ms,Ms,Webkit".split(","),
9064    _checkPropPrefix = function _checkPropPrefix(property, element, preferPrefix) {
9065  var e = element || _tempDiv,
9066      s = e.style,
9067      i = 5;
9068
9069  if (property in s && !preferPrefix) {
9070    return property;
9071  }
9072
9073  property = property.charAt(0).toUpperCase() + property.substr(1);
9074
9075  while (i-- && !(_prefixes[i] + property in s)) {}
9076
9077  return i < 0 ? null : (i === 3 ? "ms" : i >= 0 ? _prefixes[i] : "") + property;
9078},
9079    _initCore = function _initCore() {
9080  if (_windowExists() && window.document) {
9081    _win = window;
9082    _doc = _win.document;
9083    _docElement = _doc.documentElement;
9084    _tempDiv = _createElement("div") || {
9085      style: {}
9086    };
9087    _tempDivStyler = _createElement("div");
9088    _transformProp = _checkPropPrefix(_transformProp);
9089    _transformOriginProp = _transformProp + "Origin";
9090    _tempDiv.style.cssText = "border-width:0;line-height:0;position:absolute;padding:0"; //make sure to override certain properties that may contaminate measurements, in case the user has overreaching style sheets.
9091
9092    _supports3D = !!_checkPropPrefix("perspective");
9093    _pluginInitted = 1;
9094  }
9095},
9096    _getBBoxHack = function _getBBoxHack(swapIfPossible) {
9097  //works around issues in some browsers (like Firefox) that don't correctly report getBBox() on SVG elements inside a <defs> element and/or <mask>. We try creating an SVG, adding it to the documentElement and toss the element in there so that it's definitely part of the rendering tree, then grab the bbox and if it works, we actually swap out the original getBBox() method for our own that does these extra steps whenever getBBox is needed. This helps ensure that performance is optimal (only do all these extra steps when absolutely necessary...most elements don't need it).
9098  var svg = _createElement("svg", this.ownerSVGElement && this.ownerSVGElement.getAttribute("xmlns") || "http://www.w3.org/2000/svg"),
9099      oldParent = this.parentNode,
9100      oldSibling = this.nextSibling,
9101      oldCSS = this.style.cssText,
9102      bbox;
9103
9104  _docElement.appendChild(svg);
9105
9106  svg.appendChild(this);
9107  this.style.display = "block";
9108
9109  if (swapIfPossible) {
9110    try {
9111      bbox = this.getBBox();
9112      this._gsapBBox = this.getBBox; //store the original
9113
9114      this.getBBox = _getBBoxHack;
9115    } catch (e) {}
9116  } else if (this._gsapBBox) {
9117    bbox = this._gsapBBox();
9118  }
9119
9120  if (oldParent) {
9121    if (oldSibling) {
9122      oldParent.insertBefore(this, oldSibling);
9123    } else {
9124      oldParent.appendChild(this);
9125    }
9126  }
9127
9128  _docElement.removeChild(svg);
9129
9130  this.style.cssText = oldCSS;
9131  return bbox;
9132},
9133    _getAttributeFallbacks = function _getAttributeFallbacks(target, attributesArray) {
9134  var i = attributesArray.length;
9135
9136  while (i--) {
9137    if (target.hasAttribute(attributesArray[i])) {
9138      return target.getAttribute(attributesArray[i]);
9139    }
9140  }
9141},
9142    _getBBox = function _getBBox(target) {
9143  var bounds;
9144
9145  try {
9146    bounds = target.getBBox(); //Firefox throws errors if you try calling getBBox() on an SVG element that's not rendered (like in a <symbol> or <defs>). https://bugzilla.mozilla.org/show_bug.cgi?id=612118
9147  } catch (error) {
9148    bounds = _getBBoxHack.call(target, true);
9149  }
9150
9151  bounds && (bounds.width || bounds.height) || target.getBBox === _getBBoxHack || (bounds = _getBBoxHack.call(target, true)); //some browsers (like Firefox) misreport the bounds if the element has zero width and height (it just assumes it's at x:0, y:0), thus we need to manually grab the position in that case.
9152
9153  return bounds && !bounds.width && !bounds.x && !bounds.y ? {
9154    x: +_getAttributeFallbacks(target, ["x", "cx", "x1"]) || 0,
9155    y: +_getAttributeFallbacks(target, ["y", "cy", "y1"]) || 0,
9156    width: 0,
9157    height: 0
9158  } : bounds;
9159},
9160    _isSVG = function _isSVG(e) {
9161  return !!(e.getCTM && (!e.parentNode || e.ownerSVGElement) && _getBBox(e));
9162},
9163    //reports if the element is an SVG on which getBBox() actually works
9164_removeProperty = function _removeProperty(target, property) {
9165  if (property) {
9166    var style = target.style;
9167
9168    if (property in _transformProps && property !== _transformOriginProp) {
9169      property = _transformProp;
9170    }
9171
9172    if (style.removeProperty) {
9173      if (property.substr(0, 2) === "ms" || property.substr(0, 6) === "webkit") {
9174        //Microsoft and some Webkit browsers don't conform to the standard of capitalizing the first prefix character, so we adjust so that when we prefix the caps with a dash, it's correct (otherwise it'd be "ms-transform" instead of "-ms-transform" for IE9, for example)
9175        property = "-" + property;
9176      }
9177
9178      style.removeProperty(property.replace(_capsExp, "-$1").toLowerCase());
9179    } else {
9180      //note: old versions of IE use "removeAttribute()" instead of "removeProperty()"
9181      style.removeAttribute(property);
9182    }
9183  }
9184},
9185    _addNonTweeningPT = function _addNonTweeningPT(plugin, target, property, beginning, end, onlySetAtEnd) {
9186  var pt = new __WEBPACK_IMPORTED_MODULE_0__gsap_core_js__["b" /* PropTween */](plugin._pt, target, property, 0, 1, onlySetAtEnd ? _renderNonTweeningValueOnlyAtEnd : _renderNonTweeningValue);
9187  plugin._pt = pt;
9188  pt.b = beginning;
9189  pt.e = end;
9190
9191  plugin._props.push(property);
9192
9193  return pt;
9194},
9195    _nonConvertibleUnits = {
9196  deg: 1,
9197  rad: 1,
9198  turn: 1
9199},
9200    //takes a single value like 20px and converts it to the unit specified, like "%", returning only the numeric amount.
9201_convertToUnit = function _convertToUnit(target, property, value, unit) {
9202  var curValue = parseFloat(value) || 0,
9203      curUnit = (value + "").trim().substr((curValue + "").length) || "px",
9204      // some browsers leave extra whitespace at the beginning of CSS variables, hence the need to trim()
9205  style = _tempDiv.style,
9206      horizontal = _horizontalExp.test(property),
9207      isRootSVG = target.tagName.toLowerCase() === "svg",
9208      measureProperty = (isRootSVG ? "client" : "offset") + (horizontal ? "Width" : "Height"),
9209      amount = 100,
9210      toPixels = unit === "px",
9211      toPercent = unit === "%",
9212      px,
9213      parent,
9214      cache,
9215      isSVG;
9216
9217  if (unit === curUnit || !curValue || _nonConvertibleUnits[unit] || _nonConvertibleUnits[curUnit]) {
9218    return curValue;
9219  }
9220
9221  curUnit !== "px" && !toPixels && (curValue = _convertToUnit(target, property, value, "px"));
9222  isSVG = target.getCTM && _isSVG(target);
9223
9224  if ((toPercent || curUnit === "%") && (_transformProps[property] || ~property.indexOf("adius"))) {
9225    px = isSVG ? target.getBBox()[horizontal ? "width" : "height"] : target[measureProperty];
9226    return Object(__WEBPACK_IMPORTED_MODULE_0__gsap_core_js__["s" /* _round */])(toPercent ? curValue / px * amount : curValue / 100 * px);
9227  }
9228
9229  style[horizontal ? "width" : "height"] = amount + (toPixels ? curUnit : unit);
9230  parent = ~property.indexOf("adius") || unit === "em" && target.appendChild && !isRootSVG ? target : target.parentNode;
9231
9232  if (isSVG) {
9233    parent = (target.ownerSVGElement || {}).parentNode;
9234  }
9235
9236  if (!parent || parent === _doc || !parent.appendChild) {
9237    parent = _doc.body;
9238  }
9239
9240  cache = parent._gsap;
9241
9242  if (cache && toPercent && cache.width && horizontal && cache.time === __WEBPACK_IMPORTED_MODULE_0__gsap_core_js__["u" /* _ticker */].time) {
9243    return Object(__WEBPACK_IMPORTED_MODULE_0__gsap_core_js__["s" /* _round */])(curValue / cache.width * amount);
9244  } else {
9245    (toPercent || curUnit === "%") && (style.position = _getComputedProperty(target, "position"));
9246    parent === target && (style.position = "static"); // like for borderRadius, if it's a % we must have it relative to the target itself but that may not have position: relative or position: absolute in 
9246which case it'd go up the chain until it finds its offsetParent (bad). position: static protects against that.
9247
9248    parent.appendChild(_tempDiv);
9249    px = _tempDiv[measureProperty];
9250    parent.removeChild(_tempDiv);
9251    style.position = "absolute";
9252
9253    if (horizontal && toPercent) {
9254      cache = Object(__WEBPACK_IMPORTED_MODULE_0__gsap_core_js__["g" /* _getCache */])(parent);
9255      cache.time = __WEBPACK_IMPORTED_MODULE_0__gsap_core_js__["u" /* _ticker */].time;
9256      cache.width = parent[measureProperty];
9257    }
9258  }
9259
9260  return Object(__WEBPACK_IMPORTED_MODULE_0__gsap_core_js__["s" /* _round */])(toPixels ? px * curValue / amount : px && curValue ? amount / px * curValue : 0);
9261},
9262    _get = function _get(target, property, unit, uncache) {
9263  var value;
9264  _pluginInitted || _initCore();
9265
9266  if (property in _propertyAliases && property !== "transform") {
9267    property = _propertyAliases[property];
9268
9269    if (~property.indexOf(",")) {
9270      property = property.split(",")[0];
9271    }
9272  }
9273
9274  if (_transformProps[property] && property !== "transform") {
9275    value = _parseTransform(target, uncache);
9276    value = property !== "transformOrigin" ? value[property] : _firstTwoOnly(_getComputedProperty(target, _transformOriginProp)) + " " + value.zOrigin + "px";
9277  } else {
9278    value = target.style[property];
9279
9280    if (!value || value === "auto" || uncache || ~(value + "").indexOf("calc(")) {
9281      value = _specialProps[property] && _specialProps[property](target, property, unit) || _getComputedProperty(target, property) || Object(__WEBPACK_IMPORTED_MODULE_0__gsap_core_js__["h" /* _getProperty */])(target, property) || (property === "opacity" ? 1 : 0); // note: some browsers, like Firefox, don't report borderRadius correctly! Instead, it only reports every corner like  borderTopLeftRadius
9282    }
9283  }
9284
9285  return unit && !~(value + "").trim().indexOf(" ") ? _convertToUnit(target, property, value, unit) + unit : value;
9286},
9287    _tweenComplexCSSString = function _tweenComplexCSSString(target, prop, start, end) {
9288  //note: we call _tweenComplexCSSString.call(pluginInstance...) to ensure that it's scoped properly. We may call it from within a plugin too, thus "this" would refer to the plugin.
9289  if (!start || start === "none") {
9290    // some browsers like Safari actually PREFER the prefixed property and mis-report the unprefixed value like clipPath (BUG). In other words, even though clipPath exists in the style ("clipPath" in target.style) and it's set in the CSS properly (along with -webkit-clip-path), Safari reports clipPath as "none" whereas WebkitClipPath reports accurately like "ellipse(100% 0% at 50% 0%)", so in this case we must SWITCH to using the prefixed property instead. See https://greensock.com/forums/topic/18310-clippath-doesnt-work-on-ios/
9291    var p = _checkPropPrefix(prop, target, 1),
9292        s = p && _getComputedProperty(target, p, 1);
9293
9294    if (s && s !== start) {
9295      prop = p;
9296      start = s;
9297    } else if (prop === "borderColor") {
9298      start = _getComputedProperty(target, "borderTopColor"); // Firefox bug: always reports "borderColor" as "", so we must fall back to borderTopColor. See https://greensock.com/forums/topic/24583-how-to-return-colors-that-i-had-after-reverse/
9299    }
9300  }
9301
9302  var pt = new __WEBPACK_IMPORTED_MODULE_0__gsap_core_js__["b" /* PropTween */](this._pt, target.style, prop, 0, 1, __WEBPACK_IMPORTED_MODULE_0__gsap_core_js__["q" /* _renderComplexString */]),
9303      index = 0,
9304      matchIndex = 0,
9305      a,
9306      result,
9307      startValues,
9308      startNum,
9309      color,
9310      startValue,
9311      endValue,
9312      endNum,
9313      chunk,
9314      endUnit,
9315      startUnit,
9316      relative,
9317      endValues;
9318  pt.b = start;
9319  pt.e = end;
9320  start += ""; //ensure values are strings
9321
9322  end += "";
9323
9324  if (end === "auto") {
9325    target.style[prop] = end;
9326    end = _getComputedProperty(target, prop) || end;
9327    target.style[prop] = start;
9328  }
9329
9330  a = [start, end];
9331
9332  Object(__WEBPACK_IMPORTED_MODULE_0__gsap_core_js__["d" /* _colorStringFilter */])(a); //pass an array with the starting and ending values and let the filter do whatever it needs to the values. If colors are found, it returns true and then we must match where the color shows up order-wise because for things like boxShadow, sometimes the browser provides the computed values with the color FIRST, but the user provides it with the color LAST, so flip them if necessary. Same for drop-shadow().
9333
9334
9335  start = a[0];
9336  end = a[1];
9337  startValues = start.match(__WEBPACK_IMPORTED_MODULE_0__gsap_core_js__["n" /* _numWithUnitExp */]) || [];
9338  endValues = end.match(__WEBPACK_IMPORTED_MODULE_0__gsap_core_js__["n" /* _numWithUnitExp */]) || [];
9339
9340  if (endValues.length) {
9341    while (result = __WEBPACK_IMPORTED_MODULE_0__gsap_core_js__["n" /* _numWithUnitExp */].exec(end)) {
9342      endValue = result[0];
9343      chunk = end.substring(index, result.index);
9344
9345      if (color) {
9346        color = (color + 1) % 5;
9347      } else if (chunk.substr(-5) === "rgba(" || chunk.substr(-5) === "hsla(") {
9348        color = 1;
9349      }
9350
9351      if (endValue !== (startValue = startValues[matchIndex++] || "")) {
9352        startNum = parseFloat(startValue) || 0;
9353        startUnit = startValue.substr((startNum + "").length);
9354        relative = endValue.charAt(1) === "=" ? +(endValue.charAt(0) + "1") : 0;
9355
9356        if (relative) {
9357          endValue = endValue.substr(2);
9358        }
9359
9360        endNum = parseFloat(endValue);
9361        endUnit = endValue.substr((endNum + "").length);
9362        index = __WEBPACK_IMPORTED_MODULE_0__gsap_core_js__["n" /* _numWithUnitExp */].lastIndex - endUnit.length;
9363
9364        if (!endUnit) {
9365          //if something like "perspective:300" is passed in and we must add a unit to the end
9366          endUnit = endUnit || __WEBPACK_IMPORTED_MODULE_0__gsap_core_js__["e" /* _config */].units[prop] || startUnit;
9367
9368          if (index === end.length) {
9369            end += endUnit;
9370            pt.e += endUnit;
9371          }
9372        }
9373
9374        if (startUnit !== endUnit) {
9375          startNum = _convertToUnit(target, prop, startValue, endUnit) || 0;
9376        } //these nested PropTweens are handled in a special way - we'll never actually call a render or setter method on them. We'll just loop through them in the parent complex string PropTween's render method.
9377
9378
9379        pt._pt = {
9380          _next: pt._pt,
9381          p: chunk || matchIndex === 1 ? chunk : ",",
vendor: 4,794 bytes, lines 9382-9513
9382          //note: SVG spec allows omission of comma/space when a negative sign is wedged between two numbers, like 2.5-5.3 instead of 2.5,-5.3 but when tweening, the negative value may switch to positive, so we insert the comma just in case.
9383          s: startNum,
9384          c: relative ? relative * endNum : endNum - startNum,
9385          m: color && color < 4 || prop === "zIndex" ? Math.round : 0
9386        };
9387      }
9388    }
9389
9390    pt.c = index < end.length ? end.substring(index, end.length) : ""; //we use the "c" of the PropTween to store the final part of the string (after the last number)
9391  } else {
9392    pt.r = prop === "display" && end === "none" ? _renderNonTweeningValueOnlyAtEnd : _renderNonTweeningValue;
9393  }
9394
9395  __WEBPACK_IMPORTED_MODULE_0__gsap_core_js__["p" /* _relExp */].test(end) && (pt.e = 0); //if the end string contains relative values or dynamic random(...) values, delete the end it so that on the final render we don't actually set it to the string with += or -= characters (forces it to use the calculated value).
9396
9397  this._pt = pt; //start the linked list with this new PropTween. Remember, we call _tweenComplexCSSString.call(pluginInstance...) to ensure that it's scoped properly. We may call it from within another plugin too, thus "this" would refer to the plugin.
9398
9399  return pt;
9400},
9401    _keywordToPercent = {
9402  top: "0%",
9403  bottom: "100%",
9404  left: "0%",
9405  right: "100%",
9406  center: "50%"
9407},
9408    _convertKeywordsToPercentages = function _convertKeywordsToPercentages(value) {
9409  var split = value.split(" "),
9410      x = split[0],
9411      y = split[1] || "50%";
9412
9413  if (x === "top" || x === "bottom" || y === "left" || y === "right") {
9414    //the user provided them in the wrong order, so flip them
9415    value = x;
9416    x = y;
9417    y = value;
9418  }
9419
9420  split[0] = _keywordToPercent[x] || x;
9421  split[1] = _keywordToPercent[y] || y;
9422  return split.join(" ");
9423},
9424    _renderClearProps = function _renderClearProps(ratio, data) {
9425  if (data.tween && data.tween._time === data.tween._dur) {
9426    var target = data.t,
9427        style = target.style,
9428        props = data.u,
9429        cache = target._gsap,
9430        prop,
9431        clearTransforms,
9432        i;
9433
9434    if (props === "all" || props === true) {
9435      style.cssText = "";
9436      clearTransforms = 1;
9437    } else {
9438      props = props.split(",");
9439      i = props.length;
9440
9441      while (--i > -1) {
9442        prop = props[i];
9443
9444        if (_transformProps[prop]) {
9445          clearTransforms = 1;
9446          prop = prop === "transformOrigin" ? _transformOriginProp : _transformProp;
9447        }
9448
9449        _removeProperty(target, prop);
9450      }
9451    }
9452
9453    if (clearTransforms) {
9454      _removeProperty(target, _transformProp);
9455
9456      if (cache) {
9457        cache.svg && target.removeAttribute("transform");
9458
9459        _parseTransform(target, 1); // force all the cached values back to "normal"/identity, otherwise if there's another tween that's already set to render transforms on this element, it could display the wrong values.
9460
9461
9462        cache.uncache = 1;
9463      }
9464    }
9465  }
9466},
9467    // note: specialProps should return 1 if (and only if) they have a non-zero priority. It indicates we need to sort the linked list.
9468_specialProps = {
9469  clearProps: function clearProps(plugin, target, property, endValue, tween) {
9470    if (tween.data !== "isFromStart") {
9471      var pt = plugin._pt = new __WEBPACK_IMPORTED_MODULE_0__gsap_core_js__["b" /* PropTween */](plugin._pt, target, property, 0, 0, _renderClearProps);
9472      pt.u = endValue;
9473      pt.pr = -10;
9474      pt.tween = tween;
9475
9476      plugin._props.push(property);
9477
9478      return 1;
9479    }
9480  }
9481  /* className feature (about 0.4kb gzipped).
9482  , className(plugin, target, property, endValue, tween) {
9483  	let _renderClassName = (ratio, data) => {
9484  			data.css.render(ratio, data.css);
9485  			if (!ratio || ratio === 1) {
9486  				let inline = data.rmv,
9487  					target = data.t,
9488  					p;
9489  				target.setAttribute("class", ratio ? data.e : data.b);
9490  				for (p in inline) {
9491  					_removeProperty(target, p);
9492  				}
9493  			}
9494  		},
9495  		_getAllStyles = (target) => {
9496  			let styles = {},
9497  				computed = getComputedStyle(target),
9498  				p;
9499  			for (p in computed) {
9500  				if (isNaN(p) && p !== "cssText" && p !== "length") {
9501  					styles[p] = computed[p];
9502  				}
9503  			}
9504  			_setDefaults(styles, _parseTransform(target, 1));
9505  			return styles;
9506  		},
9507  		startClassList = target.getAttribute("class"),
9508  		style = target.style,
9509  		cssText = style.cssText,
9510  		cache = target._gsap,
9511  		classPT = cache.classPT,
9512  		inlineToRemoveAtEnd = {},
9513  		data = {t:target, plugin:plugin, rmv:inlineToRemoveAtEnd, b:startClassList, e:(endValue.charAt(1) !== "=") ? endValue : startClassList.replace(new RegExp("(?:\\s|^)" + endValue.substr(2) + "(?![\\w-])"), "") + ((endValue.charAt(0) === "+") ? " " + endValue.substr(2) : "")},
9514  		changingVars = {},
9515  		startVars = _getAllStyles(target),
9516  		transformRelated = /(transform|perspective)/i,
9517  		endVars, p;
9518  	if (classPT) {
9519  		classPT.r(1, classPT.d);
9520  		_removeLinkedListItem(classPT.d.plugin, classPT, "_pt");
9521  	}
9522  	target.setAttribute("class", data.e);
9523  	endVars = _getAllStyles(target, true);
9524  	target.setAttribute("class", startClassList);
9525  	for (p in endVars) {
9526  		if (endVars[p] !== startVars[p] && !transformRelated.test(p)) {
9527  			changingVars[p] = endVars[p];
9528  			if (!style[p] && style[p] !== "0") {
9529  				inlineToRemoveAtEnd[p] = 1;
9530  			}
9531  		}
9532  	}
9533  	cache.classPT = plugin._pt = new PropTween(plugin._pt, target, "className", 0, 0, _renderClassName, data, 0, -11);
9534  	if (style.cssText !== cssText) { //only apply if things change. Otherwise, in cases like a background-image that's pulled dynamically, it could cause a refresh. See https://greensock.com/forums/topic/20368-possible-gsap-bug-switching-classnames-in-chrome/.
9535  		style.cssText = cssText; //we recorded cssText before we swapped classes and ran _getAllStyles() because in cases when a className tween is overwritten, we remove all the related tweening properties from that class change (otherwise class-specific stuff can't override properties we've directly set on the target's style object due to specificity).
9536  	}
9537  	_parseTransform(target, true); //to clear the caching of transforms
9538  	data.css = new gsap.plugins.css();
vendor: 4,308 bytes, lines 9539-9626
9539  	data.css.init(target, changingVars, tween);
9540  	plugin._props.push(...data.css._props);
9541  	return 1;
9542  }
9543  */
9544
9545},
9546
9547/*
9548 * --------------------------------------------------------------------------------------
9549 * TRANSFORMS
9550 * --------------------------------------------------------------------------------------
9551 */
9552_identity2DMatrix = [1, 0, 0, 1, 0, 0],
9553    _rotationalProperties = {},
9554    _isNullTransform = function _isNullTransform(value) {
9555  return value === "matrix(1, 0, 0, 1, 0, 0)" || value === "none" || !value;
9556},
9557    _getComputedTransformMatrixAsArray = function _getComputedTransformMatrixAsArray(target) {
9558  var matrixString = _getComputedProperty(target, _transformProp);
9559
9560  return _isNullTransform(matrixString) ? _identity2DMatrix : matrixString.substr(7).match(__WEBPACK_IMPORTED_MODULE_0__gsap_core_js__["m" /* _numExp */]).map(__WEBPACK_IMPORTED_MODULE_0__gsap_core_js__["s" /* _round */]);
9561},
9562    _getMatrix = function _getMatrix(target, force2D) {
9563  var cache = target._gsap || Object(__WEBPACK_IMPORTED_MODULE_0__gsap_core_js__["g" /* _getCache */])(target),
9564      style = target.style,
9565      matrix = _getComputedTransformMatrixAsArray(target),
9566      parent,
9567      nextSibling,
9568      temp,
9569      addedToDOM;
9570
9571  if (cache.svg && target.getAttribute("transform")) {
9572    temp = target.transform.baseVal.consolidate().matrix; //ensures that even complex values like "translate(50,60) rotate(135,0,0)" are parsed because it mashes it into a matrix.
9573
9574    matrix = [temp.a, temp.b, temp.c, temp.d, temp.e, temp.f];
9575    return matrix.join(",") === "1,0,0,1,0,0" ? _identity2DMatrix : matrix;
9576  } else if (matrix === _identity2DMatrix && !target.offsetParent && target !== _docElement && !cache.svg) {
9577    //note: if offsetParent is null, that means the element isn't in the normal document flow, like if it has display:none or one of its ancestors has display:none). Firefox returns null for getComputedStyle() if the element is in an iframe that has display:none. https://bugzilla.mozilla.org/show_bug.cgi?id=548397
9578    //browsers don't report transforms accurately unless the element is in the DOM and has a display value that's not "none". Firefox and Microsoft browsers have a partial bug where they'll report transforms even if display:none BUT not any percentage-based values like translate(-50%, 8px) will be reported as if it's translate(0, 8px).
9579    temp = style.display;
9580    style.display = "block";
9581    parent = target.parentNode;
9582
9583    if (!parent || !target.offsetParent) {
9584      // note: in 3.3.0 we switched target.offsetParent to _doc.body.contains(target) to avoid [sometimes unnecessary] MutationObserver calls but that wasn't adequate because there are edge cases where nested position: fixed elements need to get reparented to accurately sense transforms. See https://github.com/greensock/GSAP/issues/388 and https://github.com/greensock/GSAP/issues/375
9585      addedToDOM = 1; //flag
9586
9587      nextSibling = target.nextSibling;
9588
9589      _docElement.appendChild(target); //we must add it to the DOM in order to get values properly
9590
9591    }
9592
9593    matrix = _getComputedTransformMatrixAsArray(target);
9594    temp ? style.display = temp : _removeProperty(target, "display");
9595
9596    if (addedToDOM) {
9597      nextSibling ? parent.insertBefore(target, nextSibling) : parent ? parent.appendChild(target) : _docElement.removeChild(target);
9598    }
9599  }
9600
9601  return force2D && matrix.length > 6 ? [matrix[0], matrix[1], matrix[4], matrix[5], matrix[12], matrix[13]] : matrix;
9602},
9603    _applySVGOrigin = function _applySVGOrigin(target, origin, originIsAbsolute, smooth, matrixArray, pluginToAddPropTweensTo) {
9604  var cache = target._gsap,
9605      matrix = matrixArray || _getMatrix(target, true),
9606      xOriginOld = cache.xOrigin || 0,
9607      yOriginOld = cache.yOrigin || 0,
9608      xOffsetOld = cache.xOffset || 0,
9609      yOffsetOld = cache.yOffset || 0,
9610      a = matrix[0],
9611      b = matrix[1],
9612      c = matrix[2],
9613      d = matrix[3],
9614      tx = matrix[4],
9615      ty = matrix[5],
9616      originSplit = origin.split(" "),
9617      xOrigin = parseFloat(originSplit[0]) || 0,
9618      yOrigin = parseFloat(originSplit[1]) || 0,
9619      bounds,
9620      determinant,
9621      x,
9622      y;
9623
9624  if (!originIsAbsolute) {
9625    bounds = _getBBox(target);
9626    xOrigin = bounds.x + (~originSplit[0].indexOf("%") ? xOrigin / 100 * boun
vendor: 6,067 bytes, lines 9626-9820
9626ds.width : xOrigin);
9627    yOrigin = bounds.y + (~(originSplit[1] || originSplit[0]).indexOf("%") ? yOrigin / 100 * bounds.height : yOrigin);
9628  } else if (matrix !== _identity2DMatrix && (determinant = a * d - b * c)) {
9629    //if it's zero (like if scaleX and scaleY are zero), skip it to avoid errors with dividing by zero.
9630    x = xOrigin * (d / determinant) + yOrigin * (-c / determinant) + (c * ty - d * tx) / determinant;
9631    y = xOrigin * (-b / determinant) + yOrigin * (a / determinant) - (a * ty - b * tx) / determinant;
9632    xOrigin = x;
9633    yOrigin = y;
9634  }
9635
9636  if (smooth || smooth !== false && cache.smooth) {
9637    tx = xOrigin - xOriginOld;
9638    ty = yOrigin - yOriginOld;
9639    cache.xOffset = xOffsetOld + (tx * a + ty * c) - tx;
9640    cache.yOffset = yOffsetOld + (tx * b + ty * d) - ty;
9641  } else {
9642    cache.xOffset = cache.yOffset = 0;
9643  }
9644
9645  cache.xOrigin = xOrigin;
9646  cache.yOrigin = yOrigin;
9647  cache.smooth = !!smooth;
9648  cache.origin = origin;
9649  cache.originIsAbsolute = !!originIsAbsolute;
9650  target.style[_transformOriginProp] = "0px 0px"; //otherwise, if someone sets  an origin via CSS, it will likely interfere with the SVG transform attribute ones (because remember, we're baking the origin into the matrix() value).
9651
9652  if (pluginToAddPropTweensTo) {
9653    _addNonTweeningPT(pluginToAddPropTweensTo, cache, "xOrigin", xOriginOld, xOrigin);
9654
9655    _addNonTweeningPT(pluginToAddPropTweensTo, cache, "yOrigin", yOriginOld, yOrigin);
9656
9657    _addNonTweeningPT(pluginToAddPropTweensTo, cache, "xOffset", xOffsetOld, cache.xOffset);
9658
9659    _addNonTweeningPT(pluginToAddPropTweensTo, cache, "yOffset", yOffsetOld, cache.yOffset);
9660  }
9661
9662  target.setAttribute("data-svg-origin", xOrigin + " " + yOrigin);
9663},
9664    _parseTransform = function _parseTransform(target, uncache) {
9665  var cache = target._gsap || new __WEBPACK_IMPORTED_MODULE_0__gsap_core_js__["a" /* GSCache */](target);
9666
9667  if ("x" in cache && !uncache && !cache.uncache) {
9668    return cache;
9669  }
9670
9671  var style = target.style,
9672      invertedScaleX = cache.scaleX < 0,
9673      px = "px",
9674      deg = "deg",
9675      origin = _getComputedProperty(target, _transformOriginProp) || "0",
9676      x,
9677      y,
9678      z,
9679      scaleX,
9680      scaleY,
9681      rotation,
9682      rotationX,
9683      rotationY,
9684      skewX,
9685      skewY,
9686      perspective,
9687      xOrigin,
9688      yOrigin,
9689      matrix,
9690      angle,
9691      cos,
9692      sin,
9693      a,
9694      b,
9695      c,
9696      d,
9697      a12,
9698      a22,
9699      t1,
9700      t2,
9701      t3,
9702      a13,
9703      a23,
9704      a33,
9705      a42,
9706      a43,
9707      a32;
9708  x = y = z = rotation = rotationX = rotationY = skewX = skewY = perspective = 0;
9709  scaleX = scaleY = 1;
9710  cache.svg = !!(target.getCTM && _isSVG(target));
9711  matrix = _getMatrix(target, cache.svg);
9712
9713  if (cache.svg) {
9714    t1 = !cache.uncache && target.getAttribute("data-svg-origin");
9715
9716    _applySVGOrigin(target, t1 || origin, !!t1 || cache.originIsAbsolute, cache.smooth !== false, matrix);
9717  }
9718
9719  xOrigin = cache.xOrigin || 0;
9720  yOrigin = cache.yOrigin || 0;
9721
9722  if (matrix !== _identity2DMatrix) {
9723    a = matrix[0]; //a11
9724
9725    b = matrix[1]; //a21
9726
9727    c = matrix[2]; //a31
9728
9729    d = matrix[3]; //a41
9730
9731    x = a12 = matrix[4];
9732    y = a22 = matrix[5]; //2D matrix
9733
9734    if (matrix.length === 6) {
9735      scaleX = Math.sqrt(a * a + b * b);
9736      scaleY = Math.sqrt(d * d + c * c);
9737      rotation = a || b ? _atan2(b, a) * _RAD2DEG : 0; //note: if scaleX is 0, we cannot accurately measure rotation. Same for skewX with a scaleY of 0. Therefore, we default to the previously recorded value (or zero if that doesn't exist).
9738
9739      skewX = c || d ? _atan2(c, d) * _RAD2DEG + rotation : 0;
9740      skewX && (scaleY *= Math.cos(skewX * _DEG2RAD));
9741
9742      if (cache.svg) {
9743        x -= xOrigin - (xOrigin * a + yOrigin * c);
9744        y -= yOrigin - (xOrigin * b + yOrigin * d);
9745      } //3D matrix
9746
9747    } else {
9748      a32 = matrix[6];
9749      a42 = matrix[7];
9750      a13 = matrix[8];
9751      a23 = matrix[9];
9752      a33 = matrix[10];
9753      a43 = matrix[11];
9754      x = matrix[12];
9755      y = matrix[13];
9756      z = matrix[14];
9757      angle = _atan2(a32, a33);
9758      rotationX = angle * _RAD2DEG; //rotationX
9759
9760      if (angle) {
9761        cos = Math.cos(-angle);
9762        sin = Math.sin(-angle);
9763        t1 = a12 * cos + a13 * sin;
9764        t2 = a22 * cos + a23 * sin;
9765        t3 = a32 * cos + a33 * sin;
9766        a13 = a12 * -sin + a13 * cos;
9767        a23 = a22 * -sin + a23 * cos;
9768        a33 = a32 * -sin + a33 * cos;
9769        a43 = a42 * -sin + a43 * cos;
9770        a12 = t1;
9771        a22 = t2;
9772        a32 = t3;
9773      } //rotationY
9774
9775
9776      angle = _atan2(-c, a33);
9777      rotationY = angle * _RAD2DEG;
9778
9779      if (angle) {
9780        cos = Math.cos(-angle);
9781        sin = Math.sin(-angle);
9782        t1 = a * cos - a13 * sin;
9783        t2 = b * cos - a23 * sin;
9784        t3 = c * cos - a33 * sin;
9785        a43 = d * sin + a43 * cos;
9786        a = t1;
9787        b = t2;
9788        c = t3;
9789      } //rotationZ
9790
9791
9792      angle = _atan2(b, a);
9793      rotation = angle * _RAD2DEG;
9794
9795      if (angle) {
9796        cos = Math.cos(angle);
9797        sin = Math.sin(angle);
9798        t1 = a * cos + b * sin;
9799        t2 = a12 * cos + a22 * sin;
9800        b = b * cos - a * sin;
9801        a22 = a22 * cos - a12 * sin;
9802        a = t1;
9803        a12 = t2;
9804      }
9805
9806      if (rotationX && Math.abs(rotationX) + Math.abs(rotation) > 359.9) {
9807        //when rotationY is set, it will often be parsed as 180 degrees different than it should be, and rotationX and rotation both being 180 (it looks the same), so we adjust for that here.
9808        rotationX = rotation = 0;
9809        rotationY = 180 - rotationY;
9810      }
9811
9812      scaleX = Object(__WEBPACK_IMPORTED_MODULE_0__gsap_core_js__["s" /* _round */])(Math.sqrt(a * a + b * b + c * c));
9813      scaleY = Object(__WEBPACK_IMPORTED_MODULE_0__gsap_core_js__["s" /* _round */])(Math.sqrt(a22 * a22 + a32 * a32));
9814      angle = _atan2(a12, a22);
9815      skewX = Math.abs(angle) > 0.0002 ? angle * _RAD2DEG : 0;
9816      perspective = a43 ? 1 / (a43 < 0 ? -a43 : a43) : 0;
9817    }
9818
9819    if (cache.svg) {
9820      //sense if there are CSS transforms applied on an SVG element in which case we must over
9820write them when rendering. The transform attribute is more reliable cross-browser, but we can't just remove the CSS ones because they may be applied in a CSS rule somewhere (not just inline).
9821      t1 = target.getAttribute("transform");
9822      cache.forceCSS = target.setAttribute("transform", "") || !_isNullTransform(_getComputedProperty(target, _transformProp));
9823      t1 && target.setAttribute("transform", t1);
9824    }
9825  }
9826
9827  if (Math.abs(skewX) > 90 && Math.abs(skewX) < 270) {
9828    if (invertedScaleX) {
9829      scaleX *= -1;
9830      skewX += rotation <= 0 ? 180 : -180;
9831      rotation += rotation <= 0 ? 180 : -180;
9832    } else {
9833      scaleY *= -1;
9834      skewX += skewX <= 0 ? 180 : -180;
9835    }
9836  }
9837
9838  cache.x = x - ((cache.xPercent = x && (cache.xPercent || (Math.round(target.offsetWidth / 2) === Math.round(-x) ? -50 : 0))) ? target.offsetWidth * cache.xPercent / 100 : 0) + px;
9839  cache.y = y - ((cache.yPercent = y && (cache.yPercent || (Math.round(target.offsetHeight / 2) === Math.round(-y) ? -50 : 0))) ? target.offsetHeight * cache.yPercent / 100 : 0) + px;
9840  cache.z = z + px;
9841  cache.scaleX = Object(__WEBPACK_IMPORTED_MODULE_0__gsap_core_js__["s" /* _round */])(scaleX);
9842  cache.scaleY = Object(__WEBPACK_IMPORTED_MODULE_0__gsap_core_js__["s" /* _round */])(scaleY);
9843  cache.rotation = Object(__WEBPACK_IMPORTED_MODULE_0__gsap_core_js__["s" /* _round */])(rotation) + deg;
9844  cache.rotationX = Object(__WEBPACK_IMPORTED_MODULE_0__gsap_core_js__["s" /* _round */])(rotationX) + deg;
9845  cache.rotationY = Object(__WEBPACK_IMPORTED_MODULE_0__gsap_core_js__["s" /* _round */])(rotationY) + deg;
9846  cache.skewX = skewX + deg;
9847  cache.skewY = skewY + deg;
9848  cache.transformPerspective = perspective + px;
9849
9850  if (cache.zOrigin = parseFloat(origin.split(" ")[2]) || 0) {
9851    style[_transformOriginProp] = _firstTwoOnly(origin);
9852  }
9853
9854  cache.xOffset = cache.yOffset = 0;
9855  cache.force3D = __WEBPACK_IMPORTED_MODULE_0__gsap_core_js__["e" /* _config */].force3D;
9856  cache.renderTransform = cache.svg ? _renderSVGTransforms : _supports3D ? _renderCSSTransforms : _renderNon3DTransforms;
9857  cache.uncache = 0;
9858  return cache;
9859},
9860    _firstTwoOnly = function _firstTwoOnly(value) {
9861  return (value = value.split(" "))[0] + " " + value[1];
9862},
9863    //for handling transformOrigin values, stripping out the 3rd dimension
9864_addPxTranslate = function _addPxTranslate(target, start, value) {
9865  var unit = Object(__WEBPACK_IMPORTED_MODULE_0__gsap_core_js__["v" /* getUnit */])(start);
9866  return Object(__WEBPACK_IMPORTED_MODULE_0__gsap_core_js__["s" /* _round */])(parseFloat(start) + parseFloat(_convertToUnit(target, "x", value + "px", unit))) + unit;
9867},
9868    _renderNon3DTransforms = function _renderNon3DTransforms(ratio, cache) {
9869  cache.z = "0px";
9870  cache.rotationY = cache.rotationX = "0deg";
vendor: 5,516 bytes, lines 9871-10032
9871  cache.force3D = 0;
9872
9873  _renderCSSTransforms(ratio, cache);
9874},
9875    _zeroDeg = "0deg",
9876    _zeroPx = "0px",
9877    _endParenthesis = ") ",
9878    _renderCSSTransforms = function _renderCSSTransforms(ratio, cache) {
9879  var _ref = cache || this,
9880      xPercent = _ref.xPercent,
9881      yPercent = _ref.yPercent,
9882      x = _ref.x,
9883      y = _ref.y,
9884      z = _ref.z,
9885      rotation = _ref.rotation,
9886      rotationY = _ref.rotationY,
9887      rotationX = _ref.rotationX,
9888      skewX = _ref.skewX,
9889      skewY = _ref.skewY,
9890      scaleX = _ref.scaleX,
9891      scaleY = _ref.scaleY,
9892      transformPerspective = _ref.transformPerspective,
9893      force3D = _ref.force3D,
9894      target = _ref.target,
9895      zOrigin = _ref.zOrigin,
9896      transforms = "",
9897      use3D = force3D === "auto" && ratio && ratio !== 1 || force3D === true; // Safari has a bug that causes it not to render 3D transform-origin values properly, so we force the z origin to 0, record it in the cache, and then do the math here to offset the translate values accordingly (basically do the 3D transform-origin part manually)
9898
9899
9900  if (zOrigin && (rotationX !== _zeroDeg || rotationY !== _zeroDeg)) {
9901    var angle = parseFloat(rotationY) * _DEG2RAD,
9902        a13 = Math.sin(angle),
9903        a33 = Math.cos(angle),
9904        cos;
9905
9906    angle = parseFloat(rotationX) * _DEG2RAD;
9907    cos = Math.cos(angle);
9908    x = _addPxTranslate(target, x, a13 * cos * -zOrigin);
9909    y = _addPxTranslate(target, y, -Math.sin(angle) * -zOrigin);
9910    z = _addPxTranslate(target, z, a33 * cos * -zOrigin + zOrigin);
9911  }
9912
9913  if (transformPerspective !== _zeroPx) {
9914    transforms += "perspective(" + transformPerspective + _endParenthesis;
9915  }
9916
9917  if (xPercent || yPercent) {
9918    transforms += "translate(" + xPercent + "%, " + yPercent + "%) ";
9919  }
9920
9921  if (use3D || x !== _zeroPx || y !== _zeroPx || z !== _zeroPx) {
9922    transforms += z !== _zeroPx || use3D ? "translate3d(" + x + ", " + y + ", " + z + ") " : "translate(" + x + ", " + y + _endParenthesis;
9923  }
9924
9925  if (rotation !== _zeroDeg) {
9926    transforms += "rotate(" + rotation + _endParenthesis;
9927  }
9928
9929  if (rotationY !== _zeroDeg) {
9930    transforms += "rotateY(" + rotationY + _endParenthesis;
9931  }
9932
9933  if (rotationX !== _zeroDeg) {
9934    transforms += "rotateX(" + rotationX + _endParenthesis;
9935  }
9936
9937  if (skewX !== _zeroDeg || skewY !== _zeroDeg) {
9938    transforms += "skew(" + skewX + ", " + skewY + _endParenthesis;
9939  }
9940
9941  if (scaleX !== 1 || scaleY !== 1) {
9942    transforms += "scale(" + scaleX + ", " + scaleY + _endParenthesis;
9943  }
9944
9945  target.style[_transformProp] = transforms || "translate(0, 0)";
9946},
9947    _renderSVGTransforms = function _renderSVGTransforms(ratio, cache) {
9948  var _ref2 = cache || this,
9949      xPercent = _ref2.xPercent,
9950      yPercent = _ref2.yPercent,
9951      x = _ref2.x,
9952      y = _ref2.y,
9953      rotation = _ref2.rotation,
9954      skewX = _ref2.skewX,
9955      skewY = _ref2.skewY,
9956      scaleX = _ref2.scaleX,
9957      scaleY = _ref2.scaleY,
9958      target = _ref2.target,
9959      xOrigin = _ref2.xOrigin,
9960      yOrigin = _ref2.yOrigin,
9961      xOffset = _ref2.xOffset,
9962      yOffset = _ref2.yOffset,
9963      forceCSS = _ref2.forceCSS,
9964      tx = parseFloat(x),
9965      ty = parseFloat(y),
9966      a11,
9967      a21,
9968      a12,
9969      a22,
9970      temp;
9971
9972  rotation = parseFloat(rotation);
9973  skewX = parseFloat(skewX);
9974  skewY = parseFloat(skewY);
9975
9976  if (skewY) {
9977    //for performance reasons, we combine all skewing into the skewX and rotation values. Remember, a skewY of 10 degrees looks the same as a rotation of 10 degrees plus a skewX of 10 degrees.
9978    skewY = parseFloat(skewY);
9979    skewX += skewY;
9980    rotation += skewY;
9981  }
9982
9983  if (rotation || skewX) {
9984    rotation *= _DEG2RAD;
9985    skewX *= _DEG2RAD;
9986    a11 = Math.cos(rotation) * scaleX;
9987    a21 = Math.sin(rotation) * scaleX;
9988    a12 = Math.sin(rotation - skewX) * -scaleY;
9989    a22 = Math.cos(rotation - skewX) * scaleY;
9990
9991    if (skewX) {
9992      skewY *= _DEG2RAD;
9993      temp = Math.tan(skewX - skewY);
9994      temp = Math.sqrt(1 + temp * temp);
9995      a12 *= temp;
9996      a22 *= temp;
9997
9998      if (skewY) {
9999        temp = Math.tan(skewY);
10000        temp = Math.sqrt(1 + temp * temp);
10001        a11 *= temp;
10002        a21 *= temp;
10003      }
10004    }
10005
10006    a11 = Object(__WEBPACK_IMPORTED_MODULE_0__gsap_core_js__["s" /* _round */])(a11);
10007    a21 = Object(__WEBPACK_IMPORTED_MODULE_0__gsap_core_js__["s" /* _round */])(a21);
10008    a12 = Object(__WEBPACK_IMPORTED_MODULE_0__gsap_core_js__["s" /* _round */])(a12);
10009    a22 = Object(__WEBPACK_IMPORTED_MODULE_0__gsap_core_js__["s" /* _round */])(a22);
10010  } else {
10011    a11 = scaleX;
10012    a22 = scaleY;
10013    a21 = a12 = 0;
10014  }
10015
10016  if (tx && !~(x + "").indexOf("px") || ty && !~(y + "").indexOf("px")) {
10017    tx = _convertToUnit(target, "x", x, "px");
10018    ty = _convertToUnit(target, "y", y, "px");
10019  }
10020
10021  if (xOrigin || yOrigin || xOffset || yOffset) {
10022    tx = Object(__WEBPACK_IMPORTED_MODULE_0__gsap_core_js__["s" /* _round */])(tx + xOrigin - (xOrigin * a11 + yOrigin * a12) + xOffset);
10023    ty = Object(__WEBPACK_IMPORTED_MODULE_0__gsap_core_js__["s" /* _round */])(ty + yOrigin - (xOrigin * a21 + yOrigin * a22) + yOffset);
10024  }
10025
10026  if (xPercent || yPercent) {
10027    //The SVG spec doesn't support percentage-based translation in the "transform" attribute, so we merge it into the translation to simulate it.
10028    temp = target.getBBox();
10029    tx = Object(__WEBPACK_IMPORTED_MODULE_0__gsap_core_js__["s" /* _round */])(tx + xPercent / 100 * temp.width);
10030    ty = Object(__WEBPACK_IMPORTED_MODULE_0__gsap_core_js__["s" /* _round */])(ty + yPercent / 100 * temp.height);
10031  }
10032
vendor: 8,632 bytes, lines 10033-10237
10033  temp = "matrix(" + a11 + "," + a21 + "," + a12 + "," + a22 + "," + tx + "," + ty + ")";
10034  target.setAttribute("transform", temp);
10035  forceCSS && (target.style[_transformProp] = temp); //some browsers prioritize CSS transforms over the transform attribute. When we sense that the user has CSS transforms applied, we must overwrite them this way (otherwise some browser simply won't render the  transform attribute changes!)
10036},
10037    _addRotationalPropTween = function _addRotationalPropTween(plugin, target, property, startNum, endValue, relative) {
10038  var cap = 360,
10039      isString = Object(__WEBPACK_IMPORTED_MODULE_0__gsap_core_js__["j" /* _isString */])(endValue),
10040      endNum = parseFloat(endValue) * (isString && ~endValue.indexOf("rad") ? _RAD2DEG : 1),
10041      change = relative ? endNum * relative : endNum - startNum,
10042      finalValue = startNum + change + "deg",
10043      direction,
10044      pt;
10045
10046  if (isString) {
10047    direction = endValue.split("_")[1];
10048
10049    if (direction === "short") {
10050      change %= cap;
10051
10052      if (change !== change % (cap / 2)) {
10053        change += change < 0 ? cap : -cap;
10054      }
10055    }
10056
10057    if (direction === "cw" && change < 0) {
10058      change = (change + cap * _bigNum) % cap - ~~(change / cap) * cap;
10059    } else if (direction === "ccw" && change > 0) {
10060      change = (change - cap * _bigNum) % cap - ~~(change / cap) * cap;
10061    }
10062  }
10063
10064  plugin._pt = pt = new __WEBPACK_IMPORTED_MODULE_0__gsap_core_js__["b" /* PropTween */](plugin._pt, target, property, startNum, change, _renderPropWithEnd);
10065  pt.e = finalValue;
10066  pt.u = "deg";
10067
10068  plugin._props.push(property);
10069
10070  return pt;
10071},
10072    _addRawTransformPTs = function _addRawTransformPTs(plugin, transforms, target) {
10073  //for handling cases where someone passes in a whole transform string, like transform: "scale(2, 3) rotate(20deg) translateY(30em)"
10074  var style = _tempDivStyler.style,
10075      startCache = target._gsap,
10076      exclude = "perspective,force3D,transformOrigin,svgOrigin",
10077      endCache,
10078      p,
10079      startValue,
10080      endValue,
10081      startNum,
10082      endNum,
10083      startUnit,
10084      endUnit;
10085  style.cssText = getComputedStyle(target).cssText + ";position:absolute;display:block;"; //%-based translations will fail unless we set the width/height to match the original target (and padding/borders can affect it)
10086
10087  style[_transformProp] = transforms;
10088
10089  _doc.body.appendChild(_tempDivStyler);
10090
10091  endCache = _parseTransform(_tempDivStyler, 1);
10092
10093  for (p in _transformProps) {
10094    startValue = startCache[p];
10095    endValue = endCache[p];
10096
10097    if (startValue !== endValue && exclude.indexOf(p) < 0) {
10098      //tweening to no perspective gives very unintuitive results - just keep the same perspective in that case.
10099      startUnit = Object(__WEBPACK_IMPORTED_MODULE_0__gsap_core_js__["v" /* getUnit */])(startValue);
10100      endUnit = Object(__WEBPACK_IMPORTED_MODULE_0__gsap_core_js__["v" /* getUnit */])(endValue);
10101      startNum = startUnit !== endUnit ? _convertToUnit(target, p, startValue, endUnit) : parseFloat(startValue);
10102      endNum = parseFloat(endValue);
10103      plugin._pt = new __WEBPACK_IMPORTED_MODULE_0__gsap_core_js__["b" /* PropTween */](plugin._pt, startCache, p, startNum, endNum - startNum, _renderCSSProp);
10104      plugin._pt.u = endUnit || 0;
10105
10106      plugin._props.push(p);
10107    }
10108  }
10109
10110  _doc.body.removeChild(_tempDivStyler);
10111}; // handle splitting apart padding, margin, borderWidth, and borderRadius into their 4 components. Firefox, for example, won't report borderRadius correctly - it will only do borderTopLeftRadius and the other corners. We also want to handle paddingTop, marginLeft, borderRightWidth, etc.
10112
10113
10114Object(__WEBPACK_IMPORTED_MODULE_0__gsap_core_js__["f" /* _forEachName */])("padding,margin,Width,Radius", function (name, index) {
10115  var t = "Top",
10116      r = "Right",
10117      b = "Bottom",
10118      l = "Left",
10119      props = (index < 3 ? [t, r, b, l] : [t + l, t + r, b + r, b + l]).map(function (side) {
10120    return index < 2 ? name + side : "border" + side + name;
10121  });
10122
10123  _specialProps[index > 1 ? "border" + name : name] = function (plugin, target, property, endValue, tween) {
10124    var a, vars;
10125
10126    if (arguments.length < 4) {
10127      // getter, passed target, property, and unit (from _get())
10128      a = props.map(function (prop) {
10129        return _get(plugin, prop, property);
10130      });
10131      vars = a.join(" ");
10132      return vars.split(a[0]).length === 5 ? a[0] : vars;
10133    }
10134
10135    a = (endValue + "").split(" ");
10136    vars = {};
10137    props.forEach(function (prop, i) {
10138      return vars[prop] = a[i] = a[i] || a[(i - 1) / 2 | 0];
10139    });
10140    plugin.init(target, vars, tween);
10141  };
10142});
10143
10144var CSSPlugin = {
10145  name: "css",
10146  register: _initCore,
10147  targetTest: function targetTest(target) {
10148    return target.style && target.nodeType;
10149  },
10150  init: function init(target, vars, tween, index, targets) {
10151    var props = this._props,
10152        style = target.style,
10153        startAt = tween.vars.startAt,
10154        startValue,
10155        endValue,
10156        endNum,
10157        startNum,
10158        type,
10159        specialProp,
10160        p,
10161        startUnit,
10162        endUnit,
10163        relative,
10164        isTransformRelated,
10165        transformPropTween,
10166        cache,
10167        smooth,
10168        hasPriority;
10169    _pluginInitted || _initCore();
10170
10171    for (p in vars) {
10172      if (p === "autoRound") {
10173        continue;
10174      }
10175
10176      endValue = vars[p];
10177
10178      if (__WEBPACK_IMPORTED_MODULE_0__gsap_core_js__["o" /* _plugins */][p] && Object(__WEBPACK_IMPORTED_MODULE_0__gsap_core_js__["c" /* _checkPlugin */])(p, vars, tween, index, target, targets)) {
10179        // plugins
10180        continue;
10181      }
10182
10183      type = typeof endValue;
10184      specialProp = _specialProps[p];
10185
10186      if (type === "function") {
10187        endValue = endValue.call(tween, index, target, targets);
10188        type = typeof endValue;
10189      }
10190
10191      if (type === "string" && ~endValue.indexOf("random(")) {
10192        endValue = Object(__WEBPACK_IMPORTED_MODULE_0__gsap_core_js__["r" /* _replaceRandom */])(endValue);
10193      }
10194
10195      if (specialProp) {
10196        specialProp(this, target, p, endValue, tween) && (hasPriority = 1);
10197      } else if (p.substr(0, 2) === "--") {
10198        //CSS variable
10199        startValue = (getComputedStyle(target).getPropertyValue(p) + "").trim();
10200        endValue += "";
10201        startUnit = Object(__WEBPACK_IMPORTED_MODULE_0__gsap_core_js__["v" /* getUnit */])(startValue);
10202        endUnit = Object(__WEBPACK_IMPORTED_MODULE_0__gsap_core_js__["v" /* getUnit */])(endValue);
10203        endUnit ? startUnit !== endUnit && (startValue = _convertToUnit(target, p, startValue, endUnit) + endUnit) : startUnit && (endValue += startUnit);
10204        this.add(style, "setProperty", startValue, endValue, index, targets, 0, 0, p);
10205      } else if (type !== "undefined") {
10206        if (startAt && p in startAt) {
10207          // in case someone hard-codes a complex value as the start, like top: "calc(2vh / 2)". Without this, it'd use the computed value (always in px)
10208          startValue = typeof startAt[p] === "function" ? startAt[p].call(tween, index, target, targets) : startAt[p];
10209          p in __WEBPACK_IMPORTED_MODULE_0__gsap_core_js__["e" /* _config */].units && !Object(__WEBPACK_IMPORTED_MODULE_0__gsap_core_js__["v" /* getUnit */])(startValue) && (startValue += __WEBPACK_IMPORTED_MODULE_0__gsap_core_js__["e" /* _config */].units[p]); // for cases when someone passes in a unitless value like {x: 100}; if we try setting translate(100, 0px) it won't work.
10210
10211          (startValue + "").charAt(1) === "=" && (startValue = _get(target, p)); // can't work with relative values
10212        } else {
10213          startValue = _get(target, p);
10214        }
10215
10216        startNum = parseFloat(startValue);
10217        relative = type === "string" && endValue.charAt(1) === "=" ? +(endValue.charAt(0) + "1") : 0;
10218        relative && (endValue = endValue.substr(2));
10219        endNum = parseFloat(endValue);
10220
10221        if (p in _propertyAliases) {
10222          if (p === "autoAlpha") {
10223            //special case where we control the visibility along with opacity. We still allow the opacity value to pass through and get tweened.
10224            if (startNum === 1 && _get(target, "visibility") === "hidden" && endNum) {
10225              //if visibility is initially set to "hidden", we should interpret that as intent to make opacity 0 (a convenience)
10226              startNum = 0;
10227            }
10228
10229            _addNonTweeningPT(this, style, "visibility", startNum ? "inherit" : "hidden", endNum ? "inherit" : "hidden", !endNum);
10230          }
10231
10232          if (p !== "scale" && p !== "transform") {
10233            p = _propertyAliases[p];
10234            ~p.indexOf(",") && (p = p.split(",")[0]);
10235          }
10236        }
10237
10238        isTransformRelated = p in _transformProps; //--- TRANSFORM-RELATED ---
10239
10240        if (isTransformRelated) {
10241          if (!transformPropTween) {
10242            cache = target._gsap;
10243            cache.renderTransform && !vars.parseTransform || _parseTransform(target, vars.parseTransform); // if, for example, gsap.set(... {transform:"translateX(50vw)"}), the _get() call doesn't parse the transform, thus cache.renderTransform won't be set yet so force the parsing of the transform here.
10244
10245            smooth = vars.smoothOrigin !== false && cache.smooth;
10246            transformPropTween = this._pt = new __WEBPACK_IMPORTED_MODULE_0__gsap_core_js__["b" /* PropTween */](this._pt, style, _transformProp, 0, 1, cache.renderTransform, cache, 0, -1); //the first time through, create the rendering PropTween so that it runs LAST (in the linked list, we keep adding to the beginning)
10247
10248            transformPropTween.dep = 1; //flag it as dependent so that if things get killed/overwritten and this is the only PropTween left, we can safely kill the whole tween.
10249          }
10250
10251          if (p === "scale") {
10252            this._pt = new __WEBPACK_IMPORTED_MODULE_0__gsap_core_js__["b" /* PropTween */](this._pt, cache, "scaleY", cache.scaleY, relative ? relative * endNum : endNum - cache.scaleY);
10253            props.push("scaleY", p);
10254            p += "X";
10255          } else if (p === "transformOrigin") {
10256            endValue = _convertKeywordsToPercentages(endValue); //in case something like "left top" or "bottom right" is passed in. Convert to percentages.
10257
10258            if (cache.svg) {
10259              _applySVGOrigin(target, endValue, 0, smooth, 0, this);
10260            } else {
10261              endUnit = parseFloat(endValue.split(" ")[2]) || 0; //handle the zOrigin separately!
10262
10263              endUnit !== cache.zOrigin && _addNonTweeningPT(this, cache, "zOrigin", cache.zOrigin, endUnit);
10264
10265              _addNonTweeningPT(this, style, p, _firstTwoOnly(startValue), _firstTwoOnly(endValue));
10266            }
10267
10268            continue;
10269          } else if (p === "svgOrigin") {
10270            _applySVGOrigin(target, endValue, 1, smooth, 0, this);
10271
10272            continue;
10273          } else if (p in _rotationalProperties) {
10274            _addRotationalPropTween(this, cache, p, startNum, endValue, relative);
10275
10276            continue;
10277          } else if (p === "smoothOrigin") {
10278            _addNonTweeningPT(this, cache, "smooth", cache.smooth, endValue);
10279
10280            continue;
10281          } else if (p === "force3D") {
10282            cache[p] = endValue;
10283            continue;
10284          } else if (p === "transform") {
10285            _addRawTransformPTs(this, endValue, target);
10286
10287            continue;
10288          }
10289        } else if (!(p in style)) {
10290          p = _checkPropPrefix(p) || p;
10291        }
10292
10293        if (isTransformRelated || (endNum || endNum === 0) && (startNum || startNum === 0) && !_complexExp.test(endValue) && p in style) {
10294          startUnit = (startValue + "").substr((startNum + "").length);
10295          endNum || (endNum = 0); // protect against NaN
10296
10297          endUnit = Object(__WEBPACK_IMPORTED_MODULE_0__gsap_core_js__["v" /* getUnit */])(endValue) || (p in __WEBPACK_IMPORTED_MODULE_0__gsap_core_js__["e" /* _config */].units ? __WEBPACK_IMPORTED_MODULE_0__gsap_core_js__["e" /* _config */].units[p] : startUnit);
10298          startUnit !== endUnit && (startNum = _convertToUnit(target, p, startValue, endUnit));
10299          this._pt = new __WEBPACK_IMPORTED_MODULE_0__gsap_core_js__["b" /* PropTween */](this._pt, isTransformRelated ? cache : style, p, startNum, relative ? relative * endNum : endNum - startNum, !isTransformRelated && (endUnit === "px" || p === "zIndex") && vars.autoRound !== false ? _renderRoundedCSSProp : _renderCSSProp);
10300          this._pt.u = endUnit || 0;
10301
10302          if (startUnit !== endUnit) {
10303            //when the tween goes all the way back to the beginning, we need to revert it to the OLD/ORIGINAL value (with those units). We record that as a "b" (beginning) property and point to a render method that handles that. (performance optimization)
10304            this._pt.b = startValue;
10305            this._pt.r = _renderCSSPropWithBeginning;
10306          }
10307        } else if (!(p in style)) {
10308          if (p in target) {
10309            //maybe it's not a style - it could be a property added directly to an element in which case we'll try to animate that.
10310            this.add(target, p, target[p], endValue, index, targets);
10311          } else {
10312            Object(__WEBPACK_IMPORTED_MODULE_0__gsap_core_js__["l" /* _missingPlugin */])(p, endValue);
10313
10314            continue;
10315          }
10316        } else {
10317          _tweenComplexCSSString.call(this, target, p, startValue, endValue);
10318        }
10319
10320        props.push(p);
10321      }
10322    }
10323
10324    hasPriority && Object(__WEBPACK_IMPORTED_MODULE_0__gsap_core_js__["t" /* _sortPropTweensByPriority */])(this);
10325  },
10326  get: _get,
10327  aliases: _propertyAliases,
10328  getSetter: function getSetter(target, property, plugin) {
10329    //returns a setter function that accepts target, property, value and applies it accordingly. Remember, properties like "x" aren't as simple as target.style.property = value because they've got to be applied to a proxy object and then merged into a transform string in a renderer.
10330    var p = _propertyAliases[property];
10331    p && p.indexOf(",") < 0 && (property = p);
10332    return property in _transformProps && property !== _transformOriginProp && (target._gsap.x || _get(target, "x")) ? plugin && _recentSetterPlugin === plugin ? property === "scale" ? _setterScale : _setterTransform : (_recentSetterPlugin = plugin || {}) && (property === "scale" ? _setterScaleWithRender : _setterTransformWithRender) : target.style && !Object(__WEBPACK_IMPORTED_MODULE_0__gsap_core_js__["k" /* _isUndefined */])(target.style[property]) ? _setterCSSStyle : ~property.indexOf("-") ? _setterCSSProp : Object(__WEBPACK_IMPORTED_MODULE_0__gsap_core_js__["i" /* _get
10332Setter */])(target, property);
10333  },
10334  core: {
10335    _removeProperty: _removeProperty,
10336    _getMatrix: _getMatrix
10337  }
10338};
10339__WEBPACK_IMPORTED_MODULE_0__gsap_core_js__["w" /* gsap */].utils.checkPrefix = _checkPropPrefix;
10340
10341(function (positionAndScale, rotation, others, aliases) {
10342  var all = Object(__WEBPACK_IMPORTED_MODULE_0__gsap_core_js__["f" /* _forEachName */])(positionAndScale + "," + rotation + "," + others, function (name) {
10343    _transformProps[name] = 1;
10344  });
10345
10346  Object(__WEBPACK_IMPORTED_MODULE_0__gsap_core_js__["f" /* _forEachName */])(rotation, function (name) {
10347    __WEBPACK_IMPORTED_MODULE_0__gsap_core_js__["e" /* _config */].units[name] = "deg";
10348    _rotationalProperties[name] = 1;
10349  });
10350
10351  _propertyAliases[all[13]] = positionAndScale + "," + rotation;
10352
10353  Object(__WEBPACK_IMPORTED_MODULE_0__gsap_core_js__["f" /* _forEachName */])(aliases, function (name) {
10354    var split = name.split(":");
10355    _propertyAliases[split[1]] = all[split[0]];
10356  });
10357})("x,y,z,scale,scaleX,scaleY,xPercent,yPercent", "rotation,rotationX,rotationY,skewX,skewY", "transform,transformOrigin,svgOrigin,force3D,smoothOrigin,transformPerspective", "0:translateX,1:translateY,2:translateZ,8:rotate,8:rotationZ,8:rotateZ,9:rotateX,10:rotateY");
10358
10359Object(__WEBPACK_IMPORTED_MODULE_0__gsap_core_js__["f" /* _forEachName */])("x,y,z,top,right,bottom,left,width,height,fontSize,padding,margin,perspective", function (name) {
10360  __WEBPACK_IMPORTED_MODULE_0__gsap_core_js__["e" /* _config */].units[name] = "px";
10361});
10362
10363__WEBPACK_IMPORTED_MODULE_0__gsap_core_js__["w" /* gsap */].registerPlugin(CSSPlugin);
10364
10365
10366/***/ }),
10367/* 21 */
10368/***/ (function(module, __webpack_exports__, __webpack_require__) {
10369
10370"use strict";
10371/* unused harmony export ScrollTrigger */
10372/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, "a", function() { return ScrollTrigger; });
10373/*!
10374 * ScrollTrigger 3.6.0
10375 * https://greensock.com
10376 *
10377 * @license Copyright 2008-2021, GreenSock. All rights reserved.
10378 * Subject to the terms at https://greensock.com/standard-license or for
10379 * Club GreenSock members, the agreement issued with that membership.
10380 * @author: Jack Doyle, [email protected]
10381*/
10382
10383/* eslint-disable */
10384var gsap,
10385    _coreInitted,
10386    _win,
10387    _doc,
10388    _docEl,
10389    _body,
10390    _root,
10391    _resizeDelay,
10392    _raf,
10393    _request,
10394    _toArray,
10395    _clamp,
10396    _time2,
10397    _syncInterval,
10398    _refreshing,
10399    _pointerIsDown,
10400    _transformProp,
10401    _i,
10402    _prevWidth,
10403    _prevHeight,
10404    _autoRefresh,
10405    _sort,
10406    _suppressOverwrites,
10407    _ignoreResize,
10408    _limitCallbacks,
10409    // if true, we'll only trigger callbacks if the active state toggles, so if you scroll immediately past both the start and end positions of a ScrollTrigger (thus inactive to inactive), neither its onEnter nor onLeave will be called. This is useful during startup.
10410_startup = 1,
10411    _proxies = [],
10412    _scrollers = [],
10413    _getTime = Date.now,
10414    _time1 = _getTime(),
10415    _lastScrollTime = 0,
10416    _enabled = 1,
10417    _passThrough = function _passThrough(v) {
10418  return v;
10419},
10420    _windowExists = function _windowExists() {
10421  return typeof window !== "undefined";
10422},
10423    _getGSAP = function _getGSAP() {
10424  return gsap || _windowExists() && (gsap = window.gsap) && gsap.registerPlugin && gsap;
10425},
10426    _isViewport = function _isViewport(e) {
10427  return !!~_root.indexOf(e);
10428},
10429    _getProxyProp = function _getProxyProp(element, property) {
10430  return ~_proxies.indexOf(element) && _proxies[_proxies.indexOf(element) + 1][property];
10431},
10432    _getScrollFunc = function _getScrollFunc(element, _ref) {
10433  var s = _ref.s,
10434      sc = _ref.sc;
10435
10436  var i = _scrollers.indexOf(element),
10437      offset = sc === _vertical.sc ? 1 : 2;
10438
10439  !~i && (i = _scrollers.push(element) - 1);
10440  return _scrollers[i + offset] || (_scrollers[i + offset] = _getProxyProp(element, s) || (_isViewport(element) ? sc : function (value) {
10441    return arguments.length ? element[s] = value : element[s];
10442  }));
10443},
10444    _getBoundsFunc = function _getBoundsFunc(element) {
10445  return _getProxyProp(element, "getBoundingClientRect") || (_isViewport(element) ? function () {
10446    _winOffsets.width = _win.innerWidth;
10447    _winOffsets.height = _win.innerHeight;
10448    return _winOffsets;
10449  } : function () {
10450    return _getBounds(element);
10451  });
10452},
10453    _getSizeFunc = function _getSizeFunc(scroller, isViewport, _ref2) {
10454  var d = _ref2.d,
10455      d2 = _ref2.d2,
10456      a = _ref2.a;
10457  return (a = _getProxyProp(scroller, "getBoundingClientRect")) ? function () {
10458    return a()[d];
10459  } : function () {
10460    return (isViewport ? _win["inner" + d2] : scroller["client" + d2]) || 0;
10461  };
10462},
10463    _getOffsetsFunc = function _getOffsetsFunc(element, isViewport) {
10464  return !isViewport || ~_proxies.indexOf(element) ? _getBoundsFunc(element) : function () {
10465    return _winOffsets;
10466  };
10467},
10468    _maxScroll = function _maxScroll(element, _ref3) {
10469  var s = _ref3.s,
10470      d2 = _ref3.d2,
10471      d = _ref3.d,
10472      a = _ref3.a;
10473  return (s = "scroll" + d2) && (a = _getProxyProp(element, s)) ? a() - _getBoundsFunc(element)()[d] : _isViewport(element) ? Math.max(_docEl[s], _body[s]) - (_win["inner" + d2] || _docEl["client" + d2] || _body["client" + d2]) : element[s] - element["offset" + d2];
10474},
10475    _iterateAutoRefresh = function _iterateAutoRefresh(func, events) {
10476  for (var i = 0; i < _autoRefresh.length; i += 3) {
10477    (!events || ~events.indexOf(_autoRefresh[i + 1])) && func(_autoRefresh[i], _autoRefresh[i + 1], _autoRefresh[i + 2]);
10478  }
10479},
10480    _isString = function _isString(value) {
10481  return typeof value === "string";
10482},
10483    _isFunction = function _isFunction(value) {
10484  return typeof value === "function";
10485},
10486    _isNumber = function _isNumber(value) {
10487  return typeof value === "number";
10488},
10489    _isObject = function _isObject(value) {
10490  return typeof value === "object";
10491},
10492    _callIfFunc = function _callIfFunc(value) {
10493  return _isFunction(value) && value();
10494},
10495    _combineFunc = function _combineFunc(f1, f2) {
10496  return function () {
10497    var result1 = _callIfFunc(f1),
10498        result2 = _callIfFunc(f2);
10499
10500    return function () {
10501      _callIfFunc(result1);
10502
10503      _callIfFunc(result2);
10504    };
10505  };
10506},
10507    _abs = Math.abs,
10508    _scrollLeft = "scrollLeft",
10509    _scrollTop = "scrollTop",
10510    _left = "left",
10511    _top = "top",
10512    _right = "right",
10513    _bottom = "bottom",
10514    _width = "width",
10515    _height = "height",
10516    _Right = "Right",
10517    _Left = "Left",
10518    _Top = "Top",
10519    _Bottom = "Bottom",
10520    _padding = "padding",
10521    _margin = "margin",
10522    _Width = "Width",
10523    _Height = "Height",
10524    _px = "px",
10525    _horizontal = {
10526  s: _scrollLeft,
10527  p: _left,
10528  p2: _Left,
10529  os: _right,
10530  os2: _Right,
10531  d: _width,
10532  d2: _Width,
10533  a: "x",
10534  sc: function sc(value) {
10535    return arguments.length ? _win.scrollTo(value, _vertical.sc()) : _win.pageXOffset || _doc[_scrollLeft] || _docEl[_scrollLeft] || _body[_scrollLeft] || 0;
10536  }
10537},
10538    _vertical = {
10539  s: _scrollTop,
10540  p: _top,
10541  p2: _Top,
10542  os: _bottom,
10543  os2: _Bottom,
10544  d: _height,
10545  d2: _Height,
10546  a: "y",
10547  op: _horizontal,
10548  sc: function sc(value) {
10549    return arguments.length ? _win.scrollTo(_horizontal.sc(), value) : _win.pageYOffset || _doc[_scrollTop] || _docEl[_scrollTop] || _body[_scrollTop] || 0;
10550  }
10551},
10552    _getComputedStyle = function _getComputedStyle(element) {
10553  return _win.getComputedStyle(element);
10554},
10555    _makePositionable = function _makePositionable(element) {
10556  return element.style.position = _getComputedStyle(element).position === "absolute" ? "absolute" : "relative";
10557},
10558    // if the element already has position: absolute, leave that, otherwise make it position: relative
10559_setDefaults = function _setDefaults(obj, defaults) {
10560  for (var p in defaults) {
10561    p in obj || (obj[p] = defaults[p]);
10562  }
10563
10564  return obj;
10565},
10566    //_isInViewport = element => (element = _getBounds(element)) && !(element.top > (_win.innerHeight || _docEl.clientHeight) || element.bottom < 0 || element.left > (_win.innerWidth || _docEl.clientWidth) || element.right < 0) && element,
10567_getBounds = function _getBounds(element, withoutTransforms) {
10568  var tween = withoutTransforms && _getComputedStyle(element)[_transformProp] !== "matrix(1, 0, 0, 1, 0, 0)" && gsap.to(element, {
10569    x: 0,
10570    y: 0,
10571    xPercent: 0,
10572    yPercent: 0,
10573    rotation: 0,
10574    rotationX: 0,
10575    rotationY: 0,
10576    scale: 1,
10577    skewX: 0,
10578    skewY: 0
10579  }).progress(1),
10580      bounds = element.getBoundingClientRect();
10581  tween && tween.progress(0).kill();
10582  return bounds;
10583},
10584    _getSize = function _getSize(element, _ref4) {
10585  var d2 = _ref4.d2;
10586  return element["offset" + d2] || element["client" + d2] || 0;
10587},
10588    _getLabelRatioArray = function _getLabelRatioArray(timeline) {
10589  var a = [],
10590      labels = timeline.labels,
10591      duration = timeline.duration(),
10592      p;
10593
10594  for (p in labels) {
10595    a.push(labels[p] / duration);
10596  }
10597
10598  return a;
10599},
10600    _getClosestLabel = function _getClosestLabel(animation) {
10601  return function (value) {
10602    return gsap.utils.snap(_getLabelRatioArray(animation), value);
10603  };
10604},
10605    _getLabelAtDirection = function _getLabelAtDirection(timeline) {
10606  return function (value, st) {
10607    var a = _getLabelRatioArray(timeline),
10608        i;
10609
10610    a.sort(function (a, b) {
10611      return a - b;
10612    });
10613
10614    if (st.direction > 0) {
10615      for (i = 0; i < a.length; i++) {
10616        if (a[i] >= value) {
10617          return a[i];
10618        }
10619      }
10620
10621      return a.pop();
10622    } else {
10623      i = a.length;
10624
10625      while (i--) {
10626        if (a[i] <= value) {
10627          return a[i];
10628        }
10629      }
10630    }
10631
10632    return a[0];
10633  };
10634},
10635    _multiListener = function _multiListener(func, element, types, callback) {
10636  return types.split(",").forEach(function (type) {
10637    return func(element, type, callback);
10638  });
10639},
10640    _addListener = function _addListener(element, type, func) {
10641  return element.addEventListener(type, func, {
10642    passive: true
10643  });
10644},
10645    _removeListener = function _removeListener(element, type, func) {
10646  return element.removeEventListener(type, func);
10647},
10648    _markerDefaults = {
10649  startColor: "green",
10650  endColor: "red",
10651  indent: 0,
10652  fontSize: "16px",
10653  fontWeight: "normal"
10654},
10655    _defaults = {
10656  toggleActions: "play",
10657  anticipatePin: 0
10658},
10659    _keywords = {
10660  top: 0,
10661  left: 0,
10662  center: 0.5,
10663  bottom: 1,
10664  right: 1
10665},
10666    _offsetToPx = function _offsetToPx(value, size) {
10667  if (_isString(value)) {
10668    var eqIndex = value.indexOf("="),
10669        relative = ~eqIndex ? +(value.charAt(eqIndex - 1) + 1) * parseFloat(value.substr(eqIndex + 1)) : 0;
10670
10671    if (~eqIndex) {
10672      value.indexOf("%") > eqIndex && (relative *= size / 100);
10673      value = value.substr(0, eqIndex - 1);
10674    }
10675
10676    value = relative + (value in _keywords ? _keywords[value] * size : ~value.indexOf("%") ? parseFloat(value) * size / 100 : parseFloat(value) || 0);
10677  }
10678
10679  return value;
10680},
10681    _createMarker = function _createMarker(type, name, container, direction, _ref5, offset, matchWidthEl) {
10682  var startColor = _ref5.startColor,
10683      endColor = _ref5.endColor,
10684      fontSize = _ref5.fontSize,
10685      indent = _ref5.indent,
10686      fontWeight = _ref5.fontWeight;
10687
10688  var e = _doc.createElement("div"),
10689      useFixedPosition = _isViewport(container) || _getProxyProp(container, "pinType") === "fixed",
10690      isScroller = type.indexOf("scroller") !== -1,
10691      parent = useFixedPosition ? _body : container,
10692      isStart = type.indexOf("start") !== -1,
10693      color = isStart ? startColor : endColor,
10694      css = "border-color:" + color + ";font-size:" + fontSize + ";color:" + color + ";font-weight:" + fontWeight + ";pointer-events:none;white-space:nowrap;font-family:sans-serif,Arial;z-index:1000;padding:4px 8px;border-width:0;border-style:solid;";
10695
10696  css += "position:" + (isScroller && useFixedPosition ? "fixed;" : "absolute;");
10697  (isScroller || !useFixedPosition) && (css += (direction === _vertical ? _right : _bottom) + ":" + (offset + parseFloat(indent)) + "px;");
10698  matchWidthEl && (css += "box-sizing:border-box;text-align:left;
10698width:" + matchWidthEl.offsetWidth + "px;");
10699  e._isStart = isStart;
10700  e.setAttribute("class", "gsap-marker-" + type);
10701  e.style.cssText = css;
10702  e.innerText = name || name === 0 ? type + "-" + name : type;
10703  parent.children[0] ? parent.insertBefore(e, parent.children[0]) : parent.appendChild(e);
10704  e._offset = e["offset" + direction.op.d2];
10705
10706  _positionMarker(e, 0, direction, isStart);
10707
10708  return e;
10709},
10710    _positionMarker = function _positionMarker(marker, start, direction, flipped) {
10711  var vars = {
10712    display: "block"
10713  },
10714      side = direction[flipped ? "os2" : "p2"],
10715      oppositeSide = direction[flipped ? "p2" : "os2"];
10716  marker._isFlipped = flipped;
10717  vars[direction.a + "Percent"] = flipped ? -100 : 0;
10718  vars[direction.a] = flipped ? "1px" : 0;
10719  vars["border" + side + _Width] = 1;
10720  vars["border" + oppositeSide + _Width] = 0;
10721  vars[direction.p] = start + "px";
10722  gsap.set(marker, vars);
10723},
10724    _triggers = [],
10725    _ids = {},
10726    _sync = function _sync() {
10727  return _request || (_request = _raf(_updateAll));
10728},
10729    _onScroll = function _onScroll() {
10730  if (!_request) {
10731    _request = _raf(_updateAll);
10732    _lastScrollTime || _dispatch("scrollStart");
10733    _lastScrollTime = _getTime();
10734  }
10735},
10736    _onResize = function _onResize() {
10737  return !_refreshing && !_ignoreResize && !_doc.fullscreenElement && _resizeDelay.restart(true);
10738},
10739    // ignore resizes triggered by refresh()
10740_listeners = {},
10741    _emptyArray = [],
10742    _media = [],
10743    _creatingMedia,
10744    // when ScrollTrigger.matchMedia() is called, we record the current media key here (like "(min-width: 800px)") so that we can assign it to everything that's created during that call. Then we can revert just those when necessary. In the ScrollTrigger's init() call, the _creatingMedia is recorded as a "media" property on the instance.
10745_lastMediaTick,
10746    _onMediaChange = function _onMediaChange(e) {
10747  var tick = gsap.ticker.frame,
10748      matches = [],
10749      i = 0,
10750      index;
10751
10752  if (_lastMediaTick !== tick || _startup) {
10753    _revertAll();
10754
10755    for (; i < _media.length; i += 4) {
10756      index = _win.matchMedia(_media[i]).matches;
10757
10758      if (index !== _media[i + 3]) {
10759        // note: some browsers fire the matchMedia event multiple times, like when going full screen, so we shouldn't call the function multiple times. Check to see if it's already matched.
10760        _media[i + 3] = index;
10761        index ? matches.push(i) : _revertAll(1, _media[i]) || _isFunction(_media[i + 2]) && _media[i + 2](); // Firefox doesn't update the "matches" property of the MediaQueryList object correctly - it only does so as it calls its change handler - so we must re-create a media query here to ensure it's accurate.
10762      }
10763    }
10764
10765    _revertRecorded(); // in case killing/reverting any of the animations actually added inline styles back.
10766
10767
10768    for (i = 0; i < matches.length; i++) {
10769      index = matches[i];
10770      _creatingMedia = _media[index];
10771      _media[index + 2] = _media[index + 1](e);
10772    }
10773
10774    _creatingMedia = 0;
10775    _coreInitted && _refreshAll(0, 1);
10776    _lastMediaTick = tick;
10777
10778    _dispatch("matchMedia");
10779  }
10780},
10781    _softRefresh = function _softRefresh() {
10782  return _removeListener(ScrollTrigger, "scrollEnd", _softRefresh) || _refreshAll(true);
10783},
10784    _dispatch = function _dispatch(type) {
10785  return _listeners[type] && _listeners[type].map(function (f) {
10786    return f();
10787  }) || _emptyArray;
10788},
10789    _savedStyles = [],
10790    // when ScrollTrigger.saveStyles() is called, the inline styles are recorded in this Array in a sequential format like [element, cssText, gsCache, media]. This keeps it very memory-efficient and fast to iterate through.
10791_revertRecorded = function _revertRecorded(media) {
10792  for (var i = 0; i < _savedStyles.length; i += 4) {
10793    if (!media || _savedStyles[i + 3] === media) {
10794      _savedStyles[i].style.cssText = _savedStyles[i + 1];
10795      _savedStyles[i + 2].uncache = 1;
10796    }
10797  }
10798},
10799    _revertAll = function _revertAll(kill, media) {
10800  var trigger;
10801
10802  for (_i = 0; _i < _triggers.length; _i++) {
10803    trigger = _triggers[_i];
10804
10805    if (!media || trigger.media === media) {
10806      if (kill) {
10807        trigger.kill(1);
10808      } else {
10809        trigger.scroll.rec || (trigger.scroll.rec = trigger.scroll()); // record the scroll positions so that in each refresh() we can ensure that it doesn't shift. Remember, pinning can make things change around, especially if the same element is pinned multiple times. If one was already recorded, don't re-record because unpinning may have occurred and made it shorter.
10810
10811        trigger.revert();
10812      }
10813    }
10814  }
10815
10816  _revertRecorded(media);
10817
10818  media || _dispatch("revert");
10819},
10820    _refreshAll = function _refreshAll(force, skipRevert) {
10821  if (_lastScrollTime && !force) {
10822    _addListener(ScrollTrigger, "scrollEnd", _softRefresh);
10823
10824    return;
10825  }
10826
10827  var refreshInits = _dispatch("refreshInit");
10828
10829  _sort && ScrollTrigger.sort();
10830  skipRevert || _revertAll();
10831
10832  for (_i = 0; _i < _triggers.length; _i++) {
10833    _triggers[_i].refresh();
10834  }
10835
vendor: 8,201 bytes, lines 10836-11069
10836  refreshInits.forEach(function (result) {
10837    return result && result.render && result.render(-1);
10838  }); // if the onRefreshInit() returns an animation (typically a gsap.set()), revert it. This makes it easy to put things in a certain spot before refreshing for measurement purposes, and then put things back.
10839
10840  _i = _triggers.length;
10841
10842  while (_i--) {
10843    _triggers[_i].scroll.rec = 0;
10844  }
10845
10846  _resizeDelay.pause();
10847
10848  _dispatch("refresh");
10849},
10850    _lastScroll = 0,
10851    _direction = 1,
10852    _updateAll = function _updateAll() {
10853  var l = _triggers.length,
10854      time = _getTime(),
10855      recordVelocity = time - _time1 >= 50,
10856      scroll = l && _triggers[0].scroll();
10857
10858  _direction = _lastScroll > scroll ? -1 : 1;
10859  _lastScroll = scroll;
10860
10861  if (recordVelocity) {
10862    if (_lastScrollTime && !_pointerIsDown && time - _lastScrollTime > 200) {
10863      _lastScrollTime = 0;
10864
10865      _dispatch("scrollEnd");
10866    }
10867
10868    _time2 = _time1;
10869    _time1 = time;
10870  }
10871
10872  if (_direction < 0) {
10873    _i = l;
10874
10875    while (_i--) {
10876      _triggers[_i] && _triggers[_i].update(0, recordVelocity);
10877    }
10878
10879    _direction = 1;
10880  } else {
10881    for (_i = 0; _i < l; _i++) {
10882      _triggers[_i] && _triggers[_i].update(0, recordVelocity);
10883    }
10884  }
10885
10886  _request = 0;
10887},
10888    _propNamesToCopy = [_left, _top, _bottom, _right, _margin + _Bottom, _margin + _Right, _margin + _Top, _margin + _Left, "display", "flexShrink", "float", "zIndex"],
10889    _stateProps = _propNamesToCopy.concat([_width, _height, "boxSizing", "max" + _Width, "max" + _Height, "position", _margin, _padding, _padding + _Top, _padding + _Right, _padding + _Bottom, _padding + _Left]),
10890    _swapPinOut = function _swapPinOut(pin, spacer, state) {
10891  _setState(state);
10892
10893  if (pin.parentNode === spacer) {
10894    var parent = spacer.parentNode;
10895
10896    if (parent) {
10897      parent.insertBefore(pin, spacer);
10898      parent.removeChild(spacer);
10899    }
10900  }
10901},
10902    _swapPinIn = function _swapPinIn(pin, spacer, cs, spacerState) {
10903  if (pin.parentNode !== spacer) {
10904    var i = _propNamesToCopy.length,
10905        spacerStyle = spacer.style,
10906        pinStyle = pin.style,
10907        p;
10908
10909    while (i--) {
10910      p = _propNamesToCopy[i];
10911      spacerStyle[p] = cs[p];
10912    }
10913
10914    spacerStyle.position = cs.position === "absolute" ? "absolute" : "relative";
10915    cs.display === "inline" && (spacerStyle.display = "inline-block");
10916    pinStyle[_bottom] = pinStyle[_right] = "auto";
10917    spacerStyle.overflow = "visible";
10918    spacerStyle.boxSizing = "border-box";
10919    spacerStyle[_width] = _getSize(pin, _horizontal) + _px;
10920    spacerStyle[_height] = _getSize(pin, _vertical) + _px;
10921    spacerStyle[_padding] = pinStyle[_margin] = pinStyle[_top] = pinStyle[_left] = "0";
10922
10923    _setState(spacerState);
10924
10925    pinStyle[_width] = pinStyle["max" + _Width] = cs[_width];
10926    pinStyle[_height] = pinStyle["max" + _Height] = cs[_height];
10927    pinStyle[_padding] = cs[_padding];
10928    pin.parentNode.insertBefore(spacer, pin);
10929    spacer.appendChild(pin);
10930  }
10931},
10932    _capsExp = /([A-Z])/g,
10933    _setState = function _setState(state) {
10934  if (state) {
10935    var style = state.t.style,
10936        l = state.length,
10937        i = 0,
10938        p,
10939        value;
10940    (state.t._gsap || gsap.core.getCache(state.t)).uncache = 1; // otherwise transforms may be off
10941
10942    for (; i < l; i += 2) {
10943      value = state[i + 1];
10944      p = state[i];
10945
10946      if (value) {
10947        style[p] = value;
10948      } else if (style[p]) {
10949        style.removeProperty(p.replace(_capsExp, "-$1").toLowerCase());
10950      }
10951    }
10952  }
10953},
10954    _getState = function _getState(element) {
10955  // returns an Array with alternating values like [property, value, property, value] and a "t" property pointing to the target (element). Makes it fast and cheap.
10956  var l = _stateProps.length,
10957      style = element.style,
10958      state = [],
10959      i = 0;
10960
10961  for (; i < l; i++) {
10962    state.push(_stateProps[i], style[_stateProps[i]]);
10963  }
10964
10965  state.t = element;
10966  return state;
10967},
10968    _copyState = function _copyState(state, override, omitOffsets) {
10969  var result = [],
10970      l = state.length,
10971      i = omitOffsets ? 8 : 0,
10972      // skip top, left, right, bottom if omitOffsets is true
10973  p;
10974
10975  for (; i < l; i += 2) {
10976    p = state[i];
10977    result.push(p, p in override ? override[p] : state[i + 1]);
10978  }
10979
10980  result.t = state.t;
10981  return result;
10982},
10983    _winOffsets = {
10984  left: 0,
10985  top: 0
10986},
10987    _parsePosition = function _parsePosition(value, trigger, scrollerSize, direction, scroll, marker, markerScroller, self, scrollerBounds, borderWidth, useFixedPosition, scrollerMax) {
10988  _isFunction(value) && (value = value(self));
10989
10990  if (_isString(value) && value.substr(0, 3) === "max") {
10991    value = scrollerMax + (value.charAt(4) === "=" ? _offsetToPx("0" + value.substr(3), scrollerSize) : 0);
10992  }
10993
10994  if (!_isNumber(value)) {
10995    _isFunction(trigger) && (trigger = trigger(self));
10996
10997    var element = _toArray(trigger)[0] || _body,
10998        bounds = _getBounds(element) || {},
10999        offsets = value.split(" "),
11000        localOffset,
11001        globalOffset,
11002        display;
11003
11004    if ((!bounds || !bounds.left && !bounds.top) && _getComputedStyle(element).display === "none") {
11005      // if display is "none", it won't report getBoundingClientRect() properly
11006      display = element.style.display;
11007      element.style.display = "block";
11008      bounds = _getBounds(element);
11009      display ? element.style.display = display : element.style.removeProperty("display");
11010    }
11011
11012    localOffset = _offsetToPx(offsets[0], bounds[direction.d]);
11013    globalOffset = _offsetToPx(offsets[1] || "0", scrollerSize);
11014    value = bounds[direction.p] - scrollerBounds[direction.p] - borderWidth + localOffset + scroll - globalOffset;
11015    markerScroller && _positionMarker(markerScroller, globalOffset, direction, scrollerSize - globalOffset < 20 || markerScroller._isStart && globalOffset > 20);
11016    scrollerSize -= scrollerSize - globalOffset; // adjust for the marker
11017  } else if (markerScroller) {
11018    _positionMarker(markerScroller, scrollerSize, direction, true);
11019  }
11020
11021  if (marker) {
11022    var position = value + scrollerSize,
11023        isStart = marker._isStart;
11024    scrollerMax = "scroll" + direction.d2;
11025
11026    _positionMarker(marker, position, direction, isStart && position > 20 || !isStart && (useFixedPosition ? Math.max(_body[scrollerMax], _docEl[scrollerMax]) : marker.parentNode[scrollerMax]) <= position + 1);
11027
11028    if (useFixedPosition) {
11029      scrollerBounds = _getBounds(markerScroller);
11030      useFixedPosition && (marker.style[direction.op.p] = scrollerBounds[direction.op.p] - direction.op.m - marker._offset + _px);
11031    }
11032  }
11033
11034  return Math.round(value);
11035},
11036    _prefixExp = /(?:webkit|moz|length|cssText|inset)/i,
11037    _reparent = function _reparent(element, parent, top, left) {
11038  if (element.parentNode !== parent) {
11039    var style = element.style,
11040        p,
11041        cs;
11042
11043    if (parent === _body) {
11044      element._stOrig = style.cssText; // record original inline styles so we can revert them later
11045
11046      cs = _getComputedStyle(element);
11047
11048      for (p in cs) {
11049        // must copy all relevant styles to ensure that nothing changes visually when we reparent to the <body>. Skip the vendor prefixed ones.
11050        if (!+p && !_prefixExp.test(p) && cs[p] && typeof style[p] === "string" && p !== "0") {
11051          style[p] = cs[p];
11052        }
11053      }
11054
11055      style.top = top;
11056      style.left = left;
11057    } else {
11058      style.cssText = element._stOrig;
11059    }
11060
11061    gsap.core.getCache(element).uncache = 1;
11062    parent.appendChild(element);
11063  }
11064},
11065    // returns a function that can be used to tween the scroll position in the direction provided, and when doing so it'll add a .tween property to the FUNCTION itself, and remove it when the tween completes or gets killed. This gives us a way to have multiple ScrollTriggers use a central function for any given scroller and see if there's a scroll tween running (which would affect if/how things get updated)
11066_getTweenCreator = function _getTweenCreator(scroller, direction) {
11067  var getScroll = _getScrollFunc(scroller, direction),
11068      prop = "_scroll" + direction.p2,
11069      // add a tweenable property to the scroller that's a getter/setter function, like _scrollTop or _scrollLeft. This way, if someone does gsap.killTweensOf(scroller) it'll 
11069kill the scroll tween.
11070  lastScroll1,
11071      lastScroll2,
11072      getTween = function getTween(scrollTo, vars, initialValue, change1, change2) {
11073    var tween = getTween.tween,
11074        onComplete = vars.onComplete,
11075        modifiers = {};
11076    tween && tween.kill();
11077    lastScroll1 = Math.round(initialValue);
11078    vars[prop] = scrollTo;
11079    vars.modifiers = modifiers;
11080
11081    modifiers[prop] = function (value) {
11082      value = Math.round(getScroll()); // round because in some [very uncommon] Windows environments, it can get reported with decimals even though it was set without.
11083
11084      if (value !== lastScroll1 && value !== lastScroll2 && Math.abs(value - lastScroll1) > 2) {
11085        // if the user scrolls, kill the tween. iOS Safari intermittently misreports the scroll position, it may be the most recently-set one or the one before that! When Safari is zoomed (CMD-+), it often misreports as 1 pixel off too! So if we set the scroll position to 125, for example, it'll actually report it as 124.
11086        tween.kill();
11087        getTween.tween = 0;
11088      } else {
11089        value = initialValue + change1 * tween.ratio + change2 * tween.ratio * tween.ratio;
11090      }
11091
11092      lastScroll2 = lastScroll1;
11093      return lastScroll1 = Math.round(value);
11094    };
11095
11096    vars.onComplete = function () {
11097      getTween.tween = 0;
11098      onComplete && onComplete.call(tween);
11099    };
11100
11101    tween = getTween.tween = gsap.to(scroller, vars);
11102    return tween;
11103  };
11104
11105  scroller[prop] = getScroll;
11106  scroller.addEventListener("mousewheel", function () {
11107    return getTween.tween && getTween.tween.kill() && (getTween.tween = 0);
11108  }); // Windows machines handle mousewheel scrolling in chunks (like "3 lines per scroll") meaning the typical strategy for cancelling the scroll isn't as sensitive. It's much more likely to match one of the previous 2 scroll event positions. So we kill any snapping as soon as there's a mousewheel event.
11109
11110  return getTween;
11111};
11112
11113_horizontal.op = _vertical;
11114var ScrollTrigger = /*#__PURE__*/function () {
11115  function ScrollTrigger(vars, animation) {
11116    _coreInitted || ScrollTrigger.register(gsap) || console.warn("Please gsap.registerPlugin(ScrollTrigger)");
11117    this.init(vars, animation);
11118  }
11119
11120  var _proto = ScrollTrigger.prototype;
11121
11122  _proto.init = function init(vars, animation) {
11123    this.progress = this.start = 0;
11124    this.vars && this.kill(1); // in case it's being initted again
11125
11126    if (!_enabled) {
11127      this.update = this.refresh = this.kill = _passThrough;
11128      return;
11129    }
11130
11131    vars = _setDefaults(_isString(vars) || _isNumber(vars) || vars.nodeType ? {
11132      trigger: vars
11133    } : vars, _defaults);
11134
11135    var direction = vars.horizontal ? _horizontal : _vertical,
11136        _vars = vars,
11137        onUpdate = _vars.onUpdate,
11138        toggleClass = _vars.toggleClass,
11139        id = _vars.id,
11140        onToggle = _vars.onToggle,
11141        onRefresh = _vars.onRefresh,
11142        scrub = _vars.scrub,
11143        trigger = _vars.trigger,
11144        pin = _vars.pin,
11145        pinSpacing = _vars.pinSpacing,
11146        invalidateOnRefresh = _vars.invalidateOnRefresh,
11147        anticipatePin = _vars.anticipatePin,
11148        onScrubComplete = _vars.onScrubComplete,
11149        onSnapComplete = _vars.onSnapComplete,
11150        once = _vars.once,
11151        snap = _vars.snap,
11152        pinReparent = _vars.pinReparent,
11153        isToggle = !scrub && scrub !== 0,
11154        scroller = _toArray(vars.scroller || _win)[0],
11155        scrollerCache = gsap.core.getCache(scroller),
11156        isViewport = _isViewport(scroller),
11157        useFixedPosition = "pinType" in vars ? vars.pinType === "fixed" : isViewport || _getProxyProp(scroller, "pinType") === "fixed",
11158        callbacks = [vars.onEnter, vars.onLeave, vars.onEnterBack, vars.onLeaveBack],
11159        toggleActions = isToggle && vars.toggleActions.split(" "),
11160        markers = "markers" in vars ? vars.markers : _defaults.markers,
11161        borderWidth = isViewport ? 0 : parseFloat(_getComputedStyle(scroller)["border" + direction.p2 + _Width]) || 0,
11162        self = this,
11163        onRefreshInit = vars.onRefreshInit && function () {
11164      return vars.onRefreshInit(self);
11165    },
11166        getScrollerSize = _getSizeFunc(scroller, isViewport, direction),
11167        getScrollerOffsets = _getOffsetsFunc(scroller, isViewport),
11168        tweenTo,
11169        pinCache,
11170        snapFunc,
11171        isReverted,
11172        scroll1,
11173        scroll2,
11174        start,
11175        end,
11176        markerStart,
11177        markerEnd,
11178        markerStartTrigger,
11179        markerEndTrigger,
11180        markerVars,
11181        change,
11182        pinOriginalState,
11183        pinActiveState,
11184        pinState,
11185        spacer,
11186        offset,
11187        pinGetter,
11188        pinSetter,
11189        pinStart,
11190        pinChange,
11191        spacingStart,
11192        spacerState,
11193        markerStartSetter,
11194        markerEndSetter,
11195        cs,
11196        snap1,
11197        snap2,
11198        scrubTween,
11199        scrubSmooth,
11200        snapDurClamp,
11201        snapDelayedCall,
11202        prevProgress,
11203        prevScroll,
11204        prevAnimProgress;
11205
11206    self.media = _creatingMedia;
11207    anticipatePin *= 45;
11208
11209    _triggers.push(self);
11210
11211    self.scroller = scroller;
11212    self.scroll = _getScrollFunc(scroller, direction);
11213    scroll1 = self.scroll();
11214    self.vars = vars;
11215    animation = animation || vars.animation;
11216    "refreshPriority" in vars && (_sort = 1);
11217    scrollerCache.tweenScroll = scrollerCache.tweenScroll || {
11218      top: _getTweenCreator(scroller, _vertical),
11219      left: _getTweenCreator(scroller, _horizontal)
11220    };
11221    self.tweenTo = tweenTo = scrollerCache.tweenScroll[direction.p];
11222
11223    if (animation) {
11224      animation.vars.lazy = false;
11225      animation._initted || animation.vars.immediateRender !== false && vars.immediateRender !== false && animation.render(0, true, true);
11226      self.animation = animation.pause();
11227      animation.scrollTrigger = self;
11228      scrubSmooth = _isNumber(scrub) && scrub;
11229      scrubSmooth && (scrubTween = gsap.to(animation, {
11230        ease: "power3",
11231        duration: scrubSmooth,
11232        onComplete: function onComplete() {
11233          return onScrubComplete && onScrubComplete(self);
11234        }
11235      }));
11236      snap1 = 0;
11237      id || (id = animation.vars.id);
11238    }
11239
11240    if (snap) {
11241      _isObject(snap) || (snap = {
11242        snapTo: snap
11243      });
11244      "scrollBehavior" in _body.style && gsap.set(isViewport ? [_body, _docEl] : scroller, {
11245        scrollBehavior: "auto"
11246      }); // smooth scrolling doesn't work with snap.
11247
11248      snapFunc = _isFunction(snap.snapTo) ? snap.snapTo : snap.snapTo === "labels" ? _getClosestLabel(animation) : snap.snapTo === "labelsDirectional" ? _getLabelAtDirection(animation) : gsap.utils.snap(snap.snapTo);
11249      snapDurClamp = snap.duration || {
11250        min: 0.1,
11251        max: 2
11252      };
11253      snapDurClamp = _isObject(snapDurClamp) ? _clamp(snapDurClamp.min, snapDurClamp.max) : _clamp(snapDurClamp, snapDurClamp);
11254      snapDelayedCall = gsap.delayedCall(snap.delay || scrubSmooth / 2 || 0.1, function () {
11255        if (Math.abs(self.getVelocity()) < 10 && !_pointerIsDown) {
11256          var totalProgress = animation && !isToggle ? animation.totalProgress() : self.progress,
11257              velocity = (totalProgress - snap2) / (_getTime() - _time2) * 1000 || 0,
11258              change1 = _abs(velocity / 2) * velocity / 0.185,
11259              naturalEnd = totalProgress + change1,
11260              endValue = _clamp(0, 1, snapFunc(naturalEnd, self)),
11261              scroll = self.scroll(),
11262              endScroll = Math.round(start + endValue * change),
11263              tween = tweenTo.tween;
11264
11265          if (scroll <= end && scroll >= start && endScroll !== scroll) {
11266            if (tween && !tween._initted && tween.data <= Math.abs(endScroll - scroll)) {
11267              // there's an overlapping snap! So we must figure out which one is closer and let that tween live.
11268              return;
11269            }
11270
11271            tweenTo(endScroll, {
11272              duration: snapDurClamp(_abs(Math.max(_abs(naturalEnd - totalProgress), _abs(endValue - totalProgress)) * 0.185 / velocity / 0.05 || 0)),
11273              ease: snap.ease || "power3",
11274              data: Math.abs(endScroll - scroll),
11275              // record the distance so that if another snap tween occurs (conflict) we 
11275can prioritize the closest snap.
11276              onComplete: function onComplete() {
11277                snap1 = snap2 = animation && !isToggle ? animation.totalProgress() : self.progress;
11278                onSnapComplete && onSnapComplete(self);
11279              }
11280            }, scroll, change1 * change, endScroll - scroll - change1 * change);
11281          }
11282        } else if (self.isActive) {
11283          snapDelayedCall.restart(true);
11284        }
11285      }).pause();
11286    }
11287
11288    id && (_ids[id] = self);
11289    trigger = self.trigger = _toArray(trigger || pin)[0];
11290    pin = pin === true ? trigger : _toArray(pin)[0];
11291    _isString(toggleClass) && (toggleClass = {
11292      targets: trigger,
11293      className: toggleClass
11294    });
11295
11296    if (pin) {
11297      pinSpacing === false || pinSpacing === _margin || (pinSpacing = !pinSpacing && _getComputedStyle(pin.parentNode).display === "flex" ? false : _padding); // if the parent is display: flex, don't apply pinSpacing by default.
11298
11299      self.pin = pin;
11300      vars.force3D !== false && gsap.set(pin, {
11301        force3D: true
11302      });
11303      pinCache = gsap.core.getCache(pin);
11304
11305      if (!pinCache.spacer) {
11306        // record the spacer and pinOriginalState on the cache in case someone tries pinning the same element with MULTIPLE ScrollTriggers - we don't want to have multiple spacers or record the "original" pin state after it has already been affected by another ScrollTrigger.
11307        pinCache.spacer = spacer = _doc.createElement("div");
11308        spacer.setAttribute("class", "pin-spacer" + (id ? " pin-spacer-" + id : ""));
11309        pinCache.pinState = pinOriginalState = _getState(pin);
11310      } else {
11311        pinOriginalState = pinCache.pinState;
11312      }
11313
11314      self.spacer = spacer = pinCache.spacer;
11315      cs = _getComputedStyle(pin);
11316      spacingStart = cs[pinSpacing + direction.os2];
11317      pinGetter = gsap.getProperty(pin);
11318      pinSetter = gsap.quickSetter(pin, direction.a, _px); // pin.firstChild && !_maxScroll(pin, direction) && (pin.style.overflow = "hidden"); // protects from collapsing margins, but can have unintended consequences as demonstrated here: https://codepen.io/GreenSock/pen/1e42c7a73bfa409d2cf1e184e7a4248d so it was removed in favor of just telling people to set up their CSS to avoid the collapsing margins (overflow: hidden | auto is just one option. Another is border-top: 1px solid transparent).
11319
11320      _swapPinIn(pin, spacer, cs);
11321
11322      pinState = _getState(pin);
11323    }
11324
11325    if (markers) {
11326      markerVars = _isObject(markers) ? _setDefaults(markers, _markerDefaults) : _markerDefaults;
11327      markerStartTrigger = _createMarker("scroller-start", id, scroller, direction, markerVars, 0);
11328      markerEndTrigger = _createMarker("scroller-end", id, scroller, direction, markerVars, 0, markerStartTrigger);
11329      offset = markerStartTrigger["offset" + direction.op.d2];
11330      markerStart = _createMarker("start", id, scroller, direction, markerVars, offset);
11331      markerEnd = _createMarker("end", id, scroller, direction, markerVars, offset);
11332
11333      if (!useFixedPosition) {
11334        _makePositionable(isViewport ? _body : scroller);
11335
11336        gsap.set([markerStartTrigger, markerEndTrigger], {
11337          force3D: true
11338        });
11339        markerStartSetter = gsap.quickSetter(markerStartTrigger, direction.a, _px);
11340        markerEndSetter = gsap.quickSetter(markerEndTrigger, direction.a, _px);
11341      }
11342    }
11343
11344    self.revert = function (revert) {
11345      var r = revert !== false || !self.enabled,
11346          prevRefreshing = _refreshing;
11347
11348      if (r !== isReverted) {
11349        if (r) {
11350          prevScroll = Math.max(self.scroll(), self.scroll.rec || 0); // record the scroll so we can revert later (repositioning/pinning things can affect scroll position). In the static refresh() method, we first record all the scroll positions as a reference.
11351
11352          prevProgress = self.progress;
11353          prevAnimProgress = animation && animation.progress();
11354        }
11355
11356        markerStart && [markerStart, markerEnd, markerStartTrigger, markerEndTrigger].forEach(function (m) {
11357          return m.style.display = r ? "none" : "block";
11358        });
11359        r && (_refreshing = 1);
11360        self.update(r); // make sure the pin is back in its original position so that all the measurements are correct.
11361
11362        _refreshing = prevRefreshing;
11363        pin && (r ? _swapPinOut(pin, spacer, pinOriginalState) : (!pinReparent || !self.isActive) && _swapPinIn(pin, spacer, _getComputedStyle(pin), spacerState));
11364        isReverted = r;
11365      }
11366    };
11367
11368    self.refresh = function (soft) {
11369      if (_refreshing || !self.enabled) {
11370        return;
11371      }
11372
11373      if (pin && soft && _lastScrollTime) {
11374        _addListener(ScrollTrigger, "scrollEnd", _softRefresh);
11375
11376        return;
11377      }
11378
11379      _refreshing = 1;
11380      scrubTween && scrubTween.pause();
11381      invalidateOnRefresh && animation && animation.progress(0).invalidate();
11382      isReverted || self.revert();
11383
11384      var size = getScrollerSize(),
11385          scrollerBounds = getScrollerOffsets(),
11386          max = _maxScroll(scroller, direction),
11387          offset = 0,
11388          otherPinOffset = 0,
11389          parsedEnd = vars.end,
11390          parsedEndTrigger = vars.endTrigger || trigger,
11391          parsedStart = vars.start || (vars.start === 0 || !trigger ? 0 : pin ? "0 0" : "0 100%"),
11392          triggerIndex = trigger && Math.max(0, _triggers.indexOf(self)) || 0,
11393          i = triggerIndex,
11394          cs,
11395          bounds,
11396          scroll,
11397          isVertical,
11398          override,
11399          curTrigger,
11400          curPin,
11401          oppositeScroll,
11402          initted;
11403
11404      while (i--) {
11405        // user might try to pin the same element more than once, so we must find any prior triggers with the same pin, revert them, and determine how long they're pinning so that we can offset things appropriately. Make sure we revert from last to first so that things "rewind" properly.
11406        curPin = _triggers[i].pin;
11407        curPin && (curPin === trigger || curPin === pin) && _triggers[i].revert();
11408      }
11409
11410      start = _parsePosition(parsedStart, trigger, size, direction, self.scroll(), markerStart, markerStartTrigger, self, scrollerBounds, borderWidth, useFixedPosition, max) || (pin ? -0.001 : 0);
11411      _isFunction(parsedEnd) && (parsedEnd = parsedEnd(self));
11412
11413      if (_isString(parsedEnd) && !parsedEnd.indexOf("+=")) {
11414        if (~parsedEnd.indexOf(" ")) {
11415          parsedEnd = (_isString(parsedStart) ? parsedStart.split(" ")[0] : "") + parsedEnd;
11416        } else {
11417          offset = _offsetToPx(parsedEnd.substr(2), size);
11418          parsedEnd = _isString(parsedStart) ? parsedStart : start + offset; // _parsePosition won't factor in the offset if the start is a 
11418number, so do it here.
11419
11420          parsedEndTrigger = trigger;
11421        }
11422      }
11423
11424      end = Math.max(start, _parsePosition(parsedEnd || (parsedEndTrigger ? "100% 0" : max), parsedEndTrigger, size, direction, self.scroll() + offset, markerEnd, markerEndTrigger, self, scrollerBounds, borderWidth, useFixedPosition, max)) || -0.001;
11425      change = end - start || (start -= 0.01) && 0.001;
11426      offset = 0;
11427      i = triggerIndex;
11428
11429      while (i--) {
11430        curTrigger = _triggers[i];
11431        curPin = curTrigger.pin;
11432
11433        if (curPin && curTrigger.start - curTrigger._pinPush < start) {
11434          cs = curTrigger.end - curTrigger.start;
11435          curPin === trigger && (offset += cs);
11436          curPin === pin && (otherPinOffset += cs);
11437        }
11438      }
11439
11440      start += offset;
11441      end += offset;
11442      self._pinPush = otherPinOffset;
11443
11444      if (markerStart && offset) {
11445        // offset the markers if necessary
11446        cs = {};
11447        cs[direction.a] = "+=" + offset;
11448        gsap.set([markerStart, markerEnd], cs);
11449      }
11450
11451      if (pin) {
11452        cs = _getComputedStyle(pin);
11453        isVertical = direction === _vertical;
11454        scroll = self.scroll(); // recalculate because the triggers can affect the scroll
11455
11456        pinStart = parseFloat(pinGetter(direction.a)) + otherPinOffset;
11457        !max && end > 1 && ((isViewport ? _body : scroller).style["overflow-" + direction.a] = "scroll"); // makes sure the scroller has a scrollbar, otherwise if something has width: 100%, for example, it would be too big (exclude the scrollbar). See https://greensock.com/forums/topic/25182-scrolltrigger-width-of-page-increase-where-markers-are-set-to-false/
11458
11459        _swapPinIn(pin, spacer, cs);
11460
11461        pinState = _getState(pin); // transforms will interfere with the top/left/right/bottom placement, so remove them temporarily. getBoundingClientRect() factors in transforms.
11462
11463        bounds = _getBounds(pin, true);
11464        oppositeScroll = useFixedPosition && _getScrollFunc(scroller, isVertical ? _horizontal : _vertical)();
11465
11466        if (pinSpacing) {
11467          spacerState = [pinSpacing + direction.os2, change + otherPinOffset + _px];
11468          spacerState.t = spacer;
11469          i = pinSpacing === _padding ? _getSize(pin, direction) + change + otherPinOffset : 0;
11470          i && spacerState.push(direction.d, i + _px); // for box-sizing: border-box (must include padding).
11471
11472          _setState(spacerState);
11473
11474          useFixedPosition && self.scroll(prevScroll);
11475        }
11476
11477        if (useFixedPosition) {
11478          override = {
11479            top: bounds.top + (isVertical ? scroll - start : oppositeScroll) + _px,
11480            left: bounds.left + (isVertical ? oppositeScroll : scroll - start) + _px,
11481            boxSizing: "border-box",
11482            position: "fixed"
11483          };
11484          override[_width] = override["max" + _Width] = Math.ceil(bounds.width) + _px;
11485          override[_height] = override["max" + _Height] = Math.ceil(bounds.height) + _px;
11486          override[_margin] = override[_margin + _Top] = override[_margin + _Right] = override[_margin + _Bottom] = override[_margin + _Left] = "0";
11487          override[_padding] = cs[_padding];
11488          override[_padding + _Top] = cs[_padding + _Top];
11489          override[_padding + _Right] = cs[_padding + _Right];
11490          override[_padding + _Bottom] = cs[_padding + _Bottom];
11491          override[_padding + _Left] = cs[_padding + _Left];
11492          pinActiveState = _copyState(pinOriginalState, override, pinReparent);
11493        }
11494
11495        if (animation) {
11496          // the animation might be affecting the transform, so we must jump to the end, check the value, and compensate accordingly. Otherwise, when it becomes unpinned, the pinSetter() will get set to a value that doesn't include whatever the animation did.
11497          initted = animation._initted; // if not, we must invalidate() after this step, otherwise it could lock in starting values prematurely.
11498
11499          _suppressOverwrites(1);
11500
11501          animation.progress(1, true);
11502          pinChange = pinGetter(direction.a) - pinStart + change + otherPinOffset;
11503          change !== pinChange && pinActiveState.splice(pinActiveState.length - 2, 2); // transform is the last property/value set in the state Array. Since the animation is controlling that, we should omit it.
11504
11505          animation.progress(0, true);
11506          initted || animation.invalidate();
11507
11508          _suppressOverwrites(0);
11509        } else {
11510          pinChange = change;
11511        }
11512      } else if (trigger && self.scroll()) {
11513        // it may be INSIDE a pinned element, so walk up the tree and look for any elements with _pinOffset to compensate because anything with pinSpacing that's already scrolled would throw off the measurements in getBoundingClientRect()
11514        bounds = trigger.parentNode;
11515
11516        while (bounds && bounds !== _body) {
11517          if (bounds._pinOffset) {
11518            start -= bounds._pinOffset;
11519            end -= bounds._pinOffset;
11520          }
11521
11522          bounds = bounds.parentNode;
11523        }
11524      }
11525
11526      for (i = 0; i < triggerIndex; i++) {
11527        // make sure we revert from first to last to make sure things reach their end state properly
11528        curTrigger = _triggers[i].pin;
11529        curTrigger && (curTrigger === trigger || curTrigger === pin) && _triggers[i].revert(false);
11530      }
11531
11532      self.start = start;
11533      self.end = end;
11534      scroll1 = scroll2 = self.scroll(); // reset velocity
11535
11536      scroll1 < prevScroll && self.scroll(prevScroll);
11537      self.revert(false);
11538      _refreshing = 0;
11539      animation && isToggle && animation._initted && animation.progress(prevAnimProgress, true).render(animation.time(), true, true); // must force a re-render because if saveStyles() was used on the target(s), the styles could have been wiped out during the refresh().
11540
11541      if (prevProgress !== self.progress) {
11542        // ensures that the direction is set properly (when refreshing, progress is set back to 0 initially, then back again to wherever it needs to be) and that callbacks are triggered.
11543        scrubTween && animation.totalProgress(prevProgress, true); // to avoid issues where animation callbacks like onStart aren't triggered.
11544
11545        self.progress = prevProgress;
11546        self.update();
11547      }
11548
11549      pin && pinSpacing && (spacer._pinOffset = Math.round(self.progress * pinChange));
11550      onRefresh && onRefresh(self);
11551    };
11552
11553    self.getVelocity = function () {
11554      return (self.scroll() - scroll2) / (_getTime() - _time2) * 1000 || 0;
11555    };
11556
11557    self.update = function (reset, recordVelocity) {
11558      var scroll = self.scroll(),
11559          p = reset ? 0 : (scroll - start) / change,
11560          clipped = p < 0 ? 0 : p > 1 ? 1 : p || 0,
11561          prevProgress = self.progress,
11562          isActive,
11563          wasActive,
11564          toggleState,
11565          action,
11566          stateChanged,
11567          toggled;
11568
11569      if (recordVelocity) {
11570        scroll2 = scroll1;
11571        scroll1 = scroll;
11572
11573        if (snap) {
11574          snap2 = snap1;
11575          snap1 = animation && !isToggle ? animation.totalProgress() : clipped;
11576        }
11577      } // anticipate the pinning a few ticks ahead of time based on velocity to avoid a visual glitch due to the fact that most browsers do scrolling on a separate thread (not synced with requestAnimationFrame).
11578
11579
11580      anticipatePin && !clipped && pin && !_refreshing && !_startup && _lastScrollTime && start < scroll + (scroll - scroll2) / (_getTime() - _time2) * anticipatePin && (clipped = 0.0001);
11581
11582      if (clipped !== prevProgress && self.enabled) {
11583        isActive = self.isActive = !!clipped && clipped < 1;
11584        wasActive = !!prevProgress && prevProgress < 1;
11585        toggled = isActive !== wasActive;
11586        stateChanged = toggled || !!clipped !== !!prevProgress; // could go from start all the way to end, thus it didn't toggle but it did change state in a sense (may need to fire a callback)
11587
11588        self.direction = clipped > prevProgress ? 1 : -1;
11589        self.progress = clipped;
11590
11591        if (!isToggle) {
11592          if (scrubTween && !_refreshing && !_startup) {
11593            scrubTween.vars.totalProgress = clipped;
11594            scrubTween.invalidate().restart();
11595          } else if (animation) {
11596            animation.totalProgress(clipped, !!_refreshing);
11597          }
11598        }
11599
11600        if (pin) {
11601          reset && pinSpacing && (spacer.style[pinSpacing + direction.os2] = spacingStart);
11602
11603          if (!useFixedPosition) {
11604            pinSetter(pinStart + pinChange * clipped);
11605          } else if (stateChanged) {
11606            action = !reset && clipped > prevProgress && end + 1 > scroll && scroll + 1 >= _maxScroll(scroller, direction); // if it's at the VERY end of the page, don't switch away from position: fixed because it's pointless and it could cause a brief flash when the user scrolls back up (when it gets pinned again)
11607
11608            if (pinReparent) {
11609              if (!reset && (isActive || action)) {
11610                var bounds = _getBounds(pin, true),
11611                    _offset = scroll - start;
11612
11613                _reparent(pin, _body, bounds.top + (direction === _vertical ? _offset : 0) + _px, bounds.left + (direction === _vertical ? 0 : _offset) + _px);
11614              } else {
11615                _reparent(pin, spacer);
11616              }
11617            }
11618
11619            _setState(isActive || action ? pinActiveState : pinState);
11620
11621            pinChange !== change && clipped < 1 && isActive || pinSetter(pinStart + (clipped === 1 && !action ? pinChange : 0));
11622          }
11623        }
11624
11625        snap && !tweenTo.tween && !_refreshing && !_startup && snapDelayedCall.restart(true);
11626        toggleClass && (toggled || once && clipped && (clipped < 1 || !_limitCallbacks)) && _toArray(toggleClass.targets).forEach(function (el) {
11627          return el.classList[isActive || once ? "add" : "remove"](toggleClass.className);
11628        }); // classes could affect positioning, so do it even if reset or refreshing is true.
11629
11630        onUpdate && !isToggle && !reset && onUpdate(self);
11631
11632        if (stateChanged && !_refreshing) {
11633          toggleState = clipped && !prevProgress ? 0 : clipped === 1 ? 1 : prevProgress === 1 ? 2 : 3; // 0 = enter, 1 = leave, 2 = enterBack, 3 = leaveBack (we prioritize the FIRST encounter, thus if you scroll really fast past the onEnter and onLeave in one tick, it'd prioritize onEnter.
11634
11635          if (isToggle) {
11636            action = !toggled && toggleActions[toggleState + 1] !== "none" && toggleActions[toggleState + 1] || toggleActions[toggleState]; // if it didn't toggle, that means it shot right past and since we prioritize the "enter" action, we should switch to the "leave" in this case (but only if one is defined)
11637
11638            if (animation && (action === "complete" || action === "reset" || action in animation)) {
11639              if (action === "complete") {
11640                animation.pause().totalProgress(1);
11641              } else if (action === "reset") {
11642                animation.restart(true).pause();
11643              } else {
11644                animation[action]();
11645              }
11646            }
11647
11648            onUpdate && onUpdate(self);
11649          }
11650
11651          if (toggled || !_limitCallbacks) {
11652            // on startup, the page could be scrolled and we don't want to fire callbacks that didn't toggle. For example onEnter shouldn't fire if the ScrollTrigger isn't actually entered.
11653            onToggle && toggled && onToggle(self);
11654            callbacks[toggleState] && callbacks[toggleState](self);
11655            once && (clipped === 1 ? self.kill(false, 1) : callbacks[toggleState] = 0); // a callback shouldn't be called again if once is true.
11656
11657            if (!toggled) {
11658              // it's possible to go completely past, like from before the start to after the end (or vice-versa) in which case BOTH callbacks should be fired in that order
11659              toggleState = clipped === 1 ? 1 : 3;
11660              callbacks[toggleState] && callbacks[toggleState](self);
11661            }
11662          }
11663        } else if (isToggle && onUpdate && !_refreshing) {
11664          onUpdate(self);
11665        }
11666      } // update absolutely-positioned markers (only if the scroller isn't the viewport)
11667
11668
11669      if (markerEndSetter) {
11670        markerStartSetter(scroll + (markerStartTrigger._isFlipped ? 1 : 0));
11671        markerEndSetter(scroll);
11672      }
11673    };
11674
11675    self.enable = function () {
11676      if (!self.enabled) {
11677        self.enabled = true;
11678
11679        _addListener(scroller, "resize", _onResize);
11680
11681        _addListener(scroller, "scroll", _onScroll);
11682
11683        onRefreshInit && _addListener(ScrollTrigger, "refreshInit", onRefreshInit);
11684        !animation || !animation.add ? self.refresh() : gsap.delayedCall(0.01, function () {
11685          return start || end || self.refresh();
11686        }) && (change = 0.01) && (start = end = 0); // if the animation is a timeline, it may not have been populated yet, so it wouldn't render at the proper place on the first refresh(), thus we should schedule one for the next tick.
11687      }
11688    };
11689
11690    self.disable = function (reset, allowAnimation) {
11691      if (self.enabled) {
11692        reset !== false && self.revert();
11693        self.enabled = self.isActive = false;
11694        allowAnimation || scrubTween && scrubTween.pause();
11695        prevScroll = 0;
11696        pinCache && (pinCache.uncache = 1);
11697        onRefreshInit && _removeListener(ScrollTrigger, "refreshInit", onRefreshInit);
11698
11699        if (snapDelayedCall) {
11700          snapDelayedCall.pause();
11701          tweenTo.tween && tweenTo.tween.kill() && (tweenTo.tween = 0);
11702        }
11703
11704        if (!isViewport) {
11705          var i = _triggers.length;
11706
11707          while (i--) {
11708            if (_triggers[i].scroller === scroller && _triggers[i] !== self) {
11709              return; //don't remove the listeners if there are still other triggers referencing it.
11710            }
11711          }
11712
11713          _removeListener(scroller, "resize", _onResize);
11714
11715          _removeListener(scroller, "scroll", _onScroll);
11716        }
11717      }
11718    };
11719
11720    self.kill = function (revert, allowAnimation) {
11721      self.disable(revert, allowAnimation);
11722      id && delete _ids[id];
11723
11724      var i = _triggers.indexOf(self);
11725
11726      _triggers.splice(i, 1);
11727
11728      i === _i && _direction > 0 && _i--; // if we're in the middle of a refresh() or update(), splicing would cause skips in the index, so adjust...
11729
11730      if (animation) {
11731        animation.scrollTrigger = null;
11732        revert && animation.render(-1);
11733        allowAnimation || animation.kill();
11734      }
11735
11736      markerStart && [markerStart, markerEnd, markerStartTrigger, markerEndTrigger].forEach(function (m) {
11737        return m.parentNode.removeChild(m);
11738      });
11739
11740      if (pin) {
11741        pinCache && (pinCache.uncache = 1);
11742        i = 0;
11743
11744        _triggers.forEach(function (t) {
11745          return t.pin === pin && i++;
11746        });
11747
11748        i || (pinCache.spacer = 0); // if there aren't any more ScrollTriggers with the same pin, remove the spacer, otherwise it could be contaminated with old/stale values if the user re-creates a ScrollTrigger for the same element.
11749      }
11750    };
11751
11752    self.enable();
11753  };
11754
11755  ScrollTrigger.register = function register(core) {
11756    if (!_coreInitted) {
11757      gsap = core || _getGSAP();
11758
11759      if (_windowExists() && window.document) {
11760        _win = window;
11761        _doc = document;
11762        _docEl = _doc.documentElement;
11763        _body = _doc.body;
11764      }
11765
11766      if (gsap) {
11767        _toArray = gsap.utils.toArray;
11768        _clamp = gsap.utils.clamp;
11769        _suppressOverwrites = gsap.core.suppressOverwrites || _passThrough;
11770        gsap.core.globals("ScrollTrigger", ScrollTrigger); // must register the global manually because in Internet Explorer, functions (classes) don't have a "name" property.
11771
11772        if (_body) {
11773          _raf = _win.requestAnimationFrame || function (f) {
11774            return setTimeout(f, 16);
11775          };
11776
11777          _addListener(_win, "mousewheel", _onScroll);
11778
11779          _root = [_win, _doc, _docEl, _body];
11780
11781          _addListener(_doc, "scroll", _onScroll); // some browsers (like Chrome), the window stops dispatching scroll events on the window if you scroll really fast, but it's consistent on the document!
11782
11783
11784          var bodyStyle = _body.style,
11785              border = bodyStyle.borderTop,
11786              bounds;
11787          bodyStyle.borderTop = "1px solid #000"; // works around an issue where a margin of a child element could throw off the bounds of the _body, making it seem like there's a margin when there actually isn't. The border ensures that the bounds are accurate.
11788
11789          bounds = _getBounds(_body);
11790          _vertical.m = Math.round(bounds.top + _vertical.sc()) || 0; // accommodate the offset of the <body> caused by margins and/or padding
11791
11792          _horizontal.m = Math.round(bounds.left + _horizontal.sc()) || 0;
11793          border ? bodyStyle.borderTop = border : bodyStyle.removeProperty("border-top");
11794          _syncInterval = setInterval(_sync, 200);
11795          gsap.delayedCall(0.5, function () {
11796            return _startup = 0;
11797          });
11798
11799          _addListener(_doc, "touchcancel", _passThrough); // some older Android devices intermittently stop dispatching "touchmove" events if we don't listen for "touchcancel" on the document.
11800
11801
11802          _addListener(_body, "touchstart", _passThrough); //works around Safari bug: https://greensock.com/forums/topic/21450-draggable-in-iframe-on-mobile-is-buggy/
11803
11804
11805          _multiListener(_addListener, _doc, "pointerdown,touchstart,mousedown", function () {
11806            return _pointerIsDown = 1;
11807          });
11808
11809          _multiListener(_addListener, _doc, "pointerup,touchend,mouseup", function () {
11810            return _pointerIsDown = 0;
11811          });
11812
11813          _transformProp = gsap.utils.checkPrefix("transform");
11814
11815          _stateProps.push(_transformProp);
11816
11817          _coreInitted = _getTime();
11818          _resizeDelay = gsap.delayedCall(0.2, _refreshAll).pause();
11819          _autoRefresh = [_doc, "visibilitychange", function () {
11820            var w = _win.innerWidth,
11821                h = _win.innerHeight;
11822
11823            if (_doc.hidden) {
11824              _prevWidth = w;
11825              _prevHeight = h;
11826            } else if (_prevWidth !== w || _prevHeight !== h) {
11827              _onResize();
11828            }
11829          }, _doc, "DOMContentLoaded", _refreshAll, _win, "load", function () {
11830            return _lastScrollTime || _refreshAll();
11831          }, _win, "resize", _onResize];
11832
11833          _iterateAutoRefresh(_addListener);
11834        }
11835      }
11836    }
11837
11838    return _coreInitted;
11839  };
11840
11841  ScrollTrigger.defaults = function defaults(config) {
11842    for (var p in config) {
11843      _defaults[p] = config[p];
11844    }
11845  };
11846
11847  ScrollTrigger.kill = function kill() {
11848    _enabled = 0;
11849
11850    _triggers.slice(0).forEach(function (trigger) {
11851      return trigger.kill(1);
11852    });
11853  };
11854
11855  ScrollTrigger.config = function config(vars) {
11856    "limitCallbacks" in vars && (_limitCallbacks = !!vars.limitCallbacks);
11857    var ms = vars.syncInterval;
11858    ms && clearInterval(_syncInterval) || (_syncInterval = ms) && setInterval(_sync, ms);
11859
11860    if ("autoRefreshEvents" in vars) {
11861      _iterateAutoRefresh(_removeListener) || _iterateAutoRefresh(_addListener, vars.autoRefreshEvents || "none");
11862      _ignoreResize = (vars.autoRefreshEvents + "").indexOf("resize") === -1;
11863    }
11864  };
11865
11866  ScrollTrigger.scrollerProxy = function scrollerProxy(target, vars) {
11867    var t = _toArray(target)[0],
11868        i = _scrollers.indexOf(t),
11869        isViewport = _isViewport(t);
11870
11871    if (~i) {
11872      _scrollers.splice(i, isViewport ? 6 : 2);
11873    }
11874
11875    isViewport ? _proxies.unshift(_win, vars, _body, vars, _docEl, vars) : _proxies.unshift(t, vars);
11876  };
11877
11878  ScrollTrigger.matchMedia = function matchMedia(vars) {
11879    // _media is populated in the following order: mediaQueryString, onMatch, onUnmatch, isMatched. So if there are two media queries, the Array would have a length of 8
11880    var mq, p, i, func, result;
11881
11882    for (p in vars) {
11883      i = _media.indexOf(p);
11884      func = vars[p];
11885      _creatingMedia = p;
11886
11887      if (p === "all") {
11888        func();
11889      } else {
11890        mq = _win.matchMedia(p);
11891
11892        if (mq) {
11893          mq.matches && (result = func());
11894
11895          if (~i) {
11896            _media[i + 1] = _combineFunc(_media[i + 1], func);
11897            _media[i + 2] = _combineFunc(_media[i + 2], result);
11898          } else {
11899            i = _media.length;
11900
11901            _media.push(p, func, result);
11902
11903            mq.addListener ? mq.addListener(_onMediaChange) : mq.addEventListener("change", _onMediaChange);
11904          }
11905
11906          _media[i + 3] = mq.matches;
11907        }
11908      }
11909
11910      _creatingMedia = 0;
11911    }
11912
11913    return _media;
11914  };
11915
11916  ScrollTrigger.clearMatchMedia = function clearMatchMedia(query) {
11917    query || (_media.length = 0);
11918    query = _media.indexOf(query);
11919    query >= 0 && _media.splice(query, 4);
11920  };
11921
11922  return ScrollTrigger;
11923}();
11924ScrollTrigger.version = "3.6.0";
11925
11926ScrollTrigger.saveStyles = function (targets) {
11927  return targets ? _toArray(targets).forEach(function (target) {
11928    if (target && target.style) {
11929      var i = _savedStyles.indexOf(target);
11930
11931      i >= 0 && _savedStyles.splice(i, 4);
11932
11933      _savedStyles.push(target, target.style.cssText, gsap.core.getCache(target), _creatingMedia);
11934    }
11935  }) : _savedStyles;
11936};
11937
11938ScrollTrigger.revert = function (soft, media) {
11939  return _revertAll(!soft, media);
11940};
11941
11942ScrollTrigger.create = function (vars, animation) {
11943  return new ScrollTrigger(vars, animation);
11944};
11945
11946ScrollTrigger.refresh = function (safe) {
11947  return safe ? _onResize() : _refreshAll(true);
11948};
11949
11950ScrollTrigger.update = _updateAll;
11951
11952ScrollTrigger.maxScroll = function (element, horizontal) {
11953  return _maxScroll(element, horizontal ? _horizontal : _vertical);
11954};
11955
11956ScrollTrigger.getScrollFunc = function (element, horizontal) {
11957  return _getScrollFunc(_toArray(element)[0], horizontal ? _horizontal : _vertical);
11958};
11959
11960ScrollTrigger.getById = function (id) {
11961  return _ids[id];
11962};
11963
11964ScrollTrigger.getAll = function () {
11965  return _triggers.slice(0);
11966};
11967
11968ScrollTrigger.isScrolling = function () {
11969  return !!_lastScrollTime;
11970};
11971
11972ScrollTrigger.addEventListener = function (type, callback) {
11973  var a = _listeners[type] || (_listeners[type] = []);
11974  ~a.indexOf(callback) || a.push(callback);
11975};
11976
11977ScrollTrigger.removeEventListener = function (type, callback) {
11978  var a = _listeners[type],
11979      i = a && a.indexOf(callback);
11980  i >= 0 && a.splice(i, 1);
11981};
11982
11983ScrollTrigger.batch = function (targets, vars) {
11984  var result = [],
11985      varsCopy = {},
11986      interval = vars.interval || 0.016,
11987      batchMax = vars.batchMax || 1e9,
11988      proxyCallback = function proxyCallback(type, callback) {
11989    var elements = [],
11990        triggers = [],
11991        delay = gsap.delayedCall(interval, function () {
11992      callback(elements, triggers);
11993      elements = [];
11994      triggers = [];
11995    }).pause();
11996    return function (self) {
11997      elements.length || delay.restart(true);
11998      elements.push(self.trigger);
11999      triggers.push(self);
12000      batchMax <= elements.length && delay.progress(1);
12001    };
12002  },
12003      p;
12004
12005  for (p in vars) {
12006    varsCopy[p] = p.substr(0, 2) === "on" && _isFunction(vars[p]) && p !== "onRefreshInit" ? proxyCallback(p, vars[p]) : vars[p];
12007  }
12008
12009  if (_isFunction(batchMax)) {
12010    batchMax = batchMax();
12011
12012    _addListener(ScrollTrigger, "refresh", function () {
12013      return batchMax = vars.batchMax();
12014    });
12015  }
12016
12017  _toArray(targets).forEach(function (target) {
12018    var config = {};
12019
12020    for (p in varsCopy) {
12021      config[p] = varsCopy[p];
12022    }
12023
12024    config.trigger = target;
12025    result.push(ScrollTrigger.create(config));
12026  });
12027
12028  return result;
12029};
12030
12031ScrollTrigger.sort = function (func) {
12032  return _triggers.sort(func || function (a, b) {
12033    return (a.vars.refreshPriority || 0) * -1e6 + a.start - (b.start + (b.vars.refreshPriority || 0) * -1e6);
12034  });
12035};
12036
12037_getGSAP() && gsap.registerPlugin(ScrollTrigger);
12038
12039
12040/***/ }),
12041/* 22 */
12042/***/ (function(module, exports, __webpack_require__) {
12043
12044var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/*
12045     _ _      _       _
12046 ___| (_) ___| | __  (_)___
12047/ __| | |/ __| |/ /  | / __|
12048\__ \ | | (__|   < _ | \__ \
12049|___/_|_|\___|_|\_(_)/ |___/
12050                   |__/
12051
12052 Version: 1.8.1
12053  Author: Ken Wheeler
12054 Website: http://kenwheeler.github.io
12055    Docs: http://kenwheeler.github.io/slick
12056    Repo: http://github.com/kenwheeler/slick
12057  Issues: http://github.com/kenwheeler/slick/issues
12058
12059 */
12060/* global window, document, define, jQuery, setInterval, clearInterval */
12061;(function(factory) {
12062    'use strict';
12063    if (true) {
12064        !(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0)], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
12065				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
12066				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
12067				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
12068    } else if (typeof exports !== 'undefined') {
12069        module.exports = factory(require('jquery'));
12070    } else {
12071        factory(jQuery);
12072    }
12073
12074}(function($) {
12075    'use strict';
vendor: 31,932 bytes, lines 12075-13138
12075
12076    var Slick = window.Slick || {};
12077
12078    Slick = (function() {
12079
12080        var instanceUid = 0;
12081
12082        function Slick(element, settings) {
12083
12084            var _ = this, dataSettings;
12085
12086            _.defaults = {
12087                accessibility: true,
12088                adaptiveHeight: false,
12089                appendArrows: $(element),
12090                appendDots: $(element),
12091                arrows: true,
12092                asNavFor: null,
12093                prevArrow: '<button class="slick-prev" aria-label="Previous" type="button">Previous</button>',
12094                nextArrow: '<button class="slick-next" aria-label="Next" type="button">Next</button>',
12095                autoplay: false,
12096                autoplaySpeed: 3000,
12097                centerMode: false,
12098                centerPadding: '50px',
12099                cssEase: 'ease',
12100                customPaging: function(slider, i) {
12101                    return $('<button type="button" />').text(i + 1);
12102                },
12103                dots: false,
12104                dotsClass: 'slick-dots',
12105                draggable: true,
12106                easing: 'linear',
12107                edgeFriction: 0.35,
12108                fade: false,
12109                focusOnSelect: false,
12110                focusOnChange: false,
12111                infinite: true,
12112                initialSlide: 0,
12113                lazyLoad: 'ondemand',
12114                mobileFirst: false,
12115                pauseOnHover: true,
12116                pauseOnFocus: true,
12117                pauseOnDotsHover: false,
12118                respondTo: 'window',
12119                responsive: null,
12120                rows: 1,
12121                rtl: false,
12122                slide: '',
12123                slidesPerRow: 1,
12124                slidesToShow: 1,
12125                slidesToScroll: 1,
12126                speed: 500,
12127                swipe: true,
12128                swipeToSlide: false,
12129                touchMove: true,
12130                touchThreshold: 5,
12131                useCSS: true,
12132                useTransform: true,
12133                variableWidth: false,
12134                vertical: false,
12135                verticalSwiping: false,
12136                waitForAnimate: true,
12137                zIndex: 1000
12138            };
12139
12140            _.initials = {
12141                animating: false,
12142                dragging: false,
12143                autoPlayTimer: null,
12144                currentDirection: 0,
12145                currentLeft: null,
12146                currentSlide: 0,
12147                direction: 1,
12148                $dots: null,
12149                listWidth: null,
12150                listHeight: null,
12151                loadIndex: 0,
12152                $nextArrow: null,
12153                $prevArrow: null,
12154                scrolling: false,
12155                slideCount: null,
12156                slideWidth: null,
12157                $slideTrack: null,
12158                $slides: null,
12159                sliding: false,
12160                slideOffset: 0,
12161                swipeLeft: null,
12162                swiping: false,
12163                $list: null,
12164                touchObject: {},
12165                transformsEnabled: false,
12166                unslicked: false
12167            };
12168
12169            $.extend(_, _.initials);
12170
12171            _.activeBreakpoint = null;
12172            _.animType = null;
12173            _.animProp = null;
12174            _.breakpoints = [];
12175            _.breakpointSettings = [];
12176            _.cssTransitions = false;
12177            _.focussed = false;
12178            _.interrupted = false;
12179            _.hidden = 'hidden';
12180            _.paused = true;
12181            _.positionProp = null;
12182            _.respondTo = null;
12183            _.rowCount = 1;
12184            _.shouldClick = true;
12185            _.$slider = $(element);
12186            _.$slidesCache = null;
12187            _.transformType = null;
12188            _.transitionType = null;
12189            _.visibilityChange = 'visibilitychange';
12190            _.windowWidth = 0;
12191            _.windowTimer = null;
12192
12193            dataSettings = $(element).data('slick') || {};
12194
12195            _.options = $.extend({}, _.defaults, settings, dataSettings);
12196
12197            _.currentSlide = _.options.initialSlide;
12198
12199            _.originalSettings = _.options;
12200
12201            if (typeof document.mozHidden !== 'undefined') {
12202                _.hidden = 'mozHidden';
12203                _.visibilityChange = 'mozvisibilitychange';
12204            } else if (typeof document.webkitHidden !== 'undefined') {
12205                _.hidden = 'webkitHidden';
12206                _.visibilityChange = 'webkitvisibilitychange';
12207            }
12208
12209            _.autoPlay = $.proxy(_.autoPlay, _);
12210            _.autoPlayClear = $.proxy(_.autoPlayClear, _);
12211            _.autoPlayIterator = $.proxy(_.autoPlayIterator, _);
12212            _.changeSlide = $.proxy(_.changeSlide, _);
12213            _.clickHandler = $.proxy(_.clickHandler, _);
12214            _.selectHandler = $.proxy(_.selectHandler, _);
12215            _.setPosition = $.proxy(_.setPosition, _);
12216            _.swipeHandler = $.proxy(_.swipeHandler, _);
12217            _.dragHandler = $.proxy(_.dragHandler, _);
12218            _.keyHandler = $.proxy(_.keyHandler, _);
12219
12220            _.instanceUid = instanceUid++;
12221
12222            // A simple way to check for HTML strings
12223            // Strict HTML recognition (must start with <)
12224            // Extracted from jQuery v1.11 source
12225            _.htmlExpr = /^(?:\s*(<[\w\W]+>)[^>]*)$/;
12226
12227
12228            _.registerBreakpoints();
12229            _.init(true);
12230
12231        }
12232
12233        return Slick;
12234
12235    }());
12236
12237    Slick.prototype.activateADA = function() {
12238        var _ = this;
12239
12240        _.$slideTrack.find('.slick-active').attr({
12241            'aria-hidden': 'false'
12242        }).find('a, input, button, select').attr({
12243            'tabindex': '0'
12244        });
12245
12246    };
12247
12248    Slick.prototype.addSlide = Slick.prototype.slickAdd = function(markup, index, addBefore) {
12249
12250        var _ = this;
12251
12252        if (typeof(index) === 'boolean') {
12253            addBefore = index;
12254            index = null;
12255        } else if (index < 0 || (index >= _.slideCount)) {
12256            return false;
12257        }
12258
12259        _.unload();
12260
12261        if (typeof(index) === 'number') {
12262            if (index === 0 && _.$slides.length === 0) {
12263                $(markup).appendTo(_.$slideTrack);
12264            } else if (addBefore) {
12265                $(markup).insertBefore(_.$slides.eq(index));
12266            } else {
12267                $(markup).insertAfter(_.$slides.eq(index));
12268            }
12269        } else {
12270            if (addBefore === true) {
12271                $(markup).prependTo(_.$slideTrack);
12272            } else {
12273                $(markup).appendTo(_.$slideTrack);
12274            }
12275        }
12276
12277        _.$slides = _.$slideTrack.children(this.options.slide);
12278
12279        _.$slideTrack.children(this.options.slide).detach();
12280
12281        _.$slideTrack.append(_.$slides);
12282
12283        _.$slides.each(function(index, element) {
12284            $(element).attr('data-slick-index', index);
12285        });
12286
12287        _.$slidesCache = _.$slides;
12288
12289        _.reinit();
12290
12291    };
12292
12293    Slick.prototype.animateHeight = function() {
12294        var _ = this;
12295        if (_.options.slidesToShow === 1 && _.options.adaptiveHeight === true && _.options.vertical === false) {
12296            var targetHeight = _.$slides.eq(_.currentSlide).outerHeight(true);
12297            _.$list.animate({
12298                height: targetHeight
12299            }, _.options.speed);
12300        }
12301    };
12302
12303    Slick.prototype.animateSlide = function(targetLeft, callback) {
12304
12305        var animProps = {},
12306            _ = this;
12307
12308        _.animateHeight();
12309
12310        if (_.options.rtl === true && _.options.vertical === false) {
12311            targetLeft = -targetLeft;
12312        }
12313        if (_.transformsEnabled === false) {
12314            if (_.options.vertical === false) {
12315                _.$slideTrack.animate({
12316                    left: targetLeft
12317                }, _.options.speed, _.options.easing, callback);
12318            } else {
12319                _.$slideTrack.animate({
12320                    top: targetLeft
12321                }, _.options.speed, _.options.easing, callback);
12322            }
12323
12324        } else {
12325
12326            if (_.cssTransitions === false) {
12327                if (_.options.rtl === true) {
12328                    _.currentLeft = -(_.currentLeft);
12329                }
12330                $({
12331                    animStart: _.currentLeft
12332                }).animate({
12333                    animStart: targetLeft
12334                }, {
12335                    duration: _.options.speed,
12336                    easing: _.options.easing,
12337                    step: function(now) {
12338                        now = Math.ceil(now);
12339                        if (_.options.vertical === false) {
12340                            animProps[_.animType] = 'translate(' +
12341                                now + 'px, 0px)';
12342                            _.$slideTrack.css(animProps);
12343                        } else {
12344                            animProps[_.animType] = 'translate(0px,' +
12345                                now + 'px)';
12346                            _.$slideTrack.css(animProps);
12347                        }
12348                    },
12349                    complete: function() {
12350                        if (callback) {
12351                            callback.call();
12352                        }
12353                    }
12354                });
12355
12356            } else {
12357
12358                _.applyTransition();
12359                targetLeft = Math.ceil(targetLeft);
12360
12361                if (_.options.vertical === false) {
12362                    animProps[_.animType] = 'translate3d(' + targetLeft + 'px, 0px, 0px)';
12363                } else {
12364                    animProps[_.animType] = 'translate3d(0px,' + targetLeft + 'px, 0px)';
12365                }
12366                _.$slideTrack.css(animProps);
12367
12368                if (callback) {
12369                    setTimeout(function() {
12370
12371                        _.disableTransition();
12372
12373                        callback.call();
12374                    }, _.options.speed);
12375                }
12376
12377            }
12378
12379        }
12380
12381    };
12382
12383    Slick.prototype.getNavTarget = function() {
12384
12385        var _ = this,
12386            asNavFor = _.options.asNavFor;
12387
12388        if ( asNavFor && asNavFor !== null ) {
12389            asNavFor = $(asNavFor).not(_.$slider);
12390        }
12391
12392        return asNavFor;
12393
12394    };
12395
12396    Slick.prototype.asNavFor = function(index) {
12397
12398        var _ = this,
12399            asNavFor = _.getNavTarget();
12400
12401        if ( asNavFor !== null && typeof asNavFor === 'object' ) {
12402            asNavFor.each(function() {
12403                var target = $(this).slick('getSlick');
12404                if(!target.unslicked) {
12405                    target.slideHandler(index, true);
12406                }
12407            });
12408        }
12409
12410    };
12411
12412    Slick.prototype.applyTransition = function(slide) {
12413
12414        var _ = this,
12415            transition = {};
12416
12417        if (_.options.fade === false) {
12418            transition[_.transitionType] = _.transformType + ' ' + _.options.speed + 'ms ' + _.options.cssEase;
12419        } else {
12420            transition[_.transitionType] = 'opacity ' + _.options.speed + 'ms ' + _.options.cssEase;
12421        }
12422
12423        if (_.options.fade === false) {
12424            _.$slideTrack.css(transition);
12425        } else {
12426            _.$slides.eq(slide).css(transition);
12427        }
12428
12429    };
12430
12431    Slick.prototype.autoPlay = function() {
12432
12433        var _ = this;
12434
12435        _.autoPlayClear();
12436
12437        if ( _.slideCount > _.options.slidesToShow ) {
12438            _.autoPlayTimer = setInterval( _.autoPlayIterator, _.options.autoplaySpeed );
12439        }
12440
12441    };
12442
12443    Slick.prototype.autoPlayClear = function() {
12444
12445        var _ = this;
12446
12447        if (_.autoPlayTimer) {
12448            clearInterval(_.autoPlayTimer);
12449        }
12450
12451    };
12452
12453    Slick.prototype.autoPlayIterator = function() {
12454
12455        var _ = this,
12456            slideTo = _.currentSlide + _.options.slidesToScroll;
12457
12458        if ( !_.paused && !_.interrupted && !_.focussed ) {
12459
12460            if ( _.options.infinite === false ) {
12461
12462                if ( _.direction === 1 && ( _.currentSlide + 1 ) === ( _.slideCount - 1 )) {
12463                    _.direction = 0;
12464                }
12465
12466                else if ( _.direction === 0 ) {
12467
12468                    slideTo = _.currentSlide - _.options.slidesToScroll;
12469
12470                    if ( _.currentSlide - 1 === 0 ) {
12471                        _.direction = 1;
12472                    }
12473
12474                }
12475
12476            }
12477
12478            _.slideHandler( slideTo );
12479
12480        }
12481
12482    };
12483
12484    Slick.prototype.buildArrows = function() {
12485
12486        var _ = this;
12487
12488        if (_.options.arrows === true ) {
12489
12490            _.$prevArrow = $(_.options.prevArrow).addClass('slick-arrow');
12491            _.$nextArrow = $(_.options.nextArrow).addClass('slick-arrow');
12492
12493            if( _.slideCount > _.options.slidesToShow ) {
12494
12495                _.$prevArrow.removeClass('slick-hidden').removeAttr('aria-hidden tabindex');
12496                _.$nextArrow.removeClass('slick-hidden').removeAttr('aria-hidden tabindex');
12497
12498                if (_.htmlExpr.test(_.options.prevArrow)) {
12499                    _.$prevArrow.prependTo(_.options.appendArrows);
12500                }
12501
12502                if (_.htmlExpr.test(_.options.nextArrow)) {
12503                    _.$nextArrow.appendTo(_.options.appendArrows);
12504                }
12505
12506                if (_.options.infinite !== true) {
12507                    _.$prevArrow
12508                        .addClass('slick-disabled')
12509                        .attr('aria-disabled', 'true');
12510                }
12511
12512            } else {
12513
12514                _.$prevArrow.add( _.$nextArrow )
12515
12516                    .addClass('slick-hidden')
12517                    .attr({
12518                        'aria-disabled': 'true',
12519                        'tabindex': '-1'
12520                    });
12521
12522            }
12523
12524        }
12525
12526    };
12527
12528    Slick.prototype.buildDots = function() {
12529
12530        var _ = this,
12531            i, dot;
12532
12533        if (_.options.dots === true && _.slideCount > _.options.slidesToShow) {
12534
12535            _.$slider.addClass('slick-dotted');
12536
12537            dot = $('<ul />').addClass(_.options.dotsClass);
12538
12539            for (i = 0; i <= _.getDotCount(); i += 1) {
12540                dot.append($('<li />').append(_.options.customPaging.call(this, _, i)));
12541            }
12542
12543            _.$dots = dot.appendTo(_.options.appendDots);
12544
12545            _.$dots.find('li').first().addClass('slick-active');
12546
12547        }
12548
12549    };
12550
12551    Slick.prototype.buildOut = function() {
12552
12553        var _ = this;
12554
12555        _.$slides =
12556            _.$slider
12557                .children( _.options.slide + ':not(.slick-cloned)')
12558                .addClass('slick-slide');
12559
12560        _.slideCount = _.$slides.length;
12561
12562        _.$slides.each(function(index, element) {
12563            $(element)
12564                .attr('data-slick-index', index)
12565                .data('originalStyling', $(element).attr('style') || '');
12566        });
12567
12568        _.$slider.addClass('slick-slider');
12569
12570        _.$slideTrack = (_.slideCount === 0) ?
12571            $('<div class="slick-track"/>').appendTo(_.$slider) :
12572            _.$slides.wrapAll('<div class="slick-track"/>').parent();
12573
12574        _.$list = _.$slideTrack.wrap(
12575            '<div class="slick-list"/>').parent();
12576        _.$slideTrack.css('opacity', 0);
12577
12578        if (_.options.centerMode === true || _.options.swipeToSlide === true) {
12579            _.options.slidesToScroll = 1;
12580        }
12581
12582        $('img[data-lazy]', _.$slider).not('[src]').addClass('slick-loading');
12583
12584        _.setupInfinite();
12585
12586        _.buildArrows();
12587
12588        _.buildDots();
12589
12590        _.updateDots();
12591
12592
12593        _.setSlideClasses(typeof _.currentSlide === 'number' ? _.currentSlide : 0);
12594
12595        if (_.options.draggable === true) {
12596            _.$list.addClass('draggable');
12597        }
12598
12599    };
12600
12601    Slick.prototype.buildRows = function() {
12602
12603        var _ = this, a, b, c, newSlides, numOfSlides, originalSlides,slidesPerSection;
12604
12605        newSlides = document.createDocumentFragment();
12606        originalSlides = _.$slider.children();
12607
12608        if(_.options.rows > 0) {
12609
12610            slidesPerSection = _.options.slidesPerRow * _.options.rows;
12611            numOfSlides = Math.ceil(
12612                originalSlides.length / slidesPerSection
12613            );
12614
12615            for(a = 0; a < numOfSlides; a++){
12616                var slide = document.createElement('div');
12617                for(b = 0; b < _.options.rows; b++) {
12618                    var row = document.createElement('div');
12619                    for(c = 0; c < _.options.slidesPerRow; c++) {
12620                        var target = (a * slidesPerSection + ((b * _.options.slidesPerRow) + c));
12621                        if (originalSlides.get(target)) {
12622                            row.appendChild(originalSlides.get(target));
12623                        }
12624                    }
12625                    slide.appendChild(row);
12626                }
12627                newSlides.appendChild(slide);
12628            }
12629
12630            _.$slider.empty().append(newSlides);
12631            _.$slider.children().children().children()
12632                .css({
12633                    'width':(100 / _.options.slidesPerRow) + '%',
12634                    'display': 'inline-block'
12635                });
12636
12637        }
12638
12639    };
12640
12641    Slick.prototype.checkResponsive = function(initial, forceUpdate) {
12642
12643        var _ = this,
12644            breakpoint, targetBreakpoint, respondToWidth, triggerBreakpoint = false;
12645        var sliderWidth = _.$slider.width();
12646        var windowWidth = window.innerWidth || $(window).width();
12647
12648        if (_.respondTo === 'window') {
12649            respondToWidth = windowWidth;
12650        } else if (_.respondTo === 'slider') {
12651            respondToWidth = sliderWidth;
12652        } else if (_.respondTo === 'min') {
12653            respondToWidth = Math.min(windowWidth, sliderWidth);
12654        }
12655
12656        if ( _.options.responsive &&
12657            _.options.responsive.length &&
12658            _.options.responsive !== null) {
12659
12660            targetBreakpoint = null;
12661
12662            for (breakpoint in _.breakpoints) {
12663                if (_.breakpoints.hasOwnProperty(breakpoint)) {
12664                    if (_.originalSettings.mobileFirst === false) {
12665                        if (respondToWidth < _.breakpoints[breakpoint]) {
12666                            targetBreakpoint = _.breakpoints[breakpoint];
12667                        }
12668                    } else {
12669                        if (respondToWidth > _.breakpoints[breakpoint]) {
12670                            targetBreakpoint = _.breakpoints[breakpoint];
12671                        }
12672                    }
12673                }
12674            }
12675
12676            if (targetBreakpoint !== null) {
12677                if (_.activeBreakpoint !== null) {
12678                    if (targetBreakpoint !== _.activeBreakpoint || forceUpdate) {
12679                        _.activeBreakpoint =
12680                            targetBreakpoint;
12681                        if (_.breakpointSettings[targetBreakpoint] === 'unslick') {
12682                            _.unslick(targetBreakpoint);
12683                        } else {
12684                            _.options = $.extend({}, _.originalSettings,
12685                                _.breakpointSettings[
12686                                    targetBreakpoint]);
12687                            if (initial === true) {
12688                                _.currentSlide = _.options.initialSlide;
12689                            }
12690                            _.refresh(initial);
12691                        }
12692                        triggerBreakpoint = targetBreakpoint;
12693                    }
12694                } else {
12695                    _.activeBreakpoint = targetBreakpoint;
12696                    if (_.breakpointSettings[targetBreakpoint] === 'unslick') {
12697                        _.unslick(targetBreakpoint);
12698                    } else {
12699                        _.options = $.extend({}, _.originalSettings,
12700                            _.breakpointSettings[
12701                                targetBreakpoint]);
12702                        if (initial === true) {
12703                            _.currentSlide = _.options.initialSlide;
12704                        }
12705                        _.refresh(initial);
12706                    }
12707                    triggerBreakpoint = targetBreakpoint;
12708                }
12709            } else {
12710                if (_.activeBreakpoint !== null) {
12711                    _.activeBreakpoint = null;
12712                    _.options = _.originalSettings;
12713                    if (initial === true) {
12714                        _.currentSlide = _.options.initialSlide;
12715                    }
12716                    _.refresh(initial);
12717                    triggerBreakpoint = targetBreakpoint;
12718                }
12719            }
12720
12721            // only trigger breakpoints during an actual break. not on initialize.
12722            if( !initial && triggerBreakpoint !== false ) {
12723                _.$slider.trigger('breakpoint', [_, triggerBreakpoint]);
12724            }
12725        }
12726
12727    };
12728
12729    Slick.prototype.changeSlide = function(event, dontAnimate) {
12730
12731        var _ = this,
12732            $target = $(event.currentTarget),
12733            indexOffset, slideOffset, unevenOffset;
12734
12735        // If target is a link, prevent default action.
12736        if($target.is('a')) {
12737            event.preventDefault();
12738        }
12739
12740        // If target is not the <li> element (ie: a child), find the <li>.
12741        if(!$target.is('li')) {
12742            $target = $target.closest('li');
12743        }
12744
12745        unevenOffset = (_.slideCount % _.options.slidesToScroll !== 0);
12746        indexOffset = unevenOffset ? 0 : (_.slideCount - _.currentSlide) % _.options.slidesToScroll;
12747
12748        switch (event.data.message) {
12749
12750            case 'previous':
12751                slideOffset = indexOffset === 0 ? _.options.slidesToScroll : _.options.slidesToShow - indexOffset;
12752                if (_.slideCount > _.options.slidesToShow) {
12753                    _.slideHandler(_.currentSlide - slideOffset, false, dontAnimate);
12754                }
12755                break;
12756
12757            case 'next':
12758                slideOffset = indexOffset === 0 ? _.options.slidesToScroll : indexOffset;
12759                if (_.slideCount > _.options.slidesToShow) {
12760                    _.slideHandler(_.currentSlide + slideOffset, false, dontAnimate);
12761                }
12762                break;
12763
12764            case 'index':
12765                var index = event.data.index === 0 ? 0 :
12766                    event.data.index || $target.index() * _.options.slidesToScroll;
12767
12768                _.slideHandler(_.checkNavigable(index), false, dontAnimate);
12769                $target.children().trigger('focus');
12770                break;
12771
12772            default:
12773                return;
12774        }
12775
12776    };
12777
12778    Slick.prototype.checkNavigable = function(index) {
12779
12780        var _ = this,
12781            navigables, prevNavigable;
12782
12783        navigables = _.getNavigableIndexes();
12784        prevNavigable = 0;
12785        if (index > navigables[navigables.length - 1]) {
12786            index = navigables[navigables.length - 1];
12787        } else {
12788            for (var n in navigables) {
12789                if (index < navigables[n]) {
12790                    index = prevNavigable;
12791                    break;
12792                }
12793                prevNavigable = navigables[n];
12794            }
12795        }
12796
12797        return index;
12798    };
12799
12800    Slick.prototype.cleanUpEvents = function() {
12801
12802        var _ = this;
12803
12804        if (_.options.dots && _.$dots !== null) {
12805
12806            $('li', _.$dots)
12807                .off('click.slick', _.changeSlide)
12808                .off('mouseenter.slick', $.proxy(_.interrupt, _, true))
12809                .off('mouseleave.slick', $.proxy(_.interrupt, _, false));
12810
12811            if (_.options.accessibility === true) {
12812                _.$dots.off('keydown.slick', _.keyHandler);
12813            }
12814        }
12815
12816        _.$slider.off('focus.slick blur.slick');
12817
12818        if (_.options.arrows === true && _.slideCount > _.options.slidesToShow) {
12819            _.$prevArrow && _.$prevArrow.off('click.slick', _.changeSlide);
12820            _.$nextArrow && _.$nextArrow.off('click.slick', _.changeSlide);
12821
12822            if (_.options.accessibility === true) {
12823                _.$prevArrow && _.$prevArrow.off('keydown.slick', _.keyHandler);
12824                _.$nextArrow && _.$nextArrow.off('keydown.slick', _.keyHandler);
12825            }
12826        }
12827
12828        _.$list.off('touchstart.slick mousedown.slick', _.swipeHandler);
12829        _.$list.off('touchmove.slick mousemove.slick', _.swipeHandler);
12830        _.$list.off('touchend.slick mouseup.slick', _.swipeHandler);
12831        _.$list.off('touchcancel.slick mouseleave.slick', _.swipeHandler);
12832
12833        _.$list.off('click.slick', _.clickHandler);
12834
12835        $(document).off(_.visibilityChange, _.visibility);
12836
12837        _.cleanUpSlideEvents();
12838
12839        if (_.options.accessibility === true) {
12840            _.$list.off('keydown.slick', _.keyHandler);
12841        }
12842
12843        if (_.options.focusOnSelect === true) {
12844            $(_.$slideTrack).children().off('click.slick', _.selectHandler);
12845        }
12846
12847        $(window).off('orientationchange.slick.slick-' + _.instanceUid, _.orientationChange);
12848
12849        $(window).off('resize.slick.slick-' + _.instanceUid, _.resize);
12850
12851        $('[draggable!=true]', _.$slideTrack).off('dragstart', _.preventDefault);
12852
12853        $(window).off('load.slick.slick-' + _.instanceUid, _.setPosition);
12854
12855    };
12856
12857    Slick.prototype.cleanUpSlideEvents = function() {
12858
12859        var _ = this;
12860
12861        _.$list.off('mouseenter.slick', $.proxy(_.interrupt, _, true));
12862        _.$list.off('mouseleave.slick', $.proxy(_.interrupt, _, false));
12863
12864    };
12865
12866    Slick.prototype.cleanUpRows = function() {
12867
12868        var _ = this, originalSlides;
12869
12870        if(_.options.rows > 0) {
12871            originalSlides = _.$slides.children().children();
12872            originalSlides.removeAttr('style');
12873            _.$slider.empty().append(originalSlides);
12874        }
12875
12876    };
12877
12878    Slick.prototype.clickHandler = function(event) {
12879
12880        var _ = this;
12881
12882        if (_.shouldClick === false) {
12883            event.stopImmediatePropagation();
12884            event.stopPropagation();
12885            event.preventDefault();
12886        }
12887
12888    };
12889
12890    Slick.prototype.destroy = function(refresh) {
12891
12892        var _ = this;
12893
12894        _.autoPlayClear();
12895
12896        _.touchObject = {};
12897
12898        _.cleanUpEvents();
12899
12900        $('.slick-cloned', _.$slider).detach();
12901
12902        if (_.$dots) {
12903            _.$dots.remove();
12904        }
12905
12906        if ( _.$prevArrow && _.$prevArrow.length ) {
12907
12908            _.$prevArrow
12909                .removeClass('slick-disabled slick-arrow slick-hidden')
12910                .removeAttr('aria-hidden aria-disabled tabindex')
12911                .css('display','');
12912
12913            if ( _.htmlExpr.test( _.options.prevArrow )) {
12914                _.$prevArrow.remove();
12915            }
12916        }
12917
12918        if ( _.$nextArrow && _.$nextArrow.length ) {
12919
12920            _.$nextArrow
12921                .removeClass('slick-disabled slick-arrow slick-hidden')
12922                .removeAttr('aria-hidden aria-disabled tabindex')
12923                .css('display','');
12924
12925            if ( _.htmlExpr.test( _.options.nextArrow )) {
12926                _.$nextArrow.remove();
12927            }
12928        }
12929
12930
12931        if (_.$slides) {
12932
12933            _.$slides
12934                .removeClass('slick-slide slick-active slick-center slick-visible slick-current')
12935                .removeAttr('aria-hidden')
12936                .removeAttr('data-slick-index')
12937                .each(function(){
12938                    $(this).attr('style', $(this).data('originalStyling'));
12939                });
12940
12941            _.$slideTrack.children(this.options.slide).detach();
12942
12943            _.$slideTrack.detach();
12944
12945            _.$list.detach();
12946
12947            _.$slider.append(_.$slides);
12948        }
12949
12950        _.cleanUpRows();
12951
12952        _.$slider.removeClass('slick-slider');
12953        _.$slider.removeClass('slick-initialized');
12954        _.$slider.removeClass('slick-dotted');
12955
12956        _.unslicked = true;
12957
12958        if(!refresh) {
12959            _.$slider.trigger('destroy', [_]);
12960        }
12961
12962    };
12963
12964    Slick.prototype.disableTransition = function(slide) {
12965
12966        var _ = this,
12967            transition = {};
12968
12969        transition[_.transitionType] = '';
12970
12971        if (_.options.fade === false) {
12972            _.$slideTrack.css(transition);
12973        } else {
12974            _.$slides.eq(slide).css(transition);
12975        }
12976
12977    };
12978
12979    Slick.prototype.fadeSlide = function(slideIndex, callback) {
12980
12981        var _ = this;
12982
12983        if (_.cssTransitions === false) {
12984
12985            _.$slides.eq(slideIndex).css({
12986                zIndex: _.options.zIndex
12987            });
12988
12989            _.$slides.eq(slideIndex).animate({
12990                opacity: 1
12991            }, _.options.speed, _.options.easing, callback);
12992
12993        } else {
12994
12995            _.applyTransition(slideIndex);
12996
12997            _.$slides.eq(slideIndex).css({
12998                opacity: 1,
12999                zIndex: _.options.zIndex
13000            });
13001
13002            if (callback) {
13003                setTimeout(function() {
13004
13005                    _.disableTransition(slideIndex);
13006
13007                    callback.call();
13008                }, _.options.speed);
13009            }
13010
13011        }
13012
13013    };
13014
13015    Slick.prototype.fadeSlideOut = function(slideIndex) {
13016
13017        var _ = this;
13018
13019        if (_.cssTransitions === false) {
13020
13021            _.$slides.eq(slideIndex).animate({
13022                opacity: 0,
13023                zIndex: _.options.zIndex - 2
13024            }, _.options.speed, _.options.easing);
13025
13026        } else {
13027
13028            _.applyTransition(slideIndex);
13029
13030            _.$slides.eq(slideIndex).css({
13031                opacity: 0,
13032                zIndex: _.options.zIndex - 2
13033            });
13034
13035        }
13036
13037    };
13038
13039    Slick.prototype.filterSlides = Slick.prototype.slickFilter = function(filter) {
13040
13041        var _ = this;
13042
13043        if (filter !== null) {
13044
13045            _.$slidesCache = _.$slides;
13046
13047            _.unload();
13048
13049            _.$slideTrack.children(this.options.slide).detach();
13050
13051            _.$slidesCache.filter(filter).appendTo(_.$slideTrack);
13052
13053            _.reinit();
13054
13055        }
13056
13057    };
13058
13059    Slick.prototype.focusHandler = function() {
13060
13061        var _ = this;
13062
13063        _.$slider
13064            .off('focus.slick blur.slick')
13065            .on('focus.slick blur.slick', '*', function(event) {
13066
13067            event.stopImmediatePropagation();
13068            var $sf = $(this);
13069
13070            setTimeout(function() {
13071
13072                if( _.options.pauseOnFocus ) {
13073                    _.focussed = $sf.is(':focus');
13074                    _.autoPlay();
13075                }
13076
13077            }, 0);
13078
13079        });
13080    };
13081
13082    Slick.prototype.getCurrent = Slick.prototype.slickCurrentSlide = function() {
13083
13084        var _ = this;
13085        return _.currentSlide;
13086
13087    };
13088
13089    Slick.prototype.getDotCount = function() {
13090
13091        var _ = this;
13092
13093        var breakPoint = 0;
13094        var counter = 0;
13095        var pagerQty = 0;
13096
13097        if (_.options.infinite === true) {
13098            if (_.slideCount <= _.options.slidesToShow) {
13099                 ++pagerQty;
13100            } else {
13101                while (breakPoint < _.slideCount) {
13102                    ++pagerQty;
13103                    breakPoint = counter + _.options.slidesToScroll;
13104                    counter += _.options.slidesToScroll <= _.options.slidesToShow ? _.options.slidesToScroll : _.options.slidesToShow;
13105                }
13106            }
13107        } else if (_.options.centerMode === true) {
13108            pagerQty = _.slideCount;
13109        } else if(!_.options.asNavFor) {
13110            pagerQty = 1 + Math.ceil((_.slideCount - _.options.slidesToShow) / _.options.slidesToScroll);
13111        }else {
13112            while (breakPoint < _.slideCount) {
13113                ++pagerQty;
13114                breakPoint = counter + _.options.slidesToScroll;
13115                counter += _.options.slidesToScroll <= _.options.slidesToShow ? _.options.slidesToScroll : _.options.slidesToShow;
13116            }
13117        }
13118
13119        return pagerQty - 1;
13120
13121    };
13122
13123    Slick.prototype.getLeft = function(slideIndex) {
13124
13125        var _ = this,
13126            targetLeft,
13127            verticalHeight,
13128            verticalOffset = 0,
13129            targetSlide,
13130            coef;
13131
13132        _.slideOffset = 0;
13133        verticalHeight = _.$slides.first().outerHeight(true);
13134
13135        if (_.options.infinite === true) {
13136            if (_.slideCount > _.options.slidesToShow) {
13137                _.slideOffset = (_.slideWidth * _.options.slidesToShow) * -1;
13138                coef = -1
13138
13139
13140                if (_.options.vertical === true && _.options.centerMode === true) {
13141                    if (_.options.slidesToShow === 2) {
13142                        coef = -1.5;
13143                    } else if (_.options.slidesToShow === 1) {
13144                        coef = -2
vendor: 47,517 bytes, lines 13144-14747
13144
13145                    }
13146                }
13147                verticalOffset = (verticalHeight * _.options.slidesToShow) * coef;
13148            }
13149            if (_.slideCount % _.options.slidesToScroll !== 0) {
13150                if (slideIndex + _.options.slidesToScroll > _.slideCount && _.slideCount > _.options.slidesToShow) {
13151                    if (slideIndex > _.slideCount) {
13152                        _.slideOffset = ((_.options.slidesToShow - (slideIndex - _.slideCount)) * _.slideWidth) * -1;
13153                        verticalOffset = ((_.options.slidesToShow - (slideIndex - _.slideCount)) * verticalHeight) * -1;
13154                    } else {
13155                        _.slideOffset = ((_.slideCount % _.options.slidesToScroll) * _.slideWidth) * -1;
13156                        verticalOffset = ((_.slideCount % _.options.slidesToScroll) * verticalHeight) * -1;
13157                    }
13158                }
13159            }
13160        } else {
13161            if (slideIndex + _.options.slidesToShow > _.slideCount) {
13162                _.slideOffset = ((slideIndex + _.options.slidesToShow) - _.slideCount) * _.slideWidth;
13163                verticalOffset = ((slideIndex + _.options.slidesToShow) - _.slideCount) * verticalHeight;
13164            }
13165        }
13166
13167        if (_.slideCount <= _.options.slidesToShow) {
13168            _.slideOffset = 0;
13169            verticalOffset = 0;
13170        }
13171
13172        if (_.options.centerMode === true && _.slideCount <= _.options.slidesToShow) {
13173            _.slideOffset = ((_.slideWidth * Math.floor(_.options.slidesToShow)) / 2) - ((_.slideWidth * _.slideCount) / 2);
13174        } else if (_.options.centerMode === true && _.options.infinite === true) {
13175            _.slideOffset += _.slideWidth * Math.floor(_.options.slidesToShow / 2) - _.slideWidth;
13176        } else if (_.options.centerMode === true) {
13177            _.slideOffset = 0;
13178            _.slideOffset += _.slideWidth * Math.floor(_.options.slidesToShow / 2);
13179        }
13180
13181        if (_.options.vertical === false) {
13182            targetLeft = ((slideIndex * _.slideWidth) * -1) + _.slideOffset;
13183        } else {
13184            targetLeft = ((slideIndex * verticalHeight) * -1) + verticalOffset;
13185        }
13186
13187        if (_.options.variableWidth === true) {
13188
13189            if (_.slideCount <= _.options.slidesToShow || _.options.infinite === false) {
13190                targetSlide = _.$slideTrack.children('.slick-slide').eq(slideIndex);
13191            } else {
13192                targetSlide = _.$slideTrack.children('.slick-slide').eq(slideIndex + _.options.slidesToShow);
13193            }
13194
13195            if (_.options.rtl === true) {
13196                if (targetSlide[0]) {
13197                    targetLeft = (_.$slideTrack.width() - targetSlide[0].offsetLeft - targetSlide.width()) * -1;
13198                } else {
13199                    targetLeft =  0;
13200                }
13201            } else {
13202                targetLeft = targetSlide[0] ? targetSlide[0].offsetLeft * -1 : 0;
13203            }
13204
13205            if (_.options.centerMode === true) {
13206                if (_.slideCount <= _.options.slidesToShow || _.options.infinite === false) {
13207                    targetSlide = _.$slideTrack.children('.slick-slide').eq(slideIndex);
13208                } else {
13209                    targetSlide = _.$slideTrack.children('.slick-slide').eq(slideIndex + _.options.slidesToShow + 1);
13210                }
13211
13212                if (_.options.rtl === true) {
13213                    if (targetSlide[0]) {
13214                        targetLeft = (_.$slideTrack.width() - targetSlide[0].offsetLeft - targetSlide.width()) * -1;
13215                    } else {
13216                        targetLeft =  0;
13217                    }
13218                } else {
13219                    targetLeft = targetSlide[0] ? targetSlide[0].offsetLeft * -1 : 0;
13220                }
13221
13222                targetLeft += (_.$list.width() - targetSlide.outerWidth()) / 2;
13223            }
13224        }
13225
13226        return targetLeft;
13227
13228    };
13229
13230    Slick.prototype.getOption = Slick.prototype.slickGetOption = function(option) {
13231
13232        var _ = this;
13233
13234        return _.options[option];
13235
13236    };
13237
13238    Slick.prototype.getNavigableIndexes = function() {
13239
13240        var _ = this,
13241            breakPoint = 0,
13242            counter = 0,
13243            indexes = [],
13244            max;
13245
13246        if (_.options.infinite === false) {
13247            max = _.slideCount;
13248        } else {
13249            breakPoint = _.options.slidesToScroll * -1;
13250            counter = _.options.slidesToScroll * -1;
13251            max = _.slideCount * 2;
13252        }
13253
13254        while (breakPoint < max) {
13255            indexes.push(breakPoint);
13256            breakPoint = counter + _.options.slidesToScroll;
13257            counter += _.options.slidesToScroll <= _.options.slidesToShow ? _.options.slidesToScroll : _.options.slidesToShow;
13258        }
13259
13260        return indexes;
13261
13262    };
13263
13264    Slick.prototype.getSlick = function() {
13265
13266        return this;
13267
13268    };
13269
13270    Slick.prototype.getSlideCount = function() {
13271
13272        var _ = this,
13273            slidesTraversed, swipedSlide, centerOffset;
13274
13275        centerOffset = _.options.centerMode === true ? _.slideWidth * Math.floor(_.options.slidesToShow / 2) : 0;
13276
13277        if (_.options.swipeToSlide === true) {
13278            _.$slideTrack.find('.slick-slide').each(function(index, slide) {
13279                if (slide.offsetLeft - centerOffset + ($(slide).outerWidth() / 2) > (_.swipeLeft * -1)) {
13280                    swipedSlide = slide;
13281                    return false;
13282                }
13283            });
13284
13285            slidesTraversed = Math.abs($(swipedSlide).attr('data-slick-index') - _.currentSlide) || 1;
13286
13287            return slidesTraversed;
13288
13289        } else {
13290            return _.options.slidesToScroll;
13291        }
13292
13293    };
13294
13295    Slick.prototype.goTo = Slick.prototype.slickGoTo = function(slide, dontAnimate) {
13296
13297        var _ = this;
13298
13299        _.changeSlide({
13300            data: {
13301                message: 'index',
13302                index: parseInt(slide)
13303            }
13304        }, dontAnimate);
13305
13306    };
13307
13308    Slick.prototype.init = function(creation) {
13309
13310        var _ = this;
13311
13312        if (!$(_.$slider).hasClass('slick-initialized')) {
13313
13314            $(_.$slider).addClass('slick-initialized');
13315
13316            _.buildRows();
13317            _.buildOut();
13318            _.setProps();
13319            _.startLoad();
13320            _.loadSlider();
13321            _.initializeEvents();
13322            _.updateArrows();
13323            _.updateDots();
13324            _.checkResponsive(true);
13325            _.focusHandler();
13326
13327        }
13328
13329        if (creation) {
13330            _.$slider.trigger('init', [_]);
13331        }
13332
13333        if (_.options.accessibility === true) {
13334            _.initADA();
13335        }
13336
13337        if ( _.options.autoplay ) {
13338
13339            _.paused = false;
13340            _.autoPlay();
13341
13342        }
13343
13344    };
13345
13346    Slick.prototype.initADA = function() {
13347        var _ = this,
13348                numDotGroups = Math.ceil(_.slideCount / _.options.slidesToShow),
13349                tabControlIndexes = _.getNavigableIndexes().filter(function(val) {
13350                    return (val >= 0) && (val < _.slideCount);
13351                });
13352
13353        _.$slides.add(_.$slideTrack.find('.slick-cloned')).attr({
13354            'aria-hidden': 'true',
13355            'tabindex': '-1'
13356        }).find('a, input, button, select').attr({
13357            'tabindex': '-1'
13358        });
13359
13360        if (_.$dots !== null) {
13361            _.$slides.not(_.$slideTrack.find('.slick-cloned')).each(function(i) {
13362                var slideControlIndex = tabControlIndexes.indexOf(i);
13363
13364                $(this).attr({
13365                    'role': 'tabpanel',
13366                    'id': 'slick-slide' + _.instanceUid + i,
13367                    'tabindex': -1
13368                });
13369
13370                if (slideControlIndex !== -1) {
13371                   var ariaButtonControl = 'slick-slide-control' + _.instanceUid + slideControlIndex
13372                   if ($('#' + ariaButtonControl).length) {
13373                     $(this).attr({
13374                         'aria-describedby': ariaButtonControl
13375                     });
13376                   }
13377                }
13378            });
13379
13380            _.$dots.attr('role', 'tablist').find('li').each(function(i) {
13381                var mappedSlideIndex = tabControlIndexes[i];
13382
13383                $(this).attr({
13384                    'role': 'presentation'
13385                });
13386
13387                $(this).find('button').first().attr({
13388                    'role': 'tab',
13389                    'id': 'slick-slide-control' + _.instanceUid + i,
13390                    'aria-controls': 'slick-slide' + _.instanceUid + mappedSlideIndex,
13391                    'aria-label': (i + 1) + ' of ' + numDotGroups,
13392                    'aria-selected': null,
13393                    'tabindex': '-1'
13394                });
13395
13396            }).eq(_.currentSlide).find('button').attr({
13397                'aria-selected': 'true',
13398                'tabindex': '0'
13399            }).end();
13400        }
13401
13402        for (var i=_.currentSlide, max=i+_.options.slidesToShow; i < max; i++) {
13403          if (_.options.focusOnChange) {
13404            _.$slides.eq(i).attr({'tabindex': '0'});
13405          } else {
13406            _.$slides.eq(i).removeAttr('tabindex');
13407          }
13408        }
13409
13410        _.activateADA();
13411
13412    };
13413
13414    Slick.prototype.initArrowEvents = function() {
13415
13416        var _ = this;
13417
13418        if (_.options.arrows === true && _.slideCount > _.options.slidesToShow) {
13419            _.$prevArrow
13420               .off('click.slick')
13421               .on('click.slick', {
13422                    message: 'previous'
13423               }, _.changeSlide);
13424            _.$nextArrow
13425               .off('click.slick')
13426               .on('click.slick', {
13427                    message: 'next'
13428               }, _.changeSlide);
13429
13430            if (_.options.accessibility === true) {
13431                _.$prevArrow.on('keydown.slick', _.keyHandler);
13432                _.$nextArrow.on('keydown.slick', _.keyHandler);
13433            }
13434        }
13435
13436    };
13437
13438    Slick.prototype.initDotEvents = function() {
13439
13440        var _ = this;
13441
13442        if (_.options.dots === true && _.slideCount > _.options.slidesToShow) {
13443            $('li', _.$dots).on('click.slick', {
13444                message: 'index'
13445            }, _.changeSlide);
13446
13447            if (_.options.accessibility === true) {
13448                _.$dots.on('keydown.slick', _.keyHandler);
13449            }
13450        }
13451
13452        if (_.options.dots === true && _.options.pauseOnDotsHover === true && _.slideCount > _.options.slidesToShow) {
13453
13454            $('li', _.$dots)
13455                .on('mouseenter.slick', $.proxy(_.interrupt, _, true))
13456                .on('mouseleave.slick', $.proxy(_.interrupt, _, false));
13457
13458        }
13459
13460    };
13461
13462    Slick.prototype.initSlideEvents = function() {
13463
13464        var _ = this;
13465
13466        if ( _.options.pauseOnHover ) {
13467
13468            _.$list.on('mouseenter.slick', $.proxy(_.interrupt, _, true));
13469            _.$list.on('mouseleave.slick', $.proxy(_.interrupt, _, false));
13470
13471        }
13472
13473    };
13474
13475    Slick.prototype.initializeEvents = function() {
13476
13477        var _ = this;
13478
13479        _.initArrowEvents();
13480
13481        _.initDotEvents();
13482        _.initSlideEvents();
13483
13484        _.$list.on('touchstart.slick mousedown.slick', {
13485            action: 'start'
13486        }, _.swipeHandler);
13487        _.$list.on('touchmove.slick mousemove.slick', {
13488            action: 'move'
13489        }, _.swipeHandler);
13490        _.$list.on('touchend.slick mouseup.slick', {
13491            action: 'end'
13492        }, _.swipeHandler);
13493        _.$list.on('touchcancel.slick mouseleave.slick', {
13494            action: 'end'
13495        }, _.swipeHandler);
13496
13497        _.$list.on('click.slick', _.clickHandler);
13498
13499        $(document).on(_.visibilityChange, $.proxy(_.visibility, _));
13500
13501        if (_.options.accessibility === true) {
13502            _.$list.on('keydown.slick', _.keyHandler);
13503        }
13504
13505        if (_.options.focusOnSelect === true) {
13506            $(_.$slideTrack).children().on('click.slick', _.selectHandler);
13507        }
13508
13509        $(window).on('orientationchange.slick.slick-' + _.instanceUid, $.proxy(_.orientationChange, _));
13510
13511        $(window).on('resize.slick.slick-' + _.instanceUid, $.proxy(_.resize, _));
13512
13513        $('[draggable!=true]', _.$slideTrack).on('dragstart', _.preventDefault);
13514
13515        $(window).on('load.slick.slick-' + _.instanceUid, _.setPosition);
13516        $(_.setPosition);
13517
13518    };
13519
13520    Slick.prototype.initUI = function() {
13521
13522        var _ = this;
13523
13524        if (_.options.arrows === true && _.slideCount > _.options.slidesToShow) {
13525
13526            _.$prevArrow.show();
13527            _.$nextArrow.show();
13528
13529        }
13530
13531        if (_.options.dots === true && _.slideCount > _.options.slidesToShow) {
13532
13533            _.$dots.show();
13534
13535        }
13536
13537    };
13538
13539    Slick.prototype.keyHandler = function(event) {
13540
13541        var _ = this;
13542         //Dont slide if the cursor is inside the form fields and arrow keys are pressed
13543        if(!event.target.tagName.match('TEXTAREA|INPUT|SELECT')) {
13544            if (event.keyCode === 37 && _.options.accessibility === true) {
13545                _.changeSlide({
13546                    data: {
13547                        message: _.options.rtl === true ? 'next' :  'previous'
13548                    }
13549                });
13550            } else if (event.keyCode === 39 && _.options.accessibility === true) {
13551                _.changeSlide({
13552                    data: {
13553                        message: _.options.rtl === true ? 'previous' : 'next'
13554                    }
13555                });
13556            }
13557        }
13558
13559    };
13560
13561    Slick.prototype.lazyLoad = function() {
13562
13563        var _ = this,
13564            loadRange, cloneRange, rangeStart, rangeEnd;
13565
13566        function loadImages(imagesScope) {
13567
13568            $('img[data-lazy]', imagesScope).each(function() {
13569
13570                var image = $(this),
13571                    imageSource = $(this).attr('data-lazy'),
13572                    imageSrcSet = $(this).attr('data-srcset'),
13573                    imageSizes  = $(this).attr('data-sizes') || _.$slider.attr('data-sizes'),
13574                    imageToLoad = document.createElement('img');
13575
13576                imageToLoad.onload = function() {
13577
13578                    image
13579                        .animate({ opacity: 0 }, 100, function() {
13580
13581                            if (imageSrcSet) {
13582                                image
13583                                    .attr('srcset', imageSrcSet );
13584
13585                                if (imageSizes) {
13586                                    image
13587                                        .attr('sizes', imageSizes );
13588                                }
13589                            }
13590
13591                            image
13592                                .attr('src', imageSource)
13593                                .animate({ opacity: 1 }, 200, function() {
13594                                    image
13595                                        .removeAttr('data-lazy data-srcset data-sizes')
13596                                        .removeClass('slick-loading');
13597                                });
13598                            _.$slider.trigger('lazyLoaded', [_, image, imageSource]);
13599                        });
13600
13601                };
13602
13603                imageToLoad.onerror = function() {
13604
13605                    image
13606                        .removeAttr( 'data-lazy' )
13607                        .removeClass( 'slick-loading' )
13608                        .addClass( 'slick-lazyload-error' );
13609
13610                    _.$slider.trigger('lazyLoadError', [ _, image, imageSource ]);
13611
13612                };
13613
13614                imageToLoad.src = imageSource;
13615
13616            });
13617
13618        }
13619
13620        if (_.options.centerMode === true) {
13621            if (_.options.infinite === true) {
13622                rangeStart = _.currentSlide + (_.options.slidesToShow / 2 + 1);
13623                rangeEnd = rangeStart + _.options.slidesToShow + 2;
13624            } else {
13625                rangeStart = Math.max(0, _.currentSlide - (_.options.slidesToShow / 2 + 1));
13626                rangeEnd = 2 + (_.options.slidesToShow / 2 + 1) + _.currentSlide;
13627            }
13628        } else {
13629            rangeStart = _.options.infinite ? _.options.slidesToShow + _.currentSlide : _.currentSlide;
13630            rangeEnd = Math.ceil(rangeStart + _.options.slidesToShow);
13631            if (_.options.fade === true) {
13632                if (rangeStart > 0) rangeStart--;
13633                if (rangeEnd <= _.slideCount) rangeEnd++;
13634            }
13635        }
13636
13637        loadRange = _.$slider.find('.slick-slide').slice(rangeStart, rangeEnd);
13638
13639        if (_.options.lazyLoad === 'anticipated') {
13640            var prevSlide = rangeStart - 1,
13641                nextSlide = rangeEnd,
13642                $slides = _.$slider.find('.slick-slide');
13643
13644            for (var i = 0; i < _.options.slidesToScroll; i++) {
13645                if (prevSlide < 0) prevSlide = _.slideCount - 1;
13646                loadRange = loadRange.add($slides.eq(prevSlide));
13647                loadRange = loadRange.add($slides.eq(nextSlide));
13648                prevSlide--;
13649                nextSlide++;
13650            }
13651        }
13652
13653        loadImages(loadRange);
13654
13655        if (_.slideCount <= _.options.slidesToShow) {
13656            cloneRange = _.$slider.find('.slick-slide');
13657            loadImages(cloneRange);
13658        } else
13659        if (_.currentSlide >= _.slideCount - _.options.slidesToShow) {
13660            cloneRange = _.$slider.find('.slick-cloned').slice(0, _.options.slidesToShow);
13661            loadImages(cloneRange);
13662        } else if (_.currentSlide === 0) {
13663            cloneRange = _.$slider.find('.slick-cloned').slice(_.options.slidesToShow * -1);
13664            loadImages(cloneRange);
13665        }
13666
13667    };
13668
13669    Slick.prototype.loadSlider = function() {
13670
13671        var _ = this;
13672
13673        _.setPosition();
13674
13675        _.$slideTrack.css({
13676            opacity: 1
13677        });
13678
13679        _.$slider.removeClass('slick-loading');
13680
13681        _.initUI();
13682
13683        if (_.options.lazyLoad === 'progressive') {
13684            _.progressiveLazyLoad();
13685        }
13686
13687    };
13688
13689    Slick.prototype.next = Slick.prototype.slickNext = function() {
13690
13691        var _ = this;
13692
13693        _.changeSlide({
13694            data: {
13695                message: 'next'
13696            }
13697        });
13698
13699    };
13700
13701    Slick.prototype.orientationChange = function() {
13702
13703        var _ = this;
13704
13705        _.checkResponsive();
13706        _.setPosition();
13707
13708    };
13709
13710    Slick.prototype.pause = Slick.prototype.slickPause = function() {
13711
13712        var _ = this;
13713
13714        _.autoPlayClear();
13715        _.paused = true;
13716
13717    };
13718
13719    Slick.prototype.play = Slick.prototype.slickPlay = function() {
13720
13721        var _ = this;
13722
13723        _.autoPlay();
13724        _.options.autoplay = true;
13725        _.paused = false;
13726        _.focussed = false;
13727        _.interrupted = false;
13728
13729    };
13730
13731    Slick.prototype.postSlide = function(index) {
13732
13733        var _ = this;
13734
13735        if( !_.unslicked ) {
13736
13737            _.$slider.trigger('afterChange', [_, index]);
13738
13739            _.animating = false;
13740
13741            if (_.slideCount > _.options.slidesToShow) {
13742                _.setPosition();
13743            }
13744
13745            _.swipeLeft = null;
13746
13747            if ( _.options.autoplay ) {
13748                _.autoPlay();
13749            }
13750
13751            if (_.options.accessibility === true) {
13752                _.initADA();
13753
13754                if (_.options.focusOnChange) {
13755                    var $currentSlide = $(_.$slides.get(_.currentSlide));
13756                    $currentSlide.attr('tabindex', 0).focus();
13757                }
13758            }
13759
13760        }
13761
13762    };
13763
13764    Slick.prototype.prev = Slick.prototype.slickPrev = function() {
13765
13766        var _ = this;
13767
13768        _.changeSlide({
13769            data: {
13770                message: 'previous'
13771            }
13772        });
13773
13774    };
13775
13776    Slick.prototype.preventDefault = function(event) {
13777
13778        event.preventDefault();
13779
13780    };
13781
13782    Slick.prototype.progressiveLazyLoad = function( tryCount ) {
13783
13784        tryCount = tryCount || 1;
13785
13786        var _ = this,
13787            $imgsToLoad = $( 'img[data-lazy]', _.$slider ),
13788            image,
13789            imageSource,
13790            imageSrcSet,
13791            imageSizes,
13792            imageToLoad;
13793
13794        if ( $imgsToLoad.length ) {
13795
13796            image = $imgsToLoad.first();
13797            imageSource = image.attr('data-lazy');
13798            imageSrcSet = image.attr('data-srcset');
13799            imageSizes  = image.attr('data-sizes') || _.$slider.attr('data-sizes');
13800            imageToLoad = document.createElement('img');
13801
13802            imageToLoad.onload = function() {
13803
13804                if (imageSrcSet) {
13805                    image
13806                        .attr('srcset', imageSrcSet );
13807
13808                    if (imageSizes) {
13809                        image
13810                            .attr('sizes', imageSizes );
13811                    }
13812                }
13813
13814                image
13815                    .attr( 'src', imageSource )
13816                    .removeAttr('data-lazy data-srcset data-sizes')
13817                    .removeClass('slick-loading');
13818
13819                if ( _.options.adaptiveHeight === true ) {
13820                    _.setPosition();
13821                }
13822
13823                _.$slider.trigger('lazyLoaded', [ _, image, imageSource ]);
13824                _.progressiveLazyLoad();
13825
13826            };
13827
13828            imageToLoad.onerror = function() {
13829
13830                if ( tryCount < 3 ) {
13831
13832                    /**
13833                     * try to load the image 3 times,
13834                     * leave a slight delay so we don't get
13835                     * servers blocking the request.
13836                     */
13837                    setTimeout( function() {
13838                        _.progressiveLazyLoad( tryCount + 1 );
13839                    }, 500 );
13840
13841                } else {
13842
13843                    image
13844                        .removeAttr( 'data-lazy' )
13845                        .removeClass( 'slick-loading' )
13846                        .addClass( 'slick-lazyload-error' );
13847
13848                    _.$slider.trigger('lazyLoadError', [ _, image, imageSource ]);
13849
13850                    _.progressiveLazyLoad();
13851
13852                }
13853
13854            };
13855
13856            imageToLoad.src = imageSource;
13857
13858        } else {
13859
13860            _.$slider.trigger('allImagesLoaded', [ _ ]);
13861
13862        }
13863
13864    };
13865
13866    Slick.prototype.refresh = function( initializing ) {
13867
13868        var _ = this, currentSlide, lastVisibleIndex;
13869
13870        lastVisibleIndex = _.slideCount - _.options.slidesToShow;
13871
13872        // in non-infinite sliders, we don't want to go past the
13873        // last visible index.
13874        if( !_.options.infinite && ( _.currentSlide > lastVisibleIndex )) {
13875            _.currentSlide = lastVisibleIndex;
13876        }
13877
13878        // if less slides than to show, go to start.
13879        if ( _.slideCount <= _.options.slidesToShow ) {
13880            _.currentSlide = 0;
13881
13882        }
13883
13884        currentSlide = _.currentSlide;
13885
13886        _.destroy(true);
13887
13888        $.extend(_, _.initials, { currentSlide: currentSlide });
13889
13890        _.init();
13891
13892        if( !initializing ) {
13893
13894            _.changeSlide({
13895                data: {
13896                    message: 'index',
13897                    index: currentSlide
13898                }
13899            }, false);
13900
13901        }
13902
13903    };
13904
13905    Slick.prototype.registerBreakpoints = function() {
13906
13907        var _ = this, breakpoint, currentBreakpoint, l,
13908            responsiveSettings = _.options.responsive || null;
13909
13910        if ( $.type(responsiveSettings) === 'array' && responsiveSettings.length ) {
13911
13912            _.respondTo = _.options.respondTo || 'window';
13913
13914            for ( breakpoint in responsiveSettings ) {
13915
13916                l = _.breakpoints.length-1;
13917
13918                if (responsiveSettings.hasOwnProperty(breakpoint)) {
13919                    currentBreakpoint = responsiveSettings[breakpoint].breakpoint;
13920
13921                    // loop through the breakpoints and cut out any existing
13922                    // ones with the same breakpoint number, we don't want dupes.
13923                    while( l >= 0 ) {
13924                        if( _.breakpoints[l] && _.breakpoints[l] === currentBreakpoint ) {
13925                            _.breakpoints.splice(l,1);
13926                        }
13927                        l--;
13928                    }
13929
13930                    _.breakpoints.push(currentBreakpoint);
13931                    _.breakpointSettings[currentBreakpoint] = responsiveSettings[breakpoint].settings;
13932
13933                }
13934
13935            }
13936
13937            _.breakpoints.sort(function(a, b) {
13938                return ( _.options.mobileFirst ) ? a-b : b-a;
13939            });
13940
13941        }
13942
13943    };
13944
13945    Slick.prototype.reinit = function() {
13946
13947        var _ = this;
13948
13949        _.$slides =
13950            _.$slideTrack
13951                .children(_.options.slide)
13952                .addClass('slick-slide');
13953
13954        _.slideCount = _.$slides.length;
13955
13956        if (_.currentSlide >= _.slideCount && _.currentSlide !== 0) {
13957            _.currentSlide = _.currentSlide - _.options.slidesToScroll;
13958        }
13959
13960        if (_.slideCount <= _.options.slidesToShow) {
13961            _.currentSlide = 0;
13962        }
13963
13964        _.registerBreakpoints();
13965
13966        _.setProps();
13967        _.setupInfinite();
13968        _.buildArrows();
13969        _.updateArrows();
13970        _.initArrowEvents();
13971        _.buildDots();
13972        _.updateDots();
13973        _.initDotEvents();
13974        _.cleanUpSlideEvents();
13975        _.initSlideEvents();
13976
13977        _.checkResponsive(false, true);
13978
13979        if (_.options.focusOnSelect === true) {
13980            $(_.$slideTrack).children().on('click.slick', _.selectHandler);
13981        }
13982
13983        _.setSlideClasses(typeof _.currentSlide === 'number' ? _.currentSlide : 0);
13984
13985        _.setPosition();
13986        _.focusHandler();
13987
13988        _.paused = !_.options.autoplay;
13989        _.autoPlay();
13990
13991        _.$slider.trigger('reInit', [_]);
13992
13993    };
13994
13995    Slick.prototype.resize = function() {
13996
13997        var _ = this;
13998
13999        if ($(window).width() !== _.windowWidth) {
14000            clearTimeout(_.windowDelay);
14001            _.windowDelay = window.setTimeout(function() {
14002                _.windowWidth = $(window).width();
14003                _.checkResponsive();
14004                if( !_.unslicked ) { _.setPosition(); }
14005            }, 50);
14006        }
14007    };
14008
14009    Slick.prototype.removeSlide = Slick.prototype.slickRemove = function(index, removeBefore, removeAll) {
14010
14011        var _ = this;
14012
14013        if (typeof(index) === 'boolean') {
14014            removeBefore = index;
14015            index = removeBefore === true ? 0 : _.slideCount - 1;
14016        } else {
14017            index = removeBefore === true ? --index : index;
14018        }
14019
14020        if (_.slideCount < 1 || index < 0 || index > _.slideCount - 1) {
14021            return false;
14022        }
14023
14024        _.unload();
14025
14026        if (removeAll === true) {
14027            _.$slideTrack.children().remove();
14028        } else {
14029            _.$slideTrack.children(this.options.slide).eq(index).remove();
14030        }
14031
14032        _.$slides = _.$slideTrack.children(this.options.slide);
14033
14034        _.$slideTrack.children(this.options.slide).detach();
14035
14036        _.$slideTrack.append(_.$slides);
14037
14038        _.$slidesCache = _.$slides;
14039
14040        _.reinit();
14041
14042    };
14043
14044    Slick.prototype.setCSS = function(position) {
14045
14046        var _ = this,
14047            positionProps = {},
14048            x, y;
14049
14050        if (_.options.rtl === true) {
14051            position = -position;
14052        }
14053        x = _.positionProp == 'left' ? Math.ceil(position) + 'px' : '0px';
14054        y = _.positionProp == 'top' ? Math.ceil(position) + 'px' : '0px';
14055
14056        positionProps[_.positionProp] = position;
14057
14058        if (_.transformsEnabled === false) {
14059            _.$slideTrack.css(positionProps);
14060        } else {
14061            positionProps = {};
14062            if (_.cssTransitions === false) {
14063                positionProps[_.animType] = 'translate(' + x + ', ' + y + ')';
14064                _.$slideTrack.css(positionProps);
14065            } else {
14066                positionProps[_.animType] = 'translate3d(' + x + ', ' + y + ', 0px)';
14067                _.$slideTrack.css(positionProps);
14068            }
14069        }
14070
14071    };
14072
14073    Slick.prototype.setDimensions = function() {
14074
14075        var _ = this;
14076
14077        if (_.options.vertical === false) {
14078            if (_.options.centerMode === true) {
14079                _.$list.css({
14080                    padding: ('0px ' + _.options.centerPadding)
14081                });
14082            }
14083        } else {
14084            _.$list.height(_.$slides.first().outerHeight(true) * _.options.slidesToShow);
14085            if (_.options.centerMode === true) {
14086                _.$list.css({
14087                    padding: (_.options.centerPadding + ' 0px')
14088                });
14089            }
14090        }
14091
14092        _.listWidth = _.$list.width();
14093        _.listHeight = _.$list.height();
14094
14095
14096        if (_.options.vertical === false && _.options.variableWidth === false) {
14097            _.slideWidth = Math.ceil(_.listWidth / _.options.slidesToShow);
14098            _.$slideTrack.width(Math.ceil((_.slideWidth * _.$slideTrack.children('.slick-slide').length)));
14099
14100        } else if (_.options.variableWidth === true) {
14101            _.$slideTrack.width(5000 * _.slideCount);
14102        } else {
14103            _.slideWidth = Math.ceil(_.listWidth);
14104            _.$slideTrack.height(Math.ceil((_.$slides.first().outerHeight(true) * _.$slideTrack.children('.slick-slide').length)));
14105        }
14106
14107        var offset = _.$slides.first().outerWidth(true) - _.$slides.first().width();
14108        if (_.options.variableWidth === false) _.$slideTrack.children('.slick-slide').width(_.slideWidth - offset);
14109
14110    };
14111
14112    Slick.prototype.setFade = function() {
14113
14114        var _ = this,
14115            targetLeft;
14116
14117        _.$slides.each(function(index, element) {
14118            targetLeft = (_.slideWidth * index) * -1;
14119            if (_.options.rtl === true) {
14120                $(element).css({
14121                    position: 'relative',
14122                    right: targetLeft,
14123                    top: 0,
14124                    zIndex: _.options.zIndex - 2,
14125                    opacity: 0
14126                });
14127            } else {
14128                $(element).css({
14129                    position: 'relative',
14130                    left: targetLeft,
14131                    top: 0,
14132                    zIndex: _.options.zIndex - 2,
14133                    opacity: 0
14134                });
14135            }
14136        });
14137
14138        _.$slides.eq(_.currentSlide).css({
14139            zIndex: _.options.zIndex - 1,
14140            opacity: 1
14141        });
14142
14143    };
14144
14145    Slick.prototype.setHeight = function() {
14146
14147        var _ = this;
14148
14149        if (_.options.slidesToShow === 1 && _.options.adaptiveHeight === true && _.options.vertical === false) {
14150            var targetHeight = _.$slides.eq(_.currentSlide).outerHeight(true);
14151            _.$list.css('height', targetHeight);
14152        }
14153
14154    };
14155
14156    Slick.prototype.setOption =
14157    Slick.prototype.slickSetOption = function() {
14158
14159        /**
14160         * accepts arguments in format of:
14161         *
14162         *  - for changing a single option's value:
14163         *     .slick("setOption", option, value, refresh )
14164         *
14165         *  - for changing a set of responsive options:
14166         *     .slick("setOption", 'responsive', [{}, ...], refresh )
14167         *
14168         *  - for updating multiple values at once (not responsive)
14169         *     .slick("setOption", { 'option': value, ... }, refresh )
14170         */
14171
14172        var _ = this, l, item, option, value, refresh = false, type;
14173
14174        if( $.type( arguments[0] ) === 'object' ) {
14175
14176            option =  arguments[0];
14177            refresh = arguments[1];
14178            type = 'multiple';
14179
14180        } else if ( $.type( arguments[0] ) === 'string' ) {
14181
14182            option =  arguments[0];
14183            value = arguments[1];
14184            refresh = arguments[2];
14185
14186            if ( arguments[0] === 'responsive' && $.type( arguments[1] ) === 'array' ) {
14187
14188                type = 'responsive';
14189
14190            } else if ( typeof arguments[1] !== 'undefined' ) {
14191
14192                type = 'single';
14193
14194            }
14195
14196        }
14197
14198        if ( type === 'single' ) {
14199
14200            _.options[option] = value;
14201
14202
14203        } else if ( type === 'multiple' ) {
14204
14205            $.each( option , function( opt, val ) {
14206
14207                _.options[opt] = val;
14208
14209            });
14210
14211
14212        } else if ( type === 'responsive' ) {
14213
14214            for ( item in value ) {
14215
14216                if( $.type( _.options.responsive ) !== 'array' ) {
14217
14218                    _.options.responsive = [ value[item] ];
14219
14220                } else {
14221
14222                    l = _.options.responsive.length-1;
14223
14224                    // loop through the responsive object and splice out duplicates.
14225                    while( l >= 0 ) {
14226
14227                        if( _.options.responsive[l].breakpoint === value[item].breakpoint ) {
14228
14229                            _.options.responsive.splice(l,1);
14230
14231                        }
14232
14233                        l--;
14234
14235                    }
14236
14237                    _.options.responsive.push( value[item] );
14238
14239                }
14240
14241            }
14242
14243        }
14244
14245        if ( refresh ) {
14246
14247            _.unload();
14248            _.reinit();
14249
14250        }
14251
14252    };
14253
14254    Slick.prototype.setPosition = function() {
14255
14256        var _ = this;
14257
14258        _.setDimensions();
14259
14260        _.setHeight();
14261
14262        if (_.options.fade === false) {
14263            _.setCSS(_.getLeft(_.currentSlide));
14264        } else {
14265            _.setFade();
14266        }
14267
14268        _.$slider.trigger('setPosition', [_]);
14269
14270    };
14271
14272    Slick.prototype.setProps = function() {
14273
14274        var _ = this,
14275            bodyStyle = document.body.style;
14276
14277        _.positionProp = _.options.vertical === true ? 'top' : 'left';
14278
14279        if (_.positionProp === 'top') {
14280            _.$slider.addClass('slick-vertical');
14281        } else {
14282            _.$slider.removeClass('slick-vertical');
14283        }
14284
14285        if (bodyStyle.WebkitTransition !== undefined ||
14286            bodyStyle.MozTransition !== undefined ||
14287            bodyStyle.msTransition !== undefined) {
14288            if (_.options.useCSS === true) {
14289                _.cssTransitions = true;
14290            }
14291        }
14292
14293        if ( _.options.fade ) {
14294            if ( typeof _.options.zIndex === 'number' ) {
14295                if( _.options.zIndex < 3 ) {
14296                    _.options.zIndex = 3;
14297                }
14298            } else {
14299                _.options.zIndex = _.defaults.zIndex;
14300            }
14301        }
14302
14303        if (bodyStyle.OTransform !== undefined) {
14304            _.animType = 'OTransform';
14305            _.transformType = '-o-transform';
14306            _.transitionType = 'OTransition';
14307            if (bodyStyle.perspectiveProperty === undefined && bodyStyle.webkitPerspective === undefined) _.animType = false;
14308        }
14309        if (bodyStyle.MozTransform !== undefined) {
14310            _.animType = 'MozTransform';
14311            _.transformType = '-moz-transform';
14312            _.transitionType = 'MozTransition';
14313            if (bodyStyle.perspectiveProperty === undefined && bodyStyle.MozPerspective === undefined) _.animType = false;
14314        }
14315        if (bodyStyle.webkitTransform !== undefined) {
14316            _.animType = 'webkitTransform';
14317            _.transformType = '-webkit-transform';
14318            _.transitionType = 'webkitTransition';
14319            if (bodyStyle.perspectiveProperty === undefined && bodyStyle.webkitPerspective === undefined) _.animType = false;
14320        }
14321        if (bodyStyle.msTransform !== undefined) {
14322            _.animType = 'msTransform';
14323            _.transformType = '-ms-transform';
14324            _.transitionType = 'msTransition';
14325            if (bodyStyle.msTransform === undefined) _.animType = false;
14326        }
14327        if (bodyStyle.transform !== undefined && _.animType !== false) {
14328            _.animType = 'transform';
14329            _.transformType = 'transform';
14330            _.transitionType = 'transition';
14331        }
14332        _.transformsEnabled = _.options.useTransform && (_.animType !== null && _.animType !== false);
14333    };
14334
14335
14336    Slick.prototype.setSlideClasses = function(index) {
14337
14338        var _ = this,
14339            centerOffset, allSlides, indexOffset, remainder;
14340
14341        allSlides = _.$slider
14342            .find('.slick-slide')
14343            .removeClass('slick-active slick-center slick-current')
14344            .attr('aria-hidden', 'true');
14345
14346        _.$slides
14347            .eq(index)
14348            .addClass('slick-current');
14349
14350        if (_.options.centerMode === true) {
14351
14352            var evenCoef = _.options.slidesToShow % 2 === 0 ? 1 : 0;
14353
14354            centerOffset = Math.floor(_.options.slidesToShow / 2);
14355
14356            if (_.options.infinite === true) {
14357
14358                if (index >= centerOffset && index <= (_.slideCount - 1) - centerOffset) {
14359                    _.$slides
14360                        .slice(index - centerOffset + evenCoef, index + centerOffset + 1)
14361                        .addClass('slick-active')
14362                        .attr('aria-hidden', 'false');
14363
14364                } else {
14365
14366                    indexOffset = _.options.slidesToShow + index;
14367                    allSlides
14368                        .slice(indexOffset - centerOffset + 1 + evenCoef, indexOffset + centerOffset + 2)
14369                        .addClass('slick-active')
14370                        .attr('aria-hidden', 'false');
14371
14372                }
14373
14374                if (index === 0) {
14375
14376                    allSlides
14377                        .eq(allSlides.length - 1 - _.options.slidesToShow)
14378                        .addClass('slick-center');
14379
14380                } else if (index === _.slideCount - 1) {
14381
14382                    allSlides
14383                        .eq(_.options.slidesToShow)
14384                        .addClass('slick-center');
14385
14386                }
14387
14388            }
14389
14390            _.$slides
14391                .eq(index)
14392                .addClass('slick-center');
14393
14394        } else {
14395
14396            if (index >= 0 && index <= (_.slideCount - _.options.slidesToShow)) {
14397
14398                _.$slides
14399                    .slice(index, index + _.options.slidesToShow)
14400                    .addClass('slick-active')
14401                    .attr('aria-hidden', 'false');
14402
14403            } else if (allSlides.length <= _.options.slidesToShow) {
14404
14405                allSlides
14406                    .addClass('slick-active')
14407                    .attr('aria-hidden', 'false');
14408
14409            } else {
14410
14411                remainder = _.slideCount % _.options.slidesToShow;
14412                indexOffset = _.options.infinite === true ? _.options.slidesToShow + index : index;
14413
14414                if (_.options.slidesToShow == _.options.slidesToScroll && (_.slideCount - index) < _.options.slidesToShow) {
14415
14416                    allSlides
14417                        .slice(indexOffset - (_.options.slidesToShow - remainder), indexOffset + remainder)
14418                        .addClass('slick-active')
14419                        .attr('aria-hidden', 'false');
14420
14421                } else {
14422
14423                    allSlides
14424                        .slice(indexOffset, indexOffset + _.options.slidesToShow)
14425                        .addClass('slick-active')
14426                        .attr('aria-hidden', 'false');
14427
14428                }
14429
14430            }
14431
14432        }
14433
14434        if (_.options.lazyLoad === 'ondemand' || _.options.lazyLoad === 'anticipated') {
14435            _.lazyLoad();
14436        }
14437    };
14438
14439    Slick.prototype.setupInfinite = function() {
14440
14441        var _ = this,
14442            i, slideIndex, infiniteCount;
14443
14444        if (_.options.fade === true) {
14445            _.options.centerMode = false;
14446        }
14447
14448        if (_.options.infinite === true && _.options.fade === false) {
14449
14450            slideIndex = null;
14451
14452            if (_.slideCount > _.options.slidesToShow) {
14453
14454                if (_.options.centerMode === true) {
14455                    infiniteCount = _.options.slidesToShow + 1;
14456                } else {
14457                    infiniteCount = _.options.slidesToShow;
14458                }
14459
14460                for (i = _.slideCount; i > (_.slideCount -
14461                        infiniteCount); i -= 1) {
14462                    slideIndex = i - 1;
14463                    $(_.$slides[slideIndex]).clone(true).attr('id', '')
14464                        .attr('data-slick-index', slideIndex - _.slideCount)
14465                        .prependTo(_.$slideTrack).addClass('slick-cloned');
14466                }
14467                for (i = 0; i < infiniteCount  + _.slideCount; i += 1) {
14468                    slideIndex = i;
14469                    $(_.$slides[slideIndex]).clone(true).attr('id', '')
14470                        .attr('data-slick-index', slideIndex + _.slideCount)
14471                        .appendTo(_.$slideTrack).addClass('slick-cloned');
14472                }
14473                _.$slideTrack.find('.slick-cloned').find('[id]').each(function() {
14474                    $(this).attr('id', '');
14475                });
14476
14477            }
14478
14479        }
14480
14481    };
14482
14483    Slick.prototype.interrupt = function( toggle ) {
14484
14485        var _ = this;
14486
14487        if( !toggle ) {
14488            _.autoPlay();
14489        }
14490        _.interrupted = toggle;
14491
14492    };
14493
14494    Slick.prototype.selectHandler = function(event) {
14495
14496        var _ = this;
14497
14498        var targetElement =
14499            $(event.target).is('.slick-slide') ?
14500                $(event.target) :
14501                $(event.target).parents('.slick-slide');
14502
14503        var index = parseInt(targetElement.attr('data-slick-index'));
14504
14505        if (!index) index = 0;
14506
14507        if (_.slideCount <= _.options.slidesToShow) {
14508
14509            _.slideHandler(index, false, true);
14510            return;
14511
14512        }
14513
14514        _.slideHandler(index);
14515
14516    };
14517
14518    Slick.prototype.slideHandler = function(index, sync, dontAnimate) {
14519
14520        var targetSlide, animSlide, oldSlide, slideLeft, targetLeft = null,
14521            _ = this, navTarget;
14522
14523        sync = sync || false;
14524
14525        if (_.animating === true && _.options.waitForAnimate === true) {
14526            return;
14527        }
14528
14529        if (_.options.fade === true && _.currentSlide === index) {
14530            return;
14531        }
14532
14533        if (sync === false) {
14534            _.asNavFor(index);
14535        }
14536
14537        targetSlide = index;
14538        targetLeft = _.getLeft(targetSlide);
14539        slideLeft = _.getLeft(_.currentSlide);
14540
14541        _.currentLeft = _.swipeLeft === null ? slideLeft : _.swipeLeft;
14542
14543        if (_.options.infinite === false && _.options.centerMode === false && (index < 0 || index > _.getDotCount() * _.options.slidesToScroll)) {
14544            if (_.options.fade === false) {
14545                targetSlide = _.currentSlide;
14546                if (dontAnimate !== true && _.slideCount > _.options.slidesToShow) {
14547                    _.animateSlide(slideLeft, function() {
14548                        _.postSlide(targetSlide);
14549                    });
14550                } else {
14551                    _.postSlide(targetSlide);
14552                }
14553            }
14554            return;
14555        } else if (_.options.infinite === false && _.options.centerMode === true && (index < 0 || index > (_.slideCount - _.options.slidesToScroll))) {
14556            if (_.options.fade === false) {
14557                targetSlide = _.currentSlide;
14558                if (dontAnimate !== true && _.slideCount > _.options.slidesToShow) {
14559                    _.animateSlide(slideLeft, function() {
14560                        _.postSlide(targetSlide);
14561                    });
14562                } else {
14563                    _.postSlide(targetSlide);
14564                }
14565            }
14566            return;
14567        }
14568
14569        if ( _.options.autoplay ) {
14570            clearInterval(_.autoPlayTimer);
14571        }
14572
14573        if (targetSlide < 0) {
14574            if (_.slideCount % _.options.slidesToScroll !== 0) {
14575                animSlide = _.slideCount - (_.slideCount % _.options.slidesToScroll);
14576            } else {
14577                animSlide = _.slideCount + targetSlide;
14578            }
14579        } else if (targetSlide >= _.slideCount) {
14580            if (_.slideCount % _.options.slidesToScroll !== 0) {
14581                animSlide = 0;
14582            } else {
14583                animSlide = targetSlide - _.slideCount;
14584            }
14585        } else {
14586            animSlide = targetSlide;
14587        }
14588
14589        _.animating = true;
14590
14591        _.$slider.trigger('beforeChange', [_, _.currentSlide, animSlide]);
14592
14593        oldSlide = _.currentSlide;
14594        _.currentSlide = animSlide;
14595
14596        _.setSlideClasses(_.currentSlide);
14597
14598        if ( _.options.asNavFor ) {
14599
14600            navTarget = _.getNavTarget();
14601            navTarget = navTarget.slick('getSlick');
14602
14603            if ( navTarget.slideCount <= navTarget.options.slidesToShow ) {
14604                navTarget.setSlideClasses(_.currentSlide);
14605            }
14606
14607        }
14608
14609        _.updateDots();
14610        _.updateArrows();
14611
14612        if (_.options.fade === true) {
14613            if (dontAnimate !== true) {
14614
14615                _.fadeSlideOut(oldSlide);
14616
14617                _.fadeSlide(animSlide, function() {
14618                    _.postSlide(animSlide);
14619                });
14620
14621            } else {
14622                _.postSlide(animSlide);
14623            }
14624            _.animateHeight();
14625            return;
14626        }
14627
14628        if (dontAnimate !== true && _.slideCount > _.options.slidesToShow) {
14629            _.animateSlide(targetLeft, function() {
14630                _.postSlide(animSlide);
14631            });
14632        } else {
14633            _.postSlide(animSlide);
14634        }
14635
14636    };
14637
14638    Slick.prototype.startLoad = function() {
14639
14640        var _ = this;
14641
14642        if (_.options.arrows === true && _.slideCount > _.options.slidesToShow) {
14643
14644            _.$prevArrow.hide();
14645            _.$nextArrow.hide();
14646
14647        }
14648
14649        if (_.options.dots === true && _.slideCount > _.options.slidesToShow) {
14650
14651            _.$dots.hide();
14652
14653        }
14654
14655        _.$slider.addClass('slick-loading');
14656
14657    };
14658
14659    Slick.prototype.swipeDirection = function() {
14660
14661        var xDist, yDist, r, swipeAngle, _ = this;
14662
14663        xDist = _.touchObject.startX - _.touchObject.curX;
14664        yDist = _.touchObject.startY - _.touchObject.curY;
14665        r = Math.atan2(yDist, xDist);
14666
14667        swipeAngle = Math.round(r * 180 / Math.PI);
14668        if (swipeAngle < 0) {
14669            swipeAngle = 360 - Math.abs(swipeAngle);
14670        }
14671
14672        if ((swipeAngle <= 45) && (swipeAngle >= 0)) {
14673            return (_.options.rtl === false ? 'left' : 'right');
14674        }
14675        if ((swipeAngle <= 360) && (swipeAngle >= 315)) {
14676            return (_.options.rtl === false ? 'left' : 'right');
14677        }
14678        if ((swipeAngle >= 135) && (swipeAngle <= 225)) {
14679            return (_.options.rtl === false ? 'right' : 'left');
14680        }
14681        if (_.options.verticalSwiping === true) {
14682            if ((swipeAngle >= 35) && (swipeAngle <= 135)) {
14683                return 'down';
14684            } else {
14685                return 'up';
14686            }
14687        }
14688
14689        return 'vertical';
14690
14691    };
14692
14693    Slick.prototype.swipeEnd = function(event) {
14694
14695        var _ = this,
14696            slideCount,
14697            direction;
14698
14699        _.dragging = false;
14700        _.swiping = false;
14701
14702        if (_.scrolling) {
14703            _.scrolling = false;
14704            return false;
14705        }
14706
14707        _.interrupted = false;
14708        _.shouldClick = ( _.touchObject.swipeLength > 10 ) ? false : true;
14709
14710        if ( _.touchObject.curX === undefined ) {
14711            return false;
14712        }
14713
14714        if ( _.touchObject.edgeHit === true ) {
14715            _.$slider.trigger('edge', [_, _.swipeDirection() ]);
14716        }
14717
14718        if ( _.touchObject.swipeLength >= _.touchObject.minSwipe ) {
14719
14720            direction = _.swipeDirection();
14721
14722            switch ( direction ) {
14723
14724                case 'left':
14725                case 'down':
14726
14727                    slideCount =
14728                        _.options.swipeToSlide ?
14729                            _.checkNavigable( _.currentSlide + _.getSlideCount() ) :
14730                            _.currentSlide + _.getSlideCount();
14731
14732                    _.currentDirection = 0;
14733
14734                    break;
14735
14736                case 'right':
14737                case 'up':
14738
14739                    slideCount =
14740                        _.options.swipeToSlide ?
14741                            _.checkNavigable( _.currentSlide - _.getSlideCount() ) :
14742                            _.currentSlide - _.getSlideCount();
14743
14744                    _.currentDirection = 1;
14745
14746                    break;
14747
vendor: 8,748 bytes, lines 14748-15064
14748                default:
14749
14750
14751            }
14752
14753            if( direction != 'vertical' ) {
14754
14755                _.slideHandler( slideCount );
14756                _.touchObject = {};
14757                _.$slider.trigger('swipe', [_, direction ]);
14758
14759            }
14760
14761        } else {
14762
14763            if ( _.touchObject.startX !== _.touchObject.curX ) {
14764
14765                _.slideHandler( _.currentSlide );
14766                _.touchObject = {};
14767
14768            }
14769
14770        }
14771
14772    };
14773
14774    Slick.prototype.swipeHandler = function(event) {
14775
14776        var _ = this;
14777
14778        if ((_.options.swipe === false) || ('ontouchend' in document && _.options.swipe === false)) {
14779            return;
14780        } else if (_.options.draggable === false && event.type.indexOf('mouse') !== -1) {
14781            return;
14782        }
14783
14784        _.touchObject.fingerCount = event.originalEvent && event.originalEvent.touches !== undefined ?
14785            event.originalEvent.touches.length : 1;
14786
14787        _.touchObject.minSwipe = _.listWidth / _.options
14788            .touchThreshold;
14789
14790        if (_.options.verticalSwiping === true) {
14791            _.touchObject.minSwipe = _.listHeight / _.options
14792                .touchThreshold;
14793        }
14794
14795        switch (event.data.action) {
14796
14797            case 'start':
14798                _.swipeStart(event);
14799                break;
14800
14801            case 'move':
14802                _.swipeMove(event);
14803                break;
14804
14805            case 'end':
14806                _.swipeEnd(event);
14807                break;
14808
14809        }
14810
14811    };
14812
14813    Slick.prototype.swipeMove = function(event) {
14814
14815        var _ = this,
14816            edgeWasHit = false,
14817            curLeft, swipeDirection, swipeLength, positionOffset, touches, verticalSwipeLength;
14818
14819        touches = event.originalEvent !== undefined ? event.originalEvent.touches : null;
14820
14821        if (!_.dragging || _.scrolling || touches && touches.length !== 1) {
14822            return false;
14823        }
14824
14825        curLeft = _.getLeft(_.currentSlide);
14826
14827        _.touchObject.curX = touches !== undefined ? touches[0].pageX : event.clientX;
14828        _.touchObject.curY = touches !== undefined ? touches[0].pageY : event.clientY;
14829
14830        _.touchObject.swipeLength = Math.round(Math.sqrt(
14831            Math.pow(_.touchObject.curX - _.touchObject.startX, 2)));
14832
14833        verticalSwipeLength = Math.round(Math.sqrt(
14834            Math.pow(_.touchObject.curY - _.touchObject.startY, 2)));
14835
14836        if (!_.options.verticalSwiping && !_.swiping && verticalSwipeLength > 4) {
14837            _.scrolling = true;
14838            return false;
14839        }
14840
14841        if (_.options.verticalSwiping === true) {
14842            _.touchObject.swipeLength = verticalSwipeLength;
14843        }
14844
14845        swipeDirection = _.swipeDirection();
14846
14847        if (event.originalEvent !== undefined && _.touchObject.swipeLength > 4) {
14848            _.swiping = true;
14849            event.preventDefault();
14850        }
14851
14852        positionOffset = (_.options.rtl === false ? 1 : -1) * (_.touchObject.curX > _.touchObject.startX ? 1 : -1);
14853        if (_.options.verticalSwiping === true) {
14854            positionOffset = _.touchObject.curY > _.touchObject.startY ? 1 : -1;
14855        }
14856
14857
14858        swipeLength = _.touchObject.swipeLength;
14859
14860        _.touchObject.edgeHit = false;
14861
14862        if (_.options.infinite === false) {
14863            if ((_.currentSlide === 0 && swipeDirection === 'right') || (_.currentSlide >= _.getDotCount() && swipeDirection === 'left')) {
14864                swipeLength = _.touchObject.swipeLength * _.options.edgeFriction;
14865                _.touchObject.edgeHit = true;
14866            }
14867        }
14868
14869        if (_.options.vertical === false) {
14870            _.swipeLeft = curLeft + swipeLength * positionOffset;
14871        } else {
14872            _.swipeLeft = curLeft + (swipeLength * (_.$list.height() / _.listWidth)) * positionOffset;
14873        }
14874        if (_.options.verticalSwiping === true) {
14875            _.swipeLeft = curLeft + swipeLength * positionOffset;
14876        }
14877
14878        if (_.options.fade === true || _.options.touchMove === false) {
14879            return false;
14880        }
14881
14882        if (_.animating === true) {
14883            _.swipeLeft = null;
14884            return false;
14885        }
14886
14887        _.setCSS(_.swipeLeft);
14888
14889    };
14890
14891    Slick.prototype.swipeStart = function(event) {
14892
14893        var _ = this,
14894            touches;
14895
14896        _.interrupted = true;
14897
14898        if (_.touchObject.fingerCount !== 1 || _.slideCount <= _.options.slidesToShow) {
14899            _.touchObject = {};
14900            return false;
14901        }
14902
14903        if (event.originalEvent !== undefined && event.originalEvent.touches !== undefined) {
14904            touches = event.originalEvent.touches[0];
14905        }
14906
14907        _.touchObject.startX = _.touchObject.curX = touches !== undefined ? touches.pageX : event.clientX;
14908        _.touchObject.startY = _.touchObject.curY = touches !== undefined ? touches.pageY : event.clientY;
14909
14910        _.dragging = true;
14911
14912    };
14913
14914    Slick.prototype.unfilterSlides = Slick.prototype.slickUnfilter = function() {
14915
14916        var _ = this;
14917
14918        if (_.$slidesCache !== null) {
14919
14920            _.unload();
14921
14922            _.$slideTrack.children(this.options.slide).detach();
14923
14924            _.$slidesCache.appendTo(_.$slideTrack);
14925
14926            _.reinit();
14927
14928        }
14929
14930    };
14931
14932    Slick.prototype.unload = function() {
14933
14934        var _ = this;
14935
14936        $('.slick-cloned', _.$slider).remove();
14937
14938        if (_.$dots) {
14939            _.$dots.remove();
14940        }
14941
14942        if (_.$prevArrow && _.htmlExpr.test(_.options.prevArrow)) {
14943            _.$prevArrow.remove();
14944        }
14945
14946        if (_.$nextArrow && _.htmlExpr.test(_.options.nextArrow)) {
14947            _.$nextArrow.remove();
14948        }
14949
14950        _.$slides
14951            .removeClass('slick-slide slick-active slick-visible slick-current')
14952            .attr('aria-hidden', 'true')
14953            .css('width', '');
14954
14955    };
14956
14957    Slick.prototype.unslick = function(fromBreakpoint) {
14958
14959        var _ = this;
14960        _.$slider.trigger('unslick', [_, fromBreakpoint]);
14961        _.destroy();
14962
14963    };
14964
14965    Slick.prototype.updateArrows = function() {
14966
14967        var _ = this,
14968            centerOffset;
14969
14970        centerOffset = Math.floor(_.options.slidesToShow / 2);
14971
14972        if ( _.options.arrows === true &&
14973            _.slideCount > _.options.slidesToShow &&
14974            !_.options.infinite ) {
14975
14976            _.$prevArrow.removeClass('slick-disabled').attr('aria-disabled', 'false');
14977            _.$nextArrow.removeClass('slick-disabled').attr('aria-disabled', 'false');
14978
14979            if (_.currentSlide === 0) {
14980
14981                _.$prevArrow.addClass('slick-disabled').attr('aria-disabled', 'true');
14982                _.$nextArrow.removeClass('slick-disabled').attr('aria-disabled', 'false');
14983
14984            } else if (_.currentSlide >= _.slideCount - _.options.slidesToShow && _.options.centerMode === false) {
14985
14986                _.$nextArrow.addClass('slick-disabled').attr('aria-disabled', 'true');
14987                _.$prevArrow.removeClass('slick-disabled').attr('aria-disabled', 'false');
14988
14989            } else if (_.currentSlide >= _.slideCount - 1 && _.options.centerMode === true) {
14990
14991                _.$nextArrow.addClass('slick-disabled').attr('aria-disabled', 'true');
14992                _.$prevArrow.removeClass('slick-disabled').attr('aria-disabled', 'false');
14993
14994            }
14995
14996        }
14997
14998    };
14999
15000    Slick.prototype.updateDots = function() {
15001
15002        var _ = this;
15003
15004        if (_.$dots !== null) {
15005
15006            _.$dots
15007                .find('li')
15008                    .removeClass('slick-active')
15009                    .end();
15010
15011            _.$dots
15012                .find('li')
15013                .eq(Math.floor(_.currentSlide / _.options.slidesToScroll))
15014                .addClass('slick-active');
15015
15016        }
15017
15018    };
15019
15020    Slick.prototype.visibility = function() {
15021
15022        var _ = this;
15023
15024        if ( _.options.autoplay ) {
15025
15026            if ( document[_.hidden] ) {
15027
15028                _.interrupted = true;
15029
15030            } else {
15031
15032                _.interrupted = false;
15033
15034            }
15035
15036        }
15037
15038    };
15039
15040    $.fn.slick = function() {
15041        var _ = this,
15042            opt = arguments[0],
15043            args = Array.prototype.slice.call(arguments, 1),
15044            l = _.length,
15045            i,
15046            ret;
15047        for (i = 0; i < l; i++) {
15048            if (typeof opt == 'object' || typeof opt == 'undefined')
15049                _[i].slick = new Slick(_[i], opt);
15050            else
15051                ret = _[i].slick[opt].apply(_[i].slick, args);
15052            if (typeof ret != 'undefined') return ret;
15053        }
15054        return _;
15055    };
15056
15057}));
15058
15059
15060/***/ }),
15061/* 23 */
15062/***/ (function(module, exports, __webpack_require__) {
15063
15064/* WEBPACK VAR INJECTION */(function(__webpack_provided_window_dot_jQuery) {var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/*! Magnific Popup - v1.1.0 - 2016-02-20
vendor: 42,148 bytes, lines 15065-16930
15065* http://dimsemenov.com/plugins/magnific-popup/
15066* Copyright (c) 2016 Dmitry Semenov; */
15067;(function (factory) { 
15068if (true) { 
15069 // AMD. Register as an anonymous module. 
15070 !(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0)], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
15071				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
15072				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
15073				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__)); 
15074 } else if (typeof exports === 'object') { 
15075 // Node/CommonJS 
15076 factory(require('jquery')); 
15077 } else { 
15078 // Browser globals 
15079 factory(window.jQuery || window.Zepto); 
15080 } 
15081 }(function($) { 
15082
15083/*>>core*/
15084/**
15085 * 
15086 * Magnific Popup Core JS file
15087 * 
15088 */
15089
15090
15091/**
15092 * Private static constants
15093 */
15094var CLOSE_EVENT = 'Close',
15095	BEFORE_CLOSE_EVENT = 'BeforeClose',
15096	AFTER_CLOSE_EVENT = 'AfterClose',
15097	BEFORE_APPEND_EVENT = 'BeforeAppend',
15098	MARKUP_PARSE_EVENT = 'MarkupParse',
15099	OPEN_EVENT = 'Open',
15100	CHANGE_EVENT = 'Change',
15101	NS = 'mfp',
15102	EVENT_NS = '.' + NS,
15103	READY_CLASS = 'mfp-ready',
15104	REMOVING_CLASS = 'mfp-removing',
15105	PREVENT_CLOSE_CLASS = 'mfp-prevent-close';
15106
15107
15108/**
15109 * Private vars 
15110 */
15111/*jshint -W079 */
15112var mfp, // As we have only one instance of MagnificPopup object, we define it locally to not to use 'this'
15113	MagnificPopup = function(){},
15114	_isJQ = !!(__webpack_provided_window_dot_jQuery),
15115	_prevStatus,
15116	_window = $(window),
15117	_document,
15118	_prevContentType,
15119	_wrapClasses,
15120	_currPopupType;
15121
15122
15123/**
15124 * Private functions
15125 */
15126var _mfpOn = function(name, f) {
15127		mfp.ev.on(NS + name + EVENT_NS, f);
15128	},
15129	_getEl = function(className, appendTo, html, raw) {
15130		var el = document.createElement('div');
15131		el.className = 'mfp-'+className;
15132		if(html) {
15133			el.innerHTML = html;
15134		}
15135		if(!raw) {
15136			el = $(el);
15137			if(appendTo) {
15138				el.appendTo(appendTo);
15139			}
15140		} else if(appendTo) {
15141			appendTo.appendChild(el);
15142		}
15143		return el;
15144	},
15145	_mfpTrigger = function(e, data) {
15146		mfp.ev.triggerHandler(NS + e, data);
15147
15148		if(mfp.st.callbacks) {
15149			// converts "mfpEventName" to "eventName" callback and triggers it if it's present
15150			e = e.charAt(0).toLowerCase() + e.slice(1);
15151			if(mfp.st.callbacks[e]) {
15152				mfp.st.callbacks[e].apply(mfp, $.isArray(data) ? data : [data]);
15153			}
15154		}
15155	},
15156	_getCloseBtn = function(type) {
15157		if(type !== _currPopupType || !mfp.currTemplate.closeBtn) {
15158			mfp.currTemplate.closeBtn = $( mfp.st.closeMarkup.replace('%title%', mfp.st.tClose ) );
15159			_currPopupType = type;
15160		}
15161		return mfp.currTemplate.closeBtn;
15162	},
15163	// Initialize Magnific Popup only when called at least once
15164	_checkInstance = function() {
15165		if(!$.magnificPopup.instance) {
15166			/*jshint -W020 */
15167			mfp = new MagnificPopup();
15168			mfp.init();
15169			$.magnificPopup.instance = mfp;
15170		}
15171	},
15172	// CSS transition detection, http://stackoverflow.com/questions/7264899/detect-css-transitions-using-javascript-and-without-modernizr
15173	supportsTransitions = function() {
15174		var s = document.createElement('p').style, // 's' for style. better to create an element if body yet to exist
15175			v = ['ms','O','Moz','Webkit']; // 'v' for vendor
15176
15177		if( s['transition'] !== undefined ) {
15178			return true; 
15179		}
15180			
15181		while( v.length ) {
15182			if( v.pop() + 'Transition' in s ) {
15183				return true;
15184			}
15185		}
15186				
15187		return false;
15188	};
15189
15190
15191
15192/**
15193 * Public functions
15194 */
15195MagnificPopup.prototype = {
15196
15197	constructor: MagnificPopup,
15198
15199	/**
15200	 * Initializes Magnific Popup plugin. 
15201	 * This function is triggered only once when $.fn.magnificPopup or $.magnificPopup is executed
15202	 */
15203	init: function() {
15204		var appVersion = navigator.appVersion;
15205		mfp.isLowIE = mfp.isIE8 = document.all && !document.addEventListener;
15206		mfp.isAndroid = (/android/gi).test(appVersion);
15207		mfp.isIOS = (/iphone|ipad|ipod/gi).test(appVersion);
15208		mfp.supportsTransition = supportsTransitions();
15209
15210		// We disable fixed positioned lightbox on devices that don't handle it nicely.
15211		// If you know a better way of detecting this - let me know.
15212		mfp.probablyMobile = (mfp.isAndroid || mfp.isIOS || /(Opera Mini)|Kindle|webOS|BlackBerry|(Opera Mobi)|(Windows Phone)|IEMobile/i.test(navigator.userAgent) );
15213		_document = $(document);
15214
15215		mfp.popupsCache = {};
15216	},
15217
15218	/**
15219	 * Opens popup
15220	 * @param  data [description]
15221	 */
15222	open: function(data) {
15223
15224		var i;
15225
15226		if(data.isObj === false) { 
15227			// convert jQuery collection to array to avoid conflicts later
15228			mfp.items = data.items.toArray();
15229
15230			mfp.index = 0;
15231			var items = data.items,
15232				item;
15233			for(i = 0; i < items.length; i++) {
15234				item = items[i];
15235				if(item.parsed) {
15236					item = item.el[0];
15237				}
15238				if(item === data.el[0]) {
15239					mfp.index = i;
15240					break;
15241				}
15242			}
15243		} else {
15244			mfp.items = $.isArray(data.items) ? data.items : [data.items];
15245			mfp.index = data.index || 0;
15246		}
15247
15248		// if popup is already opened - we just update the content
15249		if(mfp.isOpen) {
15250			mfp.updateItemHTML();
15251			return;
15252		}
15253		
15254		mfp.types = []; 
15255		_wrapClasses = '';
15256		if(data.mainEl && data.mainEl.length) {
15257			mfp.ev = data.mainEl.eq(0);
15258		} else {
15259			mfp.ev = _document;
15260		}
15261
15262		if(data.key) {
15263			if(!mfp.popupsCache[data.key]) {
15264				mfp.popupsCache[data.key] = {};
15265			}
15266			mfp.currTemplate = mfp.popupsCache[data.key];
15267		} else {
15268			mfp.currTemplate = {};
15269		}
15270
15271
15272
15273		mfp.st = $.extend(true, {}, $.magnificPopup.defaults, data ); 
15274		mfp.fixedContentPos = mfp.st.fixedContentPos === 'auto' ? !mfp.probablyMobile : mfp.st.fixedContentPos;
15275
15276		if(mfp.st.modal) {
15277			mfp.st.closeOnContentClick = false;
15278			mfp.st.closeOnBgClick = false;
15279			mfp.st.showCloseBtn = false;
15280			mfp.st.enableEscapeKey = false;
15281		}
15282		
15283
15284		// Building markup
15285		// main containers are created only once
15286		if(!mfp.bgOverlay) {
15287
15288			// Dark overlay
15289			mfp.bgOverlay = _getEl('bg').on('click'+EVENT_NS, function() {
15290				mfp.close();
15291			});
15292
15293			mfp.wrap = _getEl('wrap').attr('tabindex', -1).on('click'+EVENT_NS, function(e) {
15294				if(mfp._checkIfClose(e.target)) {
15295					mfp.close();
15296				}
15297			});
15298
15299			mfp.container = _getEl('container', mfp.wrap);
15300		}
15301
15302		mfp.contentContainer = _getEl('content');
15303		if(mfp.st.preloader) {
15304			mfp.preloader = _getEl('preloader', mfp.container, mfp.st.tLoading);
15305		}
15306
15307
15308		// Initializing modules
15309		var modules = $.magnificPopup.modules;
15310		for(i = 0; i < modules.length; i++) {
15311			var n = modules[i];
15312			n = n.charAt(0).toUpperCase() + n.slice(1);
15313			mfp['init'+n].call(mfp);
15314		}
15315		_mfpTrigger('BeforeOpen');
15316
15317
15318		if(mfp.st.showCloseBtn) {
15319			// Close button
15320			if(!mfp.st.closeBtnInside) {
15321				mfp.wrap.append( _getCloseBtn() );
15322			} else {
15323				_mfpOn(MARKUP_PARSE_EVENT, function(e, template, values, item) {
15324					values.close_replaceWith = _getCloseBtn(item.type);
15325				});
15326				_wrapClasses += ' mfp-close-btn-in';
15327			}
15328		}
15329
15330		if(mfp.st.alignTop) {
15331			_wrapClasses += ' mfp-align-top';
15332		}
15333
15334	
15335
15336		if(mfp.fixedContentPos) {
15337			mfp.wrap.css({
15338				overflow: mfp.st.overflowY,
15339				overflowX: 'hidden',
15340				overflowY: mfp.st.overflowY
15341			});
15342		} else {
15343			mfp.wrap.css({ 
15344				top: _window.scrollTop(),
15345				position: 'absolute'
15346			});
15347		}
15348		if( mfp.st.fixedBgPos === false || (mfp.st.fixedBgPos === 'auto' && !mfp.fixedContentPos) ) {
15349			mfp.bgOverlay.css({
15350				height: _document.height(),
15351				position: 'absolute'
15352			});
15353		}
15354
15355		
15356
15357		if(mfp.st.enableEscapeKey) {
15358			// Close on ESC key
15359			_document.on('keyup' + EVENT_NS, function(e) {
15360				if(e.keyCode === 27) {
15361					mfp.close();
15362				}
15363			});
15364		}
15365
15366		_window.on('resize' + EVENT_NS, function() {
15367			mfp.updateSize();
15368		});
15369
15370
15371		if(!mfp.st.closeOnContentClick) {
15372			_wrapClasses += ' mfp-auto-cursor';
15373		}
15374		
15375		if(_wrapClasses)
15376			mfp.wrap.addClass(_wrapClasses);
15377
15378
15379		// this triggers recalculation of layout, so we get it once to not to trigger twice
15380		var windowHeight = mfp.wH = _window.height();
15381
15382		
15383		var windowStyles = {};
15384
15385		if( mfp.fixedContentPos ) {
15386            if(mfp._hasScrollBar(windowHeight)){
15387                var s = mfp._getScrollbarSize();
15388                if(s) {
15389                    windowStyles.marginRight = s;
15390                }
15391            }
15392        }
15393
15394		if(mfp.fixedContentPos) {
15395			if(!mfp.isIE7) {
15396				windowStyles.overflow = 'hidden';
15397			} else {
15398				// ie7 double-scroll bug
15399				$('body, html').css('overflow', 'hidden');
15400			}
15401		}
15402
15403		
15404		
15405		var classesToadd = mfp.st.mainClass;
15406		if(mfp.isIE7) {
15407			classesToadd += ' mfp-ie7';
15408		}
15409		if(classesToadd) {
15410			mfp._addClassToMFP( classesToadd );
15411		}
15412
15413		// add content
15414		mfp.updateItemHTML();
15415
15416		_mfpTrigger('BuildControls');
15417
15418		// remove scrollbar, add margin e.t.c
15419		$('html').css(windowStyles);
15420		
15421		// add everything to DOM
15422		mfp.bgOverlay.add(mfp.wrap).prependTo( mfp.st.prependTo || $(document.body) );
15423
15424		// Save last focused element
15425		mfp._lastFocusedEl = document.activeElement;
15426		
15427		// Wait for next cycle to allow CSS transition
15428		setTimeout(function() {
15429			
15430			if(mfp.content) {
15431				mfp._addClassToMFP(READY_CLASS);
15432				mfp._setFocus();
15433			} else {
15434				// if content is not defined (not loaded e.t.c) we add class only for BG
15435				mfp.bgOverlay.addClass(READY_CLASS);
15436			}
15437			
15438			// Trap the focus in popup
15439			_document.on('focusin' + EVENT_NS, mfp._onFocusIn);
15440
15441		}, 16);
15442
15443		mfp.isOpen = true;
15444		mfp.updateSize(windowHeight);
15445		_mfpTrigger(OPEN_EVENT);
15446
15447		return data;
15448	},
15449
15450	/**
15451	 * Closes the popup
15452	 */
15453	close: function() {
15454		if(!mfp.isOpen) return;
15455		_mfpTrigger(BEFORE_CLOSE_EVENT);
15456
15457		mfp.isOpen = false;
15458		// for CSS3 animation
15459		if(mfp.st.removalDelay && !mfp.isLowIE && mfp.supportsTransition )  {
15460			mfp._addClassToMFP(REMOVING_CLASS);
15461			setTimeout(function() {
15462				mfp._close();
15463			}, mfp.st.removalDelay);
15464		} else {
15465			mfp._close();
15466		}
15467	},
15468
15469	/**
15470	 * Helper for close() function
15471	 */
15472	_close: function() {
15473		_mfpTrigger(CLOSE_EVENT);
15474
15475		var classesToRemove = REMOVING_CLASS + ' ' + READY_CLASS + ' ';
15476
15477		mfp.bgOverlay.detach();
15478		mfp.wrap.detach();
15479		mfp.container.empty();
15480
15481		if(mfp.st.mainClass) {
15482			classesToRemove += mfp.st.mainClass + ' ';
15483		}
15484
15485		mfp._removeClassFromMFP(classesToRemove);
15486
15487		if(mfp.fixedContentPos) {
15488			var windowStyles = {marginRight: ''};
15489			if(mfp.isIE7) {
15490				$('body, html').css('overflow', '');
15491			} else {
15492				windowStyles.overflow = '';
15493			}
15494			$('html').css(windowStyles);
15495		}
15496		
15497		_document.off('keyup' + EVENT_NS + ' focusin' + EVENT_NS);
15498		mfp.ev.off(EVENT_NS);
15499
15500		// clean up DOM elements that aren't removed
15501		mfp.wrap.attr('class', 'mfp-wrap').removeAttr('style');
15502		mfp.bgOverlay.attr('class', 'mfp-bg');
15503		mfp.container.attr('class', 'mfp-container');
15504
15505		// remove close button from target element
15506		if(mfp.st.showCloseBtn &&
15507		(!mfp.st.closeBtnInside || mfp.currTemplate[mfp.currItem.type] === true)) {
15508			if(mfp.currTemplate.closeBtn)
15509				mfp.currTemplate.closeBtn.detach();
15510		}
15511
15512
15513		if(mfp.st.autoFocusLast && mfp._lastFocusedEl) {
15514			$(mfp._lastFocusedEl).focus(); // put tab focus back
15515		}
15516		mfp.currItem = null;	
15517		mfp.content = null;
15518		mfp.currTemplate = null;
15519		mfp.prevHeight = 0;
15520
15521		_mfpTrigger(AFTER_CLOSE_EVENT);
15522	},
15523	
15524	updateSize: function(winHeight) {
15525
15526		if(mfp.isIOS) {
15527			// fixes iOS nav bars https://github.com/dimsemenov/Magnific-Popup/issues/2
15528			var zoomLevel = document.documentElement.clientWidth / window.innerWidth;
15529			var height = window.innerHeight * zoomLevel;
15530			mfp.wrap.css('height', height);
15531			mfp.wH = height;
15532		} else {
15533			mfp.wH = winHeight || _window.height();
15534		}
15535		// Fixes #84: popup incorrectly positioned with position:relative on body
15536		if(!mfp.fixedContentPos) {
15537			mfp.wrap.css('height', mfp.wH);
15538		}
15539
15540		_mfpTrigger('Resize');
15541
15542	},
15543
15544	/**
15545	 * Set content of popup based on current index
15546	 */
15547	updateItemHTML: function() {
15548		var item = mfp.items[mfp.index];
15549
15550		// Detach and perform modifications
15551		mfp.contentContainer.detach();
15552
15553		if(mfp.content)
15554			mfp.content.detach();
15555
15556		if(!item.parsed) {
15557			item = mfp.parseEl( mfp.index );
15558		}
15559
15560		var type = item.type;
15561
15562		_mfpTrigger('BeforeChange', [mfp.currItem ? mfp.currItem.type : '', type]);
15563		// BeforeChange event works like so:
15564		// _mfpOn('BeforeChange', function(e, prevType, newType) { });
15565
15566		mfp.currItem = item;
15567
15568		if(!mfp.currTemplate[type]) {
15569			var markup = mfp.st[type] ? mfp.st[type].markup : false;
15570
15571			// allows to modify markup
15572			_mfpTrigger('FirstMarkupParse', markup);
15573
15574			if(markup) {
15575				mfp.currTemplate[type] = $(markup);
15576			} else {
15577				// if there is no markup found we just define that template is parsed
15578				mfp.currTemplate[type] = true;
15579			}
15580		}
15581
15582		if(_prevContentType && _prevContentType !== item.type) {
15583			mfp.container.removeClass('mfp-'+_prevContentType+'-holder');
15584		}
15585
15586		var newContent = mfp['get' + type.charAt(0).toUpperCase() + type.slice(1)](item, mfp.currTemplate[type]);
15587		mfp.appendContent(newContent, type);
15588
15589		item.preloaded = true;
15590
15591		_mfpTrigger(CHANGE_EVENT, item);
15592		_prevContentType = item.type;
15593
15594		// Append container back after its content changed
15595		mfp.container.prepend(mfp.contentContainer);
15596
15597		_mfpTrigger('AfterChange');
15598	},
15599
15600
15601	/**
15602	 * Set HTML content of popup
15603	 */
15604	appendContent: function(newContent, type) {
15605		mfp.content = newContent;
15606
15607		if(newContent) {
15608			if(mfp.st.showCloseBtn && mfp.st.closeBtnInside &&
15609				mfp.currTemplate[type] === true) {
15610				// if there is no markup, we just append close button element inside
15611				if(!mfp.content.find('.mfp-close').length) {
15612					mfp.content.append(_getCloseBtn());
15613				}
15614			} else {
15615				mfp.content = newContent;
15616			}
15617		} else {
15618			mfp.content = '';
15619		}
15620
15621		_mfpTrigger(BEFORE_APPEND_EVENT);
15622		mfp.container.addClass('mfp-'+type+'-holder');
15623
15624		mfp.contentContainer.append(mfp.content);
15625	},
15626
15627
15628	/**
15629	 * Creates Magnific Popup data object based on given data
15630	 * @param  {int} index Index of item to parse
15631	 */
15632	parseEl: function(index) {
15633		var item = mfp.items[index],
15634			type;
15635
15636		if(item.tagName) {
15637			item = { el: $(item) };
15638		} else {
15639			type = item.type;
15640			item = { data: item, src: item.src };
15641		}
15642
15643		if(item.el) {
15644			var types = mfp.types;
15645
15646			// check for 'mfp-TYPE' class
15647			for(var i = 0; i < types.length; i++) {
15648				if( item.el.hasClass('mfp-'+types[i]) ) {
15649					type = types[i];
15650					break;
15651				}
15652			}
15653
15654			item.src = item.el.attr('data-mfp-src');
15655			if(!item.src) {
15656				item.src = item.el.attr('href');
15657			}
15658		}
15659
15660		item.type = type || mfp.st.type || 'inline';
15661		item.index = index;
15662		item.parsed = true;
15663		mfp.items[index] = item;
15664		_mfpTrigger('ElementParse', item);
15665
15666		return mfp.items[index];
15667	},
15668
15669
15670	/**
15671	 * Initializes single popup or a group of popups
15672	 */
15673	addGroup: function(el, options) {
15674		var eHandler = function(e) {
15675			e.mfpEl = this;
15676			mfp._openClick(e, el, options);
15677		};
15678
15679		if(!options) {
15680			options = {};
15681		}
15682
15683		var eName = 'click.magnificPopup';
15684		options.mainEl = el;
15685
15686		if(options.items) {
15687			options.isObj = true;
15688			el.off(eName).on(eName, eHandler);
15689		} else {
15690			options.isObj = false;
15691			if(options.delegate) {
15692				el.off(eName).on(eName, options.delegate , eHandler);
15693			} else {
15694				options.items = el;
15695				el.off(eName).on(eName, eHandler);
15696			}
15697		}
15698	},
15699	_openClick: function(e, el, options) {
15700		var midClick = options.midClick !== undefined ? options.midClick : $.magnificPopup.defaults.midClick;
15701
15702
15703		if(!midClick && ( e.which === 2 || e.ctrlKey || e.metaKey || e.altKey || e.shiftKey ) ) {
15704			return;
15705		}
15706
15707		var disableOn = options.disableOn !== undefined ? options.disableOn : $.magnificPopup.defaults.disableOn;
15708
15709		if(disableOn) {
15710			if($.isFunction(disableOn)) {
15711				if( !disableOn.call(mfp) ) {
15712					return true;
15713				}
15714			} else { // else it's number
15715				if( _window.width() < disableOn ) {
15716					return true;
15717				}
15718			}
15719		}
15720
15721		if(e.type) {
15722			e.preventDefault();
15723
15724			// This will prevent popup from closing if element is inside and popup is already opened
15725			if(mfp.isOpen) {
15726				e.stopPropagation();
15727			}
15728		}
15729
15730		options.el = $(e.mfpEl);
15731		if(options.delegate) {
15732			options.items = el.find(options.delegate);
15733		}
15734		mfp.open(options);
15735	},
15736
15737
15738	/**
15739	 * Updates text on preloader
15740	 */
15741	updateStatus: function(status, text) {
15742
15743		if(mfp.preloader) {
15744			if(_prevStatus !== status) {
15745				mfp.container.removeClass('mfp-s-'+_prevStatus);
15746			}
15747
15748			if(!text && status === 'loading') {
15749				text = mfp.st.tLoading;
15750			}
15751
15752			var data = {
15753				status: status,
15754				text: text
15755			};
15756			// allows to modify status
15757			_mfpTrigger('UpdateStatus', data);
15758
15759			status = data.status;
15760			text = data.text;
15761
15762			mfp.preloader.html(text);
15763
15764			mfp.preloader.find('a').on('click', function(e) {
15765				e.stopImmediatePropagation();
15766			});
15767
15768			mfp.container.addClass('mfp-s-'+status);
15769			_prevStatus = status;
15770		}
15771	},
15772
15773
15774	/*
15775		"Private" helpers that aren't private at all
15776	 */
15777	// Check to close popup or not
15778	// "target" is an element that was clicked
15779	_checkIfClose: function(target) {
15780
15781		if($(target).hasClass(PREVENT_CLOSE_CLASS)) {
15782			return;
15783		}
15784
15785		var closeOnContent = mfp.st.closeOnContentClick;
15786		var closeOnBg = mfp.st.closeOnBgClick;
15787
15788		if(closeOnContent && closeOnBg) {
15789			return true;
15790		} else {
15791
15792			// We close the popup if click is on close button or on preloader. Or if there is no content.
15793			if(!mfp.content || $(target).hasClass('mfp-close') || (mfp.preloader && target === mfp.preloader[0]) ) {
15794				return true;
15795			}
15796
15797			// if click is outside the content
15798			if(  (target !== mfp.content[0] && !$.contains(mfp.content[0], target))  ) {
15799				if(closeOnBg) {
15800					// last check, if the clicked element is in DOM, (in case it's removed onclick)
15801					if( $.contains(document, target) ) {
15802						return true;
15803					}
15804				}
15805			} else if(closeOnContent) {
15806				return true;
15807			}
15808
15809		}
15810		return false;
15811	},
15812	_addClassToMFP: function(cName) {
15813		mfp.bgOverlay.addClass(cName);
15814		mfp.wrap.addClass(cName);
15815	},
15816	_removeClassFromMFP: function(cName) {
15817		this.bgOverlay.removeClass(cName);
15818		mfp.wrap.removeClass(cName);
15819	},
15820	_hasScrollBar: function(winHeight) {
15821		return (  (mfp.isIE7 ? _document.height() : document.body.scrollHeight) > (winHeight || _window.height()) );
15822	},
15823	_setFocus: function() {
15824		(mfp.st.focus ? mfp.content.find(mfp.st.focus).eq(0) : mfp.wrap).focus();
15825	},
15826	_onFocusIn: function(e) {
15827		if( e.target !== mfp.wrap[0] && !$.contains(mfp.wrap[0], e.target) ) {
15828			mfp._setFocus();
15829			return false;
15830		}
15831	},
15832	_parseMarkup: function(template, values, item) {
15833		var arr;
15834		if(item.data) {
15835			values = $.extend(item.data, values);
15836		}
15837		_mfpTrigger(MARKUP_PARSE_EVENT, [template, values, item] );
15838
15839		$.each(values, function(key, value) {
15840			if(value === undefined || value === false) {
15841				return true;
15842			}
15843			arr = key.split('_');
15844			if(arr.length > 1) {
15845				var el = template.find(EVENT_NS + '-'+arr[0]);
15846
15847				if(el.length > 0) {
15848					var attr = arr[1];
15849					if(attr === 'replaceWith') {
15850						if(el[0] !== value[0]) {
15851							el.replaceWith(value);
15852						}
15853					} else if(attr === 'img') {
15854						if(el.is('img')) {
15855							el.attr('src', value);
15856						} else {
15857							el.replaceWith( $('<img>').attr('src', value).attr('class', el.attr('class')) );
15858						}
15859					} else {
15860						el.attr(arr[1], value);
15861					}
15862				}
15863
15864			} else {
15865				template.find(EVENT_NS + '-'+key).html(value);
15866			}
15867		});
15868	},
15869
15870	_getScrollbarSize: function() {
15871		// thx David
15872		if(mfp.scrollbarSize === undefined) {
15873			var scrollDiv = document.createElement("div");
15874			scrollDiv.style.cssText = 'width: 99px; height: 99px; overflow: scroll; position: absolute; top: -9999px;';
15875			document.body.appendChild(scrollDiv);
15876			mfp.scrollbarSize = scrollDiv.offsetWidth - scrollDiv.clientWidth;
15877			document.body.removeChild(scrollDiv);
15878		}
15879		return mfp.scrollbarSize;
15880	}
15881
15882}; /* MagnificPopup core prototype end */
15883
15884
15885
15886
15887/**
15888 * Public static functions
15889 */
15890$.magnificPopup = {
15891	instance: null,
15892	proto: MagnificPopup.prototype,
15893	modules: [],
15894
15895	open: function(options, index) {
15896		_checkInstance();
15897
15898		if(!options) {
15899			options = {};
15900		} else {
15901			options = $.extend(true, {}, options);
15902		}
15903
15904		options.isObj = true;
15905		options.index = index || 0;
15906		return this.instance.open(options);
15907	},
15908
15909	close: function() {
15910		return $.magnificPopup.instance && $.magnificPopup.instance.close();
15911	},
15912
15913	registerModule: function(name, module) {
15914		if(module.options) {
15915			$.magnificPopup.defaults[name] = module.options;
15916		}
15917		$.extend(this.proto, module.proto);
15918		this.modules.push(name);
15919	},
15920
15921	defaults: {
15922
15923		// Info about options is in docs:
15924		// http://dimsemenov.com/plugins/magnific-popup/documentation.html#options
15925
15926		disableOn: 0,
15927
15928		key: null,
15929
15930		midClick: false,
15931
15932		mainClass: '',
15933
15934		preloader: true,
15935
15936		focus: '', // CSS selector of input to focus after popup is opened
15937
15938		closeOnContentClick: false,
15939
15940		closeOnBgClick: true,
15941
15942		closeBtnInside: true,
15943
15944		showCloseBtn: true,
15945
15946		enableEscapeKey: true,
15947
15948		modal: false,
15949
15950		alignTop: false,
15951
15952		removalDelay: 0,
15953
15954		prependTo: null,
15955
15956		fixedContentPos: 'auto',
15957
15958		fixedBgPos: 'auto',
15959
15960		overflowY: 'auto',
15961
15962		closeMarkup: '<button title="%title%" type="button" class="mfp-close">&#215;</button>',
15963
15964		tClose: 'Close (Esc)',
15965
15966		tLoading: 'Loading...',
15967
15968		autoFocusLast: true
15969
15970	}
15971};
15972
15973
15974
15975$.fn.magnificPopup = function(options) {
15976	_checkInstance();
15977
15978	var jqEl = $(this);
15979
15980	// We call some API method of first param is a string
15981	if (typeof options === "string" ) {
15982
15983		if(options === 'open') {
15984			var items,
15985				itemOpts = _isJQ ? jqEl.data('magnificPopup') : jqEl[0].magnificPopup,
15986				index = parseInt(arguments[1], 10) || 0;
15987
15988			if(itemOpts.items) {
15989				items = itemOpts.items[index];
15990			} else {
15991				items = jqEl;
15992				if(itemOpts.delegate) {
15993					items = items.find(itemOpts.delegate);
15994				}
15995				items = items.eq( index );
15996			}
15997			mfp._openClick({mfpEl:items}, jqEl, itemOpts);
15998		} else {
15999			if(mfp.isOpen)
16000				mfp[options].apply(mfp, Array.prototype.slice.call(arguments, 1));
16001		}
16002
16003	} else {
16004		// clone options obj
16005		options = $.extend(true, {}, options);
16006
16007		/*
16008		 * As Zepto doesn't support .data() method for objects
16009		 * and it works only in normal browsers
16010		 * we assign "options" object directly to the DOM element. FTW!
16011		 */
16012		if(_isJQ) {
16013			jqEl.data('magnificPopup', options);
16014		} else {
16015			jqEl[0].magnificPopup = options;
16016		}
16017
16018		mfp.addGroup(jqEl, options);
16019
16020	}
16021	return jqEl;
16022};
16023
16024/*>>core*/
16025
16026/*>>inline*/
16027
16028var INLINE_NS = 'inline',
16029	_hiddenClass,
16030	_inlinePlaceholder,
16031	_lastInlineElement,
16032	_putInlineElementsBack = function() {
16033		if(_lastInlineElement) {
16034			_inlinePlaceholder.after( _lastInlineElement.addClass(_hiddenClass) ).detach();
16035			_lastInlineElement = null;
16036		}
16037	};
16038
16039$.magnificPopup.registerModule(INLINE_NS, {
16040	options: {
16041		hiddenClass: 'hide', // will be appended with `mfp-` prefix
16042		markup: '',
16043		tNotFound: 'Content not found'
16044	},
16045	proto: {
16046
16047		initInline: function() {
16048			mfp.types.push(INLINE_NS);
16049
16050			_mfpOn(CLOSE_EVENT+'.'+INLINE_NS, function() {
16051				_putInlineElementsBack();
16052			});
16053		},
16054
16055		getInline: function(item, template) {
16056
16057			_putInlineElementsBack();
16058
16059			if(item.src) {
16060				var inlineSt = mfp.st.inline,
16061					el = $(item.src);
16062
16063				if(el.length) {
16064
16065					// If target element has parent - we replace it with placeholder and put it back after popup is closed
16066					var parent = el[0].parentNode;
16067					if(parent && parent.tagName) {
16068						if(!_inlinePlaceholder) {
16069							_hiddenClass = inlineSt.hiddenClass;
16070							_inlinePlaceholder = _getEl(_hiddenClass);
16071							_hiddenClass = 'mfp-'+_hiddenClass;
16072						}
16073						// replace target inline element with placeholder
16074						_lastInlineElement = el.after(_inlinePlaceholder).detach().removeClass(_hiddenClass);
16075					}
16076
16077					mfp.updateStatus('ready');
16078				} else {
16079					mfp.updateStatus('error', inlineSt.tNotFound);
16080					el = $('<div>');
16081				}
16082
16083				item.inlineElement = el;
16084				return el;
16085			}
16086
16087			mfp.updateStatus('ready');
16088			mfp._parseMarkup(template, {}, item);
16089			return template;
16090		}
16091	}
16092});
16093
16094/*>>inline*/
16095
16096/*>>ajax*/
16097var AJAX_NS = 'ajax',
16098	_ajaxCur,
16099	_removeAjaxCursor = function() {
16100		if(_ajaxCur) {
16101			$(document.body).removeClass(_ajaxCur);
16102		}
16103	},
16104	_destroyAjaxRequest = function() {
16105		_removeAjaxCursor();
16106		if(mfp.req) {
16107			mfp.req.abort();
16108		}
16109	};
16110
16111$.magnificPopup.registerModule(AJAX_NS, {
16112
16113	options: {
16114		settings: null,
16115		cursor: 'mfp-ajax-cur',
16116		tError: '<a href="%url%">The content</a> could not be loaded.'
16117	},
16118
16119	proto: {
16120		initAjax: function() {
16121			mfp.types.push(AJAX_NS);
16122			_ajaxCur = mfp.st.ajax.cursor;
16123
16124			_mfpOn(CLOSE_EVENT+'.'+AJAX_NS, _destroyAjaxRequest);
16125			_mfpOn('BeforeChange.' + AJAX_NS, _destroyAjaxRequest);
16126		},
16127		getAjax: function(item) {
16128
16129			if(_ajaxCur) {
16130				$(document.body).addClass(_ajaxCur);
16131			}
16132
16133			mfp.updateStatus('loading');
16134
16135			var opts = $.extend({
16136				url: item.src,
16137				success: function(data, textStatus, jqXHR) {
16138					var temp = {
16139						data:data,
16140						xhr:jqXHR
16141					};
16142
16143					_mfpTrigger('ParseAjax', temp);
16144
16145					mfp.appendContent( $(temp.data), AJAX_NS );
16146
16147					item.finished = true;
16148
16149					_removeAjaxCursor();
16150
16151					mfp._setFocus();
16152
16153					setTimeout(function() {
16154						mfp.wrap.addClass(READY_CLASS);
16155					}, 16);
16156
16157					mfp.updateStatus('ready');
16158
16159					_mfpTrigger('AjaxContentAdded');
16160				},
16161				error: function() {
16162					_removeAjaxCursor();
16163					item.finished = item.loadError = true;
16164					mfp.updateStatus('error', mfp.st.ajax.tError.replace('%url%', item.src));
16165				}
16166			}, mfp.st.ajax.settings);
16167
16168			mfp.req = $.ajax(opts);
16169
16170			return '';
16171		}
16172	}
16173});
16174
16175/*>>ajax*/
16176
16177/*>>image*/
16178var _imgInterval,
16179	_getTitle = function(item) {
16180		if(item.data && item.data.title !== undefined)
16181			return item.data.title;
16182
16183		var src = mfp.st.image.titleSrc;
16184
16185		if(src) {
16186			if($.isFunction(src)) {
16187				return src.call(mfp, item);
16188			} else if(item.el) {
16189				return item.el.attr(src) || '';
16190			}
16191		}
16192		return '';
16193	};
16194
16195$.magnificPopup.registerModule('image', {
16196
16197	options: {
16198		markup: '<div class="mfp-figure">'+
16199					'<div class="mfp-close"></div>'+
16200					'<figure>'+
16201						'<div class="mfp-img"></div>'+
16202						'<figcaption>'+
16203							'<div class="mfp-bottom-bar">'+
16204								'<div class="mfp-title"></div>'+
16205								'<div class="mfp-counter"></div>'+
16206							'</div>'+
16207						'</figcaption>'+
16208					'</figure>'+
16209				'</div>',
16210		cursor: 'mfp-zoom-out-cur',
16211		titleSrc: 'title',
16212		verticalFit: true,
16213		tError: '<a href="%url%">The image</a> could not be loaded.'
16214	},
16215
16216	proto: {
16217		initImage: function() {
16218			var imgSt = mfp.st.image,
16219				ns = '.image';
16220
16221			mfp.types.push('image');
16222
16223			_mfpOn(OPEN_EVENT+ns, function() {
16224				if(mfp.currItem.type === 'image' && imgSt.cursor) {
16225					$(document.body).addClass(imgSt.cursor);
16226				}
16227			});
16228
16229			_mfpOn(CLOSE_EVENT+ns, function() {
16230				if(imgSt.cursor) {
16231					$(document.body).removeClass(imgSt.cursor);
16232				}
16233				_window.off('resize' + EVENT_NS);
16234			});
16235
16236			_mfpOn('Resize'+ns, mfp.resizeImage);
16237			if(mfp.isLowIE) {
16238				_mfpOn('AfterChange', mfp.resizeImage);
16239			}
16240		},
16241		resizeImage: function() {
16242			var item = mfp.currItem;
16243			if(!item || !item.img) return;
16244
16245			if(mfp.st.image.verticalFit) {
16246				var decr = 0;
16247				// fix box-sizing in ie7/8
16248				if(mfp.isLowIE) {
16249					decr = parseInt(item.img.css('padding-top'), 10) + parseInt(item.img.css('padding-bottom'),10);
16250				}
16251				item.img.css('max-height', mfp.wH-decr);
16252			}
16253		},
16254		_onImageHasSize: function(item) {
16255			if(item.img) {
16256
16257				item.hasSize = true;
16258
16259				if(_imgInterval) {
16260					clearInterval(_imgInterval);
16261				}
16262
16263				item.isCheckingImgSize = false;
16264
16265				_mfpTrigger('ImageHasSize', item);
16266
16267				if(item.imgHidden) {
16268					if(mfp.content)
16269						mfp.content.removeClass('mfp-loading');
16270
16271					item.imgHidden = false;
16272				}
16273
16274			}
16275		},
16276
16277		/**
16278		 * Function that loops until the image has size to display elements that rely on it asap
16279		 */
16280		findImageSize: function(item) {
16281
16282			var counter = 0,
16283				img = item.img[0],
16284				mfpSetInterval = function(delay) {
16285
16286					if(_imgInterval) {
16287						clearInterval(_imgInterval);
16288					}
16289					// decelerating interval that checks for size of an image
16290					_imgInterval = setInterval(function() {
16291						if(img.naturalWidth > 0) {
16292							mfp._onImageHasSize(item);
16293							return;
16294						}
16295
16296						if(counter > 200) {
16297							clearInterval(_imgInterval);
16298						}
16299
16300						counter++;
16301						if(counter === 3) {
16302							mfpSetInterval(10);
16303						} else if(counter === 40) {
16304							mfpSetInterval(50);
16305						} else if(counter === 100) {
16306							mfpSetInterval(500);
16307						}
16308					}, delay);
16309				};
16310
16311			mfpSetInterval(1);
16312		},
16313
16314		getImage: function(item, template) {
16315
16316			var guard = 0,
16317
16318				// image load complete handler
16319				onLoadComplete = function() {
16320					if(item) {
16321						if (item.img[0].complete) {
16322							item.img.off('.mfploader');
16323
16324							if(item === mfp.currItem){
16325								mfp._onImageHasSize(item);
16326
16327								mfp.updateStatus('ready');
16328							}
16329
16330							item.hasSize = true;
16331							item.loaded = true;
16332
16333							_mfpTrigger('ImageLoadComplete');
16334
16335						}
16336						else {
16337							// if image complete check fails 200 times (20 sec), we assume that there was an error.
16338							guard++;
16339							if(guard < 200) {
16340								setTimeout(onLoadComplete,100);
16341							} else {
16342								onLoadError();
16343							}
16344						}
16345					}
16346				},
16347
16348				// image error handler
16349				onLoadError = function() {
16350					if(item) {
16351						item.img.off('.mfploader');
16352						if(item === mfp.currItem){
16353							mfp._onImageHasSize(item);
16354							mfp.updateStatus('error', imgSt.tError.replace('%url%', item.src) );
16355						}
16356
16357						item.hasSize = true;
16358						item.loaded = true;
16359						item.loadError = true;
16360					}
16361				},
16362				imgSt = mfp.st.image;
16363
16364
16365			var el = template.find('.mfp-img');
16366			if(el.length) {
16367				var img = document.createElement('img');
16368				img.className = 'mfp-img';
16369				if(item.el && item.el.find('img').length) {
16370					img.alt = item.el.find('img').attr('alt');
16371				}
16372				item.img = $(img).on('load.mfploader', onLoadComplete).on('error.mfploader', onLoadError);
16373				img.src = item.src;
16374
16375				// without clone() "error" event is not firing when IMG is replaced by new IMG
16376				// TODO: find a way to avoid such cloning
16377				if(el.is('img')) {
16378					item.img = item.img.clone();
16379				}
16380
16381				img = item.img[0];
16382				if(img.naturalWidth > 0) {
16383					item.hasSize = true;
16384				} else if(!img.width) {
16385					item.hasSize = false;
16386				}
16387			}
16388
16389			mfp._parseMarkup(template, {
16390				title: _getTitle(item),
16391				img_replaceWith: item.img
16392			}, item);
16393
16394			mfp.resizeImage();
16395
16396			if(item.hasSize) {
16397				if(_imgInterval) clearInterval(_imgInterval);
16398
16399				if(item.loadError) {
16400					template.addClass('mfp-loading');
16401					mfp.updateStatus('error', imgSt.tError.replace('%url%', item.src) );
16402				} else {
16403					template.removeClass('mfp-loading');
16404					mfp.updateStatus('ready');
16405				}
16406				return template;
16407			}
16408
16409			mfp.updateStatus('loading');
16410			item.loading = true;
16411
16412			if(!item.hasSize) {
16413				item.imgHidden = true;
16414				template.addClass('mfp-loading');
16415				mfp.findImageSize(item);
16416			}
16417
16418			return template;
16419		}
16420	}
16421});
16422
16423/*>>image*/
16424
16425/*>>zoom*/
16426var hasMozTransform,
16427	getHasMozTransform = function() {
16428		if(hasMozTransform === undefined) {
16429			hasMozTransform = document.createElement('p').style.MozTransform !== undefined;
16430		}
16431		return hasMozTransform;
16432	};
16433
16434$.magnificPopup.registerModule('zoom', {
16435
16436	options: {
16437		enabled: false,
16438		easing: 'ease-in-out',
16439		duration: 300,
16440		opener: function(element) {
16441			return element.is('img') ? element : element.find('img');
16442		}
16443	},
16444
16445	proto: {
16446
16447		initZoom: function() {
16448			var zoomSt = mfp.st.zoom,
16449				ns = '.zoom',
16450				image;
16451
16452			if(!zoomSt.enabled || !mfp.supportsTransition) {
16453				return;
16454			}
16455
16456			var duration = zoomSt.duration,
16457				getElToAnimate = function(image) {
16458					var newImg = image.clone().removeAttr('style').removeAttr('class').addClass('mfp-animated-image'),
16459						transition = 'all '+(zoomSt.duration/1000)+'s ' + zoomSt.easing,
16460						cssObj = {
16461							position: 'fixed',
16462							zIndex: 9999,
16463							left: 0,
16464							top: 0,
16465							'-webkit-backface-visibility': 'hidden'
16466						},
16467						t = 'transition';
16468
16469					cssObj['-webkit-'+t] = cssObj['-moz-'+t] = cssObj['-o-'+t] = cssObj[t] = transition;
16470
16471					newImg.css(cssObj);
16472					return newImg;
16473				},
16474				showMainContent = function() {
16475					mfp.content.css('visibility', 'visible');
16476				},
16477				openTimeout,
16478				animatedImg;
16479
16480			_mfpOn('BuildControls'+ns, function() {
16481				if(mfp._allowZoom()) {
16482
16483					clearTimeout(openTimeout);
16484					mfp.content.css('visibility', 'hidden');
16485
16486					// Basically, all code below does is clones existing image, puts in on top of the current one and animated it
16487
16488					image = mfp._getItemToZoom();
16489
16490					if(!image) {
16491						showMainContent();
16492						return;
16493					}
16494
16495					animatedImg = getElToAnimate(image);
16496
16497					animatedImg.css( mfp._getOffset() );
16498
16499					mfp.wrap.append(animatedImg);
16500
16501					openTimeout = setTimeout(function() {
16502						animatedImg.css( mfp._getOffset( true ) );
16503						openTimeout = setTimeout(function() {
16504
16505							showMainContent();
16506
16507							setTimeout(function() {
16508								animatedImg.remove();
16509								image = animatedImg = null;
16510								_mfpTrigger('ZoomAnimationEnded');
16511							}, 16); // avoid blink when switching images
16512
16513						}, duration); // this timeout equals animation duration
16514
16515					}, 16); // by adding this timeout we avoid short glitch at the beginning of animation
16516
16517
16518					// Lots of timeouts...
16519				}
16520			});
16521			_mfpOn(BEFORE_CLOSE_EVENT+ns, function() {
16522				if(mfp._allowZoom()) {
16523
16524					clearTimeout(openTimeout);
16525
16526					mfp.st.removalDelay = duration;
16527
16528					if(!image) {
16529						image = mfp._getItemToZoom();
16530						if(!image) {
16531							return;
16532						}
16533						animatedImg = getElToAnimate(image);
16534					}
16535
16536					animatedImg.css( mfp._getOffset(true) );
16537					mfp.wrap.append(animatedImg);
16538					mfp.content.css('visibility', 'hidden');
16539
16540					setTimeout(function() {
16541						animatedImg.css( mfp._getOffset() );
16542					}, 16);
16543				}
16544
16545			});
16546
16547			_mfpOn(CLOSE_EVENT+ns, function() {
16548				if(mfp._allowZoom()) {
16549					showMainContent();
16550					if(animatedImg) {
16551						animatedImg.remove();
16552					}
16553					image = null;
16554				}
16555			});
16556		},
16557
16558		_allowZoom: function() {
16559			return mfp.currItem.type === 'image';
16560		},
16561
16562		_getItemToZoom: function() {
16563			if(mfp.currItem.hasSize) {
16564				return mfp.currItem.img;
16565			} else {
16566				return false;
16567			}
16568		},
16569
16570		// Get element postion relative to viewport
16571		_getOffset: function(isLarge) {
16572			var el;
16573			if(isLarge) {
16574				el = mfp.currItem.img;
16575			} else {
16576				el = mfp.st.zoom.opener(mfp.currItem.el || mfp.currItem);
16577			}
16578
16579			var offset = el.offset();
16580			var paddingTop = parseInt(el.css('padding-top'),10);
16581			var paddingBottom = parseInt(el.css('padding-bottom'),10);
16582			offset.top -= ( $(window).scrollTop() - paddingTop );
16583
16584
16585			/*
16586
16587			Animating left + top + width/height looks glitchy in Firefox, but perfect in Chrome. And vice-versa.
16588
16589			 */
16590			var obj = {
16591				width: el.width(),
16592				// fix Zepto height+padding issue
16593				height: (_isJQ ? el.innerHeight() : el[0].offsetHeight) - paddingBottom - paddingTop
16594			};
16595
16596			// I hate to do this, but there is no another option
16597			if( getHasMozTransform() ) {
16598				obj['-moz-transform'] = obj['transform'] = 'translate(' + offset.left + 'px,' + offset.top + 'px)';
16599			} else {
16600				obj.left = offset.left;
16601				obj.top = offset.top;
16602			}
16603			return obj;
16604		}
16605
16606	}
16607});
16608
16609
16610
16611/*>>zoom*/
16612
16613/*>>iframe*/
16614
16615var IFRAME_NS = 'iframe',
16616	_emptyPage = '//about:blank',
16617
16618	_fixIframeBugs = function(isShowing) {
16619		if(mfp.currTemplate[IFRAME_NS]) {
16620			var el = mfp.currTemplate[IFRAME_NS].find('iframe');
16621			if(el.length) {
16622				// reset src after the popup is closed to avoid "video keeps playing after popup is closed" bug
16623				if(!isShowing) {
16624					el[0].src = _emptyPage;
16625				}
16626
16627				// IE8 black screen bug fix
16628				if(mfp.isIE8) {
16629					el.css('display', isShowing ? 'block' : 'none');
16630				}
16631			}
16632		}
16633	};
16634
16635$.magnificPopup.registerModule(IFRAME_NS, {
16636
16637	options: {
16638		markup: '<div class="mfp-iframe-scaler">'+
16639					'<div class="mfp-close"></div>'+
16640					'<iframe class="mfp-iframe" src="//about:blank" frameborder="0" allowfullscreen></iframe>'+
16641				'</div>',
16642
16643		srcAction: 'iframe_src',
16644
16645		// we don't care and support only one default type of URL by default
16646		patterns: {
16647			youtube: {
16648				index: 'youtube.com',
16649				id: 'v=',
16650				src: '//www.youtube.com/embed/%id%?autoplay=1'
16651			},
16652			vimeo: {
16653				index: 'vimeo.com/',
16654				id: '/',
16655				src: '//player.vimeo.com/video/%id%?autoplay=1'
16656			},
16657			gmaps: {
16658				index: '//maps.google.',
16659				src: '%id%&output=embed'
16660			}
16661		}
16662	},
16663
16664	proto: {
16665		initIframe: function() {
16666			mfp.types.push(IFRAME_NS);
16667
16668			_mfpOn('BeforeChange', function(e, prevType, newType) {
16669				if(prevType !== newType) {
16670					if(prevType === IFRAME_NS) {
16671						_fixIframeBugs(); // iframe if removed
16672					} else if(newType === IFRAME_NS) {
16673						_fixIframeBugs(true); // iframe is showing
16674					}
16675				}// else {
16676					// iframe source is switched, don't do anything
16677				//}
16678			});
16679
16680			_mfpOn(CLOSE_EVENT + '.' + IFRAME_NS, function() {
16681				_fixIframeBugs();
16682			});
16683		},
16684
16685		getIframe: function(item, template) {
16686			var embedSrc = item.src;
16687			var iframeSt = mfp.st.iframe;
16688
16689			$.each(iframeSt.patterns, function() {
16690				if(embedSrc.indexOf( this.index ) > -1) {
16691					if(this.id) {
16692						if(typeof this.id === 'string') {
16693							embedSrc = embedSrc.substr(embedSrc.lastIndexOf(this.id)+this.id.length, embedSrc.length);
16694						} else {
16695							embedSrc = this.id.call( this, embedSrc );
16696						}
16697					}
16698					embedSrc = this.src.replace('%id%', embedSrc );
16699					return false; // break;
16700				}
16701			});
16702
16703			var dataObj = {};
16704			if(iframeSt.srcAction) {
16705				dataObj[iframeSt.srcAction] = embedSrc;
16706			}
16707			mfp._parseMarkup(template, dataObj, item);
16708
16709			mfp.updateStatus('ready');
16710
16711			return template;
16712		}
16713	}
16714});
16715
16716
16717
16718/*>>iframe*/
16719
16720/*>>gallery*/
16721/**
16722 * Get looped index depending on number of slides
16723 */
16724var _getLoopedId = function(index) {
16725		var numSlides = mfp.items.length;
16726		if(index > numSlides - 1) {
16727			return index - numSlides;
16728		} else  if(index < 0) {
16729			return numSlides + index;
16730		}
16731		return index;
16732	},
16733	_replaceCurrTotal = function(text, curr, total) {
16734		return text.replace(/%curr%/gi, curr + 1).replace(/%total%/gi, total);
16735	};
16736
16737$.magnificPopup.registerModule('gallery', {
16738
16739	options: {
16740		enabled: false,
16741		arrowMarkup: '<button title="%title%" type="button" class="mfp-arrow mfp-arrow-%dir%"></button>',
16742		preload: [0,2],
16743		navigateByImgClick: true,
16744		arrows: true,
16745
16746		tPrev: 'Previous (Left arrow key)',
16747		tNext: 'Next (Right arrow key)',
16748		tCounter: '%curr% of %total%'
16749	},
16750
16751	proto: {
16752		initGallery: function() {
16753
16754			var gSt = mfp.st.gallery,
16755				ns = '.mfp-gallery';
16756
16757			mfp.direction = true; // true - next, false - prev
16758
16759			if(!gSt || !gSt.enabled ) return false;
16760
16761			_wrapClasses += ' mfp-gallery';
16762
16763			_mfpOn(OPEN_EVENT+ns, function() {
16764
16765				if(gSt.navigateByImgClick) {
16766					mfp.wrap.on('click'+ns, '.mfp-img', function() {
16767						if(mfp.items.length > 1) {
16768							mfp.next();
16769							return false;
16770						}
16771					});
16772				}
16773
16774				_document.on('keydown'+ns, function(e) {
16775					if (e.keyCode === 37) {
16776						mfp.prev();
16777					} else if (e.keyCode === 39) {
16778						mfp.next();
16779					}
16780				});
16781			});
16782
16783			_mfpOn('UpdateStatus'+ns, function(e, data) {
16784				if(data.text) {
16785					data.text = _replaceCurrTotal(data.text, mfp.currItem.index, mfp.items.length);
16786				}
16787			});
16788
16789			_mfpOn(MARKUP_PARSE_EVENT+ns, function(e, element, values, item) {
16790				var l = mfp.items.length;
16791				values.counter = l > 1 ? _replaceCurrTotal(gSt.tCounter, item.index, l) : '';
16792			});
16793
16794			_mfpOn('BuildControls' + ns, function() {
16795				if(mfp.items.length > 1 && gSt.arrows && !mfp.arrowLeft) {
16796					var markup = gSt.arrowMarkup,
16797						arrowLeft = mfp.arrowLeft = $( markup.replace(/%title%/gi, gSt.tPrev).replace(/%dir%/gi, 'left') ).addClass(PREVENT_CLOSE_CLASS),
16798						arrowRight = mfp.arrowRight = $( markup.replace(/%title%/gi, gSt.tNext).replace(/%dir%/gi, 'right') ).addClass(PREVENT_CLOSE_CLASS);
16799
16800					arrowLeft.click(function() {
16801						mfp.prev();
16802					});
16803					arrowRight.click(function() {
16804						mfp.next();
16805					});
16806
16807					mfp.container.append(arrowLeft.add(arrowRight));
16808				}
16809			});
16810
16811			_mfpOn(CHANGE_EVENT+ns, function() {
16812				if(mfp._preloadTimeout) clearTimeout(mfp._preloadTimeout);
16813
16814				mfp._preloadTimeout = setTimeout(function() {
16815					mfp.preloadNearbyImages();
16816					mfp._preloadTimeout = null;
16817				}, 16);
16818			});
16819
16820
16821			_mfpOn(CLOSE_EVENT+ns, function() {
16822				_document.off(ns);
16823				mfp.wrap.off('click'+ns);
16824				mfp.arrowRight = mfp.arrowLeft = null;
16825			});
16826
16827		},
16828		next: function() {
16829			mfp.direction = true;
16830			mfp.index = _getLoopedId(mfp.index + 1);
16831			mfp.updateItemHTML();
16832		},
16833		prev: function() {
16834			mfp.direction = false;
16835			mfp.index = _getLoopedId(mfp.index - 1);
16836			mfp.updateItemHTML();
16837		},
16838		goTo: function(newIndex) {
16839			mfp.direction = (newIndex >= mfp.index);
16840			mfp.index = newIndex;
16841			mfp.updateItemHTML();
16842		},
16843		preloadNearbyImages: function() {
16844			var p = mfp.st.gallery.preload,
16845				preloadBefore = Math.min(p[0], mfp.items.length),
16846				preloadAfter = Math.min(p[1], mfp.items.length),
16847				i;
16848
16849			for(i = 1; i <= (mfp.direction ? preloadAfter : preloadBefore); i++) {
16850				mfp._preloadItem(mfp.index+i);
16851			}
16852			for(i = 1; i <= (mfp.direction ? preloadBefore : preloadAfter); i++) {
16853				mfp._preloadItem(mfp.index-i);
16854			}
16855		},
16856		_preloadItem: function(index) {
16857			index = _getLoopedId(index);
16858
16859			if(mfp.items[index].preloaded) {
16860				return;
16861			}
16862
16863			var item = mfp.items[index];
16864			if(!item.parsed) {
16865				item = mfp.parseEl( index );
16866			}
16867
16868			_mfpTrigger('LazyLoad', item);
16869
16870			if(item.type === 'image') {
16871				item.img = $('<img class="mfp-img" />').on('load.mfploader', function() {
16872					item.hasSize = true;
16873				}).on('error.mfploader', function() {
16874					item.hasSize = true;
16875					item.loadError = true;
16876					_mfpTrigger('LazyLoadError', item);
16877				}).attr('src', item.src);
16878			}
16879
16880
16881			item.preloaded = true;
16882		}
16883	}
16884});
16885
16886/*>>gallery*/
16887
16888/*>>retina*/
16889
16890var RETINA_NS = 'retina';
16891
16892$.magnificPopup.registerModule(RETINA_NS, {
16893	options: {
16894		replaceSrc: function(item) {
16895			return item.src.replace(/\.\w+$/, function(m) { return '@2x' + m; });
16896		},
16897		ratio: 1 // Function or number.  Set to 1 to disable.
16898	},
16899	proto: {
16900		initRetina: function() {
16901			if(window.devicePixelRatio > 1) {
16902
16903				var st = mfp.st.retina,
16904					ratio = st.ratio;
16905
16906				ratio = !isNaN(ratio) ? ratio : ratio();
16907
16908				if(ratio > 1) {
16909					_mfpOn('ImageHasSize' + '.' + RETINA_NS, function(e, item) {
16910						item.img.css({
16911							'max-width': item.img[0].naturalWidth / ratio,
16912							'width': '100%'
16913						});
16914					});
16915					_mfpOn('ElementParse' + '.' + RETINA_NS, function(e, item) {
16916						item.src = st.replaceSrc(item, ratio);
16917					});
16918				}
16919			}
16920
16921		}
16922	}
16923});
16924
16925/*>>retina*/
16926 _checkInstance(); }));
16927/* WEBPACK VAR INJECTION */}.call(exports, __webpack_require__(0)))
16928
16929/***/ }),
16930/* 24 */
vendor: 3,292 bytes, lines 16931-17054
16931/***/ (function(module, exports) {
16932
16933/**
16934 * EvEmitter v2.1.1
16935 * Lil' event emitter
16936 * MIT License
16937 */
16938
16939( function( global, factory ) {
16940  // universal module definition
16941  if ( typeof module == 'object' && module.exports ) {
16942    // CommonJS - Browserify, Webpack
16943    module.exports = factory();
16944  } else {
16945    // Browser globals
16946    global.EvEmitter = factory();
16947  }
16948
16949}( typeof window != 'undefined' ? window : this, function() {
16950
16951function EvEmitter() {}
16952
16953let proto = EvEmitter.prototype;
16954
16955proto.on = function( eventName, listener ) {
16956  if ( !eventName || !listener ) return this;
16957
16958  // set events hash
16959  let events = this._events = this._events || {};
16960  // set listeners array
16961  let listeners = events[ eventName ] = events[ eventName ] || [];
16962  // only add once
16963  if ( !listeners.includes( listener ) ) {
16964    listeners.push( listener );
16965  }
16966
16967  return this;
16968};
16969
16970proto.once = function( eventName, listener ) {
16971  if ( !eventName || !listener ) return this;
16972
16973  // add event
16974  this.on( eventName, listener );
16975  // set once flag
16976  // set onceEvents hash
16977  let onceEvents = this._onceEvents = this._onceEvents || {};
16978  // set onceListeners object
16979  let onceListeners = onceEvents[ eventName ] = onceEvents[ eventName ] || {};
16980  // set flag
16981  onceListeners[ listener ] = true;
16982
16983  return this;
16984};
16985
16986proto.off = function( eventName, listener ) {
16987  let listeners = this._events && this._events[ eventName ];
16988  if ( !listeners || !listeners.length ) return this;
16989
16990  let index = listeners.indexOf( listener );
16991  if ( index != -1 ) {
16992    listeners.splice( index, 1 );
16993  }
16994
16995  return this;
16996};
16997
16998proto.emitEvent = function( eventName, args ) {
16999  let listeners = this._events && this._events[ eventName ];
17000  if ( !listeners || !listeners.length ) return this;
17001
17002  // copy over to avoid interference if .off() in listener
17003  listeners = listeners.slice( 0 );
17004  args = args || [];
17005  // once stuff
17006  let onceListeners = this._onceEvents && this._onceEvents[ eventName ];
17007
17008  for ( let listener of listeners ) {
17009    let isOnce = onceListeners && onceListeners[ listener ];
17010    if ( isOnce ) {
17011      // remove listener
17012      // remove before trigger to prevent recursion
17013      this.off( eventName, listener );
17014      // unset once flag
17015      delete onceListeners[ listener ];
17016    }
17017    // trigger listener
17018    listener.apply( this, args );
17019  }
17020
17021  return this;
17022};
17023
17024proto.allOff = function() {
17025  delete this._events;
17026  delete this._onceEvents;
17027  return this;
17028};
17029
17030return EvEmitter;
17031
17032} ) );
17033
17034
17035/***/ }),
17036/* 25 */
17037/***/ (function(module, exports, __webpack_require__) {
17038
17039var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/**
17040 * Outlayer Item
17041 */
17042
17043( function( window, factory ) {
17044  // universal module definition
17045  /* jshint strict: false */ /* globals define, module, require */
17046  if ( true ) {
17047    // AMD - RequireJS
17048    !(__WEBPACK_AMD_DEFINE_ARRAY__ = [
17049        __webpack_require__(11),
17050        __webpack_require__(3)
17051      ], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
17052				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
17053				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
17054				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__)
vendor: 14,212 bytes, lines 17054-17594
17054);
17055  } else if ( typeof module == 'object' && module.exports ) {
17056    // CommonJS - Browserify, Webpack
17057    module.exports = factory(
17058      require('ev-emitter'),
17059      require('get-size')
17060    );
17061  } else {
17062    // browser global
17063    window.Outlayer = {};
17064    window.Outlayer.Item = factory(
17065      window.EvEmitter,
17066      window.getSize
17067    );
17068  }
17069
17070}( window, function factory( EvEmitter, getSize ) {
17071'use strict';
17072
17073// ----- helpers ----- //
17074
17075function isEmptyObj( obj ) {
17076  for ( var prop in obj ) {
17077    return false;
17078  }
17079  prop = null;
17080  return true;
17081}
17082
17083// -------------------------- CSS3 support -------------------------- //
17084
17085
17086var docElemStyle = document.documentElement.style;
17087
17088var transitionProperty = typeof docElemStyle.transition == 'string' ?
17089  'transition' : 'WebkitTransition';
17090var transformProperty = typeof docElemStyle.transform == 'string' ?
17091  'transform' : 'WebkitTransform';
17092
17093var transitionEndEvent = {
17094  WebkitTransition: 'webkitTransitionEnd',
17095  transition: 'transitionend'
17096}[ transitionProperty ];
17097
17098// cache all vendor properties that could have vendor prefix
17099var vendorProperties = {
17100  transform: transformProperty,
17101  transition: transitionProperty,
17102  transitionDuration: transitionProperty + 'Duration',
17103  transitionProperty: transitionProperty + 'Property',
17104  transitionDelay: transitionProperty + 'Delay'
17105};
17106
17107// -------------------------- Item -------------------------- //
17108
17109function Item( element, layout ) {
17110  if ( !element ) {
17111    return;
17112  }
17113
17114  this.element = element;
17115  // parent layout class, i.e. Masonry, Isotope, or Packery
17116  this.layout = layout;
17117  this.position = {
17118    x: 0,
17119    y: 0
17120  };
17121
17122  this._create();
17123}
17124
17125// inherit EvEmitter
17126var proto = Item.prototype = Object.create( EvEmitter.prototype );
17127proto.constructor = Item;
17128
17129proto._create = function() {
17130  // transition objects
17131  this._transn = {
17132    ingProperties: {},
17133    clean: {},
17134    onEnd: {}
17135  };
17136
17137  this.css({
17138    position: 'absolute'
17139  });
17140};
17141
17142// trigger specified handler for event type
17143proto.handleEvent = function( event ) {
17144  var method = 'on' + event.type;
17145  if ( this[ method ] ) {
17146    this[ method ]( event );
17147  }
17148};
17149
17150proto.getSize = function() {
17151  this.size = getSize( this.element );
17152};
17153
17154/**
17155 * apply CSS styles to element
17156 * @param {Object} style
17157 */
17158proto.css = function( style ) {
17159  var elemStyle = this.element.style;
17160
17161  for ( var prop in style ) {
17162    // use vendor property if available
17163    var supportedProp = vendorProperties[ prop ] || prop;
17164    elemStyle[ supportedProp ] = style[ prop ];
17165  }
17166};
17167
17168 // measure position, and sets it
17169proto.getPosition = function() {
17170  var style = getComputedStyle( this.element );
17171  var isOriginLeft = this.layout._getOption('originLeft');
17172  var isOriginTop = this.layout._getOption('originTop');
17173  var xValue = style[ isOriginLeft ? 'left' : 'right' ];
17174  var yValue = style[ isOriginTop ? 'top' : 'bottom' ];
17175  var x = parseFloat( xValue );
17176  var y = parseFloat( yValue );
17177  // convert percent to pixels
17178  var layoutSize = this.layout.size;
17179  if ( xValue.indexOf('%') != -1 ) {
17180    x = ( x / 100 ) * layoutSize.width;
17181  }
17182  if ( yValue.indexOf('%') != -1 ) {
17183    y = ( y / 100 ) * layoutSize.height;
17184  }
17185  // clean up 'auto' or other non-integer values
17186  x = isNaN( x ) ? 0 : x;
17187  y = isNaN( y ) ? 0 : y;
17188  // remove padding from measurement
17189  x -= isOriginLeft ? layoutSize.paddingLeft : layoutSize.paddingRight;
17190  y -= isOriginTop ? layoutSize.paddingTop : layoutSize.paddingBottom;
17191
17192  this.position.x = x;
17193  this.position.y = y;
17194};
17195
17196// set settled position, apply padding
17197proto.layoutPosition = function() {
17198  var layoutSize = this.layout.size;
17199  var style = {};
17200  var isOriginLeft = this.layout._getOption('originLeft');
17201  var isOriginTop = this.layout._getOption('originTop');
17202
17203  // x
17204  var xPadding = isOriginLeft ? 'paddingLeft' : 'paddingRight';
17205  var xProperty = isOriginLeft ? 'left' : 'right';
17206  var xResetProperty = isOriginLeft ? 'right' : 'left';
17207
17208  var x = this.position.x + layoutSize[ xPadding ];
17209  // set in percentage or pixels
17210  style[ xProperty ] = this.getXValue( x );
17211  // reset other property
17212  style[ xResetProperty ] = '';
17213
17214  // y
17215  var yPadding = isOriginTop ? 'paddingTop' : 'paddingBottom';
17216  var yProperty = isOriginTop ? 'top' : 'bottom';
17217  var yResetProperty = isOriginTop ? 'bottom' : 'top';
17218
17219  var y = this.position.y + layoutSize[ yPadding ];
17220  // set in percentage or pixels
17221  style[ yProperty ] = this.getYValue( y );
17222  // reset other property
17223  style[ yResetProperty ] = '';
17224
17225  this.css( style );
17226  this.emitEvent( 'layout', [ this ] );
17227};
17228
17229proto.getXValue = function( x ) {
17230  var isHorizontal = this.layout._getOption('horizontal');
17231  return this.layout.options.percentPosition && !isHorizontal ?
17232    ( ( x / this.layout.size.width ) * 100 ) + '%' : x + 'px';
17233};
17234
17235proto.getYValue = function( y ) {
17236  var isHorizontal = this.layout._getOption('horizontal');
17237  return this.layout.options.percentPosition && isHorizontal ?
17238    ( ( y / this.layout.size.height ) * 100 ) + '%' : y + 'px';
17239};
17240
17241proto._transitionTo = function( x, y ) {
17242  this.getPosition();
17243  // get current x & y from top/left
17244  var curX = this.position.x;
17245  var curY = this.position.y;
17246
17247  var didNotMove = x == this.position.x && y == this.position.y;
17248
17249  // save end position
17250  this.setPosition( x, y );
17251
17252  // if did not move and not transitioning, just go to layout
17253  if ( didNotMove && !this.isTransitioning ) {
17254    this.layoutPosition();
17255    return;
17256  }
17257
17258  var transX = x - curX;
17259  var transY = y - curY;
17260  var transitionStyle = {};
17261  transitionStyle.transform = this.getTranslate( transX, transY );
17262
17263  this.transition({
17264    to: transitionStyle,
17265    onTransitionEnd: {
17266      transform: this.layoutPosition
17267    },
17268    isCleaning: true
17269  });
17270};
17271
17272proto.getTranslate = function( x, y ) {
17273  // flip cooridinates if origin on right or bottom
17274  var isOriginLeft = this.layout._getOption('originLeft');
17275  var isOriginTop = this.layout._getOption('originTop');
17276  x = isOriginLeft ? x : -x;
17277  y = isOriginTop ? y : -y;
17278  return 'translate3d(' + x + 'px, ' + y + 'px, 0)';
17279};
17280
17281// non transition + transform support
17282proto.goTo = function( x, y ) {
17283  this.setPosition( x, y );
17284  this.layoutPosition();
17285};
17286
17287proto.moveTo = proto._transitionTo;
17288
17289proto.setPosition = function( x, y ) {
17290  this.position.x = parseFloat( x );
17291  this.position.y = parseFloat( y );
17292};
17293
17294// ----- transition ----- //
17295
17296/**
17297 * @param {Object} style - CSS
17298 * @param {Function} onTransitionEnd
17299 */
17300
17301// non transition, just trigger callback
17302proto._nonTransition = function( args ) {
17303  this.css( args.to );
17304  if ( args.isCleaning ) {
17305    this._removeStyles( args.to );
17306  }
17307  for ( var prop in args.onTransitionEnd ) {
17308    args.onTransitionEnd[ prop ].call( this );
17309  }
17310};
17311
17312/**
17313 * proper transition
17314 * @param {Object} args - arguments
17315 *   @param {Object} to - style to transition to
17316 *   @param {Object} from - style to start transition from
17317 *   @param {Boolean} isCleaning - removes transition styles after transition
17318 *   @param {Function} onTransitionEnd - callback
17319 */
17320proto.transition = function( args ) {
17321  // redirect to nonTransition if no transition duration
17322  if ( !parseFloat( this.layout.options.transitionDuration ) ) {
17323    this._nonTransition( args );
17324    return;
17325  }
17326
17327  var _transition = this._transn;
17328  // keep track of onTransitionEnd callback by css property
17329  for ( var prop in args.onTransitionEnd ) {
17330    _transition.onEnd[ prop ] = args.onTransitionEnd[ prop ];
17331  }
17332  // keep track of properties that are transitioning
17333  for ( prop in args.to ) {
17334    _transition.ingProperties[ prop ] = true;
17335    // keep track of properties to clean up when transition is done
17336    if ( args.isCleaning ) {
17337      _transition.clean[ prop ] = true;
17338    }
17339  }
17340
17341  // set from styles
17342  if ( args.from ) {
17343    this.css( args.from );
17344    // force redraw. http://blog.alexmaccaw.com/css-transitions
17345    var h = this.element.offsetHeight;
17346    // hack for JSHint to hush about unused var
17347    h = null;
17348  }
17349  // enable transition
17350  this.enableTransition( args.to );
17351  // set styles that are transitioning
17352  this.css( args.to );
17353
17354  this.isTransitioning = true;
17355
17356};
17357
17358// dash before all cap letters, including first for
17359// WebkitTransform => -webkit-transform
17360function toDashedAll( str ) {
17361  return str.replace( /([A-Z])/g, function( $1 ) {
17362    return '-' + $1.toLowerCase();
17363  });
17364}
17365
17366var transitionProps = 'opacity,' + toDashedAll( transformProperty );
17367
17368proto.enableTransition = function(/* style */) {
17369  // HACK changing transitionProperty during a transition
17370  // will cause transition to jump
17371  if ( this.isTransitioning ) {
17372    return;
17373  }
17374
17375  // make `transition: foo, bar, baz` from style object
17376  // HACK un-comment this when enableTransition can work
17377  // while a transition is happening
17378  // var transitionValues = [];
17379  // for ( var prop in style ) {
17380  //   // dash-ify camelCased properties like WebkitTransition
17381  //   prop = vendorProperties[ prop ] || prop;
17382  //   transitionValues.push( toDashedAll( prop ) );
17383  // }
17384  // munge number to millisecond, to match stagger
17385  var duration = this.layout.options.transitionDuration;
17386  duration = typeof duration == 'number' ? duration + 'ms' : duration;
17387  // enable transition styles
17388  this.css({
17389    transitionProperty: transitionProps,
17390    transitionDuration: duration,
17391    transitionDelay: this.staggerDelay || 0
17392  });
17393  // listen for transition end event
17394  this.element.addEventListener( transitionEndEvent, this, false );
17395};
17396
17397// ----- events ----- //
17398
17399proto.onwebkitTransitionEnd = function( event ) {
17400  this.ontransitionend( event );
17401};
17402
17403proto.onotransitionend = function( event ) {
17404  this.ontransitionend( event );
17405};
17406
17407// properties that I munge to make my life easier
17408var dashedVendorProperties = {
17409  '-webkit-transform': 'transform'
17410};
17411
17412proto.ontransitionend = function( event ) {
17413  // disregard bubbled events from children
17414  if ( event.target !== this.element ) {
17415    return;
17416  }
17417  var _transition = this._transn;
17418  // get property name of transitioned property, convert to prefix-free
17419  var propertyName = dashedVendorProperties[ event.propertyName ] || event.propertyName;
17420
17421  // remove property that has completed transitioning
17422  delete _transition.ingProperties[ propertyName ];
17423  // check if any properties are still transitioning
17424  if ( isEmptyObj( _transition.ingProperties ) ) {
17425    // all properties have completed transitioning
17426    this.disableTransition();
17427  }
17428  // clean style
17429  if ( propertyName in _transition.clean ) {
17430    // clean up style
17431    this.element.style[ event.propertyName ] = '';
17432    delete _transition.clean[ propertyName ];
17433  }
17434  // trigger onTransitionEnd callback
17435  if ( propertyName in _transition.onEnd ) {
17436    var onTransitionEnd = _transition.onEnd[ propertyName ];
17437    onTransitionEnd.call( this );
17438    delete _transition.onEnd[ propertyName ];
17439  }
17440
17441  this.emitEvent( 'transitionEnd', [ this ] );
17442};
17443
17444proto.disableTransition = function() {
17445  this.removeTransitionStyles();
17446  this.element.removeEventListener( transitionEndEvent, this, false );
17447  this.isTransitioning = false;
17448};
17449
17450/**
17451 * removes style property from element
17452 * @param {Object} style
17453**/
17454proto._removeStyles = function( style ) {
17455  // clean up transition styles
17456  var cleanStyle = {};
17457  for ( var prop in style ) {
17458    cleanStyle[ prop ] = '';
17459  }
17460  this.css( cleanStyle );
17461};
17462
17463var cleanTransitionStyle = {
17464  transitionProperty: '',
17465  transitionDuration: '',
17466  transitionDelay: ''
17467};
17468
17469proto.removeTransitionStyles = function() {
17470  // remove transition
17471  this.css( cleanTransitionStyle );
17472};
17473
17474// ----- stagger ----- //
17475
17476proto.stagger = function( delay ) {
17477  delay = isNaN( delay ) ? 0 : delay;
17478  this.staggerDelay = delay + 'ms';
17479};
17480
17481// ----- show/hide/remove ----- //
17482
17483// remove element from DOM
17484proto.removeElem = function() {
17485  this.element.parentNode.removeChild( this.element );
17486  // remove display: none
17487  this.css({ display: '' });
17488  this.emitEvent( 'remove', [ this ] );
17489};
17490
17491proto.remove = function() {
17492  // just remove element if no transition support or no transition
17493  if ( !transitionProperty || !parseFloat( this.layout.options.transitionDuration ) ) {
17494    this.removeElem();
17495    return;
17496  }
17497
17498  // start transition
17499  this.once( 'transitionEnd', function() {
17500    this.removeElem();
17501  });
17502  this.hide();
17503};
17504
17505proto.reveal = function() {
17506  delete this.isHidden;
17507  // remove display: none
17508  this.css({ display: '' });
17509
17510  var options = this.layout.options;
17511
17512  var onTransitionEnd = {};
17513  var transitionEndProperty = this.getHideRevealTransitionEndProperty('visibleStyle');
17514  onTransitionEnd[ transitionEndProperty ] = this.onRevealTransitionEnd;
17515
17516  this.transition({
17517    from: options.hiddenStyle,
17518    to: options.visibleStyle,
17519    isCleaning: true,
17520    onTransitionEnd: onTransitionEnd
17521  });
17522};
17523
17524proto.onRevealTransitionEnd = function() {
17525  // check if still visible
17526  // during transition, item may have been hidden
17527  if ( !this.isHidden ) {
17528    this.emitEvent('reveal');
17529  }
17530};
17531
17532/**
17533 * get style property use for hide/reveal transition end
17534 * @param {String} styleProperty - hiddenStyle/visibleStyle
17535 * @returns {String}
17536 */
17537proto.getHideRevealTransitionEndProperty = function( styleProperty ) {
17538  var optionStyle = this.layout.options[ styleProperty ];
17539  // use opacity
17540  if ( optionStyle.opacity ) {
17541    return 'opacity';
17542  }
17543  // get first property
17544  for ( var prop in optionStyle ) {
17545    return prop;
17546  }
17547};
17548
17549proto.hide = function() {
17550  // set flag
17551  this.isHidden = true;
17552  // remove display: none
17553  this.css({ display: '' });
17554
17555  var options = this.layout.options;
17556
17557  var onTransitionEnd = {};
17558  var transitionEndProperty = this.getHideRevealTransitionEndProperty('hiddenStyle');
17559  onTransitionEnd[ transitionEndProperty ] = this.onHideTransitionEnd;
17560
17561  this.transition({
17562    from: options.visibleStyle,
17563    to: options.hiddenStyle,
17564    // keep hidden stuff hidden
17565    isCleaning: true,
17566    onTransitionEnd: onTransitionEnd
17567  });
17568};
17569
17570proto.onHideTransitionEnd = function() {
17571  // check if still hidden
17572  // during transition, item may have been un-hidden
17573  if ( this.isHidden ) {
17574    this.css({ display: 'none' });
17575    this.emitEvent('hide');
17576  }
17577};
17578
17579proto.destroy = function() {
17580  this.css({
17581    position: '',
17582    left: '',
17583    right: '',
17584    top: '',
17585    bottom: '',
17586    transition: '',
17587    transform: ''
17588  });
17589};
17590
17591return Item;
17592
17593}));
17594
17595
17596/***/ }),
17597/* 26 */
17598/***/ (function(module, exports, __webpack_require__) {
17599
17600var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/**
17601 * Isotope Item
17602**/
17603
17604( function( window, factory ) {
17605  // universal module definition
17606  /* jshint strict: false */ /*globals define, module, require */
17607  if ( true ) {
17608    // AMD
17609    !(__WEBPACK_AMD_DEFINE_ARRAY__ = [
17610        __webpack_require__(5)
17611      ], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
17612				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
17613				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
vendor: 19,595 bytes, lines 17614-18304
17614				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
17615  } else if ( typeof module == 'object' && module.exports ) {
17616    // CommonJS
17617    module.exports = factory(
17618      require('outlayer')
17619    );
17620  } else {
17621    // browser global
17622    window.Isotope = window.Isotope || {};
17623    window.Isotope.Item = factory(
17624      window.Outlayer
17625    );
17626  }
17627
17628}( window, function factory( Outlayer ) {
17629'use strict';
17630
17631// -------------------------- Item -------------------------- //
17632
17633// sub-class Outlayer Item
17634function Item() {
17635  Outlayer.Item.apply( this, arguments );
17636}
17637
17638var proto = Item.prototype = Object.create( Outlayer.Item.prototype );
17639
17640var _create = proto._create;
17641proto._create = function() {
17642  // assign id, used for original-order sorting
17643  this.id = this.layout.itemGUID++;
17644  _create.call( this );
17645  this.sortData = {};
17646};
17647
17648proto.updateSortData = function() {
17649  if ( this.isIgnored ) {
17650    return;
17651  }
17652  // default sorters
17653  this.sortData.id = this.id;
17654  // for backward compatibility
17655  this.sortData['original-order'] = this.id;
17656  this.sortData.random = Math.random();
17657  // go thru getSortData obj and apply the sorters
17658  var getSortData = this.layout.options.getSortData;
17659  var sorters = this.layout._sorters;
17660  for ( var key in getSortData ) {
17661    var sorter = sorters[ key ];
17662    this.sortData[ key ] = sorter( this.element, this );
17663  }
17664};
17665
17666var _destroy = proto.destroy;
17667proto.destroy = function() {
17668  // call super
17669  _destroy.apply( this, arguments );
17670  // reset display, #741
17671  this.css({
17672    display: ''
17673  });
17674};
17675
17676return Item;
17677
17678}));
17679
17680
17681/***/ }),
17682/* 27 */
17683/***/ (function(module, exports, __webpack_require__) {
17684
17685var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/*!
17686 * Masonry layout mode
17687 * sub-classes Masonry
17688 * https://masonry.desandro.com
17689 */
17690
17691( function( window, factory ) {
17692  // universal module definition
17693  /* jshint strict: false */ /*globals define, module, require */
17694  if ( true ) {
17695    // AMD
17696    !(__WEBPACK_AMD_DEFINE_ARRAY__ = [
17697        __webpack_require__(6),
17698        __webpack_require__(28)
17699      ], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
17700				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
17701				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
17702				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
17703  } else if ( typeof module == 'object' && module.exports ) {
17704    // CommonJS
17705    module.exports = factory(
17706      require('../layout-mode'),
17707      require('masonry-layout')
17708    );
17709  } else {
17710    // browser global
17711    factory(
17712      window.Isotope.LayoutMode,
17713      window.Masonry
17714    );
17715  }
17716
17717}( window, function factory( LayoutMode, Masonry ) {
17718'use strict';
17719
17720// -------------------------- masonryDefinition -------------------------- //
17721
17722  // create an Outlayer layout class
17723  var MasonryMode = LayoutMode.create('masonry');
17724
17725  var proto = MasonryMode.prototype;
17726
17727  var keepModeMethods = {
17728    _getElementOffset: true,
17729    layout: true,
17730    _getMeasurement: true
17731  };
17732
17733  // inherit Masonry prototype
17734  for ( var method in Masonry.prototype ) {
17735    // do not inherit mode methods
17736    if ( !keepModeMethods[ method ] ) {
17737      proto[ method ] = Masonry.prototype[ method ];
17738    }
17739  }
17740
17741  var measureColumns = proto.measureColumns;
17742  proto.measureColumns = function() {
17743    // set items, used if measuring first item
17744    this.items = this.isotope.filteredItems;
17745    measureColumns.call( this );
17746  };
17747
17748  // point to mode options for fitWidth
17749  var _getOption = proto._getOption;
17750  proto._getOption = function( option ) {
17751    if ( option == 'fitWidth' ) {
17752      return this.options.isFitWidth !== undefined ?
17753        this.options.isFitWidth : this.options.fitWidth;
17754    }
17755    return _getOption.apply( this.isotope, arguments );
17756  };
17757
17758  return MasonryMode;
17759
17760}));
17761
17762
17763/***/ }),
17764/* 28 */
17765/***/ (function(module, exports, __webpack_require__) {
17766
17767var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/*!
17768 * Masonry v4.2.2
17769 * Cascading grid layout library
17770 * https://masonry.desandro.com
17771 * MIT License
17772 * by David DeSandro
17773 */
17774
17775( function( window, factory ) {
17776  // universal module definition
17777  /* jshint strict: false */ /*globals define, module, require */
17778  if ( true ) {
17779    // AMD
17780    !(__WEBPACK_AMD_DEFINE_ARRAY__ = [
17781        __webpack_require__(5),
17782        __webpack_require__(3)
17783      ], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
17784				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
17785				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
17786				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
17787  } else if ( typeof module == 'object' && module.exports ) {
17788    // CommonJS
17789    module.exports = factory(
17790      require('outlayer'),
17791      require('get-size')
17792    );
17793  } else {
17794    // browser global
17795    window.Masonry = factory(
17796      window.Outlayer,
17797      window.getSize
17798    );
17799  }
17800
17801}( window, function factory( Outlayer, getSize ) {
17802
17803'use strict';
17804
17805// -------------------------- masonryDefinition -------------------------- //
17806
17807  // create an Outlayer layout class
17808  var Masonry = Outlayer.create('masonry');
17809  // isFitWidth -> fitWidth
17810  Masonry.compatOptions.fitWidth = 'isFitWidth';
17811
17812  var proto = Masonry.prototype;
17813
17814  proto._resetLayout = function() {
17815    this.getSize();
17816    this._getMeasurement( 'columnWidth', 'outerWidth' );
17817    this._getMeasurement( 'gutter', 'outerWidth' );
17818    this.measureColumns();
17819
17820    // reset column Y
17821    this.colYs = [];
17822    for ( var i=0; i < this.cols; i++ ) {
17823      this.colYs.push( 0 );
17824    }
17825
17826    this.maxY = 0;
17827    this.horizontalColIndex = 0;
17828  };
17829
17830  proto.measureColumns = function() {
17831    this.getContainerWidth();
17832    // if columnWidth is 0, default to outerWidth of first item
17833    if ( !this.columnWidth ) {
17834      var firstItem = this.items[0];
17835      var firstItemElem = firstItem && firstItem.element;
17836      // columnWidth fall back to item of first element
17837      this.columnWidth = firstItemElem && getSize( firstItemElem ).outerWidth ||
17838        // if first elem has no width, default to size of container
17839        this.containerWidth;
17840    }
17841
17842    var columnWidth = this.columnWidth += this.gutter;
17843
17844    // calculate columns
17845    var containerWidth = this.containerWidth + this.gutter;
17846    var cols = containerWidth / columnWidth;
17847    // fix rounding errors, typically with gutters
17848    var excess = columnWidth - containerWidth % columnWidth;
17849    // if overshoot is less than a pixel, round up, otherwise floor it
17850    var mathMethod = excess && excess < 1 ? 'round' : 'floor';
17851    cols = Math[ mathMethod ]( cols );
17852    this.cols = Math.max( cols, 1 );
17853  };
17854
17855  proto.getContainerWidth = function() {
17856    // container is parent if fit width
17857    var isFitWidth = this._getOption('fitWidth');
17858    var container = isFitWidth ? this.element.parentNode : this.element;
17859    // check that this.size and size are there
17860    // IE8 triggers resize on body size change, so they might not be
17861    var size = getSize( container );
17862    this.containerWidth = size && size.innerWidth;
17863  };
17864
17865  proto._getItemLayoutPosition = function( item ) {
17866    item.getSize();
17867    // how many columns does this brick span
17868    var remainder = item.size.outerWidth % this.columnWidth;
17869    var mathMethod = remainder && remainder < 1 ? 'round' : 'ceil';
17870    // round if off by 1 pixel, otherwise use ceil
17871    var colSpan = Math[ mathMethod ]( item.size.outerWidth / this.columnWidth );
17872    colSpan = Math.min( colSpan, this.cols );
17873    // use horizontal or top column position
17874    var colPosMethod = this.options.horizontalOrder ?
17875      '_getHorizontalColPosition' : '_getTopColPosition';
17876    var colPosition = this[ colPosMethod ]( colSpan, item );
17877    // position the brick
17878    var position = {
17879      x: this.columnWidth * colPosition.col,
17880      y: colPosition.y
17881    };
17882    // apply setHeight to necessary columns
17883    var setHeight = colPosition.y + item.size.outerHeight;
17884    var setMax = colSpan + colPosition.col;
17885    for ( var i = colPosition.col; i < setMax; i++ ) {
17886      this.colYs[i] = setHeight;
17887    }
17888
17889    return position;
17890  };
17891
17892  proto._getTopColPosition = function( colSpan ) {
17893    var colGroup = this._getTopColGroup( colSpan );
17894    // get the minimum Y value from the columns
17895    var minimumY = Math.min.apply( Math, colGroup );
17896
17897    return {
17898      col: colGroup.indexOf( minimumY ),
17899      y: minimumY,
17900    };
17901  };
17902
17903  /**
17904   * @param {Number} colSpan - number of columns the element spans
17905   * @returns {Array} colGroup
17906   */
17907  proto._getTopColGroup = function( colSpan ) {
17908    if ( colSpan < 2 ) {
17909      // if brick spans only one column, use all the column Ys
17910      return this.colYs;
17911    }
17912
17913    var colGroup = [];
17914    // how many different places could this brick fit horizontally
17915    var groupCount = this.cols + 1 - colSpan;
17916    // for each group potential horizontal position
17917    for ( var i = 0; i < groupCount; i++ ) {
17918      colGroup[i] = this._getColGroupY( i, colSpan );
17919    }
17920    return colGroup;
17921  };
17922
17923  proto._getColGroupY = function( col, colSpan ) {
17924    if ( colSpan < 2 ) {
17925      return this.colYs[ col ];
17926    }
17927    // make an array of colY values for that one group
17928    var groupColYs = this.colYs.slice( col, col + colSpan );
17929    // and get the max value of the array
17930    return Math.max.apply( Math, groupColYs );
17931  };
17932
17933  // get column position based on horizontal index. #873
17934  proto._getHorizontalColPosition = function( colSpan, item ) {
17935    var col = this.horizontalColIndex % this.cols;
17936    var isOver = colSpan > 1 && col + colSpan > this.cols;
17937    // shift to next row if item can't fit on current row
17938    col = isOver ? 0 : col;
17939    // don't let zero-size items take up space
17940    var hasSize = item.size.outerWidth && item.size.outerHeight;
17941    this.horizontalColIndex = hasSize ? col + colSpan : this.horizontalColIndex;
17942
17943    return {
17944      col: col,
17945      y: this._getColGroupY( col, colSpan ),
17946    };
17947  };
17948
17949  proto._manageStamp = function( stamp ) {
17950    var stampSize = getSize( stamp );
17951    var offset = this._getElementOffset( stamp );
17952    // get the columns that this stamp affects
17953    var isOriginLeft = this._getOption('originLeft');
17954    var firstX = isOriginLeft ? offset.left : offset.right;
17955    var lastX = firstX + stampSize.outerWidth;
17956    var firstCol = Math.floor( firstX / this.columnWidth );
17957    firstCol = Math.max( 0, firstCol );
17958    var lastCol = Math.floor( lastX / this.columnWidth );
17959    // lastCol should not go over if multiple of columnWidth #425
17960    lastCol -= lastX % this.columnWidth ? 0 : 1;
17961    lastCol = Math.min( this.cols - 1, lastCol );
17962    // set colYs to bottom of the stamp
17963
17964    var isOriginTop = this._getOption('originTop');
17965    var stampMaxY = ( isOriginTop ? offset.top : offset.bottom ) +
17966      stampSize.outerHeight;
17967    for ( var i = firstCol; i <= lastCol; i++ ) {
17968      this.colYs[i] = Math.max( stampMaxY, this.colYs[i] );
17969    }
17970  };
17971
17972  proto._getContainerSize = function() {
17973    this.maxY = Math.max.apply( Math, this.colYs );
17974    var size = {
17975      height: this.maxY
17976    };
17977
17978    if ( this._getOption('fitWidth') ) {
17979      size.width = this._getContainerFitWidth();
17980    }
17981
17982    return size;
17983  };
17984
17985  proto._getContainerFitWidth = function() {
17986    var unusedCols = 0;
17987    // count unused columns
17988    var i = this.cols;
17989    while ( --i ) {
17990      if ( this.colYs[i] !== 0 ) {
17991        break;
17992      }
17993      unusedCols++;
17994    }
17995    // fit container to columns that have been used
17996    return ( this.cols - unusedCols ) * this.columnWidth - this.gutter;
17997  };
17998
17999  proto.needsResizeLayout = function() {
18000    var previousWidth = this.containerWidth;
18001    this.getContainerWidth();
18002    return previousWidth != this.containerWidth;
18003  };
18004
18005  return Masonry;
18006
18007}));
18008
18009
18010/***/ }),
18011/* 29 */
18012/***/ (function(module, exports, __webpack_require__) {
18013
18014var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/**
18015 * fitRows layout mode
18016 */
18017
18018( function( window, factory ) {
18019  // universal module definition
18020  /* jshint strict: false */ /*globals define, module, require */
18021  if ( true ) {
18022    // AMD
18023    !(__WEBPACK_AMD_DEFINE_ARRAY__ = [
18024        __webpack_require__(6)
18025      ], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
18026				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
18027				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
18028				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
18029  } else if ( typeof exports == 'object' ) {
18030    // CommonJS
18031    module.exports = factory(
18032      require('../layout-mode')
18033    );
18034  } else {
18035    // browser global
18036    factory(
18037      window.Isotope.LayoutMode
18038    );
18039  }
18040
18041}( window, function factory( LayoutMode ) {
18042'use strict';
18043
18044var FitRows = LayoutMode.create('fitRows');
18045
18046var proto = FitRows.prototype;
18047
18048proto._resetLayout = function() {
18049  this.x = 0;
18050  this.y = 0;
18051  this.maxY = 0;
18052  this._getMeasurement( 'gutter', 'outerWidth' );
18053};
18054
18055proto._getItemLayoutPosition = function( item ) {
18056  item.getSize();
18057
18058  var itemWidth = item.size.outerWidth + this.gutter;
18059  // if this element cannot fit in the current row
18060  var containerWidth = this.isotope.size.innerWidth + this.gutter;
18061  if ( this.x !== 0 && itemWidth + this.x > containerWidth ) {
18062    this.x = 0;
18063    this.y = this.maxY;
18064  }
18065
18066  var position = {
18067    x: this.x,
18068    y: this.y
18069  };
18070
18071  this.maxY = Math.max( this.maxY, this.y + item.size.outerHeight );
18072  this.x += itemWidth;
18073
18074  return position;
18075};
18076
18077proto._getContainerSize = function() {
18078  return { height: this.maxY };
18079};
18080
18081return FitRows;
18082
18083}));
18084
18085
18086/***/ }),
18087/* 30 */
18088/***/ (function(module, exports, __webpack_require__) {
18089
18090var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/**
18091 * vertical layout mode
18092 */
18093
18094( function( window, factory ) {
18095  // universal module definition
18096  /* jshint strict: false */ /*globals define, module, require */
18097  if ( true ) {
18098    // AMD
18099    !(__WEBPACK_AMD_DEFINE_ARRAY__ = [
18100        __webpack_require__(6)
18101      ], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
18102				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
18103				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
18104				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
18105  } else if ( typeof module == 'object' && module.exports ) {
18106    // CommonJS
18107    module.exports = factory(
18108      require('../layout-mode')
18109    );
18110  } else {
18111    // browser global
18112    factory(
18113      window.Isotope.LayoutMode
18114    );
18115  }
18116
18117}( window, function factory( LayoutMode ) {
18118'use strict';
18119
18120var Vertical = LayoutMode.create( 'vertical', {
18121  horizontalAlignment: 0
18122});
18123
18124var proto = Vertical.prototype;
18125
18126proto._resetLayout = function() {
18127  this.y = 0;
18128};
18129
18130proto._getItemLayoutPosition = function( item ) {
18131  item.getSize();
18132  var x = ( this.isotope.size.innerWidth - item.size.outerWidth ) *
18133    this.options.horizontalAlignment;
18134  var y = this.y;
18135  this.y += item.size.outerHeight;
18136  return { x: x, y: y };
18137};
18138
18139proto._getContainerSize = function() {
18140  return { height: this.y };
18141};
18142
18143return Vertical;
18144
18145}));
18146
18147
18148/***/ }),
18149/* 31 */
18150/***/ (function(module, exports, __webpack_require__) {
18151
18152var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_RESULT__;/**
18153 * EvEmitter v1.1.0
18154 * Lil' event emitter
18155 * MIT License
18156 */
18157
18158/* jshint unused: true, undef: true, strict: true */
18159
18160( function( global, factory ) {
18161  // universal module definition
18162  /* jshint strict: false */ /* globals define, module, window */
18163  if ( true ) {
18164    // AMD - RequireJS
18165    !(__WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
18166				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
18167				(__WEBPACK_AMD_DEFINE_FACTORY__.call(exports, __webpack_require__, exports, module)) :
18168				__WEBPACK_AMD_DEFINE_FACTORY__),
18169				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
18170  } else if ( typeof module == 'object' && module.exports ) {
18171    // CommonJS - Browserify, Webpack
18172    module.exports = factory();
18173  } else {
18174    // Browser globals
18175    global.EvEmitter = factory();
18176  }
18177
18178}( typeof window != 'undefined' ? window : this, function() {
18179
18180"use strict";
18181
18182function EvEmitter() {}
18183
18184var proto = EvEmitter.prototype;
18185
18186proto.on = function( eventName, listener ) {
18187  if ( !eventName || !listener ) {
18188    return;
18189  }
18190  // set events hash
18191  var events = this._events = this._events || {};
18192  // set listeners array
18193  var listeners = events[ eventName ] = events[ eventName ] || [];
18194  // only add once
18195  if ( listeners.indexOf( listener ) == -1 ) {
18196    listeners.push( listener );
18197  }
18198
18199  return this;
18200};
18201
18202proto.once = function( eventName, listener ) {
18203  if ( !eventName || !listener ) {
18204    return;
18205  }
18206  // add event
18207  this.on( eventName, listener );
18208  // set once flag
18209  // set onceEvents hash
18210  var onceEvents = this._onceEvents = this._onceEvents || {};
18211  // set onceListeners object
18212  var onceListeners = onceEvents[ eventName ] = onceEvents[ eventName ] || {};
18213  // set flag
18214  onceListeners[ listener ] = true;
18215
18216  return this;
18217};
18218
18219proto.off = function( eventName, listener ) {
18220  var listeners = this._events && this._events[ eventName ];
18221  if ( !listeners || !listeners.length ) {
18222    return;
18223  }
18224  var index = listeners.indexOf( listener );
18225  if ( index != -1 ) {
18226    listeners.splice( index, 1 );
18227  }
18228
18229  return this;
18230};
18231
18232proto.emitEvent = function( eventName, args ) {
18233  var listeners = this._events && this._events[ eventName ];
18234  if ( !listeners || !listeners.length ) {
18235    return;
18236  }
18237  // copy over to avoid interference if .off() in listener
18238  listeners = listeners.slice(0);
18239  args = args || [];
18240  // once stuff
18241  var onceListeners = this._onceEvents && this._onceEvents[ eventName ];
18242
18243  for ( var i=0; i < listeners.length; i++ ) {
18244    var listener = listeners[i]
18245    var isOnce = onceListeners && onceListeners[ listener ];
18246    if ( isOnce ) {
18247      // remove listener
18248      // remove before trigger to prevent recursion
18249      this.off( eventName, listener );
18250      // unset once flag
18251      delete onceListeners[ listener ];
18252    }
18253    // trigger listener
18254    listener.apply( this, args );
18255  }
18256
18257  return this;
18258};
18259
18260proto.allOff = function() {
18261  delete this._events;
18262  delete this._onceEvents;
18263};
18264
18265return EvEmitter;
18266
18267}));
18268
18269
18270/***/ }),
18271/* 32 */
18272/***/ (function(module, exports, __webpack_require__) {
18273
18274var __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;// page-load
18275( function( window, factory ) {
18276  // universal module definition
18277  /* globals define, module, require */
18278  if ( true ) {
18279    // AMD
18280    !(__WEBPACK_AMD_DEFINE_ARRAY__ = [
18281      __webpack_require__(2),
18282    ], __WEBPACK_AMD_DEFINE_RESULT__ = (function( InfiniteScroll ) {
18283      return factory( window, InfiniteScroll );
18284    }).apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__),
18285				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
18286  } else if ( typeof module == 'object' && module.exports ) {
18287    // CommonJS
18288    module.exports = factory(
18289      window,
18290      require('./core')
18291    );
18292  } else {
18293    // browser global
18294    factory(
18295      window,
18296      window.InfiniteScroll
18297    );
18298  }
18299
18300}( window, function factory( window, InfiniteScroll ) {
18301
18302var proto = InfiniteScroll.prototype;
18303
18304// InfiniteScroll.defaults.append = false;
18305InfiniteScroll.defaults.loadOnScroll = true;
18306InfiniteScroll.defaults.checkLastPage = true;
18307InfiniteScroll.defaults.responseType = 'document';
18308// InfiniteScroll.defaults.prefill = false;
18309// InfiniteScroll.defaults.outlayer = null;
18310
18311InfiniteScroll.create.pageLoad = function() {
18312  this.canLoad = true;
18313  this.on( 'scrollThreshold', this.onScrollThresholdLoad );
18314  this.on( 'load', this.checkLastPage );
18315  if ( this.options.outlayer ) {
18316    this.on( 'append', this.onAppendOutlayer );
18317  }
18318};
18319
18320proto.onScrollThresholdLoad = function() {
18321  if ( this.options.loadOnScroll ) {
18322    this.loadNextPage();
18323  }
18324};
18325
18326proto.loadNextPage = function() {
18327  if ( this.isLoading || !this.canLoad ) {
18328    return;
18329  }
18330
18331  var path = this.getAbsolutePath();
18332  this.isLoading = true;
18333
18334  var onLoad = function( response ) {
18335    this.onPageLoad( response, path );
18336  }.bind( this );
18337
18338  var onError = function( error ) {
18339    this.onPageError( error, path );
18340  }.bind( this );
18341
18342  request( path, this.options.responseType, onLoad, onError );
18343  this.dispatchEvent( 'request', null, [ path ] );
18344};
18345
18346proto.onPageLoad = function( response, path ) {
18347  // done loading if not appending
18348  if ( !this.options.append ) {
18349    this.isLoading = false;
18350  }
18351  this.pageIndex++;
18352  this.loadCount++;
18353  this.dispatchEvent( 'load', null, [ response, path ] );
18354  this.appendNextPage( response, path );
18355  return response;
18356};
18357
18358proto.appendNextPage = function( response, path ) {
18359  var optAppend = this.options.append;
18360  // do not append json
18361  var isDocument = this.options.responseType == 'document';
18362  if ( !isDocument || !optAppend ) {
18363    return;
18364  }
18365
18366  var items = response.querySelectorAll( optAppend );
18367  var fragment = getItemsFragment( items );
18368  var appendReady = function () {
18369    this.appendItems( items, fragment );
18370    this.isLoading = false;
18371    this.dispatchEvent( 'append', null, [ response, path, items ] );
18372  }.bind( this );
18373
18374  // TODO add hook for option to trigger appendReady
18375  if ( this.options.outlayer ) {
18376    this.appendOutlayerItems( fragment, appendReady );
18377  } else {
18378    appendReady();
18379  }
18380};
18381
18382proto.appendItems = function( items, fragment ) {
18383  if ( !items || !items.length ) {
18384    return;
18385  }
18386  // get fragment if not provided
18387  fragment = fragment || getItemsFragment( items );
18388  refreshScripts( fragment );
18389  this.element.appendChild( fragment );
18390};
18391
18392function getItemsFragment( items ) {
18393  // add items to fragment
18394  var fragment = document.createDocumentFragment();
18395  for ( var i=0; items && i < items.length; i++ ) {
18396    fragment.appendChild( items[i] );
18397  }
18398  return fragment;
18399}
18400
18401// replace <script>s with copies so they load
18402// <script>s added by InfiniteScroll will not load
18403// similar to https://stackoverflow.com/questions/610995
18404function refreshScripts( fragment ) {
18405  var scripts = fragment.querySelectorAll('script');
18406  for ( var i=0; i < scripts.length; i++ ) {
18407    var script = scripts[i];
18408    var freshScript = document.createElement('script');
18409    copyAttributes( script, freshScript );
18410    script.parentNode.replaceChild( freshScript, script );
18411  }
18412}
18413
18414function copyAttributes( fromNode, toNode ) {
18415  var attrs = fromNode.attributes;
18416  for ( var i=0; i < attrs.length; i++ ) {
18417    var attr = attrs[i];
18418    toNode.setAttribute( attr.name, attr.value );
18419  }
18420}
18421
18422// ----- outlayer ----- //
18423
18424proto.appendOutlayerItems = function( fragment, appendReady ) {
18425  var imagesLoaded = InfiniteScroll.imagesLoaded || window.imagesLoaded;
18426  if ( !imagesLoaded ) {
18427    console.error('[InfiniteScroll] imagesLoaded required for outlayer option');
18428    this.isLoading = false;
18429    return;
18430  }
18431  // append once images loaded
18432  imagesLoaded( fragment, appendReady );
18433};
18434
18435proto.onAppendOutlayer = function( response, path, items ) {
18436  this.options.outlayer.appended( items );
18437};
18438
18439// ----- checkLastPage ----- //
18440
18441// check response for next element
18442proto.checkLastPage = function( response, path ) {
18443  var checkLastPage = this.options.checkLastPage;
18444  if ( !checkLastPage ) {
18445    return;
18446  }
18447
18448  var pathOpt = this.options.path;
18449  // if path is function, check if next path is truthy
18450  if ( typeof pathOpt == 'function' ) {
18451    var nextPath = this.getPath();
18452    if ( !nextPath ) {
18453      this.lastPageReached( response, path );
18454      return;
18455    }
18456  }
18457  // get selector from checkLastPage or path option
18458  var selector;
18459  if ( typeof checkLastPage == 'string' ) {
18460    selector = checkLastPage;
18461  } else if ( this.isPathSelector ) {
18462    // path option is selector string
18463    selector = pathOpt;
18464  }
18465  // check last page for selector
18466  // bail if no selector or not document response
18467  if ( !selector || !response.querySelector ) {
18468    return;
18469  }
18470  // check if response has selector
18471  var nextElem = response.querySelector( selector );
18472  if ( !nextElem ) {
18473    this.lastPageReached( response, path );
18474  }
18475};
18476
18477proto.lastPageReached = function( response, path ) {
18478  this.canLoad = false;
18479  this.dispatchEvent( 'last', null, [ response, path ] );
18480};
18481
18482// ----- error ----- //
18483
18484proto.onPageError = function( error, path ) {
18485  this.isLoading = false;
18486  this.canLoad = false;
18487  this.dispatchEvent( 'error', null, [ error, path ] );
18488  return error;
18489};
18490
18491// -------------------------- prefill -------------------------- //
18492
18493InfiniteScroll.create.prefill = function() {
18494  if ( !this.options.prefill ) {
18495    return;
18496  }
18497  var append = this.options.append;
18498  if ( !append ) {
18499    console.error( 'append option required for prefill. Set as :' + append );
18500    return;
18501  }
18502  this.updateMeasurements();
18503  this.updateScroller();
18504  this.isPrefilling = true;
18505  this.on( 'append', this.prefill );
18506  this.once( 'error', this.stopPrefill );
18507  this.once( 'last', this.stopPrefill );
18508  this.prefill();
18509};
18510
18511proto.prefill = function() {
18512  var distance = this.getPrefillDistance();
18513  this.isPrefilling = distance >= 0;
18514  if ( this.isPrefilling ) {
18515    this.log('prefill');
18516    this.loadNextPage();
18517  } else {
18518    this.stopPrefill();
18519  }
18520};
18521
18522proto.getPrefillDistance = function() {
18523  // element scroll
18524  if ( this.options.elementScroll ) {
18525    return this.scroller.clientHeight - this.scroller.scrollHeight;
18526  }
18527  // window
18528  return this.windowHeight - this.element.clientHeight;
18529};
18530
18531proto.stopPrefill = function() {
18532  console.log('stopping prefill');
18533  this.off( 'append', this.prefill );
18534};
18535
18536// -------------------------- request -------------------------- //
18537
18538function request( url, responseType, onLoad, onError ) {
18539  var req = new XMLHttpRequest();
18540  req.open( 'GET', url, true );
18541  // set responseType document to return DOM
18542  req.responseType = responseType || '';
18543
18544  // set X-Requested-With header to check that is ajax request
18545  req.setRequestHeader('X-Requested-With', 'XMLHttpRequest');
18546
18547  req.onload = function() {
18548    if ( req.status == 200 ) {
18549      onLoad( req.response );
18550    } else {
18551      // not 200 OK, error
18552      var error = new Error( req.statusText );
18553      onError( error );
18554    }
18555  };
18556
18557  // Handle network errors
18558  req.onerror = function() {
18559    var error = new Error( 'Network error requesting ' + url );
18560    onError( error );
18561  };
18562
18563  req.send();
18564}
18565
18566// --------------------------  -------------------------- //
18567
18568return InfiniteScroll;
18569
18570}));
18571
18572
18573/***/ }),
18574/* 33 */
18575/***/ (function(module, exports, __webpack_require__) {
18576
18577var __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;// scroll-watch
18578( function( window, factory ) {
18579  // universal module definition
18580  /* globals define, module, require */
18581  if ( true ) {
18582    // AMD
18583    !(__WEBPACK_AMD_DEFINE_ARRAY__ = [
18584      __webpack_require__(2),
18585      __webpack_require__(1),
18586    ], __WEBPACK_AMD_DEFINE_RESULT__ = (function( InfiniteScroll, utils ) {
18587      return factory( window, InfiniteScroll, utils );
18588    }).apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__),
18589				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
18590  } else if ( typeof module == 'object' && module.exports ) {
18591    // CommonJS
18592    module.exports = factory(
18593      window,
18594      require('./core'),
18595      require('fizzy-ui-utils')
18596    );
18597  } else {
18598    // browser global
18599    factory(
18600      window,
18601      window.InfiniteScroll,
18602      window.fizzyUIUtils
18603    );
18604  }
18605
18606}( window, function factory( window, InfiniteScroll, utils ) {
18607
18608var proto = InfiniteScroll.prototype;
18609
18610// default options
18611InfiniteScroll.defaults.scrollThreshold = 400;
18612// InfiniteScroll.defaults.elementScroll = null;
18613
18614InfiniteScroll.create.scrollWatch = function() {
18615  // events
18616  this.pageScrollHandler = this.onPageScroll.bind( this );
18617  this.resizeHandler = this.onResize.bind( this );
18618
18619  var scrollThreshold = this.options.scrollThreshold;
18620  var isEnable = scrollThreshold || scrollThreshold === 0;
18621  if ( isEnable ) {
18622    this.enableScrollWatch();
18623  }
18624};
18625
18626InfiniteScroll.destroy.scrollWatch = function() {
18627  this.disableScrollWatch();
18628};
18629
18630proto.enableScrollWatch = function() {
18631  if ( this.isScrollWatching ) {
18632    return;
18633  }
18634  this.isScrollWatching = true;
18635  this.updateMeasurements();
18636  this.updateScroller();
18637  // TODO disable after error?
18638  this.on( 'last', this.disableScrollWatch );
18639  this.bindScrollWatchEvents( true );
18640};
18641
18642proto.disableScrollWatch = function() {
18643  if ( !this.isScrollWatching ) {
18644    return;
18645  }
18646  this.bindScrollWatchEvents( false );
18647  delete this.isScrollWatching;
18648};
18649
18650proto.bindScrollWatchEvents = function( isBind ) {
18651  var addRemove = isBind ? 'addEventListener' : 'removeEventListener';
18652  this.scroller[ addRemove ]( 'scroll', this.pageScrollHandler );
18653  window[ addRemove ]( 'resize', this.resizeHandler );
18654};
18655
18656proto.onPageScroll = InfiniteScroll.throttle( function() {
18657  var distance = this.getBottomDistance();
18658  if ( distance <= this.options.scrollThreshold ) {
18659    this.dispatchEvent('scrollThreshold');
18660  }
18661});
18662
18663proto.getBottomDistance = function() {
18664  if ( this.options.elementScroll ) {
18665    return this.getElementBottomDistance();
18666  } else {
18667    return this.getWindowBottomDistance();
18668  }
18669};
18670
18671proto.getWindowBottomDistance = function() {
18672  var bottom = this.top + this.element.clientHeight;
18673  var scrollY = window.pageYOffset + this.windowHeight;
18674  return bottom - scrollY;
18675};
18676
18677proto.getElementBottomDistance = function() {
18678  var bottom = this.scroller.scrollHeight;
18679  var scrollY = this.scroller.scrollTop + this.scroller.clientHeight;
18680  return bottom - scrollY;
18681};
18682
18683proto.onResize = function() {
18684  this.updateMeasurements();
18685};
18686
18687utils.debounceMethod( InfiniteScroll, 'onResize', 150 );
18688
18689// --------------------------  -------------------------- //
18690
18691return InfiniteScroll;
18692
18693}));
18694
18695
18696/***/ }),
18697/* 34 */
18698/***/ (function(module, exports, __webpack_require__) {
18699
18700var __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;// history
18701( function( window, factory ) {
18702  // universal module definition
18703  /* globals define, module, require */
18704  if ( true ) {
18705    // AMD
18706    !(__WEBPACK_AMD_DEFINE_ARRAY__ = [
18707      __webpack_require__(2),
18708      __webpack_require__(1),
18709    ], __WEBPACK_AMD_DEFINE_RESULT__ = (function( InfiniteScroll, utils ) {
18710      return factory( window, InfiniteScroll, utils );
18711    }).apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__),
18712				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
18713  } else if ( typeof module == 'object' && module.exports ) {
18714    // CommonJS
18715    module.exports = factory(
18716      window,
18717      require('./core'),
18718      require('fizzy-ui-utils')
18719    );
18720  } else {
18721    // browser global
18722    factory(
18723      window,
18724      window.InfiniteScroll,
18725      window.fizzyUIUtils
18726    );
18727  }
18728
18729}( window, function factory( window, InfiniteScroll, utils ) {
18730
18731var proto = InfiniteScroll.prototype;
18732
18733InfiniteScroll.defaults.history = 'replace';
18734// InfiniteScroll.defaults.historyTitle = false;
18735
18736var link = document.createElement('a');
18737
18738// ----- create/destroy ----- //
18739
18740InfiniteScroll.create.history = function() {
18741  if ( !this.options.history ) {
18742    return;
18743  }
18744  // check for same origin
18745  link.href = this.getAbsolutePath();
18746  // MS Edge does not have origin on link https://developer.microsoft.com/en-us/microsoft-edge/platform/issues/12236493/
18747  var linkOrigin = link.origin || link.protocol + '//' + link.host;
18748  var isSameOrigin = linkOrigin == location.origin;
18749  if ( !isSameOrigin ) {
18750    console.error( '[InfiniteScroll] cannot set history with different origin: ' +
18751      link.origin + ' on ' + location.origin +
18752      ' . History behavior disabled.' );
18753    return;
18754  }
18755
18756  // two ways to handle changing history
18757  if ( this.options.append ) {
18758    this.createHistoryAppend();
18759  } else {
18760    this.createHistoryPageLoad();
18761  }
18762};
18763
18764proto.createHistoryAppend = function() {
18765  this.updateMeasurements();
18766  this.updateScroller();
18767  // array of scroll positions of appended pages
18768  this.scrollPages = [
18769    {
18770      // first page
18771      top: 0,
18772      path: location.href,
18773      title: document.title,
18774    }
18775  ];
18776  this.scrollPageIndex = 0;
18777  // events
18778  this.scrollHistoryHandler = this.onScrollHistory.bind( this );
18779  this.unloadHandler = this.onUnload.bind( this );
18780  this.scroller.addEventListener( 'scroll', this.scrollHistoryHandler );
18781  this.on( 'append', this.onAppendHistory );
18782  this.bindHistoryAppendEvents( true );
18783};
18784
18785proto.bindHistoryAppendEvents = function( isBind ) {
18786  var addRemove = isBind ? 'addEventListener' : 'removeEventListener';
18787  this.scroller[ addRemove ]( 'scroll', this.scrollHistoryHandler );
18788  window[ addRemove ]( 'unload', this.unloadHandler );
18789};
18790
18791proto.createHistoryPageLoad = function() {
18792  this.on( 'load', this.onPageLoadHistory );
18793};
18794
18795InfiniteScroll.destroy.history =
18796proto.destroyHistory = function() {
18797  var isHistoryAppend = this.options.history && this.options.append;
18798  if ( isHistoryAppend ) {
18799    this.bindHistoryAppendEvents( false );
18800  }
18801};
18802
18803// ----- append history ----- //
18804
18805proto.onAppendHistory = function( response, path, items ) {
18806  var firstItem = items[0];
18807  var elemScrollY = this.getElementScrollY( firstItem );
18808  // resolve path
18809  link.href = path;
18810  // add page data to hash
18811  this.scrollPages.push({
18812    top: elemScrollY,
18813    path: link.href,
18814    title: response.title,
18815  });
18816};
18817
18818proto.getElementScrollY = function( elem ) {
18819  if ( this.options.elementScroll ) {
18820    return this.getElementElementScrollY( elem );
18821  } else {
18822    return this.getElementWindowScrollY( elem );
18823  }
18824};
18825
18826proto.getElementWindowScrollY = function( elem ) {
18827  var rect = elem.getBoundingClientRect();
18828  return rect.top + window.pageYOffset;
18829};
18830
18831// wow, stupid name
18832proto.getElementElementScrollY = function( elem ) {
18833  return elem.offsetTop - this.top;
18834};
18835
18836proto.onScrollHistory = function() {
18837  // cycle through positions, find biggest without going over
18838  var scrollViewY = this.getScrollViewY();
18839  var pageIndex, page;
18840  for ( var i=0; i < this.scrollPages.length; i++ ) {
18841    var scrollPage = this.scrollPages[i];
18842    if ( scrollPage.top >= scrollViewY ) {
18843      break;
18844    }
18845    pageIndex = i;
18846    page = scrollPage;
18847  }
18848  // set history if changed
18849  if ( pageIndex != this.scrollPageIndex ) {
18850    this.scrollPageIndex = pageIndex;
18851    this.setHistory( page.title, page.path );
18852  }
18853};
18854
18855utils.debounceMethod( InfiniteScroll, 'onScrollHistory', 150 );
18856
18857proto.getScrollViewY = function() {
18858  if ( this.options.elementScroll ) {
18859    return this.scroller.scrollTop + this.scroller.clientHeight/2;
18860  } else {
18861    return window.pageYOffset + this.windowHeight/2;
18862  }
18863};
18864
18865proto.setHistory = function( title, path ) {
18866  var optHistory = this.options.history;
18867  var historyMethod = optHistory && history[ optHistory + 'State' ];
18868  if ( !historyMethod ) {
18869    return;
18870  }
18871
18872  history[ optHistory + 'State' ]( null, title, path );
18873
18874  if ( this.options.historyTitle ) {
18875    document.title = title;
18876  }
18877
18878  this.dispatchEvent( 'history', null, [ title, path ] );
18879};
18880
18881// scroll to top to prevent initial scroll-reset after page refresh
18882// http://stackoverflow.com/a/18633915/182183
18883proto.onUnload = function() {
18884  var pageIndex = this.scrollPageIndex;
18885  if ( pageIndex === 0 ) {
18886    return;
18887  }
18888  // calculate where scroll position would be on refresh
18889  var scrollPage = this.scrollPages[ pageIndex ];
18890  var scrollY = window.pageYOffset - scrollPage.top + this.top;
18891  // disable scroll event before setting scroll #679
18892  this.destroyHistory();
18893  scrollTo( 0, scrollY );
18894};
18895
18896// ----- load history ----- //
18897
18898// update URL
18899proto.onPageLoadHistory = function( response, path ) {
18900  this.setHistory( response.title, path );
18901};
18902
18903// --------------------------  -------------------------- //
18904
18905return InfiniteScroll;
18906
18907}));
18908
18909
18910/***/ }),
18911/* 35 */
18912/***/ (function(module, exports, __webpack_require__) {
18913
18914var __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;// button
18915( function( window, factory ) {
18916  // universal module definition
18917  /* globals define, module, require */
18918  if ( true ) {
18919    // AMD
18920    !(__WEBPACK_AMD_DEFINE_ARRAY__ = [
18921      __webpack_require__(2),
18922      __webpack_require__(1),
18923    ], __WEBPACK_AMD_DEFINE_RESULT__ = (function( InfiniteScroll, utils ) {
18924      return factory( window, InfiniteScroll, utils );
18925    }).apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__),
18926				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
18927  } else if ( typeof module == 'object' && module.exports ) {
18928    // CommonJS
18929    module.exports = factory(
18930      window,
18931      require('./core'),
18932      require('fizzy-ui-utils')
18933    );
18934  } else {
18935    // browser global
18936    factory(
18937      window,
18938      window.InfiniteScroll,
18939      window.fizzyUIUtils
18940    );
18941  }
18942
18943}( window, function factory( window, InfiniteScroll, utils ) {
18944
18945// InfiniteScroll.defaults.button = null;
18946
18947InfiniteScroll.create.button = function() {
18948  var buttonElem = utils.getQueryElement( this.options.button );
18949  if ( buttonElem ) {
18950    this.button = new InfiniteScrollButton( buttonElem, this );
18951    return;
18952  }
18953};
18954
18955InfiniteScroll.destroy.button = function() {
18956  if ( this.button ) {
18957    this.button.destroy();
18958  }
18959};
18960
18961// -------------------------- InfiniteScrollButton -------------------------- //
18962
18963function InfiniteScrollButton( element, infScroll ) {
18964  this.element = element;
18965  this.infScroll = infScroll;
18966  // events
18967  this.clickHandler = this.onClick.bind( this );
18968  this.element.addEventListener( 'click', this.clickHandler );
18969  infScroll.on( 'request', this.disable.bind( this ) );
18970  infScroll.on( 'load', this.enable.bind( this ) );
18971  infScroll.on( 'error', this.hide.bind( this ) );
18972  infScroll.on( 'last', this.hide.bind( this ) );
18973}
18974
18975InfiniteScrollButton.prototype.onClick = function( event ) {
18976  event.preventDefault();
18977  this.infScroll.loadNextPage();
18978};
18979
18980InfiniteScrollButton.prototype.enable = function() {
18981  this.element.removeAttribute('disabled');
18982};
18983
18984InfiniteScrollButton.prototype.disable = function() {
18985  this.element.disabled = 'disabled';
18986};
18987
18988InfiniteScrollButton.prototype.hide = function() {
18989  this.element.style.display = 'none';
18990};
18991
18992InfiniteScrollButton.prototype.destroy = function() {
18993  this.element.removeEventListener( 'click', this.clickHandler );
18994};
18995
18996// --------------------------  -------------------------- //
18997
18998InfiniteScroll.Button = InfiniteScrollButton;
18999
19000return InfiniteScroll;
19001
19002}));
19003
19004
19005/***/ }),
19006/* 36 */
19007/***/ (function(module, exports, __webpack_require__) {
19008
19009var __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;// status
19010( function( window, factory ) {
19011  // universal module definition
19012  /* globals define, module, require */
19013  if ( true ) {
19014    // AMD
19015    !(__WEBPACK_AMD_DEFINE_ARRAY__ = [
19016      __webpack_require__(2),
19017      __webpack_require__(1),
19018    ], __WEBPACK_AMD_DEFINE_RESULT__ = (function( InfiniteScroll, utils ) {
19019      return factory( window, InfiniteScroll, utils );
19020    }).apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__),
19021				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
19022  } else if ( typeof module == 'object' && module.exports ) {
19023    // CommonJS
19024    module.exports = factory(
19025      window,
19026      require('./core'),
19027      require('fizzy-ui-utils')
19028    );
19029  } else {
19030    // browser global
19031    factory(
19032      window,
19033      window.InfiniteScroll,
19034      window.fizzyUIUtils
19035    );
19036  }
19037
19038}( window, function factory( window, InfiniteScroll, utils ) { 
19039
19040var proto = InfiniteScroll.prototype;
19041
19042// InfiniteScroll.defaults.status = null;
19043
19044InfiniteScroll.create.status = function() {
19045  var statusElem = utils.getQueryElement( this.options.status );
19046  if ( !statusElem ) {
19047    return;
19048  }
19049  // elements
19050  this.statusElement = statusElem;
19051  this.statusEventElements = {
19052    request: statusElem.querySelector('.infinite-scroll-request'),
19053    error: statusElem.querySelector('.infinite-scroll-error'),
19054    last: statusElem.querySelector('.infinite-scroll-last'),
19055  };
19056  // events
19057  this.on( 'request', this.showRequestStatus );
19058  this.on( 'error', this.showErrorStatus );
19059  this.on( 'last', this.showLastStatus );
19060  this.bindHideStatus('on');
19061};
19062
19063proto.bindHideStatus = function( bindMethod ) {
19064  var hideEvent = this.options.append ? 'append' : 'load';
19065  this[ bindMethod ]( hideEvent, this.hideAllStatus );
19066};
19067
19068proto.showRequestStatus = function() {
19069  this.showStatus('request');
19070};
19071
19072proto.showErrorStatus = function() {
19073  this.showStatus('error');
19074};
19075
19076proto.showLastStatus = function() {
19077  this.showStatus('last');
19078  // prevent last then append event race condition from showing last status #706
19079  this.bindHideStatus('off');
19080};
19081
19082proto.showStatus = function( eventName ) {
19083  show( this.statusElement );
19084  this.hideStatusEventElements();
19085  var eventElem = this.statusEventElements[ eventName ];
19086  show( eventElem );
19087};
19088
19089proto.hideAllStatus = function() {
19090  hide( this.statusElement );
19091  this.hideStatusEventElements();
19092};
19093
19094proto.hideStatusEventElements = function() {
19095  for ( var type in this.statusEventElements ) {
19096    var eventElem = this.statusEventElements[ type ];
19097    hide( eventElem );
19098  }
19099};
19100
19101// --------------------------  -------------------------- //
19102
19103function hide( elem ) {
19104  setDisplay( elem, 'none' );
19105}
19106
19107function show( elem ) {
19108  setDisplay( elem, 'block' );
19109}
19110
19111function setDisplay( elem, value ) {
19112  if ( elem ) {
19113    elem.style.display = value;
19114  }
19115}
19116
19117// --------------------------  -------------------------- //
19118
19119return InfiniteScroll;
19120
19121}));
19122
19123
19124/***/ }),
19125/* 37 */
19126/***/ (function(module, exports, __webpack_require__) {
19127
19128var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__;/**
19129 * selectize.js (v0.13.6)
19130 * Copyright (c) 2013–2015 Brian Reavis & contributors
19131 * Copyright (c) 2020-2022 Selectize Team & contributors
19132 *
19133 * Licensed under the Apache License, Version 2.0 (the "License");
19133 you may not use this
19134 * file except in compliance with the License. You may obtain a copy of the License at:
19135 * http://www.apache.org/licenses/LICENSE-2.0
19136 *
19137 * Unless required by applicable law or agreed to in writing, software distributed under
19138 * the License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF
19139 * ANY KIND, either express or implied. See the License for the specific language
19140 * governing permissions and limitations under the License.
19141 *
19142 * @author Brian Reavis <[email protected]>
19143 * @author Ris Adams <[email protected]>
19144 */
19145
19146/*jshint curly:false */
19147/*jshint browser:true */
19148
19149(function(root, factory) {
19150	if (true) {
19151		!(__WEBPACK_AMD_DEFINE_ARRAY__ = [__webpack_require__(0),__webpack_require__(38),__webpack_require__(39)], __WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
19152				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
19153				(__WEBPACK_AMD_DEFINE_FACTORY__.apply(exports, __WEBPACK_AMD_DEFINE_ARRAY__)) : __WEBPACK_AMD_DEFINE_FACTORY__),
19154				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
19155	} else if (typeof module === 'object' && typeof module.exports === 'object') {
19156		module.exports = factory(require('jquery'), require('sifter'), require('microplugin'));
19157	} else {
19158		root.Selectize = factory(root.jQuery, root.Sifter, root.MicroPlugin);
19159	}
19160}(this, function($, Sifter, MicroPlugin) {
19161	'use strict';
19162
19163	var highlight = function($element, pattern) {
19164		if (typeof pattern === 'string' && !pattern.length) return;
19165		var regex = (typeof pattern === 'string') ? new RegExp(pattern, 'i') : pattern;
19166	
19167		var highlight = function(node) {
19168			var skip = 0;
19169			// Wrap matching part of text node with highlighting <span>, e.g.
19170			// Soccer  ->  <span class="highlight">Soc</span>cer  for regex = /soc/i
19171			if (node.nodeType === 3) {
19172				var pos = node.data.search(regex);
19173				if (pos >= 0 && node.data.length > 0) {
19174					var match = node.data.match(regex);
19175					var spannode = document.createElement('span');
19176					spannode.className = 'highlight';
19177					var middlebit = node.splitText(pos);
19178					var endbit = middlebit.splitText(match[0].length);
19179					var middleclone = middlebit.cloneNode(true);
19180					spannode.appendChild(middleclone);
19181					middlebit.parentNode.replaceChild(spannode, middlebit);
19182					skip = 1;
19183				}
19184			} 
19185			// Recurse element node, looking for child text nodes to highlight, unless element 
19186			// is childless, <script>, <style>, or already highlighted: <span class="highlight">
19187			else if (node.nodeType === 1 && node.childNodes && !/(script|style)/i.test(node.tagName) && ( node.className !== 'highlight' || node.tagName !== 'SPAN' )) {
19188				for (var i = 0; i < node.childNodes.length; ++i) {
19189					i += highlight(node.childNodes[i]);
19190				}
19191			}
19192			return skip;
19193		};
19194	
19195		return $element.each(function() {
19196			highlight(this);
19197		});
19198	};
19199	
19200	/**
19201	 * removeHighlight fn copied from highlight v5 and
19202	 * edited to remove with() and pass js strict mode
19203	 */
19204	$.fn.removeHighlight = function() {
19205		return this.find("span.highlight").each(function() {
19206			this.parentNode.firstChild.nodeName;
19207			var parent = this.parentNode;
19208			parent.replaceChild(this.firstChild, this);
19209			parent.normalize();
19210		}).end();
19211	};
19212	
19213	
19214	var MicroEvent = function() {};
19215	MicroEvent.prototype = {
19216		on: function(event, fct){
19217			this._events = this._events || {};
19218			this._events[event] = this._events[event] || [];
19219			this._events[event].push(fct);
19220		},
19221		off: function(event, fct){
19222			var n = arguments.length;
19223			if (n === 0) return delete this._events;
19224			if (n === 1) return delete this._events[event];
19225	
19226			this._events = this._events || {};
19227			if (event in this._events === false) return;
19228			this._events[event].splice(this._events[event].indexOf(fct), 1);
19229		},
19230		trigger: function(event /* , args... */){
19231			this._events = this._events || {};
19232			if (event in this._events === false) return;
19233			for (var i = 0; i < this._events[event].length; i++){
19234				this._events[event][i].apply(this, Array.prototype.slice.call(arguments, 1));
19235			}
19236		}
19237	};
19238	
19239	/**
19240	 * Mixin will delegate all MicroEvent.js function in the destination object.
19241	 *
19242	 * - MicroEvent.mixin(Foobar) will make Foobar able to use MicroEvent
19243	 *
19244	 * @param {object} the object which will support MicroEvent
19245	 */
19246	MicroEvent.mixin = function(destObject){
19247		var props = ['on', 'off', 'trigger'];
19248		for (var i = 0; i < props.length; i++){
19249			destObject.prototype[props[i]] = MicroEvent.prototype[props[i]];
19250		}
19251	};
19252	
19253	function uaDetect(platform, re) {
19254	  if (navigator.userAgentData) {
19255	    return platform === navigator.userAgentData.platform;
19256	  }
19257	
19258	  return re.test(navigator.userAgent);
19259	}
19260	
19261	var IS_MAC        = uaDetect("macOS", /Mac/);
19262	
19263	var KEY_A         = 65;
19264	var KEY_COMMA     = 188;
19265	var KEY_RETURN    = 13;
19266	var KEY_ESC       = 27;
19267	var KEY_LEFT      = 37;
19268	var KEY_UP        = 38;
19269	var KEY_P         = 80;
19270	var KEY_RIGHT     = 39;
19271	var KEY_DOWN      = 40;
19272	var KEY_N         = 78;
19273	var KEY_BACKSPACE = 8;
19274	var KEY_DELETE    = 46;
19275	var KEY_SHIFT     = 16;
19276	var KEY_CMD       = IS_MAC ? 91 : 17;
19277	var KEY_CTRL      = IS_MAC ? 18 : 17;
19278	var KEY_TAB       = 9;
19279	
19280	var TAG_SELECT    = 1;
19281	var TAG_INPUT     = 2;
19282	
19283	// for now, android support in general is too spotty to support validity
19284	var SUPPORTS_VALIDITY_API = !uaDetect("Android", /android/i
vendor: 4,206 bytes, lines 19284-19472
19284) && !!document.createElement('input').validity;
19285	
19286	
19287	var isset = function(object) {
19288		return typeof object !== 'undefined';
19289	};
19290	
19291	/**
19292	 * Converts a scalar to its best string representation
19293	 * for hash keys and HTML attribute values.
19294	 *
19295	 * Transformations:
19296	 *   'str'     -> 'str'
19297	 *   null      -> ''
19298	 *   undefined -> ''
19299	 *   true      -> '1'
19300	 *   false     -> '0'
19301	 *   0         -> '0'
19302	 *   1         -> '1'
19303	 *
19304	 * @param {string} value
19305	 * @returns {string|null}
19306	 */
19307	var hash_key = function(value) {
19308		if (typeof value === 'undefined' || value === null) return null;
19309		if (typeof value === 'boolean') return value ? '1' : '0';
19310		return value + '';
19311	};
19312	
19313	/**
19314	 * Escapes a string for use within HTML.
19315	 *
19316	 * @param {string} str
19317	 * @returns {string}
19318	 */
19319	var escape_html = function(str) {
19320		return (str + '')
19321			.replace(/&/g, '&amp;')
19322			.replace(/</g, '&lt;')
19323			.replace(/>/g, '&gt;')
19324			.replace(/"/g, '&quot;');
19325	};
19326	
19327	/**
19328	 * Escapes "$" characters in replacement strings.
19329	 *
19330	 * @param {string} str
19331	 * @returns {string}
19332	 */
19333	var escape_replace = function(str) {
19334		return (str + '').replace(/\$/g, '$$$$');
19335	};
19336	
19337	var hook = {};
19338	
19339	/**
19340	 * Wraps `method` on `self` so that `fn`
19341	 * is invoked before the original method.
19342	 *
19343	 * @param {object} self
19344	 * @param {string} method
19345	 * @param {function} fn
19346	 */
19347	hook.before = function(self, method, fn) {
19348		var original = self[method];
19349		self[method] = function() {
19350			fn.apply(self, arguments);
19351			return original.apply(self, arguments);
19352		};
19353	};
19354	
19355	/**
19356	 * Wraps `method` on `self` so that `fn`
19357	 * is invoked after the original method.
19358	 *
19359	 * @param {object} self
19360	 * @param {string} method
19361	 * @param {function} fn
19362	 */
19363	hook.after = function(self, method, fn) {
19364		var original = self[method];
19365		self[method] = function() {
19366			var result = original.apply(self, arguments);
19367			fn.apply(self, arguments);
19368			return result;
19369		};
19370	};
19371	
19372	/**
19373	 * Wraps `fn` so that it can only be invoked once.
19374	 *
19375	 * @param {function} fn
19376	 * @returns {function}
19377	 */
19378	var once = function(fn) {
19379		var called = false;
19380		return function() {
19381			if (called) return;
19382			called = true;
19383			fn.apply(this, arguments);
19384		};
19385	};
19386	
19387	/**
19388	 * Wraps `fn` so that it can only be called once
19389	 * every `delay` milliseconds (invoked on the falling edge).
19390	 *
19391	 * @param {function} fn
19392	 * @param {int} delay
19393	 * @returns {function}
19394	 */
19395	var debounce = function(fn, delay) {
19396		var timeout;
19397		return function() {
19398			var self = this;
19399			var args = arguments;
19400			window.clearTimeout(timeout);
19401			timeout = window.setTimeout(function() {
19402				fn.apply(self, args);
19403			}, delay);
19404		};
19405	};
19406	
19407	/**
19408	 * Debounce all fired events types listed in `types`
19409	 * while executing the provided `fn`.
19410	 *
19411	 * @param {object} self
19412	 * @param {array} types
19413	 * @param {function} fn
19414	 */
19415	var debounce_events = function(self, types, fn) {
19416		var type;
19417		var trigger = self.trigger;
19418		var event_args = {};
19419	
19420		// override trigger method
19421		self.trigger = function() {
19422			var type = arguments[0];
19423			if (types.indexOf(type) !== -1) {
19424				event_args[type] = arguments;
19425			} else {
19426				return trigger.apply(self, arguments);
19427			}
19428		};
19429	
19430		// invoke provided function
19431		fn.apply(self, []);
19432		self.trigger = trigger;
19433	
19434		// trigger queued events
19435		for (type in event_args) {
19436			if (event_args.hasOwnProperty(type)) {
19437				trigger.apply(self, event_args[type]);
19438			}
19439		}
19440	};
19441	
19442	/**
19443	 * A workaround for http://bugs.jquery.com/ticket/6696
19444	 *
19445	 * @param {object} $parent - Parent element to listen on.
19446	 * @param {string} event - Event name.
19447	 * @param {string} selector - Descendant selector to filter by.
19448	 * @param {function} fn - Event handler.
19449	 */
19450	var watchChildEvent = function($parent, event, selector, fn) {
19451		$parent.on(event, selector, function(e) {
19452			var child = e.target;
19453			while (child && child.parentNode !== $parent[0]) {
19454				child = child.parentNode;
19455			}
19456			e.currentTarget = child;
19457			return fn.apply(this, [e]);
19458		});
19459	};
19460	
19461	/**
19462	 * Determines the current selection within a text input control.
19463	 * Returns an object containing:
19464	 *   - start
19465	 *   - length
19466	 *
19467	 * @param {object} input
19468	 * @returns {object}
19469	 */
19470	var getSelection = function(input) {
19471		var result = {};
19472	
vendor: 8,540 bytes, lines 19472-19779
19472  if(input === undefined) {
19473	    console.warn('WARN getSelection cannot locate input control');
19474	    return result;
19475	  }
19476		if ('selectionStart' in input) {
19477			result.start = input.selectionStart;
19478			result.length = input.selectionEnd - result.start;
19479		} else if (document.selection) {
19480			input.focus();
19481			var sel = document.selection.createRange();
19482			var selLen = document.selection.createRange().text.length;
19483			sel.moveStart('character', -input.value.length);
19484			result.start = sel.text.length - selLen;
19485			result.length = selLen;
19486		}
19487		return result;
19488	};
19489	
19490	/**
19491	 * Copies CSS properties from one element to another.
19492	 *
19493	 * @param {object} $from
19494	 * @param {object} $to
19495	 * @param {array} properties
19496	 */
19497	var transferStyles = function($from, $to, properties) {
19498		var i, n, styles = {};
19499		if (properties) {
19500			for (i = 0, n = properties.length; i < n; i++) {
19501				styles[properties[i]] = $from.css(properties[i]);
19502			}
19503		} else {
19504			styles = $from.css();
19505		}
19506		$to.css(styles);
19507	};
19508	
19509	/**
19510	 * Measures the width of a string within a
19511	 * parent element (in pixels).
19512	 *
19513	 * @param {string} str
19514	 * @param {object} $parent
19515	 * @returns {int}
19516	 */
19517	var measureString = function(str, $parent) {
19518		if (!str) {
19519			return 0;
19520		}
19521	
19522		if (!Selectize.$testInput) {
19523			Selectize.$testInput = $('<span />').css({
19524				position: 'absolute',
19525				width: 'auto',
19526				padding: 0,
19527				whiteSpace: 'pre'
19528			});
19529	
19530			$('<div />').css({
19531				position: 'absolute',
19532				width: 0,
19533				height: 0,
19534				overflow: 'hidden'
19535			}).append(Selectize.$testInput).appendTo('body');
19536		}
19537	
19538		Selectize.$testInput.text(str);
19539	
19540		transferStyles($parent, Selectize.$testInput, [
19541			'letterSpacing',
19542			'fontSize',
19543			'fontFamily',
19544			'fontWeight',
19545			'textTransform'
19546		]);
19547	
19548		return Selectize.$testInput.width();
19549	};
19550	
19551	/**
19552	 * Sets up an input to grow horizontally as the user
19553	 * types. If the value is changed manually, you can
19554	 * trigger the "update" handler to resize:
19555	 *
19556	 * $input.trigger('update');
19557	 *
19558	 * @param {object} $input
19559	 */
19560	var autoGrow = function($input) {
19561		var currentWidth = null;
19562	
19563		var update = function(e, options) {
19564			var value, keyCode, printable, width;
19565			var placeholder, placeholderWidth;
19566			var shift, character, selection;
19567			e = e || window.event || {};
19568			options = options || {};
19569	
19570			if (e.metaKey || e.altKey) return;
19571			if (!options.force && $input.data('grow') === false) return;
19572	
19573			value = $input.val();
19574			if (e.type && e.type.toLowerCase() === 'keydown') {
19575				keyCode = e.keyCode;
19576				printable = (
19577					(keyCode >= 48 && keyCode <= 57)  || // 0-9
19578					(keyCode >= 65 && keyCode <= 90)   || // a-z
19579					(keyCode >= 96 && keyCode <= 111)  || // numpad 0-9, numeric operators
19580					(keyCode >= 186 && keyCode <= 222) || // semicolon, equal, comma, dash, etc.
19581					keyCode === 32 // space
19582				);
19583	
19584				if (keyCode === KEY_DELETE || keyCode === KEY_BACKSPACE) {
19585					selection = getSelection($input[0]);
19586					if (selection.length) {
19587						value = value.substring(0, selection.start) + value.substring(selection.start + selection.length);
19588					} else if (keyCode === KEY_BACKSPACE && selection.start) {
19589						value = value.substring(0, selection.start - 1) + value.substring(selection.start + 1);
19590					} else if (keyCode === KEY_DELETE && typeof selection.start !== 'undefined') {
19591						value = value.substring(0, selection.start) + value.substring(selection.start + 1);
19592					}
19593				} else if (printable) {
19594					shift = e.shiftKey;
19595					character = String.fromCharCode(e.keyCode);
19596					if (shift) character = character.toUpperCase();
19597					else character = character.toLowerCase();
19598					value += character;
19599				}
19600			}
19601	
19602			placeholder = $input.attr('placeholder');
19603			if (placeholder) {
19604				placeholderWidth = measureString(placeholder, $input) + 4;
19605			} else {
19606				placeholderWidth = 0;
19607			}
19608	
19609			width = Math.max(measureString(value, $input), placeholderWidth) + 4;
19610			if (width !== currentWidth) {
19611				currentWidth = width;
19612				$input.width(width);
19613				$input.triggerHandler('resize');
19614			}
19615		};
19616	
19617		$input.on('keydown keyup update blur', update);
19618		update();
19619	};
19620	
19621	var domToString = function(d) {
19622		var tmp = document.createElement('div');
19623	
19624		tmp.appendChild(d.cloneNode(true));
19625	
19626		return tmp.innerHTML;
19627	};
19628	
19629	var logError = function(message, options){
19630		if(!options) options = {};
19631		var component = "Selectize";
19632	
19633		console.error(component + ": " + message)
19634	
19635		if(options.explanation){
19636			// console.group is undefined in <IE11
19637			if(console.group) console.group();
19638			console.error(options.explanation);
19639			if(console.group) console.groupEnd();
19640		}
19641	}
19642	
19643	
19644	var Selectize = function($input, settings) {
19645		var key, i, n, dir, input, self = this;
19646		input = $input[0];
19647		input.selectize = self;
19648	
19649		// detect rtl environment
19650		var computedStyle = window.getComputedStyle && window.getComputedStyle(input, null);
19651		dir = computedStyle ? computedStyle.getPropertyValue('direction') : input.currentStyle && input.currentStyle.direction;
19652		dir = dir || $input.parents('[dir]:first').attr('dir') || '';
19653	
19654		// setup default state
19655		$.extend(self, {
19656			order            : 0,
19657			settings         : settings,
19658			$input           : $input,
19659			tabIndex         : $input.attr('tabindex') || '',
19660			tagType          : input.tagName.toLowerCase() === 'select' ? TAG_SELECT : TAG_INPUT,
19661			rtl              : /rtl/i.test(dir),
19662	
19663			eventNS          : '.selectize' + (++Selectize.count),
19664			highlightedValue : null,
19665			isBlurring       : false,
19666			isOpen           : false,
19667			isDisabled       : false,
19668			isRequired       : $input.is('[required]'),
19669			isInvalid        : false,
19670			isLocked         : false,
19671			isFocused        : false,
19672			isInputHidden    : false,
19673			isSetup          : false,
19674			isShiftDown      : false,
19675			isCmdDown        : false,
19676			isCtrlDown       : false,
19677			ignoreFocus      : false,
19678			ignoreBlur       : false,
19679			ignoreHover      : false,
19680			hasOptions       : false,
19681			currentResults   : null,
19682			lastValue        : '',
19683			lastValidValue   : '',
19684			caretPos         : 0,
19685			loading          : 0,
19686			loadedSearches   : {},
19687	
19688			$activeOption    : null,
19689			$activeItems     : [],
19690	
19691			optgroups        : {},
19692			options          : {},
19693			userOptions      : {},
19694			items            : [],
19695			renderCache      : {},
19696			onSearchChange   : settings.loadThrottle === null ? self.onSearchChange : debounce(self.onSearchChange, settings.loadThrottle)
19697		});
19698	
19699		// search system
19700		self.sifter = new Sifter(this.options, {diacritics: settings.diacritics});
19701	
19702		// build options table
19703		if (self.settings.options) {
19704			for (i = 0, n = self.settings.options.length; i < n; i++) {
19705				self.registerOption(self.settings.options[i]);
19706			}
19707			delete self.settings.options;
19708		}
19709	
19710		// build optgroup table
19711		if (self.settings.optgroups) {
19712			for (i = 0, n = self.settings.optgroups.length; i < n; i++) {
19713				self.registerOptionGroup(self.settings.optgroups[i]);
19714			}
19715			delete self.settings.optgroups;
19716		}
19717	
19718		// option-dependent defaults
19719		self.settings.mode = self.settings.mode || (self.settings.maxItems === 1 ? 'single' : 'multi');
19720		if (typeof self.settings.hideSelected !== 'boolean') {
19721			self.settings.hideSelected = self.settings.mode === 'multi';
19722		}
19723	
19724		self.initializePlugins(self.settings.plugins);
19725		self.setupCallbacks();
19726		self.setupTemplates();
19727		self.setup();
19728	};
19729	
19730	// mixins
19731	// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
19732	
19733	MicroEvent.mixin(Selectize);
19734	
19735	if(typeof MicroPlugin !== "undefined"){
19736		MicroPlugin.mixin(Selectize);
19737	}else{
19738		logError("Dependency MicroPlugin is missing",
19739			{explanation:
19740				"Make sure you either: (1) are using the \"standalone\" "+
19741				"version of Selectize, or (2) require MicroPlugin before you "+
19742				"load Selectize."}
19743		);
19744	}
19745	
19746	
19747	// methods
19748	// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
19749	
19750	$.extend(Selectize.prototype, {
19751	
19752		/**
19753		 * Creates all elements and sets up event bindings.
19754		 */
19755		setup: function() {
19756			var self      = this;
19757			var settings  = self.settings;
19758			var eventNS   = self.eventNS;
19759			var $window   = $(window);
19760			var $document = $(document);
19761			var $input    = self.$input;
19762	
19763			var $wrapper;
19764			var $control;
19765			var $control_input;
19766			var $dropdown;
19767			var $dropdown_content;
19768			var $dropdown_parent;
19769			var inputMode;
19770			var timeout_blur;
19771			var timeout_focus;
19772			var classes;
19773			var classes_plugins;
19774			var inputId;
19775	
19776			inputMode         = self.settings.mode;
19777			classes           = $input.attr('class') || '';
19778	
19779			$wrapper          = $('<div>
vendor: 18,854 bytes, lines 19779-20446
19779').addClass(settings.wrapperClass).addClass(classes).addClass(inputMode);
19780			$control          = $('<div>').addClass(settings.inputClass).addClass('items').appendTo($wrapper);
19781			$control_input    = $('<input type="text" autocomplete="new-password" autofill="no" />').appendTo($control).attr('tabindex', $input.is(':disabled') ? '-1' : self.tabIndex);
19782			$dropdown_parent  = $(settings.dropdownParent || $wrapper);
19783			$dropdown         = $('<div>').addClass(settings.dropdownClass).addClass(inputMode).hide().appendTo($dropdown_parent);
19784			$dropdown_content = $('<div>').addClass(settings.dropdownContentClass).attr('tabindex', '-1').appendTo($dropdown);
19785	
19786			if(inputId = $input.attr('id')) {
19787				$control_input.attr('id', inputId + '-selectized');
19788				$("label[for='"+inputId+"']").attr('for', inputId + '-selectized');
19789			}
19790	
19791			if(self.settings.copyClassesToDropdown) {
19792				$dropdown.addClass(classes);
19793			}
19794	
19795			$wrapper.css({
19796				width: $input[0].style.width
19797			});
19798	
19799			if (self.plugins.names.length) {
19800				classes_plugins = 'plugin-' + self.plugins.names.join(' plugin-');
19801				$wrapper.addClass(classes_plugins);
19802				$dropdown.addClass(classes_plugins);
19803			}
19804	
19805			if ((settings.maxItems === null || settings.maxItems > 1) && self.tagType === TAG_SELECT) {
19806				$input.attr('multiple', 'multiple');
19807			}
19808	
19809			if (self.settings.placeholder) {
19810				$control_input.attr('placeholder', settings.placeholder);
19811			}
19812	
19813			// if splitOn was not passed in, construct it from the delimiter to allow pasting universally
19814			if (!self.settings.splitOn && self.settings.delimiter) {
19815				var delimiterEscaped = self.settings.delimiter.replace(/[-\/\\^$*+?.()|[\]{}]/g, '\\$&');
19816				self.settings.splitOn = new RegExp('\\s*' + delimiterEscaped + '+\\s*');
19817			}
19818	
19819			if ($input.attr('autocorrect')) {
19820				$control_input.attr('autocorrect', $input.attr('autocorrect'));
19821			}
19822	
19823			if ($input.attr('autocapitalize')) {
19824				$control_input.attr('autocapitalize', $input.attr('autocapitalize'));
19825			}
19826			if ($input.is('input')) {
19827				$control_input[0].type = $input[0].type;
19828			}
19829	
19830			self.$wrapper          = $wrapper;
19831			self.$control          = $control;
19832			self.$control_input    = $control_input;
19833			self.$dropdown         = $dropdown;
19834			self.$dropdown_content = $dropdown_content;
19835	
19836			$dropdown.on('mouseenter mousedown click', '[data-disabled]>[data-selectable]', function(e) { e.stopImmediatePropagation(); });
19837			$dropdown.on('mouseenter', '[data-selectable]', function() { return self.onOptionHover.apply(self, arguments); });
19838			$dropdown.on('mousedown click', '[data-selectable]', function() { return self.onOptionSelect.apply(self, arguments); });
19839			watchChildEvent($control, 'mousedown', '*:not(input)', function() { return self.onItemSelect.apply(self, arguments); });
19840			autoGrow($control_input);
19841	
19842			$control.on({
19843				mousedown : function() { return self.onMouseDown.apply(self, arguments); },
19844				click     : function() { return self.onClick.apply(self, arguments); }
19845			});
19846	
19847			$control_input.on({
19848				mousedown : function(e) { e.stopPropagation(); },
19849				keydown   : function() { return self.onKeyDown.apply(self, arguments); },
19850				keypress  : function() { return self.onKeyPress.apply(self, arguments); },
19851				input     : function() { return self.onInput.apply(self, arguments); },
19852				resize    : function() { self.positionDropdown.apply(self, []); },
19853				blur      : function() { return self.onBlur.apply(self, arguments); },
19854				focus     : function() { self.ignoreBlur = false; return self.onFocus.apply(self, arguments); },
19855				paste     : function() { return self.onPaste.apply(self, arguments); }
19856			});
19857	
19858			$document.on('keydown' + eventNS, function(e) {
19859				self.isCmdDown = e[IS_MAC ? 'metaKey' : 'ctrlKey'];
19860				self.isCtrlDown = e[IS_MAC ? 'altKey' : 'ctrlKey'];
19861				self.isShiftDown = e.shiftKey;
19862			});
19863	
19864			$document.on('keyup' + eventNS, function(e) {
19865				if (e.keyCode === KEY_CTRL) self.isCtrlDown = false;
19866				if (e.keyCode === KEY_SHIFT) self.isShiftDown = false;
19867				if (e.keyCode === KEY_CMD) self.isCmdDown = false;
19868			});
19869	
19870			$document.on('mousedown' + eventNS, function(e) {
19871				if (self.isFocused) {
19872					// prevent events on the dropdown scrollbar from causing the control to blur
19873					if (e.target === self.$dropdown[0] || e.target.parentNode === self.$dropdown[0]) {
19874						return false;
19875					}
19876					// blur on click outside
19877					if (!self.$control.has(e.target).length && e.target !== self.$control[0]) {
19878						self.blur(e.target);
19879					}
19880				}
19881			});
19882	
19883			$window.on(['scroll' + eventNS, 'resize' + eventNS].join(' '), function() {
19884				if (self.isOpen) {
19885					self.positionDropdown.apply(self, arguments);
19886				}
19887			});
19888			$window.on('mousemove' + eventNS, function() {
19889				self.ignoreHover = false;
19890			});
19891	
19892			// store original children and tab index so that they can be
19893			// restored when the destroy() method is called.
19894			this.revertSettings = {
19895				$children : $input.children().detach(),
19896				tabindex  : $input.attr('tabindex')
19897			};
19898	
19899			$input.attr('tabindex', -1).hide().after(self.$wrapper);
19900	
19901			if (Array.isArray(settings.items)) {
19902				self.lastValidValue = settings.items;
19903				self.setValue(settings.items);
19904				delete settings.items;
19905			}
19906	
19907			// feature detect for the validation API
19908			if (SUPPORTS_VALIDITY_API) {
19909				$input.on('invalid' + eventNS, function(e) {
19910					e.preventDefault();
19911					self.isInvalid = true;
19912					self.refreshState();
19913				});
19914			}
19915	
19916			self.updateOriginalInput();
19917			self.refreshItems();
19918			self.refreshState();
19919			self.updatePlaceholder();
19920			self.isSetup = true;
19921	
19922			if ($input.is(':disabled')) {
19923				self.disable();
19924			}
19925	
19926			self.on('change', this.onChange);
19927	
19928			$input.data('selectize', self);
19929			$input.addClass('selectized');
19930			self.trigger('initialize');
19931	
19932			// preload options
19933			if (settings.preload === true) {
19934				self.onSearchChange('');
19935			}
19936	
19937		},
19938	
19939		/**
19940		 * Sets up default rendering functions.
19941		 */
19942		setupTemplates: function() {
19943			var self = this;
19944			var field_label = self.settings.labelField;
19945			var field_value = self.settings.valueField;
19946			var field_optgroup = self.settings.optgroupLabelField;
19947	
19948			var templates = {
19949				'optgroup': function(data) {
19950					return '<div class="optgroup">' + data.html + '</div>';
19951				},
19952				'optgroup_header': function(data, escape) {
19953					return '<div class="optgroup-header">' + escape(data[field_optgroup]) + '</div>';
19954				},
19955				'option': function(data, escape) {
19956					return '<div class="option '+( data[field_value] === '' ? 'selectize-dropdown-emptyoptionlabel' : '')+'">' + escape(data[field_label]) + '</div>';
19957				},
19958				'item': function(data, escape) {
19959					return '<div class="item">' + escape(data[field_label]) + '</div>';
19960				},
19961				'option_create': function(data, escape) {
19962					return '<div class="create">Add <strong>' + escape(data.input) + '</strong>&#x2026;</div>';
19963				}
19964			};
19965	
19966			self.settings.render = $.extend({}, templates, self.settings.render);
19967		},
19968	
19969		/**
19970		 * Maps fired events to callbacks provided
19971		 * in the settings used when creating the control.
19972		 */
19973		setupCallbacks: function() {
19974			var key, fn, callbacks = {
19975				'initialize'      : 'onInitialize',
19976				'change'          : 'onChange',
19977				'item_add'        : 'onItemAdd',
19978				'item_remove'     : 'onItemRemove',
19979				'clear'           : 'onClear',
19980				'option_add'      : 'onOptionAdd',
19981				'option_remove'   : 'onOptionRemove',
19982				'option_clear'    : 'onOptionClear',
19983				'optgroup_add'    : 'onOptionGroupAdd',
19984				'optgroup_remove' : 'onOptionGroupRemove',
19985				'optgroup_clear'  : 'onOptionGroupClear',
19986				'dropdown_open'   : 'onDropdownOpen',
19987				'dropdown_close'  : 'onDropdownClose',
19988				'type'            : 'onType',
19989				'load'            : 'onLoad',
19990				'focus'           : 'onFocus',
19991				'blur'            : 'onBlur',
19992				'dropdown_item_activate'        : 'onDropdownItemActivate',
19993				'dropdown_item_deactivate'      : 'onDropdownItemDeactivate'
19994			};
19995	
19996			for (key in callbacks) {
19997				if (callbacks.hasOwnProperty(key)) {
19998					fn = this.settings[callbacks[key]];
19999					if (fn) this.on(key, fn);
20000				}
20001			}
20002		},
20003	
20004		/**
20005		 * Triggered when the main control element
20006		 * has a click event.
20007		 *
20008		 * @param {object} e
20009		 * @return {boolean}
20010		 */
20011		onClick: function(e) {
20012			var self = this;
20013	
20014			// necessary for mobile webkit devices (manual focus triggering
20015			// is ignored unless invoked within a click event)
20016	    // also necessary to reopen a dropdown that has been closed by
20017	    // closeAfterSelect
20018			if (!self.isFocused || !self.isOpen) {
20019				self.focus();
20020				e.preventDefault();
20021			}
20022		},
20023	
20024		/**
20025		 * Triggered when the main control element
20026		 * has a mouse down event.
20027		 *
20028		 * @param {object} e
20029		 * @return {boolean}
20030		 */
20031		onMouseDown: function(e) {
20032			var self = this;
20033			var defaultPrevented = e.isDefaultPrevented();
20034			var $target = $(e.target);
20035	
20036			if (self.isFocused) {
20037				// retain focus by preventing native handling. if the
20038				// event target is the input it should not be modified.
20039				// otherwise, text selection within the input won't work.
20040				if (e.target !== self.$control_input[0]) {
20041					if (self.settings.mode === 'single') {
20042						// toggle dropdown
20043						self.isOpen ? self.close() : self.open();
20044					} else if (!defaultPrevented) {
20045						self.setActiveItem(null);
20046					}
20047					return false;
20048				}
20049			} else {
20050				// give control focus
20051				if (!defaultPrevented) {
20052					window.setTimeout(function() {
20053						self.focus();
20054					}, 0);
20055				}
20056			}
20057		},
20058	
20059		/**
20060		 * Triggered when the value of the control has been changed.
20061		 * This should propagate the event to the original DOM
20062		 * input / select element.
20063		 */
20064		onChange: function() {
20065			var self = this;
20066			if (self.getValue() !== "") {
20067				self.lastValidValue = self.getValue();
20068			}
20069			this.$input.trigger('input');
20070			this.$input.trigger('change');
20071		},
20072	
20073		/**
20074		 * Triggered on <input> paste.
20075		 *
20076		 * @param {object} e
20077		 * @returns {boolean}
20078		 */
20079		onPaste: function(e) {
20080			var self = this;
20081	
20082			if (self.isFull() || self.isInputHidden || self.isLocked) {
20083				e.preventDefault();
20084				return;
20085			}
20086	
20087			// If a regex or string is included, this will split the pasted
20088			// input and create Items for each separate value
20089			if (self.settings.splitOn) {
20090	
20091				// Wait for pasted text to be recognized in value
20092				setTimeout(function() {
20093					var pastedText = self.$control_input.val();
20094					if(!pastedText.match(self.settings.splitOn)){ return }
20095	
20096					var splitInput = pastedText
20097						.trim()
20098						.split(self.settings.splitOn);
20099					for (var i = 0, n = splitInput.length; i < n; i++) {
20100						self.createItem(splitInput[i]);
20101					}
20102				}, 0);
20103			}
20104		},
20105	
20106		/**
20107		 * Triggered on <input> keypress.
20108		 *
20109		 * @param {object} e
20110		 * @returns {boolean}
20111		 */
20112		onKeyPress: function(e) {
20113			if (this.isLocked) return e && e.preventDefault();
20114			var character = String.fromCharCode(e.keyCode || e.which);
20115			if (this.settings.create && this.settings.mode === 'multi' && character === this.settings.delimiter) {
20116				this.createItem();
20117				e.preventDefault();
20118				return false;
20119			}
20120		},
20121	
20122		/**
20123		 * Triggered on <input> keydown.
20124		 *
20125		 * @param {object} e
20126		 * @returns {boolean}
20127		 */
20128		onKeyDown: function(e) {
20129			var isInput = e.target === this.$control_input[0];
20130			var self = this;
20131	
20132			if (self.isLocked) {
20133				if (e.keyCode !== KEY_TAB) {
20134					e.preventDefault();
20135				}
20136				return;
20137			}
20138	
20139			switch (e.keyCode) {
20140				case KEY_A:
20141					if (self.isCmdDown) {
20142						self.selectAll();
20143						return;
20144					}
20145					break;
20146				case KEY_ESC:
20147					if (self.isOpen) {
20148						e.preventDefault();
20149						e.stopPropagation();
20150						self.close();
20151					}
20152					return;
20153				case KEY_N:
20154					if (!e.ctrlKey || e.altKey) break;
20155				case KEY_DOWN:
20156					if (!self.isOpen && self.hasOptions) {
20157						self.open();
20158					} else if (self.$activeOption) {
20159						self.ignoreHover = true;
20160						var $next = self.getAdjacentOption(self.$activeOption, 1);
20161						if ($next.length) self.setActiveOption($next, true, true);
20162					}
20163					e.preventDefault();
20164					return;
20165				case KEY_P:
20166					if (!e.ctrlKey || e.altKey) break;
20167				case KEY_UP:
20168					if (self.$activeOption) {
20169						self.ignoreHover = true;
20170						var $prev = self.getAdjacentOption(self.$activeOption, -1);
20171						if ($prev.length) self.setActiveOption($prev, true, true);
20172					}
20173					e.preventDefault();
20174					return;
20175				case KEY_RETURN:
20176					if (self.isOpen && self.$activeOption) {
20177						self.onOptionSelect({currentTarget: self.$activeOption});
20178						e.preventDefault();
20179					}
20180					return;
20181				case KEY_LEFT:
20182					self.advanceSelection(-1, e);
20183					return;
20184				case KEY_RIGHT:
20185					self.advanceSelection(1, e);
20186					return;
20187				case KEY_TAB:
20188					if (self.settings.selectOnTab && self.isOpen && self.$activeOption) {
20189						self.onOptionSelect({currentTarget: self.$activeOption});
20190	
20191						// Default behaviour is to jump to the next field, we only want this
20192						// if the current field doesn't accept any more entries
20193						if (!self.isFull()) {
20194							e.preventDefault();
20195						}
20196					}
20197					if (self.settings.create && self.createItem() && self.settings.showAddOptionOnCreate) {
20198						e.preventDefault();
20199					}
20200					return;
20201				case KEY_BACKSPACE:
20202				case KEY_DELETE:
20203					self.deleteSelection(e);
20204					return;
20205			}
20206	
20207			if ((self.isFull() || self.isInputHidden) && !(IS_MAC ? e.metaKey : e.ctrlKey)) {
20208				e.preventDefault();
20209				return;
20210			}
20211		},
20212	
20213		/**
20214		 * Triggered on <input> input.
20215		 *
20216		 * @param {object} e
20217		 * @returns {boolean}
20218		 */
20219		onInput: function(e) {
20220			var self = this;
20221	
20222			var value = self.$control_input.val() || '';
20223			if (self.lastValue !== value) {
20224				self.lastValue = value;
20225				self.onSearchChange(value);
20226				self.refreshOptions();
20227				self.trigger('type', value);
20228			}
20229		},
20230	
20231		/**
20232		 * Invokes the user-provide option provider / loader.
20233		 *
20234		 * Note: this function is debounced in the Selectize
20235		 * constructor (by `settings.loadThrottle` milliseconds)
20236		 *
20237		 * @param {string} value
20238		 */
20239		onSearchChange: function(value) {
20240			var self = this;
20241			var fn = self.settings.load;
20242			if (!fn) return;
20243			if (self.loadedSearches.hasOwnProperty(value)) return;
20244			self.loadedSearches[value] = true;
20245			self.load(function(callback) {
20246				fn.apply(self, [value, callback]);
20247			});
20248		},
20249	
20250		/**
20251		 * Triggered on <input> focus.
20252		 *
20253		 * @param {object} e (optional)
20254		 * @returns {boolean}
20255		 */
20256		onFocus: function(e) {
20257			var self = this;
20258			var wasFocused = self.isFocused;
20259	
20260			if (self.isDisabled) {
20261				self.blur();
20262				e && e.preventDefault();
20263				return false;
20264			}
20265	
20266			if (self.ignoreFocus) return;
20267			self.isFocused = true;
20268			if (self.settings.preload === 'focus') self.onSearchChange('');
20269	
20270			if (!wasFocused) self.trigger('focus');
20271	
20272			if (!self.$activeItems.length) {
20273				self.showInput();
20274				self.setActiveItem(null);
20275				self.refreshOptions(!!self.settings.openOnFocus);
20276			}
20277	
20278			self.refreshState();
20279		},
20280	
20281		/**
20282		 * Triggered on <input> blur.
20283		 *
20284		 * @param {object} e
20285		 * @param {Element} dest
20286		 */
20287		onBlur: function(e, dest) {
20288			var self = this;
20289			if (!self.isFocused) return;
20290			self.isFocused = false;
20291	
20292			if (self.ignoreFocus) {
20293				return;
20294			} else if (!self.ignoreBlur && document.activeElement === self.$dropdown_content[0]) {
20295				// necessary to prevent IE closing the dropdown when the scrollbar is clicked
20296				self.ignoreBlur = true;
20297				self.onFocus(e);
20298				return;
20299			}
20300	
20301			var deactivate = function() {
20302				self.close();
20303				self.setTextboxValue('');
20304				self.setActiveItem(null);
20305				self.setActiveOption(null);
20306				self.setCaret(self.items.length);
20307				self.refreshState();
20308	
20309				// IE11 bug: element still marked as active
20310				dest && dest.focus && dest.focus();
20311	
20312				self.isBlurring = false;
20313				self.ignoreFocus = false;
20314				self.trigger('blur');
20315			};
20316	
20317			self.isBlurring = true;
20318			self.ignoreFocus = true;
20319			if (self.settings.create && self.settings.createOnBlur) {
20320				self.createItem(null, false, deactivate);
20321			} else {
20322				deactivate();
20323			}
20324		},
20325	
20326		/**
20327		 * Triggered when the user rolls over
20328		 * an option in the autocomplete dropdown menu.
20329		 *
20330		 * @param {object} e
20331		 * @returns {boolean}
20332		 */
20333		onOptionHover: function(e) {
20334			if (this.ignoreHover) return;
20335			this.setActiveOption(e.currentTarget, false);
20336		},
20337	
20338		/**
20339		 * Triggered when the user clicks on an option
20340		 * in the autocomplete dropdown menu.
20341		 *
20342		 * @param {object} e
20343		 * @returns {boolean}
20344		 */
20345		onOptionSelect: function(e) {
20346			var value, $target, $option, self = this;
20347	
20348			if (e.preventDefault) {
20349				e.preventDefault();
20350				e.stopPropagation();
20351			}
20352	
20353			$target = $(e.currentTarget);
20354			if ($target.hasClass('create')) {
20355				self.createItem(null, function() {
20356					if (self.settings.closeAfterSelect) {
20357						self.close();
20358					}
20359				});
20360			} else {
20361				value = $target.attr('data-value');
20362				if (typeof value !== 'undefined') {
20363					self.lastQuery = null;
20364					self.setTextboxValue('');
20365					self.addItem(value);
20366					if (self.settings.closeAfterSelect) {
20367						self.close();
20368					} else if (!self.settings.hideSelected && e.type && /mouse/.test(e.type)) {
20369						self.setActiveOption(self.getOption(value));
20370					}
20371				}
20372			}
20373		},
20374	
20375		/**
20376		 * Triggered when the user clicks on an item
20377		 * that has been selected.
20378		 *
20379		 * @param {object} e
20380		 * @returns {boolean}
20381		 */
20382		onItemSelect: function(e) {
20383			var self = this;
20384	
20385			if (self.isLocked) return;
20386			if (self.settings.mode === 'multi') {
20387				e.preventDefault();
20388				self.setActiveItem(e.currentTarget, e);
20389			}
20390		},
20391	
20392		/**
20393		 * Invokes the provided method that provides
20394		 * results to a callback---which are then added
20395		 * as options to the control.
20396		 *
20397		 * @param {function} fn
20398		 */
20399		load: function(fn) {
20400			var self = this;
20401			var $wrapper = self.$wrapper.addClass(self.settings.loadingClass);
20402	
20403			self.loading++;
20404			fn.apply(self, [function(results) {
20405				self.loading = Math.max(self.loading - 1, 0);
20406				if (results && results.length) {
20407					self.addOption(results);
20408					self.refreshOptions(self.isFocused && !self.isInputHidden);
20409				}
20410				if (!self.loading) {
20411					$wrapper.removeClass(self.settings.loadingClass);
20412				}
20413				self.trigger('load', results);
20414			}]);
20415		},
20416	
20417		/**
20418		 * Gets the value of input field of the control.
20419		 *
20420		 * @returns {string} value
20421		 */
20422		getTextboxValue: function() {
20423			var $input = this.$control_input;
20424			return $input.val();
20425		},
20426	
20427		/**
20428		 * Sets the input field of the control to the specified value.
20429		 *
20430		 * @param {string} value
20431		 */
20432		setTextboxValue: function(value) {
20433			var $input = this.$control_input;
20434			var changed = $input.val() !== value;
20435			if (changed) {
20436				$input.val(value).triggerHandler('update');
20437				this.lastValue = value;
20438			}
20439		},
20440	
20441		/**
20442		 * Returns the value of the control. If multiple items
20443		 * can be selected (e.g. <select multiple>), this returns
20444		 * an array. If only one item can be selected, this
20445		 * returns a string.
20446		 *
vendor: 27,147 bytes, lines 20447-21434
20447		 * @returns {mixed}
20448		 */
20449		getValue: function() {
20450			if (this.tagType === TAG_SELECT && this.$input.attr('multiple')) {
20451				return this.items;
20452			} else {
20453				return this.items.join(this.settings.delimiter);
20454			}
20455		},
20456	
20457		/**
20458		 * Resets the selected items to the given value.
20459		 *
20460		 * @param {mixed} value
20461		 */
20462		setValue: function(value, silent) {
20463			var events = silent ? [] : ['change'];
20464	
20465			debounce_events(this, events, function() {
20466				this.clear(silent);
20467				this.addItems(value, silent);
20468			});
20469		},
20470	
20471		/**
20472		 * Resets the number of max items to the given value
20473		 *
20474		 * @param {number} value
20475		 */
20476		setMaxItems: function(value){
20477			if(value === 0) value = null; //reset to unlimited items.
20478			this.settings.maxItems = value;
20479			this.settings.mode = this.settings.mode || (this.settings.maxItems === 1 ? 'single' : 'multi');
20480			this.refreshState();
20481		},
20482	
20483		/**
20484		 * Sets the selected item.
20485		 *
20486		 * @param {object} $item
20487		 * @param {object} e (optional)
20488		 */
20489		setActiveItem: function($item, e) {
20490			var self = this;
20491			var eventName;
20492			var i, idx, begin, end, item, swap;
20493			var $last;
20494	
20495			if (self.settings.mode === 'single') return;
20496			$item = $($item);
20497	
20498			// clear the active selection
20499			if (!$item.length) {
20500				$(self.$activeItems).removeClass('active');
20501				self.$activeItems = [];
20502				if (self.isFocused) {
20503					self.showInput();
20504				}
20505				return;
20506			}
20507	
20508			// modify selection
20509			eventName = e && e.type.toLowerCase();
20510	
20511			if (eventName === 'mousedown' && self.isShiftDown && self.$activeItems.length) {
20512				$last = self.$control.children('.active:last');
20513				begin = Array.prototype.indexOf.apply(self.$control[0].childNodes, [$last[0]]);
20514				end   = Array.prototype.indexOf.apply(self.$control[0].childNodes, [$item[0]]);
20515				if (begin > end) {
20516					swap  = begin;
20517					begin = end;
20518					end   = swap;
20519				}
20520				for (i = begin; i <= end; i++) {
20521					item = self.$control[0].childNodes[i];
20522					if (self.$activeItems.indexOf(item) === -1) {
20523						$(item).addClass('active');
20524						self.$activeItems.push(item);
20525					}
20526				}
20527				e.preventDefault();
20528			} else if ((eventName === 'mousedown' && self.isCtrlDown) || (eventName === 'keydown' && this.isShiftDown)) {
20529				if ($item.hasClass('active')) {
20530					idx = self.$activeItems.indexOf($item[0]);
20531					self.$activeItems.splice(idx, 1);
20532					$item.removeClass('active');
20533				} else {
20534					self.$activeItems.push($item.addClass('active')[0]);
20535				}
20536			} else {
20537				$(self.$activeItems).removeClass('active');
20538				self.$activeItems = [$item.addClass('active')[0]];
20539			}
20540	
20541			// ensure control has focus
20542			self.hideInput();
20543			if (!this.isFocused) {
20544				self.focus();
20545			}
20546		},
20547	
20548		/**
20549		 * Sets the selected item in the dropdown menu
20550		 * of available options.
20551		 *
20552		 * @param {object} $object
20553		 * @param {boolean} scroll
20554		 * @param {boolean} animate
20555		 */
20556		setActiveOption: function($option, scroll, animate) {
20557			var height_menu, height_item, y;
20558			var scroll_top, scroll_bottom;
20559			var self = this;
20560	
20561			if (self.$activeOption) {
20562				self.$activeOption.removeClass('active');
20563				self.trigger('dropdown_item_deactivate', self.$activeOption.attr('data-value'));
20564			}
20565			self.$activeOption = null;
20566	
20567			$option = $($option);
20568			if (!$option.length) return;
20569	
20570			self.$activeOption = $option.addClass('active');
20571			if (self.isOpen) self.trigger('dropdown_item_activate', self.$activeOption.attr('data-value'));
20572	
20573			if (scroll || !isset(scroll)) {
20574	
20575				height_menu   = self.$dropdown_content.height();
20576				height_item   = self.$activeOption.outerHeight(true);
20577				scroll        = self.$dropdown_content.scrollTop() || 0;
20578				y             = self.$activeOption.offset().top - self.$dropdown_content.offset().top + scroll;
20579				scroll_top    = y;
20580				scroll_bottom = y - height_menu + height_item;
20581	
20582				if (y + height_item > height_menu + scroll) {
20583					self.$dropdown_content.stop().animate({scrollTop: scroll_bottom}, animate ? self.settings.scrollDuration : 0);
20584				} else if (y < scroll) {
20585					self.$dropdown_content.stop().animate({scrollTop: scroll_top}, animate ? self.settings.scrollDuration : 0);
20586				}
20587	
20588			}
20589		},
20590	
20591		/**
20592		 * Selects all items (CTRL + A).
20593		 */
20594		selectAll: function() {
20595			var self = this;
20596			if (self.settings.mode === 'single') return;
20597	
20598			self.$activeItems = Array.prototype.slice.apply(self.$control.children(':not(input)').addClass('active'));
20599			if (self.$activeItems.length) {
20600				self.hideInput();
20601				self.close();
20602			}
20603			self.focus();
20604		},
20605	
20606		/**
20607		 * Hides the input element out of view, while
20608		 * retaining its focus.
20609		 */
20610		hideInput: function() {
20611			var self = this;
20612	
20613			self.setTextboxValue('');
20614			self.$control_input.css({opacity: 0, position: 'absolute', left: self.rtl ? 10000 : -10000});
20615			self.isInputHidden = true;
20616		},
20617	
20618		/**
20619		 * Restores input visibility.
20620		 */
20621		showInput: function() {
20622			this.$control_input.css({opacity: 1, position: 'relative', left: 0});
20623			this.isInputHidden = false;
20624		},
20625	
20626		/**
20627		 * Gives the control focus.
20628		 */
20629		focus: function() {
20630			var self = this;
20631			if (self.isDisabled) return self;
20632	
20633			self.ignoreFocus = true;
20634			self.$control_input[0].focus();
20635			window.setTimeout(function() {
20636				self.ignoreFocus = false;
20637				self.onFocus();
20638			}, 0);
20639			return self;
20640		},
20641	
20642		/**
20643		 * Forces the control out of focus.
20644		 *
20645		 * @param {Element} dest
20646		 */
20647		blur: function(dest) {
20648			this.$control_input[0].blur();
20649			this.onBlur(null, dest);
20650			return this;
20651		},
20652	
20653		/**
20654		 * Returns a function that scores an object
20655		 * to show how good of a match it is to the
20656		 * provided query.
20657		 *
20658		 * @param {string} query
20659		 * @param {object} options
20660		 * @return {function}
20661		 */
20662		getScoreFunction: function(query) {
20663			return this.sifter.getScoreFunction(query, this.getSearchOptions());
20664		},
20665	
20666		/**
20667		 * Returns search options for sifter (the system
20668		 * for scoring and sorting results).
20669		 *
20670		 * @see https://github.com/brianreavis/sifter.js
20671		 * @return {object}
20672		 */
20673		getSearchOptions: function() {
20674			var settings = this.settings;
20675			var sort = settings.sortField;
20676			if (typeof sort === 'string') {
20677				sort = [{field: sort}];
20678			}
20679	
20680			return {
20681				fields      : settings.searchField,
20682				conjunction : settings.searchConjunction,
20683				sort        : sort,
20684				nesting     : settings.nesting
20685			};
20686		},
20687	
20688		/**
20689		 * Searches through available options and returns
20690		 * a sorted array of matches.
20691		 *
20692		 * Returns an object containing:
20693		 *
20694		 *   - query {string}
20695		 *   - tokens {array}
20696		 *   - total {int}
20697		 *   - items {array}
20698		 *
20699		 * @param {string} query
20700		 * @returns {object}
20701		 */
20702		search: function(query) {
20703			var i, value, score, result, calculateScore;
20704			var self     = this;
20705			var settings = self.settings;
20706			var options  = this.getSearchOptions();
20707	
20708			// validate user-provided result scoring function
20709			if (settings.score) {
20710				calculateScore = self.settings.score.apply(this, [query]);
20711				if (typeof calculateScore !== 'function') {
20712					throw new Error('Selectize "score" setting must be a function that returns a function');
20713				}
20714			}
20715	
20716			// perform search
20717			if (query !== self.lastQuery) {
20718				self.lastQuery = query;
20719				result = self.sifter.search(query, $.extend(options, {score: calculateScore}));
20720				self.currentResults = result;
20721			} else {
20722				result = $.extend(true, {}, self.currentResults);
20723			}
20724	
20725			// filter out selected items
20726			if (settings.hideSelected) {
20727				for (i = result.items.length - 1; i >= 0; i--) {
20728					if (self.items.indexOf(hash_key(result.items[i].id)) !== -1) {
20729						result.items.splice(i, 1);
20730					}
20731				}
20732			}
20733	
20734			return result;
20735		},
20736	
20737		/**
20738		 * Refreshes the list of available options shown
20739		 * in the autocomplete dropdown menu.
20740		 *
20741		 * @param {boolean} triggerDropdown
20742		 */
20743		refreshOptions: function(triggerDropdown) {
20744			var i, j, k, n, groups, groups_order, option, option_html, optgroup, optgroups, html, html_children, has_create_option;
20745			var $active, $active_before, $create;
20746	
20747			if (typeof triggerDropdown === 'undefined') {
20748				triggerDropdown = true;
20749			}
20750	
20751			var self              = this;
20752			var query             = (self.$control_input.val()).trim();
20753			var results           = self.search(query);
20754			var $dropdown_content = self.$dropdown_content;
20755			var active_before     = self.$activeOption && hash_key(self.$activeOption.attr('data-value'));
20756	
20757			// build markup
20758			n = results.items.length;
20759			if (typeof self.settings.maxOptions === 'number') {
20760				n = Math.min(n, self.settings.maxOptions);
20761			}
20762	
20763			// render and group available options individually
20764			groups = {};
20765			groups_order = [];
20766	
20767			for (i = 0; i < n; i++) {
20768				option      = self.options[results.items[i].id];
20769				option_html = self.render('option', option);
20770				optgroup    = option[self.settings.optgroupField] || '';
20771				optgroups   = Array.isArray(optgroup) ? optgroup : [optgroup];
20772	
20773				for (j = 0, k = optgroups && optgroups.length; j < k; j++) {
20774					optgroup = optgroups[j];
20775					if (!self.optgroups.hasOwnProperty(optgroup)) {
20776						optgroup = '';
20777					}
20778					if (!groups.hasOwnProperty(optgroup)) {
20779						groups[optgroup] = document.createDocumentFragment();
20780						groups_order.push(optgroup);
20781					}
20782					groups[optgroup].appendChild(option_html);
20783				}
20784			}
20785	
20786			// sort optgroups
20787			if (this.settings.lockOptgroupOrder) {
20788				groups_order.sort(function(a, b) {
20789					var a_order = self.optgroups[a] && self.optgroups[a].$order || 0;
20790					var b_order = self.optgroups[b] && self.optgroups[b].$order || 0;
20791					return a_order - b_order;
20792				});
20793			}
20794	
20795			// render optgroup headers & join groups
20796			html = document.createDocumentFragment();
20797			for (i = 0, n = groups_order.length; i < n; i++) {
20798				optgroup = groups_order[i];
20799				if (self.optgroups.hasOwnProperty(optgroup) && groups[optgroup].childNodes.length) {
20800					// render the optgroup header and options within it,
20801					// then pass it to the wrapper template
20802					html_children = document.createDocumentFragment();
20803					html_children.appendChild(self.render('optgroup_header', self.optgroups[optgroup]));
20804					html_children.appendChild(groups[optgroup]);
20805	
20806					html.appendChild(self.render('optgroup', $.extend({}, self.optgroups[optgroup], {
20807						html: domToString(html_children),
20808						dom:  html_children
20809					})));
20810				} else {
20811					html.appendChild(groups[optgroup]);
20812				}
20813			}
20814	
20815			$dropdown_content.html(html);
20816	
20817			// highlight matching terms inline
20818			if (self.settings.highlight) {
20819				$dropdown_content.removeHighlight();
20820				if (results.query.length && results.tokens.length) {
20821					for (i = 0, n = results.tokens.length; i < n; i++) {
20822						highlight($dropdown_content, results.tokens[i].regex);
20823					}
20824				}
20825			}
20826	
20827			// add "selected" class to selected options
20828			if (!self.settings.hideSelected) {
20829				// clear selection on all previously selected elements first
20830				self.$dropdown.find('.selected').removeClass('selected');
20831	
20832				for (i = 0, n = self.items.length; i < n; i++) {
20833					self.getOption(self.items[i]).addClass('selected');
20834				}
20835			}
20836	
20837			// add create option
20838			has_create_option = self.canCreate(query);
20839			if (has_create_option) {
20840				if(self.settings.showAddOptionOnCreate) {
20841					$dropdown_content.prepend(self.render('option_create', {input: query}));
20842					$create = $($dropdown_content[0].childNodes[0]);
20843				}
20844			}
20845	
20846			// activate
20847			self.hasOptions = results.items.length > 0 || ( has_create_option && self.settings.showAddOptionOnCreate );
20848			if (self.hasOptions) {
20849				if (results.items.length > 0) {
20850					$active_before = active_before && self.getOption(active_before);
20851					if (results.query !== "" && $active_before && $active_before.length) {
20852						$active = $active_before;
20853					} else if (self.settings.mode === 'single' && self.items.length) {
20854						$active = self.getOption(self.items[0]);
20855					}
20856					if (!$active || !$active.length) {
20857						if ($create && !self.settings.addPrecedence) {
20858							$active = self.getAdjacentOption($create, 1);
20859						} else {
20860							$active = $dropdown_content.find('[data-selectable]:first');
20861						}
20862					}
20863				} else {
20864					$active = $create;
20865				}
20866				self.setActiveOption($active);
20867				if (triggerDropdown && !self.isOpen) { self.open(); }
20868			} else {
20869				self.setActiveOption(null);
20870				if (triggerDropdown && self.isOpen) { self.close(); }
20871			}
20872		},
20873	
20874		/**
20875		 * Adds an available option. If it already exists,
20876		 * nothing will happen. Note: this does not refresh
20877		 * the options list dropdown (use `refreshOptions`
20878		 * for that).
20879		 *
20880		 * Usage:
20881		 *
20882		 *   this.addOption(data)
20883		 *
20884		 * @param {object|array} data
20885		 */
20886		addOption: function(data) {
20887			var i, n, value, self = this;
20888	
20889			if (Array.isArray(data)) {
20890				for (i = 0, n = data.length; i < n; i++) {
20891					self.addOption(data[i]);
20892				}
20893				return;
20894			}
20895	
20896			if (value = self.registerOption(data)) {
20897				self.userOptions[value] = true;
20898				self.lastQuery = null;
20899				self.trigger('option_add', value, data);
20900			}
20901		},
20902	
20903		/**
20904		 * Registers an option to the pool of options.
20905		 *
20906		 * @param {object} data
20907		 * @return {boolean|string}
20908		 */
20909		registerOption: function(data) {
20910			var key = hash_key(data[this.settings.valueField]);
20911			if (typeof key === 'undefined' || key === null || this.options.hasOwnProperty(key)) return false;
20912			data.$order = data.$order || ++this.order;
20913			this.options[key] = data;
20914			return key;
20915		},
20916	
20917		/**
20918		 * Registers an option group to the pool of option groups.
20919		 *
20920		 * @param {object} data
20921		 * @return {boolean|string}
20922		 */
20923		registerOptionGroup: function(data) {
20924			var key = hash_key(data[this.settings.optgroupValueField]);
20925			if (!key) return false;
20926	
20927			data.$order = data.$order || ++this.order;
20928			this.optgroups[key] = data;
20929			return key;
20930		},
20931	
20932		/**
20933		 * Registers a new optgroup for options
20934		 * to be bucketed into.
20935		 *
20936		 * @param {string} id
20937		 * @param {object} data
20938		 */
20939		addOptionGroup: function(id, data) {
20940			data[this.settings.optgroupValueField] = id;
20941			if (id = this.registerOptionGroup(data)) {
20942				this.trigger('optgroup_add', id, data);
20943			}
20944		},
20945	
20946		/**
20947		 * Removes an existing option group.
20948		 *
20949		 * @param {string} id
20950		 */
20951		removeOptionGroup: function(id) {
20952			if (this.optgroups.hasOwnProperty(id)) {
20953				delete this.optgroups[id];
20954				this.renderCache = {};
20955				this.trigger('optgroup_remove', id);
20956			}
20957		},
20958	
20959		/**
20960		 * Clears all existing option groups.
20961		 */
20962		clearOptionGroups: function() {
20963			this.optgroups = {};
20964			this.renderCache = {};
20965			this.trigger('optgroup_clear');
20966		},
20967	
20968		/**
20969		 * Updates an option available for selection. If
20970		 * it is visible in the selected items or options
20971		 * dropdown, it will be re-rendered automatically.
20972		 *
20973		 * @param {string} value
20974		 * @param {object} data
20975		 */
20976		updateOption: function(value, data) {
20977			var self = this;
20978			var $item, $item_new;
20979			var value_new, index_item, cache_items, cache_options, order_old;
20980	
20981			value     = hash_key(value);
20982			value_new = hash_key(data[self.settings.valueField]);
20983	
20984			// sanity checks
20985			if (value === null) return;
20986			if (!self.options.hasOwnProperty(value)) return;
20987			if (typeof value_new !== 'string') throw new Error('Value must be set in option data');
20988	
20989			order_old = self.options[value].$order;
20990	
20991			// update references
20992			if (value_new !== value) {
20993				delete self.options[value];
20994				index_item = self.items.indexOf(value);
20995				if (index_item !== -1) {
20996					self.items.splice(index_item, 1, value_new);
20997				}
20998			}
20999			data.$order = data.$order || order_old;
21000			self.options[value_new] = data;
21001	
21002			// invalidate render cache
21003			cache_items = self.renderCache['item'];
21004			cache_options = self.renderCache['option'];
21005	
21006			if (cache_items) {
21007				delete cache_items[value];
21008				delete cache_items[value_new];
21009			}
21010			if (cache_options) {
21011				delete cache_options[value];
21012				delete cache_options[value_new];
21013			}
21014	
21015			// update the item if it's selected
21016			if (self.items.indexOf(value_new) !== -1) {
21017				$item = self.getItem(value);
21018				$item_new = $(self.render('item', data));
21019				if ($item.hasClass('active')) $item_new.addClass('active');
21020				$item.replaceWith($item_new);
21021			}
21022	
21023			// invalidate last query because we might have updated the sortField
21024			self.lastQuery = null;
21025	
21026			// update dropdown contents
21027			if (self.isOpen) {
21028				self.refreshOptions(false);
21029			}
21030		},
21031	
21032		/**
21033		 * Removes a single option.
21034		 *
21035		 * @param {string} value
21036		 * @param {boolean} silent
21037		 */
21038		removeOption: function(value, silent) {
21039			var self = this;
21040			value = hash_key(value);
21041	
21042			var cache_items = self.renderCache['item'];
21043			var cache_options = self.renderCache['option'];
21044			if (cache_items) delete cache_items[value];
21045			if (cache_options) delete cache_options[value];
21046	
21047			delete self.userOptions[value];
21048			delete self.options[value];
21049			self.lastQuery = null;
21050			self.trigger('option_remove', value);
21051			self.removeItem(value, silent);
21052		},
21053	
21054		/**
21055		 * Clears all options.
21056		 *
21057		 * @param {boolean} silent
21058		 */
21059		clearOptions: function(silent) {
21060			var self = this;
21061	
21062			self.loadedSearches = {};
21063			self.userOptions = {};
21064			self.renderCache = {};
21065			var options = self.options;
21066			$.each(self.options, function(key, value) {
21067				if(self.items.indexOf(key) == -1) {
21068					delete options[key];
21069				}
21070			});
21071			self.options = self.sifter.items = options;
21072			self.lastQuery = null;
21073			self.trigger('option_clear');
21074			self.clear(silent);
21075		},
21076	
21077		/**
21078		 * Returns the jQuery element of the option
21079		 * matching the given value.
21080		 *
21081		 * @param {string} value
21082		 * @returns {object}
21083		 */
21084		getOption: function(value) {
21085			return this.getElementWithValue(value, this.$dropdown_content.find('[data-selectable]'));
21086		},
21087	
21088		/**
21089		 * Returns the jQuery element of the first
21090		 * selectable option.
21091		 *
21092		 * @return {object}
21093		 */
21094		getFirstOption: function() {
21095			var $options = this.$dropdown.find('[data-selectable]');
21096			return $options.length > 0 ? $options.eq(0) : $();
21097		},
21098	
21099		/**
21100		 * Returns the jQuery element of the next or
21101		 * previous selectable option.
21102		 *
21103		 * @param {object} $option
21104		 * @param {int} direction  can be 1 for next or -1 for previous
21105		 * @return {object}
21106		 */
21107		getAdjacentOption: function($option, direction) {
21108			var $options = this.$dropdown.find('[data-selectable]');
21109			var index    = $options.index($option) + direction;
21110	
21111			return index >= 0 && index < $options.length ? $options.eq(index) : $();
21112		},
21113	
21114		/**
21115		 * Finds the first element with a "data-value" attribute
21116		 * that matches the given value.
21117		 *
21118		 * @param {mixed} value
21119		 * @param {object} $els
21120		 * @return {object}
21121		 */
21122		getElementWithValue: function(value, $els) {
21123			value = hash_key(value);
21124	
21125			if (typeof value !== 'undefined' && value !== null) {
21126				for (var i = 0, n = $els.length; i < n; i++) {
21127					if ($els[i].getAttribute('data-value') === value) {
21128						return $($els[i]);
21129					}
21130				}
21131			}
21132	
21133			return $();
21134		},
21135	
21136		/**
21137		 * Finds the first element with a "textContent" property
21138		 * that matches the given textContent value.
21139		 *
21140		 * @param {mixed} textContent
21141		 * @param {boolean} ignoreCase
21142		 * @param {object} $els
21143		 * @return {object}
21144		 */
21145		getElementWithTextContent: function(textContent, ignoreCase ,$els) {
21146			textContent = hash_key(textContent);
21147	
21148			if (typeof textContent !== 'undefined' && textContent !== null) {
21149				for (var i = 0, n = $els.length; i < n; i++) {
21150					var eleTextContent = $els[i].textContent
21151					if (ignoreCase == true) {
21152						eleTextContent = (eleTextContent !== null) ? eleTextContent.toLowerCase() : null;
21153						textContent = textContent.toLowerCase();
21154					}
21155					if (eleTextContent === textContent) {
21156						return $($els[i]);
21157					}
21158				}
21159			}
21160	
21161			return $();
21162		},
21163	
21164		/**
21165		 * Returns the jQuery element of the item
21166		 * matching the given value.
21167		 *
21168		 * @param {string} value
21169		 * @returns {object}
21170		 */
21171		getItem: function(value) {
21172			return this.getElementWithValue(value, this.$control.children());
21173		},
21174	
21175		/**
21176		 * Returns the jQuery element of the item
21177		 * matching the given textContent.
21178		 *
21179		 * @param {string} value
21180		 * @param {boolean} ignoreCase
21181		 * @returns {object}
21182		 */
21183		getFirstItemMatchedByTextContent: function(textContent, ignoreCase) {
21184			ignoreCase = (ignoreCase !== null && ignoreCase === true) ? true : false;
21185			return this.getElementWithTextContent(textContent, ignoreCase, this.$dropdown_content.find('[data-selectable]'));
21186		},
21187	
21188		/**
21189		 * "Selects" multiple items at once. Adds them to the list
21190		 * at the current caret position.
21191		 *
21192		 * @param {string} value
21193		 * @param {boolean} silent
21194		 */
21195		addItems: function(values, silent) {
21196			this.buffer = document.createDocumentFragment();
21197	
21198			var childNodes = this.$control[0].childNodes;
21199			for (var i = 0; i < childNodes.length; i++) {
21200				this.buffer.appendChild(childNodes[i]);
21201			}
21202	
21203			var items = Array.isArray(values) ? values : [values];
21204			for (var i = 0, n = items.length; i < n; i++) {
21205				this.isPending = (i < n - 1);
21206				this.addItem(items[i], silent);
21207			}
21208	
21209			var control = this.$control[0];
21210			control.insertBefore(this.buffer, control.firstChild);
21211	
21212			this.buffer = null;
21213		},
21214	
21215		/**
21216		 * "Selects" an item. Adds it to the list
21217		 * at the current caret position.
21218		 *
21219		 * @param {string} value
21220		 * @param {boolean} silent
21221		 */
21222		addItem: function(value, silent) {
21223			var events = silent ? [] : ['change'];
21224	
21225			debounce_events(this, events, function() {
21226				var $item, $option, $options;
21227				var self = this;
21228				var inputMode = self.settings.mode;
21229				var i, active, value_next, wasFull;
21230				value = hash_key(value);
21231	
21232				if (self.items.indexOf(value) !== -1) {
21233					if (inputMode === 'single') self.close();
21234					return;
21235				}
21236	
21237				if (!self.options.hasOwnProperty(value)) return;
21238				if (inputMode === 'single') self.clear(silent);
21239				if (inputMode === 'multi' && self.isFull()) return;
21240	
21241				$item = $(self.render('item', self.options[value]));
21242				wasFull = self.isFull();
21243				self.items.splice(self.caretPos, 0, value);
21244				self.insertAtCaret($item);
21245				if (!self.isPending || (!wasFull && self.isFull())) {
21246					self.refreshState();
21247				}
21248	
21249				if (self.isSetup) {
21250					$options = self.$dropdown_content.find('[data-selectable]');
21251	
21252					// update menu / remove the option (if this is not one item being added as part of series)
21253					if (!self.isPending) {
21254						$option = self.getOption(value);
21255						value_next = self.getAdjacentOption($option, 1).attr('data-value');
21256						self.refreshOptions(self.isFocused && inputMode !== 'single');
21257						if (value_next) {
21258							self.setActiveOption(self.getOption(value_next));
21259						}
21260					}
21261	
21262					// hide the menu if the maximum number of items have been selected or no options are left
21263					if (!$options.length || self.isFull()) {
21264						self.close();
21265					} else if (!self.isPending) {
21266						self.positionDropdown();
21267					}
21268	
21269					self.updatePlaceholder();
21270					self.trigger('item_add', value, $item);
21271	
21272					if (!self.isPending) {
21273						self.updateOriginalInput({silent: silent});
21274					}
21275				}
21276			});
21277		},
21278	
21279		/**
21280		 * Removes the selected item matching
21281		 * the provided value.
21282		 *
21283		 * @param {string} value
21284		 */
21285		removeItem: function(value, silent) {
21286			var self = this;
21287			var $item, i, idx;
21288	
21289			$item = (value instanceof $) ? value : self.getItem(value);
21290			value = hash_key($item.attr('data-value'));
21291			i = self.items.indexOf(value);
21292	
21293			if (i !== -1) {
21294				self.trigger('item_before_remove', value, $item);
21295				$item.remove();
21296				if ($item.hasClass('active')) {
21297					idx = self.$activeItems.indexOf($item[0]);
21298					self.$activeItems.splice(idx, 1);
21299				}
21300	
21301				self.items.splice(i, 1);
21302				self.lastQuery = null;
21303				if (!self.settings.persist && self.userOptions.hasOwnProperty(value)) {
21304					self.removeOption(value, silent);
21305				}
21306	
21307				if (i < self.caretPos) {
21308					self.setCaret(self.caretPos - 1);
21309				}
21310	
21311				self.refreshState();
21312				self.updatePlaceholder();
21313				self.updateOriginalInput({silent: silent});
21314				self.positionDropdown();
21315				self.trigger('item_remove', value, $item);
21316			}
21317		},
21318	
21319		/**
21320		 * Invokes the `create` method provided in the
21321		 * selectize options that should provide the data
21322		 * for the new item, given the user input.
21323		 *
21324		 * Once this completes, it will be added
21325		 * to the item list.
21326		 *
21327		 * @param {string} value
21328		 * @param {boolean} [triggerDropdown]
21329		 * @param {function} [callback]
21330		 * @return {boolean}
21331		 */
21332		createItem: function(input, triggerDropdown) {
21333			var self  = this;
21334			var caret = self.caretPos;
21335			input = input || (self.$control_input.val() || '').trim();
21336	
21337			var callback = arguments[arguments.length - 1];
21338			if (typeof callback !== 'function') callback = function() {};
21339	
21340			if (typeof triggerDropdown !== 'boolean') {
21341				triggerDropdown = true;
21342			}
21343	
21344			if (!self.canCreate(input)) {
21345				callback();
21346				return false;
21347			}
21348	
21349			self.lock();
21350	
21351			var setup = (typeof self.settings.create === 'function') ? this.settings.create : function(input) {
21352				var data = {};
21353				data[self.settings.labelField] = input;
21354				var key = input;
21355				if ( self.settings.formatValueToKey && typeof self.settings.formatValueToKey === 'function' ) {
21356					key = self.settings.formatValueToKey.apply(this, [key]);
21357					if (key === null || typeof key === 'undefined' || typeof key === 'object' || typeof key === 'function') {
21358						throw new Error('Selectize "formatValueToKey" setting must be a function that returns a value other than object or function.');
21359					}
21360				}
21361				data[self.settings.valueField] = key;
21362				return data;
21363			};
21364	
21365			var create = once(function(data) {
21366				self.unlock();
21367	
21368				if (!data || typeof data !== 'object') return callback();
21369				var value = hash_key(data[self.settings.valueField]);
21370				if (typeof value !== 'string') return callback();
21371	
21372				self.setTextboxValue('');
21373				self.addOption(data);
21374				self.setCaret(caret);
21375				self.addItem(value);
21376				self.refreshOptions(triggerDropdown && self.settings.mode !== 'single');
21377				callback(data);
21378			});
21379	
21380			var output = setup.apply(this, [input, create]);
21381			if (typeof output !== 'undefined') {
21382				create(output);
21383			}
21384	
21385			return true;
21386		},
21387	
21388		/**
21389		 * Re-renders the selected item lists.
21390		 */
21391		refreshItems: function() {
21392			this.lastQuery = null;
21393	
21394			if (this.isSetup) {
21395				this.addItem(this.items);
21396			}
21397	
21398			this.refreshState();
21399			this.updateOriginalInput();
21400		},
21401	
21402		/**
21403		 * Updates all state-dependent attributes
21404		 * and CSS classes.
21405		 */
21406		refreshState: function() {
21407			this.refreshValidityState();
21408			this.refreshClasses();
21409		},
21410	
21411		/**
21412		 * Update the `required` attribute of both input and control input.
21413		 *
21414		 * The `required` property needs to be activated on the control input
21415		 * for the error to be displayed at the right place. `required` also
21416		 * needs to be temporarily deactivated on the input since the input is
21417		 * hidden and can't show errors.
21418		 */
21419		refreshValidityState: function() {
21420			if (!this.isRequired) return false;
21421	
21422			var invalid = !this.items.length;
21423	
21424			this.isInvalid = invalid;
21425			this.$control_input.prop('required', invalid);
21426			this.$input.prop('required', !invalid);
21427		},
21428	
21429		/**
21430		 * Updates all state-dependent CSS classes.
21431		 */
21432		refreshClasses: function() {
21433			var self     = this;
21434			var isFull   = self.isFull();
vendor: 5,543 bytes, lines 21435-21630
21435			var isLocked = self.isLocked;
21436	
21437			self.$wrapper
21438				.toggleClass('rtl', self.rtl);
21439	
21440			self.$control
21441				.toggleClass('focus', self.isFocused)
21442				.toggleClass('disabled', self.isDisabled)
21443				.toggleClass('required', self.isRequired)
21444				.toggleClass('invalid', self.isInvalid)
21445				.toggleClass('locked', isLocked)
21446				.toggleClass('full', isFull).toggleClass('not-full', !isFull)
21447				.toggleClass('input-active', self.isFocused && !self.isInputHidden)
21448				.toggleClass('dropdown-active', self.isOpen)
21449				.toggleClass('has-options', !$.isEmptyObject(self.options))
21450				.toggleClass('has-items', self.items.length > 0);
21451	
21452			self.$control_input.data('grow', !isFull && !isLocked);
21453		},
21454	
21455		/**
21456		 * Determines whether or not more items can be added
21457		 * to the control without exceeding the user-defined maximum.
21458		 *
21459		 * @returns {boolean}
21460		 */
21461		isFull: function() {
21462			return this.settings.maxItems !== null && this.items.length >= this.settings.maxItems;
21463		},
21464	
21465		/**
21466		 * Refreshes the original <select> or <input>
21467		 * element to reflect the current state.
21468		 */
21469		updateOriginalInput: function(opts) {
21470			var i, n, options, label, self = this;
21471			opts = opts || {};
21472	
21473			if (self.tagType === TAG_SELECT) {
21474				options = [];
21475				for (i = 0, n = self.items.length; i < n; i++) {
21476					label = self.options[self.items[i]][self.settings.labelField] || '';
21477					options.push('<option value="' + escape_html(self.items[i]) + '" selected="selected">' + escape_html(label) + '</option>');
21478				}
21479				if (!options.length && !this.$input.attr('multiple')) {
21480					options.push('<option value="" selected="selected"></option>');
21481				}
21482				self.$input.html(options.join(''));
21483			} else {
21484				self.$input.val(self.getValue());
21485				self.$input.attr('value',self.$input.val());
21486			}
21487	
21488			if (self.isSetup) {
21489				if (!opts.silent) {
21490					self.trigger('change', self.$input.val());
21491				}
21492			}
21493		},
21494	
21495		/**
21496		 * Shows/hide the input placeholder depending
21497		 * on if there items in the list already.
21498		 */
21499		updatePlaceholder: function() {
21500			if (!this.settings.placeholder) return;
21501			var $input = this.$control_input;
21502	
21503			if (this.items.length) {
21504				$input.removeAttr('placeholder');
21505			} else {
21506				$input.attr('placeholder', this.settings.placeholder);
21507			}
21508			$input.triggerHandler('update', {force: true});
21509		},
21510	
21511		/**
21512		 * Shows the autocomplete dropdown containing
21513		 * the available options.
21514		 */
21515		open: function() {
21516			var self = this;
21517	
21518			if (self.isLocked || self.isOpen || (self.settings.mode === 'multi' && self.isFull())) return;
21519			self.focus();
21520			self.isOpen = true;
21521			self.refreshState();
21522			self.$dropdown.css({visibility: 'hidden', display: 'block'});
21523			self.positionDropdown();
21524			self.$dropdown.css({visibility: 'visible'});
21525			self.trigger('dropdown_open', self.$dropdown);
21526		},
21527	
21528		/**
21529		 * Closes the autocomplete dropdown menu.
21530		 */
21531		close: function() {
21532			var self = this;
21533			var trigger = self.isOpen;
21534	
21535			if (self.settings.mode === 'single' && self.items.length) {
21536				self.hideInput();
21537	
21538				// Do not trigger blur while inside a blur event,
21539				// this fixes some weird tabbing behavior in FF and IE.
21540				// See #1164
21541				if (self.isBlurring) {
21542					self.$control_input.blur(); // close keyboard on iOS
21543				}
21544			}
21545	
21546			self.isOpen = false;
21547			self.$dropdown.hide();
21548			self.setActiveOption(null);
21549			self.refreshState();
21550	
21551			if (trigger) self.trigger('dropdown_close', self.$dropdown);
21552		},
21553	
21554		/**
21555		 * Calculates and applies the appropriate
21556		 * position of the dropdown.
21557		 */
21558		positionDropdown: function() {
21559			var $control = this.$control;
21560			var offset = this.settings.dropdownParent === 'body' ? $control.offset() : $control.position();
21561			offset.top += $control.outerHeight(true);
21562	
21563			this.$dropdown.css({
21564				width : $control[0].getBoundingClientRect().width,
21565				top   : offset.top,
21566				left  : offset.left
21567			});
21568		},
21569	
21570		/**
21571		 * Resets / clears all selected items
21572		 * from the control.
21573		 *
21574		 * @param {boolean} silent
21575		 */
21576		clear: function(silent) {
21577			var self = this;
21578	
21579			if (!self.items.length) return;
21580			self.$control.children(':not(input)').remove();
21581			self.items = [];
21582			self.lastQuery = null;
21583			self.setCaret(0);
21584			self.setActiveItem(null);
21585			self.updatePlaceholder();
21586			self.updateOriginalInput({silent: silent});
21587			self.refreshState();
21588			self.showInput();
21589			self.trigger('clear');
21590		},
21591	
21592		/**
21593		 * A helper method for inserting an element
21594		 * at the current caret position.
21595		 *
21596		 * @param {object} $el
21597		 */
21598		insertAtCaret: function($el) {
21599			var caret = Math.min(this.caretPos, this.items.length);
21600			var el = $el[0];
21601			var target = this.buffer || this.$control[0];
21602	
21603			if (caret === 0) {
21604				target.insertBefore(el, target.firstChild);
21605			} else {
21606				target.insertBefore(el, target.childNodes[caret]);
21607			}
21608	
21609			this.setCaret(caret + 1);
21610		},
21611	
21612		/**
21613		 * Removes the current selected item(s).
21614		 *
21615		 * @param {object} e (optional)
21616		 * @returns {boolean}
21617		 */
21618		deleteSelection: function(e) {
21619			var i, n, direction, selection, values, caret, option_select, $option_select, $tail;
21620			var self = this;
21621	
21622			direction = (e && e.keyCode === KEY_BACKSPACE) ? -1 : 1;
21623			selection = getSelection(self.$control_input[0]);
21624	
21625			if (self.$activeOption && !self.settings.hideSelected) {
21626				if (typeof self.settings.deselectBehavior === 'string' && self.settings.deselectBehavior === 'top') {
21627					option_select = self.getFirstOption().attr('data-value');
21628				} else {
21629					option_select = self.getAdjacentOption(self.$activeOption, -1).attr('data-value');
21630				}
vendor: 8,464 bytes, lines 21630-21965
21630
21631			}
21632	
21633			// determine items that will be removed
21634			values = [];
21635	
21636			if (self.$activeItems.length) {
21637				$tail = self.$control.children('.active:' + (direction > 0 ? 'last' : 'first'));
21638				caret = self.$control.children(':not(input)').index($tail);
21639				if (direction > 0) { caret++; }
21640	
21641				for (i = 0, n = self.$activeItems.length; i < n; i++) {
21642					values.push($(self.$activeItems[i]).attr('data-value'));
21643				}
21644				if (e) {
21645					e.preventDefault();
21646					e.stopPropagation();
21647				}
21648			} else if ((self.isFocused || self.settings.mode === 'single') && self.items.length) {
21649				if (direction < 0 && selection.start === 0 && selection.length === 0) {
21650					values.push(self.items[self.caretPos - 1]);
21651				} else if (direction > 0 && selection.start === self.$control_input.val().length) {
21652					values.push(self.items[self.caretPos]);
21653				}
21654			}
21655	
21656			// allow the callback to abort
21657			if (!values.length || (typeof self.settings.onDelete === 'function' && self.settings.onDelete.apply(self, [values]) === false)) {
21658				return false;
21659			}
21660	
21661			// perform removal
21662			if (typeof caret !== 'undefined') {
21663				self.setCaret(caret);
21664			}
21665			while (values.length) {
21666				self.removeItem(values.pop());
21667			}
21668	
21669			self.showInput();
21670			self.positionDropdown();
21671			self.refreshOptions(true);
21672	
21673			// select previous option
21674			if (option_select) {
21675				$option_select = self.getOption(option_select);
21676				if ($option_select.length) {
21677					self.setActiveOption($option_select);
21678				}
21679			}
21680	
21681			return true;
21682		},
21683	
21684		/**
21685		 * Selects the previous / next item (depending
21686		 * on the `direction` argument).
21687		 *
21688		 * > 0 - right
21689		 * < 0 - left
21690		 *
21691		 * @param {int} direction
21692		 * @param {object} e (optional)
21693		 */
21694		advanceSelection: function(direction, e) {
21695			var tail, selection, idx, valueLength, cursorAtEdge, $tail;
21696			var self = this;
21697	
21698			if (direction === 0) return;
21699			if (self.rtl) direction *= -1;
21700	
21701			tail = direction > 0 ? 'last' : 'first';
21702			selection = getSelection(self.$control_input[0]);
21703	
21704			if (self.isFocused && !self.isInputHidden) {
21705				valueLength = self.$control_input.val().length;
21706				cursorAtEdge = direction < 0
21707					? selection.start === 0 && selection.length === 0
21708					: selection.start === valueLength;
21709	
21710				if (cursorAtEdge && !valueLength) {
21711					self.advanceCaret(direction, e);
21712				}
21713			} else {
21714				$tail = self.$control.children('.active:' + tail);
21715				if ($tail.length) {
21716					idx = self.$control.children(':not(input)').index($tail);
21717					self.setActiveItem(null);
21718					self.setCaret(direction > 0 ? idx + 1 : idx);
21719				}
21720			}
21721		},
21722	
21723		/**
21724		 * Moves the caret left / right.
21725		 *
21726		 * @param {int} direction
21727		 * @param {object} e (optional)
21728		 */
21729		advanceCaret: function(direction, e) {
21730			var self = this, fn, $adj;
21731	
21732			if (direction === 0) return;
21733	
21734			fn = direction > 0 ? 'next' : 'prev';
21735			if (self.isShiftDown) {
21736				$adj = self.$control_input[fn]();
21737				if ($adj.length) {
21738					self.hideInput();
21739					self.setActiveItem($adj);
21740					e && e.preventDefault();
21741				}
21742			} else {
21743				self.setCaret(self.caretPos + direction);
21744			}
21745		},
21746	
21747		/**
21748		 * Moves the caret to the specified index.
21749		 *
21750		 * @param {int} i
21751		 */
21752		setCaret: function(i) {
21753			var self = this;
21754	
21755			if (self.settings.mode === 'single') {
21756				i = self.items.length;
21757			} else {
21758				i = Math.max(0, Math.min(self.items.length, i));
21759			}
21760	
21761			if(!self.isPending) {
21762				// the input must be moved by leaving it in place and moving the
21763				// siblings, due to the fact that focus cannot be restored once lost
21764				// on mobile webkit devices
21765				var j, n, fn, $children, $child;
21766				$children = self.$control.children(':not(input)');
21767				for (j = 0, n = $children.length; j < n; j++) {
21768					$child = $($children[j]).detach();
21769					if (j <  i) {
21770						self.$control_input.before($child);
21771					} else {
21772						self.$control.append($child);
21773					}
21774				}
21775			}
21776	
21777			self.caretPos = i;
21778		},
21779	
21780		/**
21781		 * Disables user input on the control. Used while
21782		 * items are being asynchronously created.
21783		 */
21784		lock: function() {
21785			this.close();
21786			this.isLocked = true;
21787			this.refreshState();
21788		},
21789	
21790		/**
21791		 * Re-enables user input on the control.
21792		 */
21793		unlock: function() {
21794			this.isLocked = false;
21795			this.refreshState();
21796		},
21797	
21798		/**
21799		 * Disables user input on the control completely.
21800		 * While disabled, it cannot receive focus.
21801		 */
21802		disable: function() {
21803			var self = this;
21804			self.$input.prop('disabled', true);
21805			self.$control_input.prop('disabled', true).prop('tabindex', -1);
21806			self.isDisabled = true;
21807			self.lock();
21808		},
21809	
21810		/**
21811		 * Enables the control so that it can respond
21812		 * to focus and user input.
21813		 */
21814		enable: function() {
21815			var self = this;
21816			self.$input.prop('disabled', false);
21817			self.$control_input.prop('disabled', false).prop('tabindex', self.tabIndex);
21818			self.isDisabled = false;
21819			self.unlock();
21820		},
21821	
21822		/**
21823		 * Completely destroys the control and
21824		 * unbinds all event listeners so that it can
21825		 * be garbage collected.
21826		 */
21827		destroy: function() {
21828			var self = this;
21829			var eventNS = self.eventNS;
21830			var revertSettings = self.revertSettings;
21831	
21832			self.trigger('destroy');
21833			self.off();
21834			self.$wrapper.remove();
21835			self.$dropdown.remove();
21836	
21837			self.$input
21838				.html('')
21839				.append(revertSettings.$children)
21840				.removeAttr('tabindex')
21841				.removeClass('selectized')
21842				.attr({tabindex: revertSettings.tabindex})
21843				.show();
21844	
21845			self.$control_input.removeData('grow');
21846			self.$input.removeData('selectize');
21847	
21848			if (--Selectize.count == 0 && Selectize.$testInput) {
21849				Selectize.$testInput.remove();
21850				Selectize.$testInput = undefined;
21851			}
21852	
21853			$(window).off(eventNS);
21854			$(document).off(eventNS);
21855			$(document.body).off(eventNS);
21856	
21857			delete self.$input[0].selectize;
21858		},
21859	
21860		/**
21861		 * A helper method for rendering "item" and
21862		 * "option" templates, given the data.
21863		 *
21864		 * @param {string} templateName
21865		 * @param {object} data
21866		 * @returns {string}
21867		 */
21868		render: function(templateName, data) {
21869			var value, id, label;
21870			var html = '';
21871			var cache = false;
21872			var self = this;
21873			var regex_tag = /^[\t \r\n]*<([a-z][a-z0-9\-_]*(?:\:[a-z][a-z0-9\-_]*)?)/i;
21874	
21875			if (templateName === 'option' || templateName === 'item') {
21876				value = hash_key(data[self.settings.valueField]);
21877				cache = !!value;
21878			}
21879	
21880			// pull markup from cache if it exists
21881			if (cache) {
21882				if (!isset(self.renderCache[templateName])) {
21883					self.renderCache[templateName] = {};
21884				}
21885				if (self.renderCache[templateName].hasOwnProperty(value)) {
21886					return self.renderCache[templateName][value];
21887				}
21888			}
21889	
21890			// render markup
21891			html = $(self.settings.render[templateName].apply(this, [data, escape_html]));
21892	
21893			// add mandatory attributes
21894			if (templateName === 'option' || templateName === 'option_create') {
21895				if (!data[self.settings.disabledField]) {
21896					html.attr('data-selectable', '');
21897				}
21898			}
21899			else if (templateName === 'optgroup') {
21900				id = data[self.settings.optgroupValueField] || '';
21901				html.attr('data-group', id);
21902				if(data[self.settings.disabledField]) {
21903					html.attr('data-disabled', '');
21904				}
21905			}
21906			if (templateName === 'option' || templateName === 'item') {
21907				html.attr('data-value', value || '');
21908			}
21909	
21910			// update cache
21911			if (cache) {
21912				self.renderCache[templateName][value] = html[0];
21913			}
21914	
21915			return html[0];
21916		},
21917	
21918		/**
21919		 * Clears the render cache for a template. If
21920		 * no template is given, clears all render
21921		 * caches.
21922		 *
21923		 * @param {string} templateName
21924		 */
21925		clearCache: function(templateName) {
21926			var self = this;
21927			if (typeof templateName === 'undefined') {
21928				self.renderCache = {};
21929			} else {
21930				delete self.renderCache[templateName];
21931			}
21932		},
21933	
21934		/**
21935		 * Determines whether or not to display the
21936		 * create item prompt, given a user input.
21937		 *
21938		 * @param {string} input
21939		 * @return {boolean}
21940		 */
21941		canCreate: function(input) {
21942			var self = this;
21943			if (!self.settings.create) return false;
21944			var filter = self.settings.createFilter;
21945			return input.length
21946				&& (typeof filter !== 'function' || filter.apply(self, [input]))
21947				&& (typeof filter !== 'string' || new RegExp(filter).test(input))
21948				&& (!(filter instanceof RegExp) || filter.test(input));
21949		}
21950	
21951	});
21952	
21953	
21954	Selectize.count = 0;
21955	Selectize.defaults = {
21956		options: [],
21957		optgroups: [],
21958	
21959		plugins: [],
21960		delimiter: ',',
21961		splitOn: null, // regexp or string for splitting up values from a paste command
21962		persist: true,
21963		diacritics: true,
21964		create: false,
21965		
vendor: 4,271 bytes, lines 21965-22105
21965showAddOptionOnCreate: true,
21966		createOnBlur: false,
21967		createFilter: null,
21968		highlight: true,
21969		openOnFocus: true,
21970		maxOptions: 1000,
21971		maxItems: null,
21972		hideSelected: null,
21973		addPrecedence: false,
21974		selectOnTab: true,
21975		preload: false,
21976		allowEmptyOption: false,
21977		showEmptyOptionInDropdown: false,
21978		emptyOptionLabel: '--',
21979		closeAfterSelect: false,
21980	
21981		scrollDuration: 60,
21982		deselectBehavior: 'previous', //top, previous
21983		loadThrottle: 300,
21984		loadingClass: 'loading',
21985	
21986		dataAttr: 'data-data',
21987		optgroupField: 'optgroup',
21988		valueField: 'value',
21989		labelField: 'text',
21990		disabledField: 'disabled',
21991		optgroupLabelField: 'label',
21992		optgroupValueField: 'value',
21993		lockOptgroupOrder: false,
21994	
21995		sortField: '$order',
21996		searchField: ['text'],
21997		searchConjunction: 'and',
21998	
21999		mode: null,
22000		wrapperClass: 'selectize-control',
22001		inputClass: 'selectize-input',
22002		dropdownClass: 'selectize-dropdown',
22003		dropdownContentClass: 'selectize-dropdown-content',
22004	
22005		dropdownParent: null,
22006	
22007		copyClassesToDropdown: true,
22008	
22009		/*
22010		load                 : null, // function(query, callback) { ... }
22011		score                : null, // function(search) { ... }
22012		formatValueToKey     : null, // function(key) { ... }
22013		onInitialize         : null, // function() { ... }
22014		onChange             : null, // function(value) { ... }
22015		onItemAdd            : null, // function(value, $item) { ... }
22016		onItemRemove         : null, // function(value) { ... }
22017		onClear              : null, // function() { ... }
22018		onOptionAdd          : null, // function(value, data) { ... }
22019		onOptionRemove       : null, // function(value) { ... }
22020		onOptionClear        : null, // function() { ... }
22021		onOptionGroupAdd     : null, // function(id, data) { ... }
22022		onOptionGroupRemove  : null, // function(id) { ... }
22023		onOptionGroupClear   : null, // function() { ... }
22024		onDropdownOpen       : null, // function($dropdown) { ... }
22025		onDropdownClose      : null, // function($dropdown) { ... }
22026		onType               : null, // function(str) { ... }
22027		onDelete             : null, // function(values) { ... }
22028		*/
22029	
22030		render: {
22031			/*
22032			item: null,
22033			optgroup: null,
22034			optgroup_header: null,
22035			option: null,
22036			option_create: null
22037			*/
22038		}
22039	};
22040	
22041	
22042	$.fn.selectize = function(settings_user) {
22043		var defaults             = $.fn.selectize.defaults;
22044		var settings             = $.extend({}, defaults, settings_user);
22045		var attr_data            = settings.dataAttr;
22046		var field_label          = settings.labelField;
22047		var field_value          = settings.valueField;
22048		var field_disabled       = settings.disabledField;
22049		var field_optgroup       = settings.optgroupField;
22050		var field_optgroup_label = settings.optgroupLabelField;
22051		var field_optgroup_value = settings.optgroupValueField;
22052	
22053		/**
22054		 * Initializes selectize from a <input type="text"> element.
22055		 *
22056		 * @param {object} $input
22057		 * @param {object} settings_element
22058		 */
22059		var init_textbox = function($input, settings_element) {
22060			var i, n, values, option;
22061	
22062			var data_raw = $input.attr(attr_data);
22063	
22064			if (!data_raw) {
22065				var value = $.trim($input.val() || '');
22066				if (!settings.allowEmptyOption && !value.length) return;
22067				values = value.split(settings.delimiter);
22068				for (i = 0, n = values.length; i < n; i++) {
22069					option = {};
22070					option[field_label] = values[i];
22071					option[field_value] = values[i];
22072					settings_element.options.push(option);
22073				}
22074				settings_element.items = values;
22075			} else {
22076				settings_element.options = JSON.parse(data_raw);
22077				for (i = 0, n = settings_element.options.length; i < n; i++) {
22078					settings_element.items.push(settings_element.options[i][field_value]);
22079				}
22080			}
22081		};
22082	
22083		/**
22084		 * Initializes selectize from a <select> element.
22085		 *
22086		 * @param {object} $input
22087		 * @param {object} settings_element
22088		 */
22089		var init_select = function($input, settings_element) {
22090			var i, n, tagName, $children, order = 0;
22091			var options = settings_element.options;
22092			var optionsMap = {};
22093	
22094			var readData = function($el) {
22095				var data = attr_data && $el.attr(attr_data);
22096				if (typeof data === 'string' && data.length) {
22097					return JSON.parse(data);
22098				}
22099				return null;
22100			};
22101	
22102			var addOption = function($option, group) {
22103				$option = $($option);
22104	
22105				var value = hash_key($option.val());
vendor: 6,158 bytes, lines 22106-22308
22106				if (!value && !settings.allowEmptyOption) return;
22107	
22108				// if the option already exists, it's probably been
22109				// duplicated in another optgroup. in this case, push
22110				// the current group to the "optgroup" property on the
22111				// existing option so that it's rendered in both places.
22112				if (optionsMap.hasOwnProperty(value)) {
22113					if (group) {
22114						var arr = optionsMap[value][field_optgroup];
22115						if (!arr) {
22116							optionsMap[value][field_optgroup] = group;
22117						} else if (!$.isArray(arr)) {
22118							optionsMap[value][field_optgroup] = [arr, group];
22119						} else {
22120							arr.push(group);
22121						}
22122					}
22123					return;
22124				}
22125	
22126				var option             = readData($option) || {};
22127				option[field_label]    = option[field_label] || $option.text();
22128				option[field_value]    = option[field_value] || value;
22129				option[field_disabled] = option[field_disabled] || $option.prop('disabled');
22130				option[field_optgroup] = option[field_optgroup] || group;
22131	
22132				optionsMap[value] = option;
22133				options.push(option);
22134	
22135				if ($option.is(':selected')) {
22136					settings_element.items.push(value);
22137				}
22138			};
22139	
22140			var addGroup = function($optgroup) {
22141				var i, n, id, optgroup, $options;
22142	
22143				$optgroup = $($optgroup);
22144				id = $optgroup.attr('label');
22145	
22146				if (id) {
22147					optgroup = readData($optgroup) || {};
22148					optgroup[field_optgroup_label] = id;
22149					optgroup[field_optgroup_value] = id;
22150					optgroup[field_disabled] = $optgroup.prop('disabled');
22151					settings_element.optgroups.push(optgroup);
22152				}
22153	
22154				$options = $('option', $optgroup);
22155				for (i = 0, n = $options.length; i < n; i++) {
22156					addOption($options[i], id);
22157				}
22158			};
22159	
22160			settings_element.maxItems = $input.attr('multiple') ? null : 1;
22161	
22162			$children = $input.children();
22163			for (i = 0, n = $children.length; i < n; i++) {
22164				tagName = $children[i].tagName.toLowerCase();
22165				if (tagName === 'optgroup') {
22166					addGroup($children[i]);
22167				} else if (tagName === 'option') {
22168					addOption($children[i]);
22169				}
22170			}
22171		};
22172	
22173		return this.each(function() {
22174			if (this.selectize) return;
22175	
22176			var instance;
22177			var $input = $(this);
22178			var tag_name = this.tagName.toLowerCase();
22179			var placeholder = $input.attr('placeholder') || $input.attr('data-placeholder');
22180			if (!placeholder && !settings.allowEmptyOption) {
22181				placeholder = $input.children('option[value=""]').text();
22182			}
22183			if (settings.allowEmptyOption && settings.showEmptyOptionInDropdown && !$input.children('option[value=""]').length) {
22184				var input_html = $input.html();
22185				$input.html('<option value="">'+settings.emptyOptionLabel+'</option>'+input_html);
22186			}
22187	
22188			var settings_element = {
22189				'placeholder' : placeholder,
22190				'options'     : [],
22191				'optgroups'   : [],
22192				'items'       : []
22193			};
22194	
22195			if (tag_name === 'select') {
22196				init_select($input, settings_element);
22197			} else {
22198				init_textbox($input, settings_element);
22199			}
22200	
22201			instance = new Selectize($input, $.extend(true, {}, defaults, settings_element, settings_user));
22202			instance.settings_user = settings_user;
22203		});
22204	};
22205	
22206	$.fn.selectize.defaults = Selectize.defaults;
22207	$.fn.selectize.support = {
22208		validity: SUPPORTS_VALIDITY_API
22209	};
22210	
22211	
22212	Selectize.define("auto_position", function () {
22213	  var self = this;
22214	
22215	  const POSITION = {
22216	    top: 'top',
22217	    bottom: 'bottom',
22218	  };
22219	
22220	  self.positionDropdown = (function() {
22221	    return function() {
22222	      const $control = this.$control;
22223	      const offset = this.settings.dropdownParent === 'body' ? $control.offset() : $control.position();
22224	      offset.top += $control.outerHeight(true);
22225	
22226	      const dropdownHeight = this.$dropdown.prop('scrollHeight') + 5; // 5 - padding value;
22227	      const controlPosTop = this.$control.get(0).getBoundingClientRect().top;
22228	      const wrapperHeight = this.$wrapper.height();
22229	      const position = controlPosTop + dropdownHeight + wrapperHeight  > window.innerHeight ? POSITION.top : POSITION.bottom;
22230	      const styles = {
22231	        width: $control.outerWidth(),
22232	        left: offset.left
22233	      };
22234	
22235	      if (position === POSITION.top) {
22236	        Object.assign(styles, {bottom: offset.top, top: 'unset', margin: '0 0 5px 0'});
22237	        this.$dropdown.addClass('selectize-position-top');
22238	      } else {
22239	        Object.assign(styles, {top: offset.top, bottom: 'unset', margin: '5px 0 0 0'});
22240	        this.$dropdown.removeClass('selectize-position-top');
22241	      }
22242	
22243	      this.$dropdown.css(styles);
22244	    }
22245	  }());
22246	});
22247	
22248	
22249	Selectize.define('auto_select_on_type', function(options) {
22250		var self = this;
22251	
22252		self.onBlur = (function() {
22253			var originalBlur = self.onBlur;
22254			return function(e) {
22255				var $matchedItem = self.getFirstItemMatchedByTextContent(self.lastValue, true);
22256				if (typeof $matchedItem.attr('data-value') !== 'undefined' && self.getValue() !== $matchedItem.attr('data-value'))
22257				{
22258					self.setValue($matchedItem.attr('data-value'));
22259				}
22260				return originalBlur.apply(this, arguments);
22261			}
22262		}());
22263	});
22264	
22265	
22266	Selectize.define("autofill_disable", function (options) {
22267	  var self = this;
22268	
22269	  self.setup = (function () {
22270	    var original = self.setup;
22271	    return function () {
22272	      original.apply(self, arguments);
22273	
22274	      // https://stackoverflow.com/questions/30053167/autocomplete-off-vs-false
22275	      self.$control_input.attr({ autocomplete: "new-password", autofill: "no" });
22276	    };
22277	  })();
22278	});
22279	
22280	
22281	Selectize.define('drag_drop', function(options) {
22282		if (!$.fn.sortable) throw new Error('The "drag_drop" plugin requires jQuery UI "sortable".');
22283		if (this.settings.mode !== 'multi') return;
22284		var self = this;
22285	
22286		self.lock = (function() {
22287			var original = self.lock;
22288			return function() {
22289				var sortable = self.$control.data('sortable');
22290				if (sortable) sortable.disable();
22291				return original.apply(self, arguments);
22292			};
22293		})();
22294	
22295		self.unlock = (function() {
22296			var original = self.unlock;
22297			return function() {
22298				var sortable = self.$control.data('sortable');
22299				if (sortable) sortable.enable();
22300				return original.apply(self, arguments);
22301			};
22302		})();
22303	
22304		self.setup = (function() {
22305			var original = self.setup;
22306			return function() {
22307				original.apply(this, arguments);
22308	
vendor: 7,492 bytes, lines 22309-22562
22309				var $control = self.$control.sortable({
22310					items: '[data-value]',
22311					forcePlaceholderSize: true,
22312					disabled: self.isLocked,
22313					start: function(e, ui) {
22314						ui.placeholder.css('width', ui.helper.css('width'));
22315						// $control.css({overflow: 'visible'});
22316						$control.addClass('dragging');
22317					},
22318					stop: function() {
22319						// $control.css({overflow: 'hidden'});
22320						$control.removeClass('dragging');
22321						var active = self.$activeItems ? self.$activeItems.slice() : null;
22322						var values = [];
22323						$control.children('[data-value]').each(function() {
22324							values.push($(this).attr('data-value'));
22325						});
22326						self.isFocused = false;
22327						self.setValue(values);
22328						self.isFocused = true;
22329						self.setActiveItem(active);
22330						self.positionDropdown();
22331					}
22332				});
22333			};
22334		})();
22335	
22336	});
22337	
22338	
22339	Selectize.define('dropdown_header', function(options) {
22340		var self = this;
22341	
22342		options = $.extend({
22343			title         : 'Untitled',
22344			headerClass   : 'selectize-dropdown-header',
22345			titleRowClass : 'selectize-dropdown-header-title',
22346			labelClass    : 'selectize-dropdown-header-label',
22347			closeClass    : 'selectize-dropdown-header-close',
22348	
22349			html: function(data) {
22350				return (
22351					'<div class="' + data.headerClass + '">' +
22352						'<div class="' + data.titleRowClass + '">' +
22353							'<span class="' + data.labelClass + '">' + data.title + '</span>' +
22354							'<a href="javascript:void(0)" class="' + data.closeClass + '">&#xd7;</a>' +
22355						'</div>' +
22356					'</div>'
22357				);
22358			}
22359		}, options);
22360	
22361		self.setup = (function() {
22362			var original = self.setup;
22363			return function() {
22364				original.apply(self, arguments);
22365				self.$dropdown_header = $(options.html(options));
22366				self.$dropdown.prepend(self.$dropdown_header);
22367			};
22368		})();
22369	
22370	});
22371	
22372	
22373	Selectize.define('optgroup_columns', function(options) {
22374		var self = this;
22375	
22376		options = $.extend({
22377			equalizeWidth  : true,
22378			equalizeHeight : true
22379		}, options);
22380	
22381		this.getAdjacentOption = function($option, direction) {
22382			var $options = $option.closest('[data-group]').find('[data-selectable]');
22383			var index    = $options.index($option) + direction;
22384	
22385			return index >= 0 && index < $options.length ? $options.eq(index) : $();
22386		};
22387	
22388		this.onKeyDown = (function() {
22389			var original = self.onKeyDown;
22390			return function(e) {
22391				var index, $option, $options, $optgroup;
22392	
22393				if (this.isOpen && (e.keyCode === KEY_LEFT || e.keyCode === KEY_RIGHT)) {
22394					self.ignoreHover = true;
22395					$optgroup = this.$activeOption.closest('[data-group]');
22396					index = $optgroup.find('[data-selectable]').index(this.$activeOption);
22397	
22398					if(e.keyCode === KEY_LEFT) {
22399						$optgroup = $optgroup.prev('[data-group]');
22400					} else {
22401						$optgroup = $optgroup.next('[data-group]');
22402					}
22403	
22404					$options = $optgroup.find('[data-selectable]');
22405					$option  = $options.eq(Math.min($options.length - 1, index));
22406					if ($option.length) {
22407						this.setActiveOption($option);
22408					}
22409					return;
22410				}
22411	
22412				return original.apply(this, arguments);
22413			};
22414		})();
22415	
22416		var getScrollbarWidth = function() {
22417			var div;
22418			var width = getScrollbarWidth.width;
22419			var doc = document;
22420	
22421			if (typeof width === 'undefined') {
22422				div = doc.createElement('div');
22423				div.innerHTML = '<div style="width:50px;height:50px;position:absolute;left:-50px;top:-50px;overflow:auto;"><div style="width:1px;height:100px;"></div></div>';
22424				div = div.firstChild;
22425				doc.body.appendChild(div);
22426				width = getScrollbarWidth.width = div.offsetWidth - div.clientWidth;
22427				doc.body.removeChild(div);
22428			}
22429			return width;
22430		};
22431	
22432		var equalizeSizes = function() {
22433			var i, n, height_max, width, width_last, width_parent, $optgroups;
22434	
22435			$optgroups = $('[data-group]', self.$dropdown_content);
22436			n = $optgroups.length;
22437			if (!n || !self.$dropdown_content.width()) return;
22438	
22439			if (options.equalizeHeight) {
22440				height_max = 0;
22441				for (i = 0; i < n; i++) {
22442					height_max = Math.max(height_max, $optgroups.eq(i).height());
22443				}
22444				$optgroups.css({height: height_max});
22445			}
22446	
22447			if (options.equalizeWidth) {
22448				width_parent = self.$dropdown_content.innerWidth() - getScrollbarWidth();
22449				width = Math.round(width_parent / n);
22450				$optgroups.css({width: width});
22451				if (n > 1) {
22452					width_last = width_parent - width * (n - 1);
22453					$optgroups.eq(n - 1).css({width: width_last});
22454				}
22455			}
22456		};
22457	
22458		if (options.equalizeHeight || options.equalizeWidth) {
22459			hook.after(this, 'positionDropdown', equalizeSizes);
22460			hook.after(this, 'refreshOptions', equalizeSizes);
22461		}
22462	
22463	
22464	});
22465	
22466	
22467	Selectize.define('remove_button', function(options) {
22468		options = $.extend({
22469				label     : '&#xd7;',
22470				title     : 'Remove',
22471				className : 'remove',
22472				append    : true
22473			}, options);
22474	
22475			var singleClose = function(thisRef, options) {
22476	
22477				options.className = 'remove-single';
22478	
22479				var self = thisRef;
22480				var html = '<a href="javascript:void(0)" class="' + options.className + '" tabindex="-1" title="' + escape_html(options.title) + '">' + options.label + '</a>';
22481	
22482				/**
22483				 * Appends an element as a child (with raw HTML).
22484				 *
22485				 * @param {string} html_container
22486				 * @param {string} html_element
22487				 * @return {string}
22488				 */
22489				var append = function(html_container, html_element) {
22490					return $('<span>').append(html_container)
22491						.append(html_element);
22492				};
22493	
22494				thisRef.setup = (function() {
22495					var original = self.setup;
22496					return function() {
22497						// override the item rendering method to add the button to each
22498						if (options.append) {
22499							var id = $(self.$input.context).attr('id');
22500							var selectizer = $('#'+id);
22501	
22502							var render_item = self.settings.render.item;
22503							self.settings.render.item = function(data) {
22504								return append(render_item.apply(thisRef, arguments), html);
22505							};
22506						}
22507	
22508						original.apply(thisRef, arguments);
22509	
22510						// add event listener
22511						thisRef.$control.on('click', '.' + options.className, function(e) {
22512							e.preventDefault();
22513							if (self.isLocked) return;
22514	
22515							self.clear();
22516						});
22517	
22518					};
22519				})();
22520			};
22521	
22522			var multiClose = function(thisRef, options) {
22523	
22524				var self = thisRef;
22525				var html = '<a href="javascript:void(0)" class="' + options.className + '" tabindex="-1" title="' + escape_html(options.title) + '">' + options.label + '</a>';
22526	
22527				/**
22528				 * Appends an element as a child (with raw HTML).
22529				 *
22530				 * @param {string} html_container
22531				 * @param {string} html_element
22532				 * @return {string}
22533				 */
22534				var append = function(html_container, html_element) {
22535					var pos = html_container.search(/(<\/[^>]+>\s*)$/);
22536					return html_container.substring(0, pos) + html_element + html_container.substring(pos);
22537				};
22538	
22539				thisRef.setup = (function() {
22540					var original = self.setup;
22541					return function() {
22542						// override the item rendering method to add the button to each
22543						if (options.append) {
22544							var render_item = self.settings.render.item;
22545							self.settings.render.item = function(data) {
22546								return append(render_item.apply(thisRef, arguments), html);
22547							};
22548						}
22549	
22550						original.apply(thisRef, arguments);
22551	
22552						// add event listener
22553						thisRef.$control.on('click', '.' + options.className, function(e) {
22554							e.preventDefault();
22555							if (self.isLocked) return;
22556	
22557							var $item = $(e.currentTarget).parent();
22558							self.setActiveItem($item);
22559							if (self.deleteSelection()) {
22560								self.setCaret(self.items.length);
22561							}
22562							return false;
vendor: 4,446 bytes, lines 22563-22722
22563						});
22564	
22565					};
22566				})();
22567			};
22568	
22569			if (this.settings.mode === 'single') {
22570				singleClose(this, options);
22571				return;
22572			} else {
22573				multiClose(this, options);
22574			}
22575	});
22576	
22577	
22578	Selectize.define('restore_on_backspace', function(options) {
22579		var self = this;
22580	
22581		options.text = options.text || function(option) {
22582			return option[this.settings.labelField];
22583		};
22584	
22585		this.onKeyDown = (function() {
22586			var original = self.onKeyDown;
22587			return function(e) {
22588				var index, option;
22589				if (e.keyCode === KEY_BACKSPACE && this.$control_input.val() === '' && !this.$activeItems.length) {
22590					index = this.caretPos - 1;
22591					if (index >= 0 && index < this.items.length) {
22592						option = this.options[this.items[index]];
22593						if (this.deleteSelection(e)) {
22594							this.setTextboxValue(options.text.apply(this, [option]));
22595							this.refreshOptions(true);
22596						}
22597						e.preventDefault();
22598						return;
22599					}
22600				}
22601				return original.apply(this, arguments);
22602			};
22603		})();
22604	});
22605	
22606	
22607	Selectize.define('select_on_focus', function(options) {
22608		var self = this;
22609	
22610		self.on('focus', function() {
22611			var originalFocus = self.onFocus;
22612			return function(e) {
22613				var value = self.getItem(self.getValue()).text();
22614				self.clear();
22615				self.setTextboxValue(value);
22616				self.$control_input.select();
22617				setTimeout( function () {
22618					if (self.settings.selectOnTab) {
22619						self.setActiveOption(self.getFirstItemMatchedByTextContent(value));
22620					}
22621					self.settings.score = null;
22622				},0);
22623				return originalFocus.apply(this, arguments);
22624			};
22625		}());
22626	
22627		self.onBlur = (function() {
22628			var originalBlur = self.onBlur;
22629			return function(e) {
22630				if (self.getValue() === "" && self.lastValidValue !== self.getValue()) {
22631					self.setValue(self.lastValidValue);
22632				}
22633				setTimeout( function () {
22634					self.settings.score = function() {
22635						return function() {
22636							return 1;
22637						};
22638					};
22639				}, 0 );
22640				return originalBlur.apply(this, arguments);
22641			}
22642		}());
22643		self.settings.score = function() {
22644			return function() { return 1; };
22645		};
22646	
22647	});
22648	
22649	
22650	Selectize.define('tag_limit', function (options) {
22651	    const self = this
22652	    options.tagLimit = options.tagLimit
22653	    this.onBlur = (function (e) {
22654	        const original = self.onBlur
22655	
22656	        return function (e) {
22657	            original.apply(this, e);
22658	            if (!e)
22659	                return
22660	            const $control = this.$control
22661	            const $items = $control.find('.item')
22662	            const limit = options.tagLimit
22663	            if (limit === undefined || $items.length <= limit)
22664	                return
22665	
22666	            $items.toArray().forEach(function(item, index) {
22667	                if (index < limit)
22668	                    return
22669	                $(item).hide()
22670	            });
22671	
22672	            $control.append('<span><b>' + ($items.length - limit) + '</b></span>')
22673	        };
22674	    })()
22675	
22676	    this.onFocus = (function (e) {
22677	        const original = self.onFocus
22678	
22679	        return function (e) {
22680	            original.apply(this, e);
22681	            if (!e)
22682	                return
22683	            const $control = this.$control
22684	            const $items = $control.find('.item')
22685	            $items.show()
22686	            $control.find('span').remove()
22687	
22688	        };
22689	    })()
22690	});
22691	
22692
22693	return Selectize;
22694}));
22695
22696
22697/***/ }),
22698/* 38 */
22699/***/ (function(module, exports, __webpack_require__) {
22700
22701/* WEBPACK VAR INJECTION */(function($) {var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_RESULT__;/**
22702 * sifter.js
22703 * Copyright (c) 2013 Brian Reavis & contributors
22704 *
22705 * Licensed under the Apache License, Version 2.0 (the "License"); you may not use this
22706 * file except in compliance with the License. You may obtain a copy of the License at:
22707 * http://www.apache.org/licenses/LICENSE-2.0
22708 *
22709 * Unless required by applicable law or agreed to in writing, software distributed under
22710 * the License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF
22711 * ANY KIND, either express or implied. See the License for the specific language
22712 * governing permissions and limitations under the License.
22713 *
22714 * @author Brian Reavis <[email protected]>
22715 */
22716
22717(function(root, factory) {
22718	if (true) {
22719		!(__WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
22720				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
22721				(__WEBPACK_AMD_DEFINE_FACTORY__.call(exports, __webpack_require__, exports, module)) :
22722				__WEBPACK_AMD_DEFINE_FACTORY__),
22723				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__)
vendor: 12,838 bytes, lines 22723-23203
22723);
22724	} else if (typeof exports === 'object') {
22725		module.exports = factory();
22726	} else {
22727		root.Sifter = factory();
22728	}
22729}(this, function() {
22730
22731	/**
22732	 * Textually searches arrays and hashes of objects
22733	 * by property (or multiple properties). Designed
22734	 * specifically for autocomplete.
22735	 *
22736	 * @constructor
22737	 * @param {array|object} items
22738	 * @param {object} items
22739	 */
22740	var Sifter = function(items, settings) {
22741		this.items = items;
22742		this.settings = settings || {diacritics: true};
22743	};
22744
22745	/**
22746	 * Splits a search string into an array of individual
22747	 * regexps to be used to match results.
22748	 *
22749	 * @param {string} query
22750	 * @returns {array}
22751	 */
22752	Sifter.prototype.tokenize = function(query) {
22753		query = trim(String(query || '').toLowerCase());
22754		if (!query || !query.length) return [];
22755
22756		var i, n, regex, letter;
22757		var tokens = [];
22758		var words = query.split(/ +/);
22759
22760		for (i = 0, n = words.length; i < n; i++) {
22761			regex = escape_regex(words[i]);
22762			if (this.settings.diacritics) {
22763				for (letter in DIACRITICS) {
22764					if (DIACRITICS.hasOwnProperty(letter)) {
22765						regex = regex.replace(new RegExp(letter, 'g'), DIACRITICS[letter]);
22766					}
22767				}
22768			}
22769			tokens.push({
22770				string : words[i],
22771				regex  : new RegExp(regex, 'i')
22772			});
22773		}
22774
22775		return tokens;
22776	};
22777
22778	/**
22779	 * Iterates over arrays and hashes.
22780	 *
22781	 * ```
22782	 * this.iterator(this.items, function(item, id) {
22783	 *    // invoked for each item
22784	 * });
22785	 * ```
22786	 *
22787	 * @param {array|object} object
22788	 */
22789	Sifter.prototype.iterator = function(object, callback) {
22790		var iterator;
22791		if (is_array(object)) {
22792			iterator = Array.prototype.forEach || function(callback) {
22793				for (var i = 0, n = this.length; i < n; i++) {
22794					callback(this[i], i, this);
22795				}
22796			};
22797		} else {
22798			iterator = function(callback) {
22799				for (var key in this) {
22800					if (this.hasOwnProperty(key)) {
22801						callback(this[key], key, this);
22802					}
22803				}
22804			};
22805		}
22806
22807		iterator.apply(object, [callback]);
22808	};
22809
22810	/**
22811	 * Returns a function to be used to score individual results.
22812	 *
22813	 * Good matches will have a higher score than poor matches.
22814	 * If an item is not a match, 0 will be returned by the function.
22815	 *
22816	 * @param {object|string} search
22817	 * @param {object} options (optional)
22818	 * @returns {function}
22819	 */
22820	Sifter.prototype.getScoreFunction = function(search, options) {
22821		var self, fields, tokens, token_count, nesting;
22822
22823		self        = this;
22824		search      = self.prepareSearch(search, options);
22825		tokens      = search.tokens;
22826		fields      = search.options.fields;
22827		token_count = tokens.length;
22828		nesting     = search.options.nesting;
22829
22830		/**
22831		 * Calculates how close of a match the
22832		 * given value is against a search token.
22833		 *
22834		 * @param {mixed} value
22835		 * @param {object} token
22836		 * @return {number}
22837		 */
22838		var scoreValue = function(value, token) {
22839			var score, pos;
22840
22841			if (!value) return 0;
22842			value = String(value || '');
22843			pos = value.search(token.regex);
22844			if (pos === -1) return 0;
22845			score = token.string.length / value.length;
22846			if (pos === 0) score += 0.5;
22847			return score;
22848		};
22849
22850		/**
22851		 * Calculates the score of an object
22852		 * against the search query.
22853		 *
22854		 * @param {object} token
22855		 * @param {object} data
22856		 * @return {number}
22857		 */
22858		var scoreObject = (function() {
22859			var field_count = fields.length;
22860			if (!field_count) {
22861				return function() { return 0; };
22862			}
22863			if (field_count === 1) {
22864				return function(token, data) {
22865					return scoreValue(getattr(data, fields[0], nesting), token);
22866				};
22867			}
22868			return function(token, data) {
22869				for (var i = 0, sum = 0; i < field_count; i++) {
22870					sum += scoreValue(getattr(data, fields[i], nesting), token);
22871				}
22872				return sum / field_count;
22873			};
22874		})();
22875
22876		if (!token_count) {
22877			return function() { return 0; };
22878		}
22879		if (token_count === 1) {
22880			return function(data) {
22881				return scoreObject(tokens[0], data);
22882			};
22883		}
22884
22885		if (search.options.conjunction === 'and') {
22886			return function(data) {
22887				var score;
22888				for (var i = 0, sum = 0; i < token_count; i++) {
22889					score = scoreObject(tokens[i], data);
22890					if (score <= 0) return 0;
22891					sum += score;
22892				}
22893				return sum / token_count;
22894			};
22895		} else {
22896			return function(data) {
22897				for (var i = 0, sum = 0; i < token_count; i++) {
22898					sum += scoreObject(tokens[i], data);
22899				}
22900				return sum / token_count;
22901			};
22902		}
22903	};
22904
22905	/**
22906	 * Returns a function that can be used to compare two
22907	 * results, for sorting purposes. If no sorting should
22908	 * be performed, `null` will be returned.
22909	 *
22910	 * @param {string|object} search
22911	 * @param {object} options
22912	 * @return function(a,b)
22913	 */
22914	Sifter.prototype.getSortFunction = function(search, options) {
22915		var i, n, self, field, fields, fields_count, multiplier, multipliers, get_field, implicit_score, sort;
22916
22917		self   = this;
22918		search = self.prepareSearch(search, options);
22919		sort   = (!search.query && options.sort_empty) || options.sort;
22920
22921		/**
22922		 * Fetches the specified sort field value
22923		 * from a search result item.
22924		 *
22925		 * @param  {string} name
22926		 * @param  {object} result
22927		 * @return {mixed}
22928		 */
22929		get_field = function(name, result) {
22930			if (name === '$score') return result.score;
22931			return getattr(self.items[result.id], name, options.nesting);
22932		};
22933
22934		// parse options
22935		fields = [];
22936		if (sort) {
22937			for (i = 0, n = sort.length; i < n; i++) {
22938				if (search.query || sort[i].field !== '$score') {
22939					fields.push(sort[i]);
22940				}
22941			}
22942		}
22943
22944		// the "$score" field is implied to be the primary
22945		// sort field, unless it's manually specified
22946		if (search.query) {
22947			implicit_score = true;
22948			for (i = 0, n = fields.length; i < n; i++) {
22949				if (fields[i].field === '$score') {
22950					implicit_score = false;
22951					break;
22952				}
22953			}
22954			if (implicit_score) {
22955				fields.unshift({field: '$score', direction: 'desc'});
22956			}
22957		} else {
22958			for (i = 0, n = fields.length; i < n; i++) {
22959				if (fields[i].field === '$score') {
22960					fields.splice(i, 1);
22961					break;
22962				}
22963			}
22964		}
22965
22966		multipliers = [];
22967		for (i = 0, n = fields.length; i < n; i++) {
22968			multipliers.push(fields[i].direction === 'desc' ? -1 : 1);
22969		}
22970
22971		// build function
22972		fields_count = fields.length;
22973		if (!fields_count) {
22974			return null;
22975		} else if (fields_count === 1) {
22976			field = fields[0].field;
22977			multiplier = multipliers[0];
22978			return function(a, b) {
22979				return multiplier * cmp(
22980					get_field(field, a),
22981					get_field(field, b)
22982				);
22983			};
22984		} else {
22985			return function(a, b) {
22986				var i, result, a_value, b_value, field;
22987				for (i = 0; i < fields_count; i++) {
22988					field = fields[i].field;
22989					result = multipliers[i] * cmp(
22990						get_field(field, a),
22991						get_field(field, b)
22992					);
22993					if (result) return result;
22994				}
22995				return 0;
22996			};
22997		}
22998	};
22999
23000	/**
23001	 * Parses a search query and returns an object
23002	 * with tokens and fields ready to be populated
23003	 * with results.
23004	 *
23005	 * @param {string} query
23006	 * @param {object} options
23007	 * @returns {object}
23008	 */
23009	Sifter.prototype.prepareSearch = function(query, options) {
23010		if (typeof query === 'object') return query;
23011
23012		options = extend({}, options);
23013
23014		var option_fields     = options.fields;
23015		var option_sort       = options.sort;
23016		var option_sort_empty = options.sort_empty;
23017
23018		if (option_fields && !is_array(option_fields)) options.fields = [option_fields];
23019		if (option_sort && !is_array(option_sort)) options.sort = [option_sort];
23020		if (option_sort_empty && !is_array(option_sort_empty)) options.sort_empty = [option_sort_empty];
23021
23022		return {
23023			options : options,
23024			query   : String(query || '').toLowerCase(),
23025			tokens  : this.tokenize(query),
23026			total   : 0,
23027			items   : []
23028		};
23029	};
23030
23031	/**
23032	 * Searches through all items and returns a sorted array of matches.
23033	 *
23034	 * The `options` parameter can contain:
23035	 *
23036	 *   - fields {string|array}
23037	 *   - sort {array}
23038	 *   - score {function}
23039	 *   - filter {bool}
23040	 *   - limit {integer}
23041	 *
23042	 * Returns an object containing:
23043	 *
23044	 *   - options {object}
23045	 *   - query {string}
23046	 *   - tokens {array}
23047	 *   - total {int}
23048	 *   - items {array}
23049	 *
23050	 * @param {string} query
23051	 * @param {object} options
23052	 * @returns {object}
23053	 */
23054	Sifter.prototype.search = function(query, options) {
23055		var self = this, value, score, search, calculateScore;
23056		var fn_sort;
23057		var fn_score;
23058
23059		search  = this.prepareSearch(query, options);
23060		options = search.options;
23061		query   = search.query;
23062
23063		// generate result scoring function
23064		fn_score = options.score || self.getScoreFunction(search);
23065
23066		// perform search and sort
23067		if (query.length) {
23068			self.iterator(self.items, function(item, id) {
23069				score = fn_score(item);
23070				if (options.filter === false || score > 0) {
23071					search.items.push({'score': score, 'id': id});
23072				}
23073			});
23074		} else {
23075			self.iterator(self.items, function(item, id) {
23076				search.items.push({'score': 1, 'id': id});
23077			});
23078		}
23079
23080		fn_sort = self.getSortFunction(search, options);
23081		if (fn_sort) search.items.sort(fn_sort);
23082
23083		// apply limits
23084		search.total = search.items.length;
23085		if (typeof options.limit === 'number') {
23086			search.items = search.items.slice(0, options.limit);
23087		}
23088
23089		return search;
23090	};
23091
23092	// utilities
23093	// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
23094
23095	var cmp = function(a, b) {
23096		if (typeof a === 'number' && typeof b === 'number') {
23097			return a > b ? 1 : (a < b ? -1 : 0);
23098		}
23099		a = asciifold(String(a || ''));
23100		b = asciifold(String(b || ''));
23101		if (a > b) return 1;
23102		if (b > a) return -1;
23103		return 0;
23104	};
23105
23106	var extend = function(a, b) {
23107		var i, n, k, object;
23108		for (i = 1, n = arguments.length; i < n; i++) {
23109			object = arguments[i];
23110			if (!object) continue;
23111			for (k in object) {
23112				if (object.hasOwnProperty(k)) {
23113					a[k] = object[k];
23114				}
23115			}
23116		}
23117		return a;
23118	};
23119
23120	/**
23121	 * A property getter resolving dot-notation
23122	 * @param  {Object}  obj     The root object to fetch property on
23123	 * @param  {String}  name    The optionally dotted property name to fetch
23124	 * @param  {Boolean} nesting Handle nesting or not
23125	 * @return {Object}          The resolved property value
23126	 */
23127	var getattr = function(obj, name, nesting) {
23128	    if (!obj || !name) return;
23129	    if (!nesting) return obj[name];
23130	    var names = name.split(".");
23131	    while(names.length && (obj = obj[names.shift()]));
23132	    return obj;
23133	};
23134
23135	var trim = function(str) {
23136		return (str + '').replace(/^\s+|\s+$|/g, '');
23137	};
23138
23139	var escape_regex = function(str) {
23140		return (str + '').replace(/([.?*+^$[\]\\(){}|-])/g, '\\$1');
23141	};
23142
23143	var is_array = Array.isArray || (typeof $ !== 'undefined' && $.isArray) || function(object) {
23144		return Object.prototype.toString.call(object) === '[object Array]';
23145	};
23146
23147	var DIACRITICS = {
23148		'a': '[aḀḁĂăÂâǍǎȺⱥȦȧẠạÄäÀàÁáĀāÃãÅåąĄÃąĄ]',
23149		'b': '[b␢βΒB฿𐌁ᛒ]',
23150		'c': '[cĆćĈĉČčĊċC̄c̄ÇçḈḉȻȼƇƈɕᴄCc]',
23151		'd': '[dĎďḊḋḐḑḌḍḒḓḎḏĐđD̦d̦ƉɖƊɗƋƌᵭᶁᶑȡᴅDdð]',
23152		'e': '[eÉéÈèÊêḘḙĚěĔĕẼẽḚḛẺẻĖėËëĒēȨȩĘęᶒɆɇȄȅẾếỀềỄễỂểḜḝḖḗḔḕȆȇẸẹỆệⱸᴇEeɘǝƏƐε]',
23153		'f': '[fƑƒḞḟ]',
23154		'g': '[gɢ₲ǤǥĜĝĞğĢģƓɠĠġ]',
23155		'h': '[hĤĥĦħḨḩẖẖḤḥḢḣɦʰǶƕ]',
23156		'i': '[iÍíÌìĬĭÎîǏǐÏïḮḯĨĩĮįĪīỈỉȈȉȊȋỊịḬḭƗɨɨ̆ᵻᶖİiIıɪIi]',
23157		'j': '[jȷĴĵɈɉʝɟʲ]',
23158		'k': '[kƘƙꝀꝁḰḱǨǩḲḳḴḵκϰ₭]',
23159		'l': '[lŁłĽľĻļĹĺḶḷḸḹḼḽḺḻĿŀȽƚⱠⱡⱢɫɬᶅɭȴʟLl]',
23160		'n': '[nŃńǸǹŇňÑñṄṅŅņṆṇṊṋṈṉN̈n̈ƝɲȠƞᵰᶇɳȵɴNnŊŋ]',
23161		'o': '[oØøÖöÓóÒòÔôǑǒŐőŎŏȮȯỌọƟɵƠơỎỏŌōÕõǪǫȌȍՕօ]',
23162		'p': '[pṔṕṖṗⱣᵽƤƥᵱ]',
23163		'q': '[qꝖꝗʠɊɋꝘꝙq̃]',
23164		'r': '[rŔŕɌɍŘřŖŗṘṙȐȑȒȓṚṛⱤɽ]',
23165		's': '[sŚśṠṡṢṣꞨꞩŜŝŠšŞşȘșS̈s̈]',
23166		't': '[tŤťṪṫŢţṬṭƮʈȚțṰṱṮṯƬƭ]',
23167		'u': '[uŬŭɄʉỤụÜüÚúÙùÛûǓǔŰűŬŭƯưỦủŪūŨũŲųȔȕ∪]',
23168		'v': '[vṼṽṾṿƲʋꝞꝟⱱʋ]',
23169		'w': '[wẂẃẀẁŴŵẄẅẆẇẈẉ]',
23170		'x': '[xẌẍẊẋχ]',
23171		'y': '[yÝýỲỳŶŷŸÿỸỹẎẏỴỵɎɏƳƴ]',
23172		'z': '[zŹźẐẑŽžŻżẒẓẔẕƵƶ]'
23173	};
23174
23175	var asciifold = (function() {
23176		var i, n, k, chunk;
23177		var foreignletters = '';
23178		var lookup = {};
23179		for (k in DIACRITICS) {
23180			if (DIACRITICS.hasOwnProperty(k)) {
23181				chunk = DIACRITICS[k].substring(2, DIACRITICS[k].length - 1);
23182				foreignletters += chunk;
23183				for (i = 0, n = chunk.length; i < n; i++) {
23184					lookup[chunk.charAt(i)] = k;
23185				}
23186			}
23187		}
23188		var regexp = new RegExp('[' +  foreignletters + ']', 'g');
23189		return function(str) {
23190			return str.replace(regexp, function(foreignletter) {
23191				return lookup[foreignletter];
23192			}).toLowerCase();
23193		};
23194	})();
23195
23196
23197	// export
23198	// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
23199
23200	return Sifter;
23201}));
23202
23203
23204/* WEBPACK VAR INJECTION */}.call(exports, __webpack_require__(0)))
23205
23206/***/ }),
23207/* 39 */
23208/***/ (function(module, exports, __webpack_require__) {
23209
23210var __WEBPACK_AMD_DEFINE_FACTORY__, __WEBPACK_AMD_DEFINE_RESULT__;/**
23211 * microplugin.js
23212 * Copyright (c) 2013 Brian Reavis & contributors
23213 *
23214 * Licensed under the Apache License, Version 2.0 (the "License"); you may not use this
23215 * file except in compliance with the License. You may obtain a copy of the License at:
23216 * http://www.apache.org/licenses/LICENSE-2.0
23217 *
23218 * Unless required by applicable law or agreed to in writing, software distributed under
23219 * the License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF
23220 * ANY KIND, either express or implied. See the License for the specific language
23221 * governing permissions and limitations under the License.
23222 *
23223 * @author Brian Reavis <[email protected]>
23224 */
23225
23226(function(root, factory) {
23227	if (true) {
23228		!(__WEBPACK_AMD_DEFINE_FACTORY__ = (factory),
23229				__WEBPACK_AMD_DEFINE_RESULT__ = (typeof __WEBPACK_AMD_DEFINE_FACTORY__ === 'function' ?
23230				(__WEBPACK_AMD_DEFINE_FACTORY__.call(exports, __webpack_require__, exports, module)) :
23231				__WEBPACK_AMD_DEFINE_FACTORY__),
23232				__WEBPACK_AMD_DEFINE_RESULT__ !== undefined && (module.exports = __WEBPACK_AMD_DEFINE_RESULT__));
23233	} else if (typeof exports === 'object') {
23234		module.exports = factory();
23235	} else {
23236		root.MicroPlugin = factory();
23237	}
23238}(this, function() {
23239	var MicroPlugin = {};
23240
23241	MicroPlugin.mixin = function(Interface) {
23242		Interface.plugins = {};
23243
23244		/**
23245		 * Initializes the listed plugins (with options).
23246		 * Acceptable formats:
23247		 *
23248		 * List (without options):
23249		 *   ['a', 'b', 'c']
23250		 *
23251		 * List (with options):
23252		 *   [{'name': 'a', options: {}}, {'name': 'b', options: {}}]
23253		 *
23254		 * Hash (with options):
23255		 *   {'a': { ... }, 'b': { ... }, 'c': { ... }}
23256		 *
23257		 * @param {mixed} plugins
23258		 */
23259		Interface.prototype.initializePlugins = function(plugins) {
23260			var i, n, key;
23261			var self  = this;
23262			var queue = [];
23263
23264			self.plugins = {
23265				names     : [],
23266				settings  : {},
23267				requested : {},
23268				loaded    : {}
23269			};
23270
23271			if (utils.isArray(plugins)) {
23272				for (i = 0, n = plugins.length; i < n; i++) {
23273					if (typeof plugins[i] === 'string') {
23274						queue.push(plugins[i]);
23275					} else {
23276						self.plugins.settings[plugins[i].name] = plugins[i].options;
23277						queue.push(plugins[i].name);
23278					}
23279				}
23280			} else if (plugins) {
23281				for (key in plugins) {
23282					if (plugins.hasOwnProperty(key)) {
23283						self.plugins.settings[key] = plugins[key];
23284						queue.push(key);
23285					}
23286				}
23287			}
23288
23289			while (queue.length) {
23290				self.require(queue.shift());
23291			}
23292		};
23293
23294		Interface.prototype.loadPlugin = function(name) {
23295			var self    = this;
23296			var plugins = self.plugins;
23297			var plugin  = Interface.plugins[name];
23298
23299			if (!Interface.plugins.hasOwnProperty(name)) {
23300				throw new Error('Unable to find "' +  name + '" plugin');
23301			}
23302
23303			plugins.requested[name] = true;
23304			plugins.loaded[name] = plugin.fn.apply(self, [self.plugins.settings[name] || {}]);
23305			plugins.names.push(name);
23306		};
23307
23308		/**
23309		 * Initializes a plugin.
23310		 *
23311		 * @param {string} name
23312		 */
23313		Interface.prototype.require = function(name) {
23314			var self = this;
23315			var plugins = self.plugins;
23316
23317			if (!self.plugins.loaded.hasOwnProperty(name)) {
23318				if (plugins.requested[name]) {
23319					throw new Error('Plugin has circular dependency ("' + name + '")');
23320				}
23321				self.loadPlugin(name);
23322			}
23323
23324			return plugins.loaded[name];
23325		};
23326
23327		/**
23328		 * Registers a plugin.
23329		 *
23330		 * @param {string} name
23331		 * @param {function} fn
23332		 */
23333		Interface.define = function(name, fn) {
23334			Interface.plugins[name] = {
23335				'name' : name,
23336				'fn'   : fn
23337			};
23338		};
23339	};
23340
23341	var utils = {
23342		isArray: Array.isArray || function(vArg) {
23343			return Object.prototype.toString.call(vArg) === '[object Array]';
23344		}
23345	};
23346
23347	return MicroPlugin;
23348}));
23349
23350/***/ }),
23351/* 40 */
23352/***/ (function(module, __webpack_exports__, __webpack_require__) {
23353
23354"use strict";
23355/* WEBPACK VAR INJECTION */(function($) {/* harmony import */ var __WEBPACK_IMPORTED_MODULE_0__util_playerLoader__ = __webpack_require__(4);
23356
23357
23358/* harmony default export */ __webpack_exports__["a"] = ({
23359    kalturaSession: function kalturaSession(videoPlayerId) {
23360        var partnerId = '1529571';
23361        var playerId = '49927973';
23362        var videoPlayer = document.getElementById(videoPlayerId);
23363        var videoId = videoPlayer.dataset.video;
23364        var body = document.querySelector('body');
23365
23366        // https://github.com/kaltura/kaltura-player-js
23367        // config options: https://developer.kaltura.com/player/web/configuration-web
23368        if (videoId) {
23369            try {
23370                var kalturaPlayer = KalturaPlayer.setup({ // eslint-disable-line no-undef
23371                    targetId: videoPlayerId,
23372                    provider: {
23373                        partnerId: partnerId,
23374                        uiConfId: playerId,
23375                    },
23376                    playback: {
23377                        autoplay: true,
23378                        loop: true,
23379                        muted: true,
23380                    },
23381                });
23382                kalturaPlayer.loadMedia({
23383                    entryId: videoId,
23384                });
23385
23386                // player events: https://github.com/kaltura/playkit-js/blob/master/src/event/event-type.js
23387                kalturaPlayer.ready().then(function () {
23388                    setTimeout(function () {
23389                        body.classList.add('loaded');
23390                    }, 500);
23391                });
23392
23393            } catch (e) {
23394                console.error(e.message)
23395            }
23396        }
23397    },
23398    loadScript: function loadScript(src, callback) {
23399        var loaded = false;
23400        var tag = document.createElement('script');
23401        var firstScriptTag = document.getElementsByTagName('script')[0];
23402        if (!firstScriptTag) {
23403            // when loaded in jest without jsdom setup it doesn't get any element.
23404            // In jest it doesn't really make sense to do anything, because no one is watching youtube in jest
23405            return;
23406        }
23407        firstScriptTag.parentNode.insertBefore(tag, firstScriptTag);
23408        tag.onload = function () {
23409            if (!loaded) {
23410                loaded = true;
23411                callback();
23412            }
23413        };
23414        tag.onreadystatechange = function () {
23415            if (!loaded && (this.readyState === 'complete' || this.readyState === 'loaded')) {
23416                loaded = true;
23417                callback();
23418            }
23419        };
23420        tag.src = src;
23421    },
23422    slick: function slick() {
23423        // TODO: https://codepen.io/tommydunn/pen/rNxQLNq?editors=1010
23424        var body = document.querySelector('body');
23425
23426        var slideWrapper = $('.masthead-carousel');
23427        // iframes = slideWrapper.find('.player--masthead iframe'),
23428        // lazyImages = slideWrapper.find('.masthead-carousel__slide'),
23429        // lazyCounter = 0;
23430
23431        // POST commands to YouTube
23432        function postMessageToPlayer(player, command) {
23433            // console.log(player);
23434            if (player == null || command == null) { return; }
23435            player.contentWindow.postMessage(JSON.stringify(command), '*');
23436        }
23437
23438        // When the slide is changing
23439        function playPauseVideo(slick, control) {
23440            var currentSlide, slideType, player;
23441
23442            currentSlide = slick.find('.slick-current');
23443            slideType = currentSlide.data('video-type');
23444
23445            if (slideType === 'youtube') {
23446                player = currentSlide.find('iframe').get(0);
23447                switch (control) {
23448                    case 'play':
23449                        postMessageToPlayer(player, {
23450                            'event': 'command',
23451                            'func': 'mute',
23452                        });
23453                        postMessageToPlayer(player, {
23454                            'event': 'command',
23455                            'func': 'playVideo',
23456                        });
23457                        break;
23458                    case 'pause':
23459                        postMessageToPlayer(player, {
23460                            'event': 'command',
23461                            'func': 'stopVideo',
23462                        });
23463                        break;
23464                }
23465            }
23466
23467            if (slideType === 'native') {
23468                player = currentSlide.find('video').get(0);
23469                player.currentTime = 0;
23470                switch (control) {
23471                    case 'play':
23472                        player.play();
23473                        break;
23474                    case 'pause':
23475                        player.pause();
23476                        break;
23477                }
23478            }
23479        }
23480
23481        // Resize player
23482        // function resizePlayer(iframes, ratio) {
23483        //     if (!iframes[0]) return;
23484        //     var win = $('.masthead-carousel'),
23485        //         width = win.width(),
23486        //         playerWidth,
23487        //         height = win.height(),
23488        //         playerHeight;
23489        //     // ratio = ratio || 16 / 9;
23490
23491        //     iframes.each(function () {
23492        //         var current = $(this);
23493        //         if (width / ratio < height) {
23494        //             playerWidth = Math.ceil(height * ratio);
23495        //             current.width(playerWidth).height(height).css({
23496        //                 left: (width - playerWidth) / 2,
23497        //                 top: 0,
23498        //             });
23499        //         } else {
23500        //             playerHeight = Math.ceil(width / ratio);
23501        //             current.width(width).height(playerHeight).css({
23502        //                 left: 0,
23503        //                 top: (height - playerHeight) / 2,
23504        //             });
23505        //         }
23506        //     });
23507        // }
23508
23509        // Initialize
23510        slideWrapper.on('init', function (slick) {
23511            // setTimeout(() => {
23512            body.classList.add('loaded');
23513            // }, 500);
23514
23515            // $(slick) = slick.currentTarget
23516            // console.log($(slick.currentTarget));
23517            playPauseVideo($(slick.currentTarget), 'play');
23518
23519            // resizePlayer(iframes, 16 / 9);
23520        });
23521
23522        // JavaScript to be fired on the home page
23523        slideWrapper.slick({
23524            dots: true,
23525            arrows: false,
23526            rows: 0,
23527            fade: true,
23528            autoplay: true,
23529            autoplaySpeed: 14000,
23530            speed: 800,
23531            pauseOnHover: false,
23532            slide: '.masthead-carousel__slide',
23533            customPaging: function (slider, i) {
23534                var title = $(slider.$slides[i]).data('title');
23535                return '<span class="dots__item"><span class="dots__title">' + title + '</span><span class="dots__number">0' + Number(i + 1) + '</span></span>';
23536            },
23537            dotsClass: 'slider-dots',
23538        });
23539
23540        slideWrapper.on('beforeChange', function (event, slick) {
23541            slick = $(slick.$slider);
23542            playPauseVideo(slick, 'pause');
23543        });
23544
23545        slideWrapper.on('afterChange', function (event, slick) {
23546            slick = $(slick.$slider);
23547            playPauseVideo(slick, 'play');
23548        });
23549
23550        // slideWrapper.on('lazyLoaded', function () {
23551        // lazyCounter++;
23552        // if (lazyCounter === lazyImages.length) {
23553        //     lazyImages.addClass('show');
23554        //     slideWrapper.slick("slickPlay");
23555        // }
23556        // });
23557
23558        // Resize event
23559        // $(window).on('resize.slickVideoPlayer', function () {
23560        //     resizePlayer(iframes, 16 / 9);
23561        // });
23562    },
23563    onYouTubeIframeAPIReady: function onYouTubeIframeAPIReady(playerId) {
23564        // This function creates an <iframe> (and YouTube player) after the API code downloads.
23565        // Video player output
23566        var player;
23567        var videoPlayer = document.getElementById(playerId);
23568        var videoUrl = videoPlayer.dataset.video;
23569        var body = document.querySelector('body');
23570
23571        // Get the video ID
23572        var regex = /(https?:\/\/)?((www\.)?(youtube(-nocookie)?|youtube.googleapis)\.com.*(v\/|v=|vi=|vi\/|e\/|embed\/|user\/.*\/u\/\d+\/)|youtu\.be\/)([_0-9a-z-]+)/i;
23573        var videoId = videoUrl.match(regex);
23574
23575        window.YT.ready(function () {
23576            player = new window.YT.Player(videoPlayer, { // eslint-disable-line no-undef
23577                height: '390',
23578                width: '640',
23579                videoId: videoId[7],
23580                playerVars: {
23581                    'playsinline': 1,
23582                    'autoplay': 1,
23583                    'controls': 0,
23584                    'disablekb': 1,
23585                    'enablejsapi': 1,
23586                    'fs': 0,
23587                    'loop': 1,
23588                    'modestbranding': 1,
23589                },
23590                events: {
23591                    'onReady': onPlayerReady,
23592                    onStateChange:
23593                        function (e) {
23594                            // console.log(window.YT.PlayerState);
23595                            if (e.data === window.YT.PlayerState.CUED || e.data === window.YT.PlayerState.UNSTARTED || e.data === window.YT.PlayerState.ENDED || e.data === window.YT.PlayerState.PAUSED) {
23596                                player.playVideo();
23597                            }
23598                        },
23599                },
23600            });
23601        });
23602
23603        // Called when the player's state changes
23604        // Available states: buffering, unstarted, cued, playing, paused, ended
23605        function onPlayerReady() {
23606            player.playVideo();
23607            player.mute();
23608
23609            setTimeout(function () {
23610                body.classList.add('loaded');
23611            }, 500);
23612        }
23613    },
23614    init: function init() {
23615        var this$1 = this;
23616
23617        // Masthead carousel
23618        this.slick();
23619
23620        // Masthead videos
23621        var videoPlayers = document.querySelectorAll('.player--masthead');
23622        if (videoPlayers) {
23623            videoPlayers.forEach(function (videoPlayer) {
23624                var videoPlayerId = videoPlayer.id;
23625                var videoId = videoPlayer.dataset.video;
23626                var source = videoPlayer.dataset.source;
23627                // data-source resolves the platform; fall back to legacy detection.
23628                if (source === 'youtube' || (!source && videoId && videoId.indexOf('youtube') > -1)) {
23629                    // Loads the IFrame Player API code asynchronously.
23630                    this$1.onYouTubeIframeAPIReady(videoPlayerId);
23631                } else if (source === 'bunny') {
23632                    // Bunny Stream background video (muted, looping autoplay)
23633                    Object(__WEBPACK_IMPORTED_MODULE_0__util_playerLoader__["a" /* loadBunnyPlayer */])(videoPlayer, { background: true });
23634                } else if (videoId) { // Kaltura Web Player
23635                    // Utilizes the TV Studio Player (V7) in Kaltura Management Console (KMC)
23636                    // https://developer.kaltura.com/player/web/getting-started-web
23637                    this$1.kalturaSession(videoPlayerId);
23638                }
23639            });
23640        }
23641    },
23642    finalize: function finalize() {
23643        // JavaScript to be fired on the home page, after the init JS
23644    },
23645});
23646
23647/* WEBPACK VAR INJECTION */}.call(__webpack_exports__, __webpack_require__(0)))
23648
23649/***/ }),
23650/* 41 */
23651/***/ (function(module, __webpack_exports__, __webpack_require__) {
23652
23653"use strict";
23654/* harmony default export */ __webpack_exports__["a"] = ({
23655  init: function init() {
23656    // JavaScript to be fired on the about us page
23657  },
23658});
23659
23660
23661/***/ }),
23662/* 42 */
23663/***/ (function(module, __webpack_exports__, __webpack_require__) {
23664
23665"use strict";
23666/* WEBPACK VAR INJECTION */(function($) {/* harmony import */ var __WEBPACK_IMPORTED_MODULE_0_isotope_layout__ = __webpack_require__(8);
23667/* harmony import */ var __WEBPACK_IMPORTED_MODULE_0_isotope_layout___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_0_isotope_layout__);
23668/* harmony import */ var __WEBPACK_IMPORTED_MODULE_1_infinite_scroll__ = __webpack_require__(9);
23669/* harmony import */ var __WEBPACK_IMPORTED_MODULE_1_infinite_scroll___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_1_infinite_scroll__);
23670/* harmony import */ var __WEBPACK_IMPORTED_MODULE_2_imagesloaded__ = __webpack_require__(7);
23671/* harmony import */ var __WEBPACK_IMPORTED_MODULE_2_imagesloaded___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_2_imagesloaded__);
23672
23673
23674
23675
23676/* harmony default export */ __webpack_exports__["a"] = ({
23677    iso: function iso() {
23678        var elem = document.querySelector('.listing--contributors');
23679
23680        if (elem) {
23681            var iso;
23682            var $select = $('.input-iso-select');
23683            var $selectize;
23684            var $filterCount = $('.total-posts-filtered');
23685
23686            // Instantiate selectize to use in conjunction
23687            if ($select) {
23688                $selectize = $select.selectize({
23689                    closeAfterSelect: true,
23690                });
23691
23692                $selectize.on('click', function () {
23693                    var $active = $selectize.find('.selectize-input');
23694                    if ($active.hasClass('input-active')) {
23695                        $selectize.close();
23696                    }
23697                });
23698            }
23699
23700            // Infinite scroll
23701            __WEBPACK_IMPORTED_MODULE_2_imagesloaded___default()(elem, function () {
23702                if ($select) {
23703                    iso = new __WEBPACK_IMPORTED_MODULE_0_isotope_layout___default.a(elem, {
23704                        itemSelector: '.col',
23705                        layoutMode: 'fitRows',
23706                        percentPosition: true,
23707                        // stagger: 50,
23708                        fitRows: {
23709                            // set to the element
23710                            gutter: 16,
23711                            columnWidth: '.col',
23712                        },
23713                        hiddenStyle: {
23714                            opacity: 0,
23715                            // transform: 'translateY(10px)',
23716                        },
23717                        visibleStyle: {
23718                            opacity: 1,
23719                            // transform: 'translateY(0px)',
23720                        },
23721                    });
23722
23723                    // set up URL params
23724                    var url = new URL(window.location.href);
23725                    var params = new URLSearchParams(url.searchParams);
23726
23727                    // First get searchparams on init
23728                    if (params.get('expertise') || params.get('initial')) {
23729                        var filters$1 = {};
23730
23731                        filters$1['expertise'] = params.get('expertise') ? params.get('expertise') : '';
23732                        filters$1['initial'] = params.get('initial') ? params.get('initial') : '';
23733
23734                        console.log(concatValues(filters$1));
23735                        iso.arrange({
23736                            filter: concatValues(filters$1),
23737                        });
23738
23739                        if ($selectize && filters$1['expertise']) {
23740                            var expertise$1 = $selectize[0].selectize;
23741                            expertise$1.setValue(params.get('expertise'));
23742                        }
23743
23744                        if ($selectize && filters$1['initial']) {
23745                            var initial = $selectize[1].selectize;
23746                            initial.setValue(params.get('initial'));
23747                        }
23748                    }
23749
23750                    // Filter on selection
23751                    // check if selectize is active, and use that as a trigger if so
23752                    if ($selectize) {
23753                        // fetch the instance
23754                        var expertise = $selectize[0].selectize;
23755
23756                        // store filter for each group
23757                        var filters = {};
23758
23759                        expertise.on('change', function (e) {
23760                            filters['expertise'] = e;
23761                            var filterValue = concatValues(filters);
23762                            iso.arrange({
23763                                filter: filterValue,
23764                            });
23765
23766                            // set filter in hash
23767                            params.set('expertise', e);
23768
23769                            // change the search property of the main url
23770                            url.search = params.toString();
23771
23772                            // Replace current querystring with the new one
23773                            history.pushState(null, null, '?' + params.toString());
23774
23775                            updateFilterCount();
23776                        });
23777
23778                        var selectizeName = $selectize[1].selectize;
23779
23780                        selectizeName.on('change', function (e) {
23781                            filters['name'] = e;
23782                            var filterValue = concatValues(filters);
23783                            iso.arrange({
23784                                filter: filterValue,
23785                            });
23786
23787                            params.set('initial', e);
23788
23789                            // change the search property of the main url
23790                            url.search = params.toString();
23791
23792                            // Replace current querystring with the new one
23793                            history.pushState(null, null, '?' + params.toString());
23794
23795                            updateFilterCount();
23796                        });
23797                    } else { // otherwise, use the <select>
23798                        // bind filter on select change
23799                        $select.on('change', function () {
23800                            // get filter value from option value
23801                            var filterValue = $(this).value;
23802
23803                            iso.arrange({
23804                                filter: filterValue,
23805                            });
23806
23807                            updateFilterCount();
23808                        });
23809                    }
23810
23811                    // flatten object by concatting values
23812                    function concatValues(obj) { // eslint-disable-line no-inner-declarations
23813                        var value = '';
23814                        for (var prop in obj) {
23815                            value += obj[prop];
23816                        }
23817                        return value;
23818                    }
23819
23820                    function updateFilterCount() { // eslint-disable-line no-inner-declarations
23821                        $filterCount.text(iso.filteredItems.length);
23822                    }
23823                }
23824
23825                // make imagesLoaded available for InfiniteScroll
23826                __WEBPACK_IMPORTED_MODULE_1_infinite_scroll___default.a.imagesLoaded = __WEBPACK_IMPORTED_MODULE_2_imagesloaded___default.a;
23827
23828                var infScroll = new __WEBPACK_IMPORTED_MODULE_1_infinite_scroll___default.a(elem, {  // eslint-disable-line no-unused-vars
23829                    path: '.next',
23830                    append: '.inf-post',
23831                    history: 'push',
23832                    outlayer: iso,
23833                    // debug: true,
23834                    scrollThreshold: 700,
23835                    hideNav: '.pagination',
23836                    status: '.page-load-status',
23837                });
23838            });
23839
23840            // imagesloaded(elem).on('progress', function () {
23841            //     iso.layout();
23842            // });
23843        }
23844    },
23845    init: function init() {
23846        // JavaScript to be fired on the contributors page
23847        this.iso();
23848    },
23849});
23850
23851/* WEBPACK VAR INJECTION */}.call(__webpack_exports__, __webpack_require__(0)))
23852
23853/***/ }),
23854/* 43 */
23855/***/ (function(module, __webpack_exports__, __webpack_require__) {
23856
23857"use strict";
23858/* harmony default export */ __webpack_exports__["a"] = ({
23859    init: function init() {
23860        // JavaScript to be fired on the topic guide page
23861        var el = document.querySelector('.sticky-labels');
23862        var pillars = document.querySelectorAll('.pillar-sticky__scrolly');
23863        var observer = new IntersectionObserver(function (ref) {
23864                var e = ref[0];
23865
23866                return e.target.classList.toggle('is-pinned', e.intersectionRatio < 1);
23867        },
23868            { threshold: [1] }
23869        );
23870
23871        observer.observe(el);
23872        pillars.forEach(function (pillar) {
23873            observer.observe(pillar);
23874        })
23875    },
23876});
23877
23878
23879/***/ }),
23880/* 44 */
23881/***/ (function(module, __webpack_exports__, __webpack_require__) {
23882
23883"use strict";
23884/* WEBPACK VAR INJECTION */(function($) {/* harmony import */ var __WEBPACK_IMPORTED_MODULE_0_imagesloaded__ = __webpack_require__(7);
23885/* harmony import */ var __WEBPACK_IMPORTED_MODULE_0_imagesloaded___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_0_imagesloaded__);
23886/* harmony import */ var __WEBPACK_IMPORTED_MODULE_1_isotope_layout__ = __webpack_require__(8);
23887/* harmony import */ var __WEBPACK_IMPORTED_MODULE_1_isotope_layout___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_1_isotope_layout__);
23888/* harmony import */ var __WEBPACK_IMPORTED_MODULE_2_infinite_scroll__ = __webpack_require__(9);
23889/* harmony import */ var __WEBPACK_IMPORTED_MODULE_2_infinite_scroll___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_2_infinite_scroll__);
23890
23891
23892
23893
23894/* harmony default export */ __webpack_exports__["a"] = ({
23895    isotope: function isotope() {
23896        // Set up isotope options
23897        var isoOptions = {
23898            itemSelector: '.col',
23899            layoutMode: 'fitRows',
23900            percentPosition: true,
23901            stagger: 100,
23902            fitRows: {
23903                // set to the element
23904                gutter: 16,
23905                columnWidth: '.col',
23906            },
23907            hiddenStyle: {
23908                opacity: 0,
23909                transform: 'translateY(10px)',
23910            },
23911            visibleStyle: {
23912                opacity: 1,
23913                transform: 'translateY(0px)',
23914            },
23915        };
23916
23917        // Instantiate selectize to use in conjunction
23918        var select = document.querySelector('.input-iso-select');
23919        if (select) {
23920            var $selectize = $('.input-iso-select').selectize({
23921                create: true,
23922                sortField: 'text',
23923            });
23924        }
23925
23926
23927        var iso;
23928
23929        // initialize Isotope
23930        function episodesIso() {
23931            var grid = document.querySelector('.listing--videos-episodes');
23932
23933            if (grid) {
23934                __WEBPACK_IMPORTED_MODULE_0_imagesloaded___default()(grid, function () {
23935                    if (select) {
23936                        // images have loaded
23937                        iso = new __WEBPACK_IMPORTED_MODULE_1_isotope_layout___default.a(grid, isoOptions);
23938
23939                        // Filter on selection
23940                        // check if selectize is active, and use that as a trigger if so
23941                        if ($selectize) {
23942                            // fetch the instance
23943                            var selectize = $selectize[0].selectize;
23944
23945                            selectize.on('change', function (e) {
23946                                console.log(e);
23947                                iso.arrange({
23948                                    filter: e,
23949                                });
23950                            });
23951                        } else { // otherwise, use the <select>
23952                            // bind filter on select change
23953                            select.addEventListener('change', function () {
23954                                // get filter value from option value
23955                                var filterValue = this.value;
23956                                // console.log(filterValue);
23957
23958                                iso.arrange({
23959                                    filter: filterValue,
23960                                });
23961                            });
23962                        }
23963                    }
23964
23965                    // make imagesLoaded available for InfiniteScroll
23966                    __WEBPACK_IMPORTED_MODULE_2_infinite_scroll___default.a.imagesLoaded = __WEBPACK_IMPORTED_MODULE_0_imagesloaded___default.a;
23967
23968                    // Infinite scroll
23969                    var infScroll = new __WEBPACK_IMPORTED_MODULE_2_infinite_scroll___default.a(grid, {  // eslint-disable-line no-unused-vars
23970                        path: '.next',
23971                        append: '.inf-post',
23972                        history: 'push',
23973                        outlayer: iso,
23974                        // debug: true,
23975                        scrollThreshold: 450,
23976                        hideNav: '.pagination',
23977                        status: '.page-load-status',
23978                    });
23979                });
23980            }
23981        }
23982
23983        // On sub-nav item click, check if Episodes wrapper has class active
23984        var subNav = document.querySelectorAll('.sub-nav__item');
23985        var episodes = document.querySelector('#episodes');
23986
23987        subNav.forEach(function (item) {
23988            item.addEventListener('click', function () {
23989                if (episodes.classList.contains('active')) {
23990                    episodesIso();
23991                } else {
23992                    console.log('destroyed');
23993                    iso.destroy();
23994                }
23995                // set flag
23996                // isActive = !isActive;
23997            });
23998        });
23999
24000
24001    },
24002    init: function init() {
24003        this.isotope();
24004
24005        // JavaScript to be fired on the episodes page
24006        var toggleLink = document.querySelectorAll('.tab-toggle__link');
24007        var toggleContent = document.querySelectorAll('.tab-toggle__content');
24008
24009        toggleLink.forEach(function (link) {
24010            link.addEventListener('click', function (e) {
24011                e.preventDefault();
24012                var id = this.getAttribute('href');
24013
24014                [].forEach.call(toggleLink, function (el) {
24015                    el.classList.remove('active');
24016                });
24017
24018                // find corresponding content
24019                var content = document.querySelector(id);
24020                if (content) {
24021                    link.classList.add('active');
24022
24023                    [].forEach.call(toggleContent, function (el) {
24024                        el.classList.remove('active');
24025                    });
24026
24027                    content.classList.add('active');
24028                }
24029            });
24030        });
24031    },
24032});
24033
24034/* WEBPACK VAR INJECTION */}.call(__webpack_exports__, __webpack_require__(0)))
24035
24036/***/ }),
24037/* 45 */
24038/***/ (function(module, __webpack_exports__, __webpack_require__) {
24039
24040"use strict";
24041/* WEBPACK VAR INJECTION */(function(jQuery) {/* harmony import */ var __WEBPACK_IMPORTED_MODULE_0__util_playerLoader__ = __webpack_require__(4);
24042// import kaltura from 'kaltura-client';
24043
24044
24045// Holds the active YouTube player so the format toggle can switch the video
24046// in-place (preserving its state/event handlers) rather than recreating it.
24047var ytPlayer = null;
24048
24049// The platform last mounted in #video-player. Set in init() and at mount time on
24050// each cross-platform switch; used by replacePlayerEl to know which player to tear
24051// down. (The same-vs-cross decision in switchPlayer uses live-player checks, not
24052// this, because this value lags during an async SDK load.)
24053var currentSource = null;
24054
24055// YouTube watch-URL → 11-char video id (mirrors the legacy toggle regex).
24056var YT_ID_REGEX = /(?:youtube(?:-nocookie)?\.com.*(?:v=|embed\/|v\/)|youtu\.be\/)([_0-9a-z-]{11})/i;
24057
24058// Monotonic token for cross-platform switches. Incremented at the start of each
24059// switch; deferred SDK-load callbacks bail if a newer switch has superseded them
24060// (prevents a slow script load from mounting a player the user already left).
24061var switchToken = 0;
24062
24063// The YouTube session registers a window 'unload' progress-write. Bind it only
24064// once per page (it reads the module-scoped current ytPlayer) so repeated
24065// cross-platform returns to YouTube don't accumulate duplicate unload handlers.
24066var ytUnloadBound = false;
24067
24068// Flushes the current YouTube player's watch position to the tracker. Set by the
24069// YouTube session when it mounts (closes over its tracker context); called before
24070// the player is destroyed on a source switch so "Continue Watching" isn't lost.
24071var ytFlushProgress = null;
24072
24073// Tear down whatever player currently occupies #video-player and replace it with
24074// a fresh empty container carrying the new id/source. Required because
24075// new YT.Player()/KalturaPlayer.setup() replace or mutate the node, so loading a
24076// different platform needs a clean div to mount into. Captures the parent before
24077// teardown so it works whether the old player removed the node (YouTube) or left
24078// it in place (Kaltura/Bunny).
24079function replacePlayerEl(id, source) {
24080    var old = document.getElementById('video-player');
24081    var parent = old ? old.parentNode : null;
24082    var anchor = old ? old.nextSibling : null;
24083    try {
24084        if (currentSource === 'youtube' && ytPlayer && typeof ytPlayer.destroy === 'function') {
24085            // Capture the watch position BEFORE destroying — the YouTube tracker
24086            // otherwise only writes on pause/ended/unload, and destroy() + null
24087            // would drop the current position on a source switch.
24088            if (ytFlushProgress) { ytFlushProgress(); }
24089            ytPlayer.destroy();
24090        } else if (currentSource === 'kaltura' && window.KalturaPlayer && typeof window.KalturaPlayer.getPlayer === 'function') {
24091            var kp = window.KalturaPlayer.getPlayer('video-player');
24092            if (kp) { kp.destroy(); }
24093        }
24094    } catch (e) {
24095        // Best-effort teardown; rebuild the container regardless.
24096    }
24097    ytPlayer = null;
24098    var leftover = document.getElementById('video-player');
24099    if (leftover && leftover.parentNode) {
24100        leftover.parentNode.removeChild(leftover);
24101    }
24102    var fresh = document.createElement('div');
24103    fresh.id = 'video-player';
24104    fresh.className = 'player';
24105    fresh.style.cssText = 'width: 770px;height: 360px';
24106    fresh.dataset.video = id;
24107    fresh.dataset.source = source;
24108    if (parent) {
24109        parent.insertBefore(fresh, anchor);
24110    }
24111    return fresh;
24112}
24113
24114// Switch the single-video player to (id, source) from a format-toggle click.
24115// Same platform → fast in-place switch (preserves the loaded player + its
24116// tracking/auto-advance handlers). Different platform → rebuild the container and
24117// load the target platform fresh, with autoplay (the click is a user gesture) and
24118// the cover overlay hidden. `self` is the route object (for loadScript + sessions).
24119function switchPlayer(self, id, source) {
24120    // Every click bumps the token, so any in-flight cross-platform load is
24121    // cancelled (its mount() bails). This must happen on EVERY click — including
24122    // ones that look "same-platform" — or a pending load could still mount a
24123    // player the user has since clicked away from.
24124    var token = ++switchToken;
24125
24126    // Decide in-place vs rebuild from the ACTUALLY-LIVE player, not from
24127    // currentSource (which lags during an async load). If the requested
24128    // platform's player isn't live right now, fall through to a fresh rebuild.
24129    var kalturaLive = window.KalturaPlayer && typeof window.KalturaPlayer.getPlayer === 'function' && window.KalturaPlayer.getPlayer('video-player');
24130    var playerEl = document.getElementById('video-player');
24131    var bunnyIframe = playerEl ? playerEl.querySelector('iframe') : null;
24132    var bunnyLive = bunnyIframe && bunnyIframe.src.indexOf('mediadelivery.net') > -1;
24133
24134    if (source === 'youtube' && ytPlayer && typeof ytPlayer.loadVideoById === 'function') {
24135        var m = id.match(YT_ID_REGEX);
24136        if (m) { ytPlayer.loadVideoById(m[1]); }
24137        return;
24138    }
24139    if (source === 'bunny' && bunnyLive) {
24140        Object(__WEBPACK_IMPORTED_MODULE_0__util_playerLoader__["b" /* swapBunnyVideo */])(playerEl, id, { background: false });
24141        return;
24142    }
24143    if (source === 'kaltura' && kalturaLive) {
24144        try {
24145            // Tear down the existing Kaltura player before recreating so a
24146            // Short/Long switch can't double-instantiate.
24147            var existing = window.KalturaPlayer.getPlayer('video-player');
24148            if (existing) { existing.destroy(); }
24149            var kalturaPlayer = KalturaPlayer.setup({ // eslint-disable-line no-undef
24150                targetId: 'video-player',
24151                provider: { partnerId: '1529571', uiConfId: '49927973' },
24152                playback: { autoplay: true },
24153            });
24154            kalturaPlayer.loadMedia({ entryId: id });
24155        } catch (err) {
24156            console.error(err.message); // eslint-disable-line no-console
24157        }
24158        return;
24159    }
24160
24161    // Cross-platform (or the target isn't live yet): clean container, then load
24162    // the target platform. The `token` captured above guards the async SDK-load
24163    // callbacks below — a stale callback bails instead of mounting the wrong
24164    // player. currentSource is set only at mount time, so a failed/blocked script
24165    // load doesn't strand the toggle treating the same target as "same-platform".
24166    replacePlayerEl(id, source);
24167    var overlay = document.querySelector('.video-player-wrap__image');
24168    if (overlay) { overlay.style.display = 'none'; }
24169
24170    var mount = function () {
24171        if (token !== switchToken) {
24172            return; // a newer switch superseded this one
24173        }
24174        currentSource = source;
24175        if (source === 'youtube') {
24176            self.onYouTubeIframeAPIReady({ autoplay: true });
24177        } else if (source === 'bunny') {
24178            self.bunnySession({ autoplay: true });
24179        } else if (source === 'kaltura') {
24180            self.kalturaSession({ autoplay: true });
24181        }
24182    };
24183
24184    if (source === 'youtube' && !(window.YT && typeof window.YT.ready === 'function')) {
24185        self.loadScript('https://www.youtube.com/iframe_api', mount);
24186    } else if (source === 'kaltura' && !window.KalturaPlayer) {
24187        self.loadScript('https://cdnapisec.kaltura.com/p/1529571/embedPlaykitJs/flavorId/861301/uiconf_id/49927973', mount);
24188    } else {
24189        // SDK already present (or Bunny, which lazy-loads Player.js inside bunnySession).
24190        mount();
24191    }
24192}
24193
24194/* harmony default export */ __webpack_exports__["a"] = ({
24195    contentToggle: function contentToggle() {
24196        var toggle = document.querySelectorAll('.tab-toggle');
24197
24198        if (toggle) {
24199            toggle.forEach(function (item) {
24200                var toggleLink = item.querySelectorAll('.tab-toggle__link');
24201                var toggleContent = item.querySelectorAll('.tab-toggle__content');
24202
24203                toggleLink.forEach(function (link) {
24204                    link.addEventListener('click', function (e) {
24205                        e.preventDefault();
24206                        var id = this.getAttribute('href');
24207
24208                        [].forEach.call(toggleLink, function (el) {
24209                            el.classList.remove('active');
24210                        });
24211
24212                        // find corresponding content
24213                        var content = document.querySelector(id);
24214                        if (content) {
24215                            link.classList.add('active');
24216
24217                            [].forEach.call(toggleContent, function (el) {
24218                                el.classList.remove('active');
24219                            });
24220
24221                            content.classList.add('active');
24222                        }
24223                    });
24224                });
24225            });
24226        }
24227    },
24228    loadScript: function loadScript(src, callback) {
24229        var loaded = false;
24230        var tag = document.createElement('script');
24231        var firstScriptTag = document.getElementsByTagName('script')[0];
24232        if (!firstScriptTag) {
24233            // when loaded in jest without jsdom setup it doesn't get any element.
24234            // In jest it doesn't really make sense to do anything, because no one is watching youtube in jest
24235            return;
24236        }
24237        firstScriptTag.parentNode.insertBefore(tag, firstScriptTag);
24238        tag.onload = function () {
24239            if (!loaded) {
24240                loaded = true;
24241                callback();
24242            }
24243        };
24244        tag.onreadystatechange = function () {
24245            if (!loaded && (this.readyState === 'complete' || this.readyState === 'loaded')) {
24246                loaded = true;
24247                callback();
24248            }
24249        };
24250        tag.src = src;
24251    },
24252    onYouTubeIframeAPIReady: function onYouTubeIframeAPIReady(ref) {
24253        if ( ref === void 0 ) ref = {};
24254        var autoplay = ref.autoplay; if ( autoplay === void 0 ) autoplay = false;
24255
24256        // This function creates an <iframe> (and YouTube player)
24257        // after the API code downloads. `autoplay` is set when a cross-platform
24258        // format-toggle click recreates the player (a user gesture); the initial
24259        // page load calls this with no args (autoplay off, overlay-driven).
24260
24261        // Video player output
24262        var player;
24263        var videoPlayer = document.getElementById('video-player');
24264        var videoUrl = videoPlayer.dataset.video;
24265        var article = document.querySelector('article.single-video');
24266        var userId = article.dataset.uid;
24267        var postId = article.dataset.pid;
24268        var videoImage = document.querySelector('.video-player-wrap__image');
24269
24270        // Get the video ID
24271        var regex = /(https?:\/\/)?((www\.)?(youtube(-nocookie)?|youtube.googleapis)\.com.*(v\/|v=|vi=|vi\/|e\/|embed\/|user\/.*\/u\/\d+\/)|youtu\.be\/)([_0-9a-z-]+)/i;
24272        var videoId = videoUrl.match(regex);
24273
24274        // Set duration
24275        var params = new URLSearchParams(window.location.search);
24276        var watched = params.get('watched');
24277        var seconds = watched ? watched : 0;
24278
24279        window.YT.ready(function () {
24280            player = new window.YT.Player(videoPlayer, { // eslint-disable-line no-undef
24281                height: '390',
24282                width: '640',
24283                videoId: videoId[7],
24284                startSeconds: seconds,
24285                playerVars: {
24286                    'playsinline': 1,
24287                    'rel': 0,
24288                    'color': 'white',
24289                    'autoplay': autoplay ? 1 : 0,
24290                },
24291                events: {
24292                    // 'onReady': onPlayerReady,
24293                    'onStateChange': onPlayerStateChange,
24294                },
24295            });
24296            // Expose for in-place video switching from the format toggle.
24297            ytPlayer = player;
24298        });
24299
24300        // If a video exists, we'll use it as an initial "play" button, on click the video will play and the image will be hidden
24301        if (videoImage) {
24302            videoImage.addEventListener('click', function () {
24303                player.playVideo();
24304                videoImage.style.display = 'none';
24305            });
24306        }
24307
24308        // Redirect to next video in playlist, if it exists
24309        function redirectNext() {
24310            var nextVideo = false,
24311                playlist = document.querySelector('#current-playlist');
24312
24313            if (playlist) {
24314                var currentVideo = playlist.querySelector('.list-item--playing');
24315                var sibling = currentVideo.nextElementSibling;
24316                if (sibling) {
24317                    nextVideo = sibling.querySelector('a');
24318                    location.assign(nextVideo.href);
24319                }
24320            }
24321        }
24322
24323        // Called when the player's state changes
24324        // Available states: buffering, unstarted, cued, playing, paused, ended
24325        function onPlayerStateChange() {
24326            var state = player.getPlayerState();
24327
24328            if (state == 2) { // Paused
24329                var totalTime = player.getDuration(); // Total video length (in seconds)
24330                var currentTime = player.getCurrentTime(); // Current elasped time (in seconds)
24331                var percentage = (currentTime / totalTime) * 100; // Percentage of video watched
24332                percentage = Math.round(percentage);
24333
24334                // Add video data to custom user meta
24335                UpdateVideoTracker(currentTime, percentage); // This is only used for front-end display so a rounded number is fine
24336            }
24337
24338            // Completed
24339            if (state == 0) { // Ended
24340                UpdateVideoTracker(player.getCurrentTime(), 100);
24341
24342                redirectNext();
24343            }
24344        }
24345
24346        // Add percentage to video tracker
24347        function UpdateVideoTracker(duration, percentage) {
24348            jQuery.ajax({
24349                type: 'post',
24350                dataType: 'json',
24351                url: ajax_obj.ajax_url, // eslint-disable-line no-undef
24352                data: { // TODO: Should this be stored as postmeta instead? We will need to query this meta data throughout
24353                    action: 'video_tracker',
24354                    post_id: postId,
24355                    user_id: userId,
24356                    percentage: percentage,
24357                    duration: duration,
24358                    _ajax_nonce: ajax_obj.nonce, // eslint-disable-line no-undef
24359                },
24360                success: function (response) {
24361                    if (response.type != 'success') {
24362                        alert('Sorry, an error occured. Please try again.');
24363                    }
24364                },
24365            });
24366        }
24367
24368        // Expose a progress flush so a cross-platform source switch can capture the
24369        // current watch position before this player is destroyed (replacePlayerEl
24370        // calls this before ytPlayer.destroy()). Reads the module-scoped ytPlayer.
24371        ytFlushProgress = function () {
24372            if (!ytPlayer || typeof ytPlayer.getPlayerState !== 'function') {
24373                return;
24374            }
24375            var state = ytPlayer.getPlayerState();
24376            if (state === 1 || state === 2) { // playing or paused
24377                var totalTime = ytPlayer.getDuration();
24378                var currentTime = ytPlayer.getCurrentTime();
24379                var percentage = Math.round((currentTime / totalTime) * 100);
24380                UpdateVideoTracker(currentTime, percentage);
24381            }
24382        };
24383
24384        // On page close, if video is playing or paused, mark as Watched or Continue
24385        // Watching. Bind ONCE per page and read the module-scoped current ytPlayer,
24386        // so repeated cross-platform returns to YouTube don't stack duplicate unload
24387        // handlers (which would write skewed progress and read destroyed players).
24388        // postId/userId are page-constant, so the first binding's closure is correct.
24389        if (!ytUnloadBound) {
24390            ytUnloadBound = true;
24391            window.addEventListener('unload', function () {
24392                if (!ytPlayer || typeof ytPlayer.getPlayerState !== 'function') {
24393                    return; // no live YouTube player (e.g. switched to another source)
24394                }
24395                if (ytPlayer.getPlayerState() == (1 || 2)) { // Playing or paused
24396                    var totalTime = ytPlayer.getDuration(); // Total video length (in seconds)
24397                    var currentTime = ytPlayer.getCurrentTime(); // Current elasped time (in seconds)
24398                    var percentage = (currentTime / totalTime) * 100; // Percentage of video watched
24399                    percentage = Math.round(percentage); // This is only used for front-end display so a rounded number is fine
24400
24401                    console.log(percentage);
24402                    // Add video data to custom user meta
24403                    UpdateVideoTracker(currentTime, percentage);
24404                }
24405            });
24406        }
24407    },
24408    bunnySession: function bunnySession(ref) {
24409        if ( ref === void 0 ) ref = {};
24410        var autoplay = ref.autoplay; if ( autoplay === void 0 ) autoplay = false;
24411
24412        // Bunny Stream player on a single video page, with progress tracking.
24413        // `autoplay` is set when a cross-platform format-toggle click recreates
24414        // the player; the initial page load passes no args (overlay-driven).
24415        var videoPlayer = document.getElementById('video-player');
24416        if (!videoPlayer) {
24417            return;
24418        }
24419
24420        // Custom overlay image (custom_overlay_image), sits above the player.
24421        var videoImage = document.querySelector('.video-player-wrap__image');
24422
24423        var article = document.querySelector('article.single-video');
24424        var userId = article ? article.dataset.uid : null;
24425        var postId = article ? article.dataset.pid : null;
24426
24427        // Resume from the watched position when present — mirrors the YouTube
24428        // (startSeconds) and Kaltura (startTime) paths so "Continue Watching"
24429        // links restore the same place on Bunny.
24430        var params = new URLSearchParams(window.location.search);
24431        var watched = params.get('watched');
24432        var startSeconds = watched ? parseInt(watched, 10) : 0;
24433
24434        function BunnyUpdateVideoTracker(duration, percentage) {
24435            jQuery.ajax({
24436                type: 'post',
24437                dataType: 'json',
24438                url: ajax_obj.ajax_url, // eslint-disable-line no-undef
24439                data: {
24440                    action: 'video_tracker',
24441                    post_id: postId,
24442                    user_id: userId,
24443                    percentage: percentage,
24444                    duration: duration,
24445                    _ajax_nonce: ajax_obj.nonce, // eslint-disable-line no-undef
24446                },
24447            });
24448        }
24449
24450        // Cache the latest position from the high-frequency timeupdate event
24451        // (no network here), and only write progress on the coarse pause/ended
24452        // events — matching the YouTube (state 2 / 0) and Kaltura tracker cadence
24453        // so we don't flood admin-ajax / wp_ctt_video_tracker.
24454        var lastSeconds = 0;
24455        var lastDuration = 0;
24456
24457        var onTimeUpdate = function (data) {
24458            var d = (typeof data === 'string') ? JSON.parse(data) : data;
24459            lastSeconds = d.seconds || 0;
24460            lastDuration = d.duration || 0;
24461        };
24462
24463        var onPause = function () {
24464            if (!userId) {
24465                return;
24466            }
24467            var percentage = lastDuration ? Math.round((lastSeconds / lastDuration) * 100) : 0;
24468            BunnyUpdateVideoTracker(Math.round(lastSeconds), percentage);
24469        };
24470
24471        var onEnded = function () {
24472            if (userId) {
24473                BunnyUpdateVideoTracker(Math.round(lastSeconds || lastDuration), 100);
24474            }
24475            // Auto-advance to the next playlist item on completion, mirroring the
24476            // YouTube (redirectNext) and Kaltura ('idle' state) behaviour.
24477            var playlist = document.querySelector('#current-playlist');
24478            if (playlist) {
24479                var currentVideo = playlist.querySelector('.list-item--playing');
24480                var sibling = currentVideo ? currentVideo.nextElementSibling : null;
24481                if (sibling) {
24482                    var nextVideo = sibling.querySelector('a');
24483                    if (nextVideo) {
24484                        location.assign(nextVideo.href);
24485                    }
24486                }
24487            }
24488        };
24489
24490        var render = function () {
24491            // Don't autoplay — mirror the YouTube path: the custom overlay (if
24492            // present) is the play affordance; otherwise the iframe's own
24493            // controls start playback.
24494            var player = Object(__WEBPACK_IMPORTED_MODULE_0__util_playerLoader__["a" /* loadBunnyPlayer */])(videoPlayer, {
24495                background: false,
24496                autoplay: autoplay,
24497                start: startSeconds,
24498                onTimeUpdate: onTimeUpdate,
24499                onPause: onPause,
24500                onEnded: onEnded,
24501            });
24502
24503            // Overlay click → start playback and hide the overlay (mirrors YouTube).
24504            if (videoImage) {
24505                videoImage.addEventListener('click', function () {
24506                    if (player && typeof player.play === 'function') {
24507                        player.play();
24508                    }
24509                    videoImage.style.display = 'none';
24510                });
24511            }
24512        };
24513
24514        // Player.js powers the events; load it on demand if not already present.
24515        if (window.playerjs) {
24516            render();
24517        } else {
24518            this.loadScript('https://assets.mediadelivery.net/playerjs/playerjs-latest.min.js', render);
24519        }
24520    },
24521    loadFormats: function loadFormats() {
24522        // Short/Long format toggle — platform-aware (YouTube / Bunny / Kaltura).
24523        var formats = document.querySelectorAll('.video-format');
24524        var videoPlayer = document.getElementById('video-player');
24525        if (!formats.length || !videoPlayer) {
24526            return;
24527        }
24528
24529        var self = this;
24530        formats.forEach(function (link) {
24531            link.addEventListener('click', function (e) {
24532                e.preventDefault();
24533                var id = link.dataset.videoId;
24534                var source = link.dataset.source;
24535                // switchPlayer decides same-platform (in-place) vs cross-platform
24536                // (rebuild + load the other platform). Each format link carries its
24537                // own data-source, so Short and Long can live on different platforms.
24538                switchPlayer(self, id, source);
24539            });
24540        });
24541    },
24542    kalturaSession: function kalturaSession(ref) {
24543        if ( ref === void 0 ) ref = {};
24544        var autoplay = ref.autoplay; if ( autoplay === void 0 ) autoplay = false;
24545
24546        // `autoplay` is set when a cross-platform format-toggle click recreates
24547        // the player; the initial page load passes no args (autoplay off).
24548        var partnerId = '1529571',
24549            playerId = '49927973',
24550            videoPlayer = document.getElementById('video-player'),
24551            videoId = videoPlayer.dataset.video,
24552            nextVideo = false,
24553            playlist = document.querySelector('#current-playlist');
24554
24555        var article = document.querySelector('article.single-video');
24556        var userId = article.dataset.uid;
24557        var postId = article.dataset.pid;
24558
24559        // Set duration
24560        var params = new URLSearchParams(window.location.search);
24561        var watched = params.get('watched');
24562        var seconds = watched ? parseInt(watched) : 0;
24563
24564        function KalturaUpdateVideoTracker(duration, percentage, userId, postId) {
24565            jQuery.ajax({
24566                type: 'post',
24567                dataType: 'json',
24568                url: ajax_obj.ajax_url, // eslint-disable-line no-undef
24569                data: {
24570                    action: 'video_tracker',
24571                    post_id: postId,
24572                    user_id: userId,
24573                    percentage: percentage,
24574                    duration: duration,
24575                    _ajax_nonce: ajax_obj.nonce, // eslint-disable-line no-undef
24576                },
24577                success: function (response) {
24578                    if (response.type != 'success') {
24579                        alert('Sorry, an error occured. Please try again.');
24580                    }
24581                },
24582            });
24583        }
24584
24585        if (playlist) {
24586            var currentVideo = playlist.querySelector('.list-item--playing');
24587            var sibling = currentVideo.nextElementSibling;
24588            if (sibling) {
24589                nextVideo = sibling.querySelector('a');
24590            }
24591        }
24592
24593        // config options: https://developer.kaltura.com/player/web/configuration-web
24594        // repo: https://github.com/kaltura/kaltura-player-js
24595        try {
24596            var kalturaPlayer = KalturaPlayer.setup({ // eslint-disable-line no-undef
24597                targetId: 'video-player',
24598                provider: {
24599                    partnerId: partnerId,
24600                    uiConfId: playerId,
24601                },
24602                playback: {
24603                    autoplay: autoplay,
24604                },
24605                sources: {
24606                    startTime: seconds,
24607                },
24608            });
24609
24610            kalturaPlayer.loadMedia({ entryId: videoId });
24611
24612            // let player = kalturaPlayer;
24613
24614            // var videoTracks = player.getTracks(player.Track.VIDEO);
24615            // var lowBandwidthTrack;
24616            // var lowBandwidth = 725624;
24617            // for (var i = 0; i < videoTracks.length; i++) {
24618            //     if (videoTracks[i].bandwidth < lowBandwidth) {
24619            //         lowBandwidthTrack = videoTracks[i];
24620            //         lowBandwidth = lowBandwidthTrack.bandwidth;
24621            //     }
24622            // }
24623            // player.selectTrack(lowBandwidthTrack);
24624
24625            // player.addEventListener(player.Event.VIDEO_TRACK_CHANGED, function (event) {
24626            //     console.log('The new bitrate is: ' + event.payload.selectedVideoTrack.bandwidth);
24627            // });
24628
24629            // TODO: Figure out how tf to adjust bitrate to load audio version
24630            // kalturaPlayer.ready().then(function () {
24631            // console.log(kalturaPlayer.isAdaptiveBitrateEnabled());
24632            // let tracks = kalturaPlayer.getTracks();
24633            // let activeTracks = kalturaPlayer.getActiveTracks();
24634            // console.log('This source has ' + tracks.length + ' tracks');
24635            // console.log('The active video track is: ' + JSON.stringify(activeTracks.video));
24636            // let videoTracks = kalturaPlayer.getTracks();
24637            // for (var i = 0; i < videoTracks.length; i++) {
24638            //     console.log(videoTracks[i].bandwidth);
24639            // console.log('Track ' + [i] + ': ' + JSON.stringify(videoTracks[i]));
24640            // });
24641
24642            // Redirect to next video in playlist, if it exists
24643
24644            kalturaPlayer.addEventListener(kalturaPlayer.Event.PLAYER_STATE_CHANGED, function (event) {
24645                var newState = event.payload.newState.type;
24646                if (newState == 'paused') { // Paused
24647                    var totalTime = Math.round(kalturaPlayer.duration); // Total video length (in seconds)
24648                    var currentTime = Math.round(kalturaPlayer.currentTime); // Current elasped time (in seconds)
24649                    var percentage = (currentTime / totalTime) * 100; // Percentage of video watched
24650                    percentage = Math.round(percentage);
24651
24652                    // Add video data to custom user meta
24653                    KalturaUpdateVideoTracker(currentTime, percentage, userId, postId);
24654                }
24655
24656                if (newState == 'idle' && nextVideo) { // Complete
24657                    location.assign(nextVideo.href);
24658                }
24659
24660                if (newState == 'idle') { // Complete
24661                    var totalTime$1 = Math.round(kalturaPlayer.duration); // Total video length (in seconds)
24662                    var currentTime$1 = Math.round(kalturaPlayer.currentTime); // Current elasped time (in seconds)
24663                    var percentage$1 = (currentTime$1 / totalTime$1) * 100; // Percentage of video watched
24664                    percentage$1 = Math.round(percentage$1);
24665
24666                    // Add video data to custom user meta
24667                    KalturaUpdateVideoTracker(currentTime$1, percentage$1, userId, postId);
24668                }
24669            });
24670
24671            // Add percentage to video tracker
24672
24673
24674            // Short/Long format switching is owned by loadFormats() (single
24675            // handler for all platforms) — no per-player format binding here.
24676        } catch (e) {
24677            console.error(e.message)
24678        }
24679    },
24680    playlists: function playlists() {
24681        var currentPlaylist = document.querySelector('#current-playlist');
24682
24683        if (currentPlaylist) {
24684            var titles = currentPlaylist.querySelectorAll('.list-item__title');
24685            var titleCounts = {};
24686
24687            // First pass: count occurrences of each title
24688            titles.forEach(function(title) {
24689                var titleText = title.innerText;
24690                titleCounts[titleText] = (titleCounts[titleText] || 0) + 1;
24691            });
24692
24693            // Second pass: add numbers to duplicate titles
24694            titles.forEach(function(title) {
24695                var titleText = title.innerText;
24696                if (titleCounts[titleText] > 1) {
24697                    // Create a counter for this specific title
24698                    titleCounts[titleText + '_counter'] = (titleCounts[titleText + '_counter'] || 0) + 1;
24699                    title.innerText = titleText + ' #' + titleCounts[titleText + '_counter'];
24700                }
24701            });
24702        }
24703    },
24704    transcripts: function transcripts() {
24705        // Long
24706        var btnLong = document.querySelector('.transcript--long .transcript__copy-btn');
24707        var transcriptLong = document.querySelector('.transcript--long .transcript__content');
24708
24709        if (btnLong && transcriptLong) {
24710            btnLong.addEventListener('click', function (e) {
24711                e.preventDefault();
24712
24713                /* Select the text field */
24714                navigator.clipboard.writeText(transcriptLong.textContent).then(function () {
24715                    // Alert the user that the action took place.
24716                    // Nobody likes hidden stuff being done under the hood!
24717                    console.log('Copied to clipboard');
24718                });
24719
24720            });
24721        }
24722    },
24723    init: function init() {
24724        // Video player output
24725        var videoPlayer = document.getElementById('video-player');
24726
24727        if (videoPlayer) {
24728            var videoId = videoPlayer.dataset.video;
24729            var source = videoPlayer.dataset.source;
24730
24731            // Record the platform initially mounted so the format toggle can detect
24732            // same- vs cross-platform switches (see switchPlayer / currentSource).
24733            currentSource = source || (videoId.indexOf('youtube') > -1 ? 'youtube' : 'kaltura');
24734
24735            // Priority chain is resolved server-side; data-source tells us which
24736            // player to load. Fall back to the legacy youtube/kaltura detection
24737            // if data-source is somehow absent.
24738            if (source === 'youtube' || (!source && videoId.indexOf('youtube') > -1)) {
24739                // Loads the IFrame Player API code asynchronously.
24740                this.loadScript('https://www.youtube.com/iframe_api', this.onYouTubeIframeAPIReady);
24741            } else if (source === 'bunny') {
24742                // Bunny Stream player (iframe + Player.js for tracking)
24743                this.bunnySession();
24744            } else {
24745                // Kaltura Web Player
24746                // Utilizes the TV Studio Player (V7) in Kaltura Management Console (KMC)
24747                // https://developer.kaltura.com/player/web/getting-started-web
24748                var partnerId = '1529571';
24749                var playerId = '49927973';
24750                this.loadScript('https://cdnapisec.kaltura.com/p/' + partnerId + '/embedPlaykitJs/flavorId/861301/uiconf_id/' + playerId, this.kalturaSession);
24751            }
24752        }
24753
24754        this.playlists();
24755
24756        this.transcripts();
24757
24758        // Short/Long format toggle (platform-aware: YouTube / Bunny / Kaltura)
24759        this.loadFormats();
24760
24761        this.contentToggle();
24762    },
24763    finalize: function finalize() {
24764        // JavaScript to be fired on the home page, after the init JS
24765    },
24766});
24767
24768/* WEBPACK VAR INJECTION */}.call(__webpack_exports__, __webpack_require__(0)))
24769
24770/***/ }),
24771/* 46 */
24772/***/ (function(module, __webpack_exports__, __webpack_require__) {
24773
24774"use strict";
24775/* harmony import */ var __WEBPACK_IMPORTED_MODULE_0__util_playerLoader__ = __webpack_require__(4);
24776// import kaltura from 'kaltura-client';
24777
24778
24779/* harmony default export */ __webpack_exports__["a"] = ({
24780    loadScript: function loadScript(src, callback) {
24781        var loaded = false;
24782        var tag = document.createElement('script');
24783        var firstScriptTag = document.getElementsByTagName('script')[0];
24784        if (!firstScriptTag) {
24785            // when loaded in jest without jsdom setup it doesn't get any element.
24786            // In jest it doesn't really make sense to do anything, because no one is watching youtube in jest
24787            return;
24788        }
24789        firstScriptTag.parentNode.insertBefore(tag, firstScriptTag);
24790        tag.onload = function () {
24791            if (!loaded) {
24792                loaded = true;
24793                callback();
24794            }
24795        };
24796        tag.onreadystatechange = function () {
24797            if (!loaded && (this.readyState === 'complete' || this.readyState === 'loaded')) {
24798                loaded = true;
24799                callback();
24800            }
24801        };
24802        tag.src = src;
24803    },
24804    onYouTubeIframeAPIReady: function onYouTubeIframeAPIReady() {
24805        // This function creates an <iframe> (and YouTube player)
24806        // after the API code downloads.
24807
24808        // Video player output
24809        var player;
24810        var videoPlayer = document.getElementById('video-player');
24811        var videoUrl = videoPlayer.dataset.video;
24812
24813        // Get the video ID
24814        var regex = /(https?:\/\/)?((www\.)?(youtube(-nocookie)?|youtube.googleapis)\.com.*(v\/|v=|vi=|vi\/|e\/|embed\/|user\/.*\/u\/\d+\/)|youtu\.be\/)([_0-9a-z-]+)/i;
24815        var videoId = videoUrl.match(regex);
24816
24817        window.YT.ready(function () {
24818            player = new window.YT.Player(videoPlayer, { // eslint-disable-line no-undef
24819                height: '390',
24820                width: '640',
24821                videoId: videoId[7],
24822                playerVars: {
24823                    'playsinline': 1,
24824                    'autoplay': 1,
24825                    'controls': 0,
24826                    'disablekb': 1,
24827                    'fs': 0,
24828                    'loop': 1,
24829                    'modestbranding': 1,
24830                },
24831                events: {
24832                    'onReady': onPlayerReady,
24833                    onStateChange:
24834                        function (e) {
24835                            if (e.data === window.YT.PlayerState.ENDED) {
24836                                player.playVideo();
24837                            }
24838                        },
24839                },
24840            });
24841        });
24842
24843        // Called when the player's state changes
24844        // Available states: buffering, unstarted, cued, playing, paused, ended
24845        function onPlayerReady() {
24846            player.playVideo();
24847            player.mute();
24848        }
24849    },
24850    kalturaSession: function kalturaSession() {
24851        var partnerId = '1529571';
24852        var playerId = '49927973';
24853        var videoPlayer = document.getElementById('video-player');
24854        var videoId = videoPlayer.dataset.video;
24855
24856        // config options: https://developer.kaltura.com/player/web/configuration-web
24857        try {
24858            var kalturaPlayer = KalturaPlayer.setup({ // eslint-disable-line no-undef
24859                targetId: 'video-player',
24860                provider: {
24861                    partnerId: partnerId,
24862                    uiConfId: playerId,
24863                },
24864            });
24865            kalturaPlayer.loadMedia({ entryId: videoId });
24866        } catch (e) {
24867            console.error(e.message)
24868        }
24869    },
24870    init: function init() {
24871        // Video player output
24872        var videoPlayer = document.getElementById('video-player');
24873
24874        if (videoPlayer) {
24875            var videoId = videoPlayer.dataset.video;
24876            var source = videoPlayer.dataset.source;
24877            // data-source resolves the platform; fall back to legacy detection.
24878            if (source === 'youtube' || (!source && videoId.indexOf('youtube') > -1)) {
24879                // Loads the IFrame Player API code asynchronously.
24880                this.loadScript('https://www.youtube.com/iframe_api', this.onYouTubeIframeAPIReady);
24881            } else if (source === 'bunny') {
24882                // Bunny Stream player
24883                Object(__WEBPACK_IMPORTED_MODULE_0__util_playerLoader__["a" /* loadBunnyPlayer */])(videoPlayer, { background: false });
24884            } else {
24885                // Kaltura Web Player
24886                // Utilizes the TV Studio Player (V7) in Kaltura Management Console (KMC)
24887                // https://developer.kaltura.com/player/web/getting-started-web
24888                var partnerId = '1529571';
24889                var playerId = '49927973';
24890                this.loadScript('https://cdnapisec.kaltura.com/p/' + partnerId + '/embedPlaykitJs/uiconf_id/' + playerId, this.kalturaSession);
24891            }
24892        }
24893    },
24894    finalize: function finalize() {
24895        // JavaScript to be fired on the home page, after the init JS
24896    },
24897});
24898
24899
24900/***/ }),
24901/* 47 */
24902/***/ (function(module, exports) {
24903
24904// removed by extract-text-webpack-plugin
24905
24906/***/ })
24907/******/ ]);
24908//# sourceMappingURL=main.js.map

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