` elements it contains.
- *
- * That is the problem this mixin solves. After applying this mixin, your
- * component code has access to `this.distributedChildren`, whose `length`
- * will return the total number of all children distributed to your component
- * in the composed tree.
- *
- * Note: The latest Custom Elements API design calls for a new function,
- * `getAssignedNodes` that takes an optional `deep` parameter, that will solve
- * this problem at the API level.
- */
- var DistributedChildren = function (_base) {
- _inherits(DistributedChildren, _base);
-
- function DistributedChildren() {
- _classCallCheck(this, DistributedChildren);
-
- return _possibleConstructorReturn(this, (DistributedChildren.__proto__ || Object.getPrototypeOf(DistributedChildren)).apply(this, arguments));
- }
-
- _createClass(DistributedChildren, [{
- key: 'distributedChildren',
-
-
- /**
- * An in-order collection of distributed children, expanding any slot
- * elements. Like the standard children property, this skips text nodes.
- *
- * @type {HTMLElement[]}
- */
- get: function get() {
- return expandContentElements(this.children, false);
- }
-
- /**
- * An in-order collection of distributed child nodes, expanding any slot
- * elements. Like the standard childNodes property, this includes text
- * nodes.
- *
- * @type {Node[]}
- */
-
- }, {
- key: 'distributedChildNodes',
- get: function get() {
- return expandContentElements(this.childNodes, true);
- }
-
- /**
- * The concatenated text content of all distributed child nodes, expanding
- * any slot elements.
- *
- * @type {string}
- */
-
- }, {
- key: 'distributedTextContent',
- get: function get() {
- var strings = this.distributedChildNodes.map(function (child) {
- return child.textContent;
- });
- return strings.join('');
- }
- }]);
-
- return DistributedChildren;
- }(base);
-
- return DistributedChildren;
-};
-
-/*
- * Given a array of nodes, return a new array with any content elements expanded
- * to the nodes distributed to that content element. This rule is applied
- * recursively.
- *
- * If includeTextNodes is true, text nodes will be included, as in the
- * standard childNodes property; by default, this skips text nodes, like the
- * standard children property.
- */
-
-
-function expandContentElements(nodes, includeTextNodes) {
- var _ref;
-
- var expanded = Array.prototype.map.call(nodes, function (node) {
- // We want to see if the node is an instanceof HTMLSlotELement, but
- // that class won't exist if the browser that doesn't support native
- // Shadow DOM and if the Shadow DOM polyfill hasn't been loaded. Instead,
- // we do a simplistic check to see if the tag name is "slot".
- var isSlot = typeof HTMLSlotElement !== 'undefined' ? node instanceof HTMLSlotElement : node.localName === 'slot';
- if (isSlot) {
- // Use the nodes assigned to this node instead.
- var assignedNodes = node.assignedNodes({ flatten: true });
- return assignedNodes ? expandContentElements(assignedNodes, includeTextNodes) : [];
- } else if (node instanceof HTMLElement) {
- // Plain element; use as is.
- return [node];
- } else if (node instanceof Text && includeTextNodes) {
- // Text node.
- return [node];
- } else {
- // Comment, processing instruction, etc.; skip.
- return [];
- }
- });
- var flattened = (_ref = []).concat.apply(_ref, _toConsumableArray(expanded));
- return flattened;
-}
-
-},{}],10:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
-
-var _set = function set(object, property, value, receiver) { var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent !== null) { set(parent, property, value, receiver); } } else if ("value" in desc && desc.writable) { desc.value = value; } else { var setter = desc.set; if (setter !== undefined) { setter.call(receiver, value); } } return value; };
-
-var _get = function get(object, property, receiver) { if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { return get(parent, property, receiver); } } else if ("value" in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } };
-
-exports.default = mixin;
-
-var _createSymbol = require('./createSymbol');
-
-var _createSymbol2 = _interopRequireDefault(_createSymbol);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-// Symbols for private data members on an element.
-var selectedFractionSymbol = (0, _createSymbol2.default)('selectedFraction');
-
-/* Exported function extends a base class with FractionalSelection. */
-function mixin(base) {
-
- /**
- * Adds support for fractional selection: treating a selection as a real
- * number that combines an integer portion (an index into a list), and a
- * fraction (indicating how far of the way we are to the next or previous
- * item).
- *
- * This is useful in components that support incremental operations during
- * dragging and swiping. Example: a carousel component has several items, and the
- * currently selected item is item 3. The user begins swiping to the left,
- * moving towards selecting item 4. Halfway through this operation, the
- * fractional selection value is 3.5.
- *
- * This value permits communication between mixins like
- * [SwipeDirectionMixin](./SwipeDirectionMixin.md) and
- * [TrackpadDirectionMixin](./TrackpadDirectionMixin.md), which generate
- * fractional selection values, and mixins like
- * [SelectionAnimationMixin](./SelectionAnimationMixin.md), which can render
- * selection at a fractional value.
- */
- var FractionalSelection = function (_base) {
- _inherits(FractionalSelection, _base);
-
- function FractionalSelection() {
- _classCallCheck(this, FractionalSelection);
-
- return _possibleConstructorReturn(this, (FractionalSelection.__proto__ || Object.getPrototypeOf(FractionalSelection)).apply(this, arguments));
- }
-
- _createClass(FractionalSelection, [{
- key: 'connectedCallback',
- value: function connectedCallback() {
- if (_get(FractionalSelection.prototype.__proto__ || Object.getPrototypeOf(FractionalSelection.prototype), 'connectedCallback', this)) {
- _get(FractionalSelection.prototype.__proto__ || Object.getPrototypeOf(FractionalSelection.prototype), 'connectedCallback', this).call(this);
- }
- this.selectedFraction = 0;
- }
-
- /**
- * A fractional value indicating how far the user has currently advanced to
- * the next/previous item. E.g., a `selectedFraction` of 3.5 indicates the
- * user is halfway between items 3 and 4.
- *
- * @type {number}
- */
-
- }, {
- key: 'selectedFraction',
- get: function get() {
- return this[selectedFractionSymbol];
- },
- set: function set(value) {
- this[selectedFractionSymbol] = value;
- if ('selectedFraction' in base.prototype) {
- _set(FractionalSelection.prototype.__proto__ || Object.getPrototypeOf(FractionalSelection.prototype), 'selectedFraction', value, this);
- }
- var event = new CustomEvent('selected-fraction-changed');
- this.dispatchEvent(event);
- }
- }]);
-
- return FractionalSelection;
- }(base);
-
- return FractionalSelection;
-}
-
-mixin.helpers = {
-
- /*
- * Dampen a selection that goes past the beginning or end of a list. This is
- * generally used to produce a visual effect of tension as the user tries to
- * go further in a direction that has no more items.
- *
- * Example: suppose `itemCount` is 5, indicating a list of 5 items. The index of
- * the last item is 4. If the `selection` parameter is 4.5, the user is trying
- * to go past this last item. When a damping function is applied, the resulting
- * value will be less than 4.5 (the actual value will be 4.25). When this
- * selection state is rendered, the user will see that, each unit distance the
- * drag travels has less and less visible effect. This is perceived as tension.
- *
- * @param {number} selection - A real number indicating a selection position
- * @param {number} itemCount - An integer for the number of items in the list
- * @returns {number} A real number representing the damped selection value.
- */
- dampedSelection: function dampedSelection(selection, itemCount) {
- var bound = itemCount - 1;
- var damped = void 0;
- if (selection < 0) {
- // Trying to go past beginning of list. Apply tension from the left edge.
- damped = -mixin.helpers.damping(-selection);
- } else if (selection >= bound) {
- // Trying to go past end of list. Apply tension from the right edge.
- damped = bound + mixin.helpers.damping(selection - bound);
- } else {
- // No damping required.
- damped = selection;
- }
- return damped;
- },
-
-
- /*
- * Calculate damping as a function of the distance past the minimum/maximum
- * values.
- *
- * We want to asymptotically approach an absolute minimum of 1 unit
- * below/above the actual minimum/maximum. This requires calculating a
- * hyperbolic function.
- *
- * See http://www.wolframalpha.com/input/?i=y+%3D+-1%2F%28x%2B1%29+%2B+1
- * for the one we use. The only portion of that function we care about is when
- * x is zero or greater. An important consideration is that the curve be
- * tangent to the diagonal line x=y at (0, 0). This ensures smooth continuity
- * with the normal drag behavior, in which the visible sliding is linear with
- * the distance the touchpoint has been dragged.
- */
- damping: function damping(x) {
- var y = -1 / (x + 1) + 1;
- return y;
- },
-
-
- /*
- * Return the current fractional selection value for the given element.
- *
- * This simply adds the element's `selectedIndex` and `selectedFraction`
- * properties.
- *
- * @param {HTMLElement} element - An element that supports selection
- */
- elementSelection: function elementSelection(element) {
- var selectedIndex = element.selectedIndex;
- if (selectedIndex < 0) {
- // No selection
- return;
- }
- var selectedFraction = element.selectedFraction || 0;
- return selectedIndex + selectedFraction;
- },
-
-
- /*
- * Breaks a fractional selection into its integer and fractional parts.
- *
- * Example: if passed 3.5, this returns { index: 3, fraction: 5 }.
- *
- * @param {number} selection – A real number representing a selection point
- * @returns {object} - An object with an `index` property holding the
- * selection's integer component, and a `fraction` property holding the
- * selection's fractional component.
- */
- selectionParts: function selectionParts(selection) {
- // Stupid IE doesn't have Math.trunc.
- // const index = Math.trunc(selection);
- var index = selection < 0 ? Math.ceil(selection) : Math.floor(selection);
- var fraction = selection - index;
- return { index: index, fraction: fraction };
- },
-
-
- /*
- * Returns a fractional selection point after accounting for wrapping, ensuring
- * that the integer portion of the selection stays between 0 and `itemCount`-1.
- * That is, the integer portion will always be a valid index into the list.
- *
- * Example of wrapping past the end of the list: if `selection` is 5.5 and
- * `itemCount` is 5, this returns 0.5. Example of wrapping past the beginning of
- * the list: if `selection` is 0.5 and `itemCount` is 5, this returns 4.5.
- *
- * @param {number} selection - A real number representing a selection point
- * @param {number} itemCount - The number of items in the list
- * @returns {number} - The result of wrapping the selection point
- */
- wrappedSelection: function wrappedSelection(selection, itemCount) {
- // Handles possibility of negative mod.
- // See http://stackoverflow.com/a/18618250/76472
- return (selection % itemCount + itemCount) % itemCount;
- },
-
-
- /*
- * Return the parts of a selection, first wrapping if necessary.
- *
- * @param {number} selection – A real number representing a selection point
- * @param {number} itemCount - The number of items in the list
- * @param {boolean} wrap – True if the selection should wrap to stay within the
- * list
- * @returns {object} – The parts of the selection, using the same format as
- * `selectionParts`.
- */
- wrappedSelectionParts: function wrappedSelectionParts(selection, itemCount, wrap) {
- if (wrap) {
- selection = mixin.helpers.wrappedSelection(selection, itemCount);
- }
- return mixin.helpers.selectionParts(selection);
- }
-};
-
-},{"./createSymbol":28}],11:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
-
-var _set = function set(object, property, value, receiver) { var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent !== null) { set(parent, property, value, receiver); } } else if ("value" in desc && desc.writable) { desc.value = value; } else { var setter = desc.set; if (setter !== undefined) { setter.call(receiver, value); } } return value; };
-
-var _get = function get(object, property, receiver) { if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { return get(parent, property, receiver); } } else if ("value" in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } };
-
-var _createSymbol = require('./createSymbol');
-
-var _createSymbol2 = _interopRequireDefault(_createSymbol);
-
-var _safeAttributes = require('./safeAttributes');
-
-var _safeAttributes2 = _interopRequireDefault(_safeAttributes);
-
-var _symbols = require('./symbols');
-
-var _symbols2 = _interopRequireDefault(_symbols);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-// Symbols for private data members on an element.
-var genericSymbol = (0, _createSymbol2.default)('generic');
-
-/* Exported function extends a base class with Generic. */
-
-exports.default = function (base) {
-
- /**
- * Mixin which allows a component to support a "generic" style: a minimalist
- * style that can easily be removed to reset its visual appearance to a
- * baseline state.
- *
- * By default, a component should provide a minimal visual presentation that
- * allows the component to function. However, the more styling the component
- * provides by default, the harder it becomes to get the component to fit in
- * in other settings. Each CSS rule has to be overridden. Worse, new CSS rules
- * added to the default style won't be overridden by default, making it hard
- * to know whether a new version of a component will still look okay.
- *
- * As a compromise, the mixin defines a `generic` attribute. This attribute is
- * normally set by default, and styles can be written that apply only when the
- * generic attribute is set. This allows the construction of CSS rules that
- * will only apply to generic components like:
- *
- * :host([generic=""]) {
- * ... generic appearance defined here ...
- * }
- *
- * This makes it easy to remove all default styling — set the `GenericMixin`
- * attribute to false, and all default styling will be removed.
- */
- var Generic = function (_base) {
- _inherits(Generic, _base);
-
- function Generic() {
- _classCallCheck(this, Generic);
-
- // Set defaults.
- var _this = _possibleConstructorReturn(this, (Generic.__proto__ || Object.getPrototypeOf(Generic)).call(this));
-
- if (typeof _this.generic === 'undefined') {
- _this.generic = _this[_symbols2.default.defaults].generic;
- }
- return _this;
- }
-
- // This mixin doesn't actually respond to attribute changes, but relies
- // on separately-defined behavior (e.g., in AttributeMarshallingMixin) for that.
- // Still, we need define a baseline attributeChangedCallback that does
- // nothing, in case this mixin gets used on its own.
-
-
- _createClass(Generic, [{
- key: 'attributeChangedCallback',
- value: function attributeChangedCallback(name, oldValue, newValue) {
- if (_get(Generic.prototype.__proto__ || Object.getPrototypeOf(Generic.prototype), 'attributeChangedCallback', this)) {
- _get(Generic.prototype.__proto__ || Object.getPrototypeOf(Generic.prototype), 'attributeChangedCallback', this).call(this, name, oldValue, newValue);
- }
- }
- }, {
- key: 'connectedCallback',
- value: function connectedCallback() {
- if (_get(Generic.prototype.__proto__ || Object.getPrototypeOf(Generic.prototype), 'connectedCallback', this)) {
- _get(Generic.prototype.__proto__ || Object.getPrototypeOf(Generic.prototype), 'connectedCallback', this).call(this);
- }
- _safeAttributes2.default.connected(this);
- }
- }, {
- key: _symbols2.default.defaults,
- get: function get() {
- var defaults = _get(Generic.prototype.__proto__ || Object.getPrototypeOf(Generic.prototype), _symbols2.default.defaults, this) || {};
- defaults.generic = true;
- return defaults;
- }
-
- /**
- * True if the component would like to receive generic styling.
- *
- * This property is true by default — set it to false to turn off all
- * generic styles. This makes it easier to apply custom styling; you won't
- * have to explicitly override styling you don't want.
- *
- * @type Boolean
- * @default true
- */
-
- }, {
- key: 'generic',
- get: function get() {
- return this[genericSymbol];
- },
- set: function set(value) {
- var parsed = typeof value === 'string' ? String(value) !== 'false' : value;
- this[genericSymbol] = parsed;
-
- if ('generic' in base.prototype) {
- _set(Generic.prototype.__proto__ || Object.getPrototypeOf(Generic.prototype), 'generic', value, this);
- }
-
- // We roll our own attribute setting so that an explicitly false value
- // shows up as GenericMixin="false".
- if (parsed === false) {
- // Explicitly use false string.
- _safeAttributes2.default.setAttribute(this, 'generic', 'false');
- } else if (parsed == null) {
- // Explicitly remove attribute. (Always safe to do this.)
- this.removeAttribute('generic');
- } else {
- // Use the empty string to get attribute to appear with no value.
- _safeAttributes2.default.setAttribute(this, 'generic', '');
- }
- }
- }]);
-
- return Generic;
- }(base);
-
- return Generic;
-};
-
-},{"./createSymbol":28,"./safeAttributes":31,"./symbols":32}],12:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
-
-var _set = function set(object, property, value, receiver) { var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent !== null) { set(parent, property, value, receiver); } } else if ("value" in desc && desc.writable) { desc.value = value; } else { var setter = desc.set; if (setter !== undefined) { setter.call(receiver, value); } } return value; };
-
-var _get = function get(object, property, receiver) { if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { return get(parent, property, receiver); } } else if ("value" in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } };
-
-var _createSymbol = require('./createSymbol');
-
-var _createSymbol2 = _interopRequireDefault(_createSymbol);
-
-var _symbols = require('./symbols');
-
-var _symbols2 = _interopRequireDefault(_symbols);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-// Symbols for private data members on an element.
-var navigationAxisSymbol = (0, _createSymbol2.default)('navigationAxis');
-
-/* Exported function extends a base class with KeyboardDirection. */
-
-exports.default = function (base) {
-
- /**
- * Mixin which maps direction keys (Left, Right, etc.) to direction semantics
- * (go left, go right, etc.).
- *
- * This mixin expects the component to invoke a `keydown` method when a key is
- * pressed. You can use [KeyboardMixin](KeyboardMixin.md) for that
- * purpose, or wire up your own keyboard handling and call `keydown` yourself.
- *
- * This mixin calls methods such as `goLeft` and `goRight`. You can define
- * what that means by implementing those methods yourself. If you want to use
- * direction keys to navigate a selection, use this mixin with
- * [DirectionSelectionMixin](DirectionSelectionMixin.md).
- */
- var KeyboardDirection = function (_base) {
- _inherits(KeyboardDirection, _base);
-
- function KeyboardDirection() {
- _classCallCheck(this, KeyboardDirection);
-
- // Set defaults.
- var _this = _possibleConstructorReturn(this, (KeyboardDirection.__proto__ || Object.getPrototypeOf(KeyboardDirection)).call(this));
-
- if (typeof _this.navigationAxis === 'undefined') {
- _this.navigationAxis = _this[_symbols2.default.defaults].navigationAxis;
- }
- return _this;
- }
-
- _createClass(KeyboardDirection, [{
- key: _symbols2.default.goDown,
-
-
- /**
- * Invoked when the user wants to go/navigate down.
- * The default implementation of this method does nothing.
- */
- value: function value() {
- if (_get(KeyboardDirection.prototype.__proto__ || Object.getPrototypeOf(KeyboardDirection.prototype), _symbols2.default.goDown, this)) {
- return _get(KeyboardDirection.prototype.__proto__ || Object.getPrototypeOf(KeyboardDirection.prototype), _symbols2.default.goDown, this).call(this);
- }
- }
-
- /**
- * Invoked when the user wants to go/navigate to the end (e.g., of a list).
- * The default implementation of this method does nothing.
- */
-
- }, {
- key: _symbols2.default.goEnd,
- value: function value() {
- if (_get(KeyboardDirection.prototype.__proto__ || Object.getPrototypeOf(KeyboardDirection.prototype), _symbols2.default.goEnd, this)) {
- return _get(KeyboardDirection.prototype.__proto__ || Object.getPrototypeOf(KeyboardDirection.prototype), _symbols2.default.goEnd, this).call(this);
- }
- }
-
- /**
- * Invoked when the user wants to go/navigate left.
- * The default implementation of this method does nothing.
- */
-
- }, {
- key: _symbols2.default.goLeft,
- value: function value() {
- if (_get(KeyboardDirection.prototype.__proto__ || Object.getPrototypeOf(KeyboardDirection.prototype), _symbols2.default.goLeft, this)) {
- return _get(KeyboardDirection.prototype.__proto__ || Object.getPrototypeOf(KeyboardDirection.prototype), _symbols2.default.goLeft, this).call(this);
- }
- }
-
- /**
- * Invoked when the user wants to go/navigate right.
- * The default implementation of this method does nothing.
- */
-
- }, {
- key: _symbols2.default.goRight,
- value: function value() {
- if (_get(KeyboardDirection.prototype.__proto__ || Object.getPrototypeOf(KeyboardDirection.prototype), _symbols2.default.goRight, this)) {
- return _get(KeyboardDirection.prototype.__proto__ || Object.getPrototypeOf(KeyboardDirection.prototype), _symbols2.default.goRight, this).call(this);
- }
- }
-
- /**
- * Invoked when the user wants to go/navigate to the start (e.g., of a
- * list). The default implementation of this method does nothing.
- */
-
- }, {
- key: _symbols2.default.goStart,
- value: function value() {
- if (_get(KeyboardDirection.prototype.__proto__ || Object.getPrototypeOf(KeyboardDirection.prototype), _symbols2.default.goStart, this)) {
- return _get(KeyboardDirection.prototype.__proto__ || Object.getPrototypeOf(KeyboardDirection.prototype), _symbols2.default.goStart, this).call(this);
- }
- }
-
- /**
- * Invoked when the user wants to go/navigate up.
- * The default implementation of this method does nothing.
- */
-
- }, {
- key: _symbols2.default.goUp,
- value: function value() {
- if (_get(KeyboardDirection.prototype.__proto__ || Object.getPrototypeOf(KeyboardDirection.prototype), _symbols2.default.goUp, this)) {
- return _get(KeyboardDirection.prototype.__proto__ || Object.getPrototypeOf(KeyboardDirection.prototype), _symbols2.default.goUp, this).call(this);
- }
- }
-
- /**
- * Indicates the direction of permitted navigation with the keyboard.
- *
- * Accepted values are "horizontal", "vertical", or "both" (the default).
- * If this property is "horizontal", the Up Arrow and Down Arrow keys will
- * be ignored. Conversely, if this is "vertical", the Left Arrow and Right
- * Arrow keys will be ignored.
- *
- * @type {string}
- */
-
- }, {
- key: _symbols2.default.keydown,
- value: function value(event) {
- var handled = void 0;
-
- var axis = this.navigationAxis;
- var horizontal = axis === 'horizontal' || axis === 'both';
- var vertical = axis === 'vertical' || axis === 'both';
-
- // Ignore Left/Right keys when metaKey or altKey modifier is also pressed,
- // as the user may be trying to navigate back or forward in the browser.
- switch (event.keyCode) {
- case 35:
- // End
- handled = this[_symbols2.default.goEnd]();
- break;
- case 36:
- // Home
- handled = this[_symbols2.default.goStart]();
- break;
- case 37:
- // Left
- if (horizontal && !event.metaKey && !event.altKey) {
- handled = this[_symbols2.default.goLeft]();
- }
- break;
- case 38:
- // Up
- if (vertical) {
- handled = event.altKey ? this[_symbols2.default.goStart]() : this[_symbols2.default.goUp]();
- }
- break;
- case 39:
- // Right
- if (horizontal && !event.metaKey && !event.altKey) {
- handled = this[_symbols2.default.goRight]();
- }
- break;
- case 40:
- // Down
- if (vertical) {
- handled = event.altKey ? this[_symbols2.default.goEnd]() : this[_symbols2.default.goDown]();
- }
- break;
- }
- // Prefer mixin result if it's defined, otherwise use base result.
- return handled || _get(KeyboardDirection.prototype.__proto__ || Object.getPrototypeOf(KeyboardDirection.prototype), _symbols2.default.keydown, this) && _get(KeyboardDirection.prototype.__proto__ || Object.getPrototypeOf(KeyboardDirection.prototype), _symbols2.default.keydown, this).call(this, event);
- }
- }, {
- key: _symbols2.default.defaults,
- get: function get() {
- var defaults = _get(KeyboardDirection.prototype.__proto__ || Object.getPrototypeOf(KeyboardDirection.prototype), _symbols2.default.defaults, this) || {};
- defaults.navigationAxis = 'both';
- return defaults;
- }
- }, {
- key: 'navigationAxis',
- get: function get() {
- return this[navigationAxisSymbol];
- },
- set: function set(value) {
- this[navigationAxisSymbol] = value;
- if ('navigationAxis' in base.prototype) {
- _set(KeyboardDirection.prototype.__proto__ || Object.getPrototypeOf(KeyboardDirection.prototype), 'navigationAxis', value, this);
- }
- }
- }]);
-
- return KeyboardDirection;
- }(base);
-
- return KeyboardDirection;
-};
-
-},{"./createSymbol":28,"./symbols":32}],13:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
-
-var _get = function get(object, property, receiver) { if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { return get(parent, property, receiver); } } else if ("value" in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } };
-
-var _symbols = require('./symbols');
-
-var _symbols2 = _interopRequireDefault(_symbols);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-/* Exported function extends a base class with Keyboard. */
-exports.default = function (base) {
-
- /**
- * Mixin which manages the keydown handling for a component.
- *
- * This mixin handles several keyboard-related features.
- *
- * First, it wires up a single keydown event handler that can be shared by
- * multiple mixins on a component. The event handler will invoke a `keydown`
- * method with the event object, and any mixin along the prototype chain that
- * wants to handle that method can do so.
- *
- * If a mixin wants to indicate that keyboard event has been handled, and that
- * other mixins should *not* handle it, the mixin's `keydown` handler should
- * return a value of true. The convention that seems to work well is that a
- * mixin should see if it wants to handle the event and, if not, then ask the
- * superclass to see if it wants to handle the event. This has the effect of
- * giving the mixin that was applied last the first chance at handling a
- * keyboard event.
- *
- * Example:
- *
- * [symbols.keydown](event) {
- * let handled;
- * switch (event.keyCode) {
- * // Handle the keys you want, setting handled = true if appropriate.
- * }
- * // Prefer mixin result if it's defined, otherwise use base result.
- * return handled || (super[symbols.keydown] && super[symbols.keydown](event));
- * }
- *
- * A second feature provided by this mixin is that it implicitly makes the
- * component a tab stop if it isn't already, by setting `tabIndex` to 0. This
- * has the effect of adding the component to the tab order in document order.
- */
- var Keyboard = function (_base) {
- _inherits(Keyboard, _base);
-
- function Keyboard() {
- _classCallCheck(this, Keyboard);
-
- var _this = _possibleConstructorReturn(this, (Keyboard.__proto__ || Object.getPrototypeOf(Keyboard)).call(this));
-
- _this.addEventListener('keydown', function (event) {
- var handled = _this[_symbols2.default.keydown](event);
- if (handled) {
- event.preventDefault();
- event.stopPropagation();
- }
- });
- return _this;
- }
-
- _createClass(Keyboard, [{
- key: 'connectedCallback',
- value: function connectedCallback() {
- if (_get(Keyboard.prototype.__proto__ || Object.getPrototypeOf(Keyboard.prototype), 'connectedCallback', this)) {
- _get(Keyboard.prototype.__proto__ || Object.getPrototypeOf(Keyboard.prototype), 'connectedCallback', this).call(this);
- }
- if (this.getAttribute('tabindex') == null && this[_symbols2.default.defaults].tabindex !== null) {
- this.setAttribute('tabindex', this[_symbols2.default.defaults].tabindex);
- }
- }
- }, {
- key: _symbols2.default.keydown,
-
-
- /**
- * Handle the indicated keyboard event.
- *
- * The default implementation of this method does nothing. This will
- * typically be handled by other mixins.
- *
- * @param {KeyboardEvent} event - the keyboard event
- * @return {boolean} true if the event was handled
- */
- value: function value(event) {
- if (_get(Keyboard.prototype.__proto__ || Object.getPrototypeOf(Keyboard.prototype), _symbols2.default.keydown, this)) {
- return _get(Keyboard.prototype.__proto__ || Object.getPrototypeOf(Keyboard.prototype), _symbols2.default.keydown, this).call(this, event);
- }
- }
- }, {
- key: _symbols2.default.defaults,
- get: function get() {
- var defaults = _get(Keyboard.prototype.__proto__ || Object.getPrototypeOf(Keyboard.prototype), _symbols2.default.defaults, this) || {};
- // The default tab index is 0 (document order).
- defaults.tabindex = 0;
- return defaults;
- }
- }]);
-
- return Keyboard;
- }(base);
-
- return Keyboard;
-};
-
-},{"./symbols":32}],14:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
-
-var _set = function set(object, property, value, receiver) { var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent !== null) { set(parent, property, value, receiver); } } else if ("value" in desc && desc.writable) { desc.value = value; } else { var setter = desc.set; if (setter !== undefined) { setter.call(receiver, value); } } return value; };
-
-var _get = function get(object, property, receiver) { if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { return get(parent, property, receiver); } } else if ("value" in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } };
-
-var _symbols = require('./symbols');
-
-var _symbols2 = _interopRequireDefault(_symbols);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-/* Exported function extends a base class with KeyboardPagedSelection. */
-exports.default = function (base) {
-
- /**
- * Mixin which maps page keys (Page Up, Page Down) into operations that move
- * the selection by one page.
- *
- * The keyboard interaction model generally follows that of Microsoft Windows'
- * list boxes instead of those in OS X:
- *
- * * The Page Up/Down and Home/End keys actually change the selection, rather
- * than just scrolling. The former behavior seems more generally useful for
- * keyboard users.
- *
- * * Pressing Page Up/Down will change the selection to the topmost/bottommost
- * visible item if the selection is not already there. Thereafter, the key
- * will move the selection up/down by a page, and (per the above point) make
- * the selected item visible.
- *
- * To ensure the selected item is in view following use of Page Up/Down, use
- * the related [SelectionInViewMixin](SelectionInViewMixin.md).
- *
- * This mixin expects the component to invoke a `keydown` method when a key is
- * pressed. You can use [KeyboardMixin](KeyboardMixin.md) for that
- * purpose, or wire up your own keyboard handling and call `keydown` yourself.
- */
- var KeyboardPagedSelection = function (_base) {
- _inherits(KeyboardPagedSelection, _base);
-
- function KeyboardPagedSelection() {
- _classCallCheck(this, KeyboardPagedSelection);
-
- return _possibleConstructorReturn(this, (KeyboardPagedSelection.__proto__ || Object.getPrototypeOf(KeyboardPagedSelection)).apply(this, arguments));
- }
-
- _createClass(KeyboardPagedSelection, [{
- key: _symbols2.default.keydown,
- value: function value(event) {
- var handled = void 0;
- switch (event.keyCode) {
- case 33:
- // Page Up
- handled = this.pageUp();
- break;
- case 34:
- // Page Down
- handled = this.pageDown();
- break;
- }
- // Prefer mixin result if it's defined, otherwise use base result.
- return handled || _get(KeyboardPagedSelection.prototype.__proto__ || Object.getPrototypeOf(KeyboardPagedSelection.prototype), _symbols2.default.keydown, this) && _get(KeyboardPagedSelection.prototype.__proto__ || Object.getPrototypeOf(KeyboardPagedSelection.prototype), _symbols2.default.keydown, this).call(this, event);
- }
-
- /**
- * Scroll down one page.
- */
-
- }, {
- key: 'pageDown',
- value: function pageDown() {
- if (_get(KeyboardPagedSelection.prototype.__proto__ || Object.getPrototypeOf(KeyboardPagedSelection.prototype), 'pageDown', this)) {
- _get(KeyboardPagedSelection.prototype.__proto__ || Object.getPrototypeOf(KeyboardPagedSelection.prototype), 'pageDown', this).call(this);
- }
- return scrollOnePage(this, true);
- }
-
- /**
- * Scroll up one page.
- */
-
- }, {
- key: 'pageUp',
- value: function pageUp() {
- if (_get(KeyboardPagedSelection.prototype.__proto__ || Object.getPrototypeOf(KeyboardPagedSelection.prototype), 'pageUp', this)) {
- _get(KeyboardPagedSelection.prototype.__proto__ || Object.getPrototypeOf(KeyboardPagedSelection.prototype), 'pageUp', this).call(this);
- }
- return scrollOnePage(this, false);
- }
-
- /**
- * The element that should be scrolled with the Page Up/Down keys.
- * Default is the current element.
- *
- * @type {HTMLElement}
- */
-
- }, {
- key: 'scrollTarget',
- get: function get() {
- // Prefer base result.
- return 'scrollTarget' in base.prototype ? _get(KeyboardPagedSelection.prototype.__proto__ || Object.getPrototypeOf(KeyboardPagedSelection.prototype), 'scrollTarget', this) : this;
- },
- set: function set(element) {
- if ('scrollTarget' in base.prototype) {
- _set(KeyboardPagedSelection.prototype.__proto__ || Object.getPrototypeOf(KeyboardPagedSelection.prototype), 'scrollTarget', element, this);
- }
- }
- }]);
-
- return KeyboardPagedSelection;
- }(base);
-
- return KeyboardPagedSelection;
-};
-
-// Return the item whose content spans the given y position (relative to the
-// top of the list's scrolling client area), or null if not found.
-//
-// If downward is true, move down the list of items to find the first item
-// found at the given y position; if downward is false, move up the list of
-// items to find the last item at that position.
-
-
-function getIndexOfItemAtY(element, y, downward) {
- var items = element.items;
- var start = downward ? 0 : items.length - 1;
- var end = downward ? items.length : 0;
- var step = downward ? 1 : -1;
- var scrollTarget = element.scrollTarget;
- var topOfClientArea = scrollTarget.offsetTop + scrollTarget.clientTop;
-
- // Find the item spanning the indicated y coordinate.
- var item = void 0;
- var itemIndex = start;
- var itemTop = void 0;
- var found = false;
- while (itemIndex !== end) {
- item = items[itemIndex];
- itemTop = item.offsetTop - topOfClientArea;
- var itemBottom = itemTop + item.offsetHeight;
- if (itemTop <= y && itemBottom >= y) {
- // Item spans the indicated y coordinate.
- found = true;
- break;
- }
- itemIndex += step;
- }
-
- if (!found) {
- return null;
- }
-
- // We may have found an item whose padding spans the given y coordinate,
- // but whose content is actually above/below that point.
- // TODO: If the item has a border, then padding should be included in
- // considering a hit.
- var itemStyle = getComputedStyle(item);
- var itemPaddingTop = parseFloat(itemStyle.paddingTop);
- var itemPaddingBottom = parseFloat(itemStyle.paddingBottom);
- var contentTop = itemTop + item.clientTop + itemPaddingTop;
- var contentBottom = contentTop + item.clientHeight - itemPaddingTop - itemPaddingBottom;
- if (downward && contentTop <= y || !downward && contentBottom >= y) {
- // The indicated coordinate hits the actual item content.
- return itemIndex;
- } else {
- // The indicated coordinate falls within the item's padding. Back up to
- // the item below/above the item we found and return that.
- return itemIndex - step;
- }
-}
-
-// Move by one page downward (if downward is true), or upward (if false).
-// Return true if we ended up changing the selection, false if not.
-// TODO: Better support for horizontal lists.
-function scrollOnePage(element, downward) {
-
- // Determine the item visible just at the edge of direction we're heading.
- // We'll select that item if it's not already selected.
- var scrollTarget = element.scrollTarget;
- var edge = scrollTarget.scrollTop + (downward ? scrollTarget.clientHeight : 0);
- var indexOfItemAtEdge = getIndexOfItemAtY(element, edge, downward);
-
- var selectedIndex = element.selectedIndex;
- var newIndex = void 0;
- if (indexOfItemAtEdge && selectedIndex === indexOfItemAtEdge) {
- // The item at the edge was already selected, so scroll in the indicated
- // direction by one page. Leave the new item at that edge selected.
- var delta = (downward ? 1 : -1) * scrollTarget.clientHeight;
- newIndex = getIndexOfItemAtY(element, edge + delta, downward);
- } else {
- // The item at the edge wasn't selected yet. Instead of scrolling, we'll
- // just select that item. That is, the first attempt to page up/down
- // usually just moves the selection to the edge in that direction.
- newIndex = indexOfItemAtEdge;
- }
-
- if (!newIndex) {
- // We can't find an item in the direction we want to travel. Select the
- // last item (if moving downward) or first item (if moving upward).
- newIndex = downward ? element.items.length - 1 : 0;
- }
-
- if (newIndex !== selectedIndex) {
- element.selectedIndex = newIndex;
- return true; // We handled the page up/down ourselves.
- } else {
- return false; // We didn't do anything.
- }
-}
-
-},{"./symbols":32}],15:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
-
-var _get = function get(object, property, receiver) { if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { return get(parent, property, receiver); } } else if ("value" in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } };
-
-var _createSymbol = require('./createSymbol');
-
-var _createSymbol2 = _interopRequireDefault(_createSymbol);
-
-var _symbols = require('./symbols');
-
-var _symbols2 = _interopRequireDefault(_symbols);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-// Symbols for private data members on an element.
-var itemTextContentsSymbol = (0, _createSymbol2.default)('itemTextContents');
-var typedPrefixSymbol = (0, _createSymbol2.default)('typedPrefix');
-var prefixTimeoutSymbol = (0, _createSymbol2.default)('prefixTimeout');
-
-/* Exported function extends a base class with KeyboardPrefixSelection. */
-
-exports.default = function (base) {
-
- /**
- * Mixin that handles list box-style prefix typing, in which the user can type
- * a string to select the first item that begins with that string.
- *
- * Example: suppose a component using this mixin has the following items:
- *
- *
- * Apple
- * Apricot
- * Banana
- * Blackberry
- * Blueberry
- * Cantaloupe
- * Cherry
- * Lemon
- * Lime
- *
- *
- * If this component receives the focus, and the user presses the "b" or "B"
- * key, the "Banana" item will be selected, because it's the first item that
- * matches the prefix "b". (Matching is case-insensitive.) If the user now
- * presses the "l" or "L" key quickly, the prefix to match becomes "bl", so
- * "Blackberry" will be selected.
- *
- * The prefix typing feature has a one second timeout — the prefix to match
- * will be reset after a second has passed since the user last typed a key.
- * If, in the above example, the user waits a second between typing "b" and
- * "l", the prefix will become "l", so "Lemon" would be selected.
- *
- * This mixin expects the component to invoke a `keydown` method when a key is
- * pressed. You can use [KeyboardMixin](KeyboardMixin.md) for that
- * purpose, or wire up your own keyboard handling and call `keydown` yourself.
- *
- * This mixin also expects the component to provide an `items` property. The
- * `textContent` of those items will be used for purposes of prefix matching.
- */
- var KeyboardPrefixSelection = function (_base) {
- _inherits(KeyboardPrefixSelection, _base);
-
- function KeyboardPrefixSelection() {
- _classCallCheck(this, KeyboardPrefixSelection);
-
- return _possibleConstructorReturn(this, (KeyboardPrefixSelection.__proto__ || Object.getPrototypeOf(KeyboardPrefixSelection)).apply(this, arguments));
- }
-
- _createClass(KeyboardPrefixSelection, [{
- key: _symbols2.default.keydown,
-
-
- // TODO: If the set of items is changed, reset the prefix.
- // [symbols.itemsChanged]() {
- // this[itemTextContentsSymbol] = null;
- // resetTypedPrefix(this);
- // }
-
- // TODO: If the selection is changed by some other means (e.g., arrow keys)
- // other than prefix typing, then that act should reset the prefix.
-
- value: function value(event) {
- var handled = void 0;
- var resetPrefix = true;
-
- switch (event.keyCode) {
- case 8:
- // Backspace
- handleBackspace(this);
- handled = true;
- resetPrefix = false;
- break;
- case 27:
- // Escape
- handled = true;
- break;
- default:
- if (!event.ctrlKey && !event.metaKey && !event.altKey && event.which !== 32 /* Space */) {
- handlePlainCharacter(this, String.fromCharCode(event.which));
- }
- resetPrefix = false;
- }
-
- if (resetPrefix) {
- resetTypedPrefix(this);
- }
-
- // Prefer mixin result if it's defined, otherwise use base result.
- return handled || _get(KeyboardPrefixSelection.prototype.__proto__ || Object.getPrototypeOf(KeyboardPrefixSelection.prototype), _symbols2.default.keydown, this) && _get(KeyboardPrefixSelection.prototype.__proto__ || Object.getPrototypeOf(KeyboardPrefixSelection.prototype), _symbols2.default.keydown, this).call(this, event);
- }
-
- /**
- * Select the first item whose text content begins with the given prefix.
- *
- * @param prefix [String] The prefix string to search for
- */
-
- }, {
- key: 'selectItemWithTextPrefix',
- value: function selectItemWithTextPrefix(prefix) {
- if (_get(KeyboardPrefixSelection.prototype.__proto__ || Object.getPrototypeOf(KeyboardPrefixSelection.prototype), 'selectItemWithTextPrefix', this)) {
- _get(KeyboardPrefixSelection.prototype.__proto__ || Object.getPrototypeOf(KeyboardPrefixSelection.prototype), 'selectItemWithTextPrefix', this).call(this, prefix);
- }
- if (prefix == null || prefix.length === 0) {
- return;
- }
- var index = getIndexOfItemWithTextPrefix(this, prefix);
- if (index >= 0) {
- this.selectedIndex = index;
- }
- }
- }]);
-
- return KeyboardPrefixSelection;
- }(base);
-
- return KeyboardPrefixSelection;
-};
-
-// Time in milliseconds after which the user is considered to have stopped
-// typing.
-
-
-var PREFIX_TIMEOUT_DURATION = 1000;
-
-// Return the index of the first item with the given prefix, else -1.
-function getIndexOfItemWithTextPrefix(element, prefix) {
- var itemTextContents = getItemTextContents(element);
- var prefixLength = prefix.length;
- for (var i = 0; i < itemTextContents.length; i++) {
- var itemTextContent = itemTextContents[i];
- if (itemTextContent.substr(0, prefixLength) === prefix) {
- return i;
- }
- }
- return -1;
-}
-
-// Return an array of the text content (in lowercase) of all items.
-// Cache these results.
-function getItemTextContents(element) {
- if (!element[itemTextContentsSymbol]) {
- var items = element.items;
- element[itemTextContentsSymbol] = items.map(function (child) {
- var text = child.textContent || child.alt;
- return text.toLowerCase();
- });
- }
- return element[itemTextContentsSymbol];
-}
-
-function handleBackspace(element) {
- var length = element[typedPrefixSymbol] ? element[typedPrefixSymbol].length : 0;
- if (length > 0) {
- element[typedPrefixSymbol] = element[typedPrefixSymbol].substr(0, length - 1);
- }
- element.selectItemWithTextPrefix(element[typedPrefixSymbol]);
- setPrefixTimeout(element);
-}
-
-function handlePlainCharacter(element, char) {
- var prefix = element[typedPrefixSymbol] || '';
- element[typedPrefixSymbol] = prefix + char.toLowerCase();
- element.selectItemWithTextPrefix(element[typedPrefixSymbol]);
- setPrefixTimeout(element);
-}
-
-function resetPrefixTimeout(element) {
- if (element[prefixTimeoutSymbol]) {
- clearTimeout(element[prefixTimeoutSymbol]);
- element[prefixTimeoutSymbol] = false;
- }
-}
-
-function resetTypedPrefix(element) {
- element[typedPrefixSymbol] = '';
- resetPrefixTimeout(element);
-}
-
-function setPrefixTimeout(element) {
- resetPrefixTimeout(element);
- element[prefixTimeoutSymbol] = setTimeout(function () {
- resetTypedPrefix(element);
- }, PREFIX_TIMEOUT_DURATION);
-}
-
-},{"./createSymbol":28,"./symbols":32}],16:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
-
-var _set = function set(object, property, value, receiver) { var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent !== null) { set(parent, property, value, receiver); } } else if ("value" in desc && desc.writable) { desc.value = value; } else { var setter = desc.set; if (setter !== undefined) { setter.call(receiver, value); } } return value; };
-
-var _get = function get(object, property, receiver) { if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { return get(parent, property, receiver); } } else if ("value" in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } };
-
-var _renderArrayAsElements = require('../../basic-component-mixins/src/renderArrayAsElements');
-
-var _renderArrayAsElements2 = _interopRequireDefault(_renderArrayAsElements);
-
-var _symbols = require('../../basic-component-mixins/src/symbols');
-
-var _symbols2 = _interopRequireDefault(_symbols);
-
-var _toggleClass = require('../../basic-component-mixins/src/toggleClass');
-
-var _toggleClass2 = _interopRequireDefault(_toggleClass);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-/* Exported function extends a base class with PageDots. */
-exports.default = function (base) {
-
- /**
- * Template mixin which adds small dots to show the number of items and let
- * the user select a specific item.
- *
- * You can see a
- * [live demo](http://basicwebcomponents.org/basic-web-components/packages/demos/carousel-with-dots.html)
- * of this mixin applied to a carousel.
- *
- * There will be one dot for each item, and the dot for the currently selected
- * item will be shown selected.
- *
- * Typical usage:
- *
- * class CarouselWithDots extends PageDotsMixin(Carousel) {}
- * customElements.define('carousel-with-dots', CarouselWithDots);
- *
- * Although the dots are quite small by default, clicking/tapping a dot will
- * will select the corresponding list item.
- */
- var PageDots = function (_base) {
- _inherits(PageDots, _base);
-
- function PageDots() {
- _classCallCheck(this, PageDots);
-
- var _this = _possibleConstructorReturn(this, (PageDots.__proto__ || Object.getPrototypeOf(PageDots)).call(this));
-
- _this.$.dots.addEventListener('click', function (event) {
- var dot = event.target;
- var dotIndex = _this.dots.indexOf(dot);
- if (dotIndex >= 0) {
- _this.selectedIndex = dotIndex;
- }
- });
- return _this;
- }
-
- _createClass(PageDots, [{
- key: _symbols2.default.itemsChanged,
- value: function value() {
- if (_get(PageDots.prototype.__proto__ || Object.getPrototypeOf(PageDots.prototype), _symbols2.default.itemsChanged, this)) {
- _get(PageDots.prototype.__proto__ || Object.getPrototypeOf(PageDots.prototype), _symbols2.default.itemsChanged, this).call(this);
- }
- (0, _renderArrayAsElements2.default)(this.items, this.$.dots, function (item, element) {
- // We don't use the item parameter, because any item will produce an
- // identical corresponding dot.
- if (!element) {
- element = document.createElement('div');
- element.classList.add('dot');
- element.classList.add('style-scope');
- element.classList.add('basic-page-dots');
- element.setAttribute('role', 'none');
- return element;
- }
- });
- refreshDots(this);
- }
- }, {
- key: _symbols2.default.itemSelected,
- value: function value(item, selected) {
- if (_get(PageDots.prototype.__proto__ || Object.getPrototypeOf(PageDots.prototype), _symbols2.default.itemSelected, this)) {
- _get(PageDots.prototype.__proto__ || Object.getPrototypeOf(PageDots.prototype), _symbols2.default.itemSelected, this).call(this, item, selected);
- }
- var index = this.items.indexOf(item);
- // See if the corresponding dot has already been created.
- // If not, the correct dot will be selected when it gets created.
- var dots = this.dots;
- if (dots && dots.length > index) {
- var dot = this.dots[index];
- if (dot) {
- (0, _toggleClass2.default)(dot, 'selected', selected);
- }
- }
- }
-
- /**
- * The distance the user has moved the first touchpoint since the beginning
- * of a drag, expressed as a fraction of the element's width.
- *
- * @type number
- */
-
- }, {
- key: 'dots',
- get: function get() {
- return [].slice.call(this.$.dots.querySelectorAll('.dot'));
- }
- }, {
- key: 'selectedFraction',
- get: function get() {
- return _get(PageDots.prototype.__proto__ || Object.getPrototypeOf(PageDots.prototype), 'selectedFraction', this);
- },
- set: function set(value) {
- if ('selectedFraction' in base.prototype) {
- _set(PageDots.prototype.__proto__ || Object.getPrototypeOf(PageDots.prototype), 'selectedFraction', value, this);
- }
- renderTransition(this, this.selectedIndex, value);
- }
- }, {
- key: 'selectedIndex',
- get: function get() {
- return _get(PageDots.prototype.__proto__ || Object.getPrototypeOf(PageDots.prototype), 'selectedIndex', this);
- },
- set: function set(index) {
- if ('selectedIndex' in base.prototype) {
- _set(PageDots.prototype.__proto__ || Object.getPrototypeOf(PageDots.prototype), 'selectedIndex', index, this);
- }
- refreshDots(this);
- }
- }, {
- key: _symbols2.default.template,
- get: function get() {
- var baseTemplate = _get(PageDots.prototype.__proto__ || Object.getPrototypeOf(PageDots.prototype), _symbols2.default.template, this) || '';
- return '\n \n\n
\n \n ' + baseTemplate + '\n
\n ';
- }
- }]);
-
- return PageDots;
- }(base);
-
- return PageDots;
-};
-
-// Return the index, ensuring it stays between 0 and the given length.
-
-
-function keepIndexWithinBounds(length, index) {
- // Handle possibility of negative mod.
- // See http://stackoverflow.com/a/18618250/76472
- return (index % length + length) % length;
-}
-
-function renderTransition(element, selectedIndex, selectedFraction) {
- var dots = element.dots;
- if (!dots || dots.length === 0) {
- return;
- }
- var dotCount = dots.length;
- var opacityMinimum = 0.4;
- var opacityMaximum = 0.95;
- var opacityRange = opacityMaximum - opacityMinimum;
- var fractionalIndex = selectedIndex + selectedFraction;
- var leftIndex = Math.floor(fractionalIndex);
- var rightIndex = Math.ceil(fractionalIndex);
- var selectionWraps = element.selectionWraps;
- var awayIndex = selectedFraction >= 0 ? leftIndex : rightIndex;
- var towardIndex = selectedFraction >= 0 ? rightIndex : leftIndex;
- if (selectionWraps) {
- awayIndex = keepIndexWithinBounds(dotCount, awayIndex);
- towardIndex = keepIndexWithinBounds(dotCount, towardIndex);
- }
- // Stupid IE doesn't have Math.trunc.
- // const truncatedSelectedFraction = Math.trunc(selectedFraction);
- var truncatedSelectedFraction = selectedFraction < 0 ? Math.ceil(selectedFraction) : Math.floor(selectedFraction);
- var progress = selectedFraction - truncatedSelectedFraction;
- var opacityProgressThroughRange = Math.abs(progress) * opacityRange;
- dots.forEach(function (dot, index) {
- var dotOpacity = void 0;
- if (selectedFraction === 0) {
- // Remove explicit opacity and rely on styling.
- dotOpacity = '';
- } else if (index === awayIndex) {
- dotOpacity = opacityMaximum - opacityProgressThroughRange;
- } else if (index === towardIndex) {
- dotOpacity = opacityMinimum + opacityProgressThroughRange;
- } else {
- dotOpacity = opacityMinimum;
- }
- dot.style.opacity = dotOpacity;
- });
-}
-
-function refreshDots(element) {
- var selectedIndex = element.selectedIndex;
- element.dots.forEach(function (dot, i) {
- (0, _toggleClass2.default)(dot, 'selected', i === selectedIndex);
- });
-}
-
-},{"../../basic-component-mixins/src/renderArrayAsElements":30,"../../basic-component-mixins/src/symbols":32,"../../basic-component-mixins/src/toggleClass":33}],17:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
-
-var _set = function set(object, property, value, receiver) { var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent !== null) { set(parent, property, value, receiver); } } else if ("value" in desc && desc.writable) { desc.value = value; } else { var setter = desc.set; if (setter !== undefined) { setter.call(receiver, value); } } return value; };
-
-var _get = function get(object, property, receiver) { if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { return get(parent, property, receiver); } } else if ("value" in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } };
-
-var _safeAttributes = require('../../basic-component-mixins/src/safeAttributes');
-
-var _safeAttributes2 = _interopRequireDefault(_safeAttributes);
-
-var _symbols = require('../../basic-component-mixins/src/symbols');
-
-var _symbols2 = _interopRequireDefault(_symbols);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-/* Exported function extends a base class with PlayControls. */
-exports.default = function (base) {
-
- /**
- * Template mixin which adds buttons for managing playback of a slideshow,
- * audio playlist, etc.
- *
- * Typical usage:
- *
- * class SlideshowWithControls extends PlayControlsMixin(Slideshow) {}
- * customElements.define('slideshow-with-controls', SlideshowWithControls);
- *
- */
- var PlayControls = function (_base) {
- _inherits(PlayControls, _base);
-
- function PlayControls() {
- _classCallCheck(this, PlayControls);
-
- var _this = _possibleConstructorReturn(this, (PlayControls.__proto__ || Object.getPrototypeOf(PlayControls)).call(this));
-
- _this.$.previousButton.addEventListener('click', function (event) {
- _this.selectPrevious();
- });
- _this.$.playButton.addEventListener('click', function (event) {
- _this.playing = !_this.playing;
- });
- _this.$.nextButton.addEventListener('click', function (event) {
- _this.selectNext();
- });
- return _this;
- }
-
- _createClass(PlayControls, [{
- key: 'connectedCallback',
- value: function connectedCallback() {
- if (_get(PlayControls.prototype.__proto__ || Object.getPrototypeOf(PlayControls.prototype), 'connectedCallback', this)) {
- _get(PlayControls.prototype.__proto__ || Object.getPrototypeOf(PlayControls.prototype), 'connectedCallback', this).call(this);
- }
- _safeAttributes2.default.connected(this);
- }
- }, {
- key: _symbols2.default.keydown,
- value: function value(event) {
- var handled = void 0;
-
- switch (event.keyCode) {
- case 32:
- /* Space */
- this.playing = !this.playing;
- handled = true;
- break;
- }
-
- // Prefer mixin result if it's defined, otherwise use base result.
- return handled || _get(PlayControls.prototype.__proto__ || Object.getPrototypeOf(PlayControls.prototype), _symbols2.default.keydown, this) && _get(PlayControls.prototype.__proto__ || Object.getPrototypeOf(PlayControls.prototype), _symbols2.default.keydown, this).call(this, event);
- }
- }, {
- key: 'playing',
- get: function get() {
- return _get(PlayControls.prototype.__proto__ || Object.getPrototypeOf(PlayControls.prototype), 'playing', this);
- },
- set: function set(value) {
- if ('playing' in base.prototype) {
- _set(PlayControls.prototype.__proto__ || Object.getPrototypeOf(PlayControls.prototype), 'playing', value, this);
- }
- _safeAttributes2.default.toggleClass(this, 'playing', value);
- }
- }, {
- key: _symbols2.default.template,
- get: function get() {
- var baseTemplate = _get(PlayControls.prototype.__proto__ || Object.getPrototypeOf(PlayControls.prototype), _symbols2.default.template, this) || '';
- return '\n \n\n \n\n \n ' + baseTemplate + '\n
\n ';
- }
- }]);
-
- return PlayControls;
- }(base);
-
- return PlayControls;
-};
-
-},{"../../basic-component-mixins/src/safeAttributes":31,"../../basic-component-mixins/src/symbols":32}],18:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
-
-var _set = function set(object, property, value, receiver) { var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent !== null) { set(parent, property, value, receiver); } } else if ("value" in desc && desc.writable) { desc.value = value; } else { var setter = desc.set; if (setter !== undefined) { setter.call(receiver, value); } } return value; };
-
-var _get = function get(object, property, receiver) { if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { return get(parent, property, receiver); } } else if ("value" in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } };
-
-exports.default = mixin;
-
-var _createSymbol = require('./createSymbol');
-
-var _createSymbol2 = _interopRequireDefault(_createSymbol);
-
-var _FractionalSelectionMixin = require('./FractionalSelectionMixin');
-
-var _FractionalSelectionMixin2 = _interopRequireDefault(_FractionalSelectionMixin);
-
-var _symbols = require('./symbols');
-
-var _symbols2 = _interopRequireDefault(_symbols);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-// Symbols for private data members on an element.
-var animationSymbol = (0, _createSymbol2.default)('animation');
-var draggingSymbol = (0, _createSymbol2.default)('dragging');
-var lastAnimationSymbol = (0, _createSymbol2.default)('lastAnimation');
-var playingAnimationSymbol = (0, _createSymbol2.default)('animatingSelection');
-var previousSelectionSymbol = (0, _createSymbol2.default)('previousSelection');
-var selectionAnimationDurationSymbol = (0, _createSymbol2.default)('selectionAnimationDuration');
-var selectionAnimationEffectSymbol = (0, _createSymbol2.default)('selectionAnimationEffect');
-var selectionAnimationKeyframesSymbol = (0, _createSymbol2.default)('selectionAnimationKeyframes');
-var resetAnimationsOnNextRenderSymbol = (0, _createSymbol2.default)('resetAnimationsOnNextRender');
-
-/* Exported function extends a base class with SelectionAnimation. */
-function mixin(base) {
-
- /**
- * Mixin which uses animation to show transitions between selection states.
- *
- * This mixin can be used by components that want to provide visible
- * animations when changing the selection. For example, a carousel component
- * may want to define a sliding animation effect shown when moving between
- * items.
- *
- * The animation is defined by a `selectionAnimationKeyframes` property; see
- * that property for details on how to define these keyframes. This animation
- * will be used in two ways. First, when moving strictly between items, the
- * animation will play smoothly to show the selection changing. Second, the
- * animation can be used to render the selection at a fixed point in the
- * transition between states. E.g., if the user pauses halfway through
- * dragging an element using [SwipeDirectionMixin](SwipeDirectionMixin.md)
- * or [TrackpadDirectionMixin](TrackpadDirectionMixin.md)s, then the selection
- * animation will be shown at the point exactly halfway through.
- *
- * This mixin expects a component to provide an `items` array of all elements
- * in the list, which can be provided via
- * [ContentItemsMixin](ContentItemsMixin.md). This mixin also expects
- * `selectedIndex` and `selectedItem` properties, which can be provided via
- * [SingleSelectionMixin](SingleSelectionMixin.md).
- *
- * This mixin supports a `selectionWraps` property. When true, the user can
- * navigate forward from the last item in the list and wrap around to the
- * first item, or navigate backward from the first item and wrap around to the
- * last item.
- *
- * This mixin uses the Web Animations API. For use on browsers which
- * do not support that API natively, you will need to load the
- * [Web Animations polyfill](https://github.com/web-animations/web-animations-js).
- */
- var SelectionAnimation = function (_base) {
- _inherits(SelectionAnimation, _base);
-
- function SelectionAnimation() {
- _classCallCheck(this, SelectionAnimation);
-
- // Set defaults.
- var _this = _possibleConstructorReturn(this, (SelectionAnimation.__proto__ || Object.getPrototypeOf(SelectionAnimation)).call(this));
-
- if (typeof _this.selectionAnimationDuration === 'undefined') {
- _this.selectionAnimationDuration = _this[_symbols2.default.defaults].selectionAnimationDuration;
- }
- if (typeof _this.selectionAnimationEffect === 'undefined' && _this.selectionAnimationKeyframes == null) {
- _this.selectionAnimationEffect = _this[_symbols2.default.defaults].selectionAnimationEffect;
- }
-
- _this[_symbols2.default.dragging] = false;
- return _this;
- }
-
- _createClass(SelectionAnimation, [{
- key: _symbols2.default.itemAdded,
- value: function value(item) {
- // We mark new items in the list as explicitly visible to ARIA. Otherwise,
- // when an item isn't visible on the screen, ARIA will assume the item is
- // of no interest to the user, and leave it out of the accessibility tree.
- // If the list contains 10 items, but only 3 are visible, a screen reader
- // might then announce the list only has 3 items. To ensure that screen
- // readers and other assistive technologies announce the correct total
- // number of items, we explicitly mark all items as not hidden. This will
- // expose them all in the accessibility tree, even the items which are
- // currently not rendered.
- //
- // TODO: Generally speaking, this entire mixin assumes that the user can
- // navigate through all items in a list. But an app could style an item as
- // display:none or visibility:hidden because the user is not allowed to
- // interact with that item at the moment. Support for this scenario should
- // be added. This would entail changing all locations where a mixin
- // function is counting items, iterating over the (visible) items, and
- // showing or hiding items. Among other things, the code below to make
- // items visible to ARIA would need to discriminate between items which
- // are invisible because of animation state, or invisible because the user
- // shouldn't interact with them.
- item.setAttribute('aria-hidden', false);
- }
- }, {
- key: _symbols2.default.itemsChanged,
- value: function value() {
- if (_get(SelectionAnimation.prototype.__proto__ || Object.getPrototypeOf(SelectionAnimation.prototype), _symbols2.default.itemsChanged, this)) {
- _get(SelectionAnimation.prototype.__proto__ || Object.getPrototypeOf(SelectionAnimation.prototype), _symbols2.default.itemsChanged, this).call(this);
- }
-
- _resetAnimations(this);
-
- // TODO: Also reset our notion of the last rendered selection? This comes
- // up when a DOM removal causes the selected item to change position.
- // this[previousSelectionSymbol] = null;
-
- renderSelection(this);
- }
- }, {
- key: 'resetAnimations',
- value: function resetAnimations() {
- _resetAnimations(this);
- }
-
- /**
- * A fractional value indicating how far the user has currently advanced to
- * the next/previous item. E.g., a `selectedFraction` of 3.5 indicates the
- * user is halfway between items 3 and 4.
- *
- * For more details, see [FractionalSelectionMixin](FractionalSelectionMixin.md)
- * mixin.
- *
- * @type {number}
- */
-
- }, {
- key: _symbols2.default.defaults,
- get: function get() {
- var defaults = _get(SelectionAnimation.prototype.__proto__ || Object.getPrototypeOf(SelectionAnimation.prototype), _symbols2.default.defaults, this) || {};
- defaults.selectionAnimationDuration = 250;
- defaults.selectionAnimationEffect = 'slide';
- return defaults;
- }
-
- /*
- * Provide backing for the dragging property.
- * Also, when a drag begins, reset the animations.
- */
-
- }, {
- key: _symbols2.default.dragging,
- get: function get() {
- return this[draggingSymbol];
- },
- set: function set(value) {
- var previousValue = this[_symbols2.default.dragging];
- this[draggingSymbol] = value;
- if (_symbols2.default.dragging in base.prototype) {
- _set(SelectionAnimation.prototype.__proto__ || Object.getPrototypeOf(SelectionAnimation.prototype), _symbols2.default.dragging, value, this);
- }
- if (value && !previousValue) {
- // Have begun a drag.
- this[resetAnimationsOnNextRenderSymbol] = true;
- }
- }
- }, {
- key: 'selectedFraction',
- get: function get() {
- return _get(SelectionAnimation.prototype.__proto__ || Object.getPrototypeOf(SelectionAnimation.prototype), 'selectedFraction', this) || 0;
- },
- set: function set(value) {
- if ('selectedFraction' in base.prototype) {
- _set(SelectionAnimation.prototype.__proto__ || Object.getPrototypeOf(SelectionAnimation.prototype), 'selectedFraction', value, this);
- }
- renderSelection(this, this.selectedIndex, value);
- }
- }, {
- key: 'selectedIndex',
- get: function get() {
- return _get(SelectionAnimation.prototype.__proto__ || Object.getPrototypeOf(SelectionAnimation.prototype), 'selectedIndex', this);
- },
- set: function set(index) {
- if ('selectedIndex' in base.prototype) {
- _set(SelectionAnimation.prototype.__proto__ || Object.getPrototypeOf(SelectionAnimation.prototype), 'selectedIndex', index, this);
- }
- renderSelection(this, index, 0);
- }
-
- /**
- * The duration of a selection animation in milliseconds.
- *
- * This measures the amount of time required for a selection animation to
- * complete. This number remains constant, even if the number of items being
- * animated increases.
- *
- * The default value is 250 milliseconds (a quarter a second).
- *
- * @type {number}
- * @default 250
- */
-
- }, {
- key: 'selectionAnimationDuration',
- get: function get() {
- return this[selectionAnimationDurationSymbol];
- },
- set: function set(value) {
- this[selectionAnimationDurationSymbol] = value;
- if ('selectionAnimationDuration' in base.prototype) {
- _set(SelectionAnimation.prototype.__proto__ || Object.getPrototypeOf(SelectionAnimation.prototype), 'selectionAnimationDuration', value, this);
- }
- }
-
- /**
- * The name of a standard selection animation effect.
- *
- * This is a shorthand for setting the `selectionAnimationKeyframes`
- * property to standard keyframes. Supported string values:
- *
- * * "crossfade"
- * * "reveal"
- * * "revealWithFade"
- * * "showAdjacent"
- * * "slide"
- * * "slideWithGap"
- *
- * @type {string}
- * @default "slide"
- */
-
- }, {
- key: 'selectionAnimationEffect',
- get: function get() {
- return this[selectionAnimationEffectSymbol];
- },
- set: function set(value) {
- this[selectionAnimationEffectSymbol] = value;
- if ('selectionAnimationEffect' in base.prototype) {
- _set(SelectionAnimation.prototype.__proto__ || Object.getPrototypeOf(SelectionAnimation.prototype), 'selectionAnimationEffect', value, this);
- }
- this.selectionAnimationKeyframes = mixin.standardEffectKeyframes[value];
- }
-
- /**
- * The keyframes that define an animation that plays for an item when moving
- * forward in the sequence.
- *
- * This is an array of CSS rules that will be applied. These are used as
- * [keyframes](http://w3c.github.io/web-animations/#keyframes-section)
- * to animate the item with the
- * [Web Animations API](https://developer.mozilla.org/en-US/docs/Web/API/animation).
- *
- * The animation represents the state of the next item as it moves from
- * completely unselected (offstage, usually right), to selected (center
- * stage), to completely unselected (offstage, usually left). The center time
- * of the animation should correspond to the item's quiscent selected state,
- * typically in the center of the stage and at the item's largest size.
- *
- * The default forward animation is a smooth slide at full size from right to
- * left.
- *
- * When moving the selection backward, this animation is played in reverse.
- *
- * @type {cssRules[]}
- */
-
- }, {
- key: 'selectionAnimationKeyframes',
- get: function get() {
- // Standard animation slides left/right, keeps adjacent items out of view.
- return this[selectionAnimationKeyframesSymbol];
- },
- set: function set(value) {
- this[selectionAnimationKeyframesSymbol] = value;
- if ('selectionAnimationKeyframes' in base.prototype) {
- _set(SelectionAnimation.prototype.__proto__ || Object.getPrototypeOf(SelectionAnimation.prototype), 'selectionAnimationKeyframes', value, this);
- }
- _resetAnimations(this);
- renderSelection(this);
- }
- }, {
- key: 'selectionWraps',
- get: function get() {
- return _get(SelectionAnimation.prototype.__proto__ || Object.getPrototypeOf(SelectionAnimation.prototype), 'selectionWraps', this);
- },
- set: function set(value) {
- if ('selectionWraps' in base.prototype) {
- _set(SelectionAnimation.prototype.__proto__ || Object.getPrototypeOf(SelectionAnimation.prototype), 'selectionWraps', value, this);
- }
- _resetAnimations(this);
- renderSelection(this);
- }
- }]);
-
- return SelectionAnimation;
- }(base);
-
- return SelectionAnimation;
-}
-
-// We expose helpers on the mixin function that we want to be able to unit test.
-// Since these are on the function, not on the class emitted by the function,
-// they don't end up getting exposed on actual element instances.
-mixin.helpers = {
-
- /*
- * Calculate the animation fractions for an element's items at the given
- * selection point. This is used when rendering the element's selection state
- * instantaneously.
- *
- * This function considers the selectedIndex parameter, which can be a whole
- * or fractional number, and determines which items will be visible at that
- * index. This function then calculates a corresponding animation fraction: a
- * number between 0 and 1 indicating how far through the selection animation
- * an item should be shown, or null if the item should not be visible at that
- * selection index. These fractions are returned as an array, where the
- * animation fraction at position N corresponds to how item N should be shown.
- */
- animationFractionsForSelection: function animationFractionsForSelection(element, selection) {
-
- var items = element.items;
- if (!items) {
- return;
- }
-
- var itemCount = items.length;
- var selectionWraps = element.selectionWraps;
-
- return items.map(function (item, itemIndex) {
- // How many steps from the selection point to this item?
- var steps = stepsToIndex(itemCount, selectionWraps, selection, itemIndex);
- // To convert steps to animation fraction:
- // steps animation fraction
- // 1 0 (stage right)
- // 0 0.5 (center stage)
- // -1 1 (stage left)
- var animationFraction = (1 - steps) / 2;
- return animationFraction >= 0 && animationFraction <= 1 ? animationFraction : null; // Outside animation range
- });
- },
-
-
- /*
- * Calculate the animation timings that should be used to smoothly animate the
- * element's items from one selection state to another.
- *
- * This returns an array of timings, where the timing at position N should be
- * used to animate item N. If an item's timing is null, then that item should
- * not take place in the animation, and should be hidden instead.
- */
- effectTimingsForSelectionAnimation: function effectTimingsForSelectionAnimation(element, fromSelection, toSelection) {
-
- var items = element.items;
- if (!items) {
- return;
- }
- var itemCount = items.length;
- var selectionWraps = element.selectionWraps;
- var toIndex = _FractionalSelectionMixin2.default.helpers.wrappedSelectionParts(toSelection, itemCount, selectionWraps).index;
- var totalSteps = stepsToIndex(itemCount, selectionWraps, fromSelection, toSelection);
- var direction = totalSteps >= 0 ? 'normal' : 'reverse';
- var fill = 'both';
- var totalDuration = element.selectionAnimationDuration;
- var stepDuration = totalSteps !== 0 ? totalDuration * 2 / Math.ceil(Math.abs(totalSteps)) : 0; // No steps required, animation will be instantenous.
-
- var timings = items.map(function (item, itemIndex) {
- var steps = stepsToIndex(itemCount, selectionWraps, itemIndex, toSelection);
- // If we include this item in the staggered sequence of animations we're
- // creating, where would the item appear in the sequence?
- var positionInSequence = totalSteps - steps;
- if (totalSteps < 0) {
- positionInSequence = -positionInSequence;
- }
- // So, is this item really included in the sequence?
- if (Math.ceil(positionInSequence) >= 0 && positionInSequence <= Math.abs(totalSteps)) {
- // Note that delay for first item will be negative. That will cause
- // the animation to start halfway through, which is what we want.
- var delay = stepDuration * (positionInSequence - 1) / 2;
- var endDelay = itemIndex === toIndex ? -stepDuration / 2 : // Stop halfway through.
- 0; // Play animation until end.
- return { duration: stepDuration, direction: direction, fill: fill, delay: delay, endDelay: endDelay };
- } else {
- return null;
- }
- });
-
- return timings;
- }
-};
-
-// Keyframes for standard selection animation effects.
-mixin.standardEffectKeyframes = {
-
- // Simple crossfade
- crossfade: [{ opacity: 0 }, { opacity: 1 }, { opacity: 0 }],
-
- // Reveal, as if sliding the top card off a deck of cards
- reveal: [{ transform: 'translateX(0%)', zIndex: 0 }, { transform: 'translateX(0%)', zIndex: 1 }, { transform: 'translateX(-100%)', zIndex: 2 }],
-
- // Google Photos-style reveal-with-fade animation
- revealWithFade: [{ transform: 'translateX(0%) scale(0.75)', opacity: 0, zIndex: 0 }, { transform: 'translateX(0%) scale(1.0)', opacity: 1, zIndex: 1 }, { transform: 'translateX(-100%) scale(1.0)', opacity: 1, zIndex: 2 }],
-
- // Carousel variant with a bit of off-stage elements showing
- showAdjacent: [{ transform: 'translateX(78%) scale(0.7)', zIndex: 0 }, { transform: 'translateX(0%) scale(0.82)', zIndex: 1 }, { transform: 'translateX(-78%) scale(0.7)', zIndex: 0 }],
-
- // Simple slide
- slide: [{ transform: 'translateX(100%)' }, { transform: 'translateX(-100%)' }],
-
- // Slide, with a gap between
- slideWithGap: [{ transform: 'translateX(110%)' }, { transform: 'translateX(-110%)' }]
-
-};
-
-/*
- * Smoothly animate the selection between the indicated "from" and "to"
- * indices. The former can be a fraction, e.g., when the user releases a finger
- * to complete a touch drag, and the selection will snap to the closest whole
- * index.
- */
-function animateSelection(element, fromSelection, toSelection) {
-
- _resetAnimations(element);
-
- // Calculate the animation timings.
- var items = element.items;
- var keyframes = element.selectionAnimationKeyframes;
- element[playingAnimationSymbol] = true;
- var timings = mixin.helpers.effectTimingsForSelectionAnimation(element, fromSelection, toSelection);
-
- // Figure out which item will be the one *after* the one we're selecting.
- var itemCount = items.length;
- var selectionWraps = element.selectionWraps;
- var selectionIndex = _FractionalSelectionMixin2.default.helpers.selectionParts(toSelection, itemCount, selectionWraps).index;
- var totalSteps = stepsToIndex(itemCount, selectionWraps, fromSelection, toSelection);
- var forward = totalSteps >= 0;
- var nextUpIndex = selectionIndex + (forward ? 1 : -1);
- if (selectionWraps) {
- nextUpIndex = _FractionalSelectionMixin2.default.helpers.wrappedSelection(nextUpIndex, itemCount);
- } else if (!isItemIndexInBounds(element, nextUpIndex)) {
- nextUpIndex = null; // At start/end of list; don't have a next item to show.
- }
-
- // Play the animations using those timings.
- var lastAnimationDetails = void 0;
- timings.forEach(function (timing, index) {
- var item = items[index];
- if (timing) {
- showItem(item, true);
- var animation = item.animate(keyframes, timing);
- element[animationSymbol][index] = animation;
- if (index === nextUpIndex) {
- // This item will be animated, so will already be in the desired state
- // after the animation completes.
- nextUpIndex = null;
- }
- if (timing.endDelay !== 0) {
- // This is the animation for the item that will be left selected.
- // We want to clean up when this animation completes.
- lastAnimationDetails = { animation: animation, index: index, timing: timing, forward: forward };
- }
- } else {
- // This item doesn't participate in the animation.
- showItem(item, false);
- }
- });
-
- if (lastAnimationDetails != null) {
- // Arrange for clean-up work to be performed.
- lastAnimationDetails.nextUpIndex = nextUpIndex;
- lastAnimationDetails.animation.onfinish = function (event) {
- return selectionAnimationFinished(element, lastAnimationDetails);
- };
- element[lastAnimationSymbol] = lastAnimationDetails.animation;
- } else {
- // Shouldn't happen -- we should always have at least one animation.
- element[playingAnimationSymbol] = false;
- }
-}
-
-function getAnimationForItemIndex(element, index) {
- if (element[animationSymbol] == null) {
- // Not ready yet;
- return null;
- }
- var animation = element[animationSymbol][index];
- if (!animation) {
- var item = element.items[index];
- animation = item.animate(element.selectionAnimationKeyframes, {
- duration: element.selectionAnimationDuration,
- fill: 'both'
- });
- animation.pause();
- element[animationSymbol][index] = animation;
- }
- return animation;
-}
-
-function isItemIndexInBounds(element, index) {
- return index >= 0 && element.items && index < element.items.length;
-}
-
-/*
- * Render the selection state of the element.
- *
- * This can be used to re-render a previous selection state (if the
- * selectedIndex param is omitted), render the selection instantly at a given
- * whole or fractional selection index, or animate to a given selection index.
- *
- * There are several distinct scenarios we need to cover:
- *
- * 1. Initial positioning, or repositioning after changing a property like
- * selectionAnimationKeyframes that affects rendering.
- * 2. Animate on selectedIndex change. This should override any animation/swipe
- * already in progress.
- * 3. Instantly render the current position of a drag operation in progress.
- * 4. Complete a drag operation. If the drag wasn't far enough to affect
- * selection, we'll just be restoring the selectedFraction to 0.
- *
- * If the list does not wrap, any selection position outside the list's bounds
- * will be damped to produce a visual effect of tension.
- */
-function renderSelection(element) {
- var selectedIndex = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : element.selectedIndex;
- var selectedFraction = arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : element.selectedFraction;
-
- var itemCount = element.items ? element.items.length : 0;
- if (itemCount === 0) {
- // Nothing to render.
- return;
- }
- if (selectedIndex < 0) {
- // TODO: Handle no selection.
- return;
- }
- var selection = selectedIndex + selectedFraction;
- if (element.selectionWraps) {
- // Apply wrapping to ensure consistent representation of selection.
- selection = _FractionalSelectionMixin2.default.helpers.wrappedSelection(selection, itemCount);
- } else {
- // Apply damping if necessary.
- selection = _FractionalSelectionMixin2.default.helpers.dampedSelection(selection, itemCount);
- }
- var previousSelection = element[previousSelectionSymbol];
- // TODO: If an item changes position in the DOM, we end up animating from
- // its old index to its new index, but we really don't want to animate at all.
- if (!element[_symbols2.default.dragging] && previousSelection != null && previousSelection !== selection) {
- // Animate selection from previous state to new state.
- animateSelection(element, previousSelection, selection);
- } else if (selectedFraction === 0 && element[playingAnimationSymbol]) {
- // Already in process of animating to fraction 0. During that process,
- // ignore subsequent attempts to renderSelection to fraction 0.
- return;
- } else {
- // Render current selection state instantly.
- renderSelectionInstantly(element, selection);
- }
- element[previousSelectionSymbol] = selection;
-}
-
-/*
- * Instantly render (don't animate) the element's items at the given whole or
- * fractional selection index.
- */
-function renderSelectionInstantly(element, toSelection) {
- if (element[resetAnimationsOnNextRenderSymbol]) {
- _resetAnimations(element);
- element[resetAnimationsOnNextRenderSymbol] = false;
- }
- var animationFractions = mixin.helpers.animationFractionsForSelection(element, toSelection);
- animationFractions.map(function (animationFraction, index) {
- var item = element.items[index];
- if (animationFraction != null) {
- showItem(item, true);
- setAnimationFraction(element, index, animationFraction);
- } else {
- showItem(item, false);
- }
- });
-}
-
-/*
- * We maintain an array containing an animation per item. This is used for two
- * reasons:
- *
- * * During a drag operation, we want to be able to reuse animations between
- * drag updates.
- * * When a selection animation completes, we need to be able to leave the
- * visibile items in a paused state. Later, we'll want to be able to clean up
- * those animations.
- *
- * Note that this array is sparse: it will only hold up from 0–3 animations at
- * any given point.
- */
-function _resetAnimations(element) {
- var animations = element[animationSymbol];
- if (animations) {
- // Cancel existing animations to remove the effects they're applying.
- animations.forEach(function (animation, index) {
- if (animation) {
- animation.cancel();
- animations[index] = null;
- }
- });
- }
- var itemCount = element.items ? element.items.length : 0;
- if (!animations || animations.length !== itemCount) {
- // Haven't animated before with this number of items; (re)create array.
- element[animationSymbol] = new Array(itemCount);
- }
-}
-
-/*
- * The last animation in our selection animation has completed. Clean up.
- */
-function selectionAnimationFinished(element, details) {
-
- // When the last animation completes, show the next item in the direction
- // we're going. Waiting to that until this point is a bit of a hack to avoid
- // having a next item that's higher in the natural z-order obscure other items
- // during animation.
- var nextUpIndex = details.nextUpIndex;
- if (nextUpIndex != null) {
- if (element[animationSymbol][nextUpIndex]) {
- // Cancel existing selection animation so we can construct a new one.
- element[animationSymbol][nextUpIndex].cancel();
- element[animationSymbol][nextUpIndex] = null;
- }
- var animationFraction = details.forward ? 0 : 1;
- setAnimationFraction(element, nextUpIndex, animationFraction);
- showItem(element.items[nextUpIndex], true);
- }
-
- element[lastAnimationSymbol].onfinish = null;
- element[playingAnimationSymbol] = false;
-}
-
-/*
- * Pause the indicated animation and have it show the animation at the given
- * fraction (between 0 and 1) of the way through the animation.
- */
-function setAnimationFraction(element, itemIndex, fraction) {
- var animation = getAnimationForItemIndex(element, itemIndex);
- if (animation) {
- var duration = element.selectionAnimationDuration;
- if (duration) {
- animation.currentTime = fraction * duration;
- }
- }
-}
-
-function showItem(item, flag) {
- item.style.visibility = flag ? 'visible' : 'hidden';
-}
-
-/*
- * Figure out how many steps it will take to go from fromSelection to
- * toSelection. To go from item 3 to item 4 is one step.
- *
- * If wrapping is allowed, then going from the last item to the first will take
- * one step (forward), and going from the first item to the last will take one
- * step (backward).
- */
-function stepsToIndex(length, allowWrap, fromSelection, toSelection) {
- var steps = toSelection - fromSelection;
- // Wrapping only kicks in when list has more than 1 item.
- if (allowWrap && length > 1) {
- var wrapSteps = length - Math.abs(steps);
- if (wrapSteps <= 1) {
- // Special case
- steps = steps < 0 ? wrapSteps : // Wrap forward from last item to first.
- -wrapSteps; // Wrap backward from first item to last.
- }
- }
- return steps;
-}
-
-},{"./FractionalSelectionMixin":10,"./createSymbol":28,"./symbols":32}],19:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
-
-var _set = function set(object, property, value, receiver) { var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent !== null) { set(parent, property, value, receiver); } } else if ("value" in desc && desc.writable) { desc.value = value; } else { var setter = desc.set; if (setter !== undefined) { setter.call(receiver, value); } } return value; };
-
-var _get = function get(object, property, receiver) { if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { return get(parent, property, receiver); } } else if ("value" in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } };
-
-var _symbols = require('./symbols');
-
-var _symbols2 = _interopRequireDefault(_symbols);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-// Used to assign unique IDs to item elements without IDs.
-var idCount = 0;
-
-/* Exported function extends a base class with SelectionAriaActive. */
-
-exports.default = function (base) {
-
- /**
- * Mixin which treats the selected item in a list as the active item in ARIA
- * accessibility terms.
- *
- * Handling ARIA selection state properly is actually quite complex:
- *
- * * The items in the list need to be indicated as possible items via an ARIA
- * `role` attribute value such as "option".
- * * The selected item need to be marked as selected by setting the item's
- * `aria-selected` attribute to true *and* the other items need be marked as
- * *not* selected by setting `aria-selected` to false.
- * * The outermost element with the keyboard focus needs to have attributes
- * set on it so that the selection is knowable at the list level via the
- * `aria-activedescendant` attribute.
- * * Use of `aria-activedescendant` in turn requires that all items in the
- * list have ID attributes assigned to them.
- *
- * This mixin tries to address all of the above requirements. To that end,
- * this mixin will assign generated IDs to any item that doesn't already have
- * an ID.
- *
- * ARIA relies on elements to provide `role` attributes. This mixin will apply
- * a default role of "listbox" on the outer list if it doesn't already have an
- * explicit role. Similarly, this mixin will apply a default role of "option"
- * to any list item that does not already have a role specified.
- *
- * This mixin expects a set of members that manage the state of the selection:
- * `[symbols.itemSelected]`, `itemAdded`, and `selectedIndex`. You can
- * supply these yourself, or do so via
- * [SingleSelectionMixin](SingleSelectionMixin.md).
- */
- var SelectionAriaActive = function (_base) {
- _inherits(SelectionAriaActive, _base);
-
- function SelectionAriaActive() {
- _classCallCheck(this, SelectionAriaActive);
-
- return _possibleConstructorReturn(this, (SelectionAriaActive.__proto__ || Object.getPrototypeOf(SelectionAriaActive)).apply(this, arguments));
- }
-
- _createClass(SelectionAriaActive, [{
- key: 'connectedCallback',
- value: function connectedCallback() {
- if (_get(SelectionAriaActive.prototype.__proto__ || Object.getPrototypeOf(SelectionAriaActive.prototype), 'connectedCallback', this)) {
- _get(SelectionAriaActive.prototype.__proto__ || Object.getPrototypeOf(SelectionAriaActive.prototype), 'connectedCallback', this).call(this);
- }
- // Set default ARIA role.
- if (this.getAttribute('role') == null && this[_symbols2.default.defaults].role) {
- this.setAttribute('role', this[_symbols2.default.defaults].role);
- }
- }
- }, {
- key: _symbols2.default.itemAdded,
- value: function value(item) {
- if (_get(SelectionAriaActive.prototype.__proto__ || Object.getPrototypeOf(SelectionAriaActive.prototype), _symbols2.default.itemAdded, this)) {
- _get(SelectionAriaActive.prototype.__proto__ || Object.getPrototypeOf(SelectionAriaActive.prototype), _symbols2.default.itemAdded, this).call(this, item);
- }
-
- if (!item.getAttribute('role')) {
- // Assign a default ARIA role.
- item.setAttribute('role', 'option');
- }
-
- // Ensure each item has an ID so we can set aria-activedescendant on the
- // overall list whenever the selection changes.
- //
- // The ID will take the form of a base ID plus a unique integer. The base
- // ID will be incorporate the component's own ID. E.g., if a component has
- // ID "foo", then its items will have IDs that look like "_fooOption1". If
- // the compnent has no ID itself, its items will get IDs that look like
- // "_option1". Item IDs are prefixed with an underscore to differentiate
- // them from manually-assigned IDs, and to minimize the potential for ID
- // conflicts.
- if (!item.id) {
- var baseId = this.id ? "_" + this.id + "Option" : "_option";
- item.id = baseId + idCount++;
- }
- }
- }, {
- key: _symbols2.default.itemSelected,
- value: function value(item, selected) {
- if (_get(SelectionAriaActive.prototype.__proto__ || Object.getPrototypeOf(SelectionAriaActive.prototype), _symbols2.default.itemSelected, this)) {
- _get(SelectionAriaActive.prototype.__proto__ || Object.getPrototypeOf(SelectionAriaActive.prototype), _symbols2.default.itemSelected, this).call(this, item, selected);
- }
- item.setAttribute('aria-selected', selected);
- var itemId = item.id;
- if (itemId && selected) {
- this.setAttribute('aria-activedescendant', itemId);
- }
- }
- }, {
- key: _symbols2.default.defaults,
- get: function get() {
- var defaults = _get(SelectionAriaActive.prototype.__proto__ || Object.getPrototypeOf(SelectionAriaActive.prototype), _symbols2.default.defaults, this) || {};
- defaults.role = 'listbox';
- return defaults;
- }
- }, {
- key: 'selectedItem',
- get: function get() {
- return _get(SelectionAriaActive.prototype.__proto__ || Object.getPrototypeOf(SelectionAriaActive.prototype), 'selectedItem', this);
- },
- set: function set(item) {
- if ('selectedItem' in base.prototype) {
- _set(SelectionAriaActive.prototype.__proto__ || Object.getPrototypeOf(SelectionAriaActive.prototype), 'selectedItem', item, this);
- }
- if (item == null) {
- // Selection was removed.
- this.removeAttribute('aria-activedescendant');
- }
- }
- }]);
-
- return SelectionAriaActive;
- }(base);
-
- return SelectionAriaActive;
-};
-
-},{"./symbols":32}],20:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
-
-var _get = function get(object, property, receiver) { if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { return get(parent, property, receiver); } } else if ("value" in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } };
-
-var _symbols = require('../src/symbols');
-
-var _symbols2 = _interopRequireDefault(_symbols);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-/* Exported function extends a base class with SelectionHighlight. */
-exports.default = function (base) {
-
- /**
- * Template mixin which applies standard highlight colors to a selected item.
- *
- * This mixin highlights textual items (e.g., in a list) in a standard way by
- * using the CSS `highlight` and `highlighttext` color values. These values
- * respect operating system defaults and user preferences, and hence are good
- * default values for highlight colors.
- *
- * This mixin expects a `selected` class to be applied to selected items. You
- * can use [ContentItemsMixin](ContentItemsMixin.md) for that purpose.
- */
- var SelectionHighlight = function (_base) {
- _inherits(SelectionHighlight, _base);
-
- function SelectionHighlight() {
- _classCallCheck(this, SelectionHighlight);
-
- return _possibleConstructorReturn(this, (SelectionHighlight.__proto__ || Object.getPrototypeOf(SelectionHighlight)).apply(this, arguments));
- }
-
- _createClass(SelectionHighlight, [{
- key: _symbols2.default.template,
- get: function get() {
- var baseTemplate = _get(SelectionHighlight.prototype.__proto__ || Object.getPrototypeOf(SelectionHighlight.prototype), _symbols2.default.template, this) || '';
- return '\n \n ' + baseTemplate + '\n ';
- }
- }]);
-
- return SelectionHighlight;
- }(base);
-
- return SelectionHighlight;
-};
-
-},{"../src/symbols":32}],21:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
-
-var _set = function set(object, property, value, receiver) { var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent !== null) { set(parent, property, value, receiver); } } else if ("value" in desc && desc.writable) { desc.value = value; } else { var setter = desc.set; if (setter !== undefined) { setter.call(receiver, value); } } return value; };
-
-var _get = function get(object, property, receiver) { if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { return get(parent, property, receiver); } } else if ("value" in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } };
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-/* Exported function extends a base class with SelectionInView. */
-exports.default = function (base) {
-
- /**
- * Mixin which scrolls a container to ensure that a newly-selected item is
- * visible to the user.
- *
- * When the selected item in a list-like component changes, it's easier for
- * the to confirm that the selection has changed to an appropriate item if the
- * user can actually see that item.
- *
- * This mixin expects a `selectedItem` property to be set when the selection
- * changes. You can supply that yourself, or use
- * [SingleSelectionMixin](SingleSelectionMixin.md).
- */
- var SelectionInView = function (_base) {
- _inherits(SelectionInView, _base);
-
- function SelectionInView() {
- _classCallCheck(this, SelectionInView);
-
- return _possibleConstructorReturn(this, (SelectionInView.__proto__ || Object.getPrototypeOf(SelectionInView)).apply(this, arguments));
- }
-
- _createClass(SelectionInView, [{
- key: 'connectedCallback',
- value: function connectedCallback() {
- if (_get(SelectionInView.prototype.__proto__ || Object.getPrototypeOf(SelectionInView.prototype), 'connectedCallback', this)) {
- _get(SelectionInView.prototype.__proto__ || Object.getPrototypeOf(SelectionInView.prototype), 'connectedCallback', this).call(this);
- }
- var selectedItem = this.selectedItem;
- if (selectedItem) {
- this.scrollItemIntoView(selectedItem);
- }
- }
- }, {
- key: 'scrollItemIntoView',
-
-
- /**
- * Scroll the given element completely into view, minimizing the degree of
- * scrolling performed.
- *
- * Blink has a `scrollIntoViewIfNeeded()` function that does something
- * similar, but unfortunately it's non-standard, and in any event often ends
- * up scrolling more than is absolutely necessary.
- *
- * @param {HTMLElement} item - the item to scroll into view.
- */
- value: function scrollItemIntoView(item) {
- if (_get(SelectionInView.prototype.__proto__ || Object.getPrototypeOf(SelectionInView.prototype), 'scrollItemIntoView', this)) {
- _get(SelectionInView.prototype.__proto__ || Object.getPrototypeOf(SelectionInView.prototype), 'scrollItemIntoView', this).call(this);
- }
- // Get the relative position of the item with respect to the top of the
- // list's scrollable canvas. An item at the top of the list will have a
- // elementTop of 0.
-
- var scrollTarget = this.scrollTarget;
- var elementTop = item.offsetTop - scrollTarget.offsetTop - scrollTarget.clientTop;
- var elementBottom = elementTop + item.offsetHeight;
- // Determine the bottom of the scrollable canvas.
- var scrollBottom = scrollTarget.scrollTop + scrollTarget.clientHeight;
- if (elementBottom > scrollBottom) {
- // Scroll up until item is entirely visible.
- scrollTarget.scrollTop += elementBottom - scrollBottom;
- } else if (elementTop < scrollTarget.scrollTop) {
- // Scroll down until item is entirely visible.
- scrollTarget.scrollTop = elementTop;
- }
- }
-
- /**
- * The element that should be scrolled to bring an item into view.
- *
- * The default value of this property is the element itself.
- *
- * @type {HTMLElement}
- */
-
- }, {
- key: 'selectedItem',
- get: function get() {
- return _get(SelectionInView.prototype.__proto__ || Object.getPrototypeOf(SelectionInView.prototype), 'selectedItem', this);
- },
- set: function set(item) {
- if ('selectedItem' in base.prototype) {
- _set(SelectionInView.prototype.__proto__ || Object.getPrototypeOf(SelectionInView.prototype), 'selectedItem', item, this);
- }
- if (item) {
- // Keep the selected item in view.
- this.scrollItemIntoView(item);
- }
- }
- }, {
- key: 'scrollTarget',
- get: function get() {
- // Prefer base result.
- return 'scrollTarget' in base.prototype ? _get(SelectionInView.prototype.__proto__ || Object.getPrototypeOf(SelectionInView.prototype), 'scrollTarget', this) : this;
- },
- set: function set(element) {
- if ('scrollTarget' in base.prototype) {
- _set(SelectionInView.prototype.__proto__ || Object.getPrototypeOf(SelectionInView.prototype), 'scrollTarget', element, this);
- }
- }
- }]);
-
- return SelectionInView;
- }(base);
-
- return SelectionInView;
-};
-
-},{}],22:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-/* Exported function extends a base class with ShadowElementReferences. */
-exports.default = function (base) {
-
- /**
- * Mixin to create references to elements in a component's Shadow DOM subtree.
- *
- * This adds a member on the component called `this.$` that can be used to
- * reference shadow elements with IDs. E.g., if component's shadow contains an
- * element ``, then this mixin will create a member
- * `this.$.foo` that points to that button.
- *
- * Such references simplify a component's access to its own elements. In
- * exchange, this mixin trades off a one-time cost of querying all elements in
- * the shadow tree instead of paying an ongoing cost to query for an element
- * each time the component wants to inspect or manipulate it.
- *
- * This mixin expects the component to define a Shadow DOM subtree. You can
- * create that tree yourself, or make use of
- * [ShadowTemplateMixin](ShadowTemplateMixin.md).
- *
- * This mixin is inspired by Polymer's [automatic
- * node finding](https://www.polymer-project.org/1.0/docs/devguide/local-dom.html#node-finding)
- * feature.
- */
- var ShadowElementReferences = function (_base) {
- _inherits(ShadowElementReferences, _base);
-
- function ShadowElementReferences() {
- _classCallCheck(this, ShadowElementReferences);
-
- var _this = _possibleConstructorReturn(this, (ShadowElementReferences.__proto__ || Object.getPrototypeOf(ShadowElementReferences)).call(this));
-
- if (_this.shadowRoot) {
- // Look for elements in the shadow subtree that have id attributes.
- // An alternatively implementation of this mixin would be to just define
- // a this.$ getter that lazily does this search the first time someone
- // tries to access this.$. That might introduce some complexity – if the
- // the tree changed after it was first populated, the result of
- // searching for a node might be somewhat unpredictable.
- _this.$ = {};
- var nodesWithIds = _this.shadowRoot.querySelectorAll('[id]');
- [].forEach.call(nodesWithIds, function (node) {
- var id = node.getAttribute('id');
- _this.$[id] = node;
- });
- }
- return _this;
- }
-
- /**
- * The collection of references to the elements with IDs in a component's
- * Shadow DOM subtree.
- *
- * @type {object}
- * @member $
- */
-
-
- return ShadowElementReferences;
- }(base);
-
- return ShadowElementReferences;
-};
-
-},{}],23:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _symbols = require('../src/symbols');
-
-var _symbols2 = _interopRequireDefault(_symbols);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-/* Exported function extends a base class with ShadowTemplate. */
-exports.default = function (base) {
-
- /**
- * Mixin for stamping a template into a Shadow DOM subtree upon component
- * instantiation.
- *
- * To use this mixin, define a `template` property as a string or HTML
- * `` element:
- *
- * class MyElement extends ShadowTemplateMixin(HTMLElement) {
- * get [symbols.template]() {
- * return `Hello, world .`;
- * }
- * }
- *
- * When your component class is instantiated, a shadow root will be created on
- * the instance, and the contents of the template will be cloned into the
- * shadow root. If your component does not define a `template` property, this
- * mixin has no effect.
- *
- * For the time being, this extension retains support for Shadow DOM v0. That
- * will eventually be deprecated as browsers (and the Shadow DOM polyfill)
- * implement Shadow DOM v1.
- */
- var ShadowTemplate = function (_base) {
- _inherits(ShadowTemplate, _base);
-
- /*
- * If the component defines a template, a shadow root will be created on the
- * component instance, and the template stamped into it.
- */
- function ShadowTemplate() {
- _classCallCheck(this, ShadowTemplate);
-
- var _this = _possibleConstructorReturn(this, (ShadowTemplate.__proto__ || Object.getPrototypeOf(ShadowTemplate)).call(this));
-
- var template = _this[_symbols2.default.template];
- // TODO: Save the processed template with the component's class prototype
- // so it doesn't need to be processed with every instantiation.
- if (template) {
-
- if (typeof template === 'string') {
- // Upgrade plain string to real template.
- template = createTemplateWithInnerHTML(template);
- }
-
- if (window.ShadowDOMPolyfill) {
- shimTemplateStyles(template, _this.localName);
- }
-
- var root = _this.attachShadow({ mode: 'open' });
- var clone = document.importNode(template.content, true);
- root.appendChild(clone);
- }
- return _this;
- }
-
- return ShadowTemplate;
- }(base);
-
- return ShadowTemplate;
-};
-
-// Convert a plain string of HTML into a real template element.
-
-
-function createTemplateWithInnerHTML(innerHTML) {
- var template = document.createElement('template');
- // REVIEW: Is there an easier way to do this?
- // We'd like to just set innerHTML on the template content, but since it's
- // a DocumentFragment, that doesn't work.
- var div = document.createElement('div');
- div.innerHTML = innerHTML;
- while (div.childNodes.length > 0) {
- template.content.appendChild(div.childNodes[0]);
- }
- return template;
-}
-
-// Invoke basic style shimming with ShadowCSS.
-function shimTemplateStyles(template, tag) {
- window.WebComponents.ShadowCSS.shimStyling(template.content, tag);
-}
-
-},{"../src/symbols":32}],24:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
-
-var _get = function get(object, property, receiver) { if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { return get(parent, property, receiver); } } else if ("value" in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } };
-
-var _set = function set(object, property, value, receiver) { var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent !== null) { set(parent, property, value, receiver); } } else if ("value" in desc && desc.writable) { desc.value = value; } else { var setter = desc.set; if (setter !== undefined) { setter.call(receiver, value); } } return value; };
-
-var _createSymbol = require('./createSymbol');
-
-var _createSymbol2 = _interopRequireDefault(_createSymbol);
-
-var _symbols = require('./symbols');
-
-var _symbols2 = _interopRequireDefault(_symbols);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-// Symbols for private data members on an element.
-var canSelectNextSymbol = (0, _createSymbol2.default)('canSelectNext');
-var canSelectPreviousSymbol = (0, _createSymbol2.default)('canSelectPrevious');
-var selectionRequiredSymbol = (0, _createSymbol2.default)('selectionRequired');
-var selectionWrapsSymbol = (0, _createSymbol2.default)('selectionWraps');
-
-// We want to expose both selectedIndex and selectedItem as independent
-// properties but keep them in sync. This allows a component user to reference
-// the selection by whatever means is most natural for their situation.
-//
-// To efficiently keep these properties in sync, we track "external" and
-// "internal" references for each property:
-//
-// The external index or item is the one we report to the outside world when
-// asked for selection. When handling a change to index or item, we update the
-// external reference as soon as possible, so that if anyone immediately asks
-// for the current selection, they will receive a stable answer.
-//
-// The internal index or item tracks whichever index or item last received the
-// full set of processing. Processing includes raising a change event for the
-// new value. Once we've begun that processing, we store the new value as the
-// internal value to indicate we've handled it.
-//
-var externalSelectedIndexSymbol = (0, _createSymbol2.default)('externalSelectedIndex');
-var externalSelectedItemSymbol = (0, _createSymbol2.default)('externalSelectedItem');
-var internalSelectedIndexSymbol = (0, _createSymbol2.default)('internalSelectedIndex');
-var internalSelectedItemSymbol = (0, _createSymbol2.default)('internalSelectedItem');
-
-/* Exported function extends a base class with SingleSelection. */
-
-exports.default = function (base) {
-
- /**
- * Mixin which manages single-selection semantics for items in a list.
- *
- * This mixin expects a component to provide an `items` Array or NodeList of
- * all elements in the list. A standard way to do that with is the
- * [ContentItemsMixin](ContentItemsMixin.md), which takes a component's
- * content (typically its distributed children) as the set of list items; see
- * that mixin for details.
- *
- * This mixin tracks a single selected item in the list, and provides means to
- * get and set that state by item position (`selectedIndex`) or item identity
- * (`selectedItem`). The selection can be moved in the list via the methods
- * `selectFirst`, `selectLast`, `selectNext`, and `selectPrevious`.
- *
- * This mixin does not produce any user-visible effects to represent
- * selection. Other mixins, such as
- * [SelectionAriaActiveMixin](SelectionAriaActiveMixin.md),
- * [SelectionHighlightMixin](SelectionHighlightMixin.md) and
- * [SelectionInViewMixin](SelectionInViewMixin.md), modify the selected item
- * in common ways to let the user know a given item is selected or not
- * selected.
- */
- var SingleSelection = function (_base) {
- _inherits(SingleSelection, _base);
-
- function SingleSelection() {
- _classCallCheck(this, SingleSelection);
-
- // Set defaults.
- var _this = _possibleConstructorReturn(this, (SingleSelection.__proto__ || Object.getPrototypeOf(SingleSelection)).call(this));
-
- if (typeof _this.selectionRequired === 'undefined') {
- _this.selectionRequired = _this[_symbols2.default.defaults].selectionRequired;
- }
- if (typeof _this.selectionWraps === 'undefined') {
- _this.selectionWraps = _this[_symbols2.default.defaults].selectionWraps;
- }
- return _this;
- }
-
- /**
- * True if the selection can be moved to the next item, false if not (the
- * selected item is the last item in the list).
- *
- * @type {boolean}
- */
-
-
- _createClass(SingleSelection, [{
- key: _symbols2.default.itemAdded,
-
-
- /**
- * Handle a new item being added to the list.
- *
- * The default implementation of this method simply sets the item's
- * selection state to false.
- *
- * @param {HTMLElement} item - the item being added
- */
- value: function value(item) {
- if (_get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), _symbols2.default.itemAdded, this)) {
- _get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), _symbols2.default.itemAdded, this).call(this, item);
- }
- this[_symbols2.default.itemSelected](item, item === this.selectedItem);
- }
- }, {
- key: _symbols2.default.itemsChanged,
- value: function value() {
- if (_get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), _symbols2.default.itemsChanged, this)) {
- _get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), _symbols2.default.itemsChanged, this).call(this);
- }
-
- // In case selected item changed position or was removed.
- trackSelectedItem(this);
-
- // In case the change in items affected which navigations are possible.
- updatePossibleNavigations(this);
- }
-
- /**
- * Apply the indicate selection state to the item.
- *
- * The default implementation of this method does nothing. User-visible
- * effects will typically be handled by other mixins.
- *
- * @param {HTMLElement} item - the item being selected/deselected
- * @param {boolean} selected - true if the item is selected, false if not
- */
-
- }, {
- key: _symbols2.default.itemSelected,
- value: function value(item, selected) {
- if (_get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), _symbols2.default.itemSelected, this)) {
- _get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), _symbols2.default.itemSelected, this).call(this, item, selected);
- }
- }
-
- /**
- * The index of the item which is currently selected.
- *
- * A `selectedIndex` of -1 indicates there is no selection. Setting this
- * property to -1 will remove any existing selection.
- *
- * @type {number}
- */
-
- }, {
- key: 'selectFirst',
-
-
- /**
- * Select the first item in the list.
- */
- value: function selectFirst() {
- if (_get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), 'selectFirst', this)) {
- _get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), 'selectFirst', this).call(this);
- }
- return selectIndex(this, 0);
- }
-
- /**
- * True if the list should always have a selection (if it has items).
- *
- * @type {boolean}
- * @default false
- */
-
- }, {
- key: 'selectLast',
-
-
- /**
- * Select the last item in the list.
- */
- value: function selectLast() {
- if (_get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), 'selectLast', this)) {
- _get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), 'selectLast', this).call(this);
- }
- return selectIndex(this, this.items.length - 1);
- }
-
- /**
- * Select the next item in the list.
- */
-
- }, {
- key: 'selectNext',
- value: function selectNext() {
- if (_get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), 'selectNext', this)) {
- _get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), 'selectNext', this).call(this);
- }
- return selectIndex(this, this.selectedIndex + 1);
- }
-
- /**
- * Select the previous item in the list.
- *
- * If the list has no selection, the last item will be selected.
- */
-
- }, {
- key: 'selectPrevious',
- value: function selectPrevious() {
- if (_get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), 'selectPrevious', this)) {
- _get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), 'selectPrevious', this).call(this);
- }
- var newIndex = this.selectedIndex < 0 ? this.items.length - 1 : // No selection yet; select last item.
- this.selectedIndex - 1;
- return selectIndex(this, newIndex);
- }
-
- /**
- * Fires when the selectedItem property changes.
- *
- * @memberof SingleSelection
- * @event selected-item-changed
- * @param {HTMLElement} detail.selectedItem The new selected item.
- * @param {HTMLElement} detail.previousItem The previously selected item.
- */
-
- /**
- * Fires when the selectedIndex property changes.
- *
- * @memberof SingleSelection
- * @event selected-index-changed
- * @param {number} detail.selectedIndex The new selected index.
- */
-
- }, {
- key: 'canSelectNext',
- get: function get() {
- return this[canSelectNextSymbol];
- },
- set: function set(canSelectNext) {
- var previousCanSelectNext = this[canSelectNextSymbol];
- this[canSelectNextSymbol] = canSelectNext;
- if ('canSelectNext' in base.prototype) {
- _set(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), 'canSelectNext', canSelectNext, this);
- }
- if (canSelectNext !== previousCanSelectNext) {
- this.dispatchEvent(new CustomEvent('can-select-next-changed'));
- }
- }
-
- /**
- * True if the selection can be moved to the previous item, false if not
- * (the selected item is the first one in the list).
- *
- * @type {boolean}
- */
-
- }, {
- key: 'canSelectPrevious',
- get: function get() {
- return this[canSelectPreviousSymbol];
- },
- set: function set(canSelectPrevious) {
- var previousCanSelectPrevious = this[canSelectPreviousSymbol];
- this[canSelectPreviousSymbol] = canSelectPrevious;
- if ('canSelectPrevious' in base.prototype) {
- _set(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), 'canSelectPrevious', canSelectPrevious, this);
- }
- if (canSelectPrevious !== previousCanSelectPrevious) {
- this.dispatchEvent(new CustomEvent('can-select-previous-changed'));
- }
- }
- }, {
- key: _symbols2.default.defaults,
- get: function get() {
- var defaults = _get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), _symbols2.default.defaults, this) || {};
- defaults.selectionRequired = false;
- defaults.selectionWraps = false;
- return defaults;
- }
- }, {
- key: 'selectedIndex',
- get: function get() {
- return this[externalSelectedIndexSymbol] != null ? this[externalSelectedIndexSymbol] : -1;
- },
- set: function set(index) {
- // See notes at top about internal vs. external copies of this property.
- var previousSelectedIndex = this[internalSelectedIndexSymbol];
- var item = void 0;
- if (index !== this[externalSelectedIndexSymbol]) {
- // Store the new index and the corresponding item.
- var items = this.items;
- var hasItems = items && items.length > 0;
- if (!(hasItems && index >= 0 && index < items.length)) {
- index = -1; // No item at that index.
- }
- this[externalSelectedIndexSymbol] = index;
- item = hasItems && index >= 0 ? items[index] : null;
- this[externalSelectedItemSymbol] = item;
- } else {
- item = this[externalSelectedItemSymbol];
- }
-
- // Now let super do any work.
- if ('selectedIndex' in base.prototype) {
- _set(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), 'selectedIndex', index, this);
- }
-
- if (index !== previousSelectedIndex) {
- // The selected index changed.
- this[internalSelectedIndexSymbol] = index;
-
- var event = new CustomEvent('selected-index-changed', {
- detail: {
- selectedIndex: index,
- value: index // for Polymer binding. TODO: Verify still necessary
- }
- });
- this.dispatchEvent(event);
- }
-
- if (this[internalSelectedItemSymbol] !== item) {
- // Update selectedItem property so it can have its own effects.
- this.selectedItem = item;
- }
- }
-
- /**
- * The currently selected item, or null if there is no selection.
- *
- * Setting this property to null deselects any currently-selected item.
- * Setting this property to an object that is not in the list has no effect.
- *
- * TODO: Even if selectionRequired, can still explicitly set selectedItem to null.
- * TODO: If selectionRequired, leave selection alone?
- *
- * @type {object}
- */
-
- }, {
- key: 'selectedItem',
- get: function get() {
- return this[externalSelectedItemSymbol] || null;
- },
- set: function set(item) {
- // See notes at top about internal vs. external copies of this property.
- var previousSelectedItem = this[internalSelectedItemSymbol];
- var index = void 0;
- if (item !== this[externalSelectedItemSymbol]) {
- // Store item and look up corresponding index.
- var items = this.items;
- var hasItems = items && items.length > 0;
- index = hasItems ? Array.prototype.indexOf.call(items, item) : -1;
- this[externalSelectedIndexSymbol] = index;
- if (index < 0) {
- item = null; // The indicated item isn't actually in `items`.
- }
- this[externalSelectedItemSymbol] = item;
- } else {
- index = this[externalSelectedIndexSymbol];
- }
-
- // Now let super do any work.
- if ('selectedItem' in base.prototype) {
- _set(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), 'selectedItem', item, this);
- }
-
- if (item !== previousSelectedItem) {
- // The selected item changed.
- this[internalSelectedItemSymbol] = item;
-
- if (previousSelectedItem) {
- // Update selection state of old item.
- this[_symbols2.default.itemSelected](previousSelectedItem, false);
- }
- if (item) {
- // Update selection state to new item.
- this[_symbols2.default.itemSelected](item, true);
- }
-
- updatePossibleNavigations(this);
-
- var event = new CustomEvent('selected-item-changed', {
- detail: {
- selectedItem: item,
- value: item // for Polymer binding
- }
- });
- this.dispatchEvent(event);
- }
-
- if (this[internalSelectedIndexSymbol] !== index) {
- // Update selectedIndex property so it can have its own effects.
- this.selectedIndex = index;
- }
- }
- }, {
- key: 'selectionRequired',
- get: function get() {
- return this[selectionRequiredSymbol];
- },
- set: function set(selectionRequired) {
- this[selectionRequiredSymbol] = selectionRequired;
- if ('selectionRequired' in base.prototype) {
- _set(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), 'selectionRequired', selectionRequired, this);
- }
- trackSelectedItem(this);
- }
-
- /**
- * True if selection navigations wrap from last to first, and vice versa.
- *
- * @type {boolean}
- * @default false
- */
-
- }, {
- key: 'selectionWraps',
- get: function get() {
- return this[selectionWrapsSymbol];
- },
- set: function set(value) {
- this[selectionWrapsSymbol] = String(value) === 'true';
- if ('selectionWraps' in base.prototype) {
- _set(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), 'selectionWraps', value, this);
- }
- updatePossibleNavigations(this);
- }
- }]);
-
- return SingleSelection;
- }(base);
-
- return SingleSelection;
-};
-
-// Ensure the given index is within bounds, and select it if it's not already
-// selected.
-
-
-function selectIndex(element, index) {
- var count = element.items.length;
-
- var boundedIndex = element.selectionWraps ?
- // JavaScript mod doesn't handle negative numbers the way we want to wrap.
- // See http://stackoverflow.com/a/18618250/76472
- (index % count + count) % count :
-
- // Keep index within bounds of array.
- Math.max(Math.min(index, count - 1), 0);
-
- var previousIndex = element.selectedIndex;
- if (previousIndex !== boundedIndex) {
- element.selectedIndex = boundedIndex;
- return true;
- } else {
- return false;
- }
-}
-
-// Following a change in the set of items, or in the value of the
-// `selectionRequired` property, reacquire the selected item. If it's moved,
-// update `selectedIndex`. If it's been removed, and a selection is required,
-// try to select another item.
-function trackSelectedItem(element) {
-
- var items = element.items;
- var itemCount = items ? items.length : 0;
-
- var previousSelectedItem = element.selectedItem;
- if (!previousSelectedItem) {
- // No item was previously selected.
- if (element.selectionRequired) {
- // Select the first item by default.
- element.selectedIndex = 0;
- }
- } else if (itemCount === 0) {
- // We've lost the selection, and there's nothing left to select.
- element.selectedItem = null;
- } else {
- // Try to find the previously-selected item in the current set of items.
- var indexInCurrentItems = Array.prototype.indexOf.call(items, previousSelectedItem);
- var previousSelectedIndex = element.selectedIndex;
- if (indexInCurrentItems < 0) {
- // Previously-selected item was removed from the items.
- // Select the item at the same index (if it exists) or as close as possible.
- var newSelectedIndex = Math.min(previousSelectedIndex, itemCount - 1);
- // Select by item, since index may be the same, and we want to raise the
- // selected-item-changed event.
- element.selectedItem = items[newSelectedIndex];
- } else if (indexInCurrentItems !== previousSelectedIndex) {
- // Previously-selected item still there, but changed position.
- element.selectedIndex = indexInCurrentItems;
- }
- }
-}
-
-// Following a change in selection, report whether it's now possible to
-// go next/previous from the given index.
-function updatePossibleNavigations(element) {
- var canSelectNext = void 0;
- var canSelectPrevious = void 0;
- var items = element.items;
- if (items == null || items.length === 0) {
- // No items to select.
- canSelectNext = false;
- canSelectPrevious = false;
- }if (element.selectionWraps) {
- // Since there are items, can always go next/previous.
- canSelectNext = true;
- canSelectPrevious = true;
- } else {
- var index = element.selectedIndex;
- if (index < 0 && items.length > 0) {
- // Special case. If there are items but no selection, declare that it's
- // always possible to go next/previous to create a selection.
- canSelectNext = true;
- canSelectPrevious = true;
- } else {
- // Normal case: we have an index in a list that has items.
- canSelectPrevious = index > 0;
- canSelectNext = index < items.length - 1;
- }
- }
- if (element.canSelectNext !== canSelectNext) {
- element.canSelectNext = canSelectNext;
- }
- if (element.canSelectPrevious !== canSelectPrevious) {
- element.canSelectPrevious = canSelectPrevious;
- }
-}
-
-},{"./createSymbol":28,"./symbols":32}],25:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
-
-var _set = function set(object, property, value, receiver) { var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent !== null) { set(parent, property, value, receiver); } } else if ("value" in desc && desc.writable) { desc.value = value; } else { var setter = desc.set; if (setter !== undefined) { setter.call(receiver, value); } } return value; };
-
-var _get = function get(object, property, receiver) { if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { return get(parent, property, receiver); } } else if ("value" in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } };
-
-var _createSymbol = require('./createSymbol');
-
-var _createSymbol2 = _interopRequireDefault(_createSymbol);
-
-var _symbols = require('./symbols');
-
-var _symbols2 = _interopRequireDefault(_symbols);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-// Symbols for private data members on an element.
-var deltaXSymbol = (0, _createSymbol2.default)('deltaX');
-var deltaYSymbol = (0, _createSymbol2.default)('deltaY');
-var multiTouchSymbol = (0, _createSymbol2.default)('multiTouch');
-var previousXSymbol = (0, _createSymbol2.default)('previousX');
-var previousYSymbol = (0, _createSymbol2.default)('previousY');
-var startXSymbol = (0, _createSymbol2.default)('startX');
-var travelFractionSymbol = (0, _createSymbol2.default)('travelFraction');
-
-/* Exported function extends a base class with SwipeDirection. */
-
-exports.default = function (base) {
-
- /**
- * Mixin which maps touch gestures (swipe left, swipe right) to direction
- * semantics (go right, go left).
- *
- * By default, this mixin presents no user-visible effects; it just indicates
- * a direction in which the user is currently swiping or has finished swiping.
- * To map the direction to a change in selection, use
- * [DirectionSelectionMixin](DirectionSelectionMixin.md).
- */
- var SwipeDirection = function (_base) {
- _inherits(SwipeDirection, _base);
-
- function SwipeDirection() {
- _classCallCheck(this, SwipeDirection);
-
- var _this = _possibleConstructorReturn(this, (SwipeDirection.__proto__ || Object.getPrototypeOf(SwipeDirection)).call(this));
-
- _this.travelFraction = 0;
-
- // In all touch events, only handle single touches. We don't want to
- // inadvertently do work when the user's trying to pinch-zoom for example.
- // TODO: Even better approach than below would be to ignore touches after
- // the first if the user has already begun a swipe.
- // TODO: Touch events should probably be factored out into its own mixin.
- if (window.PointerEvent) {
- // Prefer listening to standard pointer events.
- _this.addEventListener('pointerdown', function (event) {
- if (isEventForPenOrPrimaryTouch(event)) {
- touchStart(_this, event.clientX, event.clientY);
- }
- });
- _this.addEventListener('pointermove', function (event) {
- if (isEventForPenOrPrimaryTouch(event)) {
- var handled = touchMove(_this, event.clientX, event.clientY);
- if (handled) {
- event.preventDefault();
- }
- }
- });
- _this.addEventListener('pointerup', function (event) {
- if (isEventForPenOrPrimaryTouch(event)) {
- touchEnd(_this, event.clientX, event.clientY);
- }
- });
- } else {
- // Pointer events not supported -- listen to older touch events.
- _this.addEventListener('touchstart', function (event) {
- if (_this[multiTouchSymbol]) {
- return;
- } else if (event.touches.length === 1) {
- var clientX = event.changedTouches[0].clientX;
- var clientY = event.changedTouches[0].clientY;
- touchStart(_this, clientX, clientY);
- } else {
- _this[multiTouchSymbol] = true;
- }
- });
- _this.addEventListener('touchmove', function (event) {
- if (!_this[multiTouchSymbol] && event.touches.length === 1) {
- var clientX = event.changedTouches[0].clientX;
- var clientY = event.changedTouches[0].clientY;
- var handled = touchMove(_this, clientX, clientY);
- if (handled) {
- event.preventDefault();
- }
- }
- });
- _this.addEventListener('touchend', function (event) {
- if (event.touches.length === 0) {
- // All touches removed; gesture is complete.
- if (!_this[multiTouchSymbol]) {
- // Single-touch swipe has finished.
- var clientX = event.changedTouches[0].clientX;
- var clientY = event.changedTouches[0].clientY;
- touchEnd(_this, clientX, clientY);
- }
- _this[multiTouchSymbol] = false;
- }
- });
- }
- return _this;
- }
-
- _createClass(SwipeDirection, [{
- key: 'connectedCallback',
- value: function connectedCallback() {
- if (_get(SwipeDirection.prototype.__proto__ || Object.getPrototypeOf(SwipeDirection.prototype), 'connectedCallback', this)) {
- _get(SwipeDirection.prototype.__proto__ || Object.getPrototypeOf(SwipeDirection.prototype), 'connectedCallback', this).call(this);
- }
-
- // For the component to receive PointerEvents in IE/Edge, we need to set
- // touch-action: none. Only make this change if touch-action is currently
- // the default value ("auto"), in case the developer knows better than we
- // do what they want in their particular context.
- if (getComputedStyle(this).touchAction === 'auto') {
- this.style.touchAction = 'none';
- }
- }
-
- // Default implementation.
-
- }, {
- key: _symbols2.default.goLeft,
-
-
- /**
- * Invoked when the user wants to go/navigate left.
- * The default implementation of this method does nothing.
- */
- value: function value() {
- if (_get(SwipeDirection.prototype.__proto__ || Object.getPrototypeOf(SwipeDirection.prototype), _symbols2.default.goLeft, this)) {
- return _get(SwipeDirection.prototype.__proto__ || Object.getPrototypeOf(SwipeDirection.prototype), _symbols2.default.goLeft, this).call(this);
- }
- }
-
- /**
- * Invoked when the user wants to go/navigate right.
- * The default implementation of this method does nothing.
- */
-
- }, {
- key: _symbols2.default.goRight,
- value: function value() {
- if (_get(SwipeDirection.prototype.__proto__ || Object.getPrototypeOf(SwipeDirection.prototype), _symbols2.default.goRight, this)) {
- return _get(SwipeDirection.prototype.__proto__ || Object.getPrototypeOf(SwipeDirection.prototype), _symbols2.default.goRight, this).call(this);
- }
- }
-
- /**
- * The distance the first touchpoint has traveled since the beginning of a
- * drag, expressed as a fraction of the element's width.
- *
- * @type number
- */
-
- }, {
- key: _symbols2.default.dragging,
- get: function get() {
- return _get(SwipeDirection.prototype.__proto__ || Object.getPrototypeOf(SwipeDirection.prototype), _symbols2.default.dragging, this);
- },
- set: function set(value) {
- if (_symbols2.default.dragging in base.prototype) {
- _set(SwipeDirection.prototype.__proto__ || Object.getPrototypeOf(SwipeDirection.prototype), _symbols2.default.dragging, value, this);
- }
- }
- }, {
- key: 'travelFraction',
- get: function get() {
- return this[travelFractionSymbol];
- },
- set: function set(value) {
- this[travelFractionSymbol] = value;
- if ('travelFraction' in base.prototype) {
- _set(SwipeDirection.prototype.__proto__ || Object.getPrototypeOf(SwipeDirection.prototype), 'travelFraction', value, this);
- }
- }
- }]);
-
- return SwipeDirection;
- }(base);
-
- return SwipeDirection;
-};
-
-// Return true if the pointer event is for the pen, or the primary touch point.
-
-
-function isEventForPenOrPrimaryTouch(event) {
- return event.pointerType === 'pen' || event.pointerType === 'touch' && event.isPrimary;
-}
-
-/*
- * Invoked when the user has finished a touch operation.
- */
-function touchEnd(element, clientX, clientY) {
- element[_symbols2.default.dragging] = false;
- if (element[deltaXSymbol] >= 20) {
- // Finished going right at high speed.
- element[_symbols2.default.goLeft]();
- } else if (element[deltaXSymbol] <= -20) {
- // Finished going left at high speed.
- element[_symbols2.default.goRight]();
- } else {
- // Finished at low speed.
- trackTo(element, clientX);
- var travelFraction = element.travelFraction;
- if (travelFraction >= 0.5) {
- element[_symbols2.default.goRight]();
- } else if (travelFraction <= -0.5) {
- element[_symbols2.default.goLeft]();
- }
- }
- element.travelFraction = 0;
- element[deltaXSymbol] = null;
- element[deltaYSymbol] = null;
-}
-
-/*
- * Invoked when the user has moved during a touch operation.
- */
-function touchMove(element, clientX, clientY) {
-
- element[deltaXSymbol] = clientX - element[previousXSymbol];
- element[deltaYSymbol] = clientY - element[previousYSymbol];
- element[previousXSymbol] = clientX;
- element[previousYSymbol] = clientY;
- if (Math.abs(element[deltaXSymbol]) > Math.abs(element[deltaYSymbol])) {
- // Move was mostly horizontal.
- trackTo(element, clientX);
- // Indicate that the event was handled. It'd be nicer if we didn't have
- // to do this so that, e.g., a user could be swiping left and right
- // while simultaneously scrolling up and down. (Native touch apps can do
- // that.) However, Mobile Safari wants to handle swipe events near the
- // page and interpret them as navigations. To avoid having a horiziontal
- // swipe misintepreted as a navigation, we indicate that we've handled
- // the event, and prevent default behavior.
- return true;
- } else {
- // Move was mostly vertical.
- return false; // Not handled
- }
-}
-
-/*
- * Invoked when the user has begun a touch operation.
- */
-function touchStart(element, clientX, clientY) {
- element[_symbols2.default.dragging] = true;
- element[startXSymbol] = clientX;
- element[previousXSymbol] = clientX;
- element[previousYSymbol] = clientY;
- element[deltaXSymbol] = 0;
- element[deltaYSymbol] = 0;
-}
-
-function trackTo(element, x) {
- var width = element.offsetWidth;
- var dragDistance = element[startXSymbol] - x;
- var fraction = width > 0 ? dragDistance / width : 0;
- element.travelFraction = fraction;
-}
-
-},{"./createSymbol":28,"./symbols":32}],26:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
-
-var _set = function set(object, property, value, receiver) { var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent !== null) { set(parent, property, value, receiver); } } else if ("value" in desc && desc.writable) { desc.value = value; } else { var setter = desc.set; if (setter !== undefined) { setter.call(receiver, value); } } return value; };
-
-var _get = function get(object, property, receiver) { if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { return get(parent, property, receiver); } } else if ("value" in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } };
-
-var _createSymbol = require('./createSymbol');
-
-var _createSymbol2 = _interopRequireDefault(_createSymbol);
-
-var _symbols = require('./symbols');
-
-var _symbols2 = _interopRequireDefault(_symbols);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-var playingSymbol = (0, _createSymbol2.default)('playing');
-var selectionTimerDurationSymbol = (0, _createSymbol2.default)('selectionTimerDuration');
-var timerTimeoutSymbol = (0, _createSymbol2.default)('timerTimeout');
-
-/* Exported function extends a base class with TimerSelection. */
-
-exports.default = function (base) {
-
- /**
- * Mixin which provides for automatic timed changes in selection.
- *
- * This mixin is useful for creating slideshow-like elements such as
- * [basic-slideshow](../packages/basic-slideshow) and
- * [basic-slideshow-with-controls](../packages/basic-slideshow-with-controls).
- *
- * Typical usage:
- *
- * class CarouselWithTimer extends TimerSelectionMixin(Carousel) {}
- * customElements.define('carousel-with-arrows', CarouselWithTimer);
- *
- * This mixin expects the component to define an `items` property, as well as
- * `selectFirst` and `selectNext` methods. You can implement those yourself,
- * or use [ContentItemsMixin](ContentItemsMixin.md) and
- * [SingleSelectionMixin](SingleSelectionMixin.md).
- */
- var TimerSelection = function (_base) {
- _inherits(TimerSelection, _base);
-
- function TimerSelection() {
- _classCallCheck(this, TimerSelection);
-
- // Set defaults.
- var _this = _possibleConstructorReturn(this, (TimerSelection.__proto__ || Object.getPrototypeOf(TimerSelection)).call(this));
-
- if (typeof _this.playing === 'undefined') {
- _this.playing = _this[_symbols2.default.defaults].playing;
- }
- if (typeof _this.selectionTimerDuration === 'undefined') {
- _this.selectionTimerDuration = _this[_symbols2.default.defaults].selectionTimerDuration;
- }
- return _this;
- }
-
- _createClass(TimerSelection, [{
- key: 'contentChanged',
- value: function contentChanged() {
- if (_get(TimerSelection.prototype.__proto__ || Object.getPrototypeOf(TimerSelection.prototype), 'contentChanged', this)) {
- _get(TimerSelection.prototype.__proto__ || Object.getPrototypeOf(TimerSelection.prototype), 'contentChanged', this).call(this);
- }
- restartTimer(this);
- }
- }, {
- key: 'play',
-
-
- /**
- * Begin automatic progression of the selection.
- */
- value: function play() {
- if (_get(TimerSelection.prototype.__proto__ || Object.getPrototypeOf(TimerSelection.prototype), 'play', this)) {
- _get(TimerSelection.prototype.__proto__ || Object.getPrototypeOf(TimerSelection.prototype), 'play', this).call(this);
- }
- startTimer(this);
- this[playingSymbol] = true;
- }
-
- /**
- * Pause automatic progression of the selection.
- */
-
- }, {
- key: 'pause',
- value: function pause() {
- if (_get(TimerSelection.prototype.__proto__ || Object.getPrototypeOf(TimerSelection.prototype), 'pause', this)) {
- _get(TimerSelection.prototype.__proto__ || Object.getPrototypeOf(TimerSelection.prototype), 'pause', this).call(this);
- }
- clearTimer(this);
- this[playingSymbol] = false;
- }
-
- /**
- * True if the selection is being automatically advanced.
- *
- * @type {boolean}
- * @default false
- */
-
- }, {
- key: _symbols2.default.defaults,
- get: function get() {
- var defaults = _get(TimerSelection.prototype.__proto__ || Object.getPrototypeOf(TimerSelection.prototype), _symbols2.default.defaults, this) || {};
- defaults.playing = false;
- defaults.selectionTimerDuration = 1000;
- return defaults;
- }
- }, {
- key: 'playing',
- get: function get() {
- return this[playingSymbol];
- },
- set: function set(playing) {
- var previousPlaying = this[playingSymbol];
- var parsed = String(playing) === 'true'; // Cast to boolean
- if ('playing' in base.prototype) {
- _set(TimerSelection.prototype.__proto__ || Object.getPrototypeOf(TimerSelection.prototype), 'playing', playing, this);
- }
- if (parsed !== previousPlaying) {
- if (playing) {
- this.play();
- } else {
- this.pause();
- }
- }
- }
-
- /*
- * When the selected item changes (because of something this mixin did, or
- * was changed by an outside agent like the user), we wait before advancing
- * to the next item. By triggering the next item this way, we implicitly get
- * a desirable behavior: if the user changes the selection (e.g., in a
- * carousel), we let them see that selection state for a while before
- * advancing the selection ourselves.
- */
-
- }, {
- key: 'selectedItem',
- get: function get() {
- return _get(TimerSelection.prototype.__proto__ || Object.getPrototypeOf(TimerSelection.prototype), 'selectedItem', this);
- },
- set: function set(item) {
- if ('selectedItem' in base.prototype) {
- _set(TimerSelection.prototype.__proto__ || Object.getPrototypeOf(TimerSelection.prototype), 'selectedItem', item, this);
- }
- restartTimer(this);
- }
-
- /**
- * The time in milliseconds that will elapse after the selection changes
- * before the selection will be advanced to the next item in the list.
- *
- * @type {number} - Time in milliseconds
- * @default 1000 (1 second)
- */
-
- }, {
- key: 'selectionTimerDuration',
- get: function get() {
- return this[selectionTimerDurationSymbol];
- },
- set: function set(value) {
- this[selectionTimerDurationSymbol] = parseInt(value);
- if ('selectionTimerDuration' in base.prototype) {
- _set(TimerSelection.prototype.__proto__ || Object.getPrototypeOf(TimerSelection.prototype), 'selectionTimerDuration', value, this);
- }
- }
- }]);
-
- return TimerSelection;
- }(base);
-
- return TimerSelection;
-};
-
-function clearTimer(element) {
- if (element[timerTimeoutSymbol]) {
- clearTimeout(element[timerTimeoutSymbol]);
- element[timerTimeoutSymbol] = null;
- }
-}
-
-function restartTimer(element) {
- clearTimer(element);
- if (element.playing && element.items && element.items.length > 0) {
- startTimer(element);
- }
-}
-
-function startTimer(element) {
- // If play() is called more than once, cancel any existing timer.
- clearTimer(element);
- element[timerTimeoutSymbol] = setTimeout(function () {
- selectNextWithWrap(element);
- }, element.selectionTimerDuration);
-}
-
-// Select the next item, wrapping to first item if necessary.
-function selectNextWithWrap(element) {
- var items = element.items;
- if (items && items.length > 0) {
- if (element.selectedIndex == null || element.selectedIndex === items.length - 1) {
- element.selectFirst();
- } else {
- element.selectNext();
- }
- }
-}
-
-},{"./createSymbol":28,"./symbols":32}],27:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
-
-var _set = function set(object, property, value, receiver) { var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent !== null) { set(parent, property, value, receiver); } } else if ("value" in desc && desc.writable) { desc.value = value; } else { var setter = desc.set; if (setter !== undefined) { setter.call(receiver, value); } } return value; };
-
-var _get = function get(object, property, receiver) { if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { return get(parent, property, receiver); } } else if ("value" in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } };
-
-var _createSymbol = require('../../basic-component-mixins/src/createSymbol');
-
-var _createSymbol2 = _interopRequireDefault(_createSymbol);
-
-var _symbols = require('./symbols');
-
-var _symbols2 = _interopRequireDefault(_symbols);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-// Symbols for private data members on an element.
-var absorbDecelerationSymbol = (0, _createSymbol2.default)('absorbDeceleration');
-var lastDeltaXSymbol = (0, _createSymbol2.default)('lastDeltaX');
-var lastWheelTimeoutSymbol = (0, _createSymbol2.default)('lastWheelTimeout');
-var postNavigateDelayCompleteSymbol = (0, _createSymbol2.default)('postNavigateDelayComplete');
-var wheelDistanceSymbol = (0, _createSymbol2.default)('wheelDistance');
-
-/* Exported function extends a base class with TrackpadDirection. */
-
-exports.default = function (base) {
-
- /**
- * Mixin which maps a horizontal trackpad swipe gestures (or horizontal mouse
- * wheel actions) to direction semantics.
- *
- * You can use this mixin with a mixin like
- * [DirectionSelectionMixin](DirectionSelectionMixin.md) to let the user
- * change the selection with the trackpad or mouse wheel.
- *
- * To respond to the trackpad, we can listen to the DOM's "wheel" events.
- * These events are fired as the user drags their fingers across a trackpad.
- * Unfortunately, browsers are missing a critical event — there is no event
- * when the user *stops* a gestured on the trackpad or mouse wheel.
- *
- * To make things worse, the mainstream browsers continue to generate fake
- * wheel events even after the user has stopped dragging their fingers. These
- * fake events simulate the user gradually slowing down the drag until they
- * come to a smooth stop. In some contexts, these fake wheel events might be
- * helpful, but in trying to supply typical trackpad swipe navigation, these
- * fake events get in the way.
- *
- * This component uses heuristics to work around these problems, but the
- * complex nature of the problem make it extremely difficult to achieve the
- * same degree of trackpad responsiveness possible with native applications.
- */
- var TrackpadDirection = function (_base) {
- _inherits(TrackpadDirection, _base);
-
- function TrackpadDirection() {
- _classCallCheck(this, TrackpadDirection);
-
- var _this = _possibleConstructorReturn(this, (TrackpadDirection.__proto__ || Object.getPrototypeOf(TrackpadDirection)).call(this));
-
- _this.addEventListener('wheel', function (event) {
- var handled = wheel(_this, event);
- if (handled) {
- event.preventDefault();
- }
- });
- resetWheelTracking(_this);
- return _this;
- }
-
- // Default implementation.
-
-
- _createClass(TrackpadDirection, [{
- key: _symbols2.default.goLeft,
-
-
- /**
- * Invoked when the user wants to go/navigate left.
- * The default implementation of this method does nothing.
- */
- value: function value() {
- if (_get(TrackpadDirection.prototype.__proto__ || Object.getPrototypeOf(TrackpadDirection.prototype), _symbols2.default.goLeft, this)) {
- return _get(TrackpadDirection.prototype.__proto__ || Object.getPrototypeOf(TrackpadDirection.prototype), _symbols2.default.goLeft, this).call(this);
- }
- }
-
- /**
- * Invoked when the user wants to go/navigate right.
- * The default implementation of this method does nothing.
- */
-
- }, {
- key: _symbols2.default.goRight,
- value: function value() {
- if (_get(TrackpadDirection.prototype.__proto__ || Object.getPrototypeOf(TrackpadDirection.prototype), _symbols2.default.goRight, this)) {
- return _get(TrackpadDirection.prototype.__proto__ || Object.getPrototypeOf(TrackpadDirection.prototype), _symbols2.default.goRight, this).call(this);
- }
- }
-
- /**
- * The distance the user has moved the first touchpoint since the beginning
- * of a trackpad/wheel operation, expressed as a fraction of the element's
- * width.
- *
- * @type number
- */
-
- }, {
- key: _symbols2.default.dragging,
- get: function get() {
- return _get(TrackpadDirection.prototype.__proto__ || Object.getPrototypeOf(TrackpadDirection.prototype), _symbols2.default.dragging, this);
- },
- set: function set(value) {
- if (_symbols2.default.dragging in base.prototype) {
- _set(TrackpadDirection.prototype.__proto__ || Object.getPrototypeOf(TrackpadDirection.prototype), _symbols2.default.dragging, value, this);
- }
- }
- }, {
- key: 'travelFraction',
- get: function get() {
- return _get(TrackpadDirection.prototype.__proto__ || Object.getPrototypeOf(TrackpadDirection.prototype), 'travelFraction', this);
- },
- set: function set(value) {
- if ('travelFraction' in base.prototype) {
- _set(TrackpadDirection.prototype.__proto__ || Object.getPrototypeOf(TrackpadDirection.prototype), 'travelFraction', value, this);
- }
- }
- }]);
-
- return TrackpadDirection;
- }(base);
-
- return TrackpadDirection;
-};
-
-// Time we wait following a navigation before paying attention to wheel
-// events again.
-
-
-var POST_NAVIGATE_TIME = 250;
-
-// Time we wait after the last wheel event before we reset things.
-var WHEEL_TIME = 100;
-
-// Following a navigation, partially reset our wheel tracking.
-function postNavigate(element) {
- element.travelFraction = 0;
- element[wheelDistanceSymbol] = 0;
- element[postNavigateDelayCompleteSymbol] = true;
- element[absorbDecelerationSymbol] = true;
- setTimeout(function () {
- element[postNavigateDelayCompleteSymbol] = false;
- }, POST_NAVIGATE_TIME);
-}
-
-// Reset all state related to the tracking of the wheel.
-function resetWheelTracking(element) {
- element.travelFraction = 0;
- element[wheelDistanceSymbol] = 0;
- element[lastDeltaXSymbol] = 0;
- element[absorbDecelerationSymbol] = false;
- element[postNavigateDelayCompleteSymbol] = false;
- if (element[lastWheelTimeoutSymbol]) {
- clearTimeout(element[lastWheelTimeoutSymbol]);
- element[lastWheelTimeoutSymbol] = null;
- }
-}
-
-// Define our own sign function, since (as of May 2015), Safari and IE don't
-// supply Math.sign().
-function sign(x) {
- return x === 0 ? 0 : x > 0 ? 1 : -1;
-}
-
-// TODO: Damping, or some other treatment for going past the ends.
-
-/*
- * A wheel event has been generated. This could be a real wheel event, or it
- * could be fake (see notes in the header).
- *
- * This handler uses several strategies to try to approximate native trackpad
- * swipe navigation.
- *
- * If the user has dragged enough to cause a navigation, then for a short
- * delay following that navigation, subsequent wheel events will be ignored.
- *
- * Furthermore, follwowing a navigation, we ignore all wheel events until we
- * receive at least one event where the event's deltaX (distance traveled) is
- * *greater* than the previous event's deltaX. This helps us filter out the
- * fake wheel events generated by the browser to simulate deceleration.
- *
- */
-function wheel(element, event) {
-
- // Since we have a new wheel event, reset our timer waiting for the last
- // wheel event to pass.
- if (element[lastWheelTimeoutSymbol]) {
- clearTimeout(element[lastWheelTimeoutSymbol]);
- }
- element[lastWheelTimeoutSymbol] = setTimeout(function () {
- wheelTimedOut(element);
- }, WHEEL_TIME);
-
- var deltaX = event.deltaX;
- var deltaY = event.deltaY;
-
- // See if element event represents acceleration or deceleration.
- var acceleration = sign(deltaX) * (deltaX - element[lastDeltaXSymbol]);
- element[lastDeltaXSymbol] = deltaX;
-
- if (Math.abs(deltaX) < Math.abs(deltaY)) {
- // Move was mostly vertical. The user may be trying scroll with the
- // trackpad/wheel. To be on the safe, we ignore such events.
- return false;
- }
-
- if (element[postNavigateDelayCompleteSymbol]) {
- // It's too soon after a navigation; ignore the event.
- return true;
- }
-
- if (acceleration > 0) {
- // The events are not (or are no longer) decelerating, so we can start
- // paying attention to them again.
- element[absorbDecelerationSymbol] = false;
- } else if (element[absorbDecelerationSymbol]) {
- // The wheel event was likely faked to simulate deceleration; ignore it.
- return true;
- }
-
- element[wheelDistanceSymbol] += deltaX;
-
- // Update the travel fraction of the element being navigated.
- var width = element.offsetWidth;
- var travelFraction = width > 0 ? element[wheelDistanceSymbol] / width : 0;
- element[_symbols2.default.dragging] = true;
- travelFraction = sign(travelFraction) * Math.min(Math.abs(travelFraction), 1);
- element.travelFraction = travelFraction;
-
- // If the user has dragged enough to reach the previous/next item, then
- // complete a navigation to that item.
- if (travelFraction === 1) {
- element[_symbols2.default.dragging] = false;
- element[_symbols2.default.goRight]();
- postNavigate(element);
- } else if (travelFraction === -1) {
- element[_symbols2.default.dragging] = false;
- element[_symbols2.default.goLeft]();
- postNavigate(element);
- }
-
- return true;
-}
-
-// A sufficiently long period of time has passed since the last wheel event.
-// We snap the selection to the closest item, then reset our state.
-function wheelTimedOut(element) {
-
- // Snap to the closest item.
- element[_symbols2.default.dragging] = false;
- var travelFraction = element.travelFraction;
- if (travelFraction >= 0.5) {
- element[_symbols2.default.goRight]();
- } else if (travelFraction <= -0.5) {
- element[_symbols2.default.goLeft]();
- }
-
- // TODO: Listen for the transition to complete, and then restore
- // dragging to false (or the previous value).
-
- resetWheelTracking(element);
-}
-
-},{"../../basic-component-mixins/src/createSymbol":28,"./symbols":32}],28:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-exports.default = createSymbol;
-/**
- * Helper function to create a symbol that can be used for associating private
- * data with an element.
- *
- * Mixins and component classes often want to associate private data with an
- * element instance, but JavaScript does not have direct support for true
- * private properties. One approach is to use the
- * [Symbol](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Symbol)
- * data type to set and retrieve data on an element.
- *
- * Unfortunately, the Symbol type is not available in Internet Explorer 11. The
- * `createSymbol` helper function exists as a workaround for IE 11. Rather than
- * returning a true Symbol, it simply returns an underscore-prefixed string.
- *
- * Usage:
- *
- * const fooSymbol = createSymbol('foo');
- *
- * class MyElement extends HTMLElement {
- * get foo() {
- * return this[fooSymbol];
- * }
- * set foo(value) {
- * this[fooSymbol] = value;
- * }
- * }
- *
- * In IE 11, this sample will "hide" data behind an instance property this._foo.
- * The use of the underscore is meant to reduce (not eliminate) the potential
- * for name conflicts, and discourage (not prevent) external access to this
- * data. In modern browsers, the above code will eliminate the potential of
- * naming conflicts, and better hide the data behind a real Symbol.
- *
- * @function createSymbol
- * @param {string} description - A string to identify the symbol when debugging
- */
-function createSymbol(description) {
- return typeof Symbol === 'function' ? Symbol(description) : '_' + description;
-}
-
-},{}],29:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-exports.default = microtask;
-/*
- * Microtask helper for IE 11.
- *
- * Executing a function as a microtask is trivial in browsers that support
- * promises, whose then() clauses use microtask timing. IE 11 doesn't support
- * promises, but does support MutationObservers, which are also executed as
- * microtasks. So this helper uses an MutationObserver to achieve microtask
- * timing.
- *
- * See https://jakearchibald.com/2015/tasks-microtasks-queues-and-schedules/
- *
- * Inspired by Polymer's async() function.
- */
-
-// The queue of pending callbacks to be executed as microtasks.
-var callbacks = [];
-
-// Create an element that we will modify to force observable mutations.
-var element = document.createTextNode('');
-
-// A monotonically-increasing value.
-var counter = 0;
-
-/**
- * Add a callback to the microtask queue.
- *
- * This uses a MutationObserver so that it works on IE 11.
- *
- * NOTE: IE 11 may actually use timeout timing with MutationObservers. This
- * needs more investigation.
- *
- * @function microtask
- * @param {function} callback
- */
-function microtask(callback) {
- callbacks.push(callback);
- // Force a mutation.
- element.textContent = ++counter;
-}
-
-// Execute any pending callbacks.
-function executeCallbacks() {
- while (callbacks.length > 0) {
- var callback = callbacks.shift();
- callback();
- }
-}
-
-// Create the observer.
-var observer = new MutationObserver(executeCallbacks);
-observer.observe(element, {
- characterData: true
-});
-
-},{}],30:[function(require,module,exports){
-"use strict";
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-/**
- * Helper function for rendering an array of items as elements.
- *
- * This is not a mixin, but a function components can use if they need to
- * generate a set of elements for the items in an array.
- *
- * This function will reuse existing elements if possible. E.g., if it is called
- * to render an array of 4 items, and later called to render an array of 5
- * items, it can reuse the existing 4 items, creating just one new element.
- * Note, however, that this re-rendering is not automatic. If, after calling
- * this function, you manipulate the array you used, you must still call this
- * function again to re-render the array.
- *
- * The `renderItem` parameter takes a function of two arguments: an item to
- * to render, and an existing element (if one exists) which can be repurposed to
- * render that item. If the latter argument is null, the `renderItem()` function
- * should create a new element and return it. The function should do the same
- * if the supplied existing element is not suitable for rendering the given
- * item; the returned element will be used to replace the existing one. If the
- * existing element *is* suitable, the function can simply update it and return
- * it as is.
- *
- * Example: The following will render an array of strings in divs as children
- * of the `container` element:
- *
- * let strings = ['a', 'b', 'c', ...];
- * let container = this.querySelector(...);
- * renderArrayAsElements(strings, container, (string, element) => {
- * if (!element) {
- * // No element exists yet, so create a new one.
- * element = document.createElement('div');
- * }
- * // Set/update the text content of the element.
- * element.textContent = string;
- * return element;
- * });
- *
- * @param {Array} items - the items to render
- * @param {HTMLElement} container - the parent that will hold the elements
- * @param {function} renderItem - returns a new element for an item, or
- * repurposes an existing element for an item
- */
-function renderArrayAsElements(items, container, renderItem) {
- // Create a new set of elements for the current items.
- items.forEach(function (item, index) {
- var oldElement = container.childNodes[index];
- var newElement = renderItem(item, oldElement);
- if (newElement) {
- if (!oldElement) {
- container.appendChild(newElement);
- } else if (newElement !== oldElement) {
- container.replaceChild(newElement, oldElement);
- }
- }
- });
-
- // If the array shrank, remove the extra elements which are no longer needed.
- while (container.childNodes.length > items.length) {
- container.removeChild(container.childNodes[items.length]);
- }
-}
-
-exports.default = renderArrayAsElements;
-
-},{}],31:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createSymbol = require('./createSymbol');
-
-var _createSymbol2 = _interopRequireDefault(_createSymbol);
-
-var _toggleClass2 = require('./toggleClass');
-
-var _toggleClass3 = _interopRequireDefault(_toggleClass2);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-// Symbols for private data members on an element.
-var safeToSetAttributesSymbol = (0, _createSymbol2.default)('safeToSetAttributes');
-var pendingAttributesSymbol = (0, _createSymbol2.default)('pendingAttributes');
-var pendingClassesSymbol = (0, _createSymbol2.default)('pendingClasses');
-
-/**
- * Helper functions for updating attributes, including the `class` attribute.
- */
-exports.default = {
-
- /**
- * Perform any pending updates to attributes and classes.
- *
- * This writes any `setAttribute` or `toggleClass` values that were performed
- * before an element was attached to the document for the first time.
- *
- * This method should be called by mixins/components in their
- * `connectedCallback`. If mulitple mixins/components invoke this during the
- * same `connectedCallback`, only the first call will have any effect. The
- * subsequent calls will be harmless.
- *
- * @param {HTMLElement} element - The element being added to the document.
- */
- connected: function connected(element) {
- element[safeToSetAttributesSymbol] = true;
-
- // Set any pending attributes.
- if (element[pendingAttributesSymbol]) {
- for (var attribute in element[pendingAttributesSymbol]) {
- var value = element[pendingAttributesSymbol][attribute];
- setAttributeToElement(element, attribute, value);
- }
- element[pendingAttributesSymbol] = null;
- }
-
- // Set any pending classes.
- if (element[pendingClassesSymbol]) {
- for (var className in element[pendingClassesSymbol]) {
- var _value = element[pendingClassesSymbol][className];
- (0, _toggleClass3.default)(element, className, _value);
- }
- element[pendingClassesSymbol] = null;
- }
- },
-
-
- /**
- * Set/unset the attribute with the indicated name.
- *
- * This method exists primarily to handle the case where an element wants to
- * set a default property value that should be reflected as an attribute. An
- * important limitation of custom element consturctors is that they cannot
- * set attributes. A call to `setAttribute` during the constructor will
- * be deferred until the element is connected to the document.
- *
- * @param {string} attribute - The name of the *attribute* (not property) to set.
- * @param {object} value - The value to set. If null, the attribute will be removed.
- */
- setAttribute: function setAttribute(element, attribute, value) {
- if (element[safeToSetAttributesSymbol]) {
- // Safe to set attributes immediately.
- setAttributeToElement(element, attribute, value);
- } else {
- // Defer setting attributes until the first time we're connected.
- if (!element[pendingAttributesSymbol]) {
- element[pendingAttributesSymbol] = {};
- }
- element[pendingAttributesSymbol][attribute] = value;
- }
- },
-
-
- /**
- * Set/unset the class with the indicated name.
- *
- * This method exists primarily to handle the case where an element wants to
- * set a default property value that should be reflected as as class. An
- * important limitation of custom element consturctors is that they cannot
- * set attributes, including the `class` attribute. A call to
- * `toggleClass` during the constructor will be deferred until the element
- * is connected to the document.
- *
- * @param {string} className - The name of the class to set.
- * @param {object} value - True to set the class, false to remove it.
- */
- toggleClass: function toggleClass(element, className, value) {
- if (element[safeToSetAttributesSymbol]) {
- // Safe to set class immediately.
- (0, _toggleClass3.default)(element, className, value);
- } else {
- // Defer setting class until the first time we're connected.
- if (!element[pendingClassesSymbol]) {
- element[pendingClassesSymbol] = {};
- }
- element[pendingClassesSymbol][className] = value;
- }
- }
-};
-
-// Reflect the attribute to the given element.
-// If the value is null, remove the attribute.
-
-function setAttributeToElement(element, attributeName, value) {
- if (value === null || typeof value === 'undefined') {
- element.removeAttribute(attributeName);
- } else {
- var text = String(value);
- // Avoid recursive attributeChangedCallback calls.
- if (element.getAttribute(attributeName) !== text) {
- element.setAttribute(attributeName, value);
- }
- }
-}
-
-},{"./createSymbol":28,"./toggleClass":33}],32:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createSymbol = require('./createSymbol');
-
-var _createSymbol2 = _interopRequireDefault(_createSymbol);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-/**
- * A collection of Symbol objects for standard component properties and methods.
- *
- * These Symbol objects are used to allow mixins and a component to internally
- * communicate, without exposing these properties and methods in the component's
- * public API.
- *
- * To use these Symbol objects in your own component, include this module and
- * then create a property or method whose key is the desired Symbol.
- *
- * import 'SingleSelectionMixin' from 'basic-component-mixins/src/SingleSelectionMixin';
- * import 'symbols' from 'basic-component-mixins/src/symbols';
- *
- * class MyElement extends SingleSelectionMixin(HTMLElement) {
- * [symbols.itemSelected](item, selected) {
- * // This will be invoked whenever an item is selected/deselected.
- * }
- * }
- *
- * @module symbols
- */
-var symbols = {
-
- /**
- * Symbol for the `defaults` property.
- *
- * This property can be used to set or override defaults that will be applied
- * to a new component instance. When implementing this property, take care to
- * first acquire any defaults defined by the superclass. The standard idiom is
- * as follows:
- *
- * get [symbols.defaults]() {
- * const defaults = super[symbols.defaults] || {};
- * // Set or override default values here
- * defaults.customProperty = false;
- * return defaults;
- * }
- *
- * @var {object} defaults
- */
- defaults: (0, _createSymbol2.default)('defaults'),
-
- /**
- * Symbol for the `dragging` property.
- *
- * Components like carousels often define animated CSS transitions for
- * sliding effects. Such a transition should usually *not* be applied while
- * the user is dragging, because a CSS animation will introduce a lag that
- * makes the swipe feel sluggish. Instead, as long as the user is dragging
- * with their finger down, the transition should be suppressed. When the
- * user releases their finger, the transition can be restored, allowing the
- * animation to show the carousel sliding into its final position.
- *
- * @type {boolean} true if a drag is in progress, false if not.
- */
- dragging: (0, _createSymbol2.default)('dragging'),
-
- /**
- * Symbol for the `goDown` method.
- *
- * This method is invoked when the user wants to go/navigate down.
- *
- * @function goDown
- */
- goDown: (0, _createSymbol2.default)('goDown'),
-
- /**
- * Symbol for the `goEnd` method.
- *
- * This method is invoked when the user wants to go/navigate to the end (e.g.,
- * of a list).
- *
- * @function goEnd
- */
- goEnd: (0, _createSymbol2.default)('goEnd'),
-
- /**
- * Symbol for the `goLeft` method.
- *
- * This method is invoked when the user wants to go/navigate left.
- *
- * @function goLeft
- */
- goLeft: (0, _createSymbol2.default)('goLeft'),
-
- /**
- * Symbol for the `goRight` method.
- *
- * This method is invoked when the user wants to go/navigate right.
- *
- * @function goRight
- */
- goRight: (0, _createSymbol2.default)('goRight'),
-
- /**
- * Symbol for the `goStart` method.
- *
- * This method is invoked when the user wants to go/navigate to the start
- * (e.g., of a list).
- *
- * @function goStart
- */
- goStart: (0, _createSymbol2.default)('goStart'),
-
- /**
- * Symbol for the `goUp` method.
- *
- * This method is invoked when the user wants to go/navigate up.
- *
- * @function goUp
- */
- goUp: (0, _createSymbol2.default)('goUp'),
-
- /**
- * Symbol for the `itemAdded` method.
- *
- * This method is invoked when a new item is added to a list.
- *
- * @function itemAdded
- * @param {HTMLElement} item - the item being selected/deselected
- */
- itemAdded: (0, _createSymbol2.default)('itemAdded'),
-
- /**
- * Symbol for the `itemsChanged` method.
- *
- * This method is invoked when the underlying contents change. It is also
- * invoked on component initialization – since the items have "changed" from
- * being nothing.
- */
- itemsChanged: (0, _createSymbol2.default)('itemsChanged'),
-
- /**
- * Symbol for the `itemSelected` method.
- *
- * This method is invoked when an item becomes selected or deselected.
- *
- * @function itemSelected
- * @param {HTMLElement} item - the item being selected/deselected
- * @param {boolean} selected - true if the item is selected, false if not
- */
- itemSelected: (0, _createSymbol2.default)('itemSelected'),
-
- /**
- * Symbol for the `keydown` method.
- *
- * This method is invoked when an element receives a `keydown` event.
- *
- * @function keydown
- * @param {KeyboardEvent} event - the event being processed
- */
- keydown: (0, _createSymbol2.default)('keydown'),
-
- /**
- * Symbol for the `template` property.
- *
- * This property returns a component's template.
- *
- * @type {string|HTMLElement}
- */
- template: (0, _createSymbol2.default)('template')
-};
-
-exports.default = symbols;
-
-},{"./createSymbol":28}],33:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-exports.default = toggleClass;
-/**
- * Helper function for standard classList.toggle() behavior on old browsers,
- * namely IE 11.
- *
- * The standard
- * [classlist](https://developer.mozilla.org/en-US/docs/Web/API/Element/classList)
- * object has a `toggle()` function that supports a second Boolean parameter
- * that can be used to succinctly turn a class on or off. This feature is often
- * useful in designing custom elements, which may want to externally reflect
- * component state in a CSS class that can be used for styling purposes.
- *
- * Unfortunately, IE 11 does not support the Boolean parameter to
- * `classList.toggle()`. This helper function behaves like the standard
- * `toggle()`, including support for the Boolean parameter, so that it can be
- * used even on IE 11.
- *
- * @function toggleClass
- * @param {HTMLElement} element - The element to modify
- * @param {string} className - The class to add/remove
- * @param {boolean} [force] - Force the class to be added (if true) or removed
- * (if false)
- */
-function toggleClass(element, className, force) {
- var classList = element.classList;
- var addClass = typeof force === 'undefined' ? !classList.contains(className) : force;
- if (addClass) {
- classList.add(className);
- } else {
- classList.remove(className);
- }
- return addClass;
-}
-
-},{}]},{},[1])
-//# sourceMappingURL=data:application/json;charset:utf-8;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbIm5vZGVfbW9kdWxlcy9ncnVudC1icm93c2VyaWZ5L25vZGVfbW9kdWxlcy9icm93c2VyLXBhY2svX3ByZWx1ZGUuanMiLCJwYWNrYWdlcy9iYXNpYy1jb21wb25lbnQtbWl4aW5zL2dsb2JhbHMuanMiLCJwYWNrYWdlcy9iYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy9BcnJvd1NlbGVjdGlvbk1peGluLmpzIiwicGFja2FnZXMvYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvQXR0cmlidXRlTWFyc2hhbGxpbmdNaXhpbi5qcyIsInBhY2thZ2VzL2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL0NsaWNrU2VsZWN0aW9uTWl4aW4uanMiLCJwYWNrYWdlcy9iYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy9Db21wb3NhYmxlTWl4aW4uanMiLCJwYWNrYWdlcy9iYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy9Db250ZW50SXRlbXNNaXhpbi5qcyIsInBhY2thZ2VzL2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL0RpcmVjdGlvblNlbGVjdGlvbk1peGluLmpzIiwicGFja2FnZXMvYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvRGlzdHJpYnV0ZWRDaGlsZHJlbkNvbnRlbnRNaXhpbi5qcyIsInBhY2thZ2VzL2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL0Rpc3RyaWJ1dGVkQ2hpbGRyZW5NaXhpbi5qcyIsInBhY2thZ2VzL2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL0ZyYWN0aW9uYWxTZWxlY3Rpb25NaXhpbi5qcyIsInBhY2thZ2VzL2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL0dlbmVyaWNNaXhpbi5qcyIsInBhY2thZ2VzL2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL0tleWJvYXJkRGlyZWN0aW9uTWl4aW4uanMiLCJwYWNrYWdlcy9iYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy9LZXlib2FyZE1peGluLmpzIiwicGFja2FnZXMvYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvS2V5Ym9hcmRQYWdlZFNlbGVjdGlvbk1peGluLmpzIiwicGFja2FnZXMvYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvS2V5Ym9hcmRQcmVmaXhTZWxlY3Rpb25NaXhpbi5qcyIsInBhY2thZ2VzL2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL1BhZ2VEb3RzTWl4aW4uanMiLCJwYWNrYWdlcy9iYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy9QbGF5Q29udHJvbHNNaXhpbi5qcyIsInBhY2thZ2VzL2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL1NlbGVjdGlvbkFuaW1hdGlvbk1peGluLmpzIiwicGFja2FnZXMvYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvU2VsZWN0aW9uQXJpYUFjdGl2ZU1peGluLmpzIiwicGFja2FnZXMvYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvU2VsZWN0aW9uSGlnaGxpZ2h0TWl4aW4uanMiLCJwYWNrYWdlcy9iYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy9TZWxlY3Rpb25JblZpZXdNaXhpbi5qcyIsInBhY2thZ2VzL2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL1NoYWRvd0VsZW1lbnRSZWZlcmVuY2VzTWl4aW4uanMiLCJwYWNrYWdlcy9iYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy9TaGFkb3dUZW1wbGF0ZU1peGluLmpzIiwicGFja2FnZXMvYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvU2luZ2xlU2VsZWN0aW9uTWl4aW4uanMiLCJwYWNrYWdlcy9iYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy9Td2lwZURpcmVjdGlvbk1peGluLmpzIiwicGFja2FnZXMvYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvVGltZXJTZWxlY3Rpb25NaXhpbi5qcyIsInBhY2thZ2VzL2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL1RyYWNrcGFkRGlyZWN0aW9uTWl4aW4uanMiLCJwYWNrYWdlcy9iYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy9jcmVhdGVTeW1ib2wuanMiLCJwYWNrYWdlcy9iYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy9taWNyb3Rhc2suanMiLCJwYWNrYWdlcy9iYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy9yZW5kZXJBcnJheUFzRWxlbWVudHMuanMiLCJwYWNrYWdlcy9iYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy9zYWZlQXR0cmlidXRlcy5qcyIsInBhY2thZ2VzL2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL3N5bWJvbHMuanMiLCJwYWNrYWdlcy9iYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy90b2dnbGVDbGFzcy5qcyJdLCJuYW1lcyI6W10sIm1hcHBpbmdzIjoiQUFBQTs7O0FDT0E7Ozs7QUFDQTs7OztBQUNBOzs7O0FBQ0E7Ozs7QUFDQTs7OztBQUNBOzs7O0FBQ0E7Ozs7QUFDQTs7OztBQUNBOzs7O0FBQ0E7Ozs7QUFDQTs7OztBQUNBOzs7O0FBQ0E7Ozs7QUFDQTs7OztBQUNBOzs7O0FBQ0E7Ozs7QUFDQTs7OztBQUNBOzs7O0FBQ0E7Ozs7QUFDQTs7OztBQUNBOzs7O0FBQ0E7Ozs7QUFDQTs7OztBQUNBOzs7O0FBQ0E7Ozs7QUFDQTs7OztBQUNBOzs7O0FBQ0E7Ozs7QUFDQTs7Ozs7O0FBRUEsT0FBTyxLQUFQLEdBQWUsT0FBTyxLQUFQLElBQWdCLEVBQS9CLEMsQ0FyQ0E7Ozs7Ozs7QUF1Q0EsT0FBTyxLQUFQLENBQWEsbUJBQWI7QUFDQSxPQUFPLEtBQVAsQ0FBYSx5QkFBYjtBQUNBLE9BQU8sS0FBUCxDQUFhLG1CQUFiO0FBQ0EsT0FBTyxLQUFQLENBQWEsZUFBYjtBQUNBLE9BQU8sS0FBUCxDQUFhLGlCQUFiO0FBQ0EsT0FBTyxLQUFQLENBQWEsWUFBYjtBQUNBLE9BQU8sS0FBUCxDQUFhLHVCQUFiO0FBQ0EsT0FBTyxLQUFQLENBQWEsd0JBQWI7QUFDQSxPQUFPLEtBQVAsQ0FBYSwrQkFBYjtBQUNBLE9BQU8sS0FBUCxDQUFhLE9BQWI7QUFDQSxPQUFPLEtBQVAsQ0FB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OztBQXlFZDs7Ozs7Ozs7QUFRQSxXQUFTLDRCQUFhLFNBQWIsQ0FqRks7O0FBbUZkOzs7Ozs7O0FBT0EsUUFBTSw0QkFBYSxNQUFiLENBMUZROztBQTRGZDs7Ozs7Ozs7QUFRQSxhQUFXLDRCQUFhLFdBQWIsQ0FwR0c7O0FBdUdkOzs7Ozs7O0FBT0EsZ0JBQWMsNEJBQWEsY0FBYixDQTlHQTs7QUFnSGQ7Ozs7Ozs7OztBQVNBLGdCQUFjLDRCQUFhLGNBQWIsQ0F6SEE7O0FBMkhkOzs7Ozs7OztBQVFBLFdBQVMsNEJBQWEsU0FBYixDQW5JSzs7QUFxSWQ7Ozs7Ozs7QUFPQSxZQUFVLDRCQUFhLFVBQWI7QUE1SUksQ0FBaEI7O2tCQStJZSxPOzs7Ozs7OztrQkNoSlMsVztBQXRCeEI7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7QUFzQmUsU0FBUyxXQUFULENBQXFCLE9BQXJCLEVBQThCLFNBQTlCLEVBQXlDLEtBQXpDLEVBQWdEO0FBQzdELE1BQU0sWUFBWSxRQUFRLFNBQTFCO0FBQ0EsTUFBTSxXQUFZLE9BQU8sS0FBUCxLQUFpQixXQUFsQixHQUNmLENBQUMsVUFBVSxRQUFWLENBQW1CLFNBQW5CLENBRGMsR0FFZixLQUZGO0FBR0EsTUFBSSxRQUFKLEVBQWM7QUFDWixjQUFVLEdBQVYsQ0FBYyxTQUFkO0FBQ0QsR0FGRCxNQUVPO0FBQ0wsY0FBVSxNQUFWLENBQWlCLFNBQWpCO0FBQ0Q7QUFDRCxTQUFPLFFBQVA7QUFDRCIsImZpbGUiOiJnZW5lcmF0ZWQuanMiLCJzb3VyY2VSb290IjoiIiwic291cmNlc0NvbnRlbnQiOlsiKGZ1bmN0aW9uIGUodCxuLHIpe2Z1bmN0aW9uIHMobyx1KXtpZighbltvXSl7aWYoIXRbb10pe3ZhciBhPXR5cGVvZiByZXF1aXJlPT1cImZ1bmN0aW9uXCImJnJlcXVpcmU7aWYoIXUmJmEpcmV0dXJuIGEobywhMCk7aWYoaSlyZXR1cm4gaShvLCEwKTt2YXIgZj1uZXcgRXJyb3IoXCJDYW5ub3QgZmluZCBtb2R1bGUgJ1wiK28rXCInXCIpO3Rocm93IGYuY29kZT1cIk1PRFVMRV9OT1RfRk9VTkRcIixmfXZhciBsPW5bb109e2V4cG9ydHM6e319O3Rbb11bMF0uY2FsbChsLmV4cG9ydHMsZnVuY3Rpb24oZSl7dmFyIG49dFtvXVsxXVtlXTtyZXR1cm4gcyhuP246ZSl9LGwsbC5leHBvcnRzLGUsdCxuLHIpfXJldHVybiBuW29dLmV4cG9ydHN9dmFyIGk9dHlwZW9mIHJlcXVpcmU9PVwiZnVuY3Rpb25cIiYmcmVxdWlyZTtmb3IodmFyIG89MDtvPHIubGVuZ3RoO28rKylzKHJbb10pO3JldHVybiBzfSkiLCIvKlxuICogVGhpcyBmaWxlIGlzIHRyYW5zcGlsZWQgdG8gY3JlYXRlIGFuIEVTNS1jb21wYXRpYmxlIGRpc3RyaWJ1dGlvbiBpbiB3aGljaFxuICogdGhlIHBhY2thZ2UncyBtYWluIGZlYXR1cmUocykgYXJlIGF2YWlsYWJsZSB2aWEgdGhlIHdpbmRvdy5CYXNpYyBnbG9iYWwuXG4gKiBJZiB5b3UncmUgYWxyZWFkeSB1c2luZyBFUzYgeW91cnNlbGYsIGlnbm9yZSB0aGlzIGZpbGUsIGFuZCBpbnN0ZWFkIGltcG9ydFxuICogdGhlIHNvdXJjZSBmaWxlKHMpIHlvdSB3YW50IGZyb20gdGhlIHNyYyBmb2xkZXIuXG4gKi9cblxuaW1wb3J0IEFycm93U2VsZWN0aW9uTWl4aW4gZnJvbSAnLi9zcmMvQXJyb3dTZWxlY3Rpb25NaXhpbic7XG5pbXBvcnQgQXR0cmlidXRlTWFyc2hhbGxpbmdNaXhpbiBmcm9tICcuL3NyYy9BdHRyaWJ1dGVNYXJzaGFsbGluZ01peGluJztcbmltcG9ydCBDbGlja1NlbGVjdGlvbk1peGluIGZyb20gJy4vc3JjL0NsaWNrU2VsZWN0aW9uTWl4aW4nO1xuaW1wb3J0IENvbXBvc2FibGVNaXhpbiBmcm9tICcuL3NyYy9Db21wb3NhYmxlTWl4aW4nO1xuaW1wb3J0IENvbnRlbnRJdGVtc01peGluIGZyb20gJy4vc3JjL0NvbnRlbnRJdGVtc01peGluJztcbmltcG9ydCBjcmVhdGVTeW1ib2wgZnJvbSAnLi9zcmMvY3JlYXRlU3ltYm9sJztcbmltcG9ydCBEaXJlY3Rpb25TZWxlY3Rpb25NaXhpbiBmcm9tICcuL3NyYy9EaXJlY3Rpb25TZWxlY3Rpb25NaXhpbic7XG5pbXBvcnQgRGlzdHJpYnV0ZWRDaGlsZHJlbk1peGluIGZyb20gJy4vc3JjL0Rpc3RyaWJ1dGVkQ2hpbGRyZW5NaXhpbic7XG5pbXBvcnQgRGlzdHJpYnV0ZWRDaGlsZHJlbkNvbnRlbnRNaXhpbiBmcm9tICcuL3NyYy9EaXN0cmlidXRlZENoaWxkcmVuQ29udGVudE1peGluJztcbmltcG9ydCBHZW5lcmljTWl4aW4gZnJvbSAnLi9zcmMvR2VuZXJpY01peGluJztcbmltcG9ydCBLZXlib2FyZE1peGluIGZyb20gJy4vc3JjL0tleWJvYXJkTWl4aW4nO1xuaW1wb3J0IEtleWJvYXJkRGlyZWN0aW9uTWl4aW4gZnJvbSAnLi9zcmMvS2V5Ym9hcmREaXJlY3Rpb25NaXhpbic7XG5pbXBvcnQgS2V5Ym9hcmRQYWdlZFNlbGVjdGlvbk1peGluIGZyb20gJy4vc3JjL0tleWJvYXJkUGFnZWRTZWxlY3Rpb25NaXhpbic7XG5pbXBvcnQgS2V5Ym9hcmRQcmVmaXhTZWxlY3Rpb25NaXhpbiBmcm9tICcuL3NyYy9LZXlib2FyZFByZWZpeFNlbGVjdGlvbk1peGluJztcbmltcG9ydCBtaWNyb3Rhc2sgZnJvbSAnLi9zcmMvbWljcm90YXNrJztcbmltcG9ydCBQYWdlRG90c01peGluIGZyb20gJy4vc3JjL1BhZ2VEb3RzTWl4aW4nO1xuaW1wb3J0IFBsYXlDb250cm9sc01peGluIGZyb20gJy4vc3JjL1BsYXlDb250cm9sc01peGluJztcbmltcG9ydCBzYWZlQXR0cmlidXRlcyBmcm9tICcuL3NyYy9zYWZlQXR0cmlidXRlcyc7XG5pbXBvcnQgU2VsZWN0aW9uQW5pbWF0aW9uTWl4aW4gZnJvbSAnLi9zcmMvU2VsZWN0aW9uQW5pbWF0aW9uTWl4aW4nO1xuaW1wb3J0IFNlbGVjdGlvbkFyaWFBY3RpdmVNaXhpbiBmcm9tICcuL3NyYy9TZWxlY3Rpb25BcmlhQWN0aXZlTWl4aW4nO1xuaW1wb3J0IFNlbGVjdGlvbkhpZ2hsaWdodE1peGluIGZyb20gJy4vc3JjL1NlbGVjdGlvbkhpZ2hsaWdodE1peGluJztcbmltcG9ydCBTZWxlY3Rpb25JblZpZXdNaXhpbiBmcm9tICcuL3NyYy9TZWxlY3Rpb25JblZpZXdNaXhpbic7XG5pbXBvcnQgU2hhZG93RWxlbWVudFJlZmVyZW5jZXNNaXhpbiBmcm9tICcuL3NyYy9TaGFkb3dFbGVtZW50UmVmZXJlbmNlc01peGluJztcbmltcG9ydCBTaGFkb3dUZW1wbGF0ZU1peGluIGZyb20gJy4vc3JjL1NoYWRvd1RlbXBsYXRlTWl4aW4nO1xuaW1wb3J0IFNpbmdsZVNlbGVjdGlvbk1peGluIGZyb20gJy4vc3JjL1NpbmdsZVNlbGVjdGlvbk1peGluJztcbmltcG9ydCBTd2lwZURpcmVjdGlvbk1peGluIGZyb20gJy4vc3JjL1N3aXBlRGlyZWN0aW9uTWl4aW4nO1xuaW1wb3J0IHN5bWJvbHMgZnJvbSAnLi9zcmMvc3ltYm9scyc7XG5pbXBvcnQgVGltZXJTZWxlY3Rpb25NaXhpbiBmcm9tICcuL3NyYy9UaW1lclNlbGVjdGlvbk1peGluJztcbmltcG9ydCBUcmFja3BhZERpcmVjdGlvbk1peGluIGZyb20gJy4vc3JjL1RyYWNrcGFkRGlyZWN0aW9uTWl4aW4nO1xuXG53aW5kb3cuQmFzaWMgPSB3aW5kb3cuQmFzaWMgfHwge307XG5cbndpbmRvdy5CYXNpYy5BcnJvd1NlbGVjdGlvbk1peGluID0gQXJyb3dTZWxlY3Rpb25NaXhpbjtcbndpbmRvdy5CYXNpYy5BdHRyaWJ1dGVNYXJzaGFsbGluZ01peGluID0gQXR0cmlidXRlTWFyc2hhbGxpbmdNaXhpbjtcbndpbmRvdy5CYXNpYy5DbGlja1NlbGVjdGlvbk1peGluID0gQ2xpY2tTZWxlY3Rpb25NaXhpbjtcbndpbmRvdy5CYXNpYy5Db21wb3NhYmxlTWl4aW4gPSBDb21wb3NhYmxlTWl4aW47XG53aW5kb3cuQmFzaWMuQ29udGVudEl0ZW1zTWl4aW4gPSBDb250ZW50SXRlbXNNaXhpbjtcbndpbmRvdy5CYXNpYy5jcmVhdGVTeW1ib2wgPSBjcmVhdGVTeW1ib2w7XG53aW5kb3cuQmFzaWMuRGlyZWN0aW9uU2VsZWN0aW9uTWl4aW4gPSBEaXJlY3Rpb25TZWxlY3Rpb25NaXhpbjtcbndpbmRvdy5CYXNpYy5EaXN0cmlidXRlZENoaWxkcmVuTWl4aW4gPSBEaXN0cmlidXRlZENoaWxkcmVuTWl4aW47XG53aW5kb3cuQmFzaWMuRGlzdHJpYnV0ZWRDaGlsZHJlbkNvbnRlbnRNaXhpbiA9IERpc3RyaWJ1dGVkQ2hpbGRyZW5Db250ZW50TWl4aW47XG53aW5kb3cuQmFzaWMuZ2VuZXJpYyA9IEdlbmVyaWNNaXhpbjtcbndpbmRvdy5CYXNpYy5LZXlib2FyZE1peGluID0gS2V5Ym9hcmRNaXhpbjtcbndpbmRvdy5CYXNpYy5LZXlib2FyZERpcmVjdGlvbk1peGluID0gS2V5Ym9hcmREaXJlY3Rpb25NaXhpbjtcbndpbmRvdy5CYXNpYy5LZXlib2FyZFBhZ2VkU2VsZWN0aW9uTWl4aW4gPSBLZXlib2FyZFBhZ2VkU2VsZWN0aW9uTWl4aW47XG53aW5kb3cuQmFzaWMuS2V5Ym9hcmRQcmVmaXhTZWxlY3Rpb25NaXhpbiA9IEtleWJvYXJkUHJlZml4U2VsZWN0aW9uTWl4aW47XG53aW5kb3cuQmFzaWMubWljcm90YXNrID0gbWljcm90YXNrO1xud2luZG93LkJhc2ljLlBhZ2VEb3RzTWl4aW4gPSBQYWdlRG90c01peGluO1xud2luZG93LkJhc2ljLlBsYXlDb250cm9sc01peGluID0gUGxheUNvbnRyb2xzTWl4aW47XG53aW5kb3cuQmFzaWMuc2FmZUF0dHJpYnV0ZXMgPSBzYWZlQXR0cmlidXRlcztcbndpbmRvdy5CYXNpYy5TZWxlY3Rpb25BbmltYXRpb25NaXhpbiA9IFNlbGVjdGlvbkFuaW1hdGlvbk1peGluO1xud2luZG93LkJhc2ljLlNlbGVjdGlvbkFyaWFBY3RpdmVNaXhpbiA9IFNlbGVjdGlvbkFyaWFBY3RpdmVNaXhpbjtcbndpbmRvdy5CYXNpYy5TZWxlY3Rpb25IaWdobGlnaHRNaXhpbiA9IFNlbGVjdGlvbkhpZ2hsaWdodE1peGluO1xud2luZG93LkJhc2ljLlNlbGVjdGlvbkluVmlld01peGluID0gU2VsZWN0aW9uSW5WaWV3TWl4aW47XG53aW5kb3cuQmFzaWMuU2hhZG93RWxlbWVudFJlZmVyZW5jZXNNaXhpbiA9IFNoYWRvd0VsZW1lbnRSZWZlcmVuY2VzTWl4aW47XG53aW5kb3cuQmFzaWMuU2hhZG93VGVtcGxhdGVNaXhpbiA9IFNoYWRvd1RlbXBsYXRlTWl4aW47XG53aW5kb3cuQmFzaWMuU2luZ2xlU2VsZWN0aW9uTWl4aW4gPSBTaW5nbGVTZWxlY3Rpb25NaXhpbjtcbndpbmRvdy5CYXNpYy5Td2lwZURpcmVjdGlvbk1peGluID0gU3dpcGVEaXJlY3Rpb25NaXhpbjtcbndpbmRvdy5CYXNpYy5zeW1ib2xzID0gc3ltYm9scztcbndpbmRvdy5CYXNpYy5UaW1lclNlbGVjdGlvbk1peGluID0gVGltZXJTZWxlY3Rpb25NaXhpbjtcbndpbmRvdy5CYXNpYy5UcmFja3BhZERpcmVjdGlvbk1peGluID0gVHJhY2twYWREaXJlY3Rpb25NaXhpbjtcbiIsImltcG9ydCBjcmVhdGVTeW1ib2wgZnJvbSAnLi4vLi4vYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvY3JlYXRlU3ltYm9sJztcbmltcG9ydCBzeW1ib2xzIGZyb20gJy4uLy4uL2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL3N5bWJvbHMnO1xuXG5cbi8vIFN5bWJvbHMgZm9yIHByaXZhdGUgZGF0YSBtZW1iZXJzIG9uIGFuIGVsZW1lbnQuXG5jb25zdCBtb3VzZWRvd25MaXN0ZW5lclN5bWJvbCA9IGNyZWF0ZVN5bWJvbCgnbW91c2Vkb3duTGlzdGVuZXInKTtcbmNvbnN0IG1vdXNlbW92ZUxpc3RlbmVyU3ltYm9sID0gY3JlYXRlU3ltYm9sKCdtb3VzZW1vdmVMaXN0ZW5lcicpO1xuY29uc3QgbGFzdE1vdXNlWFN5bWJvbCA9IGNyZWF0ZVN5bWJvbCgnbGFzdE1vdXNlWCcpO1xuY29uc3QgbGFzdE1vdXNlWVN5bWJvbCA9IGNyZWF0ZVN5bWJvbCgnbGFzdE1vdXNlWScpO1xuY29uc3QgbW91c2VUaW1lb3V0U3ltYm9sID0gY3JlYXRlU3ltYm9sKCdtb3VzZVRpbWVvdXQnKTtcblxuXG4vKiBFeHBvcnRlZCBmdW5jdGlvbiBleHRlbmRzIGEgYmFzZSBjbGFzcyB3aXRoIEFycm93U2VsZWN0aW9uLiAqL1xuZXhwb3J0IGRlZmF1bHQgKGJhc2UpID0+IHtcblxuICAvKipcbiAgICogVGVtcGxhdGUgbWl4aW4gd2hpY2ggYWRkcyBwcm9taW5lbnQgbGVmdCBhbmQgcmlnaHQgYXJyb3cgYnV0dG9ucyB0byBhXG4gICAqIHdyYXBwZWQgY2hpbGQgc3VjaCBhcyBhIGNhcm91c2VsLlxuICAgKlxuICAgKiBZb3UgY2FuIHNlZSBhXG4gICAqIFtsaXZlIGRlbW9dKGh0dHA6Ly9iYXNpY3dlYmNvbXBvbmVudHMub3JnL2Jhc2ljLXdlYi1jb21wb25lbnRzL3BhY2thZ2VzL2RlbW9zL2Nhcm91c2VsLXdpdGgtYXJyb3dzLmh0bWwpXG4gICAqIG9mIHRoaXMgbWl4aW4gYXBwbGllZCB0byBhIGNhcm91c2VsLlxuICAgKlxuICAgKiBDbGlja2luZyB0aGUgbGVmdC9yaWdodCBidXR0b25zIHNlbGVjdHMgdGhlIHByZXZpb3VzL25leHQgaXRlbS5cbiAgICpcbiAgICogVHlwaWNhbCB1c2FnZTpcbiAgICpcbiAgICogICAgIGNsYXNzIENhcm91c2VsV2l0aEFycm93cyBleHRlbmRzIEFycm93U2VsZWN0aW9uTWl4aW4oQ2Fyb3VzZWwpIHt9XG4gICAqICAgICBjdXN0b21FbGVtZW50cy5kZWZpbmUoJ2Nhcm91c2VsLXdpdGgtYXJyb3dzJywgQ2Fyb3VzZWxXaXRoQXJyb3dzKTtcbiAgICpcbiAgICogQnkgZGVmYXVsdCwgdGhlIGFycm93IGJ1dHRvbnMgYXJlIHNob3duIG9uIGRldmljZXMgd2l0aCBhIG1vdXNlIG9yIG1vdXNlLWxpa2VcbiAgICogcG9pbnRpbmcgZGV2aWNlLiBUaGV5IGFyZSBub3Qgc2hvd24gb24gYSB0b3VjaC1jYXBhYmxlIGRldmljZSB1bmxlc3MgbW91c2VcbiAgICogbW92ZW1lbnQgaXMgZGV0ZWN0ZWQuIFRvIGNhdXNlIHRoZSBidXR0b25zIHRvIGFsd2F5cyBhcHBlYXIsIGFwcGx5IHRoZVxuICAgKiAnc2hvd0Fycm93cycgQ1NTIGNsYXNzLlxuICAgKi9cbiAgY2xhc3MgQXJyb3dTZWxlY3Rpb24gZXh0ZW5kcyBiYXNlIHtcblxuICAgIGNvbnN0cnVjdG9yKCkge1xuICAgICAgc3VwZXIoKTtcblxuICAgICAgdGhpcy4kLmJ1dHRvbkxlZnQuYWRkRXZlbnRMaXN0ZW5lcignY2xpY2snLCBldmVudCA9PiB7XG4gICAgICAgIHRoaXMuc2VsZWN0UHJldmlvdXMoKTtcbiAgICAgICAgZXZlbnQuc3RvcFByb3BhZ2F0aW9uKCk7XG4gICAgICB9KTtcbiAgICAgIHRoaXMuJC5idXR0b25SaWdodC5hZGRFdmVudExpc3RlbmVyKCdjbGljaycsIGV2ZW50ID0+IHtcbiAgICAgICAgdGhpcy5zZWxlY3ROZXh0KCk7XG4gICAgICAgIGV2ZW50LnN0b3BQcm9wYWdhdGlvbigpO1xuICAgICAgfSk7XG4gICAgICBhc3N1bWVCdXR0b25Gb2N1cyh0aGlzLCB0aGlzLiQuYnV0dG9uTGVmdCk7XG4gICAgICBhc3N1bWVCdXR0b25Gb2N1cyh0aGlzLCB0aGlzLiQuYnV0dG9uUmlnaHQpO1xuICAgIH1cblxuICAgIGdldCBjYW5TZWxlY3ROZXh0KCkge1xuICAgICAgcmV0dXJuIHN1cGVyLmNhblNlbGVjdE5leHQ7XG4gICAgfVxuICAgIHNldCBjYW5TZWxlY3ROZXh0KGNhblNlbGVjdE5leHQpIHtcbiAgICAgIGlmICgnY2FuU2VsZWN0TmV4dCcgaW4gYmFzZS5wcm90b3R5cGUpIHsgc3VwZXIuY2FuU2VsZWN0TmV4dCA9IGNhblNlbGVjdE5leHQ7IH1cbiAgICAgIHRoaXMuJC5idXR0b25SaWdodC5kaXNhYmxlZCA9ICFjYW5TZWxlY3ROZXh0O1xuICAgIH1cblxuICAgIGdldCBjYW5TZWxlY3RQcmV2aW91cygpIHtcbiAgICAgIHJldHVybiBzdXBlci5jYW5TZWxlY3RQcmV2aW91cztcbiAgICB9XG4gICAgc2V0IGNhblNlbGVjdFByZXZpb3VzKGNhblNlbGVjdFByZXZpb3VzKSB7XG4gICAgICBpZiAoJ2NhblNlbGVjdFByZXZpb3VzJyBpbiBiYXNlLnByb3RvdHlwZSkgeyBzdXBlci5jYW5TZWxlY3RQcmV2aW91cyA9IGNhblNlbGVjdFByZXZpb3VzOyB9XG4gICAgICB0aGlzLiQuYnV0dG9uTGVmdC5kaXNhYmxlZCA9ICFjYW5TZWxlY3RQcmV2aW91cztcbiAgICB9XG5cbiAgICBjb25uZWN0ZWRDYWxsYmFjaygpIHtcbiAgICAgIGlmIChzdXBlci5jb25uZWN0ZWRDYWxsYmFjaykgeyBzdXBlci5jb25uZWN0ZWRDYWxsYmFjaygpOyB9XG5cbiAgICAgIGlmICghdGhpcy5jbGFzc0xpc3QuY29udGFpbnMoJ3Nob3dBcnJvd3MnKSkge1xuICAgICAgICAvLyBEZXRlcm1pbmUgd2hldGhlciB3ZSBzaG91bGQgc2hvdyBhcnJvdyBidXR0b25zIG9yIG5vdC5cbiAgICAgICAgaWYgKGRldmljZVN1cHBvcnRzVG91Y2goKSkge1xuICAgICAgICAgIC8vIEEgdG91Y2ggZGV2aWNlIG1pZ2h0IGFsc28gc3VwcG9ydCBhIG1vdXNlLCBidXQgd2UgY2FuJ3Qga25vdyB3aGV0aGVyXG4gICAgICAgICAgLy8gdGhlcmUncyBhY3R1YWxseSBhIG1vdXNlIHVudGlsIHdlIGhlYXIgZnJvbSBpdC5cbiAgICAgICAgICBsaXN0ZW5Gb3JNb3VzZSh0aGlzKTtcbiAgICAgICAgfSBlbHNlIHtcbiAgICAgICAgICAvLyBUaGUgZGV2aWNlIGRvZXNuJ3Qgc3VwcG9ydCB0b3VjaCwgc28gYXNzdW1lIGl0IGhhcyBhIG1vdXNlLlxuICAgICAgICAgIHNob3dBcnJvd3ModGhpcyk7XG4gICAgICAgIH1cbiAgICAgIH1cbiAgICB9XG5cbiAgICBnZXQgW3N5bWJvbHMuZGVmYXVsdHNdKCkge1xuICAgICAgY29uc3QgZGVmYXVsdHMgPSBzdXBlcltzeW1ib2xzLmRlZmF1bHRzXSB8fCB7fTtcbiAgICAgIGRlZmF1bHRzLm5hdmlnYXRpb25BeGlzID0gJ2hvcml6b250YWwnO1xuICAgICAgcmV0dXJuIGRlZmF1bHRzO1xuICAgIH1cblxuICAgIC8qXG4gICAgICogVGhlIHRlbXBsYXRlIHVzZXMgdGhlIGNoZXZyb24tbGVmdCBhbmQgY2hldnJvbi1yaWdodCBTVkcgaWNvbnMgZnJvbVxuICAgICAqIGh0dHBzOi8vZ2l0aHViLmNvbS9Qb2x5bWVyRWxlbWVudHMvaXJvbi1pY29ucy9ibG9iL21hc3Rlci9pcm9uLWljb25zLmh0bWwuXG4gICAgICovXG4gICAgZ2V0IFtzeW1ib2xzLnRlbXBsYXRlXSgpIHtcbiAgICAgIGNvbnN0IGJhc2VUZW1wbGF0ZSA9IHN1cGVyW3N5bWJvbHMudGVtcGxhdGVdIHx8ICcnO1xuICAgICAgcmV0dXJuIGBcbiAgICAgICAgPHN0eWxlPlxuICAgICAgICA6aG9zdCB7XG4gICAgICAgICAgLXdlYmtpdC1hbGlnbi1pdGVtczogc3RyZXRjaDtcbiAgICAgICAgICBhbGlnbi1pdGVtczogc3RyZXRjaDtcbiAgICAgICAgICBkaXNwbGF5OiAtd2Via2l0LWZsZXg7XG4gICAgICAgICAgZGlzcGxheTogZmxleDtcbiAgICAgICAgICAtd2Via2l0LWZsZXg6IDE7XG4gICAgICAgICAgZmxleDogMTtcbiAgICAgICAgICAtd2Via2l0LWp1c3RpZnktY29udGVudDogY2VudGVyO1xuICAgICAgICAgIGp1c3RpZnktY29udGVudDogY2VudGVyO1xuICAgICAgICB9XG5cbiAgICAgICAgI2Fycm93TmF2aWdhdGlvbkNvbnRhaW5lciB7XG4gICAgICAgICAgZGlzcGxheTogLXdlYmtpdC1mbGV4O1xuICAgICAgICAgIGRpc3BsYXk6IGZsZXg7XG4gICAgICAgICAgLXdlYmtpdC1mbGV4OiAxO1xuICAgICAgICAgIGZsZXg6IDE7XG4gICAgICAgICAgcG9zaXRpb246IHJlbGF0aXZlO1xuICAgICAgICB9XG5cbiAgICAgICAgLm5hdmlnYXRpb25CdXR0b24ge1xuICAgICAgICAgIGJhY2tncm91bmQ6IHRyYW5zcGFyZW50O1xuICAgICAgICAgIGJvcmRlcjogMXB4IHNvbGlkIHRyYW5zcGFyZW50O1xuICAgICAgICAgIGJveC1zaXppbmc6IGJvcmRlci1ib3g7XG4gICAgICAgICAgY29sb3I6IHJnYmEoMCwgMCwgMCwgMC43KTtcbiAgICAgICAgICBmaWxsOiBjdXJyZW50Q29sb3I7XG4gICAgICAgICAgbWFyZ2luOiAwO1xuICAgICAgICAgIG9wYWNpdHk6IDE7XG4gICAgICAgICAgb3V0bGluZTogbm9uZTsgLyogUkVWSUVXOiBBY2Nlc3NpYmlsaXR5IHNob3VsZCBiZSBwcm92aWRlZCBieSBvdGhlciBlbGVtZW50cy4gKi9cbiAgICAgICAgICBwYWRkaW5nOiAwO1xuICAgICAgICAgIHRyYW5zaXRpb246IG9wYWNpdHkgMXM7XG4gICAgICAgICAgei1pbmRleDogMTtcbiAgICAgICAgfVxuXG4gICAgICAgIC5uYXZpZ2F0aW9uQnV0dG9uOmhvdmVyOm5vdCg6ZGlzYWJsZWQpIHtcbiAgICAgICAgICBiYWNrZ3JvdW5kOiByZ2JhKDAsIDAsIDAsIDAuNSk7XG4gICAgICAgICAgY29sb3I6IHJnYmEoMCwgMCwgMCwgMC44KTtcbiAgICAgICAgICBjdXJzb3I6IHBvaW50ZXI7XG4gICAgICAgIH1cbiAgICAgICAgLm5hdmlnYXRpb25CdXR0b246YWN0aXZlOm5vdCg6ZGlzYWJsZWQpIHtcbiAgICAgICAgICBiYWNrZ3JvdW5kOiByZ2JhKDAsIDAsIDAsIDAuNyk7XG4gICAgICAgICAgY29sb3I6IHJnYmEoMCwgMCwgMCwgMC45KTtcbiAgICAgICAgfVxuICAgICAgICAubmF2aWdhdGlvbkJ1dHRvbjpkaXNhYmxlZCB7XG4gICAgICAgICAgY29sb3I6IHJnYmEoMCwgMCwgMCwgMC4yKTtcbiAgICAgICAgfVxuXG4gICAgICAgIDpob3N0KDpub3QoLnNob3dBcnJvd3MpKSAubmF2aWdhdGlvbkJ1dHRvbiB7XG4gICAgICAgICAgb3BhY2l0eTogMDtcbiAgICAgICAgICB2aXNpYmlsaXR5OiBoaWRkZW47XG4gICAgICAgIH1cblxuICAgICAgICAubmF2aWdhdGlvbkJ1dHRvbiAuaWNvbiB7XG4gICAgICAgICAgaGVpZ2h0OiA0OHB4O1xuICAgICAgICAgIHdpZHRoOiA0OHB4O1xuICAgICAgICB9XG5cbiAgICAgICAgLyogT3ZlcmxheSB2YXJpYW50ICovXG4gICAgICAgIDpob3N0KC5vdmVybGF5QXJyb3dzKSB7XG4gICAgICAgICAgcG9zaXRpb246IHJlbGF0aXZlO1xuICAgICAgICB9XG4gICAgICAgIDpob3N0KC5vdmVybGF5QXJyb3dzKSAubmF2aWdhdGlvbkJ1dHRvbiB7XG4gICAgICAgICAgYm90dG9tOiAwO1xuICAgICAgICAgIGNvbG9yOiByZ2JhKDI1NSwgMjU1LCAyNTUsIDAuNyk7XG4gICAgICAgICAgcG9zaXRpb246IGFic29sdXRlO1xuICAgICAgICAgIHRvcDogMDtcbiAgICAgICAgfVxuICAgICAgICA6aG9zdCgub3ZlcmxheUFycm93cykgI2J1dHRvbkxlZnQge1xuICAgICAgICAgIGxlZnQ6IDA7XG4gICAgICAgIH1cbiAgICAgICAgOmhvc3QoLm92ZXJsYXlBcnJvd3MpICNidXR0b25SaWdodCB7XG4gICAgICAgICAgcmlnaHQ6IDA7XG4gICAgICAgIH1cbiAgICAgICAgOmhvc3QoLm92ZXJsYXlBcnJvd3MpIC5uYXZpZ2F0aW9uQnV0dG9uOmhvdmVyOm5vdCg6ZGlzYWJsZWQpIHtcbiAgICAgICAgICBiYWNrZ3JvdW5kOiByZ2JhKDI1NSwgMjU1LCAyNTUsIDAuMik7XG4gICAgICAgICAgY29sb3I6IHJnYmEoMjU1LCAyNTUsIDI1NSwgMC44KTtcbiAgICAgICAgfVxuICAgICAgICA6aG9zdCgub3ZlcmxheUFycm93cykgLm5hdmlnYXRpb25CdXR0b246YWN0aXZlOm5vdCg6ZGlzYWJsZWQpIHtcbiAgICAgICAgICBiYWNrZ3JvdW5kOiByZ2JhKDI1NSwgMjU1LCAyNTUsIDAuNCk7XG4gICAgICAgICAgY29sb3I6IHJnYmEoMjU1LCAyNTUsIDI1NSwgMC45KTtcbiAgICAgICAgfVxuICAgICAgICA6aG9zdCgub3ZlcmxheUFycm93cykgLm5hdmlnYXRpb25CdXR0b246ZGlzYWJsZWQge1xuICAgICAgICAgIGNvbG9yOiByZ2JhKDI1NSwgMjU1LCAyNTUsIDAuMyk7XG4gICAgICAgIH1cbiAgICAgICAgPC9zdHlsZT5cblxuICAgICAgICA8IS0tXG4gICAgICAgIEFjY2Vzc2liaWxpdHkgbm90ZTogc2luY2UgdGhlIG5hdmlnYXRpb24gb2ZmZXJlZCBieSB0aGUgYXJyb3cgYnV0dG9ucyBzaG91bGRcbiAgICAgICAgYmUgcmVkdW5kYW50ICh0aGF0IGlzLCB0aGVyZSBzaG91bGQgYmUgb3RoZXIgd2F5cyBvZiBuYXZpZ2F0aW5nIHRoZSBsaXN0KSxcbiAgICAgICAgd2UgbWFyayB0aGUgYnV0dG9uIGFzIGFyaWEtaGlkZGVuIHNvIHRoYXQgYXNzaXN0aXZlIGRldmljZXMgaWdub3JlIHRoZW0uXG4gICAgICAgIC0tPlxuICAgICAgICA8YnV0dG9uIGlkPVwiYnV0dG9uTGVmdFwiIGNsYXNzPVwibmF2aWdhdGlvbkJ1dHRvblwiIGRpc2FibGVkIHRhYmluZGV4PVwiLTFcIiBhcmlhLWhpZGRlbj1cInRydWVcIj5cbiAgICAgICAgICA8c3ZnIGNsYXNzPVwiaWNvblwiIHZpZXdCb3g9XCIwIDAgMjQgMjRcIiBwcmVzZXJ2ZUFzcGVjdFJhdGlvPVwieE1pZFlNaWQgbWVldFwiPlxuICAgICAgICAgICAgPGcgaWQ9XCJjaGV2cm9uLWxlZnRcIj5cbiAgICAgICAgICAgICAgPHBhdGggZD1cIk0xNS40MSA3LjQxTDE0IDZsLTYgNiA2IDYgMS40MS0xLjQxTDEwLjgzIDEyelwiLz5cbiAgICAgICAgICAgIDwvZz5cbiAgICAgICAgICA8L3N2Zz5cbiAgICAgICAgPC9idXR0b24+XG4gICAgICAgIDxkaXYgaWQ9XCJhcnJvd05hdmlnYXRpb25Db250YWluZXJcIiByb2xlPVwibm9uZVwiPlxuICAgICAgICAgICR7YmFzZVRlbXBsYXRlfVxuICAgICAgICA8L2Rpdj5cbiAgICAgICAgPGJ1dHRvbiBpZD1cImJ1dHRvblJpZ2h0XCIgY2xhc3M9XCJuYXZpZ2F0aW9uQnV0dG9uXCIgZGlzYWJsZWQgdGFiaW5kZXg9XCItMVwiIGFyaWEtaGlkZGVuPVwidHJ1ZVwiPlxuICAgICAgICAgIDxzdmcgY2xhc3M9XCJpY29uXCIgdmlld0JveD1cIjAgMCAyNCAyNFwiIHByZXNlcnZlQXNwZWN0UmF0aW89XCJ4TWlkWU1pZCBtZWV0XCI+XG4gICAgICAgICAgICA8ZyBpZD1cImNoZXZyb24tcmlnaHRcIj5cbiAgICAgICAgICAgICAgPHBhdGggZD1cIk0xMCA2TDguNTkgNy40MSAxMy4xNyAxMmwtNC41OCA0LjU5TDEwIDE4bDYtNnpcIi8+XG4gICAgICAgICAgICA8L2c+XG4gICAgICAgICAgPC9zdmc+XG4gICAgICAgIDwvYnV0dG9uPlxuICAgICAgYDtcbiAgICB9XG5cbiAgfVxuXG4gIHJldHVybiBBcnJvd1NlbGVjdGlvbjtcbn07XG5cblxuLypcbiAqIEJ5IGRlZmF1bHQsIGEgYnV0dG9uIHdpbGwgYWx3YXlzIHRha2UgZm9jdXMgb24gbW91c2Vkb3duLiBGb3IgdGhpcyBjb21wb25lbnQsXG4gKiB3ZSB3YW50IHRvIG92ZXJyaWRlIHRoYXQgYmVoYXZpb3IsIHN1Y2ggdGhhdCBhIG1vdXNlZG93biBvbiBhIGJ1dHRvbiBrZWVwc1xuICogdGhlIGZvY3VzIG9uIHRoZSBvdXRlciBjb21wb25lbnQuXG4gKi9cbmZ1bmN0aW9uIGFzc3VtZUJ1dHRvbkZvY3VzKGVsZW1lbnQsIGJ1dHRvbikge1xuICBidXR0b24uYWRkRXZlbnRMaXN0ZW5lcignbW91c2Vkb3duJywgZXZlbnQgPT4ge1xuICAgIC8vIEdpdmVuIHRoZSBtYWluIGVsZW1lbnQgdGhlIGZvY3VzIGlmIGl0IGRvZXNuJ3QgYWxyZWFkeSBoYXZlIGl0LlxuICAgIGVsZW1lbnQuZm9jdXMoKTtcbiAgICAvLyBQcmV2ZW50IHRoZSBkZWZhdWx0IGZvY3VzLW9uLW1vdXNlZG93biBiZWhhdmlvci5cbiAgICBldmVudC5wcmV2ZW50RGVmYXVsdCgpO1xuICB9KTtcbn1cblxuZnVuY3Rpb24gZGV2aWNlU3VwcG9ydHNUb3VjaCgpIHtcbiAgcmV0dXJuICdvbnRvdWNoc3RhcnQnIGluIHdpbmRvdyB8fFxuICAgICAgKHdpbmRvdy5Eb2N1bWVudFRvdWNoICYmIGRvY3VtZW50IGluc3RhbmNlb2Ygd2luZG93LkRvY3VtZW50VG91Y2gpO1xufVxuXG4vLyBXZSB0cnkgdG8gZGV0ZWN0IHRoZSBwcmVzZW5jZSBvZiBhIG1vdXNlIGJ5IGxpc3RlbmluZyBmb3IgbW91c2Vtb3ZlIGV2ZW50c1xuLy8gd2hpY2ggYXJlICpub3QqIHRoZSByZXN1bHQgb2YgYSBtb3VzZWRvd24uIE9uIGEgdG91Y2ggZGV2aWNlLCBhIHRhcCBvbiB0aGVcbi8vIHBhZ2Ugd2lsbCBnZW5lcmF0ZSBhIGZha2UgbW91c2Vtb3ZlLCBmb2xsb3dlZCBieSBhIG1vdXNlZG93bi4gV2UgZG9uJ3Qgd2FudFxuLy8gdG8gcmVzcG9uZCB0byB0aG9zZSBmYWtlIG1vdXNlbW92ZSBldmVudHMuIFRvIGRpc2NyaW1pbmF0ZSBiZXR3ZWVuIGZha2UgYW5kXG4vLyByZWFsIG1vdXNlbW92ZSBldmVudHMsIHdoZW4gd2UgZ2V0IGEgbW91c2Vtb3ZlIGV2ZW50LCB3ZSB3YWl0IGZvciBhIGJpdCB0b1xuLy8gc2VlIGlmIHRoZSBzYW1lIGxvY2F0aW9uIGlzIHJlcG9ydGVkIGFzIHRoZSBsb2NhdGlvbiBvZiBhIHN1YnNlcXVlbnRcbi8vIG1vdXNlZG93bi5cbmZ1bmN0aW9uIGxpc3RlbkZvck1vdXNlKGVsZW1lbnQpIHtcblxuICBlbGVtZW50W21vdXNlZG93bkxpc3RlbmVyU3ltYm9sXSA9IGV2ZW50ID0+IHtcbiAgICBpZiAoZWxlbWVudFttb3VzZVRpbWVvdXRTeW1ib2xdKSB7XG4gICAgICBjbGVhclRpbWVvdXQoZWxlbWVudFttb3VzZVRpbWVvdXRTeW1ib2xdKTtcbiAgICB9XG4gICAgZWxlbWVudFtsYXN0TW91c2VYU3ltYm9sXSA9IGV2ZW50LnBhZ2VYO1xuICAgIGVsZW1lbnRbbGFzdE1vdXNlWVN5bWJvbF0gPSBldmVudC5wYWdlWTtcbiAgfTtcbiAgd2luZG93LmFkZEV2ZW50TGlzdGVuZXIoJ21vdXNlZG93bicsIGVsZW1lbnRbbW91c2Vkb3duTGlzdGVuZXJTeW1ib2xdKTtcblxuICBlbGVtZW50W21vdXNlbW92ZUxpc3RlbmVyU3ltYm9sXSA9IGV2ZW50ID0+IHtcbiAgICAvLyBQb3N0cG9uZSBjaGVja2luZyB0aGUgbW91c2Vtb3ZlIGxvY2F0aW9uIHRvIGdpdmUgdGhlIG1vdXNlZG93biBldmVudCBhXG4gICAgLy8gY2hhbmNlIHRvIGZpcmUuIFRoZSAyNTAgbXMgZGVsYXkgaXMganVzdCBndWVzc3dvcms7IGEgc2hvcnRlciBkZWxheVxuICAgIC8vIGRvZXNuJ3Qgc2VlbSB0byB3b3JrLlxuICAgIGVsZW1lbnRbbW91c2VUaW1lb3V0U3ltYm9sXSA9IHNldFRpbWVvdXQoKCkgPT4ge1xuICAgICAgaWYgKGVsZW1lbnRbbGFzdE1vdXNlWFN5bWJvbF0gIT0gbnVsbCAmJiBldmVudC5wYWdlWCAhPT0gZWxlbWVudFtsYXN0TW91c2VYU3ltYm9sXSB8fFxuICAgICAgICAgIGVsZW1lbnRbbGFzdE1vdXNlWVN5bWJvbF0gIT0gbnVsbCAmJiBldmVudC5wYWdlWSAhPT0gZWxlbWVudFtsYXN0TW91c2VZU3ltYm9sXSkge1xuICAgICAgICAvLyBtb3VzZW1vdmUgZXZlbnQgd2FzIGF0IGEgbG9jYXRpb24gb3RoZXIgdGhhbiB0aGUgbGFzdCBtb3VzZWRvd24sXG4gICAgICAgIC8vIGFuZCBoZW5jZSBtb3N0IGxpa2VseSBhIHJlYWwgbW91c2Vtb3ZlIGV2ZW50LlxuICAgICAgICBtb3VzZURldGVjdGVkKGVsZW1lbnQpO1xuICAgICAgfSBlbHNlIHtcbiAgICAgICAgZWxlbWVudFtsYXN0TW91c2VYU3ltYm9sXSA9IGV2ZW50LnBhZ2VYO1xuICAgICAgICBlbGVtZW50W2xhc3RNb3VzZVlTeW1ib2xdID0gZXZlbnQucGFnZVk7XG4gICAgICB9XG4gICAgfSwgMjUwKTtcbiAgfTtcbiAgd2luZG93LmFkZEV2ZW50TGlzdGVuZXIoJ21vdXNlbW92ZScsIGVsZW1lbnRbbW91c2Vtb3ZlTGlzdGVuZXJTeW1ib2xdKTtcbn1cblxuZnVuY3Rpb24gbW91c2VEZXRlY3RlZChlbGVtZW50KSB7XG4gIHNob3dBcnJvd3MoZWxlbWVudCk7XG5cbiAgLy8gV2UgY2FuIHN0b3AgbGlzdGVuaW5nIGZvciBtb3VzZSBldmVudHMgbm93LlxuICBpZiAoZWxlbWVudFttb3VzZVRpbWVvdXRTeW1ib2xdKSB7XG4gICAgY2xlYXJUaW1lb3V0KGVsZW1lbnRbbW91c2VUaW1lb3V0U3ltYm9sXSk7XG4gIH1cbiAgd2luZG93LnJlbW92ZUV2ZW50TGlzdGVuZXIoJ21vdXNlZG93bicsIGVsZW1lbnRbbW91c2Vkb3duTGlzdGVuZXJTeW1ib2xdKTtcbiAgd2luZG93LnJlbW92ZUV2ZW50TGlzdGVuZXIoJ21vdXNlbW92ZScsIGVsZW1lbnRbbW91c2Vtb3ZlTGlzdGVuZXJTeW1ib2xdKTtcbiAgZWxlbWVudFttb3VzZWRvd25MaXN0ZW5lclN5bWJvbF0gPSBudWxsO1xuICBlbGVtZW50W21vdXNlbW92ZUxpc3RlbmVyU3ltYm9sXSA9IG51bGw7XG59XG5cbmZ1bmN0aW9uIHNob3dBcnJvd3MoZWxlbWVudCkge1xuICBlbGVtZW50LmNsYXNzTGlzdC5hZGQoJ3Nob3dBcnJvd3MnKTtcbn1cbiIsImltcG9ydCBzYWZlQXR0cmlidXRlcyBmcm9tICcuL3NhZmVBdHRyaWJ1dGVzJztcblxuXG4vLyBNZW1vaXplZCBtYXBzIG9mIGF0dHJpYnV0ZSB0byBwcm9wZXJ0eSBuYW1lcyBhbmQgdmljZSB2ZXJzYS5cbmNvbnN0IGF0dHJpYnV0ZVRvUHJvcGVydHlOYW1lcyA9IHt9O1xuY29uc3QgcHJvcGVydHlOYW1lc1RvQXR0cmlidXRlcyA9IHt9O1xuXG5cbi8qIEV4cG9ydGVkIGZ1bmN0aW9uIGV4dGVuZHMgYSBiYXNlIGNsYXNzIHdpdGggQXR0cmlidXRlTWFyc2hhbGxpbmcuICovXG5leHBvcnQgZGVmYXVsdCAoYmFzZSkgPT4ge1xuXG4gIC8qKlxuICAgKiBNaXhpbiB3aGljaCBtYXJzaGFsbHMgYXR0cmlidXRlcyB0byBwcm9wZXJ0aWVzIGFuZCB2aWNlIHZlcnNhLlxuICAgKlxuICAgKiBJZiB5b3VyIGNvbXBvbmVudCBleHBvc2VzIGEgc2V0dGVyIGZvciBhIHByb3BlcnR5LCBpdCdzIGdlbmVyYWxseSBhIGdvb2RcbiAgICogaWRlYSB0byBsZXQgZGV2cyB1c2luZyB5b3VyIGNvbXBvbmVudCBiZSBhYmxlIHRvIHNldCB0aGF0IHByb3BlcnR5IGluIEhUTUxcbiAgICogdmlhIGFuIGVsZW1lbnQgYXR0cmlidXRlLiBZb3UgY2FuIGNvZGUgdGhhdCB5b3Vyc2VsZiBieSB3cml0aW5nIGFuXG4gICAqIGBhdHRyaWJ1dGVDaGFuZ2VkQ2FsbGJhY2tgLCBvciB5b3UgY2FuIHVzZSB0aGlzIG1peGluIHRvIGdldCBhIGRlZ3JlZSBvZlxuICAgKiBhdXRvbWF0aWMgc3VwcG9ydC5cbiAgICpcbiAgICogVGhpcyBtaXhpbiBpbXBsZW1lbnRzIGFuIGBhdHRyaWJ1dGVDaGFuZ2VkQ2FsbGJhY2tgIHRoYXQgd2lsbCBhdHRlbXB0IHRvXG4gICAqIGNvbnZlcnQgYSBjaGFuZ2UgaW4gYW4gZWxlbWVudCBhdHRyaWJ1dGUgaW50byBhIGNhbGwgdG8gdGhlIGNvcnJlc3BvbmRpbmdcbiAgICogcHJvcGVydHkgc2V0dGVyLiBBdHRyaWJ1dGVzIHR5cGljYWxseSBmb2xsb3cgaHlwaGVuYXRlZCBuYW1lcyAoXCJmb28tYmFyXCIpLFxuICAgKiB3aGVyZWFzIHByb3BlcnRpZXMgdHlwaWNhbGx5IHVzZSBjYW1lbENhc2UgbmFtZXMgKFwiZm9vQmFyXCIpLiBUaGlzIG1peGluXG4gICAqIHJlc3BlY3RzIHRoYXQgY29udmVudGlvbiwgYXV0b21hdGljYWxseSBtYXBwaW5nIHRoZSBoeXBoZW5hdGVkIGF0dHJpYnV0ZVxuICAgKiBuYW1lIHRvIHRoZSBjb3JyZXNwb25kaW5nIGNhbWVsQ2FzZSBwcm9wZXJ0eSBuYW1lLlxuICAgKlxuICAgKiBFeGFtcGxlOiBZb3UgZGVmaW5lIGEgY29tcG9uZW50IHVzaW5nIHRoaXMgbWl4aW46XG4gICAqXG4gICAqICAgICBjbGFzcyBNeUVsZW1lbnQgZXh0ZW5kcyBBdHRyaWJ1dGVNYXJzaGFsbGluZ01peGluKEhUTUxFbGVtZW50KSB7XG4gICAqICAgICAgIGdldCBmb29CYXIoKSB7IHJldHVybiB0aGlzLl9mb29CYXI7IH1cbiAgICogICAgICAgc2V0IGZvb0Jhcih2YWx1ZSkgeyB0aGlzLl9mb29CYXIgPSB2YWx1ZTsgfVxuICAgKiAgICAgfVxuICAgKiAgICAgY3VzdG9tRWxlbWVudHMuZGVmaW5lKCdteS1lbGVtZW50JywgTXlFbGVtZW50KTtcbiAgICpcbiAgICogSWYgc29tZW9uZSB0aGVuIGluc3RhbnRpYXRlcyB5b3VyIGNvbXBvbmVudCBpbiBIVE1MOlxuICAgKlxuICAgKiAgICAgPG15LWVsZW1lbnQgZm9vLWJhcj1cIkhlbGxvXCI+PC9teS1lbGVtZW50PlxuICAgKlxuICAgKiBUaGVuLCBhZnRlciB0aGUgZWxlbWVudCBoYXMgYmVlbiB1cGdyYWRlZCwgdGhlIGBmb29CYXJgIHNldHRlciB3aWxsXG4gICAqIGF1dG9tYXRpY2FsbHkgYmUgaW52b2tlZCB3aXRoIHRoZSBpbml0aWFsIHZhbHVlIFwiSGVsbG9cIi5cbiAgICpcbiAgICogRm9yIHRoZSB0aW1lIGJlaW5nLCB0aGlzIG1peGluIG9ubHkgc3VwcG9ydHMgc3RyaW5nLXZhbHVlZCBwcm9wZXJ0aWVzLlxuICAgKiBJZiB5b3UnZCBsaWtlIHRvIGNvbnZlcnQgc3RyaW5nIGF0dHJpYnV0ZXMgdG8gb3RoZXIgdHlwZXMgKG51bWJlcnMsXG4gICAqIGJvb2xlYW5zKSwgeW91IG5lZWQgdG8gaW1wbGVtZW50IGBhdHRyaWJ1dGVDaGFuZ2VkQ2FsbGJhY2tgIHlvdXJzZWxmLlxuICAgKi9cbiAgY2xhc3MgQXR0cmlidXRlTWFyc2hhbGxpbmcgZXh0ZW5kcyBiYXNlIHtcblxuICAgIC8qXG4gICAgICogSGFuZGxlIGEgY2hhbmdlIHRvIHRoZSBhdHRyaWJ1dGUgd2l0aCB0aGUgZ2l2ZW4gbmFtZS5cbiAgICAgKi9cbiAgICBhdHRyaWJ1dGVDaGFuZ2VkQ2FsbGJhY2soYXR0cmlidXRlTmFtZSwgb2xkVmFsdWUsIG5ld1ZhbHVlKSB7XG4gICAgICBpZiAoc3VwZXIuYXR0cmlidXRlQ2hhbmdlZENhbGxiYWNrKSB7IHN1cGVyLmF0dHJpYnV0ZUNoYW5nZWRDYWxsYmFjaygpOyB9XG4gICAgICBjb25zdCBwcm9wZXJ0eU5hbWUgPSBhdHRyaWJ1dGVUb1Byb3BlcnR5TmFtZShhdHRyaWJ1dGVOYW1lKTtcbiAgICAgIC8vIElmIHRoZSBhdHRyaWJ1dGUgbmFtZSBjb3JyZXNwb25kcyB0byBhIHByb3BlcnR5IG5hbWUsIHNldCB0aGUgcHJvcGVydHkuXG4gICAgICAvLyBJZ25vcmUgc3RhbmRhcmQgSFRNTEVsZW1lbnQgcHJvcGVydGllcyBoYW5kbGVkIGJ5IHRoZSBET00uXG4gICAgICBpZiAocHJvcGVydHlOYW1lIGluIHRoaXMgJiYgIShwcm9wZXJ0eU5hbWUgaW4gSFRNTEVsZW1lbnQucHJvdG90eXBlKSkge1xuICAgICAgICB0aGlzW3Byb3BlcnR5TmFtZV0gPSBuZXdWYWx1ZTtcbiAgICAgIH1cbiAgICB9XG5cbiAgICBjb25uZWN0ZWRDYWxsYmFjaygpIHtcbiAgICAgIGlmIChzdXBlci5jb25uZWN0ZWRDYWxsYmFjaykgeyBzdXBlci5jb25uZWN0ZWRDYWxsYmFjaygpOyB9XG4gICAgICBzYWZlQXR0cmlidXRlcy5jb25uZWN0ZWQodGhpcyk7XG4gICAgfVxuXG4gICAgc3RhdGljIGdldCBvYnNlcnZlZEF0dHJpYnV0ZXMoKSB7XG4gICAgICByZXR1cm4gYXR0cmlidXRlc0ZvckNsYXNzKHRoaXMpO1xuICAgIH1cblxuICAgIC8qKlxuICAgICAqIFNldC91bnNldCB0aGUgYXR0cmlidXRlIHdpdGggdGhlIGluZGljYXRlZCBuYW1lLlxuICAgICAqXG4gICAgICogVGhpcyBtZXRob2QgZXhpc3RzIHByaW1hcmlseSB0byBoYW5kbGUgdGhlIGNhc2Ugd2hlcmUgYW4gZWxlbWVudCB3YW50cyB0b1xuICAgICAqIHNldCBhIGRlZmF1bHQgcHJvcGVydHkgdmFsdWUgdGhhdCBzaG91bGQgYmUgcmVmbGVjdGVkIGFzIGFuIGF0dHJpYnV0ZS4gQW5cbiAgICAgKiBpbXBvcnRhbnQgbGltaXRhdGlvbiBvZiBjdXN0b20gZWxlbWVudCBjb25zdHVyY3RvcnMgaXMgdGhhdCB0aGV5IGNhbm5vdFxuICAgICAqIHNldCBhdHRyaWJ1dGVzLiBBIGNhbGwgdG8gYHJlZmxlY3RBdHRyaWJ1dGVgIGR1cmluZyB0aGUgY29uc3RydWN0b3Igd2lsbFxuICAgICAqIGJlIGRlZmVycmVkIHVudGlsIHRoZSBlbGVtZW50IGlzIGNvbm5lY3RlZCB0byB0aGUgZG9jdW1lbnQuXG4gICAgICpcbiAgICAgKiBAcGFyYW0ge3N0cmluZ30gYXR0cmlidXRlIC0gVGhlIG5hbWUgb2YgdGhlICphdHRyaWJ1dGUqIChub3QgcHJvcGVydHkpIHRvIHNldC5cbiAgICAgKiBAcGFyYW0ge29iamVjdH0gdmFsdWUgLSBUaGUgdmFsdWUgdG8gc2V0LiBJZiBudWxsLCB0aGUgYXR0cmlidXRlIHdpbGwgYmUgcmVtb3ZlZC5cbiAgICAgKi9cbiAgICByZWZsZWN0QXR0cmlidXRlKGF0dHJpYnV0ZSwgdmFsdWUpIHtcbiAgICAgIHJldHVybiBzYWZlQXR0cmlidXRlcy5zZXRBdHRyaWJ1dGUodGhpcywgYXR0cmlidXRlLCB2YWx1ZSk7XG4gICAgfVxuXG4gICAgLyoqXG4gICAgICogU2V0L3Vuc2V0IHRoZSBjbGFzcyB3aXRoIHRoZSBpbmRpY2F0ZWQgbmFtZS5cbiAgICAgKlxuICAgICAqIFRoaXMgbWV0aG9kIGV4aXN0cyBwcmltYXJpbHkgdG8gaGFuZGxlIHRoZSBjYXNlIHdoZXJlIGFuIGVsZW1lbnQgd2FudHMgdG9cbiAgICAgKiBzZXQgYSBkZWZhdWx0IHByb3BlcnR5IHZhbHVlIHRoYXQgc2hvdWxkIGJlIHJlZmxlY3RlZCBhcyBhcyBjbGFzcy4gQW5cbiAgICAgKiBpbXBvcnRhbnQgbGltaXRhdGlvbiBvZiBjdXN0b20gZWxlbWVudCBjb25zdHVyY3RvcnMgaXMgdGhhdCB0aGV5IGNhbm5vdFxuICAgICAqIHNldCBhdHRyaWJ1dGVzLCBpbmNsdWRpbmcgdGhlIGBjbGFzc2AgYXR0cmlidXRlLiBBIGNhbGwgdG9cbiAgICAgKiBgcmVmbGVjdENsYXNzYCBkdXJpbmcgdGhlIGNvbnN0cnVjdG9yIHdpbGwgYmUgZGVmZXJyZWQgdW50aWwgdGhlIGVsZW1lbnRcbiAgICAgKiBpcyBjb25uZWN0ZWQgdG8gdGhlIGRvY3VtZW50LlxuICAgICAqXG4gICAgICogQHBhcmFtIHtzdHJpbmd9IGNsYXNzTmFtZSAtIFRoZSBuYW1lIG9mIHRoZSBjbGFzcyB0byBzZXQuXG4gICAgICogQHBhcmFtIHtvYmplY3R9IHZhbHVlIC0gVHJ1ZSB0byBzZXQgdGhlIGNsYXNzLCBmYWxzZSB0byByZW1vdmUgaXQuXG4gICAgICovXG4gICAgcmVmbGVjdENsYXNzKGNsYXNzTmFtZSwgdmFsdWUpIHtcbiAgICAgIHJldHVybiBzYWZlQXR0cmlidXRlcy50b2dnbGVDbGFzcyh0aGlzLCBjbGFzc05hbWUsIHZhbHVlKTtcbiAgICB9XG5cbiAgfVxuXG4gIHJldHVybiBBdHRyaWJ1dGVNYXJzaGFsbGluZztcbn07XG5cblxuLy8gQ29udmVydCBoeXBoZW5hdGVkIGZvby1iYXIgYXR0cmlidXRlIG5hbWUgdG8gY2FtZWwgY2FzZSBmb29CYXIgcHJvcGVydHkgbmFtZS5cbmZ1bmN0aW9uIGF0dHJpYnV0ZVRvUHJvcGVydHlOYW1lKGF0dHJpYnV0ZU5hbWUpIHtcbiAgbGV0IHByb3BlcnR5TmFtZSA9IGF0dHJpYnV0ZVRvUHJvcGVydHlOYW1lc1thdHRyaWJ1dGVOYW1lXTtcbiAgaWYgKCFwcm9wZXJ0eU5hbWUpIHtcbiAgICAvLyBDb252ZXJ0IGFuZCBtZW1vaXplLlxuICAgIGNvbnN0IGh5cGVuUmVnRXggPSAvLShbYS16XSkvZztcbiAgICBwcm9wZXJ0eU5hbWUgPSBhdHRyaWJ1dGVOYW1lLnJlcGxhY2UoaHlwZW5SZWdFeCxcbiAgICAgICAgbWF0Y2ggPT4gbWF0Y2hbMV0udG9VcHBlckNhc2UoKSk7XG4gICAgYXR0cmlidXRlVG9Qcm9wZXJ0eU5hbWVzW2F0dHJpYnV0ZU5hbWVdID0gcHJvcGVydHlOYW1lO1xuICB9XG4gIHJldHVybiBwcm9wZXJ0eU5hbWU7XG59XG5cbmZ1bmN0aW9uIGF0dHJpYnV0ZXNGb3JDbGFzcyhjbGFzc0ZuKSB7XG5cbiAgLy8gV2UgdHJlYXQgdGhlIGVsZW1lbnQgYmFzZSBjbGFzc2VzIGFzIGlmIHRoZXkgaGF2ZSBubyBhdHRyaWJ1dGVzLCBzaW5jZSB3ZVxuICAvLyBkb24ndCB3YW50IHRvIHJlY2VpdmUgYXR0cmlidXRlQ2hhbmdlZENhbGxiYWNrIGZvciB0aGVtLlxuICBpZiAoY2xhc3NGbiA9PT0gSFRNTEVsZW1lbnQgfHwgY2xhc3NGbiA9PT0gT2JqZWN0KSB7XG4gICAgcmV0dXJuIFtdO1xuICB9XG5cbiAgLy8gR2V0IGF0dHJpYnV0ZXMgZm9yIHBhcmVudCBjbGFzcy5cbiAgY29uc3QgYmFzZUNsYXNzID0gT2JqZWN0LmdldFByb3RvdHlwZU9mKGNsYXNzRm4ucHJvdG90eXBlKS5jb25zdHJ1Y3RvcjtcbiAgY29uc3QgYmFzZUF0dHJpYnV0ZXMgPSBhdHRyaWJ1dGVzRm9yQ2xhc3MoYmFzZUNsYXNzKTtcblxuICAvLyBHZXQgYXR0cmlidXRlcyBmb3IgdGhpcyBjbGFzcy5cbiAgY29uc3QgcHJvcGVydHlOYW1lcyA9IE9iamVjdC5nZXRPd25Qcm9wZXJ0eU5hbWVzKGNsYXNzRm4ucHJvdG90eXBlKTtcbiAgY29uc3Qgc2V0dGVyTmFtZXMgPSBwcm9wZXJ0eU5hbWVzLmZpbHRlcihwcm9wZXJ0eU5hbWUgPT5cbiAgICB0eXBlb2YgT2JqZWN0LmdldE93blByb3BlcnR5RGVzY3JpcHRvcihcbiAgICAgICAgY2xhc3NGbi5wcm90b3R5cGUsIHByb3BlcnR5TmFtZSkuc2V0ID09PSAnZnVuY3Rpb24nKTtcbiAgY29uc3QgYXR0cmlidXRlcyA9IHNldHRlck5hbWVzLm1hcChzZXR0ZXJOYW1lID0+XG4gICAgICBwcm9wZXJ0eU5hbWVUb0F0dHJpYnV0ZShzZXR0ZXJOYW1lKSk7XG5cbiAgLy8gTWVyZ2UuXG4gIGNvbnN0IGRpZmYgPSBhdHRyaWJ1dGVzLmZpbHRlcihhdHRyaWJ1dGUgPT5cbiAgICAgIGJhc2VBdHRyaWJ1dGVzLmluZGV4T2YoYXR0cmlidXRlKSA8IDApO1xuICByZXR1cm4gYmFzZUF0dHJpYnV0ZXMuY29uY2F0KGRpZmYpO1xufVxuXG4vLyBDb252ZXJ0IGEgY2FtZWwgY2FzZSBmb29CYXIgcHJvcGVydHkgbmFtZSB0byBhIGh5cGhlbmF0ZWQgZm9vLWJhciBhdHRyaWJ1dGUuXG5mdW5jdGlvbiBwcm9wZXJ0eU5hbWVUb0F0dHJpYnV0ZShwcm9wZXJ0eU5hbWUpIHtcbiAgbGV0IGF0dHJpYnV0ZSA9IHByb3BlcnR5TmFtZXNUb0F0dHJpYnV0ZXNbcHJvcGVydHlOYW1lXTtcbiAgaWYgKCFhdHRyaWJ1dGUpIHtcbiAgICAvLyBDb252ZXJ0IGFuZCBtZW1vaXplLlxuICAgIGNvbnN0IHVwcGVyY2FzZVJlZ0V4ID0gLyhbQS1aXSkvZztcbiAgICBhdHRyaWJ1dGUgPSBwcm9wZXJ0eU5hbWUucmVwbGFjZSh1cHBlcmNhc2VSZWdFeCwgJy0kMScpLnRvTG93ZXJDYXNlKCk7XG4gIH1cbiAgcmV0dXJuIGF0dHJpYnV0ZTtcbn1cbiIsIi8qIEV4cG9ydGVkIGZ1bmN0aW9uIGV4dGVuZHMgYSBiYXNlIGNsYXNzIHdpdGggQ2xpY2tTZWxlY3Rpb24uICovXG5leHBvcnQgZGVmYXVsdCAoYmFzZSkgPT4ge1xuXG4gIC8qKlxuICAgKiBNaXhpbiB3aGljaCBtYXBzIGEgY2xpY2sgKGFjdHVhbGx5LCBhIG1vdXNlZG93bikgdG8gYSBzZWxlY3Rpb24uXG4gICAqXG4gICAqIFRoaXMgc2ltcGxlIG1peGluIGlzIHVzZWZ1bCBpbiBsaXN0IGJveC1saWtlIGVsZW1lbnRzLCB3aGVyZSBhIGNsaWNrIG9uIGFcbiAgICogbGlzdCBpdGVtIGltcGxpY2l0bHkgc2VsZWN0cyBpdC5cbiAgICpcbiAgICogVGhpcyBtaXhpbiBleHBlY3RzIHRoZSBjb21wb25lbnQgdG8gcHJvdmlkZSBhbiBgaXRlbXNgIHByb3BlcnR5LiBZb3UgY2FuXG4gICAqIHByb3ZpZGUgdGhhdCBwcm9wZXJ0eSB5b3Vyc2VsZiwgb3IgdXNlXG4gICAqIFtDb250ZW50SXRlbXNNaXhpbl0oQ29udGVudEl0ZW1zTWl4aW4ubWQpLiBUaGlzIG1peGluIGFsc28gZXhwZWN0cyB0aGVcbiAgICogY29tcG9uZW50IHRvIGRlZmluZSBhIGBzZWxlY3RlZEluZGV4YCBwcm9wZXJ0eS4gWW91IGNhbiBwcm92aWRlIHRoYXRcbiAgICogeW91cnNlbGYsIG9yIHVzZSBbU2luZ2xlU2VsZWN0aW9uTWl4aW5dKFNpbmdsZVNlbGVjdGlvbk1peGluLm1kKS5cbiAgICovXG4gIGNsYXNzIENsaWNrU2VsZWN0aW9uIGV4dGVuZHMgYmFzZSB7XG5cbiAgICBjb25zdHJ1Y3RvcigpIHtcbiAgICAgIHN1cGVyKCk7XG4gICAgICAvKlxuICAgICAgICogUkVWSUVXOiBXaGljaCBldmVudCBzaG91bGQgd2UgbGlzdGVuIHRvIGhlcmU/XG4gICAgICAgKlxuICAgICAgICogVGhlIHN0YW5kYXJkIHVzZSBmb3IgdGhpcyBtaXhpbiBpcyBpbiBsaXN0IGJveGVzLiBMaXN0IGJveGVzIGRvbid0XG4gICAgICAgKiBhcHBlYXIgdG8gYmUgY29uc2lzdGVudCB3aXRoIHJlZ2FyZCB0byB3aGV0aGVyIHRoZXkgc2VsZWN0IG9uIG1vdXNlZG93blxuICAgICAgICogb3IgY2xpY2svbW91c2V1cC5cbiAgICAgICAqL1xuICAgICAgdGhpcy5hZGRFdmVudExpc3RlbmVyKCdtb3VzZWRvd24nLCBldmVudCA9PiB7XG4gICAgICAgIC8vIEhBQ0s6IElmIHRoZSBpdGVtIGlzIGEgYnV0dG9uLCB0aGUgZXZlbnQgc2VlbXMgdG8gYmUgcmFpc2VkIGluXG4gICAgICAgIC8vIHBoYXNlIDIgKEFUX1RBUkdFVCksIGJ1dCB0aGUgdGFyZ2V0IGlzIHRoZSBjb21wb25lbnQsIG5vdCBpdGVtLlxuICAgICAgICAvLyBOZWVkIHRvIGludmVzaWdhdGUuXG4gICAgICAgIGNvbnN0IHRhcmdldCA9IGV2ZW50LnRhcmdldCA9PT0gdGhpcyA/XG4gICAgICAgICAgZXZlbnQucGF0aFswXSA6XG4gICAgICAgICAgZXZlbnQudGFyZ2V0O1xuICAgICAgICBjb25zdCBpbmRleCA9IGluZGV4T2ZDb250YWluaW5nSXRlbSh0aGlzLCB0YXJnZXQpO1xuICAgICAgICBpZiAoaW5kZXggPj0gMCkge1xuICAgICAgICAgIHRoaXMuc2VsZWN0ZWRJbmRleCA9IGluZGV4O1xuICAgICAgICAgIC8vIE5vdGU6IFdlIGRvbid0IGNhbGwgcHJldmVudERlZmF1bHQgaGVyZS4gVGhlIGRlZmF1bHQgYmVoYXZpb3IgZm9yXG4gICAgICAgICAgLy8gbW91c2Vkb3duIGluY2x1ZGVzIHNldHRpbmcga2V5Ym9hcmQgZm9jdXMgaWYgdGhlIGVsZW1lbnQgZG9lc24ndFxuICAgICAgICAgIC8vIGFscmVhZHkgaGF2ZSB0aGUgZm9jdXMsIGFuZCB3ZSB3YW50IHRvIHByZXNlcnZlIHRoYXQgYmVoYXZpb3IuXG4gICAgICAgICAgZXZlbnQuc3RvcFByb3BhZ2F0aW9uKCk7XG4gICAgICAgIH1cbiAgICAgIH0pO1xuICAgIH1cblxuICAgIC8vIERlZmF1bHQgaW1wbGVtZW50YXRpb24uIFRoaXMgd2lsbCB0eXBpY2FsbHkgYmUgaGFuZGxlZCBieSBvdGhlciBtaXhpbnMuXG4gICAgZ2V0IHNlbGVjdGVkSW5kZXgoKSB7XG4gICAgICByZXR1cm4gc3VwZXIuc2VsZWN0ZWRJbmRleDtcbiAgICB9XG4gICAgc2V0IHNlbGVjdGVkSW5kZXgoaW5kZXgpIHtcbiAgICAgIGlmICgnc2VsZWN0ZWRJbmRleCcgaW4gYmFzZS5wcm90b3R5cGUpIHsgc3VwZXIuc2VsZWN0ZWRJbmRleCA9IGluZGV4OyB9XG4gICAgfVxuXG4gIH1cblxuICByZXR1cm4gQ2xpY2tTZWxlY3Rpb247XG59O1xuXG5cbi8qXG4gKiBSZXR1cm4gaW5kZXggb2YgdGhlIGVsZW1lbnQgaXRlbXMgdGhhdCBlaXRoZXIgaXMgb3IgY29udGFpbnMgdGhlIGluZGljYXRlZFxuICogdGFyZ2V0LiBSZXR1cm4gLTEgaWYgbm90IGZvdW5kLlxuICovXG5mdW5jdGlvbiBpbmRleE9mQ29udGFpbmluZ0l0ZW0oZWxlbWVudCwgdGFyZ2V0KSB7XG4gIGNvbnN0IGl0ZW1zID0gZWxlbWVudC5pdGVtcztcbiAgY29uc3QgaXRlbUNvdW50ID0gaXRlbXMgPyBpdGVtcy5sZW5ndGggOiAwO1xuICBmb3IgKGxldCBpID0gMDsgaSA8IGl0ZW1Db3VudDsgaSsrKSB7XG4gICAgbGV0IGl0ZW0gPSBpdGVtc1tpXTtcbiAgICBpZiAoaXRlbSA9PT0gdGFyZ2V0IHx8IGl0ZW0uY29udGFpbnModGFyZ2V0KSkge1xuICAgICAgcmV0dXJuIGk7XG4gICAgfVxuICB9XG4gIHJldHVybiAtMTtcbn1cbiIsIi8qIEV4cG9ydGVkIGZ1bmN0aW9uIGV4dGVuZHMgYSBiYXNlIGNsYXNzIHdpdGggQ29tcG9zYWJsZS4gKi9cbmV4cG9ydCBkZWZhdWx0IChiYXNlKSA9PiB7XG5cbiAgLyoqXG4gICAqIE1peGluIHRvIG1ha2UgYSBjbGFzcyBtb3JlIGVhc2lseSBjb21wb3NhYmxlIHdpdGggb3RoZXIgbWl4aW5zLlxuICAgKlxuICAgKiBUaGlzIG1peGluIGNvbnRyaWJ1dGVzIGEgYGNvbXBvc2VgIG1ldGhvZCB0aGF0IGFwcGxpZXMgYSBzZXQgb2YgbWl4aW5cbiAgICogZnVuY3Rpb25zIGFuZCByZXR1cm5zIHRoZSByZXN1bHRpbmcgbmV3IGNsYXNzLiBUaGlzIHN1Z2FyIGNhbiBtYWtlIHRoZVxuICAgKiBhcHBsaWNhdGlvbiBvZiBtYW55IG1peGlucyBhdCBvbmNlIGVhc2llciB0byByZWFkLlxuICAgKi9cbiAgY2xhc3MgQ29tcG9zYWJsZSBleHRlbmRzIGJhc2Uge1xuXG4gICAgLyoqXG4gICAgICogQXBwbHkgYSBzZXQgb2YgbWl4aW4gZnVuY3Rpb25zIG9yIG1peGluIG9iamVjdHMgdG8gdGhlIHByZXNlbnQgY2xhc3MgYW5kXG4gICAgICogcmV0dXJuIHRoZSBuZXcgY2xhc3MuXG4gICAgICpcbiAgICAgKiBJbnN0ZWFkIG9mIHdyaXRpbmc6XG4gICAgICpcbiAgICAgKiAgICAgbGV0IE15Q2xhc3MgPSBNaXhpbjEoTWl4aW4yKE1peGluMyhNaXhpbjQoTWl4aW41KEJhc2VDbGFzcykpKSkpO1xuICAgICAqXG4gICAgICogWW91IGNhbiB3cml0ZTpcbiAgICAgKlxuICAgICAqICAgICBsZXQgTXlDbGFzcyA9IENvbXBvc2FibGVNaXhpbihCYXNlQ2xhc3MpLmNvbXBvc2UoXG4gICAgICogICAgICAgTWl4aW4xLFxuICAgICAqICAgICAgIE1peGluMixcbiAgICAgKiAgICAgICBNaXhpbjMsXG4gICAgICogICAgICAgTWl4aW40LFxuICAgICAqICAgICAgIE1peGluNVxuICAgICAqICAgICApO1xuICAgICAqXG4gICAgICogVGhpcyBmdW5jdGlvbiBjYW4gYWxzbyB0YWtlIG1peGluIG9iamVjdHMuIEEgbWl4aW4gb2JqZWN0IGlzIGp1c3QgYVxuICAgICAqIHNob3J0aGFuZCBmb3IgYSBtaXhpbiBmdW5jdGlvbiB0aGF0IGNyZWF0ZXMgYSBuZXcgc3ViY2xhc3Mgd2l0aCB0aGUgZ2l2ZW5cbiAgICAgKiBtZW1iZXJzLiBUaGUgbWl4aW4gb2JqZWN0J3MgbWVtYmVycyBhcmUgKm5vdCogY29waWVkIGRpcmVjdGx5IG9udG8gdGhlXG4gICAgICogcHJvdG90eXBlIG9mIHRoZSBiYXNlIGNsYXNzLCBhcyB3aXRoIHRyYWRpdGlvbmFsIG1peGlucy5cbiAgICAgKlxuICAgICAqIEluIGFkZGl0aW9uIHRvIHByb3ZpZGluZyBzeW50YWN0aWMgc3VnYXIsIHRoaXMgbWl4aW4gY2FuIGJlIHVzZWQgdG9cbiAgICAgKiBkZWZpbmUgYSBjbGFzcyBpbiBFUzUsIHdoaWNoIGxhY2tzIEVTNidzIGBjbGFzc2Aga2V5d29yZC5cbiAgICAgKlxuICAgICAqIEBwYXJhbSB7Li4ubWl4aW5zfSBtaXhpbnMgLSBBIHNldCBvZiBtaXhpbiBmdW5jdGlvbnMgb3Igb2JqZWN0cyB0byBhcHBseS5cbiAgICAgKi9cbiAgICBzdGF0aWMgY29tcG9zZSguLi5taXhpbnMpIHtcbiAgICAgIC8vIFdlIGNyZWF0ZSBhIG5ldyBzdWJjbGFzcyBmb3IgZWFjaCBtaXhpbiBpbiB0dXJuLiBUaGUgcmVzdWx0IGJlY29tZXNcbiAgICAgIC8vIHRoZSBiYXNlIGNsYXNzIGV4dGVuZGVkIGJ5IGFueSBzdWJzZXF1ZW50IG1peGlucy4gSXQgdHVybnMgb3V0IHRoYXRcbiAgICAgIC8vIHdlIGNhbiB1c2UgQXJyYXkucmVkdWNlKCkgdG8gY29uY2lzZWx5IGV4cHJlc3MgdGhpcywgdXNpbmcgdGhlIGN1cnJlbnRcbiAgICAgIC8vIG9iamVjdCBhcyB0aGUgc2VlZCBmb3IgcmVkdWNlKCkuXG4gICAgICByZXR1cm4gbWl4aW5zLnJlZHVjZShjb21wb3NlQ2xhc3MsIHRoaXMpO1xuICAgIH1cblxuICB9XG5cbiAgcmV0dXJuIENvbXBvc2FibGU7XG59O1xuXG5cbi8vIFByb3BlcnRpZXMgZGVmaW5lZCBieSBPYmplY3QgdGhhdCB3ZSBkb24ndCB3YW50IHRvIG1peGluLlxuY29uc3QgTk9OX01JWEFCTEVfT0JKRUNUX1BST1BFUlRJRVMgPSBbXG4gICdjb25zdHJ1Y3Rvcidcbl07XG5cbi8qXG4gKiBBcHBseSB0aGUgbWl4aW4gdG8gdGhlIGdpdmVuIGJhc2UgY2xhc3MgdG8gcmV0dXJuIGEgbmV3IGNsYXNzLlxuICogVGhlIG1peGluIGNhbiBlaXRoZXIgYmUgYSBmdW5jdGlvbiB0aGF0IHJldHVybnMgdGhlIG1vZGlmaWVkIGNsYXNzLCBvciBhXG4gKiBwbGFpbiBvYmplY3Qgd2hvc2UgbWVtYmVycyB3aWxsIGJlIGNvcGllZCB0byB0aGUgbmV3IGNsYXNzJyBwcm90b3R5cGUuXG4gKi9cbmZ1bmN0aW9uIGNvbXBvc2VDbGFzcyhiYXNlLCBtaXhpbikge1xuICBpZiAodHlwZW9mIG1peGluID09PSAnZnVuY3Rpb24nKSB7XG4gICAgLy8gTWl4aW4gZnVuY3Rpb25cbiAgICByZXR1cm4gbWl4aW4oYmFzZSk7XG4gIH0gZWxzZSB7XG4gICAgLy8gTWl4aW4gb2JqZWN0XG4gICAgY2xhc3MgU3ViY2xhc3MgZXh0ZW5kcyBiYXNlIHt9XG4gICAgY29weU93blByb3BlcnRpZXMobWl4aW4sIFN1YmNsYXNzLnByb3RvdHlwZSwgTk9OX01JWEFCTEVfT0JKRUNUX1BST1BFUlRJRVMpO1xuICAgIHJldHVybiBTdWJjbGFzcztcbiAgfVxufVxuXG5cbi8qXG4gKiBDb3B5IHRoZSBnaXZlbiBwcm9wZXJ0aWVzL21ldGhvZHMgdG8gdGhlIHRhcmdldC5cbiAqIFJldHVybiB0aGUgdXBkYXRlZCB0YXJnZXQuXG4gKi9cbmZ1bmN0aW9uIGNvcHlPd25Qcm9wZXJ0aWVzKHNvdXJjZSwgdGFyZ2V0LCBpZ25vcmVQcm9wZXJ0eU5hbWVzID0gW10pIHtcbiAgT2JqZWN0LmdldE93blByb3BlcnR5TmFtZXMoc291cmNlKS5mb3JFYWNoKG5hbWUgPT4ge1xuICAgIGlmIChpZ25vcmVQcm9wZXJ0eU5hbWVzLmluZGV4T2YobmFtZSkgPCAwKSB7XG4gICAgICBjb25zdCBkZXNjcmlwdG9yID0gT2JqZWN0LmdldE93blByb3BlcnR5RGVzY3JpcHRvcihzb3VyY2UsIG5hbWUpO1xuICAgICAgT2JqZWN0LmRlZmluZVByb3BlcnR5KHRhcmdldCwgbmFtZSwgZGVzY3JpcHRvcik7XG4gICAgfVxuICB9KTtcbiAgcmV0dXJuIHRhcmdldDtcbn1cbiIsImltcG9ydCBjcmVhdGVTeW1ib2wgZnJvbSAnLi9jcmVhdGVTeW1ib2wnO1xuaW1wb3J0IHRvZ2dsZUNsYXNzIGZyb20gJy4vdG9nZ2xlQ2xhc3MnO1xuaW1wb3J0IHN5bWJvbHMgZnJvbSAnLi9zeW1ib2xzJztcblxuXG4vLyBTeW1ib2xzIGZvciBwcml2YXRlIGRhdGEgbWVtYmVycyBvbiBhbiBlbGVtZW50LlxuY29uc3QgaXRlbXNTeW1ib2wgPSBjcmVhdGVTeW1ib2woJ2l0ZW1zJyk7XG5jb25zdCBpdGVtSW5pdGlhbGl6ZWRTeW1ib2wgPSBjcmVhdGVTeW1ib2woJ2l0ZW1Jbml0aWFsaXplZCcpO1xuXG5cbi8qIEV4cG9ydGVkIGZ1bmN0aW9uIGV4dGVuZHMgYSBiYXNlIGNsYXNzIHdpdGggQ29udGVudEl0ZW1zLiAqL1xuZXhwb3J0IGRlZmF1bHQgKGJhc2UpID0+IHtcblxuICAvKipcbiAgICogTWl4aW4gd2hpY2ggbWFwcyBjb250ZW50IHNlbWFudGljcyAoZWxlbWVudHMpIHRvIGxpc3QgaXRlbSBzZW1hbnRpY3MuXG4gICAqXG4gICAqIEl0ZW1zIGRpZmZlciBmcm9tIGVsZW1lbnQgY29udGVudHMgaW4gc2V2ZXJhbCB3YXlzOlxuICAgKlxuICAgKiAqIFRoZXkgYXJlIG9mdGVuIHJlZmVyZW5jZWQgdmlhIGluZGV4LlxuICAgKiAqIFRoZXkgbWF5IGhhdmUgYSBzZWxlY3Rpb24gc3RhdGUuXG4gICAqICogSXQncyBjb21tb24gdG8gZG8gd29yayB0byBpbml0aWFsaXplIHRoZSBhcHBlYXJhbmNlIG9yIHN0YXRlIG9mIGEgbmV3XG4gICAqICAgaXRlbS5cbiAgICogKiBBdXhpbGlhcnkgaW52aXNpYmxlIGNoaWxkIGVsZW1lbnRzIGFyZSBmaWx0ZXJlZCBvdXQgYW5kIG5vdCBjb3VudGVkIGFzXG4gICAqICAgaXRlbXMuIEF1eGlsaWFyeSBlbGVtZW50cyBpbmNsdWRlIGxpbmssIHNjcmlwdCwgc3R5bGUsIGFuZCB0ZW1wbGF0ZVxuICAgKiAgIGVsZW1lbnRzLiBUaGlzIGZpbHRlcmluZyBlbnN1cmVzIHRoYXQgdGhvc2UgYXV4aWxpYXJ5IGVsZW1lbnRzIGNhbiBiZVxuICAgKiAgIHVzZWQgaW4gbWFya3VwIGluc2lkZSBvZiBhIGxpc3Qgd2l0aG91dCBiZWluZyB0cmVhdGVkIGFzIGxpc3QgaXRlbXMuXG4gICAqXG4gICAqIFRoaXMgbWl4aW4gZXhwZWN0cyBhIGNvbXBvbmVudCB0byBwcm92aWRlIGEgYGNvbnRlbnRgIHByb3BlcnR5IHJldHVybmluZyBhXG4gICAqIHJhdyBzZXQgb2YgZWxlbWVudHMuIFlvdSBjYW4gcHJvdmlkZSB0aGF0IHlvdXJzZWxmLCBvciB1c2VcbiAgICogW0Rpc3RyaWJ1dGVkQ2hpbGRyZW5Db250ZW50TWl4aW5dKERpc3RyaWJ1dGVkQ2hpbGRyZW5Db250ZW50TWl4aW4ubWQpLlxuICAgKlxuICAgKiBUaGUgbW9zdCBjb21tb25seSByZWZlcmVuY2VkIHByb3BlcnR5IGRlZmluZWQgYnkgdGhpcyBtaXhpbiBpcyB0aGUgYGl0ZW1zYFxuICAgKiBwcm9wZXJ0eS4gVG8gYXZvaWQgaGF2aW5nIHRvIGRvIHdvcmsgZWFjaCB0aW1lIHRoYXQgcHJvcGVydHkgaXMgcmVxdWVzdGVkLFxuICAgKiB0aGlzIG1peGluIHN1cHBvcnRzIGFuIG9wdGltaXplZCBtb2RlLiBJZiB5b3UgaW52b2tlIHRoZSBgY29udGVudENoYW5nZWRgXG4gICAqIG1ldGhvZCB3aGVuIHRoZSBzZXQgb2YgaXRlbXMgY2hhbmdlcywgdGhlIG1peGluIGNvbmNsdWRlcyB0aGF0IHlvdSdsbCB0YWtlXG4gICAqIGNhcmUgb2Ygbm90aWZ5aW5nIGl0IG9mIGZ1dHVyZSBjaGFuZ2VzLCBhbmQgdHVybnMgb24gdGhlIG9wdGltaXphdGlvbi4gV2l0aFxuICAgKiB0aGF0IG9uLCB0aGUgbWl4aW4gc2F2ZXMgYSByZWZlcmVuY2UgdG8gdGhlIGNvbXB1dGVkIHNldCBvZiBpdGVtcywgYW5kIHdpbGxcbiAgICogcmV0dXJuIHRoYXQgaW1tZWRpYXRlbHkgb24gc3Vic2VxdWVudCBjYWxscyB0byB0aGUgYGl0ZW1zYCBwcm9wZXJ0eS4gSWYgeW91XG4gICAqIHVzZSB0aGlzIG1peGluIGluIGNvbmp1bmN0aW9uIHdpdGhcbiAgICogW0Rpc3RyaWJ1dGVkQ2hpbGRyZW5Db250ZW50TWl4aW5dKERpc3RyaWJ1dGVkQ2hpbGRyZW5Db250ZW50TWl4aW4ubWQpLCB0aGVcbiAgICogYGNvbnRlbnRDaGFuZ2VkYCBtZXRob2Qgd2lsbCBiZSBpbnZva2VkIGZvciB5b3Ugd2hlbiB0aGUgZWxlbWVudCdzIGNoaWxkcmVuXG4gICAqIGNoYW5nZSwgdHVybmluZyBvbiB0aGUgb3B0aW1pemF0aW9uIGF1dG9tYXRpY2FsbHkuXG4gICAqL1xuICBjbGFzcyBDb250ZW50SXRlbXMgZXh0ZW5kcyBiYXNlIHtcblxuICAgIGNvbnRlbnRDaGFuZ2VkKCkge1xuICAgICAgaWYgKHN1cGVyLmNvbnRlbnRDaGFuZ2VkKSB7IHN1cGVyLmNvbnRlbnRDaGFuZ2VkKCk7IH1cblxuICAgICAgLy8gU2luY2Ugd2UgZ290IHRoZSBjb250ZW50Q2hhbmdlZCBjYWxsLCB3ZSdsbCBhc3N1bWUgd2UnbGwgYmUgbm90aWZpZWQgaWZcbiAgICAgIC8vIHRoZSBzZXQgb2YgaXRlbXMgY2hhbmdlcyBsYXRlci4gV2UgdHVybiBvbiBtZW1vaXphdGlvbiBvZiB0aGUgaXRlbXNcbiAgICAgIC8vIHByb3BlcnR5IGJ5IHNldHRpbmcgb3VyIGludGVybmFsIHByb3BlcnR5IHRvIG51bGwgKGluc3RlYWQgb2ZcbiAgICAgIC8vIHVuZGVmaW5lZCkuXG4gICAgICB0aGlzW2l0ZW1zU3ltYm9sXSA9IG51bGw7XG5cbiAgICAgIHRoaXNbc3ltYm9scy5pdGVtc0NoYW5nZWRdKCk7XG4gICAgfVxuXG4gICAgLyoqXG4gICAgICogVGhpcyBtZXRob2QgaXMgaW52b2tlZCB3aGVuZXZlciBhIG5ldyBpdGVtIGlzIGFkZGVkIHRvIHRoZSBsaXN0LlxuICAgICAqXG4gICAgICogVGhlIGRlZmF1bHQgaW1wbGVtZW50YXRpb24gb2YgdGhpcyBtZXRob2QgZG9lcyBub3RoaW5nLiBZb3UgY2FuIG92ZXJyaWRlXG4gICAgICogdGhpcyB0byBwZXJmb3JtIHBlci1pdGVtIGluaXRpYWxpemF0aW9uLlxuICAgICAqXG4gICAgICogQHBhcmFtIHtIVE1MRWxlbWVudH0gaXRlbSAtIFRoZSBpdGVtIHRoYXQgd2FzIGFkZGVkLlxuICAgICAqL1xuICAgIFtzeW1ib2xzLml0ZW1BZGRlZF0oaXRlbSkge1xuICAgICAgaWYgKHN1cGVyW3N5bWJvbHMuaXRlbUFkZGVkXSkgeyBzdXBlcltzeW1ib2xzLml0ZW1BZGRlZF0oaXRlbSk7IH1cbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBUaGUgc2VsZWN0aW9uIHN0YXRlIGZvciBhIHNpbmdsZSBpdGVtIGhhcyBjaGFuZ2VkLlxuICAgICAqXG4gICAgICogSW52b2tlIHRoaXMgbWV0aG9kIHRvIHNpZ25hbCB0aGF0IHRoZSBzZWxlY3RlZCBzdGF0ZSBvZiB0aGUgaW5kaWNhdGVkIGl0ZW1cbiAgICAgKiBoYXMgY2hhbmdlZC4gQnkgZGVmYXVsdCwgdGhpcyBhcHBsaWVzIGEgYHNlbGVjdGVkYCBDU1MgY2xhc3MgaWYgdGhlIGl0ZW1cbiAgICAgKiBpcyBzZWxlY3RlZCwgYW5kIHJlbW92ZWQgaXQgaWYgbm90IHNlbGVjdGVkLlxuICAgICAqXG4gICAgICogQHBhcmFtIHtIVE1MRWxlbWVudH0gaXRlbSAtIFRoZSBpdGVtIHdob3NlIHNlbGVjdGlvbiBzdGF0ZSBoYXMgY2hhbmdlZC5cbiAgICAgKiBAcGFyYW0ge2Jvb2xlYW59IHNlbGVjdGVkIC0gVHJ1ZSBpZiB0aGUgaXRlbSBpcyBzZWxlY3RlZCwgZmFsc2UgaWYgbm90LlxuICAgICAqL1xuICAgIFtzeW1ib2xzLml0ZW1TZWxlY3RlZF0oaXRlbSwgc2VsZWN0ZWQpIHtcbiAgICAgIGlmIChzdXBlcltzeW1ib2xzLml0ZW1TZWxlY3RlZF0pIHsgc3VwZXJbc3ltYm9scy5pdGVtU2VsZWN0ZWRdKGl0ZW0sIHNlbGVjdGVkKTsgfVxuICAgICAgdG9nZ2xlQ2xhc3MoaXRlbSwgJ3NlbGVjdGVkJywgc2VsZWN0ZWQpO1xuICAgIH1cblxuICAgIC8qKlxuICAgICAqIFRoZSBjdXJyZW50IHNldCBvZiBpdGVtcyBpbiB0aGUgbGlzdC4gU2VlIHRoZSB0b3AtbGV2ZWwgZG9jdW1lbnRhdGlvbiBmb3JcbiAgICAgKiBtaXhpbiBmb3IgYSBkZXNjcmlwdGlvbiBvZiBob3cgaXRlbXMgZGlmZmVyIGZyb20gcGxhaW4gY29udGVudC5cbiAgICAgKlxuICAgICAqIEB0eXBlIHtIVE1MRWxlbWVudFtdfVxuICAgICAqL1xuICAgIGdldCBpdGVtcygpIHtcbiAgICAgIGxldCBpdGVtcztcbiAgICAgIGlmICh0aGlzW2l0ZW1zU3ltYm9sXSA9PSBudWxsKSB7XG4gICAgICAgIGl0ZW1zID0gZmlsdGVyQXV4aWxpYXJ5RWxlbWVudHModGhpcy5jb250ZW50KTtcbiAgICAgICAgLy8gTm90ZTogdGVzdCBmb3IgKmVxdWFsaXR5KiB3aXRoIG51bGw7IGRvbid0IHRyZWF0IHVuZGVmaW5lZCBhcyBhIG1hdGNoLlxuICAgICAgICBpZiAodGhpc1tpdGVtc1N5bWJvbF0gPT09IG51bGwpIHtcbiAgICAgICAgICAvLyBNZW1vaXplIHRoZSBzZXQgb2YgaXRlbXMuXG4gICAgICAgICAgdGhpc1tpdGVtc1N5bWJvbF0gPSBpdGVtcztcbiAgICAgICAgfVxuICAgICAgfSBlbHNlIHtcbiAgICAgICAgLy8gUmV0dXJuIHRoZSBtZW1vaXplZCBpdGVtcy5cbiAgICAgICAgaXRlbXMgPSB0aGlzW2l0ZW1zU3ltYm9sXTtcbiAgICAgIH1cbiAgICAgIHJldHVybiBpdGVtcztcbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBUaGlzIG1ldGhvZCBpcyBpbnZva2VkIHdoZW4gdGhlIHVuZGVybHlpbmcgY29udGVudHMgY2hhbmdlLiBJdCBpcyBhbHNvXG4gICAgICogaW52b2tlZCBvbiBjb21wb25lbnQgaW5pdGlhbGl6YXRpb24g4oCTIHNpbmNlIHRoZSBpdGVtcyBoYXZlIFwiY2hhbmdlZFwiIGZyb21cbiAgICAgKiBiZWluZyBub3RoaW5nLlxuICAgICAqL1xuICAgIFtzeW1ib2xzLml0ZW1zQ2hhbmdlZF0oKSB7XG4gICAgICBpZiAoc3VwZXJbc3ltYm9scy5pdGVtc0NoYW5nZWRdKSB7IHN1cGVyW3N5bWJvbHMuaXRlbXNDaGFuZ2VkXSgpOyB9XG5cbiAgICAgIC8vIFBlcmZvcm0gcGVyLWl0ZW0gaW5pdGlhbGl6YXRpb24uXG4gICAgICBBcnJheS5wcm90b3R5cGUuZm9yRWFjaC5jYWxsKHRoaXMuaXRlbXMsIGl0ZW0gPT4ge1xuICAgICAgICBpZiAoIWl0ZW1baXRlbUluaXRpYWxpemVkU3ltYm9sXSkge1xuICAgICAgICAgIHRoaXNbc3ltYm9scy5pdGVtQWRkZWRdKGl0ZW0pO1xuICAgICAgICAgIGl0ZW1baXRlbUluaXRpYWxpemVkU3ltYm9sXSA9IHRydWU7XG4gICAgICAgIH1cbiAgICAgIH0pO1xuXG4gICAgICB0aGlzLmRpc3BhdGNoRXZlbnQobmV3IEN1c3RvbUV2ZW50KCdpdGVtcy1jaGFuZ2VkJykpO1xuICAgIH1cblxuICAgIC8qKlxuICAgICAqIEZpcmVzIHdoZW4gdGhlIGl0ZW1zIGluIHRoZSBsaXN0IGNoYW5nZS5cbiAgICAgKlxuICAgICAqIEBtZW1iZXJvZiBDb250ZW50SXRlbXNcbiAgICAgKiBAZXZlbnQgaXRlbXMtY2hhbmdlZFxuICAgICAqL1xuICB9XG5cbiAgcmV0dXJuIENvbnRlbnRJdGVtcztcbn07XG5cblxuLy8gUmV0dXJuIHRoZSBnaXZlbiBlbGVtZW50cywgZmlsdGVyaW5nIG91dCBhdXhpbGlhcnkgZWxlbWVudHMgdGhhdCBhcmVuJ3Rcbi8vIHR5cGljYWxseSB2aXNpYmxlLiBJdGVtcyB3aGljaCBhcmUgbm90IGVsZW1lbnRzIGFyZSByZXR1cm5lZCBhcyBpcy5cbmZ1bmN0aW9uIGZpbHRlckF1eGlsaWFyeUVsZW1lbnRzKGl0ZW1zKSB7XG4gIGNvbnN0IGF1eGlsaWFyeVRhZ3MgPSBbXG4gICAgJ2xpbmsnLFxuICAgICdzY3JpcHQnLFxuICAgICdzdHlsZScsXG4gICAgJ3RlbXBsYXRlJ1xuICBdO1xuICByZXR1cm4gW10uZmlsdGVyLmNhbGwoaXRlbXMsIGZ1bmN0aW9uKGl0ZW0pIHtcbiAgICByZXR1cm4gIWl0ZW0ubG9jYWxOYW1lIHx8IGF1eGlsaWFyeVRhZ3MuaW5kZXhPZihpdGVtLmxvY2FsTmFtZSkgPCAwO1xuICB9KTtcbn1cbiIsImltcG9ydCBzeW1ib2xzIGZyb20gJy4vc3ltYm9scyc7XG5cblxuLyogRXhwb3J0ZWQgZnVuY3Rpb24gZXh0ZW5kcyBhIGJhc2UgY2xhc3Mgd2l0aCBEaXJlY3Rpb25TZWxlY3Rpb24uICovXG5leHBvcnQgZGVmYXVsdCAoYmFzZSkgPT4ge1xuXG4gIC8qKlxuICAgKiBNaXhpbiB3aGljaCBtYXBzIGRpcmVjdGlvbiBzZW1hbnRpY3MgKGdvTGVmdCwgZ29SaWdodCwgZXRjLikgdG8gc2VsZWN0aW9uXG4gICAqIHNlbWFudGljcyAoc2VsZWN0UHJldmlvdXMsIHNlbGVjdE5leHQsIGV0Yy4pLlxuICAgKlxuICAgKiBUaGlzIG1peGluIGNhbiBiZSB1c2VkIGluIGNvbmp1bmN0aW9uIHdpdGhcbiAgICogW0tleWJvYXJkRGlyZWN0aW9uTWl4aW5dKEtleWJvYXJkRGlyZWN0aW9uTWl4aW4ubWQpICh3aGljaCBtYXBzIGtleWJvYXJkXG4gICAqIGV2ZW50cyB0byBkaXJlY3Rpb25zKSBhbmQgYSBtaXhpbiB0aGF0IGhhbmRsZXMgc2VsZWN0aW9uIGxpa2VcbiAgICogW1NpbmdsZVNlbGVjdGlvbk1peGluXShTaW5nbGVTZWxlY3Rpb25NaXhpbi5tZCkuXG4gICAqL1xuICBjbGFzcyBEaXJlY3Rpb25TZWxlY3Rpb24gZXh0ZW5kcyBiYXNlIHtcblxuICAgIFtzeW1ib2xzLmdvRG93bl0oKSB7XG4gICAgICBpZiAoc3VwZXJbc3ltYm9scy5nb0Rvd25dKSB7IHN1cGVyW3N5bWJvbHMuZ29Eb3duXSgpOyB9XG4gICAgICByZXR1cm4gdGhpcy5zZWxlY3ROZXh0KCk7XG4gICAgfVxuXG4gICAgW3N5bWJvbHMuZ29FbmRdKCkge1xuICAgICAgaWYgKHN1cGVyW3N5bWJvbHMuZ29FbmRdKSB7IHN1cGVyW3N5bWJvbHMuZ29FbmRdKCk7IH1cbiAgICAgIHJldHVybiB0aGlzLnNlbGVjdExhc3QoKTtcbiAgICB9XG5cbiAgICBbc3ltYm9scy5nb0xlZnRdKCkge1xuICAgICAgaWYgKHN1cGVyW3N5bWJvbHMuZ29MZWZ0XSkgeyBzdXBlcltzeW1ib2xzLmdvTGVmdF0oKTsgfVxuICAgICAgcmV0dXJuIHRoaXMuc2VsZWN0UHJldmlvdXMoKTtcbiAgICB9XG5cbiAgICBbc3ltYm9scy5nb1JpZ2h0XSgpIHtcbiAgICAgIGlmIChzdXBlcltzeW1ib2xzLmdvUmlnaHRdKSB7IHN1cGVyW3N5bWJvbHMuZ29SaWdodF0oKTsgfVxuICAgICAgcmV0dXJuIHRoaXMuc2VsZWN0TmV4dCgpO1xuICAgIH1cblxuICAgIFtzeW1ib2xzLmdvU3RhcnRdKCkge1xuICAgICAgaWYgKHN1cGVyW3N5bWJvbHMuZ29TdGFydF0pIHsgc3VwZXJbc3ltYm9scy5nb1N0YXJ0XSgpOyB9XG4gICAgICByZXR1cm4gdGhpcy5zZWxlY3RGaXJzdCgpO1xuICAgIH1cblxuICAgIFtzeW1ib2xzLmdvVXBdKCkge1xuICAgICAgaWYgKHN1cGVyW3N5bWJvbHMuZ29VcF0pIHsgc3VwZXJbc3ltYm9scy5nb1VwXSgpOyB9XG4gICAgICByZXR1cm4gdGhpcy5zZWxlY3RQcmV2aW91cygpO1xuICAgIH1cblxuICAgIC8vIERlZmF1bHQgaW1wbGVtZW50YXRpb24uIFRoaXMgd2lsbCB0eXBpY2FsbHkgYmUgaGFuZGxlZCBieSBvdGhlciBtaXhpbnMuXG4gICAgZ2V0IHNlbGVjdGVkRnJhY3Rpb24oKSB7XG4gICAgICByZXR1cm4gc3VwZXIuc2VsZWN0ZWRGcmFjdGlvbjtcbiAgICB9XG4gICAgc2V0IHNlbGVjdGVkRnJhY3Rpb24odmFsdWUpIHtcbiAgICAgIGlmICgnc2VsZWN0ZWRGcmFjdGlvbicgaW4gYmFzZS5wcm90b3R5cGUpIHsgc3VwZXIuc2VsZWN0ZWRGcmFjdGlvbiA9IHZhbHVlOyB9XG4gICAgfVxuXG4gICAgLy8gRGVmYXVsdCBpbXBsZW1lbnRhdGlvbi4gVGhpcyB3aWxsIHR5cGljYWxseSBiZSBoYW5kbGVkIGJ5IG90aGVyIG1peGlucy5cbiAgICBzZWxlY3RGaXJzdCgpIHtcbiAgICAgIGlmIChzdXBlci5zZWxlY3RGaXJzdCkgeyByZXR1cm4gc3VwZXIuc2VsZWN0Rmlyc3QoKTsgfVxuICAgIH1cblxuICAgIC8vIERlZmF1bHQgaW1wbGVtZW50YXRpb24uIFRoaXMgd2lsbCB0eXBpY2FsbHkgYmUgaGFuZGxlZCBieSBvdGhlciBtaXhpbnMuXG4gICAgc2VsZWN0TGFzdCgpIHtcbiAgICAgIGlmIChzdXBlci5zZWxlY3RMYXN0KSB7IHJldHVybiBzdXBlci5zZWxlY3RMYXN0KCk7IH1cbiAgICB9XG5cbiAgICAvLyBEZWZhdWx0IGltcGxlbWVudGF0aW9uLiBUaGlzIHdpbGwgdHlwaWNhbGx5IGJlIGhhbmRsZWQgYnkgb3RoZXIgbWl4aW5zLlxuICAgIHNlbGVjdE5leHQoKSB7XG4gICAgICBpZiAoc3VwZXIuc2VsZWN0TmV4dCkgeyByZXR1cm4gc3VwZXIuc2VsZWN0TmV4dCgpOyB9XG4gICAgfVxuXG4gICAgLy8gRGVmYXVsdCBpbXBsZW1lbnRhdGlvbi4gVGhpcyB3aWxsIHR5cGljYWxseSBiZSBoYW5kbGVkIGJ5IG90aGVyIG1peGlucy5cbiAgICBzZWxlY3RQcmV2aW91cygpIHtcbiAgICAgIGlmIChzdXBlci5zZWxlY3RQcmV2aW91cykgeyByZXR1cm4gc3VwZXIuc2VsZWN0UHJldmlvdXMoKTsgfVxuICAgIH1cblxuICAgIC8vIE1hcCBkcmFnIHRyYXZlbCBmcmFjdGlvbiB0byBzZWxlY3Rpb24gZnJhY3Rpb24uXG4gICAgZ2V0IHRyYXZlbEZyYWN0aW9uKCkge1xuICAgICAgcmV0dXJuIHN1cGVyLnRyYXZlbEZyYWN0aW9uO1xuICAgIH1cbiAgICBzZXQgdHJhdmVsRnJhY3Rpb24odmFsdWUpIHtcbiAgICAgIGlmICgndHJhdmVsRnJhY3Rpb24nIGluIGJhc2UucHJvdG90eXBlKSB7IHN1cGVyLnRyYXZlbEZyYWN0aW9uID0gdmFsdWU7IH1cbiAgICAgIHRoaXMuc2VsZWN0ZWRGcmFjdGlvbiA9IHZhbHVlO1xuICAgIH1cblxuICB9XG5cbiAgcmV0dXJuIERpcmVjdGlvblNlbGVjdGlvbjtcbn07XG4iLCJpbXBvcnQgbWljcm90YXNrIGZyb20gJy4vbWljcm90YXNrJztcblxuXG4vKiBFeHBvcnRlZCBmdW5jdGlvbiBleHRlbmRzIGEgYmFzZSBjbGFzcyB3aXRoIERpc3RyaWJ1dGVkQ2hpbGRyZW5Db250ZW50LiAqL1xuZXhwb3J0IGRlZmF1bHQgKGJhc2UpID0+IHtcblxuICAvKipcbiAgICogTWl4aW4gd2hpY2ggZGVmaW5lcyBhIGNvbXBvbmVudCdzIGNvbnRlbnQgYXMgaXRzIGNoaWxkcmVuLCBleHBhbmRpbmcgYW55XG4gICAqIG5vZGVzIGRpc3RyaWJ1dGVkIHRvIHRoZSBjb21wb25lbnQncyBzbG90cy5cbiAgICpcbiAgICogVGhpcyBhbHNvIHByb3ZpZGVzIG5vdGlmaWNhdGlvbiBvZiBjaGFuZ2VzIHRvIGEgY29tcG9uZW50J3MgY29udGVudC4gSXRcbiAgICogd2lsbCBpbnZva2UgYSBgY29udGVudENoYW5nZWRgIG1ldGhvZCB3aGVuIHRoZSBjb21wb25lbnQgaXMgZmlyc3RcbiAgICogaW5zdGFudGlhdGVkLCBhbmQgd2hlbmV2ZXIgaXRzIGRpc3RyaWJ1dGVkIGNoaWxkcmVuIGNoYW5nZS4gVGhpcyBpcyBhblxuICAgKiBlYXN5IHdheSB0byBzYXRpc2Z5IHRoZSBHb2xkIFN0YW5kYXJkIGNoZWNrbGlzdCBpdGVtIGZvciBtb25pdG9yaW5nXG4gICAqIFtDb250ZW50IENoYW5nZXNdKGh0dHBzOi8vZ2l0aHViLmNvbS93ZWJjb21wb25lbnRzL2dvbGQtc3RhbmRhcmQvd2lraS9Db250ZW50LUNoYW5nZXMpLlxuICAgKlxuICAgKiBFeGFtcGxlOlxuICAgKlxuICAgKiBgYGBcbiAgICogbGV0IGJhc2UgPSBEaXN0cmlidXRlZENoaWxkcmVuQ29udGVudE1peGluKERpc3RyaWJ1dGVkQ2hpbGRyZW5NaXhpbihIVE1MRWxlbWVudCkpO1xuICAgKiBjbGFzcyBDb3VudGluZ0VsZW1lbnQgZXh0ZW5kcyBiYXNlIHtcbiAgICpcbiAgICogICBjb25zdHJ1Y3RvcigpIHtcbiAgICogICAgIHN1cGVyKCk7XG4gICAqICAgICBsZXQgcm9vdCA9IHRoaXMuYXR0YWNoU2hhZG93KHsgbW9kZTogJ29wZW4nIH0pO1xuICAgKiAgICAgcm9vdC5pbm5lckhUTUwgPSBgPHNsb3Q+PC9zbG90PmA7XG4gICAqICAgfVxuICAgKlxuICAgKiAgIGNvbnRlbnRDaGFuZ2VkKCkge1xuICAgKiAgICAgLy8gQ291bnQgdGhlIGNvbXBvbmVudCdzIGNoaWxkcmVuLCBib3RoIGluaXRpYWxseSBhbmQgd2hlbiBjaGFuZ2VkLlxuICAgKiAgICAgdGhpcy5jb3VudCA9IHRoaXMuZGlzdHJpYnV0ZWRDaGlsZHJlbi5sZW5ndGg7XG4gICAqICAgfVxuICAgKlxuICAgKiB9XG4gICAqIGBgYFxuICAgKlxuICAgKiBOb3RlIHRoYXQgY29udGVudCBjaGFuZ2UgZGV0ZWN0aW9uIGRlcGVuZHMgdXBvbiB0aGUgZWxlbWVudCBoYXZpbmcgYXQgbGVhc3RcbiAgICogb25lIGBzbG90YCBlbGVtZW50IGluIGl0cyBzaGFkb3cgc3VidHJlZS5cbiAgICpcbiAgICogVGhpcyBtaXhpbiBpcyBpbnRlbmRlZCBmb3IgdXNlIHdpdGggdGhlXG4gICAqIFtEaXN0cmlidXRlZENoaWxkcmVuTWl4aW5dKERpc3RyaWJ1dGVkQ2hpbGRyZW5NaXhpbi5tZCkuIFNlZSB0aGF0IG1peGluIGZvclxuICAgKiBhIGRpc2N1c3Npb24gb2YgaG93IHRoYXQgd29ya3MuIFRoaXMgRGlzdHJpYnV0ZWRDaGlsZHJlbkNvbnRlbnRNaXhpblxuICAgKiBwcm92aWRlcyBhbiBlYXN5IHdheSBvZiBkZWZpbmluZyB0aGUgXCJjb250ZW50XCIgb2YgYSBjb21wb25lbnQgYXMgdGhlXG4gICAqIGNvbXBvbmVudCdzIGRpc3RyaWJ1dGVkIGNoaWxkcmVuLiBUaGF0IGluIHR1cm4gbGV0cyBtaXhpbnMgbGlrZVxuICAgKiBbQ29udGVudEl0ZW1zTWl4aW5dKENvbnRlbnRJdGVtc01peGluLm1kKSBtYW5pcHVsYXRlIHRoZSBjaGlsZHJlbiBhcyBsaXN0XG4gICAqIGl0ZW1zLlxuICAgKi9cbiAgY2xhc3MgRGlzdHJpYnV0ZWRDaGlsZHJlbkNvbnRlbnQgZXh0ZW5kcyBiYXNlIHtcblxuICAgIGNvbnN0cnVjdG9yKCkge1xuICAgICAgc3VwZXIoKTtcblxuICAgICAgaWYgKHRoaXMuc2hhZG93Um9vdCkge1xuICAgICAgICAvLyBMaXN0ZW4gdG8gY2hhbmdlcyBvbiBhbGwgc2xvdHMuXG4gICAgICAgIGNvbnN0IHNsb3RzID0gdGhpcy5zaGFkb3dSb290LnF1ZXJ5U2VsZWN0b3JBbGwoJ3Nsb3QnKTtcbiAgICAgICAgc2xvdHMuZm9yRWFjaChzbG90ID0+IHNsb3QuYWRkRXZlbnRMaXN0ZW5lcignc2xvdGNoYW5nZScsIGV2ZW50ID0+IHtcbiAgICAgICAgICB0aGlzLmNvbnRlbnRDaGFuZ2VkKCk7XG4gICAgICAgIH0pKTtcbiAgICAgIH1cblxuICAgICAgLy8gTWFrZSBhbiBpbml0aWFsIGNhbGwgdG8gY29udGVudENoYW5nZWQoKSBzbyB0aGF0IHRoZSBjb21wb25lbnQgY2FuIGRvXG4gICAgICAvLyBpbml0aWFsaXphdGlvbiB0aGF0IGl0IG5vcm1hbGx5IGRvZXMgd2hlbiBjb250ZW50IGNoYW5nZXMuXG4gICAgICAvL1xuICAgICAgLy8gVGhpcyB3aWxsIGludm9rZSBjb250ZW50Q2hhbmdlZCgpIGhhbmRsZXJzIGluIG90aGVyIG1peGlucy4gSW4gb3JkZXJcbiAgICAgIC8vIHRoYXQgdGhvc2UgbWl4aW5zIGhhdmUgYSBjaGFuY2UgdG8gY29tcGxldGUgdGhlaXIgb3duIGluaXRpYWxpemF0aW9uLFxuICAgICAgLy8gd2UgYWRkIHRoZSBjb250ZW50Q2hhbmdlZCgpIGNhbGwgdG8gdGhlIG1pY3JvdGFzayBxdWV1ZS5cbiAgICAgIG1pY3JvdGFzaygoKSA9PiB0aGlzLmNvbnRlbnRDaGFuZ2VkKCkpO1xuICAgIH1cblxuICAgIC8qKlxuICAgICAqIEludm9rZWQgd2hlbiB0aGUgY29udGVudHMgb2YgdGhlIGNvbXBvbmVudCAoaW5jbHVkaW5nIGRpc3RyaWJ1dGVkXG4gICAgICogY2hpbGRyZW4pIGhhdmUgY2hhbmdlZC5cbiAgICAgKlxuICAgICAqIFRoaXMgbWV0aG9kIGlzIGFsc28gaW52b2tlZCB3aGVuIGEgY29tcG9uZW50IGlzIGZpcnN0IGluc3RhbnRpYXRlZDsgdGhlXG4gICAgICogY29udGVudHMgaGF2ZSBlc3NlbnRpYWxseSBcImNoYW5nZWRcIiBmcm9tIGJlaW5nIG5vdGhpbmcuIFRoaXMgYWxsb3dzIHRoZVxuICAgICAqIGNvbXBvbmVudCB0byBwZXJmb3JtIGluaXRpYWwgcHJvY2Vzc2luZyBvZiBpdHMgY2hpbGRyZW4uXG4gICAgICovXG4gICAgY29udGVudENoYW5nZWQoKSB7XG4gICAgICBpZiAoc3VwZXIuY29udGVudENoYW5nZWQpIHsgc3VwZXIuY29udGVudENoYW5nZWQoKTsgfVxuICAgICAgY29uc3QgZXZlbnQgPSBuZXcgQ3VzdG9tRXZlbnQoJ2NvbnRlbnQtY2hhbmdlZCcpO1xuICAgICAgdGhpcy5kaXNwYXRjaEV2ZW50KGV2ZW50KTtcbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBUaGUgY29udGVudCBvZiB0aGlzIGNvbXBvbmVudCwgZGVmaW5lZCB0byBiZSB0aGUgZmxhdHRlbmVkIGFycmF5IG9mXG4gICAgICogY2hpbGRyZW4gZGlzdHJpYnV0ZWQgdG8gdGhlIGNvbXBvbmVudC5cbiAgICAgKlxuICAgICAqIEB0eXBlIHtIVE1MRWxlbWVudFtdfVxuICAgICAqL1xuICAgIGdldCBjb250ZW50KCkge1xuICAgICAgY29uc3QgZGlzdHJpYnV0ZWRDaGlsZHJlbiA9IHRoaXMuZGlzdHJpYnV0ZWRDaGlsZHJlbjtcbiAgICAgIGlmICh0eXBlb2YgZGlzdHJpYnV0ZWRDaGlsZHJlbiA9PT0gJ3VuZGVmaW5lZCcpIHtcbiAgICAgICAgY29uc29sZS53YXJuKGBEaXN0cmlidXRlZENoaWxkcmVuQ29udGVudE1peGluIGV4cGVjdHMgdGhlIGNvbXBvbmVudCB0byBkZWZpbmUgYSBcImRpc3RyaWJ1dGVkQ2hpbGRyZW5cIiBwcm9wZXJ0eS5gKTtcbiAgICAgIH1cbiAgICAgIHJldHVybiBkaXN0cmlidXRlZENoaWxkcmVuO1xuICAgIH1cbiAgICBzZXQgY29udGVudCh2YWx1ZSkge1xuICAgICAgaWYgKCdjb250ZW50JyBpbiBiYXNlLnByb3RvdHlwZSkgeyBzdXBlci5jb250ZW50ID0gdmFsdWU7IH1cbiAgICAgIC8vIFRPRE86IFNldCB0aGUgY2hpbGRyZW4gdG8gdGhlIGdpdmVuIHZhbHVlICh3aGljaCBzaG91bGQgYmUgYW4gYXJyYXkgb2ZcbiAgICAgIC8vIGVsZW1lbnRzKT9cbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBUaGlzIGV2ZW50IGlzIHJhaXNlZCB3aGVuIHRoZSBjb21wb25lbnQncyBjb250ZW50cyAoaW5jbHVkaW5nIGRpc3RyaWJ1dGVkXG4gICAgICogY2hpbGRyZW4pIGhhdmUgY2hhbmdlZC5cbiAgICAgKlxuICAgICAqIEBtZW1iZXJvZiBEaXN0cmlidXRlZENoaWxkcmVuQ29udGVudFxuICAgICAqIEBldmVudCBjb250ZW50LWNoYW5nZWRcbiAgICAgKi9cbiAgfVxuXG4gIHJldHVybiBEaXN0cmlidXRlZENoaWxkcmVuQ29udGVudDtcbn07XG4iLCIvKiBFeHBvcnRlZCBmdW5jdGlvbiBleHRlbmRzIGEgYmFzZSBjbGFzcyB3aXRoIERpc3RyaWJ1dGVkQ2hpbGRyZW4uICovXG5leHBvcnQgZGVmYXVsdCAoYmFzZSkgPT4ge1xuXG4gIC8qKlxuICAgKiBNaXhpbiB3aGljaCBkZWZpbmVzIGhlbHBlcnMgZm9yIGFjY2Vzc2luZyBhIGNvbXBvbmVudCdzIGRpc3RyaWJ1dGVkXG4gICAqIGNoaWxkcmVuIGFzIGEgZmxhdHRlbmVkIGFycmF5IG9yIHN0cmluZy5cbiAgICpcbiAgICogVGhlIHN0YW5kYXJkIERPTSBBUEkgcHJvdmlkZXMgc2V2ZXJhbCB3YXlzIG9mIGFjY2Vzc2luZyBjaGlsZCBjb250ZW50OlxuICAgKiBgY2hpbGRyZW5gLCBgY2hpbGROb2Rlc2AsIGFuZCBgdGV4dENvbnRlbnRgLiBOb25lIG9mIHRoZXNlIGZ1bmN0aW9ucyBhcmVcbiAgICogU2hhZG93IERPTSBhd2FyZS4gVGhpcyBtaXhpbiBkZWZpbmVzIHZhcmlhdGlvbnMgb2YgdGhvc2UgZnVuY3Rpb25zIHRoYXRcbiAgICogKmFyZSogU2hhZG93IERPTSBhd2FyZS5cbiAgICpcbiAgICogRXhhbXBsZTogeW91IGNyZWF0ZSBhIGNvbXBvbmVudCBgPGNvdW50LWNoaWxkcmVuPmAgdGhhdCBkaXNwbGF5cyBhIG51bWJlclxuICAgKiBlcXVhbCB0byB0aGUgbnVtYmVyIG9mIGNoaWxkcmVuIHBsYWNlZCBpbnNpZGUgdGhhdCBjb21wb25lbnQuIElmIHNvbWVvbmVcbiAgICogaW5zdGFudGlhdGVzIHlvdXIgY29tcG9uZW50IGxpa2U6XG4gICAqXG4gICAqICAgICA8Y291bnQtY2hpbGRyZW4+XG4gICAqICAgICAgIDxkaXY+PC9kaXY+XG4gICAqICAgICAgIDxkaXY+PC9kaXY+XG4gICAqICAgICAgIDxkaXY+PC9kaXY+XG4gICAqICAgICA8L2NvdW50LWNoaWxkcmVuPlxuICAgKlxuICAgKiBUaGVuIHRoZSBjb21wb25lbnQgc2hvdWxkIHNob3cgXCIzXCIsIGJlY2F1c2UgdGhlcmUgYXJlIHRocmVlIGNoaWxkcmVuLiBUb1xuICAgKiBjYWxjdWxhdGUgdGhlIG51bWJlciBvZiBjaGlsZHJlbiwgdGhlIGNvbXBvbmVudCBjYW4ganVzdCBjYWxjdWxhdGVcbiAgICogYHRoaXMuY2hpbGRyZW4ubGVuZ3RoYC4gSG93ZXZlciwgc3VwcG9zZSBzb21lb25lIGluc3RhbnRpYXRlcyB5b3VyXG4gICAqIGNvbXBvbmVudCBpbnNpZGUgb25lIG9mIHRoZWlyIG93biBjb21wb25lbnRzLCBhbmQgcHV0cyBhIGA8c2xvdD5gIGVsZW1lbnRcbiAgICogaW5zaWRlIHlvdXIgY29tcG9uZW50OlxuICAgKlxuICAgKiAgICAgPGNvdW50LWNoaWxkcmVuPlxuICAgKiAgICAgICA8c2xvdD48L3Nsb3Q+XG4gICAqICAgICA8L2NvdW50LWNoaWxkcmVuPlxuICAgKlxuICAgKiBJZiB5b3VyIGNvbXBvbmVudCBvbmx5IGxvb2tzIGF0IGB0aGlzLmNoaWxkcmVuYCwgaXQgd2lsbCBhbHdheXMgc2VlIGV4YWN0bHlcbiAgICogb25lIGNoaWxkIOKAlMKgdGhlIGA8c2xvdD5gIGVsZW1lbnQuIEJ1dCB0aGUgdXNlciBsb29raW5nIGF0IHRoZSBwYWdlIHdpbGxcbiAgICogKnNlZSogYW55IG5vZGVzIGRpc3RyaWJ1dGVkIHRvIHRoYXQgc2xvdC4gVG8gbWF0Y2ggd2hhdCB0aGUgdXNlciBzZWVzLCB5b3VyXG4gICAqIGNvbXBvbmVudCBzaG91bGQgZXhwYW5kIGFueSBgPHNsb3Q+YCBlbGVtZW50cyBpdCBjb250YWlucy5cbiAgICpcbiAgICogVGhhdCBpcyB0aGUgcHJvYmxlbSB0aGlzIG1peGluIHNvbHZlcy4gQWZ0ZXIgYXBwbHlpbmcgdGhpcyBtaXhpbiwgeW91clxuICAgKiBjb21wb25lbnQgY29kZSBoYXMgYWNjZXNzIHRvIGB0aGlzLmRpc3RyaWJ1dGVkQ2hpbGRyZW5gLCB3aG9zZSBgbGVuZ3RoYFxuICAgKiB3aWxsIHJldHVybiB0aGUgdG90YWwgbnVtYmVyIG9mIGFsbCBjaGlsZHJlbiBkaXN0cmlidXRlZCB0byB5b3VyIGNvbXBvbmVudFxuICAgKiBpbiB0aGUgY29tcG9zZWQgdHJlZS5cbiAgICpcbiAgICogTm90ZTogVGhlIGxhdGVzdCBDdXN0b20gRWxlbWVudHMgQVBJIGRlc2lnbiBjYWxscyBmb3IgYSBuZXcgZnVuY3Rpb24sXG4gICAqIGBnZXRBc3NpZ25lZE5vZGVzYCB0aGF0IHRha2VzIGFuIG9wdGlvbmFsIGBkZWVwYCBwYXJhbWV0ZXIsIHRoYXQgd2lsbCBzb2x2ZVxuICAgKiB0aGlzIHByb2JsZW0gYXQgdGhlIEFQSSBsZXZlbC5cbiAgICovXG4gIGNsYXNzIERpc3RyaWJ1dGVkQ2hpbGRyZW4gZXh0ZW5kcyBiYXNlIHtcblxuICAgIC8qKlxuICAgICAqIEFuIGluLW9yZGVyIGNvbGxlY3Rpb24gb2YgZGlzdHJpYnV0ZWQgY2hpbGRyZW4sIGV4cGFuZGluZyBhbnkgc2xvdFxuICAgICAqIGVsZW1lbnRzLiBMaWtlIHRoZSBzdGFuZGFyZCBjaGlsZHJlbiBwcm9wZXJ0eSwgdGhpcyBza2lwcyB0ZXh0IG5vZGVzLlxuICAgICAqXG4gICAgICogQHR5cGUge0hUTUxFbGVtZW50W119XG4gICAgICovXG4gICAgZ2V0IGRpc3RyaWJ1dGVkQ2hpbGRyZW4oKSB7XG4gICAgICByZXR1cm4gZXhwYW5kQ29udGVudEVsZW1lbnRzKHRoaXMuY2hpbGRyZW4sIGZhbHNlKTtcbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBBbiBpbi1vcmRlciBjb2xsZWN0aW9uIG9mIGRpc3RyaWJ1dGVkIGNoaWxkIG5vZGVzLCBleHBhbmRpbmcgYW55IHNsb3RcbiAgICAgKiBlbGVtZW50cy4gTGlrZSB0aGUgc3RhbmRhcmQgY2hpbGROb2RlcyBwcm9wZXJ0eSwgdGhpcyBpbmNsdWRlcyB0ZXh0XG4gICAgICogbm9kZXMuXG4gICAgICpcbiAgICAgKiBAdHlwZSB7Tm9kZVtdfVxuICAgICAqL1xuICAgIGdldCBkaXN0cmlidXRlZENoaWxkTm9kZXMoKSB7XG4gICAgICByZXR1cm4gZXhwYW5kQ29udGVudEVsZW1lbnRzKHRoaXMuY2hpbGROb2RlcywgdHJ1ZSk7XG4gICAgfVxuXG4gICAgLyoqXG4gICAgICogVGhlIGNvbmNhdGVuYXRlZCB0ZXh0IGNvbnRlbnQgb2YgYWxsIGRpc3RyaWJ1dGVkIGNoaWxkIG5vZGVzLCBleHBhbmRpbmdcbiAgICAgKiBhbnkgc2xvdCBlbGVtZW50cy5cbiAgICAgKlxuICAgICAqIEB0eXBlIHtzdHJpbmd9XG4gICAgICovXG4gICAgZ2V0IGRpc3RyaWJ1dGVkVGV4dENvbnRlbnQoKSB7XG4gICAgICBjb25zdCBzdHJpbmdzID0gdGhpcy5kaXN0cmlidXRlZENoaWxkTm9kZXMubWFwKGZ1bmN0aW9uKGNoaWxkKSB7XG4gICAgICAgIHJldHVybiBjaGlsZC50ZXh0Q29udGVudDtcbiAgICAgIH0pO1xuICAgICAgcmV0dXJuIHN0cmluZ3Muam9pbignJyk7XG4gICAgfVxuXG4gIH1cblxuICByZXR1cm4gRGlzdHJpYnV0ZWRDaGlsZHJlbjtcbn07XG5cblxuLypcbiAqIEdpdmVuIGEgYXJyYXkgb2Ygbm9kZXMsIHJldHVybiBhIG5ldyBhcnJheSB3aXRoIGFueSBjb250ZW50IGVsZW1lbnRzIGV4cGFuZGVkXG4gKiB0byB0aGUgbm9kZXMgZGlzdHJpYnV0ZWQgdG8gdGhhdCBjb250ZW50IGVsZW1lbnQuIFRoaXMgcnVsZSBpcyBhcHBsaWVkXG4gKiByZWN1cnNpdmVseS5cbiAqXG4gKiBJZiBpbmNsdWRlVGV4dE5vZGVzIGlzIHRydWUsIHRleHQgbm9kZXMgd2lsbCBiZSBpbmNsdWRlZCwgYXMgaW4gdGhlXG4gKiBzdGFuZGFyZCBjaGlsZE5vZGVzIHByb3BlcnR5OyBieSBkZWZhdWx0LCB0aGlzIHNraXBzIHRleHQgbm9kZXMsIGxpa2UgdGhlXG4gKiBzdGFuZGFyZCBjaGlsZHJlbiBwcm9wZXJ0eS5cbiAqL1xuZnVuY3Rpb24gZXhwYW5kQ29udGVudEVsZW1lbnRzKG5vZGVzLCBpbmNsdWRlVGV4dE5vZGVzKSB7XG4gIGNvbnN0IGV4cGFuZGVkID0gQXJyYXkucHJvdG90eXBlLm1hcC5jYWxsKG5vZGVzLCBub2RlID0+IHtcbiAgICAvLyBXZSB3YW50IHRvIHNlZSBpZiB0aGUgbm9kZSBpcyBhbiBpbnN0YW5jZW9mIEhUTUxTbG90RUxlbWVudCwgYnV0XG4gICAgLy8gdGhhdCBjbGFzcyB3b24ndCBleGlzdCBpZiB0aGUgYnJvd3NlciB0aGF0IGRvZXNuJ3Qgc3VwcG9ydCBuYXRpdmVcbiAgICAvLyBTaGFkb3cgRE9NIGFuZCBpZiB0aGUgU2hhZG93IERPTSBwb2x5ZmlsbCBoYXNuJ3QgYmVlbiBsb2FkZWQuIEluc3RlYWQsXG4gICAgLy8gd2UgZG8gYSBzaW1wbGlzdGljIGNoZWNrIHRvIHNlZSBpZiB0aGUgdGFnIG5hbWUgaXMgXCJzbG90XCIuXG4gICAgY29uc3QgaXNTbG90ID0gdHlwZW9mIEhUTUxTbG90RWxlbWVudCAhPT0gJ3VuZGVmaW5lZCcgP1xuICAgICAgbm9kZSBpbnN0YW5jZW9mIEhUTUxTbG90RWxlbWVudCA6XG4gICAgICBub2RlLmxvY2FsTmFtZSA9PT0gJ3Nsb3QnO1xuICAgIGlmIChpc1Nsb3QpIHtcbiAgICAgIC8vIFVzZSB0aGUgbm9kZXMgYXNzaWduZWQgdG8gdGhpcyBub2RlIGluc3RlYWQuXG4gICAgICBjb25zdCBhc3NpZ25lZE5vZGVzID0gbm9kZS5hc3NpZ25lZE5vZGVzKHsgZmxhdHRlbjogdHJ1ZSB9KTtcbiAgICAgIHJldHVybiBhc3NpZ25lZE5vZGVzID9cbiAgICAgICAgZXhwYW5kQ29udGVudEVsZW1lbnRzKGFzc2lnbmVkTm9kZXMsIGluY2x1ZGVUZXh0Tm9kZXMpIDpcbiAgICAgICAgW107XG4gICAgfSBlbHNlIGlmIChub2RlIGluc3RhbmNlb2YgSFRNTEVsZW1lbnQpIHtcbiAgICAgIC8vIFBsYWluIGVsZW1lbnQ7IHVzZSBhcyBpcy5cbiAgICAgIHJldHVybiBbbm9kZV07XG4gICAgfSBlbHNlIGlmIChub2RlIGluc3RhbmNlb2YgVGV4dCAmJiBpbmNsdWRlVGV4dE5vZGVzKSB7XG4gICAgICAvLyBUZXh0IG5vZGUuXG4gICAgICByZXR1cm4gW25vZGVdO1xuICAgIH0gZWxzZSB7XG4gICAgICAvLyBDb21tZW50LCBwcm9jZXNzaW5nIGluc3RydWN0aW9uLCBldGMuOyBza2lwLlxuICAgICAgcmV0dXJuIFtdO1xuICAgIH1cbiAgfSk7XG4gIGNvbnN0IGZsYXR0ZW5lZCA9IFtdLmNvbmNhdCguLi5leHBhbmRlZCk7XG4gIHJldHVybiBmbGF0dGVuZWQ7XG59XG4iLCJpbXBvcnQgY3JlYXRlU3ltYm9sIGZyb20gJy4vY3JlYXRlU3ltYm9sJztcblxuXG4vLyBTeW1ib2xzIGZvciBwcml2YXRlIGRhdGEgbWVtYmVycyBvbiBhbiBlbGVtZW50LlxuY29uc3Qgc2VsZWN0ZWRGcmFjdGlvblN5bWJvbCA9IGNyZWF0ZVN5bWJvbCgnc2VsZWN0ZWRGcmFjdGlvbicpO1xuXG5cbi8qIEV4cG9ydGVkIGZ1bmN0aW9uIGV4dGVuZHMgYSBiYXNlIGNsYXNzIHdpdGggRnJhY3Rpb25hbFNlbGVjdGlvbi4gKi9cbmV4cG9ydCBkZWZhdWx0IGZ1bmN0aW9uIG1peGluKGJhc2UpIHtcblxuICAvKipcbiAgICogQWRkcyBzdXBwb3J0IGZvciBmcmFjdGlvbmFsIHNlbGVjdGlvbjogdHJlYXRpbmcgYSBzZWxlY3Rpb24gYXMgYSByZWFsXG4gICAqIG51bWJlciB0aGF0IGNvbWJpbmVzIGFuIGludGVnZXIgcG9ydGlvbiAoYW4gaW5kZXggaW50byBhIGxpc3QpLCBhbmQgYVxuICAgKiBmcmFjdGlvbiAoaW5kaWNhdGluZyBob3cgZmFyIG9mIHRoZSB3YXkgd2UgYXJlIHRvIHRoZSBuZXh0IG9yIHByZXZpb3VzXG4gICAqIGl0ZW0pLlxuICAgKlxuICAgKiBUaGlzIGlzIHVzZWZ1bCBpbiBjb21wb25lbnRzIHRoYXQgc3VwcG9ydCBpbmNyZW1lbnRhbCBvcGVyYXRpb25zIGR1cmluZ1xuICAgKiBkcmFnZ2luZyBhbmQgc3dpcGluZy4gRXhhbXBsZTogYSBjYXJvdXNlbCBjb21wb25lbnQgaGFzIHNldmVyYWwgaXRlbXMsIGFuZCB0aGVcbiAgICogY3VycmVudGx5IHNlbGVjdGVkIGl0ZW0gaXMgaXRlbSAzLiBUaGUgdXNlciBiZWdpbnMgc3dpcGluZyB0byB0aGUgbGVmdCxcbiAgICogbW92aW5nIHRvd2FyZHMgc2VsZWN0aW5nIGl0ZW0gNC4gSGFsZndheSB0aHJvdWdoIHRoaXMgb3BlcmF0aW9uLCB0aGVcbiAgICogZnJhY3Rpb25hbCBzZWxlY3Rpb24gdmFsdWUgaXMgMy41LlxuICAgKlxuICAgKiBUaGlzIHZhbHVlIHBlcm1pdHMgY29tbXVuaWNhdGlvbiBiZXR3ZWVuIG1peGlucyBsaWtlXG4gICAqIFtTd2lwZURpcmVjdGlvbk1peGluXSguL1N3aXBlRGlyZWN0aW9uTWl4aW4ubWQpIGFuZFxuICAgKiBbVHJhY2twYWREaXJlY3Rpb25NaXhpbl0oLi9UcmFja3BhZERpcmVjdGlvbk1peGluLm1kKSwgd2hpY2ggZ2VuZXJhdGVcbiAgICogZnJhY3Rpb25hbCBzZWxlY3Rpb24gdmFsdWVzLCBhbmQgbWl4aW5zIGxpa2VcbiAgICogW1NlbGVjdGlvbkFuaW1hdGlvbk1peGluXSguL1NlbGVjdGlvbkFuaW1hdGlvbk1peGluLm1kKSwgd2hpY2ggY2FuIHJlbmRlclxuICAgKiBzZWxlY3Rpb24gYXQgYSBmcmFjdGlvbmFsIHZhbHVlLlxuICAgKi9cbiAgY2xhc3MgRnJhY3Rpb25hbFNlbGVjdGlvbiBleHRlbmRzIGJhc2Uge1xuXG4gICAgY29ubmVjdGVkQ2FsbGJhY2soKSB7XG4gICAgICBpZiAoc3VwZXIuY29ubmVjdGVkQ2FsbGJhY2spIHsgc3VwZXIuY29ubmVjdGVkQ2FsbGJhY2soKTsgfVxuICAgICAgdGhpcy5zZWxlY3RlZEZyYWN0aW9uID0gMDtcbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBBIGZyYWN0aW9uYWwgdmFsdWUgaW5kaWNhdGluZyBob3cgZmFyIHRoZSB1c2VyIGhhcyBjdXJyZW50bHkgYWR2YW5jZWQgdG9cbiAgICAgKiB0aGUgbmV4dC9wcmV2aW91cyBpdGVtLiBFLmcuLCBhIGBzZWxlY3RlZEZyYWN0aW9uYCBvZiAzLjUgaW5kaWNhdGVzIHRoZVxuICAgICAqIHVzZXIgaXMgaGFsZndheSBiZXR3ZWVuIGl0ZW1zIDMgYW5kIDQuXG4gICAgICpcbiAgICAgKiBAdHlwZSB7bnVtYmVyfVxuICAgICAqL1xuICAgIGdldCBzZWxlY3RlZEZyYWN0aW9uKCkge1xuICAgICAgcmV0dXJuIHRoaXNbc2VsZWN0ZWRGcmFjdGlvblN5bWJvbF07XG4gICAgfVxuICAgIHNldCBzZWxlY3RlZEZyYWN0aW9uKHZhbHVlKSB7XG4gICAgICB0aGlzW3NlbGVjdGVkRnJhY3Rpb25TeW1ib2xdID0gdmFsdWU7XG4gICAgICBpZiAoJ3NlbGVjdGVkRnJhY3Rpb24nIGluIGJhc2UucHJvdG90eXBlKSB7IHN1cGVyLnNlbGVjdGVkRnJhY3Rpb24gPSB2YWx1ZTsgfVxuICAgICAgY29uc3QgZXZlbnQgPSBuZXcgQ3VzdG9tRXZlbnQoJ3NlbGVjdGVkLWZyYWN0aW9uLWNoYW5nZWQnKTtcbiAgICAgIHRoaXMuZGlzcGF0Y2hFdmVudChldmVudCk7XG4gICAgfVxuXG4gIH1cblxuICByZXR1cm4gRnJhY3Rpb25hbFNlbGVjdGlvbjtcbn1cblxuXG5taXhpbi5oZWxwZXJzID0ge1xuXG4gIC8qXG4gICAqIERhbXBlbiBhIHNlbGVjdGlvbiB0aGF0IGdvZXMgcGFzdCB0aGUgYmVnaW5uaW5nIG9yIGVuZCBvZiBhIGxpc3QuIFRoaXMgaXNcbiAgICogZ2VuZXJhbGx5IHVzZWQgdG8gcHJvZHVjZSBhIHZpc3VhbCBlZmZlY3Qgb2YgdGVuc2lvbiBhcyB0aGUgdXNlciB0cmllcyB0b1xuICAgKiBnbyBmdXJ0aGVyIGluIGEgZGlyZWN0aW9uIHRoYXQgaGFzIG5vIG1vcmUgaXRlbXMuXG4gICAqXG4gICAqIEV4YW1wbGU6IHN1cHBvc2UgYGl0ZW1Db3VudGAgaXMgNSwgaW5kaWNhdGluZyBhIGxpc3Qgb2YgNSBpdGVtcy4gVGhlIGluZGV4IG9mXG4gICAqIHRoZSBsYXN0IGl0ZW0gaXMgNC4gSWYgdGhlIGBzZWxlY3Rpb25gIHBhcmFtZXRlciBpcyA0LjUsIHRoZSB1c2VyIGlzIHRyeWluZ1xuICAgKiB0byBnbyBwYXN0IHRoaXMgbGFzdCBpdGVtLiBXaGVuIGEgZGFtcGluZyBmdW5jdGlvbiBpcyBhcHBsaWVkLCB0aGUgcmVzdWx0aW5nXG4gICAqIHZhbHVlIHdpbGwgYmUgbGVzcyB0aGFuIDQuNSAodGhlIGFjdHVhbCB2YWx1ZSB3aWxsIGJlIDQuMjUpLiBXaGVuIHRoaXNcbiAgICogc2VsZWN0aW9uIHN0YXRlIGlzIHJlbmRlcmVkLCB0aGUgdXNlciB3aWxsIHNlZSB0aGF0LCBlYWNoIHVuaXQgZGlzdGFuY2UgdGhlXG4gICAqIGRyYWcgdHJhdmVscyBoYXMgbGVzcyBhbmQgbGVzcyB2aXNpYmxlIGVmZmVjdC4gVGhpcyBpcyBwZXJjZWl2ZWQgYXMgdGVuc2lvbi5cbiAgICpcbiAgICogQHBhcmFtIHtudW1iZXJ9IHNlbGVjdGlvbiAtIEEgcmVhbCBudW1iZXIgaW5kaWNhdGluZyBhIHNlbGVjdGlvbiBwb3NpdGlvblxuICAgKiBAcGFyYW0ge251bWJlcn0gaXRlbUNvdW50IC0gQW4gaW50ZWdlciBmb3IgdGhlIG51bWJlciBvZiBpdGVtcyBpbiB0aGUgbGlzdFxuICAgKiBAcmV0dXJucyB7bnVtYmVyfSBBIHJlYWwgbnVtYmVyIHJlcHJlc2VudGluZyB0aGUgZGFtcGVkIHNlbGVjdGlvbiB2YWx1ZS5cbiAgICovXG4gIGRhbXBlZFNlbGVjdGlvbihzZWxlY3Rpb24sIGl0ZW1Db3VudCkge1xuICAgIGNvbnN0IGJvdW5kID0gaXRlbUNvdW50IC0gMTtcbiAgICBsZXQgZGFtcGVkO1xuICAgIGlmIChzZWxlY3Rpb24gPCAwKSB7XG4gICAgICAvLyBUcnlpbmcgdG8gZ28gcGFzdCBiZWdpbm5pbmcgb2YgbGlzdC4gQXBwbHkgdGVuc2lvbiBmcm9tIHRoZSBsZWZ0IGVkZ2UuXG4gICAgICBkYW1wZWQgPSAtbWl4aW4uaGVscGVycy5kYW1waW5nKC1zZWxlY3Rpb24pO1xuICAgIH0gZWxzZSBpZiAoc2VsZWN0aW9uID49IGJvdW5kKSB7XG4gICAgICAvLyBUcnlpbmcgdG8gZ28gcGFzdCBlbmQgb2YgbGlzdC4gQXBwbHkgdGVuc2lvbiBmcm9tIHRoZSByaWdodCBlZGdlLlxuICAgICAgZGFtcGVkID0gYm91bmQgKyBtaXhpbi5oZWxwZXJzLmRhbXBpbmcoc2VsZWN0aW9uIC0gYm91bmQpO1xuICAgIH0gZWxzZSB7XG4gICAgICAvLyBObyBkYW1waW5nIHJlcXVpcmVkLlxuICAgICAgZGFtcGVkID0gc2VsZWN0aW9uO1xuICAgIH1cbiAgICByZXR1cm4gZGFtcGVkO1xuICB9LFxuXG4gIC8qXG4gICAqIENhbGN1bGF0ZSBkYW1waW5nIGFzIGEgZnVuY3Rpb24gb2YgdGhlIGRpc3RhbmNlIHBhc3QgdGhlIG1pbmltdW0vbWF4aW11bVxuICAgKiB2YWx1ZXMuXG4gICAqXG4gICAqIFdlIHdhbnQgdG8gYXN5bXB0b3RpY2FsbHkgYXBwcm9hY2ggYW4gYWJzb2x1dGUgbWluaW11bSBvZiAxIHVuaXRcbiAgICogYmVsb3cvYWJvdmUgdGhlIGFjdHVhbCBtaW5pbXVtL21heGltdW0uIFRoaXMgcmVxdWlyZXMgY2FsY3VsYXRpbmcgYVxuICAgKiBoeXBlcmJvbGljIGZ1bmN0aW9uLlxuICAgKlxuICAgKiBTZWUgaHR0cDovL3d3dy53b2xmcmFtYWxwaGEuY29tL2lucHV0Lz9pPXkrJTNEKy0xJTJGJTI4eCUyQjElMjkrJTJCKzFcbiAgICogZm9yIHRoZSBvbmUgd2UgdXNlLiBUaGUgb25seSBwb3J0aW9uIG9mIHRoYXQgZnVuY3Rpb24gd2UgY2FyZSBhYm91dCBpcyB3aGVuXG4gICAqIHggaXMgemVybyBvciBncmVhdGVyLiBBbiBpbXBvcnRhbnQgY29uc2lkZXJhdGlvbiBpcyB0aGF0IHRoZSBjdXJ2ZSBiZVxuICAgKiB0YW5nZW50IHRvIHRoZSBkaWFnb25hbCBsaW5lIHg9eSBhdCAoMCwgMCkuIFRoaXMgZW5zdXJlcyBzbW9vdGggY29udGludWl0eVxuICAgKiB3aXRoIHRoZSBub3JtYWwgZHJhZyBiZWhhdmlvciwgaW4gd2hpY2ggdGhlIHZpc2libGUgc2xpZGluZyBpcyBsaW5lYXIgd2l0aFxuICAgKiB0aGUgZGlzdGFuY2UgdGhlIHRvdWNocG9pbnQgaGFzIGJlZW4gZHJhZ2dlZC5cbiAgICovXG4gIGRhbXBpbmcoeCkge1xuICAgIGNvbnN0IHkgPSAoLTEgLyAoeCArIDEpKSArIDE7XG4gICAgcmV0dXJuIHk7XG4gIH0sXG5cbiAgLypcbiAgICogUmV0dXJuIHRoZSBjdXJyZW50IGZyYWN0aW9uYWwgc2VsZWN0aW9uIHZhbHVlIGZvciB0aGUgZ2l2ZW4gZWxlbWVudC5cbiAgICpcbiAgICogVGhpcyBzaW1wbHkgYWRkcyB0aGUgZWxlbWVudCdzIGBzZWxlY3RlZEluZGV4YCBhbmQgYHNlbGVjdGVkRnJhY3Rpb25gXG4gICAqIHByb3BlcnRpZXMuXG4gICAqXG4gICAqIEBwYXJhbSB7SFRNTEVsZW1lbnR9IGVsZW1lbnQgLSBBbiBlbGVtZW50IHRoYXQgc3VwcG9ydHMgc2VsZWN0aW9uXG4gICAqL1xuICBlbGVtZW50U2VsZWN0aW9uKGVsZW1lbnQpIHtcbiAgICBjb25zdCBzZWxlY3RlZEluZGV4ID0gZWxlbWVudC5zZWxlY3RlZEluZGV4O1xuICAgIGlmIChzZWxlY3RlZEluZGV4IDwgMCkge1xuICAgICAgLy8gTm8gc2VsZWN0aW9uXG4gICAgICByZXR1cm47XG4gICAgfVxuICAgIGNvbnN0IHNlbGVjdGVkRnJhY3Rpb24gPSBlbGVtZW50LnNlbGVjdGVkRnJhY3Rpb24gfHwgMDtcbiAgICByZXR1cm4gc2VsZWN0ZWRJbmRleCArIHNlbGVjdGVkRnJhY3Rpb247XG4gIH0sXG5cbiAgLypcbiAgICogQnJlYWtzIGEgZnJhY3Rpb25hbCBzZWxlY3Rpb24gaW50byBpdHMgaW50ZWdlciBhbmQgZnJhY3Rpb25hbCBwYXJ0cy5cbiAgICpcbiAgICogRXhhbXBsZTogaWYgcGFzc2VkIDMuNSwgdGhpcyByZXR1cm5zIHsgaW5kZXg6IDMsIGZyYWN0aW9uOiA1IH0uXG4gICAqXG4gICAqIEBwYXJhbSB7bnVtYmVyfSBzZWxlY3Rpb24g4oCTwqBBIHJlYWwgbnVtYmVyIHJlcHJlc2VudGluZyBhIHNlbGVjdGlvbiBwb2ludFxuICAgKiBAcmV0dXJucyB7b2JqZWN0fSAtIEFuIG9iamVjdCB3aXRoIGFuIGBpbmRleGAgcHJvcGVydHkgaG9sZGluZyB0aGVcbiAgICogc2VsZWN0aW9uJ3MgaW50ZWdlciBjb21wb25lbnQsIGFuZCBhIGBmcmFjdGlvbmAgcHJvcGVydHkgaG9sZGluZyB0aGVcbiAgICogc2VsZWN0aW9uJ3MgZnJhY3Rpb25hbCBjb21wb25lbnQuXG4gICAqL1xuICBzZWxlY3Rpb25QYXJ0cyhzZWxlY3Rpb24pIHtcbiAgICAvLyBTdHVwaWQgSUUgZG9lc24ndCBoYXZlIE1hdGgudHJ1bmMuXG4gICAgLy8gY29uc3QgaW5kZXggPSBNYXRoLnRydW5jKHNlbGVjdGlvbik7XG4gICAgY29uc3QgaW5kZXggPSBzZWxlY3Rpb24gPCAwID8gTWF0aC5jZWlsKHNlbGVjdGlvbikgOiBNYXRoLmZsb29yKHNlbGVjdGlvbik7XG4gICAgY29uc3QgZnJhY3Rpb24gPSBzZWxlY3Rpb24gLSBpbmRleDtcbiAgICByZXR1cm4geyBpbmRleCwgZnJhY3Rpb24gfTtcbiAgfSxcblxuICAvKlxuICAgKiBSZXR1cm5zIGEgZnJhY3Rpb25hbCBzZWxlY3Rpb24gcG9pbnQgYWZ0ZXIgYWNjb3VudGluZyBmb3Igd3JhcHBpbmcsIGVuc3VyaW5nXG4gICAqIHRoYXQgdGhlIGludGVnZXIgcG9ydGlvbiBvZiB0aGUgc2VsZWN0aW9uIHN0YXlzIGJldHdlZW4gMCBhbmQgYGl0ZW1Db3VudGAtMS5cbiAgICogVGhhdCBpcywgdGhlIGludGVnZXIgcG9ydGlvbiB3aWxsIGFsd2F5cyBiZSBhIHZhbGlkIGluZGV4IGludG8gdGhlIGxpc3QuXG4gICAqXG4gICAqIEV4YW1wbGUgb2Ygd3JhcHBpbmcgcGFzdCB0aGUgZW5kIG9mIHRoZSBsaXN0OiBpZiBgc2VsZWN0aW9uYCBpcyA1LjUgYW5kXG4gICAqIGBpdGVtQ291bnRgIGlzIDUsIHRoaXMgcmV0dXJucyAwLjUuIEV4YW1wbGUgb2Ygd3JhcHBpbmcgcGFzdCB0aGUgYmVnaW5uaW5nIG9mXG4gICAqIHRoZSBsaXN0OiBpZiBgc2VsZWN0aW9uYCBpcyAwLjUgYW5kIGBpdGVtQ291bnRgIGlzIDUsIHRoaXMgcmV0dXJucyA0LjUuXG4gICAqXG4gICAqIEBwYXJhbSB7bnVtYmVyfSBzZWxlY3Rpb24gLSBBIHJlYWwgbnVtYmVyIHJlcHJlc2VudGluZyBhIHNlbGVjdGlvbiBwb2ludFxuICAgKiBAcGFyYW0ge251bWJlcn0gaXRlbUNvdW50IC0gVGhlIG51bWJlciBvZiBpdGVtcyBpbiB0aGUgbGlzdFxuICAgKiBAcmV0dXJucyB7bnVtYmVyfSAtIFRoZSByZXN1bHQgb2Ygd3JhcHBpbmcgdGhlIHNlbGVjdGlvbiBwb2ludFxuICAgKi9cbiAgd3JhcHBlZFNlbGVjdGlvbihzZWxlY3Rpb24sIGl0ZW1Db3VudCkge1xuICAgIC8vIEhhbmRsZXMgcG9zc2liaWxpdHkgb2YgbmVnYXRpdmUgbW9kLlxuICAgIC8vIFNlZSBodHRwOi8vc3RhY2tvdmVyZmxvdy5jb20vYS8xODYxODI1MC83NjQ3MlxuICAgIHJldHVybiAoKHNlbGVjdGlvbiAlIGl0ZW1Db3VudCkgKyBpdGVtQ291bnQpICUgaXRlbUNvdW50O1xuICB9LFxuXG4gIC8qXG4gICAqIFJldHVybiB0aGUgcGFydHMgb2YgYSBzZWxlY3Rpb24sIGZpcnN0IHdyYXBwaW5nIGlmIG5lY2Vzc2FyeS5cbiAgICpcbiAgICogQHBhcmFtIHtudW1iZXJ9IHNlbGVjdGlvbiDigJMgQSByZWFsIG51bWJlciByZXByZXNlbnRpbmcgYSBzZWxlY3Rpb24gcG9pbnRcbiAgICogQHBhcmFtIHtudW1iZXJ9IGl0ZW1Db3VudCAtIFRoZSBudW1iZXIgb2YgaXRlbXMgaW4gdGhlIGxpc3RcbiAgICogQHBhcmFtIHtib29sZWFufSB3cmFwIOKAkyBUcnVlIGlmIHRoZSBzZWxlY3Rpb24gc2hvdWxkIHdyYXAgdG8gc3RheSB3aXRoaW4gdGhlXG4gICAqIGxpc3RcbiAgICogQHJldHVybnMge29iamVjdH0g4oCTIFRoZSBwYXJ0cyBvZiB0aGUgc2VsZWN0aW9uLCB1c2luZyB0aGUgc2FtZSBmb3JtYXQgYXNcbiAgICogYHNlbGVjdGlvblBhcnRzYC5cbiAgICovXG4gIHdyYXBwZWRTZWxlY3Rpb25QYXJ0cyhzZWxlY3Rpb24sIGl0ZW1Db3VudCwgd3JhcCkge1xuICAgIGlmICh3cmFwKSB7XG4gICAgICBzZWxlY3Rpb24gPSBtaXhpbi5oZWxwZXJzLndyYXBwZWRTZWxlY3Rpb24oc2VsZWN0aW9uLCBpdGVtQ291bnQpO1xuICAgIH1cbiAgICByZXR1cm4gbWl4aW4uaGVscGVycy5zZWxlY3Rpb25QYXJ0cyhzZWxlY3Rpb24pO1xuICB9XG5cbn07XG4iLCJpbXBvcnQgY3JlYXRlU3ltYm9sIGZyb20gJy4vY3JlYXRlU3ltYm9sJztcbmltcG9ydCBzYWZlQXR0cmlidXRlcyBmcm9tICcuL3NhZmVBdHRyaWJ1dGVzJztcbmltcG9ydCBzeW1ib2xzIGZyb20gJy4vc3ltYm9scyc7XG5cblxuLy8gU3ltYm9scyBmb3IgcHJpdmF0ZSBkYXRhIG1lbWJlcnMgb24gYW4gZWxlbWVudC5cbmNvbnN0IGdlbmVyaWNTeW1ib2wgPSBjcmVhdGVTeW1ib2woJ2dlbmVyaWMnKTtcblxuXG4vKiBFeHBvcnRlZCBmdW5jdGlvbiBleHRlbmRzIGEgYmFzZSBjbGFzcyB3aXRoIEdlbmVyaWMuICovXG5leHBvcnQgZGVmYXVsdCAoYmFzZSkgPT4ge1xuXG4gIC8qKlxuICAgKiBNaXhpbiB3aGljaCBhbGxvd3MgYSBjb21wb25lbnQgdG8gc3VwcG9ydCBhIFwiZ2VuZXJpY1wiIHN0eWxlOiBhIG1pbmltYWxpc3RcbiAgICogc3R5bGUgdGhhdCBjYW4gZWFzaWx5IGJlIHJlbW92ZWQgdG8gcmVzZXQgaXRzIHZpc3VhbCBhcHBlYXJhbmNlIHRvIGFcbiAgICogYmFzZWxpbmUgc3RhdGUuXG4gICAqXG4gICAqIEJ5IGRlZmF1bHQsIGEgY29tcG9uZW50IHNob3VsZCBwcm92aWRlIGEgbWluaW1hbCB2aXN1YWwgcHJlc2VudGF0aW9uIHRoYXRcbiAgICogYWxsb3dzIHRoZSBjb21wb25lbnQgdG8gZnVuY3Rpb24uIEhvd2V2ZXIsIHRoZSBtb3JlIHN0eWxpbmcgdGhlIGNvbXBvbmVudFxuICAgKiBwcm92aWRlcyBieSBkZWZhdWx0LCB0aGUgaGFyZGVyIGl0IGJlY29tZXMgdG8gZ2V0IHRoZSBjb21wb25lbnQgdG8gZml0IGluXG4gICAqIGluIG90aGVyIHNldHRpbmdzLiBFYWNoIENTUyBydWxlIGhhcyB0byBiZSBvdmVycmlkZGVuLiBXb3JzZSwgbmV3IENTUyBydWxlc1xuICAgKiBhZGRlZCB0byB0aGUgZGVmYXVsdCBzdHlsZSB3b24ndCBiZSBvdmVycmlkZGVuIGJ5IGRlZmF1bHQsIG1ha2luZyBpdCBoYXJkXG4gICAqIHRvIGtub3cgd2hldGhlciBhIG5ldyB2ZXJzaW9uIG9mIGEgY29tcG9uZW50IHdpbGwgc3RpbGwgbG9vayBva2F5LlxuICAgKlxuICAgKiBBcyBhIGNvbXByb21pc2UsIHRoZSBtaXhpbiBkZWZpbmVzIGEgYGdlbmVyaWNgIGF0dHJpYnV0ZS4gVGhpcyBhdHRyaWJ1dGUgaXNcbiAgICogbm9ybWFsbHkgc2V0IGJ5IGRlZmF1bHQsIGFuZCBzdHlsZXMgY2FuIGJlIHdyaXR0ZW4gdGhhdCBhcHBseSBvbmx5IHdoZW4gdGhlXG4gICAqIGdlbmVyaWMgYXR0cmlidXRlIGlzIHNldC4gVGhpcyBhbGxvd3MgdGhlIGNvbnN0cnVjdGlvbiBvZiBDU1MgcnVsZXMgdGhhdFxuICAgKiB3aWxsIG9ubHkgYXBwbHkgdG8gZ2VuZXJpYyBjb21wb25lbnRzIGxpa2U6XG4gICAqXG4gICAqICAgICA6aG9zdChbZ2VuZXJpYz1cIlwiXSkge1xuICAgKiAgICAgICAuLi4gZ2VuZXJpYyBhcHBlYXJhbmNlIGRlZmluZWQgaGVyZSAuLi5cbiAgICogICAgIH1cbiAgICpcbiAgICogVGhpcyBtYWtlcyBpdCBlYXN5IHRvIHJlbW92ZSBhbGwgZGVmYXVsdCBzdHlsaW5nIOKAlCBzZXQgdGhlIGBHZW5lcmljTWl4aW5gXG4gICAqIGF0dHJpYnV0ZSB0byBmYWxzZSwgYW5kIGFsbCBkZWZhdWx0IHN0eWxpbmcgd2lsbCBiZSByZW1vdmVkLlxuICAgKi9cbiAgY2xhc3MgR2VuZXJpYyBleHRlbmRzIGJhc2Uge1xuXG4gICAgY29uc3RydWN0b3IoKSB7XG4gICAgICBzdXBlcigpO1xuICAgICAgLy8gU2V0IGRlZmF1bHRzLlxuICAgICAgaWYgKHR5cGVvZiB0aGlzLmdlbmVyaWMgPT09ICd1bmRlZmluZWQnKSB7XG4gICAgICAgIHRoaXMuZ2VuZXJpYyA9IHRoaXNbc3ltYm9scy5kZWZhdWx0c10uZ2VuZXJpYztcbiAgICAgIH1cbiAgICB9XG5cbiAgICAvLyBUaGlzIG1peGluIGRvZXNuJ3QgYWN0dWFsbHkgcmVzcG9uZCB0byBhdHRyaWJ1dGUgY2hhbmdlcywgYnV0IHJlbGllc1xuICAgIC8vIG9uIHNlcGFyYXRlbHktZGVmaW5lZCBiZWhhdmlvciAoZS5nLiwgaW4gQXR0cmlidXRlTWFyc2hhbGxpbmdNaXhpbikgZm9yIHRoYXQuXG4gICAgLy8gU3RpbGwsIHdlIG5lZWQgZGVmaW5lIGEgYmFzZWxpbmUgYXR0cmlidXRlQ2hhbmdlZENhbGxiYWNrIHRoYXQgZG9lc1xuICAgIC8vIG5vdGhpbmcsIGluIGNhc2UgdGhpcyBtaXhpbiBnZXRzIHVzZWQgb24gaXRzIG93bi5cbiAgICBhdHRyaWJ1dGVDaGFuZ2VkQ2FsbGJhY2sobmFtZSwgb2xkVmFsdWUsIG5ld1ZhbHVlKSB7XG4gICAgICBpZiAoc3VwZXIuYXR0cmlidXRlQ2hhbmdlZENhbGxiYWNrKSB7IHN1cGVyLmF0dHJpYnV0ZUNoYW5nZWRDYWxsYmFjayhuYW1lLCBvbGRWYWx1ZSwgbmV3VmFsdWUpOyB9XG4gICAgfVxuXG4gICAgY29ubmVjdGVkQ2FsbGJhY2soKSB7XG4gICAgICBpZiAoc3VwZXIuY29ubmVjdGVkQ2FsbGJhY2spIHsgc3VwZXIuY29ubmVjdGVkQ2FsbGJhY2soKTsgfVxuICAgICAgc2FmZUF0dHJpYnV0ZXMuY29ubmVjdGVkKHRoaXMpO1xuICAgIH1cblxuICAgIGdldCBbc3ltYm9scy5kZWZhdWx0c10oKSB7XG4gICAgICBjb25zdCBkZWZhdWx0cyA9IHN1cGVyW3N5bWJvbHMuZGVmYXVsdHNdIHx8IHt9O1xuICAgICAgZGVmYXVsdHMuZ2VuZXJpYyA9IHRydWU7XG4gICAgICByZXR1cm4gZGVmYXVsdHM7XG4gICAgfVxuXG4gICAgLyoqXG4gICAgICogVHJ1ZSBpZiB0aGUgY29tcG9uZW50IHdvdWxkIGxpa2UgdG8gcmVjZWl2ZSBnZW5lcmljIHN0eWxpbmcuXG4gICAgICpcbiAgICAgKiBUaGlzIHByb3BlcnR5IGlzIHRydWUgYnkgZGVmYXVsdCDigJTCoHNldCBpdCB0byBmYWxzZSB0byB0dXJuIG9mZiBhbGxcbiAgICAgKiBnZW5lcmljIHN0eWxlcy4gVGhpcyBtYWtlcyBpdCBlYXNpZXIgdG8gYXBwbHkgY3VzdG9tIHN0eWxpbmc7IHlvdSB3b24ndFxuICAgICAqIGhhdmUgdG8gZXhwbGljaXRseSBvdmVycmlkZSBzdHlsaW5nIHlvdSBkb24ndCB3YW50LlxuICAgICAqXG4gICAgICogQHR5cGUgQm9vbGVhblxuICAgICAqIEBkZWZhdWx0IHRydWVcbiAgICAgKi9cbiAgICBnZXQgZ2VuZXJpYygpIHtcbiAgICAgIHJldHVybiB0aGlzW2dlbmVyaWNTeW1ib2xdO1xuICAgIH1cbiAgICBzZXQgZ2VuZXJpYyh2YWx1ZSkge1xuICAgICAgY29uc3QgcGFyc2VkID0gdHlwZW9mIHZhbHVlID09PSAnc3RyaW5nJyA/XG4gICAgICAgIFN0cmluZyh2YWx1ZSkgIT09ICdmYWxzZScgOlxuICAgICAgICB2YWx1ZTtcbiAgICAgIHRoaXNbZ2VuZXJpY1N5bWJvbF0gPSBwYXJzZWQ7XG5cbiAgICAgIGlmICgnZ2VuZXJpYycgaW4gYmFzZS5wcm90b3R5cGUpIHsgc3VwZXIuZ2VuZXJpYyA9IHZhbHVlOyB9XG5cbiAgICAgIC8vIFdlIHJvbGwgb3VyIG93biBhdHRyaWJ1dGUgc2V0dGluZyBzbyB0aGF0IGFuIGV4cGxpY2l0bHkgZmFsc2UgdmFsdWVcbiAgICAgIC8vIHNob3dzIHVwIGFzIEdlbmVyaWNNaXhpbj1cImZhbHNlXCIuXG4gICAgICBpZiAocGFyc2VkID09PSBmYWxzZSkge1xuICAgICAgICAvLyBFeHBsaWNpdGx5IHVzZSBmYWxzZSBzdHJpbmcuXG4gICAgICAgIHNhZmVBdHRyaWJ1dGVzLnNldEF0dHJpYnV0ZSh0aGlzLCAnZ2VuZXJpYycsICdmYWxzZScpO1xuICAgICAgfSBlbHNlIGlmIChwYXJzZWQgPT0gbnVsbCkge1xuICAgICAgICAvLyBFeHBsaWNpdGx5IHJlbW92ZSBhdHRyaWJ1dGUuIChBbHdheXMgc2FmZSB0byBkbyB0aGlzLilcbiAgICAgICAgdGhpcy5yZW1vdmVBdHRyaWJ1dGUoJ2dlbmVyaWMnKTtcbiAgICAgIH0gZWxzZSB7XG4gICAgICAgIC8vIFVzZSB0aGUgZW1wdHkgc3RyaW5nIHRvIGdldCBhdHRyaWJ1dGUgdG8gYXBwZWFyIHdpdGggbm8gdmFsdWUuXG4gICAgICAgIHNhZmVBdHRyaWJ1dGVzLnNldEF0dHJpYnV0ZSh0aGlzLCAnZ2VuZXJpYycsICcnKTtcbiAgICAgIH1cbiAgICB9XG5cbiAgfVxuXG4gIHJldHVybiBHZW5lcmljO1xufTtcblxuXG4iLCJpbXBvcnQgY3JlYXRlU3ltYm9sIGZyb20gJy4vY3JlYXRlU3ltYm9sJztcbmltcG9ydCBzeW1ib2xzIGZyb20gJy4vc3ltYm9scyc7XG5cblxuLy8gU3ltYm9scyBmb3IgcHJpdmF0ZSBkYXRhIG1lbWJlcnMgb24gYW4gZWxlbWVudC5cbmNvbnN0IG5hdmlnYXRpb25BeGlzU3ltYm9sID0gY3JlYXRlU3ltYm9sKCduYXZpZ2F0aW9uQXhpcycpO1xuXG5cbi8qIEV4cG9ydGVkIGZ1bmN0aW9uIGV4dGVuZHMgYSBiYXNlIGNsYXNzIHdpdGggS2V5Ym9hcmREaXJlY3Rpb24uICovXG5leHBvcnQgZGVmYXVsdCAoYmFzZSkgPT4ge1xuXG4gIC8qKlxuICAgKiBNaXhpbiB3aGljaCBtYXBzIGRpcmVjdGlvbiBrZXlzIChMZWZ0LCBSaWdodCwgZXRjLikgdG8gZGlyZWN0aW9uIHNlbWFudGljc1xuICAgKiAoZ28gbGVmdCwgZ28gcmlnaHQsIGV0Yy4pLlxuICAgKlxuICAgKiBUaGlzIG1peGluIGV4cGVjdHMgdGhlIGNvbXBvbmVudCB0byBpbnZva2UgYSBga2V5ZG93bmAgbWV0aG9kIHdoZW4gYSBrZXkgaXNcbiAgICogcHJlc3NlZC4gWW91IGNhbiB1c2UgW0tleWJvYXJkTWl4aW5dKEtleWJvYXJkTWl4aW4ubWQpIGZvciB0aGF0XG4gICAqIHB1cnBvc2UsIG9yIHdpcmUgdXAgeW91ciBvd24ga2V5Ym9hcmQgaGFuZGxpbmcgYW5kIGNhbGwgYGtleWRvd25gIHlvdXJzZWxmLlxuICAgKlxuICAgKiBUaGlzIG1peGluIGNhbGxzIG1ldGhvZHMgc3VjaCBhcyBgZ29MZWZ0YCBhbmQgYGdvUmlnaHRgLiBZb3UgY2FuIGRlZmluZVxuICAgKiB3aGF0IHRoYXQgbWVhbnMgYnkgaW1wbGVtZW50aW5nIHRob3NlIG1ldGhvZHMgeW91cnNlbGYuIElmIHlvdSB3YW50IHRvIHVzZVxuICAgKiBkaXJlY3Rpb24ga2V5cyB0byBuYXZpZ2F0ZSBhIHNlbGVjdGlvbiwgdXNlIHRoaXMgbWl4aW4gd2l0aFxuICAgKiBbRGlyZWN0aW9uU2VsZWN0aW9uTWl4aW5dKERpcmVjdGlvblNlbGVjdGlvbk1peGluLm1kKS5cbiAgICovXG4gIGNsYXNzIEtleWJvYXJkRGlyZWN0aW9uIGV4dGVuZHMgYmFzZSB7XG5cbiAgICBjb25zdHJ1Y3RvcigpIHtcbiAgICAgIHN1cGVyKCk7XG4gICAgICAvLyBTZXQgZGVmYXVsdHMuXG4gICAgICBpZiAodHlwZW9mIHRoaXMubmF2aWdhdGlvbkF4aXMgPT09ICd1bmRlZmluZWQnKSB7XG4gICAgICAgIHRoaXMubmF2aWdhdGlvbkF4aXMgPSB0aGlzW3N5bWJvbHMuZGVmYXVsdHNdLm5hdmlnYXRpb25BeGlzO1xuICAgICAgfVxuICAgIH1cblxuICAgIGdldCBbc3ltYm9scy5kZWZhdWx0c10oKSB7XG4gICAgICBjb25zdCBkZWZhdWx0cyA9IHN1cGVyW3N5bWJvbHMuZGVmYXVsdHNdIHx8IHt9O1xuICAgICAgZGVmYXVsdHMubmF2aWdhdGlvbkF4aXMgPSAnYm90aCc7XG4gICAgICByZXR1cm4gZGVmYXVsdHM7XG4gICAgfVxuXG4gICAgLyoqXG4gICAgICogSW52b2tlZCB3aGVuIHRoZSB1c2VyIHdhbnRzIHRvIGdvL25hdmlnYXRlIGRvd24uXG4gICAgICogVGhlIGRlZmF1bHQgaW1wbGVtZW50YXRpb24gb2YgdGhpcyBtZXRob2QgZG9lcyBub3RoaW5nLlxuICAgICAqL1xuICAgIFtzeW1ib2xzLmdvRG93bl0oKSB7XG4gICAgICBpZiAoc3VwZXJbc3ltYm9scy5nb0Rvd25dKSB7IHJldHVybiBzdXBlcltzeW1ib2xzLmdvRG93bl0oKTsgfVxuICAgIH1cblxuICAgIC8qKlxuICAgICAqIEludm9rZWQgd2hlbiB0aGUgdXNlciB3YW50cyB0byBnby9uYXZpZ2F0ZSB0byB0aGUgZW5kIChlLmcuLCBvZiBhIGxpc3QpLlxuICAgICAqIFRoZSBkZWZhdWx0IGltcGxlbWVudGF0aW9uIG9mIHRoaXMgbWV0aG9kIGRvZXMgbm90aGluZy5cbiAgICAgKi9cbiAgICBbc3ltYm9scy5nb0VuZF0oKSB7XG4gICAgICBpZiAoc3VwZXJbc3ltYm9scy5nb0VuZF0pIHsgcmV0dXJuIHN1cGVyW3N5bWJvbHMuZ29FbmRdKCk7IH1cbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBJbnZva2VkIHdoZW4gdGhlIHVzZXIgd2FudHMgdG8gZ28vbmF2aWdhdGUgbGVmdC5cbiAgICAgKiBUaGUgZGVmYXVsdCBpbXBsZW1lbnRhdGlvbiBvZiB0aGlzIG1ldGhvZCBkb2VzIG5vdGhpbmcuXG4gICAgICovXG4gICAgW3N5bWJvbHMuZ29MZWZ0XSgpIHtcbiAgICAgIGlmIChzdXBlcltzeW1ib2xzLmdvTGVmdF0pIHsgcmV0dXJuIHN1cGVyW3N5bWJvbHMuZ29MZWZ0XSgpOyB9XG4gICAgfVxuXG4gICAgLyoqXG4gICAgICogSW52b2tlZCB3aGVuIHRoZSB1c2VyIHdhbnRzIHRvIGdvL25hdmlnYXRlIHJpZ2h0LlxuICAgICAqIFRoZSBkZWZhdWx0IGltcGxlbWVudGF0aW9uIG9mIHRoaXMgbWV0aG9kIGRvZXMgbm90aGluZy5cbiAgICAgKi9cbiAgICBbc3ltYm9scy5nb1JpZ2h0XSgpIHtcbiAgICAgIGlmIChzdXBlcltzeW1ib2xzLmdvUmlnaHRdKSB7IHJldHVybiBzdXBlcltzeW1ib2xzLmdvUmlnaHRdKCk7IH1cbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBJbnZva2VkIHdoZW4gdGhlIHVzZXIgd2FudHMgdG8gZ28vbmF2aWdhdGUgdG8gdGhlIHN0YXJ0IChlLmcuLCBvZiBhXG4gICAgICogbGlzdCkuIFRoZSBkZWZhdWx0IGltcGxlbWVudGF0aW9uIG9mIHRoaXMgbWV0aG9kIGRvZXMgbm90aGluZy5cbiAgICAgKi9cbiAgICBbc3ltYm9scy5nb1N0YXJ0XSgpIHtcbiAgICAgIGlmIChzdXBlcltzeW1ib2xzLmdvU3RhcnRdKSB7IHJldHVybiBzdXBlcltzeW1ib2xzLmdvU3RhcnRdKCk7IH1cbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBJbnZva2VkIHdoZW4gdGhlIHVzZXIgd2FudHMgdG8gZ28vbmF2aWdhdGUgdXAuXG4gICAgICogVGhlIGRlZmF1bHQgaW1wbGVtZW50YXRpb24gb2YgdGhpcyBtZXRob2QgZG9lcyBub3RoaW5nLlxuICAgICAqL1xuICAgIFtzeW1ib2xzLmdvVXBdKCkge1xuICAgICAgaWYgKHN1cGVyW3N5bWJvbHMuZ29VcF0pIHsgcmV0dXJuIHN1cGVyW3N5bWJvbHMuZ29VcF0oKTsgfVxuICAgIH1cblxuICAgIC8qKlxuICAgICAqIEluZGljYXRlcyB0aGUgZGlyZWN0aW9uIG9mIHBlcm1pdHRlZCBuYXZpZ2F0aW9uIHdpdGggdGhlIGtleWJvYXJkLlxuICAgICAqXG4gICAgICogQWNjZXB0ZWQgdmFsdWVzIGFyZSBcImhvcml6b250YWxcIiwgXCJ2ZXJ0aWNhbFwiLCBvciBcImJvdGhcIiAodGhlIGRlZmF1bHQpLlxuICAgICAqIElmIHRoaXMgcHJvcGVydHkgaXMgXCJob3Jpem9udGFsXCIsIHRoZSBVcCBBcnJvdyBhbmQgRG93biBBcnJvdyBrZXlzIHdpbGxcbiAgICAgKiBiZSBpZ25vcmVkLiBDb252ZXJzZWx5LCBpZiB0aGlzIGlzIFwidmVydGljYWxcIiwgdGhlIExlZnQgQXJyb3cgYW5kIFJpZ2h0XG4gICAgICogQXJyb3cga2V5cyB3aWxsIGJlIGlnbm9yZWQuXG4gICAgICpcbiAgICAgKiBAdHlwZSB7c3RyaW5nfVxuICAgICAqL1xuICAgIGdldCBuYXZpZ2F0aW9uQXhpcygpIHtcbiAgICAgIHJldHVybiB0aGlzW25hdmlnYXRpb25BeGlzU3ltYm9sXTtcbiAgICB9XG4gICAgc2V0IG5hdmlnYXRpb25BeGlzKHZhbHVlKSB7XG4gICAgICB0aGlzW25hdmlnYXRpb25BeGlzU3ltYm9sXSA9IHZhbHVlO1xuICAgICAgaWYgKCduYXZpZ2F0aW9uQXhpcycgaW4gYmFzZS5wcm90b3R5cGUpIHsgc3VwZXIubmF2aWdhdGlvbkF4aXMgPSB2YWx1ZTsgfVxuICAgIH1cblxuICAgIFtzeW1ib2xzLmtleWRvd25dKGV2ZW50KSB7XG4gICAgICBsZXQgaGFuZGxlZDtcblxuICAgICAgY29uc3QgYXhpcyA9IHRoaXMubmF2aWdhdGlvbkF4aXM7XG4gICAgICBjb25zdCBob3Jpem9udGFsID0gKGF4aXMgPT09ICdob3Jpem9udGFsJyB8fCBheGlzID09PSAnYm90aCcpO1xuICAgICAgY29uc3QgdmVydGljYWwgPSAoYXhpcyA9PT0gJ3ZlcnRpY2FsJyB8fCBheGlzID09PSAnYm90aCcpO1xuXG4gICAgICAvLyBJZ25vcmUgTGVmdC9SaWdodCBrZXlzIHdoZW4gbWV0YUtleSBvciBhbHRLZXkgbW9kaWZpZXIgaXMgYWxzbyBwcmVzc2VkLFxuICAgICAgLy8gYXMgdGhlIHVzZXIgbWF5IGJlIHRyeWluZyB0byBuYXZpZ2F0ZSBiYWNrIG9yIGZvcndhcmQgaW4gdGhlIGJyb3dzZXIuXG4gICAgICBzd2l0Y2ggKGV2ZW50LmtleUNvZGUpIHtcbiAgICAgICAgY2FzZSAzNTogLy8gRW5kXG4gICAgICAgICAgaGFuZGxlZCA9IHRoaXNbc3ltYm9scy5nb0VuZF0oKTtcbiAgICAgICAgICBicmVhaztcbiAgICAgICAgY2FzZSAzNjogLy8gSG9tZVxuICAgICAgICAgIGhhbmRsZWQgPSB0aGlzW3N5bWJvbHMuZ29TdGFydF0oKTtcbiAgICAgICAgICBicmVhaztcbiAgICAgICAgY2FzZSAzNzogLy8gTGVmdFxuICAgICAgICAgIGlmIChob3Jpem9udGFsICYmICFldmVudC5tZXRhS2V5ICYmICFldmVudC5hbHRLZXkpIHtcbiAgICAgICAgICAgIGhhbmRsZWQgPSB0aGlzW3N5bWJvbHMuZ29MZWZ0XSgpO1xuICAgICAgICAgIH1cbiAgICAgICAgICBicmVhaztcbiAgICAgICAgY2FzZSAzODogLy8gVXBcbiAgICAgICAgICBpZiAodmVydGljYWwpIHtcbiAgICAgICAgICAgIGhhbmRsZWQgPSBldmVudC5hbHRLZXkgPyB0aGlzW3N5bWJvbHMuZ29TdGFydF0oKSA6IHRoaXNbc3ltYm9scy5nb1VwXSgpO1xuICAgICAgICAgIH1cbiAgICAgICAgICBicmVhaztcbiAgICAgICAgY2FzZSAzOTogLy8gUmlnaHRcbiAgICAgICAgICBpZiAoaG9yaXpvbnRhbCAmJiAhZXZlbnQubWV0YUtleSAmJiAhZXZlbnQuYWx0S2V5KSB7XG4gICAgICAgICAgICBoYW5kbGVkID0gdGhpc1tzeW1ib2xzLmdvUmlnaHRdKCk7XG4gICAgICAgICAgfVxuICAgICAgICAgIGJyZWFrO1xuICAgICAgICBjYXNlIDQwOiAvLyBEb3duXG4gICAgICAgICAgaWYgKHZlcnRpY2FsKSB7XG4gICAgICAgICAgICBoYW5kbGVkID0gZXZlbnQuYWx0S2V5ID8gdGhpc1tzeW1ib2xzLmdvRW5kXSgpIDogdGhpc1tzeW1ib2xzLmdvRG93bl0oKTtcbiAgICAgICAgICB9XG4gICAgICAgICAgYnJlYWs7XG4gICAgICB9XG4gICAgICAvLyBQcmVmZXIgbWl4aW4gcmVzdWx0IGlmIGl0J3MgZGVmaW5lZCwgb3RoZXJ3aXNlIHVzZSBiYXNlIHJlc3VsdC5cbiAgICAgIHJldHVybiBoYW5kbGVkIHx8IChzdXBlcltzeW1ib2xzLmtleWRvd25dICYmIHN1cGVyW3N5bWJvbHMua2V5ZG93bl0oZXZlbnQpKTtcbiAgICB9XG5cbiAgfVxuXG4gIHJldHVybiBLZXlib2FyZERpcmVjdGlvbjtcbn07XG4iLCJpbXBvcnQgc3ltYm9scyBmcm9tICcuL3N5bWJvbHMnO1xuXG5cbi8qIEV4cG9ydGVkIGZ1bmN0aW9uIGV4dGVuZHMgYSBiYXNlIGNsYXNzIHdpdGggS2V5Ym9hcmQuICovXG5leHBvcnQgZGVmYXVsdCAoYmFzZSkgPT4ge1xuXG4gIC8qKlxuICAgKiBNaXhpbiB3aGljaCBtYW5hZ2VzIHRoZSBrZXlkb3duIGhhbmRsaW5nIGZvciBhIGNvbXBvbmVudC5cbiAgICpcbiAgICogVGhpcyBtaXhpbiBoYW5kbGVzIHNldmVyYWwga2V5Ym9hcmQtcmVsYXRlZCBmZWF0dXJlcy5cbiAgICpcbiAgICogRmlyc3QsIGl0IHdpcmVzIHVwIGEgc2luZ2xlIGtleWRvd24gZXZlbnQgaGFuZGxlciB0aGF0IGNhbiBiZSBzaGFyZWQgYnlcbiAgICogbXVsdGlwbGUgbWl4aW5zIG9uIGEgY29tcG9uZW50LiBUaGUgZXZlbnQgaGFuZGxlciB3aWxsIGludm9rZSBhIGBrZXlkb3duYFxuICAgKiBtZXRob2Qgd2l0aCB0aGUgZXZlbnQgb2JqZWN0LCBhbmQgYW55IG1peGluIGFsb25nIHRoZSBwcm90b3R5cGUgY2hhaW4gdGhhdFxuICAgKiB3YW50cyB0byBoYW5kbGUgdGhhdCBtZXRob2QgY2FuIGRvIHNvLlxuICAgKlxuICAgKiBJZiBhIG1peGluIHdhbnRzIHRvIGluZGljYXRlIHRoYXQga2V5Ym9hcmQgZXZlbnQgaGFzIGJlZW4gaGFuZGxlZCwgYW5kIHRoYXRcbiAgICogb3RoZXIgbWl4aW5zIHNob3VsZCAqbm90KiBoYW5kbGUgaXQsIHRoZSBtaXhpbidzIGBrZXlkb3duYCBoYW5kbGVyIHNob3VsZFxuICAgKiByZXR1cm4gYSB2YWx1ZSBvZiB0cnVlLiBUaGUgY29udmVudGlvbiB0aGF0IHNlZW1zIHRvIHdvcmsgd2VsbCBpcyB0aGF0IGFcbiAgICogbWl4aW4gc2hvdWxkIHNlZSBpZiBpdCB3YW50cyB0byBoYW5kbGUgdGhlIGV2ZW50IGFuZCwgaWYgbm90LCB0aGVuIGFzayB0aGVcbiAgICogc3VwZXJjbGFzcyB0byBzZWUgaWYgaXQgd2FudHMgdG8gaGFuZGxlIHRoZSBldmVudC4gVGhpcyBoYXMgdGhlIGVmZmVjdCBvZlxuICAgKiBnaXZpbmcgdGhlIG1peGluIHRoYXQgd2FzIGFwcGxpZWQgbGFzdCB0aGUgZmlyc3QgY2hhbmNlIGF0IGhhbmRsaW5nIGFcbiAgICoga2V5Ym9hcmQgZXZlbnQuXG4gICAqXG4gICAqIEV4YW1wbGU6XG4gICAqXG4gICAqICAgICBbc3ltYm9scy5rZXlkb3duXShldmVudCkge1xuICAgKiAgICAgICBsZXQgaGFuZGxlZDtcbiAgICogICAgICAgc3dpdGNoIChldmVudC5rZXlDb2RlKSB7XG4gICAqICAgICAgICAgLy8gSGFuZGxlIHRoZSBrZXlzIHlvdSB3YW50LCBzZXR0aW5nIGhhbmRsZWQgPSB0cnVlIGlmIGFwcHJvcHJpYXRlLlxuICAgKiAgICAgICB9XG4gICAqICAgICAgIC8vIFByZWZlciBtaXhpbiByZXN1bHQgaWYgaXQncyBkZWZpbmVkLCBvdGhlcndpc2UgdXNlIGJhc2UgcmVzdWx0LlxuICAgKiAgICAgICByZXR1cm4gaGFuZGxlZCB8fCAoc3VwZXJbc3ltYm9scy5rZXlkb3duXSAmJiBzdXBlcltzeW1ib2xzLmtleWRvd25dKGV2ZW50KSk7XG4gICAqICAgICB9XG4gICAqXG4gICAqIEEgc2Vjb25kIGZlYXR1cmUgcHJvdmlkZWQgYnkgdGhpcyBtaXhpbiBpcyB0aGF0IGl0IGltcGxpY2l0bHkgbWFrZXMgdGhlXG4gICAqIGNvbXBvbmVudCBhIHRhYiBzdG9wIGlmIGl0IGlzbid0IGFscmVhZHksIGJ5IHNldHRpbmcgYHRhYkluZGV4YCB0byAwLiBUaGlzXG4gICAqIGhhcyB0aGUgZWZmZWN0IG9mIGFkZGluZyB0aGUgY29tcG9uZW50IHRvIHRoZSB0YWIgb3JkZXIgaW4gZG9jdW1lbnQgb3JkZXIuXG4gICAqL1xuICBjbGFzcyBLZXlib2FyZCBleHRlbmRzIGJhc2Uge1xuXG4gICAgY29uc3RydWN0b3IoKSB7XG4gICAgICBzdXBlcigpO1xuICAgICAgdGhpcy5hZGRFdmVudExpc3RlbmVyKCdrZXlkb3duJywgZXZlbnQgPT4ge1xuICAgICAgICBjb25zdCBoYW5kbGVkID0gdGhpc1tzeW1ib2xzLmtleWRvd25dKGV2ZW50KTtcbiAgICAgICAgaWYgKGhhbmRsZWQpIHtcbiAgICAgICAgICBldmVudC5wcmV2ZW50RGVmYXVsdCgpO1xuICAgICAgICAgIGV2ZW50LnN0b3BQcm9wYWdhdGlvbigpO1xuICAgICAgICB9XG4gICAgICB9KTtcbiAgICB9XG5cbiAgICBjb25uZWN0ZWRDYWxsYmFjaygpIHtcbiAgICAgIGlmIChzdXBlci5jb25uZWN0ZWRDYWxsYmFjaykgeyBzdXBlci5jb25uZWN0ZWRDYWxsYmFjaygpOyB9XG4gICAgICBpZiAodGhpcy5nZXRBdHRyaWJ1dGUoJ3RhYmluZGV4JykgPT0gbnVsbCAmJiB0aGlzW3N5bWJvbHMuZGVmYXVsdHNdLnRhYmluZGV4ICE9PSBudWxsKSB7XG4gICAgICAgIHRoaXMuc2V0QXR0cmlidXRlKCd0YWJpbmRleCcsIHRoaXNbc3ltYm9scy5kZWZhdWx0c10udGFiaW5kZXgpO1xuICAgICAgfVxuICAgIH1cblxuICAgIGdldCBbc3ltYm9scy5kZWZhdWx0c10oKSB7XG4gICAgICBjb25zdCBkZWZhdWx0cyA9IHN1cGVyW3N5bWJvbHMuZGVmYXVsdHNdIHx8IHt9O1xuICAgICAgLy8gVGhlIGRlZmF1bHQgdGFiIGluZGV4IGlzIDAgKGRvY3VtZW50IG9yZGVyKS5cbiAgICAgIGRlZmF1bHRzLnRhYmluZGV4ID0gMDtcbiAgICAgIHJldHVybiBkZWZhdWx0cztcbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBIYW5kbGUgdGhlIGluZGljYXRlZCBrZXlib2FyZCBldmVudC5cbiAgICAgKlxuICAgICAqIFRoZSBkZWZhdWx0IGltcGxlbWVudGF0aW9uIG9mIHRoaXMgbWV0aG9kIGRvZXMgbm90aGluZy4gVGhpcyB3aWxsXG4gICAgICogdHlwaWNhbGx5IGJlIGhhbmRsZWQgYnkgb3RoZXIgbWl4aW5zLlxuICAgICAqXG4gICAgICogQHBhcmFtIHtLZXlib2FyZEV2ZW50fSBldmVudCAtIHRoZSBrZXlib2FyZCBldmVudFxuICAgICAqIEByZXR1cm4ge2Jvb2xlYW59IHRydWUgaWYgdGhlIGV2ZW50IHdhcyBoYW5kbGVkXG4gICAgICovXG4gICAgW3N5bWJvbHMua2V5ZG93bl0oZXZlbnQpIHtcbiAgICAgIGlmIChzdXBlcltzeW1ib2xzLmtleWRvd25dKSB7IHJldHVybiBzdXBlcltzeW1ib2xzLmtleWRvd25dKGV2ZW50KTsgfVxuICAgIH1cblxuICB9XG5cbiAgcmV0dXJuIEtleWJvYXJkO1xufTtcbiIsImltcG9ydCBzeW1ib2xzIGZyb20gJy4vc3ltYm9scyc7XG5cblxuLyogRXhwb3J0ZWQgZnVuY3Rpb24gZXh0ZW5kcyBhIGJhc2UgY2xhc3Mgd2l0aCBLZXlib2FyZFBhZ2VkU2VsZWN0aW9uLiAqL1xuZXhwb3J0IGRlZmF1bHQgKGJhc2UpID0+IHtcblxuICAvKipcbiAgICogTWl4aW4gd2hpY2ggbWFwcyBwYWdlIGtleXMgKFBhZ2UgVXAsIFBhZ2UgRG93bikgaW50byBvcGVyYXRpb25zIHRoYXQgbW92ZVxuICAgKiB0aGUgc2VsZWN0aW9uIGJ5IG9uZSBwYWdlLlxuICAgKlxuICAgKiBUaGUga2V5Ym9hcmQgaW50ZXJhY3Rpb24gbW9kZWwgZ2VuZXJhbGx5IGZvbGxvd3MgdGhhdCBvZiBNaWNyb3NvZnQgV2luZG93cydcbiAgICogbGlzdCBib3hlcyBpbnN0ZWFkIG9mIHRob3NlIGluIE9TIFg6XG4gICAqXG4gICAqICogVGhlIFBhZ2UgVXAvRG93biBhbmQgSG9tZS9FbmQga2V5cyBhY3R1YWxseSBjaGFuZ2UgdGhlIHNlbGVjdGlvbiwgcmF0aGVyXG4gICAqICAgdGhhbiBqdXN0IHNjcm9sbGluZy4gVGhlIGZvcm1lciBiZWhhdmlvciBzZWVtcyBtb3JlIGdlbmVyYWxseSB1c2VmdWwgZm9yXG4gICAqICAga2V5Ym9hcmQgdXNlcnMuXG4gICAqXG4gICAqICogUHJlc3NpbmcgUGFnZSBVcC9Eb3duIHdpbGwgY2hhbmdlIHRoZSBzZWxlY3Rpb24gdG8gdGhlIHRvcG1vc3QvYm90dG9tbW9zdFxuICAgKiAgIHZpc2libGUgaXRlbSBpZiB0aGUgc2VsZWN0aW9uIGlzIG5vdCBhbHJlYWR5IHRoZXJlLiBUaGVyZWFmdGVyLCB0aGUga2V5XG4gICAqICAgd2lsbCBtb3ZlIHRoZSBzZWxlY3Rpb24gdXAvZG93biBieSBhIHBhZ2UsIGFuZCAocGVyIHRoZSBhYm92ZSBwb2ludCkgbWFrZVxuICAgKiAgIHRoZSBzZWxlY3RlZCBpdGVtIHZpc2libGUuXG4gICAqXG4gICAqIFRvIGVuc3VyZSB0aGUgc2VsZWN0ZWQgaXRlbSBpcyBpbiB2aWV3IGZvbGxvd2luZyB1c2Ugb2YgUGFnZSBVcC9Eb3duLCB1c2VcbiAgICogdGhlIHJlbGF0ZWQgW1NlbGVjdGlvbkluVmlld01peGluXShTZWxlY3Rpb25JblZpZXdNaXhpbi5tZCkuXG4gICAqXG4gICAqIFRoaXMgbWl4aW4gZXhwZWN0cyB0aGUgY29tcG9uZW50IHRvIGludm9rZSBhIGBrZXlkb3duYCBtZXRob2Qgd2hlbiBhIGtleSBpc1xuICAgKiBwcmVzc2VkLiBZb3UgY2FuIHVzZSBbS2V5Ym9hcmRNaXhpbl0oS2V5Ym9hcmRNaXhpbi5tZCkgZm9yIHRoYXRcbiAgICogcHVycG9zZSwgb3Igd2lyZSB1cCB5b3VyIG93biBrZXlib2FyZCBoYW5kbGluZyBhbmQgY2FsbCBga2V5ZG93bmAgeW91cnNlbGYuXG4gICAqL1xuICBjbGFzcyBLZXlib2FyZFBhZ2VkU2VsZWN0aW9uIGV4dGVuZHMgYmFzZSB7XG5cbiAgICBbc3ltYm9scy5rZXlkb3duXShldmVudCkge1xuICAgICAgbGV0IGhhbmRsZWQ7XG4gICAgICBzd2l0Y2ggKGV2ZW50LmtleUNvZGUpIHtcbiAgICAgICAgY2FzZSAzMzogLy8gUGFnZSBVcFxuICAgICAgICAgIGhhbmRsZWQgPSB0aGlzLnBhZ2VVcCgpO1xuICAgICAgICAgIGJyZWFrO1xuICAgICAgICBjYXNlIDM0OiAvLyBQYWdlIERvd25cbiAgICAgICAgICBoYW5kbGVkID0gdGhpcy5wYWdlRG93bigpO1xuICAgICAgICAgIGJyZWFrO1xuICAgICAgfVxuICAgICAgLy8gUHJlZmVyIG1peGluIHJlc3VsdCBpZiBpdCdzIGRlZmluZWQsIG90aGVyd2lzZSB1c2UgYmFzZSByZXN1bHQuXG4gICAgICByZXR1cm4gaGFuZGxlZCB8fCAoc3VwZXJbc3ltYm9scy5rZXlkb3duXSAmJiBzdXBlcltzeW1ib2xzLmtleWRvd25dKGV2ZW50KSk7XG4gICAgfVxuXG4gICAgLyoqXG4gICAgICogU2Nyb2xsIGRvd24gb25lIHBhZ2UuXG4gICAgICovXG4gICAgcGFnZURvd24oKSB7XG4gICAgICBpZiAoc3VwZXIucGFnZURvd24pIHsgc3VwZXIucGFnZURvd24oKTsgfVxuICAgICAgcmV0dXJuIHNjcm9sbE9uZVBhZ2UodGhpcywgdHJ1ZSk7XG4gICAgfVxuXG4gICAgLyoqXG4gICAgICogU2Nyb2xsIHVwIG9uZSBwYWdlLlxuICAgICAqL1xuICAgIHBhZ2VVcCgpIHtcbiAgICAgIGlmIChzdXBlci5wYWdlVXApIHsgc3VwZXIucGFnZVVwKCk7IH1cbiAgICAgIHJldHVybiBzY3JvbGxPbmVQYWdlKHRoaXMsIGZhbHNlKTtcbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBUaGUgZWxlbWVudCB0aGF0IHNob3VsZCBiZSBzY3JvbGxlZCB3aXRoIHRoZSBQYWdlIFVwL0Rvd24ga2V5cy5cbiAgICAgKiBEZWZhdWx0IGlzIHRoZSBjdXJyZW50IGVsZW1lbnQuXG4gICAgICpcbiAgICAgKiBAdHlwZSB7SFRNTEVsZW1lbnR9XG4gICAgICovXG4gICAgZ2V0IHNjcm9sbFRhcmdldCgpIHtcbiAgICAgIC8vIFByZWZlciBiYXNlIHJlc3VsdC5cbiAgICAgIHJldHVybiAnc2Nyb2xsVGFyZ2V0JyBpbiBiYXNlLnByb3RvdHlwZSA/IHN1cGVyLnNjcm9sbFRhcmdldCA6IHRoaXM7XG4gICAgfVxuICAgIHNldCBzY3JvbGxUYXJnZXQoZWxlbWVudCkge1xuICAgICAgaWYgKCdzY3JvbGxUYXJnZXQnIGluIGJhc2UucHJvdG90eXBlKSB7IHN1cGVyLnNjcm9sbFRhcmdldCA9IGVsZW1lbnQ7IH1cbiAgICB9XG4gIH1cblxuICByZXR1cm4gS2V5Ym9hcmRQYWdlZFNlbGVjdGlvbjtcbn07XG5cblxuLy8gUmV0dXJuIHRoZSBpdGVtIHdob3NlIGNvbnRlbnQgc3BhbnMgdGhlIGdpdmVuIHkgcG9zaXRpb24gKHJlbGF0aXZlIHRvIHRoZVxuLy8gdG9wIG9mIHRoZSBsaXN0J3Mgc2Nyb2xsaW5nIGNsaWVudCBhcmVhKSwgb3IgbnVsbCBpZiBub3QgZm91bmQuXG4vL1xuLy8gSWYgZG93bndhcmQgaXMgdHJ1ZSwgbW92ZSBkb3duIHRoZSBsaXN0IG9mIGl0ZW1zIHRvIGZpbmQgdGhlIGZpcnN0IGl0ZW1cbi8vIGZvdW5kIGF0IHRoZSBnaXZlbiB5IHBvc2l0aW9uOyBpZiBkb3dud2FyZCBpcyBmYWxzZSwgbW92ZSB1cCB0aGUgbGlzdCBvZlxuLy8gaXRlbXMgdG8gZmluZCB0aGUgbGFzdCBpdGVtIGF0IHRoYXQgcG9zaXRpb24uXG5mdW5jdGlvbiBnZXRJbmRleE9mSXRlbUF0WShlbGVtZW50LCB5LCBkb3dud2FyZCkge1xuICBjb25zdCBpdGVtcyA9IGVsZW1lbnQuaXRlbXM7XG4gIGNvbnN0IHN0YXJ0ID0gZG93bndhcmQgPyAwIDogaXRlbXMubGVuZ3RoIC0gMTtcbiAgY29uc3QgZW5kID0gZG93bndhcmQgPyBpdGVtcy5sZW5ndGggOiAwO1xuICBjb25zdCBzdGVwID0gZG93bndhcmQgPyAxIDogLTE7XG4gIGNvbnN0IHNjcm9sbFRhcmdldCA9IGVsZW1lbnQuc2Nyb2xsVGFyZ2V0O1xuICBjb25zdCB0b3BPZkNsaWVudEFyZWEgPSBzY3JvbGxUYXJnZXQub2Zmc2V0VG9wICsgc2Nyb2xsVGFyZ2V0LmNsaWVudFRvcDtcblxuICAvLyBGaW5kIHRoZSBpdGVtIHNwYW5uaW5nIHRoZSBpbmRpY2F0ZWQgeSBjb29yZGluYXRlLlxuICBsZXQgaXRlbTtcbiAgbGV0IGl0ZW1JbmRleCA9IHN0YXJ0O1xuICBsZXQgaXRlbVRvcDtcbiAgbGV0IGZvdW5kID0gZmFsc2U7XG4gIHdoaWxlIChpdGVtSW5kZXggIT09IGVuZCkge1xuICAgIGl0ZW0gPSBpdGVtc1tpdGVtSW5kZXhdO1xuICAgIGl0ZW1Ub3AgPSBpdGVtLm9mZnNldFRvcCAtIHRvcE9mQ2xpZW50QXJlYTtcbiAgICBjb25zdCBpdGVtQm90dG9tID0gaXRlbVRvcCArIGl0ZW0ub2Zmc2V0SGVpZ2h0O1xuICAgIGlmIChpdGVtVG9wIDw9IHkgJiYgaXRlbUJvdHRvbSA+PSB5KSB7XG4gICAgICAvLyBJdGVtIHNwYW5zIHRoZSBpbmRpY2F0ZWQgeSBjb29yZGluYXRlLlxuICAgICAgZm91bmQgPSB0cnVlO1xuICAgICAgYnJlYWs7XG4gICAgfVxuICAgIGl0ZW1JbmRleCArPSBzdGVwO1xuICB9XG5cbiAgaWYgKCFmb3VuZCkge1xuICAgIHJldHVybiBudWxsO1xuICB9XG5cbiAgLy8gV2UgbWF5IGhhdmUgZm91bmQgYW4gaXRlbSB3aG9zZSBwYWRkaW5nIHNwYW5zIHRoZSBnaXZlbiB5IGNvb3JkaW5hdGUsXG4gIC8vIGJ1dCB3aG9zZSBjb250ZW50IGlzIGFjdHVhbGx5IGFib3ZlL2JlbG93IHRoYXQgcG9pbnQuXG4gIC8vIFRPRE86IElmIHRoZSBpdGVtIGhhcyBhIGJvcmRlciwgdGhlbiBwYWRkaW5nIHNob3VsZCBiZSBpbmNsdWRlZCBpblxuICAvLyBjb25zaWRlcmluZyBhIGhpdC5cbiAgY29uc3QgaXRlbVN0eWxlID0gZ2V0Q29tcHV0ZWRTdHlsZShpdGVtKTtcbiAgY29uc3QgaXRlbVBhZGRpbmdUb3AgPSBwYXJzZUZsb2F0KGl0ZW1TdHlsZS5wYWRkaW5nVG9wKTtcbiAgY29uc3QgaXRlbVBhZGRpbmdCb3R0b20gPSBwYXJzZUZsb2F0KGl0ZW1TdHlsZS5wYWRkaW5nQm90dG9tKTtcbiAgY29uc3QgY29udGVudFRvcCA9IGl0ZW1Ub3AgKyBpdGVtLmNsaWVudFRvcCArIGl0ZW1QYWRkaW5nVG9wO1xuICBjb25zdCBjb250ZW50Qm90dG9tID0gY29udGVudFRvcCArIGl0ZW0uY2xpZW50SGVpZ2h0IC0gaXRlbVBhZGRpbmdUb3AgLSBpdGVtUGFkZGluZ0JvdHRvbTtcbiAgaWYgKGRvd253YXJkICYmIGNvbnRlbnRUb3AgPD0geSB8fCAhZG93bndhcmQgJiYgY29udGVudEJvdHRvbSA+PSB5KSB7XG4gICAgLy8gVGhlIGluZGljYXRlZCBjb29yZGluYXRlIGhpdHMgdGhlIGFjdHVhbCBpdGVtIGNvbnRlbnQuXG4gICAgcmV0dXJuIGl0ZW1JbmRleDtcbiAgfVxuICBlbHNlIHtcbiAgICAvLyBUaGUgaW5kaWNhdGVkIGNvb3JkaW5hdGUgZmFsbHMgd2l0aGluIHRoZSBpdGVtJ3MgcGFkZGluZy4gQmFjayB1cCB0b1xuICAgIC8vIHRoZSBpdGVtIGJlbG93L2Fib3ZlIHRoZSBpdGVtIHdlIGZvdW5kIGFuZCByZXR1cm4gdGhhdC5cbiAgICByZXR1cm4gaXRlbUluZGV4IC0gc3RlcDtcbiAgfVxufVxuXG4vLyBNb3ZlIGJ5IG9uZSBwYWdlIGRvd253YXJkIChpZiBkb3dud2FyZCBpcyB0cnVlKSwgb3IgdXB3YXJkIChpZiBmYWxzZSkuXG4vLyBSZXR1cm4gdHJ1ZSBpZiB3ZSBlbmRlZCB1cCBjaGFuZ2luZyB0aGUgc2VsZWN0aW9uLCBmYWxzZSBpZiBub3QuXG4vLyBUT0RPOiBCZXR0ZXIgc3VwcG9ydCBmb3IgaG9yaXpvbnRhbCBsaXN0cy5cbmZ1bmN0aW9uIHNjcm9sbE9uZVBhZ2UoZWxlbWVudCwgZG93bndhcmQpIHtcblxuICAvLyBEZXRlcm1pbmUgdGhlIGl0ZW0gdmlzaWJsZSBqdXN0IGF0IHRoZSBlZGdlIG9mIGRpcmVjdGlvbiB3ZSdyZSBoZWFkaW5nLlxuICAvLyBXZSdsbCBzZWxlY3QgdGhhdCBpdGVtIGlmIGl0J3Mgbm90IGFscmVhZHkgc2VsZWN0ZWQuXG4gIGNvbnN0IHNjcm9sbFRhcmdldCA9IGVsZW1lbnQuc2Nyb2xsVGFyZ2V0O1xuICBjb25zdCBlZGdlID0gc2Nyb2xsVGFyZ2V0LnNjcm9sbFRvcCArIChkb3dud2FyZCA/IHNjcm9sbFRhcmdldC5jbGllbnRIZWlnaHQgOiAwKTtcbiAgY29uc3QgaW5kZXhPZkl0ZW1BdEVkZ2UgPSBnZXRJbmRleE9mSXRlbUF0WShlbGVtZW50LCBlZGdlLCBkb3dud2FyZCk7XG5cbiAgY29uc3Qgc2VsZWN0ZWRJbmRleCA9IGVsZW1lbnQuc2VsZWN0ZWRJbmRleDtcbiAgbGV0IG5ld0luZGV4O1xuICBpZiAoaW5kZXhPZkl0ZW1BdEVkZ2UgJiYgc2VsZWN0ZWRJbmRleCA9PT0gaW5kZXhPZkl0ZW1BdEVkZ2UpIHtcbiAgICAvLyBUaGUgaXRlbSBhdCB0aGUgZWRnZSB3YXMgYWxyZWFkeSBzZWxlY3RlZCwgc28gc2Nyb2xsIGluIHRoZSBpbmRpY2F0ZWRcbiAgICAvLyBkaXJlY3Rpb24gYnkgb25lIHBhZ2UuIExlYXZlIHRoZSBuZXcgaXRlbSBhdCB0aGF0IGVkZ2Ugc2VsZWN0ZWQuXG4gICAgY29uc3QgZGVsdGEgPSAoZG93bndhcmQgPyAxIDogLTEpICogc2Nyb2xsVGFyZ2V0LmNsaWVudEhlaWdodDtcbiAgICBuZXdJbmRleCA9IGdldEluZGV4T2ZJdGVtQXRZKGVsZW1lbnQsIGVkZ2UgKyBkZWx0YSwgZG93bndhcmQpO1xuICB9XG4gIGVsc2Uge1xuICAgIC8vIFRoZSBpdGVtIGF0IHRoZSBlZGdlIHdhc24ndCBzZWxlY3RlZCB5ZXQuIEluc3RlYWQgb2Ygc2Nyb2xsaW5nLCB3ZSdsbFxuICAgIC8vIGp1c3Qgc2VsZWN0IHRoYXQgaXRlbS4gVGhhdCBpcywgdGhlIGZpcnN0IGF0dGVtcHQgdG8gcGFnZSB1cC9kb3duXG4gICAgLy8gdXN1YWxseSBqdXN0IG1vdmVzIHRoZSBzZWxlY3Rpb24gdG8gdGhlIGVkZ2UgaW4gdGhhdCBkaXJlY3Rpb24uXG4gICAgbmV3SW5kZXggPSBpbmRleE9mSXRlbUF0RWRnZTtcbiAgfVxuXG4gIGlmICghbmV3SW5kZXgpIHtcbiAgICAvLyBXZSBjYW4ndCBmaW5kIGFuIGl0ZW0gaW4gdGhlIGRpcmVjdGlvbiB3ZSB3YW50IHRvIHRyYXZlbC4gU2VsZWN0IHRoZVxuICAgIC8vIGxhc3QgaXRlbSAoaWYgbW92aW5nIGRvd253YXJkKSBvciBmaXJzdCBpdGVtIChpZiBtb3ZpbmcgdXB3YXJkKS5cbiAgICBuZXdJbmRleCA9IChkb3dud2FyZCA/IGVsZW1lbnQuaXRlbXMubGVuZ3RoIC0gMSA6IDApO1xuICB9XG5cbiAgaWYgKG5ld0luZGV4ICE9PSBzZWxlY3RlZEluZGV4KSB7XG4gICAgZWxlbWVudC5zZWxlY3RlZEluZGV4ID0gbmV3SW5kZXg7XG4gICAgcmV0dXJuIHRydWU7IC8vIFdlIGhhbmRsZWQgdGhlIHBhZ2UgdXAvZG93biBvdXJzZWx2ZXMuXG4gIH1cbiAgZWxzZSB7XG4gICAgcmV0dXJuIGZhbHNlOyAvLyBXZSBkaWRuJ3QgZG8gYW55dGhpbmcuXG4gIH1cbn1cbiIsImltcG9ydCBjcmVhdGVTeW1ib2wgZnJvbSAnLi9jcmVhdGVTeW1ib2wnO1xuaW1wb3J0IHN5bWJvbHMgZnJvbSAnLi9zeW1ib2xzJztcblxuXG4vLyBTeW1ib2xzIGZvciBwcml2YXRlIGRhdGEgbWVtYmVycyBvbiBhbiBlbGVtZW50LlxuY29uc3QgaXRlbVRleHRDb250ZW50c1N5bWJvbCA9IGNyZWF0ZVN5bWJvbCgnaXRlbVRleHRDb250ZW50cycpO1xuY29uc3QgdHlwZWRQcmVmaXhTeW1ib2wgPSBjcmVhdGVTeW1ib2woJ3R5cGVkUHJlZml4Jyk7XG5jb25zdCBwcmVmaXhUaW1lb3V0U3ltYm9sID0gY3JlYXRlU3ltYm9sKCdwcmVmaXhUaW1lb3V0Jyk7XG5cblxuLyogRXhwb3J0ZWQgZnVuY3Rpb24gZXh0ZW5kcyBhIGJhc2UgY2xhc3Mgd2l0aCBLZXlib2FyZFByZWZpeFNlbGVjdGlvbi4gKi9cbmV4cG9ydCBkZWZhdWx0IChiYXNlKSA9PiB7XG5cbiAgLyoqXG4gICAqIE1peGluIHRoYXQgaGFuZGxlcyBsaXN0IGJveC1zdHlsZSBwcmVmaXggdHlwaW5nLCBpbiB3aGljaCB0aGUgdXNlciBjYW4gdHlwZVxuICAgKiBhIHN0cmluZyB0byBzZWxlY3QgdGhlIGZpcnN0IGl0ZW0gdGhhdCBiZWdpbnMgd2l0aCB0aGF0IHN0cmluZy5cbiAgICpcbiAgICogRXhhbXBsZTogc3VwcG9zZSBhIGNvbXBvbmVudCB1c2luZyB0aGlzIG1peGluIGhhcyB0aGUgZm9sbG93aW5nIGl0ZW1zOlxuICAgKlxuICAgKiAgICAgPHNhbXBsZS1saXN0LWNvbXBvbmVudD5cbiAgICogICAgICAgPGRpdj5BcHBsZTwvZGl2PlxuICAgKiAgICAgICA8ZGl2PkFwcmljb3Q8L2Rpdj5cbiAgICogICAgICAgPGRpdj5CYW5hbmE8L2Rpdj5cbiAgICogICAgICAgPGRpdj5CbGFja2JlcnJ5PC9kaXY+XG4gICAqICAgICAgIDxkaXY+Qmx1ZWJlcnJ5PC9kaXY+XG4gICAqICAgICAgIDxkaXY+Q2FudGFsb3VwZTwvZGl2PlxuICAgKiAgICAgICA8ZGl2PkNoZXJyeTwvZGl2PlxuICAgKiAgICAgICA8ZGl2PkxlbW9uPC9kaXY+XG4gICAqICAgICAgIDxkaXY+TGltZTwvZGl2PlxuICAgKiAgICAgPC9zYW1wbGUtbGlzdC1jb21wb25lbnQ+XG4gICAqXG4gICAqIElmIHRoaXMgY29tcG9uZW50IHJlY2VpdmVzIHRoZSBmb2N1cywgYW5kIHRoZSB1c2VyIHByZXNzZXMgdGhlIFwiYlwiIG9yIFwiQlwiXG4gICAqIGtleSwgdGhlIFwiQmFuYW5hXCIgaXRlbSB3aWxsIGJlIHNlbGVjdGVkLCBiZWNhdXNlIGl0J3MgdGhlIGZpcnN0IGl0ZW0gdGhhdFxuICAgKiBtYXRjaGVzIHRoZSBwcmVmaXggXCJiXCIuIChNYXRjaGluZyBpcyBjYXNlLWluc2Vuc2l0aXZlLikgSWYgdGhlIHVzZXIgbm93XG4gICAqIHByZXNzZXMgdGhlIFwibFwiIG9yIFwiTFwiIGtleSBxdWlja2x5LCB0aGUgcHJlZml4IHRvIG1hdGNoIGJlY29tZXMgXCJibFwiLCBzb1xuICAgKiBcIkJsYWNrYmVycnlcIiB3aWxsIGJlIHNlbGVjdGVkLlxuICAgKlxuICAgKiBUaGUgcHJlZml4IHR5cGluZyBmZWF0dXJlIGhhcyBhIG9uZSBzZWNvbmQgdGltZW91dCDigJTCoHRoZSBwcmVmaXggdG8gbWF0Y2hcbiAgICogd2lsbCBiZSByZXNldCBhZnRlciBhIHNlY29uZCBoYXMgcGFzc2VkIHNpbmNlIHRoZSB1c2VyIGxhc3QgdHlwZWQgYSBrZXkuXG4gICAqIElmLCBpbiB0aGUgYWJvdmUgZXhhbXBsZSwgdGhlIHVzZXIgd2FpdHMgYSBzZWNvbmQgYmV0d2VlbiB0eXBpbmcgXCJiXCIgYW5kXG4gICAqIFwibFwiLCB0aGUgcHJlZml4IHdpbGwgYmVjb21lIFwibFwiLCBzbyBcIkxlbW9uXCIgd291bGQgYmUgc2VsZWN0ZWQuXG4gICAqXG4gICAqIFRoaXMgbWl4aW4gZXhwZWN0cyB0aGUgY29tcG9uZW50IHRvIGludm9rZSBhIGBrZXlkb3duYCBtZXRob2Qgd2hlbiBhIGtleSBpc1xuICAgKiBwcmVzc2VkLiBZb3UgY2FuIHVzZSBbS2V5Ym9hcmRNaXhpbl0oS2V5Ym9hcmRNaXhpbi5tZCkgZm9yIHRoYXRcbiAgICogcHVycG9zZSwgb3Igd2lyZSB1cCB5b3VyIG93biBrZXlib2FyZCBoYW5kbGluZyBhbmQgY2FsbCBga2V5ZG93bmAgeW91cnNlbGYuXG4gICAqXG4gICAqIFRoaXMgbWl4aW4gYWxzbyBleHBlY3RzIHRoZSBjb21wb25lbnQgdG8gcHJvdmlkZSBhbiBgaXRlbXNgIHByb3BlcnR5LiBUaGVcbiAgICogYHRleHRDb250ZW50YCBvZiB0aG9zZSBpdGVtcyB3aWxsIGJlIHVzZWQgZm9yIHB1cnBvc2VzIG9mIHByZWZpeCBtYXRjaGluZy5cbiAgICovXG4gIGNsYXNzIEtleWJvYXJkUHJlZml4U2VsZWN0aW9uIGV4dGVuZHMgYmFzZSB7XG5cbiAgICAvLyBUT0RPOiBJZiB0aGUgc2V0IG9mIGl0ZW1zIGlzIGNoYW5nZWQsIHJlc2V0IHRoZSBwcmVmaXguXG4gICAgLy8gW3N5bWJvbHMuaXRlbXNDaGFuZ2VkXSgpIHtcbiAgICAvLyAgIHRoaXNbaXRlbVRleHRDb250ZW50c1N5bWJvbF0gPSBudWxsO1xuICAgIC8vICAgcmVzZXRUeXBlZFByZWZpeCh0aGlzKTtcbiAgICAvLyB9XG5cbiAgICAvLyBUT0RPOiBJZiB0aGUgc2VsZWN0aW9uIGlzIGNoYW5nZWQgYnkgc29tZSBvdGhlciBtZWFucyAoZS5nLiwgYXJyb3cga2V5cylcbiAgICAvLyBvdGhlciB0aGFuIHByZWZpeCB0eXBpbmcsIHRoZW4gdGhhdCBhY3Qgc2hvdWxkIHJlc2V0IHRoZSBwcmVmaXguXG5cbiAgICBbc3ltYm9scy5rZXlkb3duXShldmVudCkge1xuICAgICAgbGV0IGhhbmRsZWQ7XG4gICAgICBsZXQgcmVzZXRQcmVmaXggPSB0cnVlO1xuXG4gICAgICBzd2l0Y2ggKGV2ZW50LmtleUNvZGUpIHtcbiAgICAgICAgY2FzZSA4OiAvLyBCYWNrc3BhY2VcbiAgICAgICAgICBoYW5kbGVCYWNrc3BhY2UodGhpcyk7XG4gICAgICAgICAgaGFuZGxlZCA9IHRydWU7XG4gICAgICAgICAgcmVzZXRQcmVmaXggPSBmYWxzZTtcbiAgICAgICAgICBicmVhaztcbiAgICAgICAgY2FzZSAyNzogLy8gRXNjYXBlXG4gICAgICAgICAgaGFuZGxlZCA9IHRydWU7XG4gICAgICAgICAgYnJlYWs7XG4gICAgICAgIGRlZmF1bHQ6XG4gICAgICAgICAgaWYgKCFldmVudC5jdHJsS2V5ICYmICFldmVudC5tZXRhS2V5ICYmICFldmVudC5hbHRLZXkgJiZcbiAgICAgICAgICAgICAgZXZlbnQud2hpY2ggIT09IDMyIC8qIFNwYWNlICovKSB7XG4gICAgICAgICAgICBoYW5kbGVQbGFpbkNoYXJhY3Rlcih0aGlzLCBTdHJpbmcuZnJvbUNoYXJDb2RlKGV2ZW50LndoaWNoKSk7XG4gICAgICAgICAgfVxuICAgICAgICAgIHJlc2V0UHJlZml4ID0gZmFsc2U7XG4gICAgICB9XG5cbiAgICAgIGlmIChyZXNldFByZWZpeCkge1xuICAgICAgICByZXNldFR5cGVkUHJlZml4KHRoaXMpO1xuICAgICAgfVxuXG4gICAgICAvLyBQcmVmZXIgbWl4aW4gcmVzdWx0IGlmIGl0J3MgZGVmaW5lZCwgb3RoZXJ3aXNlIHVzZSBiYXNlIHJlc3VsdC5cbiAgICAgIHJldHVybiBoYW5kbGVkIHx8IChzdXBlcltzeW1ib2xzLmtleWRvd25dICYmIHN1cGVyW3N5bWJvbHMua2V5ZG93bl0oZXZlbnQpKTtcbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBTZWxlY3QgdGhlIGZpcnN0IGl0ZW0gd2hvc2UgdGV4dCBjb250ZW50IGJlZ2lucyB3aXRoIHRoZSBnaXZlbiBwcmVmaXguXG4gICAgICpcbiAgICAgKiBAcGFyYW0gcHJlZml4IFtTdHJpbmddIFRoZSBwcmVmaXggc3RyaW5nIHRvIHNlYXJjaCBmb3JcbiAgICAgKi9cbiAgICBzZWxlY3RJdGVtV2l0aFRleHRQcmVmaXgocHJlZml4KSB7XG4gICAgICBpZiAoc3VwZXIuc2VsZWN0SXRlbVdpdGhUZXh0UHJlZml4KSB7IHN1cGVyLnNlbGVjdEl0ZW1XaXRoVGV4dFByZWZpeChwcmVmaXgpOyB9XG4gICAgICBpZiAocHJlZml4ID09IG51bGwgfHwgcHJlZml4Lmxlbmd0aCA9PT0gMCkge1xuICAgICAgICByZXR1cm47XG4gICAgICB9XG4gICAgICBjb25zdCBpbmRleCA9IGdldEluZGV4T2ZJdGVtV2l0aFRleHRQcmVmaXgodGhpcywgcHJlZml4KTtcbiAgICAgIGlmIChpbmRleCA+PSAwKSB7XG4gICAgICAgIHRoaXMuc2VsZWN0ZWRJbmRleCA9IGluZGV4O1xuICAgICAgfVxuICAgIH1cblxuICB9XG5cbiAgcmV0dXJuIEtleWJvYXJkUHJlZml4U2VsZWN0aW9uO1xufTtcblxuXG4vLyBUaW1lIGluIG1pbGxpc2Vjb25kcyBhZnRlciB3aGljaCB0aGUgdXNlciBpcyBjb25zaWRlcmVkIHRvIGhhdmUgc3RvcHBlZFxuLy8gdHlwaW5nLlxuY29uc3QgUFJFRklYX1RJTUVPVVRfRFVSQVRJT04gPSAxMDAwO1xuXG5cbi8vIFJldHVybiB0aGUgaW5kZXggb2YgdGhlIGZpcnN0IGl0ZW0gd2l0aCB0aGUgZ2l2ZW4gcHJlZml4LCBlbHNlIC0xLlxuZnVuY3Rpb24gZ2V0SW5kZXhPZkl0ZW1XaXRoVGV4dFByZWZpeChlbGVtZW50LCBwcmVmaXgpIHtcbiAgY29uc3QgaXRlbVRleHRDb250ZW50cyA9IGdldEl0ZW1UZXh0Q29udGVudHMoZWxlbWVudCk7XG4gIGNvbnN0IHByZWZpeExlbmd0aCA9IHByZWZpeC5sZW5ndGg7XG4gIGZvciAobGV0IGkgPSAwOyBpIDwgaXRlbVRleHRDb250ZW50cy5sZW5ndGg7IGkrKykge1xuICAgIGNvbnN0IGl0ZW1UZXh0Q29udGVudCA9IGl0ZW1UZXh0Q29udGVudHNbaV07XG4gICAgaWYgKGl0ZW1UZXh0Q29udGVudC5zdWJzdHIoMCwgcHJlZml4TGVuZ3RoKSA9PT0gcHJlZml4KSB7XG4gICAgICByZXR1cm4gaTtcbiAgICB9XG4gIH1cbiAgcmV0dXJuIC0xO1xufVxuXG4vLyBSZXR1cm4gYW4gYXJyYXkgb2YgdGhlIHRleHQgY29udGVudCAoaW4gbG93ZXJjYXNlKSBvZiBhbGwgaXRlbXMuXG4vLyBDYWNoZSB0aGVzZSByZXN1bHRzLlxuZnVuY3Rpb24gZ2V0SXRlbVRleHRDb250ZW50cyhlbGVtZW50KSB7XG4gIGlmICghZWxlbWVudFtpdGVtVGV4dENvbnRlbnRzU3ltYm9sXSkge1xuICAgIGNvbnN0IGl0ZW1zID0gZWxlbWVudC5pdGVtcztcbiAgICBlbGVtZW50W2l0ZW1UZXh0Q29udGVudHNTeW1ib2xdID0gaXRlbXMubWFwKGNoaWxkID0+IHtcbiAgICAgIGNvbnN0IHRleHQgPSBjaGlsZC50ZXh0Q29udGVudCB8fCBjaGlsZC5hbHQ7XG4gICAgICByZXR1cm4gdGV4dC50b0xvd2VyQ2FzZSgpO1xuICAgIH0pO1xuICB9XG4gIHJldHVybiBlbGVtZW50W2l0ZW1UZXh0Q29udGVudHNTeW1ib2xdO1xufVxuXG5mdW5jdGlvbiBoYW5kbGVCYWNrc3BhY2UoZWxlbWVudCkge1xuICBjb25zdCBsZW5ndGggPSBlbGVtZW50W3R5cGVkUHJlZml4U3ltYm9sXSA/IGVsZW1lbnRbdHlwZWRQcmVmaXhTeW1ib2xdLmxlbmd0aCA6IDA7XG4gIGlmIChsZW5ndGggPiAwKSB7XG4gICAgZWxlbWVudFt0eXBlZFByZWZpeFN5bWJvbF0gPSBlbGVtZW50W3R5cGVkUHJlZml4U3ltYm9sXS5zdWJzdHIoMCwgbGVuZ3RoIC0gMSk7XG4gIH1cbiAgZWxlbWVudC5zZWxlY3RJdGVtV2l0aFRleHRQcmVmaXgoZWxlbWVudFt0eXBlZFByZWZpeFN5bWJvbF0pO1xuICBzZXRQcmVmaXhUaW1lb3V0KGVsZW1lbnQpO1xufVxuXG5mdW5jdGlvbiBoYW5kbGVQbGFpbkNoYXJhY3RlcihlbGVtZW50LCBjaGFyKSB7XG4gIGNvbnN0IHByZWZpeCA9IGVsZW1lbnRbdHlwZWRQcmVmaXhTeW1ib2xdIHx8ICcnO1xuICBlbGVtZW50W3R5cGVkUHJlZml4U3ltYm9sXSA9IHByZWZpeCArIGNoYXIudG9Mb3dlckNhc2UoKTtcbiAgZWxlbWVudC5zZWxlY3RJdGVtV2l0aFRleHRQcmVmaXgoZWxlbWVudFt0eXBlZFByZWZpeFN5bWJvbF0pO1xuICBzZXRQcmVmaXhUaW1lb3V0KGVsZW1lbnQpO1xufVxuXG5mdW5jdGlvbiByZXNldFByZWZpeFRpbWVvdXQoZWxlbWVudCkge1xuICBpZiAoZWxlbWVudFtwcmVmaXhUaW1lb3V0U3ltYm9sXSkge1xuICAgIGNsZWFyVGltZW91dChlbGVtZW50W3ByZWZpeFRpbWVvdXRTeW1ib2xdKTtcbiAgICBlbGVtZW50W3ByZWZpeFRpbWVvdXRTeW1ib2xdID0gZmFsc2U7XG4gIH1cbn1cblxuZnVuY3Rpb24gcmVzZXRUeXBlZFByZWZpeChlbGVtZW50KSB7XG4gIGVsZW1lbnRbdHlwZWRQcmVmaXhTeW1ib2xdID0gJyc7XG4gIHJlc2V0UHJlZml4VGltZW91dChlbGVtZW50KTtcbn1cblxuZnVuY3Rpb24gc2V0UHJlZml4VGltZW91dChlbGVtZW50KSB7XG4gIHJlc2V0UHJlZml4VGltZW91dChlbGVtZW50KTtcbiAgZWxlbWVudFtwcmVmaXhUaW1lb3V0U3ltYm9sXSA9IHNldFRpbWVvdXQoKCkgPT4ge1xuICAgIHJlc2V0VHlwZWRQcmVmaXgoZWxlbWVudCk7XG4gIH0sIFBSRUZJWF9USU1FT1VUX0RVUkFUSU9OKTtcbn1cbiIsImltcG9ydCByZW5kZXJBcnJheUFzRWxlbWVudHMgZnJvbSAnLi4vLi4vYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvcmVuZGVyQXJyYXlBc0VsZW1lbnRzJztcbmltcG9ydCBzeW1ib2xzIGZyb20gJy4uLy4uL2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL3N5bWJvbHMnO1xuaW1wb3J0IHRvZ2dsZUNsYXNzIGZyb20gJy4uLy4uL2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL3RvZ2dsZUNsYXNzJztcblxuXG4vKiBFeHBvcnRlZCBmdW5jdGlvbiBleHRlbmRzIGEgYmFzZSBjbGFzcyB3aXRoIFBhZ2VEb3RzLiAqL1xuZXhwb3J0IGRlZmF1bHQgKGJhc2UpID0+IHtcblxuICAvKipcbiAgICogVGVtcGxhdGUgbWl4aW4gd2hpY2ggYWRkcyBzbWFsbCBkb3RzIHRvIHNob3cgdGhlIG51bWJlciBvZiBpdGVtcyBhbmQgbGV0XG4gICAqIHRoZSB1c2VyIHNlbGVjdCBhIHNwZWNpZmljIGl0ZW0uXG4gICAqXG4gICAqIFlvdSBjYW4gc2VlIGFcbiAgICogW2xpdmUgZGVtb10oaHR0cDovL2Jhc2ljd2ViY29tcG9uZW50cy5vcmcvYmFzaWMtd2ViLWNvbXBvbmVudHMvcGFja2FnZXMvZGVtb3MvY2Fyb3VzZWwtd2l0aC1kb3RzLmh0bWwpXG4gICAqIG9mIHRoaXMgbWl4aW4gYXBwbGllZCB0byBhIGNhcm91c2VsLlxuICAgKlxuICAgKiBUaGVyZSB3aWxsIGJlIG9uZSBkb3QgZm9yIGVhY2ggaXRlbSwgYW5kIHRoZSBkb3QgZm9yIHRoZSBjdXJyZW50bHkgc2VsZWN0ZWRcbiAgICogaXRlbSB3aWxsIGJlIHNob3duIHNlbGVjdGVkLlxuICAgKlxuICAgKiBUeXBpY2FsIHVzYWdlOlxuICAgKlxuICAgKiAgICAgY2xhc3MgQ2Fyb3VzZWxXaXRoRG90cyBleHRlbmRzIFBhZ2VEb3RzTWl4aW4oQ2Fyb3VzZWwpIHt9XG4gICAqICAgICBjdXN0b21FbGVtZW50cy5kZWZpbmUoJ2Nhcm91c2VsLXdpdGgtZG90cycsIENhcm91c2VsV2l0aERvdHMpO1xuICAgKlxuICAgKiBBbHRob3VnaCB0aGUgZG90cyBhcmUgcXVpdGUgc21hbGwgYnkgZGVmYXVsdCwgY2xpY2tpbmcvdGFwcGluZyBhIGRvdCB3aWxsXG4gICAqIHdpbGwgc2VsZWN0IHRoZSBjb3JyZXNwb25kaW5nIGxpc3QgaXRlbS5cbiAgICovXG4gIGNsYXNzIFBhZ2VEb3RzIGV4dGVuZHMgYmFzZSB7XG5cbiAgICBjb25zdHJ1Y3RvcigpIHtcbiAgICAgIHN1cGVyKCk7XG5cbiAgICAgIHRoaXMuJC5kb3RzLmFkZEV2ZW50TGlzdGVuZXIoJ2NsaWNrJywgZXZlbnQgPT4ge1xuICAgICAgICBjb25zdCBkb3QgPSBldmVudC50YXJnZXQ7XG4gICAgICAgIGNvbnN0IGRvdEluZGV4ID0gdGhpcy5kb3RzLmluZGV4T2YoZG90KTtcbiAgICAgICAgaWYgKGRvdEluZGV4ID49IDApIHtcbiAgICAgICAgICB0aGlzLnNlbGVjdGVkSW5kZXggPSBkb3RJbmRleDtcbiAgICAgICAgfVxuICAgICAgfSk7XG4gICAgfVxuXG4gICAgZ2V0IGRvdHMoKSB7XG4gICAgICByZXR1cm4gW10uc2xpY2UuY2FsbCh0aGlzLiQuZG90cy5xdWVyeVNlbGVjdG9yQWxsKCcuZG90JykpO1xuICAgIH1cblxuICAgIFtzeW1ib2xzLml0ZW1zQ2hhbmdlZF0oKSB7XG4gICAgICBpZiAoc3VwZXJbc3ltYm9scy5pdGVtc0NoYW5nZWRdKSB7IHN1cGVyW3N5bWJvbHMuaXRlbXNDaGFuZ2VkXSgpOyB9XG4gICAgICByZW5kZXJBcnJheUFzRWxlbWVudHModGhpcy5pdGVtcywgdGhpcy4kLmRvdHMsIChpdGVtLCBlbGVtZW50KSA9PiB7XG4gICAgICAgIC8vIFdlIGRvbid0IHVzZSB0aGUgaXRlbSBwYXJhbWV0ZXIsIGJlY2F1c2UgYW55IGl0ZW0gd2lsbCBwcm9kdWNlIGFuXG4gICAgICAgIC8vIGlkZW50aWNhbCBjb3JyZXNwb25kaW5nIGRvdC5cbiAgICAgICAgaWYgKCFlbGVtZW50KSB7XG4gICAgICAgICAgZWxlbWVudCA9IGRvY3VtZW50LmNyZWF0ZUVsZW1lbnQoJ2RpdicpO1xuICAgICAgICAgIGVsZW1lbnQuY2xhc3NMaXN0LmFkZCgnZG90Jyk7XG4gICAgICAgICAgZWxlbWVudC5jbGFzc0xpc3QuYWRkKCdzdHlsZS1zY29wZScpO1xuICAgICAgICAgIGVsZW1lbnQuY2xhc3NMaXN0LmFkZCgnYmFzaWMtcGFnZS1kb3RzJyk7XG4gICAgICAgICAgZWxlbWVudC5zZXRBdHRyaWJ1dGUoJ3JvbGUnLCAnbm9uZScpO1xuICAgICAgICAgIHJldHVybiBlbGVtZW50O1xuICAgICAgICB9XG4gICAgICB9KTtcbiAgICAgIHJlZnJlc2hEb3RzKHRoaXMpO1xuICAgIH1cblxuICAgIFtzeW1ib2xzLml0ZW1TZWxlY3RlZF0oaXRlbSwgc2VsZWN0ZWQpIHtcbiAgICAgIGlmIChzdXBlcltzeW1ib2xzLml0ZW1TZWxlY3RlZF0pIHsgc3VwZXJbc3ltYm9scy5pdGVtU2VsZWN0ZWRdKGl0ZW0sIHNlbGVjdGVkKTsgfVxuICAgICAgY29uc3QgaW5kZXggPSB0aGlzLml0ZW1zLmluZGV4T2YoaXRlbSk7XG4gICAgICAvLyBTZWUgaWYgdGhlIGNvcnJlc3BvbmRpbmcgZG90IGhhcyBhbHJlYWR5IGJlZW4gY3JlYXRlZC5cbiAgICAgIC8vIElmIG5vdCwgdGhlIGNvcnJlY3QgZG90IHdpbGwgYmUgc2VsZWN0ZWQgd2hlbiBpdCBnZXRzIGNyZWF0ZWQuXG4gICAgICBjb25zdCBkb3RzID0gdGhpcy5kb3RzO1xuICAgICAgaWYgKGRvdHMgJiYgZG90cy5sZW5ndGggPiBpbmRleCkge1xuICAgICAgICBjb25zdCBkb3QgPSB0aGlzLmRvdHNbaW5kZXhdO1xuICAgICAgICBpZiAoZG90KSB7XG4gICAgICAgICAgdG9nZ2xlQ2xhc3MoZG90LCAnc2VsZWN0ZWQnLCBzZWxlY3RlZCk7XG4gICAgICAgIH1cbiAgICAgIH1cbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBUaGUgZGlzdGFuY2UgdGhlIHVzZXIgaGFzIG1vdmVkIHRoZSBmaXJzdCB0b3VjaHBvaW50IHNpbmNlIHRoZSBiZWdpbm5pbmdcbiAgICAgKiBvZiBhIGRyYWcsIGV4cHJlc3NlZCBhcyBhIGZyYWN0aW9uIG9mIHRoZSBlbGVtZW50J3Mgd2lkdGguXG4gICAgICpcbiAgICAgKiBAdHlwZSBudW1iZXJcbiAgICAgKi9cbiAgICBnZXQgc2VsZWN0ZWRGcmFjdGlvbigpIHtcbiAgICAgIHJldHVybiBzdXBlci5zZWxlY3RlZEZyYWN0aW9uO1xuICAgIH1cbiAgICBzZXQgc2VsZWN0ZWRGcmFjdGlvbih2YWx1ZSkge1xuICAgICAgaWYgKCdzZWxlY3RlZEZyYWN0aW9uJyBpbiBiYXNlLnByb3RvdHlwZSkgeyBzdXBlci5zZWxlY3RlZEZyYWN0aW9uID0gdmFsdWU7IH1cbiAgICAgIHJlbmRlclRyYW5zaXRpb24odGhpcywgdGhpcy5zZWxlY3RlZEluZGV4LCB2YWx1ZSk7XG4gICAgfVxuXG4gICAgZ2V0IHNlbGVjdGVkSW5kZXgoKSB7XG4gICAgICByZXR1cm4gc3VwZXIuc2VsZWN0ZWRJbmRleDtcbiAgICB9XG4gICAgc2V0IHNlbGVjdGVkSW5kZXgoaW5kZXgpIHtcbiAgICAgIGlmICgnc2VsZWN0ZWRJbmRleCcgaW4gYmFzZS5wcm90b3R5cGUpIHsgc3VwZXIuc2VsZWN0ZWRJbmRleCA9IGluZGV4OyB9XG4gICAgICByZWZyZXNoRG90cyh0aGlzKTtcbiAgICB9XG5cbiAgICBnZXQgW3N5bWJvbHMudGVtcGxhdGVdKCkge1xuICAgICAgY29uc3QgYmFzZVRlbXBsYXRlID0gc3VwZXJbc3ltYm9scy50ZW1wbGF0ZV0gfHwgJyc7XG4gICAgICByZXR1cm4gYFxuICAgICAgICA8c3R5bGU+XG4gICAgICAgIDpob3N0IHtcbiAgICAgICAgICBkaXNwbGF5OiAtd2Via2l0LWZsZXg7XG4gICAgICAgICAgZGlzcGxheTogZmxleDtcbiAgICAgICAgICBwb3NpdGlvbjogcmVsYXRpdmU7XG4gICAgICAgIH1cblxuICAgICAgICAjZG90cyB7XG4gICAgICAgICAgYm90dG9tOiAwO1xuICAgICAgICAgIGRpc3BsYXk6IC13ZWJraXQtZmxleDtcbiAgICAgICAgICBkaXNwbGF5OiBmbGV4O1xuICAgICAgICAgIC13ZWJraXQtanVzdGlmeS1jb250ZW50OiBjZW50ZXI7XG4gICAgICAgICAganVzdGlmeS1jb250ZW50OiBjZW50ZXI7XG4gICAgICAgICAgcG9zaXRpb246IGFic29sdXRlO1xuICAgICAgICAgIHdpZHRoOiAxMDAlO1xuICAgICAgICAgIHotaW5kZXg6IDE7XG4gICAgICAgIH1cblxuICAgICAgICAjZG90TmF2aWdhdGlvbkNvbnRhaW5lciB7XG4gICAgICAgICAgZGlzcGxheTogLXdlYmtpdC1mbGV4O1xuICAgICAgICAgIGRpc3BsYXk6IGZsZXg7XG4gICAgICAgICAgLXdlYmtpdC1mbGV4OiAxO1xuICAgICAgICAgIGZsZXg6IDE7XG4gICAgICAgICAgcG9zaXRpb246IHJlbGF0aXZlO1xuICAgICAgICAgIHotaW5kZXg6IDA7XG4gICAgICAgIH1cblxuICAgICAgICAjY29udGFpbmVyIDo6c2xvdHRlZCgqKSB7XG4gICAgICAgICAgLXdlYmtpdC1mbGV4OiAxO1xuICAgICAgICAgIGZsZXg6IDE7XG4gICAgICAgIH1cblxuICAgICAgICAuZG90IHtcbiAgICAgICAgICBiYWNrZ3JvdW5kOiByZ2IoMjU1LCAyNTUsIDI1NSk7XG4gICAgICAgICAgYm9yZGVyLXJhZGl1czogN3B4O1xuICAgICAgICAgIGJveC1zaGFkb3c6IDAgMCAxcHggMXB4IHJnYmEoMCwgMCwgMCwgMC41KTtcbiAgICAgICAgICBib3gtc2l6aW5nOiBib3JkZXItYm94O1xuICAgICAgICAgIGN1cnNvcjogcG9pbnRlcjtcbiAgICAgICAgICBoZWlnaHQ6IDhweDtcbiAgICAgICAgICBtYXJnaW46IDdweCA1cHg7XG4gICAgICAgICAgb3BhY2l0eTogMC40O1xuICAgICAgICAgIHBhZGRpbmc6IDA7XG4gICAgICAgICAgdHJhbnNpdGlvbjogYmFja2dyb3VuZCAwLjJzIGJveC1zaGFkb3cgMC4ycztcbiAgICAgICAgICB3aWR0aDogOHB4O1xuICAgICAgICB9XG5cbiAgICAgICAgLmRvdDpob3ZlciB7XG4gICAgICAgICAgYmFja2dyb3VuZDogcmdiYSgwLCAwLCAwLCAwLjc1KTtcbiAgICAgICAgICBib3gtc2hhZG93OiAwIDAgMXB4IDNweCByZ2JhKDI1NSwgMjU1LCAyNTUsIDAuNSk7XG4gICAgICAgIH1cblxuICAgICAgICAuZG90LnNlbGVjdGVkIHtcbiAgICAgICAgICBvcGFjaXR5OiAwLjk1O1xuICAgICAgICB9XG5cbiAgICAgICAgQG1lZGlhIChtaW4td2lkdGg6IDc2OHB4KSB7XG4gICAgICAgICAgLmRvdCB7XG4gICAgICAgICAgICBoZWlnaHQ6IDEycHg7XG4gICAgICAgICAgICB3aWR0aDogMTJweDtcbiAgICAgICAgICB9XG4gICAgICAgIH1cbiAgICAgICAgPC9zdHlsZT5cblxuICAgICAgICA8ZGl2IGlkPVwiZG90c1wiIHJvbGU9XCJub25lXCI+PC9kaXY+XG4gICAgICAgIDxkaXYgaWQ9XCJkb3ROYXZpZ2F0aW9uQ29udGFpbmVyXCIgcm9sZT1cIm5vbmVcIj5cbiAgICAgICAgICAke2Jhc2VUZW1wbGF0ZX1cbiAgICAgICAgPC9kaXY+XG4gICAgICBgO1xuICAgIH1cblxuICB9XG5cbiAgcmV0dXJuIFBhZ2VEb3RzO1xufTtcblxuXG4vLyBSZXR1cm4gdGhlIGluZGV4LCBlbnN1cmluZyBpdCBzdGF5cyBiZXR3ZWVuIDAgYW5kIHRoZSBnaXZlbiBsZW5ndGguXG5mdW5jdGlvbiBrZWVwSW5kZXhXaXRoaW5Cb3VuZHMobGVuZ3RoLCBpbmRleCkge1xuICAvLyBIYW5kbGUgcG9zc2liaWxpdHkgb2YgbmVnYXRpdmUgbW9kLlxuICAvLyBTZWUgaHR0cDovL3N0YWNrb3ZlcmZsb3cuY29tL2EvMTg2MTgyNTAvNzY0NzJcbiAgcmV0dXJuICgoaW5kZXggJSBsZW5ndGgpICsgbGVuZ3RoKSAlIGxlbmd0aDtcbn1cblxuZnVuY3Rpb24gcmVuZGVyVHJhbnNpdGlvbihlbGVtZW50LCBzZWxlY3RlZEluZGV4LCBzZWxlY3RlZEZyYWN0aW9uKSB7XG4gIGNvbnN0IGRvdHMgPSBlbGVtZW50LmRvdHM7XG4gIGlmICghZG90cyB8fCBkb3RzLmxlbmd0aCA9PT0gMCkge1xuICAgIHJldHVybjtcbiAgfVxuICBjb25zdCBkb3RDb3VudCA9IGRvdHMubGVuZ3RoO1xuICBjb25zdCBvcGFjaXR5TWluaW11bSA9IDAuNDtcbiAgY29uc3Qgb3BhY2l0eU1heGltdW0gPSAwLjk1O1xuICBjb25zdCBvcGFjaXR5UmFuZ2UgPSBvcGFjaXR5TWF4aW11bSAtIG9wYWNpdHlNaW5pbXVtO1xuICBjb25zdCBmcmFjdGlvbmFsSW5kZXggPSBzZWxlY3RlZEluZGV4ICsgc2VsZWN0ZWRGcmFjdGlvbjtcbiAgY29uc3QgbGVmdEluZGV4ID0gTWF0aC5mbG9vcihmcmFjdGlvbmFsSW5kZXgpO1xuICBjb25zdCByaWdodEluZGV4ID0gTWF0aC5jZWlsKGZyYWN0aW9uYWxJbmRleCk7XG4gIGNvbnN0IHNlbGVjdGlvbldyYXBzID0gZWxlbWVudC5zZWxlY3Rpb25XcmFwcztcbiAgbGV0IGF3YXlJbmRleCA9IHNlbGVjdGVkRnJhY3Rpb24gPj0gMCA/IGxlZnRJbmRleCA6IHJpZ2h0SW5kZXg7XG4gIGxldCB0b3dhcmRJbmRleCA9IHNlbGVjdGVkRnJhY3Rpb24gPj0gMCA/IHJpZ2h0SW5kZXggOiBsZWZ0SW5kZXg7XG4gIGlmIChzZWxlY3Rpb25XcmFwcykge1xuICAgIGF3YXlJbmRleCA9IGtlZXBJbmRleFdpdGhpbkJvdW5kcyhkb3RDb3VudCwgYXdheUluZGV4KTtcbiAgICB0b3dhcmRJbmRleCA9IGtlZXBJbmRleFdpdGhpbkJvdW5kcyhkb3RDb3VudCwgdG93YXJkSW5kZXgpO1xuICB9XG4gIC8vIFN0dXBpZCBJRSBkb2Vzbid0IGhhdmUgTWF0aC50cnVuYy5cbiAgLy8gY29uc3QgdHJ1bmNhdGVkU2VsZWN0ZWRGcmFjdGlvbiA9IE1hdGgudHJ1bmMoc2VsZWN0ZWRGcmFjdGlvbik7XG4gIGNvbnN0IHRydW5jYXRlZFNlbGVjdGVkRnJhY3Rpb24gPSBzZWxlY3RlZEZyYWN0aW9uIDwgMCA/IE1hdGguY2VpbChzZWxlY3RlZEZyYWN0aW9uKSA6IE1hdGguZmxvb3Ioc2VsZWN0ZWRGcmFjdGlvbik7XG4gIGNvbnN0IHByb2dyZXNzID0gc2VsZWN0ZWRGcmFjdGlvbiAtIHRydW5jYXRlZFNlbGVjdGVkRnJhY3Rpb247XG4gIGNvbnN0IG9wYWNpdHlQcm9ncmVzc1Rocm91Z2hSYW5nZSA9IE1hdGguYWJzKHByb2dyZXNzKSAqIG9wYWNpdHlSYW5nZTtcbiAgZG90cy5mb3JFYWNoKChkb3QsIGluZGV4KSA9PiB7XG4gICAgbGV0IGRvdE9wYWNpdHk7XG4gICAgaWYgKHNlbGVjdGVkRnJhY3Rpb24gPT09IDApIHtcbiAgICAgIC8vIFJlbW92ZSBleHBsaWNpdCBvcGFjaXR5IGFuZCByZWx5IG9uIHN0eWxpbmcuXG4gICAgICBkb3RPcGFjaXR5ID0gJyc7XG4gICAgfSBlbHNlIGlmIChpbmRleCA9PT0gYXdheUluZGV4KSB7XG4gICAgICBkb3RPcGFjaXR5ID0gb3BhY2l0eU1heGltdW0gLSBvcGFjaXR5UHJvZ3Jlc3NUaHJvdWdoUmFuZ2U7XG4gICAgfSBlbHNlIGlmIChpbmRleCA9PT0gdG93YXJkSW5kZXgpIHtcbiAgICAgIGRvdE9wYWNpdHkgPSBvcGFjaXR5TWluaW11bSArIG9wYWNpdHlQcm9ncmVzc1Rocm91Z2hSYW5nZTtcbiAgICB9IGVsc2Uge1xuICAgICAgZG90T3BhY2l0eSA9IG9wYWNpdHlNaW5pbXVtO1xuICAgIH1cbiAgICBkb3Quc3R5bGUub3BhY2l0eSA9IGRvdE9wYWNpdHk7XG4gIH0pO1xufVxuXG5mdW5jdGlvbiByZWZyZXNoRG90cyhlbGVtZW50KSB7XG4gIGNvbnN0IHNlbGVjdGVkSW5kZXggPSBlbGVtZW50LnNlbGVjdGVkSW5kZXg7XG4gIGVsZW1lbnQuZG90cy5mb3JFYWNoKChkb3QsIGkpID0+IHtcbiAgICB0b2dnbGVDbGFzcyhkb3QsICdzZWxlY3RlZCcsIGkgPT09IHNlbGVjdGVkSW5kZXgpO1xuICB9KTtcbn1cbiIsImltcG9ydCBzYWZlQXR0cmlidXRlcyBmcm9tICcuLi8uLi9iYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy9zYWZlQXR0cmlidXRlcyc7XG5pbXBvcnQgc3ltYm9scyBmcm9tICcuLi8uLi9iYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy9zeW1ib2xzJztcblxuXG4vKiBFeHBvcnRlZCBmdW5jdGlvbiBleHRlbmRzIGEgYmFzZSBjbGFzcyB3aXRoIFBsYXlDb250cm9scy4gKi9cbmV4cG9ydCBkZWZhdWx0IChiYXNlKSA9PiB7XG5cbiAgLyoqXG4gICAqIFRlbXBsYXRlIG1peGluIHdoaWNoIGFkZHMgYnV0dG9ucyBmb3IgbWFuYWdpbmcgcGxheWJhY2sgb2YgYSBzbGlkZXNob3csXG4gICAqIGF1ZGlvIHBsYXlsaXN0LCBldGMuXG4gICAqXG4gICAqIFR5cGljYWwgdXNhZ2U6XG4gICAqXG4gICAqICAgICBjbGFzcyBTbGlkZXNob3dXaXRoQ29udHJvbHMgZXh0ZW5kcyBQbGF5Q29udHJvbHNNaXhpbihTbGlkZXNob3cpIHt9XG4gICAqICAgICBjdXN0b21FbGVtZW50cy5kZWZpbmUoJ3NsaWRlc2hvdy13aXRoLWNvbnRyb2xzJywgU2xpZGVzaG93V2l0aENvbnRyb2xzKTtcbiAgICpcbiAgICovXG4gIGNsYXNzIFBsYXlDb250cm9scyBleHRlbmRzIGJhc2Uge1xuXG4gICAgY29uc3RydWN0b3IoKSB7XG4gICAgICBzdXBlcigpO1xuICAgICAgdGhpcy4kLnByZXZpb3VzQnV0dG9uLmFkZEV2ZW50TGlzdGVuZXIoJ2NsaWNrJywgZXZlbnQgPT4ge1xuICAgICAgICB0aGlzLnNlbGVjdFByZXZpb3VzKCk7XG4gICAgICB9KTtcbiAgICAgIHRoaXMuJC5wbGF5QnV0dG9uLmFkZEV2ZW50TGlzdGVuZXIoJ2NsaWNrJywgZXZlbnQgPT4ge1xuICAgICAgICB0aGlzLnBsYXlpbmcgPSAhdGhpcy5wbGF5aW5nO1xuICAgICAgfSk7XG4gICAgICB0aGlzLiQubmV4dEJ1dHRvbi5hZGRFdmVudExpc3RlbmVyKCdjbGljaycsIGV2ZW50ID0+IHtcbiAgICAgICAgdGhpcy5zZWxlY3ROZXh0KCk7XG4gICAgICB9KTtcbiAgICB9XG5cbiAgICBjb25uZWN0ZWRDYWxsYmFjaygpIHtcbiAgICAgIGlmIChzdXBlci5jb25uZWN0ZWRDYWxsYmFjaykgeyBzdXBlci5jb25uZWN0ZWRDYWxsYmFjaygpOyB9XG4gICAgICBzYWZlQXR0cmlidXRlcy5jb25uZWN0ZWQodGhpcyk7XG4gICAgfVxuXG4gICAgW3N5bWJvbHMua2V5ZG93bl0oZXZlbnQpIHtcbiAgICAgIGxldCBoYW5kbGVkO1xuXG4gICAgICBzd2l0Y2ggKGV2ZW50LmtleUNvZGUpIHtcbiAgICAgICAgY2FzZSAzMjogLyogU3BhY2UgKi9cbiAgICAgICAgICB0aGlzLnBsYXlpbmcgPSAhdGhpcy5wbGF5aW5nO1xuICAgICAgICAgIGhhbmRsZWQgPSB0cnVlO1xuICAgICAgICAgIGJyZWFrO1xuICAgICAgfVxuXG4gICAgICAvLyBQcmVmZXIgbWl4aW4gcmVzdWx0IGlmIGl0J3MgZGVmaW5lZCwgb3RoZXJ3aXNlIHVzZSBiYXNlIHJlc3VsdC5cbiAgICAgIHJldHVybiBoYW5kbGVkIHx8IChzdXBlcltzeW1ib2xzLmtleWRvd25dICYmIHN1cGVyW3N5bWJvbHMua2V5ZG93bl0oZXZlbnQpKTtcbiAgICB9XG5cbiAgICBnZXQgcGxheWluZygpIHtcbiAgICAgIHJldHVybiBzdXBlci5wbGF5aW5nO1xuICAgIH1cbiAgICBzZXQgcGxheWluZyh2YWx1ZSkge1xuICAgICAgaWYgKCdwbGF5aW5nJyBpbiBiYXNlLnByb3RvdHlwZSkgeyBzdXBlci5wbGF5aW5nID0gdmFsdWU7IH1cbiAgICAgIHNhZmVBdHRyaWJ1dGVzLnRvZ2dsZUNsYXNzKHRoaXMsICdwbGF5aW5nJywgdmFsdWUpO1xuICAgIH1cblxuICAgIGdldCBbc3ltYm9scy50ZW1wbGF0ZV0oKSB7XG4gICAgICBjb25zdCBiYXNlVGVtcGxhdGUgPSBzdXBlcltzeW1ib2xzLnRlbXBsYXRlXSB8fCAnJztcbiAgICAgIHJldHVybiBgXG4gICAgICAgIDxzdHlsZT5cbiAgICAgICAgOmhvc3Qge1xuICAgICAgICAgIGRpc3BsYXk6IC13ZWJraXQtZmxleDtcbiAgICAgICAgICBkaXNwbGF5OiBmbGV4O1xuICAgICAgICAgIHBvc2l0aW9uOiByZWxhdGl2ZTtcbiAgICAgICAgfVxuXG4gICAgICAgICNidXR0b25zIHtcbiAgICAgICAgICBib3R0b206IDA7XG4gICAgICAgICAgYm94LXNpemluZzogYm9yZGVyLWJveDtcbiAgICAgICAgICBwYWRkaW5nOiAwLjVlbTtcbiAgICAgICAgICBwb3NpdGlvbjogYWJzb2x1dGU7XG4gICAgICAgICAgdGV4dC1hbGlnbjogY2VudGVyO1xuICAgICAgICAgIHdpZHRoOiAxMDAlO1xuICAgICAgICAgIHotaW5kZXg6IDE7XG4gICAgICAgIH1cblxuICAgICAgICBidXR0b24ge1xuICAgICAgICAgIGJhY2tncm91bmQ6IHRyYW5zcGFyZW50O1xuICAgICAgICAgIGJvcmRlcjogbm9uZTtcbiAgICAgICAgICBmaWxsOiByZ2JhKDI1NSwgMjU1LCAyNTUsIDAuNSk7XG4gICAgICAgICAgcGFkZGluZzogMDtcbiAgICAgICAgICB0cmFuc2l0aW9uOiBmaWxsIDAuNXM7XG4gICAgICAgICAgdmVydGljYWwtYWxpZ246IG1pZGRsZTtcbiAgICAgICAgfVxuICAgICAgICA6aG9zdCg6aG92ZXIpIGJ1dHRvbiB7XG4gICAgICAgICAgZmlsbDogcmdiYSgyNTUsIDI1NSwgMjU1LCAwLjcpO1xuICAgICAgICB9XG4gICAgICAgIGJ1dHRvbjpob3ZlciB7XG4gICAgICAgICAgZmlsbDogcmdiYSgyNTUsIDI1NSwgMjU1LCAwLjg1KTtcbiAgICAgICAgfVxuICAgICAgICBidXR0b246YWN0aXZlIHtcbiAgICAgICAgICBmaWxsOiB3aGl0ZTtcbiAgICAgICAgfVxuXG4gICAgICAgIC5pY29uIHtcbiAgICAgICAgICBoZWlnaHQ6IDMwcHg7XG4gICAgICAgICAgd2lkdGg6IDMwcHg7XG4gICAgICAgIH1cbiAgICAgICAgI3BsYXlCdXR0b24gLmljb24ge1xuICAgICAgICAgIGhlaWdodDogNDBweDtcbiAgICAgICAgICB3aWR0aDogNDBweDtcbiAgICAgICAgfVxuXG4gICAgICAgIDpob3N0KC5wbGF5aW5nKSAucGF1c2VkQ29udHJvbCB7XG4gICAgICAgICAgZGlzcGxheTogbm9uZTtcbiAgICAgICAgfVxuICAgICAgICA6aG9zdCg6bm90KC5wbGF5aW5nKSkgLnBsYXlpbmdDb250cm9sIHtcbiAgICAgICAgICBkaXNwbGF5OiBub25lO1xuICAgICAgICB9XG5cbiAgICAgICAgI2NvbnRhaW5lciB7XG4gICAgICAgICAgZGlzcGxheTogLXdlYmtpdC1mbGV4O1xuICAgICAgICAgIGRpc3BsYXk6IGZsZXg7XG4gICAgICAgICAgLXdlYmtpdC1mbGV4OiAxO1xuICAgICAgICAgIGZsZXg6IDE7XG4gICAgICAgIH1cblxuICAgICAgICAjY29udGFpbmVyIDo6c2xvdHRlZCgqKSB7XG4gICAgICAgICAgLXdlYmtpdC1mbGV4OiAxO1xuICAgICAgICAgIGZsZXg6IDE7XG4gICAgICAgIH1cbiAgICAgICAgPC9zdHlsZT5cblxuICAgICAgICA8ZGl2IGlkPVwiYnV0dG9uc1wiPlxuICAgICAgICAgIDxidXR0b24gaWQ9XCJwcmV2aW91c0J1dHRvblwiPlxuICAgICAgICAgICAgPHN2ZyBjbGFzcz1cImljb25cIiB2aWV3Qm94PVwiMCAwIDI0IDI0XCIgcHJlc2VydmVBc3BlY3RSYXRpbz1cInhNaWRZTWlkIG1lZXRcIj5cbiAgICAgICAgICAgICAgPGcgaWQ9XCJza2lwLXByZXZpb3VzXCI+XG4gICAgICAgICAgICAgICAgPHBhdGggZD1cIk02IDZoMnYxMkg2em0zLjUgNmw4LjUgNlY2elwiLz5cbiAgICAgICAgICAgICAgPC9nPlxuICAgICAgICAgICAgPC9zdmc+XG4gICAgICAgICAgPC9idXR0b24+XG4gICAgICAgICAgPGJ1dHRvbiBpZD1cInBsYXlCdXR0b25cIj5cbiAgICAgICAgICAgIDxzdmcgY2xhc3M9XCJpY29uIHBsYXlpbmdDb250cm9sXCIgdmlld0JveD1cIjAgMCAyNCAyNFwiIHByZXNlcnZlQXNwZWN0UmF0aW89XCJ4TWlkWU1pZCBtZWV0XCI+XG4gICAgICAgICAgICAgIDxnIGlkPVwicGF1c2UtY2lyY2xlLW91dGxpbmVcIj5cbiAgICAgICAgICAgICAgICA8cGF0aCBkPVwiTTkgMTZoMlY4SDl2OHptMy0xNEM2LjQ4IDIgMiA2LjQ4IDIgMTJzNC40OCAxMCAxMCAxMCAxMC00LjQ4IDEwLTEwUzE3LjUyIDIgMTIgMnptMCAxOGMtNC40MSAwLTgtMy41OS04LThzMy41OS04IDgtOCA4IDMuNTkgOCA4LTMuNTkgOC04IDh6bTEtNGgyVjhoLTJ2OHpcIj48L3BhdGg+XG4gICAgICAgICAgICAgIDwvZz5cbiAgICAgICAgICAgIDwvc3ZnPlxuICAgICAgICAgICAgPHN2ZyBjbGFzcz1cImljb24gcGF1c2VkQ29udHJvbFwiIHZpZXdCb3g9XCIwIDAgMjQgMjRcIiBwcmVzZXJ2ZUFzcGVjdFJhdGlvPVwieE1pZFlNaWQgbWVldFwiPlxuICAgICAgICAgICAgICA8ZyBpZD1cInBsYXktY2lyY2xlLW91dGxpbmVcIj5cbiAgICAgICAgICAgICAgICA8cGF0aCBkPVwiTTEwIDE2LjVsNi00LjUtNi00LjV2OXpNMTIgMkM2LjQ4IDIgMiA2LjQ4IDIgMTJzNC40OCAxMCAxMCAxMCAxMC00LjQ4IDEwLTEwUzE3LjUyIDIgMTIgMnptMCAxOGMtNC40MSAwLTgtMy41OS04LThzMy41OS04IDgtOCA4IDMuNTkgOCA4LTMuNTkgOC04IDh6XCI+PC9wYXRoPlxuICAgICAgICAgICAgICA8L2c+XG4gICAgICAgICAgICA8L3N2Zz5cbiAgICAgICAgICA8L2J1dHRvbj5cbiAgICAgICAgICA8YnV0dG9uIGlkPVwibmV4dEJ1dHRvblwiPlxuICAgICAgICAgICAgPHN2ZyBjbGFzcz1cImljb25cIiB2aWV3Qm94PVwiMCAwIDI0IDI0XCIgcHJlc2VydmVBc3BlY3RSYXRpbz1cInhNaWRZTWlkIG1lZXRcIj5cbiAgICAgICAgICAgICAgPGcgaWQ9XCJza2lwLW5leHRcIj5cbiAgICAgICAgICAgICAgICA8cGF0aCBkPVwiTTYgMThsOC41LTZMNiA2djEyek0xNiA2djEyaDJWNmgtMnpcIi8+XG4gICAgICAgICAgICAgIDwvZz5cbiAgICAgICAgICAgIDwvc3ZnPlxuICAgICAgICAgIDwvYnV0dG9uPlxuICAgICAgICA8L2Rpdj5cblxuICAgICAgICA8ZGl2IGlkPVwiY29udGFpbmVyXCIgcm9sZT1cIm5vbmVcIj5cbiAgICAgICAgICAke2Jhc2VUZW1wbGF0ZX1cbiAgICAgICAgPC9kaXY+XG4gICAgICBgO1xuICAgIH1cblxuICB9XG5cbiAgcmV0dXJuIFBsYXlDb250cm9scztcbn07XG4iLCJpbXBvcnQgY3JlYXRlU3ltYm9sIGZyb20gJy4vY3JlYXRlU3ltYm9sJztcbmltcG9ydCBGcmFjdGlvbmFsU2VsZWN0aW9uTWl4aW4gZnJvbSAnLi9GcmFjdGlvbmFsU2VsZWN0aW9uTWl4aW4nO1xuaW1wb3J0IHN5bWJvbHMgZnJvbSAnLi9zeW1ib2xzJztcblxuXG4vLyBTeW1ib2xzIGZvciBwcml2YXRlIGRhdGEgbWVtYmVycyBvbiBhbiBlbGVtZW50LlxuY29uc3QgYW5pbWF0aW9uU3ltYm9sID0gY3JlYXRlU3ltYm9sKCdhbmltYXRpb24nKTtcbmNvbnN0IGRyYWdnaW5nU3ltYm9sID0gY3JlYXRlU3ltYm9sKCdkcmFnZ2luZycpO1xuY29uc3QgbGFzdEFuaW1hdGlvblN5bWJvbCA9IGNyZWF0ZVN5bWJvbCgnbGFzdEFuaW1hdGlvbicpO1xuY29uc3QgcGxheWluZ0FuaW1hdGlvblN5bWJvbCA9IGNyZWF0ZVN5bWJvbCgnYW5pbWF0aW5nU2VsZWN0aW9uJyk7XG5jb25zdCBwcmV2aW91c1NlbGVjdGlvblN5bWJvbCA9IGNyZWF0ZVN5bWJvbCgncHJldmlvdXNTZWxlY3Rpb24nKTtcbmNvbnN0IHNlbGVjdGlvbkFuaW1hdGlvbkR1cmF0aW9uU3ltYm9sID0gY3JlYXRlU3ltYm9sKCdzZWxlY3Rpb25BbmltYXRpb25EdXJhdGlvbicpO1xuY29uc3Qgc2VsZWN0aW9uQW5pbWF0aW9uRWZmZWN0U3ltYm9sID0gY3JlYXRlU3ltYm9sKCdzZWxlY3Rpb25BbmltYXRpb25FZmZlY3QnKTtcbmNvbnN0IHNlbGVjdGlvbkFuaW1hdGlvbktleWZyYW1lc1N5bWJvbCA9IGNyZWF0ZVN5bWJvbCgnc2VsZWN0aW9uQW5pbWF0aW9uS2V5ZnJhbWVzJyk7XG5jb25zdCByZXNldEFuaW1hdGlvbnNPbk5leHRSZW5kZXJTeW1ib2wgPSBjcmVhdGVTeW1ib2woJ3Jlc2V0QW5pbWF0aW9uc09uTmV4dFJlbmRlcicpO1xuXG5cbi8qIEV4cG9ydGVkIGZ1bmN0aW9uIGV4dGVuZHMgYSBiYXNlIGNsYXNzIHdpdGggU2VsZWN0aW9uQW5pbWF0aW9uLiAqL1xuZXhwb3J0IGRlZmF1bHQgZnVuY3Rpb24gbWl4aW4oYmFzZSkge1xuXG4gIC8qKlxuICAgKiBNaXhpbiB3aGljaCB1c2VzIGFuaW1hdGlvbiB0byBzaG93IHRyYW5zaXRpb25zIGJldHdlZW4gc2VsZWN0aW9uIHN0YXRlcy5cbiAgICpcbiAgICogVGhpcyBtaXhpbiBjYW4gYmUgdXNlZCBieSBjb21wb25lbnRzIHRoYXQgd2FudCB0byBwcm92aWRlIHZpc2libGVcbiAgICogYW5pbWF0aW9ucyB3aGVuIGNoYW5naW5nIHRoZSBzZWxlY3Rpb24uIEZvciBleGFtcGxlLCBhIGNhcm91c2VsIGNvbXBvbmVudFxuICAgKiBtYXkgd2FudCB0byBkZWZpbmUgYSBzbGlkaW5nIGFuaW1hdGlvbiBlZmZlY3Qgc2hvd24gd2hlbiBtb3ZpbmcgYmV0d2VlblxuICAgKiBpdGVtcy5cbiAgICpcbiAgICogVGhlIGFuaW1hdGlvbiBpcyBkZWZpbmVkIGJ5IGEgYHNlbGVjdGlvbkFuaW1hdGlvbktleWZyYW1lc2AgcHJvcGVydHk7IHNlZVxuICAgKiB0aGF0IHByb3BlcnR5IGZvciBkZXRhaWxzIG9uIGhvdyB0byBkZWZpbmUgdGhlc2Uga2V5ZnJhbWVzLiBUaGlzIGFuaW1hdGlvblxuICAgKiB3aWxsIGJlIHVzZWQgaW4gdHdvIHdheXMuIEZpcnN0LCB3aGVuIG1vdmluZyBzdHJpY3RseSBiZXR3ZWVuIGl0ZW1zLCB0aGVcbiAgICogYW5pbWF0aW9uIHdpbGwgcGxheSBzbW9vdGhseSB0byBzaG93IHRoZSBzZWxlY3Rpb24gY2hhbmdpbmcuIFNlY29uZCwgdGhlXG4gICAqIGFuaW1hdGlvbiBjYW4gYmUgdXNlZCB0byByZW5kZXIgdGhlIHNlbGVjdGlvbiBhdCBhIGZpeGVkIHBvaW50IGluIHRoZVxuICAgKiB0cmFuc2l0aW9uIGJldHdlZW4gc3RhdGVzLiBFLmcuLCBpZiB0aGUgdXNlciBwYXVzZXMgaGFsZndheSB0aHJvdWdoXG4gICAqIGRyYWdnaW5nIGFuIGVsZW1lbnQgdXNpbmcgW1N3aXBlRGlyZWN0aW9uTWl4aW5dKFN3aXBlRGlyZWN0aW9uTWl4aW4ubWQpXG4gICAqIG9yIFtUcmFja3BhZERpcmVjdGlvbk1peGluXShUcmFja3BhZERpcmVjdGlvbk1peGluLm1kKXMsIHRoZW4gdGhlIHNlbGVjdGlvblxuICAgKiBhbmltYXRpb24gd2lsbCBiZSBzaG93biBhdCB0aGUgcG9pbnQgZXhhY3RseSBoYWxmd2F5IHRocm91Z2guXG4gICAqXG4gICAqIFRoaXMgbWl4aW4gZXhwZWN0cyBhIGNvbXBvbmVudCB0byBwcm92aWRlIGFuIGBpdGVtc2AgYXJyYXkgb2YgYWxsIGVsZW1lbnRzXG4gICAqIGluIHRoZSBsaXN0LCB3aGljaCBjYW4gYmUgcHJvdmlkZWQgdmlhXG4gICAqIFtDb250ZW50SXRlbXNNaXhpbl0oQ29udGVudEl0ZW1zTWl4aW4ubWQpLiBUaGlzIG1peGluIGFsc28gZXhwZWN0c1xuICAgKiBgc2VsZWN0ZWRJbmRleGAgYW5kIGBzZWxlY3RlZEl0ZW1gIHByb3BlcnRpZXMsIHdoaWNoIGNhbiBiZSBwcm92aWRlZCB2aWFcbiAgICogW1NpbmdsZVNlbGVjdGlvbk1peGluXShTaW5nbGVTZWxlY3Rpb25NaXhpbi5tZCkuXG4gICAqXG4gICAqIFRoaXMgbWl4aW4gc3VwcG9ydHMgYSBgc2VsZWN0aW9uV3JhcHNgIHByb3BlcnR5LiBXaGVuIHRydWUsIHRoZSB1c2VyIGNhblxuICAgKiBuYXZpZ2F0ZSBmb3J3YXJkIGZyb20gdGhlIGxhc3QgaXRlbSBpbiB0aGUgbGlzdCBhbmQgd3JhcCBhcm91bmQgdG8gdGhlXG4gICAqIGZpcnN0IGl0ZW0sIG9yIG5hdmlnYXRlIGJhY2t3YXJkIGZyb20gdGhlIGZpcnN0IGl0ZW0gYW5kIHdyYXAgYXJvdW5kIHRvIHRoZVxuICAgKiBsYXN0IGl0ZW0uXG4gICAqXG4gICAqIFRoaXMgbWl4aW4gdXNlcyB0aGUgV2ViIEFuaW1hdGlvbnMgQVBJLiBGb3IgdXNlIG9uIGJyb3dzZXJzIHdoaWNoXG4gICAqIGRvIG5vdCBzdXBwb3J0IHRoYXQgQVBJIG5hdGl2ZWx5LCB5b3Ugd2lsbCBuZWVkIHRvIGxvYWQgdGhlXG4gICAqIFtXZWIgQW5pbWF0aW9ucyBwb2x5ZmlsbF0oaHR0cHM6Ly9naXRodWIuY29tL3dlYi1hbmltYXRpb25zL3dlYi1hbmltYXRpb25zLWpzKS5cbiAgICovXG4gIGNsYXNzIFNlbGVjdGlvbkFuaW1hdGlvbiBleHRlbmRzIGJhc2Uge1xuXG4gICAgY29uc3RydWN0b3IoKSB7XG4gICAgICBzdXBlcigpO1xuXG4gICAgICAvLyBTZXQgZGVmYXVsdHMuXG4gICAgICBpZiAodHlwZW9mIHRoaXMuc2VsZWN0aW9uQW5pbWF0aW9uRHVyYXRpb24gPT09ICd1bmRlZmluZWQnKSB7XG4gICAgICAgIHRoaXMuc2VsZWN0aW9uQW5pbWF0aW9uRHVyYXRpb24gPSB0aGlzW3N5bWJvbHMuZGVmYXVsdHNdLnNlbGVjdGlvbkFuaW1hdGlvbkR1cmF0aW9uO1xuICAgICAgfVxuICAgICAgaWYgKHR5cGVvZiB0aGlzLnNlbGVjdGlvbkFuaW1hdGlvbkVmZmVjdCA9PT0gJ3VuZGVmaW5lZCcgJiYgdGhpcy5zZWxlY3Rpb25BbmltYXRpb25LZXlmcmFtZXMgPT0gbnVsbCkge1xuICAgICAgICB0aGlzLnNlbGVjdGlvbkFuaW1hdGlvbkVmZmVjdCA9IHRoaXNbc3ltYm9scy5kZWZhdWx0c10uc2VsZWN0aW9uQW5pbWF0aW9uRWZmZWN0O1xuICAgICAgfVxuXG4gICAgICB0aGlzW3N5bWJvbHMuZHJhZ2dpbmddID0gZmFsc2U7XG4gICAgfVxuXG4gICAgZ2V0IFtzeW1ib2xzLmRlZmF1bHRzXSgpIHtcbiAgICAgIGNvbnN0IGRlZmF1bHRzID0gc3VwZXJbc3ltYm9scy5kZWZhdWx0c10gfHwge307XG4gICAgICBkZWZhdWx0cy5zZWxlY3Rpb25BbmltYXRpb25EdXJhdGlvbiA9IDI1MDtcbiAgICAgIGRlZmF1bHRzLnNlbGVjdGlvbkFuaW1hdGlvbkVmZmVjdCA9ICdzbGlkZSc7XG4gICAgICByZXR1cm4gZGVmYXVsdHM7XG4gICAgfVxuXG4gICAgLypcbiAgICAgKiBQcm92aWRlIGJhY2tpbmcgZm9yIHRoZSBkcmFnZ2luZyBwcm9wZXJ0eS5cbiAgICAgKiBBbHNvLCB3aGVuIGEgZHJhZyBiZWdpbnMsIHJlc2V0IHRoZSBhbmltYXRpb25zLlxuICAgICAqL1xuICAgIGdldCBbc3ltYm9scy5kcmFnZ2luZ10oKSB7XG4gICAgICByZXR1cm4gdGhpc1tkcmFnZ2luZ1N5bWJvbF07XG4gICAgfVxuICAgIHNldCBbc3ltYm9scy5kcmFnZ2luZ10odmFsdWUpIHtcbiAgICAgIGNvbnN0IHByZXZpb3VzVmFsdWUgPSB0aGlzW3N5bWJvbHMuZHJhZ2dpbmddO1xuICAgICAgdGhpc1tkcmFnZ2luZ1N5bWJvbF0gPSB2YWx1ZTtcbiAgICAgIGlmIChzeW1ib2xzLmRyYWdnaW5nIGluIGJhc2UucHJvdG90eXBlKSB7IHN1cGVyW3N5bWJvbHMuZHJhZ2dpbmddID0gdmFsdWU7IH1cbiAgICAgIGlmICh2YWx1ZSAmJiAhcHJldmlvdXNWYWx1ZSkge1xuICAgICAgICAvLyBIYXZlIGJlZ3VuIGEgZHJhZy5cbiAgICAgICAgdGhpc1tyZXNldEFuaW1hdGlvbnNPbk5leHRSZW5kZXJTeW1ib2xdID0gdHJ1ZTtcbiAgICAgIH1cbiAgICB9XG5cbiAgICBbc3ltYm9scy5pdGVtQWRkZWRdKGl0ZW0pIHtcbiAgICAgIC8vIFdlIG1hcmsgbmV3IGl0ZW1zIGluIHRoZSBsaXN0IGFzIGV4cGxpY2l0bHkgdmlzaWJsZSB0byBBUklBLiBPdGhlcndpc2UsXG4gICAgICAvLyB3aGVuIGFuIGl0ZW0gaXNuJ3QgdmlzaWJsZSBvbiB0aGUgc2NyZWVuLCBBUklBIHdpbGwgYXNzdW1lIHRoZSBpdGVtIGlzXG4gICAgICAvLyBvZiBubyBpbnRlcmVzdCB0byB0aGUgdXNlciwgYW5kIGxlYXZlIGl0IG91dCBvZiB0aGUgYWNjZXNzaWJpbGl0eSB0cmVlLlxuICAgICAgLy8gSWYgdGhlIGxpc3QgY29udGFpbnMgMTAgaXRlbXMsIGJ1dCBvbmx5IDMgYXJlIHZpc2libGUsIGEgc2NyZWVuIHJlYWRlclxuICAgICAgLy8gbWlnaHQgdGhlbiBhbm5vdW5jZSB0aGUgbGlzdCBvbmx5IGhhcyAzIGl0ZW1zLiBUbyBlbnN1cmUgdGhhdCBzY3JlZW5cbiAgICAgIC8vIHJlYWRlcnMgYW5kIG90aGVyIGFzc2lzdGl2ZSB0ZWNobm9sb2dpZXMgYW5ub3VuY2UgdGhlIGNvcnJlY3QgdG90YWxcbiAgICAgIC8vIG51bWJlciBvZiBpdGVtcywgd2UgZXhwbGljaXRseSBtYXJrIGFsbCBpdGVtcyBhcyBub3QgaGlkZGVuLiBUaGlzIHdpbGxcbiAgICAgIC8vIGV4cG9zZSB0aGVtIGFsbCBpbiB0aGUgYWNjZXNzaWJpbGl0eSB0cmVlLCBldmVuIHRoZSBpdGVtcyB3aGljaCBhcmVcbiAgICAgIC8vIGN1cnJlbnRseSBub3QgcmVuZGVyZWQuXG4gICAgICAvL1xuICAgICAgLy8gVE9ETzogR2VuZXJhbGx5IHNwZWFraW5nLCB0aGlzIGVudGlyZSBtaXhpbiBhc3N1bWVzIHRoYXQgdGhlIHVzZXIgY2FuXG4gICAgICAvLyBuYXZpZ2F0ZSB0aHJvdWdoIGFsbCBpdGVtcyBpbiBhIGxpc3QuIEJ1dCBhbiBhcHAgY291bGQgc3R5bGUgYW4gaXRlbSBhc1xuICAgICAgLy8gZGlzcGxheTpub25lIG9yIHZpc2liaWxpdHk6aGlkZGVuIGJlY2F1c2UgdGhlIHVzZXIgaXMgbm90IGFsbG93ZWQgdG9cbiAgICAgIC8vIGludGVyYWN0IHdpdGggdGhhdCBpdGVtIGF0IHRoZSBtb21lbnQuIFN1cHBvcnQgZm9yIHRoaXMgc2NlbmFyaW8gc2hvdWxkXG4gICAgICAvLyBiZSBhZGRlZC4gVGhpcyB3b3VsZCBlbnRhaWwgY2hhbmdpbmcgYWxsIGxvY2F0aW9ucyB3aGVyZSBhIG1peGluXG4gICAgICAvLyBmdW5jdGlvbiBpcyBjb3VudGluZyBpdGVtcywgaXRlcmF0aW5nIG92ZXIgdGhlICh2aXNpYmxlKSBpdGVtcywgYW5kXG4gICAgICAvLyBzaG93aW5nIG9yIGhpZGluZyBpdGVtcy4gQW1vbmcgb3RoZXIgdGhpbmdzLCB0aGUgY29kZSBiZWxvdyB0byBtYWtlXG4gICAgICAvLyBpdGVtcyB2aXNpYmxlIHRvIEFSSUEgd291bGQgbmVlZCB0byBkaXNjcmltaW5hdGUgYmV0d2VlbiBpdGVtcyB3aGljaFxuICAgICAgLy8gYXJlIGludmlzaWJsZSBiZWNhdXNlIG9mIGFuaW1hdGlvbiBzdGF0ZSwgb3IgaW52aXNpYmxlIGJlY2F1c2UgdGhlIHVzZXJcbiAgICAgIC8vIHNob3VsZG4ndCBpbnRlcmFjdCB3aXRoIHRoZW0uXG4gICAgICBpdGVtLnNldEF0dHJpYnV0ZSgnYXJpYS1oaWRkZW4nLCBmYWxzZSk7XG4gICAgfVxuXG4gICAgW3N5bWJvbHMuaXRlbXNDaGFuZ2VkXSgpIHtcbiAgICAgIGlmIChzdXBlcltzeW1ib2xzLml0ZW1zQ2hhbmdlZF0pIHsgc3VwZXJbc3ltYm9scy5pdGVtc0NoYW5nZWRdKCk7IH1cblxuICAgICAgcmVzZXRBbmltYXRpb25zKHRoaXMpO1xuXG4gICAgICAvLyBUT0RPOiBBbHNvIHJlc2V0IG91ciBub3Rpb24gb2YgdGhlIGxhc3QgcmVuZGVyZWQgc2VsZWN0aW9uPyBUaGlzIGNvbWVzXG4gICAgICAvLyB1cCB3aGVuIGEgRE9NIHJlbW92YWwgY2F1c2VzIHRoZSBzZWxlY3RlZCBpdGVtIHRvIGNoYW5nZSBwb3NpdGlvbi5cbiAgICAgIC8vIHRoaXNbcHJldmlvdXNTZWxlY3Rpb25TeW1ib2xdID0gbnVsbDtcblxuICAgICAgcmVuZGVyU2VsZWN0aW9uKHRoaXMpO1xuICAgIH1cblxuICAgIHJlc2V0QW5pbWF0aW9ucygpIHtcbiAgICAgIHJlc2V0QW5pbWF0aW9ucyh0aGlzKTtcbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBBIGZyYWN0aW9uYWwgdmFsdWUgaW5kaWNhdGluZyBob3cgZmFyIHRoZSB1c2VyIGhhcyBjdXJyZW50bHkgYWR2YW5jZWQgdG9cbiAgICAgKiB0aGUgbmV4dC9wcmV2aW91cyBpdGVtLiBFLmcuLCBhIGBzZWxlY3RlZEZyYWN0aW9uYCBvZiAzLjUgaW5kaWNhdGVzIHRoZVxuICAgICAqIHVzZXIgaXMgaGFsZndheSBiZXR3ZWVuIGl0ZW1zIDMgYW5kIDQuXG4gICAgICpcbiAgICAgKiBGb3IgbW9yZSBkZXRhaWxzLCBzZWUgW0ZyYWN0aW9uYWxTZWxlY3Rpb25NaXhpbl0oRnJhY3Rpb25hbFNlbGVjdGlvbk1peGluLm1kKVxuICAgICAqIG1peGluLlxuICAgICAqXG4gICAgICogQHR5cGUge251bWJlcn1cbiAgICAgKi9cbiAgICBnZXQgc2VsZWN0ZWRGcmFjdGlvbigpIHtcbiAgICAgIHJldHVybiBzdXBlci5zZWxlY3RlZEZyYWN0aW9uIHx8IDA7XG4gICAgfVxuICAgIHNldCBzZWxlY3RlZEZyYWN0aW9uKHZhbHVlKSB7XG4gICAgICBpZiAoJ3NlbGVjdGVkRnJhY3Rpb24nIGluIGJhc2UucHJvdG90eXBlKSB7IHN1cGVyLnNlbGVjdGVkRnJhY3Rpb24gPSB2YWx1ZTsgfVxuICAgICAgcmVuZGVyU2VsZWN0aW9uKHRoaXMsIHRoaXMuc2VsZWN0ZWRJbmRleCwgdmFsdWUpO1xuICAgIH1cblxuICAgIGdldCBzZWxlY3RlZEluZGV4KCkge1xuICAgICAgcmV0dXJuIHN1cGVyLnNlbGVjdGVkSW5kZXg7XG4gICAgfVxuICAgIHNldCBzZWxlY3RlZEluZGV4KGluZGV4KSB7XG4gICAgICBpZiAoJ3NlbGVjdGVkSW5kZXgnIGluIGJhc2UucHJvdG90eXBlKSB7IHN1cGVyLnNlbGVjdGVkSW5kZXggPSBpbmRleDsgfVxuICAgICAgcmVuZGVyU2VsZWN0aW9uKHRoaXMsIGluZGV4LCAwKTtcbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBUaGUgZHVyYXRpb24gb2YgYSBzZWxlY3Rpb24gYW5pbWF0aW9uIGluIG1pbGxpc2Vjb25kcy5cbiAgICAgKlxuICAgICAqIFRoaXMgbWVhc3VyZXMgdGhlIGFtb3VudCBvZiB0aW1lIHJlcXVpcmVkIGZvciBhIHNlbGVjdGlvbiBhbmltYXRpb24gdG9cbiAgICAgKiBjb21wbGV0ZS4gVGhpcyBudW1iZXIgcmVtYWlucyBjb25zdGFudCwgZXZlbiBpZiB0aGUgbnVtYmVyIG9mIGl0ZW1zIGJlaW5nXG4gICAgICogYW5pbWF0ZWQgaW5jcmVhc2VzLlxuICAgICAqXG4gICAgICogVGhlIGRlZmF1bHQgdmFsdWUgaXMgMjUwIG1pbGxpc2Vjb25kcyAoYSBxdWFydGVyIGEgc2Vjb25kKS5cbiAgICAgKlxuICAgICAqIEB0eXBlIHtudW1iZXJ9XG4gICAgICogQGRlZmF1bHQgMjUwXG4gICAgICovXG4gICAgZ2V0IHNlbGVjdGlvbkFuaW1hdGlvbkR1cmF0aW9uKCkge1xuICAgICAgcmV0dXJuIHRoaXNbc2VsZWN0aW9uQW5pbWF0aW9uRHVyYXRpb25TeW1ib2xdO1xuICAgIH1cbiAgICBzZXQgc2VsZWN0aW9uQW5pbWF0aW9uRHVyYXRpb24odmFsdWUpIHtcbiAgICAgIHRoaXNbc2VsZWN0aW9uQW5pbWF0aW9uRHVyYXRpb25TeW1ib2xdID0gdmFsdWU7XG4gICAgICBpZiAoJ3NlbGVjdGlvbkFuaW1hdGlvbkR1cmF0aW9uJyBpbiBiYXNlLnByb3RvdHlwZSkgeyBzdXBlci5zZWxlY3Rpb25BbmltYXRpb25EdXJhdGlvbiA9IHZhbHVlOyB9XG4gICAgfVxuXG4gICAgLyoqXG4gICAgICogVGhlIG5hbWUgb2YgYSBzdGFuZGFyZCBzZWxlY3Rpb24gYW5pbWF0aW9uIGVmZmVjdC5cbiAgICAgKlxuICAgICAqIFRoaXMgaXMgYSBzaG9ydGhhbmQgZm9yIHNldHRpbmcgdGhlIGBzZWxlY3Rpb25BbmltYXRpb25LZXlmcmFtZXNgXG4gICAgICogcHJvcGVydHkgdG8gc3RhbmRhcmQga2V5ZnJhbWVzLiBTdXBwb3J0ZWQgc3RyaW5nIHZhbHVlczpcbiAgICAgKlxuICAgICAqICogXCJjcm9zc2ZhZGVcIlxuICAgICAqICogXCJyZXZlYWxcIlxuICAgICAqICogXCJyZXZlYWxXaXRoRmFkZVwiXG4gICAgICogKiBcInNob3dBZGphY2VudFwiXG4gICAgICogKiBcInNsaWRlXCJcbiAgICAgKiAqIFwic2xpZGVXaXRoR2FwXCJcbiAgICAgKlxuICAgICAqIEB0eXBlIHtzdHJpbmd9XG4gICAgICogQGRlZmF1bHQgXCJzbGlkZVwiXG4gICAgICovXG4gICAgZ2V0IHNlbGVjdGlvbkFuaW1hdGlvbkVmZmVjdCgpIHtcbiAgICAgIHJldHVybiB0aGlzW3NlbGVjdGlvbkFuaW1hdGlvbkVmZmVjdFN5bWJvbF07XG4gICAgfVxuICAgIHNldCBzZWxlY3Rpb25BbmltYXRpb25FZmZlY3QodmFsdWUpIHtcbiAgICAgIHRoaXNbc2VsZWN0aW9uQW5pbWF0aW9uRWZmZWN0U3ltYm9sXSA9IHZhbHVlO1xuICAgICAgaWYgKCdzZWxlY3Rpb25BbmltYXRpb25FZmZlY3QnIGluIGJhc2UucHJvdG90eXBlKSB7IHN1cGVyLnNlbGVjdGlvbkFuaW1hdGlvbkVmZmVjdCA9IHZhbHVlOyB9XG4gICAgICB0aGlzLnNlbGVjdGlvbkFuaW1hdGlvbktleWZyYW1lcyA9IG1peGluLnN0YW5kYXJkRWZmZWN0S2V5ZnJhbWVzW3ZhbHVlXTtcbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBUaGUga2V5ZnJhbWVzIHRoYXQgZGVmaW5lIGFuIGFuaW1hdGlvbiB0aGF0IHBsYXlzIGZvciBhbiBpdGVtIHdoZW4gbW92aW5nXG4gICAgICogZm9yd2FyZCBpbiB0aGUgc2VxdWVuY2UuXG4gICAgICpcbiAgICAgKiBUaGlzIGlzIGFuIGFycmF5IG9mIENTUyBydWxlcyB0aGF0IHdpbGwgYmUgYXBwbGllZC4gVGhlc2UgYXJlIHVzZWQgYXNcbiAgICAgKiBba2V5ZnJhbWVzXShodHRwOi8vdzNjLmdpdGh1Yi5pby93ZWItYW5pbWF0aW9ucy8ja2V5ZnJhbWVzLXNlY3Rpb24pXG4gICAgICogdG8gYW5pbWF0ZSB0aGUgaXRlbSB3aXRoIHRoZVxuICAgICAqIFtXZWIgQW5pbWF0aW9ucyBBUEldKGh0dHBzOi8vZGV2ZWxvcGVyLm1vemlsbGEub3JnL2VuLVVTL2RvY3MvV2ViL0FQSS9hbmltYXRpb24pLlxuICAgICAqXG4gICAgICogVGhlIGFuaW1hdGlvbiByZXByZXNlbnRzIHRoZSBzdGF0ZSBvZiB0aGUgbmV4dCBpdGVtIGFzIGl0IG1vdmVzIGZyb21cbiAgICAgKiBjb21wbGV0ZWx5IHVuc2VsZWN0ZWQgKG9mZnN0YWdlLCB1c3VhbGx5IHJpZ2h0KSwgdG8gc2VsZWN0ZWQgKGNlbnRlclxuICAgICAqIHN0YWdlKSwgdG8gY29tcGxldGVseSB1bnNlbGVjdGVkIChvZmZzdGFnZSwgdXN1YWxseSBsZWZ0KS4gVGhlIGNlbnRlciB0aW1lXG4gICAgICogb2YgdGhlIGFuaW1hdGlvbiBzaG91bGQgY29ycmVzcG9uZCB0byB0aGUgaXRlbSdzIHF1aXNjZW50IHNlbGVjdGVkIHN0YXRlLFxuICAgICAqIHR5cGljYWxseSBpbiB0aGUgY2VudGVyIG9mIHRoZSBzdGFnZSBhbmQgYXQgdGhlIGl0ZW0ncyBsYXJnZXN0IHNpemUuXG4gICAgICpcbiAgICAgKiBUaGUgZGVmYXVsdCBmb3J3YXJkIGFuaW1hdGlvbiBpcyBhIHNtb290aCBzbGlkZSBhdCBmdWxsIHNpemUgZnJvbSByaWdodCB0b1xuICAgICAqIGxlZnQuXG4gICAgICpcbiAgICAgKiBXaGVuIG1vdmluZyB0aGUgc2VsZWN0aW9uIGJhY2t3YXJkLCB0aGlzIGFuaW1hdGlvbiBpcyBwbGF5ZWQgaW4gcmV2ZXJzZS5cbiAgICAgKlxuICAgICAqIEB0eXBlIHtjc3NSdWxlc1tdfVxuICAgICAqL1xuICAgIGdldCBzZWxlY3Rpb25BbmltYXRpb25LZXlmcmFtZXMoKSB7XG4gICAgICAvLyBTdGFuZGFyZCBhbmltYXRpb24gc2xpZGVzIGxlZnQvcmlnaHQsIGtlZXBzIGFkamFjZW50IGl0ZW1zIG91dCBvZiB2aWV3LlxuICAgICAgcmV0dXJuIHRoaXNbc2VsZWN0aW9uQW5pbWF0aW9uS2V5ZnJhbWVzU3ltYm9sXTtcbiAgICB9XG4gICAgc2V0IHNlbGVjdGlvbkFuaW1hdGlvbktleWZyYW1lcyh2YWx1ZSkge1xuICAgICAgdGhpc1tzZWxlY3Rpb25BbmltYXRpb25LZXlmcmFtZXNTeW1ib2xdID0gdmFsdWU7XG4gICAgICBpZiAoJ3NlbGVjdGlvbkFuaW1hdGlvbktleWZyYW1lcycgaW4gYmFzZS5wcm90b3R5cGUpIHsgc3VwZXIuc2VsZWN0aW9uQW5pbWF0aW9uS2V5ZnJhbWVzID0gdmFsdWU7IH1cbiAgICAgIHJlc2V0QW5pbWF0aW9ucyh0aGlzKTtcbiAgICAgIHJlbmRlclNlbGVjdGlvbih0aGlzKTtcbiAgICB9XG5cbiAgICBnZXQgc2VsZWN0aW9uV3JhcHMoKSB7XG4gICAgICByZXR1cm4gc3VwZXIuc2VsZWN0aW9uV3JhcHM7XG4gICAgfVxuICAgIHNldCBzZWxlY3Rpb25XcmFwcyh2YWx1ZSkge1xuICAgICAgaWYgKCdzZWxlY3Rpb25XcmFwcycgaW4gYmFzZS5wcm90b3R5cGUpIHsgc3VwZXIuc2VsZWN0aW9uV3JhcHMgPSB2YWx1ZTsgfVxuICAgICAgcmVzZXRBbmltYXRpb25zKHRoaXMpO1xuICAgICAgcmVuZGVyU2VsZWN0aW9uKHRoaXMpO1xuICAgIH1cbiAgfVxuXG4gIHJldHVybiBTZWxlY3Rpb25BbmltYXRpb247XG59XG5cblxuLy8gV2UgZXhwb3NlIGhlbHBlcnMgb24gdGhlIG1peGluIGZ1bmN0aW9uIHRoYXQgd2Ugd2FudCB0byBiZSBhYmxlIHRvIHVuaXQgdGVzdC5cbi8vIFNpbmNlIHRoZXNlIGFyZSBvbiB0aGUgZnVuY3Rpb24sIG5vdCBvbiB0aGUgY2xhc3MgZW1pdHRlZCBieSB0aGUgZnVuY3Rpb24sXG4vLyB0aGV5IGRvbid0IGVuZCB1cCBnZXR0aW5nIGV4cG9zZWQgb24gYWN0dWFsIGVsZW1lbnQgaW5zdGFuY2VzLlxubWl4aW4uaGVscGVycyA9IHtcblxuICAvKlxuICAgKiBDYWxjdWxhdGUgdGhlIGFuaW1hdGlvbiBmcmFjdGlvbnMgZm9yIGFuIGVsZW1lbnQncyBpdGVtcyBhdCB0aGUgZ2l2ZW5cbiAgICogc2VsZWN0aW9uIHBvaW50LiBUaGlzIGlzIHVzZWQgd2hlbiByZW5kZXJpbmcgdGhlIGVsZW1lbnQncyBzZWxlY3Rpb24gc3RhdGVcbiAgICogaW5zdGFudGFuZW91c2x5LlxuICAgKlxuICAgKiBUaGlzIGZ1bmN0aW9uIGNvbnNpZGVycyB0aGUgc2VsZWN0ZWRJbmRleCBwYXJhbWV0ZXIsIHdoaWNoIGNhbiBiZSBhIHdob2xlXG4gICAqIG9yIGZyYWN0aW9uYWwgbnVtYmVyLCBhbmQgZGV0ZXJtaW5lcyB3aGljaCBpdGVtcyB3aWxsIGJlIHZpc2libGUgYXQgdGhhdFxuICAgKiBpbmRleC4gVGhpcyBmdW5jdGlvbiB0aGVuIGNhbGN1bGF0ZXMgYSBjb3JyZXNwb25kaW5nIGFuaW1hdGlvbiBmcmFjdGlvbjogYVxuICAgKiBudW1iZXIgYmV0d2VlbiAwIGFuZCAxIGluZGljYXRpbmcgaG93IGZhciB0aHJvdWdoIHRoZSBzZWxlY3Rpb24gYW5pbWF0aW9uXG4gICAqIGFuIGl0ZW0gc2hvdWxkIGJlIHNob3duLCBvciBudWxsIGlmIHRoZSBpdGVtIHNob3VsZCBub3QgYmUgdmlzaWJsZSBhdCB0aGF0XG4gICAqIHNlbGVjdGlvbiBpbmRleC4gVGhlc2UgZnJhY3Rpb25zIGFyZSByZXR1cm5lZCBhcyBhbiBhcnJheSwgd2hlcmUgdGhlXG4gICAqIGFuaW1hdGlvbiBmcmFjdGlvbiBhdCBwb3NpdGlvbiBOIGNvcnJlc3BvbmRzIHRvIGhvdyBpdGVtIE4gc2hvdWxkIGJlIHNob3duLlxuICAgKi9cbiAgYW5pbWF0aW9uRnJhY3Rpb25zRm9yU2VsZWN0aW9uKGVsZW1lbnQsIHNlbGVjdGlvbikge1xuXG4gICAgY29uc3QgaXRlbXMgPSBlbGVtZW50Lml0ZW1zO1xuICAgIGlmICghaXRlbXMpIHtcbiAgICAgIHJldHVybjtcbiAgICB9XG5cbiAgICBjb25zdCBpdGVtQ291bnQgPSBpdGVtcy5sZW5ndGg7XG4gICAgY29uc3Qgc2VsZWN0aW9uV3JhcHMgPSBlbGVtZW50LnNlbGVjdGlvbldyYXBzO1xuXG4gICAgcmV0dXJuIGl0ZW1zLm1hcCgoaXRlbSwgaXRlbUluZGV4KSA9PiB7XG4gICAgICAvLyBIb3cgbWFueSBzdGVwcyBmcm9tIHRoZSBzZWxlY3Rpb24gcG9pbnQgdG8gdGhpcyBpdGVtP1xuICAgICAgY29uc3Qgc3RlcHMgPSBzdGVwc1RvSW5kZXgoaXRlbUNvdW50LCBzZWxlY3Rpb25XcmFwcywgc2VsZWN0aW9uLCBpdGVtSW5kZXgpO1xuICAgICAgLy8gVG8gY29udmVydCBzdGVwcyB0byBhbmltYXRpb24gZnJhY3Rpb246XG4gICAgICAvLyBzdGVwcyAgICAgIGFuaW1hdGlvbiBmcmFjdGlvblxuICAgICAgLy8gIDEgICAgICAgICAwICAgICAoc3RhZ2UgcmlnaHQpXG4gICAgICAvLyAgMCAgICAgICAgIDAuNSAgIChjZW50ZXIgc3RhZ2UpXG4gICAgICAvLyAtMSAgICAgICAgIDEgICAgIChzdGFnZSBsZWZ0KVxuICAgICAgY29uc3QgYW5pbWF0aW9uRnJhY3Rpb24gPSAoMSAtIHN0ZXBzKSAvIDI7XG4gICAgICByZXR1cm4gKGFuaW1hdGlvbkZyYWN0aW9uID49IDAgJiYgYW5pbWF0aW9uRnJhY3Rpb24gPD0gMSkgP1xuICAgICAgICBhbmltYXRpb25GcmFjdGlvbiA6XG4gICAgICAgIG51bGw7IC8vIE91dHNpZGUgYW5pbWF0aW9uIHJhbmdlXG4gICAgfSk7XG4gIH0sXG5cbiAgLypcbiAgICogQ2FsY3VsYXRlIHRoZSBhbmltYXRpb24gdGltaW5ncyB0aGF0IHNob3VsZCBiZSB1c2VkIHRvIHNtb290aGx5IGFuaW1hdGUgdGhlXG4gICAqIGVsZW1lbnQncyBpdGVtcyBmcm9tIG9uZSBzZWxlY3Rpb24gc3RhdGUgdG8gYW5vdGhlci5cbiAgICpcbiAgICogVGhpcyByZXR1cm5zIGFuIGFycmF5IG9mIHRpbWluZ3MsIHdoZXJlIHRoZSB0aW1pbmcgYXQgcG9zaXRpb24gTiBzaG91bGQgYmVcbiAgICogdXNlZCB0byBhbmltYXRlIGl0ZW0gTi4gSWYgYW4gaXRlbSdzIHRpbWluZyBpcyBudWxsLCB0aGVuIHRoYXQgaXRlbSBzaG91bGRcbiAgICogbm90IHRha2UgcGxhY2UgaW4gdGhlIGFuaW1hdGlvbiwgYW5kIHNob3VsZCBiZSBoaWRkZW4gaW5zdGVhZC5cbiAgICovXG4gIGVmZmVjdFRpbWluZ3NGb3JTZWxlY3Rpb25BbmltYXRpb24oZWxlbWVudCwgZnJvbVNlbGVjdGlvbiwgdG9TZWxlY3Rpb24pIHtcblxuICAgIGNvbnN0IGl0ZW1zID0gZWxlbWVudC5pdGVtcztcbiAgICBpZiAoIWl0ZW1zKSB7XG4gICAgICByZXR1cm47XG4gICAgfVxuICAgIGNvbnN0IGl0ZW1Db3VudCA9IGl0ZW1zLmxlbmd0aDtcbiAgICBjb25zdCBzZWxlY3Rpb25XcmFwcyA9IGVsZW1lbnQuc2VsZWN0aW9uV3JhcHM7XG4gICAgY29uc3QgdG9JbmRleCA9IEZyYWN0aW9uYWxTZWxlY3Rpb25NaXhpbi5oZWxwZXJzLndyYXBwZWRTZWxlY3Rpb25QYXJ0cyh0b1NlbGVjdGlvbiwgaXRlbUNvdW50LCBzZWxlY3Rpb25XcmFwcykuaW5kZXg7XG4gICAgY29uc3QgdG90YWxTdGVwcyA9IHN0ZXBzVG9JbmRleChpdGVtQ291bnQsIHNlbGVjdGlvbldyYXBzLCBmcm9tU2VsZWN0aW9uLCB0b1NlbGVjdGlvbik7XG4gICAgY29uc3QgZGlyZWN0aW9uID0gdG90YWxTdGVwcyA+PSAwID8gJ25vcm1hbCc6ICdyZXZlcnNlJztcbiAgICBjb25zdCBmaWxsID0gJ2JvdGgnO1xuICAgIGNvbnN0IHRvdGFsRHVyYXRpb24gPSBlbGVtZW50LnNlbGVjdGlvbkFuaW1hdGlvbkR1cmF0aW9uO1xuICAgIGNvbnN0IHN0ZXBEdXJhdGlvbiA9IHRvdGFsU3RlcHMgIT09IDAgP1xuICAgICAgdG90YWxEdXJhdGlvbiAqIDIgLyBNYXRoLmNlaWwoTWF0aC5hYnModG90YWxTdGVwcykpIDpcbiAgICAgIDA7ICAvLyBObyBzdGVwcyByZXF1aXJlZCwgYW5pbWF0aW9uIHdpbGwgYmUgaW5zdGFudGVub3VzLlxuXG4gICAgY29uc3QgdGltaW5ncyA9IGl0ZW1zLm1hcCgoaXRlbSwgaXRlbUluZGV4KSA9PiB7XG4gICAgICBjb25zdCBzdGVwcyA9IHN0ZXBzVG9JbmRleChpdGVtQ291bnQsIHNlbGVjdGlvbldyYXBzLCBpdGVtSW5kZXgsIHRvU2VsZWN0aW9uKTtcbiAgICAgIC8vIElmIHdlIGluY2x1ZGUgdGhpcyBpdGVtIGluIHRoZSBzdGFnZ2VyZWQgc2VxdWVuY2Ugb2YgYW5pbWF0aW9ucyB3ZSdyZVxuICAgICAgLy8gY3JlYXRpbmcsIHdoZXJlIHdvdWxkIHRoZSBpdGVtIGFwcGVhciBpbiB0aGUgc2VxdWVuY2U/XG4gICAgICBsZXQgcG9zaXRpb25JblNlcXVlbmNlID0gdG90YWxTdGVwcyAtIHN0ZXBzO1xuICAgICAgaWYgKHRvdGFsU3RlcHMgPCAwKSB7XG4gICAgICAgIHBvc2l0aW9uSW5TZXF1ZW5jZSA9IC1wb3NpdGlvbkluU2VxdWVuY2U7XG4gICAgICB9XG4gICAgICAvLyBTbywgaXMgdGhpcyBpdGVtIHJlYWxseSBpbmNsdWRlZCBpbiB0aGUgc2VxdWVuY2U/XG4gICAgICBpZiAoTWF0aC5jZWlsKHBvc2l0aW9uSW5TZXF1ZW5jZSkgPj0gMCAmJiBwb3NpdGlvbkluU2VxdWVuY2UgPD0gTWF0aC5hYnModG90YWxTdGVwcykpIHtcbiAgICAgICAgLy8gTm90ZSB0aGF0IGRlbGF5IGZvciBmaXJzdCBpdGVtIHdpbGwgYmUgbmVnYXRpdmUuIFRoYXQgd2lsbCBjYXVzZVxuICAgICAgICAvLyB0aGUgYW5pbWF0aW9uIHRvIHN0YXJ0IGhhbGZ3YXkgdGhyb3VnaCwgd2hpY2ggaXMgd2hhdCB3ZSB3YW50LlxuICAgICAgICBjb25zdCBkZWxheSA9IHN0ZXBEdXJhdGlvbiAqIChwb3NpdGlvbkluU2VxdWVuY2UgLSAxKS8yO1xuICAgICAgICBjb25zdCBlbmREZWxheSA9IGl0ZW1JbmRleCA9PT0gdG9JbmRleCA/XG4gICAgICAgICAgLXN0ZXBEdXJhdGlvbi8yIDogICAvLyBTdG9wIGhhbGZ3YXkgdGhyb3VnaC5cbiAgICAgICAgICAwOyAgICAgICAgICAgICAgLy8gUGxheSBhbmltYXRpb24gdW50aWwgZW5kLlxuICAgICAgICByZXR1cm4geyBkdXJhdGlvbjogc3RlcER1cmF0aW9uLCBkaXJlY3Rpb24sIGZpbGwsIGRlbGF5LCBlbmREZWxheSB9O1xuICAgICAgfSBlbHNlIHtcbiAgICAgICAgcmV0dXJuIG51bGw7XG4gICAgICB9XG4gICAgfSk7XG5cbiAgICByZXR1cm4gdGltaW5ncztcbiAgfVxuXG59O1xuXG5cbi8vIEtleWZyYW1lcyBmb3Igc3RhbmRhcmQgc2VsZWN0aW9uIGFuaW1hdGlvbiBlZmZlY3RzLlxubWl4aW4uc3RhbmRhcmRFZmZlY3RLZXlmcmFtZXMgPSB7XG5cbiAgLy8gU2ltcGxlIGNyb3NzZmFkZVxuICBjcm9zc2ZhZGU6IFtcbiAgICB7IG9wYWNpdHk6IDAgfSxcbiAgICB7IG9wYWNpdHk6IDEgfSxcbiAgICB7IG9wYWNpdHk6IDAgfVxuICBdLFxuXG4gIC8vIFJldmVhbCwgYXMgaWYgc2xpZGluZyB0aGUgdG9wIGNhcmQgb2ZmIGEgZGVjayBvZiBjYXJkc1xuICByZXZlYWw6IFtcbiAgICB7IHRyYW5zZm9ybTogJ3RyYW5zbGF0ZVgoMCUpJywgekluZGV4OiAwIH0sXG4gICAgeyB0cmFuc2Zvcm06ICd0cmFuc2xhdGVYKDAlKScsIHpJbmRleDogMSB9LFxuICAgIHsgdHJhbnNmb3JtOiAndHJhbnNsYXRlWCgtMTAwJSknLCB6SW5kZXg6IDIgfVxuICBdLFxuXG4gIC8vIEdvb2dsZSBQaG90b3Mtc3R5bGUgcmV2ZWFsLXdpdGgtZmFkZSBhbmltYXRpb25cbiAgcmV2ZWFsV2l0aEZhZGU6IFtcbiAgICB7IHRyYW5zZm9ybTogJ3RyYW5zbGF0ZVgoMCUpIHNjYWxlKDAuNzUpJywgb3BhY2l0eTogMCwgekluZGV4OiAwIH0sXG4gICAgeyB0cmFuc2Zvcm06ICd0cmFuc2xhdGVYKDAlKSBzY2FsZSgxLjApJywgb3BhY2l0eTogMSwgekluZGV4OiAxIH0sXG4gICAgeyB0cmFuc2Zvcm06ICd0cmFuc2xhdGVYKC0xMDAlKSBzY2FsZSgxLjApJywgb3BhY2l0eTogMSwgekluZGV4OiAyIH1cbiAgXSxcblxuICAvLyBDYXJvdXNlbCB2YXJpYW50IHdpdGggYSBiaXQgb2Ygb2ZmLXN0YWdlIGVsZW1lbnRzIHNob3dpbmdcbiAgc2hvd0FkamFjZW50OiBbXG4gICAgeyB0cmFuc2Zvcm06ICd0cmFuc2xhdGVYKDc4JSkgc2NhbGUoMC43KScsIHpJbmRleDogMCB9LFxuICAgIHsgdHJhbnNmb3JtOiAndHJhbnNsYXRlWCgwJSkgc2NhbGUoMC44MiknLCB6SW5kZXg6IDEgfSxcbiAgICB7IHRyYW5zZm9ybTogJ3RyYW5zbGF0ZVgoLTc4JSkgc2NhbGUoMC43KScsIHpJbmRleDogMCB9XG4gIF0sXG5cbiAgLy8gU2ltcGxlIHNsaWRlXG4gIHNsaWRlOiBbXG4gICAgeyB0cmFuc2Zvcm06ICd0cmFuc2xhdGVYKDEwMCUpJyB9LFxuICAgIHsgdHJhbnNmb3JtOiAndHJhbnNsYXRlWCgtMTAwJSknIH1cbiAgXSxcblxuICAvLyBTbGlkZSwgd2l0aCBhIGdhcCBiZXR3ZWVuXG4gIHNsaWRlV2l0aEdhcDogW1xuICAgIHsgdHJhbnNmb3JtOiAndHJhbnNsYXRlWCgxMTAlKScgfSxcbiAgICB7IHRyYW5zZm9ybTogJ3RyYW5zbGF0ZVgoLTExMCUpJyB9XG4gIF1cblxufTtcblxuXG4vKlxuICogU21vb3RobHkgYW5pbWF0ZSB0aGUgc2VsZWN0aW9uIGJldHdlZW4gdGhlIGluZGljYXRlZCBcImZyb21cIiBhbmQgXCJ0b1wiXG4gKiBpbmRpY2VzLiBUaGUgZm9ybWVyIGNhbiBiZSBhIGZyYWN0aW9uLCBlLmcuLCB3aGVuIHRoZSB1c2VyIHJlbGVhc2VzIGEgZmluZ2VyXG4gKiB0byBjb21wbGV0ZSBhIHRvdWNoIGRyYWcsIGFuZCB0aGUgc2VsZWN0aW9uIHdpbGwgc25hcCB0byB0aGUgY2xvc2VzdCB3aG9sZVxuICogaW5kZXguXG4gKi9cbmZ1bmN0aW9uIGFuaW1hdGVTZWxlY3Rpb24oZWxlbWVudCwgZnJvbVNlbGVjdGlvbiwgdG9TZWxlY3Rpb24pIHtcblxuICByZXNldEFuaW1hdGlvbnMoZWxlbWVudCk7XG5cbiAgLy8gQ2FsY3VsYXRlIHRoZSBhbmltYXRpb24gdGltaW5ncy5cbiAgY29uc3QgaXRlbXMgPSBlbGVtZW50Lml0ZW1zO1xuICBjb25zdCBrZXlmcmFtZXMgPSBlbGVtZW50LnNlbGVjdGlvbkFuaW1hdGlvbktleWZyYW1lcztcbiAgZWxlbWVudFtwbGF5aW5nQW5pbWF0aW9uU3ltYm9sXSA9IHRydWU7XG4gIGNvbnN0IHRpbWluZ3MgPSBtaXhpbi5oZWxwZXJzLmVmZmVjdFRpbWluZ3NGb3JTZWxlY3Rpb25BbmltYXRpb24oZWxlbWVudCwgZnJvbVNlbGVjdGlvbiwgdG9TZWxlY3Rpb24pO1xuXG4gIC8vIEZpZ3VyZSBvdXQgd2hpY2ggaXRlbSB3aWxsIGJlIHRoZSBvbmUgKmFmdGVyKiB0aGUgb25lIHdlJ3JlIHNlbGVjdGluZy5cbiAgY29uc3QgaXRlbUNvdW50ID0gaXRlbXMubGVuZ3RoO1xuICBjb25zdCBzZWxlY3Rpb25XcmFwcyA9IGVsZW1lbnQuc2VsZWN0aW9uV3JhcHM7XG4gIGNvbnN0IHNlbGVjdGlvbkluZGV4ID0gRnJhY3Rpb25hbFNlbGVjdGlvbk1peGluLmhlbHBlcnMuc2VsZWN0aW9uUGFydHModG9TZWxlY3Rpb24sIGl0ZW1Db3VudCwgc2VsZWN0aW9uV3JhcHMpLmluZGV4O1xuICBjb25zdCB0b3RhbFN0ZXBzID0gc3RlcHNUb0luZGV4KGl0ZW1Db3VudCwgc2VsZWN0aW9uV3JhcHMsIGZyb21TZWxlY3Rpb24sIHRvU2VsZWN0aW9uKTtcbiAgY29uc3QgZm9yd2FyZCA9IHRvdGFsU3RlcHMgPj0gMDtcbiAgbGV0IG5leHRVcEluZGV4ID0gc2VsZWN0aW9uSW5kZXggKyAoZm9yd2FyZCA/IDEgOiAtIDEpO1xuICBpZiAoc2VsZWN0aW9uV3JhcHMpIHtcbiAgICBuZXh0VXBJbmRleCA9IEZyYWN0aW9uYWxTZWxlY3Rpb25NaXhpbi5oZWxwZXJzLndyYXBwZWRTZWxlY3Rpb24obmV4dFVwSW5kZXgsIGl0ZW1Db3VudCk7XG4gIH0gZWxzZSBpZiAoIWlzSXRlbUluZGV4SW5Cb3VuZHMoZWxlbWVudCwgbmV4dFVwSW5kZXgpKSB7XG4gICAgbmV4dFVwSW5kZXggPSBudWxsOyAvLyBBdCBzdGFydC9lbmQgb2YgbGlzdDsgZG9uJ3QgaGF2ZSBhIG5leHQgaXRlbSB0byBzaG93LlxuICB9XG5cbiAgLy8gUGxheSB0aGUgYW5pbWF0aW9ucyB1c2luZyB0aG9zZSB0aW1pbmdzLlxuICBsZXQgbGFzdEFuaW1hdGlvbkRldGFpbHM7XG4gIHRpbWluZ3MuZm9yRWFjaCgodGltaW5nLCBpbmRleCkgPT4ge1xuICAgIGNvbnN0IGl0ZW0gPSBpdGVtc1tpbmRleF07XG4gICAgaWYgKHRpbWluZykge1xuICAgICAgc2hvd0l0ZW0oaXRlbSwgdHJ1ZSk7XG4gICAgICBjb25zdCBhbmltYXRpb24gPSBpdGVtLmFuaW1hdGUoa2V5ZnJhbWVzLCB0aW1pbmcpO1xuICAgICAgZWxlbWVudFthbmltYXRpb25TeW1ib2xdW2luZGV4XSA9IGFuaW1hdGlvbjtcbiAgICAgIGlmIChpbmRleCA9PT0gbmV4dFVwSW5kZXgpIHtcbiAgICAgICAgLy8gVGhpcyBpdGVtIHdpbGwgYmUgYW5pbWF0ZWQsIHNvIHdpbGwgYWxyZWFkeSBiZSBpbiB0aGUgZGVzaXJlZCBzdGF0ZVxuICAgICAgICAvLyBhZnRlciB0aGUgYW5pbWF0aW9uIGNvbXBsZXRlcy5cbiAgICAgICAgbmV4dFVwSW5kZXggPSBudWxsO1xuICAgICAgfVxuICAgICAgaWYgKHRpbWluZy5lbmREZWxheSAhPT0gMCkge1xuICAgICAgICAvLyBUaGlzIGlzIHRoZSBhbmltYXRpb24gZm9yIHRoZSBpdGVtIHRoYXQgd2lsbCBiZSBsZWZ0IHNlbGVjdGVkLlxuICAgICAgICAvLyBXZSB3YW50IHRvIGNsZWFuIHVwIHdoZW4gdGhpcyBhbmltYXRpb24gY29tcGxldGVzLlxuICAgICAgICBsYXN0QW5pbWF0aW9uRGV0YWlscyA9IHsgYW5pbWF0aW9uLCBpbmRleCwgdGltaW5nLCBmb3J3YXJkIH07XG4gICAgICB9XG4gICAgfSBlbHNlIHtcbiAgICAgIC8vIFRoaXMgaXRlbSBkb2Vzbid0IHBhcnRpY2lwYXRlIGluIHRoZSBhbmltYXRpb24uXG4gICAgICBzaG93SXRlbShpdGVtLCBmYWxzZSk7XG4gICAgfVxuICB9KTtcblxuICBpZiAobGFzdEFuaW1hdGlvbkRldGFpbHMgIT0gbnVsbCkge1xuICAgIC8vIEFycmFuZ2UgZm9yIGNsZWFuLXVwIHdvcmsgdG8gYmUgcGVyZm9ybWVkLlxuICAgIGxhc3RBbmltYXRpb25EZXRhaWxzLm5leHRVcEluZGV4ID0gbmV4dFVwSW5kZXg7XG4gICAgbGFzdEFuaW1hdGlvbkRldGFpbHMuYW5pbWF0aW9uLm9uZmluaXNoID0gZXZlbnQgPT4gc2VsZWN0aW9uQW5pbWF0aW9uRmluaXNoZWQoZWxlbWVudCwgbGFzdEFuaW1hdGlvbkRldGFpbHMpO1xuICAgIGVsZW1lbnRbbGFzdEFuaW1hdGlvblN5bWJvbF0gPSBsYXN0QW5pbWF0aW9uRGV0YWlscy5hbmltYXRpb247XG4gIH0gZWxzZSB7XG4gICAgLy8gU2hvdWxkbid0IGhhcHBlbiAtLSB3ZSBzaG91bGQgYWx3YXlzIGhhdmUgYXQgbGVhc3Qgb25lIGFuaW1hdGlvbi5cbiAgICBlbGVtZW50W3BsYXlpbmdBbmltYXRpb25TeW1ib2xdID0gZmFsc2U7XG4gIH1cbn1cblxuXG5mdW5jdGlvbiBnZXRBbmltYXRpb25Gb3JJdGVtSW5kZXgoZWxlbWVudCwgaW5kZXgpIHtcbiAgaWYgKGVsZW1lbnRbYW5pbWF0aW9uU3ltYm9sXSA9PSBudWxsKSB7XG4gICAgLy8gTm90IHJlYWR5IHlldDtcbiAgICByZXR1cm4gbnVsbDtcbiAgfVxuICBsZXQgYW5pbWF0aW9uID0gZWxlbWVudFthbmltYXRpb25TeW1ib2xdW2luZGV4XTtcbiAgaWYgKCFhbmltYXRpb24pIHtcbiAgICBjb25zdCBpdGVtID0gZWxlbWVudC5pdGVtc1tpbmRleF07XG4gICAgYW5pbWF0aW9uID0gaXRlbS5hbmltYXRlKGVsZW1lbnQuc2VsZWN0aW9uQW5pbWF0aW9uS2V5ZnJhbWVzLCB7XG4gICAgICBkdXJhdGlvbjogZWxlbWVudC5zZWxlY3Rpb25BbmltYXRpb25EdXJhdGlvbixcbiAgICAgIGZpbGw6ICdib3RoJ1xuICAgIH0pO1xuICAgIGFuaW1hdGlvbi5wYXVzZSgpO1xuICAgIGVsZW1lbnRbYW5pbWF0aW9uU3ltYm9sXVtpbmRleF0gPSBhbmltYXRpb247XG4gIH1cbiAgcmV0dXJuIGFuaW1hdGlvbjtcbn1cblxuZnVuY3Rpb24gaXNJdGVtSW5kZXhJbkJvdW5kcyhlbGVtZW50LCBpbmRleCkge1xuICByZXR1cm4gaW5kZXggPj0gMCAmJiBlbGVtZW50Lml0ZW1zICYmIGluZGV4IDwgZWxlbWVudC5pdGVtcy5sZW5ndGg7XG59XG5cbi8qXG4gKiBSZW5kZXIgdGhlIHNlbGVjdGlvbiBzdGF0ZSBvZiB0aGUgZWxlbWVudC5cbiAqXG4gKiBUaGlzIGNhbiBiZSB1c2VkIHRvIHJlLXJlbmRlciBhIHByZXZpb3VzIHNlbGVjdGlvbiBzdGF0ZSAoaWYgdGhlXG4gKiBzZWxlY3RlZEluZGV4IHBhcmFtIGlzIG9taXR0ZWQpLCByZW5kZXIgdGhlIHNlbGVjdGlvbiBpbnN0YW50bHkgYXQgYSBnaXZlblxuICogd2hvbGUgb3IgZnJhY3Rpb25hbCBzZWxlY3Rpb24gaW5kZXgsIG9yIGFuaW1hdGUgdG8gYSBnaXZlbiBzZWxlY3Rpb24gaW5kZXguXG4gKlxuICogVGhlcmUgYXJlIHNldmVyYWwgZGlzdGluY3Qgc2NlbmFyaW9zIHdlIG5lZWQgdG8gY292ZXI6XG4gKlxuICogMS4gSW5pdGlhbCBwb3NpdGlvbmluZywgb3IgcmVwb3NpdGlvbmluZyBhZnRlciBjaGFuZ2luZyBhIHByb3BlcnR5IGxpa2VcbiAqICAgIHNlbGVjdGlvbkFuaW1hdGlvbktleWZyYW1lcyB0aGF0IGFmZmVjdHMgcmVuZGVyaW5nLlxuICogMi4gQW5pbWF0ZSBvbiBzZWxlY3RlZEluZGV4IGNoYW5nZS4gVGhpcyBzaG91bGQgb3ZlcnJpZGUgYW55IGFuaW1hdGlvbi9zd2lwZVxuICogICAgYWxyZWFkeSBpbiBwcm9ncmVzcy5cbiAqIDMuIEluc3RhbnRseSByZW5kZXIgdGhlIGN1cnJlbnQgcG9zaXRpb24gb2YgYSBkcmFnIG9wZXJhdGlvbiBpbiBwcm9ncmVzcy5cbiAqIDQuIENvbXBsZXRlIGEgZHJhZyBvcGVyYXRpb24uIElmIHRoZSBkcmFnIHdhc24ndCBmYXIgZW5vdWdoIHRvIGFmZmVjdFxuICogICAgc2VsZWN0aW9uLCB3ZSdsbCBqdXN0IGJlIHJlc3RvcmluZyB0aGUgc2VsZWN0ZWRGcmFjdGlvbiB0byAwLlxuICpcbiAqIElmIHRoZSBsaXN0IGRvZXMgbm90IHdyYXAsIGFueSBzZWxlY3Rpb24gcG9zaXRpb24gb3V0c2lkZSB0aGUgbGlzdCdzIGJvdW5kc1xuICogd2lsbCBiZSBkYW1wZWQgdG8gcHJvZHVjZSBhIHZpc3VhbCBlZmZlY3Qgb2YgdGVuc2lvbi5cbiAqL1xuZnVuY3Rpb24gcmVuZGVyU2VsZWN0aW9uKGVsZW1lbnQsIHNlbGVjdGVkSW5kZXg9ZWxlbWVudC5zZWxlY3RlZEluZGV4LCBzZWxlY3RlZEZyYWN0aW9uPWVsZW1lbnQuc2VsZWN0ZWRGcmFjdGlvbikge1xuICBjb25zdCBpdGVtQ291bnQgPSBlbGVtZW50Lml0ZW1zID8gZWxlbWVudC5pdGVtcy5sZW5ndGggOiAwO1xuICBpZiAoaXRlbUNvdW50ID09PSAwKSB7XG4gICAgLy8gTm90aGluZyB0byByZW5kZXIuXG4gICAgcmV0dXJuO1xuICB9XG4gIGlmIChzZWxlY3RlZEluZGV4IDwgMCkge1xuICAgIC8vIFRPRE86IEhhbmRsZSBubyBzZWxlY3Rpb24uXG4gICAgcmV0dXJuO1xuICB9XG4gIGxldCBzZWxlY3Rpb24gPSBzZWxlY3RlZEluZGV4ICsgc2VsZWN0ZWRGcmFjdGlvbjtcbiAgaWYgKGVsZW1lbnQuc2VsZWN0aW9uV3JhcHMpIHtcbiAgICAvLyBBcHBseSB3cmFwcGluZyB0byBlbnN1cmUgY29uc2lzdGVudCByZXByZXNlbnRhdGlvbiBvZiBzZWxlY3Rpb24uXG4gICAgc2VsZWN0aW9uID0gRnJhY3Rpb25hbFNlbGVjdGlvbk1peGluLmhlbHBlcnMud3JhcHBlZFNlbGVjdGlvbihzZWxlY3Rpb24sIGl0ZW1Db3VudCk7XG4gIH0gZWxzZSB7XG4gICAgLy8gQXBwbHkgZGFtcGluZyBpZiBuZWNlc3NhcnkuXG4gICAgc2VsZWN0aW9uID0gRnJhY3Rpb25hbFNlbGVjdGlvbk1peGluLmhlbHBlcnMuZGFtcGVkU2VsZWN0aW9uKHNlbGVjdGlvbiwgaXRlbUNvdW50KTtcbiAgfVxuICBjb25zdCBwcmV2aW91c1NlbGVjdGlvbiA9IGVsZW1lbnRbcHJldmlvdXNTZWxlY3Rpb25TeW1ib2xdO1xuICAvLyBUT0RPOiBJZiBhbiBpdGVtIGNoYW5nZXMgcG9zaXRpb24gaW4gdGhlIERPTSwgd2UgZW5kIHVwIGFuaW1hdGluZyBmcm9tXG4gIC8vIGl0cyBvbGQgaW5kZXggdG8gaXRzIG5ldyBpbmRleCwgYnV0IHdlIHJlYWxseSBkb24ndCB3YW50IHRvIGFuaW1hdGUgYXQgYWxsLlxuICBpZiAoIWVsZW1lbnRbc3ltYm9scy5kcmFnZ2luZ10gJiYgcHJldmlvdXNTZWxlY3Rpb24gIT0gbnVsbCAmJlxuICAgICAgcHJldmlvdXNTZWxlY3Rpb24gIT09IHNlbGVjdGlvbikge1xuICAgIC8vIEFuaW1hdGUgc2VsZWN0aW9uIGZyb20gcHJldmlvdXMgc3RhdGUgdG8gbmV3IHN0YXRlLlxuICAgIGFuaW1hdGVTZWxlY3Rpb24oZWxlbWVudCwgcHJldmlvdXNTZWxlY3Rpb24sIHNlbGVjdGlvbik7XG4gIH0gZWxzZSBpZiAoc2VsZWN0ZWRGcmFjdGlvbiA9PT0gMCAmJiBlbGVtZW50W3BsYXlpbmdBbmltYXRpb25TeW1ib2xdKSB7XG4gICAgLy8gQWxyZWFkeSBpbiBwcm9jZXNzIG9mIGFuaW1hdGluZyB0byBmcmFjdGlvbiAwLiBEdXJpbmcgdGhhdCBwcm9jZXNzLFxuICAgIC8vIGlnbm9yZSBzdWJzZXF1ZW50IGF0dGVtcHRzIHRvIHJlbmRlclNlbGVjdGlvbiB0byBmcmFjdGlvbiAwLlxuICAgIHJldHVybjtcbiAgfSBlbHNlIHtcbiAgICAvLyBSZW5kZXIgY3VycmVudCBzZWxlY3Rpb24gc3RhdGUgaW5zdGFudGx5LlxuICAgIHJlbmRlclNlbGVjdGlvbkluc3RhbnRseShlbGVtZW50LCBzZWxlY3Rpb24pO1xuICB9XG4gIGVsZW1lbnRbcHJldmlvdXNTZWxlY3Rpb25TeW1ib2xdID0gc2VsZWN0aW9uO1xufVxuXG4vKlxuICogSW5zdGFudGx5IHJlbmRlciAoZG9uJ3QgYW5pbWF0ZSkgdGhlIGVsZW1lbnQncyBpdGVtcyBhdCB0aGUgZ2l2ZW4gd2hvbGUgb3JcbiAqIGZyYWN0aW9uYWwgc2VsZWN0aW9uIGluZGV4LlxuICovXG5mdW5jdGlvbiByZW5kZXJTZWxlY3Rpb25JbnN0YW50bHkoZWxlbWVudCwgdG9TZWxlY3Rpb24pIHtcbiAgaWYgKGVsZW1lbnRbcmVzZXRBbmltYXRpb25zT25OZXh0UmVuZGVyU3ltYm9sXSkge1xuICAgIHJlc2V0QW5pbWF0aW9ucyhlbGVtZW50KTtcbiAgICBlbGVtZW50W3Jlc2V0QW5pbWF0aW9uc09uTmV4dFJlbmRlclN5bWJvbF0gPSBmYWxzZTtcbiAgfVxuICBjb25zdCBhbmltYXRpb25GcmFjdGlvbnMgPSBtaXhpbi5oZWxwZXJzLmFuaW1hdGlvbkZyYWN0aW9uc0ZvclNlbGVjdGlvbihlbGVtZW50LCB0b1NlbGVjdGlvbik7XG4gIGFuaW1hdGlvbkZyYWN0aW9ucy5tYXAoKGFuaW1hdGlvbkZyYWN0aW9uLCBpbmRleCkgPT4ge1xuICAgIGNvbnN0IGl0ZW0gPSBlbGVtZW50Lml0ZW1zW2luZGV4XTtcbiAgICBpZiAoYW5pbWF0aW9uRnJhY3Rpb24gIT0gbnVsbCkge1xuICAgICAgc2hvd0l0ZW0oaXRlbSwgdHJ1ZSk7XG4gICAgICBzZXRBbmltYXRpb25GcmFjdGlvbihlbGVtZW50LCBpbmRleCwgYW5pbWF0aW9uRnJhY3Rpb24pO1xuICAgIH0gZWxzZSB7XG4gICAgICBzaG93SXRlbShpdGVtLCBmYWxzZSk7XG4gICAgfVxuICB9KTtcbn1cblxuLypcbiAqIFdlIG1haW50YWluIGFuIGFycmF5IGNvbnRhaW5pbmcgYW4gYW5pbWF0aW9uIHBlciBpdGVtLiBUaGlzIGlzIHVzZWQgZm9yIHR3b1xuICogcmVhc29uczpcbiAqXG4gKiAqIER1cmluZyBhIGRyYWcgb3BlcmF0aW9uLCB3ZSB3YW50IHRvIGJlIGFibGUgdG8gcmV1c2UgYW5pbWF0aW9ucyBiZXR3ZWVuXG4gKiAgIGRyYWcgdXBkYXRlcy5cbiAqICogV2hlbiBhIHNlbGVjdGlvbiBhbmltYXRpb24gY29tcGxldGVzLCB3ZSBuZWVkIHRvIGJlIGFibGUgdG8gbGVhdmUgdGhlXG4gKiAgIHZpc2liaWxlIGl0ZW1zIGluIGEgcGF1c2VkIHN0YXRlLiBMYXRlciwgd2UnbGwgd2FudCB0byBiZSBhYmxlIHRvIGNsZWFuIHVwXG4gKiAgIHRob3NlIGFuaW1hdGlvbnMuXG4gKlxuICogTm90ZSB0aGF0IHRoaXMgYXJyYXkgaXMgc3BhcnNlOiBpdCB3aWxsIG9ubHkgaG9sZCB1cCBmcm9tIDDigJMzIGFuaW1hdGlvbnMgYXRcbiAqIGFueSBnaXZlbiBwb2ludC5cbiAqL1xuZnVuY3Rpb24gcmVzZXRBbmltYXRpb25zKGVsZW1lbnQpIHtcbiAgY29uc3QgYW5pbWF0aW9ucyA9IGVsZW1lbnRbYW5pbWF0aW9uU3ltYm9sXTtcbiAgaWYgKGFuaW1hdGlvbnMpIHtcbiAgICAvLyBDYW5jZWwgZXhpc3RpbmcgYW5pbWF0aW9ucyB0byByZW1vdmUgdGhlIGVmZmVjdHMgdGhleSdyZSBhcHBseWluZy5cbiAgICBhbmltYXRpb25zLmZvckVhY2goKGFuaW1hdGlvbiwgaW5kZXgpID0+IHtcbiAgICAgIGlmIChhbmltYXRpb24pIHtcbiAgICAgICAgYW5pbWF0aW9uLmNhbmNlbCgpO1xuICAgICAgICBhbmltYXRpb25zW2luZGV4XSA9IG51bGw7XG4gICAgICB9XG4gICAgfSk7XG4gIH1cbiAgY29uc3QgaXRlbUNvdW50ID0gZWxlbWVudC5pdGVtcyA/IGVsZW1lbnQuaXRlbXMubGVuZ3RoIDogMDtcbiAgaWYgKCFhbmltYXRpb25zIHx8IGFuaW1hdGlvbnMubGVuZ3RoICE9PSBpdGVtQ291bnQpIHtcbiAgICAvLyBIYXZlbid0IGFuaW1hdGVkIGJlZm9yZSB3aXRoIHRoaXMgbnVtYmVyIG9mIGl0ZW1zOyAocmUpY3JlYXRlIGFycmF5LlxuICAgIGVsZW1lbnRbYW5pbWF0aW9uU3ltYm9sXSA9IG5ldyBBcnJheShpdGVtQ291bnQpO1xuICB9XG59XG5cbi8qXG4gKiBUaGUgbGFzdCBhbmltYXRpb24gaW4gb3VyIHNlbGVjdGlvbiBhbmltYXRpb24gaGFzIGNvbXBsZXRlZC4gQ2xlYW4gdXAuXG4gKi9cbmZ1bmN0aW9uIHNlbGVjdGlvbkFuaW1hdGlvbkZpbmlzaGVkKGVsZW1lbnQsIGRldGFpbHMpIHtcblxuICAvLyBXaGVuIHRoZSBsYXN0IGFuaW1hdGlvbiBjb21wbGV0ZXMsIHNob3cgdGhlIG5leHQgaXRlbSBpbiB0aGUgZGlyZWN0aW9uXG4gIC8vIHdlJ3JlIGdvaW5nLiBXYWl0aW5nIHRvIHRoYXQgdW50aWwgdGhpcyBwb2ludCBpcyBhIGJpdCBvZiBhIGhhY2sgdG8gYXZvaWRcbiAgLy8gaGF2aW5nIGEgbmV4dCBpdGVtIHRoYXQncyBoaWdoZXIgaW4gdGhlIG5hdHVyYWwgei1vcmRlciBvYnNjdXJlIG90aGVyIGl0ZW1zXG4gIC8vIGR1cmluZyBhbmltYXRpb24uXG4gIGNvbnN0IG5leHRVcEluZGV4ID0gZGV0YWlscy5uZXh0VXBJbmRleDtcbiAgaWYgKG5leHRVcEluZGV4ICE9IG51bGwpIHtcbiAgICBpZiAoZWxlbWVudFthbmltYXRpb25TeW1ib2xdW25leHRVcEluZGV4XSkge1xuICAgICAgLy8gQ2FuY2VsIGV4aXN0aW5nIHNlbGVjdGlvbiBhbmltYXRpb24gc28gd2UgY2FuIGNvbnN0cnVjdCBhIG5ldyBvbmUuXG4gICAgICBlbGVtZW50W2FuaW1hdGlvblN5bWJvbF1bbmV4dFVwSW5kZXhdLmNhbmNlbCgpO1xuICAgICAgZWxlbWVudFthbmltYXRpb25TeW1ib2xdW25leHRVcEluZGV4XSA9IG51bGw7XG4gICAgfVxuICAgIGNvbnN0IGFuaW1hdGlvbkZyYWN0aW9uID0gZGV0YWlscy5mb3J3YXJkID8gMCA6IDE7XG4gICAgc2V0QW5pbWF0aW9uRnJhY3Rpb24oZWxlbWVudCwgbmV4dFVwSW5kZXgsIGFuaW1hdGlvbkZyYWN0aW9uKTtcbiAgICBzaG93SXRlbShlbGVtZW50Lml0ZW1zW25leHRVcEluZGV4XSwgdHJ1ZSk7XG4gIH1cblxuICBlbGVtZW50W2xhc3RBbmltYXRpb25TeW1ib2xdLm9uZmluaXNoID0gbnVsbDtcbiAgZWxlbWVudFtwbGF5aW5nQW5pbWF0aW9uU3ltYm9sXSA9IGZhbHNlO1xufVxuXG4vKlxuICogUGF1c2UgdGhlIGluZGljYXRlZCBhbmltYXRpb24gYW5kIGhhdmUgaXQgc2hvdyB0aGUgYW5pbWF0aW9uIGF0IHRoZSBnaXZlblxuICogZnJhY3Rpb24gKGJldHdlZW4gMCBhbmQgMSkgb2YgdGhlIHdheSB0aHJvdWdoIHRoZSBhbmltYXRpb24uXG4gKi9cbmZ1bmN0aW9uIHNldEFuaW1hdGlvbkZyYWN0aW9uKGVsZW1lbnQsIGl0ZW1JbmRleCwgZnJhY3Rpb24pIHtcbiAgY29uc3QgYW5pbWF0aW9uID0gZ2V0QW5pbWF0aW9uRm9ySXRlbUluZGV4KGVsZW1lbnQsIGl0ZW1JbmRleCk7XG4gIGlmIChhbmltYXRpb24pIHtcbiAgICBjb25zdCBkdXJhdGlvbiA9IGVsZW1lbnQuc2VsZWN0aW9uQW5pbWF0aW9uRHVyYXRpb247XG4gICAgaWYgKGR1cmF0aW9uKSB7XG4gICAgICBhbmltYXRpb24uY3VycmVudFRpbWUgPSBmcmFjdGlvbiAqIGR1cmF0aW9uO1xuICAgIH1cbiAgfVxufVxuXG5mdW5jdGlvbiBzaG93SXRlbShpdGVtLCBmbGFnKSB7XG4gIGl0ZW0uc3R5bGUudmlzaWJpbGl0eSA9IGZsYWcgPyAndmlzaWJsZScgOiAnaGlkZGVuJztcbn1cblxuLypcbiAqIEZpZ3VyZSBvdXQgaG93IG1hbnkgc3RlcHMgaXQgd2lsbCB0YWtlIHRvIGdvIGZyb20gZnJvbVNlbGVjdGlvbiB0b1xuICogdG9TZWxlY3Rpb24uIFRvIGdvIGZyb20gaXRlbSAzIHRvIGl0ZW0gNCBpcyBvbmUgc3RlcC5cbiAqXG4gKiBJZiB3cmFwcGluZyBpcyBhbGxvd2VkLCB0aGVuIGdvaW5nIGZyb20gdGhlIGxhc3QgaXRlbSB0byB0aGUgZmlyc3Qgd2lsbCB0YWtlXG4gKiBvbmUgc3RlcCAoZm9yd2FyZCksIGFuZCBnb2luZyBmcm9tIHRoZSBmaXJzdCBpdGVtIHRvIHRoZSBsYXN0IHdpbGwgdGFrZSBvbmVcbiAqIHN0ZXAgKGJhY2t3YXJkKS5cbiAqL1xuZnVuY3Rpb24gc3RlcHNUb0luZGV4KGxlbmd0aCwgYWxsb3dXcmFwLCBmcm9tU2VsZWN0aW9uLCB0b1NlbGVjdGlvbikge1xuICBsZXQgc3RlcHMgPSB0b1NlbGVjdGlvbiAtIGZyb21TZWxlY3Rpb247XG4gIC8vIFdyYXBwaW5nIG9ubHkga2lja3MgaW4gd2hlbiBsaXN0IGhhcyBtb3JlIHRoYW4gMSBpdGVtLlxuICBpZiAoYWxsb3dXcmFwICYmIGxlbmd0aCA+IDEpIHtcbiAgICBjb25zdCB3cmFwU3RlcHMgPSBsZW5ndGggLSBNYXRoLmFicyhzdGVwcyk7XG4gICAgaWYgKHdyYXBTdGVwcyA8PSAxKSB7XG4gICAgICAvLyBTcGVjaWFsIGNhc2VcbiAgICAgIHN0ZXBzID0gc3RlcHMgPCAwID9cbiAgICAgICAgd3JhcFN0ZXBzIDogICAvLyBXcmFwIGZvcndhcmQgZnJvbSBsYXN0IGl0ZW0gdG8gZmlyc3QuXG4gICAgICAgIC13cmFwU3RlcHM7ICAgLy8gV3JhcCBiYWNrd2FyZCBmcm9tIGZpcnN0IGl0ZW0gdG8gbGFzdC5cbiAgICB9XG4gIH1cbiAgcmV0dXJuIHN0ZXBzO1xufVxuIiwiaW1wb3J0IHN5bWJvbHMgZnJvbSAnLi9zeW1ib2xzJztcblxuXG4vLyBVc2VkIHRvIGFzc2lnbiB1bmlxdWUgSURzIHRvIGl0ZW0gZWxlbWVudHMgd2l0aG91dCBJRHMuXG5sZXQgaWRDb3VudCA9IDA7XG5cblxuLyogRXhwb3J0ZWQgZnVuY3Rpb24gZXh0ZW5kcyBhIGJhc2UgY2xhc3Mgd2l0aCBTZWxlY3Rpb25BcmlhQWN0aXZlLiAqL1xuZXhwb3J0IGRlZmF1bHQgKGJhc2UpID0+IHtcblxuICAvKipcbiAgICogTWl4aW4gd2hpY2ggdHJlYXRzIHRoZSBzZWxlY3RlZCBpdGVtIGluIGEgbGlzdCBhcyB0aGUgYWN0aXZlIGl0ZW0gaW4gQVJJQVxuICAgKiBhY2Nlc3NpYmlsaXR5IHRlcm1zLlxuICAgKlxuICAgKiBIYW5kbGluZyBBUklBIHNlbGVjdGlvbiBzdGF0ZSBwcm9wZXJseSBpcyBhY3R1YWxseSBxdWl0ZSBjb21wbGV4OlxuICAgKlxuICAgKiAqIFRoZSBpdGVtcyBpbiB0aGUgbGlzdCBuZWVkIHRvIGJlIGluZGljYXRlZCBhcyBwb3NzaWJsZSBpdGVtcyB2aWEgYW4gQVJJQVxuICAgKiAgIGByb2xlYCBhdHRyaWJ1dGUgdmFsdWUgc3VjaCBhcyBcIm9wdGlvblwiLlxuICAgKiAqIFRoZSBzZWxlY3RlZCBpdGVtIG5lZWQgdG8gYmUgbWFya2VkIGFzIHNlbGVjdGVkIGJ5IHNldHRpbmcgdGhlIGl0ZW0nc1xuICAgKiAgIGBhcmlhLXNlbGVjdGVkYCBhdHRyaWJ1dGUgdG8gdHJ1ZSAqYW5kKiB0aGUgb3RoZXIgaXRlbXMgbmVlZCBiZSBtYXJrZWQgYXNcbiAgICogICAqbm90KiBzZWxlY3RlZCBieSBzZXR0aW5nIGBhcmlhLXNlbGVjdGVkYCB0byBmYWxzZS5cbiAgICogKiBUaGUgb3V0ZXJtb3N0IGVsZW1lbnQgd2l0aCB0aGUga2V5Ym9hcmQgZm9jdXMgbmVlZHMgdG8gaGF2ZSBhdHRyaWJ1dGVzXG4gICAqICAgc2V0IG9uIGl0IHNvIHRoYXQgdGhlIHNlbGVjdGlvbiBpcyBrbm93YWJsZSBhdCB0aGUgbGlzdCBsZXZlbCB2aWEgdGhlXG4gICAqICAgYGFyaWEtYWN0aXZlZGVzY2VuZGFudGAgYXR0cmlidXRlLlxuICAgKiAqIFVzZSBvZiBgYXJpYS1hY3RpdmVkZXNjZW5kYW50YCBpbiB0dXJuIHJlcXVpcmVzIHRoYXQgYWxsIGl0ZW1zIGluIHRoZVxuICAgKiAgIGxpc3QgaGF2ZSBJRCBhdHRyaWJ1dGVzIGFzc2lnbmVkIHRvIHRoZW0uXG4gICAqXG4gICAqIFRoaXMgbWl4aW4gdHJpZXMgdG8gYWRkcmVzcyBhbGwgb2YgdGhlIGFib3ZlIHJlcXVpcmVtZW50cy4gVG8gdGhhdCBlbmQsXG4gICAqIHRoaXMgbWl4aW4gd2lsbCBhc3NpZ24gZ2VuZXJhdGVkIElEcyB0byBhbnkgaXRlbSB0aGF0IGRvZXNuJ3QgYWxyZWFkeSBoYXZlXG4gICAqIGFuIElELlxuICAgKlxuICAgKiBBUklBIHJlbGllcyBvbiBlbGVtZW50cyB0byBwcm92aWRlIGByb2xlYCBhdHRyaWJ1dGVzLiBUaGlzIG1peGluIHdpbGwgYXBwbHlcbiAgICogYSBkZWZhdWx0IHJvbGUgb2YgXCJsaXN0Ym94XCIgb24gdGhlIG91dGVyIGxpc3QgaWYgaXQgZG9lc24ndCBhbHJlYWR5IGhhdmUgYW5cbiAgICogZXhwbGljaXQgcm9sZS4gU2ltaWxhcmx5LCB0aGlzIG1peGluIHdpbGwgYXBwbHkgYSBkZWZhdWx0IHJvbGUgb2YgXCJvcHRpb25cIlxuICAgKiB0byBhbnkgbGlzdCBpdGVtIHRoYXQgZG9lcyBub3QgYWxyZWFkeSBoYXZlIGEgcm9sZSBzcGVjaWZpZWQuXG4gICAqXG4gICAqIFRoaXMgbWl4aW4gZXhwZWN0cyBhIHNldCBvZiBtZW1iZXJzIHRoYXQgbWFuYWdlIHRoZSBzdGF0ZSBvZiB0aGUgc2VsZWN0aW9uOlxuICAgKiBgW3N5bWJvbHMuaXRlbVNlbGVjdGVkXWAsIGBpdGVtQWRkZWRgLCBhbmQgYHNlbGVjdGVkSW5kZXhgLiBZb3UgY2FuXG4gICAqIHN1cHBseSB0aGVzZSB5b3Vyc2VsZiwgb3IgZG8gc28gdmlhXG4gICAqIFtTaW5nbGVTZWxlY3Rpb25NaXhpbl0oU2luZ2xlU2VsZWN0aW9uTWl4aW4ubWQpLlxuICAgKi9cbiAgY2xhc3MgU2VsZWN0aW9uQXJpYUFjdGl2ZSBleHRlbmRzIGJhc2Uge1xuXG4gICAgY29ubmVjdGVkQ2FsbGJhY2soKSB7XG4gICAgICBpZiAoc3VwZXIuY29ubmVjdGVkQ2FsbGJhY2spIHsgc3VwZXIuY29ubmVjdGVkQ2FsbGJhY2soKTsgfVxuICAgICAgLy8gU2V0IGRlZmF1bHQgQVJJQSByb2xlLlxuICAgICAgaWYgKHRoaXMuZ2V0QXR0cmlidXRlKCdyb2xlJykgPT0gbnVsbCAmJiB0aGlzW3N5bWJvbHMuZGVmYXVsdHNdLnJvbGUpIHtcbiAgICAgICAgdGhpcy5zZXRBdHRyaWJ1dGUoJ3JvbGUnLCB0aGlzW3N5bWJvbHMuZGVmYXVsdHNdLnJvbGUpO1xuICAgICAgfVxuICAgIH1cblxuICAgIGdldCBbc3ltYm9scy5kZWZhdWx0c10oKSB7XG4gICAgICBjb25zdCBkZWZhdWx0cyA9IHN1cGVyW3N5bWJvbHMuZGVmYXVsdHNdIHx8IHt9O1xuICAgICAgZGVmYXVsdHMucm9sZSA9ICdsaXN0Ym94JztcbiAgICAgIHJldHVybiBkZWZhdWx0cztcbiAgICB9XG5cbiAgICBbc3ltYm9scy5pdGVtQWRkZWRdKGl0ZW0pIHtcbiAgICAgIGlmIChzdXBlcltzeW1ib2xzLml0ZW1BZGRlZF0pIHsgc3VwZXJbc3ltYm9scy5pdGVtQWRkZWRdKGl0ZW0pOyB9XG5cbiAgICAgIGlmICghaXRlbS5nZXRBdHRyaWJ1dGUoJ3JvbGUnKSkge1xuICAgICAgICAvLyBBc3NpZ24gYSBkZWZhdWx0IEFSSUEgcm9sZS5cbiAgICAgICAgaXRlbS5zZXRBdHRyaWJ1dGUoJ3JvbGUnLCAnb3B0aW9uJyk7XG4gICAgICB9XG5cbiAgICAgIC8vIEVuc3VyZSBlYWNoIGl0ZW0gaGFzIGFuIElEIHNvIHdlIGNhbiBzZXQgYXJpYS1hY3RpdmVkZXNjZW5kYW50IG9uIHRoZVxuICAgICAgLy8gb3ZlcmFsbCBsaXN0IHdoZW5ldmVyIHRoZSBzZWxlY3Rpb24gY2hhbmdlcy5cbiAgICAgIC8vXG4gICAgICAvLyBUaGUgSUQgd2lsbCB0YWtlIHRoZSBmb3JtIG9mIGEgYmFzZSBJRCBwbHVzIGEgdW5pcXVlIGludGVnZXIuIFRoZSBiYXNlXG4gICAgICAvLyBJRCB3aWxsIGJlIGluY29ycG9yYXRlIHRoZSBjb21wb25lbnQncyBvd24gSUQuIEUuZy4sIGlmIGEgY29tcG9uZW50IGhhc1xuICAgICAgLy8gSUQgXCJmb29cIiwgdGhlbiBpdHMgaXRlbXMgd2lsbCBoYXZlIElEcyB0aGF0IGxvb2sgbGlrZSBcIl9mb29PcHRpb24xXCIuIElmXG4gICAgICAvLyB0aGUgY29tcG5lbnQgaGFzIG5vIElEIGl0c2VsZiwgaXRzIGl0ZW1zIHdpbGwgZ2V0IElEcyB0aGF0IGxvb2sgbGlrZVxuICAgICAgLy8gXCJfb3B0aW9uMVwiLiBJdGVtIElEcyBhcmUgcHJlZml4ZWQgd2l0aCBhbiB1bmRlcnNjb3JlIHRvIGRpZmZlcmVudGlhdGVcbiAgICAgIC8vIHRoZW0gZnJvbSBtYW51YWxseS1hc3NpZ25lZCBJRHMsIGFuZCB0byBtaW5pbWl6ZSB0aGUgcG90ZW50aWFsIGZvciBJRFxuICAgICAgLy8gY29uZmxpY3RzLlxuICAgICAgaWYgKCFpdGVtLmlkKSB7XG4gICAgICAgIGNvbnN0IGJhc2VJZCA9IHRoaXMuaWQgP1xuICAgICAgICAgICAgXCJfXCIgKyB0aGlzLmlkICsgXCJPcHRpb25cIiA6XG4gICAgICAgICAgICBcIl9vcHRpb25cIjtcbiAgICAgICAgaXRlbS5pZCA9IGJhc2VJZCArIGlkQ291bnQrKztcbiAgICAgIH1cbiAgICB9XG5cbiAgICBbc3ltYm9scy5pdGVtU2VsZWN0ZWRdKGl0ZW0sIHNlbGVjdGVkKSB7XG4gICAgICBpZiAoc3VwZXJbc3ltYm9scy5pdGVtU2VsZWN0ZWRdKSB7IHN1cGVyW3N5bWJvbHMuaXRlbVNlbGVjdGVkXShpdGVtLCBzZWxlY3RlZCk7IH1cbiAgICAgIGl0ZW0uc2V0QXR0cmlidXRlKCdhcmlhLXNlbGVjdGVkJywgc2VsZWN0ZWQpO1xuICAgICAgY29uc3QgaXRlbUlkID0gaXRlbS5pZDtcbiAgICAgIGlmIChpdGVtSWQgJiYgc2VsZWN0ZWQpIHtcbiAgICAgICAgdGhpcy5zZXRBdHRyaWJ1dGUoJ2FyaWEtYWN0aXZlZGVzY2VuZGFudCcsIGl0ZW1JZCk7XG4gICAgICB9XG4gICAgfVxuXG4gICAgZ2V0IHNlbGVjdGVkSXRlbSgpIHtcbiAgICAgIHJldHVybiBzdXBlci5zZWxlY3RlZEl0ZW07XG4gICAgfVxuICAgIHNldCBzZWxlY3RlZEl0ZW0oaXRlbSkge1xuICAgICAgaWYgKCdzZWxlY3RlZEl0ZW0nIGluIGJhc2UucHJvdG90eXBlKSB7IHN1cGVyLnNlbGVjdGVkSXRlbSA9IGl0ZW07IH1cbiAgICAgIGlmIChpdGVtID09IG51bGwpIHtcbiAgICAgICAgLy8gU2VsZWN0aW9uIHdhcyByZW1vdmVkLlxuICAgICAgICB0aGlzLnJlbW92ZUF0dHJpYnV0ZSgnYXJpYS1hY3RpdmVkZXNjZW5kYW50Jyk7XG4gICAgICB9XG4gICAgfVxuXG4gIH1cblxuICByZXR1cm4gU2VsZWN0aW9uQXJpYUFjdGl2ZTtcbn07XG4iLCJpbXBvcnQgc3ltYm9scyBmcm9tICcuLi9zcmMvc3ltYm9scyc7XG5cblxuLyogRXhwb3J0ZWQgZnVuY3Rpb24gZXh0ZW5kcyBhIGJhc2UgY2xhc3Mgd2l0aCBTZWxlY3Rpb25IaWdobGlnaHQuICovXG5leHBvcnQgZGVmYXVsdCAoYmFzZSkgPT4ge1xuXG4gIC8qKlxuICAgKiBUZW1wbGF0ZSBtaXhpbiB3aGljaCBhcHBsaWVzIHN0YW5kYXJkIGhpZ2hsaWdodCBjb2xvcnMgdG8gYSBzZWxlY3RlZCBpdGVtLlxuICAgKlxuICAgKiBUaGlzIG1peGluIGhpZ2hsaWdodHMgdGV4dHVhbCBpdGVtcyAoZS5nLiwgaW4gYSBsaXN0KSBpbiBhIHN0YW5kYXJkIHdheSBieVxuICAgKiB1c2luZyB0aGUgQ1NTIGBoaWdobGlnaHRgIGFuZCBgaGlnaGxpZ2h0dGV4dGAgY29sb3IgdmFsdWVzLiBUaGVzZSB2YWx1ZXNcbiAgICogcmVzcGVjdCBvcGVyYXRpbmcgc3lzdGVtIGRlZmF1bHRzIGFuZCB1c2VyIHByZWZlcmVuY2VzLCBhbmQgaGVuY2UgYXJlIGdvb2RcbiAgICogZGVmYXVsdCB2YWx1ZXMgZm9yIGhpZ2hsaWdodCBjb2xvcnMuXG4gICAqXG4gICAqIFRoaXMgbWl4aW4gZXhwZWN0cyBhIGBzZWxlY3RlZGAgY2xhc3MgdG8gYmUgYXBwbGllZCB0byBzZWxlY3RlZCBpdGVtcy4gWW91XG4gICAqIGNhbiB1c2UgW0NvbnRlbnRJdGVtc01peGluXShDb250ZW50SXRlbXNNaXhpbi5tZCkgZm9yIHRoYXQgcHVycG9zZS5cbiAgICovXG4gIGNsYXNzIFNlbGVjdGlvbkhpZ2hsaWdodCBleHRlbmRzIGJhc2Uge1xuXG4gICAgZ2V0IFtzeW1ib2xzLnRlbXBsYXRlXSgpIHtcbiAgICAgIGNvbnN0IGJhc2VUZW1wbGF0ZSA9IHN1cGVyW3N5bWJvbHMudGVtcGxhdGVdIHx8ICcnO1xuICAgICAgcmV0dXJuIGBcbiAgICAgICAgPHN0eWxlPlxuICAgICAgICAgIDpob3N0KFtnZW5lcmljPVwiXCJdKSA6OnNsb3R0ZWQoLnNlbGVjdGVkKSB7XG4gICAgICAgICAgICBiYWNrZ3JvdW5kLWNvbG9yOiBoaWdobGlnaHQ7XG4gICAgICAgICAgICBjb2xvcjogaGlnaGxpZ2h0dGV4dDtcbiAgICAgICAgICB9XG4gICAgICAgIDwvc3R5bGU+XG4gICAgICAgICR7YmFzZVRlbXBsYXRlfVxuICAgICAgYDtcbiAgICB9XG5cbiAgfVxuXG4gIHJldHVybiBTZWxlY3Rpb25IaWdobGlnaHQ7XG59O1xuIiwiLyogRXhwb3J0ZWQgZnVuY3Rpb24gZXh0ZW5kcyBhIGJhc2UgY2xhc3Mgd2l0aCBTZWxlY3Rpb25JblZpZXcuICovXG5leHBvcnQgZGVmYXVsdCAoYmFzZSkgPT4ge1xuXG4gIC8qKlxuICAgKiBNaXhpbiB3aGljaCBzY3JvbGxzIGEgY29udGFpbmVyIHRvIGVuc3VyZSB0aGF0IGEgbmV3bHktc2VsZWN0ZWQgaXRlbSBpc1xuICAgKiB2aXNpYmxlIHRvIHRoZSB1c2VyLlxuICAgKlxuICAgKiBXaGVuIHRoZSBzZWxlY3RlZCBpdGVtIGluIGEgbGlzdC1saWtlIGNvbXBvbmVudCBjaGFuZ2VzLCBpdCdzIGVhc2llciBmb3JcbiAgICogdGhlIHRvIGNvbmZpcm0gdGhhdCB0aGUgc2VsZWN0aW9uIGhhcyBjaGFuZ2VkIHRvIGFuIGFwcHJvcHJpYXRlIGl0ZW0gaWYgdGhlXG4gICAqIHVzZXIgY2FuIGFjdHVhbGx5IHNlZSB0aGF0IGl0ZW0uXG4gICAqXG4gICAqIFRoaXMgbWl4aW4gZXhwZWN0cyBhIGBzZWxlY3RlZEl0ZW1gIHByb3BlcnR5IHRvIGJlIHNldCB3aGVuIHRoZSBzZWxlY3Rpb25cbiAgICogY2hhbmdlcy4gWW91IGNhbiBzdXBwbHkgdGhhdCB5b3Vyc2VsZiwgb3IgdXNlXG4gICAqIFtTaW5nbGVTZWxlY3Rpb25NaXhpbl0oU2luZ2xlU2VsZWN0aW9uTWl4aW4ubWQpLlxuICAgKi9cbiAgY2xhc3MgU2VsZWN0aW9uSW5WaWV3IGV4dGVuZHMgYmFzZSB7XG5cbiAgICBjb25uZWN0ZWRDYWxsYmFjaygpIHtcbiAgICAgIGlmIChzdXBlci5jb25uZWN0ZWRDYWxsYmFjaykgeyBzdXBlci5jb25uZWN0ZWRDYWxsYmFjaygpOyB9XG4gICAgICBjb25zdCBzZWxlY3RlZEl0ZW0gPSB0aGlzLnNlbGVjdGVkSXRlbTtcbiAgICAgIGlmIChzZWxlY3RlZEl0ZW0pIHtcbiAgICAgICAgdGhpcy5zY3JvbGxJdGVtSW50b1ZpZXcoc2VsZWN0ZWRJdGVtKTtcbiAgICAgIH1cbiAgICB9XG5cbiAgICBnZXQgc2VsZWN0ZWRJdGVtKCkge1xuICAgICAgcmV0dXJuIHN1cGVyLnNlbGVjdGVkSXRlbTtcbiAgICB9XG4gICAgc2V0IHNlbGVjdGVkSXRlbShpdGVtKSB7XG4gICAgICBpZiAoJ3NlbGVjdGVkSXRlbScgaW4gYmFzZS5wcm90b3R5cGUpIHsgc3VwZXIuc2VsZWN0ZWRJdGVtID0gaXRlbTsgfVxuICAgICAgaWYgKGl0ZW0pIHtcbiAgICAgICAgLy8gS2VlcCB0aGUgc2VsZWN0ZWQgaXRlbSBpbiB2aWV3LlxuICAgICAgICB0aGlzLnNjcm9sbEl0ZW1JbnRvVmlldyhpdGVtKTtcbiAgICAgIH1cbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBTY3JvbGwgdGhlIGdpdmVuIGVsZW1lbnQgY29tcGxldGVseSBpbnRvIHZpZXcsIG1pbmltaXppbmcgdGhlIGRlZ3JlZSBvZlxuICAgICAqIHNjcm9sbGluZyBwZXJmb3JtZWQuXG4gICAgICpcbiAgICAgKiBCbGluayBoYXMgYSBgc2Nyb2xsSW50b1ZpZXdJZk5lZWRlZCgpYCBmdW5jdGlvbiB0aGF0IGRvZXMgc29tZXRoaW5nXG4gICAgICogc2ltaWxhciwgYnV0IHVuZm9ydHVuYXRlbHkgaXQncyBub24tc3RhbmRhcmQsIGFuZCBpbiBhbnkgZXZlbnQgb2Z0ZW4gZW5kc1xuICAgICAqIHVwIHNjcm9sbGluZyBtb3JlIHRoYW4gaXMgYWJzb2x1dGVseSBuZWNlc3NhcnkuXG4gICAgICpcbiAgICAgKiBAcGFyYW0ge0hUTUxFbGVtZW50fSBpdGVtIC0gdGhlIGl0ZW0gdG8gc2Nyb2xsIGludG8gdmlldy5cbiAgICAgKi9cbiAgICBzY3JvbGxJdGVtSW50b1ZpZXcoaXRlbSkge1xuICAgICAgaWYgKHN1cGVyLnNjcm9sbEl0ZW1JbnRvVmlldykgeyBzdXBlci5zY3JvbGxJdGVtSW50b1ZpZXcoKTsgfVxuICAgICAgLy8gR2V0IHRoZSByZWxhdGl2ZSBwb3NpdGlvbiBvZiB0aGUgaXRlbSB3aXRoIHJlc3BlY3QgdG8gdGhlIHRvcCBvZiB0aGVcbiAgICAgIC8vIGxpc3QncyBzY3JvbGxhYmxlIGNhbnZhcy4gQW4gaXRlbSBhdCB0aGUgdG9wIG9mIHRoZSBsaXN0IHdpbGwgaGF2ZSBhXG4gICAgICAvLyBlbGVtZW50VG9wIG9mIDAuXG5cbiAgICAgIGNvbnN0IHNjcm9sbFRhcmdldCA9IHRoaXMuc2Nyb2xsVGFyZ2V0O1xuICAgICAgY29uc3QgZWxlbWVudFRvcCA9IGl0ZW0ub2Zmc2V0VG9wIC0gc2Nyb2xsVGFyZ2V0Lm9mZnNldFRvcCAtIHNjcm9sbFRhcmdldC5jbGllbnRUb3A7XG4gICAgICBjb25zdCBlbGVtZW50Qm90dG9tID0gZWxlbWVudFRvcCArIGl0ZW0ub2Zmc2V0SGVpZ2h0O1xuICAgICAgLy8gRGV0ZXJtaW5lIHRoZSBib3R0b20gb2YgdGhlIHNjcm9sbGFibGUgY2FudmFzLlxuICAgICAgY29uc3Qgc2Nyb2xsQm90dG9tID0gc2Nyb2xsVGFyZ2V0LnNjcm9sbFRvcCArIHNjcm9sbFRhcmdldC5jbGllbnRIZWlnaHQ7XG4gICAgICBpZiAoZWxlbWVudEJvdHRvbSA+IHNjcm9sbEJvdHRvbSkge1xuICAgICAgICAvLyBTY3JvbGwgdXAgdW50aWwgaXRlbSBpcyBlbnRpcmVseSB2aXNpYmxlLlxuICAgICAgICBzY3JvbGxUYXJnZXQuc2Nyb2xsVG9wICs9IGVsZW1lbnRCb3R0b20gLSBzY3JvbGxCb3R0b207XG4gICAgICB9XG4gICAgICBlbHNlIGlmIChlbGVtZW50VG9wIDwgc2Nyb2xsVGFyZ2V0LnNjcm9sbFRvcCkge1xuICAgICAgICAvLyBTY3JvbGwgZG93biB1bnRpbCBpdGVtIGlzIGVudGlyZWx5IHZpc2libGUuXG4gICAgICAgIHNjcm9sbFRhcmdldC5zY3JvbGxUb3AgPSBlbGVtZW50VG9wO1xuICAgICAgfVxuICAgIH1cblxuICAgIC8qKlxuICAgICAqIFRoZSBlbGVtZW50IHRoYXQgc2hvdWxkIGJlIHNjcm9sbGVkIHRvIGJyaW5nIGFuIGl0ZW0gaW50byB2aWV3LlxuICAgICAqXG4gICAgICogVGhlIGRlZmF1bHQgdmFsdWUgb2YgdGhpcyBwcm9wZXJ0eSBpcyB0aGUgZWxlbWVudCBpdHNlbGYuXG4gICAgICpcbiAgICAgKiBAdHlwZSB7SFRNTEVsZW1lbnR9XG4gICAgICovXG4gICAgZ2V0IHNjcm9sbFRhcmdldCgpIHtcbiAgICAgIC8vIFByZWZlciBiYXNlIHJlc3VsdC5cbiAgICAgIHJldHVybiAnc2Nyb2xsVGFyZ2V0JyBpbiBiYXNlLnByb3RvdHlwZSA/IHN1cGVyLnNjcm9sbFRhcmdldCA6IHRoaXM7XG4gICAgfVxuICAgIHNldCBzY3JvbGxUYXJnZXQoZWxlbWVudCkge1xuICAgICAgaWYgKCdzY3JvbGxUYXJnZXQnIGluIGJhc2UucHJvdG90eXBlKSB7IHN1cGVyLnNjcm9sbFRhcmdldCA9IGVsZW1lbnQ7IH1cbiAgICB9XG5cbiAgfVxuXG4gIHJldHVybiBTZWxlY3Rpb25JblZpZXc7XG59O1xuIiwiLyogRXhwb3J0ZWQgZnVuY3Rpb24gZXh0ZW5kcyBhIGJhc2UgY2xhc3Mgd2l0aCBTaGFkb3dFbGVtZW50UmVmZXJlbmNlcy4gKi9cbmV4cG9ydCBkZWZhdWx0IChiYXNlKSA9PiB7XG5cbiAgLyoqXG4gICAqIE1peGluIHRvIGNyZWF0ZSByZWZlcmVuY2VzIHRvIGVsZW1lbnRzIGluIGEgY29tcG9uZW50J3MgU2hhZG93IERPTSBzdWJ0cmVlLlxuICAgKlxuICAgKiBUaGlzIGFkZHMgYSBtZW1iZXIgb24gdGhlIGNvbXBvbmVudCBjYWxsZWQgYHRoaXMuJGAgdGhhdCBjYW4gYmUgdXNlZCB0b1xuICAgKiByZWZlcmVuY2Ugc2hhZG93IGVsZW1lbnRzIHdpdGggSURzLiBFLmcuLCBpZiBjb21wb25lbnQncyBzaGFkb3cgY29udGFpbnMgYW5cbiAgICogZWxlbWVudCBgPGJ1dHRvbiBpZD1cImZvb1wiPmAsIHRoZW4gdGhpcyBtaXhpbiB3aWxsIGNyZWF0ZSBhIG1lbWJlclxuICAgKiBgdGhpcy4kLmZvb2AgdGhhdCBwb2ludHMgdG8gdGhhdCBidXR0b24uXG4gICAqXG4gICAqIFN1Y2ggcmVmZXJlbmNlcyBzaW1wbGlmeSBhIGNvbXBvbmVudCdzIGFjY2VzcyB0byBpdHMgb3duIGVsZW1lbnRzLiBJblxuICAgKiBleGNoYW5nZSwgdGhpcyBtaXhpbiB0cmFkZXMgb2ZmIGEgb25lLXRpbWUgY29zdCBvZiBxdWVyeWluZyBhbGwgZWxlbWVudHMgaW5cbiAgICogdGhlIHNoYWRvdyB0cmVlIGluc3RlYWQgb2YgcGF5aW5nIGFuIG9uZ29pbmcgY29zdCB0byBxdWVyeSBmb3IgYW4gZWxlbWVudFxuICAgKiBlYWNoIHRpbWUgdGhlIGNvbXBvbmVudCB3YW50cyB0byBpbnNwZWN0IG9yIG1hbmlwdWxhdGUgaXQuXG4gICAqXG4gICAqIFRoaXMgbWl4aW4gZXhwZWN0cyB0aGUgY29tcG9uZW50IHRvIGRlZmluZSBhIFNoYWRvdyBET00gc3VidHJlZS4gWW91IGNhblxuICAgKiBjcmVhdGUgdGhhdCB0cmVlIHlvdXJzZWxmLCBvciBtYWtlIHVzZSBvZlxuICAgKiBbU2hhZG93VGVtcGxhdGVNaXhpbl0oU2hhZG93VGVtcGxhdGVNaXhpbi5tZCkuXG4gICAqXG4gICAqIFRoaXMgbWl4aW4gaXMgaW5zcGlyZWQgYnkgUG9seW1lcidzIFthdXRvbWF0aWNcbiAgICogbm9kZSBmaW5kaW5nXShodHRwczovL3d3dy5wb2x5bWVyLXByb2plY3Qub3JnLzEuMC9kb2NzL2Rldmd1aWRlL2xvY2FsLWRvbS5odG1sI25vZGUtZmluZGluZylcbiAgICogZmVhdHVyZS5cbiAgICovXG4gIGNsYXNzIFNoYWRvd0VsZW1lbnRSZWZlcmVuY2VzIGV4dGVuZHMgYmFzZSB7XG5cbiAgICBjb25zdHJ1Y3RvcigpIHtcbiAgICAgIHN1cGVyKCk7XG4gICAgICBpZiAodGhpcy5zaGFkb3dSb290KSB7XG4gICAgICAgIC8vIExvb2sgZm9yIGVsZW1lbnRzIGluIHRoZSBzaGFkb3cgc3VidHJlZSB0aGF0IGhhdmUgaWQgYXR0cmlidXRlcy5cbiAgICAgICAgLy8gQW4gYWx0ZXJuYXRpdmVseSBpbXBsZW1lbnRhdGlvbiBvZiB0aGlzIG1peGluIHdvdWxkIGJlIHRvIGp1c3QgZGVmaW5lXG4gICAgICAgIC8vIGEgdGhpcy4kIGdldHRlciB0aGF0IGxhemlseSBkb2VzIHRoaXMgc2VhcmNoIHRoZSBmaXJzdCB0aW1lIHNvbWVvbmVcbiAgICAgICAgLy8gdHJpZXMgdG8gYWNjZXNzIHRoaXMuJC4gVGhhdCBtaWdodCBpbnRyb2R1Y2Ugc29tZSBjb21wbGV4aXR5IOKAkyBpZiB0aGVcbiAgICAgICAgLy8gdGhlIHRyZWUgY2hhbmdlZCBhZnRlciBpdCB3YXMgZmlyc3QgcG9wdWxhdGVkLCB0aGUgcmVzdWx0IG9mXG4gICAgICAgIC8vIHNlYXJjaGluZyBmb3IgYSBub2RlIG1pZ2h0IGJlIHNvbWV3aGF0IHVucHJlZGljdGFibGUuXG4gICAgICAgIHRoaXMuJCA9IHt9O1xuICAgICAgICBjb25zdCBub2Rlc1dpdGhJZHMgPSB0aGlzLnNoYWRvd1Jvb3QucXVlcnlTZWxlY3RvckFsbCgnW2lkXScpO1xuICAgICAgICBbXS5mb3JFYWNoLmNhbGwobm9kZXNXaXRoSWRzLCBub2RlID0+IHtcbiAgICAgICAgICBjb25zdCBpZCA9IG5vZGUuZ2V0QXR0cmlidXRlKCdpZCcpO1xuICAgICAgICAgIHRoaXMuJFtpZF0gPSBub2RlO1xuICAgICAgICB9KTtcbiAgICAgIH1cbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBUaGUgY29sbGVjdGlvbiBvZiByZWZlcmVuY2VzIHRvIHRoZSBlbGVtZW50cyB3aXRoIElEcyBpbiBhIGNvbXBvbmVudCdzXG4gICAgICogU2hhZG93IERPTSBzdWJ0cmVlLlxuICAgICAqXG4gICAgICogQHR5cGUge29iamVjdH1cbiAgICAgKiBAbWVtYmVyICRcbiAgICAgKi9cbiAgfVxuXG4gIHJldHVybiBTaGFkb3dFbGVtZW50UmVmZXJlbmNlcztcbn07XG4iLCJpbXBvcnQgc3ltYm9scyBmcm9tICcuLi9zcmMvc3ltYm9scyc7XG5cblxuLyogRXhwb3J0ZWQgZnVuY3Rpb24gZXh0ZW5kcyBhIGJhc2UgY2xhc3Mgd2l0aCBTaGFkb3dUZW1wbGF0ZS4gKi9cbmV4cG9ydCBkZWZhdWx0IChiYXNlKSA9PiB7XG5cbiAgLyoqXG4gICAqIE1peGluIGZvciBzdGFtcGluZyBhIHRlbXBsYXRlIGludG8gYSBTaGFkb3cgRE9NIHN1YnRyZWUgdXBvbiBjb21wb25lbnRcbiAgICogaW5zdGFudGlhdGlvbi5cbiAgICpcbiAgICogVG8gdXNlIHRoaXMgbWl4aW4sIGRlZmluZSBhIGB0ZW1wbGF0ZWAgcHJvcGVydHkgYXMgYSBzdHJpbmcgb3IgSFRNTFxuICAgKiBgPHRlbXBsYXRlPmAgZWxlbWVudDpcbiAgICpcbiAgICogICAgIGNsYXNzIE15RWxlbWVudCBleHRlbmRzIFNoYWRvd1RlbXBsYXRlTWl4aW4oSFRNTEVsZW1lbnQpIHtcbiAgICogICAgICAgZ2V0IFtzeW1ib2xzLnRlbXBsYXRlXSgpIHtcbiAgICogICAgICAgICByZXR1cm4gYEhlbGxvLCA8ZW0+d29ybGQ8L2VtPi5gO1xuICAgKiAgICAgICB9XG4gICAqICAgICB9XG4gICAqXG4gICAqIFdoZW4geW91ciBjb21wb25lbnQgY2xhc3MgaXMgaW5zdGFudGlhdGVkLCBhIHNoYWRvdyByb290IHdpbGwgYmUgY3JlYXRlZCBvblxuICAgKiB0aGUgaW5zdGFuY2UsIGFuZCB0aGUgY29udGVudHMgb2YgdGhlIHRlbXBsYXRlIHdpbGwgYmUgY2xvbmVkIGludG8gdGhlXG4gICAqIHNoYWRvdyByb290LiBJZiB5b3VyIGNvbXBvbmVudCBkb2VzIG5vdCBkZWZpbmUgYSBgdGVtcGxhdGVgIHByb3BlcnR5LCB0aGlzXG4gICAqIG1peGluIGhhcyBubyBlZmZlY3QuXG4gICAqXG4gICAqIEZvciB0aGUgdGltZSBiZWluZywgdGhpcyBleHRlbnNpb24gcmV0YWlucyBzdXBwb3J0IGZvciBTaGFkb3cgRE9NIHYwLiBUaGF0XG4gICAqIHdpbGwgZXZlbnR1YWxseSBiZSBkZXByZWNhdGVkIGFzIGJyb3dzZXJzIChhbmQgdGhlIFNoYWRvdyBET00gcG9seWZpbGwpXG4gICAqIGltcGxlbWVudCBTaGFkb3cgRE9NIHYxLlxuICAgKi9cbiAgY2xhc3MgU2hhZG93VGVtcGxhdGUgZXh0ZW5kcyBiYXNlIHtcblxuICAgIC8qXG4gICAgICogSWYgdGhlIGNvbXBvbmVudCBkZWZpbmVzIGEgdGVtcGxhdGUsIGEgc2hhZG93IHJvb3Qgd2lsbCBiZSBjcmVhdGVkIG9uIHRoZVxuICAgICAqIGNvbXBvbmVudCBpbnN0YW5jZSwgYW5kIHRoZSB0ZW1wbGF0ZSBzdGFtcGVkIGludG8gaXQuXG4gICAgICovXG4gICAgY29uc3RydWN0b3IoKSB7XG4gICAgICBzdXBlcigpO1xuICAgICAgbGV0IHRlbXBsYXRlID0gdGhpc1tzeW1ib2xzLnRlbXBsYXRlXTtcbiAgICAgIC8vIFRPRE86IFNhdmUgdGhlIHByb2Nlc3NlZCB0ZW1wbGF0ZSB3aXRoIHRoZSBjb21wb25lbnQncyBjbGFzcyBwcm90b3R5cGVcbiAgICAgIC8vIHNvIGl0IGRvZXNuJ3QgbmVlZCB0byBiZSBwcm9jZXNzZWQgd2l0aCBldmVyeSBpbnN0YW50aWF0aW9uLlxuICAgICAgaWYgKHRlbXBsYXRlKSB7XG5cbiAgICAgICAgaWYgKHR5cGVvZiB0ZW1wbGF0ZSA9PT0gJ3N0cmluZycpIHtcbiAgICAgICAgICAvLyBVcGdyYWRlIHBsYWluIHN0cmluZyB0byByZWFsIHRlbXBsYXRlLlxuICAgICAgICAgIHRlbXBsYXRlID0gY3JlYXRlVGVtcGxhdGVXaXRoSW5uZXJIVE1MKHRlbXBsYXRlKTtcbiAgICAgICAgfVxuXG4gICAgICAgIGlmICh3aW5kb3cuU2hhZG93RE9NUG9seWZpbGwpIHtcbiAgICAgICAgICBzaGltVGVtcGxhdGVTdHlsZXModGVtcGxhdGUsIHRoaXMubG9jYWxOYW1lKTtcbiAgICAgICAgfVxuXG4gICAgICAgIGNvbnN0IHJvb3QgPSB0aGlzLmF0dGFjaFNoYWRvdyh7IG1vZGU6ICdvcGVuJyB9KTtcbiAgICAgICAgY29uc3QgY2xvbmUgPSBkb2N1bWVudC5pbXBvcnROb2RlKHRlbXBsYXRlLmNvbnRlbnQsIHRydWUpO1xuICAgICAgICByb290LmFwcGVuZENoaWxkKGNsb25lKTtcbiAgICAgIH1cbiAgICB9XG5cbiAgfVxuXG4gIHJldHVybiBTaGFkb3dUZW1wbGF0ZTtcbn07XG5cblxuLy8gQ29udmVydCBhIHBsYWluIHN0cmluZyBvZiBIVE1MIGludG8gYSByZWFsIHRlbXBsYXRlIGVsZW1lbnQuXG5mdW5jdGlvbiBjcmVhdGVUZW1wbGF0ZVdpdGhJbm5lckhUTUwoaW5uZXJIVE1MKSB7XG4gIGNvbnN0IHRlbXBsYXRlID0gZG9jdW1lbnQuY3JlYXRlRWxlbWVudCgndGVtcGxhdGUnKTtcbiAgLy8gUkVWSUVXOiBJcyB0aGVyZSBhbiBlYXNpZXIgd2F5IHRvIGRvIHRoaXM/XG4gIC8vIFdlJ2QgbGlrZSB0byBqdXN0IHNldCBpbm5lckhUTUwgb24gdGhlIHRlbXBsYXRlIGNvbnRlbnQsIGJ1dCBzaW5jZSBpdCdzXG4gIC8vIGEgRG9jdW1lbnRGcmFnbWVudCwgdGhhdCBkb2Vzbid0IHdvcmsuXG4gIGNvbnN0IGRpdiA9IGRvY3VtZW50LmNyZWF0ZUVsZW1lbnQoJ2RpdicpO1xuICBkaXYuaW5uZXJIVE1MID0gaW5uZXJIVE1MO1xuICB3aGlsZSAoZGl2LmNoaWxkTm9kZXMubGVuZ3RoID4gMCkge1xuICAgIHRlbXBsYXRlLmNvbnRlbnQuYXBwZW5kQ2hpbGQoZGl2LmNoaWxkTm9kZXNbMF0pO1xuICB9XG4gIHJldHVybiB0ZW1wbGF0ZTtcbn1cblxuLy8gSW52b2tlIGJhc2ljIHN0eWxlIHNoaW1taW5nIHdpdGggU2hhZG93Q1NTLlxuZnVuY3Rpb24gc2hpbVRlbXBsYXRlU3R5bGVzKHRlbXBsYXRlLCB0YWcpIHtcbiAgd2luZG93LldlYkNvbXBvbmVudHMuU2hhZG93Q1NTLnNoaW1TdHlsaW5nKHRlbXBsYXRlLmNvbnRlbnQsIHRhZyk7XG59XG4iLCJpbXBvcnQgY3JlYXRlU3ltYm9sIGZyb20gJy4vY3JlYXRlU3ltYm9sJztcbmltcG9ydCBzeW1ib2xzIGZyb20gJy4vc3ltYm9scyc7XG5cblxuLy8gU3ltYm9scyBmb3IgcHJpdmF0ZSBkYXRhIG1lbWJlcnMgb24gYW4gZWxlbWVudC5cbmNvbnN0IGNhblNlbGVjdE5leHRTeW1ib2wgPSBjcmVhdGVTeW1ib2woJ2NhblNlbGVjdE5leHQnKTtcbmNvbnN0IGNhblNlbGVjdFByZXZpb3VzU3ltYm9sID0gY3JlYXRlU3ltYm9sKCdjYW5TZWxlY3RQcmV2aW91cycpO1xuY29uc3Qgc2VsZWN0aW9uUmVxdWlyZWRTeW1ib2wgPSBjcmVhdGVTeW1ib2woJ3NlbGVjdGlvblJlcXVpcmVkJyk7XG5jb25zdCBzZWxlY3Rpb25XcmFwc1N5bWJvbCA9IGNyZWF0ZVN5bWJvbCgnc2VsZWN0aW9uV3JhcHMnKTtcblxuLy8gV2Ugd2FudCB0byBleHBvc2UgYm90aCBzZWxlY3RlZEluZGV4IGFuZCBzZWxlY3RlZEl0ZW0gYXMgaW5kZXBlbmRlbnRcbi8vIHByb3BlcnRpZXMgYnV0IGtlZXAgdGhlbSBpbiBzeW5jLiBUaGlzIGFsbG93cyBhIGNvbXBvbmVudCB1c2VyIHRvIHJlZmVyZW5jZVxuLy8gdGhlIHNlbGVjdGlvbiBieSB3aGF0ZXZlciBtZWFucyBpcyBtb3N0IG5hdHVyYWwgZm9yIHRoZWlyIHNpdHVhdGlvbi5cbi8vXG4vLyBUbyBlZmZpY2llbnRseSBrZWVwIHRoZXNlIHByb3BlcnRpZXMgaW4gc3luYywgd2UgdHJhY2sgXCJleHRlcm5hbFwiIGFuZFxuLy8gXCJpbnRlcm5hbFwiIHJlZmVyZW5jZXMgZm9yIGVhY2ggcHJvcGVydHk6XG4vL1xuLy8gVGhlIGV4dGVybmFsIGluZGV4IG9yIGl0ZW0gaXMgdGhlIG9uZSB3ZSByZXBvcnQgdG8gdGhlIG91dHNpZGUgd29ybGQgd2hlblxuLy8gYXNrZWQgZm9yIHNlbGVjdGlvbi4gIFdoZW4gaGFuZGxpbmcgYSBjaGFuZ2UgdG8gaW5kZXggb3IgaXRlbSwgd2UgdXBkYXRlIHRoZVxuLy8gZXh0ZXJuYWwgcmVmZXJlbmNlIGFzIHNvb24gYXMgcG9zc2libGUsIHNvIHRoYXQgaWYgYW55b25lIGltbWVkaWF0ZWx5IGFza3Ncbi8vIGZvciB0aGUgY3VycmVudCBzZWxlY3Rpb24sIHRoZXkgd2lsbCByZWNlaXZlIGEgc3RhYmxlIGFuc3dlci5cbi8vXG4vLyBUaGUgaW50ZXJuYWwgaW5kZXggb3IgaXRlbSB0cmFja3Mgd2hpY2hldmVyIGluZGV4IG9yIGl0ZW0gbGFzdCByZWNlaXZlZCB0aGVcbi8vIGZ1bGwgc2V0IG9mIHByb2Nlc3NpbmcuIFByb2Nlc3NpbmcgaW5jbHVkZXMgcmFpc2luZyBhIGNoYW5nZSBldmVudCBmb3IgdGhlXG4vLyBuZXcgdmFsdWUuIE9uY2Ugd2UndmUgYmVndW4gdGhhdCBwcm9jZXNzaW5nLCB3ZSBzdG9yZSB0aGUgbmV3IHZhbHVlIGFzIHRoZVxuLy8gaW50ZXJuYWwgdmFsdWUgdG8gaW5kaWNhdGUgd2UndmUgaGFuZGxlZCBpdC5cbi8vXG5jb25zdCBleHRlcm5hbFNlbGVjdGVkSW5kZXhTeW1ib2wgPSBjcmVhdGVTeW1ib2woJ2V4dGVybmFsU2VsZWN0ZWRJbmRleCcpO1xuY29uc3QgZXh0ZXJuYWxTZWxlY3RlZEl0ZW1TeW1ib2wgPSBjcmVhdGVTeW1ib2woJ2V4dGVybmFsU2VsZWN0ZWRJdGVtJyk7XG5jb25zdCBpbnRlcm5hbFNlbGVjdGVkSW5kZXhTeW1ib2wgPSBjcmVhdGVTeW1ib2woJ2ludGVybmFsU2VsZWN0ZWRJbmRleCcpO1xuY29uc3QgaW50ZXJuYWxTZWxlY3RlZEl0ZW1TeW1ib2wgPSBjcmVhdGVTeW1ib2woJ2ludGVybmFsU2VsZWN0ZWRJdGVtJyk7XG5cblxuLyogRXhwb3J0ZWQgZnVuY3Rpb24gZXh0ZW5kcyBhIGJhc2UgY2xhc3Mgd2l0aCBTaW5nbGVTZWxlY3Rpb24uICovXG5leHBvcnQgZGVmYXVsdCAoYmFzZSkgPT4ge1xuXG4gIC8qKlxuICAgKiBNaXhpbiB3aGljaCBtYW5hZ2VzIHNpbmdsZS1zZWxlY3Rpb24gc2VtYW50aWNzIGZvciBpdGVtcyBpbiBhIGxpc3QuXG4gICAqXG4gICAqIFRoaXMgbWl4aW4gZXhwZWN0cyBhIGNvbXBvbmVudCB0byBwcm92aWRlIGFuIGBpdGVtc2AgQXJyYXkgb3IgTm9kZUxpc3Qgb2ZcbiAgICogYWxsIGVsZW1lbnRzIGluIHRoZSBsaXN0LiBBIHN0YW5kYXJkIHdheSB0byBkbyB0aGF0IHdpdGggaXMgdGhlXG4gICAqIFtDb250ZW50SXRlbXNNaXhpbl0oQ29udGVudEl0ZW1zTWl4aW4ubWQpLCB3aGljaCB0YWtlcyBhIGNvbXBvbmVudCdzXG4gICAqIGNvbnRlbnQgKHR5cGljYWxseSBpdHMgZGlzdHJpYnV0ZWQgY2hpbGRyZW4pIGFzIHRoZSBzZXQgb2YgbGlzdCBpdGVtczsgc2VlXG4gICAqIHRoYXQgbWl4aW4gZm9yIGRldGFpbHMuXG4gICAqXG4gICAqIFRoaXMgbWl4aW4gdHJhY2tzIGEgc2luZ2xlIHNlbGVjdGVkIGl0ZW0gaW4gdGhlIGxpc3QsIGFuZCBwcm92aWRlcyBtZWFucyB0b1xuICAgKiBnZXQgYW5kIHNldCB0aGF0IHN0YXRlIGJ5IGl0ZW0gcG9zaXRpb24gKGBzZWxlY3RlZEluZGV4YCkgb3IgaXRlbSBpZGVudGl0eVxuICAgKiAoYHNlbGVjdGVkSXRlbWApLiBUaGUgc2VsZWN0aW9uIGNhbiBiZSBtb3ZlZCBpbiB0aGUgbGlzdCB2aWEgdGhlIG1ldGhvZHNcbiAgICogYHNlbGVjdEZpcnN0YCwgYHNlbGVjdExhc3RgLCBgc2VsZWN0TmV4dGAsIGFuZCBgc2VsZWN0UHJldmlvdXNgLlxuICAgKlxuICAgKiBUaGlzIG1peGluIGRvZXMgbm90IHByb2R1Y2UgYW55IHVzZXItdmlzaWJsZSBlZmZlY3RzIHRvIHJlcHJlc2VudFxuICAgKiBzZWxlY3Rpb24uIE90aGVyIG1peGlucywgc3VjaCBhc1xuICAgKiBbU2VsZWN0aW9uQXJpYUFjdGl2ZU1peGluXShTZWxlY3Rpb25BcmlhQWN0aXZlTWl4aW4ubWQpLFxuICAgKiBbU2VsZWN0aW9uSGlnaGxpZ2h0TWl4aW5dKFNlbGVjdGlvbkhpZ2hsaWdodE1peGluLm1kKSBhbmRcbiAgICogW1NlbGVjdGlvbkluVmlld01peGluXShTZWxlY3Rpb25JblZpZXdNaXhpbi5tZCksIG1vZGlmeSB0aGUgc2VsZWN0ZWQgaXRlbVxuICAgKiBpbiBjb21tb24gd2F5cyB0byBsZXQgdGhlIHVzZXIga25vdyBhIGdpdmVuIGl0ZW0gaXMgc2VsZWN0ZWQgb3Igbm90XG4gICAqIHNlbGVjdGVkLlxuICAgKi9cbiAgY2xhc3MgU2luZ2xlU2VsZWN0aW9uIGV4dGVuZHMgYmFzZSB7XG5cbiAgICBjb25zdHJ1Y3RvcigpIHtcbiAgICAgIHN1cGVyKCk7XG4gICAgICAvLyBTZXQgZGVmYXVsdHMuXG4gICAgICBpZiAodHlwZW9mIHRoaXMuc2VsZWN0aW9uUmVxdWlyZWQgPT09ICd1bmRlZmluZWQnKSB7XG4gICAgICAgIHRoaXMuc2VsZWN0aW9uUmVxdWlyZWQgPSB0aGlzW3N5bWJvbHMuZGVmYXVsdHNdLnNlbGVjdGlvblJlcXVpcmVkO1xuICAgICAgfVxuICAgICAgaWYgKHR5cGVvZiB0aGlzLnNlbGVjdGlvbldyYXBzID09PSAndW5kZWZpbmVkJykge1xuICAgICAgICB0aGlzLnNlbGVjdGlvbldyYXBzID0gdGhpc1tzeW1ib2xzLmRlZmF1bHRzXS5zZWxlY3Rpb25XcmFwcztcbiAgICAgIH1cbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBUcnVlIGlmIHRoZSBzZWxlY3Rpb24gY2FuIGJlIG1vdmVkIHRvIHRoZSBuZXh0IGl0ZW0sIGZhbHNlIGlmIG5vdCAodGhlXG4gICAgICogc2VsZWN0ZWQgaXRlbSBpcyB0aGUgbGFzdCBpdGVtIGluIHRoZSBsaXN0KS5cbiAgICAgKlxuICAgICAqIEB0eXBlIHtib29sZWFufVxuICAgICAqL1xuICAgIGdldCBjYW5TZWxlY3ROZXh0KCkge1xuICAgICAgcmV0dXJuIHRoaXNbY2FuU2VsZWN0TmV4dFN5bWJvbF07XG4gICAgfVxuICAgIHNldCBjYW5TZWxlY3ROZXh0KGNhblNlbGVjdE5leHQpIHtcbiAgICAgIGNvbnN0IHByZXZpb3VzQ2FuU2VsZWN0TmV4dCA9IHRoaXNbY2FuU2VsZWN0TmV4dFN5bWJvbF07XG4gICAgICB0aGlzW2NhblNlbGVjdE5leHRTeW1ib2xdID0gY2FuU2VsZWN0TmV4dDtcbiAgICAgIGlmICgnY2FuU2VsZWN0TmV4dCcgaW4gYmFzZS5wcm90b3R5cGUpIHsgc3VwZXIuY2FuU2VsZWN0TmV4dCA9IGNhblNlbGVjdE5leHQ7IH1cbiAgICAgIGlmIChjYW5TZWxlY3ROZXh0ICE9PSBwcmV2aW91c0NhblNlbGVjdE5leHQpIHtcbiAgICAgICAgdGhpcy5kaXNwYXRjaEV2ZW50KG5ldyBDdXN0b21FdmVudCgnY2FuLXNlbGVjdC1uZXh0LWNoYW5nZWQnKSk7XG4gICAgICB9XG4gICAgfVxuXG4gICAgLyoqXG4gICAgICogVHJ1ZSBpZiB0aGUgc2VsZWN0aW9uIGNhbiBiZSBtb3ZlZCB0byB0aGUgcHJldmlvdXMgaXRlbSwgZmFsc2UgaWYgbm90XG4gICAgICogKHRoZSBzZWxlY3RlZCBpdGVtIGlzIHRoZSBmaXJzdCBvbmUgaW4gdGhlIGxpc3QpLlxuICAgICAqXG4gICAgICogQHR5cGUge2Jvb2xlYW59XG4gICAgICovXG4gICAgZ2V0IGNhblNlbGVjdFByZXZpb3VzKCkge1xuICAgICAgcmV0dXJuIHRoaXNbY2FuU2VsZWN0UHJldmlvdXNTeW1ib2xdO1xuICAgIH1cbiAgICBzZXQgY2FuU2VsZWN0UHJldmlvdXMoY2FuU2VsZWN0UHJldmlvdXMpIHtcbiAgICAgIGNvbnN0IHByZXZpb3VzQ2FuU2VsZWN0UHJldmlvdXMgPSB0aGlzW2NhblNlbGVjdFByZXZpb3VzU3ltYm9sXTtcbiAgICAgIHRoaXNbY2FuU2VsZWN0UHJldmlvdXNTeW1ib2xdID0gY2FuU2VsZWN0UHJldmlvdXM7XG4gICAgICBpZiAoJ2NhblNlbGVjdFByZXZpb3VzJyBpbiBiYXNlLnByb3RvdHlwZSkgeyBzdXBlci5jYW5TZWxlY3RQcmV2aW91cyA9IGNhblNlbGVjdFByZXZpb3VzOyB9XG4gICAgICBpZiAoY2FuU2VsZWN0UHJldmlvdXMgIT09IHByZXZpb3VzQ2FuU2VsZWN0UHJldmlvdXMpIHtcbiAgICAgICAgdGhpcy5kaXNwYXRjaEV2ZW50KG5ldyBDdXN0b21FdmVudCgnY2FuLXNlbGVjdC1wcmV2aW91cy1jaGFuZ2VkJykpO1xuICAgICAgfVxuICAgIH1cblxuICAgIGdldCBbc3ltYm9scy5kZWZhdWx0c10oKSB7XG4gICAgICBjb25zdCBkZWZhdWx0cyA9IHN1cGVyW3N5bWJvbHMuZGVmYXVsdHNdIHx8IHt9O1xuICAgICAgZGVmYXVsdHMuc2VsZWN0aW9uUmVxdWlyZWQgPSBmYWxzZTtcbiAgICAgIGRlZmF1bHRzLnNlbGVjdGlvbldyYXBzID0gZmFsc2U7XG4gICAgICByZXR1cm4gZGVmYXVsdHM7XG4gICAgfVxuXG4gICAgLyoqXG4gICAgICogSGFuZGxlIGEgbmV3IGl0ZW0gYmVpbmcgYWRkZWQgdG8gdGhlIGxpc3QuXG4gICAgICpcbiAgICAgKiBUaGUgZGVmYXVsdCBpbXBsZW1lbnRhdGlvbiBvZiB0aGlzIG1ldGhvZCBzaW1wbHkgc2V0cyB0aGUgaXRlbSdzXG4gICAgICogc2VsZWN0aW9uIHN0YXRlIHRvIGZhbHNlLlxuICAgICAqXG4gICAgICogQHBhcmFtIHtIVE1MRWxlbWVudH0gaXRlbSAtIHRoZSBpdGVtIGJlaW5nIGFkZGVkXG4gICAgICovXG4gICAgW3N5bWJvbHMuaXRlbUFkZGVkXShpdGVtKSB7XG4gICAgICBpZiAoc3VwZXJbc3ltYm9scy5pdGVtQWRkZWRdKSB7IHN1cGVyW3N5bWJvbHMuaXRlbUFkZGVkXShpdGVtKTsgfVxuICAgICAgdGhpc1tzeW1ib2xzLml0ZW1TZWxlY3RlZF0oaXRlbSwgaXRlbSA9PT0gdGhpcy5zZWxlY3RlZEl0ZW0pO1xuICAgIH1cblxuICAgIFtzeW1ib2xzLml0ZW1zQ2hhbmdlZF0oKSB7XG4gICAgICBpZiAoc3VwZXJbc3ltYm9scy5pdGVtc0NoYW5nZWRdKSB7IHN1cGVyW3N5bWJvbHMuaXRlbXNDaGFuZ2VkXSgpOyB9XG5cbiAgICAgIC8vIEluIGNhc2Ugc2VsZWN0ZWQgaXRlbSBjaGFuZ2VkIHBvc2l0aW9uIG9yIHdhcyByZW1vdmVkLlxuICAgICAgdHJhY2tTZWxlY3RlZEl0ZW0odGhpcyk7XG5cbiAgICAgIC8vIEluIGNhc2UgdGhlIGNoYW5nZSBpbiBpdGVtcyBhZmZlY3RlZCB3aGljaCBuYXZpZ2F0aW9ucyBhcmUgcG9zc2libGUuXG4gICAgICB1cGRhdGVQb3NzaWJsZU5hdmlnYXRpb25zKHRoaXMpO1xuICAgIH1cblxuICAgIC8qKlxuICAgICAqIEFwcGx5IHRoZSBpbmRpY2F0ZSBzZWxlY3Rpb24gc3RhdGUgdG8gdGhlIGl0ZW0uXG4gICAgICpcbiAgICAgKiBUaGUgZGVmYXVsdCBpbXBsZW1lbnRhdGlvbiBvZiB0aGlzIG1ldGhvZCBkb2VzIG5vdGhpbmcuIFVzZXItdmlzaWJsZVxuICAgICAqIGVmZmVjdHMgd2lsbCB0eXBpY2FsbHkgYmUgaGFuZGxlZCBieSBvdGhlciBtaXhpbnMuXG4gICAgICpcbiAgICAgKiBAcGFyYW0ge0hUTUxFbGVtZW50fSBpdGVtIC0gdGhlIGl0ZW0gYmVpbmcgc2VsZWN0ZWQvZGVzZWxlY3RlZFxuICAgICAqIEBwYXJhbSB7Ym9vbGVhbn0gc2VsZWN0ZWQgLSB0cnVlIGlmIHRoZSBpdGVtIGlzIHNlbGVjdGVkLCBmYWxzZSBpZiBub3RcbiAgICAgKi9cbiAgICBbc3ltYm9scy5pdGVtU2VsZWN0ZWRdKGl0ZW0sIHNlbGVjdGVkKSB7XG4gICAgICBpZiAoc3VwZXJbc3ltYm9scy5pdGVtU2VsZWN0ZWRdKSB7IHN1cGVyW3N5bWJvbHMuaXRlbVNlbGVjdGVkXShpdGVtLCBzZWxlY3RlZCk7IH1cbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBUaGUgaW5kZXggb2YgdGhlIGl0ZW0gd2hpY2ggaXMgY3VycmVudGx5IHNlbGVjdGVkLlxuICAgICAqXG4gICAgICogQSBgc2VsZWN0ZWRJbmRleGAgb2YgLTEgaW5kaWNhdGVzIHRoZXJlIGlzIG5vIHNlbGVjdGlvbi4gU2V0dGluZyB0aGlzXG4gICAgICogcHJvcGVydHkgdG8gLTEgd2lsbCByZW1vdmUgYW55IGV4aXN0aW5nIHNlbGVjdGlvbi5cbiAgICAgKlxuICAgICAqIEB0eXBlIHtudW1iZXJ9XG4gICAgICovXG4gICAgZ2V0IHNlbGVjdGVkSW5kZXgoKSB7XG4gICAgICByZXR1cm4gdGhpc1tleHRlcm5hbFNlbGVjdGVkSW5kZXhTeW1ib2xdICE9IG51bGwgP1xuICAgICAgICB0aGlzW2V4dGVybmFsU2VsZWN0ZWRJbmRleFN5bWJvbF0gOlxuICAgICAgICAtMTtcbiAgICB9XG4gICAgc2V0IHNlbGVjdGVkSW5kZXgoaW5kZXgpIHtcbiAgICAgIC8vIFNlZSBub3RlcyBhdCB0b3AgYWJvdXQgaW50ZXJuYWwgdnMuIGV4dGVybmFsIGNvcGllcyBvZiB0aGlzIHByb3BlcnR5LlxuICAgICAgY29uc3QgcHJldmlvdXNTZWxlY3RlZEluZGV4ID0gdGhpc1tpbnRlcm5hbFNlbGVjdGVkSW5kZXhTeW1ib2xdO1xuICAgICAgbGV0IGl0ZW07XG4gICAgICBpZiAoaW5kZXggIT09IHRoaXNbZXh0ZXJuYWxTZWxlY3RlZEluZGV4U3ltYm9sXSkge1xuICAgICAgICAvLyBTdG9yZSB0aGUgbmV3IGluZGV4IGFuZCB0aGUgY29ycmVzcG9uZGluZyBpdGVtLlxuICAgICAgICBjb25zdCBpdGVtcyA9IHRoaXMuaXRlbXM7XG4gICAgICAgIGNvbnN0IGhhc0l0ZW1zID0gaXRlbXMgJiYgaXRlbXMubGVuZ3RoID4gMDtcbiAgICAgICAgaWYgKCEoaGFzSXRlbXMgJiYgaW5kZXggPj0gMCAmJiBpbmRleCA8IGl0ZW1zLmxlbmd0aCkpIHtcbiAgICAgICAgICBpbmRleCA9IC0xOyAvLyBObyBpdGVtIGF0IHRoYXQgaW5kZXguXG4gICAgICAgIH1cbiAgICAgICAgdGhpc1tleHRlcm5hbFNlbGVjdGVkSW5kZXhTeW1ib2xdID0gaW5kZXg7XG4gICAgICAgIGl0ZW0gPSBoYXNJdGVtcyAmJiBpbmRleCA+PSAwID8gaXRlbXNbaW5kZXhdIDogbnVsbDtcbiAgICAgICAgdGhpc1tleHRlcm5hbFNlbGVjdGVkSXRlbVN5bWJvbF0gPSBpdGVtO1xuICAgICAgfSBlbHNlIHtcbiAgICAgICAgaXRlbSA9IHRoaXNbZXh0ZXJuYWxTZWxlY3RlZEl0ZW1TeW1ib2xdO1xuICAgICAgfVxuXG4gICAgICAvLyBOb3cgbGV0IHN1cGVyIGRvIGFueSB3b3JrLlxuICAgICAgaWYgKCdzZWxlY3RlZEluZGV4JyBpbiBiYXNlLnByb3RvdHlwZSkgeyBzdXBlci5zZWxlY3RlZEluZGV4ID0gaW5kZXg7IH1cblxuICAgICAgaWYgKGluZGV4ICE9PSBwcmV2aW91c1NlbGVjdGVkSW5kZXgpIHtcbiAgICAgICAgLy8gVGhlIHNlbGVjdGVkIGluZGV4IGNoYW5nZWQuXG4gICAgICAgIHRoaXNbaW50ZXJuYWxTZWxlY3RlZEluZGV4U3ltYm9sXSA9IGluZGV4O1xuXG4gICAgICAgIGNvbnN0IGV2ZW50ID0gbmV3IEN1c3RvbUV2ZW50KCdzZWxlY3RlZC1pbmRleC1jaGFuZ2VkJywge1xuICAgICAgICAgIGRldGFpbDoge1xuICAgICAgICAgICAgc2VsZWN0ZWRJbmRleDogaW5kZXgsXG4gICAgICAgICAgICB2YWx1ZTogaW5kZXggLy8gZm9yIFBvbHltZXIgYmluZGluZy4gVE9ETzogVmVyaWZ5IHN0aWxsIG5lY2Vzc2FyeVxuICAgICAgICAgIH1cbiAgICAgICAgfSk7XG4gICAgICAgIHRoaXMuZGlzcGF0Y2hFdmVudChldmVudCk7XG4gICAgICB9XG5cbiAgICAgIGlmICh0aGlzW2ludGVybmFsU2VsZWN0ZWRJdGVtU3ltYm9sXSAhPT0gaXRlbSkge1xuICAgICAgICAvLyBVcGRhdGUgc2VsZWN0ZWRJdGVtIHByb3BlcnR5IHNvIGl0IGNhbiBoYXZlIGl0cyBvd24gZWZmZWN0cy5cbiAgICAgICAgdGhpcy5zZWxlY3RlZEl0ZW0gPSBpdGVtO1xuICAgICAgfVxuICAgIH1cblxuICAgIC8qKlxuICAgICAqIFRoZSBjdXJyZW50bHkgc2VsZWN0ZWQgaXRlbSwgb3IgbnVsbCBpZiB0aGVyZSBpcyBubyBzZWxlY3Rpb24uXG4gICAgICpcbiAgICAgKiBTZXR0aW5nIHRoaXMgcHJvcGVydHkgdG8gbnVsbCBkZXNlbGVjdHMgYW55IGN1cnJlbnRseS1zZWxlY3RlZCBpdGVtLlxuICAgICAqIFNldHRpbmcgdGhpcyBwcm9wZXJ0eSB0byBhbiBvYmplY3QgdGhhdCBpcyBub3QgaW4gdGhlIGxpc3QgaGFzIG5vIGVmZmVjdC5cbiAgICAgKlxuICAgICAqIFRPRE86IEV2ZW4gaWYgc2VsZWN0aW9uUmVxdWlyZWQsIGNhbiBzdGlsbCBleHBsaWNpdGx5IHNldCBzZWxlY3RlZEl0ZW0gdG8gbnVsbC5cbiAgICAgKiBUT0RPOiBJZiBzZWxlY3Rpb25SZXF1aXJlZCwgbGVhdmUgc2VsZWN0aW9uIGFsb25lP1xuICAgICAqXG4gICAgICogQHR5cGUge29iamVjdH1cbiAgICAgKi9cbiAgICBnZXQgc2VsZWN0ZWRJdGVtKCkge1xuICAgICAgcmV0dXJuIHRoaXNbZXh0ZXJuYWxTZWxlY3RlZEl0ZW1TeW1ib2xdIHx8IG51bGw7XG4gICAgfVxuICAgIHNldCBzZWxlY3RlZEl0ZW0oaXRlbSkge1xuICAgICAgLy8gU2VlIG5vdGVzIGF0IHRvcCBhYm91dCBpbnRlcm5hbCB2cy4gZXh0ZXJuYWwgY29waWVzIG9mIHRoaXMgcHJvcGVydHkuXG4gICAgICBjb25zdCBwcmV2aW91c1NlbGVjdGVkSXRlbSA9IHRoaXNbaW50ZXJuYWxTZWxlY3RlZEl0ZW1TeW1ib2xdO1xuICAgICAgbGV0IGluZGV4O1xuICAgICAgaWYgKGl0ZW0gIT09IHRoaXNbZXh0ZXJuYWxTZWxlY3RlZEl0ZW1TeW1ib2xdKSB7XG4gICAgICAgIC8vIFN0b3JlIGl0ZW0gYW5kIGxvb2sgdXAgY29ycmVzcG9uZGluZyBpbmRleC5cbiAgICAgICAgY29uc3QgaXRlbXMgPSB0aGlzLml0ZW1zO1xuICAgICAgICBjb25zdCBoYXNJdGVtcyA9IGl0ZW1zICYmIGl0ZW1zLmxlbmd0aCA+IDA7XG4gICAgICAgIGluZGV4ID0gaGFzSXRlbXMgPyBBcnJheS5wcm90b3R5cGUuaW5kZXhPZi5jYWxsKGl0ZW1zLCBpdGVtKSA6IC0xO1xuICAgICAgICB0aGlzW2V4dGVybmFsU2VsZWN0ZWRJbmRleFN5bWJvbF0gPSBpbmRleDtcbiAgICAgICAgaWYgKGluZGV4IDwgMCkge1xuICAgICAgICAgIGl0ZW0gPSBudWxsOyAvLyBUaGUgaW5kaWNhdGVkIGl0ZW0gaXNuJ3QgYWN0dWFsbHkgaW4gYGl0ZW1zYC5cbiAgICAgICAgfVxuICAgICAgICB0aGlzW2V4dGVybmFsU2VsZWN0ZWRJdGVtU3ltYm9sXSA9IGl0ZW07XG4gICAgICB9IGVsc2Uge1xuICAgICAgICBpbmRleCA9IHRoaXNbZXh0ZXJuYWxTZWxlY3RlZEluZGV4U3ltYm9sXTtcbiAgICAgIH1cblxuICAgICAgLy8gTm93IGxldCBzdXBlciBkbyBhbnkgd29yay5cbiAgICAgIGlmICgnc2VsZWN0ZWRJdGVtJyBpbiBiYXNlLnByb3RvdHlwZSkgeyBzdXBlci5zZWxlY3RlZEl0ZW0gPSBpdGVtOyB9XG5cbiAgICAgIGlmIChpdGVtICE9PSBwcmV2aW91c1NlbGVjdGVkSXRlbSkge1xuICAgICAgICAvLyBUaGUgc2VsZWN0ZWQgaXRlbSBjaGFuZ2VkLlxuICAgICAgICB0aGlzW2ludGVybmFsU2VsZWN0ZWRJdGVtU3ltYm9sXSA9IGl0ZW07XG5cbiAgICAgICAgaWYgKHByZXZpb3VzU2VsZWN0ZWRJdGVtKSB7XG4gICAgICAgICAgLy8gVXBkYXRlIHNlbGVjdGlvbiBzdGF0ZSBvZiBvbGQgaXRlbS5cbiAgICAgICAgICB0aGlzW3N5bWJvbHMuaXRlbVNlbGVjdGVkXShwcmV2aW91c1NlbGVjdGVkSXRlbSwgZmFsc2UpO1xuICAgICAgICB9XG4gICAgICAgIGlmIChpdGVtKSB7XG4gICAgICAgICAgLy8gVXBkYXRlIHNlbGVjdGlvbiBzdGF0ZSB0byBuZXcgaXRlbS5cbiAgICAgICAgICB0aGlzW3N5bWJvbHMuaXRlbVNlbGVjdGVkXShpdGVtLCB0cnVlKTtcbiAgICAgICAgfVxuXG4gICAgICAgIHVwZGF0ZVBvc3NpYmxlTmF2aWdhdGlvbnModGhpcyk7XG5cbiAgICAgICAgY29uc3QgZXZlbnQgPSBuZXcgQ3VzdG9tRXZlbnQoJ3NlbGVjdGVkLWl0ZW0tY2hhbmdlZCcsIHtcbiAgICAgICAgICBkZXRhaWw6IHtcbiAgICAgICAgICAgIHNlbGVjdGVkSXRlbTogaXRlbSxcbiAgICAgICAgICAgIHZhbHVlOiBpdGVtIC8vIGZvciBQb2x5bWVyIGJpbmRpbmdcbiAgICAgICAgICB9XG4gICAgICAgIH0pO1xuICAgICAgICB0aGlzLmRpc3BhdGNoRXZlbnQoZXZlbnQpO1xuICAgICAgfVxuXG4gICAgICBpZiAodGhpc1tpbnRlcm5hbFNlbGVjdGVkSW5kZXhTeW1ib2xdICE9PSBpbmRleCkge1xuICAgICAgICAvLyBVcGRhdGUgc2VsZWN0ZWRJbmRleCBwcm9wZXJ0eSBzbyBpdCBjYW4gaGF2ZSBpdHMgb3duIGVmZmVjdHMuXG4gICAgICAgIHRoaXMuc2VsZWN0ZWRJbmRleCA9IGluZGV4O1xuICAgICAgfVxuICAgIH1cblxuICAgIC8qKlxuICAgICAqIFNlbGVjdCB0aGUgZmlyc3QgaXRlbSBpbiB0aGUgbGlzdC5cbiAgICAgKi9cbiAgICBzZWxlY3RGaXJzdCgpIHtcbiAgICAgIGlmIChzdXBlci5zZWxlY3RGaXJzdCkgeyBzdXBlci5zZWxlY3RGaXJzdCgpOyB9XG4gICAgICByZXR1cm4gc2VsZWN0SW5kZXgodGhpcywgMCk7XG4gICAgfVxuXG4gICAgLyoqXG4gICAgICogVHJ1ZSBpZiB0aGUgbGlzdCBzaG91bGQgYWx3YXlzIGhhdmUgYSBzZWxlY3Rpb24gKGlmIGl0IGhhcyBpdGVtcykuXG4gICAgICpcbiAgICAgKiBAdHlwZSB7Ym9vbGVhbn1cbiAgICAgKiBAZGVmYXVsdCBmYWxzZVxuICAgICAqL1xuICAgIGdldCBzZWxlY3Rpb25SZXF1aXJlZCgpIHtcbiAgICAgIHJldHVybiB0aGlzW3NlbGVjdGlvblJlcXVpcmVkU3ltYm9sXTtcbiAgICB9XG4gICAgc2V0IHNlbGVjdGlvblJlcXVpcmVkKHNlbGVjdGlvblJlcXVpcmVkKSB7XG4gICAgICB0aGlzW3NlbGVjdGlvblJlcXVpcmVkU3ltYm9sXSA9IHNlbGVjdGlvblJlcXVpcmVkO1xuICAgICAgaWYgKCdzZWxlY3Rpb25SZXF1aXJlZCcgaW4gYmFzZS5wcm90b3R5cGUpIHsgc3VwZXIuc2VsZWN0aW9uUmVxdWlyZWQgPSBzZWxlY3Rpb25SZXF1aXJlZDsgfVxuICAgICAgdHJhY2tTZWxlY3RlZEl0ZW0odGhpcyk7XG4gICAgfVxuXG4gICAgLyoqXG4gICAgICogVHJ1ZSBpZiBzZWxlY3Rpb24gbmF2aWdhdGlvbnMgd3JhcCBmcm9tIGxhc3QgdG8gZmlyc3QsIGFuZCB2aWNlIHZlcnNhLlxuICAgICAqXG4gICAgICogQHR5cGUge2Jvb2xlYW59XG4gICAgICogQGRlZmF1bHQgZmFsc2VcbiAgICAgKi9cbiAgICBnZXQgc2VsZWN0aW9uV3JhcHMoKSB7XG4gICAgICByZXR1cm4gdGhpc1tzZWxlY3Rpb25XcmFwc1N5bWJvbF07XG4gICAgfVxuICAgIHNldCBzZWxlY3Rpb25XcmFwcyh2YWx1ZSkge1xuICAgICAgdGhpc1tzZWxlY3Rpb25XcmFwc1N5bWJvbF0gPSBTdHJpbmcodmFsdWUpID09PSAndHJ1ZSc7XG4gICAgICBpZiAoJ3NlbGVjdGlvbldyYXBzJyBpbiBiYXNlLnByb3RvdHlwZSkgeyBzdXBlci5zZWxlY3Rpb25XcmFwcyA9IHZhbHVlOyB9XG4gICAgICB1cGRhdGVQb3NzaWJsZU5hdmlnYXRpb25zKHRoaXMpO1xuICAgIH1cblxuICAgIC8qKlxuICAgICAqIFNlbGVjdCB0aGUgbGFzdCBpdGVtIGluIHRoZSBsaXN0LlxuICAgICAqL1xuICAgIHNlbGVjdExhc3QoKSB7XG4gICAgICBpZiAoc3VwZXIuc2VsZWN0TGFzdCkgeyBzdXBlci5zZWxlY3RMYXN0KCk7IH1cbiAgICAgIHJldHVybiBzZWxlY3RJbmRleCh0aGlzLCB0aGlzLml0ZW1zLmxlbmd0aCAtIDEpO1xuICAgIH1cblxuICAgIC8qKlxuICAgICAqIFNlbGVjdCB0aGUgbmV4dCBpdGVtIGluIHRoZSBsaXN0LlxuICAgICAqL1xuICAgIHNlbGVjdE5leHQoKSB7XG4gICAgICBpZiAoc3VwZXIuc2VsZWN0TmV4dCkgeyBzdXBlci5zZWxlY3ROZXh0KCk7IH1cbiAgICAgIHJldHVybiBzZWxlY3RJbmRleCh0aGlzLCB0aGlzLnNlbGVjdGVkSW5kZXggKyAxKTtcbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBTZWxlY3QgdGhlIHByZXZpb3VzIGl0ZW0gaW4gdGhlIGxpc3QuXG4gICAgICpcbiAgICAgKiBJZiB0aGUgbGlzdCBoYXMgbm8gc2VsZWN0aW9uLCB0aGUgbGFzdCBpdGVtIHdpbGwgYmUgc2VsZWN0ZWQuXG4gICAgICovXG4gICAgc2VsZWN0UHJldmlvdXMoKSB7XG4gICAgICBpZiAoc3VwZXIuc2VsZWN0UHJldmlvdXMpIHsgc3VwZXIuc2VsZWN0UHJldmlvdXMoKTsgfVxuICAgICAgY29uc3QgbmV3SW5kZXggPSB0aGlzLnNlbGVjdGVkSW5kZXggPCAwID9cbiAgICAgICAgdGhpcy5pdGVtcy5sZW5ndGggLSAxIDogICAgIC8vIE5vIHNlbGVjdGlvbiB5ZXQ7IHNlbGVjdCBsYXN0IGl0ZW0uXG4gICAgICAgIHRoaXMuc2VsZWN0ZWRJbmRleCAtIDE7XG4gICAgICByZXR1cm4gc2VsZWN0SW5kZXgodGhpcywgbmV3SW5kZXgpO1xuICAgIH1cblxuICAgIC8qKlxuICAgICAqIEZpcmVzIHdoZW4gdGhlIHNlbGVjdGVkSXRlbSBwcm9wZXJ0eSBjaGFuZ2VzLlxuICAgICAqXG4gICAgICogQG1lbWJlcm9mIFNpbmdsZVNlbGVjdGlvblxuICAgICAqIEBldmVudCBzZWxlY3RlZC1pdGVtLWNoYW5nZWRcbiAgICAgKiBAcGFyYW0ge0hUTUxFbGVtZW50fSBkZXRhaWwuc2VsZWN0ZWRJdGVtIFRoZSBuZXcgc2VsZWN0ZWQgaXRlbS5cbiAgICAgKiBAcGFyYW0ge0hUTUxFbGVtZW50fSBkZXRhaWwucHJldmlvdXNJdGVtIFRoZSBwcmV2aW91c2x5IHNlbGVjdGVkIGl0ZW0uXG4gICAgICovXG5cbiAgICAvKipcbiAgICAgKiBGaXJlcyB3aGVuIHRoZSBzZWxlY3RlZEluZGV4IHByb3BlcnR5IGNoYW5nZXMuXG4gICAgICpcbiAgICAgKiBAbWVtYmVyb2YgU2luZ2xlU2VsZWN0aW9uXG4gICAgICogQGV2ZW50IHNlbGVjdGVkLWluZGV4LWNoYW5nZWRcbiAgICAgKiBAcGFyYW0ge251bWJlcn0gZGV0YWlsLnNlbGVjdGVkSW5kZXggVGhlIG5ldyBzZWxlY3RlZCBpbmRleC5cbiAgICAgKi9cblxuICB9XG5cbiAgcmV0dXJuIFNpbmdsZVNlbGVjdGlvbjtcbn07XG5cblxuLy8gRW5zdXJlIHRoZSBnaXZlbiBpbmRleCBpcyB3aXRoaW4gYm91bmRzLCBhbmQgc2VsZWN0IGl0IGlmIGl0J3Mgbm90IGFscmVhZHlcbi8vIHNlbGVjdGVkLlxuZnVuY3Rpb24gc2VsZWN0SW5kZXgoZWxlbWVudCwgaW5kZXgpIHtcbiAgY29uc3QgY291bnQgPSBlbGVtZW50Lml0ZW1zLmxlbmd0aDtcblxuICBjb25zdCBib3VuZGVkSW5kZXggPSAoZWxlbWVudC5zZWxlY3Rpb25XcmFwcykgP1xuICAgIC8vIEphdmFTY3JpcHQgbW9kIGRvZXNuJ3QgaGFuZGxlIG5lZ2F0aXZlIG51bWJlcnMgdGhlIHdheSB3ZSB3YW50IHRvIHdyYXAuXG4gICAgLy8gU2VlIGh0dHA6Ly9zdGFja292ZXJmbG93LmNvbS9hLzE4NjE4MjUwLzc2NDcyXG4gICAgKChpbmRleCAlIGNvdW50KSArIGNvdW50KSAlIGNvdW50IDpcblxuICAgIC8vIEtlZXAgaW5kZXggd2l0aGluIGJvdW5kcyBvZiBhcnJheS5cbiAgICBNYXRoLm1heChNYXRoLm1pbihpbmRleCwgY291bnQgLSAxKSwgMCk7XG5cbiAgY29uc3QgcHJldmlvdXNJbmRleCA9IGVsZW1lbnQuc2VsZWN0ZWRJbmRleDtcbiAgaWYgKHByZXZpb3VzSW5kZXggIT09IGJvdW5kZWRJbmRleCkge1xuICAgIGVsZW1lbnQuc2VsZWN0ZWRJbmRleCA9IGJvdW5kZWRJbmRleDtcbiAgICByZXR1cm4gdHJ1ZTtcbiAgfSBlbHNlIHtcbiAgICByZXR1cm4gZmFsc2U7XG4gIH1cbn1cblxuLy8gRm9sbG93aW5nIGEgY2hhbmdlIGluIHRoZSBzZXQgb2YgaXRlbXMsIG9yIGluIHRoZSB2YWx1ZSBvZiB0aGVcbi8vIGBzZWxlY3Rpb25SZXF1aXJlZGAgcHJvcGVydHksIHJlYWNxdWlyZSB0aGUgc2VsZWN0ZWQgaXRlbS4gSWYgaXQncyBtb3ZlZCxcbi8vIHVwZGF0ZSBgc2VsZWN0ZWRJbmRleGAuIElmIGl0J3MgYmVlbiByZW1vdmVkLCBhbmQgYSBzZWxlY3Rpb24gaXMgcmVxdWlyZWQsXG4vLyB0cnkgdG8gc2VsZWN0IGFub3RoZXIgaXRlbS5cbmZ1bmN0aW9uIHRyYWNrU2VsZWN0ZWRJdGVtKGVsZW1lbnQpIHtcblxuICBjb25zdCBpdGVtcyA9IGVsZW1lbnQuaXRlbXM7XG4gIGNvbnN0IGl0ZW1Db3VudCA9IGl0ZW1zID8gaXRlbXMubGVuZ3RoIDogMDtcblxuICBjb25zdCBwcmV2aW91c1NlbGVjdGVkSXRlbSA9IGVsZW1lbnQuc2VsZWN0ZWRJdGVtO1xuICBpZiAoIXByZXZpb3VzU2VsZWN0ZWRJdGVtKSB7XG4gICAgLy8gTm8gaXRlbSB3YXMgcHJldmlvdXNseSBzZWxlY3RlZC5cbiAgICBpZiAoZWxlbWVudC5zZWxlY3Rpb25SZXF1aXJlZCkge1xuICAgICAgLy8gU2VsZWN0IHRoZSBmaXJzdCBpdGVtIGJ5IGRlZmF1bHQuXG4gICAgICBlbGVtZW50LnNlbGVjdGVkSW5kZXggPSAwO1xuICAgIH1cbiAgfSBlbHNlIGlmIChpdGVtQ291bnQgPT09IDApIHtcbiAgICAvLyBXZSd2ZSBsb3N0IHRoZSBzZWxlY3Rpb24sIGFuZCB0aGVyZSdzIG5vdGhpbmcgbGVmdCB0byBzZWxlY3QuXG4gICAgZWxlbWVudC5zZWxlY3RlZEl0ZW0gPSBudWxsO1xuICB9IGVsc2Uge1xuICAgIC8vIFRyeSB0byBmaW5kIHRoZSBwcmV2aW91c2x5LXNlbGVjdGVkIGl0ZW0gaW4gdGhlIGN1cnJlbnQgc2V0IG9mIGl0ZW1zLlxuICAgIGNvbnN0IGluZGV4SW5DdXJyZW50SXRlbXMgPSBBcnJheS5wcm90b3R5cGUuaW5kZXhPZi5jYWxsKGl0ZW1zLCBwcmV2aW91c1NlbGVjdGVkSXRlbSk7XG4gICAgY29uc3QgcHJldmlvdXNTZWxlY3RlZEluZGV4ID0gZWxlbWVudC5zZWxlY3RlZEluZGV4O1xuICAgIGlmIChpbmRleEluQ3VycmVudEl0ZW1zIDwgMCkge1xuICAgICAgLy8gUHJldmlvdXNseS1zZWxlY3RlZCBpdGVtIHdhcyByZW1vdmVkIGZyb20gdGhlIGl0ZW1zLlxuICAgICAgLy8gU2VsZWN0IHRoZSBpdGVtIGF0IHRoZSBzYW1lIGluZGV4IChpZiBpdCBleGlzdHMpIG9yIGFzIGNsb3NlIGFzIHBvc3NpYmxlLlxuICAgICAgY29uc3QgbmV3U2VsZWN0ZWRJbmRleCA9IE1hdGgubWluKHByZXZpb3VzU2VsZWN0ZWRJbmRleCwgaXRlbUNvdW50IC0gMSk7XG4gICAgICAvLyBTZWxlY3QgYnkgaXRlbSwgc2luY2UgaW5kZXggbWF5IGJlIHRoZSBzYW1lLCBhbmQgd2Ugd2FudCB0byByYWlzZSB0aGVcbiAgICAgIC8vIHNlbGVjdGVkLWl0ZW0tY2hhbmdlZCBldmVudC5cbiAgICAgIGVsZW1lbnQuc2VsZWN0ZWRJdGVtID0gaXRlbXNbbmV3U2VsZWN0ZWRJbmRleF07XG4gICAgfSBlbHNlIGlmIChpbmRleEluQ3VycmVudEl0ZW1zICE9PSBwcmV2aW91c1NlbGVjdGVkSW5kZXgpIHtcbiAgICAgIC8vIFByZXZpb3VzbHktc2VsZWN0ZWQgaXRlbSBzdGlsbCB0aGVyZSwgYnV0IGNoYW5nZWQgcG9zaXRpb24uXG4gICAgICBlbGVtZW50LnNlbGVjdGVkSW5kZXggPSBpbmRleEluQ3VycmVudEl0ZW1zO1xuICAgIH1cbiAgfVxufVxuXG4vLyBGb2xsb3dpbmcgYSBjaGFuZ2UgaW4gc2VsZWN0aW9uLCByZXBvcnQgd2hldGhlciBpdCdzIG5vdyBwb3NzaWJsZSB0b1xuLy8gZ28gbmV4dC9wcmV2aW91cyBmcm9tIHRoZSBnaXZlbiBpbmRleC5cbmZ1bmN0aW9uIHVwZGF0ZVBvc3NpYmxlTmF2aWdhdGlvbnMoZWxlbWVudCkge1xuICBsZXQgY2FuU2VsZWN0TmV4dDtcbiAgbGV0IGNhblNlbGVjdFByZXZpb3VzO1xuICBjb25zdCBpdGVtcyA9IGVsZW1lbnQuaXRlbXM7XG4gIGlmIChpdGVtcyA9PSBudWxsIHx8IGl0ZW1zLmxlbmd0aCA9PT0gMCkge1xuICAgIC8vIE5vIGl0ZW1zIHRvIHNlbGVjdC5cbiAgICBjYW5TZWxlY3ROZXh0ID0gZmFsc2U7XG4gICAgY2FuU2VsZWN0UHJldmlvdXMgPSBmYWxzZTtcbiAgfSBpZiAoZWxlbWVudC5zZWxlY3Rpb25XcmFwcykge1xuICAgIC8vIFNpbmNlIHRoZXJlIGFyZSBpdGVtcywgY2FuIGFsd2F5cyBnbyBuZXh0L3ByZXZpb3VzLlxuICAgIGNhblNlbGVjdE5leHQgPSB0cnVlO1xuICAgIGNhblNlbGVjdFByZXZpb3VzID0gdHJ1ZTtcbiAgfSBlbHNlIHtcbiAgICBjb25zdCBpbmRleCA9IGVsZW1lbnQuc2VsZWN0ZWRJbmRleDtcbiAgICBpZiAoaW5kZXggPCAwICYmIGl0ZW1zLmxlbmd0aCA+IDApIHtcbiAgICAgIC8vIFNwZWNpYWwgY2FzZS4gSWYgdGhlcmUgYXJlIGl0ZW1zIGJ1dCBubyBzZWxlY3Rpb24sIGRlY2xhcmUgdGhhdCBpdCdzXG4gICAgICAvLyBhbHdheXMgcG9zc2libGUgdG8gZ28gbmV4dC9wcmV2aW91cyB0byBjcmVhdGUgYSBzZWxlY3Rpb24uXG4gICAgICBjYW5TZWxlY3ROZXh0ID0gdHJ1ZTtcbiAgICAgIGNhblNlbGVjdFByZXZpb3VzID0gdHJ1ZTtcbiAgICB9IGVsc2Uge1xuICAgICAgLy8gTm9ybWFsIGNhc2U6IHdlIGhhdmUgYW4gaW5kZXggaW4gYSBsaXN0IHRoYXQgaGFzIGl0ZW1zLlxuICAgICAgY2FuU2VsZWN0UHJldmlvdXMgPSAoaW5kZXggPiAwKTtcbiAgICAgIGNhblNlbGVjdE5leHQgPSAoaW5kZXggPCBpdGVtcy5sZW5ndGggLSAxKTtcbiAgICB9XG4gIH1cbiAgaWYgKGVsZW1lbnQuY2FuU2VsZWN0TmV4dCAhPT0gY2FuU2VsZWN0TmV4dCkge1xuICAgIGVsZW1lbnQuY2FuU2VsZWN0TmV4dCA9IGNhblNlbGVjdE5leHQ7XG4gIH1cbiAgaWYgKGVsZW1lbnQuY2FuU2VsZWN0UHJldmlvdXMgIT09IGNhblNlbGVjdFByZXZpb3VzKSB7XG4gICAgZWxlbWVudC5jYW5TZWxlY3RQcmV2aW91cyA9IGNhblNlbGVjdFByZXZpb3VzO1xuICB9XG59XG4iLCJpbXBvcnQgY3JlYXRlU3ltYm9sIGZyb20gJy4vY3JlYXRlU3ltYm9sJztcbmltcG9ydCBzeW1ib2xzIGZyb20gJy4vc3ltYm9scyc7XG5cblxuLy8gU3ltYm9scyBmb3IgcHJpdmF0ZSBkYXRhIG1lbWJlcnMgb24gYW4gZWxlbWVudC5cbmNvbnN0IGRlbHRhWFN5bWJvbCA9IGNyZWF0ZVN5bWJvbCgnZGVsdGFYJyk7XG5jb25zdCBkZWx0YVlTeW1ib2wgPSBjcmVhdGVTeW1ib2woJ2RlbHRhWScpO1xuY29uc3QgbXVsdGlUb3VjaFN5bWJvbCA9IGNyZWF0ZVN5bWJvbCgnbXVsdGlUb3VjaCcpO1xuY29uc3QgcHJldmlvdXNYU3ltYm9sID0gY3JlYXRlU3ltYm9sKCdwcmV2aW91c1gnKTtcbmNvbnN0IHByZXZpb3VzWVN5bWJvbCA9IGNyZWF0ZVN5bWJvbCgncHJldmlvdXNZJyk7XG5jb25zdCBzdGFydFhTeW1ib2wgPSBjcmVhdGVTeW1ib2woJ3N0YXJ0WCcpO1xuY29uc3QgdHJhdmVsRnJhY3Rpb25TeW1ib2wgPSBjcmVhdGVTeW1ib2woJ3RyYXZlbEZyYWN0aW9uJyk7XG5cblxuLyogRXhwb3J0ZWQgZnVuY3Rpb24gZXh0ZW5kcyBhIGJhc2UgY2xhc3Mgd2l0aCBTd2lwZURpcmVjdGlvbi4gKi9cbmV4cG9ydCBkZWZhdWx0IChiYXNlKSA9PiB7XG5cbiAgLyoqXG4gICAqIE1peGluIHdoaWNoIG1hcHMgdG91Y2ggZ2VzdHVyZXMgKHN3aXBlIGxlZnQsIHN3aXBlIHJpZ2h0KSB0byBkaXJlY3Rpb25cbiAgICogc2VtYW50aWNzIChnbyByaWdodCwgZ28gbGVmdCkuXG4gICAqXG4gICAqIEJ5IGRlZmF1bHQsIHRoaXMgbWl4aW4gcHJlc2VudHMgbm8gdXNlci12aXNpYmxlIGVmZmVjdHM7IGl0IGp1c3QgaW5kaWNhdGVzXG4gICAqIGEgZGlyZWN0aW9uIGluIHdoaWNoIHRoZSB1c2VyIGlzIGN1cnJlbnRseSBzd2lwaW5nIG9yIGhhcyBmaW5pc2hlZCBzd2lwaW5nLlxuICAgKiBUbyBtYXAgdGhlIGRpcmVjdGlvbiB0byBhIGNoYW5nZSBpbiBzZWxlY3Rpb24sIHVzZVxuICAgKiBbRGlyZWN0aW9uU2VsZWN0aW9uTWl4aW5dKERpcmVjdGlvblNlbGVjdGlvbk1peGluLm1kKS5cbiAgICovXG4gIGNsYXNzIFN3aXBlRGlyZWN0aW9uIGV4dGVuZHMgYmFzZSB7XG5cbiAgICBjb25zdHJ1Y3RvcigpIHtcbiAgICAgIHN1cGVyKCk7XG5cbiAgICAgIHRoaXMudHJhdmVsRnJhY3Rpb24gPSAwO1xuXG4gICAgICAvLyBJbiBhbGwgdG91Y2ggZXZlbnRzLCBvbmx5IGhhbmRsZSBzaW5nbGUgdG91Y2hlcy4gV2UgZG9uJ3Qgd2FudCB0b1xuICAgICAgLy8gaW5hZHZlcnRlbnRseSBkbyB3b3JrIHdoZW4gdGhlIHVzZXIncyB0cnlpbmcgdG8gcGluY2gtem9vbSBmb3IgZXhhbXBsZS5cbiAgICAgIC8vIFRPRE86IEV2ZW4gYmV0dGVyIGFwcHJvYWNoIHRoYW4gYmVsb3cgd291bGQgYmUgdG8gaWdub3JlIHRvdWNoZXMgYWZ0ZXJcbiAgICAgIC8vIHRoZSBmaXJzdCBpZiB0aGUgdXNlciBoYXMgYWxyZWFkeSBiZWd1biBhIHN3aXBlLlxuICAgICAgLy8gVE9ETzogVG91Y2ggZXZlbnRzIHNob3VsZCBwcm9iYWJseSBiZSBmYWN0b3JlZCBvdXQgaW50byBpdHMgb3duIG1peGluLlxuICAgICAgaWYgKHdpbmRvdy5Qb2ludGVyRXZlbnQpIHtcbiAgICAgICAgLy8gUHJlZmVyIGxpc3RlbmluZyB0byBzdGFuZGFyZCBwb2ludGVyIGV2ZW50cy5cbiAgICAgICAgdGhpcy5hZGRFdmVudExpc3RlbmVyKCdwb2ludGVyZG93bicsIGV2ZW50ID0+IHtcbiAgICAgICAgICBpZiAoaXNFdmVudEZvclBlbk9yUHJpbWFyeVRvdWNoKGV2ZW50KSkge1xuICAgICAgICAgICAgdG91Y2hTdGFydCh0aGlzLCBldmVudC5jbGllbnRYLCBldmVudC5jbGllbnRZKTtcbiAgICAgICAgICB9XG4gICAgICAgIH0pO1xuICAgICAgICB0aGlzLmFkZEV2ZW50TGlzdGVuZXIoJ3BvaW50ZXJtb3ZlJywgZXZlbnQgPT4ge1xuICAgICAgICAgIGlmIChpc0V2ZW50Rm9yUGVuT3JQcmltYXJ5VG91Y2goZXZlbnQpKSB7XG4gICAgICAgICAgICBjb25zdCBoYW5kbGVkID0gdG91Y2hNb3ZlKHRoaXMsIGV2ZW50LmNsaWVudFgsIGV2ZW50LmNsaWVudFkpO1xuICAgICAgICAgICAgaWYgKGhhbmRsZWQpIHtcbiAgICAgICAgICAgICAgZXZlbnQucHJldmVudERlZmF1bHQoKTtcbiAgICAgICAgICAgIH1cbiAgICAgICAgICB9XG4gICAgICAgIH0pO1xuICAgICAgICB0aGlzLmFkZEV2ZW50TGlzdGVuZXIoJ3BvaW50ZXJ1cCcsIGV2ZW50ID0+IHtcbiAgICAgICAgICBpZiAoaXNFdmVudEZvclBlbk9yUHJpbWFyeVRvdWNoKGV2ZW50KSkge1xuICAgICAgICAgICAgdG91Y2hFbmQodGhpcywgZXZlbnQuY2xpZW50WCwgZXZlbnQuY2xpZW50WSk7XG4gICAgICAgICAgfVxuICAgICAgICB9KTtcbiAgICAgIH0gZWxzZSB7XG4gICAgICAgIC8vIFBvaW50ZXIgZXZlbnRzIG5vdCBzdXBwb3J0ZWQgLS0gbGlzdGVuIHRvIG9sZGVyIHRvdWNoIGV2ZW50cy5cbiAgICAgICAgdGhpcy5hZGRFdmVudExpc3RlbmVyKCd0b3VjaHN0YXJ0JywgZXZlbnQgPT4ge1xuICAgICAgICAgIGlmICh0aGlzW211bHRpVG91Y2hTeW1ib2xdKSB7XG4gICAgICAgICAgICByZXR1cm47XG4gICAgICAgICAgfSBlbHNlIGlmIChldmVudC50b3VjaGVzLmxlbmd0aCA9PT0gMSkge1xuICAgICAgICAgICAgY29uc3QgY2xpZW50WCA9IGV2ZW50LmNoYW5nZWRUb3VjaGVzWzBdLmNsaWVudFg7XG4gICAgICAgICAgICBjb25zdCBjbGllbnRZID0gZXZlbnQuY2hhbmdlZFRvdWNoZXNbMF0uY2xpZW50WTtcbiAgICAgICAgICAgIHRvdWNoU3RhcnQodGhpcywgY2xpZW50WCwgY2xpZW50WSk7XG4gICAgICAgICAgfSBlbHNlIHtcbiAgICAgICAgICAgIHRoaXNbbXVsdGlUb3VjaFN5bWJvbF0gPSB0cnVlO1xuICAgICAgICAgIH1cbiAgICAgICAgfSk7XG4gICAgICAgIHRoaXMuYWRkRXZlbnRMaXN0ZW5lcigndG91Y2htb3ZlJywgZXZlbnQgPT4ge1xuICAgICAgICAgIGlmICghdGhpc1ttdWx0aVRvdWNoU3ltYm9sXSAmJiBldmVudC50b3VjaGVzLmxlbmd0aCA9PT0gMSkge1xuICAgICAgICAgICAgY29uc3QgY2xpZW50WCA9IGV2ZW50LmNoYW5nZWRUb3VjaGVzWzBdLmNsaWVudFg7XG4gICAgICAgICAgICBjb25zdCBjbGllbnRZID0gZXZlbnQuY2hhbmdlZFRvdWNoZXNbMF0uY2xpZW50WTtcbiAgICAgICAgICAgIGNvbnN0IGhhbmRsZWQgPSB0b3VjaE1vdmUodGhpcywgY2xpZW50WCwgY2xpZW50WSk7XG4gICAgICAgICAgICBpZiAoaGFuZGxlZCkge1xuICAgICAgICAgICAgICBldmVudC5wcmV2ZW50RGVmYXVsdCgpO1xuICAgICAgICAgICAgfVxuICAgICAgICAgIH1cbiAgICAgICAgfSk7XG4gICAgICAgIHRoaXMuYWRkRXZlbnRMaXN0ZW5lcigndG91Y2hlbmQnLCBldmVudCA9PiB7XG4gICAgICAgICAgaWYgKGV2ZW50LnRvdWNoZXMubGVuZ3RoID09PSAwKSB7XG4gICAgICAgICAgICAvLyBBbGwgdG91Y2hlcyByZW1vdmVkOyBnZXN0dXJlIGlzIGNvbXBsZXRlLlxuICAgICAgICAgICAgaWYgKCF0aGlzW211bHRpVG91Y2hTeW1ib2xdKSB7XG4gICAgICAgICAgICAgIC8vIFNpbmdsZS10b3VjaCBzd2lwZSBoYXMgZmluaXNoZWQuXG4gICAgICAgICAgICAgIGNvbnN0IGNsaWVudFggPSBldmVudC5jaGFuZ2VkVG91Y2hlc1swXS5jbGllbnRYO1xuICAgICAgICAgICAgICBjb25zdCBjbGllbnRZID0gZXZlbnQuY2hhbmdlZFRvdWNoZXNbMF0uY2xpZW50WTtcbiAgICAgICAgICAgICAgdG91Y2hFbmQodGhpcywgY2xpZW50WCwgY2xpZW50WSk7XG4gICAgICAgICAgICB9XG4gICAgICAgICAgICB0aGlzW211bHRpVG91Y2hTeW1ib2xdID0gZmFsc2U7XG4gICAgICAgICAgfVxuICAgICAgICB9KTtcbiAgICAgIH1cbiAgICB9XG5cbiAgICBjb25uZWN0ZWRDYWxsYmFjaygpIHtcbiAgICAgIGlmIChzdXBlci5jb25uZWN0ZWRDYWxsYmFjaykgeyBzdXBlci5jb25uZWN0ZWRDYWxsYmFjaygpOyB9XG5cbiAgICAgIC8vIEZvciB0aGUgY29tcG9uZW50IHRvIHJlY2VpdmUgUG9pbnRlckV2ZW50cyBpbiBJRS9FZGdlLCB3ZSBuZWVkIHRvIHNldFxuICAgICAgLy8gdG91Y2gtYWN0aW9uOiBub25lLiBPbmx5IG1ha2UgdGhpcyBjaGFuZ2UgaWYgdG91Y2gtYWN0aW9uIGlzIGN1cnJlbnRseVxuICAgICAgLy8gdGhlIGRlZmF1bHQgdmFsdWUgKFwiYXV0b1wiKSwgaW4gY2FzZSB0aGUgZGV2ZWxvcGVyIGtub3dzIGJldHRlciB0aGFuIHdlXG4gICAgICAvLyBkbyB3aGF0IHRoZXkgd2FudCBpbiB0aGVpciBwYXJ0aWN1bGFyIGNvbnRleHQuXG4gICAgICBpZiAoZ2V0Q29tcHV0ZWRTdHlsZSh0aGlzKS50b3VjaEFjdGlvbiA9PT0gJ2F1dG8nKSB7XG4gICAgICAgIHRoaXMuc3R5bGUudG91Y2hBY3Rpb24gPSAnbm9uZSc7XG4gICAgICB9XG4gICAgfVxuXG4gICAgLy8gRGVmYXVsdCBpbXBsZW1lbnRhdGlvbi5cbiAgICBnZXQgW3N5bWJvbHMuZHJhZ2dpbmddKCkge1xuICAgICAgcmV0dXJuIHN1cGVyW3N5bWJvbHMuZHJhZ2dpbmddO1xuICAgIH1cbiAgICBzZXQgW3N5bWJvbHMuZHJhZ2dpbmddKHZhbHVlKSB7XG4gICAgICBpZiAoc3ltYm9scy5kcmFnZ2luZyBpbiBiYXNlLnByb3RvdHlwZSkgeyBzdXBlcltzeW1ib2xzLmRyYWdnaW5nXSA9IHZhbHVlOyB9XG4gICAgfVxuXG4gICAgLyoqXG4gICAgICogSW52b2tlZCB3aGVuIHRoZSB1c2VyIHdhbnRzIHRvIGdvL25hdmlnYXRlIGxlZnQuXG4gICAgICogVGhlIGRlZmF1bHQgaW1wbGVtZW50YXRpb24gb2YgdGhpcyBtZXRob2QgZG9lcyBub3RoaW5nLlxuICAgICAqL1xuICAgIFtzeW1ib2xzLmdvTGVmdF0oKSB7XG4gICAgICBpZiAoc3VwZXJbc3ltYm9scy5nb0xlZnRdKSB7IHJldHVybiBzdXBlcltzeW1ib2xzLmdvTGVmdF0oKTsgfVxuICAgIH1cblxuICAgIC8qKlxuICAgICAqIEludm9rZWQgd2hlbiB0aGUgdXNlciB3YW50cyB0byBnby9uYXZpZ2F0ZSByaWdodC5cbiAgICAgKiBUaGUgZGVmYXVsdCBpbXBsZW1lbnRhdGlvbiBvZiB0aGlzIG1ldGhvZCBkb2VzIG5vdGhpbmcuXG4gICAgICovXG4gICAgW3N5bWJvbHMuZ29SaWdodF0oKSB7XG4gICAgICBpZiAoc3VwZXJbc3ltYm9scy5nb1JpZ2h0XSkgeyByZXR1cm4gc3VwZXJbc3ltYm9scy5nb1JpZ2h0XSgpOyB9XG4gICAgfVxuXG4gICAgLyoqXG4gICAgICogVGhlIGRpc3RhbmNlIHRoZSBmaXJzdCB0b3VjaHBvaW50IGhhcyB0cmF2ZWxlZCBzaW5jZSB0aGUgYmVnaW5uaW5nIG9mIGFcbiAgICAgKiBkcmFnLCBleHByZXNzZWQgYXMgYSBmcmFjdGlvbiBvZiB0aGUgZWxlbWVudCdzIHdpZHRoLlxuICAgICAqXG4gICAgICogQHR5cGUgbnVtYmVyXG4gICAgICovXG4gICAgZ2V0IHRyYXZlbEZyYWN0aW9uKCkge1xuICAgICAgcmV0dXJuIHRoaXNbdHJhdmVsRnJhY3Rpb25TeW1ib2xdO1xuICAgIH1cbiAgICBzZXQgdHJhdmVsRnJhY3Rpb24odmFsdWUpIHtcbiAgICAgIHRoaXNbdHJhdmVsRnJhY3Rpb25TeW1ib2xdID0gdmFsdWU7XG4gICAgICBpZiAoJ3RyYXZlbEZyYWN0aW9uJyBpbiBiYXNlLnByb3RvdHlwZSkgeyBzdXBlci50cmF2ZWxGcmFjdGlvbiA9IHZhbHVlOyB9XG4gICAgfVxuXG4gIH1cblxuICByZXR1cm4gU3dpcGVEaXJlY3Rpb247XG59O1xuXG5cbi8vIFJldHVybiB0cnVlIGlmIHRoZSBwb2ludGVyIGV2ZW50IGlzIGZvciB0aGUgcGVuLCBvciB0aGUgcHJpbWFyeSB0b3VjaCBwb2ludC5cbmZ1bmN0aW9uIGlzRXZlbnRGb3JQZW5PclByaW1hcnlUb3VjaChldmVudCkge1xuICByZXR1cm4gZXZlbnQucG9pbnRlclR5cGUgPT09ICdwZW4nIHx8XG4gICAgICAoZXZlbnQucG9pbnRlclR5cGUgPT09ICd0b3VjaCcgJiYgZXZlbnQuaXNQcmltYXJ5KTtcbn1cblxuLypcbiAqIEludm9rZWQgd2hlbiB0aGUgdXNlciBoYXMgZmluaXNoZWQgYSB0b3VjaCBvcGVyYXRpb24uXG4gKi9cbmZ1bmN0aW9uIHRvdWNoRW5kKGVsZW1lbnQsIGNsaWVudFgsIGNsaWVudFkpIHtcbiAgZWxlbWVudFtzeW1ib2xzLmRyYWdnaW5nXSA9IGZhbHNlO1xuICBpZiAoZWxlbWVudFtkZWx0YVhTeW1ib2xdID49IDIwKSB7XG4gICAgLy8gRmluaXNoZWQgZ29pbmcgcmlnaHQgYXQgaGlnaCBzcGVlZC5cbiAgICBlbGVtZW50W3N5bWJvbHMuZ29MZWZ0XSgpO1xuICB9IGVsc2UgaWYgKGVsZW1lbnRbZGVsdGFYU3ltYm9sXSA8PSAtMjApIHtcbiAgICAvLyBGaW5pc2hlZCBnb2luZyBsZWZ0IGF0IGhpZ2ggc3BlZWQuXG4gICAgZWxlbWVudFtzeW1ib2xzLmdvUmlnaHRdKCk7XG4gIH0gZWxzZSB7XG4gICAgLy8gRmluaXNoZWQgYXQgbG93IHNwZWVkLlxuICAgIHRyYWNrVG8oZWxlbWVudCwgY2xpZW50WCk7XG4gICAgY29uc3QgdHJhdmVsRnJhY3Rpb24gPSBlbGVtZW50LnRyYXZlbEZyYWN0aW9uO1xuICAgIGlmICh0cmF2ZWxGcmFjdGlvbiA+PSAwLjUpIHtcbiAgICAgIGVsZW1lbnRbc3ltYm9scy5nb1JpZ2h0XSgpO1xuICAgIH0gZWxzZSBpZiAodHJhdmVsRnJhY3Rpb24gPD0gLTAuNSkge1xuICAgICAgZWxlbWVudFtzeW1ib2xzLmdvTGVmdF0oKTtcbiAgICB9XG4gIH1cbiAgZWxlbWVudC50cmF2ZWxGcmFjdGlvbiA9IDA7XG4gIGVsZW1lbnRbZGVsdGFYU3ltYm9sXSA9IG51bGw7XG4gIGVsZW1lbnRbZGVsdGFZU3ltYm9sXSA9IG51bGw7XG59XG5cbi8qXG4gKiBJbnZva2VkIHdoZW4gdGhlIHVzZXIgaGFzIG1vdmVkIGR1cmluZyBhIHRvdWNoIG9wZXJhdGlvbi5cbiAqL1xuZnVuY3Rpb24gdG91Y2hNb3ZlKGVsZW1lbnQsIGNsaWVudFgsIGNsaWVudFkpIHtcblxuICBlbGVtZW50W2RlbHRhWFN5bWJvbF0gPSBjbGllbnRYIC0gZWxlbWVudFtwcmV2aW91c1hTeW1ib2xdO1xuICBlbGVtZW50W2RlbHRhWVN5bWJvbF0gPSBjbGllbnRZIC0gZWxlbWVudFtwcmV2aW91c1lTeW1ib2xdO1xuICBlbGVtZW50W3ByZXZpb3VzWFN5bWJvbF0gPSBjbGllbnRYO1xuICBlbGVtZW50W3ByZXZpb3VzWVN5bWJvbF0gPSBjbGllbnRZO1xuICBpZiAoTWF0aC5hYnMoZWxlbWVudFtkZWx0YVhTeW1ib2xdKSA+IE1hdGguYWJzKGVsZW1lbnRbZGVsdGFZU3ltYm9sXSkpIHtcbiAgICAvLyBNb3ZlIHdhcyBtb3N0bHkgaG9yaXpvbnRhbC5cbiAgICB0cmFja1RvKGVsZW1lbnQsIGNsaWVudFgpO1xuICAgIC8vIEluZGljYXRlIHRoYXQgdGhlIGV2ZW50IHdhcyBoYW5kbGVkLiBJdCdkIGJlIG5pY2VyIGlmIHdlIGRpZG4ndCBoYXZlXG4gICAgLy8gdG8gZG8gdGhpcyBzbyB0aGF0LCBlLmcuLCBhIHVzZXIgY291bGQgYmUgc3dpcGluZyBsZWZ0IGFuZCByaWdodFxuICAgIC8vIHdoaWxlIHNpbXVsdGFuZW91c2x5IHNjcm9sbGluZyB1cCBhbmQgZG93bi4gKE5hdGl2ZSB0b3VjaCBhcHBzIGNhbiBkb1xuICAgIC8vIHRoYXQuKSBIb3dldmVyLCBNb2JpbGUgU2FmYXJpIHdhbnRzIHRvIGhhbmRsZSBzd2lwZSBldmVudHMgbmVhciB0aGVcbiAgICAvLyBwYWdlIGFuZCBpbnRlcnByZXQgdGhlbSBhcyBuYXZpZ2F0aW9ucy4gVG8gYXZvaWQgaGF2aW5nIGEgaG9yaXppb250YWxcbiAgICAvLyBzd2lwZSBtaXNpbnRlcHJldGVkIGFzIGEgbmF2aWdhdGlvbiwgd2UgaW5kaWNhdGUgdGhhdCB3ZSd2ZSBoYW5kbGVkXG4gICAgLy8gdGhlIGV2ZW50LCBhbmQgcHJldmVudCBkZWZhdWx0IGJlaGF2aW9yLlxuICAgIHJldHVybiB0cnVlO1xuICB9IGVsc2Uge1xuICAgIC8vIE1vdmUgd2FzIG1vc3RseSB2ZXJ0aWNhbC5cbiAgICByZXR1cm4gZmFsc2U7IC8vIE5vdCBoYW5kbGVkXG4gIH1cbn1cblxuLypcbiAqIEludm9rZWQgd2hlbiB0aGUgdXNlciBoYXMgYmVndW4gYSB0b3VjaCBvcGVyYXRpb24uXG4gKi9cbmZ1bmN0aW9uIHRvdWNoU3RhcnQoZWxlbWVudCwgY2xpZW50WCwgY2xpZW50WSkge1xuICBlbGVtZW50W3N5bWJvbHMuZHJhZ2dpbmddID0gdHJ1ZTtcbiAgZWxlbWVudFtzdGFydFhTeW1ib2xdID0gY2xpZW50WDtcbiAgZWxlbWVudFtwcmV2aW91c1hTeW1ib2xdID0gY2xpZW50WDtcbiAgZWxlbWVudFtwcmV2aW91c1lTeW1ib2xdID0gY2xpZW50WTtcbiAgZWxlbWVudFtkZWx0YVhTeW1ib2xdID0gMDtcbiAgZWxlbWVudFtkZWx0YVlTeW1ib2xdID0gMDtcbn1cblxuZnVuY3Rpb24gdHJhY2tUbyhlbGVtZW50LCB4KSB7XG4gIGNvbnN0IHdpZHRoID0gZWxlbWVudC5vZmZzZXRXaWR0aDtcbiAgY29uc3QgZHJhZ0Rpc3RhbmNlID0gZWxlbWVudFtzdGFydFhTeW1ib2xdIC0geDtcbiAgY29uc3QgZnJhY3Rpb24gPSB3aWR0aCA+IDAgP1xuICAgIGRyYWdEaXN0YW5jZSAvIHdpZHRoIDpcbiAgICAwO1xuICBlbGVtZW50LnRyYXZlbEZyYWN0aW9uID0gZnJhY3Rpb247XG59XG4iLCJpbXBvcnQgY3JlYXRlU3ltYm9sIGZyb20gJy4vY3JlYXRlU3ltYm9sJztcbmltcG9ydCBzeW1ib2xzIGZyb20gJy4vc3ltYm9scyc7XG5cblxuY29uc3QgcGxheWluZ1N5bWJvbCA9IGNyZWF0ZVN5bWJvbCgncGxheWluZycpO1xuY29uc3Qgc2VsZWN0aW9uVGltZXJEdXJhdGlvblN5bWJvbCA9IGNyZWF0ZVN5bWJvbCgnc2VsZWN0aW9uVGltZXJEdXJhdGlvbicpO1xuY29uc3QgdGltZXJUaW1lb3V0U3ltYm9sID0gY3JlYXRlU3ltYm9sKCd0aW1lclRpbWVvdXQnKTtcblxuXG4vKiBFeHBvcnRlZCBmdW5jdGlvbiBleHRlbmRzIGEgYmFzZSBjbGFzcyB3aXRoIFRpbWVyU2VsZWN0aW9uLiAqL1xuZXhwb3J0IGRlZmF1bHQgKGJhc2UpID0+IHtcblxuICAvKipcbiAgICogTWl4aW4gd2hpY2ggcHJvdmlkZXMgZm9yIGF1dG9tYXRpYyB0aW1lZCBjaGFuZ2VzIGluIHNlbGVjdGlvbi5cbiAgICpcbiAgICogVGhpcyBtaXhpbiBpcyB1c2VmdWwgZm9yIGNyZWF0aW5nIHNsaWRlc2hvdy1saWtlIGVsZW1lbnRzIHN1Y2ggYXNcbiAgICogW2Jhc2ljLXNsaWRlc2hvd10oLi4vcGFja2FnZXMvYmFzaWMtc2xpZGVzaG93KSBhbmRcbiAgICogW2Jhc2ljLXNsaWRlc2hvdy13aXRoLWNvbnRyb2xzXSguLi9wYWNrYWdlcy9iYXNpYy1zbGlkZXNob3ctd2l0aC1jb250cm9scykuXG4gICAqXG4gICAqIFR5cGljYWwgdXNhZ2U6XG4gICAqXG4gICAqICAgICBjbGFzcyBDYXJvdXNlbFdpdGhUaW1lciBleHRlbmRzIFRpbWVyU2VsZWN0aW9uTWl4aW4oQ2Fyb3VzZWwpIHt9XG4gICAqICAgICBjdXN0b21FbGVtZW50cy5kZWZpbmUoJ2Nhcm91c2VsLXdpdGgtYXJyb3dzJywgQ2Fyb3VzZWxXaXRoVGltZXIpO1xuICAgKlxuICAgKiBUaGlzIG1peGluIGV4cGVjdHMgdGhlIGNvbXBvbmVudCB0byBkZWZpbmUgYW4gYGl0ZW1zYCBwcm9wZXJ0eSwgYXMgd2VsbCBhc1xuICAgKiBgc2VsZWN0Rmlyc3RgIGFuZCBgc2VsZWN0TmV4dGAgbWV0aG9kcy4gWW91IGNhbiBpbXBsZW1lbnQgdGhvc2UgeW91cnNlbGYsXG4gICAqIG9yIHVzZSBbQ29udGVudEl0ZW1zTWl4aW5dKENvbnRlbnRJdGVtc01peGluLm1kKSBhbmRcbiAgICogW1NpbmdsZVNlbGVjdGlvbk1peGluXShTaW5nbGVTZWxlY3Rpb25NaXhpbi5tZCkuXG4gICAqL1xuICBjbGFzcyBUaW1lclNlbGVjdGlvbiBleHRlbmRzIGJhc2Uge1xuXG4gICAgY29uc3RydWN0b3IoKSB7XG4gICAgICBzdXBlcigpO1xuICAgICAgLy8gU2V0IGRlZmF1bHRzLlxuICAgICAgaWYgKHR5cGVvZiB0aGlzLnBsYXlpbmcgPT09ICd1bmRlZmluZWQnKSB7XG4gICAgICAgIHRoaXMucGxheWluZyA9IHRoaXNbc3ltYm9scy5kZWZhdWx0c10ucGxheWluZztcbiAgICAgIH1cbiAgICAgIGlmICh0eXBlb2YgdGhpcy5zZWxlY3Rpb25UaW1lckR1cmF0aW9uID09PSAndW5kZWZpbmVkJykge1xuICAgICAgICB0aGlzLnNlbGVjdGlvblRpbWVyRHVyYXRpb24gPSB0aGlzW3N5bWJvbHMuZGVmYXVsdHNdLnNlbGVjdGlvblRpbWVyRHVyYXRpb247XG4gICAgICB9XG4gICAgfVxuXG4gICAgY29udGVudENoYW5nZWQoKSB7XG4gICAgICBpZiAoc3VwZXIuY29udGVudENoYW5nZWQpIHsgc3VwZXIuY29udGVudENoYW5nZWQoKTsgfVxuICAgICAgcmVzdGFydFRpbWVyKHRoaXMpO1xuICAgIH1cblxuICAgIGdldCBbc3ltYm9scy5kZWZhdWx0c10oKSB7XG4gICAgICBjb25zdCBkZWZhdWx0cyA9IHN1cGVyW3N5bWJvbHMuZGVmYXVsdHNdIHx8IHt9O1xuICAgICAgZGVmYXVsdHMucGxheWluZyA9IGZhbHNlO1xuICAgICAgZGVmYXVsdHMuc2VsZWN0aW9uVGltZXJEdXJhdGlvbiA9IDEwMDA7XG4gICAgICByZXR1cm4gZGVmYXVsdHM7XG4gICAgfVxuXG4gICAgLyoqXG4gICAgICogQmVnaW4gYXV0b21hdGljIHByb2dyZXNzaW9uIG9mIHRoZSBzZWxlY3Rpb24uXG4gICAgICovXG4gICAgcGxheSgpIHtcbiAgICAgIGlmIChzdXBlci5wbGF5KSB7IHN1cGVyLnBsYXkoKTsgfVxuICAgICAgc3RhcnRUaW1lcih0aGlzKTtcbiAgICAgIHRoaXNbcGxheWluZ1N5bWJvbF0gPSB0cnVlO1xuICAgIH1cblxuICAgIC8qKlxuICAgICAqIFBhdXNlIGF1dG9tYXRpYyBwcm9ncmVzc2lvbiBvZiB0aGUgc2VsZWN0aW9uLlxuICAgICAqL1xuICAgIHBhdXNlKCkge1xuICAgICAgaWYgKHN1cGVyLnBhdXNlKSB7IHN1cGVyLnBhdXNlKCk7IH1cbiAgICAgIGNsZWFyVGltZXIodGhpcyk7XG4gICAgICB0aGlzW3BsYXlpbmdTeW1ib2xdID0gZmFsc2U7XG4gICAgfVxuXG4gICAgLyoqXG4gICAgICogVHJ1ZSBpZiB0aGUgc2VsZWN0aW9uIGlzIGJlaW5nIGF1dG9tYXRpY2FsbHkgYWR2YW5jZWQuXG4gICAgICpcbiAgICAgKiBAdHlwZSB7Ym9vbGVhbn1cbiAgICAgKiBAZGVmYXVsdCBmYWxzZVxuICAgICAqL1xuICAgIGdldCBwbGF5aW5nKCkge1xuICAgICAgcmV0dXJuIHRoaXNbcGxheWluZ1N5bWJvbF07XG4gICAgfVxuICAgIHNldCBwbGF5aW5nKHBsYXlpbmcpIHtcbiAgICAgIGNvbnN0IHByZXZpb3VzUGxheWluZyA9IHRoaXNbcGxheWluZ1N5bWJvbF07XG4gICAgICBjb25zdCBwYXJzZWQgPSBTdHJpbmcocGxheWluZykgPT09ICd0cnVlJzsgLy8gQ2FzdCB0byBib29sZWFuXG4gICAgICBpZiAoJ3BsYXlpbmcnIGluIGJhc2UucHJvdG90eXBlKSB7IHN1cGVyLnBsYXlpbmcgPSBwbGF5aW5nOyB9XG4gICAgICBpZiAocGFyc2VkICE9PSBwcmV2aW91c1BsYXlpbmcpIHtcbiAgICAgICAgaWYgKHBsYXlpbmcpIHtcbiAgICAgICAgICB0aGlzLnBsYXkoKTtcbiAgICAgICAgfSBlbHNlIHtcbiAgICAgICAgICB0aGlzLnBhdXNlKCk7XG4gICAgICAgIH1cbiAgICAgIH1cbiAgICB9XG5cbiAgICAvKlxuICAgICAqIFdoZW4gdGhlIHNlbGVjdGVkIGl0ZW0gY2hhbmdlcyAoYmVjYXVzZSBvZiBzb21ldGhpbmcgdGhpcyBtaXhpbiBkaWQsIG9yXG4gICAgICogd2FzIGNoYW5nZWQgYnkgYW4gb3V0c2lkZSBhZ2VudCBsaWtlIHRoZSB1c2VyKSwgd2Ugd2FpdCBiZWZvcmUgYWR2YW5jaW5nXG4gICAgICogdG8gdGhlIG5leHQgaXRlbS4gQnkgdHJpZ2dlcmluZyB0aGUgbmV4dCBpdGVtIHRoaXMgd2F5LCB3ZSBpbXBsaWNpdGx5IGdldFxuICAgICAqIGEgZGVzaXJhYmxlIGJlaGF2aW9yOiBpZiB0aGUgdXNlciBjaGFuZ2VzIHRoZSBzZWxlY3Rpb24gKGUuZy4sIGluIGFcbiAgICAgKiBjYXJvdXNlbCksIHdlIGxldCB0aGVtIHNlZSB0aGF0IHNlbGVjdGlvbiBzdGF0ZSBmb3IgYSB3aGlsZSBiZWZvcmVcbiAgICAgKiBhZHZhbmNpbmcgdGhlIHNlbGVjdGlvbiBvdXJzZWx2ZXMuXG4gICAgICovXG4gICAgZ2V0IHNlbGVjdGVkSXRlbSgpIHtcbiAgICAgIHJldHVybiBzdXBlci5zZWxlY3RlZEl0ZW07XG4gICAgfVxuICAgIHNldCBzZWxlY3RlZEl0ZW0oaXRlbSkge1xuICAgICAgaWYgKCdzZWxlY3RlZEl0ZW0nIGluIGJhc2UucHJvdG90eXBlKSB7IHN1cGVyLnNlbGVjdGVkSXRlbSA9IGl0ZW07IH1cbiAgICAgIHJlc3RhcnRUaW1lcih0aGlzKTtcbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBUaGUgdGltZSBpbiBtaWxsaXNlY29uZHMgdGhhdCB3aWxsIGVsYXBzZSBhZnRlciB0aGUgc2VsZWN0aW9uIGNoYW5nZXNcbiAgICAgKiBiZWZvcmUgdGhlIHNlbGVjdGlvbiB3aWxsIGJlIGFkdmFuY2VkIHRvIHRoZSBuZXh0IGl0ZW0gaW4gdGhlIGxpc3QuXG4gICAgICpcbiAgICAgKiBAdHlwZSB7bnVtYmVyfSAtIFRpbWUgaW4gbWlsbGlzZWNvbmRzXG4gICAgICogQGRlZmF1bHQgMTAwMCAoMSBzZWNvbmQpXG4gICAgICovXG4gICAgZ2V0IHNlbGVjdGlvblRpbWVyRHVyYXRpb24oKSB7XG4gICAgICByZXR1cm4gdGhpc1tzZWxlY3Rpb25UaW1lckR1cmF0aW9uU3ltYm9sXTtcbiAgICB9XG4gICAgc2V0IHNlbGVjdGlvblRpbWVyRHVyYXRpb24odmFsdWUpIHtcbiAgICAgIHRoaXNbc2VsZWN0aW9uVGltZXJEdXJhdGlvblN5bWJvbF0gPSBwYXJzZUludCh2YWx1ZSk7XG4gICAgICBpZiAoJ3NlbGVjdGlvblRpbWVyRHVyYXRpb24nIGluIGJhc2UucHJvdG90eXBlKSB7IHN1cGVyLnNlbGVjdGlvblRpbWVyRHVyYXRpb24gPSB2YWx1ZTsgfVxuICAgIH1cblxuICB9XG5cbiAgcmV0dXJuIFRpbWVyU2VsZWN0aW9uO1xufTtcblxuXG5mdW5jdGlvbiBjbGVhclRpbWVyKGVsZW1lbnQpIHtcbiAgaWYgKGVsZW1lbnRbdGltZXJUaW1lb3V0U3ltYm9sXSkge1xuICAgIGNsZWFyVGltZW91dChlbGVtZW50W3RpbWVyVGltZW91dFN5bWJvbF0pO1xuICAgIGVsZW1lbnRbdGltZXJUaW1lb3V0U3ltYm9sXSA9IG51bGw7XG4gIH1cbn1cblxuZnVuY3Rpb24gcmVzdGFydFRpbWVyKGVsZW1lbnQpIHtcbiAgY2xlYXJUaW1lcihlbGVtZW50KTtcbiAgaWYgKGVsZW1lbnQucGxheWluZyAmJiBlbGVtZW50Lml0ZW1zICYmIGVsZW1lbnQuaXRlbXMubGVuZ3RoID4gMCkge1xuICAgIHN0YXJ0VGltZXIoZWxlbWVudCk7XG4gIH1cbn1cblxuZnVuY3Rpb24gc3RhcnRUaW1lcihlbGVtZW50KSB7XG4gIC8vIElmIHBsYXkoKSBpcyBjYWxsZWQgbW9yZSB0aGFuIG9uY2UsIGNhbmNlbCBhbnkgZXhpc3RpbmcgdGltZXIuXG4gIGNsZWFyVGltZXIoZWxlbWVudCk7XG4gIGVsZW1lbnRbdGltZXJUaW1lb3V0U3ltYm9sXSA9IHNldFRpbWVvdXQoKCkgPT4ge1xuICAgIHNlbGVjdE5leHRXaXRoV3JhcChlbGVtZW50KTtcbiAgfSwgZWxlbWVudC5zZWxlY3Rpb25UaW1lckR1cmF0aW9uKTtcbn1cblxuLy8gU2VsZWN0IHRoZSBuZXh0IGl0ZW0sIHdyYXBwaW5nIHRvIGZpcnN0IGl0ZW0gaWYgbmVjZXNzYXJ5LlxuZnVuY3Rpb24gc2VsZWN0TmV4dFdpdGhXcmFwKGVsZW1lbnQpIHtcbiAgY29uc3QgaXRlbXMgPSBlbGVtZW50Lml0ZW1zO1xuICBpZiAoaXRlbXMgJiYgaXRlbXMubGVuZ3RoID4gMCkge1xuICAgIGlmIChlbGVtZW50LnNlbGVjdGVkSW5kZXggPT0gbnVsbCB8fCBlbGVtZW50LnNlbGVjdGVkSW5kZXggPT09IGl0ZW1zLmxlbmd0aCAtIDEpIHtcbiAgICAgIGVsZW1lbnQuc2VsZWN0Rmlyc3QoKTtcbiAgICB9IGVsc2Uge1xuICAgICAgZWxlbWVudC5zZWxlY3ROZXh0KCk7XG4gICAgfVxuICB9XG59XG4iLCJpbXBvcnQgY3JlYXRlU3ltYm9sIGZyb20gJy4uLy4uL2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL2NyZWF0ZVN5bWJvbCc7XG5pbXBvcnQgc3ltYm9scyBmcm9tICcuL3N5bWJvbHMnO1xuXG5cbi8vIFN5bWJvbHMgZm9yIHByaXZhdGUgZGF0YSBtZW1iZXJzIG9uIGFuIGVsZW1lbnQuXG5jb25zdCBhYnNvcmJEZWNlbGVyYXRpb25TeW1ib2wgPSBjcmVhdGVTeW1ib2woJ2Fic29yYkRlY2VsZXJhdGlvbicpO1xuY29uc3QgbGFzdERlbHRhWFN5bWJvbCA9IGNyZWF0ZVN5bWJvbCgnbGFzdERlbHRhWCcpO1xuY29uc3QgbGFzdFdoZWVsVGltZW91dFN5bWJvbCA9IGNyZWF0ZVN5bWJvbCgnbGFzdFdoZWVsVGltZW91dCcpO1xuY29uc3QgcG9zdE5hdmlnYXRlRGVsYXlDb21wbGV0ZVN5bWJvbCA9IGNyZWF0ZVN5bWJvbCgncG9zdE5hdmlnYXRlRGVsYXlDb21wbGV0ZScpO1xuY29uc3Qgd2hlZWxEaXN0YW5jZVN5bWJvbCA9IGNyZWF0ZVN5bWJvbCgnd2hlZWxEaXN0YW5jZScpO1xuXG5cbi8qIEV4cG9ydGVkIGZ1bmN0aW9uIGV4dGVuZHMgYSBiYXNlIGNsYXNzIHdpdGggVHJhY2twYWREaXJlY3Rpb24uICovXG5leHBvcnQgZGVmYXVsdCAoYmFzZSkgPT4ge1xuXG4gIC8qKlxuICAgKiBNaXhpbiB3aGljaCBtYXBzIGEgaG9yaXpvbnRhbCB0cmFja3BhZCBzd2lwZSBnZXN0dXJlcyAob3IgaG9yaXpvbnRhbCBtb3VzZVxuICAgKiB3aGVlbCBhY3Rpb25zKSB0byBkaXJlY3Rpb24gc2VtYW50aWNzLlxuICAgKlxuICAgKiBZb3UgY2FuIHVzZSB0aGlzIG1peGluIHdpdGggYSBtaXhpbiBsaWtlXG4gICAqIFtEaXJlY3Rpb25TZWxlY3Rpb25NaXhpbl0oRGlyZWN0aW9uU2VsZWN0aW9uTWl4aW4ubWQpIHRvIGxldCB0aGUgdXNlclxuICAgKiBjaGFuZ2UgdGhlIHNlbGVjdGlvbiB3aXRoIHRoZSB0cmFja3BhZCBvciBtb3VzZSB3aGVlbC5cbiAgICpcbiAgICogVG8gcmVzcG9uZCB0byB0aGUgdHJhY2twYWQsIHdlIGNhbiBsaXN0ZW4gdG8gdGhlIERPTSdzIFwid2hlZWxcIiBldmVudHMuXG4gICAqIFRoZXNlIGV2ZW50cyBhcmUgZmlyZWQgYXMgdGhlIHVzZXIgZHJhZ3MgdGhlaXIgZmluZ2VycyBhY3Jvc3MgYSB0cmFja3BhZC5cbiAgICogVW5mb3J0dW5hdGVseSwgYnJvd3NlcnMgYXJlIG1pc3NpbmcgYSBjcml0aWNhbCBldmVudCDigJTCoHRoZXJlIGlzIG5vIGV2ZW50XG4gICAqIHdoZW4gdGhlIHVzZXIgKnN0b3BzKiBhIGdlc3R1cmVkIG9uIHRoZSB0cmFja3BhZCBvciBtb3VzZSB3aGVlbC5cbiAgICpcbiAgICogVG8gbWFrZSB0aGluZ3Mgd29yc2UsIHRoZSBtYWluc3RyZWFtIGJyb3dzZXJzIGNvbnRpbnVlIHRvIGdlbmVyYXRlIGZha2VcbiAgICogd2hlZWwgZXZlbnRzIGV2ZW4gYWZ0ZXIgdGhlIHVzZXIgaGFzIHN0b3BwZWQgZHJhZ2dpbmcgdGhlaXIgZmluZ2Vycy4gVGhlc2VcbiAgICogZmFrZSBldmVudHMgc2ltdWxhdGUgdGhlIHVzZXIgZ3JhZHVhbGx5IHNsb3dpbmcgZG93biB0aGUgZHJhZyB1bnRpbCB0aGV5XG4gICAqIGNvbWUgdG8gYSBzbW9vdGggc3RvcC4gSW4gc29tZSBjb250ZXh0cywgdGhlc2UgZmFrZSB3aGVlbCBldmVudHMgbWlnaHQgYmVcbiAgICogaGVscGZ1bCwgYnV0IGluIHRyeWluZyB0byBzdXBwbHkgdHlwaWNhbCB0cmFja3BhZCBzd2lwZSBuYXZpZ2F0aW9uLCB0aGVzZVxuICAgKiBmYWtlIGV2ZW50cyBnZXQgaW4gdGhlIHdheS5cbiAgICpcbiAgICogVGhpcyBjb21wb25lbnQgdXNlcyBoZXVyaXN0aWNzIHRvIHdvcmsgYXJvdW5kIHRoZXNlIHByb2JsZW1zLCBidXQgdGhlXG4gICAqIGNvbXBsZXggbmF0dXJlIG9mIHRoZSBwcm9ibGVtIG1ha2UgaXQgZXh0cmVtZWx5IGRpZmZpY3VsdCB0byBhY2hpZXZlIHRoZVxuICAgKiBzYW1lIGRlZ3JlZSBvZiB0cmFja3BhZCByZXNwb25zaXZlbmVzcyBwb3NzaWJsZSB3aXRoIG5hdGl2ZSBhcHBsaWNhdGlvbnMuXG4gICAqL1xuICBjbGFzcyBUcmFja3BhZERpcmVjdGlvbiBleHRlbmRzIGJhc2Uge1xuXG4gICAgY29uc3RydWN0b3IoKSB7XG4gICAgICBzdXBlcigpO1xuICAgICAgdGhpcy5hZGRFdmVudExpc3RlbmVyKCd3aGVlbCcsIGV2ZW50ID0+IHtcbiAgICAgICAgY29uc3QgaGFuZGxlZCA9IHdoZWVsKHRoaXMsIGV2ZW50KTtcbiAgICAgICAgaWYgKGhhbmRsZWQpIHtcbiAgICAgICAgICBldmVudC5wcmV2ZW50RGVmYXVsdCgpO1xuICAgICAgICB9XG4gICAgICB9KTtcbiAgICAgIHJlc2V0V2hlZWxUcmFja2luZyh0aGlzKTtcbiAgICB9XG5cbiAgICAvLyBEZWZhdWx0IGltcGxlbWVudGF0aW9uLlxuICAgIGdldCBbc3ltYm9scy5kcmFnZ2luZ10oKSB7XG4gICAgICByZXR1cm4gc3VwZXJbc3ltYm9scy5kcmFnZ2luZ107XG4gICAgfVxuICAgIHNldCBbc3ltYm9scy5kcmFnZ2luZ10odmFsdWUpIHtcbiAgICAgIGlmIChzeW1ib2xzLmRyYWdnaW5nIGluIGJhc2UucHJvdG90eXBlKSB7IHN1cGVyW3N5bWJvbHMuZHJhZ2dpbmddID0gdmFsdWU7IH1cbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBJbnZva2VkIHdoZW4gdGhlIHVzZXIgd2FudHMgdG8gZ28vbmF2aWdhdGUgbGVmdC5cbiAgICAgKiBUaGUgZGVmYXVsdCBpbXBsZW1lbnRhdGlvbiBvZiB0aGlzIG1ldGhvZCBkb2VzIG5vdGhpbmcuXG4gICAgICovXG4gICAgW3N5bWJvbHMuZ29MZWZ0XSgpIHtcbiAgICAgIGlmIChzdXBlcltzeW1ib2xzLmdvTGVmdF0pIHsgcmV0dXJuIHN1cGVyW3N5bWJvbHMuZ29MZWZ0XSgpOyB9XG4gICAgfVxuXG4gICAgLyoqXG4gICAgICogSW52b2tlZCB3aGVuIHRoZSB1c2VyIHdhbnRzIHRvIGdvL25hdmlnYXRlIHJpZ2h0LlxuICAgICAqIFRoZSBkZWZhdWx0IGltcGxlbWVudGF0aW9uIG9mIHRoaXMgbWV0aG9kIGRvZXMgbm90aGluZy5cbiAgICAgKi9cbiAgICBbc3ltYm9scy5nb1JpZ2h0XSgpIHtcbiAgICAgIGlmIChzdXBlcltzeW1ib2xzLmdvUmlnaHRdKSB7IHJldHVybiBzdXBlcltzeW1ib2xzLmdvUmlnaHRdKCk7IH1cbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBUaGUgZGlzdGFuY2UgdGhlIHVzZXIgaGFzIG1vdmVkIHRoZSBmaXJzdCB0b3VjaHBvaW50IHNpbmNlIHRoZSBiZWdpbm5pbmdcbiAgICAgKiBvZiBhIHRyYWNrcGFkL3doZWVsIG9wZXJhdGlvbiwgZXhwcmVzc2VkIGFzIGEgZnJhY3Rpb24gb2YgdGhlIGVsZW1lbnQnc1xuICAgICAqIHdpZHRoLlxuICAgICAqXG4gICAgICogQHR5cGUgbnVtYmVyXG4gICAgICovXG4gICAgZ2V0IHRyYXZlbEZyYWN0aW9uKCkge1xuICAgICAgcmV0dXJuIHN1cGVyLnRyYXZlbEZyYWN0aW9uO1xuICAgIH1cbiAgICBzZXQgdHJhdmVsRnJhY3Rpb24odmFsdWUpIHtcbiAgICAgIGlmICgndHJhdmVsRnJhY3Rpb24nIGluIGJhc2UucHJvdG90eXBlKSB7IHN1cGVyLnRyYXZlbEZyYWN0aW9uID0gdmFsdWU7IH1cbiAgICB9XG5cbiAgfVxuXG4gIHJldHVybiBUcmFja3BhZERpcmVjdGlvbjtcbn07XG5cblxuLy8gVGltZSB3ZSB3YWl0IGZvbGxvd2luZyBhIG5hdmlnYXRpb24gYmVmb3JlIHBheWluZyBhdHRlbnRpb24gdG8gd2hlZWxcbi8vIGV2ZW50cyBhZ2Fpbi5cbmNvbnN0IFBPU1RfTkFWSUdBVEVfVElNRSA9IDI1MDtcblxuLy8gVGltZSB3ZSB3YWl0IGFmdGVyIHRoZSBsYXN0IHdoZWVsIGV2ZW50IGJlZm9yZSB3ZSByZXNldCB0aGluZ3MuXG5jb25zdCBXSEVFTF9USU1FID0gMTAwO1xuXG5cbi8vIEZvbGxvd2luZyBhIG5hdmlnYXRpb24sIHBhcnRpYWxseSByZXNldCBvdXIgd2hlZWwgdHJhY2tpbmcuXG5mdW5jdGlvbiBwb3N0TmF2aWdhdGUoZWxlbWVudCkge1xuICBlbGVtZW50LnRyYXZlbEZyYWN0aW9uID0gMDtcbiAgZWxlbWVudFt3aGVlbERpc3RhbmNlU3ltYm9sXSA9IDA7XG4gIGVsZW1lbnRbcG9zdE5hdmlnYXRlRGVsYXlDb21wbGV0ZVN5bWJvbF0gPSB0cnVlO1xuICBlbGVtZW50W2Fic29yYkRlY2VsZXJhdGlvblN5bWJvbF0gPSB0cnVlO1xuICBzZXRUaW1lb3V0KCgpID0+IHtcbiAgICBlbGVtZW50W3Bvc3ROYXZpZ2F0ZURlbGF5Q29tcGxldGVTeW1ib2xdID0gZmFsc2U7XG4gIH0sIFBPU1RfTkFWSUdBVEVfVElNRSk7XG59XG5cbi8vIFJlc2V0IGFsbCBzdGF0ZSByZWxhdGVkIHRvIHRoZSB0cmFja2luZyBvZiB0aGUgd2hlZWwuXG5mdW5jdGlvbiByZXNldFdoZWVsVHJhY2tpbmcoZWxlbWVudCkge1xuICBlbGVtZW50LnRyYXZlbEZyYWN0aW9uID0gMDtcbiAgZWxlbWVudFt3aGVlbERpc3RhbmNlU3ltYm9sXSA9IDA7XG4gIGVsZW1lbnRbbGFzdERlbHRhWFN5bWJvbF0gPSAwO1xuICBlbGVtZW50W2Fic29yYkRlY2VsZXJhdGlvblN5bWJvbF0gPSBmYWxzZTtcbiAgZWxlbWVudFtwb3N0TmF2aWdhdGVEZWxheUNvbXBsZXRlU3ltYm9sXSA9IGZhbHNlO1xuICBpZiAoZWxlbWVudFtsYXN0V2hlZWxUaW1lb3V0U3ltYm9sXSkge1xuICAgIGNsZWFyVGltZW91dChlbGVtZW50W2xhc3RXaGVlbFRpbWVvdXRTeW1ib2xdKTtcbiAgICBlbGVtZW50W2xhc3RXaGVlbFRpbWVvdXRTeW1ib2xdID0gbnVsbDtcbiAgfVxufVxuXG4vLyBEZWZpbmUgb3VyIG93biBzaWduIGZ1bmN0aW9uLCBzaW5jZSAoYXMgb2YgTWF5IDIwMTUpLCBTYWZhcmkgYW5kIElFIGRvbid0XG4vLyBzdXBwbHkgTWF0aC5zaWduKCkuXG5mdW5jdGlvbiBzaWduKHgpIHtcbiAgcmV0dXJuICh4ID09PSAwKSA/XG4gICAgMCA6XG4gICAgKHggPiAwKSA/XG4gICAgICAxIDpcbiAgICAgIC0xO1xufVxuXG4vLyBUT0RPOiBEYW1waW5nLCBvciBzb21lIG90aGVyIHRyZWF0bWVudCBmb3IgZ29pbmcgcGFzdCB0aGUgZW5kcy5cblxuLypcbiAqIEEgd2hlZWwgZXZlbnQgaGFzIGJlZW4gZ2VuZXJhdGVkLiBUaGlzIGNvdWxkIGJlIGEgcmVhbCB3aGVlbCBldmVudCwgb3IgaXRcbiAqIGNvdWxkIGJlIGZha2UgKHNlZSBub3RlcyBpbiB0aGUgaGVhZGVyKS5cbiAqXG4gKiBUaGlzIGhhbmRsZXIgdXNlcyBzZXZlcmFsIHN0cmF0ZWdpZXMgdG8gdHJ5IHRvIGFwcHJveGltYXRlIG5hdGl2ZSB0cmFja3BhZFxuICogc3dpcGUgbmF2aWdhdGlvbi5cbiAqXG4gKiBJZiB0aGUgdXNlciBoYXMgZHJhZ2dlZCBlbm91Z2ggdG8gY2F1c2UgYSBuYXZpZ2F0aW9uLCB0aGVuIGZvciBhIHNob3J0XG4gKiBkZWxheSBmb2xsb3dpbmcgdGhhdCBuYXZpZ2F0aW9uLCBzdWJzZXF1ZW50IHdoZWVsIGV2ZW50cyB3aWxsIGJlIGlnbm9yZWQuXG4gKlxuICogRnVydGhlcm1vcmUsIGZvbGx3b3dpbmcgYSBuYXZpZ2F0aW9uLCB3ZSBpZ25vcmUgYWxsIHdoZWVsIGV2ZW50cyB1bnRpbCB3ZVxuICogcmVjZWl2ZSBhdCBsZWFzdCBvbmUgZXZlbnQgd2hlcmUgdGhlIGV2ZW50J3MgZGVsdGFYIChkaXN0YW5jZSB0cmF2ZWxlZCkgaXNcbiAqICpncmVhdGVyKiB0aGFuIHRoZSBwcmV2aW91cyBldmVudCdzIGRlbHRhWC4gVGhpcyBoZWxwcyB1cyBmaWx0ZXIgb3V0IHRoZVxuICogZmFrZSB3aGVlbCBldmVudHMgZ2VuZXJhdGVkIGJ5IHRoZSBicm93c2VyIHRvIHNpbXVsYXRlIGRlY2VsZXJhdGlvbi5cbiAqXG4gKi9cbmZ1bmN0aW9uIHdoZWVsKGVsZW1lbnQsIGV2ZW50KSB7XG5cbiAgLy8gU2luY2Ugd2UgaGF2ZSBhIG5ldyB3aGVlbCBldmVudCwgcmVzZXQgb3VyIHRpbWVyIHdhaXRpbmcgZm9yIHRoZSBsYXN0XG4gIC8vIHdoZWVsIGV2ZW50IHRvIHBhc3MuXG4gIGlmIChlbGVtZW50W2xhc3RXaGVlbFRpbWVvdXRTeW1ib2xdKSB7XG4gICAgY2xlYXJUaW1lb3V0KGVsZW1lbnRbbGFzdFdoZWVsVGltZW91dFN5bWJvbF0pO1xuICB9XG4gIGVsZW1lbnRbbGFzdFdoZWVsVGltZW91dFN5bWJvbF0gPSBzZXRUaW1lb3V0KCgpID0+IHtcbiAgICB3aGVlbFRpbWVkT3V0KGVsZW1lbnQpO1xuICB9LCBXSEVFTF9USU1FKTtcblxuICBjb25zdCBkZWx0YVggPSBldmVudC5kZWx0YVg7XG4gIGNvbnN0IGRlbHRhWSA9IGV2ZW50LmRlbHRhWTtcblxuICAvLyBTZWUgaWYgZWxlbWVudCBldmVudCByZXByZXNlbnRzIGFjY2VsZXJhdGlvbiBvciBkZWNlbGVyYXRpb24uXG4gIGNvbnN0IGFjY2VsZXJhdGlvbiA9IHNpZ24oZGVsdGFYKSAqIChkZWx0YVggLSBlbGVtZW50W2xhc3REZWx0YVhTeW1ib2xdKTtcbiAgZWxlbWVudFtsYXN0RGVsdGFYU3ltYm9sXSA9IGRlbHRhWDtcblxuICBpZiAoTWF0aC5hYnMoZGVsdGFYKSA8IE1hdGguYWJzKGRlbHRhWSkpIHtcbiAgICAvLyBNb3ZlIHdhcyBtb3N0bHkgdmVydGljYWwuIFRoZSB1c2VyIG1heSBiZSB0cnlpbmcgc2Nyb2xsIHdpdGggdGhlXG4gICAgLy8gdHJhY2twYWQvd2hlZWwuIFRvIGJlIG9uIHRoZSBzYWZlLCB3ZSBpZ25vcmUgc3VjaCBldmVudHMuXG4gICAgcmV0dXJuIGZhbHNlO1xuICB9XG5cbiAgaWYgKGVsZW1lbnRbcG9zdE5hdmlnYXRlRGVsYXlDb21wbGV0ZVN5bWJvbF0pIHtcbiAgICAvLyBJdCdzIHRvbyBzb29uIGFmdGVyIGEgbmF2aWdhdGlvbjsgaWdub3JlIHRoZSBldmVudC5cbiAgICByZXR1cm4gdHJ1ZTtcbiAgfVxuXG4gIGlmIChhY2NlbGVyYXRpb24gPiAwKSB7XG4gICAgLy8gVGhlIGV2ZW50cyBhcmUgbm90IChvciBhcmUgbm8gbG9uZ2VyKSBkZWNlbGVyYXRpbmcsIHNvIHdlIGNhbiBzdGFydFxuICAgIC8vIHBheWluZyBhdHRlbnRpb24gdG8gdGhlbSBhZ2Fpbi5cbiAgICBlbGVtZW50W2Fic29yYkRlY2VsZXJhdGlvblN5bWJvbF0gPSBmYWxzZTtcbiAgfSBlbHNlIGlmIChlbGVtZW50W2Fic29yYkRlY2VsZXJhdGlvblN5bWJvbF0pIHtcbiAgICAvLyBUaGUgd2hlZWwgZXZlbnQgd2FzIGxpa2VseSBmYWtlZCB0byBzaW11bGF0ZSBkZWNlbGVyYXRpb247IGlnbm9yZSBpdC5cbiAgICByZXR1cm4gdHJ1ZTtcbiAgfVxuXG4gIGVsZW1lbnRbd2hlZWxEaXN0YW5jZVN5bWJvbF0gKz0gZGVsdGFYO1xuXG4gIC8vIFVwZGF0ZSB0aGUgdHJhdmVsIGZyYWN0aW9uIG9mIHRoZSBlbGVtZW50IGJlaW5nIG5hdmlnYXRlZC5cbiAgY29uc3Qgd2lkdGggPSBlbGVtZW50Lm9mZnNldFdpZHRoO1xuICBsZXQgdHJhdmVsRnJhY3Rpb24gPSB3aWR0aCA+IDAgP1xuICAgIGVsZW1lbnRbd2hlZWxEaXN0YW5jZVN5bWJvbF0gLyB3aWR0aCA6XG4gICAgMDtcbiAgZWxlbWVudFtzeW1ib2xzLmRyYWdnaW5nXSA9IHRydWU7XG4gIHRyYXZlbEZyYWN0aW9uID0gc2lnbih0cmF2ZWxGcmFjdGlvbikgKiBNYXRoLm1pbihNYXRoLmFicyh0cmF2ZWxGcmFjdGlvbiksIDEpO1xuICBlbGVtZW50LnRyYXZlbEZyYWN0aW9uID0gdHJhdmVsRnJhY3Rpb247XG5cbiAgLy8gSWYgdGhlIHVzZXIgaGFzIGRyYWdnZWQgZW5vdWdoIHRvIHJlYWNoIHRoZSBwcmV2aW91cy9uZXh0IGl0ZW0sIHRoZW5cbiAgLy8gY29tcGxldGUgYSBuYXZpZ2F0aW9uIHRvIHRoYXQgaXRlbS5cbiAgaWYgKHRyYXZlbEZyYWN0aW9uID09PSAxKSB7XG4gICAgZWxlbWVudFtzeW1ib2xzLmRyYWdnaW5nXSA9IGZhbHNlO1xuICAgIGVsZW1lbnRbc3ltYm9scy5nb1JpZ2h0XSgpO1xuICAgIHBvc3ROYXZpZ2F0ZShlbGVtZW50KTtcbiAgfSBlbHNlIGlmICh0cmF2ZWxGcmFjdGlvbiA9PT0gLTEpIHtcbiAgICBlbGVtZW50W3N5bWJvbHMuZHJhZ2dpbmddID0gZmFsc2U7XG4gICAgZWxlbWVudFtzeW1ib2xzLmdvTGVmdF0oKTtcbiAgICBwb3N0TmF2aWdhdGUoZWxlbWVudCk7XG4gIH1cblxuICByZXR1cm4gdHJ1ZTtcbn1cblxuLy8gQSBzdWZmaWNpZW50bHkgbG9uZyBwZXJpb2Qgb2YgdGltZSBoYXMgcGFzc2VkIHNpbmNlIHRoZSBsYXN0IHdoZWVsIGV2ZW50LlxuLy8gV2Ugc25hcCB0aGUgc2VsZWN0aW9uIHRvIHRoZSBjbG9zZXN0IGl0ZW0sIHRoZW4gcmVzZXQgb3VyIHN0YXRlLlxuZnVuY3Rpb24gd2hlZWxUaW1lZE91dChlbGVtZW50KSB7XG5cbiAgLy8gU25hcCB0byB0aGUgY2xvc2VzdCBpdGVtLlxuICBlbGVtZW50W3N5bWJvbHMuZHJhZ2dpbmddID0gZmFsc2U7XG4gIGNvbnN0IHRyYXZlbEZyYWN0aW9uID0gZWxlbWVudC50cmF2ZWxGcmFjdGlvbjtcbiAgaWYgKHRyYXZlbEZyYWN0aW9uID49IDAuNSkge1xuICAgIGVsZW1lbnRbc3ltYm9scy5nb1JpZ2h0XSgpO1xuICB9IGVsc2UgaWYgKHRyYXZlbEZyYWN0aW9uIDw9IC0wLjUpIHtcbiAgICBlbGVtZW50W3N5bWJvbHMuZ29MZWZ0XSgpO1xuICB9XG5cbiAgLy8gVE9ETzogTGlzdGVuIGZvciB0aGUgdHJhbnNpdGlvbiB0byBjb21wbGV0ZSwgYW5kIHRoZW4gcmVzdG9yZVxuICAvLyBkcmFnZ2luZyB0byBmYWxzZSAob3IgdGhlIHByZXZpb3VzIHZhbHVlKS5cblxuICByZXNldFdoZWVsVHJhY2tpbmcoZWxlbWVudCk7XG59XG4iLCIvKipcbiAqIEhlbHBlciBmdW5jdGlvbiB0byBjcmVhdGUgYSBzeW1ib2wgdGhhdCBjYW4gYmUgdXNlZCBmb3IgYXNzb2NpYXRpbmcgcHJpdmF0ZVxuICogZGF0YSB3aXRoIGFuIGVsZW1lbnQuXG4gKlxuICogTWl4aW5zIGFuZCBjb21wb25lbnQgY2xhc3NlcyBvZnRlbiB3YW50IHRvIGFzc29jaWF0ZSBwcml2YXRlIGRhdGEgd2l0aCBhblxuICogZWxlbWVudCBpbnN0YW5jZSwgYnV0IEphdmFTY3JpcHQgZG9lcyBub3QgaGF2ZSBkaXJlY3Qgc3VwcG9ydCBmb3IgdHJ1ZVxuICogcHJpdmF0ZSBwcm9wZXJ0aWVzLiBPbmUgYXBwcm9hY2ggaXMgdG8gdXNlIHRoZVxuICogW1N5bWJvbF0oaHR0cHM6Ly9kZXZlbG9wZXIubW96aWxsYS5vcmcvZW4tVVMvZG9jcy9XZWIvSmF2YVNjcmlwdC9SZWZlcmVuY2UvR2xvYmFsX09iamVjdHMvU3ltYm9sKVxuICogZGF0YSB0eXBlIHRvIHNldCBhbmQgcmV0cmlldmUgZGF0YSBvbiBhbiBlbGVtZW50LlxuICpcbiAqIFVuZm9ydHVuYXRlbHksIHRoZSBTeW1ib2wgdHlwZSBpcyBub3QgYXZhaWxhYmxlIGluIEludGVybmV0IEV4cGxvcmVyIDExLiBUaGVcbiAqIGBjcmVhdGVTeW1ib2xgIGhlbHBlciBmdW5jdGlvbiBleGlzdHMgYXMgYSB3b3JrYXJvdW5kIGZvciBJRSAxMS4gUmF0aGVyIHRoYW5cbiAqIHJldHVybmluZyBhIHRydWUgU3ltYm9sLCBpdCBzaW1wbHkgcmV0dXJucyBhbiB1bmRlcnNjb3JlLXByZWZpeGVkIHN0cmluZy5cbiAqXG4gKiBVc2FnZTpcbiAqXG4gKiAgICAgY29uc3QgZm9vU3ltYm9sID0gY3JlYXRlU3ltYm9sKCdmb28nKTtcbiAqXG4gKiAgICAgY2xhc3MgTXlFbGVtZW50IGV4dGVuZHMgSFRNTEVsZW1lbnQge1xuICogICAgICAgZ2V0IGZvbygpIHtcbiAqICAgICAgICAgcmV0dXJuIHRoaXNbZm9vU3ltYm9sXTtcbiAqICAgICAgIH1cbiAqICAgICAgIHNldCBmb28odmFsdWUpIHtcbiAqICAgICAgICAgdGhpc1tmb29TeW1ib2xdID0gdmFsdWU7XG4gKiAgICAgICB9XG4gKiAgICAgfVxuICpcbiAqIEluIElFIDExLCB0aGlzIHNhbXBsZSB3aWxsIFwiaGlkZVwiIGRhdGEgYmVoaW5kIGFuIGluc3RhbmNlIHByb3BlcnR5IHRoaXMuX2Zvby5cbiAqIFRoZSB1c2Ugb2YgdGhlIHVuZGVyc2NvcmUgaXMgbWVhbnQgdG8gcmVkdWNlIChub3QgZWxpbWluYXRlKSB0aGUgcG90ZW50aWFsXG4gKiBmb3IgbmFtZSBjb25mbGljdHMsIGFuZCBkaXNjb3VyYWdlIChub3QgcHJldmVudCkgZXh0ZXJuYWwgYWNjZXNzIHRvIHRoaXNcbiAqIGRhdGEuIEluIG1vZGVybiBicm93c2VycywgdGhlIGFib3ZlIGNvZGUgd2lsbCBlbGltaW5hdGUgdGhlIHBvdGVudGlhbCBvZlxuICogbmFtaW5nIGNvbmZsaWN0cywgYW5kIGJldHRlciBoaWRlIHRoZSBkYXRhIGJlaGluZCBhIHJlYWwgU3ltYm9sLlxuICpcbiAqIEBmdW5jdGlvbiBjcmVhdGVTeW1ib2xcbiAqIEBwYXJhbSB7c3RyaW5nfSBkZXNjcmlwdGlvbiAtIEEgc3RyaW5nIHRvIGlkZW50aWZ5IHRoZSBzeW1ib2wgd2hlbiBkZWJ1Z2dpbmdcbiAqL1xuZXhwb3J0IGRlZmF1bHQgZnVuY3Rpb24gY3JlYXRlU3ltYm9sKGRlc2NyaXB0aW9uKSB7XG4gIHJldHVybiB0eXBlb2YgU3ltYm9sID09PSAnZnVuY3Rpb24nID9cbiAgICBTeW1ib2woZGVzY3JpcHRpb24pIDpcbiAgICBgXyR7ZGVzY3JpcHRpb259YDtcbn1cbiIsIi8qXG4gKiBNaWNyb3Rhc2sgaGVscGVyIGZvciBJRSAxMS5cbiAqXG4gKiBFeGVjdXRpbmcgYSBmdW5jdGlvbiBhcyBhIG1pY3JvdGFzayBpcyB0cml2aWFsIGluIGJyb3dzZXJzIHRoYXQgc3VwcG9ydFxuICogcHJvbWlzZXMsIHdob3NlIHRoZW4oKSBjbGF1c2VzIHVzZSBtaWNyb3Rhc2sgdGltaW5nLiBJRSAxMSBkb2Vzbid0IHN1cHBvcnRcbiAqIHByb21pc2VzLCBidXQgZG9lcyBzdXBwb3J0IE11dGF0aW9uT2JzZXJ2ZXJzLCB3aGljaCBhcmUgYWxzbyBleGVjdXRlZCBhc1xuICogbWljcm90YXNrcy4gU28gdGhpcyBoZWxwZXIgdXNlcyBhbiBNdXRhdGlvbk9ic2VydmVyIHRvIGFjaGlldmUgbWljcm90YXNrXG4gKiB0aW1pbmcuXG4gKlxuICogU2VlIGh0dHBzOi8vamFrZWFyY2hpYmFsZC5jb20vMjAxNS90YXNrcy1taWNyb3Rhc2tzLXF1ZXVlcy1hbmQtc2NoZWR1bGVzL1xuICpcbiAqIEluc3BpcmVkIGJ5IFBvbHltZXIncyBhc3luYygpIGZ1bmN0aW9uLlxuICovXG5cblxuLy8gVGhlIHF1ZXVlIG9mIHBlbmRpbmcgY2FsbGJhY2tzIHRvIGJlIGV4ZWN1dGVkIGFzIG1pY3JvdGFza3MuXG5jb25zdCBjYWxsYmFja3MgPSBbXTtcblxuLy8gQ3JlYXRlIGFuIGVsZW1lbnQgdGhhdCB3ZSB3aWxsIG1vZGlmeSB0byBmb3JjZSBvYnNlcnZhYmxlIG11dGF0aW9ucy5cbmNvbnN0IGVsZW1lbnQgPSBkb2N1bWVudC5jcmVhdGVUZXh0Tm9kZSgnJyk7XG5cbi8vIEEgbW9ub3RvbmljYWxseS1pbmNyZWFzaW5nIHZhbHVlLlxubGV0IGNvdW50ZXIgPSAwO1xuXG5cbi8qKlxuICogQWRkIGEgY2FsbGJhY2sgdG8gdGhlIG1pY3JvdGFzayBxdWV1ZS5cbiAqXG4gKiBUaGlzIHVzZXMgYSBNdXRhdGlvbk9ic2VydmVyIHNvIHRoYXQgaXQgd29ya3Mgb24gSUUgMTEuXG4gKlxuICogTk9URTogSUUgMTEgbWF5IGFjdHVhbGx5IHVzZSB0aW1lb3V0IHRpbWluZyB3aXRoIE11dGF0aW9uT2JzZXJ2ZXJzLiBUaGlzXG4gKiBuZWVkcyBtb3JlIGludmVzdGlnYXRpb24uXG4gKlxuICogQGZ1bmN0aW9uIG1pY3JvdGFza1xuICogQHBhcmFtIHtmdW5jdGlvbn0gY2FsbGJhY2tcbiAqL1xuZXhwb3J0IGRlZmF1bHQgZnVuY3Rpb24gbWljcm90YXNrKGNhbGxiYWNrKSB7XG4gIGNhbGxiYWNrcy5wdXNoKGNhbGxiYWNrKTtcbiAgLy8gRm9yY2UgYSBtdXRhdGlvbi5cbiAgZWxlbWVudC50ZXh0Q29udGVudCA9ICsrY291bnRlcjtcbn1cblxuXG4vLyBFeGVjdXRlIGFueSBwZW5kaW5nIGNhbGxiYWNrcy5cbmZ1bmN0aW9uIGV4ZWN1dGVDYWxsYmFja3MoKSB7XG4gIHdoaWxlIChjYWxsYmFja3MubGVuZ3RoID4gMCkge1xuICAgIGNvbnN0IGNhbGxiYWNrID0gY2FsbGJhY2tzLnNoaWZ0KCk7XG4gICAgY2FsbGJhY2soKTtcbiAgfVxufVxuXG5cbi8vIENyZWF0ZSB0aGUgb2JzZXJ2ZXIuXG5jb25zdCBvYnNlcnZlciA9IG5ldyBNdXRhdGlvbk9ic2VydmVyKGV4ZWN1dGVDYWxsYmFja3MpO1xub2JzZXJ2ZXIub2JzZXJ2ZShlbGVtZW50LCB7XG4gIGNoYXJhY3RlckRhdGE6IHRydWVcbn0pO1xuIiwiLyoqXG4gKiBIZWxwZXIgZnVuY3Rpb24gZm9yIHJlbmRlcmluZyBhbiBhcnJheSBvZiBpdGVtcyBhcyBlbGVtZW50cy5cbiAqXG4gKiBUaGlzIGlzIG5vdCBhIG1peGluLCBidXQgYSBmdW5jdGlvbiBjb21wb25lbnRzIGNhbiB1c2UgaWYgdGhleSBuZWVkIHRvXG4gKiBnZW5lcmF0ZSBhIHNldCBvZiBlbGVtZW50cyBmb3IgdGhlIGl0ZW1zIGluIGFuIGFycmF5LlxuICpcbiAqIFRoaXMgZnVuY3Rpb24gd2lsbCByZXVzZSBleGlzdGluZyBlbGVtZW50cyBpZiBwb3NzaWJsZS4gRS5nLiwgaWYgaXQgaXMgY2FsbGVkXG4gKiB0byByZW5kZXIgYW4gYXJyYXkgb2YgNCBpdGVtcywgYW5kIGxhdGVyIGNhbGxlZCB0byByZW5kZXIgYW4gYXJyYXkgb2YgNVxuICogaXRlbXMsIGl0IGNhbiByZXVzZSB0aGUgZXhpc3RpbmcgNCBpdGVtcywgY3JlYXRpbmcganVzdCBvbmUgbmV3IGVsZW1lbnQuXG4gKiBOb3RlLCBob3dldmVyLCB0aGF0IHRoaXMgcmUtcmVuZGVyaW5nIGlzIG5vdCBhdXRvbWF0aWMuIElmLCBhZnRlciBjYWxsaW5nXG4gKiB0aGlzIGZ1bmN0aW9uLCB5b3UgbWFuaXB1bGF0ZSB0aGUgYXJyYXkgeW91IHVzZWQsIHlvdSBtdXN0IHN0aWxsIGNhbGwgdGhpc1xuICogZnVuY3Rpb24gYWdhaW4gdG8gcmUtcmVuZGVyIHRoZSBhcnJheS5cbiAqXG4gKiBUaGUgYHJlbmRlckl0ZW1gIHBhcmFtZXRlciB0YWtlcyBhIGZ1bmN0aW9uIG9mIHR3byBhcmd1bWVudHM6IGFuIGl0ZW0gdG9cbiAqIHRvIHJlbmRlciwgYW5kIGFuIGV4aXN0aW5nIGVsZW1lbnQgKGlmIG9uZSBleGlzdHMpIHdoaWNoIGNhbiBiZSByZXB1cnBvc2VkIHRvXG4gKiByZW5kZXIgdGhhdCBpdGVtLiBJZiB0aGUgbGF0dGVyIGFyZ3VtZW50IGlzIG51bGwsIHRoZSBgcmVuZGVySXRlbSgpYCBmdW5jdGlvblxuICogc2hvdWxkIGNyZWF0ZSBhIG5ldyBlbGVtZW50IGFuZCByZXR1cm4gaXQuIFRoZSBmdW5jdGlvbiBzaG91bGQgZG8gdGhlIHNhbWVcbiAqIGlmIHRoZSBzdXBwbGllZCBleGlzdGluZyBlbGVtZW50IGlzIG5vdCBzdWl0YWJsZSBmb3IgcmVuZGVyaW5nIHRoZSBnaXZlblxuICogaXRlbTsgdGhlIHJldHVybmVkIGVsZW1lbnQgd2lsbCBiZSB1c2VkIHRvIHJlcGxhY2UgdGhlIGV4aXN0aW5nIG9uZS4gSWYgdGhlXG4gKiBleGlzdGluZyBlbGVtZW50ICppcyogc3VpdGFibGUsIHRoZSBmdW5jdGlvbiBjYW4gc2ltcGx5IHVwZGF0ZSBpdCBhbmQgcmV0dXJuXG4gKiBpdCBhcyBpcy5cbiAqXG4gKiBFeGFtcGxlOiBUaGUgZm9sbG93aW5nIHdpbGwgcmVuZGVyIGFuIGFycmF5IG9mIHN0cmluZ3MgaW4gZGl2cyBhcyBjaGlsZHJlblxuICogb2YgdGhlIGBjb250YWluZXJgIGVsZW1lbnQ6XG4gKlxuICogICAgIGxldCBzdHJpbmdzID0gWydhJywgJ2InLCAnYycsIC4uLl07XG4gKiAgICAgbGV0IGNvbnRhaW5lciA9IHRoaXMucXVlcnlTZWxlY3RvciguLi4pO1xuICogICAgIHJlbmRlckFycmF5QXNFbGVtZW50cyhzdHJpbmdzLCBjb250YWluZXIsIChzdHJpbmcsIGVsZW1lbnQpID0+IHtcbiAqICAgICAgIGlmICghZWxlbWVudCkge1xuICogICAgICAgICAvLyBObyBlbGVtZW50IGV4aXN0cyB5ZXQsIHNvIGNyZWF0ZSBhIG5ldyBvbmUuXG4gKiAgICAgICAgIGVsZW1lbnQgPSBkb2N1bWVudC5jcmVhdGVFbGVtZW50KCdkaXYnKTtcbiAqICAgICAgIH1cbiAqICAgICAgIC8vIFNldC91cGRhdGUgdGhlIHRleHQgY29udGVudCBvZiB0aGUgZWxlbWVudC5cbiAqICAgICAgIGVsZW1lbnQudGV4dENvbnRlbnQgPSBzdHJpbmc7XG4gKiAgICAgICByZXR1cm4gZWxlbWVudDtcbiAqICAgICB9KTtcbiAqXG4gKiBAcGFyYW0ge0FycmF5fSBpdGVtcyAtIHRoZSBpdGVtcyB0byByZW5kZXJcbiAqIEBwYXJhbSB7SFRNTEVsZW1lbnR9IGNvbnRhaW5lciAtIHRoZSBwYXJlbnQgdGhhdCB3aWxsIGhvbGQgdGhlIGVsZW1lbnRzXG4gKiBAcGFyYW0ge2Z1bmN0aW9ufSByZW5kZXJJdGVtIC0gcmV0dXJucyBhIG5ldyBlbGVtZW50IGZvciBhbiBpdGVtLCBvclxuICogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHJlcHVycG9zZXMgYW4gZXhpc3RpbmcgZWxlbWVudCBmb3IgYW4gaXRlbVxuICovXG5mdW5jdGlvbiByZW5kZXJBcnJheUFzRWxlbWVudHMoaXRlbXMsIGNvbnRhaW5lciwgcmVuZGVySXRlbSkge1xuICAvLyBDcmVhdGUgYSBuZXcgc2V0IG9mIGVsZW1lbnRzIGZvciB0aGUgY3VycmVudCBpdGVtcy5cbiAgaXRlbXMuZm9yRWFjaCgoaXRlbSwgaW5kZXgpID0+IHtcbiAgICBjb25zdCBvbGRFbGVtZW50ID0gY29udGFpbmVyLmNoaWxkTm9kZXNbaW5kZXhdO1xuICAgIGNvbnN0IG5ld0VsZW1lbnQgPSByZW5kZXJJdGVtKGl0ZW0sIG9sZEVsZW1lbnQpO1xuICAgIGlmIChuZXdFbGVtZW50KSB7XG4gICAgICBpZiAoIW9sZEVsZW1lbnQpIHtcbiAgICAgICAgY29udGFpbmVyLmFwcGVuZENoaWxkKG5ld0VsZW1lbnQpO1xuICAgICAgfSBlbHNlIGlmIChuZXdFbGVtZW50ICE9PSBvbGRFbGVtZW50KSB7XG4gICAgICAgIGNvbnRhaW5lci5yZXBsYWNlQ2hpbGQobmV3RWxlbWVudCwgb2xkRWxlbWVudCk7XG4gICAgICB9XG4gICAgfVxuICB9KTtcblxuICAvLyBJZiB0aGUgYXJyYXkgc2hyYW5rLCByZW1vdmUgdGhlIGV4dHJhIGVsZW1lbnRzIHdoaWNoIGFyZSBubyBsb25nZXIgbmVlZGVkLlxuICB3aGlsZSAoY29udGFpbmVyLmNoaWxkTm9kZXMubGVuZ3RoID4gaXRlbXMubGVuZ3RoKSB7XG4gICAgY29udGFpbmVyLnJlbW92ZUNoaWxkKGNvbnRhaW5lci5jaGlsZE5vZGVzW2l0ZW1zLmxlbmd0aF0pO1xuICB9XG59XG5cbmV4cG9ydCBkZWZhdWx0IHJlbmRlckFycmF5QXNFbGVtZW50cztcbiIsImltcG9ydCBjcmVhdGVTeW1ib2wgZnJvbSAnLi9jcmVhdGVTeW1ib2wnO1xuaW1wb3J0IHRvZ2dsZUNsYXNzIGZyb20gJy4vdG9nZ2xlQ2xhc3MnO1xuXG5cbi8vIFN5bWJvbHMgZm9yIHByaXZhdGUgZGF0YSBtZW1iZXJzIG9uIGFuIGVsZW1lbnQuXG5jb25zdCBzYWZlVG9TZXRBdHRyaWJ1dGVzU3ltYm9sID0gY3JlYXRlU3ltYm9sKCdzYWZlVG9TZXRBdHRyaWJ1dGVzJyk7XG5jb25zdCBwZW5kaW5nQXR0cmlidXRlc1N5bWJvbCA9IGNyZWF0ZVN5bWJvbCgncGVuZGluZ0F0dHJpYnV0ZXMnKTtcbmNvbnN0IHBlbmRpbmdDbGFzc2VzU3ltYm9sID0gY3JlYXRlU3ltYm9sKCdwZW5kaW5nQ2xhc3NlcycpO1xuXG5cbi8qKlxuICogSGVscGVyIGZ1bmN0aW9ucyBmb3IgdXBkYXRpbmcgYXR0cmlidXRlcywgaW5jbHVkaW5nIHRoZSBgY2xhc3NgIGF0dHJpYnV0ZS5cbiAqL1xuZXhwb3J0IGRlZmF1bHQge1xuXG4gIC8qKlxuICAgKiBQZXJmb3JtIGFueSBwZW5kaW5nIHVwZGF0ZXMgdG8gYXR0cmlidXRlcyBhbmQgY2xhc3Nlcy5cbiAgICpcbiAgICogVGhpcyB3cml0ZXMgYW55IGBzZXRBdHRyaWJ1dGVgIG9yIGB0b2dnbGVDbGFzc2AgdmFsdWVzIHRoYXQgd2VyZSBwZXJmb3JtZWRcbiAgICogYmVmb3JlIGFuIGVsZW1lbnQgd2FzIGF0dGFjaGVkIHRvIHRoZSBkb2N1bWVudCBmb3IgdGhlIGZpcnN0IHRpbWUuXG4gICAqXG4gICAqIFRoaXMgbWV0aG9kIHNob3VsZCBiZSBjYWxsZWQgYnkgbWl4aW5zL2NvbXBvbmVudHMgaW4gdGhlaXJcbiAgICogYGNvbm5lY3RlZENhbGxiYWNrYC4gSWYgbXVsaXRwbGUgbWl4aW5zL2NvbXBvbmVudHMgaW52b2tlIHRoaXMgZHVyaW5nIHRoZVxuICAgKiBzYW1lIGBjb25uZWN0ZWRDYWxsYmFja2AsIG9ubHkgdGhlIGZpcnN0IGNhbGwgd2lsbCBoYXZlIGFueSBlZmZlY3QuIFRoZVxuICAgKiBzdWJzZXF1ZW50IGNhbGxzIHdpbGwgYmUgaGFybWxlc3MuXG4gICAqXG4gICAqIEBwYXJhbSB7SFRNTEVsZW1lbnR9IGVsZW1lbnQgLSBUaGUgZWxlbWVudCBiZWluZyBhZGRlZCB0byB0aGUgZG9jdW1lbnQuXG4gICAqL1xuICBjb25uZWN0ZWQoZWxlbWVudCkge1xuICAgIGVsZW1lbnRbc2FmZVRvU2V0QXR0cmlidXRlc1N5bWJvbF0gPSB0cnVlO1xuXG4gICAgLy8gU2V0IGFueSBwZW5kaW5nIGF0dHJpYnV0ZXMuXG4gICAgaWYgKGVsZW1lbnRbcGVuZGluZ0F0dHJpYnV0ZXNTeW1ib2xdKSB7XG4gICAgICBmb3IgKGxldCBhdHRyaWJ1dGUgaW4gZWxlbWVudFtwZW5kaW5nQXR0cmlidXRlc1N5bWJvbF0pIHtcbiAgICAgICAgY29uc3QgdmFsdWUgPSBlbGVtZW50W3BlbmRpbmdBdHRyaWJ1dGVzU3ltYm9sXVthdHRyaWJ1dGVdO1xuICAgICAgICBzZXRBdHRyaWJ1dGVUb0VsZW1lbnQoZWxlbWVudCwgYXR0cmlidXRlLCB2YWx1ZSk7XG4gICAgICB9XG4gICAgICBlbGVtZW50W3BlbmRpbmdBdHRyaWJ1dGVzU3ltYm9sXSA9IG51bGw7XG4gICAgfVxuXG4gICAgLy8gU2V0IGFueSBwZW5kaW5nIGNsYXNzZXMuXG4gICAgaWYgKGVsZW1lbnRbcGVuZGluZ0NsYXNzZXNTeW1ib2xdKSB7XG4gICAgICBmb3IgKGxldCBjbGFzc05hbWUgaW4gZWxlbWVudFtwZW5kaW5nQ2xhc3Nlc1N5bWJvbF0pIHtcbiAgICAgICAgY29uc3QgdmFsdWUgPSBlbGVtZW50W3BlbmRpbmdDbGFzc2VzU3ltYm9sXVtjbGFzc05hbWVdO1xuICAgICAgICB0b2dnbGVDbGFzcyhlbGVtZW50LCBjbGFzc05hbWUsIHZhbHVlKTtcbiAgICAgIH1cbiAgICAgIGVsZW1lbnRbcGVuZGluZ0NsYXNzZXNTeW1ib2xdID0gbnVsbDtcbiAgICB9XG4gIH0sXG5cbiAgLyoqXG4gICAqIFNldC91bnNldCB0aGUgYXR0cmlidXRlIHdpdGggdGhlIGluZGljYXRlZCBuYW1lLlxuICAgKlxuICAgKiBUaGlzIG1ldGhvZCBleGlzdHMgcHJpbWFyaWx5IHRvIGhhbmRsZSB0aGUgY2FzZSB3aGVyZSBhbiBlbGVtZW50IHdhbnRzIHRvXG4gICAqIHNldCBhIGRlZmF1bHQgcHJvcGVydHkgdmFsdWUgdGhhdCBzaG91bGQgYmUgcmVmbGVjdGVkIGFzIGFuIGF0dHJpYnV0ZS4gQW5cbiAgICogaW1wb3J0YW50IGxpbWl0YXRpb24gb2YgY3VzdG9tIGVsZW1lbnQgY29uc3R1cmN0b3JzIGlzIHRoYXQgdGhleSBjYW5ub3RcbiAgICogc2V0IGF0dHJpYnV0ZXMuIEEgY2FsbCB0byBgc2V0QXR0cmlidXRlYCBkdXJpbmcgdGhlIGNvbnN0cnVjdG9yIHdpbGxcbiAgICogYmUgZGVmZXJyZWQgdW50aWwgdGhlIGVsZW1lbnQgaXMgY29ubmVjdGVkIHRvIHRoZSBkb2N1bWVudC5cbiAgICpcbiAgICogQHBhcmFtIHtzdHJpbmd9IGF0dHJpYnV0ZSAtIFRoZSBuYW1lIG9mIHRoZSAqYXR0cmlidXRlKiAobm90IHByb3BlcnR5KSB0byBzZXQuXG4gICAqIEBwYXJhbSB7b2JqZWN0fSB2YWx1ZSAtIFRoZSB2YWx1ZSB0byBzZXQuIElmIG51bGwsIHRoZSBhdHRyaWJ1dGUgd2lsbCBiZSByZW1vdmVkLlxuICAgKi9cbiAgc2V0QXR0cmlidXRlKGVsZW1lbnQsIGF0dHJpYnV0ZSwgdmFsdWUpIHtcbiAgICBpZiAoZWxlbWVudFtzYWZlVG9TZXRBdHRyaWJ1dGVzU3ltYm9sXSkge1xuICAgICAgLy8gU2FmZSB0byBzZXQgYXR0cmlidXRlcyBpbW1lZGlhdGVseS5cbiAgICAgIHNldEF0dHJpYnV0ZVRvRWxlbWVudChlbGVtZW50LCBhdHRyaWJ1dGUsIHZhbHVlKTtcbiAgICB9IGVsc2Uge1xuICAgICAgLy8gRGVmZXIgc2V0dGluZyBhdHRyaWJ1dGVzIHVudGlsIHRoZSBmaXJzdCB0aW1lIHdlJ3JlIGNvbm5lY3RlZC5cbiAgICAgIGlmICghZWxlbWVudFtwZW5kaW5nQXR0cmlidXRlc1N5bWJvbF0pIHtcbiAgICAgICAgZWxlbWVudFtwZW5kaW5nQXR0cmlidXRlc1N5bWJvbF0gPSB7fTtcbiAgICAgIH1cbiAgICAgIGVsZW1lbnRbcGVuZGluZ0F0dHJpYnV0ZXNTeW1ib2xdW2F0dHJpYnV0ZV0gPSB2YWx1ZTtcbiAgICB9XG4gIH0sXG5cbiAgLyoqXG4gICAqIFNldC91bnNldCB0aGUgY2xhc3Mgd2l0aCB0aGUgaW5kaWNhdGVkIG5hbWUuXG4gICAqXG4gICAqIFRoaXMgbWV0aG9kIGV4aXN0cyBwcmltYXJpbHkgdG8gaGFuZGxlIHRoZSBjYXNlIHdoZXJlIGFuIGVsZW1lbnQgd2FudHMgdG9cbiAgICogc2V0IGEgZGVmYXVsdCBwcm9wZXJ0eSB2YWx1ZSB0aGF0IHNob3VsZCBiZSByZWZsZWN0ZWQgYXMgYXMgY2xhc3MuIEFuXG4gICAqIGltcG9ydGFudCBsaW1pdGF0aW9uIG9mIGN1c3RvbSBlbGVtZW50IGNvbnN0dXJjdG9ycyBpcyB0aGF0IHRoZXkgY2Fubm90XG4gICAqIHNldCBhdHRyaWJ1dGVzLCBpbmNsdWRpbmcgdGhlIGBjbGFzc2AgYXR0cmlidXRlLiBBIGNhbGwgdG9cbiAgICogYHRvZ2dsZUNsYXNzYCBkdXJpbmcgdGhlIGNvbnN0cnVjdG9yIHdpbGwgYmUgZGVmZXJyZWQgdW50aWwgdGhlIGVsZW1lbnRcbiAgICogaXMgY29ubmVjdGVkIHRvIHRoZSBkb2N1bWVudC5cbiAgICpcbiAgICogQHBhcmFtIHtzdHJpbmd9IGNsYXNzTmFtZSAtIFRoZSBuYW1lIG9mIHRoZSBjbGFzcyB0byBzZXQuXG4gICAqIEBwYXJhbSB7b2JqZWN0fSB2YWx1ZSAtIFRydWUgdG8gc2V0IHRoZSBjbGFzcywgZmFsc2UgdG8gcmVtb3ZlIGl0LlxuICAgKi9cbiAgdG9nZ2xlQ2xhc3MoZWxlbWVudCwgY2xhc3NOYW1lLCB2YWx1ZSkge1xuICAgIGlmIChlbGVtZW50W3NhZmVUb1NldEF0dHJpYnV0ZXNTeW1ib2xdKSB7XG4gICAgICAvLyBTYWZlIHRvIHNldCBjbGFzcyBpbW1lZGlhdGVseS5cbiAgICAgIHRvZ2dsZUNsYXNzKGVsZW1lbnQsIGNsYXNzTmFtZSwgdmFsdWUpO1xuICAgIH0gZWxzZSB7XG4gICAgICAvLyBEZWZlciBzZXR0aW5nIGNsYXNzIHVudGlsIHRoZSBmaXJzdCB0aW1lIHdlJ3JlIGNvbm5lY3RlZC5cbiAgICAgIGlmICghZWxlbWVudFtwZW5kaW5nQ2xhc3Nlc1N5bWJvbF0pIHtcbiAgICAgICAgZWxlbWVudFtwZW5kaW5nQ2xhc3Nlc1N5bWJvbF0gPSB7fTtcbiAgICAgIH1cbiAgICAgIGVsZW1lbnRbcGVuZGluZ0NsYXNzZXNTeW1ib2xdW2NsYXNzTmFtZV0gPSB2YWx1ZTtcbiAgICB9XG4gIH1cblxufTtcblxuXG4vLyBSZWZsZWN0IHRoZSBhdHRyaWJ1dGUgdG8gdGhlIGdpdmVuIGVsZW1lbnQuXG4vLyBJZiB0aGUgdmFsdWUgaXMgbnVsbCwgcmVtb3ZlIHRoZSBhdHRyaWJ1dGUuXG5mdW5jdGlvbiBzZXRBdHRyaWJ1dGVUb0VsZW1lbnQoZWxlbWVudCwgYXR0cmlidXRlTmFtZSwgdmFsdWUpIHtcbiAgaWYgKHZhbHVlID09PSBudWxsIHx8IHR5cGVvZiB2YWx1ZSA9PT0gJ3VuZGVmaW5lZCcpIHtcbiAgICBlbGVtZW50LnJlbW92ZUF0dHJpYnV0ZShhdHRyaWJ1dGVOYW1lKTtcbiAgfSBlbHNlIHtcbiAgICBjb25zdCB0ZXh0ID0gU3RyaW5nKHZhbHVlKTtcbiAgICAvLyBBdm9pZCByZWN1cnNpdmUgYXR0cmlidXRlQ2hhbmdlZENhbGxiYWNrIGNhbGxzLlxuICAgIGlmIChlbGVtZW50LmdldEF0dHJpYnV0ZShhdHRyaWJ1dGVOYW1lKSAhPT0gdGV4dCkge1xuICAgICAgZWxlbWVudC5zZXRBdHRyaWJ1dGUoYXR0cmlidXRlTmFtZSwgdmFsdWUpO1xuICAgIH1cbiAgfVxufVxuIiwiaW1wb3J0IGNyZWF0ZVN5bWJvbCBmcm9tICcuL2NyZWF0ZVN5bWJvbCc7XG5cbi8qKlxuICogQSBjb2xsZWN0aW9uIG9mIFN5bWJvbCBvYmplY3RzIGZvciBzdGFuZGFyZCBjb21wb25lbnQgcHJvcGVydGllcyBhbmQgbWV0aG9kcy5cbiAqXG4gKiBUaGVzZSBTeW1ib2wgb2JqZWN0cyBhcmUgdXNlZCB0byBhbGxvdyBtaXhpbnMgYW5kIGEgY29tcG9uZW50IHRvIGludGVybmFsbHlcbiAqIGNvbW11bmljYXRlLCB3aXRob3V0IGV4cG9zaW5nIHRoZXNlIHByb3BlcnRpZXMgYW5kIG1ldGhvZHMgaW4gdGhlIGNvbXBvbmVudCdzXG4gKiBwdWJsaWMgQVBJLlxuICpcbiAqIFRvIHVzZSB0aGVzZSBTeW1ib2wgb2JqZWN0cyBpbiB5b3VyIG93biBjb21wb25lbnQsIGluY2x1ZGUgdGhpcyBtb2R1bGUgYW5kXG4gKiB0aGVuIGNyZWF0ZSBhIHByb3BlcnR5IG9yIG1ldGhvZCB3aG9zZSBrZXkgaXMgdGhlIGRlc2lyZWQgU3ltYm9sLlxuICpcbiAqICAgICBpbXBvcnQgJ1NpbmdsZVNlbGVjdGlvbk1peGluJyBmcm9tICdiYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy9TaW5nbGVTZWxlY3Rpb25NaXhpbic7XG4gKiAgICAgaW1wb3J0ICdzeW1ib2xzJyBmcm9tICdiYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy9zeW1ib2xzJztcbiAqXG4gKiAgICAgY2xhc3MgTXlFbGVtZW50IGV4dGVuZHMgU2luZ2xlU2VsZWN0aW9uTWl4aW4oSFRNTEVsZW1lbnQpIHtcbiAqICAgICAgIFtzeW1ib2xzLml0ZW1TZWxlY3RlZF0oaXRlbSwgc2VsZWN0ZWQpIHtcbiAqICAgICAgICAgLy8gVGhpcyB3aWxsIGJlIGludm9rZWQgd2hlbmV2ZXIgYW4gaXRlbSBpcyBzZWxlY3RlZC9kZXNlbGVjdGVkLlxuICogICAgICAgfVxuICogICAgIH1cbiAqXG4gKiBAbW9kdWxlIHN5bWJvbHNcbiAqL1xuY29uc3Qgc3ltYm9scyA9IHtcblxuICAvKipcbiAgICogU3ltYm9sIGZvciB0aGUgYGRlZmF1bHRzYCBwcm9wZXJ0eS5cbiAgICpcbiAgICogVGhpcyBwcm9wZXJ0eSBjYW4gYmUgdXNlZCB0byBzZXQgb3Igb3ZlcnJpZGUgZGVmYXVsdHMgdGhhdCB3aWxsIGJlIGFwcGxpZWRcbiAgICogdG8gYSBuZXcgY29tcG9uZW50IGluc3RhbmNlLiBXaGVuIGltcGxlbWVudGluZyB0aGlzIHByb3BlcnR5LCB0YWtlIGNhcmUgdG9cbiAgICogZmlyc3QgYWNxdWlyZSBhbnkgZGVmYXVsdHMgZGVmaW5lZCBieSB0aGUgc3VwZXJjbGFzcy4gVGhlIHN0YW5kYXJkIGlkaW9tIGlzXG4gICAqIGFzIGZvbGxvd3M6XG4gICAqXG4gICAqICAgICBnZXQgW3N5bWJvbHMuZGVmYXVsdHNdKCkge1xuICAgKiAgICAgICBjb25zdCBkZWZhdWx0cyA9IHN1cGVyW3N5bWJvbHMuZGVmYXVsdHNdIHx8IHt9O1xuICAgKiAgICAgICAvLyBTZXQgb3Igb3ZlcnJpZGUgZGVmYXVsdCB2YWx1ZXMgaGVyZVxuICAgKiAgICAgICBkZWZhdWx0cy5jdXN0b21Qcm9wZXJ0eSA9IGZhbHNlO1xuICAgKiAgICAgICByZXR1cm4gZGVmYXVsdHM7XG4gICAqICAgICB9XG4gICAqXG4gICAqIEB2YXIge29iamVjdH0gZGVmYXVsdHNcbiAgICovXG4gIGRlZmF1bHRzOiBjcmVhdGVTeW1ib2woJ2RlZmF1bHRzJyksXG5cbiAgLyoqXG4gICAqIFN5bWJvbCBmb3IgdGhlIGBkcmFnZ2luZ2AgcHJvcGVydHkuXG4gICAqXG4gICAqIENvbXBvbmVudHMgbGlrZSBjYXJvdXNlbHMgb2Z0ZW4gZGVmaW5lIGFuaW1hdGVkIENTUyB0cmFuc2l0aW9ucyBmb3JcbiAgICogc2xpZGluZyBlZmZlY3RzLiBTdWNoIGEgdHJhbnNpdGlvbiBzaG91bGQgdXN1YWxseSAqbm90KiBiZSBhcHBsaWVkIHdoaWxlXG4gICAqIHRoZSB1c2VyIGlzIGRyYWdnaW5nLCBiZWNhdXNlIGEgQ1NTIGFuaW1hdGlvbiB3aWxsIGludHJvZHVjZSBhIGxhZyB0aGF0XG4gICAqIG1ha2VzIHRoZSBzd2lwZSBmZWVsIHNsdWdnaXNoLiBJbnN0ZWFkLCBhcyBsb25nIGFzIHRoZSB1c2VyIGlzIGRyYWdnaW5nXG4gICAqIHdpdGggdGhlaXIgZmluZ2VyIGRvd24sIHRoZSB0cmFuc2l0aW9uIHNob3VsZCBiZSBzdXBwcmVzc2VkLiBXaGVuIHRoZVxuICAgKiB1c2VyIHJlbGVhc2VzIHRoZWlyIGZpbmdlciwgdGhlIHRyYW5zaXRpb24gY2FuIGJlIHJlc3RvcmVkLCBhbGxvd2luZyB0aGVcbiAgICogYW5pbWF0aW9uIHRvIHNob3cgdGhlIGNhcm91c2VsIHNsaWRpbmcgaW50byBpdHMgZmluYWwgcG9zaXRpb24uXG4gICAqXG4gICAqIEB0eXBlIHtib29sZWFufSB0cnVlIGlmIGEgZHJhZyBpcyBpbiBwcm9ncmVzcywgZmFsc2UgaWYgbm90LlxuICAgKi9cbiAgZHJhZ2dpbmc6IGNyZWF0ZVN5bWJvbCgnZHJhZ2dpbmcnKSxcblxuICAvKipcbiAgICogU3ltYm9sIGZvciB0aGUgYGdvRG93bmAgbWV0aG9kLlxuICAgKlxuICAgKiBUaGlzIG1ldGhvZCBpcyBpbnZva2VkIHdoZW4gdGhlIHVzZXIgd2FudHMgdG8gZ28vbmF2aWdhdGUgZG93bi5cbiAgICpcbiAgICogQGZ1bmN0aW9uIGdvRG93blxuICAgKi9cbiAgZ29Eb3duOiBjcmVhdGVTeW1ib2woJ2dvRG93bicpLFxuXG4gIC8qKlxuICAgKiBTeW1ib2wgZm9yIHRoZSBgZ29FbmRgIG1ldGhvZC5cbiAgICpcbiAgICogVGhpcyBtZXRob2QgaXMgaW52b2tlZCB3aGVuIHRoZSB1c2VyIHdhbnRzIHRvIGdvL25hdmlnYXRlIHRvIHRoZSBlbmQgKGUuZy4sXG4gICAqIG9mIGEgbGlzdCkuXG4gICAqXG4gICAqIEBmdW5jdGlvbiBnb0VuZFxuICAgKi9cbiAgZ29FbmQ6IGNyZWF0ZVN5bWJvbCgnZ29FbmQnKSxcblxuICAvKipcbiAgICogU3ltYm9sIGZvciB0aGUgYGdvTGVmdGAgbWV0aG9kLlxuICAgKlxuICAgKiBUaGlzIG1ldGhvZCBpcyBpbnZva2VkIHdoZW4gdGhlIHVzZXIgd2FudHMgdG8gZ28vbmF2aWdhdGUgbGVmdC5cbiAgICpcbiAgICogQGZ1bmN0aW9uIGdvTGVmdFxuICAgKi9cbiAgZ29MZWZ0OiBjcmVhdGVTeW1ib2woJ2dvTGVmdCcpLFxuXG4gIC8qKlxuICAgKiBTeW1ib2wgZm9yIHRoZSBgZ29SaWdodGAgbWV0aG9kLlxuICAgKlxuICAgKiBUaGlzIG1ldGhvZCBpcyBpbnZva2VkIHdoZW4gdGhlIHVzZXIgd2FudHMgdG8gZ28vbmF2aWdhdGUgcmlnaHQuXG4gICAqXG4gICAqIEBmdW5jdGlvbiBnb1JpZ2h0XG4gICAqL1xuICBnb1JpZ2h0OiBjcmVhdGVTeW1ib2woJ2dvUmlnaHQnKSxcblxuICAvKipcbiAgICogU3ltYm9sIGZvciB0aGUgYGdvU3RhcnRgIG1ldGhvZC5cbiAgICpcbiAgICogVGhpcyBtZXRob2QgaXMgaW52b2tlZCB3aGVuIHRoZSB1c2VyIHdhbnRzIHRvIGdvL25hdmlnYXRlIHRvIHRoZSBzdGFydFxuICAgKiAoZS5nLiwgb2YgYSBsaXN0KS5cbiAgICpcbiAgICogQGZ1bmN0aW9uIGdvU3RhcnRcbiAgICovXG4gIGdvU3RhcnQ6IGNyZWF0ZVN5bWJvbCgnZ29TdGFydCcpLFxuXG4gIC8qKlxuICAgKiBTeW1ib2wgZm9yIHRoZSBgZ29VcGAgbWV0aG9kLlxuICAgKlxuICAgKiBUaGlzIG1ldGhvZCBpcyBpbnZva2VkIHdoZW4gdGhlIHVzZXIgd2FudHMgdG8gZ28vbmF2aWdhdGUgdXAuXG4gICAqXG4gICAqIEBmdW5jdGlvbiBnb1VwXG4gICAqL1xuICBnb1VwOiBjcmVhdGVTeW1ib2woJ2dvVXAnKSxcblxuICAvKipcbiAgICogU3ltYm9sIGZvciB0aGUgYGl0ZW1BZGRlZGAgbWV0aG9kLlxuICAgKlxuICAgKiBUaGlzIG1ldGhvZCBpcyBpbnZva2VkIHdoZW4gYSBuZXcgaXRlbSBpcyBhZGRlZCB0byBhIGxpc3QuXG4gICAqXG4gICAqIEBmdW5jdGlvbiBpdGVtQWRkZWRcbiAgICogQHBhcmFtIHtIVE1MRWxlbWVudH0gaXRlbSAtIHRoZSBpdGVtIGJlaW5nIHNlbGVjdGVkL2Rlc2VsZWN0ZWRcbiAgICovXG4gIGl0ZW1BZGRlZDogY3JlYXRlU3ltYm9sKCdpdGVtQWRkZWQnKSxcblxuXG4gIC8qKlxuICAgKiBTeW1ib2wgZm9yIHRoZSBgaXRlbXNDaGFuZ2VkYCBtZXRob2QuXG4gICAqXG4gICAqIFRoaXMgbWV0aG9kIGlzIGludm9rZWQgd2hlbiB0aGUgdW5kZXJseWluZyBjb250ZW50cyBjaGFuZ2UuIEl0IGlzIGFsc29cbiAgICogaW52b2tlZCBvbiBjb21wb25lbnQgaW5pdGlhbGl6YXRpb24g4oCTIHNpbmNlIHRoZSBpdGVtcyBoYXZlIFwiY2hhbmdlZFwiIGZyb21cbiAgICogYmVpbmcgbm90aGluZy5cbiAgICovXG4gIGl0ZW1zQ2hhbmdlZDogY3JlYXRlU3ltYm9sKCdpdGVtc0NoYW5nZWQnKSxcblxuICAvKipcbiAgICogU3ltYm9sIGZvciB0aGUgYGl0ZW1TZWxlY3RlZGAgbWV0aG9kLlxuICAgKlxuICAgKiBUaGlzIG1ldGhvZCBpcyBpbnZva2VkIHdoZW4gYW4gaXRlbSBiZWNvbWVzIHNlbGVjdGVkIG9yIGRlc2VsZWN0ZWQuXG4gICAqXG4gICAqIEBmdW5jdGlvbiBpdGVtU2VsZWN0ZWRcbiAgICogQHBhcmFtIHtIVE1MRWxlbWVudH0gaXRlbSAtIHRoZSBpdGVtIGJlaW5nIHNlbGVjdGVkL2Rlc2VsZWN0ZWRcbiAgICogQHBhcmFtIHtib29sZWFufSBzZWxlY3RlZCAtIHRydWUgaWYgdGhlIGl0ZW0gaXMgc2VsZWN0ZWQsIGZhbHNlIGlmIG5vdFxuICAgKi9cbiAgaXRlbVNlbGVjdGVkOiBjcmVhdGVTeW1ib2woJ2l0ZW1TZWxlY3RlZCcpLFxuXG4gIC8qKlxuICAgKiBTeW1ib2wgZm9yIHRoZSBga2V5ZG93bmAgbWV0aG9kLlxuICAgKlxuICAgKiBUaGlzIG1ldGhvZCBpcyBpbnZva2VkIHdoZW4gYW4gZWxlbWVudCByZWNlaXZlcyBhIGBrZXlkb3duYCBldmVudC5cbiAgICpcbiAgICogQGZ1bmN0aW9uIGtleWRvd25cbiAgICogQHBhcmFtIHtLZXlib2FyZEV2ZW50fSBldmVudCAtIHRoZSBldmVudCBiZWluZyBwcm9jZXNzZWRcbiAgICovXG4gIGtleWRvd246IGNyZWF0ZVN5bWJvbCgna2V5ZG93bicpLFxuXG4gIC8qKlxuICAgKiBTeW1ib2wgZm9yIHRoZSBgdGVtcGxhdGVgIHByb3BlcnR5LlxuICAgKlxuICAgKiBUaGlzIHByb3BlcnR5IHJldHVybnMgYSBjb21wb25lbnQncyB0ZW1wbGF0ZS5cbiAgICpcbiAgICogQHR5cGUge3N0cmluZ3xIVE1MRWxlbWVudH1cbiAgICovXG4gIHRlbXBsYXRlOiBjcmVhdGVTeW1ib2woJ3RlbXBsYXRlJylcbn07XG5cbmV4cG9ydCBkZWZhdWx0IHN5bWJvbHM7XG4iLCIvKipcbiAqIEhlbHBlciBmdW5jdGlvbiBmb3Igc3RhbmRhcmQgY2xhc3NMaXN0LnRvZ2dsZSgpIGJlaGF2aW9yIG9uIG9sZCBicm93c2VycyxcbiAqIG5hbWVseSBJRSAxMS5cbiAqXG4gKiBUaGUgc3RhbmRhcmRcbiAqIFtjbGFzc2xpc3RdKGh0dHBzOi8vZGV2ZWxvcGVyLm1vemlsbGEub3JnL2VuLVVTL2RvY3MvV2ViL0FQSS9FbGVtZW50L2NsYXNzTGlzdClcbiAqIG9iamVjdCBoYXMgYSBgdG9nZ2xlKClgIGZ1bmN0aW9uIHRoYXQgc3VwcG9ydHMgYSBzZWNvbmQgQm9vbGVhbiBwYXJhbWV0ZXJcbiAqIHRoYXQgY2FuIGJlIHVzZWQgdG8gc3VjY2luY3RseSB0dXJuIGEgY2xhc3Mgb24gb3Igb2ZmLiBUaGlzIGZlYXR1cmUgaXMgb2Z0ZW5cbiAqIHVzZWZ1bCBpbiBkZXNpZ25pbmcgY3VzdG9tIGVsZW1lbnRzLCB3aGljaCBtYXkgd2FudCB0byBleHRlcm5hbGx5IHJlZmxlY3RcbiAqIGNvbXBvbmVudCBzdGF0ZSBpbiBhIENTUyBjbGFzcyB0aGF0IGNhbiBiZSB1c2VkIGZvciBzdHlsaW5nIHB1cnBvc2VzLlxuICpcbiAqIFVuZm9ydHVuYXRlbHksIElFIDExIGRvZXMgbm90IHN1cHBvcnQgdGhlIEJvb2xlYW4gcGFyYW1ldGVyIHRvXG4gKiBgY2xhc3NMaXN0LnRvZ2dsZSgpYC4gVGhpcyBoZWxwZXIgZnVuY3Rpb24gYmVoYXZlcyBsaWtlIHRoZSBzdGFuZGFyZFxuICogYHRvZ2dsZSgpYCwgaW5jbHVkaW5nIHN1cHBvcnQgZm9yIHRoZSBCb29sZWFuIHBhcmFtZXRlciwgc28gdGhhdCBpdCBjYW4gYmVcbiAqIHVzZWQgZXZlbiBvbiBJRSAxMS5cbiAqXG4gKiBAZnVuY3Rpb24gdG9nZ2xlQ2xhc3NcbiAqIEBwYXJhbSB7SFRNTEVsZW1lbnR9IGVsZW1lbnQgLSBUaGUgZWxlbWVudCB0byBtb2RpZnlcbiAqIEBwYXJhbSB7c3RyaW5nfSBjbGFzc05hbWUgLSBUaGUgY2xhc3MgdG8gYWRkL3JlbW92ZVxuICogQHBhcmFtIHtib29sZWFufSBbZm9yY2VdIC0gRm9yY2UgdGhlIGNsYXNzIHRvIGJlIGFkZGVkIChpZiB0cnVlKSBvciByZW1vdmVkXG4gKiAgICAgICAgICAgICAgICAgICAgICAgICAgICAoaWYgZmFsc2UpXG4gKi9cbmV4cG9ydCBkZWZhdWx0IGZ1bmN0aW9uIHRvZ2dsZUNsYXNzKGVsZW1lbnQsIGNsYXNzTmFtZSwgZm9yY2UpIHtcbiAgY29uc3QgY2xhc3NMaXN0ID0gZWxlbWVudC5jbGFzc0xpc3Q7XG4gIGNvbnN0IGFkZENsYXNzID0gKHR5cGVvZiBmb3JjZSA9PT0gJ3VuZGVmaW5lZCcpID9cbiAgICAhY2xhc3NMaXN0LmNvbnRhaW5zKGNsYXNzTmFtZSkgOlxuICAgIGZvcmNlO1xuICBpZiAoYWRkQ2xhc3MpIHtcbiAgICBjbGFzc0xpc3QuYWRkKGNsYXNzTmFtZSk7XG4gIH0gZWxzZSB7XG4gICAgY2xhc3NMaXN0LnJlbW92ZShjbGFzc05hbWUpO1xuICB9XG4gIHJldHVybiBhZGRDbGFzcztcbn1cbiJdfQ==
+!function t(e,o,n){function r(a,c){if(!o[a]){if(!e[a]){var l="function"==typeof require&&require;if(!c&&l)return l(a,!0);if(i)return i(a,!0);var u=new Error("Cannot find module '"+a+"'");throw u.code="MODULE_NOT_FOUND",u}var p=o[a]={exports:{}};e[a][0].call(p.exports,function(t){var o=e[a][1][t];return r(o?o:t)},p,p.exports,t,e,o,n)}return o[a].exports}for(var i="function"==typeof require&&require,a=0;a\n :host {\n -webkit-align-items: stretch;\n align-items: stretch;\n display: -webkit-flex;\n display: flex;\n -webkit-flex: 1;\n flex: 1;\n -webkit-justify-content: center;\n justify-content: center;\n }\n\n #arrowNavigationContainer {\n display: -webkit-flex;\n display: flex;\n -webkit-flex: 1;\n flex: 1;\n position: relative;\n }\n\n .navigationButton {\n background: transparent;\n border: 1px solid transparent;\n box-sizing: border-box;\n color: rgba(0, 0, 0, 0.7);\n fill: currentColor;\n margin: 0;\n opacity: 1;\n outline: none; /* REVIEW: Accessibility should be provided by other elements. */\n padding: 0;\n transition: opacity 1s;\n z-index: 1;\n }\n\n .navigationButton:hover:not(:disabled) {\n background: rgba(0, 0, 0, 0.5);\n color: rgba(0, 0, 0, 0.8);\n cursor: pointer;\n }\n .navigationButton:active:not(:disabled) {\n background: rgba(0, 0, 0, 0.7);\n color: rgba(0, 0, 0, 0.9);\n }\n .navigationButton:disabled {\n color: rgba(0, 0, 0, 0.2);\n }\n\n :host(:not(.showArrows)) .navigationButton {\n opacity: 0;\n visibility: hidden;\n }\n\n .navigationButton .icon {\n height: 48px;\n width: 48px;\n }\n\n /* Overlay variant */\n :host(.overlayArrows) {\n position: relative;\n }\n :host(.overlayArrows) .navigationButton {\n bottom: 0;\n color: rgba(255, 255, 255, 0.7);\n position: absolute;\n top: 0;\n }\n :host(.overlayArrows) #buttonLeft {\n left: 0;\n }\n :host(.overlayArrows) #buttonRight {\n right: 0;\n }\n :host(.overlayArrows) .navigationButton:hover:not(:disabled) {\n background: rgba(255, 255, 255, 0.2);\n color: rgba(255, 255, 255, 0.8);\n }\n :host(.overlayArrows) .navigationButton:active:not(:disabled) {\n background: rgba(255, 255, 255, 0.4);\n color: rgba(255, 255, 255, 0.9);\n }\n :host(.overlayArrows) .navigationButton:disabled {\n color: rgba(255, 255, 255, 0.3);\n }\n \n\n \n \n \n \n \n \n \n \n \n '+t+'\n
\n \n \n \n \n \n \n \n '}}]),o}(t);return e}},{"../../basic-component-mixins/src/createSymbol":28,"../../basic-component-mixins/src/symbols":32}],3:[function(t,e,o){"use strict";function n(t){return t&&t.__esModule?t:{default:t}}function r(t,e){if(!(t instanceof e))throw new TypeError("Cannot call a class as a function")}function i(t,e){if(!t)throw new ReferenceError("this hasn't been initialised - super() hasn't been called");return!e||"object"!=typeof e&&"function"!=typeof e?t:e}function a(t,e){if("function"!=typeof e&&null!==e)throw new TypeError("Super expression must either be null or a function, not "+typeof e);t.prototype=Object.create(e&&e.prototype,{constructor:{value:t,enumerable:!1,writable:!0,configurable:!0}}),e&&(Object.setPrototypeOf?Object.setPrototypeOf(t,e):t.__proto__=e)}function c(t){var e=d[t];if(!e){var o=/-([a-z])/g;e=t.replace(o,function(t){return t[1].toUpperCase()}),d[t]=e}return e}function l(t){if(t===HTMLElement||t===Object)return[];var e=Object.getPrototypeOf(t.prototype).constructor,o=l(e),n=Object.getOwnPropertyNames(t.prototype),r=n.filter(function(e){return"function"==typeof Object.getOwnPropertyDescriptor(t.prototype,e).set}),i=r.map(function(t){return u(t)}),a=i.filter(function(t){return o.indexOf(t)<0});return o.concat(a)}function u(t){var e=h[t];if(!e){var o=/([A-Z])/g;e=t.replace(o,"-$1").toLowerCase()}return e}Object.defineProperty(o,"__esModule",{value:!0});var p=function(){function t(t,e){for(var o=0;o=0&&(t.selectedIndex=n,e.stopPropagation())}),t}return i(o,e),c(o,[{key:"selectedIndex",get:function(){return u(o.prototype.__proto__||Object.getPrototypeOf(o.prototype),"selectedIndex",this)},set:function(e){"selectedIndex"in t.prototype&&l(o.prototype.__proto__||Object.getPrototypeOf(o.prototype),"selectedIndex",e,this)}}]),o}(t);return e}},{}],5:[function(t,e,o){"use strict";function n(t,e){if(!(t instanceof e))throw new TypeError("Cannot call a class as a function")}function r(t,e){if(!t)throw new ReferenceError("this hasn't been initialised - super() hasn't been called");return!e||"object"!=typeof e&&"function"!=typeof e?t:e}function i(t,e){if("function"!=typeof e&&null!==e)throw new TypeError("Super expression must either be null or a function, not "+typeof e);t.prototype=Object.create(e&&e.prototype,{constructor:{value:t,enumerable:!1,writable:!0,configurable:!0}}),e&&(Object.setPrototypeOf?Object.setPrototypeOf(t,e):t.__proto__=e)}function a(t,e){if("function"==typeof e)return e(t);var o=function(t){function e(){return n(this,e),r(this,(e.__proto__||Object.getPrototypeOf(e)).apply(this,arguments))}return i(e,t),e}(t);return c(e,o.prototype,u),o}function c(t,e){var o=arguments.length>2&&void 0!==arguments[2]?arguments[2]:[];return Object.getOwnPropertyNames(t).forEach(function(n){if(o.indexOf(n)<0){var r=Object.getOwnPropertyDescriptor(t,n);Object.defineProperty(e,n,r)}}),e}Object.defineProperty(o,"__esModule",{value:!0});var l=function(){function t(t,e){for(var o=0;o=o?o+c.helpers.damping(t-o):t},damping:function(t){var e=-1/(t+1)+1;return e},elementSelection:function(t){var e=t.selectedIndex;if(!(e<0)){var o=t.selectedFraction||0;return e+o}},selectionParts:function(t){var e=t<0?Math.ceil(t):Math.floor(t),o=t-e;return{index:e,fraction:o}},wrappedSelection:function(t,e){return(t%e+e)%e},wrappedSelectionParts:function(t,e,o){return o&&(t=c.helpers.wrappedSelection(t,e)),c.helpers.selectionParts(t)}}},{"./createSymbol":28}],11:[function(t,e,o){"use strict";function n(t){return t&&t.__esModule?t:{default:t}}function r(t,e){if(!(t instanceof e))throw new TypeError("Cannot call a class as a function")}function i(t,e){if(!t)throw new ReferenceError("this hasn't been initialised - super() hasn't been called");return!e||"object"!=typeof e&&"function"!=typeof e?t:e}function a(t,e){if("function"!=typeof e&&null!==e)throw new TypeError("Super expression must either be null or a function, not "+typeof e);t.prototype=Object.create(e&&e.prototype,{constructor:{value:t,enumerable:!1,writable:!0,configurable:!0}}),e&&(Object.setPrototypeOf?Object.setPrototypeOf(t,e):t.__proto__=e)}Object.defineProperty(o,"__esModule",{value:!0});var c=function(){function t(t,e){for(var o=0;o=e){f=!0;break}p+=a}if(!f)return null;var d=getComputedStyle(u),h=parseFloat(d.paddingTop),_=parseFloat(d.paddingBottom),b=s+u.clientTop+h,g=b+u.clientHeight-h-_;return o&&b<=e||!o&&g>=e?p:p-a}function l(t,e){var o=t.scrollTarget,n=o.scrollTop+(e?o.clientHeight:0),r=c(t,n,e),i=t.selectedIndex,a=void 0;if(r&&i===r){var l=(e?1:-1)*o.clientHeight;a=c(t,n+l,e)}else a=r;return a||(a=e?t.items.length-1:0),a!==i&&(t.selectedIndex=a,!0)}Object.defineProperty(o,"__esModule",{value:!0});var u=function(){function t(t,e){for(var o=0;o0&&(t[m]=t[m].substr(0,e-1)),t.selectItemWithTextPrefix(t[m]),y(t)}function p(t,e){var o=t[m]||"";t[m]=o+e.toLowerCase(),t.selectItemWithTextPrefix(t[m]),y(t)}function s(t){t[w]&&(clearTimeout(t[w]),t[w]=!1)}function f(t){t[m]="",s(t)}function y(t){s(t),t[w]=setTimeout(function(){f(t)},j)}Object.defineProperty(o,"__esModule",{value:!0});var d=function(){function t(t,e){for(var o=0;o=0&&(this.selectedIndex=o)}}}]),e}(t);return e};var j=1e3},{"./createSymbol":28,"./symbols":32}],16:[function(t,e,o){"use strict";function n(t){return t&&t.__esModule?t:{default:t}}function r(t,e){if(!(t instanceof e))throw new TypeError("Cannot call a class as a function")}function i(t,e){if(!t)throw new ReferenceError("this hasn't been initialised - super() hasn't been called");return!e||"object"!=typeof e&&"function"!=typeof e?t:e}function a(t,e){if("function"!=typeof e&&null!==e)throw new TypeError("Super expression must either be null or a function, not "+typeof e);t.prototype=Object.create(e&&e.prototype,{constructor:{value:t,enumerable:!1,writable:!0,configurable:!0}}),e&&(Object.setPrototypeOf?Object.setPrototypeOf(t,e):t.__proto__=e)}function c(t,e){return(e%t+t)%t}function l(t,e,o){var n=t.dots;if(n&&0!==n.length){var r=n.length,i=.4,a=.95,l=a-i,u=e+o,p=Math.floor(u),s=Math.ceil(u),f=t.selectionWraps,y=o>=0?p:s,d=o>=0?s:p;f&&(y=c(r,y),d=c(r,d));var h=o<0?Math.ceil(o):Math.floor(o),_=o-h,b=Math.abs(_)*l;n.forEach(function(t,e){var n=void 0;n=0===o?"":e===y?a-b:e===d?i+b:i,t.style.opacity=n})}}function u(t){var e=t.selectedIndex;t.dots.forEach(function(t,o){(0,g.default)(t,"selected",o===e)})}Object.defineProperty(o,"__esModule",{value:!0});var p=function(){function t(t,e){for(var o=0;o=0&&(t.selectedIndex=n)}),t}return a(o,e),p(o,[{key:_.default.itemsChanged,value:function(){f(o.prototype.__proto__||Object.getPrototypeOf(o.prototype),_.default.itemsChanged,this)&&f(o.prototype.__proto__||Object.getPrototypeOf(o.prototype),_.default.itemsChanged,this).call(this),(0,d.default)(this.items,this.$.dots,function(t,e){if(!e)return e=document.createElement("div"),e.classList.add("dot"),e.classList.add("style-scope"),e.classList.add("basic-page-dots"),e.setAttribute("role","none"),e}),u(this)}},{key:_.default.itemSelected,value:function(t,e){f(o.prototype.__proto__||Object.getPrototypeOf(o.prototype),_.default.itemSelected,this)&&f(o.prototype.__proto__||Object.getPrototypeOf(o.prototype),_.default.itemSelected,this).call(this,t,e);var n=this.items.indexOf(t),r=this.dots;if(r&&r.length>n){var i=this.dots[n];i&&(0,g.default)(i,"selected",e)}}},{key:"dots",get:function(){return[].slice.call(this.$.dots.querySelectorAll(".dot"))}},{key:"selectedFraction",get:function(){return f(o.prototype.__proto__||Object.getPrototypeOf(o.prototype),"selectedFraction",this)},set:function(e){"selectedFraction"in t.prototype&&s(o.prototype.__proto__||Object.getPrototypeOf(o.prototype),"selectedFraction",e,this),l(this,this.selectedIndex,e)}},{key:"selectedIndex",get:function(){return f(o.prototype.__proto__||Object.getPrototypeOf(o.prototype),"selectedIndex",this)},set:function(e){"selectedIndex"in t.prototype&&s(o.prototype.__proto__||Object.getPrototypeOf(o.prototype),"selectedIndex",e,this),u(this)}},{key:_.default.template,get:function(){var t=f(o.prototype.__proto__||Object.getPrototypeOf(o.prototype),_.default.template,this)||"";return'\n \n\n
\n \n '+t+"\n
\n "}}]),o}(t);return e}},{"../../basic-component-mixins/src/renderArrayAsElements":30,"../../basic-component-mixins/src/symbols":32,"../../basic-component-mixins/src/toggleClass":33}],17:[function(t,e,o){"use strict";function n(t){return t&&t.__esModule?t:{default:t}}function r(t,e){if(!(t instanceof e))throw new TypeError("Cannot call a class as a function")}function i(t,e){if(!t)throw new ReferenceError("this hasn't been initialised - super() hasn't been called");return!e||"object"!=typeof e&&"function"!=typeof e?t:e}function a(t,e){if("function"!=typeof e&&null!==e)throw new TypeError("Super expression must either be null or a function, not "+typeof e);t.prototype=Object.create(e&&e.prototype,{constructor:{value:t,enumerable:!1,writable:!0,configurable:!0}}),e&&(Object.setPrototypeOf?Object.setPrototypeOf(t,e):t.__proto__=e)}Object.defineProperty(o,"__esModule",{value:!0});var c=function(){function t(t,e){for(var o=0;o\n :host {\n display: -webkit-flex;\n display: flex;\n position: relative;\n }\n\n #buttons {\n bottom: 0;\n box-sizing: border-box;\n padding: 0.5em;\n position: absolute;\n text-align: center;\n width: 100%;\n z-index: 1;\n }\n\n button {\n background: transparent;\n border: none;\n fill: rgba(255, 255, 255, 0.5);\n padding: 0;\n transition: fill 0.5s;\n vertical-align: middle;\n }\n :host(:hover) button {\n fill: rgba(255, 255, 255, 0.7);\n }\n button:hover {\n fill: rgba(255, 255, 255, 0.85);\n }\n button:active {\n fill: white;\n }\n\n .icon {\n height: 30px;\n width: 30px;\n }\n #playButton .icon {\n height: 40px;\n width: 40px;\n }\n\n :host(.playing) .pausedControl {\n display: none;\n }\n :host(:not(.playing)) .playingControl {\n display: none;\n }\n\n #container {\n display: -webkit-flex;\n display: flex;\n -webkit-flex: 1;\n flex: 1;\n }\n\n #container ::slotted(*) {\n -webkit-flex: 1;\n flex: 1;\n }\n \n\n \n\n \n '+t+"\n
\n "}}]),o}(t);return e}},{"../../basic-component-mixins/src/safeAttributes":31,"../../basic-component-mixins/src/symbols":32}],18:[function(t,e,o){"use strict";function n(t){return t&&t.__esModule?t:{default:t}}function r(t,e){if(!(t instanceof e))throw new TypeError("Cannot call a class as a function")}function i(t,e){if(!t)throw new ReferenceError("this hasn't been initialised - super() hasn't been called");return!e||"object"!=typeof e&&"function"!=typeof e?t:e}function a(t,e){if("function"!=typeof e&&null!==e)throw new TypeError("Super expression must either be null or a function, not "+typeof e);t.prototype=Object.create(e&&e.prototype,{constructor:{value:t,enumerable:!1,writable:!0,configurable:!0}}),e&&(Object.setPrototypeOf?Object.setPrototypeOf(t,e):t.__proto__=e)}function c(t){var e=function(e){function o(){r(this,o);var t=i(this,(o.__proto__||Object.getPrototypeOf(o)).call(this));return"undefined"==typeof t.selectionAnimationDuration&&(t.selectionAnimationDuration=t[k.default.defaults].selectionAnimationDuration),"undefined"==typeof t.selectionAnimationEffect&&null==t.selectionAnimationKeyframes&&(t.selectionAnimationEffect=t[k.default.defaults].selectionAnimationEffect),t[k.default.dragging]=!1,t}return a(o,e),g(o,[{key:k.default.itemAdded,value:function(t){t.setAttribute("aria-hidden",!1)}},{key:k.default.itemsChanged,value:function(){O(o.prototype.__proto__||Object.getPrototypeOf(o.prototype),k.default.itemsChanged,this)&&O(o.prototype.__proto__||Object.getPrototypeOf(o.prototype),k.default.itemsChanged,this).call(this),y(this),s(this)}},{key:"resetAnimations",value:function(){y(this)}},{key:k.default.defaults,get:function(){var t=O(o.prototype.__proto__||Object.getPrototypeOf(o.prototype),k.default.defaults,this)||{};return t.selectionAnimationDuration=250,t.selectionAnimationEffect="slide",t}},{key:k.default.dragging,get:function(){return this[M]},set:function(e){var n=this[k.default.dragging];this[M]=e,k.default.dragging in t.prototype&&v(o.prototype.__proto__||Object.getPrototypeOf(o.prototype),k.default.dragging,e,this),e&&!n&&(this[F]=!0)}},{key:"selectedFraction",get:function(){return O(o.prototype.__proto__||Object.getPrototypeOf(o.prototype),"selectedFraction",this)||0},set:function(e){"selectedFraction"in t.prototype&&v(o.prototype.__proto__||Object.getPrototypeOf(o.prototype),"selectedFraction",e,this),s(this,this.selectedIndex,e)}},{key:"selectedIndex",get:function(){return O(o.prototype.__proto__||Object.getPrototypeOf(o.prototype),"selectedIndex",this)},set:function(e){"selectedIndex"in t.prototype&&v(o.prototype.__proto__||Object.getPrototypeOf(o.prototype),"selectedIndex",e,this),s(this,e,0)}},{key:"selectionAnimationDuration",get:function(){return this[T]},set:function(e){this[T]=e,"selectionAnimationDuration"in t.prototype&&v(o.prototype.__proto__||Object.getPrototypeOf(o.prototype),"selectionAnimationDuration",e,this)}},{key:"selectionAnimationEffect",get:function(){return this[D]},set:function(e){this[D]=e,"selectionAnimationEffect"in t.prototype&&v(o.prototype.__proto__||Object.getPrototypeOf(o.prototype),"selectionAnimationEffect",e,this),this.selectionAnimationKeyframes=c.standardEffectKeyframes[e]}},{key:"selectionAnimationKeyframes",get:function(){return this[I]},set:function(e){this[I]=e,"selectionAnimationKeyframes"in t.prototype&&v(o.prototype.__proto__||Object.getPrototypeOf(o.prototype),"selectionAnimationKeyframes",e,this),y(this),s(this)}},{key:"selectionWraps",get:function(){return O(o.prototype.__proto__||Object.getPrototypeOf(o.prototype),"selectionWraps",this)},set:function(e){"selectionWraps"in t.prototype&&v(o.prototype.__proto__||Object.getPrototypeOf(o.prototype),"selectionWraps",e,this),y(this),s(this)}}]),o}(t);return e}function l(t,e,o){y(t);var n=t.items,r=t.selectionAnimationKeyframes;t[E]=!0;var i=c.helpers.effectTimingsForSelectionAnimation(t,e,o),a=n.length,l=t.selectionWraps,u=P.default.helpers.selectionParts(o,a,l).index,s=b(a,l,e,o),f=s>=0,h=u+(f?1:-1);l?h=P.default.helpers.wrappedSelection(h,a):p(t,h)||(h=null);
+var g=void 0;i.forEach(function(e,o){var i=n[o];if(e){_(i,!0);var a=i.animate(r,e);t[S][o]=a,o===h&&(h=null),0!==e.endDelay&&(g={animation:a,index:o,timing:e,forward:f})}else _(i,!1)}),null!=g?(g.nextUpIndex=h,g.animation.onfinish=function(e){return d(t,g)},t[C]=g.animation):t[E]=!1}function u(t,e){if(null==t[S])return null;var o=t[S][e];if(!o){var n=t.items[e];o=n.animate(t.selectionAnimationKeyframes,{duration:t.selectionAnimationDuration,fill:"both"}),o.pause(),t[S][e]=o}return o}function p(t,e){return e>=0&&t.items&&e1&&void 0!==arguments[1]?arguments[1]:t.selectedIndex,o=arguments.length>2&&void 0!==arguments[2]?arguments[2]:t.selectedFraction,n=t.items?t.items.length:0;if(0!==n&&!(e<0)){var r=e+o;r=t.selectionWraps?P.default.helpers.wrappedSelection(r,n):P.default.helpers.dampedSelection(r,n);var i=t[A];if(t[k.default.dragging]||null==i||i===r){if(0===o&&t[E])return;f(t,r)}else l(t,i,r);t[A]=r}}function f(t,e){t[F]&&(y(t),t[F]=!1);var o=c.helpers.animationFractionsForSelection(t,e);o.map(function(e,o){var n=t.items[o];null!=e?(_(n,!0),h(t,o,e)):_(n,!1)})}function y(t){var e=t[S];e&&e.forEach(function(t,o){t&&(t.cancel(),e[o]=null)});var o=t.items?t.items.length:0;e&&e.length===o||(t[S]=new Array(o))}function d(t,e){var o=e.nextUpIndex;if(null!=o){t[S][o]&&(t[S][o].cancel(),t[S][o]=null);var n=e.forward?0:1;h(t,o,n),_(t.items[o],!0)}t[C].onfinish=null,t[E]=!1}function h(t,e,o){var n=u(t,e);if(n){var r=t.selectionAnimationDuration;r&&(n.currentTime=o*r)}}function _(t,e){t.style.visibility=e?"visible":"hidden"}function b(t,e,o,n){var r=n-o;if(e&&t>1){var i=t-Math.abs(r);i<=1&&(r=r<0?i:-i)}return r}Object.defineProperty(o,"__esModule",{value:!0});var g=function(){function t(t,e){for(var o=0;o=0&&a<=1?a:null})}},effectTimingsForSelectionAnimation:function(t,e,o){var n=t.items;if(n){var r=n.length,i=t.selectionWraps,a=P.default.helpers.wrappedSelectionParts(o,r,i).index,c=b(r,i,e,o),l=c>=0?"normal":"reverse",u="both",p=t.selectionAnimationDuration,s=0!==c?2*p/Math.ceil(Math.abs(c)):0,f=n.map(function(t,e){var n=b(r,i,e,o),p=c-n;if(c<0&&(p=-p),Math.ceil(p)>=0&&p<=Math.abs(c)){var f=s*(p-1)/2,y=e===a?-s/2:0;return{duration:s,direction:l,fill:u,delay:f,endDelay:y}}return null});return f}}},c.standardEffectKeyframes={crossfade:[{opacity:0},{opacity:1},{opacity:0}],reveal:[{transform:"translateX(0%)",zIndex:0},{transform:"translateX(0%)",zIndex:1},{transform:"translateX(-100%)",zIndex:2}],revealWithFade:[{transform:"translateX(0%) scale(0.75)",opacity:0,zIndex:0},{transform:"translateX(0%) scale(1.0)",opacity:1,zIndex:1},{transform:"translateX(-100%) scale(1.0)",opacity:1,zIndex:2}],showAdjacent:[{transform:"translateX(78%) scale(0.7)",zIndex:0},{transform:"translateX(0%) scale(0.82)",zIndex:1},{transform:"translateX(-78%) scale(0.7)",zIndex:0}],slide:[{transform:"translateX(100%)"},{transform:"translateX(-100%)"}],slideWithGap:[{transform:"translateX(110%)"},{transform:"translateX(-110%)"}]}},{"./FractionalSelectionMixin":10,"./createSymbol":28,"./symbols":32}],19:[function(t,e,o){"use strict";function n(t){return t&&t.__esModule?t:{default:t}}function r(t,e){if(!(t instanceof e))throw new TypeError("Cannot call a class as a function")}function i(t,e){if(!t)throw new ReferenceError("this hasn't been initialised - super() hasn't been called");return!e||"object"!=typeof e&&"function"!=typeof e?t:e}function a(t,e){if("function"!=typeof e&&null!==e)throw new TypeError("Super expression must either be null or a function, not "+typeof e);t.prototype=Object.create(e&&e.prototype,{constructor:{value:t,enumerable:!1,writable:!0,configurable:!0}}),e&&(Object.setPrototypeOf?Object.setPrototypeOf(t,e):t.__proto__=e)}Object.defineProperty(o,"__esModule",{value:!0});var c=function(){function t(t,e){for(var o=0;o\n :host([generic=""]) ::slotted(.selected) {\n background-color: highlight;\n color: highlighttext;\n }\n \n '+t+"\n "}}]),e}(t);return e}},{"../src/symbols":32}],21:[function(t,e,o){"use strict";function n(t,e){if(!(t instanceof e))throw new TypeError("Cannot call a class as a function")}function r(t,e){if(!t)throw new ReferenceError("this hasn't been initialised - super() hasn't been called");return!e||"object"!=typeof e&&"function"!=typeof e?t:e}function i(t,e){if("function"!=typeof e&&null!==e)throw new TypeError("Super expression must either be null or a function, not "+typeof e);t.prototype=Object.create(e&&e.prototype,{constructor:{value:t,enumerable:!1,writable:!0,configurable:!0}}),e&&(Object.setPrototypeOf?Object.setPrototypeOf(t,e):t.__proto__=e)}Object.defineProperty(o,"__esModule",{value:!0});var a=function(){function t(t,e){for(var o=0;oi?e.scrollTop+=r-i:n0;)e.content.appendChild(o.childNodes[0]);return e}function l(t,e){window.WebComponents.ShadowCSS.shimStyling(t.content,e)}Object.defineProperty(o,"__esModule",{value:!0});var u=t("../src/symbols"),p=n(u);o.default=function(t){var e=function(t){function e(){r(this,e);var t=i(this,(e.__proto__||Object.getPrototypeOf(e)).call(this)),o=t[p.default.template];if(o){"string"==typeof o&&(o=c(o)),window.ShadowDOMPolyfill&&l(o,t.localName);var n=t.attachShadow({mode:"open"}),a=document.importNode(o.content,!0);n.appendChild(a)}return t}return a(e,t),e}(t);return e}},{"../src/symbols":32}],24:[function(t,e,o){"use strict";function n(t){return t&&t.__esModule?t:{default:t}}function r(t,e){if(!(t instanceof e))throw new TypeError("Cannot call a class as a function")}function i(t,e){if(!t)throw new ReferenceError("this hasn't been initialised - super() hasn't been called");return!e||"object"!=typeof e&&"function"!=typeof e?t:e}function a(t,e){if("function"!=typeof e&&null!==e)throw new TypeError("Super expression must either be null or a function, not "+typeof e);t.prototype=Object.create(e&&e.prototype,{constructor:{value:t,enumerable:!1,writable:!0,configurable:!0}}),e&&(Object.setPrototypeOf?Object.setPrototypeOf(t,e):t.__proto__=e)}function c(t,e){var o=t.items.length,n=t.selectionWraps?(e%o+o)%o:Math.max(Math.min(e,o-1),0),r=t.selectedIndex;return r!==n&&(t.selectedIndex=n,!0)}function l(t){var e=t.items,o=e?e.length:0,n=t.selectedItem;if(n)if(0===o)t.selectedItem=null;else{var r=Array.prototype.indexOf.call(e,n),i=t.selectedIndex;if(r<0){var a=Math.min(i,o-1);t.selectedItem=e[a]}else r!==i&&(t.selectedIndex=r)}else t.selectionRequired&&(t.selectedIndex=0)}function u(t){var e=void 0,o=void 0,n=t.items;if(null!=n&&0!==n.length||(e=!1,o=!1),t.selectionWraps)e=!0,o=!0;else{var r=t.selectedIndex;r<0&&n.length>0?(e=!0,o=!0):(o=r>0,e=r0;a&&e>=0&&e=0?i[e]:null,this[w]=r}else r=this[w];if("selectedIndex"in t.prototype&&f(o.prototype.__proto__||Object.getPrototypeOf(o.prototype),"selectedIndex",e,this),e!==n){this[j]=e;var c=new CustomEvent("selected-index-changed",{detail:{selectedIndex:e,value:e}});this.dispatchEvent(c)}this[P]!==r&&(this.selectedItem=r)}},{key:"selectedItem",get:function(){return this[w]||null},set:function(e){var n=this[P],r=void 0;if(e!==this[w]){var i=this.items,a=i&&i.length>0;r=a?Array.prototype.indexOf.call(i,e):-1,this[m]=r,r<0&&(e=null),this[w]=e}else r=this[m];if("selectedItem"in t.prototype&&f(o.prototype.__proto__||Object.getPrototypeOf(o.prototype),"selectedItem",e,this),e!==n){this[P]=e,n&&this[_.default.itemSelected](n,!1),e&&this[_.default.itemSelected](e,!0),u(this);var c=new CustomEvent("selected-item-changed",{detail:{selectedItem:e,value:e}});this.dispatchEvent(c)}this[j]!==r&&(this.selectedIndex=r)}},{key:"selectionRequired",get:function(){return this[v]},set:function(e){this[v]=e,"selectionRequired"in t.prototype&&f(o.prototype.__proto__||Object.getPrototypeOf(o.prototype),"selectionRequired",e,this),l(this)}},{key:"selectionWraps",get:function(){return this[O]},set:function(e){this[O]="true"===String(e),"selectionWraps"in t.prototype&&f(o.prototype.__proto__||Object.getPrototypeOf(o.prototype),"selectionWraps",e,this),u(this)}}]),o}(t);return e}},{"./createSymbol":28,"./symbols":32}],25:[function(t,e,o){"use strict";function n(t){return t&&t.__esModule?t:{default:t}}function r(t,e){if(!(t instanceof e))throw new TypeError("Cannot call a class as a function")}function i(t,e){if(!t)throw new ReferenceError("this hasn't been initialised - super() hasn't been called");return!e||"object"!=typeof e&&"function"!=typeof e?t:e}function a(t,e){if("function"!=typeof e&&null!==e)throw new TypeError("Super expression must either be null or a function, not "+typeof e);t.prototype=Object.create(e&&e.prototype,{constructor:{value:t,enumerable:!1,writable:!0,configurable:!0}}),e&&(Object.setPrototypeOf?Object.setPrototypeOf(t,e):t.__proto__=e)}function c(t){return"pen"===t.pointerType||"touch"===t.pointerType&&t.isPrimary}function l(t,e,o){if(t[g.default.dragging]=!1,t[v]>=20)t[g.default.goLeft]();else if(t[v]<=-20)t[g.default.goRight]();else{s(t,e);var n=t.travelFraction;n>=.5?t[g.default.goRight]():n<=-.5&&t[g.default.goLeft]()}t.travelFraction=0,t[v]=null,t[O]=null}function u(t,e,o){return t[v]=e-t[w],t[O]=o-t[j],t[w]=e,t[j]=o,Math.abs(t[v])>Math.abs(t[O])&&(s(t,e),!0)}function p(t,e,o){t[g.default.dragging]=!0,t[P]=e,t[w]=e,t[j]=o,t[v]=0,t[O]=0}function s(t,e){var o=t.offsetWidth,n=t[P]-e,r=o>0?n/o:0;t.travelFraction=r}Object.defineProperty(o,"__esModule",{value:!0});var f=function(){function t(t,e){for(var o=0;o0&&u(t)}function u(t){c(t),t[O]=setTimeout(function(){p(t)},t.selectionTimerDuration)}function p(t){var e=t.items;e&&e.length>0&&(null==t.selectedIndex||t.selectedIndex===e.length-1?t.selectFirst():t.selectNext())}Object.defineProperty(o,"__esModule",{value:!0});var s=function(){function t(t,e){for(var o=0;o0?1:-1}function p(t,e){t[m]&&clearTimeout(t[m]),t[m]=setTimeout(function(){s(t)},x);var o=e.deltaX,n=e.deltaY,r=u(o)*(o-t[O]);if(t[O]=o,Math.abs(o)0)t[v]=!1;else if(t[v])return!0;t[j]+=o;var i=t.offsetWidth,a=i>0?t[j]/i:0;return t[g.default.dragging]=!0,a=u(a)*Math.min(Math.abs(a),1),t.travelFraction=a,1===a?(t[g.default.dragging]=!1,t[g.default.goRight](),c(t)):a===-1&&(t[g.default.dragging]=!1,t[g.default.goLeft](),c(t)),!0}function s(t){t[g.default.dragging]=!1;var e=t.travelFraction;e>=.5?t[g.default.goRight]():e<=-.5&&t[g.default.goLeft](),l(t)}Object.defineProperty(o,"__esModule",{value:!0});var f=function(){function t(t,e){for(var o=0;o0;){var t=i.shift();t()}}Object.defineProperty(o,"__esModule",{value:!0}),o.default=n;var i=[],a=document.createTextNode(""),c=0,l=new MutationObserver(r);l.observe(a,{characterData:!0})},{}],30:[function(t,e,o){"use strict";function n(t,e,o){for(t.forEach(function(t,n){var r=e.childNodes[n],i=o(t,r);i&&(r?i!==r&&e.replaceChild(i,r):e.appendChild(i))});e.childNodes.length>t.length;)e.removeChild(e.childNodes[t.length])}Object.defineProperty(o,"__esModule",{value:!0}),o.default=n},{}],31:[function(t,e,o){"use strict";function n(t){return t&&t.__esModule?t:{default:t}}function r(t,e,o){if(null===o||"undefined"==typeof o)t.removeAttribute(e);else{var n=String(o);t.getAttribute(e)!==n&&t.setAttribute(e,o)}}Object.defineProperty(o,"__esModule",{value:!0});var i=t("./createSymbol"),a=n(i),c=t("./toggleClass"),l=n(c),u=(0,a.default)("safeToSetAttributes"),p=(0,a.default)("pendingAttributes"),s=(0,a.default)("pendingClasses");o.default={connected:function(t){if(t[u]=!0,t[p]){for(var e in t[p]){var o=t[p][e];r(t,e,o)}t[p]=null}if(t[s]){for(var n in t[s]){var i=t[s][n];(0,l.default)(t,n,i)}t[s]=null}},setAttribute:function(t,e,o){t[u]?r(t,e,o):(t[p]||(t[p]={}),t[p][e]=o)},toggleClass:function(t,e,o){t[u]?(0,l.default)(t,e,o):(t[s]||(t[s]={}),t[s][e]=o)}}},{"./createSymbol":28,"./toggleClass":33}],32:[function(t,e,o){"use strict";function n(t){return t&&t.__esModule?t:{default:t}}Object.defineProperty(o,"__esModule",{value:!0});var r=t("./createSymbol"),i=n(r),a={defaults:(0,i.default)("defaults"),dragging:(0,i.default)("dragging"),goDown:(0,i.default)("goDown"),goEnd:(0,i.default)("goEnd"),goLeft:(0,i.default)("goLeft"),goRight:(0,i.default)("goRight"),goStart:(0,i.default)("goStart"),goUp:(0,i.default)("goUp"),itemAdded:(0,i.default)("itemAdded"),itemsChanged:(0,i.default)("itemsChanged"),itemSelected:(0,i.default)("itemSelected"),keydown:(0,i.default)("keydown"),template:(0,i.default)("template")};o.default=a},{"./createSymbol":28}],33:[function(t,e,o){"use strict";function n(t,e,o){var n=t.classList,r="undefined"==typeof o?!n.contains(e):o;return r?n.add(e):n.remove(e),r}Object.defineProperty(o,"__esModule",{value:!0}),o.default=n},{}]},{},[1]);
+//# sourceMappingURL=basic-component-mixins.js.map
diff --git a/packages/basic-component-mixins/dist/basic-component-mixins.js.map b/packages/basic-component-mixins/dist/basic-component-mixins.js.map
new file mode 100644
index 00000000..028cb856
--- /dev/null
+++ b/packages/basic-component-mixins/dist/basic-component-mixins.js.map
@@ -0,0 +1 @@
+{"version":3,"sources":["node_modules/browser-pack/_prelude.js","packages/basic-component-mixins/globals.js","packages/basic-component-mixins/src/ArrowSelectionMixin.js","packages/basic-component-mixins/src/AttributeMarshallingMixin.js","packages/basic-component-mixins/src/ClickSelectionMixin.js","packages/basic-component-mixins/src/ComposableMixin.js","packages/basic-component-mixins/src/ContentItemsMixin.js","packages/basic-component-mixins/src/DirectionSelectionMixin.js","packages/basic-component-mixins/src/DistributedChildrenContentMixin.js","packages/basic-component-mixins/src/DistributedChildrenMixin.js","packages/basic-component-mixins/src/FractionalSelectionMixin.js","packages/basic-component-mixins/src/GenericMixin.js","packages/basic-component-mixins/src/KeyboardDirectionMixin.js","packages/basic-component-mixins/src/KeyboardMixin.js","packages/basic-component-mixins/src/KeyboardPagedSelectionMixin.js","packages/basic-component-mixins/src/KeyboardPrefixSelectionMixin.js","packages/basic-component-mixins/src/PageDotsMixin.js","packages/basic-component-mixins/src/PlayControlsMixin.js","packages/basic-component-mixins/src/SelectionAnimationMixin.js","packages/basic-component-mixins/src/SelectionAriaActiveMixin.js","packages/basic-component-mixins/src/SelectionHighlightMixin.js","packages/basic-component-mixins/src/SelectionInViewMixin.js","packages/basic-component-mixins/src/ShadowElementReferencesMixin.js","packages/basic-component-mixins/src/ShadowTemplateMixin.js","packages/basic-component-mixins/src/SingleSelectionMixin.js","packages/basic-component-mixins/src/SwipeDirectionMixin.js","packages/basic-component-mixins/src/TimerSelectionMixin.js","packages/basic-component-mixins/src/TrackpadDirectionMixin.js","packages/basic-component-mixins/src/createSymbol.js","packages/basic-component-mixins/src/microtask.js","packages/basic-component-mixins/src/renderArrayAsElements.js","packages/basic-component-mixins/src/safeAttributes.js","packages/basic-component-mixins/src/symbols.js","packages/basic-component-mixins/src/toggleClass.js"],"names":["e","t","n","r","s","o","u","a","require","i","f","Error","code","l","exports","call","length","1","module","_ArrowSelectionMixin","_AttributeMarshallingMixin","_ClickSelectionMixin","_ComposableMixin","_ContentItemsMixin","_createSymbol","_DirectionSelectionMixin","_DistributedChildrenMixin","_DistributedChildrenContentMixin","_GenericMixin","_KeyboardMixin","_KeyboardDirectionMixin","_KeyboardPagedSelectionMixin","_KeyboardPrefixSelectionMixin","_microtask","_PageDotsMixin","_PlayControlsMixin","_safeAttributes","_SelectionAnimationMixin","_SelectionAriaActiveMixin","_SelectionHighlightMixin","_SelectionInViewMixin","_ShadowElementReferencesMixin","_ShadowTemplateMixin","_SingleSelectionMixin","_SwipeDirectionMixin","_symbols","_TimerSelectionMixin","_TrackpadDirectionMixin","window","Basic","ArrowSelectionMixin","_ArrowSelectionMixin2","default","AttributeMarshallingMixin","_AttributeMarshallingMixin2","ClickSelectionMixin","_ClickSelectionMixin2","ComposableMixin","_ComposableMixin2","ContentItemsMixin","_ContentItemsMixin2","createSymbol","_createSymbol2","DirectionSelectionMixin","_DirectionSelectionMixin2","DistributedChildrenMixin","_DistributedChildrenMixin2","DistributedChildrenContentMixin","_DistributedChildrenContentMixin2","generic","_GenericMixin2","KeyboardMixin","_KeyboardMixin2","KeyboardDirectionMixin","_KeyboardDirectionMixin2","KeyboardPagedSelectionMixin","_KeyboardPagedSelectionMixin2","KeyboardPrefixSelectionMixin","_KeyboardPrefixSelectionMixin2","microtask","_microtask2","PageDotsMixin","_PageDotsMixin2","PlayControlsMixin","_PlayControlsMixin2","safeAttributes","_safeAttributes2","SelectionAnimationMixin","_SelectionAnimationMixin2","SelectionAriaActiveMixin","_SelectionAriaActiveMixin2","SelectionHighlightMixin","_SelectionHighlightMixin2","SelectionInViewMixin","_SelectionInViewMixin2","ShadowElementReferencesMixin","_ShadowElementReferencesMixin2","ShadowTemplateMixin","_ShadowTemplateMixin2","SingleSelectionMixin","_SingleSelectionMixin2","SwipeDirectionMixin","_SwipeDirectionMixin2","symbols","_symbols2","TimerSelectionMixin","_TimerSelectionMixin2","TrackpadDirectionMixin","_TrackpadDirectionMixin2","assumeButtonFocus","element","button","addEventListener","event","focus","preventDefault","deviceSupportsTouch","DocumentTouch","document","listenForMouse","mousedownListenerSymbol","mouseTimeoutSymbol","clearTimeout","lastMouseXSymbol","pageX","lastMouseYSymbol","pageY","mousemoveListenerSymbol","setTimeout","mouseDetected","showArrows","removeEventListener","classList","add","base","ArrowSelection","_base","_classCallCheck","this","_this","_possibleConstructorReturn","__proto__","Object","getPrototypeOf","$","buttonLeft","selectPrevious","stopPropagation","buttonRight","selectNext","_inherits","_createClass","key","value","_get","prototype","contains","get","set","canSelectNext","_set","disabled","canSelectPrevious","defaults","navigationAxis","template","baseTemplate","attributeToPropertyName","attributeName","propertyName","attributeToPropertyNames","hypenRegEx","replace","match","toUpperCase","attributesForClass","classFn","HTMLElement","baseClass","constructor","baseAttributes","propertyNames","getOwnPropertyNames","setterNames","filter","getOwnPropertyDescriptor","attributes","map","setterName","propertyNameToAttribute","diff","attribute","indexOf","concat","propertyNamesToAttributes","uppercaseRegEx","toLowerCase","AttributeMarshalling","apply","arguments","oldValue","newValue","connected","setAttribute","className","toggleClass","indexOfContainingItem","target","items","itemCount","item","ClickSelection","path","index","selectedIndex","composeClass","mixin","Subclass","_base2","copyOwnProperties","NON_MIXABLE_OBJECT_PROPERTIES","source","ignorePropertyNames","undefined","forEach","name","descriptor","defineProperty","Composable","_len","mixins","Array","_key","reduce","filterAuxiliaryElements","auxiliaryTags","localName","_toggleClass","itemsSymbol","itemInitializedSymbol","ContentItems","itemsChanged","itemAdded","itemSelected","selected","_toggleClass2","_this2","dispatchEvent","CustomEvent","content","DirectionSelection","goDown","goEnd","selectLast","goLeft","goRight","goStart","selectFirst","goUp","selectedFraction","DistributedChildrenContent","shadowRoot","slots","querySelectorAll","slot","contentChanged","distributedChildren","console","warn","expandContentElements","nodes","includeTextNodes","_ref","expanded","node","isSlot","HTMLSlotElement","assignedNodes","flatten","Text","flattened","_toConsumableArray","DistributedChildren","children","childNodes","strings","distributedChildNodes","child","textContent","join","FractionalSelection","selectedFractionSymbol","helpers","dampedSelection","selection","bound","damped","damping","x","y","elementSelection","selectionParts","Math","ceil","floor","fraction","wrappedSelection","wrappedSelectionParts","wrap","genericSymbol","Generic","parsed","String","removeAttribute","navigationAxisSymbol","KeyboardDirection","keydown","handled","axis","horizontal","vertical","keyCode","metaKey","altKey","Keyboard","getAttribute","tabindex","getIndexOfItemAtY","downward","start","end","step","scrollTarget","topOfClientArea","offsetTop","clientTop","itemIndex","itemTop","found","itemBottom","offsetHeight","itemStyle","getComputedStyle","itemPaddingTop","parseFloat","paddingTop","itemPaddingBottom","paddingBottom","contentTop","contentBottom","clientHeight","scrollOnePage","edge","scrollTop","indexOfItemAtEdge","newIndex","delta","KeyboardPagedSelection","pageUp","pageDown","getIndexOfItemWithTextPrefix","prefix","itemTextContents","getItemTextContents","prefixLength","itemTextContent","substr","itemTextContentsSymbol","text","alt","handleBackspace","typedPrefixSymbol","selectItemWithTextPrefix","setPrefixTimeout","handlePlainCharacter","char","resetPrefixTimeout","prefixTimeoutSymbol","resetTypedPrefix","PREFIX_TIMEOUT_DURATION","KeyboardPrefixSelection","resetPrefix","ctrlKey","which","fromCharCode","keepIndexWithinBounds","renderTransition","dots","dotCount","opacityMinimum","opacityMaximum","opacityRange","fractionalIndex","leftIndex","rightIndex","selectionWraps","awayIndex","towardIndex","truncatedSelectedFraction","progress","opacityProgressThroughRange","abs","dot","dotOpacity","style","opacity","refreshDots","_renderArrayAsElements","PageDots","dotIndex","_renderArrayAsElements2","createElement","slice","PlayControls","previousButton","playButton","playing","nextButton","SelectionAnimation","selectionAnimationDuration","selectionAnimationEffect","selectionAnimationKeyframes","dragging","_resetAnimations","renderSelection","draggingSymbol","previousValue","resetAnimationsOnNextRenderSymbol","selectionAnimationDurationSymbol","selectionAnimationEffectSymbol","standardEffectKeyframes","selectionAnimationKeyframesSymbol","animateSelection","fromSelection","toSelection","keyframes","playingAnimationSymbol","timings","effectTimingsForSelectionAnimation","selectionIndex","_FractionalSelectionMixin2","totalSteps","stepsToIndex","forward","nextUpIndex","isItemIndexInBounds","lastAnimationDetails","timing","showItem","animation","animate","animationSymbol","endDelay","onfinish","selectionAnimationFinished","lastAnimationSymbol","getAnimationForItemIndex","duration","fill","pause","previousSelection","previousSelectionSymbol","renderSelectionInstantly","animationFractions","animationFractionsForSelection","animationFraction","setAnimationFraction","animations","cancel","details","currentTime","flag","visibility","allowWrap","steps","wrapSteps","_FractionalSelectionMixin","toIndex","direction","totalDuration","stepDuration","positionInSequence","delay","crossfade","reveal","transform","zIndex","revealWithFade","showAdjacent","slide","slideWithGap","idCount","SelectionAriaActive","role","id","baseId","itemId","SelectionHighlight","SelectionInView","selectedItem","scrollItemIntoView","elementTop","elementBottom","scrollBottom","ShadowElementReferences","nodesWithIds","createTemplateWithInnerHTML","innerHTML","div","appendChild","shimTemplateStyles","tag","WebComponents","ShadowCSS","shimStyling","ShadowTemplate","ShadowDOMPolyfill","root","attachShadow","mode","clone","importNode","selectIndex","count","boundedIndex","max","min","previousIndex","trackSelectedItem","previousSelectedItem","indexInCurrentItems","previousSelectedIndex","newSelectedIndex","selectionRequired","updatePossibleNavigations","canSelectNextSymbol","canSelectPreviousSymbol","selectionRequiredSymbol","selectionWrapsSymbol","externalSelectedIndexSymbol","externalSelectedItemSymbol","internalSelectedIndexSymbol","internalSelectedItemSymbol","SingleSelection","previousCanSelectNext","previousCanSelectPrevious","hasItems","detail","isEventForPenOrPrimaryTouch","pointerType","isPrimary","touchEnd","clientX","clientY","deltaXSymbol","trackTo","travelFraction","deltaYSymbol","touchMove","previousXSymbol","previousYSymbol","touchStart","startXSymbol","width","offsetWidth","dragDistance","multiTouchSymbol","travelFractionSymbol","SwipeDirection","PointerEvent","touches","changedTouches","touchAction","clearTimer","timerTimeoutSymbol","restartTimer","startTimer","selectNextWithWrap","selectionTimerDuration","playingSymbol","selectionTimerDurationSymbol","TimerSelection","previousPlaying","play","parseInt","postNavigate","wheelDistanceSymbol","postNavigateDelayCompleteSymbol","absorbDecelerationSymbol","POST_NAVIGATE_TIME","resetWheelTracking","lastDeltaXSymbol","lastWheelTimeoutSymbol","sign","wheel","wheelTimedOut","WHEEL_TIME","deltaX","deltaY","acceleration","TrackpadDirection","description","Symbol","callback","callbacks","push","counter","executeCallbacks","shift","createTextNode","observer","MutationObserver","observe","characterData","renderArrayAsElements","container","renderItem","oldElement","newElement","replaceChild","removeChild","setAttributeToElement","safeToSetAttributesSymbol","pendingAttributesSymbol","pendingClassesSymbol","_value","_toggleClass3","force","addClass","remove"],"mappings":"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","file":"basic-component-mixins.js","sourcesContent":["(function e(t,n,r){function s(o,u){if(!n[o]){if(!t[o]){var a=typeof require==\"function\"&&require;if(!u&&a)return a(o,!0);if(i)return i(o,!0);var f=new Error(\"Cannot find module '\"+o+\"'\");throw f.code=\"MODULE_NOT_FOUND\",f}var l=n[o]={exports:{}};t[o][0].call(l.exports,function(e){var n=t[o][1][e];return s(n?n:e)},l,l.exports,e,t,n,r)}return n[o].exports}var i=typeof require==\"function\"&&require;for(var o=0;o {\n\n /**\n * Template mixin which adds prominent left and right arrow buttons to a\n * wrapped child such as a carousel.\n *\n * You can see a\n * [live demo](http://basicwebcomponents.org/basic-web-components/packages/demos/carousel-with-arrows.html)\n * of this mixin applied to a carousel.\n *\n * Clicking the left/right buttons selects the previous/next item.\n *\n * Typical usage:\n *\n * class CarouselWithArrows extends ArrowSelectionMixin(Carousel) {}\n * customElements.define('carousel-with-arrows', CarouselWithArrows);\n *\n * By default, the arrow buttons are shown on devices with a mouse or mouse-like\n * pointing device. They are not shown on a touch-capable device unless mouse\n * movement is detected. To cause the buttons to always appear, apply the\n * 'showArrows' CSS class.\n */\n class ArrowSelection extends base {\n\n constructor() {\n super();\n\n this.$.buttonLeft.addEventListener('click', event => {\n this.selectPrevious();\n event.stopPropagation();\n });\n this.$.buttonRight.addEventListener('click', event => {\n this.selectNext();\n event.stopPropagation();\n });\n assumeButtonFocus(this, this.$.buttonLeft);\n assumeButtonFocus(this, this.$.buttonRight);\n }\n\n get canSelectNext() {\n return super.canSelectNext;\n }\n set canSelectNext(canSelectNext) {\n if ('canSelectNext' in base.prototype) { super.canSelectNext = canSelectNext; }\n this.$.buttonRight.disabled = !canSelectNext;\n }\n\n get canSelectPrevious() {\n return super.canSelectPrevious;\n }\n set canSelectPrevious(canSelectPrevious) {\n if ('canSelectPrevious' in base.prototype) { super.canSelectPrevious = canSelectPrevious; }\n this.$.buttonLeft.disabled = !canSelectPrevious;\n }\n\n connectedCallback() {\n if (super.connectedCallback) { super.connectedCallback(); }\n\n if (!this.classList.contains('showArrows')) {\n // Determine whether we should show arrow buttons or not.\n if (deviceSupportsTouch()) {\n // A touch device might also support a mouse, but we can't know whether\n // there's actually a mouse until we hear from it.\n listenForMouse(this);\n } else {\n // The device doesn't support touch, so assume it has a mouse.\n showArrows(this);\n }\n }\n }\n\n get [symbols.defaults]() {\n const defaults = super[symbols.defaults] || {};\n defaults.navigationAxis = 'horizontal';\n return defaults;\n }\n\n /*\n * The template uses the chevron-left and chevron-right SVG icons from\n * https://github.com/PolymerElements/iron-icons/blob/master/iron-icons.html.\n */\n get [symbols.template]() {\n const baseTemplate = super[symbols.template] || '';\n return `\n \n\n \n \n \n \n \n \n \n \n \n ${baseTemplate}\n
\n \n \n \n \n \n \n \n `;\n }\n\n }\n\n return ArrowSelection;\n};\n\n\n/*\n * By default, a button will always take focus on mousedown. For this component,\n * we want to override that behavior, such that a mousedown on a button keeps\n * the focus on the outer component.\n */\nfunction assumeButtonFocus(element, button) {\n button.addEventListener('mousedown', event => {\n // Given the main element the focus if it doesn't already have it.\n element.focus();\n // Prevent the default focus-on-mousedown behavior.\n event.preventDefault();\n });\n}\n\nfunction deviceSupportsTouch() {\n return 'ontouchstart' in window ||\n (window.DocumentTouch && document instanceof window.DocumentTouch);\n}\n\n// We try to detect the presence of a mouse by listening for mousemove events\n// which are *not* the result of a mousedown. On a touch device, a tap on the\n// page will generate a fake mousemove, followed by a mousedown. We don't want\n// to respond to those fake mousemove events. To discriminate between fake and\n// real mousemove events, when we get a mousemove event, we wait for a bit to\n// see if the same location is reported as the location of a subsequent\n// mousedown.\nfunction listenForMouse(element) {\n\n element[mousedownListenerSymbol] = event => {\n if (element[mouseTimeoutSymbol]) {\n clearTimeout(element[mouseTimeoutSymbol]);\n }\n element[lastMouseXSymbol] = event.pageX;\n element[lastMouseYSymbol] = event.pageY;\n };\n window.addEventListener('mousedown', element[mousedownListenerSymbol]);\n\n element[mousemoveListenerSymbol] = event => {\n // Postpone checking the mousemove location to give the mousedown event a\n // chance to fire. The 250 ms delay is just guesswork; a shorter delay\n // doesn't seem to work.\n element[mouseTimeoutSymbol] = setTimeout(() => {\n if (element[lastMouseXSymbol] != null && event.pageX !== element[lastMouseXSymbol] ||\n element[lastMouseYSymbol] != null && event.pageY !== element[lastMouseYSymbol]) {\n // mousemove event was at a location other than the last mousedown,\n // and hence most likely a real mousemove event.\n mouseDetected(element);\n } else {\n element[lastMouseXSymbol] = event.pageX;\n element[lastMouseYSymbol] = event.pageY;\n }\n }, 250);\n };\n window.addEventListener('mousemove', element[mousemoveListenerSymbol]);\n}\n\nfunction mouseDetected(element) {\n showArrows(element);\n\n // We can stop listening for mouse events now.\n if (element[mouseTimeoutSymbol]) {\n clearTimeout(element[mouseTimeoutSymbol]);\n }\n window.removeEventListener('mousedown', element[mousedownListenerSymbol]);\n window.removeEventListener('mousemove', element[mousemoveListenerSymbol]);\n element[mousedownListenerSymbol] = null;\n element[mousemoveListenerSymbol] = null;\n}\n\nfunction showArrows(element) {\n element.classList.add('showArrows');\n}\n","import safeAttributes from './safeAttributes';\n\n\n// Memoized maps of attribute to property names and vice versa.\nconst attributeToPropertyNames = {};\nconst propertyNamesToAttributes = {};\n\n\n/* Exported function extends a base class with AttributeMarshalling. */\nexport default (base) => {\n\n /**\n * Mixin which marshalls attributes to properties and vice versa.\n *\n * If your component exposes a setter for a property, it's generally a good\n * idea to let devs using your component be able to set that property in HTML\n * via an element attribute. You can code that yourself by writing an\n * `attributeChangedCallback`, or you can use this mixin to get a degree of\n * automatic support.\n *\n * This mixin implements an `attributeChangedCallback` that will attempt to\n * convert a change in an element attribute into a call to the corresponding\n * property setter. Attributes typically follow hyphenated names (\"foo-bar\"),\n * whereas properties typically use camelCase names (\"fooBar\"). This mixin\n * respects that convention, automatically mapping the hyphenated attribute\n * name to the corresponding camelCase property name.\n *\n * Example: You define a component using this mixin:\n *\n * class MyElement extends AttributeMarshallingMixin(HTMLElement) {\n * get fooBar() { return this._fooBar; }\n * set fooBar(value) { this._fooBar = value; }\n * }\n * customElements.define('my-element', MyElement);\n *\n * If someone then instantiates your component in HTML:\n *\n * \n *\n * Then, after the element has been upgraded, the `fooBar` setter will\n * automatically be invoked with the initial value \"Hello\".\n *\n * For the time being, this mixin only supports string-valued properties.\n * If you'd like to convert string attributes to other types (numbers,\n * booleans), you need to implement `attributeChangedCallback` yourself.\n */\n class AttributeMarshalling extends base {\n\n /*\n * Handle a change to the attribute with the given name.\n */\n attributeChangedCallback(attributeName, oldValue, newValue) {\n if (super.attributeChangedCallback) { super.attributeChangedCallback(); }\n const propertyName = attributeToPropertyName(attributeName);\n // If the attribute name corresponds to a property name, set the property.\n // Ignore standard HTMLElement properties handled by the DOM.\n if (propertyName in this && !(propertyName in HTMLElement.prototype)) {\n this[propertyName] = newValue;\n }\n }\n\n connectedCallback() {\n if (super.connectedCallback) { super.connectedCallback(); }\n safeAttributes.connected(this);\n }\n\n static get observedAttributes() {\n return attributesForClass(this);\n }\n\n /**\n * Set/unset the attribute with the indicated name.\n *\n * This method exists primarily to handle the case where an element wants to\n * set a default property value that should be reflected as an attribute. An\n * important limitation of custom element consturctors is that they cannot\n * set attributes. A call to `reflectAttribute` during the constructor will\n * be deferred until the element is connected to the document.\n *\n * @param {string} attribute - The name of the *attribute* (not property) to set.\n * @param {object} value - The value to set. If null, the attribute will be removed.\n */\n reflectAttribute(attribute, value) {\n return safeAttributes.setAttribute(this, attribute, value);\n }\n\n /**\n * Set/unset the class with the indicated name.\n *\n * This method exists primarily to handle the case where an element wants to\n * set a default property value that should be reflected as as class. An\n * important limitation of custom element consturctors is that they cannot\n * set attributes, including the `class` attribute. A call to\n * `reflectClass` during the constructor will be deferred until the element\n * is connected to the document.\n *\n * @param {string} className - The name of the class to set.\n * @param {object} value - True to set the class, false to remove it.\n */\n reflectClass(className, value) {\n return safeAttributes.toggleClass(this, className, value);\n }\n\n }\n\n return AttributeMarshalling;\n};\n\n\n// Convert hyphenated foo-bar attribute name to camel case fooBar property name.\nfunction attributeToPropertyName(attributeName) {\n let propertyName = attributeToPropertyNames[attributeName];\n if (!propertyName) {\n // Convert and memoize.\n const hypenRegEx = /-([a-z])/g;\n propertyName = attributeName.replace(hypenRegEx,\n match => match[1].toUpperCase());\n attributeToPropertyNames[attributeName] = propertyName;\n }\n return propertyName;\n}\n\nfunction attributesForClass(classFn) {\n\n // We treat the element base classes as if they have no attributes, since we\n // don't want to receive attributeChangedCallback for them.\n if (classFn === HTMLElement || classFn === Object) {\n return [];\n }\n\n // Get attributes for parent class.\n const baseClass = Object.getPrototypeOf(classFn.prototype).constructor;\n const baseAttributes = attributesForClass(baseClass);\n\n // Get attributes for this class.\n const propertyNames = Object.getOwnPropertyNames(classFn.prototype);\n const setterNames = propertyNames.filter(propertyName =>\n typeof Object.getOwnPropertyDescriptor(\n classFn.prototype, propertyName).set === 'function');\n const attributes = setterNames.map(setterName =>\n propertyNameToAttribute(setterName));\n\n // Merge.\n const diff = attributes.filter(attribute =>\n baseAttributes.indexOf(attribute) < 0);\n return baseAttributes.concat(diff);\n}\n\n// Convert a camel case fooBar property name to a hyphenated foo-bar attribute.\nfunction propertyNameToAttribute(propertyName) {\n let attribute = propertyNamesToAttributes[propertyName];\n if (!attribute) {\n // Convert and memoize.\n const uppercaseRegEx = /([A-Z])/g;\n attribute = propertyName.replace(uppercaseRegEx, '-$1').toLowerCase();\n }\n return attribute;\n}\n","/* Exported function extends a base class with ClickSelection. */\nexport default (base) => {\n\n /**\n * Mixin which maps a click (actually, a mousedown) to a selection.\n *\n * This simple mixin is useful in list box-like elements, where a click on a\n * list item implicitly selects it.\n *\n * This mixin expects the component to provide an `items` property. You can\n * provide that property yourself, or use\n * [ContentItemsMixin](ContentItemsMixin.md). This mixin also expects the\n * component to define a `selectedIndex` property. You can provide that\n * yourself, or use [SingleSelectionMixin](SingleSelectionMixin.md).\n */\n class ClickSelection extends base {\n\n constructor() {\n super();\n /*\n * REVIEW: Which event should we listen to here?\n *\n * The standard use for this mixin is in list boxes. List boxes don't\n * appear to be consistent with regard to whether they select on mousedown\n * or click/mouseup.\n */\n this.addEventListener('mousedown', event => {\n // HACK: If the item is a button, the event seems to be raised in\n // phase 2 (AT_TARGET), but the target is the component, not item.\n // Need to invesigate.\n const target = event.target === this ?\n event.path[0] :\n event.target;\n const index = indexOfContainingItem(this, target);\n if (index >= 0) {\n this.selectedIndex = index;\n // Note: We don't call preventDefault here. The default behavior for\n // mousedown includes setting keyboard focus if the element doesn't\n // already have the focus, and we want to preserve that behavior.\n event.stopPropagation();\n }\n });\n }\n\n // Default implementation. This will typically be handled by other mixins.\n get selectedIndex() {\n return super.selectedIndex;\n }\n set selectedIndex(index) {\n if ('selectedIndex' in base.prototype) { super.selectedIndex = index; }\n }\n\n }\n\n return ClickSelection;\n};\n\n\n/*\n * Return index of the element items that either is or contains the indicated\n * target. Return -1 if not found.\n */\nfunction indexOfContainingItem(element, target) {\n const items = element.items;\n const itemCount = items ? items.length : 0;\n for (let i = 0; i < itemCount; i++) {\n let item = items[i];\n if (item === target || item.contains(target)) {\n return i;\n }\n }\n return -1;\n}\n","/* Exported function extends a base class with Composable. */\nexport default (base) => {\n\n /**\n * Mixin to make a class more easily composable with other mixins.\n *\n * This mixin contributes a `compose` method that applies a set of mixin\n * functions and returns the resulting new class. This sugar can make the\n * application of many mixins at once easier to read.\n */\n class Composable extends base {\n\n /**\n * Apply a set of mixin functions or mixin objects to the present class and\n * return the new class.\n *\n * Instead of writing:\n *\n * let MyClass = Mixin1(Mixin2(Mixin3(Mixin4(Mixin5(BaseClass)))));\n *\n * You can write:\n *\n * let MyClass = ComposableMixin(BaseClass).compose(\n * Mixin1,\n * Mixin2,\n * Mixin3,\n * Mixin4,\n * Mixin5\n * );\n *\n * This function can also take mixin objects. A mixin object is just a\n * shorthand for a mixin function that creates a new subclass with the given\n * members. The mixin object's members are *not* copied directly onto the\n * prototype of the base class, as with traditional mixins.\n *\n * In addition to providing syntactic sugar, this mixin can be used to\n * define a class in ES5, which lacks ES6's `class` keyword.\n *\n * @param {...mixins} mixins - A set of mixin functions or objects to apply.\n */\n static compose(...mixins) {\n // We create a new subclass for each mixin in turn. The result becomes\n // the base class extended by any subsequent mixins. It turns out that\n // we can use Array.reduce() to concisely express this, using the current\n // object as the seed for reduce().\n return mixins.reduce(composeClass, this);\n }\n\n }\n\n return Composable;\n};\n\n\n// Properties defined by Object that we don't want to mixin.\nconst NON_MIXABLE_OBJECT_PROPERTIES = [\n 'constructor'\n];\n\n/*\n * Apply the mixin to the given base class to return a new class.\n * The mixin can either be a function that returns the modified class, or a\n * plain object whose members will be copied to the new class' prototype.\n */\nfunction composeClass(base, mixin) {\n if (typeof mixin === 'function') {\n // Mixin function\n return mixin(base);\n } else {\n // Mixin object\n class Subclass extends base {}\n copyOwnProperties(mixin, Subclass.prototype, NON_MIXABLE_OBJECT_PROPERTIES);\n return Subclass;\n }\n}\n\n\n/*\n * Copy the given properties/methods to the target.\n * Return the updated target.\n */\nfunction copyOwnProperties(source, target, ignorePropertyNames = []) {\n Object.getOwnPropertyNames(source).forEach(name => {\n if (ignorePropertyNames.indexOf(name) < 0) {\n const descriptor = Object.getOwnPropertyDescriptor(source, name);\n Object.defineProperty(target, name, descriptor);\n }\n });\n return target;\n}\n","import createSymbol from './createSymbol';\nimport toggleClass from './toggleClass';\nimport symbols from './symbols';\n\n\n// Symbols for private data members on an element.\nconst itemsSymbol = createSymbol('items');\nconst itemInitializedSymbol = createSymbol('itemInitialized');\n\n\n/* Exported function extends a base class with ContentItems. */\nexport default (base) => {\n\n /**\n * Mixin which maps content semantics (elements) to list item semantics.\n *\n * Items differ from element contents in several ways:\n *\n * * They are often referenced via index.\n * * They may have a selection state.\n * * It's common to do work to initialize the appearance or state of a new\n * item.\n * * Auxiliary invisible child elements are filtered out and not counted as\n * items. Auxiliary elements include link, script, style, and template\n * elements. This filtering ensures that those auxiliary elements can be\n * used in markup inside of a list without being treated as list items.\n *\n * This mixin expects a component to provide a `content` property returning a\n * raw set of elements. You can provide that yourself, or use\n * [DistributedChildrenContentMixin](DistributedChildrenContentMixin.md).\n *\n * The most commonly referenced property defined by this mixin is the `items`\n * property. To avoid having to do work each time that property is requested,\n * this mixin supports an optimized mode. If you invoke the `contentChanged`\n * method when the set of items changes, the mixin concludes that you'll take\n * care of notifying it of future changes, and turns on the optimization. With\n * that on, the mixin saves a reference to the computed set of items, and will\n * return that immediately on subsequent calls to the `items` property. If you\n * use this mixin in conjunction with\n * [DistributedChildrenContentMixin](DistributedChildrenContentMixin.md), the\n * `contentChanged` method will be invoked for you when the element's children\n * change, turning on the optimization automatically.\n */\n class ContentItems extends base {\n\n contentChanged() {\n if (super.contentChanged) { super.contentChanged(); }\n\n // Since we got the contentChanged call, we'll assume we'll be notified if\n // the set of items changes later. We turn on memoization of the items\n // property by setting our internal property to null (instead of\n // undefined).\n this[itemsSymbol] = null;\n\n this[symbols.itemsChanged]();\n }\n\n /**\n * This method is invoked whenever a new item is added to the list.\n *\n * The default implementation of this method does nothing. You can override\n * this to perform per-item initialization.\n *\n * @param {HTMLElement} item - The item that was added.\n */\n [symbols.itemAdded](item) {\n if (super[symbols.itemAdded]) { super[symbols.itemAdded](item); }\n }\n\n /**\n * The selection state for a single item has changed.\n *\n * Invoke this method to signal that the selected state of the indicated item\n * has changed. By default, this applies a `selected` CSS class if the item\n * is selected, and removed it if not selected.\n *\n * @param {HTMLElement} item - The item whose selection state has changed.\n * @param {boolean} selected - True if the item is selected, false if not.\n */\n [symbols.itemSelected](item, selected) {\n if (super[symbols.itemSelected]) { super[symbols.itemSelected](item, selected); }\n toggleClass(item, 'selected', selected);\n }\n\n /**\n * The current set of items in the list. See the top-level documentation for\n * mixin for a description of how items differ from plain content.\n *\n * @type {HTMLElement[]}\n */\n get items() {\n let items;\n if (this[itemsSymbol] == null) {\n items = filterAuxiliaryElements(this.content);\n // Note: test for *equality* with null; don't treat undefined as a match.\n if (this[itemsSymbol] === null) {\n // Memoize the set of items.\n this[itemsSymbol] = items;\n }\n } else {\n // Return the memoized items.\n items = this[itemsSymbol];\n }\n return items;\n }\n\n /**\n * This method is invoked when the underlying contents change. It is also\n * invoked on component initialization – since the items have \"changed\" from\n * being nothing.\n */\n [symbols.itemsChanged]() {\n if (super[symbols.itemsChanged]) { super[symbols.itemsChanged](); }\n\n // Perform per-item initialization.\n Array.prototype.forEach.call(this.items, item => {\n if (!item[itemInitializedSymbol]) {\n this[symbols.itemAdded](item);\n item[itemInitializedSymbol] = true;\n }\n });\n\n this.dispatchEvent(new CustomEvent('items-changed'));\n }\n\n /**\n * Fires when the items in the list change.\n *\n * @memberof ContentItems\n * @event items-changed\n */\n }\n\n return ContentItems;\n};\n\n\n// Return the given elements, filtering out auxiliary elements that aren't\n// typically visible. Items which are not elements are returned as is.\nfunction filterAuxiliaryElements(items) {\n const auxiliaryTags = [\n 'link',\n 'script',\n 'style',\n 'template'\n ];\n return [].filter.call(items, function(item) {\n return !item.localName || auxiliaryTags.indexOf(item.localName) < 0;\n });\n}\n","import symbols from './symbols';\n\n\n/* Exported function extends a base class with DirectionSelection. */\nexport default (base) => {\n\n /**\n * Mixin which maps direction semantics (goLeft, goRight, etc.) to selection\n * semantics (selectPrevious, selectNext, etc.).\n *\n * This mixin can be used in conjunction with\n * [KeyboardDirectionMixin](KeyboardDirectionMixin.md) (which maps keyboard\n * events to directions) and a mixin that handles selection like\n * [SingleSelectionMixin](SingleSelectionMixin.md).\n */\n class DirectionSelection extends base {\n\n [symbols.goDown]() {\n if (super[symbols.goDown]) { super[symbols.goDown](); }\n return this.selectNext();\n }\n\n [symbols.goEnd]() {\n if (super[symbols.goEnd]) { super[symbols.goEnd](); }\n return this.selectLast();\n }\n\n [symbols.goLeft]() {\n if (super[symbols.goLeft]) { super[symbols.goLeft](); }\n return this.selectPrevious();\n }\n\n [symbols.goRight]() {\n if (super[symbols.goRight]) { super[symbols.goRight](); }\n return this.selectNext();\n }\n\n [symbols.goStart]() {\n if (super[symbols.goStart]) { super[symbols.goStart](); }\n return this.selectFirst();\n }\n\n [symbols.goUp]() {\n if (super[symbols.goUp]) { super[symbols.goUp](); }\n return this.selectPrevious();\n }\n\n // Default implementation. This will typically be handled by other mixins.\n get selectedFraction() {\n return super.selectedFraction;\n }\n set selectedFraction(value) {\n if ('selectedFraction' in base.prototype) { super.selectedFraction = value; }\n }\n\n // Default implementation. This will typically be handled by other mixins.\n selectFirst() {\n if (super.selectFirst) { return super.selectFirst(); }\n }\n\n // Default implementation. This will typically be handled by other mixins.\n selectLast() {\n if (super.selectLast) { return super.selectLast(); }\n }\n\n // Default implementation. This will typically be handled by other mixins.\n selectNext() {\n if (super.selectNext) { return super.selectNext(); }\n }\n\n // Default implementation. This will typically be handled by other mixins.\n selectPrevious() {\n if (super.selectPrevious) { return super.selectPrevious(); }\n }\n\n // Map drag travel fraction to selection fraction.\n get travelFraction() {\n return super.travelFraction;\n }\n set travelFraction(value) {\n if ('travelFraction' in base.prototype) { super.travelFraction = value; }\n this.selectedFraction = value;\n }\n\n }\n\n return DirectionSelection;\n};\n","import microtask from './microtask';\n\n\n/* Exported function extends a base class with DistributedChildrenContent. */\nexport default (base) => {\n\n /**\n * Mixin which defines a component's content as its children, expanding any\n * nodes distributed to the component's slots.\n *\n * This also provides notification of changes to a component's content. It\n * will invoke a `contentChanged` method when the component is first\n * instantiated, and whenever its distributed children change. This is an\n * easy way to satisfy the Gold Standard checklist item for monitoring\n * [Content Changes](https://github.com/webcomponents/gold-standard/wiki/Content-Changes).\n *\n * Example:\n *\n * ```\n * let base = DistributedChildrenContentMixin(DistributedChildrenMixin(HTMLElement));\n * class CountingElement extends base {\n *\n * constructor() {\n * super();\n * let root = this.attachShadow({ mode: 'open' });\n * root.innerHTML = ` `;\n * }\n *\n * contentChanged() {\n * // Count the component's children, both initially and when changed.\n * this.count = this.distributedChildren.length;\n * }\n *\n * }\n * ```\n *\n * Note that content change detection depends upon the element having at least\n * one `slot` element in its shadow subtree.\n *\n * This mixin is intended for use with the\n * [DistributedChildrenMixin](DistributedChildrenMixin.md). See that mixin for\n * a discussion of how that works. This DistributedChildrenContentMixin\n * provides an easy way of defining the \"content\" of a component as the\n * component's distributed children. That in turn lets mixins like\n * [ContentItemsMixin](ContentItemsMixin.md) manipulate the children as list\n * items.\n */\n class DistributedChildrenContent extends base {\n\n constructor() {\n super();\n\n if (this.shadowRoot) {\n // Listen to changes on all slots.\n const slots = this.shadowRoot.querySelectorAll('slot');\n slots.forEach(slot => slot.addEventListener('slotchange', event => {\n this.contentChanged();\n }));\n }\n\n // Make an initial call to contentChanged() so that the component can do\n // initialization that it normally does when content changes.\n //\n // This will invoke contentChanged() handlers in other mixins. In order\n // that those mixins have a chance to complete their own initialization,\n // we add the contentChanged() call to the microtask queue.\n microtask(() => this.contentChanged());\n }\n\n /**\n * Invoked when the contents of the component (including distributed\n * children) have changed.\n *\n * This method is also invoked when a component is first instantiated; the\n * contents have essentially \"changed\" from being nothing. This allows the\n * component to perform initial processing of its children.\n */\n contentChanged() {\n if (super.contentChanged) { super.contentChanged(); }\n const event = new CustomEvent('content-changed');\n this.dispatchEvent(event);\n }\n\n /**\n * The content of this component, defined to be the flattened array of\n * children distributed to the component.\n *\n * @type {HTMLElement[]}\n */\n get content() {\n const distributedChildren = this.distributedChildren;\n if (typeof distributedChildren === 'undefined') {\n console.warn(`DistributedChildrenContentMixin expects the component to define a \"distributedChildren\" property.`);\n }\n return distributedChildren;\n }\n set content(value) {\n if ('content' in base.prototype) { super.content = value; }\n // TODO: Set the children to the given value (which should be an array of\n // elements)?\n }\n\n /**\n * This event is raised when the component's contents (including distributed\n * children) have changed.\n *\n * @memberof DistributedChildrenContent\n * @event content-changed\n */\n }\n\n return DistributedChildrenContent;\n};\n","/* Exported function extends a base class with DistributedChildren. */\nexport default (base) => {\n\n /**\n * Mixin which defines helpers for accessing a component's distributed\n * children as a flattened array or string.\n *\n * The standard DOM API provides several ways of accessing child content:\n * `children`, `childNodes`, and `textContent`. None of these functions are\n * Shadow DOM aware. This mixin defines variations of those functions that\n * *are* Shadow DOM aware.\n *\n * Example: you create a component `` that displays a number\n * equal to the number of children placed inside that component. If someone\n * instantiates your component like:\n *\n * \n *
\n *
\n *
\n * \n *\n * Then the component should show \"3\", because there are three children. To\n * calculate the number of children, the component can just calculate\n * `this.children.length`. However, suppose someone instantiates your\n * component inside one of their own components, and puts a `` element\n * inside your component:\n *\n * \n * \n * \n *\n * If your component only looks at `this.children`, it will always see exactly\n * one child — the `` element. But the user looking at the page will\n * *see* any nodes distributed to that slot. To match what the user sees, your\n * component should expand any `` elements it contains.\n *\n * That is the problem this mixin solves. After applying this mixin, your\n * component code has access to `this.distributedChildren`, whose `length`\n * will return the total number of all children distributed to your component\n * in the composed tree.\n *\n * Note: The latest Custom Elements API design calls for a new function,\n * `getAssignedNodes` that takes an optional `deep` parameter, that will solve\n * this problem at the API level.\n */\n class DistributedChildren extends base {\n\n /**\n * An in-order collection of distributed children, expanding any slot\n * elements. Like the standard children property, this skips text nodes.\n *\n * @type {HTMLElement[]}\n */\n get distributedChildren() {\n return expandContentElements(this.children, false);\n }\n\n /**\n * An in-order collection of distributed child nodes, expanding any slot\n * elements. Like the standard childNodes property, this includes text\n * nodes.\n *\n * @type {Node[]}\n */\n get distributedChildNodes() {\n return expandContentElements(this.childNodes, true);\n }\n\n /**\n * The concatenated text content of all distributed child nodes, expanding\n * any slot elements.\n *\n * @type {string}\n */\n get distributedTextContent() {\n const strings = this.distributedChildNodes.map(function(child) {\n return child.textContent;\n });\n return strings.join('');\n }\n\n }\n\n return DistributedChildren;\n};\n\n\n/*\n * Given a array of nodes, return a new array with any content elements expanded\n * to the nodes distributed to that content element. This rule is applied\n * recursively.\n *\n * If includeTextNodes is true, text nodes will be included, as in the\n * standard childNodes property; by default, this skips text nodes, like the\n * standard children property.\n */\nfunction expandContentElements(nodes, includeTextNodes) {\n const expanded = Array.prototype.map.call(nodes, node => {\n // We want to see if the node is an instanceof HTMLSlotELement, but\n // that class won't exist if the browser that doesn't support native\n // Shadow DOM and if the Shadow DOM polyfill hasn't been loaded. Instead,\n // we do a simplistic check to see if the tag name is \"slot\".\n const isSlot = typeof HTMLSlotElement !== 'undefined' ?\n node instanceof HTMLSlotElement :\n node.localName === 'slot';\n if (isSlot) {\n // Use the nodes assigned to this node instead.\n const assignedNodes = node.assignedNodes({ flatten: true });\n return assignedNodes ?\n expandContentElements(assignedNodes, includeTextNodes) :\n [];\n } else if (node instanceof HTMLElement) {\n // Plain element; use as is.\n return [node];\n } else if (node instanceof Text && includeTextNodes) {\n // Text node.\n return [node];\n } else {\n // Comment, processing instruction, etc.; skip.\n return [];\n }\n });\n const flattened = [].concat(...expanded);\n return flattened;\n}\n","import createSymbol from './createSymbol';\n\n\n// Symbols for private data members on an element.\nconst selectedFractionSymbol = createSymbol('selectedFraction');\n\n\n/* Exported function extends a base class with FractionalSelection. */\nexport default function mixin(base) {\n\n /**\n * Adds support for fractional selection: treating a selection as a real\n * number that combines an integer portion (an index into a list), and a\n * fraction (indicating how far of the way we are to the next or previous\n * item).\n *\n * This is useful in components that support incremental operations during\n * dragging and swiping. Example: a carousel component has several items, and the\n * currently selected item is item 3. The user begins swiping to the left,\n * moving towards selecting item 4. Halfway through this operation, the\n * fractional selection value is 3.5.\n *\n * This value permits communication between mixins like\n * [SwipeDirectionMixin](./SwipeDirectionMixin.md) and\n * [TrackpadDirectionMixin](./TrackpadDirectionMixin.md), which generate\n * fractional selection values, and mixins like\n * [SelectionAnimationMixin](./SelectionAnimationMixin.md), which can render\n * selection at a fractional value.\n */\n class FractionalSelection extends base {\n\n connectedCallback() {\n if (super.connectedCallback) { super.connectedCallback(); }\n this.selectedFraction = 0;\n }\n\n /**\n * A fractional value indicating how far the user has currently advanced to\n * the next/previous item. E.g., a `selectedFraction` of 3.5 indicates the\n * user is halfway between items 3 and 4.\n *\n * @type {number}\n */\n get selectedFraction() {\n return this[selectedFractionSymbol];\n }\n set selectedFraction(value) {\n this[selectedFractionSymbol] = value;\n if ('selectedFraction' in base.prototype) { super.selectedFraction = value; }\n const event = new CustomEvent('selected-fraction-changed');\n this.dispatchEvent(event);\n }\n\n }\n\n return FractionalSelection;\n}\n\n\nmixin.helpers = {\n\n /*\n * Dampen a selection that goes past the beginning or end of a list. This is\n * generally used to produce a visual effect of tension as the user tries to\n * go further in a direction that has no more items.\n *\n * Example: suppose `itemCount` is 5, indicating a list of 5 items. The index of\n * the last item is 4. If the `selection` parameter is 4.5, the user is trying\n * to go past this last item. When a damping function is applied, the resulting\n * value will be less than 4.5 (the actual value will be 4.25). When this\n * selection state is rendered, the user will see that, each unit distance the\n * drag travels has less and less visible effect. This is perceived as tension.\n *\n * @param {number} selection - A real number indicating a selection position\n * @param {number} itemCount - An integer for the number of items in the list\n * @returns {number} A real number representing the damped selection value.\n */\n dampedSelection(selection, itemCount) {\n const bound = itemCount - 1;\n let damped;\n if (selection < 0) {\n // Trying to go past beginning of list. Apply tension from the left edge.\n damped = -mixin.helpers.damping(-selection);\n } else if (selection >= bound) {\n // Trying to go past end of list. Apply tension from the right edge.\n damped = bound + mixin.helpers.damping(selection - bound);\n } else {\n // No damping required.\n damped = selection;\n }\n return damped;\n },\n\n /*\n * Calculate damping as a function of the distance past the minimum/maximum\n * values.\n *\n * We want to asymptotically approach an absolute minimum of 1 unit\n * below/above the actual minimum/maximum. This requires calculating a\n * hyperbolic function.\n *\n * See http://www.wolframalpha.com/input/?i=y+%3D+-1%2F%28x%2B1%29+%2B+1\n * for the one we use. The only portion of that function we care about is when\n * x is zero or greater. An important consideration is that the curve be\n * tangent to the diagonal line x=y at (0, 0). This ensures smooth continuity\n * with the normal drag behavior, in which the visible sliding is linear with\n * the distance the touchpoint has been dragged.\n */\n damping(x) {\n const y = (-1 / (x + 1)) + 1;\n return y;\n },\n\n /*\n * Return the current fractional selection value for the given element.\n *\n * This simply adds the element's `selectedIndex` and `selectedFraction`\n * properties.\n *\n * @param {HTMLElement} element - An element that supports selection\n */\n elementSelection(element) {\n const selectedIndex = element.selectedIndex;\n if (selectedIndex < 0) {\n // No selection\n return;\n }\n const selectedFraction = element.selectedFraction || 0;\n return selectedIndex + selectedFraction;\n },\n\n /*\n * Breaks a fractional selection into its integer and fractional parts.\n *\n * Example: if passed 3.5, this returns { index: 3, fraction: 5 }.\n *\n * @param {number} selection – A real number representing a selection point\n * @returns {object} - An object with an `index` property holding the\n * selection's integer component, and a `fraction` property holding the\n * selection's fractional component.\n */\n selectionParts(selection) {\n // Stupid IE doesn't have Math.trunc.\n // const index = Math.trunc(selection);\n const index = selection < 0 ? Math.ceil(selection) : Math.floor(selection);\n const fraction = selection - index;\n return { index, fraction };\n },\n\n /*\n * Returns a fractional selection point after accounting for wrapping, ensuring\n * that the integer portion of the selection stays between 0 and `itemCount`-1.\n * That is, the integer portion will always be a valid index into the list.\n *\n * Example of wrapping past the end of the list: if `selection` is 5.5 and\n * `itemCount` is 5, this returns 0.5. Example of wrapping past the beginning of\n * the list: if `selection` is 0.5 and `itemCount` is 5, this returns 4.5.\n *\n * @param {number} selection - A real number representing a selection point\n * @param {number} itemCount - The number of items in the list\n * @returns {number} - The result of wrapping the selection point\n */\n wrappedSelection(selection, itemCount) {\n // Handles possibility of negative mod.\n // See http://stackoverflow.com/a/18618250/76472\n return ((selection % itemCount) + itemCount) % itemCount;\n },\n\n /*\n * Return the parts of a selection, first wrapping if necessary.\n *\n * @param {number} selection – A real number representing a selection point\n * @param {number} itemCount - The number of items in the list\n * @param {boolean} wrap – True if the selection should wrap to stay within the\n * list\n * @returns {object} – The parts of the selection, using the same format as\n * `selectionParts`.\n */\n wrappedSelectionParts(selection, itemCount, wrap) {\n if (wrap) {\n selection = mixin.helpers.wrappedSelection(selection, itemCount);\n }\n return mixin.helpers.selectionParts(selection);\n }\n\n};\n","import createSymbol from './createSymbol';\nimport safeAttributes from './safeAttributes';\nimport symbols from './symbols';\n\n\n// Symbols for private data members on an element.\nconst genericSymbol = createSymbol('generic');\n\n\n/* Exported function extends a base class with Generic. */\nexport default (base) => {\n\n /**\n * Mixin which allows a component to support a \"generic\" style: a minimalist\n * style that can easily be removed to reset its visual appearance to a\n * baseline state.\n *\n * By default, a component should provide a minimal visual presentation that\n * allows the component to function. However, the more styling the component\n * provides by default, the harder it becomes to get the component to fit in\n * in other settings. Each CSS rule has to be overridden. Worse, new CSS rules\n * added to the default style won't be overridden by default, making it hard\n * to know whether a new version of a component will still look okay.\n *\n * As a compromise, the mixin defines a `generic` attribute. This attribute is\n * normally set by default, and styles can be written that apply only when the\n * generic attribute is set. This allows the construction of CSS rules that\n * will only apply to generic components like:\n *\n * :host([generic=\"\"]) {\n * ... generic appearance defined here ...\n * }\n *\n * This makes it easy to remove all default styling — set the `GenericMixin`\n * attribute to false, and all default styling will be removed.\n */\n class Generic extends base {\n\n constructor() {\n super();\n // Set defaults.\n if (typeof this.generic === 'undefined') {\n this.generic = this[symbols.defaults].generic;\n }\n }\n\n // This mixin doesn't actually respond to attribute changes, but relies\n // on separately-defined behavior (e.g., in AttributeMarshallingMixin) for that.\n // Still, we need define a baseline attributeChangedCallback that does\n // nothing, in case this mixin gets used on its own.\n attributeChangedCallback(name, oldValue, newValue) {\n if (super.attributeChangedCallback) { super.attributeChangedCallback(name, oldValue, newValue); }\n }\n\n connectedCallback() {\n if (super.connectedCallback) { super.connectedCallback(); }\n safeAttributes.connected(this);\n }\n\n get [symbols.defaults]() {\n const defaults = super[symbols.defaults] || {};\n defaults.generic = true;\n return defaults;\n }\n\n /**\n * True if the component would like to receive generic styling.\n *\n * This property is true by default — set it to false to turn off all\n * generic styles. This makes it easier to apply custom styling; you won't\n * have to explicitly override styling you don't want.\n *\n * @type Boolean\n * @default true\n */\n get generic() {\n return this[genericSymbol];\n }\n set generic(value) {\n const parsed = typeof value === 'string' ?\n String(value) !== 'false' :\n value;\n this[genericSymbol] = parsed;\n\n if ('generic' in base.prototype) { super.generic = value; }\n\n // We roll our own attribute setting so that an explicitly false value\n // shows up as GenericMixin=\"false\".\n if (parsed === false) {\n // Explicitly use false string.\n safeAttributes.setAttribute(this, 'generic', 'false');\n } else if (parsed == null) {\n // Explicitly remove attribute. (Always safe to do this.)\n this.removeAttribute('generic');\n } else {\n // Use the empty string to get attribute to appear with no value.\n safeAttributes.setAttribute(this, 'generic', '');\n }\n }\n\n }\n\n return Generic;\n};\n\n\n","import createSymbol from './createSymbol';\nimport symbols from './symbols';\n\n\n// Symbols for private data members on an element.\nconst navigationAxisSymbol = createSymbol('navigationAxis');\n\n\n/* Exported function extends a base class with KeyboardDirection. */\nexport default (base) => {\n\n /**\n * Mixin which maps direction keys (Left, Right, etc.) to direction semantics\n * (go left, go right, etc.).\n *\n * This mixin expects the component to invoke a `keydown` method when a key is\n * pressed. You can use [KeyboardMixin](KeyboardMixin.md) for that\n * purpose, or wire up your own keyboard handling and call `keydown` yourself.\n *\n * This mixin calls methods such as `goLeft` and `goRight`. You can define\n * what that means by implementing those methods yourself. If you want to use\n * direction keys to navigate a selection, use this mixin with\n * [DirectionSelectionMixin](DirectionSelectionMixin.md).\n */\n class KeyboardDirection extends base {\n\n constructor() {\n super();\n // Set defaults.\n if (typeof this.navigationAxis === 'undefined') {\n this.navigationAxis = this[symbols.defaults].navigationAxis;\n }\n }\n\n get [symbols.defaults]() {\n const defaults = super[symbols.defaults] || {};\n defaults.navigationAxis = 'both';\n return defaults;\n }\n\n /**\n * Invoked when the user wants to go/navigate down.\n * The default implementation of this method does nothing.\n */\n [symbols.goDown]() {\n if (super[symbols.goDown]) { return super[symbols.goDown](); }\n }\n\n /**\n * Invoked when the user wants to go/navigate to the end (e.g., of a list).\n * The default implementation of this method does nothing.\n */\n [symbols.goEnd]() {\n if (super[symbols.goEnd]) { return super[symbols.goEnd](); }\n }\n\n /**\n * Invoked when the user wants to go/navigate left.\n * The default implementation of this method does nothing.\n */\n [symbols.goLeft]() {\n if (super[symbols.goLeft]) { return super[symbols.goLeft](); }\n }\n\n /**\n * Invoked when the user wants to go/navigate right.\n * The default implementation of this method does nothing.\n */\n [symbols.goRight]() {\n if (super[symbols.goRight]) { return super[symbols.goRight](); }\n }\n\n /**\n * Invoked when the user wants to go/navigate to the start (e.g., of a\n * list). The default implementation of this method does nothing.\n */\n [symbols.goStart]() {\n if (super[symbols.goStart]) { return super[symbols.goStart](); }\n }\n\n /**\n * Invoked when the user wants to go/navigate up.\n * The default implementation of this method does nothing.\n */\n [symbols.goUp]() {\n if (super[symbols.goUp]) { return super[symbols.goUp](); }\n }\n\n /**\n * Indicates the direction of permitted navigation with the keyboard.\n *\n * Accepted values are \"horizontal\", \"vertical\", or \"both\" (the default).\n * If this property is \"horizontal\", the Up Arrow and Down Arrow keys will\n * be ignored. Conversely, if this is \"vertical\", the Left Arrow and Right\n * Arrow keys will be ignored.\n *\n * @type {string}\n */\n get navigationAxis() {\n return this[navigationAxisSymbol];\n }\n set navigationAxis(value) {\n this[navigationAxisSymbol] = value;\n if ('navigationAxis' in base.prototype) { super.navigationAxis = value; }\n }\n\n [symbols.keydown](event) {\n let handled;\n\n const axis = this.navigationAxis;\n const horizontal = (axis === 'horizontal' || axis === 'both');\n const vertical = (axis === 'vertical' || axis === 'both');\n\n // Ignore Left/Right keys when metaKey or altKey modifier is also pressed,\n // as the user may be trying to navigate back or forward in the browser.\n switch (event.keyCode) {\n case 35: // End\n handled = this[symbols.goEnd]();\n break;\n case 36: // Home\n handled = this[symbols.goStart]();\n break;\n case 37: // Left\n if (horizontal && !event.metaKey && !event.altKey) {\n handled = this[symbols.goLeft]();\n }\n break;\n case 38: // Up\n if (vertical) {\n handled = event.altKey ? this[symbols.goStart]() : this[symbols.goUp]();\n }\n break;\n case 39: // Right\n if (horizontal && !event.metaKey && !event.altKey) {\n handled = this[symbols.goRight]();\n }\n break;\n case 40: // Down\n if (vertical) {\n handled = event.altKey ? this[symbols.goEnd]() : this[symbols.goDown]();\n }\n break;\n }\n // Prefer mixin result if it's defined, otherwise use base result.\n return handled || (super[symbols.keydown] && super[symbols.keydown](event));\n }\n\n }\n\n return KeyboardDirection;\n};\n","import symbols from './symbols';\n\n\n/* Exported function extends a base class with Keyboard. */\nexport default (base) => {\n\n /**\n * Mixin which manages the keydown handling for a component.\n *\n * This mixin handles several keyboard-related features.\n *\n * First, it wires up a single keydown event handler that can be shared by\n * multiple mixins on a component. The event handler will invoke a `keydown`\n * method with the event object, and any mixin along the prototype chain that\n * wants to handle that method can do so.\n *\n * If a mixin wants to indicate that keyboard event has been handled, and that\n * other mixins should *not* handle it, the mixin's `keydown` handler should\n * return a value of true. The convention that seems to work well is that a\n * mixin should see if it wants to handle the event and, if not, then ask the\n * superclass to see if it wants to handle the event. This has the effect of\n * giving the mixin that was applied last the first chance at handling a\n * keyboard event.\n *\n * Example:\n *\n * [symbols.keydown](event) {\n * let handled;\n * switch (event.keyCode) {\n * // Handle the keys you want, setting handled = true if appropriate.\n * }\n * // Prefer mixin result if it's defined, otherwise use base result.\n * return handled || (super[symbols.keydown] && super[symbols.keydown](event));\n * }\n *\n * A second feature provided by this mixin is that it implicitly makes the\n * component a tab stop if it isn't already, by setting `tabIndex` to 0. This\n * has the effect of adding the component to the tab order in document order.\n */\n class Keyboard extends base {\n\n constructor() {\n super();\n this.addEventListener('keydown', event => {\n const handled = this[symbols.keydown](event);\n if (handled) {\n event.preventDefault();\n event.stopPropagation();\n }\n });\n }\n\n connectedCallback() {\n if (super.connectedCallback) { super.connectedCallback(); }\n if (this.getAttribute('tabindex') == null && this[symbols.defaults].tabindex !== null) {\n this.setAttribute('tabindex', this[symbols.defaults].tabindex);\n }\n }\n\n get [symbols.defaults]() {\n const defaults = super[symbols.defaults] || {};\n // The default tab index is 0 (document order).\n defaults.tabindex = 0;\n return defaults;\n }\n\n /**\n * Handle the indicated keyboard event.\n *\n * The default implementation of this method does nothing. This will\n * typically be handled by other mixins.\n *\n * @param {KeyboardEvent} event - the keyboard event\n * @return {boolean} true if the event was handled\n */\n [symbols.keydown](event) {\n if (super[symbols.keydown]) { return super[symbols.keydown](event); }\n }\n\n }\n\n return Keyboard;\n};\n","import symbols from './symbols';\n\n\n/* Exported function extends a base class with KeyboardPagedSelection. */\nexport default (base) => {\n\n /**\n * Mixin which maps page keys (Page Up, Page Down) into operations that move\n * the selection by one page.\n *\n * The keyboard interaction model generally follows that of Microsoft Windows'\n * list boxes instead of those in OS X:\n *\n * * The Page Up/Down and Home/End keys actually change the selection, rather\n * than just scrolling. The former behavior seems more generally useful for\n * keyboard users.\n *\n * * Pressing Page Up/Down will change the selection to the topmost/bottommost\n * visible item if the selection is not already there. Thereafter, the key\n * will move the selection up/down by a page, and (per the above point) make\n * the selected item visible.\n *\n * To ensure the selected item is in view following use of Page Up/Down, use\n * the related [SelectionInViewMixin](SelectionInViewMixin.md).\n *\n * This mixin expects the component to invoke a `keydown` method when a key is\n * pressed. You can use [KeyboardMixin](KeyboardMixin.md) for that\n * purpose, or wire up your own keyboard handling and call `keydown` yourself.\n */\n class KeyboardPagedSelection extends base {\n\n [symbols.keydown](event) {\n let handled;\n switch (event.keyCode) {\n case 33: // Page Up\n handled = this.pageUp();\n break;\n case 34: // Page Down\n handled = this.pageDown();\n break;\n }\n // Prefer mixin result if it's defined, otherwise use base result.\n return handled || (super[symbols.keydown] && super[symbols.keydown](event));\n }\n\n /**\n * Scroll down one page.\n */\n pageDown() {\n if (super.pageDown) { super.pageDown(); }\n return scrollOnePage(this, true);\n }\n\n /**\n * Scroll up one page.\n */\n pageUp() {\n if (super.pageUp) { super.pageUp(); }\n return scrollOnePage(this, false);\n }\n\n /**\n * The element that should be scrolled with the Page Up/Down keys.\n * Default is the current element.\n *\n * @type {HTMLElement}\n */\n get scrollTarget() {\n // Prefer base result.\n return 'scrollTarget' in base.prototype ? super.scrollTarget : this;\n }\n set scrollTarget(element) {\n if ('scrollTarget' in base.prototype) { super.scrollTarget = element; }\n }\n }\n\n return KeyboardPagedSelection;\n};\n\n\n// Return the item whose content spans the given y position (relative to the\n// top of the list's scrolling client area), or null if not found.\n//\n// If downward is true, move down the list of items to find the first item\n// found at the given y position; if downward is false, move up the list of\n// items to find the last item at that position.\nfunction getIndexOfItemAtY(element, y, downward) {\n const items = element.items;\n const start = downward ? 0 : items.length - 1;\n const end = downward ? items.length : 0;\n const step = downward ? 1 : -1;\n const scrollTarget = element.scrollTarget;\n const topOfClientArea = scrollTarget.offsetTop + scrollTarget.clientTop;\n\n // Find the item spanning the indicated y coordinate.\n let item;\n let itemIndex = start;\n let itemTop;\n let found = false;\n while (itemIndex !== end) {\n item = items[itemIndex];\n itemTop = item.offsetTop - topOfClientArea;\n const itemBottom = itemTop + item.offsetHeight;\n if (itemTop <= y && itemBottom >= y) {\n // Item spans the indicated y coordinate.\n found = true;\n break;\n }\n itemIndex += step;\n }\n\n if (!found) {\n return null;\n }\n\n // We may have found an item whose padding spans the given y coordinate,\n // but whose content is actually above/below that point.\n // TODO: If the item has a border, then padding should be included in\n // considering a hit.\n const itemStyle = getComputedStyle(item);\n const itemPaddingTop = parseFloat(itemStyle.paddingTop);\n const itemPaddingBottom = parseFloat(itemStyle.paddingBottom);\n const contentTop = itemTop + item.clientTop + itemPaddingTop;\n const contentBottom = contentTop + item.clientHeight - itemPaddingTop - itemPaddingBottom;\n if (downward && contentTop <= y || !downward && contentBottom >= y) {\n // The indicated coordinate hits the actual item content.\n return itemIndex;\n }\n else {\n // The indicated coordinate falls within the item's padding. Back up to\n // the item below/above the item we found and return that.\n return itemIndex - step;\n }\n}\n\n// Move by one page downward (if downward is true), or upward (if false).\n// Return true if we ended up changing the selection, false if not.\n// TODO: Better support for horizontal lists.\nfunction scrollOnePage(element, downward) {\n\n // Determine the item visible just at the edge of direction we're heading.\n // We'll select that item if it's not already selected.\n const scrollTarget = element.scrollTarget;\n const edge = scrollTarget.scrollTop + (downward ? scrollTarget.clientHeight : 0);\n const indexOfItemAtEdge = getIndexOfItemAtY(element, edge, downward);\n\n const selectedIndex = element.selectedIndex;\n let newIndex;\n if (indexOfItemAtEdge && selectedIndex === indexOfItemAtEdge) {\n // The item at the edge was already selected, so scroll in the indicated\n // direction by one page. Leave the new item at that edge selected.\n const delta = (downward ? 1 : -1) * scrollTarget.clientHeight;\n newIndex = getIndexOfItemAtY(element, edge + delta, downward);\n }\n else {\n // The item at the edge wasn't selected yet. Instead of scrolling, we'll\n // just select that item. That is, the first attempt to page up/down\n // usually just moves the selection to the edge in that direction.\n newIndex = indexOfItemAtEdge;\n }\n\n if (!newIndex) {\n // We can't find an item in the direction we want to travel. Select the\n // last item (if moving downward) or first item (if moving upward).\n newIndex = (downward ? element.items.length - 1 : 0);\n }\n\n if (newIndex !== selectedIndex) {\n element.selectedIndex = newIndex;\n return true; // We handled the page up/down ourselves.\n }\n else {\n return false; // We didn't do anything.\n }\n}\n","import createSymbol from './createSymbol';\nimport symbols from './symbols';\n\n\n// Symbols for private data members on an element.\nconst itemTextContentsSymbol = createSymbol('itemTextContents');\nconst typedPrefixSymbol = createSymbol('typedPrefix');\nconst prefixTimeoutSymbol = createSymbol('prefixTimeout');\n\n\n/* Exported function extends a base class with KeyboardPrefixSelection. */\nexport default (base) => {\n\n /**\n * Mixin that handles list box-style prefix typing, in which the user can type\n * a string to select the first item that begins with that string.\n *\n * Example: suppose a component using this mixin has the following items:\n *\n * \n * Apple
\n * Apricot
\n * Banana
\n * Blackberry
\n * Blueberry
\n * Cantaloupe
\n * Cherry
\n * Lemon
\n * Lime
\n * \n *\n * If this component receives the focus, and the user presses the \"b\" or \"B\"\n * key, the \"Banana\" item will be selected, because it's the first item that\n * matches the prefix \"b\". (Matching is case-insensitive.) If the user now\n * presses the \"l\" or \"L\" key quickly, the prefix to match becomes \"bl\", so\n * \"Blackberry\" will be selected.\n *\n * The prefix typing feature has a one second timeout — the prefix to match\n * will be reset after a second has passed since the user last typed a key.\n * If, in the above example, the user waits a second between typing \"b\" and\n * \"l\", the prefix will become \"l\", so \"Lemon\" would be selected.\n *\n * This mixin expects the component to invoke a `keydown` method when a key is\n * pressed. You can use [KeyboardMixin](KeyboardMixin.md) for that\n * purpose, or wire up your own keyboard handling and call `keydown` yourself.\n *\n * This mixin also expects the component to provide an `items` property. The\n * `textContent` of those items will be used for purposes of prefix matching.\n */\n class KeyboardPrefixSelection extends base {\n\n // TODO: If the set of items is changed, reset the prefix.\n // [symbols.itemsChanged]() {\n // this[itemTextContentsSymbol] = null;\n // resetTypedPrefix(this);\n // }\n\n // TODO: If the selection is changed by some other means (e.g., arrow keys)\n // other than prefix typing, then that act should reset the prefix.\n\n [symbols.keydown](event) {\n let handled;\n let resetPrefix = true;\n\n switch (event.keyCode) {\n case 8: // Backspace\n handleBackspace(this);\n handled = true;\n resetPrefix = false;\n break;\n case 27: // Escape\n handled = true;\n break;\n default:\n if (!event.ctrlKey && !event.metaKey && !event.altKey &&\n event.which !== 32 /* Space */) {\n handlePlainCharacter(this, String.fromCharCode(event.which));\n }\n resetPrefix = false;\n }\n\n if (resetPrefix) {\n resetTypedPrefix(this);\n }\n\n // Prefer mixin result if it's defined, otherwise use base result.\n return handled || (super[symbols.keydown] && super[symbols.keydown](event));\n }\n\n /**\n * Select the first item whose text content begins with the given prefix.\n *\n * @param prefix [String] The prefix string to search for\n */\n selectItemWithTextPrefix(prefix) {\n if (super.selectItemWithTextPrefix) { super.selectItemWithTextPrefix(prefix); }\n if (prefix == null || prefix.length === 0) {\n return;\n }\n const index = getIndexOfItemWithTextPrefix(this, prefix);\n if (index >= 0) {\n this.selectedIndex = index;\n }\n }\n\n }\n\n return KeyboardPrefixSelection;\n};\n\n\n// Time in milliseconds after which the user is considered to have stopped\n// typing.\nconst PREFIX_TIMEOUT_DURATION = 1000;\n\n\n// Return the index of the first item with the given prefix, else -1.\nfunction getIndexOfItemWithTextPrefix(element, prefix) {\n const itemTextContents = getItemTextContents(element);\n const prefixLength = prefix.length;\n for (let i = 0; i < itemTextContents.length; i++) {\n const itemTextContent = itemTextContents[i];\n if (itemTextContent.substr(0, prefixLength) === prefix) {\n return i;\n }\n }\n return -1;\n}\n\n// Return an array of the text content (in lowercase) of all items.\n// Cache these results.\nfunction getItemTextContents(element) {\n if (!element[itemTextContentsSymbol]) {\n const items = element.items;\n element[itemTextContentsSymbol] = items.map(child => {\n const text = child.textContent || child.alt;\n return text.toLowerCase();\n });\n }\n return element[itemTextContentsSymbol];\n}\n\nfunction handleBackspace(element) {\n const length = element[typedPrefixSymbol] ? element[typedPrefixSymbol].length : 0;\n if (length > 0) {\n element[typedPrefixSymbol] = element[typedPrefixSymbol].substr(0, length - 1);\n }\n element.selectItemWithTextPrefix(element[typedPrefixSymbol]);\n setPrefixTimeout(element);\n}\n\nfunction handlePlainCharacter(element, char) {\n const prefix = element[typedPrefixSymbol] || '';\n element[typedPrefixSymbol] = prefix + char.toLowerCase();\n element.selectItemWithTextPrefix(element[typedPrefixSymbol]);\n setPrefixTimeout(element);\n}\n\nfunction resetPrefixTimeout(element) {\n if (element[prefixTimeoutSymbol]) {\n clearTimeout(element[prefixTimeoutSymbol]);\n element[prefixTimeoutSymbol] = false;\n }\n}\n\nfunction resetTypedPrefix(element) {\n element[typedPrefixSymbol] = '';\n resetPrefixTimeout(element);\n}\n\nfunction setPrefixTimeout(element) {\n resetPrefixTimeout(element);\n element[prefixTimeoutSymbol] = setTimeout(() => {\n resetTypedPrefix(element);\n }, PREFIX_TIMEOUT_DURATION);\n}\n","import renderArrayAsElements from '../../basic-component-mixins/src/renderArrayAsElements';\nimport symbols from '../../basic-component-mixins/src/symbols';\nimport toggleClass from '../../basic-component-mixins/src/toggleClass';\n\n\n/* Exported function extends a base class with PageDots. */\nexport default (base) => {\n\n /**\n * Template mixin which adds small dots to show the number of items and let\n * the user select a specific item.\n *\n * You can see a\n * [live demo](http://basicwebcomponents.org/basic-web-components/packages/demos/carousel-with-dots.html)\n * of this mixin applied to a carousel.\n *\n * There will be one dot for each item, and the dot for the currently selected\n * item will be shown selected.\n *\n * Typical usage:\n *\n * class CarouselWithDots extends PageDotsMixin(Carousel) {}\n * customElements.define('carousel-with-dots', CarouselWithDots);\n *\n * Although the dots are quite small by default, clicking/tapping a dot will\n * will select the corresponding list item.\n */\n class PageDots extends base {\n\n constructor() {\n super();\n\n this.$.dots.addEventListener('click', event => {\n const dot = event.target;\n const dotIndex = this.dots.indexOf(dot);\n if (dotIndex >= 0) {\n this.selectedIndex = dotIndex;\n }\n });\n }\n\n get dots() {\n return [].slice.call(this.$.dots.querySelectorAll('.dot'));\n }\n\n [symbols.itemsChanged]() {\n if (super[symbols.itemsChanged]) { super[symbols.itemsChanged](); }\n renderArrayAsElements(this.items, this.$.dots, (item, element) => {\n // We don't use the item parameter, because any item will produce an\n // identical corresponding dot.\n if (!element) {\n element = document.createElement('div');\n element.classList.add('dot');\n element.classList.add('style-scope');\n element.classList.add('basic-page-dots');\n element.setAttribute('role', 'none');\n return element;\n }\n });\n refreshDots(this);\n }\n\n [symbols.itemSelected](item, selected) {\n if (super[symbols.itemSelected]) { super[symbols.itemSelected](item, selected); }\n const index = this.items.indexOf(item);\n // See if the corresponding dot has already been created.\n // If not, the correct dot will be selected when it gets created.\n const dots = this.dots;\n if (dots && dots.length > index) {\n const dot = this.dots[index];\n if (dot) {\n toggleClass(dot, 'selected', selected);\n }\n }\n }\n\n /**\n * The distance the user has moved the first touchpoint since the beginning\n * of a drag, expressed as a fraction of the element's width.\n *\n * @type number\n */\n get selectedFraction() {\n return super.selectedFraction;\n }\n set selectedFraction(value) {\n if ('selectedFraction' in base.prototype) { super.selectedFraction = value; }\n renderTransition(this, this.selectedIndex, value);\n }\n\n get selectedIndex() {\n return super.selectedIndex;\n }\n set selectedIndex(index) {\n if ('selectedIndex' in base.prototype) { super.selectedIndex = index; }\n refreshDots(this);\n }\n\n get [symbols.template]() {\n const baseTemplate = super[symbols.template] || '';\n return `\n \n\n
\n \n ${baseTemplate}\n
\n `;\n }\n\n }\n\n return PageDots;\n};\n\n\n// Return the index, ensuring it stays between 0 and the given length.\nfunction keepIndexWithinBounds(length, index) {\n // Handle possibility of negative mod.\n // See http://stackoverflow.com/a/18618250/76472\n return ((index % length) + length) % length;\n}\n\nfunction renderTransition(element, selectedIndex, selectedFraction) {\n const dots = element.dots;\n if (!dots || dots.length === 0) {\n return;\n }\n const dotCount = dots.length;\n const opacityMinimum = 0.4;\n const opacityMaximum = 0.95;\n const opacityRange = opacityMaximum - opacityMinimum;\n const fractionalIndex = selectedIndex + selectedFraction;\n const leftIndex = Math.floor(fractionalIndex);\n const rightIndex = Math.ceil(fractionalIndex);\n const selectionWraps = element.selectionWraps;\n let awayIndex = selectedFraction >= 0 ? leftIndex : rightIndex;\n let towardIndex = selectedFraction >= 0 ? rightIndex : leftIndex;\n if (selectionWraps) {\n awayIndex = keepIndexWithinBounds(dotCount, awayIndex);\n towardIndex = keepIndexWithinBounds(dotCount, towardIndex);\n }\n // Stupid IE doesn't have Math.trunc.\n // const truncatedSelectedFraction = Math.trunc(selectedFraction);\n const truncatedSelectedFraction = selectedFraction < 0 ? Math.ceil(selectedFraction) : Math.floor(selectedFraction);\n const progress = selectedFraction - truncatedSelectedFraction;\n const opacityProgressThroughRange = Math.abs(progress) * opacityRange;\n dots.forEach((dot, index) => {\n let dotOpacity;\n if (selectedFraction === 0) {\n // Remove explicit opacity and rely on styling.\n dotOpacity = '';\n } else if (index === awayIndex) {\n dotOpacity = opacityMaximum - opacityProgressThroughRange;\n } else if (index === towardIndex) {\n dotOpacity = opacityMinimum + opacityProgressThroughRange;\n } else {\n dotOpacity = opacityMinimum;\n }\n dot.style.opacity = dotOpacity;\n });\n}\n\nfunction refreshDots(element) {\n const selectedIndex = element.selectedIndex;\n element.dots.forEach((dot, i) => {\n toggleClass(dot, 'selected', i === selectedIndex);\n });\n}\n","import safeAttributes from '../../basic-component-mixins/src/safeAttributes';\nimport symbols from '../../basic-component-mixins/src/symbols';\n\n\n/* Exported function extends a base class with PlayControls. */\nexport default (base) => {\n\n /**\n * Template mixin which adds buttons for managing playback of a slideshow,\n * audio playlist, etc.\n *\n * Typical usage:\n *\n * class SlideshowWithControls extends PlayControlsMixin(Slideshow) {}\n * customElements.define('slideshow-with-controls', SlideshowWithControls);\n *\n */\n class PlayControls extends base {\n\n constructor() {\n super();\n this.$.previousButton.addEventListener('click', event => {\n this.selectPrevious();\n });\n this.$.playButton.addEventListener('click', event => {\n this.playing = !this.playing;\n });\n this.$.nextButton.addEventListener('click', event => {\n this.selectNext();\n });\n }\n\n connectedCallback() {\n if (super.connectedCallback) { super.connectedCallback(); }\n safeAttributes.connected(this);\n }\n\n [symbols.keydown](event) {\n let handled;\n\n switch (event.keyCode) {\n case 32: /* Space */\n this.playing = !this.playing;\n handled = true;\n break;\n }\n\n // Prefer mixin result if it's defined, otherwise use base result.\n return handled || (super[symbols.keydown] && super[symbols.keydown](event));\n }\n\n get playing() {\n return super.playing;\n }\n set playing(value) {\n if ('playing' in base.prototype) { super.playing = value; }\n safeAttributes.toggleClass(this, 'playing', value);\n }\n\n get [symbols.template]() {\n const baseTemplate = super[symbols.template] || '';\n return `\n \n\n \n\n \n ${baseTemplate}\n
\n `;\n }\n\n }\n\n return PlayControls;\n};\n","import createSymbol from './createSymbol';\nimport FractionalSelectionMixin from './FractionalSelectionMixin';\nimport symbols from './symbols';\n\n\n// Symbols for private data members on an element.\nconst animationSymbol = createSymbol('animation');\nconst draggingSymbol = createSymbol('dragging');\nconst lastAnimationSymbol = createSymbol('lastAnimation');\nconst playingAnimationSymbol = createSymbol('animatingSelection');\nconst previousSelectionSymbol = createSymbol('previousSelection');\nconst selectionAnimationDurationSymbol = createSymbol('selectionAnimationDuration');\nconst selectionAnimationEffectSymbol = createSymbol('selectionAnimationEffect');\nconst selectionAnimationKeyframesSymbol = createSymbol('selectionAnimationKeyframes');\nconst resetAnimationsOnNextRenderSymbol = createSymbol('resetAnimationsOnNextRender');\n\n\n/* Exported function extends a base class with SelectionAnimation. */\nexport default function mixin(base) {\n\n /**\n * Mixin which uses animation to show transitions between selection states.\n *\n * This mixin can be used by components that want to provide visible\n * animations when changing the selection. For example, a carousel component\n * may want to define a sliding animation effect shown when moving between\n * items.\n *\n * The animation is defined by a `selectionAnimationKeyframes` property; see\n * that property for details on how to define these keyframes. This animation\n * will be used in two ways. First, when moving strictly between items, the\n * animation will play smoothly to show the selection changing. Second, the\n * animation can be used to render the selection at a fixed point in the\n * transition between states. E.g., if the user pauses halfway through\n * dragging an element using [SwipeDirectionMixin](SwipeDirectionMixin.md)\n * or [TrackpadDirectionMixin](TrackpadDirectionMixin.md)s, then the selection\n * animation will be shown at the point exactly halfway through.\n *\n * This mixin expects a component to provide an `items` array of all elements\n * in the list, which can be provided via\n * [ContentItemsMixin](ContentItemsMixin.md). This mixin also expects\n * `selectedIndex` and `selectedItem` properties, which can be provided via\n * [SingleSelectionMixin](SingleSelectionMixin.md).\n *\n * This mixin supports a `selectionWraps` property. When true, the user can\n * navigate forward from the last item in the list and wrap around to the\n * first item, or navigate backward from the first item and wrap around to the\n * last item.\n *\n * This mixin uses the Web Animations API. For use on browsers which\n * do not support that API natively, you will need to load the\n * [Web Animations polyfill](https://github.com/web-animations/web-animations-js).\n */\n class SelectionAnimation extends base {\n\n constructor() {\n super();\n\n // Set defaults.\n if (typeof this.selectionAnimationDuration === 'undefined') {\n this.selectionAnimationDuration = this[symbols.defaults].selectionAnimationDuration;\n }\n if (typeof this.selectionAnimationEffect === 'undefined' && this.selectionAnimationKeyframes == null) {\n this.selectionAnimationEffect = this[symbols.defaults].selectionAnimationEffect;\n }\n\n this[symbols.dragging] = false;\n }\n\n get [symbols.defaults]() {\n const defaults = super[symbols.defaults] || {};\n defaults.selectionAnimationDuration = 250;\n defaults.selectionAnimationEffect = 'slide';\n return defaults;\n }\n\n /*\n * Provide backing for the dragging property.\n * Also, when a drag begins, reset the animations.\n */\n get [symbols.dragging]() {\n return this[draggingSymbol];\n }\n set [symbols.dragging](value) {\n const previousValue = this[symbols.dragging];\n this[draggingSymbol] = value;\n if (symbols.dragging in base.prototype) { super[symbols.dragging] = value; }\n if (value && !previousValue) {\n // Have begun a drag.\n this[resetAnimationsOnNextRenderSymbol] = true;\n }\n }\n\n [symbols.itemAdded](item) {\n // We mark new items in the list as explicitly visible to ARIA. Otherwise,\n // when an item isn't visible on the screen, ARIA will assume the item is\n // of no interest to the user, and leave it out of the accessibility tree.\n // If the list contains 10 items, but only 3 are visible, a screen reader\n // might then announce the list only has 3 items. To ensure that screen\n // readers and other assistive technologies announce the correct total\n // number of items, we explicitly mark all items as not hidden. This will\n // expose them all in the accessibility tree, even the items which are\n // currently not rendered.\n //\n // TODO: Generally speaking, this entire mixin assumes that the user can\n // navigate through all items in a list. But an app could style an item as\n // display:none or visibility:hidden because the user is not allowed to\n // interact with that item at the moment. Support for this scenario should\n // be added. This would entail changing all locations where a mixin\n // function is counting items, iterating over the (visible) items, and\n // showing or hiding items. Among other things, the code below to make\n // items visible to ARIA would need to discriminate between items which\n // are invisible because of animation state, or invisible because the user\n // shouldn't interact with them.\n item.setAttribute('aria-hidden', false);\n }\n\n [symbols.itemsChanged]() {\n if (super[symbols.itemsChanged]) { super[symbols.itemsChanged](); }\n\n resetAnimations(this);\n\n // TODO: Also reset our notion of the last rendered selection? This comes\n // up when a DOM removal causes the selected item to change position.\n // this[previousSelectionSymbol] = null;\n\n renderSelection(this);\n }\n\n resetAnimations() {\n resetAnimations(this);\n }\n\n /**\n * A fractional value indicating how far the user has currently advanced to\n * the next/previous item. E.g., a `selectedFraction` of 3.5 indicates the\n * user is halfway between items 3 and 4.\n *\n * For more details, see [FractionalSelectionMixin](FractionalSelectionMixin.md)\n * mixin.\n *\n * @type {number}\n */\n get selectedFraction() {\n return super.selectedFraction || 0;\n }\n set selectedFraction(value) {\n if ('selectedFraction' in base.prototype) { super.selectedFraction = value; }\n renderSelection(this, this.selectedIndex, value);\n }\n\n get selectedIndex() {\n return super.selectedIndex;\n }\n set selectedIndex(index) {\n if ('selectedIndex' in base.prototype) { super.selectedIndex = index; }\n renderSelection(this, index, 0);\n }\n\n /**\n * The duration of a selection animation in milliseconds.\n *\n * This measures the amount of time required for a selection animation to\n * complete. This number remains constant, even if the number of items being\n * animated increases.\n *\n * The default value is 250 milliseconds (a quarter a second).\n *\n * @type {number}\n * @default 250\n */\n get selectionAnimationDuration() {\n return this[selectionAnimationDurationSymbol];\n }\n set selectionAnimationDuration(value) {\n this[selectionAnimationDurationSymbol] = value;\n if ('selectionAnimationDuration' in base.prototype) { super.selectionAnimationDuration = value; }\n }\n\n /**\n * The name of a standard selection animation effect.\n *\n * This is a shorthand for setting the `selectionAnimationKeyframes`\n * property to standard keyframes. Supported string values:\n *\n * * \"crossfade\"\n * * \"reveal\"\n * * \"revealWithFade\"\n * * \"showAdjacent\"\n * * \"slide\"\n * * \"slideWithGap\"\n *\n * @type {string}\n * @default \"slide\"\n */\n get selectionAnimationEffect() {\n return this[selectionAnimationEffectSymbol];\n }\n set selectionAnimationEffect(value) {\n this[selectionAnimationEffectSymbol] = value;\n if ('selectionAnimationEffect' in base.prototype) { super.selectionAnimationEffect = value; }\n this.selectionAnimationKeyframes = mixin.standardEffectKeyframes[value];\n }\n\n /**\n * The keyframes that define an animation that plays for an item when moving\n * forward in the sequence.\n *\n * This is an array of CSS rules that will be applied. These are used as\n * [keyframes](http://w3c.github.io/web-animations/#keyframes-section)\n * to animate the item with the\n * [Web Animations API](https://developer.mozilla.org/en-US/docs/Web/API/animation).\n *\n * The animation represents the state of the next item as it moves from\n * completely unselected (offstage, usually right), to selected (center\n * stage), to completely unselected (offstage, usually left). The center time\n * of the animation should correspond to the item's quiscent selected state,\n * typically in the center of the stage and at the item's largest size.\n *\n * The default forward animation is a smooth slide at full size from right to\n * left.\n *\n * When moving the selection backward, this animation is played in reverse.\n *\n * @type {cssRules[]}\n */\n get selectionAnimationKeyframes() {\n // Standard animation slides left/right, keeps adjacent items out of view.\n return this[selectionAnimationKeyframesSymbol];\n }\n set selectionAnimationKeyframes(value) {\n this[selectionAnimationKeyframesSymbol] = value;\n if ('selectionAnimationKeyframes' in base.prototype) { super.selectionAnimationKeyframes = value; }\n resetAnimations(this);\n renderSelection(this);\n }\n\n get selectionWraps() {\n return super.selectionWraps;\n }\n set selectionWraps(value) {\n if ('selectionWraps' in base.prototype) { super.selectionWraps = value; }\n resetAnimations(this);\n renderSelection(this);\n }\n }\n\n return SelectionAnimation;\n}\n\n\n// We expose helpers on the mixin function that we want to be able to unit test.\n// Since these are on the function, not on the class emitted by the function,\n// they don't end up getting exposed on actual element instances.\nmixin.helpers = {\n\n /*\n * Calculate the animation fractions for an element's items at the given\n * selection point. This is used when rendering the element's selection state\n * instantaneously.\n *\n * This function considers the selectedIndex parameter, which can be a whole\n * or fractional number, and determines which items will be visible at that\n * index. This function then calculates a corresponding animation fraction: a\n * number between 0 and 1 indicating how far through the selection animation\n * an item should be shown, or null if the item should not be visible at that\n * selection index. These fractions are returned as an array, where the\n * animation fraction at position N corresponds to how item N should be shown.\n */\n animationFractionsForSelection(element, selection) {\n\n const items = element.items;\n if (!items) {\n return;\n }\n\n const itemCount = items.length;\n const selectionWraps = element.selectionWraps;\n\n return items.map((item, itemIndex) => {\n // How many steps from the selection point to this item?\n const steps = stepsToIndex(itemCount, selectionWraps, selection, itemIndex);\n // To convert steps to animation fraction:\n // steps animation fraction\n // 1 0 (stage right)\n // 0 0.5 (center stage)\n // -1 1 (stage left)\n const animationFraction = (1 - steps) / 2;\n return (animationFraction >= 0 && animationFraction <= 1) ?\n animationFraction :\n null; // Outside animation range\n });\n },\n\n /*\n * Calculate the animation timings that should be used to smoothly animate the\n * element's items from one selection state to another.\n *\n * This returns an array of timings, where the timing at position N should be\n * used to animate item N. If an item's timing is null, then that item should\n * not take place in the animation, and should be hidden instead.\n */\n effectTimingsForSelectionAnimation(element, fromSelection, toSelection) {\n\n const items = element.items;\n if (!items) {\n return;\n }\n const itemCount = items.length;\n const selectionWraps = element.selectionWraps;\n const toIndex = FractionalSelectionMixin.helpers.wrappedSelectionParts(toSelection, itemCount, selectionWraps).index;\n const totalSteps = stepsToIndex(itemCount, selectionWraps, fromSelection, toSelection);\n const direction = totalSteps >= 0 ? 'normal': 'reverse';\n const fill = 'both';\n const totalDuration = element.selectionAnimationDuration;\n const stepDuration = totalSteps !== 0 ?\n totalDuration * 2 / Math.ceil(Math.abs(totalSteps)) :\n 0; // No steps required, animation will be instantenous.\n\n const timings = items.map((item, itemIndex) => {\n const steps = stepsToIndex(itemCount, selectionWraps, itemIndex, toSelection);\n // If we include this item in the staggered sequence of animations we're\n // creating, where would the item appear in the sequence?\n let positionInSequence = totalSteps - steps;\n if (totalSteps < 0) {\n positionInSequence = -positionInSequence;\n }\n // So, is this item really included in the sequence?\n if (Math.ceil(positionInSequence) >= 0 && positionInSequence <= Math.abs(totalSteps)) {\n // Note that delay for first item will be negative. That will cause\n // the animation to start halfway through, which is what we want.\n const delay = stepDuration * (positionInSequence - 1)/2;\n const endDelay = itemIndex === toIndex ?\n -stepDuration/2 : // Stop halfway through.\n 0; // Play animation until end.\n return { duration: stepDuration, direction, fill, delay, endDelay };\n } else {\n return null;\n }\n });\n\n return timings;\n }\n\n};\n\n\n// Keyframes for standard selection animation effects.\nmixin.standardEffectKeyframes = {\n\n // Simple crossfade\n crossfade: [\n { opacity: 0 },\n { opacity: 1 },\n { opacity: 0 }\n ],\n\n // Reveal, as if sliding the top card off a deck of cards\n reveal: [\n { transform: 'translateX(0%)', zIndex: 0 },\n { transform: 'translateX(0%)', zIndex: 1 },\n { transform: 'translateX(-100%)', zIndex: 2 }\n ],\n\n // Google Photos-style reveal-with-fade animation\n revealWithFade: [\n { transform: 'translateX(0%) scale(0.75)', opacity: 0, zIndex: 0 },\n { transform: 'translateX(0%) scale(1.0)', opacity: 1, zIndex: 1 },\n { transform: 'translateX(-100%) scale(1.0)', opacity: 1, zIndex: 2 }\n ],\n\n // Carousel variant with a bit of off-stage elements showing\n showAdjacent: [\n { transform: 'translateX(78%) scale(0.7)', zIndex: 0 },\n { transform: 'translateX(0%) scale(0.82)', zIndex: 1 },\n { transform: 'translateX(-78%) scale(0.7)', zIndex: 0 }\n ],\n\n // Simple slide\n slide: [\n { transform: 'translateX(100%)' },\n { transform: 'translateX(-100%)' }\n ],\n\n // Slide, with a gap between\n slideWithGap: [\n { transform: 'translateX(110%)' },\n { transform: 'translateX(-110%)' }\n ]\n\n};\n\n\n/*\n * Smoothly animate the selection between the indicated \"from\" and \"to\"\n * indices. The former can be a fraction, e.g., when the user releases a finger\n * to complete a touch drag, and the selection will snap to the closest whole\n * index.\n */\nfunction animateSelection(element, fromSelection, toSelection) {\n\n resetAnimations(element);\n\n // Calculate the animation timings.\n const items = element.items;\n const keyframes = element.selectionAnimationKeyframes;\n element[playingAnimationSymbol] = true;\n const timings = mixin.helpers.effectTimingsForSelectionAnimation(element, fromSelection, toSelection);\n\n // Figure out which item will be the one *after* the one we're selecting.\n const itemCount = items.length;\n const selectionWraps = element.selectionWraps;\n const selectionIndex = FractionalSelectionMixin.helpers.selectionParts(toSelection, itemCount, selectionWraps).index;\n const totalSteps = stepsToIndex(itemCount, selectionWraps, fromSelection, toSelection);\n const forward = totalSteps >= 0;\n let nextUpIndex = selectionIndex + (forward ? 1 : - 1);\n if (selectionWraps) {\n nextUpIndex = FractionalSelectionMixin.helpers.wrappedSelection(nextUpIndex, itemCount);\n } else if (!isItemIndexInBounds(element, nextUpIndex)) {\n nextUpIndex = null; // At start/end of list; don't have a next item to show.\n }\n\n // Play the animations using those timings.\n let lastAnimationDetails;\n timings.forEach((timing, index) => {\n const item = items[index];\n if (timing) {\n showItem(item, true);\n const animation = item.animate(keyframes, timing);\n element[animationSymbol][index] = animation;\n if (index === nextUpIndex) {\n // This item will be animated, so will already be in the desired state\n // after the animation completes.\n nextUpIndex = null;\n }\n if (timing.endDelay !== 0) {\n // This is the animation for the item that will be left selected.\n // We want to clean up when this animation completes.\n lastAnimationDetails = { animation, index, timing, forward };\n }\n } else {\n // This item doesn't participate in the animation.\n showItem(item, false);\n }\n });\n\n if (lastAnimationDetails != null) {\n // Arrange for clean-up work to be performed.\n lastAnimationDetails.nextUpIndex = nextUpIndex;\n lastAnimationDetails.animation.onfinish = event => selectionAnimationFinished(element, lastAnimationDetails);\n element[lastAnimationSymbol] = lastAnimationDetails.animation;\n } else {\n // Shouldn't happen -- we should always have at least one animation.\n element[playingAnimationSymbol] = false;\n }\n}\n\n\nfunction getAnimationForItemIndex(element, index) {\n if (element[animationSymbol] == null) {\n // Not ready yet;\n return null;\n }\n let animation = element[animationSymbol][index];\n if (!animation) {\n const item = element.items[index];\n animation = item.animate(element.selectionAnimationKeyframes, {\n duration: element.selectionAnimationDuration,\n fill: 'both'\n });\n animation.pause();\n element[animationSymbol][index] = animation;\n }\n return animation;\n}\n\nfunction isItemIndexInBounds(element, index) {\n return index >= 0 && element.items && index < element.items.length;\n}\n\n/*\n * Render the selection state of the element.\n *\n * This can be used to re-render a previous selection state (if the\n * selectedIndex param is omitted), render the selection instantly at a given\n * whole or fractional selection index, or animate to a given selection index.\n *\n * There are several distinct scenarios we need to cover:\n *\n * 1. Initial positioning, or repositioning after changing a property like\n * selectionAnimationKeyframes that affects rendering.\n * 2. Animate on selectedIndex change. This should override any animation/swipe\n * already in progress.\n * 3. Instantly render the current position of a drag operation in progress.\n * 4. Complete a drag operation. If the drag wasn't far enough to affect\n * selection, we'll just be restoring the selectedFraction to 0.\n *\n * If the list does not wrap, any selection position outside the list's bounds\n * will be damped to produce a visual effect of tension.\n */\nfunction renderSelection(element, selectedIndex=element.selectedIndex, selectedFraction=element.selectedFraction) {\n const itemCount = element.items ? element.items.length : 0;\n if (itemCount === 0) {\n // Nothing to render.\n return;\n }\n if (selectedIndex < 0) {\n // TODO: Handle no selection.\n return;\n }\n let selection = selectedIndex + selectedFraction;\n if (element.selectionWraps) {\n // Apply wrapping to ensure consistent representation of selection.\n selection = FractionalSelectionMixin.helpers.wrappedSelection(selection, itemCount);\n } else {\n // Apply damping if necessary.\n selection = FractionalSelectionMixin.helpers.dampedSelection(selection, itemCount);\n }\n const previousSelection = element[previousSelectionSymbol];\n // TODO: If an item changes position in the DOM, we end up animating from\n // its old index to its new index, but we really don't want to animate at all.\n if (!element[symbols.dragging] && previousSelection != null &&\n previousSelection !== selection) {\n // Animate selection from previous state to new state.\n animateSelection(element, previousSelection, selection);\n } else if (selectedFraction === 0 && element[playingAnimationSymbol]) {\n // Already in process of animating to fraction 0. During that process,\n // ignore subsequent attempts to renderSelection to fraction 0.\n return;\n } else {\n // Render current selection state instantly.\n renderSelectionInstantly(element, selection);\n }\n element[previousSelectionSymbol] = selection;\n}\n\n/*\n * Instantly render (don't animate) the element's items at the given whole or\n * fractional selection index.\n */\nfunction renderSelectionInstantly(element, toSelection) {\n if (element[resetAnimationsOnNextRenderSymbol]) {\n resetAnimations(element);\n element[resetAnimationsOnNextRenderSymbol] = false;\n }\n const animationFractions = mixin.helpers.animationFractionsForSelection(element, toSelection);\n animationFractions.map((animationFraction, index) => {\n const item = element.items[index];\n if (animationFraction != null) {\n showItem(item, true);\n setAnimationFraction(element, index, animationFraction);\n } else {\n showItem(item, false);\n }\n });\n}\n\n/*\n * We maintain an array containing an animation per item. This is used for two\n * reasons:\n *\n * * During a drag operation, we want to be able to reuse animations between\n * drag updates.\n * * When a selection animation completes, we need to be able to leave the\n * visibile items in a paused state. Later, we'll want to be able to clean up\n * those animations.\n *\n * Note that this array is sparse: it will only hold up from 0–3 animations at\n * any given point.\n */\nfunction resetAnimations(element) {\n const animations = element[animationSymbol];\n if (animations) {\n // Cancel existing animations to remove the effects they're applying.\n animations.forEach((animation, index) => {\n if (animation) {\n animation.cancel();\n animations[index] = null;\n }\n });\n }\n const itemCount = element.items ? element.items.length : 0;\n if (!animations || animations.length !== itemCount) {\n // Haven't animated before with this number of items; (re)create array.\n element[animationSymbol] = new Array(itemCount);\n }\n}\n\n/*\n * The last animation in our selection animation has completed. Clean up.\n */\nfunction selectionAnimationFinished(element, details) {\n\n // When the last animation completes, show the next item in the direction\n // we're going. Waiting to that until this point is a bit of a hack to avoid\n // having a next item that's higher in the natural z-order obscure other items\n // during animation.\n const nextUpIndex = details.nextUpIndex;\n if (nextUpIndex != null) {\n if (element[animationSymbol][nextUpIndex]) {\n // Cancel existing selection animation so we can construct a new one.\n element[animationSymbol][nextUpIndex].cancel();\n element[animationSymbol][nextUpIndex] = null;\n }\n const animationFraction = details.forward ? 0 : 1;\n setAnimationFraction(element, nextUpIndex, animationFraction);\n showItem(element.items[nextUpIndex], true);\n }\n\n element[lastAnimationSymbol].onfinish = null;\n element[playingAnimationSymbol] = false;\n}\n\n/*\n * Pause the indicated animation and have it show the animation at the given\n * fraction (between 0 and 1) of the way through the animation.\n */\nfunction setAnimationFraction(element, itemIndex, fraction) {\n const animation = getAnimationForItemIndex(element, itemIndex);\n if (animation) {\n const duration = element.selectionAnimationDuration;\n if (duration) {\n animation.currentTime = fraction * duration;\n }\n }\n}\n\nfunction showItem(item, flag) {\n item.style.visibility = flag ? 'visible' : 'hidden';\n}\n\n/*\n * Figure out how many steps it will take to go from fromSelection to\n * toSelection. To go from item 3 to item 4 is one step.\n *\n * If wrapping is allowed, then going from the last item to the first will take\n * one step (forward), and going from the first item to the last will take one\n * step (backward).\n */\nfunction stepsToIndex(length, allowWrap, fromSelection, toSelection) {\n let steps = toSelection - fromSelection;\n // Wrapping only kicks in when list has more than 1 item.\n if (allowWrap && length > 1) {\n const wrapSteps = length - Math.abs(steps);\n if (wrapSteps <= 1) {\n // Special case\n steps = steps < 0 ?\n wrapSteps : // Wrap forward from last item to first.\n -wrapSteps; // Wrap backward from first item to last.\n }\n }\n return steps;\n}\n","import symbols from './symbols';\n\n\n// Used to assign unique IDs to item elements without IDs.\nlet idCount = 0;\n\n\n/* Exported function extends a base class with SelectionAriaActive. */\nexport default (base) => {\n\n /**\n * Mixin which treats the selected item in a list as the active item in ARIA\n * accessibility terms.\n *\n * Handling ARIA selection state properly is actually quite complex:\n *\n * * The items in the list need to be indicated as possible items via an ARIA\n * `role` attribute value such as \"option\".\n * * The selected item need to be marked as selected by setting the item's\n * `aria-selected` attribute to true *and* the other items need be marked as\n * *not* selected by setting `aria-selected` to false.\n * * The outermost element with the keyboard focus needs to have attributes\n * set on it so that the selection is knowable at the list level via the\n * `aria-activedescendant` attribute.\n * * Use of `aria-activedescendant` in turn requires that all items in the\n * list have ID attributes assigned to them.\n *\n * This mixin tries to address all of the above requirements. To that end,\n * this mixin will assign generated IDs to any item that doesn't already have\n * an ID.\n *\n * ARIA relies on elements to provide `role` attributes. This mixin will apply\n * a default role of \"listbox\" on the outer list if it doesn't already have an\n * explicit role. Similarly, this mixin will apply a default role of \"option\"\n * to any list item that does not already have a role specified.\n *\n * This mixin expects a set of members that manage the state of the selection:\n * `[symbols.itemSelected]`, `itemAdded`, and `selectedIndex`. You can\n * supply these yourself, or do so via\n * [SingleSelectionMixin](SingleSelectionMixin.md).\n */\n class SelectionAriaActive extends base {\n\n connectedCallback() {\n if (super.connectedCallback) { super.connectedCallback(); }\n // Set default ARIA role.\n if (this.getAttribute('role') == null && this[symbols.defaults].role) {\n this.setAttribute('role', this[symbols.defaults].role);\n }\n }\n\n get [symbols.defaults]() {\n const defaults = super[symbols.defaults] || {};\n defaults.role = 'listbox';\n return defaults;\n }\n\n [symbols.itemAdded](item) {\n if (super[symbols.itemAdded]) { super[symbols.itemAdded](item); }\n\n if (!item.getAttribute('role')) {\n // Assign a default ARIA role.\n item.setAttribute('role', 'option');\n }\n\n // Ensure each item has an ID so we can set aria-activedescendant on the\n // overall list whenever the selection changes.\n //\n // The ID will take the form of a base ID plus a unique integer. The base\n // ID will be incorporate the component's own ID. E.g., if a component has\n // ID \"foo\", then its items will have IDs that look like \"_fooOption1\". If\n // the compnent has no ID itself, its items will get IDs that look like\n // \"_option1\". Item IDs are prefixed with an underscore to differentiate\n // them from manually-assigned IDs, and to minimize the potential for ID\n // conflicts.\n if (!item.id) {\n const baseId = this.id ?\n \"_\" + this.id + \"Option\" :\n \"_option\";\n item.id = baseId + idCount++;\n }\n }\n\n [symbols.itemSelected](item, selected) {\n if (super[symbols.itemSelected]) { super[symbols.itemSelected](item, selected); }\n item.setAttribute('aria-selected', selected);\n const itemId = item.id;\n if (itemId && selected) {\n this.setAttribute('aria-activedescendant', itemId);\n }\n }\n\n get selectedItem() {\n return super.selectedItem;\n }\n set selectedItem(item) {\n if ('selectedItem' in base.prototype) { super.selectedItem = item; }\n if (item == null) {\n // Selection was removed.\n this.removeAttribute('aria-activedescendant');\n }\n }\n\n }\n\n return SelectionAriaActive;\n};\n","import symbols from '../src/symbols';\n\n\n/* Exported function extends a base class with SelectionHighlight. */\nexport default (base) => {\n\n /**\n * Template mixin which applies standard highlight colors to a selected item.\n *\n * This mixin highlights textual items (e.g., in a list) in a standard way by\n * using the CSS `highlight` and `highlighttext` color values. These values\n * respect operating system defaults and user preferences, and hence are good\n * default values for highlight colors.\n *\n * This mixin expects a `selected` class to be applied to selected items. You\n * can use [ContentItemsMixin](ContentItemsMixin.md) for that purpose.\n */\n class SelectionHighlight extends base {\n\n get [symbols.template]() {\n const baseTemplate = super[symbols.template] || '';\n return `\n \n ${baseTemplate}\n `;\n }\n\n }\n\n return SelectionHighlight;\n};\n","/* Exported function extends a base class with SelectionInView. */\nexport default (base) => {\n\n /**\n * Mixin which scrolls a container to ensure that a newly-selected item is\n * visible to the user.\n *\n * When the selected item in a list-like component changes, it's easier for\n * the to confirm that the selection has changed to an appropriate item if the\n * user can actually see that item.\n *\n * This mixin expects a `selectedItem` property to be set when the selection\n * changes. You can supply that yourself, or use\n * [SingleSelectionMixin](SingleSelectionMixin.md).\n */\n class SelectionInView extends base {\n\n connectedCallback() {\n if (super.connectedCallback) { super.connectedCallback(); }\n const selectedItem = this.selectedItem;\n if (selectedItem) {\n this.scrollItemIntoView(selectedItem);\n }\n }\n\n get selectedItem() {\n return super.selectedItem;\n }\n set selectedItem(item) {\n if ('selectedItem' in base.prototype) { super.selectedItem = item; }\n if (item) {\n // Keep the selected item in view.\n this.scrollItemIntoView(item);\n }\n }\n\n /**\n * Scroll the given element completely into view, minimizing the degree of\n * scrolling performed.\n *\n * Blink has a `scrollIntoViewIfNeeded()` function that does something\n * similar, but unfortunately it's non-standard, and in any event often ends\n * up scrolling more than is absolutely necessary.\n *\n * @param {HTMLElement} item - the item to scroll into view.\n */\n scrollItemIntoView(item) {\n if (super.scrollItemIntoView) { super.scrollItemIntoView(); }\n // Get the relative position of the item with respect to the top of the\n // list's scrollable canvas. An item at the top of the list will have a\n // elementTop of 0.\n\n const scrollTarget = this.scrollTarget;\n const elementTop = item.offsetTop - scrollTarget.offsetTop - scrollTarget.clientTop;\n const elementBottom = elementTop + item.offsetHeight;\n // Determine the bottom of the scrollable canvas.\n const scrollBottom = scrollTarget.scrollTop + scrollTarget.clientHeight;\n if (elementBottom > scrollBottom) {\n // Scroll up until item is entirely visible.\n scrollTarget.scrollTop += elementBottom - scrollBottom;\n }\n else if (elementTop < scrollTarget.scrollTop) {\n // Scroll down until item is entirely visible.\n scrollTarget.scrollTop = elementTop;\n }\n }\n\n /**\n * The element that should be scrolled to bring an item into view.\n *\n * The default value of this property is the element itself.\n *\n * @type {HTMLElement}\n */\n get scrollTarget() {\n // Prefer base result.\n return 'scrollTarget' in base.prototype ? super.scrollTarget : this;\n }\n set scrollTarget(element) {\n if ('scrollTarget' in base.prototype) { super.scrollTarget = element; }\n }\n\n }\n\n return SelectionInView;\n};\n","/* Exported function extends a base class with ShadowElementReferences. */\nexport default (base) => {\n\n /**\n * Mixin to create references to elements in a component's Shadow DOM subtree.\n *\n * This adds a member on the component called `this.$` that can be used to\n * reference shadow elements with IDs. E.g., if component's shadow contains an\n * element ``, then this mixin will create a member\n * `this.$.foo` that points to that button.\n *\n * Such references simplify a component's access to its own elements. In\n * exchange, this mixin trades off a one-time cost of querying all elements in\n * the shadow tree instead of paying an ongoing cost to query for an element\n * each time the component wants to inspect or manipulate it.\n *\n * This mixin expects the component to define a Shadow DOM subtree. You can\n * create that tree yourself, or make use of\n * [ShadowTemplateMixin](ShadowTemplateMixin.md).\n *\n * This mixin is inspired by Polymer's [automatic\n * node finding](https://www.polymer-project.org/1.0/docs/devguide/local-dom.html#node-finding)\n * feature.\n */\n class ShadowElementReferences extends base {\n\n constructor() {\n super();\n if (this.shadowRoot) {\n // Look for elements in the shadow subtree that have id attributes.\n // An alternatively implementation of this mixin would be to just define\n // a this.$ getter that lazily does this search the first time someone\n // tries to access this.$. That might introduce some complexity – if the\n // the tree changed after it was first populated, the result of\n // searching for a node might be somewhat unpredictable.\n this.$ = {};\n const nodesWithIds = this.shadowRoot.querySelectorAll('[id]');\n [].forEach.call(nodesWithIds, node => {\n const id = node.getAttribute('id');\n this.$[id] = node;\n });\n }\n }\n\n /**\n * The collection of references to the elements with IDs in a component's\n * Shadow DOM subtree.\n *\n * @type {object}\n * @member $\n */\n }\n\n return ShadowElementReferences;\n};\n","import symbols from '../src/symbols';\n\n\n/* Exported function extends a base class with ShadowTemplate. */\nexport default (base) => {\n\n /**\n * Mixin for stamping a template into a Shadow DOM subtree upon component\n * instantiation.\n *\n * To use this mixin, define a `template` property as a string or HTML\n * `` element:\n *\n * class MyElement extends ShadowTemplateMixin(HTMLElement) {\n * get [symbols.template]() {\n * return `Hello, world .`;\n * }\n * }\n *\n * When your component class is instantiated, a shadow root will be created on\n * the instance, and the contents of the template will be cloned into the\n * shadow root. If your component does not define a `template` property, this\n * mixin has no effect.\n *\n * For the time being, this extension retains support for Shadow DOM v0. That\n * will eventually be deprecated as browsers (and the Shadow DOM polyfill)\n * implement Shadow DOM v1.\n */\n class ShadowTemplate extends base {\n\n /*\n * If the component defines a template, a shadow root will be created on the\n * component instance, and the template stamped into it.\n */\n constructor() {\n super();\n let template = this[symbols.template];\n // TODO: Save the processed template with the component's class prototype\n // so it doesn't need to be processed with every instantiation.\n if (template) {\n\n if (typeof template === 'string') {\n // Upgrade plain string to real template.\n template = createTemplateWithInnerHTML(template);\n }\n\n if (window.ShadowDOMPolyfill) {\n shimTemplateStyles(template, this.localName);\n }\n\n const root = this.attachShadow({ mode: 'open' });\n const clone = document.importNode(template.content, true);\n root.appendChild(clone);\n }\n }\n\n }\n\n return ShadowTemplate;\n};\n\n\n// Convert a plain string of HTML into a real template element.\nfunction createTemplateWithInnerHTML(innerHTML) {\n const template = document.createElement('template');\n // REVIEW: Is there an easier way to do this?\n // We'd like to just set innerHTML on the template content, but since it's\n // a DocumentFragment, that doesn't work.\n const div = document.createElement('div');\n div.innerHTML = innerHTML;\n while (div.childNodes.length > 0) {\n template.content.appendChild(div.childNodes[0]);\n }\n return template;\n}\n\n// Invoke basic style shimming with ShadowCSS.\nfunction shimTemplateStyles(template, tag) {\n window.WebComponents.ShadowCSS.shimStyling(template.content, tag);\n}\n","import createSymbol from './createSymbol';\nimport symbols from './symbols';\n\n\n// Symbols for private data members on an element.\nconst canSelectNextSymbol = createSymbol('canSelectNext');\nconst canSelectPreviousSymbol = createSymbol('canSelectPrevious');\nconst selectionRequiredSymbol = createSymbol('selectionRequired');\nconst selectionWrapsSymbol = createSymbol('selectionWraps');\n\n// We want to expose both selectedIndex and selectedItem as independent\n// properties but keep them in sync. This allows a component user to reference\n// the selection by whatever means is most natural for their situation.\n//\n// To efficiently keep these properties in sync, we track \"external\" and\n// \"internal\" references for each property:\n//\n// The external index or item is the one we report to the outside world when\n// asked for selection. When handling a change to index or item, we update the\n// external reference as soon as possible, so that if anyone immediately asks\n// for the current selection, they will receive a stable answer.\n//\n// The internal index or item tracks whichever index or item last received the\n// full set of processing. Processing includes raising a change event for the\n// new value. Once we've begun that processing, we store the new value as the\n// internal value to indicate we've handled it.\n//\nconst externalSelectedIndexSymbol = createSymbol('externalSelectedIndex');\nconst externalSelectedItemSymbol = createSymbol('externalSelectedItem');\nconst internalSelectedIndexSymbol = createSymbol('internalSelectedIndex');\nconst internalSelectedItemSymbol = createSymbol('internalSelectedItem');\n\n\n/* Exported function extends a base class with SingleSelection. */\nexport default (base) => {\n\n /**\n * Mixin which manages single-selection semantics for items in a list.\n *\n * This mixin expects a component to provide an `items` Array or NodeList of\n * all elements in the list. A standard way to do that with is the\n * [ContentItemsMixin](ContentItemsMixin.md), which takes a component's\n * content (typically its distributed children) as the set of list items; see\n * that mixin for details.\n *\n * This mixin tracks a single selected item in the list, and provides means to\n * get and set that state by item position (`selectedIndex`) or item identity\n * (`selectedItem`). The selection can be moved in the list via the methods\n * `selectFirst`, `selectLast`, `selectNext`, and `selectPrevious`.\n *\n * This mixin does not produce any user-visible effects to represent\n * selection. Other mixins, such as\n * [SelectionAriaActiveMixin](SelectionAriaActiveMixin.md),\n * [SelectionHighlightMixin](SelectionHighlightMixin.md) and\n * [SelectionInViewMixin](SelectionInViewMixin.md), modify the selected item\n * in common ways to let the user know a given item is selected or not\n * selected.\n */\n class SingleSelection extends base {\n\n constructor() {\n super();\n // Set defaults.\n if (typeof this.selectionRequired === 'undefined') {\n this.selectionRequired = this[symbols.defaults].selectionRequired;\n }\n if (typeof this.selectionWraps === 'undefined') {\n this.selectionWraps = this[symbols.defaults].selectionWraps;\n }\n }\n\n /**\n * True if the selection can be moved to the next item, false if not (the\n * selected item is the last item in the list).\n *\n * @type {boolean}\n */\n get canSelectNext() {\n return this[canSelectNextSymbol];\n }\n set canSelectNext(canSelectNext) {\n const previousCanSelectNext = this[canSelectNextSymbol];\n this[canSelectNextSymbol] = canSelectNext;\n if ('canSelectNext' in base.prototype) { super.canSelectNext = canSelectNext; }\n if (canSelectNext !== previousCanSelectNext) {\n this.dispatchEvent(new CustomEvent('can-select-next-changed'));\n }\n }\n\n /**\n * True if the selection can be moved to the previous item, false if not\n * (the selected item is the first one in the list).\n *\n * @type {boolean}\n */\n get canSelectPrevious() {\n return this[canSelectPreviousSymbol];\n }\n set canSelectPrevious(canSelectPrevious) {\n const previousCanSelectPrevious = this[canSelectPreviousSymbol];\n this[canSelectPreviousSymbol] = canSelectPrevious;\n if ('canSelectPrevious' in base.prototype) { super.canSelectPrevious = canSelectPrevious; }\n if (canSelectPrevious !== previousCanSelectPrevious) {\n this.dispatchEvent(new CustomEvent('can-select-previous-changed'));\n }\n }\n\n get [symbols.defaults]() {\n const defaults = super[symbols.defaults] || {};\n defaults.selectionRequired = false;\n defaults.selectionWraps = false;\n return defaults;\n }\n\n /**\n * Handle a new item being added to the list.\n *\n * The default implementation of this method simply sets the item's\n * selection state to false.\n *\n * @param {HTMLElement} item - the item being added\n */\n [symbols.itemAdded](item) {\n if (super[symbols.itemAdded]) { super[symbols.itemAdded](item); }\n this[symbols.itemSelected](item, item === this.selectedItem);\n }\n\n [symbols.itemsChanged]() {\n if (super[symbols.itemsChanged]) { super[symbols.itemsChanged](); }\n\n // In case selected item changed position or was removed.\n trackSelectedItem(this);\n\n // In case the change in items affected which navigations are possible.\n updatePossibleNavigations(this);\n }\n\n /**\n * Apply the indicate selection state to the item.\n *\n * The default implementation of this method does nothing. User-visible\n * effects will typically be handled by other mixins.\n *\n * @param {HTMLElement} item - the item being selected/deselected\n * @param {boolean} selected - true if the item is selected, false if not\n */\n [symbols.itemSelected](item, selected) {\n if (super[symbols.itemSelected]) { super[symbols.itemSelected](item, selected); }\n }\n\n /**\n * The index of the item which is currently selected.\n *\n * A `selectedIndex` of -1 indicates there is no selection. Setting this\n * property to -1 will remove any existing selection.\n *\n * @type {number}\n */\n get selectedIndex() {\n return this[externalSelectedIndexSymbol] != null ?\n this[externalSelectedIndexSymbol] :\n -1;\n }\n set selectedIndex(index) {\n // See notes at top about internal vs. external copies of this property.\n const previousSelectedIndex = this[internalSelectedIndexSymbol];\n let item;\n if (index !== this[externalSelectedIndexSymbol]) {\n // Store the new index and the corresponding item.\n const items = this.items;\n const hasItems = items && items.length > 0;\n if (!(hasItems && index >= 0 && index < items.length)) {\n index = -1; // No item at that index.\n }\n this[externalSelectedIndexSymbol] = index;\n item = hasItems && index >= 0 ? items[index] : null;\n this[externalSelectedItemSymbol] = item;\n } else {\n item = this[externalSelectedItemSymbol];\n }\n\n // Now let super do any work.\n if ('selectedIndex' in base.prototype) { super.selectedIndex = index; }\n\n if (index !== previousSelectedIndex) {\n // The selected index changed.\n this[internalSelectedIndexSymbol] = index;\n\n const event = new CustomEvent('selected-index-changed', {\n detail: {\n selectedIndex: index,\n value: index // for Polymer binding. TODO: Verify still necessary\n }\n });\n this.dispatchEvent(event);\n }\n\n if (this[internalSelectedItemSymbol] !== item) {\n // Update selectedItem property so it can have its own effects.\n this.selectedItem = item;\n }\n }\n\n /**\n * The currently selected item, or null if there is no selection.\n *\n * Setting this property to null deselects any currently-selected item.\n * Setting this property to an object that is not in the list has no effect.\n *\n * TODO: Even if selectionRequired, can still explicitly set selectedItem to null.\n * TODO: If selectionRequired, leave selection alone?\n *\n * @type {object}\n */\n get selectedItem() {\n return this[externalSelectedItemSymbol] || null;\n }\n set selectedItem(item) {\n // See notes at top about internal vs. external copies of this property.\n const previousSelectedItem = this[internalSelectedItemSymbol];\n let index;\n if (item !== this[externalSelectedItemSymbol]) {\n // Store item and look up corresponding index.\n const items = this.items;\n const hasItems = items && items.length > 0;\n index = hasItems ? Array.prototype.indexOf.call(items, item) : -1;\n this[externalSelectedIndexSymbol] = index;\n if (index < 0) {\n item = null; // The indicated item isn't actually in `items`.\n }\n this[externalSelectedItemSymbol] = item;\n } else {\n index = this[externalSelectedIndexSymbol];\n }\n\n // Now let super do any work.\n if ('selectedItem' in base.prototype) { super.selectedItem = item; }\n\n if (item !== previousSelectedItem) {\n // The selected item changed.\n this[internalSelectedItemSymbol] = item;\n\n if (previousSelectedItem) {\n // Update selection state of old item.\n this[symbols.itemSelected](previousSelectedItem, false);\n }\n if (item) {\n // Update selection state to new item.\n this[symbols.itemSelected](item, true);\n }\n\n updatePossibleNavigations(this);\n\n const event = new CustomEvent('selected-item-changed', {\n detail: {\n selectedItem: item,\n value: item // for Polymer binding\n }\n });\n this.dispatchEvent(event);\n }\n\n if (this[internalSelectedIndexSymbol] !== index) {\n // Update selectedIndex property so it can have its own effects.\n this.selectedIndex = index;\n }\n }\n\n /**\n * Select the first item in the list.\n */\n selectFirst() {\n if (super.selectFirst) { super.selectFirst(); }\n return selectIndex(this, 0);\n }\n\n /**\n * True if the list should always have a selection (if it has items).\n *\n * @type {boolean}\n * @default false\n */\n get selectionRequired() {\n return this[selectionRequiredSymbol];\n }\n set selectionRequired(selectionRequired) {\n this[selectionRequiredSymbol] = selectionRequired;\n if ('selectionRequired' in base.prototype) { super.selectionRequired = selectionRequired; }\n trackSelectedItem(this);\n }\n\n /**\n * True if selection navigations wrap from last to first, and vice versa.\n *\n * @type {boolean}\n * @default false\n */\n get selectionWraps() {\n return this[selectionWrapsSymbol];\n }\n set selectionWraps(value) {\n this[selectionWrapsSymbol] = String(value) === 'true';\n if ('selectionWraps' in base.prototype) { super.selectionWraps = value; }\n updatePossibleNavigations(this);\n }\n\n /**\n * Select the last item in the list.\n */\n selectLast() {\n if (super.selectLast) { super.selectLast(); }\n return selectIndex(this, this.items.length - 1);\n }\n\n /**\n * Select the next item in the list.\n */\n selectNext() {\n if (super.selectNext) { super.selectNext(); }\n return selectIndex(this, this.selectedIndex + 1);\n }\n\n /**\n * Select the previous item in the list.\n *\n * If the list has no selection, the last item will be selected.\n */\n selectPrevious() {\n if (super.selectPrevious) { super.selectPrevious(); }\n const newIndex = this.selectedIndex < 0 ?\n this.items.length - 1 : // No selection yet; select last item.\n this.selectedIndex - 1;\n return selectIndex(this, newIndex);\n }\n\n /**\n * Fires when the selectedItem property changes.\n *\n * @memberof SingleSelection\n * @event selected-item-changed\n * @param {HTMLElement} detail.selectedItem The new selected item.\n * @param {HTMLElement} detail.previousItem The previously selected item.\n */\n\n /**\n * Fires when the selectedIndex property changes.\n *\n * @memberof SingleSelection\n * @event selected-index-changed\n * @param {number} detail.selectedIndex The new selected index.\n */\n\n }\n\n return SingleSelection;\n};\n\n\n// Ensure the given index is within bounds, and select it if it's not already\n// selected.\nfunction selectIndex(element, index) {\n const count = element.items.length;\n\n const boundedIndex = (element.selectionWraps) ?\n // JavaScript mod doesn't handle negative numbers the way we want to wrap.\n // See http://stackoverflow.com/a/18618250/76472\n ((index % count) + count) % count :\n\n // Keep index within bounds of array.\n Math.max(Math.min(index, count - 1), 0);\n\n const previousIndex = element.selectedIndex;\n if (previousIndex !== boundedIndex) {\n element.selectedIndex = boundedIndex;\n return true;\n } else {\n return false;\n }\n}\n\n// Following a change in the set of items, or in the value of the\n// `selectionRequired` property, reacquire the selected item. If it's moved,\n// update `selectedIndex`. If it's been removed, and a selection is required,\n// try to select another item.\nfunction trackSelectedItem(element) {\n\n const items = element.items;\n const itemCount = items ? items.length : 0;\n\n const previousSelectedItem = element.selectedItem;\n if (!previousSelectedItem) {\n // No item was previously selected.\n if (element.selectionRequired) {\n // Select the first item by default.\n element.selectedIndex = 0;\n }\n } else if (itemCount === 0) {\n // We've lost the selection, and there's nothing left to select.\n element.selectedItem = null;\n } else {\n // Try to find the previously-selected item in the current set of items.\n const indexInCurrentItems = Array.prototype.indexOf.call(items, previousSelectedItem);\n const previousSelectedIndex = element.selectedIndex;\n if (indexInCurrentItems < 0) {\n // Previously-selected item was removed from the items.\n // Select the item at the same index (if it exists) or as close as possible.\n const newSelectedIndex = Math.min(previousSelectedIndex, itemCount - 1);\n // Select by item, since index may be the same, and we want to raise the\n // selected-item-changed event.\n element.selectedItem = items[newSelectedIndex];\n } else if (indexInCurrentItems !== previousSelectedIndex) {\n // Previously-selected item still there, but changed position.\n element.selectedIndex = indexInCurrentItems;\n }\n }\n}\n\n// Following a change in selection, report whether it's now possible to\n// go next/previous from the given index.\nfunction updatePossibleNavigations(element) {\n let canSelectNext;\n let canSelectPrevious;\n const items = element.items;\n if (items == null || items.length === 0) {\n // No items to select.\n canSelectNext = false;\n canSelectPrevious = false;\n } if (element.selectionWraps) {\n // Since there are items, can always go next/previous.\n canSelectNext = true;\n canSelectPrevious = true;\n } else {\n const index = element.selectedIndex;\n if (index < 0 && items.length > 0) {\n // Special case. If there are items but no selection, declare that it's\n // always possible to go next/previous to create a selection.\n canSelectNext = true;\n canSelectPrevious = true;\n } else {\n // Normal case: we have an index in a list that has items.\n canSelectPrevious = (index > 0);\n canSelectNext = (index < items.length - 1);\n }\n }\n if (element.canSelectNext !== canSelectNext) {\n element.canSelectNext = canSelectNext;\n }\n if (element.canSelectPrevious !== canSelectPrevious) {\n element.canSelectPrevious = canSelectPrevious;\n }\n}\n","import createSymbol from './createSymbol';\nimport symbols from './symbols';\n\n\n// Symbols for private data members on an element.\nconst deltaXSymbol = createSymbol('deltaX');\nconst deltaYSymbol = createSymbol('deltaY');\nconst multiTouchSymbol = createSymbol('multiTouch');\nconst previousXSymbol = createSymbol('previousX');\nconst previousYSymbol = createSymbol('previousY');\nconst startXSymbol = createSymbol('startX');\nconst travelFractionSymbol = createSymbol('travelFraction');\n\n\n/* Exported function extends a base class with SwipeDirection. */\nexport default (base) => {\n\n /**\n * Mixin which maps touch gestures (swipe left, swipe right) to direction\n * semantics (go right, go left).\n *\n * By default, this mixin presents no user-visible effects; it just indicates\n * a direction in which the user is currently swiping or has finished swiping.\n * To map the direction to a change in selection, use\n * [DirectionSelectionMixin](DirectionSelectionMixin.md).\n */\n class SwipeDirection extends base {\n\n constructor() {\n super();\n\n this.travelFraction = 0;\n\n // In all touch events, only handle single touches. We don't want to\n // inadvertently do work when the user's trying to pinch-zoom for example.\n // TODO: Even better approach than below would be to ignore touches after\n // the first if the user has already begun a swipe.\n // TODO: Touch events should probably be factored out into its own mixin.\n if (window.PointerEvent) {\n // Prefer listening to standard pointer events.\n this.addEventListener('pointerdown', event => {\n if (isEventForPenOrPrimaryTouch(event)) {\n touchStart(this, event.clientX, event.clientY);\n }\n });\n this.addEventListener('pointermove', event => {\n if (isEventForPenOrPrimaryTouch(event)) {\n const handled = touchMove(this, event.clientX, event.clientY);\n if (handled) {\n event.preventDefault();\n }\n }\n });\n this.addEventListener('pointerup', event => {\n if (isEventForPenOrPrimaryTouch(event)) {\n touchEnd(this, event.clientX, event.clientY);\n }\n });\n } else {\n // Pointer events not supported -- listen to older touch events.\n this.addEventListener('touchstart', event => {\n if (this[multiTouchSymbol]) {\n return;\n } else if (event.touches.length === 1) {\n const clientX = event.changedTouches[0].clientX;\n const clientY = event.changedTouches[0].clientY;\n touchStart(this, clientX, clientY);\n } else {\n this[multiTouchSymbol] = true;\n }\n });\n this.addEventListener('touchmove', event => {\n if (!this[multiTouchSymbol] && event.touches.length === 1) {\n const clientX = event.changedTouches[0].clientX;\n const clientY = event.changedTouches[0].clientY;\n const handled = touchMove(this, clientX, clientY);\n if (handled) {\n event.preventDefault();\n }\n }\n });\n this.addEventListener('touchend', event => {\n if (event.touches.length === 0) {\n // All touches removed; gesture is complete.\n if (!this[multiTouchSymbol]) {\n // Single-touch swipe has finished.\n const clientX = event.changedTouches[0].clientX;\n const clientY = event.changedTouches[0].clientY;\n touchEnd(this, clientX, clientY);\n }\n this[multiTouchSymbol] = false;\n }\n });\n }\n }\n\n connectedCallback() {\n if (super.connectedCallback) { super.connectedCallback(); }\n\n // For the component to receive PointerEvents in IE/Edge, we need to set\n // touch-action: none. Only make this change if touch-action is currently\n // the default value (\"auto\"), in case the developer knows better than we\n // do what they want in their particular context.\n if (getComputedStyle(this).touchAction === 'auto') {\n this.style.touchAction = 'none';\n }\n }\n\n // Default implementation.\n get [symbols.dragging]() {\n return super[symbols.dragging];\n }\n set [symbols.dragging](value) {\n if (symbols.dragging in base.prototype) { super[symbols.dragging] = value; }\n }\n\n /**\n * Invoked when the user wants to go/navigate left.\n * The default implementation of this method does nothing.\n */\n [symbols.goLeft]() {\n if (super[symbols.goLeft]) { return super[symbols.goLeft](); }\n }\n\n /**\n * Invoked when the user wants to go/navigate right.\n * The default implementation of this method does nothing.\n */\n [symbols.goRight]() {\n if (super[symbols.goRight]) { return super[symbols.goRight](); }\n }\n\n /**\n * The distance the first touchpoint has traveled since the beginning of a\n * drag, expressed as a fraction of the element's width.\n *\n * @type number\n */\n get travelFraction() {\n return this[travelFractionSymbol];\n }\n set travelFraction(value) {\n this[travelFractionSymbol] = value;\n if ('travelFraction' in base.prototype) { super.travelFraction = value; }\n }\n\n }\n\n return SwipeDirection;\n};\n\n\n// Return true if the pointer event is for the pen, or the primary touch point.\nfunction isEventForPenOrPrimaryTouch(event) {\n return event.pointerType === 'pen' ||\n (event.pointerType === 'touch' && event.isPrimary);\n}\n\n/*\n * Invoked when the user has finished a touch operation.\n */\nfunction touchEnd(element, clientX, clientY) {\n element[symbols.dragging] = false;\n if (element[deltaXSymbol] >= 20) {\n // Finished going right at high speed.\n element[symbols.goLeft]();\n } else if (element[deltaXSymbol] <= -20) {\n // Finished going left at high speed.\n element[symbols.goRight]();\n } else {\n // Finished at low speed.\n trackTo(element, clientX);\n const travelFraction = element.travelFraction;\n if (travelFraction >= 0.5) {\n element[symbols.goRight]();\n } else if (travelFraction <= -0.5) {\n element[symbols.goLeft]();\n }\n }\n element.travelFraction = 0;\n element[deltaXSymbol] = null;\n element[deltaYSymbol] = null;\n}\n\n/*\n * Invoked when the user has moved during a touch operation.\n */\nfunction touchMove(element, clientX, clientY) {\n\n element[deltaXSymbol] = clientX - element[previousXSymbol];\n element[deltaYSymbol] = clientY - element[previousYSymbol];\n element[previousXSymbol] = clientX;\n element[previousYSymbol] = clientY;\n if (Math.abs(element[deltaXSymbol]) > Math.abs(element[deltaYSymbol])) {\n // Move was mostly horizontal.\n trackTo(element, clientX);\n // Indicate that the event was handled. It'd be nicer if we didn't have\n // to do this so that, e.g., a user could be swiping left and right\n // while simultaneously scrolling up and down. (Native touch apps can do\n // that.) However, Mobile Safari wants to handle swipe events near the\n // page and interpret them as navigations. To avoid having a horiziontal\n // swipe misintepreted as a navigation, we indicate that we've handled\n // the event, and prevent default behavior.\n return true;\n } else {\n // Move was mostly vertical.\n return false; // Not handled\n }\n}\n\n/*\n * Invoked when the user has begun a touch operation.\n */\nfunction touchStart(element, clientX, clientY) {\n element[symbols.dragging] = true;\n element[startXSymbol] = clientX;\n element[previousXSymbol] = clientX;\n element[previousYSymbol] = clientY;\n element[deltaXSymbol] = 0;\n element[deltaYSymbol] = 0;\n}\n\nfunction trackTo(element, x) {\n const width = element.offsetWidth;\n const dragDistance = element[startXSymbol] - x;\n const fraction = width > 0 ?\n dragDistance / width :\n 0;\n element.travelFraction = fraction;\n}\n","import createSymbol from './createSymbol';\nimport symbols from './symbols';\n\n\nconst playingSymbol = createSymbol('playing');\nconst selectionTimerDurationSymbol = createSymbol('selectionTimerDuration');\nconst timerTimeoutSymbol = createSymbol('timerTimeout');\n\n\n/* Exported function extends a base class with TimerSelection. */\nexport default (base) => {\n\n /**\n * Mixin which provides for automatic timed changes in selection.\n *\n * This mixin is useful for creating slideshow-like elements such as\n * [basic-slideshow](../../basic-slideshow) and\n * [basic-slideshow-with-controls](../../basic-slideshow-with-controls).\n *\n * Typical usage:\n *\n * class CarouselWithTimer extends TimerSelectionMixin(Carousel) {}\n * customElements.define('carousel-with-arrows', CarouselWithTimer);\n *\n * This mixin expects the component to define an `items` property, as well as\n * `selectFirst` and `selectNext` methods. You can implement those yourself,\n * or use [ContentItemsMixin](ContentItemsMixin.md) and\n * [SingleSelectionMixin](SingleSelectionMixin.md).\n */\n class TimerSelection extends base {\n\n constructor() {\n super();\n // Set defaults.\n if (typeof this.playing === 'undefined') {\n this.playing = this[symbols.defaults].playing;\n }\n if (typeof this.selectionTimerDuration === 'undefined') {\n this.selectionTimerDuration = this[symbols.defaults].selectionTimerDuration;\n }\n }\n\n contentChanged() {\n if (super.contentChanged) { super.contentChanged(); }\n restartTimer(this);\n }\n\n get [symbols.defaults]() {\n const defaults = super[symbols.defaults] || {};\n defaults.playing = false;\n defaults.selectionTimerDuration = 1000;\n return defaults;\n }\n\n /**\n * Begin automatic progression of the selection.\n */\n play() {\n if (super.play) { super.play(); }\n startTimer(this);\n this[playingSymbol] = true;\n }\n\n /**\n * Pause automatic progression of the selection.\n */\n pause() {\n if (super.pause) { super.pause(); }\n clearTimer(this);\n this[playingSymbol] = false;\n }\n\n /**\n * True if the selection is being automatically advanced.\n *\n * @type {boolean}\n * @default false\n */\n get playing() {\n return this[playingSymbol];\n }\n set playing(playing) {\n const previousPlaying = this[playingSymbol];\n const parsed = String(playing) === 'true'; // Cast to boolean\n if ('playing' in base.prototype) { super.playing = playing; }\n if (parsed !== previousPlaying) {\n if (playing) {\n this.play();\n } else {\n this.pause();\n }\n }\n }\n\n /*\n * When the selected item changes (because of something this mixin did, or\n * was changed by an outside agent like the user), we wait before advancing\n * to the next item. By triggering the next item this way, we implicitly get\n * a desirable behavior: if the user changes the selection (e.g., in a\n * carousel), we let them see that selection state for a while before\n * advancing the selection ourselves.\n */\n get selectedItem() {\n return super.selectedItem;\n }\n set selectedItem(item) {\n if ('selectedItem' in base.prototype) { super.selectedItem = item; }\n restartTimer(this);\n }\n\n /**\n * The time in milliseconds that will elapse after the selection changes\n * before the selection will be advanced to the next item in the list.\n *\n * @type {number} - Time in milliseconds\n * @default 1000 (1 second)\n */\n get selectionTimerDuration() {\n return this[selectionTimerDurationSymbol];\n }\n set selectionTimerDuration(value) {\n this[selectionTimerDurationSymbol] = parseInt(value);\n if ('selectionTimerDuration' in base.prototype) { super.selectionTimerDuration = value; }\n }\n\n }\n\n return TimerSelection;\n};\n\n\nfunction clearTimer(element) {\n if (element[timerTimeoutSymbol]) {\n clearTimeout(element[timerTimeoutSymbol]);\n element[timerTimeoutSymbol] = null;\n }\n}\n\nfunction restartTimer(element) {\n clearTimer(element);\n if (element.playing && element.items && element.items.length > 0) {\n startTimer(element);\n }\n}\n\nfunction startTimer(element) {\n // If play() is called more than once, cancel any existing timer.\n clearTimer(element);\n element[timerTimeoutSymbol] = setTimeout(() => {\n selectNextWithWrap(element);\n }, element.selectionTimerDuration);\n}\n\n// Select the next item, wrapping to first item if necessary.\nfunction selectNextWithWrap(element) {\n const items = element.items;\n if (items && items.length > 0) {\n if (element.selectedIndex == null || element.selectedIndex === items.length - 1) {\n element.selectFirst();\n } else {\n element.selectNext();\n }\n }\n}\n","import createSymbol from '../../basic-component-mixins/src/createSymbol';\nimport symbols from './symbols';\n\n\n// Symbols for private data members on an element.\nconst absorbDecelerationSymbol = createSymbol('absorbDeceleration');\nconst lastDeltaXSymbol = createSymbol('lastDeltaX');\nconst lastWheelTimeoutSymbol = createSymbol('lastWheelTimeout');\nconst postNavigateDelayCompleteSymbol = createSymbol('postNavigateDelayComplete');\nconst wheelDistanceSymbol = createSymbol('wheelDistance');\n\n\n/* Exported function extends a base class with TrackpadDirection. */\nexport default (base) => {\n\n /**\n * Mixin which maps a horizontal trackpad swipe gestures (or horizontal mouse\n * wheel actions) to direction semantics.\n *\n * You can use this mixin with a mixin like\n * [DirectionSelectionMixin](DirectionSelectionMixin.md) to let the user\n * change the selection with the trackpad or mouse wheel.\n *\n * To respond to the trackpad, we can listen to the DOM's \"wheel\" events.\n * These events are fired as the user drags their fingers across a trackpad.\n * Unfortunately, browsers are missing a critical event — there is no event\n * when the user *stops* a gestured on the trackpad or mouse wheel.\n *\n * To make things worse, the mainstream browsers continue to generate fake\n * wheel events even after the user has stopped dragging their fingers. These\n * fake events simulate the user gradually slowing down the drag until they\n * come to a smooth stop. In some contexts, these fake wheel events might be\n * helpful, but in trying to supply typical trackpad swipe navigation, these\n * fake events get in the way.\n *\n * This component uses heuristics to work around these problems, but the\n * complex nature of the problem make it extremely difficult to achieve the\n * same degree of trackpad responsiveness possible with native applications.\n */\n class TrackpadDirection extends base {\n\n constructor() {\n super();\n this.addEventListener('wheel', event => {\n const handled = wheel(this, event);\n if (handled) {\n event.preventDefault();\n }\n });\n resetWheelTracking(this);\n }\n\n // Default implementation.\n get [symbols.dragging]() {\n return super[symbols.dragging];\n }\n set [symbols.dragging](value) {\n if (symbols.dragging in base.prototype) { super[symbols.dragging] = value; }\n }\n\n /**\n * Invoked when the user wants to go/navigate left.\n * The default implementation of this method does nothing.\n */\n [symbols.goLeft]() {\n if (super[symbols.goLeft]) { return super[symbols.goLeft](); }\n }\n\n /**\n * Invoked when the user wants to go/navigate right.\n * The default implementation of this method does nothing.\n */\n [symbols.goRight]() {\n if (super[symbols.goRight]) { return super[symbols.goRight](); }\n }\n\n /**\n * The distance the user has moved the first touchpoint since the beginning\n * of a trackpad/wheel operation, expressed as a fraction of the element's\n * width.\n *\n * @type number\n */\n get travelFraction() {\n return super.travelFraction;\n }\n set travelFraction(value) {\n if ('travelFraction' in base.prototype) { super.travelFraction = value; }\n }\n\n }\n\n return TrackpadDirection;\n};\n\n\n// Time we wait following a navigation before paying attention to wheel\n// events again.\nconst POST_NAVIGATE_TIME = 250;\n\n// Time we wait after the last wheel event before we reset things.\nconst WHEEL_TIME = 100;\n\n\n// Following a navigation, partially reset our wheel tracking.\nfunction postNavigate(element) {\n element.travelFraction = 0;\n element[wheelDistanceSymbol] = 0;\n element[postNavigateDelayCompleteSymbol] = true;\n element[absorbDecelerationSymbol] = true;\n setTimeout(() => {\n element[postNavigateDelayCompleteSymbol] = false;\n }, POST_NAVIGATE_TIME);\n}\n\n// Reset all state related to the tracking of the wheel.\nfunction resetWheelTracking(element) {\n element.travelFraction = 0;\n element[wheelDistanceSymbol] = 0;\n element[lastDeltaXSymbol] = 0;\n element[absorbDecelerationSymbol] = false;\n element[postNavigateDelayCompleteSymbol] = false;\n if (element[lastWheelTimeoutSymbol]) {\n clearTimeout(element[lastWheelTimeoutSymbol]);\n element[lastWheelTimeoutSymbol] = null;\n }\n}\n\n// Define our own sign function, since (as of May 2015), Safari and IE don't\n// supply Math.sign().\nfunction sign(x) {\n return (x === 0) ?\n 0 :\n (x > 0) ?\n 1 :\n -1;\n}\n\n// TODO: Damping, or some other treatment for going past the ends.\n\n/*\n * A wheel event has been generated. This could be a real wheel event, or it\n * could be fake (see notes in the header).\n *\n * This handler uses several strategies to try to approximate native trackpad\n * swipe navigation.\n *\n * If the user has dragged enough to cause a navigation, then for a short\n * delay following that navigation, subsequent wheel events will be ignored.\n *\n * Furthermore, follwowing a navigation, we ignore all wheel events until we\n * receive at least one event where the event's deltaX (distance traveled) is\n * *greater* than the previous event's deltaX. This helps us filter out the\n * fake wheel events generated by the browser to simulate deceleration.\n *\n */\nfunction wheel(element, event) {\n\n // Since we have a new wheel event, reset our timer waiting for the last\n // wheel event to pass.\n if (element[lastWheelTimeoutSymbol]) {\n clearTimeout(element[lastWheelTimeoutSymbol]);\n }\n element[lastWheelTimeoutSymbol] = setTimeout(() => {\n wheelTimedOut(element);\n }, WHEEL_TIME);\n\n const deltaX = event.deltaX;\n const deltaY = event.deltaY;\n\n // See if element event represents acceleration or deceleration.\n const acceleration = sign(deltaX) * (deltaX - element[lastDeltaXSymbol]);\n element[lastDeltaXSymbol] = deltaX;\n\n if (Math.abs(deltaX) < Math.abs(deltaY)) {\n // Move was mostly vertical. The user may be trying scroll with the\n // trackpad/wheel. To be on the safe, we ignore such events.\n return false;\n }\n\n if (element[postNavigateDelayCompleteSymbol]) {\n // It's too soon after a navigation; ignore the event.\n return true;\n }\n\n if (acceleration > 0) {\n // The events are not (or are no longer) decelerating, so we can start\n // paying attention to them again.\n element[absorbDecelerationSymbol] = false;\n } else if (element[absorbDecelerationSymbol]) {\n // The wheel event was likely faked to simulate deceleration; ignore it.\n return true;\n }\n\n element[wheelDistanceSymbol] += deltaX;\n\n // Update the travel fraction of the element being navigated.\n const width = element.offsetWidth;\n let travelFraction = width > 0 ?\n element[wheelDistanceSymbol] / width :\n 0;\n element[symbols.dragging] = true;\n travelFraction = sign(travelFraction) * Math.min(Math.abs(travelFraction), 1);\n element.travelFraction = travelFraction;\n\n // If the user has dragged enough to reach the previous/next item, then\n // complete a navigation to that item.\n if (travelFraction === 1) {\n element[symbols.dragging] = false;\n element[symbols.goRight]();\n postNavigate(element);\n } else if (travelFraction === -1) {\n element[symbols.dragging] = false;\n element[symbols.goLeft]();\n postNavigate(element);\n }\n\n return true;\n}\n\n// A sufficiently long period of time has passed since the last wheel event.\n// We snap the selection to the closest item, then reset our state.\nfunction wheelTimedOut(element) {\n\n // Snap to the closest item.\n element[symbols.dragging] = false;\n const travelFraction = element.travelFraction;\n if (travelFraction >= 0.5) {\n element[symbols.goRight]();\n } else if (travelFraction <= -0.5) {\n element[symbols.goLeft]();\n }\n\n // TODO: Listen for the transition to complete, and then restore\n // dragging to false (or the previous value).\n\n resetWheelTracking(element);\n}\n","/**\n * Helper function to create a symbol that can be used for associating private\n * data with an element.\n *\n * Mixins and component classes often want to associate private data with an\n * element instance, but JavaScript does not have direct support for true\n * private properties. One approach is to use the\n * [Symbol](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Symbol)\n * data type to set and retrieve data on an element.\n *\n * Unfortunately, the Symbol type is not available in Internet Explorer 11. The\n * `createSymbol` helper function exists as a workaround for IE 11. Rather than\n * returning a true Symbol, it simply returns an underscore-prefixed string.\n *\n * Usage:\n *\n * const fooSymbol = createSymbol('foo');\n *\n * class MyElement extends HTMLElement {\n * get foo() {\n * return this[fooSymbol];\n * }\n * set foo(value) {\n * this[fooSymbol] = value;\n * }\n * }\n *\n * In IE 11, this sample will \"hide\" data behind an instance property this._foo.\n * The use of the underscore is meant to reduce (not eliminate) the potential\n * for name conflicts, and discourage (not prevent) external access to this\n * data. In modern browsers, the above code will eliminate the potential of\n * naming conflicts, and better hide the data behind a real Symbol.\n *\n * @function createSymbol\n * @param {string} description - A string to identify the symbol when debugging\n */\nexport default function createSymbol(description) {\n return typeof Symbol === 'function' ?\n Symbol(description) :\n `_${description}`;\n}\n","/*\n * Microtask helper for IE 11.\n *\n * Executing a function as a microtask is trivial in browsers that support\n * promises, whose then() clauses use microtask timing. IE 11 doesn't support\n * promises, but does support MutationObservers, which are also executed as\n * microtasks. So this helper uses an MutationObserver to achieve microtask\n * timing.\n *\n * See https://jakearchibald.com/2015/tasks-microtasks-queues-and-schedules/\n *\n * Inspired by Polymer's async() function.\n */\n\n\n// The queue of pending callbacks to be executed as microtasks.\nconst callbacks = [];\n\n// Create an element that we will modify to force observable mutations.\nconst element = document.createTextNode('');\n\n// A monotonically-increasing value.\nlet counter = 0;\n\n\n/**\n * Add a callback to the microtask queue.\n *\n * This uses a MutationObserver so that it works on IE 11.\n *\n * NOTE: IE 11 may actually use timeout timing with MutationObservers. This\n * needs more investigation.\n *\n * @function microtask\n * @param {function} callback\n */\nexport default function microtask(callback) {\n callbacks.push(callback);\n // Force a mutation.\n element.textContent = ++counter;\n}\n\n\n// Execute any pending callbacks.\nfunction executeCallbacks() {\n while (callbacks.length > 0) {\n const callback = callbacks.shift();\n callback();\n }\n}\n\n\n// Create the observer.\nconst observer = new MutationObserver(executeCallbacks);\nobserver.observe(element, {\n characterData: true\n});\n","/**\n * Helper function for rendering an array of items as elements.\n *\n * This is not a mixin, but a function components can use if they need to\n * generate a set of elements for the items in an array.\n *\n * This function will reuse existing elements if possible. E.g., if it is called\n * to render an array of 4 items, and later called to render an array of 5\n * items, it can reuse the existing 4 items, creating just one new element.\n * Note, however, that this re-rendering is not automatic. If, after calling\n * this function, you manipulate the array you used, you must still call this\n * function again to re-render the array.\n *\n * The `renderItem` parameter takes a function of two arguments: an item to\n * to render, and an existing element (if one exists) which can be repurposed to\n * render that item. If the latter argument is null, the `renderItem()` function\n * should create a new element and return it. The function should do the same\n * if the supplied existing element is not suitable for rendering the given\n * item; the returned element will be used to replace the existing one. If the\n * existing element *is* suitable, the function can simply update it and return\n * it as is.\n *\n * Example: The following will render an array of strings in divs as children\n * of the `container` element:\n *\n * let strings = ['a', 'b', 'c', ...];\n * let container = this.querySelector(...);\n * renderArrayAsElements(strings, container, (string, element) => {\n * if (!element) {\n * // No element exists yet, so create a new one.\n * element = document.createElement('div');\n * }\n * // Set/update the text content of the element.\n * element.textContent = string;\n * return element;\n * });\n *\n * @param {Array} items - the items to render\n * @param {HTMLElement} container - the parent that will hold the elements\n * @param {function} renderItem - returns a new element for an item, or\n * repurposes an existing element for an item\n */\nfunction renderArrayAsElements(items, container, renderItem) {\n // Create a new set of elements for the current items.\n items.forEach((item, index) => {\n const oldElement = container.childNodes[index];\n const newElement = renderItem(item, oldElement);\n if (newElement) {\n if (!oldElement) {\n container.appendChild(newElement);\n } else if (newElement !== oldElement) {\n container.replaceChild(newElement, oldElement);\n }\n }\n });\n\n // If the array shrank, remove the extra elements which are no longer needed.\n while (container.childNodes.length > items.length) {\n container.removeChild(container.childNodes[items.length]);\n }\n}\n\nexport default renderArrayAsElements;\n","import createSymbol from './createSymbol';\nimport toggleClass from './toggleClass';\n\n\n// Symbols for private data members on an element.\nconst safeToSetAttributesSymbol = createSymbol('safeToSetAttributes');\nconst pendingAttributesSymbol = createSymbol('pendingAttributes');\nconst pendingClassesSymbol = createSymbol('pendingClasses');\n\n\n/**\n * Helper functions for updating attributes, including the `class` attribute.\n */\nexport default {\n\n /**\n * Perform any pending updates to attributes and classes.\n *\n * This writes any `setAttribute` or `toggleClass` values that were performed\n * before an element was attached to the document for the first time.\n *\n * This method should be called by mixins/components in their\n * `connectedCallback`. If mulitple mixins/components invoke this during the\n * same `connectedCallback`, only the first call will have any effect. The\n * subsequent calls will be harmless.\n *\n * @param {HTMLElement} element - The element being added to the document.\n */\n connected(element) {\n element[safeToSetAttributesSymbol] = true;\n\n // Set any pending attributes.\n if (element[pendingAttributesSymbol]) {\n for (let attribute in element[pendingAttributesSymbol]) {\n const value = element[pendingAttributesSymbol][attribute];\n setAttributeToElement(element, attribute, value);\n }\n element[pendingAttributesSymbol] = null;\n }\n\n // Set any pending classes.\n if (element[pendingClassesSymbol]) {\n for (let className in element[pendingClassesSymbol]) {\n const value = element[pendingClassesSymbol][className];\n toggleClass(element, className, value);\n }\n element[pendingClassesSymbol] = null;\n }\n },\n\n /**\n * Set/unset the attribute with the indicated name.\n *\n * This method exists primarily to handle the case where an element wants to\n * set a default property value that should be reflected as an attribute. An\n * important limitation of custom element consturctors is that they cannot\n * set attributes. A call to `setAttribute` during the constructor will\n * be deferred until the element is connected to the document.\n *\n * @param {string} attribute - The name of the *attribute* (not property) to set.\n * @param {object} value - The value to set. If null, the attribute will be removed.\n */\n setAttribute(element, attribute, value) {\n if (element[safeToSetAttributesSymbol]) {\n // Safe to set attributes immediately.\n setAttributeToElement(element, attribute, value);\n } else {\n // Defer setting attributes until the first time we're connected.\n if (!element[pendingAttributesSymbol]) {\n element[pendingAttributesSymbol] = {};\n }\n element[pendingAttributesSymbol][attribute] = value;\n }\n },\n\n /**\n * Set/unset the class with the indicated name.\n *\n * This method exists primarily to handle the case where an element wants to\n * set a default property value that should be reflected as as class. An\n * important limitation of custom element consturctors is that they cannot\n * set attributes, including the `class` attribute. A call to\n * `toggleClass` during the constructor will be deferred until the element\n * is connected to the document.\n *\n * @param {string} className - The name of the class to set.\n * @param {object} value - True to set the class, false to remove it.\n */\n toggleClass(element, className, value) {\n if (element[safeToSetAttributesSymbol]) {\n // Safe to set class immediately.\n toggleClass(element, className, value);\n } else {\n // Defer setting class until the first time we're connected.\n if (!element[pendingClassesSymbol]) {\n element[pendingClassesSymbol] = {};\n }\n element[pendingClassesSymbol][className] = value;\n }\n }\n\n};\n\n\n// Reflect the attribute to the given element.\n// If the value is null, remove the attribute.\nfunction setAttributeToElement(element, attributeName, value) {\n if (value === null || typeof value === 'undefined') {\n element.removeAttribute(attributeName);\n } else {\n const text = String(value);\n // Avoid recursive attributeChangedCallback calls.\n if (element.getAttribute(attributeName) !== text) {\n element.setAttribute(attributeName, value);\n }\n }\n}\n","import createSymbol from './createSymbol';\n\n/**\n * A collection of Symbol objects for standard component properties and methods.\n *\n * These Symbol objects are used to allow mixins and a component to internally\n * communicate, without exposing these properties and methods in the component's\n * public API.\n *\n * To use these Symbol objects in your own component, include this module and\n * then create a property or method whose key is the desired Symbol.\n *\n * import 'SingleSelectionMixin' from 'basic-component-mixins/src/SingleSelectionMixin';\n * import 'symbols' from 'basic-component-mixins/src/symbols';\n *\n * class MyElement extends SingleSelectionMixin(HTMLElement) {\n * [symbols.itemSelected](item, selected) {\n * // This will be invoked whenever an item is selected/deselected.\n * }\n * }\n *\n * @module symbols\n */\nconst symbols = {\n\n /**\n * Symbol for the `defaults` property.\n *\n * This property can be used to set or override defaults that will be applied\n * to a new component instance. When implementing this property, take care to\n * first acquire any defaults defined by the superclass. The standard idiom is\n * as follows:\n *\n * get [symbols.defaults]() {\n * const defaults = super[symbols.defaults] || {};\n * // Set or override default values here\n * defaults.customProperty = false;\n * return defaults;\n * }\n *\n * @var {object} defaults\n */\n defaults: createSymbol('defaults'),\n\n /**\n * Symbol for the `dragging` property.\n *\n * Components like carousels often define animated CSS transitions for\n * sliding effects. Such a transition should usually *not* be applied while\n * the user is dragging, because a CSS animation will introduce a lag that\n * makes the swipe feel sluggish. Instead, as long as the user is dragging\n * with their finger down, the transition should be suppressed. When the\n * user releases their finger, the transition can be restored, allowing the\n * animation to show the carousel sliding into its final position.\n *\n * @type {boolean} true if a drag is in progress, false if not.\n */\n dragging: createSymbol('dragging'),\n\n /**\n * Symbol for the `goDown` method.\n *\n * This method is invoked when the user wants to go/navigate down.\n *\n * @function goDown\n */\n goDown: createSymbol('goDown'),\n\n /**\n * Symbol for the `goEnd` method.\n *\n * This method is invoked when the user wants to go/navigate to the end (e.g.,\n * of a list).\n *\n * @function goEnd\n */\n goEnd: createSymbol('goEnd'),\n\n /**\n * Symbol for the `goLeft` method.\n *\n * This method is invoked when the user wants to go/navigate left.\n *\n * @function goLeft\n */\n goLeft: createSymbol('goLeft'),\n\n /**\n * Symbol for the `goRight` method.\n *\n * This method is invoked when the user wants to go/navigate right.\n *\n * @function goRight\n */\n goRight: createSymbol('goRight'),\n\n /**\n * Symbol for the `goStart` method.\n *\n * This method is invoked when the user wants to go/navigate to the start\n * (e.g., of a list).\n *\n * @function goStart\n */\n goStart: createSymbol('goStart'),\n\n /**\n * Symbol for the `goUp` method.\n *\n * This method is invoked when the user wants to go/navigate up.\n *\n * @function goUp\n */\n goUp: createSymbol('goUp'),\n\n /**\n * Symbol for the `itemAdded` method.\n *\n * This method is invoked when a new item is added to a list.\n *\n * @function itemAdded\n * @param {HTMLElement} item - the item being selected/deselected\n */\n itemAdded: createSymbol('itemAdded'),\n\n\n /**\n * Symbol for the `itemsChanged` method.\n *\n * This method is invoked when the underlying contents change. It is also\n * invoked on component initialization – since the items have \"changed\" from\n * being nothing.\n */\n itemsChanged: createSymbol('itemsChanged'),\n\n /**\n * Symbol for the `itemSelected` method.\n *\n * This method is invoked when an item becomes selected or deselected.\n *\n * @function itemSelected\n * @param {HTMLElement} item - the item being selected/deselected\n * @param {boolean} selected - true if the item is selected, false if not\n */\n itemSelected: createSymbol('itemSelected'),\n\n /**\n * Symbol for the `keydown` method.\n *\n * This method is invoked when an element receives a `keydown` event.\n *\n * @function keydown\n * @param {KeyboardEvent} event - the event being processed\n */\n keydown: createSymbol('keydown'),\n\n /**\n * Symbol for the `template` property.\n *\n * This property returns a component's template.\n *\n * @type {string|HTMLElement}\n */\n template: createSymbol('template')\n};\n\nexport default symbols;\n","/**\n * Helper function for standard classList.toggle() behavior on old browsers,\n * namely IE 11.\n *\n * The standard\n * [classlist](https://developer.mozilla.org/en-US/docs/Web/API/Element/classList)\n * object has a `toggle()` function that supports a second Boolean parameter\n * that can be used to succinctly turn a class on or off. This feature is often\n * useful in designing custom elements, which may want to externally reflect\n * component state in a CSS class that can be used for styling purposes.\n *\n * Unfortunately, IE 11 does not support the Boolean parameter to\n * `classList.toggle()`. This helper function behaves like the standard\n * `toggle()`, including support for the Boolean parameter, so that it can be\n * used even on IE 11.\n *\n * @function toggleClass\n * @param {HTMLElement} element - The element to modify\n * @param {string} className - The class to add/remove\n * @param {boolean} [force] - Force the class to be added (if true) or removed\n * (if false)\n */\nexport default function toggleClass(element, className, force) {\n const classList = element.classList;\n const addClass = (typeof force === 'undefined') ?\n !classList.contains(className) :\n force;\n if (addClass) {\n classList.add(className);\n } else {\n classList.remove(className);\n }\n return addClass;\n}\n"]}
\ No newline at end of file
diff --git a/packages/basic-component-mixins/docs/HorizontalNavigationMixin.md b/packages/basic-component-mixins/docs/HorizontalNavigationMixin.md
new file mode 100644
index 00000000..54cb2702
--- /dev/null
+++ b/packages/basic-component-mixins/docs/HorizontalNavigationMixin.md
@@ -0,0 +1,138 @@
+# API Documentation
+
+
+## HorizontalNavigation
+ **Kind**: global class
+**Mixes**: [KeyboardMixin](../basic-component-mixins/docs/KeyboardMixin.md)
+ , [KeyboardDirectionMixin](../basic-component-mixins/docs/KeyboardDirectionMixin.md)
+ , [SwipeDirectionMixin](../basic-component-mixins/docs/SwipeDirectionMixin.md)
+ , [TrackpadDirectionMixin](../basic-component-mixins/docs/TrackpadDirectionMixin.md)
+
+
+* [HorizontalNavigation](#HorizontalNavigation)
+ * [.goDown()](#KeyboardDirection+symbols.goDown)
+ * [.goEnd()](#KeyboardDirection+symbols.goEnd)
+ * [.goLeft()](#TrackpadDirection+symbols.goLeft)
+ * [.goLeft()](#KeyboardDirection+symbols.goLeft)
+ * [.goLeft()](#SwipeDirection+symbols.goLeft)
+ * [.goRight()](#KeyboardDirection+symbols.goRight)
+ * [.goRight()](#SwipeDirection+symbols.goRight)
+ * [.goRight()](#TrackpadDirection+symbols.goRight)
+ * [.goStart()](#KeyboardDirection+symbols.goStart)
+ * [.goUp()](#KeyboardDirection+symbols.goUp)
+ * [.keydown(event)](#Keyboard+symbols.keydown) ⇒ boolean
+ * [.navigationAxis](#KeyboardDirection+navigationAxis) : string
+ * [.travelFraction](#SwipeDirection+travelFraction) : number
+ * [.travelFraction](#TrackpadDirection+travelFraction) : number
+
+
+
+### HorizontalNavigation.goDown()
+Invoked when the user wants to go/navigate down.
+The default implementation of this method does nothing.
+
+ **Kind**: static method of [HorizontalNavigation](#HorizontalNavigation). Defined by [KeyboardDirection#symbols](../basic-component-mixins/docs/KeyboardDirection#symbols.md) mixin.
+
+
+### HorizontalNavigation.goEnd()
+Invoked when the user wants to go/navigate to the end (e.g., of a list).
+The default implementation of this method does nothing.
+
+ **Kind**: static method of [HorizontalNavigation](#HorizontalNavigation). Defined by [KeyboardDirection#symbols](../basic-component-mixins/docs/KeyboardDirection#symbols.md) mixin.
+
+
+### HorizontalNavigation.goLeft()
+Invoked when the user wants to go/navigate left.
+The default implementation of this method does nothing.
+
+ **Kind**: static method of [HorizontalNavigation](#HorizontalNavigation). Defined by [TrackpadDirection#symbols](../basic-component-mixins/docs/TrackpadDirection#symbols.md) mixin.
+
+
+### HorizontalNavigation.goLeft()
+Invoked when the user wants to go/navigate left.
+The default implementation of this method does nothing.
+
+ **Kind**: static method of [HorizontalNavigation](#HorizontalNavigation). Defined by [KeyboardDirection#symbols](../basic-component-mixins/docs/KeyboardDirection#symbols.md) mixin.
+
+
+### HorizontalNavigation.goLeft()
+Invoked when the user wants to go/navigate left.
+The default implementation of this method does nothing.
+
+ **Kind**: static method of [HorizontalNavigation](#HorizontalNavigation). Defined by [SwipeDirection#symbols](../basic-component-mixins/docs/SwipeDirection#symbols.md) mixin.
+
+
+### HorizontalNavigation.goRight()
+Invoked when the user wants to go/navigate right.
+The default implementation of this method does nothing.
+
+ **Kind**: static method of [HorizontalNavigation](#HorizontalNavigation). Defined by [KeyboardDirection#symbols](../basic-component-mixins/docs/KeyboardDirection#symbols.md) mixin.
+
+
+### HorizontalNavigation.goRight()
+Invoked when the user wants to go/navigate right.
+The default implementation of this method does nothing.
+
+ **Kind**: static method of [HorizontalNavigation](#HorizontalNavigation). Defined by [SwipeDirection#symbols](../basic-component-mixins/docs/SwipeDirection#symbols.md) mixin.
+
+
+### HorizontalNavigation.goRight()
+Invoked when the user wants to go/navigate right.
+The default implementation of this method does nothing.
+
+ **Kind**: static method of [HorizontalNavigation](#HorizontalNavigation). Defined by [TrackpadDirection#symbols](../basic-component-mixins/docs/TrackpadDirection#symbols.md) mixin.
+
+
+### HorizontalNavigation.goStart()
+Invoked when the user wants to go/navigate to the start (e.g., of a
+list). The default implementation of this method does nothing.
+
+ **Kind**: static method of [HorizontalNavigation](#HorizontalNavigation). Defined by [KeyboardDirection#symbols](../basic-component-mixins/docs/KeyboardDirection#symbols.md) mixin.
+
+
+### HorizontalNavigation.goUp()
+Invoked when the user wants to go/navigate up.
+The default implementation of this method does nothing.
+
+ **Kind**: static method of [HorizontalNavigation](#HorizontalNavigation). Defined by [KeyboardDirection#symbols](../basic-component-mixins/docs/KeyboardDirection#symbols.md) mixin.
+
+
+### HorizontalNavigation.keydown(event) ⇒ boolean
+Handle the indicated keyboard event.
+
+The default implementation of this method does nothing. This will
+typically be handled by other mixins.
+
+ **Kind**: static method of [HorizontalNavigation](#HorizontalNavigation). Defined by [Keyboard#symbols](../basic-component-mixins/docs/Keyboard#symbols.md) mixin.
+**Returns**: boolean - true if the event was handled
+
+| Param | Type | Description |
+| --- | --- | --- |
+| event | KeyboardEvent | the keyboard event |
+
+
+
+### horizontalNavigation.navigationAxis : string
+Indicates the direction of permitted navigation with the keyboard.
+
+Accepted values are "horizontal", "vertical", or "both" (the default).
+If this property is "horizontal", the Up Arrow and Down Arrow keys will
+be ignored. Conversely, if this is "vertical", the Left Arrow and Right
+Arrow keys will be ignored.
+
+ **Kind**: instance property of [HorizontalNavigation](#HorizontalNavigation). Defined by [KeyboardDirection](../basic-component-mixins/docs/KeyboardDirection.md) mixin.
+
+
+### horizontalNavigation.travelFraction : number
+The distance the first touchpoint has traveled since the beginning of a
+drag, expressed as a fraction of the element's width.
+
+ **Kind**: instance property of [HorizontalNavigation](#HorizontalNavigation). Defined by [SwipeDirection](../basic-component-mixins/docs/SwipeDirection.md) mixin.
+
+
+### horizontalNavigation.travelFraction : number
+The distance the user has moved the first touchpoint since the beginning
+of a trackpad/wheel operation, expressed as a fraction of the element's
+width.
+
+ **Kind**: instance property of [HorizontalNavigation](#HorizontalNavigation). Defined by [TrackpadDirection](../basic-component-mixins/docs/TrackpadDirection.md) mixin.
diff --git a/packages/basic-component-mixins/docs/TimerSelectionMixin.md b/packages/basic-component-mixins/docs/TimerSelectionMixin.md
index 2bf062a3..0458b29a 100644
--- a/packages/basic-component-mixins/docs/TimerSelectionMixin.md
+++ b/packages/basic-component-mixins/docs/TimerSelectionMixin.md
@@ -5,8 +5,8 @@
Mixin which provides for automatic timed changes in selection.
This mixin is useful for creating slideshow-like elements such as
-[basic-slideshow](../packages/basic-slideshow) and
-[basic-slideshow-with-controls](../packages/basic-slideshow-with-controls).
+[basic-slideshow](../../basic-slideshow) and
+[basic-slideshow-with-controls](../../basic-slideshow-with-controls).
Typical usage:
diff --git a/packages/basic-component-mixins/src/HorizontalNavigationMixin.js b/packages/basic-component-mixins/src/HorizontalNavigationMixin.js
new file mode 100644
index 00000000..c8ff14aa
--- /dev/null
+++ b/packages/basic-component-mixins/src/HorizontalNavigationMixin.js
@@ -0,0 +1,42 @@
+import DirectionSelectionMixin from '../../basic-component-mixins/src/DirectionSelectionMixin';
+import KeyboardDirectionMixin from '../../basic-component-mixins/src/KeyboardDirectionMixin';
+import KeyboardMixin from '../../basic-component-mixins/src/KeyboardMixin';
+import SwipeDirectionMixin from '../../basic-component-mixins/src/SwipeDirectionMixin';
+import symbols from '../../basic-component-mixins/src/symbols';
+import TrackpadDirectionMixin from '../../basic-component-mixins/src/TrackpadDirectionMixin';
+
+
+export default (base) => {
+
+ const mixins = [
+ DirectionSelectionMixin,
+ KeyboardMixin,
+ KeyboardDirectionMixin,
+ SwipeDirectionMixin,
+ TrackpadDirectionMixin
+ ];
+
+ // Don't assume base class uses ComposableMixin. Do composition by hand.
+ const baseWithMixins = mixins.reduce((c, mixin) => mixin(c), base);
+
+ /**
+ * @mixes KeyboardMixin
+ * @mixes KeyboardDirectionMixin
+ * @mixes SwipeDirectionMixin
+ * @mixes TrackpadDirectionMixin
+ */
+ class HorizontalNavigation extends baseWithMixins {
+
+ get [symbols.defaults]() {
+ const defaults = super[symbols.defaults] || {};
+ defaults.navigationAxis = 'horizontal';
+ defaults.selectionAnimationEffect = 'slideWithGap';
+ // defaults.selectionRequired = true;
+ return defaults;
+ }
+
+ }
+
+ return HorizontalNavigation;
+
+};
diff --git a/packages/basic-current-anchor/README.md b/packages/basic-current-anchor/README.md
index 528a7b39..e9e631e6 100644
--- a/packages/basic-current-anchor/README.md
+++ b/packages/basic-current-anchor/README.md
@@ -1,7 +1,7 @@
# API Documentation
-## CurrentAnchor
+## CurrentAnchor ⇐ WrappedStandardElement
An anchor (link) that highlights itself when its destination matches the
current location.
@@ -22,8 +22,9 @@ want to explicitly specific link colors anyway, e.g., to reflect your
application's visual style and brand.
**Kind**: global class
+**Extends:** WrappedStandardElement
-* [CurrentAnchor](#CurrentAnchor)
+* [CurrentAnchor](#CurrentAnchor) ⇐ WrappedStandardElement
* [.areaLink](#CurrentAnchor+areaLink) : boolean
* [.current](#CurrentAnchor+current) : boolean
diff --git a/packages/basic-current-anchor/dist/basic-current-anchor.js b/packages/basic-current-anchor/dist/basic-current-anchor.js
index e308395c..143acbc5 100644
--- a/packages/basic-current-anchor/dist/basic-current-anchor.js
+++ b/packages/basic-current-anchor/dist/basic-current-anchor.js
@@ -1,1681 +1,2 @@
-(function e(t,n,r){function s(o,u){if(!n[o]){if(!t[o]){var a=typeof require=="function"&&require;if(!u&&a)return a(o,!0);if(i)return i(o,!0);var f=new Error("Cannot find module '"+o+"'");throw f.code="MODULE_NOT_FOUND",f}var l=n[o]={exports:{}};t[o][0].call(l.exports,function(e){var n=t[o][1][e];return s(n?n:e)},l,l.exports,e,t,n,r)}return n[o].exports}var i=typeof require=="function"&&require;for(var o=0;o
- *
- * Then, after the element has been upgraded, the `fooBar` setter will
- * automatically be invoked with the initial value "Hello".
- *
- * For the time being, this mixin only supports string-valued properties.
- * If you'd like to convert string attributes to other types (numbers,
- * booleans), you need to implement `attributeChangedCallback` yourself.
- */
- var AttributeMarshalling = function (_base) {
- _inherits(AttributeMarshalling, _base);
-
- function AttributeMarshalling() {
- _classCallCheck(this, AttributeMarshalling);
-
- return _possibleConstructorReturn(this, (AttributeMarshalling.__proto__ || Object.getPrototypeOf(AttributeMarshalling)).apply(this, arguments));
- }
-
- _createClass(AttributeMarshalling, [{
- key: 'attributeChangedCallback',
-
-
- /*
- * Handle a change to the attribute with the given name.
- */
- value: function attributeChangedCallback(attributeName, oldValue, newValue) {
- if (_get(AttributeMarshalling.prototype.__proto__ || Object.getPrototypeOf(AttributeMarshalling.prototype), 'attributeChangedCallback', this)) {
- _get(AttributeMarshalling.prototype.__proto__ || Object.getPrototypeOf(AttributeMarshalling.prototype), 'attributeChangedCallback', this).call(this);
- }
- var propertyName = attributeToPropertyName(attributeName);
- // If the attribute name corresponds to a property name, set the property.
- // Ignore standard HTMLElement properties handled by the DOM.
- if (propertyName in this && !(propertyName in HTMLElement.prototype)) {
- this[propertyName] = newValue;
- }
- }
- }, {
- key: 'connectedCallback',
- value: function connectedCallback() {
- if (_get(AttributeMarshalling.prototype.__proto__ || Object.getPrototypeOf(AttributeMarshalling.prototype), 'connectedCallback', this)) {
- _get(AttributeMarshalling.prototype.__proto__ || Object.getPrototypeOf(AttributeMarshalling.prototype), 'connectedCallback', this).call(this);
- }
- _safeAttributes2.default.connected(this);
- }
- }, {
- key: 'reflectAttribute',
-
-
- /**
- * Set/unset the attribute with the indicated name.
- *
- * This method exists primarily to handle the case where an element wants to
- * set a default property value that should be reflected as an attribute. An
- * important limitation of custom element consturctors is that they cannot
- * set attributes. A call to `reflectAttribute` during the constructor will
- * be deferred until the element is connected to the document.
- *
- * @param {string} attribute - The name of the *attribute* (not property) to set.
- * @param {object} value - The value to set. If null, the attribute will be removed.
- */
- value: function reflectAttribute(attribute, value) {
- return _safeAttributes2.default.setAttribute(this, attribute, value);
- }
-
- /**
- * Set/unset the class with the indicated name.
- *
- * This method exists primarily to handle the case where an element wants to
- * set a default property value that should be reflected as as class. An
- * important limitation of custom element consturctors is that they cannot
- * set attributes, including the `class` attribute. A call to
- * `reflectClass` during the constructor will be deferred until the element
- * is connected to the document.
- *
- * @param {string} className - The name of the class to set.
- * @param {object} value - True to set the class, false to remove it.
- */
-
- }, {
- key: 'reflectClass',
- value: function reflectClass(className, value) {
- return _safeAttributes2.default.toggleClass(this, className, value);
- }
- }], [{
- key: 'observedAttributes',
- get: function get() {
- return attributesForClass(this);
- }
- }]);
-
- return AttributeMarshalling;
- }(base);
-
- return AttributeMarshalling;
-};
-
-// Convert hyphenated foo-bar attribute name to camel case fooBar property name.
-
-
-function attributeToPropertyName(attributeName) {
- var propertyName = attributeToPropertyNames[attributeName];
- if (!propertyName) {
- // Convert and memoize.
- var hypenRegEx = /-([a-z])/g;
- propertyName = attributeName.replace(hypenRegEx, function (match) {
- return match[1].toUpperCase();
- });
- attributeToPropertyNames[attributeName] = propertyName;
- }
- return propertyName;
-}
-
-function attributesForClass(classFn) {
-
- // We treat the element base classes as if they have no attributes, since we
- // don't want to receive attributeChangedCallback for them.
- if (classFn === HTMLElement || classFn === Object) {
- return [];
- }
-
- // Get attributes for parent class.
- var baseClass = Object.getPrototypeOf(classFn.prototype).constructor;
- var baseAttributes = attributesForClass(baseClass);
-
- // Get attributes for this class.
- var propertyNames = Object.getOwnPropertyNames(classFn.prototype);
- var setterNames = propertyNames.filter(function (propertyName) {
- return typeof Object.getOwnPropertyDescriptor(classFn.prototype, propertyName).set === 'function';
- });
- var attributes = setterNames.map(function (setterName) {
- return propertyNameToAttribute(setterName);
- });
-
- // Merge.
- var diff = attributes.filter(function (attribute) {
- return baseAttributes.indexOf(attribute) < 0;
- });
- return baseAttributes.concat(diff);
-}
-
-// Convert a camel case fooBar property name to a hyphenated foo-bar attribute.
-function propertyNameToAttribute(propertyName) {
- var attribute = propertyNamesToAttributes[propertyName];
- if (!attribute) {
- // Convert and memoize.
- var uppercaseRegEx = /([A-Z])/g;
- attribute = propertyName.replace(uppercaseRegEx, '-$1').toLowerCase();
- }
- return attribute;
-}
-
-},{"./safeAttributes":7}],2:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-/* Exported function extends a base class with Composable. */
-exports.default = function (base) {
-
- /**
- * Mixin to make a class more easily composable with other mixins.
- *
- * This mixin contributes a `compose` method that applies a set of mixin
- * functions and returns the resulting new class. This sugar can make the
- * application of many mixins at once easier to read.
- */
- var Composable = function (_base) {
- _inherits(Composable, _base);
-
- function Composable() {
- _classCallCheck(this, Composable);
-
- return _possibleConstructorReturn(this, (Composable.__proto__ || Object.getPrototypeOf(Composable)).apply(this, arguments));
- }
-
- _createClass(Composable, null, [{
- key: 'compose',
-
-
- /**
- * Apply a set of mixin functions or mixin objects to the present class and
- * return the new class.
- *
- * Instead of writing:
- *
- * let MyClass = Mixin1(Mixin2(Mixin3(Mixin4(Mixin5(BaseClass)))));
- *
- * You can write:
- *
- * let MyClass = ComposableMixin(BaseClass).compose(
- * Mixin1,
- * Mixin2,
- * Mixin3,
- * Mixin4,
- * Mixin5
- * );
- *
- * This function can also take mixin objects. A mixin object is just a
- * shorthand for a mixin function that creates a new subclass with the given
- * members. The mixin object's members are *not* copied directly onto the
- * prototype of the base class, as with traditional mixins.
- *
- * In addition to providing syntactic sugar, this mixin can be used to
- * define a class in ES5, which lacks ES6's `class` keyword.
- *
- * @param {...mixins} mixins - A set of mixin functions or objects to apply.
- */
- value: function compose() {
- for (var _len = arguments.length, mixins = Array(_len), _key = 0; _key < _len; _key++) {
- mixins[_key] = arguments[_key];
- }
-
- // We create a new subclass for each mixin in turn. The result becomes
- // the base class extended by any subsequent mixins. It turns out that
- // we can use Array.reduce() to concisely express this, using the current
- // object as the seed for reduce().
- return mixins.reduce(composeClass, this);
- }
- }]);
-
- return Composable;
- }(base);
-
- return Composable;
-};
-
-// Properties defined by Object that we don't want to mixin.
-
-
-var NON_MIXABLE_OBJECT_PROPERTIES = ['constructor'];
-
-/*
- * Apply the mixin to the given base class to return a new class.
- * The mixin can either be a function that returns the modified class, or a
- * plain object whose members will be copied to the new class' prototype.
- */
-function composeClass(base, mixin) {
- if (typeof mixin === 'function') {
- // Mixin function
- return mixin(base);
- } else {
- // Mixin object
- var Subclass = function (_base2) {
- _inherits(Subclass, _base2);
-
- function Subclass() {
- _classCallCheck(this, Subclass);
-
- return _possibleConstructorReturn(this, (Subclass.__proto__ || Object.getPrototypeOf(Subclass)).apply(this, arguments));
- }
-
- return Subclass;
- }(base);
-
- copyOwnProperties(mixin, Subclass.prototype, NON_MIXABLE_OBJECT_PROPERTIES);
- return Subclass;
- }
-}
-
-/*
- * Copy the given properties/methods to the target.
- * Return the updated target.
- */
-function copyOwnProperties(source, target) {
- var ignorePropertyNames = arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : [];
-
- Object.getOwnPropertyNames(source).forEach(function (name) {
- if (ignorePropertyNames.indexOf(name) < 0) {
- var descriptor = Object.getOwnPropertyDescriptor(source, name);
- Object.defineProperty(target, name, descriptor);
- }
- });
- return target;
-}
-
-},{}],3:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
-
-function _toConsumableArray(arr) { if (Array.isArray(arr)) { for (var i = 0, arr2 = Array(arr.length); i < arr.length; i++) { arr2[i] = arr[i]; } return arr2; } else { return Array.from(arr); } }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-/* Exported function extends a base class with DistributedChildren. */
-exports.default = function (base) {
-
- /**
- * Mixin which defines helpers for accessing a component's distributed
- * children as a flattened array or string.
- *
- * The standard DOM API provides several ways of accessing child content:
- * `children`, `childNodes`, and `textContent`. None of these functions are
- * Shadow DOM aware. This mixin defines variations of those functions that
- * *are* Shadow DOM aware.
- *
- * Example: you create a component `` that displays a number
- * equal to the number of children placed inside that component. If someone
- * instantiates your component like:
- *
- *
- *
- *
- *
- *
- *
- * Then the component should show "3", because there are three children. To
- * calculate the number of children, the component can just calculate
- * `this.children.length`. However, suppose someone instantiates your
- * component inside one of their own components, and puts a `` element
- * inside your component:
- *
- *
- *
- *
- *
- * If your component only looks at `this.children`, it will always see exactly
- * one child — the `` element. But the user looking at the page will
- * *see* any nodes distributed to that slot. To match what the user sees, your
- * component should expand any `` elements it contains.
- *
- * That is the problem this mixin solves. After applying this mixin, your
- * component code has access to `this.distributedChildren`, whose `length`
- * will return the total number of all children distributed to your component
- * in the composed tree.
- *
- * Note: The latest Custom Elements API design calls for a new function,
- * `getAssignedNodes` that takes an optional `deep` parameter, that will solve
- * this problem at the API level.
- */
- var DistributedChildren = function (_base) {
- _inherits(DistributedChildren, _base);
-
- function DistributedChildren() {
- _classCallCheck(this, DistributedChildren);
-
- return _possibleConstructorReturn(this, (DistributedChildren.__proto__ || Object.getPrototypeOf(DistributedChildren)).apply(this, arguments));
- }
-
- _createClass(DistributedChildren, [{
- key: 'distributedChildren',
-
-
- /**
- * An in-order collection of distributed children, expanding any slot
- * elements. Like the standard children property, this skips text nodes.
- *
- * @type {HTMLElement[]}
- */
- get: function get() {
- return expandContentElements(this.children, false);
- }
-
- /**
- * An in-order collection of distributed child nodes, expanding any slot
- * elements. Like the standard childNodes property, this includes text
- * nodes.
- *
- * @type {Node[]}
- */
-
- }, {
- key: 'distributedChildNodes',
- get: function get() {
- return expandContentElements(this.childNodes, true);
- }
-
- /**
- * The concatenated text content of all distributed child nodes, expanding
- * any slot elements.
- *
- * @type {string}
- */
-
- }, {
- key: 'distributedTextContent',
- get: function get() {
- var strings = this.distributedChildNodes.map(function (child) {
- return child.textContent;
- });
- return strings.join('');
- }
- }]);
-
- return DistributedChildren;
- }(base);
-
- return DistributedChildren;
-};
-
-/*
- * Given a array of nodes, return a new array with any content elements expanded
- * to the nodes distributed to that content element. This rule is applied
- * recursively.
- *
- * If includeTextNodes is true, text nodes will be included, as in the
- * standard childNodes property; by default, this skips text nodes, like the
- * standard children property.
- */
-
-
-function expandContentElements(nodes, includeTextNodes) {
- var _ref;
-
- var expanded = Array.prototype.map.call(nodes, function (node) {
- // We want to see if the node is an instanceof HTMLSlotELement, but
- // that class won't exist if the browser that doesn't support native
- // Shadow DOM and if the Shadow DOM polyfill hasn't been loaded. Instead,
- // we do a simplistic check to see if the tag name is "slot".
- var isSlot = typeof HTMLSlotElement !== 'undefined' ? node instanceof HTMLSlotElement : node.localName === 'slot';
- if (isSlot) {
- // Use the nodes assigned to this node instead.
- var assignedNodes = node.assignedNodes({ flatten: true });
- return assignedNodes ? expandContentElements(assignedNodes, includeTextNodes) : [];
- } else if (node instanceof HTMLElement) {
- // Plain element; use as is.
- return [node];
- } else if (node instanceof Text && includeTextNodes) {
- // Text node.
- return [node];
- } else {
- // Comment, processing instruction, etc.; skip.
- return [];
- }
- });
- var flattened = (_ref = []).concat.apply(_ref, _toConsumableArray(expanded));
- return flattened;
-}
-
-},{}],4:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-/* Exported function extends a base class with ShadowElementReferences. */
-exports.default = function (base) {
-
- /**
- * Mixin to create references to elements in a component's Shadow DOM subtree.
- *
- * This adds a member on the component called `this.$` that can be used to
- * reference shadow elements with IDs. E.g., if component's shadow contains an
- * element ``, then this mixin will create a member
- * `this.$.foo` that points to that button.
- *
- * Such references simplify a component's access to its own elements. In
- * exchange, this mixin trades off a one-time cost of querying all elements in
- * the shadow tree instead of paying an ongoing cost to query for an element
- * each time the component wants to inspect or manipulate it.
- *
- * This mixin expects the component to define a Shadow DOM subtree. You can
- * create that tree yourself, or make use of
- * [ShadowTemplateMixin](ShadowTemplateMixin.md).
- *
- * This mixin is inspired by Polymer's [automatic
- * node finding](https://www.polymer-project.org/1.0/docs/devguide/local-dom.html#node-finding)
- * feature.
- */
- var ShadowElementReferences = function (_base) {
- _inherits(ShadowElementReferences, _base);
-
- function ShadowElementReferences() {
- _classCallCheck(this, ShadowElementReferences);
-
- var _this = _possibleConstructorReturn(this, (ShadowElementReferences.__proto__ || Object.getPrototypeOf(ShadowElementReferences)).call(this));
-
- if (_this.shadowRoot) {
- // Look for elements in the shadow subtree that have id attributes.
- // An alternatively implementation of this mixin would be to just define
- // a this.$ getter that lazily does this search the first time someone
- // tries to access this.$. That might introduce some complexity – if the
- // the tree changed after it was first populated, the result of
- // searching for a node might be somewhat unpredictable.
- _this.$ = {};
- var nodesWithIds = _this.shadowRoot.querySelectorAll('[id]');
- [].forEach.call(nodesWithIds, function (node) {
- var id = node.getAttribute('id');
- _this.$[id] = node;
- });
- }
- return _this;
- }
-
- /**
- * The collection of references to the elements with IDs in a component's
- * Shadow DOM subtree.
- *
- * @type {object}
- * @member $
- */
-
-
- return ShadowElementReferences;
- }(base);
-
- return ShadowElementReferences;
-};
-
-},{}],5:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _symbols = require('../src/symbols');
-
-var _symbols2 = _interopRequireDefault(_symbols);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-/* Exported function extends a base class with ShadowTemplate. */
-exports.default = function (base) {
-
- /**
- * Mixin for stamping a template into a Shadow DOM subtree upon component
- * instantiation.
- *
- * To use this mixin, define a `template` property as a string or HTML
- * `` element:
- *
- * class MyElement extends ShadowTemplateMixin(HTMLElement) {
- * get [symbols.template]() {
- * return `Hello, world .`;
- * }
- * }
- *
- * When your component class is instantiated, a shadow root will be created on
- * the instance, and the contents of the template will be cloned into the
- * shadow root. If your component does not define a `template` property, this
- * mixin has no effect.
- *
- * For the time being, this extension retains support for Shadow DOM v0. That
- * will eventually be deprecated as browsers (and the Shadow DOM polyfill)
- * implement Shadow DOM v1.
- */
- var ShadowTemplate = function (_base) {
- _inherits(ShadowTemplate, _base);
-
- /*
- * If the component defines a template, a shadow root will be created on the
- * component instance, and the template stamped into it.
- */
- function ShadowTemplate() {
- _classCallCheck(this, ShadowTemplate);
-
- var _this = _possibleConstructorReturn(this, (ShadowTemplate.__proto__ || Object.getPrototypeOf(ShadowTemplate)).call(this));
-
- var template = _this[_symbols2.default.template];
- // TODO: Save the processed template with the component's class prototype
- // so it doesn't need to be processed with every instantiation.
- if (template) {
-
- if (typeof template === 'string') {
- // Upgrade plain string to real template.
- template = createTemplateWithInnerHTML(template);
- }
-
- if (window.ShadowDOMPolyfill) {
- shimTemplateStyles(template, _this.localName);
- }
-
- var root = _this.attachShadow({ mode: 'open' });
- var clone = document.importNode(template.content, true);
- root.appendChild(clone);
- }
- return _this;
- }
-
- return ShadowTemplate;
- }(base);
-
- return ShadowTemplate;
-};
-
-// Convert a plain string of HTML into a real template element.
-
-
-function createTemplateWithInnerHTML(innerHTML) {
- var template = document.createElement('template');
- // REVIEW: Is there an easier way to do this?
- // We'd like to just set innerHTML on the template content, but since it's
- // a DocumentFragment, that doesn't work.
- var div = document.createElement('div');
- div.innerHTML = innerHTML;
- while (div.childNodes.length > 0) {
- template.content.appendChild(div.childNodes[0]);
- }
- return template;
-}
-
-// Invoke basic style shimming with ShadowCSS.
-function shimTemplateStyles(template, tag) {
- window.WebComponents.ShadowCSS.shimStyling(template.content, tag);
-}
-
-},{"../src/symbols":8}],6:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-exports.default = createSymbol;
-/**
- * Helper function to create a symbol that can be used for associating private
- * data with an element.
- *
- * Mixins and component classes often want to associate private data with an
- * element instance, but JavaScript does not have direct support for true
- * private properties. One approach is to use the
- * [Symbol](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Symbol)
- * data type to set and retrieve data on an element.
- *
- * Unfortunately, the Symbol type is not available in Internet Explorer 11. The
- * `createSymbol` helper function exists as a workaround for IE 11. Rather than
- * returning a true Symbol, it simply returns an underscore-prefixed string.
- *
- * Usage:
- *
- * const fooSymbol = createSymbol('foo');
- *
- * class MyElement extends HTMLElement {
- * get foo() {
- * return this[fooSymbol];
- * }
- * set foo(value) {
- * this[fooSymbol] = value;
- * }
- * }
- *
- * In IE 11, this sample will "hide" data behind an instance property this._foo.
- * The use of the underscore is meant to reduce (not eliminate) the potential
- * for name conflicts, and discourage (not prevent) external access to this
- * data. In modern browsers, the above code will eliminate the potential of
- * naming conflicts, and better hide the data behind a real Symbol.
- *
- * @function createSymbol
- * @param {string} description - A string to identify the symbol when debugging
- */
-function createSymbol(description) {
- return typeof Symbol === 'function' ? Symbol(description) : '_' + description;
-}
-
-},{}],7:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createSymbol = require('./createSymbol');
-
-var _createSymbol2 = _interopRequireDefault(_createSymbol);
-
-var _toggleClass2 = require('./toggleClass');
-
-var _toggleClass3 = _interopRequireDefault(_toggleClass2);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-// Symbols for private data members on an element.
-var safeToSetAttributesSymbol = (0, _createSymbol2.default)('safeToSetAttributes');
-var pendingAttributesSymbol = (0, _createSymbol2.default)('pendingAttributes');
-var pendingClassesSymbol = (0, _createSymbol2.default)('pendingClasses');
-
-/**
- * Helper functions for updating attributes, including the `class` attribute.
- */
-exports.default = {
-
- /**
- * Perform any pending updates to attributes and classes.
- *
- * This writes any `setAttribute` or `toggleClass` values that were performed
- * before an element was attached to the document for the first time.
- *
- * This method should be called by mixins/components in their
- * `connectedCallback`. If mulitple mixins/components invoke this during the
- * same `connectedCallback`, only the first call will have any effect. The
- * subsequent calls will be harmless.
- *
- * @param {HTMLElement} element - The element being added to the document.
- */
- connected: function connected(element) {
- element[safeToSetAttributesSymbol] = true;
-
- // Set any pending attributes.
- if (element[pendingAttributesSymbol]) {
- for (var attribute in element[pendingAttributesSymbol]) {
- var value = element[pendingAttributesSymbol][attribute];
- setAttributeToElement(element, attribute, value);
- }
- element[pendingAttributesSymbol] = null;
- }
-
- // Set any pending classes.
- if (element[pendingClassesSymbol]) {
- for (var className in element[pendingClassesSymbol]) {
- var _value = element[pendingClassesSymbol][className];
- (0, _toggleClass3.default)(element, className, _value);
- }
- element[pendingClassesSymbol] = null;
- }
- },
-
-
- /**
- * Set/unset the attribute with the indicated name.
- *
- * This method exists primarily to handle the case where an element wants to
- * set a default property value that should be reflected as an attribute. An
- * important limitation of custom element consturctors is that they cannot
- * set attributes. A call to `setAttribute` during the constructor will
- * be deferred until the element is connected to the document.
- *
- * @param {string} attribute - The name of the *attribute* (not property) to set.
- * @param {object} value - The value to set. If null, the attribute will be removed.
- */
- setAttribute: function setAttribute(element, attribute, value) {
- if (element[safeToSetAttributesSymbol]) {
- // Safe to set attributes immediately.
- setAttributeToElement(element, attribute, value);
- } else {
- // Defer setting attributes until the first time we're connected.
- if (!element[pendingAttributesSymbol]) {
- element[pendingAttributesSymbol] = {};
- }
- element[pendingAttributesSymbol][attribute] = value;
- }
- },
-
-
- /**
- * Set/unset the class with the indicated name.
- *
- * This method exists primarily to handle the case where an element wants to
- * set a default property value that should be reflected as as class. An
- * important limitation of custom element consturctors is that they cannot
- * set attributes, including the `class` attribute. A call to
- * `toggleClass` during the constructor will be deferred until the element
- * is connected to the document.
- *
- * @param {string} className - The name of the class to set.
- * @param {object} value - True to set the class, false to remove it.
- */
- toggleClass: function toggleClass(element, className, value) {
- if (element[safeToSetAttributesSymbol]) {
- // Safe to set class immediately.
- (0, _toggleClass3.default)(element, className, value);
- } else {
- // Defer setting class until the first time we're connected.
- if (!element[pendingClassesSymbol]) {
- element[pendingClassesSymbol] = {};
- }
- element[pendingClassesSymbol][className] = value;
- }
- }
-};
-
-// Reflect the attribute to the given element.
-// If the value is null, remove the attribute.
-
-function setAttributeToElement(element, attributeName, value) {
- if (value === null || typeof value === 'undefined') {
- element.removeAttribute(attributeName);
- } else {
- var text = String(value);
- // Avoid recursive attributeChangedCallback calls.
- if (element.getAttribute(attributeName) !== text) {
- element.setAttribute(attributeName, value);
- }
- }
-}
-
-},{"./createSymbol":6,"./toggleClass":9}],8:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createSymbol = require('./createSymbol');
-
-var _createSymbol2 = _interopRequireDefault(_createSymbol);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-/**
- * A collection of Symbol objects for standard component properties and methods.
- *
- * These Symbol objects are used to allow mixins and a component to internally
- * communicate, without exposing these properties and methods in the component's
- * public API.
- *
- * To use these Symbol objects in your own component, include this module and
- * then create a property or method whose key is the desired Symbol.
- *
- * import 'SingleSelectionMixin' from 'basic-component-mixins/src/SingleSelectionMixin';
- * import 'symbols' from 'basic-component-mixins/src/symbols';
- *
- * class MyElement extends SingleSelectionMixin(HTMLElement) {
- * [symbols.itemSelected](item, selected) {
- * // This will be invoked whenever an item is selected/deselected.
- * }
- * }
- *
- * @module symbols
- */
-var symbols = {
-
- /**
- * Symbol for the `defaults` property.
- *
- * This property can be used to set or override defaults that will be applied
- * to a new component instance. When implementing this property, take care to
- * first acquire any defaults defined by the superclass. The standard idiom is
- * as follows:
- *
- * get [symbols.defaults]() {
- * const defaults = super[symbols.defaults] || {};
- * // Set or override default values here
- * defaults.customProperty = false;
- * return defaults;
- * }
- *
- * @var {object} defaults
- */
- defaults: (0, _createSymbol2.default)('defaults'),
-
- /**
- * Symbol for the `dragging` property.
- *
- * Components like carousels often define animated CSS transitions for
- * sliding effects. Such a transition should usually *not* be applied while
- * the user is dragging, because a CSS animation will introduce a lag that
- * makes the swipe feel sluggish. Instead, as long as the user is dragging
- * with their finger down, the transition should be suppressed. When the
- * user releases their finger, the transition can be restored, allowing the
- * animation to show the carousel sliding into its final position.
- *
- * @type {boolean} true if a drag is in progress, false if not.
- */
- dragging: (0, _createSymbol2.default)('dragging'),
-
- /**
- * Symbol for the `goDown` method.
- *
- * This method is invoked when the user wants to go/navigate down.
- *
- * @function goDown
- */
- goDown: (0, _createSymbol2.default)('goDown'),
-
- /**
- * Symbol for the `goEnd` method.
- *
- * This method is invoked when the user wants to go/navigate to the end (e.g.,
- * of a list).
- *
- * @function goEnd
- */
- goEnd: (0, _createSymbol2.default)('goEnd'),
-
- /**
- * Symbol for the `goLeft` method.
- *
- * This method is invoked when the user wants to go/navigate left.
- *
- * @function goLeft
- */
- goLeft: (0, _createSymbol2.default)('goLeft'),
-
- /**
- * Symbol for the `goRight` method.
- *
- * This method is invoked when the user wants to go/navigate right.
- *
- * @function goRight
- */
- goRight: (0, _createSymbol2.default)('goRight'),
-
- /**
- * Symbol for the `goStart` method.
- *
- * This method is invoked when the user wants to go/navigate to the start
- * (e.g., of a list).
- *
- * @function goStart
- */
- goStart: (0, _createSymbol2.default)('goStart'),
-
- /**
- * Symbol for the `goUp` method.
- *
- * This method is invoked when the user wants to go/navigate up.
- *
- * @function goUp
- */
- goUp: (0, _createSymbol2.default)('goUp'),
-
- /**
- * Symbol for the `itemAdded` method.
- *
- * This method is invoked when a new item is added to a list.
- *
- * @function itemAdded
- * @param {HTMLElement} item - the item being selected/deselected
- */
- itemAdded: (0, _createSymbol2.default)('itemAdded'),
-
- /**
- * Symbol for the `itemsChanged` method.
- *
- * This method is invoked when the underlying contents change. It is also
- * invoked on component initialization – since the items have "changed" from
- * being nothing.
- */
- itemsChanged: (0, _createSymbol2.default)('itemsChanged'),
-
- /**
- * Symbol for the `itemSelected` method.
- *
- * This method is invoked when an item becomes selected or deselected.
- *
- * @function itemSelected
- * @param {HTMLElement} item - the item being selected/deselected
- * @param {boolean} selected - true if the item is selected, false if not
- */
- itemSelected: (0, _createSymbol2.default)('itemSelected'),
-
- /**
- * Symbol for the `keydown` method.
- *
- * This method is invoked when an element receives a `keydown` event.
- *
- * @function keydown
- * @param {KeyboardEvent} event - the event being processed
- */
- keydown: (0, _createSymbol2.default)('keydown'),
-
- /**
- * Symbol for the `template` property.
- *
- * This property returns a component's template.
- *
- * @type {string|HTMLElement}
- */
- template: (0, _createSymbol2.default)('template')
-};
-
-exports.default = symbols;
-
-},{"./createSymbol":6}],9:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-exports.default = toggleClass;
-/**
- * Helper function for standard classList.toggle() behavior on old browsers,
- * namely IE 11.
- *
- * The standard
- * [classlist](https://developer.mozilla.org/en-US/docs/Web/API/Element/classList)
- * object has a `toggle()` function that supports a second Boolean parameter
- * that can be used to succinctly turn a class on or off. This feature is often
- * useful in designing custom elements, which may want to externally reflect
- * component state in a CSS class that can be used for styling purposes.
- *
- * Unfortunately, IE 11 does not support the Boolean parameter to
- * `classList.toggle()`. This helper function behaves like the standard
- * `toggle()`, including support for the Boolean parameter, so that it can be
- * used even on IE 11.
- *
- * @function toggleClass
- * @param {HTMLElement} element - The element to modify
- * @param {string} className - The class to add/remove
- * @param {boolean} [force] - Force the class to be added (if true) or removed
- * (if false)
- */
-function toggleClass(element, className, force) {
- var classList = element.classList;
- var addClass = typeof force === 'undefined' ? !classList.contains(className) : force;
- if (addClass) {
- classList.add(className);
- } else {
- classList.remove(className);
- }
- return addClass;
-}
-
-},{}],10:[function(require,module,exports){
-'use strict';
-
-var _CurrentAnchor = require('./src/CurrentAnchor');
-
-var _CurrentAnchor2 = _interopRequireDefault(_CurrentAnchor);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-window.Basic = window.Basic || {}; /*
- * This file is transpiled to create an ES5-compatible distribution in which
- * the package's main feature(s) are available via the window.Basic global.
- * If you're already using ES6 yourself, ignore this file, and instead import
- * the source file(s) you want from the src folder.
- */
-
-window.Basic.CurrentAnchor = _CurrentAnchor2.default;
-
-},{"./src/CurrentAnchor":11}],11:[function(require,module,exports){
-'use strict';
-
-var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
-
-var _set = function set(object, property, value, receiver) { var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent !== null) { set(parent, property, value, receiver); } } else if ("value" in desc && desc.writable) { desc.value = value; } else { var setter = desc.set; if (setter !== undefined) { setter.call(receiver, value); } } return value; };
-
-var _get = function get(object, property, receiver) { if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { return get(parent, property, receiver); } } else if ("value" in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } };
-
-var _createSymbol = require('../../basic-component-mixins/src/createSymbol');
-
-var _createSymbol2 = _interopRequireDefault(_createSymbol);
-
-var _safeAttributes = require('../../basic-component-mixins/src/safeAttributes');
-
-var _safeAttributes2 = _interopRequireDefault(_safeAttributes);
-
-var _symbols = require('../../basic-component-mixins/src/symbols');
-
-var _symbols2 = _interopRequireDefault(_symbols);
-
-var _WrappedStandardElement = require('../../basic-wrapped-standard-element/src/WrappedStandardElement');
-
-var _WrappedStandardElement2 = _interopRequireDefault(_WrappedStandardElement);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-// Symbols for private data members on an element.
-var areaLinkSymbol = (0, _createSymbol2.default)('areaLink');
-
-/**
- * An anchor (link) that highlights itself when its destination matches the
- * current location.
- *
- * [Live demo](http://basicwebcomponents.org/basic-web-components/packages/basic-current-anchor/)
- *
- * Such a link commonly appears in toolbars, side bars, and other navigation
- * elements. In these situations, you generally want the user to understand what
- * page or area the user is already on.
- *
- * When the link is current — when it points to the current location — the
- * link will have the CSS `current` class applied to it, and its `current`
- * property will be true.
- *
- * Note: one limitation of this component is that, by default, the link does
- * *not* show the standard link color (usually blue) and text decoration
- * (underline). However, in navigation elements like toolbars, you often will
- * want to explicitly specific link colors anyway, e.g., to reflect your
- * application's visual style and brand.
- */
-
-var CurrentAnchor = function (_WrappedStandardEleme) {
- _inherits(CurrentAnchor, _WrappedStandardEleme);
-
- function CurrentAnchor() {
- _classCallCheck(this, CurrentAnchor);
-
- var _this = _possibleConstructorReturn(this, (CurrentAnchor.__proto__ || Object.getPrototypeOf(CurrentAnchor)).call(this));
-
- window.addEventListener('popstate', function (event) {
- refresh(_this);
- });
-
- // Stupid Edge/IE "support" popstate, but don't fire it on hashchange.
- // So we have to listen for hashchange as well, with the result that a
- // standards-compliant browser may end up refreshing the link twice.
- window.addEventListener('hashchange', function (event) {
- refresh(_this);
- });
-
- // Set defaults.
- if (typeof _this.areaLink === 'undefined') {
- _this.areaLink = _this[_symbols2.default.defaults].areaLink;
- }
- return _this;
- }
-
- /**
- * True if the link points to an area within a site, not just a single page.
- *
- * If true, the matching rule to determine whether the link is current changes:
- * an area link is considered to be current if the link's destination forms a
- * prefix of the current location (instead of matching the complete URL).
- *
- * @type {boolean}
- */
-
-
- _createClass(CurrentAnchor, [{
- key: 'connectedCallback',
- value: function connectedCallback() {
- if (_get(CurrentAnchor.prototype.__proto__ || Object.getPrototypeOf(CurrentAnchor.prototype), 'connectedCallback', this)) {
- _get(CurrentAnchor.prototype.__proto__ || Object.getPrototypeOf(CurrentAnchor.prototype), 'connectedCallback', this).call(this);
- }
- _safeAttributes2.default.connected(this);
- refresh(this);
- }
-
- /**
- * True if the link's destination matches the current page location.
- *
- * If this is true, the element will have an `current` CSS class applied to it.
- *
- * @type {boolean}
- */
-
- }, {
- key: 'areaLink',
- get: function get() {
- return this[areaLinkSymbol];
- },
- set: function set(value) {
- // Cast boolean or string values to boolean.
- this[areaLinkSymbol] = String(value) === 'true';
- refresh(this);
- }
- }, {
- key: 'current',
- get: function get() {
- return this.classList.contains('current');
- },
- set: function set(value) {
- _safeAttributes2.default.toggleClass(this, 'current', value);
- this.dispatchEvent(new CustomEvent('current-changed'));
- }
- }, {
- key: _symbols2.default.defaults,
- get: function get() {
- var defaults = _get(CurrentAnchor.prototype.__proto__ || Object.getPrototypeOf(CurrentAnchor.prototype), _symbols2.default.defaults, this) || {};
- defaults.areaLink = false;
- return defaults;
- }
-
- // Augment href implementation so that changing href checks the active status.
-
- }, {
- key: 'href',
- get: function get() {
- return _get(CurrentAnchor.prototype.__proto__ || Object.getPrototypeOf(CurrentAnchor.prototype), 'href', this);
- },
- set: function set(value) {
- _set(CurrentAnchor.prototype.__proto__ || Object.getPrototypeOf(CurrentAnchor.prototype), 'href', value, this);
- refresh(this);
- }
- }, {
- key: _symbols2.default.template,
- get: function get() {
- // Reset styles so that color can be specified from the outside without
- // having to define a CSS variable.
- return '\n \n ';
- }
- }]);
-
- return CurrentAnchor;
-}(_WrappedStandardElement2.default.wrap('a'));
-
-// Update the current status of the element based on the current location.
-
-
-function refresh(element) {
- var url = window.location.href;
- var match = void 0;
- if (element.areaLink) {
- // Match prefix
- var prefix = element.href;
- // If prefix doesn't end in slash, add a slash.
- // We want to avoid matching in the middle of a folder name.
- if (prefix.length < url.length && prefix.substr(-1) !== '/') {
- prefix += '/';
- }
- match = url.substr(0, prefix.length) === prefix;
- } else {
- // Match whole path
- match = url === element.href;
- }
- element.current = match;
-}
-
-customElements.define('basic-current-anchor', CurrentAnchor);
-
-},{"../../basic-component-mixins/src/createSymbol":6,"../../basic-component-mixins/src/safeAttributes":7,"../../basic-component-mixins/src/symbols":8,"../../basic-wrapped-standard-element/src/WrappedStandardElement":13}],12:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _AttributeMarshallingMixin = require('../../basic-component-mixins/src/AttributeMarshallingMixin');
-
-var _AttributeMarshallingMixin2 = _interopRequireDefault(_AttributeMarshallingMixin);
-
-var _ComposableMixin = require('../../basic-component-mixins/src/ComposableMixin');
-
-var _ComposableMixin2 = _interopRequireDefault(_ComposableMixin);
-
-var _DistributedChildrenMixin = require('../../basic-component-mixins/src/DistributedChildrenMixin');
-
-var _DistributedChildrenMixin2 = _interopRequireDefault(_DistributedChildrenMixin);
-
-var _ShadowElementReferencesMixin = require('../../basic-component-mixins/src/ShadowElementReferencesMixin');
-
-var _ShadowElementReferencesMixin2 = _interopRequireDefault(_ShadowElementReferencesMixin);
-
-var _ShadowTemplateMixin = require('../../basic-component-mixins/src/ShadowTemplateMixin');
-
-var _ShadowTemplateMixin2 = _interopRequireDefault(_ShadowTemplateMixin);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-/**
- * A sample general-purpose base class for defining custom elements that mixes
- * in some common features: template stamping into a shadow root, shadow element
- * references, marshalling attributes to properties, and retrieving the children
- * distributed to a component.
- *
- * This base class is not special in any way, and is defined only as a
- * convenient shorthand for applying the mixins listed above. You can use this
- * class as a base class for your own elements, or easily create your own base
- * class by applying the same set of mixins.
- *
- * The ElementBase base class does not register itself as a custom element with
- * the browser, and hence cannot be independently instantiated.
- *
- * @mixes AttributeMarshallingMixin
- * @mixes ComposableMixin
- * @mixes DistributedChildrenMixin
- * @mixes ShadowElementReferencesMixin
- * @mixes ShadowTemplateMixin
- */
-var ElementBase = function (_ComposableMixin$comp) {
- _inherits(ElementBase, _ComposableMixin$comp);
-
- function ElementBase() {
- _classCallCheck(this, ElementBase);
-
- return _possibleConstructorReturn(this, (ElementBase.__proto__ || Object.getPrototypeOf(ElementBase)).apply(this, arguments));
- }
-
- return ElementBase;
-}((0, _ComposableMixin2.default)(HTMLElement).compose(_ShadowTemplateMixin2.default, // before node finding, so shadow root is populated
-_ShadowElementReferencesMixin2.default, // before marshalling, so properties can use refs
-_AttributeMarshallingMixin2.default, _DistributedChildrenMixin2.default));
-
-exports.default = ElementBase;
-
-},{"../../basic-component-mixins/src/AttributeMarshallingMixin":1,"../../basic-component-mixins/src/ComposableMixin":2,"../../basic-component-mixins/src/DistributedChildrenMixin":3,"../../basic-component-mixins/src/ShadowElementReferencesMixin":4,"../../basic-component-mixins/src/ShadowTemplateMixin":5}],13:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
-
-var _ElementBase2 = require('../../basic-element-base/src/ElementBase');
-
-var _ElementBase3 = _interopRequireDefault(_ElementBase2);
-
-var _symbols = require('../../basic-component-mixins/src/symbols');
-
-var _symbols2 = _interopRequireDefault(_symbols);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-/*
- * A set of events which, if fired by the inner standard element, should be
- * re-raised by the custom element. (We only need to do that under native
- * Shadow DOM, not the polyfill.)
- *
- * These are events which are spec'ed to NOT get retargetted across a Shadow DOM
- * boundary, organized by which element(s) raise the events. To properly
- * simulate these, we will need to listen for the real events, then re-raise a
- * simulation of the original event. For more information, see
- * https://www.w3.org/TR/shadow-dom/#h-events-that-are-not-leaked-into-ancestor-trees.
- *
- * It appears that we do *not* need to re-raise the non-bubbling "focus" and
- * "blur" events. These appear to be automatically re-raised as expected -- but
- * it's not clear why that happens.
- *
- * The list below is reasonably complete. It omits elements that cannot be
- * wrapped (see class notes above). Also, we haven't actually tried wrapping
- * every element in this list; some of the more obscure ones might not actually
- * work as expected, but it was easier to include them for completeness than
- * to actually verify whether or not the element can be wrapped.
- */
-var reraiseEvents = {
- address: ['scroll'],
- blockquote: ['scroll'],
- caption: ['scroll'],
- center: ['scroll'],
- dd: ['scroll'],
- dir: ['scroll'],
- div: ['scroll'],
- dl: ['scroll'],
- dt: ['scroll'],
- fieldset: ['scroll'],
- form: ['reset', 'scroll'],
- frame: ['load'],
- h1: ['scroll'],
- h2: ['scroll'],
- h3: ['scroll'],
- h4: ['scroll'],
- h5: ['scroll'],
- h6: ['scroll'],
- iframe: ['load'],
- img: ['abort', 'error', 'load'],
- input: ['abort', 'change', 'error', 'select', 'load'],
- keygen: ['reset', 'select'],
- li: ['scroll'],
- link: ['load'],
- menu: ['scroll'],
- object: ['error', 'scroll'],
- ol: ['scroll'],
- p: ['scroll'],
- script: ['error', 'load'],
- select: ['change', 'scroll'],
- tbody: ['scroll'],
- tfoot: ['scroll'],
- thead: ['scroll'],
- textarea: ['change', 'select', 'scroll']
-};
-
-// Keep track of which re-raised events should bubble.
-var eventBubbles = {
- abort: true,
- change: true,
- reset: true
-};
-
-// Elements which are display: block by default.
-// Source: https://developer.mozilla.org/en-US/docs/Web/HTML/Block-level_elements
-var blockElements = ['address', 'article', 'aside', 'blockquote', 'canvas', 'dd', 'div', 'dl', 'fieldset', 'figcaption', 'figure', 'footer', 'form', 'h1', 'h2', 'h3', 'h4', 'h5', 'h6', 'header', 'hgroup', 'hr', 'li', 'main', 'nav', 'noscript', 'ol', 'output', 'p', 'pre', 'section', 'table', 'tfoot', 'ul', 'video'];
-
-/**
- * Wraps a standard HTML element so that the standard behavior can then be
- * extended.
- *
- * [Live demo](http://basicwebcomponents.org/basic-web-components/packages/basic-wrapped-standard-element/)
- *
- * See also [basic-autosize-textarea](../basic-autosize-textarea) and
- * [basic-current-anchor](../basic-current-anchor). The former uses
- * WrappedStandardElement to wrap a standard `
- *
- * The `display` styling applied to the host will be `block` for elements that
- * are block elements by default, and `inline-block` (not `inline`) for other
- * elements.
- *
- * If you'd like the template to include other elements, then override this
- * property and return a template of your own. The template should include an
- * instance of the standard HTML element you are wrapping, and the ID of that
- * element should be "inner".
- *
- * @type {(string|HTMLTemplateElement)}
- */
-
- }, {
- key: _symbols2.default.template,
- get: function get() {
- var display = blockElements.indexOf(this.extends) >= 0 ? 'block' : 'inline-block';
- return '<' + this.extends + ' id="inner"> ' + this.extends;
- }
-
- /**
- * Creates a class that wraps a standard HTML element.
- *
- * Note that the resulting class is a subclass of WrappedStandardElement, not
- * the standard class being wrapped. E.g., if you call
- * `WrappedStandardElement.wrap('a')`, you will get a class whose shadow tree
- * will include an anchor element, but the class will *not* inherit from
- * HTMLAnchorElement.
- *
- * @param {string} extendsTag - the standard HTML element tag to extend
- */
-
- }], [{
- key: 'wrap',
- value: function wrap(extendsTag) {
-
- // Create the new class.
- var Wrapped = function (_WrappedStandardEleme) {
- _inherits(Wrapped, _WrappedStandardEleme);
-
- function Wrapped() {
- _classCallCheck(this, Wrapped);
-
- return _possibleConstructorReturn(this, (Wrapped.__proto__ || Object.getPrototypeOf(Wrapped)).apply(this, arguments));
- }
-
- return Wrapped;
- }(WrappedStandardElement);
-
- // Indicate which tag it wraps.
-
-
- Wrapped.prototype.extends = extendsTag;
-
- // Create getter/setters that delegate to the wrapped element.
- var element = document.createElement(extendsTag);
- var extendsPrototype = element.constructor.prototype;
- var names = Object.getOwnPropertyNames(extendsPrototype);
- names.forEach(function (name) {
- var descriptor = Object.getOwnPropertyDescriptor(extendsPrototype, name);
- var delegate = createPropertyDelegate(name, descriptor);
- Object.defineProperty(Wrapped.prototype, name, delegate);
- });
-
- return Wrapped;
- }
- }]);
-
- return WrappedStandardElement;
-}(_ElementBase3.default);
-
-function createPropertyDelegate(name, descriptor) {
- var delegate = {
- configurable: descriptor.configurable,
- enumerable: descriptor.enumerable
- };
- if (descriptor.get) {
- delegate.get = function () {
- return this.inner[name];
- };
- }
- if (descriptor.set) {
- delegate.set = function (value) {
- this.inner[name] = value;
- };
- }
- if (descriptor.writable) {
- delegate.writable = descriptor.writable;
- }
- return delegate;
-}
-
-exports.default = WrappedStandardElement;
-
-},{"../../basic-component-mixins/src/symbols":8,"../../basic-element-base/src/ElementBase":12}]},{},[10])
-//# sourceMappingURL=data:application/json;charset:utf-8;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbIm5vZGVfbW9kdWxlcy9ncnVudC1icm93c2VyaWZ5L25vZGVfbW9kdWxlcy9icm93c2VyLXBhY2svX3ByZWx1ZGUuanMiLCJwYWNrYWdlcy9iYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy9BdHRyaWJ1dGVNYXJzaGFsbGluZ01peGluLmpzIiwicGFja2FnZXMvYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvQ29tcG9zYWJsZU1peGluLmpzIiwicGFja2FnZXMvYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvRGlzdHJpYnV0ZWRDaGlsZHJlbk1peGluLmpzIiwicGFja2FnZXMvYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvU2hhZG93RWxlbWVudFJlZmVyZW5jZXNNaXhpbi5qcyIsInBhY2thZ2VzL2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL1NoYWRvd1RlbXBsYXRlTWl4aW4uanMiLCJwYWNrYWdlcy9iYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy9jcmVhdGVTeW1ib2wuanMiLCJwYWNrYWdlcy9iYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy9zYWZlQXR0cmlidXRlcy5qcyIsInBhY2thZ2VzL2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL3N5bWJvbHMuanMiLCJwYWNrYWdlcy9iYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy90b2dnbGVDbGFzcy5qcyIsInBhY2thZ2VzL2Jhc2ljLWN1cnJlbnQtYW5jaG9yL2dsb2JhbHMuanMiLCJwYWNrYWdlcy9iYXNpYy1jdXJyZW50LWFuY2hvci9zcmMvQ3VycmVudEFuY2hvci5qcyIsInBhY2thZ2VzL2Jhc2ljLWVsZW1lbnQtYmFzZS9zcmMvRWxlbWVudEJhc2UuanMiLCJwYWNrYWdlcy9iYXNpYy13cmFwcGVkLXN0YW5kYXJkLWVsZW1lbnQvc3JjL1dyYXBwZWRTdGFuZGFyZEVsZW1lbnQuanMiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6IkFBQUE7Ozs7Ozs7Ozs7O0FDQUE7Ozs7Ozs7Ozs7OztB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LGFBQVMsUUFBVCxHQUFvQixXQUFXLFFBQS9CO0FBQ0Q7QUFDRCxTQUFPLFFBQVA7QUFDRDs7a0JBR2Msc0IiLCJmaWxlIjoiZ2VuZXJhdGVkLmpzIiwic291cmNlUm9vdCI6IiIsInNvdXJjZXNDb250ZW50IjpbIihmdW5jdGlvbiBlKHQsbixyKXtmdW5jdGlvbiBzKG8sdSl7aWYoIW5bb10pe2lmKCF0W29dKXt2YXIgYT10eXBlb2YgcmVxdWlyZT09XCJmdW5jdGlvblwiJiZyZXF1aXJlO2lmKCF1JiZhKXJldHVybiBhKG8sITApO2lmKGkpcmV0dXJuIGkobywhMCk7dmFyIGY9bmV3IEVycm9yKFwiQ2Fubm90IGZpbmQgbW9kdWxlICdcIitvK1wiJ1wiKTt0aHJvdyBmLmNvZGU9XCJNT0RVTEVfTk9UX0ZPVU5EXCIsZn12YXIgbD1uW29dPXtleHBvcnRzOnt9fTt0W29dWzBdLmNhbGwobC5leHBvcnRzLGZ1bmN0aW9uKGUpe3ZhciBuPXRbb11bMV1bZV07cmV0dXJuIHMobj9uOmUpfSxsLGwuZXhwb3J0cyxlLHQsbixyKX1yZXR1cm4gbltvXS5leHBvcnRzfXZhciBpPXR5cGVvZiByZXF1aXJlPT1cImZ1bmN0aW9uXCImJnJlcXVpcmU7Zm9yKHZhciBvPTA7bzxyLmxlbmd0aDtvKyspcyhyW29dKTtyZXR1cm4gc30pIiwiaW1wb3J0IHNhZmVBdHRyaWJ1dGVzIGZyb20gJy4vc2FmZUF0dHJpYnV0ZXMnO1xuXG5cbi8vIE1lbW9pemVkIG1hcHMgb2YgYXR0cmlidXRlIHRvIHByb3BlcnR5IG5hbWVzIGFuZCB2aWNlIHZlcnNhLlxuY29uc3QgYXR0cmlidXRlVG9Qcm9wZXJ0eU5hbWVzID0ge307XG5jb25zdCBwcm9wZXJ0eU5hbWVzVG9BdHRyaWJ1dGVzID0ge307XG5cblxuLyogRXhwb3J0ZWQgZnVuY3Rpb24gZXh0ZW5kcyBhIGJhc2UgY2xhc3Mgd2l0aCBBdHRyaWJ1dGVNYXJzaGFsbGluZy4gKi9cbmV4cG9ydCBkZWZhdWx0IChiYXNlKSA9PiB7XG5cbiAgLyoqXG4gICAqIE1peGluIHdoaWNoIG1hcnNoYWxscyBhdHRyaWJ1dGVzIHRvIHByb3BlcnRpZXMgYW5kIHZpY2UgdmVyc2EuXG4gICAqXG4gICAqIElmIHlvdXIgY29tcG9uZW50IGV4cG9zZXMgYSBzZXR0ZXIgZm9yIGEgcHJvcGVydHksIGl0J3MgZ2VuZXJhbGx5IGEgZ29vZFxuICAgKiBpZGVhIHRvIGxldCBkZXZzIHVzaW5nIHlvdXIgY29tcG9uZW50IGJlIGFibGUgdG8gc2V0IHRoYXQgcHJvcGVydHkgaW4gSFRNTFxuICAgKiB2aWEgYW4gZWxlbWVudCBhdHRyaWJ1dGUuIFlvdSBjYW4gY29kZSB0aGF0IHlvdXJzZWxmIGJ5IHdyaXRpbmcgYW5cbiAgICogYGF0dHJpYnV0ZUNoYW5nZWRDYWxsYmFja2AsIG9yIHlvdSBjYW4gdXNlIHRoaXMgbWl4aW4gdG8gZ2V0IGEgZGVncmVlIG9mXG4gICAqIGF1dG9tYXRpYyBzdXBwb3J0LlxuICAgKlxuICAgKiBUaGlzIG1peGluIGltcGxlbWVudHMgYW4gYGF0dHJpYnV0ZUNoYW5nZWRDYWxsYmFja2AgdGhhdCB3aWxsIGF0dGVtcHQgdG9cbiAgICogY29udmVydCBhIGNoYW5nZSBpbiBhbiBlbGVtZW50IGF0dHJpYnV0ZSBpbnRvIGEgY2FsbCB0byB0aGUgY29ycmVzcG9uZGluZ1xuICAgKiBwcm9wZXJ0eSBzZXR0ZXIuIEF0dHJpYnV0ZXMgdHlwaWNhbGx5IGZvbGxvdyBoeXBoZW5hdGVkIG5hbWVzIChcImZvby1iYXJcIiksXG4gICAqIHdoZXJlYXMgcHJvcGVydGllcyB0eXBpY2FsbHkgdXNlIGNhbWVsQ2FzZSBuYW1lcyAoXCJmb29CYXJcIikuIFRoaXMgbWl4aW5cbiAgICogcmVzcGVjdHMgdGhhdCBjb252ZW50aW9uLCBhdXRvbWF0aWNhbGx5IG1hcHBpbmcgdGhlIGh5cGhlbmF0ZWQgYXR0cmlidXRlXG4gICAqIG5hbWUgdG8gdGhlIGNvcnJlc3BvbmRpbmcgY2FtZWxDYXNlIHByb3BlcnR5IG5hbWUuXG4gICAqXG4gICAqIEV4YW1wbGU6IFlvdSBkZWZpbmUgYSBjb21wb25lbnQgdXNpbmcgdGhpcyBtaXhpbjpcbiAgICpcbiAgICogICAgIGNsYXNzIE15RWxlbWVudCBleHRlbmRzIEF0dHJpYnV0ZU1hcnNoYWxsaW5nTWl4aW4oSFRNTEVsZW1lbnQpIHtcbiAgICogICAgICAgZ2V0IGZvb0JhcigpIHsgcmV0dXJuIHRoaXMuX2Zvb0JhcjsgfVxuICAgKiAgICAgICBzZXQgZm9vQmFyKHZhbHVlKSB7IHRoaXMuX2Zvb0JhciA9IHZhbHVlOyB9XG4gICAqICAgICB9XG4gICAqICAgICBjdXN0b21FbGVtZW50cy5kZWZpbmUoJ215LWVsZW1lbnQnLCBNeUVsZW1lbnQpO1xuICAgKlxuICAgKiBJZiBzb21lb25lIHRoZW4gaW5zdGFudGlhdGVzIHlvdXIgY29tcG9uZW50IGluIEhUTUw6XG4gICAqXG4gICAqICAgICA8bXktZWxlbWVudCBmb28tYmFyPVwiSGVsbG9cIj48L215LWVsZW1lbnQ+XG4gICAqXG4gICAqIFRoZW4sIGFmdGVyIHRoZSBlbGVtZW50IGhhcyBiZWVuIHVwZ3JhZGVkLCB0aGUgYGZvb0JhcmAgc2V0dGVyIHdpbGxcbiAgICogYXV0b21hdGljYWxseSBiZSBpbnZva2VkIHdpdGggdGhlIGluaXRpYWwgdmFsdWUgXCJIZWxsb1wiLlxuICAgKlxuICAgKiBGb3IgdGhlIHRpbWUgYmVpbmcsIHRoaXMgbWl4aW4gb25seSBzdXBwb3J0cyBzdHJpbmctdmFsdWVkIHByb3BlcnRpZXMuXG4gICAqIElmIHlvdSdkIGxpa2UgdG8gY29udmVydCBzdHJpbmcgYXR0cmlidXRlcyB0byBvdGhlciB0eXBlcyAobnVtYmVycyxcbiAgICogYm9vbGVhbnMpLCB5b3UgbmVlZCB0byBpbXBsZW1lbnQgYGF0dHJpYnV0ZUNoYW5nZWRDYWxsYmFja2AgeW91cnNlbGYuXG4gICAqL1xuICBjbGFzcyBBdHRyaWJ1dGVNYXJzaGFsbGluZyBleHRlbmRzIGJhc2Uge1xuXG4gICAgLypcbiAgICAgKiBIYW5kbGUgYSBjaGFuZ2UgdG8gdGhlIGF0dHJpYnV0ZSB3aXRoIHRoZSBnaXZlbiBuYW1lLlxuICAgICAqL1xuICAgIGF0dHJpYnV0ZUNoYW5nZWRDYWxsYmFjayhhdHRyaWJ1dGVOYW1lLCBvbGRWYWx1ZSwgbmV3VmFsdWUpIHtcbiAgICAgIGlmIChzdXBlci5hdHRyaWJ1dGVDaGFuZ2VkQ2FsbGJhY2spIHsgc3VwZXIuYXR0cmlidXRlQ2hhbmdlZENhbGxiYWNrKCk7IH1cbiAgICAgIGNvbnN0IHByb3BlcnR5TmFtZSA9IGF0dHJpYnV0ZVRvUHJvcGVydHlOYW1lKGF0dHJpYnV0ZU5hbWUpO1xuICAgICAgLy8gSWYgdGhlIGF0dHJpYnV0ZSBuYW1lIGNvcnJlc3BvbmRzIHRvIGEgcHJvcGVydHkgbmFtZSwgc2V0IHRoZSBwcm9wZXJ0eS5cbiAgICAgIC8vIElnbm9yZSBzdGFuZGFyZCBIVE1MRWxlbWVudCBwcm9wZXJ0aWVzIGhhbmRsZWQgYnkgdGhlIERPTS5cbiAgICAgIGlmIChwcm9wZXJ0eU5hbWUgaW4gdGhpcyAmJiAhKHByb3BlcnR5TmFtZSBpbiBIVE1MRWxlbWVudC5wcm90b3R5cGUpKSB7XG4gICAgICAgIHRoaXNbcHJvcGVydHlOYW1lXSA9IG5ld1ZhbHVlO1xuICAgICAgfVxuICAgIH1cblxuICAgIGNvbm5lY3RlZENhbGxiYWNrKCkge1xuICAgICAgaWYgKHN1cGVyLmNvbm5lY3RlZENhbGxiYWNrKSB7IHN1cGVyLmNvbm5lY3RlZENhbGxiYWNrKCk7IH1cbiAgICAgIHNhZmVBdHRyaWJ1dGVzLmNvbm5lY3RlZCh0aGlzKTtcbiAgICB9XG5cbiAgICBzdGF0aWMgZ2V0IG9ic2VydmVkQXR0cmlidXRlcygpIHtcbiAgICAgIHJldHVybiBhdHRyaWJ1dGVzRm9yQ2xhc3ModGhpcyk7XG4gICAgfVxuXG4gICAgLyoqXG4gICAgICogU2V0L3Vuc2V0IHRoZSBhdHRyaWJ1dGUgd2l0aCB0aGUgaW5kaWNhdGVkIG5hbWUuXG4gICAgICpcbiAgICAgKiBUaGlzIG1ldGhvZCBleGlzdHMgcHJpbWFyaWx5IHRvIGhhbmRsZSB0aGUgY2FzZSB3aGVyZSBhbiBlbGVtZW50IHdhbnRzIHRvXG4gICAgICogc2V0IGEgZGVmYXVsdCBwcm9wZXJ0eSB2YWx1ZSB0aGF0IHNob3VsZCBiZSByZWZsZWN0ZWQgYXMgYW4gYXR0cmlidXRlLiBBblxuICAgICAqIGltcG9ydGFudCBsaW1pdGF0aW9uIG9mIGN1c3RvbSBlbGVtZW50IGNvbnN0dXJjdG9ycyBpcyB0aGF0IHRoZXkgY2Fubm90XG4gICAgICogc2V0IGF0dHJpYnV0ZXMuIEEgY2FsbCB0byBgcmVmbGVjdEF0dHJpYnV0ZWAgZHVyaW5nIHRoZSBjb25zdHJ1Y3RvciB3aWxsXG4gICAgICogYmUgZGVmZXJyZWQgdW50aWwgdGhlIGVsZW1lbnQgaXMgY29ubmVjdGVkIHRvIHRoZSBkb2N1bWVudC5cbiAgICAgKlxuICAgICAqIEBwYXJhbSB7c3RyaW5nfSBhdHRyaWJ1dGUgLSBUaGUgbmFtZSBvZiB0aGUgKmF0dHJpYnV0ZSogKG5vdCBwcm9wZXJ0eSkgdG8gc2V0LlxuICAgICAqIEBwYXJhbSB7b2JqZWN0fSB2YWx1ZSAtIFRoZSB2YWx1ZSB0byBzZXQuIElmIG51bGwsIHRoZSBhdHRyaWJ1dGUgd2lsbCBiZSByZW1vdmVkLlxuICAgICAqL1xuICAgIHJlZmxlY3RBdHRyaWJ1dGUoYXR0cmlidXRlLCB2YWx1ZSkge1xuICAgICAgcmV0dXJuIHNhZmVBdHRyaWJ1dGVzLnNldEF0dHJpYnV0ZSh0aGlzLCBhdHRyaWJ1dGUsIHZhbHVlKTtcbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBTZXQvdW5zZXQgdGhlIGNsYXNzIHdpdGggdGhlIGluZGljYXRlZCBuYW1lLlxuICAgICAqXG4gICAgICogVGhpcyBtZXRob2QgZXhpc3RzIHByaW1hcmlseSB0byBoYW5kbGUgdGhlIGNhc2Ugd2hlcmUgYW4gZWxlbWVudCB3YW50cyB0b1xuICAgICAqIHNldCBhIGRlZmF1bHQgcHJvcGVydHkgdmFsdWUgdGhhdCBzaG91bGQgYmUgcmVmbGVjdGVkIGFzIGFzIGNsYXNzLiBBblxuICAgICAqIGltcG9ydGFudCBsaW1pdGF0aW9uIG9mIGN1c3RvbSBlbGVtZW50IGNvbnN0dXJjdG9ycyBpcyB0aGF0IHRoZXkgY2Fubm90XG4gICAgICogc2V0IGF0dHJpYnV0ZXMsIGluY2x1ZGluZyB0aGUgYGNsYXNzYCBhdHRyaWJ1dGUuIEEgY2FsbCB0b1xuICAgICAqIGByZWZsZWN0Q2xhc3NgIGR1cmluZyB0aGUgY29uc3RydWN0b3Igd2lsbCBiZSBkZWZlcnJlZCB1bnRpbCB0aGUgZWxlbWVudFxuICAgICAqIGlzIGNvbm5lY3RlZCB0byB0aGUgZG9jdW1lbnQuXG4gICAgICpcbiAgICAgKiBAcGFyYW0ge3N0cmluZ30gY2xhc3NOYW1lIC0gVGhlIG5hbWUgb2YgdGhlIGNsYXNzIHRvIHNldC5cbiAgICAgKiBAcGFyYW0ge29iamVjdH0gdmFsdWUgLSBUcnVlIHRvIHNldCB0aGUgY2xhc3MsIGZhbHNlIHRvIHJlbW92ZSBpdC5cbiAgICAgKi9cbiAgICByZWZsZWN0Q2xhc3MoY2xhc3NOYW1lLCB2YWx1ZSkge1xuICAgICAgcmV0dXJuIHNhZmVBdHRyaWJ1dGVzLnRvZ2dsZUNsYXNzKHRoaXMsIGNsYXNzTmFtZSwgdmFsdWUpO1xuICAgIH1cblxuICB9XG5cbiAgcmV0dXJuIEF0dHJpYnV0ZU1hcnNoYWxsaW5nO1xufTtcblxuXG4vLyBDb252ZXJ0IGh5cGhlbmF0ZWQgZm9vLWJhciBhdHRyaWJ1dGUgbmFtZSB0byBjYW1lbCBjYXNlIGZvb0JhciBwcm9wZXJ0eSBuYW1lLlxuZnVuY3Rpb24gYXR0cmlidXRlVG9Qcm9wZXJ0eU5hbWUoYXR0cmlidXRlTmFtZSkge1xuICBsZXQgcHJvcGVydHlOYW1lID0gYXR0cmlidXRlVG9Qcm9wZXJ0eU5hbWVzW2F0dHJpYnV0ZU5hbWVdO1xuICBpZiAoIXByb3BlcnR5TmFtZSkge1xuICAgIC8vIENvbnZlcnQgYW5kIG1lbW9pemUuXG4gICAgY29uc3QgaHlwZW5SZWdFeCA9IC8tKFthLXpdKS9nO1xuICAgIHByb3BlcnR5TmFtZSA9IGF0dHJpYnV0ZU5hbWUucmVwbGFjZShoeXBlblJlZ0V4LFxuICAgICAgICBtYXRjaCA9PiBtYXRjaFsxXS50b1VwcGVyQ2FzZSgpKTtcbiAgICBhdHRyaWJ1dGVUb1Byb3BlcnR5TmFtZXNbYXR0cmlidXRlTmFtZV0gPSBwcm9wZXJ0eU5hbWU7XG4gIH1cbiAgcmV0dXJuIHByb3BlcnR5TmFtZTtcbn1cblxuZnVuY3Rpb24gYXR0cmlidXRlc0ZvckNsYXNzKGNsYXNzRm4pIHtcblxuICAvLyBXZSB0cmVhdCB0aGUgZWxlbWVudCBiYXNlIGNsYXNzZXMgYXMgaWYgdGhleSBoYXZlIG5vIGF0dHJpYnV0ZXMsIHNpbmNlIHdlXG4gIC8vIGRvbid0IHdhbnQgdG8gcmVjZWl2ZSBhdHRyaWJ1dGVDaGFuZ2VkQ2FsbGJhY2sgZm9yIHRoZW0uXG4gIGlmIChjbGFzc0ZuID09PSBIVE1MRWxlbWVudCB8fCBjbGFzc0ZuID09PSBPYmplY3QpIHtcbiAgICByZXR1cm4gW107XG4gIH1cblxuICAvLyBHZXQgYXR0cmlidXRlcyBmb3IgcGFyZW50IGNsYXNzLlxuICBjb25zdCBiYXNlQ2xhc3MgPSBPYmplY3QuZ2V0UHJvdG90eXBlT2YoY2xhc3NGbi5wcm90b3R5cGUpLmNvbnN0cnVjdG9yO1xuICBjb25zdCBiYXNlQXR0cmlidXRlcyA9IGF0dHJpYnV0ZXNGb3JDbGFzcyhiYXNlQ2xhc3MpO1xuXG4gIC8vIEdldCBhdHRyaWJ1dGVzIGZvciB0aGlzIGNsYXNzLlxuICBjb25zdCBwcm9wZXJ0eU5hbWVzID0gT2JqZWN0LmdldE93blByb3BlcnR5TmFtZXMoY2xhc3NGbi5wcm90b3R5cGUpO1xuICBjb25zdCBzZXR0ZXJOYW1lcyA9IHByb3BlcnR5TmFtZXMuZmlsdGVyKHByb3BlcnR5TmFtZSA9PlxuICAgIHR5cGVvZiBPYmplY3QuZ2V0T3duUHJvcGVydHlEZXNjcmlwdG9yKFxuICAgICAgICBjbGFzc0ZuLnByb3RvdHlwZSwgcHJvcGVydHlOYW1lKS5zZXQgPT09ICdmdW5jdGlvbicpO1xuICBjb25zdCBhdHRyaWJ1dGVzID0gc2V0dGVyTmFtZXMubWFwKHNldHRlck5hbWUgPT5cbiAgICAgIHByb3BlcnR5TmFtZVRvQXR0cmlidXRlKHNldHRlck5hbWUpKTtcblxuICAvLyBNZXJnZS5cbiAgY29uc3QgZGlmZiA9IGF0dHJpYnV0ZXMuZmlsdGVyKGF0dHJpYnV0ZSA9PlxuICAgICAgYmFzZUF0dHJpYnV0ZXMuaW5kZXhPZihhdHRyaWJ1dGUpIDwgMCk7XG4gIHJldHVybiBiYXNlQXR0cmlidXRlcy5jb25jYXQoZGlmZik7XG59XG5cbi8vIENvbnZlcnQgYSBjYW1lbCBjYXNlIGZvb0JhciBwcm9wZXJ0eSBuYW1lIHRvIGEgaHlwaGVuYXRlZCBmb28tYmFyIGF0dHJpYnV0ZS5cbmZ1bmN0aW9uIHByb3BlcnR5TmFtZVRvQXR0cmlidXRlKHByb3BlcnR5TmFtZSkge1xuICBsZXQgYXR0cmlidXRlID0gcHJvcGVydHlOYW1lc1RvQXR0cmlidXRlc1twcm9wZXJ0eU5hbWVdO1xuICBpZiAoIWF0dHJpYnV0ZSkge1xuICAgIC8vIENvbnZlcnQgYW5kIG1lbW9pemUuXG4gICAgY29uc3QgdXBwZXJjYXNlUmVnRXggPSAvKFtBLVpdKS9nO1xuICAgIGF0dHJpYnV0ZSA9IHByb3BlcnR5TmFtZS5yZXBsYWNlKHVwcGVyY2FzZVJlZ0V4LCAnLSQxJykudG9Mb3dlckNhc2UoKTtcbiAgfVxuICByZXR1cm4gYXR0cmlidXRlO1xufVxuIiwiLyogRXhwb3J0ZWQgZnVuY3Rpb24gZXh0ZW5kcyBhIGJhc2UgY2xhc3Mgd2l0aCBDb21wb3NhYmxlLiAqL1xuZXhwb3J0IGRlZmF1bHQgKGJhc2UpID0+IHtcblxuICAvKipcbiAgICogTWl4aW4gdG8gbWFrZSBhIGNsYXNzIG1vcmUgZWFzaWx5IGNvbXBvc2FibGUgd2l0aCBvdGhlciBtaXhpbnMuXG4gICAqXG4gICAqIFRoaXMgbWl4aW4gY29udHJpYnV0ZXMgYSBgY29tcG9zZWAgbWV0aG9kIHRoYXQgYXBwbGllcyBhIHNldCBvZiBtaXhpblxuICAgKiBmdW5jdGlvbnMgYW5kIHJldHVybnMgdGhlIHJlc3VsdGluZyBuZXcgY2xhc3MuIFRoaXMgc3VnYXIgY2FuIG1ha2UgdGhlXG4gICAqIGFwcGxpY2F0aW9uIG9mIG1hbnkgbWl4aW5zIGF0IG9uY2UgZWFzaWVyIHRvIHJlYWQuXG4gICAqL1xuICBjbGFzcyBDb21wb3NhYmxlIGV4dGVuZHMgYmFzZSB7XG5cbiAgICAvKipcbiAgICAgKiBBcHBseSBhIHNldCBvZiBtaXhpbiBmdW5jdGlvbnMgb3IgbWl4aW4gb2JqZWN0cyB0byB0aGUgcHJlc2VudCBjbGFzcyBhbmRcbiAgICAgKiByZXR1cm4gdGhlIG5ldyBjbGFzcy5cbiAgICAgKlxuICAgICAqIEluc3RlYWQgb2Ygd3JpdGluZzpcbiAgICAgKlxuICAgICAqICAgICBsZXQgTXlDbGFzcyA9IE1peGluMShNaXhpbjIoTWl4aW4zKE1peGluNChNaXhpbjUoQmFzZUNsYXNzKSkpKSk7XG4gICAgICpcbiAgICAgKiBZb3UgY2FuIHdyaXRlOlxuICAgICAqXG4gICAgICogICAgIGxldCBNeUNsYXNzID0gQ29tcG9zYWJsZU1peGluKEJhc2VDbGFzcykuY29tcG9zZShcbiAgICAgKiAgICAgICBNaXhpbjEsXG4gICAgICogICAgICAgTWl4aW4yLFxuICAgICAqICAgICAgIE1peGluMyxcbiAgICAgKiAgICAgICBNaXhpbjQsXG4gICAgICogICAgICAgTWl4aW41XG4gICAgICogICAgICk7XG4gICAgICpcbiAgICAgKiBUaGlzIGZ1bmN0aW9uIGNhbiBhbHNvIHRha2UgbWl4aW4gb2JqZWN0cy4gQSBtaXhpbiBvYmplY3QgaXMganVzdCBhXG4gICAgICogc2hvcnRoYW5kIGZvciBhIG1peGluIGZ1bmN0aW9uIHRoYXQgY3JlYXRlcyBhIG5ldyBzdWJjbGFzcyB3aXRoIHRoZSBnaXZlblxuICAgICAqIG1lbWJlcnMuIFRoZSBtaXhpbiBvYmplY3QncyBtZW1iZXJzIGFyZSAqbm90KiBjb3BpZWQgZGlyZWN0bHkgb250byB0aGVcbiAgICAgKiBwcm90b3R5cGUgb2YgdGhlIGJhc2UgY2xhc3MsIGFzIHdpdGggdHJhZGl0aW9uYWwgbWl4aW5zLlxuICAgICAqXG4gICAgICogSW4gYWRkaXRpb24gdG8gcHJvdmlkaW5nIHN5bnRhY3RpYyBzdWdhciwgdGhpcyBtaXhpbiBjYW4gYmUgdXNlZCB0b1xuICAgICAqIGRlZmluZSBhIGNsYXNzIGluIEVTNSwgd2hpY2ggbGFja3MgRVM2J3MgYGNsYXNzYCBrZXl3b3JkLlxuICAgICAqXG4gICAgICogQHBhcmFtIHsuLi5taXhpbnN9IG1peGlucyAtIEEgc2V0IG9mIG1peGluIGZ1bmN0aW9ucyBvciBvYmplY3RzIHRvIGFwcGx5LlxuICAgICAqL1xuICAgIHN0YXRpYyBjb21wb3NlKC4uLm1peGlucykge1xuICAgICAgLy8gV2UgY3JlYXRlIGEgbmV3IHN1YmNsYXNzIGZvciBlYWNoIG1peGluIGluIHR1cm4uIFRoZSByZXN1bHQgYmVjb21lc1xuICAgICAgLy8gdGhlIGJhc2UgY2xhc3MgZXh0ZW5kZWQgYnkgYW55IHN1YnNlcXVlbnQgbWl4aW5zLiBJdCB0dXJucyBvdXQgdGhhdFxuICAgICAgLy8gd2UgY2FuIHVzZSBBcnJheS5yZWR1Y2UoKSB0byBjb25jaXNlbHkgZXhwcmVzcyB0aGlzLCB1c2luZyB0aGUgY3VycmVudFxuICAgICAgLy8gb2JqZWN0IGFzIHRoZSBzZWVkIGZvciByZWR1Y2UoKS5cbiAgICAgIHJldHVybiBtaXhpbnMucmVkdWNlKGNvbXBvc2VDbGFzcywgdGhpcyk7XG4gICAgfVxuXG4gIH1cblxuICByZXR1cm4gQ29tcG9zYWJsZTtcbn07XG5cblxuLy8gUHJvcGVydGllcyBkZWZpbmVkIGJ5IE9iamVjdCB0aGF0IHdlIGRvbid0IHdhbnQgdG8gbWl4aW4uXG5jb25zdCBOT05fTUlYQUJMRV9PQkpFQ1RfUFJPUEVSVElFUyA9IFtcbiAgJ2NvbnN0cnVjdG9yJ1xuXTtcblxuLypcbiAqIEFwcGx5IHRoZSBtaXhpbiB0byB0aGUgZ2l2ZW4gYmFzZSBjbGFzcyB0byByZXR1cm4gYSBuZXcgY2xhc3MuXG4gKiBUaGUgbWl4aW4gY2FuIGVpdGhlciBiZSBhIGZ1bmN0aW9uIHRoYXQgcmV0dXJucyB0aGUgbW9kaWZpZWQgY2xhc3MsIG9yIGFcbiAqIHBsYWluIG9iamVjdCB3aG9zZSBtZW1iZXJzIHdpbGwgYmUgY29waWVkIHRvIHRoZSBuZXcgY2xhc3MnIHByb3RvdHlwZS5cbiAqL1xuZnVuY3Rpb24gY29tcG9zZUNsYXNzKGJhc2UsIG1peGluKSB7XG4gIGlmICh0eXBlb2YgbWl4aW4gPT09ICdmdW5jdGlvbicpIHtcbiAgICAvLyBNaXhpbiBmdW5jdGlvblxuICAgIHJldHVybiBtaXhpbihiYXNlKTtcbiAgfSBlbHNlIHtcbiAgICAvLyBNaXhpbiBvYmplY3RcbiAgICBjbGFzcyBTdWJjbGFzcyBleHRlbmRzIGJhc2Uge31cbiAgICBjb3B5T3duUHJvcGVydGllcyhtaXhpbiwgU3ViY2xhc3MucHJvdG90eXBlLCBOT05fTUlYQUJMRV9PQkpFQ1RfUFJPUEVSVElFUyk7XG4gICAgcmV0dXJuIFN1YmNsYXNzO1xuICB9XG59XG5cblxuLypcbiAqIENvcHkgdGhlIGdpdmVuIHByb3BlcnRpZXMvbWV0aG9kcyB0byB0aGUgdGFyZ2V0LlxuICogUmV0dXJuIHRoZSB1cGRhdGVkIHRhcmdldC5cbiAqL1xuZnVuY3Rpb24gY29weU93blByb3BlcnRpZXMoc291cmNlLCB0YXJnZXQsIGlnbm9yZVByb3BlcnR5TmFtZXMgPSBbXSkge1xuICBPYmplY3QuZ2V0T3duUHJvcGVydHlOYW1lcyhzb3VyY2UpLmZvckVhY2gobmFtZSA9PiB7XG4gICAgaWYgKGlnbm9yZVByb3BlcnR5TmFtZXMuaW5kZXhPZihuYW1lKSA8IDApIHtcbiAgICAgIGNvbnN0IGRlc2NyaXB0b3IgPSBPYmplY3QuZ2V0T3duUHJvcGVydHlEZXNjcmlwdG9yKHNvdXJjZSwgbmFtZSk7XG4gICAgICBPYmplY3QuZGVmaW5lUHJvcGVydHkodGFyZ2V0LCBuYW1lLCBkZXNjcmlwdG9yKTtcbiAgICB9XG4gIH0pO1xuICByZXR1cm4gdGFyZ2V0O1xufVxuIiwiLyogRXhwb3J0ZWQgZnVuY3Rpb24gZXh0ZW5kcyBhIGJhc2UgY2xhc3Mgd2l0aCBEaXN0cmlidXRlZENoaWxkcmVuLiAqL1xuZXhwb3J0IGRlZmF1bHQgKGJhc2UpID0+IHtcblxuICAvKipcbiAgICogTWl4aW4gd2hpY2ggZGVmaW5lcyBoZWxwZXJzIGZvciBhY2Nlc3NpbmcgYSBjb21wb25lbnQncyBkaXN0cmlidXRlZFxuICAgKiBjaGlsZHJlbiBhcyBhIGZsYXR0ZW5lZCBhcnJheSBvciBzdHJpbmcuXG4gICAqXG4gICAqIFRoZSBzdGFuZGFyZCBET00gQVBJIHByb3ZpZGVzIHNldmVyYWwgd2F5cyBvZiBhY2Nlc3NpbmcgY2hpbGQgY29udGVudDpcbiAgICogYGNoaWxkcmVuYCwgYGNoaWxkTm9kZXNgLCBhbmQgYHRleHRDb250ZW50YC4gTm9uZSBvZiB0aGVzZSBmdW5jdGlvbnMgYXJlXG4gICAqIFNoYWRvdyBET00gYXdhcmUuIFRoaXMgbWl4aW4gZGVmaW5lcyB2YXJpYXRpb25zIG9mIHRob3NlIGZ1bmN0aW9ucyB0aGF0XG4gICAqICphcmUqIFNoYWRvdyBET00gYXdhcmUuXG4gICAqXG4gICAqIEV4YW1wbGU6IHlvdSBjcmVhdGUgYSBjb21wb25lbnQgYDxjb3VudC1jaGlsZHJlbj5gIHRoYXQgZGlzcGxheXMgYSBudW1iZXJcbiAgICogZXF1YWwgdG8gdGhlIG51bWJlciBvZiBjaGlsZHJlbiBwbGFjZWQgaW5zaWRlIHRoYXQgY29tcG9uZW50LiBJZiBzb21lb25lXG4gICAqIGluc3RhbnRpYXRlcyB5b3VyIGNvbXBvbmVudCBsaWtlOlxuICAgKlxuICAgKiAgICAgPGNvdW50LWNoaWxkcmVuPlxuICAgKiAgICAgICA8ZGl2PjwvZGl2PlxuICAgKiAgICAgICA8ZGl2PjwvZGl2PlxuICAgKiAgICAgICA8ZGl2PjwvZGl2PlxuICAgKiAgICAgPC9jb3VudC1jaGlsZHJlbj5cbiAgICpcbiAgICogVGhlbiB0aGUgY29tcG9uZW50IHNob3VsZCBzaG93IFwiM1wiLCBiZWNhdXNlIHRoZXJlIGFyZSB0aHJlZSBjaGlsZHJlbi4gVG9cbiAgICogY2FsY3VsYXRlIHRoZSBudW1iZXIgb2YgY2hpbGRyZW4sIHRoZSBjb21wb25lbnQgY2FuIGp1c3QgY2FsY3VsYXRlXG4gICAqIGB0aGlzLmNoaWxkcmVuLmxlbmd0aGAuIEhvd2V2ZXIsIHN1cHBvc2Ugc29tZW9uZSBpbnN0YW50aWF0ZXMgeW91clxuICAgKiBjb21wb25lbnQgaW5zaWRlIG9uZSBvZiB0aGVpciBvd24gY29tcG9uZW50cywgYW5kIHB1dHMgYSBgPHNsb3Q+YCBlbGVtZW50XG4gICAqIGluc2lkZSB5b3VyIGNvbXBvbmVudDpcbiAgICpcbiAgICogICAgIDxjb3VudC1jaGlsZHJlbj5cbiAgICogICAgICAgPHNsb3Q+PC9zbG90PlxuICAgKiAgICAgPC9jb3VudC1jaGlsZHJlbj5cbiAgICpcbiAgICogSWYgeW91ciBjb21wb25lbnQgb25seSBsb29rcyBhdCBgdGhpcy5jaGlsZHJlbmAsIGl0IHdpbGwgYWx3YXlzIHNlZSBleGFjdGx5XG4gICAqIG9uZSBjaGlsZCDigJTCoHRoZSBgPHNsb3Q+YCBlbGVtZW50LiBCdXQgdGhlIHVzZXIgbG9va2luZyBhdCB0aGUgcGFnZSB3aWxsXG4gICAqICpzZWUqIGFueSBub2RlcyBkaXN0cmlidXRlZCB0byB0aGF0IHNsb3QuIFRvIG1hdGNoIHdoYXQgdGhlIHVzZXIgc2VlcywgeW91clxuICAgKiBjb21wb25lbnQgc2hvdWxkIGV4cGFuZCBhbnkgYDxzbG90PmAgZWxlbWVudHMgaXQgY29udGFpbnMuXG4gICAqXG4gICAqIFRoYXQgaXMgdGhlIHByb2JsZW0gdGhpcyBtaXhpbiBzb2x2ZXMuIEFmdGVyIGFwcGx5aW5nIHRoaXMgbWl4aW4sIHlvdXJcbiAgICogY29tcG9uZW50IGNvZGUgaGFzIGFjY2VzcyB0byBgdGhpcy5kaXN0cmlidXRlZENoaWxkcmVuYCwgd2hvc2UgYGxlbmd0aGBcbiAgICogd2lsbCByZXR1cm4gdGhlIHRvdGFsIG51bWJlciBvZiBhbGwgY2hpbGRyZW4gZGlzdHJpYnV0ZWQgdG8geW91ciBjb21wb25lbnRcbiAgICogaW4gdGhlIGNvbXBvc2VkIHRyZWUuXG4gICAqXG4gICAqIE5vdGU6IFRoZSBsYXRlc3QgQ3VzdG9tIEVsZW1lbnRzIEFQSSBkZXNpZ24gY2FsbHMgZm9yIGEgbmV3IGZ1bmN0aW9uLFxuICAgKiBgZ2V0QXNzaWduZWROb2Rlc2AgdGhhdCB0YWtlcyBhbiBvcHRpb25hbCBgZGVlcGAgcGFyYW1ldGVyLCB0aGF0IHdpbGwgc29sdmVcbiAgICogdGhpcyBwcm9ibGVtIGF0IHRoZSBBUEkgbGV2ZWwuXG4gICAqL1xuICBjbGFzcyBEaXN0cmlidXRlZENoaWxkcmVuIGV4dGVuZHMgYmFzZSB7XG5cbiAgICAvKipcbiAgICAgKiBBbiBpbi1vcmRlciBjb2xsZWN0aW9uIG9mIGRpc3RyaWJ1dGVkIGNoaWxkcmVuLCBleHBhbmRpbmcgYW55IHNsb3RcbiAgICAgKiBlbGVtZW50cy4gTGlrZSB0aGUgc3RhbmRhcmQgY2hpbGRyZW4gcHJvcGVydHksIHRoaXMgc2tpcHMgdGV4dCBub2Rlcy5cbiAgICAgKlxuICAgICAqIEB0eXBlIHtIVE1MRWxlbWVudFtdfVxuICAgICAqL1xuICAgIGdldCBkaXN0cmlidXRlZENoaWxkcmVuKCkge1xuICAgICAgcmV0dXJuIGV4cGFuZENvbnRlbnRFbGVtZW50cyh0aGlzLmNoaWxkcmVuLCBmYWxzZSk7XG4gICAgfVxuXG4gICAgLyoqXG4gICAgICogQW4gaW4tb3JkZXIgY29sbGVjdGlvbiBvZiBkaXN0cmlidXRlZCBjaGlsZCBub2RlcywgZXhwYW5kaW5nIGFueSBzbG90XG4gICAgICogZWxlbWVudHMuIExpa2UgdGhlIHN0YW5kYXJkIGNoaWxkTm9kZXMgcHJvcGVydHksIHRoaXMgaW5jbHVkZXMgdGV4dFxuICAgICAqIG5vZGVzLlxuICAgICAqXG4gICAgICogQHR5cGUge05vZGVbXX1cbiAgICAgKi9cbiAgICBnZXQgZGlzdHJpYnV0ZWRDaGlsZE5vZGVzKCkge1xuICAgICAgcmV0dXJuIGV4cGFuZENvbnRlbnRFbGVtZW50cyh0aGlzLmNoaWxkTm9kZXMsIHRydWUpO1xuICAgIH1cblxuICAgIC8qKlxuICAgICAqIFRoZSBjb25jYXRlbmF0ZWQgdGV4dCBjb250ZW50IG9mIGFsbCBkaXN0cmlidXRlZCBjaGlsZCBub2RlcywgZXhwYW5kaW5nXG4gICAgICogYW55IHNsb3QgZWxlbWVudHMuXG4gICAgICpcbiAgICAgKiBAdHlwZSB7c3RyaW5nfVxuICAgICAqL1xuICAgIGdldCBkaXN0cmlidXRlZFRleHRDb250ZW50KCkge1xuICAgICAgY29uc3Qgc3RyaW5ncyA9IHRoaXMuZGlzdHJpYnV0ZWRDaGlsZE5vZGVzLm1hcChmdW5jdGlvbihjaGlsZCkge1xuICAgICAgICByZXR1cm4gY2hpbGQudGV4dENvbnRlbnQ7XG4gICAgICB9KTtcbiAgICAgIHJldHVybiBzdHJpbmdzLmpvaW4oJycpO1xuICAgIH1cblxuICB9XG5cbiAgcmV0dXJuIERpc3RyaWJ1dGVkQ2hpbGRyZW47XG59O1xuXG5cbi8qXG4gKiBHaXZlbiBhIGFycmF5IG9mIG5vZGVzLCByZXR1cm4gYSBuZXcgYXJyYXkgd2l0aCBhbnkgY29udGVudCBlbGVtZW50cyBleHBhbmRlZFxuICogdG8gdGhlIG5vZGVzIGRpc3RyaWJ1dGVkIHRvIHRoYXQgY29udGVudCBlbGVtZW50LiBUaGlzIHJ1bGUgaXMgYXBwbGllZFxuICogcmVjdXJzaXZlbHkuXG4gKlxuICogSWYgaW5jbHVkZVRleHROb2RlcyBpcyB0cnVlLCB0ZXh0IG5vZGVzIHdpbGwgYmUgaW5jbHVkZWQsIGFzIGluIHRoZVxuICogc3RhbmRhcmQgY2hpbGROb2RlcyBwcm9wZXJ0eTsgYnkgZGVmYXVsdCwgdGhpcyBza2lwcyB0ZXh0IG5vZGVzLCBsaWtlIHRoZVxuICogc3RhbmRhcmQgY2hpbGRyZW4gcHJvcGVydHkuXG4gKi9cbmZ1bmN0aW9uIGV4cGFuZENvbnRlbnRFbGVtZW50cyhub2RlcywgaW5jbHVkZVRleHROb2Rlcykge1xuICBjb25zdCBleHBhbmRlZCA9IEFycmF5LnByb3RvdHlwZS5tYXAuY2FsbChub2Rlcywgbm9kZSA9PiB7XG4gICAgLy8gV2Ugd2FudCB0byBzZWUgaWYgdGhlIG5vZGUgaXMgYW4gaW5zdGFuY2VvZiBIVE1MU2xvdEVMZW1lbnQsIGJ1dFxuICAgIC8vIHRoYXQgY2xhc3Mgd29uJ3QgZXhpc3QgaWYgdGhlIGJyb3dzZXIgdGhhdCBkb2Vzbid0IHN1cHBvcnQgbmF0aXZlXG4gICAgLy8gU2hhZG93IERPTSBhbmQgaWYgdGhlIFNoYWRvdyBET00gcG9seWZpbGwgaGFzbid0IGJlZW4gbG9hZGVkLiBJbnN0ZWFkLFxuICAgIC8vIHdlIGRvIGEgc2ltcGxpc3RpYyBjaGVjayB0byBzZWUgaWYgdGhlIHRhZyBuYW1lIGlzIFwic2xvdFwiLlxuICAgIGNvbnN0IGlzU2xvdCA9IHR5cGVvZiBIVE1MU2xvdEVsZW1lbnQgIT09ICd1bmRlZmluZWQnID9cbiAgICAgIG5vZGUgaW5zdGFuY2VvZiBIVE1MU2xvdEVsZW1lbnQgOlxuICAgICAgbm9kZS5sb2NhbE5hbWUgPT09ICdzbG90JztcbiAgICBpZiAoaXNTbG90KSB7XG4gICAgICAvLyBVc2UgdGhlIG5vZGVzIGFzc2lnbmVkIHRvIHRoaXMgbm9kZSBpbnN0ZWFkLlxuICAgICAgY29uc3QgYXNzaWduZWROb2RlcyA9IG5vZGUuYXNzaWduZWROb2Rlcyh7IGZsYXR0ZW46IHRydWUgfSk7XG4gICAgICByZXR1cm4gYXNzaWduZWROb2RlcyA/XG4gICAgICAgIGV4cGFuZENvbnRlbnRFbGVtZW50cyhhc3NpZ25lZE5vZGVzLCBpbmNsdWRlVGV4dE5vZGVzKSA6XG4gICAgICAgIFtdO1xuICAgIH0gZWxzZSBpZiAobm9kZSBpbnN0YW5jZW9mIEhUTUxFbGVtZW50KSB7XG4gICAgICAvLyBQbGFpbiBlbGVtZW50OyB1c2UgYXMgaXMuXG4gICAgICByZXR1cm4gW25vZGVdO1xuICAgIH0gZWxzZSBpZiAobm9kZSBpbnN0YW5jZW9mIFRleHQgJiYgaW5jbHVkZVRleHROb2Rlcykge1xuICAgICAgLy8gVGV4dCBub2RlLlxuICAgICAgcmV0dXJuIFtub2RlXTtcbiAgICB9IGVsc2Uge1xuICAgICAgLy8gQ29tbWVudCwgcHJvY2Vzc2luZyBpbnN0cnVjdGlvbiwgZXRjLjsgc2tpcC5cbiAgICAgIHJldHVybiBbXTtcbiAgICB9XG4gIH0pO1xuICBjb25zdCBmbGF0dGVuZWQgPSBbXS5jb25jYXQoLi4uZXhwYW5kZWQpO1xuICByZXR1cm4gZmxhdHRlbmVkO1xufVxuIiwiLyogRXhwb3J0ZWQgZnVuY3Rpb24gZXh0ZW5kcyBhIGJhc2UgY2xhc3Mgd2l0aCBTaGFkb3dFbGVtZW50UmVmZXJlbmNlcy4gKi9cbmV4cG9ydCBkZWZhdWx0IChiYXNlKSA9PiB7XG5cbiAgLyoqXG4gICAqIE1peGluIHRvIGNyZWF0ZSByZWZlcmVuY2VzIHRvIGVsZW1lbnRzIGluIGEgY29tcG9uZW50J3MgU2hhZG93IERPTSBzdWJ0cmVlLlxuICAgKlxuICAgKiBUaGlzIGFkZHMgYSBtZW1iZXIgb24gdGhlIGNvbXBvbmVudCBjYWxsZWQgYHRoaXMuJGAgdGhhdCBjYW4gYmUgdXNlZCB0b1xuICAgKiByZWZlcmVuY2Ugc2hhZG93IGVsZW1lbnRzIHdpdGggSURzLiBFLmcuLCBpZiBjb21wb25lbnQncyBzaGFkb3cgY29udGFpbnMgYW5cbiAgICogZWxlbWVudCBgPGJ1dHRvbiBpZD1cImZvb1wiPmAsIHRoZW4gdGhpcyBtaXhpbiB3aWxsIGNyZWF0ZSBhIG1lbWJlclxuICAgKiBgdGhpcy4kLmZvb2AgdGhhdCBwb2ludHMgdG8gdGhhdCBidXR0b24uXG4gICAqXG4gICAqIFN1Y2ggcmVmZXJlbmNlcyBzaW1wbGlmeSBhIGNvbXBvbmVudCdzIGFjY2VzcyB0byBpdHMgb3duIGVsZW1lbnRzLiBJblxuICAgKiBleGNoYW5nZSwgdGhpcyBtaXhpbiB0cmFkZXMgb2ZmIGEgb25lLXRpbWUgY29zdCBvZiBxdWVyeWluZyBhbGwgZWxlbWVudHMgaW5cbiAgICogdGhlIHNoYWRvdyB0cmVlIGluc3RlYWQgb2YgcGF5aW5nIGFuIG9uZ29pbmcgY29zdCB0byBxdWVyeSBmb3IgYW4gZWxlbWVudFxuICAgKiBlYWNoIHRpbWUgdGhlIGNvbXBvbmVudCB3YW50cyB0byBpbnNwZWN0IG9yIG1hbmlwdWxhdGUgaXQuXG4gICAqXG4gICAqIFRoaXMgbWl4aW4gZXhwZWN0cyB0aGUgY29tcG9uZW50IHRvIGRlZmluZSBhIFNoYWRvdyBET00gc3VidHJlZS4gWW91IGNhblxuICAgKiBjcmVhdGUgdGhhdCB0cmVlIHlvdXJzZWxmLCBvciBtYWtlIHVzZSBvZlxuICAgKiBbU2hhZG93VGVtcGxhdGVNaXhpbl0oU2hhZG93VGVtcGxhdGVNaXhpbi5tZCkuXG4gICAqXG4gICAqIFRoaXMgbWl4aW4gaXMgaW5zcGlyZWQgYnkgUG9seW1lcidzIFthdXRvbWF0aWNcbiAgICogbm9kZSBmaW5kaW5nXShodHRwczovL3d3dy5wb2x5bWVyLXByb2plY3Qub3JnLzEuMC9kb2NzL2Rldmd1aWRlL2xvY2FsLWRvbS5odG1sI25vZGUtZmluZGluZylcbiAgICogZmVhdHVyZS5cbiAgICovXG4gIGNsYXNzIFNoYWRvd0VsZW1lbnRSZWZlcmVuY2VzIGV4dGVuZHMgYmFzZSB7XG5cbiAgICBjb25zdHJ1Y3RvcigpIHtcbiAgICAgIHN1cGVyKCk7XG4gICAgICBpZiAodGhpcy5zaGFkb3dSb290KSB7XG4gICAgICAgIC8vIExvb2sgZm9yIGVsZW1lbnRzIGluIHRoZSBzaGFkb3cgc3VidHJlZSB0aGF0IGhhdmUgaWQgYXR0cmlidXRlcy5cbiAgICAgICAgLy8gQW4gYWx0ZXJuYXRpdmVseSBpbXBsZW1lbnRhdGlvbiBvZiB0aGlzIG1peGluIHdvdWxkIGJlIHRvIGp1c3QgZGVmaW5lXG4gICAgICAgIC8vIGEgdGhpcy4kIGdldHRlciB0aGF0IGxhemlseSBkb2VzIHRoaXMgc2VhcmNoIHRoZSBmaXJzdCB0aW1lIHNvbWVvbmVcbiAgICAgICAgLy8gdHJpZXMgdG8gYWNjZXNzIHRoaXMuJC4gVGhhdCBtaWdodCBpbnRyb2R1Y2Ugc29tZSBjb21wbGV4aXR5IOKAkyBpZiB0aGVcbiAgICAgICAgLy8gdGhlIHRyZWUgY2hhbmdlZCBhZnRlciBpdCB3YXMgZmlyc3QgcG9wdWxhdGVkLCB0aGUgcmVzdWx0IG9mXG4gICAgICAgIC8vIHNlYXJjaGluZyBmb3IgYSBub2RlIG1pZ2h0IGJlIHNvbWV3aGF0IHVucHJlZGljdGFibGUuXG4gICAgICAgIHRoaXMuJCA9IHt9O1xuICAgICAgICBjb25zdCBub2Rlc1dpdGhJZHMgPSB0aGlzLnNoYWRvd1Jvb3QucXVlcnlTZWxlY3RvckFsbCgnW2lkXScpO1xuICAgICAgICBbXS5mb3JFYWNoLmNhbGwobm9kZXNXaXRoSWRzLCBub2RlID0+IHtcbiAgICAgICAgICBjb25zdCBpZCA9IG5vZGUuZ2V0QXR0cmlidXRlKCdpZCcpO1xuICAgICAgICAgIHRoaXMuJFtpZF0gPSBub2RlO1xuICAgICAgICB9KTtcbiAgICAgIH1cbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBUaGUgY29sbGVjdGlvbiBvZiByZWZlcmVuY2VzIHRvIHRoZSBlbGVtZW50cyB3aXRoIElEcyBpbiBhIGNvbXBvbmVudCdzXG4gICAgICogU2hhZG93IERPTSBzdWJ0cmVlLlxuICAgICAqXG4gICAgICogQHR5cGUge29iamVjdH1cbiAgICAgKiBAbWVtYmVyICRcbiAgICAgKi9cbiAgfVxuXG4gIHJldHVybiBTaGFkb3dFbGVtZW50UmVmZXJlbmNlcztcbn07XG4iLCJpbXBvcnQgc3ltYm9scyBmcm9tICcuLi9zcmMvc3ltYm9scyc7XG5cblxuLyogRXhwb3J0ZWQgZnVuY3Rpb24gZXh0ZW5kcyBhIGJhc2UgY2xhc3Mgd2l0aCBTaGFkb3dUZW1wbGF0ZS4gKi9cbmV4cG9ydCBkZWZhdWx0IChiYXNlKSA9PiB7XG5cbiAgLyoqXG4gICAqIE1peGluIGZvciBzdGFtcGluZyBhIHRlbXBsYXRlIGludG8gYSBTaGFkb3cgRE9NIHN1YnRyZWUgdXBvbiBjb21wb25lbnRcbiAgICogaW5zdGFudGlhdGlvbi5cbiAgICpcbiAgICogVG8gdXNlIHRoaXMgbWl4aW4sIGRlZmluZSBhIGB0ZW1wbGF0ZWAgcHJvcGVydHkgYXMgYSBzdHJpbmcgb3IgSFRNTFxuICAgKiBgPHRlbXBsYXRlPmAgZWxlbWVudDpcbiAgICpcbiAgICogICAgIGNsYXNzIE15RWxlbWVudCBleHRlbmRzIFNoYWRvd1RlbXBsYXRlTWl4aW4oSFRNTEVsZW1lbnQpIHtcbiAgICogICAgICAgZ2V0IFtzeW1ib2xzLnRlbXBsYXRlXSgpIHtcbiAgICogICAgICAgICByZXR1cm4gYEhlbGxvLCA8ZW0+d29ybGQ8L2VtPi5gO1xuICAgKiAgICAgICB9XG4gICAqICAgICB9XG4gICAqXG4gICAqIFdoZW4geW91ciBjb21wb25lbnQgY2xhc3MgaXMgaW5zdGFudGlhdGVkLCBhIHNoYWRvdyByb290IHdpbGwgYmUgY3JlYXRlZCBvblxuICAgKiB0aGUgaW5zdGFuY2UsIGFuZCB0aGUgY29udGVudHMgb2YgdGhlIHRlbXBsYXRlIHdpbGwgYmUgY2xvbmVkIGludG8gdGhlXG4gICAqIHNoYWRvdyByb290LiBJZiB5b3VyIGNvbXBvbmVudCBkb2VzIG5vdCBkZWZpbmUgYSBgdGVtcGxhdGVgIHByb3BlcnR5LCB0aGlzXG4gICAqIG1peGluIGhhcyBubyBlZmZlY3QuXG4gICAqXG4gICAqIEZvciB0aGUgdGltZSBiZWluZywgdGhpcyBleHRlbnNpb24gcmV0YWlucyBzdXBwb3J0IGZvciBTaGFkb3cgRE9NIHYwLiBUaGF0XG4gICAqIHdpbGwgZXZlbnR1YWxseSBiZSBkZXByZWNhdGVkIGFzIGJyb3dzZXJzIChhbmQgdGhlIFNoYWRvdyBET00gcG9seWZpbGwpXG4gICAqIGltcGxlbWVudCBTaGFkb3cgRE9NIHYxLlxuICAgKi9cbiAgY2xhc3MgU2hhZG93VGVtcGxhdGUgZXh0ZW5kcyBiYXNlIHtcblxuICAgIC8qXG4gICAgICogSWYgdGhlIGNvbXBvbmVudCBkZWZpbmVzIGEgdGVtcGxhdGUsIGEgc2hhZG93IHJvb3Qgd2lsbCBiZSBjcmVhdGVkIG9uIHRoZVxuICAgICAqIGNvbXBvbmVudCBpbnN0YW5jZSwgYW5kIHRoZSB0ZW1wbGF0ZSBzdGFtcGVkIGludG8gaXQuXG4gICAgICovXG4gICAgY29uc3RydWN0b3IoKSB7XG4gICAgICBzdXBlcigpO1xuICAgICAgbGV0IHRlbXBsYXRlID0gdGhpc1tzeW1ib2xzLnRlbXBsYXRlXTtcbiAgICAgIC8vIFRPRE86IFNhdmUgdGhlIHByb2Nlc3NlZCB0ZW1wbGF0ZSB3aXRoIHRoZSBjb21wb25lbnQncyBjbGFzcyBwcm90b3R5cGVcbiAgICAgIC8vIHNvIGl0IGRvZXNuJ3QgbmVlZCB0byBiZSBwcm9jZXNzZWQgd2l0aCBldmVyeSBpbnN0YW50aWF0aW9uLlxuICAgICAgaWYgKHRlbXBsYXRlKSB7XG5cbiAgICAgICAgaWYgKHR5cGVvZiB0ZW1wbGF0ZSA9PT0gJ3N0cmluZycpIHtcbiAgICAgICAgICAvLyBVcGdyYWRlIHBsYWluIHN0cmluZyB0byByZWFsIHRlbXBsYXRlLlxuICAgICAgICAgIHRlbXBsYXRlID0gY3JlYXRlVGVtcGxhdGVXaXRoSW5uZXJIVE1MKHRlbXBsYXRlKTtcbiAgICAgICAgfVxuXG4gICAgICAgIGlmICh3aW5kb3cuU2hhZG93RE9NUG9seWZpbGwpIHtcbiAgICAgICAgICBzaGltVGVtcGxhdGVTdHlsZXModGVtcGxhdGUsIHRoaXMubG9jYWxOYW1lKTtcbiAgICAgICAgfVxuXG4gICAgICAgIGNvbnN0IHJvb3QgPSB0aGlzLmF0dGFjaFNoYWRvdyh7IG1vZGU6ICdvcGVuJyB9KTtcbiAgICAgICAgY29uc3QgY2xvbmUgPSBkb2N1bWVudC5pbXBvcnROb2RlKHRlbXBsYXRlLmNvbnRlbnQsIHRydWUpO1xuICAgICAgICByb290LmFwcGVuZENoaWxkKGNsb25lKTtcbiAgICAgIH1cbiAgICB9XG5cbiAgfVxuXG4gIHJldHVybiBTaGFkb3dUZW1wbGF0ZTtcbn07XG5cblxuLy8gQ29udmVydCBhIHBsYWluIHN0cmluZyBvZiBIVE1MIGludG8gYSByZWFsIHRlbXBsYXRlIGVsZW1lbnQuXG5mdW5jdGlvbiBjcmVhdGVUZW1wbGF0ZVdpdGhJbm5lckhUTUwoaW5uZXJIVE1MKSB7XG4gIGNvbnN0IHRlbXBsYXRlID0gZG9jdW1lbnQuY3JlYXRlRWxlbWVudCgndGVtcGxhdGUnKTtcbiAgLy8gUkVWSUVXOiBJcyB0aGVyZSBhbiBlYXNpZXIgd2F5IHRvIGRvIHRoaXM/XG4gIC8vIFdlJ2QgbGlrZSB0byBqdXN0IHNldCBpbm5lckhUTUwgb24gdGhlIHRlbXBsYXRlIGNvbnRlbnQsIGJ1dCBzaW5jZSBpdCdzXG4gIC8vIGEgRG9jdW1lbnRGcmFnbWVudCwgdGhhdCBkb2Vzbid0IHdvcmsuXG4gIGNvbnN0IGRpdiA9IGRvY3VtZW50LmNyZWF0ZUVsZW1lbnQoJ2RpdicpO1xuICBkaXYuaW5uZXJIVE1MID0gaW5uZXJIVE1MO1xuICB3aGlsZSAoZGl2LmNoaWxkTm9kZXMubGVuZ3RoID4gMCkge1xuICAgIHRlbXBsYXRlLmNvbnRlbnQuYXBwZW5kQ2hpbGQoZGl2LmNoaWxkTm9kZXNbMF0pO1xuICB9XG4gIHJldHVybiB0ZW1wbGF0ZTtcbn1cblxuLy8gSW52b2tlIGJhc2ljIHN0eWxlIHNoaW1taW5nIHdpdGggU2hhZG93Q1NTLlxuZnVuY3Rpb24gc2hpbVRlbXBsYXRlU3R5bGVzKHRlbXBsYXRlLCB0YWcpIHtcbiAgd2luZG93LldlYkNvbXBvbmVudHMuU2hhZG93Q1NTLnNoaW1TdHlsaW5nKHRlbXBsYXRlLmNvbnRlbnQsIHRhZyk7XG59XG4iLCIvKipcbiAqIEhlbHBlciBmdW5jdGlvbiB0byBjcmVhdGUgYSBzeW1ib2wgdGhhdCBjYW4gYmUgdXNlZCBmb3IgYXNzb2NpYXRpbmcgcHJpdmF0ZVxuICogZGF0YSB3aXRoIGFuIGVsZW1lbnQuXG4gKlxuICogTWl4aW5zIGFuZCBjb21wb25lbnQgY2xhc3NlcyBvZnRlbiB3YW50IHRvIGFzc29jaWF0ZSBwcml2YXRlIGRhdGEgd2l0aCBhblxuICogZWxlbWVudCBpbnN0YW5jZSwgYnV0IEphdmFTY3JpcHQgZG9lcyBub3QgaGF2ZSBkaXJlY3Qgc3VwcG9ydCBmb3IgdHJ1ZVxuICogcHJpdmF0ZSBwcm9wZXJ0aWVzLiBPbmUgYXBwcm9hY2ggaXMgdG8gdXNlIHRoZVxuICogW1N5bWJvbF0oaHR0cHM6Ly9kZXZlbG9wZXIubW96aWxsYS5vcmcvZW4tVVMvZG9jcy9XZWIvSmF2YVNjcmlwdC9SZWZlcmVuY2UvR2xvYmFsX09iamVjdHMvU3ltYm9sKVxuICogZGF0YSB0eXBlIHRvIHNldCBhbmQgcmV0cmlldmUgZGF0YSBvbiBhbiBlbGVtZW50LlxuICpcbiAqIFVuZm9ydHVuYXRlbHksIHRoZSBTeW1ib2wgdHlwZSBpcyBub3QgYXZhaWxhYmxlIGluIEludGVybmV0IEV4cGxvcmVyIDExLiBUaGVcbiAqIGBjcmVhdGVTeW1ib2xgIGhlbHBlciBmdW5jdGlvbiBleGlzdHMgYXMgYSB3b3JrYXJvdW5kIGZvciBJRSAxMS4gUmF0aGVyIHRoYW5cbiAqIHJldHVybmluZyBhIHRydWUgU3ltYm9sLCBpdCBzaW1wbHkgcmV0dXJucyBhbiB1bmRlcnNjb3JlLXByZWZpeGVkIHN0cmluZy5cbiAqXG4gKiBVc2FnZTpcbiAqXG4gKiAgICAgY29uc3QgZm9vU3ltYm9sID0gY3JlYXRlU3ltYm9sKCdmb28nKTtcbiAqXG4gKiAgICAgY2xhc3MgTXlFbGVtZW50IGV4dGVuZHMgSFRNTEVsZW1lbnQge1xuICogICAgICAgZ2V0IGZvbygpIHtcbiAqICAgICAgICAgcmV0dXJuIHRoaXNbZm9vU3ltYm9sXTtcbiAqICAgICAgIH1cbiAqICAgICAgIHNldCBmb28odmFsdWUpIHtcbiAqICAgICAgICAgdGhpc1tmb29TeW1ib2xdID0gdmFsdWU7XG4gKiAgICAgICB9XG4gKiAgICAgfVxuICpcbiAqIEluIElFIDExLCB0aGlzIHNhbXBsZSB3aWxsIFwiaGlkZVwiIGRhdGEgYmVoaW5kIGFuIGluc3RhbmNlIHByb3BlcnR5IHRoaXMuX2Zvby5cbiAqIFRoZSB1c2Ugb2YgdGhlIHVuZGVyc2NvcmUgaXMgbWVhbnQgdG8gcmVkdWNlIChub3QgZWxpbWluYXRlKSB0aGUgcG90ZW50aWFsXG4gKiBmb3IgbmFtZSBjb25mbGljdHMsIGFuZCBkaXNjb3VyYWdlIChub3QgcHJldmVudCkgZXh0ZXJuYWwgYWNjZXNzIHRvIHRoaXNcbiAqIGRhdGEuIEluIG1vZGVybiBicm93c2VycywgdGhlIGFib3ZlIGNvZGUgd2lsbCBlbGltaW5hdGUgdGhlIHBvdGVudGlhbCBvZlxuICogbmFtaW5nIGNvbmZsaWN0cywgYW5kIGJldHRlciBoaWRlIHRoZSBkYXRhIGJlaGluZCBhIHJlYWwgU3ltYm9sLlxuICpcbiAqIEBmdW5jdGlvbiBjcmVhdGVTeW1ib2xcbiAqIEBwYXJhbSB7c3RyaW5nfSBkZXNjcmlwdGlvbiAtIEEgc3RyaW5nIHRvIGlkZW50aWZ5IHRoZSBzeW1ib2wgd2hlbiBkZWJ1Z2dpbmdcbiAqL1xuZXhwb3J0IGRlZmF1bHQgZnVuY3Rpb24gY3JlYXRlU3ltYm9sKGRlc2NyaXB0aW9uKSB7XG4gIHJldHVybiB0eXBlb2YgU3ltYm9sID09PSAnZnVuY3Rpb24nID9cbiAgICBTeW1ib2woZGVzY3JpcHRpb24pIDpcbiAgICBgXyR7ZGVzY3JpcHRpb259YDtcbn1cbiIsImltcG9ydCBjcmVhdGVTeW1ib2wgZnJvbSAnLi9jcmVhdGVTeW1ib2wnO1xuaW1wb3J0IHRvZ2dsZUNsYXNzIGZyb20gJy4vdG9nZ2xlQ2xhc3MnO1xuXG5cbi8vIFN5bWJvbHMgZm9yIHByaXZhdGUgZGF0YSBtZW1iZXJzIG9uIGFuIGVsZW1lbnQuXG5jb25zdCBzYWZlVG9TZXRBdHRyaWJ1dGVzU3ltYm9sID0gY3JlYXRlU3ltYm9sKCdzYWZlVG9TZXRBdHRyaWJ1dGVzJyk7XG5jb25zdCBwZW5kaW5nQXR0cmlidXRlc1N5bWJvbCA9IGNyZWF0ZVN5bWJvbCgncGVuZGluZ0F0dHJpYnV0ZXMnKTtcbmNvbnN0IHBlbmRpbmdDbGFzc2VzU3ltYm9sID0gY3JlYXRlU3ltYm9sKCdwZW5kaW5nQ2xhc3NlcycpO1xuXG5cbi8qKlxuICogSGVscGVyIGZ1bmN0aW9ucyBmb3IgdXBkYXRpbmcgYXR0cmlidXRlcywgaW5jbHVkaW5nIHRoZSBgY2xhc3NgIGF0dHJpYnV0ZS5cbiAqL1xuZXhwb3J0IGRlZmF1bHQge1xuXG4gIC8qKlxuICAgKiBQZXJmb3JtIGFueSBwZW5kaW5nIHVwZGF0ZXMgdG8gYXR0cmlidXRlcyBhbmQgY2xhc3Nlcy5cbiAgICpcbiAgICogVGhpcyB3cml0ZXMgYW55IGBzZXRBdHRyaWJ1dGVgIG9yIGB0b2dnbGVDbGFzc2AgdmFsdWVzIHRoYXQgd2VyZSBwZXJmb3JtZWRcbiAgICogYmVmb3JlIGFuIGVsZW1lbnQgd2FzIGF0dGFjaGVkIHRvIHRoZSBkb2N1bWVudCBmb3IgdGhlIGZpcnN0IHRpbWUuXG4gICAqXG4gICAqIFRoaXMgbWV0aG9kIHNob3VsZCBiZSBjYWxsZWQgYnkgbWl4aW5zL2NvbXBvbmVudHMgaW4gdGhlaXJcbiAgICogYGNvbm5lY3RlZENhbGxiYWNrYC4gSWYgbXVsaXRwbGUgbWl4aW5zL2NvbXBvbmVudHMgaW52b2tlIHRoaXMgZHVyaW5nIHRoZVxuICAgKiBzYW1lIGBjb25uZWN0ZWRDYWxsYmFja2AsIG9ubHkgdGhlIGZpcnN0IGNhbGwgd2lsbCBoYXZlIGFueSBlZmZlY3QuIFRoZVxuICAgKiBzdWJzZXF1ZW50IGNhbGxzIHdpbGwgYmUgaGFybWxlc3MuXG4gICAqXG4gICAqIEBwYXJhbSB7SFRNTEVsZW1lbnR9IGVsZW1lbnQgLSBUaGUgZWxlbWVudCBiZWluZyBhZGRlZCB0byB0aGUgZG9jdW1lbnQuXG4gICAqL1xuICBjb25uZWN0ZWQoZWxlbWVudCkge1xuICAgIGVsZW1lbnRbc2FmZVRvU2V0QXR0cmlidXRlc1N5bWJvbF0gPSB0cnVlO1xuXG4gICAgLy8gU2V0IGFueSBwZW5kaW5nIGF0dHJpYnV0ZXMuXG4gICAgaWYgKGVsZW1lbnRbcGVuZGluZ0F0dHJpYnV0ZXNTeW1ib2xdKSB7XG4gICAgICBmb3IgKGxldCBhdHRyaWJ1dGUgaW4gZWxlbWVudFtwZW5kaW5nQXR0cmlidXRlc1N5bWJvbF0pIHtcbiAgICAgICAgY29uc3QgdmFsdWUgPSBlbGVtZW50W3BlbmRpbmdBdHRyaWJ1dGVzU3ltYm9sXVthdHRyaWJ1dGVdO1xuICAgICAgICBzZXRBdHRyaWJ1dGVUb0VsZW1lbnQoZWxlbWVudCwgYXR0cmlidXRlLCB2YWx1ZSk7XG4gICAgICB9XG4gICAgICBlbGVtZW50W3BlbmRpbmdBdHRyaWJ1dGVzU3ltYm9sXSA9IG51bGw7XG4gICAgfVxuXG4gICAgLy8gU2V0IGFueSBwZW5kaW5nIGNsYXNzZXMuXG4gICAgaWYgKGVsZW1lbnRbcGVuZGluZ0NsYXNzZXNTeW1ib2xdKSB7XG4gICAgICBmb3IgKGxldCBjbGFzc05hbWUgaW4gZWxlbWVudFtwZW5kaW5nQ2xhc3Nlc1N5bWJvbF0pIHtcbiAgICAgICAgY29uc3QgdmFsdWUgPSBlbGVtZW50W3BlbmRpbmdDbGFzc2VzU3ltYm9sXVtjbGFzc05hbWVdO1xuICAgICAgICB0b2dnbGVDbGFzcyhlbGVtZW50LCBjbGFzc05hbWUsIHZhbHVlKTtcbiAgICAgIH1cbiAgICAgIGVsZW1lbnRbcGVuZGluZ0NsYXNzZXNTeW1ib2xdID0gbnVsbDtcbiAgICB9XG4gIH0sXG5cbiAgLyoqXG4gICAqIFNldC91bnNldCB0aGUgYXR0cmlidXRlIHdpdGggdGhlIGluZGljYXRlZCBuYW1lLlxuICAgKlxuICAgKiBUaGlzIG1ldGhvZCBleGlzdHMgcHJpbWFyaWx5IHRvIGhhbmRsZSB0aGUgY2FzZSB3aGVyZSBhbiBlbGVtZW50IHdhbnRzIHRvXG4gICAqIHNldCBhIGRlZmF1bHQgcHJvcGVydHkgdmFsdWUgdGhhdCBzaG91bGQgYmUgcmVmbGVjdGVkIGFzIGFuIGF0dHJpYnV0ZS4gQW5cbiAgICogaW1wb3J0YW50IGxpbWl0YXRpb24gb2YgY3VzdG9tIGVsZW1lbnQgY29uc3R1cmN0b3JzIGlzIHRoYXQgdGhleSBjYW5ub3RcbiAgICogc2V0IGF0dHJpYnV0ZXMuIEEgY2FsbCB0byBgc2V0QXR0cmlidXRlYCBkdXJpbmcgdGhlIGNvbnN0cnVjdG9yIHdpbGxcbiAgICogYmUgZGVmZXJyZWQgdW50aWwgdGhlIGVsZW1lbnQgaXMgY29ubmVjdGVkIHRvIHRoZSBkb2N1bWVudC5cbiAgICpcbiAgICogQHBhcmFtIHtzdHJpbmd9IGF0dHJpYnV0ZSAtIFRoZSBuYW1lIG9mIHRoZSAqYXR0cmlidXRlKiAobm90IHByb3BlcnR5KSB0byBzZXQuXG4gICAqIEBwYXJhbSB7b2JqZWN0fSB2YWx1ZSAtIFRoZSB2YWx1ZSB0byBzZXQuIElmIG51bGwsIHRoZSBhdHRyaWJ1dGUgd2lsbCBiZSByZW1vdmVkLlxuICAgKi9cbiAgc2V0QXR0cmlidXRlKGVsZW1lbnQsIGF0dHJpYnV0ZSwgdmFsdWUpIHtcbiAgICBpZiAoZWxlbWVudFtzYWZlVG9TZXRBdHRyaWJ1dGVzU3ltYm9sXSkge1xuICAgICAgLy8gU2FmZSB0byBzZXQgYXR0cmlidXRlcyBpbW1lZGlhdGVseS5cbiAgICAgIHNldEF0dHJpYnV0ZVRvRWxlbWVudChlbGVtZW50LCBhdHRyaWJ1dGUsIHZhbHVlKTtcbiAgICB9IGVsc2Uge1xuICAgICAgLy8gRGVmZXIgc2V0dGluZyBhdHRyaWJ1dGVzIHVudGlsIHRoZSBmaXJzdCB0aW1lIHdlJ3JlIGNvbm5lY3RlZC5cbiAgICAgIGlmICghZWxlbWVudFtwZW5kaW5nQXR0cmlidXRlc1N5bWJvbF0pIHtcbiAgICAgICAgZWxlbWVudFtwZW5kaW5nQXR0cmlidXRlc1N5bWJvbF0gPSB7fTtcbiAgICAgIH1cbiAgICAgIGVsZW1lbnRbcGVuZGluZ0F0dHJpYnV0ZXNTeW1ib2xdW2F0dHJpYnV0ZV0gPSB2YWx1ZTtcbiAgICB9XG4gIH0sXG5cbiAgLyoqXG4gICAqIFNldC91bnNldCB0aGUgY2xhc3Mgd2l0aCB0aGUgaW5kaWNhdGVkIG5hbWUuXG4gICAqXG4gICAqIFRoaXMgbWV0aG9kIGV4aXN0cyBwcmltYXJpbHkgdG8gaGFuZGxlIHRoZSBjYXNlIHdoZXJlIGFuIGVsZW1lbnQgd2FudHMgdG9cbiAgICogc2V0IGEgZGVmYXVsdCBwcm9wZXJ0eSB2YWx1ZSB0aGF0IHNob3VsZCBiZSByZWZsZWN0ZWQgYXMgYXMgY2xhc3MuIEFuXG4gICAqIGltcG9ydGFudCBsaW1pdGF0aW9uIG9mIGN1c3RvbSBlbGVtZW50IGNvbnN0dXJjdG9ycyBpcyB0aGF0IHRoZXkgY2Fubm90XG4gICAqIHNldCBhdHRyaWJ1dGVzLCBpbmNsdWRpbmcgdGhlIGBjbGFzc2AgYXR0cmlidXRlLiBBIGNhbGwgdG9cbiAgICogYHRvZ2dsZUNsYXNzYCBkdXJpbmcgdGhlIGNvbnN0cnVjdG9yIHdpbGwgYmUgZGVmZXJyZWQgdW50aWwgdGhlIGVsZW1lbnRcbiAgICogaXMgY29ubmVjdGVkIHRvIHRoZSBkb2N1bWVudC5cbiAgICpcbiAgICogQHBhcmFtIHtzdHJpbmd9IGNsYXNzTmFtZSAtIFRoZSBuYW1lIG9mIHRoZSBjbGFzcyB0byBzZXQuXG4gICAqIEBwYXJhbSB7b2JqZWN0fSB2YWx1ZSAtIFRydWUgdG8gc2V0IHRoZSBjbGFzcywgZmFsc2UgdG8gcmVtb3ZlIGl0LlxuICAgKi9cbiAgdG9nZ2xlQ2xhc3MoZWxlbWVudCwgY2xhc3NOYW1lLCB2YWx1ZSkge1xuICAgIGlmIChlbGVtZW50W3NhZmVUb1NldEF0dHJpYnV0ZXNTeW1ib2xdKSB7XG4gICAgICAvLyBTYWZlIHRvIHNldCBjbGFzcyBpbW1lZGlhdGVseS5cbiAgICAgIHRvZ2dsZUNsYXNzKGVsZW1lbnQsIGNsYXNzTmFtZSwgdmFsdWUpO1xuICAgIH0gZWxzZSB7XG4gICAgICAvLyBEZWZlciBzZXR0aW5nIGNsYXNzIHVudGlsIHRoZSBmaXJzdCB0aW1lIHdlJ3JlIGNvbm5lY3RlZC5cbiAgICAgIGlmICghZWxlbWVudFtwZW5kaW5nQ2xhc3Nlc1N5bWJvbF0pIHtcbiAgICAgICAgZWxlbWVudFtwZW5kaW5nQ2xhc3Nlc1N5bWJvbF0gPSB7fTtcbiAgICAgIH1cbiAgICAgIGVsZW1lbnRbcGVuZGluZ0NsYXNzZXNTeW1ib2xdW2NsYXNzTmFtZV0gPSB2YWx1ZTtcbiAgICB9XG4gIH1cblxufTtcblxuXG4vLyBSZWZsZWN0IHRoZSBhdHRyaWJ1dGUgdG8gdGhlIGdpdmVuIGVsZW1lbnQuXG4vLyBJZiB0aGUgdmFsdWUgaXMgbnVsbCwgcmVtb3ZlIHRoZSBhdHRyaWJ1dGUuXG5mdW5jdGlvbiBzZXRBdHRyaWJ1dGVUb0VsZW1lbnQoZWxlbWVudCwgYXR0cmlidXRlTmFtZSwgdmFsdWUpIHtcbiAgaWYgKHZhbHVlID09PSBudWxsIHx8IHR5cGVvZiB2YWx1ZSA9PT0gJ3VuZGVmaW5lZCcpIHtcbiAgICBlbGVtZW50LnJlbW92ZUF0dHJpYnV0ZShhdHRyaWJ1dGVOYW1lKTtcbiAgfSBlbHNlIHtcbiAgICBjb25zdCB0ZXh0ID0gU3RyaW5nKHZhbHVlKTtcbiAgICAvLyBBdm9pZCByZWN1cnNpdmUgYXR0cmlidXRlQ2hhbmdlZENhbGxiYWNrIGNhbGxzLlxuICAgIGlmIChlbGVtZW50LmdldEF0dHJpYnV0ZShhdHRyaWJ1dGVOYW1lKSAhPT0gdGV4dCkge1xuICAgICAgZWxlbWVudC5zZXRBdHRyaWJ1dGUoYXR0cmlidXRlTmFtZSwgdmFsdWUpO1xuICAgIH1cbiAgfVxufVxuIiwiaW1wb3J0IGNyZWF0ZVN5bWJvbCBmcm9tICcuL2NyZWF0ZVN5bWJvbCc7XG5cbi8qKlxuICogQSBjb2xsZWN0aW9uIG9mIFN5bWJvbCBvYmplY3RzIGZvciBzdGFuZGFyZCBjb21wb25lbnQgcHJvcGVydGllcyBhbmQgbWV0aG9kcy5cbiAqXG4gKiBUaGVzZSBTeW1ib2wgb2JqZWN0cyBhcmUgdXNlZCB0byBhbGxvdyBtaXhpbnMgYW5kIGEgY29tcG9uZW50IHRvIGludGVybmFsbHlcbiAqIGNvbW11bmljYXRlLCB3aXRob3V0IGV4cG9zaW5nIHRoZXNlIHByb3BlcnRpZXMgYW5kIG1ldGhvZHMgaW4gdGhlIGNvbXBvbmVudCdzXG4gKiBwdWJsaWMgQVBJLlxuICpcbiAqIFRvIHVzZSB0aGVzZSBTeW1ib2wgb2JqZWN0cyBpbiB5b3VyIG93biBjb21wb25lbnQsIGluY2x1ZGUgdGhpcyBtb2R1bGUgYW5kXG4gKiB0aGVuIGNyZWF0ZSBhIHByb3BlcnR5IG9yIG1ldGhvZCB3aG9zZSBrZXkgaXMgdGhlIGRlc2lyZWQgU3ltYm9sLlxuICpcbiAqICAgICBpbXBvcnQgJ1NpbmdsZVNlbGVjdGlvbk1peGluJyBmcm9tICdiYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy9TaW5nbGVTZWxlY3Rpb25NaXhpbic7XG4gKiAgICAgaW1wb3J0ICdzeW1ib2xzJyBmcm9tICdiYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy9zeW1ib2xzJztcbiAqXG4gKiAgICAgY2xhc3MgTXlFbGVtZW50IGV4dGVuZHMgU2luZ2xlU2VsZWN0aW9uTWl4aW4oSFRNTEVsZW1lbnQpIHtcbiAqICAgICAgIFtzeW1ib2xzLml0ZW1TZWxlY3RlZF0oaXRlbSwgc2VsZWN0ZWQpIHtcbiAqICAgICAgICAgLy8gVGhpcyB3aWxsIGJlIGludm9rZWQgd2hlbmV2ZXIgYW4gaXRlbSBpcyBzZWxlY3RlZC9kZXNlbGVjdGVkLlxuICogICAgICAgfVxuICogICAgIH1cbiAqXG4gKiBAbW9kdWxlIHN5bWJvbHNcbiAqL1xuY29uc3Qgc3ltYm9scyA9IHtcblxuICAvKipcbiAgICogU3ltYm9sIGZvciB0aGUgYGRlZmF1bHRzYCBwcm9wZXJ0eS5cbiAgICpcbiAgICogVGhpcyBwcm9wZXJ0eSBjYW4gYmUgdXNlZCB0byBzZXQgb3Igb3ZlcnJpZGUgZGVmYXVsdHMgdGhhdCB3aWxsIGJlIGFwcGxpZWRcbiAgICogdG8gYSBuZXcgY29tcG9uZW50IGluc3RhbmNlLiBXaGVuIGltcGxlbWVudGluZyB0aGlzIHByb3BlcnR5LCB0YWtlIGNhcmUgdG9cbiAgICogZmlyc3QgYWNxdWlyZSBhbnkgZGVmYXVsdHMgZGVmaW5lZCBieSB0aGUgc3VwZXJjbGFzcy4gVGhlIHN0YW5kYXJkIGlkaW9tIGlzXG4gICAqIGFzIGZvbGxvd3M6XG4gICAqXG4gICAqICAgICBnZXQgW3N5bWJvbHMuZGVmYXVsdHNdKCkge1xuICAgKiAgICAgICBjb25zdCBkZWZhdWx0cyA9IHN1cGVyW3N5bWJvbHMuZGVmYXVsdHNdIHx8IHt9O1xuICAgKiAgICAgICAvLyBTZXQgb3Igb3ZlcnJpZGUgZGVmYXVsdCB2YWx1ZXMgaGVyZVxuICAgKiAgICAgICBkZWZhdWx0cy5jdXN0b21Qcm9wZXJ0eSA9IGZhbHNlO1xuICAgKiAgICAgICByZXR1cm4gZGVmYXVsdHM7XG4gICAqICAgICB9XG4gICAqXG4gICAqIEB2YXIge29iamVjdH0gZGVmYXVsdHNcbiAgICovXG4gIGRlZmF1bHRzOiBjcmVhdGVTeW1ib2woJ2RlZmF1bHRzJyksXG5cbiAgLyoqXG4gICAqIFN5bWJvbCBmb3IgdGhlIGBkcmFnZ2luZ2AgcHJvcGVydHkuXG4gICAqXG4gICAqIENvbXBvbmVudHMgbGlrZSBjYXJvdXNlbHMgb2Z0ZW4gZGVmaW5lIGFuaW1hdGVkIENTUyB0cmFuc2l0aW9ucyBmb3JcbiAgICogc2xpZGluZyBlZmZlY3RzLiBTdWNoIGEgdHJhbnNpdGlvbiBzaG91bGQgdXN1YWxseSAqbm90KiBiZSBhcHBsaWVkIHdoaWxlXG4gICAqIHRoZSB1c2VyIGlzIGRyYWdnaW5nLCBiZWNhdXNlIGEgQ1NTIGFuaW1hdGlvbiB3aWxsIGludHJvZHVjZSBhIGxhZyB0aGF0XG4gICAqIG1ha2VzIHRoZSBzd2lwZSBmZWVsIHNsdWdnaXNoLiBJbnN0ZWFkLCBhcyBsb25nIGFzIHRoZSB1c2VyIGlzIGRyYWdnaW5nXG4gICAqIHdpdGggdGhlaXIgZmluZ2VyIGRvd24sIHRoZSB0cmFuc2l0aW9uIHNob3VsZCBiZSBzdXBwcmVzc2VkLiBXaGVuIHRoZVxuICAgKiB1c2VyIHJlbGVhc2VzIHRoZWlyIGZpbmdlciwgdGhlIHRyYW5zaXRpb24gY2FuIGJlIHJlc3RvcmVkLCBhbGxvd2luZyB0aGVcbiAgICogYW5pbWF0aW9uIHRvIHNob3cgdGhlIGNhcm91c2VsIHNsaWRpbmcgaW50byBpdHMgZmluYWwgcG9zaXRpb24uXG4gICAqXG4gICAqIEB0eXBlIHtib29sZWFufSB0cnVlIGlmIGEgZHJhZyBpcyBpbiBwcm9ncmVzcywgZmFsc2UgaWYgbm90LlxuICAgKi9cbiAgZHJhZ2dpbmc6IGNyZWF0ZVN5bWJvbCgnZHJhZ2dpbmcnKSxcblxuICAvKipcbiAgICogU3ltYm9sIGZvciB0aGUgYGdvRG93bmAgbWV0aG9kLlxuICAgKlxuICAgKiBUaGlzIG1ldGhvZCBpcyBpbnZva2VkIHdoZW4gdGhlIHVzZXIgd2FudHMgdG8gZ28vbmF2aWdhdGUgZG93bi5cbiAgICpcbiAgICogQGZ1bmN0aW9uIGdvRG93blxuICAgKi9cbiAgZ29Eb3duOiBjcmVhdGVTeW1ib2woJ2dvRG93bicpLFxuXG4gIC8qKlxuICAgKiBTeW1ib2wgZm9yIHRoZSBgZ29FbmRgIG1ldGhvZC5cbiAgICpcbiAgICogVGhpcyBtZXRob2QgaXMgaW52b2tlZCB3aGVuIHRoZSB1c2VyIHdhbnRzIHRvIGdvL25hdmlnYXRlIHRvIHRoZSBlbmQgKGUuZy4sXG4gICAqIG9mIGEgbGlzdCkuXG4gICAqXG4gICAqIEBmdW5jdGlvbiBnb0VuZFxuICAgKi9cbiAgZ29FbmQ6IGNyZWF0ZVN5bWJvbCgnZ29FbmQnKSxcblxuICAvKipcbiAgICogU3ltYm9sIGZvciB0aGUgYGdvTGVmdGAgbWV0aG9kLlxuICAgKlxuICAgKiBUaGlzIG1ldGhvZCBpcyBpbnZva2VkIHdoZW4gdGhlIHVzZXIgd2FudHMgdG8gZ28vbmF2aWdhdGUgbGVmdC5cbiAgICpcbiAgICogQGZ1bmN0aW9uIGdvTGVmdFxuICAgKi9cbiAgZ29MZWZ0OiBjcmVhdGVTeW1ib2woJ2dvTGVmdCcpLFxuXG4gIC8qKlxuICAgKiBTeW1ib2wgZm9yIHRoZSBgZ29SaWdodGAgbWV0aG9kLlxuICAgKlxuICAgKiBUaGlzIG1ldGhvZCBpcyBpbnZva2VkIHdoZW4gdGhlIHVzZXIgd2FudHMgdG8gZ28vbmF2aWdhdGUgcmlnaHQuXG4gICAqXG4gICAqIEBmdW5jdGlvbiBnb1JpZ2h0XG4gICAqL1xuICBnb1JpZ2h0OiBjcmVhdGVTeW1ib2woJ2dvUmlnaHQnKSxcblxuICAvKipcbiAgICogU3ltYm9sIGZvciB0aGUgYGdvU3RhcnRgIG1ldGhvZC5cbiAgICpcbiAgICogVGhpcyBtZXRob2QgaXMgaW52b2tlZCB3aGVuIHRoZSB1c2VyIHdhbnRzIHRvIGdvL25hdmlnYXRlIHRvIHRoZSBzdGFydFxuICAgKiAoZS5nLiwgb2YgYSBsaXN0KS5cbiAgICpcbiAgICogQGZ1bmN0aW9uIGdvU3RhcnRcbiAgICovXG4gIGdvU3RhcnQ6IGNyZWF0ZVN5bWJvbCgnZ29TdGFydCcpLFxuXG4gIC8qKlxuICAgKiBTeW1ib2wgZm9yIHRoZSBgZ29VcGAgbWV0aG9kLlxuICAgKlxuICAgKiBUaGlzIG1ldGhvZCBpcyBpbnZva2VkIHdoZW4gdGhlIHVzZXIgd2FudHMgdG8gZ28vbmF2aWdhdGUgdXAuXG4gICAqXG4gICAqIEBmdW5jdGlvbiBnb1VwXG4gICAqL1xuICBnb1VwOiBjcmVhdGVTeW1ib2woJ2dvVXAnKSxcblxuICAvKipcbiAgICogU3ltYm9sIGZvciB0aGUgYGl0ZW1BZGRlZGAgbWV0aG9kLlxuICAgKlxuICAgKiBUaGlzIG1ldGhvZCBpcyBpbnZva2VkIHdoZW4gYSBuZXcgaXRlbSBpcyBhZGRlZCB0byBhIGxpc3QuXG4gICAqXG4gICAqIEBmdW5jdGlvbiBpdGVtQWRkZWRcbiAgICogQHBhcmFtIHtIVE1MRWxlbWVudH0gaXRlbSAtIHRoZSBpdGVtIGJlaW5nIHNlbGVjdGVkL2Rlc2VsZWN0ZWRcbiAgICovXG4gIGl0ZW1BZGRlZDogY3JlYXRlU3ltYm9sKCdpdGVtQWRkZWQnKSxcblxuXG4gIC8qKlxuICAgKiBTeW1ib2wgZm9yIHRoZSBgaXRlbXNDaGFuZ2VkYCBtZXRob2QuXG4gICAqXG4gICAqIFRoaXMgbWV0aG9kIGlzIGludm9rZWQgd2hlbiB0aGUgdW5kZXJseWluZyBjb250ZW50cyBjaGFuZ2UuIEl0IGlzIGFsc29cbiAgICogaW52b2tlZCBvbiBjb21wb25lbnQgaW5pdGlhbGl6YXRpb24g4oCTIHNpbmNlIHRoZSBpdGVtcyBoYXZlIFwiY2hhbmdlZFwiIGZyb21cbiAgICogYmVpbmcgbm90aGluZy5cbiAgICovXG4gIGl0ZW1zQ2hhbmdlZDogY3JlYXRlU3ltYm9sKCdpdGVtc0NoYW5nZWQnKSxcblxuICAvKipcbiAgICogU3ltYm9sIGZvciB0aGUgYGl0ZW1TZWxlY3RlZGAgbWV0aG9kLlxuICAgKlxuICAgKiBUaGlzIG1ldGhvZCBpcyBpbnZva2VkIHdoZW4gYW4gaXRlbSBiZWNvbWVzIHNlbGVjdGVkIG9yIGRlc2VsZWN0ZWQuXG4gICAqXG4gICAqIEBmdW5jdGlvbiBpdGVtU2VsZWN0ZWRcbiAgICogQHBhcmFtIHtIVE1MRWxlbWVudH0gaXRlbSAtIHRoZSBpdGVtIGJlaW5nIHNlbGVjdGVkL2Rlc2VsZWN0ZWRcbiAgICogQHBhcmFtIHtib29sZWFufSBzZWxlY3RlZCAtIHRydWUgaWYgdGhlIGl0ZW0gaXMgc2VsZWN0ZWQsIGZhbHNlIGlmIG5vdFxuICAgKi9cbiAgaXRlbVNlbGVjdGVkOiBjcmVhdGVTeW1ib2woJ2l0ZW1TZWxlY3RlZCcpLFxuXG4gIC8qKlxuICAgKiBTeW1ib2wgZm9yIHRoZSBga2V5ZG93bmAgbWV0aG9kLlxuICAgKlxuICAgKiBUaGlzIG1ldGhvZCBpcyBpbnZva2VkIHdoZW4gYW4gZWxlbWVudCByZWNlaXZlcyBhIGBrZXlkb3duYCBldmVudC5cbiAgICpcbiAgICogQGZ1bmN0aW9uIGtleWRvd25cbiAgICogQHBhcmFtIHtLZXlib2FyZEV2ZW50fSBldmVudCAtIHRoZSBldmVudCBiZWluZyBwcm9jZXNzZWRcbiAgICovXG4gIGtleWRvd246IGNyZWF0ZVN5bWJvbCgna2V5ZG93bicpLFxuXG4gIC8qKlxuICAgKiBTeW1ib2wgZm9yIHRoZSBgdGVtcGxhdGVgIHByb3BlcnR5LlxuICAgKlxuICAgKiBUaGlzIHByb3BlcnR5IHJldHVybnMgYSBjb21wb25lbnQncyB0ZW1wbGF0ZS5cbiAgICpcbiAgICogQHR5cGUge3N0cmluZ3xIVE1MRWxlbWVudH1cbiAgICovXG4gIHRlbXBsYXRlOiBjcmVhdGVTeW1ib2woJ3RlbXBsYXRlJylcbn07XG5cbmV4cG9ydCBkZWZhdWx0IHN5bWJvbHM7XG4iLCIvKipcbiAqIEhlbHBlciBmdW5jdGlvbiBmb3Igc3RhbmRhcmQgY2xhc3NMaXN0LnRvZ2dsZSgpIGJlaGF2aW9yIG9uIG9sZCBicm93c2VycyxcbiAqIG5hbWVseSBJRSAxMS5cbiAqXG4gKiBUaGUgc3RhbmRhcmRcbiAqIFtjbGFzc2xpc3RdKGh0dHBzOi8vZGV2ZWxvcGVyLm1vemlsbGEub3JnL2VuLVVTL2RvY3MvV2ViL0FQSS9FbGVtZW50L2NsYXNzTGlzdClcbiAqIG9iamVjdCBoYXMgYSBgdG9nZ2xlKClgIGZ1bmN0aW9uIHRoYXQgc3VwcG9ydHMgYSBzZWNvbmQgQm9vbGVhbiBwYXJhbWV0ZXJcbiAqIHRoYXQgY2FuIGJlIHVzZWQgdG8gc3VjY2luY3RseSB0dXJuIGEgY2xhc3Mgb24gb3Igb2ZmLiBUaGlzIGZlYXR1cmUgaXMgb2Z0ZW5cbiAqIHVzZWZ1bCBpbiBkZXNpZ25pbmcgY3VzdG9tIGVsZW1lbnRzLCB3aGljaCBtYXkgd2FudCB0byBleHRlcm5hbGx5IHJlZmxlY3RcbiAqIGNvbXBvbmVudCBzdGF0ZSBpbiBhIENTUyBjbGFzcyB0aGF0IGNhbiBiZSB1c2VkIGZvciBzdHlsaW5nIHB1cnBvc2VzLlxuICpcbiAqIFVuZm9ydHVuYXRlbHksIElFIDExIGRvZXMgbm90IHN1cHBvcnQgdGhlIEJvb2xlYW4gcGFyYW1ldGVyIHRvXG4gKiBgY2xhc3NMaXN0LnRvZ2dsZSgpYC4gVGhpcyBoZWxwZXIgZnVuY3Rpb24gYmVoYXZlcyBsaWtlIHRoZSBzdGFuZGFyZFxuICogYHRvZ2dsZSgpYCwgaW5jbHVkaW5nIHN1cHBvcnQgZm9yIHRoZSBCb29sZWFuIHBhcmFtZXRlciwgc28gdGhhdCBpdCBjYW4gYmVcbiAqIHVzZWQgZXZlbiBvbiBJRSAxMS5cbiAqXG4gKiBAZnVuY3Rpb24gdG9nZ2xlQ2xhc3NcbiAqIEBwYXJhbSB7SFRNTEVsZW1lbnR9IGVsZW1lbnQgLSBUaGUgZWxlbWVudCB0byBtb2RpZnlcbiAqIEBwYXJhbSB7c3RyaW5nfSBjbGFzc05hbWUgLSBUaGUgY2xhc3MgdG8gYWRkL3JlbW92ZVxuICogQHBhcmFtIHtib29sZWFufSBbZm9yY2VdIC0gRm9yY2UgdGhlIGNsYXNzIHRvIGJlIGFkZGVkIChpZiB0cnVlKSBvciByZW1vdmVkXG4gKiAgICAgICAgICAgICAgICAgICAgICAgICAgICAoaWYgZmFsc2UpXG4gKi9cbmV4cG9ydCBkZWZhdWx0IGZ1bmN0aW9uIHRvZ2dsZUNsYXNzKGVsZW1lbnQsIGNsYXNzTmFtZSwgZm9yY2UpIHtcbiAgY29uc3QgY2xhc3NMaXN0ID0gZWxlbWVudC5jbGFzc0xpc3Q7XG4gIGNvbnN0IGFkZENsYXNzID0gKHR5cGVvZiBmb3JjZSA9PT0gJ3VuZGVmaW5lZCcpID9cbiAgICAhY2xhc3NMaXN0LmNvbnRhaW5zKGNsYXNzTmFtZSkgOlxuICAgIGZvcmNlO1xuICBpZiAoYWRkQ2xhc3MpIHtcbiAgICBjbGFzc0xpc3QuYWRkKGNsYXNzTmFtZSk7XG4gIH0gZWxzZSB7XG4gICAgY2xhc3NMaXN0LnJlbW92ZShjbGFzc05hbWUpO1xuICB9XG4gIHJldHVybiBhZGRDbGFzcztcbn1cbiIsIi8qXG4gKiBUaGlzIGZpbGUgaXMgdHJhbnNwaWxlZCB0byBjcmVhdGUgYW4gRVM1LWNvbXBhdGlibGUgZGlzdHJpYnV0aW9uIGluIHdoaWNoXG4gKiB0aGUgcGFja2FnZSdzIG1haW4gZmVhdHVyZShzKSBhcmUgYXZhaWxhYmxlIHZpYSB0aGUgd2luZG93LkJhc2ljIGdsb2JhbC5cbiAqIElmIHlvdSdyZSBhbHJlYWR5IHVzaW5nIEVTNiB5b3Vyc2VsZiwgaWdub3JlIHRoaXMgZmlsZSwgYW5kIGluc3RlYWQgaW1wb3J0XG4gKiB0aGUgc291cmNlIGZpbGUocykgeW91IHdhbnQgZnJvbSB0aGUgc3JjIGZvbGRlci5cbiAqL1xuXG5pbXBvcnQgQ3VycmVudEFuY2hvciBmcm9tICcuL3NyYy9DdXJyZW50QW5jaG9yJztcblxud2luZG93LkJhc2ljID0gd2luZG93LkJhc2ljIHx8IHt9O1xud2luZG93LkJhc2ljLkN1cnJlbnRBbmNob3IgPSBDdXJyZW50QW5jaG9yO1xuIiwiaW1wb3J0IGNyZWF0ZVN5bWJvbCBmcm9tICcuLi8uLi9iYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy9jcmVhdGVTeW1ib2wnO1xuaW1wb3J0IHNhZmVBdHRyaWJ1dGVzIGZyb20gJy4uLy4uL2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL3NhZmVBdHRyaWJ1dGVzJztcbmltcG9ydCBzeW1ib2xzIGZyb20gJy4uLy4uL2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL3N5bWJvbHMnO1xuaW1wb3J0IFdyYXBwZWRTdGFuZGFyZEVsZW1lbnQgZnJvbSAnLi4vLi4vYmFzaWMtd3JhcHBlZC1zdGFuZGFyZC1lbGVtZW50L3NyYy9XcmFwcGVkU3RhbmRhcmRFbGVtZW50JztcblxuXG4vLyBTeW1ib2xzIGZvciBwcml2YXRlIGRhdGEgbWVtYmVycyBvbiBhbiBlbGVtZW50LlxuY29uc3QgYXJlYUxpbmtTeW1ib2wgPSBjcmVhdGVTeW1ib2woJ2FyZWFMaW5rJyk7XG5cblxuLyoqXG4gKiBBbiBhbmNob3IgKGxpbmspIHRoYXQgaGlnaGxpZ2h0cyBpdHNlbGYgd2hlbiBpdHMgZGVzdGluYXRpb24gbWF0Y2hlcyB0aGVcbiAqIGN1cnJlbnQgbG9jYXRpb24uXG4gKlxuICogW0xpdmUgZGVtb10oaHR0cDovL2Jhc2ljd2ViY29tcG9uZW50cy5vcmcvYmFzaWMtd2ViLWNvbXBvbmVudHMvcGFja2FnZXMvYmFzaWMtY3VycmVudC1hbmNob3IvKVxuICpcbiAqIFN1Y2ggYSBsaW5rIGNvbW1vbmx5IGFwcGVhcnMgaW4gdG9vbGJhcnMsIHNpZGUgYmFycywgYW5kIG90aGVyIG5hdmlnYXRpb25cbiAqIGVsZW1lbnRzLiBJbiB0aGVzZSBzaXR1YXRpb25zLCB5b3UgZ2VuZXJhbGx5IHdhbnQgdGhlIHVzZXIgdG8gdW5kZXJzdGFuZCB3aGF0XG4gKiBwYWdlIG9yIGFyZWEgdGhlIHVzZXIgaXMgYWxyZWFkeSBvbi5cbiAqXG4gKiBXaGVuIHRoZSBsaW5rIGlzIGN1cnJlbnQg4oCUIHdoZW4gaXQgcG9pbnRzIHRvIHRoZSBjdXJyZW50IGxvY2F0aW9uIOKAlCB0aGVcbiAqIGxpbmsgd2lsbCBoYXZlIHRoZSBDU1MgYGN1cnJlbnRgIGNsYXNzIGFwcGxpZWQgdG8gaXQsIGFuZCBpdHMgYGN1cnJlbnRgXG4gKiBwcm9wZXJ0eSB3aWxsIGJlIHRydWUuXG4gKlxuICogTm90ZTogb25lIGxpbWl0YXRpb24gb2YgdGhpcyBjb21wb25lbnQgaXMgdGhhdCwgYnkgZGVmYXVsdCwgdGhlIGxpbmsgZG9lc1xuICogKm5vdCogc2hvdyB0aGUgc3RhbmRhcmQgbGluayBjb2xvciAodXN1YWxseSBibHVlKSBhbmQgdGV4dCBkZWNvcmF0aW9uXG4gKiAodW5kZXJsaW5lKS4gSG93ZXZlciwgaW4gbmF2aWdhdGlvbiBlbGVtZW50cyBsaWtlIHRvb2xiYXJzLCB5b3Ugb2Z0ZW4gd2lsbFxuICogd2FudCB0byBleHBsaWNpdGx5IHNwZWNpZmljIGxpbmsgY29sb3JzIGFueXdheSwgZS5nLiwgdG8gcmVmbGVjdCB5b3VyXG4gKiBhcHBsaWNhdGlvbidzIHZpc3VhbCBzdHlsZSBhbmQgYnJhbmQuXG4gKi9cbmNsYXNzIEN1cnJlbnRBbmNob3IgZXh0ZW5kcyBXcmFwcGVkU3RhbmRhcmRFbGVtZW50LndyYXAoJ2EnKSB7XG5cbiAgY29uc3RydWN0b3IoKSB7XG4gICAgc3VwZXIoKTtcblxuICAgIHdpbmRvdy5hZGRFdmVudExpc3RlbmVyKCdwb3BzdGF0ZScsIGV2ZW50ID0+IHtcbiAgICAgIHJlZnJlc2godGhpcyk7XG4gICAgfSk7XG5cbiAgICAvLyBTdHVwaWQgRWRnZS9JRSBcInN1cHBvcnRcIiBwb3BzdGF0ZSwgYnV0IGRvbid0IGZpcmUgaXQgb24gaGFzaGNoYW5nZS5cbiAgICAvLyBTbyB3ZSBoYXZlIHRvIGxpc3RlbiBmb3IgaGFzaGNoYW5nZSBhcyB3ZWxsLCB3aXRoIHRoZSByZXN1bHQgdGhhdCBhXG4gICAgLy8gc3RhbmRhcmRzLWNvbXBsaWFudCBicm93c2VyIG1heSBlbmQgdXAgcmVmcmVzaGluZyB0aGUgbGluayB0d2ljZS5cbiAgICB3aW5kb3cuYWRkRXZlbnRMaXN0ZW5lcignaGFzaGNoYW5nZScsIGV2ZW50ID0+IHtcbiAgICAgIHJlZnJlc2godGhpcyk7XG4gICAgfSk7XG5cbiAgICAvLyBTZXQgZGVmYXVsdHMuXG4gICAgaWYgKHR5cGVvZiB0aGlzLmFyZWFMaW5rID09PSAndW5kZWZpbmVkJykge1xuICAgICAgdGhpcy5hcmVhTGluayA9IHRoaXNbc3ltYm9scy5kZWZhdWx0c10uYXJlYUxpbms7XG4gICAgfVxuICB9XG5cbiAgLyoqXG4gICAqIFRydWUgaWYgdGhlIGxpbmsgcG9pbnRzIHRvIGFuIGFyZWEgd2l0aGluIGEgc2l0ZSwgbm90IGp1c3QgYSBzaW5nbGUgcGFnZS5cbiAgICpcbiAgICogSWYgdHJ1ZSwgdGhlIG1hdGNoaW5nIHJ1bGUgdG8gZGV0ZXJtaW5lIHdoZXRoZXIgdGhlIGxpbmsgaXMgY3VycmVudCBjaGFuZ2VzOlxuICAgKiBhbiBhcmVhIGxpbmsgaXMgY29uc2lkZXJlZCB0byBiZSBjdXJyZW50IGlmIHRoZSBsaW5rJ3MgZGVzdGluYXRpb24gZm9ybXMgYVxuICAgKiBwcmVmaXggb2YgdGhlIGN1cnJlbnQgbG9jYXRpb24gKGluc3RlYWQgb2YgbWF0Y2hpbmcgdGhlIGNvbXBsZXRlIFVSTCkuXG4gICAqXG4gICAqIEB0eXBlIHtib29sZWFufVxuICAgKi9cbiAgZ2V0IGFyZWFMaW5rKCkge1xuICAgIHJldHVybiB0aGlzW2FyZWFMaW5rU3ltYm9sXTtcbiAgfVxuICBzZXQgYXJlYUxpbmsodmFsdWUpIHtcbiAgICAvLyBDYXN0IGJvb2xlYW4gb3Igc3RyaW5nIHZhbHVlcyB0byBib29sZWFuLlxuICAgIHRoaXNbYXJlYUxpbmtTeW1ib2xdID0gKFN0cmluZyh2YWx1ZSkgPT09ICd0cnVlJyk7XG4gICAgcmVmcmVzaCh0aGlzKTtcbiAgfVxuXG4gIGNvbm5lY3RlZENhbGxiYWNrKCkge1xuICAgIGlmIChzdXBlci5jb25uZWN0ZWRDYWxsYmFjaykgeyBzdXBlci5jb25uZWN0ZWRDYWxsYmFjaygpOyB9XG4gICAgc2FmZUF0dHJpYnV0ZXMuY29ubmVjdGVkKHRoaXMpO1xuICAgIHJlZnJlc2godGhpcyk7XG4gIH1cblxuICAvKipcbiAgICogVHJ1ZSBpZiB0aGUgbGluaydzIGRlc3RpbmF0aW9uIG1hdGNoZXMgdGhlIGN1cnJlbnQgcGFnZSBsb2NhdGlvbi5cbiAgICpcbiAgICogSWYgdGhpcyBpcyB0cnVlLCB0aGUgZWxlbWVudCB3aWxsIGhhdmUgYW4gYGN1cnJlbnRgIENTUyBjbGFzcyBhcHBsaWVkIHRvIGl0LlxuICAgKlxuICAgKiBAdHlwZSB7Ym9vbGVhbn1cbiAgICovXG4gIGdldCBjdXJyZW50KCkge1xuICAgIHJldHVybiB0aGlzLmNsYXNzTGlzdC5jb250YWlucygnY3VycmVudCcpO1xuICB9XG4gIHNldCBjdXJyZW50KHZhbHVlKSB7XG4gICAgc2FmZUF0dHJpYnV0ZXMudG9nZ2xlQ2xhc3ModGhpcywgJ2N1cnJlbnQnLCB2YWx1ZSk7XG4gICAgdGhpcy5kaXNwYXRjaEV2ZW50KG5ldyBDdXN0b21FdmVudCgnY3VycmVudC1jaGFuZ2VkJykpO1xuICB9XG5cbiAgZ2V0IFtzeW1ib2xzLmRlZmF1bHRzXSgpIHtcbiAgICBjb25zdCBkZWZhdWx0cyA9IHN1cGVyW3N5bWJvbHMuZGVmYXVsdHNdIHx8IHt9O1xuICAgIGRlZmF1bHRzLmFyZWFMaW5rID0gZmFsc2U7XG4gICAgcmV0dXJuIGRlZmF1bHRzO1xuICB9XG5cbiAgLy8gQXVnbWVudCBocmVmIGltcGxlbWVudGF0aW9uIHNvIHRoYXQgY2hhbmdpbmcgaHJlZiBjaGVja3MgdGhlIGFjdGl2ZSBzdGF0dXMuXG4gIGdldCBocmVmKCkge1xuICAgIHJldHVybiBzdXBlci5ocmVmO1xuICB9XG4gIHNldCBocmVmKHZhbHVlKSB7XG4gICAgc3VwZXIuaHJlZiA9IHZhbHVlO1xuICAgIHJlZnJlc2godGhpcyk7XG4gIH1cblxuICBnZXQgW3N5bWJvbHMudGVtcGxhdGVdKCkge1xuICAgIC8vIFJlc2V0IHN0eWxlcyBzbyB0aGF0IGNvbG9yIGNhbiBiZSBzcGVjaWZpZWQgZnJvbSB0aGUgb3V0c2lkZSB3aXRob3V0XG4gICAgLy8gaGF2aW5nIHRvIGRlZmluZSBhIENTUyB2YXJpYWJsZS5cbiAgICByZXR1cm4gYFxuICAgICAgPHN0eWxlPlxuICAgICAgOmhvc3Qge1xuICAgICAgICBkaXNwbGF5OiBpbmxpbmUtYmxvY2s7XG4gICAgICB9XG5cbiAgICAgICNpbm5lciB7XG4gICAgICAgIGNvbG9yOiBpbmhlcml0O1xuICAgICAgICBkaXNwbGF5OiBpbmxpbmUtYmxvY2s7XG4gICAgICAgIHRleHQtZGVjb3JhdGlvbjogaW5oZXJpdDtcbiAgICAgIH1cbiAgICAgIDwvc3R5bGU+XG4gICAgICA8YSBpZD1cImlubmVyXCI+PHNsb3Q+PC9zbG90PjwvYT5gO1xuICB9XG5cbn1cblxuXG4vLyBVcGRhdGUgdGhlIGN1cnJlbnQgc3RhdHVzIG9mIHRoZSBlbGVtZW50IGJhc2VkIG9uIHRoZSBjdXJyZW50IGxvY2F0aW9uLlxuZnVuY3Rpb24gcmVmcmVzaChlbGVtZW50KSB7XG4gIGNvbnN0IHVybCA9IHdpbmRvdy5sb2NhdGlvbi5ocmVmO1xuICBsZXQgbWF0Y2g7XG4gIGlmIChlbGVtZW50LmFyZWFMaW5rKSB7XG4gICAgLy8gTWF0Y2ggcHJlZml4XG4gICAgbGV0IHByZWZpeCA9IGVsZW1lbnQuaHJlZjtcbiAgICAvLyBJZiBwcmVmaXggZG9lc24ndCBlbmQgaW4gc2xhc2gsIGFkZCBhIHNsYXNoLlxuICAgIC8vIFdlIHdhbnQgdG8gYXZvaWQgbWF0Y2hpbmcgaW4gdGhlIG1pZGRsZSBvZiBhIGZvbGRlciBuYW1lLlxuICAgIGlmIChwcmVmaXgubGVuZ3RoIDwgdXJsLmxlbmd0aCAmJiBwcmVmaXguc3Vic3RyKC0xKSAhPT0gJy8nKSB7XG4gICAgICBwcmVmaXggKz0gJy8nO1xuICAgIH1cbiAgICBtYXRjaCA9ICh1cmwuc3Vic3RyKDAsIHByZWZpeC5sZW5ndGgpID09PSBwcmVmaXgpO1xuICB9IGVsc2Uge1xuICAgIC8vIE1hdGNoIHdob2xlIHBhdGhcbiAgICBtYXRjaCA9ICh1cmwgPT09IGVsZW1lbnQuaHJlZik7XG4gIH1cbiAgZWxlbWVudC5jdXJyZW50ID0gbWF0Y2g7XG59XG5cblxuY3VzdG9tRWxlbWVudHMuZGVmaW5lKCdiYXNpYy1jdXJyZW50LWFuY2hvcicsIEN1cnJlbnRBbmNob3IpO1xuIiwiaW1wb3J0IEF0dHJpYnV0ZU1hcnNoYWxsaW5nTWl4aW4gZnJvbSAnLi4vLi4vYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvQXR0cmlidXRlTWFyc2hhbGxpbmdNaXhpbic7XG5pbXBvcnQgQ29tcG9zYWJsZU1peGluIGZyb20gJy4uLy4uL2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL0NvbXBvc2FibGVNaXhpbic7XG5pbXBvcnQgRGlzdHJpYnV0ZWRDaGlsZHJlbk1peGluIGZyb20gJy4uLy4uL2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL0Rpc3RyaWJ1dGVkQ2hpbGRyZW5NaXhpbic7XG5pbXBvcnQgU2hhZG93RWxlbWVudFJlZmVyZW5jZXNNaXhpbiBmcm9tICcuLi8uLi9iYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy9TaGFkb3dFbGVtZW50UmVmZXJlbmNlc01peGluJztcbmltcG9ydCBTaGFkb3dUZW1wbGF0ZU1peGluIGZyb20gJy4uLy4uL2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL1NoYWRvd1RlbXBsYXRlTWl4aW4nO1xuXG5cbi8qKlxuICogQSBzYW1wbGUgZ2VuZXJhbC1wdXJwb3NlIGJhc2UgY2xhc3MgZm9yIGRlZmluaW5nIGN1c3RvbSBlbGVtZW50cyB0aGF0IG1peGVzXG4gKiBpbiBzb21lIGNvbW1vbiBmZWF0dXJlczogdGVtcGxhdGUgc3RhbXBpbmcgaW50byBhIHNoYWRvdyByb290LCBzaGFkb3cgZWxlbWVudFxuICogcmVmZXJlbmNlcywgbWFyc2hhbGxpbmcgYXR0cmlidXRlcyB0byBwcm9wZXJ0aWVzLCBhbmQgcmV0cmlldmluZyB0aGUgY2hpbGRyZW5cbiAqIGRpc3RyaWJ1dGVkIHRvIGEgY29tcG9uZW50LlxuICpcbiAqIFRoaXMgYmFzZSBjbGFzcyBpcyBub3Qgc3BlY2lhbCBpbiBhbnkgd2F5LCBhbmQgaXMgZGVmaW5lZCBvbmx5IGFzIGFcbiAqIGNvbnZlbmllbnQgc2hvcnRoYW5kIGZvciBhcHBseWluZyB0aGUgbWl4aW5zIGxpc3RlZCBhYm92ZS4gWW91IGNhbiB1c2UgdGhpc1xuICogY2xhc3MgYXMgYSBiYXNlIGNsYXNzIGZvciB5b3VyIG93biBlbGVtZW50cywgb3IgZWFzaWx5IGNyZWF0ZSB5b3VyIG93biBiYXNlXG4gKiBjbGFzcyBieSBhcHBseWluZyB0aGUgc2FtZSBzZXQgb2YgbWl4aW5zLlxuICpcbiAqIFRoZSBFbGVtZW50QmFzZSBiYXNlIGNsYXNzIGRvZXMgbm90IHJlZ2lzdGVyIGl0c2VsZiBhcyBhIGN1c3RvbSBlbGVtZW50IHdpdGhcbiAqIHRoZSBicm93c2VyLCBhbmQgaGVuY2UgY2Fubm90IGJlIGluZGVwZW5kZW50bHkgaW5zdGFudGlhdGVkLlxuICpcbiAqIEBtaXhlcyBBdHRyaWJ1dGVNYXJzaGFsbGluZ01peGluXG4gKiBAbWl4ZXMgQ29tcG9zYWJsZU1peGluXG4gKiBAbWl4ZXMgRGlzdHJpYnV0ZWRDaGlsZHJlbk1peGluXG4gKiBAbWl4ZXMgU2hhZG93RWxlbWVudFJlZmVyZW5jZXNNaXhpblxuICogQG1peGVzIFNoYWRvd1RlbXBsYXRlTWl4aW5cbiAqL1xuY2xhc3MgRWxlbWVudEJhc2UgZXh0ZW5kcyBDb21wb3NhYmxlTWl4aW4oSFRNTEVsZW1lbnQpLmNvbXBvc2UoXG4gIFNoYWRvd1RlbXBsYXRlTWl4aW4sICAgICAgICAgIC8vIGJlZm9yZSBub2RlIGZpbmRpbmcsIHNvIHNoYWRvdyByb290IGlzIHBvcHVsYXRlZFxuICBTaGFkb3dFbGVtZW50UmVmZXJlbmNlc01peGluLCAvLyBiZWZvcmUgbWFyc2hhbGxpbmcsIHNvIHByb3BlcnRpZXMgY2FuIHVzZSByZWZzXG4gIEF0dHJpYnV0ZU1hcnNoYWxsaW5nTWl4aW4sXG4gIERpc3RyaWJ1dGVkQ2hpbGRyZW5NaXhpblxuKSB7fVxuXG5leHBvcnQgZGVmYXVsdCBFbGVtZW50QmFzZTtcbiIsImltcG9ydCBFbGVtZW50QmFzZSBmcm9tICcuLi8uLi9iYXNpYy1lbGVtZW50LWJhc2Uvc3JjL0VsZW1lbnRCYXNlJztcbmltcG9ydCBzeW1ib2xzIGZyb20gJy4uLy4uL2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL3N5bWJvbHMnO1xuXG5cbi8qXG4gKiBBIHNldCBvZiBldmVudHMgd2hpY2gsIGlmIGZpcmVkIGJ5IHRoZSBpbm5lciBzdGFuZGFyZCBlbGVtZW50LCBzaG91bGQgYmVcbiAqIHJlLXJhaXNlZCBieSB0aGUgY3VzdG9tIGVsZW1lbnQuIChXZSBvbmx5IG5lZWQgdG8gZG8gdGhhdCB1bmRlciBuYXRpdmVcbiAqIFNoYWRvdyBET00sIG5vdCB0aGUgcG9seWZpbGwuKVxuICpcbiAqIFRoZXNlIGFyZSBldmVudHMgd2hpY2ggYXJlIHNwZWMnZWQgdG8gTk9UIGdldCByZXRhcmdldHRlZCBhY3Jvc3MgYSBTaGFkb3cgRE9NXG4gKiBib3VuZGFyeSwgb3JnYW5pemVkIGJ5IHdoaWNoIGVsZW1lbnQocykgcmFpc2UgdGhlIGV2ZW50cy4gVG8gcHJvcGVybHlcbiAqIHNpbXVsYXRlIHRoZXNlLCB3ZSB3aWxsIG5lZWQgdG8gbGlzdGVuIGZvciB0aGUgcmVhbCBldmVudHMsIHRoZW4gcmUtcmFpc2UgYVxuICogc2ltdWxhdGlvbiBvZiB0aGUgb3JpZ2luYWwgZXZlbnQuIEZvciBtb3JlIGluZm9ybWF0aW9uLCBzZWVcbiAqIGh0dHBzOi8vd3d3LnczLm9yZy9UUi9zaGFkb3ctZG9tLyNoLWV2ZW50cy10aGF0LWFyZS1ub3QtbGVha2VkLWludG8tYW5jZXN0b3ItdHJlZXMuXG4gKlxuICogSXQgYXBwZWFycyB0aGF0IHdlIGRvICpub3QqIG5lZWQgdG8gcmUtcmFpc2UgdGhlIG5vbi1idWJibGluZyBcImZvY3VzXCIgYW5kXG4gKiBcImJsdXJcIiBldmVudHMuIFRoZXNlIGFwcGVhciB0byBiZSBhdXRvbWF0aWNhbGx5IHJlLXJhaXNlZCBhcyBleHBlY3RlZCAtLSBidXRcbiAqIGl0J3Mgbm90IGNsZWFyIHdoeSB0aGF0IGhhcHBlbnMuXG4gKlxuICogVGhlIGxpc3QgYmVsb3cgaXMgcmVhc29uYWJseSBjb21wbGV0ZS4gSXQgb21pdHMgZWxlbWVudHMgdGhhdCBjYW5ub3QgYmVcbiAqIHdyYXBwZWQgKHNlZSBjbGFzcyBub3RlcyBhYm92ZSkuIEFsc28sIHdlIGhhdmVuJ3QgYWN0dWFsbHkgdHJpZWQgd3JhcHBpbmdcbiAqIGV2ZXJ5IGVsZW1lbnQgaW4gdGhpcyBsaXN0OyBzb21lIG9mIHRoZSBtb3JlIG9ic2N1cmUgb25lcyBtaWdodCBub3QgYWN0dWFsbHlcbiAqIHdvcmsgYXMgZXhwZWN0ZWQsIGJ1dCBpdCB3YXMgZWFzaWVyIHRvIGluY2x1ZGUgdGhlbSBmb3IgY29tcGxldGVuZXNzIHRoYW5cbiAqIHRvIGFjdHVhbGx5IHZlcmlmeSB3aGV0aGVyIG9yIG5vdCB0aGUgZWxlbWVudCBjYW4gYmUgd3JhcHBlZC5cbiAqL1xuY29uc3QgcmVyYWlzZUV2ZW50cyA9IHtcbiAgYWRkcmVzczogWydzY3JvbGwnXSxcbiAgYmxvY2txdW90ZTogWydzY3JvbGwnXSxcbiAgY2FwdGlvbjogWydzY3JvbGwnXSxcbiAgY2VudGVyOiBbJ3Njcm9sbCddLFxuICBkZDogWydzY3JvbGwnXSxcbiAgZGlyOiBbJ3Njcm9sbCddLFxuICBkaXY6IFsnc2Nyb2xsJ10sXG4gIGRsOiBbJ3Njcm9sbCddLFxuICBkdDogWydzY3JvbGwnXSxcbiAgZmllbGRzZXQ6IFsnc2Nyb2xsJ10sXG4gIGZvcm06IFsncmVzZXQnLCAnc2Nyb2xsJ10sXG4gIGZyYW1lOiBbJ2xvYWQnXSxcbiAgaDE6IFsnc2Nyb2xsJ10sXG4gIGgyOiBbJ3Njcm9sbCddLFxuICBoMzogWydzY3JvbGwnXSxcbiAgaDQ6IFsnc2Nyb2xsJ10sXG4gIGg1OiBbJ3Njcm9sbCddLFxuICBoNjogWydzY3JvbGwnXSxcbiAgaWZyYW1lOiBbJ2xvYWQnXSxcbiAgaW1nOiBbJ2Fib3J0JywgJ2Vycm9yJywgJ2xvYWQnXSxcbiAgaW5wdXQ6IFsnYWJvcnQnLCAnY2hhbmdlJywgJ2Vycm9yJywgJ3NlbGVjdCcsICdsb2FkJ10sXG4gIGtleWdlbjogWydyZXNldCcsICdzZWxlY3QnXSxcbiAgbGk6IFsnc2Nyb2xsJ10sXG4gIGxpbms6IFsnbG9hZCddLFxuICBtZW51OiBbJ3Njcm9sbCddLFxuICBvYmplY3Q6IFsnZXJyb3InLCAnc2Nyb2xsJ10sXG4gIG9sOiBbJ3Njcm9sbCddLFxuICBwOiBbJ3Njcm9sbCddLFxuICBzY3JpcHQ6IFsnZXJyb3InLCAnbG9hZCddLFxuICBzZWxlY3Q6IFsnY2hhbmdlJywgJ3Njcm9sbCddLFxuICB0Ym9keTogWydzY3JvbGwnXSxcbiAgdGZvb3Q6IFsnc2Nyb2xsJ10sXG4gIHRoZWFkOiBbJ3Njcm9sbCddLFxuICB0ZXh0YXJlYTogWydjaGFuZ2UnLCAnc2VsZWN0JywgJ3Njcm9sbCddXG59O1xuXG5cbi8vIEtlZXAgdHJhY2sgb2Ygd2hpY2ggcmUtcmFpc2VkIGV2ZW50cyBzaG91bGQgYnViYmxlLlxuY29uc3QgZXZlbnRCdWJibGVzID0ge1xuICBhYm9ydDogdHJ1ZSxcbiAgY2hhbmdlOiB0cnVlLFxuICByZXNldDogdHJ1ZVxufTtcblxuXG4vLyBFbGVtZW50cyB3aGljaCBhcmUgZGlzcGxheTogYmxvY2sgYnkgZGVmYXVsdC5cbi8vIFNvdXJjZTogaHR0cHM6Ly9kZXZlbG9wZXIubW96aWxsYS5vcmcvZW4tVVMvZG9jcy9XZWIvSFRNTC9CbG9jay1sZXZlbF9lbGVtZW50c1xuY29uc3QgYmxvY2tFbGVtZW50cyA9IFtcbiAgJ2FkZHJlc3MnLFxuICAnYXJ0aWNsZScsXG4gICdhc2lkZScsXG4gICdibG9ja3F1b3RlJyxcbiAgJ2NhbnZhcycsXG4gICdkZCcsXG4gICdkaXYnLFxuICAnZGwnLFxuICAnZmllbGRzZXQnLFxuICAnZmlnY2FwdGlvbicsXG4gICdmaWd1cmUnLFxuICAnZm9vdGVyJyxcbiAgJ2Zvcm0nLFxuICAnaDEnLFxuICAnaDInLFxuICAnaDMnLFxuICAnaDQnLFxuICAnaDUnLFxuICAnaDYnLFxuICAnaGVhZGVyJyxcbiAgJ2hncm91cCcsXG4gICdocicsXG4gICdsaScsXG4gICdtYWluJyxcbiAgJ25hdicsXG4gICdub3NjcmlwdCcsXG4gICdvbCcsXG4gICdvdXRwdXQnLFxuICAncCcsXG4gICdwcmUnLFxuICAnc2VjdGlvbicsXG4gICd0YWJsZScsXG4gICd0Zm9vdCcsXG4gICd1bCcsXG4gICd2aWRlbydcbl07XG5cblxuLyoqXG4gKiBXcmFwcyBhIHN0YW5kYXJkIEhUTUwgZWxlbWVudCBzbyB0aGF0IHRoZSBzdGFuZGFyZCBiZWhhdmlvciBjYW4gdGhlbiBiZVxuICogZXh0ZW5kZWQuXG4gKlxuICogW0xpdmUgZGVtb10oaHR0cDovL2Jhc2ljd2ViY29tcG9uZW50cy5vcmcvYmFzaWMtd2ViLWNvbXBvbmVudHMvcGFja2FnZXMvYmFzaWMtd3JhcHBlZC1zdGFuZGFyZC1lbGVtZW50LylcbiAqXG4gKiBTZWUgYWxzbyBbYmFzaWMtYXV0b3NpemUtdGV4dGFyZWFdKC4uL2Jhc2ljLWF1dG9zaXplLXRleHRhcmVhKSBhbmRcbiAqIFtiYXNpYy1jdXJyZW50LWFuY2hvcl0oLi4vYmFzaWMtY3VycmVudC1hbmNob3IpLiBUaGUgZm9ybWVyIHVzZXNcbiAqIFdyYXBwZWRTdGFuZGFyZEVsZW1lbnQgdG8gd3JhcCBhIHN0YW5kYXJkIGA8dGV4dGFyZWE+YCBhbmQgYDxhPmAsXG4gKiByZXNwZWN0aXZlbHkuXG4gKlxuICogVGhlIEN1c3RvbSBFbGVtZW50cyBzcGVjIGRvZXMgbm90IGN1cnJlbnRseSAoYXMgb2YgTWFyY2ggMjAxNikgYWxsb3cgeW91IHRvXG4gKiBleHRlbmQgdGhlIGJlaGF2aW9yIG9mIGEgc3RhbmRhcmQgSFRNTCBlbGVtZW50IGxpa2UgYDxhPmAgb3IgYDxidXR0b24+YC5cbiAqIEFzIGEgcGFydGlhbCB3b3JrYXJvdW5kLCB0aGUgV3JhcHBlZFN0YW5kYXJkRWxlbWVudCBjbGFzcyBjYW4gY3JlYXRlIGEgY2xhc3NcbiAqIGZvciB5b3UgdGhhdCB3cmFwcyBhbiBpbnN0YW5jZSBvZiBhIHN0YW5kYXJkIEhUTUwgZWxlbWVudC4gRm9yIGV4YW1wbGUsIHRoZVxuICogY29kZSBiZWxvdyBjcmVhdGVzIGEgY2xhc3MgdGhhdCB3aWxsIHdyYXAgYW4gaW5zdGFuY2Ugb2YgYSBzdGFuZGFyZCBgPGE+YFxuICogZWxlbWVudDpcbiAqXG4gKiAgICAgY2xhc3MgV3JhcHBlZEEgZXh0ZW5kcyBXcmFwcGVkU3RhbmRhcmRFbGVtZW50LndyYXAoJ2EnKSB7XG4gKiAgICAgICBjdXN0b21NZXRob2QoKSB7IC4uLiB9XG4gKiAgICAgfVxuICogICAgIGN1c3RvbUVsZW1lbnRzLmRlZmluZSgnd3JhcHBlZC1hJywgV3JhcHBlZEEpO1xuICpcbiAqIEFuIGluc3RhbmNlIG9mIHRoZSByZXN1bHRpbmcgY2xhc3Mgd2lsbCBsb29rIHRvIHRoZSB1c2VyIGxpa2UgYW4gaW5zdGFuY2Ugb2ZcbiAqIHRoZSBzdGFuZGFyZCBlbGVtZW50IGNsYXNzIGl0IHdyYXBzLiBUaGUgcmVzdWx0aW5nIGNsYXNzIHdpbGwgKm5vdCogYmUgYW5cbiAqIGBpbnN0YW5jZW9mYCB0aGUgc3RhbmRhcmQgY2xhc3MgKGhlcmUsIEhUTUxBbmNob3JFbGVtZW50KS4gQW5vdGhlciBsaW1pdGF0aW9uXG4gKiBpcyB0aGF0IHRoZSByZXN1bHRpbmcgYDx3cmFwcGVkLWE+YCB3aWxsIG5vdCBhdXRvbWF0aWNhbGx5IHBpY2sgdXAgQ1NTIHN0eWxlc1xuICogZm9yIHN0YW5kYXJkIGA8YT5gIGVsZW1lbnRzLiBIb3dldmVyLCB0aGUgcmVzdWx0aW5nIGNsYXNzICpjYW4qIGJlIGV4dGVuZGVkLlxuICogRS5nLiwgaW5zdGFuY2VzIG9mIHRoZSBhYm92ZSBjbGFzcyBoYXZlIGEgYGN1c3RvbU1ldGhvZCgpYCBhdmFpbGFibGUgdG8gdGhlbS5cbiAqXG4gKiBBbnkgcHJvcGVydGllcyBkZWZpbmVkIGJ5IHRoZSBvcmlnaW5hbCBzdGFuZGFyZCBlbGVtZW50IHdpbGwgYmUgZXhwb3NlZCBvblxuICogdGhlIHJlc3VsdGluZyB3cmFwcGVyIGNsYXNzLCBhbmQgY2FsbHMgdG8gZ2V0IG9yIHNldCB0aG9zZSBwcm9wZXJ0aWVzIHdpbGwgYmVcbiAqIGRlbGVnYXRlZCB0byB0aGUgd3JhcHBlZCBlbGVtZW50IGluc3RhbmNlLiBDb250aW51aW5nIHRoZSBhYm92ZSBleGFtcGxlOlxuICpcbiAqICAgICBsZXQgd3JhcHBlZCA9IGRvY3VtZW50LmNyZWF0ZUVsZW1lbnQoJ3dyYXBwZWQtYScpO1xuICogICAgIHdyYXBwZWQuaHJlZiA9ICdodHRwOi8vZXhhbXBsZS5jb20vJztcbiAqICAgICB3cmFwcGVkLnRleHRDb250ZW50ID0gJ0NsaWNrIGhlcmUnO1xuICpcbiAqIEhlcmUsIHRoZSBjcmVhdGVkIGN1c3RvbSBgPHdyYXBwZWQtYT5gIGVsZW1lbnQgd2lsbCBjb250YWluIGluc2lkZSBpdHNcbiAqIHNoYWRvdyB0cmVlIGFuIGluc3RhbmNlIG9mIGEgc3RhbmRhcmQgYDxhPmAgZWxlbWVudC4gVGhlIGNhbGwgdG8gc2V0IHRoZVxuICogd3JhcHBlcidzIGBocmVmYCBwcm9wZXJ0eSB3aWxsIHVsdGltYXRlbHkgc2V0IHRoZSBgaHJlZmAgb24gdGhlIGlubmVyIGxpbmsuXG4gKiBNb3Jlb3ZlciwgdGhlIHRleHQgY29udGVudCBvZiB0aGUgYDx3cmFwcGVkLWE+YCBlbGVtZW50IHdpbGwgYXBwZWFyIGluc2lkZVxuICogdGhlIGlubmVyIGxpbmsuIFRoZSByZXN1bHQgb2YgYWxsIHRoaXMgaXMgdGhhdCB0aGUgdXNlciB3aWxsIHNlZSB3aGF0ICpsb29rcypcbiAqIGxpa2UgYSBub3JtYWwgbGluaywganVzdCBhcyBpZiB5b3UgaGFkIHdyaXR0ZW5cbiAqIGA8YSBocmVmPVwiaHR0cDovL2V4YW1wbGUuY29tL1wiPkNsaWNrIGhlcmU8L2E+YC4gSG93ZXZlciwgdGhlIGFjdHVhbCBlbGVtZW50XG4gKiB3aWxsIGJlIGFuIGluc3RhbmNlIG9mIHlvdXIgY3VzdG9tIGNsYXNzLCB3aXRoIHdoYXRldmVyIGJlaGF2aW9yIHlvdSd2ZVxuICogZGVmaW5lZCBmb3IgaXQuXG4gKlxuICogV3JhcHBlZCBlbGVtZW50cyBzaG91bGQgcmFpc2UgdGhlIHNhbWUgZXZlbnRzIGFzIHRoZSBvcmlnaW5hbCBzdGFuZGFyZFxuICogZWxlbWVudHMuIEUuZy4sIGlmIHlvdSB3cmFwIGFuIGA8aW1nPmAgZWxlbWVudCwgdGhlIHdyYXBwZWQgcmVzdWx0IHdpbGwgcmFpc2VcbiAqIHRoZSBzdGFuZGFyZCBgbG9hZGAgZXZlbnQgYXMgZXhwZWN0ZWQuXG4gKlxuICogU29tZSBlbGVtZW50cywgc3VjaCBhcyBgPGJvZHk+YCwgYDxodG1sPmAsIGFuZCBgPHN0eWxlPmAgY2Fubm90IGJlIHdyYXBwZWRcbiAqIGFuZCBzdGlsbCBhY2hpZXZlIHRoZWlyIHN0YW5kYXJkIGJlaGF2aW9yLlxuICpcbiAqIEBleHRlbmRzIEVsZW1lbnRCYXNlXG4gKi9cbmNsYXNzIFdyYXBwZWRTdGFuZGFyZEVsZW1lbnQgZXh0ZW5kcyBFbGVtZW50QmFzZSB7XG5cbiAgY29uc3RydWN0b3IoKSB7XG4gICAgc3VwZXIoKTtcblxuICAgIC8vIExpc3RlbiBmb3IgYW55IGV2ZW50cyByYWlzZWQgYnkgdGhlIGlubmVyIGVsZW1lbnQgd2hpY2ggd2lsbCBub3RcbiAgICAvLyBhdXRvbWF0aWNhbGx5IGJlIHJldGFyZ2V0dGVkIGFjcm9zcyB0aGUgU2hhZG93IERPTSBib3VuZGFyeSwgYW5kIHJlLXJhaXNlXG4gICAgLy8gdGhvc2UgZXZlbnRzIHdoZW4gdGhleSBoYXBwZW4uXG4gICAgLy9cbiAgICAvLyBOb3RlOiBJdCdzIHVuY2xlYXIgd2h5IHdlIG5lZWQgdG8gZG8gdGhpcyBpbiB0aGUgU2hhZG93IERPTSBwb2x5ZmlsbC5cbiAgICAvLyBJbiB0aGVvcnksIGV2ZW50cyBpbiB0aGUgbGlnaHQgRE9NIHNob3VsZCBidWJibGUgYXMgbm9ybWFsLiBCdXQgdGhpc1xuICAgIC8vIGNvZGUgYXBwZWFycyB0byBiZSByZXF1aXJlZCBpbiB0aGUgcG9seWZpbGwgY2FzZSBhcyB3ZWxsLlxuICAgIGNvbnN0IGV2ZW50TmFtZXMgPSByZXJhaXNlRXZlbnRzW3RoaXMuZXh0ZW5kc10gfHwgW107XG4gICAgZXZlbnROYW1lcy5mb3JFYWNoKGV2ZW50TmFtZSA9PiB7XG4gICAgICB0aGlzLmlubmVyLmFkZEV2ZW50TGlzdGVuZXIoZXZlbnROYW1lLCByZWFsRXZlbnQgPT4ge1xuICAgICAgICBjb25zdCBldmVudCA9IG5ldyBFdmVudChldmVudE5hbWUsIHtcbiAgICAgICAgICBidWJibGVzOiBldmVudEJ1YmJsZXNbZXZlbnROYW1lXSB8fCBmYWxzZVxuICAgICAgICB9KTtcbiAgICAgICAgdGhpcy5kaXNwYXRjaEV2ZW50KGV2ZW50KTtcbiAgICAgIH0pO1xuICAgIH0pO1xuICB9XG5cbiAgLyoqXG4gICAqIEEgZGVzY3JpcHRpb24gZm9yIHRoZSB1c2VyIG9mIHRoZSBlbGVtZW50J3MgcHVycG9zZSBvbiB0aGUgcGFnZS4gU2V0dGluZ1xuICAgKiB0aGlzIGFwcGxpZXMgdGhlIGxhYmVsIHRvIHRoZSBpbm5lciBlbGVtZW50LCBlbnN1cmluZyB0aGF0IHNjcmVlbiByZWFkZXJzXG4gICAqIGFuZCBvdGhlciBhc3Npc3RpdmUgdGVjaG5vbG9naWVzIHdpbGwgcHJvdmlkZSBhIG1lYW5pbmdmdWwgZGVzY3JpcHRpb24gdG9cbiAgICogdGhlIHVzZXIuXG4gICAqXG4gICAqIEB0eXBlIHtzdHJpbmd9XG4gICAqL1xuICBnZXQgYXJpYUxhYmVsKCkge1xuICAgIHJldHVybiB0aGlzLmlubmVyLmdldEF0dHJpYnV0ZSgnYXJpYS1sYWJlbCcpO1xuICB9XG4gIHNldCBhcmlhTGFiZWwobGFiZWwpIHtcbiAgICAvLyBQcm9wYWdhdGUgdGhlIEFSSUEgbGFiZWwgdG8gdGhlIGlubmVyIHRleHRhcmVhLlxuICAgIHRoaXMuaW5uZXIuc2V0QXR0cmlidXRlKCdhcmlhLWxhYmVsJywgbGFiZWwpO1xuICB9XG5cbiAgLyoqXG4gICAqIFJldHVybnMgYSByZWZlcmVuY2UgdG8gdGhlIGlubmVyIHN0YW5kYXJkIEhUTUwgZWxlbWVudC5cbiAgICpcbiAgICogQHR5cGUge0hUTUxFbGVtZW50fVxuICAgKi9cbiAgZ2V0IGlubmVyKCkge1xuICAgIHJldHVybiB0aGlzLiQuaW5uZXI7XG4gIH1cblxuICAvKipcbiAgICogVGhlIHRlbXBsYXRlIGNvcGllZCBpbnRvIHRoZSBzaGFkb3cgdHJlZSBvZiBuZXcgaW5zdGFuY2VzIG9mIHRoaXMgZWxlbWVudC5cbiAgICpcbiAgICogVGhlIGRlZmF1bHQgdmFsdWUgb2YgdGhpcyBwcm9wZXJ0eSBpcyBhIHRlbXBsYXRlIHRoYXQgaW5jbHVkZXMgYW4gaW5zdGFuY2VcbiAgICogdGhlIHN0YW5kYXJkIGVsZW1lbnQgYmVpbmcgd3JhcHBlZCwgd2l0aCBhIGA8c2xvdD5gIGVsZW1lbnQgaW5zaWRlIHRoYXRcbiAgICogdG8gcGljayB1cCB0aGUgZWxlbWVudCdzIGxpZ2h0IERPTSBjb250ZW50LiBGb3IgZXhhbXBsZSwgaWYgeW91IHdyYXAgYW5cbiAgICogYDxhPmAgZWxlbWVudCwgdGhlbiB0aGUgZGVmYXVsdCB0ZW1wbGF0ZSB3aWxsIGxvb2sgbGlrZTpcbiAgICpcbiAgICogICAgIDx0ZW1wbGF0ZT5cbiAgICogICAgICAgPHN0eWxlPlxuICAgKiAgICAgICA6aG9zdCB7XG4gICAqICAgICAgICAgZGlzcGxheTogaW5saW5lLWJsb2NrO1xuICAgKiAgICAgICB9XG4gICAqICAgICAgIDwvc3R5bGU+XG4gICAqICAgICAgIDxhIGlkPVwiaW5uZXJcIj5cbiAgICogICAgICAgICA8c2xvdD48L3Nsb3Q+XG4gICAqICAgICAgIDwvYT5cbiAgICogICAgIDwvdGVtcGxhdGU+XG4gICAqXG4gICAqIFRoZSBgZGlzcGxheWAgc3R5bGluZyBhcHBsaWVkIHRvIHRoZSBob3N0IHdpbGwgYmUgYGJsb2NrYCBmb3IgZWxlbWVudHMgdGhhdFxuICAgKiBhcmUgYmxvY2sgZWxlbWVudHMgYnkgZGVmYXVsdCwgYW5kIGBpbmxpbmUtYmxvY2tgIChub3QgYGlubGluZWApIGZvciBvdGhlclxuICAgKiBlbGVtZW50cy5cbiAgICpcbiAgICogSWYgeW91J2QgbGlrZSB0aGUgdGVtcGxhdGUgdG8gaW5jbHVkZSBvdGhlciBlbGVtZW50cywgdGhlbiBvdmVycmlkZSB0aGlzXG4gICAqIHByb3BlcnR5IGFuZCByZXR1cm4gYSB0ZW1wbGF0ZSBvZiB5b3VyIG93bi4gVGhlIHRlbXBsYXRlIHNob3VsZCBpbmNsdWRlIGFuXG4gICAqIGluc3RhbmNlIG9mIHRoZSBzdGFuZGFyZCBIVE1MIGVsZW1lbnQgeW91IGFyZSB3cmFwcGluZywgYW5kIHRoZSBJRCBvZiB0aGF0XG4gICAqIGVsZW1lbnQgc2hvdWxkIGJlIFwiaW5uZXJcIi5cbiAgICpcbiAgICogQHR5cGUgeyhzdHJpbmd8SFRNTFRlbXBsYXRlRWxlbWVudCl9XG4gICAqL1xuICBnZXQgW3N5bWJvbHMudGVtcGxhdGVdKCkge1xuICAgIGNvbnN0IGRpc3BsYXkgPSBibG9ja0VsZW1lbnRzLmluZGV4T2YodGhpcy5leHRlbmRzKSA+PSAwID9cbiAgICAgICdibG9jaycgOlxuICAgICAgJ2lubGluZS1ibG9jayc7XG4gICAgcmV0dXJuIGA8c3R5bGU+Omhvc3QgeyBkaXNwbGF5OiAke2Rpc3BsYXl9fTwvc3R5bGU+PCR7dGhpcy5leHRlbmRzfSBpZD1cImlubmVyXCI+PHNsb3Q+PC9zbG90PjwvJHt0aGlzLmV4dGVuZHN9YDtcbiAgfVxuXG4gIC8qKlxuICAgKiBDcmVhdGVzIGEgY2xhc3MgdGhhdCB3cmFwcyBhIHN0YW5kYXJkIEhUTUwgZWxlbWVudC5cbiAgICpcbiAgICogTm90ZSB0aGF0IHRoZSByZXN1bHRpbmcgY2xhc3MgaXMgYSBzdWJjbGFzcyBvZiBXcmFwcGVkU3RhbmRhcmRFbGVtZW50LCBub3RcbiAgICogdGhlIHN0YW5kYXJkIGNsYXNzIGJlaW5nIHdyYXBwZWQuIEUuZy4sIGlmIHlvdSBjYWxsXG4gICAqIGBXcmFwcGVkU3RhbmRhcmRFbGVtZW50LndyYXAoJ2EnKWAsIHlvdSB3aWxsIGdldCBhIGNsYXNzIHdob3NlIHNoYWRvdyB0cmVlXG4gICAqIHdpbGwgaW5jbHVkZSBhbiBhbmNob3IgZWxlbWVudCwgYnV0IHRoZSBjbGFzcyB3aWxsICpub3QqIGluaGVyaXQgZnJvbVxuICAgKiBIVE1MQW5jaG9yRWxlbWVudC5cbiAgICpcbiAgICogQHBhcmFtIHtzdHJpbmd9IGV4dGVuZHNUYWcgLSB0aGUgc3RhbmRhcmQgSFRNTCBlbGVtZW50IHRhZyB0byBleHRlbmRcbiAgICovXG4gIHN0YXRpYyB3cmFwKGV4dGVuZHNUYWcpIHtcblxuICAgIC8vIENyZWF0ZSB0aGUgbmV3IGNsYXNzLlxuICAgIGNsYXNzIFdyYXBwZWQgZXh0ZW5kcyBXcmFwcGVkU3RhbmRhcmRFbGVtZW50IHt9XG5cbiAgICAvLyBJbmRpY2F0ZSB3aGljaCB0YWcgaXQgd3JhcHMuXG4gICAgV3JhcHBlZC5wcm90b3R5cGUuZXh0ZW5kcyA9IGV4dGVuZHNUYWc7XG5cbiAgICAvLyBDcmVhdGUgZ2V0dGVyL3NldHRlcnMgdGhhdCBkZWxlZ2F0ZSB0byB0aGUgd3JhcHBlZCBlbGVtZW50LlxuICAgIGNvbnN0IGVsZW1lbnQgPSBkb2N1bWVudC5jcmVhdGVFbGVtZW50KGV4dGVuZHNUYWcpO1xuICAgIGNvbnN0IGV4dGVuZHNQcm90b3R5cGUgPSBlbGVtZW50LmNvbnN0cnVjdG9yLnByb3RvdHlwZTtcbiAgICBjb25zdCBuYW1lcyA9IE9iamVjdC5nZXRPd25Qcm9wZXJ0eU5hbWVzKGV4dGVuZHNQcm90b3R5cGUpO1xuICAgIG5hbWVzLmZvckVhY2gobmFtZSA9PiB7XG4gICAgICAgIGNvbnN0IGRlc2NyaXB0b3IgPSBPYmplY3QuZ2V0T3duUHJvcGVydHlEZXNjcmlwdG9yKGV4dGVuZHNQcm90b3R5cGUsIG5hbWUpO1xuICAgICAgICBjb25zdCBkZWxlZ2F0ZSA9IGNyZWF0ZVByb3BlcnR5RGVsZWdhdGUobmFtZSwgZGVzY3JpcHRvcik7XG4gICAgICAgIE9iamVjdC5kZWZpbmVQcm9wZXJ0eShXcmFwcGVkLnByb3RvdHlwZSwgbmFtZSwgZGVsZWdhdGUpO1xuICAgIH0pO1xuXG4gICAgcmV0dXJuIFdyYXBwZWQ7XG4gIH1cblxufVxuXG5cbmZ1bmN0aW9uIGNyZWF0ZVByb3BlcnR5RGVsZWdhdGUobmFtZSwgZGVzY3JpcHRvcikge1xuICBjb25zdCBkZWxlZ2F0ZSA9IHtcbiAgICBjb25maWd1cmFibGU6IGRlc2NyaXB0b3IuY29uZmlndXJhYmxlLFxuICAgIGVudW1lcmFibGU6IGRlc2NyaXB0b3IuZW51bWVyYWJsZSxcbiAgfTtcbiAgaWYgKGRlc2NyaXB0b3IuZ2V0KSB7XG4gICAgZGVsZWdhdGUuZ2V0ID0gZnVuY3Rpb24oKSB7XG4gICAgICByZXR1cm4gdGhpcy5pbm5lcltuYW1lXTtcbiAgICB9O1xuICB9XG4gIGlmIChkZXNjcmlwdG9yLnNldCkge1xuICAgIGRlbGVnYXRlLnNldCA9IGZ1bmN0aW9uKHZhbHVlKSB7XG4gICAgICB0aGlzLmlubmVyW25hbWVdID0gdmFsdWU7XG4gICAgfTtcbiAgfVxuICBpZiAoZGVzY3JpcHRvci53cml0YWJsZSkge1xuICAgIGRlbGVnYXRlLndyaXRhYmxlID0gZGVzY3JpcHRvci53cml0YWJsZTtcbiAgfVxuICByZXR1cm4gZGVsZWdhdGU7XG59XG5cblxuZXhwb3J0IGRlZmF1bHQgV3JhcHBlZFN0YW5kYXJkRWxlbWVudDtcbiJdfQ==
+!function e(t,n,r){function o(c,a){if(!n[c]){if(!t[c]){var u="function"==typeof require&&require;if(!a&&u)return u(c,!0);if(i)return i(c,!0);var l=new Error("Cannot find module '"+c+"'");throw l.code="MODULE_NOT_FOUND",l}var s=n[c]={exports:{}};t[c][0].call(s.exports,function(e){var n=t[c][1][e];return o(n?n:e)},s,s.exports,e,t,n,r)}return n[c].exports}for(var i="function"==typeof require&&require,c=0;c2&&void 0!==arguments[2]?arguments[2]:[];return Object.getOwnPropertyNames(e).forEach(function(r){if(n.indexOf(r)<0){var o=Object.getOwnPropertyDescriptor(e,r);Object.defineProperty(t,r,o)}}),t}Object.defineProperty(n,"__esModule",{value:!0});var u=function(){function e(e,t){for(var n=0;n0;)t.content.appendChild(n.childNodes[0]);return t}function u(e,t){window.WebComponents.ShadowCSS.shimStyling(e.content,t)}Object.defineProperty(n,"__esModule",{value:!0});var l=e("../src/symbols"),s=r(l);n.default=function(e){var t=function(e){function t(){o(this,t);var e=i(this,(t.__proto__||Object.getPrototypeOf(t)).call(this)),n=e[s.default.template];if(n){"string"==typeof n&&(n=a(n)),window.ShadowDOMPolyfill&&u(n,e.localName);var r=e.attachShadow({mode:"open"}),c=document.importNode(n.content,!0);r.appendChild(c)}return e}return c(t,e),t}(e);return t}},{"../src/symbols":8}],6:[function(e,t,n){"use strict";function r(e){return"function"==typeof Symbol?Symbol(e):"_"+e}Object.defineProperty(n,"__esModule",{value:!0}),n.default=r},{}],7:[function(e,t,n){"use strict";function r(e){return e&&e.__esModule?e:{default:e}}function o(e,t,n){if(null===n||"undefined"==typeof n)e.removeAttribute(t);else{var r=String(n);e.getAttribute(t)!==r&&e.setAttribute(t,n)}}Object.defineProperty(n,"__esModule",{value:!0});var i=e("./createSymbol"),c=r(i),a=e("./toggleClass"),u=r(a),l=(0,c.default)("safeToSetAttributes"),s=(0,c.default)("pendingAttributes"),f=(0,c.default)("pendingClasses");n.default={connected:function(e){if(e[l]=!0,e[s]){for(var t in e[s]){var n=e[s][t];o(e,t,n)}e[s]=null}if(e[f]){for(var r in e[f]){var i=e[f][r];(0,u.default)(e,r,i)}e[f]=null}},setAttribute:function(e,t,n){e[l]?o(e,t,n):(e[s]||(e[s]={}),e[s][t]=n)},toggleClass:function(e,t,n){e[l]?(0,u.default)(e,t,n):(e[f]||(e[f]={}),e[f][t]=n)}}},{"./createSymbol":6,"./toggleClass":9}],8:[function(e,t,n){"use strict";function r(e){return e&&e.__esModule?e:{default:e}}Object.defineProperty(n,"__esModule",{value:!0});var o=e("./createSymbol"),i=r(o),c={defaults:(0,i.default)("defaults"),dragging:(0,i.default)("dragging"),goDown:(0,i.default)("goDown"),goEnd:(0,i.default)("goEnd"),goLeft:(0,i.default)("goLeft"),goRight:(0,i.default)("goRight"),goStart:(0,i.default)("goStart"),goUp:(0,i.default)("goUp"),itemAdded:(0,i.default)("itemAdded"),itemsChanged:(0,i.default)("itemsChanged"),itemSelected:(0,i.default)("itemSelected"),keydown:(0,i.default)("keydown"),template:(0,i.default)("template")};n.default=c},{"./createSymbol":6}],9:[function(e,t,n){"use strict";function r(e,t,n){var r=e.classList,o="undefined"==typeof n?!r.contains(t):n;return o?r.add(t):r.remove(t),o}Object.defineProperty(n,"__esModule",{value:!0}),n.default=r},{}],10:[function(e,t,n){"use strict";function r(e){return e&&e.__esModule?e:{default:e}}var o=e("./src/CurrentAnchor"),i=r(o);window.Basic=window.Basic||{},window.Basic.CurrentAnchor=i.default},{"./src/CurrentAnchor":11}],11:[function(e,t,n){"use strict";function r(e){return e&&e.__esModule?e:{default:e}}function o(e,t){if(!(e instanceof t))throw new TypeError("Cannot call a class as a function")}function i(e,t){if(!e)throw new ReferenceError("this hasn't been initialised - super() hasn't been called");return!t||"object"!=typeof t&&"function"!=typeof t?e:t}function c(e,t){if("function"!=typeof t&&null!==t)throw new TypeError("Super expression must either be null or a function, not "+typeof t);e.prototype=Object.create(t&&t.prototype,{constructor:{value:e,enumerable:!1,writable:!0,configurable:!0}}),t&&(Object.setPrototypeOf?Object.setPrototypeOf(e,t):e.__proto__=t)}function a(e){var t=window.location.href,n=void 0;if(e.areaLink){var r=e.href;r.length\n :host {\n display: inline-block;\n }\n\n #inner {\n color: inherit;\n display: inline-block;\n text-decoration: inherit;\n }\n \n '}}]),t}(m.default.wrap("a"));customElements.define("basic-current-anchor",g)},{"../../basic-component-mixins/src/createSymbol":6,"../../basic-component-mixins/src/safeAttributes":7,"../../basic-component-mixins/src/symbols":8,"../../basic-wrapped-standard-element/src/WrappedStandardElement":13}],12:[function(e,t,n){"use strict";function r(e){return e&&e.__esModule?e:{default:e}}function o(e,t){if(!(e instanceof t))throw new TypeError("Cannot call a class as a function")}function i(e,t){if(!e)throw new ReferenceError("this hasn't been initialised - super() hasn't been called");return!t||"object"!=typeof t&&"function"!=typeof t?e:t}function c(e,t){if("function"!=typeof t&&null!==t)throw new TypeError("Super expression must either be null or a function, not "+typeof t);e.prototype=Object.create(t&&t.prototype,{constructor:{value:e,enumerable:!1,writable:!0,configurable:!0}}),t&&(Object.setPrototypeOf?Object.setPrototypeOf(e,t):e.__proto__=t)}Object.defineProperty(n,"__esModule",{value:!0});var a=e("../../basic-component-mixins/src/AttributeMarshallingMixin"),u=r(a),l=e("../../basic-component-mixins/src/ComposableMixin"),s=r(l),f=e("../../basic-component-mixins/src/DistributedChildrenMixin"),p=r(f),d=e("../../basic-component-mixins/src/ShadowElementReferencesMixin"),b=r(d),y=e("../../basic-component-mixins/src/ShadowTemplateMixin"),h=r(y),_=function(e){function t(){return o(this,t),i(this,(t.__proto__||Object.getPrototypeOf(t)).apply(this,arguments))}return c(t,e),t}((0,s.default)(HTMLElement).compose(h.default,b.default,u.default,p.default));n.default=_},{"../../basic-component-mixins/src/AttributeMarshallingMixin":1,"../../basic-component-mixins/src/ComposableMixin":2,"../../basic-component-mixins/src/DistributedChildrenMixin":3,"../../basic-component-mixins/src/ShadowElementReferencesMixin":4,"../../basic-component-mixins/src/ShadowTemplateMixin":5}],13:[function(e,t,n){"use strict";function r(e){return e&&e.__esModule?e:{default:e}}function o(e,t){if(!(e instanceof t))throw new TypeError("Cannot call a class as a function")}function i(e,t){if(!e)throw new ReferenceError("this hasn't been initialised - super() hasn't been called");return!t||"object"!=typeof t&&"function"!=typeof t?e:t}function c(e,t){if("function"!=typeof t&&null!==t)throw new TypeError("Super expression must either be null or a function, not "+typeof t);e.prototype=Object.create(t&&t.prototype,{constructor:{value:e,enumerable:!1,writable:!0,configurable:!0}}),t&&(Object.setPrototypeOf?Object.setPrototypeOf(e,t):e.__proto__=t)}function a(e,t){var n={configurable:t.configurable,enumerable:t.enumerable};return t.get&&(n.get=function(){return this.inner[e]}),t.set&&(n.set=function(t){this.inner[e]=t}),t.writable&&(n.writable=t.writable),n}Object.defineProperty(n,"__esModule",{value:!0});var u=function(){function e(e,t){for(var n=0;n=0?"block":"inline-block";return"<"+this.extends+' id="inner"> '+this.extends}}],[{key:"wrap",value:function(e){var n=function(e){function t(){return o(this,t),i(this,(t.__proto__||Object.getPrototypeOf(t)).apply(this,arguments))}return c(t,e),t}(t);n.prototype.extends=e;var r=document.createElement(e),u=r.constructor.prototype,l=Object.getOwnPropertyNames(u);return l.forEach(function(e){var t=Object.getOwnPropertyDescriptor(u,e),r=a(e,t);Object.defineProperty(n.prototype,e,r)}),n}}]),t}(s.default);n.default=h},{"../../basic-component-mixins/src/symbols":8,"../../basic-element-base/src/ElementBase":12}]},{},[10]);
+//# sourceMappingURL=basic-current-anchor.js.map
diff --git a/packages/basic-current-anchor/dist/basic-current-anchor.js.map b/packages/basic-current-anchor/dist/basic-current-anchor.js.map
new file mode 100644
index 00000000..3e1563b1
--- /dev/null
+++ b/packages/basic-current-anchor/dist/basic-current-anchor.js.map
@@ -0,0 +1 @@
+{"version":3,"sources":["node_modules/browser-pack/_prelude.js","packages/basic-component-mixins/src/AttributeMarshallingMixin.js","packages/basic-component-mixins/src/ComposableMixin.js","packages/basic-component-mixins/src/DistributedChildrenMixin.js","packages/basic-component-mixins/src/ShadowElementReferencesMixin.js","packages/basic-component-mixins/src/ShadowTemplateMixin.js","packages/basic-component-mixins/src/createSymbol.js","packages/basic-component-mixins/src/safeAttributes.js","packages/basic-component-mixins/src/symbols.js","packages/basic-component-mixins/src/toggleClass.js","packages/basic-current-anchor/globals.js","packages/basic-current-anchor/src/CurrentAnchor.js","packages/basic-element-base/src/ElementBase.js","packages/basic-wrapped-standard-element/src/WrappedStandardElement.js"],"names":["e","t","n","r","s","o","u","a","require","i","f","Error","code","l","exports","call","length","1","module","attributeToPropertyName","attributeName","propertyName","attributeToPropertyNames","hypenRegEx","replace","match","toUpperCase","attributesForClass","classFn","HTMLElement","Object","baseClass","getPrototypeOf","prototype","constructor","baseAttributes","propertyNames","getOwnPropertyNames","setterNames","filter","getOwnPropertyDescriptor","set","attributes","map","setterName","propertyNameToAttribute","diff","attribute","indexOf","concat","propertyNamesToAttributes","uppercaseRegEx","toLowerCase","_safeAttributes","base","AttributeMarshalling","_base","_classCallCheck","this","_possibleConstructorReturn","__proto__","apply","arguments","_inherits","_createClass","key","value","oldValue","newValue","_get","_safeAttributes2","default","connected","setAttribute","className","toggleClass","get","composeClass","mixin","Subclass","_base2","copyOwnProperties","NON_MIXABLE_OBJECT_PROPERTIES","source","target","ignorePropertyNames","undefined","forEach","name","descriptor","defineProperty","Composable","_len","mixins","Array","_key","reduce","expandContentElements","nodes","includeTextNodes","_ref","expanded","node","isSlot","HTMLSlotElement","localName","assignedNodes","flatten","Text","flattened","_toConsumableArray","DistributedChildren","children","childNodes","strings","distributedChildNodes","child","textContent","join","ShadowElementReferences","_this","shadowRoot","$","nodesWithIds","querySelectorAll","id","getAttribute","createTemplateWithInnerHTML","innerHTML","template","document","createElement","div","content","appendChild","shimTemplateStyles","tag","window","WebComponents","ShadowCSS","shimStyling","_symbols","ShadowTemplate","_symbols2","ShadowDOMPolyfill","root","attachShadow","mode","clone","importNode","createSymbol","description","Symbol","setAttributeToElement","element","removeAttribute","text","String","_createSymbol","_toggleClass2","safeToSetAttributesSymbol","_createSymbol2","pendingAttributesSymbol","pendingClassesSymbol","_value","_toggleClass3","symbols","defaults","dragging","goDown","goEnd","goLeft","goRight","goStart","goUp","itemAdded","itemsChanged","itemSelected","keydown","force","classList","addClass","contains","add","remove","_CurrentAnchor","Basic","CurrentAnchor","_CurrentAnchor2","refresh","url","location","href","areaLink","prefix","substr","current","_WrappedStandardElement","areaLinkSymbol","addEventListener","event","dispatchEvent","CustomEvent","_set","_WrappedStandardElement2","wrap","customElements","define","_AttributeMarshallingMixin","_ComposableMixin","_DistributedChildrenMixin","_ShadowElementReferencesMixin","_ShadowTemplateMixin","ElementBase","_ComposableMixin2","compose","_ShadowTemplateMixin2","_ShadowElementReferencesMixin2","_AttributeMarshallingMixin2","_DistributedChildrenMixin2","createPropertyDelegate","delegate","configurable","enumerable","inner","writable","_ElementBase2","reraiseEvents","address","blockquote","caption","center","dd","dir","dl","dt","fieldset","form","frame","h1","h2","h3","h4","h5","h6","iframe","img","input","keygen","li","link","menu","object","ol","p","script","select","tbody","tfoot","thead","textarea","eventBubbles","abort","change","reset","blockElements","WrappedStandardElement","eventNames","extends","eventName","realEvent","Event","bubbles","label","display","extendsTag","Wrapped","_WrappedStandardEleme","extendsPrototype","names"],"mappings":"CAAA,QAAAA,GAAAC,EAAAC,EAAAC,GAAA,QAAAC,GAAAC,EAAAC,GAAA,IAAAJ,EAAAG,GAAA,CAAA,IAAAJ,EAAAI,GAAA,CAAA,GAAAE,GAAA,kBAAAC,UAAAA,OAAA,KAAAF,GAAAC,EAAA,MAAAA,GAAAF,GAAA,EAAA,IAAAI,EAAA,MAAAA,GAAAJ,GAAA,EAAA,IAAAK,GAAA,GAAAC,OAAA,uBAAAN,EAAA,IAAA,MAAAK,GAAAE,KAAA,mBAAAF,EAAA,GAAAG,GAAAX,EAAAG,IAAAS,WAAAb,GAAAI,GAAA,GAAAU,KAAAF,EAAAC,QAAA,SAAAd,GAAA,GAAAE,GAAAD,EAAAI,GAAA,GAAAL,EAAA,OAAAI,GAAAF,EAAAA,EAAAF,IAAAa,EAAAA,EAAAC,QAAAd,EAAAC,EAAAC,EAAAC,GAAA,MAAAD,GAAAG,GAAAS,QAAA,IAAA,GAAAL,GAAA,kBAAAD,UAAAA,QAAAH,EAAA,EAAAA,EAAAF,EAAAa,OAAAX,IAAAD,EAAAD,EAAAE,GAAA,OAAAD,KAAAa,GAAA,SAAAT,EAAAU,EAAAJ,+nBC8GA,QAASK,GAAwBC,GAC/B,GAAIC,GAAeC,EAAyBF,EAC5C,KAAKC,EAAc,CAEjB,GAAME,GAAa,WACnBF,GAAeD,EAAcI,QAAQD,EACjC,SAAAE,GAAA,MAASA,GAAM,GAAGC,gBACtBJ,EAAyBF,GAAiBC,EAE5C,MAAOA,GAGT,QAASM,GAAmBC,GAI1B,GAAIA,IAAYC,aAAeD,IAAYE,OACzC,QAIF,IAAMC,GAAYD,OAAOE,eAAeJ,EAAQK,WAAWC,YACrDC,EAAiBR,EAAmBI,GAGpCK,EAAgBN,OAAOO,oBAAoBT,EAAQK,WACnDK,EAAcF,EAAcG,OAAO,SAAAlB,GAAA,MAEM,kBADtCS,QAAOU,yBACVZ,EAAQK,UAAWZ,GAAcoB,MACjCC,EAAaJ,EAAYK,IAAI,SAAAC,GAAA,MAC/BC,GAAwBD,KAGtBE,EAAOJ,EAAWH,OAAO,SAAAQ,GAAA,MAC3BZ,GAAea,QAAQD,GAAa,GACxC,OAAOZ,GAAec,OAAOH,GAI/B,QAASD,GAAwBxB,GAC/B,GAAI0B,GAAYG,EAA0B7B,EAC1C,KAAK0B,EAAW,CAEd,GAAMI,GAAiB,UACvBJ,GAAY1B,EAAaG,QAAQ2B,EAAgB,OAAOC,cAE1D,MAAOL,qiBA5JTM,EAAA7C,EAAA,2BAIMc,KACA4B,eAIS,SAACI,GAAS,GAqCjBC,GArCiB,SAAAC,GAAA,QAAAD,KAAA,MAAAE,GAAAC,KAAAH,GAAAI,EAAAD,MAAAH,EAAAK,WAAA9B,OAAAE,eAAAuB,IAAAM,MAAAH,KAAAI,YAAA,MAAAC,GAAAR,EAAAC,GAAAQ,EAAAT,IAAAU,IAAA,2BAAAC,MAAA,SA0CI9C,EAAe+C,EAAUC,GAChDC,EAAAd,EAAAtB,UAAA2B,WAAA9B,OAAAE,eAAAuB,EAAAtB,WAAA,2BAAAyB,OAAsCW,EAAAd,EAAAtB,UAAA2B,WAAA9B,OAAAE,eAAAuB,EAAAtB,WAAA,2BAAAyB,MAAA3C,KAAA2C,KACtC,IAAMrC,GAAeF,EAAwBC,EAGzCC,KAAgBqC,SAAUrC,IAAgBQ,aAAYI,aACxDyB,KAAKrC,GAAgB+C,MAhDJH,IAAA,oBAAAC,MAAA,WAqDnBG,EAAAd,EAAAtB,UAAA2B,WAAA9B,OAAAE,eAAAuB,EAAAtB,WAAA,oBAAAyB,OAA+BW,EAAAd,EAAAtB,UAAA2B,WAAA9B,OAAAE,eAAAuB,EAAAtB,WAAA,oBAAAyB,MAAA3C,KAAA2C,MAC/BY,EAAAC,QAAeC,UAAUd,SAtDNO,IAAA,mBAAAC,MAAA,SAyEJnB,EAAWmB,GAC1B,MAAOI,GAAAC,QAAeE,aAAaf,KAAMX,EAAWmB,MA1EjCD,IAAA,eAAAC,MAAA,SA0FRQ,EAAWR,GACtB,MAAOI,GAAAC,QAAeI,YAAYjB,KAAMgB,EAAWR,QA3FhCD,IAAA,qBAAAW,IAAA,WA0DnB,MAAOjD,GAAmB+B,UA1DPH,GAqCYD,EA2DnC,OAAOC,ynBCzCT,QAASsB,GAAavB,EAAMwB,GAC1B,GAAqB,kBAAVA,GAET,MAAOA,GAAMxB,EACR,IAECyB,GAFD,SAAAC,GAAA,QAAAD,KAAA,MAAAtB,GAAAC,KAAAqB,GAAApB,EAAAD,MAAAqB,EAAAnB,WAAA9B,OAAAE,eAAA+C,IAAAlB,MAAAH,KAAAI,YAAA,MAAAC,GAAAgB,EAAAC,GAAAD,GAEkBzB,EAEvB,OADA2B,GAAkBH,EAAOC,EAAS9C,UAAWiD,GACtCH,EASX,QAASE,GAAkBE,EAAQC,GAAkC,GAA1BC,GAA0BvB,UAAA9C,OAAA,GAAAsE,SAAAxB,UAAA,GAAAA,UAAA,KAOnE,OANAhC,QAAOO,oBAAoB8C,GAAQI,QAAQ,SAAAC,GACzC,GAAIH,EAAoBrC,QAAQwC,GAAQ,EAAG,CACzC,GAAMC,GAAa3D,OAAOU,yBAAyB2C,EAAQK,EAC3D1D,QAAO4D,eAAeN,EAAQI,EAAMC,MAGjCL,sTAvFM,SAAC9B,GAAS,GASjBqC,GATiB,SAAAnC,GAAA,QAAAmC,KAAA,MAAAlC,GAAAC,KAAAiC,GAAAhC,EAAAD,MAAAiC,EAAA/B,WAAA9B,OAAAE,eAAA2D,IAAA9B,MAAAH,KAAAI,YAAA,MAAAC,GAAA4B,EAAAnC,GAAAQ,EAAA2B,EAAA,OAAA1B,IAAA,UAAAC,MAAA,WAuCK,IAAA,GAAA0B,GAAA9B,UAAA9C,OAAR6E,EAAQC,MAAAF,GAAAG,EAAA,EAAAA,EAAAH,EAAAG,IAARF,EAAQE,GAAAjC,UAAAiC,EAKxB,OAAOF,GAAOG,OAAOnB,EAAcnB,UA5ChBiC,GASErC,EAwCzB,OAAOqC,GAKT,IAAMT,IACJ,wuBCyCF,QAASe,GAAsBC,EAAOC,GAAkB,GAAAC,GAChDC,EAAWP,MAAM7D,UAAUU,IAAI5B,KAAKmF,EAAO,SAAAI,GAK/C,GAAMC,GAAoC,mBAApBC,iBACpBF,YAAgBE,iBACG,SAAnBF,EAAKG,SACP,IAAIF,EAAQ,CAEV,GAAMG,GAAgBJ,EAAKI,eAAgBC,SAAS,GACpD,OAAOD,GACLT,EAAsBS,EAAeP,MAElC,MAAIG,aAAgBzE,cAEjByE,GACCA,YAAgBM,OAAQT,GAEzBG,QAMNO,GAAYT,MAAGnD,OAAHY,MAAAuC,EAAAU,EAAaT,GAC/B,OAAOQ,uTA3HM,SAACvD,GAAS,GA6CjByD,GA7CiB,SAAAvD,GAAA,QAAAuD,KAAA,MAAAtD,GAAAC,KAAAqD,GAAApD,EAAAD,MAAAqD,EAAAnD,WAAA9B,OAAAE,eAAA+E,IAAAlD,MAAAH,KAAAI,YAAA,MAAAC,GAAAgD,EAAAvD,GAAAQ,EAAA+C,IAAA9C,IAAA,sBAAAW,IAAA,WAsDnB,MAAOqB,GAAsBvC,KAAKsD,UAAU,MAtDzB/C,IAAA,wBAAAW,IAAA,WAiEnB,MAAOqB,GAAsBvC,KAAKuD,YAAY,MAjE3BhD,IAAA,yBAAAW,IAAA,WA2EnB,GAAMsC,GAAUxD,KAAKyD,sBAAsBxE,IAAI,SAASyE,GACtD,MAAOA,GAAMC,aAEf,OAAOH,GAAQI,KAAK,QA9EDP,GA6CWzD,EAsClC,OAAOyD,gqBCnFM,SAACzD,GAAS,GAuBjBiE,GAvBiB,SAAA/D,GAyBrB,QAAA+D,KAAc9D,EAAAC,KAAA6D,EAAA,IAAAC,GAAA7D,EAAAD,MAAA6D,EAAA3D,WAAA9B,OAAAE,eAAAuF,IAAAxG,KAAA2C,MAEZ,IAAI8D,EAAKC,WAAY,CAOnBD,EAAKE,IACL,IAAMC,GAAeH,EAAKC,WAAWG,iBAAiB,WACnDrC,QAAQxE,KAAK4G,EAAc,SAAArB,GAC5B,GAAMuB,GAAKvB,EAAKwB,aAAa,KAC7BN,GAAKE,EAAEG,GAAMvB,IAbL,MAAAkB,GAzBO,MAAAzD,GAAAwD,EAAA/D,GAAA+D,GAuBejE,EA6BtC,OAAOiE,wpBCUT,QAASQ,GAA4BC,GACnC,GAAMC,GAAWC,SAASC,cAAc,YAIlCC,EAAMF,SAASC,cAAc,MAEnC,KADAC,EAAIJ,UAAYA,EACTI,EAAInB,WAAWjG,OAAS,GAC7BiH,EAASI,QAAQC,YAAYF,EAAInB,WAAW,GAE9C,OAAOgB,GAIT,QAASM,GAAmBN,EAAUO,GACpCC,OAAOC,cAAcC,UAAUC,YAAYX,EAASI,QAASG,mDA9E/D,IAAAK,GAAArI,EAAA,mCAIe,SAAC8C,GAAS,GAwBjBwF,GAxBiB,SAAAtF,GA8BrB,QAAAsF,KAAcrF,EAAAC,KAAAoF,EAAA,IAAAtB,GAAA7D,EAAAD,MAAAoF,EAAAlF,WAAA9B,OAAAE,eAAA8G,IAAA/H,KAAA2C,OAERuE,EAAWT,EAAKuB,EAAAxE,QAAQ0D,SAG5B,IAAIA,EAAU,CAEY,gBAAbA,KAETA,EAAWF,EAA4BE,IAGrCQ,OAAOO,mBACTT,EAAmBN,EAAUT,EAAKf,UAGpC,IAAMwC,GAAOzB,EAAK0B,cAAeC,KAAM,SACjCC,EAAQlB,SAASmB,WAAWpB,EAASI,SAAS,EACpDY,GAAKX,YAAYc,GAlBP,MAAA5B,GA9BO,MAAAzD,GAAA+E,EAAAtF,GAAAsF,GAwBMxF,EA8B7B,OAAOwF,0DCtBM,SAASQ,GAAaC,GACnC,MAAyB,kBAAXC,QACZA,OAAOD,GADF,IAEDA,6DAHgBD,0FCsExB,QAASG,GAAsBC,EAAStI,EAAe8C,GACrD,GAAc,OAAVA,GAAmC,mBAAVA,GAC3BwF,EAAQC,gBAAgBvI,OACnB,CACL,GAAMwI,GAAOC,OAAO3F,EAEhBwF,GAAQ5B,aAAa1G,KAAmBwI,GAC1CF,EAAQjF,aAAarD,EAAe8C,oDAjH1C,IAAA4F,GAAAtJ,EAAA,yBACAuJ,EAAAvJ,EAAA,wBAIMwJ,GAA4B,EAAAC,EAAA1F,SAAa,uBACzC2F,GAA0B,EAAAD,EAAA1F,SAAa,qBACvC4F,GAAuB,EAAAF,EAAA1F,SAAa,6BAqBxCC,UAfa,SAeHkF,GAIR,GAHAA,EAAQM,IAA6B,EAGjCN,EAAQQ,GAA0B,CACpC,IAAK,GAAInH,KAAa2G,GAAQQ,GAA0B,CACtD,GAAMhG,GAAQwF,EAAQQ,GAAyBnH,EAC/C0G,GAAsBC,EAAS3G,EAAWmB,GAE5CwF,EAAQQ,GAA2B,KAIrC,GAAIR,EAAQS,GAAuB,CACjC,IAAK,GAAIzF,KAAagF,GAAQS,GAAuB,CACnD,GAAMC,GAAQV,EAAQS,GAAsBzF,IAC5C,EAAA2F,EAAA9F,SAAYmF,EAAShF,EAAW0F,GAElCV,EAAQS,GAAwB,OAgBpC1F,aAjDa,SAiDAiF,EAAS3G,EAAWmB,GAC3BwF,EAAQM,GAEVP,EAAsBC,EAAS3G,EAAWmB,IAGrCwF,EAAQQ,KACXR,EAAQQ,OAEVR,EAAQQ,GAAyBnH,GAAamB,IAiBlDS,YA3Ea,SA2ED+E,EAAShF,EAAWR,GAC1BwF,EAAQM,IAEV,EAAAK,EAAA9F,SAAYmF,EAAShF,EAAWR,IAG3BwF,EAAQS,KACXT,EAAQS,OAEVT,EAAQS,GAAsBzF,GAAaR,iLCjGjD,IAAA4F,GAAAtJ,EAAA,yBAuBM8J,GAmBJC,UAAU,EAAAN,EAAA1F,SAAa,YAevBiG,UAAU,EAAAP,EAAA1F,SAAa,YASvBkG,QAAQ,EAAAR,EAAA1F,SAAa,UAUrBmG,OAAO,EAAAT,EAAA1F,SAAa,SASpBoG,QAAQ,EAAAV,EAAA1F,SAAa,UASrBqG,SAAS,EAAAX,EAAA1F,SAAa,WAUtBsG,SAAS,EAAAZ,EAAA1F,SAAa,WAStBuG,MAAM,EAAAb,EAAA1F,SAAa,QAUnBwG,WAAW,EAAAd,EAAA1F,SAAa,aAUxByG,cAAc,EAAAf,EAAA1F,SAAa,gBAW3B0G,cAAc,EAAAhB,EAAA1F,SAAa,gBAU3B2G,SAAS,EAAAjB,EAAA1F,SAAa,WAStB0D,UAAU,EAAAgC,EAAA1F,SAAa,uBAGV+F,wDChJA,SAAS3F,GAAY+E,EAAShF,EAAWyG,GACtD,GAAMC,GAAY1B,EAAQ0B,UACpBC,EAA6B,mBAAVF,IACtBC,EAAUE,SAAS5G,GACpByG,CAMF,OALIE,GACFD,EAAUG,IAAI7G,GAEd0G,EAAUI,OAAO9G,GAEZ2G,6DAVe1G,2FCfxB,GAAA8G,GAAAjL,EAAA,6BAEAiI,QAAOiD,MAAQjD,OAAOiD,UACtBjD,OAAOiD,MAAMC,cAAbC,EAAArH,qrBCwHA,QAASsH,GAAQnC,GACf,GAAMoC,GAAMrD,OAAOsD,SAASC,KACxBvK,EAAA,MACJ,IAAIiI,EAAQuC,SAAU,CAEpB,GAAIC,GAASxC,EAAQsC,IAGjBE,GAAOlL,OAAS8K,EAAI9K,QAAgC,MAAtBkL,EAAOC,QAAO,KAC9CD,GAAU,KAEZzK,EAASqK,EAAIK,OAAO,EAAGD,EAAOlL,UAAYkL,MAG1CzK,GAASqK,IAAQpC,EAAQsC,IAE3BtC,GAAQ0C,QAAU3K,otBAlJpBqI,EAAAtJ,EAAA,wDACA6C,EAAA7C,EAAA,0DACAqI,EAAArI,EAAA,mDACA6L,EAAA7L,EAAA,0EAIM8L,GAAiB,EAAArC,EAAA1F,SAAa,YAyB9BoH,cAEJ,QAAAA,KAAclI,EAAAC,KAAAiI,EAAA,IAAAnE,GAAA7D,EAAAD,MAAAiI,EAAA/H,WAAA9B,OAAAE,eAAA2J,IAAA5K,KAAA2C,MAAA,OAGZ+E,QAAO8D,iBAAiB,WAAY,SAAAC,GAClCX,EAAArE,KAMFiB,OAAO8D,iBAAiB,aAAc,SAAAC,GACpCX,EAAArE,KAI2B,mBAAlBA,GAAKyE,WACdzE,EAAKyE,SAAWzE,EAAKuB,EAAAxE,QAAQgG,UAAU0B,UAhB7BzE,+DAuCZnD,EAAAsH,EAAA1J,UAAA2B,WAAA9B,OAAAE,eAAA2J,EAAA1J,WAAA,oBAAAyB,OAA+BW,EAAAsH,EAAA1J,UAAA2B,WAAA9B,OAAAE,eAAA2J,EAAA1J,WAAA,oBAAAyB,MAAA3C,KAAA2C,MAC/BY,EAAAC,QAAeC,UAAUd,MACzBmI,EAAQnI,uCAXR,MAAOA,MAAK4I,iBAEDpI,GAEXR,KAAK4I,GAAqC,SAAlBzC,OAAO3F,GAC/B2H,EAAQnI,sCAiBR,MAAOA,MAAK0H,UAAUE,SAAS,yBAErBpH,GACVI,EAAAC,QAAeI,YAAYjB,KAAM,UAAWQ,GAC5CR,KAAK+I,cAAc,GAAIC,aAAY,2BAGhC3D,EAAAxE,QAAQgG,wBACX,GAAMA,GAAWlG,EAAAsH,EAAA1J,UAAA2B,WAAA9B,OAAAE,eAAA2J,EAAA1J,WAAM8G,EAAAxE,QAAQgG,SAAd7G,SAEjB,OADA6G,GAAS0B,UAAW,EACb1B,+BAKP,MAAAlG,GAAAsH,EAAA1J,UAAA2B,WAAA9B,OAAAE,eAAA2J,EAAA1J,WAAA,OAAAyB,oBAEOQ,GACPyI,EAAAhB,EAAA1J,UAAA2B,WAAA9B,OAAAE,eAAA2J,EAAA1J,WAAA,OAAaiC,EAAbR,MACAmI,EAAQnI,aAGLqF,EAAAxE,QAAQ0D,wBAGX,MAAA,+PA/EwB2E,EAAArI,QAAuBsI,KAAK,KAsHxDC,gBAAeC,OAAO,uBAAwBpB,+5BCtJ9C,IAAAqB,GAAAxM,EAAA,qEACAyM,EAAAzM,EAAA,2DACA0M,EAAA1M,EAAA,oEACA2M,EAAA3M,EAAA,wEACA4M,EAAA5M,EAAA,+DAuBM6M,oIAAoB,EAAAC,EAAA/I,SAAgB1C,aAAa0L,QAA7BC,EAAAjJ,QAAAkJ,EAAAlJ,QAAAmJ,EAAAnJ,QAAAoJ,EAAApJ,oBAOX8I,m8BC+Pf,QAASO,GAAuBpI,EAAMC,GACpC,GAAMoI,IACJC,aAAcrI,EAAWqI,aACzBC,WAAYtI,EAAWsI,WAezB,OAbItI,GAAWb,MACbiJ,EAASjJ,IAAM,WACb,MAAOlB,MAAKsK,MAAMxI,KAGlBC,EAAWhD,MACboL,EAASpL,IAAM,SAASyB,GACtBR,KAAKsK,MAAMxI,GAAQtB,IAGnBuB,EAAWwI,WACbJ,EAASI,SAAWxI,EAAWwI,UAE1BJ,4SAnTTK,EAAA1N,EAAA,mDACAqI,EAAArI,EAAA,mDAwBM2N,GACJC,SAAU,UACVC,YAAa,UACbC,SAAU,UACVC,QAAS,UACTC,IAAK,UACLC,KAAM,UACNrG,KAAM,UACNsG,IAAK,UACLC,IAAK,UACLC,UAAW,UACXC,MAAO,QAAS,UAChBC,OAAQ,QACRC,IAAK,UACLC,IAAK,UACLC,IAAK,UACLC,IAAK,UACLC,IAAK,UACLC,IAAK,UACLC,QAAS,QACTC,KAAM,QAAS,QAAS,QACxBC,OAAQ,QAAS,SAAU,QAAS,SAAU,QAC9CC,QAAS,QAAS,UAClBC,IAAK,UACLC,MAAO,QACPC,MAAO,UACPC,QAAS,QAAS,UAClBC,IAAK,UACLC,GAAI,UACJC,QAAS,QAAS,QAClBC,QAAS,SAAU,UACnBC,OAAQ,UACRC,OAAQ,UACRC,OAAQ,UACRC,UAAW,SAAU,SAAU,WAK3BC,GACJC,OAAO,EACPC,QAAQ,EACRC,OAAO,GAMHC,GACJ,UACA,UACA,QACA,aACA,SACA,KACA,MACA,KACA,WACA,aACA,SACA,SACA,OACA,KACA,KACA,KACA,KACA,KACA,KACA,SACA,SACA,KACA,KACA,OACA,MACA,WACA,KACA,SACA,IACA,MACA,UACA,QACA,QACA,KACA,SA6DIC,cAEJ,QAAAA,KAAcjN,EAAAC,KAAAgN,EAAA,IAAAlJ,GAAA7D,EAAAD,MAAAgN,EAAA9M,WAAA9B,OAAAE,eAAA0O,IAAA3P,KAAA2C,OAUNiN,EAAaxC,EAAc3G,EAAKoJ,YAV1B,OAWZD,GAAWpL,QAAQ,SAAAsL,GACjBrJ,EAAKwG,MAAMzB,iBAAiBsE,EAAW,SAAAC,GACrC,GAAMtE,GAAQ,GAAIuE,OAAMF,GACtBG,QAASX,EAAaQ,KAAc,GAEtCrJ,GAAKiF,cAAcD,OAhBXhF,qDA8BZ,MAAO9D,MAAKsK,MAAMlG,aAAa,4BAEnBmJ,GAEZvN,KAAKsK,MAAMvJ,aAAa,aAAcwM,iCAStC,MAAOvN,MAAKgE,EAAEsG,aAiCXjF,EAAAxE,QAAQ0D,wBACX,GAAMiJ,GAAUT,EAAczN,QAAQU,KAAKkN,UAAY,EACrD,QACA,cACF,OAAA,2BAAkCM,EAAlC,aAAsDxN,KAAKkN,QAA3D,8BAAgGlN,KAAKkN,uCAc3FO,GAAY,GAGhBC,GAHgB,SAAAC,GAAA,QAAAD,KAAA,MAAA3N,GAAAC,KAAA0N,GAAAzN,EAAAD,MAAA0N,EAAAxN,WAAA9B,OAAAE,eAAAoP,IAAAvN,MAAAH,KAAAI,YAAA,MAAAC,GAAAqN,EAAAC,GAAAD,GAGAV,EAGtBU,GAAQnP,UAAU2O,QAAUO,CAG5B,IAAMzH,GAAUxB,SAASC,cAAcgJ,GACjCG,EAAmB5H,EAAQxH,YAAYD,UACvCsP,EAAQzP,OAAOO,oBAAoBiP,EAOzC,OANAC,GAAMhM,QAAQ,SAAAC,GACV,GAAMC,GAAa3D,OAAOU,yBAAyB8O,EAAkB9L,GAC/DqI,EAAWD,EAAuBpI,EAAMC,EAC9C3D,QAAO4D,eAAe0L,EAAQnP,UAAWuD,EAAMqI,KAG5CuD,8BA4BIV","file":"basic-current-anchor.js","sourcesContent":["(function e(t,n,r){function s(o,u){if(!n[o]){if(!t[o]){var a=typeof require==\"function\"&&require;if(!u&&a)return a(o,!0);if(i)return i(o,!0);var f=new Error(\"Cannot find module '\"+o+\"'\");throw f.code=\"MODULE_NOT_FOUND\",f}var l=n[o]={exports:{}};t[o][0].call(l.exports,function(e){var n=t[o][1][e];return s(n?n:e)},l,l.exports,e,t,n,r)}return n[o].exports}var i=typeof require==\"function\"&&require;for(var o=0;o {\n\n /**\n * Mixin which marshalls attributes to properties and vice versa.\n *\n * If your component exposes a setter for a property, it's generally a good\n * idea to let devs using your component be able to set that property in HTML\n * via an element attribute. You can code that yourself by writing an\n * `attributeChangedCallback`, or you can use this mixin to get a degree of\n * automatic support.\n *\n * This mixin implements an `attributeChangedCallback` that will attempt to\n * convert a change in an element attribute into a call to the corresponding\n * property setter. Attributes typically follow hyphenated names (\"foo-bar\"),\n * whereas properties typically use camelCase names (\"fooBar\"). This mixin\n * respects that convention, automatically mapping the hyphenated attribute\n * name to the corresponding camelCase property name.\n *\n * Example: You define a component using this mixin:\n *\n * class MyElement extends AttributeMarshallingMixin(HTMLElement) {\n * get fooBar() { return this._fooBar; }\n * set fooBar(value) { this._fooBar = value; }\n * }\n * customElements.define('my-element', MyElement);\n *\n * If someone then instantiates your component in HTML:\n *\n * \n *\n * Then, after the element has been upgraded, the `fooBar` setter will\n * automatically be invoked with the initial value \"Hello\".\n *\n * For the time being, this mixin only supports string-valued properties.\n * If you'd like to convert string attributes to other types (numbers,\n * booleans), you need to implement `attributeChangedCallback` yourself.\n */\n class AttributeMarshalling extends base {\n\n /*\n * Handle a change to the attribute with the given name.\n */\n attributeChangedCallback(attributeName, oldValue, newValue) {\n if (super.attributeChangedCallback) { super.attributeChangedCallback(); }\n const propertyName = attributeToPropertyName(attributeName);\n // If the attribute name corresponds to a property name, set the property.\n // Ignore standard HTMLElement properties handled by the DOM.\n if (propertyName in this && !(propertyName in HTMLElement.prototype)) {\n this[propertyName] = newValue;\n }\n }\n\n connectedCallback() {\n if (super.connectedCallback) { super.connectedCallback(); }\n safeAttributes.connected(this);\n }\n\n static get observedAttributes() {\n return attributesForClass(this);\n }\n\n /**\n * Set/unset the attribute with the indicated name.\n *\n * This method exists primarily to handle the case where an element wants to\n * set a default property value that should be reflected as an attribute. An\n * important limitation of custom element consturctors is that they cannot\n * set attributes. A call to `reflectAttribute` during the constructor will\n * be deferred until the element is connected to the document.\n *\n * @param {string} attribute - The name of the *attribute* (not property) to set.\n * @param {object} value - The value to set. If null, the attribute will be removed.\n */\n reflectAttribute(attribute, value) {\n return safeAttributes.setAttribute(this, attribute, value);\n }\n\n /**\n * Set/unset the class with the indicated name.\n *\n * This method exists primarily to handle the case where an element wants to\n * set a default property value that should be reflected as as class. An\n * important limitation of custom element consturctors is that they cannot\n * set attributes, including the `class` attribute. A call to\n * `reflectClass` during the constructor will be deferred until the element\n * is connected to the document.\n *\n * @param {string} className - The name of the class to set.\n * @param {object} value - True to set the class, false to remove it.\n */\n reflectClass(className, value) {\n return safeAttributes.toggleClass(this, className, value);\n }\n\n }\n\n return AttributeMarshalling;\n};\n\n\n// Convert hyphenated foo-bar attribute name to camel case fooBar property name.\nfunction attributeToPropertyName(attributeName) {\n let propertyName = attributeToPropertyNames[attributeName];\n if (!propertyName) {\n // Convert and memoize.\n const hypenRegEx = /-([a-z])/g;\n propertyName = attributeName.replace(hypenRegEx,\n match => match[1].toUpperCase());\n attributeToPropertyNames[attributeName] = propertyName;\n }\n return propertyName;\n}\n\nfunction attributesForClass(classFn) {\n\n // We treat the element base classes as if they have no attributes, since we\n // don't want to receive attributeChangedCallback for them.\n if (classFn === HTMLElement || classFn === Object) {\n return [];\n }\n\n // Get attributes for parent class.\n const baseClass = Object.getPrototypeOf(classFn.prototype).constructor;\n const baseAttributes = attributesForClass(baseClass);\n\n // Get attributes for this class.\n const propertyNames = Object.getOwnPropertyNames(classFn.prototype);\n const setterNames = propertyNames.filter(propertyName =>\n typeof Object.getOwnPropertyDescriptor(\n classFn.prototype, propertyName).set === 'function');\n const attributes = setterNames.map(setterName =>\n propertyNameToAttribute(setterName));\n\n // Merge.\n const diff = attributes.filter(attribute =>\n baseAttributes.indexOf(attribute) < 0);\n return baseAttributes.concat(diff);\n}\n\n// Convert a camel case fooBar property name to a hyphenated foo-bar attribute.\nfunction propertyNameToAttribute(propertyName) {\n let attribute = propertyNamesToAttributes[propertyName];\n if (!attribute) {\n // Convert and memoize.\n const uppercaseRegEx = /([A-Z])/g;\n attribute = propertyName.replace(uppercaseRegEx, '-$1').toLowerCase();\n }\n return attribute;\n}\n","/* Exported function extends a base class with Composable. */\nexport default (base) => {\n\n /**\n * Mixin to make a class more easily composable with other mixins.\n *\n * This mixin contributes a `compose` method that applies a set of mixin\n * functions and returns the resulting new class. This sugar can make the\n * application of many mixins at once easier to read.\n */\n class Composable extends base {\n\n /**\n * Apply a set of mixin functions or mixin objects to the present class and\n * return the new class.\n *\n * Instead of writing:\n *\n * let MyClass = Mixin1(Mixin2(Mixin3(Mixin4(Mixin5(BaseClass)))));\n *\n * You can write:\n *\n * let MyClass = ComposableMixin(BaseClass).compose(\n * Mixin1,\n * Mixin2,\n * Mixin3,\n * Mixin4,\n * Mixin5\n * );\n *\n * This function can also take mixin objects. A mixin object is just a\n * shorthand for a mixin function that creates a new subclass with the given\n * members. The mixin object's members are *not* copied directly onto the\n * prototype of the base class, as with traditional mixins.\n *\n * In addition to providing syntactic sugar, this mixin can be used to\n * define a class in ES5, which lacks ES6's `class` keyword.\n *\n * @param {...mixins} mixins - A set of mixin functions or objects to apply.\n */\n static compose(...mixins) {\n // We create a new subclass for each mixin in turn. The result becomes\n // the base class extended by any subsequent mixins. It turns out that\n // we can use Array.reduce() to concisely express this, using the current\n // object as the seed for reduce().\n return mixins.reduce(composeClass, this);\n }\n\n }\n\n return Composable;\n};\n\n\n// Properties defined by Object that we don't want to mixin.\nconst NON_MIXABLE_OBJECT_PROPERTIES = [\n 'constructor'\n];\n\n/*\n * Apply the mixin to the given base class to return a new class.\n * The mixin can either be a function that returns the modified class, or a\n * plain object whose members will be copied to the new class' prototype.\n */\nfunction composeClass(base, mixin) {\n if (typeof mixin === 'function') {\n // Mixin function\n return mixin(base);\n } else {\n // Mixin object\n class Subclass extends base {}\n copyOwnProperties(mixin, Subclass.prototype, NON_MIXABLE_OBJECT_PROPERTIES);\n return Subclass;\n }\n}\n\n\n/*\n * Copy the given properties/methods to the target.\n * Return the updated target.\n */\nfunction copyOwnProperties(source, target, ignorePropertyNames = []) {\n Object.getOwnPropertyNames(source).forEach(name => {\n if (ignorePropertyNames.indexOf(name) < 0) {\n const descriptor = Object.getOwnPropertyDescriptor(source, name);\n Object.defineProperty(target, name, descriptor);\n }\n });\n return target;\n}\n","/* Exported function extends a base class with DistributedChildren. */\nexport default (base) => {\n\n /**\n * Mixin which defines helpers for accessing a component's distributed\n * children as a flattened array or string.\n *\n * The standard DOM API provides several ways of accessing child content:\n * `children`, `childNodes`, and `textContent`. None of these functions are\n * Shadow DOM aware. This mixin defines variations of those functions that\n * *are* Shadow DOM aware.\n *\n * Example: you create a component `` that displays a number\n * equal to the number of children placed inside that component. If someone\n * instantiates your component like:\n *\n * \n *
\n *
\n *
\n * \n *\n * Then the component should show \"3\", because there are three children. To\n * calculate the number of children, the component can just calculate\n * `this.children.length`. However, suppose someone instantiates your\n * component inside one of their own components, and puts a `` element\n * inside your component:\n *\n * \n * \n * \n *\n * If your component only looks at `this.children`, it will always see exactly\n * one child — the `` element. But the user looking at the page will\n * *see* any nodes distributed to that slot. To match what the user sees, your\n * component should expand any `` elements it contains.\n *\n * That is the problem this mixin solves. After applying this mixin, your\n * component code has access to `this.distributedChildren`, whose `length`\n * will return the total number of all children distributed to your component\n * in the composed tree.\n *\n * Note: The latest Custom Elements API design calls for a new function,\n * `getAssignedNodes` that takes an optional `deep` parameter, that will solve\n * this problem at the API level.\n */\n class DistributedChildren extends base {\n\n /**\n * An in-order collection of distributed children, expanding any slot\n * elements. Like the standard children property, this skips text nodes.\n *\n * @type {HTMLElement[]}\n */\n get distributedChildren() {\n return expandContentElements(this.children, false);\n }\n\n /**\n * An in-order collection of distributed child nodes, expanding any slot\n * elements. Like the standard childNodes property, this includes text\n * nodes.\n *\n * @type {Node[]}\n */\n get distributedChildNodes() {\n return expandContentElements(this.childNodes, true);\n }\n\n /**\n * The concatenated text content of all distributed child nodes, expanding\n * any slot elements.\n *\n * @type {string}\n */\n get distributedTextContent() {\n const strings = this.distributedChildNodes.map(function(child) {\n return child.textContent;\n });\n return strings.join('');\n }\n\n }\n\n return DistributedChildren;\n};\n\n\n/*\n * Given a array of nodes, return a new array with any content elements expanded\n * to the nodes distributed to that content element. This rule is applied\n * recursively.\n *\n * If includeTextNodes is true, text nodes will be included, as in the\n * standard childNodes property; by default, this skips text nodes, like the\n * standard children property.\n */\nfunction expandContentElements(nodes, includeTextNodes) {\n const expanded = Array.prototype.map.call(nodes, node => {\n // We want to see if the node is an instanceof HTMLSlotELement, but\n // that class won't exist if the browser that doesn't support native\n // Shadow DOM and if the Shadow DOM polyfill hasn't been loaded. Instead,\n // we do a simplistic check to see if the tag name is \"slot\".\n const isSlot = typeof HTMLSlotElement !== 'undefined' ?\n node instanceof HTMLSlotElement :\n node.localName === 'slot';\n if (isSlot) {\n // Use the nodes assigned to this node instead.\n const assignedNodes = node.assignedNodes({ flatten: true });\n return assignedNodes ?\n expandContentElements(assignedNodes, includeTextNodes) :\n [];\n } else if (node instanceof HTMLElement) {\n // Plain element; use as is.\n return [node];\n } else if (node instanceof Text && includeTextNodes) {\n // Text node.\n return [node];\n } else {\n // Comment, processing instruction, etc.; skip.\n return [];\n }\n });\n const flattened = [].concat(...expanded);\n return flattened;\n}\n","/* Exported function extends a base class with ShadowElementReferences. */\nexport default (base) => {\n\n /**\n * Mixin to create references to elements in a component's Shadow DOM subtree.\n *\n * This adds a member on the component called `this.$` that can be used to\n * reference shadow elements with IDs. E.g., if component's shadow contains an\n * element ``, then this mixin will create a member\n * `this.$.foo` that points to that button.\n *\n * Such references simplify a component's access to its own elements. In\n * exchange, this mixin trades off a one-time cost of querying all elements in\n * the shadow tree instead of paying an ongoing cost to query for an element\n * each time the component wants to inspect or manipulate it.\n *\n * This mixin expects the component to define a Shadow DOM subtree. You can\n * create that tree yourself, or make use of\n * [ShadowTemplateMixin](ShadowTemplateMixin.md).\n *\n * This mixin is inspired by Polymer's [automatic\n * node finding](https://www.polymer-project.org/1.0/docs/devguide/local-dom.html#node-finding)\n * feature.\n */\n class ShadowElementReferences extends base {\n\n constructor() {\n super();\n if (this.shadowRoot) {\n // Look for elements in the shadow subtree that have id attributes.\n // An alternatively implementation of this mixin would be to just define\n // a this.$ getter that lazily does this search the first time someone\n // tries to access this.$. That might introduce some complexity – if the\n // the tree changed after it was first populated, the result of\n // searching for a node might be somewhat unpredictable.\n this.$ = {};\n const nodesWithIds = this.shadowRoot.querySelectorAll('[id]');\n [].forEach.call(nodesWithIds, node => {\n const id = node.getAttribute('id');\n this.$[id] = node;\n });\n }\n }\n\n /**\n * The collection of references to the elements with IDs in a component's\n * Shadow DOM subtree.\n *\n * @type {object}\n * @member $\n */\n }\n\n return ShadowElementReferences;\n};\n","import symbols from '../src/symbols';\n\n\n/* Exported function extends a base class with ShadowTemplate. */\nexport default (base) => {\n\n /**\n * Mixin for stamping a template into a Shadow DOM subtree upon component\n * instantiation.\n *\n * To use this mixin, define a `template` property as a string or HTML\n * `` element:\n *\n * class MyElement extends ShadowTemplateMixin(HTMLElement) {\n * get [symbols.template]() {\n * return `Hello, world .`;\n * }\n * }\n *\n * When your component class is instantiated, a shadow root will be created on\n * the instance, and the contents of the template will be cloned into the\n * shadow root. If your component does not define a `template` property, this\n * mixin has no effect.\n *\n * For the time being, this extension retains support for Shadow DOM v0. That\n * will eventually be deprecated as browsers (and the Shadow DOM polyfill)\n * implement Shadow DOM v1.\n */\n class ShadowTemplate extends base {\n\n /*\n * If the component defines a template, a shadow root will be created on the\n * component instance, and the template stamped into it.\n */\n constructor() {\n super();\n let template = this[symbols.template];\n // TODO: Save the processed template with the component's class prototype\n // so it doesn't need to be processed with every instantiation.\n if (template) {\n\n if (typeof template === 'string') {\n // Upgrade plain string to real template.\n template = createTemplateWithInnerHTML(template);\n }\n\n if (window.ShadowDOMPolyfill) {\n shimTemplateStyles(template, this.localName);\n }\n\n const root = this.attachShadow({ mode: 'open' });\n const clone = document.importNode(template.content, true);\n root.appendChild(clone);\n }\n }\n\n }\n\n return ShadowTemplate;\n};\n\n\n// Convert a plain string of HTML into a real template element.\nfunction createTemplateWithInnerHTML(innerHTML) {\n const template = document.createElement('template');\n // REVIEW: Is there an easier way to do this?\n // We'd like to just set innerHTML on the template content, but since it's\n // a DocumentFragment, that doesn't work.\n const div = document.createElement('div');\n div.innerHTML = innerHTML;\n while (div.childNodes.length > 0) {\n template.content.appendChild(div.childNodes[0]);\n }\n return template;\n}\n\n// Invoke basic style shimming with ShadowCSS.\nfunction shimTemplateStyles(template, tag) {\n window.WebComponents.ShadowCSS.shimStyling(template.content, tag);\n}\n","/**\n * Helper function to create a symbol that can be used for associating private\n * data with an element.\n *\n * Mixins and component classes often want to associate private data with an\n * element instance, but JavaScript does not have direct support for true\n * private properties. One approach is to use the\n * [Symbol](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Symbol)\n * data type to set and retrieve data on an element.\n *\n * Unfortunately, the Symbol type is not available in Internet Explorer 11. The\n * `createSymbol` helper function exists as a workaround for IE 11. Rather than\n * returning a true Symbol, it simply returns an underscore-prefixed string.\n *\n * Usage:\n *\n * const fooSymbol = createSymbol('foo');\n *\n * class MyElement extends HTMLElement {\n * get foo() {\n * return this[fooSymbol];\n * }\n * set foo(value) {\n * this[fooSymbol] = value;\n * }\n * }\n *\n * In IE 11, this sample will \"hide\" data behind an instance property this._foo.\n * The use of the underscore is meant to reduce (not eliminate) the potential\n * for name conflicts, and discourage (not prevent) external access to this\n * data. In modern browsers, the above code will eliminate the potential of\n * naming conflicts, and better hide the data behind a real Symbol.\n *\n * @function createSymbol\n * @param {string} description - A string to identify the symbol when debugging\n */\nexport default function createSymbol(description) {\n return typeof Symbol === 'function' ?\n Symbol(description) :\n `_${description}`;\n}\n","import createSymbol from './createSymbol';\nimport toggleClass from './toggleClass';\n\n\n// Symbols for private data members on an element.\nconst safeToSetAttributesSymbol = createSymbol('safeToSetAttributes');\nconst pendingAttributesSymbol = createSymbol('pendingAttributes');\nconst pendingClassesSymbol = createSymbol('pendingClasses');\n\n\n/**\n * Helper functions for updating attributes, including the `class` attribute.\n */\nexport default {\n\n /**\n * Perform any pending updates to attributes and classes.\n *\n * This writes any `setAttribute` or `toggleClass` values that were performed\n * before an element was attached to the document for the first time.\n *\n * This method should be called by mixins/components in their\n * `connectedCallback`. If mulitple mixins/components invoke this during the\n * same `connectedCallback`, only the first call will have any effect. The\n * subsequent calls will be harmless.\n *\n * @param {HTMLElement} element - The element being added to the document.\n */\n connected(element) {\n element[safeToSetAttributesSymbol] = true;\n\n // Set any pending attributes.\n if (element[pendingAttributesSymbol]) {\n for (let attribute in element[pendingAttributesSymbol]) {\n const value = element[pendingAttributesSymbol][attribute];\n setAttributeToElement(element, attribute, value);\n }\n element[pendingAttributesSymbol] = null;\n }\n\n // Set any pending classes.\n if (element[pendingClassesSymbol]) {\n for (let className in element[pendingClassesSymbol]) {\n const value = element[pendingClassesSymbol][className];\n toggleClass(element, className, value);\n }\n element[pendingClassesSymbol] = null;\n }\n },\n\n /**\n * Set/unset the attribute with the indicated name.\n *\n * This method exists primarily to handle the case where an element wants to\n * set a default property value that should be reflected as an attribute. An\n * important limitation of custom element consturctors is that they cannot\n * set attributes. A call to `setAttribute` during the constructor will\n * be deferred until the element is connected to the document.\n *\n * @param {string} attribute - The name of the *attribute* (not property) to set.\n * @param {object} value - The value to set. If null, the attribute will be removed.\n */\n setAttribute(element, attribute, value) {\n if (element[safeToSetAttributesSymbol]) {\n // Safe to set attributes immediately.\n setAttributeToElement(element, attribute, value);\n } else {\n // Defer setting attributes until the first time we're connected.\n if (!element[pendingAttributesSymbol]) {\n element[pendingAttributesSymbol] = {};\n }\n element[pendingAttributesSymbol][attribute] = value;\n }\n },\n\n /**\n * Set/unset the class with the indicated name.\n *\n * This method exists primarily to handle the case where an element wants to\n * set a default property value that should be reflected as as class. An\n * important limitation of custom element consturctors is that they cannot\n * set attributes, including the `class` attribute. A call to\n * `toggleClass` during the constructor will be deferred until the element\n * is connected to the document.\n *\n * @param {string} className - The name of the class to set.\n * @param {object} value - True to set the class, false to remove it.\n */\n toggleClass(element, className, value) {\n if (element[safeToSetAttributesSymbol]) {\n // Safe to set class immediately.\n toggleClass(element, className, value);\n } else {\n // Defer setting class until the first time we're connected.\n if (!element[pendingClassesSymbol]) {\n element[pendingClassesSymbol] = {};\n }\n element[pendingClassesSymbol][className] = value;\n }\n }\n\n};\n\n\n// Reflect the attribute to the given element.\n// If the value is null, remove the attribute.\nfunction setAttributeToElement(element, attributeName, value) {\n if (value === null || typeof value === 'undefined') {\n element.removeAttribute(attributeName);\n } else {\n const text = String(value);\n // Avoid recursive attributeChangedCallback calls.\n if (element.getAttribute(attributeName) !== text) {\n element.setAttribute(attributeName, value);\n }\n }\n}\n","import createSymbol from './createSymbol';\n\n/**\n * A collection of Symbol objects for standard component properties and methods.\n *\n * These Symbol objects are used to allow mixins and a component to internally\n * communicate, without exposing these properties and methods in the component's\n * public API.\n *\n * To use these Symbol objects in your own component, include this module and\n * then create a property or method whose key is the desired Symbol.\n *\n * import 'SingleSelectionMixin' from 'basic-component-mixins/src/SingleSelectionMixin';\n * import 'symbols' from 'basic-component-mixins/src/symbols';\n *\n * class MyElement extends SingleSelectionMixin(HTMLElement) {\n * [symbols.itemSelected](item, selected) {\n * // This will be invoked whenever an item is selected/deselected.\n * }\n * }\n *\n * @module symbols\n */\nconst symbols = {\n\n /**\n * Symbol for the `defaults` property.\n *\n * This property can be used to set or override defaults that will be applied\n * to a new component instance. When implementing this property, take care to\n * first acquire any defaults defined by the superclass. The standard idiom is\n * as follows:\n *\n * get [symbols.defaults]() {\n * const defaults = super[symbols.defaults] || {};\n * // Set or override default values here\n * defaults.customProperty = false;\n * return defaults;\n * }\n *\n * @var {object} defaults\n */\n defaults: createSymbol('defaults'),\n\n /**\n * Symbol for the `dragging` property.\n *\n * Components like carousels often define animated CSS transitions for\n * sliding effects. Such a transition should usually *not* be applied while\n * the user is dragging, because a CSS animation will introduce a lag that\n * makes the swipe feel sluggish. Instead, as long as the user is dragging\n * with their finger down, the transition should be suppressed. When the\n * user releases their finger, the transition can be restored, allowing the\n * animation to show the carousel sliding into its final position.\n *\n * @type {boolean} true if a drag is in progress, false if not.\n */\n dragging: createSymbol('dragging'),\n\n /**\n * Symbol for the `goDown` method.\n *\n * This method is invoked when the user wants to go/navigate down.\n *\n * @function goDown\n */\n goDown: createSymbol('goDown'),\n\n /**\n * Symbol for the `goEnd` method.\n *\n * This method is invoked when the user wants to go/navigate to the end (e.g.,\n * of a list).\n *\n * @function goEnd\n */\n goEnd: createSymbol('goEnd'),\n\n /**\n * Symbol for the `goLeft` method.\n *\n * This method is invoked when the user wants to go/navigate left.\n *\n * @function goLeft\n */\n goLeft: createSymbol('goLeft'),\n\n /**\n * Symbol for the `goRight` method.\n *\n * This method is invoked when the user wants to go/navigate right.\n *\n * @function goRight\n */\n goRight: createSymbol('goRight'),\n\n /**\n * Symbol for the `goStart` method.\n *\n * This method is invoked when the user wants to go/navigate to the start\n * (e.g., of a list).\n *\n * @function goStart\n */\n goStart: createSymbol('goStart'),\n\n /**\n * Symbol for the `goUp` method.\n *\n * This method is invoked when the user wants to go/navigate up.\n *\n * @function goUp\n */\n goUp: createSymbol('goUp'),\n\n /**\n * Symbol for the `itemAdded` method.\n *\n * This method is invoked when a new item is added to a list.\n *\n * @function itemAdded\n * @param {HTMLElement} item - the item being selected/deselected\n */\n itemAdded: createSymbol('itemAdded'),\n\n\n /**\n * Symbol for the `itemsChanged` method.\n *\n * This method is invoked when the underlying contents change. It is also\n * invoked on component initialization – since the items have \"changed\" from\n * being nothing.\n */\n itemsChanged: createSymbol('itemsChanged'),\n\n /**\n * Symbol for the `itemSelected` method.\n *\n * This method is invoked when an item becomes selected or deselected.\n *\n * @function itemSelected\n * @param {HTMLElement} item - the item being selected/deselected\n * @param {boolean} selected - true if the item is selected, false if not\n */\n itemSelected: createSymbol('itemSelected'),\n\n /**\n * Symbol for the `keydown` method.\n *\n * This method is invoked when an element receives a `keydown` event.\n *\n * @function keydown\n * @param {KeyboardEvent} event - the event being processed\n */\n keydown: createSymbol('keydown'),\n\n /**\n * Symbol for the `template` property.\n *\n * This property returns a component's template.\n *\n * @type {string|HTMLElement}\n */\n template: createSymbol('template')\n};\n\nexport default symbols;\n","/**\n * Helper function for standard classList.toggle() behavior on old browsers,\n * namely IE 11.\n *\n * The standard\n * [classlist](https://developer.mozilla.org/en-US/docs/Web/API/Element/classList)\n * object has a `toggle()` function that supports a second Boolean parameter\n * that can be used to succinctly turn a class on or off. This feature is often\n * useful in designing custom elements, which may want to externally reflect\n * component state in a CSS class that can be used for styling purposes.\n *\n * Unfortunately, IE 11 does not support the Boolean parameter to\n * `classList.toggle()`. This helper function behaves like the standard\n * `toggle()`, including support for the Boolean parameter, so that it can be\n * used even on IE 11.\n *\n * @function toggleClass\n * @param {HTMLElement} element - The element to modify\n * @param {string} className - The class to add/remove\n * @param {boolean} [force] - Force the class to be added (if true) or removed\n * (if false)\n */\nexport default function toggleClass(element, className, force) {\n const classList = element.classList;\n const addClass = (typeof force === 'undefined') ?\n !classList.contains(className) :\n force;\n if (addClass) {\n classList.add(className);\n } else {\n classList.remove(className);\n }\n return addClass;\n}\n","/*\n * This file is transpiled to create an ES5-compatible distribution in which\n * the package's main feature(s) are available via the window.Basic global.\n * If you're already using ES6 yourself, ignore this file, and instead import\n * the source file(s) you want from the src folder.\n */\n\nimport CurrentAnchor from './src/CurrentAnchor';\n\nwindow.Basic = window.Basic || {};\nwindow.Basic.CurrentAnchor = CurrentAnchor;\n","import createSymbol from '../../basic-component-mixins/src/createSymbol';\nimport safeAttributes from '../../basic-component-mixins/src/safeAttributes';\nimport symbols from '../../basic-component-mixins/src/symbols';\nimport WrappedStandardElement from '../../basic-wrapped-standard-element/src/WrappedStandardElement';\n\n\n// Symbols for private data members on an element.\nconst areaLinkSymbol = createSymbol('areaLink');\n\n\n/**\n * An anchor (link) that highlights itself when its destination matches the\n * current location.\n *\n * [Live demo](http://basicwebcomponents.org/basic-web-components/packages/basic-current-anchor/)\n *\n * Such a link commonly appears in toolbars, side bars, and other navigation\n * elements. In these situations, you generally want the user to understand what\n * page or area the user is already on.\n *\n * When the link is current — when it points to the current location — the\n * link will have the CSS `current` class applied to it, and its `current`\n * property will be true.\n *\n * Note: one limitation of this component is that, by default, the link does\n * *not* show the standard link color (usually blue) and text decoration\n * (underline). However, in navigation elements like toolbars, you often will\n * want to explicitly specific link colors anyway, e.g., to reflect your\n * application's visual style and brand.\n *\n * @extends WrappedStandardElement\n */\nclass CurrentAnchor extends WrappedStandardElement.wrap('a') {\n\n constructor() {\n super();\n\n window.addEventListener('popstate', event => {\n refresh(this);\n });\n\n // Stupid Edge/IE \"support\" popstate, but don't fire it on hashchange.\n // So we have to listen for hashchange as well, with the result that a\n // standards-compliant browser may end up refreshing the link twice.\n window.addEventListener('hashchange', event => {\n refresh(this);\n });\n\n // Set defaults.\n if (typeof this.areaLink === 'undefined') {\n this.areaLink = this[symbols.defaults].areaLink;\n }\n }\n\n /**\n * True if the link points to an area within a site, not just a single page.\n *\n * If true, the matching rule to determine whether the link is current changes:\n * an area link is considered to be current if the link's destination forms a\n * prefix of the current location (instead of matching the complete URL).\n *\n * @type {boolean}\n */\n get areaLink() {\n return this[areaLinkSymbol];\n }\n set areaLink(value) {\n // Cast boolean or string values to boolean.\n this[areaLinkSymbol] = (String(value) === 'true');\n refresh(this);\n }\n\n connectedCallback() {\n if (super.connectedCallback) { super.connectedCallback(); }\n safeAttributes.connected(this);\n refresh(this);\n }\n\n /**\n * True if the link's destination matches the current page location.\n *\n * If this is true, the element will have an `current` CSS class applied to it.\n *\n * @type {boolean}\n */\n get current() {\n return this.classList.contains('current');\n }\n set current(value) {\n safeAttributes.toggleClass(this, 'current', value);\n this.dispatchEvent(new CustomEvent('current-changed'));\n }\n\n get [symbols.defaults]() {\n const defaults = super[symbols.defaults] || {};\n defaults.areaLink = false;\n return defaults;\n }\n\n // Augment href implementation so that changing href checks the active status.\n get href() {\n return super.href;\n }\n set href(value) {\n super.href = value;\n refresh(this);\n }\n\n get [symbols.template]() {\n // Reset styles so that color can be specified from the outside without\n // having to define a CSS variable.\n return `\n \n `;\n }\n\n}\n\n\n// Update the current status of the element based on the current location.\nfunction refresh(element) {\n const url = window.location.href;\n let match;\n if (element.areaLink) {\n // Match prefix\n let prefix = element.href;\n // If prefix doesn't end in slash, add a slash.\n // We want to avoid matching in the middle of a folder name.\n if (prefix.length < url.length && prefix.substr(-1) !== '/') {\n prefix += '/';\n }\n match = (url.substr(0, prefix.length) === prefix);\n } else {\n // Match whole path\n match = (url === element.href);\n }\n element.current = match;\n}\n\n\ncustomElements.define('basic-current-anchor', CurrentAnchor);\n","import AttributeMarshallingMixin from '../../basic-component-mixins/src/AttributeMarshallingMixin';\nimport ComposableMixin from '../../basic-component-mixins/src/ComposableMixin';\nimport DistributedChildrenMixin from '../../basic-component-mixins/src/DistributedChildrenMixin';\nimport ShadowElementReferencesMixin from '../../basic-component-mixins/src/ShadowElementReferencesMixin';\nimport ShadowTemplateMixin from '../../basic-component-mixins/src/ShadowTemplateMixin';\n\n\n/**\n * A sample general-purpose base class for defining custom elements that mixes\n * in some common features: template stamping into a shadow root, shadow element\n * references, marshalling attributes to properties, and retrieving the children\n * distributed to a component.\n *\n * This base class is not special in any way, and is defined only as a\n * convenient shorthand for applying the mixins listed above. You can use this\n * class as a base class for your own elements, or easily create your own base\n * class by applying the same set of mixins.\n *\n * The ElementBase base class does not register itself as a custom element with\n * the browser, and hence cannot be independently instantiated.\n *\n * @mixes AttributeMarshallingMixin\n * @mixes ComposableMixin\n * @mixes DistributedChildrenMixin\n * @mixes ShadowElementReferencesMixin\n * @mixes ShadowTemplateMixin\n */\nclass ElementBase extends ComposableMixin(HTMLElement).compose(\n ShadowTemplateMixin, // before node finding, so shadow root is populated\n ShadowElementReferencesMixin, // before marshalling, so properties can use refs\n AttributeMarshallingMixin,\n DistributedChildrenMixin\n) {}\n\nexport default ElementBase;\n","import ElementBase from '../../basic-element-base/src/ElementBase';\nimport symbols from '../../basic-component-mixins/src/symbols';\n\n\n/*\n * A set of events which, if fired by the inner standard element, should be\n * re-raised by the custom element. (We only need to do that under native\n * Shadow DOM, not the polyfill.)\n *\n * These are events which are spec'ed to NOT get retargetted across a Shadow DOM\n * boundary, organized by which element(s) raise the events. To properly\n * simulate these, we will need to listen for the real events, then re-raise a\n * simulation of the original event. For more information, see\n * https://www.w3.org/TR/shadow-dom/#h-events-that-are-not-leaked-into-ancestor-trees.\n *\n * It appears that we do *not* need to re-raise the non-bubbling \"focus\" and\n * \"blur\" events. These appear to be automatically re-raised as expected -- but\n * it's not clear why that happens.\n *\n * The list below is reasonably complete. It omits elements that cannot be\n * wrapped (see class notes above). Also, we haven't actually tried wrapping\n * every element in this list; some of the more obscure ones might not actually\n * work as expected, but it was easier to include them for completeness than\n * to actually verify whether or not the element can be wrapped.\n */\nconst reraiseEvents = {\n address: ['scroll'],\n blockquote: ['scroll'],\n caption: ['scroll'],\n center: ['scroll'],\n dd: ['scroll'],\n dir: ['scroll'],\n div: ['scroll'],\n dl: ['scroll'],\n dt: ['scroll'],\n fieldset: ['scroll'],\n form: ['reset', 'scroll'],\n frame: ['load'],\n h1: ['scroll'],\n h2: ['scroll'],\n h3: ['scroll'],\n h4: ['scroll'],\n h5: ['scroll'],\n h6: ['scroll'],\n iframe: ['load'],\n img: ['abort', 'error', 'load'],\n input: ['abort', 'change', 'error', 'select', 'load'],\n keygen: ['reset', 'select'],\n li: ['scroll'],\n link: ['load'],\n menu: ['scroll'],\n object: ['error', 'scroll'],\n ol: ['scroll'],\n p: ['scroll'],\n script: ['error', 'load'],\n select: ['change', 'scroll'],\n tbody: ['scroll'],\n tfoot: ['scroll'],\n thead: ['scroll'],\n textarea: ['change', 'select', 'scroll']\n};\n\n\n// Keep track of which re-raised events should bubble.\nconst eventBubbles = {\n abort: true,\n change: true,\n reset: true\n};\n\n\n// Elements which are display: block by default.\n// Source: https://developer.mozilla.org/en-US/docs/Web/HTML/Block-level_elements\nconst blockElements = [\n 'address',\n 'article',\n 'aside',\n 'blockquote',\n 'canvas',\n 'dd',\n 'div',\n 'dl',\n 'fieldset',\n 'figcaption',\n 'figure',\n 'footer',\n 'form',\n 'h1',\n 'h2',\n 'h3',\n 'h4',\n 'h5',\n 'h6',\n 'header',\n 'hgroup',\n 'hr',\n 'li',\n 'main',\n 'nav',\n 'noscript',\n 'ol',\n 'output',\n 'p',\n 'pre',\n 'section',\n 'table',\n 'tfoot',\n 'ul',\n 'video'\n];\n\n\n/**\n * Wraps a standard HTML element so that the standard behavior can then be\n * extended.\n *\n * [Live demo](http://basicwebcomponents.org/basic-web-components/packages/basic-wrapped-standard-element/)\n *\n * See also [basic-autosize-textarea](../basic-autosize-textarea) and\n * [basic-current-anchor](../basic-current-anchor). The former uses\n * WrappedStandardElement to wrap a standard ` \n *\n * The `display` styling applied to the host will be `block` for elements that\n * are block elements by default, and `inline-block` (not `inline`) for other\n * elements.\n *\n * If you'd like the template to include other elements, then override this\n * property and return a template of your own. The template should include an\n * instance of the standard HTML element you are wrapping, and the ID of that\n * element should be \"inner\".\n *\n * @type {(string|HTMLTemplateElement)}\n */\n get [symbols.template]() {\n const display = blockElements.indexOf(this.extends) >= 0 ?\n 'block' :\n 'inline-block';\n return `<${this.extends} id=\"inner\"> ${this.extends}`;\n }\n\n /**\n * Creates a class that wraps a standard HTML element.\n *\n * Note that the resulting class is a subclass of WrappedStandardElement, not\n * the standard class being wrapped. E.g., if you call\n * `WrappedStandardElement.wrap('a')`, you will get a class whose shadow tree\n * will include an anchor element, but the class will *not* inherit from\n * HTMLAnchorElement.\n *\n * @param {string} extendsTag - the standard HTML element tag to extend\n */\n static wrap(extendsTag) {\n\n // Create the new class.\n class Wrapped extends WrappedStandardElement {}\n\n // Indicate which tag it wraps.\n Wrapped.prototype.extends = extendsTag;\n\n // Create getter/setters that delegate to the wrapped element.\n const element = document.createElement(extendsTag);\n const extendsPrototype = element.constructor.prototype;\n const names = Object.getOwnPropertyNames(extendsPrototype);\n names.forEach(name => {\n const descriptor = Object.getOwnPropertyDescriptor(extendsPrototype, name);\n const delegate = createPropertyDelegate(name, descriptor);\n Object.defineProperty(Wrapped.prototype, name, delegate);\n });\n\n return Wrapped;\n }\n\n}\n\n\nfunction createPropertyDelegate(name, descriptor) {\n const delegate = {\n configurable: descriptor.configurable,\n enumerable: descriptor.enumerable,\n };\n if (descriptor.get) {\n delegate.get = function() {\n return this.inner[name];\n };\n }\n if (descriptor.set) {\n delegate.set = function(value) {\n this.inner[name] = value;\n };\n }\n if (descriptor.writable) {\n delegate.writable = descriptor.writable;\n }\n return delegate;\n}\n\n\nexport default WrappedStandardElement;\n"]}
\ No newline at end of file
diff --git a/packages/basic-current-anchor/index.html b/packages/basic-current-anchor/index.html
index cd805154..a4b7909a 100644
--- a/packages/basic-current-anchor/index.html
+++ b/packages/basic-current-anchor/index.html
@@ -7,7 +7,8 @@
basic-current-anchor
-
+
+
diff --git a/packages/basic-current-anchor/src/CurrentAnchor.js b/packages/basic-current-anchor/src/CurrentAnchor.js
index 432c0cef..8e4daa96 100644
--- a/packages/basic-current-anchor/src/CurrentAnchor.js
+++ b/packages/basic-current-anchor/src/CurrentAnchor.js
@@ -27,6 +27,8 @@ const areaLinkSymbol = createSymbol('areaLink');
* (underline). However, in navigation elements like toolbars, you often will
* want to explicitly specific link colors anyway, e.g., to reflect your
* application's visual style and brand.
+ *
+ * @extends WrappedStandardElement
*/
class CurrentAnchor extends WrappedStandardElement.wrap('a') {
diff --git a/packages/basic-element-base/dist/basic-element-base.js b/packages/basic-element-base/dist/basic-element-base.js
index 667f3fad..31232956 100644
--- a/packages/basic-element-base/dist/basic-element-base.js
+++ b/packages/basic-element-base/dist/basic-element-base.js
@@ -1,1172 +1,2 @@
-(function e(t,n,r){function s(o,u){if(!n[o]){if(!t[o]){var a=typeof require=="function"&&require;if(!u&&a)return a(o,!0);if(i)return i(o,!0);var f=new Error("Cannot find module '"+o+"'");throw f.code="MODULE_NOT_FOUND",f}var l=n[o]={exports:{}};t[o][0].call(l.exports,function(e){var n=t[o][1][e];return s(n?n:e)},l,l.exports,e,t,n,r)}return n[o].exports}var i=typeof require=="function"&&require;for(var o=0;o
- *
- * Then, after the element has been upgraded, the `fooBar` setter will
- * automatically be invoked with the initial value "Hello".
- *
- * For the time being, this mixin only supports string-valued properties.
- * If you'd like to convert string attributes to other types (numbers,
- * booleans), you need to implement `attributeChangedCallback` yourself.
- */
- var AttributeMarshalling = function (_base) {
- _inherits(AttributeMarshalling, _base);
-
- function AttributeMarshalling() {
- _classCallCheck(this, AttributeMarshalling);
-
- return _possibleConstructorReturn(this, (AttributeMarshalling.__proto__ || Object.getPrototypeOf(AttributeMarshalling)).apply(this, arguments));
- }
-
- _createClass(AttributeMarshalling, [{
- key: 'attributeChangedCallback',
-
-
- /*
- * Handle a change to the attribute with the given name.
- */
- value: function attributeChangedCallback(attributeName, oldValue, newValue) {
- if (_get(AttributeMarshalling.prototype.__proto__ || Object.getPrototypeOf(AttributeMarshalling.prototype), 'attributeChangedCallback', this)) {
- _get(AttributeMarshalling.prototype.__proto__ || Object.getPrototypeOf(AttributeMarshalling.prototype), 'attributeChangedCallback', this).call(this);
- }
- var propertyName = attributeToPropertyName(attributeName);
- // If the attribute name corresponds to a property name, set the property.
- // Ignore standard HTMLElement properties handled by the DOM.
- if (propertyName in this && !(propertyName in HTMLElement.prototype)) {
- this[propertyName] = newValue;
- }
- }
- }, {
- key: 'connectedCallback',
- value: function connectedCallback() {
- if (_get(AttributeMarshalling.prototype.__proto__ || Object.getPrototypeOf(AttributeMarshalling.prototype), 'connectedCallback', this)) {
- _get(AttributeMarshalling.prototype.__proto__ || Object.getPrototypeOf(AttributeMarshalling.prototype), 'connectedCallback', this).call(this);
- }
- _safeAttributes2.default.connected(this);
- }
- }, {
- key: 'reflectAttribute',
-
-
- /**
- * Set/unset the attribute with the indicated name.
- *
- * This method exists primarily to handle the case where an element wants to
- * set a default property value that should be reflected as an attribute. An
- * important limitation of custom element consturctors is that they cannot
- * set attributes. A call to `reflectAttribute` during the constructor will
- * be deferred until the element is connected to the document.
- *
- * @param {string} attribute - The name of the *attribute* (not property) to set.
- * @param {object} value - The value to set. If null, the attribute will be removed.
- */
- value: function reflectAttribute(attribute, value) {
- return _safeAttributes2.default.setAttribute(this, attribute, value);
- }
-
- /**
- * Set/unset the class with the indicated name.
- *
- * This method exists primarily to handle the case where an element wants to
- * set a default property value that should be reflected as as class. An
- * important limitation of custom element consturctors is that they cannot
- * set attributes, including the `class` attribute. A call to
- * `reflectClass` during the constructor will be deferred until the element
- * is connected to the document.
- *
- * @param {string} className - The name of the class to set.
- * @param {object} value - True to set the class, false to remove it.
- */
-
- }, {
- key: 'reflectClass',
- value: function reflectClass(className, value) {
- return _safeAttributes2.default.toggleClass(this, className, value);
- }
- }], [{
- key: 'observedAttributes',
- get: function get() {
- return attributesForClass(this);
- }
- }]);
-
- return AttributeMarshalling;
- }(base);
-
- return AttributeMarshalling;
-};
-
-// Convert hyphenated foo-bar attribute name to camel case fooBar property name.
-
-
-function attributeToPropertyName(attributeName) {
- var propertyName = attributeToPropertyNames[attributeName];
- if (!propertyName) {
- // Convert and memoize.
- var hypenRegEx = /-([a-z])/g;
- propertyName = attributeName.replace(hypenRegEx, function (match) {
- return match[1].toUpperCase();
- });
- attributeToPropertyNames[attributeName] = propertyName;
- }
- return propertyName;
-}
-
-function attributesForClass(classFn) {
-
- // We treat the element base classes as if they have no attributes, since we
- // don't want to receive attributeChangedCallback for them.
- if (classFn === HTMLElement || classFn === Object) {
- return [];
- }
-
- // Get attributes for parent class.
- var baseClass = Object.getPrototypeOf(classFn.prototype).constructor;
- var baseAttributes = attributesForClass(baseClass);
-
- // Get attributes for this class.
- var propertyNames = Object.getOwnPropertyNames(classFn.prototype);
- var setterNames = propertyNames.filter(function (propertyName) {
- return typeof Object.getOwnPropertyDescriptor(classFn.prototype, propertyName).set === 'function';
- });
- var attributes = setterNames.map(function (setterName) {
- return propertyNameToAttribute(setterName);
- });
-
- // Merge.
- var diff = attributes.filter(function (attribute) {
- return baseAttributes.indexOf(attribute) < 0;
- });
- return baseAttributes.concat(diff);
-}
-
-// Convert a camel case fooBar property name to a hyphenated foo-bar attribute.
-function propertyNameToAttribute(propertyName) {
- var attribute = propertyNamesToAttributes[propertyName];
- if (!attribute) {
- // Convert and memoize.
- var uppercaseRegEx = /([A-Z])/g;
- attribute = propertyName.replace(uppercaseRegEx, '-$1').toLowerCase();
- }
- return attribute;
-}
-
-},{"./safeAttributes":7}],2:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-/* Exported function extends a base class with Composable. */
-exports.default = function (base) {
-
- /**
- * Mixin to make a class more easily composable with other mixins.
- *
- * This mixin contributes a `compose` method that applies a set of mixin
- * functions and returns the resulting new class. This sugar can make the
- * application of many mixins at once easier to read.
- */
- var Composable = function (_base) {
- _inherits(Composable, _base);
-
- function Composable() {
- _classCallCheck(this, Composable);
-
- return _possibleConstructorReturn(this, (Composable.__proto__ || Object.getPrototypeOf(Composable)).apply(this, arguments));
- }
-
- _createClass(Composable, null, [{
- key: 'compose',
-
-
- /**
- * Apply a set of mixin functions or mixin objects to the present class and
- * return the new class.
- *
- * Instead of writing:
- *
- * let MyClass = Mixin1(Mixin2(Mixin3(Mixin4(Mixin5(BaseClass)))));
- *
- * You can write:
- *
- * let MyClass = ComposableMixin(BaseClass).compose(
- * Mixin1,
- * Mixin2,
- * Mixin3,
- * Mixin4,
- * Mixin5
- * );
- *
- * This function can also take mixin objects. A mixin object is just a
- * shorthand for a mixin function that creates a new subclass with the given
- * members. The mixin object's members are *not* copied directly onto the
- * prototype of the base class, as with traditional mixins.
- *
- * In addition to providing syntactic sugar, this mixin can be used to
- * define a class in ES5, which lacks ES6's `class` keyword.
- *
- * @param {...mixins} mixins - A set of mixin functions or objects to apply.
- */
- value: function compose() {
- for (var _len = arguments.length, mixins = Array(_len), _key = 0; _key < _len; _key++) {
- mixins[_key] = arguments[_key];
- }
-
- // We create a new subclass for each mixin in turn. The result becomes
- // the base class extended by any subsequent mixins. It turns out that
- // we can use Array.reduce() to concisely express this, using the current
- // object as the seed for reduce().
- return mixins.reduce(composeClass, this);
- }
- }]);
-
- return Composable;
- }(base);
-
- return Composable;
-};
-
-// Properties defined by Object that we don't want to mixin.
-
-
-var NON_MIXABLE_OBJECT_PROPERTIES = ['constructor'];
-
-/*
- * Apply the mixin to the given base class to return a new class.
- * The mixin can either be a function that returns the modified class, or a
- * plain object whose members will be copied to the new class' prototype.
- */
-function composeClass(base, mixin) {
- if (typeof mixin === 'function') {
- // Mixin function
- return mixin(base);
- } else {
- // Mixin object
- var Subclass = function (_base2) {
- _inherits(Subclass, _base2);
-
- function Subclass() {
- _classCallCheck(this, Subclass);
-
- return _possibleConstructorReturn(this, (Subclass.__proto__ || Object.getPrototypeOf(Subclass)).apply(this, arguments));
- }
-
- return Subclass;
- }(base);
-
- copyOwnProperties(mixin, Subclass.prototype, NON_MIXABLE_OBJECT_PROPERTIES);
- return Subclass;
- }
-}
-
-/*
- * Copy the given properties/methods to the target.
- * Return the updated target.
- */
-function copyOwnProperties(source, target) {
- var ignorePropertyNames = arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : [];
-
- Object.getOwnPropertyNames(source).forEach(function (name) {
- if (ignorePropertyNames.indexOf(name) < 0) {
- var descriptor = Object.getOwnPropertyDescriptor(source, name);
- Object.defineProperty(target, name, descriptor);
- }
- });
- return target;
-}
-
-},{}],3:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
-
-function _toConsumableArray(arr) { if (Array.isArray(arr)) { for (var i = 0, arr2 = Array(arr.length); i < arr.length; i++) { arr2[i] = arr[i]; } return arr2; } else { return Array.from(arr); } }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-/* Exported function extends a base class with DistributedChildren. */
-exports.default = function (base) {
-
- /**
- * Mixin which defines helpers for accessing a component's distributed
- * children as a flattened array or string.
- *
- * The standard DOM API provides several ways of accessing child content:
- * `children`, `childNodes`, and `textContent`. None of these functions are
- * Shadow DOM aware. This mixin defines variations of those functions that
- * *are* Shadow DOM aware.
- *
- * Example: you create a component `` that displays a number
- * equal to the number of children placed inside that component. If someone
- * instantiates your component like:
- *
- *
- *
- *
- *
- *
- *
- * Then the component should show "3", because there are three children. To
- * calculate the number of children, the component can just calculate
- * `this.children.length`. However, suppose someone instantiates your
- * component inside one of their own components, and puts a `` element
- * inside your component:
- *
- *
- *
- *
- *
- * If your component only looks at `this.children`, it will always see exactly
- * one child — the `` element. But the user looking at the page will
- * *see* any nodes distributed to that slot. To match what the user sees, your
- * component should expand any `` elements it contains.
- *
- * That is the problem this mixin solves. After applying this mixin, your
- * component code has access to `this.distributedChildren`, whose `length`
- * will return the total number of all children distributed to your component
- * in the composed tree.
- *
- * Note: The latest Custom Elements API design calls for a new function,
- * `getAssignedNodes` that takes an optional `deep` parameter, that will solve
- * this problem at the API level.
- */
- var DistributedChildren = function (_base) {
- _inherits(DistributedChildren, _base);
-
- function DistributedChildren() {
- _classCallCheck(this, DistributedChildren);
-
- return _possibleConstructorReturn(this, (DistributedChildren.__proto__ || Object.getPrototypeOf(DistributedChildren)).apply(this, arguments));
- }
-
- _createClass(DistributedChildren, [{
- key: 'distributedChildren',
-
-
- /**
- * An in-order collection of distributed children, expanding any slot
- * elements. Like the standard children property, this skips text nodes.
- *
- * @type {HTMLElement[]}
- */
- get: function get() {
- return expandContentElements(this.children, false);
- }
-
- /**
- * An in-order collection of distributed child nodes, expanding any slot
- * elements. Like the standard childNodes property, this includes text
- * nodes.
- *
- * @type {Node[]}
- */
-
- }, {
- key: 'distributedChildNodes',
- get: function get() {
- return expandContentElements(this.childNodes, true);
- }
-
- /**
- * The concatenated text content of all distributed child nodes, expanding
- * any slot elements.
- *
- * @type {string}
- */
-
- }, {
- key: 'distributedTextContent',
- get: function get() {
- var strings = this.distributedChildNodes.map(function (child) {
- return child.textContent;
- });
- return strings.join('');
- }
- }]);
-
- return DistributedChildren;
- }(base);
-
- return DistributedChildren;
-};
-
-/*
- * Given a array of nodes, return a new array with any content elements expanded
- * to the nodes distributed to that content element. This rule is applied
- * recursively.
- *
- * If includeTextNodes is true, text nodes will be included, as in the
- * standard childNodes property; by default, this skips text nodes, like the
- * standard children property.
- */
-
-
-function expandContentElements(nodes, includeTextNodes) {
- var _ref;
-
- var expanded = Array.prototype.map.call(nodes, function (node) {
- // We want to see if the node is an instanceof HTMLSlotELement, but
- // that class won't exist if the browser that doesn't support native
- // Shadow DOM and if the Shadow DOM polyfill hasn't been loaded. Instead,
- // we do a simplistic check to see if the tag name is "slot".
- var isSlot = typeof HTMLSlotElement !== 'undefined' ? node instanceof HTMLSlotElement : node.localName === 'slot';
- if (isSlot) {
- // Use the nodes assigned to this node instead.
- var assignedNodes = node.assignedNodes({ flatten: true });
- return assignedNodes ? expandContentElements(assignedNodes, includeTextNodes) : [];
- } else if (node instanceof HTMLElement) {
- // Plain element; use as is.
- return [node];
- } else if (node instanceof Text && includeTextNodes) {
- // Text node.
- return [node];
- } else {
- // Comment, processing instruction, etc.; skip.
- return [];
- }
- });
- var flattened = (_ref = []).concat.apply(_ref, _toConsumableArray(expanded));
- return flattened;
-}
-
-},{}],4:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-/* Exported function extends a base class with ShadowElementReferences. */
-exports.default = function (base) {
-
- /**
- * Mixin to create references to elements in a component's Shadow DOM subtree.
- *
- * This adds a member on the component called `this.$` that can be used to
- * reference shadow elements with IDs. E.g., if component's shadow contains an
- * element ``, then this mixin will create a member
- * `this.$.foo` that points to that button.
- *
- * Such references simplify a component's access to its own elements. In
- * exchange, this mixin trades off a one-time cost of querying all elements in
- * the shadow tree instead of paying an ongoing cost to query for an element
- * each time the component wants to inspect or manipulate it.
- *
- * This mixin expects the component to define a Shadow DOM subtree. You can
- * create that tree yourself, or make use of
- * [ShadowTemplateMixin](ShadowTemplateMixin.md).
- *
- * This mixin is inspired by Polymer's [automatic
- * node finding](https://www.polymer-project.org/1.0/docs/devguide/local-dom.html#node-finding)
- * feature.
- */
- var ShadowElementReferences = function (_base) {
- _inherits(ShadowElementReferences, _base);
-
- function ShadowElementReferences() {
- _classCallCheck(this, ShadowElementReferences);
-
- var _this = _possibleConstructorReturn(this, (ShadowElementReferences.__proto__ || Object.getPrototypeOf(ShadowElementReferences)).call(this));
-
- if (_this.shadowRoot) {
- // Look for elements in the shadow subtree that have id attributes.
- // An alternatively implementation of this mixin would be to just define
- // a this.$ getter that lazily does this search the first time someone
- // tries to access this.$. That might introduce some complexity – if the
- // the tree changed after it was first populated, the result of
- // searching for a node might be somewhat unpredictable.
- _this.$ = {};
- var nodesWithIds = _this.shadowRoot.querySelectorAll('[id]');
- [].forEach.call(nodesWithIds, function (node) {
- var id = node.getAttribute('id');
- _this.$[id] = node;
- });
- }
- return _this;
- }
-
- /**
- * The collection of references to the elements with IDs in a component's
- * Shadow DOM subtree.
- *
- * @type {object}
- * @member $
- */
-
-
- return ShadowElementReferences;
- }(base);
-
- return ShadowElementReferences;
-};
-
-},{}],5:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _symbols = require('../src/symbols');
-
-var _symbols2 = _interopRequireDefault(_symbols);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-/* Exported function extends a base class with ShadowTemplate. */
-exports.default = function (base) {
-
- /**
- * Mixin for stamping a template into a Shadow DOM subtree upon component
- * instantiation.
- *
- * To use this mixin, define a `template` property as a string or HTML
- * `` element:
- *
- * class MyElement extends ShadowTemplateMixin(HTMLElement) {
- * get [symbols.template]() {
- * return `Hello, world .`;
- * }
- * }
- *
- * When your component class is instantiated, a shadow root will be created on
- * the instance, and the contents of the template will be cloned into the
- * shadow root. If your component does not define a `template` property, this
- * mixin has no effect.
- *
- * For the time being, this extension retains support for Shadow DOM v0. That
- * will eventually be deprecated as browsers (and the Shadow DOM polyfill)
- * implement Shadow DOM v1.
- */
- var ShadowTemplate = function (_base) {
- _inherits(ShadowTemplate, _base);
-
- /*
- * If the component defines a template, a shadow root will be created on the
- * component instance, and the template stamped into it.
- */
- function ShadowTemplate() {
- _classCallCheck(this, ShadowTemplate);
-
- var _this = _possibleConstructorReturn(this, (ShadowTemplate.__proto__ || Object.getPrototypeOf(ShadowTemplate)).call(this));
-
- var template = _this[_symbols2.default.template];
- // TODO: Save the processed template with the component's class prototype
- // so it doesn't need to be processed with every instantiation.
- if (template) {
-
- if (typeof template === 'string') {
- // Upgrade plain string to real template.
- template = createTemplateWithInnerHTML(template);
- }
-
- if (window.ShadowDOMPolyfill) {
- shimTemplateStyles(template, _this.localName);
- }
-
- var root = _this.attachShadow({ mode: 'open' });
- var clone = document.importNode(template.content, true);
- root.appendChild(clone);
- }
- return _this;
- }
-
- return ShadowTemplate;
- }(base);
-
- return ShadowTemplate;
-};
-
-// Convert a plain string of HTML into a real template element.
-
-
-function createTemplateWithInnerHTML(innerHTML) {
- var template = document.createElement('template');
- // REVIEW: Is there an easier way to do this?
- // We'd like to just set innerHTML on the template content, but since it's
- // a DocumentFragment, that doesn't work.
- var div = document.createElement('div');
- div.innerHTML = innerHTML;
- while (div.childNodes.length > 0) {
- template.content.appendChild(div.childNodes[0]);
- }
- return template;
-}
-
-// Invoke basic style shimming with ShadowCSS.
-function shimTemplateStyles(template, tag) {
- window.WebComponents.ShadowCSS.shimStyling(template.content, tag);
-}
-
-},{"../src/symbols":8}],6:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-exports.default = createSymbol;
-/**
- * Helper function to create a symbol that can be used for associating private
- * data with an element.
- *
- * Mixins and component classes often want to associate private data with an
- * element instance, but JavaScript does not have direct support for true
- * private properties. One approach is to use the
- * [Symbol](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Symbol)
- * data type to set and retrieve data on an element.
- *
- * Unfortunately, the Symbol type is not available in Internet Explorer 11. The
- * `createSymbol` helper function exists as a workaround for IE 11. Rather than
- * returning a true Symbol, it simply returns an underscore-prefixed string.
- *
- * Usage:
- *
- * const fooSymbol = createSymbol('foo');
- *
- * class MyElement extends HTMLElement {
- * get foo() {
- * return this[fooSymbol];
- * }
- * set foo(value) {
- * this[fooSymbol] = value;
- * }
- * }
- *
- * In IE 11, this sample will "hide" data behind an instance property this._foo.
- * The use of the underscore is meant to reduce (not eliminate) the potential
- * for name conflicts, and discourage (not prevent) external access to this
- * data. In modern browsers, the above code will eliminate the potential of
- * naming conflicts, and better hide the data behind a real Symbol.
- *
- * @function createSymbol
- * @param {string} description - A string to identify the symbol when debugging
- */
-function createSymbol(description) {
- return typeof Symbol === 'function' ? Symbol(description) : '_' + description;
-}
-
-},{}],7:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createSymbol = require('./createSymbol');
-
-var _createSymbol2 = _interopRequireDefault(_createSymbol);
-
-var _toggleClass2 = require('./toggleClass');
-
-var _toggleClass3 = _interopRequireDefault(_toggleClass2);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-// Symbols for private data members on an element.
-var safeToSetAttributesSymbol = (0, _createSymbol2.default)('safeToSetAttributes');
-var pendingAttributesSymbol = (0, _createSymbol2.default)('pendingAttributes');
-var pendingClassesSymbol = (0, _createSymbol2.default)('pendingClasses');
-
-/**
- * Helper functions for updating attributes, including the `class` attribute.
- */
-exports.default = {
-
- /**
- * Perform any pending updates to attributes and classes.
- *
- * This writes any `setAttribute` or `toggleClass` values that were performed
- * before an element was attached to the document for the first time.
- *
- * This method should be called by mixins/components in their
- * `connectedCallback`. If mulitple mixins/components invoke this during the
- * same `connectedCallback`, only the first call will have any effect. The
- * subsequent calls will be harmless.
- *
- * @param {HTMLElement} element - The element being added to the document.
- */
- connected: function connected(element) {
- element[safeToSetAttributesSymbol] = true;
-
- // Set any pending attributes.
- if (element[pendingAttributesSymbol]) {
- for (var attribute in element[pendingAttributesSymbol]) {
- var value = element[pendingAttributesSymbol][attribute];
- setAttributeToElement(element, attribute, value);
- }
- element[pendingAttributesSymbol] = null;
- }
-
- // Set any pending classes.
- if (element[pendingClassesSymbol]) {
- for (var className in element[pendingClassesSymbol]) {
- var _value = element[pendingClassesSymbol][className];
- (0, _toggleClass3.default)(element, className, _value);
- }
- element[pendingClassesSymbol] = null;
- }
- },
-
-
- /**
- * Set/unset the attribute with the indicated name.
- *
- * This method exists primarily to handle the case where an element wants to
- * set a default property value that should be reflected as an attribute. An
- * important limitation of custom element consturctors is that they cannot
- * set attributes. A call to `setAttribute` during the constructor will
- * be deferred until the element is connected to the document.
- *
- * @param {string} attribute - The name of the *attribute* (not property) to set.
- * @param {object} value - The value to set. If null, the attribute will be removed.
- */
- setAttribute: function setAttribute(element, attribute, value) {
- if (element[safeToSetAttributesSymbol]) {
- // Safe to set attributes immediately.
- setAttributeToElement(element, attribute, value);
- } else {
- // Defer setting attributes until the first time we're connected.
- if (!element[pendingAttributesSymbol]) {
- element[pendingAttributesSymbol] = {};
- }
- element[pendingAttributesSymbol][attribute] = value;
- }
- },
-
-
- /**
- * Set/unset the class with the indicated name.
- *
- * This method exists primarily to handle the case where an element wants to
- * set a default property value that should be reflected as as class. An
- * important limitation of custom element consturctors is that they cannot
- * set attributes, including the `class` attribute. A call to
- * `toggleClass` during the constructor will be deferred until the element
- * is connected to the document.
- *
- * @param {string} className - The name of the class to set.
- * @param {object} value - True to set the class, false to remove it.
- */
- toggleClass: function toggleClass(element, className, value) {
- if (element[safeToSetAttributesSymbol]) {
- // Safe to set class immediately.
- (0, _toggleClass3.default)(element, className, value);
- } else {
- // Defer setting class until the first time we're connected.
- if (!element[pendingClassesSymbol]) {
- element[pendingClassesSymbol] = {};
- }
- element[pendingClassesSymbol][className] = value;
- }
- }
-};
-
-// Reflect the attribute to the given element.
-// If the value is null, remove the attribute.
-
-function setAttributeToElement(element, attributeName, value) {
- if (value === null || typeof value === 'undefined') {
- element.removeAttribute(attributeName);
- } else {
- var text = String(value);
- // Avoid recursive attributeChangedCallback calls.
- if (element.getAttribute(attributeName) !== text) {
- element.setAttribute(attributeName, value);
- }
- }
-}
-
-},{"./createSymbol":6,"./toggleClass":9}],8:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createSymbol = require('./createSymbol');
-
-var _createSymbol2 = _interopRequireDefault(_createSymbol);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-/**
- * A collection of Symbol objects for standard component properties and methods.
- *
- * These Symbol objects are used to allow mixins and a component to internally
- * communicate, without exposing these properties and methods in the component's
- * public API.
- *
- * To use these Symbol objects in your own component, include this module and
- * then create a property or method whose key is the desired Symbol.
- *
- * import 'SingleSelectionMixin' from 'basic-component-mixins/src/SingleSelectionMixin';
- * import 'symbols' from 'basic-component-mixins/src/symbols';
- *
- * class MyElement extends SingleSelectionMixin(HTMLElement) {
- * [symbols.itemSelected](item, selected) {
- * // This will be invoked whenever an item is selected/deselected.
- * }
- * }
- *
- * @module symbols
- */
-var symbols = {
-
- /**
- * Symbol for the `defaults` property.
- *
- * This property can be used to set or override defaults that will be applied
- * to a new component instance. When implementing this property, take care to
- * first acquire any defaults defined by the superclass. The standard idiom is
- * as follows:
- *
- * get [symbols.defaults]() {
- * const defaults = super[symbols.defaults] || {};
- * // Set or override default values here
- * defaults.customProperty = false;
- * return defaults;
- * }
- *
- * @var {object} defaults
- */
- defaults: (0, _createSymbol2.default)('defaults'),
-
- /**
- * Symbol for the `dragging` property.
- *
- * Components like carousels often define animated CSS transitions for
- * sliding effects. Such a transition should usually *not* be applied while
- * the user is dragging, because a CSS animation will introduce a lag that
- * makes the swipe feel sluggish. Instead, as long as the user is dragging
- * with their finger down, the transition should be suppressed. When the
- * user releases their finger, the transition can be restored, allowing the
- * animation to show the carousel sliding into its final position.
- *
- * @type {boolean} true if a drag is in progress, false if not.
- */
- dragging: (0, _createSymbol2.default)('dragging'),
-
- /**
- * Symbol for the `goDown` method.
- *
- * This method is invoked when the user wants to go/navigate down.
- *
- * @function goDown
- */
- goDown: (0, _createSymbol2.default)('goDown'),
-
- /**
- * Symbol for the `goEnd` method.
- *
- * This method is invoked when the user wants to go/navigate to the end (e.g.,
- * of a list).
- *
- * @function goEnd
- */
- goEnd: (0, _createSymbol2.default)('goEnd'),
-
- /**
- * Symbol for the `goLeft` method.
- *
- * This method is invoked when the user wants to go/navigate left.
- *
- * @function goLeft
- */
- goLeft: (0, _createSymbol2.default)('goLeft'),
-
- /**
- * Symbol for the `goRight` method.
- *
- * This method is invoked when the user wants to go/navigate right.
- *
- * @function goRight
- */
- goRight: (0, _createSymbol2.default)('goRight'),
-
- /**
- * Symbol for the `goStart` method.
- *
- * This method is invoked when the user wants to go/navigate to the start
- * (e.g., of a list).
- *
- * @function goStart
- */
- goStart: (0, _createSymbol2.default)('goStart'),
-
- /**
- * Symbol for the `goUp` method.
- *
- * This method is invoked when the user wants to go/navigate up.
- *
- * @function goUp
- */
- goUp: (0, _createSymbol2.default)('goUp'),
-
- /**
- * Symbol for the `itemAdded` method.
- *
- * This method is invoked when a new item is added to a list.
- *
- * @function itemAdded
- * @param {HTMLElement} item - the item being selected/deselected
- */
- itemAdded: (0, _createSymbol2.default)('itemAdded'),
-
- /**
- * Symbol for the `itemsChanged` method.
- *
- * This method is invoked when the underlying contents change. It is also
- * invoked on component initialization – since the items have "changed" from
- * being nothing.
- */
- itemsChanged: (0, _createSymbol2.default)('itemsChanged'),
-
- /**
- * Symbol for the `itemSelected` method.
- *
- * This method is invoked when an item becomes selected or deselected.
- *
- * @function itemSelected
- * @param {HTMLElement} item - the item being selected/deselected
- * @param {boolean} selected - true if the item is selected, false if not
- */
- itemSelected: (0, _createSymbol2.default)('itemSelected'),
-
- /**
- * Symbol for the `keydown` method.
- *
- * This method is invoked when an element receives a `keydown` event.
- *
- * @function keydown
- * @param {KeyboardEvent} event - the event being processed
- */
- keydown: (0, _createSymbol2.default)('keydown'),
-
- /**
- * Symbol for the `template` property.
- *
- * This property returns a component's template.
- *
- * @type {string|HTMLElement}
- */
- template: (0, _createSymbol2.default)('template')
-};
-
-exports.default = symbols;
-
-},{"./createSymbol":6}],9:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-exports.default = toggleClass;
-/**
- * Helper function for standard classList.toggle() behavior on old browsers,
- * namely IE 11.
- *
- * The standard
- * [classlist](https://developer.mozilla.org/en-US/docs/Web/API/Element/classList)
- * object has a `toggle()` function that supports a second Boolean parameter
- * that can be used to succinctly turn a class on or off. This feature is often
- * useful in designing custom elements, which may want to externally reflect
- * component state in a CSS class that can be used for styling purposes.
- *
- * Unfortunately, IE 11 does not support the Boolean parameter to
- * `classList.toggle()`. This helper function behaves like the standard
- * `toggle()`, including support for the Boolean parameter, so that it can be
- * used even on IE 11.
- *
- * @function toggleClass
- * @param {HTMLElement} element - The element to modify
- * @param {string} className - The class to add/remove
- * @param {boolean} [force] - Force the class to be added (if true) or removed
- * (if false)
- */
-function toggleClass(element, className, force) {
- var classList = element.classList;
- var addClass = typeof force === 'undefined' ? !classList.contains(className) : force;
- if (addClass) {
- classList.add(className);
- } else {
- classList.remove(className);
- }
- return addClass;
-}
-
-},{}],10:[function(require,module,exports){
-'use strict';
-
-var _ElementBase = require('./src/ElementBase');
-
-var _ElementBase2 = _interopRequireDefault(_ElementBase);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-window.Basic = window.Basic || {}; /*
- * This file is transpiled to create an ES5-compatible distribution in which
- * the package's main feature(s) are available via the window.Basic global.
- * If you're already using ES6 yourself, ignore this file, and instead import
- * the source file(s) you want from the src folder.
- */
-
-window.Basic.ElementBase = _ElementBase2.default;
-
-},{"./src/ElementBase":11}],11:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _AttributeMarshallingMixin = require('../../basic-component-mixins/src/AttributeMarshallingMixin');
-
-var _AttributeMarshallingMixin2 = _interopRequireDefault(_AttributeMarshallingMixin);
-
-var _ComposableMixin = require('../../basic-component-mixins/src/ComposableMixin');
-
-var _ComposableMixin2 = _interopRequireDefault(_ComposableMixin);
-
-var _DistributedChildrenMixin = require('../../basic-component-mixins/src/DistributedChildrenMixin');
-
-var _DistributedChildrenMixin2 = _interopRequireDefault(_DistributedChildrenMixin);
-
-var _ShadowElementReferencesMixin = require('../../basic-component-mixins/src/ShadowElementReferencesMixin');
-
-var _ShadowElementReferencesMixin2 = _interopRequireDefault(_ShadowElementReferencesMixin);
-
-var _ShadowTemplateMixin = require('../../basic-component-mixins/src/ShadowTemplateMixin');
-
-var _ShadowTemplateMixin2 = _interopRequireDefault(_ShadowTemplateMixin);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-/**
- * A sample general-purpose base class for defining custom elements that mixes
- * in some common features: template stamping into a shadow root, shadow element
- * references, marshalling attributes to properties, and retrieving the children
- * distributed to a component.
- *
- * This base class is not special in any way, and is defined only as a
- * convenient shorthand for applying the mixins listed above. You can use this
- * class as a base class for your own elements, or easily create your own base
- * class by applying the same set of mixins.
- *
- * The ElementBase base class does not register itself as a custom element with
- * the browser, and hence cannot be independently instantiated.
- *
- * @mixes AttributeMarshallingMixin
- * @mixes ComposableMixin
- * @mixes DistributedChildrenMixin
- * @mixes ShadowElementReferencesMixin
- * @mixes ShadowTemplateMixin
- */
-var ElementBase = function (_ComposableMixin$comp) {
- _inherits(ElementBase, _ComposableMixin$comp);
-
- function ElementBase() {
- _classCallCheck(this, ElementBase);
-
- return _possibleConstructorReturn(this, (ElementBase.__proto__ || Object.getPrototypeOf(ElementBase)).apply(this, arguments));
- }
-
- return ElementBase;
-}((0, _ComposableMixin2.default)(HTMLElement).compose(_ShadowTemplateMixin2.default, // before node finding, so shadow root is populated
-_ShadowElementReferencesMixin2.default, // before marshalling, so properties can use refs
-_AttributeMarshallingMixin2.default, _DistributedChildrenMixin2.default));
-
-exports.default = ElementBase;
-
-},{"../../basic-component-mixins/src/AttributeMarshallingMixin":1,"../../basic-component-mixins/src/ComposableMixin":2,"../../basic-component-mixins/src/DistributedChildrenMixin":3,"../../basic-component-mixins/src/ShadowElementReferencesMixin":4,"../../basic-component-mixins/src/ShadowTemplateMixin":5}]},{},[10])
-//# sourceMappingURL=data:application/json;charset:utf-8;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbIm5vZGVfbW9kdWxlcy9ncnVudC1icm93c2VyaWZ5L25vZGVfbW9kdWxlcy9icm93c2VyLXBhY2svX3ByZWx1ZGUuanMiLCJwYWNrYWdlcy9iYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy9BdHRyaWJ1dGVNYXJzaGFsbGluZ01peGluLmpzIiwicGFja2FnZXMvYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvQ29tcG9zYWJsZU1peGluLmpzIiwicGFja2FnZXMvYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvRGlzdHJpYnV0ZWRDaGlsZHJlbk1peGluLmpzIiwicGFja2FnZXMvYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvU2hhZG93RWxlbWVudFJlZmVyZW5jZXNNaXhpbi5qcyIsInBhY2thZ2VzL2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL1NoYWRvd1RlbXBsYXRlTWl4aW4uanMiLCJwYWNrYWdlcy9iYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy9jcmVhdGVTeW1ib2wuanMiLCJwYWNrYWdlcy9iYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy9zYWZlQXR0cmlidXRlcy5qcyIsInBhY2thZ2VzL2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL3N5bWJvbHMuanMiLCJwYWNrYWdlcy9iYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy90b2dnbGVDbGFzcy5qcyIsInBhY2thZ2VzL2Jhc2ljLWVsZW1lbnQtYmFzZS9nbG9iYWxzLmpzIiwicGFja2FnZXMvYmFzaWMtZWxlbWVudC1iYXNlL3NyYy9FbGVtZW50QmFzZS5qcyJdLCJuYW1lcyI6W10sIm1hcHBpbmdzIjoiQUFBQTs7Ozs7Ozs7Ozs7QUNBQTs7Ozs7Ozs7Ozs7O0FBR0E7QUFDQSxJQUFNLDJCQUEyQixFQUFqQztBQUNBLElBQU0sNEJBQTRCLEVBQWxDOztBQUdBOztrQkFDZSxVQUFDLElBQUQsRUFBVTs7QUFFdkI7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7O0FBRnVCLE1B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QUFjO0FBQ1osY0FBVSxHQUFWLENBQWMsU0FBZDtBQUNELEdBRkQsTUFFTztBQUNMLGNBQVUsTUFBVixDQUFpQixTQUFqQjtBQUNEO0FBQ0QsU0FBTyxRQUFQO0FBQ0Q7Ozs7O0FDMUJEOzs7Ozs7QUFFQSxPQUFPLEtBQVAsR0FBZSxPQUFPLEtBQVAsSUFBZ0IsRUFBL0IsQyxDQVRBOzs7Ozs7O0FBVUEsT0FBTyxLQUFQLENBQWEsV0FBYjs7Ozs7Ozs7O0FDVkE7Ozs7QUFDQTs7OztBQUNBOzs7O0FBQ0E7Ozs7QUFDQTs7Ozs7Ozs7Ozs7O0FBR0E7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7O0lBb0JNLFc7Ozs7Ozs7Ozs7RUFBb0IsK0JBQWdCLFdBQWhCLEVBQTZCLE9BQTdCLGdDQUNNO0FBRE4sd0NBRU07QUFGTix3RTs7a0JBT1gsVyIsImZpbGUiOiJnZW5lcmF0ZWQuanMiLCJzb3VyY2VSb290IjoiIiwic291cmNlc0NvbnRlbnQiOlsiKGZ1bmN0aW9uIGUodCxuLHIpe2Z1bmN0aW9uIHMobyx1KXtpZighbltvXSl7aWYoIXRbb10pe3ZhciBhPXR5cGVvZiByZXF1aXJlPT1cImZ1bmN0aW9uXCImJnJlcXVpcmU7aWYoIXUmJmEpcmV0dXJuIGEobywhMCk7aWYoaSlyZXR1cm4gaShvLCEwKTt2YXIgZj1uZXcgRXJyb3IoXCJDYW5ub3QgZmluZCBtb2R1bGUgJ1wiK28rXCInXCIpO3Rocm93IGYuY29kZT1cIk1PRFVMRV9OT1RfRk9VTkRcIixmfXZhciBsPW5bb109e2V4cG9ydHM6e319O3Rbb11bMF0uY2FsbChsLmV4cG9ydHMsZnVuY3Rpb24oZSl7dmFyIG49dFtvXVsxXVtlXTtyZXR1cm4gcyhuP246ZSl9LGwsbC5leHBvcnRzLGUsdCxuLHIpfXJldHVybiBuW29dLmV4cG9ydHN9dmFyIGk9dHlwZW9mIHJlcXVpcmU9PVwiZnVuY3Rpb25cIiYmcmVxdWlyZTtmb3IodmFyIG89MDtvPHIubGVuZ3RoO28rKylzKHJbb10pO3JldHVybiBzfSkiLCJpbXBvcnQgc2FmZUF0dHJpYnV0ZXMgZnJvbSAnLi9zYWZlQXR0cmlidXRlcyc7XG5cblxuLy8gTWVtb2l6ZWQgbWFwcyBvZiBhdHRyaWJ1dGUgdG8gcHJvcGVydHkgbmFtZXMgYW5kIHZpY2UgdmVyc2EuXG5jb25zdCBhdHRyaWJ1dGVUb1Byb3BlcnR5TmFtZXMgPSB7fTtcbmNvbnN0IHByb3BlcnR5TmFtZXNUb0F0dHJpYnV0ZXMgPSB7fTtcblxuXG4vKiBFeHBvcnRlZCBmdW5jdGlvbiBleHRlbmRzIGEgYmFzZSBjbGFzcyB3aXRoIEF0dHJpYnV0ZU1hcnNoYWxsaW5nLiAqL1xuZXhwb3J0IGRlZmF1bHQgKGJhc2UpID0+IHtcblxuICAvKipcbiAgICogTWl4aW4gd2hpY2ggbWFyc2hhbGxzIGF0dHJpYnV0ZXMgdG8gcHJvcGVydGllcyBhbmQgdmljZSB2ZXJzYS5cbiAgICpcbiAgICogSWYgeW91ciBjb21wb25lbnQgZXhwb3NlcyBhIHNldHRlciBmb3IgYSBwcm9wZXJ0eSwgaXQncyBnZW5lcmFsbHkgYSBnb29kXG4gICAqIGlkZWEgdG8gbGV0IGRldnMgdXNpbmcgeW91ciBjb21wb25lbnQgYmUgYWJsZSB0byBzZXQgdGhhdCBwcm9wZXJ0eSBpbiBIVE1MXG4gICAqIHZpYSBhbiBlbGVtZW50IGF0dHJpYnV0ZS4gWW91IGNhbiBjb2RlIHRoYXQgeW91cnNlbGYgYnkgd3JpdGluZyBhblxuICAgKiBgYXR0cmlidXRlQ2hhbmdlZENhbGxiYWNrYCwgb3IgeW91IGNhbiB1c2UgdGhpcyBtaXhpbiB0byBnZXQgYSBkZWdyZWUgb2ZcbiAgICogYXV0b21hdGljIHN1cHBvcnQuXG4gICAqXG4gICAqIFRoaXMgbWl4aW4gaW1wbGVtZW50cyBhbiBgYXR0cmlidXRlQ2hhbmdlZENhbGxiYWNrYCB0aGF0IHdpbGwgYXR0ZW1wdCB0b1xuICAgKiBjb252ZXJ0IGEgY2hhbmdlIGluIGFuIGVsZW1lbnQgYXR0cmlidXRlIGludG8gYSBjYWxsIHRvIHRoZSBjb3JyZXNwb25kaW5nXG4gICAqIHByb3BlcnR5IHNldHRlci4gQXR0cmlidXRlcyB0eXBpY2FsbHkgZm9sbG93IGh5cGhlbmF0ZWQgbmFtZXMgKFwiZm9vLWJhclwiKSxcbiAgICogd2hlcmVhcyBwcm9wZXJ0aWVzIHR5cGljYWxseSB1c2UgY2FtZWxDYXNlIG5hbWVzIChcImZvb0JhclwiKS4gVGhpcyBtaXhpblxuICAgKiByZXNwZWN0cyB0aGF0IGNvbnZlbnRpb24sIGF1dG9tYXRpY2FsbHkgbWFwcGluZyB0aGUgaHlwaGVuYXRlZCBhdHRyaWJ1dGVcbiAgICogbmFtZSB0byB0aGUgY29ycmVzcG9uZGluZyBjYW1lbENhc2UgcHJvcGVydHkgbmFtZS5cbiAgICpcbiAgICogRXhhbXBsZTogWW91IGRlZmluZSBhIGNvbXBvbmVudCB1c2luZyB0aGlzIG1peGluOlxuICAgKlxuICAgKiAgICAgY2xhc3MgTXlFbGVtZW50IGV4dGVuZHMgQXR0cmlidXRlTWFyc2hhbGxpbmdNaXhpbihIVE1MRWxlbWVudCkge1xuICAgKiAgICAgICBnZXQgZm9vQmFyKCkgeyByZXR1cm4gdGhpcy5fZm9vQmFyOyB9XG4gICAqICAgICAgIHNldCBmb29CYXIodmFsdWUpIHsgdGhpcy5fZm9vQmFyID0gdmFsdWU7IH1cbiAgICogICAgIH1cbiAgICogICAgIGN1c3RvbUVsZW1lbnRzLmRlZmluZSgnbXktZWxlbWVudCcsIE15RWxlbWVudCk7XG4gICAqXG4gICAqIElmIHNvbWVvbmUgdGhlbiBpbnN0YW50aWF0ZXMgeW91ciBjb21wb25lbnQgaW4gSFRNTDpcbiAgICpcbiAgICogICAgIDxteS1lbGVtZW50IGZvby1iYXI9XCJIZWxsb1wiPjwvbXktZWxlbWVudD5cbiAgICpcbiAgICogVGhlbiwgYWZ0ZXIgdGhlIGVsZW1lbnQgaGFzIGJlZW4gdXBncmFkZWQsIHRoZSBgZm9vQmFyYCBzZXR0ZXIgd2lsbFxuICAgKiBhdXRvbWF0aWNhbGx5IGJlIGludm9rZWQgd2l0aCB0aGUgaW5pdGlhbCB2YWx1ZSBcIkhlbGxvXCIuXG4gICAqXG4gICAqIEZvciB0aGUgdGltZSBiZWluZywgdGhpcyBtaXhpbiBvbmx5IHN1cHBvcnRzIHN0cmluZy12YWx1ZWQgcHJvcGVydGllcy5cbiAgICogSWYgeW91J2QgbGlrZSB0byBjb252ZXJ0IHN0cmluZyBhdHRyaWJ1dGVzIHRvIG90aGVyIHR5cGVzIChudW1iZXJzLFxuICAgKiBib29sZWFucyksIHlvdSBuZWVkIHRvIGltcGxlbWVudCBgYXR0cmlidXRlQ2hhbmdlZENhbGxiYWNrYCB5b3Vyc2VsZi5cbiAgICovXG4gIGNsYXNzIEF0dHJpYnV0ZU1hcnNoYWxsaW5nIGV4dGVuZHMgYmFzZSB7XG5cbiAgICAvKlxuICAgICAqIEhhbmRsZSBhIGNoYW5nZSB0byB0aGUgYXR0cmlidXRlIHdpdGggdGhlIGdpdmVuIG5hbWUuXG4gICAgICovXG4gICAgYXR0cmlidXRlQ2hhbmdlZENhbGxiYWNrKGF0dHJpYnV0ZU5hbWUsIG9sZFZhbHVlLCBuZXdWYWx1ZSkge1xuICAgICAgaWYgKHN1cGVyLmF0dHJpYnV0ZUNoYW5nZWRDYWxsYmFjaykgeyBzdXBlci5hdHRyaWJ1dGVDaGFuZ2VkQ2FsbGJhY2soKTsgfVxuICAgICAgY29uc3QgcHJvcGVydHlOYW1lID0gYXR0cmlidXRlVG9Qcm9wZXJ0eU5hbWUoYXR0cmlidXRlTmFtZSk7XG4gICAgICAvLyBJZiB0aGUgYXR0cmlidXRlIG5hbWUgY29ycmVzcG9uZHMgdG8gYSBwcm9wZXJ0eSBuYW1lLCBzZXQgdGhlIHByb3BlcnR5LlxuICAgICAgLy8gSWdub3JlIHN0YW5kYXJkIEhUTUxFbGVtZW50IHByb3BlcnRpZXMgaGFuZGxlZCBieSB0aGUgRE9NLlxuICAgICAgaWYgKHByb3BlcnR5TmFtZSBpbiB0aGlzICYmICEocHJvcGVydHlOYW1lIGluIEhUTUxFbGVtZW50LnByb3RvdHlwZSkpIHtcbiAgICAgICAgdGhpc1twcm9wZXJ0eU5hbWVdID0gbmV3VmFsdWU7XG4gICAgICB9XG4gICAgfVxuXG4gICAgY29ubmVjdGVkQ2FsbGJhY2soKSB7XG4gICAgICBpZiAoc3VwZXIuY29ubmVjdGVkQ2FsbGJhY2spIHsgc3VwZXIuY29ubmVjdGVkQ2FsbGJhY2soKTsgfVxuICAgICAgc2FmZUF0dHJpYnV0ZXMuY29ubmVjdGVkKHRoaXMpO1xuICAgIH1cblxuICAgIHN0YXRpYyBnZXQgb2JzZXJ2ZWRBdHRyaWJ1dGVzKCkge1xuICAgICAgcmV0dXJuIGF0dHJpYnV0ZXNGb3JDbGFzcyh0aGlzKTtcbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBTZXQvdW5zZXQgdGhlIGF0dHJpYnV0ZSB3aXRoIHRoZSBpbmRpY2F0ZWQgbmFtZS5cbiAgICAgKlxuICAgICAqIFRoaXMgbWV0aG9kIGV4aXN0cyBwcmltYXJpbHkgdG8gaGFuZGxlIHRoZSBjYXNlIHdoZXJlIGFuIGVsZW1lbnQgd2FudHMgdG9cbiAgICAgKiBzZXQgYSBkZWZhdWx0IHByb3BlcnR5IHZhbHVlIHRoYXQgc2hvdWxkIGJlIHJlZmxlY3RlZCBhcyBhbiBhdHRyaWJ1dGUuIEFuXG4gICAgICogaW1wb3J0YW50IGxpbWl0YXRpb24gb2YgY3VzdG9tIGVsZW1lbnQgY29uc3R1cmN0b3JzIGlzIHRoYXQgdGhleSBjYW5ub3RcbiAgICAgKiBzZXQgYXR0cmlidXRlcy4gQSBjYWxsIHRvIGByZWZsZWN0QXR0cmlidXRlYCBkdXJpbmcgdGhlIGNvbnN0cnVjdG9yIHdpbGxcbiAgICAgKiBiZSBkZWZlcnJlZCB1bnRpbCB0aGUgZWxlbWVudCBpcyBjb25uZWN0ZWQgdG8gdGhlIGRvY3VtZW50LlxuICAgICAqXG4gICAgICogQHBhcmFtIHtzdHJpbmd9IGF0dHJpYnV0ZSAtIFRoZSBuYW1lIG9mIHRoZSAqYXR0cmlidXRlKiAobm90IHByb3BlcnR5KSB0byBzZXQuXG4gICAgICogQHBhcmFtIHtvYmplY3R9IHZhbHVlIC0gVGhlIHZhbHVlIHRvIHNldC4gSWYgbnVsbCwgdGhlIGF0dHJpYnV0ZSB3aWxsIGJlIHJlbW92ZWQuXG4gICAgICovXG4gICAgcmVmbGVjdEF0dHJpYnV0ZShhdHRyaWJ1dGUsIHZhbHVlKSB7XG4gICAgICByZXR1cm4gc2FmZUF0dHJpYnV0ZXMuc2V0QXR0cmlidXRlKHRoaXMsIGF0dHJpYnV0ZSwgdmFsdWUpO1xuICAgIH1cblxuICAgIC8qKlxuICAgICAqIFNldC91bnNldCB0aGUgY2xhc3Mgd2l0aCB0aGUgaW5kaWNhdGVkIG5hbWUuXG4gICAgICpcbiAgICAgKiBUaGlzIG1ldGhvZCBleGlzdHMgcHJpbWFyaWx5IHRvIGhhbmRsZSB0aGUgY2FzZSB3aGVyZSBhbiBlbGVtZW50IHdhbnRzIHRvXG4gICAgICogc2V0IGEgZGVmYXVsdCBwcm9wZXJ0eSB2YWx1ZSB0aGF0IHNob3VsZCBiZSByZWZsZWN0ZWQgYXMgYXMgY2xhc3MuIEFuXG4gICAgICogaW1wb3J0YW50IGxpbWl0YXRpb24gb2YgY3VzdG9tIGVsZW1lbnQgY29uc3R1cmN0b3JzIGlzIHRoYXQgdGhleSBjYW5ub3RcbiAgICAgKiBzZXQgYXR0cmlidXRlcywgaW5jbHVkaW5nIHRoZSBgY2xhc3NgIGF0dHJpYnV0ZS4gQSBjYWxsIHRvXG4gICAgICogYHJlZmxlY3RDbGFzc2AgZHVyaW5nIHRoZSBjb25zdHJ1Y3RvciB3aWxsIGJlIGRlZmVycmVkIHVudGlsIHRoZSBlbGVtZW50XG4gICAgICogaXMgY29ubmVjdGVkIHRvIHRoZSBkb2N1bWVudC5cbiAgICAgKlxuICAgICAqIEBwYXJhbSB7c3RyaW5nfSBjbGFzc05hbWUgLSBUaGUgbmFtZSBvZiB0aGUgY2xhc3MgdG8gc2V0LlxuICAgICAqIEBwYXJhbSB7b2JqZWN0fSB2YWx1ZSAtIFRydWUgdG8gc2V0IHRoZSBjbGFzcywgZmFsc2UgdG8gcmVtb3ZlIGl0LlxuICAgICAqL1xuICAgIHJlZmxlY3RDbGFzcyhjbGFzc05hbWUsIHZhbHVlKSB7XG4gICAgICByZXR1cm4gc2FmZUF0dHJpYnV0ZXMudG9nZ2xlQ2xhc3ModGhpcywgY2xhc3NOYW1lLCB2YWx1ZSk7XG4gICAgfVxuXG4gIH1cblxuICByZXR1cm4gQXR0cmlidXRlTWFyc2hhbGxpbmc7XG59O1xuXG5cbi8vIENvbnZlcnQgaHlwaGVuYXRlZCBmb28tYmFyIGF0dHJpYnV0ZSBuYW1lIHRvIGNhbWVsIGNhc2UgZm9vQmFyIHByb3BlcnR5IG5hbWUuXG5mdW5jdGlvbiBhdHRyaWJ1dGVUb1Byb3BlcnR5TmFtZShhdHRyaWJ1dGVOYW1lKSB7XG4gIGxldCBwcm9wZXJ0eU5hbWUgPSBhdHRyaWJ1dGVUb1Byb3BlcnR5TmFtZXNbYXR0cmlidXRlTmFtZV07XG4gIGlmICghcHJvcGVydHlOYW1lKSB7XG4gICAgLy8gQ29udmVydCBhbmQgbWVtb2l6ZS5cbiAgICBjb25zdCBoeXBlblJlZ0V4ID0gLy0oW2Etel0pL2c7XG4gICAgcHJvcGVydHlOYW1lID0gYXR0cmlidXRlTmFtZS5yZXBsYWNlKGh5cGVuUmVnRXgsXG4gICAgICAgIG1hdGNoID0+IG1hdGNoWzFdLnRvVXBwZXJDYXNlKCkpO1xuICAgIGF0dHJpYnV0ZVRvUHJvcGVydHlOYW1lc1thdHRyaWJ1dGVOYW1lXSA9IHByb3BlcnR5TmFtZTtcbiAgfVxuICByZXR1cm4gcHJvcGVydHlOYW1lO1xufVxuXG5mdW5jdGlvbiBhdHRyaWJ1dGVzRm9yQ2xhc3MoY2xhc3NGbikge1xuXG4gIC8vIFdlIHRyZWF0IHRoZSBlbGVtZW50IGJhc2UgY2xhc3NlcyBhcyBpZiB0aGV5IGhhdmUgbm8gYXR0cmlidXRlcywgc2luY2Ugd2VcbiAgLy8gZG9uJ3Qgd2FudCB0byByZWNlaXZlIGF0dHJpYnV0ZUNoYW5nZWRDYWxsYmFjayBmb3IgdGhlbS5cbiAgaWYgKGNsYXNzRm4gPT09IEhUTUxFbGVtZW50IHx8IGNsYXNzRm4gPT09IE9iamVjdCkge1xuICAgIHJldHVybiBbXTtcbiAgfVxuXG4gIC8vIEdldCBhdHRyaWJ1dGVzIGZvciBwYXJlbnQgY2xhc3MuXG4gIGNvbnN0IGJhc2VDbGFzcyA9IE9iamVjdC5nZXRQcm90b3R5cGVPZihjbGFzc0ZuLnByb3RvdHlwZSkuY29uc3RydWN0b3I7XG4gIGNvbnN0IGJhc2VBdHRyaWJ1dGVzID0gYXR0cmlidXRlc0ZvckNsYXNzKGJhc2VDbGFzcyk7XG5cbiAgLy8gR2V0IGF0dHJpYnV0ZXMgZm9yIHRoaXMgY2xhc3MuXG4gIGNvbnN0IHByb3BlcnR5TmFtZXMgPSBPYmplY3QuZ2V0T3duUHJvcGVydHlOYW1lcyhjbGFzc0ZuLnByb3RvdHlwZSk7XG4gIGNvbnN0IHNldHRlck5hbWVzID0gcHJvcGVydHlOYW1lcy5maWx0ZXIocHJvcGVydHlOYW1lID0+XG4gICAgdHlwZW9mIE9iamVjdC5nZXRPd25Qcm9wZXJ0eURlc2NyaXB0b3IoXG4gICAgICAgIGNsYXNzRm4ucHJvdG90eXBlLCBwcm9wZXJ0eU5hbWUpLnNldCA9PT0gJ2Z1bmN0aW9uJyk7XG4gIGNvbnN0IGF0dHJpYnV0ZXMgPSBzZXR0ZXJOYW1lcy5tYXAoc2V0dGVyTmFtZSA9PlxuICAgICAgcHJvcGVydHlOYW1lVG9BdHRyaWJ1dGUoc2V0dGVyTmFtZSkpO1xuXG4gIC8vIE1lcmdlLlxuICBjb25zdCBkaWZmID0gYXR0cmlidXRlcy5maWx0ZXIoYXR0cmlidXRlID0+XG4gICAgICBiYXNlQXR0cmlidXRlcy5pbmRleE9mKGF0dHJpYnV0ZSkgPCAwKTtcbiAgcmV0dXJuIGJhc2VBdHRyaWJ1dGVzLmNvbmNhdChkaWZmKTtcbn1cblxuLy8gQ29udmVydCBhIGNhbWVsIGNhc2UgZm9vQmFyIHByb3BlcnR5IG5hbWUgdG8gYSBoeXBoZW5hdGVkIGZvby1iYXIgYXR0cmlidXRlLlxuZnVuY3Rpb24gcHJvcGVydHlOYW1lVG9BdHRyaWJ1dGUocHJvcGVydHlOYW1lKSB7XG4gIGxldCBhdHRyaWJ1dGUgPSBwcm9wZXJ0eU5hbWVzVG9BdHRyaWJ1dGVzW3Byb3BlcnR5TmFtZV07XG4gIGlmICghYXR0cmlidXRlKSB7XG4gICAgLy8gQ29udmVydCBhbmQgbWVtb2l6ZS5cbiAgICBjb25zdCB1cHBlcmNhc2VSZWdFeCA9IC8oW0EtWl0pL2c7XG4gICAgYXR0cmlidXRlID0gcHJvcGVydHlOYW1lLnJlcGxhY2UodXBwZXJjYXNlUmVnRXgsICctJDEnKS50b0xvd2VyQ2FzZSgpO1xuICB9XG4gIHJldHVybiBhdHRyaWJ1dGU7XG59XG4iLCIvKiBFeHBvcnRlZCBmdW5jdGlvbiBleHRlbmRzIGEgYmFzZSBjbGFzcyB3aXRoIENvbXBvc2FibGUuICovXG5leHBvcnQgZGVmYXVsdCAoYmFzZSkgPT4ge1xuXG4gIC8qKlxuICAgKiBNaXhpbiB0byBtYWtlIGEgY2xhc3MgbW9yZSBlYXNpbHkgY29tcG9zYWJsZSB3aXRoIG90aGVyIG1peGlucy5cbiAgICpcbiAgICogVGhpcyBtaXhpbiBjb250cmlidXRlcyBhIGBjb21wb3NlYCBtZXRob2QgdGhhdCBhcHBsaWVzIGEgc2V0IG9mIG1peGluXG4gICAqIGZ1bmN0aW9ucyBhbmQgcmV0dXJucyB0aGUgcmVzdWx0aW5nIG5ldyBjbGFzcy4gVGhpcyBzdWdhciBjYW4gbWFrZSB0aGVcbiAgICogYXBwbGljYXRpb24gb2YgbWFueSBtaXhpbnMgYXQgb25jZSBlYXNpZXIgdG8gcmVhZC5cbiAgICovXG4gIGNsYXNzIENvbXBvc2FibGUgZXh0ZW5kcyBiYXNlIHtcblxuICAgIC8qKlxuICAgICAqIEFwcGx5IGEgc2V0IG9mIG1peGluIGZ1bmN0aW9ucyBvciBtaXhpbiBvYmplY3RzIHRvIHRoZSBwcmVzZW50IGNsYXNzIGFuZFxuICAgICAqIHJldHVybiB0aGUgbmV3IGNsYXNzLlxuICAgICAqXG4gICAgICogSW5zdGVhZCBvZiB3cml0aW5nOlxuICAgICAqXG4gICAgICogICAgIGxldCBNeUNsYXNzID0gTWl4aW4xKE1peGluMihNaXhpbjMoTWl4aW40KE1peGluNShCYXNlQ2xhc3MpKSkpKTtcbiAgICAgKlxuICAgICAqIFlvdSBjYW4gd3JpdGU6XG4gICAgICpcbiAgICAgKiAgICAgbGV0IE15Q2xhc3MgPSBDb21wb3NhYmxlTWl4aW4oQmFzZUNsYXNzKS5jb21wb3NlKFxuICAgICAqICAgICAgIE1peGluMSxcbiAgICAgKiAgICAgICBNaXhpbjIsXG4gICAgICogICAgICAgTWl4aW4zLFxuICAgICAqICAgICAgIE1peGluNCxcbiAgICAgKiAgICAgICBNaXhpbjVcbiAgICAgKiAgICAgKTtcbiAgICAgKlxuICAgICAqIFRoaXMgZnVuY3Rpb24gY2FuIGFsc28gdGFrZSBtaXhpbiBvYmplY3RzLiBBIG1peGluIG9iamVjdCBpcyBqdXN0IGFcbiAgICAgKiBzaG9ydGhhbmQgZm9yIGEgbWl4aW4gZnVuY3Rpb24gdGhhdCBjcmVhdGVzIGEgbmV3IHN1YmNsYXNzIHdpdGggdGhlIGdpdmVuXG4gICAgICogbWVtYmVycy4gVGhlIG1peGluIG9iamVjdCdzIG1lbWJlcnMgYXJlICpub3QqIGNvcGllZCBkaXJlY3RseSBvbnRvIHRoZVxuICAgICAqIHByb3RvdHlwZSBvZiB0aGUgYmFzZSBjbGFzcywgYXMgd2l0aCB0cmFkaXRpb25hbCBtaXhpbnMuXG4gICAgICpcbiAgICAgKiBJbiBhZGRpdGlvbiB0byBwcm92aWRpbmcgc3ludGFjdGljIHN1Z2FyLCB0aGlzIG1peGluIGNhbiBiZSB1c2VkIHRvXG4gICAgICogZGVmaW5lIGEgY2xhc3MgaW4gRVM1LCB3aGljaCBsYWNrcyBFUzYncyBgY2xhc3NgIGtleXdvcmQuXG4gICAgICpcbiAgICAgKiBAcGFyYW0gey4uLm1peGluc30gbWl4aW5zIC0gQSBzZXQgb2YgbWl4aW4gZnVuY3Rpb25zIG9yIG9iamVjdHMgdG8gYXBwbHkuXG4gICAgICovXG4gICAgc3RhdGljIGNvbXBvc2UoLi4ubWl4aW5zKSB7XG4gICAgICAvLyBXZSBjcmVhdGUgYSBuZXcgc3ViY2xhc3MgZm9yIGVhY2ggbWl4aW4gaW4gdHVybi4gVGhlIHJlc3VsdCBiZWNvbWVzXG4gICAgICAvLyB0aGUgYmFzZSBjbGFzcyBleHRlbmRlZCBieSBhbnkgc3Vic2VxdWVudCBtaXhpbnMuIEl0IHR1cm5zIG91dCB0aGF0XG4gICAgICAvLyB3ZSBjYW4gdXNlIEFycmF5LnJlZHVjZSgpIHRvIGNvbmNpc2VseSBleHByZXNzIHRoaXMsIHVzaW5nIHRoZSBjdXJyZW50XG4gICAgICAvLyBvYmplY3QgYXMgdGhlIHNlZWQgZm9yIHJlZHVjZSgpLlxuICAgICAgcmV0dXJuIG1peGlucy5yZWR1Y2UoY29tcG9zZUNsYXNzLCB0aGlzKTtcbiAgICB9XG5cbiAgfVxuXG4gIHJldHVybiBDb21wb3NhYmxlO1xufTtcblxuXG4vLyBQcm9wZXJ0aWVzIGRlZmluZWQgYnkgT2JqZWN0IHRoYXQgd2UgZG9uJ3Qgd2FudCB0byBtaXhpbi5cbmNvbnN0IE5PTl9NSVhBQkxFX09CSkVDVF9QUk9QRVJUSUVTID0gW1xuICAnY29uc3RydWN0b3InXG5dO1xuXG4vKlxuICogQXBwbHkgdGhlIG1peGluIHRvIHRoZSBnaXZlbiBiYXNlIGNsYXNzIHRvIHJldHVybiBhIG5ldyBjbGFzcy5cbiAqIFRoZSBtaXhpbiBjYW4gZWl0aGVyIGJlIGEgZnVuY3Rpb24gdGhhdCByZXR1cm5zIHRoZSBtb2RpZmllZCBjbGFzcywgb3IgYVxuICogcGxhaW4gb2JqZWN0IHdob3NlIG1lbWJlcnMgd2lsbCBiZSBjb3BpZWQgdG8gdGhlIG5ldyBjbGFzcycgcHJvdG90eXBlLlxuICovXG5mdW5jdGlvbiBjb21wb3NlQ2xhc3MoYmFzZSwgbWl4aW4pIHtcbiAgaWYgKHR5cGVvZiBtaXhpbiA9PT0gJ2Z1bmN0aW9uJykge1xuICAgIC8vIE1peGluIGZ1bmN0aW9uXG4gICAgcmV0dXJuIG1peGluKGJhc2UpO1xuICB9IGVsc2Uge1xuICAgIC8vIE1peGluIG9iamVjdFxuICAgIGNsYXNzIFN1YmNsYXNzIGV4dGVuZHMgYmFzZSB7fVxuICAgIGNvcHlPd25Qcm9wZXJ0aWVzKG1peGluLCBTdWJjbGFzcy5wcm90b3R5cGUsIE5PTl9NSVhBQkxFX09CSkVDVF9QUk9QRVJUSUVTKTtcbiAgICByZXR1cm4gU3ViY2xhc3M7XG4gIH1cbn1cblxuXG4vKlxuICogQ29weSB0aGUgZ2l2ZW4gcHJvcGVydGllcy9tZXRob2RzIHRvIHRoZSB0YXJnZXQuXG4gKiBSZXR1cm4gdGhlIHVwZGF0ZWQgdGFyZ2V0LlxuICovXG5mdW5jdGlvbiBjb3B5T3duUHJvcGVydGllcyhzb3VyY2UsIHRhcmdldCwgaWdub3JlUHJvcGVydHlOYW1lcyA9IFtdKSB7XG4gIE9iamVjdC5nZXRPd25Qcm9wZXJ0eU5hbWVzKHNvdXJjZSkuZm9yRWFjaChuYW1lID0+IHtcbiAgICBpZiAoaWdub3JlUHJvcGVydHlOYW1lcy5pbmRleE9mKG5hbWUpIDwgMCkge1xuICAgICAgY29uc3QgZGVzY3JpcHRvciA9IE9iamVjdC5nZXRPd25Qcm9wZXJ0eURlc2NyaXB0b3Ioc291cmNlLCBuYW1lKTtcbiAgICAgIE9iamVjdC5kZWZpbmVQcm9wZXJ0eSh0YXJnZXQsIG5hbWUsIGRlc2NyaXB0b3IpO1xuICAgIH1cbiAgfSk7XG4gIHJldHVybiB0YXJnZXQ7XG59XG4iLCIvKiBFeHBvcnRlZCBmdW5jdGlvbiBleHRlbmRzIGEgYmFzZSBjbGFzcyB3aXRoIERpc3RyaWJ1dGVkQ2hpbGRyZW4uICovXG5leHBvcnQgZGVmYXVsdCAoYmFzZSkgPT4ge1xuXG4gIC8qKlxuICAgKiBNaXhpbiB3aGljaCBkZWZpbmVzIGhlbHBlcnMgZm9yIGFjY2Vzc2luZyBhIGNvbXBvbmVudCdzIGRpc3RyaWJ1dGVkXG4gICAqIGNoaWxkcmVuIGFzIGEgZmxhdHRlbmVkIGFycmF5IG9yIHN0cmluZy5cbiAgICpcbiAgICogVGhlIHN0YW5kYXJkIERPTSBBUEkgcHJvdmlkZXMgc2V2ZXJhbCB3YXlzIG9mIGFjY2Vzc2luZyBjaGlsZCBjb250ZW50OlxuICAgKiBgY2hpbGRyZW5gLCBgY2hpbGROb2Rlc2AsIGFuZCBgdGV4dENvbnRlbnRgLiBOb25lIG9mIHRoZXNlIGZ1bmN0aW9ucyBhcmVcbiAgICogU2hhZG93IERPTSBhd2FyZS4gVGhpcyBtaXhpbiBkZWZpbmVzIHZhcmlhdGlvbnMgb2YgdGhvc2UgZnVuY3Rpb25zIHRoYXRcbiAgICogKmFyZSogU2hhZG93IERPTSBhd2FyZS5cbiAgICpcbiAgICogRXhhbXBsZTogeW91IGNyZWF0ZSBhIGNvbXBvbmVudCBgPGNvdW50LWNoaWxkcmVuPmAgdGhhdCBkaXNwbGF5cyBhIG51bWJlclxuICAgKiBlcXVhbCB0byB0aGUgbnVtYmVyIG9mIGNoaWxkcmVuIHBsYWNlZCBpbnNpZGUgdGhhdCBjb21wb25lbnQuIElmIHNvbWVvbmVcbiAgICogaW5zdGFudGlhdGVzIHlvdXIgY29tcG9uZW50IGxpa2U6XG4gICAqXG4gICAqICAgICA8Y291bnQtY2hpbGRyZW4+XG4gICAqICAgICAgIDxkaXY+PC9kaXY+XG4gICAqICAgICAgIDxkaXY+PC9kaXY+XG4gICAqICAgICAgIDxkaXY+PC9kaXY+XG4gICAqICAgICA8L2NvdW50LWNoaWxkcmVuPlxuICAgKlxuICAgKiBUaGVuIHRoZSBjb21wb25lbnQgc2hvdWxkIHNob3cgXCIzXCIsIGJlY2F1c2UgdGhlcmUgYXJlIHRocmVlIGNoaWxkcmVuLiBUb1xuICAgKiBjYWxjdWxhdGUgdGhlIG51bWJlciBvZiBjaGlsZHJlbiwgdGhlIGNvbXBvbmVudCBjYW4ganVzdCBjYWxjdWxhdGVcbiAgICogYHRoaXMuY2hpbGRyZW4ubGVuZ3RoYC4gSG93ZXZlciwgc3VwcG9zZSBzb21lb25lIGluc3RhbnRpYXRlcyB5b3VyXG4gICAqIGNvbXBvbmVudCBpbnNpZGUgb25lIG9mIHRoZWlyIG93biBjb21wb25lbnRzLCBhbmQgcHV0cyBhIGA8c2xvdD5gIGVsZW1lbnRcbiAgICogaW5zaWRlIHlvdXIgY29tcG9uZW50OlxuICAgKlxuICAgKiAgICAgPGNvdW50LWNoaWxkcmVuPlxuICAgKiAgICAgICA8c2xvdD48L3Nsb3Q+XG4gICAqICAgICA8L2NvdW50LWNoaWxkcmVuPlxuICAgKlxuICAgKiBJZiB5b3VyIGNvbXBvbmVudCBvbmx5IGxvb2tzIGF0IGB0aGlzLmNoaWxkcmVuYCwgaXQgd2lsbCBhbHdheXMgc2VlIGV4YWN0bHlcbiAgICogb25lIGNoaWxkIOKAlMKgdGhlIGA8c2xvdD5gIGVsZW1lbnQuIEJ1dCB0aGUgdXNlciBsb29raW5nIGF0IHRoZSBwYWdlIHdpbGxcbiAgICogKnNlZSogYW55IG5vZGVzIGRpc3RyaWJ1dGVkIHRvIHRoYXQgc2xvdC4gVG8gbWF0Y2ggd2hhdCB0aGUgdXNlciBzZWVzLCB5b3VyXG4gICAqIGNvbXBvbmVudCBzaG91bGQgZXhwYW5kIGFueSBgPHNsb3Q+YCBlbGVtZW50cyBpdCBjb250YWlucy5cbiAgICpcbiAgICogVGhhdCBpcyB0aGUgcHJvYmxlbSB0aGlzIG1peGluIHNvbHZlcy4gQWZ0ZXIgYXBwbHlpbmcgdGhpcyBtaXhpbiwgeW91clxuICAgKiBjb21wb25lbnQgY29kZSBoYXMgYWNjZXNzIHRvIGB0aGlzLmRpc3RyaWJ1dGVkQ2hpbGRyZW5gLCB3aG9zZSBgbGVuZ3RoYFxuICAgKiB3aWxsIHJldHVybiB0aGUgdG90YWwgbnVtYmVyIG9mIGFsbCBjaGlsZHJlbiBkaXN0cmlidXRlZCB0byB5b3VyIGNvbXBvbmVudFxuICAgKiBpbiB0aGUgY29tcG9zZWQgdHJlZS5cbiAgICpcbiAgICogTm90ZTogVGhlIGxhdGVzdCBDdXN0b20gRWxlbWVudHMgQVBJIGRlc2lnbiBjYWxscyBmb3IgYSBuZXcgZnVuY3Rpb24sXG4gICAqIGBnZXRBc3NpZ25lZE5vZGVzYCB0aGF0IHRha2VzIGFuIG9wdGlvbmFsIGBkZWVwYCBwYXJhbWV0ZXIsIHRoYXQgd2lsbCBzb2x2ZVxuICAgKiB0aGlzIHByb2JsZW0gYXQgdGhlIEFQSSBsZXZlbC5cbiAgICovXG4gIGNsYXNzIERpc3RyaWJ1dGVkQ2hpbGRyZW4gZXh0ZW5kcyBiYXNlIHtcblxuICAgIC8qKlxuICAgICAqIEFuIGluLW9yZGVyIGNvbGxlY3Rpb24gb2YgZGlzdHJpYnV0ZWQgY2hpbGRyZW4sIGV4cGFuZGluZyBhbnkgc2xvdFxuICAgICAqIGVsZW1lbnRzLiBMaWtlIHRoZSBzdGFuZGFyZCBjaGlsZHJlbiBwcm9wZXJ0eSwgdGhpcyBza2lwcyB0ZXh0IG5vZGVzLlxuICAgICAqXG4gICAgICogQHR5cGUge0hUTUxFbGVtZW50W119XG4gICAgICovXG4gICAgZ2V0IGRpc3RyaWJ1dGVkQ2hpbGRyZW4oKSB7XG4gICAgICByZXR1cm4gZXhwYW5kQ29udGVudEVsZW1lbnRzKHRoaXMuY2hpbGRyZW4sIGZhbHNlKTtcbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBBbiBpbi1vcmRlciBjb2xsZWN0aW9uIG9mIGRpc3RyaWJ1dGVkIGNoaWxkIG5vZGVzLCBleHBhbmRpbmcgYW55IHNsb3RcbiAgICAgKiBlbGVtZW50cy4gTGlrZSB0aGUgc3RhbmRhcmQgY2hpbGROb2RlcyBwcm9wZXJ0eSwgdGhpcyBpbmNsdWRlcyB0ZXh0XG4gICAgICogbm9kZXMuXG4gICAgICpcbiAgICAgKiBAdHlwZSB7Tm9kZVtdfVxuICAgICAqL1xuICAgIGdldCBkaXN0cmlidXRlZENoaWxkTm9kZXMoKSB7XG4gICAgICByZXR1cm4gZXhwYW5kQ29udGVudEVsZW1lbnRzKHRoaXMuY2hpbGROb2RlcywgdHJ1ZSk7XG4gICAgfVxuXG4gICAgLyoqXG4gICAgICogVGhlIGNvbmNhdGVuYXRlZCB0ZXh0IGNvbnRlbnQgb2YgYWxsIGRpc3RyaWJ1dGVkIGNoaWxkIG5vZGVzLCBleHBhbmRpbmdcbiAgICAgKiBhbnkgc2xvdCBlbGVtZW50cy5cbiAgICAgKlxuICAgICAqIEB0eXBlIHtzdHJpbmd9XG4gICAgICovXG4gICAgZ2V0IGRpc3RyaWJ1dGVkVGV4dENvbnRlbnQoKSB7XG4gICAgICBjb25zdCBzdHJpbmdzID0gdGhpcy5kaXN0cmlidXRlZENoaWxkTm9kZXMubWFwKGZ1bmN0aW9uKGNoaWxkKSB7XG4gICAgICAgIHJldHVybiBjaGlsZC50ZXh0Q29udGVudDtcbiAgICAgIH0pO1xuICAgICAgcmV0dXJuIHN0cmluZ3Muam9pbignJyk7XG4gICAgfVxuXG4gIH1cblxuICByZXR1cm4gRGlzdHJpYnV0ZWRDaGlsZHJlbjtcbn07XG5cblxuLypcbiAqIEdpdmVuIGEgYXJyYXkgb2Ygbm9kZXMsIHJldHVybiBhIG5ldyBhcnJheSB3aXRoIGFueSBjb250ZW50IGVsZW1lbnRzIGV4cGFuZGVkXG4gKiB0byB0aGUgbm9kZXMgZGlzdHJpYnV0ZWQgdG8gdGhhdCBjb250ZW50IGVsZW1lbnQuIFRoaXMgcnVsZSBpcyBhcHBsaWVkXG4gKiByZWN1cnNpdmVseS5cbiAqXG4gKiBJZiBpbmNsdWRlVGV4dE5vZGVzIGlzIHRydWUsIHRleHQgbm9kZXMgd2lsbCBiZSBpbmNsdWRlZCwgYXMgaW4gdGhlXG4gKiBzdGFuZGFyZCBjaGlsZE5vZGVzIHByb3BlcnR5OyBieSBkZWZhdWx0LCB0aGlzIHNraXBzIHRleHQgbm9kZXMsIGxpa2UgdGhlXG4gKiBzdGFuZGFyZCBjaGlsZHJlbiBwcm9wZXJ0eS5cbiAqL1xuZnVuY3Rpb24gZXhwYW5kQ29udGVudEVsZW1lbnRzKG5vZGVzLCBpbmNsdWRlVGV4dE5vZGVzKSB7XG4gIGNvbnN0IGV4cGFuZGVkID0gQXJyYXkucHJvdG90eXBlLm1hcC5jYWxsKG5vZGVzLCBub2RlID0+IHtcbiAgICAvLyBXZSB3YW50IHRvIHNlZSBpZiB0aGUgbm9kZSBpcyBhbiBpbnN0YW5jZW9mIEhUTUxTbG90RUxlbWVudCwgYnV0XG4gICAgLy8gdGhhdCBjbGFzcyB3b24ndCBleGlzdCBpZiB0aGUgYnJvd3NlciB0aGF0IGRvZXNuJ3Qgc3VwcG9ydCBuYXRpdmVcbiAgICAvLyBTaGFkb3cgRE9NIGFuZCBpZiB0aGUgU2hhZG93IERPTSBwb2x5ZmlsbCBoYXNuJ3QgYmVlbiBsb2FkZWQuIEluc3RlYWQsXG4gICAgLy8gd2UgZG8gYSBzaW1wbGlzdGljIGNoZWNrIHRvIHNlZSBpZiB0aGUgdGFnIG5hbWUgaXMgXCJzbG90XCIuXG4gICAgY29uc3QgaXNTbG90ID0gdHlwZW9mIEhUTUxTbG90RWxlbWVudCAhPT0gJ3VuZGVmaW5lZCcgP1xuICAgICAgbm9kZSBpbnN0YW5jZW9mIEhUTUxTbG90RWxlbWVudCA6XG4gICAgICBub2RlLmxvY2FsTmFtZSA9PT0gJ3Nsb3QnO1xuICAgIGlmIChpc1Nsb3QpIHtcbiAgICAgIC8vIFVzZSB0aGUgbm9kZXMgYXNzaWduZWQgdG8gdGhpcyBub2RlIGluc3RlYWQuXG4gICAgICBjb25zdCBhc3NpZ25lZE5vZGVzID0gbm9kZS5hc3NpZ25lZE5vZGVzKHsgZmxhdHRlbjogdHJ1ZSB9KTtcbiAgICAgIHJldHVybiBhc3NpZ25lZE5vZGVzID9cbiAgICAgICAgZXhwYW5kQ29udGVudEVsZW1lbnRzKGFzc2lnbmVkTm9kZXMsIGluY2x1ZGVUZXh0Tm9kZXMpIDpcbiAgICAgICAgW107XG4gICAgfSBlbHNlIGlmIChub2RlIGluc3RhbmNlb2YgSFRNTEVsZW1lbnQpIHtcbiAgICAgIC8vIFBsYWluIGVsZW1lbnQ7IHVzZSBhcyBpcy5cbiAgICAgIHJldHVybiBbbm9kZV07XG4gICAgfSBlbHNlIGlmIChub2RlIGluc3RhbmNlb2YgVGV4dCAmJiBpbmNsdWRlVGV4dE5vZGVzKSB7XG4gICAgICAvLyBUZXh0IG5vZGUuXG4gICAgICByZXR1cm4gW25vZGVdO1xuICAgIH0gZWxzZSB7XG4gICAgICAvLyBDb21tZW50LCBwcm9jZXNzaW5nIGluc3RydWN0aW9uLCBldGMuOyBza2lwLlxuICAgICAgcmV0dXJuIFtdO1xuICAgIH1cbiAgfSk7XG4gIGNvbnN0IGZsYXR0ZW5lZCA9IFtdLmNvbmNhdCguLi5leHBhbmRlZCk7XG4gIHJldHVybiBmbGF0dGVuZWQ7XG59XG4iLCIvKiBFeHBvcnRlZCBmdW5jdGlvbiBleHRlbmRzIGEgYmFzZSBjbGFzcyB3aXRoIFNoYWRvd0VsZW1lbnRSZWZlcmVuY2VzLiAqL1xuZXhwb3J0IGRlZmF1bHQgKGJhc2UpID0+IHtcblxuICAvKipcbiAgICogTWl4aW4gdG8gY3JlYXRlIHJlZmVyZW5jZXMgdG8gZWxlbWVudHMgaW4gYSBjb21wb25lbnQncyBTaGFkb3cgRE9NIHN1YnRyZWUuXG4gICAqXG4gICAqIFRoaXMgYWRkcyBhIG1lbWJlciBvbiB0aGUgY29tcG9uZW50IGNhbGxlZCBgdGhpcy4kYCB0aGF0IGNhbiBiZSB1c2VkIHRvXG4gICAqIHJlZmVyZW5jZSBzaGFkb3cgZWxlbWVudHMgd2l0aCBJRHMuIEUuZy4sIGlmIGNvbXBvbmVudCdzIHNoYWRvdyBjb250YWlucyBhblxuICAgKiBlbGVtZW50IGA8YnV0dG9uIGlkPVwiZm9vXCI+YCwgdGhlbiB0aGlzIG1peGluIHdpbGwgY3JlYXRlIGEgbWVtYmVyXG4gICAqIGB0aGlzLiQuZm9vYCB0aGF0IHBvaW50cyB0byB0aGF0IGJ1dHRvbi5cbiAgICpcbiAgICogU3VjaCByZWZlcmVuY2VzIHNpbXBsaWZ5IGEgY29tcG9uZW50J3MgYWNjZXNzIHRvIGl0cyBvd24gZWxlbWVudHMuIEluXG4gICAqIGV4Y2hhbmdlLCB0aGlzIG1peGluIHRyYWRlcyBvZmYgYSBvbmUtdGltZSBjb3N0IG9mIHF1ZXJ5aW5nIGFsbCBlbGVtZW50cyBpblxuICAgKiB0aGUgc2hhZG93IHRyZWUgaW5zdGVhZCBvZiBwYXlpbmcgYW4gb25nb2luZyBjb3N0IHRvIHF1ZXJ5IGZvciBhbiBlbGVtZW50XG4gICAqIGVhY2ggdGltZSB0aGUgY29tcG9uZW50IHdhbnRzIHRvIGluc3BlY3Qgb3IgbWFuaXB1bGF0ZSBpdC5cbiAgICpcbiAgICogVGhpcyBtaXhpbiBleHBlY3RzIHRoZSBjb21wb25lbnQgdG8gZGVmaW5lIGEgU2hhZG93IERPTSBzdWJ0cmVlLiBZb3UgY2FuXG4gICAqIGNyZWF0ZSB0aGF0IHRyZWUgeW91cnNlbGYsIG9yIG1ha2UgdXNlIG9mXG4gICAqIFtTaGFkb3dUZW1wbGF0ZU1peGluXShTaGFkb3dUZW1wbGF0ZU1peGluLm1kKS5cbiAgICpcbiAgICogVGhpcyBtaXhpbiBpcyBpbnNwaXJlZCBieSBQb2x5bWVyJ3MgW2F1dG9tYXRpY1xuICAgKiBub2RlIGZpbmRpbmddKGh0dHBzOi8vd3d3LnBvbHltZXItcHJvamVjdC5vcmcvMS4wL2RvY3MvZGV2Z3VpZGUvbG9jYWwtZG9tLmh0bWwjbm9kZS1maW5kaW5nKVxuICAgKiBmZWF0dXJlLlxuICAgKi9cbiAgY2xhc3MgU2hhZG93RWxlbWVudFJlZmVyZW5jZXMgZXh0ZW5kcyBiYXNlIHtcblxuICAgIGNvbnN0cnVjdG9yKCkge1xuICAgICAgc3VwZXIoKTtcbiAgICAgIGlmICh0aGlzLnNoYWRvd1Jvb3QpIHtcbiAgICAgICAgLy8gTG9vayBmb3IgZWxlbWVudHMgaW4gdGhlIHNoYWRvdyBzdWJ0cmVlIHRoYXQgaGF2ZSBpZCBhdHRyaWJ1dGVzLlxuICAgICAgICAvLyBBbiBhbHRlcm5hdGl2ZWx5IGltcGxlbWVudGF0aW9uIG9mIHRoaXMgbWl4aW4gd291bGQgYmUgdG8ganVzdCBkZWZpbmVcbiAgICAgICAgLy8gYSB0aGlzLiQgZ2V0dGVyIHRoYXQgbGF6aWx5IGRvZXMgdGhpcyBzZWFyY2ggdGhlIGZpcnN0IHRpbWUgc29tZW9uZVxuICAgICAgICAvLyB0cmllcyB0byBhY2Nlc3MgdGhpcy4kLiBUaGF0IG1pZ2h0IGludHJvZHVjZSBzb21lIGNvbXBsZXhpdHkg4oCTIGlmIHRoZVxuICAgICAgICAvLyB0aGUgdHJlZSBjaGFuZ2VkIGFmdGVyIGl0IHdhcyBmaXJzdCBwb3B1bGF0ZWQsIHRoZSByZXN1bHQgb2ZcbiAgICAgICAgLy8gc2VhcmNoaW5nIGZvciBhIG5vZGUgbWlnaHQgYmUgc29tZXdoYXQgdW5wcmVkaWN0YWJsZS5cbiAgICAgICAgdGhpcy4kID0ge307XG4gICAgICAgIGNvbnN0IG5vZGVzV2l0aElkcyA9IHRoaXMuc2hhZG93Um9vdC5xdWVyeVNlbGVjdG9yQWxsKCdbaWRdJyk7XG4gICAgICAgIFtdLmZvckVhY2guY2FsbChub2Rlc1dpdGhJZHMsIG5vZGUgPT4ge1xuICAgICAgICAgIGNvbnN0IGlkID0gbm9kZS5nZXRBdHRyaWJ1dGUoJ2lkJyk7XG4gICAgICAgICAgdGhpcy4kW2lkXSA9IG5vZGU7XG4gICAgICAgIH0pO1xuICAgICAgfVxuICAgIH1cblxuICAgIC8qKlxuICAgICAqIFRoZSBjb2xsZWN0aW9uIG9mIHJlZmVyZW5jZXMgdG8gdGhlIGVsZW1lbnRzIHdpdGggSURzIGluIGEgY29tcG9uZW50J3NcbiAgICAgKiBTaGFkb3cgRE9NIHN1YnRyZWUuXG4gICAgICpcbiAgICAgKiBAdHlwZSB7b2JqZWN0fVxuICAgICAqIEBtZW1iZXIgJFxuICAgICAqL1xuICB9XG5cbiAgcmV0dXJuIFNoYWRvd0VsZW1lbnRSZWZlcmVuY2VzO1xufTtcbiIsImltcG9ydCBzeW1ib2xzIGZyb20gJy4uL3NyYy9zeW1ib2xzJztcblxuXG4vKiBFeHBvcnRlZCBmdW5jdGlvbiBleHRlbmRzIGEgYmFzZSBjbGFzcyB3aXRoIFNoYWRvd1RlbXBsYXRlLiAqL1xuZXhwb3J0IGRlZmF1bHQgKGJhc2UpID0+IHtcblxuICAvKipcbiAgICogTWl4aW4gZm9yIHN0YW1waW5nIGEgdGVtcGxhdGUgaW50byBhIFNoYWRvdyBET00gc3VidHJlZSB1cG9uIGNvbXBvbmVudFxuICAgKiBpbnN0YW50aWF0aW9uLlxuICAgKlxuICAgKiBUbyB1c2UgdGhpcyBtaXhpbiwgZGVmaW5lIGEgYHRlbXBsYXRlYCBwcm9wZXJ0eSBhcyBhIHN0cmluZyBvciBIVE1MXG4gICAqIGA8dGVtcGxhdGU+YCBlbGVtZW50OlxuICAgKlxuICAgKiAgICAgY2xhc3MgTXlFbGVtZW50IGV4dGVuZHMgU2hhZG93VGVtcGxhdGVNaXhpbihIVE1MRWxlbWVudCkge1xuICAgKiAgICAgICBnZXQgW3N5bWJvbHMudGVtcGxhdGVdKCkge1xuICAgKiAgICAgICAgIHJldHVybiBgSGVsbG8sIDxlbT53b3JsZDwvZW0+LmA7XG4gICAqICAgICAgIH1cbiAgICogICAgIH1cbiAgICpcbiAgICogV2hlbiB5b3VyIGNvbXBvbmVudCBjbGFzcyBpcyBpbnN0YW50aWF0ZWQsIGEgc2hhZG93IHJvb3Qgd2lsbCBiZSBjcmVhdGVkIG9uXG4gICAqIHRoZSBpbnN0YW5jZSwgYW5kIHRoZSBjb250ZW50cyBvZiB0aGUgdGVtcGxhdGUgd2lsbCBiZSBjbG9uZWQgaW50byB0aGVcbiAgICogc2hhZG93IHJvb3QuIElmIHlvdXIgY29tcG9uZW50IGRvZXMgbm90IGRlZmluZSBhIGB0ZW1wbGF0ZWAgcHJvcGVydHksIHRoaXNcbiAgICogbWl4aW4gaGFzIG5vIGVmZmVjdC5cbiAgICpcbiAgICogRm9yIHRoZSB0aW1lIGJlaW5nLCB0aGlzIGV4dGVuc2lvbiByZXRhaW5zIHN1cHBvcnQgZm9yIFNoYWRvdyBET00gdjAuIFRoYXRcbiAgICogd2lsbCBldmVudHVhbGx5IGJlIGRlcHJlY2F0ZWQgYXMgYnJvd3NlcnMgKGFuZCB0aGUgU2hhZG93IERPTSBwb2x5ZmlsbClcbiAgICogaW1wbGVtZW50IFNoYWRvdyBET00gdjEuXG4gICAqL1xuICBjbGFzcyBTaGFkb3dUZW1wbGF0ZSBleHRlbmRzIGJhc2Uge1xuXG4gICAgLypcbiAgICAgKiBJZiB0aGUgY29tcG9uZW50IGRlZmluZXMgYSB0ZW1wbGF0ZSwgYSBzaGFkb3cgcm9vdCB3aWxsIGJlIGNyZWF0ZWQgb24gdGhlXG4gICAgICogY29tcG9uZW50IGluc3RhbmNlLCBhbmQgdGhlIHRlbXBsYXRlIHN0YW1wZWQgaW50byBpdC5cbiAgICAgKi9cbiAgICBjb25zdHJ1Y3RvcigpIHtcbiAgICAgIHN1cGVyKCk7XG4gICAgICBsZXQgdGVtcGxhdGUgPSB0aGlzW3N5bWJvbHMudGVtcGxhdGVdO1xuICAgICAgLy8gVE9ETzogU2F2ZSB0aGUgcHJvY2Vzc2VkIHRlbXBsYXRlIHdpdGggdGhlIGNvbXBvbmVudCdzIGNsYXNzIHByb3RvdHlwZVxuICAgICAgLy8gc28gaXQgZG9lc24ndCBuZWVkIHRvIGJlIHByb2Nlc3NlZCB3aXRoIGV2ZXJ5IGluc3RhbnRpYXRpb24uXG4gICAgICBpZiAodGVtcGxhdGUpIHtcblxuICAgICAgICBpZiAodHlwZW9mIHRlbXBsYXRlID09PSAnc3RyaW5nJykge1xuICAgICAgICAgIC8vIFVwZ3JhZGUgcGxhaW4gc3RyaW5nIHRvIHJlYWwgdGVtcGxhdGUuXG4gICAgICAgICAgdGVtcGxhdGUgPSBjcmVhdGVUZW1wbGF0ZVdpdGhJbm5lckhUTUwodGVtcGxhdGUpO1xuICAgICAgICB9XG5cbiAgICAgICAgaWYgKHdpbmRvdy5TaGFkb3dET01Qb2x5ZmlsbCkge1xuICAgICAgICAgIHNoaW1UZW1wbGF0ZVN0eWxlcyh0ZW1wbGF0ZSwgdGhpcy5sb2NhbE5hbWUpO1xuICAgICAgICB9XG5cbiAgICAgICAgY29uc3Qgcm9vdCA9IHRoaXMuYXR0YWNoU2hhZG93KHsgbW9kZTogJ29wZW4nIH0pO1xuICAgICAgICBjb25zdCBjbG9uZSA9IGRvY3VtZW50LmltcG9ydE5vZGUodGVtcGxhdGUuY29udGVudCwgdHJ1ZSk7XG4gICAgICAgIHJvb3QuYXBwZW5kQ2hpbGQoY2xvbmUpO1xuICAgICAgfVxuICAgIH1cblxuICB9XG5cbiAgcmV0dXJuIFNoYWRvd1RlbXBsYXRlO1xufTtcblxuXG4vLyBDb252ZXJ0IGEgcGxhaW4gc3RyaW5nIG9mIEhUTUwgaW50byBhIHJlYWwgdGVtcGxhdGUgZWxlbWVudC5cbmZ1bmN0aW9uIGNyZWF0ZVRlbXBsYXRlV2l0aElubmVySFRNTChpbm5lckhUTUwpIHtcbiAgY29uc3QgdGVtcGxhdGUgPSBkb2N1bWVudC5jcmVhdGVFbGVtZW50KCd0ZW1wbGF0ZScpO1xuICAvLyBSRVZJRVc6IElzIHRoZXJlIGFuIGVhc2llciB3YXkgdG8gZG8gdGhpcz9cbiAgLy8gV2UnZCBsaWtlIHRvIGp1c3Qgc2V0IGlubmVySFRNTCBvbiB0aGUgdGVtcGxhdGUgY29udGVudCwgYnV0IHNpbmNlIGl0J3NcbiAgLy8gYSBEb2N1bWVudEZyYWdtZW50LCB0aGF0IGRvZXNuJ3Qgd29yay5cbiAgY29uc3QgZGl2ID0gZG9jdW1lbnQuY3JlYXRlRWxlbWVudCgnZGl2Jyk7XG4gIGRpdi5pbm5lckhUTUwgPSBpbm5lckhUTUw7XG4gIHdoaWxlIChkaXYuY2hpbGROb2Rlcy5sZW5ndGggPiAwKSB7XG4gICAgdGVtcGxhdGUuY29udGVudC5hcHBlbmRDaGlsZChkaXYuY2hpbGROb2Rlc1swXSk7XG4gIH1cbiAgcmV0dXJuIHRlbXBsYXRlO1xufVxuXG4vLyBJbnZva2UgYmFzaWMgc3R5bGUgc2hpbW1pbmcgd2l0aCBTaGFkb3dDU1MuXG5mdW5jdGlvbiBzaGltVGVtcGxhdGVTdHlsZXModGVtcGxhdGUsIHRhZykge1xuICB3aW5kb3cuV2ViQ29tcG9uZW50cy5TaGFkb3dDU1Muc2hpbVN0eWxpbmcodGVtcGxhdGUuY29udGVudCwgdGFnKTtcbn1cbiIsIi8qKlxuICogSGVscGVyIGZ1bmN0aW9uIHRvIGNyZWF0ZSBhIHN5bWJvbCB0aGF0IGNhbiBiZSB1c2VkIGZvciBhc3NvY2lhdGluZyBwcml2YXRlXG4gKiBkYXRhIHdpdGggYW4gZWxlbWVudC5cbiAqXG4gKiBNaXhpbnMgYW5kIGNvbXBvbmVudCBjbGFzc2VzIG9mdGVuIHdhbnQgdG8gYXNzb2NpYXRlIHByaXZhdGUgZGF0YSB3aXRoIGFuXG4gKiBlbGVtZW50IGluc3RhbmNlLCBidXQgSmF2YVNjcmlwdCBkb2VzIG5vdCBoYXZlIGRpcmVjdCBzdXBwb3J0IGZvciB0cnVlXG4gKiBwcml2YXRlIHByb3BlcnRpZXMuIE9uZSBhcHByb2FjaCBpcyB0byB1c2UgdGhlXG4gKiBbU3ltYm9sXShodHRwczovL2RldmVsb3Blci5tb3ppbGxhLm9yZy9lbi1VUy9kb2NzL1dlYi9KYXZhU2NyaXB0L1JlZmVyZW5jZS9HbG9iYWxfT2JqZWN0cy9TeW1ib2wpXG4gKiBkYXRhIHR5cGUgdG8gc2V0IGFuZCByZXRyaWV2ZSBkYXRhIG9uIGFuIGVsZW1lbnQuXG4gKlxuICogVW5mb3J0dW5hdGVseSwgdGhlIFN5bWJvbCB0eXBlIGlzIG5vdCBhdmFpbGFibGUgaW4gSW50ZXJuZXQgRXhwbG9yZXIgMTEuIFRoZVxuICogYGNyZWF0ZVN5bWJvbGAgaGVscGVyIGZ1bmN0aW9uIGV4aXN0cyBhcyBhIHdvcmthcm91bmQgZm9yIElFIDExLiBSYXRoZXIgdGhhblxuICogcmV0dXJuaW5nIGEgdHJ1ZSBTeW1ib2wsIGl0IHNpbXBseSByZXR1cm5zIGFuIHVuZGVyc2NvcmUtcHJlZml4ZWQgc3RyaW5nLlxuICpcbiAqIFVzYWdlOlxuICpcbiAqICAgICBjb25zdCBmb29TeW1ib2wgPSBjcmVhdGVTeW1ib2woJ2ZvbycpO1xuICpcbiAqICAgICBjbGFzcyBNeUVsZW1lbnQgZXh0ZW5kcyBIVE1MRWxlbWVudCB7XG4gKiAgICAgICBnZXQgZm9vKCkge1xuICogICAgICAgICByZXR1cm4gdGhpc1tmb29TeW1ib2xdO1xuICogICAgICAgfVxuICogICAgICAgc2V0IGZvbyh2YWx1ZSkge1xuICogICAgICAgICB0aGlzW2Zvb1N5bWJvbF0gPSB2YWx1ZTtcbiAqICAgICAgIH1cbiAqICAgICB9XG4gKlxuICogSW4gSUUgMTEsIHRoaXMgc2FtcGxlIHdpbGwgXCJoaWRlXCIgZGF0YSBiZWhpbmQgYW4gaW5zdGFuY2UgcHJvcGVydHkgdGhpcy5fZm9vLlxuICogVGhlIHVzZSBvZiB0aGUgdW5kZXJzY29yZSBpcyBtZWFudCB0byByZWR1Y2UgKG5vdCBlbGltaW5hdGUpIHRoZSBwb3RlbnRpYWxcbiAqIGZvciBuYW1lIGNvbmZsaWN0cywgYW5kIGRpc2NvdXJhZ2UgKG5vdCBwcmV2ZW50KSBleHRlcm5hbCBhY2Nlc3MgdG8gdGhpc1xuICogZGF0YS4gSW4gbW9kZXJuIGJyb3dzZXJzLCB0aGUgYWJvdmUgY29kZSB3aWxsIGVsaW1pbmF0ZSB0aGUgcG90ZW50aWFsIG9mXG4gKiBuYW1pbmcgY29uZmxpY3RzLCBhbmQgYmV0dGVyIGhpZGUgdGhlIGRhdGEgYmVoaW5kIGEgcmVhbCBTeW1ib2wuXG4gKlxuICogQGZ1bmN0aW9uIGNyZWF0ZVN5bWJvbFxuICogQHBhcmFtIHtzdHJpbmd9IGRlc2NyaXB0aW9uIC0gQSBzdHJpbmcgdG8gaWRlbnRpZnkgdGhlIHN5bWJvbCB3aGVuIGRlYnVnZ2luZ1xuICovXG5leHBvcnQgZGVmYXVsdCBmdW5jdGlvbiBjcmVhdGVTeW1ib2woZGVzY3JpcHRpb24pIHtcbiAgcmV0dXJuIHR5cGVvZiBTeW1ib2wgPT09ICdmdW5jdGlvbicgP1xuICAgIFN5bWJvbChkZXNjcmlwdGlvbikgOlxuICAgIGBfJHtkZXNjcmlwdGlvbn1gO1xufVxuIiwiaW1wb3J0IGNyZWF0ZVN5bWJvbCBmcm9tICcuL2NyZWF0ZVN5bWJvbCc7XG5pbXBvcnQgdG9nZ2xlQ2xhc3MgZnJvbSAnLi90b2dnbGVDbGFzcyc7XG5cblxuLy8gU3ltYm9scyBmb3IgcHJpdmF0ZSBkYXRhIG1lbWJlcnMgb24gYW4gZWxlbWVudC5cbmNvbnN0IHNhZmVUb1NldEF0dHJpYnV0ZXNTeW1ib2wgPSBjcmVhdGVTeW1ib2woJ3NhZmVUb1NldEF0dHJpYnV0ZXMnKTtcbmNvbnN0IHBlbmRpbmdBdHRyaWJ1dGVzU3ltYm9sID0gY3JlYXRlU3ltYm9sKCdwZW5kaW5nQXR0cmlidXRlcycpO1xuY29uc3QgcGVuZGluZ0NsYXNzZXNTeW1ib2wgPSBjcmVhdGVTeW1ib2woJ3BlbmRpbmdDbGFzc2VzJyk7XG5cblxuLyoqXG4gKiBIZWxwZXIgZnVuY3Rpb25zIGZvciB1cGRhdGluZyBhdHRyaWJ1dGVzLCBpbmNsdWRpbmcgdGhlIGBjbGFzc2AgYXR0cmlidXRlLlxuICovXG5leHBvcnQgZGVmYXVsdCB7XG5cbiAgLyoqXG4gICAqIFBlcmZvcm0gYW55IHBlbmRpbmcgdXBkYXRlcyB0byBhdHRyaWJ1dGVzIGFuZCBjbGFzc2VzLlxuICAgKlxuICAgKiBUaGlzIHdyaXRlcyBhbnkgYHNldEF0dHJpYnV0ZWAgb3IgYHRvZ2dsZUNsYXNzYCB2YWx1ZXMgdGhhdCB3ZXJlIHBlcmZvcm1lZFxuICAgKiBiZWZvcmUgYW4gZWxlbWVudCB3YXMgYXR0YWNoZWQgdG8gdGhlIGRvY3VtZW50IGZvciB0aGUgZmlyc3QgdGltZS5cbiAgICpcbiAgICogVGhpcyBtZXRob2Qgc2hvdWxkIGJlIGNhbGxlZCBieSBtaXhpbnMvY29tcG9uZW50cyBpbiB0aGVpclxuICAgKiBgY29ubmVjdGVkQ2FsbGJhY2tgLiBJZiBtdWxpdHBsZSBtaXhpbnMvY29tcG9uZW50cyBpbnZva2UgdGhpcyBkdXJpbmcgdGhlXG4gICAqIHNhbWUgYGNvbm5lY3RlZENhbGxiYWNrYCwgb25seSB0aGUgZmlyc3QgY2FsbCB3aWxsIGhhdmUgYW55IGVmZmVjdC4gVGhlXG4gICAqIHN1YnNlcXVlbnQgY2FsbHMgd2lsbCBiZSBoYXJtbGVzcy5cbiAgICpcbiAgICogQHBhcmFtIHtIVE1MRWxlbWVudH0gZWxlbWVudCAtIFRoZSBlbGVtZW50IGJlaW5nIGFkZGVkIHRvIHRoZSBkb2N1bWVudC5cbiAgICovXG4gIGNvbm5lY3RlZChlbGVtZW50KSB7XG4gICAgZWxlbWVudFtzYWZlVG9TZXRBdHRyaWJ1dGVzU3ltYm9sXSA9IHRydWU7XG5cbiAgICAvLyBTZXQgYW55IHBlbmRpbmcgYXR0cmlidXRlcy5cbiAgICBpZiAoZWxlbWVudFtwZW5kaW5nQXR0cmlidXRlc1N5bWJvbF0pIHtcbiAgICAgIGZvciAobGV0IGF0dHJpYnV0ZSBpbiBlbGVtZW50W3BlbmRpbmdBdHRyaWJ1dGVzU3ltYm9sXSkge1xuICAgICAgICBjb25zdCB2YWx1ZSA9IGVsZW1lbnRbcGVuZGluZ0F0dHJpYnV0ZXNTeW1ib2xdW2F0dHJpYnV0ZV07XG4gICAgICAgIHNldEF0dHJpYnV0ZVRvRWxlbWVudChlbGVtZW50LCBhdHRyaWJ1dGUsIHZhbHVlKTtcbiAgICAgIH1cbiAgICAgIGVsZW1lbnRbcGVuZGluZ0F0dHJpYnV0ZXNTeW1ib2xdID0gbnVsbDtcbiAgICB9XG5cbiAgICAvLyBTZXQgYW55IHBlbmRpbmcgY2xhc3Nlcy5cbiAgICBpZiAoZWxlbWVudFtwZW5kaW5nQ2xhc3Nlc1N5bWJvbF0pIHtcbiAgICAgIGZvciAobGV0IGNsYXNzTmFtZSBpbiBlbGVtZW50W3BlbmRpbmdDbGFzc2VzU3ltYm9sXSkge1xuICAgICAgICBjb25zdCB2YWx1ZSA9IGVsZW1lbnRbcGVuZGluZ0NsYXNzZXNTeW1ib2xdW2NsYXNzTmFtZV07XG4gICAgICAgIHRvZ2dsZUNsYXNzKGVsZW1lbnQsIGNsYXNzTmFtZSwgdmFsdWUpO1xuICAgICAgfVxuICAgICAgZWxlbWVudFtwZW5kaW5nQ2xhc3Nlc1N5bWJvbF0gPSBudWxsO1xuICAgIH1cbiAgfSxcblxuICAvKipcbiAgICogU2V0L3Vuc2V0IHRoZSBhdHRyaWJ1dGUgd2l0aCB0aGUgaW5kaWNhdGVkIG5hbWUuXG4gICAqXG4gICAqIFRoaXMgbWV0aG9kIGV4aXN0cyBwcmltYXJpbHkgdG8gaGFuZGxlIHRoZSBjYXNlIHdoZXJlIGFuIGVsZW1lbnQgd2FudHMgdG9cbiAgICogc2V0IGEgZGVmYXVsdCBwcm9wZXJ0eSB2YWx1ZSB0aGF0IHNob3VsZCBiZSByZWZsZWN0ZWQgYXMgYW4gYXR0cmlidXRlLiBBblxuICAgKiBpbXBvcnRhbnQgbGltaXRhdGlvbiBvZiBjdXN0b20gZWxlbWVudCBjb25zdHVyY3RvcnMgaXMgdGhhdCB0aGV5IGNhbm5vdFxuICAgKiBzZXQgYXR0cmlidXRlcy4gQSBjYWxsIHRvIGBzZXRBdHRyaWJ1dGVgIGR1cmluZyB0aGUgY29uc3RydWN0b3Igd2lsbFxuICAgKiBiZSBkZWZlcnJlZCB1bnRpbCB0aGUgZWxlbWVudCBpcyBjb25uZWN0ZWQgdG8gdGhlIGRvY3VtZW50LlxuICAgKlxuICAgKiBAcGFyYW0ge3N0cmluZ30gYXR0cmlidXRlIC0gVGhlIG5hbWUgb2YgdGhlICphdHRyaWJ1dGUqIChub3QgcHJvcGVydHkpIHRvIHNldC5cbiAgICogQHBhcmFtIHtvYmplY3R9IHZhbHVlIC0gVGhlIHZhbHVlIHRvIHNldC4gSWYgbnVsbCwgdGhlIGF0dHJpYnV0ZSB3aWxsIGJlIHJlbW92ZWQuXG4gICAqL1xuICBzZXRBdHRyaWJ1dGUoZWxlbWVudCwgYXR0cmlidXRlLCB2YWx1ZSkge1xuICAgIGlmIChlbGVtZW50W3NhZmVUb1NldEF0dHJpYnV0ZXNTeW1ib2xdKSB7XG4gICAgICAvLyBTYWZlIHRvIHNldCBhdHRyaWJ1dGVzIGltbWVkaWF0ZWx5LlxuICAgICAgc2V0QXR0cmlidXRlVG9FbGVtZW50KGVsZW1lbnQsIGF0dHJpYnV0ZSwgdmFsdWUpO1xuICAgIH0gZWxzZSB7XG4gICAgICAvLyBEZWZlciBzZXR0aW5nIGF0dHJpYnV0ZXMgdW50aWwgdGhlIGZpcnN0IHRpbWUgd2UncmUgY29ubmVjdGVkLlxuICAgICAgaWYgKCFlbGVtZW50W3BlbmRpbmdBdHRyaWJ1dGVzU3ltYm9sXSkge1xuICAgICAgICBlbGVtZW50W3BlbmRpbmdBdHRyaWJ1dGVzU3ltYm9sXSA9IHt9O1xuICAgICAgfVxuICAgICAgZWxlbWVudFtwZW5kaW5nQXR0cmlidXRlc1N5bWJvbF1bYXR0cmlidXRlXSA9IHZhbHVlO1xuICAgIH1cbiAgfSxcblxuICAvKipcbiAgICogU2V0L3Vuc2V0IHRoZSBjbGFzcyB3aXRoIHRoZSBpbmRpY2F0ZWQgbmFtZS5cbiAgICpcbiAgICogVGhpcyBtZXRob2QgZXhpc3RzIHByaW1hcmlseSB0byBoYW5kbGUgdGhlIGNhc2Ugd2hlcmUgYW4gZWxlbWVudCB3YW50cyB0b1xuICAgKiBzZXQgYSBkZWZhdWx0IHByb3BlcnR5IHZhbHVlIHRoYXQgc2hvdWxkIGJlIHJlZmxlY3RlZCBhcyBhcyBjbGFzcy4gQW5cbiAgICogaW1wb3J0YW50IGxpbWl0YXRpb24gb2YgY3VzdG9tIGVsZW1lbnQgY29uc3R1cmN0b3JzIGlzIHRoYXQgdGhleSBjYW5ub3RcbiAgICogc2V0IGF0dHJpYnV0ZXMsIGluY2x1ZGluZyB0aGUgYGNsYXNzYCBhdHRyaWJ1dGUuIEEgY2FsbCB0b1xuICAgKiBgdG9nZ2xlQ2xhc3NgIGR1cmluZyB0aGUgY29uc3RydWN0b3Igd2lsbCBiZSBkZWZlcnJlZCB1bnRpbCB0aGUgZWxlbWVudFxuICAgKiBpcyBjb25uZWN0ZWQgdG8gdGhlIGRvY3VtZW50LlxuICAgKlxuICAgKiBAcGFyYW0ge3N0cmluZ30gY2xhc3NOYW1lIC0gVGhlIG5hbWUgb2YgdGhlIGNsYXNzIHRvIHNldC5cbiAgICogQHBhcmFtIHtvYmplY3R9IHZhbHVlIC0gVHJ1ZSB0byBzZXQgdGhlIGNsYXNzLCBmYWxzZSB0byByZW1vdmUgaXQuXG4gICAqL1xuICB0b2dnbGVDbGFzcyhlbGVtZW50LCBjbGFzc05hbWUsIHZhbHVlKSB7XG4gICAgaWYgKGVsZW1lbnRbc2FmZVRvU2V0QXR0cmlidXRlc1N5bWJvbF0pIHtcbiAgICAgIC8vIFNhZmUgdG8gc2V0IGNsYXNzIGltbWVkaWF0ZWx5LlxuICAgICAgdG9nZ2xlQ2xhc3MoZWxlbWVudCwgY2xhc3NOYW1lLCB2YWx1ZSk7XG4gICAgfSBlbHNlIHtcbiAgICAgIC8vIERlZmVyIHNldHRpbmcgY2xhc3MgdW50aWwgdGhlIGZpcnN0IHRpbWUgd2UncmUgY29ubmVjdGVkLlxuICAgICAgaWYgKCFlbGVtZW50W3BlbmRpbmdDbGFzc2VzU3ltYm9sXSkge1xuICAgICAgICBlbGVtZW50W3BlbmRpbmdDbGFzc2VzU3ltYm9sXSA9IHt9O1xuICAgICAgfVxuICAgICAgZWxlbWVudFtwZW5kaW5nQ2xhc3Nlc1N5bWJvbF1bY2xhc3NOYW1lXSA9IHZhbHVlO1xuICAgIH1cbiAgfVxuXG59O1xuXG5cbi8vIFJlZmxlY3QgdGhlIGF0dHJpYnV0ZSB0byB0aGUgZ2l2ZW4gZWxlbWVudC5cbi8vIElmIHRoZSB2YWx1ZSBpcyBudWxsLCByZW1vdmUgdGhlIGF0dHJpYnV0ZS5cbmZ1bmN0aW9uIHNldEF0dHJpYnV0ZVRvRWxlbWVudChlbGVtZW50LCBhdHRyaWJ1dGVOYW1lLCB2YWx1ZSkge1xuICBpZiAodmFsdWUgPT09IG51bGwgfHwgdHlwZW9mIHZhbHVlID09PSAndW5kZWZpbmVkJykge1xuICAgIGVsZW1lbnQucmVtb3ZlQXR0cmlidXRlKGF0dHJpYnV0ZU5hbWUpO1xuICB9IGVsc2Uge1xuICAgIGNvbnN0IHRleHQgPSBTdHJpbmcodmFsdWUpO1xuICAgIC8vIEF2b2lkIHJlY3Vyc2l2ZSBhdHRyaWJ1dGVDaGFuZ2VkQ2FsbGJhY2sgY2FsbHMuXG4gICAgaWYgKGVsZW1lbnQuZ2V0QXR0cmlidXRlKGF0dHJpYnV0ZU5hbWUpICE9PSB0ZXh0KSB7XG4gICAgICBlbGVtZW50LnNldEF0dHJpYnV0ZShhdHRyaWJ1dGVOYW1lLCB2YWx1ZSk7XG4gICAgfVxuICB9XG59XG4iLCJpbXBvcnQgY3JlYXRlU3ltYm9sIGZyb20gJy4vY3JlYXRlU3ltYm9sJztcblxuLyoqXG4gKiBBIGNvbGxlY3Rpb24gb2YgU3ltYm9sIG9iamVjdHMgZm9yIHN0YW5kYXJkIGNvbXBvbmVudCBwcm9wZXJ0aWVzIGFuZCBtZXRob2RzLlxuICpcbiAqIFRoZXNlIFN5bWJvbCBvYmplY3RzIGFyZSB1c2VkIHRvIGFsbG93IG1peGlucyBhbmQgYSBjb21wb25lbnQgdG8gaW50ZXJuYWxseVxuICogY29tbXVuaWNhdGUsIHdpdGhvdXQgZXhwb3NpbmcgdGhlc2UgcHJvcGVydGllcyBhbmQgbWV0aG9kcyBpbiB0aGUgY29tcG9uZW50J3NcbiAqIHB1YmxpYyBBUEkuXG4gKlxuICogVG8gdXNlIHRoZXNlIFN5bWJvbCBvYmplY3RzIGluIHlvdXIgb3duIGNvbXBvbmVudCwgaW5jbHVkZSB0aGlzIG1vZHVsZSBhbmRcbiAqIHRoZW4gY3JlYXRlIGEgcHJvcGVydHkgb3IgbWV0aG9kIHdob3NlIGtleSBpcyB0aGUgZGVzaXJlZCBTeW1ib2wuXG4gKlxuICogICAgIGltcG9ydCAnU2luZ2xlU2VsZWN0aW9uTWl4aW4nIGZyb20gJ2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL1NpbmdsZVNlbGVjdGlvbk1peGluJztcbiAqICAgICBpbXBvcnQgJ3N5bWJvbHMnIGZyb20gJ2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL3N5bWJvbHMnO1xuICpcbiAqICAgICBjbGFzcyBNeUVsZW1lbnQgZXh0ZW5kcyBTaW5nbGVTZWxlY3Rpb25NaXhpbihIVE1MRWxlbWVudCkge1xuICogICAgICAgW3N5bWJvbHMuaXRlbVNlbGVjdGVkXShpdGVtLCBzZWxlY3RlZCkge1xuICogICAgICAgICAvLyBUaGlzIHdpbGwgYmUgaW52b2tlZCB3aGVuZXZlciBhbiBpdGVtIGlzIHNlbGVjdGVkL2Rlc2VsZWN0ZWQuXG4gKiAgICAgICB9XG4gKiAgICAgfVxuICpcbiAqIEBtb2R1bGUgc3ltYm9sc1xuICovXG5jb25zdCBzeW1ib2xzID0ge1xuXG4gIC8qKlxuICAgKiBTeW1ib2wgZm9yIHRoZSBgZGVmYXVsdHNgIHByb3BlcnR5LlxuICAgKlxuICAgKiBUaGlzIHByb3BlcnR5IGNhbiBiZSB1c2VkIHRvIHNldCBvciBvdmVycmlkZSBkZWZhdWx0cyB0aGF0IHdpbGwgYmUgYXBwbGllZFxuICAgKiB0byBhIG5ldyBjb21wb25lbnQgaW5zdGFuY2UuIFdoZW4gaW1wbGVtZW50aW5nIHRoaXMgcHJvcGVydHksIHRha2UgY2FyZSB0b1xuICAgKiBmaXJzdCBhY3F1aXJlIGFueSBkZWZhdWx0cyBkZWZpbmVkIGJ5IHRoZSBzdXBlcmNsYXNzLiBUaGUgc3RhbmRhcmQgaWRpb20gaXNcbiAgICogYXMgZm9sbG93czpcbiAgICpcbiAgICogICAgIGdldCBbc3ltYm9scy5kZWZhdWx0c10oKSB7XG4gICAqICAgICAgIGNvbnN0IGRlZmF1bHRzID0gc3VwZXJbc3ltYm9scy5kZWZhdWx0c10gfHwge307XG4gICAqICAgICAgIC8vIFNldCBvciBvdmVycmlkZSBkZWZhdWx0IHZhbHVlcyBoZXJlXG4gICAqICAgICAgIGRlZmF1bHRzLmN1c3RvbVByb3BlcnR5ID0gZmFsc2U7XG4gICAqICAgICAgIHJldHVybiBkZWZhdWx0cztcbiAgICogICAgIH1cbiAgICpcbiAgICogQHZhciB7b2JqZWN0fSBkZWZhdWx0c1xuICAgKi9cbiAgZGVmYXVsdHM6IGNyZWF0ZVN5bWJvbCgnZGVmYXVsdHMnKSxcblxuICAvKipcbiAgICogU3ltYm9sIGZvciB0aGUgYGRyYWdnaW5nYCBwcm9wZXJ0eS5cbiAgICpcbiAgICogQ29tcG9uZW50cyBsaWtlIGNhcm91c2VscyBvZnRlbiBkZWZpbmUgYW5pbWF0ZWQgQ1NTIHRyYW5zaXRpb25zIGZvclxuICAgKiBzbGlkaW5nIGVmZmVjdHMuIFN1Y2ggYSB0cmFuc2l0aW9uIHNob3VsZCB1c3VhbGx5ICpub3QqIGJlIGFwcGxpZWQgd2hpbGVcbiAgICogdGhlIHVzZXIgaXMgZHJhZ2dpbmcsIGJlY2F1c2UgYSBDU1MgYW5pbWF0aW9uIHdpbGwgaW50cm9kdWNlIGEgbGFnIHRoYXRcbiAgICogbWFrZXMgdGhlIHN3aXBlIGZlZWwgc2x1Z2dpc2guIEluc3RlYWQsIGFzIGxvbmcgYXMgdGhlIHVzZXIgaXMgZHJhZ2dpbmdcbiAgICogd2l0aCB0aGVpciBmaW5nZXIgZG93biwgdGhlIHRyYW5zaXRpb24gc2hvdWxkIGJlIHN1cHByZXNzZWQuIFdoZW4gdGhlXG4gICAqIHVzZXIgcmVsZWFzZXMgdGhlaXIgZmluZ2VyLCB0aGUgdHJhbnNpdGlvbiBjYW4gYmUgcmVzdG9yZWQsIGFsbG93aW5nIHRoZVxuICAgKiBhbmltYXRpb24gdG8gc2hvdyB0aGUgY2Fyb3VzZWwgc2xpZGluZyBpbnRvIGl0cyBmaW5hbCBwb3NpdGlvbi5cbiAgICpcbiAgICogQHR5cGUge2Jvb2xlYW59IHRydWUgaWYgYSBkcmFnIGlzIGluIHByb2dyZXNzLCBmYWxzZSBpZiBub3QuXG4gICAqL1xuICBkcmFnZ2luZzogY3JlYXRlU3ltYm9sKCdkcmFnZ2luZycpLFxuXG4gIC8qKlxuICAgKiBTeW1ib2wgZm9yIHRoZSBgZ29Eb3duYCBtZXRob2QuXG4gICAqXG4gICAqIFRoaXMgbWV0aG9kIGlzIGludm9rZWQgd2hlbiB0aGUgdXNlciB3YW50cyB0byBnby9uYXZpZ2F0ZSBkb3duLlxuICAgKlxuICAgKiBAZnVuY3Rpb24gZ29Eb3duXG4gICAqL1xuICBnb0Rvd246IGNyZWF0ZVN5bWJvbCgnZ29Eb3duJyksXG5cbiAgLyoqXG4gICAqIFN5bWJvbCBmb3IgdGhlIGBnb0VuZGAgbWV0aG9kLlxuICAgKlxuICAgKiBUaGlzIG1ldGhvZCBpcyBpbnZva2VkIHdoZW4gdGhlIHVzZXIgd2FudHMgdG8gZ28vbmF2aWdhdGUgdG8gdGhlIGVuZCAoZS5nLixcbiAgICogb2YgYSBsaXN0KS5cbiAgICpcbiAgICogQGZ1bmN0aW9uIGdvRW5kXG4gICAqL1xuICBnb0VuZDogY3JlYXRlU3ltYm9sKCdnb0VuZCcpLFxuXG4gIC8qKlxuICAgKiBTeW1ib2wgZm9yIHRoZSBgZ29MZWZ0YCBtZXRob2QuXG4gICAqXG4gICAqIFRoaXMgbWV0aG9kIGlzIGludm9rZWQgd2hlbiB0aGUgdXNlciB3YW50cyB0byBnby9uYXZpZ2F0ZSBsZWZ0LlxuICAgKlxuICAgKiBAZnVuY3Rpb24gZ29MZWZ0XG4gICAqL1xuICBnb0xlZnQ6IGNyZWF0ZVN5bWJvbCgnZ29MZWZ0JyksXG5cbiAgLyoqXG4gICAqIFN5bWJvbCBmb3IgdGhlIGBnb1JpZ2h0YCBtZXRob2QuXG4gICAqXG4gICAqIFRoaXMgbWV0aG9kIGlzIGludm9rZWQgd2hlbiB0aGUgdXNlciB3YW50cyB0byBnby9uYXZpZ2F0ZSByaWdodC5cbiAgICpcbiAgICogQGZ1bmN0aW9uIGdvUmlnaHRcbiAgICovXG4gIGdvUmlnaHQ6IGNyZWF0ZVN5bWJvbCgnZ29SaWdodCcpLFxuXG4gIC8qKlxuICAgKiBTeW1ib2wgZm9yIHRoZSBgZ29TdGFydGAgbWV0aG9kLlxuICAgKlxuICAgKiBUaGlzIG1ldGhvZCBpcyBpbnZva2VkIHdoZW4gdGhlIHVzZXIgd2FudHMgdG8gZ28vbmF2aWdhdGUgdG8gdGhlIHN0YXJ0XG4gICAqIChlLmcuLCBvZiBhIGxpc3QpLlxuICAgKlxuICAgKiBAZnVuY3Rpb24gZ29TdGFydFxuICAgKi9cbiAgZ29TdGFydDogY3JlYXRlU3ltYm9sKCdnb1N0YXJ0JyksXG5cbiAgLyoqXG4gICAqIFN5bWJvbCBmb3IgdGhlIGBnb1VwYCBtZXRob2QuXG4gICAqXG4gICAqIFRoaXMgbWV0aG9kIGlzIGludm9rZWQgd2hlbiB0aGUgdXNlciB3YW50cyB0byBnby9uYXZpZ2F0ZSB1cC5cbiAgICpcbiAgICogQGZ1bmN0aW9uIGdvVXBcbiAgICovXG4gIGdvVXA6IGNyZWF0ZVN5bWJvbCgnZ29VcCcpLFxuXG4gIC8qKlxuICAgKiBTeW1ib2wgZm9yIHRoZSBgaXRlbUFkZGVkYCBtZXRob2QuXG4gICAqXG4gICAqIFRoaXMgbWV0aG9kIGlzIGludm9rZWQgd2hlbiBhIG5ldyBpdGVtIGlzIGFkZGVkIHRvIGEgbGlzdC5cbiAgICpcbiAgICogQGZ1bmN0aW9uIGl0ZW1BZGRlZFxuICAgKiBAcGFyYW0ge0hUTUxFbGVtZW50fSBpdGVtIC0gdGhlIGl0ZW0gYmVpbmcgc2VsZWN0ZWQvZGVzZWxlY3RlZFxuICAgKi9cbiAgaXRlbUFkZGVkOiBjcmVhdGVTeW1ib2woJ2l0ZW1BZGRlZCcpLFxuXG5cbiAgLyoqXG4gICAqIFN5bWJvbCBmb3IgdGhlIGBpdGVtc0NoYW5nZWRgIG1ldGhvZC5cbiAgICpcbiAgICogVGhpcyBtZXRob2QgaXMgaW52b2tlZCB3aGVuIHRoZSB1bmRlcmx5aW5nIGNvbnRlbnRzIGNoYW5nZS4gSXQgaXMgYWxzb1xuICAgKiBpbnZva2VkIG9uIGNvbXBvbmVudCBpbml0aWFsaXphdGlvbiDigJMgc2luY2UgdGhlIGl0ZW1zIGhhdmUgXCJjaGFuZ2VkXCIgZnJvbVxuICAgKiBiZWluZyBub3RoaW5nLlxuICAgKi9cbiAgaXRlbXNDaGFuZ2VkOiBjcmVhdGVTeW1ib2woJ2l0ZW1zQ2hhbmdlZCcpLFxuXG4gIC8qKlxuICAgKiBTeW1ib2wgZm9yIHRoZSBgaXRlbVNlbGVjdGVkYCBtZXRob2QuXG4gICAqXG4gICAqIFRoaXMgbWV0aG9kIGlzIGludm9rZWQgd2hlbiBhbiBpdGVtIGJlY29tZXMgc2VsZWN0ZWQgb3IgZGVzZWxlY3RlZC5cbiAgICpcbiAgICogQGZ1bmN0aW9uIGl0ZW1TZWxlY3RlZFxuICAgKiBAcGFyYW0ge0hUTUxFbGVtZW50fSBpdGVtIC0gdGhlIGl0ZW0gYmVpbmcgc2VsZWN0ZWQvZGVzZWxlY3RlZFxuICAgKiBAcGFyYW0ge2Jvb2xlYW59IHNlbGVjdGVkIC0gdHJ1ZSBpZiB0aGUgaXRlbSBpcyBzZWxlY3RlZCwgZmFsc2UgaWYgbm90XG4gICAqL1xuICBpdGVtU2VsZWN0ZWQ6IGNyZWF0ZVN5bWJvbCgnaXRlbVNlbGVjdGVkJyksXG5cbiAgLyoqXG4gICAqIFN5bWJvbCBmb3IgdGhlIGBrZXlkb3duYCBtZXRob2QuXG4gICAqXG4gICAqIFRoaXMgbWV0aG9kIGlzIGludm9rZWQgd2hlbiBhbiBlbGVtZW50IHJlY2VpdmVzIGEgYGtleWRvd25gIGV2ZW50LlxuICAgKlxuICAgKiBAZnVuY3Rpb24ga2V5ZG93blxuICAgKiBAcGFyYW0ge0tleWJvYXJkRXZlbnR9IGV2ZW50IC0gdGhlIGV2ZW50IGJlaW5nIHByb2Nlc3NlZFxuICAgKi9cbiAga2V5ZG93bjogY3JlYXRlU3ltYm9sKCdrZXlkb3duJyksXG5cbiAgLyoqXG4gICAqIFN5bWJvbCBmb3IgdGhlIGB0ZW1wbGF0ZWAgcHJvcGVydHkuXG4gICAqXG4gICAqIFRoaXMgcHJvcGVydHkgcmV0dXJucyBhIGNvbXBvbmVudCdzIHRlbXBsYXRlLlxuICAgKlxuICAgKiBAdHlwZSB7c3RyaW5nfEhUTUxFbGVtZW50fVxuICAgKi9cbiAgdGVtcGxhdGU6IGNyZWF0ZVN5bWJvbCgndGVtcGxhdGUnKVxufTtcblxuZXhwb3J0IGRlZmF1bHQgc3ltYm9scztcbiIsIi8qKlxuICogSGVscGVyIGZ1bmN0aW9uIGZvciBzdGFuZGFyZCBjbGFzc0xpc3QudG9nZ2xlKCkgYmVoYXZpb3Igb24gb2xkIGJyb3dzZXJzLFxuICogbmFtZWx5IElFIDExLlxuICpcbiAqIFRoZSBzdGFuZGFyZFxuICogW2NsYXNzbGlzdF0oaHR0cHM6Ly9kZXZlbG9wZXIubW96aWxsYS5vcmcvZW4tVVMvZG9jcy9XZWIvQVBJL0VsZW1lbnQvY2xhc3NMaXN0KVxuICogb2JqZWN0IGhhcyBhIGB0b2dnbGUoKWAgZnVuY3Rpb24gdGhhdCBzdXBwb3J0cyBhIHNlY29uZCBCb29sZWFuIHBhcmFtZXRlclxuICogdGhhdCBjYW4gYmUgdXNlZCB0byBzdWNjaW5jdGx5IHR1cm4gYSBjbGFzcyBvbiBvciBvZmYuIFRoaXMgZmVhdHVyZSBpcyBvZnRlblxuICogdXNlZnVsIGluIGRlc2lnbmluZyBjdXN0b20gZWxlbWVudHMsIHdoaWNoIG1heSB3YW50IHRvIGV4dGVybmFsbHkgcmVmbGVjdFxuICogY29tcG9uZW50IHN0YXRlIGluIGEgQ1NTIGNsYXNzIHRoYXQgY2FuIGJlIHVzZWQgZm9yIHN0eWxpbmcgcHVycG9zZXMuXG4gKlxuICogVW5mb3J0dW5hdGVseSwgSUUgMTEgZG9lcyBub3Qgc3VwcG9ydCB0aGUgQm9vbGVhbiBwYXJhbWV0ZXIgdG9cbiAqIGBjbGFzc0xpc3QudG9nZ2xlKClgLiBUaGlzIGhlbHBlciBmdW5jdGlvbiBiZWhhdmVzIGxpa2UgdGhlIHN0YW5kYXJkXG4gKiBgdG9nZ2xlKClgLCBpbmNsdWRpbmcgc3VwcG9ydCBmb3IgdGhlIEJvb2xlYW4gcGFyYW1ldGVyLCBzbyB0aGF0IGl0IGNhbiBiZVxuICogdXNlZCBldmVuIG9uIElFIDExLlxuICpcbiAqIEBmdW5jdGlvbiB0b2dnbGVDbGFzc1xuICogQHBhcmFtIHtIVE1MRWxlbWVudH0gZWxlbWVudCAtIFRoZSBlbGVtZW50IHRvIG1vZGlmeVxuICogQHBhcmFtIHtzdHJpbmd9IGNsYXNzTmFtZSAtIFRoZSBjbGFzcyB0byBhZGQvcmVtb3ZlXG4gKiBAcGFyYW0ge2Jvb2xlYW59IFtmb3JjZV0gLSBGb3JjZSB0aGUgY2xhc3MgdG8gYmUgYWRkZWQgKGlmIHRydWUpIG9yIHJlbW92ZWRcbiAqICAgICAgICAgICAgICAgICAgICAgICAgICAgIChpZiBmYWxzZSlcbiAqL1xuZXhwb3J0IGRlZmF1bHQgZnVuY3Rpb24gdG9nZ2xlQ2xhc3MoZWxlbWVudCwgY2xhc3NOYW1lLCBmb3JjZSkge1xuICBjb25zdCBjbGFzc0xpc3QgPSBlbGVtZW50LmNsYXNzTGlzdDtcbiAgY29uc3QgYWRkQ2xhc3MgPSAodHlwZW9mIGZvcmNlID09PSAndW5kZWZpbmVkJykgP1xuICAgICFjbGFzc0xpc3QuY29udGFpbnMoY2xhc3NOYW1lKSA6XG4gICAgZm9yY2U7XG4gIGlmIChhZGRDbGFzcykge1xuICAgIGNsYXNzTGlzdC5hZGQoY2xhc3NOYW1lKTtcbiAgfSBlbHNlIHtcbiAgICBjbGFzc0xpc3QucmVtb3ZlKGNsYXNzTmFtZSk7XG4gIH1cbiAgcmV0dXJuIGFkZENsYXNzO1xufVxuIiwiLypcbiAqIFRoaXMgZmlsZSBpcyB0cmFuc3BpbGVkIHRvIGNyZWF0ZSBhbiBFUzUtY29tcGF0aWJsZSBkaXN0cmlidXRpb24gaW4gd2hpY2hcbiAqIHRoZSBwYWNrYWdlJ3MgbWFpbiBmZWF0dXJlKHMpIGFyZSBhdmFpbGFibGUgdmlhIHRoZSB3aW5kb3cuQmFzaWMgZ2xvYmFsLlxuICogSWYgeW91J3JlIGFscmVhZHkgdXNpbmcgRVM2IHlvdXJzZWxmLCBpZ25vcmUgdGhpcyBmaWxlLCBhbmQgaW5zdGVhZCBpbXBvcnRcbiAqIHRoZSBzb3VyY2UgZmlsZShzKSB5b3Ugd2FudCBmcm9tIHRoZSBzcmMgZm9sZGVyLlxuICovXG5cbmltcG9ydCBFbGVtZW50QmFzZSBmcm9tICcuL3NyYy9FbGVtZW50QmFzZSc7XG5cbndpbmRvdy5CYXNpYyA9IHdpbmRvdy5CYXNpYyB8fCB7fTtcbndpbmRvdy5CYXNpYy5FbGVtZW50QmFzZSA9IEVsZW1lbnRCYXNlO1xuIiwiaW1wb3J0IEF0dHJpYnV0ZU1hcnNoYWxsaW5nTWl4aW4gZnJvbSAnLi4vLi4vYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvQXR0cmlidXRlTWFyc2hhbGxpbmdNaXhpbic7XG5pbXBvcnQgQ29tcG9zYWJsZU1peGluIGZyb20gJy4uLy4uL2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL0NvbXBvc2FibGVNaXhpbic7XG5pbXBvcnQgRGlzdHJpYnV0ZWRDaGlsZHJlbk1peGluIGZyb20gJy4uLy4uL2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL0Rpc3RyaWJ1dGVkQ2hpbGRyZW5NaXhpbic7XG5pbXBvcnQgU2hhZG93RWxlbWVudFJlZmVyZW5jZXNNaXhpbiBmcm9tICcuLi8uLi9iYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy9TaGFkb3dFbGVtZW50UmVmZXJlbmNlc01peGluJztcbmltcG9ydCBTaGFkb3dUZW1wbGF0ZU1peGluIGZyb20gJy4uLy4uL2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL1NoYWRvd1RlbXBsYXRlTWl4aW4nO1xuXG5cbi8qKlxuICogQSBzYW1wbGUgZ2VuZXJhbC1wdXJwb3NlIGJhc2UgY2xhc3MgZm9yIGRlZmluaW5nIGN1c3RvbSBlbGVtZW50cyB0aGF0IG1peGVzXG4gKiBpbiBzb21lIGNvbW1vbiBmZWF0dXJlczogdGVtcGxhdGUgc3RhbXBpbmcgaW50byBhIHNoYWRvdyByb290LCBzaGFkb3cgZWxlbWVudFxuICogcmVmZXJlbmNlcywgbWFyc2hhbGxpbmcgYXR0cmlidXRlcyB0byBwcm9wZXJ0aWVzLCBhbmQgcmV0cmlldmluZyB0aGUgY2hpbGRyZW5cbiAqIGRpc3RyaWJ1dGVkIHRvIGEgY29tcG9uZW50LlxuICpcbiAqIFRoaXMgYmFzZSBjbGFzcyBpcyBub3Qgc3BlY2lhbCBpbiBhbnkgd2F5LCBhbmQgaXMgZGVmaW5lZCBvbmx5IGFzIGFcbiAqIGNvbnZlbmllbnQgc2hvcnRoYW5kIGZvciBhcHBseWluZyB0aGUgbWl4aW5zIGxpc3RlZCBhYm92ZS4gWW91IGNhbiB1c2UgdGhpc1xuICogY2xhc3MgYXMgYSBiYXNlIGNsYXNzIGZvciB5b3VyIG93biBlbGVtZW50cywgb3IgZWFzaWx5IGNyZWF0ZSB5b3VyIG93biBiYXNlXG4gKiBjbGFzcyBieSBhcHBseWluZyB0aGUgc2FtZSBzZXQgb2YgbWl4aW5zLlxuICpcbiAqIFRoZSBFbGVtZW50QmFzZSBiYXNlIGNsYXNzIGRvZXMgbm90IHJlZ2lzdGVyIGl0c2VsZiBhcyBhIGN1c3RvbSBlbGVtZW50IHdpdGhcbiAqIHRoZSBicm93c2VyLCBhbmQgaGVuY2UgY2Fubm90IGJlIGluZGVwZW5kZW50bHkgaW5zdGFudGlhdGVkLlxuICpcbiAqIEBtaXhlcyBBdHRyaWJ1dGVNYXJzaGFsbGluZ01peGluXG4gKiBAbWl4ZXMgQ29tcG9zYWJsZU1peGluXG4gKiBAbWl4ZXMgRGlzdHJpYnV0ZWRDaGlsZHJlbk1peGluXG4gKiBAbWl4ZXMgU2hhZG93RWxlbWVudFJlZmVyZW5jZXNNaXhpblxuICogQG1peGVzIFNoYWRvd1RlbXBsYXRlTWl4aW5cbiAqL1xuY2xhc3MgRWxlbWVudEJhc2UgZXh0ZW5kcyBDb21wb3NhYmxlTWl4aW4oSFRNTEVsZW1lbnQpLmNvbXBvc2UoXG4gIFNoYWRvd1RlbXBsYXRlTWl4aW4sICAgICAgICAgIC8vIGJlZm9yZSBub2RlIGZpbmRpbmcsIHNvIHNoYWRvdyByb290IGlzIHBvcHVsYXRlZFxuICBTaGFkb3dFbGVtZW50UmVmZXJlbmNlc01peGluLCAvLyBiZWZvcmUgbWFyc2hhbGxpbmcsIHNvIHByb3BlcnRpZXMgY2FuIHVzZSByZWZzXG4gIEF0dHJpYnV0ZU1hcnNoYWxsaW5nTWl4aW4sXG4gIERpc3RyaWJ1dGVkQ2hpbGRyZW5NaXhpblxuKSB7fVxuXG5leHBvcnQgZGVmYXVsdCBFbGVtZW50QmFzZTtcbiJdfQ==
+!function e(t,n,r){function o(u,c){if(!n[u]){if(!t[u]){var a="function"==typeof require&&require;if(!c&&a)return a(u,!0);if(i)return i(u,!0);var f=new Error("Cannot find module '"+u+"'");throw f.code="MODULE_NOT_FOUND",f}var l=n[u]={exports:{}};t[u][0].call(l.exports,function(e){var n=t[u][1][e];return o(n?n:e)},l,l.exports,e,t,n,r)}return n[u].exports}for(var i="function"==typeof require&&require,u=0;u2&&void 0!==arguments[2]?arguments[2]:[];return Object.getOwnPropertyNames(e).forEach(function(r){if(n.indexOf(r)<0){var o=Object.getOwnPropertyDescriptor(e,r);Object.defineProperty(t,r,o)}}),t}Object.defineProperty(n,"__esModule",{value:!0});var a=function(){function e(e,t){for(var n=0;n0;)t.content.appendChild(n.childNodes[0]);return t}function a(e,t){window.WebComponents.ShadowCSS.shimStyling(e.content,t)}Object.defineProperty(n,"__esModule",{value:!0});var f=e("../src/symbols"),l=r(f);n.default=function(e){var t=function(e){function t(){o(this,t);var e=i(this,(t.__proto__||Object.getPrototypeOf(t)).call(this)),n=e[l.default.template];if(n){"string"==typeof n&&(n=c(n)),window.ShadowDOMPolyfill&&a(n,e.localName);var r=e.attachShadow({mode:"open"}),u=document.importNode(n.content,!0);r.appendChild(u)}return e}return u(t,e),t}(e);return t}},{"../src/symbols":8}],6:[function(e,t,n){"use strict";function r(e){return"function"==typeof Symbol?Symbol(e):"_"+e}Object.defineProperty(n,"__esModule",{value:!0}),n.default=r},{}],7:[function(e,t,n){"use strict";function r(e){return e&&e.__esModule?e:{default:e}}function o(e,t,n){if(null===n||"undefined"==typeof n)e.removeAttribute(t);else{var r=String(n);e.getAttribute(t)!==r&&e.setAttribute(t,n)}}Object.defineProperty(n,"__esModule",{value:!0});var i=e("./createSymbol"),u=r(i),c=e("./toggleClass"),a=r(c),f=(0,u.default)("safeToSetAttributes"),l=(0,u.default)("pendingAttributes"),s=(0,u.default)("pendingClasses");n.default={connected:function(e){if(e[f]=!0,e[l]){for(var t in e[l]){var n=e[l][t];o(e,t,n)}e[l]=null}if(e[s]){for(var r in e[s]){var i=e[s][r];(0,a.default)(e,r,i)}e[s]=null}},setAttribute:function(e,t,n){e[f]?o(e,t,n):(e[l]||(e[l]={}),e[l][t]=n)},toggleClass:function(e,t,n){e[f]?(0,a.default)(e,t,n):(e[s]||(e[s]={}),e[s][t]=n)}}},{"./createSymbol":6,"./toggleClass":9}],8:[function(e,t,n){"use strict";function r(e){return e&&e.__esModule?e:{default:e}}Object.defineProperty(n,"__esModule",{value:!0});var o=e("./createSymbol"),i=r(o),u={defaults:(0,i.default)("defaults"),dragging:(0,i.default)("dragging"),goDown:(0,i.default)("goDown"),goEnd:(0,i.default)("goEnd"),goLeft:(0,i.default)("goLeft"),goRight:(0,i.default)("goRight"),goStart:(0,i.default)("goStart"),goUp:(0,i.default)("goUp"),itemAdded:(0,i.default)("itemAdded"),itemsChanged:(0,i.default)("itemsChanged"),itemSelected:(0,i.default)("itemSelected"),keydown:(0,i.default)("keydown"),template:(0,i.default)("template")};n.default=u},{"./createSymbol":6}],9:[function(e,t,n){"use strict";function r(e,t,n){var r=e.classList,o="undefined"==typeof n?!r.contains(t):n;return o?r.add(t):r.remove(t),o}Object.defineProperty(n,"__esModule",{value:!0}),n.default=r},{}],10:[function(e,t,n){"use strict";function r(e){return e&&e.__esModule?e:{default:e}}var o=e("./src/ElementBase"),i=r(o);window.Basic=window.Basic||{},window.Basic.ElementBase=i.default},{"./src/ElementBase":11}],11:[function(e,t,n){"use strict";function r(e){return e&&e.__esModule?e:{default:e}}function o(e,t){if(!(e instanceof t))throw new TypeError("Cannot call a class as a function")}function i(e,t){if(!e)throw new ReferenceError("this hasn't been initialised - super() hasn't been called");return!t||"object"!=typeof t&&"function"!=typeof t?e:t}function u(e,t){if("function"!=typeof t&&null!==t)throw new TypeError("Super expression must either be null or a function, not "+typeof t);e.prototype=Object.create(t&&t.prototype,{constructor:{value:e,enumerable:!1,writable:!0,configurable:!0}}),t&&(Object.setPrototypeOf?Object.setPrototypeOf(e,t):e.__proto__=t)}Object.defineProperty(n,"__esModule",{value:!0});var c=e("../../basic-component-mixins/src/AttributeMarshallingMixin"),a=r(c),f=e("../../basic-component-mixins/src/ComposableMixin"),l=r(f),s=e("../../basic-component-mixins/src/DistributedChildrenMixin"),p=r(s),d=e("../../basic-component-mixins/src/ShadowElementReferencesMixin"),b=r(d),y=e("../../basic-component-mixins/src/ShadowTemplateMixin"),h=r(y),_=function(e){function t(){return o(this,t),i(this,(t.__proto__||Object.getPrototypeOf(t)).apply(this,arguments))}return u(t,e),t}((0,l.default)(HTMLElement).compose(h.default,b.default,a.default,p.default));n.default=_},{"../../basic-component-mixins/src/AttributeMarshallingMixin":1,"../../basic-component-mixins/src/ComposableMixin":2,"../../basic-component-mixins/src/DistributedChildrenMixin":3,"../../basic-component-mixins/src/ShadowElementReferencesMixin":4,"../../basic-component-mixins/src/ShadowTemplateMixin":5}]},{},[10]);
+//# sourceMappingURL=basic-element-base.js.map
diff --git a/packages/basic-element-base/dist/basic-element-base.js.map b/packages/basic-element-base/dist/basic-element-base.js.map
new file mode 100644
index 00000000..70e35a54
--- /dev/null
+++ b/packages/basic-element-base/dist/basic-element-base.js.map
@@ -0,0 +1 @@
+{"version":3,"sources":["node_modules/browser-pack/_prelude.js","packages/basic-component-mixins/src/AttributeMarshallingMixin.js","packages/basic-component-mixins/src/ComposableMixin.js","packages/basic-component-mixins/src/DistributedChildrenMixin.js","packages/basic-component-mixins/src/ShadowElementReferencesMixin.js","packages/basic-component-mixins/src/ShadowTemplateMixin.js","packages/basic-component-mixins/src/createSymbol.js","packages/basic-component-mixins/src/safeAttributes.js","packages/basic-component-mixins/src/symbols.js","packages/basic-component-mixins/src/toggleClass.js","packages/basic-element-base/globals.js","packages/basic-element-base/src/ElementBase.js"],"names":["e","t","n","r","s","o","u","a","require","i","f","Error","code","l","exports","call","length","1","module","attributeToPropertyName","attributeName","propertyName","attributeToPropertyNames","hypenRegEx","replace","match","toUpperCase","attributesForClass","classFn","HTMLElement","Object","baseClass","getPrototypeOf","prototype","constructor","baseAttributes","propertyNames","getOwnPropertyNames","setterNames","filter","getOwnPropertyDescriptor","set","attributes","map","setterName","propertyNameToAttribute","diff","attribute","indexOf","concat","propertyNamesToAttributes","uppercaseRegEx","toLowerCase","_safeAttributes","base","AttributeMarshalling","_base","_classCallCheck","this","_possibleConstructorReturn","__proto__","apply","arguments","_inherits","_createClass","key","value","oldValue","newValue","_get","_safeAttributes2","default","connected","setAttribute","className","toggleClass","get","composeClass","mixin","Subclass","_base2","copyOwnProperties","NON_MIXABLE_OBJECT_PROPERTIES","source","target","ignorePropertyNames","undefined","forEach","name","descriptor","defineProperty","Composable","_len","mixins","Array","_key","reduce","expandContentElements","nodes","includeTextNodes","_ref","expanded","node","isSlot","HTMLSlotElement","localName","assignedNodes","flatten","Text","flattened","_toConsumableArray","DistributedChildren","children","childNodes","strings","distributedChildNodes","child","textContent","join","ShadowElementReferences","_this","shadowRoot","$","nodesWithIds","querySelectorAll","id","getAttribute","createTemplateWithInnerHTML","innerHTML","template","document","createElement","div","content","appendChild","shimTemplateStyles","tag","window","WebComponents","ShadowCSS","shimStyling","_symbols","ShadowTemplate","_symbols2","ShadowDOMPolyfill","root","attachShadow","mode","clone","importNode","createSymbol","description","Symbol","setAttributeToElement","element","removeAttribute","text","String","_createSymbol","_toggleClass2","safeToSetAttributesSymbol","_createSymbol2","pendingAttributesSymbol","pendingClassesSymbol","_value","_toggleClass3","symbols","defaults","dragging","goDown","goEnd","goLeft","goRight","goStart","goUp","itemAdded","itemsChanged","itemSelected","keydown","force","classList","addClass","contains","add","remove","_ElementBase","Basic","ElementBase","_ElementBase2","_AttributeMarshallingMixin","_ComposableMixin","_DistributedChildrenMixin","_ShadowElementReferencesMixin","_ShadowTemplateMixin","_ComposableMixin2","compose","_ShadowTemplateMixin2","_ShadowElementReferencesMixin2","_AttributeMarshallingMixin2","_DistributedChildrenMixin2"],"mappings":"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","file":"basic-element-base.js","sourcesContent":["(function e(t,n,r){function s(o,u){if(!n[o]){if(!t[o]){var a=typeof require==\"function\"&&require;if(!u&&a)return a(o,!0);if(i)return i(o,!0);var f=new Error(\"Cannot find module '\"+o+\"'\");throw f.code=\"MODULE_NOT_FOUND\",f}var l=n[o]={exports:{}};t[o][0].call(l.exports,function(e){var n=t[o][1][e];return s(n?n:e)},l,l.exports,e,t,n,r)}return n[o].exports}var i=typeof require==\"function\"&&require;for(var o=0;o {\n\n /**\n * Mixin which marshalls attributes to properties and vice versa.\n *\n * If your component exposes a setter for a property, it's generally a good\n * idea to let devs using your component be able to set that property in HTML\n * via an element attribute. You can code that yourself by writing an\n * `attributeChangedCallback`, or you can use this mixin to get a degree of\n * automatic support.\n *\n * This mixin implements an `attributeChangedCallback` that will attempt to\n * convert a change in an element attribute into a call to the corresponding\n * property setter. Attributes typically follow hyphenated names (\"foo-bar\"),\n * whereas properties typically use camelCase names (\"fooBar\"). This mixin\n * respects that convention, automatically mapping the hyphenated attribute\n * name to the corresponding camelCase property name.\n *\n * Example: You define a component using this mixin:\n *\n * class MyElement extends AttributeMarshallingMixin(HTMLElement) {\n * get fooBar() { return this._fooBar; }\n * set fooBar(value) { this._fooBar = value; }\n * }\n * customElements.define('my-element', MyElement);\n *\n * If someone then instantiates your component in HTML:\n *\n * \n *\n * Then, after the element has been upgraded, the `fooBar` setter will\n * automatically be invoked with the initial value \"Hello\".\n *\n * For the time being, this mixin only supports string-valued properties.\n * If you'd like to convert string attributes to other types (numbers,\n * booleans), you need to implement `attributeChangedCallback` yourself.\n */\n class AttributeMarshalling extends base {\n\n /*\n * Handle a change to the attribute with the given name.\n */\n attributeChangedCallback(attributeName, oldValue, newValue) {\n if (super.attributeChangedCallback) { super.attributeChangedCallback(); }\n const propertyName = attributeToPropertyName(attributeName);\n // If the attribute name corresponds to a property name, set the property.\n // Ignore standard HTMLElement properties handled by the DOM.\n if (propertyName in this && !(propertyName in HTMLElement.prototype)) {\n this[propertyName] = newValue;\n }\n }\n\n connectedCallback() {\n if (super.connectedCallback) { super.connectedCallback(); }\n safeAttributes.connected(this);\n }\n\n static get observedAttributes() {\n return attributesForClass(this);\n }\n\n /**\n * Set/unset the attribute with the indicated name.\n *\n * This method exists primarily to handle the case where an element wants to\n * set a default property value that should be reflected as an attribute. An\n * important limitation of custom element consturctors is that they cannot\n * set attributes. A call to `reflectAttribute` during the constructor will\n * be deferred until the element is connected to the document.\n *\n * @param {string} attribute - The name of the *attribute* (not property) to set.\n * @param {object} value - The value to set. If null, the attribute will be removed.\n */\n reflectAttribute(attribute, value) {\n return safeAttributes.setAttribute(this, attribute, value);\n }\n\n /**\n * Set/unset the class with the indicated name.\n *\n * This method exists primarily to handle the case where an element wants to\n * set a default property value that should be reflected as as class. An\n * important limitation of custom element consturctors is that they cannot\n * set attributes, including the `class` attribute. A call to\n * `reflectClass` during the constructor will be deferred until the element\n * is connected to the document.\n *\n * @param {string} className - The name of the class to set.\n * @param {object} value - True to set the class, false to remove it.\n */\n reflectClass(className, value) {\n return safeAttributes.toggleClass(this, className, value);\n }\n\n }\n\n return AttributeMarshalling;\n};\n\n\n// Convert hyphenated foo-bar attribute name to camel case fooBar property name.\nfunction attributeToPropertyName(attributeName) {\n let propertyName = attributeToPropertyNames[attributeName];\n if (!propertyName) {\n // Convert and memoize.\n const hypenRegEx = /-([a-z])/g;\n propertyName = attributeName.replace(hypenRegEx,\n match => match[1].toUpperCase());\n attributeToPropertyNames[attributeName] = propertyName;\n }\n return propertyName;\n}\n\nfunction attributesForClass(classFn) {\n\n // We treat the element base classes as if they have no attributes, since we\n // don't want to receive attributeChangedCallback for them.\n if (classFn === HTMLElement || classFn === Object) {\n return [];\n }\n\n // Get attributes for parent class.\n const baseClass = Object.getPrototypeOf(classFn.prototype).constructor;\n const baseAttributes = attributesForClass(baseClass);\n\n // Get attributes for this class.\n const propertyNames = Object.getOwnPropertyNames(classFn.prototype);\n const setterNames = propertyNames.filter(propertyName =>\n typeof Object.getOwnPropertyDescriptor(\n classFn.prototype, propertyName).set === 'function');\n const attributes = setterNames.map(setterName =>\n propertyNameToAttribute(setterName));\n\n // Merge.\n const diff = attributes.filter(attribute =>\n baseAttributes.indexOf(attribute) < 0);\n return baseAttributes.concat(diff);\n}\n\n// Convert a camel case fooBar property name to a hyphenated foo-bar attribute.\nfunction propertyNameToAttribute(propertyName) {\n let attribute = propertyNamesToAttributes[propertyName];\n if (!attribute) {\n // Convert and memoize.\n const uppercaseRegEx = /([A-Z])/g;\n attribute = propertyName.replace(uppercaseRegEx, '-$1').toLowerCase();\n }\n return attribute;\n}\n","/* Exported function extends a base class with Composable. */\nexport default (base) => {\n\n /**\n * Mixin to make a class more easily composable with other mixins.\n *\n * This mixin contributes a `compose` method that applies a set of mixin\n * functions and returns the resulting new class. This sugar can make the\n * application of many mixins at once easier to read.\n */\n class Composable extends base {\n\n /**\n * Apply a set of mixin functions or mixin objects to the present class and\n * return the new class.\n *\n * Instead of writing:\n *\n * let MyClass = Mixin1(Mixin2(Mixin3(Mixin4(Mixin5(BaseClass)))));\n *\n * You can write:\n *\n * let MyClass = ComposableMixin(BaseClass).compose(\n * Mixin1,\n * Mixin2,\n * Mixin3,\n * Mixin4,\n * Mixin5\n * );\n *\n * This function can also take mixin objects. A mixin object is just a\n * shorthand for a mixin function that creates a new subclass with the given\n * members. The mixin object's members are *not* copied directly onto the\n * prototype of the base class, as with traditional mixins.\n *\n * In addition to providing syntactic sugar, this mixin can be used to\n * define a class in ES5, which lacks ES6's `class` keyword.\n *\n * @param {...mixins} mixins - A set of mixin functions or objects to apply.\n */\n static compose(...mixins) {\n // We create a new subclass for each mixin in turn. The result becomes\n // the base class extended by any subsequent mixins. It turns out that\n // we can use Array.reduce() to concisely express this, using the current\n // object as the seed for reduce().\n return mixins.reduce(composeClass, this);\n }\n\n }\n\n return Composable;\n};\n\n\n// Properties defined by Object that we don't want to mixin.\nconst NON_MIXABLE_OBJECT_PROPERTIES = [\n 'constructor'\n];\n\n/*\n * Apply the mixin to the given base class to return a new class.\n * The mixin can either be a function that returns the modified class, or a\n * plain object whose members will be copied to the new class' prototype.\n */\nfunction composeClass(base, mixin) {\n if (typeof mixin === 'function') {\n // Mixin function\n return mixin(base);\n } else {\n // Mixin object\n class Subclass extends base {}\n copyOwnProperties(mixin, Subclass.prototype, NON_MIXABLE_OBJECT_PROPERTIES);\n return Subclass;\n }\n}\n\n\n/*\n * Copy the given properties/methods to the target.\n * Return the updated target.\n */\nfunction copyOwnProperties(source, target, ignorePropertyNames = []) {\n Object.getOwnPropertyNames(source).forEach(name => {\n if (ignorePropertyNames.indexOf(name) < 0) {\n const descriptor = Object.getOwnPropertyDescriptor(source, name);\n Object.defineProperty(target, name, descriptor);\n }\n });\n return target;\n}\n","/* Exported function extends a base class with DistributedChildren. */\nexport default (base) => {\n\n /**\n * Mixin which defines helpers for accessing a component's distributed\n * children as a flattened array or string.\n *\n * The standard DOM API provides several ways of accessing child content:\n * `children`, `childNodes`, and `textContent`. None of these functions are\n * Shadow DOM aware. This mixin defines variations of those functions that\n * *are* Shadow DOM aware.\n *\n * Example: you create a component `` that displays a number\n * equal to the number of children placed inside that component. If someone\n * instantiates your component like:\n *\n * \n *
\n *
\n *
\n * \n *\n * Then the component should show \"3\", because there are three children. To\n * calculate the number of children, the component can just calculate\n * `this.children.length`. However, suppose someone instantiates your\n * component inside one of their own components, and puts a `` element\n * inside your component:\n *\n * \n * \n * \n *\n * If your component only looks at `this.children`, it will always see exactly\n * one child — the `` element. But the user looking at the page will\n * *see* any nodes distributed to that slot. To match what the user sees, your\n * component should expand any `` elements it contains.\n *\n * That is the problem this mixin solves. After applying this mixin, your\n * component code has access to `this.distributedChildren`, whose `length`\n * will return the total number of all children distributed to your component\n * in the composed tree.\n *\n * Note: The latest Custom Elements API design calls for a new function,\n * `getAssignedNodes` that takes an optional `deep` parameter, that will solve\n * this problem at the API level.\n */\n class DistributedChildren extends base {\n\n /**\n * An in-order collection of distributed children, expanding any slot\n * elements. Like the standard children property, this skips text nodes.\n *\n * @type {HTMLElement[]}\n */\n get distributedChildren() {\n return expandContentElements(this.children, false);\n }\n\n /**\n * An in-order collection of distributed child nodes, expanding any slot\n * elements. Like the standard childNodes property, this includes text\n * nodes.\n *\n * @type {Node[]}\n */\n get distributedChildNodes() {\n return expandContentElements(this.childNodes, true);\n }\n\n /**\n * The concatenated text content of all distributed child nodes, expanding\n * any slot elements.\n *\n * @type {string}\n */\n get distributedTextContent() {\n const strings = this.distributedChildNodes.map(function(child) {\n return child.textContent;\n });\n return strings.join('');\n }\n\n }\n\n return DistributedChildren;\n};\n\n\n/*\n * Given a array of nodes, return a new array with any content elements expanded\n * to the nodes distributed to that content element. This rule is applied\n * recursively.\n *\n * If includeTextNodes is true, text nodes will be included, as in the\n * standard childNodes property; by default, this skips text nodes, like the\n * standard children property.\n */\nfunction expandContentElements(nodes, includeTextNodes) {\n const expanded = Array.prototype.map.call(nodes, node => {\n // We want to see if the node is an instanceof HTMLSlotELement, but\n // that class won't exist if the browser that doesn't support native\n // Shadow DOM and if the Shadow DOM polyfill hasn't been loaded. Instead,\n // we do a simplistic check to see if the tag name is \"slot\".\n const isSlot = typeof HTMLSlotElement !== 'undefined' ?\n node instanceof HTMLSlotElement :\n node.localName === 'slot';\n if (isSlot) {\n // Use the nodes assigned to this node instead.\n const assignedNodes = node.assignedNodes({ flatten: true });\n return assignedNodes ?\n expandContentElements(assignedNodes, includeTextNodes) :\n [];\n } else if (node instanceof HTMLElement) {\n // Plain element; use as is.\n return [node];\n } else if (node instanceof Text && includeTextNodes) {\n // Text node.\n return [node];\n } else {\n // Comment, processing instruction, etc.; skip.\n return [];\n }\n });\n const flattened = [].concat(...expanded);\n return flattened;\n}\n","/* Exported function extends a base class with ShadowElementReferences. */\nexport default (base) => {\n\n /**\n * Mixin to create references to elements in a component's Shadow DOM subtree.\n *\n * This adds a member on the component called `this.$` that can be used to\n * reference shadow elements with IDs. E.g., if component's shadow contains an\n * element ``, then this mixin will create a member\n * `this.$.foo` that points to that button.\n *\n * Such references simplify a component's access to its own elements. In\n * exchange, this mixin trades off a one-time cost of querying all elements in\n * the shadow tree instead of paying an ongoing cost to query for an element\n * each time the component wants to inspect or manipulate it.\n *\n * This mixin expects the component to define a Shadow DOM subtree. You can\n * create that tree yourself, or make use of\n * [ShadowTemplateMixin](ShadowTemplateMixin.md).\n *\n * This mixin is inspired by Polymer's [automatic\n * node finding](https://www.polymer-project.org/1.0/docs/devguide/local-dom.html#node-finding)\n * feature.\n */\n class ShadowElementReferences extends base {\n\n constructor() {\n super();\n if (this.shadowRoot) {\n // Look for elements in the shadow subtree that have id attributes.\n // An alternatively implementation of this mixin would be to just define\n // a this.$ getter that lazily does this search the first time someone\n // tries to access this.$. That might introduce some complexity – if the\n // the tree changed after it was first populated, the result of\n // searching for a node might be somewhat unpredictable.\n this.$ = {};\n const nodesWithIds = this.shadowRoot.querySelectorAll('[id]');\n [].forEach.call(nodesWithIds, node => {\n const id = node.getAttribute('id');\n this.$[id] = node;\n });\n }\n }\n\n /**\n * The collection of references to the elements with IDs in a component's\n * Shadow DOM subtree.\n *\n * @type {object}\n * @member $\n */\n }\n\n return ShadowElementReferences;\n};\n","import symbols from '../src/symbols';\n\n\n/* Exported function extends a base class with ShadowTemplate. */\nexport default (base) => {\n\n /**\n * Mixin for stamping a template into a Shadow DOM subtree upon component\n * instantiation.\n *\n * To use this mixin, define a `template` property as a string or HTML\n * `` element:\n *\n * class MyElement extends ShadowTemplateMixin(HTMLElement) {\n * get [symbols.template]() {\n * return `Hello, world .`;\n * }\n * }\n *\n * When your component class is instantiated, a shadow root will be created on\n * the instance, and the contents of the template will be cloned into the\n * shadow root. If your component does not define a `template` property, this\n * mixin has no effect.\n *\n * For the time being, this extension retains support for Shadow DOM v0. That\n * will eventually be deprecated as browsers (and the Shadow DOM polyfill)\n * implement Shadow DOM v1.\n */\n class ShadowTemplate extends base {\n\n /*\n * If the component defines a template, a shadow root will be created on the\n * component instance, and the template stamped into it.\n */\n constructor() {\n super();\n let template = this[symbols.template];\n // TODO: Save the processed template with the component's class prototype\n // so it doesn't need to be processed with every instantiation.\n if (template) {\n\n if (typeof template === 'string') {\n // Upgrade plain string to real template.\n template = createTemplateWithInnerHTML(template);\n }\n\n if (window.ShadowDOMPolyfill) {\n shimTemplateStyles(template, this.localName);\n }\n\n const root = this.attachShadow({ mode: 'open' });\n const clone = document.importNode(template.content, true);\n root.appendChild(clone);\n }\n }\n\n }\n\n return ShadowTemplate;\n};\n\n\n// Convert a plain string of HTML into a real template element.\nfunction createTemplateWithInnerHTML(innerHTML) {\n const template = document.createElement('template');\n // REVIEW: Is there an easier way to do this?\n // We'd like to just set innerHTML on the template content, but since it's\n // a DocumentFragment, that doesn't work.\n const div = document.createElement('div');\n div.innerHTML = innerHTML;\n while (div.childNodes.length > 0) {\n template.content.appendChild(div.childNodes[0]);\n }\n return template;\n}\n\n// Invoke basic style shimming with ShadowCSS.\nfunction shimTemplateStyles(template, tag) {\n window.WebComponents.ShadowCSS.shimStyling(template.content, tag);\n}\n","/**\n * Helper function to create a symbol that can be used for associating private\n * data with an element.\n *\n * Mixins and component classes often want to associate private data with an\n * element instance, but JavaScript does not have direct support for true\n * private properties. One approach is to use the\n * [Symbol](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Symbol)\n * data type to set and retrieve data on an element.\n *\n * Unfortunately, the Symbol type is not available in Internet Explorer 11. The\n * `createSymbol` helper function exists as a workaround for IE 11. Rather than\n * returning a true Symbol, it simply returns an underscore-prefixed string.\n *\n * Usage:\n *\n * const fooSymbol = createSymbol('foo');\n *\n * class MyElement extends HTMLElement {\n * get foo() {\n * return this[fooSymbol];\n * }\n * set foo(value) {\n * this[fooSymbol] = value;\n * }\n * }\n *\n * In IE 11, this sample will \"hide\" data behind an instance property this._foo.\n * The use of the underscore is meant to reduce (not eliminate) the potential\n * for name conflicts, and discourage (not prevent) external access to this\n * data. In modern browsers, the above code will eliminate the potential of\n * naming conflicts, and better hide the data behind a real Symbol.\n *\n * @function createSymbol\n * @param {string} description - A string to identify the symbol when debugging\n */\nexport default function createSymbol(description) {\n return typeof Symbol === 'function' ?\n Symbol(description) :\n `_${description}`;\n}\n","import createSymbol from './createSymbol';\nimport toggleClass from './toggleClass';\n\n\n// Symbols for private data members on an element.\nconst safeToSetAttributesSymbol = createSymbol('safeToSetAttributes');\nconst pendingAttributesSymbol = createSymbol('pendingAttributes');\nconst pendingClassesSymbol = createSymbol('pendingClasses');\n\n\n/**\n * Helper functions for updating attributes, including the `class` attribute.\n */\nexport default {\n\n /**\n * Perform any pending updates to attributes and classes.\n *\n * This writes any `setAttribute` or `toggleClass` values that were performed\n * before an element was attached to the document for the first time.\n *\n * This method should be called by mixins/components in their\n * `connectedCallback`. If mulitple mixins/components invoke this during the\n * same `connectedCallback`, only the first call will have any effect. The\n * subsequent calls will be harmless.\n *\n * @param {HTMLElement} element - The element being added to the document.\n */\n connected(element) {\n element[safeToSetAttributesSymbol] = true;\n\n // Set any pending attributes.\n if (element[pendingAttributesSymbol]) {\n for (let attribute in element[pendingAttributesSymbol]) {\n const value = element[pendingAttributesSymbol][attribute];\n setAttributeToElement(element, attribute, value);\n }\n element[pendingAttributesSymbol] = null;\n }\n\n // Set any pending classes.\n if (element[pendingClassesSymbol]) {\n for (let className in element[pendingClassesSymbol]) {\n const value = element[pendingClassesSymbol][className];\n toggleClass(element, className, value);\n }\n element[pendingClassesSymbol] = null;\n }\n },\n\n /**\n * Set/unset the attribute with the indicated name.\n *\n * This method exists primarily to handle the case where an element wants to\n * set a default property value that should be reflected as an attribute. An\n * important limitation of custom element consturctors is that they cannot\n * set attributes. A call to `setAttribute` during the constructor will\n * be deferred until the element is connected to the document.\n *\n * @param {string} attribute - The name of the *attribute* (not property) to set.\n * @param {object} value - The value to set. If null, the attribute will be removed.\n */\n setAttribute(element, attribute, value) {\n if (element[safeToSetAttributesSymbol]) {\n // Safe to set attributes immediately.\n setAttributeToElement(element, attribute, value);\n } else {\n // Defer setting attributes until the first time we're connected.\n if (!element[pendingAttributesSymbol]) {\n element[pendingAttributesSymbol] = {};\n }\n element[pendingAttributesSymbol][attribute] = value;\n }\n },\n\n /**\n * Set/unset the class with the indicated name.\n *\n * This method exists primarily to handle the case where an element wants to\n * set a default property value that should be reflected as as class. An\n * important limitation of custom element consturctors is that they cannot\n * set attributes, including the `class` attribute. A call to\n * `toggleClass` during the constructor will be deferred until the element\n * is connected to the document.\n *\n * @param {string} className - The name of the class to set.\n * @param {object} value - True to set the class, false to remove it.\n */\n toggleClass(element, className, value) {\n if (element[safeToSetAttributesSymbol]) {\n // Safe to set class immediately.\n toggleClass(element, className, value);\n } else {\n // Defer setting class until the first time we're connected.\n if (!element[pendingClassesSymbol]) {\n element[pendingClassesSymbol] = {};\n }\n element[pendingClassesSymbol][className] = value;\n }\n }\n\n};\n\n\n// Reflect the attribute to the given element.\n// If the value is null, remove the attribute.\nfunction setAttributeToElement(element, attributeName, value) {\n if (value === null || typeof value === 'undefined') {\n element.removeAttribute(attributeName);\n } else {\n const text = String(value);\n // Avoid recursive attributeChangedCallback calls.\n if (element.getAttribute(attributeName) !== text) {\n element.setAttribute(attributeName, value);\n }\n }\n}\n","import createSymbol from './createSymbol';\n\n/**\n * A collection of Symbol objects for standard component properties and methods.\n *\n * These Symbol objects are used to allow mixins and a component to internally\n * communicate, without exposing these properties and methods in the component's\n * public API.\n *\n * To use these Symbol objects in your own component, include this module and\n * then create a property or method whose key is the desired Symbol.\n *\n * import 'SingleSelectionMixin' from 'basic-component-mixins/src/SingleSelectionMixin';\n * import 'symbols' from 'basic-component-mixins/src/symbols';\n *\n * class MyElement extends SingleSelectionMixin(HTMLElement) {\n * [symbols.itemSelected](item, selected) {\n * // This will be invoked whenever an item is selected/deselected.\n * }\n * }\n *\n * @module symbols\n */\nconst symbols = {\n\n /**\n * Symbol for the `defaults` property.\n *\n * This property can be used to set or override defaults that will be applied\n * to a new component instance. When implementing this property, take care to\n * first acquire any defaults defined by the superclass. The standard idiom is\n * as follows:\n *\n * get [symbols.defaults]() {\n * const defaults = super[symbols.defaults] || {};\n * // Set or override default values here\n * defaults.customProperty = false;\n * return defaults;\n * }\n *\n * @var {object} defaults\n */\n defaults: createSymbol('defaults'),\n\n /**\n * Symbol for the `dragging` property.\n *\n * Components like carousels often define animated CSS transitions for\n * sliding effects. Such a transition should usually *not* be applied while\n * the user is dragging, because a CSS animation will introduce a lag that\n * makes the swipe feel sluggish. Instead, as long as the user is dragging\n * with their finger down, the transition should be suppressed. When the\n * user releases their finger, the transition can be restored, allowing the\n * animation to show the carousel sliding into its final position.\n *\n * @type {boolean} true if a drag is in progress, false if not.\n */\n dragging: createSymbol('dragging'),\n\n /**\n * Symbol for the `goDown` method.\n *\n * This method is invoked when the user wants to go/navigate down.\n *\n * @function goDown\n */\n goDown: createSymbol('goDown'),\n\n /**\n * Symbol for the `goEnd` method.\n *\n * This method is invoked when the user wants to go/navigate to the end (e.g.,\n * of a list).\n *\n * @function goEnd\n */\n goEnd: createSymbol('goEnd'),\n\n /**\n * Symbol for the `goLeft` method.\n *\n * This method is invoked when the user wants to go/navigate left.\n *\n * @function goLeft\n */\n goLeft: createSymbol('goLeft'),\n\n /**\n * Symbol for the `goRight` method.\n *\n * This method is invoked when the user wants to go/navigate right.\n *\n * @function goRight\n */\n goRight: createSymbol('goRight'),\n\n /**\n * Symbol for the `goStart` method.\n *\n * This method is invoked when the user wants to go/navigate to the start\n * (e.g., of a list).\n *\n * @function goStart\n */\n goStart: createSymbol('goStart'),\n\n /**\n * Symbol for the `goUp` method.\n *\n * This method is invoked when the user wants to go/navigate up.\n *\n * @function goUp\n */\n goUp: createSymbol('goUp'),\n\n /**\n * Symbol for the `itemAdded` method.\n *\n * This method is invoked when a new item is added to a list.\n *\n * @function itemAdded\n * @param {HTMLElement} item - the item being selected/deselected\n */\n itemAdded: createSymbol('itemAdded'),\n\n\n /**\n * Symbol for the `itemsChanged` method.\n *\n * This method is invoked when the underlying contents change. It is also\n * invoked on component initialization – since the items have \"changed\" from\n * being nothing.\n */\n itemsChanged: createSymbol('itemsChanged'),\n\n /**\n * Symbol for the `itemSelected` method.\n *\n * This method is invoked when an item becomes selected or deselected.\n *\n * @function itemSelected\n * @param {HTMLElement} item - the item being selected/deselected\n * @param {boolean} selected - true if the item is selected, false if not\n */\n itemSelected: createSymbol('itemSelected'),\n\n /**\n * Symbol for the `keydown` method.\n *\n * This method is invoked when an element receives a `keydown` event.\n *\n * @function keydown\n * @param {KeyboardEvent} event - the event being processed\n */\n keydown: createSymbol('keydown'),\n\n /**\n * Symbol for the `template` property.\n *\n * This property returns a component's template.\n *\n * @type {string|HTMLElement}\n */\n template: createSymbol('template')\n};\n\nexport default symbols;\n","/**\n * Helper function for standard classList.toggle() behavior on old browsers,\n * namely IE 11.\n *\n * The standard\n * [classlist](https://developer.mozilla.org/en-US/docs/Web/API/Element/classList)\n * object has a `toggle()` function that supports a second Boolean parameter\n * that can be used to succinctly turn a class on or off. This feature is often\n * useful in designing custom elements, which may want to externally reflect\n * component state in a CSS class that can be used for styling purposes.\n *\n * Unfortunately, IE 11 does not support the Boolean parameter to\n * `classList.toggle()`. This helper function behaves like the standard\n * `toggle()`, including support for the Boolean parameter, so that it can be\n * used even on IE 11.\n *\n * @function toggleClass\n * @param {HTMLElement} element - The element to modify\n * @param {string} className - The class to add/remove\n * @param {boolean} [force] - Force the class to be added (if true) or removed\n * (if false)\n */\nexport default function toggleClass(element, className, force) {\n const classList = element.classList;\n const addClass = (typeof force === 'undefined') ?\n !classList.contains(className) :\n force;\n if (addClass) {\n classList.add(className);\n } else {\n classList.remove(className);\n }\n return addClass;\n}\n","/*\n * This file is transpiled to create an ES5-compatible distribution in which\n * the package's main feature(s) are available via the window.Basic global.\n * If you're already using ES6 yourself, ignore this file, and instead import\n * the source file(s) you want from the src folder.\n */\n\nimport ElementBase from './src/ElementBase';\n\nwindow.Basic = window.Basic || {};\nwindow.Basic.ElementBase = ElementBase;\n","import AttributeMarshallingMixin from '../../basic-component-mixins/src/AttributeMarshallingMixin';\nimport ComposableMixin from '../../basic-component-mixins/src/ComposableMixin';\nimport DistributedChildrenMixin from '../../basic-component-mixins/src/DistributedChildrenMixin';\nimport ShadowElementReferencesMixin from '../../basic-component-mixins/src/ShadowElementReferencesMixin';\nimport ShadowTemplateMixin from '../../basic-component-mixins/src/ShadowTemplateMixin';\n\n\n/**\n * A sample general-purpose base class for defining custom elements that mixes\n * in some common features: template stamping into a shadow root, shadow element\n * references, marshalling attributes to properties, and retrieving the children\n * distributed to a component.\n *\n * This base class is not special in any way, and is defined only as a\n * convenient shorthand for applying the mixins listed above. You can use this\n * class as a base class for your own elements, or easily create your own base\n * class by applying the same set of mixins.\n *\n * The ElementBase base class does not register itself as a custom element with\n * the browser, and hence cannot be independently instantiated.\n *\n * @mixes AttributeMarshallingMixin\n * @mixes ComposableMixin\n * @mixes DistributedChildrenMixin\n * @mixes ShadowElementReferencesMixin\n * @mixes ShadowTemplateMixin\n */\nclass ElementBase extends ComposableMixin(HTMLElement).compose(\n ShadowTemplateMixin, // before node finding, so shadow root is populated\n ShadowElementReferencesMixin, // before marshalling, so properties can use refs\n AttributeMarshallingMixin,\n DistributedChildrenMixin\n) {}\n\nexport default ElementBase;\n"]}
\ No newline at end of file
diff --git a/packages/basic-fade-overflow/dist/basic-fade-overflow.js b/packages/basic-fade-overflow/dist/basic-fade-overflow.js
index 3106f453..f3b4cf16 100644
--- a/packages/basic-fade-overflow/dist/basic-fade-overflow.js
+++ b/packages/basic-fade-overflow/dist/basic-fade-overflow.js
@@ -1,1345 +1,2 @@
-(function e(t,n,r){function s(o,u){if(!n[o]){if(!t[o]){var a=typeof require=="function"&&require;if(!u&&a)return a(o,!0);if(i)return i(o,!0);var f=new Error("Cannot find module '"+o+"'");throw f.code="MODULE_NOT_FOUND",f}var l=n[o]={exports:{}};t[o][0].call(l.exports,function(e){var n=t[o][1][e];return s(n?n:e)},l,l.exports,e,t,n,r)}return n[o].exports}var i=typeof require=="function"&&require;for(var o=0;o
- *
- * Then, after the element has been upgraded, the `fooBar` setter will
- * automatically be invoked with the initial value "Hello".
- *
- * For the time being, this mixin only supports string-valued properties.
- * If you'd like to convert string attributes to other types (numbers,
- * booleans), you need to implement `attributeChangedCallback` yourself.
- */
- var AttributeMarshalling = function (_base) {
- _inherits(AttributeMarshalling, _base);
-
- function AttributeMarshalling() {
- _classCallCheck(this, AttributeMarshalling);
-
- return _possibleConstructorReturn(this, (AttributeMarshalling.__proto__ || Object.getPrototypeOf(AttributeMarshalling)).apply(this, arguments));
- }
-
- _createClass(AttributeMarshalling, [{
- key: 'attributeChangedCallback',
-
-
- /*
- * Handle a change to the attribute with the given name.
- */
- value: function attributeChangedCallback(attributeName, oldValue, newValue) {
- if (_get(AttributeMarshalling.prototype.__proto__ || Object.getPrototypeOf(AttributeMarshalling.prototype), 'attributeChangedCallback', this)) {
- _get(AttributeMarshalling.prototype.__proto__ || Object.getPrototypeOf(AttributeMarshalling.prototype), 'attributeChangedCallback', this).call(this);
- }
- var propertyName = attributeToPropertyName(attributeName);
- // If the attribute name corresponds to a property name, set the property.
- // Ignore standard HTMLElement properties handled by the DOM.
- if (propertyName in this && !(propertyName in HTMLElement.prototype)) {
- this[propertyName] = newValue;
- }
- }
- }, {
- key: 'connectedCallback',
- value: function connectedCallback() {
- if (_get(AttributeMarshalling.prototype.__proto__ || Object.getPrototypeOf(AttributeMarshalling.prototype), 'connectedCallback', this)) {
- _get(AttributeMarshalling.prototype.__proto__ || Object.getPrototypeOf(AttributeMarshalling.prototype), 'connectedCallback', this).call(this);
- }
- _safeAttributes2.default.connected(this);
- }
- }, {
- key: 'reflectAttribute',
-
-
- /**
- * Set/unset the attribute with the indicated name.
- *
- * This method exists primarily to handle the case where an element wants to
- * set a default property value that should be reflected as an attribute. An
- * important limitation of custom element consturctors is that they cannot
- * set attributes. A call to `reflectAttribute` during the constructor will
- * be deferred until the element is connected to the document.
- *
- * @param {string} attribute - The name of the *attribute* (not property) to set.
- * @param {object} value - The value to set. If null, the attribute will be removed.
- */
- value: function reflectAttribute(attribute, value) {
- return _safeAttributes2.default.setAttribute(this, attribute, value);
- }
-
- /**
- * Set/unset the class with the indicated name.
- *
- * This method exists primarily to handle the case where an element wants to
- * set a default property value that should be reflected as as class. An
- * important limitation of custom element consturctors is that they cannot
- * set attributes, including the `class` attribute. A call to
- * `reflectClass` during the constructor will be deferred until the element
- * is connected to the document.
- *
- * @param {string} className - The name of the class to set.
- * @param {object} value - True to set the class, false to remove it.
- */
-
- }, {
- key: 'reflectClass',
- value: function reflectClass(className, value) {
- return _safeAttributes2.default.toggleClass(this, className, value);
- }
- }], [{
- key: 'observedAttributes',
- get: function get() {
- return attributesForClass(this);
- }
- }]);
-
- return AttributeMarshalling;
- }(base);
-
- return AttributeMarshalling;
-};
-
-// Convert hyphenated foo-bar attribute name to camel case fooBar property name.
-
-
-function attributeToPropertyName(attributeName) {
- var propertyName = attributeToPropertyNames[attributeName];
- if (!propertyName) {
- // Convert and memoize.
- var hypenRegEx = /-([a-z])/g;
- propertyName = attributeName.replace(hypenRegEx, function (match) {
- return match[1].toUpperCase();
- });
- attributeToPropertyNames[attributeName] = propertyName;
- }
- return propertyName;
-}
-
-function attributesForClass(classFn) {
-
- // We treat the element base classes as if they have no attributes, since we
- // don't want to receive attributeChangedCallback for them.
- if (classFn === HTMLElement || classFn === Object) {
- return [];
- }
-
- // Get attributes for parent class.
- var baseClass = Object.getPrototypeOf(classFn.prototype).constructor;
- var baseAttributes = attributesForClass(baseClass);
-
- // Get attributes for this class.
- var propertyNames = Object.getOwnPropertyNames(classFn.prototype);
- var setterNames = propertyNames.filter(function (propertyName) {
- return typeof Object.getOwnPropertyDescriptor(classFn.prototype, propertyName).set === 'function';
- });
- var attributes = setterNames.map(function (setterName) {
- return propertyNameToAttribute(setterName);
- });
-
- // Merge.
- var diff = attributes.filter(function (attribute) {
- return baseAttributes.indexOf(attribute) < 0;
- });
- return baseAttributes.concat(diff);
-}
-
-// Convert a camel case fooBar property name to a hyphenated foo-bar attribute.
-function propertyNameToAttribute(propertyName) {
- var attribute = propertyNamesToAttributes[propertyName];
- if (!attribute) {
- // Convert and memoize.
- var uppercaseRegEx = /([A-Z])/g;
- attribute = propertyName.replace(uppercaseRegEx, '-$1').toLowerCase();
- }
- return attribute;
-}
-
-},{"./safeAttributes":7}],2:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-/* Exported function extends a base class with Composable. */
-exports.default = function (base) {
-
- /**
- * Mixin to make a class more easily composable with other mixins.
- *
- * This mixin contributes a `compose` method that applies a set of mixin
- * functions and returns the resulting new class. This sugar can make the
- * application of many mixins at once easier to read.
- */
- var Composable = function (_base) {
- _inherits(Composable, _base);
-
- function Composable() {
- _classCallCheck(this, Composable);
-
- return _possibleConstructorReturn(this, (Composable.__proto__ || Object.getPrototypeOf(Composable)).apply(this, arguments));
- }
-
- _createClass(Composable, null, [{
- key: 'compose',
-
-
- /**
- * Apply a set of mixin functions or mixin objects to the present class and
- * return the new class.
- *
- * Instead of writing:
- *
- * let MyClass = Mixin1(Mixin2(Mixin3(Mixin4(Mixin5(BaseClass)))));
- *
- * You can write:
- *
- * let MyClass = ComposableMixin(BaseClass).compose(
- * Mixin1,
- * Mixin2,
- * Mixin3,
- * Mixin4,
- * Mixin5
- * );
- *
- * This function can also take mixin objects. A mixin object is just a
- * shorthand for a mixin function that creates a new subclass with the given
- * members. The mixin object's members are *not* copied directly onto the
- * prototype of the base class, as with traditional mixins.
- *
- * In addition to providing syntactic sugar, this mixin can be used to
- * define a class in ES5, which lacks ES6's `class` keyword.
- *
- * @param {...mixins} mixins - A set of mixin functions or objects to apply.
- */
- value: function compose() {
- for (var _len = arguments.length, mixins = Array(_len), _key = 0; _key < _len; _key++) {
- mixins[_key] = arguments[_key];
- }
-
- // We create a new subclass for each mixin in turn. The result becomes
- // the base class extended by any subsequent mixins. It turns out that
- // we can use Array.reduce() to concisely express this, using the current
- // object as the seed for reduce().
- return mixins.reduce(composeClass, this);
- }
- }]);
-
- return Composable;
- }(base);
-
- return Composable;
-};
-
-// Properties defined by Object that we don't want to mixin.
-
-
-var NON_MIXABLE_OBJECT_PROPERTIES = ['constructor'];
-
-/*
- * Apply the mixin to the given base class to return a new class.
- * The mixin can either be a function that returns the modified class, or a
- * plain object whose members will be copied to the new class' prototype.
- */
-function composeClass(base, mixin) {
- if (typeof mixin === 'function') {
- // Mixin function
- return mixin(base);
- } else {
- // Mixin object
- var Subclass = function (_base2) {
- _inherits(Subclass, _base2);
-
- function Subclass() {
- _classCallCheck(this, Subclass);
-
- return _possibleConstructorReturn(this, (Subclass.__proto__ || Object.getPrototypeOf(Subclass)).apply(this, arguments));
- }
-
- return Subclass;
- }(base);
-
- copyOwnProperties(mixin, Subclass.prototype, NON_MIXABLE_OBJECT_PROPERTIES);
- return Subclass;
- }
-}
-
-/*
- * Copy the given properties/methods to the target.
- * Return the updated target.
- */
-function copyOwnProperties(source, target) {
- var ignorePropertyNames = arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : [];
-
- Object.getOwnPropertyNames(source).forEach(function (name) {
- if (ignorePropertyNames.indexOf(name) < 0) {
- var descriptor = Object.getOwnPropertyDescriptor(source, name);
- Object.defineProperty(target, name, descriptor);
- }
- });
- return target;
-}
-
-},{}],3:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
-
-function _toConsumableArray(arr) { if (Array.isArray(arr)) { for (var i = 0, arr2 = Array(arr.length); i < arr.length; i++) { arr2[i] = arr[i]; } return arr2; } else { return Array.from(arr); } }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-/* Exported function extends a base class with DistributedChildren. */
-exports.default = function (base) {
-
- /**
- * Mixin which defines helpers for accessing a component's distributed
- * children as a flattened array or string.
- *
- * The standard DOM API provides several ways of accessing child content:
- * `children`, `childNodes`, and `textContent`. None of these functions are
- * Shadow DOM aware. This mixin defines variations of those functions that
- * *are* Shadow DOM aware.
- *
- * Example: you create a component `` that displays a number
- * equal to the number of children placed inside that component. If someone
- * instantiates your component like:
- *
- *
- *
- *
- *
- *
- *
- * Then the component should show "3", because there are three children. To
- * calculate the number of children, the component can just calculate
- * `this.children.length`. However, suppose someone instantiates your
- * component inside one of their own components, and puts a `` element
- * inside your component:
- *
- *
- *
- *
- *
- * If your component only looks at `this.children`, it will always see exactly
- * one child — the `` element. But the user looking at the page will
- * *see* any nodes distributed to that slot. To match what the user sees, your
- * component should expand any `` elements it contains.
- *
- * That is the problem this mixin solves. After applying this mixin, your
- * component code has access to `this.distributedChildren`, whose `length`
- * will return the total number of all children distributed to your component
- * in the composed tree.
- *
- * Note: The latest Custom Elements API design calls for a new function,
- * `getAssignedNodes` that takes an optional `deep` parameter, that will solve
- * this problem at the API level.
- */
- var DistributedChildren = function (_base) {
- _inherits(DistributedChildren, _base);
-
- function DistributedChildren() {
- _classCallCheck(this, DistributedChildren);
-
- return _possibleConstructorReturn(this, (DistributedChildren.__proto__ || Object.getPrototypeOf(DistributedChildren)).apply(this, arguments));
- }
-
- _createClass(DistributedChildren, [{
- key: 'distributedChildren',
-
-
- /**
- * An in-order collection of distributed children, expanding any slot
- * elements. Like the standard children property, this skips text nodes.
- *
- * @type {HTMLElement[]}
- */
- get: function get() {
- return expandContentElements(this.children, false);
- }
-
- /**
- * An in-order collection of distributed child nodes, expanding any slot
- * elements. Like the standard childNodes property, this includes text
- * nodes.
- *
- * @type {Node[]}
- */
-
- }, {
- key: 'distributedChildNodes',
- get: function get() {
- return expandContentElements(this.childNodes, true);
- }
-
- /**
- * The concatenated text content of all distributed child nodes, expanding
- * any slot elements.
- *
- * @type {string}
- */
-
- }, {
- key: 'distributedTextContent',
- get: function get() {
- var strings = this.distributedChildNodes.map(function (child) {
- return child.textContent;
- });
- return strings.join('');
- }
- }]);
-
- return DistributedChildren;
- }(base);
-
- return DistributedChildren;
-};
-
-/*
- * Given a array of nodes, return a new array with any content elements expanded
- * to the nodes distributed to that content element. This rule is applied
- * recursively.
- *
- * If includeTextNodes is true, text nodes will be included, as in the
- * standard childNodes property; by default, this skips text nodes, like the
- * standard children property.
- */
-
-
-function expandContentElements(nodes, includeTextNodes) {
- var _ref;
-
- var expanded = Array.prototype.map.call(nodes, function (node) {
- // We want to see if the node is an instanceof HTMLSlotELement, but
- // that class won't exist if the browser that doesn't support native
- // Shadow DOM and if the Shadow DOM polyfill hasn't been loaded. Instead,
- // we do a simplistic check to see if the tag name is "slot".
- var isSlot = typeof HTMLSlotElement !== 'undefined' ? node instanceof HTMLSlotElement : node.localName === 'slot';
- if (isSlot) {
- // Use the nodes assigned to this node instead.
- var assignedNodes = node.assignedNodes({ flatten: true });
- return assignedNodes ? expandContentElements(assignedNodes, includeTextNodes) : [];
- } else if (node instanceof HTMLElement) {
- // Plain element; use as is.
- return [node];
- } else if (node instanceof Text && includeTextNodes) {
- // Text node.
- return [node];
- } else {
- // Comment, processing instruction, etc.; skip.
- return [];
- }
- });
- var flattened = (_ref = []).concat.apply(_ref, _toConsumableArray(expanded));
- return flattened;
-}
-
-},{}],4:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-/* Exported function extends a base class with ShadowElementReferences. */
-exports.default = function (base) {
-
- /**
- * Mixin to create references to elements in a component's Shadow DOM subtree.
- *
- * This adds a member on the component called `this.$` that can be used to
- * reference shadow elements with IDs. E.g., if component's shadow contains an
- * element ``, then this mixin will create a member
- * `this.$.foo` that points to that button.
- *
- * Such references simplify a component's access to its own elements. In
- * exchange, this mixin trades off a one-time cost of querying all elements in
- * the shadow tree instead of paying an ongoing cost to query for an element
- * each time the component wants to inspect or manipulate it.
- *
- * This mixin expects the component to define a Shadow DOM subtree. You can
- * create that tree yourself, or make use of
- * [ShadowTemplateMixin](ShadowTemplateMixin.md).
- *
- * This mixin is inspired by Polymer's [automatic
- * node finding](https://www.polymer-project.org/1.0/docs/devguide/local-dom.html#node-finding)
- * feature.
- */
- var ShadowElementReferences = function (_base) {
- _inherits(ShadowElementReferences, _base);
-
- function ShadowElementReferences() {
- _classCallCheck(this, ShadowElementReferences);
-
- var _this = _possibleConstructorReturn(this, (ShadowElementReferences.__proto__ || Object.getPrototypeOf(ShadowElementReferences)).call(this));
-
- if (_this.shadowRoot) {
- // Look for elements in the shadow subtree that have id attributes.
- // An alternatively implementation of this mixin would be to just define
- // a this.$ getter that lazily does this search the first time someone
- // tries to access this.$. That might introduce some complexity – if the
- // the tree changed after it was first populated, the result of
- // searching for a node might be somewhat unpredictable.
- _this.$ = {};
- var nodesWithIds = _this.shadowRoot.querySelectorAll('[id]');
- [].forEach.call(nodesWithIds, function (node) {
- var id = node.getAttribute('id');
- _this.$[id] = node;
- });
- }
- return _this;
- }
-
- /**
- * The collection of references to the elements with IDs in a component's
- * Shadow DOM subtree.
- *
- * @type {object}
- * @member $
- */
-
-
- return ShadowElementReferences;
- }(base);
-
- return ShadowElementReferences;
-};
-
-},{}],5:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _symbols = require('../src/symbols');
-
-var _symbols2 = _interopRequireDefault(_symbols);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-/* Exported function extends a base class with ShadowTemplate. */
-exports.default = function (base) {
-
- /**
- * Mixin for stamping a template into a Shadow DOM subtree upon component
- * instantiation.
- *
- * To use this mixin, define a `template` property as a string or HTML
- * `` element:
- *
- * class MyElement extends ShadowTemplateMixin(HTMLElement) {
- * get [symbols.template]() {
- * return `Hello, world .`;
- * }
- * }
- *
- * When your component class is instantiated, a shadow root will be created on
- * the instance, and the contents of the template will be cloned into the
- * shadow root. If your component does not define a `template` property, this
- * mixin has no effect.
- *
- * For the time being, this extension retains support for Shadow DOM v0. That
- * will eventually be deprecated as browsers (and the Shadow DOM polyfill)
- * implement Shadow DOM v1.
- */
- var ShadowTemplate = function (_base) {
- _inherits(ShadowTemplate, _base);
-
- /*
- * If the component defines a template, a shadow root will be created on the
- * component instance, and the template stamped into it.
- */
- function ShadowTemplate() {
- _classCallCheck(this, ShadowTemplate);
-
- var _this = _possibleConstructorReturn(this, (ShadowTemplate.__proto__ || Object.getPrototypeOf(ShadowTemplate)).call(this));
-
- var template = _this[_symbols2.default.template];
- // TODO: Save the processed template with the component's class prototype
- // so it doesn't need to be processed with every instantiation.
- if (template) {
-
- if (typeof template === 'string') {
- // Upgrade plain string to real template.
- template = createTemplateWithInnerHTML(template);
- }
-
- if (window.ShadowDOMPolyfill) {
- shimTemplateStyles(template, _this.localName);
- }
-
- var root = _this.attachShadow({ mode: 'open' });
- var clone = document.importNode(template.content, true);
- root.appendChild(clone);
- }
- return _this;
- }
-
- return ShadowTemplate;
- }(base);
-
- return ShadowTemplate;
-};
-
-// Convert a plain string of HTML into a real template element.
-
-
-function createTemplateWithInnerHTML(innerHTML) {
- var template = document.createElement('template');
- // REVIEW: Is there an easier way to do this?
- // We'd like to just set innerHTML on the template content, but since it's
- // a DocumentFragment, that doesn't work.
- var div = document.createElement('div');
- div.innerHTML = innerHTML;
- while (div.childNodes.length > 0) {
- template.content.appendChild(div.childNodes[0]);
- }
- return template;
-}
-
-// Invoke basic style shimming with ShadowCSS.
-function shimTemplateStyles(template, tag) {
- window.WebComponents.ShadowCSS.shimStyling(template.content, tag);
-}
-
-},{"../src/symbols":8}],6:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-exports.default = createSymbol;
-/**
- * Helper function to create a symbol that can be used for associating private
- * data with an element.
- *
- * Mixins and component classes often want to associate private data with an
- * element instance, but JavaScript does not have direct support for true
- * private properties. One approach is to use the
- * [Symbol](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Symbol)
- * data type to set and retrieve data on an element.
- *
- * Unfortunately, the Symbol type is not available in Internet Explorer 11. The
- * `createSymbol` helper function exists as a workaround for IE 11. Rather than
- * returning a true Symbol, it simply returns an underscore-prefixed string.
- *
- * Usage:
- *
- * const fooSymbol = createSymbol('foo');
- *
- * class MyElement extends HTMLElement {
- * get foo() {
- * return this[fooSymbol];
- * }
- * set foo(value) {
- * this[fooSymbol] = value;
- * }
- * }
- *
- * In IE 11, this sample will "hide" data behind an instance property this._foo.
- * The use of the underscore is meant to reduce (not eliminate) the potential
- * for name conflicts, and discourage (not prevent) external access to this
- * data. In modern browsers, the above code will eliminate the potential of
- * naming conflicts, and better hide the data behind a real Symbol.
- *
- * @function createSymbol
- * @param {string} description - A string to identify the symbol when debugging
- */
-function createSymbol(description) {
- return typeof Symbol === 'function' ? Symbol(description) : '_' + description;
-}
-
-},{}],7:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createSymbol = require('./createSymbol');
-
-var _createSymbol2 = _interopRequireDefault(_createSymbol);
-
-var _toggleClass2 = require('./toggleClass');
-
-var _toggleClass3 = _interopRequireDefault(_toggleClass2);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-// Symbols for private data members on an element.
-var safeToSetAttributesSymbol = (0, _createSymbol2.default)('safeToSetAttributes');
-var pendingAttributesSymbol = (0, _createSymbol2.default)('pendingAttributes');
-var pendingClassesSymbol = (0, _createSymbol2.default)('pendingClasses');
-
-/**
- * Helper functions for updating attributes, including the `class` attribute.
- */
-exports.default = {
-
- /**
- * Perform any pending updates to attributes and classes.
- *
- * This writes any `setAttribute` or `toggleClass` values that were performed
- * before an element was attached to the document for the first time.
- *
- * This method should be called by mixins/components in their
- * `connectedCallback`. If mulitple mixins/components invoke this during the
- * same `connectedCallback`, only the first call will have any effect. The
- * subsequent calls will be harmless.
- *
- * @param {HTMLElement} element - The element being added to the document.
- */
- connected: function connected(element) {
- element[safeToSetAttributesSymbol] = true;
-
- // Set any pending attributes.
- if (element[pendingAttributesSymbol]) {
- for (var attribute in element[pendingAttributesSymbol]) {
- var value = element[pendingAttributesSymbol][attribute];
- setAttributeToElement(element, attribute, value);
- }
- element[pendingAttributesSymbol] = null;
- }
-
- // Set any pending classes.
- if (element[pendingClassesSymbol]) {
- for (var className in element[pendingClassesSymbol]) {
- var _value = element[pendingClassesSymbol][className];
- (0, _toggleClass3.default)(element, className, _value);
- }
- element[pendingClassesSymbol] = null;
- }
- },
-
-
- /**
- * Set/unset the attribute with the indicated name.
- *
- * This method exists primarily to handle the case where an element wants to
- * set a default property value that should be reflected as an attribute. An
- * important limitation of custom element consturctors is that they cannot
- * set attributes. A call to `setAttribute` during the constructor will
- * be deferred until the element is connected to the document.
- *
- * @param {string} attribute - The name of the *attribute* (not property) to set.
- * @param {object} value - The value to set. If null, the attribute will be removed.
- */
- setAttribute: function setAttribute(element, attribute, value) {
- if (element[safeToSetAttributesSymbol]) {
- // Safe to set attributes immediately.
- setAttributeToElement(element, attribute, value);
- } else {
- // Defer setting attributes until the first time we're connected.
- if (!element[pendingAttributesSymbol]) {
- element[pendingAttributesSymbol] = {};
- }
- element[pendingAttributesSymbol][attribute] = value;
- }
- },
-
-
- /**
- * Set/unset the class with the indicated name.
- *
- * This method exists primarily to handle the case where an element wants to
- * set a default property value that should be reflected as as class. An
- * important limitation of custom element consturctors is that they cannot
- * set attributes, including the `class` attribute. A call to
- * `toggleClass` during the constructor will be deferred until the element
- * is connected to the document.
- *
- * @param {string} className - The name of the class to set.
- * @param {object} value - True to set the class, false to remove it.
- */
- toggleClass: function toggleClass(element, className, value) {
- if (element[safeToSetAttributesSymbol]) {
- // Safe to set class immediately.
- (0, _toggleClass3.default)(element, className, value);
- } else {
- // Defer setting class until the first time we're connected.
- if (!element[pendingClassesSymbol]) {
- element[pendingClassesSymbol] = {};
- }
- element[pendingClassesSymbol][className] = value;
- }
- }
-};
-
-// Reflect the attribute to the given element.
-// If the value is null, remove the attribute.
-
-function setAttributeToElement(element, attributeName, value) {
- if (value === null || typeof value === 'undefined') {
- element.removeAttribute(attributeName);
- } else {
- var text = String(value);
- // Avoid recursive attributeChangedCallback calls.
- if (element.getAttribute(attributeName) !== text) {
- element.setAttribute(attributeName, value);
- }
- }
-}
-
-},{"./createSymbol":6,"./toggleClass":9}],8:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createSymbol = require('./createSymbol');
-
-var _createSymbol2 = _interopRequireDefault(_createSymbol);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-/**
- * A collection of Symbol objects for standard component properties and methods.
- *
- * These Symbol objects are used to allow mixins and a component to internally
- * communicate, without exposing these properties and methods in the component's
- * public API.
- *
- * To use these Symbol objects in your own component, include this module and
- * then create a property or method whose key is the desired Symbol.
- *
- * import 'SingleSelectionMixin' from 'basic-component-mixins/src/SingleSelectionMixin';
- * import 'symbols' from 'basic-component-mixins/src/symbols';
- *
- * class MyElement extends SingleSelectionMixin(HTMLElement) {
- * [symbols.itemSelected](item, selected) {
- * // This will be invoked whenever an item is selected/deselected.
- * }
- * }
- *
- * @module symbols
- */
-var symbols = {
-
- /**
- * Symbol for the `defaults` property.
- *
- * This property can be used to set or override defaults that will be applied
- * to a new component instance. When implementing this property, take care to
- * first acquire any defaults defined by the superclass. The standard idiom is
- * as follows:
- *
- * get [symbols.defaults]() {
- * const defaults = super[symbols.defaults] || {};
- * // Set or override default values here
- * defaults.customProperty = false;
- * return defaults;
- * }
- *
- * @var {object} defaults
- */
- defaults: (0, _createSymbol2.default)('defaults'),
-
- /**
- * Symbol for the `dragging` property.
- *
- * Components like carousels often define animated CSS transitions for
- * sliding effects. Such a transition should usually *not* be applied while
- * the user is dragging, because a CSS animation will introduce a lag that
- * makes the swipe feel sluggish. Instead, as long as the user is dragging
- * with their finger down, the transition should be suppressed. When the
- * user releases their finger, the transition can be restored, allowing the
- * animation to show the carousel sliding into its final position.
- *
- * @type {boolean} true if a drag is in progress, false if not.
- */
- dragging: (0, _createSymbol2.default)('dragging'),
-
- /**
- * Symbol for the `goDown` method.
- *
- * This method is invoked when the user wants to go/navigate down.
- *
- * @function goDown
- */
- goDown: (0, _createSymbol2.default)('goDown'),
-
- /**
- * Symbol for the `goEnd` method.
- *
- * This method is invoked when the user wants to go/navigate to the end (e.g.,
- * of a list).
- *
- * @function goEnd
- */
- goEnd: (0, _createSymbol2.default)('goEnd'),
-
- /**
- * Symbol for the `goLeft` method.
- *
- * This method is invoked when the user wants to go/navigate left.
- *
- * @function goLeft
- */
- goLeft: (0, _createSymbol2.default)('goLeft'),
-
- /**
- * Symbol for the `goRight` method.
- *
- * This method is invoked when the user wants to go/navigate right.
- *
- * @function goRight
- */
- goRight: (0, _createSymbol2.default)('goRight'),
-
- /**
- * Symbol for the `goStart` method.
- *
- * This method is invoked when the user wants to go/navigate to the start
- * (e.g., of a list).
- *
- * @function goStart
- */
- goStart: (0, _createSymbol2.default)('goStart'),
-
- /**
- * Symbol for the `goUp` method.
- *
- * This method is invoked when the user wants to go/navigate up.
- *
- * @function goUp
- */
- goUp: (0, _createSymbol2.default)('goUp'),
-
- /**
- * Symbol for the `itemAdded` method.
- *
- * This method is invoked when a new item is added to a list.
- *
- * @function itemAdded
- * @param {HTMLElement} item - the item being selected/deselected
- */
- itemAdded: (0, _createSymbol2.default)('itemAdded'),
-
- /**
- * Symbol for the `itemsChanged` method.
- *
- * This method is invoked when the underlying contents change. It is also
- * invoked on component initialization – since the items have "changed" from
- * being nothing.
- */
- itemsChanged: (0, _createSymbol2.default)('itemsChanged'),
-
- /**
- * Symbol for the `itemSelected` method.
- *
- * This method is invoked when an item becomes selected or deselected.
- *
- * @function itemSelected
- * @param {HTMLElement} item - the item being selected/deselected
- * @param {boolean} selected - true if the item is selected, false if not
- */
- itemSelected: (0, _createSymbol2.default)('itemSelected'),
-
- /**
- * Symbol for the `keydown` method.
- *
- * This method is invoked when an element receives a `keydown` event.
- *
- * @function keydown
- * @param {KeyboardEvent} event - the event being processed
- */
- keydown: (0, _createSymbol2.default)('keydown'),
-
- /**
- * Symbol for the `template` property.
- *
- * This property returns a component's template.
- *
- * @type {string|HTMLElement}
- */
- template: (0, _createSymbol2.default)('template')
-};
-
-exports.default = symbols;
-
-},{"./createSymbol":6}],9:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-exports.default = toggleClass;
-/**
- * Helper function for standard classList.toggle() behavior on old browsers,
- * namely IE 11.
- *
- * The standard
- * [classlist](https://developer.mozilla.org/en-US/docs/Web/API/Element/classList)
- * object has a `toggle()` function that supports a second Boolean parameter
- * that can be used to succinctly turn a class on or off. This feature is often
- * useful in designing custom elements, which may want to externally reflect
- * component state in a CSS class that can be used for styling purposes.
- *
- * Unfortunately, IE 11 does not support the Boolean parameter to
- * `classList.toggle()`. This helper function behaves like the standard
- * `toggle()`, including support for the Boolean parameter, so that it can be
- * used even on IE 11.
- *
- * @function toggleClass
- * @param {HTMLElement} element - The element to modify
- * @param {string} className - The class to add/remove
- * @param {boolean} [force] - Force the class to be added (if true) or removed
- * (if false)
- */
-function toggleClass(element, className, force) {
- var classList = element.classList;
- var addClass = typeof force === 'undefined' ? !classList.contains(className) : force;
- if (addClass) {
- classList.add(className);
- } else {
- classList.remove(className);
- }
- return addClass;
-}
-
-},{}],10:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _AttributeMarshallingMixin = require('../../basic-component-mixins/src/AttributeMarshallingMixin');
-
-var _AttributeMarshallingMixin2 = _interopRequireDefault(_AttributeMarshallingMixin);
-
-var _ComposableMixin = require('../../basic-component-mixins/src/ComposableMixin');
-
-var _ComposableMixin2 = _interopRequireDefault(_ComposableMixin);
-
-var _DistributedChildrenMixin = require('../../basic-component-mixins/src/DistributedChildrenMixin');
-
-var _DistributedChildrenMixin2 = _interopRequireDefault(_DistributedChildrenMixin);
-
-var _ShadowElementReferencesMixin = require('../../basic-component-mixins/src/ShadowElementReferencesMixin');
-
-var _ShadowElementReferencesMixin2 = _interopRequireDefault(_ShadowElementReferencesMixin);
-
-var _ShadowTemplateMixin = require('../../basic-component-mixins/src/ShadowTemplateMixin');
-
-var _ShadowTemplateMixin2 = _interopRequireDefault(_ShadowTemplateMixin);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-/**
- * A sample general-purpose base class for defining custom elements that mixes
- * in some common features: template stamping into a shadow root, shadow element
- * references, marshalling attributes to properties, and retrieving the children
- * distributed to a component.
- *
- * This base class is not special in any way, and is defined only as a
- * convenient shorthand for applying the mixins listed above. You can use this
- * class as a base class for your own elements, or easily create your own base
- * class by applying the same set of mixins.
- *
- * The ElementBase base class does not register itself as a custom element with
- * the browser, and hence cannot be independently instantiated.
- *
- * @mixes AttributeMarshallingMixin
- * @mixes ComposableMixin
- * @mixes DistributedChildrenMixin
- * @mixes ShadowElementReferencesMixin
- * @mixes ShadowTemplateMixin
- */
-var ElementBase = function (_ComposableMixin$comp) {
- _inherits(ElementBase, _ComposableMixin$comp);
-
- function ElementBase() {
- _classCallCheck(this, ElementBase);
-
- return _possibleConstructorReturn(this, (ElementBase.__proto__ || Object.getPrototypeOf(ElementBase)).apply(this, arguments));
- }
-
- return ElementBase;
-}((0, _ComposableMixin2.default)(HTMLElement).compose(_ShadowTemplateMixin2.default, // before node finding, so shadow root is populated
-_ShadowElementReferencesMixin2.default, // before marshalling, so properties can use refs
-_AttributeMarshallingMixin2.default, _DistributedChildrenMixin2.default));
-
-exports.default = ElementBase;
-
-},{"../../basic-component-mixins/src/AttributeMarshallingMixin":1,"../../basic-component-mixins/src/ComposableMixin":2,"../../basic-component-mixins/src/DistributedChildrenMixin":3,"../../basic-component-mixins/src/ShadowElementReferencesMixin":4,"../../basic-component-mixins/src/ShadowTemplateMixin":5}],11:[function(require,module,exports){
-'use strict';
-
-var _FadeOverflow = require('./src/FadeOverflow');
-
-var _FadeOverflow2 = _interopRequireDefault(_FadeOverflow);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-window.Basic = window.Basic || {}; /*
- * This file is transpiled to create an ES5-compatible distribution in which
- * the package's main feature(s) are available via the window.Basic global.
- * If you're already using ES6 yourself, ignore this file, and instead import
- * the source file(s) you want from the src folder.
- */
-
-window.Basic.FadeOverflow = _FadeOverflow2.default;
-
-},{"./src/FadeOverflow":12}],12:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
-
-var _get = function get(object, property, receiver) { if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { return get(parent, property, receiver); } } else if ("value" in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } };
-
-var _createSymbol = require('../../basic-component-mixins/src/createSymbol');
-
-var _createSymbol2 = _interopRequireDefault(_createSymbol);
-
-var _ElementBase2 = require('../../basic-element-base/src/ElementBase');
-
-var _ElementBase3 = _interopRequireDefault(_ElementBase2);
-
-var _symbols = require('../../basic-component-mixins/src/symbols');
-
-var _symbols2 = _interopRequireDefault(_symbols);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-// Symbols for private data members on an element.
-var fadeColorSymbol = (0, _createSymbol2.default)('fadeColor');
-
-/**
- * Fades out content that overflows so the user knows there's more.
- *
- * This component doesn't handle interactivity.
- *
- * The component needs to know the color it should fade to, which it tries to
- * infer from the background color. In some situations, this may not work, in
- * which case you can explicitly set the fadeColor attribute.
- *
- * The component currently always displays the fade, even if the component's
- * content is short enough to fit completely in view.
- *
- * @extends ElementBase
- */
-
-var FadeOverflow = function (_ElementBase) {
- _inherits(FadeOverflow, _ElementBase);
-
- function FadeOverflow() {
- _classCallCheck(this, FadeOverflow);
-
- return _possibleConstructorReturn(this, (FadeOverflow.__proto__ || Object.getPrototypeOf(FadeOverflow)).apply(this, arguments));
- }
-
- _createClass(FadeOverflow, [{
- key: 'connectedCallback',
- value: function connectedCallback() {
- if (_get(FadeOverflow.prototype.__proto__ || Object.getPrototypeOf(FadeOverflow.prototype), 'connectedCallback', this)) {
- _get(FadeOverflow.prototype.__proto__ || Object.getPrototypeOf(FadeOverflow.prototype), 'connectedCallback', this).call(this);
- }
- if (this.fadeColor == null) {
- this.refresh();
- }
- }
-
- /**
- * The color of the fade.
- *
- * The fade color should match the background color. The component does its
- * best to infer the background color, but in some situations, that may not
- * work. In those cases, you can manually identify the background color.
- * This should be a solid color.
- *
- * @attribute fadeColor
- * @default white
- */
-
- }, {
- key: 'refresh',
-
-
- /**
- * Infer the fade color from background color. If you have programmatically
- * changed the color behind the component, you can invoke this method to have
- * the component try to pick up the new background color.
- */
- value: function refresh() {
- // TODO: Automatically hide the fade if all the content can be seen.
- this.fadeColor = findBackgroundColor(this);
- }
-
- /**
- * True if the component should show the fade to the background color.
- *
- * @type {boolean}
- * @default true
- */
-
- }, {
- key: 'fadeColor',
- get: function get() {
- return this[fadeColorSymbol];
- },
- set: function set(value) {
- this[fadeColorSymbol] = value;
- if (value) {
- var rgb = extractRgbValues(value);
- if (rgb) {
- var fadeColorTransparent = 'rgba(' + rgb.r + ',' + rgb.g + ',' + rgb.b + ',0)';
- var gradient = 'linear-gradient(' + fadeColorTransparent + ' 0%, ' + value + ' 100%)';
- this.$.fade.style.backgroundImage = gradient;
- }
- }
- }
- }, {
- key: 'showFade',
- get: function get() {
- return this.$.fade.style.display !== 'none';
- },
- set: function set(value) {
- this.$.fade.style.display = value ? '' : 'none';
- }
- }, {
- key: _symbols2.default.template,
- get: function get() {
- return '\n \n\n
\n \n ';
- }
- }]);
-
- return FadeOverflow;
-}(_ElementBase3.default);
-
-// Return the background color of the given element. If the color is
-// "transparent" (the default in Mozilla and IE) or "rgba(0, 0, 0, 0)" (the
-// default transparent value in Blink and Webkit), walk up the parent chain
-// until a non-transparent color is found.
-
-
-function findBackgroundColor(element) {
- if (element == null || typeof element.style === 'undefined') {
- // This element has no background, assume white.
- return 'rgb(255,255,255)';
- }
- var backgroundColor = getComputedStyle(element).backgroundColor;
- if (backgroundColor === 'transparent' || backgroundColor === 'rgba(0, 0, 0, 0)') {
- return findBackgroundColor(element.parentNode);
- } else {
- return backgroundColor;
- }
-}
-
-// Return the individual RGB values from a CSS color string.
-function extractRgbValues(rgbString) {
- var rgbRegex = /rgba?\(\s*(\d+)\s*,\s*(\d+)\s*,\s*(\d+)\s*(?:,\s*[\d\.]+\s*)?\)/;
- var match = rgbRegex.exec(rgbString);
- if (match) {
- return {
- r: parseInt(match[1]),
- g: parseInt(match[2]),
- b: parseInt(match[3])
- };
- } else {
- return null;
- }
-}
-
-customElements.define('basic-fade-overflow', FadeOverflow);
-exports.default = FadeOverflow;
-
-},{"../../basic-component-mixins/src/createSymbol":6,"../../basic-component-mixins/src/symbols":8,"../../basic-element-base/src/ElementBase":10}]},{},[11])
-//# sourceMappingURL=data:application/json;charset:utf-8;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbIm5vZGVfbW9kdWxlcy9ncnVudC1icm93c2VyaWZ5L25vZGVfbW9kdWxlcy9icm93c2VyLXBhY2svX3ByZWx1ZGUuanMiLCJwYWNrYWdlcy9iYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy9BdHRyaWJ1dGVNYXJzaGFsbGluZ01peGluLmpzIiwicGFja2FnZXMvYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvQ29tcG9zYWJsZU1peGluLmpzIiwicGFja2FnZXMvYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvRGlzdHJpYnV0ZWRDaGlsZHJlbk1peGluLmpzIiwicGFja2FnZXMvYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvU2hhZG93RWxlbWVudFJlZmVyZW5jZXNNaXhpbi5qcyIsInBhY2thZ2VzL2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL1NoYWRvd1RlbXBsYXRlTWl4aW4uanMiLCJwYWNrYWdlcy9iYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy9jcmVhdGVTeW1ib2wuanMiLCJwYWNrYWdlcy9iYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy9zYWZlQXR0cmlidXRlcy5qcyIsInBhY2thZ2VzL2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL3N5bWJvbHMuanMiLCJwYWNrYWdlcy9iYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy90b2dnbGVDbGFzcy5qcyIsInBhY2thZ2VzL2Jhc2ljLWVsZW1lbnQtYmFzZS9zcmMvRWxlbWVudEJhc2UuanMiLCJwYWNrYWdlcy9iYXNpYy1mYWRlLW92ZXJmbG93L2dsb2JhbHMuanMiLCJwYWNrYWdlcy9iYXNpYy1mYWRlLW92ZXJmbG93L3NyYy9GYWRlT3ZlcmZsb3cuanMiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6IkFBQUE7Ozs7Ozs7Ozs7O0FDQUE7Ozs7Ozs7Ozs7OztBQUdBO0FBQ0EsSUFBTSwyQkFBMkIsRUFBakM7QUFDQSxJQUFNLDRCQUE0QixFQUFsQzs7QUFHQTs7a0JBQ2UsVUFBQyxJQUFELEVBQVU7O0FBRXZCOzs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7OztBQUZ1QixNQXFDakIsb0JBckNpQjtBQUFBOztBQUFBO0FBQUE7O0FBQUE7QUFBQTs7QUFBQTtBQUFBOzs7QUF1Q3JCOzs7QUF2Q3FCLCtDQTBDSSxhQTFDSixFQTBDbUIsUUExQ25CLEVBMEM2QixRQTFDN0IsRUEwQ3VDO0FBQzFELHVKQUFvQztBQUFFO0FBQW1DO0FBQ3pFLFlBQU0sZUFBZSx3QkFBd0IsYUFBeEIsQ0FBckI7QUFDQTtBQUNBO0FBQ0EsWUFBSSxnQkFBZ0IsSUFBaEIsSUFBd0IsRUFBRSxnQkFBZ0IsWUFBWSxTQUE5QixDQUE1QixFQUFzRTtBQUNwRSxlQUFLLFlBQUwsSUFBcUIsUUFBckI7QUFDRDtBQUNGO0FBbERvQjtBQUFBO0FBQUEsMENBb0REO0FBQ2xCLGdKQUE2QjtBQUFFO0FBQTRCO0FBQzNELGlDQUFlLFNBQWYsQ0FBeUIsSUFBekI7QUFDRDtBQXZEb0I7QUFBQTs7O0FBNkRyQjs7Ozs7Ozs7Ozs7O0FBN0RxQix1Q0F5RUosU0F6RUksRUF5RU8sS0F6RVAsRUF5RWM7QUFDakMsZUFBTyx5QkFBZSxZQUFmLENBQTRCLElBQTVCLEVBQWtDLFNBQWxDLEVBQTZDLEtBQTdDLENBQVA7QUFDRDs7QUFFRDs7Ozs7Ozs7Ozs7Ozs7QUE3RXFCO0FBQUE7QUFBQSxtQ0EwRlIsU0ExRlEsRUEwRkcsS0ExRkgsRUEwRlU7QUFDN0IsZUFBTyx5QkFBZSxXQUFmLENBQTJCLElBQTNCLEVBQWlDLFNBQWpDLEVBQTRDLEtBQTVDLENBQVA7QUFDRDtBQTVGb0I7QUFBQTtBQUFBLDBCQXlEVztBQUM5QixlQUFPLG1CQUFtQixJQUFuQixDQUFQO0FBQ0Q7QUEzRG9COztBQUFBO0FBQUEsSUFxQ1ksSUFyQ1o7O0FBZ0d2QixTQUFPLG9CQUFQO0FBQ0QsQzs7QUFHRDs7O0FBQ0EsU0FBUyx1QkFBVCxDQUFpQyxhQUFqQyxFQUFnRDtBQUM5QyxNQUFJLGVBQWUseUJBQXlCLGFBQXpCLENBQW5CO0FBQ0EsTUFBSSxDQUFDLFlBQUwsRUFBbUI7QUFDakI7QUFDQSxRQUFNLGFBQWEsV0FBbkI7QUFDQSxtQkFBZSxjQUFjLE9BQWQsQ0FBc0IsVUFBdEIsRUFDWDtBQUFBLGFBQVMsTUFBTSxDQUFOLEVBQVMsV0FBVCxFQUFUO0FBQUEsS0FEVyxDQUFmO0FBRUEsNkJBQXlCLGFBQXpCLElBQTBDLFlBQTFDO0FBQ0Q7QUFDRCxTQUFPLFlBQVA7QUFDRDs7QUFFRCxTQUFTLGtCQUFULENBQTRCLE9BQTVCLEVBQXFDOztBQUVuQztBQUNBO0FBQ0EsTUFBSSxZQUFZLFdBQVosSUFBMkIsWUFBWSxNQUEzQyxFQUFtRDtBQUNqRCxXQUFPLEVBQVA7QUFDRDs7QUFFRDtBQUNBLE1BQU0sWUFBWSxPQUFPLGNBQVAsQ0FBc0IsUUFBUSxTQUE5QixFQUF5QyxXQUEzRDtBQUNBLE1BQU0saUJBQWlCLG1CQUFtQixTQUFuQixDQUF2Qjs7QUFFQTtBQUNBLE1BQU0sZ0JBQWdCLE9BQU8sbUJBQVAsQ0FBMkIsUUFBUSxTQUFuQyxDQUF0QjtBQUNBLE1BQU0sY0FBYyxjQUFjLE1BQWQsQ0FBcUI7QUFBQSxXQUN2QyxPQUFPLE9BQU8sd0JBQVAsQ0FDSCxRQUFRLFNBREwsRUFDZ0IsWUFEaEIsRUFDOEIsR0FEckMsS0FDNkMsVUFGTjtBQUFBLEdBQXJCLENBQXBCO0FBR0EsTUFBTSxhQUFhLFlBQVksR0FBWixDQUFnQjtBQUFBLFdBQy9CLHdCQUF3QixVQUF4QixDQUQrQjtBQUFBLEdBQWhCLENBQW5COztBQUdBO0FBQ0EsTUFBTSxPQUFPLFdBQVcsTUFBWCxDQUFrQjtBQUFBLFdBQzNCLGVBQWUsT0FBZixDQUF1QixTQUF2QixJQUFvQyxDQURUO0FBQUEsR0FBbEIsQ0FBYjtBQUVBLFNBQU8sZUFBZSxNQUFmLENBQXNCLElBQXRCLENBQVA7QUFDRDs7QUFFRDtBQUNBLFNBQVMsdUJBQVQsQ0FBaUMsWUFBakMsRUFBK0M7QUFDN0MsTUFBSSxZQUFZLDBCQUEwQixZQUExQixDQUFoQjtBQUNBLE1BQUksQ0FBQyxTQUFMLEVBQWdCO0FBQ2Q7QUFDQSxRQUFNLGlCQUFpQixVQUF2QjtBQUNBLGdCQUFZLGFBQWEsT0FBYixDQUFxQixjQUFyQixFQUFxQyxLQUFyQyxFQUE0QyxXQUE1QyxFQUFaO0FBQ0Q7QUFDRCxTQUFPLFNBQVA7QUFDRDs7Ozs7Ozs7Ozs7Ozs7Ozs7QUM3SkQ7a0JBQ2UsVUFBQyxJQUFELEVBQVU7O0FBRXZCOzs7Ozs7O0FBRnVCLE1BU2pCLFVBVGlCO0FBQUE7O0FBQUE7QUFBQTs7QUFBQTtBQUFBOztBQUFBO0FBQUE7OztBQVdyQjs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7OztBQVhxQixnQ0F1Q0s7QUFBQSwwQ0FBUixNQUFRO0FBQVIsZ0JBQVE7QUFBQTs7QUFDeEI7QUFDQTtBQUNBO0FBQ0E7QUFDQSxlQUFPLE9BQU8sTUFBUCxDQUFjLFlBQWQsRUFBNEIsSUFBNUIsQ0FBUDtBQUNEO0FBN0NvQjs7QUFBQTtBQUFBLElBU0UsSUFURjs7QUFpRHZCLFNBQU8sVUFBUDtBQUNELEM7O0FBR0Q7OztBQUNBLElBQU0sZ0NBQWdDLENBQ3BDLGFBRG9DLENBQXRDOztBQUlBOzs7OztBQUtBLFNBQVMsWUFBVCxDQUFzQixJQUF0QixFQUE0QixLQUE1QixFQUFtQztBQUNqQyxNQUFJLE9BQU8sS0FBUCxLQUFpQixVQUFyQixFQUFpQztBQUMvQjtBQUNBLFdBQU8sTUFBTSxJQUFOLENBQVA7QUFDRCxHQUhELE1BR087QUFDTDtBQURLLFFBRUMsUUFGRDtBQUFBOztBQUFBO0FBQUE7O0FBQUE7QUFBQTs7QUFBQTtBQUFBLE1BRWtCLElBRmxCOztBQUdMLHNCQUFrQixLQUFsQixFQUF5QixTQUFTLFNBQWxDLEVBQTZDLDZCQUE3QztBQUNBLFdBQU8sUUFBUDtBQUNEO0FBQ0Y7O0FBR0Q7Ozs7QUFJQSxTQUFTLGlCQUFULENBQTJCLE1BQTNCLEVBQW1DLE1BQW5DLEVBQXFFO0FBQUEsTUFBMUIsbUJBQTBCLHVFQUFKLEVBQUk7O0FBQ25FLFNBQU8sbUJBQVAsQ0FBMkIsTUFBM0IsRUFBbUMsT0FBbkMsQ0FBMkMsZ0JBQVE7QUFDakQsUUFBSSxvQkFBb0IsT0FBcEIsQ0FBNEIsSUFBNUIsSUFBb0MsQ0FBeEMsRUFBMkM7QUFDekMsVUFBTSxhQUFhLE9BQU8sd0JBQVAsQ0FBZ0MsTUFBaEMsRUFBd0MsSUFBeEMsQ0FBbkI7QUFDQSxhQUFPLGNBQVAsQ0FBc0IsTUFBdEIsRUFBOEIsSUFBOUIsRUFBb0MsVUFBcEM7QUFDRDtBQUNGLEdBTEQ7QUFNQSxTQUFPLE1BQVA7QUFDRDs7Ozs7Ozs7Ozs7Ozs7Ozs7OztBQ3pGRDtrQkFDZSxVQUFDLElBQUQsRUFBVTs7QUFFdkI7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7QUFGdUIsTUE2Q2pCLG1CQTdDaUI7QUFBQTs7QUFBQTtBQUFBOztBQUFBO0FBQUE7O0FBQUE7QUFBQTs7O0FBK0NyQjs7Ozs7O0FBL0NxQiwwQkFxREs7QUFDeEIsZUFBTyxzQkFBc0IsS0FBSyxRQUEzQixFQUFxQyxLQUFyQyxDQUFQO0FBQ0Q7O0FBRUQ7Ozs7Ozs7O0FBekRxQjtBQUFBO0FBQUEsMEJBZ0VPO0FBQzFCLGVBQU8sc0JBQXNCLEtBQUssVUFBM0IsRUFBdUMsSUFBdkMsQ0FBUDtBQUNEOztBQUVEOzs7Ozs7O0FBcEVxQjtBQUFBO0FBQUEsMEJBMEVRO0FBQzNCLFlBQU0sVUFBVSxLQUFLLHFCQUFMLENBQTJCLEdBQTNCLENBQStCLFVBQVMsS0FBVCxFQUFnQjtBQUM3RCxpQkFBTyxNQUFNLFdBQWI7QUFDRCxTQUZlLENBQWhCO0FBR0EsZUFBTyxRQUFRLElBQVIsQ0FBYSxFQUFiLENBQVA7QUFDRDtBQS9Fb0I7O0FBQUE7QUFBQSxJQTZDVyxJQTdDWDs7QUFtRnZCLFNBQU8sbUJBQVA7QUFDRCxDOztBQUdEOzs7Ozs7Ozs7OztBQVNBLFNBQVMscUJBQVQsQ0FBK0IsS0FBL0IsRUFBc0MsZ0JBQXRDLEVBQXdEO0FBQUE7O0FBQ3RELE1BQU0sV0FBVyxNQUFNLFNBQU4sQ0FBZ0IsR0FBaEIsQ0FBb0IsSUFBcEIsQ0FBeUIsS0FBekIsRUFBZ0MsZ0JBQVE7QUFDdkQ7QUFDQTtBQUNBO0FBQ0E7QUFDQSxRQUFNLFNBQVMsT0FBTyxlQUFQLEtBQTJCLFdBQTNCLEdBQ2IsZ0JBQWdCLGVBREgsR0FFYixLQUFLLFNBQUwsS0FBbUIsTUFGckI7QUFHQSxRQUFJLE1BQUosRUFBWTtBQUNWO0FBQ0EsVUFBTSxnQkFBZ0IsS0FBSyxhQUFMLENBQW1CLEVBQUUsU0FBUyxJQUFYLEVBQW5CLENBQXRCO0FBQ0EsYUFBTyxnQkFDTCxzQkFBc0IsYUFBdEIsRUFBcUMsZ0JBQXJDLENBREssR0FFTCxFQUZGO0FBR0QsS0FORCxNQU1PLElBQUksZ0JBQWdCLFdBQXBCLEVBQWlDO0FBQ3RDO0FBQ0EsYUFBTyxDQUFDLElBQUQsQ0FBUDtBQUNELEtBSE0sTUFHQSxJQUFJLGdCQUFnQixJQUFoQixJQUF3QixnQkFBNUIsRUFBOEM7QUFDbkQ7QUFDQSxhQUFPLENBQUMsSUFBRCxDQUFQO0FBQ0QsS0FITSxNQUdBO0FBQ0w7QUFDQSxhQUFPLEVBQVA7QUFDRDtBQUNGLEdBeEJnQixDQUFqQjtBQXlCQSxNQUFNLFlBQVksWUFBRyxNQUFILGdDQUFhLFFBQWIsRUFBbEI7QUFDQSxTQUFPLFNBQVA7QUFDRDs7Ozs7Ozs7Ozs7Ozs7O0FDN0hEO2tCQUNlLFVBQUMsSUFBRCxFQUFVOztBQUV2Qjs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7O0FBRnVCLE1BdUJqQix1QkF2QmlCO0FBQUE7O0FBeUJyQix1Q0FBYztBQUFBOztBQUFBOztBQUVaLFVBQUksTUFBSyxVQUFULEVBQXFCO0FBQ25CO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBLGNBQUssQ0FBTCxHQUFTLEVBQVQ7QUFDQSxZQUFNLGVBQWUsTUFBSyxVQUFMLENBQWdCLGdCQUFoQixDQUFpQyxNQUFqQyxDQUFyQjtBQUNBLFdBQUcsT0FBSCxDQUFXLElBQVgsQ0FBZ0IsWUFBaEIsRUFBOEIsZ0JBQVE7QUFDcEMsY0FBTSxLQUFLLEtBQUssWUFBTCxDQUFrQixJQUFsQixDQUFYO0FBQ0EsZ0JBQUssQ0FBTCxDQUFPLEVBQVAsSUFBYSxJQUFiO0FBQ0QsU0FIRDtBQUlEO0FBZlc7QUFnQmI7O0FBRUQ7Ozs7Ozs7OztBQTNDcUI7QUFBQSxJQXVCZSxJQXZCZjs7QUFvRHZCLFNBQU8sdUJBQVA7QUFDRCxDOzs7Ozs7Ozs7QUN0REQ7Ozs7Ozs7Ozs7OztBQUdBO2tCQUNlLFVBQUMsSUFBRCxFQUFVOztBQUV2Qjs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7OztBQUZ1QixNQXdCakIsY0F4QmlCO0FBQUE7O0FBMEJyQjs7OztBQUlBLDhCQUFjO0FBQUE7O0FBQUE7O0FBRVosVUFBSSxXQUFXLE1BQUssa0JBQVEsUUFBYixDQUFmO0FBQ0E7QUFDQTtBQUNBLFVBQUksUUFBSixFQUFjOztBQUVaLFlBQUksT0FBTyxRQUFQLEtBQW9CLFFBQXhCLEVBQWtDO0FBQ2hDO0FBQ0EscUJBQVcsNEJBQTRCLFFBQTVCLENBQVg7QUFDRDs7QUFFRCxZQUFJLE9BQU8saUJBQVgsRUFBOEI7QUFDNUIsNkJBQW1CLFFBQW5CLEVBQTZCLE1BQUssU0FBbEM7QUFDRDs7QUFFRCxZQUFNLE9BQU8sTUFBSyxZQUFMLENBQWtCLEVBQUUsTUFBTSxNQUFSLEVBQWxCLENBQWI7QUFDQSxZQUFNLFFBQVEsU0FBUyxVQUFULENBQW9CLFNBQVMsT0FBN0IsRUFBc0MsSUFBdEMsQ0FBZDtBQUNBLGFBQUssV0FBTCxDQUFpQixLQUFqQjtBQUNEO0FBbkJXO0FBb0JiOztBQWxEb0I7QUFBQSxJQXdCTSxJQXhCTjs7QUFzRHZCLFNBQU8sY0FBUDtBQUNELEM7O0FBR0Q7OztBQUNBLFNBQVMsMkJBQVQsQ0FBcUMsU0FBckMsRUFBZ0Q7QUFDOUMsTUFBTSxXQUFXLFNBQVMsYUFBVCxDQUF1QixVQUF2QixDQUFqQjtBQUNBO0FBQ0E7QUFDQTtBQUNBLE1BQU0sTUFBTSxTQUFTLGFBQVQsQ0FBdUIsS0FBdkIsQ0FBWjtBQUNBLE1BQUksU0FBSixHQUFnQixTQUFoQjtBQUNBLFNBQU8sSUFBSSxVQUFKLENBQWUsTUFBZixHQUF3QixDQUEvQixFQUFrQztBQUNoQyxhQUFTLE9BQVQsQ0FBaUIsV0FBakIsQ0FBNkIsSUFBSSxVQUFKLENBQWUsQ0FBZixDQUE3QjtBQUNEO0FBQ0QsU0FBTyxRQUFQO0FBQ0Q7O0FBRUQ7QUFDQSxTQUFTLGtCQUFULENBQTRCLFFBQTVCLEVBQXNDLEdBQXRDLEVBQTJDO0FBQ3pDLFNBQU8sYUFBUCxDQUFxQixTQUFyQixDQUErQixXQUEvQixDQUEyQyxTQUFTLE9BQXBELEVBQTZELEdBQTdEO0FBQ0Q7Ozs7Ozs7O2tCQzNDdUIsWTtBQXBDeEI7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7OztBQW9DZSxTQUFTLFlBQVQsQ0FBc0IsV0FBdEIsRUFBbUM7QUFDaEQsU0FBTyxPQUFPLE1BQVAsS0FBa0IsVUFBbEIsR0FDTCxPQUFPLFdBQVAsQ0FESyxTQUVELFdBRk47QUFHRDs7Ozs7Ozs7O0FDeENEOzs7O0FBQ0E7Ozs7OztBQUdBO0FBQ0EsSUFBTSw0QkFBNEIsNEJBQWEscUJBQWIsQ0FBbEM7QUFDQSxJQUFNLDBCQUEwQiw0QkFBYSxtQkFBYixDQUFoQztBQUNBLElBQU0sdUJBQXVCLDRCQUFhLGdCQUFiLENBQTdCOztBQUdBOzs7a0JBR2U7O0FBRWI7Ozs7Ozs7Ozs7Ozs7QUFhQSxXQWZhLHFCQWVILE9BZkcsRUFlTTtBQUNqQixZQUFRLHlCQUFSLElBQXFDLElBQXJDOztBQUVBO0FBQ0EsUUFBSSxRQUFRLHVCQUFSLENBQUosRUFBc0M7QUFDcEMsV0FBSyxJQUFJLFNBQVQsSUFBc0IsUUFBUSx1QkFBUixDQUF0QixFQUF3RDtBQUN0RCxZQUFNLFFBQVEsUUFBUSx1QkFBUixFQUFpQyxTQUFqQyxDQUFkO0FBQ0EsOEJBQXNCLE9BQXRCLEVBQStCLFNBQS9CLEVBQTBDLEtBQTFDO0FBQ0Q7QUFDRCxjQUFRLHVCQUFSLElBQW1DLElBQW5DO0FBQ0Q7O0FBRUQ7QUFDQSxRQUFJLFFBQVEsb0JBQVIsQ0FBSixFQUFtQztBQUNqQyxXQUFLLElBQUksU0FBVCxJQUFzQixRQUFRLG9CQUFSLENBQXRCLEVBQXFEO0FBQ25ELFlBQU0sU0FBUSxRQUFRLG9CQUFSLEVBQThCLFNBQTlCLENBQWQ7QUFDQSxtQ0FBWSxPQUFaLEVBQXFCLFNBQXJCLEVBQWdDLE1BQWhDO0FBQ0Q7QUFDRCxjQUFRLG9CQUFSLElBQWdDLElBQWhDO0FBQ0Q7QUFDRixHQW5DWTs7O0FBcUNiOzs7Ozs7Ozs7Ozs7QUFZQSxjQWpEYSx3QkFpREEsT0FqREEsRUFpRFMsU0FqRFQsRUFpRG9CLEtBakRwQixFQWlEMkI7QUFDdEMsUUFBSSxRQUFRLHlCQUFSLENBQUosRUFBd0M7QUFDdEM7QUFDQSw0QkFBc0IsT0FBdEIsRUFBK0IsU0FBL0IsRUFBMEMsS0FBMUM7QUFDRCxLQUhELE1BR087QUFDTDtBQUNBLFVBQUksQ0FBQyxRQUFRLHVCQUFSLENBQUwsRUFBdUM7QUFDckMsZ0JBQVEsdUJBQVIsSUFBbUMsRUFBbkM7QUFDRDtBQUNELGNBQVEsdUJBQVIsRUFBaUMsU0FBakMsSUFBOEMsS0FBOUM7QUFDRDtBQUNGLEdBNURZOzs7QUE4RGI7Ozs7Ozs7Ozs7Ozs7QUFhQSxhQTNFYSx1QkEyRUQsT0EzRUMsRUEyRVEsU0EzRVIsRUEyRW1CLEtBM0VuQixFQTJFMEI7QUFDckMsUUFBSSxRQUFRLHlCQUFSLENBQUosRUFBd0M7QUFDdEM7QUFDQSxpQ0FBWSxPQUFaLEVBQXFCLFNBQXJCLEVBQWdDLEtBQWhDO0FBQ0QsS0FIRCxNQUdPO0FBQ0w7QUFDQSxVQUFJLENBQUMsUUFBUSxvQkFBUixDQUFMLEVBQW9DO0FBQ2xDLGdCQUFRLG9CQUFSLElBQWdDLEVBQWhDO0FBQ0Q7QUFDRCxjQUFRLG9CQUFSLEVBQThCLFNBQTlCLElBQTJDLEtBQTNDO0FBQ0Q7QUFDRjtBQXRGWSxDOztBQTJGZjtBQUNBOztBQUNBLFNBQVMscUJBQVQsQ0FBK0IsT0FBL0IsRUFBd0MsYUFBeEMsRUFBdUQsS0FBdkQsRUFBOEQ7QUFDNUQsTUFBSSxVQUFVLElBQVYsSUFBa0IsT0FBTyxLQUFQLEtBQWlCLFdBQXZDLEVBQW9EO0FBQ2xELFlBQVEsZUFBUixDQUF3QixhQUF4QjtBQUNELEdBRkQsTUFFTztBQUNMLFFBQU0sT0FBTyxPQUFPLEtBQVAsQ0FBYjtBQUNBO0FBQ0EsUUFBSSxRQUFRLFlBQVIsQ0FBcUIsYUFBckIsTUFBd0MsSUFBNUMsRUFBa0Q7QUFDaEQsY0FBUSxZQUFSLENBQXFCLGFBQXJCLEVBQW9DLEtBQXBDO0FBQ0Q7QUFDRjtBQUNGOzs7Ozs7Ozs7QUNwSEQ7Ozs7OztBQUVBOzs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7QUFxQkEsSUFBTSxVQUFVOztBQUVkOzs7Ozs7Ozs7Ozs7Ozs7OztBQWlCQSxZQUFVLDRCQUFhLFVBQWIsQ0FuQkk7O0FBcUJkOzs7Ozs7Ozs7Ozs7O0FBYUEsWUFBVSw0QkFBYSxVQUFiLENBbENJOztBQW9DZDs7Ozs7OztBQU9BLFVBQVEsNEJBQWEsUUFBYixDQTNDTTs7QUE2Q2Q7Ozs7Ozs7O0FBUUEsU0FBTyw0QkFBYSxPQUFiLENBckRPOztBQXVEZDs7Ozs7OztBQU9BLFVBQVEsNEJBQWEsUUFBYixDQTlETTs7QUFnRWQ7Ozs7Ozs7QUFPQSxXQUFTLDRCQUFhLFNBQWIsQ0F2RUs7O0FBeUVkOzs7Ozs7OztBQVFBLFdBQVMsNEJBQWEsU0FBYixDQWpGSzs7QUFtRmQ7Ozs7Ozs7QUFPQSxRQUFNLDRCQUFhLE1BQWIsQ0ExRlE7O0FBNEZkOzs7Ozs7OztBQVFBLGFBQVcsNEJBQWEsV0FBYixDQXBHRzs7QUF1R2Q7Ozs7Ozs7QUFPQSxnQkFBYyw0QkFBYSxjQUFiLENBOUdBOztBQWdIZDs7Ozs7Ozs7O0FBU0EsZ0JBQWMsNEJBQWEsY0FBYixDQXpIQTs7QUEySGQ7Ozs7Ozs7O0FBUUEsV0FBUyw0QkFBYSxTQUFiLENBbklLOztBQXFJZDs7Ozs7OztBQU9BLFlBQVUsNEJBQWEsVUFBYjtBQTVJSSxDQUFoQjs7a0JBK0llLE87Ozs7Ozs7O2tCQ2hKUyxXO0FBdEJ4Qjs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7OztBQXNCZSxTQUFTLFdBQVQsQ0FBcUIsT0FBckIsRUFBOEIsU0FBOUIsRUFBeUMsS0FBekMsRUFBZ0Q7QUFDN0QsTUFBTSxZQUFZLFFBQVEsU0FBMUI7QUFDQSxNQUFNLFdBQVksT0FBTyxLQUFQLEtBQWlCLFdBQWxCLEdBQ2YsQ0FBQyxVQUFVLFFBQVYsQ0FBbUIsU0FBbkIsQ0FEYyxHQUVmLEtBRkY7QUFHQSxNQUFJLFFBQUosRUFBYztBQUNaLGNBQVUsR0FBVixDQUFjLFNBQWQ7QUFDRCxHQUZELE1BRU87QUFDTCxjQUFVLE1BQVYsQ0FBaUIsU0FBakI7QUFDRDtBQUNELFNBQU8sUUFBUDtBQUNEOzs7Ozs7Ozs7QUNqQ0Q7Ozs7QUFDQTs7OztBQUNBOzs7O0FBQ0E7Ozs7QUFDQTs7Ozs7Ozs7Ozs7O0FBR0E7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7O0lBb0JNLFc7Ozs7Ozs7Ozs7RUFBb0IsK0JBQWdCLFdBQWhCLEVBQTZCLE9BQTdCLGdDQUNNO0FBRE4sd0NBRU07QUFGTix3RTs7a0JBT1gsVzs7Ozs7QUMzQmY7Ozs7OztBQUVBLE9BQU8sS0FBUCxHQUFlLE9BQU8sS0FBUCxJQUFnQixFQUEvQixDLENBVEE7Ozs7Ozs7QUFVQSxPQUFPLEtBQVAsQ0FBYSxZQUFiOzs7Ozs7Ozs7Ozs7O0FDVkE7Ozs7QUFDQTs7OztBQUNBOzs7Ozs7Ozs7Ozs7QUFHQTtBQUNBLElBQU0sa0JBQWtCLDRCQUFhLFdBQWIsQ0FBeEI7O0FBR0E7Ozs7Ozs7Ozs7Ozs7OztJQWNNLFk7Ozs7Ozs7Ozs7O3dDQUVnQjtBQUNsQiw4SEFBNkI7QUFBRTtBQUE0QjtBQUMzRCxVQUFJLEtBQUssU0FBTCxJQUFrQixJQUF0QixFQUE0QjtBQUMxQixhQUFLLE9BQUw7QUFDRDtBQUNGOztBQUVEOzs7Ozs7Ozs7Ozs7Ozs7O0FBMEJBOzs7Ozs4QkFLVTtBQUNSO0FBQ0EsV0FBSyxTQUFMLEdBQWlCLG9CQUFvQixJQUFwQixDQUFqQjtBQUNEOztBQUVEOzs7Ozs7Ozs7d0JBekJnQjtBQUNkLGFBQU8sS0FBSyxlQUFMLENBQVA7QUFDRCxLO3NCQUNhLEssRUFBTztBQUNuQixXQUFLLGVBQUwsSUFBd0IsS0FBeEI7QUFDQSxVQUFJLEtBQUosRUFBVztBQUNULFlBQU0sTUFBTSxpQkFBaUIsS0FBakIsQ0FBWjtBQUNBLFlBQUksR0FBSixFQUFTO0FBQ1AsY0FBTSxpQ0FBK0IsSUFBSSxDQUFuQyxTQUF3QyxJQUFJLENBQTVDLFNBQWlELElBQUksQ0FBckQsUUFBTjtBQUNBLGNBQU0sZ0NBQThCLG9CQUE5QixhQUEwRCxLQUExRCxXQUFOO0FBQ0EsZUFBSyxDQUFMLENBQU8sSUFBUCxDQUFZLEtBQVosQ0FBa0IsZUFBbEIsR0FBb0MsUUFBcEM7QUFDRDtBQUNGO0FBQ0Y7Ozt3QkFrQmM7QUFDYixhQUFPLEtBQUssQ0FBTCxDQUFPLElBQVAsQ0FBWSxLQUFaLENBQWtCLE9BQWxCLEtBQThCLE1BQXJDO0FBQ0QsSztzQkFDWSxLLEVBQU87QUFDbEIsV0FBSyxDQUFMLENBQU8sSUFBUCxDQUFZLEtBQVosQ0FBa0IsT0FBbEIsR0FBNEIsUUFBUSxFQUFSLEdBQWEsTUFBekM7QUFDRDs7U0FFSSxrQkFBUSxRO3dCQUFZO0FBQ3ZCO0FBcUJEOzs7Ozs7QUFLSDtBQUNBO0FBQ0E7QUFDQTs7O0FBQ0EsU0FBUyxtQkFBVCxDQUE2QixPQUE3QixFQUFzQztBQUNwQyxNQUFJLFdBQVcsSUFBWCxJQUFtQixPQUFPLFFBQVEsS0FBZixLQUF5QixXQUFoRCxFQUE2RDtBQUMzRDtBQUNBLFdBQU8sa0JBQVA7QUFDRDtBQUNELE1BQU0sa0JBQWtCLGlCQUFpQixPQUFqQixFQUEwQixlQUFsRDtBQUNBLE1BQUksb0JBQW9CLGFBQXBCLElBQXFDLG9CQUFvQixrQkFBN0QsRUFBaUY7QUFDL0UsV0FBTyxvQkFBb0IsUUFBUSxVQUE1QixDQUFQO0FBQ0QsR0FGRCxNQUVPO0FBQ0wsV0FBTyxlQUFQO0FBQ0Q7QUFDRjs7QUFHRDtBQUNBLFNBQVMsZ0JBQVQsQ0FBMEIsU0FBMUIsRUFBcUM7QUFDbkMsTUFBTSxXQUFXLGlFQUFqQjtBQUNBLE1BQU0sUUFBUSxTQUFTLElBQVQsQ0FBYyxTQUFkLENBQWQ7QUFDQSxNQUFJLEtBQUosRUFBVztBQUNULFdBQU87QUFDTCxTQUFHLFNBQVMsTUFBTSxDQUFOLENBQVQsQ0FERTtBQUVMLFNBQUcsU0FBUyxNQUFNLENBQU4sQ0FBVCxDQUZFO0FBR0wsU0FBRyxTQUFTLE1BQU0sQ0FBTixDQUFUO0FBSEUsS0FBUDtBQUtELEdBTkQsTUFNTztBQUNMLFdBQU8sSUFBUDtBQUNEO0FBQ0Y7O0FBR0QsZUFBZSxNQUFmLENBQXNCLHFCQUF0QixFQUE2QyxZQUE3QztrQkFDZSxZIiwiZmlsZSI6ImdlbmVyYXRlZC5qcyIsInNvdXJjZVJvb3QiOiIiLCJzb3VyY2VzQ29udGVudCI6WyIoZnVuY3Rpb24gZSh0LG4scil7ZnVuY3Rpb24gcyhvLHUpe2lmKCFuW29dKXtpZighdFtvXSl7dmFyIGE9dHlwZW9mIHJlcXVpcmU9PVwiZnVuY3Rpb25cIiYmcmVxdWlyZTtpZighdSYmYSlyZXR1cm4gYShvLCEwKTtpZihpKXJldHVybiBpKG8sITApO3ZhciBmPW5ldyBFcnJvcihcIkNhbm5vdCBmaW5kIG1vZHVsZSAnXCIrbytcIidcIik7dGhyb3cgZi5jb2RlPVwiTU9EVUxFX05PVF9GT1VORFwiLGZ9dmFyIGw9bltvXT17ZXhwb3J0czp7fX07dFtvXVswXS5jYWxsKGwuZXhwb3J0cyxmdW5jdGlvbihlKXt2YXIgbj10W29dWzFdW2VdO3JldHVybiBzKG4/bjplKX0sbCxsLmV4cG9ydHMsZSx0LG4scil9cmV0dXJuIG5bb10uZXhwb3J0c312YXIgaT10eXBlb2YgcmVxdWlyZT09XCJmdW5jdGlvblwiJiZyZXF1aXJlO2Zvcih2YXIgbz0wO288ci5sZW5ndGg7bysrKXMocltvXSk7cmV0dXJuIHN9KSIsImltcG9ydCBzYWZlQXR0cmlidXRlcyBmcm9tICcuL3NhZmVBdHRyaWJ1dGVzJztcblxuXG4vLyBNZW1vaXplZCBtYXBzIG9mIGF0dHJpYnV0ZSB0byBwcm9wZXJ0eSBuYW1lcyBhbmQgdmljZSB2ZXJzYS5cbmNvbnN0IGF0dHJpYnV0ZVRvUHJvcGVydHlOYW1lcyA9IHt9O1xuY29uc3QgcHJvcGVydHlOYW1lc1RvQXR0cmlidXRlcyA9IHt9O1xuXG5cbi8qIEV4cG9ydGVkIGZ1bmN0aW9uIGV4dGVuZHMgYSBiYXNlIGNsYXNzIHdpdGggQXR0cmlidXRlTWFyc2hhbGxpbmcuICovXG5leHBvcnQgZGVmYXVsdCAoYmFzZSkgPT4ge1xuXG4gIC8qKlxuICAgKiBNaXhpbiB3aGljaCBtYXJzaGFsbHMgYXR0cmlidXRlcyB0byBwcm9wZXJ0aWVzIGFuZCB2aWNlIHZlcnNhLlxuICAgKlxuICAgKiBJZiB5b3VyIGNvbXBvbmVudCBleHBvc2VzIGEgc2V0dGVyIGZvciBhIHByb3BlcnR5LCBpdCdzIGdlbmVyYWxseSBhIGdvb2RcbiAgICogaWRlYSB0byBsZXQgZGV2cyB1c2luZyB5b3VyIGNvbXBvbmVudCBiZSBhYmxlIHRvIHNldCB0aGF0IHByb3BlcnR5IGluIEhUTUxcbiAgICogdmlhIGFuIGVsZW1lbnQgYXR0cmlidXRlLiBZb3UgY2FuIGNvZGUgdGhhdCB5b3Vyc2VsZiBieSB3cml0aW5nIGFuXG4gICAqIGBhdHRyaWJ1dGVDaGFuZ2VkQ2FsbGJhY2tgLCBvciB5b3UgY2FuIHVzZSB0aGlzIG1peGluIHRvIGdldCBhIGRlZ3JlZSBvZlxuICAgKiBhdXRvbWF0aWMgc3VwcG9ydC5cbiAgICpcbiAgICogVGhpcyBtaXhpbiBpbXBsZW1lbnRzIGFuIGBhdHRyaWJ1dGVDaGFuZ2VkQ2FsbGJhY2tgIHRoYXQgd2lsbCBhdHRlbXB0IHRvXG4gICAqIGNvbnZlcnQgYSBjaGFuZ2UgaW4gYW4gZWxlbWVudCBhdHRyaWJ1dGUgaW50byBhIGNhbGwgdG8gdGhlIGNvcnJlc3BvbmRpbmdcbiAgICogcHJvcGVydHkgc2V0dGVyLiBBdHRyaWJ1dGVzIHR5cGljYWxseSBmb2xsb3cgaHlwaGVuYXRlZCBuYW1lcyAoXCJmb28tYmFyXCIpLFxuICAgKiB3aGVyZWFzIHByb3BlcnRpZXMgdHlwaWNhbGx5IHVzZSBjYW1lbENhc2UgbmFtZXMgKFwiZm9vQmFyXCIpLiBUaGlzIG1peGluXG4gICAqIHJlc3BlY3RzIHRoYXQgY29udmVudGlvbiwgYXV0b21hdGljYWxseSBtYXBwaW5nIHRoZSBoeXBoZW5hdGVkIGF0dHJpYnV0ZVxuICAgKiBuYW1lIHRvIHRoZSBjb3JyZXNwb25kaW5nIGNhbWVsQ2FzZSBwcm9wZXJ0eSBuYW1lLlxuICAgKlxuICAgKiBFeGFtcGxlOiBZb3UgZGVmaW5lIGEgY29tcG9uZW50IHVzaW5nIHRoaXMgbWl4aW46XG4gICAqXG4gICAqICAgICBjbGFzcyBNeUVsZW1lbnQgZXh0ZW5kcyBBdHRyaWJ1dGVNYXJzaGFsbGluZ01peGluKEhUTUxFbGVtZW50KSB7XG4gICAqICAgICAgIGdldCBmb29CYXIoKSB7IHJldHVybiB0aGlzLl9mb29CYXI7IH1cbiAgICogICAgICAgc2V0IGZvb0Jhcih2YWx1ZSkgeyB0aGlzLl9mb29CYXIgPSB2YWx1ZTsgfVxuICAgKiAgICAgfVxuICAgKiAgICAgY3VzdG9tRWxlbWVudHMuZGVmaW5lKCdteS1lbGVtZW50JywgTXlFbGVtZW50KTtcbiAgICpcbiAgICogSWYgc29tZW9uZSB0aGVuIGluc3RhbnRpYXRlcyB5b3VyIGNvbXBvbmVudCBpbiBIVE1MOlxuICAgKlxuICAgKiAgICAgPG15LWVsZW1lbnQgZm9vLWJhcj1cIkhlbGxvXCI+PC9teS1lbGVtZW50PlxuICAgKlxuICAgKiBUaGVuLCBhZnRlciB0aGUgZWxlbWVudCBoYXMgYmVlbiB1cGdyYWRlZCwgdGhlIGBmb29CYXJgIHNldHRlciB3aWxsXG4gICAqIGF1dG9tYXRpY2FsbHkgYmUgaW52b2tlZCB3aXRoIHRoZSBpbml0aWFsIHZhbHVlIFwiSGVsbG9cIi5cbiAgICpcbiAgICogRm9yIHRoZSB0aW1lIGJlaW5nLCB0aGlzIG1peGluIG9ubHkgc3VwcG9ydHMgc3RyaW5nLXZhbHVlZCBwcm9wZXJ0aWVzLlxuICAgKiBJZiB5b3UnZCBsaWtlIHRvIGNvbnZlcnQgc3RyaW5nIGF0dHJpYnV0ZXMgdG8gb3RoZXIgdHlwZXMgKG51bWJlcnMsXG4gICAqIGJvb2xlYW5zKSwgeW91IG5lZWQgdG8gaW1wbGVtZW50IGBhdHRyaWJ1dGVDaGFuZ2VkQ2FsbGJhY2tgIHlvdXJzZWxmLlxuICAgKi9cbiAgY2xhc3MgQXR0cmlidXRlTWFyc2hhbGxpbmcgZXh0ZW5kcyBiYXNlIHtcblxuICAgIC8qXG4gICAgICogSGFuZGxlIGEgY2hhbmdlIHRvIHRoZSBhdHRyaWJ1dGUgd2l0aCB0aGUgZ2l2ZW4gbmFtZS5cbiAgICAgKi9cbiAgICBhdHRyaWJ1dGVDaGFuZ2VkQ2FsbGJhY2soYXR0cmlidXRlTmFtZSwgb2xkVmFsdWUsIG5ld1ZhbHVlKSB7XG4gICAgICBpZiAoc3VwZXIuYXR0cmlidXRlQ2hhbmdlZENhbGxiYWNrKSB7IHN1cGVyLmF0dHJpYnV0ZUNoYW5nZWRDYWxsYmFjaygpOyB9XG4gICAgICBjb25zdCBwcm9wZXJ0eU5hbWUgPSBhdHRyaWJ1dGVUb1Byb3BlcnR5TmFtZShhdHRyaWJ1dGVOYW1lKTtcbiAgICAgIC8vIElmIHRoZSBhdHRyaWJ1dGUgbmFtZSBjb3JyZXNwb25kcyB0byBhIHByb3BlcnR5IG5hbWUsIHNldCB0aGUgcHJvcGVydHkuXG4gICAgICAvLyBJZ25vcmUgc3RhbmRhcmQgSFRNTEVsZW1lbnQgcHJvcGVydGllcyBoYW5kbGVkIGJ5IHRoZSBET00uXG4gICAgICBpZiAocHJvcGVydHlOYW1lIGluIHRoaXMgJiYgIShwcm9wZXJ0eU5hbWUgaW4gSFRNTEVsZW1lbnQucHJvdG90eXBlKSkge1xuICAgICAgICB0aGlzW3Byb3BlcnR5TmFtZV0gPSBuZXdWYWx1ZTtcbiAgICAgIH1cbiAgICB9XG5cbiAgICBjb25uZWN0ZWRDYWxsYmFjaygpIHtcbiAgICAgIGlmIChzdXBlci5jb25uZWN0ZWRDYWxsYmFjaykgeyBzdXBlci5jb25uZWN0ZWRDYWxsYmFjaygpOyB9XG4gICAgICBzYWZlQXR0cmlidXRlcy5jb25uZWN0ZWQodGhpcyk7XG4gICAgfVxuXG4gICAgc3RhdGljIGdldCBvYnNlcnZlZEF0dHJpYnV0ZXMoKSB7XG4gICAgICByZXR1cm4gYXR0cmlidXRlc0ZvckNsYXNzKHRoaXMpO1xuICAgIH1cblxuICAgIC8qKlxuICAgICAqIFNldC91bnNldCB0aGUgYXR0cmlidXRlIHdpdGggdGhlIGluZGljYXRlZCBuYW1lLlxuICAgICAqXG4gICAgICogVGhpcyBtZXRob2QgZXhpc3RzIHByaW1hcmlseSB0byBoYW5kbGUgdGhlIGNhc2Ugd2hlcmUgYW4gZWxlbWVudCB3YW50cyB0b1xuICAgICAqIHNldCBhIGRlZmF1bHQgcHJvcGVydHkgdmFsdWUgdGhhdCBzaG91bGQgYmUgcmVmbGVjdGVkIGFzIGFuIGF0dHJpYnV0ZS4gQW5cbiAgICAgKiBpbXBvcnRhbnQgbGltaXRhdGlvbiBvZiBjdXN0b20gZWxlbWVudCBjb25zdHVyY3RvcnMgaXMgdGhhdCB0aGV5IGNhbm5vdFxuICAgICAqIHNldCBhdHRyaWJ1dGVzLiBBIGNhbGwgdG8gYHJlZmxlY3RBdHRyaWJ1dGVgIGR1cmluZyB0aGUgY29uc3RydWN0b3Igd2lsbFxuICAgICAqIGJlIGRlZmVycmVkIHVudGlsIHRoZSBlbGVtZW50IGlzIGNvbm5lY3RlZCB0byB0aGUgZG9jdW1lbnQuXG4gICAgICpcbiAgICAgKiBAcGFyYW0ge3N0cmluZ30gYXR0cmlidXRlIC0gVGhlIG5hbWUgb2YgdGhlICphdHRyaWJ1dGUqIChub3QgcHJvcGVydHkpIHRvIHNldC5cbiAgICAgKiBAcGFyYW0ge29iamVjdH0gdmFsdWUgLSBUaGUgdmFsdWUgdG8gc2V0LiBJZiBudWxsLCB0aGUgYXR0cmlidXRlIHdpbGwgYmUgcmVtb3ZlZC5cbiAgICAgKi9cbiAgICByZWZsZWN0QXR0cmlidXRlKGF0dHJpYnV0ZSwgdmFsdWUpIHtcbiAgICAgIHJldHVybiBzYWZlQXR0cmlidXRlcy5zZXRBdHRyaWJ1dGUodGhpcywgYXR0cmlidXRlLCB2YWx1ZSk7XG4gICAgfVxuXG4gICAgLyoqXG4gICAgICogU2V0L3Vuc2V0IHRoZSBjbGFzcyB3aXRoIHRoZSBpbmRpY2F0ZWQgbmFtZS5cbiAgICAgKlxuICAgICAqIFRoaXMgbWV0aG9kIGV4aXN0cyBwcmltYXJpbHkgdG8gaGFuZGxlIHRoZSBjYXNlIHdoZXJlIGFuIGVsZW1lbnQgd2FudHMgdG9cbiAgICAgKiBzZXQgYSBkZWZhdWx0IHByb3BlcnR5IHZhbHVlIHRoYXQgc2hvdWxkIGJlIHJlZmxlY3RlZCBhcyBhcyBjbGFzcy4gQW5cbiAgICAgKiBpbXBvcnRhbnQgbGltaXRhdGlvbiBvZiBjdXN0b20gZWxlbWVudCBjb25zdHVyY3RvcnMgaXMgdGhhdCB0aGV5IGNhbm5vdFxuICAgICAqIHNldCBhdHRyaWJ1dGVzLCBpbmNsdWRpbmcgdGhlIGBjbGFzc2AgYXR0cmlidXRlLiBBIGNhbGwgdG9cbiAgICAgKiBgcmVmbGVjdENsYXNzYCBkdXJpbmcgdGhlIGNvbnN0cnVjdG9yIHdpbGwgYmUgZGVmZXJyZWQgdW50aWwgdGhlIGVsZW1lbnRcbiAgICAgKiBpcyBjb25uZWN0ZWQgdG8gdGhlIGRvY3VtZW50LlxuICAgICAqXG4gICAgICogQHBhcmFtIHtzdHJpbmd9IGNsYXNzTmFtZSAtIFRoZSBuYW1lIG9mIHRoZSBjbGFzcyB0byBzZXQuXG4gICAgICogQHBhcmFtIHtvYmplY3R9IHZhbHVlIC0gVHJ1ZSB0byBzZXQgdGhlIGNsYXNzLCBmYWxzZSB0byByZW1vdmUgaXQuXG4gICAgICovXG4gICAgcmVmbGVjdENsYXNzKGNsYXNzTmFtZSwgdmFsdWUpIHtcbiAgICAgIHJldHVybiBzYWZlQXR0cmlidXRlcy50b2dnbGVDbGFzcyh0aGlzLCBjbGFzc05hbWUsIHZhbHVlKTtcbiAgICB9XG5cbiAgfVxuXG4gIHJldHVybiBBdHRyaWJ1dGVNYXJzaGFsbGluZztcbn07XG5cblxuLy8gQ29udmVydCBoeXBoZW5hdGVkIGZvby1iYXIgYXR0cmlidXRlIG5hbWUgdG8gY2FtZWwgY2FzZSBmb29CYXIgcHJvcGVydHkgbmFtZS5cbmZ1bmN0aW9uIGF0dHJpYnV0ZVRvUHJvcGVydHlOYW1lKGF0dHJpYnV0ZU5hbWUpIHtcbiAgbGV0IHByb3BlcnR5TmFtZSA9IGF0dHJpYnV0ZVRvUHJvcGVydHlOYW1lc1thdHRyaWJ1dGVOYW1lXTtcbiAgaWYgKCFwcm9wZXJ0eU5hbWUpIHtcbiAgICAvLyBDb252ZXJ0IGFuZCBtZW1vaXplLlxuICAgIGNvbnN0IGh5cGVuUmVnRXggPSAvLShbYS16XSkvZztcbiAgICBwcm9wZXJ0eU5hbWUgPSBhdHRyaWJ1dGVOYW1lLnJlcGxhY2UoaHlwZW5SZWdFeCxcbiAgICAgICAgbWF0Y2ggPT4gbWF0Y2hbMV0udG9VcHBlckNhc2UoKSk7XG4gICAgYXR0cmlidXRlVG9Qcm9wZXJ0eU5hbWVzW2F0dHJpYnV0ZU5hbWVdID0gcHJvcGVydHlOYW1lO1xuICB9XG4gIHJldHVybiBwcm9wZXJ0eU5hbWU7XG59XG5cbmZ1bmN0aW9uIGF0dHJpYnV0ZXNGb3JDbGFzcyhjbGFzc0ZuKSB7XG5cbiAgLy8gV2UgdHJlYXQgdGhlIGVsZW1lbnQgYmFzZSBjbGFzc2VzIGFzIGlmIHRoZXkgaGF2ZSBubyBhdHRyaWJ1dGVzLCBzaW5jZSB3ZVxuICAvLyBkb24ndCB3YW50IHRvIHJlY2VpdmUgYXR0cmlidXRlQ2hhbmdlZENhbGxiYWNrIGZvciB0aGVtLlxuICBpZiAoY2xhc3NGbiA9PT0gSFRNTEVsZW1lbnQgfHwgY2xhc3NGbiA9PT0gT2JqZWN0KSB7XG4gICAgcmV0dXJuIFtdO1xuICB9XG5cbiAgLy8gR2V0IGF0dHJpYnV0ZXMgZm9yIHBhcmVudCBjbGFzcy5cbiAgY29uc3QgYmFzZUNsYXNzID0gT2JqZWN0LmdldFByb3RvdHlwZU9mKGNsYXNzRm4ucHJvdG90eXBlKS5jb25zdHJ1Y3RvcjtcbiAgY29uc3QgYmFzZUF0dHJpYnV0ZXMgPSBhdHRyaWJ1dGVzRm9yQ2xhc3MoYmFzZUNsYXNzKTtcblxuICAvLyBHZXQgYXR0cmlidXRlcyBmb3IgdGhpcyBjbGFzcy5cbiAgY29uc3QgcHJvcGVydHlOYW1lcyA9IE9iamVjdC5nZXRPd25Qcm9wZXJ0eU5hbWVzKGNsYXNzRm4ucHJvdG90eXBlKTtcbiAgY29uc3Qgc2V0dGVyTmFtZXMgPSBwcm9wZXJ0eU5hbWVzLmZpbHRlcihwcm9wZXJ0eU5hbWUgPT5cbiAgICB0eXBlb2YgT2JqZWN0LmdldE93blByb3BlcnR5RGVzY3JpcHRvcihcbiAgICAgICAgY2xhc3NGbi5wcm90b3R5cGUsIHByb3BlcnR5TmFtZSkuc2V0ID09PSAnZnVuY3Rpb24nKTtcbiAgY29uc3QgYXR0cmlidXRlcyA9IHNldHRlck5hbWVzLm1hcChzZXR0ZXJOYW1lID0+XG4gICAgICBwcm9wZXJ0eU5hbWVUb0F0dHJpYnV0ZShzZXR0ZXJOYW1lKSk7XG5cbiAgLy8gTWVyZ2UuXG4gIGNvbnN0IGRpZmYgPSBhdHRyaWJ1dGVzLmZpbHRlcihhdHRyaWJ1dGUgPT5cbiAgICAgIGJhc2VBdHRyaWJ1dGVzLmluZGV4T2YoYXR0cmlidXRlKSA8IDApO1xuICByZXR1cm4gYmFzZUF0dHJpYnV0ZXMuY29uY2F0KGRpZmYpO1xufVxuXG4vLyBDb252ZXJ0IGEgY2FtZWwgY2FzZSBmb29CYXIgcHJvcGVydHkgbmFtZSB0byBhIGh5cGhlbmF0ZWQgZm9vLWJhciBhdHRyaWJ1dGUuXG5mdW5jdGlvbiBwcm9wZXJ0eU5hbWVUb0F0dHJpYnV0ZShwcm9wZXJ0eU5hbWUpIHtcbiAgbGV0IGF0dHJpYnV0ZSA9IHByb3BlcnR5TmFtZXNUb0F0dHJpYnV0ZXNbcHJvcGVydHlOYW1lXTtcbiAgaWYgKCFhdHRyaWJ1dGUpIHtcbiAgICAvLyBDb252ZXJ0IGFuZCBtZW1vaXplLlxuICAgIGNvbnN0IHVwcGVyY2FzZVJlZ0V4ID0gLyhbQS1aXSkvZztcbiAgICBhdHRyaWJ1dGUgPSBwcm9wZXJ0eU5hbWUucmVwbGFjZSh1cHBlcmNhc2VSZWdFeCwgJy0kMScpLnRvTG93ZXJDYXNlKCk7XG4gIH1cbiAgcmV0dXJuIGF0dHJpYnV0ZTtcbn1cbiIsIi8qIEV4cG9ydGVkIGZ1bmN0aW9uIGV4dGVuZHMgYSBiYXNlIGNsYXNzIHdpdGggQ29tcG9zYWJsZS4gKi9cbmV4cG9ydCBkZWZhdWx0IChiYXNlKSA9PiB7XG5cbiAgLyoqXG4gICAqIE1peGluIHRvIG1ha2UgYSBjbGFzcyBtb3JlIGVhc2lseSBjb21wb3NhYmxlIHdpdGggb3RoZXIgbWl4aW5zLlxuICAgKlxuICAgKiBUaGlzIG1peGluIGNvbnRyaWJ1dGVzIGEgYGNvbXBvc2VgIG1ldGhvZCB0aGF0IGFwcGxpZXMgYSBzZXQgb2YgbWl4aW5cbiAgICogZnVuY3Rpb25zIGFuZCByZXR1cm5zIHRoZSByZXN1bHRpbmcgbmV3IGNsYXNzLiBUaGlzIHN1Z2FyIGNhbiBtYWtlIHRoZVxuICAgKiBhcHBsaWNhdGlvbiBvZiBtYW55IG1peGlucyBhdCBvbmNlIGVhc2llciB0byByZWFkLlxuICAgKi9cbiAgY2xhc3MgQ29tcG9zYWJsZSBleHRlbmRzIGJhc2Uge1xuXG4gICAgLyoqXG4gICAgICogQXBwbHkgYSBzZXQgb2YgbWl4aW4gZnVuY3Rpb25zIG9yIG1peGluIG9iamVjdHMgdG8gdGhlIHByZXNlbnQgY2xhc3MgYW5kXG4gICAgICogcmV0dXJuIHRoZSBuZXcgY2xhc3MuXG4gICAgICpcbiAgICAgKiBJbnN0ZWFkIG9mIHdyaXRpbmc6XG4gICAgICpcbiAgICAgKiAgICAgbGV0IE15Q2xhc3MgPSBNaXhpbjEoTWl4aW4yKE1peGluMyhNaXhpbjQoTWl4aW41KEJhc2VDbGFzcykpKSkpO1xuICAgICAqXG4gICAgICogWW91IGNhbiB3cml0ZTpcbiAgICAgKlxuICAgICAqICAgICBsZXQgTXlDbGFzcyA9IENvbXBvc2FibGVNaXhpbihCYXNlQ2xhc3MpLmNvbXBvc2UoXG4gICAgICogICAgICAgTWl4aW4xLFxuICAgICAqICAgICAgIE1peGluMixcbiAgICAgKiAgICAgICBNaXhpbjMsXG4gICAgICogICAgICAgTWl4aW40LFxuICAgICAqICAgICAgIE1peGluNVxuICAgICAqICAgICApO1xuICAgICAqXG4gICAgICogVGhpcyBmdW5jdGlvbiBjYW4gYWxzbyB0YWtlIG1peGluIG9iamVjdHMuIEEgbWl4aW4gb2JqZWN0IGlzIGp1c3QgYVxuICAgICAqIHNob3J0aGFuZCBmb3IgYSBtaXhpbiBmdW5jdGlvbiB0aGF0IGNyZWF0ZXMgYSBuZXcgc3ViY2xhc3Mgd2l0aCB0aGUgZ2l2ZW5cbiAgICAgKiBtZW1iZXJzLiBUaGUgbWl4aW4gb2JqZWN0J3MgbWVtYmVycyBhcmUgKm5vdCogY29waWVkIGRpcmVjdGx5IG9udG8gdGhlXG4gICAgICogcHJvdG90eXBlIG9mIHRoZSBiYXNlIGNsYXNzLCBhcyB3aXRoIHRyYWRpdGlvbmFsIG1peGlucy5cbiAgICAgKlxuICAgICAqIEluIGFkZGl0aW9uIHRvIHByb3ZpZGluZyBzeW50YWN0aWMgc3VnYXIsIHRoaXMgbWl4aW4gY2FuIGJlIHVzZWQgdG9cbiAgICAgKiBkZWZpbmUgYSBjbGFzcyBpbiBFUzUsIHdoaWNoIGxhY2tzIEVTNidzIGBjbGFzc2Aga2V5d29yZC5cbiAgICAgKlxuICAgICAqIEBwYXJhbSB7Li4ubWl4aW5zfSBtaXhpbnMgLSBBIHNldCBvZiBtaXhpbiBmdW5jdGlvbnMgb3Igb2JqZWN0cyB0byBhcHBseS5cbiAgICAgKi9cbiAgICBzdGF0aWMgY29tcG9zZSguLi5taXhpbnMpIHtcbiAgICAgIC8vIFdlIGNyZWF0ZSBhIG5ldyBzdWJjbGFzcyBmb3IgZWFjaCBtaXhpbiBpbiB0dXJuLiBUaGUgcmVzdWx0IGJlY29tZXNcbiAgICAgIC8vIHRoZSBiYXNlIGNsYXNzIGV4dGVuZGVkIGJ5IGFueSBzdWJzZXF1ZW50IG1peGlucy4gSXQgdHVybnMgb3V0IHRoYXRcbiAgICAgIC8vIHdlIGNhbiB1c2UgQXJyYXkucmVkdWNlKCkgdG8gY29uY2lzZWx5IGV4cHJlc3MgdGhpcywgdXNpbmcgdGhlIGN1cnJlbnRcbiAgICAgIC8vIG9iamVjdCBhcyB0aGUgc2VlZCBmb3IgcmVkdWNlKCkuXG4gICAgICByZXR1cm4gbWl4aW5zLnJlZHVjZShjb21wb3NlQ2xhc3MsIHRoaXMpO1xuICAgIH1cblxuICB9XG5cbiAgcmV0dXJuIENvbXBvc2FibGU7XG59O1xuXG5cbi8vIFByb3BlcnRpZXMgZGVmaW5lZCBieSBPYmplY3QgdGhhdCB3ZSBkb24ndCB3YW50IHRvIG1peGluLlxuY29uc3QgTk9OX01JWEFCTEVfT0JKRUNUX1BST1BFUlRJRVMgPSBbXG4gICdjb25zdHJ1Y3Rvcidcbl07XG5cbi8qXG4gKiBBcHBseSB0aGUgbWl4aW4gdG8gdGhlIGdpdmVuIGJhc2UgY2xhc3MgdG8gcmV0dXJuIGEgbmV3IGNsYXNzLlxuICogVGhlIG1peGluIGNhbiBlaXRoZXIgYmUgYSBmdW5jdGlvbiB0aGF0IHJldHVybnMgdGhlIG1vZGlmaWVkIGNsYXNzLCBvciBhXG4gKiBwbGFpbiBvYmplY3Qgd2hvc2UgbWVtYmVycyB3aWxsIGJlIGNvcGllZCB0byB0aGUgbmV3IGNsYXNzJyBwcm90b3R5cGUuXG4gKi9cbmZ1bmN0aW9uIGNvbXBvc2VDbGFzcyhiYXNlLCBtaXhpbikge1xuICBpZiAodHlwZW9mIG1peGluID09PSAnZnVuY3Rpb24nKSB7XG4gICAgLy8gTWl4aW4gZnVuY3Rpb25cbiAgICByZXR1cm4gbWl4aW4oYmFzZSk7XG4gIH0gZWxzZSB7XG4gICAgLy8gTWl4aW4gb2JqZWN0XG4gICAgY2xhc3MgU3ViY2xhc3MgZXh0ZW5kcyBiYXNlIHt9XG4gICAgY29weU93blByb3BlcnRpZXMobWl4aW4sIFN1YmNsYXNzLnByb3RvdHlwZSwgTk9OX01JWEFCTEVfT0JKRUNUX1BST1BFUlRJRVMpO1xuICAgIHJldHVybiBTdWJjbGFzcztcbiAgfVxufVxuXG5cbi8qXG4gKiBDb3B5IHRoZSBnaXZlbiBwcm9wZXJ0aWVzL21ldGhvZHMgdG8gdGhlIHRhcmdldC5cbiAqIFJldHVybiB0aGUgdXBkYXRlZCB0YXJnZXQuXG4gKi9cbmZ1bmN0aW9uIGNvcHlPd25Qcm9wZXJ0aWVzKHNvdXJjZSwgdGFyZ2V0LCBpZ25vcmVQcm9wZXJ0eU5hbWVzID0gW10pIHtcbiAgT2JqZWN0LmdldE93blByb3BlcnR5TmFtZXMoc291cmNlKS5mb3JFYWNoKG5hbWUgPT4ge1xuICAgIGlmIChpZ25vcmVQcm9wZXJ0eU5hbWVzLmluZGV4T2YobmFtZSkgPCAwKSB7XG4gICAgICBjb25zdCBkZXNjcmlwdG9yID0gT2JqZWN0LmdldE93blByb3BlcnR5RGVzY3JpcHRvcihzb3VyY2UsIG5hbWUpO1xuICAgICAgT2JqZWN0LmRlZmluZVByb3BlcnR5KHRhcmdldCwgbmFtZSwgZGVzY3JpcHRvcik7XG4gICAgfVxuICB9KTtcbiAgcmV0dXJuIHRhcmdldDtcbn1cbiIsIi8qIEV4cG9ydGVkIGZ1bmN0aW9uIGV4dGVuZHMgYSBiYXNlIGNsYXNzIHdpdGggRGlzdHJpYnV0ZWRDaGlsZHJlbi4gKi9cbmV4cG9ydCBkZWZhdWx0IChiYXNlKSA9PiB7XG5cbiAgLyoqXG4gICAqIE1peGluIHdoaWNoIGRlZmluZXMgaGVscGVycyBmb3IgYWNjZXNzaW5nIGEgY29tcG9uZW50J3MgZGlzdHJpYnV0ZWRcbiAgICogY2hpbGRyZW4gYXMgYSBmbGF0dGVuZWQgYXJyYXkgb3Igc3RyaW5nLlxuICAgKlxuICAgKiBUaGUgc3RhbmRhcmQgRE9NIEFQSSBwcm92aWRlcyBzZXZlcmFsIHdheXMgb2YgYWNjZXNzaW5nIGNoaWxkIGNvbnRlbnQ6XG4gICAqIGBjaGlsZHJlbmAsIGBjaGlsZE5vZGVzYCwgYW5kIGB0ZXh0Q29udGVudGAuIE5vbmUgb2YgdGhlc2UgZnVuY3Rpb25zIGFyZVxuICAgKiBTaGFkb3cgRE9NIGF3YXJlLiBUaGlzIG1peGluIGRlZmluZXMgdmFyaWF0aW9ucyBvZiB0aG9zZSBmdW5jdGlvbnMgdGhhdFxuICAgKiAqYXJlKiBTaGFkb3cgRE9NIGF3YXJlLlxuICAgKlxuICAgKiBFeGFtcGxlOiB5b3UgY3JlYXRlIGEgY29tcG9uZW50IGA8Y291bnQtY2hpbGRyZW4+YCB0aGF0IGRpc3BsYXlzIGEgbnVtYmVyXG4gICAqIGVxdWFsIHRvIHRoZSBudW1iZXIgb2YgY2hpbGRyZW4gcGxhY2VkIGluc2lkZSB0aGF0IGNvbXBvbmVudC4gSWYgc29tZW9uZVxuICAgKiBpbnN0YW50aWF0ZXMgeW91ciBjb21wb25lbnQgbGlrZTpcbiAgICpcbiAgICogICAgIDxjb3VudC1jaGlsZHJlbj5cbiAgICogICAgICAgPGRpdj48L2Rpdj5cbiAgICogICAgICAgPGRpdj48L2Rpdj5cbiAgICogICAgICAgPGRpdj48L2Rpdj5cbiAgICogICAgIDwvY291bnQtY2hpbGRyZW4+XG4gICAqXG4gICAqIFRoZW4gdGhlIGNvbXBvbmVudCBzaG91bGQgc2hvdyBcIjNcIiwgYmVjYXVzZSB0aGVyZSBhcmUgdGhyZWUgY2hpbGRyZW4uIFRvXG4gICAqIGNhbGN1bGF0ZSB0aGUgbnVtYmVyIG9mIGNoaWxkcmVuLCB0aGUgY29tcG9uZW50IGNhbiBqdXN0IGNhbGN1bGF0ZVxuICAgKiBgdGhpcy5jaGlsZHJlbi5sZW5ndGhgLiBIb3dldmVyLCBzdXBwb3NlIHNvbWVvbmUgaW5zdGFudGlhdGVzIHlvdXJcbiAgICogY29tcG9uZW50IGluc2lkZSBvbmUgb2YgdGhlaXIgb3duIGNvbXBvbmVudHMsIGFuZCBwdXRzIGEgYDxzbG90PmAgZWxlbWVudFxuICAgKiBpbnNpZGUgeW91ciBjb21wb25lbnQ6XG4gICAqXG4gICAqICAgICA8Y291bnQtY2hpbGRyZW4+XG4gICAqICAgICAgIDxzbG90Pjwvc2xvdD5cbiAgICogICAgIDwvY291bnQtY2hpbGRyZW4+XG4gICAqXG4gICAqIElmIHlvdXIgY29tcG9uZW50IG9ubHkgbG9va3MgYXQgYHRoaXMuY2hpbGRyZW5gLCBpdCB3aWxsIGFsd2F5cyBzZWUgZXhhY3RseVxuICAgKiBvbmUgY2hpbGQg4oCUwqB0aGUgYDxzbG90PmAgZWxlbWVudC4gQnV0IHRoZSB1c2VyIGxvb2tpbmcgYXQgdGhlIHBhZ2Ugd2lsbFxuICAgKiAqc2VlKiBhbnkgbm9kZXMgZGlzdHJpYnV0ZWQgdG8gdGhhdCBzbG90LiBUbyBtYXRjaCB3aGF0IHRoZSB1c2VyIHNlZXMsIHlvdXJcbiAgICogY29tcG9uZW50IHNob3VsZCBleHBhbmQgYW55IGA8c2xvdD5gIGVsZW1lbnRzIGl0IGNvbnRhaW5zLlxuICAgKlxuICAgKiBUaGF0IGlzIHRoZSBwcm9ibGVtIHRoaXMgbWl4aW4gc29sdmVzLiBBZnRlciBhcHBseWluZyB0aGlzIG1peGluLCB5b3VyXG4gICAqIGNvbXBvbmVudCBjb2RlIGhhcyBhY2Nlc3MgdG8gYHRoaXMuZGlzdHJpYnV0ZWRDaGlsZHJlbmAsIHdob3NlIGBsZW5ndGhgXG4gICAqIHdpbGwgcmV0dXJuIHRoZSB0b3RhbCBudW1iZXIgb2YgYWxsIGNoaWxkcmVuIGRpc3RyaWJ1dGVkIHRvIHlvdXIgY29tcG9uZW50XG4gICAqIGluIHRoZSBjb21wb3NlZCB0cmVlLlxuICAgKlxuICAgKiBOb3RlOiBUaGUgbGF0ZXN0IEN1c3RvbSBFbGVtZW50cyBBUEkgZGVzaWduIGNhbGxzIGZvciBhIG5ldyBmdW5jdGlvbixcbiAgICogYGdldEFzc2lnbmVkTm9kZXNgIHRoYXQgdGFrZXMgYW4gb3B0aW9uYWwgYGRlZXBgIHBhcmFtZXRlciwgdGhhdCB3aWxsIHNvbHZlXG4gICAqIHRoaXMgcHJvYmxlbSBhdCB0aGUgQVBJIGxldmVsLlxuICAgKi9cbiAgY2xhc3MgRGlzdHJpYnV0ZWRDaGlsZHJlbiBleHRlbmRzIGJhc2Uge1xuXG4gICAgLyoqXG4gICAgICogQW4gaW4tb3JkZXIgY29sbGVjdGlvbiBvZiBkaXN0cmlidXRlZCBjaGlsZHJlbiwgZXhwYW5kaW5nIGFueSBzbG90XG4gICAgICogZWxlbWVudHMuIExpa2UgdGhlIHN0YW5kYXJkIGNoaWxkcmVuIHByb3BlcnR5LCB0aGlzIHNraXBzIHRleHQgbm9kZXMuXG4gICAgICpcbiAgICAgKiBAdHlwZSB7SFRNTEVsZW1lbnRbXX1cbiAgICAgKi9cbiAgICBnZXQgZGlzdHJpYnV0ZWRDaGlsZHJlbigpIHtcbiAgICAgIHJldHVybiBleHBhbmRDb250ZW50RWxlbWVudHModGhpcy5jaGlsZHJlbiwgZmFsc2UpO1xuICAgIH1cblxuICAgIC8qKlxuICAgICAqIEFuIGluLW9yZGVyIGNvbGxlY3Rpb24gb2YgZGlzdHJpYnV0ZWQgY2hpbGQgbm9kZXMsIGV4cGFuZGluZyBhbnkgc2xvdFxuICAgICAqIGVsZW1lbnRzLiBMaWtlIHRoZSBzdGFuZGFyZCBjaGlsZE5vZGVzIHByb3BlcnR5LCB0aGlzIGluY2x1ZGVzIHRleHRcbiAgICAgKiBub2Rlcy5cbiAgICAgKlxuICAgICAqIEB0eXBlIHtOb2RlW119XG4gICAgICovXG4gICAgZ2V0IGRpc3RyaWJ1dGVkQ2hpbGROb2RlcygpIHtcbiAgICAgIHJldHVybiBleHBhbmRDb250ZW50RWxlbWVudHModGhpcy5jaGlsZE5vZGVzLCB0cnVlKTtcbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBUaGUgY29uY2F0ZW5hdGVkIHRleHQgY29udGVudCBvZiBhbGwgZGlzdHJpYnV0ZWQgY2hpbGQgbm9kZXMsIGV4cGFuZGluZ1xuICAgICAqIGFueSBzbG90IGVsZW1lbnRzLlxuICAgICAqXG4gICAgICogQHR5cGUge3N0cmluZ31cbiAgICAgKi9cbiAgICBnZXQgZGlzdHJpYnV0ZWRUZXh0Q29udGVudCgpIHtcbiAgICAgIGNvbnN0IHN0cmluZ3MgPSB0aGlzLmRpc3RyaWJ1dGVkQ2hpbGROb2Rlcy5tYXAoZnVuY3Rpb24oY2hpbGQpIHtcbiAgICAgICAgcmV0dXJuIGNoaWxkLnRleHRDb250ZW50O1xuICAgICAgfSk7XG4gICAgICByZXR1cm4gc3RyaW5ncy5qb2luKCcnKTtcbiAgICB9XG5cbiAgfVxuXG4gIHJldHVybiBEaXN0cmlidXRlZENoaWxkcmVuO1xufTtcblxuXG4vKlxuICogR2l2ZW4gYSBhcnJheSBvZiBub2RlcywgcmV0dXJuIGEgbmV3IGFycmF5IHdpdGggYW55IGNvbnRlbnQgZWxlbWVudHMgZXhwYW5kZWRcbiAqIHRvIHRoZSBub2RlcyBkaXN0cmlidXRlZCB0byB0aGF0IGNvbnRlbnQgZWxlbWVudC4gVGhpcyBydWxlIGlzIGFwcGxpZWRcbiAqIHJlY3Vyc2l2ZWx5LlxuICpcbiAqIElmIGluY2x1ZGVUZXh0Tm9kZXMgaXMgdHJ1ZSwgdGV4dCBub2RlcyB3aWxsIGJlIGluY2x1ZGVkLCBhcyBpbiB0aGVcbiAqIHN0YW5kYXJkIGNoaWxkTm9kZXMgcHJvcGVydHk7IGJ5IGRlZmF1bHQsIHRoaXMgc2tpcHMgdGV4dCBub2RlcywgbGlrZSB0aGVcbiAqIHN0YW5kYXJkIGNoaWxkcmVuIHByb3BlcnR5LlxuICovXG5mdW5jdGlvbiBleHBhbmRDb250ZW50RWxlbWVudHMobm9kZXMsIGluY2x1ZGVUZXh0Tm9kZXMpIHtcbiAgY29uc3QgZXhwYW5kZWQgPSBBcnJheS5wcm90b3R5cGUubWFwLmNhbGwobm9kZXMsIG5vZGUgPT4ge1xuICAgIC8vIFdlIHdhbnQgdG8gc2VlIGlmIHRoZSBub2RlIGlzIGFuIGluc3RhbmNlb2YgSFRNTFNsb3RFTGVtZW50LCBidXRcbiAgICAvLyB0aGF0IGNsYXNzIHdvbid0IGV4aXN0IGlmIHRoZSBicm93c2VyIHRoYXQgZG9lc24ndCBzdXBwb3J0IG5hdGl2ZVxuICAgIC8vIFNoYWRvdyBET00gYW5kIGlmIHRoZSBTaGFkb3cgRE9NIHBvbHlmaWxsIGhhc24ndCBiZWVuIGxvYWRlZC4gSW5zdGVhZCxcbiAgICAvLyB3ZSBkbyBhIHNpbXBsaXN0aWMgY2hlY2sgdG8gc2VlIGlmIHRoZSB0YWcgbmFtZSBpcyBcInNsb3RcIi5cbiAgICBjb25zdCBpc1Nsb3QgPSB0eXBlb2YgSFRNTFNsb3RFbGVtZW50ICE9PSAndW5kZWZpbmVkJyA/XG4gICAgICBub2RlIGluc3RhbmNlb2YgSFRNTFNsb3RFbGVtZW50IDpcbiAgICAgIG5vZGUubG9jYWxOYW1lID09PSAnc2xvdCc7XG4gICAgaWYgKGlzU2xvdCkge1xuICAgICAgLy8gVXNlIHRoZSBub2RlcyBhc3NpZ25lZCB0byB0aGlzIG5vZGUgaW5zdGVhZC5cbiAgICAgIGNvbnN0IGFzc2lnbmVkTm9kZXMgPSBub2RlLmFzc2lnbmVkTm9kZXMoeyBmbGF0dGVuOiB0cnVlIH0pO1xuICAgICAgcmV0dXJuIGFzc2lnbmVkTm9kZXMgP1xuICAgICAgICBleHBhbmRDb250ZW50RWxlbWVudHMoYXNzaWduZWROb2RlcywgaW5jbHVkZVRleHROb2RlcykgOlxuICAgICAgICBbXTtcbiAgICB9IGVsc2UgaWYgKG5vZGUgaW5zdGFuY2VvZiBIVE1MRWxlbWVudCkge1xuICAgICAgLy8gUGxhaW4gZWxlbWVudDsgdXNlIGFzIGlzLlxuICAgICAgcmV0dXJuIFtub2RlXTtcbiAgICB9IGVsc2UgaWYgKG5vZGUgaW5zdGFuY2VvZiBUZXh0ICYmIGluY2x1ZGVUZXh0Tm9kZXMpIHtcbiAgICAgIC8vIFRleHQgbm9kZS5cbiAgICAgIHJldHVybiBbbm9kZV07XG4gICAgfSBlbHNlIHtcbiAgICAgIC8vIENvbW1lbnQsIHByb2Nlc3NpbmcgaW5zdHJ1Y3Rpb24sIGV0Yy47IHNraXAuXG4gICAgICByZXR1cm4gW107XG4gICAgfVxuICB9KTtcbiAgY29uc3QgZmxhdHRlbmVkID0gW10uY29uY2F0KC4uLmV4cGFuZGVkKTtcbiAgcmV0dXJuIGZsYXR0ZW5lZDtcbn1cbiIsIi8qIEV4cG9ydGVkIGZ1bmN0aW9uIGV4dGVuZHMgYSBiYXNlIGNsYXNzIHdpdGggU2hhZG93RWxlbWVudFJlZmVyZW5jZXMuICovXG5leHBvcnQgZGVmYXVsdCAoYmFzZSkgPT4ge1xuXG4gIC8qKlxuICAgKiBNaXhpbiB0byBjcmVhdGUgcmVmZXJlbmNlcyB0byBlbGVtZW50cyBpbiBhIGNvbXBvbmVudCdzIFNoYWRvdyBET00gc3VidHJlZS5cbiAgICpcbiAgICogVGhpcyBhZGRzIGEgbWVtYmVyIG9uIHRoZSBjb21wb25lbnQgY2FsbGVkIGB0aGlzLiRgIHRoYXQgY2FuIGJlIHVzZWQgdG9cbiAgICogcmVmZXJlbmNlIHNoYWRvdyBlbGVtZW50cyB3aXRoIElEcy4gRS5nLiwgaWYgY29tcG9uZW50J3Mgc2hhZG93IGNvbnRhaW5zIGFuXG4gICAqIGVsZW1lbnQgYDxidXR0b24gaWQ9XCJmb29cIj5gLCB0aGVuIHRoaXMgbWl4aW4gd2lsbCBjcmVhdGUgYSBtZW1iZXJcbiAgICogYHRoaXMuJC5mb29gIHRoYXQgcG9pbnRzIHRvIHRoYXQgYnV0dG9uLlxuICAgKlxuICAgKiBTdWNoIHJlZmVyZW5jZXMgc2ltcGxpZnkgYSBjb21wb25lbnQncyBhY2Nlc3MgdG8gaXRzIG93biBlbGVtZW50cy4gSW5cbiAgICogZXhjaGFuZ2UsIHRoaXMgbWl4aW4gdHJhZGVzIG9mZiBhIG9uZS10aW1lIGNvc3Qgb2YgcXVlcnlpbmcgYWxsIGVsZW1lbnRzIGluXG4gICAqIHRoZSBzaGFkb3cgdHJlZSBpbnN0ZWFkIG9mIHBheWluZyBhbiBvbmdvaW5nIGNvc3QgdG8gcXVlcnkgZm9yIGFuIGVsZW1lbnRcbiAgICogZWFjaCB0aW1lIHRoZSBjb21wb25lbnQgd2FudHMgdG8gaW5zcGVjdCBvciBtYW5pcHVsYXRlIGl0LlxuICAgKlxuICAgKiBUaGlzIG1peGluIGV4cGVjdHMgdGhlIGNvbXBvbmVudCB0byBkZWZpbmUgYSBTaGFkb3cgRE9NIHN1YnRyZWUuIFlvdSBjYW5cbiAgICogY3JlYXRlIHRoYXQgdHJlZSB5b3Vyc2VsZiwgb3IgbWFrZSB1c2Ugb2ZcbiAgICogW1NoYWRvd1RlbXBsYXRlTWl4aW5dKFNoYWRvd1RlbXBsYXRlTWl4aW4ubWQpLlxuICAgKlxuICAgKiBUaGlzIG1peGluIGlzIGluc3BpcmVkIGJ5IFBvbHltZXIncyBbYXV0b21hdGljXG4gICAqIG5vZGUgZmluZGluZ10oaHR0cHM6Ly93d3cucG9seW1lci1wcm9qZWN0Lm9yZy8xLjAvZG9jcy9kZXZndWlkZS9sb2NhbC1kb20uaHRtbCNub2RlLWZpbmRpbmcpXG4gICAqIGZlYXR1cmUuXG4gICAqL1xuICBjbGFzcyBTaGFkb3dFbGVtZW50UmVmZXJlbmNlcyBleHRlbmRzIGJhc2Uge1xuXG4gICAgY29uc3RydWN0b3IoKSB7XG4gICAgICBzdXBlcigpO1xuICAgICAgaWYgKHRoaXMuc2hhZG93Um9vdCkge1xuICAgICAgICAvLyBMb29rIGZvciBlbGVtZW50cyBpbiB0aGUgc2hhZG93IHN1YnRyZWUgdGhhdCBoYXZlIGlkIGF0dHJpYnV0ZXMuXG4gICAgICAgIC8vIEFuIGFsdGVybmF0aXZlbHkgaW1wbGVtZW50YXRpb24gb2YgdGhpcyBtaXhpbiB3b3VsZCBiZSB0byBqdXN0IGRlZmluZVxuICAgICAgICAvLyBhIHRoaXMuJCBnZXR0ZXIgdGhhdCBsYXppbHkgZG9lcyB0aGlzIHNlYXJjaCB0aGUgZmlyc3QgdGltZSBzb21lb25lXG4gICAgICAgIC8vIHRyaWVzIHRvIGFjY2VzcyB0aGlzLiQuIFRoYXQgbWlnaHQgaW50cm9kdWNlIHNvbWUgY29tcGxleGl0eSDigJMgaWYgdGhlXG4gICAgICAgIC8vIHRoZSB0cmVlIGNoYW5nZWQgYWZ0ZXIgaXQgd2FzIGZpcnN0IHBvcHVsYXRlZCwgdGhlIHJlc3VsdCBvZlxuICAgICAgICAvLyBzZWFyY2hpbmcgZm9yIGEgbm9kZSBtaWdodCBiZSBzb21ld2hhdCB1bnByZWRpY3RhYmxlLlxuICAgICAgICB0aGlzLiQgPSB7fTtcbiAgICAgICAgY29uc3Qgbm9kZXNXaXRoSWRzID0gdGhpcy5zaGFkb3dSb290LnF1ZXJ5U2VsZWN0b3JBbGwoJ1tpZF0nKTtcbiAgICAgICAgW10uZm9yRWFjaC5jYWxsKG5vZGVzV2l0aElkcywgbm9kZSA9PiB7XG4gICAgICAgICAgY29uc3QgaWQgPSBub2RlLmdldEF0dHJpYnV0ZSgnaWQnKTtcbiAgICAgICAgICB0aGlzLiRbaWRdID0gbm9kZTtcbiAgICAgICAgfSk7XG4gICAgICB9XG4gICAgfVxuXG4gICAgLyoqXG4gICAgICogVGhlIGNvbGxlY3Rpb24gb2YgcmVmZXJlbmNlcyB0byB0aGUgZWxlbWVudHMgd2l0aCBJRHMgaW4gYSBjb21wb25lbnQnc1xuICAgICAqIFNoYWRvdyBET00gc3VidHJlZS5cbiAgICAgKlxuICAgICAqIEB0eXBlIHtvYmplY3R9XG4gICAgICogQG1lbWJlciAkXG4gICAgICovXG4gIH1cblxuICByZXR1cm4gU2hhZG93RWxlbWVudFJlZmVyZW5jZXM7XG59O1xuIiwiaW1wb3J0IHN5bWJvbHMgZnJvbSAnLi4vc3JjL3N5bWJvbHMnO1xuXG5cbi8qIEV4cG9ydGVkIGZ1bmN0aW9uIGV4dGVuZHMgYSBiYXNlIGNsYXNzIHdpdGggU2hhZG93VGVtcGxhdGUuICovXG5leHBvcnQgZGVmYXVsdCAoYmFzZSkgPT4ge1xuXG4gIC8qKlxuICAgKiBNaXhpbiBmb3Igc3RhbXBpbmcgYSB0ZW1wbGF0ZSBpbnRvIGEgU2hhZG93IERPTSBzdWJ0cmVlIHVwb24gY29tcG9uZW50XG4gICAqIGluc3RhbnRpYXRpb24uXG4gICAqXG4gICAqIFRvIHVzZSB0aGlzIG1peGluLCBkZWZpbmUgYSBgdGVtcGxhdGVgIHByb3BlcnR5IGFzIGEgc3RyaW5nIG9yIEhUTUxcbiAgICogYDx0ZW1wbGF0ZT5gIGVsZW1lbnQ6XG4gICAqXG4gICAqICAgICBjbGFzcyBNeUVsZW1lbnQgZXh0ZW5kcyBTaGFkb3dUZW1wbGF0ZU1peGluKEhUTUxFbGVtZW50KSB7XG4gICAqICAgICAgIGdldCBbc3ltYm9scy50ZW1wbGF0ZV0oKSB7XG4gICAqICAgICAgICAgcmV0dXJuIGBIZWxsbywgPGVtPndvcmxkPC9lbT4uYDtcbiAgICogICAgICAgfVxuICAgKiAgICAgfVxuICAgKlxuICAgKiBXaGVuIHlvdXIgY29tcG9uZW50IGNsYXNzIGlzIGluc3RhbnRpYXRlZCwgYSBzaGFkb3cgcm9vdCB3aWxsIGJlIGNyZWF0ZWQgb25cbiAgICogdGhlIGluc3RhbmNlLCBhbmQgdGhlIGNvbnRlbnRzIG9mIHRoZSB0ZW1wbGF0ZSB3aWxsIGJlIGNsb25lZCBpbnRvIHRoZVxuICAgKiBzaGFkb3cgcm9vdC4gSWYgeW91ciBjb21wb25lbnQgZG9lcyBub3QgZGVmaW5lIGEgYHRlbXBsYXRlYCBwcm9wZXJ0eSwgdGhpc1xuICAgKiBtaXhpbiBoYXMgbm8gZWZmZWN0LlxuICAgKlxuICAgKiBGb3IgdGhlIHRpbWUgYmVpbmcsIHRoaXMgZXh0ZW5zaW9uIHJldGFpbnMgc3VwcG9ydCBmb3IgU2hhZG93IERPTSB2MC4gVGhhdFxuICAgKiB3aWxsIGV2ZW50dWFsbHkgYmUgZGVwcmVjYXRlZCBhcyBicm93c2VycyAoYW5kIHRoZSBTaGFkb3cgRE9NIHBvbHlmaWxsKVxuICAgKiBpbXBsZW1lbnQgU2hhZG93IERPTSB2MS5cbiAgICovXG4gIGNsYXNzIFNoYWRvd1RlbXBsYXRlIGV4dGVuZHMgYmFzZSB7XG5cbiAgICAvKlxuICAgICAqIElmIHRoZSBjb21wb25lbnQgZGVmaW5lcyBhIHRlbXBsYXRlLCBhIHNoYWRvdyByb290IHdpbGwgYmUgY3JlYXRlZCBvbiB0aGVcbiAgICAgKiBjb21wb25lbnQgaW5zdGFuY2UsIGFuZCB0aGUgdGVtcGxhdGUgc3RhbXBlZCBpbnRvIGl0LlxuICAgICAqL1xuICAgIGNvbnN0cnVjdG9yKCkge1xuICAgICAgc3VwZXIoKTtcbiAgICAgIGxldCB0ZW1wbGF0ZSA9IHRoaXNbc3ltYm9scy50ZW1wbGF0ZV07XG4gICAgICAvLyBUT0RPOiBTYXZlIHRoZSBwcm9jZXNzZWQgdGVtcGxhdGUgd2l0aCB0aGUgY29tcG9uZW50J3MgY2xhc3MgcHJvdG90eXBlXG4gICAgICAvLyBzbyBpdCBkb2Vzbid0IG5lZWQgdG8gYmUgcHJvY2Vzc2VkIHdpdGggZXZlcnkgaW5zdGFudGlhdGlvbi5cbiAgICAgIGlmICh0ZW1wbGF0ZSkge1xuXG4gICAgICAgIGlmICh0eXBlb2YgdGVtcGxhdGUgPT09ICdzdHJpbmcnKSB7XG4gICAgICAgICAgLy8gVXBncmFkZSBwbGFpbiBzdHJpbmcgdG8gcmVhbCB0ZW1wbGF0ZS5cbiAgICAgICAgICB0ZW1wbGF0ZSA9IGNyZWF0ZVRlbXBsYXRlV2l0aElubmVySFRNTCh0ZW1wbGF0ZSk7XG4gICAgICAgIH1cblxuICAgICAgICBpZiAod2luZG93LlNoYWRvd0RPTVBvbHlmaWxsKSB7XG4gICAgICAgICAgc2hpbVRlbXBsYXRlU3R5bGVzKHRlbXBsYXRlLCB0aGlzLmxvY2FsTmFtZSk7XG4gICAgICAgIH1cblxuICAgICAgICBjb25zdCByb290ID0gdGhpcy5hdHRhY2hTaGFkb3coeyBtb2RlOiAnb3BlbicgfSk7XG4gICAgICAgIGNvbnN0IGNsb25lID0gZG9jdW1lbnQuaW1wb3J0Tm9kZSh0ZW1wbGF0ZS5jb250ZW50LCB0cnVlKTtcbiAgICAgICAgcm9vdC5hcHBlbmRDaGlsZChjbG9uZSk7XG4gICAgICB9XG4gICAgfVxuXG4gIH1cblxuICByZXR1cm4gU2hhZG93VGVtcGxhdGU7XG59O1xuXG5cbi8vIENvbnZlcnQgYSBwbGFpbiBzdHJpbmcgb2YgSFRNTCBpbnRvIGEgcmVhbCB0ZW1wbGF0ZSBlbGVtZW50LlxuZnVuY3Rpb24gY3JlYXRlVGVtcGxhdGVXaXRoSW5uZXJIVE1MKGlubmVySFRNTCkge1xuICBjb25zdCB0ZW1wbGF0ZSA9IGRvY3VtZW50LmNyZWF0ZUVsZW1lbnQoJ3RlbXBsYXRlJyk7XG4gIC8vIFJFVklFVzogSXMgdGhlcmUgYW4gZWFzaWVyIHdheSB0byBkbyB0aGlzP1xuICAvLyBXZSdkIGxpa2UgdG8ganVzdCBzZXQgaW5uZXJIVE1MIG9uIHRoZSB0ZW1wbGF0ZSBjb250ZW50LCBidXQgc2luY2UgaXQnc1xuICAvLyBhIERvY3VtZW50RnJhZ21lbnQsIHRoYXQgZG9lc24ndCB3b3JrLlxuICBjb25zdCBkaXYgPSBkb2N1bWVudC5jcmVhdGVFbGVtZW50KCdkaXYnKTtcbiAgZGl2LmlubmVySFRNTCA9IGlubmVySFRNTDtcbiAgd2hpbGUgKGRpdi5jaGlsZE5vZGVzLmxlbmd0aCA+IDApIHtcbiAgICB0ZW1wbGF0ZS5jb250ZW50LmFwcGVuZENoaWxkKGRpdi5jaGlsZE5vZGVzWzBdKTtcbiAgfVxuICByZXR1cm4gdGVtcGxhdGU7XG59XG5cbi8vIEludm9rZSBiYXNpYyBzdHlsZSBzaGltbWluZyB3aXRoIFNoYWRvd0NTUy5cbmZ1bmN0aW9uIHNoaW1UZW1wbGF0ZVN0eWxlcyh0ZW1wbGF0ZSwgdGFnKSB7XG4gIHdpbmRvdy5XZWJDb21wb25lbnRzLlNoYWRvd0NTUy5zaGltU3R5bGluZyh0ZW1wbGF0ZS5jb250ZW50LCB0YWcpO1xufVxuIiwiLyoqXG4gKiBIZWxwZXIgZnVuY3Rpb24gdG8gY3JlYXRlIGEgc3ltYm9sIHRoYXQgY2FuIGJlIHVzZWQgZm9yIGFzc29jaWF0aW5nIHByaXZhdGVcbiAqIGRhdGEgd2l0aCBhbiBlbGVtZW50LlxuICpcbiAqIE1peGlucyBhbmQgY29tcG9uZW50IGNsYXNzZXMgb2Z0ZW4gd2FudCB0byBhc3NvY2lhdGUgcHJpdmF0ZSBkYXRhIHdpdGggYW5cbiAqIGVsZW1lbnQgaW5zdGFuY2UsIGJ1dCBKYXZhU2NyaXB0IGRvZXMgbm90IGhhdmUgZGlyZWN0IHN1cHBvcnQgZm9yIHRydWVcbiAqIHByaXZhdGUgcHJvcGVydGllcy4gT25lIGFwcHJvYWNoIGlzIHRvIHVzZSB0aGVcbiAqIFtTeW1ib2xdKGh0dHBzOi8vZGV2ZWxvcGVyLm1vemlsbGEub3JnL2VuLVVTL2RvY3MvV2ViL0phdmFTY3JpcHQvUmVmZXJlbmNlL0dsb2JhbF9PYmplY3RzL1N5bWJvbClcbiAqIGRhdGEgdHlwZSB0byBzZXQgYW5kIHJldHJpZXZlIGRhdGEgb24gYW4gZWxlbWVudC5cbiAqXG4gKiBVbmZvcnR1bmF0ZWx5LCB0aGUgU3ltYm9sIHR5cGUgaXMgbm90IGF2YWlsYWJsZSBpbiBJbnRlcm5ldCBFeHBsb3JlciAxMS4gVGhlXG4gKiBgY3JlYXRlU3ltYm9sYCBoZWxwZXIgZnVuY3Rpb24gZXhpc3RzIGFzIGEgd29ya2Fyb3VuZCBmb3IgSUUgMTEuIFJhdGhlciB0aGFuXG4gKiByZXR1cm5pbmcgYSB0cnVlIFN5bWJvbCwgaXQgc2ltcGx5IHJldHVybnMgYW4gdW5kZXJzY29yZS1wcmVmaXhlZCBzdHJpbmcuXG4gKlxuICogVXNhZ2U6XG4gKlxuICogICAgIGNvbnN0IGZvb1N5bWJvbCA9IGNyZWF0ZVN5bWJvbCgnZm9vJyk7XG4gKlxuICogICAgIGNsYXNzIE15RWxlbWVudCBleHRlbmRzIEhUTUxFbGVtZW50IHtcbiAqICAgICAgIGdldCBmb28oKSB7XG4gKiAgICAgICAgIHJldHVybiB0aGlzW2Zvb1N5bWJvbF07XG4gKiAgICAgICB9XG4gKiAgICAgICBzZXQgZm9vKHZhbHVlKSB7XG4gKiAgICAgICAgIHRoaXNbZm9vU3ltYm9sXSA9IHZhbHVlO1xuICogICAgICAgfVxuICogICAgIH1cbiAqXG4gKiBJbiBJRSAxMSwgdGhpcyBzYW1wbGUgd2lsbCBcImhpZGVcIiBkYXRhIGJlaGluZCBhbiBpbnN0YW5jZSBwcm9wZXJ0eSB0aGlzLl9mb28uXG4gKiBUaGUgdXNlIG9mIHRoZSB1bmRlcnNjb3JlIGlzIG1lYW50IHRvIHJlZHVjZSAobm90IGVsaW1pbmF0ZSkgdGhlIHBvdGVudGlhbFxuICogZm9yIG5hbWUgY29uZmxpY3RzLCBhbmQgZGlzY291cmFnZSAobm90IHByZXZlbnQpIGV4dGVybmFsIGFjY2VzcyB0byB0aGlzXG4gKiBkYXRhLiBJbiBtb2Rlcm4gYnJvd3NlcnMsIHRoZSBhYm92ZSBjb2RlIHdpbGwgZWxpbWluYXRlIHRoZSBwb3RlbnRpYWwgb2ZcbiAqIG5hbWluZyBjb25mbGljdHMsIGFuZCBiZXR0ZXIgaGlkZSB0aGUgZGF0YSBiZWhpbmQgYSByZWFsIFN5bWJvbC5cbiAqXG4gKiBAZnVuY3Rpb24gY3JlYXRlU3ltYm9sXG4gKiBAcGFyYW0ge3N0cmluZ30gZGVzY3JpcHRpb24gLSBBIHN0cmluZyB0byBpZGVudGlmeSB0aGUgc3ltYm9sIHdoZW4gZGVidWdnaW5nXG4gKi9cbmV4cG9ydCBkZWZhdWx0IGZ1bmN0aW9uIGNyZWF0ZVN5bWJvbChkZXNjcmlwdGlvbikge1xuICByZXR1cm4gdHlwZW9mIFN5bWJvbCA9PT0gJ2Z1bmN0aW9uJyA/XG4gICAgU3ltYm9sKGRlc2NyaXB0aW9uKSA6XG4gICAgYF8ke2Rlc2NyaXB0aW9ufWA7XG59XG4iLCJpbXBvcnQgY3JlYXRlU3ltYm9sIGZyb20gJy4vY3JlYXRlU3ltYm9sJztcbmltcG9ydCB0b2dnbGVDbGFzcyBmcm9tICcuL3RvZ2dsZUNsYXNzJztcblxuXG4vLyBTeW1ib2xzIGZvciBwcml2YXRlIGRhdGEgbWVtYmVycyBvbiBhbiBlbGVtZW50LlxuY29uc3Qgc2FmZVRvU2V0QXR0cmlidXRlc1N5bWJvbCA9IGNyZWF0ZVN5bWJvbCgnc2FmZVRvU2V0QXR0cmlidXRlcycpO1xuY29uc3QgcGVuZGluZ0F0dHJpYnV0ZXNTeW1ib2wgPSBjcmVhdGVTeW1ib2woJ3BlbmRpbmdBdHRyaWJ1dGVzJyk7XG5jb25zdCBwZW5kaW5nQ2xhc3Nlc1N5bWJvbCA9IGNyZWF0ZVN5bWJvbCgncGVuZGluZ0NsYXNzZXMnKTtcblxuXG4vKipcbiAqIEhlbHBlciBmdW5jdGlvbnMgZm9yIHVwZGF0aW5nIGF0dHJpYnV0ZXMsIGluY2x1ZGluZyB0aGUgYGNsYXNzYCBhdHRyaWJ1dGUuXG4gKi9cbmV4cG9ydCBkZWZhdWx0IHtcblxuICAvKipcbiAgICogUGVyZm9ybSBhbnkgcGVuZGluZyB1cGRhdGVzIHRvIGF0dHJpYnV0ZXMgYW5kIGNsYXNzZXMuXG4gICAqXG4gICAqIFRoaXMgd3JpdGVzIGFueSBgc2V0QXR0cmlidXRlYCBvciBgdG9nZ2xlQ2xhc3NgIHZhbHVlcyB0aGF0IHdlcmUgcGVyZm9ybWVkXG4gICAqIGJlZm9yZSBhbiBlbGVtZW50IHdhcyBhdHRhY2hlZCB0byB0aGUgZG9jdW1lbnQgZm9yIHRoZSBmaXJzdCB0aW1lLlxuICAgKlxuICAgKiBUaGlzIG1ldGhvZCBzaG91bGQgYmUgY2FsbGVkIGJ5IG1peGlucy9jb21wb25lbnRzIGluIHRoZWlyXG4gICAqIGBjb25uZWN0ZWRDYWxsYmFja2AuIElmIG11bGl0cGxlIG1peGlucy9jb21wb25lbnRzIGludm9rZSB0aGlzIGR1cmluZyB0aGVcbiAgICogc2FtZSBgY29ubmVjdGVkQ2FsbGJhY2tgLCBvbmx5IHRoZSBmaXJzdCBjYWxsIHdpbGwgaGF2ZSBhbnkgZWZmZWN0LiBUaGVcbiAgICogc3Vic2VxdWVudCBjYWxscyB3aWxsIGJlIGhhcm1sZXNzLlxuICAgKlxuICAgKiBAcGFyYW0ge0hUTUxFbGVtZW50fSBlbGVtZW50IC0gVGhlIGVsZW1lbnQgYmVpbmcgYWRkZWQgdG8gdGhlIGRvY3VtZW50LlxuICAgKi9cbiAgY29ubmVjdGVkKGVsZW1lbnQpIHtcbiAgICBlbGVtZW50W3NhZmVUb1NldEF0dHJpYnV0ZXNTeW1ib2xdID0gdHJ1ZTtcblxuICAgIC8vIFNldCBhbnkgcGVuZGluZyBhdHRyaWJ1dGVzLlxuICAgIGlmIChlbGVtZW50W3BlbmRpbmdBdHRyaWJ1dGVzU3ltYm9sXSkge1xuICAgICAgZm9yIChsZXQgYXR0cmlidXRlIGluIGVsZW1lbnRbcGVuZGluZ0F0dHJpYnV0ZXNTeW1ib2xdKSB7XG4gICAgICAgIGNvbnN0IHZhbHVlID0gZWxlbWVudFtwZW5kaW5nQXR0cmlidXRlc1N5bWJvbF1bYXR0cmlidXRlXTtcbiAgICAgICAgc2V0QXR0cmlidXRlVG9FbGVtZW50KGVsZW1lbnQsIGF0dHJpYnV0ZSwgdmFsdWUpO1xuICAgICAgfVxuICAgICAgZWxlbWVudFtwZW5kaW5nQXR0cmlidXRlc1N5bWJvbF0gPSBudWxsO1xuICAgIH1cblxuICAgIC8vIFNldCBhbnkgcGVuZGluZyBjbGFzc2VzLlxuICAgIGlmIChlbGVtZW50W3BlbmRpbmdDbGFzc2VzU3ltYm9sXSkge1xuICAgICAgZm9yIChsZXQgY2xhc3NOYW1lIGluIGVsZW1lbnRbcGVuZGluZ0NsYXNzZXNTeW1ib2xdKSB7XG4gICAgICAgIGNvbnN0IHZhbHVlID0gZWxlbWVudFtwZW5kaW5nQ2xhc3Nlc1N5bWJvbF1bY2xhc3NOYW1lXTtcbiAgICAgICAgdG9nZ2xlQ2xhc3MoZWxlbWVudCwgY2xhc3NOYW1lLCB2YWx1ZSk7XG4gICAgICB9XG4gICAgICBlbGVtZW50W3BlbmRpbmdDbGFzc2VzU3ltYm9sXSA9IG51bGw7XG4gICAgfVxuICB9LFxuXG4gIC8qKlxuICAgKiBTZXQvdW5zZXQgdGhlIGF0dHJpYnV0ZSB3aXRoIHRoZSBpbmRpY2F0ZWQgbmFtZS5cbiAgICpcbiAgICogVGhpcyBtZXRob2QgZXhpc3RzIHByaW1hcmlseSB0byBoYW5kbGUgdGhlIGNhc2Ugd2hlcmUgYW4gZWxlbWVudCB3YW50cyB0b1xuICAgKiBzZXQgYSBkZWZhdWx0IHByb3BlcnR5IHZhbHVlIHRoYXQgc2hvdWxkIGJlIHJlZmxlY3RlZCBhcyBhbiBhdHRyaWJ1dGUuIEFuXG4gICAqIGltcG9ydGFudCBsaW1pdGF0aW9uIG9mIGN1c3RvbSBlbGVtZW50IGNvbnN0dXJjdG9ycyBpcyB0aGF0IHRoZXkgY2Fubm90XG4gICAqIHNldCBhdHRyaWJ1dGVzLiBBIGNhbGwgdG8gYHNldEF0dHJpYnV0ZWAgZHVyaW5nIHRoZSBjb25zdHJ1Y3RvciB3aWxsXG4gICAqIGJlIGRlZmVycmVkIHVudGlsIHRoZSBlbGVtZW50IGlzIGNvbm5lY3RlZCB0byB0aGUgZG9jdW1lbnQuXG4gICAqXG4gICAqIEBwYXJhbSB7c3RyaW5nfSBhdHRyaWJ1dGUgLSBUaGUgbmFtZSBvZiB0aGUgKmF0dHJpYnV0ZSogKG5vdCBwcm9wZXJ0eSkgdG8gc2V0LlxuICAgKiBAcGFyYW0ge29iamVjdH0gdmFsdWUgLSBUaGUgdmFsdWUgdG8gc2V0LiBJZiBudWxsLCB0aGUgYXR0cmlidXRlIHdpbGwgYmUgcmVtb3ZlZC5cbiAgICovXG4gIHNldEF0dHJpYnV0ZShlbGVtZW50LCBhdHRyaWJ1dGUsIHZhbHVlKSB7XG4gICAgaWYgKGVsZW1lbnRbc2FmZVRvU2V0QXR0cmlidXRlc1N5bWJvbF0pIHtcbiAgICAgIC8vIFNhZmUgdG8gc2V0IGF0dHJpYnV0ZXMgaW1tZWRpYXRlbHkuXG4gICAgICBzZXRBdHRyaWJ1dGVUb0VsZW1lbnQoZWxlbWVudCwgYXR0cmlidXRlLCB2YWx1ZSk7XG4gICAgfSBlbHNlIHtcbiAgICAgIC8vIERlZmVyIHNldHRpbmcgYXR0cmlidXRlcyB1bnRpbCB0aGUgZmlyc3QgdGltZSB3ZSdyZSBjb25uZWN0ZWQuXG4gICAgICBpZiAoIWVsZW1lbnRbcGVuZGluZ0F0dHJpYnV0ZXNTeW1ib2xdKSB7XG4gICAgICAgIGVsZW1lbnRbcGVuZGluZ0F0dHJpYnV0ZXNTeW1ib2xdID0ge307XG4gICAgICB9XG4gICAgICBlbGVtZW50W3BlbmRpbmdBdHRyaWJ1dGVzU3ltYm9sXVthdHRyaWJ1dGVdID0gdmFsdWU7XG4gICAgfVxuICB9LFxuXG4gIC8qKlxuICAgKiBTZXQvdW5zZXQgdGhlIGNsYXNzIHdpdGggdGhlIGluZGljYXRlZCBuYW1lLlxuICAgKlxuICAgKiBUaGlzIG1ldGhvZCBleGlzdHMgcHJpbWFyaWx5IHRvIGhhbmRsZSB0aGUgY2FzZSB3aGVyZSBhbiBlbGVtZW50IHdhbnRzIHRvXG4gICAqIHNldCBhIGRlZmF1bHQgcHJvcGVydHkgdmFsdWUgdGhhdCBzaG91bGQgYmUgcmVmbGVjdGVkIGFzIGFzIGNsYXNzLiBBblxuICAgKiBpbXBvcnRhbnQgbGltaXRhdGlvbiBvZiBjdXN0b20gZWxlbWVudCBjb25zdHVyY3RvcnMgaXMgdGhhdCB0aGV5IGNhbm5vdFxuICAgKiBzZXQgYXR0cmlidXRlcywgaW5jbHVkaW5nIHRoZSBgY2xhc3NgIGF0dHJpYnV0ZS4gQSBjYWxsIHRvXG4gICAqIGB0b2dnbGVDbGFzc2AgZHVyaW5nIHRoZSBjb25zdHJ1Y3RvciB3aWxsIGJlIGRlZmVycmVkIHVudGlsIHRoZSBlbGVtZW50XG4gICAqIGlzIGNvbm5lY3RlZCB0byB0aGUgZG9jdW1lbnQuXG4gICAqXG4gICAqIEBwYXJhbSB7c3RyaW5nfSBjbGFzc05hbWUgLSBUaGUgbmFtZSBvZiB0aGUgY2xhc3MgdG8gc2V0LlxuICAgKiBAcGFyYW0ge29iamVjdH0gdmFsdWUgLSBUcnVlIHRvIHNldCB0aGUgY2xhc3MsIGZhbHNlIHRvIHJlbW92ZSBpdC5cbiAgICovXG4gIHRvZ2dsZUNsYXNzKGVsZW1lbnQsIGNsYXNzTmFtZSwgdmFsdWUpIHtcbiAgICBpZiAoZWxlbWVudFtzYWZlVG9TZXRBdHRyaWJ1dGVzU3ltYm9sXSkge1xuICAgICAgLy8gU2FmZSB0byBzZXQgY2xhc3MgaW1tZWRpYXRlbHkuXG4gICAgICB0b2dnbGVDbGFzcyhlbGVtZW50LCBjbGFzc05hbWUsIHZhbHVlKTtcbiAgICB9IGVsc2Uge1xuICAgICAgLy8gRGVmZXIgc2V0dGluZyBjbGFzcyB1bnRpbCB0aGUgZmlyc3QgdGltZSB3ZSdyZSBjb25uZWN0ZWQuXG4gICAgICBpZiAoIWVsZW1lbnRbcGVuZGluZ0NsYXNzZXNTeW1ib2xdKSB7XG4gICAgICAgIGVsZW1lbnRbcGVuZGluZ0NsYXNzZXNTeW1ib2xdID0ge307XG4gICAgICB9XG4gICAgICBlbGVtZW50W3BlbmRpbmdDbGFzc2VzU3ltYm9sXVtjbGFzc05hbWVdID0gdmFsdWU7XG4gICAgfVxuICB9XG5cbn07XG5cblxuLy8gUmVmbGVjdCB0aGUgYXR0cmlidXRlIHRvIHRoZSBnaXZlbiBlbGVtZW50LlxuLy8gSWYgdGhlIHZhbHVlIGlzIG51bGwsIHJlbW92ZSB0aGUgYXR0cmlidXRlLlxuZnVuY3Rpb24gc2V0QXR0cmlidXRlVG9FbGVtZW50KGVsZW1lbnQsIGF0dHJpYnV0ZU5hbWUsIHZhbHVlKSB7XG4gIGlmICh2YWx1ZSA9PT0gbnVsbCB8fCB0eXBlb2YgdmFsdWUgPT09ICd1bmRlZmluZWQnKSB7XG4gICAgZWxlbWVudC5yZW1vdmVBdHRyaWJ1dGUoYXR0cmlidXRlTmFtZSk7XG4gIH0gZWxzZSB7XG4gICAgY29uc3QgdGV4dCA9IFN0cmluZyh2YWx1ZSk7XG4gICAgLy8gQXZvaWQgcmVjdXJzaXZlIGF0dHJpYnV0ZUNoYW5nZWRDYWxsYmFjayBjYWxscy5cbiAgICBpZiAoZWxlbWVudC5nZXRBdHRyaWJ1dGUoYXR0cmlidXRlTmFtZSkgIT09IHRleHQpIHtcbiAgICAgIGVsZW1lbnQuc2V0QXR0cmlidXRlKGF0dHJpYnV0ZU5hbWUsIHZhbHVlKTtcbiAgICB9XG4gIH1cbn1cbiIsImltcG9ydCBjcmVhdGVTeW1ib2wgZnJvbSAnLi9jcmVhdGVTeW1ib2wnO1xuXG4vKipcbiAqIEEgY29sbGVjdGlvbiBvZiBTeW1ib2wgb2JqZWN0cyBmb3Igc3RhbmRhcmQgY29tcG9uZW50IHByb3BlcnRpZXMgYW5kIG1ldGhvZHMuXG4gKlxuICogVGhlc2UgU3ltYm9sIG9iamVjdHMgYXJlIHVzZWQgdG8gYWxsb3cgbWl4aW5zIGFuZCBhIGNvbXBvbmVudCB0byBpbnRlcm5hbGx5XG4gKiBjb21tdW5pY2F0ZSwgd2l0aG91dCBleHBvc2luZyB0aGVzZSBwcm9wZXJ0aWVzIGFuZCBtZXRob2RzIGluIHRoZSBjb21wb25lbnQnc1xuICogcHVibGljIEFQSS5cbiAqXG4gKiBUbyB1c2UgdGhlc2UgU3ltYm9sIG9iamVjdHMgaW4geW91ciBvd24gY29tcG9uZW50LCBpbmNsdWRlIHRoaXMgbW9kdWxlIGFuZFxuICogdGhlbiBjcmVhdGUgYSBwcm9wZXJ0eSBvciBtZXRob2Qgd2hvc2Uga2V5IGlzIHRoZSBkZXNpcmVkIFN5bWJvbC5cbiAqXG4gKiAgICAgaW1wb3J0ICdTaW5nbGVTZWxlY3Rpb25NaXhpbicgZnJvbSAnYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvU2luZ2xlU2VsZWN0aW9uTWl4aW4nO1xuICogICAgIGltcG9ydCAnc3ltYm9scycgZnJvbSAnYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvc3ltYm9scyc7XG4gKlxuICogICAgIGNsYXNzIE15RWxlbWVudCBleHRlbmRzIFNpbmdsZVNlbGVjdGlvbk1peGluKEhUTUxFbGVtZW50KSB7XG4gKiAgICAgICBbc3ltYm9scy5pdGVtU2VsZWN0ZWRdKGl0ZW0sIHNlbGVjdGVkKSB7XG4gKiAgICAgICAgIC8vIFRoaXMgd2lsbCBiZSBpbnZva2VkIHdoZW5ldmVyIGFuIGl0ZW0gaXMgc2VsZWN0ZWQvZGVzZWxlY3RlZC5cbiAqICAgICAgIH1cbiAqICAgICB9XG4gKlxuICogQG1vZHVsZSBzeW1ib2xzXG4gKi9cbmNvbnN0IHN5bWJvbHMgPSB7XG5cbiAgLyoqXG4gICAqIFN5bWJvbCBmb3IgdGhlIGBkZWZhdWx0c2AgcHJvcGVydHkuXG4gICAqXG4gICAqIFRoaXMgcHJvcGVydHkgY2FuIGJlIHVzZWQgdG8gc2V0IG9yIG92ZXJyaWRlIGRlZmF1bHRzIHRoYXQgd2lsbCBiZSBhcHBsaWVkXG4gICAqIHRvIGEgbmV3IGNvbXBvbmVudCBpbnN0YW5jZS4gV2hlbiBpbXBsZW1lbnRpbmcgdGhpcyBwcm9wZXJ0eSwgdGFrZSBjYXJlIHRvXG4gICAqIGZpcnN0IGFjcXVpcmUgYW55IGRlZmF1bHRzIGRlZmluZWQgYnkgdGhlIHN1cGVyY2xhc3MuIFRoZSBzdGFuZGFyZCBpZGlvbSBpc1xuICAgKiBhcyBmb2xsb3dzOlxuICAgKlxuICAgKiAgICAgZ2V0IFtzeW1ib2xzLmRlZmF1bHRzXSgpIHtcbiAgICogICAgICAgY29uc3QgZGVmYXVsdHMgPSBzdXBlcltzeW1ib2xzLmRlZmF1bHRzXSB8fCB7fTtcbiAgICogICAgICAgLy8gU2V0IG9yIG92ZXJyaWRlIGRlZmF1bHQgdmFsdWVzIGhlcmVcbiAgICogICAgICAgZGVmYXVsdHMuY3VzdG9tUHJvcGVydHkgPSBmYWxzZTtcbiAgICogICAgICAgcmV0dXJuIGRlZmF1bHRzO1xuICAgKiAgICAgfVxuICAgKlxuICAgKiBAdmFyIHtvYmplY3R9IGRlZmF1bHRzXG4gICAqL1xuICBkZWZhdWx0czogY3JlYXRlU3ltYm9sKCdkZWZhdWx0cycpLFxuXG4gIC8qKlxuICAgKiBTeW1ib2wgZm9yIHRoZSBgZHJhZ2dpbmdgIHByb3BlcnR5LlxuICAgKlxuICAgKiBDb21wb25lbnRzIGxpa2UgY2Fyb3VzZWxzIG9mdGVuIGRlZmluZSBhbmltYXRlZCBDU1MgdHJhbnNpdGlvbnMgZm9yXG4gICAqIHNsaWRpbmcgZWZmZWN0cy4gU3VjaCBhIHRyYW5zaXRpb24gc2hvdWxkIHVzdWFsbHkgKm5vdCogYmUgYXBwbGllZCB3aGlsZVxuICAgKiB0aGUgdXNlciBpcyBkcmFnZ2luZywgYmVjYXVzZSBhIENTUyBhbmltYXRpb24gd2lsbCBpbnRyb2R1Y2UgYSBsYWcgdGhhdFxuICAgKiBtYWtlcyB0aGUgc3dpcGUgZmVlbCBzbHVnZ2lzaC4gSW5zdGVhZCwgYXMgbG9uZyBhcyB0aGUgdXNlciBpcyBkcmFnZ2luZ1xuICAgKiB3aXRoIHRoZWlyIGZpbmdlciBkb3duLCB0aGUgdHJhbnNpdGlvbiBzaG91bGQgYmUgc3VwcHJlc3NlZC4gV2hlbiB0aGVcbiAgICogdXNlciByZWxlYXNlcyB0aGVpciBmaW5nZXIsIHRoZSB0cmFuc2l0aW9uIGNhbiBiZSByZXN0b3JlZCwgYWxsb3dpbmcgdGhlXG4gICAqIGFuaW1hdGlvbiB0byBzaG93IHRoZSBjYXJvdXNlbCBzbGlkaW5nIGludG8gaXRzIGZpbmFsIHBvc2l0aW9uLlxuICAgKlxuICAgKiBAdHlwZSB7Ym9vbGVhbn0gdHJ1ZSBpZiBhIGRyYWcgaXMgaW4gcHJvZ3Jlc3MsIGZhbHNlIGlmIG5vdC5cbiAgICovXG4gIGRyYWdnaW5nOiBjcmVhdGVTeW1ib2woJ2RyYWdnaW5nJyksXG5cbiAgLyoqXG4gICAqIFN5bWJvbCBmb3IgdGhlIGBnb0Rvd25gIG1ldGhvZC5cbiAgICpcbiAgICogVGhpcyBtZXRob2QgaXMgaW52b2tlZCB3aGVuIHRoZSB1c2VyIHdhbnRzIHRvIGdvL25hdmlnYXRlIGRvd24uXG4gICAqXG4gICAqIEBmdW5jdGlvbiBnb0Rvd25cbiAgICovXG4gIGdvRG93bjogY3JlYXRlU3ltYm9sKCdnb0Rvd24nKSxcblxuICAvKipcbiAgICogU3ltYm9sIGZvciB0aGUgYGdvRW5kYCBtZXRob2QuXG4gICAqXG4gICAqIFRoaXMgbWV0aG9kIGlzIGludm9rZWQgd2hlbiB0aGUgdXNlciB3YW50cyB0byBnby9uYXZpZ2F0ZSB0byB0aGUgZW5kIChlLmcuLFxuICAgKiBvZiBhIGxpc3QpLlxuICAgKlxuICAgKiBAZnVuY3Rpb24gZ29FbmRcbiAgICovXG4gIGdvRW5kOiBjcmVhdGVTeW1ib2woJ2dvRW5kJyksXG5cbiAgLyoqXG4gICAqIFN5bWJvbCBmb3IgdGhlIGBnb0xlZnRgIG1ldGhvZC5cbiAgICpcbiAgICogVGhpcyBtZXRob2QgaXMgaW52b2tlZCB3aGVuIHRoZSB1c2VyIHdhbnRzIHRvIGdvL25hdmlnYXRlIGxlZnQuXG4gICAqXG4gICAqIEBmdW5jdGlvbiBnb0xlZnRcbiAgICovXG4gIGdvTGVmdDogY3JlYXRlU3ltYm9sKCdnb0xlZnQnKSxcblxuICAvKipcbiAgICogU3ltYm9sIGZvciB0aGUgYGdvUmlnaHRgIG1ldGhvZC5cbiAgICpcbiAgICogVGhpcyBtZXRob2QgaXMgaW52b2tlZCB3aGVuIHRoZSB1c2VyIHdhbnRzIHRvIGdvL25hdmlnYXRlIHJpZ2h0LlxuICAgKlxuICAgKiBAZnVuY3Rpb24gZ29SaWdodFxuICAgKi9cbiAgZ29SaWdodDogY3JlYXRlU3ltYm9sKCdnb1JpZ2h0JyksXG5cbiAgLyoqXG4gICAqIFN5bWJvbCBmb3IgdGhlIGBnb1N0YXJ0YCBtZXRob2QuXG4gICAqXG4gICAqIFRoaXMgbWV0aG9kIGlzIGludm9rZWQgd2hlbiB0aGUgdXNlciB3YW50cyB0byBnby9uYXZpZ2F0ZSB0byB0aGUgc3RhcnRcbiAgICogKGUuZy4sIG9mIGEgbGlzdCkuXG4gICAqXG4gICAqIEBmdW5jdGlvbiBnb1N0YXJ0XG4gICAqL1xuICBnb1N0YXJ0OiBjcmVhdGVTeW1ib2woJ2dvU3RhcnQnKSxcblxuICAvKipcbiAgICogU3ltYm9sIGZvciB0aGUgYGdvVXBgIG1ldGhvZC5cbiAgICpcbiAgICogVGhpcyBtZXRob2QgaXMgaW52b2tlZCB3aGVuIHRoZSB1c2VyIHdhbnRzIHRvIGdvL25hdmlnYXRlIHVwLlxuICAgKlxuICAgKiBAZnVuY3Rpb24gZ29VcFxuICAgKi9cbiAgZ29VcDogY3JlYXRlU3ltYm9sKCdnb1VwJyksXG5cbiAgLyoqXG4gICAqIFN5bWJvbCBmb3IgdGhlIGBpdGVtQWRkZWRgIG1ldGhvZC5cbiAgICpcbiAgICogVGhpcyBtZXRob2QgaXMgaW52b2tlZCB3aGVuIGEgbmV3IGl0ZW0gaXMgYWRkZWQgdG8gYSBsaXN0LlxuICAgKlxuICAgKiBAZnVuY3Rpb24gaXRlbUFkZGVkXG4gICAqIEBwYXJhbSB7SFRNTEVsZW1lbnR9IGl0ZW0gLSB0aGUgaXRlbSBiZWluZyBzZWxlY3RlZC9kZXNlbGVjdGVkXG4gICAqL1xuICBpdGVtQWRkZWQ6IGNyZWF0ZVN5bWJvbCgnaXRlbUFkZGVkJyksXG5cblxuICAvKipcbiAgICogU3ltYm9sIGZvciB0aGUgYGl0ZW1zQ2hhbmdlZGAgbWV0aG9kLlxuICAgKlxuICAgKiBUaGlzIG1ldGhvZCBpcyBpbnZva2VkIHdoZW4gdGhlIHVuZGVybHlpbmcgY29udGVudHMgY2hhbmdlLiBJdCBpcyBhbHNvXG4gICAqIGludm9rZWQgb24gY29tcG9uZW50IGluaXRpYWxpemF0aW9uIOKAkyBzaW5jZSB0aGUgaXRlbXMgaGF2ZSBcImNoYW5nZWRcIiBmcm9tXG4gICAqIGJlaW5nIG5vdGhpbmcuXG4gICAqL1xuICBpdGVtc0NoYW5nZWQ6IGNyZWF0ZVN5bWJvbCgnaXRlbXNDaGFuZ2VkJyksXG5cbiAgLyoqXG4gICAqIFN5bWJvbCBmb3IgdGhlIGBpdGVtU2VsZWN0ZWRgIG1ldGhvZC5cbiAgICpcbiAgICogVGhpcyBtZXRob2QgaXMgaW52b2tlZCB3aGVuIGFuIGl0ZW0gYmVjb21lcyBzZWxlY3RlZCBvciBkZXNlbGVjdGVkLlxuICAgKlxuICAgKiBAZnVuY3Rpb24gaXRlbVNlbGVjdGVkXG4gICAqIEBwYXJhbSB7SFRNTEVsZW1lbnR9IGl0ZW0gLSB0aGUgaXRlbSBiZWluZyBzZWxlY3RlZC9kZXNlbGVjdGVkXG4gICAqIEBwYXJhbSB7Ym9vbGVhbn0gc2VsZWN0ZWQgLSB0cnVlIGlmIHRoZSBpdGVtIGlzIHNlbGVjdGVkLCBmYWxzZSBpZiBub3RcbiAgICovXG4gIGl0ZW1TZWxlY3RlZDogY3JlYXRlU3ltYm9sKCdpdGVtU2VsZWN0ZWQnKSxcblxuICAvKipcbiAgICogU3ltYm9sIGZvciB0aGUgYGtleWRvd25gIG1ldGhvZC5cbiAgICpcbiAgICogVGhpcyBtZXRob2QgaXMgaW52b2tlZCB3aGVuIGFuIGVsZW1lbnQgcmVjZWl2ZXMgYSBga2V5ZG93bmAgZXZlbnQuXG4gICAqXG4gICAqIEBmdW5jdGlvbiBrZXlkb3duXG4gICAqIEBwYXJhbSB7S2V5Ym9hcmRFdmVudH0gZXZlbnQgLSB0aGUgZXZlbnQgYmVpbmcgcHJvY2Vzc2VkXG4gICAqL1xuICBrZXlkb3duOiBjcmVhdGVTeW1ib2woJ2tleWRvd24nKSxcblxuICAvKipcbiAgICogU3ltYm9sIGZvciB0aGUgYHRlbXBsYXRlYCBwcm9wZXJ0eS5cbiAgICpcbiAgICogVGhpcyBwcm9wZXJ0eSByZXR1cm5zIGEgY29tcG9uZW50J3MgdGVtcGxhdGUuXG4gICAqXG4gICAqIEB0eXBlIHtzdHJpbmd8SFRNTEVsZW1lbnR9XG4gICAqL1xuICB0ZW1wbGF0ZTogY3JlYXRlU3ltYm9sKCd0ZW1wbGF0ZScpXG59O1xuXG5leHBvcnQgZGVmYXVsdCBzeW1ib2xzO1xuIiwiLyoqXG4gKiBIZWxwZXIgZnVuY3Rpb24gZm9yIHN0YW5kYXJkIGNsYXNzTGlzdC50b2dnbGUoKSBiZWhhdmlvciBvbiBvbGQgYnJvd3NlcnMsXG4gKiBuYW1lbHkgSUUgMTEuXG4gKlxuICogVGhlIHN0YW5kYXJkXG4gKiBbY2xhc3NsaXN0XShodHRwczovL2RldmVsb3Blci5tb3ppbGxhLm9yZy9lbi1VUy9kb2NzL1dlYi9BUEkvRWxlbWVudC9jbGFzc0xpc3QpXG4gKiBvYmplY3QgaGFzIGEgYHRvZ2dsZSgpYCBmdW5jdGlvbiB0aGF0IHN1cHBvcnRzIGEgc2Vjb25kIEJvb2xlYW4gcGFyYW1ldGVyXG4gKiB0aGF0IGNhbiBiZSB1c2VkIHRvIHN1Y2NpbmN0bHkgdHVybiBhIGNsYXNzIG9uIG9yIG9mZi4gVGhpcyBmZWF0dXJlIGlzIG9mdGVuXG4gKiB1c2VmdWwgaW4gZGVzaWduaW5nIGN1c3RvbSBlbGVtZW50cywgd2hpY2ggbWF5IHdhbnQgdG8gZXh0ZXJuYWxseSByZWZsZWN0XG4gKiBjb21wb25lbnQgc3RhdGUgaW4gYSBDU1MgY2xhc3MgdGhhdCBjYW4gYmUgdXNlZCBmb3Igc3R5bGluZyBwdXJwb3Nlcy5cbiAqXG4gKiBVbmZvcnR1bmF0ZWx5LCBJRSAxMSBkb2VzIG5vdCBzdXBwb3J0IHRoZSBCb29sZWFuIHBhcmFtZXRlciB0b1xuICogYGNsYXNzTGlzdC50b2dnbGUoKWAuIFRoaXMgaGVscGVyIGZ1bmN0aW9uIGJlaGF2ZXMgbGlrZSB0aGUgc3RhbmRhcmRcbiAqIGB0b2dnbGUoKWAsIGluY2x1ZGluZyBzdXBwb3J0IGZvciB0aGUgQm9vbGVhbiBwYXJhbWV0ZXIsIHNvIHRoYXQgaXQgY2FuIGJlXG4gKiB1c2VkIGV2ZW4gb24gSUUgMTEuXG4gKlxuICogQGZ1bmN0aW9uIHRvZ2dsZUNsYXNzXG4gKiBAcGFyYW0ge0hUTUxFbGVtZW50fSBlbGVtZW50IC0gVGhlIGVsZW1lbnQgdG8gbW9kaWZ5XG4gKiBAcGFyYW0ge3N0cmluZ30gY2xhc3NOYW1lIC0gVGhlIGNsYXNzIHRvIGFkZC9yZW1vdmVcbiAqIEBwYXJhbSB7Ym9vbGVhbn0gW2ZvcmNlXSAtIEZvcmNlIHRoZSBjbGFzcyB0byBiZSBhZGRlZCAoaWYgdHJ1ZSkgb3IgcmVtb3ZlZFxuICogICAgICAgICAgICAgICAgICAgICAgICAgICAgKGlmIGZhbHNlKVxuICovXG5leHBvcnQgZGVmYXVsdCBmdW5jdGlvbiB0b2dnbGVDbGFzcyhlbGVtZW50LCBjbGFzc05hbWUsIGZvcmNlKSB7XG4gIGNvbnN0IGNsYXNzTGlzdCA9IGVsZW1lbnQuY2xhc3NMaXN0O1xuICBjb25zdCBhZGRDbGFzcyA9ICh0eXBlb2YgZm9yY2UgPT09ICd1bmRlZmluZWQnKSA/XG4gICAgIWNsYXNzTGlzdC5jb250YWlucyhjbGFzc05hbWUpIDpcbiAgICBmb3JjZTtcbiAgaWYgKGFkZENsYXNzKSB7XG4gICAgY2xhc3NMaXN0LmFkZChjbGFzc05hbWUpO1xuICB9IGVsc2Uge1xuICAgIGNsYXNzTGlzdC5yZW1vdmUoY2xhc3NOYW1lKTtcbiAgfVxuICByZXR1cm4gYWRkQ2xhc3M7XG59XG4iLCJpbXBvcnQgQXR0cmlidXRlTWFyc2hhbGxpbmdNaXhpbiBmcm9tICcuLi8uLi9iYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy9BdHRyaWJ1dGVNYXJzaGFsbGluZ01peGluJztcbmltcG9ydCBDb21wb3NhYmxlTWl4aW4gZnJvbSAnLi4vLi4vYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvQ29tcG9zYWJsZU1peGluJztcbmltcG9ydCBEaXN0cmlidXRlZENoaWxkcmVuTWl4aW4gZnJvbSAnLi4vLi4vYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvRGlzdHJpYnV0ZWRDaGlsZHJlbk1peGluJztcbmltcG9ydCBTaGFkb3dFbGVtZW50UmVmZXJlbmNlc01peGluIGZyb20gJy4uLy4uL2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL1NoYWRvd0VsZW1lbnRSZWZlcmVuY2VzTWl4aW4nO1xuaW1wb3J0IFNoYWRvd1RlbXBsYXRlTWl4aW4gZnJvbSAnLi4vLi4vYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvU2hhZG93VGVtcGxhdGVNaXhpbic7XG5cblxuLyoqXG4gKiBBIHNhbXBsZSBnZW5lcmFsLXB1cnBvc2UgYmFzZSBjbGFzcyBmb3IgZGVmaW5pbmcgY3VzdG9tIGVsZW1lbnRzIHRoYXQgbWl4ZXNcbiAqIGluIHNvbWUgY29tbW9uIGZlYXR1cmVzOiB0ZW1wbGF0ZSBzdGFtcGluZyBpbnRvIGEgc2hhZG93IHJvb3QsIHNoYWRvdyBlbGVtZW50XG4gKiByZWZlcmVuY2VzLCBtYXJzaGFsbGluZyBhdHRyaWJ1dGVzIHRvIHByb3BlcnRpZXMsIGFuZCByZXRyaWV2aW5nIHRoZSBjaGlsZHJlblxuICogZGlzdHJpYnV0ZWQgdG8gYSBjb21wb25lbnQuXG4gKlxuICogVGhpcyBiYXNlIGNsYXNzIGlzIG5vdCBzcGVjaWFsIGluIGFueSB3YXksIGFuZCBpcyBkZWZpbmVkIG9ubHkgYXMgYVxuICogY29udmVuaWVudCBzaG9ydGhhbmQgZm9yIGFwcGx5aW5nIHRoZSBtaXhpbnMgbGlzdGVkIGFib3ZlLiBZb3UgY2FuIHVzZSB0aGlzXG4gKiBjbGFzcyBhcyBhIGJhc2UgY2xhc3MgZm9yIHlvdXIgb3duIGVsZW1lbnRzLCBvciBlYXNpbHkgY3JlYXRlIHlvdXIgb3duIGJhc2VcbiAqIGNsYXNzIGJ5IGFwcGx5aW5nIHRoZSBzYW1lIHNldCBvZiBtaXhpbnMuXG4gKlxuICogVGhlIEVsZW1lbnRCYXNlIGJhc2UgY2xhc3MgZG9lcyBub3QgcmVnaXN0ZXIgaXRzZWxmIGFzIGEgY3VzdG9tIGVsZW1lbnQgd2l0aFxuICogdGhlIGJyb3dzZXIsIGFuZCBoZW5jZSBjYW5ub3QgYmUgaW5kZXBlbmRlbnRseSBpbnN0YW50aWF0ZWQuXG4gKlxuICogQG1peGVzIEF0dHJpYnV0ZU1hcnNoYWxsaW5nTWl4aW5cbiAqIEBtaXhlcyBDb21wb3NhYmxlTWl4aW5cbiAqIEBtaXhlcyBEaXN0cmlidXRlZENoaWxkcmVuTWl4aW5cbiAqIEBtaXhlcyBTaGFkb3dFbGVtZW50UmVmZXJlbmNlc01peGluXG4gKiBAbWl4ZXMgU2hhZG93VGVtcGxhdGVNaXhpblxuICovXG5jbGFzcyBFbGVtZW50QmFzZSBleHRlbmRzIENvbXBvc2FibGVNaXhpbihIVE1MRWxlbWVudCkuY29tcG9zZShcbiAgU2hhZG93VGVtcGxhdGVNaXhpbiwgICAgICAgICAgLy8gYmVmb3JlIG5vZGUgZmluZGluZywgc28gc2hhZG93IHJvb3QgaXMgcG9wdWxhdGVkXG4gIFNoYWRvd0VsZW1lbnRSZWZlcmVuY2VzTWl4aW4sIC8vIGJlZm9yZSBtYXJzaGFsbGluZywgc28gcHJvcGVydGllcyBjYW4gdXNlIHJlZnNcbiAgQXR0cmlidXRlTWFyc2hhbGxpbmdNaXhpbixcbiAgRGlzdHJpYnV0ZWRDaGlsZHJlbk1peGluXG4pIHt9XG5cbmV4cG9ydCBkZWZhdWx0IEVsZW1lbnRCYXNlO1xuIiwiLypcbiAqIFRoaXMgZmlsZSBpcyB0cmFuc3BpbGVkIHRvIGNyZWF0ZSBhbiBFUzUtY29tcGF0aWJsZSBkaXN0cmlidXRpb24gaW4gd2hpY2hcbiAqIHRoZSBwYWNrYWdlJ3MgbWFpbiBmZWF0dXJlKHMpIGFyZSBhdmFpbGFibGUgdmlhIHRoZSB3aW5kb3cuQmFzaWMgZ2xvYmFsLlxuICogSWYgeW91J3JlIGFscmVhZHkgdXNpbmcgRVM2IHlvdXJzZWxmLCBpZ25vcmUgdGhpcyBmaWxlLCBhbmQgaW5zdGVhZCBpbXBvcnRcbiAqIHRoZSBzb3VyY2UgZmlsZShzKSB5b3Ugd2FudCBmcm9tIHRoZSBzcmMgZm9sZGVyLlxuICovXG5cbmltcG9ydCBGYWRlT3ZlcmZsb3cgZnJvbSAnLi9zcmMvRmFkZU92ZXJmbG93Jztcblxud2luZG93LkJhc2ljID0gd2luZG93LkJhc2ljIHx8IHt9O1xud2luZG93LkJhc2ljLkZhZGVPdmVyZmxvdyA9IEZhZGVPdmVyZmxvdztcbiIsImltcG9ydCBjcmVhdGVTeW1ib2wgZnJvbSAnLi4vLi4vYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvY3JlYXRlU3ltYm9sJztcbmltcG9ydCBFbGVtZW50QmFzZSBmcm9tICcuLi8uLi9iYXNpYy1lbGVtZW50LWJhc2Uvc3JjL0VsZW1lbnRCYXNlJztcbmltcG9ydCBzeW1ib2xzIGZyb20gJy4uLy4uL2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL3N5bWJvbHMnO1xuXG5cbi8vIFN5bWJvbHMgZm9yIHByaXZhdGUgZGF0YSBtZW1iZXJzIG9uIGFuIGVsZW1lbnQuXG5jb25zdCBmYWRlQ29sb3JTeW1ib2wgPSBjcmVhdGVTeW1ib2woJ2ZhZGVDb2xvcicpO1xuXG5cbi8qKlxuICogRmFkZXMgb3V0IGNvbnRlbnQgdGhhdCBvdmVyZmxvd3Mgc28gdGhlIHVzZXIga25vd3MgdGhlcmUncyBtb3JlLlxuICpcbiAqIFRoaXMgY29tcG9uZW50IGRvZXNuJ3QgaGFuZGxlIGludGVyYWN0aXZpdHkuXG4gKlxuICogVGhlIGNvbXBvbmVudCBuZWVkcyB0byBrbm93IHRoZSBjb2xvciBpdCBzaG91bGQgZmFkZSB0bywgd2hpY2ggaXQgdHJpZXMgdG9cbiAqIGluZmVyIGZyb20gdGhlIGJhY2tncm91bmQgY29sb3IuIEluIHNvbWUgc2l0dWF0aW9ucywgdGhpcyBtYXkgbm90IHdvcmssIGluXG4gKiB3aGljaCBjYXNlIHlvdSBjYW4gZXhwbGljaXRseSBzZXQgdGhlIGZhZGVDb2xvciBhdHRyaWJ1dGUuXG4gKlxuICogVGhlIGNvbXBvbmVudCBjdXJyZW50bHkgYWx3YXlzIGRpc3BsYXlzIHRoZSBmYWRlLCBldmVuIGlmIHRoZSBjb21wb25lbnQnc1xuICogY29udGVudCBpcyBzaG9ydCBlbm91Z2ggdG8gZml0IGNvbXBsZXRlbHkgaW4gdmlldy5cbiAqXG4gKiBAZXh0ZW5kcyBFbGVtZW50QmFzZVxuICovXG5jbGFzcyBGYWRlT3ZlcmZsb3cgZXh0ZW5kcyBFbGVtZW50QmFzZSB7XG5cbiAgY29ubmVjdGVkQ2FsbGJhY2soKSB7XG4gICAgaWYgKHN1cGVyLmNvbm5lY3RlZENhbGxiYWNrKSB7IHN1cGVyLmNvbm5lY3RlZENhbGxiYWNrKCk7IH1cbiAgICBpZiAodGhpcy5mYWRlQ29sb3IgPT0gbnVsbCkge1xuICAgICAgdGhpcy5yZWZyZXNoKCk7XG4gICAgfVxuICB9XG5cbiAgLyoqXG4gICAqIFRoZSBjb2xvciBvZiB0aGUgZmFkZS5cbiAgICpcbiAgICogVGhlIGZhZGUgY29sb3Igc2hvdWxkIG1hdGNoIHRoZSBiYWNrZ3JvdW5kIGNvbG9yLiBUaGUgY29tcG9uZW50IGRvZXMgaXRzXG4gICAqIGJlc3QgdG8gaW5mZXIgdGhlIGJhY2tncm91bmQgY29sb3IsIGJ1dCBpbiBzb21lIHNpdHVhdGlvbnMsIHRoYXQgbWF5IG5vdFxuICAgKiB3b3JrLiBJbiB0aG9zZSBjYXNlcywgeW91IGNhbiBtYW51YWxseSBpZGVudGlmeSB0aGUgYmFja2dyb3VuZCBjb2xvci5cbiAgICogVGhpcyBzaG91bGQgYmUgYSBzb2xpZCBjb2xvci5cbiAgICpcbiAgICogQGF0dHJpYnV0ZSBmYWRlQ29sb3JcbiAgICogQGRlZmF1bHQgd2hpdGVcbiAgICovXG4gIGdldCBmYWRlQ29sb3IoKSB7XG4gICAgcmV0dXJuIHRoaXNbZmFkZUNvbG9yU3ltYm9sXTtcbiAgfVxuICBzZXQgZmFkZUNvbG9yKHZhbHVlKSB7XG4gICAgdGhpc1tmYWRlQ29sb3JTeW1ib2xdID0gdmFsdWU7XG4gICAgaWYgKHZhbHVlKSB7XG4gICAgICBjb25zdCByZ2IgPSBleHRyYWN0UmdiVmFsdWVzKHZhbHVlKTtcbiAgICAgIGlmIChyZ2IpIHtcbiAgICAgICAgY29uc3QgZmFkZUNvbG9yVHJhbnNwYXJlbnQgPSBgcmdiYSgke3JnYi5yfSwke3JnYi5nfSwke3JnYi5ifSwwKWA7XG4gICAgICAgIGNvbnN0IGdyYWRpZW50ID0gYGxpbmVhci1ncmFkaWVudCgke2ZhZGVDb2xvclRyYW5zcGFyZW50fSAwJSwgJHt2YWx1ZX0gMTAwJSlgO1xuICAgICAgICB0aGlzLiQuZmFkZS5zdHlsZS5iYWNrZ3JvdW5kSW1hZ2UgPSBncmFkaWVudDtcbiAgICAgIH1cbiAgICB9XG4gIH1cblxuICAvKipcbiAgICogSW5mZXIgdGhlIGZhZGUgY29sb3IgZnJvbSBiYWNrZ3JvdW5kIGNvbG9yLiBJZiB5b3UgaGF2ZSBwcm9ncmFtbWF0aWNhbGx5XG4gICAqIGNoYW5nZWQgdGhlIGNvbG9yIGJlaGluZCB0aGUgY29tcG9uZW50LCB5b3UgY2FuIGludm9rZSB0aGlzIG1ldGhvZCB0byBoYXZlXG4gICAqIHRoZSBjb21wb25lbnQgdHJ5IHRvIHBpY2sgdXAgdGhlIG5ldyBiYWNrZ3JvdW5kIGNvbG9yLlxuICAgKi9cbiAgcmVmcmVzaCgpIHtcbiAgICAvLyBUT0RPOiBBdXRvbWF0aWNhbGx5IGhpZGUgdGhlIGZhZGUgaWYgYWxsIHRoZSBjb250ZW50IGNhbiBiZSBzZWVuLlxuICAgIHRoaXMuZmFkZUNvbG9yID0gZmluZEJhY2tncm91bmRDb2xvcih0aGlzKTtcbiAgfVxuXG4gIC8qKlxuICAgKiBUcnVlIGlmIHRoZSBjb21wb25lbnQgc2hvdWxkIHNob3cgdGhlIGZhZGUgdG8gdGhlIGJhY2tncm91bmQgY29sb3IuXG4gICAqXG4gICAqIEB0eXBlIHtib29sZWFufVxuICAgKiBAZGVmYXVsdCB0cnVlXG4gICAqL1xuICBnZXQgc2hvd0ZhZGUoKSB7XG4gICAgcmV0dXJuIHRoaXMuJC5mYWRlLnN0eWxlLmRpc3BsYXkgIT09ICdub25lJztcbiAgfVxuICBzZXQgc2hvd0ZhZGUodmFsdWUpIHtcbiAgICB0aGlzLiQuZmFkZS5zdHlsZS5kaXNwbGF5ID0gdmFsdWUgPyAnJyA6ICdub25lJztcbiAgfVxuXG4gIGdldCBbc3ltYm9scy50ZW1wbGF0ZV0oKSB7XG4gICAgcmV0dXJuIGBcbiAgICAgIDxzdHlsZT5cbiAgICAgIDpob3N0IHtcbiAgICAgICAgZGlzcGxheTogYmxvY2s7XG4gICAgICAgIHBvc2l0aW9uOiByZWxhdGl2ZTtcbiAgICAgICAgb3ZlcmZsb3c6IGhpZGRlbjtcbiAgICAgIH1cblxuICAgICAgI2ZhZGUge1xuICAgICAgICBib3R0b206IDA7XG4gICAgICAgIGhlaWdodDogM2VtO1xuICAgICAgICBtYXgtaGVpZ2h0OiA1MCU7XG4gICAgICAgIHBvaW50ZXItZXZlbnRzOiBub25lOyAvKiBMZXRzIHVzZXIgaW50ZXJhY3Qgd2l0aCBjb250ZW50IHRocm91Z2ggdGhlIGZhZGUuICovXG4gICAgICAgIHBvc2l0aW9uOiBhYnNvbHV0ZTtcbiAgICAgICAgd2lkdGg6IDEwMCU7XG4gICAgICB9XG4gICAgICA8L3N0eWxlPlxuXG4gICAgICA8ZGl2IGlkPVwiZmFkZVwiPjwvZGl2PlxuICAgICAgPHNsb3Q+PC9zbG90PlxuICAgIGA7XG4gIH1cblxufVxuXG5cbi8vIFJldHVybiB0aGUgYmFja2dyb3VuZCBjb2xvciBvZiB0aGUgZ2l2ZW4gZWxlbWVudC4gSWYgdGhlIGNvbG9yIGlzXG4vLyBcInRyYW5zcGFyZW50XCIgKHRoZSBkZWZhdWx0IGluIE1vemlsbGEgYW5kIElFKSBvciBcInJnYmEoMCwgMCwgMCwgMClcIiAodGhlXG4vLyBkZWZhdWx0IHRyYW5zcGFyZW50IHZhbHVlIGluIEJsaW5rIGFuZCBXZWJraXQpLCB3YWxrIHVwIHRoZSBwYXJlbnQgY2hhaW5cbi8vIHVudGlsIGEgbm9uLXRyYW5zcGFyZW50IGNvbG9yIGlzIGZvdW5kLlxuZnVuY3Rpb24gZmluZEJhY2tncm91bmRDb2xvcihlbGVtZW50KSB7XG4gIGlmIChlbGVtZW50ID09IG51bGwgfHwgdHlwZW9mIGVsZW1lbnQuc3R5bGUgPT09ICd1bmRlZmluZWQnKSB7XG4gICAgLy8gVGhpcyBlbGVtZW50IGhhcyBubyBiYWNrZ3JvdW5kLCBhc3N1bWUgd2hpdGUuXG4gICAgcmV0dXJuICdyZ2IoMjU1LDI1NSwyNTUpJztcbiAgfVxuICBjb25zdCBiYWNrZ3JvdW5kQ29sb3IgPSBnZXRDb21wdXRlZFN0eWxlKGVsZW1lbnQpLmJhY2tncm91bmRDb2xvcjtcbiAgaWYgKGJhY2tncm91bmRDb2xvciA9PT0gJ3RyYW5zcGFyZW50JyB8fCBiYWNrZ3JvdW5kQ29sb3IgPT09ICdyZ2JhKDAsIDAsIDAsIDApJykge1xuICAgIHJldHVybiBmaW5kQmFja2dyb3VuZENvbG9yKGVsZW1lbnQucGFyZW50Tm9kZSk7XG4gIH0gZWxzZSB7XG4gICAgcmV0dXJuIGJhY2tncm91bmRDb2xvcjtcbiAgfVxufVxuXG5cbi8vIFJldHVybiB0aGUgaW5kaXZpZHVhbCBSR0IgdmFsdWVzIGZyb20gYSBDU1MgY29sb3Igc3RyaW5nLlxuZnVuY3Rpb24gZXh0cmFjdFJnYlZhbHVlcyhyZ2JTdHJpbmcpIHtcbiAgY29uc3QgcmdiUmVnZXggPSAvcmdiYT9cXChcXHMqKFxcZCspXFxzKixcXHMqKFxcZCspXFxzKixcXHMqKFxcZCspXFxzKig/OixcXHMqW1xcZFxcLl0rXFxzKik/XFwpLztcbiAgY29uc3QgbWF0Y2ggPSByZ2JSZWdleC5leGVjKHJnYlN0cmluZyk7XG4gIGlmIChtYXRjaCkge1xuICAgIHJldHVybiB7XG4gICAgICByOiBwYXJzZUludChtYXRjaFsxXSksXG4gICAgICBnOiBwYXJzZUludChtYXRjaFsyXSksXG4gICAgICBiOiBwYXJzZUludChtYXRjaFszXSlcbiAgICB9O1xuICB9IGVsc2Uge1xuICAgIHJldHVybiBudWxsO1xuICB9XG59XG5cblxuY3VzdG9tRWxlbWVudHMuZGVmaW5lKCdiYXNpYy1mYWRlLW92ZXJmbG93JywgRmFkZU92ZXJmbG93KTtcbmV4cG9ydCBkZWZhdWx0IEZhZGVPdmVyZmxvdztcbiJdfQ==
+!function e(t,n,r){function o(u,a){if(!n[u]){if(!t[u]){var c="function"==typeof require&&require;if(!a&&c)return c(u,!0);if(i)return i(u,!0);var f=new Error("Cannot find module '"+u+"'");throw f.code="MODULE_NOT_FOUND",f}var l=n[u]={exports:{}};t[u][0].call(l.exports,function(e){var n=t[u][1][e];return o(n?n:e)},l,l.exports,e,t,n,r)}return n[u].exports}for(var i="function"==typeof require&&require,u=0;u2&&void 0!==arguments[2]?arguments[2]:[];return Object.getOwnPropertyNames(e).forEach(function(r){if(n.indexOf(r)<0){var o=Object.getOwnPropertyDescriptor(e,r);Object.defineProperty(t,r,o)}}),t}Object.defineProperty(n,"__esModule",{value:!0});var c=function(){function e(e,t){for(var n=0;n0;)t.content.appendChild(n.childNodes[0]);return t}function c(e,t){window.WebComponents.ShadowCSS.shimStyling(e.content,t)}Object.defineProperty(n,"__esModule",{value:!0});var f=e("../src/symbols"),l=r(f);n.default=function(e){var t=function(e){function t(){o(this,t);var e=i(this,(t.__proto__||Object.getPrototypeOf(t)).call(this)),n=e[l.default.template];if(n){"string"==typeof n&&(n=a(n)),window.ShadowDOMPolyfill&&c(n,e.localName);var r=e.attachShadow({mode:"open"}),u=document.importNode(n.content,!0);r.appendChild(u)}return e}return u(t,e),t}(e);return t}},{"../src/symbols":8}],6:[function(e,t,n){"use strict";function r(e){return"function"==typeof Symbol?Symbol(e):"_"+e}Object.defineProperty(n,"__esModule",{value:!0}),n.default=r},{}],7:[function(e,t,n){"use strict";function r(e){return e&&e.__esModule?e:{default:e}}function o(e,t,n){if(null===n||"undefined"==typeof n)e.removeAttribute(t);else{var r=String(n);e.getAttribute(t)!==r&&e.setAttribute(t,n)}}Object.defineProperty(n,"__esModule",{value:!0});var i=e("./createSymbol"),u=r(i),a=e("./toggleClass"),c=r(a),f=(0,u.default)("safeToSetAttributes"),l=(0,u.default)("pendingAttributes"),s=(0,u.default)("pendingClasses");n.default={connected:function(e){if(e[f]=!0,e[l]){for(var t in e[l]){var n=e[l][t];o(e,t,n)}e[l]=null}if(e[s]){for(var r in e[s]){var i=e[s][r];(0,c.default)(e,r,i)}e[s]=null}},setAttribute:function(e,t,n){e[f]?o(e,t,n):(e[l]||(e[l]={}),e[l][t]=n)},toggleClass:function(e,t,n){e[f]?(0,c.default)(e,t,n):(e[s]||(e[s]={}),e[s][t]=n)}}},{"./createSymbol":6,"./toggleClass":9}],8:[function(e,t,n){"use strict";function r(e){return e&&e.__esModule?e:{default:e}}Object.defineProperty(n,"__esModule",{value:!0});var o=e("./createSymbol"),i=r(o),u={defaults:(0,i.default)("defaults"),dragging:(0,i.default)("dragging"),goDown:(0,i.default)("goDown"),goEnd:(0,i.default)("goEnd"),goLeft:(0,i.default)("goLeft"),goRight:(0,i.default)("goRight"),goStart:(0,i.default)("goStart"),goUp:(0,i.default)("goUp"),itemAdded:(0,i.default)("itemAdded"),itemsChanged:(0,i.default)("itemsChanged"),itemSelected:(0,i.default)("itemSelected"),keydown:(0,i.default)("keydown"),template:(0,i.default)("template")};n.default=u},{"./createSymbol":6}],9:[function(e,t,n){"use strict";function r(e,t,n){var r=e.classList,o="undefined"==typeof n?!r.contains(t):n;return o?r.add(t):r.remove(t),o}Object.defineProperty(n,"__esModule",{value:!0}),n.default=r},{}],10:[function(e,t,n){"use strict";function r(e){return e&&e.__esModule?e:{default:e}}function o(e,t){if(!(e instanceof t))throw new TypeError("Cannot call a class as a function")}function i(e,t){if(!e)throw new ReferenceError("this hasn't been initialised - super() hasn't been called");return!t||"object"!=typeof t&&"function"!=typeof t?e:t}function u(e,t){if("function"!=typeof t&&null!==t)throw new TypeError("Super expression must either be null or a function, not "+typeof t);e.prototype=Object.create(t&&t.prototype,{constructor:{value:e,enumerable:!1,writable:!0,configurable:!0}}),t&&(Object.setPrototypeOf?Object.setPrototypeOf(e,t):e.__proto__=t)}Object.defineProperty(n,"__esModule",{value:!0});var a=e("../../basic-component-mixins/src/AttributeMarshallingMixin"),c=r(a),f=e("../../basic-component-mixins/src/ComposableMixin"),l=r(f),s=e("../../basic-component-mixins/src/DistributedChildrenMixin"),p=r(s),d=e("../../basic-component-mixins/src/ShadowElementReferencesMixin"),b=r(d),y=e("../../basic-component-mixins/src/ShadowTemplateMixin"),h=r(y),_=function(e){function t(){return o(this,t),i(this,(t.__proto__||Object.getPrototypeOf(t)).apply(this,arguments))}return u(t,e),t}((0,l.default)(HTMLElement).compose(h.default,b.default,c.default,p.default));n.default=_},{"../../basic-component-mixins/src/AttributeMarshallingMixin":1,"../../basic-component-mixins/src/ComposableMixin":2,"../../basic-component-mixins/src/DistributedChildrenMixin":3,"../../basic-component-mixins/src/ShadowElementReferencesMixin":4,"../../basic-component-mixins/src/ShadowTemplateMixin":5}],11:[function(e,t,n){"use strict";function r(e){return e&&e.__esModule?e:{default:e}}var o=e("./src/FadeOverflow"),i=r(o);window.Basic=window.Basic||{},window.Basic.FadeOverflow=i.default},{"./src/FadeOverflow":12}],12:[function(e,t,n){"use strict";function r(e){return e&&e.__esModule?e:{default:e}}function o(e,t){if(!(e instanceof t))throw new TypeError("Cannot call a class as a function")}function i(e,t){if(!e)throw new ReferenceError("this hasn't been initialised - super() hasn't been called");return!t||"object"!=typeof t&&"function"!=typeof t?e:t}function u(e,t){if("function"!=typeof t&&null!==t)throw new TypeError("Super expression must either be null or a function, not "+typeof t);e.prototype=Object.create(t&&t.prototype,{constructor:{value:e,enumerable:!1,writable:!0,configurable:!0}}),t&&(Object.setPrototypeOf?Object.setPrototypeOf(e,t):e.__proto__=t)}function a(e){if(null==e||"undefined"==typeof e.style)return"rgb(255,255,255)";var t=getComputedStyle(e).backgroundColor;return"transparent"===t||"rgba(0, 0, 0, 0)"===t?a(e.parentNode):t}function c(e){var t=/rgba?\(\s*(\d+)\s*,\s*(\d+)\s*,\s*(\d+)\s*(?:,\s*[\d\.]+\s*)?\)/,n=t.exec(e);return n?{r:parseInt(n[1]),g:parseInt(n[2]),b:parseInt(n[3])}:null}Object.defineProperty(n,"__esModule",{value:!0});var f=function(){function e(e,t){for(var n=0;n\n :host {\n display: block;\n position: relative;\n overflow: hidden;\n }\n\n #fade {\n bottom: 0;\n height: 3em;\n max-height: 50%;\n pointer-events: none; /* Lets user interact with content through the fade. */\n position: absolute;\n width: 100%;\n }\n \n\n
\n \n '}}]),t}(b.default);customElements.define("basic-fade-overflow",m),n.default=m},{"../../basic-component-mixins/src/createSymbol":6,"../../basic-component-mixins/src/symbols":8,"../../basic-element-base/src/ElementBase":10}]},{},[11]);
+//# sourceMappingURL=basic-fade-overflow.js.map
diff --git a/packages/basic-fade-overflow/dist/basic-fade-overflow.js.map b/packages/basic-fade-overflow/dist/basic-fade-overflow.js.map
new file mode 100644
index 00000000..ee0b5420
--- /dev/null
+++ b/packages/basic-fade-overflow/dist/basic-fade-overflow.js.map
@@ -0,0 +1 @@
+{"version":3,"sources":["node_modules/browser-pack/_prelude.js","packages/basic-component-mixins/src/AttributeMarshallingMixin.js","packages/basic-component-mixins/src/ComposableMixin.js","packages/basic-component-mixins/src/DistributedChildrenMixin.js","packages/basic-component-mixins/src/ShadowElementReferencesMixin.js","packages/basic-component-mixins/src/ShadowTemplateMixin.js","packages/basic-component-mixins/src/createSymbol.js","packages/basic-component-mixins/src/safeAttributes.js","packages/basic-component-mixins/src/symbols.js","packages/basic-component-mixins/src/toggleClass.js","packages/basic-element-base/src/ElementBase.js","packages/basic-fade-overflow/globals.js","packages/basic-fade-overflow/src/FadeOverflow.js"],"names":["e","t","n","r","s","o","u","a","require","i","f","Error","code","l","exports","call","length","1","module","attributeToPropertyName","attributeName","propertyName","attributeToPropertyNames","hypenRegEx","replace","match","toUpperCase","attributesForClass","classFn","HTMLElement","Object","baseClass","getPrototypeOf","prototype","constructor","baseAttributes","propertyNames","getOwnPropertyNames","setterNames","filter","getOwnPropertyDescriptor","set","attributes","map","setterName","propertyNameToAttribute","diff","attribute","indexOf","concat","propertyNamesToAttributes","uppercaseRegEx","toLowerCase","_safeAttributes","base","AttributeMarshalling","_base","_classCallCheck","this","_possibleConstructorReturn","__proto__","apply","arguments","_inherits","_createClass","key","value","oldValue","newValue","_get","_safeAttributes2","default","connected","setAttribute","className","toggleClass","get","composeClass","mixin","Subclass","_base2","copyOwnProperties","NON_MIXABLE_OBJECT_PROPERTIES","source","target","ignorePropertyNames","undefined","forEach","name","descriptor","defineProperty","Composable","_len","mixins","Array","_key","reduce","expandContentElements","nodes","includeTextNodes","_ref","expanded","node","isSlot","HTMLSlotElement","localName","assignedNodes","flatten","Text","flattened","_toConsumableArray","DistributedChildren","children","childNodes","strings","distributedChildNodes","child","textContent","join","ShadowElementReferences","_this","shadowRoot","$","nodesWithIds","querySelectorAll","id","getAttribute","createTemplateWithInnerHTML","innerHTML","template","document","createElement","div","content","appendChild","shimTemplateStyles","tag","window","WebComponents","ShadowCSS","shimStyling","_symbols","ShadowTemplate","_symbols2","ShadowDOMPolyfill","root","attachShadow","mode","clone","importNode","createSymbol","description","Symbol","setAttributeToElement","element","removeAttribute","text","String","_createSymbol","_toggleClass2","safeToSetAttributesSymbol","_createSymbol2","pendingAttributesSymbol","pendingClassesSymbol","_value","_toggleClass3","symbols","defaults","dragging","goDown","goEnd","goLeft","goRight","goStart","goUp","itemAdded","itemsChanged","itemSelected","keydown","force","classList","addClass","contains","add","remove","_AttributeMarshallingMixin","_ComposableMixin","_DistributedChildrenMixin","_ShadowElementReferencesMixin","_ShadowTemplateMixin","ElementBase","_ComposableMixin2","compose","_ShadowTemplateMixin2","_ShadowElementReferencesMixin2","_AttributeMarshallingMixin2","_DistributedChildrenMixin2","_FadeOverflow","Basic","FadeOverflow","_FadeOverflow2","findBackgroundColor","style","backgroundColor","getComputedStyle","parentNode","extractRgbValues","rgbString","rgbRegex","exec","parseInt","g","b","_ElementBase2","fadeColorSymbol","fadeColor","refresh","rgb","fadeColorTransparent","gradient","fade","backgroundImage","display","customElements","define"],"mappings":"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","file":"basic-fade-overflow.js","sourcesContent":["(function e(t,n,r){function s(o,u){if(!n[o]){if(!t[o]){var a=typeof require==\"function\"&&require;if(!u&&a)return a(o,!0);if(i)return i(o,!0);var f=new Error(\"Cannot find module '\"+o+\"'\");throw f.code=\"MODULE_NOT_FOUND\",f}var l=n[o]={exports:{}};t[o][0].call(l.exports,function(e){var n=t[o][1][e];return s(n?n:e)},l,l.exports,e,t,n,r)}return n[o].exports}var i=typeof require==\"function\"&&require;for(var o=0;o {\n\n /**\n * Mixin which marshalls attributes to properties and vice versa.\n *\n * If your component exposes a setter for a property, it's generally a good\n * idea to let devs using your component be able to set that property in HTML\n * via an element attribute. You can code that yourself by writing an\n * `attributeChangedCallback`, or you can use this mixin to get a degree of\n * automatic support.\n *\n * This mixin implements an `attributeChangedCallback` that will attempt to\n * convert a change in an element attribute into a call to the corresponding\n * property setter. Attributes typically follow hyphenated names (\"foo-bar\"),\n * whereas properties typically use camelCase names (\"fooBar\"). This mixin\n * respects that convention, automatically mapping the hyphenated attribute\n * name to the corresponding camelCase property name.\n *\n * Example: You define a component using this mixin:\n *\n * class MyElement extends AttributeMarshallingMixin(HTMLElement) {\n * get fooBar() { return this._fooBar; }\n * set fooBar(value) { this._fooBar = value; }\n * }\n * customElements.define('my-element', MyElement);\n *\n * If someone then instantiates your component in HTML:\n *\n * \n *\n * Then, after the element has been upgraded, the `fooBar` setter will\n * automatically be invoked with the initial value \"Hello\".\n *\n * For the time being, this mixin only supports string-valued properties.\n * If you'd like to convert string attributes to other types (numbers,\n * booleans), you need to implement `attributeChangedCallback` yourself.\n */\n class AttributeMarshalling extends base {\n\n /*\n * Handle a change to the attribute with the given name.\n */\n attributeChangedCallback(attributeName, oldValue, newValue) {\n if (super.attributeChangedCallback) { super.attributeChangedCallback(); }\n const propertyName = attributeToPropertyName(attributeName);\n // If the attribute name corresponds to a property name, set the property.\n // Ignore standard HTMLElement properties handled by the DOM.\n if (propertyName in this && !(propertyName in HTMLElement.prototype)) {\n this[propertyName] = newValue;\n }\n }\n\n connectedCallback() {\n if (super.connectedCallback) { super.connectedCallback(); }\n safeAttributes.connected(this);\n }\n\n static get observedAttributes() {\n return attributesForClass(this);\n }\n\n /**\n * Set/unset the attribute with the indicated name.\n *\n * This method exists primarily to handle the case where an element wants to\n * set a default property value that should be reflected as an attribute. An\n * important limitation of custom element consturctors is that they cannot\n * set attributes. A call to `reflectAttribute` during the constructor will\n * be deferred until the element is connected to the document.\n *\n * @param {string} attribute - The name of the *attribute* (not property) to set.\n * @param {object} value - The value to set. If null, the attribute will be removed.\n */\n reflectAttribute(attribute, value) {\n return safeAttributes.setAttribute(this, attribute, value);\n }\n\n /**\n * Set/unset the class with the indicated name.\n *\n * This method exists primarily to handle the case where an element wants to\n * set a default property value that should be reflected as as class. An\n * important limitation of custom element consturctors is that they cannot\n * set attributes, including the `class` attribute. A call to\n * `reflectClass` during the constructor will be deferred until the element\n * is connected to the document.\n *\n * @param {string} className - The name of the class to set.\n * @param {object} value - True to set the class, false to remove it.\n */\n reflectClass(className, value) {\n return safeAttributes.toggleClass(this, className, value);\n }\n\n }\n\n return AttributeMarshalling;\n};\n\n\n// Convert hyphenated foo-bar attribute name to camel case fooBar property name.\nfunction attributeToPropertyName(attributeName) {\n let propertyName = attributeToPropertyNames[attributeName];\n if (!propertyName) {\n // Convert and memoize.\n const hypenRegEx = /-([a-z])/g;\n propertyName = attributeName.replace(hypenRegEx,\n match => match[1].toUpperCase());\n attributeToPropertyNames[attributeName] = propertyName;\n }\n return propertyName;\n}\n\nfunction attributesForClass(classFn) {\n\n // We treat the element base classes as if they have no attributes, since we\n // don't want to receive attributeChangedCallback for them.\n if (classFn === HTMLElement || classFn === Object) {\n return [];\n }\n\n // Get attributes for parent class.\n const baseClass = Object.getPrototypeOf(classFn.prototype).constructor;\n const baseAttributes = attributesForClass(baseClass);\n\n // Get attributes for this class.\n const propertyNames = Object.getOwnPropertyNames(classFn.prototype);\n const setterNames = propertyNames.filter(propertyName =>\n typeof Object.getOwnPropertyDescriptor(\n classFn.prototype, propertyName).set === 'function');\n const attributes = setterNames.map(setterName =>\n propertyNameToAttribute(setterName));\n\n // Merge.\n const diff = attributes.filter(attribute =>\n baseAttributes.indexOf(attribute) < 0);\n return baseAttributes.concat(diff);\n}\n\n// Convert a camel case fooBar property name to a hyphenated foo-bar attribute.\nfunction propertyNameToAttribute(propertyName) {\n let attribute = propertyNamesToAttributes[propertyName];\n if (!attribute) {\n // Convert and memoize.\n const uppercaseRegEx = /([A-Z])/g;\n attribute = propertyName.replace(uppercaseRegEx, '-$1').toLowerCase();\n }\n return attribute;\n}\n","/* Exported function extends a base class with Composable. */\nexport default (base) => {\n\n /**\n * Mixin to make a class more easily composable with other mixins.\n *\n * This mixin contributes a `compose` method that applies a set of mixin\n * functions and returns the resulting new class. This sugar can make the\n * application of many mixins at once easier to read.\n */\n class Composable extends base {\n\n /**\n * Apply a set of mixin functions or mixin objects to the present class and\n * return the new class.\n *\n * Instead of writing:\n *\n * let MyClass = Mixin1(Mixin2(Mixin3(Mixin4(Mixin5(BaseClass)))));\n *\n * You can write:\n *\n * let MyClass = ComposableMixin(BaseClass).compose(\n * Mixin1,\n * Mixin2,\n * Mixin3,\n * Mixin4,\n * Mixin5\n * );\n *\n * This function can also take mixin objects. A mixin object is just a\n * shorthand for a mixin function that creates a new subclass with the given\n * members. The mixin object's members are *not* copied directly onto the\n * prototype of the base class, as with traditional mixins.\n *\n * In addition to providing syntactic sugar, this mixin can be used to\n * define a class in ES5, which lacks ES6's `class` keyword.\n *\n * @param {...mixins} mixins - A set of mixin functions or objects to apply.\n */\n static compose(...mixins) {\n // We create a new subclass for each mixin in turn. The result becomes\n // the base class extended by any subsequent mixins. It turns out that\n // we can use Array.reduce() to concisely express this, using the current\n // object as the seed for reduce().\n return mixins.reduce(composeClass, this);\n }\n\n }\n\n return Composable;\n};\n\n\n// Properties defined by Object that we don't want to mixin.\nconst NON_MIXABLE_OBJECT_PROPERTIES = [\n 'constructor'\n];\n\n/*\n * Apply the mixin to the given base class to return a new class.\n * The mixin can either be a function that returns the modified class, or a\n * plain object whose members will be copied to the new class' prototype.\n */\nfunction composeClass(base, mixin) {\n if (typeof mixin === 'function') {\n // Mixin function\n return mixin(base);\n } else {\n // Mixin object\n class Subclass extends base {}\n copyOwnProperties(mixin, Subclass.prototype, NON_MIXABLE_OBJECT_PROPERTIES);\n return Subclass;\n }\n}\n\n\n/*\n * Copy the given properties/methods to the target.\n * Return the updated target.\n */\nfunction copyOwnProperties(source, target, ignorePropertyNames = []) {\n Object.getOwnPropertyNames(source).forEach(name => {\n if (ignorePropertyNames.indexOf(name) < 0) {\n const descriptor = Object.getOwnPropertyDescriptor(source, name);\n Object.defineProperty(target, name, descriptor);\n }\n });\n return target;\n}\n","/* Exported function extends a base class with DistributedChildren. */\nexport default (base) => {\n\n /**\n * Mixin which defines helpers for accessing a component's distributed\n * children as a flattened array or string.\n *\n * The standard DOM API provides several ways of accessing child content:\n * `children`, `childNodes`, and `textContent`. None of these functions are\n * Shadow DOM aware. This mixin defines variations of those functions that\n * *are* Shadow DOM aware.\n *\n * Example: you create a component `` that displays a number\n * equal to the number of children placed inside that component. If someone\n * instantiates your component like:\n *\n * \n *
\n *
\n *
\n * \n *\n * Then the component should show \"3\", because there are three children. To\n * calculate the number of children, the component can just calculate\n * `this.children.length`. However, suppose someone instantiates your\n * component inside one of their own components, and puts a `` element\n * inside your component:\n *\n * \n * \n * \n *\n * If your component only looks at `this.children`, it will always see exactly\n * one child — the `` element. But the user looking at the page will\n * *see* any nodes distributed to that slot. To match what the user sees, your\n * component should expand any `` elements it contains.\n *\n * That is the problem this mixin solves. After applying this mixin, your\n * component code has access to `this.distributedChildren`, whose `length`\n * will return the total number of all children distributed to your component\n * in the composed tree.\n *\n * Note: The latest Custom Elements API design calls for a new function,\n * `getAssignedNodes` that takes an optional `deep` parameter, that will solve\n * this problem at the API level.\n */\n class DistributedChildren extends base {\n\n /**\n * An in-order collection of distributed children, expanding any slot\n * elements. Like the standard children property, this skips text nodes.\n *\n * @type {HTMLElement[]}\n */\n get distributedChildren() {\n return expandContentElements(this.children, false);\n }\n\n /**\n * An in-order collection of distributed child nodes, expanding any slot\n * elements. Like the standard childNodes property, this includes text\n * nodes.\n *\n * @type {Node[]}\n */\n get distributedChildNodes() {\n return expandContentElements(this.childNodes, true);\n }\n\n /**\n * The concatenated text content of all distributed child nodes, expanding\n * any slot elements.\n *\n * @type {string}\n */\n get distributedTextContent() {\n const strings = this.distributedChildNodes.map(function(child) {\n return child.textContent;\n });\n return strings.join('');\n }\n\n }\n\n return DistributedChildren;\n};\n\n\n/*\n * Given a array of nodes, return a new array with any content elements expanded\n * to the nodes distributed to that content element. This rule is applied\n * recursively.\n *\n * If includeTextNodes is true, text nodes will be included, as in the\n * standard childNodes property; by default, this skips text nodes, like the\n * standard children property.\n */\nfunction expandContentElements(nodes, includeTextNodes) {\n const expanded = Array.prototype.map.call(nodes, node => {\n // We want to see if the node is an instanceof HTMLSlotELement, but\n // that class won't exist if the browser that doesn't support native\n // Shadow DOM and if the Shadow DOM polyfill hasn't been loaded. Instead,\n // we do a simplistic check to see if the tag name is \"slot\".\n const isSlot = typeof HTMLSlotElement !== 'undefined' ?\n node instanceof HTMLSlotElement :\n node.localName === 'slot';\n if (isSlot) {\n // Use the nodes assigned to this node instead.\n const assignedNodes = node.assignedNodes({ flatten: true });\n return assignedNodes ?\n expandContentElements(assignedNodes, includeTextNodes) :\n [];\n } else if (node instanceof HTMLElement) {\n // Plain element; use as is.\n return [node];\n } else if (node instanceof Text && includeTextNodes) {\n // Text node.\n return [node];\n } else {\n // Comment, processing instruction, etc.; skip.\n return [];\n }\n });\n const flattened = [].concat(...expanded);\n return flattened;\n}\n","/* Exported function extends a base class with ShadowElementReferences. */\nexport default (base) => {\n\n /**\n * Mixin to create references to elements in a component's Shadow DOM subtree.\n *\n * This adds a member on the component called `this.$` that can be used to\n * reference shadow elements with IDs. E.g., if component's shadow contains an\n * element ``, then this mixin will create a member\n * `this.$.foo` that points to that button.\n *\n * Such references simplify a component's access to its own elements. In\n * exchange, this mixin trades off a one-time cost of querying all elements in\n * the shadow tree instead of paying an ongoing cost to query for an element\n * each time the component wants to inspect or manipulate it.\n *\n * This mixin expects the component to define a Shadow DOM subtree. You can\n * create that tree yourself, or make use of\n * [ShadowTemplateMixin](ShadowTemplateMixin.md).\n *\n * This mixin is inspired by Polymer's [automatic\n * node finding](https://www.polymer-project.org/1.0/docs/devguide/local-dom.html#node-finding)\n * feature.\n */\n class ShadowElementReferences extends base {\n\n constructor() {\n super();\n if (this.shadowRoot) {\n // Look for elements in the shadow subtree that have id attributes.\n // An alternatively implementation of this mixin would be to just define\n // a this.$ getter that lazily does this search the first time someone\n // tries to access this.$. That might introduce some complexity – if the\n // the tree changed after it was first populated, the result of\n // searching for a node might be somewhat unpredictable.\n this.$ = {};\n const nodesWithIds = this.shadowRoot.querySelectorAll('[id]');\n [].forEach.call(nodesWithIds, node => {\n const id = node.getAttribute('id');\n this.$[id] = node;\n });\n }\n }\n\n /**\n * The collection of references to the elements with IDs in a component's\n * Shadow DOM subtree.\n *\n * @type {object}\n * @member $\n */\n }\n\n return ShadowElementReferences;\n};\n","import symbols from '../src/symbols';\n\n\n/* Exported function extends a base class with ShadowTemplate. */\nexport default (base) => {\n\n /**\n * Mixin for stamping a template into a Shadow DOM subtree upon component\n * instantiation.\n *\n * To use this mixin, define a `template` property as a string or HTML\n * `` element:\n *\n * class MyElement extends ShadowTemplateMixin(HTMLElement) {\n * get [symbols.template]() {\n * return `Hello, world .`;\n * }\n * }\n *\n * When your component class is instantiated, a shadow root will be created on\n * the instance, and the contents of the template will be cloned into the\n * shadow root. If your component does not define a `template` property, this\n * mixin has no effect.\n *\n * For the time being, this extension retains support for Shadow DOM v0. That\n * will eventually be deprecated as browsers (and the Shadow DOM polyfill)\n * implement Shadow DOM v1.\n */\n class ShadowTemplate extends base {\n\n /*\n * If the component defines a template, a shadow root will be created on the\n * component instance, and the template stamped into it.\n */\n constructor() {\n super();\n let template = this[symbols.template];\n // TODO: Save the processed template with the component's class prototype\n // so it doesn't need to be processed with every instantiation.\n if (template) {\n\n if (typeof template === 'string') {\n // Upgrade plain string to real template.\n template = createTemplateWithInnerHTML(template);\n }\n\n if (window.ShadowDOMPolyfill) {\n shimTemplateStyles(template, this.localName);\n }\n\n const root = this.attachShadow({ mode: 'open' });\n const clone = document.importNode(template.content, true);\n root.appendChild(clone);\n }\n }\n\n }\n\n return ShadowTemplate;\n};\n\n\n// Convert a plain string of HTML into a real template element.\nfunction createTemplateWithInnerHTML(innerHTML) {\n const template = document.createElement('template');\n // REVIEW: Is there an easier way to do this?\n // We'd like to just set innerHTML on the template content, but since it's\n // a DocumentFragment, that doesn't work.\n const div = document.createElement('div');\n div.innerHTML = innerHTML;\n while (div.childNodes.length > 0) {\n template.content.appendChild(div.childNodes[0]);\n }\n return template;\n}\n\n// Invoke basic style shimming with ShadowCSS.\nfunction shimTemplateStyles(template, tag) {\n window.WebComponents.ShadowCSS.shimStyling(template.content, tag);\n}\n","/**\n * Helper function to create a symbol that can be used for associating private\n * data with an element.\n *\n * Mixins and component classes often want to associate private data with an\n * element instance, but JavaScript does not have direct support for true\n * private properties. One approach is to use the\n * [Symbol](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Symbol)\n * data type to set and retrieve data on an element.\n *\n * Unfortunately, the Symbol type is not available in Internet Explorer 11. The\n * `createSymbol` helper function exists as a workaround for IE 11. Rather than\n * returning a true Symbol, it simply returns an underscore-prefixed string.\n *\n * Usage:\n *\n * const fooSymbol = createSymbol('foo');\n *\n * class MyElement extends HTMLElement {\n * get foo() {\n * return this[fooSymbol];\n * }\n * set foo(value) {\n * this[fooSymbol] = value;\n * }\n * }\n *\n * In IE 11, this sample will \"hide\" data behind an instance property this._foo.\n * The use of the underscore is meant to reduce (not eliminate) the potential\n * for name conflicts, and discourage (not prevent) external access to this\n * data. In modern browsers, the above code will eliminate the potential of\n * naming conflicts, and better hide the data behind a real Symbol.\n *\n * @function createSymbol\n * @param {string} description - A string to identify the symbol when debugging\n */\nexport default function createSymbol(description) {\n return typeof Symbol === 'function' ?\n Symbol(description) :\n `_${description}`;\n}\n","import createSymbol from './createSymbol';\nimport toggleClass from './toggleClass';\n\n\n// Symbols for private data members on an element.\nconst safeToSetAttributesSymbol = createSymbol('safeToSetAttributes');\nconst pendingAttributesSymbol = createSymbol('pendingAttributes');\nconst pendingClassesSymbol = createSymbol('pendingClasses');\n\n\n/**\n * Helper functions for updating attributes, including the `class` attribute.\n */\nexport default {\n\n /**\n * Perform any pending updates to attributes and classes.\n *\n * This writes any `setAttribute` or `toggleClass` values that were performed\n * before an element was attached to the document for the first time.\n *\n * This method should be called by mixins/components in their\n * `connectedCallback`. If mulitple mixins/components invoke this during the\n * same `connectedCallback`, only the first call will have any effect. The\n * subsequent calls will be harmless.\n *\n * @param {HTMLElement} element - The element being added to the document.\n */\n connected(element) {\n element[safeToSetAttributesSymbol] = true;\n\n // Set any pending attributes.\n if (element[pendingAttributesSymbol]) {\n for (let attribute in element[pendingAttributesSymbol]) {\n const value = element[pendingAttributesSymbol][attribute];\n setAttributeToElement(element, attribute, value);\n }\n element[pendingAttributesSymbol] = null;\n }\n\n // Set any pending classes.\n if (element[pendingClassesSymbol]) {\n for (let className in element[pendingClassesSymbol]) {\n const value = element[pendingClassesSymbol][className];\n toggleClass(element, className, value);\n }\n element[pendingClassesSymbol] = null;\n }\n },\n\n /**\n * Set/unset the attribute with the indicated name.\n *\n * This method exists primarily to handle the case where an element wants to\n * set a default property value that should be reflected as an attribute. An\n * important limitation of custom element consturctors is that they cannot\n * set attributes. A call to `setAttribute` during the constructor will\n * be deferred until the element is connected to the document.\n *\n * @param {string} attribute - The name of the *attribute* (not property) to set.\n * @param {object} value - The value to set. If null, the attribute will be removed.\n */\n setAttribute(element, attribute, value) {\n if (element[safeToSetAttributesSymbol]) {\n // Safe to set attributes immediately.\n setAttributeToElement(element, attribute, value);\n } else {\n // Defer setting attributes until the first time we're connected.\n if (!element[pendingAttributesSymbol]) {\n element[pendingAttributesSymbol] = {};\n }\n element[pendingAttributesSymbol][attribute] = value;\n }\n },\n\n /**\n * Set/unset the class with the indicated name.\n *\n * This method exists primarily to handle the case where an element wants to\n * set a default property value that should be reflected as as class. An\n * important limitation of custom element consturctors is that they cannot\n * set attributes, including the `class` attribute. A call to\n * `toggleClass` during the constructor will be deferred until the element\n * is connected to the document.\n *\n * @param {string} className - The name of the class to set.\n * @param {object} value - True to set the class, false to remove it.\n */\n toggleClass(element, className, value) {\n if (element[safeToSetAttributesSymbol]) {\n // Safe to set class immediately.\n toggleClass(element, className, value);\n } else {\n // Defer setting class until the first time we're connected.\n if (!element[pendingClassesSymbol]) {\n element[pendingClassesSymbol] = {};\n }\n element[pendingClassesSymbol][className] = value;\n }\n }\n\n};\n\n\n// Reflect the attribute to the given element.\n// If the value is null, remove the attribute.\nfunction setAttributeToElement(element, attributeName, value) {\n if (value === null || typeof value === 'undefined') {\n element.removeAttribute(attributeName);\n } else {\n const text = String(value);\n // Avoid recursive attributeChangedCallback calls.\n if (element.getAttribute(attributeName) !== text) {\n element.setAttribute(attributeName, value);\n }\n }\n}\n","import createSymbol from './createSymbol';\n\n/**\n * A collection of Symbol objects for standard component properties and methods.\n *\n * These Symbol objects are used to allow mixins and a component to internally\n * communicate, without exposing these properties and methods in the component's\n * public API.\n *\n * To use these Symbol objects in your own component, include this module and\n * then create a property or method whose key is the desired Symbol.\n *\n * import 'SingleSelectionMixin' from 'basic-component-mixins/src/SingleSelectionMixin';\n * import 'symbols' from 'basic-component-mixins/src/symbols';\n *\n * class MyElement extends SingleSelectionMixin(HTMLElement) {\n * [symbols.itemSelected](item, selected) {\n * // This will be invoked whenever an item is selected/deselected.\n * }\n * }\n *\n * @module symbols\n */\nconst symbols = {\n\n /**\n * Symbol for the `defaults` property.\n *\n * This property can be used to set or override defaults that will be applied\n * to a new component instance. When implementing this property, take care to\n * first acquire any defaults defined by the superclass. The standard idiom is\n * as follows:\n *\n * get [symbols.defaults]() {\n * const defaults = super[symbols.defaults] || {};\n * // Set or override default values here\n * defaults.customProperty = false;\n * return defaults;\n * }\n *\n * @var {object} defaults\n */\n defaults: createSymbol('defaults'),\n\n /**\n * Symbol for the `dragging` property.\n *\n * Components like carousels often define animated CSS transitions for\n * sliding effects. Such a transition should usually *not* be applied while\n * the user is dragging, because a CSS animation will introduce a lag that\n * makes the swipe feel sluggish. Instead, as long as the user is dragging\n * with their finger down, the transition should be suppressed. When the\n * user releases their finger, the transition can be restored, allowing the\n * animation to show the carousel sliding into its final position.\n *\n * @type {boolean} true if a drag is in progress, false if not.\n */\n dragging: createSymbol('dragging'),\n\n /**\n * Symbol for the `goDown` method.\n *\n * This method is invoked when the user wants to go/navigate down.\n *\n * @function goDown\n */\n goDown: createSymbol('goDown'),\n\n /**\n * Symbol for the `goEnd` method.\n *\n * This method is invoked when the user wants to go/navigate to the end (e.g.,\n * of a list).\n *\n * @function goEnd\n */\n goEnd: createSymbol('goEnd'),\n\n /**\n * Symbol for the `goLeft` method.\n *\n * This method is invoked when the user wants to go/navigate left.\n *\n * @function goLeft\n */\n goLeft: createSymbol('goLeft'),\n\n /**\n * Symbol for the `goRight` method.\n *\n * This method is invoked when the user wants to go/navigate right.\n *\n * @function goRight\n */\n goRight: createSymbol('goRight'),\n\n /**\n * Symbol for the `goStart` method.\n *\n * This method is invoked when the user wants to go/navigate to the start\n * (e.g., of a list).\n *\n * @function goStart\n */\n goStart: createSymbol('goStart'),\n\n /**\n * Symbol for the `goUp` method.\n *\n * This method is invoked when the user wants to go/navigate up.\n *\n * @function goUp\n */\n goUp: createSymbol('goUp'),\n\n /**\n * Symbol for the `itemAdded` method.\n *\n * This method is invoked when a new item is added to a list.\n *\n * @function itemAdded\n * @param {HTMLElement} item - the item being selected/deselected\n */\n itemAdded: createSymbol('itemAdded'),\n\n\n /**\n * Symbol for the `itemsChanged` method.\n *\n * This method is invoked when the underlying contents change. It is also\n * invoked on component initialization – since the items have \"changed\" from\n * being nothing.\n */\n itemsChanged: createSymbol('itemsChanged'),\n\n /**\n * Symbol for the `itemSelected` method.\n *\n * This method is invoked when an item becomes selected or deselected.\n *\n * @function itemSelected\n * @param {HTMLElement} item - the item being selected/deselected\n * @param {boolean} selected - true if the item is selected, false if not\n */\n itemSelected: createSymbol('itemSelected'),\n\n /**\n * Symbol for the `keydown` method.\n *\n * This method is invoked when an element receives a `keydown` event.\n *\n * @function keydown\n * @param {KeyboardEvent} event - the event being processed\n */\n keydown: createSymbol('keydown'),\n\n /**\n * Symbol for the `template` property.\n *\n * This property returns a component's template.\n *\n * @type {string|HTMLElement}\n */\n template: createSymbol('template')\n};\n\nexport default symbols;\n","/**\n * Helper function for standard classList.toggle() behavior on old browsers,\n * namely IE 11.\n *\n * The standard\n * [classlist](https://developer.mozilla.org/en-US/docs/Web/API/Element/classList)\n * object has a `toggle()` function that supports a second Boolean parameter\n * that can be used to succinctly turn a class on or off. This feature is often\n * useful in designing custom elements, which may want to externally reflect\n * component state in a CSS class that can be used for styling purposes.\n *\n * Unfortunately, IE 11 does not support the Boolean parameter to\n * `classList.toggle()`. This helper function behaves like the standard\n * `toggle()`, including support for the Boolean parameter, so that it can be\n * used even on IE 11.\n *\n * @function toggleClass\n * @param {HTMLElement} element - The element to modify\n * @param {string} className - The class to add/remove\n * @param {boolean} [force] - Force the class to be added (if true) or removed\n * (if false)\n */\nexport default function toggleClass(element, className, force) {\n const classList = element.classList;\n const addClass = (typeof force === 'undefined') ?\n !classList.contains(className) :\n force;\n if (addClass) {\n classList.add(className);\n } else {\n classList.remove(className);\n }\n return addClass;\n}\n","import AttributeMarshallingMixin from '../../basic-component-mixins/src/AttributeMarshallingMixin';\nimport ComposableMixin from '../../basic-component-mixins/src/ComposableMixin';\nimport DistributedChildrenMixin from '../../basic-component-mixins/src/DistributedChildrenMixin';\nimport ShadowElementReferencesMixin from '../../basic-component-mixins/src/ShadowElementReferencesMixin';\nimport ShadowTemplateMixin from '../../basic-component-mixins/src/ShadowTemplateMixin';\n\n\n/**\n * A sample general-purpose base class for defining custom elements that mixes\n * in some common features: template stamping into a shadow root, shadow element\n * references, marshalling attributes to properties, and retrieving the children\n * distributed to a component.\n *\n * This base class is not special in any way, and is defined only as a\n * convenient shorthand for applying the mixins listed above. You can use this\n * class as a base class for your own elements, or easily create your own base\n * class by applying the same set of mixins.\n *\n * The ElementBase base class does not register itself as a custom element with\n * the browser, and hence cannot be independently instantiated.\n *\n * @mixes AttributeMarshallingMixin\n * @mixes ComposableMixin\n * @mixes DistributedChildrenMixin\n * @mixes ShadowElementReferencesMixin\n * @mixes ShadowTemplateMixin\n */\nclass ElementBase extends ComposableMixin(HTMLElement).compose(\n ShadowTemplateMixin, // before node finding, so shadow root is populated\n ShadowElementReferencesMixin, // before marshalling, so properties can use refs\n AttributeMarshallingMixin,\n DistributedChildrenMixin\n) {}\n\nexport default ElementBase;\n","/*\n * This file is transpiled to create an ES5-compatible distribution in which\n * the package's main feature(s) are available via the window.Basic global.\n * If you're already using ES6 yourself, ignore this file, and instead import\n * the source file(s) you want from the src folder.\n */\n\nimport FadeOverflow from './src/FadeOverflow';\n\nwindow.Basic = window.Basic || {};\nwindow.Basic.FadeOverflow = FadeOverflow;\n","import createSymbol from '../../basic-component-mixins/src/createSymbol';\nimport ElementBase from '../../basic-element-base/src/ElementBase';\nimport symbols from '../../basic-component-mixins/src/symbols';\n\n\n// Symbols for private data members on an element.\nconst fadeColorSymbol = createSymbol('fadeColor');\n\n\n/**\n * Fades out content that overflows so the user knows there's more.\n *\n * This component doesn't handle interactivity.\n *\n * The component needs to know the color it should fade to, which it tries to\n * infer from the background color. In some situations, this may not work, in\n * which case you can explicitly set the fadeColor attribute.\n *\n * The component currently always displays the fade, even if the component's\n * content is short enough to fit completely in view.\n *\n * @extends ElementBase\n */\nclass FadeOverflow extends ElementBase {\n\n connectedCallback() {\n if (super.connectedCallback) { super.connectedCallback(); }\n if (this.fadeColor == null) {\n this.refresh();\n }\n }\n\n /**\n * The color of the fade.\n *\n * The fade color should match the background color. The component does its\n * best to infer the background color, but in some situations, that may not\n * work. In those cases, you can manually identify the background color.\n * This should be a solid color.\n *\n * @attribute fadeColor\n * @default white\n */\n get fadeColor() {\n return this[fadeColorSymbol];\n }\n set fadeColor(value) {\n this[fadeColorSymbol] = value;\n if (value) {\n const rgb = extractRgbValues(value);\n if (rgb) {\n const fadeColorTransparent = `rgba(${rgb.r},${rgb.g},${rgb.b},0)`;\n const gradient = `linear-gradient(${fadeColorTransparent} 0%, ${value} 100%)`;\n this.$.fade.style.backgroundImage = gradient;\n }\n }\n }\n\n /**\n * Infer the fade color from background color. If you have programmatically\n * changed the color behind the component, you can invoke this method to have\n * the component try to pick up the new background color.\n */\n refresh() {\n // TODO: Automatically hide the fade if all the content can be seen.\n this.fadeColor = findBackgroundColor(this);\n }\n\n /**\n * True if the component should show the fade to the background color.\n *\n * @type {boolean}\n * @default true\n */\n get showFade() {\n return this.$.fade.style.display !== 'none';\n }\n set showFade(value) {\n this.$.fade.style.display = value ? '' : 'none';\n }\n\n get [symbols.template]() {\n return `\n \n\n
\n \n `;\n }\n\n}\n\n\n// Return the background color of the given element. If the color is\n// \"transparent\" (the default in Mozilla and IE) or \"rgba(0, 0, 0, 0)\" (the\n// default transparent value in Blink and Webkit), walk up the parent chain\n// until a non-transparent color is found.\nfunction findBackgroundColor(element) {\n if (element == null || typeof element.style === 'undefined') {\n // This element has no background, assume white.\n return 'rgb(255,255,255)';\n }\n const backgroundColor = getComputedStyle(element).backgroundColor;\n if (backgroundColor === 'transparent' || backgroundColor === 'rgba(0, 0, 0, 0)') {\n return findBackgroundColor(element.parentNode);\n } else {\n return backgroundColor;\n }\n}\n\n\n// Return the individual RGB values from a CSS color string.\nfunction extractRgbValues(rgbString) {\n const rgbRegex = /rgba?\\(\\s*(\\d+)\\s*,\\s*(\\d+)\\s*,\\s*(\\d+)\\s*(?:,\\s*[\\d\\.]+\\s*)?\\)/;\n const match = rgbRegex.exec(rgbString);\n if (match) {\n return {\n r: parseInt(match[1]),\n g: parseInt(match[2]),\n b: parseInt(match[3])\n };\n } else {\n return null;\n }\n}\n\n\ncustomElements.define('basic-fade-overflow', FadeOverflow);\nexport default FadeOverflow;\n"]}
\ No newline at end of file
diff --git a/packages/basic-fade-overflow/index.html b/packages/basic-fade-overflow/index.html
index 9bf11d25..4bfc2367 100644
--- a/packages/basic-fade-overflow/index.html
+++ b/packages/basic-fade-overflow/index.html
@@ -7,7 +7,8 @@
basic-collapsible-panel
-
+
+
diff --git a/packages/basic-list-box/dist/basic-list-box.js b/packages/basic-list-box/dist/basic-list-box.js
index f95edede..ef0197e2 100644
--- a/packages/basic-list-box/dist/basic-list-box.js
+++ b/packages/basic-list-box/dist/basic-list-box.js
@@ -1,3974 +1,3 @@
-(function e(t,n,r){function s(o,u){if(!n[o]){if(!t[o]){var a=typeof require=="function"&&require;if(!u&&a)return a(o,!0);if(i)return i(o,!0);var f=new Error("Cannot find module '"+o+"'");throw f.code="MODULE_NOT_FOUND",f}var l=n[o]={exports:{}};t[o][0].call(l.exports,function(e){var n=t[o][1][e];return s(n?n:e)},l,l.exports,e,t,n,r)}return n[o].exports}var i=typeof require=="function"&&require;for(var o=0;o
- *
- * Then, after the element has been upgraded, the `fooBar` setter will
- * automatically be invoked with the initial value "Hello".
- *
- * For the time being, this mixin only supports string-valued properties.
- * If you'd like to convert string attributes to other types (numbers,
- * booleans), you need to implement `attributeChangedCallback` yourself.
- */
- var AttributeMarshalling = function (_base) {
- _inherits(AttributeMarshalling, _base);
-
- function AttributeMarshalling() {
- _classCallCheck(this, AttributeMarshalling);
-
- return _possibleConstructorReturn(this, (AttributeMarshalling.__proto__ || Object.getPrototypeOf(AttributeMarshalling)).apply(this, arguments));
- }
-
- _createClass(AttributeMarshalling, [{
- key: 'attributeChangedCallback',
-
-
- /*
- * Handle a change to the attribute with the given name.
- */
- value: function attributeChangedCallback(attributeName, oldValue, newValue) {
- if (_get(AttributeMarshalling.prototype.__proto__ || Object.getPrototypeOf(AttributeMarshalling.prototype), 'attributeChangedCallback', this)) {
- _get(AttributeMarshalling.prototype.__proto__ || Object.getPrototypeOf(AttributeMarshalling.prototype), 'attributeChangedCallback', this).call(this);
- }
- var propertyName = attributeToPropertyName(attributeName);
- // If the attribute name corresponds to a property name, set the property.
- // Ignore standard HTMLElement properties handled by the DOM.
- if (propertyName in this && !(propertyName in HTMLElement.prototype)) {
- this[propertyName] = newValue;
- }
- }
- }, {
- key: 'connectedCallback',
- value: function connectedCallback() {
- if (_get(AttributeMarshalling.prototype.__proto__ || Object.getPrototypeOf(AttributeMarshalling.prototype), 'connectedCallback', this)) {
- _get(AttributeMarshalling.prototype.__proto__ || Object.getPrototypeOf(AttributeMarshalling.prototype), 'connectedCallback', this).call(this);
- }
- _safeAttributes2.default.connected(this);
- }
- }, {
- key: 'reflectAttribute',
-
-
- /**
- * Set/unset the attribute with the indicated name.
- *
- * This method exists primarily to handle the case where an element wants to
- * set a default property value that should be reflected as an attribute. An
- * important limitation of custom element consturctors is that they cannot
- * set attributes. A call to `reflectAttribute` during the constructor will
- * be deferred until the element is connected to the document.
- *
- * @param {string} attribute - The name of the *attribute* (not property) to set.
- * @param {object} value - The value to set. If null, the attribute will be removed.
- */
- value: function reflectAttribute(attribute, value) {
- return _safeAttributes2.default.setAttribute(this, attribute, value);
- }
-
- /**
- * Set/unset the class with the indicated name.
- *
- * This method exists primarily to handle the case where an element wants to
- * set a default property value that should be reflected as as class. An
- * important limitation of custom element consturctors is that they cannot
- * set attributes, including the `class` attribute. A call to
- * `reflectClass` during the constructor will be deferred until the element
- * is connected to the document.
- *
- * @param {string} className - The name of the class to set.
- * @param {object} value - True to set the class, false to remove it.
- */
-
- }, {
- key: 'reflectClass',
- value: function reflectClass(className, value) {
- return _safeAttributes2.default.toggleClass(this, className, value);
- }
- }], [{
- key: 'observedAttributes',
- get: function get() {
- return attributesForClass(this);
- }
- }]);
-
- return AttributeMarshalling;
- }(base);
-
- return AttributeMarshalling;
-};
-
-// Convert hyphenated foo-bar attribute name to camel case fooBar property name.
-
-
-function attributeToPropertyName(attributeName) {
- var propertyName = attributeToPropertyNames[attributeName];
- if (!propertyName) {
- // Convert and memoize.
- var hypenRegEx = /-([a-z])/g;
- propertyName = attributeName.replace(hypenRegEx, function (match) {
- return match[1].toUpperCase();
- });
- attributeToPropertyNames[attributeName] = propertyName;
- }
- return propertyName;
-}
-
-function attributesForClass(classFn) {
-
- // We treat the element base classes as if they have no attributes, since we
- // don't want to receive attributeChangedCallback for them.
- if (classFn === HTMLElement || classFn === Object) {
- return [];
- }
-
- // Get attributes for parent class.
- var baseClass = Object.getPrototypeOf(classFn.prototype).constructor;
- var baseAttributes = attributesForClass(baseClass);
-
- // Get attributes for this class.
- var propertyNames = Object.getOwnPropertyNames(classFn.prototype);
- var setterNames = propertyNames.filter(function (propertyName) {
- return typeof Object.getOwnPropertyDescriptor(classFn.prototype, propertyName).set === 'function';
- });
- var attributes = setterNames.map(function (setterName) {
- return propertyNameToAttribute(setterName);
- });
-
- // Merge.
- var diff = attributes.filter(function (attribute) {
- return baseAttributes.indexOf(attribute) < 0;
- });
- return baseAttributes.concat(diff);
-}
-
-// Convert a camel case fooBar property name to a hyphenated foo-bar attribute.
-function propertyNameToAttribute(propertyName) {
- var attribute = propertyNamesToAttributes[propertyName];
- if (!attribute) {
- // Convert and memoize.
- var uppercaseRegEx = /([A-Z])/g;
- attribute = propertyName.replace(uppercaseRegEx, '-$1').toLowerCase();
- }
- return attribute;
-}
-
-},{"./safeAttributes":22}],2:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
-
-var _set = function set(object, property, value, receiver) { var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent !== null) { set(parent, property, value, receiver); } } else if ("value" in desc && desc.writable) { desc.value = value; } else { var setter = desc.set; if (setter !== undefined) { setter.call(receiver, value); } } return value; };
-
-var _get = function get(object, property, receiver) { if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { return get(parent, property, receiver); } } else if ("value" in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } };
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-/* Exported function extends a base class with ClickSelection. */
-exports.default = function (base) {
-
- /**
- * Mixin which maps a click (actually, a mousedown) to a selection.
- *
- * This simple mixin is useful in list box-like elements, where a click on a
- * list item implicitly selects it.
- *
- * This mixin expects the component to provide an `items` property. You can
- * provide that property yourself, or use
- * [ContentItemsMixin](ContentItemsMixin.md). This mixin also expects the
- * component to define a `selectedIndex` property. You can provide that
- * yourself, or use [SingleSelectionMixin](SingleSelectionMixin.md).
- */
- var ClickSelection = function (_base) {
- _inherits(ClickSelection, _base);
-
- function ClickSelection() {
- _classCallCheck(this, ClickSelection);
-
- /*
- * REVIEW: Which event should we listen to here?
- *
- * The standard use for this mixin is in list boxes. List boxes don't
- * appear to be consistent with regard to whether they select on mousedown
- * or click/mouseup.
- */
- var _this = _possibleConstructorReturn(this, (ClickSelection.__proto__ || Object.getPrototypeOf(ClickSelection)).call(this));
-
- _this.addEventListener('mousedown', function (event) {
- // HACK: If the item is a button, the event seems to be raised in
- // phase 2 (AT_TARGET), but the target is the component, not item.
- // Need to invesigate.
- var target = event.target === _this ? event.path[0] : event.target;
- var index = indexOfContainingItem(_this, target);
- if (index >= 0) {
- _this.selectedIndex = index;
- // Note: We don't call preventDefault here. The default behavior for
- // mousedown includes setting keyboard focus if the element doesn't
- // already have the focus, and we want to preserve that behavior.
- event.stopPropagation();
- }
- });
- return _this;
- }
-
- // Default implementation. This will typically be handled by other mixins.
-
-
- _createClass(ClickSelection, [{
- key: 'selectedIndex',
- get: function get() {
- return _get(ClickSelection.prototype.__proto__ || Object.getPrototypeOf(ClickSelection.prototype), 'selectedIndex', this);
- },
- set: function set(index) {
- if ('selectedIndex' in base.prototype) {
- _set(ClickSelection.prototype.__proto__ || Object.getPrototypeOf(ClickSelection.prototype), 'selectedIndex', index, this);
- }
- }
- }]);
-
- return ClickSelection;
- }(base);
-
- return ClickSelection;
-};
-
-/*
- * Return index of the element items that either is or contains the indicated
- * target. Return -1 if not found.
- */
-
-
-function indexOfContainingItem(element, target) {
- var items = element.items;
- var itemCount = items ? items.length : 0;
- for (var i = 0; i < itemCount; i++) {
- var item = items[i];
- if (item === target || item.contains(target)) {
- return i;
- }
- }
- return -1;
-}
-
-},{}],3:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-/* Exported function extends a base class with Composable. */
-exports.default = function (base) {
-
- /**
- * Mixin to make a class more easily composable with other mixins.
- *
- * This mixin contributes a `compose` method that applies a set of mixin
- * functions and returns the resulting new class. This sugar can make the
- * application of many mixins at once easier to read.
- */
- var Composable = function (_base) {
- _inherits(Composable, _base);
-
- function Composable() {
- _classCallCheck(this, Composable);
-
- return _possibleConstructorReturn(this, (Composable.__proto__ || Object.getPrototypeOf(Composable)).apply(this, arguments));
- }
-
- _createClass(Composable, null, [{
- key: 'compose',
-
-
- /**
- * Apply a set of mixin functions or mixin objects to the present class and
- * return the new class.
- *
- * Instead of writing:
- *
- * let MyClass = Mixin1(Mixin2(Mixin3(Mixin4(Mixin5(BaseClass)))));
- *
- * You can write:
- *
- * let MyClass = ComposableMixin(BaseClass).compose(
- * Mixin1,
- * Mixin2,
- * Mixin3,
- * Mixin4,
- * Mixin5
- * );
- *
- * This function can also take mixin objects. A mixin object is just a
- * shorthand for a mixin function that creates a new subclass with the given
- * members. The mixin object's members are *not* copied directly onto the
- * prototype of the base class, as with traditional mixins.
- *
- * In addition to providing syntactic sugar, this mixin can be used to
- * define a class in ES5, which lacks ES6's `class` keyword.
- *
- * @param {...mixins} mixins - A set of mixin functions or objects to apply.
- */
- value: function compose() {
- for (var _len = arguments.length, mixins = Array(_len), _key = 0; _key < _len; _key++) {
- mixins[_key] = arguments[_key];
- }
-
- // We create a new subclass for each mixin in turn. The result becomes
- // the base class extended by any subsequent mixins. It turns out that
- // we can use Array.reduce() to concisely express this, using the current
- // object as the seed for reduce().
- return mixins.reduce(composeClass, this);
- }
- }]);
-
- return Composable;
- }(base);
-
- return Composable;
-};
-
-// Properties defined by Object that we don't want to mixin.
-
-
-var NON_MIXABLE_OBJECT_PROPERTIES = ['constructor'];
-
-/*
- * Apply the mixin to the given base class to return a new class.
- * The mixin can either be a function that returns the modified class, or a
- * plain object whose members will be copied to the new class' prototype.
- */
-function composeClass(base, mixin) {
- if (typeof mixin === 'function') {
- // Mixin function
- return mixin(base);
- } else {
- // Mixin object
- var Subclass = function (_base2) {
- _inherits(Subclass, _base2);
-
- function Subclass() {
- _classCallCheck(this, Subclass);
-
- return _possibleConstructorReturn(this, (Subclass.__proto__ || Object.getPrototypeOf(Subclass)).apply(this, arguments));
- }
-
- return Subclass;
- }(base);
-
- copyOwnProperties(mixin, Subclass.prototype, NON_MIXABLE_OBJECT_PROPERTIES);
- return Subclass;
- }
-}
-
-/*
- * Copy the given properties/methods to the target.
- * Return the updated target.
- */
-function copyOwnProperties(source, target) {
- var ignorePropertyNames = arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : [];
-
- Object.getOwnPropertyNames(source).forEach(function (name) {
- if (ignorePropertyNames.indexOf(name) < 0) {
- var descriptor = Object.getOwnPropertyDescriptor(source, name);
- Object.defineProperty(target, name, descriptor);
- }
- });
- return target;
-}
-
-},{}],4:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
-
-var _get = function get(object, property, receiver) { if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { return get(parent, property, receiver); } } else if ("value" in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } };
-
-var _createSymbol = require('./createSymbol');
-
-var _createSymbol2 = _interopRequireDefault(_createSymbol);
-
-var _toggleClass = require('./toggleClass');
-
-var _toggleClass2 = _interopRequireDefault(_toggleClass);
-
-var _symbols = require('./symbols');
-
-var _symbols2 = _interopRequireDefault(_symbols);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-// Symbols for private data members on an element.
-var itemsSymbol = (0, _createSymbol2.default)('items');
-var itemInitializedSymbol = (0, _createSymbol2.default)('itemInitialized');
-
-/* Exported function extends a base class with ContentItems. */
-
-exports.default = function (base) {
-
- /**
- * Mixin which maps content semantics (elements) to list item semantics.
- *
- * Items differ from element contents in several ways:
- *
- * * They are often referenced via index.
- * * They may have a selection state.
- * * It's common to do work to initialize the appearance or state of a new
- * item.
- * * Auxiliary invisible child elements are filtered out and not counted as
- * items. Auxiliary elements include link, script, style, and template
- * elements. This filtering ensures that those auxiliary elements can be
- * used in markup inside of a list without being treated as list items.
- *
- * This mixin expects a component to provide a `content` property returning a
- * raw set of elements. You can provide that yourself, or use
- * [DistributedChildrenContentMixin](DistributedChildrenContentMixin.md).
- *
- * The most commonly referenced property defined by this mixin is the `items`
- * property. To avoid having to do work each time that property is requested,
- * this mixin supports an optimized mode. If you invoke the `contentChanged`
- * method when the set of items changes, the mixin concludes that you'll take
- * care of notifying it of future changes, and turns on the optimization. With
- * that on, the mixin saves a reference to the computed set of items, and will
- * return that immediately on subsequent calls to the `items` property. If you
- * use this mixin in conjunction with
- * [DistributedChildrenContentMixin](DistributedChildrenContentMixin.md), the
- * `contentChanged` method will be invoked for you when the element's children
- * change, turning on the optimization automatically.
- */
- var ContentItems = function (_base) {
- _inherits(ContentItems, _base);
-
- function ContentItems() {
- _classCallCheck(this, ContentItems);
-
- return _possibleConstructorReturn(this, (ContentItems.__proto__ || Object.getPrototypeOf(ContentItems)).apply(this, arguments));
- }
-
- _createClass(ContentItems, [{
- key: 'contentChanged',
- value: function contentChanged() {
- if (_get(ContentItems.prototype.__proto__ || Object.getPrototypeOf(ContentItems.prototype), 'contentChanged', this)) {
- _get(ContentItems.prototype.__proto__ || Object.getPrototypeOf(ContentItems.prototype), 'contentChanged', this).call(this);
- }
-
- // Since we got the contentChanged call, we'll assume we'll be notified if
- // the set of items changes later. We turn on memoization of the items
- // property by setting our internal property to null (instead of
- // undefined).
- this[itemsSymbol] = null;
-
- this[_symbols2.default.itemsChanged]();
- }
-
- /**
- * This method is invoked whenever a new item is added to the list.
- *
- * The default implementation of this method does nothing. You can override
- * this to perform per-item initialization.
- *
- * @param {HTMLElement} item - The item that was added.
- */
-
- }, {
- key: _symbols2.default.itemAdded,
- value: function value(item) {
- if (_get(ContentItems.prototype.__proto__ || Object.getPrototypeOf(ContentItems.prototype), _symbols2.default.itemAdded, this)) {
- _get(ContentItems.prototype.__proto__ || Object.getPrototypeOf(ContentItems.prototype), _symbols2.default.itemAdded, this).call(this, item);
- }
- }
-
- /**
- * The selection state for a single item has changed.
- *
- * Invoke this method to signal that the selected state of the indicated item
- * has changed. By default, this applies a `selected` CSS class if the item
- * is selected, and removed it if not selected.
- *
- * @param {HTMLElement} item - The item whose selection state has changed.
- * @param {boolean} selected - True if the item is selected, false if not.
- */
-
- }, {
- key: _symbols2.default.itemSelected,
- value: function value(item, selected) {
- if (_get(ContentItems.prototype.__proto__ || Object.getPrototypeOf(ContentItems.prototype), _symbols2.default.itemSelected, this)) {
- _get(ContentItems.prototype.__proto__ || Object.getPrototypeOf(ContentItems.prototype), _symbols2.default.itemSelected, this).call(this, item, selected);
- }
- (0, _toggleClass2.default)(item, 'selected', selected);
- }
-
- /**
- * The current set of items in the list. See the top-level documentation for
- * mixin for a description of how items differ from plain content.
- *
- * @type {HTMLElement[]}
- */
-
- }, {
- key: _symbols2.default.itemsChanged,
-
-
- /**
- * This method is invoked when the underlying contents change. It is also
- * invoked on component initialization – since the items have "changed" from
- * being nothing.
- */
- value: function value() {
- var _this2 = this;
-
- if (_get(ContentItems.prototype.__proto__ || Object.getPrototypeOf(ContentItems.prototype), _symbols2.default.itemsChanged, this)) {
- _get(ContentItems.prototype.__proto__ || Object.getPrototypeOf(ContentItems.prototype), _symbols2.default.itemsChanged, this).call(this);
- }
-
- // Perform per-item initialization.
- Array.prototype.forEach.call(this.items, function (item) {
- if (!item[itemInitializedSymbol]) {
- _this2[_symbols2.default.itemAdded](item);
- item[itemInitializedSymbol] = true;
- }
- });
-
- this.dispatchEvent(new CustomEvent('items-changed'));
- }
-
- /**
- * Fires when the items in the list change.
- *
- * @memberof ContentItems
- * @event items-changed
- */
-
- }, {
- key: 'items',
- get: function get() {
- var items = void 0;
- if (this[itemsSymbol] == null) {
- items = filterAuxiliaryElements(this.content);
- // Note: test for *equality* with null; don't treat undefined as a match.
- if (this[itemsSymbol] === null) {
- // Memoize the set of items.
- this[itemsSymbol] = items;
- }
- } else {
- // Return the memoized items.
- items = this[itemsSymbol];
- }
- return items;
- }
- }]);
-
- return ContentItems;
- }(base);
-
- return ContentItems;
-};
-
-// Return the given elements, filtering out auxiliary elements that aren't
-// typically visible. Items which are not elements are returned as is.
-
-
-function filterAuxiliaryElements(items) {
- var auxiliaryTags = ['link', 'script', 'style', 'template'];
- return [].filter.call(items, function (item) {
- return !item.localName || auxiliaryTags.indexOf(item.localName) < 0;
- });
-}
-
-},{"./createSymbol":20,"./symbols":23,"./toggleClass":24}],5:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
-
-var _set = function set(object, property, value, receiver) { var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent !== null) { set(parent, property, value, receiver); } } else if ("value" in desc && desc.writable) { desc.value = value; } else { var setter = desc.set; if (setter !== undefined) { setter.call(receiver, value); } } return value; };
-
-var _get = function get(object, property, receiver) { if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { return get(parent, property, receiver); } } else if ("value" in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } };
-
-var _symbols = require('./symbols');
-
-var _symbols2 = _interopRequireDefault(_symbols);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-/* Exported function extends a base class with DirectionSelection. */
-exports.default = function (base) {
-
- /**
- * Mixin which maps direction semantics (goLeft, goRight, etc.) to selection
- * semantics (selectPrevious, selectNext, etc.).
- *
- * This mixin can be used in conjunction with
- * [KeyboardDirectionMixin](KeyboardDirectionMixin.md) (which maps keyboard
- * events to directions) and a mixin that handles selection like
- * [SingleSelectionMixin](SingleSelectionMixin.md).
- */
- var DirectionSelection = function (_base) {
- _inherits(DirectionSelection, _base);
-
- function DirectionSelection() {
- _classCallCheck(this, DirectionSelection);
-
- return _possibleConstructorReturn(this, (DirectionSelection.__proto__ || Object.getPrototypeOf(DirectionSelection)).apply(this, arguments));
- }
-
- _createClass(DirectionSelection, [{
- key: _symbols2.default.goDown,
- value: function value() {
- if (_get(DirectionSelection.prototype.__proto__ || Object.getPrototypeOf(DirectionSelection.prototype), _symbols2.default.goDown, this)) {
- _get(DirectionSelection.prototype.__proto__ || Object.getPrototypeOf(DirectionSelection.prototype), _symbols2.default.goDown, this).call(this);
- }
- return this.selectNext();
- }
- }, {
- key: _symbols2.default.goEnd,
- value: function value() {
- if (_get(DirectionSelection.prototype.__proto__ || Object.getPrototypeOf(DirectionSelection.prototype), _symbols2.default.goEnd, this)) {
- _get(DirectionSelection.prototype.__proto__ || Object.getPrototypeOf(DirectionSelection.prototype), _symbols2.default.goEnd, this).call(this);
- }
- return this.selectLast();
- }
- }, {
- key: _symbols2.default.goLeft,
- value: function value() {
- if (_get(DirectionSelection.prototype.__proto__ || Object.getPrototypeOf(DirectionSelection.prototype), _symbols2.default.goLeft, this)) {
- _get(DirectionSelection.prototype.__proto__ || Object.getPrototypeOf(DirectionSelection.prototype), _symbols2.default.goLeft, this).call(this);
- }
- return this.selectPrevious();
- }
- }, {
- key: _symbols2.default.goRight,
- value: function value() {
- if (_get(DirectionSelection.prototype.__proto__ || Object.getPrototypeOf(DirectionSelection.prototype), _symbols2.default.goRight, this)) {
- _get(DirectionSelection.prototype.__proto__ || Object.getPrototypeOf(DirectionSelection.prototype), _symbols2.default.goRight, this).call(this);
- }
- return this.selectNext();
- }
- }, {
- key: _symbols2.default.goStart,
- value: function value() {
- if (_get(DirectionSelection.prototype.__proto__ || Object.getPrototypeOf(DirectionSelection.prototype), _symbols2.default.goStart, this)) {
- _get(DirectionSelection.prototype.__proto__ || Object.getPrototypeOf(DirectionSelection.prototype), _symbols2.default.goStart, this).call(this);
- }
- return this.selectFirst();
- }
- }, {
- key: _symbols2.default.goUp,
- value: function value() {
- if (_get(DirectionSelection.prototype.__proto__ || Object.getPrototypeOf(DirectionSelection.prototype), _symbols2.default.goUp, this)) {
- _get(DirectionSelection.prototype.__proto__ || Object.getPrototypeOf(DirectionSelection.prototype), _symbols2.default.goUp, this).call(this);
- }
- return this.selectPrevious();
- }
-
- // Default implementation. This will typically be handled by other mixins.
-
- }, {
- key: 'selectFirst',
-
-
- // Default implementation. This will typically be handled by other mixins.
- value: function selectFirst() {
- if (_get(DirectionSelection.prototype.__proto__ || Object.getPrototypeOf(DirectionSelection.prototype), 'selectFirst', this)) {
- return _get(DirectionSelection.prototype.__proto__ || Object.getPrototypeOf(DirectionSelection.prototype), 'selectFirst', this).call(this);
- }
- }
-
- // Default implementation. This will typically be handled by other mixins.
-
- }, {
- key: 'selectLast',
- value: function selectLast() {
- if (_get(DirectionSelection.prototype.__proto__ || Object.getPrototypeOf(DirectionSelection.prototype), 'selectLast', this)) {
- return _get(DirectionSelection.prototype.__proto__ || Object.getPrototypeOf(DirectionSelection.prototype), 'selectLast', this).call(this);
- }
- }
-
- // Default implementation. This will typically be handled by other mixins.
-
- }, {
- key: 'selectNext',
- value: function selectNext() {
- if (_get(DirectionSelection.prototype.__proto__ || Object.getPrototypeOf(DirectionSelection.prototype), 'selectNext', this)) {
- return _get(DirectionSelection.prototype.__proto__ || Object.getPrototypeOf(DirectionSelection.prototype), 'selectNext', this).call(this);
- }
- }
-
- // Default implementation. This will typically be handled by other mixins.
-
- }, {
- key: 'selectPrevious',
- value: function selectPrevious() {
- if (_get(DirectionSelection.prototype.__proto__ || Object.getPrototypeOf(DirectionSelection.prototype), 'selectPrevious', this)) {
- return _get(DirectionSelection.prototype.__proto__ || Object.getPrototypeOf(DirectionSelection.prototype), 'selectPrevious', this).call(this);
- }
- }
-
- // Map drag travel fraction to selection fraction.
-
- }, {
- key: 'selectedFraction',
- get: function get() {
- return _get(DirectionSelection.prototype.__proto__ || Object.getPrototypeOf(DirectionSelection.prototype), 'selectedFraction', this);
- },
- set: function set(value) {
- if ('selectedFraction' in base.prototype) {
- _set(DirectionSelection.prototype.__proto__ || Object.getPrototypeOf(DirectionSelection.prototype), 'selectedFraction', value, this);
- }
- }
- }, {
- key: 'travelFraction',
- get: function get() {
- return _get(DirectionSelection.prototype.__proto__ || Object.getPrototypeOf(DirectionSelection.prototype), 'travelFraction', this);
- },
- set: function set(value) {
- if ('travelFraction' in base.prototype) {
- _set(DirectionSelection.prototype.__proto__ || Object.getPrototypeOf(DirectionSelection.prototype), 'travelFraction', value, this);
- }
- this.selectedFraction = value;
- }
- }]);
-
- return DirectionSelection;
- }(base);
-
- return DirectionSelection;
-};
-
-},{"./symbols":23}],6:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
-
-var _set = function set(object, property, value, receiver) { var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent !== null) { set(parent, property, value, receiver); } } else if ("value" in desc && desc.writable) { desc.value = value; } else { var setter = desc.set; if (setter !== undefined) { setter.call(receiver, value); } } return value; };
-
-var _get = function get(object, property, receiver) { if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { return get(parent, property, receiver); } } else if ("value" in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } };
-
-var _microtask = require('./microtask');
-
-var _microtask2 = _interopRequireDefault(_microtask);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-/* Exported function extends a base class with DistributedChildrenContent. */
-exports.default = function (base) {
-
- /**
- * Mixin which defines a component's content as its children, expanding any
- * nodes distributed to the component's slots.
- *
- * This also provides notification of changes to a component's content. It
- * will invoke a `contentChanged` method when the component is first
- * instantiated, and whenever its distributed children change. This is an
- * easy way to satisfy the Gold Standard checklist item for monitoring
- * [Content Changes](https://github.com/webcomponents/gold-standard/wiki/Content-Changes).
- *
- * Example:
- *
- * ```
- * let base = DistributedChildrenContentMixin(DistributedChildrenMixin(HTMLElement));
- * class CountingElement extends base {
- *
- * constructor() {
- * super();
- * let root = this.attachShadow({ mode: 'open' });
- * root.innerHTML = ` `;
- * }
- *
- * contentChanged() {
- * // Count the component's children, both initially and when changed.
- * this.count = this.distributedChildren.length;
- * }
- *
- * }
- * ```
- *
- * Note that content change detection depends upon the element having at least
- * one `slot` element in its shadow subtree.
- *
- * This mixin is intended for use with the
- * [DistributedChildrenMixin](DistributedChildrenMixin.md). See that mixin for
- * a discussion of how that works. This DistributedChildrenContentMixin
- * provides an easy way of defining the "content" of a component as the
- * component's distributed children. That in turn lets mixins like
- * [ContentItemsMixin](ContentItemsMixin.md) manipulate the children as list
- * items.
- */
- var DistributedChildrenContent = function (_base) {
- _inherits(DistributedChildrenContent, _base);
-
- function DistributedChildrenContent() {
- _classCallCheck(this, DistributedChildrenContent);
-
- var _this = _possibleConstructorReturn(this, (DistributedChildrenContent.__proto__ || Object.getPrototypeOf(DistributedChildrenContent)).call(this));
-
- if (_this.shadowRoot) {
- // Listen to changes on all slots.
- var slots = _this.shadowRoot.querySelectorAll('slot');
- slots.forEach(function (slot) {
- return slot.addEventListener('slotchange', function (event) {
- _this.contentChanged();
- });
- });
- }
-
- // Make an initial call to contentChanged() so that the component can do
- // initialization that it normally does when content changes.
- //
- // This will invoke contentChanged() handlers in other mixins. In order
- // that those mixins have a chance to complete their own initialization,
- // we add the contentChanged() call to the microtask queue.
- (0, _microtask2.default)(function () {
- return _this.contentChanged();
- });
- return _this;
- }
-
- /**
- * Invoked when the contents of the component (including distributed
- * children) have changed.
- *
- * This method is also invoked when a component is first instantiated; the
- * contents have essentially "changed" from being nothing. This allows the
- * component to perform initial processing of its children.
- */
-
-
- _createClass(DistributedChildrenContent, [{
- key: 'contentChanged',
- value: function contentChanged() {
- if (_get(DistributedChildrenContent.prototype.__proto__ || Object.getPrototypeOf(DistributedChildrenContent.prototype), 'contentChanged', this)) {
- _get(DistributedChildrenContent.prototype.__proto__ || Object.getPrototypeOf(DistributedChildrenContent.prototype), 'contentChanged', this).call(this);
- }
- var event = new CustomEvent('content-changed');
- this.dispatchEvent(event);
- }
-
- /**
- * The content of this component, defined to be the flattened array of
- * children distributed to the component.
- *
- * @type {HTMLElement[]}
- */
-
- }, {
- key: 'content',
- get: function get() {
- var distributedChildren = this.distributedChildren;
- if (typeof distributedChildren === 'undefined') {
- console.warn('DistributedChildrenContentMixin expects the component to define a "distributedChildren" property.');
- }
- return distributedChildren;
- },
- set: function set(value) {
- if ('content' in base.prototype) {
- _set(DistributedChildrenContent.prototype.__proto__ || Object.getPrototypeOf(DistributedChildrenContent.prototype), 'content', value, this);
- }
- // TODO: Set the children to the given value (which should be an array of
- // elements)?
- }
-
- /**
- * This event is raised when the component's contents (including distributed
- * children) have changed.
- *
- * @memberof DistributedChildrenContent
- * @event content-changed
- */
-
- }]);
-
- return DistributedChildrenContent;
- }(base);
-
- return DistributedChildrenContent;
-};
-
-},{"./microtask":21}],7:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
-
-function _toConsumableArray(arr) { if (Array.isArray(arr)) { for (var i = 0, arr2 = Array(arr.length); i < arr.length; i++) { arr2[i] = arr[i]; } return arr2; } else { return Array.from(arr); } }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-/* Exported function extends a base class with DistributedChildren. */
-exports.default = function (base) {
-
- /**
- * Mixin which defines helpers for accessing a component's distributed
- * children as a flattened array or string.
- *
- * The standard DOM API provides several ways of accessing child content:
- * `children`, `childNodes`, and `textContent`. None of these functions are
- * Shadow DOM aware. This mixin defines variations of those functions that
- * *are* Shadow DOM aware.
- *
- * Example: you create a component `` that displays a number
- * equal to the number of children placed inside that component. If someone
- * instantiates your component like:
- *
- *
- *
- *
- *
- *
- *
- * Then the component should show "3", because there are three children. To
- * calculate the number of children, the component can just calculate
- * `this.children.length`. However, suppose someone instantiates your
- * component inside one of their own components, and puts a `` element
- * inside your component:
- *
- *
- *
- *
- *
- * If your component only looks at `this.children`, it will always see exactly
- * one child — the `` element. But the user looking at the page will
- * *see* any nodes distributed to that slot. To match what the user sees, your
- * component should expand any `` elements it contains.
- *
- * That is the problem this mixin solves. After applying this mixin, your
- * component code has access to `this.distributedChildren`, whose `length`
- * will return the total number of all children distributed to your component
- * in the composed tree.
- *
- * Note: The latest Custom Elements API design calls for a new function,
- * `getAssignedNodes` that takes an optional `deep` parameter, that will solve
- * this problem at the API level.
- */
- var DistributedChildren = function (_base) {
- _inherits(DistributedChildren, _base);
-
- function DistributedChildren() {
- _classCallCheck(this, DistributedChildren);
-
- return _possibleConstructorReturn(this, (DistributedChildren.__proto__ || Object.getPrototypeOf(DistributedChildren)).apply(this, arguments));
- }
-
- _createClass(DistributedChildren, [{
- key: 'distributedChildren',
-
-
- /**
- * An in-order collection of distributed children, expanding any slot
- * elements. Like the standard children property, this skips text nodes.
- *
- * @type {HTMLElement[]}
- */
- get: function get() {
- return expandContentElements(this.children, false);
- }
-
- /**
- * An in-order collection of distributed child nodes, expanding any slot
- * elements. Like the standard childNodes property, this includes text
- * nodes.
- *
- * @type {Node[]}
- */
-
- }, {
- key: 'distributedChildNodes',
- get: function get() {
- return expandContentElements(this.childNodes, true);
- }
-
- /**
- * The concatenated text content of all distributed child nodes, expanding
- * any slot elements.
- *
- * @type {string}
- */
-
- }, {
- key: 'distributedTextContent',
- get: function get() {
- var strings = this.distributedChildNodes.map(function (child) {
- return child.textContent;
- });
- return strings.join('');
- }
- }]);
-
- return DistributedChildren;
- }(base);
-
- return DistributedChildren;
-};
-
-/*
- * Given a array of nodes, return a new array with any content elements expanded
- * to the nodes distributed to that content element. This rule is applied
- * recursively.
- *
- * If includeTextNodes is true, text nodes will be included, as in the
- * standard childNodes property; by default, this skips text nodes, like the
- * standard children property.
- */
-
-
-function expandContentElements(nodes, includeTextNodes) {
- var _ref;
-
- var expanded = Array.prototype.map.call(nodes, function (node) {
- // We want to see if the node is an instanceof HTMLSlotELement, but
- // that class won't exist if the browser that doesn't support native
- // Shadow DOM and if the Shadow DOM polyfill hasn't been loaded. Instead,
- // we do a simplistic check to see if the tag name is "slot".
- var isSlot = typeof HTMLSlotElement !== 'undefined' ? node instanceof HTMLSlotElement : node.localName === 'slot';
- if (isSlot) {
- // Use the nodes assigned to this node instead.
- var assignedNodes = node.assignedNodes({ flatten: true });
- return assignedNodes ? expandContentElements(assignedNodes, includeTextNodes) : [];
- } else if (node instanceof HTMLElement) {
- // Plain element; use as is.
- return [node];
- } else if (node instanceof Text && includeTextNodes) {
- // Text node.
- return [node];
- } else {
- // Comment, processing instruction, etc.; skip.
- return [];
- }
- });
- var flattened = (_ref = []).concat.apply(_ref, _toConsumableArray(expanded));
- return flattened;
-}
-
-},{}],8:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
-
-var _set = function set(object, property, value, receiver) { var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent !== null) { set(parent, property, value, receiver); } } else if ("value" in desc && desc.writable) { desc.value = value; } else { var setter = desc.set; if (setter !== undefined) { setter.call(receiver, value); } } return value; };
-
-var _get = function get(object, property, receiver) { if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { return get(parent, property, receiver); } } else if ("value" in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } };
-
-var _createSymbol = require('./createSymbol');
-
-var _createSymbol2 = _interopRequireDefault(_createSymbol);
-
-var _safeAttributes = require('./safeAttributes');
-
-var _safeAttributes2 = _interopRequireDefault(_safeAttributes);
-
-var _symbols = require('./symbols');
-
-var _symbols2 = _interopRequireDefault(_symbols);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-// Symbols for private data members on an element.
-var genericSymbol = (0, _createSymbol2.default)('generic');
-
-/* Exported function extends a base class with Generic. */
-
-exports.default = function (base) {
-
- /**
- * Mixin which allows a component to support a "generic" style: a minimalist
- * style that can easily be removed to reset its visual appearance to a
- * baseline state.
- *
- * By default, a component should provide a minimal visual presentation that
- * allows the component to function. However, the more styling the component
- * provides by default, the harder it becomes to get the component to fit in
- * in other settings. Each CSS rule has to be overridden. Worse, new CSS rules
- * added to the default style won't be overridden by default, making it hard
- * to know whether a new version of a component will still look okay.
- *
- * As a compromise, the mixin defines a `generic` attribute. This attribute is
- * normally set by default, and styles can be written that apply only when the
- * generic attribute is set. This allows the construction of CSS rules that
- * will only apply to generic components like:
- *
- * :host([generic=""]) {
- * ... generic appearance defined here ...
- * }
- *
- * This makes it easy to remove all default styling — set the `GenericMixin`
- * attribute to false, and all default styling will be removed.
- */
- var Generic = function (_base) {
- _inherits(Generic, _base);
-
- function Generic() {
- _classCallCheck(this, Generic);
-
- // Set defaults.
- var _this = _possibleConstructorReturn(this, (Generic.__proto__ || Object.getPrototypeOf(Generic)).call(this));
-
- if (typeof _this.generic === 'undefined') {
- _this.generic = _this[_symbols2.default.defaults].generic;
- }
- return _this;
- }
-
- // This mixin doesn't actually respond to attribute changes, but relies
- // on separately-defined behavior (e.g., in AttributeMarshallingMixin) for that.
- // Still, we need define a baseline attributeChangedCallback that does
- // nothing, in case this mixin gets used on its own.
-
-
- _createClass(Generic, [{
- key: 'attributeChangedCallback',
- value: function attributeChangedCallback(name, oldValue, newValue) {
- if (_get(Generic.prototype.__proto__ || Object.getPrototypeOf(Generic.prototype), 'attributeChangedCallback', this)) {
- _get(Generic.prototype.__proto__ || Object.getPrototypeOf(Generic.prototype), 'attributeChangedCallback', this).call(this, name, oldValue, newValue);
- }
- }
- }, {
- key: 'connectedCallback',
- value: function connectedCallback() {
- if (_get(Generic.prototype.__proto__ || Object.getPrototypeOf(Generic.prototype), 'connectedCallback', this)) {
- _get(Generic.prototype.__proto__ || Object.getPrototypeOf(Generic.prototype), 'connectedCallback', this).call(this);
- }
- _safeAttributes2.default.connected(this);
- }
- }, {
- key: _symbols2.default.defaults,
- get: function get() {
- var defaults = _get(Generic.prototype.__proto__ || Object.getPrototypeOf(Generic.prototype), _symbols2.default.defaults, this) || {};
- defaults.generic = true;
- return defaults;
- }
-
- /**
- * True if the component would like to receive generic styling.
- *
- * This property is true by default — set it to false to turn off all
- * generic styles. This makes it easier to apply custom styling; you won't
- * have to explicitly override styling you don't want.
- *
- * @type Boolean
- * @default true
- */
-
- }, {
- key: 'generic',
- get: function get() {
- return this[genericSymbol];
- },
- set: function set(value) {
- var parsed = typeof value === 'string' ? String(value) !== 'false' : value;
- this[genericSymbol] = parsed;
-
- if ('generic' in base.prototype) {
- _set(Generic.prototype.__proto__ || Object.getPrototypeOf(Generic.prototype), 'generic', value, this);
- }
-
- // We roll our own attribute setting so that an explicitly false value
- // shows up as GenericMixin="false".
- if (parsed === false) {
- // Explicitly use false string.
- _safeAttributes2.default.setAttribute(this, 'generic', 'false');
- } else if (parsed == null) {
- // Explicitly remove attribute. (Always safe to do this.)
- this.removeAttribute('generic');
- } else {
- // Use the empty string to get attribute to appear with no value.
- _safeAttributes2.default.setAttribute(this, 'generic', '');
- }
- }
- }]);
-
- return Generic;
- }(base);
-
- return Generic;
-};
-
-},{"./createSymbol":20,"./safeAttributes":22,"./symbols":23}],9:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
-
-var _set = function set(object, property, value, receiver) { var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent !== null) { set(parent, property, value, receiver); } } else if ("value" in desc && desc.writable) { desc.value = value; } else { var setter = desc.set; if (setter !== undefined) { setter.call(receiver, value); } } return value; };
-
-var _get = function get(object, property, receiver) { if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { return get(parent, property, receiver); } } else if ("value" in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } };
-
-var _createSymbol = require('./createSymbol');
-
-var _createSymbol2 = _interopRequireDefault(_createSymbol);
-
-var _symbols = require('./symbols');
-
-var _symbols2 = _interopRequireDefault(_symbols);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-// Symbols for private data members on an element.
-var navigationAxisSymbol = (0, _createSymbol2.default)('navigationAxis');
-
-/* Exported function extends a base class with KeyboardDirection. */
-
-exports.default = function (base) {
-
- /**
- * Mixin which maps direction keys (Left, Right, etc.) to direction semantics
- * (go left, go right, etc.).
- *
- * This mixin expects the component to invoke a `keydown` method when a key is
- * pressed. You can use [KeyboardMixin](KeyboardMixin.md) for that
- * purpose, or wire up your own keyboard handling and call `keydown` yourself.
- *
- * This mixin calls methods such as `goLeft` and `goRight`. You can define
- * what that means by implementing those methods yourself. If you want to use
- * direction keys to navigate a selection, use this mixin with
- * [DirectionSelectionMixin](DirectionSelectionMixin.md).
- */
- var KeyboardDirection = function (_base) {
- _inherits(KeyboardDirection, _base);
-
- function KeyboardDirection() {
- _classCallCheck(this, KeyboardDirection);
-
- // Set defaults.
- var _this = _possibleConstructorReturn(this, (KeyboardDirection.__proto__ || Object.getPrototypeOf(KeyboardDirection)).call(this));
-
- if (typeof _this.navigationAxis === 'undefined') {
- _this.navigationAxis = _this[_symbols2.default.defaults].navigationAxis;
- }
- return _this;
- }
-
- _createClass(KeyboardDirection, [{
- key: _symbols2.default.goDown,
-
-
- /**
- * Invoked when the user wants to go/navigate down.
- * The default implementation of this method does nothing.
- */
- value: function value() {
- if (_get(KeyboardDirection.prototype.__proto__ || Object.getPrototypeOf(KeyboardDirection.prototype), _symbols2.default.goDown, this)) {
- return _get(KeyboardDirection.prototype.__proto__ || Object.getPrototypeOf(KeyboardDirection.prototype), _symbols2.default.goDown, this).call(this);
- }
- }
-
- /**
- * Invoked when the user wants to go/navigate to the end (e.g., of a list).
- * The default implementation of this method does nothing.
- */
-
- }, {
- key: _symbols2.default.goEnd,
- value: function value() {
- if (_get(KeyboardDirection.prototype.__proto__ || Object.getPrototypeOf(KeyboardDirection.prototype), _symbols2.default.goEnd, this)) {
- return _get(KeyboardDirection.prototype.__proto__ || Object.getPrototypeOf(KeyboardDirection.prototype), _symbols2.default.goEnd, this).call(this);
- }
- }
-
- /**
- * Invoked when the user wants to go/navigate left.
- * The default implementation of this method does nothing.
- */
-
- }, {
- key: _symbols2.default.goLeft,
- value: function value() {
- if (_get(KeyboardDirection.prototype.__proto__ || Object.getPrototypeOf(KeyboardDirection.prototype), _symbols2.default.goLeft, this)) {
- return _get(KeyboardDirection.prototype.__proto__ || Object.getPrototypeOf(KeyboardDirection.prototype), _symbols2.default.goLeft, this).call(this);
- }
- }
-
- /**
- * Invoked when the user wants to go/navigate right.
- * The default implementation of this method does nothing.
- */
-
- }, {
- key: _symbols2.default.goRight,
- value: function value() {
- if (_get(KeyboardDirection.prototype.__proto__ || Object.getPrototypeOf(KeyboardDirection.prototype), _symbols2.default.goRight, this)) {
- return _get(KeyboardDirection.prototype.__proto__ || Object.getPrototypeOf(KeyboardDirection.prototype), _symbols2.default.goRight, this).call(this);
- }
- }
-
- /**
- * Invoked when the user wants to go/navigate to the start (e.g., of a
- * list). The default implementation of this method does nothing.
- */
-
- }, {
- key: _symbols2.default.goStart,
- value: function value() {
- if (_get(KeyboardDirection.prototype.__proto__ || Object.getPrototypeOf(KeyboardDirection.prototype), _symbols2.default.goStart, this)) {
- return _get(KeyboardDirection.prototype.__proto__ || Object.getPrototypeOf(KeyboardDirection.prototype), _symbols2.default.goStart, this).call(this);
- }
- }
-
- /**
- * Invoked when the user wants to go/navigate up.
- * The default implementation of this method does nothing.
- */
-
- }, {
- key: _symbols2.default.goUp,
- value: function value() {
- if (_get(KeyboardDirection.prototype.__proto__ || Object.getPrototypeOf(KeyboardDirection.prototype), _symbols2.default.goUp, this)) {
- return _get(KeyboardDirection.prototype.__proto__ || Object.getPrototypeOf(KeyboardDirection.prototype), _symbols2.default.goUp, this).call(this);
- }
- }
-
- /**
- * Indicates the direction of permitted navigation with the keyboard.
- *
- * Accepted values are "horizontal", "vertical", or "both" (the default).
- * If this property is "horizontal", the Up Arrow and Down Arrow keys will
- * be ignored. Conversely, if this is "vertical", the Left Arrow and Right
- * Arrow keys will be ignored.
- *
- * @type {string}
- */
-
- }, {
- key: _symbols2.default.keydown,
- value: function value(event) {
- var handled = void 0;
-
- var axis = this.navigationAxis;
- var horizontal = axis === 'horizontal' || axis === 'both';
- var vertical = axis === 'vertical' || axis === 'both';
-
- // Ignore Left/Right keys when metaKey or altKey modifier is also pressed,
- // as the user may be trying to navigate back or forward in the browser.
- switch (event.keyCode) {
- case 35:
- // End
- handled = this[_symbols2.default.goEnd]();
- break;
- case 36:
- // Home
- handled = this[_symbols2.default.goStart]();
- break;
- case 37:
- // Left
- if (horizontal && !event.metaKey && !event.altKey) {
- handled = this[_symbols2.default.goLeft]();
- }
- break;
- case 38:
- // Up
- if (vertical) {
- handled = event.altKey ? this[_symbols2.default.goStart]() : this[_symbols2.default.goUp]();
- }
- break;
- case 39:
- // Right
- if (horizontal && !event.metaKey && !event.altKey) {
- handled = this[_symbols2.default.goRight]();
- }
- break;
- case 40:
- // Down
- if (vertical) {
- handled = event.altKey ? this[_symbols2.default.goEnd]() : this[_symbols2.default.goDown]();
- }
- break;
- }
- // Prefer mixin result if it's defined, otherwise use base result.
- return handled || _get(KeyboardDirection.prototype.__proto__ || Object.getPrototypeOf(KeyboardDirection.prototype), _symbols2.default.keydown, this) && _get(KeyboardDirection.prototype.__proto__ || Object.getPrototypeOf(KeyboardDirection.prototype), _symbols2.default.keydown, this).call(this, event);
- }
- }, {
- key: _symbols2.default.defaults,
- get: function get() {
- var defaults = _get(KeyboardDirection.prototype.__proto__ || Object.getPrototypeOf(KeyboardDirection.prototype), _symbols2.default.defaults, this) || {};
- defaults.navigationAxis = 'both';
- return defaults;
- }
- }, {
- key: 'navigationAxis',
- get: function get() {
- return this[navigationAxisSymbol];
- },
- set: function set(value) {
- this[navigationAxisSymbol] = value;
- if ('navigationAxis' in base.prototype) {
- _set(KeyboardDirection.prototype.__proto__ || Object.getPrototypeOf(KeyboardDirection.prototype), 'navigationAxis', value, this);
- }
- }
- }]);
-
- return KeyboardDirection;
- }(base);
-
- return KeyboardDirection;
-};
-
-},{"./createSymbol":20,"./symbols":23}],10:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
-
-var _get = function get(object, property, receiver) { if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { return get(parent, property, receiver); } } else if ("value" in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } };
-
-var _symbols = require('./symbols');
-
-var _symbols2 = _interopRequireDefault(_symbols);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-/* Exported function extends a base class with Keyboard. */
-exports.default = function (base) {
-
- /**
- * Mixin which manages the keydown handling for a component.
- *
- * This mixin handles several keyboard-related features.
- *
- * First, it wires up a single keydown event handler that can be shared by
- * multiple mixins on a component. The event handler will invoke a `keydown`
- * method with the event object, and any mixin along the prototype chain that
- * wants to handle that method can do so.
- *
- * If a mixin wants to indicate that keyboard event has been handled, and that
- * other mixins should *not* handle it, the mixin's `keydown` handler should
- * return a value of true. The convention that seems to work well is that a
- * mixin should see if it wants to handle the event and, if not, then ask the
- * superclass to see if it wants to handle the event. This has the effect of
- * giving the mixin that was applied last the first chance at handling a
- * keyboard event.
- *
- * Example:
- *
- * [symbols.keydown](event) {
- * let handled;
- * switch (event.keyCode) {
- * // Handle the keys you want, setting handled = true if appropriate.
- * }
- * // Prefer mixin result if it's defined, otherwise use base result.
- * return handled || (super[symbols.keydown] && super[symbols.keydown](event));
- * }
- *
- * A second feature provided by this mixin is that it implicitly makes the
- * component a tab stop if it isn't already, by setting `tabIndex` to 0. This
- * has the effect of adding the component to the tab order in document order.
- */
- var Keyboard = function (_base) {
- _inherits(Keyboard, _base);
-
- function Keyboard() {
- _classCallCheck(this, Keyboard);
-
- var _this = _possibleConstructorReturn(this, (Keyboard.__proto__ || Object.getPrototypeOf(Keyboard)).call(this));
-
- _this.addEventListener('keydown', function (event) {
- var handled = _this[_symbols2.default.keydown](event);
- if (handled) {
- event.preventDefault();
- event.stopPropagation();
- }
- });
- return _this;
- }
-
- _createClass(Keyboard, [{
- key: 'connectedCallback',
- value: function connectedCallback() {
- if (_get(Keyboard.prototype.__proto__ || Object.getPrototypeOf(Keyboard.prototype), 'connectedCallback', this)) {
- _get(Keyboard.prototype.__proto__ || Object.getPrototypeOf(Keyboard.prototype), 'connectedCallback', this).call(this);
- }
- if (this.getAttribute('tabindex') == null && this[_symbols2.default.defaults].tabindex !== null) {
- this.setAttribute('tabindex', this[_symbols2.default.defaults].tabindex);
- }
- }
- }, {
- key: _symbols2.default.keydown,
-
-
- /**
- * Handle the indicated keyboard event.
- *
- * The default implementation of this method does nothing. This will
- * typically be handled by other mixins.
- *
- * @param {KeyboardEvent} event - the keyboard event
- * @return {boolean} true if the event was handled
- */
- value: function value(event) {
- if (_get(Keyboard.prototype.__proto__ || Object.getPrototypeOf(Keyboard.prototype), _symbols2.default.keydown, this)) {
- return _get(Keyboard.prototype.__proto__ || Object.getPrototypeOf(Keyboard.prototype), _symbols2.default.keydown, this).call(this, event);
- }
- }
- }, {
- key: _symbols2.default.defaults,
- get: function get() {
- var defaults = _get(Keyboard.prototype.__proto__ || Object.getPrototypeOf(Keyboard.prototype), _symbols2.default.defaults, this) || {};
- // The default tab index is 0 (document order).
- defaults.tabindex = 0;
- return defaults;
- }
- }]);
-
- return Keyboard;
- }(base);
-
- return Keyboard;
-};
-
-},{"./symbols":23}],11:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
-
-var _set = function set(object, property, value, receiver) { var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent !== null) { set(parent, property, value, receiver); } } else if ("value" in desc && desc.writable) { desc.value = value; } else { var setter = desc.set; if (setter !== undefined) { setter.call(receiver, value); } } return value; };
-
-var _get = function get(object, property, receiver) { if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { return get(parent, property, receiver); } } else if ("value" in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } };
-
-var _symbols = require('./symbols');
-
-var _symbols2 = _interopRequireDefault(_symbols);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-/* Exported function extends a base class with KeyboardPagedSelection. */
-exports.default = function (base) {
-
- /**
- * Mixin which maps page keys (Page Up, Page Down) into operations that move
- * the selection by one page.
- *
- * The keyboard interaction model generally follows that of Microsoft Windows'
- * list boxes instead of those in OS X:
- *
- * * The Page Up/Down and Home/End keys actually change the selection, rather
- * than just scrolling. The former behavior seems more generally useful for
- * keyboard users.
- *
- * * Pressing Page Up/Down will change the selection to the topmost/bottommost
- * visible item if the selection is not already there. Thereafter, the key
- * will move the selection up/down by a page, and (per the above point) make
- * the selected item visible.
- *
- * To ensure the selected item is in view following use of Page Up/Down, use
- * the related [SelectionInViewMixin](SelectionInViewMixin.md).
- *
- * This mixin expects the component to invoke a `keydown` method when a key is
- * pressed. You can use [KeyboardMixin](KeyboardMixin.md) for that
- * purpose, or wire up your own keyboard handling and call `keydown` yourself.
- */
- var KeyboardPagedSelection = function (_base) {
- _inherits(KeyboardPagedSelection, _base);
-
- function KeyboardPagedSelection() {
- _classCallCheck(this, KeyboardPagedSelection);
-
- return _possibleConstructorReturn(this, (KeyboardPagedSelection.__proto__ || Object.getPrototypeOf(KeyboardPagedSelection)).apply(this, arguments));
- }
-
- _createClass(KeyboardPagedSelection, [{
- key: _symbols2.default.keydown,
- value: function value(event) {
- var handled = void 0;
- switch (event.keyCode) {
- case 33:
- // Page Up
- handled = this.pageUp();
- break;
- case 34:
- // Page Down
- handled = this.pageDown();
- break;
- }
- // Prefer mixin result if it's defined, otherwise use base result.
- return handled || _get(KeyboardPagedSelection.prototype.__proto__ || Object.getPrototypeOf(KeyboardPagedSelection.prototype), _symbols2.default.keydown, this) && _get(KeyboardPagedSelection.prototype.__proto__ || Object.getPrototypeOf(KeyboardPagedSelection.prototype), _symbols2.default.keydown, this).call(this, event);
- }
-
- /**
- * Scroll down one page.
- */
-
- }, {
- key: 'pageDown',
- value: function pageDown() {
- if (_get(KeyboardPagedSelection.prototype.__proto__ || Object.getPrototypeOf(KeyboardPagedSelection.prototype), 'pageDown', this)) {
- _get(KeyboardPagedSelection.prototype.__proto__ || Object.getPrototypeOf(KeyboardPagedSelection.prototype), 'pageDown', this).call(this);
- }
- return scrollOnePage(this, true);
- }
-
- /**
- * Scroll up one page.
- */
-
- }, {
- key: 'pageUp',
- value: function pageUp() {
- if (_get(KeyboardPagedSelection.prototype.__proto__ || Object.getPrototypeOf(KeyboardPagedSelection.prototype), 'pageUp', this)) {
- _get(KeyboardPagedSelection.prototype.__proto__ || Object.getPrototypeOf(KeyboardPagedSelection.prototype), 'pageUp', this).call(this);
- }
- return scrollOnePage(this, false);
- }
-
- /**
- * The element that should be scrolled with the Page Up/Down keys.
- * Default is the current element.
- *
- * @type {HTMLElement}
- */
-
- }, {
- key: 'scrollTarget',
- get: function get() {
- // Prefer base result.
- return 'scrollTarget' in base.prototype ? _get(KeyboardPagedSelection.prototype.__proto__ || Object.getPrototypeOf(KeyboardPagedSelection.prototype), 'scrollTarget', this) : this;
- },
- set: function set(element) {
- if ('scrollTarget' in base.prototype) {
- _set(KeyboardPagedSelection.prototype.__proto__ || Object.getPrototypeOf(KeyboardPagedSelection.prototype), 'scrollTarget', element, this);
- }
- }
- }]);
-
- return KeyboardPagedSelection;
- }(base);
-
- return KeyboardPagedSelection;
-};
-
-// Return the item whose content spans the given y position (relative to the
-// top of the list's scrolling client area), or null if not found.
-//
-// If downward is true, move down the list of items to find the first item
-// found at the given y position; if downward is false, move up the list of
-// items to find the last item at that position.
-
-
-function getIndexOfItemAtY(element, y, downward) {
- var items = element.items;
- var start = downward ? 0 : items.length - 1;
- var end = downward ? items.length : 0;
- var step = downward ? 1 : -1;
- var scrollTarget = element.scrollTarget;
- var topOfClientArea = scrollTarget.offsetTop + scrollTarget.clientTop;
-
- // Find the item spanning the indicated y coordinate.
- var item = void 0;
- var itemIndex = start;
- var itemTop = void 0;
- var found = false;
- while (itemIndex !== end) {
- item = items[itemIndex];
- itemTop = item.offsetTop - topOfClientArea;
- var itemBottom = itemTop + item.offsetHeight;
- if (itemTop <= y && itemBottom >= y) {
- // Item spans the indicated y coordinate.
- found = true;
- break;
- }
- itemIndex += step;
- }
-
- if (!found) {
- return null;
- }
-
- // We may have found an item whose padding spans the given y coordinate,
- // but whose content is actually above/below that point.
- // TODO: If the item has a border, then padding should be included in
- // considering a hit.
- var itemStyle = getComputedStyle(item);
- var itemPaddingTop = parseFloat(itemStyle.paddingTop);
- var itemPaddingBottom = parseFloat(itemStyle.paddingBottom);
- var contentTop = itemTop + item.clientTop + itemPaddingTop;
- var contentBottom = contentTop + item.clientHeight - itemPaddingTop - itemPaddingBottom;
- if (downward && contentTop <= y || !downward && contentBottom >= y) {
- // The indicated coordinate hits the actual item content.
- return itemIndex;
- } else {
- // The indicated coordinate falls within the item's padding. Back up to
- // the item below/above the item we found and return that.
- return itemIndex - step;
- }
-}
-
-// Move by one page downward (if downward is true), or upward (if false).
-// Return true if we ended up changing the selection, false if not.
-// TODO: Better support for horizontal lists.
-function scrollOnePage(element, downward) {
-
- // Determine the item visible just at the edge of direction we're heading.
- // We'll select that item if it's not already selected.
- var scrollTarget = element.scrollTarget;
- var edge = scrollTarget.scrollTop + (downward ? scrollTarget.clientHeight : 0);
- var indexOfItemAtEdge = getIndexOfItemAtY(element, edge, downward);
-
- var selectedIndex = element.selectedIndex;
- var newIndex = void 0;
- if (indexOfItemAtEdge && selectedIndex === indexOfItemAtEdge) {
- // The item at the edge was already selected, so scroll in the indicated
- // direction by one page. Leave the new item at that edge selected.
- var delta = (downward ? 1 : -1) * scrollTarget.clientHeight;
- newIndex = getIndexOfItemAtY(element, edge + delta, downward);
- } else {
- // The item at the edge wasn't selected yet. Instead of scrolling, we'll
- // just select that item. That is, the first attempt to page up/down
- // usually just moves the selection to the edge in that direction.
- newIndex = indexOfItemAtEdge;
- }
-
- if (!newIndex) {
- // We can't find an item in the direction we want to travel. Select the
- // last item (if moving downward) or first item (if moving upward).
- newIndex = downward ? element.items.length - 1 : 0;
- }
-
- if (newIndex !== selectedIndex) {
- element.selectedIndex = newIndex;
- return true; // We handled the page up/down ourselves.
- } else {
- return false; // We didn't do anything.
- }
-}
-
-},{"./symbols":23}],12:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
-
-var _get = function get(object, property, receiver) { if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { return get(parent, property, receiver); } } else if ("value" in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } };
-
-var _createSymbol = require('./createSymbol');
-
-var _createSymbol2 = _interopRequireDefault(_createSymbol);
-
-var _symbols = require('./symbols');
-
-var _symbols2 = _interopRequireDefault(_symbols);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-// Symbols for private data members on an element.
-var itemTextContentsSymbol = (0, _createSymbol2.default)('itemTextContents');
-var typedPrefixSymbol = (0, _createSymbol2.default)('typedPrefix');
-var prefixTimeoutSymbol = (0, _createSymbol2.default)('prefixTimeout');
-
-/* Exported function extends a base class with KeyboardPrefixSelection. */
-
-exports.default = function (base) {
-
- /**
- * Mixin that handles list box-style prefix typing, in which the user can type
- * a string to select the first item that begins with that string.
- *
- * Example: suppose a component using this mixin has the following items:
- *
- *
- * Apple
- * Apricot
- * Banana
- * Blackberry
- * Blueberry
- * Cantaloupe
- * Cherry
- * Lemon
- * Lime
- *
- *
- * If this component receives the focus, and the user presses the "b" or "B"
- * key, the "Banana" item will be selected, because it's the first item that
- * matches the prefix "b". (Matching is case-insensitive.) If the user now
- * presses the "l" or "L" key quickly, the prefix to match becomes "bl", so
- * "Blackberry" will be selected.
- *
- * The prefix typing feature has a one second timeout — the prefix to match
- * will be reset after a second has passed since the user last typed a key.
- * If, in the above example, the user waits a second between typing "b" and
- * "l", the prefix will become "l", so "Lemon" would be selected.
- *
- * This mixin expects the component to invoke a `keydown` method when a key is
- * pressed. You can use [KeyboardMixin](KeyboardMixin.md) for that
- * purpose, or wire up your own keyboard handling and call `keydown` yourself.
- *
- * This mixin also expects the component to provide an `items` property. The
- * `textContent` of those items will be used for purposes of prefix matching.
- */
- var KeyboardPrefixSelection = function (_base) {
- _inherits(KeyboardPrefixSelection, _base);
-
- function KeyboardPrefixSelection() {
- _classCallCheck(this, KeyboardPrefixSelection);
-
- return _possibleConstructorReturn(this, (KeyboardPrefixSelection.__proto__ || Object.getPrototypeOf(KeyboardPrefixSelection)).apply(this, arguments));
- }
-
- _createClass(KeyboardPrefixSelection, [{
- key: _symbols2.default.keydown,
-
-
- // TODO: If the set of items is changed, reset the prefix.
- // [symbols.itemsChanged]() {
- // this[itemTextContentsSymbol] = null;
- // resetTypedPrefix(this);
- // }
-
- // TODO: If the selection is changed by some other means (e.g., arrow keys)
- // other than prefix typing, then that act should reset the prefix.
-
- value: function value(event) {
- var handled = void 0;
- var resetPrefix = true;
-
- switch (event.keyCode) {
- case 8:
- // Backspace
- handleBackspace(this);
- handled = true;
- resetPrefix = false;
- break;
- case 27:
- // Escape
- handled = true;
- break;
- default:
- if (!event.ctrlKey && !event.metaKey && !event.altKey && event.which !== 32 /* Space */) {
- handlePlainCharacter(this, String.fromCharCode(event.which));
- }
- resetPrefix = false;
- }
-
- if (resetPrefix) {
- resetTypedPrefix(this);
- }
-
- // Prefer mixin result if it's defined, otherwise use base result.
- return handled || _get(KeyboardPrefixSelection.prototype.__proto__ || Object.getPrototypeOf(KeyboardPrefixSelection.prototype), _symbols2.default.keydown, this) && _get(KeyboardPrefixSelection.prototype.__proto__ || Object.getPrototypeOf(KeyboardPrefixSelection.prototype), _symbols2.default.keydown, this).call(this, event);
- }
-
- /**
- * Select the first item whose text content begins with the given prefix.
- *
- * @param prefix [String] The prefix string to search for
- */
-
- }, {
- key: 'selectItemWithTextPrefix',
- value: function selectItemWithTextPrefix(prefix) {
- if (_get(KeyboardPrefixSelection.prototype.__proto__ || Object.getPrototypeOf(KeyboardPrefixSelection.prototype), 'selectItemWithTextPrefix', this)) {
- _get(KeyboardPrefixSelection.prototype.__proto__ || Object.getPrototypeOf(KeyboardPrefixSelection.prototype), 'selectItemWithTextPrefix', this).call(this, prefix);
- }
- if (prefix == null || prefix.length === 0) {
- return;
- }
- var index = getIndexOfItemWithTextPrefix(this, prefix);
- if (index >= 0) {
- this.selectedIndex = index;
- }
- }
- }]);
-
- return KeyboardPrefixSelection;
- }(base);
-
- return KeyboardPrefixSelection;
-};
-
-// Time in milliseconds after which the user is considered to have stopped
-// typing.
-
-
-var PREFIX_TIMEOUT_DURATION = 1000;
-
-// Return the index of the first item with the given prefix, else -1.
-function getIndexOfItemWithTextPrefix(element, prefix) {
- var itemTextContents = getItemTextContents(element);
- var prefixLength = prefix.length;
- for (var i = 0; i < itemTextContents.length; i++) {
- var itemTextContent = itemTextContents[i];
- if (itemTextContent.substr(0, prefixLength) === prefix) {
- return i;
- }
- }
- return -1;
-}
-
-// Return an array of the text content (in lowercase) of all items.
-// Cache these results.
-function getItemTextContents(element) {
- if (!element[itemTextContentsSymbol]) {
- var items = element.items;
- element[itemTextContentsSymbol] = items.map(function (child) {
- var text = child.textContent || child.alt;
- return text.toLowerCase();
- });
- }
- return element[itemTextContentsSymbol];
-}
-
-function handleBackspace(element) {
- var length = element[typedPrefixSymbol] ? element[typedPrefixSymbol].length : 0;
- if (length > 0) {
- element[typedPrefixSymbol] = element[typedPrefixSymbol].substr(0, length - 1);
- }
- element.selectItemWithTextPrefix(element[typedPrefixSymbol]);
- setPrefixTimeout(element);
-}
-
-function handlePlainCharacter(element, char) {
- var prefix = element[typedPrefixSymbol] || '';
- element[typedPrefixSymbol] = prefix + char.toLowerCase();
- element.selectItemWithTextPrefix(element[typedPrefixSymbol]);
- setPrefixTimeout(element);
-}
-
-function resetPrefixTimeout(element) {
- if (element[prefixTimeoutSymbol]) {
- clearTimeout(element[prefixTimeoutSymbol]);
- element[prefixTimeoutSymbol] = false;
- }
-}
-
-function resetTypedPrefix(element) {
- element[typedPrefixSymbol] = '';
- resetPrefixTimeout(element);
-}
-
-function setPrefixTimeout(element) {
- resetPrefixTimeout(element);
- element[prefixTimeoutSymbol] = setTimeout(function () {
- resetTypedPrefix(element);
- }, PREFIX_TIMEOUT_DURATION);
-}
-
-},{"./createSymbol":20,"./symbols":23}],13:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-/* Exported function extends a base class with SelectedItemTextValue. */
-exports.default = function (base) {
-
- /**
- * Mixin which defines a `value` property that reflects the text content of a
- * selected item.
- *
- * This mixin exists for list-like components that want to provide a more
- * convenient way to get/set the selected item using text.
- *
- * This mixin expects a component to provide an `items` array of all elements
- * in the list. A standard way to do that with is
- * [ContentItemsMixin](ContentItemsMixin.md). This also expects the definition
- * of `selectedIndex` and `selectedItem` properties, which can be obtained
- * from [SingleSelectionMixin](SingleSelectionMixin.md).
- */
- var SelectedItemTextValue = function (_base) {
- _inherits(SelectedItemTextValue, _base);
-
- function SelectedItemTextValue() {
- _classCallCheck(this, SelectedItemTextValue);
-
- return _possibleConstructorReturn(this, (SelectedItemTextValue.__proto__ || Object.getPrototypeOf(SelectedItemTextValue)).apply(this, arguments));
- }
-
- _createClass(SelectedItemTextValue, [{
- key: 'value',
-
-
- /**
- * The text content of the selected item.
- *
- * Setting this value to a string will attempt to select the first list item
- * whose text content match that string. Setting this to a string not matching
- * any list item will result in no selection.
- *
- * @type {string}
- */
- get: function get() {
- return this.selectedItem == null || this.selectedItem.textContent == null ? '' : this.selectedItem.textContent;
- },
- set: function set(text) {
-
- var currentIndex = this.selectedIndex;
- var newIndex = -1; // Assume we won't find the text.
-
- // Find the item with the indicated text.
- var items = this.items;
- for (var i = 0, length = items.length; i < length; i++) {
- if (items[i].textContent === text) {
- newIndex = i;
- break;
- }
- }
-
- if (newIndex !== currentIndex) {
- this.selectedIndex = newIndex;
- var event = new CustomEvent('value-changed');
- this.dispatchEvent(event);
- }
- }
- }]);
-
- return SelectedItemTextValue;
- }(base);
-
- return SelectedItemTextValue;
-};
-
-},{}],14:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
-
-var _set = function set(object, property, value, receiver) { var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent !== null) { set(parent, property, value, receiver); } } else if ("value" in desc && desc.writable) { desc.value = value; } else { var setter = desc.set; if (setter !== undefined) { setter.call(receiver, value); } } return value; };
-
-var _get = function get(object, property, receiver) { if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { return get(parent, property, receiver); } } else if ("value" in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } };
-
-var _symbols = require('./symbols');
-
-var _symbols2 = _interopRequireDefault(_symbols);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-// Used to assign unique IDs to item elements without IDs.
-var idCount = 0;
-
-/* Exported function extends a base class with SelectionAriaActive. */
-
-exports.default = function (base) {
-
- /**
- * Mixin which treats the selected item in a list as the active item in ARIA
- * accessibility terms.
- *
- * Handling ARIA selection state properly is actually quite complex:
- *
- * * The items in the list need to be indicated as possible items via an ARIA
- * `role` attribute value such as "option".
- * * The selected item need to be marked as selected by setting the item's
- * `aria-selected` attribute to true *and* the other items need be marked as
- * *not* selected by setting `aria-selected` to false.
- * * The outermost element with the keyboard focus needs to have attributes
- * set on it so that the selection is knowable at the list level via the
- * `aria-activedescendant` attribute.
- * * Use of `aria-activedescendant` in turn requires that all items in the
- * list have ID attributes assigned to them.
- *
- * This mixin tries to address all of the above requirements. To that end,
- * this mixin will assign generated IDs to any item that doesn't already have
- * an ID.
- *
- * ARIA relies on elements to provide `role` attributes. This mixin will apply
- * a default role of "listbox" on the outer list if it doesn't already have an
- * explicit role. Similarly, this mixin will apply a default role of "option"
- * to any list item that does not already have a role specified.
- *
- * This mixin expects a set of members that manage the state of the selection:
- * `[symbols.itemSelected]`, `itemAdded`, and `selectedIndex`. You can
- * supply these yourself, or do so via
- * [SingleSelectionMixin](SingleSelectionMixin.md).
- */
- var SelectionAriaActive = function (_base) {
- _inherits(SelectionAriaActive, _base);
-
- function SelectionAriaActive() {
- _classCallCheck(this, SelectionAriaActive);
-
- return _possibleConstructorReturn(this, (SelectionAriaActive.__proto__ || Object.getPrototypeOf(SelectionAriaActive)).apply(this, arguments));
- }
-
- _createClass(SelectionAriaActive, [{
- key: 'connectedCallback',
- value: function connectedCallback() {
- if (_get(SelectionAriaActive.prototype.__proto__ || Object.getPrototypeOf(SelectionAriaActive.prototype), 'connectedCallback', this)) {
- _get(SelectionAriaActive.prototype.__proto__ || Object.getPrototypeOf(SelectionAriaActive.prototype), 'connectedCallback', this).call(this);
- }
- // Set default ARIA role.
- if (this.getAttribute('role') == null && this[_symbols2.default.defaults].role) {
- this.setAttribute('role', this[_symbols2.default.defaults].role);
- }
- }
- }, {
- key: _symbols2.default.itemAdded,
- value: function value(item) {
- if (_get(SelectionAriaActive.prototype.__proto__ || Object.getPrototypeOf(SelectionAriaActive.prototype), _symbols2.default.itemAdded, this)) {
- _get(SelectionAriaActive.prototype.__proto__ || Object.getPrototypeOf(SelectionAriaActive.prototype), _symbols2.default.itemAdded, this).call(this, item);
- }
-
- if (!item.getAttribute('role')) {
- // Assign a default ARIA role.
- item.setAttribute('role', 'option');
- }
-
- // Ensure each item has an ID so we can set aria-activedescendant on the
- // overall list whenever the selection changes.
- //
- // The ID will take the form of a base ID plus a unique integer. The base
- // ID will be incorporate the component's own ID. E.g., if a component has
- // ID "foo", then its items will have IDs that look like "_fooOption1". If
- // the compnent has no ID itself, its items will get IDs that look like
- // "_option1". Item IDs are prefixed with an underscore to differentiate
- // them from manually-assigned IDs, and to minimize the potential for ID
- // conflicts.
- if (!item.id) {
- var baseId = this.id ? "_" + this.id + "Option" : "_option";
- item.id = baseId + idCount++;
- }
- }
- }, {
- key: _symbols2.default.itemSelected,
- value: function value(item, selected) {
- if (_get(SelectionAriaActive.prototype.__proto__ || Object.getPrototypeOf(SelectionAriaActive.prototype), _symbols2.default.itemSelected, this)) {
- _get(SelectionAriaActive.prototype.__proto__ || Object.getPrototypeOf(SelectionAriaActive.prototype), _symbols2.default.itemSelected, this).call(this, item, selected);
- }
- item.setAttribute('aria-selected', selected);
- var itemId = item.id;
- if (itemId && selected) {
- this.setAttribute('aria-activedescendant', itemId);
- }
- }
- }, {
- key: _symbols2.default.defaults,
- get: function get() {
- var defaults = _get(SelectionAriaActive.prototype.__proto__ || Object.getPrototypeOf(SelectionAriaActive.prototype), _symbols2.default.defaults, this) || {};
- defaults.role = 'listbox';
- return defaults;
- }
- }, {
- key: 'selectedItem',
- get: function get() {
- return _get(SelectionAriaActive.prototype.__proto__ || Object.getPrototypeOf(SelectionAriaActive.prototype), 'selectedItem', this);
- },
- set: function set(item) {
- if ('selectedItem' in base.prototype) {
- _set(SelectionAriaActive.prototype.__proto__ || Object.getPrototypeOf(SelectionAriaActive.prototype), 'selectedItem', item, this);
- }
- if (item == null) {
- // Selection was removed.
- this.removeAttribute('aria-activedescendant');
- }
- }
- }]);
-
- return SelectionAriaActive;
- }(base);
-
- return SelectionAriaActive;
-};
-
-},{"./symbols":23}],15:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
-
-var _get = function get(object, property, receiver) { if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { return get(parent, property, receiver); } } else if ("value" in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } };
-
-var _symbols = require('../src/symbols');
-
-var _symbols2 = _interopRequireDefault(_symbols);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-/* Exported function extends a base class with SelectionHighlight. */
-exports.default = function (base) {
-
- /**
- * Template mixin which applies standard highlight colors to a selected item.
- *
- * This mixin highlights textual items (e.g., in a list) in a standard way by
- * using the CSS `highlight` and `highlighttext` color values. These values
- * respect operating system defaults and user preferences, and hence are good
- * default values for highlight colors.
- *
- * This mixin expects a `selected` class to be applied to selected items. You
- * can use [ContentItemsMixin](ContentItemsMixin.md) for that purpose.
- */
- var SelectionHighlight = function (_base) {
- _inherits(SelectionHighlight, _base);
-
- function SelectionHighlight() {
- _classCallCheck(this, SelectionHighlight);
-
- return _possibleConstructorReturn(this, (SelectionHighlight.__proto__ || Object.getPrototypeOf(SelectionHighlight)).apply(this, arguments));
- }
-
- _createClass(SelectionHighlight, [{
- key: _symbols2.default.template,
- get: function get() {
- var baseTemplate = _get(SelectionHighlight.prototype.__proto__ || Object.getPrototypeOf(SelectionHighlight.prototype), _symbols2.default.template, this) || '';
- return '\n \n ' + baseTemplate + '\n ';
- }
- }]);
-
- return SelectionHighlight;
- }(base);
-
- return SelectionHighlight;
-};
-
-},{"../src/symbols":23}],16:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
-
-var _set = function set(object, property, value, receiver) { var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent !== null) { set(parent, property, value, receiver); } } else if ("value" in desc && desc.writable) { desc.value = value; } else { var setter = desc.set; if (setter !== undefined) { setter.call(receiver, value); } } return value; };
-
-var _get = function get(object, property, receiver) { if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { return get(parent, property, receiver); } } else if ("value" in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } };
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-/* Exported function extends a base class with SelectionInView. */
-exports.default = function (base) {
-
- /**
- * Mixin which scrolls a container to ensure that a newly-selected item is
- * visible to the user.
- *
- * When the selected item in a list-like component changes, it's easier for
- * the to confirm that the selection has changed to an appropriate item if the
- * user can actually see that item.
- *
- * This mixin expects a `selectedItem` property to be set when the selection
- * changes. You can supply that yourself, or use
- * [SingleSelectionMixin](SingleSelectionMixin.md).
- */
- var SelectionInView = function (_base) {
- _inherits(SelectionInView, _base);
-
- function SelectionInView() {
- _classCallCheck(this, SelectionInView);
-
- return _possibleConstructorReturn(this, (SelectionInView.__proto__ || Object.getPrototypeOf(SelectionInView)).apply(this, arguments));
- }
-
- _createClass(SelectionInView, [{
- key: 'connectedCallback',
- value: function connectedCallback() {
- if (_get(SelectionInView.prototype.__proto__ || Object.getPrototypeOf(SelectionInView.prototype), 'connectedCallback', this)) {
- _get(SelectionInView.prototype.__proto__ || Object.getPrototypeOf(SelectionInView.prototype), 'connectedCallback', this).call(this);
- }
- var selectedItem = this.selectedItem;
- if (selectedItem) {
- this.scrollItemIntoView(selectedItem);
- }
- }
- }, {
- key: 'scrollItemIntoView',
-
-
- /**
- * Scroll the given element completely into view, minimizing the degree of
- * scrolling performed.
- *
- * Blink has a `scrollIntoViewIfNeeded()` function that does something
- * similar, but unfortunately it's non-standard, and in any event often ends
- * up scrolling more than is absolutely necessary.
- *
- * @param {HTMLElement} item - the item to scroll into view.
- */
- value: function scrollItemIntoView(item) {
- if (_get(SelectionInView.prototype.__proto__ || Object.getPrototypeOf(SelectionInView.prototype), 'scrollItemIntoView', this)) {
- _get(SelectionInView.prototype.__proto__ || Object.getPrototypeOf(SelectionInView.prototype), 'scrollItemIntoView', this).call(this);
- }
- // Get the relative position of the item with respect to the top of the
- // list's scrollable canvas. An item at the top of the list will have a
- // elementTop of 0.
-
- var scrollTarget = this.scrollTarget;
- var elementTop = item.offsetTop - scrollTarget.offsetTop - scrollTarget.clientTop;
- var elementBottom = elementTop + item.offsetHeight;
- // Determine the bottom of the scrollable canvas.
- var scrollBottom = scrollTarget.scrollTop + scrollTarget.clientHeight;
- if (elementBottom > scrollBottom) {
- // Scroll up until item is entirely visible.
- scrollTarget.scrollTop += elementBottom - scrollBottom;
- } else if (elementTop < scrollTarget.scrollTop) {
- // Scroll down until item is entirely visible.
- scrollTarget.scrollTop = elementTop;
- }
- }
-
- /**
- * The element that should be scrolled to bring an item into view.
- *
- * The default value of this property is the element itself.
- *
- * @type {HTMLElement}
- */
-
- }, {
- key: 'selectedItem',
- get: function get() {
- return _get(SelectionInView.prototype.__proto__ || Object.getPrototypeOf(SelectionInView.prototype), 'selectedItem', this);
- },
- set: function set(item) {
- if ('selectedItem' in base.prototype) {
- _set(SelectionInView.prototype.__proto__ || Object.getPrototypeOf(SelectionInView.prototype), 'selectedItem', item, this);
- }
- if (item) {
- // Keep the selected item in view.
- this.scrollItemIntoView(item);
- }
- }
- }, {
- key: 'scrollTarget',
- get: function get() {
- // Prefer base result.
- return 'scrollTarget' in base.prototype ? _get(SelectionInView.prototype.__proto__ || Object.getPrototypeOf(SelectionInView.prototype), 'scrollTarget', this) : this;
- },
- set: function set(element) {
- if ('scrollTarget' in base.prototype) {
- _set(SelectionInView.prototype.__proto__ || Object.getPrototypeOf(SelectionInView.prototype), 'scrollTarget', element, this);
- }
- }
- }]);
-
- return SelectionInView;
- }(base);
-
- return SelectionInView;
-};
-
-},{}],17:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-/* Exported function extends a base class with ShadowElementReferences. */
-exports.default = function (base) {
-
- /**
- * Mixin to create references to elements in a component's Shadow DOM subtree.
- *
- * This adds a member on the component called `this.$` that can be used to
- * reference shadow elements with IDs. E.g., if component's shadow contains an
- * element ``, then this mixin will create a member
- * `this.$.foo` that points to that button.
- *
- * Such references simplify a component's access to its own elements. In
- * exchange, this mixin trades off a one-time cost of querying all elements in
- * the shadow tree instead of paying an ongoing cost to query for an element
- * each time the component wants to inspect or manipulate it.
- *
- * This mixin expects the component to define a Shadow DOM subtree. You can
- * create that tree yourself, or make use of
- * [ShadowTemplateMixin](ShadowTemplateMixin.md).
- *
- * This mixin is inspired by Polymer's [automatic
- * node finding](https://www.polymer-project.org/1.0/docs/devguide/local-dom.html#node-finding)
- * feature.
- */
- var ShadowElementReferences = function (_base) {
- _inherits(ShadowElementReferences, _base);
-
- function ShadowElementReferences() {
- _classCallCheck(this, ShadowElementReferences);
-
- var _this = _possibleConstructorReturn(this, (ShadowElementReferences.__proto__ || Object.getPrototypeOf(ShadowElementReferences)).call(this));
-
- if (_this.shadowRoot) {
- // Look for elements in the shadow subtree that have id attributes.
- // An alternatively implementation of this mixin would be to just define
- // a this.$ getter that lazily does this search the first time someone
- // tries to access this.$. That might introduce some complexity – if the
- // the tree changed after it was first populated, the result of
- // searching for a node might be somewhat unpredictable.
- _this.$ = {};
- var nodesWithIds = _this.shadowRoot.querySelectorAll('[id]');
- [].forEach.call(nodesWithIds, function (node) {
- var id = node.getAttribute('id');
- _this.$[id] = node;
- });
- }
- return _this;
- }
-
- /**
- * The collection of references to the elements with IDs in a component's
- * Shadow DOM subtree.
- *
- * @type {object}
- * @member $
- */
-
-
- return ShadowElementReferences;
- }(base);
-
- return ShadowElementReferences;
-};
-
-},{}],18:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _symbols = require('../src/symbols');
-
-var _symbols2 = _interopRequireDefault(_symbols);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-/* Exported function extends a base class with ShadowTemplate. */
-exports.default = function (base) {
-
- /**
- * Mixin for stamping a template into a Shadow DOM subtree upon component
- * instantiation.
- *
- * To use this mixin, define a `template` property as a string or HTML
- * `` element:
- *
- * class MyElement extends ShadowTemplateMixin(HTMLElement) {
- * get [symbols.template]() {
- * return `Hello, world .`;
- * }
- * }
- *
- * When your component class is instantiated, a shadow root will be created on
- * the instance, and the contents of the template will be cloned into the
- * shadow root. If your component does not define a `template` property, this
- * mixin has no effect.
- *
- * For the time being, this extension retains support for Shadow DOM v0. That
- * will eventually be deprecated as browsers (and the Shadow DOM polyfill)
- * implement Shadow DOM v1.
- */
- var ShadowTemplate = function (_base) {
- _inherits(ShadowTemplate, _base);
-
- /*
- * If the component defines a template, a shadow root will be created on the
- * component instance, and the template stamped into it.
- */
- function ShadowTemplate() {
- _classCallCheck(this, ShadowTemplate);
-
- var _this = _possibleConstructorReturn(this, (ShadowTemplate.__proto__ || Object.getPrototypeOf(ShadowTemplate)).call(this));
-
- var template = _this[_symbols2.default.template];
- // TODO: Save the processed template with the component's class prototype
- // so it doesn't need to be processed with every instantiation.
- if (template) {
-
- if (typeof template === 'string') {
- // Upgrade plain string to real template.
- template = createTemplateWithInnerHTML(template);
- }
-
- if (window.ShadowDOMPolyfill) {
- shimTemplateStyles(template, _this.localName);
- }
-
- var root = _this.attachShadow({ mode: 'open' });
- var clone = document.importNode(template.content, true);
- root.appendChild(clone);
- }
- return _this;
- }
-
- return ShadowTemplate;
- }(base);
-
- return ShadowTemplate;
-};
-
-// Convert a plain string of HTML into a real template element.
-
-
-function createTemplateWithInnerHTML(innerHTML) {
- var template = document.createElement('template');
- // REVIEW: Is there an easier way to do this?
- // We'd like to just set innerHTML on the template content, but since it's
- // a DocumentFragment, that doesn't work.
- var div = document.createElement('div');
- div.innerHTML = innerHTML;
- while (div.childNodes.length > 0) {
- template.content.appendChild(div.childNodes[0]);
- }
- return template;
-}
-
-// Invoke basic style shimming with ShadowCSS.
-function shimTemplateStyles(template, tag) {
- window.WebComponents.ShadowCSS.shimStyling(template.content, tag);
-}
-
-},{"../src/symbols":23}],19:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
-
-var _get = function get(object, property, receiver) { if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { return get(parent, property, receiver); } } else if ("value" in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } };
-
-var _set = function set(object, property, value, receiver) { var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent !== null) { set(parent, property, value, receiver); } } else if ("value" in desc && desc.writable) { desc.value = value; } else { var setter = desc.set; if (setter !== undefined) { setter.call(receiver, value); } } return value; };
-
-var _createSymbol = require('./createSymbol');
-
-var _createSymbol2 = _interopRequireDefault(_createSymbol);
-
-var _symbols = require('./symbols');
-
-var _symbols2 = _interopRequireDefault(_symbols);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-// Symbols for private data members on an element.
-var canSelectNextSymbol = (0, _createSymbol2.default)('canSelectNext');
-var canSelectPreviousSymbol = (0, _createSymbol2.default)('canSelectPrevious');
-var selectionRequiredSymbol = (0, _createSymbol2.default)('selectionRequired');
-var selectionWrapsSymbol = (0, _createSymbol2.default)('selectionWraps');
-
-// We want to expose both selectedIndex and selectedItem as independent
-// properties but keep them in sync. This allows a component user to reference
-// the selection by whatever means is most natural for their situation.
-//
-// To efficiently keep these properties in sync, we track "external" and
-// "internal" references for each property:
-//
-// The external index or item is the one we report to the outside world when
-// asked for selection. When handling a change to index or item, we update the
-// external reference as soon as possible, so that if anyone immediately asks
-// for the current selection, they will receive a stable answer.
-//
-// The internal index or item tracks whichever index or item last received the
-// full set of processing. Processing includes raising a change event for the
-// new value. Once we've begun that processing, we store the new value as the
-// internal value to indicate we've handled it.
-//
-var externalSelectedIndexSymbol = (0, _createSymbol2.default)('externalSelectedIndex');
-var externalSelectedItemSymbol = (0, _createSymbol2.default)('externalSelectedItem');
-var internalSelectedIndexSymbol = (0, _createSymbol2.default)('internalSelectedIndex');
-var internalSelectedItemSymbol = (0, _createSymbol2.default)('internalSelectedItem');
-
-/* Exported function extends a base class with SingleSelection. */
-
-exports.default = function (base) {
-
- /**
- * Mixin which manages single-selection semantics for items in a list.
- *
- * This mixin expects a component to provide an `items` Array or NodeList of
- * all elements in the list. A standard way to do that with is the
- * [ContentItemsMixin](ContentItemsMixin.md), which takes a component's
- * content (typically its distributed children) as the set of list items; see
- * that mixin for details.
- *
- * This mixin tracks a single selected item in the list, and provides means to
- * get and set that state by item position (`selectedIndex`) or item identity
- * (`selectedItem`). The selection can be moved in the list via the methods
- * `selectFirst`, `selectLast`, `selectNext`, and `selectPrevious`.
- *
- * This mixin does not produce any user-visible effects to represent
- * selection. Other mixins, such as
- * [SelectionAriaActiveMixin](SelectionAriaActiveMixin.md),
- * [SelectionHighlightMixin](SelectionHighlightMixin.md) and
- * [SelectionInViewMixin](SelectionInViewMixin.md), modify the selected item
- * in common ways to let the user know a given item is selected or not
- * selected.
- */
- var SingleSelection = function (_base) {
- _inherits(SingleSelection, _base);
-
- function SingleSelection() {
- _classCallCheck(this, SingleSelection);
-
- // Set defaults.
- var _this = _possibleConstructorReturn(this, (SingleSelection.__proto__ || Object.getPrototypeOf(SingleSelection)).call(this));
-
- if (typeof _this.selectionRequired === 'undefined') {
- _this.selectionRequired = _this[_symbols2.default.defaults].selectionRequired;
- }
- if (typeof _this.selectionWraps === 'undefined') {
- _this.selectionWraps = _this[_symbols2.default.defaults].selectionWraps;
- }
- return _this;
- }
-
- /**
- * True if the selection can be moved to the next item, false if not (the
- * selected item is the last item in the list).
- *
- * @type {boolean}
- */
-
-
- _createClass(SingleSelection, [{
- key: _symbols2.default.itemAdded,
-
-
- /**
- * Handle a new item being added to the list.
- *
- * The default implementation of this method simply sets the item's
- * selection state to false.
- *
- * @param {HTMLElement} item - the item being added
- */
- value: function value(item) {
- if (_get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), _symbols2.default.itemAdded, this)) {
- _get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), _symbols2.default.itemAdded, this).call(this, item);
- }
- this[_symbols2.default.itemSelected](item, item === this.selectedItem);
- }
- }, {
- key: _symbols2.default.itemsChanged,
- value: function value() {
- if (_get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), _symbols2.default.itemsChanged, this)) {
- _get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), _symbols2.default.itemsChanged, this).call(this);
- }
-
- // In case selected item changed position or was removed.
- trackSelectedItem(this);
-
- // In case the change in items affected which navigations are possible.
- updatePossibleNavigations(this);
- }
-
- /**
- * Apply the indicate selection state to the item.
- *
- * The default implementation of this method does nothing. User-visible
- * effects will typically be handled by other mixins.
- *
- * @param {HTMLElement} item - the item being selected/deselected
- * @param {boolean} selected - true if the item is selected, false if not
- */
-
- }, {
- key: _symbols2.default.itemSelected,
- value: function value(item, selected) {
- if (_get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), _symbols2.default.itemSelected, this)) {
- _get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), _symbols2.default.itemSelected, this).call(this, item, selected);
- }
- }
-
- /**
- * The index of the item which is currently selected.
- *
- * A `selectedIndex` of -1 indicates there is no selection. Setting this
- * property to -1 will remove any existing selection.
- *
- * @type {number}
- */
-
- }, {
- key: 'selectFirst',
-
-
- /**
- * Select the first item in the list.
- */
- value: function selectFirst() {
- if (_get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), 'selectFirst', this)) {
- _get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), 'selectFirst', this).call(this);
- }
- return selectIndex(this, 0);
- }
-
- /**
- * True if the list should always have a selection (if it has items).
- *
- * @type {boolean}
- * @default false
- */
-
- }, {
- key: 'selectLast',
-
-
- /**
- * Select the last item in the list.
- */
- value: function selectLast() {
- if (_get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), 'selectLast', this)) {
- _get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), 'selectLast', this).call(this);
- }
- return selectIndex(this, this.items.length - 1);
- }
-
- /**
- * Select the next item in the list.
- */
-
- }, {
- key: 'selectNext',
- value: function selectNext() {
- if (_get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), 'selectNext', this)) {
- _get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), 'selectNext', this).call(this);
- }
- return selectIndex(this, this.selectedIndex + 1);
- }
-
- /**
- * Select the previous item in the list.
- *
- * If the list has no selection, the last item will be selected.
- */
-
- }, {
- key: 'selectPrevious',
- value: function selectPrevious() {
- if (_get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), 'selectPrevious', this)) {
- _get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), 'selectPrevious', this).call(this);
- }
- var newIndex = this.selectedIndex < 0 ? this.items.length - 1 : // No selection yet; select last item.
- this.selectedIndex - 1;
- return selectIndex(this, newIndex);
- }
-
- /**
- * Fires when the selectedItem property changes.
- *
- * @memberof SingleSelection
- * @event selected-item-changed
- * @param {HTMLElement} detail.selectedItem The new selected item.
- * @param {HTMLElement} detail.previousItem The previously selected item.
- */
-
- /**
- * Fires when the selectedIndex property changes.
- *
- * @memberof SingleSelection
- * @event selected-index-changed
- * @param {number} detail.selectedIndex The new selected index.
- */
-
- }, {
- key: 'canSelectNext',
- get: function get() {
- return this[canSelectNextSymbol];
- },
- set: function set(canSelectNext) {
- var previousCanSelectNext = this[canSelectNextSymbol];
- this[canSelectNextSymbol] = canSelectNext;
- if ('canSelectNext' in base.prototype) {
- _set(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), 'canSelectNext', canSelectNext, this);
- }
- if (canSelectNext !== previousCanSelectNext) {
- this.dispatchEvent(new CustomEvent('can-select-next-changed'));
- }
- }
-
- /**
- * True if the selection can be moved to the previous item, false if not
- * (the selected item is the first one in the list).
- *
- * @type {boolean}
- */
-
- }, {
- key: 'canSelectPrevious',
- get: function get() {
- return this[canSelectPreviousSymbol];
- },
- set: function set(canSelectPrevious) {
- var previousCanSelectPrevious = this[canSelectPreviousSymbol];
- this[canSelectPreviousSymbol] = canSelectPrevious;
- if ('canSelectPrevious' in base.prototype) {
- _set(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), 'canSelectPrevious', canSelectPrevious, this);
- }
- if (canSelectPrevious !== previousCanSelectPrevious) {
- this.dispatchEvent(new CustomEvent('can-select-previous-changed'));
- }
- }
- }, {
- key: _symbols2.default.defaults,
- get: function get() {
- var defaults = _get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), _symbols2.default.defaults, this) || {};
- defaults.selectionRequired = false;
- defaults.selectionWraps = false;
- return defaults;
- }
- }, {
- key: 'selectedIndex',
- get: function get() {
- return this[externalSelectedIndexSymbol] != null ? this[externalSelectedIndexSymbol] : -1;
- },
- set: function set(index) {
- // See notes at top about internal vs. external copies of this property.
- var previousSelectedIndex = this[internalSelectedIndexSymbol];
- var item = void 0;
- if (index !== this[externalSelectedIndexSymbol]) {
- // Store the new index and the corresponding item.
- var items = this.items;
- var hasItems = items && items.length > 0;
- if (!(hasItems && index >= 0 && index < items.length)) {
- index = -1; // No item at that index.
- }
- this[externalSelectedIndexSymbol] = index;
- item = hasItems && index >= 0 ? items[index] : null;
- this[externalSelectedItemSymbol] = item;
- } else {
- item = this[externalSelectedItemSymbol];
- }
-
- // Now let super do any work.
- if ('selectedIndex' in base.prototype) {
- _set(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), 'selectedIndex', index, this);
- }
-
- if (index !== previousSelectedIndex) {
- // The selected index changed.
- this[internalSelectedIndexSymbol] = index;
-
- var event = new CustomEvent('selected-index-changed', {
- detail: {
- selectedIndex: index,
- value: index // for Polymer binding. TODO: Verify still necessary
- }
- });
- this.dispatchEvent(event);
- }
-
- if (this[internalSelectedItemSymbol] !== item) {
- // Update selectedItem property so it can have its own effects.
- this.selectedItem = item;
- }
- }
-
- /**
- * The currently selected item, or null if there is no selection.
- *
- * Setting this property to null deselects any currently-selected item.
- * Setting this property to an object that is not in the list has no effect.
- *
- * TODO: Even if selectionRequired, can still explicitly set selectedItem to null.
- * TODO: If selectionRequired, leave selection alone?
- *
- * @type {object}
- */
-
- }, {
- key: 'selectedItem',
- get: function get() {
- return this[externalSelectedItemSymbol] || null;
- },
- set: function set(item) {
- // See notes at top about internal vs. external copies of this property.
- var previousSelectedItem = this[internalSelectedItemSymbol];
- var index = void 0;
- if (item !== this[externalSelectedItemSymbol]) {
- // Store item and look up corresponding index.
- var items = this.items;
- var hasItems = items && items.length > 0;
- index = hasItems ? Array.prototype.indexOf.call(items, item) : -1;
- this[externalSelectedIndexSymbol] = index;
- if (index < 0) {
- item = null; // The indicated item isn't actually in `items`.
- }
- this[externalSelectedItemSymbol] = item;
- } else {
- index = this[externalSelectedIndexSymbol];
- }
-
- // Now let super do any work.
- if ('selectedItem' in base.prototype) {
- _set(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), 'selectedItem', item, this);
- }
-
- if (item !== previousSelectedItem) {
- // The selected item changed.
- this[internalSelectedItemSymbol] = item;
-
- if (previousSelectedItem) {
- // Update selection state of old item.
- this[_symbols2.default.itemSelected](previousSelectedItem, false);
- }
- if (item) {
- // Update selection state to new item.
- this[_symbols2.default.itemSelected](item, true);
- }
-
- updatePossibleNavigations(this);
-
- var event = new CustomEvent('selected-item-changed', {
- detail: {
- selectedItem: item,
- value: item // for Polymer binding
- }
- });
- this.dispatchEvent(event);
- }
-
- if (this[internalSelectedIndexSymbol] !== index) {
- // Update selectedIndex property so it can have its own effects.
- this.selectedIndex = index;
- }
- }
- }, {
- key: 'selectionRequired',
- get: function get() {
- return this[selectionRequiredSymbol];
- },
- set: function set(selectionRequired) {
- this[selectionRequiredSymbol] = selectionRequired;
- if ('selectionRequired' in base.prototype) {
- _set(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), 'selectionRequired', selectionRequired, this);
- }
- trackSelectedItem(this);
- }
-
- /**
- * True if selection navigations wrap from last to first, and vice versa.
- *
- * @type {boolean}
- * @default false
- */
-
- }, {
- key: 'selectionWraps',
- get: function get() {
- return this[selectionWrapsSymbol];
- },
- set: function set(value) {
- this[selectionWrapsSymbol] = String(value) === 'true';
- if ('selectionWraps' in base.prototype) {
- _set(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), 'selectionWraps', value, this);
- }
- updatePossibleNavigations(this);
- }
- }]);
-
- return SingleSelection;
- }(base);
-
- return SingleSelection;
-};
-
-// Ensure the given index is within bounds, and select it if it's not already
-// selected.
-
-
-function selectIndex(element, index) {
- var count = element.items.length;
-
- var boundedIndex = element.selectionWraps ?
- // JavaScript mod doesn't handle negative numbers the way we want to wrap.
- // See http://stackoverflow.com/a/18618250/76472
- (index % count + count) % count :
-
- // Keep index within bounds of array.
- Math.max(Math.min(index, count - 1), 0);
-
- var previousIndex = element.selectedIndex;
- if (previousIndex !== boundedIndex) {
- element.selectedIndex = boundedIndex;
- return true;
- } else {
- return false;
- }
-}
-
-// Following a change in the set of items, or in the value of the
-// `selectionRequired` property, reacquire the selected item. If it's moved,
-// update `selectedIndex`. If it's been removed, and a selection is required,
-// try to select another item.
-function trackSelectedItem(element) {
-
- var items = element.items;
- var itemCount = items ? items.length : 0;
-
- var previousSelectedItem = element.selectedItem;
- if (!previousSelectedItem) {
- // No item was previously selected.
- if (element.selectionRequired) {
- // Select the first item by default.
- element.selectedIndex = 0;
- }
- } else if (itemCount === 0) {
- // We've lost the selection, and there's nothing left to select.
- element.selectedItem = null;
- } else {
- // Try to find the previously-selected item in the current set of items.
- var indexInCurrentItems = Array.prototype.indexOf.call(items, previousSelectedItem);
- var previousSelectedIndex = element.selectedIndex;
- if (indexInCurrentItems < 0) {
- // Previously-selected item was removed from the items.
- // Select the item at the same index (if it exists) or as close as possible.
- var newSelectedIndex = Math.min(previousSelectedIndex, itemCount - 1);
- // Select by item, since index may be the same, and we want to raise the
- // selected-item-changed event.
- element.selectedItem = items[newSelectedIndex];
- } else if (indexInCurrentItems !== previousSelectedIndex) {
- // Previously-selected item still there, but changed position.
- element.selectedIndex = indexInCurrentItems;
- }
- }
-}
-
-// Following a change in selection, report whether it's now possible to
-// go next/previous from the given index.
-function updatePossibleNavigations(element) {
- var canSelectNext = void 0;
- var canSelectPrevious = void 0;
- var items = element.items;
- if (items == null || items.length === 0) {
- // No items to select.
- canSelectNext = false;
- canSelectPrevious = false;
- }if (element.selectionWraps) {
- // Since there are items, can always go next/previous.
- canSelectNext = true;
- canSelectPrevious = true;
- } else {
- var index = element.selectedIndex;
- if (index < 0 && items.length > 0) {
- // Special case. If there are items but no selection, declare that it's
- // always possible to go next/previous to create a selection.
- canSelectNext = true;
- canSelectPrevious = true;
- } else {
- // Normal case: we have an index in a list that has items.
- canSelectPrevious = index > 0;
- canSelectNext = index < items.length - 1;
- }
- }
- if (element.canSelectNext !== canSelectNext) {
- element.canSelectNext = canSelectNext;
- }
- if (element.canSelectPrevious !== canSelectPrevious) {
- element.canSelectPrevious = canSelectPrevious;
- }
-}
-
-},{"./createSymbol":20,"./symbols":23}],20:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-exports.default = createSymbol;
-/**
- * Helper function to create a symbol that can be used for associating private
- * data with an element.
- *
- * Mixins and component classes often want to associate private data with an
- * element instance, but JavaScript does not have direct support for true
- * private properties. One approach is to use the
- * [Symbol](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Symbol)
- * data type to set and retrieve data on an element.
- *
- * Unfortunately, the Symbol type is not available in Internet Explorer 11. The
- * `createSymbol` helper function exists as a workaround for IE 11. Rather than
- * returning a true Symbol, it simply returns an underscore-prefixed string.
- *
- * Usage:
- *
- * const fooSymbol = createSymbol('foo');
- *
- * class MyElement extends HTMLElement {
- * get foo() {
- * return this[fooSymbol];
- * }
- * set foo(value) {
- * this[fooSymbol] = value;
- * }
- * }
- *
- * In IE 11, this sample will "hide" data behind an instance property this._foo.
- * The use of the underscore is meant to reduce (not eliminate) the potential
- * for name conflicts, and discourage (not prevent) external access to this
- * data. In modern browsers, the above code will eliminate the potential of
- * naming conflicts, and better hide the data behind a real Symbol.
- *
- * @function createSymbol
- * @param {string} description - A string to identify the symbol when debugging
- */
-function createSymbol(description) {
- return typeof Symbol === 'function' ? Symbol(description) : '_' + description;
-}
-
-},{}],21:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-exports.default = microtask;
-/*
- * Microtask helper for IE 11.
- *
- * Executing a function as a microtask is trivial in browsers that support
- * promises, whose then() clauses use microtask timing. IE 11 doesn't support
- * promises, but does support MutationObservers, which are also executed as
- * microtasks. So this helper uses an MutationObserver to achieve microtask
- * timing.
- *
- * See https://jakearchibald.com/2015/tasks-microtasks-queues-and-schedules/
- *
- * Inspired by Polymer's async() function.
- */
-
-// The queue of pending callbacks to be executed as microtasks.
-var callbacks = [];
-
-// Create an element that we will modify to force observable mutations.
-var element = document.createTextNode('');
-
-// A monotonically-increasing value.
-var counter = 0;
-
-/**
- * Add a callback to the microtask queue.
- *
- * This uses a MutationObserver so that it works on IE 11.
- *
- * NOTE: IE 11 may actually use timeout timing with MutationObservers. This
- * needs more investigation.
- *
- * @function microtask
- * @param {function} callback
- */
-function microtask(callback) {
- callbacks.push(callback);
- // Force a mutation.
- element.textContent = ++counter;
-}
-
-// Execute any pending callbacks.
-function executeCallbacks() {
- while (callbacks.length > 0) {
- var callback = callbacks.shift();
- callback();
- }
-}
-
-// Create the observer.
-var observer = new MutationObserver(executeCallbacks);
-observer.observe(element, {
- characterData: true
-});
-
-},{}],22:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createSymbol = require('./createSymbol');
-
-var _createSymbol2 = _interopRequireDefault(_createSymbol);
-
-var _toggleClass2 = require('./toggleClass');
-
-var _toggleClass3 = _interopRequireDefault(_toggleClass2);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-// Symbols for private data members on an element.
-var safeToSetAttributesSymbol = (0, _createSymbol2.default)('safeToSetAttributes');
-var pendingAttributesSymbol = (0, _createSymbol2.default)('pendingAttributes');
-var pendingClassesSymbol = (0, _createSymbol2.default)('pendingClasses');
-
-/**
- * Helper functions for updating attributes, including the `class` attribute.
- */
-exports.default = {
-
- /**
- * Perform any pending updates to attributes and classes.
- *
- * This writes any `setAttribute` or `toggleClass` values that were performed
- * before an element was attached to the document for the first time.
- *
- * This method should be called by mixins/components in their
- * `connectedCallback`. If mulitple mixins/components invoke this during the
- * same `connectedCallback`, only the first call will have any effect. The
- * subsequent calls will be harmless.
- *
- * @param {HTMLElement} element - The element being added to the document.
- */
- connected: function connected(element) {
- element[safeToSetAttributesSymbol] = true;
-
- // Set any pending attributes.
- if (element[pendingAttributesSymbol]) {
- for (var attribute in element[pendingAttributesSymbol]) {
- var value = element[pendingAttributesSymbol][attribute];
- setAttributeToElement(element, attribute, value);
- }
- element[pendingAttributesSymbol] = null;
- }
-
- // Set any pending classes.
- if (element[pendingClassesSymbol]) {
- for (var className in element[pendingClassesSymbol]) {
- var _value = element[pendingClassesSymbol][className];
- (0, _toggleClass3.default)(element, className, _value);
- }
- element[pendingClassesSymbol] = null;
- }
- },
-
-
- /**
- * Set/unset the attribute with the indicated name.
- *
- * This method exists primarily to handle the case where an element wants to
- * set a default property value that should be reflected as an attribute. An
- * important limitation of custom element consturctors is that they cannot
- * set attributes. A call to `setAttribute` during the constructor will
- * be deferred until the element is connected to the document.
- *
- * @param {string} attribute - The name of the *attribute* (not property) to set.
- * @param {object} value - The value to set. If null, the attribute will be removed.
- */
- setAttribute: function setAttribute(element, attribute, value) {
- if (element[safeToSetAttributesSymbol]) {
- // Safe to set attributes immediately.
- setAttributeToElement(element, attribute, value);
- } else {
- // Defer setting attributes until the first time we're connected.
- if (!element[pendingAttributesSymbol]) {
- element[pendingAttributesSymbol] = {};
- }
- element[pendingAttributesSymbol][attribute] = value;
- }
- },
-
-
- /**
- * Set/unset the class with the indicated name.
- *
- * This method exists primarily to handle the case where an element wants to
- * set a default property value that should be reflected as as class. An
- * important limitation of custom element consturctors is that they cannot
- * set attributes, including the `class` attribute. A call to
- * `toggleClass` during the constructor will be deferred until the element
- * is connected to the document.
- *
- * @param {string} className - The name of the class to set.
- * @param {object} value - True to set the class, false to remove it.
- */
- toggleClass: function toggleClass(element, className, value) {
- if (element[safeToSetAttributesSymbol]) {
- // Safe to set class immediately.
- (0, _toggleClass3.default)(element, className, value);
- } else {
- // Defer setting class until the first time we're connected.
- if (!element[pendingClassesSymbol]) {
- element[pendingClassesSymbol] = {};
- }
- element[pendingClassesSymbol][className] = value;
- }
- }
-};
-
-// Reflect the attribute to the given element.
-// If the value is null, remove the attribute.
-
-function setAttributeToElement(element, attributeName, value) {
- if (value === null || typeof value === 'undefined') {
- element.removeAttribute(attributeName);
- } else {
- var text = String(value);
- // Avoid recursive attributeChangedCallback calls.
- if (element.getAttribute(attributeName) !== text) {
- element.setAttribute(attributeName, value);
- }
- }
-}
-
-},{"./createSymbol":20,"./toggleClass":24}],23:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createSymbol = require('./createSymbol');
-
-var _createSymbol2 = _interopRequireDefault(_createSymbol);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-/**
- * A collection of Symbol objects for standard component properties and methods.
- *
- * These Symbol objects are used to allow mixins and a component to internally
- * communicate, without exposing these properties and methods in the component's
- * public API.
- *
- * To use these Symbol objects in your own component, include this module and
- * then create a property or method whose key is the desired Symbol.
- *
- * import 'SingleSelectionMixin' from 'basic-component-mixins/src/SingleSelectionMixin';
- * import 'symbols' from 'basic-component-mixins/src/symbols';
- *
- * class MyElement extends SingleSelectionMixin(HTMLElement) {
- * [symbols.itemSelected](item, selected) {
- * // This will be invoked whenever an item is selected/deselected.
- * }
- * }
- *
- * @module symbols
- */
-var symbols = {
-
- /**
- * Symbol for the `defaults` property.
- *
- * This property can be used to set or override defaults that will be applied
- * to a new component instance. When implementing this property, take care to
- * first acquire any defaults defined by the superclass. The standard idiom is
- * as follows:
- *
- * get [symbols.defaults]() {
- * const defaults = super[symbols.defaults] || {};
- * // Set or override default values here
- * defaults.customProperty = false;
- * return defaults;
- * }
- *
- * @var {object} defaults
- */
- defaults: (0, _createSymbol2.default)('defaults'),
-
- /**
- * Symbol for the `dragging` property.
- *
- * Components like carousels often define animated CSS transitions for
- * sliding effects. Such a transition should usually *not* be applied while
- * the user is dragging, because a CSS animation will introduce a lag that
- * makes the swipe feel sluggish. Instead, as long as the user is dragging
- * with their finger down, the transition should be suppressed. When the
- * user releases their finger, the transition can be restored, allowing the
- * animation to show the carousel sliding into its final position.
- *
- * @type {boolean} true if a drag is in progress, false if not.
- */
- dragging: (0, _createSymbol2.default)('dragging'),
-
- /**
- * Symbol for the `goDown` method.
- *
- * This method is invoked when the user wants to go/navigate down.
- *
- * @function goDown
- */
- goDown: (0, _createSymbol2.default)('goDown'),
-
- /**
- * Symbol for the `goEnd` method.
- *
- * This method is invoked when the user wants to go/navigate to the end (e.g.,
- * of a list).
- *
- * @function goEnd
- */
- goEnd: (0, _createSymbol2.default)('goEnd'),
-
- /**
- * Symbol for the `goLeft` method.
- *
- * This method is invoked when the user wants to go/navigate left.
- *
- * @function goLeft
- */
- goLeft: (0, _createSymbol2.default)('goLeft'),
-
- /**
- * Symbol for the `goRight` method.
- *
- * This method is invoked when the user wants to go/navigate right.
- *
- * @function goRight
- */
- goRight: (0, _createSymbol2.default)('goRight'),
-
- /**
- * Symbol for the `goStart` method.
- *
- * This method is invoked when the user wants to go/navigate to the start
- * (e.g., of a list).
- *
- * @function goStart
- */
- goStart: (0, _createSymbol2.default)('goStart'),
-
- /**
- * Symbol for the `goUp` method.
- *
- * This method is invoked when the user wants to go/navigate up.
- *
- * @function goUp
- */
- goUp: (0, _createSymbol2.default)('goUp'),
-
- /**
- * Symbol for the `itemAdded` method.
- *
- * This method is invoked when a new item is added to a list.
- *
- * @function itemAdded
- * @param {HTMLElement} item - the item being selected/deselected
- */
- itemAdded: (0, _createSymbol2.default)('itemAdded'),
-
- /**
- * Symbol for the `itemsChanged` method.
- *
- * This method is invoked when the underlying contents change. It is also
- * invoked on component initialization – since the items have "changed" from
- * being nothing.
- */
- itemsChanged: (0, _createSymbol2.default)('itemsChanged'),
-
- /**
- * Symbol for the `itemSelected` method.
- *
- * This method is invoked when an item becomes selected or deselected.
- *
- * @function itemSelected
- * @param {HTMLElement} item - the item being selected/deselected
- * @param {boolean} selected - true if the item is selected, false if not
- */
- itemSelected: (0, _createSymbol2.default)('itemSelected'),
-
- /**
- * Symbol for the `keydown` method.
- *
- * This method is invoked when an element receives a `keydown` event.
- *
- * @function keydown
- * @param {KeyboardEvent} event - the event being processed
- */
- keydown: (0, _createSymbol2.default)('keydown'),
-
- /**
- * Symbol for the `template` property.
- *
- * This property returns a component's template.
- *
- * @type {string|HTMLElement}
- */
- template: (0, _createSymbol2.default)('template')
-};
-
-exports.default = symbols;
-
-},{"./createSymbol":20}],24:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-exports.default = toggleClass;
-/**
- * Helper function for standard classList.toggle() behavior on old browsers,
- * namely IE 11.
- *
- * The standard
- * [classlist](https://developer.mozilla.org/en-US/docs/Web/API/Element/classList)
- * object has a `toggle()` function that supports a second Boolean parameter
- * that can be used to succinctly turn a class on or off. This feature is often
- * useful in designing custom elements, which may want to externally reflect
- * component state in a CSS class that can be used for styling purposes.
- *
- * Unfortunately, IE 11 does not support the Boolean parameter to
- * `classList.toggle()`. This helper function behaves like the standard
- * `toggle()`, including support for the Boolean parameter, so that it can be
- * used even on IE 11.
- *
- * @function toggleClass
- * @param {HTMLElement} element - The element to modify
- * @param {string} className - The class to add/remove
- * @param {boolean} [force] - Force the class to be added (if true) or removed
- * (if false)
- */
-function toggleClass(element, className, force) {
- var classList = element.classList;
- var addClass = typeof force === 'undefined' ? !classList.contains(className) : force;
- if (addClass) {
- classList.add(className);
- } else {
- classList.remove(className);
- }
- return addClass;
-}
-
-},{}],25:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _AttributeMarshallingMixin = require('../../basic-component-mixins/src/AttributeMarshallingMixin');
-
-var _AttributeMarshallingMixin2 = _interopRequireDefault(_AttributeMarshallingMixin);
-
-var _ComposableMixin = require('../../basic-component-mixins/src/ComposableMixin');
-
-var _ComposableMixin2 = _interopRequireDefault(_ComposableMixin);
-
-var _DistributedChildrenMixin = require('../../basic-component-mixins/src/DistributedChildrenMixin');
-
-var _DistributedChildrenMixin2 = _interopRequireDefault(_DistributedChildrenMixin);
-
-var _ShadowElementReferencesMixin = require('../../basic-component-mixins/src/ShadowElementReferencesMixin');
-
-var _ShadowElementReferencesMixin2 = _interopRequireDefault(_ShadowElementReferencesMixin);
-
-var _ShadowTemplateMixin = require('../../basic-component-mixins/src/ShadowTemplateMixin');
-
-var _ShadowTemplateMixin2 = _interopRequireDefault(_ShadowTemplateMixin);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-/**
- * A sample general-purpose base class for defining custom elements that mixes
- * in some common features: template stamping into a shadow root, shadow element
- * references, marshalling attributes to properties, and retrieving the children
- * distributed to a component.
- *
- * This base class is not special in any way, and is defined only as a
- * convenient shorthand for applying the mixins listed above. You can use this
- * class as a base class for your own elements, or easily create your own base
- * class by applying the same set of mixins.
- *
- * The ElementBase base class does not register itself as a custom element with
- * the browser, and hence cannot be independently instantiated.
- *
- * @mixes AttributeMarshallingMixin
- * @mixes ComposableMixin
- * @mixes DistributedChildrenMixin
- * @mixes ShadowElementReferencesMixin
- * @mixes ShadowTemplateMixin
- */
-var ElementBase = function (_ComposableMixin$comp) {
- _inherits(ElementBase, _ComposableMixin$comp);
-
- function ElementBase() {
- _classCallCheck(this, ElementBase);
-
- return _possibleConstructorReturn(this, (ElementBase.__proto__ || Object.getPrototypeOf(ElementBase)).apply(this, arguments));
- }
-
- return ElementBase;
-}((0, _ComposableMixin2.default)(HTMLElement).compose(_ShadowTemplateMixin2.default, // before node finding, so shadow root is populated
-_ShadowElementReferencesMixin2.default, // before marshalling, so properties can use refs
-_AttributeMarshallingMixin2.default, _DistributedChildrenMixin2.default));
-
-exports.default = ElementBase;
-
-},{"../../basic-component-mixins/src/AttributeMarshallingMixin":1,"../../basic-component-mixins/src/ComposableMixin":3,"../../basic-component-mixins/src/DistributedChildrenMixin":7,"../../basic-component-mixins/src/ShadowElementReferencesMixin":17,"../../basic-component-mixins/src/ShadowTemplateMixin":18}],26:[function(require,module,exports){
-'use strict';
-
-var _ListBox = require('./src/ListBox');
-
-var _ListBox2 = _interopRequireDefault(_ListBox);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-window.Basic = window.Basic || {}; /*
- * This file is transpiled to create an ES5-compatible distribution in which
- * the package's main feature(s) are available via the window.Basic global.
- * If you're already using ES6 yourself, ignore this file, and instead import
- * the source file(s) you want from the src folder.
- */
-
-window.Basic.ListBox = _ListBox2.default;
-
-},{"./src/ListBox":27}],27:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
-
-var _get = function get(object, property, receiver) { if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { return get(parent, property, receiver); } } else if ("value" in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } };
-
-var _ElementBase = require('../../basic-element-base/src/ElementBase');
-
-var _ElementBase2 = _interopRequireDefault(_ElementBase);
-
-var _DistributedChildrenContentMixin = require('../../basic-component-mixins/src/DistributedChildrenContentMixin');
-
-var _DistributedChildrenContentMixin2 = _interopRequireDefault(_DistributedChildrenContentMixin);
-
-var _ClickSelectionMixin = require('../../basic-component-mixins/src/ClickSelectionMixin');
-
-var _ClickSelectionMixin2 = _interopRequireDefault(_ClickSelectionMixin);
-
-var _ContentItemsMixin = require('../../basic-component-mixins/src/ContentItemsMixin');
-
-var _ContentItemsMixin2 = _interopRequireDefault(_ContentItemsMixin);
-
-var _DirectionSelectionMixin = require('../../basic-component-mixins/src/DirectionSelectionMixin');
-
-var _DirectionSelectionMixin2 = _interopRequireDefault(_DirectionSelectionMixin);
-
-var _GenericMixin = require('../../basic-component-mixins/src/GenericMixin');
-
-var _GenericMixin2 = _interopRequireDefault(_GenericMixin);
-
-var _KeyboardMixin = require('../../basic-component-mixins/src/KeyboardMixin');
-
-var _KeyboardMixin2 = _interopRequireDefault(_KeyboardMixin);
-
-var _KeyboardDirectionMixin = require('../../basic-component-mixins/src/KeyboardDirectionMixin');
-
-var _KeyboardDirectionMixin2 = _interopRequireDefault(_KeyboardDirectionMixin);
-
-var _KeyboardPagedSelectionMixin = require('../../basic-component-mixins/src/KeyboardPagedSelectionMixin');
-
-var _KeyboardPagedSelectionMixin2 = _interopRequireDefault(_KeyboardPagedSelectionMixin);
-
-var _KeyboardPrefixSelectionMixin = require('../../basic-component-mixins/src/KeyboardPrefixSelectionMixin');
-
-var _KeyboardPrefixSelectionMixin2 = _interopRequireDefault(_KeyboardPrefixSelectionMixin);
-
-var _SelectedItemTextValueMixin = require('../../basic-component-mixins/src/SelectedItemTextValueMixin');
-
-var _SelectedItemTextValueMixin2 = _interopRequireDefault(_SelectedItemTextValueMixin);
-
-var _SelectionAriaActiveMixin = require('../../basic-component-mixins/src/SelectionAriaActiveMixin');
-
-var _SelectionAriaActiveMixin2 = _interopRequireDefault(_SelectionAriaActiveMixin);
-
-var _SelectionHighlightMixin = require('../../basic-component-mixins/src/SelectionHighlightMixin');
-
-var _SelectionHighlightMixin2 = _interopRequireDefault(_SelectionHighlightMixin);
-
-var _SelectionInViewMixin = require('../../basic-component-mixins/src/SelectionInViewMixin');
-
-var _SelectionInViewMixin2 = _interopRequireDefault(_SelectionInViewMixin);
-
-var _SingleSelectionMixin = require('../../basic-component-mixins/src/SingleSelectionMixin');
-
-var _SingleSelectionMixin2 = _interopRequireDefault(_SingleSelectionMixin);
-
-var _symbols = require('../../basic-component-mixins/src/symbols');
-
-var _symbols2 = _interopRequireDefault(_symbols);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-/**
- * A single-selection list box that supports selection highlighting (using the
- * system highlight color) and keyboard navigation.
- *
- * [Live demo](http://basicwebcomponents.org/basic-web-components/packages/basic-list-box/)
- *
- * The user can select an item with the mouse/touch or keyboard: Up/Down, Page
- * Up/Down, Home/End.
- *
- * Like other Basic Web Components, this can handle distributed content: you can
- * include a content element inside a basic-list-box, and the list will navigate
- * through the distributed content.
- *
- * This component includes basic ARIA support to provide a reasonable default
- * experience, e.g., for screen readers. The list component itself will be
- * assigned an appropriate ARIA role (default is "listbox"). The ID of the
- * selected item will be reflected in an "aria-activedescendant" attribute
- * applied to the list. To support this feature, all items in the list need
- * unique IDs. If an item does not have an ID, basic-list-box will automatically
- * assign a default ID.
- *
- * The keyboard interaction model generally follows that of Microsoft Windows'
- * list boxes instead of those in OS X:
- *
- * * The Page Up/Down and Home/End keys actually move the selection, rather than
- * just scrolling the list. The former behavior seems more generally useful
- * for keyboard users.
- *
- * * Pressing Page Up/Down will move the selection to the topmost/bottommost
- * visible item if the selection is not already there. Thereafter, the key
- * will move the selection up/down by a page, and (per the above point) make
- * the selected item visible.
- *
- * Programmatically selecting an item (by setting the selected property) scrolls
- * the item into view.
- *
- * The user can also select an item by typing the beginning of an item's text.
- *
- * @extends ElementBase
- * @mixes ClickSelectionMixin
- * @mixes ContentItemsMixin
- * @mixes DirectionSelectionMixin
- * @mixes DistributedChildrenContentMixin
- * @mixes GenericMixin
- * @mixes KeyboardMixin
- * @mixes KeyboardDirectionMixin
- * @mixes KeyboardPagedSelectionMixin
- * @mixes KeyboardPrefixSelectionMixin
- * @mixis SelectedItemTextValueMixin
- * @mixes SelectionAriaActiveMixin
- * @mixes SelectionHighlightMixin
- * @mixes SelectionInViewMixin
- * @mixes SingleSelectionMixin
- */
-var ListBox = function (_ElementBase$compose) {
- _inherits(ListBox, _ElementBase$compose);
-
- function ListBox() {
- _classCallCheck(this, ListBox);
-
- return _possibleConstructorReturn(this, (ListBox.__proto__ || Object.getPrototypeOf(ListBox)).apply(this, arguments));
- }
-
- _createClass(ListBox, [{
- key: _symbols2.default.defaults,
- get: function get() {
- var defaults = _get(ListBox.prototype.__proto__ || Object.getPrototypeOf(ListBox.prototype), _symbols2.default.defaults, this) || {};
- defaults.navigationAxis = 'vertical';
- return defaults;
- }
- }, {
- key: 'scrollTarget',
- get: function get() {
- return this.$.itemsContainer;
- }
- }, {
- key: _symbols2.default.template,
- get: function get() {
- var baseTemplate = _get(ListBox.prototype.__proto__ || Object.getPrototypeOf(ListBox.prototype), _symbols2.default.template, this) || '';
- return '\n \n\n \n \n
\n ' + baseTemplate + '\n ';
- }
-
- /**
- * Fires when the list's value property changes.
- *
- * @memberof ListBox
- * @event value-changed
- */
-
- }]);
-
- return ListBox;
-}(_ElementBase2.default.compose(_ClickSelectionMixin2.default, _ContentItemsMixin2.default, _DirectionSelectionMixin2.default, _DistributedChildrenContentMixin2.default, _GenericMixin2.default, _KeyboardMixin2.default, _KeyboardDirectionMixin2.default, _KeyboardPagedSelectionMixin2.default, _KeyboardPrefixSelectionMixin2.default, _SelectedItemTextValueMixin2.default, _SelectionAriaActiveMixin2.default, _SelectionHighlightMixin2.default, _SelectionInViewMixin2.default, _SingleSelectionMixin2.default));
-
-customElements.define('basic-list-box', ListBox);
-exports.default = ListBox;
-
-},{"../../basic-component-mixins/src/ClickSelectionMixin":2,"../../basic-component-mixins/src/ContentItemsMixin":4,"../../basic-component-mixins/src/DirectionSelectionMixin":5,"../../basic-component-mixins/src/DistributedChildrenContentMixin":6,"../../basic-component-mixins/src/GenericMixin":8,"../../basic-component-mixins/src/KeyboardDirectionMixin":9,"../../basic-component-mixins/src/KeyboardMixin":10,"../../basic-component-mixins/src/KeyboardPagedSelectionMixin":11,"../../basic-component-mixins/src/KeyboardPrefixSelectionMixin":12,"../../basic-component-mixins/src/SelectedItemTextValueMixin":13,"../../basic-component-mixins/src/SelectionAriaActiveMixin":14,"../../basic-component-mixins/src/SelectionHighlightMixin":15,"../../basic-component-mixins/src/SelectionInViewMixin":16,"../../basic-component-mixins/src/SingleSelectionMixin":19,"../../basic-component-mixins/src/symbols":23,"../../basic-element-base/src/ElementBase":25}]},{},[26])
-//# sourceMappingURL=data:application/json;charset:utf-8;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbIm5vZGVfbW9kdWxlcy9ncnVudC1icm93c2VyaWZ5L25vZGVfbW9kdWxlcy9icm93c2VyLXBhY2svX3ByZWx1ZGUuanMiLCJwYWNrYWdlcy9iYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy9BdHRyaWJ1dGVNYXJzaGFsbGluZ01peGluLmpzIiwicGFja2FnZXMvYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvQ2xpY2tTZWxlY3Rpb25NaXhpbi5qcyIsInBhY2thZ2VzL2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL0NvbXBvc2FibGVNaXhpbi5qcyIsInBhY2thZ2VzL2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL0NvbnRlbnRJdGVtc01peGluLmpzIiwicGFja2FnZXMvYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvRGlyZWN0aW9uU2VsZWN0aW9uTWl4aW4uanMiLCJwYWNrYWdlcy9iYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy9EaXN0cmlidXRlZENoaWxkcmVuQ29udGVudE1peGluLmpzIiwicGFja2FnZXMvYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvRGlzdHJpYnV0ZWRDaGlsZHJlbk1peGluLmpzIiwicGFja2FnZXMvYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvR2VuZXJpY01peGluLmpzIiwicGFja2FnZXMvYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvS2V5Ym9hcmREaXJlY3Rpb25NaXhpbi5qcyIsInBhY2thZ2VzL2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL0tleWJvYXJkTWl4aW4uanMiLCJwYWNrYWdlcy9iYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy9LZXlib2FyZFBhZ2VkU2VsZWN0aW9uTWl4aW4uanMiLCJwYWNrYWdlcy9iYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy9LZXlib2FyZFByZWZpeFNlbGVjdGlvbk1peGluLmpzIiwicGFja2FnZXMvYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvU2VsZWN0ZWRJdGVtVGV4dFZhbHVlTWl4aW4uanMiLCJwYWNrYWdlcy9iYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy9TZWxlY3Rpb25BcmlhQWN0aXZlTWl4aW4uanMiLCJwYWNrYWdlcy9iYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy9TZWxlY3Rpb25IaWdobGlnaHRNaXhpbi5qcyIsInBhY2thZ2VzL2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL1NlbGVjdGlvbkluVmlld01peGluLmpzIiwicGFja2FnZXMvYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvU2hhZG93RWxlbWVudFJlZmVyZW5jZXNNaXhpbi5qcyIsInBhY2thZ2VzL2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL1NoYWRvd1RlbXBsYXRlTWl4aW4uanMiLCJwYWNrYWdlcy9iYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy9TaW5nbGVTZWxlY3Rpb25NaXhpbi5qcyIsInBhY2thZ2VzL2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL2NyZWF0ZVN5bWJvbC5qcyIsInBhY2thZ2VzL2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL21pY3JvdGFzay5qcyIsInBhY2thZ2VzL2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL3NhZmVBdHRyaWJ1dGVzLmpzIiwicGFja2FnZXMvYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvc3ltYm9scy5qcyIsInBhY2thZ2VzL2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL3RvZ2dsZUNsYXNzLmpzIiwicGFja2FnZXMvYmFzaWMtZWxlbWVudC1iYXNlL3NyYy9FbGVtZW50QmFzZS5qcyIsInBhY2thZ2VzL2Jhc2ljLWxpc3QtYm94L2dsb2JhbHMuanMiLCJwYWNrYWdlcy9iYXNpYy1saXN0LWJveC9zcmMvTGlzdEJveC5qcyJdLCJuYW1lcyI6W10sIm1hcHBpbmdzIjoiQUFBQTs7Ozs7Ozs7Ozs7QUNBQTs7Ozs7Ozs7Ozs7O0FBR0E7QUFDQSxJQUFNLDJCQUEyQixFQUFqQztBQUNBLElBQU0sNEJBQTRCLEVB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O0FBQ0E7Ozs7QUFDQTs7OztBQUNBOzs7O0FBQ0E7Ozs7QUFDQTs7OztBQUNBOzs7O0FBQ0E7Ozs7QUFDQTs7OztBQUNBOzs7O0FBQ0E7Ozs7QUFDQTs7OztBQUNBOzs7O0FBQ0E7Ozs7Ozs7Ozs7OztBQUdBOzs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7SUFzRE0sTzs7Ozs7Ozs7OztTQWlCQyxrQkFBUSxRO3dCQUFZO0FBQ3ZCLFVBQU0sV0FBVyw4RUFBTSxrQkFBUSxRQUFkLFdBQTJCLEVBQTVDO0FBQ0EsZUFBUyxjQUFULEdBQTBCLFVBQTFCO0FBQ0EsYUFBTyxRQUFQO0FBQ0Q7Ozt3QkFFa0I7QUFDakIsYUFBTyxLQUFLLENBQUwsQ0FBTyxjQUFkO0FBQ0Q7O1NBRUksa0JBQVEsUTt3QkFBWTtBQUN2QixVQUFNLGVBQWUsOEVBQU0sa0JBQVEsUUFBZCxXQUEyQixFQUFoRDtBQUNBLHUvQkEwQ0ksWUExQ0o7QUE0Q0Q7O0FBRUQ7Ozs7Ozs7Ozs7RUEzRW9CLHNCQUFZLE9BQVoseWQ7O0FBb0Z0QixlQUFlLE1BQWYsQ0FBc0IsZ0JBQXRCLEVBQXdDLE9BQXhDO2tCQUNlLE8iLCJmaWxlIjoiZ2VuZXJhdGVkLmpzIiwic291cmNlUm9vdCI6IiIsInNvdXJjZXNDb250ZW50IjpbIihmdW5jdGlvbiBlKHQsbixyKXtmdW5jdGlvbiBzKG8sdSl7aWYoIW5bb10pe2lmKCF0W29dKXt2YXIgYT10eXBlb2YgcmVxdWlyZT09XCJmdW5jdGlvblwiJiZyZXF1aXJlO2lmKCF1JiZhKXJldHVybiBhKG8sITApO2lmKGkpcmV0dXJuIGkobywhMCk7dmFyIGY9bmV3IEVycm9yKFwiQ2Fubm90IGZpbmQgbW9kdWxlICdcIitvK1wiJ1wiKTt0aHJvdyBmLmNvZGU9XCJNT0RVTEVfTk9UX0ZPVU5EXCIsZn12YXIgbD1uW29dPXtleHBvcnRzOnt9fTt0W29dWzBdLmNhbGwobC5leHBvcnRzLGZ1bmN0aW9uKGUpe3ZhciBuPXRbb11bMV1bZV07cmV0dXJuIHMobj9uOmUpfSxsLGwuZXhwb3J0cyxlLHQsbixyKX1yZXR1cm4gbltvXS5leHBvcnRzfXZhciBpPXR5cGVvZiByZXF1aXJlPT1cImZ1bmN0aW9uXCImJnJlcXVpcmU7Zm9yKHZhciBvPTA7bzxyLmxlbmd0aDtvKyspcyhyW29dKTtyZXR1cm4gc30pIiwiaW1wb3J0IHNhZmVBdHRyaWJ1dGVzIGZyb20gJy4vc2FmZUF0dHJpYnV0ZXMnO1xuXG5cbi8vIE1lbW9pemVkIG1hcHMgb2YgYXR0cmlidXRlIHRvIHByb3BlcnR5IG5hbWVzIGFuZCB2aWNlIHZlcnNhLlxuY29uc3QgYXR0cmlidXRlVG9Qcm9wZXJ0eU5hbWVzID0ge307XG5jb25zdCBwcm9wZXJ0eU5hbWVzVG9BdHRyaWJ1dGVzID0ge307XG5cblxuLyogRXhwb3J0ZWQgZnVuY3Rpb24gZXh0ZW5kcyBhIGJhc2UgY2xhc3Mgd2l0aCBBdHRyaWJ1dGVNYXJzaGFsbGluZy4gKi9cbmV4cG9ydCBkZWZhdWx0IChiYXNlKSA9PiB7XG5cbiAgLyoqXG4gICAqIE1peGluIHdoaWNoIG1hcnNoYWxscyBhdHRyaWJ1dGVzIHRvIHByb3BlcnRpZXMgYW5kIHZpY2UgdmVyc2EuXG4gICAqXG4gICAqIElmIHlvdXIgY29tcG9uZW50IGV4cG9zZXMgYSBzZXR0ZXIgZm9yIGEgcHJvcGVydHksIGl0J3MgZ2VuZXJhbGx5IGEgZ29vZFxuICAgKiBpZGVhIHRvIGxldCBkZXZzIHVzaW5nIHlvdXIgY29tcG9uZW50IGJlIGFibGUgdG8gc2V0IHRoYXQgcHJvcGVydHkgaW4gSFRNTFxuICAgKiB2aWEgYW4gZWxlbWVudCBhdHRyaWJ1dGUuIFlvdSBjYW4gY29kZSB0aGF0IHlvdXJzZWxmIGJ5IHdyaXRpbmcgYW5cbiAgICogYGF0dHJpYnV0ZUNoYW5nZWRDYWxsYmFja2AsIG9yIHlvdSBjYW4gdXNlIHRoaXMgbWl4aW4gdG8gZ2V0IGEgZGVncmVlIG9mXG4gICAqIGF1dG9tYXRpYyBzdXBwb3J0LlxuICAgKlxuICAgKiBUaGlzIG1peGluIGltcGxlbWVudHMgYW4gYGF0dHJpYnV0ZUNoYW5nZWRDYWxsYmFja2AgdGhhdCB3aWxsIGF0dGVtcHQgdG9cbiAgICogY29udmVydCBhIGNoYW5nZSBpbiBhbiBlbGVtZW50IGF0dHJpYnV0ZSBpbnRvIGEgY2FsbCB0byB0aGUgY29ycmVzcG9uZGluZ1xuICAgKiBwcm9wZXJ0eSBzZXR0ZXIuIEF0dHJpYnV0ZXMgdHlwaWNhbGx5IGZvbGxvdyBoeXBoZW5hdGVkIG5hbWVzIChcImZvby1iYXJcIiksXG4gICAqIHdoZXJlYXMgcHJvcGVydGllcyB0eXBpY2FsbHkgdXNlIGNhbWVsQ2FzZSBuYW1lcyAoXCJmb29CYXJcIikuIFRoaXMgbWl4aW5cbiAgICogcmVzcGVjdHMgdGhhdCBjb252ZW50aW9uLCBhdXRvbWF0aWNhbGx5IG1hcHBpbmcgdGhlIGh5cGhlbmF0ZWQgYXR0cmlidXRlXG4gICAqIG5hbWUgdG8gdGhlIGNvcnJlc3BvbmRpbmcgY2FtZWxDYXNlIHByb3BlcnR5IG5hbWUuXG4gICAqXG4gICAqIEV4YW1wbGU6IFlvdSBkZWZpbmUgYSBjb21wb25lbnQgdXNpbmcgdGhpcyBtaXhpbjpcbiAgICpcbiAgICogICAgIGNsYXNzIE15RWxlbWVudCBleHRlbmRzIEF0dHJpYnV0ZU1hcnNoYWxsaW5nTWl4aW4oSFRNTEVsZW1lbnQpIHtcbiAgICogICAgICAgZ2V0IGZvb0JhcigpIHsgcmV0dXJuIHRoaXMuX2Zvb0JhcjsgfVxuICAgKiAgICAgICBzZXQgZm9vQmFyKHZhbHVlKSB7IHRoaXMuX2Zvb0JhciA9IHZhbHVlOyB9XG4gICAqICAgICB9XG4gICAqICAgICBjdXN0b21FbGVtZW50cy5kZWZpbmUoJ215LWVsZW1lbnQnLCBNeUVsZW1lbnQpO1xuICAgKlxuICAgKiBJZiBzb21lb25lIHRoZW4gaW5zdGFudGlhdGVzIHlvdXIgY29tcG9uZW50IGluIEhUTUw6XG4gICAqXG4gICAqICAgICA8bXktZWxlbWVudCBmb28tYmFyPVwiSGVsbG9cIj48L215LWVsZW1lbnQ+XG4gICAqXG4gICAqIFRoZW4sIGFmdGVyIHRoZSBlbGVtZW50IGhhcyBiZWVuIHVwZ3JhZGVkLCB0aGUgYGZvb0JhcmAgc2V0dGVyIHdpbGxcbiAgICogYXV0b21hdGljYWxseSBiZSBpbnZva2VkIHdpdGggdGhlIGluaXRpYWwgdmFsdWUgXCJIZWxsb1wiLlxuICAgKlxuICAgKiBGb3IgdGhlIHRpbWUgYmVpbmcsIHRoaXMgbWl4aW4gb25seSBzdXBwb3J0cyBzdHJpbmctdmFsdWVkIHByb3BlcnRpZXMuXG4gICAqIElmIHlvdSdkIGxpa2UgdG8gY29udmVydCBzdHJpbmcgYXR0cmlidXRlcyB0byBvdGhlciB0eXBlcyAobnVtYmVycyxcbiAgICogYm9vbGVhbnMpLCB5b3UgbmVlZCB0byBpbXBsZW1lbnQgYGF0dHJpYnV0ZUNoYW5nZWRDYWxsYmFja2AgeW91cnNlbGYuXG4gICAqL1xuICBjbGFzcyBBdHRyaWJ1dGVNYXJzaGFsbGluZyBleHRlbmRzIGJhc2Uge1xuXG4gICAgLypcbiAgICAgKiBIYW5kbGUgYSBjaGFuZ2UgdG8gdGhlIGF0dHJpYnV0ZSB3aXRoIHRoZSBnaXZlbiBuYW1lLlxuICAgICAqL1xuICAgIGF0dHJpYnV0ZUNoYW5nZWRDYWxsYmFjayhhdHRyaWJ1dGVOYW1lLCBvbGRWYWx1ZSwgbmV3VmFsdWUpIHtcbiAgICAgIGlmIChzdXBlci5hdHRyaWJ1dGVDaGFuZ2VkQ2FsbGJhY2spIHsgc3VwZXIuYXR0cmlidXRlQ2hhbmdlZENhbGxiYWNrKCk7IH1cbiAgICAgIGNvbnN0IHByb3BlcnR5TmFtZSA9IGF0dHJpYnV0ZVRvUHJvcGVydHlOYW1lKGF0dHJpYnV0ZU5hbWUpO1xuICAgICAgLy8gSWYgdGhlIGF0dHJpYnV0ZSBuYW1lIGNvcnJlc3BvbmRzIHRvIGEgcHJvcGVydHkgbmFtZSwgc2V0IHRoZSBwcm9wZXJ0eS5cbiAgICAgIC8vIElnbm9yZSBzdGFuZGFyZCBIVE1MRWxlbWVudCBwcm9wZXJ0aWVzIGhhbmRsZWQgYnkgdGhlIERPTS5cbiAgICAgIGlmIChwcm9wZXJ0eU5hbWUgaW4gdGhpcyAmJiAhKHByb3BlcnR5TmFtZSBpbiBIVE1MRWxlbWVudC5wcm90b3R5cGUpKSB7XG4gICAgICAgIHRoaXNbcHJvcGVydHlOYW1lXSA9IG5ld1ZhbHVlO1xuICAgICAgfVxuICAgIH1cblxuICAgIGNvbm5lY3RlZENhbGxiYWNrKCkge1xuICAgICAgaWYgKHN1cGVyLmNvbm5lY3RlZENhbGxiYWNrKSB7IHN1cGVyLmNvbm5lY3RlZENhbGxiYWNrKCk7IH1cbiAgICAgIHNhZmVBdHRyaWJ1dGVzLmNvbm5lY3RlZCh0aGlzKTtcbiAgICB9XG5cbiAgICBzdGF0aWMgZ2V0IG9ic2VydmVkQXR0cmlidXRlcygpIHtcbiAgICAgIHJldHVybiBhdHRyaWJ1dGVzRm9yQ2xhc3ModGhpcyk7XG4gICAgfVxuXG4gICAgLyoqXG4gICAgICogU2V0L3Vuc2V0IHRoZSBhdHRyaWJ1dGUgd2l0aCB0aGUgaW5kaWNhdGVkIG5hbWUuXG4gICAgICpcbiAgICAgKiBUaGlzIG1ldGhvZCBleGlzdHMgcHJpbWFyaWx5IHRvIGhhbmRsZSB0aGUgY2FzZSB3aGVyZSBhbiBlbGVtZW50IHdhbnRzIHRvXG4gICAgICogc2V0IGEgZGVmYXVsdCBwcm9wZXJ0eSB2YWx1ZSB0aGF0IHNob3VsZCBiZSByZWZsZWN0ZWQgYXMgYW4gYXR0cmlidXRlLiBBblxuICAgICAqIGltcG9ydGFudCBsaW1pdGF0aW9uIG9mIGN1c3RvbSBlbGVtZW50IGNvbnN0dXJjdG9ycyBpcyB0aGF0IHRoZXkgY2Fubm90XG4gICAgICogc2V0IGF0dHJpYnV0ZXMuIEEgY2FsbCB0byBgcmVmbGVjdEF0dHJpYnV0ZWAgZHVyaW5nIHRoZSBjb25zdHJ1Y3RvciB3aWxsXG4gICAgICogYmUgZGVmZXJyZWQgdW50aWwgdGhlIGVsZW1lbnQgaXMgY29ubmVjdGVkIHRvIHRoZSBkb2N1bWVudC5cbiAgICAgKlxuICAgICAqIEBwYXJhbSB7c3RyaW5nfSBhdHRyaWJ1dGUgLSBUaGUgbmFtZSBvZiB0aGUgKmF0dHJpYnV0ZSogKG5vdCBwcm9wZXJ0eSkgdG8gc2V0LlxuICAgICAqIEBwYXJhbSB7b2JqZWN0fSB2YWx1ZSAtIFRoZSB2YWx1ZSB0byBzZXQuIElmIG51bGwsIHRoZSBhdHRyaWJ1dGUgd2lsbCBiZSByZW1vdmVkLlxuICAgICAqL1xuICAgIHJlZmxlY3RBdHRyaWJ1dGUoYXR0cmlidXRlLCB2YWx1ZSkge1xuICAgICAgcmV0dXJuIHNhZmVBdHRyaWJ1dGVzLnNldEF0dHJpYnV0ZSh0aGlzLCBhdHRyaWJ1dGUsIHZhbHVlKTtcbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBTZXQvdW5zZXQgdGhlIGNsYXNzIHdpdGggdGhlIGluZGljYXRlZCBuYW1lLlxuICAgICAqXG4gICAgICogVGhpcyBtZXRob2QgZXhpc3RzIHByaW1hcmlseSB0byBoYW5kbGUgdGhlIGNhc2Ugd2hlcmUgYW4gZWxlbWVudCB3YW50cyB0b1xuICAgICAqIHNldCBhIGRlZmF1bHQgcHJvcGVydHkgdmFsdWUgdGhhdCBzaG91bGQgYmUgcmVmbGVjdGVkIGFzIGFzIGNsYXNzLiBBblxuICAgICAqIGltcG9ydGFudCBsaW1pdGF0aW9uIG9mIGN1c3RvbSBlbGVtZW50IGNvbnN0dXJjdG9ycyBpcyB0aGF0IHRoZXkgY2Fubm90XG4gICAgICogc2V0IGF0dHJpYnV0ZXMsIGluY2x1ZGluZyB0aGUgYGNsYXNzYCBhdHRyaWJ1dGUuIEEgY2FsbCB0b1xuICAgICAqIGByZWZsZWN0Q2xhc3NgIGR1cmluZyB0aGUgY29uc3RydWN0b3Igd2lsbCBiZSBkZWZlcnJlZCB1bnRpbCB0aGUgZWxlbWVudFxuICAgICAqIGlzIGNvbm5lY3RlZCB0byB0aGUgZG9jdW1lbnQuXG4gICAgICpcbiAgICAgKiBAcGFyYW0ge3N0cmluZ30gY2xhc3NOYW1lIC0gVGhlIG5hbWUgb2YgdGhlIGNsYXNzIHRvIHNldC5cbiAgICAgKiBAcGFyYW0ge29iamVjdH0gdmFsdWUgLSBUcnVlIHRvIHNldCB0aGUgY2xhc3MsIGZhbHNlIHRvIHJlbW92ZSBpdC5cbiAgICAgKi9cbiAgICByZWZsZWN0Q2xhc3MoY2xhc3NOYW1lLCB2YWx1ZSkge1xuICAgICAgcmV0dXJuIHNhZmVBdHRyaWJ1dGVzLnRvZ2dsZUNsYXNzKHRoaXMsIGNsYXNzTmFtZSwgdmFsdWUpO1xuICAgIH1cblxuICB9XG5cbiAgcmV0dXJuIEF0dHJpYnV0ZU1hcnNoYWxsaW5nO1xufTtcblxuXG4vLyBDb252ZXJ0IGh5cGhlbmF0ZWQgZm9vLWJhciBhdHRyaWJ1dGUgbmFtZSB0byBjYW1lbCBjYXNlIGZvb0JhciBwcm9wZXJ0eSBuYW1lLlxuZnVuY3Rpb24gYXR0cmlidXRlVG9Qcm9wZXJ0eU5hbWUoYXR0cmlidXRlTmFtZSkge1xuICBsZXQgcHJvcGVydHlOYW1lID0gYXR0cmlidXRlVG9Qcm9wZXJ0eU5hbWVzW2F0dHJpYnV0ZU5hbWVdO1xuICBpZiAoIXByb3BlcnR5TmFtZSkge1xuICAgIC8vIENvbnZlcnQgYW5kIG1lbW9pemUuXG4gICAgY29uc3QgaHlwZW5SZWdFeCA9IC8tKFthLXpdKS9nO1xuICAgIHByb3BlcnR5TmFtZSA9IGF0dHJpYnV0ZU5hbWUucmVwbGFjZShoeXBlblJlZ0V4LFxuICAgICAgICBtYXRjaCA9PiBtYXRjaFsxXS50b1VwcGVyQ2FzZSgpKTtcbiAgICBhdHRyaWJ1dGVUb1Byb3BlcnR5TmFtZXNbYXR0cmlidXRlTmFtZV0gPSBwcm9wZXJ0eU5hbWU7XG4gIH1cbiAgcmV0dXJuIHByb3BlcnR5TmFtZTtcbn1cblxuZnVuY3Rpb24gYXR0cmlidXRlc0ZvckNsYXNzKGNsYXNzRm4pIHtcblxuICAvLyBXZSB0cmVhdCB0aGUgZWxlbWVudCBiYXNlIGNsYXNzZXMgYXMgaWYgdGhleSBoYXZlIG5vIGF0dHJpYnV0ZXMsIHNpbmNlIHdlXG4gIC8vIGRvbid0IHdhbnQgdG8gcmVjZWl2ZSBhdHRyaWJ1dGVDaGFuZ2VkQ2FsbGJhY2sgZm9yIHRoZW0uXG4gIGlmIChjbGFzc0ZuID09PSBIVE1MRWxlbWVudCB8fCBjbGFzc0ZuID09PSBPYmplY3QpIHtcbiAgICByZXR1cm4gW107XG4gIH1cblxuICAvLyBHZXQgYXR0cmlidXRlcyBmb3IgcGFyZW50IGNsYXNzLlxuICBjb25zdCBiYXNlQ2xhc3MgPSBPYmplY3QuZ2V0UHJvdG90eXBlT2YoY2xhc3NGbi5wcm90b3R5cGUpLmNvbnN0cnVjdG9yO1xuICBjb25zdCBiYXNlQXR0cmlidXRlcyA9IGF0dHJpYnV0ZXNGb3JDbGFzcyhiYXNlQ2xhc3MpO1xuXG4gIC8vIEdldCBhdHRyaWJ1dGVzIGZvciB0aGlzIGNsYXNzLlxuICBjb25zdCBwcm9wZXJ0eU5hbWVzID0gT2JqZWN0LmdldE93blByb3BlcnR5TmFtZXMoY2xhc3NGbi5wcm90b3R5cGUpO1xuICBjb25zdCBzZXR0ZXJOYW1lcyA9IHByb3BlcnR5TmFtZXMuZmlsdGVyKHByb3BlcnR5TmFtZSA9PlxuICAgIHR5cGVvZiBPYmplY3QuZ2V0T3duUHJvcGVydHlEZXNjcmlwdG9yKFxuICAgICAgICBjbGFzc0ZuLnByb3RvdHlwZSwgcHJvcGVydHlOYW1lKS5zZXQgPT09ICdmdW5jdGlvbicpO1xuICBjb25zdCBhdHRyaWJ1dGVzID0gc2V0dGVyTmFtZXMubWFwKHNldHRlck5hbWUgPT5cbiAgICAgIHByb3BlcnR5TmFtZVRvQXR0cmlidXRlKHNldHRlck5hbWUpKTtcblxuICAvLyBNZXJnZS5cbiAgY29uc3QgZGlmZiA9IGF0dHJpYnV0ZXMuZmlsdGVyKGF0dHJpYnV0ZSA9PlxuICAgICAgYmFzZUF0dHJpYnV0ZXMuaW5kZXhPZihhdHRyaWJ1dGUpIDwgMCk7XG4gIHJldHVybiBiYXNlQXR0cmlidXRlcy5jb25jYXQoZGlmZik7XG59XG5cbi8vIENvbnZlcnQgYSBjYW1lbCBjYXNlIGZvb0JhciBwcm9wZXJ0eSBuYW1lIHRvIGEgaHlwaGVuYXRlZCBmb28tYmFyIGF0dHJpYnV0ZS5cbmZ1bmN0aW9uIHByb3BlcnR5TmFtZVRvQXR0cmlidXRlKHByb3BlcnR5TmFtZSkge1xuICBsZXQgYXR0cmlidXRlID0gcHJvcGVydHlOYW1lc1RvQXR0cmlidXRlc1twcm9wZXJ0eU5hbWVdO1xuICBpZiAoIWF0dHJpYnV0ZSkge1xuICAgIC8vIENvbnZlcnQgYW5kIG1lbW9pemUuXG4gICAgY29uc3QgdXBwZXJjYXNlUmVnRXggPSAvKFtBLVpdKS9nO1xuICAgIGF0dHJpYnV0ZSA9IHByb3BlcnR5TmFtZS5yZXBsYWNlKHVwcGVyY2FzZVJlZ0V4LCAnLSQxJykudG9Mb3dlckNhc2UoKTtcbiAgfVxuICByZXR1cm4gYXR0cmlidXRlO1xufVxuIiwiLyogRXhwb3J0ZWQgZnVuY3Rpb24gZXh0ZW5kcyBhIGJhc2UgY2xhc3Mgd2l0aCBDbGlja1NlbGVjdGlvbi4gKi9cbmV4cG9ydCBkZWZhdWx0IChiYXNlKSA9PiB7XG5cbiAgLyoqXG4gICAqIE1peGluIHdoaWNoIG1hcHMgYSBjbGljayAoYWN0dWFsbHksIGEgbW91c2Vkb3duKSB0byBhIHNlbGVjdGlvbi5cbiAgICpcbiAgICogVGhpcyBzaW1wbGUgbWl4aW4gaXMgdXNlZnVsIGluIGxpc3QgYm94LWxpa2UgZWxlbWVudHMsIHdoZXJlIGEgY2xpY2sgb24gYVxuICAgKiBsaXN0IGl0ZW0gaW1wbGljaXRseSBzZWxlY3RzIGl0LlxuICAgKlxuICAgKiBUaGlzIG1peGluIGV4cGVjdHMgdGhlIGNvbXBvbmVudCB0byBwcm92aWRlIGFuIGBpdGVtc2AgcHJvcGVydHkuIFlvdSBjYW5cbiAgICogcHJvdmlkZSB0aGF0IHByb3BlcnR5IHlvdXJzZWxmLCBvciB1c2VcbiAgICogW0NvbnRlbnRJdGVtc01peGluXShDb250ZW50SXRlbXNNaXhpbi5tZCkuIFRoaXMgbWl4aW4gYWxzbyBleHBlY3RzIHRoZVxuICAgKiBjb21wb25lbnQgdG8gZGVmaW5lIGEgYHNlbGVjdGVkSW5kZXhgIHByb3BlcnR5LiBZb3UgY2FuIHByb3ZpZGUgdGhhdFxuICAgKiB5b3Vyc2VsZiwgb3IgdXNlIFtTaW5nbGVTZWxlY3Rpb25NaXhpbl0oU2luZ2xlU2VsZWN0aW9uTWl4aW4ubWQpLlxuICAgKi9cbiAgY2xhc3MgQ2xpY2tTZWxlY3Rpb24gZXh0ZW5kcyBiYXNlIHtcblxuICAgIGNvbnN0cnVjdG9yKCkge1xuICAgICAgc3VwZXIoKTtcbiAgICAgIC8qXG4gICAgICAgKiBSRVZJRVc6IFdoaWNoIGV2ZW50IHNob3VsZCB3ZSBsaXN0ZW4gdG8gaGVyZT9cbiAgICAgICAqXG4gICAgICAgKiBUaGUgc3RhbmRhcmQgdXNlIGZvciB0aGlzIG1peGluIGlzIGluIGxpc3QgYm94ZXMuIExpc3QgYm94ZXMgZG9uJ3RcbiAgICAgICAqIGFwcGVhciB0byBiZSBjb25zaXN0ZW50IHdpdGggcmVnYXJkIHRvIHdoZXRoZXIgdGhleSBzZWxlY3Qgb24gbW91c2Vkb3duXG4gICAgICAgKiBvciBjbGljay9tb3VzZXVwLlxuICAgICAgICovXG4gICAgICB0aGlzLmFkZEV2ZW50TGlzdGVuZXIoJ21vdXNlZG93bicsIGV2ZW50ID0+IHtcbiAgICAgICAgLy8gSEFDSzogSWYgdGhlIGl0ZW0gaXMgYSBidXR0b24sIHRoZSBldmVudCBzZWVtcyB0byBiZSByYWlzZWQgaW5cbiAgICAgICAgLy8gcGhhc2UgMiAoQVRfVEFSR0VUKSwgYnV0IHRoZSB0YXJnZXQgaXMgdGhlIGNvbXBvbmVudCwgbm90IGl0ZW0uXG4gICAgICAgIC8vIE5lZWQgdG8gaW52ZXNpZ2F0ZS5cbiAgICAgICAgY29uc3QgdGFyZ2V0ID0gZXZlbnQudGFyZ2V0ID09PSB0aGlzID9cbiAgICAgICAgICBldmVudC5wYXRoWzBdIDpcbiAgICAgICAgICBldmVudC50YXJnZXQ7XG4gICAgICAgIGNvbnN0IGluZGV4ID0gaW5kZXhPZkNvbnRhaW5pbmdJdGVtKHRoaXMsIHRhcmdldCk7XG4gICAgICAgIGlmIChpbmRleCA+PSAwKSB7XG4gICAgICAgICAgdGhpcy5zZWxlY3RlZEluZGV4ID0gaW5kZXg7XG4gICAgICAgICAgLy8gTm90ZTogV2UgZG9uJ3QgY2FsbCBwcmV2ZW50RGVmYXVsdCBoZXJlLiBUaGUgZGVmYXVsdCBiZWhhdmlvciBmb3JcbiAgICAgICAgICAvLyBtb3VzZWRvd24gaW5jbHVkZXMgc2V0dGluZyBrZXlib2FyZCBmb2N1cyBpZiB0aGUgZWxlbWVudCBkb2Vzbid0XG4gICAgICAgICAgLy8gYWxyZWFkeSBoYXZlIHRoZSBmb2N1cywgYW5kIHdlIHdhbnQgdG8gcHJlc2VydmUgdGhhdCBiZWhhdmlvci5cbiAgICAgICAgICBldmVudC5zdG9wUHJvcGFnYXRpb24oKTtcbiAgICAgICAgfVxuICAgICAgfSk7XG4gICAgfVxuXG4gICAgLy8gRGVmYXVsdCBpbXBsZW1lbnRhdGlvbi4gVGhpcyB3aWxsIHR5cGljYWxseSBiZSBoYW5kbGVkIGJ5IG90aGVyIG1peGlucy5cbiAgICBnZXQgc2VsZWN0ZWRJbmRleCgpIHtcbiAgICAgIHJldHVybiBzdXBlci5zZWxlY3RlZEluZGV4O1xuICAgIH1cbiAgICBzZXQgc2VsZWN0ZWRJbmRleChpbmRleCkge1xuICAgICAgaWYgKCdzZWxlY3RlZEluZGV4JyBpbiBiYXNlLnByb3RvdHlwZSkgeyBzdXBlci5zZWxlY3RlZEluZGV4ID0gaW5kZXg7IH1cbiAgICB9XG5cbiAgfVxuXG4gIHJldHVybiBDbGlja1NlbGVjdGlvbjtcbn07XG5cblxuLypcbiAqIFJldHVybiBpbmRleCBvZiB0aGUgZWxlbWVudCBpdGVtcyB0aGF0IGVpdGhlciBpcyBvciBjb250YWlucyB0aGUgaW5kaWNhdGVkXG4gKiB0YXJnZXQuIFJldHVybiAtMSBpZiBub3QgZm91bmQuXG4gKi9cbmZ1bmN0aW9uIGluZGV4T2ZDb250YWluaW5nSXRlbShlbGVtZW50LCB0YXJnZXQpIHtcbiAgY29uc3QgaXRlbXMgPSBlbGVtZW50Lml0ZW1zO1xuICBjb25zdCBpdGVtQ291bnQgPSBpdGVtcyA/IGl0ZW1zLmxlbmd0aCA6IDA7XG4gIGZvciAobGV0IGkgPSAwOyBpIDwgaXRlbUNvdW50OyBpKyspIHtcbiAgICBsZXQgaXRlbSA9IGl0ZW1zW2ldO1xuICAgIGlmIChpdGVtID09PSB0YXJnZXQgfHwgaXRlbS5jb250YWlucyh0YXJnZXQpKSB7XG4gICAgICByZXR1cm4gaTtcbiAgICB9XG4gIH1cbiAgcmV0dXJuIC0xO1xufVxuIiwiLyogRXhwb3J0ZWQgZnVuY3Rpb24gZXh0ZW5kcyBhIGJhc2UgY2xhc3Mgd2l0aCBDb21wb3NhYmxlLiAqL1xuZXhwb3J0IGRlZmF1bHQgKGJhc2UpID0+IHtcblxuICAvKipcbiAgICogTWl4aW4gdG8gbWFrZSBhIGNsYXNzIG1vcmUgZWFzaWx5IGNvbXBvc2FibGUgd2l0aCBvdGhlciBtaXhpbnMuXG4gICAqXG4gICAqIFRoaXMgbWl4aW4gY29udHJpYnV0ZXMgYSBgY29tcG9zZWAgbWV0aG9kIHRoYXQgYXBwbGllcyBhIHNldCBvZiBtaXhpblxuICAgKiBmdW5jdGlvbnMgYW5kIHJldHVybnMgdGhlIHJlc3VsdGluZyBuZXcgY2xhc3MuIFRoaXMgc3VnYXIgY2FuIG1ha2UgdGhlXG4gICAqIGFwcGxpY2F0aW9uIG9mIG1hbnkgbWl4aW5zIGF0IG9uY2UgZWFzaWVyIHRvIHJlYWQuXG4gICAqL1xuICBjbGFzcyBDb21wb3NhYmxlIGV4dGVuZHMgYmFzZSB7XG5cbiAgICAvKipcbiAgICAgKiBBcHBseSBhIHNldCBvZiBtaXhpbiBmdW5jdGlvbnMgb3IgbWl4aW4gb2JqZWN0cyB0byB0aGUgcHJlc2VudCBjbGFzcyBhbmRcbiAgICAgKiByZXR1cm4gdGhlIG5ldyBjbGFzcy5cbiAgICAgKlxuICAgICAqIEluc3RlYWQgb2Ygd3JpdGluZzpcbiAgICAgKlxuICAgICAqICAgICBsZXQgTXlDbGFzcyA9IE1peGluMShNaXhpbjIoTWl4aW4zKE1peGluNChNaXhpbjUoQmFzZUNsYXNzKSkpKSk7XG4gICAgICpcbiAgICAgKiBZb3UgY2FuIHdyaXRlOlxuICAgICAqXG4gICAgICogICAgIGxldCBNeUNsYXNzID0gQ29tcG9zYWJsZU1peGluKEJhc2VDbGFzcykuY29tcG9zZShcbiAgICAgKiAgICAgICBNaXhpbjEsXG4gICAgICogICAgICAgTWl4aW4yLFxuICAgICAqICAgICAgIE1peGluMyxcbiAgICAgKiAgICAgICBNaXhpbjQsXG4gICAgICogICAgICAgTWl4aW41XG4gICAgICogICAgICk7XG4gICAgICpcbiAgICAgKiBUaGlzIGZ1bmN0aW9uIGNhbiBhbHNvIHRha2UgbWl4aW4gb2JqZWN0cy4gQSBtaXhpbiBvYmplY3QgaXMganVzdCBhXG4gICAgICogc2hvcnRoYW5kIGZvciBhIG1peGluIGZ1bmN0aW9uIHRoYXQgY3JlYXRlcyBhIG5ldyBzdWJjbGFzcyB3aXRoIHRoZSBnaXZlblxuICAgICAqIG1lbWJlcnMuIFRoZSBtaXhpbiBvYmplY3QncyBtZW1iZXJzIGFyZSAqbm90KiBjb3BpZWQgZGlyZWN0bHkgb250byB0aGVcbiAgICAgKiBwcm90b3R5cGUgb2YgdGhlIGJhc2UgY2xhc3MsIGFzIHdpdGggdHJhZGl0aW9uYWwgbWl4aW5zLlxuICAgICAqXG4gICAgICogSW4gYWRkaXRpb24gdG8gcHJvdmlkaW5nIHN5bnRhY3RpYyBzdWdhciwgdGhpcyBtaXhpbiBjYW4gYmUgdXNlZCB0b1xuICAgICAqIGRlZmluZSBhIGNsYXNzIGluIEVTNSwgd2hpY2ggbGFja3MgRVM2J3MgYGNsYXNzYCBrZXl3b3JkLlxuICAgICAqXG4gICAgICogQHBhcmFtIHsuLi5taXhpbnN9IG1peGlucyAtIEEgc2V0IG9mIG1peGluIGZ1bmN0aW9ucyBvciBvYmplY3RzIHRvIGFwcGx5LlxuICAgICAqL1xuICAgIHN0YXRpYyBjb21wb3NlKC4uLm1peGlucykge1xuICAgICAgLy8gV2UgY3JlYXRlIGEgbmV3IHN1YmNsYXNzIGZvciBlYWNoIG1peGluIGluIHR1cm4uIFRoZSByZXN1bHQgYmVjb21lc1xuICAgICAgLy8gdGhlIGJhc2UgY2xhc3MgZXh0ZW5kZWQgYnkgYW55IHN1YnNlcXVlbnQgbWl4aW5zLiBJdCB0dXJucyBvdXQgdGhhdFxuICAgICAgLy8gd2UgY2FuIHVzZSBBcnJheS5yZWR1Y2UoKSB0byBjb25jaXNlbHkgZXhwcmVzcyB0aGlzLCB1c2luZyB0aGUgY3VycmVudFxuICAgICAgLy8gb2JqZWN0IGFzIHRoZSBzZWVkIGZvciByZWR1Y2UoKS5cbiAgICAgIHJldHVybiBtaXhpbnMucmVkdWNlKGNvbXBvc2VDbGFzcywgdGhpcyk7XG4gICAgfVxuXG4gIH1cblxuICByZXR1cm4gQ29tcG9zYWJsZTtcbn07XG5cblxuLy8gUHJvcGVydGllcyBkZWZpbmVkIGJ5IE9iamVjdCB0aGF0IHdlIGRvbid0IHdhbnQgdG8gbWl4aW4uXG5jb25zdCBOT05fTUlYQUJMRV9PQkpFQ1RfUFJPUEVSVElFUyA9IFtcbiAgJ2NvbnN0cnVjdG9yJ1xuXTtcblxuLypcbiAqIEFwcGx5IHRoZSBtaXhpbiB0byB0aGUgZ2l2ZW4gYmFzZSBjbGFzcyB0byByZXR1cm4gYSBuZXcgY2xhc3MuXG4gKiBUaGUgbWl4aW4gY2FuIGVpdGhlciBiZSBhIGZ1bmN0aW9uIHRoYXQgcmV0dXJucyB0aGUgbW9kaWZpZWQgY2xhc3MsIG9yIGFcbiAqIHBsYWluIG9iamVjdCB3aG9zZSBtZW1iZXJzIHdpbGwgYmUgY29waWVkIHRvIHRoZSBuZXcgY2xhc3MnIHByb3RvdHlwZS5cbiAqL1xuZnVuY3Rpb24gY29tcG9zZUNsYXNzKGJhc2UsIG1peGluKSB7XG4gIGlmICh0eXBlb2YgbWl4aW4gPT09ICdmdW5jdGlvbicpIHtcbiAgICAvLyBNaXhpbiBmdW5jdGlvblxuICAgIHJldHVybiBtaXhpbihiYXNlKTtcbiAgfSBlbHNlIHtcbiAgICAvLyBNaXhpbiBvYmplY3RcbiAgICBjbGFzcyBTdWJjbGFzcyBleHRlbmRzIGJhc2Uge31cbiAgICBjb3B5T3duUHJvcGVydGllcyhtaXhpbiwgU3ViY2xhc3MucHJvdG90eXBlLCBOT05fTUlYQUJMRV9PQkpFQ1RfUFJPUEVSVElFUyk7XG4gICAgcmV0dXJuIFN1YmNsYXNzO1xuICB9XG59XG5cblxuLypcbiAqIENvcHkgdGhlIGdpdmVuIHByb3BlcnRpZXMvbWV0aG9kcyB0byB0aGUgdGFyZ2V0LlxuICogUmV0dXJuIHRoZSB1cGRhdGVkIHRhcmdldC5cbiAqL1xuZnVuY3Rpb24gY29weU93blByb3BlcnRpZXMoc291cmNlLCB0YXJnZXQsIGlnbm9yZVByb3BlcnR5TmFtZXMgPSBbXSkge1xuICBPYmplY3QuZ2V0T3duUHJvcGVydHlOYW1lcyhzb3VyY2UpLmZvckVhY2gobmFtZSA9PiB7XG4gICAgaWYgKGlnbm9yZVByb3BlcnR5TmFtZXMuaW5kZXhPZihuYW1lKSA8IDApIHtcbiAgICAgIGNvbnN0IGRlc2NyaXB0b3IgPSBPYmplY3QuZ2V0T3duUHJvcGVydHlEZXNjcmlwdG9yKHNvdXJjZSwgbmFtZSk7XG4gICAgICBPYmplY3QuZGVmaW5lUHJvcGVydHkodGFyZ2V0LCBuYW1lLCBkZXNjcmlwdG9yKTtcbiAgICB9XG4gIH0pO1xuICByZXR1cm4gdGFyZ2V0O1xufVxuIiwiaW1wb3J0IGNyZWF0ZVN5bWJvbCBmcm9tICcuL2NyZWF0ZVN5bWJvbCc7XG5pbXBvcnQgdG9nZ2xlQ2xhc3MgZnJvbSAnLi90b2dnbGVDbGFzcyc7XG5pbXBvcnQgc3ltYm9scyBmcm9tICcuL3N5bWJvbHMnO1xuXG5cbi8vIFN5bWJvbHMgZm9yIHByaXZhdGUgZGF0YSBtZW1iZXJzIG9uIGFuIGVsZW1lbnQuXG5jb25zdCBpdGVtc1N5bWJvbCA9IGNyZWF0ZVN5bWJvbCgnaXRlbXMnKTtcbmNvbnN0IGl0ZW1Jbml0aWFsaXplZFN5bWJvbCA9IGNyZWF0ZVN5bWJvbCgnaXRlbUluaXRpYWxpemVkJyk7XG5cblxuLyogRXhwb3J0ZWQgZnVuY3Rpb24gZXh0ZW5kcyBhIGJhc2UgY2xhc3Mgd2l0aCBDb250ZW50SXRlbXMuICovXG5leHBvcnQgZGVmYXVsdCAoYmFzZSkgPT4ge1xuXG4gIC8qKlxuICAgKiBNaXhpbiB3aGljaCBtYXBzIGNvbnRlbnQgc2VtYW50aWNzIChlbGVtZW50cykgdG8gbGlzdCBpdGVtIHNlbWFudGljcy5cbiAgICpcbiAgICogSXRlbXMgZGlmZmVyIGZyb20gZWxlbWVudCBjb250ZW50cyBpbiBzZXZlcmFsIHdheXM6XG4gICAqXG4gICAqICogVGhleSBhcmUgb2Z0ZW4gcmVmZXJlbmNlZCB2aWEgaW5kZXguXG4gICAqICogVGhleSBtYXkgaGF2ZSBhIHNlbGVjdGlvbiBzdGF0ZS5cbiAgICogKiBJdCdzIGNvbW1vbiB0byBkbyB3b3JrIHRvIGluaXRpYWxpemUgdGhlIGFwcGVhcmFuY2Ugb3Igc3RhdGUgb2YgYSBuZXdcbiAgICogICBpdGVtLlxuICAgKiAqIEF1eGlsaWFyeSBpbnZpc2libGUgY2hpbGQgZWxlbWVudHMgYXJlIGZpbHRlcmVkIG91dCBhbmQgbm90IGNvdW50ZWQgYXNcbiAgICogICBpdGVtcy4gQXV4aWxpYXJ5IGVsZW1lbnRzIGluY2x1ZGUgbGluaywgc2NyaXB0LCBzdHlsZSwgYW5kIHRlbXBsYXRlXG4gICAqICAgZWxlbWVudHMuIFRoaXMgZmlsdGVyaW5nIGVuc3VyZXMgdGhhdCB0aG9zZSBhdXhpbGlhcnkgZWxlbWVudHMgY2FuIGJlXG4gICAqICAgdXNlZCBpbiBtYXJrdXAgaW5zaWRlIG9mIGEgbGlzdCB3aXRob3V0IGJlaW5nIHRyZWF0ZWQgYXMgbGlzdCBpdGVtcy5cbiAgICpcbiAgICogVGhpcyBtaXhpbiBleHBlY3RzIGEgY29tcG9uZW50IHRvIHByb3ZpZGUgYSBgY29udGVudGAgcHJvcGVydHkgcmV0dXJuaW5nIGFcbiAgICogcmF3IHNldCBvZiBlbGVtZW50cy4gWW91IGNhbiBwcm92aWRlIHRoYXQgeW91cnNlbGYsIG9yIHVzZVxuICAgKiBbRGlzdHJpYnV0ZWRDaGlsZHJlbkNvbnRlbnRNaXhpbl0oRGlzdHJpYnV0ZWRDaGlsZHJlbkNvbnRlbnRNaXhpbi5tZCkuXG4gICAqXG4gICAqIFRoZSBtb3N0IGNvbW1vbmx5IHJlZmVyZW5jZWQgcHJvcGVydHkgZGVmaW5lZCBieSB0aGlzIG1peGluIGlzIHRoZSBgaXRlbXNgXG4gICAqIHByb3BlcnR5LiBUbyBhdm9pZCBoYXZpbmcgdG8gZG8gd29yayBlYWNoIHRpbWUgdGhhdCBwcm9wZXJ0eSBpcyByZXF1ZXN0ZWQsXG4gICAqIHRoaXMgbWl4aW4gc3VwcG9ydHMgYW4gb3B0aW1pemVkIG1vZGUuIElmIHlvdSBpbnZva2UgdGhlIGBjb250ZW50Q2hhbmdlZGBcbiAgICogbWV0aG9kIHdoZW4gdGhlIHNldCBvZiBpdGVtcyBjaGFuZ2VzLCB0aGUgbWl4aW4gY29uY2x1ZGVzIHRoYXQgeW91J2xsIHRha2VcbiAgICogY2FyZSBvZiBub3RpZnlpbmcgaXQgb2YgZnV0dXJlIGNoYW5nZXMsIGFuZCB0dXJucyBvbiB0aGUgb3B0aW1pemF0aW9uLiBXaXRoXG4gICAqIHRoYXQgb24sIHRoZSBtaXhpbiBzYXZlcyBhIHJlZmVyZW5jZSB0byB0aGUgY29tcHV0ZWQgc2V0IG9mIGl0ZW1zLCBhbmQgd2lsbFxuICAgKiByZXR1cm4gdGhhdCBpbW1lZGlhdGVseSBvbiBzdWJzZXF1ZW50IGNhbGxzIHRvIHRoZSBgaXRlbXNgIHByb3BlcnR5LiBJZiB5b3VcbiAgICogdXNlIHRoaXMgbWl4aW4gaW4gY29uanVuY3Rpb24gd2l0aFxuICAgKiBbRGlzdHJpYnV0ZWRDaGlsZHJlbkNvbnRlbnRNaXhpbl0oRGlzdHJpYnV0ZWRDaGlsZHJlbkNvbnRlbnRNaXhpbi5tZCksIHRoZVxuICAgKiBgY29udGVudENoYW5nZWRgIG1ldGhvZCB3aWxsIGJlIGludm9rZWQgZm9yIHlvdSB3aGVuIHRoZSBlbGVtZW50J3MgY2hpbGRyZW5cbiAgICogY2hhbmdlLCB0dXJuaW5nIG9uIHRoZSBvcHRpbWl6YXRpb24gYXV0b21hdGljYWxseS5cbiAgICovXG4gIGNsYXNzIENvbnRlbnRJdGVtcyBleHRlbmRzIGJhc2Uge1xuXG4gICAgY29udGVudENoYW5nZWQoKSB7XG4gICAgICBpZiAoc3VwZXIuY29udGVudENoYW5nZWQpIHsgc3VwZXIuY29udGVudENoYW5nZWQoKTsgfVxuXG4gICAgICAvLyBTaW5jZSB3ZSBnb3QgdGhlIGNvbnRlbnRDaGFuZ2VkIGNhbGwsIHdlJ2xsIGFzc3VtZSB3ZSdsbCBiZSBub3RpZmllZCBpZlxuICAgICAgLy8gdGhlIHNldCBvZiBpdGVtcyBjaGFuZ2VzIGxhdGVyLiBXZSB0dXJuIG9uIG1lbW9pemF0aW9uIG9mIHRoZSBpdGVtc1xuICAgICAgLy8gcHJvcGVydHkgYnkgc2V0dGluZyBvdXIgaW50ZXJuYWwgcHJvcGVydHkgdG8gbnVsbCAoaW5zdGVhZCBvZlxuICAgICAgLy8gdW5kZWZpbmVkKS5cbiAgICAgIHRoaXNbaXRlbXNTeW1ib2xdID0gbnVsbDtcblxuICAgICAgdGhpc1tzeW1ib2xzLml0ZW1zQ2hhbmdlZF0oKTtcbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBUaGlzIG1ldGhvZCBpcyBpbnZva2VkIHdoZW5ldmVyIGEgbmV3IGl0ZW0gaXMgYWRkZWQgdG8gdGhlIGxpc3QuXG4gICAgICpcbiAgICAgKiBUaGUgZGVmYXVsdCBpbXBsZW1lbnRhdGlvbiBvZiB0aGlzIG1ldGhvZCBkb2VzIG5vdGhpbmcuIFlvdSBjYW4gb3ZlcnJpZGVcbiAgICAgKiB0aGlzIHRvIHBlcmZvcm0gcGVyLWl0ZW0gaW5pdGlhbGl6YXRpb24uXG4gICAgICpcbiAgICAgKiBAcGFyYW0ge0hUTUxFbGVtZW50fSBpdGVtIC0gVGhlIGl0ZW0gdGhhdCB3YXMgYWRkZWQuXG4gICAgICovXG4gICAgW3N5bWJvbHMuaXRlbUFkZGVkXShpdGVtKSB7XG4gICAgICBpZiAoc3VwZXJbc3ltYm9scy5pdGVtQWRkZWRdKSB7IHN1cGVyW3N5bWJvbHMuaXRlbUFkZGVkXShpdGVtKTsgfVxuICAgIH1cblxuICAgIC8qKlxuICAgICAqIFRoZSBzZWxlY3Rpb24gc3RhdGUgZm9yIGEgc2luZ2xlIGl0ZW0gaGFzIGNoYW5nZWQuXG4gICAgICpcbiAgICAgKiBJbnZva2UgdGhpcyBtZXRob2QgdG8gc2lnbmFsIHRoYXQgdGhlIHNlbGVjdGVkIHN0YXRlIG9mIHRoZSBpbmRpY2F0ZWQgaXRlbVxuICAgICAqIGhhcyBjaGFuZ2VkLiBCeSBkZWZhdWx0LCB0aGlzIGFwcGxpZXMgYSBgc2VsZWN0ZWRgIENTUyBjbGFzcyBpZiB0aGUgaXRlbVxuICAgICAqIGlzIHNlbGVjdGVkLCBhbmQgcmVtb3ZlZCBpdCBpZiBub3Qgc2VsZWN0ZWQuXG4gICAgICpcbiAgICAgKiBAcGFyYW0ge0hUTUxFbGVtZW50fSBpdGVtIC0gVGhlIGl0ZW0gd2hvc2Ugc2VsZWN0aW9uIHN0YXRlIGhhcyBjaGFuZ2VkLlxuICAgICAqIEBwYXJhbSB7Ym9vbGVhbn0gc2VsZWN0ZWQgLSBUcnVlIGlmIHRoZSBpdGVtIGlzIHNlbGVjdGVkLCBmYWxzZSBpZiBub3QuXG4gICAgICovXG4gICAgW3N5bWJvbHMuaXRlbVNlbGVjdGVkXShpdGVtLCBzZWxlY3RlZCkge1xuICAgICAgaWYgKHN1cGVyW3N5bWJvbHMuaXRlbVNlbGVjdGVkXSkgeyBzdXBlcltzeW1ib2xzLml0ZW1TZWxlY3RlZF0oaXRlbSwgc2VsZWN0ZWQpOyB9XG4gICAgICB0b2dnbGVDbGFzcyhpdGVtLCAnc2VsZWN0ZWQnLCBzZWxlY3RlZCk7XG4gICAgfVxuXG4gICAgLyoqXG4gICAgICogVGhlIGN1cnJlbnQgc2V0IG9mIGl0ZW1zIGluIHRoZSBsaXN0LiBTZWUgdGhlIHRvcC1sZXZlbCBkb2N1bWVudGF0aW9uIGZvclxuICAgICAqIG1peGluIGZvciBhIGRlc2NyaXB0aW9uIG9mIGhvdyBpdGVtcyBkaWZmZXIgZnJvbSBwbGFpbiBjb250ZW50LlxuICAgICAqXG4gICAgICogQHR5cGUge0hUTUxFbGVtZW50W119XG4gICAgICovXG4gICAgZ2V0IGl0ZW1zKCkge1xuICAgICAgbGV0IGl0ZW1zO1xuICAgICAgaWYgKHRoaXNbaXRlbXNTeW1ib2xdID09IG51bGwpIHtcbiAgICAgICAgaXRlbXMgPSBmaWx0ZXJBdXhpbGlhcnlFbGVtZW50cyh0aGlzLmNvbnRlbnQpO1xuICAgICAgICAvLyBOb3RlOiB0ZXN0IGZvciAqZXF1YWxpdHkqIHdpdGggbnVsbDsgZG9uJ3QgdHJlYXQgdW5kZWZpbmVkIGFzIGEgbWF0Y2guXG4gICAgICAgIGlmICh0aGlzW2l0ZW1zU3ltYm9sXSA9PT0gbnVsbCkge1xuICAgICAgICAgIC8vIE1lbW9pemUgdGhlIHNldCBvZiBpdGVtcy5cbiAgICAgICAgICB0aGlzW2l0ZW1zU3ltYm9sXSA9IGl0ZW1zO1xuICAgICAgICB9XG4gICAgICB9IGVsc2Uge1xuICAgICAgICAvLyBSZXR1cm4gdGhlIG1lbW9pemVkIGl0ZW1zLlxuICAgICAgICBpdGVtcyA9IHRoaXNbaXRlbXNTeW1ib2xdO1xuICAgICAgfVxuICAgICAgcmV0dXJuIGl0ZW1zO1xuICAgIH1cblxuICAgIC8qKlxuICAgICAqIFRoaXMgbWV0aG9kIGlzIGludm9rZWQgd2hlbiB0aGUgdW5kZXJseWluZyBjb250ZW50cyBjaGFuZ2UuIEl0IGlzIGFsc29cbiAgICAgKiBpbnZva2VkIG9uIGNvbXBvbmVudCBpbml0aWFsaXphdGlvbiDigJMgc2luY2UgdGhlIGl0ZW1zIGhhdmUgXCJjaGFuZ2VkXCIgZnJvbVxuICAgICAqIGJlaW5nIG5vdGhpbmcuXG4gICAgICovXG4gICAgW3N5bWJvbHMuaXRlbXNDaGFuZ2VkXSgpIHtcbiAgICAgIGlmIChzdXBlcltzeW1ib2xzLml0ZW1zQ2hhbmdlZF0pIHsgc3VwZXJbc3ltYm9scy5pdGVtc0NoYW5nZWRdKCk7IH1cblxuICAgICAgLy8gUGVyZm9ybSBwZXItaXRlbSBpbml0aWFsaXphdGlvbi5cbiAgICAgIEFycmF5LnByb3RvdHlwZS5mb3JFYWNoLmNhbGwodGhpcy5pdGVtcywgaXRlbSA9PiB7XG4gICAgICAgIGlmICghaXRlbVtpdGVtSW5pdGlhbGl6ZWRTeW1ib2xdKSB7XG4gICAgICAgICAgdGhpc1tzeW1ib2xzLml0ZW1BZGRlZF0oaXRlbSk7XG4gICAgICAgICAgaXRlbVtpdGVtSW5pdGlhbGl6ZWRTeW1ib2xdID0gdHJ1ZTtcbiAgICAgICAgfVxuICAgICAgfSk7XG5cbiAgICAgIHRoaXMuZGlzcGF0Y2hFdmVudChuZXcgQ3VzdG9tRXZlbnQoJ2l0ZW1zLWNoYW5nZWQnKSk7XG4gICAgfVxuXG4gICAgLyoqXG4gICAgICogRmlyZXMgd2hlbiB0aGUgaXRlbXMgaW4gdGhlIGxpc3QgY2hhbmdlLlxuICAgICAqXG4gICAgICogQG1lbWJlcm9mIENvbnRlbnRJdGVtc1xuICAgICAqIEBldmVudCBpdGVtcy1jaGFuZ2VkXG4gICAgICovXG4gIH1cblxuICByZXR1cm4gQ29udGVudEl0ZW1zO1xufTtcblxuXG4vLyBSZXR1cm4gdGhlIGdpdmVuIGVsZW1lbnRzLCBmaWx0ZXJpbmcgb3V0IGF1eGlsaWFyeSBlbGVtZW50cyB0aGF0IGFyZW4ndFxuLy8gdHlwaWNhbGx5IHZpc2libGUuIEl0ZW1zIHdoaWNoIGFyZSBub3QgZWxlbWVudHMgYXJlIHJldHVybmVkIGFzIGlzLlxuZnVuY3Rpb24gZmlsdGVyQXV4aWxpYXJ5RWxlbWVudHMoaXRlbXMpIHtcbiAgY29uc3QgYXV4aWxpYXJ5VGFncyA9IFtcbiAgICAnbGluaycsXG4gICAgJ3NjcmlwdCcsXG4gICAgJ3N0eWxlJyxcbiAgICAndGVtcGxhdGUnXG4gIF07XG4gIHJldHVybiBbXS5maWx0ZXIuY2FsbChpdGVtcywgZnVuY3Rpb24oaXRlbSkge1xuICAgIHJldHVybiAhaXRlbS5sb2NhbE5hbWUgfHwgYXV4aWxpYXJ5VGFncy5pbmRleE9mKGl0ZW0ubG9jYWxOYW1lKSA8IDA7XG4gIH0pO1xufVxuIiwiaW1wb3J0IHN5bWJvbHMgZnJvbSAnLi9zeW1ib2xzJztcblxuXG4vKiBFeHBvcnRlZCBmdW5jdGlvbiBleHRlbmRzIGEgYmFzZSBjbGFzcyB3aXRoIERpcmVjdGlvblNlbGVjdGlvbi4gKi9cbmV4cG9ydCBkZWZhdWx0IChiYXNlKSA9PiB7XG5cbiAgLyoqXG4gICAqIE1peGluIHdoaWNoIG1hcHMgZGlyZWN0aW9uIHNlbWFudGljcyAoZ29MZWZ0LCBnb1JpZ2h0LCBldGMuKSB0byBzZWxlY3Rpb25cbiAgICogc2VtYW50aWNzIChzZWxlY3RQcmV2aW91cywgc2VsZWN0TmV4dCwgZXRjLikuXG4gICAqXG4gICAqIFRoaXMgbWl4aW4gY2FuIGJlIHVzZWQgaW4gY29uanVuY3Rpb24gd2l0aFxuICAgKiBbS2V5Ym9hcmREaXJlY3Rpb25NaXhpbl0oS2V5Ym9hcmREaXJlY3Rpb25NaXhpbi5tZCkgKHdoaWNoIG1hcHMga2V5Ym9hcmRcbiAgICogZXZlbnRzIHRvIGRpcmVjdGlvbnMpIGFuZCBhIG1peGluIHRoYXQgaGFuZGxlcyBzZWxlY3Rpb24gbGlrZVxuICAgKiBbU2luZ2xlU2VsZWN0aW9uTWl4aW5dKFNpbmdsZVNlbGVjdGlvbk1peGluLm1kKS5cbiAgICovXG4gIGNsYXNzIERpcmVjdGlvblNlbGVjdGlvbiBleHRlbmRzIGJhc2Uge1xuXG4gICAgW3N5bWJvbHMuZ29Eb3duXSgpIHtcbiAgICAgIGlmIChzdXBlcltzeW1ib2xzLmdvRG93bl0pIHsgc3VwZXJbc3ltYm9scy5nb0Rvd25dKCk7IH1cbiAgICAgIHJldHVybiB0aGlzLnNlbGVjdE5leHQoKTtcbiAgICB9XG5cbiAgICBbc3ltYm9scy5nb0VuZF0oKSB7XG4gICAgICBpZiAoc3VwZXJbc3ltYm9scy5nb0VuZF0pIHsgc3VwZXJbc3ltYm9scy5nb0VuZF0oKTsgfVxuICAgICAgcmV0dXJuIHRoaXMuc2VsZWN0TGFzdCgpO1xuICAgIH1cblxuICAgIFtzeW1ib2xzLmdvTGVmdF0oKSB7XG4gICAgICBpZiAoc3VwZXJbc3ltYm9scy5nb0xlZnRdKSB7IHN1cGVyW3N5bWJvbHMuZ29MZWZ0XSgpOyB9XG4gICAgICByZXR1cm4gdGhpcy5zZWxlY3RQcmV2aW91cygpO1xuICAgIH1cblxuICAgIFtzeW1ib2xzLmdvUmlnaHRdKCkge1xuICAgICAgaWYgKHN1cGVyW3N5bWJvbHMuZ29SaWdodF0pIHsgc3VwZXJbc3ltYm9scy5nb1JpZ2h0XSgpOyB9XG4gICAgICByZXR1cm4gdGhpcy5zZWxlY3ROZXh0KCk7XG4gICAgfVxuXG4gICAgW3N5bWJvbHMuZ29TdGFydF0oKSB7XG4gICAgICBpZiAoc3VwZXJbc3ltYm9scy5nb1N0YXJ0XSkgeyBzdXBlcltzeW1ib2xzLmdvU3RhcnRdKCk7IH1cbiAgICAgIHJldHVybiB0aGlzLnNlbGVjdEZpcnN0KCk7XG4gICAgfVxuXG4gICAgW3N5bWJvbHMuZ29VcF0oKSB7XG4gICAgICBpZiAoc3VwZXJbc3ltYm9scy5nb1VwXSkgeyBzdXBlcltzeW1ib2xzLmdvVXBdKCk7IH1cbiAgICAgIHJldHVybiB0aGlzLnNlbGVjdFByZXZpb3VzKCk7XG4gICAgfVxuXG4gICAgLy8gRGVmYXVsdCBpbXBsZW1lbnRhdGlvbi4gVGhpcyB3aWxsIHR5cGljYWxseSBiZSBoYW5kbGVkIGJ5IG90aGVyIG1peGlucy5cbiAgICBnZXQgc2VsZWN0ZWRGcmFjdGlvbigpIHtcbiAgICAgIHJldHVybiBzdXBlci5zZWxlY3RlZEZyYWN0aW9uO1xuICAgIH1cbiAgICBzZXQgc2VsZWN0ZWRGcmFjdGlvbih2YWx1ZSkge1xuICAgICAgaWYgKCdzZWxlY3RlZEZyYWN0aW9uJyBpbiBiYXNlLnByb3RvdHlwZSkgeyBzdXBlci5zZWxlY3RlZEZyYWN0aW9uID0gdmFsdWU7IH1cbiAgICB9XG5cbiAgICAvLyBEZWZhdWx0IGltcGxlbWVudGF0aW9uLiBUaGlzIHdpbGwgdHlwaWNhbGx5IGJlIGhhbmRsZWQgYnkgb3RoZXIgbWl4aW5zLlxuICAgIHNlbGVjdEZpcnN0KCkge1xuICAgICAgaWYgKHN1cGVyLnNlbGVjdEZpcnN0KSB7IHJldHVybiBzdXBlci5zZWxlY3RGaXJzdCgpOyB9XG4gICAgfVxuXG4gICAgLy8gRGVmYXVsdCBpbXBsZW1lbnRhdGlvbi4gVGhpcyB3aWxsIHR5cGljYWxseSBiZSBoYW5kbGVkIGJ5IG90aGVyIG1peGlucy5cbiAgICBzZWxlY3RMYXN0KCkge1xuICAgICAgaWYgKHN1cGVyLnNlbGVjdExhc3QpIHsgcmV0dXJuIHN1cGVyLnNlbGVjdExhc3QoKTsgfVxuICAgIH1cblxuICAgIC8vIERlZmF1bHQgaW1wbGVtZW50YXRpb24uIFRoaXMgd2lsbCB0eXBpY2FsbHkgYmUgaGFuZGxlZCBieSBvdGhlciBtaXhpbnMuXG4gICAgc2VsZWN0TmV4dCgpIHtcbiAgICAgIGlmIChzdXBlci5zZWxlY3ROZXh0KSB7IHJldHVybiBzdXBlci5zZWxlY3ROZXh0KCk7IH1cbiAgICB9XG5cbiAgICAvLyBEZWZhdWx0IGltcGxlbWVudGF0aW9uLiBUaGlzIHdpbGwgdHlwaWNhbGx5IGJlIGhhbmRsZWQgYnkgb3RoZXIgbWl4aW5zLlxuICAgIHNlbGVjdFByZXZpb3VzKCkge1xuICAgICAgaWYgKHN1cGVyLnNlbGVjdFByZXZpb3VzKSB7IHJldHVybiBzdXBlci5zZWxlY3RQcmV2aW91cygpOyB9XG4gICAgfVxuXG4gICAgLy8gTWFwIGRyYWcgdHJhdmVsIGZyYWN0aW9uIHRvIHNlbGVjdGlvbiBmcmFjdGlvbi5cbiAgICBnZXQgdHJhdmVsRnJhY3Rpb24oKSB7XG4gICAgICByZXR1cm4gc3VwZXIudHJhdmVsRnJhY3Rpb247XG4gICAgfVxuICAgIHNldCB0cmF2ZWxGcmFjdGlvbih2YWx1ZSkge1xuICAgICAgaWYgKCd0cmF2ZWxGcmFjdGlvbicgaW4gYmFzZS5wcm90b3R5cGUpIHsgc3VwZXIudHJhdmVsRnJhY3Rpb24gPSB2YWx1ZTsgfVxuICAgICAgdGhpcy5zZWxlY3RlZEZyYWN0aW9uID0gdmFsdWU7XG4gICAgfVxuXG4gIH1cblxuICByZXR1cm4gRGlyZWN0aW9uU2VsZWN0aW9uO1xufTtcbiIsImltcG9ydCBtaWNyb3Rhc2sgZnJvbSAnLi9taWNyb3Rhc2snO1xuXG5cbi8qIEV4cG9ydGVkIGZ1bmN0aW9uIGV4dGVuZHMgYSBiYXNlIGNsYXNzIHdpdGggRGlzdHJpYnV0ZWRDaGlsZHJlbkNvbnRlbnQuICovXG5leHBvcnQgZGVmYXVsdCAoYmFzZSkgPT4ge1xuXG4gIC8qKlxuICAgKiBNaXhpbiB3aGljaCBkZWZpbmVzIGEgY29tcG9uZW50J3MgY29udGVudCBhcyBpdHMgY2hpbGRyZW4sIGV4cGFuZGluZyBhbnlcbiAgICogbm9kZXMgZGlzdHJpYnV0ZWQgdG8gdGhlIGNvbXBvbmVudCdzIHNsb3RzLlxuICAgKlxuICAgKiBUaGlzIGFsc28gcHJvdmlkZXMgbm90aWZpY2F0aW9uIG9mIGNoYW5nZXMgdG8gYSBjb21wb25lbnQncyBjb250ZW50LiBJdFxuICAgKiB3aWxsIGludm9rZSBhIGBjb250ZW50Q2hhbmdlZGAgbWV0aG9kIHdoZW4gdGhlIGNvbXBvbmVudCBpcyBmaXJzdFxuICAgKiBpbnN0YW50aWF0ZWQsIGFuZCB3aGVuZXZlciBpdHMgZGlzdHJpYnV0ZWQgY2hpbGRyZW4gY2hhbmdlLiBUaGlzIGlzIGFuXG4gICAqIGVhc3kgd2F5IHRvIHNhdGlzZnkgdGhlIEdvbGQgU3RhbmRhcmQgY2hlY2tsaXN0IGl0ZW0gZm9yIG1vbml0b3JpbmdcbiAgICogW0NvbnRlbnQgQ2hhbmdlc10oaHR0cHM6Ly9naXRodWIuY29tL3dlYmNvbXBvbmVudHMvZ29sZC1zdGFuZGFyZC93aWtpL0NvbnRlbnQtQ2hhbmdlcykuXG4gICAqXG4gICAqIEV4YW1wbGU6XG4gICAqXG4gICAqIGBgYFxuICAgKiBsZXQgYmFzZSA9IERpc3RyaWJ1dGVkQ2hpbGRyZW5Db250ZW50TWl4aW4oRGlzdHJpYnV0ZWRDaGlsZHJlbk1peGluKEhUTUxFbGVtZW50KSk7XG4gICAqIGNsYXNzIENvdW50aW5nRWxlbWVudCBleHRlbmRzIGJhc2Uge1xuICAgKlxuICAgKiAgIGNvbnN0cnVjdG9yKCkge1xuICAgKiAgICAgc3VwZXIoKTtcbiAgICogICAgIGxldCByb290ID0gdGhpcy5hdHRhY2hTaGFkb3coeyBtb2RlOiAnb3BlbicgfSk7XG4gICAqICAgICByb290LmlubmVySFRNTCA9IGA8c2xvdD48L3Nsb3Q+YDtcbiAgICogICB9XG4gICAqXG4gICAqICAgY29udGVudENoYW5nZWQoKSB7XG4gICAqICAgICAvLyBDb3VudCB0aGUgY29tcG9uZW50J3MgY2hpbGRyZW4sIGJvdGggaW5pdGlhbGx5IGFuZCB3aGVuIGNoYW5nZWQuXG4gICAqICAgICB0aGlzLmNvdW50ID0gdGhpcy5kaXN0cmlidXRlZENoaWxkcmVuLmxlbmd0aDtcbiAgICogICB9XG4gICAqXG4gICAqIH1cbiAgICogYGBgXG4gICAqXG4gICAqIE5vdGUgdGhhdCBjb250ZW50IGNoYW5nZSBkZXRlY3Rpb24gZGVwZW5kcyB1cG9uIHRoZSBlbGVtZW50IGhhdmluZyBhdCBsZWFzdFxuICAgKiBvbmUgYHNsb3RgIGVsZW1lbnQgaW4gaXRzIHNoYWRvdyBzdWJ0cmVlLlxuICAgKlxuICAgKiBUaGlzIG1peGluIGlzIGludGVuZGVkIGZvciB1c2Ugd2l0aCB0aGVcbiAgICogW0Rpc3RyaWJ1dGVkQ2hpbGRyZW5NaXhpbl0oRGlzdHJpYnV0ZWRDaGlsZHJlbk1peGluLm1kKS4gU2VlIHRoYXQgbWl4aW4gZm9yXG4gICAqIGEgZGlzY3Vzc2lvbiBvZiBob3cgdGhhdCB3b3Jrcy4gVGhpcyBEaXN0cmlidXRlZENoaWxkcmVuQ29udGVudE1peGluXG4gICAqIHByb3ZpZGVzIGFuIGVhc3kgd2F5IG9mIGRlZmluaW5nIHRoZSBcImNvbnRlbnRcIiBvZiBhIGNvbXBvbmVudCBhcyB0aGVcbiAgICogY29tcG9uZW50J3MgZGlzdHJpYnV0ZWQgY2hpbGRyZW4uIFRoYXQgaW4gdHVybiBsZXRzIG1peGlucyBsaWtlXG4gICAqIFtDb250ZW50SXRlbXNNaXhpbl0oQ29udGVudEl0ZW1zTWl4aW4ubWQpIG1hbmlwdWxhdGUgdGhlIGNoaWxkcmVuIGFzIGxpc3RcbiAgICogaXRlbXMuXG4gICAqL1xuICBjbGFzcyBEaXN0cmlidXRlZENoaWxkcmVuQ29udGVudCBleHRlbmRzIGJhc2Uge1xuXG4gICAgY29uc3RydWN0b3IoKSB7XG4gICAgICBzdXBlcigpO1xuXG4gICAgICBpZiAodGhpcy5zaGFkb3dSb290KSB7XG4gICAgICAgIC8vIExpc3RlbiB0byBjaGFuZ2VzIG9uIGFsbCBzbG90cy5cbiAgICAgICAgY29uc3Qgc2xvdHMgPSB0aGlzLnNoYWRvd1Jvb3QucXVlcnlTZWxlY3RvckFsbCgnc2xvdCcpO1xuICAgICAgICBzbG90cy5mb3JFYWNoKHNsb3QgPT4gc2xvdC5hZGRFdmVudExpc3RlbmVyKCdzbG90Y2hhbmdlJywgZXZlbnQgPT4ge1xuICAgICAgICAgIHRoaXMuY29udGVudENoYW5nZWQoKTtcbiAgICAgICAgfSkpO1xuICAgICAgfVxuXG4gICAgICAvLyBNYWtlIGFuIGluaXRpYWwgY2FsbCB0byBjb250ZW50Q2hhbmdlZCgpIHNvIHRoYXQgdGhlIGNvbXBvbmVudCBjYW4gZG9cbiAgICAgIC8vIGluaXRpYWxpemF0aW9uIHRoYXQgaXQgbm9ybWFsbHkgZG9lcyB3aGVuIGNvbnRlbnQgY2hhbmdlcy5cbiAgICAgIC8vXG4gICAgICAvLyBUaGlzIHdpbGwgaW52b2tlIGNvbnRlbnRDaGFuZ2VkKCkgaGFuZGxlcnMgaW4gb3RoZXIgbWl4aW5zLiBJbiBvcmRlclxuICAgICAgLy8gdGhhdCB0aG9zZSBtaXhpbnMgaGF2ZSBhIGNoYW5jZSB0byBjb21wbGV0ZSB0aGVpciBvd24gaW5pdGlhbGl6YXRpb24sXG4gICAgICAvLyB3ZSBhZGQgdGhlIGNvbnRlbnRDaGFuZ2VkKCkgY2FsbCB0byB0aGUgbWljcm90YXNrIHF1ZXVlLlxuICAgICAgbWljcm90YXNrKCgpID0+IHRoaXMuY29udGVudENoYW5nZWQoKSk7XG4gICAgfVxuXG4gICAgLyoqXG4gICAgICogSW52b2tlZCB3aGVuIHRoZSBjb250ZW50cyBvZiB0aGUgY29tcG9uZW50IChpbmNsdWRpbmcgZGlzdHJpYnV0ZWRcbiAgICAgKiBjaGlsZHJlbikgaGF2ZSBjaGFuZ2VkLlxuICAgICAqXG4gICAgICogVGhpcyBtZXRob2QgaXMgYWxzbyBpbnZva2VkIHdoZW4gYSBjb21wb25lbnQgaXMgZmlyc3QgaW5zdGFudGlhdGVkOyB0aGVcbiAgICAgKiBjb250ZW50cyBoYXZlIGVzc2VudGlhbGx5IFwiY2hhbmdlZFwiIGZyb20gYmVpbmcgbm90aGluZy4gVGhpcyBhbGxvd3MgdGhlXG4gICAgICogY29tcG9uZW50IHRvIHBlcmZvcm0gaW5pdGlhbCBwcm9jZXNzaW5nIG9mIGl0cyBjaGlsZHJlbi5cbiAgICAgKi9cbiAgICBjb250ZW50Q2hhbmdlZCgpIHtcbiAgICAgIGlmIChzdXBlci5jb250ZW50Q2hhbmdlZCkgeyBzdXBlci5jb250ZW50Q2hhbmdlZCgpOyB9XG4gICAgICBjb25zdCBldmVudCA9IG5ldyBDdXN0b21FdmVudCgnY29udGVudC1jaGFuZ2VkJyk7XG4gICAgICB0aGlzLmRpc3BhdGNoRXZlbnQoZXZlbnQpO1xuICAgIH1cblxuICAgIC8qKlxuICAgICAqIFRoZSBjb250ZW50IG9mIHRoaXMgY29tcG9uZW50LCBkZWZpbmVkIHRvIGJlIHRoZSBmbGF0dGVuZWQgYXJyYXkgb2ZcbiAgICAgKiBjaGlsZHJlbiBkaXN0cmlidXRlZCB0byB0aGUgY29tcG9uZW50LlxuICAgICAqXG4gICAgICogQHR5cGUge0hUTUxFbGVtZW50W119XG4gICAgICovXG4gICAgZ2V0IGNvbnRlbnQoKSB7XG4gICAgICBjb25zdCBkaXN0cmlidXRlZENoaWxkcmVuID0gdGhpcy5kaXN0cmlidXRlZENoaWxkcmVuO1xuICAgICAgaWYgKHR5cGVvZiBkaXN0cmlidXRlZENoaWxkcmVuID09PSAndW5kZWZpbmVkJykge1xuICAgICAgICBjb25zb2xlLndhcm4oYERpc3RyaWJ1dGVkQ2hpbGRyZW5Db250ZW50TWl4aW4gZXhwZWN0cyB0aGUgY29tcG9uZW50IHRvIGRlZmluZSBhIFwiZGlzdHJpYnV0ZWRDaGlsZHJlblwiIHByb3BlcnR5LmApO1xuICAgICAgfVxuICAgICAgcmV0dXJuIGRpc3RyaWJ1dGVkQ2hpbGRyZW47XG4gICAgfVxuICAgIHNldCBjb250ZW50KHZhbHVlKSB7XG4gICAgICBpZiAoJ2NvbnRlbnQnIGluIGJhc2UucHJvdG90eXBlKSB7IHN1cGVyLmNvbnRlbnQgPSB2YWx1ZTsgfVxuICAgICAgLy8gVE9ETzogU2V0IHRoZSBjaGlsZHJlbiB0byB0aGUgZ2l2ZW4gdmFsdWUgKHdoaWNoIHNob3VsZCBiZSBhbiBhcnJheSBvZlxuICAgICAgLy8gZWxlbWVudHMpP1xuICAgIH1cblxuICAgIC8qKlxuICAgICAqIFRoaXMgZXZlbnQgaXMgcmFpc2VkIHdoZW4gdGhlIGNvbXBvbmVudCdzIGNvbnRlbnRzIChpbmNsdWRpbmcgZGlzdHJpYnV0ZWRcbiAgICAgKiBjaGlsZHJlbikgaGF2ZSBjaGFuZ2VkLlxuICAgICAqXG4gICAgICogQG1lbWJlcm9mIERpc3RyaWJ1dGVkQ2hpbGRyZW5Db250ZW50XG4gICAgICogQGV2ZW50IGNvbnRlbnQtY2hhbmdlZFxuICAgICAqL1xuICB9XG5cbiAgcmV0dXJuIERpc3RyaWJ1dGVkQ2hpbGRyZW5Db250ZW50O1xufTtcbiIsIi8qIEV4cG9ydGVkIGZ1bmN0aW9uIGV4dGVuZHMgYSBiYXNlIGNsYXNzIHdpdGggRGlzdHJpYnV0ZWRDaGlsZHJlbi4gKi9cbmV4cG9ydCBkZWZhdWx0IChiYXNlKSA9PiB7XG5cbiAgLyoqXG4gICAqIE1peGluIHdoaWNoIGRlZmluZXMgaGVscGVycyBmb3IgYWNjZXNzaW5nIGEgY29tcG9uZW50J3MgZGlzdHJpYnV0ZWRcbiAgICogY2hpbGRyZW4gYXMgYSBmbGF0dGVuZWQgYXJyYXkgb3Igc3RyaW5nLlxuICAgKlxuICAgKiBUaGUgc3RhbmRhcmQgRE9NIEFQSSBwcm92aWRlcyBzZXZlcmFsIHdheXMgb2YgYWNjZXNzaW5nIGNoaWxkIGNvbnRlbnQ6XG4gICAqIGBjaGlsZHJlbmAsIGBjaGlsZE5vZGVzYCwgYW5kIGB0ZXh0Q29udGVudGAuIE5vbmUgb2YgdGhlc2UgZnVuY3Rpb25zIGFyZVxuICAgKiBTaGFkb3cgRE9NIGF3YXJlLiBUaGlzIG1peGluIGRlZmluZXMgdmFyaWF0aW9ucyBvZiB0aG9zZSBmdW5jdGlvbnMgdGhhdFxuICAgKiAqYXJlKiBTaGFkb3cgRE9NIGF3YXJlLlxuICAgKlxuICAgKiBFeGFtcGxlOiB5b3UgY3JlYXRlIGEgY29tcG9uZW50IGA8Y291bnQtY2hpbGRyZW4+YCB0aGF0IGRpc3BsYXlzIGEgbnVtYmVyXG4gICAqIGVxdWFsIHRvIHRoZSBudW1iZXIgb2YgY2hpbGRyZW4gcGxhY2VkIGluc2lkZSB0aGF0IGNvbXBvbmVudC4gSWYgc29tZW9uZVxuICAgKiBpbnN0YW50aWF0ZXMgeW91ciBjb21wb25lbnQgbGlrZTpcbiAgICpcbiAgICogICAgIDxjb3VudC1jaGlsZHJlbj5cbiAgICogICAgICAgPGRpdj48L2Rpdj5cbiAgICogICAgICAgPGRpdj48L2Rpdj5cbiAgICogICAgICAgPGRpdj48L2Rpdj5cbiAgICogICAgIDwvY291bnQtY2hpbGRyZW4+XG4gICAqXG4gICAqIFRoZW4gdGhlIGNvbXBvbmVudCBzaG91bGQgc2hvdyBcIjNcIiwgYmVjYXVzZSB0aGVyZSBhcmUgdGhyZWUgY2hpbGRyZW4uIFRvXG4gICAqIGNhbGN1bGF0ZSB0aGUgbnVtYmVyIG9mIGNoaWxkcmVuLCB0aGUgY29tcG9uZW50IGNhbiBqdXN0IGNhbGN1bGF0ZVxuICAgKiBgdGhpcy5jaGlsZHJlbi5sZW5ndGhgLiBIb3dldmVyLCBzdXBwb3NlIHNvbWVvbmUgaW5zdGFudGlhdGVzIHlvdXJcbiAgICogY29tcG9uZW50IGluc2lkZSBvbmUgb2YgdGhlaXIgb3duIGNvbXBvbmVudHMsIGFuZCBwdXRzIGEgYDxzbG90PmAgZWxlbWVudFxuICAgKiBpbnNpZGUgeW91ciBjb21wb25lbnQ6XG4gICAqXG4gICAqICAgICA8Y291bnQtY2hpbGRyZW4+XG4gICAqICAgICAgIDxzbG90Pjwvc2xvdD5cbiAgICogICAgIDwvY291bnQtY2hpbGRyZW4+XG4gICAqXG4gICAqIElmIHlvdXIgY29tcG9uZW50IG9ubHkgbG9va3MgYXQgYHRoaXMuY2hpbGRyZW5gLCBpdCB3aWxsIGFsd2F5cyBzZWUgZXhhY3RseVxuICAgKiBvbmUgY2hpbGQg4oCUwqB0aGUgYDxzbG90PmAgZWxlbWVudC4gQnV0IHRoZSB1c2VyIGxvb2tpbmcgYXQgdGhlIHBhZ2Ugd2lsbFxuICAgKiAqc2VlKiBhbnkgbm9kZXMgZGlzdHJpYnV0ZWQgdG8gdGhhdCBzbG90LiBUbyBtYXRjaCB3aGF0IHRoZSB1c2VyIHNlZXMsIHlvdXJcbiAgICogY29tcG9uZW50IHNob3VsZCBleHBhbmQgYW55IGA8c2xvdD5gIGVsZW1lbnRzIGl0IGNvbnRhaW5zLlxuICAgKlxuICAgKiBUaGF0IGlzIHRoZSBwcm9ibGVtIHRoaXMgbWl4aW4gc29sdmVzLiBBZnRlciBhcHBseWluZyB0aGlzIG1peGluLCB5b3VyXG4gICAqIGNvbXBvbmVudCBjb2RlIGhhcyBhY2Nlc3MgdG8gYHRoaXMuZGlzdHJpYnV0ZWRDaGlsZHJlbmAsIHdob3NlIGBsZW5ndGhgXG4gICAqIHdpbGwgcmV0dXJuIHRoZSB0b3RhbCBudW1iZXIgb2YgYWxsIGNoaWxkcmVuIGRpc3RyaWJ1dGVkIHRvIHlvdXIgY29tcG9uZW50XG4gICAqIGluIHRoZSBjb21wb3NlZCB0cmVlLlxuICAgKlxuICAgKiBOb3RlOiBUaGUgbGF0ZXN0IEN1c3RvbSBFbGVtZW50cyBBUEkgZGVzaWduIGNhbGxzIGZvciBhIG5ldyBmdW5jdGlvbixcbiAgICogYGdldEFzc2lnbmVkTm9kZXNgIHRoYXQgdGFrZXMgYW4gb3B0aW9uYWwgYGRlZXBgIHBhcmFtZXRlciwgdGhhdCB3aWxsIHNvbHZlXG4gICAqIHRoaXMgcHJvYmxlbSBhdCB0aGUgQVBJIGxldmVsLlxuICAgKi9cbiAgY2xhc3MgRGlzdHJpYnV0ZWRDaGlsZHJlbiBleHRlbmRzIGJhc2Uge1xuXG4gICAgLyoqXG4gICAgICogQW4gaW4tb3JkZXIgY29sbGVjdGlvbiBvZiBkaXN0cmlidXRlZCBjaGlsZHJlbiwgZXhwYW5kaW5nIGFueSBzbG90XG4gICAgICogZWxlbWVudHMuIExpa2UgdGhlIHN0YW5kYXJkIGNoaWxkcmVuIHByb3BlcnR5LCB0aGlzIHNraXBzIHRleHQgbm9kZXMuXG4gICAgICpcbiAgICAgKiBAdHlwZSB7SFRNTEVsZW1lbnRbXX1cbiAgICAgKi9cbiAgICBnZXQgZGlzdHJpYnV0ZWRDaGlsZHJlbigpIHtcbiAgICAgIHJldHVybiBleHBhbmRDb250ZW50RWxlbWVudHModGhpcy5jaGlsZHJlbiwgZmFsc2UpO1xuICAgIH1cblxuICAgIC8qKlxuICAgICAqIEFuIGluLW9yZGVyIGNvbGxlY3Rpb24gb2YgZGlzdHJpYnV0ZWQgY2hpbGQgbm9kZXMsIGV4cGFuZGluZyBhbnkgc2xvdFxuICAgICAqIGVsZW1lbnRzLiBMaWtlIHRoZSBzdGFuZGFyZCBjaGlsZE5vZGVzIHByb3BlcnR5LCB0aGlzIGluY2x1ZGVzIHRleHRcbiAgICAgKiBub2Rlcy5cbiAgICAgKlxuICAgICAqIEB0eXBlIHtOb2RlW119XG4gICAgICovXG4gICAgZ2V0IGRpc3RyaWJ1dGVkQ2hpbGROb2RlcygpIHtcbiAgICAgIHJldHVybiBleHBhbmRDb250ZW50RWxlbWVudHModGhpcy5jaGlsZE5vZGVzLCB0cnVlKTtcbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBUaGUgY29uY2F0ZW5hdGVkIHRleHQgY29udGVudCBvZiBhbGwgZGlzdHJpYnV0ZWQgY2hpbGQgbm9kZXMsIGV4cGFuZGluZ1xuICAgICAqIGFueSBzbG90IGVsZW1lbnRzLlxuICAgICAqXG4gICAgICogQHR5cGUge3N0cmluZ31cbiAgICAgKi9cbiAgICBnZXQgZGlzdHJpYnV0ZWRUZXh0Q29udGVudCgpIHtcbiAgICAgIGNvbnN0IHN0cmluZ3MgPSB0aGlzLmRpc3RyaWJ1dGVkQ2hpbGROb2Rlcy5tYXAoZnVuY3Rpb24oY2hpbGQpIHtcbiAgICAgICAgcmV0dXJuIGNoaWxkLnRleHRDb250ZW50O1xuICAgICAgfSk7XG4gICAgICByZXR1cm4gc3RyaW5ncy5qb2luKCcnKTtcbiAgICB9XG5cbiAgfVxuXG4gIHJldHVybiBEaXN0cmlidXRlZENoaWxkcmVuO1xufTtcblxuXG4vKlxuICogR2l2ZW4gYSBhcnJheSBvZiBub2RlcywgcmV0dXJuIGEgbmV3IGFycmF5IHdpdGggYW55IGNvbnRlbnQgZWxlbWVudHMgZXhwYW5kZWRcbiAqIHRvIHRoZSBub2RlcyBkaXN0cmlidXRlZCB0byB0aGF0IGNvbnRlbnQgZWxlbWVudC4gVGhpcyBydWxlIGlzIGFwcGxpZWRcbiAqIHJlY3Vyc2l2ZWx5LlxuICpcbiAqIElmIGluY2x1ZGVUZXh0Tm9kZXMgaXMgdHJ1ZSwgdGV4dCBub2RlcyB3aWxsIGJlIGluY2x1ZGVkLCBhcyBpbiB0aGVcbiAqIHN0YW5kYXJkIGNoaWxkTm9kZXMgcHJvcGVydHk7IGJ5IGRlZmF1bHQsIHRoaXMgc2tpcHMgdGV4dCBub2RlcywgbGlrZSB0aGVcbiAqIHN0YW5kYXJkIGNoaWxkcmVuIHByb3BlcnR5LlxuICovXG5mdW5jdGlvbiBleHBhbmRDb250ZW50RWxlbWVudHMobm9kZXMsIGluY2x1ZGVUZXh0Tm9kZXMpIHtcbiAgY29uc3QgZXhwYW5kZWQgPSBBcnJheS5wcm90b3R5cGUubWFwLmNhbGwobm9kZXMsIG5vZGUgPT4ge1xuICAgIC8vIFdlIHdhbnQgdG8gc2VlIGlmIHRoZSBub2RlIGlzIGFuIGluc3RhbmNlb2YgSFRNTFNsb3RFTGVtZW50LCBidXRcbiAgICAvLyB0aGF0IGNsYXNzIHdvbid0IGV4aXN0IGlmIHRoZSBicm93c2VyIHRoYXQgZG9lc24ndCBzdXBwb3J0IG5hdGl2ZVxuICAgIC8vIFNoYWRvdyBET00gYW5kIGlmIHRoZSBTaGFkb3cgRE9NIHBvbHlmaWxsIGhhc24ndCBiZWVuIGxvYWRlZC4gSW5zdGVhZCxcbiAgICAvLyB3ZSBkbyBhIHNpbXBsaXN0aWMgY2hlY2sgdG8gc2VlIGlmIHRoZSB0YWcgbmFtZSBpcyBcInNsb3RcIi5cbiAgICBjb25zdCBpc1Nsb3QgPSB0eXBlb2YgSFRNTFNsb3RFbGVtZW50ICE9PSAndW5kZWZpbmVkJyA/XG4gICAgICBub2RlIGluc3RhbmNlb2YgSFRNTFNsb3RFbGVtZW50IDpcbiAgICAgIG5vZGUubG9jYWxOYW1lID09PSAnc2xvdCc7XG4gICAgaWYgKGlzU2xvdCkge1xuICAgICAgLy8gVXNlIHRoZSBub2RlcyBhc3NpZ25lZCB0byB0aGlzIG5vZGUgaW5zdGVhZC5cbiAgICAgIGNvbnN0IGFzc2lnbmVkTm9kZXMgPSBub2RlLmFzc2lnbmVkTm9kZXMoeyBmbGF0dGVuOiB0cnVlIH0pO1xuICAgICAgcmV0dXJuIGFzc2lnbmVkTm9kZXMgP1xuICAgICAgICBleHBhbmRDb250ZW50RWxlbWVudHMoYXNzaWduZWROb2RlcywgaW5jbHVkZVRleHROb2RlcykgOlxuICAgICAgICBbXTtcbiAgICB9IGVsc2UgaWYgKG5vZGUgaW5zdGFuY2VvZiBIVE1MRWxlbWVudCkge1xuICAgICAgLy8gUGxhaW4gZWxlbWVudDsgdXNlIGFzIGlzLlxuICAgICAgcmV0dXJuIFtub2RlXTtcbiAgICB9IGVsc2UgaWYgKG5vZGUgaW5zdGFuY2VvZiBUZXh0ICYmIGluY2x1ZGVUZXh0Tm9kZXMpIHtcbiAgICAgIC8vIFRleHQgbm9kZS5cbiAgICAgIHJldHVybiBbbm9kZV07XG4gICAgfSBlbHNlIHtcbiAgICAgIC8vIENvbW1lbnQsIHByb2Nlc3NpbmcgaW5zdHJ1Y3Rpb24sIGV0Yy47IHNraXAuXG4gICAgICByZXR1cm4gW107XG4gICAgfVxuICB9KTtcbiAgY29uc3QgZmxhdHRlbmVkID0gW10uY29uY2F0KC4uLmV4cGFuZGVkKTtcbiAgcmV0dXJuIGZsYXR0ZW5lZDtcbn1cbiIsImltcG9ydCBjcmVhdGVTeW1ib2wgZnJvbSAnLi9jcmVhdGVTeW1ib2wnO1xuaW1wb3J0IHNhZmVBdHRyaWJ1dGVzIGZyb20gJy4vc2FmZUF0dHJpYnV0ZXMnO1xuaW1wb3J0IHN5bWJvbHMgZnJvbSAnLi9zeW1ib2xzJztcblxuXG4vLyBTeW1ib2xzIGZvciBwcml2YXRlIGRhdGEgbWVtYmVycyBvbiBhbiBlbGVtZW50LlxuY29uc3QgZ2VuZXJpY1N5bWJvbCA9IGNyZWF0ZVN5bWJvbCgnZ2VuZXJpYycpO1xuXG5cbi8qIEV4cG9ydGVkIGZ1bmN0aW9uIGV4dGVuZHMgYSBiYXNlIGNsYXNzIHdpdGggR2VuZXJpYy4gKi9cbmV4cG9ydCBkZWZhdWx0IChiYXNlKSA9PiB7XG5cbiAgLyoqXG4gICAqIE1peGluIHdoaWNoIGFsbG93cyBhIGNvbXBvbmVudCB0byBzdXBwb3J0IGEgXCJnZW5lcmljXCIgc3R5bGU6IGEgbWluaW1hbGlzdFxuICAgKiBzdHlsZSB0aGF0IGNhbiBlYXNpbHkgYmUgcmVtb3ZlZCB0byByZXNldCBpdHMgdmlzdWFsIGFwcGVhcmFuY2UgdG8gYVxuICAgKiBiYXNlbGluZSBzdGF0ZS5cbiAgICpcbiAgICogQnkgZGVmYXVsdCwgYSBjb21wb25lbnQgc2hvdWxkIHByb3ZpZGUgYSBtaW5pbWFsIHZpc3VhbCBwcmVzZW50YXRpb24gdGhhdFxuICAgKiBhbGxvd3MgdGhlIGNvbXBvbmVudCB0byBmdW5jdGlvbi4gSG93ZXZlciwgdGhlIG1vcmUgc3R5bGluZyB0aGUgY29tcG9uZW50XG4gICAqIHByb3ZpZGVzIGJ5IGRlZmF1bHQsIHRoZSBoYXJkZXIgaXQgYmVjb21lcyB0byBnZXQgdGhlIGNvbXBvbmVudCB0byBmaXQgaW5cbiAgICogaW4gb3RoZXIgc2V0dGluZ3MuIEVhY2ggQ1NTIHJ1bGUgaGFzIHRvIGJlIG92ZXJyaWRkZW4uIFdvcnNlLCBuZXcgQ1NTIHJ1bGVzXG4gICAqIGFkZGVkIHRvIHRoZSBkZWZhdWx0IHN0eWxlIHdvbid0IGJlIG92ZXJyaWRkZW4gYnkgZGVmYXVsdCwgbWFraW5nIGl0IGhhcmRcbiAgICogdG8ga25vdyB3aGV0aGVyIGEgbmV3IHZlcnNpb24gb2YgYSBjb21wb25lbnQgd2lsbCBzdGlsbCBsb29rIG9rYXkuXG4gICAqXG4gICAqIEFzIGEgY29tcHJvbWlzZSwgdGhlIG1peGluIGRlZmluZXMgYSBgZ2VuZXJpY2AgYXR0cmlidXRlLiBUaGlzIGF0dHJpYnV0ZSBpc1xuICAgKiBub3JtYWxseSBzZXQgYnkgZGVmYXVsdCwgYW5kIHN0eWxlcyBjYW4gYmUgd3JpdHRlbiB0aGF0IGFwcGx5IG9ubHkgd2hlbiB0aGVcbiAgICogZ2VuZXJpYyBhdHRyaWJ1dGUgaXMgc2V0LiBUaGlzIGFsbG93cyB0aGUgY29uc3RydWN0aW9uIG9mIENTUyBydWxlcyB0aGF0XG4gICAqIHdpbGwgb25seSBhcHBseSB0byBnZW5lcmljIGNvbXBvbmVudHMgbGlrZTpcbiAgICpcbiAgICogICAgIDpob3N0KFtnZW5lcmljPVwiXCJdKSB7XG4gICAqICAgICAgIC4uLiBnZW5lcmljIGFwcGVhcmFuY2UgZGVmaW5lZCBoZXJlIC4uLlxuICAgKiAgICAgfVxuICAgKlxuICAgKiBUaGlzIG1ha2VzIGl0IGVhc3kgdG8gcmVtb3ZlIGFsbCBkZWZhdWx0IHN0eWxpbmcg4oCUIHNldCB0aGUgYEdlbmVyaWNNaXhpbmBcbiAgICogYXR0cmlidXRlIHRvIGZhbHNlLCBhbmQgYWxsIGRlZmF1bHQgc3R5bGluZyB3aWxsIGJlIHJlbW92ZWQuXG4gICAqL1xuICBjbGFzcyBHZW5lcmljIGV4dGVuZHMgYmFzZSB7XG5cbiAgICBjb25zdHJ1Y3RvcigpIHtcbiAgICAgIHN1cGVyKCk7XG4gICAgICAvLyBTZXQgZGVmYXVsdHMuXG4gICAgICBpZiAodHlwZW9mIHRoaXMuZ2VuZXJpYyA9PT0gJ3VuZGVmaW5lZCcpIHtcbiAgICAgICAgdGhpcy5nZW5lcmljID0gdGhpc1tzeW1ib2xzLmRlZmF1bHRzXS5nZW5lcmljO1xuICAgICAgfVxuICAgIH1cblxuICAgIC8vIFRoaXMgbWl4aW4gZG9lc24ndCBhY3R1YWxseSByZXNwb25kIHRvIGF0dHJpYnV0ZSBjaGFuZ2VzLCBidXQgcmVsaWVzXG4gICAgLy8gb24gc2VwYXJhdGVseS1kZWZpbmVkIGJlaGF2aW9yIChlLmcuLCBpbiBBdHRyaWJ1dGVNYXJzaGFsbGluZ01peGluKSBmb3IgdGhhdC5cbiAgICAvLyBTdGlsbCwgd2UgbmVlZCBkZWZpbmUgYSBiYXNlbGluZSBhdHRyaWJ1dGVDaGFuZ2VkQ2FsbGJhY2sgdGhhdCBkb2VzXG4gICAgLy8gbm90aGluZywgaW4gY2FzZSB0aGlzIG1peGluIGdldHMgdXNlZCBvbiBpdHMgb3duLlxuICAgIGF0dHJpYnV0ZUNoYW5nZWRDYWxsYmFjayhuYW1lLCBvbGRWYWx1ZSwgbmV3VmFsdWUpIHtcbiAgICAgIGlmIChzdXBlci5hdHRyaWJ1dGVDaGFuZ2VkQ2FsbGJhY2spIHsgc3VwZXIuYXR0cmlidXRlQ2hhbmdlZENhbGxiYWNrKG5hbWUsIG9sZFZhbHVlLCBuZXdWYWx1ZSk7IH1cbiAgICB9XG5cbiAgICBjb25uZWN0ZWRDYWxsYmFjaygpIHtcbiAgICAgIGlmIChzdXBlci5jb25uZWN0ZWRDYWxsYmFjaykgeyBzdXBlci5jb25uZWN0ZWRDYWxsYmFjaygpOyB9XG4gICAgICBzYWZlQXR0cmlidXRlcy5jb25uZWN0ZWQodGhpcyk7XG4gICAgfVxuXG4gICAgZ2V0IFtzeW1ib2xzLmRlZmF1bHRzXSgpIHtcbiAgICAgIGNvbnN0IGRlZmF1bHRzID0gc3VwZXJbc3ltYm9scy5kZWZhdWx0c10gfHwge307XG4gICAgICBkZWZhdWx0cy5nZW5lcmljID0gdHJ1ZTtcbiAgICAgIHJldHVybiBkZWZhdWx0cztcbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBUcnVlIGlmIHRoZSBjb21wb25lbnQgd291bGQgbGlrZSB0byByZWNlaXZlIGdlbmVyaWMgc3R5bGluZy5cbiAgICAgKlxuICAgICAqIFRoaXMgcHJvcGVydHkgaXMgdHJ1ZSBieSBkZWZhdWx0IOKAlMKgc2V0IGl0IHRvIGZhbHNlIHRvIHR1cm4gb2ZmIGFsbFxuICAgICAqIGdlbmVyaWMgc3R5bGVzLiBUaGlzIG1ha2VzIGl0IGVhc2llciB0byBhcHBseSBjdXN0b20gc3R5bGluZzsgeW91IHdvbid0XG4gICAgICogaGF2ZSB0byBleHBsaWNpdGx5IG92ZXJyaWRlIHN0eWxpbmcgeW91IGRvbid0IHdhbnQuXG4gICAgICpcbiAgICAgKiBAdHlwZSBCb29sZWFuXG4gICAgICogQGRlZmF1bHQgdHJ1ZVxuICAgICAqL1xuICAgIGdldCBnZW5lcmljKCkge1xuICAgICAgcmV0dXJuIHRoaXNbZ2VuZXJpY1N5bWJvbF07XG4gICAgfVxuICAgIHNldCBnZW5lcmljKHZhbHVlKSB7XG4gICAgICBjb25zdCBwYXJzZWQgPSB0eXBlb2YgdmFsdWUgPT09ICdzdHJpbmcnID9cbiAgICAgICAgU3RyaW5nKHZhbHVlKSAhPT0gJ2ZhbHNlJyA6XG4gICAgICAgIHZhbHVlO1xuICAgICAgdGhpc1tnZW5lcmljU3ltYm9sXSA9IHBhcnNlZDtcblxuICAgICAgaWYgKCdnZW5lcmljJyBpbiBiYXNlLnByb3RvdHlwZSkgeyBzdXBlci5nZW5lcmljID0gdmFsdWU7IH1cblxuICAgICAgLy8gV2Ugcm9sbCBvdXIgb3duIGF0dHJpYnV0ZSBzZXR0aW5nIHNvIHRoYXQgYW4gZXhwbGljaXRseSBmYWxzZSB2YWx1ZVxuICAgICAgLy8gc2hvd3MgdXAgYXMgR2VuZXJpY01peGluPVwiZmFsc2VcIi5cbiAgICAgIGlmIChwYXJzZWQgPT09IGZhbHNlKSB7XG4gICAgICAgIC8vIEV4cGxpY2l0bHkgdXNlIGZhbHNlIHN0cmluZy5cbiAgICAgICAgc2FmZUF0dHJpYnV0ZXMuc2V0QXR0cmlidXRlKHRoaXMsICdnZW5lcmljJywgJ2ZhbHNlJyk7XG4gICAgICB9IGVsc2UgaWYgKHBhcnNlZCA9PSBudWxsKSB7XG4gICAgICAgIC8vIEV4cGxpY2l0bHkgcmVtb3ZlIGF0dHJpYnV0ZS4gKEFsd2F5cyBzYWZlIHRvIGRvIHRoaXMuKVxuICAgICAgICB0aGlzLnJlbW92ZUF0dHJpYnV0ZSgnZ2VuZXJpYycpO1xuICAgICAgfSBlbHNlIHtcbiAgICAgICAgLy8gVXNlIHRoZSBlbXB0eSBzdHJpbmcgdG8gZ2V0IGF0dHJpYnV0ZSB0byBhcHBlYXIgd2l0aCBubyB2YWx1ZS5cbiAgICAgICAgc2FmZUF0dHJpYnV0ZXMuc2V0QXR0cmlidXRlKHRoaXMsICdnZW5lcmljJywgJycpO1xuICAgICAgfVxuICAgIH1cblxuICB9XG5cbiAgcmV0dXJuIEdlbmVyaWM7XG59O1xuXG5cbiIsImltcG9ydCBjcmVhdGVTeW1ib2wgZnJvbSAnLi9jcmVhdGVTeW1ib2wnO1xuaW1wb3J0IHN5bWJvbHMgZnJvbSAnLi9zeW1ib2xzJztcblxuXG4vLyBTeW1ib2xzIGZvciBwcml2YXRlIGRhdGEgbWVtYmVycyBvbiBhbiBlbGVtZW50LlxuY29uc3QgbmF2aWdhdGlvbkF4aXNTeW1ib2wgPSBjcmVhdGVTeW1ib2woJ25hdmlnYXRpb25BeGlzJyk7XG5cblxuLyogRXhwb3J0ZWQgZnVuY3Rpb24gZXh0ZW5kcyBhIGJhc2UgY2xhc3Mgd2l0aCBLZXlib2FyZERpcmVjdGlvbi4gKi9cbmV4cG9ydCBkZWZhdWx0IChiYXNlKSA9PiB7XG5cbiAgLyoqXG4gICAqIE1peGluIHdoaWNoIG1hcHMgZGlyZWN0aW9uIGtleXMgKExlZnQsIFJpZ2h0LCBldGMuKSB0byBkaXJlY3Rpb24gc2VtYW50aWNzXG4gICAqIChnbyBsZWZ0LCBnbyByaWdodCwgZXRjLikuXG4gICAqXG4gICAqIFRoaXMgbWl4aW4gZXhwZWN0cyB0aGUgY29tcG9uZW50IHRvIGludm9rZSBhIGBrZXlkb3duYCBtZXRob2Qgd2hlbiBhIGtleSBpc1xuICAgKiBwcmVzc2VkLiBZb3UgY2FuIHVzZSBbS2V5Ym9hcmRNaXhpbl0oS2V5Ym9hcmRNaXhpbi5tZCkgZm9yIHRoYXRcbiAgICogcHVycG9zZSwgb3Igd2lyZSB1cCB5b3VyIG93biBrZXlib2FyZCBoYW5kbGluZyBhbmQgY2FsbCBga2V5ZG93bmAgeW91cnNlbGYuXG4gICAqXG4gICAqIFRoaXMgbWl4aW4gY2FsbHMgbWV0aG9kcyBzdWNoIGFzIGBnb0xlZnRgIGFuZCBgZ29SaWdodGAuIFlvdSBjYW4gZGVmaW5lXG4gICAqIHdoYXQgdGhhdCBtZWFucyBieSBpbXBsZW1lbnRpbmcgdGhvc2UgbWV0aG9kcyB5b3Vyc2VsZi4gSWYgeW91IHdhbnQgdG8gdXNlXG4gICAqIGRpcmVjdGlvbiBrZXlzIHRvIG5hdmlnYXRlIGEgc2VsZWN0aW9uLCB1c2UgdGhpcyBtaXhpbiB3aXRoXG4gICAqIFtEaXJlY3Rpb25TZWxlY3Rpb25NaXhpbl0oRGlyZWN0aW9uU2VsZWN0aW9uTWl4aW4ubWQpLlxuICAgKi9cbiAgY2xhc3MgS2V5Ym9hcmREaXJlY3Rpb24gZXh0ZW5kcyBiYXNlIHtcblxuICAgIGNvbnN0cnVjdG9yKCkge1xuICAgICAgc3VwZXIoKTtcbiAgICAgIC8vIFNldCBkZWZhdWx0cy5cbiAgICAgIGlmICh0eXBlb2YgdGhpcy5uYXZpZ2F0aW9uQXhpcyA9PT0gJ3VuZGVmaW5lZCcpIHtcbiAgICAgICAgdGhpcy5uYXZpZ2F0aW9uQXhpcyA9IHRoaXNbc3ltYm9scy5kZWZhdWx0c10ubmF2aWdhdGlvbkF4aXM7XG4gICAgICB9XG4gICAgfVxuXG4gICAgZ2V0IFtzeW1ib2xzLmRlZmF1bHRzXSgpIHtcbiAgICAgIGNvbnN0IGRlZmF1bHRzID0gc3VwZXJbc3ltYm9scy5kZWZhdWx0c10gfHwge307XG4gICAgICBkZWZhdWx0cy5uYXZpZ2F0aW9uQXhpcyA9ICdib3RoJztcbiAgICAgIHJldHVybiBkZWZhdWx0cztcbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBJbnZva2VkIHdoZW4gdGhlIHVzZXIgd2FudHMgdG8gZ28vbmF2aWdhdGUgZG93bi5cbiAgICAgKiBUaGUgZGVmYXVsdCBpbXBsZW1lbnRhdGlvbiBvZiB0aGlzIG1ldGhvZCBkb2VzIG5vdGhpbmcuXG4gICAgICovXG4gICAgW3N5bWJvbHMuZ29Eb3duXSgpIHtcbiAgICAgIGlmIChzdXBlcltzeW1ib2xzLmdvRG93bl0pIHsgcmV0dXJuIHN1cGVyW3N5bWJvbHMuZ29Eb3duXSgpOyB9XG4gICAgfVxuXG4gICAgLyoqXG4gICAgICogSW52b2tlZCB3aGVuIHRoZSB1c2VyIHdhbnRzIHRvIGdvL25hdmlnYXRlIHRvIHRoZSBlbmQgKGUuZy4sIG9mIGEgbGlzdCkuXG4gICAgICogVGhlIGRlZmF1bHQgaW1wbGVtZW50YXRpb24gb2YgdGhpcyBtZXRob2QgZG9lcyBub3RoaW5nLlxuICAgICAqL1xuICAgIFtzeW1ib2xzLmdvRW5kXSgpIHtcbiAgICAgIGlmIChzdXBlcltzeW1ib2xzLmdvRW5kXSkgeyByZXR1cm4gc3VwZXJbc3ltYm9scy5nb0VuZF0oKTsgfVxuICAgIH1cblxuICAgIC8qKlxuICAgICAqIEludm9rZWQgd2hlbiB0aGUgdXNlciB3YW50cyB0byBnby9uYXZpZ2F0ZSBsZWZ0LlxuICAgICAqIFRoZSBkZWZhdWx0IGltcGxlbWVudGF0aW9uIG9mIHRoaXMgbWV0aG9kIGRvZXMgbm90aGluZy5cbiAgICAgKi9cbiAgICBbc3ltYm9scy5nb0xlZnRdKCkge1xuICAgICAgaWYgKHN1cGVyW3N5bWJvbHMuZ29MZWZ0XSkgeyByZXR1cm4gc3VwZXJbc3ltYm9scy5nb0xlZnRdKCk7IH1cbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBJbnZva2VkIHdoZW4gdGhlIHVzZXIgd2FudHMgdG8gZ28vbmF2aWdhdGUgcmlnaHQuXG4gICAgICogVGhlIGRlZmF1bHQgaW1wbGVtZW50YXRpb24gb2YgdGhpcyBtZXRob2QgZG9lcyBub3RoaW5nLlxuICAgICAqL1xuICAgIFtzeW1ib2xzLmdvUmlnaHRdKCkge1xuICAgICAgaWYgKHN1cGVyW3N5bWJvbHMuZ29SaWdodF0pIHsgcmV0dXJuIHN1cGVyW3N5bWJvbHMuZ29SaWdodF0oKTsgfVxuICAgIH1cblxuICAgIC8qKlxuICAgICAqIEludm9rZWQgd2hlbiB0aGUgdXNlciB3YW50cyB0byBnby9uYXZpZ2F0ZSB0byB0aGUgc3RhcnQgKGUuZy4sIG9mIGFcbiAgICAgKiBsaXN0KS4gVGhlIGRlZmF1bHQgaW1wbGVtZW50YXRpb24gb2YgdGhpcyBtZXRob2QgZG9lcyBub3RoaW5nLlxuICAgICAqL1xuICAgIFtzeW1ib2xzLmdvU3RhcnRdKCkge1xuICAgICAgaWYgKHN1cGVyW3N5bWJvbHMuZ29TdGFydF0pIHsgcmV0dXJuIHN1cGVyW3N5bWJvbHMuZ29TdGFydF0oKTsgfVxuICAgIH1cblxuICAgIC8qKlxuICAgICAqIEludm9rZWQgd2hlbiB0aGUgdXNlciB3YW50cyB0byBnby9uYXZpZ2F0ZSB1cC5cbiAgICAgKiBUaGUgZGVmYXVsdCBpbXBsZW1lbnRhdGlvbiBvZiB0aGlzIG1ldGhvZCBkb2VzIG5vdGhpbmcuXG4gICAgICovXG4gICAgW3N5bWJvbHMuZ29VcF0oKSB7XG4gICAgICBpZiAoc3VwZXJbc3ltYm9scy5nb1VwXSkgeyByZXR1cm4gc3VwZXJbc3ltYm9scy5nb1VwXSgpOyB9XG4gICAgfVxuXG4gICAgLyoqXG4gICAgICogSW5kaWNhdGVzIHRoZSBkaXJlY3Rpb24gb2YgcGVybWl0dGVkIG5hdmlnYXRpb24gd2l0aCB0aGUga2V5Ym9hcmQuXG4gICAgICpcbiAgICAgKiBBY2NlcHRlZCB2YWx1ZXMgYXJlIFwiaG9yaXpvbnRhbFwiLCBcInZlcnRpY2FsXCIsIG9yIFwiYm90aFwiICh0aGUgZGVmYXVsdCkuXG4gICAgICogSWYgdGhpcyBwcm9wZXJ0eSBpcyBcImhvcml6b250YWxcIiwgdGhlIFVwIEFycm93IGFuZCBEb3duIEFycm93IGtleXMgd2lsbFxuICAgICAqIGJlIGlnbm9yZWQuIENvbnZlcnNlbHksIGlmIHRoaXMgaXMgXCJ2ZXJ0aWNhbFwiLCB0aGUgTGVmdCBBcnJvdyBhbmQgUmlnaHRcbiAgICAgKiBBcnJvdyBrZXlzIHdpbGwgYmUgaWdub3JlZC5cbiAgICAgKlxuICAgICAqIEB0eXBlIHtzdHJpbmd9XG4gICAgICovXG4gICAgZ2V0IG5hdmlnYXRpb25BeGlzKCkge1xuICAgICAgcmV0dXJuIHRoaXNbbmF2aWdhdGlvbkF4aXNTeW1ib2xdO1xuICAgIH1cbiAgICBzZXQgbmF2aWdhdGlvbkF4aXModmFsdWUpIHtcbiAgICAgIHRoaXNbbmF2aWdhdGlvbkF4aXNTeW1ib2xdID0gdmFsdWU7XG4gICAgICBpZiAoJ25hdmlnYXRpb25BeGlzJyBpbiBiYXNlLnByb3RvdHlwZSkgeyBzdXBlci5uYXZpZ2F0aW9uQXhpcyA9IHZhbHVlOyB9XG4gICAgfVxuXG4gICAgW3N5bWJvbHMua2V5ZG93bl0oZXZlbnQpIHtcbiAgICAgIGxldCBoYW5kbGVkO1xuXG4gICAgICBjb25zdCBheGlzID0gdGhpcy5uYXZpZ2F0aW9uQXhpcztcbiAgICAgIGNvbnN0IGhvcml6b250YWwgPSAoYXhpcyA9PT0gJ2hvcml6b250YWwnIHx8IGF4aXMgPT09ICdib3RoJyk7XG4gICAgICBjb25zdCB2ZXJ0aWNhbCA9IChheGlzID09PSAndmVydGljYWwnIHx8IGF4aXMgPT09ICdib3RoJyk7XG5cbiAgICAgIC8vIElnbm9yZSBMZWZ0L1JpZ2h0IGtleXMgd2hlbiBtZXRhS2V5IG9yIGFsdEtleSBtb2RpZmllciBpcyBhbHNvIHByZXNzZWQsXG4gICAgICAvLyBhcyB0aGUgdXNlciBtYXkgYmUgdHJ5aW5nIHRvIG5hdmlnYXRlIGJhY2sgb3IgZm9yd2FyZCBpbiB0aGUgYnJvd3Nlci5cbiAgICAgIHN3aXRjaCAoZXZlbnQua2V5Q29kZSkge1xuICAgICAgICBjYXNlIDM1OiAvLyBFbmRcbiAgICAgICAgICBoYW5kbGVkID0gdGhpc1tzeW1ib2xzLmdvRW5kXSgpO1xuICAgICAgICAgIGJyZWFrO1xuICAgICAgICBjYXNlIDM2OiAvLyBIb21lXG4gICAgICAgICAgaGFuZGxlZCA9IHRoaXNbc3ltYm9scy5nb1N0YXJ0XSgpO1xuICAgICAgICAgIGJyZWFrO1xuICAgICAgICBjYXNlIDM3OiAvLyBMZWZ0XG4gICAgICAgICAgaWYgKGhvcml6b250YWwgJiYgIWV2ZW50Lm1ldGFLZXkgJiYgIWV2ZW50LmFsdEtleSkge1xuICAgICAgICAgICAgaGFuZGxlZCA9IHRoaXNbc3ltYm9scy5nb0xlZnRdKCk7XG4gICAgICAgICAgfVxuICAgICAgICAgIGJyZWFrO1xuICAgICAgICBjYXNlIDM4OiAvLyBVcFxuICAgICAgICAgIGlmICh2ZXJ0aWNhbCkge1xuICAgICAgICAgICAgaGFuZGxlZCA9IGV2ZW50LmFsdEtleSA/IHRoaXNbc3ltYm9scy5nb1N0YXJ0XSgpIDogdGhpc1tzeW1ib2xzLmdvVXBdKCk7XG4gICAgICAgICAgfVxuICAgICAgICAgIGJyZWFrO1xuICAgICAgICBjYXNlIDM5OiAvLyBSaWdodFxuICAgICAgICAgIGlmIChob3Jpem9udGFsICYmICFldmVudC5tZXRhS2V5ICYmICFldmVudC5hbHRLZXkpIHtcbiAgICAgICAgICAgIGhhbmRsZWQgPSB0aGlzW3N5bWJvbHMuZ29SaWdodF0oKTtcbiAgICAgICAgICB9XG4gICAgICAgICAgYnJlYWs7XG4gICAgICAgIGNhc2UgNDA6IC8vIERvd25cbiAgICAgICAgICBpZiAodmVydGljYWwpIHtcbiAgICAgICAgICAgIGhhbmRsZWQgPSBldmVudC5hbHRLZXkgPyB0aGlzW3N5bWJvbHMuZ29FbmRdKCkgOiB0aGlzW3N5bWJvbHMuZ29Eb3duXSgpO1xuICAgICAgICAgIH1cbiAgICAgICAgICBicmVhaztcbiAgICAgIH1cbiAgICAgIC8vIFByZWZlciBtaXhpbiByZXN1bHQgaWYgaXQncyBkZWZpbmVkLCBvdGhlcndpc2UgdXNlIGJhc2UgcmVzdWx0LlxuICAgICAgcmV0dXJuIGhhbmRsZWQgfHwgKHN1cGVyW3N5bWJvbHMua2V5ZG93bl0gJiYgc3VwZXJbc3ltYm9scy5rZXlkb3duXShldmVudCkpO1xuICAgIH1cblxuICB9XG5cbiAgcmV0dXJuIEtleWJvYXJkRGlyZWN0aW9uO1xufTtcbiIsImltcG9ydCBzeW1ib2xzIGZyb20gJy4vc3ltYm9scyc7XG5cblxuLyogRXhwb3J0ZWQgZnVuY3Rpb24gZXh0ZW5kcyBhIGJhc2UgY2xhc3Mgd2l0aCBLZXlib2FyZC4gKi9cbmV4cG9ydCBkZWZhdWx0IChiYXNlKSA9PiB7XG5cbiAgLyoqXG4gICAqIE1peGluIHdoaWNoIG1hbmFnZXMgdGhlIGtleWRvd24gaGFuZGxpbmcgZm9yIGEgY29tcG9uZW50LlxuICAgKlxuICAgKiBUaGlzIG1peGluIGhhbmRsZXMgc2V2ZXJhbCBrZXlib2FyZC1yZWxhdGVkIGZlYXR1cmVzLlxuICAgKlxuICAgKiBGaXJzdCwgaXQgd2lyZXMgdXAgYSBzaW5nbGUga2V5ZG93biBldmVudCBoYW5kbGVyIHRoYXQgY2FuIGJlIHNoYXJlZCBieVxuICAgKiBtdWx0aXBsZSBtaXhpbnMgb24gYSBjb21wb25lbnQuIFRoZSBldmVudCBoYW5kbGVyIHdpbGwgaW52b2tlIGEgYGtleWRvd25gXG4gICAqIG1ldGhvZCB3aXRoIHRoZSBldmVudCBvYmplY3QsIGFuZCBhbnkgbWl4aW4gYWxvbmcgdGhlIHByb3RvdHlwZSBjaGFpbiB0aGF0XG4gICAqIHdhbnRzIHRvIGhhbmRsZSB0aGF0IG1ldGhvZCBjYW4gZG8gc28uXG4gICAqXG4gICAqIElmIGEgbWl4aW4gd2FudHMgdG8gaW5kaWNhdGUgdGhhdCBrZXlib2FyZCBldmVudCBoYXMgYmVlbiBoYW5kbGVkLCBhbmQgdGhhdFxuICAgKiBvdGhlciBtaXhpbnMgc2hvdWxkICpub3QqIGhhbmRsZSBpdCwgdGhlIG1peGluJ3MgYGtleWRvd25gIGhhbmRsZXIgc2hvdWxkXG4gICAqIHJldHVybiBhIHZhbHVlIG9mIHRydWUuIFRoZSBjb252ZW50aW9uIHRoYXQgc2VlbXMgdG8gd29yayB3ZWxsIGlzIHRoYXQgYVxuICAgKiBtaXhpbiBzaG91bGQgc2VlIGlmIGl0IHdhbnRzIHRvIGhhbmRsZSB0aGUgZXZlbnQgYW5kLCBpZiBub3QsIHRoZW4gYXNrIHRoZVxuICAgKiBzdXBlcmNsYXNzIHRvIHNlZSBpZiBpdCB3YW50cyB0byBoYW5kbGUgdGhlIGV2ZW50LiBUaGlzIGhhcyB0aGUgZWZmZWN0IG9mXG4gICAqIGdpdmluZyB0aGUgbWl4aW4gdGhhdCB3YXMgYXBwbGllZCBsYXN0IHRoZSBmaXJzdCBjaGFuY2UgYXQgaGFuZGxpbmcgYVxuICAgKiBrZXlib2FyZCBldmVudC5cbiAgICpcbiAgICogRXhhbXBsZTpcbiAgICpcbiAgICogICAgIFtzeW1ib2xzLmtleWRvd25dKGV2ZW50KSB7XG4gICAqICAgICAgIGxldCBoYW5kbGVkO1xuICAgKiAgICAgICBzd2l0Y2ggKGV2ZW50LmtleUNvZGUpIHtcbiAgICogICAgICAgICAvLyBIYW5kbGUgdGhlIGtleXMgeW91IHdhbnQsIHNldHRpbmcgaGFuZGxlZCA9IHRydWUgaWYgYXBwcm9wcmlhdGUuXG4gICAqICAgICAgIH1cbiAgICogICAgICAgLy8gUHJlZmVyIG1peGluIHJlc3VsdCBpZiBpdCdzIGRlZmluZWQsIG90aGVyd2lzZSB1c2UgYmFzZSByZXN1bHQuXG4gICAqICAgICAgIHJldHVybiBoYW5kbGVkIHx8IChzdXBlcltzeW1ib2xzLmtleWRvd25dICYmIHN1cGVyW3N5bWJvbHMua2V5ZG93bl0oZXZlbnQpKTtcbiAgICogICAgIH1cbiAgICpcbiAgICogQSBzZWNvbmQgZmVhdHVyZSBwcm92aWRlZCBieSB0aGlzIG1peGluIGlzIHRoYXQgaXQgaW1wbGljaXRseSBtYWtlcyB0aGVcbiAgICogY29tcG9uZW50IGEgdGFiIHN0b3AgaWYgaXQgaXNuJ3QgYWxyZWFkeSwgYnkgc2V0dGluZyBgdGFiSW5kZXhgIHRvIDAuIFRoaXNcbiAgICogaGFzIHRoZSBlZmZlY3Qgb2YgYWRkaW5nIHRoZSBjb21wb25lbnQgdG8gdGhlIHRhYiBvcmRlciBpbiBkb2N1bWVudCBvcmRlci5cbiAgICovXG4gIGNsYXNzIEtleWJvYXJkIGV4dGVuZHMgYmFzZSB7XG5cbiAgICBjb25zdHJ1Y3RvcigpIHtcbiAgICAgIHN1cGVyKCk7XG4gICAgICB0aGlzLmFkZEV2ZW50TGlzdGVuZXIoJ2tleWRvd24nLCBldmVudCA9PiB7XG4gICAgICAgIGNvbnN0IGhhbmRsZWQgPSB0aGlzW3N5bWJvbHMua2V5ZG93bl0oZXZlbnQpO1xuICAgICAgICBpZiAoaGFuZGxlZCkge1xuICAgICAgICAgIGV2ZW50LnByZXZlbnREZWZhdWx0KCk7XG4gICAgICAgICAgZXZlbnQuc3RvcFByb3BhZ2F0aW9uKCk7XG4gICAgICAgIH1cbiAgICAgIH0pO1xuICAgIH1cblxuICAgIGNvbm5lY3RlZENhbGxiYWNrKCkge1xuICAgICAgaWYgKHN1cGVyLmNvbm5lY3RlZENhbGxiYWNrKSB7IHN1cGVyLmNvbm5lY3RlZENhbGxiYWNrKCk7IH1cbiAgICAgIGlmICh0aGlzLmdldEF0dHJpYnV0ZSgndGFiaW5kZXgnKSA9PSBudWxsICYmIHRoaXNbc3ltYm9scy5kZWZhdWx0c10udGFiaW5kZXggIT09IG51bGwpIHtcbiAgICAgICAgdGhpcy5zZXRBdHRyaWJ1dGUoJ3RhYmluZGV4JywgdGhpc1tzeW1ib2xzLmRlZmF1bHRzXS50YWJpbmRleCk7XG4gICAgICB9XG4gICAgfVxuXG4gICAgZ2V0IFtzeW1ib2xzLmRlZmF1bHRzXSgpIHtcbiAgICAgIGNvbnN0IGRlZmF1bHRzID0gc3VwZXJbc3ltYm9scy5kZWZhdWx0c10gfHwge307XG4gICAgICAvLyBUaGUgZGVmYXVsdCB0YWIgaW5kZXggaXMgMCAoZG9jdW1lbnQgb3JkZXIpLlxuICAgICAgZGVmYXVsdHMudGFiaW5kZXggPSAwO1xuICAgICAgcmV0dXJuIGRlZmF1bHRzO1xuICAgIH1cblxuICAgIC8qKlxuICAgICAqIEhhbmRsZSB0aGUgaW5kaWNhdGVkIGtleWJvYXJkIGV2ZW50LlxuICAgICAqXG4gICAgICogVGhlIGRlZmF1bHQgaW1wbGVtZW50YXRpb24gb2YgdGhpcyBtZXRob2QgZG9lcyBub3RoaW5nLiBUaGlzIHdpbGxcbiAgICAgKiB0eXBpY2FsbHkgYmUgaGFuZGxlZCBieSBvdGhlciBtaXhpbnMuXG4gICAgICpcbiAgICAgKiBAcGFyYW0ge0tleWJvYXJkRXZlbnR9IGV2ZW50IC0gdGhlIGtleWJvYXJkIGV2ZW50XG4gICAgICogQHJldHVybiB7Ym9vbGVhbn0gdHJ1ZSBpZiB0aGUgZXZlbnQgd2FzIGhhbmRsZWRcbiAgICAgKi9cbiAgICBbc3ltYm9scy5rZXlkb3duXShldmVudCkge1xuICAgICAgaWYgKHN1cGVyW3N5bWJvbHMua2V5ZG93bl0pIHsgcmV0dXJuIHN1cGVyW3N5bWJvbHMua2V5ZG93bl0oZXZlbnQpOyB9XG4gICAgfVxuXG4gIH1cblxuICByZXR1cm4gS2V5Ym9hcmQ7XG59O1xuIiwiaW1wb3J0IHN5bWJvbHMgZnJvbSAnLi9zeW1ib2xzJztcblxuXG4vKiBFeHBvcnRlZCBmdW5jdGlvbiBleHRlbmRzIGEgYmFzZSBjbGFzcyB3aXRoIEtleWJvYXJkUGFnZWRTZWxlY3Rpb24uICovXG5leHBvcnQgZGVmYXVsdCAoYmFzZSkgPT4ge1xuXG4gIC8qKlxuICAgKiBNaXhpbiB3aGljaCBtYXBzIHBhZ2Uga2V5cyAoUGFnZSBVcCwgUGFnZSBEb3duKSBpbnRvIG9wZXJhdGlvbnMgdGhhdCBtb3ZlXG4gICAqIHRoZSBzZWxlY3Rpb24gYnkgb25lIHBhZ2UuXG4gICAqXG4gICAqIFRoZSBrZXlib2FyZCBpbnRlcmFjdGlvbiBtb2RlbCBnZW5lcmFsbHkgZm9sbG93cyB0aGF0IG9mIE1pY3Jvc29mdCBXaW5kb3dzJ1xuICAgKiBsaXN0IGJveGVzIGluc3RlYWQgb2YgdGhvc2UgaW4gT1MgWDpcbiAgICpcbiAgICogKiBUaGUgUGFnZSBVcC9Eb3duIGFuZCBIb21lL0VuZCBrZXlzIGFjdHVhbGx5IGNoYW5nZSB0aGUgc2VsZWN0aW9uLCByYXRoZXJcbiAgICogICB0aGFuIGp1c3Qgc2Nyb2xsaW5nLiBUaGUgZm9ybWVyIGJlaGF2aW9yIHNlZW1zIG1vcmUgZ2VuZXJhbGx5IHVzZWZ1bCBmb3JcbiAgICogICBrZXlib2FyZCB1c2Vycy5cbiAgICpcbiAgICogKiBQcmVzc2luZyBQYWdlIFVwL0Rvd24gd2lsbCBjaGFuZ2UgdGhlIHNlbGVjdGlvbiB0byB0aGUgdG9wbW9zdC9ib3R0b21tb3N0XG4gICAqICAgdmlzaWJsZSBpdGVtIGlmIHRoZSBzZWxlY3Rpb24gaXMgbm90IGFscmVhZHkgdGhlcmUuIFRoZXJlYWZ0ZXIsIHRoZSBrZXlcbiAgICogICB3aWxsIG1vdmUgdGhlIHNlbGVjdGlvbiB1cC9kb3duIGJ5IGEgcGFnZSwgYW5kIChwZXIgdGhlIGFib3ZlIHBvaW50KSBtYWtlXG4gICAqICAgdGhlIHNlbGVjdGVkIGl0ZW0gdmlzaWJsZS5cbiAgICpcbiAgICogVG8gZW5zdXJlIHRoZSBzZWxlY3RlZCBpdGVtIGlzIGluIHZpZXcgZm9sbG93aW5nIHVzZSBvZiBQYWdlIFVwL0Rvd24sIHVzZVxuICAgKiB0aGUgcmVsYXRlZCBbU2VsZWN0aW9uSW5WaWV3TWl4aW5dKFNlbGVjdGlvbkluVmlld01peGluLm1kKS5cbiAgICpcbiAgICogVGhpcyBtaXhpbiBleHBlY3RzIHRoZSBjb21wb25lbnQgdG8gaW52b2tlIGEgYGtleWRvd25gIG1ldGhvZCB3aGVuIGEga2V5IGlzXG4gICAqIHByZXNzZWQuIFlvdSBjYW4gdXNlIFtLZXlib2FyZE1peGluXShLZXlib2FyZE1peGluLm1kKSBmb3IgdGhhdFxuICAgKiBwdXJwb3NlLCBvciB3aXJlIHVwIHlvdXIgb3duIGtleWJvYXJkIGhhbmRsaW5nIGFuZCBjYWxsIGBrZXlkb3duYCB5b3Vyc2VsZi5cbiAgICovXG4gIGNsYXNzIEtleWJvYXJkUGFnZWRTZWxlY3Rpb24gZXh0ZW5kcyBiYXNlIHtcblxuICAgIFtzeW1ib2xzLmtleWRvd25dKGV2ZW50KSB7XG4gICAgICBsZXQgaGFuZGxlZDtcbiAgICAgIHN3aXRjaCAoZXZlbnQua2V5Q29kZSkge1xuICAgICAgICBjYXNlIDMzOiAvLyBQYWdlIFVwXG4gICAgICAgICAgaGFuZGxlZCA9IHRoaXMucGFnZVVwKCk7XG4gICAgICAgICAgYnJlYWs7XG4gICAgICAgIGNhc2UgMzQ6IC8vIFBhZ2UgRG93blxuICAgICAgICAgIGhhbmRsZWQgPSB0aGlzLnBhZ2VEb3duKCk7XG4gICAgICAgICAgYnJlYWs7XG4gICAgICB9XG4gICAgICAvLyBQcmVmZXIgbWl4aW4gcmVzdWx0IGlmIGl0J3MgZGVmaW5lZCwgb3RoZXJ3aXNlIHVzZSBiYXNlIHJlc3VsdC5cbiAgICAgIHJldHVybiBoYW5kbGVkIHx8IChzdXBlcltzeW1ib2xzLmtleWRvd25dICYmIHN1cGVyW3N5bWJvbHMua2V5ZG93bl0oZXZlbnQpKTtcbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBTY3JvbGwgZG93biBvbmUgcGFnZS5cbiAgICAgKi9cbiAgICBwYWdlRG93bigpIHtcbiAgICAgIGlmIChzdXBlci5wYWdlRG93bikgeyBzdXBlci5wYWdlRG93bigpOyB9XG4gICAgICByZXR1cm4gc2Nyb2xsT25lUGFnZSh0aGlzLCB0cnVlKTtcbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBTY3JvbGwgdXAgb25lIHBhZ2UuXG4gICAgICovXG4gICAgcGFnZVVwKCkge1xuICAgICAgaWYgKHN1cGVyLnBhZ2VVcCkgeyBzdXBlci5wYWdlVXAoKTsgfVxuICAgICAgcmV0dXJuIHNjcm9sbE9uZVBhZ2UodGhpcywgZmFsc2UpO1xuICAgIH1cblxuICAgIC8qKlxuICAgICAqIFRoZSBlbGVtZW50IHRoYXQgc2hvdWxkIGJlIHNjcm9sbGVkIHdpdGggdGhlIFBhZ2UgVXAvRG93biBrZXlzLlxuICAgICAqIERlZmF1bHQgaXMgdGhlIGN1cnJlbnQgZWxlbWVudC5cbiAgICAgKlxuICAgICAqIEB0eXBlIHtIVE1MRWxlbWVudH1cbiAgICAgKi9cbiAgICBnZXQgc2Nyb2xsVGFyZ2V0KCkge1xuICAgICAgLy8gUHJlZmVyIGJhc2UgcmVzdWx0LlxuICAgICAgcmV0dXJuICdzY3JvbGxUYXJnZXQnIGluIGJhc2UucHJvdG90eXBlID8gc3VwZXIuc2Nyb2xsVGFyZ2V0IDogdGhpcztcbiAgICB9XG4gICAgc2V0IHNjcm9sbFRhcmdldChlbGVtZW50KSB7XG4gICAgICBpZiAoJ3Njcm9sbFRhcmdldCcgaW4gYmFzZS5wcm90b3R5cGUpIHsgc3VwZXIuc2Nyb2xsVGFyZ2V0ID0gZWxlbWVudDsgfVxuICAgIH1cbiAgfVxuXG4gIHJldHVybiBLZXlib2FyZFBhZ2VkU2VsZWN0aW9uO1xufTtcblxuXG4vLyBSZXR1cm4gdGhlIGl0ZW0gd2hvc2UgY29udGVudCBzcGFucyB0aGUgZ2l2ZW4geSBwb3NpdGlvbiAocmVsYXRpdmUgdG8gdGhlXG4vLyB0b3Agb2YgdGhlIGxpc3QncyBzY3JvbGxpbmcgY2xpZW50IGFyZWEpLCBvciBudWxsIGlmIG5vdCBmb3VuZC5cbi8vXG4vLyBJZiBkb3dud2FyZCBpcyB0cnVlLCBtb3ZlIGRvd24gdGhlIGxpc3Qgb2YgaXRlbXMgdG8gZmluZCB0aGUgZmlyc3QgaXRlbVxuLy8gZm91bmQgYXQgdGhlIGdpdmVuIHkgcG9zaXRpb247IGlmIGRvd253YXJkIGlzIGZhbHNlLCBtb3ZlIHVwIHRoZSBsaXN0IG9mXG4vLyBpdGVtcyB0byBmaW5kIHRoZSBsYXN0IGl0ZW0gYXQgdGhhdCBwb3NpdGlvbi5cbmZ1bmN0aW9uIGdldEluZGV4T2ZJdGVtQXRZKGVsZW1lbnQsIHksIGRvd253YXJkKSB7XG4gIGNvbnN0IGl0ZW1zID0gZWxlbWVudC5pdGVtcztcbiAgY29uc3Qgc3RhcnQgPSBkb3dud2FyZCA/IDAgOiBpdGVtcy5sZW5ndGggLSAxO1xuICBjb25zdCBlbmQgPSBkb3dud2FyZCA/IGl0ZW1zLmxlbmd0aCA6IDA7XG4gIGNvbnN0IHN0ZXAgPSBkb3dud2FyZCA/IDEgOiAtMTtcbiAgY29uc3Qgc2Nyb2xsVGFyZ2V0ID0gZWxlbWVudC5zY3JvbGxUYXJnZXQ7XG4gIGNvbnN0IHRvcE9mQ2xpZW50QXJlYSA9IHNjcm9sbFRhcmdldC5vZmZzZXRUb3AgKyBzY3JvbGxUYXJnZXQuY2xpZW50VG9wO1xuXG4gIC8vIEZpbmQgdGhlIGl0ZW0gc3Bhbm5pbmcgdGhlIGluZGljYXRlZCB5IGNvb3JkaW5hdGUuXG4gIGxldCBpdGVtO1xuICBsZXQgaXRlbUluZGV4ID0gc3RhcnQ7XG4gIGxldCBpdGVtVG9wO1xuICBsZXQgZm91bmQgPSBmYWxzZTtcbiAgd2hpbGUgKGl0ZW1JbmRleCAhPT0gZW5kKSB7XG4gICAgaXRlbSA9IGl0ZW1zW2l0ZW1JbmRleF07XG4gICAgaXRlbVRvcCA9IGl0ZW0ub2Zmc2V0VG9wIC0gdG9wT2ZDbGllbnRBcmVhO1xuICAgIGNvbnN0IGl0ZW1Cb3R0b20gPSBpdGVtVG9wICsgaXRlbS5vZmZzZXRIZWlnaHQ7XG4gICAgaWYgKGl0ZW1Ub3AgPD0geSAmJiBpdGVtQm90dG9tID49IHkpIHtcbiAgICAgIC8vIEl0ZW0gc3BhbnMgdGhlIGluZGljYXRlZCB5IGNvb3JkaW5hdGUuXG4gICAgICBmb3VuZCA9IHRydWU7XG4gICAgICBicmVhaztcbiAgICB9XG4gICAgaXRlbUluZGV4ICs9IHN0ZXA7XG4gIH1cblxuICBpZiAoIWZvdW5kKSB7XG4gICAgcmV0dXJuIG51bGw7XG4gIH1cblxuICAvLyBXZSBtYXkgaGF2ZSBmb3VuZCBhbiBpdGVtIHdob3NlIHBhZGRpbmcgc3BhbnMgdGhlIGdpdmVuIHkgY29vcmRpbmF0ZSxcbiAgLy8gYnV0IHdob3NlIGNvbnRlbnQgaXMgYWN0dWFsbHkgYWJvdmUvYmVsb3cgdGhhdCBwb2ludC5cbiAgLy8gVE9ETzogSWYgdGhlIGl0ZW0gaGFzIGEgYm9yZGVyLCB0aGVuIHBhZGRpbmcgc2hvdWxkIGJlIGluY2x1ZGVkIGluXG4gIC8vIGNvbnNpZGVyaW5nIGEgaGl0LlxuICBjb25zdCBpdGVtU3R5bGUgPSBnZXRDb21wdXRlZFN0eWxlKGl0ZW0pO1xuICBjb25zdCBpdGVtUGFkZGluZ1RvcCA9IHBhcnNlRmxvYXQoaXRlbVN0eWxlLnBhZGRpbmdUb3ApO1xuICBjb25zdCBpdGVtUGFkZGluZ0JvdHRvbSA9IHBhcnNlRmxvYXQoaXRlbVN0eWxlLnBhZGRpbmdCb3R0b20pO1xuICBjb25zdCBjb250ZW50VG9wID0gaXRlbVRvcCArIGl0ZW0uY2xpZW50VG9wICsgaXRlbVBhZGRpbmdUb3A7XG4gIGNvbnN0IGNvbnRlbnRCb3R0b20gPSBjb250ZW50VG9wICsgaXRlbS5jbGllbnRIZWlnaHQgLSBpdGVtUGFkZGluZ1RvcCAtIGl0ZW1QYWRkaW5nQm90dG9tO1xuICBpZiAoZG93bndhcmQgJiYgY29udGVudFRvcCA8PSB5IHx8ICFkb3dud2FyZCAmJiBjb250ZW50Qm90dG9tID49IHkpIHtcbiAgICAvLyBUaGUgaW5kaWNhdGVkIGNvb3JkaW5hdGUgaGl0cyB0aGUgYWN0dWFsIGl0ZW0gY29udGVudC5cbiAgICByZXR1cm4gaXRlbUluZGV4O1xuICB9XG4gIGVsc2Uge1xuICAgIC8vIFRoZSBpbmRpY2F0ZWQgY29vcmRpbmF0ZSBmYWxscyB3aXRoaW4gdGhlIGl0ZW0ncyBwYWRkaW5nLiBCYWNrIHVwIHRvXG4gICAgLy8gdGhlIGl0ZW0gYmVsb3cvYWJvdmUgdGhlIGl0ZW0gd2UgZm91bmQgYW5kIHJldHVybiB0aGF0LlxuICAgIHJldHVybiBpdGVtSW5kZXggLSBzdGVwO1xuICB9XG59XG5cbi8vIE1vdmUgYnkgb25lIHBhZ2UgZG93bndhcmQgKGlmIGRvd253YXJkIGlzIHRydWUpLCBvciB1cHdhcmQgKGlmIGZhbHNlKS5cbi8vIFJldHVybiB0cnVlIGlmIHdlIGVuZGVkIHVwIGNoYW5naW5nIHRoZSBzZWxlY3Rpb24sIGZhbHNlIGlmIG5vdC5cbi8vIFRPRE86IEJldHRlciBzdXBwb3J0IGZvciBob3Jpem9udGFsIGxpc3RzLlxuZnVuY3Rpb24gc2Nyb2xsT25lUGFnZShlbGVtZW50LCBkb3dud2FyZCkge1xuXG4gIC8vIERldGVybWluZSB0aGUgaXRlbSB2aXNpYmxlIGp1c3QgYXQgdGhlIGVkZ2Ugb2YgZGlyZWN0aW9uIHdlJ3JlIGhlYWRpbmcuXG4gIC8vIFdlJ2xsIHNlbGVjdCB0aGF0IGl0ZW0gaWYgaXQncyBub3QgYWxyZWFkeSBzZWxlY3RlZC5cbiAgY29uc3Qgc2Nyb2xsVGFyZ2V0ID0gZWxlbWVudC5zY3JvbGxUYXJnZXQ7XG4gIGNvbnN0IGVkZ2UgPSBzY3JvbGxUYXJnZXQuc2Nyb2xsVG9wICsgKGRvd253YXJkID8gc2Nyb2xsVGFyZ2V0LmNsaWVudEhlaWdodCA6IDApO1xuICBjb25zdCBpbmRleE9mSXRlbUF0RWRnZSA9IGdldEluZGV4T2ZJdGVtQXRZKGVsZW1lbnQsIGVkZ2UsIGRvd253YXJkKTtcblxuICBjb25zdCBzZWxlY3RlZEluZGV4ID0gZWxlbWVudC5zZWxlY3RlZEluZGV4O1xuICBsZXQgbmV3SW5kZXg7XG4gIGlmIChpbmRleE9mSXRlbUF0RWRnZSAmJiBzZWxlY3RlZEluZGV4ID09PSBpbmRleE9mSXRlbUF0RWRnZSkge1xuICAgIC8vIFRoZSBpdGVtIGF0IHRoZSBlZGdlIHdhcyBhbHJlYWR5IHNlbGVjdGVkLCBzbyBzY3JvbGwgaW4gdGhlIGluZGljYXRlZFxuICAgIC8vIGRpcmVjdGlvbiBieSBvbmUgcGFnZS4gTGVhdmUgdGhlIG5ldyBpdGVtIGF0IHRoYXQgZWRnZSBzZWxlY3RlZC5cbiAgICBjb25zdCBkZWx0YSA9IChkb3dud2FyZCA/IDEgOiAtMSkgKiBzY3JvbGxUYXJnZXQuY2xpZW50SGVpZ2h0O1xuICAgIG5ld0luZGV4ID0gZ2V0SW5kZXhPZkl0ZW1BdFkoZWxlbWVudCwgZWRnZSArIGRlbHRhLCBkb3dud2FyZCk7XG4gIH1cbiAgZWxzZSB7XG4gICAgLy8gVGhlIGl0ZW0gYXQgdGhlIGVkZ2Ugd2Fzbid0IHNlbGVjdGVkIHlldC4gSW5zdGVhZCBvZiBzY3JvbGxpbmcsIHdlJ2xsXG4gICAgLy8ganVzdCBzZWxlY3QgdGhhdCBpdGVtLiBUaGF0IGlzLCB0aGUgZmlyc3QgYXR0ZW1wdCB0byBwYWdlIHVwL2Rvd25cbiAgICAvLyB1c3VhbGx5IGp1c3QgbW92ZXMgdGhlIHNlbGVjdGlvbiB0byB0aGUgZWRnZSBpbiB0aGF0IGRpcmVjdGlvbi5cbiAgICBuZXdJbmRleCA9IGluZGV4T2ZJdGVtQXRFZGdlO1xuICB9XG5cbiAgaWYgKCFuZXdJbmRleCkge1xuICAgIC8vIFdlIGNhbid0IGZpbmQgYW4gaXRlbSBpbiB0aGUgZGlyZWN0aW9uIHdlIHdhbnQgdG8gdHJhdmVsLiBTZWxlY3QgdGhlXG4gICAgLy8gbGFzdCBpdGVtIChpZiBtb3ZpbmcgZG93bndhcmQpIG9yIGZpcnN0IGl0ZW0gKGlmIG1vdmluZyB1cHdhcmQpLlxuICAgIG5ld0luZGV4ID0gKGRvd253YXJkID8gZWxlbWVudC5pdGVtcy5sZW5ndGggLSAxIDogMCk7XG4gIH1cblxuICBpZiAobmV3SW5kZXggIT09IHNlbGVjdGVkSW5kZXgpIHtcbiAgICBlbGVtZW50LnNlbGVjdGVkSW5kZXggPSBuZXdJbmRleDtcbiAgICByZXR1cm4gdHJ1ZTsgLy8gV2UgaGFuZGxlZCB0aGUgcGFnZSB1cC9kb3duIG91cnNlbHZlcy5cbiAgfVxuICBlbHNlIHtcbiAgICByZXR1cm4gZmFsc2U7IC8vIFdlIGRpZG4ndCBkbyBhbnl0aGluZy5cbiAgfVxufVxuIiwiaW1wb3J0IGNyZWF0ZVN5bWJvbCBmcm9tICcuL2NyZWF0ZVN5bWJvbCc7XG5pbXBvcnQgc3ltYm9scyBmcm9tICcuL3N5bWJvbHMnO1xuXG5cbi8vIFN5bWJvbHMgZm9yIHByaXZhdGUgZGF0YSBtZW1iZXJzIG9uIGFuIGVsZW1lbnQuXG5jb25zdCBpdGVtVGV4dENvbnRlbnRzU3ltYm9sID0gY3JlYXRlU3ltYm9sKCdpdGVtVGV4dENvbnRlbnRzJyk7XG5jb25zdCB0eXBlZFByZWZpeFN5bWJvbCA9IGNyZWF0ZVN5bWJvbCgndHlwZWRQcmVmaXgnKTtcbmNvbnN0IHByZWZpeFRpbWVvdXRTeW1ib2wgPSBjcmVhdGVTeW1ib2woJ3ByZWZpeFRpbWVvdXQnKTtcblxuXG4vKiBFeHBvcnRlZCBmdW5jdGlvbiBleHRlbmRzIGEgYmFzZSBjbGFzcyB3aXRoIEtleWJvYXJkUHJlZml4U2VsZWN0aW9uLiAqL1xuZXhwb3J0IGRlZmF1bHQgKGJhc2UpID0+IHtcblxuICAvKipcbiAgICogTWl4aW4gdGhhdCBoYW5kbGVzIGxpc3QgYm94LXN0eWxlIHByZWZpeCB0eXBpbmcsIGluIHdoaWNoIHRoZSB1c2VyIGNhbiB0eXBlXG4gICAqIGEgc3RyaW5nIHRvIHNlbGVjdCB0aGUgZmlyc3QgaXRlbSB0aGF0IGJlZ2lucyB3aXRoIHRoYXQgc3RyaW5nLlxuICAgKlxuICAgKiBFeGFtcGxlOiBzdXBwb3NlIGEgY29tcG9uZW50IHVzaW5nIHRoaXMgbWl4aW4gaGFzIHRoZSBmb2xsb3dpbmcgaXRlbXM6XG4gICAqXG4gICAqICAgICA8c2FtcGxlLWxpc3QtY29tcG9uZW50PlxuICAgKiAgICAgICA8ZGl2PkFwcGxlPC9kaXY+XG4gICAqICAgICAgIDxkaXY+QXByaWNvdDwvZGl2PlxuICAgKiAgICAgICA8ZGl2PkJhbmFuYTwvZGl2PlxuICAgKiAgICAgICA8ZGl2PkJsYWNrYmVycnk8L2Rpdj5cbiAgICogICAgICAgPGRpdj5CbHVlYmVycnk8L2Rpdj5cbiAgICogICAgICAgPGRpdj5DYW50YWxvdXBlPC9kaXY+XG4gICAqICAgICAgIDxkaXY+Q2hlcnJ5PC9kaXY+XG4gICAqICAgICAgIDxkaXY+TGVtb248L2Rpdj5cbiAgICogICAgICAgPGRpdj5MaW1lPC9kaXY+XG4gICAqICAgICA8L3NhbXBsZS1saXN0LWNvbXBvbmVudD5cbiAgICpcbiAgICogSWYgdGhpcyBjb21wb25lbnQgcmVjZWl2ZXMgdGhlIGZvY3VzLCBhbmQgdGhlIHVzZXIgcHJlc3NlcyB0aGUgXCJiXCIgb3IgXCJCXCJcbiAgICoga2V5LCB0aGUgXCJCYW5hbmFcIiBpdGVtIHdpbGwgYmUgc2VsZWN0ZWQsIGJlY2F1c2UgaXQncyB0aGUgZmlyc3QgaXRlbSB0aGF0XG4gICAqIG1hdGNoZXMgdGhlIHByZWZpeCBcImJcIi4gKE1hdGNoaW5nIGlzIGNhc2UtaW5zZW5zaXRpdmUuKSBJZiB0aGUgdXNlciBub3dcbiAgICogcHJlc3NlcyB0aGUgXCJsXCIgb3IgXCJMXCIga2V5IHF1aWNrbHksIHRoZSBwcmVmaXggdG8gbWF0Y2ggYmVjb21lcyBcImJsXCIsIHNvXG4gICAqIFwiQmxhY2tiZXJyeVwiIHdpbGwgYmUgc2VsZWN0ZWQuXG4gICAqXG4gICAqIFRoZSBwcmVmaXggdHlwaW5nIGZlYXR1cmUgaGFzIGEgb25lIHNlY29uZCB0aW1lb3V0IOKAlMKgdGhlIHByZWZpeCB0byBtYXRjaFxuICAgKiB3aWxsIGJlIHJlc2V0IGFmdGVyIGEgc2Vjb25kIGhhcyBwYXNzZWQgc2luY2UgdGhlIHVzZXIgbGFzdCB0eXBlZCBhIGtleS5cbiAgICogSWYsIGluIHRoZSBhYm92ZSBleGFtcGxlLCB0aGUgdXNlciB3YWl0cyBhIHNlY29uZCBiZXR3ZWVuIHR5cGluZyBcImJcIiBhbmRcbiAgICogXCJsXCIsIHRoZSBwcmVmaXggd2lsbCBiZWNvbWUgXCJsXCIsIHNvIFwiTGVtb25cIiB3b3VsZCBiZSBzZWxlY3RlZC5cbiAgICpcbiAgICogVGhpcyBtaXhpbiBleHBlY3RzIHRoZSBjb21wb25lbnQgdG8gaW52b2tlIGEgYGtleWRvd25gIG1ldGhvZCB3aGVuIGEga2V5IGlzXG4gICAqIHByZXNzZWQuIFlvdSBjYW4gdXNlIFtLZXlib2FyZE1peGluXShLZXlib2FyZE1peGluLm1kKSBmb3IgdGhhdFxuICAgKiBwdXJwb3NlLCBvciB3aXJlIHVwIHlvdXIgb3duIGtleWJvYXJkIGhhbmRsaW5nIGFuZCBjYWxsIGBrZXlkb3duYCB5b3Vyc2VsZi5cbiAgICpcbiAgICogVGhpcyBtaXhpbiBhbHNvIGV4cGVjdHMgdGhlIGNvbXBvbmVudCB0byBwcm92aWRlIGFuIGBpdGVtc2AgcHJvcGVydHkuIFRoZVxuICAgKiBgdGV4dENvbnRlbnRgIG9mIHRob3NlIGl0ZW1zIHdpbGwgYmUgdXNlZCBmb3IgcHVycG9zZXMgb2YgcHJlZml4IG1hdGNoaW5nLlxuICAgKi9cbiAgY2xhc3MgS2V5Ym9hcmRQcmVmaXhTZWxlY3Rpb24gZXh0ZW5kcyBiYXNlIHtcblxuICAgIC8vIFRPRE86IElmIHRoZSBzZXQgb2YgaXRlbXMgaXMgY2hhbmdlZCwgcmVzZXQgdGhlIHByZWZpeC5cbiAgICAvLyBbc3ltYm9scy5pdGVtc0NoYW5nZWRdKCkge1xuICAgIC8vICAgdGhpc1tpdGVtVGV4dENvbnRlbnRzU3ltYm9sXSA9IG51bGw7XG4gICAgLy8gICByZXNldFR5cGVkUHJlZml4KHRoaXMpO1xuICAgIC8vIH1cblxuICAgIC8vIFRPRE86IElmIHRoZSBzZWxlY3Rpb24gaXMgY2hhbmdlZCBieSBzb21lIG90aGVyIG1lYW5zIChlLmcuLCBhcnJvdyBrZXlzKVxuICAgIC8vIG90aGVyIHRoYW4gcHJlZml4IHR5cGluZywgdGhlbiB0aGF0IGFjdCBzaG91bGQgcmVzZXQgdGhlIHByZWZpeC5cblxuICAgIFtzeW1ib2xzLmtleWRvd25dKGV2ZW50KSB7XG4gICAgICBsZXQgaGFuZGxlZDtcbiAgICAgIGxldCByZXNldFByZWZpeCA9IHRydWU7XG5cbiAgICAgIHN3aXRjaCAoZXZlbnQua2V5Q29kZSkge1xuICAgICAgICBjYXNlIDg6IC8vIEJhY2tzcGFjZVxuICAgICAgICAgIGhhbmRsZUJhY2tzcGFjZSh0aGlzKTtcbiAgICAgICAgICBoYW5kbGVkID0gdHJ1ZTtcbiAgICAgICAgICByZXNldFByZWZpeCA9IGZhbHNlO1xuICAgICAgICAgIGJyZWFrO1xuICAgICAgICBjYXNlIDI3OiAvLyBFc2NhcGVcbiAgICAgICAgICBoYW5kbGVkID0gdHJ1ZTtcbiAgICAgICAgICBicmVhaztcbiAgICAgICAgZGVmYXVsdDpcbiAgICAgICAgICBpZiAoIWV2ZW50LmN0cmxLZXkgJiYgIWV2ZW50Lm1ldGFLZXkgJiYgIWV2ZW50LmFsdEtleSAmJlxuICAgICAgICAgICAgICBldmVudC53aGljaCAhPT0gMzIgLyogU3BhY2UgKi8pIHtcbiAgICAgICAgICAgIGhhbmRsZVBsYWluQ2hhcmFjdGVyKHRoaXMsIFN0cmluZy5mcm9tQ2hhckNvZGUoZXZlbnQud2hpY2gpKTtcbiAgICAgICAgICB9XG4gICAgICAgICAgcmVzZXRQcmVmaXggPSBmYWxzZTtcbiAgICAgIH1cblxuICAgICAgaWYgKHJlc2V0UHJlZml4KSB7XG4gICAgICAgIHJlc2V0VHlwZWRQcmVmaXgodGhpcyk7XG4gICAgICB9XG5cbiAgICAgIC8vIFByZWZlciBtaXhpbiByZXN1bHQgaWYgaXQncyBkZWZpbmVkLCBvdGhlcndpc2UgdXNlIGJhc2UgcmVzdWx0LlxuICAgICAgcmV0dXJuIGhhbmRsZWQgfHwgKHN1cGVyW3N5bWJvbHMua2V5ZG93bl0gJiYgc3VwZXJbc3ltYm9scy5rZXlkb3duXShldmVudCkpO1xuICAgIH1cblxuICAgIC8qKlxuICAgICAqIFNlbGVjdCB0aGUgZmlyc3QgaXRlbSB3aG9zZSB0ZXh0IGNvbnRlbnQgYmVnaW5zIHdpdGggdGhlIGdpdmVuIHByZWZpeC5cbiAgICAgKlxuICAgICAqIEBwYXJhbSBwcmVmaXggW1N0cmluZ10gVGhlIHByZWZpeCBzdHJpbmcgdG8gc2VhcmNoIGZvclxuICAgICAqL1xuICAgIHNlbGVjdEl0ZW1XaXRoVGV4dFByZWZpeChwcmVmaXgpIHtcbiAgICAgIGlmIChzdXBlci5zZWxlY3RJdGVtV2l0aFRleHRQcmVmaXgpIHsgc3VwZXIuc2VsZWN0SXRlbVdpdGhUZXh0UHJlZml4KHByZWZpeCk7IH1cbiAgICAgIGlmIChwcmVmaXggPT0gbnVsbCB8fCBwcmVmaXgubGVuZ3RoID09PSAwKSB7XG4gICAgICAgIHJldHVybjtcbiAgICAgIH1cbiAgICAgIGNvbnN0IGluZGV4ID0gZ2V0SW5kZXhPZkl0ZW1XaXRoVGV4dFByZWZpeCh0aGlzLCBwcmVmaXgpO1xuICAgICAgaWYgKGluZGV4ID49IDApIHtcbiAgICAgICAgdGhpcy5zZWxlY3RlZEluZGV4ID0gaW5kZXg7XG4gICAgICB9XG4gICAgfVxuXG4gIH1cblxuICByZXR1cm4gS2V5Ym9hcmRQcmVmaXhTZWxlY3Rpb247XG59O1xuXG5cbi8vIFRpbWUgaW4gbWlsbGlzZWNvbmRzIGFmdGVyIHdoaWNoIHRoZSB1c2VyIGlzIGNvbnNpZGVyZWQgdG8gaGF2ZSBzdG9wcGVkXG4vLyB0eXBpbmcuXG5jb25zdCBQUkVGSVhfVElNRU9VVF9EVVJBVElPTiA9IDEwMDA7XG5cblxuLy8gUmV0dXJuIHRoZSBpbmRleCBvZiB0aGUgZmlyc3QgaXRlbSB3aXRoIHRoZSBnaXZlbiBwcmVmaXgsIGVsc2UgLTEuXG5mdW5jdGlvbiBnZXRJbmRleE9mSXRlbVdpdGhUZXh0UHJlZml4KGVsZW1lbnQsIHByZWZpeCkge1xuICBjb25zdCBpdGVtVGV4dENvbnRlbnRzID0gZ2V0SXRlbVRleHRDb250ZW50cyhlbGVtZW50KTtcbiAgY29uc3QgcHJlZml4TGVuZ3RoID0gcHJlZml4Lmxlbmd0aDtcbiAgZm9yIChsZXQgaSA9IDA7IGkgPCBpdGVtVGV4dENvbnRlbnRzLmxlbmd0aDsgaSsrKSB7XG4gICAgY29uc3QgaXRlbVRleHRDb250ZW50ID0gaXRlbVRleHRDb250ZW50c1tpXTtcbiAgICBpZiAoaXRlbVRleHRDb250ZW50LnN1YnN0cigwLCBwcmVmaXhMZW5ndGgpID09PSBwcmVmaXgpIHtcbiAgICAgIHJldHVybiBpO1xuICAgIH1cbiAgfVxuICByZXR1cm4gLTE7XG59XG5cbi8vIFJldHVybiBhbiBhcnJheSBvZiB0aGUgdGV4dCBjb250ZW50IChpbiBsb3dlcmNhc2UpIG9mIGFsbCBpdGVtcy5cbi8vIENhY2hlIHRoZXNlIHJlc3VsdHMuXG5mdW5jdGlvbiBnZXRJdGVtVGV4dENvbnRlbnRzKGVsZW1lbnQpIHtcbiAgaWYgKCFlbGVtZW50W2l0ZW1UZXh0Q29udGVudHNTeW1ib2xdKSB7XG4gICAgY29uc3QgaXRlbXMgPSBlbGVtZW50Lml0ZW1zO1xuICAgIGVsZW1lbnRbaXRlbVRleHRDb250ZW50c1N5bWJvbF0gPSBpdGVtcy5tYXAoY2hpbGQgPT4ge1xuICAgICAgY29uc3QgdGV4dCA9IGNoaWxkLnRleHRDb250ZW50IHx8IGNoaWxkLmFsdDtcbiAgICAgIHJldHVybiB0ZXh0LnRvTG93ZXJDYXNlKCk7XG4gICAgfSk7XG4gIH1cbiAgcmV0dXJuIGVsZW1lbnRbaXRlbVRleHRDb250ZW50c1N5bWJvbF07XG59XG5cbmZ1bmN0aW9uIGhhbmRsZUJhY2tzcGFjZShlbGVtZW50KSB7XG4gIGNvbnN0IGxlbmd0aCA9IGVsZW1lbnRbdHlwZWRQcmVmaXhTeW1ib2xdID8gZWxlbWVudFt0eXBlZFByZWZpeFN5bWJvbF0ubGVuZ3RoIDogMDtcbiAgaWYgKGxlbmd0aCA+IDApIHtcbiAgICBlbGVtZW50W3R5cGVkUHJlZml4U3ltYm9sXSA9IGVsZW1lbnRbdHlwZWRQcmVmaXhTeW1ib2xdLnN1YnN0cigwLCBsZW5ndGggLSAxKTtcbiAgfVxuICBlbGVtZW50LnNlbGVjdEl0ZW1XaXRoVGV4dFByZWZpeChlbGVtZW50W3R5cGVkUHJlZml4U3ltYm9sXSk7XG4gIHNldFByZWZpeFRpbWVvdXQoZWxlbWVudCk7XG59XG5cbmZ1bmN0aW9uIGhhbmRsZVBsYWluQ2hhcmFjdGVyKGVsZW1lbnQsIGNoYXIpIHtcbiAgY29uc3QgcHJlZml4ID0gZWxlbWVudFt0eXBlZFByZWZpeFN5bWJvbF0gfHwgJyc7XG4gIGVsZW1lbnRbdHlwZWRQcmVmaXhTeW1ib2xdID0gcHJlZml4ICsgY2hhci50b0xvd2VyQ2FzZSgpO1xuICBlbGVtZW50LnNlbGVjdEl0ZW1XaXRoVGV4dFByZWZpeChlbGVtZW50W3R5cGVkUHJlZml4U3ltYm9sXSk7XG4gIHNldFByZWZpeFRpbWVvdXQoZWxlbWVudCk7XG59XG5cbmZ1bmN0aW9uIHJlc2V0UHJlZml4VGltZW91dChlbGVtZW50KSB7XG4gIGlmIChlbGVtZW50W3ByZWZpeFRpbWVvdXRTeW1ib2xdKSB7XG4gICAgY2xlYXJUaW1lb3V0KGVsZW1lbnRbcHJlZml4VGltZW91dFN5bWJvbF0pO1xuICAgIGVsZW1lbnRbcHJlZml4VGltZW91dFN5bWJvbF0gPSBmYWxzZTtcbiAgfVxufVxuXG5mdW5jdGlvbiByZXNldFR5cGVkUHJlZml4KGVsZW1lbnQpIHtcbiAgZWxlbWVudFt0eXBlZFByZWZpeFN5bWJvbF0gPSAnJztcbiAgcmVzZXRQcmVmaXhUaW1lb3V0KGVsZW1lbnQpO1xufVxuXG5mdW5jdGlvbiBzZXRQcmVmaXhUaW1lb3V0KGVsZW1lbnQpIHtcbiAgcmVzZXRQcmVmaXhUaW1lb3V0KGVsZW1lbnQpO1xuICBlbGVtZW50W3ByZWZpeFRpbWVvdXRTeW1ib2xdID0gc2V0VGltZW91dCgoKSA9PiB7XG4gICAgcmVzZXRUeXBlZFByZWZpeChlbGVtZW50KTtcbiAgfSwgUFJFRklYX1RJTUVPVVRfRFVSQVRJT04pO1xufVxuIiwiLyogRXhwb3J0ZWQgZnVuY3Rpb24gZXh0ZW5kcyBhIGJhc2UgY2xhc3Mgd2l0aCBTZWxlY3RlZEl0ZW1UZXh0VmFsdWUuICovXG5leHBvcnQgZGVmYXVsdCAoYmFzZSkgPT4ge1xuXG4gIC8qKlxuICAgKiBNaXhpbiB3aGljaCBkZWZpbmVzIGEgYHZhbHVlYCBwcm9wZXJ0eSB0aGF0IHJlZmxlY3RzIHRoZSB0ZXh0IGNvbnRlbnQgb2YgYVxuICAgKiBzZWxlY3RlZCBpdGVtLlxuICAgKlxuICAgKiBUaGlzIG1peGluIGV4aXN0cyBmb3IgbGlzdC1saWtlIGNvbXBvbmVudHMgdGhhdCB3YW50IHRvIHByb3ZpZGUgYSBtb3JlXG4gICAqIGNvbnZlbmllbnQgd2F5IHRvIGdldC9zZXQgdGhlIHNlbGVjdGVkIGl0ZW0gdXNpbmcgdGV4dC5cbiAgICpcbiAgICogVGhpcyBtaXhpbiBleHBlY3RzIGEgY29tcG9uZW50IHRvIHByb3ZpZGUgYW4gYGl0ZW1zYCBhcnJheSBvZiBhbGwgZWxlbWVudHNcbiAgICogaW4gdGhlIGxpc3QuIEEgc3RhbmRhcmQgd2F5IHRvIGRvIHRoYXQgd2l0aCBpc1xuICAgKiBbQ29udGVudEl0ZW1zTWl4aW5dKENvbnRlbnRJdGVtc01peGluLm1kKS4gVGhpcyBhbHNvIGV4cGVjdHMgdGhlIGRlZmluaXRpb25cbiAgICogb2YgYHNlbGVjdGVkSW5kZXhgIGFuZCBgc2VsZWN0ZWRJdGVtYCBwcm9wZXJ0aWVzLCB3aGljaCBjYW4gYmUgb2J0YWluZWRcbiAgICogZnJvbSBbU2luZ2xlU2VsZWN0aW9uTWl4aW5dKFNpbmdsZVNlbGVjdGlvbk1peGluLm1kKS5cbiAgICovXG4gIGNsYXNzIFNlbGVjdGVkSXRlbVRleHRWYWx1ZSBleHRlbmRzIGJhc2Uge1xuXG4gICAgLyoqXG4gICAgICogVGhlIHRleHQgY29udGVudCBvZiB0aGUgc2VsZWN0ZWQgaXRlbS5cbiAgICAgKlxuICAgICAqIFNldHRpbmcgdGhpcyB2YWx1ZSB0byBhIHN0cmluZyB3aWxsIGF0dGVtcHQgdG8gc2VsZWN0IHRoZSBmaXJzdCBsaXN0IGl0ZW1cbiAgICAgKiB3aG9zZSB0ZXh0IGNvbnRlbnQgbWF0Y2ggdGhhdCBzdHJpbmcuIFNldHRpbmcgdGhpcyB0byBhIHN0cmluZyBub3QgbWF0Y2hpbmdcbiAgICAgKiBhbnkgbGlzdCBpdGVtIHdpbGwgcmVzdWx0IGluIG5vIHNlbGVjdGlvbi5cbiAgICAgKlxuICAgICAqIEB0eXBlIHtzdHJpbmd9XG4gICAgICovXG4gICAgZ2V0IHZhbHVlKCkge1xuICAgICAgcmV0dXJuIHRoaXMuc2VsZWN0ZWRJdGVtID09IG51bGwgfHwgdGhpcy5zZWxlY3RlZEl0ZW0udGV4dENvbnRlbnQgPT0gbnVsbCA/XG4gICAgICAgICcnIDpcbiAgICAgICAgdGhpcy5zZWxlY3RlZEl0ZW0udGV4dENvbnRlbnQ7XG4gICAgfVxuICAgIHNldCB2YWx1ZSh0ZXh0KSB7XG5cbiAgICAgIGNvbnN0IGN1cnJlbnRJbmRleCA9IHRoaXMuc2VsZWN0ZWRJbmRleDtcbiAgICAgIGxldCBuZXdJbmRleCA9IC0xOyAvLyBBc3N1bWUgd2Ugd29uJ3QgZmluZCB0aGUgdGV4dC5cblxuICAgICAgLy8gRmluZCB0aGUgaXRlbSB3aXRoIHRoZSBpbmRpY2F0ZWQgdGV4dC5cbiAgICAgIGNvbnN0IGl0ZW1zID0gdGhpcy5pdGVtcztcbiAgICAgIGZvciAobGV0IGkgPSAwLCBsZW5ndGggPSBpdGVtcy5sZW5ndGg7IGkgPCBsZW5ndGg7IGkrKykge1xuICAgICAgICBpZiAoaXRlbXNbaV0udGV4dENvbnRlbnQgPT09IHRleHQpIHtcbiAgICAgICAgICBuZXdJbmRleCA9IGk7XG4gICAgICAgICAgYnJlYWs7XG4gICAgICAgIH1cbiAgICAgIH1cblxuICAgICAgaWYgKG5ld0luZGV4ICE9PSBjdXJyZW50SW5kZXgpIHtcbiAgICAgICAgdGhpcy5zZWxlY3RlZEluZGV4ID0gbmV3SW5kZXg7XG4gICAgICAgIGNvbnN0IGV2ZW50ID0gbmV3IEN1c3RvbUV2ZW50KCd2YWx1ZS1jaGFuZ2VkJyk7XG4gICAgICAgIHRoaXMuZGlzcGF0Y2hFdmVudChldmVudCk7XG4gICAgICB9XG4gICAgfVxuICB9XG5cbiAgcmV0dXJuIFNlbGVjdGVkSXRlbVRleHRWYWx1ZTtcbn07XG4iLCJpbXBvcnQgc3ltYm9scyBmcm9tICcuL3N5bWJvbHMnO1xuXG5cbi8vIFVzZWQgdG8gYXNzaWduIHVuaXF1ZSBJRHMgdG8gaXRlbSBlbGVtZW50cyB3aXRob3V0IElEcy5cbmxldCBpZENvdW50ID0gMDtcblxuXG4vKiBFeHBvcnRlZCBmdW5jdGlvbiBleHRlbmRzIGEgYmFzZSBjbGFzcyB3aXRoIFNlbGVjdGlvbkFyaWFBY3RpdmUuICovXG5leHBvcnQgZGVmYXVsdCAoYmFzZSkgPT4ge1xuXG4gIC8qKlxuICAgKiBNaXhpbiB3aGljaCB0cmVhdHMgdGhlIHNlbGVjdGVkIGl0ZW0gaW4gYSBsaXN0IGFzIHRoZSBhY3RpdmUgaXRlbSBpbiBBUklBXG4gICAqIGFjY2Vzc2liaWxpdHkgdGVybXMuXG4gICAqXG4gICAqIEhhbmRsaW5nIEFSSUEgc2VsZWN0aW9uIHN0YXRlIHByb3Blcmx5IGlzIGFjdHVhbGx5IHF1aXRlIGNvbXBsZXg6XG4gICAqXG4gICAqICogVGhlIGl0ZW1zIGluIHRoZSBsaXN0IG5lZWQgdG8gYmUgaW5kaWNhdGVkIGFzIHBvc3NpYmxlIGl0ZW1zIHZpYSBhbiBBUklBXG4gICAqICAgYHJvbGVgIGF0dHJpYnV0ZSB2YWx1ZSBzdWNoIGFzIFwib3B0aW9uXCIuXG4gICAqICogVGhlIHNlbGVjdGVkIGl0ZW0gbmVlZCB0byBiZSBtYXJrZWQgYXMgc2VsZWN0ZWQgYnkgc2V0dGluZyB0aGUgaXRlbSdzXG4gICAqICAgYGFyaWEtc2VsZWN0ZWRgIGF0dHJpYnV0ZSB0byB0cnVlICphbmQqIHRoZSBvdGhlciBpdGVtcyBuZWVkIGJlIG1hcmtlZCBhc1xuICAgKiAgICpub3QqIHNlbGVjdGVkIGJ5IHNldHRpbmcgYGFyaWEtc2VsZWN0ZWRgIHRvIGZhbHNlLlxuICAgKiAqIFRoZSBvdXRlcm1vc3QgZWxlbWVudCB3aXRoIHRoZSBrZXlib2FyZCBmb2N1cyBuZWVkcyB0byBoYXZlIGF0dHJpYnV0ZXNcbiAgICogICBzZXQgb24gaXQgc28gdGhhdCB0aGUgc2VsZWN0aW9uIGlzIGtub3dhYmxlIGF0IHRoZSBsaXN0IGxldmVsIHZpYSB0aGVcbiAgICogICBgYXJpYS1hY3RpdmVkZXNjZW5kYW50YCBhdHRyaWJ1dGUuXG4gICAqICogVXNlIG9mIGBhcmlhLWFjdGl2ZWRlc2NlbmRhbnRgIGluIHR1cm4gcmVxdWlyZXMgdGhhdCBhbGwgaXRlbXMgaW4gdGhlXG4gICAqICAgbGlzdCBoYXZlIElEIGF0dHJpYnV0ZXMgYXNzaWduZWQgdG8gdGhlbS5cbiAgICpcbiAgICogVGhpcyBtaXhpbiB0cmllcyB0byBhZGRyZXNzIGFsbCBvZiB0aGUgYWJvdmUgcmVxdWlyZW1lbnRzLiBUbyB0aGF0IGVuZCxcbiAgICogdGhpcyBtaXhpbiB3aWxsIGFzc2lnbiBnZW5lcmF0ZWQgSURzIHRvIGFueSBpdGVtIHRoYXQgZG9lc24ndCBhbHJlYWR5IGhhdmVcbiAgICogYW4gSUQuXG4gICAqXG4gICAqIEFSSUEgcmVsaWVzIG9uIGVsZW1lbnRzIHRvIHByb3ZpZGUgYHJvbGVgIGF0dHJpYnV0ZXMuIFRoaXMgbWl4aW4gd2lsbCBhcHBseVxuICAgKiBhIGRlZmF1bHQgcm9sZSBvZiBcImxpc3Rib3hcIiBvbiB0aGUgb3V0ZXIgbGlzdCBpZiBpdCBkb2Vzbid0IGFscmVhZHkgaGF2ZSBhblxuICAgKiBleHBsaWNpdCByb2xlLiBTaW1pbGFybHksIHRoaXMgbWl4aW4gd2lsbCBhcHBseSBhIGRlZmF1bHQgcm9sZSBvZiBcIm9wdGlvblwiXG4gICAqIHRvIGFueSBsaXN0IGl0ZW0gdGhhdCBkb2VzIG5vdCBhbHJlYWR5IGhhdmUgYSByb2xlIHNwZWNpZmllZC5cbiAgICpcbiAgICogVGhpcyBtaXhpbiBleHBlY3RzIGEgc2V0IG9mIG1lbWJlcnMgdGhhdCBtYW5hZ2UgdGhlIHN0YXRlIG9mIHRoZSBzZWxlY3Rpb246XG4gICAqIGBbc3ltYm9scy5pdGVtU2VsZWN0ZWRdYCwgYGl0ZW1BZGRlZGAsIGFuZCBgc2VsZWN0ZWRJbmRleGAuIFlvdSBjYW5cbiAgICogc3VwcGx5IHRoZXNlIHlvdXJzZWxmLCBvciBkbyBzbyB2aWFcbiAgICogW1NpbmdsZVNlbGVjdGlvbk1peGluXShTaW5nbGVTZWxlY3Rpb25NaXhpbi5tZCkuXG4gICAqL1xuICBjbGFzcyBTZWxlY3Rpb25BcmlhQWN0aXZlIGV4dGVuZHMgYmFzZSB7XG5cbiAgICBjb25uZWN0ZWRDYWxsYmFjaygpIHtcbiAgICAgIGlmIChzdXBlci5jb25uZWN0ZWRDYWxsYmFjaykgeyBzdXBlci5jb25uZWN0ZWRDYWxsYmFjaygpOyB9XG4gICAgICAvLyBTZXQgZGVmYXVsdCBBUklBIHJvbGUuXG4gICAgICBpZiAodGhpcy5nZXRBdHRyaWJ1dGUoJ3JvbGUnKSA9PSBudWxsICYmIHRoaXNbc3ltYm9scy5kZWZhdWx0c10ucm9sZSkge1xuICAgICAgICB0aGlzLnNldEF0dHJpYnV0ZSgncm9sZScsIHRoaXNbc3ltYm9scy5kZWZhdWx0c10ucm9sZSk7XG4gICAgICB9XG4gICAgfVxuXG4gICAgZ2V0IFtzeW1ib2xzLmRlZmF1bHRzXSgpIHtcbiAgICAgIGNvbnN0IGRlZmF1bHRzID0gc3VwZXJbc3ltYm9scy5kZWZhdWx0c10gfHwge307XG4gICAgICBkZWZhdWx0cy5yb2xlID0gJ2xpc3Rib3gnO1xuICAgICAgcmV0dXJuIGRlZmF1bHRzO1xuICAgIH1cblxuICAgIFtzeW1ib2xzLml0ZW1BZGRlZF0oaXRlbSkge1xuICAgICAgaWYgKHN1cGVyW3N5bWJvbHMuaXRlbUFkZGVkXSkgeyBzdXBlcltzeW1ib2xzLml0ZW1BZGRlZF0oaXRlbSk7IH1cblxuICAgICAgaWYgKCFpdGVtLmdldEF0dHJpYnV0ZSgncm9sZScpKSB7XG4gICAgICAgIC8vIEFzc2lnbiBhIGRlZmF1bHQgQVJJQSByb2xlLlxuICAgICAgICBpdGVtLnNldEF0dHJpYnV0ZSgncm9sZScsICdvcHRpb24nKTtcbiAgICAgIH1cblxuICAgICAgLy8gRW5zdXJlIGVhY2ggaXRlbSBoYXMgYW4gSUQgc28gd2UgY2FuIHNldCBhcmlhLWFjdGl2ZWRlc2NlbmRhbnQgb24gdGhlXG4gICAgICAvLyBvdmVyYWxsIGxpc3Qgd2hlbmV2ZXIgdGhlIHNlbGVjdGlvbiBjaGFuZ2VzLlxuICAgICAgLy9cbiAgICAgIC8vIFRoZSBJRCB3aWxsIHRha2UgdGhlIGZvcm0gb2YgYSBiYXNlIElEIHBsdXMgYSB1bmlxdWUgaW50ZWdlci4gVGhlIGJhc2VcbiAgICAgIC8vIElEIHdpbGwgYmUgaW5jb3Jwb3JhdGUgdGhlIGNvbXBvbmVudCdzIG93biBJRC4gRS5nLiwgaWYgYSBjb21wb25lbnQgaGFzXG4gICAgICAvLyBJRCBcImZvb1wiLCB0aGVuIGl0cyBpdGVtcyB3aWxsIGhhdmUgSURzIHRoYXQgbG9vayBsaWtlIFwiX2Zvb09wdGlvbjFcIi4gSWZcbiAgICAgIC8vIHRoZSBjb21wbmVudCBoYXMgbm8gSUQgaXRzZWxmLCBpdHMgaXRlbXMgd2lsbCBnZXQgSURzIHRoYXQgbG9vayBsaWtlXG4gICAgICAvLyBcIl9vcHRpb24xXCIuIEl0ZW0gSURzIGFyZSBwcmVmaXhlZCB3aXRoIGFuIHVuZGVyc2NvcmUgdG8gZGlmZmVyZW50aWF0ZVxuICAgICAgLy8gdGhlbSBmcm9tIG1hbnVhbGx5LWFzc2lnbmVkIElEcywgYW5kIHRvIG1pbmltaXplIHRoZSBwb3RlbnRpYWwgZm9yIElEXG4gICAgICAvLyBjb25mbGljdHMuXG4gICAgICBpZiAoIWl0ZW0uaWQpIHtcbiAgICAgICAgY29uc3QgYmFzZUlkID0gdGhpcy5pZCA/XG4gICAgICAgICAgICBcIl9cIiArIHRoaXMuaWQgKyBcIk9wdGlvblwiIDpcbiAgICAgICAgICAgIFwiX29wdGlvblwiO1xuICAgICAgICBpdGVtLmlkID0gYmFzZUlkICsgaWRDb3VudCsrO1xuICAgICAgfVxuICAgIH1cblxuICAgIFtzeW1ib2xzLml0ZW1TZWxlY3RlZF0oaXRlbSwgc2VsZWN0ZWQpIHtcbiAgICAgIGlmIChzdXBlcltzeW1ib2xzLml0ZW1TZWxlY3RlZF0pIHsgc3VwZXJbc3ltYm9scy5pdGVtU2VsZWN0ZWRdKGl0ZW0sIHNlbGVjdGVkKTsgfVxuICAgICAgaXRlbS5zZXRBdHRyaWJ1dGUoJ2FyaWEtc2VsZWN0ZWQnLCBzZWxlY3RlZCk7XG4gICAgICBjb25zdCBpdGVtSWQgPSBpdGVtLmlkO1xuICAgICAgaWYgKGl0ZW1JZCAmJiBzZWxlY3RlZCkge1xuICAgICAgICB0aGlzLnNldEF0dHJpYnV0ZSgnYXJpYS1hY3RpdmVkZXNjZW5kYW50JywgaXRlbUlkKTtcbiAgICAgIH1cbiAgICB9XG5cbiAgICBnZXQgc2VsZWN0ZWRJdGVtKCkge1xuICAgICAgcmV0dXJuIHN1cGVyLnNlbGVjdGVkSXRlbTtcbiAgICB9XG4gICAgc2V0IHNlbGVjdGVkSXRlbShpdGVtKSB7XG4gICAgICBpZiAoJ3NlbGVjdGVkSXRlbScgaW4gYmFzZS5wcm90b3R5cGUpIHsgc3VwZXIuc2VsZWN0ZWRJdGVtID0gaXRlbTsgfVxuICAgICAgaWYgKGl0ZW0gPT0gbnVsbCkge1xuICAgICAgICAvLyBTZWxlY3Rpb24gd2FzIHJlbW92ZWQuXG4gICAgICAgIHRoaXMucmVtb3ZlQXR0cmlidXRlKCdhcmlhLWFjdGl2ZWRlc2NlbmRhbnQnKTtcbiAgICAgIH1cbiAgICB9XG5cbiAgfVxuXG4gIHJldHVybiBTZWxlY3Rpb25BcmlhQWN0aXZlO1xufTtcbiIsImltcG9ydCBzeW1ib2xzIGZyb20gJy4uL3NyYy9zeW1ib2xzJztcblxuXG4vKiBFeHBvcnRlZCBmdW5jdGlvbiBleHRlbmRzIGEgYmFzZSBjbGFzcyB3aXRoIFNlbGVjdGlvbkhpZ2hsaWdodC4gKi9cbmV4cG9ydCBkZWZhdWx0IChiYXNlKSA9PiB7XG5cbiAgLyoqXG4gICAqIFRlbXBsYXRlIG1peGluIHdoaWNoIGFwcGxpZXMgc3RhbmRhcmQgaGlnaGxpZ2h0IGNvbG9ycyB0byBhIHNlbGVjdGVkIGl0ZW0uXG4gICAqXG4gICAqIFRoaXMgbWl4aW4gaGlnaGxpZ2h0cyB0ZXh0dWFsIGl0ZW1zIChlLmcuLCBpbiBhIGxpc3QpIGluIGEgc3RhbmRhcmQgd2F5IGJ5XG4gICAqIHVzaW5nIHRoZSBDU1MgYGhpZ2hsaWdodGAgYW5kIGBoaWdobGlnaHR0ZXh0YCBjb2xvciB2YWx1ZXMuIFRoZXNlIHZhbHVlc1xuICAgKiByZXNwZWN0IG9wZXJhdGluZyBzeXN0ZW0gZGVmYXVsdHMgYW5kIHVzZXIgcHJlZmVyZW5jZXMsIGFuZCBoZW5jZSBhcmUgZ29vZFxuICAgKiBkZWZhdWx0IHZhbHVlcyBmb3IgaGlnaGxpZ2h0IGNvbG9ycy5cbiAgICpcbiAgICogVGhpcyBtaXhpbiBleHBlY3RzIGEgYHNlbGVjdGVkYCBjbGFzcyB0byBiZSBhcHBsaWVkIHRvIHNlbGVjdGVkIGl0ZW1zLiBZb3VcbiAgICogY2FuIHVzZSBbQ29udGVudEl0ZW1zTWl4aW5dKENvbnRlbnRJdGVtc01peGluLm1kKSBmb3IgdGhhdCBwdXJwb3NlLlxuICAgKi9cbiAgY2xhc3MgU2VsZWN0aW9uSGlnaGxpZ2h0IGV4dGVuZHMgYmFzZSB7XG5cbiAgICBnZXQgW3N5bWJvbHMudGVtcGxhdGVdKCkge1xuICAgICAgY29uc3QgYmFzZVRlbXBsYXRlID0gc3VwZXJbc3ltYm9scy50ZW1wbGF0ZV0gfHwgJyc7XG4gICAgICByZXR1cm4gYFxuICAgICAgICA8c3R5bGU+XG4gICAgICAgICAgOmhvc3QoW2dlbmVyaWM9XCJcIl0pIDo6c2xvdHRlZCguc2VsZWN0ZWQpIHtcbiAgICAgICAgICAgIGJhY2tncm91bmQtY29sb3I6IGhpZ2hsaWdodDtcbiAgICAgICAgICAgIGNvbG9yOiBoaWdobGlnaHR0ZXh0O1xuICAgICAgICAgIH1cbiAgICAgICAgPC9zdHlsZT5cbiAgICAgICAgJHtiYXNlVGVtcGxhdGV9XG4gICAgICBgO1xuICAgIH1cblxuICB9XG5cbiAgcmV0dXJuIFNlbGVjdGlvbkhpZ2hsaWdodDtcbn07XG4iLCIvKiBFeHBvcnRlZCBmdW5jdGlvbiBleHRlbmRzIGEgYmFzZSBjbGFzcyB3aXRoIFNlbGVjdGlvbkluVmlldy4gKi9cbmV4cG9ydCBkZWZhdWx0IChiYXNlKSA9PiB7XG5cbiAgLyoqXG4gICAqIE1peGluIHdoaWNoIHNjcm9sbHMgYSBjb250YWluZXIgdG8gZW5zdXJlIHRoYXQgYSBuZXdseS1zZWxlY3RlZCBpdGVtIGlzXG4gICAqIHZpc2libGUgdG8gdGhlIHVzZXIuXG4gICAqXG4gICAqIFdoZW4gdGhlIHNlbGVjdGVkIGl0ZW0gaW4gYSBsaXN0LWxpa2UgY29tcG9uZW50IGNoYW5nZXMsIGl0J3MgZWFzaWVyIGZvclxuICAgKiB0aGUgdG8gY29uZmlybSB0aGF0IHRoZSBzZWxlY3Rpb24gaGFzIGNoYW5nZWQgdG8gYW4gYXBwcm9wcmlhdGUgaXRlbSBpZiB0aGVcbiAgICogdXNlciBjYW4gYWN0dWFsbHkgc2VlIHRoYXQgaXRlbS5cbiAgICpcbiAgICogVGhpcyBtaXhpbiBleHBlY3RzIGEgYHNlbGVjdGVkSXRlbWAgcHJvcGVydHkgdG8gYmUgc2V0IHdoZW4gdGhlIHNlbGVjdGlvblxuICAgKiBjaGFuZ2VzLiBZb3UgY2FuIHN1cHBseSB0aGF0IHlvdXJzZWxmLCBvciB1c2VcbiAgICogW1NpbmdsZVNlbGVjdGlvbk1peGluXShTaW5nbGVTZWxlY3Rpb25NaXhpbi5tZCkuXG4gICAqL1xuICBjbGFzcyBTZWxlY3Rpb25JblZpZXcgZXh0ZW5kcyBiYXNlIHtcblxuICAgIGNvbm5lY3RlZENhbGxiYWNrKCkge1xuICAgICAgaWYgKHN1cGVyLmNvbm5lY3RlZENhbGxiYWNrKSB7IHN1cGVyLmNvbm5lY3RlZENhbGxiYWNrKCk7IH1cbiAgICAgIGNvbnN0IHNlbGVjdGVkSXRlbSA9IHRoaXMuc2VsZWN0ZWRJdGVtO1xuICAgICAgaWYgKHNlbGVjdGVkSXRlbSkge1xuICAgICAgICB0aGlzLnNjcm9sbEl0ZW1JbnRvVmlldyhzZWxlY3RlZEl0ZW0pO1xuICAgICAgfVxuICAgIH1cblxuICAgIGdldCBzZWxlY3RlZEl0ZW0oKSB7XG4gICAgICByZXR1cm4gc3VwZXIuc2VsZWN0ZWRJdGVtO1xuICAgIH1cbiAgICBzZXQgc2VsZWN0ZWRJdGVtKGl0ZW0pIHtcbiAgICAgIGlmICgnc2VsZWN0ZWRJdGVtJyBpbiBiYXNlLnByb3RvdHlwZSkgeyBzdXBlci5zZWxlY3RlZEl0ZW0gPSBpdGVtOyB9XG4gICAgICBpZiAoaXRlbSkge1xuICAgICAgICAvLyBLZWVwIHRoZSBzZWxlY3RlZCBpdGVtIGluIHZpZXcuXG4gICAgICAgIHRoaXMuc2Nyb2xsSXRlbUludG9WaWV3KGl0ZW0pO1xuICAgICAgfVxuICAgIH1cblxuICAgIC8qKlxuICAgICAqIFNjcm9sbCB0aGUgZ2l2ZW4gZWxlbWVudCBjb21wbGV0ZWx5IGludG8gdmlldywgbWluaW1pemluZyB0aGUgZGVncmVlIG9mXG4gICAgICogc2Nyb2xsaW5nIHBlcmZvcm1lZC5cbiAgICAgKlxuICAgICAqIEJsaW5rIGhhcyBhIGBzY3JvbGxJbnRvVmlld0lmTmVlZGVkKClgIGZ1bmN0aW9uIHRoYXQgZG9lcyBzb21ldGhpbmdcbiAgICAgKiBzaW1pbGFyLCBidXQgdW5mb3J0dW5hdGVseSBpdCdzIG5vbi1zdGFuZGFyZCwgYW5kIGluIGFueSBldmVudCBvZnRlbiBlbmRzXG4gICAgICogdXAgc2Nyb2xsaW5nIG1vcmUgdGhhbiBpcyBhYnNvbHV0ZWx5IG5lY2Vzc2FyeS5cbiAgICAgKlxuICAgICAqIEBwYXJhbSB7SFRNTEVsZW1lbnR9IGl0ZW0gLSB0aGUgaXRlbSB0byBzY3JvbGwgaW50byB2aWV3LlxuICAgICAqL1xuICAgIHNjcm9sbEl0ZW1JbnRvVmlldyhpdGVtKSB7XG4gICAgICBpZiAoc3VwZXIuc2Nyb2xsSXRlbUludG9WaWV3KSB7IHN1cGVyLnNjcm9sbEl0ZW1JbnRvVmlldygpOyB9XG4gICAgICAvLyBHZXQgdGhlIHJlbGF0aXZlIHBvc2l0aW9uIG9mIHRoZSBpdGVtIHdpdGggcmVzcGVjdCB0byB0aGUgdG9wIG9mIHRoZVxuICAgICAgLy8gbGlzdCdzIHNjcm9sbGFibGUgY2FudmFzLiBBbiBpdGVtIGF0IHRoZSB0b3Agb2YgdGhlIGxpc3Qgd2lsbCBoYXZlIGFcbiAgICAgIC8vIGVsZW1lbnRUb3Agb2YgMC5cblxuICAgICAgY29uc3Qgc2Nyb2xsVGFyZ2V0ID0gdGhpcy5zY3JvbGxUYXJnZXQ7XG4gICAgICBjb25zdCBlbGVtZW50VG9wID0gaXRlbS5vZmZzZXRUb3AgLSBzY3JvbGxUYXJnZXQub2Zmc2V0VG9wIC0gc2Nyb2xsVGFyZ2V0LmNsaWVudFRvcDtcbiAgICAgIGNvbnN0IGVsZW1lbnRCb3R0b20gPSBlbGVtZW50VG9wICsgaXRlbS5vZmZzZXRIZWlnaHQ7XG4gICAgICAvLyBEZXRlcm1pbmUgdGhlIGJvdHRvbSBvZiB0aGUgc2Nyb2xsYWJsZSBjYW52YXMuXG4gICAgICBjb25zdCBzY3JvbGxCb3R0b20gPSBzY3JvbGxUYXJnZXQuc2Nyb2xsVG9wICsgc2Nyb2xsVGFyZ2V0LmNsaWVudEhlaWdodDtcbiAgICAgIGlmIChlbGVtZW50Qm90dG9tID4gc2Nyb2xsQm90dG9tKSB7XG4gICAgICAgIC8vIFNjcm9sbCB1cCB1bnRpbCBpdGVtIGlzIGVudGlyZWx5IHZpc2libGUuXG4gICAgICAgIHNjcm9sbFRhcmdldC5zY3JvbGxUb3AgKz0gZWxlbWVudEJvdHRvbSAtIHNjcm9sbEJvdHRvbTtcbiAgICAgIH1cbiAgICAgIGVsc2UgaWYgKGVsZW1lbnRUb3AgPCBzY3JvbGxUYXJnZXQuc2Nyb2xsVG9wKSB7XG4gICAgICAgIC8vIFNjcm9sbCBkb3duIHVudGlsIGl0ZW0gaXMgZW50aXJlbHkgdmlzaWJsZS5cbiAgICAgICAgc2Nyb2xsVGFyZ2V0LnNjcm9sbFRvcCA9IGVsZW1lbnRUb3A7XG4gICAgICB9XG4gICAgfVxuXG4gICAgLyoqXG4gICAgICogVGhlIGVsZW1lbnQgdGhhdCBzaG91bGQgYmUgc2Nyb2xsZWQgdG8gYnJpbmcgYW4gaXRlbSBpbnRvIHZpZXcuXG4gICAgICpcbiAgICAgKiBUaGUgZGVmYXVsdCB2YWx1ZSBvZiB0aGlzIHByb3BlcnR5IGlzIHRoZSBlbGVtZW50IGl0c2VsZi5cbiAgICAgKlxuICAgICAqIEB0eXBlIHtIVE1MRWxlbWVudH1cbiAgICAgKi9cbiAgICBnZXQgc2Nyb2xsVGFyZ2V0KCkge1xuICAgICAgLy8gUHJlZmVyIGJhc2UgcmVzdWx0LlxuICAgICAgcmV0dXJuICdzY3JvbGxUYXJnZXQnIGluIGJhc2UucHJvdG90eXBlID8gc3VwZXIuc2Nyb2xsVGFyZ2V0IDogdGhpcztcbiAgICB9XG4gICAgc2V0IHNjcm9sbFRhcmdldChlbGVtZW50KSB7XG4gICAgICBpZiAoJ3Njcm9sbFRhcmdldCcgaW4gYmFzZS5wcm90b3R5cGUpIHsgc3VwZXIuc2Nyb2xsVGFyZ2V0ID0gZWxlbWVudDsgfVxuICAgIH1cblxuICB9XG5cbiAgcmV0dXJuIFNlbGVjdGlvbkluVmlldztcbn07XG4iLCIvKiBFeHBvcnRlZCBmdW5jdGlvbiBleHRlbmRzIGEgYmFzZSBjbGFzcyB3aXRoIFNoYWRvd0VsZW1lbnRSZWZlcmVuY2VzLiAqL1xuZXhwb3J0IGRlZmF1bHQgKGJhc2UpID0+IHtcblxuICAvKipcbiAgICogTWl4aW4gdG8gY3JlYXRlIHJlZmVyZW5jZXMgdG8gZWxlbWVudHMgaW4gYSBjb21wb25lbnQncyBTaGFkb3cgRE9NIHN1YnRyZWUuXG4gICAqXG4gICAqIFRoaXMgYWRkcyBhIG1lbWJlciBvbiB0aGUgY29tcG9uZW50IGNhbGxlZCBgdGhpcy4kYCB0aGF0IGNhbiBiZSB1c2VkIHRvXG4gICAqIHJlZmVyZW5jZSBzaGFkb3cgZWxlbWVudHMgd2l0aCBJRHMuIEUuZy4sIGlmIGNvbXBvbmVudCdzIHNoYWRvdyBjb250YWlucyBhblxuICAgKiBlbGVtZW50IGA8YnV0dG9uIGlkPVwiZm9vXCI+YCwgdGhlbiB0aGlzIG1peGluIHdpbGwgY3JlYXRlIGEgbWVtYmVyXG4gICAqIGB0aGlzLiQuZm9vYCB0aGF0IHBvaW50cyB0byB0aGF0IGJ1dHRvbi5cbiAgICpcbiAgICogU3VjaCByZWZlcmVuY2VzIHNpbXBsaWZ5IGEgY29tcG9uZW50J3MgYWNjZXNzIHRvIGl0cyBvd24gZWxlbWVudHMuIEluXG4gICAqIGV4Y2hhbmdlLCB0aGlzIG1peGluIHRyYWRlcyBvZmYgYSBvbmUtdGltZSBjb3N0IG9mIHF1ZXJ5aW5nIGFsbCBlbGVtZW50cyBpblxuICAgKiB0aGUgc2hhZG93IHRyZWUgaW5zdGVhZCBvZiBwYXlpbmcgYW4gb25nb2luZyBjb3N0IHRvIHF1ZXJ5IGZvciBhbiBlbGVtZW50XG4gICAqIGVhY2ggdGltZSB0aGUgY29tcG9uZW50IHdhbnRzIHRvIGluc3BlY3Qgb3IgbWFuaXB1bGF0ZSBpdC5cbiAgICpcbiAgICogVGhpcyBtaXhpbiBleHBlY3RzIHRoZSBjb21wb25lbnQgdG8gZGVmaW5lIGEgU2hhZG93IERPTSBzdWJ0cmVlLiBZb3UgY2FuXG4gICAqIGNyZWF0ZSB0aGF0IHRyZWUgeW91cnNlbGYsIG9yIG1ha2UgdXNlIG9mXG4gICAqIFtTaGFkb3dUZW1wbGF0ZU1peGluXShTaGFkb3dUZW1wbGF0ZU1peGluLm1kKS5cbiAgICpcbiAgICogVGhpcyBtaXhpbiBpcyBpbnNwaXJlZCBieSBQb2x5bWVyJ3MgW2F1dG9tYXRpY1xuICAgKiBub2RlIGZpbmRpbmddKGh0dHBzOi8vd3d3LnBvbHltZXItcHJvamVjdC5vcmcvMS4wL2RvY3MvZGV2Z3VpZGUvbG9jYWwtZG9tLmh0bWwjbm9kZS1maW5kaW5nKVxuICAgKiBmZWF0dXJlLlxuICAgKi9cbiAgY2xhc3MgU2hhZG93RWxlbWVudFJlZmVyZW5jZXMgZXh0ZW5kcyBiYXNlIHtcblxuICAgIGNvbnN0cnVjdG9yKCkge1xuICAgICAgc3VwZXIoKTtcbiAgICAgIGlmICh0aGlzLnNoYWRvd1Jvb3QpIHtcbiAgICAgICAgLy8gTG9vayBmb3IgZWxlbWVudHMgaW4gdGhlIHNoYWRvdyBzdWJ0cmVlIHRoYXQgaGF2ZSBpZCBhdHRyaWJ1dGVzLlxuICAgICAgICAvLyBBbiBhbHRlcm5hdGl2ZWx5IGltcGxlbWVudGF0aW9uIG9mIHRoaXMgbWl4aW4gd291bGQgYmUgdG8ganVzdCBkZWZpbmVcbiAgICAgICAgLy8gYSB0aGlzLiQgZ2V0dGVyIHRoYXQgbGF6aWx5IGRvZXMgdGhpcyBzZWFyY2ggdGhlIGZpcnN0IHRpbWUgc29tZW9uZVxuICAgICAgICAvLyB0cmllcyB0byBhY2Nlc3MgdGhpcy4kLiBUaGF0IG1pZ2h0IGludHJvZHVjZSBzb21lIGNvbXBsZXhpdHkg4oCTIGlmIHRoZVxuICAgICAgICAvLyB0aGUgdHJlZSBjaGFuZ2VkIGFmdGVyIGl0IHdhcyBmaXJzdCBwb3B1bGF0ZWQsIHRoZSByZXN1bHQgb2ZcbiAgICAgICAgLy8gc2VhcmNoaW5nIGZvciBhIG5vZGUgbWlnaHQgYmUgc29tZXdoYXQgdW5wcmVkaWN0YWJsZS5cbiAgICAgICAgdGhpcy4kID0ge307XG4gICAgICAgIGNvbnN0IG5vZGVzV2l0aElkcyA9IHRoaXMuc2hhZG93Um9vdC5xdWVyeVNlbGVjdG9yQWxsKCdbaWRdJyk7XG4gICAgICAgIFtdLmZvckVhY2guY2FsbChub2Rlc1dpdGhJZHMsIG5vZGUgPT4ge1xuICAgICAgICAgIGNvbnN0IGlkID0gbm9kZS5nZXRBdHRyaWJ1dGUoJ2lkJyk7XG4gICAgICAgICAgdGhpcy4kW2lkXSA9IG5vZGU7XG4gICAgICAgIH0pO1xuICAgICAgfVxuICAgIH1cblxuICAgIC8qKlxuICAgICAqIFRoZSBjb2xsZWN0aW9uIG9mIHJlZmVyZW5jZXMgdG8gdGhlIGVsZW1lbnRzIHdpdGggSURzIGluIGEgY29tcG9uZW50J3NcbiAgICAgKiBTaGFkb3cgRE9NIHN1YnRyZWUuXG4gICAgICpcbiAgICAgKiBAdHlwZSB7b2JqZWN0fVxuICAgICAqIEBtZW1iZXIgJFxuICAgICAqL1xuICB9XG5cbiAgcmV0dXJuIFNoYWRvd0VsZW1lbnRSZWZlcmVuY2VzO1xufTtcbiIsImltcG9ydCBzeW1ib2xzIGZyb20gJy4uL3NyYy9zeW1ib2xzJztcblxuXG4vKiBFeHBvcnRlZCBmdW5jdGlvbiBleHRlbmRzIGEgYmFzZSBjbGFzcyB3aXRoIFNoYWRvd1RlbXBsYXRlLiAqL1xuZXhwb3J0IGRlZmF1bHQgKGJhc2UpID0+IHtcblxuICAvKipcbiAgICogTWl4aW4gZm9yIHN0YW1waW5nIGEgdGVtcGxhdGUgaW50byBhIFNoYWRvdyBET00gc3VidHJlZSB1cG9uIGNvbXBvbmVudFxuICAgKiBpbnN0YW50aWF0aW9uLlxuICAgKlxuICAgKiBUbyB1c2UgdGhpcyBtaXhpbiwgZGVmaW5lIGEgYHRlbXBsYXRlYCBwcm9wZXJ0eSBhcyBhIHN0cmluZyBvciBIVE1MXG4gICAqIGA8dGVtcGxhdGU+YCBlbGVtZW50OlxuICAgKlxuICAgKiAgICAgY2xhc3MgTXlFbGVtZW50IGV4dGVuZHMgU2hhZG93VGVtcGxhdGVNaXhpbihIVE1MRWxlbWVudCkge1xuICAgKiAgICAgICBnZXQgW3N5bWJvbHMudGVtcGxhdGVdKCkge1xuICAgKiAgICAgICAgIHJldHVybiBgSGVsbG8sIDxlbT53b3JsZDwvZW0+LmA7XG4gICAqICAgICAgIH1cbiAgICogICAgIH1cbiAgICpcbiAgICogV2hlbiB5b3VyIGNvbXBvbmVudCBjbGFzcyBpcyBpbnN0YW50aWF0ZWQsIGEgc2hhZG93IHJvb3Qgd2lsbCBiZSBjcmVhdGVkIG9uXG4gICAqIHRoZSBpbnN0YW5jZSwgYW5kIHRoZSBjb250ZW50cyBvZiB0aGUgdGVtcGxhdGUgd2lsbCBiZSBjbG9uZWQgaW50byB0aGVcbiAgICogc2hhZG93IHJvb3QuIElmIHlvdXIgY29tcG9uZW50IGRvZXMgbm90IGRlZmluZSBhIGB0ZW1wbGF0ZWAgcHJvcGVydHksIHRoaXNcbiAgICogbWl4aW4gaGFzIG5vIGVmZmVjdC5cbiAgICpcbiAgICogRm9yIHRoZSB0aW1lIGJlaW5nLCB0aGlzIGV4dGVuc2lvbiByZXRhaW5zIHN1cHBvcnQgZm9yIFNoYWRvdyBET00gdjAuIFRoYXRcbiAgICogd2lsbCBldmVudHVhbGx5IGJlIGRlcHJlY2F0ZWQgYXMgYnJvd3NlcnMgKGFuZCB0aGUgU2hhZG93IERPTSBwb2x5ZmlsbClcbiAgICogaW1wbGVtZW50IFNoYWRvdyBET00gdjEuXG4gICAqL1xuICBjbGFzcyBTaGFkb3dUZW1wbGF0ZSBleHRlbmRzIGJhc2Uge1xuXG4gICAgLypcbiAgICAgKiBJZiB0aGUgY29tcG9uZW50IGRlZmluZXMgYSB0ZW1wbGF0ZSwgYSBzaGFkb3cgcm9vdCB3aWxsIGJlIGNyZWF0ZWQgb24gdGhlXG4gICAgICogY29tcG9uZW50IGluc3RhbmNlLCBhbmQgdGhlIHRlbXBsYXRlIHN0YW1wZWQgaW50byBpdC5cbiAgICAgKi9cbiAgICBjb25zdHJ1Y3RvcigpIHtcbiAgICAgIHN1cGVyKCk7XG4gICAgICBsZXQgdGVtcGxhdGUgPSB0aGlzW3N5bWJvbHMudGVtcGxhdGVdO1xuICAgICAgLy8gVE9ETzogU2F2ZSB0aGUgcHJvY2Vzc2VkIHRlbXBsYXRlIHdpdGggdGhlIGNvbXBvbmVudCdzIGNsYXNzIHByb3RvdHlwZVxuICAgICAgLy8gc28gaXQgZG9lc24ndCBuZWVkIHRvIGJlIHByb2Nlc3NlZCB3aXRoIGV2ZXJ5IGluc3RhbnRpYXRpb24uXG4gICAgICBpZiAodGVtcGxhdGUpIHtcblxuICAgICAgICBpZiAodHlwZW9mIHRlbXBsYXRlID09PSAnc3RyaW5nJykge1xuICAgICAgICAgIC8vIFVwZ3JhZGUgcGxhaW4gc3RyaW5nIHRvIHJlYWwgdGVtcGxhdGUuXG4gICAgICAgICAgdGVtcGxhdGUgPSBjcmVhdGVUZW1wbGF0ZVdpdGhJbm5lckhUTUwodGVtcGxhdGUpO1xuICAgICAgICB9XG5cbiAgICAgICAgaWYgKHdpbmRvdy5TaGFkb3dET01Qb2x5ZmlsbCkge1xuICAgICAgICAgIHNoaW1UZW1wbGF0ZVN0eWxlcyh0ZW1wbGF0ZSwgdGhpcy5sb2NhbE5hbWUpO1xuICAgICAgICB9XG5cbiAgICAgICAgY29uc3Qgcm9vdCA9IHRoaXMuYXR0YWNoU2hhZG93KHsgbW9kZTogJ29wZW4nIH0pO1xuICAgICAgICBjb25zdCBjbG9uZSA9IGRvY3VtZW50LmltcG9ydE5vZGUodGVtcGxhdGUuY29udGVudCwgdHJ1ZSk7XG4gICAgICAgIHJvb3QuYXBwZW5kQ2hpbGQoY2xvbmUpO1xuICAgICAgfVxuICAgIH1cblxuICB9XG5cbiAgcmV0dXJuIFNoYWRvd1RlbXBsYXRlO1xufTtcblxuXG4vLyBDb252ZXJ0IGEgcGxhaW4gc3RyaW5nIG9mIEhUTUwgaW50byBhIHJlYWwgdGVtcGxhdGUgZWxlbWVudC5cbmZ1bmN0aW9uIGNyZWF0ZVRlbXBsYXRlV2l0aElubmVySFRNTChpbm5lckhUTUwpIHtcbiAgY29uc3QgdGVtcGxhdGUgPSBkb2N1bWVudC5jcmVhdGVFbGVtZW50KCd0ZW1wbGF0ZScpO1xuICAvLyBSRVZJRVc6IElzIHRoZXJlIGFuIGVhc2llciB3YXkgdG8gZG8gdGhpcz9cbiAgLy8gV2UnZCBsaWtlIHRvIGp1c3Qgc2V0IGlubmVySFRNTCBvbiB0aGUgdGVtcGxhdGUgY29udGVudCwgYnV0IHNpbmNlIGl0J3NcbiAgLy8gYSBEb2N1bWVudEZyYWdtZW50LCB0aGF0IGRvZXNuJ3Qgd29yay5cbiAgY29uc3QgZGl2ID0gZG9jdW1lbnQuY3JlYXRlRWxlbWVudCgnZGl2Jyk7XG4gIGRpdi5pbm5lckhUTUwgPSBpbm5lckhUTUw7XG4gIHdoaWxlIChkaXYuY2hpbGROb2Rlcy5sZW5ndGggPiAwKSB7XG4gICAgdGVtcGxhdGUuY29udGVudC5hcHBlbmRDaGlsZChkaXYuY2hpbGROb2Rlc1swXSk7XG4gIH1cbiAgcmV0dXJuIHRlbXBsYXRlO1xufVxuXG4vLyBJbnZva2UgYmFzaWMgc3R5bGUgc2hpbW1pbmcgd2l0aCBTaGFkb3dDU1MuXG5mdW5jdGlvbiBzaGltVGVtcGxhdGVTdHlsZXModGVtcGxhdGUsIHRhZykge1xuICB3aW5kb3cuV2ViQ29tcG9uZW50cy5TaGFkb3dDU1Muc2hpbVN0eWxpbmcodGVtcGxhdGUuY29udGVudCwgdGFnKTtcbn1cbiIsImltcG9ydCBjcmVhdGVTeW1ib2wgZnJvbSAnLi9jcmVhdGVTeW1ib2wnO1xuaW1wb3J0IHN5bWJvbHMgZnJvbSAnLi9zeW1ib2xzJztcblxuXG4vLyBTeW1ib2xzIGZvciBwcml2YXRlIGRhdGEgbWVtYmVycyBvbiBhbiBlbGVtZW50LlxuY29uc3QgY2FuU2VsZWN0TmV4dFN5bWJvbCA9IGNyZWF0ZVN5bWJvbCgnY2FuU2VsZWN0TmV4dCcpO1xuY29uc3QgY2FuU2VsZWN0UHJldmlvdXNTeW1ib2wgPSBjcmVhdGVTeW1ib2woJ2NhblNlbGVjdFByZXZpb3VzJyk7XG5jb25zdCBzZWxlY3Rpb25SZXF1aXJlZFN5bWJvbCA9IGNyZWF0ZVN5bWJvbCgnc2VsZWN0aW9uUmVxdWlyZWQnKTtcbmNvbnN0IHNlbGVjdGlvbldyYXBzU3ltYm9sID0gY3JlYXRlU3ltYm9sKCdzZWxlY3Rpb25XcmFwcycpO1xuXG4vLyBXZSB3YW50IHRvIGV4cG9zZSBib3RoIHNlbGVjdGVkSW5kZXggYW5kIHNlbGVjdGVkSXRlbSBhcyBpbmRlcGVuZGVudFxuLy8gcHJvcGVydGllcyBidXQga2VlcCB0aGVtIGluIHN5bmMuIFRoaXMgYWxsb3dzIGEgY29tcG9uZW50IHVzZXIgdG8gcmVmZXJlbmNlXG4vLyB0aGUgc2VsZWN0aW9uIGJ5IHdoYXRldmVyIG1lYW5zIGlzIG1vc3QgbmF0dXJhbCBmb3IgdGhlaXIgc2l0dWF0aW9uLlxuLy9cbi8vIFRvIGVmZmljaWVudGx5IGtlZXAgdGhlc2UgcHJvcGVydGllcyBpbiBzeW5jLCB3ZSB0cmFjayBcImV4dGVybmFsXCIgYW5kXG4vLyBcImludGVybmFsXCIgcmVmZXJlbmNlcyBmb3IgZWFjaCBwcm9wZXJ0eTpcbi8vXG4vLyBUaGUgZXh0ZXJuYWwgaW5kZXggb3IgaXRlbSBpcyB0aGUgb25lIHdlIHJlcG9ydCB0byB0aGUgb3V0c2lkZSB3b3JsZCB3aGVuXG4vLyBhc2tlZCBmb3Igc2VsZWN0aW9uLiAgV2hlbiBoYW5kbGluZyBhIGNoYW5nZSB0byBpbmRleCBvciBpdGVtLCB3ZSB1cGRhdGUgdGhlXG4vLyBleHRlcm5hbCByZWZlcmVuY2UgYXMgc29vbiBhcyBwb3NzaWJsZSwgc28gdGhhdCBpZiBhbnlvbmUgaW1tZWRpYXRlbHkgYXNrc1xuLy8gZm9yIHRoZSBjdXJyZW50IHNlbGVjdGlvbiwgdGhleSB3aWxsIHJlY2VpdmUgYSBzdGFibGUgYW5zd2VyLlxuLy9cbi8vIFRoZSBpbnRlcm5hbCBpbmRleCBvciBpdGVtIHRyYWNrcyB3aGljaGV2ZXIgaW5kZXggb3IgaXRlbSBsYXN0IHJlY2VpdmVkIHRoZVxuLy8gZnVsbCBzZXQgb2YgcHJvY2Vzc2luZy4gUHJvY2Vzc2luZyBpbmNsdWRlcyByYWlzaW5nIGEgY2hhbmdlIGV2ZW50IGZvciB0aGVcbi8vIG5ldyB2YWx1ZS4gT25jZSB3ZSd2ZSBiZWd1biB0aGF0IHByb2Nlc3NpbmcsIHdlIHN0b3JlIHRoZSBuZXcgdmFsdWUgYXMgdGhlXG4vLyBpbnRlcm5hbCB2YWx1ZSB0byBpbmRpY2F0ZSB3ZSd2ZSBoYW5kbGVkIGl0LlxuLy9cbmNvbnN0IGV4dGVybmFsU2VsZWN0ZWRJbmRleFN5bWJvbCA9IGNyZWF0ZVN5bWJvbCgnZXh0ZXJuYWxTZWxlY3RlZEluZGV4Jyk7XG5jb25zdCBleHRlcm5hbFNlbGVjdGVkSXRlbVN5bWJvbCA9IGNyZWF0ZVN5bWJvbCgnZXh0ZXJuYWxTZWxlY3RlZEl0ZW0nKTtcbmNvbnN0IGludGVybmFsU2VsZWN0ZWRJbmRleFN5bWJvbCA9IGNyZWF0ZVN5bWJvbCgnaW50ZXJuYWxTZWxlY3RlZEluZGV4Jyk7XG5jb25zdCBpbnRlcm5hbFNlbGVjdGVkSXRlbVN5bWJvbCA9IGNyZWF0ZVN5bWJvbCgnaW50ZXJuYWxTZWxlY3RlZEl0ZW0nKTtcblxuXG4vKiBFeHBvcnRlZCBmdW5jdGlvbiBleHRlbmRzIGEgYmFzZSBjbGFzcyB3aXRoIFNpbmdsZVNlbGVjdGlvbi4gKi9cbmV4cG9ydCBkZWZhdWx0IChiYXNlKSA9PiB7XG5cbiAgLyoqXG4gICAqIE1peGluIHdoaWNoIG1hbmFnZXMgc2luZ2xlLXNlbGVjdGlvbiBzZW1hbnRpY3MgZm9yIGl0ZW1zIGluIGEgbGlzdC5cbiAgICpcbiAgICogVGhpcyBtaXhpbiBleHBlY3RzIGEgY29tcG9uZW50IHRvIHByb3ZpZGUgYW4gYGl0ZW1zYCBBcnJheSBvciBOb2RlTGlzdCBvZlxuICAgKiBhbGwgZWxlbWVudHMgaW4gdGhlIGxpc3QuIEEgc3RhbmRhcmQgd2F5IHRvIGRvIHRoYXQgd2l0aCBpcyB0aGVcbiAgICogW0NvbnRlbnRJdGVtc01peGluXShDb250ZW50SXRlbXNNaXhpbi5tZCksIHdoaWNoIHRha2VzIGEgY29tcG9uZW50J3NcbiAgICogY29udGVudCAodHlwaWNhbGx5IGl0cyBkaXN0cmlidXRlZCBjaGlsZHJlbikgYXMgdGhlIHNldCBvZiBsaXN0IGl0ZW1zOyBzZWVcbiAgICogdGhhdCBtaXhpbiBmb3IgZGV0YWlscy5cbiAgICpcbiAgICogVGhpcyBtaXhpbiB0cmFja3MgYSBzaW5nbGUgc2VsZWN0ZWQgaXRlbSBpbiB0aGUgbGlzdCwgYW5kIHByb3ZpZGVzIG1lYW5zIHRvXG4gICAqIGdldCBhbmQgc2V0IHRoYXQgc3RhdGUgYnkgaXRlbSBwb3NpdGlvbiAoYHNlbGVjdGVkSW5kZXhgKSBvciBpdGVtIGlkZW50aXR5XG4gICAqIChgc2VsZWN0ZWRJdGVtYCkuIFRoZSBzZWxlY3Rpb24gY2FuIGJlIG1vdmVkIGluIHRoZSBsaXN0IHZpYSB0aGUgbWV0aG9kc1xuICAgKiBgc2VsZWN0Rmlyc3RgLCBgc2VsZWN0TGFzdGAsIGBzZWxlY3ROZXh0YCwgYW5kIGBzZWxlY3RQcmV2aW91c2AuXG4gICAqXG4gICAqIFRoaXMgbWl4aW4gZG9lcyBub3QgcHJvZHVjZSBhbnkgdXNlci12aXNpYmxlIGVmZmVjdHMgdG8gcmVwcmVzZW50XG4gICAqIHNlbGVjdGlvbi4gT3RoZXIgbWl4aW5zLCBzdWNoIGFzXG4gICAqIFtTZWxlY3Rpb25BcmlhQWN0aXZlTWl4aW5dKFNlbGVjdGlvbkFyaWFBY3RpdmVNaXhpbi5tZCksXG4gICAqIFtTZWxlY3Rpb25IaWdobGlnaHRNaXhpbl0oU2VsZWN0aW9uSGlnaGxpZ2h0TWl4aW4ubWQpIGFuZFxuICAgKiBbU2VsZWN0aW9uSW5WaWV3TWl4aW5dKFNlbGVjdGlvbkluVmlld01peGluLm1kKSwgbW9kaWZ5IHRoZSBzZWxlY3RlZCBpdGVtXG4gICAqIGluIGNvbW1vbiB3YXlzIHRvIGxldCB0aGUgdXNlciBrbm93IGEgZ2l2ZW4gaXRlbSBpcyBzZWxlY3RlZCBvciBub3RcbiAgICogc2VsZWN0ZWQuXG4gICAqL1xuICBjbGFzcyBTaW5nbGVTZWxlY3Rpb24gZXh0ZW5kcyBiYXNlIHtcblxuICAgIGNvbnN0cnVjdG9yKCkge1xuICAgICAgc3VwZXIoKTtcbiAgICAgIC8vIFNldCBkZWZhdWx0cy5cbiAgICAgIGlmICh0eXBlb2YgdGhpcy5zZWxlY3Rpb25SZXF1aXJlZCA9PT0gJ3VuZGVmaW5lZCcpIHtcbiAgICAgICAgdGhpcy5zZWxlY3Rpb25SZXF1aXJlZCA9IHRoaXNbc3ltYm9scy5kZWZhdWx0c10uc2VsZWN0aW9uUmVxdWlyZWQ7XG4gICAgICB9XG4gICAgICBpZiAodHlwZW9mIHRoaXMuc2VsZWN0aW9uV3JhcHMgPT09ICd1bmRlZmluZWQnKSB7XG4gICAgICAgIHRoaXMuc2VsZWN0aW9uV3JhcHMgPSB0aGlzW3N5bWJvbHMuZGVmYXVsdHNdLnNlbGVjdGlvbldyYXBzO1xuICAgICAgfVxuICAgIH1cblxuICAgIC8qKlxuICAgICAqIFRydWUgaWYgdGhlIHNlbGVjdGlvbiBjYW4gYmUgbW92ZWQgdG8gdGhlIG5leHQgaXRlbSwgZmFsc2UgaWYgbm90ICh0aGVcbiAgICAgKiBzZWxlY3RlZCBpdGVtIGlzIHRoZSBsYXN0IGl0ZW0gaW4gdGhlIGxpc3QpLlxuICAgICAqXG4gICAgICogQHR5cGUge2Jvb2xlYW59XG4gICAgICovXG4gICAgZ2V0IGNhblNlbGVjdE5leHQoKSB7XG4gICAgICByZXR1cm4gdGhpc1tjYW5TZWxlY3ROZXh0U3ltYm9sXTtcbiAgICB9XG4gICAgc2V0IGNhblNlbGVjdE5leHQoY2FuU2VsZWN0TmV4dCkge1xuICAgICAgY29uc3QgcHJldmlvdXNDYW5TZWxlY3ROZXh0ID0gdGhpc1tjYW5TZWxlY3ROZXh0U3ltYm9sXTtcbiAgICAgIHRoaXNbY2FuU2VsZWN0TmV4dFN5bWJvbF0gPSBjYW5TZWxlY3ROZXh0O1xuICAgICAgaWYgKCdjYW5TZWxlY3ROZXh0JyBpbiBiYXNlLnByb3RvdHlwZSkgeyBzdXBlci5jYW5TZWxlY3ROZXh0ID0gY2FuU2VsZWN0TmV4dDsgfVxuICAgICAgaWYgKGNhblNlbGVjdE5leHQgIT09IHByZXZpb3VzQ2FuU2VsZWN0TmV4dCkge1xuICAgICAgICB0aGlzLmRpc3BhdGNoRXZlbnQobmV3IEN1c3RvbUV2ZW50KCdjYW4tc2VsZWN0LW5leHQtY2hhbmdlZCcpKTtcbiAgICAgIH1cbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBUcnVlIGlmIHRoZSBzZWxlY3Rpb24gY2FuIGJlIG1vdmVkIHRvIHRoZSBwcmV2aW91cyBpdGVtLCBmYWxzZSBpZiBub3RcbiAgICAgKiAodGhlIHNlbGVjdGVkIGl0ZW0gaXMgdGhlIGZpcnN0IG9uZSBpbiB0aGUgbGlzdCkuXG4gICAgICpcbiAgICAgKiBAdHlwZSB7Ym9vbGVhbn1cbiAgICAgKi9cbiAgICBnZXQgY2FuU2VsZWN0UHJldmlvdXMoKSB7XG4gICAgICByZXR1cm4gdGhpc1tjYW5TZWxlY3RQcmV2aW91c1N5bWJvbF07XG4gICAgfVxuICAgIHNldCBjYW5TZWxlY3RQcmV2aW91cyhjYW5TZWxlY3RQcmV2aW91cykge1xuICAgICAgY29uc3QgcHJldmlvdXNDYW5TZWxlY3RQcmV2aW91cyA9IHRoaXNbY2FuU2VsZWN0UHJldmlvdXNTeW1ib2xdO1xuICAgICAgdGhpc1tjYW5TZWxlY3RQcmV2aW91c1N5bWJvbF0gPSBjYW5TZWxlY3RQcmV2aW91cztcbiAgICAgIGlmICgnY2FuU2VsZWN0UHJldmlvdXMnIGluIGJhc2UucHJvdG90eXBlKSB7IHN1cGVyLmNhblNlbGVjdFByZXZpb3VzID0gY2FuU2VsZWN0UHJldmlvdXM7IH1cbiAgICAgIGlmIChjYW5TZWxlY3RQcmV2aW91cyAhPT0gcHJldmlvdXNDYW5TZWxlY3RQcmV2aW91cykge1xuICAgICAgICB0aGlzLmRpc3BhdGNoRXZlbnQobmV3IEN1c3RvbUV2ZW50KCdjYW4tc2VsZWN0LXByZXZpb3VzLWNoYW5nZWQnKSk7XG4gICAgICB9XG4gICAgfVxuXG4gICAgZ2V0IFtzeW1ib2xzLmRlZmF1bHRzXSgpIHtcbiAgICAgIGNvbnN0IGRlZmF1bHRzID0gc3VwZXJbc3ltYm9scy5kZWZhdWx0c10gfHwge307XG4gICAgICBkZWZhdWx0cy5zZWxlY3Rpb25SZXF1aXJlZCA9IGZhbHNlO1xuICAgICAgZGVmYXVsdHMuc2VsZWN0aW9uV3JhcHMgPSBmYWxzZTtcbiAgICAgIHJldHVybiBkZWZhdWx0cztcbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBIYW5kbGUgYSBuZXcgaXRlbSBiZWluZyBhZGRlZCB0byB0aGUgbGlzdC5cbiAgICAgKlxuICAgICAqIFRoZSBkZWZhdWx0IGltcGxlbWVudGF0aW9uIG9mIHRoaXMgbWV0aG9kIHNpbXBseSBzZXRzIHRoZSBpdGVtJ3NcbiAgICAgKiBzZWxlY3Rpb24gc3RhdGUgdG8gZmFsc2UuXG4gICAgICpcbiAgICAgKiBAcGFyYW0ge0hUTUxFbGVtZW50fSBpdGVtIC0gdGhlIGl0ZW0gYmVpbmcgYWRkZWRcbiAgICAgKi9cbiAgICBbc3ltYm9scy5pdGVtQWRkZWRdKGl0ZW0pIHtcbiAgICAgIGlmIChzdXBlcltzeW1ib2xzLml0ZW1BZGRlZF0pIHsgc3VwZXJbc3ltYm9scy5pdGVtQWRkZWRdKGl0ZW0pOyB9XG4gICAgICB0aGlzW3N5bWJvbHMuaXRlbVNlbGVjdGVkXShpdGVtLCBpdGVtID09PSB0aGlzLnNlbGVjdGVkSXRlbSk7XG4gICAgfVxuXG4gICAgW3N5bWJvbHMuaXRlbXNDaGFuZ2VkXSgpIHtcbiAgICAgIGlmIChzdXBlcltzeW1ib2xzLml0ZW1zQ2hhbmdlZF0pIHsgc3VwZXJbc3ltYm9scy5pdGVtc0NoYW5nZWRdKCk7IH1cblxuICAgICAgLy8gSW4gY2FzZSBzZWxlY3RlZCBpdGVtIGNoYW5nZWQgcG9zaXRpb24gb3Igd2FzIHJlbW92ZWQuXG4gICAgICB0cmFja1NlbGVjdGVkSXRlbSh0aGlzKTtcblxuICAgICAgLy8gSW4gY2FzZSB0aGUgY2hhbmdlIGluIGl0ZW1zIGFmZmVjdGVkIHdoaWNoIG5hdmlnYXRpb25zIGFyZSBwb3NzaWJsZS5cbiAgICAgIHVwZGF0ZVBvc3NpYmxlTmF2aWdhdGlvbnModGhpcyk7XG4gICAgfVxuXG4gICAgLyoqXG4gICAgICogQXBwbHkgdGhlIGluZGljYXRlIHNlbGVjdGlvbiBzdGF0ZSB0byB0aGUgaXRlbS5cbiAgICAgKlxuICAgICAqIFRoZSBkZWZhdWx0IGltcGxlbWVudGF0aW9uIG9mIHRoaXMgbWV0aG9kIGRvZXMgbm90aGluZy4gVXNlci12aXNpYmxlXG4gICAgICogZWZmZWN0cyB3aWxsIHR5cGljYWxseSBiZSBoYW5kbGVkIGJ5IG90aGVyIG1peGlucy5cbiAgICAgKlxuICAgICAqIEBwYXJhbSB7SFRNTEVsZW1lbnR9IGl0ZW0gLSB0aGUgaXRlbSBiZWluZyBzZWxlY3RlZC9kZXNlbGVjdGVkXG4gICAgICogQHBhcmFtIHtib29sZWFufSBzZWxlY3RlZCAtIHRydWUgaWYgdGhlIGl0ZW0gaXMgc2VsZWN0ZWQsIGZhbHNlIGlmIG5vdFxuICAgICAqL1xuICAgIFtzeW1ib2xzLml0ZW1TZWxlY3RlZF0oaXRlbSwgc2VsZWN0ZWQpIHtcbiAgICAgIGlmIChzdXBlcltzeW1ib2xzLml0ZW1TZWxlY3RlZF0pIHsgc3VwZXJbc3ltYm9scy5pdGVtU2VsZWN0ZWRdKGl0ZW0sIHNlbGVjdGVkKTsgfVxuICAgIH1cblxuICAgIC8qKlxuICAgICAqIFRoZSBpbmRleCBvZiB0aGUgaXRlbSB3aGljaCBpcyBjdXJyZW50bHkgc2VsZWN0ZWQuXG4gICAgICpcbiAgICAgKiBBIGBzZWxlY3RlZEluZGV4YCBvZiAtMSBpbmRpY2F0ZXMgdGhlcmUgaXMgbm8gc2VsZWN0aW9uLiBTZXR0aW5nIHRoaXNcbiAgICAgKiBwcm9wZXJ0eSB0byAtMSB3aWxsIHJlbW92ZSBhbnkgZXhpc3Rpbmcgc2VsZWN0aW9uLlxuICAgICAqXG4gICAgICogQHR5cGUge251bWJlcn1cbiAgICAgKi9cbiAgICBnZXQgc2VsZWN0ZWRJbmRleCgpIHtcbiAgICAgIHJldHVybiB0aGlzW2V4dGVybmFsU2VsZWN0ZWRJbmRleFN5bWJvbF0gIT0gbnVsbCA/XG4gICAgICAgIHRoaXNbZXh0ZXJuYWxTZWxlY3RlZEluZGV4U3ltYm9sXSA6XG4gICAgICAgIC0xO1xuICAgIH1cbiAgICBzZXQgc2VsZWN0ZWRJbmRleChpbmRleCkge1xuICAgICAgLy8gU2VlIG5vdGVzIGF0IHRvcCBhYm91dCBpbnRlcm5hbCB2cy4gZXh0ZXJuYWwgY29waWVzIG9mIHRoaXMgcHJvcGVydHkuXG4gICAgICBjb25zdCBwcmV2aW91c1NlbGVjdGVkSW5kZXggPSB0aGlzW2ludGVybmFsU2VsZWN0ZWRJbmRleFN5bWJvbF07XG4gICAgICBsZXQgaXRlbTtcbiAgICAgIGlmIChpbmRleCAhPT0gdGhpc1tleHRlcm5hbFNlbGVjdGVkSW5kZXhTeW1ib2xdKSB7XG4gICAgICAgIC8vIFN0b3JlIHRoZSBuZXcgaW5kZXggYW5kIHRoZSBjb3JyZXNwb25kaW5nIGl0ZW0uXG4gICAgICAgIGNvbnN0IGl0ZW1zID0gdGhpcy5pdGVtcztcbiAgICAgICAgY29uc3QgaGFzSXRlbXMgPSBpdGVtcyAmJiBpdGVtcy5sZW5ndGggPiAwO1xuICAgICAgICBpZiAoIShoYXNJdGVtcyAmJiBpbmRleCA+PSAwICYmIGluZGV4IDwgaXRlbXMubGVuZ3RoKSkge1xuICAgICAgICAgIGluZGV4ID0gLTE7IC8vIE5vIGl0ZW0gYXQgdGhhdCBpbmRleC5cbiAgICAgICAgfVxuICAgICAgICB0aGlzW2V4dGVybmFsU2VsZWN0ZWRJbmRleFN5bWJvbF0gPSBpbmRleDtcbiAgICAgICAgaXRlbSA9IGhhc0l0ZW1zICYmIGluZGV4ID49IDAgPyBpdGVtc1tpbmRleF0gOiBudWxsO1xuICAgICAgICB0aGlzW2V4dGVybmFsU2VsZWN0ZWRJdGVtU3ltYm9sXSA9IGl0ZW07XG4gICAgICB9IGVsc2Uge1xuICAgICAgICBpdGVtID0gdGhpc1tleHRlcm5hbFNlbGVjdGVkSXRlbVN5bWJvbF07XG4gICAgICB9XG5cbiAgICAgIC8vIE5vdyBsZXQgc3VwZXIgZG8gYW55IHdvcmsuXG4gICAgICBpZiAoJ3NlbGVjdGVkSW5kZXgnIGluIGJhc2UucHJvdG90eXBlKSB7IHN1cGVyLnNlbGVjdGVkSW5kZXggPSBpbmRleDsgfVxuXG4gICAgICBpZiAoaW5kZXggIT09IHByZXZpb3VzU2VsZWN0ZWRJbmRleCkge1xuICAgICAgICAvLyBUaGUgc2VsZWN0ZWQgaW5kZXggY2hhbmdlZC5cbiAgICAgICAgdGhpc1tpbnRlcm5hbFNlbGVjdGVkSW5kZXhTeW1ib2xdID0gaW5kZXg7XG5cbiAgICAgICAgY29uc3QgZXZlbnQgPSBuZXcgQ3VzdG9tRXZlbnQoJ3NlbGVjdGVkLWluZGV4LWNoYW5nZWQnLCB7XG4gICAgICAgICAgZGV0YWlsOiB7XG4gICAgICAgICAgICBzZWxlY3RlZEluZGV4OiBpbmRleCxcbiAgICAgICAgICAgIHZhbHVlOiBpbmRleCAvLyBmb3IgUG9seW1lciBiaW5kaW5nLiBUT0RPOiBWZXJpZnkgc3RpbGwgbmVjZXNzYXJ5XG4gICAgICAgICAgfVxuICAgICAgICB9KTtcbiAgICAgICAgdGhpcy5kaXNwYXRjaEV2ZW50KGV2ZW50KTtcbiAgICAgIH1cblxuICAgICAgaWYgKHRoaXNbaW50ZXJuYWxTZWxlY3RlZEl0ZW1TeW1ib2xdICE9PSBpdGVtKSB7XG4gICAgICAgIC8vIFVwZGF0ZSBzZWxlY3RlZEl0ZW0gcHJvcGVydHkgc28gaXQgY2FuIGhhdmUgaXRzIG93biBlZmZlY3RzLlxuICAgICAgICB0aGlzLnNlbGVjdGVkSXRlbSA9IGl0ZW07XG4gICAgICB9XG4gICAgfVxuXG4gICAgLyoqXG4gICAgICogVGhlIGN1cnJlbnRseSBzZWxlY3RlZCBpdGVtLCBvciBudWxsIGlmIHRoZXJlIGlzIG5vIHNlbGVjdGlvbi5cbiAgICAgKlxuICAgICAqIFNldHRpbmcgdGhpcyBwcm9wZXJ0eSB0byBudWxsIGRlc2VsZWN0cyBhbnkgY3VycmVudGx5LXNlbGVjdGVkIGl0ZW0uXG4gICAgICogU2V0dGluZyB0aGlzIHByb3BlcnR5IHRvIGFuIG9iamVjdCB0aGF0IGlzIG5vdCBpbiB0aGUgbGlzdCBoYXMgbm8gZWZmZWN0LlxuICAgICAqXG4gICAgICogVE9ETzogRXZlbiBpZiBzZWxlY3Rpb25SZXF1aXJlZCwgY2FuIHN0aWxsIGV4cGxpY2l0bHkgc2V0IHNlbGVjdGVkSXRlbSB0byBudWxsLlxuICAgICAqIFRPRE86IElmIHNlbGVjdGlvblJlcXVpcmVkLCBsZWF2ZSBzZWxlY3Rpb24gYWxvbmU/XG4gICAgICpcbiAgICAgKiBAdHlwZSB7b2JqZWN0fVxuICAgICAqL1xuICAgIGdldCBzZWxlY3RlZEl0ZW0oKSB7XG4gICAgICByZXR1cm4gdGhpc1tleHRlcm5hbFNlbGVjdGVkSXRlbVN5bWJvbF0gfHwgbnVsbDtcbiAgICB9XG4gICAgc2V0IHNlbGVjdGVkSXRlbShpdGVtKSB7XG4gICAgICAvLyBTZWUgbm90ZXMgYXQgdG9wIGFib3V0IGludGVybmFsIHZzLiBleHRlcm5hbCBjb3BpZXMgb2YgdGhpcyBwcm9wZXJ0eS5cbiAgICAgIGNvbnN0IHByZXZpb3VzU2VsZWN0ZWRJdGVtID0gdGhpc1tpbnRlcm5hbFNlbGVjdGVkSXRlbVN5bWJvbF07XG4gICAgICBsZXQgaW5kZXg7XG4gICAgICBpZiAoaXRlbSAhPT0gdGhpc1tleHRlcm5hbFNlbGVjdGVkSXRlbVN5bWJvbF0pIHtcbiAgICAgICAgLy8gU3RvcmUgaXRlbSBhbmQgbG9vayB1cCBjb3JyZXNwb25kaW5nIGluZGV4LlxuICAgICAgICBjb25zdCBpdGVtcyA9IHRoaXMuaXRlbXM7XG4gICAgICAgIGNvbnN0IGhhc0l0ZW1zID0gaXRlbXMgJiYgaXRlbXMubGVuZ3RoID4gMDtcbiAgICAgICAgaW5kZXggPSBoYXNJdGVtcyA/IEFycmF5LnByb3RvdHlwZS5pbmRleE9mLmNhbGwoaXRlbXMsIGl0ZW0pIDogLTE7XG4gICAgICAgIHRoaXNbZXh0ZXJuYWxTZWxlY3RlZEluZGV4U3ltYm9sXSA9IGluZGV4O1xuICAgICAgICBpZiAoaW5kZXggPCAwKSB7XG4gICAgICAgICAgaXRlbSA9IG51bGw7IC8vIFRoZSBpbmRpY2F0ZWQgaXRlbSBpc24ndCBhY3R1YWxseSBpbiBgaXRlbXNgLlxuICAgICAgICB9XG4gICAgICAgIHRoaXNbZXh0ZXJuYWxTZWxlY3RlZEl0ZW1TeW1ib2xdID0gaXRlbTtcbiAgICAgIH0gZWxzZSB7XG4gICAgICAgIGluZGV4ID0gdGhpc1tleHRlcm5hbFNlbGVjdGVkSW5kZXhTeW1ib2xdO1xuICAgICAgfVxuXG4gICAgICAvLyBOb3cgbGV0IHN1cGVyIGRvIGFueSB3b3JrLlxuICAgICAgaWYgKCdzZWxlY3RlZEl0ZW0nIGluIGJhc2UucHJvdG90eXBlKSB7IHN1cGVyLnNlbGVjdGVkSXRlbSA9IGl0ZW07IH1cblxuICAgICAgaWYgKGl0ZW0gIT09IHByZXZpb3VzU2VsZWN0ZWRJdGVtKSB7XG4gICAgICAgIC8vIFRoZSBzZWxlY3RlZCBpdGVtIGNoYW5nZWQuXG4gICAgICAgIHRoaXNbaW50ZXJuYWxTZWxlY3RlZEl0ZW1TeW1ib2xdID0gaXRlbTtcblxuICAgICAgICBpZiAocHJldmlvdXNTZWxlY3RlZEl0ZW0pIHtcbiAgICAgICAgICAvLyBVcGRhdGUgc2VsZWN0aW9uIHN0YXRlIG9mIG9sZCBpdGVtLlxuICAgICAgICAgIHRoaXNbc3ltYm9scy5pdGVtU2VsZWN0ZWRdKHByZXZpb3VzU2VsZWN0ZWRJdGVtLCBmYWxzZSk7XG4gICAgICAgIH1cbiAgICAgICAgaWYgKGl0ZW0pIHtcbiAgICAgICAgICAvLyBVcGRhdGUgc2VsZWN0aW9uIHN0YXRlIHRvIG5ldyBpdGVtLlxuICAgICAgICAgIHRoaXNbc3ltYm9scy5pdGVtU2VsZWN0ZWRdKGl0ZW0sIHRydWUpO1xuICAgICAgICB9XG5cbiAgICAgICAgdXBkYXRlUG9zc2libGVOYXZpZ2F0aW9ucyh0aGlzKTtcblxuICAgICAgICBjb25zdCBldmVudCA9IG5ldyBDdXN0b21FdmVudCgnc2VsZWN0ZWQtaXRlbS1jaGFuZ2VkJywge1xuICAgICAgICAgIGRldGFpbDoge1xuICAgICAgICAgICAgc2VsZWN0ZWRJdGVtOiBpdGVtLFxuICAgICAgICAgICAgdmFsdWU6IGl0ZW0gLy8gZm9yIFBvbHltZXIgYmluZGluZ1xuICAgICAgICAgIH1cbiAgICAgICAgfSk7XG4gICAgICAgIHRoaXMuZGlzcGF0Y2hFdmVudChldmVudCk7XG4gICAgICB9XG5cbiAgICAgIGlmICh0aGlzW2ludGVybmFsU2VsZWN0ZWRJbmRleFN5bWJvbF0gIT09IGluZGV4KSB7XG4gICAgICAgIC8vIFVwZGF0ZSBzZWxlY3RlZEluZGV4IHByb3BlcnR5IHNvIGl0IGNhbiBoYXZlIGl0cyBvd24gZWZmZWN0cy5cbiAgICAgICAgdGhpcy5zZWxlY3RlZEluZGV4ID0gaW5kZXg7XG4gICAgICB9XG4gICAgfVxuXG4gICAgLyoqXG4gICAgICogU2VsZWN0IHRoZSBmaXJzdCBpdGVtIGluIHRoZSBsaXN0LlxuICAgICAqL1xuICAgIHNlbGVjdEZpcnN0KCkge1xuICAgICAgaWYgKHN1cGVyLnNlbGVjdEZpcnN0KSB7IHN1cGVyLnNlbGVjdEZpcnN0KCk7IH1cbiAgICAgIHJldHVybiBzZWxlY3RJbmRleCh0aGlzLCAwKTtcbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBUcnVlIGlmIHRoZSBsaXN0IHNob3VsZCBhbHdheXMgaGF2ZSBhIHNlbGVjdGlvbiAoaWYgaXQgaGFzIGl0ZW1zKS5cbiAgICAgKlxuICAgICAqIEB0eXBlIHtib29sZWFufVxuICAgICAqIEBkZWZhdWx0IGZhbHNlXG4gICAgICovXG4gICAgZ2V0IHNlbGVjdGlvblJlcXVpcmVkKCkge1xuICAgICAgcmV0dXJuIHRoaXNbc2VsZWN0aW9uUmVxdWlyZWRTeW1ib2xdO1xuICAgIH1cbiAgICBzZXQgc2VsZWN0aW9uUmVxdWlyZWQoc2VsZWN0aW9uUmVxdWlyZWQpIHtcbiAgICAgIHRoaXNbc2VsZWN0aW9uUmVxdWlyZWRTeW1ib2xdID0gc2VsZWN0aW9uUmVxdWlyZWQ7XG4gICAgICBpZiAoJ3NlbGVjdGlvblJlcXVpcmVkJyBpbiBiYXNlLnByb3RvdHlwZSkgeyBzdXBlci5zZWxlY3Rpb25SZXF1aXJlZCA9IHNlbGVjdGlvblJlcXVpcmVkOyB9XG4gICAgICB0cmFja1NlbGVjdGVkSXRlbSh0aGlzKTtcbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBUcnVlIGlmIHNlbGVjdGlvbiBuYXZpZ2F0aW9ucyB3cmFwIGZyb20gbGFzdCB0byBmaXJzdCwgYW5kIHZpY2UgdmVyc2EuXG4gICAgICpcbiAgICAgKiBAdHlwZSB7Ym9vbGVhbn1cbiAgICAgKiBAZGVmYXVsdCBmYWxzZVxuICAgICAqL1xuICAgIGdldCBzZWxlY3Rpb25XcmFwcygpIHtcbiAgICAgIHJldHVybiB0aGlzW3NlbGVjdGlvbldyYXBzU3ltYm9sXTtcbiAgICB9XG4gICAgc2V0IHNlbGVjdGlvbldyYXBzKHZhbHVlKSB7XG4gICAgICB0aGlzW3NlbGVjdGlvbldyYXBzU3ltYm9sXSA9IFN0cmluZyh2YWx1ZSkgPT09ICd0cnVlJztcbiAgICAgIGlmICgnc2VsZWN0aW9uV3JhcHMnIGluIGJhc2UucHJvdG90eXBlKSB7IHN1cGVyLnNlbGVjdGlvbldyYXBzID0gdmFsdWU7IH1cbiAgICAgIHVwZGF0ZVBvc3NpYmxlTmF2aWdhdGlvbnModGhpcyk7XG4gICAgfVxuXG4gICAgLyoqXG4gICAgICogU2VsZWN0IHRoZSBsYXN0IGl0ZW0gaW4gdGhlIGxpc3QuXG4gICAgICovXG4gICAgc2VsZWN0TGFzdCgpIHtcbiAgICAgIGlmIChzdXBlci5zZWxlY3RMYXN0KSB7IHN1cGVyLnNlbGVjdExhc3QoKTsgfVxuICAgICAgcmV0dXJuIHNlbGVjdEluZGV4KHRoaXMsIHRoaXMuaXRlbXMubGVuZ3RoIC0gMSk7XG4gICAgfVxuXG4gICAgLyoqXG4gICAgICogU2VsZWN0IHRoZSBuZXh0IGl0ZW0gaW4gdGhlIGxpc3QuXG4gICAgICovXG4gICAgc2VsZWN0TmV4dCgpIHtcbiAgICAgIGlmIChzdXBlci5zZWxlY3ROZXh0KSB7IHN1cGVyLnNlbGVjdE5leHQoKTsgfVxuICAgICAgcmV0dXJuIHNlbGVjdEluZGV4KHRoaXMsIHRoaXMuc2VsZWN0ZWRJbmRleCArIDEpO1xuICAgIH1cblxuICAgIC8qKlxuICAgICAqIFNlbGVjdCB0aGUgcHJldmlvdXMgaXRlbSBpbiB0aGUgbGlzdC5cbiAgICAgKlxuICAgICAqIElmIHRoZSBsaXN0IGhhcyBubyBzZWxlY3Rpb24sIHRoZSBsYXN0IGl0ZW0gd2lsbCBiZSBzZWxlY3RlZC5cbiAgICAgKi9cbiAgICBzZWxlY3RQcmV2aW91cygpIHtcbiAgICAgIGlmIChzdXBlci5zZWxlY3RQcmV2aW91cykgeyBzdXBlci5zZWxlY3RQcmV2aW91cygpOyB9XG4gICAgICBjb25zdCBuZXdJbmRleCA9IHRoaXMuc2VsZWN0ZWRJbmRleCA8IDAgP1xuICAgICAgICB0aGlzLml0ZW1zLmxlbmd0aCAtIDEgOiAgICAgLy8gTm8gc2VsZWN0aW9uIHlldDsgc2VsZWN0IGxhc3QgaXRlbS5cbiAgICAgICAgdGhpcy5zZWxlY3RlZEluZGV4IC0gMTtcbiAgICAgIHJldHVybiBzZWxlY3RJbmRleCh0aGlzLCBuZXdJbmRleCk7XG4gICAgfVxuXG4gICAgLyoqXG4gICAgICogRmlyZXMgd2hlbiB0aGUgc2VsZWN0ZWRJdGVtIHByb3BlcnR5IGNoYW5nZXMuXG4gICAgICpcbiAgICAgKiBAbWVtYmVyb2YgU2luZ2xlU2VsZWN0aW9uXG4gICAgICogQGV2ZW50IHNlbGVjdGVkLWl0ZW0tY2hhbmdlZFxuICAgICAqIEBwYXJhbSB7SFRNTEVsZW1lbnR9IGRldGFpbC5zZWxlY3RlZEl0ZW0gVGhlIG5ldyBzZWxlY3RlZCBpdGVtLlxuICAgICAqIEBwYXJhbSB7SFRNTEVsZW1lbnR9IGRldGFpbC5wcmV2aW91c0l0ZW0gVGhlIHByZXZpb3VzbHkgc2VsZWN0ZWQgaXRlbS5cbiAgICAgKi9cblxuICAgIC8qKlxuICAgICAqIEZpcmVzIHdoZW4gdGhlIHNlbGVjdGVkSW5kZXggcHJvcGVydHkgY2hhbmdlcy5cbiAgICAgKlxuICAgICAqIEBtZW1iZXJvZiBTaW5nbGVTZWxlY3Rpb25cbiAgICAgKiBAZXZlbnQgc2VsZWN0ZWQtaW5kZXgtY2hhbmdlZFxuICAgICAqIEBwYXJhbSB7bnVtYmVyfSBkZXRhaWwuc2VsZWN0ZWRJbmRleCBUaGUgbmV3IHNlbGVjdGVkIGluZGV4LlxuICAgICAqL1xuXG4gIH1cblxuICByZXR1cm4gU2luZ2xlU2VsZWN0aW9uO1xufTtcblxuXG4vLyBFbnN1cmUgdGhlIGdpdmVuIGluZGV4IGlzIHdpdGhpbiBib3VuZHMsIGFuZCBzZWxlY3QgaXQgaWYgaXQncyBub3QgYWxyZWFkeVxuLy8gc2VsZWN0ZWQuXG5mdW5jdGlvbiBzZWxlY3RJbmRleChlbGVtZW50LCBpbmRleCkge1xuICBjb25zdCBjb3VudCA9IGVsZW1lbnQuaXRlbXMubGVuZ3RoO1xuXG4gIGNvbnN0IGJvdW5kZWRJbmRleCA9IChlbGVtZW50LnNlbGVjdGlvbldyYXBzKSA/XG4gICAgLy8gSmF2YVNjcmlwdCBtb2QgZG9lc24ndCBoYW5kbGUgbmVnYXRpdmUgbnVtYmVycyB0aGUgd2F5IHdlIHdhbnQgdG8gd3JhcC5cbiAgICAvLyBTZWUgaHR0cDovL3N0YWNrb3ZlcmZsb3cuY29tL2EvMTg2MTgyNTAvNzY0NzJcbiAgICAoKGluZGV4ICUgY291bnQpICsgY291bnQpICUgY291bnQgOlxuXG4gICAgLy8gS2VlcCBpbmRleCB3aXRoaW4gYm91bmRzIG9mIGFycmF5LlxuICAgIE1hdGgubWF4KE1hdGgubWluKGluZGV4LCBjb3VudCAtIDEpLCAwKTtcblxuICBjb25zdCBwcmV2aW91c0luZGV4ID0gZWxlbWVudC5zZWxlY3RlZEluZGV4O1xuICBpZiAocHJldmlvdXNJbmRleCAhPT0gYm91bmRlZEluZGV4KSB7XG4gICAgZWxlbWVudC5zZWxlY3RlZEluZGV4ID0gYm91bmRlZEluZGV4O1xuICAgIHJldHVybiB0cnVlO1xuICB9IGVsc2Uge1xuICAgIHJldHVybiBmYWxzZTtcbiAgfVxufVxuXG4vLyBGb2xsb3dpbmcgYSBjaGFuZ2UgaW4gdGhlIHNldCBvZiBpdGVtcywgb3IgaW4gdGhlIHZhbHVlIG9mIHRoZVxuLy8gYHNlbGVjdGlvblJlcXVpcmVkYCBwcm9wZXJ0eSwgcmVhY3F1aXJlIHRoZSBzZWxlY3RlZCBpdGVtLiBJZiBpdCdzIG1vdmVkLFxuLy8gdXBkYXRlIGBzZWxlY3RlZEluZGV4YC4gSWYgaXQncyBiZWVuIHJlbW92ZWQsIGFuZCBhIHNlbGVjdGlvbiBpcyByZXF1aXJlZCxcbi8vIHRyeSB0byBzZWxlY3QgYW5vdGhlciBpdGVtLlxuZnVuY3Rpb24gdHJhY2tTZWxlY3RlZEl0ZW0oZWxlbWVudCkge1xuXG4gIGNvbnN0IGl0ZW1zID0gZWxlbWVudC5pdGVtcztcbiAgY29uc3QgaXRlbUNvdW50ID0gaXRlbXMgPyBpdGVtcy5sZW5ndGggOiAwO1xuXG4gIGNvbnN0IHByZXZpb3VzU2VsZWN0ZWRJdGVtID0gZWxlbWVudC5zZWxlY3RlZEl0ZW07XG4gIGlmICghcHJldmlvdXNTZWxlY3RlZEl0ZW0pIHtcbiAgICAvLyBObyBpdGVtIHdhcyBwcmV2aW91c2x5IHNlbGVjdGVkLlxuICAgIGlmIChlbGVtZW50LnNlbGVjdGlvblJlcXVpcmVkKSB7XG4gICAgICAvLyBTZWxlY3QgdGhlIGZpcnN0IGl0ZW0gYnkgZGVmYXVsdC5cbiAgICAgIGVsZW1lbnQuc2VsZWN0ZWRJbmRleCA9IDA7XG4gICAgfVxuICB9IGVsc2UgaWYgKGl0ZW1Db3VudCA9PT0gMCkge1xuICAgIC8vIFdlJ3ZlIGxvc3QgdGhlIHNlbGVjdGlvbiwgYW5kIHRoZXJlJ3Mgbm90aGluZyBsZWZ0IHRvIHNlbGVjdC5cbiAgICBlbGVtZW50LnNlbGVjdGVkSXRlbSA9IG51bGw7XG4gIH0gZWxzZSB7XG4gICAgLy8gVHJ5IHRvIGZpbmQgdGhlIHByZXZpb3VzbHktc2VsZWN0ZWQgaXRlbSBpbiB0aGUgY3VycmVudCBzZXQgb2YgaXRlbXMuXG4gICAgY29uc3QgaW5kZXhJbkN1cnJlbnRJdGVtcyA9IEFycmF5LnByb3RvdHlwZS5pbmRleE9mLmNhbGwoaXRlbXMsIHByZXZpb3VzU2VsZWN0ZWRJdGVtKTtcbiAgICBjb25zdCBwcmV2aW91c1NlbGVjdGVkSW5kZXggPSBlbGVtZW50LnNlbGVjdGVkSW5kZXg7XG4gICAgaWYgKGluZGV4SW5DdXJyZW50SXRlbXMgPCAwKSB7XG4gICAgICAvLyBQcmV2aW91c2x5LXNlbGVjdGVkIGl0ZW0gd2FzIHJlbW92ZWQgZnJvbSB0aGUgaXRlbXMuXG4gICAgICAvLyBTZWxlY3QgdGhlIGl0ZW0gYXQgdGhlIHNhbWUgaW5kZXggKGlmIGl0IGV4aXN0cykgb3IgYXMgY2xvc2UgYXMgcG9zc2libGUuXG4gICAgICBjb25zdCBuZXdTZWxlY3RlZEluZGV4ID0gTWF0aC5taW4ocHJldmlvdXNTZWxlY3RlZEluZGV4LCBpdGVtQ291bnQgLSAxKTtcbiAgICAgIC8vIFNlbGVjdCBieSBpdGVtLCBzaW5jZSBpbmRleCBtYXkgYmUgdGhlIHNhbWUsIGFuZCB3ZSB3YW50IHRvIHJhaXNlIHRoZVxuICAgICAgLy8gc2VsZWN0ZWQtaXRlbS1jaGFuZ2VkIGV2ZW50LlxuICAgICAgZWxlbWVudC5zZWxlY3RlZEl0ZW0gPSBpdGVtc1tuZXdTZWxlY3RlZEluZGV4XTtcbiAgICB9IGVsc2UgaWYgKGluZGV4SW5DdXJyZW50SXRlbXMgIT09IHByZXZpb3VzU2VsZWN0ZWRJbmRleCkge1xuICAgICAgLy8gUHJldmlvdXNseS1zZWxlY3RlZCBpdGVtIHN0aWxsIHRoZXJlLCBidXQgY2hhbmdlZCBwb3NpdGlvbi5cbiAgICAgIGVsZW1lbnQuc2VsZWN0ZWRJbmRleCA9IGluZGV4SW5DdXJyZW50SXRlbXM7XG4gICAgfVxuICB9XG59XG5cbi8vIEZvbGxvd2luZyBhIGNoYW5nZSBpbiBzZWxlY3Rpb24sIHJlcG9ydCB3aGV0aGVyIGl0J3Mgbm93IHBvc3NpYmxlIHRvXG4vLyBnbyBuZXh0L3ByZXZpb3VzIGZyb20gdGhlIGdpdmVuIGluZGV4LlxuZnVuY3Rpb24gdXBkYXRlUG9zc2libGVOYXZpZ2F0aW9ucyhlbGVtZW50KSB7XG4gIGxldCBjYW5TZWxlY3ROZXh0O1xuICBsZXQgY2FuU2VsZWN0UHJldmlvdXM7XG4gIGNvbnN0IGl0ZW1zID0gZWxlbWVudC5pdGVtcztcbiAgaWYgKGl0ZW1zID09IG51bGwgfHwgaXRlbXMubGVuZ3RoID09PSAwKSB7XG4gICAgLy8gTm8gaXRlbXMgdG8gc2VsZWN0LlxuICAgIGNhblNlbGVjdE5leHQgPSBmYWxzZTtcbiAgICBjYW5TZWxlY3RQcmV2aW91cyA9IGZhbHNlO1xuICB9IGlmIChlbGVtZW50LnNlbGVjdGlvbldyYXBzKSB7XG4gICAgLy8gU2luY2UgdGhlcmUgYXJlIGl0ZW1zLCBjYW4gYWx3YXlzIGdvIG5leHQvcHJldmlvdXMuXG4gICAgY2FuU2VsZWN0TmV4dCA9IHRydWU7XG4gICAgY2FuU2VsZWN0UHJldmlvdXMgPSB0cnVlO1xuICB9IGVsc2Uge1xuICAgIGNvbnN0IGluZGV4ID0gZWxlbWVudC5zZWxlY3RlZEluZGV4O1xuICAgIGlmIChpbmRleCA8IDAgJiYgaXRlbXMubGVuZ3RoID4gMCkge1xuICAgICAgLy8gU3BlY2lhbCBjYXNlLiBJZiB0aGVyZSBhcmUgaXRlbXMgYnV0IG5vIHNlbGVjdGlvbiwgZGVjbGFyZSB0aGF0IGl0J3NcbiAgICAgIC8vIGFsd2F5cyBwb3NzaWJsZSB0byBnbyBuZXh0L3ByZXZpb3VzIHRvIGNyZWF0ZSBhIHNlbGVjdGlvbi5cbiAgICAgIGNhblNlbGVjdE5leHQgPSB0cnVlO1xuICAgICAgY2FuU2VsZWN0UHJldmlvdXMgPSB0cnVlO1xuICAgIH0gZWxzZSB7XG4gICAgICAvLyBOb3JtYWwgY2FzZTogd2UgaGF2ZSBhbiBpbmRleCBpbiBhIGxpc3QgdGhhdCBoYXMgaXRlbXMuXG4gICAgICBjYW5TZWxlY3RQcmV2aW91cyA9IChpbmRleCA+IDApO1xuICAgICAgY2FuU2VsZWN0TmV4dCA9IChpbmRleCA8IGl0ZW1zLmxlbmd0aCAtIDEpO1xuICAgIH1cbiAgfVxuICBpZiAoZWxlbWVudC5jYW5TZWxlY3ROZXh0ICE9PSBjYW5TZWxlY3ROZXh0KSB7XG4gICAgZWxlbWVudC5jYW5TZWxlY3ROZXh0ID0gY2FuU2VsZWN0TmV4dDtcbiAgfVxuICBpZiAoZWxlbWVudC5jYW5TZWxlY3RQcmV2aW91cyAhPT0gY2FuU2VsZWN0UHJldmlvdXMpIHtcbiAgICBlbGVtZW50LmNhblNlbGVjdFByZXZpb3VzID0gY2FuU2VsZWN0UHJldmlvdXM7XG4gIH1cbn1cbiIsIi8qKlxuICogSGVscGVyIGZ1bmN0aW9uIHRvIGNyZWF0ZSBhIHN5bWJvbCB0aGF0IGNhbiBiZSB1c2VkIGZvciBhc3NvY2lhdGluZyBwcml2YXRlXG4gKiBkYXRhIHdpdGggYW4gZWxlbWVudC5cbiAqXG4gKiBNaXhpbnMgYW5kIGNvbXBvbmVudCBjbGFzc2VzIG9mdGVuIHdhbnQgdG8gYXNzb2NpYXRlIHByaXZhdGUgZGF0YSB3aXRoIGFuXG4gKiBlbGVtZW50IGluc3RhbmNlLCBidXQgSmF2YVNjcmlwdCBkb2VzIG5vdCBoYXZlIGRpcmVjdCBzdXBwb3J0IGZvciB0cnVlXG4gKiBwcml2YXRlIHByb3BlcnRpZXMuIE9uZSBhcHByb2FjaCBpcyB0byB1c2UgdGhlXG4gKiBbU3ltYm9sXShodHRwczovL2RldmVsb3Blci5tb3ppbGxhLm9yZy9lbi1VUy9kb2NzL1dlYi9KYXZhU2NyaXB0L1JlZmVyZW5jZS9HbG9iYWxfT2JqZWN0cy9TeW1ib2wpXG4gKiBkYXRhIHR5cGUgdG8gc2V0IGFuZCByZXRyaWV2ZSBkYXRhIG9uIGFuIGVsZW1lbnQuXG4gKlxuICogVW5mb3J0dW5hdGVseSwgdGhlIFN5bWJvbCB0eXBlIGlzIG5vdCBhdmFpbGFibGUgaW4gSW50ZXJuZXQgRXhwbG9yZXIgMTEuIFRoZVxuICogYGNyZWF0ZVN5bWJvbGAgaGVscGVyIGZ1bmN0aW9uIGV4aXN0cyBhcyBhIHdvcmthcm91bmQgZm9yIElFIDExLiBSYXRoZXIgdGhhblxuICogcmV0dXJuaW5nIGEgdHJ1ZSBTeW1ib2wsIGl0IHNpbXBseSByZXR1cm5zIGFuIHVuZGVyc2NvcmUtcHJlZml4ZWQgc3RyaW5nLlxuICpcbiAqIFVzYWdlOlxuICpcbiAqICAgICBjb25zdCBmb29TeW1ib2wgPSBjcmVhdGVTeW1ib2woJ2ZvbycpO1xuICpcbiAqICAgICBjbGFzcyBNeUVsZW1lbnQgZXh0ZW5kcyBIVE1MRWxlbWVudCB7XG4gKiAgICAgICBnZXQgZm9vKCkge1xuICogICAgICAgICByZXR1cm4gdGhpc1tmb29TeW1ib2xdO1xuICogICAgICAgfVxuICogICAgICAgc2V0IGZvbyh2YWx1ZSkge1xuICogICAgICAgICB0aGlzW2Zvb1N5bWJvbF0gPSB2YWx1ZTtcbiAqICAgICAgIH1cbiAqICAgICB9XG4gKlxuICogSW4gSUUgMTEsIHRoaXMgc2FtcGxlIHdpbGwgXCJoaWRlXCIgZGF0YSBiZWhpbmQgYW4gaW5zdGFuY2UgcHJvcGVydHkgdGhpcy5fZm9vLlxuICogVGhlIHVzZSBvZiB0aGUgdW5kZXJzY29yZSBpcyBtZWFudCB0byByZWR1Y2UgKG5vdCBlbGltaW5hdGUpIHRoZSBwb3RlbnRpYWxcbiAqIGZvciBuYW1lIGNvbmZsaWN0cywgYW5kIGRpc2NvdXJhZ2UgKG5vdCBwcmV2ZW50KSBleHRlcm5hbCBhY2Nlc3MgdG8gdGhpc1xuICogZGF0YS4gSW4gbW9kZXJuIGJyb3dzZXJzLCB0aGUgYWJvdmUgY29kZSB3aWxsIGVsaW1pbmF0ZSB0aGUgcG90ZW50aWFsIG9mXG4gKiBuYW1pbmcgY29uZmxpY3RzLCBhbmQgYmV0dGVyIGhpZGUgdGhlIGRhdGEgYmVoaW5kIGEgcmVhbCBTeW1ib2wuXG4gKlxuICogQGZ1bmN0aW9uIGNyZWF0ZVN5bWJvbFxuICogQHBhcmFtIHtzdHJpbmd9IGRlc2NyaXB0aW9uIC0gQSBzdHJpbmcgdG8gaWRlbnRpZnkgdGhlIHN5bWJvbCB3aGVuIGRlYnVnZ2luZ1xuICovXG5leHBvcnQgZGVmYXVsdCBmdW5jdGlvbiBjcmVhdGVTeW1ib2woZGVzY3JpcHRpb24pIHtcbiAgcmV0dXJuIHR5cGVvZiBTeW1ib2wgPT09ICdmdW5jdGlvbicgP1xuICAgIFN5bWJvbChkZXNjcmlwdGlvbikgOlxuICAgIGBfJHtkZXNjcmlwdGlvbn1gO1xufVxuIiwiLypcbiAqIE1pY3JvdGFzayBoZWxwZXIgZm9yIElFIDExLlxuICpcbiAqIEV4ZWN1dGluZyBhIGZ1bmN0aW9uIGFzIGEgbWljcm90YXNrIGlzIHRyaXZpYWwgaW4gYnJvd3NlcnMgdGhhdCBzdXBwb3J0XG4gKiBwcm9taXNlcywgd2hvc2UgdGhlbigpIGNsYXVzZXMgdXNlIG1pY3JvdGFzayB0aW1pbmcuIElFIDExIGRvZXNuJ3Qgc3VwcG9ydFxuICogcHJvbWlzZXMsIGJ1dCBkb2VzIHN1cHBvcnQgTXV0YXRpb25PYnNlcnZlcnMsIHdoaWNoIGFyZSBhbHNvIGV4ZWN1dGVkIGFzXG4gKiBtaWNyb3Rhc2tzLiBTbyB0aGlzIGhlbHBlciB1c2VzIGFuIE11dGF0aW9uT2JzZXJ2ZXIgdG8gYWNoaWV2ZSBtaWNyb3Rhc2tcbiAqIHRpbWluZy5cbiAqXG4gKiBTZWUgaHR0cHM6Ly9qYWtlYXJjaGliYWxkLmNvbS8yMDE1L3Rhc2tzLW1pY3JvdGFza3MtcXVldWVzLWFuZC1zY2hlZHVsZXMvXG4gKlxuICogSW5zcGlyZWQgYnkgUG9seW1lcidzIGFzeW5jKCkgZnVuY3Rpb24uXG4gKi9cblxuXG4vLyBUaGUgcXVldWUgb2YgcGVuZGluZyBjYWxsYmFja3MgdG8gYmUgZXhlY3V0ZWQgYXMgbWljcm90YXNrcy5cbmNvbnN0IGNhbGxiYWNrcyA9IFtdO1xuXG4vLyBDcmVhdGUgYW4gZWxlbWVudCB0aGF0IHdlIHdpbGwgbW9kaWZ5IHRvIGZvcmNlIG9ic2VydmFibGUgbXV0YXRpb25zLlxuY29uc3QgZWxlbWVudCA9IGRvY3VtZW50LmNyZWF0ZVRleHROb2RlKCcnKTtcblxuLy8gQSBtb25vdG9uaWNhbGx5LWluY3JlYXNpbmcgdmFsdWUuXG5sZXQgY291bnRlciA9IDA7XG5cblxuLyoqXG4gKiBBZGQgYSBjYWxsYmFjayB0byB0aGUgbWljcm90YXNrIHF1ZXVlLlxuICpcbiAqIFRoaXMgdXNlcyBhIE11dGF0aW9uT2JzZXJ2ZXIgc28gdGhhdCBpdCB3b3JrcyBvbiBJRSAxMS5cbiAqXG4gKiBOT1RFOiBJRSAxMSBtYXkgYWN0dWFsbHkgdXNlIHRpbWVvdXQgdGltaW5nIHdpdGggTXV0YXRpb25PYnNlcnZlcnMuIFRoaXNcbiAqIG5lZWRzIG1vcmUgaW52ZXN0aWdhdGlvbi5cbiAqXG4gKiBAZnVuY3Rpb24gbWljcm90YXNrXG4gKiBAcGFyYW0ge2Z1bmN0aW9ufSBjYWxsYmFja1xuICovXG5leHBvcnQgZGVmYXVsdCBmdW5jdGlvbiBtaWNyb3Rhc2soY2FsbGJhY2spIHtcbiAgY2FsbGJhY2tzLnB1c2goY2FsbGJhY2spO1xuICAvLyBGb3JjZSBhIG11dGF0aW9uLlxuICBlbGVtZW50LnRleHRDb250ZW50ID0gKytjb3VudGVyO1xufVxuXG5cbi8vIEV4ZWN1dGUgYW55IHBlbmRpbmcgY2FsbGJhY2tzLlxuZnVuY3Rpb24gZXhlY3V0ZUNhbGxiYWNrcygpIHtcbiAgd2hpbGUgKGNhbGxiYWNrcy5sZW5ndGggPiAwKSB7XG4gICAgY29uc3QgY2FsbGJhY2sgPSBjYWxsYmFja3Muc2hpZnQoKTtcbiAgICBjYWxsYmFjaygpO1xuICB9XG59XG5cblxuLy8gQ3JlYXRlIHRoZSBvYnNlcnZlci5cbmNvbnN0IG9ic2VydmVyID0gbmV3IE11dGF0aW9uT2JzZXJ2ZXIoZXhlY3V0ZUNhbGxiYWNrcyk7XG5vYnNlcnZlci5vYnNlcnZlKGVsZW1lbnQsIHtcbiAgY2hhcmFjdGVyRGF0YTogdHJ1ZVxufSk7XG4iLCJpbXBvcnQgY3JlYXRlU3ltYm9sIGZyb20gJy4vY3JlYXRlU3ltYm9sJztcbmltcG9ydCB0b2dnbGVDbGFzcyBmcm9tICcuL3RvZ2dsZUNsYXNzJztcblxuXG4vLyBTeW1ib2xzIGZvciBwcml2YXRlIGRhdGEgbWVtYmVycyBvbiBhbiBlbGVtZW50LlxuY29uc3Qgc2FmZVRvU2V0QXR0cmlidXRlc1N5bWJvbCA9IGNyZWF0ZVN5bWJvbCgnc2FmZVRvU2V0QXR0cmlidXRlcycpO1xuY29uc3QgcGVuZGluZ0F0dHJpYnV0ZXNTeW1ib2wgPSBjcmVhdGVTeW1ib2woJ3BlbmRpbmdBdHRyaWJ1dGVzJyk7XG5jb25zdCBwZW5kaW5nQ2xhc3Nlc1N5bWJvbCA9IGNyZWF0ZVN5bWJvbCgncGVuZGluZ0NsYXNzZXMnKTtcblxuXG4vKipcbiAqIEhlbHBlciBmdW5jdGlvbnMgZm9yIHVwZGF0aW5nIGF0dHJpYnV0ZXMsIGluY2x1ZGluZyB0aGUgYGNsYXNzYCBhdHRyaWJ1dGUuXG4gKi9cbmV4cG9ydCBkZWZhdWx0IHtcblxuICAvKipcbiAgICogUGVyZm9ybSBhbnkgcGVuZGluZyB1cGRhdGVzIHRvIGF0dHJpYnV0ZXMgYW5kIGNsYXNzZXMuXG4gICAqXG4gICAqIFRoaXMgd3JpdGVzIGFueSBgc2V0QXR0cmlidXRlYCBvciBgdG9nZ2xlQ2xhc3NgIHZhbHVlcyB0aGF0IHdlcmUgcGVyZm9ybWVkXG4gICAqIGJlZm9yZSBhbiBlbGVtZW50IHdhcyBhdHRhY2hlZCB0byB0aGUgZG9jdW1lbnQgZm9yIHRoZSBmaXJzdCB0aW1lLlxuICAgKlxuICAgKiBUaGlzIG1ldGhvZCBzaG91bGQgYmUgY2FsbGVkIGJ5IG1peGlucy9jb21wb25lbnRzIGluIHRoZWlyXG4gICAqIGBjb25uZWN0ZWRDYWxsYmFja2AuIElmIG11bGl0cGxlIG1peGlucy9jb21wb25lbnRzIGludm9rZSB0aGlzIGR1cmluZyB0aGVcbiAgICogc2FtZSBgY29ubmVjdGVkQ2FsbGJhY2tgLCBvbmx5IHRoZSBmaXJzdCBjYWxsIHdpbGwgaGF2ZSBhbnkgZWZmZWN0LiBUaGVcbiAgICogc3Vic2VxdWVudCBjYWxscyB3aWxsIGJlIGhhcm1sZXNzLlxuICAgKlxuICAgKiBAcGFyYW0ge0hUTUxFbGVtZW50fSBlbGVtZW50IC0gVGhlIGVsZW1lbnQgYmVpbmcgYWRkZWQgdG8gdGhlIGRvY3VtZW50LlxuICAgKi9cbiAgY29ubmVjdGVkKGVsZW1lbnQpIHtcbiAgICBlbGVtZW50W3NhZmVUb1NldEF0dHJpYnV0ZXNTeW1ib2xdID0gdHJ1ZTtcblxuICAgIC8vIFNldCBhbnkgcGVuZGluZyBhdHRyaWJ1dGVzLlxuICAgIGlmIChlbGVtZW50W3BlbmRpbmdBdHRyaWJ1dGVzU3ltYm9sXSkge1xuICAgICAgZm9yIChsZXQgYXR0cmlidXRlIGluIGVsZW1lbnRbcGVuZGluZ0F0dHJpYnV0ZXNTeW1ib2xdKSB7XG4gICAgICAgIGNvbnN0IHZhbHVlID0gZWxlbWVudFtwZW5kaW5nQXR0cmlidXRlc1N5bWJvbF1bYXR0cmlidXRlXTtcbiAgICAgICAgc2V0QXR0cmlidXRlVG9FbGVtZW50KGVsZW1lbnQsIGF0dHJpYnV0ZSwgdmFsdWUpO1xuICAgICAgfVxuICAgICAgZWxlbWVudFtwZW5kaW5nQXR0cmlidXRlc1N5bWJvbF0gPSBudWxsO1xuICAgIH1cblxuICAgIC8vIFNldCBhbnkgcGVuZGluZyBjbGFzc2VzLlxuICAgIGlmIChlbGVtZW50W3BlbmRpbmdDbGFzc2VzU3ltYm9sXSkge1xuICAgICAgZm9yIChsZXQgY2xhc3NOYW1lIGluIGVsZW1lbnRbcGVuZGluZ0NsYXNzZXNTeW1ib2xdKSB7XG4gICAgICAgIGNvbnN0IHZhbHVlID0gZWxlbWVudFtwZW5kaW5nQ2xhc3Nlc1N5bWJvbF1bY2xhc3NOYW1lXTtcbiAgICAgICAgdG9nZ2xlQ2xhc3MoZWxlbWVudCwgY2xhc3NOYW1lLCB2YWx1ZSk7XG4gICAgICB9XG4gICAgICBlbGVtZW50W3BlbmRpbmdDbGFzc2VzU3ltYm9sXSA9IG51bGw7XG4gICAgfVxuICB9LFxuXG4gIC8qKlxuICAgKiBTZXQvdW5zZXQgdGhlIGF0dHJpYnV0ZSB3aXRoIHRoZSBpbmRpY2F0ZWQgbmFtZS5cbiAgICpcbiAgICogVGhpcyBtZXRob2QgZXhpc3RzIHByaW1hcmlseSB0byBoYW5kbGUgdGhlIGNhc2Ugd2hlcmUgYW4gZWxlbWVudCB3YW50cyB0b1xuICAgKiBzZXQgYSBkZWZhdWx0IHByb3BlcnR5IHZhbHVlIHRoYXQgc2hvdWxkIGJlIHJlZmxlY3RlZCBhcyBhbiBhdHRyaWJ1dGUuIEFuXG4gICAqIGltcG9ydGFudCBsaW1pdGF0aW9uIG9mIGN1c3RvbSBlbGVtZW50IGNvbnN0dXJjdG9ycyBpcyB0aGF0IHRoZXkgY2Fubm90XG4gICAqIHNldCBhdHRyaWJ1dGVzLiBBIGNhbGwgdG8gYHNldEF0dHJpYnV0ZWAgZHVyaW5nIHRoZSBjb25zdHJ1Y3RvciB3aWxsXG4gICAqIGJlIGRlZmVycmVkIHVudGlsIHRoZSBlbGVtZW50IGlzIGNvbm5lY3RlZCB0byB0aGUgZG9jdW1lbnQuXG4gICAqXG4gICAqIEBwYXJhbSB7c3RyaW5nfSBhdHRyaWJ1dGUgLSBUaGUgbmFtZSBvZiB0aGUgKmF0dHJpYnV0ZSogKG5vdCBwcm9wZXJ0eSkgdG8gc2V0LlxuICAgKiBAcGFyYW0ge29iamVjdH0gdmFsdWUgLSBUaGUgdmFsdWUgdG8gc2V0LiBJZiBudWxsLCB0aGUgYXR0cmlidXRlIHdpbGwgYmUgcmVtb3ZlZC5cbiAgICovXG4gIHNldEF0dHJpYnV0ZShlbGVtZW50LCBhdHRyaWJ1dGUsIHZhbHVlKSB7XG4gICAgaWYgKGVsZW1lbnRbc2FmZVRvU2V0QXR0cmlidXRlc1N5bWJvbF0pIHtcbiAgICAgIC8vIFNhZmUgdG8gc2V0IGF0dHJpYnV0ZXMgaW1tZWRpYXRlbHkuXG4gICAgICBzZXRBdHRyaWJ1dGVUb0VsZW1lbnQoZWxlbWVudCwgYXR0cmlidXRlLCB2YWx1ZSk7XG4gICAgfSBlbHNlIHtcbiAgICAgIC8vIERlZmVyIHNldHRpbmcgYXR0cmlidXRlcyB1bnRpbCB0aGUgZmlyc3QgdGltZSB3ZSdyZSBjb25uZWN0ZWQuXG4gICAgICBpZiAoIWVsZW1lbnRbcGVuZGluZ0F0dHJpYnV0ZXNTeW1ib2xdKSB7XG4gICAgICAgIGVsZW1lbnRbcGVuZGluZ0F0dHJpYnV0ZXNTeW1ib2xdID0ge307XG4gICAgICB9XG4gICAgICBlbGVtZW50W3BlbmRpbmdBdHRyaWJ1dGVzU3ltYm9sXVthdHRyaWJ1dGVdID0gdmFsdWU7XG4gICAgfVxuICB9LFxuXG4gIC8qKlxuICAgKiBTZXQvdW5zZXQgdGhlIGNsYXNzIHdpdGggdGhlIGluZGljYXRlZCBuYW1lLlxuICAgKlxuICAgKiBUaGlzIG1ldGhvZCBleGlzdHMgcHJpbWFyaWx5IHRvIGhhbmRsZSB0aGUgY2FzZSB3aGVyZSBhbiBlbGVtZW50IHdhbnRzIHRvXG4gICAqIHNldCBhIGRlZmF1bHQgcHJvcGVydHkgdmFsdWUgdGhhdCBzaG91bGQgYmUgcmVmbGVjdGVkIGFzIGFzIGNsYXNzLiBBblxuICAgKiBpbXBvcnRhbnQgbGltaXRhdGlvbiBvZiBjdXN0b20gZWxlbWVudCBjb25zdHVyY3RvcnMgaXMgdGhhdCB0aGV5IGNhbm5vdFxuICAgKiBzZXQgYXR0cmlidXRlcywgaW5jbHVkaW5nIHRoZSBgY2xhc3NgIGF0dHJpYnV0ZS4gQSBjYWxsIHRvXG4gICAqIGB0b2dnbGVDbGFzc2AgZHVyaW5nIHRoZSBjb25zdHJ1Y3RvciB3aWxsIGJlIGRlZmVycmVkIHVudGlsIHRoZSBlbGVtZW50XG4gICAqIGlzIGNvbm5lY3RlZCB0byB0aGUgZG9jdW1lbnQuXG4gICAqXG4gICAqIEBwYXJhbSB7c3RyaW5nfSBjbGFzc05hbWUgLSBUaGUgbmFtZSBvZiB0aGUgY2xhc3MgdG8gc2V0LlxuICAgKiBAcGFyYW0ge29iamVjdH0gdmFsdWUgLSBUcnVlIHRvIHNldCB0aGUgY2xhc3MsIGZhbHNlIHRvIHJlbW92ZSBpdC5cbiAgICovXG4gIHRvZ2dsZUNsYXNzKGVsZW1lbnQsIGNsYXNzTmFtZSwgdmFsdWUpIHtcbiAgICBpZiAoZWxlbWVudFtzYWZlVG9TZXRBdHRyaWJ1dGVzU3ltYm9sXSkge1xuICAgICAgLy8gU2FmZSB0byBzZXQgY2xhc3MgaW1tZWRpYXRlbHkuXG4gICAgICB0b2dnbGVDbGFzcyhlbGVtZW50LCBjbGFzc05hbWUsIHZhbHVlKTtcbiAgICB9IGVsc2Uge1xuICAgICAgLy8gRGVmZXIgc2V0dGluZyBjbGFzcyB1bnRpbCB0aGUgZmlyc3QgdGltZSB3ZSdyZSBjb25uZWN0ZWQuXG4gICAgICBpZiAoIWVsZW1lbnRbcGVuZGluZ0NsYXNzZXNTeW1ib2xdKSB7XG4gICAgICAgIGVsZW1lbnRbcGVuZGluZ0NsYXNzZXNTeW1ib2xdID0ge307XG4gICAgICB9XG4gICAgICBlbGVtZW50W3BlbmRpbmdDbGFzc2VzU3ltYm9sXVtjbGFzc05hbWVdID0gdmFsdWU7XG4gICAgfVxuICB9XG5cbn07XG5cblxuLy8gUmVmbGVjdCB0aGUgYXR0cmlidXRlIHRvIHRoZSBnaXZlbiBlbGVtZW50LlxuLy8gSWYgdGhlIHZhbHVlIGlzIG51bGwsIHJlbW92ZSB0aGUgYXR0cmlidXRlLlxuZnVuY3Rpb24gc2V0QXR0cmlidXRlVG9FbGVtZW50KGVsZW1lbnQsIGF0dHJpYnV0ZU5hbWUsIHZhbHVlKSB7XG4gIGlmICh2YWx1ZSA9PT0gbnVsbCB8fCB0eXBlb2YgdmFsdWUgPT09ICd1bmRlZmluZWQnKSB7XG4gICAgZWxlbWVudC5yZW1vdmVBdHRyaWJ1dGUoYXR0cmlidXRlTmFtZSk7XG4gIH0gZWxzZSB7XG4gICAgY29uc3QgdGV4dCA9IFN0cmluZyh2YWx1ZSk7XG4gICAgLy8gQXZvaWQgcmVjdXJzaXZlIGF0dHJpYnV0ZUNoYW5nZWRDYWxsYmFjayBjYWxscy5cbiAgICBpZiAoZWxlbWVudC5nZXRBdHRyaWJ1dGUoYXR0cmlidXRlTmFtZSkgIT09IHRleHQpIHtcbiAgICAgIGVsZW1lbnQuc2V0QXR0cmlidXRlKGF0dHJpYnV0ZU5hbWUsIHZhbHVlKTtcbiAgICB9XG4gIH1cbn1cbiIsImltcG9ydCBjcmVhdGVTeW1ib2wgZnJvbSAnLi9jcmVhdGVTeW1ib2wnO1xuXG4vKipcbiAqIEEgY29sbGVjdGlvbiBvZiBTeW1ib2wgb2JqZWN0cyBmb3Igc3RhbmRhcmQgY29tcG9uZW50IHByb3BlcnRpZXMgYW5kIG1ldGhvZHMuXG4gKlxuICogVGhlc2UgU3ltYm9sIG9iamVjdHMgYXJlIHVzZWQgdG8gYWxsb3cgbWl4aW5zIGFuZCBhIGNvbXBvbmVudCB0byBpbnRlcm5hbGx5XG4gKiBjb21tdW5pY2F0ZSwgd2l0aG91dCBleHBvc2luZyB0aGVzZSBwcm9wZXJ0aWVzIGFuZCBtZXRob2RzIGluIHRoZSBjb21wb25lbnQnc1xuICogcHVibGljIEFQSS5cbiAqXG4gKiBUbyB1c2UgdGhlc2UgU3ltYm9sIG9iamVjdHMgaW4geW91ciBvd24gY29tcG9uZW50LCBpbmNsdWRlIHRoaXMgbW9kdWxlIGFuZFxuICogdGhlbiBjcmVhdGUgYSBwcm9wZXJ0eSBvciBtZXRob2Qgd2hvc2Uga2V5IGlzIHRoZSBkZXNpcmVkIFN5bWJvbC5cbiAqXG4gKiAgICAgaW1wb3J0ICdTaW5nbGVTZWxlY3Rpb25NaXhpbicgZnJvbSAnYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvU2luZ2xlU2VsZWN0aW9uTWl4aW4nO1xuICogICAgIGltcG9ydCAnc3ltYm9scycgZnJvbSAnYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvc3ltYm9scyc7XG4gKlxuICogICAgIGNsYXNzIE15RWxlbWVudCBleHRlbmRzIFNpbmdsZVNlbGVjdGlvbk1peGluKEhUTUxFbGVtZW50KSB7XG4gKiAgICAgICBbc3ltYm9scy5pdGVtU2VsZWN0ZWRdKGl0ZW0sIHNlbGVjdGVkKSB7XG4gKiAgICAgICAgIC8vIFRoaXMgd2lsbCBiZSBpbnZva2VkIHdoZW5ldmVyIGFuIGl0ZW0gaXMgc2VsZWN0ZWQvZGVzZWxlY3RlZC5cbiAqICAgICAgIH1cbiAqICAgICB9XG4gKlxuICogQG1vZHVsZSBzeW1ib2xzXG4gKi9cbmNvbnN0IHN5bWJvbHMgPSB7XG5cbiAgLyoqXG4gICAqIFN5bWJvbCBmb3IgdGhlIGBkZWZhdWx0c2AgcHJvcGVydHkuXG4gICAqXG4gICAqIFRoaXMgcHJvcGVydHkgY2FuIGJlIHVzZWQgdG8gc2V0IG9yIG92ZXJyaWRlIGRlZmF1bHRzIHRoYXQgd2lsbCBiZSBhcHBsaWVkXG4gICAqIHRvIGEgbmV3IGNvbXBvbmVudCBpbnN0YW5jZS4gV2hlbiBpbXBsZW1lbnRpbmcgdGhpcyBwcm9wZXJ0eSwgdGFrZSBjYXJlIHRvXG4gICAqIGZpcnN0IGFjcXVpcmUgYW55IGRlZmF1bHRzIGRlZmluZWQgYnkgdGhlIHN1cGVyY2xhc3MuIFRoZSBzdGFuZGFyZCBpZGlvbSBpc1xuICAgKiBhcyBmb2xsb3dzOlxuICAgKlxuICAgKiAgICAgZ2V0IFtzeW1ib2xzLmRlZmF1bHRzXSgpIHtcbiAgICogICAgICAgY29uc3QgZGVmYXVsdHMgPSBzdXBlcltzeW1ib2xzLmRlZmF1bHRzXSB8fCB7fTtcbiAgICogICAgICAgLy8gU2V0IG9yIG92ZXJyaWRlIGRlZmF1bHQgdmFsdWVzIGhlcmVcbiAgICogICAgICAgZGVmYXVsdHMuY3VzdG9tUHJvcGVydHkgPSBmYWxzZTtcbiAgICogICAgICAgcmV0dXJuIGRlZmF1bHRzO1xuICAgKiAgICAgfVxuICAgKlxuICAgKiBAdmFyIHtvYmplY3R9IGRlZmF1bHRzXG4gICAqL1xuICBkZWZhdWx0czogY3JlYXRlU3ltYm9sKCdkZWZhdWx0cycpLFxuXG4gIC8qKlxuICAgKiBTeW1ib2wgZm9yIHRoZSBgZHJhZ2dpbmdgIHByb3BlcnR5LlxuICAgKlxuICAgKiBDb21wb25lbnRzIGxpa2UgY2Fyb3VzZWxzIG9mdGVuIGRlZmluZSBhbmltYXRlZCBDU1MgdHJhbnNpdGlvbnMgZm9yXG4gICAqIHNsaWRpbmcgZWZmZWN0cy4gU3VjaCBhIHRyYW5zaXRpb24gc2hvdWxkIHVzdWFsbHkgKm5vdCogYmUgYXBwbGllZCB3aGlsZVxuICAgKiB0aGUgdXNlciBpcyBkcmFnZ2luZywgYmVjYXVzZSBhIENTUyBhbmltYXRpb24gd2lsbCBpbnRyb2R1Y2UgYSBsYWcgdGhhdFxuICAgKiBtYWtlcyB0aGUgc3dpcGUgZmVlbCBzbHVnZ2lzaC4gSW5zdGVhZCwgYXMgbG9uZyBhcyB0aGUgdXNlciBpcyBkcmFnZ2luZ1xuICAgKiB3aXRoIHRoZWlyIGZpbmdlciBkb3duLCB0aGUgdHJhbnNpdGlvbiBzaG91bGQgYmUgc3VwcHJlc3NlZC4gV2hlbiB0aGVcbiAgICogdXNlciByZWxlYXNlcyB0aGVpciBmaW5nZXIsIHRoZSB0cmFuc2l0aW9uIGNhbiBiZSByZXN0b3JlZCwgYWxsb3dpbmcgdGhlXG4gICAqIGFuaW1hdGlvbiB0byBzaG93IHRoZSBjYXJvdXNlbCBzbGlkaW5nIGludG8gaXRzIGZpbmFsIHBvc2l0aW9uLlxuICAgKlxuICAgKiBAdHlwZSB7Ym9vbGVhbn0gdHJ1ZSBpZiBhIGRyYWcgaXMgaW4gcHJvZ3Jlc3MsIGZhbHNlIGlmIG5vdC5cbiAgICovXG4gIGRyYWdnaW5nOiBjcmVhdGVTeW1ib2woJ2RyYWdnaW5nJyksXG5cbiAgLyoqXG4gICAqIFN5bWJvbCBmb3IgdGhlIGBnb0Rvd25gIG1ldGhvZC5cbiAgICpcbiAgICogVGhpcyBtZXRob2QgaXMgaW52b2tlZCB3aGVuIHRoZSB1c2VyIHdhbnRzIHRvIGdvL25hdmlnYXRlIGRvd24uXG4gICAqXG4gICAqIEBmdW5jdGlvbiBnb0Rvd25cbiAgICovXG4gIGdvRG93bjogY3JlYXRlU3ltYm9sKCdnb0Rvd24nKSxcblxuICAvKipcbiAgICogU3ltYm9sIGZvciB0aGUgYGdvRW5kYCBtZXRob2QuXG4gICAqXG4gICAqIFRoaXMgbWV0aG9kIGlzIGludm9rZWQgd2hlbiB0aGUgdXNlciB3YW50cyB0byBnby9uYXZpZ2F0ZSB0byB0aGUgZW5kIChlLmcuLFxuICAgKiBvZiBhIGxpc3QpLlxuICAgKlxuICAgKiBAZnVuY3Rpb24gZ29FbmRcbiAgICovXG4gIGdvRW5kOiBjcmVhdGVTeW1ib2woJ2dvRW5kJyksXG5cbiAgLyoqXG4gICAqIFN5bWJvbCBmb3IgdGhlIGBnb0xlZnRgIG1ldGhvZC5cbiAgICpcbiAgICogVGhpcyBtZXRob2QgaXMgaW52b2tlZCB3aGVuIHRoZSB1c2VyIHdhbnRzIHRvIGdvL25hdmlnYXRlIGxlZnQuXG4gICAqXG4gICAqIEBmdW5jdGlvbiBnb0xlZnRcbiAgICovXG4gIGdvTGVmdDogY3JlYXRlU3ltYm9sKCdnb0xlZnQnKSxcblxuICAvKipcbiAgICogU3ltYm9sIGZvciB0aGUgYGdvUmlnaHRgIG1ldGhvZC5cbiAgICpcbiAgICogVGhpcyBtZXRob2QgaXMgaW52b2tlZCB3aGVuIHRoZSB1c2VyIHdhbnRzIHRvIGdvL25hdmlnYXRlIHJpZ2h0LlxuICAgKlxuICAgKiBAZnVuY3Rpb24gZ29SaWdodFxuICAgKi9cbiAgZ29SaWdodDogY3JlYXRlU3ltYm9sKCdnb1JpZ2h0JyksXG5cbiAgLyoqXG4gICAqIFN5bWJvbCBmb3IgdGhlIGBnb1N0YXJ0YCBtZXRob2QuXG4gICAqXG4gICAqIFRoaXMgbWV0aG9kIGlzIGludm9rZWQgd2hlbiB0aGUgdXNlciB3YW50cyB0byBnby9uYXZpZ2F0ZSB0byB0aGUgc3RhcnRcbiAgICogKGUuZy4sIG9mIGEgbGlzdCkuXG4gICAqXG4gICAqIEBmdW5jdGlvbiBnb1N0YXJ0XG4gICAqL1xuICBnb1N0YXJ0OiBjcmVhdGVTeW1ib2woJ2dvU3RhcnQnKSxcblxuICAvKipcbiAgICogU3ltYm9sIGZvciB0aGUgYGdvVXBgIG1ldGhvZC5cbiAgICpcbiAgICogVGhpcyBtZXRob2QgaXMgaW52b2tlZCB3aGVuIHRoZSB1c2VyIHdhbnRzIHRvIGdvL25hdmlnYXRlIHVwLlxuICAgKlxuICAgKiBAZnVuY3Rpb24gZ29VcFxuICAgKi9cbiAgZ29VcDogY3JlYXRlU3ltYm9sKCdnb1VwJyksXG5cbiAgLyoqXG4gICAqIFN5bWJvbCBmb3IgdGhlIGBpdGVtQWRkZWRgIG1ldGhvZC5cbiAgICpcbiAgICogVGhpcyBtZXRob2QgaXMgaW52b2tlZCB3aGVuIGEgbmV3IGl0ZW0gaXMgYWRkZWQgdG8gYSBsaXN0LlxuICAgKlxuICAgKiBAZnVuY3Rpb24gaXRlbUFkZGVkXG4gICAqIEBwYXJhbSB7SFRNTEVsZW1lbnR9IGl0ZW0gLSB0aGUgaXRlbSBiZWluZyBzZWxlY3RlZC9kZXNlbGVjdGVkXG4gICAqL1xuICBpdGVtQWRkZWQ6IGNyZWF0ZVN5bWJvbCgnaXRlbUFkZGVkJyksXG5cblxuICAvKipcbiAgICogU3ltYm9sIGZvciB0aGUgYGl0ZW1zQ2hhbmdlZGAgbWV0aG9kLlxuICAgKlxuICAgKiBUaGlzIG1ldGhvZCBpcyBpbnZva2VkIHdoZW4gdGhlIHVuZGVybHlpbmcgY29udGVudHMgY2hhbmdlLiBJdCBpcyBhbHNvXG4gICAqIGludm9rZWQgb24gY29tcG9uZW50IGluaXRpYWxpemF0aW9uIOKAkyBzaW5jZSB0aGUgaXRlbXMgaGF2ZSBcImNoYW5nZWRcIiBmcm9tXG4gICAqIGJlaW5nIG5vdGhpbmcuXG4gICAqL1xuICBpdGVtc0NoYW5nZWQ6IGNyZWF0ZVN5bWJvbCgnaXRlbXNDaGFuZ2VkJyksXG5cbiAgLyoqXG4gICAqIFN5bWJvbCBmb3IgdGhlIGBpdGVtU2VsZWN0ZWRgIG1ldGhvZC5cbiAgICpcbiAgICogVGhpcyBtZXRob2QgaXMgaW52b2tlZCB3aGVuIGFuIGl0ZW0gYmVjb21lcyBzZWxlY3RlZCBvciBkZXNlbGVjdGVkLlxuICAgKlxuICAgKiBAZnVuY3Rpb24gaXRlbVNlbGVjdGVkXG4gICAqIEBwYXJhbSB7SFRNTEVsZW1lbnR9IGl0ZW0gLSB0aGUgaXRlbSBiZWluZyBzZWxlY3RlZC9kZXNlbGVjdGVkXG4gICAqIEBwYXJhbSB7Ym9vbGVhbn0gc2VsZWN0ZWQgLSB0cnVlIGlmIHRoZSBpdGVtIGlzIHNlbGVjdGVkLCBmYWxzZSBpZiBub3RcbiAgICovXG4gIGl0ZW1TZWxlY3RlZDogY3JlYXRlU3ltYm9sKCdpdGVtU2VsZWN0ZWQnKSxcblxuICAvKipcbiAgICogU3ltYm9sIGZvciB0aGUgYGtleWRvd25gIG1ldGhvZC5cbiAgICpcbiAgICogVGhpcyBtZXRob2QgaXMgaW52b2tlZCB3aGVuIGFuIGVsZW1lbnQgcmVjZWl2ZXMgYSBga2V5ZG93bmAgZXZlbnQuXG4gICAqXG4gICAqIEBmdW5jdGlvbiBrZXlkb3duXG4gICAqIEBwYXJhbSB7S2V5Ym9hcmRFdmVudH0gZXZlbnQgLSB0aGUgZXZlbnQgYmVpbmcgcHJvY2Vzc2VkXG4gICAqL1xuICBrZXlkb3duOiBjcmVhdGVTeW1ib2woJ2tleWRvd24nKSxcblxuICAvKipcbiAgICogU3ltYm9sIGZvciB0aGUgYHRlbXBsYXRlYCBwcm9wZXJ0eS5cbiAgICpcbiAgICogVGhpcyBwcm9wZXJ0eSByZXR1cm5zIGEgY29tcG9uZW50J3MgdGVtcGxhdGUuXG4gICAqXG4gICAqIEB0eXBlIHtzdHJpbmd8SFRNTEVsZW1lbnR9XG4gICAqL1xuICB0ZW1wbGF0ZTogY3JlYXRlU3ltYm9sKCd0ZW1wbGF0ZScpXG59O1xuXG5leHBvcnQgZGVmYXVsdCBzeW1ib2xzO1xuIiwiLyoqXG4gKiBIZWxwZXIgZnVuY3Rpb24gZm9yIHN0YW5kYXJkIGNsYXNzTGlzdC50b2dnbGUoKSBiZWhhdmlvciBvbiBvbGQgYnJvd3NlcnMsXG4gKiBuYW1lbHkgSUUgMTEuXG4gKlxuICogVGhlIHN0YW5kYXJkXG4gKiBbY2xhc3NsaXN0XShodHRwczovL2RldmVsb3Blci5tb3ppbGxhLm9yZy9lbi1VUy9kb2NzL1dlYi9BUEkvRWxlbWVudC9jbGFzc0xpc3QpXG4gKiBvYmplY3QgaGFzIGEgYHRvZ2dsZSgpYCBmdW5jdGlvbiB0aGF0IHN1cHBvcnRzIGEgc2Vjb25kIEJvb2xlYW4gcGFyYW1ldGVyXG4gKiB0aGF0IGNhbiBiZSB1c2VkIHRvIHN1Y2NpbmN0bHkgdHVybiBhIGNsYXNzIG9uIG9yIG9mZi4gVGhpcyBmZWF0dXJlIGlzIG9mdGVuXG4gKiB1c2VmdWwgaW4gZGVzaWduaW5nIGN1c3RvbSBlbGVtZW50cywgd2hpY2ggbWF5IHdhbnQgdG8gZXh0ZXJuYWxseSByZWZsZWN0XG4gKiBjb21wb25lbnQgc3RhdGUgaW4gYSBDU1MgY2xhc3MgdGhhdCBjYW4gYmUgdXNlZCBmb3Igc3R5bGluZyBwdXJwb3Nlcy5cbiAqXG4gKiBVbmZvcnR1bmF0ZWx5LCBJRSAxMSBkb2VzIG5vdCBzdXBwb3J0IHRoZSBCb29sZWFuIHBhcmFtZXRlciB0b1xuICogYGNsYXNzTGlzdC50b2dnbGUoKWAuIFRoaXMgaGVscGVyIGZ1bmN0aW9uIGJlaGF2ZXMgbGlrZSB0aGUgc3RhbmRhcmRcbiAqIGB0b2dnbGUoKWAsIGluY2x1ZGluZyBzdXBwb3J0IGZvciB0aGUgQm9vbGVhbiBwYXJhbWV0ZXIsIHNvIHRoYXQgaXQgY2FuIGJlXG4gKiB1c2VkIGV2ZW4gb24gSUUgMTEuXG4gKlxuICogQGZ1bmN0aW9uIHRvZ2dsZUNsYXNzXG4gKiBAcGFyYW0ge0hUTUxFbGVtZW50fSBlbGVtZW50IC0gVGhlIGVsZW1lbnQgdG8gbW9kaWZ5XG4gKiBAcGFyYW0ge3N0cmluZ30gY2xhc3NOYW1lIC0gVGhlIGNsYXNzIHRvIGFkZC9yZW1vdmVcbiAqIEBwYXJhbSB7Ym9vbGVhbn0gW2ZvcmNlXSAtIEZvcmNlIHRoZSBjbGFzcyB0byBiZSBhZGRlZCAoaWYgdHJ1ZSkgb3IgcmVtb3ZlZFxuICogICAgICAgICAgICAgICAgICAgICAgICAgICAgKGlmIGZhbHNlKVxuICovXG5leHBvcnQgZGVmYXVsdCBmdW5jdGlvbiB0b2dnbGVDbGFzcyhlbGVtZW50LCBjbGFzc05hbWUsIGZvcmNlKSB7XG4gIGNvbnN0IGNsYXNzTGlzdCA9IGVsZW1lbnQuY2xhc3NMaXN0O1xuICBjb25zdCBhZGRDbGFzcyA9ICh0eXBlb2YgZm9yY2UgPT09ICd1bmRlZmluZWQnKSA/XG4gICAgIWNsYXNzTGlzdC5jb250YWlucyhjbGFzc05hbWUpIDpcbiAgICBmb3JjZTtcbiAgaWYgKGFkZENsYXNzKSB7XG4gICAgY2xhc3NMaXN0LmFkZChjbGFzc05hbWUpO1xuICB9IGVsc2Uge1xuICAgIGNsYXNzTGlzdC5yZW1vdmUoY2xhc3NOYW1lKTtcbiAgfVxuICByZXR1cm4gYWRkQ2xhc3M7XG59XG4iLCJpbXBvcnQgQXR0cmlidXRlTWFyc2hhbGxpbmdNaXhpbiBmcm9tICcuLi8uLi9iYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy9BdHRyaWJ1dGVNYXJzaGFsbGluZ01peGluJztcbmltcG9ydCBDb21wb3NhYmxlTWl4aW4gZnJvbSAnLi4vLi4vYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvQ29tcG9zYWJsZU1peGluJztcbmltcG9ydCBEaXN0cmlidXRlZENoaWxkcmVuTWl4aW4gZnJvbSAnLi4vLi4vYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvRGlzdHJpYnV0ZWRDaGlsZHJlbk1peGluJztcbmltcG9ydCBTaGFkb3dFbGVtZW50UmVmZXJlbmNlc01peGluIGZyb20gJy4uLy4uL2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL1NoYWRvd0VsZW1lbnRSZWZlcmVuY2VzTWl4aW4nO1xuaW1wb3J0IFNoYWRvd1RlbXBsYXRlTWl4aW4gZnJvbSAnLi4vLi4vYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvU2hhZG93VGVtcGxhdGVNaXhpbic7XG5cblxuLyoqXG4gKiBBIHNhbXBsZSBnZW5lcmFsLXB1cnBvc2UgYmFzZSBjbGFzcyBmb3IgZGVmaW5pbmcgY3VzdG9tIGVsZW1lbnRzIHRoYXQgbWl4ZXNcbiAqIGluIHNvbWUgY29tbW9uIGZlYXR1cmVzOiB0ZW1wbGF0ZSBzdGFtcGluZyBpbnRvIGEgc2hhZG93IHJvb3QsIHNoYWRvdyBlbGVtZW50XG4gKiByZWZlcmVuY2VzLCBtYXJzaGFsbGluZyBhdHRyaWJ1dGVzIHRvIHByb3BlcnRpZXMsIGFuZCByZXRyaWV2aW5nIHRoZSBjaGlsZHJlblxuICogZGlzdHJpYnV0ZWQgdG8gYSBjb21wb25lbnQuXG4gKlxuICogVGhpcyBiYXNlIGNsYXNzIGlzIG5vdCBzcGVjaWFsIGluIGFueSB3YXksIGFuZCBpcyBkZWZpbmVkIG9ubHkgYXMgYVxuICogY29udmVuaWVudCBzaG9ydGhhbmQgZm9yIGFwcGx5aW5nIHRoZSBtaXhpbnMgbGlzdGVkIGFib3ZlLiBZb3UgY2FuIHVzZSB0aGlzXG4gKiBjbGFzcyBhcyBhIGJhc2UgY2xhc3MgZm9yIHlvdXIgb3duIGVsZW1lbnRzLCBvciBlYXNpbHkgY3JlYXRlIHlvdXIgb3duIGJhc2VcbiAqIGNsYXNzIGJ5IGFwcGx5aW5nIHRoZSBzYW1lIHNldCBvZiBtaXhpbnMuXG4gKlxuICogVGhlIEVsZW1lbnRCYXNlIGJhc2UgY2xhc3MgZG9lcyBub3QgcmVnaXN0ZXIgaXRzZWxmIGFzIGEgY3VzdG9tIGVsZW1lbnQgd2l0aFxuICogdGhlIGJyb3dzZXIsIGFuZCBoZW5jZSBjYW5ub3QgYmUgaW5kZXBlbmRlbnRseSBpbnN0YW50aWF0ZWQuXG4gKlxuICogQG1peGVzIEF0dHJpYnV0ZU1hcnNoYWxsaW5nTWl4aW5cbiAqIEBtaXhlcyBDb21wb3NhYmxlTWl4aW5cbiAqIEBtaXhlcyBEaXN0cmlidXRlZENoaWxkcmVuTWl4aW5cbiAqIEBtaXhlcyBTaGFkb3dFbGVtZW50UmVmZXJlbmNlc01peGluXG4gKiBAbWl4ZXMgU2hhZG93VGVtcGxhdGVNaXhpblxuICovXG5jbGFzcyBFbGVtZW50QmFzZSBleHRlbmRzIENvbXBvc2FibGVNaXhpbihIVE1MRWxlbWVudCkuY29tcG9zZShcbiAgU2hhZG93VGVtcGxhdGVNaXhpbiwgICAgICAgICAgLy8gYmVmb3JlIG5vZGUgZmluZGluZywgc28gc2hhZG93IHJvb3QgaXMgcG9wdWxhdGVkXG4gIFNoYWRvd0VsZW1lbnRSZWZlcmVuY2VzTWl4aW4sIC8vIGJlZm9yZSBtYXJzaGFsbGluZywgc28gcHJvcGVydGllcyBjYW4gdXNlIHJlZnNcbiAgQXR0cmlidXRlTWFyc2hhbGxpbmdNaXhpbixcbiAgRGlzdHJpYnV0ZWRDaGlsZHJlbk1peGluXG4pIHt9XG5cbmV4cG9ydCBkZWZhdWx0IEVsZW1lbnRCYXNlO1xuIiwiLypcbiAqIFRoaXMgZmlsZSBpcyB0cmFuc3BpbGVkIHRvIGNyZWF0ZSBhbiBFUzUtY29tcGF0aWJsZSBkaXN0cmlidXRpb24gaW4gd2hpY2hcbiAqIHRoZSBwYWNrYWdlJ3MgbWFpbiBmZWF0dXJlKHMpIGFyZSBhdmFpbGFibGUgdmlhIHRoZSB3aW5kb3cuQmFzaWMgZ2xvYmFsLlxuICogSWYgeW91J3JlIGFscmVhZHkgdXNpbmcgRVM2IHlvdXJzZWxmLCBpZ25vcmUgdGhpcyBmaWxlLCBhbmQgaW5zdGVhZCBpbXBvcnRcbiAqIHRoZSBzb3VyY2UgZmlsZShzKSB5b3Ugd2FudCBmcm9tIHRoZSBzcmMgZm9sZGVyLlxuICovXG5cbmltcG9ydCBMaXN0Qm94IGZyb20gJy4vc3JjL0xpc3RCb3gnO1xuXG53aW5kb3cuQmFzaWMgPSB3aW5kb3cuQmFzaWMgfHwge307XG53aW5kb3cuQmFzaWMuTGlzdEJveCA9IExpc3RCb3g7XG4iLCJpbXBvcnQgRWxlbWVudEJhc2UgZnJvbSAnLi4vLi4vYmFzaWMtZWxlbWVudC1iYXNlL3NyYy9FbGVtZW50QmFzZSc7XG5pbXBvcnQgRGlzdHJpYnV0ZWRDaGlsZHJlbkNvbnRlbnRNaXhpbiBmcm9tICcuLi8uLi9iYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy9EaXN0cmlidXRlZENoaWxkcmVuQ29udGVudE1peGluJztcbmltcG9ydCBDbGlja1NlbGVjdGlvbk1peGluIGZyb20gJy4uLy4uL2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL0NsaWNrU2VsZWN0aW9uTWl4aW4nO1xuaW1wb3J0IENvbnRlbnRJdGVtc01peGluIGZyb20gJy4uLy4uL2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL0NvbnRlbnRJdGVtc01peGluJztcbmltcG9ydCBEaXJlY3Rpb25TZWxlY3Rpb25NaXhpbiBmcm9tICcuLi8uLi9iYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy9EaXJlY3Rpb25TZWxlY3Rpb25NaXhpbic7XG5pbXBvcnQgR2VuZXJpY01peGluIGZyb20gJy4uLy4uL2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL0dlbmVyaWNNaXhpbic7XG5pbXBvcnQgS2V5Ym9hcmRNaXhpbiBmcm9tICcuLi8uLi9iYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy9LZXlib2FyZE1peGluJztcbmltcG9ydCBLZXlib2FyZERpcmVjdGlvbk1peGluIGZyb20gJy4uLy4uL2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL0tleWJvYXJkRGlyZWN0aW9uTWl4aW4nO1xuaW1wb3J0IEtleWJvYXJkUGFnZWRTZWxlY3Rpb25NaXhpbiBmcm9tICcuLi8uLi9iYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy9LZXlib2FyZFBhZ2VkU2VsZWN0aW9uTWl4aW4nO1xuaW1wb3J0IEtleWJvYXJkUHJlZml4U2VsZWN0aW9uTWl4aW4gZnJvbSAnLi4vLi4vYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvS2V5Ym9hcmRQcmVmaXhTZWxlY3Rpb25NaXhpbic7XG5pbXBvcnQgU2VsZWN0ZWRJdGVtVGV4dFZhbHVlTWl4aW4gZnJvbSAnLi4vLi4vYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvU2VsZWN0ZWRJdGVtVGV4dFZhbHVlTWl4aW4nO1xuaW1wb3J0IFNlbGVjdGlvbkFyaWFBY3RpdmVNaXhpbiBmcm9tICcuLi8uLi9iYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy9TZWxlY3Rpb25BcmlhQWN0aXZlTWl4aW4nO1xuaW1wb3J0IFNlbGVjdGlvbkhpZ2hsaWdodE1peGluIGZyb20gJy4uLy4uL2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL1NlbGVjdGlvbkhpZ2hsaWdodE1peGluJztcbmltcG9ydCBTZWxlY3Rpb25JblZpZXdNaXhpbiBmcm9tICcuLi8uLi9iYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy9TZWxlY3Rpb25JblZpZXdNaXhpbic7XG5pbXBvcnQgU2luZ2xlU2VsZWN0aW9uTWl4aW4gZnJvbSAnLi4vLi4vYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvU2luZ2xlU2VsZWN0aW9uTWl4aW4nO1xuaW1wb3J0IHN5bWJvbHMgZnJvbSAnLi4vLi4vYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvc3ltYm9scyc7XG5cblxuLyoqXG4gKiBBIHNpbmdsZS1zZWxlY3Rpb24gbGlzdCBib3ggdGhhdCBzdXBwb3J0cyBzZWxlY3Rpb24gaGlnaGxpZ2h0aW5nICh1c2luZyB0aGVcbiAqIHN5c3RlbSBoaWdobGlnaHQgY29sb3IpIGFuZCBrZXlib2FyZCBuYXZpZ2F0aW9uLlxuICpcbiAqIFtMaXZlIGRlbW9dKGh0dHA6Ly9iYXNpY3dlYmNvbXBvbmVudHMub3JnL2Jhc2ljLXdlYi1jb21wb25lbnRzL3BhY2thZ2VzL2Jhc2ljLWxpc3QtYm94LylcbiAqXG4gKiBUaGUgdXNlciBjYW4gc2VsZWN0IGFuIGl0ZW0gd2l0aCB0aGUgbW91c2UvdG91Y2ggb3Iga2V5Ym9hcmQ6IFVwL0Rvd24sIFBhZ2VcbiAqIFVwL0Rvd24sIEhvbWUvRW5kLlxuICpcbiAqIExpa2Ugb3RoZXIgQmFzaWMgV2ViIENvbXBvbmVudHMsIHRoaXMgY2FuIGhhbmRsZSBkaXN0cmlidXRlZCBjb250ZW50OiB5b3UgY2FuXG4gKiBpbmNsdWRlIGEgY29udGVudCBlbGVtZW50IGluc2lkZSBhIGJhc2ljLWxpc3QtYm94LCBhbmQgdGhlIGxpc3Qgd2lsbCBuYXZpZ2F0ZVxuICogdGhyb3VnaCB0aGUgZGlzdHJpYnV0ZWQgY29udGVudC5cbiAqXG4gKiBUaGlzIGNvbXBvbmVudCBpbmNsdWRlcyBiYXNpYyBBUklBIHN1cHBvcnQgdG8gcHJvdmlkZSBhIHJlYXNvbmFibGUgZGVmYXVsdFxuICogZXhwZXJpZW5jZSwgZS5nLiwgZm9yIHNjcmVlbiByZWFkZXJzLiBUaGUgbGlzdCBjb21wb25lbnQgaXRzZWxmIHdpbGwgYmVcbiAqIGFzc2lnbmVkIGFuIGFwcHJvcHJpYXRlIEFSSUEgcm9sZSAoZGVmYXVsdCBpcyBcImxpc3Rib3hcIikuIFRoZSBJRCBvZiB0aGVcbiAqIHNlbGVjdGVkIGl0ZW0gd2lsbCBiZSByZWZsZWN0ZWQgaW4gYW4gXCJhcmlhLWFjdGl2ZWRlc2NlbmRhbnRcIiBhdHRyaWJ1dGVcbiAqIGFwcGxpZWQgdG8gdGhlIGxpc3QuIFRvIHN1cHBvcnQgdGhpcyBmZWF0dXJlLCBhbGwgaXRlbXMgaW4gdGhlIGxpc3QgbmVlZFxuICogdW5pcXVlIElEcy4gSWYgYW4gaXRlbSBkb2VzIG5vdCBoYXZlIGFuIElELCBiYXNpYy1saXN0LWJveCB3aWxsIGF1dG9tYXRpY2FsbHlcbiAqIGFzc2lnbiBhIGRlZmF1bHQgSUQuXG4gKlxuICogVGhlIGtleWJvYXJkIGludGVyYWN0aW9uIG1vZGVsIGdlbmVyYWxseSBmb2xsb3dzIHRoYXQgb2YgTWljcm9zb2Z0IFdpbmRvd3MnXG4gKiBsaXN0IGJveGVzIGluc3RlYWQgb2YgdGhvc2UgaW4gT1MgWDpcbiAqXG4gKiAqIFRoZSBQYWdlIFVwL0Rvd24gYW5kIEhvbWUvRW5kIGtleXMgYWN0dWFsbHkgbW92ZSB0aGUgc2VsZWN0aW9uLCByYXRoZXIgdGhhblxuICogICBqdXN0IHNjcm9sbGluZyB0aGUgbGlzdC4gVGhlIGZvcm1lciBiZWhhdmlvciBzZWVtcyBtb3JlIGdlbmVyYWxseSB1c2VmdWxcbiAqICAgZm9yIGtleWJvYXJkIHVzZXJzLlxuICpcbiAqICogUHJlc3NpbmcgUGFnZSBVcC9Eb3duIHdpbGwgbW92ZSB0aGUgc2VsZWN0aW9uIHRvIHRoZSB0b3Btb3N0L2JvdHRvbW1vc3RcbiAqICAgdmlzaWJsZSBpdGVtIGlmIHRoZSBzZWxlY3Rpb24gaXMgbm90IGFscmVhZHkgdGhlcmUuIFRoZXJlYWZ0ZXIsIHRoZSBrZXlcbiAqICAgd2lsbCBtb3ZlIHRoZSBzZWxlY3Rpb24gdXAvZG93biBieSBhIHBhZ2UsIGFuZCAocGVyIHRoZSBhYm92ZSBwb2ludCkgbWFrZVxuICogICB0aGUgc2VsZWN0ZWQgaXRlbSB2aXNpYmxlLlxuICpcbiAqIFByb2dyYW1tYXRpY2FsbHkgc2VsZWN0aW5nIGFuIGl0ZW0gKGJ5IHNldHRpbmcgdGhlIHNlbGVjdGVkIHByb3BlcnR5KSBzY3JvbGxzXG4gKiB0aGUgaXRlbSBpbnRvIHZpZXcuXG4gKlxuICogVGhlIHVzZXIgY2FuIGFsc28gc2VsZWN0IGFuIGl0ZW0gYnkgdHlwaW5nIHRoZSBiZWdpbm5pbmcgb2YgYW4gaXRlbSdzIHRleHQuXG4gKlxuICogQGV4dGVuZHMgRWxlbWVudEJhc2VcbiAqIEBtaXhlcyBDbGlja1NlbGVjdGlvbk1peGluXG4gKiBAbWl4ZXMgQ29udGVudEl0ZW1zTWl4aW5cbiAqIEBtaXhlcyBEaXJlY3Rpb25TZWxlY3Rpb25NaXhpblxuICogQG1peGVzIERpc3RyaWJ1dGVkQ2hpbGRyZW5Db250ZW50TWl4aW5cbiAqIEBtaXhlcyBHZW5lcmljTWl4aW5cbiAqIEBtaXhlcyBLZXlib2FyZE1peGluXG4gKiBAbWl4ZXMgS2V5Ym9hcmREaXJlY3Rpb25NaXhpblxuICogQG1peGVzIEtleWJvYXJkUGFnZWRTZWxlY3Rpb25NaXhpblxuICogQG1peGVzIEtleWJvYXJkUHJlZml4U2VsZWN0aW9uTWl4aW5cbiAqIEBtaXhpcyBTZWxlY3RlZEl0ZW1UZXh0VmFsdWVNaXhpblxuICogQG1peGVzIFNlbGVjdGlvbkFyaWFBY3RpdmVNaXhpblxuICogQG1peGVzIFNlbGVjdGlvbkhpZ2hsaWdodE1peGluXG4gKiBAbWl4ZXMgU2VsZWN0aW9uSW5WaWV3TWl4aW5cbiAqIEBtaXhlcyBTaW5nbGVTZWxlY3Rpb25NaXhpblxuICovXG5jbGFzcyBMaXN0Qm94IGV4dGVuZHMgRWxlbWVudEJhc2UuY29tcG9zZShcbiAgQ2xpY2tTZWxlY3Rpb25NaXhpbixcbiAgQ29udGVudEl0ZW1zTWl4aW4sXG4gIERpcmVjdGlvblNlbGVjdGlvbk1peGluLFxuICBEaXN0cmlidXRlZENoaWxkcmVuQ29udGVudE1peGluLFxuICBHZW5lcmljTWl4aW4sXG4gIEtleWJvYXJkTWl4aW4sXG4gIEtleWJvYXJkRGlyZWN0aW9uTWl4aW4sXG4gIEtleWJvYXJkUGFnZWRTZWxlY3Rpb25NaXhpbixcbiAgS2V5Ym9hcmRQcmVmaXhTZWxlY3Rpb25NaXhpbixcbiAgU2VsZWN0ZWRJdGVtVGV4dFZhbHVlTWl4aW4sXG4gIFNlbGVjdGlvbkFyaWFBY3RpdmVNaXhpbixcbiAgU2VsZWN0aW9uSGlnaGxpZ2h0TWl4aW4sXG4gIFNlbGVjdGlvbkluVmlld01peGluLFxuICBTaW5nbGVTZWxlY3Rpb25NaXhpblxuKSB7XG5cbiAgZ2V0IFtzeW1ib2xzLmRlZmF1bHRzXSgpIHtcbiAgICBjb25zdCBkZWZhdWx0cyA9IHN1cGVyW3N5bWJvbHMuZGVmYXVsdHNdIHx8IHt9O1xuICAgIGRlZmF1bHRzLm5hdmlnYXRpb25BeGlzID0gJ3ZlcnRpY2FsJztcbiAgICByZXR1cm4gZGVmYXVsdHM7XG4gIH1cblxuICBnZXQgc2Nyb2xsVGFyZ2V0KCkge1xuICAgIHJldHVybiB0aGlzLiQuaXRlbXNDb250YWluZXI7XG4gIH1cblxuICBnZXQgW3N5bWJvbHMudGVtcGxhdGVdKCkge1xuICAgIGNvbnN0IGJhc2VUZW1wbGF0ZSA9IHN1cGVyW3N5bWJvbHMudGVtcGxhdGVdIHx8ICcnO1xuICAgIHJldHVybiBgXG4gICAgICA8c3R5bGU+XG4gICAgICA6aG9zdCB7XG4gICAgICAgIGRpc3BsYXk6IC13ZWJraXQtZmxleDtcbiAgICAgICAgZGlzcGxheTogZmxleDtcbiAgICAgICAgLXdlYmtpdC10YXAtaGlnaGxpZ2h0LWNvbG9yOiByZ2JhKDAsIDAsIDAsIDApO1xuICAgICAgfVxuXG4gICAgICBbdGFyZ2V0PVwiY2hpbGRcIl0ge1xuICAgICAgICBkaXNwbGF5OiAtd2Via2l0LWZsZXg7XG4gICAgICAgIGRpc3BsYXk6IGZsZXg7XG4gICAgICAgIC13ZWJraXQtZmxleDogMTtcbiAgICAgICAgZmxleDogMTtcbiAgICAgIH1cblxuICAgICAgI2l0ZW1zQ29udGFpbmVyIHtcbiAgICAgICAgLXdlYmtpdC1mbGV4OiAxO1xuICAgICAgICBmbGV4OiAxO1xuICAgICAgICAtd2Via2l0LW92ZXJmbG93LXNjcm9sbGluZzogdG91Y2g7XG4gICAgICAgIG92ZXJmbG93LXk6IHNjcm9sbDsgLyogZm9yIG1vbWVudHVtIHNjcm9sbGluZyAqL1xuICAgICAgfVxuXG4gICAgICAvKiBHZW5lcmljTWl4aW4gYXBwZWFyYW5jZSAqL1xuICAgICAgOmhvc3QoW2dlbmVyaWM9XCJcIl0pIHtcbiAgICAgICAgYm9yZGVyOiAxcHggc29saWQgZ3JheTtcbiAgICAgICAgYm94LXNpemluZzogYm9yZGVyLWJveDtcbiAgICAgICAgY3Vyc29yOiBkZWZhdWx0O1xuICAgICAgfVxuXG4gICAgICA6aG9zdChbZ2VuZXJpYz1cIlwiXSkgI2l0ZW1zQ29udGFpbmVyIDo6c2xvdHRlZCgqKSB7XG4gICAgICAgIGN1cnNvcjogZGVmYXVsdDtcbiAgICAgICAgcGFkZGluZzogMC4yNWVtO1xuICAgICAgICAtd2Via2l0LXVzZXItc2VsZWN0OiBub25lO1xuICAgICAgICAtbW96LXVzZXItc2VsZWN0OiBub25lO1xuICAgICAgICAtbXMtdXNlci1zZWxlY3Q6IG5vbmU7XG4gICAgICAgIHVzZXItc2VsZWN0OiBub25lO1xuICAgICAgfVxuICAgICAgPC9zdHlsZT5cblxuICAgICAgPGRpdiBpZD1cIml0ZW1zQ29udGFpbmVyXCIgcm9sZT1cIm5vbmVcIj5cbiAgICAgICAgPHNsb3Q+PC9zbG90PlxuICAgICAgPC9kaXY+XG4gICAgICAke2Jhc2VUZW1wbGF0ZX1cbiAgICBgO1xuICB9XG5cbiAgLyoqXG4gICAqIEZpcmVzIHdoZW4gdGhlIGxpc3QncyB2YWx1ZSBwcm9wZXJ0eSBjaGFuZ2VzLlxuICAgKlxuICAgKiBAbWVtYmVyb2YgTGlzdEJveFxuICAgKiBAZXZlbnQgdmFsdWUtY2hhbmdlZFxuICAgKi9cbn1cblxuXG5jdXN0b21FbGVtZW50cy5kZWZpbmUoJ2Jhc2ljLWxpc3QtYm94JywgTGlzdEJveCk7XG5leHBvcnQgZGVmYXVsdCBMaXN0Qm94O1xuIl19
+!function t(e,o,r){function n(c,u){if(!o[c]){if(!e[c]){var l="function"==typeof require&&require;if(!u&&l)return l(c,!0);if(i)return i(c,!0);var a=new Error("Cannot find module '"+c+"'");throw a.code="MODULE_NOT_FOUND",a}var p=o[c]={exports:{}};e[c][0].call(p.exports,function(t){var o=e[c][1][t];return n(o?o:t)},p,p.exports,t,e,o,r)}return o[c].exports}for(var i="function"==typeof require&&require,c=0;c=0&&(t.selectedIndex=r,e.stopPropagation())}),t}return i(o,e),u(o,[{key:"selectedIndex",get:function(){return a(o.prototype.__proto__||Object.getPrototypeOf(o.prototype),"selectedIndex",this)},set:function(e){"selectedIndex"in t.prototype&&l(o.prototype.__proto__||Object.getPrototypeOf(o.prototype),"selectedIndex",e,this)}}]),o}(t);return e}},{}],3:[function(t,e,o){"use strict";function r(t,e){if(!(t instanceof e))throw new TypeError("Cannot call a class as a function")}function n(t,e){if(!t)throw new ReferenceError("this hasn't been initialised - super() hasn't been called");return!e||"object"!=typeof e&&"function"!=typeof e?t:e}function i(t,e){if("function"!=typeof e&&null!==e)throw new TypeError("Super expression must either be null or a function, not "+typeof e);t.prototype=Object.create(e&&e.prototype,{constructor:{value:t,enumerable:!1,writable:!0,configurable:!0}}),e&&(Object.setPrototypeOf?Object.setPrototypeOf(t,e):t.__proto__=e)}function c(t,e){if("function"==typeof e)return e(t);var o=function(t){function e(){return r(this,e),n(this,(e.__proto__||Object.getPrototypeOf(e)).apply(this,arguments))}return i(e,t),e}(t);return u(e,o.prototype,a),o}function u(t,e){var o=arguments.length>2&&void 0!==arguments[2]?arguments[2]:[];return Object.getOwnPropertyNames(t).forEach(function(r){if(o.indexOf(r)<0){var n=Object.getOwnPropertyDescriptor(t,r);Object.defineProperty(e,r,n)}}),e}Object.defineProperty(o,"__esModule",{value:!0});var l=function(){function t(t,e){for(var o=0;o=e){f=!0;break}p+=c}if(!f)return null;var d=getComputedStyle(a),_=parseFloat(d.paddingTop),b=parseFloat(d.paddingBottom),h=s+a.clientTop+_,O=h+a.clientHeight-_-b;return o&&h<=e||!o&&O>=e?p:p-c}function l(t,e){var o=t.scrollTarget,r=o.scrollTop+(e?o.clientHeight:0),n=u(t,r,e),i=t.selectedIndex,c=void 0;if(n&&i===n){var l=(e?1:-1)*o.clientHeight;c=u(t,r+l,e)}else c=n;return c||(c=e?t.items.length-1:0),c!==i&&(t.selectedIndex=c,!0)}Object.defineProperty(o,"__esModule",{value:!0});var a=function(){function t(t,e){for(var o=0;o0&&(t[m]=t[m].substr(0,e-1)),t.selectItemWithTextPrefix(t[m]),y(t)}function p(t,e){var o=t[m]||"";t[m]=o+e.toLowerCase(),t.selectItemWithTextPrefix(t[m]),y(t)}function s(t){t[j]&&(clearTimeout(t[j]),t[j]=!1)}function f(t){t[m]="",s(t)}function y(t){s(t),t[j]=setTimeout(function(){f(t)},P)}Object.defineProperty(o,"__esModule",{value:!0});var d=function(){function t(t,e){for(var o=0;o=0&&(this.selectedIndex=o)}}}]),e}(t);return e};var P=1e3},{"./createSymbol":20,"./symbols":23}],13:[function(t,e,o){"use strict";function r(t,e){if(!(t instanceof e))throw new TypeError("Cannot call a class as a function")}function n(t,e){if(!t)throw new ReferenceError("this hasn't been initialised - super() hasn't been called");return!e||"object"!=typeof e&&"function"!=typeof e?t:e}function i(t,e){if("function"!=typeof e&&null!==e)throw new TypeError("Super expression must either be null or a function, not "+typeof e);t.prototype=Object.create(e&&e.prototype,{constructor:{value:t,enumerable:!1,writable:!0,configurable:!0}}),e&&(Object.setPrototypeOf?Object.setPrototypeOf(t,e):t.__proto__=e)}Object.defineProperty(o,"__esModule",{value:!0});var c=function(){function t(t,e){for(var o=0;o\n :host([generic=""]) ::slotted(.selected) {\n background-color: highlight;\n color: highlighttext;\n }\n \n '+t+"\n "}}]),e}(t);return e}},{"../src/symbols":23}],16:[function(t,e,o){"use strict";function r(t,e){if(!(t instanceof e))throw new TypeError("Cannot call a class as a function")}function n(t,e){if(!t)throw new ReferenceError("this hasn't been initialised - super() hasn't been called");return!e||"object"!=typeof e&&"function"!=typeof e?t:e}function i(t,e){if("function"!=typeof e&&null!==e)throw new TypeError("Super expression must either be null or a function, not "+typeof e);t.prototype=Object.create(e&&e.prototype,{constructor:{value:t,enumerable:!1,writable:!0,configurable:!0}}),e&&(Object.setPrototypeOf?Object.setPrototypeOf(t,e):t.__proto__=e)}Object.defineProperty(o,"__esModule",{value:!0});var c=function(){function t(t,e){for(var o=0;oi?e.scrollTop+=n-i:r0;)e.content.appendChild(o.childNodes[0]);return e}function l(t,e){window.WebComponents.ShadowCSS.shimStyling(t.content,e)}Object.defineProperty(o,"__esModule",{value:!0});var a=t("../src/symbols"),p=r(a);o.default=function(t){var e=function(t){function e(){n(this,e);var t=i(this,(e.__proto__||Object.getPrototypeOf(e)).call(this)),o=t[p.default.template];if(o){"string"==typeof o&&(o=u(o)),window.ShadowDOMPolyfill&&l(o,t.localName);var r=t.attachShadow({mode:"open"}),c=document.importNode(o.content,!0);r.appendChild(c)}return t}return c(e,t),e}(t);return e}},{"../src/symbols":23}],19:[function(t,e,o){"use strict";function r(t){return t&&t.__esModule?t:{default:t}}function n(t,e){if(!(t instanceof e))throw new TypeError("Cannot call a class as a function")}function i(t,e){if(!t)throw new ReferenceError("this hasn't been initialised - super() hasn't been called");return!e||"object"!=typeof e&&"function"!=typeof e?t:e}function c(t,e){if("function"!=typeof e&&null!==e)throw new TypeError("Super expression must either be null or a function, not "+typeof e);t.prototype=Object.create(e&&e.prototype,{constructor:{value:t,enumerable:!1,writable:!0,configurable:!0}}),e&&(Object.setPrototypeOf?Object.setPrototypeOf(t,e):t.__proto__=e)}function u(t,e){var o=t.items.length,r=t.selectionWraps?(e%o+o)%o:Math.max(Math.min(e,o-1),0),n=t.selectedIndex;return n!==r&&(t.selectedIndex=r,!0)}function l(t){var e=t.items,o=e?e.length:0,r=t.selectedItem;if(r)if(0===o)t.selectedItem=null;else{var n=Array.prototype.indexOf.call(e,r),i=t.selectedIndex;if(n<0){var c=Math.min(i,o-1);t.selectedItem=e[c]}else n!==i&&(t.selectedIndex=n)}else t.selectionRequired&&(t.selectedIndex=0)}function a(t){var e=void 0,o=void 0,r=t.items;if(null!=r&&0!==r.length||(e=!1,o=!1),t.selectionWraps)e=!0,o=!0;else{var n=t.selectedIndex;n<0&&r.length>0?(e=!0,o=!0):(o=n>0,e=n0;c&&e>=0&&e=0?i[e]:null,this[j]=n}else n=this[j];if("selectedIndex"in t.prototype&&f(o.prototype.__proto__||Object.getPrototypeOf(o.prototype),"selectedIndex",e,this),e!==r){this[P]=e;var u=new CustomEvent("selected-index-changed",{detail:{selectedIndex:e,value:e}});this.dispatchEvent(u)}this[w]!==n&&(this.selectedItem=n)}},{key:"selectedItem",get:function(){return this[j]||null},set:function(e){var r=this[w],n=void 0;if(e!==this[j]){var i=this.items,c=i&&i.length>0;n=c?Array.prototype.indexOf.call(i,e):-1,this[m]=n,n<0&&(e=null),this[j]=e}else n=this[m];if("selectedItem"in t.prototype&&f(o.prototype.__proto__||Object.getPrototypeOf(o.prototype),"selectedItem",e,this),e!==r){this[w]=e,r&&this[b.default.itemSelected](r,!1),e&&this[b.default.itemSelected](e,!0),a(this);var u=new CustomEvent("selected-item-changed",{detail:{selectedItem:e,value:e}});this.dispatchEvent(u)}this[P]!==n&&(this.selectedIndex=n)}},{key:"selectionRequired",get:function(){return this[v]},set:function(e){this[v]=e,"selectionRequired"in t.prototype&&f(o.prototype.__proto__||Object.getPrototypeOf(o.prototype),"selectionRequired",e,this),l(this)}},{key:"selectionWraps",get:function(){return this[g]},set:function(e){this[g]="true"===String(e),"selectionWraps"in t.prototype&&f(o.prototype.__proto__||Object.getPrototypeOf(o.prototype),"selectionWraps",e,this),a(this)}}]),o}(t);return e}},{"./createSymbol":20,"./symbols":23}],20:[function(t,e,o){"use strict";function r(t){return"function"==typeof Symbol?Symbol(t):"_"+t}Object.defineProperty(o,"__esModule",{value:!0}),o.default=r},{}],21:[function(t,e,o){"use strict";function r(t){i.push(t),c.textContent=++u}function n(){for(;i.length>0;){var t=i.shift();t()}}Object.defineProperty(o,"__esModule",{value:!0}),o.default=r;var i=[],c=document.createTextNode(""),u=0,l=new MutationObserver(n);l.observe(c,{characterData:!0})},{}],22:[function(t,e,o){"use strict";function r(t){return t&&t.__esModule?t:{default:t}}function n(t,e,o){if(null===o||"undefined"==typeof o)t.removeAttribute(e);else{var r=String(o);t.getAttribute(e)!==r&&t.setAttribute(e,o)}}Object.defineProperty(o,"__esModule",{value:!0});var i=t("./createSymbol"),c=r(i),u=t("./toggleClass"),l=r(u),a=(0,c.default)("safeToSetAttributes"),p=(0,c.default)("pendingAttributes"),s=(0,c.default)("pendingClasses");o.default={connected:function(t){if(t[a]=!0,t[p]){for(var e in t[p]){var o=t[p][e];n(t,e,o)}t[p]=null}if(t[s]){for(var r in t[s]){var i=t[s][r];(0,l.default)(t,r,i)}t[s]=null}},setAttribute:function(t,e,o){t[a]?n(t,e,o):(t[p]||(t[p]={}),t[p][e]=o)},toggleClass:function(t,e,o){t[a]?(0,l.default)(t,e,o):(t[s]||(t[s]={}),t[s][e]=o)}}},{"./createSymbol":20,"./toggleClass":24}],23:[function(t,e,o){"use strict";function r(t){return t&&t.__esModule?t:{default:t}}Object.defineProperty(o,"__esModule",{value:!0});var n=t("./createSymbol"),i=r(n),c={defaults:(0,i.default)("defaults"),dragging:(0,i.default)("dragging"),goDown:(0,i.default)("goDown"),goEnd:(0,i.default)("goEnd"),goLeft:(0,i.default)("goLeft"),goRight:(0,i.default)("goRight"),goStart:(0,i.default)("goStart"),goUp:(0,i.default)("goUp"),itemAdded:(0,i.default)("itemAdded"),itemsChanged:(0,i.default)("itemsChanged"),itemSelected:(0,i.default)("itemSelected"),keydown:(0,i.default)("keydown"),template:(0,i.default)("template")};o.default=c},{"./createSymbol":20}],24:[function(t,e,o){"use strict";function r(t,e,o){var r=t.classList,n="undefined"==typeof o?!r.contains(e):o;return n?r.add(e):r.remove(e),n}Object.defineProperty(o,"__esModule",{value:!0}),o.default=r},{}],25:[function(t,e,o){"use strict";function r(t){return t&&t.__esModule?t:{default:t}}function n(t,e){if(!(t instanceof e))throw new TypeError("Cannot call a class as a function")}function i(t,e){if(!t)throw new ReferenceError("this hasn't been initialised - super() hasn't been called");return!e||"object"!=typeof e&&"function"!=typeof e?t:e}function c(t,e){if("function"!=typeof e&&null!==e)throw new TypeError("Super expression must either be null or a function, not "+typeof e);t.prototype=Object.create(e&&e.prototype,{constructor:{value:t,enumerable:!1,writable:!0,configurable:!0}}),e&&(Object.setPrototypeOf?Object.setPrototypeOf(t,e):t.__proto__=e)}Object.defineProperty(o,"__esModule",{value:!0});var u=t("../../basic-component-mixins/src/AttributeMarshallingMixin"),l=r(u),a=t("../../basic-component-mixins/src/ComposableMixin"),p=r(a),s=t("../../basic-component-mixins/src/DistributedChildrenMixin"),f=r(s),y=t("../../basic-component-mixins/src/ShadowElementReferencesMixin"),d=r(y),_=t("../../basic-component-mixins/src/ShadowTemplateMixin"),b=r(_),h=function(t){function e(){return n(this,e),i(this,(e.__proto__||Object.getPrototypeOf(e)).apply(this,arguments))}return c(e,t),e}((0,p.default)(HTMLElement).compose(b.default,d.default,l.default,f.default));o.default=h},{"../../basic-component-mixins/src/AttributeMarshallingMixin":1,"../../basic-component-mixins/src/ComposableMixin":3,"../../basic-component-mixins/src/DistributedChildrenMixin":7,"../../basic-component-mixins/src/ShadowElementReferencesMixin":17,"../../basic-component-mixins/src/ShadowTemplateMixin":18}],26:[function(t,e,o){"use strict";function r(t){return t&&t.__esModule?t:{default:t}}var n=t("./src/ListBox"),i=r(n);window.Basic=window.Basic||{},window.Basic.ListBox=i.default},{"./src/ListBox":27}],27:[function(t,e,o){"use strict";function r(t){return t&&t.__esModule?t:{default:t}}function n(t,e){if(!(t instanceof e))throw new TypeError("Cannot call a class as a function")}function i(t,e){if(!t)throw new ReferenceError("this hasn't been initialised - super() hasn't been called");return!e||"object"!=typeof e&&"function"!=typeof e?t:e}function c(t,e){if("function"!=typeof e&&null!==e)throw new TypeError("Super expression must either be null or a function, not "+typeof e);t.prototype=Object.create(e&&e.prototype,{constructor:{value:t,enumerable:!1,writable:!0,configurable:!0}}),e&&(Object.setPrototypeOf?Object.setPrototypeOf(t,e):t.__proto__=e)}Object.defineProperty(o,"__esModule",{value:!0});var u=function(){function t(t,e){for(var o=0;o\n :host {\n display: -webkit-flex;\n display: flex;\n -webkit-tap-highlight-color: rgba(0, 0, 0, 0);\n }\n\n [target="child"] {\n display: -webkit-flex;\n display: flex;\n -webkit-flex: 1;\n flex: 1;\n }\n\n #itemsContainer {\n -webkit-flex: 1;\n flex: 1;\n -webkit-overflow-scrolling: touch;\n overflow-y: scroll; /* for momentum scrolling */\n }\n\n /* GenericMixin appearance */\n :host([generic=""]) {\n border: 1px solid gray;\n box-sizing: border-box;\n cursor: default;\n }\n\n :host([generic=""]) #itemsContainer ::slotted(*) {\n cursor: default;\n padding: 0.25em;\n -webkit-user-select: none;\n -moz-user-select: none;\n -ms-user-select: none;\n user-select: none;\n }\n \n\n \n \n
\n '+t+"\n "}}]),e}(p.default.compose(d.default,b.default,O.default,f.default,g.default,j.default,w.default,k.default,S.default,M.default,I.default,D.default,F.default,N.default));customElements.define("basic-list-box",W),o.default=W},{"../../basic-component-mixins/src/ClickSelectionMixin":2,"../../basic-component-mixins/src/ContentItemsMixin":4,"../../basic-component-mixins/src/DirectionSelectionMixin":5,"../../basic-component-mixins/src/DistributedChildrenContentMixin":6,"../../basic-component-mixins/src/GenericMixin":8,"../../basic-component-mixins/src/KeyboardDirectionMixin":9,"../../basic-component-mixins/src/KeyboardMixin":10,"../../basic-component-mixins/src/KeyboardPagedSelectionMixin":11,"../../basic-component-mixins/src/KeyboardPrefixSelectionMixin":12,"../../basic-component-mixins/src/SelectedItemTextValueMixin":13,"../../basic-component-mixins/src/SelectionAriaActiveMixin":14,"../../basic-component-mixins/src/SelectionHighlightMixin":15,"../../basic-component-mixins/src/SelectionInViewMixin":16,"../../basic-component-mixins/src/SingleSelectionMixin":19,"../../basic-component-mixins/src/symbols":23,"../../basic-element-base/src/ElementBase":25}]},{},[26]);
+//# sourceMappingURL=basic-list-box.js.map
diff --git a/packages/basic-list-box/dist/basic-list-box.js.map b/packages/basic-list-box/dist/basic-list-box.js.map
new file mode 100644
index 00000000..533009c5
--- /dev/null
+++ b/packages/basic-list-box/dist/basic-list-box.js.map
@@ -0,0 +1 @@
+{"version":3,"sources":["node_modules/browser-pack/_prelude.js","packages/basic-component-mixins/src/AttributeMarshallingMixin.js","packages/basic-component-mixins/src/ClickSelectionMixin.js","packages/basic-component-mixins/src/ComposableMixin.js","packages/basic-component-mixins/src/ContentItemsMixin.js","packages/basic-component-mixins/src/DirectionSelectionMixin.js","packages/basic-component-mixins/src/DistributedChildrenContentMixin.js","packages/basic-component-mixins/src/DistributedChildrenMixin.js","packages/basic-component-mixins/src/GenericMixin.js","packages/basic-component-mixins/src/KeyboardDirectionMixin.js","packages/basic-component-mixins/src/KeyboardMixin.js","packages/basic-component-mixins/src/KeyboardPagedSelectionMixin.js","packages/basic-component-mixins/src/KeyboardPrefixSelectionMixin.js","packages/basic-component-mixins/src/SelectedItemTextValueMixin.js","packages/basic-component-mixins/src/SelectionAriaActiveMixin.js","packages/basic-component-mixins/src/SelectionHighlightMixin.js","packages/basic-component-mixins/src/SelectionInViewMixin.js","packages/basic-component-mixins/src/ShadowElementReferencesMixin.js","packages/basic-component-mixins/src/ShadowTemplateMixin.js","packages/basic-component-mixins/src/SingleSelectionMixin.js","packages/basic-component-mixins/src/createSymbol.js","packages/basic-component-mixins/src/microtask.js","packages/basic-component-mixins/src/safeAttributes.js","packages/basic-component-mixins/src/symbols.js","packages/basic-component-mixins/src/toggleClass.js","packages/basic-element-base/src/ElementBase.js","packages/basic-list-box/globals.js","packages/basic-list-box/src/ListBox.js"],"names":["e","t","n","r","s","o","u","a","require","i","f","Error","code","l","exports","call","length","1","module","attributeToPropertyName","attributeName","propertyName","attributeToPropertyNames","hypenRegEx","replace","match","toUpperCase","attributesForClass","classFn","HTMLElement","Object","baseClass","getPrototypeOf","prototype","constructor","baseAttributes","propertyNames","getOwnPropertyNames","setterNames","filter","getOwnPropertyDescriptor","set","attributes","map","setterName","propertyNameToAttribute","diff","attribute","indexOf","concat","propertyNamesToAttributes","uppercaseRegEx","toLowerCase","_safeAttributes","base","AttributeMarshalling","_base","_classCallCheck","this","_possibleConstructorReturn","__proto__","apply","arguments","_inherits","_createClass","key","value","oldValue","newValue","_get","_safeAttributes2","default","connected","setAttribute","className","toggleClass","get","indexOfContainingItem","element","target","items","itemCount","item","contains","ClickSelection","_this","addEventListener","event","path","index","selectedIndex","stopPropagation","_set","composeClass","mixin","Subclass","_base2","copyOwnProperties","NON_MIXABLE_OBJECT_PROPERTIES","source","ignorePropertyNames","undefined","forEach","name","descriptor","defineProperty","Composable","_len","mixins","Array","_key","reduce","filterAuxiliaryElements","auxiliaryTags","localName","_createSymbol","_toggleClass","_symbols","itemsSymbol","_createSymbol2","itemInitializedSymbol","ContentItems","_symbols2","itemsChanged","itemAdded","itemSelected","selected","_toggleClass2","_this2","dispatchEvent","CustomEvent","content","DirectionSelection","goDown","selectNext","goEnd","selectLast","goLeft","selectPrevious","goRight","goStart","selectFirst","goUp","selectedFraction","_microtask","DistributedChildrenContent","shadowRoot","slots","querySelectorAll","slot","contentChanged","_microtask2","distributedChildren","console","warn","expandContentElements","nodes","includeTextNodes","_ref","expanded","node","isSlot","HTMLSlotElement","assignedNodes","flatten","Text","flattened","_toConsumableArray","DistributedChildren","children","childNodes","strings","distributedChildNodes","child","textContent","join","genericSymbol","Generic","generic","defaults","parsed","String","removeAttribute","navigationAxisSymbol","KeyboardDirection","navigationAxis","keydown","handled","axis","horizontal","vertical","keyCode","metaKey","altKey","Keyboard","preventDefault","getAttribute","tabindex","getIndexOfItemAtY","y","downward","start","end","step","scrollTarget","topOfClientArea","offsetTop","clientTop","itemIndex","itemTop","found","itemBottom","offsetHeight","itemStyle","getComputedStyle","itemPaddingTop","parseFloat","paddingTop","itemPaddingBottom","paddingBottom","contentTop","contentBottom","clientHeight","scrollOnePage","edge","scrollTop","indexOfItemAtEdge","newIndex","delta","KeyboardPagedSelection","pageUp","pageDown","getIndexOfItemWithTextPrefix","prefix","itemTextContents","getItemTextContents","prefixLength","itemTextContent","substr","itemTextContentsSymbol","text","alt","handleBackspace","typedPrefixSymbol","selectItemWithTextPrefix","setPrefixTimeout","handlePlainCharacter","char","resetPrefixTimeout","prefixTimeoutSymbol","clearTimeout","resetTypedPrefix","setTimeout","PREFIX_TIMEOUT_DURATION","KeyboardPrefixSelection","resetPrefix","ctrlKey","which","fromCharCode","SelectedItemTextValue","selectedItem","currentIndex","idCount","SelectionAriaActive","role","id","baseId","itemId","SelectionHighlight","template","baseTemplate","SelectionInView","scrollItemIntoView","elementTop","elementBottom","scrollBottom","ShadowElementReferences","$","nodesWithIds","createTemplateWithInnerHTML","innerHTML","document","createElement","div","appendChild","shimTemplateStyles","tag","window","WebComponents","ShadowCSS","shimStyling","ShadowTemplate","ShadowDOMPolyfill","root","attachShadow","mode","clone","importNode","selectIndex","count","boundedIndex","selectionWraps","Math","max","min","previousIndex","trackSelectedItem","previousSelectedItem","indexInCurrentItems","previousSelectedIndex","newSelectedIndex","selectionRequired","updatePossibleNavigations","canSelectNext","canSelectPrevious","canSelectNextSymbol","canSelectPreviousSymbol","selectionRequiredSymbol","selectionWrapsSymbol","externalSelectedIndexSymbol","externalSelectedItemSymbol","internalSelectedIndexSymbol","internalSelectedItemSymbol","SingleSelection","previousCanSelectNext","previousCanSelectPrevious","hasItems","detail","createSymbol","description","Symbol","microtask","callback","callbacks","push","counter","executeCallbacks","shift","createTextNode","observer","MutationObserver","observe","characterData","setAttributeToElement","safeToSetAttributesSymbol","pendingAttributesSymbol","pendingClassesSymbol","_value","_toggleClass3","symbols","dragging","force","classList","addClass","add","remove","_AttributeMarshallingMixin","_ComposableMixin","_DistributedChildrenMixin","_ShadowElementReferencesMixin","_ShadowTemplateMixin","ElementBase","_ComposableMixin2","compose","_ShadowTemplateMixin2","_ShadowElementReferencesMixin2","_AttributeMarshallingMixin2","_DistributedChildrenMixin2","_ListBox","Basic","ListBox","_ListBox2","_ElementBase","_DistributedChildrenContentMixin","_ClickSelectionMixin","_ContentItemsMixin","_DirectionSelectionMixin","_GenericMixin","_KeyboardMixin","_KeyboardDirectionMixin","_KeyboardPagedSelectionMixin","_KeyboardPrefixSelectionMixin","_SelectedItemTextValueMixin","_SelectionAriaActiveMixin","_SelectionHighlightMixin","_SelectionInViewMixin","_SingleSelectionMixin","itemsContainer","_ElementBase2","_ClickSelectionMixin2","_ContentItemsMixin2","_DirectionSelectionMixin2","_DistributedChildrenContentMixin2","_GenericMixin2","_KeyboardMixin2","_KeyboardDirectionMixin2","_KeyboardPagedSelectionMixin2","_KeyboardPrefixSelectionMixin2","_SelectedItemTextValueMixin2","_SelectionAriaActiveMixin2","_SelectionHighlightMixin2","_SelectionInViewMixin2","_SingleSelectionMixin2","customElements","define"],"mappings":"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","file":"basic-list-box.js","sourcesContent":["(function e(t,n,r){function s(o,u){if(!n[o]){if(!t[o]){var a=typeof require==\"function\"&&require;if(!u&&a)return a(o,!0);if(i)return i(o,!0);var f=new Error(\"Cannot find module '\"+o+\"'\");throw f.code=\"MODULE_NOT_FOUND\",f}var l=n[o]={exports:{}};t[o][0].call(l.exports,function(e){var n=t[o][1][e];return s(n?n:e)},l,l.exports,e,t,n,r)}return n[o].exports}var i=typeof require==\"function\"&&require;for(var o=0;o {\n\n /**\n * Mixin which marshalls attributes to properties and vice versa.\n *\n * If your component exposes a setter for a property, it's generally a good\n * idea to let devs using your component be able to set that property in HTML\n * via an element attribute. You can code that yourself by writing an\n * `attributeChangedCallback`, or you can use this mixin to get a degree of\n * automatic support.\n *\n * This mixin implements an `attributeChangedCallback` that will attempt to\n * convert a change in an element attribute into a call to the corresponding\n * property setter. Attributes typically follow hyphenated names (\"foo-bar\"),\n * whereas properties typically use camelCase names (\"fooBar\"). This mixin\n * respects that convention, automatically mapping the hyphenated attribute\n * name to the corresponding camelCase property name.\n *\n * Example: You define a component using this mixin:\n *\n * class MyElement extends AttributeMarshallingMixin(HTMLElement) {\n * get fooBar() { return this._fooBar; }\n * set fooBar(value) { this._fooBar = value; }\n * }\n * customElements.define('my-element', MyElement);\n *\n * If someone then instantiates your component in HTML:\n *\n * \n *\n * Then, after the element has been upgraded, the `fooBar` setter will\n * automatically be invoked with the initial value \"Hello\".\n *\n * For the time being, this mixin only supports string-valued properties.\n * If you'd like to convert string attributes to other types (numbers,\n * booleans), you need to implement `attributeChangedCallback` yourself.\n */\n class AttributeMarshalling extends base {\n\n /*\n * Handle a change to the attribute with the given name.\n */\n attributeChangedCallback(attributeName, oldValue, newValue) {\n if (super.attributeChangedCallback) { super.attributeChangedCallback(); }\n const propertyName = attributeToPropertyName(attributeName);\n // If the attribute name corresponds to a property name, set the property.\n // Ignore standard HTMLElement properties handled by the DOM.\n if (propertyName in this && !(propertyName in HTMLElement.prototype)) {\n this[propertyName] = newValue;\n }\n }\n\n connectedCallback() {\n if (super.connectedCallback) { super.connectedCallback(); }\n safeAttributes.connected(this);\n }\n\n static get observedAttributes() {\n return attributesForClass(this);\n }\n\n /**\n * Set/unset the attribute with the indicated name.\n *\n * This method exists primarily to handle the case where an element wants to\n * set a default property value that should be reflected as an attribute. An\n * important limitation of custom element consturctors is that they cannot\n * set attributes. A call to `reflectAttribute` during the constructor will\n * be deferred until the element is connected to the document.\n *\n * @param {string} attribute - The name of the *attribute* (not property) to set.\n * @param {object} value - The value to set. If null, the attribute will be removed.\n */\n reflectAttribute(attribute, value) {\n return safeAttributes.setAttribute(this, attribute, value);\n }\n\n /**\n * Set/unset the class with the indicated name.\n *\n * This method exists primarily to handle the case where an element wants to\n * set a default property value that should be reflected as as class. An\n * important limitation of custom element consturctors is that they cannot\n * set attributes, including the `class` attribute. A call to\n * `reflectClass` during the constructor will be deferred until the element\n * is connected to the document.\n *\n * @param {string} className - The name of the class to set.\n * @param {object} value - True to set the class, false to remove it.\n */\n reflectClass(className, value) {\n return safeAttributes.toggleClass(this, className, value);\n }\n\n }\n\n return AttributeMarshalling;\n};\n\n\n// Convert hyphenated foo-bar attribute name to camel case fooBar property name.\nfunction attributeToPropertyName(attributeName) {\n let propertyName = attributeToPropertyNames[attributeName];\n if (!propertyName) {\n // Convert and memoize.\n const hypenRegEx = /-([a-z])/g;\n propertyName = attributeName.replace(hypenRegEx,\n match => match[1].toUpperCase());\n attributeToPropertyNames[attributeName] = propertyName;\n }\n return propertyName;\n}\n\nfunction attributesForClass(classFn) {\n\n // We treat the element base classes as if they have no attributes, since we\n // don't want to receive attributeChangedCallback for them.\n if (classFn === HTMLElement || classFn === Object) {\n return [];\n }\n\n // Get attributes for parent class.\n const baseClass = Object.getPrototypeOf(classFn.prototype).constructor;\n const baseAttributes = attributesForClass(baseClass);\n\n // Get attributes for this class.\n const propertyNames = Object.getOwnPropertyNames(classFn.prototype);\n const setterNames = propertyNames.filter(propertyName =>\n typeof Object.getOwnPropertyDescriptor(\n classFn.prototype, propertyName).set === 'function');\n const attributes = setterNames.map(setterName =>\n propertyNameToAttribute(setterName));\n\n // Merge.\n const diff = attributes.filter(attribute =>\n baseAttributes.indexOf(attribute) < 0);\n return baseAttributes.concat(diff);\n}\n\n// Convert a camel case fooBar property name to a hyphenated foo-bar attribute.\nfunction propertyNameToAttribute(propertyName) {\n let attribute = propertyNamesToAttributes[propertyName];\n if (!attribute) {\n // Convert and memoize.\n const uppercaseRegEx = /([A-Z])/g;\n attribute = propertyName.replace(uppercaseRegEx, '-$1').toLowerCase();\n }\n return attribute;\n}\n","/* Exported function extends a base class with ClickSelection. */\nexport default (base) => {\n\n /**\n * Mixin which maps a click (actually, a mousedown) to a selection.\n *\n * This simple mixin is useful in list box-like elements, where a click on a\n * list item implicitly selects it.\n *\n * This mixin expects the component to provide an `items` property. You can\n * provide that property yourself, or use\n * [ContentItemsMixin](ContentItemsMixin.md). This mixin also expects the\n * component to define a `selectedIndex` property. You can provide that\n * yourself, or use [SingleSelectionMixin](SingleSelectionMixin.md).\n */\n class ClickSelection extends base {\n\n constructor() {\n super();\n /*\n * REVIEW: Which event should we listen to here?\n *\n * The standard use for this mixin is in list boxes. List boxes don't\n * appear to be consistent with regard to whether they select on mousedown\n * or click/mouseup.\n */\n this.addEventListener('mousedown', event => {\n // HACK: If the item is a button, the event seems to be raised in\n // phase 2 (AT_TARGET), but the target is the component, not item.\n // Need to invesigate.\n const target = event.target === this ?\n event.path[0] :\n event.target;\n const index = indexOfContainingItem(this, target);\n if (index >= 0) {\n this.selectedIndex = index;\n // Note: We don't call preventDefault here. The default behavior for\n // mousedown includes setting keyboard focus if the element doesn't\n // already have the focus, and we want to preserve that behavior.\n event.stopPropagation();\n }\n });\n }\n\n // Default implementation. This will typically be handled by other mixins.\n get selectedIndex() {\n return super.selectedIndex;\n }\n set selectedIndex(index) {\n if ('selectedIndex' in base.prototype) { super.selectedIndex = index; }\n }\n\n }\n\n return ClickSelection;\n};\n\n\n/*\n * Return index of the element items that either is or contains the indicated\n * target. Return -1 if not found.\n */\nfunction indexOfContainingItem(element, target) {\n const items = element.items;\n const itemCount = items ? items.length : 0;\n for (let i = 0; i < itemCount; i++) {\n let item = items[i];\n if (item === target || item.contains(target)) {\n return i;\n }\n }\n return -1;\n}\n","/* Exported function extends a base class with Composable. */\nexport default (base) => {\n\n /**\n * Mixin to make a class more easily composable with other mixins.\n *\n * This mixin contributes a `compose` method that applies a set of mixin\n * functions and returns the resulting new class. This sugar can make the\n * application of many mixins at once easier to read.\n */\n class Composable extends base {\n\n /**\n * Apply a set of mixin functions or mixin objects to the present class and\n * return the new class.\n *\n * Instead of writing:\n *\n * let MyClass = Mixin1(Mixin2(Mixin3(Mixin4(Mixin5(BaseClass)))));\n *\n * You can write:\n *\n * let MyClass = ComposableMixin(BaseClass).compose(\n * Mixin1,\n * Mixin2,\n * Mixin3,\n * Mixin4,\n * Mixin5\n * );\n *\n * This function can also take mixin objects. A mixin object is just a\n * shorthand for a mixin function that creates a new subclass with the given\n * members. The mixin object's members are *not* copied directly onto the\n * prototype of the base class, as with traditional mixins.\n *\n * In addition to providing syntactic sugar, this mixin can be used to\n * define a class in ES5, which lacks ES6's `class` keyword.\n *\n * @param {...mixins} mixins - A set of mixin functions or objects to apply.\n */\n static compose(...mixins) {\n // We create a new subclass for each mixin in turn. The result becomes\n // the base class extended by any subsequent mixins. It turns out that\n // we can use Array.reduce() to concisely express this, using the current\n // object as the seed for reduce().\n return mixins.reduce(composeClass, this);\n }\n\n }\n\n return Composable;\n};\n\n\n// Properties defined by Object that we don't want to mixin.\nconst NON_MIXABLE_OBJECT_PROPERTIES = [\n 'constructor'\n];\n\n/*\n * Apply the mixin to the given base class to return a new class.\n * The mixin can either be a function that returns the modified class, or a\n * plain object whose members will be copied to the new class' prototype.\n */\nfunction composeClass(base, mixin) {\n if (typeof mixin === 'function') {\n // Mixin function\n return mixin(base);\n } else {\n // Mixin object\n class Subclass extends base {}\n copyOwnProperties(mixin, Subclass.prototype, NON_MIXABLE_OBJECT_PROPERTIES);\n return Subclass;\n }\n}\n\n\n/*\n * Copy the given properties/methods to the target.\n * Return the updated target.\n */\nfunction copyOwnProperties(source, target, ignorePropertyNames = []) {\n Object.getOwnPropertyNames(source).forEach(name => {\n if (ignorePropertyNames.indexOf(name) < 0) {\n const descriptor = Object.getOwnPropertyDescriptor(source, name);\n Object.defineProperty(target, name, descriptor);\n }\n });\n return target;\n}\n","import createSymbol from './createSymbol';\nimport toggleClass from './toggleClass';\nimport symbols from './symbols';\n\n\n// Symbols for private data members on an element.\nconst itemsSymbol = createSymbol('items');\nconst itemInitializedSymbol = createSymbol('itemInitialized');\n\n\n/* Exported function extends a base class with ContentItems. */\nexport default (base) => {\n\n /**\n * Mixin which maps content semantics (elements) to list item semantics.\n *\n * Items differ from element contents in several ways:\n *\n * * They are often referenced via index.\n * * They may have a selection state.\n * * It's common to do work to initialize the appearance or state of a new\n * item.\n * * Auxiliary invisible child elements are filtered out and not counted as\n * items. Auxiliary elements include link, script, style, and template\n * elements. This filtering ensures that those auxiliary elements can be\n * used in markup inside of a list without being treated as list items.\n *\n * This mixin expects a component to provide a `content` property returning a\n * raw set of elements. You can provide that yourself, or use\n * [DistributedChildrenContentMixin](DistributedChildrenContentMixin.md).\n *\n * The most commonly referenced property defined by this mixin is the `items`\n * property. To avoid having to do work each time that property is requested,\n * this mixin supports an optimized mode. If you invoke the `contentChanged`\n * method when the set of items changes, the mixin concludes that you'll take\n * care of notifying it of future changes, and turns on the optimization. With\n * that on, the mixin saves a reference to the computed set of items, and will\n * return that immediately on subsequent calls to the `items` property. If you\n * use this mixin in conjunction with\n * [DistributedChildrenContentMixin](DistributedChildrenContentMixin.md), the\n * `contentChanged` method will be invoked for you when the element's children\n * change, turning on the optimization automatically.\n */\n class ContentItems extends base {\n\n contentChanged() {\n if (super.contentChanged) { super.contentChanged(); }\n\n // Since we got the contentChanged call, we'll assume we'll be notified if\n // the set of items changes later. We turn on memoization of the items\n // property by setting our internal property to null (instead of\n // undefined).\n this[itemsSymbol] = null;\n\n this[symbols.itemsChanged]();\n }\n\n /**\n * This method is invoked whenever a new item is added to the list.\n *\n * The default implementation of this method does nothing. You can override\n * this to perform per-item initialization.\n *\n * @param {HTMLElement} item - The item that was added.\n */\n [symbols.itemAdded](item) {\n if (super[symbols.itemAdded]) { super[symbols.itemAdded](item); }\n }\n\n /**\n * The selection state for a single item has changed.\n *\n * Invoke this method to signal that the selected state of the indicated item\n * has changed. By default, this applies a `selected` CSS class if the item\n * is selected, and removed it if not selected.\n *\n * @param {HTMLElement} item - The item whose selection state has changed.\n * @param {boolean} selected - True if the item is selected, false if not.\n */\n [symbols.itemSelected](item, selected) {\n if (super[symbols.itemSelected]) { super[symbols.itemSelected](item, selected); }\n toggleClass(item, 'selected', selected);\n }\n\n /**\n * The current set of items in the list. See the top-level documentation for\n * mixin for a description of how items differ from plain content.\n *\n * @type {HTMLElement[]}\n */\n get items() {\n let items;\n if (this[itemsSymbol] == null) {\n items = filterAuxiliaryElements(this.content);\n // Note: test for *equality* with null; don't treat undefined as a match.\n if (this[itemsSymbol] === null) {\n // Memoize the set of items.\n this[itemsSymbol] = items;\n }\n } else {\n // Return the memoized items.\n items = this[itemsSymbol];\n }\n return items;\n }\n\n /**\n * This method is invoked when the underlying contents change. It is also\n * invoked on component initialization – since the items have \"changed\" from\n * being nothing.\n */\n [symbols.itemsChanged]() {\n if (super[symbols.itemsChanged]) { super[symbols.itemsChanged](); }\n\n // Perform per-item initialization.\n Array.prototype.forEach.call(this.items, item => {\n if (!item[itemInitializedSymbol]) {\n this[symbols.itemAdded](item);\n item[itemInitializedSymbol] = true;\n }\n });\n\n this.dispatchEvent(new CustomEvent('items-changed'));\n }\n\n /**\n * Fires when the items in the list change.\n *\n * @memberof ContentItems\n * @event items-changed\n */\n }\n\n return ContentItems;\n};\n\n\n// Return the given elements, filtering out auxiliary elements that aren't\n// typically visible. Items which are not elements are returned as is.\nfunction filterAuxiliaryElements(items) {\n const auxiliaryTags = [\n 'link',\n 'script',\n 'style',\n 'template'\n ];\n return [].filter.call(items, function(item) {\n return !item.localName || auxiliaryTags.indexOf(item.localName) < 0;\n });\n}\n","import symbols from './symbols';\n\n\n/* Exported function extends a base class with DirectionSelection. */\nexport default (base) => {\n\n /**\n * Mixin which maps direction semantics (goLeft, goRight, etc.) to selection\n * semantics (selectPrevious, selectNext, etc.).\n *\n * This mixin can be used in conjunction with\n * [KeyboardDirectionMixin](KeyboardDirectionMixin.md) (which maps keyboard\n * events to directions) and a mixin that handles selection like\n * [SingleSelectionMixin](SingleSelectionMixin.md).\n */\n class DirectionSelection extends base {\n\n [symbols.goDown]() {\n if (super[symbols.goDown]) { super[symbols.goDown](); }\n return this.selectNext();\n }\n\n [symbols.goEnd]() {\n if (super[symbols.goEnd]) { super[symbols.goEnd](); }\n return this.selectLast();\n }\n\n [symbols.goLeft]() {\n if (super[symbols.goLeft]) { super[symbols.goLeft](); }\n return this.selectPrevious();\n }\n\n [symbols.goRight]() {\n if (super[symbols.goRight]) { super[symbols.goRight](); }\n return this.selectNext();\n }\n\n [symbols.goStart]() {\n if (super[symbols.goStart]) { super[symbols.goStart](); }\n return this.selectFirst();\n }\n\n [symbols.goUp]() {\n if (super[symbols.goUp]) { super[symbols.goUp](); }\n return this.selectPrevious();\n }\n\n // Default implementation. This will typically be handled by other mixins.\n get selectedFraction() {\n return super.selectedFraction;\n }\n set selectedFraction(value) {\n if ('selectedFraction' in base.prototype) { super.selectedFraction = value; }\n }\n\n // Default implementation. This will typically be handled by other mixins.\n selectFirst() {\n if (super.selectFirst) { return super.selectFirst(); }\n }\n\n // Default implementation. This will typically be handled by other mixins.\n selectLast() {\n if (super.selectLast) { return super.selectLast(); }\n }\n\n // Default implementation. This will typically be handled by other mixins.\n selectNext() {\n if (super.selectNext) { return super.selectNext(); }\n }\n\n // Default implementation. This will typically be handled by other mixins.\n selectPrevious() {\n if (super.selectPrevious) { return super.selectPrevious(); }\n }\n\n // Map drag travel fraction to selection fraction.\n get travelFraction() {\n return super.travelFraction;\n }\n set travelFraction(value) {\n if ('travelFraction' in base.prototype) { super.travelFraction = value; }\n this.selectedFraction = value;\n }\n\n }\n\n return DirectionSelection;\n};\n","import microtask from './microtask';\n\n\n/* Exported function extends a base class with DistributedChildrenContent. */\nexport default (base) => {\n\n /**\n * Mixin which defines a component's content as its children, expanding any\n * nodes distributed to the component's slots.\n *\n * This also provides notification of changes to a component's content. It\n * will invoke a `contentChanged` method when the component is first\n * instantiated, and whenever its distributed children change. This is an\n * easy way to satisfy the Gold Standard checklist item for monitoring\n * [Content Changes](https://github.com/webcomponents/gold-standard/wiki/Content-Changes).\n *\n * Example:\n *\n * ```\n * let base = DistributedChildrenContentMixin(DistributedChildrenMixin(HTMLElement));\n * class CountingElement extends base {\n *\n * constructor() {\n * super();\n * let root = this.attachShadow({ mode: 'open' });\n * root.innerHTML = ` `;\n * }\n *\n * contentChanged() {\n * // Count the component's children, both initially and when changed.\n * this.count = this.distributedChildren.length;\n * }\n *\n * }\n * ```\n *\n * Note that content change detection depends upon the element having at least\n * one `slot` element in its shadow subtree.\n *\n * This mixin is intended for use with the\n * [DistributedChildrenMixin](DistributedChildrenMixin.md). See that mixin for\n * a discussion of how that works. This DistributedChildrenContentMixin\n * provides an easy way of defining the \"content\" of a component as the\n * component's distributed children. That in turn lets mixins like\n * [ContentItemsMixin](ContentItemsMixin.md) manipulate the children as list\n * items.\n */\n class DistributedChildrenContent extends base {\n\n constructor() {\n super();\n\n if (this.shadowRoot) {\n // Listen to changes on all slots.\n const slots = this.shadowRoot.querySelectorAll('slot');\n slots.forEach(slot => slot.addEventListener('slotchange', event => {\n this.contentChanged();\n }));\n }\n\n // Make an initial call to contentChanged() so that the component can do\n // initialization that it normally does when content changes.\n //\n // This will invoke contentChanged() handlers in other mixins. In order\n // that those mixins have a chance to complete their own initialization,\n // we add the contentChanged() call to the microtask queue.\n microtask(() => this.contentChanged());\n }\n\n /**\n * Invoked when the contents of the component (including distributed\n * children) have changed.\n *\n * This method is also invoked when a component is first instantiated; the\n * contents have essentially \"changed\" from being nothing. This allows the\n * component to perform initial processing of its children.\n */\n contentChanged() {\n if (super.contentChanged) { super.contentChanged(); }\n const event = new CustomEvent('content-changed');\n this.dispatchEvent(event);\n }\n\n /**\n * The content of this component, defined to be the flattened array of\n * children distributed to the component.\n *\n * @type {HTMLElement[]}\n */\n get content() {\n const distributedChildren = this.distributedChildren;\n if (typeof distributedChildren === 'undefined') {\n console.warn(`DistributedChildrenContentMixin expects the component to define a \"distributedChildren\" property.`);\n }\n return distributedChildren;\n }\n set content(value) {\n if ('content' in base.prototype) { super.content = value; }\n // TODO: Set the children to the given value (which should be an array of\n // elements)?\n }\n\n /**\n * This event is raised when the component's contents (including distributed\n * children) have changed.\n *\n * @memberof DistributedChildrenContent\n * @event content-changed\n */\n }\n\n return DistributedChildrenContent;\n};\n","/* Exported function extends a base class with DistributedChildren. */\nexport default (base) => {\n\n /**\n * Mixin which defines helpers for accessing a component's distributed\n * children as a flattened array or string.\n *\n * The standard DOM API provides several ways of accessing child content:\n * `children`, `childNodes`, and `textContent`. None of these functions are\n * Shadow DOM aware. This mixin defines variations of those functions that\n * *are* Shadow DOM aware.\n *\n * Example: you create a component `` that displays a number\n * equal to the number of children placed inside that component. If someone\n * instantiates your component like:\n *\n * \n *
\n *
\n *
\n * \n *\n * Then the component should show \"3\", because there are three children. To\n * calculate the number of children, the component can just calculate\n * `this.children.length`. However, suppose someone instantiates your\n * component inside one of their own components, and puts a `` element\n * inside your component:\n *\n * \n * \n * \n *\n * If your component only looks at `this.children`, it will always see exactly\n * one child — the `` element. But the user looking at the page will\n * *see* any nodes distributed to that slot. To match what the user sees, your\n * component should expand any `` elements it contains.\n *\n * That is the problem this mixin solves. After applying this mixin, your\n * component code has access to `this.distributedChildren`, whose `length`\n * will return the total number of all children distributed to your component\n * in the composed tree.\n *\n * Note: The latest Custom Elements API design calls for a new function,\n * `getAssignedNodes` that takes an optional `deep` parameter, that will solve\n * this problem at the API level.\n */\n class DistributedChildren extends base {\n\n /**\n * An in-order collection of distributed children, expanding any slot\n * elements. Like the standard children property, this skips text nodes.\n *\n * @type {HTMLElement[]}\n */\n get distributedChildren() {\n return expandContentElements(this.children, false);\n }\n\n /**\n * An in-order collection of distributed child nodes, expanding any slot\n * elements. Like the standard childNodes property, this includes text\n * nodes.\n *\n * @type {Node[]}\n */\n get distributedChildNodes() {\n return expandContentElements(this.childNodes, true);\n }\n\n /**\n * The concatenated text content of all distributed child nodes, expanding\n * any slot elements.\n *\n * @type {string}\n */\n get distributedTextContent() {\n const strings = this.distributedChildNodes.map(function(child) {\n return child.textContent;\n });\n return strings.join('');\n }\n\n }\n\n return DistributedChildren;\n};\n\n\n/*\n * Given a array of nodes, return a new array with any content elements expanded\n * to the nodes distributed to that content element. This rule is applied\n * recursively.\n *\n * If includeTextNodes is true, text nodes will be included, as in the\n * standard childNodes property; by default, this skips text nodes, like the\n * standard children property.\n */\nfunction expandContentElements(nodes, includeTextNodes) {\n const expanded = Array.prototype.map.call(nodes, node => {\n // We want to see if the node is an instanceof HTMLSlotELement, but\n // that class won't exist if the browser that doesn't support native\n // Shadow DOM and if the Shadow DOM polyfill hasn't been loaded. Instead,\n // we do a simplistic check to see if the tag name is \"slot\".\n const isSlot = typeof HTMLSlotElement !== 'undefined' ?\n node instanceof HTMLSlotElement :\n node.localName === 'slot';\n if (isSlot) {\n // Use the nodes assigned to this node instead.\n const assignedNodes = node.assignedNodes({ flatten: true });\n return assignedNodes ?\n expandContentElements(assignedNodes, includeTextNodes) :\n [];\n } else if (node instanceof HTMLElement) {\n // Plain element; use as is.\n return [node];\n } else if (node instanceof Text && includeTextNodes) {\n // Text node.\n return [node];\n } else {\n // Comment, processing instruction, etc.; skip.\n return [];\n }\n });\n const flattened = [].concat(...expanded);\n return flattened;\n}\n","import createSymbol from './createSymbol';\nimport safeAttributes from './safeAttributes';\nimport symbols from './symbols';\n\n\n// Symbols for private data members on an element.\nconst genericSymbol = createSymbol('generic');\n\n\n/* Exported function extends a base class with Generic. */\nexport default (base) => {\n\n /**\n * Mixin which allows a component to support a \"generic\" style: a minimalist\n * style that can easily be removed to reset its visual appearance to a\n * baseline state.\n *\n * By default, a component should provide a minimal visual presentation that\n * allows the component to function. However, the more styling the component\n * provides by default, the harder it becomes to get the component to fit in\n * in other settings. Each CSS rule has to be overridden. Worse, new CSS rules\n * added to the default style won't be overridden by default, making it hard\n * to know whether a new version of a component will still look okay.\n *\n * As a compromise, the mixin defines a `generic` attribute. This attribute is\n * normally set by default, and styles can be written that apply only when the\n * generic attribute is set. This allows the construction of CSS rules that\n * will only apply to generic components like:\n *\n * :host([generic=\"\"]) {\n * ... generic appearance defined here ...\n * }\n *\n * This makes it easy to remove all default styling — set the `GenericMixin`\n * attribute to false, and all default styling will be removed.\n */\n class Generic extends base {\n\n constructor() {\n super();\n // Set defaults.\n if (typeof this.generic === 'undefined') {\n this.generic = this[symbols.defaults].generic;\n }\n }\n\n // This mixin doesn't actually respond to attribute changes, but relies\n // on separately-defined behavior (e.g., in AttributeMarshallingMixin) for that.\n // Still, we need define a baseline attributeChangedCallback that does\n // nothing, in case this mixin gets used on its own.\n attributeChangedCallback(name, oldValue, newValue) {\n if (super.attributeChangedCallback) { super.attributeChangedCallback(name, oldValue, newValue); }\n }\n\n connectedCallback() {\n if (super.connectedCallback) { super.connectedCallback(); }\n safeAttributes.connected(this);\n }\n\n get [symbols.defaults]() {\n const defaults = super[symbols.defaults] || {};\n defaults.generic = true;\n return defaults;\n }\n\n /**\n * True if the component would like to receive generic styling.\n *\n * This property is true by default — set it to false to turn off all\n * generic styles. This makes it easier to apply custom styling; you won't\n * have to explicitly override styling you don't want.\n *\n * @type Boolean\n * @default true\n */\n get generic() {\n return this[genericSymbol];\n }\n set generic(value) {\n const parsed = typeof value === 'string' ?\n String(value) !== 'false' :\n value;\n this[genericSymbol] = parsed;\n\n if ('generic' in base.prototype) { super.generic = value; }\n\n // We roll our own attribute setting so that an explicitly false value\n // shows up as GenericMixin=\"false\".\n if (parsed === false) {\n // Explicitly use false string.\n safeAttributes.setAttribute(this, 'generic', 'false');\n } else if (parsed == null) {\n // Explicitly remove attribute. (Always safe to do this.)\n this.removeAttribute('generic');\n } else {\n // Use the empty string to get attribute to appear with no value.\n safeAttributes.setAttribute(this, 'generic', '');\n }\n }\n\n }\n\n return Generic;\n};\n\n\n","import createSymbol from './createSymbol';\nimport symbols from './symbols';\n\n\n// Symbols for private data members on an element.\nconst navigationAxisSymbol = createSymbol('navigationAxis');\n\n\n/* Exported function extends a base class with KeyboardDirection. */\nexport default (base) => {\n\n /**\n * Mixin which maps direction keys (Left, Right, etc.) to direction semantics\n * (go left, go right, etc.).\n *\n * This mixin expects the component to invoke a `keydown` method when a key is\n * pressed. You can use [KeyboardMixin](KeyboardMixin.md) for that\n * purpose, or wire up your own keyboard handling and call `keydown` yourself.\n *\n * This mixin calls methods such as `goLeft` and `goRight`. You can define\n * what that means by implementing those methods yourself. If you want to use\n * direction keys to navigate a selection, use this mixin with\n * [DirectionSelectionMixin](DirectionSelectionMixin.md).\n */\n class KeyboardDirection extends base {\n\n constructor() {\n super();\n // Set defaults.\n if (typeof this.navigationAxis === 'undefined') {\n this.navigationAxis = this[symbols.defaults].navigationAxis;\n }\n }\n\n get [symbols.defaults]() {\n const defaults = super[symbols.defaults] || {};\n defaults.navigationAxis = 'both';\n return defaults;\n }\n\n /**\n * Invoked when the user wants to go/navigate down.\n * The default implementation of this method does nothing.\n */\n [symbols.goDown]() {\n if (super[symbols.goDown]) { return super[symbols.goDown](); }\n }\n\n /**\n * Invoked when the user wants to go/navigate to the end (e.g., of a list).\n * The default implementation of this method does nothing.\n */\n [symbols.goEnd]() {\n if (super[symbols.goEnd]) { return super[symbols.goEnd](); }\n }\n\n /**\n * Invoked when the user wants to go/navigate left.\n * The default implementation of this method does nothing.\n */\n [symbols.goLeft]() {\n if (super[symbols.goLeft]) { return super[symbols.goLeft](); }\n }\n\n /**\n * Invoked when the user wants to go/navigate right.\n * The default implementation of this method does nothing.\n */\n [symbols.goRight]() {\n if (super[symbols.goRight]) { return super[symbols.goRight](); }\n }\n\n /**\n * Invoked when the user wants to go/navigate to the start (e.g., of a\n * list). The default implementation of this method does nothing.\n */\n [symbols.goStart]() {\n if (super[symbols.goStart]) { return super[symbols.goStart](); }\n }\n\n /**\n * Invoked when the user wants to go/navigate up.\n * The default implementation of this method does nothing.\n */\n [symbols.goUp]() {\n if (super[symbols.goUp]) { return super[symbols.goUp](); }\n }\n\n /**\n * Indicates the direction of permitted navigation with the keyboard.\n *\n * Accepted values are \"horizontal\", \"vertical\", or \"both\" (the default).\n * If this property is \"horizontal\", the Up Arrow and Down Arrow keys will\n * be ignored. Conversely, if this is \"vertical\", the Left Arrow and Right\n * Arrow keys will be ignored.\n *\n * @type {string}\n */\n get navigationAxis() {\n return this[navigationAxisSymbol];\n }\n set navigationAxis(value) {\n this[navigationAxisSymbol] = value;\n if ('navigationAxis' in base.prototype) { super.navigationAxis = value; }\n }\n\n [symbols.keydown](event) {\n let handled;\n\n const axis = this.navigationAxis;\n const horizontal = (axis === 'horizontal' || axis === 'both');\n const vertical = (axis === 'vertical' || axis === 'both');\n\n // Ignore Left/Right keys when metaKey or altKey modifier is also pressed,\n // as the user may be trying to navigate back or forward in the browser.\n switch (event.keyCode) {\n case 35: // End\n handled = this[symbols.goEnd]();\n break;\n case 36: // Home\n handled = this[symbols.goStart]();\n break;\n case 37: // Left\n if (horizontal && !event.metaKey && !event.altKey) {\n handled = this[symbols.goLeft]();\n }\n break;\n case 38: // Up\n if (vertical) {\n handled = event.altKey ? this[symbols.goStart]() : this[symbols.goUp]();\n }\n break;\n case 39: // Right\n if (horizontal && !event.metaKey && !event.altKey) {\n handled = this[symbols.goRight]();\n }\n break;\n case 40: // Down\n if (vertical) {\n handled = event.altKey ? this[symbols.goEnd]() : this[symbols.goDown]();\n }\n break;\n }\n // Prefer mixin result if it's defined, otherwise use base result.\n return handled || (super[symbols.keydown] && super[symbols.keydown](event));\n }\n\n }\n\n return KeyboardDirection;\n};\n","import symbols from './symbols';\n\n\n/* Exported function extends a base class with Keyboard. */\nexport default (base) => {\n\n /**\n * Mixin which manages the keydown handling for a component.\n *\n * This mixin handles several keyboard-related features.\n *\n * First, it wires up a single keydown event handler that can be shared by\n * multiple mixins on a component. The event handler will invoke a `keydown`\n * method with the event object, and any mixin along the prototype chain that\n * wants to handle that method can do so.\n *\n * If a mixin wants to indicate that keyboard event has been handled, and that\n * other mixins should *not* handle it, the mixin's `keydown` handler should\n * return a value of true. The convention that seems to work well is that a\n * mixin should see if it wants to handle the event and, if not, then ask the\n * superclass to see if it wants to handle the event. This has the effect of\n * giving the mixin that was applied last the first chance at handling a\n * keyboard event.\n *\n * Example:\n *\n * [symbols.keydown](event) {\n * let handled;\n * switch (event.keyCode) {\n * // Handle the keys you want, setting handled = true if appropriate.\n * }\n * // Prefer mixin result if it's defined, otherwise use base result.\n * return handled || (super[symbols.keydown] && super[symbols.keydown](event));\n * }\n *\n * A second feature provided by this mixin is that it implicitly makes the\n * component a tab stop if it isn't already, by setting `tabIndex` to 0. This\n * has the effect of adding the component to the tab order in document order.\n */\n class Keyboard extends base {\n\n constructor() {\n super();\n this.addEventListener('keydown', event => {\n const handled = this[symbols.keydown](event);\n if (handled) {\n event.preventDefault();\n event.stopPropagation();\n }\n });\n }\n\n connectedCallback() {\n if (super.connectedCallback) { super.connectedCallback(); }\n if (this.getAttribute('tabindex') == null && this[symbols.defaults].tabindex !== null) {\n this.setAttribute('tabindex', this[symbols.defaults].tabindex);\n }\n }\n\n get [symbols.defaults]() {\n const defaults = super[symbols.defaults] || {};\n // The default tab index is 0 (document order).\n defaults.tabindex = 0;\n return defaults;\n }\n\n /**\n * Handle the indicated keyboard event.\n *\n * The default implementation of this method does nothing. This will\n * typically be handled by other mixins.\n *\n * @param {KeyboardEvent} event - the keyboard event\n * @return {boolean} true if the event was handled\n */\n [symbols.keydown](event) {\n if (super[symbols.keydown]) { return super[symbols.keydown](event); }\n }\n\n }\n\n return Keyboard;\n};\n","import symbols from './symbols';\n\n\n/* Exported function extends a base class with KeyboardPagedSelection. */\nexport default (base) => {\n\n /**\n * Mixin which maps page keys (Page Up, Page Down) into operations that move\n * the selection by one page.\n *\n * The keyboard interaction model generally follows that of Microsoft Windows'\n * list boxes instead of those in OS X:\n *\n * * The Page Up/Down and Home/End keys actually change the selection, rather\n * than just scrolling. The former behavior seems more generally useful for\n * keyboard users.\n *\n * * Pressing Page Up/Down will change the selection to the topmost/bottommost\n * visible item if the selection is not already there. Thereafter, the key\n * will move the selection up/down by a page, and (per the above point) make\n * the selected item visible.\n *\n * To ensure the selected item is in view following use of Page Up/Down, use\n * the related [SelectionInViewMixin](SelectionInViewMixin.md).\n *\n * This mixin expects the component to invoke a `keydown` method when a key is\n * pressed. You can use [KeyboardMixin](KeyboardMixin.md) for that\n * purpose, or wire up your own keyboard handling and call `keydown` yourself.\n */\n class KeyboardPagedSelection extends base {\n\n [symbols.keydown](event) {\n let handled;\n switch (event.keyCode) {\n case 33: // Page Up\n handled = this.pageUp();\n break;\n case 34: // Page Down\n handled = this.pageDown();\n break;\n }\n // Prefer mixin result if it's defined, otherwise use base result.\n return handled || (super[symbols.keydown] && super[symbols.keydown](event));\n }\n\n /**\n * Scroll down one page.\n */\n pageDown() {\n if (super.pageDown) { super.pageDown(); }\n return scrollOnePage(this, true);\n }\n\n /**\n * Scroll up one page.\n */\n pageUp() {\n if (super.pageUp) { super.pageUp(); }\n return scrollOnePage(this, false);\n }\n\n /**\n * The element that should be scrolled with the Page Up/Down keys.\n * Default is the current element.\n *\n * @type {HTMLElement}\n */\n get scrollTarget() {\n // Prefer base result.\n return 'scrollTarget' in base.prototype ? super.scrollTarget : this;\n }\n set scrollTarget(element) {\n if ('scrollTarget' in base.prototype) { super.scrollTarget = element; }\n }\n }\n\n return KeyboardPagedSelection;\n};\n\n\n// Return the item whose content spans the given y position (relative to the\n// top of the list's scrolling client area), or null if not found.\n//\n// If downward is true, move down the list of items to find the first item\n// found at the given y position; if downward is false, move up the list of\n// items to find the last item at that position.\nfunction getIndexOfItemAtY(element, y, downward) {\n const items = element.items;\n const start = downward ? 0 : items.length - 1;\n const end = downward ? items.length : 0;\n const step = downward ? 1 : -1;\n const scrollTarget = element.scrollTarget;\n const topOfClientArea = scrollTarget.offsetTop + scrollTarget.clientTop;\n\n // Find the item spanning the indicated y coordinate.\n let item;\n let itemIndex = start;\n let itemTop;\n let found = false;\n while (itemIndex !== end) {\n item = items[itemIndex];\n itemTop = item.offsetTop - topOfClientArea;\n const itemBottom = itemTop + item.offsetHeight;\n if (itemTop <= y && itemBottom >= y) {\n // Item spans the indicated y coordinate.\n found = true;\n break;\n }\n itemIndex += step;\n }\n\n if (!found) {\n return null;\n }\n\n // We may have found an item whose padding spans the given y coordinate,\n // but whose content is actually above/below that point.\n // TODO: If the item has a border, then padding should be included in\n // considering a hit.\n const itemStyle = getComputedStyle(item);\n const itemPaddingTop = parseFloat(itemStyle.paddingTop);\n const itemPaddingBottom = parseFloat(itemStyle.paddingBottom);\n const contentTop = itemTop + item.clientTop + itemPaddingTop;\n const contentBottom = contentTop + item.clientHeight - itemPaddingTop - itemPaddingBottom;\n if (downward && contentTop <= y || !downward && contentBottom >= y) {\n // The indicated coordinate hits the actual item content.\n return itemIndex;\n }\n else {\n // The indicated coordinate falls within the item's padding. Back up to\n // the item below/above the item we found and return that.\n return itemIndex - step;\n }\n}\n\n// Move by one page downward (if downward is true), or upward (if false).\n// Return true if we ended up changing the selection, false if not.\n// TODO: Better support for horizontal lists.\nfunction scrollOnePage(element, downward) {\n\n // Determine the item visible just at the edge of direction we're heading.\n // We'll select that item if it's not already selected.\n const scrollTarget = element.scrollTarget;\n const edge = scrollTarget.scrollTop + (downward ? scrollTarget.clientHeight : 0);\n const indexOfItemAtEdge = getIndexOfItemAtY(element, edge, downward);\n\n const selectedIndex = element.selectedIndex;\n let newIndex;\n if (indexOfItemAtEdge && selectedIndex === indexOfItemAtEdge) {\n // The item at the edge was already selected, so scroll in the indicated\n // direction by one page. Leave the new item at that edge selected.\n const delta = (downward ? 1 : -1) * scrollTarget.clientHeight;\n newIndex = getIndexOfItemAtY(element, edge + delta, downward);\n }\n else {\n // The item at the edge wasn't selected yet. Instead of scrolling, we'll\n // just select that item. That is, the first attempt to page up/down\n // usually just moves the selection to the edge in that direction.\n newIndex = indexOfItemAtEdge;\n }\n\n if (!newIndex) {\n // We can't find an item in the direction we want to travel. Select the\n // last item (if moving downward) or first item (if moving upward).\n newIndex = (downward ? element.items.length - 1 : 0);\n }\n\n if (newIndex !== selectedIndex) {\n element.selectedIndex = newIndex;\n return true; // We handled the page up/down ourselves.\n }\n else {\n return false; // We didn't do anything.\n }\n}\n","import createSymbol from './createSymbol';\nimport symbols from './symbols';\n\n\n// Symbols for private data members on an element.\nconst itemTextContentsSymbol = createSymbol('itemTextContents');\nconst typedPrefixSymbol = createSymbol('typedPrefix');\nconst prefixTimeoutSymbol = createSymbol('prefixTimeout');\n\n\n/* Exported function extends a base class with KeyboardPrefixSelection. */\nexport default (base) => {\n\n /**\n * Mixin that handles list box-style prefix typing, in which the user can type\n * a string to select the first item that begins with that string.\n *\n * Example: suppose a component using this mixin has the following items:\n *\n * \n * Apple
\n * Apricot
\n * Banana
\n * Blackberry
\n * Blueberry
\n * Cantaloupe
\n * Cherry
\n * Lemon
\n * Lime
\n * \n *\n * If this component receives the focus, and the user presses the \"b\" or \"B\"\n * key, the \"Banana\" item will be selected, because it's the first item that\n * matches the prefix \"b\". (Matching is case-insensitive.) If the user now\n * presses the \"l\" or \"L\" key quickly, the prefix to match becomes \"bl\", so\n * \"Blackberry\" will be selected.\n *\n * The prefix typing feature has a one second timeout — the prefix to match\n * will be reset after a second has passed since the user last typed a key.\n * If, in the above example, the user waits a second between typing \"b\" and\n * \"l\", the prefix will become \"l\", so \"Lemon\" would be selected.\n *\n * This mixin expects the component to invoke a `keydown` method when a key is\n * pressed. You can use [KeyboardMixin](KeyboardMixin.md) for that\n * purpose, or wire up your own keyboard handling and call `keydown` yourself.\n *\n * This mixin also expects the component to provide an `items` property. The\n * `textContent` of those items will be used for purposes of prefix matching.\n */\n class KeyboardPrefixSelection extends base {\n\n // TODO: If the set of items is changed, reset the prefix.\n // [symbols.itemsChanged]() {\n // this[itemTextContentsSymbol] = null;\n // resetTypedPrefix(this);\n // }\n\n // TODO: If the selection is changed by some other means (e.g., arrow keys)\n // other than prefix typing, then that act should reset the prefix.\n\n [symbols.keydown](event) {\n let handled;\n let resetPrefix = true;\n\n switch (event.keyCode) {\n case 8: // Backspace\n handleBackspace(this);\n handled = true;\n resetPrefix = false;\n break;\n case 27: // Escape\n handled = true;\n break;\n default:\n if (!event.ctrlKey && !event.metaKey && !event.altKey &&\n event.which !== 32 /* Space */) {\n handlePlainCharacter(this, String.fromCharCode(event.which));\n }\n resetPrefix = false;\n }\n\n if (resetPrefix) {\n resetTypedPrefix(this);\n }\n\n // Prefer mixin result if it's defined, otherwise use base result.\n return handled || (super[symbols.keydown] && super[symbols.keydown](event));\n }\n\n /**\n * Select the first item whose text content begins with the given prefix.\n *\n * @param prefix [String] The prefix string to search for\n */\n selectItemWithTextPrefix(prefix) {\n if (super.selectItemWithTextPrefix) { super.selectItemWithTextPrefix(prefix); }\n if (prefix == null || prefix.length === 0) {\n return;\n }\n const index = getIndexOfItemWithTextPrefix(this, prefix);\n if (index >= 0) {\n this.selectedIndex = index;\n }\n }\n\n }\n\n return KeyboardPrefixSelection;\n};\n\n\n// Time in milliseconds after which the user is considered to have stopped\n// typing.\nconst PREFIX_TIMEOUT_DURATION = 1000;\n\n\n// Return the index of the first item with the given prefix, else -1.\nfunction getIndexOfItemWithTextPrefix(element, prefix) {\n const itemTextContents = getItemTextContents(element);\n const prefixLength = prefix.length;\n for (let i = 0; i < itemTextContents.length; i++) {\n const itemTextContent = itemTextContents[i];\n if (itemTextContent.substr(0, prefixLength) === prefix) {\n return i;\n }\n }\n return -1;\n}\n\n// Return an array of the text content (in lowercase) of all items.\n// Cache these results.\nfunction getItemTextContents(element) {\n if (!element[itemTextContentsSymbol]) {\n const items = element.items;\n element[itemTextContentsSymbol] = items.map(child => {\n const text = child.textContent || child.alt;\n return text.toLowerCase();\n });\n }\n return element[itemTextContentsSymbol];\n}\n\nfunction handleBackspace(element) {\n const length = element[typedPrefixSymbol] ? element[typedPrefixSymbol].length : 0;\n if (length > 0) {\n element[typedPrefixSymbol] = element[typedPrefixSymbol].substr(0, length - 1);\n }\n element.selectItemWithTextPrefix(element[typedPrefixSymbol]);\n setPrefixTimeout(element);\n}\n\nfunction handlePlainCharacter(element, char) {\n const prefix = element[typedPrefixSymbol] || '';\n element[typedPrefixSymbol] = prefix + char.toLowerCase();\n element.selectItemWithTextPrefix(element[typedPrefixSymbol]);\n setPrefixTimeout(element);\n}\n\nfunction resetPrefixTimeout(element) {\n if (element[prefixTimeoutSymbol]) {\n clearTimeout(element[prefixTimeoutSymbol]);\n element[prefixTimeoutSymbol] = false;\n }\n}\n\nfunction resetTypedPrefix(element) {\n element[typedPrefixSymbol] = '';\n resetPrefixTimeout(element);\n}\n\nfunction setPrefixTimeout(element) {\n resetPrefixTimeout(element);\n element[prefixTimeoutSymbol] = setTimeout(() => {\n resetTypedPrefix(element);\n }, PREFIX_TIMEOUT_DURATION);\n}\n","/* Exported function extends a base class with SelectedItemTextValue. */\nexport default (base) => {\n\n /**\n * Mixin which defines a `value` property that reflects the text content of a\n * selected item.\n *\n * This mixin exists for list-like components that want to provide a more\n * convenient way to get/set the selected item using text.\n *\n * This mixin expects a component to provide an `items` array of all elements\n * in the list. A standard way to do that with is\n * [ContentItemsMixin](ContentItemsMixin.md). This also expects the definition\n * of `selectedIndex` and `selectedItem` properties, which can be obtained\n * from [SingleSelectionMixin](SingleSelectionMixin.md).\n */\n class SelectedItemTextValue extends base {\n\n /**\n * The text content of the selected item.\n *\n * Setting this value to a string will attempt to select the first list item\n * whose text content match that string. Setting this to a string not matching\n * any list item will result in no selection.\n *\n * @type {string}\n */\n get value() {\n return this.selectedItem == null || this.selectedItem.textContent == null ?\n '' :\n this.selectedItem.textContent;\n }\n set value(text) {\n\n const currentIndex = this.selectedIndex;\n let newIndex = -1; // Assume we won't find the text.\n\n // Find the item with the indicated text.\n const items = this.items;\n for (let i = 0, length = items.length; i < length; i++) {\n if (items[i].textContent === text) {\n newIndex = i;\n break;\n }\n }\n\n if (newIndex !== currentIndex) {\n this.selectedIndex = newIndex;\n const event = new CustomEvent('value-changed');\n this.dispatchEvent(event);\n }\n }\n }\n\n return SelectedItemTextValue;\n};\n","import symbols from './symbols';\n\n\n// Used to assign unique IDs to item elements without IDs.\nlet idCount = 0;\n\n\n/* Exported function extends a base class with SelectionAriaActive. */\nexport default (base) => {\n\n /**\n * Mixin which treats the selected item in a list as the active item in ARIA\n * accessibility terms.\n *\n * Handling ARIA selection state properly is actually quite complex:\n *\n * * The items in the list need to be indicated as possible items via an ARIA\n * `role` attribute value such as \"option\".\n * * The selected item need to be marked as selected by setting the item's\n * `aria-selected` attribute to true *and* the other items need be marked as\n * *not* selected by setting `aria-selected` to false.\n * * The outermost element with the keyboard focus needs to have attributes\n * set on it so that the selection is knowable at the list level via the\n * `aria-activedescendant` attribute.\n * * Use of `aria-activedescendant` in turn requires that all items in the\n * list have ID attributes assigned to them.\n *\n * This mixin tries to address all of the above requirements. To that end,\n * this mixin will assign generated IDs to any item that doesn't already have\n * an ID.\n *\n * ARIA relies on elements to provide `role` attributes. This mixin will apply\n * a default role of \"listbox\" on the outer list if it doesn't already have an\n * explicit role. Similarly, this mixin will apply a default role of \"option\"\n * to any list item that does not already have a role specified.\n *\n * This mixin expects a set of members that manage the state of the selection:\n * `[symbols.itemSelected]`, `itemAdded`, and `selectedIndex`. You can\n * supply these yourself, or do so via\n * [SingleSelectionMixin](SingleSelectionMixin.md).\n */\n class SelectionAriaActive extends base {\n\n connectedCallback() {\n if (super.connectedCallback) { super.connectedCallback(); }\n // Set default ARIA role.\n if (this.getAttribute('role') == null && this[symbols.defaults].role) {\n this.setAttribute('role', this[symbols.defaults].role);\n }\n }\n\n get [symbols.defaults]() {\n const defaults = super[symbols.defaults] || {};\n defaults.role = 'listbox';\n return defaults;\n }\n\n [symbols.itemAdded](item) {\n if (super[symbols.itemAdded]) { super[symbols.itemAdded](item); }\n\n if (!item.getAttribute('role')) {\n // Assign a default ARIA role.\n item.setAttribute('role', 'option');\n }\n\n // Ensure each item has an ID so we can set aria-activedescendant on the\n // overall list whenever the selection changes.\n //\n // The ID will take the form of a base ID plus a unique integer. The base\n // ID will be incorporate the component's own ID. E.g., if a component has\n // ID \"foo\", then its items will have IDs that look like \"_fooOption1\". If\n // the compnent has no ID itself, its items will get IDs that look like\n // \"_option1\". Item IDs are prefixed with an underscore to differentiate\n // them from manually-assigned IDs, and to minimize the potential for ID\n // conflicts.\n if (!item.id) {\n const baseId = this.id ?\n \"_\" + this.id + \"Option\" :\n \"_option\";\n item.id = baseId + idCount++;\n }\n }\n\n [symbols.itemSelected](item, selected) {\n if (super[symbols.itemSelected]) { super[symbols.itemSelected](item, selected); }\n item.setAttribute('aria-selected', selected);\n const itemId = item.id;\n if (itemId && selected) {\n this.setAttribute('aria-activedescendant', itemId);\n }\n }\n\n get selectedItem() {\n return super.selectedItem;\n }\n set selectedItem(item) {\n if ('selectedItem' in base.prototype) { super.selectedItem = item; }\n if (item == null) {\n // Selection was removed.\n this.removeAttribute('aria-activedescendant');\n }\n }\n\n }\n\n return SelectionAriaActive;\n};\n","import symbols from '../src/symbols';\n\n\n/* Exported function extends a base class with SelectionHighlight. */\nexport default (base) => {\n\n /**\n * Template mixin which applies standard highlight colors to a selected item.\n *\n * This mixin highlights textual items (e.g., in a list) in a standard way by\n * using the CSS `highlight` and `highlighttext` color values. These values\n * respect operating system defaults and user preferences, and hence are good\n * default values for highlight colors.\n *\n * This mixin expects a `selected` class to be applied to selected items. You\n * can use [ContentItemsMixin](ContentItemsMixin.md) for that purpose.\n */\n class SelectionHighlight extends base {\n\n get [symbols.template]() {\n const baseTemplate = super[symbols.template] || '';\n return `\n \n ${baseTemplate}\n `;\n }\n\n }\n\n return SelectionHighlight;\n};\n","/* Exported function extends a base class with SelectionInView. */\nexport default (base) => {\n\n /**\n * Mixin which scrolls a container to ensure that a newly-selected item is\n * visible to the user.\n *\n * When the selected item in a list-like component changes, it's easier for\n * the to confirm that the selection has changed to an appropriate item if the\n * user can actually see that item.\n *\n * This mixin expects a `selectedItem` property to be set when the selection\n * changes. You can supply that yourself, or use\n * [SingleSelectionMixin](SingleSelectionMixin.md).\n */\n class SelectionInView extends base {\n\n connectedCallback() {\n if (super.connectedCallback) { super.connectedCallback(); }\n const selectedItem = this.selectedItem;\n if (selectedItem) {\n this.scrollItemIntoView(selectedItem);\n }\n }\n\n get selectedItem() {\n return super.selectedItem;\n }\n set selectedItem(item) {\n if ('selectedItem' in base.prototype) { super.selectedItem = item; }\n if (item) {\n // Keep the selected item in view.\n this.scrollItemIntoView(item);\n }\n }\n\n /**\n * Scroll the given element completely into view, minimizing the degree of\n * scrolling performed.\n *\n * Blink has a `scrollIntoViewIfNeeded()` function that does something\n * similar, but unfortunately it's non-standard, and in any event often ends\n * up scrolling more than is absolutely necessary.\n *\n * @param {HTMLElement} item - the item to scroll into view.\n */\n scrollItemIntoView(item) {\n if (super.scrollItemIntoView) { super.scrollItemIntoView(); }\n // Get the relative position of the item with respect to the top of the\n // list's scrollable canvas. An item at the top of the list will have a\n // elementTop of 0.\n\n const scrollTarget = this.scrollTarget;\n const elementTop = item.offsetTop - scrollTarget.offsetTop - scrollTarget.clientTop;\n const elementBottom = elementTop + item.offsetHeight;\n // Determine the bottom of the scrollable canvas.\n const scrollBottom = scrollTarget.scrollTop + scrollTarget.clientHeight;\n if (elementBottom > scrollBottom) {\n // Scroll up until item is entirely visible.\n scrollTarget.scrollTop += elementBottom - scrollBottom;\n }\n else if (elementTop < scrollTarget.scrollTop) {\n // Scroll down until item is entirely visible.\n scrollTarget.scrollTop = elementTop;\n }\n }\n\n /**\n * The element that should be scrolled to bring an item into view.\n *\n * The default value of this property is the element itself.\n *\n * @type {HTMLElement}\n */\n get scrollTarget() {\n // Prefer base result.\n return 'scrollTarget' in base.prototype ? super.scrollTarget : this;\n }\n set scrollTarget(element) {\n if ('scrollTarget' in base.prototype) { super.scrollTarget = element; }\n }\n\n }\n\n return SelectionInView;\n};\n","/* Exported function extends a base class with ShadowElementReferences. */\nexport default (base) => {\n\n /**\n * Mixin to create references to elements in a component's Shadow DOM subtree.\n *\n * This adds a member on the component called `this.$` that can be used to\n * reference shadow elements with IDs. E.g., if component's shadow contains an\n * element ``, then this mixin will create a member\n * `this.$.foo` that points to that button.\n *\n * Such references simplify a component's access to its own elements. In\n * exchange, this mixin trades off a one-time cost of querying all elements in\n * the shadow tree instead of paying an ongoing cost to query for an element\n * each time the component wants to inspect or manipulate it.\n *\n * This mixin expects the component to define a Shadow DOM subtree. You can\n * create that tree yourself, or make use of\n * [ShadowTemplateMixin](ShadowTemplateMixin.md).\n *\n * This mixin is inspired by Polymer's [automatic\n * node finding](https://www.polymer-project.org/1.0/docs/devguide/local-dom.html#node-finding)\n * feature.\n */\n class ShadowElementReferences extends base {\n\n constructor() {\n super();\n if (this.shadowRoot) {\n // Look for elements in the shadow subtree that have id attributes.\n // An alternatively implementation of this mixin would be to just define\n // a this.$ getter that lazily does this search the first time someone\n // tries to access this.$. That might introduce some complexity – if the\n // the tree changed after it was first populated, the result of\n // searching for a node might be somewhat unpredictable.\n this.$ = {};\n const nodesWithIds = this.shadowRoot.querySelectorAll('[id]');\n [].forEach.call(nodesWithIds, node => {\n const id = node.getAttribute('id');\n this.$[id] = node;\n });\n }\n }\n\n /**\n * The collection of references to the elements with IDs in a component's\n * Shadow DOM subtree.\n *\n * @type {object}\n * @member $\n */\n }\n\n return ShadowElementReferences;\n};\n","import symbols from '../src/symbols';\n\n\n/* Exported function extends a base class with ShadowTemplate. */\nexport default (base) => {\n\n /**\n * Mixin for stamping a template into a Shadow DOM subtree upon component\n * instantiation.\n *\n * To use this mixin, define a `template` property as a string or HTML\n * `` element:\n *\n * class MyElement extends ShadowTemplateMixin(HTMLElement) {\n * get [symbols.template]() {\n * return `Hello, world .`;\n * }\n * }\n *\n * When your component class is instantiated, a shadow root will be created on\n * the instance, and the contents of the template will be cloned into the\n * shadow root. If your component does not define a `template` property, this\n * mixin has no effect.\n *\n * For the time being, this extension retains support for Shadow DOM v0. That\n * will eventually be deprecated as browsers (and the Shadow DOM polyfill)\n * implement Shadow DOM v1.\n */\n class ShadowTemplate extends base {\n\n /*\n * If the component defines a template, a shadow root will be created on the\n * component instance, and the template stamped into it.\n */\n constructor() {\n super();\n let template = this[symbols.template];\n // TODO: Save the processed template with the component's class prototype\n // so it doesn't need to be processed with every instantiation.\n if (template) {\n\n if (typeof template === 'string') {\n // Upgrade plain string to real template.\n template = createTemplateWithInnerHTML(template);\n }\n\n if (window.ShadowDOMPolyfill) {\n shimTemplateStyles(template, this.localName);\n }\n\n const root = this.attachShadow({ mode: 'open' });\n const clone = document.importNode(template.content, true);\n root.appendChild(clone);\n }\n }\n\n }\n\n return ShadowTemplate;\n};\n\n\n// Convert a plain string of HTML into a real template element.\nfunction createTemplateWithInnerHTML(innerHTML) {\n const template = document.createElement('template');\n // REVIEW: Is there an easier way to do this?\n // We'd like to just set innerHTML on the template content, but since it's\n // a DocumentFragment, that doesn't work.\n const div = document.createElement('div');\n div.innerHTML = innerHTML;\n while (div.childNodes.length > 0) {\n template.content.appendChild(div.childNodes[0]);\n }\n return template;\n}\n\n// Invoke basic style shimming with ShadowCSS.\nfunction shimTemplateStyles(template, tag) {\n window.WebComponents.ShadowCSS.shimStyling(template.content, tag);\n}\n","import createSymbol from './createSymbol';\nimport symbols from './symbols';\n\n\n// Symbols for private data members on an element.\nconst canSelectNextSymbol = createSymbol('canSelectNext');\nconst canSelectPreviousSymbol = createSymbol('canSelectPrevious');\nconst selectionRequiredSymbol = createSymbol('selectionRequired');\nconst selectionWrapsSymbol = createSymbol('selectionWraps');\n\n// We want to expose both selectedIndex and selectedItem as independent\n// properties but keep them in sync. This allows a component user to reference\n// the selection by whatever means is most natural for their situation.\n//\n// To efficiently keep these properties in sync, we track \"external\" and\n// \"internal\" references for each property:\n//\n// The external index or item is the one we report to the outside world when\n// asked for selection. When handling a change to index or item, we update the\n// external reference as soon as possible, so that if anyone immediately asks\n// for the current selection, they will receive a stable answer.\n//\n// The internal index or item tracks whichever index or item last received the\n// full set of processing. Processing includes raising a change event for the\n// new value. Once we've begun that processing, we store the new value as the\n// internal value to indicate we've handled it.\n//\nconst externalSelectedIndexSymbol = createSymbol('externalSelectedIndex');\nconst externalSelectedItemSymbol = createSymbol('externalSelectedItem');\nconst internalSelectedIndexSymbol = createSymbol('internalSelectedIndex');\nconst internalSelectedItemSymbol = createSymbol('internalSelectedItem');\n\n\n/* Exported function extends a base class with SingleSelection. */\nexport default (base) => {\n\n /**\n * Mixin which manages single-selection semantics for items in a list.\n *\n * This mixin expects a component to provide an `items` Array or NodeList of\n * all elements in the list. A standard way to do that with is the\n * [ContentItemsMixin](ContentItemsMixin.md), which takes a component's\n * content (typically its distributed children) as the set of list items; see\n * that mixin for details.\n *\n * This mixin tracks a single selected item in the list, and provides means to\n * get and set that state by item position (`selectedIndex`) or item identity\n * (`selectedItem`). The selection can be moved in the list via the methods\n * `selectFirst`, `selectLast`, `selectNext`, and `selectPrevious`.\n *\n * This mixin does not produce any user-visible effects to represent\n * selection. Other mixins, such as\n * [SelectionAriaActiveMixin](SelectionAriaActiveMixin.md),\n * [SelectionHighlightMixin](SelectionHighlightMixin.md) and\n * [SelectionInViewMixin](SelectionInViewMixin.md), modify the selected item\n * in common ways to let the user know a given item is selected or not\n * selected.\n */\n class SingleSelection extends base {\n\n constructor() {\n super();\n // Set defaults.\n if (typeof this.selectionRequired === 'undefined') {\n this.selectionRequired = this[symbols.defaults].selectionRequired;\n }\n if (typeof this.selectionWraps === 'undefined') {\n this.selectionWraps = this[symbols.defaults].selectionWraps;\n }\n }\n\n /**\n * True if the selection can be moved to the next item, false if not (the\n * selected item is the last item in the list).\n *\n * @type {boolean}\n */\n get canSelectNext() {\n return this[canSelectNextSymbol];\n }\n set canSelectNext(canSelectNext) {\n const previousCanSelectNext = this[canSelectNextSymbol];\n this[canSelectNextSymbol] = canSelectNext;\n if ('canSelectNext' in base.prototype) { super.canSelectNext = canSelectNext; }\n if (canSelectNext !== previousCanSelectNext) {\n this.dispatchEvent(new CustomEvent('can-select-next-changed'));\n }\n }\n\n /**\n * True if the selection can be moved to the previous item, false if not\n * (the selected item is the first one in the list).\n *\n * @type {boolean}\n */\n get canSelectPrevious() {\n return this[canSelectPreviousSymbol];\n }\n set canSelectPrevious(canSelectPrevious) {\n const previousCanSelectPrevious = this[canSelectPreviousSymbol];\n this[canSelectPreviousSymbol] = canSelectPrevious;\n if ('canSelectPrevious' in base.prototype) { super.canSelectPrevious = canSelectPrevious; }\n if (canSelectPrevious !== previousCanSelectPrevious) {\n this.dispatchEvent(new CustomEvent('can-select-previous-changed'));\n }\n }\n\n get [symbols.defaults]() {\n const defaults = super[symbols.defaults] || {};\n defaults.selectionRequired = false;\n defaults.selectionWraps = false;\n return defaults;\n }\n\n /**\n * Handle a new item being added to the list.\n *\n * The default implementation of this method simply sets the item's\n * selection state to false.\n *\n * @param {HTMLElement} item - the item being added\n */\n [symbols.itemAdded](item) {\n if (super[symbols.itemAdded]) { super[symbols.itemAdded](item); }\n this[symbols.itemSelected](item, item === this.selectedItem);\n }\n\n [symbols.itemsChanged]() {\n if (super[symbols.itemsChanged]) { super[symbols.itemsChanged](); }\n\n // In case selected item changed position or was removed.\n trackSelectedItem(this);\n\n // In case the change in items affected which navigations are possible.\n updatePossibleNavigations(this);\n }\n\n /**\n * Apply the indicate selection state to the item.\n *\n * The default implementation of this method does nothing. User-visible\n * effects will typically be handled by other mixins.\n *\n * @param {HTMLElement} item - the item being selected/deselected\n * @param {boolean} selected - true if the item is selected, false if not\n */\n [symbols.itemSelected](item, selected) {\n if (super[symbols.itemSelected]) { super[symbols.itemSelected](item, selected); }\n }\n\n /**\n * The index of the item which is currently selected.\n *\n * A `selectedIndex` of -1 indicates there is no selection. Setting this\n * property to -1 will remove any existing selection.\n *\n * @type {number}\n */\n get selectedIndex() {\n return this[externalSelectedIndexSymbol] != null ?\n this[externalSelectedIndexSymbol] :\n -1;\n }\n set selectedIndex(index) {\n // See notes at top about internal vs. external copies of this property.\n const previousSelectedIndex = this[internalSelectedIndexSymbol];\n let item;\n if (index !== this[externalSelectedIndexSymbol]) {\n // Store the new index and the corresponding item.\n const items = this.items;\n const hasItems = items && items.length > 0;\n if (!(hasItems && index >= 0 && index < items.length)) {\n index = -1; // No item at that index.\n }\n this[externalSelectedIndexSymbol] = index;\n item = hasItems && index >= 0 ? items[index] : null;\n this[externalSelectedItemSymbol] = item;\n } else {\n item = this[externalSelectedItemSymbol];\n }\n\n // Now let super do any work.\n if ('selectedIndex' in base.prototype) { super.selectedIndex = index; }\n\n if (index !== previousSelectedIndex) {\n // The selected index changed.\n this[internalSelectedIndexSymbol] = index;\n\n const event = new CustomEvent('selected-index-changed', {\n detail: {\n selectedIndex: index,\n value: index // for Polymer binding. TODO: Verify still necessary\n }\n });\n this.dispatchEvent(event);\n }\n\n if (this[internalSelectedItemSymbol] !== item) {\n // Update selectedItem property so it can have its own effects.\n this.selectedItem = item;\n }\n }\n\n /**\n * The currently selected item, or null if there is no selection.\n *\n * Setting this property to null deselects any currently-selected item.\n * Setting this property to an object that is not in the list has no effect.\n *\n * TODO: Even if selectionRequired, can still explicitly set selectedItem to null.\n * TODO: If selectionRequired, leave selection alone?\n *\n * @type {object}\n */\n get selectedItem() {\n return this[externalSelectedItemSymbol] || null;\n }\n set selectedItem(item) {\n // See notes at top about internal vs. external copies of this property.\n const previousSelectedItem = this[internalSelectedItemSymbol];\n let index;\n if (item !== this[externalSelectedItemSymbol]) {\n // Store item and look up corresponding index.\n const items = this.items;\n const hasItems = items && items.length > 0;\n index = hasItems ? Array.prototype.indexOf.call(items, item) : -1;\n this[externalSelectedIndexSymbol] = index;\n if (index < 0) {\n item = null; // The indicated item isn't actually in `items`.\n }\n this[externalSelectedItemSymbol] = item;\n } else {\n index = this[externalSelectedIndexSymbol];\n }\n\n // Now let super do any work.\n if ('selectedItem' in base.prototype) { super.selectedItem = item; }\n\n if (item !== previousSelectedItem) {\n // The selected item changed.\n this[internalSelectedItemSymbol] = item;\n\n if (previousSelectedItem) {\n // Update selection state of old item.\n this[symbols.itemSelected](previousSelectedItem, false);\n }\n if (item) {\n // Update selection state to new item.\n this[symbols.itemSelected](item, true);\n }\n\n updatePossibleNavigations(this);\n\n const event = new CustomEvent('selected-item-changed', {\n detail: {\n selectedItem: item,\n value: item // for Polymer binding\n }\n });\n this.dispatchEvent(event);\n }\n\n if (this[internalSelectedIndexSymbol] !== index) {\n // Update selectedIndex property so it can have its own effects.\n this.selectedIndex = index;\n }\n }\n\n /**\n * Select the first item in the list.\n */\n selectFirst() {\n if (super.selectFirst) { super.selectFirst(); }\n return selectIndex(this, 0);\n }\n\n /**\n * True if the list should always have a selection (if it has items).\n *\n * @type {boolean}\n * @default false\n */\n get selectionRequired() {\n return this[selectionRequiredSymbol];\n }\n set selectionRequired(selectionRequired) {\n this[selectionRequiredSymbol] = selectionRequired;\n if ('selectionRequired' in base.prototype) { super.selectionRequired = selectionRequired; }\n trackSelectedItem(this);\n }\n\n /**\n * True if selection navigations wrap from last to first, and vice versa.\n *\n * @type {boolean}\n * @default false\n */\n get selectionWraps() {\n return this[selectionWrapsSymbol];\n }\n set selectionWraps(value) {\n this[selectionWrapsSymbol] = String(value) === 'true';\n if ('selectionWraps' in base.prototype) { super.selectionWraps = value; }\n updatePossibleNavigations(this);\n }\n\n /**\n * Select the last item in the list.\n */\n selectLast() {\n if (super.selectLast) { super.selectLast(); }\n return selectIndex(this, this.items.length - 1);\n }\n\n /**\n * Select the next item in the list.\n */\n selectNext() {\n if (super.selectNext) { super.selectNext(); }\n return selectIndex(this, this.selectedIndex + 1);\n }\n\n /**\n * Select the previous item in the list.\n *\n * If the list has no selection, the last item will be selected.\n */\n selectPrevious() {\n if (super.selectPrevious) { super.selectPrevious(); }\n const newIndex = this.selectedIndex < 0 ?\n this.items.length - 1 : // No selection yet; select last item.\n this.selectedIndex - 1;\n return selectIndex(this, newIndex);\n }\n\n /**\n * Fires when the selectedItem property changes.\n *\n * @memberof SingleSelection\n * @event selected-item-changed\n * @param {HTMLElement} detail.selectedItem The new selected item.\n * @param {HTMLElement} detail.previousItem The previously selected item.\n */\n\n /**\n * Fires when the selectedIndex property changes.\n *\n * @memberof SingleSelection\n * @event selected-index-changed\n * @param {number} detail.selectedIndex The new selected index.\n */\n\n }\n\n return SingleSelection;\n};\n\n\n// Ensure the given index is within bounds, and select it if it's not already\n// selected.\nfunction selectIndex(element, index) {\n const count = element.items.length;\n\n const boundedIndex = (element.selectionWraps) ?\n // JavaScript mod doesn't handle negative numbers the way we want to wrap.\n // See http://stackoverflow.com/a/18618250/76472\n ((index % count) + count) % count :\n\n // Keep index within bounds of array.\n Math.max(Math.min(index, count - 1), 0);\n\n const previousIndex = element.selectedIndex;\n if (previousIndex !== boundedIndex) {\n element.selectedIndex = boundedIndex;\n return true;\n } else {\n return false;\n }\n}\n\n// Following a change in the set of items, or in the value of the\n// `selectionRequired` property, reacquire the selected item. If it's moved,\n// update `selectedIndex`. If it's been removed, and a selection is required,\n// try to select another item.\nfunction trackSelectedItem(element) {\n\n const items = element.items;\n const itemCount = items ? items.length : 0;\n\n const previousSelectedItem = element.selectedItem;\n if (!previousSelectedItem) {\n // No item was previously selected.\n if (element.selectionRequired) {\n // Select the first item by default.\n element.selectedIndex = 0;\n }\n } else if (itemCount === 0) {\n // We've lost the selection, and there's nothing left to select.\n element.selectedItem = null;\n } else {\n // Try to find the previously-selected item in the current set of items.\n const indexInCurrentItems = Array.prototype.indexOf.call(items, previousSelectedItem);\n const previousSelectedIndex = element.selectedIndex;\n if (indexInCurrentItems < 0) {\n // Previously-selected item was removed from the items.\n // Select the item at the same index (if it exists) or as close as possible.\n const newSelectedIndex = Math.min(previousSelectedIndex, itemCount - 1);\n // Select by item, since index may be the same, and we want to raise the\n // selected-item-changed event.\n element.selectedItem = items[newSelectedIndex];\n } else if (indexInCurrentItems !== previousSelectedIndex) {\n // Previously-selected item still there, but changed position.\n element.selectedIndex = indexInCurrentItems;\n }\n }\n}\n\n// Following a change in selection, report whether it's now possible to\n// go next/previous from the given index.\nfunction updatePossibleNavigations(element) {\n let canSelectNext;\n let canSelectPrevious;\n const items = element.items;\n if (items == null || items.length === 0) {\n // No items to select.\n canSelectNext = false;\n canSelectPrevious = false;\n } if (element.selectionWraps) {\n // Since there are items, can always go next/previous.\n canSelectNext = true;\n canSelectPrevious = true;\n } else {\n const index = element.selectedIndex;\n if (index < 0 && items.length > 0) {\n // Special case. If there are items but no selection, declare that it's\n // always possible to go next/previous to create a selection.\n canSelectNext = true;\n canSelectPrevious = true;\n } else {\n // Normal case: we have an index in a list that has items.\n canSelectPrevious = (index > 0);\n canSelectNext = (index < items.length - 1);\n }\n }\n if (element.canSelectNext !== canSelectNext) {\n element.canSelectNext = canSelectNext;\n }\n if (element.canSelectPrevious !== canSelectPrevious) {\n element.canSelectPrevious = canSelectPrevious;\n }\n}\n","/**\n * Helper function to create a symbol that can be used for associating private\n * data with an element.\n *\n * Mixins and component classes often want to associate private data with an\n * element instance, but JavaScript does not have direct support for true\n * private properties. One approach is to use the\n * [Symbol](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Symbol)\n * data type to set and retrieve data on an element.\n *\n * Unfortunately, the Symbol type is not available in Internet Explorer 11. The\n * `createSymbol` helper function exists as a workaround for IE 11. Rather than\n * returning a true Symbol, it simply returns an underscore-prefixed string.\n *\n * Usage:\n *\n * const fooSymbol = createSymbol('foo');\n *\n * class MyElement extends HTMLElement {\n * get foo() {\n * return this[fooSymbol];\n * }\n * set foo(value) {\n * this[fooSymbol] = value;\n * }\n * }\n *\n * In IE 11, this sample will \"hide\" data behind an instance property this._foo.\n * The use of the underscore is meant to reduce (not eliminate) the potential\n * for name conflicts, and discourage (not prevent) external access to this\n * data. In modern browsers, the above code will eliminate the potential of\n * naming conflicts, and better hide the data behind a real Symbol.\n *\n * @function createSymbol\n * @param {string} description - A string to identify the symbol when debugging\n */\nexport default function createSymbol(description) {\n return typeof Symbol === 'function' ?\n Symbol(description) :\n `_${description}`;\n}\n","/*\n * Microtask helper for IE 11.\n *\n * Executing a function as a microtask is trivial in browsers that support\n * promises, whose then() clauses use microtask timing. IE 11 doesn't support\n * promises, but does support MutationObservers, which are also executed as\n * microtasks. So this helper uses an MutationObserver to achieve microtask\n * timing.\n *\n * See https://jakearchibald.com/2015/tasks-microtasks-queues-and-schedules/\n *\n * Inspired by Polymer's async() function.\n */\n\n\n// The queue of pending callbacks to be executed as microtasks.\nconst callbacks = [];\n\n// Create an element that we will modify to force observable mutations.\nconst element = document.createTextNode('');\n\n// A monotonically-increasing value.\nlet counter = 0;\n\n\n/**\n * Add a callback to the microtask queue.\n *\n * This uses a MutationObserver so that it works on IE 11.\n *\n * NOTE: IE 11 may actually use timeout timing with MutationObservers. This\n * needs more investigation.\n *\n * @function microtask\n * @param {function} callback\n */\nexport default function microtask(callback) {\n callbacks.push(callback);\n // Force a mutation.\n element.textContent = ++counter;\n}\n\n\n// Execute any pending callbacks.\nfunction executeCallbacks() {\n while (callbacks.length > 0) {\n const callback = callbacks.shift();\n callback();\n }\n}\n\n\n// Create the observer.\nconst observer = new MutationObserver(executeCallbacks);\nobserver.observe(element, {\n characterData: true\n});\n","import createSymbol from './createSymbol';\nimport toggleClass from './toggleClass';\n\n\n// Symbols for private data members on an element.\nconst safeToSetAttributesSymbol = createSymbol('safeToSetAttributes');\nconst pendingAttributesSymbol = createSymbol('pendingAttributes');\nconst pendingClassesSymbol = createSymbol('pendingClasses');\n\n\n/**\n * Helper functions for updating attributes, including the `class` attribute.\n */\nexport default {\n\n /**\n * Perform any pending updates to attributes and classes.\n *\n * This writes any `setAttribute` or `toggleClass` values that were performed\n * before an element was attached to the document for the first time.\n *\n * This method should be called by mixins/components in their\n * `connectedCallback`. If mulitple mixins/components invoke this during the\n * same `connectedCallback`, only the first call will have any effect. The\n * subsequent calls will be harmless.\n *\n * @param {HTMLElement} element - The element being added to the document.\n */\n connected(element) {\n element[safeToSetAttributesSymbol] = true;\n\n // Set any pending attributes.\n if (element[pendingAttributesSymbol]) {\n for (let attribute in element[pendingAttributesSymbol]) {\n const value = element[pendingAttributesSymbol][attribute];\n setAttributeToElement(element, attribute, value);\n }\n element[pendingAttributesSymbol] = null;\n }\n\n // Set any pending classes.\n if (element[pendingClassesSymbol]) {\n for (let className in element[pendingClassesSymbol]) {\n const value = element[pendingClassesSymbol][className];\n toggleClass(element, className, value);\n }\n element[pendingClassesSymbol] = null;\n }\n },\n\n /**\n * Set/unset the attribute with the indicated name.\n *\n * This method exists primarily to handle the case where an element wants to\n * set a default property value that should be reflected as an attribute. An\n * important limitation of custom element consturctors is that they cannot\n * set attributes. A call to `setAttribute` during the constructor will\n * be deferred until the element is connected to the document.\n *\n * @param {string} attribute - The name of the *attribute* (not property) to set.\n * @param {object} value - The value to set. If null, the attribute will be removed.\n */\n setAttribute(element, attribute, value) {\n if (element[safeToSetAttributesSymbol]) {\n // Safe to set attributes immediately.\n setAttributeToElement(element, attribute, value);\n } else {\n // Defer setting attributes until the first time we're connected.\n if (!element[pendingAttributesSymbol]) {\n element[pendingAttributesSymbol] = {};\n }\n element[pendingAttributesSymbol][attribute] = value;\n }\n },\n\n /**\n * Set/unset the class with the indicated name.\n *\n * This method exists primarily to handle the case where an element wants to\n * set a default property value that should be reflected as as class. An\n * important limitation of custom element consturctors is that they cannot\n * set attributes, including the `class` attribute. A call to\n * `toggleClass` during the constructor will be deferred until the element\n * is connected to the document.\n *\n * @param {string} className - The name of the class to set.\n * @param {object} value - True to set the class, false to remove it.\n */\n toggleClass(element, className, value) {\n if (element[safeToSetAttributesSymbol]) {\n // Safe to set class immediately.\n toggleClass(element, className, value);\n } else {\n // Defer setting class until the first time we're connected.\n if (!element[pendingClassesSymbol]) {\n element[pendingClassesSymbol] = {};\n }\n element[pendingClassesSymbol][className] = value;\n }\n }\n\n};\n\n\n// Reflect the attribute to the given element.\n// If the value is null, remove the attribute.\nfunction setAttributeToElement(element, attributeName, value) {\n if (value === null || typeof value === 'undefined') {\n element.removeAttribute(attributeName);\n } else {\n const text = String(value);\n // Avoid recursive attributeChangedCallback calls.\n if (element.getAttribute(attributeName) !== text) {\n element.setAttribute(attributeName, value);\n }\n }\n}\n","import createSymbol from './createSymbol';\n\n/**\n * A collection of Symbol objects for standard component properties and methods.\n *\n * These Symbol objects are used to allow mixins and a component to internally\n * communicate, without exposing these properties and methods in the component's\n * public API.\n *\n * To use these Symbol objects in your own component, include this module and\n * then create a property or method whose key is the desired Symbol.\n *\n * import 'SingleSelectionMixin' from 'basic-component-mixins/src/SingleSelectionMixin';\n * import 'symbols' from 'basic-component-mixins/src/symbols';\n *\n * class MyElement extends SingleSelectionMixin(HTMLElement) {\n * [symbols.itemSelected](item, selected) {\n * // This will be invoked whenever an item is selected/deselected.\n * }\n * }\n *\n * @module symbols\n */\nconst symbols = {\n\n /**\n * Symbol for the `defaults` property.\n *\n * This property can be used to set or override defaults that will be applied\n * to a new component instance. When implementing this property, take care to\n * first acquire any defaults defined by the superclass. The standard idiom is\n * as follows:\n *\n * get [symbols.defaults]() {\n * const defaults = super[symbols.defaults] || {};\n * // Set or override default values here\n * defaults.customProperty = false;\n * return defaults;\n * }\n *\n * @var {object} defaults\n */\n defaults: createSymbol('defaults'),\n\n /**\n * Symbol for the `dragging` property.\n *\n * Components like carousels often define animated CSS transitions for\n * sliding effects. Such a transition should usually *not* be applied while\n * the user is dragging, because a CSS animation will introduce a lag that\n * makes the swipe feel sluggish. Instead, as long as the user is dragging\n * with their finger down, the transition should be suppressed. When the\n * user releases their finger, the transition can be restored, allowing the\n * animation to show the carousel sliding into its final position.\n *\n * @type {boolean} true if a drag is in progress, false if not.\n */\n dragging: createSymbol('dragging'),\n\n /**\n * Symbol for the `goDown` method.\n *\n * This method is invoked when the user wants to go/navigate down.\n *\n * @function goDown\n */\n goDown: createSymbol('goDown'),\n\n /**\n * Symbol for the `goEnd` method.\n *\n * This method is invoked when the user wants to go/navigate to the end (e.g.,\n * of a list).\n *\n * @function goEnd\n */\n goEnd: createSymbol('goEnd'),\n\n /**\n * Symbol for the `goLeft` method.\n *\n * This method is invoked when the user wants to go/navigate left.\n *\n * @function goLeft\n */\n goLeft: createSymbol('goLeft'),\n\n /**\n * Symbol for the `goRight` method.\n *\n * This method is invoked when the user wants to go/navigate right.\n *\n * @function goRight\n */\n goRight: createSymbol('goRight'),\n\n /**\n * Symbol for the `goStart` method.\n *\n * This method is invoked when the user wants to go/navigate to the start\n * (e.g., of a list).\n *\n * @function goStart\n */\n goStart: createSymbol('goStart'),\n\n /**\n * Symbol for the `goUp` method.\n *\n * This method is invoked when the user wants to go/navigate up.\n *\n * @function goUp\n */\n goUp: createSymbol('goUp'),\n\n /**\n * Symbol for the `itemAdded` method.\n *\n * This method is invoked when a new item is added to a list.\n *\n * @function itemAdded\n * @param {HTMLElement} item - the item being selected/deselected\n */\n itemAdded: createSymbol('itemAdded'),\n\n\n /**\n * Symbol for the `itemsChanged` method.\n *\n * This method is invoked when the underlying contents change. It is also\n * invoked on component initialization – since the items have \"changed\" from\n * being nothing.\n */\n itemsChanged: createSymbol('itemsChanged'),\n\n /**\n * Symbol for the `itemSelected` method.\n *\n * This method is invoked when an item becomes selected or deselected.\n *\n * @function itemSelected\n * @param {HTMLElement} item - the item being selected/deselected\n * @param {boolean} selected - true if the item is selected, false if not\n */\n itemSelected: createSymbol('itemSelected'),\n\n /**\n * Symbol for the `keydown` method.\n *\n * This method is invoked when an element receives a `keydown` event.\n *\n * @function keydown\n * @param {KeyboardEvent} event - the event being processed\n */\n keydown: createSymbol('keydown'),\n\n /**\n * Symbol for the `template` property.\n *\n * This property returns a component's template.\n *\n * @type {string|HTMLElement}\n */\n template: createSymbol('template')\n};\n\nexport default symbols;\n","/**\n * Helper function for standard classList.toggle() behavior on old browsers,\n * namely IE 11.\n *\n * The standard\n * [classlist](https://developer.mozilla.org/en-US/docs/Web/API/Element/classList)\n * object has a `toggle()` function that supports a second Boolean parameter\n * that can be used to succinctly turn a class on or off. This feature is often\n * useful in designing custom elements, which may want to externally reflect\n * component state in a CSS class that can be used for styling purposes.\n *\n * Unfortunately, IE 11 does not support the Boolean parameter to\n * `classList.toggle()`. This helper function behaves like the standard\n * `toggle()`, including support for the Boolean parameter, so that it can be\n * used even on IE 11.\n *\n * @function toggleClass\n * @param {HTMLElement} element - The element to modify\n * @param {string} className - The class to add/remove\n * @param {boolean} [force] - Force the class to be added (if true) or removed\n * (if false)\n */\nexport default function toggleClass(element, className, force) {\n const classList = element.classList;\n const addClass = (typeof force === 'undefined') ?\n !classList.contains(className) :\n force;\n if (addClass) {\n classList.add(className);\n } else {\n classList.remove(className);\n }\n return addClass;\n}\n","import AttributeMarshallingMixin from '../../basic-component-mixins/src/AttributeMarshallingMixin';\nimport ComposableMixin from '../../basic-component-mixins/src/ComposableMixin';\nimport DistributedChildrenMixin from '../../basic-component-mixins/src/DistributedChildrenMixin';\nimport ShadowElementReferencesMixin from '../../basic-component-mixins/src/ShadowElementReferencesMixin';\nimport ShadowTemplateMixin from '../../basic-component-mixins/src/ShadowTemplateMixin';\n\n\n/**\n * A sample general-purpose base class for defining custom elements that mixes\n * in some common features: template stamping into a shadow root, shadow element\n * references, marshalling attributes to properties, and retrieving the children\n * distributed to a component.\n *\n * This base class is not special in any way, and is defined only as a\n * convenient shorthand for applying the mixins listed above. You can use this\n * class as a base class for your own elements, or easily create your own base\n * class by applying the same set of mixins.\n *\n * The ElementBase base class does not register itself as a custom element with\n * the browser, and hence cannot be independently instantiated.\n *\n * @mixes AttributeMarshallingMixin\n * @mixes ComposableMixin\n * @mixes DistributedChildrenMixin\n * @mixes ShadowElementReferencesMixin\n * @mixes ShadowTemplateMixin\n */\nclass ElementBase extends ComposableMixin(HTMLElement).compose(\n ShadowTemplateMixin, // before node finding, so shadow root is populated\n ShadowElementReferencesMixin, // before marshalling, so properties can use refs\n AttributeMarshallingMixin,\n DistributedChildrenMixin\n) {}\n\nexport default ElementBase;\n","/*\n * This file is transpiled to create an ES5-compatible distribution in which\n * the package's main feature(s) are available via the window.Basic global.\n * If you're already using ES6 yourself, ignore this file, and instead import\n * the source file(s) you want from the src folder.\n */\n\nimport ListBox from './src/ListBox';\n\nwindow.Basic = window.Basic || {};\nwindow.Basic.ListBox = ListBox;\n","import ElementBase from '../../basic-element-base/src/ElementBase';\nimport DistributedChildrenContentMixin from '../../basic-component-mixins/src/DistributedChildrenContentMixin';\nimport ClickSelectionMixin from '../../basic-component-mixins/src/ClickSelectionMixin';\nimport ContentItemsMixin from '../../basic-component-mixins/src/ContentItemsMixin';\nimport DirectionSelectionMixin from '../../basic-component-mixins/src/DirectionSelectionMixin';\nimport GenericMixin from '../../basic-component-mixins/src/GenericMixin';\nimport KeyboardMixin from '../../basic-component-mixins/src/KeyboardMixin';\nimport KeyboardDirectionMixin from '../../basic-component-mixins/src/KeyboardDirectionMixin';\nimport KeyboardPagedSelectionMixin from '../../basic-component-mixins/src/KeyboardPagedSelectionMixin';\nimport KeyboardPrefixSelectionMixin from '../../basic-component-mixins/src/KeyboardPrefixSelectionMixin';\nimport SelectedItemTextValueMixin from '../../basic-component-mixins/src/SelectedItemTextValueMixin';\nimport SelectionAriaActiveMixin from '../../basic-component-mixins/src/SelectionAriaActiveMixin';\nimport SelectionHighlightMixin from '../../basic-component-mixins/src/SelectionHighlightMixin';\nimport SelectionInViewMixin from '../../basic-component-mixins/src/SelectionInViewMixin';\nimport SingleSelectionMixin from '../../basic-component-mixins/src/SingleSelectionMixin';\nimport symbols from '../../basic-component-mixins/src/symbols';\n\n\n/**\n * A single-selection list box that supports selection highlighting (using the\n * system highlight color) and keyboard navigation.\n *\n * [Live demo](http://basicwebcomponents.org/basic-web-components/packages/basic-list-box/)\n *\n * The user can select an item with the mouse/touch or keyboard: Up/Down, Page\n * Up/Down, Home/End.\n *\n * Like other Basic Web Components, this can handle distributed content: you can\n * include a content element inside a basic-list-box, and the list will navigate\n * through the distributed content.\n *\n * This component includes basic ARIA support to provide a reasonable default\n * experience, e.g., for screen readers. The list component itself will be\n * assigned an appropriate ARIA role (default is \"listbox\"). The ID of the\n * selected item will be reflected in an \"aria-activedescendant\" attribute\n * applied to the list. To support this feature, all items in the list need\n * unique IDs. If an item does not have an ID, basic-list-box will automatically\n * assign a default ID.\n *\n * The keyboard interaction model generally follows that of Microsoft Windows'\n * list boxes instead of those in OS X:\n *\n * * The Page Up/Down and Home/End keys actually move the selection, rather than\n * just scrolling the list. The former behavior seems more generally useful\n * for keyboard users.\n *\n * * Pressing Page Up/Down will move the selection to the topmost/bottommost\n * visible item if the selection is not already there. Thereafter, the key\n * will move the selection up/down by a page, and (per the above point) make\n * the selected item visible.\n *\n * Programmatically selecting an item (by setting the selected property) scrolls\n * the item into view.\n *\n * The user can also select an item by typing the beginning of an item's text.\n *\n * @extends ElementBase\n * @mixes ClickSelectionMixin\n * @mixes ContentItemsMixin\n * @mixes DirectionSelectionMixin\n * @mixes DistributedChildrenContentMixin\n * @mixes GenericMixin\n * @mixes KeyboardMixin\n * @mixes KeyboardDirectionMixin\n * @mixes KeyboardPagedSelectionMixin\n * @mixes KeyboardPrefixSelectionMixin\n * @mixis SelectedItemTextValueMixin\n * @mixes SelectionAriaActiveMixin\n * @mixes SelectionHighlightMixin\n * @mixes SelectionInViewMixin\n * @mixes SingleSelectionMixin\n */\nclass ListBox extends ElementBase.compose(\n ClickSelectionMixin,\n ContentItemsMixin,\n DirectionSelectionMixin,\n DistributedChildrenContentMixin,\n GenericMixin,\n KeyboardMixin,\n KeyboardDirectionMixin,\n KeyboardPagedSelectionMixin,\n KeyboardPrefixSelectionMixin,\n SelectedItemTextValueMixin,\n SelectionAriaActiveMixin,\n SelectionHighlightMixin,\n SelectionInViewMixin,\n SingleSelectionMixin\n) {\n\n get [symbols.defaults]() {\n const defaults = super[symbols.defaults] || {};\n defaults.navigationAxis = 'vertical';\n return defaults;\n }\n\n get scrollTarget() {\n return this.$.itemsContainer;\n }\n\n get [symbols.template]() {\n const baseTemplate = super[symbols.template] || '';\n return `\n \n\n \n \n
\n ${baseTemplate}\n `;\n }\n\n /**\n * Fires when the list's value property changes.\n *\n * @memberof ListBox\n * @event value-changed\n */\n}\n\n\ncustomElements.define('basic-list-box', ListBox);\nexport default ListBox;\n"]}
\ No newline at end of file
diff --git a/packages/basic-list-box/index.html b/packages/basic-list-box/index.html
index 9a2a0ef8..81cc65d4 100644
--- a/packages/basic-list-box/index.html
+++ b/packages/basic-list-box/index.html
@@ -7,7 +7,8 @@
basic-list-box
-
+
+
diff --git a/packages/basic-modes/README.md b/packages/basic-modes/README.md
index 104b4e5d..a46d01ee 100644
--- a/packages/basic-modes/README.md
+++ b/packages/basic-modes/README.md
@@ -6,6 +6,8 @@ Shows exactly one child element at a time. This can be useful, for example,
if a given UI element has multiple modes that present substantially different
elements.
+[Live demo](http://basicwebcomponents.org/basic-web-components/packages/demos/modes-with-arrows-and-keyboard.html)
+
The transition between child elements is instantenous. If you'd like the
transition to be accompanied by visible animated effects, see
[basic-animation-stage](../basic-animation-stage).
diff --git a/packages/basic-modes/dist/basic-modes.js b/packages/basic-modes/dist/basic-modes.js
index 5d4aac45..432277b0 100644
--- a/packages/basic-modes/dist/basic-modes.js
+++ b/packages/basic-modes/dist/basic-modes.js
@@ -1,2244 +1,2 @@
-(function e(t,n,r){function s(o,u){if(!n[o]){if(!t[o]){var a=typeof require=="function"&&require;if(!u&&a)return a(o,!0);if(i)return i(o,!0);var f=new Error("Cannot find module '"+o+"'");throw f.code="MODULE_NOT_FOUND",f}var l=n[o]={exports:{}};t[o][0].call(l.exports,function(e){var n=t[o][1][e];return s(n?n:e)},l,l.exports,e,t,n,r)}return n[o].exports}var i=typeof require=="function"&&require;for(var o=0;o
- *
- * Then, after the element has been upgraded, the `fooBar` setter will
- * automatically be invoked with the initial value "Hello".
- *
- * For the time being, this mixin only supports string-valued properties.
- * If you'd like to convert string attributes to other types (numbers,
- * booleans), you need to implement `attributeChangedCallback` yourself.
- */
- var AttributeMarshalling = function (_base) {
- _inherits(AttributeMarshalling, _base);
-
- function AttributeMarshalling() {
- _classCallCheck(this, AttributeMarshalling);
-
- return _possibleConstructorReturn(this, (AttributeMarshalling.__proto__ || Object.getPrototypeOf(AttributeMarshalling)).apply(this, arguments));
- }
-
- _createClass(AttributeMarshalling, [{
- key: 'attributeChangedCallback',
-
-
- /*
- * Handle a change to the attribute with the given name.
- */
- value: function attributeChangedCallback(attributeName, oldValue, newValue) {
- if (_get(AttributeMarshalling.prototype.__proto__ || Object.getPrototypeOf(AttributeMarshalling.prototype), 'attributeChangedCallback', this)) {
- _get(AttributeMarshalling.prototype.__proto__ || Object.getPrototypeOf(AttributeMarshalling.prototype), 'attributeChangedCallback', this).call(this);
- }
- var propertyName = attributeToPropertyName(attributeName);
- // If the attribute name corresponds to a property name, set the property.
- // Ignore standard HTMLElement properties handled by the DOM.
- if (propertyName in this && !(propertyName in HTMLElement.prototype)) {
- this[propertyName] = newValue;
- }
- }
- }, {
- key: 'connectedCallback',
- value: function connectedCallback() {
- if (_get(AttributeMarshalling.prototype.__proto__ || Object.getPrototypeOf(AttributeMarshalling.prototype), 'connectedCallback', this)) {
- _get(AttributeMarshalling.prototype.__proto__ || Object.getPrototypeOf(AttributeMarshalling.prototype), 'connectedCallback', this).call(this);
- }
- _safeAttributes2.default.connected(this);
- }
- }, {
- key: 'reflectAttribute',
-
-
- /**
- * Set/unset the attribute with the indicated name.
- *
- * This method exists primarily to handle the case where an element wants to
- * set a default property value that should be reflected as an attribute. An
- * important limitation of custom element consturctors is that they cannot
- * set attributes. A call to `reflectAttribute` during the constructor will
- * be deferred until the element is connected to the document.
- *
- * @param {string} attribute - The name of the *attribute* (not property) to set.
- * @param {object} value - The value to set. If null, the attribute will be removed.
- */
- value: function reflectAttribute(attribute, value) {
- return _safeAttributes2.default.setAttribute(this, attribute, value);
- }
-
- /**
- * Set/unset the class with the indicated name.
- *
- * This method exists primarily to handle the case where an element wants to
- * set a default property value that should be reflected as as class. An
- * important limitation of custom element consturctors is that they cannot
- * set attributes, including the `class` attribute. A call to
- * `reflectClass` during the constructor will be deferred until the element
- * is connected to the document.
- *
- * @param {string} className - The name of the class to set.
- * @param {object} value - True to set the class, false to remove it.
- */
-
- }, {
- key: 'reflectClass',
- value: function reflectClass(className, value) {
- return _safeAttributes2.default.toggleClass(this, className, value);
- }
- }], [{
- key: 'observedAttributes',
- get: function get() {
- return attributesForClass(this);
- }
- }]);
-
- return AttributeMarshalling;
- }(base);
-
- return AttributeMarshalling;
-};
-
-// Convert hyphenated foo-bar attribute name to camel case fooBar property name.
-
-
-function attributeToPropertyName(attributeName) {
- var propertyName = attributeToPropertyNames[attributeName];
- if (!propertyName) {
- // Convert and memoize.
- var hypenRegEx = /-([a-z])/g;
- propertyName = attributeName.replace(hypenRegEx, function (match) {
- return match[1].toUpperCase();
- });
- attributeToPropertyNames[attributeName] = propertyName;
- }
- return propertyName;
-}
-
-function attributesForClass(classFn) {
-
- // We treat the element base classes as if they have no attributes, since we
- // don't want to receive attributeChangedCallback for them.
- if (classFn === HTMLElement || classFn === Object) {
- return [];
- }
-
- // Get attributes for parent class.
- var baseClass = Object.getPrototypeOf(classFn.prototype).constructor;
- var baseAttributes = attributesForClass(baseClass);
-
- // Get attributes for this class.
- var propertyNames = Object.getOwnPropertyNames(classFn.prototype);
- var setterNames = propertyNames.filter(function (propertyName) {
- return typeof Object.getOwnPropertyDescriptor(classFn.prototype, propertyName).set === 'function';
- });
- var attributes = setterNames.map(function (setterName) {
- return propertyNameToAttribute(setterName);
- });
-
- // Merge.
- var diff = attributes.filter(function (attribute) {
- return baseAttributes.indexOf(attribute) < 0;
- });
- return baseAttributes.concat(diff);
-}
-
-// Convert a camel case fooBar property name to a hyphenated foo-bar attribute.
-function propertyNameToAttribute(propertyName) {
- var attribute = propertyNamesToAttributes[propertyName];
- if (!attribute) {
- // Convert and memoize.
- var uppercaseRegEx = /([A-Z])/g;
- attribute = propertyName.replace(uppercaseRegEx, '-$1').toLowerCase();
- }
- return attribute;
-}
-
-},{"./safeAttributes":11}],2:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-/* Exported function extends a base class with Composable. */
-exports.default = function (base) {
-
- /**
- * Mixin to make a class more easily composable with other mixins.
- *
- * This mixin contributes a `compose` method that applies a set of mixin
- * functions and returns the resulting new class. This sugar can make the
- * application of many mixins at once easier to read.
- */
- var Composable = function (_base) {
- _inherits(Composable, _base);
-
- function Composable() {
- _classCallCheck(this, Composable);
-
- return _possibleConstructorReturn(this, (Composable.__proto__ || Object.getPrototypeOf(Composable)).apply(this, arguments));
- }
-
- _createClass(Composable, null, [{
- key: 'compose',
-
-
- /**
- * Apply a set of mixin functions or mixin objects to the present class and
- * return the new class.
- *
- * Instead of writing:
- *
- * let MyClass = Mixin1(Mixin2(Mixin3(Mixin4(Mixin5(BaseClass)))));
- *
- * You can write:
- *
- * let MyClass = ComposableMixin(BaseClass).compose(
- * Mixin1,
- * Mixin2,
- * Mixin3,
- * Mixin4,
- * Mixin5
- * );
- *
- * This function can also take mixin objects. A mixin object is just a
- * shorthand for a mixin function that creates a new subclass with the given
- * members. The mixin object's members are *not* copied directly onto the
- * prototype of the base class, as with traditional mixins.
- *
- * In addition to providing syntactic sugar, this mixin can be used to
- * define a class in ES5, which lacks ES6's `class` keyword.
- *
- * @param {...mixins} mixins - A set of mixin functions or objects to apply.
- */
- value: function compose() {
- for (var _len = arguments.length, mixins = Array(_len), _key = 0; _key < _len; _key++) {
- mixins[_key] = arguments[_key];
- }
-
- // We create a new subclass for each mixin in turn. The result becomes
- // the base class extended by any subsequent mixins. It turns out that
- // we can use Array.reduce() to concisely express this, using the current
- // object as the seed for reduce().
- return mixins.reduce(composeClass, this);
- }
- }]);
-
- return Composable;
- }(base);
-
- return Composable;
-};
-
-// Properties defined by Object that we don't want to mixin.
-
-
-var NON_MIXABLE_OBJECT_PROPERTIES = ['constructor'];
-
-/*
- * Apply the mixin to the given base class to return a new class.
- * The mixin can either be a function that returns the modified class, or a
- * plain object whose members will be copied to the new class' prototype.
- */
-function composeClass(base, mixin) {
- if (typeof mixin === 'function') {
- // Mixin function
- return mixin(base);
- } else {
- // Mixin object
- var Subclass = function (_base2) {
- _inherits(Subclass, _base2);
-
- function Subclass() {
- _classCallCheck(this, Subclass);
-
- return _possibleConstructorReturn(this, (Subclass.__proto__ || Object.getPrototypeOf(Subclass)).apply(this, arguments));
- }
-
- return Subclass;
- }(base);
-
- copyOwnProperties(mixin, Subclass.prototype, NON_MIXABLE_OBJECT_PROPERTIES);
- return Subclass;
- }
-}
-
-/*
- * Copy the given properties/methods to the target.
- * Return the updated target.
- */
-function copyOwnProperties(source, target) {
- var ignorePropertyNames = arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : [];
-
- Object.getOwnPropertyNames(source).forEach(function (name) {
- if (ignorePropertyNames.indexOf(name) < 0) {
- var descriptor = Object.getOwnPropertyDescriptor(source, name);
- Object.defineProperty(target, name, descriptor);
- }
- });
- return target;
-}
-
-},{}],3:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
-
-var _get = function get(object, property, receiver) { if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { return get(parent, property, receiver); } } else if ("value" in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } };
-
-var _createSymbol = require('./createSymbol');
-
-var _createSymbol2 = _interopRequireDefault(_createSymbol);
-
-var _toggleClass = require('./toggleClass');
-
-var _toggleClass2 = _interopRequireDefault(_toggleClass);
-
-var _symbols = require('./symbols');
-
-var _symbols2 = _interopRequireDefault(_symbols);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-// Symbols for private data members on an element.
-var itemsSymbol = (0, _createSymbol2.default)('items');
-var itemInitializedSymbol = (0, _createSymbol2.default)('itemInitialized');
-
-/* Exported function extends a base class with ContentItems. */
-
-exports.default = function (base) {
-
- /**
- * Mixin which maps content semantics (elements) to list item semantics.
- *
- * Items differ from element contents in several ways:
- *
- * * They are often referenced via index.
- * * They may have a selection state.
- * * It's common to do work to initialize the appearance or state of a new
- * item.
- * * Auxiliary invisible child elements are filtered out and not counted as
- * items. Auxiliary elements include link, script, style, and template
- * elements. This filtering ensures that those auxiliary elements can be
- * used in markup inside of a list without being treated as list items.
- *
- * This mixin expects a component to provide a `content` property returning a
- * raw set of elements. You can provide that yourself, or use
- * [DistributedChildrenContentMixin](DistributedChildrenContentMixin.md).
- *
- * The most commonly referenced property defined by this mixin is the `items`
- * property. To avoid having to do work each time that property is requested,
- * this mixin supports an optimized mode. If you invoke the `contentChanged`
- * method when the set of items changes, the mixin concludes that you'll take
- * care of notifying it of future changes, and turns on the optimization. With
- * that on, the mixin saves a reference to the computed set of items, and will
- * return that immediately on subsequent calls to the `items` property. If you
- * use this mixin in conjunction with
- * [DistributedChildrenContentMixin](DistributedChildrenContentMixin.md), the
- * `contentChanged` method will be invoked for you when the element's children
- * change, turning on the optimization automatically.
- */
- var ContentItems = function (_base) {
- _inherits(ContentItems, _base);
-
- function ContentItems() {
- _classCallCheck(this, ContentItems);
-
- return _possibleConstructorReturn(this, (ContentItems.__proto__ || Object.getPrototypeOf(ContentItems)).apply(this, arguments));
- }
-
- _createClass(ContentItems, [{
- key: 'contentChanged',
- value: function contentChanged() {
- if (_get(ContentItems.prototype.__proto__ || Object.getPrototypeOf(ContentItems.prototype), 'contentChanged', this)) {
- _get(ContentItems.prototype.__proto__ || Object.getPrototypeOf(ContentItems.prototype), 'contentChanged', this).call(this);
- }
-
- // Since we got the contentChanged call, we'll assume we'll be notified if
- // the set of items changes later. We turn on memoization of the items
- // property by setting our internal property to null (instead of
- // undefined).
- this[itemsSymbol] = null;
-
- this[_symbols2.default.itemsChanged]();
- }
-
- /**
- * This method is invoked whenever a new item is added to the list.
- *
- * The default implementation of this method does nothing. You can override
- * this to perform per-item initialization.
- *
- * @param {HTMLElement} item - The item that was added.
- */
-
- }, {
- key: _symbols2.default.itemAdded,
- value: function value(item) {
- if (_get(ContentItems.prototype.__proto__ || Object.getPrototypeOf(ContentItems.prototype), _symbols2.default.itemAdded, this)) {
- _get(ContentItems.prototype.__proto__ || Object.getPrototypeOf(ContentItems.prototype), _symbols2.default.itemAdded, this).call(this, item);
- }
- }
-
- /**
- * The selection state for a single item has changed.
- *
- * Invoke this method to signal that the selected state of the indicated item
- * has changed. By default, this applies a `selected` CSS class if the item
- * is selected, and removed it if not selected.
- *
- * @param {HTMLElement} item - The item whose selection state has changed.
- * @param {boolean} selected - True if the item is selected, false if not.
- */
-
- }, {
- key: _symbols2.default.itemSelected,
- value: function value(item, selected) {
- if (_get(ContentItems.prototype.__proto__ || Object.getPrototypeOf(ContentItems.prototype), _symbols2.default.itemSelected, this)) {
- _get(ContentItems.prototype.__proto__ || Object.getPrototypeOf(ContentItems.prototype), _symbols2.default.itemSelected, this).call(this, item, selected);
- }
- (0, _toggleClass2.default)(item, 'selected', selected);
- }
-
- /**
- * The current set of items in the list. See the top-level documentation for
- * mixin for a description of how items differ from plain content.
- *
- * @type {HTMLElement[]}
- */
-
- }, {
- key: _symbols2.default.itemsChanged,
-
-
- /**
- * This method is invoked when the underlying contents change. It is also
- * invoked on component initialization – since the items have "changed" from
- * being nothing.
- */
- value: function value() {
- var _this2 = this;
-
- if (_get(ContentItems.prototype.__proto__ || Object.getPrototypeOf(ContentItems.prototype), _symbols2.default.itemsChanged, this)) {
- _get(ContentItems.prototype.__proto__ || Object.getPrototypeOf(ContentItems.prototype), _symbols2.default.itemsChanged, this).call(this);
- }
-
- // Perform per-item initialization.
- Array.prototype.forEach.call(this.items, function (item) {
- if (!item[itemInitializedSymbol]) {
- _this2[_symbols2.default.itemAdded](item);
- item[itemInitializedSymbol] = true;
- }
- });
-
- this.dispatchEvent(new CustomEvent('items-changed'));
- }
-
- /**
- * Fires when the items in the list change.
- *
- * @memberof ContentItems
- * @event items-changed
- */
-
- }, {
- key: 'items',
- get: function get() {
- var items = void 0;
- if (this[itemsSymbol] == null) {
- items = filterAuxiliaryElements(this.content);
- // Note: test for *equality* with null; don't treat undefined as a match.
- if (this[itemsSymbol] === null) {
- // Memoize the set of items.
- this[itemsSymbol] = items;
- }
- } else {
- // Return the memoized items.
- items = this[itemsSymbol];
- }
- return items;
- }
- }]);
-
- return ContentItems;
- }(base);
-
- return ContentItems;
-};
-
-// Return the given elements, filtering out auxiliary elements that aren't
-// typically visible. Items which are not elements are returned as is.
-
-
-function filterAuxiliaryElements(items) {
- var auxiliaryTags = ['link', 'script', 'style', 'template'];
- return [].filter.call(items, function (item) {
- return !item.localName || auxiliaryTags.indexOf(item.localName) < 0;
- });
-}
-
-},{"./createSymbol":9,"./symbols":12,"./toggleClass":13}],4:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
-
-var _set = function set(object, property, value, receiver) { var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent !== null) { set(parent, property, value, receiver); } } else if ("value" in desc && desc.writable) { desc.value = value; } else { var setter = desc.set; if (setter !== undefined) { setter.call(receiver, value); } } return value; };
-
-var _get = function get(object, property, receiver) { if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { return get(parent, property, receiver); } } else if ("value" in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } };
-
-var _microtask = require('./microtask');
-
-var _microtask2 = _interopRequireDefault(_microtask);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-/* Exported function extends a base class with DistributedChildrenContent. */
-exports.default = function (base) {
-
- /**
- * Mixin which defines a component's content as its children, expanding any
- * nodes distributed to the component's slots.
- *
- * This also provides notification of changes to a component's content. It
- * will invoke a `contentChanged` method when the component is first
- * instantiated, and whenever its distributed children change. This is an
- * easy way to satisfy the Gold Standard checklist item for monitoring
- * [Content Changes](https://github.com/webcomponents/gold-standard/wiki/Content-Changes).
- *
- * Example:
- *
- * ```
- * let base = DistributedChildrenContentMixin(DistributedChildrenMixin(HTMLElement));
- * class CountingElement extends base {
- *
- * constructor() {
- * super();
- * let root = this.attachShadow({ mode: 'open' });
- * root.innerHTML = ` `;
- * }
- *
- * contentChanged() {
- * // Count the component's children, both initially and when changed.
- * this.count = this.distributedChildren.length;
- * }
- *
- * }
- * ```
- *
- * Note that content change detection depends upon the element having at least
- * one `slot` element in its shadow subtree.
- *
- * This mixin is intended for use with the
- * [DistributedChildrenMixin](DistributedChildrenMixin.md). See that mixin for
- * a discussion of how that works. This DistributedChildrenContentMixin
- * provides an easy way of defining the "content" of a component as the
- * component's distributed children. That in turn lets mixins like
- * [ContentItemsMixin](ContentItemsMixin.md) manipulate the children as list
- * items.
- */
- var DistributedChildrenContent = function (_base) {
- _inherits(DistributedChildrenContent, _base);
-
- function DistributedChildrenContent() {
- _classCallCheck(this, DistributedChildrenContent);
-
- var _this = _possibleConstructorReturn(this, (DistributedChildrenContent.__proto__ || Object.getPrototypeOf(DistributedChildrenContent)).call(this));
-
- if (_this.shadowRoot) {
- // Listen to changes on all slots.
- var slots = _this.shadowRoot.querySelectorAll('slot');
- slots.forEach(function (slot) {
- return slot.addEventListener('slotchange', function (event) {
- _this.contentChanged();
- });
- });
- }
-
- // Make an initial call to contentChanged() so that the component can do
- // initialization that it normally does when content changes.
- //
- // This will invoke contentChanged() handlers in other mixins. In order
- // that those mixins have a chance to complete their own initialization,
- // we add the contentChanged() call to the microtask queue.
- (0, _microtask2.default)(function () {
- return _this.contentChanged();
- });
- return _this;
- }
-
- /**
- * Invoked when the contents of the component (including distributed
- * children) have changed.
- *
- * This method is also invoked when a component is first instantiated; the
- * contents have essentially "changed" from being nothing. This allows the
- * component to perform initial processing of its children.
- */
-
-
- _createClass(DistributedChildrenContent, [{
- key: 'contentChanged',
- value: function contentChanged() {
- if (_get(DistributedChildrenContent.prototype.__proto__ || Object.getPrototypeOf(DistributedChildrenContent.prototype), 'contentChanged', this)) {
- _get(DistributedChildrenContent.prototype.__proto__ || Object.getPrototypeOf(DistributedChildrenContent.prototype), 'contentChanged', this).call(this);
- }
- var event = new CustomEvent('content-changed');
- this.dispatchEvent(event);
- }
-
- /**
- * The content of this component, defined to be the flattened array of
- * children distributed to the component.
- *
- * @type {HTMLElement[]}
- */
-
- }, {
- key: 'content',
- get: function get() {
- var distributedChildren = this.distributedChildren;
- if (typeof distributedChildren === 'undefined') {
- console.warn('DistributedChildrenContentMixin expects the component to define a "distributedChildren" property.');
- }
- return distributedChildren;
- },
- set: function set(value) {
- if ('content' in base.prototype) {
- _set(DistributedChildrenContent.prototype.__proto__ || Object.getPrototypeOf(DistributedChildrenContent.prototype), 'content', value, this);
- }
- // TODO: Set the children to the given value (which should be an array of
- // elements)?
- }
-
- /**
- * This event is raised when the component's contents (including distributed
- * children) have changed.
- *
- * @memberof DistributedChildrenContent
- * @event content-changed
- */
-
- }]);
-
- return DistributedChildrenContent;
- }(base);
-
- return DistributedChildrenContent;
-};
-
-},{"./microtask":10}],5:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
-
-function _toConsumableArray(arr) { if (Array.isArray(arr)) { for (var i = 0, arr2 = Array(arr.length); i < arr.length; i++) { arr2[i] = arr[i]; } return arr2; } else { return Array.from(arr); } }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-/* Exported function extends a base class with DistributedChildren. */
-exports.default = function (base) {
-
- /**
- * Mixin which defines helpers for accessing a component's distributed
- * children as a flattened array or string.
- *
- * The standard DOM API provides several ways of accessing child content:
- * `children`, `childNodes`, and `textContent`. None of these functions are
- * Shadow DOM aware. This mixin defines variations of those functions that
- * *are* Shadow DOM aware.
- *
- * Example: you create a component `` that displays a number
- * equal to the number of children placed inside that component. If someone
- * instantiates your component like:
- *
- *
- *
- *
- *
- *
- *
- * Then the component should show "3", because there are three children. To
- * calculate the number of children, the component can just calculate
- * `this.children.length`. However, suppose someone instantiates your
- * component inside one of their own components, and puts a `` element
- * inside your component:
- *
- *
- *
- *
- *
- * If your component only looks at `this.children`, it will always see exactly
- * one child — the `` element. But the user looking at the page will
- * *see* any nodes distributed to that slot. To match what the user sees, your
- * component should expand any `` elements it contains.
- *
- * That is the problem this mixin solves. After applying this mixin, your
- * component code has access to `this.distributedChildren`, whose `length`
- * will return the total number of all children distributed to your component
- * in the composed tree.
- *
- * Note: The latest Custom Elements API design calls for a new function,
- * `getAssignedNodes` that takes an optional `deep` parameter, that will solve
- * this problem at the API level.
- */
- var DistributedChildren = function (_base) {
- _inherits(DistributedChildren, _base);
-
- function DistributedChildren() {
- _classCallCheck(this, DistributedChildren);
-
- return _possibleConstructorReturn(this, (DistributedChildren.__proto__ || Object.getPrototypeOf(DistributedChildren)).apply(this, arguments));
- }
-
- _createClass(DistributedChildren, [{
- key: 'distributedChildren',
-
-
- /**
- * An in-order collection of distributed children, expanding any slot
- * elements. Like the standard children property, this skips text nodes.
- *
- * @type {HTMLElement[]}
- */
- get: function get() {
- return expandContentElements(this.children, false);
- }
-
- /**
- * An in-order collection of distributed child nodes, expanding any slot
- * elements. Like the standard childNodes property, this includes text
- * nodes.
- *
- * @type {Node[]}
- */
-
- }, {
- key: 'distributedChildNodes',
- get: function get() {
- return expandContentElements(this.childNodes, true);
- }
-
- /**
- * The concatenated text content of all distributed child nodes, expanding
- * any slot elements.
- *
- * @type {string}
- */
-
- }, {
- key: 'distributedTextContent',
- get: function get() {
- var strings = this.distributedChildNodes.map(function (child) {
- return child.textContent;
- });
- return strings.join('');
- }
- }]);
-
- return DistributedChildren;
- }(base);
-
- return DistributedChildren;
-};
-
-/*
- * Given a array of nodes, return a new array with any content elements expanded
- * to the nodes distributed to that content element. This rule is applied
- * recursively.
- *
- * If includeTextNodes is true, text nodes will be included, as in the
- * standard childNodes property; by default, this skips text nodes, like the
- * standard children property.
- */
-
-
-function expandContentElements(nodes, includeTextNodes) {
- var _ref;
-
- var expanded = Array.prototype.map.call(nodes, function (node) {
- // We want to see if the node is an instanceof HTMLSlotELement, but
- // that class won't exist if the browser that doesn't support native
- // Shadow DOM and if the Shadow DOM polyfill hasn't been loaded. Instead,
- // we do a simplistic check to see if the tag name is "slot".
- var isSlot = typeof HTMLSlotElement !== 'undefined' ? node instanceof HTMLSlotElement : node.localName === 'slot';
- if (isSlot) {
- // Use the nodes assigned to this node instead.
- var assignedNodes = node.assignedNodes({ flatten: true });
- return assignedNodes ? expandContentElements(assignedNodes, includeTextNodes) : [];
- } else if (node instanceof HTMLElement) {
- // Plain element; use as is.
- return [node];
- } else if (node instanceof Text && includeTextNodes) {
- // Text node.
- return [node];
- } else {
- // Comment, processing instruction, etc.; skip.
- return [];
- }
- });
- var flattened = (_ref = []).concat.apply(_ref, _toConsumableArray(expanded));
- return flattened;
-}
-
-},{}],6:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-/* Exported function extends a base class with ShadowElementReferences. */
-exports.default = function (base) {
-
- /**
- * Mixin to create references to elements in a component's Shadow DOM subtree.
- *
- * This adds a member on the component called `this.$` that can be used to
- * reference shadow elements with IDs. E.g., if component's shadow contains an
- * element ``, then this mixin will create a member
- * `this.$.foo` that points to that button.
- *
- * Such references simplify a component's access to its own elements. In
- * exchange, this mixin trades off a one-time cost of querying all elements in
- * the shadow tree instead of paying an ongoing cost to query for an element
- * each time the component wants to inspect or manipulate it.
- *
- * This mixin expects the component to define a Shadow DOM subtree. You can
- * create that tree yourself, or make use of
- * [ShadowTemplateMixin](ShadowTemplateMixin.md).
- *
- * This mixin is inspired by Polymer's [automatic
- * node finding](https://www.polymer-project.org/1.0/docs/devguide/local-dom.html#node-finding)
- * feature.
- */
- var ShadowElementReferences = function (_base) {
- _inherits(ShadowElementReferences, _base);
-
- function ShadowElementReferences() {
- _classCallCheck(this, ShadowElementReferences);
-
- var _this = _possibleConstructorReturn(this, (ShadowElementReferences.__proto__ || Object.getPrototypeOf(ShadowElementReferences)).call(this));
-
- if (_this.shadowRoot) {
- // Look for elements in the shadow subtree that have id attributes.
- // An alternatively implementation of this mixin would be to just define
- // a this.$ getter that lazily does this search the first time someone
- // tries to access this.$. That might introduce some complexity – if the
- // the tree changed after it was first populated, the result of
- // searching for a node might be somewhat unpredictable.
- _this.$ = {};
- var nodesWithIds = _this.shadowRoot.querySelectorAll('[id]');
- [].forEach.call(nodesWithIds, function (node) {
- var id = node.getAttribute('id');
- _this.$[id] = node;
- });
- }
- return _this;
- }
-
- /**
- * The collection of references to the elements with IDs in a component's
- * Shadow DOM subtree.
- *
- * @type {object}
- * @member $
- */
-
-
- return ShadowElementReferences;
- }(base);
-
- return ShadowElementReferences;
-};
-
-},{}],7:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _symbols = require('../src/symbols');
-
-var _symbols2 = _interopRequireDefault(_symbols);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-/* Exported function extends a base class with ShadowTemplate. */
-exports.default = function (base) {
-
- /**
- * Mixin for stamping a template into a Shadow DOM subtree upon component
- * instantiation.
- *
- * To use this mixin, define a `template` property as a string or HTML
- * `` element:
- *
- * class MyElement extends ShadowTemplateMixin(HTMLElement) {
- * get [symbols.template]() {
- * return `Hello, world .`;
- * }
- * }
- *
- * When your component class is instantiated, a shadow root will be created on
- * the instance, and the contents of the template will be cloned into the
- * shadow root. If your component does not define a `template` property, this
- * mixin has no effect.
- *
- * For the time being, this extension retains support for Shadow DOM v0. That
- * will eventually be deprecated as browsers (and the Shadow DOM polyfill)
- * implement Shadow DOM v1.
- */
- var ShadowTemplate = function (_base) {
- _inherits(ShadowTemplate, _base);
-
- /*
- * If the component defines a template, a shadow root will be created on the
- * component instance, and the template stamped into it.
- */
- function ShadowTemplate() {
- _classCallCheck(this, ShadowTemplate);
-
- var _this = _possibleConstructorReturn(this, (ShadowTemplate.__proto__ || Object.getPrototypeOf(ShadowTemplate)).call(this));
-
- var template = _this[_symbols2.default.template];
- // TODO: Save the processed template with the component's class prototype
- // so it doesn't need to be processed with every instantiation.
- if (template) {
-
- if (typeof template === 'string') {
- // Upgrade plain string to real template.
- template = createTemplateWithInnerHTML(template);
- }
-
- if (window.ShadowDOMPolyfill) {
- shimTemplateStyles(template, _this.localName);
- }
-
- var root = _this.attachShadow({ mode: 'open' });
- var clone = document.importNode(template.content, true);
- root.appendChild(clone);
- }
- return _this;
- }
-
- return ShadowTemplate;
- }(base);
-
- return ShadowTemplate;
-};
-
-// Convert a plain string of HTML into a real template element.
-
-
-function createTemplateWithInnerHTML(innerHTML) {
- var template = document.createElement('template');
- // REVIEW: Is there an easier way to do this?
- // We'd like to just set innerHTML on the template content, but since it's
- // a DocumentFragment, that doesn't work.
- var div = document.createElement('div');
- div.innerHTML = innerHTML;
- while (div.childNodes.length > 0) {
- template.content.appendChild(div.childNodes[0]);
- }
- return template;
-}
-
-// Invoke basic style shimming with ShadowCSS.
-function shimTemplateStyles(template, tag) {
- window.WebComponents.ShadowCSS.shimStyling(template.content, tag);
-}
-
-},{"../src/symbols":12}],8:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
-
-var _get = function get(object, property, receiver) { if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { return get(parent, property, receiver); } } else if ("value" in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } };
-
-var _set = function set(object, property, value, receiver) { var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent !== null) { set(parent, property, value, receiver); } } else if ("value" in desc && desc.writable) { desc.value = value; } else { var setter = desc.set; if (setter !== undefined) { setter.call(receiver, value); } } return value; };
-
-var _createSymbol = require('./createSymbol');
-
-var _createSymbol2 = _interopRequireDefault(_createSymbol);
-
-var _symbols = require('./symbols');
-
-var _symbols2 = _interopRequireDefault(_symbols);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-// Symbols for private data members on an element.
-var canSelectNextSymbol = (0, _createSymbol2.default)('canSelectNext');
-var canSelectPreviousSymbol = (0, _createSymbol2.default)('canSelectPrevious');
-var selectionRequiredSymbol = (0, _createSymbol2.default)('selectionRequired');
-var selectionWrapsSymbol = (0, _createSymbol2.default)('selectionWraps');
-
-// We want to expose both selectedIndex and selectedItem as independent
-// properties but keep them in sync. This allows a component user to reference
-// the selection by whatever means is most natural for their situation.
-//
-// To efficiently keep these properties in sync, we track "external" and
-// "internal" references for each property:
-//
-// The external index or item is the one we report to the outside world when
-// asked for selection. When handling a change to index or item, we update the
-// external reference as soon as possible, so that if anyone immediately asks
-// for the current selection, they will receive a stable answer.
-//
-// The internal index or item tracks whichever index or item last received the
-// full set of processing. Processing includes raising a change event for the
-// new value. Once we've begun that processing, we store the new value as the
-// internal value to indicate we've handled it.
-//
-var externalSelectedIndexSymbol = (0, _createSymbol2.default)('externalSelectedIndex');
-var externalSelectedItemSymbol = (0, _createSymbol2.default)('externalSelectedItem');
-var internalSelectedIndexSymbol = (0, _createSymbol2.default)('internalSelectedIndex');
-var internalSelectedItemSymbol = (0, _createSymbol2.default)('internalSelectedItem');
-
-/* Exported function extends a base class with SingleSelection. */
-
-exports.default = function (base) {
-
- /**
- * Mixin which manages single-selection semantics for items in a list.
- *
- * This mixin expects a component to provide an `items` Array or NodeList of
- * all elements in the list. A standard way to do that with is the
- * [ContentItemsMixin](ContentItemsMixin.md), which takes a component's
- * content (typically its distributed children) as the set of list items; see
- * that mixin for details.
- *
- * This mixin tracks a single selected item in the list, and provides means to
- * get and set that state by item position (`selectedIndex`) or item identity
- * (`selectedItem`). The selection can be moved in the list via the methods
- * `selectFirst`, `selectLast`, `selectNext`, and `selectPrevious`.
- *
- * This mixin does not produce any user-visible effects to represent
- * selection. Other mixins, such as
- * [SelectionAriaActiveMixin](SelectionAriaActiveMixin.md),
- * [SelectionHighlightMixin](SelectionHighlightMixin.md) and
- * [SelectionInViewMixin](SelectionInViewMixin.md), modify the selected item
- * in common ways to let the user know a given item is selected or not
- * selected.
- */
- var SingleSelection = function (_base) {
- _inherits(SingleSelection, _base);
-
- function SingleSelection() {
- _classCallCheck(this, SingleSelection);
-
- // Set defaults.
- var _this = _possibleConstructorReturn(this, (SingleSelection.__proto__ || Object.getPrototypeOf(SingleSelection)).call(this));
-
- if (typeof _this.selectionRequired === 'undefined') {
- _this.selectionRequired = _this[_symbols2.default.defaults].selectionRequired;
- }
- if (typeof _this.selectionWraps === 'undefined') {
- _this.selectionWraps = _this[_symbols2.default.defaults].selectionWraps;
- }
- return _this;
- }
-
- /**
- * True if the selection can be moved to the next item, false if not (the
- * selected item is the last item in the list).
- *
- * @type {boolean}
- */
-
-
- _createClass(SingleSelection, [{
- key: _symbols2.default.itemAdded,
-
-
- /**
- * Handle a new item being added to the list.
- *
- * The default implementation of this method simply sets the item's
- * selection state to false.
- *
- * @param {HTMLElement} item - the item being added
- */
- value: function value(item) {
- if (_get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), _symbols2.default.itemAdded, this)) {
- _get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), _symbols2.default.itemAdded, this).call(this, item);
- }
- this[_symbols2.default.itemSelected](item, item === this.selectedItem);
- }
- }, {
- key: _symbols2.default.itemsChanged,
- value: function value() {
- if (_get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), _symbols2.default.itemsChanged, this)) {
- _get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), _symbols2.default.itemsChanged, this).call(this);
- }
-
- // In case selected item changed position or was removed.
- trackSelectedItem(this);
-
- // In case the change in items affected which navigations are possible.
- updatePossibleNavigations(this);
- }
-
- /**
- * Apply the indicate selection state to the item.
- *
- * The default implementation of this method does nothing. User-visible
- * effects will typically be handled by other mixins.
- *
- * @param {HTMLElement} item - the item being selected/deselected
- * @param {boolean} selected - true if the item is selected, false if not
- */
-
- }, {
- key: _symbols2.default.itemSelected,
- value: function value(item, selected) {
- if (_get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), _symbols2.default.itemSelected, this)) {
- _get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), _symbols2.default.itemSelected, this).call(this, item, selected);
- }
- }
-
- /**
- * The index of the item which is currently selected.
- *
- * A `selectedIndex` of -1 indicates there is no selection. Setting this
- * property to -1 will remove any existing selection.
- *
- * @type {number}
- */
-
- }, {
- key: 'selectFirst',
-
-
- /**
- * Select the first item in the list.
- */
- value: function selectFirst() {
- if (_get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), 'selectFirst', this)) {
- _get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), 'selectFirst', this).call(this);
- }
- return selectIndex(this, 0);
- }
-
- /**
- * True if the list should always have a selection (if it has items).
- *
- * @type {boolean}
- * @default false
- */
-
- }, {
- key: 'selectLast',
-
-
- /**
- * Select the last item in the list.
- */
- value: function selectLast() {
- if (_get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), 'selectLast', this)) {
- _get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), 'selectLast', this).call(this);
- }
- return selectIndex(this, this.items.length - 1);
- }
-
- /**
- * Select the next item in the list.
- */
-
- }, {
- key: 'selectNext',
- value: function selectNext() {
- if (_get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), 'selectNext', this)) {
- _get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), 'selectNext', this).call(this);
- }
- return selectIndex(this, this.selectedIndex + 1);
- }
-
- /**
- * Select the previous item in the list.
- *
- * If the list has no selection, the last item will be selected.
- */
-
- }, {
- key: 'selectPrevious',
- value: function selectPrevious() {
- if (_get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), 'selectPrevious', this)) {
- _get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), 'selectPrevious', this).call(this);
- }
- var newIndex = this.selectedIndex < 0 ? this.items.length - 1 : // No selection yet; select last item.
- this.selectedIndex - 1;
- return selectIndex(this, newIndex);
- }
-
- /**
- * Fires when the selectedItem property changes.
- *
- * @memberof SingleSelection
- * @event selected-item-changed
- * @param {HTMLElement} detail.selectedItem The new selected item.
- * @param {HTMLElement} detail.previousItem The previously selected item.
- */
-
- /**
- * Fires when the selectedIndex property changes.
- *
- * @memberof SingleSelection
- * @event selected-index-changed
- * @param {number} detail.selectedIndex The new selected index.
- */
-
- }, {
- key: 'canSelectNext',
- get: function get() {
- return this[canSelectNextSymbol];
- },
- set: function set(canSelectNext) {
- var previousCanSelectNext = this[canSelectNextSymbol];
- this[canSelectNextSymbol] = canSelectNext;
- if ('canSelectNext' in base.prototype) {
- _set(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), 'canSelectNext', canSelectNext, this);
- }
- if (canSelectNext !== previousCanSelectNext) {
- this.dispatchEvent(new CustomEvent('can-select-next-changed'));
- }
- }
-
- /**
- * True if the selection can be moved to the previous item, false if not
- * (the selected item is the first one in the list).
- *
- * @type {boolean}
- */
-
- }, {
- key: 'canSelectPrevious',
- get: function get() {
- return this[canSelectPreviousSymbol];
- },
- set: function set(canSelectPrevious) {
- var previousCanSelectPrevious = this[canSelectPreviousSymbol];
- this[canSelectPreviousSymbol] = canSelectPrevious;
- if ('canSelectPrevious' in base.prototype) {
- _set(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), 'canSelectPrevious', canSelectPrevious, this);
- }
- if (canSelectPrevious !== previousCanSelectPrevious) {
- this.dispatchEvent(new CustomEvent('can-select-previous-changed'));
- }
- }
- }, {
- key: _symbols2.default.defaults,
- get: function get() {
- var defaults = _get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), _symbols2.default.defaults, this) || {};
- defaults.selectionRequired = false;
- defaults.selectionWraps = false;
- return defaults;
- }
- }, {
- key: 'selectedIndex',
- get: function get() {
- return this[externalSelectedIndexSymbol] != null ? this[externalSelectedIndexSymbol] : -1;
- },
- set: function set(index) {
- // See notes at top about internal vs. external copies of this property.
- var previousSelectedIndex = this[internalSelectedIndexSymbol];
- var item = void 0;
- if (index !== this[externalSelectedIndexSymbol]) {
- // Store the new index and the corresponding item.
- var items = this.items;
- var hasItems = items && items.length > 0;
- if (!(hasItems && index >= 0 && index < items.length)) {
- index = -1; // No item at that index.
- }
- this[externalSelectedIndexSymbol] = index;
- item = hasItems && index >= 0 ? items[index] : null;
- this[externalSelectedItemSymbol] = item;
- } else {
- item = this[externalSelectedItemSymbol];
- }
-
- // Now let super do any work.
- if ('selectedIndex' in base.prototype) {
- _set(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), 'selectedIndex', index, this);
- }
-
- if (index !== previousSelectedIndex) {
- // The selected index changed.
- this[internalSelectedIndexSymbol] = index;
-
- var event = new CustomEvent('selected-index-changed', {
- detail: {
- selectedIndex: index,
- value: index // for Polymer binding. TODO: Verify still necessary
- }
- });
- this.dispatchEvent(event);
- }
-
- if (this[internalSelectedItemSymbol] !== item) {
- // Update selectedItem property so it can have its own effects.
- this.selectedItem = item;
- }
- }
-
- /**
- * The currently selected item, or null if there is no selection.
- *
- * Setting this property to null deselects any currently-selected item.
- * Setting this property to an object that is not in the list has no effect.
- *
- * TODO: Even if selectionRequired, can still explicitly set selectedItem to null.
- * TODO: If selectionRequired, leave selection alone?
- *
- * @type {object}
- */
-
- }, {
- key: 'selectedItem',
- get: function get() {
- return this[externalSelectedItemSymbol] || null;
- },
- set: function set(item) {
- // See notes at top about internal vs. external copies of this property.
- var previousSelectedItem = this[internalSelectedItemSymbol];
- var index = void 0;
- if (item !== this[externalSelectedItemSymbol]) {
- // Store item and look up corresponding index.
- var items = this.items;
- var hasItems = items && items.length > 0;
- index = hasItems ? Array.prototype.indexOf.call(items, item) : -1;
- this[externalSelectedIndexSymbol] = index;
- if (index < 0) {
- item = null; // The indicated item isn't actually in `items`.
- }
- this[externalSelectedItemSymbol] = item;
- } else {
- index = this[externalSelectedIndexSymbol];
- }
-
- // Now let super do any work.
- if ('selectedItem' in base.prototype) {
- _set(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), 'selectedItem', item, this);
- }
-
- if (item !== previousSelectedItem) {
- // The selected item changed.
- this[internalSelectedItemSymbol] = item;
-
- if (previousSelectedItem) {
- // Update selection state of old item.
- this[_symbols2.default.itemSelected](previousSelectedItem, false);
- }
- if (item) {
- // Update selection state to new item.
- this[_symbols2.default.itemSelected](item, true);
- }
-
- updatePossibleNavigations(this);
-
- var event = new CustomEvent('selected-item-changed', {
- detail: {
- selectedItem: item,
- value: item // for Polymer binding
- }
- });
- this.dispatchEvent(event);
- }
-
- if (this[internalSelectedIndexSymbol] !== index) {
- // Update selectedIndex property so it can have its own effects.
- this.selectedIndex = index;
- }
- }
- }, {
- key: 'selectionRequired',
- get: function get() {
- return this[selectionRequiredSymbol];
- },
- set: function set(selectionRequired) {
- this[selectionRequiredSymbol] = selectionRequired;
- if ('selectionRequired' in base.prototype) {
- _set(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), 'selectionRequired', selectionRequired, this);
- }
- trackSelectedItem(this);
- }
-
- /**
- * True if selection navigations wrap from last to first, and vice versa.
- *
- * @type {boolean}
- * @default false
- */
-
- }, {
- key: 'selectionWraps',
- get: function get() {
- return this[selectionWrapsSymbol];
- },
- set: function set(value) {
- this[selectionWrapsSymbol] = String(value) === 'true';
- if ('selectionWraps' in base.prototype) {
- _set(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), 'selectionWraps', value, this);
- }
- updatePossibleNavigations(this);
- }
- }]);
-
- return SingleSelection;
- }(base);
-
- return SingleSelection;
-};
-
-// Ensure the given index is within bounds, and select it if it's not already
-// selected.
-
-
-function selectIndex(element, index) {
- var count = element.items.length;
-
- var boundedIndex = element.selectionWraps ?
- // JavaScript mod doesn't handle negative numbers the way we want to wrap.
- // See http://stackoverflow.com/a/18618250/76472
- (index % count + count) % count :
-
- // Keep index within bounds of array.
- Math.max(Math.min(index, count - 1), 0);
-
- var previousIndex = element.selectedIndex;
- if (previousIndex !== boundedIndex) {
- element.selectedIndex = boundedIndex;
- return true;
- } else {
- return false;
- }
-}
-
-// Following a change in the set of items, or in the value of the
-// `selectionRequired` property, reacquire the selected item. If it's moved,
-// update `selectedIndex`. If it's been removed, and a selection is required,
-// try to select another item.
-function trackSelectedItem(element) {
-
- var items = element.items;
- var itemCount = items ? items.length : 0;
-
- var previousSelectedItem = element.selectedItem;
- if (!previousSelectedItem) {
- // No item was previously selected.
- if (element.selectionRequired) {
- // Select the first item by default.
- element.selectedIndex = 0;
- }
- } else if (itemCount === 0) {
- // We've lost the selection, and there's nothing left to select.
- element.selectedItem = null;
- } else {
- // Try to find the previously-selected item in the current set of items.
- var indexInCurrentItems = Array.prototype.indexOf.call(items, previousSelectedItem);
- var previousSelectedIndex = element.selectedIndex;
- if (indexInCurrentItems < 0) {
- // Previously-selected item was removed from the items.
- // Select the item at the same index (if it exists) or as close as possible.
- var newSelectedIndex = Math.min(previousSelectedIndex, itemCount - 1);
- // Select by item, since index may be the same, and we want to raise the
- // selected-item-changed event.
- element.selectedItem = items[newSelectedIndex];
- } else if (indexInCurrentItems !== previousSelectedIndex) {
- // Previously-selected item still there, but changed position.
- element.selectedIndex = indexInCurrentItems;
- }
- }
-}
-
-// Following a change in selection, report whether it's now possible to
-// go next/previous from the given index.
-function updatePossibleNavigations(element) {
- var canSelectNext = void 0;
- var canSelectPrevious = void 0;
- var items = element.items;
- if (items == null || items.length === 0) {
- // No items to select.
- canSelectNext = false;
- canSelectPrevious = false;
- }if (element.selectionWraps) {
- // Since there are items, can always go next/previous.
- canSelectNext = true;
- canSelectPrevious = true;
- } else {
- var index = element.selectedIndex;
- if (index < 0 && items.length > 0) {
- // Special case. If there are items but no selection, declare that it's
- // always possible to go next/previous to create a selection.
- canSelectNext = true;
- canSelectPrevious = true;
- } else {
- // Normal case: we have an index in a list that has items.
- canSelectPrevious = index > 0;
- canSelectNext = index < items.length - 1;
- }
- }
- if (element.canSelectNext !== canSelectNext) {
- element.canSelectNext = canSelectNext;
- }
- if (element.canSelectPrevious !== canSelectPrevious) {
- element.canSelectPrevious = canSelectPrevious;
- }
-}
-
-},{"./createSymbol":9,"./symbols":12}],9:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-exports.default = createSymbol;
-/**
- * Helper function to create a symbol that can be used for associating private
- * data with an element.
- *
- * Mixins and component classes often want to associate private data with an
- * element instance, but JavaScript does not have direct support for true
- * private properties. One approach is to use the
- * [Symbol](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Symbol)
- * data type to set and retrieve data on an element.
- *
- * Unfortunately, the Symbol type is not available in Internet Explorer 11. The
- * `createSymbol` helper function exists as a workaround for IE 11. Rather than
- * returning a true Symbol, it simply returns an underscore-prefixed string.
- *
- * Usage:
- *
- * const fooSymbol = createSymbol('foo');
- *
- * class MyElement extends HTMLElement {
- * get foo() {
- * return this[fooSymbol];
- * }
- * set foo(value) {
- * this[fooSymbol] = value;
- * }
- * }
- *
- * In IE 11, this sample will "hide" data behind an instance property this._foo.
- * The use of the underscore is meant to reduce (not eliminate) the potential
- * for name conflicts, and discourage (not prevent) external access to this
- * data. In modern browsers, the above code will eliminate the potential of
- * naming conflicts, and better hide the data behind a real Symbol.
- *
- * @function createSymbol
- * @param {string} description - A string to identify the symbol when debugging
- */
-function createSymbol(description) {
- return typeof Symbol === 'function' ? Symbol(description) : '_' + description;
-}
-
-},{}],10:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-exports.default = microtask;
-/*
- * Microtask helper for IE 11.
- *
- * Executing a function as a microtask is trivial in browsers that support
- * promises, whose then() clauses use microtask timing. IE 11 doesn't support
- * promises, but does support MutationObservers, which are also executed as
- * microtasks. So this helper uses an MutationObserver to achieve microtask
- * timing.
- *
- * See https://jakearchibald.com/2015/tasks-microtasks-queues-and-schedules/
- *
- * Inspired by Polymer's async() function.
- */
-
-// The queue of pending callbacks to be executed as microtasks.
-var callbacks = [];
-
-// Create an element that we will modify to force observable mutations.
-var element = document.createTextNode('');
-
-// A monotonically-increasing value.
-var counter = 0;
-
-/**
- * Add a callback to the microtask queue.
- *
- * This uses a MutationObserver so that it works on IE 11.
- *
- * NOTE: IE 11 may actually use timeout timing with MutationObservers. This
- * needs more investigation.
- *
- * @function microtask
- * @param {function} callback
- */
-function microtask(callback) {
- callbacks.push(callback);
- // Force a mutation.
- element.textContent = ++counter;
-}
-
-// Execute any pending callbacks.
-function executeCallbacks() {
- while (callbacks.length > 0) {
- var callback = callbacks.shift();
- callback();
- }
-}
-
-// Create the observer.
-var observer = new MutationObserver(executeCallbacks);
-observer.observe(element, {
- characterData: true
-});
-
-},{}],11:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createSymbol = require('./createSymbol');
-
-var _createSymbol2 = _interopRequireDefault(_createSymbol);
-
-var _toggleClass2 = require('./toggleClass');
-
-var _toggleClass3 = _interopRequireDefault(_toggleClass2);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-// Symbols for private data members on an element.
-var safeToSetAttributesSymbol = (0, _createSymbol2.default)('safeToSetAttributes');
-var pendingAttributesSymbol = (0, _createSymbol2.default)('pendingAttributes');
-var pendingClassesSymbol = (0, _createSymbol2.default)('pendingClasses');
-
-/**
- * Helper functions for updating attributes, including the `class` attribute.
- */
-exports.default = {
-
- /**
- * Perform any pending updates to attributes and classes.
- *
- * This writes any `setAttribute` or `toggleClass` values that were performed
- * before an element was attached to the document for the first time.
- *
- * This method should be called by mixins/components in their
- * `connectedCallback`. If mulitple mixins/components invoke this during the
- * same `connectedCallback`, only the first call will have any effect. The
- * subsequent calls will be harmless.
- *
- * @param {HTMLElement} element - The element being added to the document.
- */
- connected: function connected(element) {
- element[safeToSetAttributesSymbol] = true;
-
- // Set any pending attributes.
- if (element[pendingAttributesSymbol]) {
- for (var attribute in element[pendingAttributesSymbol]) {
- var value = element[pendingAttributesSymbol][attribute];
- setAttributeToElement(element, attribute, value);
- }
- element[pendingAttributesSymbol] = null;
- }
-
- // Set any pending classes.
- if (element[pendingClassesSymbol]) {
- for (var className in element[pendingClassesSymbol]) {
- var _value = element[pendingClassesSymbol][className];
- (0, _toggleClass3.default)(element, className, _value);
- }
- element[pendingClassesSymbol] = null;
- }
- },
-
-
- /**
- * Set/unset the attribute with the indicated name.
- *
- * This method exists primarily to handle the case where an element wants to
- * set a default property value that should be reflected as an attribute. An
- * important limitation of custom element consturctors is that they cannot
- * set attributes. A call to `setAttribute` during the constructor will
- * be deferred until the element is connected to the document.
- *
- * @param {string} attribute - The name of the *attribute* (not property) to set.
- * @param {object} value - The value to set. If null, the attribute will be removed.
- */
- setAttribute: function setAttribute(element, attribute, value) {
- if (element[safeToSetAttributesSymbol]) {
- // Safe to set attributes immediately.
- setAttributeToElement(element, attribute, value);
- } else {
- // Defer setting attributes until the first time we're connected.
- if (!element[pendingAttributesSymbol]) {
- element[pendingAttributesSymbol] = {};
- }
- element[pendingAttributesSymbol][attribute] = value;
- }
- },
-
-
- /**
- * Set/unset the class with the indicated name.
- *
- * This method exists primarily to handle the case where an element wants to
- * set a default property value that should be reflected as as class. An
- * important limitation of custom element consturctors is that they cannot
- * set attributes, including the `class` attribute. A call to
- * `toggleClass` during the constructor will be deferred until the element
- * is connected to the document.
- *
- * @param {string} className - The name of the class to set.
- * @param {object} value - True to set the class, false to remove it.
- */
- toggleClass: function toggleClass(element, className, value) {
- if (element[safeToSetAttributesSymbol]) {
- // Safe to set class immediately.
- (0, _toggleClass3.default)(element, className, value);
- } else {
- // Defer setting class until the first time we're connected.
- if (!element[pendingClassesSymbol]) {
- element[pendingClassesSymbol] = {};
- }
- element[pendingClassesSymbol][className] = value;
- }
- }
-};
-
-// Reflect the attribute to the given element.
-// If the value is null, remove the attribute.
-
-function setAttributeToElement(element, attributeName, value) {
- if (value === null || typeof value === 'undefined') {
- element.removeAttribute(attributeName);
- } else {
- var text = String(value);
- // Avoid recursive attributeChangedCallback calls.
- if (element.getAttribute(attributeName) !== text) {
- element.setAttribute(attributeName, value);
- }
- }
-}
-
-},{"./createSymbol":9,"./toggleClass":13}],12:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createSymbol = require('./createSymbol');
-
-var _createSymbol2 = _interopRequireDefault(_createSymbol);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-/**
- * A collection of Symbol objects for standard component properties and methods.
- *
- * These Symbol objects are used to allow mixins and a component to internally
- * communicate, without exposing these properties and methods in the component's
- * public API.
- *
- * To use these Symbol objects in your own component, include this module and
- * then create a property or method whose key is the desired Symbol.
- *
- * import 'SingleSelectionMixin' from 'basic-component-mixins/src/SingleSelectionMixin';
- * import 'symbols' from 'basic-component-mixins/src/symbols';
- *
- * class MyElement extends SingleSelectionMixin(HTMLElement) {
- * [symbols.itemSelected](item, selected) {
- * // This will be invoked whenever an item is selected/deselected.
- * }
- * }
- *
- * @module symbols
- */
-var symbols = {
-
- /**
- * Symbol for the `defaults` property.
- *
- * This property can be used to set or override defaults that will be applied
- * to a new component instance. When implementing this property, take care to
- * first acquire any defaults defined by the superclass. The standard idiom is
- * as follows:
- *
- * get [symbols.defaults]() {
- * const defaults = super[symbols.defaults] || {};
- * // Set or override default values here
- * defaults.customProperty = false;
- * return defaults;
- * }
- *
- * @var {object} defaults
- */
- defaults: (0, _createSymbol2.default)('defaults'),
-
- /**
- * Symbol for the `dragging` property.
- *
- * Components like carousels often define animated CSS transitions for
- * sliding effects. Such a transition should usually *not* be applied while
- * the user is dragging, because a CSS animation will introduce a lag that
- * makes the swipe feel sluggish. Instead, as long as the user is dragging
- * with their finger down, the transition should be suppressed. When the
- * user releases their finger, the transition can be restored, allowing the
- * animation to show the carousel sliding into its final position.
- *
- * @type {boolean} true if a drag is in progress, false if not.
- */
- dragging: (0, _createSymbol2.default)('dragging'),
-
- /**
- * Symbol for the `goDown` method.
- *
- * This method is invoked when the user wants to go/navigate down.
- *
- * @function goDown
- */
- goDown: (0, _createSymbol2.default)('goDown'),
-
- /**
- * Symbol for the `goEnd` method.
- *
- * This method is invoked when the user wants to go/navigate to the end (e.g.,
- * of a list).
- *
- * @function goEnd
- */
- goEnd: (0, _createSymbol2.default)('goEnd'),
-
- /**
- * Symbol for the `goLeft` method.
- *
- * This method is invoked when the user wants to go/navigate left.
- *
- * @function goLeft
- */
- goLeft: (0, _createSymbol2.default)('goLeft'),
-
- /**
- * Symbol for the `goRight` method.
- *
- * This method is invoked when the user wants to go/navigate right.
- *
- * @function goRight
- */
- goRight: (0, _createSymbol2.default)('goRight'),
-
- /**
- * Symbol for the `goStart` method.
- *
- * This method is invoked when the user wants to go/navigate to the start
- * (e.g., of a list).
- *
- * @function goStart
- */
- goStart: (0, _createSymbol2.default)('goStart'),
-
- /**
- * Symbol for the `goUp` method.
- *
- * This method is invoked when the user wants to go/navigate up.
- *
- * @function goUp
- */
- goUp: (0, _createSymbol2.default)('goUp'),
-
- /**
- * Symbol for the `itemAdded` method.
- *
- * This method is invoked when a new item is added to a list.
- *
- * @function itemAdded
- * @param {HTMLElement} item - the item being selected/deselected
- */
- itemAdded: (0, _createSymbol2.default)('itemAdded'),
-
- /**
- * Symbol for the `itemsChanged` method.
- *
- * This method is invoked when the underlying contents change. It is also
- * invoked on component initialization – since the items have "changed" from
- * being nothing.
- */
- itemsChanged: (0, _createSymbol2.default)('itemsChanged'),
-
- /**
- * Symbol for the `itemSelected` method.
- *
- * This method is invoked when an item becomes selected or deselected.
- *
- * @function itemSelected
- * @param {HTMLElement} item - the item being selected/deselected
- * @param {boolean} selected - true if the item is selected, false if not
- */
- itemSelected: (0, _createSymbol2.default)('itemSelected'),
-
- /**
- * Symbol for the `keydown` method.
- *
- * This method is invoked when an element receives a `keydown` event.
- *
- * @function keydown
- * @param {KeyboardEvent} event - the event being processed
- */
- keydown: (0, _createSymbol2.default)('keydown'),
-
- /**
- * Symbol for the `template` property.
- *
- * This property returns a component's template.
- *
- * @type {string|HTMLElement}
- */
- template: (0, _createSymbol2.default)('template')
-};
-
-exports.default = symbols;
-
-},{"./createSymbol":9}],13:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-exports.default = toggleClass;
-/**
- * Helper function for standard classList.toggle() behavior on old browsers,
- * namely IE 11.
- *
- * The standard
- * [classlist](https://developer.mozilla.org/en-US/docs/Web/API/Element/classList)
- * object has a `toggle()` function that supports a second Boolean parameter
- * that can be used to succinctly turn a class on or off. This feature is often
- * useful in designing custom elements, which may want to externally reflect
- * component state in a CSS class that can be used for styling purposes.
- *
- * Unfortunately, IE 11 does not support the Boolean parameter to
- * `classList.toggle()`. This helper function behaves like the standard
- * `toggle()`, including support for the Boolean parameter, so that it can be
- * used even on IE 11.
- *
- * @function toggleClass
- * @param {HTMLElement} element - The element to modify
- * @param {string} className - The class to add/remove
- * @param {boolean} [force] - Force the class to be added (if true) or removed
- * (if false)
- */
-function toggleClass(element, className, force) {
- var classList = element.classList;
- var addClass = typeof force === 'undefined' ? !classList.contains(className) : force;
- if (addClass) {
- classList.add(className);
- } else {
- classList.remove(className);
- }
- return addClass;
-}
-
-},{}],14:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _AttributeMarshallingMixin = require('../../basic-component-mixins/src/AttributeMarshallingMixin');
-
-var _AttributeMarshallingMixin2 = _interopRequireDefault(_AttributeMarshallingMixin);
-
-var _ComposableMixin = require('../../basic-component-mixins/src/ComposableMixin');
-
-var _ComposableMixin2 = _interopRequireDefault(_ComposableMixin);
-
-var _DistributedChildrenMixin = require('../../basic-component-mixins/src/DistributedChildrenMixin');
-
-var _DistributedChildrenMixin2 = _interopRequireDefault(_DistributedChildrenMixin);
-
-var _ShadowElementReferencesMixin = require('../../basic-component-mixins/src/ShadowElementReferencesMixin');
-
-var _ShadowElementReferencesMixin2 = _interopRequireDefault(_ShadowElementReferencesMixin);
-
-var _ShadowTemplateMixin = require('../../basic-component-mixins/src/ShadowTemplateMixin');
-
-var _ShadowTemplateMixin2 = _interopRequireDefault(_ShadowTemplateMixin);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-/**
- * A sample general-purpose base class for defining custom elements that mixes
- * in some common features: template stamping into a shadow root, shadow element
- * references, marshalling attributes to properties, and retrieving the children
- * distributed to a component.
- *
- * This base class is not special in any way, and is defined only as a
- * convenient shorthand for applying the mixins listed above. You can use this
- * class as a base class for your own elements, or easily create your own base
- * class by applying the same set of mixins.
- *
- * The ElementBase base class does not register itself as a custom element with
- * the browser, and hence cannot be independently instantiated.
- *
- * @mixes AttributeMarshallingMixin
- * @mixes ComposableMixin
- * @mixes DistributedChildrenMixin
- * @mixes ShadowElementReferencesMixin
- * @mixes ShadowTemplateMixin
- */
-var ElementBase = function (_ComposableMixin$comp) {
- _inherits(ElementBase, _ComposableMixin$comp);
-
- function ElementBase() {
- _classCallCheck(this, ElementBase);
-
- return _possibleConstructorReturn(this, (ElementBase.__proto__ || Object.getPrototypeOf(ElementBase)).apply(this, arguments));
- }
-
- return ElementBase;
-}((0, _ComposableMixin2.default)(HTMLElement).compose(_ShadowTemplateMixin2.default, // before node finding, so shadow root is populated
-_ShadowElementReferencesMixin2.default, // before marshalling, so properties can use refs
-_AttributeMarshallingMixin2.default, _DistributedChildrenMixin2.default));
-
-exports.default = ElementBase;
-
-},{"../../basic-component-mixins/src/AttributeMarshallingMixin":1,"../../basic-component-mixins/src/ComposableMixin":2,"../../basic-component-mixins/src/DistributedChildrenMixin":5,"../../basic-component-mixins/src/ShadowElementReferencesMixin":6,"../../basic-component-mixins/src/ShadowTemplateMixin":7}],15:[function(require,module,exports){
-'use strict';
-
-var _Modes = require('./src/Modes');
-
-var _Modes2 = _interopRequireDefault(_Modes);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-window.Basic = window.Basic || {}; /*
- * This file is transpiled to create an ES5-compatible distribution in which
- * the package's main feature(s) are available via the window.Basic global.
- * If you're already using ES6 yourself, ignore this file, and instead import
- * the source file(s) you want from the src folder.
- */
-
-window.Basic.Modes = _Modes2.default;
-
-},{"./src/Modes":16}],16:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
-
-var _get = function get(object, property, receiver) { if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { return get(parent, property, receiver); } } else if ("value" in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } };
-
-var _ElementBase = require('../../basic-element-base/src/ElementBase');
-
-var _ElementBase2 = _interopRequireDefault(_ElementBase);
-
-var _DistributedChildrenContentMixin = require('../../basic-component-mixins/src/DistributedChildrenContentMixin');
-
-var _DistributedChildrenContentMixin2 = _interopRequireDefault(_DistributedChildrenContentMixin);
-
-var _ContentItemsMixin = require('../../basic-component-mixins/src/ContentItemsMixin');
-
-var _ContentItemsMixin2 = _interopRequireDefault(_ContentItemsMixin);
-
-var _SingleSelectionMixin = require('../../basic-component-mixins/src/SingleSelectionMixin');
-
-var _SingleSelectionMixin2 = _interopRequireDefault(_SingleSelectionMixin);
-
-var _symbols = require('../../basic-component-mixins/src/symbols');
-
-var _symbols2 = _interopRequireDefault(_symbols);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-var base = _ElementBase2.default.compose(_ContentItemsMixin2.default, _DistributedChildrenContentMixin2.default, _SingleSelectionMixin2.default);
-
-/**
- * Shows exactly one child element at a time. This can be useful, for example,
- * if a given UI element has multiple modes that present substantially different
- * elements.
- *
- * The transition between child elements is instantenous. If you'd like the
- * transition to be accompanied by visible animated effects, see
- * [basic-animation-stage](../basic-animation-stage).
- *
- * This component doesn't provide any UI for changing which mode is shown.
- *
- * @extends ElementBase
- * @mixes ContentItemsMixin
- * @mixes DistributedChildrenContentMixin
- * @mixes SingleSelectionMixin
- */
-
-var Modes = function (_base) {
- _inherits(Modes, _base);
-
- function Modes() {
- _classCallCheck(this, Modes);
-
- return _possibleConstructorReturn(this, (Modes.__proto__ || Object.getPrototypeOf(Modes)).apply(this, arguments));
- }
-
- _createClass(Modes, [{
- key: _symbols2.default.itemSelected,
- value: function value(item, selected) {
- if (_get(Modes.prototype.__proto__ || Object.getPrototypeOf(Modes.prototype), _symbols2.default.itemSelected, this)) {
- _get(Modes.prototype.__proto__ || Object.getPrototypeOf(Modes.prototype), _symbols2.default.itemSelected, this).call(this, item, selected);
- }
- item.style.display = selected ? '' : 'none';
- item.setAttribute('aria-hidden', !selected);
- }
- }, {
- key: _symbols2.default.defaults,
- get: function get() {
- var defaults = _get(Modes.prototype.__proto__ || Object.getPrototypeOf(Modes.prototype), _symbols2.default.defaults, this) || {};
- defaults.selectionRequired = true;
- return defaults;
- }
- }, {
- key: _symbols2.default.template,
- get: function get() {
- return ' ';
- }
- }]);
-
- return Modes;
-}(base);
-
-customElements.define('basic-modes', Modes);
-exports.default = Modes;
-
-},{"../../basic-component-mixins/src/ContentItemsMixin":3,"../../basic-component-mixins/src/DistributedChildrenContentMixin":4,"../../basic-component-mixins/src/SingleSelectionMixin":8,"../../basic-component-mixins/src/symbols":12,"../../basic-element-base/src/ElementBase":14}]},{},[15])
-//# sourceMappingURL=data:application/json;charset:utf-8;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbIm5vZGVfbW9kdWxlcy9ncnVudC1icm93c2VyaWZ5L25vZGVfbW9kdWxlcy9icm93c2VyLXBhY2svX3ByZWx1ZGUuanMiLCJwYWNrYWdlcy9iYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy9BdHRyaWJ1dGVNYXJzaGFsbGluZ01peGluLmpzIiwicGFja2FnZXMvYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvQ29tcG9zYWJsZU1peGluLmpzIiwicGFja2FnZXMvYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvQ29udGVudEl0ZW1zTWl4aW4uanMiLCJwYWNrYWdlcy9iYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy9EaXN0cmlidXRlZENoaWxkcmVuQ29udGVudE1peGluLmpzIiwicGFja2FnZXMvYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvRGlzdHJpYnV0ZWRDaGlsZHJlbk1peGluLmpzIiwicGFja2FnZXMvYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvU2hhZG93RWxlbWVudFJlZmVyZW5jZXNNaXhpbi5qcyIsInBhY2thZ2VzL2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL1NoYWRvd1RlbXBsYXRlTWl4aW4uanMiLCJwYWNrYWdlcy9iYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy9TaW5nbGVTZWxlY3Rpb25NaXhpbi5qcyIsInBhY2thZ2VzL2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL2NyZWF0ZVN5bWJvbC5qcyIsInBhY2thZ2VzL2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL21pY3JvdGFzay5qcyIsInBhY2thZ2VzL2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL3NhZmVBdHRyaWJ1dGVzLmpzIiwicGFja2FnZXMvYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvc3ltYm9scy5qcyIsInBhY2thZ2VzL2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL3RvZ2dsZUNsYXNzLmpzIiwicGFja2FnZXMvYmFzaWMtZWxlbWVudC1iYXNlL3NyYy9FbGVtZW50QmFzZS5qcyIsInBhY2thZ2VzL2Jhc2ljLW1vZGVzL2dsb2JhbHMuanMiLCJwYWNrYWdlcy9iYXNpYy1tb2Rlcy9zcmMvTW9kZXMuanMiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6IkFBQUE7Ozs7Ozs7Ozs7O0FDQUE7Ozs7Ozs7Ozs7OztBQUdBO0FBQ0EsSUFBTSwyQkFBMkIsRUFBakM7QUFDQSxJQUFNLDRCQUE0QixFQUFsQzs7QUFHQTs7a0JBQ2UsVUFBQyxJQUFELEVBQVU7O0FBRXZCOzs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7OztBQUZ1QixNQXFDakIsb0JBckNpQjtBQUFBOztBQUFBO0FBQUE7O0FBQUE7QUFBQTs7QUFBQTtBQUFBOzs7QUF1Q3JCOzs7QUF2Q3FCLCtDQTBDSSxhQTFDSixFQTBDbUIsUUExQ25CLEVBMEM2QixRQTFDN0IsRUEwQ3VDO0FBQzFELHVKQUFvQztBQUFFO0FBQW1DO0FBQ3pFLFlBQU0sZUFBZSx3QkFBd0IsYUFBeEIsQ0FBckI7QUFDQTtBQUNBO0FBQ0EsWUFBSSxnQkFBZ0IsSUFBaEIsSUFBd0IsRUFBRSxnQkFBZ0IsWUFBWSxTQUE5QixDQUE1QixFQUFzRTtBQUNwRSxlQUFLLFlBQUwsSUFBcUIsUUFBckI7QUFDRDtBQUNGO0FBbERvQjtBQUFBO0FBQUEsMENBb0REO0FBQ2xCLGdKQUE2QjtBQUFFO0FBQTRCO0FBQzNELGlDQUFlLFNBQWYsQ0FBeUIsSUFBekI7QUFDRDtBQXZEb0I7QUFBQTs7O0FBNkRyQjs7Ozs7Ozs7Ozs7O0FBN0RxQix1Q0F5RUosU0F6RUksRUF5RU8sS0F6RVAsRUF5RWM7QUFDakMsZUFBTyx5QkFBZSxZQUFmLENBQTRCLElBQTVCLEVBQWtDLFNBQWxDLEVBQTZDLEtBQTdDLENBQVA7QUFDRDs7QUFFRDs7Ozs7Ozs7Ozs7Ozs7QUE3RXFCO0FBQUE7QUFBQSxtQ0EwRlIsU0ExRlEsRUEwRkcsS0ExRkgsRUEwRlU7QUFDN0IsZUFBTyx5QkFBZSxXQUFmLENBQTJCLElBQTNCLEVBQWlDLFNBQWpDLEVBQTRD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NEIsSUFBNUIsRUFBa0MsUUFBbEM7QUFBOEM7QUFDakYsV0FBSyxLQUFMLENBQVcsT0FBWCxHQUFxQixXQUFXLEVBQVgsR0FBZ0IsTUFBckM7QUFDQSxXQUFLLFlBQUwsQ0FBa0IsYUFBbEIsRUFBaUMsQ0FBQyxRQUFsQztBQUNEOztTQVZJLGtCQUFRLFE7d0JBQVk7QUFDdkIsVUFBTSxXQUFXLDBFQUFNLGtCQUFRLFFBQWQsV0FBMkIsRUFBNUM7QUFDQSxlQUFTLGlCQUFULEdBQTZCLElBQTdCO0FBQ0EsYUFBTyxRQUFQO0FBQ0Q7O1NBUUksa0JBQVEsUTt3QkFBWTtBQUN2QjtBQUNEOzs7O0VBaEJpQixJOztBQXFCcEIsZUFBZSxNQUFmLENBQXNCLGFBQXRCLEVBQXFDLEtBQXJDO2tCQUNlLEsiLCJmaWxlIjoiZ2VuZXJhdGVkLmpzIiwic291cmNlUm9vdCI6IiIsInNvdXJjZXNDb250ZW50IjpbIihmdW5jdGlvbiBlKHQsbixyKXtmdW5jdGlvbiBzKG8sdSl7aWYoIW5bb10pe2lmKCF0W29dKXt2YXIgYT10eXBlb2YgcmVxdWlyZT09XCJmdW5jdGlvblwiJiZyZXF1aXJlO2lmKCF1JiZhKXJldHVybiBhKG8sITApO2lmKGkpcmV0dXJuIGkobywhMCk7dmFyIGY9bmV3IEVycm9yKFwiQ2Fubm90IGZpbmQgbW9kdWxlICdcIitvK1wiJ1wiKTt0aHJvdyBmLmNvZGU9XCJNT0RVTEVfTk9UX0ZPVU5EXCIsZn12YXIgbD1uW29dPXtleHBvcnRzOnt9fTt0W29dWzBdLmNhbGwobC5leHBvcnRzLGZ1bmN0aW9uKGUpe3ZhciBuPXRbb11bMV1bZV07cmV0dXJuIHMobj9uOmUpfSxsLGwuZXhwb3J0cyxlLHQsbixyKX1yZXR1cm4gbltvXS5leHBvcnRzfXZhciBpPXR5cGVvZiByZXF1aXJlPT1cImZ1bmN0aW9uXCImJnJlcXVpcmU7Zm9yKHZhciBvPTA7bzxyLmxlbmd0aDtvKyspcyhyW29dKTtyZXR1cm4gc30pIiwiaW1wb3J0IHNhZmVBdHRyaWJ1dGVzIGZyb20gJy4vc2FmZUF0dHJpYnV0ZXMnO1xuXG5cbi8vIE1lbW9pemVkIG1hcHMgb2YgYXR0cmlidXRlIHRvIHByb3BlcnR5IG5hbWVzIGFuZCB2aWNlIHZlcnNhLlxuY29uc3QgYXR0cmlidXRlVG9Qcm9wZXJ0eU5hbWVzID0ge307XG5jb25zdCBwcm9wZXJ0eU5hbWVzVG9BdHRyaWJ1dGVzID0ge307XG5cblxuLyogRXhwb3J0ZWQgZnVuY3Rpb24gZXh0ZW5kcyBhIGJhc2UgY2xhc3Mgd2l0aCBBdHRyaWJ1dGVNYXJzaGFsbGluZy4gKi9cbmV4cG9ydCBkZWZhdWx0IChiYXNlKSA9PiB7XG5cbiAgLyoqXG4gICAqIE1peGluIHdoaWNoIG1hcnNoYWxscyBhdHRyaWJ1dGVzIHRvIHByb3BlcnRpZXMgYW5kIHZpY2UgdmVyc2EuXG4gICAqXG4gICAqIElmIHlvdXIgY29tcG9uZW50IGV4cG9zZXMgYSBzZXR0ZXIgZm9yIGEgcHJvcGVydHksIGl0J3MgZ2VuZXJhbGx5IGEgZ29vZFxuICAgKiBpZGVhIHRvIGxldCBkZXZzIHVzaW5nIHlvdXIgY29tcG9uZW50IGJlIGFibGUgdG8gc2V0IHRoYXQgcHJvcGVydHkgaW4gSFRNTFxuICAgKiB2aWEgYW4gZWxlbWVudCBhdHRyaWJ1dGUuIFlvdSBjYW4gY29kZSB0aGF0IHlvdXJzZWxmIGJ5IHdyaXRpbmcgYW5cbiAgICogYGF0dHJpYnV0ZUNoYW5nZWRDYWxsYmFja2AsIG9yIHlvdSBjYW4gdXNlIHRoaXMgbWl4aW4gdG8gZ2V0IGEgZGVncmVlIG9mXG4gICAqIGF1dG9tYXRpYyBzdXBwb3J0LlxuICAgKlxuICAgKiBUaGlzIG1peGluIGltcGxlbWVudHMgYW4gYGF0dHJpYnV0ZUNoYW5nZWRDYWxsYmFja2AgdGhhdCB3aWxsIGF0dGVtcHQgdG9cbiAgICogY29udmVydCBhIGNoYW5nZSBpbiBhbiBlbGVtZW50IGF0dHJpYnV0ZSBpbnRvIGEgY2FsbCB0byB0aGUgY29ycmVzcG9uZGluZ1xuICAgKiBwcm9wZXJ0eSBzZXR0ZXIuIEF0dHJpYnV0ZXMgdHlwaWNhbGx5IGZvbGxvdyBoeXBoZW5hdGVkIG5hbWVzIChcImZvby1iYXJcIiksXG4gICAqIHdoZXJlYXMgcHJvcGVydGllcyB0eXBpY2FsbHkgdXNlIGNhbWVsQ2FzZSBuYW1lcyAoXCJmb29CYXJcIikuIFRoaXMgbWl4aW5cbiAgICogcmVzcGVjdHMgdGhhdCBjb252ZW50aW9uLCBhdXRvbWF0aWNhbGx5IG1hcHBpbmcgdGhlIGh5cGhlbmF0ZWQgYXR0cmlidXRlXG4gICAqIG5hbWUgdG8gdGhlIGNvcnJlc3BvbmRpbmcgY2FtZWxDYXNlIHByb3BlcnR5IG5hbWUuXG4gICAqXG4gICAqIEV4YW1wbGU6IFlvdSBkZWZpbmUgYSBjb21wb25lbnQgdXNpbmcgdGhpcyBtaXhpbjpcbiAgICpcbiAgICogICAgIGNsYXNzIE15RWxlbWVudCBleHRlbmRzIEF0dHJpYnV0ZU1hcnNoYWxsaW5nTWl4aW4oSFRNTEVsZW1lbnQpIHtcbiAgICogICAgICAgZ2V0IGZvb0JhcigpIHsgcmV0dXJuIHRoaXMuX2Zvb0JhcjsgfVxuICAgKiAgICAgICBzZXQgZm9vQmFyKHZhbHVlKSB7IHRoaXMuX2Zvb0JhciA9IHZhbHVlOyB9XG4gICAqICAgICB9XG4gICAqICAgICBjdXN0b21FbGVtZW50cy5kZWZpbmUoJ215LWVsZW1lbnQnLCBNeUVsZW1lbnQpO1xuICAgKlxuICAgKiBJZiBzb21lb25lIHRoZW4gaW5zdGFudGlhdGVzIHlvdXIgY29tcG9uZW50IGluIEhUTUw6XG4gICAqXG4gICAqICAgICA8bXktZWxlbWVudCBmb28tYmFyPVwiSGVsbG9cIj48L215LWVsZW1lbnQ+XG4gICAqXG4gICAqIFRoZW4sIGFmdGVyIHRoZSBlbGVtZW50IGhhcyBiZWVuIHVwZ3JhZGVkLCB0aGUgYGZvb0JhcmAgc2V0dGVyIHdpbGxcbiAgICogYXV0b21hdGljYWxseSBiZSBpbnZva2VkIHdpdGggdGhlIGluaXRpYWwgdmFsdWUgXCJIZWxsb1wiLlxuICAgKlxuICAgKiBGb3IgdGhlIHRpbWUgYmVpbmcsIHRoaXMgbWl4aW4gb25seSBzdXBwb3J0cyBzdHJpbmctdmFsdWVkIHByb3BlcnRpZXMuXG4gICAqIElmIHlvdSdkIGxpa2UgdG8gY29udmVydCBzdHJpbmcgYXR0cmlidXRlcyB0byBvdGhlciB0eXBlcyAobnVtYmVycyxcbiAgICogYm9vbGVhbnMpLCB5b3UgbmVlZCB0byBpbXBsZW1lbnQgYGF0dHJpYnV0ZUNoYW5nZWRDYWxsYmFja2AgeW91cnNlbGYuXG4gICAqL1xuICBjbGFzcyBBdHRyaWJ1dGVNYXJzaGFsbGluZyBleHRlbmRzIGJhc2Uge1xuXG4gICAgLypcbiAgICAgKiBIYW5kbGUgYSBjaGFuZ2UgdG8gdGhlIGF0dHJpYnV0ZSB3aXRoIHRoZSBnaXZlbiBuYW1lLlxuICAgICAqL1xuICAgIGF0dHJpYnV0ZUNoYW5nZWRDYWxsYmFjayhhdHRyaWJ1dGVOYW1lLCBvbGRWYWx1ZSwgbmV3VmFsdWUpIHtcbiAgICAgIGlmIChzdXBlci5hdHRyaWJ1dGVDaGFuZ2VkQ2FsbGJhY2spIHsgc3VwZXIuYXR0cmlidXRlQ2hhbmdlZENhbGxiYWNrKCk7IH1cbiAgICAgIGNvbnN0IHByb3BlcnR5TmFtZSA9IGF0dHJpYnV0ZVRvUHJvcGVydHlOYW1lKGF0dHJpYnV0ZU5hbWUpO1xuICAgICAgLy8gSWYgdGhlIGF0dHJpYnV0ZSBuYW1lIGNvcnJlc3BvbmRzIHRvIGEgcHJvcGVydHkgbmFtZSwgc2V0IHRoZSBwcm9wZXJ0eS5cbiAgICAgIC8vIElnbm9yZSBzdGFuZGFyZCBIVE1MRWxlbWVudCBwcm9wZXJ0aWVzIGhhbmRsZWQgYnkgdGhlIERPTS5cbiAgICAgIGlmIChwcm9wZXJ0eU5hbWUgaW4gdGhpcyAmJiAhKHByb3BlcnR5TmFtZSBpbiBIVE1MRWxlbWVudC5wcm90b3R5cGUpKSB7XG4gICAgICAgIHRoaXNbcHJvcGVydHlOYW1lXSA9IG5ld1ZhbHVlO1xuICAgICAgfVxuICAgIH1cblxuICAgIGNvbm5lY3RlZENhbGxiYWNrKCkge1xuICAgICAgaWYgKHN1cGVyLmNvbm5lY3RlZENhbGxiYWNrKSB7IHN1cGVyLmNvbm5lY3RlZENhbGxiYWNrKCk7IH1cbiAgICAgIHNhZmVBdHRyaWJ1dGVzLmNvbm5lY3RlZCh0aGlzKTtcbiAgICB9XG5cbiAgICBzdGF0aWMgZ2V0IG9ic2VydmVkQXR0cmlidXRlcygpIHtcbiAgICAgIHJldHVybiBhdHRyaWJ1dGVzRm9yQ2xhc3ModGhpcyk7XG4gICAgfVxuXG4gICAgLyoqXG4gICAgICogU2V0L3Vuc2V0IHRoZSBhdHRyaWJ1dGUgd2l0aCB0aGUgaW5kaWNhdGVkIG5hbWUuXG4gICAgICpcbiAgICAgKiBUaGlzIG1ldGhvZCBleGlzdHMgcHJpbWFyaWx5IHRvIGhhbmRsZSB0aGUgY2FzZSB3aGVyZSBhbiBlbGVtZW50IHdhbnRzIHRvXG4gICAgICogc2V0IGEgZGVmYXVsdCBwcm9wZXJ0eSB2YWx1ZSB0aGF0IHNob3VsZCBiZSByZWZsZWN0ZWQgYXMgYW4gYXR0cmlidXRlLiBBblxuICAgICAqIGltcG9ydGFudCBsaW1pdGF0aW9uIG9mIGN1c3RvbSBlbGVtZW50IGNvbnN0dXJjdG9ycyBpcyB0aGF0IHRoZXkgY2Fubm90XG4gICAgICogc2V0IGF0dHJpYnV0ZXMuIEEgY2FsbCB0byBgcmVmbGVjdEF0dHJpYnV0ZWAgZHVyaW5nIHRoZSBjb25zdHJ1Y3RvciB3aWxsXG4gICAgICogYmUgZGVmZXJyZWQgdW50aWwgdGhlIGVsZW1lbnQgaXMgY29ubmVjdGVkIHRvIHRoZSBkb2N1bWVudC5cbiAgICAgKlxuICAgICAqIEBwYXJhbSB7c3RyaW5nfSBhdHRyaWJ1dGUgLSBUaGUgbmFtZSBvZiB0aGUgKmF0dHJpYnV0ZSogKG5vdCBwcm9wZXJ0eSkgdG8gc2V0LlxuICAgICAqIEBwYXJhbSB7b2JqZWN0fSB2YWx1ZSAtIFRoZSB2YWx1ZSB0byBzZXQuIElmIG51bGwsIHRoZSBhdHRyaWJ1dGUgd2lsbCBiZSByZW1vdmVkLlxuICAgICAqL1xuICAgIHJlZmxlY3RBdHRyaWJ1dGUoYXR0cmlidXRlLCB2YWx1ZSkge1xuICAgICAgcmV0dXJuIHNhZmVBdHRyaWJ1dGVzLnNldEF0dHJpYnV0ZSh0aGlzLCBhdHRyaWJ1dGUsIHZhbHVlKTtcbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBTZXQvdW5zZXQgdGhlIGNsYXNzIHdpdGggdGhlIGluZGljYXRlZCBuYW1lLlxuICAgICAqXG4gICAgICogVGhpcyBtZXRob2QgZXhpc3RzIHByaW1hcmlseSB0byBoYW5kbGUgdGhlIGNhc2Ugd2hlcmUgYW4gZWxlbWVudCB3YW50cyB0b1xuICAgICAqIHNldCBhIGRlZmF1bHQgcHJvcGVydHkgdmFsdWUgdGhhdCBzaG91bGQgYmUgcmVmbGVjdGVkIGFzIGFzIGNsYXNzLiBBblxuICAgICAqIGltcG9ydGFudCBsaW1pdGF0aW9uIG9mIGN1c3RvbSBlbGVtZW50IGNvbnN0dXJjdG9ycyBpcyB0aGF0IHRoZXkgY2Fubm90XG4gICAgICogc2V0IGF0dHJpYnV0ZXMsIGluY2x1ZGluZyB0aGUgYGNsYXNzYCBhdHRyaWJ1dGUuIEEgY2FsbCB0b1xuICAgICAqIGByZWZsZWN0Q2xhc3NgIGR1cmluZyB0aGUgY29uc3RydWN0b3Igd2lsbCBiZSBkZWZlcnJlZCB1bnRpbCB0aGUgZWxlbWVudFxuICAgICAqIGlzIGNvbm5lY3RlZCB0byB0aGUgZG9jdW1lbnQuXG4gICAgICpcbiAgICAgKiBAcGFyYW0ge3N0cmluZ30gY2xhc3NOYW1lIC0gVGhlIG5hbWUgb2YgdGhlIGNsYXNzIHRvIHNldC5cbiAgICAgKiBAcGFyYW0ge29iamVjdH0gdmFsdWUgLSBUcnVlIHRvIHNldCB0aGUgY2xhc3MsIGZhbHNlIHRvIHJlbW92ZSBpdC5cbiAgICAgKi9cbiAgICByZWZsZWN0Q2xhc3MoY2xhc3NOYW1lLCB2YWx1ZSkge1xuICAgICAgcmV0dXJuIHNhZmVBdHRyaWJ1dGVzLnRvZ2dsZUNsYXNzKHRoaXMsIGNsYXNzTmFtZSwgdmFsdWUpO1xuICAgIH1cblxuICB9XG5cbiAgcmV0dXJuIEF0dHJpYnV0ZU1hcnNoYWxsaW5nO1xufTtcblxuXG4vLyBDb252ZXJ0IGh5cGhlbmF0ZWQgZm9vLWJhciBhdHRyaWJ1dGUgbmFtZSB0byBjYW1lbCBjYXNlIGZvb0JhciBwcm9wZXJ0eSBuYW1lLlxuZnVuY3Rpb24gYXR0cmlidXRlVG9Qcm9wZXJ0eU5hbWUoYXR0cmlidXRlTmFtZSkge1xuICBsZXQgcHJvcGVydHlOYW1lID0gYXR0cmlidXRlVG9Qcm9wZXJ0eU5hbWVzW2F0dHJpYnV0ZU5hbWVdO1xuICBpZiAoIXByb3BlcnR5TmFtZSkge1xuICAgIC8vIENvbnZlcnQgYW5kIG1lbW9pemUuXG4gICAgY29uc3QgaHlwZW5SZWdFeCA9IC8tKFthLXpdKS9nO1xuICAgIHByb3BlcnR5TmFtZSA9IGF0dHJpYnV0ZU5hbWUucmVwbGFjZShoeXBlblJlZ0V4LFxuICAgICAgICBtYXRjaCA9PiBtYXRjaFsxXS50b1VwcGVyQ2FzZSgpKTtcbiAgICBhdHRyaWJ1dGVUb1Byb3BlcnR5TmFtZXNbYXR0cmlidXRlTmFtZV0gPSBwcm9wZXJ0eU5hbWU7XG4gIH1cbiAgcmV0dXJuIHByb3BlcnR5TmFtZTtcbn1cblxuZnVuY3Rpb24gYXR0cmlidXRlc0ZvckNsYXNzKGNsYXNzRm4pIHtcblxuICAvLyBXZSB0cmVhdCB0aGUgZWxlbWVudCBiYXNlIGNsYXNzZXMgYXMgaWYgdGhleSBoYXZlIG5vIGF0dHJpYnV0ZXMsIHNpbmNlIHdlXG4gIC8vIGRvbid0IHdhbnQgdG8gcmVjZWl2ZSBhdHRyaWJ1dGVDaGFuZ2VkQ2FsbGJhY2sgZm9yIHRoZW0uXG4gIGlmIChjbGFzc0ZuID09PSBIVE1MRWxlbWVudCB8fCBjbGFzc0ZuID09PSBPYmplY3QpIHtcbiAgICByZXR1cm4gW107XG4gIH1cblxuICAvLyBHZXQgYXR0cmlidXRlcyBmb3IgcGFyZW50IGNsYXNzLlxuICBjb25zdCBiYXNlQ2xhc3MgPSBPYmplY3QuZ2V0UHJvdG90eXBlT2YoY2xhc3NGbi5wcm90b3R5cGUpLmNvbnN0cnVjdG9yO1xuICBjb25zdCBiYXNlQXR0cmlidXRlcyA9IGF0dHJpYnV0ZXNGb3JDbGFzcyhiYXNlQ2xhc3MpO1xuXG4gIC8vIEdldCBhdHRyaWJ1dGVzIGZvciB0aGlzIGNsYXNzLlxuICBjb25zdCBwcm9wZXJ0eU5hbWVzID0gT2JqZWN0LmdldE93blByb3BlcnR5TmFtZXMoY2xhc3NGbi5wcm90b3R5cGUpO1xuICBjb25zdCBzZXR0ZXJOYW1lcyA9IHByb3BlcnR5TmFtZXMuZmlsdGVyKHByb3BlcnR5TmFtZSA9PlxuICAgIHR5cGVvZiBPYmplY3QuZ2V0T3duUHJvcGVydHlEZXNjcmlwdG9yKFxuICAgICAgICBjbGFzc0ZuLnByb3RvdHlwZSwgcHJvcGVydHlOYW1lKS5zZXQgPT09ICdmdW5jdGlvbicpO1xuICBjb25zdCBhdHRyaWJ1dGVzID0gc2V0dGVyTmFtZXMubWFwKHNldHRlck5hbWUgPT5cbiAgICAgIHByb3BlcnR5TmFtZVRvQXR0cmlidXRlKHNldHRlck5hbWUpKTtcblxuICAvLyBNZXJnZS5cbiAgY29uc3QgZGlmZiA9IGF0dHJpYnV0ZXMuZmlsdGVyKGF0dHJpYnV0ZSA9PlxuICAgICAgYmFzZUF0dHJpYnV0ZXMuaW5kZXhPZihhdHRyaWJ1dGUpIDwgMCk7XG4gIHJldHVybiBiYXNlQXR0cmlidXRlcy5jb25jYXQoZGlmZik7XG59XG5cbi8vIENvbnZlcnQgYSBjYW1lbCBjYXNlIGZvb0JhciBwcm9wZXJ0eSBuYW1lIHRvIGEgaHlwaGVuYXRlZCBmb28tYmFyIGF0dHJpYnV0ZS5cbmZ1bmN0aW9uIHByb3BlcnR5TmFtZVRvQXR0cmlidXRlKHByb3BlcnR5TmFtZSkge1xuICBsZXQgYXR0cmlidXRlID0gcHJvcGVydHlOYW1lc1RvQXR0cmlidXRlc1twcm9wZXJ0eU5hbWVdO1xuICBpZiAoIWF0dHJpYnV0ZSkge1xuICAgIC8vIENvbnZlcnQgYW5kIG1lbW9pemUuXG4gICAgY29uc3QgdXBwZXJjYXNlUmVnRXggPSAvKFtBLVpdKS9nO1xuICAgIGF0dHJpYnV0ZSA9IHByb3BlcnR5TmFtZS5yZXBsYWNlKHVwcGVyY2FzZVJlZ0V4LCAnLSQxJykudG9Mb3dlckNhc2UoKTtcbiAgfVxuICByZXR1cm4gYXR0cmlidXRlO1xufVxuIiwiLyogRXhwb3J0ZWQgZnVuY3Rpb24gZXh0ZW5kcyBhIGJhc2UgY2xhc3Mgd2l0aCBDb21wb3NhYmxlLiAqL1xuZXhwb3J0IGRlZmF1bHQgKGJhc2UpID0+IHtcblxuICAvKipcbiAgICogTWl4aW4gdG8gbWFrZSBhIGNsYXNzIG1vcmUgZWFzaWx5IGNvbXBvc2FibGUgd2l0aCBvdGhlciBtaXhpbnMuXG4gICAqXG4gICAqIFRoaXMgbWl4aW4gY29udHJpYnV0ZXMgYSBgY29tcG9zZWAgbWV0aG9kIHRoYXQgYXBwbGllcyBhIHNldCBvZiBtaXhpblxuICAgKiBmdW5jdGlvbnMgYW5kIHJldHVybnMgdGhlIHJlc3VsdGluZyBuZXcgY2xhc3MuIFRoaXMgc3VnYXIgY2FuIG1ha2UgdGhlXG4gICAqIGFwcGxpY2F0aW9uIG9mIG1hbnkgbWl4aW5zIGF0IG9uY2UgZWFzaWVyIHRvIHJlYWQuXG4gICAqL1xuICBjbGFzcyBDb21wb3NhYmxlIGV4dGVuZHMgYmFzZSB7XG5cbiAgICAvKipcbiAgICAgKiBBcHBseSBhIHNldCBvZiBtaXhpbiBmdW5jdGlvbnMgb3IgbWl4aW4gb2JqZWN0cyB0byB0aGUgcHJlc2VudCBjbGFzcyBhbmRcbiAgICAgKiByZXR1cm4gdGhlIG5ldyBjbGFzcy5cbiAgICAgKlxuICAgICAqIEluc3RlYWQgb2Ygd3JpdGluZzpcbiAgICAgKlxuICAgICAqICAgICBsZXQgTXlDbGFzcyA9IE1peGluMShNaXhpbjIoTWl4aW4zKE1peGluNChNaXhpbjUoQmFzZUNsYXNzKSkpKSk7XG4gICAgICpcbiAgICAgKiBZb3UgY2FuIHdyaXRlOlxuICAgICAqXG4gICAgICogICAgIGxldCBNeUNsYXNzID0gQ29tcG9zYWJsZU1peGluKEJhc2VDbGFzcykuY29tcG9zZShcbiAgICAgKiAgICAgICBNaXhpbjEsXG4gICAgICogICAgICAgTWl4aW4yLFxuICAgICAqICAgICAgIE1peGluMyxcbiAgICAgKiAgICAgICBNaXhpbjQsXG4gICAgICogICAgICAgTWl4aW41XG4gICAgICogICAgICk7XG4gICAgICpcbiAgICAgKiBUaGlzIGZ1bmN0aW9uIGNhbiBhbHNvIHRha2UgbWl4aW4gb2JqZWN0cy4gQSBtaXhpbiBvYmplY3QgaXMganVzdCBhXG4gICAgICogc2hvcnRoYW5kIGZvciBhIG1peGluIGZ1bmN0aW9uIHRoYXQgY3JlYXRlcyBhIG5ldyBzdWJjbGFzcyB3aXRoIHRoZSBnaXZlblxuICAgICAqIG1lbWJlcnMuIFRoZSBtaXhpbiBvYmplY3QncyBtZW1iZXJzIGFyZSAqbm90KiBjb3BpZWQgZGlyZWN0bHkgb250byB0aGVcbiAgICAgKiBwcm90b3R5cGUgb2YgdGhlIGJhc2UgY2xhc3MsIGFzIHdpdGggdHJhZGl0aW9uYWwgbWl4aW5zLlxuICAgICAqXG4gICAgICogSW4gYWRkaXRpb24gdG8gcHJvdmlkaW5nIHN5bnRhY3RpYyBzdWdhciwgdGhpcyBtaXhpbiBjYW4gYmUgdXNlZCB0b1xuICAgICAqIGRlZmluZSBhIGNsYXNzIGluIEVTNSwgd2hpY2ggbGFja3MgRVM2J3MgYGNsYXNzYCBrZXl3b3JkLlxuICAgICAqXG4gICAgICogQHBhcmFtIHsuLi5taXhpbnN9IG1peGlucyAtIEEgc2V0IG9mIG1peGluIGZ1bmN0aW9ucyBvciBvYmplY3RzIHRvIGFwcGx5LlxuICAgICAqL1xuICAgIHN0YXRpYyBjb21wb3NlKC4uLm1peGlucykge1xuICAgICAgLy8gV2UgY3JlYXRlIGEgbmV3IHN1YmNsYXNzIGZvciBlYWNoIG1peGluIGluIHR1cm4uIFRoZSByZXN1bHQgYmVjb21lc1xuICAgICAgLy8gdGhlIGJhc2UgY2xhc3MgZXh0ZW5kZWQgYnkgYW55IHN1YnNlcXVlbnQgbWl4aW5zLiBJdCB0dXJucyBvdXQgdGhhdFxuICAgICAgLy8gd2UgY2FuIHVzZSBBcnJheS5yZWR1Y2UoKSB0byBjb25jaXNlbHkgZXhwcmVzcyB0aGlzLCB1c2luZyB0aGUgY3VycmVudFxuICAgICAgLy8gb2JqZWN0IGFzIHRoZSBzZWVkIGZvciByZWR1Y2UoKS5cbiAgICAgIHJldHVybiBtaXhpbnMucmVkdWNlKGNvbXBvc2VDbGFzcywgdGhpcyk7XG4gICAgfVxuXG4gIH1cblxuICByZXR1cm4gQ29tcG9zYWJsZTtcbn07XG5cblxuLy8gUHJvcGVydGllcyBkZWZpbmVkIGJ5IE9iamVjdCB0aGF0IHdlIGRvbid0IHdhbnQgdG8gbWl4aW4uXG5jb25zdCBOT05fTUlYQUJMRV9PQkpFQ1RfUFJPUEVSVElFUyA9IFtcbiAgJ2NvbnN0cnVjdG9yJ1xuXTtcblxuLypcbiAqIEFwcGx5IHRoZSBtaXhpbiB0byB0aGUgZ2l2ZW4gYmFzZSBjbGFzcyB0byByZXR1cm4gYSBuZXcgY2xhc3MuXG4gKiBUaGUgbWl4aW4gY2FuIGVpdGhlciBiZSBhIGZ1bmN0aW9uIHRoYXQgcmV0dXJucyB0aGUgbW9kaWZpZWQgY2xhc3MsIG9yIGFcbiAqIHBsYWluIG9iamVjdCB3aG9zZSBtZW1iZXJzIHdpbGwgYmUgY29waWVkIHRvIHRoZSBuZXcgY2xhc3MnIHByb3RvdHlwZS5cbiAqL1xuZnVuY3Rpb24gY29tcG9zZUNsYXNzKGJhc2UsIG1peGluKSB7XG4gIGlmICh0eXBlb2YgbWl4aW4gPT09ICdmdW5jdGlvbicpIHtcbiAgICAvLyBNaXhpbiBmdW5jdGlvblxuICAgIHJldHVybiBtaXhpbihiYXNlKTtcbiAgfSBlbHNlIHtcbiAgICAvLyBNaXhpbiBvYmplY3RcbiAgICBjbGFzcyBTdWJjbGFzcyBleHRlbmRzIGJhc2Uge31cbiAgICBjb3B5T3duUHJvcGVydGllcyhtaXhpbiwgU3ViY2xhc3MucHJvdG90eXBlLCBOT05fTUlYQUJMRV9PQkpFQ1RfUFJPUEVSVElFUyk7XG4gICAgcmV0dXJuIFN1YmNsYXNzO1xuICB9XG59XG5cblxuLypcbiAqIENvcHkgdGhlIGdpdmVuIHByb3BlcnRpZXMvbWV0aG9kcyB0byB0aGUgdGFyZ2V0LlxuICogUmV0dXJuIHRoZSB1cGRhdGVkIHRhcmdldC5cbiAqL1xuZnVuY3Rpb24gY29weU93blByb3BlcnRpZXMoc291cmNlLCB0YXJnZXQsIGlnbm9yZVByb3BlcnR5TmFtZXMgPSBbXSkge1xuICBPYmplY3QuZ2V0T3duUHJvcGVydHlOYW1lcyhzb3VyY2UpLmZvckVhY2gobmFtZSA9PiB7XG4gICAgaWYgKGlnbm9yZVByb3BlcnR5TmFtZXMuaW5kZXhPZihuYW1lKSA8IDApIHtcbiAgICAgIGNvbnN0IGRlc2NyaXB0b3IgPSBPYmplY3QuZ2V0T3duUHJvcGVydHlEZXNjcmlwdG9yKHNvdXJjZSwgbmFtZSk7XG4gICAgICBPYmplY3QuZGVmaW5lUHJvcGVydHkodGFyZ2V0LCBuYW1lLCBkZXNjcmlwdG9yKTtcbiAgICB9XG4gIH0pO1xuICByZXR1cm4gdGFyZ2V0O1xufVxuIiwiaW1wb3J0IGNyZWF0ZVN5bWJvbCBmcm9tICcuL2NyZWF0ZVN5bWJvbCc7XG5pbXBvcnQgdG9nZ2xlQ2xhc3MgZnJvbSAnLi90b2dnbGVDbGFzcyc7XG5pbXBvcnQgc3ltYm9scyBmcm9tICcuL3N5bWJvbHMnO1xuXG5cbi8vIFN5bWJvbHMgZm9yIHByaXZhdGUgZGF0YSBtZW1iZXJzIG9uIGFuIGVsZW1lbnQuXG5jb25zdCBpdGVtc1N5bWJvbCA9IGNyZWF0ZVN5bWJvbCgnaXRlbXMnKTtcbmNvbnN0IGl0ZW1Jbml0aWFsaXplZFN5bWJvbCA9IGNyZWF0ZVN5bWJvbCgnaXRlbUluaXRpYWxpemVkJyk7XG5cblxuLyogRXhwb3J0ZWQgZnVuY3Rpb24gZXh0ZW5kcyBhIGJhc2UgY2xhc3Mgd2l0aCBDb250ZW50SXRlbXMuICovXG5leHBvcnQgZGVmYXVsdCAoYmFzZSkgPT4ge1xuXG4gIC8qKlxuICAgKiBNaXhpbiB3aGljaCBtYXBzIGNvbnRlbnQgc2VtYW50aWNzIChlbGVtZW50cykgdG8gbGlzdCBpdGVtIHNlbWFudGljcy5cbiAgICpcbiAgICogSXRlbXMgZGlmZmVyIGZyb20gZWxlbWVudCBjb250ZW50cyBpbiBzZXZlcmFsIHdheXM6XG4gICAqXG4gICAqICogVGhleSBhcmUgb2Z0ZW4gcmVmZXJlbmNlZCB2aWEgaW5kZXguXG4gICAqICogVGhleSBtYXkgaGF2ZSBhIHNlbGVjdGlvbiBzdGF0ZS5cbiAgICogKiBJdCdzIGNvbW1vbiB0byBkbyB3b3JrIHRvIGluaXRpYWxpemUgdGhlIGFwcGVhcmFuY2Ugb3Igc3RhdGUgb2YgYSBuZXdcbiAgICogICBpdGVtLlxuICAgKiAqIEF1eGlsaWFyeSBpbnZpc2libGUgY2hpbGQgZWxlbWVudHMgYXJlIGZpbHRlcmVkIG91dCBhbmQgbm90IGNvdW50ZWQgYXNcbiAgICogICBpdGVtcy4gQXV4aWxpYXJ5IGVsZW1lbnRzIGluY2x1ZGUgbGluaywgc2NyaXB0LCBzdHlsZSwgYW5kIHRlbXBsYXRlXG4gICAqICAgZWxlbWVudHMuIFRoaXMgZmlsdGVyaW5nIGVuc3VyZXMgdGhhdCB0aG9zZSBhdXhpbGlhcnkgZWxlbWVudHMgY2FuIGJlXG4gICAqICAgdXNlZCBpbiBtYXJrdXAgaW5zaWRlIG9mIGEgbGlzdCB3aXRob3V0IGJlaW5nIHRyZWF0ZWQgYXMgbGlzdCBpdGVtcy5cbiAgICpcbiAgICogVGhpcyBtaXhpbiBleHBlY3RzIGEgY29tcG9uZW50IHRvIHByb3ZpZGUgYSBgY29udGVudGAgcHJvcGVydHkgcmV0dXJuaW5nIGFcbiAgICogcmF3IHNldCBvZiBlbGVtZW50cy4gWW91IGNhbiBwcm92aWRlIHRoYXQgeW91cnNlbGYsIG9yIHVzZVxuICAgKiBbRGlzdHJpYnV0ZWRDaGlsZHJlbkNvbnRlbnRNaXhpbl0oRGlzdHJpYnV0ZWRDaGlsZHJlbkNvbnRlbnRNaXhpbi5tZCkuXG4gICAqXG4gICAqIFRoZSBtb3N0IGNvbW1vbmx5IHJlZmVyZW5jZWQgcHJvcGVydHkgZGVmaW5lZCBieSB0aGlzIG1peGluIGlzIHRoZSBgaXRlbXNgXG4gICAqIHByb3BlcnR5LiBUbyBhdm9pZCBoYXZpbmcgdG8gZG8gd29yayBlYWNoIHRpbWUgdGhhdCBwcm9wZXJ0eSBpcyByZXF1ZXN0ZWQsXG4gICAqIHRoaXMgbWl4aW4gc3VwcG9ydHMgYW4gb3B0aW1pemVkIG1vZGUuIElmIHlvdSBpbnZva2UgdGhlIGBjb250ZW50Q2hhbmdlZGBcbiAgICogbWV0aG9kIHdoZW4gdGhlIHNldCBvZiBpdGVtcyBjaGFuZ2VzLCB0aGUgbWl4aW4gY29uY2x1ZGVzIHRoYXQgeW91J2xsIHRha2VcbiAgICogY2FyZSBvZiBub3RpZnlpbmcgaXQgb2YgZnV0dXJlIGNoYW5nZXMsIGFuZCB0dXJucyBvbiB0aGUgb3B0aW1pemF0aW9uLiBXaXRoXG4gICAqIHRoYXQgb24sIHRoZSBtaXhpbiBzYXZlcyBhIHJlZmVyZW5jZSB0byB0aGUgY29tcHV0ZWQgc2V0IG9mIGl0ZW1zLCBhbmQgd2lsbFxuICAgKiByZXR1cm4gdGhhdCBpbW1lZGlhdGVseSBvbiBzdWJzZXF1ZW50IGNhbGxzIHRvIHRoZSBgaXRlbXNgIHByb3BlcnR5LiBJZiB5b3VcbiAgICogdXNlIHRoaXMgbWl4aW4gaW4gY29uanVuY3Rpb24gd2l0aFxuICAgKiBbRGlzdHJpYnV0ZWRDaGlsZHJlbkNvbnRlbnRNaXhpbl0oRGlzdHJpYnV0ZWRDaGlsZHJlbkNvbnRlbnRNaXhpbi5tZCksIHRoZVxuICAgKiBgY29udGVudENoYW5nZWRgIG1ldGhvZCB3aWxsIGJlIGludm9rZWQgZm9yIHlvdSB3aGVuIHRoZSBlbGVtZW50J3MgY2hpbGRyZW5cbiAgICogY2hhbmdlLCB0dXJuaW5nIG9uIHRoZSBvcHRpbWl6YXRpb24gYXV0b21hdGljYWxseS5cbiAgICovXG4gIGNsYXNzIENvbnRlbnRJdGVtcyBleHRlbmRzIGJhc2Uge1xuXG4gICAgY29udGVudENoYW5nZWQoKSB7XG4gICAgICBpZiAoc3VwZXIuY29udGVudENoYW5nZWQpIHsgc3VwZXIuY29udGVudENoYW5nZWQoKTsgfVxuXG4gICAgICAvLyBTaW5jZSB3ZSBnb3QgdGhlIGNvbnRlbnRDaGFuZ2VkIGNhbGwsIHdlJ2xsIGFzc3VtZSB3ZSdsbCBiZSBub3RpZmllZCBpZlxuICAgICAgLy8gdGhlIHNldCBvZiBpdGVtcyBjaGFuZ2VzIGxhdGVyLiBXZSB0dXJuIG9uIG1lbW9pemF0aW9uIG9mIHRoZSBpdGVtc1xuICAgICAgLy8gcHJvcGVydHkgYnkgc2V0dGluZyBvdXIgaW50ZXJuYWwgcHJvcGVydHkgdG8gbnVsbCAoaW5zdGVhZCBvZlxuICAgICAgLy8gdW5kZWZpbmVkKS5cbiAgICAgIHRoaXNbaXRlbXNTeW1ib2xdID0gbnVsbDtcblxuICAgICAgdGhpc1tzeW1ib2xzLml0ZW1zQ2hhbmdlZF0oKTtcbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBUaGlzIG1ldGhvZCBpcyBpbnZva2VkIHdoZW5ldmVyIGEgbmV3IGl0ZW0gaXMgYWRkZWQgdG8gdGhlIGxpc3QuXG4gICAgICpcbiAgICAgKiBUaGUgZGVmYXVsdCBpbXBsZW1lbnRhdGlvbiBvZiB0aGlzIG1ldGhvZCBkb2VzIG5vdGhpbmcuIFlvdSBjYW4gb3ZlcnJpZGVcbiAgICAgKiB0aGlzIHRvIHBlcmZvcm0gcGVyLWl0ZW0gaW5pdGlhbGl6YXRpb24uXG4gICAgICpcbiAgICAgKiBAcGFyYW0ge0hUTUxFbGVtZW50fSBpdGVtIC0gVGhlIGl0ZW0gdGhhdCB3YXMgYWRkZWQuXG4gICAgICovXG4gICAgW3N5bWJvbHMuaXRlbUFkZGVkXShpdGVtKSB7XG4gICAgICBpZiAoc3VwZXJbc3ltYm9scy5pdGVtQWRkZWRdKSB7IHN1cGVyW3N5bWJvbHMuaXRlbUFkZGVkXShpdGVtKTsgfVxuICAgIH1cblxuICAgIC8qKlxuICAgICAqIFRoZSBzZWxlY3Rpb24gc3RhdGUgZm9yIGEgc2luZ2xlIGl0ZW0gaGFzIGNoYW5nZWQuXG4gICAgICpcbiAgICAgKiBJbnZva2UgdGhpcyBtZXRob2QgdG8gc2lnbmFsIHRoYXQgdGhlIHNlbGVjdGVkIHN0YXRlIG9mIHRoZSBpbmRpY2F0ZWQgaXRlbVxuICAgICAqIGhhcyBjaGFuZ2VkLiBCeSBkZWZhdWx0LCB0aGlzIGFwcGxpZXMgYSBgc2VsZWN0ZWRgIENTUyBjbGFzcyBpZiB0aGUgaXRlbVxuICAgICAqIGlzIHNlbGVjdGVkLCBhbmQgcmVtb3ZlZCBpdCBpZiBub3Qgc2VsZWN0ZWQuXG4gICAgICpcbiAgICAgKiBAcGFyYW0ge0hUTUxFbGVtZW50fSBpdGVtIC0gVGhlIGl0ZW0gd2hvc2Ugc2VsZWN0aW9uIHN0YXRlIGhhcyBjaGFuZ2VkLlxuICAgICAqIEBwYXJhbSB7Ym9vbGVhbn0gc2VsZWN0ZWQgLSBUcnVlIGlmIHRoZSBpdGVtIGlzIHNlbGVjdGVkLCBmYWxzZSBpZiBub3QuXG4gICAgICovXG4gICAgW3N5bWJvbHMuaXRlbVNlbGVjdGVkXShpdGVtLCBzZWxlY3RlZCkge1xuICAgICAgaWYgKHN1cGVyW3N5bWJvbHMuaXRlbVNlbGVjdGVkXSkgeyBzdXBlcltzeW1ib2xzLml0ZW1TZWxlY3RlZF0oaXRlbSwgc2VsZWN0ZWQpOyB9XG4gICAgICB0b2dnbGVDbGFzcyhpdGVtLCAnc2VsZWN0ZWQnLCBzZWxlY3RlZCk7XG4gICAgfVxuXG4gICAgLyoqXG4gICAgICogVGhlIGN1cnJlbnQgc2V0IG9mIGl0ZW1zIGluIHRoZSBsaXN0LiBTZWUgdGhlIHRvcC1sZXZlbCBkb2N1bWVudGF0aW9uIGZvclxuICAgICAqIG1peGluIGZvciBhIGRlc2NyaXB0aW9uIG9mIGhvdyBpdGVtcyBkaWZmZXIgZnJvbSBwbGFpbiBjb250ZW50LlxuICAgICAqXG4gICAgICogQHR5cGUge0hUTUxFbGVtZW50W119XG4gICAgICovXG4gICAgZ2V0IGl0ZW1zKCkge1xuICAgICAgbGV0IGl0ZW1zO1xuICAgICAgaWYgKHRoaXNbaXRlbXNTeW1ib2xdID09IG51bGwpIHtcbiAgICAgICAgaXRlbXMgPSBmaWx0ZXJBdXhpbGlhcnlFbGVtZW50cyh0aGlzLmNvbnRlbnQpO1xuICAgICAgICAvLyBOb3RlOiB0ZXN0IGZvciAqZXF1YWxpdHkqIHdpdGggbnVsbDsgZG9uJ3QgdHJlYXQgdW5kZWZpbmVkIGFzIGEgbWF0Y2guXG4gICAgICAgIGlmICh0aGlzW2l0ZW1zU3ltYm9sXSA9PT0gbnVsbCkge1xuICAgICAgICAgIC8vIE1lbW9pemUgdGhlIHNldCBvZiBpdGVtcy5cbiAgICAgICAgICB0aGlzW2l0ZW1zU3ltYm9sXSA9IGl0ZW1zO1xuICAgICAgICB9XG4gICAgICB9IGVsc2Uge1xuICAgICAgICAvLyBSZXR1cm4gdGhlIG1lbW9pemVkIGl0ZW1zLlxuICAgICAgICBpdGVtcyA9IHRoaXNbaXRlbXNTeW1ib2xdO1xuICAgICAgfVxuICAgICAgcmV0dXJuIGl0ZW1zO1xuICAgIH1cblxuICAgIC8qKlxuICAgICAqIFRoaXMgbWV0aG9kIGlzIGludm9rZWQgd2hlbiB0aGUgdW5kZXJseWluZyBjb250ZW50cyBjaGFuZ2UuIEl0IGlzIGFsc29cbiAgICAgKiBpbnZva2VkIG9uIGNvbXBvbmVudCBpbml0aWFsaXphdGlvbiDigJMgc2luY2UgdGhlIGl0ZW1zIGhhdmUgXCJjaGFuZ2VkXCIgZnJvbVxuICAgICAqIGJlaW5nIG5vdGhpbmcuXG4gICAgICovXG4gICAgW3N5bWJvbHMuaXRlbXNDaGFuZ2VkXSgpIHtcbiAgICAgIGlmIChzdXBlcltzeW1ib2xzLml0ZW1zQ2hhbmdlZF0pIHsgc3VwZXJbc3ltYm9scy5pdGVtc0NoYW5nZWRdKCk7IH1cblxuICAgICAgLy8gUGVyZm9ybSBwZXItaXRlbSBpbml0aWFsaXphdGlvbi5cbiAgICAgIEFycmF5LnByb3RvdHlwZS5mb3JFYWNoLmNhbGwodGhpcy5pdGVtcywgaXRlbSA9PiB7XG4gICAgICAgIGlmICghaXRlbVtpdGVtSW5pdGlhbGl6ZWRTeW1ib2xdKSB7XG4gICAgICAgICAgdGhpc1tzeW1ib2xzLml0ZW1BZGRlZF0oaXRlbSk7XG4gICAgICAgICAgaXRlbVtpdGVtSW5pdGlhbGl6ZWRTeW1ib2xdID0gdHJ1ZTtcbiAgICAgICAgfVxuICAgICAgfSk7XG5cbiAgICAgIHRoaXMuZGlzcGF0Y2hFdmVudChuZXcgQ3VzdG9tRXZlbnQoJ2l0ZW1zLWNoYW5nZWQnKSk7XG4gICAgfVxuXG4gICAgLyoqXG4gICAgICogRmlyZXMgd2hlbiB0aGUgaXRlbXMgaW4gdGhlIGxpc3QgY2hhbmdlLlxuICAgICAqXG4gICAgICogQG1lbWJlcm9mIENvbnRlbnRJdGVtc1xuICAgICAqIEBldmVudCBpdGVtcy1jaGFuZ2VkXG4gICAgICovXG4gIH1cblxuICByZXR1cm4gQ29udGVudEl0ZW1zO1xufTtcblxuXG4vLyBSZXR1cm4gdGhlIGdpdmVuIGVsZW1lbnRzLCBmaWx0ZXJpbmcgb3V0IGF1eGlsaWFyeSBlbGVtZW50cyB0aGF0IGFyZW4ndFxuLy8gdHlwaWNhbGx5IHZpc2libGUuIEl0ZW1zIHdoaWNoIGFyZSBub3QgZWxlbWVudHMgYXJlIHJldHVybmVkIGFzIGlzLlxuZnVuY3Rpb24gZmlsdGVyQXV4aWxpYXJ5RWxlbWVudHMoaXRlbXMpIHtcbiAgY29uc3QgYXV4aWxpYXJ5VGFncyA9IFtcbiAgICAnbGluaycsXG4gICAgJ3NjcmlwdCcsXG4gICAgJ3N0eWxlJyxcbiAgICAndGVtcGxhdGUnXG4gIF07XG4gIHJldHVybiBbXS5maWx0ZXIuY2FsbChpdGVtcywgZnVuY3Rpb24oaXRlbSkge1xuICAgIHJldHVybiAhaXRlbS5sb2NhbE5hbWUgfHwgYXV4aWxpYXJ5VGFncy5pbmRleE9mKGl0ZW0ubG9jYWxOYW1lKSA8IDA7XG4gIH0pO1xufVxuIiwiaW1wb3J0IG1pY3JvdGFzayBmcm9tICcuL21pY3JvdGFzayc7XG5cblxuLyogRXhwb3J0ZWQgZnVuY3Rpb24gZXh0ZW5kcyBhIGJhc2UgY2xhc3Mgd2l0aCBEaXN0cmlidXRlZENoaWxkcmVuQ29udGVudC4gKi9cbmV4cG9ydCBkZWZhdWx0IChiYXNlKSA9PiB7XG5cbiAgLyoqXG4gICAqIE1peGluIHdoaWNoIGRlZmluZXMgYSBjb21wb25lbnQncyBjb250ZW50IGFzIGl0cyBjaGlsZHJlbiwgZXhwYW5kaW5nIGFueVxuICAgKiBub2RlcyBkaXN0cmlidXRlZCB0byB0aGUgY29tcG9uZW50J3Mgc2xvdHMuXG4gICAqXG4gICAqIFRoaXMgYWxzbyBwcm92aWRlcyBub3RpZmljYXRpb24gb2YgY2hhbmdlcyB0byBhIGNvbXBvbmVudCdzIGNvbnRlbnQuIEl0XG4gICAqIHdpbGwgaW52b2tlIGEgYGNvbnRlbnRDaGFuZ2VkYCBtZXRob2Qgd2hlbiB0aGUgY29tcG9uZW50IGlzIGZpcnN0XG4gICAqIGluc3RhbnRpYXRlZCwgYW5kIHdoZW5ldmVyIGl0cyBkaXN0cmlidXRlZCBjaGlsZHJlbiBjaGFuZ2UuIFRoaXMgaXMgYW5cbiAgICogZWFzeSB3YXkgdG8gc2F0aXNmeSB0aGUgR29sZCBTdGFuZGFyZCBjaGVja2xpc3QgaXRlbSBmb3IgbW9uaXRvcmluZ1xuICAgKiBbQ29udGVudCBDaGFuZ2VzXShodHRwczovL2dpdGh1Yi5jb20vd2ViY29tcG9uZW50cy9nb2xkLXN0YW5kYXJkL3dpa2kvQ29udGVudC1DaGFuZ2VzKS5cbiAgICpcbiAgICogRXhhbXBsZTpcbiAgICpcbiAgICogYGBgXG4gICAqIGxldCBiYXNlID0gRGlzdHJpYnV0ZWRDaGlsZHJlbkNvbnRlbnRNaXhpbihEaXN0cmlidXRlZENoaWxkcmVuTWl4aW4oSFRNTEVsZW1lbnQpKTtcbiAgICogY2xhc3MgQ291bnRpbmdFbGVtZW50IGV4dGVuZHMgYmFzZSB7XG4gICAqXG4gICAqICAgY29uc3RydWN0b3IoKSB7XG4gICAqICAgICBzdXBlcigpO1xuICAgKiAgICAgbGV0IHJvb3QgPSB0aGlzLmF0dGFjaFNoYWRvdyh7IG1vZGU6ICdvcGVuJyB9KTtcbiAgICogICAgIHJvb3QuaW5uZXJIVE1MID0gYDxzbG90Pjwvc2xvdD5gO1xuICAgKiAgIH1cbiAgICpcbiAgICogICBjb250ZW50Q2hhbmdlZCgpIHtcbiAgICogICAgIC8vIENvdW50IHRoZSBjb21wb25lbnQncyBjaGlsZHJlbiwgYm90aCBpbml0aWFsbHkgYW5kIHdoZW4gY2hhbmdlZC5cbiAgICogICAgIHRoaXMuY291bnQgPSB0aGlzLmRpc3RyaWJ1dGVkQ2hpbGRyZW4ubGVuZ3RoO1xuICAgKiAgIH1cbiAgICpcbiAgICogfVxuICAgKiBgYGBcbiAgICpcbiAgICogTm90ZSB0aGF0IGNvbnRlbnQgY2hhbmdlIGRldGVjdGlvbiBkZXBlbmRzIHVwb24gdGhlIGVsZW1lbnQgaGF2aW5nIGF0IGxlYXN0XG4gICAqIG9uZSBgc2xvdGAgZWxlbWVudCBpbiBpdHMgc2hhZG93IHN1YnRyZWUuXG4gICAqXG4gICAqIFRoaXMgbWl4aW4gaXMgaW50ZW5kZWQgZm9yIHVzZSB3aXRoIHRoZVxuICAgKiBbRGlzdHJpYnV0ZWRDaGlsZHJlbk1peGluXShEaXN0cmlidXRlZENoaWxkcmVuTWl4aW4ubWQpLiBTZWUgdGhhdCBtaXhpbiBmb3JcbiAgICogYSBkaXNjdXNzaW9uIG9mIGhvdyB0aGF0IHdvcmtzLiBUaGlzIERpc3RyaWJ1dGVkQ2hpbGRyZW5Db250ZW50TWl4aW5cbiAgICogcHJvdmlkZXMgYW4gZWFzeSB3YXkgb2YgZGVmaW5pbmcgdGhlIFwiY29udGVudFwiIG9mIGEgY29tcG9uZW50IGFzIHRoZVxuICAgKiBjb21wb25lbnQncyBkaXN0cmlidXRlZCBjaGlsZHJlbi4gVGhhdCBpbiB0dXJuIGxldHMgbWl4aW5zIGxpa2VcbiAgICogW0NvbnRlbnRJdGVtc01peGluXShDb250ZW50SXRlbXNNaXhpbi5tZCkgbWFuaXB1bGF0ZSB0aGUgY2hpbGRyZW4gYXMgbGlzdFxuICAgKiBpdGVtcy5cbiAgICovXG4gIGNsYXNzIERpc3RyaWJ1dGVkQ2hpbGRyZW5Db250ZW50IGV4dGVuZHMgYmFzZSB7XG5cbiAgICBjb25zdHJ1Y3RvcigpIHtcbiAgICAgIHN1cGVyKCk7XG5cbiAgICAgIGlmICh0aGlzLnNoYWRvd1Jvb3QpIHtcbiAgICAgICAgLy8gTGlzdGVuIHRvIGNoYW5nZXMgb24gYWxsIHNsb3RzLlxuICAgICAgICBjb25zdCBzbG90cyA9IHRoaXMuc2hhZG93Um9vdC5xdWVyeVNlbGVjdG9yQWxsKCdzbG90Jyk7XG4gICAgICAgIHNsb3RzLmZvckVhY2goc2xvdCA9PiBzbG90LmFkZEV2ZW50TGlzdGVuZXIoJ3Nsb3RjaGFuZ2UnLCBldmVudCA9PiB7XG4gICAgICAgICAgdGhpcy5jb250ZW50Q2hhbmdlZCgpO1xuICAgICAgICB9KSk7XG4gICAgICB9XG5cbiAgICAgIC8vIE1ha2UgYW4gaW5pdGlhbCBjYWxsIHRvIGNvbnRlbnRDaGFuZ2VkKCkgc28gdGhhdCB0aGUgY29tcG9uZW50IGNhbiBkb1xuICAgICAgLy8gaW5pdGlhbGl6YXRpb24gdGhhdCBpdCBub3JtYWxseSBkb2VzIHdoZW4gY29udGVudCBjaGFuZ2VzLlxuICAgICAgLy9cbiAgICAgIC8vIFRoaXMgd2lsbCBpbnZva2UgY29udGVudENoYW5nZWQoKSBoYW5kbGVycyBpbiBvdGhlciBtaXhpbnMuIEluIG9yZGVyXG4gICAgICAvLyB0aGF0IHRob3NlIG1peGlucyBoYXZlIGEgY2hhbmNlIHRvIGNvbXBsZXRlIHRoZWlyIG93biBpbml0aWFsaXphdGlvbixcbiAgICAgIC8vIHdlIGFkZCB0aGUgY29udGVudENoYW5nZWQoKSBjYWxsIHRvIHRoZSBtaWNyb3Rhc2sgcXVldWUuXG4gICAgICBtaWNyb3Rhc2soKCkgPT4gdGhpcy5jb250ZW50Q2hhbmdlZCgpKTtcbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBJbnZva2VkIHdoZW4gdGhlIGNvbnRlbnRzIG9mIHRoZSBjb21wb25lbnQgKGluY2x1ZGluZyBkaXN0cmlidXRlZFxuICAgICAqIGNoaWxkcmVuKSBoYXZlIGNoYW5nZWQuXG4gICAgICpcbiAgICAgKiBUaGlzIG1ldGhvZCBpcyBhbHNvIGludm9rZWQgd2hlbiBhIGNvbXBvbmVudCBpcyBmaXJzdCBpbnN0YW50aWF0ZWQ7IHRoZVxuICAgICAqIGNvbnRlbnRzIGhhdmUgZXNzZW50aWFsbHkgXCJjaGFuZ2VkXCIgZnJvbSBiZWluZyBub3RoaW5nLiBUaGlzIGFsbG93cyB0aGVcbiAgICAgKiBjb21wb25lbnQgdG8gcGVyZm9ybSBpbml0aWFsIHByb2Nlc3Npbmcgb2YgaXRzIGNoaWxkcmVuLlxuICAgICAqL1xuICAgIGNvbnRlbnRDaGFuZ2VkKCkge1xuICAgICAgaWYgKHN1cGVyLmNvbnRlbnRDaGFuZ2VkKSB7IHN1cGVyLmNvbnRlbnRDaGFuZ2VkKCk7IH1cbiAgICAgIGNvbnN0IGV2ZW50ID0gbmV3IEN1c3RvbUV2ZW50KCdjb250ZW50LWNoYW5nZWQnKTtcbiAgICAgIHRoaXMuZGlzcGF0Y2hFdmVudChldmVudCk7XG4gICAgfVxuXG4gICAgLyoqXG4gICAgICogVGhlIGNvbnRlbnQgb2YgdGhpcyBjb21wb25lbnQsIGRlZmluZWQgdG8gYmUgdGhlIGZsYXR0ZW5lZCBhcnJheSBvZlxuICAgICAqIGNoaWxkcmVuIGRpc3RyaWJ1dGVkIHRvIHRoZSBjb21wb25lbnQuXG4gICAgICpcbiAgICAgKiBAdHlwZSB7SFRNTEVsZW1lbnRbXX1cbiAgICAgKi9cbiAgICBnZXQgY29udGVudCgpIHtcbiAgICAgIGNvbnN0IGRpc3RyaWJ1dGVkQ2hpbGRyZW4gPSB0aGlzLmRpc3RyaWJ1dGVkQ2hpbGRyZW47XG4gICAgICBpZiAodHlwZW9mIGRpc3RyaWJ1dGVkQ2hpbGRyZW4gPT09ICd1bmRlZmluZWQnKSB7XG4gICAgICAgIGNvbnNvbGUud2FybihgRGlzdHJpYnV0ZWRDaGlsZHJlbkNvbnRlbnRNaXhpbiBleHBlY3RzIHRoZSBjb21wb25lbnQgdG8gZGVmaW5lIGEgXCJkaXN0cmlidXRlZENoaWxkcmVuXCIgcHJvcGVydHkuYCk7XG4gICAgICB9XG4gICAgICByZXR1cm4gZGlzdHJpYnV0ZWRDaGlsZHJlbjtcbiAgICB9XG4gICAgc2V0IGNvbnRlbnQodmFsdWUpIHtcbiAgICAgIGlmICgnY29udGVudCcgaW4gYmFzZS5wcm90b3R5cGUpIHsgc3VwZXIuY29udGVudCA9IHZhbHVlOyB9XG4gICAgICAvLyBUT0RPOiBTZXQgdGhlIGNoaWxkcmVuIHRvIHRoZSBnaXZlbiB2YWx1ZSAod2hpY2ggc2hvdWxkIGJlIGFuIGFycmF5IG9mXG4gICAgICAvLyBlbGVtZW50cyk/XG4gICAgfVxuXG4gICAgLyoqXG4gICAgICogVGhpcyBldmVudCBpcyByYWlzZWQgd2hlbiB0aGUgY29tcG9uZW50J3MgY29udGVudHMgKGluY2x1ZGluZyBkaXN0cmlidXRlZFxuICAgICAqIGNoaWxkcmVuKSBoYXZlIGNoYW5nZWQuXG4gICAgICpcbiAgICAgKiBAbWVtYmVyb2YgRGlzdHJpYnV0ZWRDaGlsZHJlbkNvbnRlbnRcbiAgICAgKiBAZXZlbnQgY29udGVudC1jaGFuZ2VkXG4gICAgICovXG4gIH1cblxuICByZXR1cm4gRGlzdHJpYnV0ZWRDaGlsZHJlbkNvbnRlbnQ7XG59O1xuIiwiLyogRXhwb3J0ZWQgZnVuY3Rpb24gZXh0ZW5kcyBhIGJhc2UgY2xhc3Mgd2l0aCBEaXN0cmlidXRlZENoaWxkcmVuLiAqL1xuZXhwb3J0IGRlZmF1bHQgKGJhc2UpID0+IHtcblxuICAvKipcbiAgICogTWl4aW4gd2hpY2ggZGVmaW5lcyBoZWxwZXJzIGZvciBhY2Nlc3NpbmcgYSBjb21wb25lbnQncyBkaXN0cmlidXRlZFxuICAgKiBjaGlsZHJlbiBhcyBhIGZsYXR0ZW5lZCBhcnJheSBvciBzdHJpbmcuXG4gICAqXG4gICAqIFRoZSBzdGFuZGFyZCBET00gQVBJIHByb3ZpZGVzIHNldmVyYWwgd2F5cyBvZiBhY2Nlc3NpbmcgY2hpbGQgY29udGVudDpcbiAgICogYGNoaWxkcmVuYCwgYGNoaWxkTm9kZXNgLCBhbmQgYHRleHRDb250ZW50YC4gTm9uZSBvZiB0aGVzZSBmdW5jdGlvbnMgYXJlXG4gICAqIFNoYWRvdyBET00gYXdhcmUuIFRoaXMgbWl4aW4gZGVmaW5lcyB2YXJpYXRpb25zIG9mIHRob3NlIGZ1bmN0aW9ucyB0aGF0XG4gICAqICphcmUqIFNoYWRvdyBET00gYXdhcmUuXG4gICAqXG4gICAqIEV4YW1wbGU6IHlvdSBjcmVhdGUgYSBjb21wb25lbnQgYDxjb3VudC1jaGlsZHJlbj5gIHRoYXQgZGlzcGxheXMgYSBudW1iZXJcbiAgICogZXF1YWwgdG8gdGhlIG51bWJlciBvZiBjaGlsZHJlbiBwbGFjZWQgaW5zaWRlIHRoYXQgY29tcG9uZW50LiBJZiBzb21lb25lXG4gICAqIGluc3RhbnRpYXRlcyB5b3VyIGNvbXBvbmVudCBsaWtlOlxuICAgKlxuICAgKiAgICAgPGNvdW50LWNoaWxkcmVuPlxuICAgKiAgICAgICA8ZGl2PjwvZGl2PlxuICAgKiAgICAgICA8ZGl2PjwvZGl2PlxuICAgKiAgICAgICA8ZGl2PjwvZGl2PlxuICAgKiAgICAgPC9jb3VudC1jaGlsZHJlbj5cbiAgICpcbiAgICogVGhlbiB0aGUgY29tcG9uZW50IHNob3VsZCBzaG93IFwiM1wiLCBiZWNhdXNlIHRoZXJlIGFyZSB0aHJlZSBjaGlsZHJlbi4gVG9cbiAgICogY2FsY3VsYXRlIHRoZSBudW1iZXIgb2YgY2hpbGRyZW4sIHRoZSBjb21wb25lbnQgY2FuIGp1c3QgY2FsY3VsYXRlXG4gICAqIGB0aGlzLmNoaWxkcmVuLmxlbmd0aGAuIEhvd2V2ZXIsIHN1cHBvc2Ugc29tZW9uZSBpbnN0YW50aWF0ZXMgeW91clxuICAgKiBjb21wb25lbnQgaW5zaWRlIG9uZSBvZiB0aGVpciBvd24gY29tcG9uZW50cywgYW5kIHB1dHMgYSBgPHNsb3Q+YCBlbGVtZW50XG4gICAqIGluc2lkZSB5b3VyIGNvbXBvbmVudDpcbiAgICpcbiAgICogICAgIDxjb3VudC1jaGlsZHJlbj5cbiAgICogICAgICAgPHNsb3Q+PC9zbG90PlxuICAgKiAgICAgPC9jb3VudC1jaGlsZHJlbj5cbiAgICpcbiAgICogSWYgeW91ciBjb21wb25lbnQgb25seSBsb29rcyBhdCBgdGhpcy5jaGlsZHJlbmAsIGl0IHdpbGwgYWx3YXlzIHNlZSBleGFjdGx5XG4gICAqIG9uZSBjaGlsZCDigJTCoHRoZSBgPHNsb3Q+YCBlbGVtZW50LiBCdXQgdGhlIHVzZXIgbG9va2luZyBhdCB0aGUgcGFnZSB3aWxsXG4gICAqICpzZWUqIGFueSBub2RlcyBkaXN0cmlidXRlZCB0byB0aGF0IHNsb3QuIFRvIG1hdGNoIHdoYXQgdGhlIHVzZXIgc2VlcywgeW91clxuICAgKiBjb21wb25lbnQgc2hvdWxkIGV4cGFuZCBhbnkgYDxzbG90PmAgZWxlbWVudHMgaXQgY29udGFpbnMuXG4gICAqXG4gICAqIFRoYXQgaXMgdGhlIHByb2JsZW0gdGhpcyBtaXhpbiBzb2x2ZXMuIEFmdGVyIGFwcGx5aW5nIHRoaXMgbWl4aW4sIHlvdXJcbiAgICogY29tcG9uZW50IGNvZGUgaGFzIGFjY2VzcyB0byBgdGhpcy5kaXN0cmlidXRlZENoaWxkcmVuYCwgd2hvc2UgYGxlbmd0aGBcbiAgICogd2lsbCByZXR1cm4gdGhlIHRvdGFsIG51bWJlciBvZiBhbGwgY2hpbGRyZW4gZGlzdHJpYnV0ZWQgdG8geW91ciBjb21wb25lbnRcbiAgICogaW4gdGhlIGNvbXBvc2VkIHRyZWUuXG4gICAqXG4gICAqIE5vdGU6IFRoZSBsYXRlc3QgQ3VzdG9tIEVsZW1lbnRzIEFQSSBkZXNpZ24gY2FsbHMgZm9yIGEgbmV3IGZ1bmN0aW9uLFxuICAgKiBgZ2V0QXNzaWduZWROb2Rlc2AgdGhhdCB0YWtlcyBhbiBvcHRpb25hbCBgZGVlcGAgcGFyYW1ldGVyLCB0aGF0IHdpbGwgc29sdmVcbiAgICogdGhpcyBwcm9ibGVtIGF0IHRoZSBBUEkgbGV2ZWwuXG4gICAqL1xuICBjbGFzcyBEaXN0cmlidXRlZENoaWxkcmVuIGV4dGVuZHMgYmFzZSB7XG5cbiAgICAvKipcbiAgICAgKiBBbiBpbi1vcmRlciBjb2xsZWN0aW9uIG9mIGRpc3RyaWJ1dGVkIGNoaWxkcmVuLCBleHBhbmRpbmcgYW55IHNsb3RcbiAgICAgKiBlbGVtZW50cy4gTGlrZSB0aGUgc3RhbmRhcmQgY2hpbGRyZW4gcHJvcGVydHksIHRoaXMgc2tpcHMgdGV4dCBub2Rlcy5cbiAgICAgKlxuICAgICAqIEB0eXBlIHtIVE1MRWxlbWVudFtdfVxuICAgICAqL1xuICAgIGdldCBkaXN0cmlidXRlZENoaWxkcmVuKCkge1xuICAgICAgcmV0dXJuIGV4cGFuZENvbnRlbnRFbGVtZW50cyh0aGlzLmNoaWxkcmVuLCBmYWxzZSk7XG4gICAgfVxuXG4gICAgLyoqXG4gICAgICogQW4gaW4tb3JkZXIgY29sbGVjdGlvbiBvZiBkaXN0cmlidXRlZCBjaGlsZCBub2RlcywgZXhwYW5kaW5nIGFueSBzbG90XG4gICAgICogZWxlbWVudHMuIExpa2UgdGhlIHN0YW5kYXJkIGNoaWxkTm9kZXMgcHJvcGVydHksIHRoaXMgaW5jbHVkZXMgdGV4dFxuICAgICAqIG5vZGVzLlxuICAgICAqXG4gICAgICogQHR5cGUge05vZGVbXX1cbiAgICAgKi9cbiAgICBnZXQgZGlzdHJpYnV0ZWRDaGlsZE5vZGVzKCkge1xuICAgICAgcmV0dXJuIGV4cGFuZENvbnRlbnRFbGVtZW50cyh0aGlzLmNoaWxkTm9kZXMsIHRydWUpO1xuICAgIH1cblxuICAgIC8qKlxuICAgICAqIFRoZSBjb25jYXRlbmF0ZWQgdGV4dCBjb250ZW50IG9mIGFsbCBkaXN0cmlidXRlZCBjaGlsZCBub2RlcywgZXhwYW5kaW5nXG4gICAgICogYW55IHNsb3QgZWxlbWVudHMuXG4gICAgICpcbiAgICAgKiBAdHlwZSB7c3RyaW5nfVxuICAgICAqL1xuICAgIGdldCBkaXN0cmlidXRlZFRleHRDb250ZW50KCkge1xuICAgICAgY29uc3Qgc3RyaW5ncyA9IHRoaXMuZGlzdHJpYnV0ZWRDaGlsZE5vZGVzLm1hcChmdW5jdGlvbihjaGlsZCkge1xuICAgICAgICByZXR1cm4gY2hpbGQudGV4dENvbnRlbnQ7XG4gICAgICB9KTtcbiAgICAgIHJldHVybiBzdHJpbmdzLmpvaW4oJycpO1xuICAgIH1cblxuICB9XG5cbiAgcmV0dXJuIERpc3RyaWJ1dGVkQ2hpbGRyZW47XG59O1xuXG5cbi8qXG4gKiBHaXZlbiBhIGFycmF5IG9mIG5vZGVzLCByZXR1cm4gYSBuZXcgYXJyYXkgd2l0aCBhbnkgY29udGVudCBlbGVtZW50cyBleHBhbmRlZFxuICogdG8gdGhlIG5vZGVzIGRpc3RyaWJ1dGVkIHRvIHRoYXQgY29udGVudCBlbGVtZW50LiBUaGlzIHJ1bGUgaXMgYXBwbGllZFxuICogcmVjdXJzaXZlbHkuXG4gKlxuICogSWYgaW5jbHVkZVRleHROb2RlcyBpcyB0cnVlLCB0ZXh0IG5vZGVzIHdpbGwgYmUgaW5jbHVkZWQsIGFzIGluIHRoZVxuICogc3RhbmRhcmQgY2hpbGROb2RlcyBwcm9wZXJ0eTsgYnkgZGVmYXVsdCwgdGhpcyBza2lwcyB0ZXh0IG5vZGVzLCBsaWtlIHRoZVxuICogc3RhbmRhcmQgY2hpbGRyZW4gcHJvcGVydHkuXG4gKi9cbmZ1bmN0aW9uIGV4cGFuZENvbnRlbnRFbGVtZW50cyhub2RlcywgaW5jbHVkZVRleHROb2Rlcykge1xuICBjb25zdCBleHBhbmRlZCA9IEFycmF5LnByb3RvdHlwZS5tYXAuY2FsbChub2Rlcywgbm9kZSA9PiB7XG4gICAgLy8gV2Ugd2FudCB0byBzZWUgaWYgdGhlIG5vZGUgaXMgYW4gaW5zdGFuY2VvZiBIVE1MU2xvdEVMZW1lbnQsIGJ1dFxuICAgIC8vIHRoYXQgY2xhc3Mgd29uJ3QgZXhpc3QgaWYgdGhlIGJyb3dzZXIgdGhhdCBkb2Vzbid0IHN1cHBvcnQgbmF0aXZlXG4gICAgLy8gU2hhZG93IERPTSBhbmQgaWYgdGhlIFNoYWRvdyBET00gcG9seWZpbGwgaGFzbid0IGJlZW4gbG9hZGVkLiBJbnN0ZWFkLFxuICAgIC8vIHdlIGRvIGEgc2ltcGxpc3RpYyBjaGVjayB0byBzZWUgaWYgdGhlIHRhZyBuYW1lIGlzIFwic2xvdFwiLlxuICAgIGNvbnN0IGlzU2xvdCA9IHR5cGVvZiBIVE1MU2xvdEVsZW1lbnQgIT09ICd1bmRlZmluZWQnID9cbiAgICAgIG5vZGUgaW5zdGFuY2VvZiBIVE1MU2xvdEVsZW1lbnQgOlxuICAgICAgbm9kZS5sb2NhbE5hbWUgPT09ICdzbG90JztcbiAgICBpZiAoaXNTbG90KSB7XG4gICAgICAvLyBVc2UgdGhlIG5vZGVzIGFzc2lnbmVkIHRvIHRoaXMgbm9kZSBpbnN0ZWFkLlxuICAgICAgY29uc3QgYXNzaWduZWROb2RlcyA9IG5vZGUuYXNzaWduZWROb2Rlcyh7IGZsYXR0ZW46IHRydWUgfSk7XG4gICAgICByZXR1cm4gYXNzaWduZWROb2RlcyA/XG4gICAgICAgIGV4cGFuZENvbnRlbnRFbGVtZW50cyhhc3NpZ25lZE5vZGVzLCBpbmNsdWRlVGV4dE5vZGVzKSA6XG4gICAgICAgIFtdO1xuICAgIH0gZWxzZSBpZiAobm9kZSBpbnN0YW5jZW9mIEhUTUxFbGVtZW50KSB7XG4gICAgICAvLyBQbGFpbiBlbGVtZW50OyB1c2UgYXMgaXMuXG4gICAgICByZXR1cm4gW25vZGVdO1xuICAgIH0gZWxzZSBpZiAobm9kZSBpbnN0YW5jZW9mIFRleHQgJiYgaW5jbHVkZVRleHROb2Rlcykge1xuICAgICAgLy8gVGV4dCBub2RlLlxuICAgICAgcmV0dXJuIFtub2RlXTtcbiAgICB9IGVsc2Uge1xuICAgICAgLy8gQ29tbWVudCwgcHJvY2Vzc2luZyBpbnN0cnVjdGlvbiwgZXRjLjsgc2tpcC5cbiAgICAgIHJldHVybiBbXTtcbiAgICB9XG4gIH0pO1xuICBjb25zdCBmbGF0dGVuZWQgPSBbXS5jb25jYXQoLi4uZXhwYW5kZWQpO1xuICByZXR1cm4gZmxhdHRlbmVkO1xufVxuIiwiLyogRXhwb3J0ZWQgZnVuY3Rpb24gZXh0ZW5kcyBhIGJhc2UgY2xhc3Mgd2l0aCBTaGFkb3dFbGVtZW50UmVmZXJlbmNlcy4gKi9cbmV4cG9ydCBkZWZhdWx0IChiYXNlKSA9PiB7XG5cbiAgLyoqXG4gICAqIE1peGluIHRvIGNyZWF0ZSByZWZlcmVuY2VzIHRvIGVsZW1lbnRzIGluIGEgY29tcG9uZW50J3MgU2hhZG93IERPTSBzdWJ0cmVlLlxuICAgKlxuICAgKiBUaGlzIGFkZHMgYSBtZW1iZXIgb24gdGhlIGNvbXBvbmVudCBjYWxsZWQgYHRoaXMuJGAgdGhhdCBjYW4gYmUgdXNlZCB0b1xuICAgKiByZWZlcmVuY2Ugc2hhZG93IGVsZW1lbnRzIHdpdGggSURzLiBFLmcuLCBpZiBjb21wb25lbnQncyBzaGFkb3cgY29udGFpbnMgYW5cbiAgICogZWxlbWVudCBgPGJ1dHRvbiBpZD1cImZvb1wiPmAsIHRoZW4gdGhpcyBtaXhpbiB3aWxsIGNyZWF0ZSBhIG1lbWJlclxuICAgKiBgdGhpcy4kLmZvb2AgdGhhdCBwb2ludHMgdG8gdGhhdCBidXR0b24uXG4gICAqXG4gICAqIFN1Y2ggcmVmZXJlbmNlcyBzaW1wbGlmeSBhIGNvbXBvbmVudCdzIGFjY2VzcyB0byBpdHMgb3duIGVsZW1lbnRzLiBJblxuICAgKiBleGNoYW5nZSwgdGhpcyBtaXhpbiB0cmFkZXMgb2ZmIGEgb25lLXRpbWUgY29zdCBvZiBxdWVyeWluZyBhbGwgZWxlbWVudHMgaW5cbiAgICogdGhlIHNoYWRvdyB0cmVlIGluc3RlYWQgb2YgcGF5aW5nIGFuIG9uZ29pbmcgY29zdCB0byBxdWVyeSBmb3IgYW4gZWxlbWVudFxuICAgKiBlYWNoIHRpbWUgdGhlIGNvbXBvbmVudCB3YW50cyB0byBpbnNwZWN0IG9yIG1hbmlwdWxhdGUgaXQuXG4gICAqXG4gICAqIFRoaXMgbWl4aW4gZXhwZWN0cyB0aGUgY29tcG9uZW50IHRvIGRlZmluZSBhIFNoYWRvdyBET00gc3VidHJlZS4gWW91IGNhblxuICAgKiBjcmVhdGUgdGhhdCB0cmVlIHlvdXJzZWxmLCBvciBtYWtlIHVzZSBvZlxuICAgKiBbU2hhZG93VGVtcGxhdGVNaXhpbl0oU2hhZG93VGVtcGxhdGVNaXhpbi5tZCkuXG4gICAqXG4gICAqIFRoaXMgbWl4aW4gaXMgaW5zcGlyZWQgYnkgUG9seW1lcidzIFthdXRvbWF0aWNcbiAgICogbm9kZSBmaW5kaW5nXShodHRwczovL3d3dy5wb2x5bWVyLXByb2plY3Qub3JnLzEuMC9kb2NzL2Rldmd1aWRlL2xvY2FsLWRvbS5odG1sI25vZGUtZmluZGluZylcbiAgICogZmVhdHVyZS5cbiAgICovXG4gIGNsYXNzIFNoYWRvd0VsZW1lbnRSZWZlcmVuY2VzIGV4dGVuZHMgYmFzZSB7XG5cbiAgICBjb25zdHJ1Y3RvcigpIHtcbiAgICAgIHN1cGVyKCk7XG4gICAgICBpZiAodGhpcy5zaGFkb3dSb290KSB7XG4gICAgICAgIC8vIExvb2sgZm9yIGVsZW1lbnRzIGluIHRoZSBzaGFkb3cgc3VidHJlZSB0aGF0IGhhdmUgaWQgYXR0cmlidXRlcy5cbiAgICAgICAgLy8gQW4gYWx0ZXJuYXRpdmVseSBpbXBsZW1lbnRhdGlvbiBvZiB0aGlzIG1peGluIHdvdWxkIGJlIHRvIGp1c3QgZGVmaW5lXG4gICAgICAgIC8vIGEgdGhpcy4kIGdldHRlciB0aGF0IGxhemlseSBkb2VzIHRoaXMgc2VhcmNoIHRoZSBmaXJzdCB0aW1lIHNvbWVvbmVcbiAgICAgICAgLy8gdHJpZXMgdG8gYWNjZXNzIHRoaXMuJC4gVGhhdCBtaWdodCBpbnRyb2R1Y2Ugc29tZSBjb21wbGV4aXR5IOKAkyBpZiB0aGVcbiAgICAgICAgLy8gdGhlIHRyZWUgY2hhbmdlZCBhZnRlciBpdCB3YXMgZmlyc3QgcG9wdWxhdGVkLCB0aGUgcmVzdWx0IG9mXG4gICAgICAgIC8vIHNlYXJjaGluZyBmb3IgYSBub2RlIG1pZ2h0IGJlIHNvbWV3aGF0IHVucHJlZGljdGFibGUuXG4gICAgICAgIHRoaXMuJCA9IHt9O1xuICAgICAgICBjb25zdCBub2Rlc1dpdGhJZHMgPSB0aGlzLnNoYWRvd1Jvb3QucXVlcnlTZWxlY3RvckFsbCgnW2lkXScpO1xuICAgICAgICBbXS5mb3JFYWNoLmNhbGwobm9kZXNXaXRoSWRzLCBub2RlID0+IHtcbiAgICAgICAgICBjb25zdCBpZCA9IG5vZGUuZ2V0QXR0cmlidXRlKCdpZCcpO1xuICAgICAgICAgIHRoaXMuJFtpZF0gPSBub2RlO1xuICAgICAgICB9KTtcbiAgICAgIH1cbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBUaGUgY29sbGVjdGlvbiBvZiByZWZlcmVuY2VzIHRvIHRoZSBlbGVtZW50cyB3aXRoIElEcyBpbiBhIGNvbXBvbmVudCdzXG4gICAgICogU2hhZG93IERPTSBzdWJ0cmVlLlxuICAgICAqXG4gICAgICogQHR5cGUge29iamVjdH1cbiAgICAgKiBAbWVtYmVyICRcbiAgICAgKi9cbiAgfVxuXG4gIHJldHVybiBTaGFkb3dFbGVtZW50UmVmZXJlbmNlcztcbn07XG4iLCJpbXBvcnQgc3ltYm9scyBmcm9tICcuLi9zcmMvc3ltYm9scyc7XG5cblxuLyogRXhwb3J0ZWQgZnVuY3Rpb24gZXh0ZW5kcyBhIGJhc2UgY2xhc3Mgd2l0aCBTaGFkb3dUZW1wbGF0ZS4gKi9cbmV4cG9ydCBkZWZhdWx0IChiYXNlKSA9PiB7XG5cbiAgLyoqXG4gICAqIE1peGluIGZvciBzdGFtcGluZyBhIHRlbXBsYXRlIGludG8gYSBTaGFkb3cgRE9NIHN1YnRyZWUgdXBvbiBjb21wb25lbnRcbiAgICogaW5zdGFudGlhdGlvbi5cbiAgICpcbiAgICogVG8gdXNlIHRoaXMgbWl4aW4sIGRlZmluZSBhIGB0ZW1wbGF0ZWAgcHJvcGVydHkgYXMgYSBzdHJpbmcgb3IgSFRNTFxuICAgKiBgPHRlbXBsYXRlPmAgZWxlbWVudDpcbiAgICpcbiAgICogICAgIGNsYXNzIE15RWxlbWVudCBleHRlbmRzIFNoYWRvd1RlbXBsYXRlTWl4aW4oSFRNTEVsZW1lbnQpIHtcbiAgICogICAgICAgZ2V0IFtzeW1ib2xzLnRlbXBsYXRlXSgpIHtcbiAgICogICAgICAgICByZXR1cm4gYEhlbGxvLCA8ZW0+d29ybGQ8L2VtPi5gO1xuICAgKiAgICAgICB9XG4gICAqICAgICB9XG4gICAqXG4gICAqIFdoZW4geW91ciBjb21wb25lbnQgY2xhc3MgaXMgaW5zdGFudGlhdGVkLCBhIHNoYWRvdyByb290IHdpbGwgYmUgY3JlYXRlZCBvblxuICAgKiB0aGUgaW5zdGFuY2UsIGFuZCB0aGUgY29udGVudHMgb2YgdGhlIHRlbXBsYXRlIHdpbGwgYmUgY2xvbmVkIGludG8gdGhlXG4gICAqIHNoYWRvdyByb290LiBJZiB5b3VyIGNvbXBvbmVudCBkb2VzIG5vdCBkZWZpbmUgYSBgdGVtcGxhdGVgIHByb3BlcnR5LCB0aGlzXG4gICAqIG1peGluIGhhcyBubyBlZmZlY3QuXG4gICAqXG4gICAqIEZvciB0aGUgdGltZSBiZWluZywgdGhpcyBleHRlbnNpb24gcmV0YWlucyBzdXBwb3J0IGZvciBTaGFkb3cgRE9NIHYwLiBUaGF0XG4gICAqIHdpbGwgZXZlbnR1YWxseSBiZSBkZXByZWNhdGVkIGFzIGJyb3dzZXJzIChhbmQgdGhlIFNoYWRvdyBET00gcG9seWZpbGwpXG4gICAqIGltcGxlbWVudCBTaGFkb3cgRE9NIHYxLlxuICAgKi9cbiAgY2xhc3MgU2hhZG93VGVtcGxhdGUgZXh0ZW5kcyBiYXNlIHtcblxuICAgIC8qXG4gICAgICogSWYgdGhlIGNvbXBvbmVudCBkZWZpbmVzIGEgdGVtcGxhdGUsIGEgc2hhZG93IHJvb3Qgd2lsbCBiZSBjcmVhdGVkIG9uIHRoZVxuICAgICAqIGNvbXBvbmVudCBpbnN0YW5jZSwgYW5kIHRoZSB0ZW1wbGF0ZSBzdGFtcGVkIGludG8gaXQuXG4gICAgICovXG4gICAgY29uc3RydWN0b3IoKSB7XG4gICAgICBzdXBlcigpO1xuICAgICAgbGV0IHRlbXBsYXRlID0gdGhpc1tzeW1ib2xzLnRlbXBsYXRlXTtcbiAgICAgIC8vIFRPRE86IFNhdmUgdGhlIHByb2Nlc3NlZCB0ZW1wbGF0ZSB3aXRoIHRoZSBjb21wb25lbnQncyBjbGFzcyBwcm90b3R5cGVcbiAgICAgIC8vIHNvIGl0IGRvZXNuJ3QgbmVlZCB0byBiZSBwcm9jZXNzZWQgd2l0aCBldmVyeSBpbnN0YW50aWF0aW9uLlxuICAgICAgaWYgKHRlbXBsYXRlKSB7XG5cbiAgICAgICAgaWYgKHR5cGVvZiB0ZW1wbGF0ZSA9PT0gJ3N0cmluZycpIHtcbiAgICAgICAgICAvLyBVcGdyYWRlIHBsYWluIHN0cmluZyB0byByZWFsIHRlbXBsYXRlLlxuICAgICAgICAgIHRlbXBsYXRlID0gY3JlYXRlVGVtcGxhdGVXaXRoSW5uZXJIVE1MKHRlbXBsYXRlKTtcbiAgICAgICAgfVxuXG4gICAgICAgIGlmICh3aW5kb3cuU2hhZG93RE9NUG9seWZpbGwpIHtcbiAgICAgICAgICBzaGltVGVtcGxhdGVTdHlsZXModGVtcGxhdGUsIHRoaXMubG9jYWxOYW1lKTtcbiAgICAgICAgfVxuXG4gICAgICAgIGNvbnN0IHJvb3QgPSB0aGlzLmF0dGFjaFNoYWRvdyh7IG1vZGU6ICdvcGVuJyB9KTtcbiAgICAgICAgY29uc3QgY2xvbmUgPSBkb2N1bWVudC5pbXBvcnROb2RlKHRlbXBsYXRlLmNvbnRlbnQsIHRydWUpO1xuICAgICAgICByb290LmFwcGVuZENoaWxkKGNsb25lKTtcbiAgICAgIH1cbiAgICB9XG5cbiAgfVxuXG4gIHJldHVybiBTaGFkb3dUZW1wbGF0ZTtcbn07XG5cblxuLy8gQ29udmVydCBhIHBsYWluIHN0cmluZyBvZiBIVE1MIGludG8gYSByZWFsIHRlbXBsYXRlIGVsZW1lbnQuXG5mdW5jdGlvbiBjcmVhdGVUZW1wbGF0ZVdpdGhJbm5lckhUTUwoaW5uZXJIVE1MKSB7XG4gIGNvbnN0IHRlbXBsYXRlID0gZG9jdW1lbnQuY3JlYXRlRWxlbWVudCgndGVtcGxhdGUnKTtcbiAgLy8gUkVWSUVXOiBJcyB0aGVyZSBhbiBlYXNpZXIgd2F5IHRvIGRvIHRoaXM/XG4gIC8vIFdlJ2QgbGlrZSB0byBqdXN0IHNldCBpbm5lckhUTUwgb24gdGhlIHRlbXBsYXRlIGNvbnRlbnQsIGJ1dCBzaW5jZSBpdCdzXG4gIC8vIGEgRG9jdW1lbnRGcmFnbWVudCwgdGhhdCBkb2Vzbid0IHdvcmsuXG4gIGNvbnN0IGRpdiA9IGRvY3VtZW50LmNyZWF0ZUVsZW1lbnQoJ2RpdicpO1xuICBkaXYuaW5uZXJIVE1MID0gaW5uZXJIVE1MO1xuICB3aGlsZSAoZGl2LmNoaWxkTm9kZXMubGVuZ3RoID4gMCkge1xuICAgIHRlbXBsYXRlLmNvbnRlbnQuYXBwZW5kQ2hpbGQoZGl2LmNoaWxkTm9kZXNbMF0pO1xuICB9XG4gIHJldHVybiB0ZW1wbGF0ZTtcbn1cblxuLy8gSW52b2tlIGJhc2ljIHN0eWxlIHNoaW1taW5nIHdpdGggU2hhZG93Q1NTLlxuZnVuY3Rpb24gc2hpbVRlbXBsYXRlU3R5bGVzKHRlbXBsYXRlLCB0YWcpIHtcbiAgd2luZG93LldlYkNvbXBvbmVudHMuU2hhZG93Q1NTLnNoaW1TdHlsaW5nKHRlbXBsYXRlLmNvbnRlbnQsIHRhZyk7XG59XG4iLCJpbXBvcnQgY3JlYXRlU3ltYm9sIGZyb20gJy4vY3JlYXRlU3ltYm9sJztcbmltcG9ydCBzeW1ib2xzIGZyb20gJy4vc3ltYm9scyc7XG5cblxuLy8gU3ltYm9scyBmb3IgcHJpdmF0ZSBkYXRhIG1lbWJlcnMgb24gYW4gZWxlbWVudC5cbmNvbnN0IGNhblNlbGVjdE5leHRTeW1ib2wgPSBjcmVhdGVTeW1ib2woJ2NhblNlbGVjdE5leHQnKTtcbmNvbnN0IGNhblNlbGVjdFByZXZpb3VzU3ltYm9sID0gY3JlYXRlU3ltYm9sKCdjYW5TZWxlY3RQcmV2aW91cycpO1xuY29uc3Qgc2VsZWN0aW9uUmVxdWlyZWRTeW1ib2wgPSBjcmVhdGVTeW1ib2woJ3NlbGVjdGlvblJlcXVpcmVkJyk7XG5jb25zdCBzZWxlY3Rpb25XcmFwc1N5bWJvbCA9IGNyZWF0ZVN5bWJvbCgnc2VsZWN0aW9uV3JhcHMnKTtcblxuLy8gV2Ugd2FudCB0byBleHBvc2UgYm90aCBzZWxlY3RlZEluZGV4IGFuZCBzZWxlY3RlZEl0ZW0gYXMgaW5kZXBlbmRlbnRcbi8vIHByb3BlcnRpZXMgYnV0IGtlZXAgdGhlbSBpbiBzeW5jLiBUaGlzIGFsbG93cyBhIGNvbXBvbmVudCB1c2VyIHRvIHJlZmVyZW5jZVxuLy8gdGhlIHNlbGVjdGlvbiBieSB3aGF0ZXZlciBtZWFucyBpcyBtb3N0IG5hdHVyYWwgZm9yIHRoZWlyIHNpdHVhdGlvbi5cbi8vXG4vLyBUbyBlZmZpY2llbnRseSBrZWVwIHRoZXNlIHByb3BlcnRpZXMgaW4gc3luYywgd2UgdHJhY2sgXCJleHRlcm5hbFwiIGFuZFxuLy8gXCJpbnRlcm5hbFwiIHJlZmVyZW5jZXMgZm9yIGVhY2ggcHJvcGVydHk6XG4vL1xuLy8gVGhlIGV4dGVybmFsIGluZGV4IG9yIGl0ZW0gaXMgdGhlIG9uZSB3ZSByZXBvcnQgdG8gdGhlIG91dHNpZGUgd29ybGQgd2hlblxuLy8gYXNrZWQgZm9yIHNlbGVjdGlvbi4gIFdoZW4gaGFuZGxpbmcgYSBjaGFuZ2UgdG8gaW5kZXggb3IgaXRlbSwgd2UgdXBkYXRlIHRoZVxuLy8gZXh0ZXJuYWwgcmVmZXJlbmNlIGFzIHNvb24gYXMgcG9zc2libGUsIHNvIHRoYXQgaWYgYW55b25lIGltbWVkaWF0ZWx5IGFza3Ncbi8vIGZvciB0aGUgY3VycmVudCBzZWxlY3Rpb24sIHRoZXkgd2lsbCByZWNlaXZlIGEgc3RhYmxlIGFuc3dlci5cbi8vXG4vLyBUaGUgaW50ZXJuYWwgaW5kZXggb3IgaXRlbSB0cmFja3Mgd2hpY2hldmVyIGluZGV4IG9yIGl0ZW0gbGFzdCByZWNlaXZlZCB0aGVcbi8vIGZ1bGwgc2V0IG9mIHByb2Nlc3NpbmcuIFByb2Nlc3NpbmcgaW5jbHVkZXMgcmFpc2luZyBhIGNoYW5nZSBldmVudCBmb3IgdGhlXG4vLyBuZXcgdmFsdWUuIE9uY2Ugd2UndmUgYmVndW4gdGhhdCBwcm9jZXNzaW5nLCB3ZSBzdG9yZSB0aGUgbmV3IHZhbHVlIGFzIHRoZVxuLy8gaW50ZXJuYWwgdmFsdWUgdG8gaW5kaWNhdGUgd2UndmUgaGFuZGxlZCBpdC5cbi8vXG5jb25zdCBleHRlcm5hbFNlbGVjdGVkSW5kZXhTeW1ib2wgPSBjcmVhdGVTeW1ib2woJ2V4dGVybmFsU2VsZWN0ZWRJbmRleCcpO1xuY29uc3QgZXh0ZXJuYWxTZWxlY3RlZEl0ZW1TeW1ib2wgPSBjcmVhdGVTeW1ib2woJ2V4dGVybmFsU2VsZWN0ZWRJdGVtJyk7XG5jb25zdCBpbnRlcm5hbFNlbGVjdGVkSW5kZXhTeW1ib2wgPSBjcmVhdGVTeW1ib2woJ2ludGVybmFsU2VsZWN0ZWRJbmRleCcpO1xuY29uc3QgaW50ZXJuYWxTZWxlY3RlZEl0ZW1TeW1ib2wgPSBjcmVhdGVTeW1ib2woJ2ludGVybmFsU2VsZWN0ZWRJdGVtJyk7XG5cblxuLyogRXhwb3J0ZWQgZnVuY3Rpb24gZXh0ZW5kcyBhIGJhc2UgY2xhc3Mgd2l0aCBTaW5nbGVTZWxlY3Rpb24uICovXG5leHBvcnQgZGVmYXVsdCAoYmFzZSkgPT4ge1xuXG4gIC8qKlxuICAgKiBNaXhpbiB3aGljaCBtYW5hZ2VzIHNpbmdsZS1zZWxlY3Rpb24gc2VtYW50aWNzIGZvciBpdGVtcyBpbiBhIGxpc3QuXG4gICAqXG4gICAqIFRoaXMgbWl4aW4gZXhwZWN0cyBhIGNvbXBvbmVudCB0byBwcm92aWRlIGFuIGBpdGVtc2AgQXJyYXkgb3IgTm9kZUxpc3Qgb2ZcbiAgICogYWxsIGVsZW1lbnRzIGluIHRoZSBsaXN0LiBBIHN0YW5kYXJkIHdheSB0byBkbyB0aGF0IHdpdGggaXMgdGhlXG4gICAqIFtDb250ZW50SXRlbXNNaXhpbl0oQ29udGVudEl0ZW1zTWl4aW4ubWQpLCB3aGljaCB0YWtlcyBhIGNvbXBvbmVudCdzXG4gICAqIGNvbnRlbnQgKHR5cGljYWxseSBpdHMgZGlzdHJpYnV0ZWQgY2hpbGRyZW4pIGFzIHRoZSBzZXQgb2YgbGlzdCBpdGVtczsgc2VlXG4gICAqIHRoYXQgbWl4aW4gZm9yIGRldGFpbHMuXG4gICAqXG4gICAqIFRoaXMgbWl4aW4gdHJhY2tzIGEgc2luZ2xlIHNlbGVjdGVkIGl0ZW0gaW4gdGhlIGxpc3QsIGFuZCBwcm92aWRlcyBtZWFucyB0b1xuICAgKiBnZXQgYW5kIHNldCB0aGF0IHN0YXRlIGJ5IGl0ZW0gcG9zaXRpb24gKGBzZWxlY3RlZEluZGV4YCkgb3IgaXRlbSBpZGVudGl0eVxuICAgKiAoYHNlbGVjdGVkSXRlbWApLiBUaGUgc2VsZWN0aW9uIGNhbiBiZSBtb3ZlZCBpbiB0aGUgbGlzdCB2aWEgdGhlIG1ldGhvZHNcbiAgICogYHNlbGVjdEZpcnN0YCwgYHNlbGVjdExhc3RgLCBgc2VsZWN0TmV4dGAsIGFuZCBgc2VsZWN0UHJldmlvdXNgLlxuICAgKlxuICAgKiBUaGlzIG1peGluIGRvZXMgbm90IHByb2R1Y2UgYW55IHVzZXItdmlzaWJsZSBlZmZlY3RzIHRvIHJlcHJlc2VudFxuICAgKiBzZWxlY3Rpb24uIE90aGVyIG1peGlucywgc3VjaCBhc1xuICAgKiBbU2VsZWN0aW9uQXJpYUFjdGl2ZU1peGluXShTZWxlY3Rpb25BcmlhQWN0aXZlTWl4aW4ubWQpLFxuICAgKiBbU2VsZWN0aW9uSGlnaGxpZ2h0TWl4aW5dKFNlbGVjdGlvbkhpZ2hsaWdodE1peGluLm1kKSBhbmRcbiAgICogW1NlbGVjdGlvbkluVmlld01peGluXShTZWxlY3Rpb25JblZpZXdNaXhpbi5tZCksIG1vZGlmeSB0aGUgc2VsZWN0ZWQgaXRlbVxuICAgKiBpbiBjb21tb24gd2F5cyB0byBsZXQgdGhlIHVzZXIga25vdyBhIGdpdmVuIGl0ZW0gaXMgc2VsZWN0ZWQgb3Igbm90XG4gICAqIHNlbGVjdGVkLlxuICAgKi9cbiAgY2xhc3MgU2luZ2xlU2VsZWN0aW9uIGV4dGVuZHMgYmFzZSB7XG5cbiAgICBjb25zdHJ1Y3RvcigpIHtcbiAgICAgIHN1cGVyKCk7XG4gICAgICAvLyBTZXQgZGVmYXVsdHMuXG4gICAgICBpZiAodHlwZW9mIHRoaXMuc2VsZWN0aW9uUmVxdWlyZWQgPT09ICd1bmRlZmluZWQnKSB7XG4gICAgICAgIHRoaXMuc2VsZWN0aW9uUmVxdWlyZWQgPSB0aGlzW3N5bWJvbHMuZGVmYXVsdHNdLnNlbGVjdGlvblJlcXVpcmVkO1xuICAgICAgfVxuICAgICAgaWYgKHR5cGVvZiB0aGlzLnNlbGVjdGlvbldyYXBzID09PSAndW5kZWZpbmVkJykge1xuICAgICAgICB0aGlzLnNlbGVjdGlvbldyYXBzID0gdGhpc1tzeW1ib2xzLmRlZmF1bHRzXS5zZWxlY3Rpb25XcmFwcztcbiAgICAgIH1cbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBUcnVlIGlmIHRoZSBzZWxlY3Rpb24gY2FuIGJlIG1vdmVkIHRvIHRoZSBuZXh0IGl0ZW0sIGZhbHNlIGlmIG5vdCAodGhlXG4gICAgICogc2VsZWN0ZWQgaXRlbSBpcyB0aGUgbGFzdCBpdGVtIGluIHRoZSBsaXN0KS5cbiAgICAgKlxuICAgICAqIEB0eXBlIHtib29sZWFufVxuICAgICAqL1xuICAgIGdldCBjYW5TZWxlY3ROZXh0KCkge1xuICAgICAgcmV0dXJuIHRoaXNbY2FuU2VsZWN0TmV4dFN5bWJvbF07XG4gICAgfVxuICAgIHNldCBjYW5TZWxlY3ROZXh0KGNhblNlbGVjdE5leHQpIHtcbiAgICAgIGNvbnN0IHByZXZpb3VzQ2FuU2VsZWN0TmV4dCA9IHRoaXNbY2FuU2VsZWN0TmV4dFN5bWJvbF07XG4gICAgICB0aGlzW2NhblNlbGVjdE5leHRTeW1ib2xdID0gY2FuU2VsZWN0TmV4dDtcbiAgICAgIGlmICgnY2FuU2VsZWN0TmV4dCcgaW4gYmFzZS5wcm90b3R5cGUpIHsgc3VwZXIuY2FuU2VsZWN0TmV4dCA9IGNhblNlbGVjdE5leHQ7IH1cbiAgICAgIGlmIChjYW5TZWxlY3ROZXh0ICE9PSBwcmV2aW91c0NhblNlbGVjdE5leHQpIHtcbiAgICAgICAgdGhpcy5kaXNwYXRjaEV2ZW50KG5ldyBDdXN0b21FdmVudCgnY2FuLXNlbGVjdC1uZXh0LWNoYW5nZWQnKSk7XG4gICAgICB9XG4gICAgfVxuXG4gICAgLyoqXG4gICAgICogVHJ1ZSBpZiB0aGUgc2VsZWN0aW9uIGNhbiBiZSBtb3ZlZCB0byB0aGUgcHJldmlvdXMgaXRlbSwgZmFsc2UgaWYgbm90XG4gICAgICogKHRoZSBzZWxlY3RlZCBpdGVtIGlzIHRoZSBmaXJzdCBvbmUgaW4gdGhlIGxpc3QpLlxuICAgICAqXG4gICAgICogQHR5cGUge2Jvb2xlYW59XG4gICAgICovXG4gICAgZ2V0IGNhblNlbGVjdFByZXZpb3VzKCkge1xuICAgICAgcmV0dXJuIHRoaXNbY2FuU2VsZWN0UHJldmlvdXNTeW1ib2xdO1xuICAgIH1cbiAgICBzZXQgY2FuU2VsZWN0UHJldmlvdXMoY2FuU2VsZWN0UHJldmlvdXMpIHtcbiAgICAgIGNvbnN0IHByZXZpb3VzQ2FuU2VsZWN0UHJldmlvdXMgPSB0aGlzW2NhblNlbGVjdFByZXZpb3VzU3ltYm9sXTtcbiAgICAgIHRoaXNbY2FuU2VsZWN0UHJldmlvdXNTeW1ib2xdID0gY2FuU2VsZWN0UHJldmlvdXM7XG4gICAgICBpZiAoJ2NhblNlbGVjdFByZXZpb3VzJyBpbiBiYXNlLnByb3RvdHlwZSkgeyBzdXBlci5jYW5TZWxlY3RQcmV2aW91cyA9IGNhblNlbGVjdFByZXZpb3VzOyB9XG4gICAgICBpZiAoY2FuU2VsZWN0UHJldmlvdXMgIT09IHByZXZpb3VzQ2FuU2VsZWN0UHJldmlvdXMpIHtcbiAgICAgICAgdGhpcy5kaXNwYXRjaEV2ZW50KG5ldyBDdXN0b21FdmVudCgnY2FuLXNlbGVjdC1wcmV2aW91cy1jaGFuZ2VkJykpO1xuICAgICAgfVxuICAgIH1cblxuICAgIGdldCBbc3ltYm9scy5kZWZhdWx0c10oKSB7XG4gICAgICBjb25zdCBkZWZhdWx0cyA9IHN1cGVyW3N5bWJvbHMuZGVmYXVsdHNdIHx8IHt9O1xuICAgICAgZGVmYXVsdHMuc2VsZWN0aW9uUmVxdWlyZWQgPSBmYWxzZTtcbiAgICAgIGRlZmF1bHRzLnNlbGVjdGlvbldyYXBzID0gZmFsc2U7XG4gICAgICByZXR1cm4gZGVmYXVsdHM7XG4gICAgfVxuXG4gICAgLyoqXG4gICAgICogSGFuZGxlIGEgbmV3IGl0ZW0gYmVpbmcgYWRkZWQgdG8gdGhlIGxpc3QuXG4gICAgICpcbiAgICAgKiBUaGUgZGVmYXVsdCBpbXBsZW1lbnRhdGlvbiBvZiB0aGlzIG1ldGhvZCBzaW1wbHkgc2V0cyB0aGUgaXRlbSdzXG4gICAgICogc2VsZWN0aW9uIHN0YXRlIHRvIGZhbHNlLlxuICAgICAqXG4gICAgICogQHBhcmFtIHtIVE1MRWxlbWVudH0gaXRlbSAtIHRoZSBpdGVtIGJlaW5nIGFkZGVkXG4gICAgICovXG4gICAgW3N5bWJvbHMuaXRlbUFkZGVkXShpdGVtKSB7XG4gICAgICBpZiAoc3VwZXJbc3ltYm9scy5pdGVtQWRkZWRdKSB7IHN1cGVyW3N5bWJvbHMuaXRlbUFkZGVkXShpdGVtKTsgfVxuICAgICAgdGhpc1tzeW1ib2xzLml0ZW1TZWxlY3RlZF0oaXRlbSwgaXRlbSA9PT0gdGhpcy5zZWxlY3RlZEl0ZW0pO1xuICAgIH1cblxuICAgIFtzeW1ib2xzLml0ZW1zQ2hhbmdlZF0oKSB7XG4gICAgICBpZiAoc3VwZXJbc3ltYm9scy5pdGVtc0NoYW5nZWRdKSB7IHN1cGVyW3N5bWJvbHMuaXRlbXNDaGFuZ2VkXSgpOyB9XG5cbiAgICAgIC8vIEluIGNhc2Ugc2VsZWN0ZWQgaXRlbSBjaGFuZ2VkIHBvc2l0aW9uIG9yIHdhcyByZW1vdmVkLlxuICAgICAgdHJhY2tTZWxlY3RlZEl0ZW0odGhpcyk7XG5cbiAgICAgIC8vIEluIGNhc2UgdGhlIGNoYW5nZSBpbiBpdGVtcyBhZmZlY3RlZCB3aGljaCBuYXZpZ2F0aW9ucyBhcmUgcG9zc2libGUuXG4gICAgICB1cGRhdGVQb3NzaWJsZU5hdmlnYXRpb25zKHRoaXMpO1xuICAgIH1cblxuICAgIC8qKlxuICAgICAqIEFwcGx5IHRoZSBpbmRpY2F0ZSBzZWxlY3Rpb24gc3RhdGUgdG8gdGhlIGl0ZW0uXG4gICAgICpcbiAgICAgKiBUaGUgZGVmYXVsdCBpbXBsZW1lbnRhdGlvbiBvZiB0aGlzIG1ldGhvZCBkb2VzIG5vdGhpbmcuIFVzZXItdmlzaWJsZVxuICAgICAqIGVmZmVjdHMgd2lsbCB0eXBpY2FsbHkgYmUgaGFuZGxlZCBieSBvdGhlciBtaXhpbnMuXG4gICAgICpcbiAgICAgKiBAcGFyYW0ge0hUTUxFbGVtZW50fSBpdGVtIC0gdGhlIGl0ZW0gYmVpbmcgc2VsZWN0ZWQvZGVzZWxlY3RlZFxuICAgICAqIEBwYXJhbSB7Ym9vbGVhbn0gc2VsZWN0ZWQgLSB0cnVlIGlmIHRoZSBpdGVtIGlzIHNlbGVjdGVkLCBmYWxzZSBpZiBub3RcbiAgICAgKi9cbiAgICBbc3ltYm9scy5pdGVtU2VsZWN0ZWRdKGl0ZW0sIHNlbGVjdGVkKSB7XG4gICAgICBpZiAoc3VwZXJbc3ltYm9scy5pdGVtU2VsZWN0ZWRdKSB7IHN1cGVyW3N5bWJvbHMuaXRlbVNlbGVjdGVkXShpdGVtLCBzZWxlY3RlZCk7IH1cbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBUaGUgaW5kZXggb2YgdGhlIGl0ZW0gd2hpY2ggaXMgY3VycmVudGx5IHNlbGVjdGVkLlxuICAgICAqXG4gICAgICogQSBgc2VsZWN0ZWRJbmRleGAgb2YgLTEgaW5kaWNhdGVzIHRoZXJlIGlzIG5vIHNlbGVjdGlvbi4gU2V0dGluZyB0aGlzXG4gICAgICogcHJvcGVydHkgdG8gLTEgd2lsbCByZW1vdmUgYW55IGV4aXN0aW5nIHNlbGVjdGlvbi5cbiAgICAgKlxuICAgICAqIEB0eXBlIHtudW1iZXJ9XG4gICAgICovXG4gICAgZ2V0IHNlbGVjdGVkSW5kZXgoKSB7XG4gICAgICByZXR1cm4gdGhpc1tleHRlcm5hbFNlbGVjdGVkSW5kZXhTeW1ib2xdICE9IG51bGwgP1xuICAgICAgICB0aGlzW2V4dGVybmFsU2VsZWN0ZWRJbmRleFN5bWJvbF0gOlxuICAgICAgICAtMTtcbiAgICB9XG4gICAgc2V0IHNlbGVjdGVkSW5kZXgoaW5kZXgpIHtcbiAgICAgIC8vIFNlZSBub3RlcyBhdCB0b3AgYWJvdXQgaW50ZXJuYWwgdnMuIGV4dGVybmFsIGNvcGllcyBvZiB0aGlzIHByb3BlcnR5LlxuICAgICAgY29uc3QgcHJldmlvdXNTZWxlY3RlZEluZGV4ID0gdGhpc1tpbnRlcm5hbFNlbGVjdGVkSW5kZXhTeW1ib2xdO1xuICAgICAgbGV0IGl0ZW07XG4gICAgICBpZiAoaW5kZXggIT09IHRoaXNbZXh0ZXJuYWxTZWxlY3RlZEluZGV4U3ltYm9sXSkge1xuICAgICAgICAvLyBTdG9yZSB0aGUgbmV3IGluZGV4IGFuZCB0aGUgY29ycmVzcG9uZGluZyBpdGVtLlxuICAgICAgICBjb25zdCBpdGVtcyA9IHRoaXMuaXRlbXM7XG4gICAgICAgIGNvbnN0IGhhc0l0ZW1zID0gaXRlbXMgJiYgaXRlbXMubGVuZ3RoID4gMDtcbiAgICAgICAgaWYgKCEoaGFzSXRlbXMgJiYgaW5kZXggPj0gMCAmJiBpbmRleCA8IGl0ZW1zLmxlbmd0aCkpIHtcbiAgICAgICAgICBpbmRleCA9IC0xOyAvLyBObyBpdGVtIGF0IHRoYXQgaW5kZXguXG4gICAgICAgIH1cbiAgICAgICAgdGhpc1tleHRlcm5hbFNlbGVjdGVkSW5kZXhTeW1ib2xdID0gaW5kZXg7XG4gICAgICAgIGl0ZW0gPSBoYXNJdGVtcyAmJiBpbmRleCA+PSAwID8gaXRlbXNbaW5kZXhdIDogbnVsbDtcbiAgICAgICAgdGhpc1tleHRlcm5hbFNlbGVjdGVkSXRlbVN5bWJvbF0gPSBpdGVtO1xuICAgICAgfSBlbHNlIHtcbiAgICAgICAgaXRlbSA9IHRoaXNbZXh0ZXJuYWxTZWxlY3RlZEl0ZW1TeW1ib2xdO1xuICAgICAgfVxuXG4gICAgICAvLyBOb3cgbGV0IHN1cGVyIGRvIGFueSB3b3JrLlxuICAgICAgaWYgKCdzZWxlY3RlZEluZGV4JyBpbiBiYXNlLnByb3RvdHlwZSkgeyBzdXBlci5zZWxlY3RlZEluZGV4ID0gaW5kZXg7IH1cblxuICAgICAgaWYgKGluZGV4ICE9PSBwcmV2aW91c1NlbGVjdGVkSW5kZXgpIHtcbiAgICAgICAgLy8gVGhlIHNlbGVjdGVkIGluZGV4IGNoYW5nZWQuXG4gICAgICAgIHRoaXNbaW50ZXJuYWxTZWxlY3RlZEluZGV4U3ltYm9sXSA9IGluZGV4O1xuXG4gICAgICAgIGNvbnN0IGV2ZW50ID0gbmV3IEN1c3RvbUV2ZW50KCdzZWxlY3RlZC1pbmRleC1jaGFuZ2VkJywge1xuICAgICAgICAgIGRldGFpbDoge1xuICAgICAgICAgICAgc2VsZWN0ZWRJbmRleDogaW5kZXgsXG4gICAgICAgICAgICB2YWx1ZTogaW5kZXggLy8gZm9yIFBvbHltZXIgYmluZGluZy4gVE9ETzogVmVyaWZ5IHN0aWxsIG5lY2Vzc2FyeVxuICAgICAgICAgIH1cbiAgICAgICAgfSk7XG4gICAgICAgIHRoaXMuZGlzcGF0Y2hFdmVudChldmVudCk7XG4gICAgICB9XG5cbiAgICAgIGlmICh0aGlzW2ludGVybmFsU2VsZWN0ZWRJdGVtU3ltYm9sXSAhPT0gaXRlbSkge1xuICAgICAgICAvLyBVcGRhdGUgc2VsZWN0ZWRJdGVtIHByb3BlcnR5IHNvIGl0IGNhbiBoYXZlIGl0cyBvd24gZWZmZWN0cy5cbiAgICAgICAgdGhpcy5zZWxlY3RlZEl0ZW0gPSBpdGVtO1xuICAgICAgfVxuICAgIH1cblxuICAgIC8qKlxuICAgICAqIFRoZSBjdXJyZW50bHkgc2VsZWN0ZWQgaXRlbSwgb3IgbnVsbCBpZiB0aGVyZSBpcyBubyBzZWxlY3Rpb24uXG4gICAgICpcbiAgICAgKiBTZXR0aW5nIHRoaXMgcHJvcGVydHkgdG8gbnVsbCBkZXNlbGVjdHMgYW55IGN1cnJlbnRseS1zZWxlY3RlZCBpdGVtLlxuICAgICAqIFNldHRpbmcgdGhpcyBwcm9wZXJ0eSB0byBhbiBvYmplY3QgdGhhdCBpcyBub3QgaW4gdGhlIGxpc3QgaGFzIG5vIGVmZmVjdC5cbiAgICAgKlxuICAgICAqIFRPRE86IEV2ZW4gaWYgc2VsZWN0aW9uUmVxdWlyZWQsIGNhbiBzdGlsbCBleHBsaWNpdGx5IHNldCBzZWxlY3RlZEl0ZW0gdG8gbnVsbC5cbiAgICAgKiBUT0RPOiBJZiBzZWxlY3Rpb25SZXF1aXJlZCwgbGVhdmUgc2VsZWN0aW9uIGFsb25lP1xuICAgICAqXG4gICAgICogQHR5cGUge29iamVjdH1cbiAgICAgKi9cbiAgICBnZXQgc2VsZWN0ZWRJdGVtKCkge1xuICAgICAgcmV0dXJuIHRoaXNbZXh0ZXJuYWxTZWxlY3RlZEl0ZW1TeW1ib2xdIHx8IG51bGw7XG4gICAgfVxuICAgIHNldCBzZWxlY3RlZEl0ZW0oaXRlbSkge1xuICAgICAgLy8gU2VlIG5vdGVzIGF0IHRvcCBhYm91dCBpbnRlcm5hbCB2cy4gZXh0ZXJuYWwgY29waWVzIG9mIHRoaXMgcHJvcGVydHkuXG4gICAgICBjb25zdCBwcmV2aW91c1NlbGVjdGVkSXRlbSA9IHRoaXNbaW50ZXJuYWxTZWxlY3RlZEl0ZW1TeW1ib2xdO1xuICAgICAgbGV0IGluZGV4O1xuICAgICAgaWYgKGl0ZW0gIT09IHRoaXNbZXh0ZXJuYWxTZWxlY3RlZEl0ZW1TeW1ib2xdKSB7XG4gICAgICAgIC8vIFN0b3JlIGl0ZW0gYW5kIGxvb2sgdXAgY29ycmVzcG9uZGluZyBpbmRleC5cbiAgICAgICAgY29uc3QgaXRlbXMgPSB0aGlzLml0ZW1zO1xuICAgICAgICBjb25zdCBoYXNJdGVtcyA9IGl0ZW1zICYmIGl0ZW1zLmxlbmd0aCA+IDA7XG4gICAgICAgIGluZGV4ID0gaGFzSXRlbXMgPyBBcnJheS5wcm90b3R5cGUuaW5kZXhPZi5jYWxsKGl0ZW1zLCBpdGVtKSA6IC0xO1xuICAgICAgICB0aGlzW2V4dGVybmFsU2VsZWN0ZWRJbmRleFN5bWJvbF0gPSBpbmRleDtcbiAgICAgICAgaWYgKGluZGV4IDwgMCkge1xuICAgICAgICAgIGl0ZW0gPSBudWxsOyAvLyBUaGUgaW5kaWNhdGVkIGl0ZW0gaXNuJ3QgYWN0dWFsbHkgaW4gYGl0ZW1zYC5cbiAgICAgICAgfVxuICAgICAgICB0aGlzW2V4dGVybmFsU2VsZWN0ZWRJdGVtU3ltYm9sXSA9IGl0ZW07XG4gICAgICB9IGVsc2Uge1xuICAgICAgICBpbmRleCA9IHRoaXNbZXh0ZXJuYWxTZWxlY3RlZEluZGV4U3ltYm9sXTtcbiAgICAgIH1cblxuICAgICAgLy8gTm93IGxldCBzdXBlciBkbyBhbnkgd29yay5cbiAgICAgIGlmICgnc2VsZWN0ZWRJdGVtJyBpbiBiYXNlLnByb3RvdHlwZSkgeyBzdXBlci5zZWxlY3RlZEl0ZW0gPSBpdGVtOyB9XG5cbiAgICAgIGlmIChpdGVtICE9PSBwcmV2aW91c1NlbGVjdGVkSXRlbSkge1xuICAgICAgICAvLyBUaGUgc2VsZWN0ZWQgaXRlbSBjaGFuZ2VkLlxuICAgICAgICB0aGlzW2ludGVybmFsU2VsZWN0ZWRJdGVtU3ltYm9sXSA9IGl0ZW07XG5cbiAgICAgICAgaWYgKHByZXZpb3VzU2VsZWN0ZWRJdGVtKSB7XG4gICAgICAgICAgLy8gVXBkYXRlIHNlbGVjdGlvbiBzdGF0ZSBvZiBvbGQgaXRlbS5cbiAgICAgICAgICB0aGlzW3N5bWJvbHMuaXRlbVNlbGVjdGVkXShwcmV2aW91c1NlbGVjdGVkSXRlbSwgZmFsc2UpO1xuICAgICAgICB9XG4gICAgICAgIGlmIChpdGVtKSB7XG4gICAgICAgICAgLy8gVXBkYXRlIHNlbGVjdGlvbiBzdGF0ZSB0byBuZXcgaXRlbS5cbiAgICAgICAgICB0aGlzW3N5bWJvbHMuaXRlbVNlbGVjdGVkXShpdGVtLCB0cnVlKTtcbiAgICAgICAgfVxuXG4gICAgICAgIHVwZGF0ZVBvc3NpYmxlTmF2aWdhdGlvbnModGhpcyk7XG5cbiAgICAgICAgY29uc3QgZXZlbnQgPSBuZXcgQ3VzdG9tRXZlbnQoJ3NlbGVjdGVkLWl0ZW0tY2hhbmdlZCcsIHtcbiAgICAgICAgICBkZXRhaWw6IHtcbiAgICAgICAgICAgIHNlbGVjdGVkSXRlbTogaXRlbSxcbiAgICAgICAgICAgIHZhbHVlOiBpdGVtIC8vIGZvciBQb2x5bWVyIGJpbmRpbmdcbiAgICAgICAgICB9XG4gICAgICAgIH0pO1xuICAgICAgICB0aGlzLmRpc3BhdGNoRXZlbnQoZXZlbnQpO1xuICAgICAgfVxuXG4gICAgICBpZiAodGhpc1tpbnRlcm5hbFNlbGVjdGVkSW5kZXhTeW1ib2xdICE9PSBpbmRleCkge1xuICAgICAgICAvLyBVcGRhdGUgc2VsZWN0ZWRJbmRleCBwcm9wZXJ0eSBzbyBpdCBjYW4gaGF2ZSBpdHMgb3duIGVmZmVjdHMuXG4gICAgICAgIHRoaXMuc2VsZWN0ZWRJbmRleCA9IGluZGV4O1xuICAgICAgfVxuICAgIH1cblxuICAgIC8qKlxuICAgICAqIFNlbGVjdCB0aGUgZmlyc3QgaXRlbSBpbiB0aGUgbGlzdC5cbiAgICAgKi9cbiAgICBzZWxlY3RGaXJzdCgpIHtcbiAgICAgIGlmIChzdXBlci5zZWxlY3RGaXJzdCkgeyBzdXBlci5zZWxlY3RGaXJzdCgpOyB9XG4gICAgICByZXR1cm4gc2VsZWN0SW5kZXgodGhpcywgMCk7XG4gICAgfVxuXG4gICAgLyoqXG4gICAgICogVHJ1ZSBpZiB0aGUgbGlzdCBzaG91bGQgYWx3YXlzIGhhdmUgYSBzZWxlY3Rpb24gKGlmIGl0IGhhcyBpdGVtcykuXG4gICAgICpcbiAgICAgKiBAdHlwZSB7Ym9vbGVhbn1cbiAgICAgKiBAZGVmYXVsdCBmYWxzZVxuICAgICAqL1xuICAgIGdldCBzZWxlY3Rpb25SZXF1aXJlZCgpIHtcbiAgICAgIHJldHVybiB0aGlzW3NlbGVjdGlvblJlcXVpcmVkU3ltYm9sXTtcbiAgICB9XG4gICAgc2V0IHNlbGVjdGlvblJlcXVpcmVkKHNlbGVjdGlvblJlcXVpcmVkKSB7XG4gICAgICB0aGlzW3NlbGVjdGlvblJlcXVpcmVkU3ltYm9sXSA9IHNlbGVjdGlvblJlcXVpcmVkO1xuICAgICAgaWYgKCdzZWxlY3Rpb25SZXF1aXJlZCcgaW4gYmFzZS5wcm90b3R5cGUpIHsgc3VwZXIuc2VsZWN0aW9uUmVxdWlyZWQgPSBzZWxlY3Rpb25SZXF1aXJlZDsgfVxuICAgICAgdHJhY2tTZWxlY3RlZEl0ZW0odGhpcyk7XG4gICAgfVxuXG4gICAgLyoqXG4gICAgICogVHJ1ZSBpZiBzZWxlY3Rpb24gbmF2aWdhdGlvbnMgd3JhcCBmcm9tIGxhc3QgdG8gZmlyc3QsIGFuZCB2aWNlIHZlcnNhLlxuICAgICAqXG4gICAgICogQHR5cGUge2Jvb2xlYW59XG4gICAgICogQGRlZmF1bHQgZmFsc2VcbiAgICAgKi9cbiAgICBnZXQgc2VsZWN0aW9uV3JhcHMoKSB7XG4gICAgICByZXR1cm4gdGhpc1tzZWxlY3Rpb25XcmFwc1N5bWJvbF07XG4gICAgfVxuICAgIHNldCBzZWxlY3Rpb25XcmFwcyh2YWx1ZSkge1xuICAgICAgdGhpc1tzZWxlY3Rpb25XcmFwc1N5bWJvbF0gPSBTdHJpbmcodmFsdWUpID09PSAndHJ1ZSc7XG4gICAgICBpZiAoJ3NlbGVjdGlvbldyYXBzJyBpbiBiYXNlLnByb3RvdHlwZSkgeyBzdXBlci5zZWxlY3Rpb25XcmFwcyA9IHZhbHVlOyB9XG4gICAgICB1cGRhdGVQb3NzaWJsZU5hdmlnYXRpb25zKHRoaXMpO1xuICAgIH1cblxuICAgIC8qKlxuICAgICAqIFNlbGVjdCB0aGUgbGFzdCBpdGVtIGluIHRoZSBsaXN0LlxuICAgICAqL1xuICAgIHNlbGVjdExhc3QoKSB7XG4gICAgICBpZiAoc3VwZXIuc2VsZWN0TGFzdCkgeyBzdXBlci5zZWxlY3RMYXN0KCk7IH1cbiAgICAgIHJldHVybiBzZWxlY3RJbmRleCh0aGlzLCB0aGlzLml0ZW1zLmxlbmd0aCAtIDEpO1xuICAgIH1cblxuICAgIC8qKlxuICAgICAqIFNlbGVjdCB0aGUgbmV4dCBpdGVtIGluIHRoZSBsaXN0LlxuICAgICAqL1xuICAgIHNlbGVjdE5leHQoKSB7XG4gICAgICBpZiAoc3VwZXIuc2VsZWN0TmV4dCkgeyBzdXBlci5zZWxlY3ROZXh0KCk7IH1cbiAgICAgIHJldHVybiBzZWxlY3RJbmRleCh0aGlzLCB0aGlzLnNlbGVjdGVkSW5kZXggKyAxKTtcbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBTZWxlY3QgdGhlIHByZXZpb3VzIGl0ZW0gaW4gdGhlIGxpc3QuXG4gICAgICpcbiAgICAgKiBJZiB0aGUgbGlzdCBoYXMgbm8gc2VsZWN0aW9uLCB0aGUgbGFzdCBpdGVtIHdpbGwgYmUgc2VsZWN0ZWQuXG4gICAgICovXG4gICAgc2VsZWN0UHJldmlvdXMoKSB7XG4gICAgICBpZiAoc3VwZXIuc2VsZWN0UHJldmlvdXMpIHsgc3VwZXIuc2VsZWN0UHJldmlvdXMoKTsgfVxuICAgICAgY29uc3QgbmV3SW5kZXggPSB0aGlzLnNlbGVjdGVkSW5kZXggPCAwID9cbiAgICAgICAgdGhpcy5pdGVtcy5sZW5ndGggLSAxIDogICAgIC8vIE5vIHNlbGVjdGlvbiB5ZXQ7IHNlbGVjdCBsYXN0IGl0ZW0uXG4gICAgICAgIHRoaXMuc2VsZWN0ZWRJbmRleCAtIDE7XG4gICAgICByZXR1cm4gc2VsZWN0SW5kZXgodGhpcywgbmV3SW5kZXgpO1xuICAgIH1cblxuICAgIC8qKlxuICAgICAqIEZpcmVzIHdoZW4gdGhlIHNlbGVjdGVkSXRlbSBwcm9wZXJ0eSBjaGFuZ2VzLlxuICAgICAqXG4gICAgICogQG1lbWJlcm9mIFNpbmdsZVNlbGVjdGlvblxuICAgICAqIEBldmVudCBzZWxlY3RlZC1pdGVtLWNoYW5nZWRcbiAgICAgKiBAcGFyYW0ge0hUTUxFbGVtZW50fSBkZXRhaWwuc2VsZWN0ZWRJdGVtIFRoZSBuZXcgc2VsZWN0ZWQgaXRlbS5cbiAgICAgKiBAcGFyYW0ge0hUTUxFbGVtZW50fSBkZXRhaWwucHJldmlvdXNJdGVtIFRoZSBwcmV2aW91c2x5IHNlbGVjdGVkIGl0ZW0uXG4gICAgICovXG5cbiAgICAvKipcbiAgICAgKiBGaXJlcyB3aGVuIHRoZSBzZWxlY3RlZEluZGV4IHByb3BlcnR5IGNoYW5nZXMuXG4gICAgICpcbiAgICAgKiBAbWVtYmVyb2YgU2luZ2xlU2VsZWN0aW9uXG4gICAgICogQGV2ZW50IHNlbGVjdGVkLWluZGV4LWNoYW5nZWRcbiAgICAgKiBAcGFyYW0ge251bWJlcn0gZGV0YWlsLnNlbGVjdGVkSW5kZXggVGhlIG5ldyBzZWxlY3RlZCBpbmRleC5cbiAgICAgKi9cblxuICB9XG5cbiAgcmV0dXJuIFNpbmdsZVNlbGVjdGlvbjtcbn07XG5cblxuLy8gRW5zdXJlIHRoZSBnaXZlbiBpbmRleCBpcyB3aXRoaW4gYm91bmRzLCBhbmQgc2VsZWN0IGl0IGlmIGl0J3Mgbm90IGFscmVhZHlcbi8vIHNlbGVjdGVkLlxuZnVuY3Rpb24gc2VsZWN0SW5kZXgoZWxlbWVudCwgaW5kZXgpIHtcbiAgY29uc3QgY291bnQgPSBlbGVtZW50Lml0ZW1zLmxlbmd0aDtcblxuICBjb25zdCBib3VuZGVkSW5kZXggPSAoZWxlbWVudC5zZWxlY3Rpb25XcmFwcykgP1xuICAgIC8vIEphdmFTY3JpcHQgbW9kIGRvZXNuJ3QgaGFuZGxlIG5lZ2F0aXZlIG51bWJlcnMgdGhlIHdheSB3ZSB3YW50IHRvIHdyYXAuXG4gICAgLy8gU2VlIGh0dHA6Ly9zdGFja292ZXJmbG93LmNvbS9hLzE4NjE4MjUwLzc2NDcyXG4gICAgKChpbmRleCAlIGNvdW50KSArIGNvdW50KSAlIGNvdW50IDpcblxuICAgIC8vIEtlZXAgaW5kZXggd2l0aGluIGJvdW5kcyBvZiBhcnJheS5cbiAgICBNYXRoLm1heChNYXRoLm1pbihpbmRleCwgY291bnQgLSAxKSwgMCk7XG5cbiAgY29uc3QgcHJldmlvdXNJbmRleCA9IGVsZW1lbnQuc2VsZWN0ZWRJbmRleDtcbiAgaWYgKHByZXZpb3VzSW5kZXggIT09IGJvdW5kZWRJbmRleCkge1xuICAgIGVsZW1lbnQuc2VsZWN0ZWRJbmRleCA9IGJvdW5kZWRJbmRleDtcbiAgICByZXR1cm4gdHJ1ZTtcbiAgfSBlbHNlIHtcbiAgICByZXR1cm4gZmFsc2U7XG4gIH1cbn1cblxuLy8gRm9sbG93aW5nIGEgY2hhbmdlIGluIHRoZSBzZXQgb2YgaXRlbXMsIG9yIGluIHRoZSB2YWx1ZSBvZiB0aGVcbi8vIGBzZWxlY3Rpb25SZXF1aXJlZGAgcHJvcGVydHksIHJlYWNxdWlyZSB0aGUgc2VsZWN0ZWQgaXRlbS4gSWYgaXQncyBtb3ZlZCxcbi8vIHVwZGF0ZSBgc2VsZWN0ZWRJbmRleGAuIElmIGl0J3MgYmVlbiByZW1vdmVkLCBhbmQgYSBzZWxlY3Rpb24gaXMgcmVxdWlyZWQsXG4vLyB0cnkgdG8gc2VsZWN0IGFub3RoZXIgaXRlbS5cbmZ1bmN0aW9uIHRyYWNrU2VsZWN0ZWRJdGVtKGVsZW1lbnQpIHtcblxuICBjb25zdCBpdGVtcyA9IGVsZW1lbnQuaXRlbXM7XG4gIGNvbnN0IGl0ZW1Db3VudCA9IGl0ZW1zID8gaXRlbXMubGVuZ3RoIDogMDtcblxuICBjb25zdCBwcmV2aW91c1NlbGVjdGVkSXRlbSA9IGVsZW1lbnQuc2VsZWN0ZWRJdGVtO1xuICBpZiAoIXByZXZpb3VzU2VsZWN0ZWRJdGVtKSB7XG4gICAgLy8gTm8gaXRlbSB3YXMgcHJldmlvdXNseSBzZWxlY3RlZC5cbiAgICBpZiAoZWxlbWVudC5zZWxlY3Rpb25SZXF1aXJlZCkge1xuICAgICAgLy8gU2VsZWN0IHRoZSBmaXJzdCBpdGVtIGJ5IGRlZmF1bHQuXG4gICAgICBlbGVtZW50LnNlbGVjdGVkSW5kZXggPSAwO1xuICAgIH1cbiAgfSBlbHNlIGlmIChpdGVtQ291bnQgPT09IDApIHtcbiAgICAvLyBXZSd2ZSBsb3N0IHRoZSBzZWxlY3Rpb24sIGFuZCB0aGVyZSdzIG5vdGhpbmcgbGVmdCB0byBzZWxlY3QuXG4gICAgZWxlbWVudC5zZWxlY3RlZEl0ZW0gPSBudWxsO1xuICB9IGVsc2Uge1xuICAgIC8vIFRyeSB0byBmaW5kIHRoZSBwcmV2aW91c2x5LXNlbGVjdGVkIGl0ZW0gaW4gdGhlIGN1cnJlbnQgc2V0IG9mIGl0ZW1zLlxuICAgIGNvbnN0IGluZGV4SW5DdXJyZW50SXRlbXMgPSBBcnJheS5wcm90b3R5cGUuaW5kZXhPZi5jYWxsKGl0ZW1zLCBwcmV2aW91c1NlbGVjdGVkSXRlbSk7XG4gICAgY29uc3QgcHJldmlvdXNTZWxlY3RlZEluZGV4ID0gZWxlbWVudC5zZWxlY3RlZEluZGV4O1xuICAgIGlmIChpbmRleEluQ3VycmVudEl0ZW1zIDwgMCkge1xuICAgICAgLy8gUHJldmlvdXNseS1zZWxlY3RlZCBpdGVtIHdhcyByZW1vdmVkIGZyb20gdGhlIGl0ZW1zLlxuICAgICAgLy8gU2VsZWN0IHRoZSBpdGVtIGF0IHRoZSBzYW1lIGluZGV4IChpZiBpdCBleGlzdHMpIG9yIGFzIGNsb3NlIGFzIHBvc3NpYmxlLlxuICAgICAgY29uc3QgbmV3U2VsZWN0ZWRJbmRleCA9IE1hdGgubWluKHByZXZpb3VzU2VsZWN0ZWRJbmRleCwgaXRlbUNvdW50IC0gMSk7XG4gICAgICAvLyBTZWxlY3QgYnkgaXRlbSwgc2luY2UgaW5kZXggbWF5IGJlIHRoZSBzYW1lLCBhbmQgd2Ugd2FudCB0byByYWlzZSB0aGVcbiAgICAgIC8vIHNlbGVjdGVkLWl0ZW0tY2hhbmdlZCBldmVudC5cbiAgICAgIGVsZW1lbnQuc2VsZWN0ZWRJdGVtID0gaXRlbXNbbmV3U2VsZWN0ZWRJbmRleF07XG4gICAgfSBlbHNlIGlmIChpbmRleEluQ3VycmVudEl0ZW1zICE9PSBwcmV2aW91c1NlbGVjdGVkSW5kZXgpIHtcbiAgICAgIC8vIFByZXZpb3VzbHktc2VsZWN0ZWQgaXRlbSBzdGlsbCB0aGVyZSwgYnV0IGNoYW5nZWQgcG9zaXRpb24uXG4gICAgICBlbGVtZW50LnNlbGVjdGVkSW5kZXggPSBpbmRleEluQ3VycmVudEl0ZW1zO1xuICAgIH1cbiAgfVxufVxuXG4vLyBGb2xsb3dpbmcgYSBjaGFuZ2UgaW4gc2VsZWN0aW9uLCByZXBvcnQgd2hldGhlciBpdCdzIG5vdyBwb3NzaWJsZSB0b1xuLy8gZ28gbmV4dC9wcmV2aW91cyBmcm9tIHRoZSBnaXZlbiBpbmRleC5cbmZ1bmN0aW9uIHVwZGF0ZVBvc3NpYmxlTmF2aWdhdGlvbnMoZWxlbWVudCkge1xuICBsZXQgY2FuU2VsZWN0TmV4dDtcbiAgbGV0IGNhblNlbGVjdFByZXZpb3VzO1xuICBjb25zdCBpdGVtcyA9IGVsZW1lbnQuaXRlbXM7XG4gIGlmIChpdGVtcyA9PSBudWxsIHx8IGl0ZW1zLmxlbmd0aCA9PT0gMCkge1xuICAgIC8vIE5vIGl0ZW1zIHRvIHNlbGVjdC5cbiAgICBjYW5TZWxlY3ROZXh0ID0gZmFsc2U7XG4gICAgY2FuU2VsZWN0UHJldmlvdXMgPSBmYWxzZTtcbiAgfSBpZiAoZWxlbWVudC5zZWxlY3Rpb25XcmFwcykge1xuICAgIC8vIFNpbmNlIHRoZXJlIGFyZSBpdGVtcywgY2FuIGFsd2F5cyBnbyBuZXh0L3ByZXZpb3VzLlxuICAgIGNhblNlbGVjdE5leHQgPSB0cnVlO1xuICAgIGNhblNlbGVjdFByZXZpb3VzID0gdHJ1ZTtcbiAgfSBlbHNlIHtcbiAgICBjb25zdCBpbmRleCA9IGVsZW1lbnQuc2VsZWN0ZWRJbmRleDtcbiAgICBpZiAoaW5kZXggPCAwICYmIGl0ZW1zLmxlbmd0aCA+IDApIHtcbiAgICAgIC8vIFNwZWNpYWwgY2FzZS4gSWYgdGhlcmUgYXJlIGl0ZW1zIGJ1dCBubyBzZWxlY3Rpb24sIGRlY2xhcmUgdGhhdCBpdCdzXG4gICAgICAvLyBhbHdheXMgcG9zc2libGUgdG8gZ28gbmV4dC9wcmV2aW91cyB0byBjcmVhdGUgYSBzZWxlY3Rpb24uXG4gICAgICBjYW5TZWxlY3ROZXh0ID0gdHJ1ZTtcbiAgICAgIGNhblNlbGVjdFByZXZpb3VzID0gdHJ1ZTtcbiAgICB9IGVsc2Uge1xuICAgICAgLy8gTm9ybWFsIGNhc2U6IHdlIGhhdmUgYW4gaW5kZXggaW4gYSBsaXN0IHRoYXQgaGFzIGl0ZW1zLlxuICAgICAgY2FuU2VsZWN0UHJldmlvdXMgPSAoaW5kZXggPiAwKTtcbiAgICAgIGNhblNlbGVjdE5leHQgPSAoaW5kZXggPCBpdGVtcy5sZW5ndGggLSAxKTtcbiAgICB9XG4gIH1cbiAgaWYgKGVsZW1lbnQuY2FuU2VsZWN0TmV4dCAhPT0gY2FuU2VsZWN0TmV4dCkge1xuICAgIGVsZW1lbnQuY2FuU2VsZWN0TmV4dCA9IGNhblNlbGVjdE5leHQ7XG4gIH1cbiAgaWYgKGVsZW1lbnQuY2FuU2VsZWN0UHJldmlvdXMgIT09IGNhblNlbGVjdFByZXZpb3VzKSB7XG4gICAgZWxlbWVudC5jYW5TZWxlY3RQcmV2aW91cyA9IGNhblNlbGVjdFByZXZpb3VzO1xuICB9XG59XG4iLCIvKipcbiAqIEhlbHBlciBmdW5jdGlvbiB0byBjcmVhdGUgYSBzeW1ib2wgdGhhdCBjYW4gYmUgdXNlZCBmb3IgYXNzb2NpYXRpbmcgcHJpdmF0ZVxuICogZGF0YSB3aXRoIGFuIGVsZW1lbnQuXG4gKlxuICogTWl4aW5zIGFuZCBjb21wb25lbnQgY2xhc3NlcyBvZnRlbiB3YW50IHRvIGFzc29jaWF0ZSBwcml2YXRlIGRhdGEgd2l0aCBhblxuICogZWxlbWVudCBpbnN0YW5jZSwgYnV0IEphdmFTY3JpcHQgZG9lcyBub3QgaGF2ZSBkaXJlY3Qgc3VwcG9ydCBmb3IgdHJ1ZVxuICogcHJpdmF0ZSBwcm9wZXJ0aWVzLiBPbmUgYXBwcm9hY2ggaXMgdG8gdXNlIHRoZVxuICogW1N5bWJvbF0oaHR0cHM6Ly9kZXZlbG9wZXIubW96aWxsYS5vcmcvZW4tVVMvZG9jcy9XZWIvSmF2YVNjcmlwdC9SZWZlcmVuY2UvR2xvYmFsX09iamVjdHMvU3ltYm9sKVxuICogZGF0YSB0eXBlIHRvIHNldCBhbmQgcmV0cmlldmUgZGF0YSBvbiBhbiBlbGVtZW50LlxuICpcbiAqIFVuZm9ydHVuYXRlbHksIHRoZSBTeW1ib2wgdHlwZSBpcyBub3QgYXZhaWxhYmxlIGluIEludGVybmV0IEV4cGxvcmVyIDExLiBUaGVcbiAqIGBjcmVhdGVTeW1ib2xgIGhlbHBlciBmdW5jdGlvbiBleGlzdHMgYXMgYSB3b3JrYXJvdW5kIGZvciBJRSAxMS4gUmF0aGVyIHRoYW5cbiAqIHJldHVybmluZyBhIHRydWUgU3ltYm9sLCBpdCBzaW1wbHkgcmV0dXJucyBhbiB1bmRlcnNjb3JlLXByZWZpeGVkIHN0cmluZy5cbiAqXG4gKiBVc2FnZTpcbiAqXG4gKiAgICAgY29uc3QgZm9vU3ltYm9sID0gY3JlYXRlU3ltYm9sKCdmb28nKTtcbiAqXG4gKiAgICAgY2xhc3MgTXlFbGVtZW50IGV4dGVuZHMgSFRNTEVsZW1lbnQge1xuICogICAgICAgZ2V0IGZvbygpIHtcbiAqICAgICAgICAgcmV0dXJuIHRoaXNbZm9vU3ltYm9sXTtcbiAqICAgICAgIH1cbiAqICAgICAgIHNldCBmb28odmFsdWUpIHtcbiAqICAgICAgICAgdGhpc1tmb29TeW1ib2xdID0gdmFsdWU7XG4gKiAgICAgICB9XG4gKiAgICAgfVxuICpcbiAqIEluIElFIDExLCB0aGlzIHNhbXBsZSB3aWxsIFwiaGlkZVwiIGRhdGEgYmVoaW5kIGFuIGluc3RhbmNlIHByb3BlcnR5IHRoaXMuX2Zvby5cbiAqIFRoZSB1c2Ugb2YgdGhlIHVuZGVyc2NvcmUgaXMgbWVhbnQgdG8gcmVkdWNlIChub3QgZWxpbWluYXRlKSB0aGUgcG90ZW50aWFsXG4gKiBmb3IgbmFtZSBjb25mbGljdHMsIGFuZCBkaXNjb3VyYWdlIChub3QgcHJldmVudCkgZXh0ZXJuYWwgYWNjZXNzIHRvIHRoaXNcbiAqIGRhdGEuIEluIG1vZGVybiBicm93c2VycywgdGhlIGFib3ZlIGNvZGUgd2lsbCBlbGltaW5hdGUgdGhlIHBvdGVudGlhbCBvZlxuICogbmFtaW5nIGNvbmZsaWN0cywgYW5kIGJldHRlciBoaWRlIHRoZSBkYXRhIGJlaGluZCBhIHJlYWwgU3ltYm9sLlxuICpcbiAqIEBmdW5jdGlvbiBjcmVhdGVTeW1ib2xcbiAqIEBwYXJhbSB7c3RyaW5nfSBkZXNjcmlwdGlvbiAtIEEgc3RyaW5nIHRvIGlkZW50aWZ5IHRoZSBzeW1ib2wgd2hlbiBkZWJ1Z2dpbmdcbiAqL1xuZXhwb3J0IGRlZmF1bHQgZnVuY3Rpb24gY3JlYXRlU3ltYm9sKGRlc2NyaXB0aW9uKSB7XG4gIHJldHVybiB0eXBlb2YgU3ltYm9sID09PSAnZnVuY3Rpb24nID9cbiAgICBTeW1ib2woZGVzY3JpcHRpb24pIDpcbiAgICBgXyR7ZGVzY3JpcHRpb259YDtcbn1cbiIsIi8qXG4gKiBNaWNyb3Rhc2sgaGVscGVyIGZvciBJRSAxMS5cbiAqXG4gKiBFeGVjdXRpbmcgYSBmdW5jdGlvbiBhcyBhIG1pY3JvdGFzayBpcyB0cml2aWFsIGluIGJyb3dzZXJzIHRoYXQgc3VwcG9ydFxuICogcHJvbWlzZXMsIHdob3NlIHRoZW4oKSBjbGF1c2VzIHVzZSBtaWNyb3Rhc2sgdGltaW5nLiBJRSAxMSBkb2Vzbid0IHN1cHBvcnRcbiAqIHByb21pc2VzLCBidXQgZG9lcyBzdXBwb3J0IE11dGF0aW9uT2JzZXJ2ZXJzLCB3aGljaCBhcmUgYWxzbyBleGVjdXRlZCBhc1xuICogbWljcm90YXNrcy4gU28gdGhpcyBoZWxwZXIgdXNlcyBhbiBNdXRhdGlvbk9ic2VydmVyIHRvIGFjaGlldmUgbWljcm90YXNrXG4gKiB0aW1pbmcuXG4gKlxuICogU2VlIGh0dHBzOi8vamFrZWFyY2hpYmFsZC5jb20vMjAxNS90YXNrcy1taWNyb3Rhc2tzLXF1ZXVlcy1hbmQtc2NoZWR1bGVzL1xuICpcbiAqIEluc3BpcmVkIGJ5IFBvbHltZXIncyBhc3luYygpIGZ1bmN0aW9uLlxuICovXG5cblxuLy8gVGhlIHF1ZXVlIG9mIHBlbmRpbmcgY2FsbGJhY2tzIHRvIGJlIGV4ZWN1dGVkIGFzIG1pY3JvdGFza3MuXG5jb25zdCBjYWxsYmFja3MgPSBbXTtcblxuLy8gQ3JlYXRlIGFuIGVsZW1lbnQgdGhhdCB3ZSB3aWxsIG1vZGlmeSB0byBmb3JjZSBvYnNlcnZhYmxlIG11dGF0aW9ucy5cbmNvbnN0IGVsZW1lbnQgPSBkb2N1bWVudC5jcmVhdGVUZXh0Tm9kZSgnJyk7XG5cbi8vIEEgbW9ub3RvbmljYWxseS1pbmNyZWFzaW5nIHZhbHVlLlxubGV0IGNvdW50ZXIgPSAwO1xuXG5cbi8qKlxuICogQWRkIGEgY2FsbGJhY2sgdG8gdGhlIG1pY3JvdGFzayBxdWV1ZS5cbiAqXG4gKiBUaGlzIHVzZXMgYSBNdXRhdGlvbk9ic2VydmVyIHNvIHRoYXQgaXQgd29ya3Mgb24gSUUgMTEuXG4gKlxuICogTk9URTogSUUgMTEgbWF5IGFjdHVhbGx5IHVzZSB0aW1lb3V0IHRpbWluZyB3aXRoIE11dGF0aW9uT2JzZXJ2ZXJzLiBUaGlzXG4gKiBuZWVkcyBtb3JlIGludmVzdGlnYXRpb24uXG4gKlxuICogQGZ1bmN0aW9uIG1pY3JvdGFza1xuICogQHBhcmFtIHtmdW5jdGlvbn0gY2FsbGJhY2tcbiAqL1xuZXhwb3J0IGRlZmF1bHQgZnVuY3Rpb24gbWljcm90YXNrKGNhbGxiYWNrKSB7XG4gIGNhbGxiYWNrcy5wdXNoKGNhbGxiYWNrKTtcbiAgLy8gRm9yY2UgYSBtdXRhdGlvbi5cbiAgZWxlbWVudC50ZXh0Q29udGVudCA9ICsrY291bnRlcjtcbn1cblxuXG4vLyBFeGVjdXRlIGFueSBwZW5kaW5nIGNhbGxiYWNrcy5cbmZ1bmN0aW9uIGV4ZWN1dGVDYWxsYmFja3MoKSB7XG4gIHdoaWxlIChjYWxsYmFja3MubGVuZ3RoID4gMCkge1xuICAgIGNvbnN0IGNhbGxiYWNrID0gY2FsbGJhY2tzLnNoaWZ0KCk7XG4gICAgY2FsbGJhY2soKTtcbiAgfVxufVxuXG5cbi8vIENyZWF0ZSB0aGUgb2JzZXJ2ZXIuXG5jb25zdCBvYnNlcnZlciA9IG5ldyBNdXRhdGlvbk9ic2VydmVyKGV4ZWN1dGVDYWxsYmFja3MpO1xub2JzZXJ2ZXIub2JzZXJ2ZShlbGVtZW50LCB7XG4gIGNoYXJhY3RlckRhdGE6IHRydWVcbn0pO1xuIiwiaW1wb3J0IGNyZWF0ZVN5bWJvbCBmcm9tICcuL2NyZWF0ZVN5bWJvbCc7XG5pbXBvcnQgdG9nZ2xlQ2xhc3MgZnJvbSAnLi90b2dnbGVDbGFzcyc7XG5cblxuLy8gU3ltYm9scyBmb3IgcHJpdmF0ZSBkYXRhIG1lbWJlcnMgb24gYW4gZWxlbWVudC5cbmNvbnN0IHNhZmVUb1NldEF0dHJpYnV0ZXNTeW1ib2wgPSBjcmVhdGVTeW1ib2woJ3NhZmVUb1NldEF0dHJpYnV0ZXMnKTtcbmNvbnN0IHBlbmRpbmdBdHRyaWJ1dGVzU3ltYm9sID0gY3JlYXRlU3ltYm9sKCdwZW5kaW5nQXR0cmlidXRlcycpO1xuY29uc3QgcGVuZGluZ0NsYXNzZXNTeW1ib2wgPSBjcmVhdGVTeW1ib2woJ3BlbmRpbmdDbGFzc2VzJyk7XG5cblxuLyoqXG4gKiBIZWxwZXIgZnVuY3Rpb25zIGZvciB1cGRhdGluZyBhdHRyaWJ1dGVzLCBpbmNsdWRpbmcgdGhlIGBjbGFzc2AgYXR0cmlidXRlLlxuICovXG5leHBvcnQgZGVmYXVsdCB7XG5cbiAgLyoqXG4gICAqIFBlcmZvcm0gYW55IHBlbmRpbmcgdXBkYXRlcyB0byBhdHRyaWJ1dGVzIGFuZCBjbGFzc2VzLlxuICAgKlxuICAgKiBUaGlzIHdyaXRlcyBhbnkgYHNldEF0dHJpYnV0ZWAgb3IgYHRvZ2dsZUNsYXNzYCB2YWx1ZXMgdGhhdCB3ZXJlIHBlcmZvcm1lZFxuICAgKiBiZWZvcmUgYW4gZWxlbWVudCB3YXMgYXR0YWNoZWQgdG8gdGhlIGRvY3VtZW50IGZvciB0aGUgZmlyc3QgdGltZS5cbiAgICpcbiAgICogVGhpcyBtZXRob2Qgc2hvdWxkIGJlIGNhbGxlZCBieSBtaXhpbnMvY29tcG9uZW50cyBpbiB0aGVpclxuICAgKiBgY29ubmVjdGVkQ2FsbGJhY2tgLiBJZiBtdWxpdHBsZSBtaXhpbnMvY29tcG9uZW50cyBpbnZva2UgdGhpcyBkdXJpbmcgdGhlXG4gICAqIHNhbWUgYGNvbm5lY3RlZENhbGxiYWNrYCwgb25seSB0aGUgZmlyc3QgY2FsbCB3aWxsIGhhdmUgYW55IGVmZmVjdC4gVGhlXG4gICAqIHN1YnNlcXVlbnQgY2FsbHMgd2lsbCBiZSBoYXJtbGVzcy5cbiAgICpcbiAgICogQHBhcmFtIHtIVE1MRWxlbWVudH0gZWxlbWVudCAtIFRoZSBlbGVtZW50IGJlaW5nIGFkZGVkIHRvIHRoZSBkb2N1bWVudC5cbiAgICovXG4gIGNvbm5lY3RlZChlbGVtZW50KSB7XG4gICAgZWxlbWVudFtzYWZlVG9TZXRBdHRyaWJ1dGVzU3ltYm9sXSA9IHRydWU7XG5cbiAgICAvLyBTZXQgYW55IHBlbmRpbmcgYXR0cmlidXRlcy5cbiAgICBpZiAoZWxlbWVudFtwZW5kaW5nQXR0cmlidXRlc1N5bWJvbF0pIHtcbiAgICAgIGZvciAobGV0IGF0dHJpYnV0ZSBpbiBlbGVtZW50W3BlbmRpbmdBdHRyaWJ1dGVzU3ltYm9sXSkge1xuICAgICAgICBjb25zdCB2YWx1ZSA9IGVsZW1lbnRbcGVuZGluZ0F0dHJpYnV0ZXNTeW1ib2xdW2F0dHJpYnV0ZV07XG4gICAgICAgIHNldEF0dHJpYnV0ZVRvRWxlbWVudChlbGVtZW50LCBhdHRyaWJ1dGUsIHZhbHVlKTtcbiAgICAgIH1cbiAgICAgIGVsZW1lbnRbcGVuZGluZ0F0dHJpYnV0ZXNTeW1ib2xdID0gbnVsbDtcbiAgICB9XG5cbiAgICAvLyBTZXQgYW55IHBlbmRpbmcgY2xhc3Nlcy5cbiAgICBpZiAoZWxlbWVudFtwZW5kaW5nQ2xhc3Nlc1N5bWJvbF0pIHtcbiAgICAgIGZvciAobGV0IGNsYXNzTmFtZSBpbiBlbGVtZW50W3BlbmRpbmdDbGFzc2VzU3ltYm9sXSkge1xuICAgICAgICBjb25zdCB2YWx1ZSA9IGVsZW1lbnRbcGVuZGluZ0NsYXNzZXNTeW1ib2xdW2NsYXNzTmFtZV07XG4gICAgICAgIHRvZ2dsZUNsYXNzKGVsZW1lbnQsIGNsYXNzTmFtZSwgdmFsdWUpO1xuICAgICAgfVxuICAgICAgZWxlbWVudFtwZW5kaW5nQ2xhc3Nlc1N5bWJvbF0gPSBudWxsO1xuICAgIH1cbiAgfSxcblxuICAvKipcbiAgICogU2V0L3Vuc2V0IHRoZSBhdHRyaWJ1dGUgd2l0aCB0aGUgaW5kaWNhdGVkIG5hbWUuXG4gICAqXG4gICAqIFRoaXMgbWV0aG9kIGV4aXN0cyBwcmltYXJpbHkgdG8gaGFuZGxlIHRoZSBjYXNlIHdoZXJlIGFuIGVsZW1lbnQgd2FudHMgdG9cbiAgICogc2V0IGEgZGVmYXVsdCBwcm9wZXJ0eSB2YWx1ZSB0aGF0IHNob3VsZCBiZSByZWZsZWN0ZWQgYXMgYW4gYXR0cmlidXRlLiBBblxuICAgKiBpbXBvcnRhbnQgbGltaXRhdGlvbiBvZiBjdXN0b20gZWxlbWVudCBjb25zdHVyY3RvcnMgaXMgdGhhdCB0aGV5IGNhbm5vdFxuICAgKiBzZXQgYXR0cmlidXRlcy4gQSBjYWxsIHRvIGBzZXRBdHRyaWJ1dGVgIGR1cmluZyB0aGUgY29uc3RydWN0b3Igd2lsbFxuICAgKiBiZSBkZWZlcnJlZCB1bnRpbCB0aGUgZWxlbWVudCBpcyBjb25uZWN0ZWQgdG8gdGhlIGRvY3VtZW50LlxuICAgKlxuICAgKiBAcGFyYW0ge3N0cmluZ30gYXR0cmlidXRlIC0gVGhlIG5hbWUgb2YgdGhlICphdHRyaWJ1dGUqIChub3QgcHJvcGVydHkpIHRvIHNldC5cbiAgICogQHBhcmFtIHtvYmplY3R9IHZhbHVlIC0gVGhlIHZhbHVlIHRvIHNldC4gSWYgbnVsbCwgdGhlIGF0dHJpYnV0ZSB3aWxsIGJlIHJlbW92ZWQuXG4gICAqL1xuICBzZXRBdHRyaWJ1dGUoZWxlbWVudCwgYXR0cmlidXRlLCB2YWx1ZSkge1xuICAgIGlmIChlbGVtZW50W3NhZmVUb1NldEF0dHJpYnV0ZXNTeW1ib2xdKSB7XG4gICAgICAvLyBTYWZlIHRvIHNldCBhdHRyaWJ1dGVzIGltbWVkaWF0ZWx5LlxuICAgICAgc2V0QXR0cmlidXRlVG9FbGVtZW50KGVsZW1lbnQsIGF0dHJpYnV0ZSwgdmFsdWUpO1xuICAgIH0gZWxzZSB7XG4gICAgICAvLyBEZWZlciBzZXR0aW5nIGF0dHJpYnV0ZXMgdW50aWwgdGhlIGZpcnN0IHRpbWUgd2UncmUgY29ubmVjdGVkLlxuICAgICAgaWYgKCFlbGVtZW50W3BlbmRpbmdBdHRyaWJ1dGVzU3ltYm9sXSkge1xuICAgICAgICBlbGVtZW50W3BlbmRpbmdBdHRyaWJ1dGVzU3ltYm9sXSA9IHt9O1xuICAgICAgfVxuICAgICAgZWxlbWVudFtwZW5kaW5nQXR0cmlidXRlc1N5bWJvbF1bYXR0cmlidXRlXSA9IHZhbHVlO1xuICAgIH1cbiAgfSxcblxuICAvKipcbiAgICogU2V0L3Vuc2V0IHRoZSBjbGFzcyB3aXRoIHRoZSBpbmRpY2F0ZWQgbmFtZS5cbiAgICpcbiAgICogVGhpcyBtZXRob2QgZXhpc3RzIHByaW1hcmlseSB0byBoYW5kbGUgdGhlIGNhc2Ugd2hlcmUgYW4gZWxlbWVudCB3YW50cyB0b1xuICAgKiBzZXQgYSBkZWZhdWx0IHByb3BlcnR5IHZhbHVlIHRoYXQgc2hvdWxkIGJlIHJlZmxlY3RlZCBhcyBhcyBjbGFzcy4gQW5cbiAgICogaW1wb3J0YW50IGxpbWl0YXRpb24gb2YgY3VzdG9tIGVsZW1lbnQgY29uc3R1cmN0b3JzIGlzIHRoYXQgdGhleSBjYW5ub3RcbiAgICogc2V0IGF0dHJpYnV0ZXMsIGluY2x1ZGluZyB0aGUgYGNsYXNzYCBhdHRyaWJ1dGUuIEEgY2FsbCB0b1xuICAgKiBgdG9nZ2xlQ2xhc3NgIGR1cmluZyB0aGUgY29uc3RydWN0b3Igd2lsbCBiZSBkZWZlcnJlZCB1bnRpbCB0aGUgZWxlbWVudFxuICAgKiBpcyBjb25uZWN0ZWQgdG8gdGhlIGRvY3VtZW50LlxuICAgKlxuICAgKiBAcGFyYW0ge3N0cmluZ30gY2xhc3NOYW1lIC0gVGhlIG5hbWUgb2YgdGhlIGNsYXNzIHRvIHNldC5cbiAgICogQHBhcmFtIHtvYmplY3R9IHZhbHVlIC0gVHJ1ZSB0byBzZXQgdGhlIGNsYXNzLCBmYWxzZSB0byByZW1vdmUgaXQuXG4gICAqL1xuICB0b2dnbGVDbGFzcyhlbGVtZW50LCBjbGFzc05hbWUsIHZhbHVlKSB7XG4gICAgaWYgKGVsZW1lbnRbc2FmZVRvU2V0QXR0cmlidXRlc1N5bWJvbF0pIHtcbiAgICAgIC8vIFNhZmUgdG8gc2V0IGNsYXNzIGltbWVkaWF0ZWx5LlxuICAgICAgdG9nZ2xlQ2xhc3MoZWxlbWVudCwgY2xhc3NOYW1lLCB2YWx1ZSk7XG4gICAgfSBlbHNlIHtcbiAgICAgIC8vIERlZmVyIHNldHRpbmcgY2xhc3MgdW50aWwgdGhlIGZpcnN0IHRpbWUgd2UncmUgY29ubmVjdGVkLlxuICAgICAgaWYgKCFlbGVtZW50W3BlbmRpbmdDbGFzc2VzU3ltYm9sXSkge1xuICAgICAgICBlbGVtZW50W3BlbmRpbmdDbGFzc2VzU3ltYm9sXSA9IHt9O1xuICAgICAgfVxuICAgICAgZWxlbWVudFtwZW5kaW5nQ2xhc3Nlc1N5bWJvbF1bY2xhc3NOYW1lXSA9IHZhbHVlO1xuICAgIH1cbiAgfVxuXG59O1xuXG5cbi8vIFJlZmxlY3QgdGhlIGF0dHJpYnV0ZSB0byB0aGUgZ2l2ZW4gZWxlbWVudC5cbi8vIElmIHRoZSB2YWx1ZSBpcyBudWxsLCByZW1vdmUgdGhlIGF0dHJpYnV0ZS5cbmZ1bmN0aW9uIHNldEF0dHJpYnV0ZVRvRWxlbWVudChlbGVtZW50LCBhdHRyaWJ1dGVOYW1lLCB2YWx1ZSkge1xuICBpZiAodmFsdWUgPT09IG51bGwgfHwgdHlwZW9mIHZhbHVlID09PSAndW5kZWZpbmVkJykge1xuICAgIGVsZW1lbnQucmVtb3ZlQXR0cmlidXRlKGF0dHJpYnV0ZU5hbWUpO1xuICB9IGVsc2Uge1xuICAgIGNvbnN0IHRleHQgPSBTdHJpbmcodmFsdWUpO1xuICAgIC8vIEF2b2lkIHJlY3Vyc2l2ZSBhdHRyaWJ1dGVDaGFuZ2VkQ2FsbGJhY2sgY2FsbHMuXG4gICAgaWYgKGVsZW1lbnQuZ2V0QXR0cmlidXRlKGF0dHJpYnV0ZU5hbWUpICE9PSB0ZXh0KSB7XG4gICAgICBlbGVtZW50LnNldEF0dHJpYnV0ZShhdHRyaWJ1dGVOYW1lLCB2YWx1ZSk7XG4gICAgfVxuICB9XG59XG4iLCJpbXBvcnQgY3JlYXRlU3ltYm9sIGZyb20gJy4vY3JlYXRlU3ltYm9sJztcblxuLyoqXG4gKiBBIGNvbGxlY3Rpb24gb2YgU3ltYm9sIG9iamVjdHMgZm9yIHN0YW5kYXJkIGNvbXBvbmVudCBwcm9wZXJ0aWVzIGFuZCBtZXRob2RzLlxuICpcbiAqIFRoZXNlIFN5bWJvbCBvYmplY3RzIGFyZSB1c2VkIHRvIGFsbG93IG1peGlucyBhbmQgYSBjb21wb25lbnQgdG8gaW50ZXJuYWxseVxuICogY29tbXVuaWNhdGUsIHdpdGhvdXQgZXhwb3NpbmcgdGhlc2UgcHJvcGVydGllcyBhbmQgbWV0aG9kcyBpbiB0aGUgY29tcG9uZW50J3NcbiAqIHB1YmxpYyBBUEkuXG4gKlxuICogVG8gdXNlIHRoZXNlIFN5bWJvbCBvYmplY3RzIGluIHlvdXIgb3duIGNvbXBvbmVudCwgaW5jbHVkZSB0aGlzIG1vZHVsZSBhbmRcbiAqIHRoZW4gY3JlYXRlIGEgcHJvcGVydHkgb3IgbWV0aG9kIHdob3NlIGtleSBpcyB0aGUgZGVzaXJlZCBTeW1ib2wuXG4gKlxuICogICAgIGltcG9ydCAnU2luZ2xlU2VsZWN0aW9uTWl4aW4nIGZyb20gJ2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL1NpbmdsZVNlbGVjdGlvbk1peGluJztcbiAqICAgICBpbXBvcnQgJ3N5bWJvbHMnIGZyb20gJ2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL3N5bWJvbHMnO1xuICpcbiAqICAgICBjbGFzcyBNeUVsZW1lbnQgZXh0ZW5kcyBTaW5nbGVTZWxlY3Rpb25NaXhpbihIVE1MRWxlbWVudCkge1xuICogICAgICAgW3N5bWJvbHMuaXRlbVNlbGVjdGVkXShpdGVtLCBzZWxlY3RlZCkge1xuICogICAgICAgICAvLyBUaGlzIHdpbGwgYmUgaW52b2tlZCB3aGVuZXZlciBhbiBpdGVtIGlzIHNlbGVjdGVkL2Rlc2VsZWN0ZWQuXG4gKiAgICAgICB9XG4gKiAgICAgfVxuICpcbiAqIEBtb2R1bGUgc3ltYm9sc1xuICovXG5jb25zdCBzeW1ib2xzID0ge1xuXG4gIC8qKlxuICAgKiBTeW1ib2wgZm9yIHRoZSBgZGVmYXVsdHNgIHByb3BlcnR5LlxuICAgKlxuICAgKiBUaGlzIHByb3BlcnR5IGNhbiBiZSB1c2VkIHRvIHNldCBvciBvdmVycmlkZSBkZWZhdWx0cyB0aGF0IHdpbGwgYmUgYXBwbGllZFxuICAgKiB0byBhIG5ldyBjb21wb25lbnQgaW5zdGFuY2UuIFdoZW4gaW1wbGVtZW50aW5nIHRoaXMgcHJvcGVydHksIHRha2UgY2FyZSB0b1xuICAgKiBmaXJzdCBhY3F1aXJlIGFueSBkZWZhdWx0cyBkZWZpbmVkIGJ5IHRoZSBzdXBlcmNsYXNzLiBUaGUgc3RhbmRhcmQgaWRpb20gaXNcbiAgICogYXMgZm9sbG93czpcbiAgICpcbiAgICogICAgIGdldCBbc3ltYm9scy5kZWZhdWx0c10oKSB7XG4gICAqICAgICAgIGNvbnN0IGRlZmF1bHRzID0gc3VwZXJbc3ltYm9scy5kZWZhdWx0c10gfHwge307XG4gICAqICAgICAgIC8vIFNldCBvciBvdmVycmlkZSBkZWZhdWx0IHZhbHVlcyBoZXJlXG4gICAqICAgICAgIGRlZmF1bHRzLmN1c3RvbVByb3BlcnR5ID0gZmFsc2U7XG4gICAqICAgICAgIHJldHVybiBkZWZhdWx0cztcbiAgICogICAgIH1cbiAgICpcbiAgICogQHZhciB7b2JqZWN0fSBkZWZhdWx0c1xuICAgKi9cbiAgZGVmYXVsdHM6IGNyZWF0ZVN5bWJvbCgnZGVmYXVsdHMnKSxcblxuICAvKipcbiAgICogU3ltYm9sIGZvciB0aGUgYGRyYWdnaW5nYCBwcm9wZXJ0eS5cbiAgICpcbiAgICogQ29tcG9uZW50cyBsaWtlIGNhcm91c2VscyBvZnRlbiBkZWZpbmUgYW5pbWF0ZWQgQ1NTIHRyYW5zaXRpb25zIGZvclxuICAgKiBzbGlkaW5nIGVmZmVjdHMuIFN1Y2ggYSB0cmFuc2l0aW9uIHNob3VsZCB1c3VhbGx5ICpub3QqIGJlIGFwcGxpZWQgd2hpbGVcbiAgICogdGhlIHVzZXIgaXMgZHJhZ2dpbmcsIGJlY2F1c2UgYSBDU1MgYW5pbWF0aW9uIHdpbGwgaW50cm9kdWNlIGEgbGFnIHRoYXRcbiAgICogbWFrZXMgdGhlIHN3aXBlIGZlZWwgc2x1Z2dpc2guIEluc3RlYWQsIGFzIGxvbmcgYXMgdGhlIHVzZXIgaXMgZHJhZ2dpbmdcbiAgICogd2l0aCB0aGVpciBmaW5nZXIgZG93biwgdGhlIHRyYW5zaXRpb24gc2hvdWxkIGJlIHN1cHByZXNzZWQuIFdoZW4gdGhlXG4gICAqIHVzZXIgcmVsZWFzZXMgdGhlaXIgZmluZ2VyLCB0aGUgdHJhbnNpdGlvbiBjYW4gYmUgcmVzdG9yZWQsIGFsbG93aW5nIHRoZVxuICAgKiBhbmltYXRpb24gdG8gc2hvdyB0aGUgY2Fyb3VzZWwgc2xpZGluZyBpbnRvIGl0cyBmaW5hbCBwb3NpdGlvbi5cbiAgICpcbiAgICogQHR5cGUge2Jvb2xlYW59IHRydWUgaWYgYSBkcmFnIGlzIGluIHByb2dyZXNzLCBmYWxzZSBpZiBub3QuXG4gICAqL1xuICBkcmFnZ2luZzogY3JlYXRlU3ltYm9sKCdkcmFnZ2luZycpLFxuXG4gIC8qKlxuICAgKiBTeW1ib2wgZm9yIHRoZSBgZ29Eb3duYCBtZXRob2QuXG4gICAqXG4gICAqIFRoaXMgbWV0aG9kIGlzIGludm9rZWQgd2hlbiB0aGUgdXNlciB3YW50cyB0byBnby9uYXZpZ2F0ZSBkb3duLlxuICAgKlxuICAgKiBAZnVuY3Rpb24gZ29Eb3duXG4gICAqL1xuICBnb0Rvd246IGNyZWF0ZVN5bWJvbCgnZ29Eb3duJyksXG5cbiAgLyoqXG4gICAqIFN5bWJvbCBmb3IgdGhlIGBnb0VuZGAgbWV0aG9kLlxuICAgKlxuICAgKiBUaGlzIG1ldGhvZCBpcyBpbnZva2VkIHdoZW4gdGhlIHVzZXIgd2FudHMgdG8gZ28vbmF2aWdhdGUgdG8gdGhlIGVuZCAoZS5nLixcbiAgICogb2YgYSBsaXN0KS5cbiAgICpcbiAgICogQGZ1bmN0aW9uIGdvRW5kXG4gICAqL1xuICBnb0VuZDogY3JlYXRlU3ltYm9sKCdnb0VuZCcpLFxuXG4gIC8qKlxuICAgKiBTeW1ib2wgZm9yIHRoZSBgZ29MZWZ0YCBtZXRob2QuXG4gICAqXG4gICAqIFRoaXMgbWV0aG9kIGlzIGludm9rZWQgd2hlbiB0aGUgdXNlciB3YW50cyB0byBnby9uYXZpZ2F0ZSBsZWZ0LlxuICAgKlxuICAgKiBAZnVuY3Rpb24gZ29MZWZ0XG4gICAqL1xuICBnb0xlZnQ6IGNyZWF0ZVN5bWJvbCgnZ29MZWZ0JyksXG5cbiAgLyoqXG4gICAqIFN5bWJvbCBmb3IgdGhlIGBnb1JpZ2h0YCBtZXRob2QuXG4gICAqXG4gICAqIFRoaXMgbWV0aG9kIGlzIGludm9rZWQgd2hlbiB0aGUgdXNlciB3YW50cyB0byBnby9uYXZpZ2F0ZSByaWdodC5cbiAgICpcbiAgICogQGZ1bmN0aW9uIGdvUmlnaHRcbiAgICovXG4gIGdvUmlnaHQ6IGNyZWF0ZVN5bWJvbCgnZ29SaWdodCcpLFxuXG4gIC8qKlxuICAgKiBTeW1ib2wgZm9yIHRoZSBgZ29TdGFydGAgbWV0aG9kLlxuICAgKlxuICAgKiBUaGlzIG1ldGhvZCBpcyBpbnZva2VkIHdoZW4gdGhlIHVzZXIgd2FudHMgdG8gZ28vbmF2aWdhdGUgdG8gdGhlIHN0YXJ0XG4gICAqIChlLmcuLCBvZiBhIGxpc3QpLlxuICAgKlxuICAgKiBAZnVuY3Rpb24gZ29TdGFydFxuICAgKi9cbiAgZ29TdGFydDogY3JlYXRlU3ltYm9sKCdnb1N0YXJ0JyksXG5cbiAgLyoqXG4gICAqIFN5bWJvbCBmb3IgdGhlIGBnb1VwYCBtZXRob2QuXG4gICAqXG4gICAqIFRoaXMgbWV0aG9kIGlzIGludm9rZWQgd2hlbiB0aGUgdXNlciB3YW50cyB0byBnby9uYXZpZ2F0ZSB1cC5cbiAgICpcbiAgICogQGZ1bmN0aW9uIGdvVXBcbiAgICovXG4gIGdvVXA6IGNyZWF0ZVN5bWJvbCgnZ29VcCcpLFxuXG4gIC8qKlxuICAgKiBTeW1ib2wgZm9yIHRoZSBgaXRlbUFkZGVkYCBtZXRob2QuXG4gICAqXG4gICAqIFRoaXMgbWV0aG9kIGlzIGludm9rZWQgd2hlbiBhIG5ldyBpdGVtIGlzIGFkZGVkIHRvIGEgbGlzdC5cbiAgICpcbiAgICogQGZ1bmN0aW9uIGl0ZW1BZGRlZFxuICAgKiBAcGFyYW0ge0hUTUxFbGVtZW50fSBpdGVtIC0gdGhlIGl0ZW0gYmVpbmcgc2VsZWN0ZWQvZGVzZWxlY3RlZFxuICAgKi9cbiAgaXRlbUFkZGVkOiBjcmVhdGVTeW1ib2woJ2l0ZW1BZGRlZCcpLFxuXG5cbiAgLyoqXG4gICAqIFN5bWJvbCBmb3IgdGhlIGBpdGVtc0NoYW5nZWRgIG1ldGhvZC5cbiAgICpcbiAgICogVGhpcyBtZXRob2QgaXMgaW52b2tlZCB3aGVuIHRoZSB1bmRlcmx5aW5nIGNvbnRlbnRzIGNoYW5nZS4gSXQgaXMgYWxzb1xuICAgKiBpbnZva2VkIG9uIGNvbXBvbmVudCBpbml0aWFsaXphdGlvbiDigJMgc2luY2UgdGhlIGl0ZW1zIGhhdmUgXCJjaGFuZ2VkXCIgZnJvbVxuICAgKiBiZWluZyBub3RoaW5nLlxuICAgKi9cbiAgaXRlbXNDaGFuZ2VkOiBjcmVhdGVTeW1ib2woJ2l0ZW1zQ2hhbmdlZCcpLFxuXG4gIC8qKlxuICAgKiBTeW1ib2wgZm9yIHRoZSBgaXRlbVNlbGVjdGVkYCBtZXRob2QuXG4gICAqXG4gICAqIFRoaXMgbWV0aG9kIGlzIGludm9rZWQgd2hlbiBhbiBpdGVtIGJlY29tZXMgc2VsZWN0ZWQgb3IgZGVzZWxlY3RlZC5cbiAgICpcbiAgICogQGZ1bmN0aW9uIGl0ZW1TZWxlY3RlZFxuICAgKiBAcGFyYW0ge0hUTUxFbGVtZW50fSBpdGVtIC0gdGhlIGl0ZW0gYmVpbmcgc2VsZWN0ZWQvZGVzZWxlY3RlZFxuICAgKiBAcGFyYW0ge2Jvb2xlYW59IHNlbGVjdGVkIC0gdHJ1ZSBpZiB0aGUgaXRlbSBpcyBzZWxlY3RlZCwgZmFsc2UgaWYgbm90XG4gICAqL1xuICBpdGVtU2VsZWN0ZWQ6IGNyZWF0ZVN5bWJvbCgnaXRlbVNlbGVjdGVkJyksXG5cbiAgLyoqXG4gICAqIFN5bWJvbCBmb3IgdGhlIGBrZXlkb3duYCBtZXRob2QuXG4gICAqXG4gICAqIFRoaXMgbWV0aG9kIGlzIGludm9rZWQgd2hlbiBhbiBlbGVtZW50IHJlY2VpdmVzIGEgYGtleWRvd25gIGV2ZW50LlxuICAgKlxuICAgKiBAZnVuY3Rpb24ga2V5ZG93blxuICAgKiBAcGFyYW0ge0tleWJvYXJkRXZlbnR9IGV2ZW50IC0gdGhlIGV2ZW50IGJlaW5nIHByb2Nlc3NlZFxuICAgKi9cbiAga2V5ZG93bjogY3JlYXRlU3ltYm9sKCdrZXlkb3duJyksXG5cbiAgLyoqXG4gICAqIFN5bWJvbCBmb3IgdGhlIGB0ZW1wbGF0ZWAgcHJvcGVydHkuXG4gICAqXG4gICAqIFRoaXMgcHJvcGVydHkgcmV0dXJucyBhIGNvbXBvbmVudCdzIHRlbXBsYXRlLlxuICAgKlxuICAgKiBAdHlwZSB7c3RyaW5nfEhUTUxFbGVtZW50fVxuICAgKi9cbiAgdGVtcGxhdGU6IGNyZWF0ZVN5bWJvbCgndGVtcGxhdGUnKVxufTtcblxuZXhwb3J0IGRlZmF1bHQgc3ltYm9scztcbiIsIi8qKlxuICogSGVscGVyIGZ1bmN0aW9uIGZvciBzdGFuZGFyZCBjbGFzc0xpc3QudG9nZ2xlKCkgYmVoYXZpb3Igb24gb2xkIGJyb3dzZXJzLFxuICogbmFtZWx5IElFIDExLlxuICpcbiAqIFRoZSBzdGFuZGFyZFxuICogW2NsYXNzbGlzdF0oaHR0cHM6Ly9kZXZlbG9wZXIubW96aWxsYS5vcmcvZW4tVVMvZG9jcy9XZWIvQVBJL0VsZW1lbnQvY2xhc3NMaXN0KVxuICogb2JqZWN0IGhhcyBhIGB0b2dnbGUoKWAgZnVuY3Rpb24gdGhhdCBzdXBwb3J0cyBhIHNlY29uZCBCb29sZWFuIHBhcmFtZXRlclxuICogdGhhdCBjYW4gYmUgdXNlZCB0byBzdWNjaW5jdGx5IHR1cm4gYSBjbGFzcyBvbiBvciBvZmYuIFRoaXMgZmVhdHVyZSBpcyBvZnRlblxuICogdXNlZnVsIGluIGRlc2lnbmluZyBjdXN0b20gZWxlbWVudHMsIHdoaWNoIG1heSB3YW50IHRvIGV4dGVybmFsbHkgcmVmbGVjdFxuICogY29tcG9uZW50IHN0YXRlIGluIGEgQ1NTIGNsYXNzIHRoYXQgY2FuIGJlIHVzZWQgZm9yIHN0eWxpbmcgcHVycG9zZXMuXG4gKlxuICogVW5mb3J0dW5hdGVseSwgSUUgMTEgZG9lcyBub3Qgc3VwcG9ydCB0aGUgQm9vbGVhbiBwYXJhbWV0ZXIgdG9cbiAqIGBjbGFzc0xpc3QudG9nZ2xlKClgLiBUaGlzIGhlbHBlciBmdW5jdGlvbiBiZWhhdmVzIGxpa2UgdGhlIHN0YW5kYXJkXG4gKiBgdG9nZ2xlKClgLCBpbmNsdWRpbmcgc3VwcG9ydCBmb3IgdGhlIEJvb2xlYW4gcGFyYW1ldGVyLCBzbyB0aGF0IGl0IGNhbiBiZVxuICogdXNlZCBldmVuIG9uIElFIDExLlxuICpcbiAqIEBmdW5jdGlvbiB0b2dnbGVDbGFzc1xuICogQHBhcmFtIHtIVE1MRWxlbWVudH0gZWxlbWVudCAtIFRoZSBlbGVtZW50IHRvIG1vZGlmeVxuICogQHBhcmFtIHtzdHJpbmd9IGNsYXNzTmFtZSAtIFRoZSBjbGFzcyB0byBhZGQvcmVtb3ZlXG4gKiBAcGFyYW0ge2Jvb2xlYW59IFtmb3JjZV0gLSBGb3JjZSB0aGUgY2xhc3MgdG8gYmUgYWRkZWQgKGlmIHRydWUpIG9yIHJlbW92ZWRcbiAqICAgICAgICAgICAgICAgICAgICAgICAgICAgIChpZiBmYWxzZSlcbiAqL1xuZXhwb3J0IGRlZmF1bHQgZnVuY3Rpb24gdG9nZ2xlQ2xhc3MoZWxlbWVudCwgY2xhc3NOYW1lLCBmb3JjZSkge1xuICBjb25zdCBjbGFzc0xpc3QgPSBlbGVtZW50LmNsYXNzTGlzdDtcbiAgY29uc3QgYWRkQ2xhc3MgPSAodHlwZW9mIGZvcmNlID09PSAndW5kZWZpbmVkJykgP1xuICAgICFjbGFzc0xpc3QuY29udGFpbnMoY2xhc3NOYW1lKSA6XG4gICAgZm9yY2U7XG4gIGlmIChhZGRDbGFzcykge1xuICAgIGNsYXNzTGlzdC5hZGQoY2xhc3NOYW1lKTtcbiAgfSBlbHNlIHtcbiAgICBjbGFzc0xpc3QucmVtb3ZlKGNsYXNzTmFtZSk7XG4gIH1cbiAgcmV0dXJuIGFkZENsYXNzO1xufVxuIiwiaW1wb3J0IEF0dHJpYnV0ZU1hcnNoYWxsaW5nTWl4aW4gZnJvbSAnLi4vLi4vYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvQXR0cmlidXRlTWFyc2hhbGxpbmdNaXhpbic7XG5pbXBvcnQgQ29tcG9zYWJsZU1peGluIGZyb20gJy4uLy4uL2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL0NvbXBvc2FibGVNaXhpbic7XG5pbXBvcnQgRGlzdHJpYnV0ZWRDaGlsZHJlbk1peGluIGZyb20gJy4uLy4uL2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL0Rpc3RyaWJ1dGVkQ2hpbGRyZW5NaXhpbic7XG5pbXBvcnQgU2hhZG93RWxlbWVudFJlZmVyZW5jZXNNaXhpbiBmcm9tICcuLi8uLi9iYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy9TaGFkb3dFbGVtZW50UmVmZXJlbmNlc01peGluJztcbmltcG9ydCBTaGFkb3dUZW1wbGF0ZU1peGluIGZyb20gJy4uLy4uL2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL1NoYWRvd1RlbXBsYXRlTWl4aW4nO1xuXG5cbi8qKlxuICogQSBzYW1wbGUgZ2VuZXJhbC1wdXJwb3NlIGJhc2UgY2xhc3MgZm9yIGRlZmluaW5nIGN1c3RvbSBlbGVtZW50cyB0aGF0IG1peGVzXG4gKiBpbiBzb21lIGNvbW1vbiBmZWF0dXJlczogdGVtcGxhdGUgc3RhbXBpbmcgaW50byBhIHNoYWRvdyByb290LCBzaGFkb3cgZWxlbWVudFxuICogcmVmZXJlbmNlcywgbWFyc2hhbGxpbmcgYXR0cmlidXRlcyB0byBwcm9wZXJ0aWVzLCBhbmQgcmV0cmlldmluZyB0aGUgY2hpbGRyZW5cbiAqIGRpc3RyaWJ1dGVkIHRvIGEgY29tcG9uZW50LlxuICpcbiAqIFRoaXMgYmFzZSBjbGFzcyBpcyBub3Qgc3BlY2lhbCBpbiBhbnkgd2F5LCBhbmQgaXMgZGVmaW5lZCBvbmx5IGFzIGFcbiAqIGNvbnZlbmllbnQgc2hvcnRoYW5kIGZvciBhcHBseWluZyB0aGUgbWl4aW5zIGxpc3RlZCBhYm92ZS4gWW91IGNhbiB1c2UgdGhpc1xuICogY2xhc3MgYXMgYSBiYXNlIGNsYXNzIGZvciB5b3VyIG93biBlbGVtZW50cywgb3IgZWFzaWx5IGNyZWF0ZSB5b3VyIG93biBiYXNlXG4gKiBjbGFzcyBieSBhcHBseWluZyB0aGUgc2FtZSBzZXQgb2YgbWl4aW5zLlxuICpcbiAqIFRoZSBFbGVtZW50QmFzZSBiYXNlIGNsYXNzIGRvZXMgbm90IHJlZ2lzdGVyIGl0c2VsZiBhcyBhIGN1c3RvbSBlbGVtZW50IHdpdGhcbiAqIHRoZSBicm93c2VyLCBhbmQgaGVuY2UgY2Fubm90IGJlIGluZGVwZW5kZW50bHkgaW5zdGFudGlhdGVkLlxuICpcbiAqIEBtaXhlcyBBdHRyaWJ1dGVNYXJzaGFsbGluZ01peGluXG4gKiBAbWl4ZXMgQ29tcG9zYWJsZU1peGluXG4gKiBAbWl4ZXMgRGlzdHJpYnV0ZWRDaGlsZHJlbk1peGluXG4gKiBAbWl4ZXMgU2hhZG93RWxlbWVudFJlZmVyZW5jZXNNaXhpblxuICogQG1peGVzIFNoYWRvd1RlbXBsYXRlTWl4aW5cbiAqL1xuY2xhc3MgRWxlbWVudEJhc2UgZXh0ZW5kcyBDb21wb3NhYmxlTWl4aW4oSFRNTEVsZW1lbnQpLmNvbXBvc2UoXG4gIFNoYWRvd1RlbXBsYXRlTWl4aW4sICAgICAgICAgIC8vIGJlZm9yZSBub2RlIGZpbmRpbmcsIHNvIHNoYWRvdyByb290IGlzIHBvcHVsYXRlZFxuICBTaGFkb3dFbGVtZW50UmVmZXJlbmNlc01peGluLCAvLyBiZWZvcmUgbWFyc2hhbGxpbmcsIHNvIHByb3BlcnRpZXMgY2FuIHVzZSByZWZzXG4gIEF0dHJpYnV0ZU1hcnNoYWxsaW5nTWl4aW4sXG4gIERpc3RyaWJ1dGVkQ2hpbGRyZW5NaXhpblxuKSB7fVxuXG5leHBvcnQgZGVmYXVsdCBFbGVtZW50QmFzZTtcbiIsIi8qXG4gKiBUaGlzIGZpbGUgaXMgdHJhbnNwaWxlZCB0byBjcmVhdGUgYW4gRVM1LWNvbXBhdGlibGUgZGlzdHJpYnV0aW9uIGluIHdoaWNoXG4gKiB0aGUgcGFja2FnZSdzIG1haW4gZmVhdHVyZShzKSBhcmUgYXZhaWxhYmxlIHZpYSB0aGUgd2luZG93LkJhc2ljIGdsb2JhbC5cbiAqIElmIHlvdSdyZSBhbHJlYWR5IHVzaW5nIEVTNiB5b3Vyc2VsZiwgaWdub3JlIHRoaXMgZmlsZSwgYW5kIGluc3RlYWQgaW1wb3J0XG4gKiB0aGUgc291cmNlIGZpbGUocykgeW91IHdhbnQgZnJvbSB0aGUgc3JjIGZvbGRlci5cbiAqL1xuXG5pbXBvcnQgTW9kZXMgZnJvbSAnLi9zcmMvTW9kZXMnO1xuXG53aW5kb3cuQmFzaWMgPSB3aW5kb3cuQmFzaWMgfHwge307XG53aW5kb3cuQmFzaWMuTW9kZXMgPSBNb2RlcztcbiIsImltcG9ydCBFbGVtZW50QmFzZSBmcm9tICcuLi8uLi9iYXNpYy1lbGVtZW50LWJhc2Uvc3JjL0VsZW1lbnRCYXNlJztcbmltcG9ydCBEaXN0cmlidXRlZENoaWxkcmVuQ29udGVudE1peGluIGZyb20gJy4uLy4uL2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL0Rpc3RyaWJ1dGVkQ2hpbGRyZW5Db250ZW50TWl4aW4nO1xuaW1wb3J0IENvbnRlbnRJdGVtc01peGluIGZyb20gJy4uLy4uL2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL0NvbnRlbnRJdGVtc01peGluJztcbmltcG9ydCBTaW5nbGVTZWxlY3Rpb25NaXhpbiBmcm9tICcuLi8uLi9iYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy9TaW5nbGVTZWxlY3Rpb25NaXhpbic7XG5pbXBvcnQgc3ltYm9scyBmcm9tICcuLi8uLi9iYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy9zeW1ib2xzJztcblxuY29uc3QgYmFzZSA9IEVsZW1lbnRCYXNlLmNvbXBvc2UoXG4gIENvbnRlbnRJdGVtc01peGluLFxuICBEaXN0cmlidXRlZENoaWxkcmVuQ29udGVudE1peGluLFxuICBTaW5nbGVTZWxlY3Rpb25NaXhpblxuKTtcblxuXG4vKipcbiAqIFNob3dzIGV4YWN0bHkgb25lIGNoaWxkIGVsZW1lbnQgYXQgYSB0aW1lLiBUaGlzIGNhbiBiZSB1c2VmdWwsIGZvciBleGFtcGxlLFxuICogaWYgYSBnaXZlbiBVSSBlbGVtZW50IGhhcyBtdWx0aXBsZSBtb2RlcyB0aGF0IHByZXNlbnQgc3Vic3RhbnRpYWxseSBkaWZmZXJlbnRcbiAqIGVsZW1lbnRzLlxuICpcbiAqIFRoZSB0cmFuc2l0aW9uIGJldHdlZW4gY2hpbGQgZWxlbWVudHMgaXMgaW5zdGFudGVub3VzLiBJZiB5b3UnZCBsaWtlIHRoZVxuICogdHJhbnNpdGlvbiB0byBiZSBhY2NvbXBhbmllZCBieSB2aXNpYmxlIGFuaW1hdGVkIGVmZmVjdHMsIHNlZVxuICogW2Jhc2ljLWFuaW1hdGlvbi1zdGFnZV0oLi4vYmFzaWMtYW5pbWF0aW9uLXN0YWdlKS5cbiAqXG4gKiBUaGlzIGNvbXBvbmVudCBkb2Vzbid0IHByb3ZpZGUgYW55IFVJIGZvciBjaGFuZ2luZyB3aGljaCBtb2RlIGlzIHNob3duLlxuICpcbiAqIEBleHRlbmRzIEVsZW1lbnRCYXNlXG4gKiBAbWl4ZXMgQ29udGVudEl0ZW1zTWl4aW5cbiAqIEBtaXhlcyBEaXN0cmlidXRlZENoaWxkcmVuQ29udGVudE1peGluXG4gKiBAbWl4ZXMgU2luZ2xlU2VsZWN0aW9uTWl4aW5cbiAqL1xuY2xhc3MgTW9kZXMgZXh0ZW5kcyBiYXNlIHtcblxuICBnZXQgW3N5bWJvbHMuZGVmYXVsdHNdKCkge1xuICAgIGNvbnN0IGRlZmF1bHRzID0gc3VwZXJbc3ltYm9scy5kZWZhdWx0c10gfHwge307XG4gICAgZGVmYXVsdHMuc2VsZWN0aW9uUmVxdWlyZWQgPSB0cnVlO1xuICAgIHJldHVybiBkZWZhdWx0cztcbiAgfVxuXG4gIFtzeW1ib2xzLml0ZW1TZWxlY3RlZF0oaXRlbSwgc2VsZWN0ZWQpIHtcbiAgICBpZiAoc3VwZXJbc3ltYm9scy5pdGVtU2VsZWN0ZWRdKSB7IHN1cGVyW3N5bWJvbHMuaXRlbVNlbGVjdGVkXShpdGVtLCBzZWxlY3RlZCk7IH1cbiAgICBpdGVtLnN0eWxlLmRpc3BsYXkgPSBzZWxlY3RlZCA/ICcnIDogJ25vbmUnO1xuICAgIGl0ZW0uc2V0QXR0cmlidXRlKCdhcmlhLWhpZGRlbicsICFzZWxlY3RlZCk7XG4gIH1cblxuICBnZXQgW3N5bWJvbHMudGVtcGxhdGVdKCkge1xuICAgIHJldHVybiBgPHNsb3Q+PC9zbG90PmA7XG4gIH1cblxufVxuXG5cbmN1c3RvbUVsZW1lbnRzLmRlZmluZSgnYmFzaWMtbW9kZXMnLCBNb2Rlcyk7XG5leHBvcnQgZGVmYXVsdCBNb2RlcztcbiJdfQ==
+!function t(e,o,n){function r(c,u){if(!o[c]){if(!e[c]){var l="function"==typeof require&&require;if(!u&&l)return l(c,!0);if(i)return i(c,!0);var a=new Error("Cannot find module '"+c+"'");throw a.code="MODULE_NOT_FOUND",a}var s=o[c]={exports:{}};e[c][0].call(s.exports,function(t){var o=e[c][1][t];return r(o?o:t)},s,s.exports,t,e,o,n)}return o[c].exports}for(var i="function"==typeof require&&require,c=0;c2&&void 0!==arguments[2]?arguments[2]:[];return Object.getOwnPropertyNames(t).forEach(function(n){if(o.indexOf(n)<0){var r=Object.getOwnPropertyDescriptor(t,n);Object.defineProperty(e,n,r)}}),e}Object.defineProperty(o,"__esModule",{value:!0});var l=function(){function t(t,e){for(var o=0;o0;)e.content.appendChild(o.childNodes[0]);return e}function l(t,e){window.WebComponents.ShadowCSS.shimStyling(t.content,e)}Object.defineProperty(o,"__esModule",{value:!0});var a=t("../src/symbols"),s=n(a);o.default=function(t){var e=function(t){function e(){r(this,e);var t=i(this,(e.__proto__||Object.getPrototypeOf(e)).call(this)),o=t[s.default.template];if(o){"string"==typeof o&&(o=u(o)),window.ShadowDOMPolyfill&&l(o,t.localName);var n=t.attachShadow({mode:"open"}),c=document.importNode(o.content,!0);n.appendChild(c)}return t}return c(e,t),e}(t);return e}},{"../src/symbols":12}],8:[function(t,e,o){"use strict";function n(t){return t&&t.__esModule?t:{default:t}}function r(t,e){if(!(t instanceof e))throw new TypeError("Cannot call a class as a function")}function i(t,e){if(!t)throw new ReferenceError("this hasn't been initialised - super() hasn't been called");return!e||"object"!=typeof e&&"function"!=typeof e?t:e}function c(t,e){if("function"!=typeof e&&null!==e)throw new TypeError("Super expression must either be null or a function, not "+typeof e);t.prototype=Object.create(e&&e.prototype,{constructor:{value:t,enumerable:!1,writable:!0,configurable:!0}}),e&&(Object.setPrototypeOf?Object.setPrototypeOf(t,e):t.__proto__=e)}function u(t,e){var o=t.items.length,n=t.selectionWraps?(e%o+o)%o:Math.max(Math.min(e,o-1),0),r=t.selectedIndex;return r!==n&&(t.selectedIndex=n,!0)}function l(t){var e=t.items,o=e?e.length:0,n=t.selectedItem;if(n)if(0===o)t.selectedItem=null;else{var r=Array.prototype.indexOf.call(e,n),i=t.selectedIndex;if(r<0){var c=Math.min(i,o-1);t.selectedItem=e[c]}else r!==i&&(t.selectedIndex=r)}else t.selectionRequired&&(t.selectedIndex=0)}function a(t){var e=void 0,o=void 0,n=t.items;if(null!=n&&0!==n.length||(e=!1,o=!1),t.selectionWraps)e=!0,o=!0;else{var r=t.selectedIndex;r<0&&n.length>0?(e=!0,o=!0):(o=r>0,e=r0;c&&e>=0&&e=0?i[e]:null,this[j]=r}else r=this[j];if("selectedIndex"in t.prototype&&p(o.prototype.__proto__||Object.getPrototypeOf(o.prototype),"selectedIndex",e,this),e!==n){this[w]=e;var u=new CustomEvent("selected-index-changed",{detail:{selectedIndex:e,value:e}});this.dispatchEvent(u)}this[P]!==r&&(this.selectedItem=r)}},{key:"selectedItem",get:function(){return this[j]||null},set:function(e){var n=this[P],r=void 0;if(e!==this[j]){var i=this.items,c=i&&i.length>0;r=c?Array.prototype.indexOf.call(i,e):-1,this[g]=r,r<0&&(e=null),this[j]=e}else r=this[g];if("selectedItem"in t.prototype&&p(o.prototype.__proto__||Object.getPrototypeOf(o.prototype),"selectedItem",e,this),e!==n){this[P]=e,n&&this[b.default.itemSelected](n,!1),e&&this[b.default.itemSelected](e,!0),a(this);var u=new CustomEvent("selected-item-changed",{detail:{selectedItem:e,value:e}});this.dispatchEvent(u)}this[w]!==r&&(this.selectedIndex=r)}},{key:"selectionRequired",get:function(){return this[O]},set:function(e){this[O]=e,"selectionRequired"in t.prototype&&p(o.prototype.__proto__||Object.getPrototypeOf(o.prototype),"selectionRequired",e,this),l(this)}},{key:"selectionWraps",get:function(){return this[m]},set:function(e){this[m]="true"===String(e),"selectionWraps"in t.prototype&&p(o.prototype.__proto__||Object.getPrototypeOf(o.prototype),"selectionWraps",e,this),a(this)}}]),o}(t);return e}},{"./createSymbol":9,"./symbols":12}],9:[function(t,e,o){"use strict";function n(t){return"function"==typeof Symbol?Symbol(t):"_"+t}Object.defineProperty(o,"__esModule",{value:!0}),o.default=n},{}],10:[function(t,e,o){"use strict";function n(t){i.push(t),c.textContent=++u}function r(){for(;i.length>0;){var t=i.shift();t()}}Object.defineProperty(o,"__esModule",{value:!0}),o.default=n;var i=[],c=document.createTextNode(""),u=0,l=new MutationObserver(r);l.observe(c,{characterData:!0})},{}],11:[function(t,e,o){"use strict";function n(t){return t&&t.__esModule?t:{default:t}}function r(t,e,o){if(null===o||"undefined"==typeof o)t.removeAttribute(e);else{var n=String(o);t.getAttribute(e)!==n&&t.setAttribute(e,o)}}Object.defineProperty(o,"__esModule",{value:!0});var i=t("./createSymbol"),c=n(i),u=t("./toggleClass"),l=n(u),a=(0,c.default)("safeToSetAttributes"),s=(0,c.default)("pendingAttributes"),f=(0,c.default)("pendingClasses");o.default={connected:function(t){if(t[a]=!0,t[s]){for(var e in t[s]){var o=t[s][e];r(t,e,o)}t[s]=null}if(t[f]){for(var n in t[f]){var i=t[f][n];(0,l.default)(t,n,i)}t[f]=null}},setAttribute:function(t,e,o){t[a]?r(t,e,o):(t[s]||(t[s]={}),t[s][e]=o)},toggleClass:function(t,e,o){t[a]?(0,l.default)(t,e,o):(t[f]||(t[f]={}),t[f][e]=o)}}},{"./createSymbol":9,"./toggleClass":13}],12:[function(t,e,o){"use strict";function n(t){return t&&t.__esModule?t:{default:t}}Object.defineProperty(o,"__esModule",{value:!0});var r=t("./createSymbol"),i=n(r),c={defaults:(0,i.default)("defaults"),dragging:(0,i.default)("dragging"),goDown:(0,i.default)("goDown"),goEnd:(0,i.default)("goEnd"),goLeft:(0,i.default)("goLeft"),goRight:(0,i.default)("goRight"),goStart:(0,i.default)("goStart"),goUp:(0,i.default)("goUp"),itemAdded:(0,i.default)("itemAdded"),itemsChanged:(0,i.default)("itemsChanged"),itemSelected:(0,i.default)("itemSelected"),keydown:(0,i.default)("keydown"),template:(0,i.default)("template")};o.default=c},{"./createSymbol":9}],13:[function(t,e,o){"use strict";function n(t,e,o){var n=t.classList,r="undefined"==typeof o?!n.contains(e):o;return r?n.add(e):n.remove(e),r}Object.defineProperty(o,"__esModule",{value:!0}),o.default=n},{}],14:[function(t,e,o){"use strict";function n(t){return t&&t.__esModule?t:{default:t}}function r(t,e){if(!(t instanceof e))throw new TypeError("Cannot call a class as a function")}function i(t,e){if(!t)throw new ReferenceError("this hasn't been initialised - super() hasn't been called");return!e||"object"!=typeof e&&"function"!=typeof e?t:e}function c(t,e){if("function"!=typeof e&&null!==e)throw new TypeError("Super expression must either be null or a function, not "+typeof e);t.prototype=Object.create(e&&e.prototype,{constructor:{value:t,enumerable:!1,writable:!0,configurable:!0}}),e&&(Object.setPrototypeOf?Object.setPrototypeOf(t,e):t.__proto__=e)}Object.defineProperty(o,"__esModule",{value:!0});var u=t("../../basic-component-mixins/src/AttributeMarshallingMixin"),l=n(u),a=t("../../basic-component-mixins/src/ComposableMixin"),s=n(a),f=t("../../basic-component-mixins/src/DistributedChildrenMixin"),p=n(f),d=t("../../basic-component-mixins/src/ShadowElementReferencesMixin"),y=n(d),h=t("../../basic-component-mixins/src/ShadowTemplateMixin"),b=n(h),_=function(t){function e(){return r(this,e),i(this,(e.__proto__||Object.getPrototypeOf(e)).apply(this,arguments))}return c(e,t),e}((0,s.default)(HTMLElement).compose(b.default,y.default,l.default,p.default));o.default=_},{"../../basic-component-mixins/src/AttributeMarshallingMixin":1,"../../basic-component-mixins/src/ComposableMixin":2,"../../basic-component-mixins/src/DistributedChildrenMixin":5,"../../basic-component-mixins/src/ShadowElementReferencesMixin":6,"../../basic-component-mixins/src/ShadowTemplateMixin":7}],15:[function(t,e,o){"use strict";function n(t){return t&&t.__esModule?t:{default:t}}var r=t("./src/Modes"),i=n(r);window.Basic=window.Basic||{},window.Basic.Modes=i.default},{"./src/Modes":16}],16:[function(t,e,o){"use strict";function n(t){return t&&t.__esModule?t:{default:t}}function r(t,e){if(!(t instanceof e))throw new TypeError("Cannot call a class as a function")}function i(t,e){if(!t)throw new ReferenceError("this hasn't been initialised - super() hasn't been called");return!e||"object"!=typeof e&&"function"!=typeof e?t:e}function c(t,e){if("function"!=typeof e&&null!==e)throw new TypeError("Super expression must either be null or a function, not "+typeof e);t.prototype=Object.create(e&&e.prototype,{constructor:{value:t,enumerable:!1,writable:!0,configurable:!0}}),e&&(Object.setPrototypeOf?Object.setPrototypeOf(t,e):t.__proto__=e)}Object.defineProperty(o,"__esModule",{value:!0});var u=function(){function t(t,e){for(var o=0;o "}}]),e}(O);customElements.define("basic-modes",m),o.default=m},{"../../basic-component-mixins/src/ContentItemsMixin":3,"../../basic-component-mixins/src/DistributedChildrenContentMixin":4,"../../basic-component-mixins/src/SingleSelectionMixin":8,"../../basic-component-mixins/src/symbols":12,"../../basic-element-base/src/ElementBase":14}]},{},[15]);
+//# sourceMappingURL=basic-modes.js.map
diff --git a/packages/basic-modes/dist/basic-modes.js.map b/packages/basic-modes/dist/basic-modes.js.map
new file mode 100644
index 00000000..ee85f87a
--- /dev/null
+++ b/packages/basic-modes/dist/basic-modes.js.map
@@ -0,0 +1 @@
+{"version":3,"sources":["node_modules/browser-pack/_prelude.js","packages/basic-component-mixins/src/AttributeMarshallingMixin.js","packages/basic-component-mixins/src/ComposableMixin.js","packages/basic-component-mixins/src/ContentItemsMixin.js","packages/basic-component-mixins/src/DistributedChildrenContentMixin.js","packages/basic-component-mixins/src/DistributedChildrenMixin.js","packages/basic-component-mixins/src/ShadowElementReferencesMixin.js","packages/basic-component-mixins/src/ShadowTemplateMixin.js","packages/basic-component-mixins/src/SingleSelectionMixin.js","packages/basic-component-mixins/src/createSymbol.js","packages/basic-component-mixins/src/microtask.js","packages/basic-component-mixins/src/safeAttributes.js","packages/basic-component-mixins/src/symbols.js","packages/basic-component-mixins/src/toggleClass.js","packages/basic-element-base/src/ElementBase.js","packages/basic-modes/globals.js","packages/basic-modes/src/Modes.js"],"names":["e","t","n","r","s","o","u","a","require","i","f","Error","code","l","exports","call","length","1","module","attributeToPropertyName","attributeName","propertyName","attributeToPropertyNames","hypenRegEx","replace","match","toUpperCase","attributesForClass","classFn","HTMLElement","Object","baseClass","getPrototypeOf","prototype","constructor","baseAttributes","propertyNames","getOwnPropertyNames","setterNames","filter","getOwnPropertyDescriptor","set","attributes","map","setterName","propertyNameToAttribute","diff","attribute","indexOf","concat","propertyNamesToAttributes","uppercaseRegEx","toLowerCase","_safeAttributes","base","AttributeMarshalling","_base","_classCallCheck","this","_possibleConstructorReturn","__proto__","apply","arguments","_inherits","_createClass","key","value","oldValue","newValue","_get","_safeAttributes2","default","connected","setAttribute","className","toggleClass","get","composeClass","mixin","Subclass","_base2","copyOwnProperties","NON_MIXABLE_OBJECT_PROPERTIES","source","target","ignorePropertyNames","undefined","forEach","name","descriptor","defineProperty","Composable","_len","mixins","Array","_key","reduce","filterAuxiliaryElements","items","auxiliaryTags","item","localName","_createSymbol","_toggleClass","_symbols","itemsSymbol","_createSymbol2","itemInitializedSymbol","ContentItems","_symbols2","itemsChanged","itemAdded","itemSelected","selected","_toggleClass2","_this2","dispatchEvent","CustomEvent","content","_microtask","DistributedChildrenContent","_this","shadowRoot","slots","querySelectorAll","slot","addEventListener","event","contentChanged","_microtask2","distributedChildren","console","warn","_set","expandContentElements","nodes","includeTextNodes","_ref","expanded","node","isSlot","HTMLSlotElement","assignedNodes","flatten","Text","flattened","_toConsumableArray","DistributedChildren","children","childNodes","strings","distributedChildNodes","child","textContent","join","ShadowElementReferences","$","nodesWithIds","id","getAttribute","createTemplateWithInnerHTML","innerHTML","template","document","createElement","div","appendChild","shimTemplateStyles","tag","window","WebComponents","ShadowCSS","shimStyling","ShadowTemplate","ShadowDOMPolyfill","root","attachShadow","mode","clone","importNode","selectIndex","element","index","count","boundedIndex","selectionWraps","Math","max","min","previousIndex","selectedIndex","trackSelectedItem","itemCount","previousSelectedItem","selectedItem","indexInCurrentItems","previousSelectedIndex","newSelectedIndex","selectionRequired","updatePossibleNavigations","canSelectNext","canSelectPrevious","canSelectNextSymbol","canSelectPreviousSymbol","selectionRequiredSymbol","selectionWrapsSymbol","externalSelectedIndexSymbol","externalSelectedItemSymbol","internalSelectedIndexSymbol","internalSelectedItemSymbol","SingleSelection","defaults","newIndex","previousCanSelectNext","previousCanSelectPrevious","hasItems","detail","String","createSymbol","description","Symbol","microtask","callback","callbacks","push","counter","executeCallbacks","shift","createTextNode","observer","MutationObserver","observe","characterData","setAttributeToElement","removeAttribute","text","safeToSetAttributesSymbol","pendingAttributesSymbol","pendingClassesSymbol","_value","_toggleClass3","symbols","dragging","goDown","goEnd","goLeft","goRight","goStart","goUp","keydown","force","classList","addClass","contains","add","remove","_AttributeMarshallingMixin","_ComposableMixin","_DistributedChildrenMixin","_ShadowElementReferencesMixin","_ShadowTemplateMixin","ElementBase","_ComposableMixin2","compose","_ShadowTemplateMixin2","_ShadowElementReferencesMixin2","_AttributeMarshallingMixin2","_DistributedChildrenMixin2","_Modes","Basic","Modes","_Modes2","_ElementBase","_DistributedChildrenContentMixin","_ContentItemsMixin","_SingleSelectionMixin","_ElementBase2","_ContentItemsMixin2","_DistributedChildrenContentMixin2","_SingleSelectionMixin2","style","display","customElements","define"],"mappings":"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","file":"basic-modes.js","sourcesContent":["(function e(t,n,r){function s(o,u){if(!n[o]){if(!t[o]){var a=typeof require==\"function\"&&require;if(!u&&a)return a(o,!0);if(i)return i(o,!0);var f=new Error(\"Cannot find module '\"+o+\"'\");throw f.code=\"MODULE_NOT_FOUND\",f}var l=n[o]={exports:{}};t[o][0].call(l.exports,function(e){var n=t[o][1][e];return s(n?n:e)},l,l.exports,e,t,n,r)}return n[o].exports}var i=typeof require==\"function\"&&require;for(var o=0;o {\n\n /**\n * Mixin which marshalls attributes to properties and vice versa.\n *\n * If your component exposes a setter for a property, it's generally a good\n * idea to let devs using your component be able to set that property in HTML\n * via an element attribute. You can code that yourself by writing an\n * `attributeChangedCallback`, or you can use this mixin to get a degree of\n * automatic support.\n *\n * This mixin implements an `attributeChangedCallback` that will attempt to\n * convert a change in an element attribute into a call to the corresponding\n * property setter. Attributes typically follow hyphenated names (\"foo-bar\"),\n * whereas properties typically use camelCase names (\"fooBar\"). This mixin\n * respects that convention, automatically mapping the hyphenated attribute\n * name to the corresponding camelCase property name.\n *\n * Example: You define a component using this mixin:\n *\n * class MyElement extends AttributeMarshallingMixin(HTMLElement) {\n * get fooBar() { return this._fooBar; }\n * set fooBar(value) { this._fooBar = value; }\n * }\n * customElements.define('my-element', MyElement);\n *\n * If someone then instantiates your component in HTML:\n *\n * \n *\n * Then, after the element has been upgraded, the `fooBar` setter will\n * automatically be invoked with the initial value \"Hello\".\n *\n * For the time being, this mixin only supports string-valued properties.\n * If you'd like to convert string attributes to other types (numbers,\n * booleans), you need to implement `attributeChangedCallback` yourself.\n */\n class AttributeMarshalling extends base {\n\n /*\n * Handle a change to the attribute with the given name.\n */\n attributeChangedCallback(attributeName, oldValue, newValue) {\n if (super.attributeChangedCallback) { super.attributeChangedCallback(); }\n const propertyName = attributeToPropertyName(attributeName);\n // If the attribute name corresponds to a property name, set the property.\n // Ignore standard HTMLElement properties handled by the DOM.\n if (propertyName in this && !(propertyName in HTMLElement.prototype)) {\n this[propertyName] = newValue;\n }\n }\n\n connectedCallback() {\n if (super.connectedCallback) { super.connectedCallback(); }\n safeAttributes.connected(this);\n }\n\n static get observedAttributes() {\n return attributesForClass(this);\n }\n\n /**\n * Set/unset the attribute with the indicated name.\n *\n * This method exists primarily to handle the case where an element wants to\n * set a default property value that should be reflected as an attribute. An\n * important limitation of custom element consturctors is that they cannot\n * set attributes. A call to `reflectAttribute` during the constructor will\n * be deferred until the element is connected to the document.\n *\n * @param {string} attribute - The name of the *attribute* (not property) to set.\n * @param {object} value - The value to set. If null, the attribute will be removed.\n */\n reflectAttribute(attribute, value) {\n return safeAttributes.setAttribute(this, attribute, value);\n }\n\n /**\n * Set/unset the class with the indicated name.\n *\n * This method exists primarily to handle the case where an element wants to\n * set a default property value that should be reflected as as class. An\n * important limitation of custom element consturctors is that they cannot\n * set attributes, including the `class` attribute. A call to\n * `reflectClass` during the constructor will be deferred until the element\n * is connected to the document.\n *\n * @param {string} className - The name of the class to set.\n * @param {object} value - True to set the class, false to remove it.\n */\n reflectClass(className, value) {\n return safeAttributes.toggleClass(this, className, value);\n }\n\n }\n\n return AttributeMarshalling;\n};\n\n\n// Convert hyphenated foo-bar attribute name to camel case fooBar property name.\nfunction attributeToPropertyName(attributeName) {\n let propertyName = attributeToPropertyNames[attributeName];\n if (!propertyName) {\n // Convert and memoize.\n const hypenRegEx = /-([a-z])/g;\n propertyName = attributeName.replace(hypenRegEx,\n match => match[1].toUpperCase());\n attributeToPropertyNames[attributeName] = propertyName;\n }\n return propertyName;\n}\n\nfunction attributesForClass(classFn) {\n\n // We treat the element base classes as if they have no attributes, since we\n // don't want to receive attributeChangedCallback for them.\n if (classFn === HTMLElement || classFn === Object) {\n return [];\n }\n\n // Get attributes for parent class.\n const baseClass = Object.getPrototypeOf(classFn.prototype).constructor;\n const baseAttributes = attributesForClass(baseClass);\n\n // Get attributes for this class.\n const propertyNames = Object.getOwnPropertyNames(classFn.prototype);\n const setterNames = propertyNames.filter(propertyName =>\n typeof Object.getOwnPropertyDescriptor(\n classFn.prototype, propertyName).set === 'function');\n const attributes = setterNames.map(setterName =>\n propertyNameToAttribute(setterName));\n\n // Merge.\n const diff = attributes.filter(attribute =>\n baseAttributes.indexOf(attribute) < 0);\n return baseAttributes.concat(diff);\n}\n\n// Convert a camel case fooBar property name to a hyphenated foo-bar attribute.\nfunction propertyNameToAttribute(propertyName) {\n let attribute = propertyNamesToAttributes[propertyName];\n if (!attribute) {\n // Convert and memoize.\n const uppercaseRegEx = /([A-Z])/g;\n attribute = propertyName.replace(uppercaseRegEx, '-$1').toLowerCase();\n }\n return attribute;\n}\n","/* Exported function extends a base class with Composable. */\nexport default (base) => {\n\n /**\n * Mixin to make a class more easily composable with other mixins.\n *\n * This mixin contributes a `compose` method that applies a set of mixin\n * functions and returns the resulting new class. This sugar can make the\n * application of many mixins at once easier to read.\n */\n class Composable extends base {\n\n /**\n * Apply a set of mixin functions or mixin objects to the present class and\n * return the new class.\n *\n * Instead of writing:\n *\n * let MyClass = Mixin1(Mixin2(Mixin3(Mixin4(Mixin5(BaseClass)))));\n *\n * You can write:\n *\n * let MyClass = ComposableMixin(BaseClass).compose(\n * Mixin1,\n * Mixin2,\n * Mixin3,\n * Mixin4,\n * Mixin5\n * );\n *\n * This function can also take mixin objects. A mixin object is just a\n * shorthand for a mixin function that creates a new subclass with the given\n * members. The mixin object's members are *not* copied directly onto the\n * prototype of the base class, as with traditional mixins.\n *\n * In addition to providing syntactic sugar, this mixin can be used to\n * define a class in ES5, which lacks ES6's `class` keyword.\n *\n * @param {...mixins} mixins - A set of mixin functions or objects to apply.\n */\n static compose(...mixins) {\n // We create a new subclass for each mixin in turn. The result becomes\n // the base class extended by any subsequent mixins. It turns out that\n // we can use Array.reduce() to concisely express this, using the current\n // object as the seed for reduce().\n return mixins.reduce(composeClass, this);\n }\n\n }\n\n return Composable;\n};\n\n\n// Properties defined by Object that we don't want to mixin.\nconst NON_MIXABLE_OBJECT_PROPERTIES = [\n 'constructor'\n];\n\n/*\n * Apply the mixin to the given base class to return a new class.\n * The mixin can either be a function that returns the modified class, or a\n * plain object whose members will be copied to the new class' prototype.\n */\nfunction composeClass(base, mixin) {\n if (typeof mixin === 'function') {\n // Mixin function\n return mixin(base);\n } else {\n // Mixin object\n class Subclass extends base {}\n copyOwnProperties(mixin, Subclass.prototype, NON_MIXABLE_OBJECT_PROPERTIES);\n return Subclass;\n }\n}\n\n\n/*\n * Copy the given properties/methods to the target.\n * Return the updated target.\n */\nfunction copyOwnProperties(source, target, ignorePropertyNames = []) {\n Object.getOwnPropertyNames(source).forEach(name => {\n if (ignorePropertyNames.indexOf(name) < 0) {\n const descriptor = Object.getOwnPropertyDescriptor(source, name);\n Object.defineProperty(target, name, descriptor);\n }\n });\n return target;\n}\n","import createSymbol from './createSymbol';\nimport toggleClass from './toggleClass';\nimport symbols from './symbols';\n\n\n// Symbols for private data members on an element.\nconst itemsSymbol = createSymbol('items');\nconst itemInitializedSymbol = createSymbol('itemInitialized');\n\n\n/* Exported function extends a base class with ContentItems. */\nexport default (base) => {\n\n /**\n * Mixin which maps content semantics (elements) to list item semantics.\n *\n * Items differ from element contents in several ways:\n *\n * * They are often referenced via index.\n * * They may have a selection state.\n * * It's common to do work to initialize the appearance or state of a new\n * item.\n * * Auxiliary invisible child elements are filtered out and not counted as\n * items. Auxiliary elements include link, script, style, and template\n * elements. This filtering ensures that those auxiliary elements can be\n * used in markup inside of a list without being treated as list items.\n *\n * This mixin expects a component to provide a `content` property returning a\n * raw set of elements. You can provide that yourself, or use\n * [DistributedChildrenContentMixin](DistributedChildrenContentMixin.md).\n *\n * The most commonly referenced property defined by this mixin is the `items`\n * property. To avoid having to do work each time that property is requested,\n * this mixin supports an optimized mode. If you invoke the `contentChanged`\n * method when the set of items changes, the mixin concludes that you'll take\n * care of notifying it of future changes, and turns on the optimization. With\n * that on, the mixin saves a reference to the computed set of items, and will\n * return that immediately on subsequent calls to the `items` property. If you\n * use this mixin in conjunction with\n * [DistributedChildrenContentMixin](DistributedChildrenContentMixin.md), the\n * `contentChanged` method will be invoked for you when the element's children\n * change, turning on the optimization automatically.\n */\n class ContentItems extends base {\n\n contentChanged() {\n if (super.contentChanged) { super.contentChanged(); }\n\n // Since we got the contentChanged call, we'll assume we'll be notified if\n // the set of items changes later. We turn on memoization of the items\n // property by setting our internal property to null (instead of\n // undefined).\n this[itemsSymbol] = null;\n\n this[symbols.itemsChanged]();\n }\n\n /**\n * This method is invoked whenever a new item is added to the list.\n *\n * The default implementation of this method does nothing. You can override\n * this to perform per-item initialization.\n *\n * @param {HTMLElement} item - The item that was added.\n */\n [symbols.itemAdded](item) {\n if (super[symbols.itemAdded]) { super[symbols.itemAdded](item); }\n }\n\n /**\n * The selection state for a single item has changed.\n *\n * Invoke this method to signal that the selected state of the indicated item\n * has changed. By default, this applies a `selected` CSS class if the item\n * is selected, and removed it if not selected.\n *\n * @param {HTMLElement} item - The item whose selection state has changed.\n * @param {boolean} selected - True if the item is selected, false if not.\n */\n [symbols.itemSelected](item, selected) {\n if (super[symbols.itemSelected]) { super[symbols.itemSelected](item, selected); }\n toggleClass(item, 'selected', selected);\n }\n\n /**\n * The current set of items in the list. See the top-level documentation for\n * mixin for a description of how items differ from plain content.\n *\n * @type {HTMLElement[]}\n */\n get items() {\n let items;\n if (this[itemsSymbol] == null) {\n items = filterAuxiliaryElements(this.content);\n // Note: test for *equality* with null; don't treat undefined as a match.\n if (this[itemsSymbol] === null) {\n // Memoize the set of items.\n this[itemsSymbol] = items;\n }\n } else {\n // Return the memoized items.\n items = this[itemsSymbol];\n }\n return items;\n }\n\n /**\n * This method is invoked when the underlying contents change. It is also\n * invoked on component initialization – since the items have \"changed\" from\n * being nothing.\n */\n [symbols.itemsChanged]() {\n if (super[symbols.itemsChanged]) { super[symbols.itemsChanged](); }\n\n // Perform per-item initialization.\n Array.prototype.forEach.call(this.items, item => {\n if (!item[itemInitializedSymbol]) {\n this[symbols.itemAdded](item);\n item[itemInitializedSymbol] = true;\n }\n });\n\n this.dispatchEvent(new CustomEvent('items-changed'));\n }\n\n /**\n * Fires when the items in the list change.\n *\n * @memberof ContentItems\n * @event items-changed\n */\n }\n\n return ContentItems;\n};\n\n\n// Return the given elements, filtering out auxiliary elements that aren't\n// typically visible. Items which are not elements are returned as is.\nfunction filterAuxiliaryElements(items) {\n const auxiliaryTags = [\n 'link',\n 'script',\n 'style',\n 'template'\n ];\n return [].filter.call(items, function(item) {\n return !item.localName || auxiliaryTags.indexOf(item.localName) < 0;\n });\n}\n","import microtask from './microtask';\n\n\n/* Exported function extends a base class with DistributedChildrenContent. */\nexport default (base) => {\n\n /**\n * Mixin which defines a component's content as its children, expanding any\n * nodes distributed to the component's slots.\n *\n * This also provides notification of changes to a component's content. It\n * will invoke a `contentChanged` method when the component is first\n * instantiated, and whenever its distributed children change. This is an\n * easy way to satisfy the Gold Standard checklist item for monitoring\n * [Content Changes](https://github.com/webcomponents/gold-standard/wiki/Content-Changes).\n *\n * Example:\n *\n * ```\n * let base = DistributedChildrenContentMixin(DistributedChildrenMixin(HTMLElement));\n * class CountingElement extends base {\n *\n * constructor() {\n * super();\n * let root = this.attachShadow({ mode: 'open' });\n * root.innerHTML = ` `;\n * }\n *\n * contentChanged() {\n * // Count the component's children, both initially and when changed.\n * this.count = this.distributedChildren.length;\n * }\n *\n * }\n * ```\n *\n * Note that content change detection depends upon the element having at least\n * one `slot` element in its shadow subtree.\n *\n * This mixin is intended for use with the\n * [DistributedChildrenMixin](DistributedChildrenMixin.md). See that mixin for\n * a discussion of how that works. This DistributedChildrenContentMixin\n * provides an easy way of defining the \"content\" of a component as the\n * component's distributed children. That in turn lets mixins like\n * [ContentItemsMixin](ContentItemsMixin.md) manipulate the children as list\n * items.\n */\n class DistributedChildrenContent extends base {\n\n constructor() {\n super();\n\n if (this.shadowRoot) {\n // Listen to changes on all slots.\n const slots = this.shadowRoot.querySelectorAll('slot');\n slots.forEach(slot => slot.addEventListener('slotchange', event => {\n this.contentChanged();\n }));\n }\n\n // Make an initial call to contentChanged() so that the component can do\n // initialization that it normally does when content changes.\n //\n // This will invoke contentChanged() handlers in other mixins. In order\n // that those mixins have a chance to complete their own initialization,\n // we add the contentChanged() call to the microtask queue.\n microtask(() => this.contentChanged());\n }\n\n /**\n * Invoked when the contents of the component (including distributed\n * children) have changed.\n *\n * This method is also invoked when a component is first instantiated; the\n * contents have essentially \"changed\" from being nothing. This allows the\n * component to perform initial processing of its children.\n */\n contentChanged() {\n if (super.contentChanged) { super.contentChanged(); }\n const event = new CustomEvent('content-changed');\n this.dispatchEvent(event);\n }\n\n /**\n * The content of this component, defined to be the flattened array of\n * children distributed to the component.\n *\n * @type {HTMLElement[]}\n */\n get content() {\n const distributedChildren = this.distributedChildren;\n if (typeof distributedChildren === 'undefined') {\n console.warn(`DistributedChildrenContentMixin expects the component to define a \"distributedChildren\" property.`);\n }\n return distributedChildren;\n }\n set content(value) {\n if ('content' in base.prototype) { super.content = value; }\n // TODO: Set the children to the given value (which should be an array of\n // elements)?\n }\n\n /**\n * This event is raised when the component's contents (including distributed\n * children) have changed.\n *\n * @memberof DistributedChildrenContent\n * @event content-changed\n */\n }\n\n return DistributedChildrenContent;\n};\n","/* Exported function extends a base class with DistributedChildren. */\nexport default (base) => {\n\n /**\n * Mixin which defines helpers for accessing a component's distributed\n * children as a flattened array or string.\n *\n * The standard DOM API provides several ways of accessing child content:\n * `children`, `childNodes`, and `textContent`. None of these functions are\n * Shadow DOM aware. This mixin defines variations of those functions that\n * *are* Shadow DOM aware.\n *\n * Example: you create a component `` that displays a number\n * equal to the number of children placed inside that component. If someone\n * instantiates your component like:\n *\n * \n *
\n *
\n *
\n * \n *\n * Then the component should show \"3\", because there are three children. To\n * calculate the number of children, the component can just calculate\n * `this.children.length`. However, suppose someone instantiates your\n * component inside one of their own components, and puts a `` element\n * inside your component:\n *\n * \n * \n * \n *\n * If your component only looks at `this.children`, it will always see exactly\n * one child — the `` element. But the user looking at the page will\n * *see* any nodes distributed to that slot. To match what the user sees, your\n * component should expand any `` elements it contains.\n *\n * That is the problem this mixin solves. After applying this mixin, your\n * component code has access to `this.distributedChildren`, whose `length`\n * will return the total number of all children distributed to your component\n * in the composed tree.\n *\n * Note: The latest Custom Elements API design calls for a new function,\n * `getAssignedNodes` that takes an optional `deep` parameter, that will solve\n * this problem at the API level.\n */\n class DistributedChildren extends base {\n\n /**\n * An in-order collection of distributed children, expanding any slot\n * elements. Like the standard children property, this skips text nodes.\n *\n * @type {HTMLElement[]}\n */\n get distributedChildren() {\n return expandContentElements(this.children, false);\n }\n\n /**\n * An in-order collection of distributed child nodes, expanding any slot\n * elements. Like the standard childNodes property, this includes text\n * nodes.\n *\n * @type {Node[]}\n */\n get distributedChildNodes() {\n return expandContentElements(this.childNodes, true);\n }\n\n /**\n * The concatenated text content of all distributed child nodes, expanding\n * any slot elements.\n *\n * @type {string}\n */\n get distributedTextContent() {\n const strings = this.distributedChildNodes.map(function(child) {\n return child.textContent;\n });\n return strings.join('');\n }\n\n }\n\n return DistributedChildren;\n};\n\n\n/*\n * Given a array of nodes, return a new array with any content elements expanded\n * to the nodes distributed to that content element. This rule is applied\n * recursively.\n *\n * If includeTextNodes is true, text nodes will be included, as in the\n * standard childNodes property; by default, this skips text nodes, like the\n * standard children property.\n */\nfunction expandContentElements(nodes, includeTextNodes) {\n const expanded = Array.prototype.map.call(nodes, node => {\n // We want to see if the node is an instanceof HTMLSlotELement, but\n // that class won't exist if the browser that doesn't support native\n // Shadow DOM and if the Shadow DOM polyfill hasn't been loaded. Instead,\n // we do a simplistic check to see if the tag name is \"slot\".\n const isSlot = typeof HTMLSlotElement !== 'undefined' ?\n node instanceof HTMLSlotElement :\n node.localName === 'slot';\n if (isSlot) {\n // Use the nodes assigned to this node instead.\n const assignedNodes = node.assignedNodes({ flatten: true });\n return assignedNodes ?\n expandContentElements(assignedNodes, includeTextNodes) :\n [];\n } else if (node instanceof HTMLElement) {\n // Plain element; use as is.\n return [node];\n } else if (node instanceof Text && includeTextNodes) {\n // Text node.\n return [node];\n } else {\n // Comment, processing instruction, etc.; skip.\n return [];\n }\n });\n const flattened = [].concat(...expanded);\n return flattened;\n}\n","/* Exported function extends a base class with ShadowElementReferences. */\nexport default (base) => {\n\n /**\n * Mixin to create references to elements in a component's Shadow DOM subtree.\n *\n * This adds a member on the component called `this.$` that can be used to\n * reference shadow elements with IDs. E.g., if component's shadow contains an\n * element ``, then this mixin will create a member\n * `this.$.foo` that points to that button.\n *\n * Such references simplify a component's access to its own elements. In\n * exchange, this mixin trades off a one-time cost of querying all elements in\n * the shadow tree instead of paying an ongoing cost to query for an element\n * each time the component wants to inspect or manipulate it.\n *\n * This mixin expects the component to define a Shadow DOM subtree. You can\n * create that tree yourself, or make use of\n * [ShadowTemplateMixin](ShadowTemplateMixin.md).\n *\n * This mixin is inspired by Polymer's [automatic\n * node finding](https://www.polymer-project.org/1.0/docs/devguide/local-dom.html#node-finding)\n * feature.\n */\n class ShadowElementReferences extends base {\n\n constructor() {\n super();\n if (this.shadowRoot) {\n // Look for elements in the shadow subtree that have id attributes.\n // An alternatively implementation of this mixin would be to just define\n // a this.$ getter that lazily does this search the first time someone\n // tries to access this.$. That might introduce some complexity – if the\n // the tree changed after it was first populated, the result of\n // searching for a node might be somewhat unpredictable.\n this.$ = {};\n const nodesWithIds = this.shadowRoot.querySelectorAll('[id]');\n [].forEach.call(nodesWithIds, node => {\n const id = node.getAttribute('id');\n this.$[id] = node;\n });\n }\n }\n\n /**\n * The collection of references to the elements with IDs in a component's\n * Shadow DOM subtree.\n *\n * @type {object}\n * @member $\n */\n }\n\n return ShadowElementReferences;\n};\n","import symbols from '../src/symbols';\n\n\n/* Exported function extends a base class with ShadowTemplate. */\nexport default (base) => {\n\n /**\n * Mixin for stamping a template into a Shadow DOM subtree upon component\n * instantiation.\n *\n * To use this mixin, define a `template` property as a string or HTML\n * `` element:\n *\n * class MyElement extends ShadowTemplateMixin(HTMLElement) {\n * get [symbols.template]() {\n * return `Hello, world .`;\n * }\n * }\n *\n * When your component class is instantiated, a shadow root will be created on\n * the instance, and the contents of the template will be cloned into the\n * shadow root. If your component does not define a `template` property, this\n * mixin has no effect.\n *\n * For the time being, this extension retains support for Shadow DOM v0. That\n * will eventually be deprecated as browsers (and the Shadow DOM polyfill)\n * implement Shadow DOM v1.\n */\n class ShadowTemplate extends base {\n\n /*\n * If the component defines a template, a shadow root will be created on the\n * component instance, and the template stamped into it.\n */\n constructor() {\n super();\n let template = this[symbols.template];\n // TODO: Save the processed template with the component's class prototype\n // so it doesn't need to be processed with every instantiation.\n if (template) {\n\n if (typeof template === 'string') {\n // Upgrade plain string to real template.\n template = createTemplateWithInnerHTML(template);\n }\n\n if (window.ShadowDOMPolyfill) {\n shimTemplateStyles(template, this.localName);\n }\n\n const root = this.attachShadow({ mode: 'open' });\n const clone = document.importNode(template.content, true);\n root.appendChild(clone);\n }\n }\n\n }\n\n return ShadowTemplate;\n};\n\n\n// Convert a plain string of HTML into a real template element.\nfunction createTemplateWithInnerHTML(innerHTML) {\n const template = document.createElement('template');\n // REVIEW: Is there an easier way to do this?\n // We'd like to just set innerHTML on the template content, but since it's\n // a DocumentFragment, that doesn't work.\n const div = document.createElement('div');\n div.innerHTML = innerHTML;\n while (div.childNodes.length > 0) {\n template.content.appendChild(div.childNodes[0]);\n }\n return template;\n}\n\n// Invoke basic style shimming with ShadowCSS.\nfunction shimTemplateStyles(template, tag) {\n window.WebComponents.ShadowCSS.shimStyling(template.content, tag);\n}\n","import createSymbol from './createSymbol';\nimport symbols from './symbols';\n\n\n// Symbols for private data members on an element.\nconst canSelectNextSymbol = createSymbol('canSelectNext');\nconst canSelectPreviousSymbol = createSymbol('canSelectPrevious');\nconst selectionRequiredSymbol = createSymbol('selectionRequired');\nconst selectionWrapsSymbol = createSymbol('selectionWraps');\n\n// We want to expose both selectedIndex and selectedItem as independent\n// properties but keep them in sync. This allows a component user to reference\n// the selection by whatever means is most natural for their situation.\n//\n// To efficiently keep these properties in sync, we track \"external\" and\n// \"internal\" references for each property:\n//\n// The external index or item is the one we report to the outside world when\n// asked for selection. When handling a change to index or item, we update the\n// external reference as soon as possible, so that if anyone immediately asks\n// for the current selection, they will receive a stable answer.\n//\n// The internal index or item tracks whichever index or item last received the\n// full set of processing. Processing includes raising a change event for the\n// new value. Once we've begun that processing, we store the new value as the\n// internal value to indicate we've handled it.\n//\nconst externalSelectedIndexSymbol = createSymbol('externalSelectedIndex');\nconst externalSelectedItemSymbol = createSymbol('externalSelectedItem');\nconst internalSelectedIndexSymbol = createSymbol('internalSelectedIndex');\nconst internalSelectedItemSymbol = createSymbol('internalSelectedItem');\n\n\n/* Exported function extends a base class with SingleSelection. */\nexport default (base) => {\n\n /**\n * Mixin which manages single-selection semantics for items in a list.\n *\n * This mixin expects a component to provide an `items` Array or NodeList of\n * all elements in the list. A standard way to do that with is the\n * [ContentItemsMixin](ContentItemsMixin.md), which takes a component's\n * content (typically its distributed children) as the set of list items; see\n * that mixin for details.\n *\n * This mixin tracks a single selected item in the list, and provides means to\n * get and set that state by item position (`selectedIndex`) or item identity\n * (`selectedItem`). The selection can be moved in the list via the methods\n * `selectFirst`, `selectLast`, `selectNext`, and `selectPrevious`.\n *\n * This mixin does not produce any user-visible effects to represent\n * selection. Other mixins, such as\n * [SelectionAriaActiveMixin](SelectionAriaActiveMixin.md),\n * [SelectionHighlightMixin](SelectionHighlightMixin.md) and\n * [SelectionInViewMixin](SelectionInViewMixin.md), modify the selected item\n * in common ways to let the user know a given item is selected or not\n * selected.\n */\n class SingleSelection extends base {\n\n constructor() {\n super();\n // Set defaults.\n if (typeof this.selectionRequired === 'undefined') {\n this.selectionRequired = this[symbols.defaults].selectionRequired;\n }\n if (typeof this.selectionWraps === 'undefined') {\n this.selectionWraps = this[symbols.defaults].selectionWraps;\n }\n }\n\n /**\n * True if the selection can be moved to the next item, false if not (the\n * selected item is the last item in the list).\n *\n * @type {boolean}\n */\n get canSelectNext() {\n return this[canSelectNextSymbol];\n }\n set canSelectNext(canSelectNext) {\n const previousCanSelectNext = this[canSelectNextSymbol];\n this[canSelectNextSymbol] = canSelectNext;\n if ('canSelectNext' in base.prototype) { super.canSelectNext = canSelectNext; }\n if (canSelectNext !== previousCanSelectNext) {\n this.dispatchEvent(new CustomEvent('can-select-next-changed'));\n }\n }\n\n /**\n * True if the selection can be moved to the previous item, false if not\n * (the selected item is the first one in the list).\n *\n * @type {boolean}\n */\n get canSelectPrevious() {\n return this[canSelectPreviousSymbol];\n }\n set canSelectPrevious(canSelectPrevious) {\n const previousCanSelectPrevious = this[canSelectPreviousSymbol];\n this[canSelectPreviousSymbol] = canSelectPrevious;\n if ('canSelectPrevious' in base.prototype) { super.canSelectPrevious = canSelectPrevious; }\n if (canSelectPrevious !== previousCanSelectPrevious) {\n this.dispatchEvent(new CustomEvent('can-select-previous-changed'));\n }\n }\n\n get [symbols.defaults]() {\n const defaults = super[symbols.defaults] || {};\n defaults.selectionRequired = false;\n defaults.selectionWraps = false;\n return defaults;\n }\n\n /**\n * Handle a new item being added to the list.\n *\n * The default implementation of this method simply sets the item's\n * selection state to false.\n *\n * @param {HTMLElement} item - the item being added\n */\n [symbols.itemAdded](item) {\n if (super[symbols.itemAdded]) { super[symbols.itemAdded](item); }\n this[symbols.itemSelected](item, item === this.selectedItem);\n }\n\n [symbols.itemsChanged]() {\n if (super[symbols.itemsChanged]) { super[symbols.itemsChanged](); }\n\n // In case selected item changed position or was removed.\n trackSelectedItem(this);\n\n // In case the change in items affected which navigations are possible.\n updatePossibleNavigations(this);\n }\n\n /**\n * Apply the indicate selection state to the item.\n *\n * The default implementation of this method does nothing. User-visible\n * effects will typically be handled by other mixins.\n *\n * @param {HTMLElement} item - the item being selected/deselected\n * @param {boolean} selected - true if the item is selected, false if not\n */\n [symbols.itemSelected](item, selected) {\n if (super[symbols.itemSelected]) { super[symbols.itemSelected](item, selected); }\n }\n\n /**\n * The index of the item which is currently selected.\n *\n * A `selectedIndex` of -1 indicates there is no selection. Setting this\n * property to -1 will remove any existing selection.\n *\n * @type {number}\n */\n get selectedIndex() {\n return this[externalSelectedIndexSymbol] != null ?\n this[externalSelectedIndexSymbol] :\n -1;\n }\n set selectedIndex(index) {\n // See notes at top about internal vs. external copies of this property.\n const previousSelectedIndex = this[internalSelectedIndexSymbol];\n let item;\n if (index !== this[externalSelectedIndexSymbol]) {\n // Store the new index and the corresponding item.\n const items = this.items;\n const hasItems = items && items.length > 0;\n if (!(hasItems && index >= 0 && index < items.length)) {\n index = -1; // No item at that index.\n }\n this[externalSelectedIndexSymbol] = index;\n item = hasItems && index >= 0 ? items[index] : null;\n this[externalSelectedItemSymbol] = item;\n } else {\n item = this[externalSelectedItemSymbol];\n }\n\n // Now let super do any work.\n if ('selectedIndex' in base.prototype) { super.selectedIndex = index; }\n\n if (index !== previousSelectedIndex) {\n // The selected index changed.\n this[internalSelectedIndexSymbol] = index;\n\n const event = new CustomEvent('selected-index-changed', {\n detail: {\n selectedIndex: index,\n value: index // for Polymer binding. TODO: Verify still necessary\n }\n });\n this.dispatchEvent(event);\n }\n\n if (this[internalSelectedItemSymbol] !== item) {\n // Update selectedItem property so it can have its own effects.\n this.selectedItem = item;\n }\n }\n\n /**\n * The currently selected item, or null if there is no selection.\n *\n * Setting this property to null deselects any currently-selected item.\n * Setting this property to an object that is not in the list has no effect.\n *\n * TODO: Even if selectionRequired, can still explicitly set selectedItem to null.\n * TODO: If selectionRequired, leave selection alone?\n *\n * @type {object}\n */\n get selectedItem() {\n return this[externalSelectedItemSymbol] || null;\n }\n set selectedItem(item) {\n // See notes at top about internal vs. external copies of this property.\n const previousSelectedItem = this[internalSelectedItemSymbol];\n let index;\n if (item !== this[externalSelectedItemSymbol]) {\n // Store item and look up corresponding index.\n const items = this.items;\n const hasItems = items && items.length > 0;\n index = hasItems ? Array.prototype.indexOf.call(items, item) : -1;\n this[externalSelectedIndexSymbol] = index;\n if (index < 0) {\n item = null; // The indicated item isn't actually in `items`.\n }\n this[externalSelectedItemSymbol] = item;\n } else {\n index = this[externalSelectedIndexSymbol];\n }\n\n // Now let super do any work.\n if ('selectedItem' in base.prototype) { super.selectedItem = item; }\n\n if (item !== previousSelectedItem) {\n // The selected item changed.\n this[internalSelectedItemSymbol] = item;\n\n if (previousSelectedItem) {\n // Update selection state of old item.\n this[symbols.itemSelected](previousSelectedItem, false);\n }\n if (item) {\n // Update selection state to new item.\n this[symbols.itemSelected](item, true);\n }\n\n updatePossibleNavigations(this);\n\n const event = new CustomEvent('selected-item-changed', {\n detail: {\n selectedItem: item,\n value: item // for Polymer binding\n }\n });\n this.dispatchEvent(event);\n }\n\n if (this[internalSelectedIndexSymbol] !== index) {\n // Update selectedIndex property so it can have its own effects.\n this.selectedIndex = index;\n }\n }\n\n /**\n * Select the first item in the list.\n */\n selectFirst() {\n if (super.selectFirst) { super.selectFirst(); }\n return selectIndex(this, 0);\n }\n\n /**\n * True if the list should always have a selection (if it has items).\n *\n * @type {boolean}\n * @default false\n */\n get selectionRequired() {\n return this[selectionRequiredSymbol];\n }\n set selectionRequired(selectionRequired) {\n this[selectionRequiredSymbol] = selectionRequired;\n if ('selectionRequired' in base.prototype) { super.selectionRequired = selectionRequired; }\n trackSelectedItem(this);\n }\n\n /**\n * True if selection navigations wrap from last to first, and vice versa.\n *\n * @type {boolean}\n * @default false\n */\n get selectionWraps() {\n return this[selectionWrapsSymbol];\n }\n set selectionWraps(value) {\n this[selectionWrapsSymbol] = String(value) === 'true';\n if ('selectionWraps' in base.prototype) { super.selectionWraps = value; }\n updatePossibleNavigations(this);\n }\n\n /**\n * Select the last item in the list.\n */\n selectLast() {\n if (super.selectLast) { super.selectLast(); }\n return selectIndex(this, this.items.length - 1);\n }\n\n /**\n * Select the next item in the list.\n */\n selectNext() {\n if (super.selectNext) { super.selectNext(); }\n return selectIndex(this, this.selectedIndex + 1);\n }\n\n /**\n * Select the previous item in the list.\n *\n * If the list has no selection, the last item will be selected.\n */\n selectPrevious() {\n if (super.selectPrevious) { super.selectPrevious(); }\n const newIndex = this.selectedIndex < 0 ?\n this.items.length - 1 : // No selection yet; select last item.\n this.selectedIndex - 1;\n return selectIndex(this, newIndex);\n }\n\n /**\n * Fires when the selectedItem property changes.\n *\n * @memberof SingleSelection\n * @event selected-item-changed\n * @param {HTMLElement} detail.selectedItem The new selected item.\n * @param {HTMLElement} detail.previousItem The previously selected item.\n */\n\n /**\n * Fires when the selectedIndex property changes.\n *\n * @memberof SingleSelection\n * @event selected-index-changed\n * @param {number} detail.selectedIndex The new selected index.\n */\n\n }\n\n return SingleSelection;\n};\n\n\n// Ensure the given index is within bounds, and select it if it's not already\n// selected.\nfunction selectIndex(element, index) {\n const count = element.items.length;\n\n const boundedIndex = (element.selectionWraps) ?\n // JavaScript mod doesn't handle negative numbers the way we want to wrap.\n // See http://stackoverflow.com/a/18618250/76472\n ((index % count) + count) % count :\n\n // Keep index within bounds of array.\n Math.max(Math.min(index, count - 1), 0);\n\n const previousIndex = element.selectedIndex;\n if (previousIndex !== boundedIndex) {\n element.selectedIndex = boundedIndex;\n return true;\n } else {\n return false;\n }\n}\n\n// Following a change in the set of items, or in the value of the\n// `selectionRequired` property, reacquire the selected item. If it's moved,\n// update `selectedIndex`. If it's been removed, and a selection is required,\n// try to select another item.\nfunction trackSelectedItem(element) {\n\n const items = element.items;\n const itemCount = items ? items.length : 0;\n\n const previousSelectedItem = element.selectedItem;\n if (!previousSelectedItem) {\n // No item was previously selected.\n if (element.selectionRequired) {\n // Select the first item by default.\n element.selectedIndex = 0;\n }\n } else if (itemCount === 0) {\n // We've lost the selection, and there's nothing left to select.\n element.selectedItem = null;\n } else {\n // Try to find the previously-selected item in the current set of items.\n const indexInCurrentItems = Array.prototype.indexOf.call(items, previousSelectedItem);\n const previousSelectedIndex = element.selectedIndex;\n if (indexInCurrentItems < 0) {\n // Previously-selected item was removed from the items.\n // Select the item at the same index (if it exists) or as close as possible.\n const newSelectedIndex = Math.min(previousSelectedIndex, itemCount - 1);\n // Select by item, since index may be the same, and we want to raise the\n // selected-item-changed event.\n element.selectedItem = items[newSelectedIndex];\n } else if (indexInCurrentItems !== previousSelectedIndex) {\n // Previously-selected item still there, but changed position.\n element.selectedIndex = indexInCurrentItems;\n }\n }\n}\n\n// Following a change in selection, report whether it's now possible to\n// go next/previous from the given index.\nfunction updatePossibleNavigations(element) {\n let canSelectNext;\n let canSelectPrevious;\n const items = element.items;\n if (items == null || items.length === 0) {\n // No items to select.\n canSelectNext = false;\n canSelectPrevious = false;\n } if (element.selectionWraps) {\n // Since there are items, can always go next/previous.\n canSelectNext = true;\n canSelectPrevious = true;\n } else {\n const index = element.selectedIndex;\n if (index < 0 && items.length > 0) {\n // Special case. If there are items but no selection, declare that it's\n // always possible to go next/previous to create a selection.\n canSelectNext = true;\n canSelectPrevious = true;\n } else {\n // Normal case: we have an index in a list that has items.\n canSelectPrevious = (index > 0);\n canSelectNext = (index < items.length - 1);\n }\n }\n if (element.canSelectNext !== canSelectNext) {\n element.canSelectNext = canSelectNext;\n }\n if (element.canSelectPrevious !== canSelectPrevious) {\n element.canSelectPrevious = canSelectPrevious;\n }\n}\n","/**\n * Helper function to create a symbol that can be used for associating private\n * data with an element.\n *\n * Mixins and component classes often want to associate private data with an\n * element instance, but JavaScript does not have direct support for true\n * private properties. One approach is to use the\n * [Symbol](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Symbol)\n * data type to set and retrieve data on an element.\n *\n * Unfortunately, the Symbol type is not available in Internet Explorer 11. The\n * `createSymbol` helper function exists as a workaround for IE 11. Rather than\n * returning a true Symbol, it simply returns an underscore-prefixed string.\n *\n * Usage:\n *\n * const fooSymbol = createSymbol('foo');\n *\n * class MyElement extends HTMLElement {\n * get foo() {\n * return this[fooSymbol];\n * }\n * set foo(value) {\n * this[fooSymbol] = value;\n * }\n * }\n *\n * In IE 11, this sample will \"hide\" data behind an instance property this._foo.\n * The use of the underscore is meant to reduce (not eliminate) the potential\n * for name conflicts, and discourage (not prevent) external access to this\n * data. In modern browsers, the above code will eliminate the potential of\n * naming conflicts, and better hide the data behind a real Symbol.\n *\n * @function createSymbol\n * @param {string} description - A string to identify the symbol when debugging\n */\nexport default function createSymbol(description) {\n return typeof Symbol === 'function' ?\n Symbol(description) :\n `_${description}`;\n}\n","/*\n * Microtask helper for IE 11.\n *\n * Executing a function as a microtask is trivial in browsers that support\n * promises, whose then() clauses use microtask timing. IE 11 doesn't support\n * promises, but does support MutationObservers, which are also executed as\n * microtasks. So this helper uses an MutationObserver to achieve microtask\n * timing.\n *\n * See https://jakearchibald.com/2015/tasks-microtasks-queues-and-schedules/\n *\n * Inspired by Polymer's async() function.\n */\n\n\n// The queue of pending callbacks to be executed as microtasks.\nconst callbacks = [];\n\n// Create an element that we will modify to force observable mutations.\nconst element = document.createTextNode('');\n\n// A monotonically-increasing value.\nlet counter = 0;\n\n\n/**\n * Add a callback to the microtask queue.\n *\n * This uses a MutationObserver so that it works on IE 11.\n *\n * NOTE: IE 11 may actually use timeout timing with MutationObservers. This\n * needs more investigation.\n *\n * @function microtask\n * @param {function} callback\n */\nexport default function microtask(callback) {\n callbacks.push(callback);\n // Force a mutation.\n element.textContent = ++counter;\n}\n\n\n// Execute any pending callbacks.\nfunction executeCallbacks() {\n while (callbacks.length > 0) {\n const callback = callbacks.shift();\n callback();\n }\n}\n\n\n// Create the observer.\nconst observer = new MutationObserver(executeCallbacks);\nobserver.observe(element, {\n characterData: true\n});\n","import createSymbol from './createSymbol';\nimport toggleClass from './toggleClass';\n\n\n// Symbols for private data members on an element.\nconst safeToSetAttributesSymbol = createSymbol('safeToSetAttributes');\nconst pendingAttributesSymbol = createSymbol('pendingAttributes');\nconst pendingClassesSymbol = createSymbol('pendingClasses');\n\n\n/**\n * Helper functions for updating attributes, including the `class` attribute.\n */\nexport default {\n\n /**\n * Perform any pending updates to attributes and classes.\n *\n * This writes any `setAttribute` or `toggleClass` values that were performed\n * before an element was attached to the document for the first time.\n *\n * This method should be called by mixins/components in their\n * `connectedCallback`. If mulitple mixins/components invoke this during the\n * same `connectedCallback`, only the first call will have any effect. The\n * subsequent calls will be harmless.\n *\n * @param {HTMLElement} element - The element being added to the document.\n */\n connected(element) {\n element[safeToSetAttributesSymbol] = true;\n\n // Set any pending attributes.\n if (element[pendingAttributesSymbol]) {\n for (let attribute in element[pendingAttributesSymbol]) {\n const value = element[pendingAttributesSymbol][attribute];\n setAttributeToElement(element, attribute, value);\n }\n element[pendingAttributesSymbol] = null;\n }\n\n // Set any pending classes.\n if (element[pendingClassesSymbol]) {\n for (let className in element[pendingClassesSymbol]) {\n const value = element[pendingClassesSymbol][className];\n toggleClass(element, className, value);\n }\n element[pendingClassesSymbol] = null;\n }\n },\n\n /**\n * Set/unset the attribute with the indicated name.\n *\n * This method exists primarily to handle the case where an element wants to\n * set a default property value that should be reflected as an attribute. An\n * important limitation of custom element consturctors is that they cannot\n * set attributes. A call to `setAttribute` during the constructor will\n * be deferred until the element is connected to the document.\n *\n * @param {string} attribute - The name of the *attribute* (not property) to set.\n * @param {object} value - The value to set. If null, the attribute will be removed.\n */\n setAttribute(element, attribute, value) {\n if (element[safeToSetAttributesSymbol]) {\n // Safe to set attributes immediately.\n setAttributeToElement(element, attribute, value);\n } else {\n // Defer setting attributes until the first time we're connected.\n if (!element[pendingAttributesSymbol]) {\n element[pendingAttributesSymbol] = {};\n }\n element[pendingAttributesSymbol][attribute] = value;\n }\n },\n\n /**\n * Set/unset the class with the indicated name.\n *\n * This method exists primarily to handle the case where an element wants to\n * set a default property value that should be reflected as as class. An\n * important limitation of custom element consturctors is that they cannot\n * set attributes, including the `class` attribute. A call to\n * `toggleClass` during the constructor will be deferred until the element\n * is connected to the document.\n *\n * @param {string} className - The name of the class to set.\n * @param {object} value - True to set the class, false to remove it.\n */\n toggleClass(element, className, value) {\n if (element[safeToSetAttributesSymbol]) {\n // Safe to set class immediately.\n toggleClass(element, className, value);\n } else {\n // Defer setting class until the first time we're connected.\n if (!element[pendingClassesSymbol]) {\n element[pendingClassesSymbol] = {};\n }\n element[pendingClassesSymbol][className] = value;\n }\n }\n\n};\n\n\n// Reflect the attribute to the given element.\n// If the value is null, remove the attribute.\nfunction setAttributeToElement(element, attributeName, value) {\n if (value === null || typeof value === 'undefined') {\n element.removeAttribute(attributeName);\n } else {\n const text = String(value);\n // Avoid recursive attributeChangedCallback calls.\n if (element.getAttribute(attributeName) !== text) {\n element.setAttribute(attributeName, value);\n }\n }\n}\n","import createSymbol from './createSymbol';\n\n/**\n * A collection of Symbol objects for standard component properties and methods.\n *\n * These Symbol objects are used to allow mixins and a component to internally\n * communicate, without exposing these properties and methods in the component's\n * public API.\n *\n * To use these Symbol objects in your own component, include this module and\n * then create a property or method whose key is the desired Symbol.\n *\n * import 'SingleSelectionMixin' from 'basic-component-mixins/src/SingleSelectionMixin';\n * import 'symbols' from 'basic-component-mixins/src/symbols';\n *\n * class MyElement extends SingleSelectionMixin(HTMLElement) {\n * [symbols.itemSelected](item, selected) {\n * // This will be invoked whenever an item is selected/deselected.\n * }\n * }\n *\n * @module symbols\n */\nconst symbols = {\n\n /**\n * Symbol for the `defaults` property.\n *\n * This property can be used to set or override defaults that will be applied\n * to a new component instance. When implementing this property, take care to\n * first acquire any defaults defined by the superclass. The standard idiom is\n * as follows:\n *\n * get [symbols.defaults]() {\n * const defaults = super[symbols.defaults] || {};\n * // Set or override default values here\n * defaults.customProperty = false;\n * return defaults;\n * }\n *\n * @var {object} defaults\n */\n defaults: createSymbol('defaults'),\n\n /**\n * Symbol for the `dragging` property.\n *\n * Components like carousels often define animated CSS transitions for\n * sliding effects. Such a transition should usually *not* be applied while\n * the user is dragging, because a CSS animation will introduce a lag that\n * makes the swipe feel sluggish. Instead, as long as the user is dragging\n * with their finger down, the transition should be suppressed. When the\n * user releases their finger, the transition can be restored, allowing the\n * animation to show the carousel sliding into its final position.\n *\n * @type {boolean} true if a drag is in progress, false if not.\n */\n dragging: createSymbol('dragging'),\n\n /**\n * Symbol for the `goDown` method.\n *\n * This method is invoked when the user wants to go/navigate down.\n *\n * @function goDown\n */\n goDown: createSymbol('goDown'),\n\n /**\n * Symbol for the `goEnd` method.\n *\n * This method is invoked when the user wants to go/navigate to the end (e.g.,\n * of a list).\n *\n * @function goEnd\n */\n goEnd: createSymbol('goEnd'),\n\n /**\n * Symbol for the `goLeft` method.\n *\n * This method is invoked when the user wants to go/navigate left.\n *\n * @function goLeft\n */\n goLeft: createSymbol('goLeft'),\n\n /**\n * Symbol for the `goRight` method.\n *\n * This method is invoked when the user wants to go/navigate right.\n *\n * @function goRight\n */\n goRight: createSymbol('goRight'),\n\n /**\n * Symbol for the `goStart` method.\n *\n * This method is invoked when the user wants to go/navigate to the start\n * (e.g., of a list).\n *\n * @function goStart\n */\n goStart: createSymbol('goStart'),\n\n /**\n * Symbol for the `goUp` method.\n *\n * This method is invoked when the user wants to go/navigate up.\n *\n * @function goUp\n */\n goUp: createSymbol('goUp'),\n\n /**\n * Symbol for the `itemAdded` method.\n *\n * This method is invoked when a new item is added to a list.\n *\n * @function itemAdded\n * @param {HTMLElement} item - the item being selected/deselected\n */\n itemAdded: createSymbol('itemAdded'),\n\n\n /**\n * Symbol for the `itemsChanged` method.\n *\n * This method is invoked when the underlying contents change. It is also\n * invoked on component initialization – since the items have \"changed\" from\n * being nothing.\n */\n itemsChanged: createSymbol('itemsChanged'),\n\n /**\n * Symbol for the `itemSelected` method.\n *\n * This method is invoked when an item becomes selected or deselected.\n *\n * @function itemSelected\n * @param {HTMLElement} item - the item being selected/deselected\n * @param {boolean} selected - true if the item is selected, false if not\n */\n itemSelected: createSymbol('itemSelected'),\n\n /**\n * Symbol for the `keydown` method.\n *\n * This method is invoked when an element receives a `keydown` event.\n *\n * @function keydown\n * @param {KeyboardEvent} event - the event being processed\n */\n keydown: createSymbol('keydown'),\n\n /**\n * Symbol for the `template` property.\n *\n * This property returns a component's template.\n *\n * @type {string|HTMLElement}\n */\n template: createSymbol('template')\n};\n\nexport default symbols;\n","/**\n * Helper function for standard classList.toggle() behavior on old browsers,\n * namely IE 11.\n *\n * The standard\n * [classlist](https://developer.mozilla.org/en-US/docs/Web/API/Element/classList)\n * object has a `toggle()` function that supports a second Boolean parameter\n * that can be used to succinctly turn a class on or off. This feature is often\n * useful in designing custom elements, which may want to externally reflect\n * component state in a CSS class that can be used for styling purposes.\n *\n * Unfortunately, IE 11 does not support the Boolean parameter to\n * `classList.toggle()`. This helper function behaves like the standard\n * `toggle()`, including support for the Boolean parameter, so that it can be\n * used even on IE 11.\n *\n * @function toggleClass\n * @param {HTMLElement} element - The element to modify\n * @param {string} className - The class to add/remove\n * @param {boolean} [force] - Force the class to be added (if true) or removed\n * (if false)\n */\nexport default function toggleClass(element, className, force) {\n const classList = element.classList;\n const addClass = (typeof force === 'undefined') ?\n !classList.contains(className) :\n force;\n if (addClass) {\n classList.add(className);\n } else {\n classList.remove(className);\n }\n return addClass;\n}\n","import AttributeMarshallingMixin from '../../basic-component-mixins/src/AttributeMarshallingMixin';\nimport ComposableMixin from '../../basic-component-mixins/src/ComposableMixin';\nimport DistributedChildrenMixin from '../../basic-component-mixins/src/DistributedChildrenMixin';\nimport ShadowElementReferencesMixin from '../../basic-component-mixins/src/ShadowElementReferencesMixin';\nimport ShadowTemplateMixin from '../../basic-component-mixins/src/ShadowTemplateMixin';\n\n\n/**\n * A sample general-purpose base class for defining custom elements that mixes\n * in some common features: template stamping into a shadow root, shadow element\n * references, marshalling attributes to properties, and retrieving the children\n * distributed to a component.\n *\n * This base class is not special in any way, and is defined only as a\n * convenient shorthand for applying the mixins listed above. You can use this\n * class as a base class for your own elements, or easily create your own base\n * class by applying the same set of mixins.\n *\n * The ElementBase base class does not register itself as a custom element with\n * the browser, and hence cannot be independently instantiated.\n *\n * @mixes AttributeMarshallingMixin\n * @mixes ComposableMixin\n * @mixes DistributedChildrenMixin\n * @mixes ShadowElementReferencesMixin\n * @mixes ShadowTemplateMixin\n */\nclass ElementBase extends ComposableMixin(HTMLElement).compose(\n ShadowTemplateMixin, // before node finding, so shadow root is populated\n ShadowElementReferencesMixin, // before marshalling, so properties can use refs\n AttributeMarshallingMixin,\n DistributedChildrenMixin\n) {}\n\nexport default ElementBase;\n","/*\n * This file is transpiled to create an ES5-compatible distribution in which\n * the package's main feature(s) are available via the window.Basic global.\n * If you're already using ES6 yourself, ignore this file, and instead import\n * the source file(s) you want from the src folder.\n */\n\nimport Modes from './src/Modes';\n\nwindow.Basic = window.Basic || {};\nwindow.Basic.Modes = Modes;\n","import ElementBase from '../../basic-element-base/src/ElementBase';\nimport DistributedChildrenContentMixin from '../../basic-component-mixins/src/DistributedChildrenContentMixin';\nimport ContentItemsMixin from '../../basic-component-mixins/src/ContentItemsMixin';\nimport SingleSelectionMixin from '../../basic-component-mixins/src/SingleSelectionMixin';\nimport symbols from '../../basic-component-mixins/src/symbols';\n\nconst base = ElementBase.compose(\n ContentItemsMixin,\n DistributedChildrenContentMixin,\n SingleSelectionMixin\n);\n\n\n/**\n * Shows exactly one child element at a time. This can be useful, for example,\n * if a given UI element has multiple modes that present substantially different\n * elements.\n *\n * [Live demo](http://basicwebcomponents.org/basic-web-components/packages/demos/modes-with-arrows-and-keyboard.html)\n *\n * The transition between child elements is instantenous. If you'd like the\n * transition to be accompanied by visible animated effects, see\n * [basic-animation-stage](../basic-animation-stage).\n *\n * This component doesn't provide any UI for changing which mode is shown.\n *\n * @extends ElementBase\n * @mixes ContentItemsMixin\n * @mixes DistributedChildrenContentMixin\n * @mixes SingleSelectionMixin\n */\nclass Modes extends base {\n\n get [symbols.defaults]() {\n const defaults = super[symbols.defaults] || {};\n defaults.selectionRequired = true;\n return defaults;\n }\n\n [symbols.itemAdded](item) {\n if (super[symbols.itemAdded]) { super[symbols.itemAdded](item); }\n // TODO: See node about aria-hidden below.\n item.setAttribute('aria-hidden', 'false');\n }\n\n [symbols.itemSelected](item, selected) {\n if (super[symbols.itemSelected]) { super[symbols.itemSelected](item, selected); }\n item.style.display = selected ? '' : 'none';\n // TODO: Should the modes which are not visible be exposed to ARIA?\n // Sometimes this will be desirable, as when an inactive mode should be\n // both physically invisible and invisible to ARIA. In other cases, it\n // might be desirable to let the user navigate the modes with the keyboard,\n // in which case ARIA should be able to see the inactive modes.\n // item.setAttribute('aria-hidden', !selected);\n }\n\n get [symbols.template]() {\n return ` `;\n }\n\n}\n\n\ncustomElements.define('basic-modes', Modes);\nexport default Modes;\n"]}
\ No newline at end of file
diff --git a/packages/basic-modes/src/Modes.js b/packages/basic-modes/src/Modes.js
index adae2223..653ccbfc 100644
--- a/packages/basic-modes/src/Modes.js
+++ b/packages/basic-modes/src/Modes.js
@@ -16,6 +16,8 @@ const base = ElementBase.compose(
* if a given UI element has multiple modes that present substantially different
* elements.
*
+ * [Live demo](http://basicwebcomponents.org/basic-web-components/packages/demos/modes-with-arrows-and-keyboard.html)
+ *
* The transition between child elements is instantenous. If you'd like the
* transition to be accompanied by visible animated effects, see
* [basic-animation-stage](../basic-animation-stage).
@@ -35,10 +37,21 @@ class Modes extends base {
return defaults;
}
+ [symbols.itemAdded](item) {
+ if (super[symbols.itemAdded]) { super[symbols.itemAdded](item); }
+ // TODO: See node about aria-hidden below.
+ item.setAttribute('aria-hidden', 'false');
+ }
+
[symbols.itemSelected](item, selected) {
if (super[symbols.itemSelected]) { super[symbols.itemSelected](item, selected); }
item.style.display = selected ? '' : 'none';
- item.setAttribute('aria-hidden', !selected);
+ // TODO: Should the modes which are not visible be exposed to ARIA?
+ // Sometimes this will be desirable, as when an inactive mode should be
+ // both physically invisible and invisible to ARIA. In other cases, it
+ // might be desirable to let the user navigate the modes with the keyboard,
+ // in which case ARIA should be able to see the inactive modes.
+ // item.setAttribute('aria-hidden', !selected);
}
get [symbols.template]() {
diff --git a/packages/basic-slideshow-with-controls/README.md b/packages/basic-slideshow-with-controls/README.md
index 90f55077..7b6c6879 100644
--- a/packages/basic-slideshow-with-controls/README.md
+++ b/packages/basic-slideshow-with-controls/README.md
@@ -6,6 +6,8 @@ An extension of
[basic-slideshow](../basic-slideshow) that adds play controls
via [PlayControlsMixin](../basic-component-mixins/docs/PlayControlsMixin.md).
+[Live demo](http://basicwebcomponents.org/basic-web-components/packages/basic-slideshow-with-controls/)
+
**Kind**: global class
**Extends:** Slideshow
**Mixes**: [PlayControlsMixin](../basic-component-mixins/docs/PlayControlsMixin.md)
diff --git a/packages/basic-slideshow-with-controls/dist/basic-slideshow-with-controls.js b/packages/basic-slideshow-with-controls/dist/basic-slideshow-with-controls.js
index 1c393182..c2cbdcf3 100644
--- a/packages/basic-slideshow-with-controls/dist/basic-slideshow-with-controls.js
+++ b/packages/basic-slideshow-with-controls/dist/basic-slideshow-with-controls.js
@@ -1,3726 +1,3 @@
-(function e(t,n,r){function s(o,u){if(!n[o]){if(!t[o]){var a=typeof require=="function"&&require;if(!u&&a)return a(o,!0);if(i)return i(o,!0);var f=new Error("Cannot find module '"+o+"'");throw f.code="MODULE_NOT_FOUND",f}var l=n[o]={exports:{}};t[o][0].call(l.exports,function(e){var n=t[o][1][e];return s(n?n:e)},l,l.exports,e,t,n,r)}return n[o].exports}var i=typeof require=="function"&&require;for(var o=0;o
- *
- * Then, after the element has been upgraded, the `fooBar` setter will
- * automatically be invoked with the initial value "Hello".
- *
- * For the time being, this mixin only supports string-valued properties.
- * If you'd like to convert string attributes to other types (numbers,
- * booleans), you need to implement `attributeChangedCallback` yourself.
- */
- var AttributeMarshalling = function (_base) {
- _inherits(AttributeMarshalling, _base);
-
- function AttributeMarshalling() {
- _classCallCheck(this, AttributeMarshalling);
-
- return _possibleConstructorReturn(this, (AttributeMarshalling.__proto__ || Object.getPrototypeOf(AttributeMarshalling)).apply(this, arguments));
- }
-
- _createClass(AttributeMarshalling, [{
- key: 'attributeChangedCallback',
-
-
- /*
- * Handle a change to the attribute with the given name.
- */
- value: function attributeChangedCallback(attributeName, oldValue, newValue) {
- if (_get(AttributeMarshalling.prototype.__proto__ || Object.getPrototypeOf(AttributeMarshalling.prototype), 'attributeChangedCallback', this)) {
- _get(AttributeMarshalling.prototype.__proto__ || Object.getPrototypeOf(AttributeMarshalling.prototype), 'attributeChangedCallback', this).call(this);
- }
- var propertyName = attributeToPropertyName(attributeName);
- // If the attribute name corresponds to a property name, set the property.
- // Ignore standard HTMLElement properties handled by the DOM.
- if (propertyName in this && !(propertyName in HTMLElement.prototype)) {
- this[propertyName] = newValue;
- }
- }
- }, {
- key: 'connectedCallback',
- value: function connectedCallback() {
- if (_get(AttributeMarshalling.prototype.__proto__ || Object.getPrototypeOf(AttributeMarshalling.prototype), 'connectedCallback', this)) {
- _get(AttributeMarshalling.prototype.__proto__ || Object.getPrototypeOf(AttributeMarshalling.prototype), 'connectedCallback', this).call(this);
- }
- _safeAttributes2.default.connected(this);
- }
- }, {
- key: 'reflectAttribute',
-
-
- /**
- * Set/unset the attribute with the indicated name.
- *
- * This method exists primarily to handle the case where an element wants to
- * set a default property value that should be reflected as an attribute. An
- * important limitation of custom element consturctors is that they cannot
- * set attributes. A call to `reflectAttribute` during the constructor will
- * be deferred until the element is connected to the document.
- *
- * @param {string} attribute - The name of the *attribute* (not property) to set.
- * @param {object} value - The value to set. If null, the attribute will be removed.
- */
- value: function reflectAttribute(attribute, value) {
- return _safeAttributes2.default.setAttribute(this, attribute, value);
- }
-
- /**
- * Set/unset the class with the indicated name.
- *
- * This method exists primarily to handle the case where an element wants to
- * set a default property value that should be reflected as as class. An
- * important limitation of custom element consturctors is that they cannot
- * set attributes, including the `class` attribute. A call to
- * `reflectClass` during the constructor will be deferred until the element
- * is connected to the document.
- *
- * @param {string} className - The name of the class to set.
- * @param {object} value - True to set the class, false to remove it.
- */
-
- }, {
- key: 'reflectClass',
- value: function reflectClass(className, value) {
- return _safeAttributes2.default.toggleClass(this, className, value);
- }
- }], [{
- key: 'observedAttributes',
- get: function get() {
- return attributesForClass(this);
- }
- }]);
-
- return AttributeMarshalling;
- }(base);
-
- return AttributeMarshalling;
-};
-
-// Convert hyphenated foo-bar attribute name to camel case fooBar property name.
-
-
-function attributeToPropertyName(attributeName) {
- var propertyName = attributeToPropertyNames[attributeName];
- if (!propertyName) {
- // Convert and memoize.
- var hypenRegEx = /-([a-z])/g;
- propertyName = attributeName.replace(hypenRegEx, function (match) {
- return match[1].toUpperCase();
- });
- attributeToPropertyNames[attributeName] = propertyName;
- }
- return propertyName;
-}
-
-function attributesForClass(classFn) {
-
- // We treat the element base classes as if they have no attributes, since we
- // don't want to receive attributeChangedCallback for them.
- if (classFn === HTMLElement || classFn === Object) {
- return [];
- }
-
- // Get attributes for parent class.
- var baseClass = Object.getPrototypeOf(classFn.prototype).constructor;
- var baseAttributes = attributesForClass(baseClass);
-
- // Get attributes for this class.
- var propertyNames = Object.getOwnPropertyNames(classFn.prototype);
- var setterNames = propertyNames.filter(function (propertyName) {
- return typeof Object.getOwnPropertyDescriptor(classFn.prototype, propertyName).set === 'function';
- });
- var attributes = setterNames.map(function (setterName) {
- return propertyNameToAttribute(setterName);
- });
-
- // Merge.
- var diff = attributes.filter(function (attribute) {
- return baseAttributes.indexOf(attribute) < 0;
- });
- return baseAttributes.concat(diff);
-}
-
-// Convert a camel case fooBar property name to a hyphenated foo-bar attribute.
-function propertyNameToAttribute(propertyName) {
- var attribute = propertyNamesToAttributes[propertyName];
- if (!attribute) {
- // Convert and memoize.
- var uppercaseRegEx = /([A-Z])/g;
- attribute = propertyName.replace(uppercaseRegEx, '-$1').toLowerCase();
- }
- return attribute;
-}
-
-},{"./safeAttributes":16}],2:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-/* Exported function extends a base class with Composable. */
-exports.default = function (base) {
-
- /**
- * Mixin to make a class more easily composable with other mixins.
- *
- * This mixin contributes a `compose` method that applies a set of mixin
- * functions and returns the resulting new class. This sugar can make the
- * application of many mixins at once easier to read.
- */
- var Composable = function (_base) {
- _inherits(Composable, _base);
-
- function Composable() {
- _classCallCheck(this, Composable);
-
- return _possibleConstructorReturn(this, (Composable.__proto__ || Object.getPrototypeOf(Composable)).apply(this, arguments));
- }
-
- _createClass(Composable, null, [{
- key: 'compose',
-
-
- /**
- * Apply a set of mixin functions or mixin objects to the present class and
- * return the new class.
- *
- * Instead of writing:
- *
- * let MyClass = Mixin1(Mixin2(Mixin3(Mixin4(Mixin5(BaseClass)))));
- *
- * You can write:
- *
- * let MyClass = ComposableMixin(BaseClass).compose(
- * Mixin1,
- * Mixin2,
- * Mixin3,
- * Mixin4,
- * Mixin5
- * );
- *
- * This function can also take mixin objects. A mixin object is just a
- * shorthand for a mixin function that creates a new subclass with the given
- * members. The mixin object's members are *not* copied directly onto the
- * prototype of the base class, as with traditional mixins.
- *
- * In addition to providing syntactic sugar, this mixin can be used to
- * define a class in ES5, which lacks ES6's `class` keyword.
- *
- * @param {...mixins} mixins - A set of mixin functions or objects to apply.
- */
- value: function compose() {
- for (var _len = arguments.length, mixins = Array(_len), _key = 0; _key < _len; _key++) {
- mixins[_key] = arguments[_key];
- }
-
- // We create a new subclass for each mixin in turn. The result becomes
- // the base class extended by any subsequent mixins. It turns out that
- // we can use Array.reduce() to concisely express this, using the current
- // object as the seed for reduce().
- return mixins.reduce(composeClass, this);
- }
- }]);
-
- return Composable;
- }(base);
-
- return Composable;
-};
-
-// Properties defined by Object that we don't want to mixin.
-
-
-var NON_MIXABLE_OBJECT_PROPERTIES = ['constructor'];
-
-/*
- * Apply the mixin to the given base class to return a new class.
- * The mixin can either be a function that returns the modified class, or a
- * plain object whose members will be copied to the new class' prototype.
- */
-function composeClass(base, mixin) {
- if (typeof mixin === 'function') {
- // Mixin function
- return mixin(base);
- } else {
- // Mixin object
- var Subclass = function (_base2) {
- _inherits(Subclass, _base2);
-
- function Subclass() {
- _classCallCheck(this, Subclass);
-
- return _possibleConstructorReturn(this, (Subclass.__proto__ || Object.getPrototypeOf(Subclass)).apply(this, arguments));
- }
-
- return Subclass;
- }(base);
-
- copyOwnProperties(mixin, Subclass.prototype, NON_MIXABLE_OBJECT_PROPERTIES);
- return Subclass;
- }
-}
-
-/*
- * Copy the given properties/methods to the target.
- * Return the updated target.
- */
-function copyOwnProperties(source, target) {
- var ignorePropertyNames = arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : [];
-
- Object.getOwnPropertyNames(source).forEach(function (name) {
- if (ignorePropertyNames.indexOf(name) < 0) {
- var descriptor = Object.getOwnPropertyDescriptor(source, name);
- Object.defineProperty(target, name, descriptor);
- }
- });
- return target;
-}
-
-},{}],3:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
-
-var _get = function get(object, property, receiver) { if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { return get(parent, property, receiver); } } else if ("value" in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } };
-
-var _createSymbol = require('./createSymbol');
-
-var _createSymbol2 = _interopRequireDefault(_createSymbol);
-
-var _toggleClass = require('./toggleClass');
-
-var _toggleClass2 = _interopRequireDefault(_toggleClass);
-
-var _symbols = require('./symbols');
-
-var _symbols2 = _interopRequireDefault(_symbols);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-// Symbols for private data members on an element.
-var itemsSymbol = (0, _createSymbol2.default)('items');
-var itemInitializedSymbol = (0, _createSymbol2.default)('itemInitialized');
-
-/* Exported function extends a base class with ContentItems. */
-
-exports.default = function (base) {
-
- /**
- * Mixin which maps content semantics (elements) to list item semantics.
- *
- * Items differ from element contents in several ways:
- *
- * * They are often referenced via index.
- * * They may have a selection state.
- * * It's common to do work to initialize the appearance or state of a new
- * item.
- * * Auxiliary invisible child elements are filtered out and not counted as
- * items. Auxiliary elements include link, script, style, and template
- * elements. This filtering ensures that those auxiliary elements can be
- * used in markup inside of a list without being treated as list items.
- *
- * This mixin expects a component to provide a `content` property returning a
- * raw set of elements. You can provide that yourself, or use
- * [DistributedChildrenContentMixin](DistributedChildrenContentMixin.md).
- *
- * The most commonly referenced property defined by this mixin is the `items`
- * property. To avoid having to do work each time that property is requested,
- * this mixin supports an optimized mode. If you invoke the `contentChanged`
- * method when the set of items changes, the mixin concludes that you'll take
- * care of notifying it of future changes, and turns on the optimization. With
- * that on, the mixin saves a reference to the computed set of items, and will
- * return that immediately on subsequent calls to the `items` property. If you
- * use this mixin in conjunction with
- * [DistributedChildrenContentMixin](DistributedChildrenContentMixin.md), the
- * `contentChanged` method will be invoked for you when the element's children
- * change, turning on the optimization automatically.
- */
- var ContentItems = function (_base) {
- _inherits(ContentItems, _base);
-
- function ContentItems() {
- _classCallCheck(this, ContentItems);
-
- return _possibleConstructorReturn(this, (ContentItems.__proto__ || Object.getPrototypeOf(ContentItems)).apply(this, arguments));
- }
-
- _createClass(ContentItems, [{
- key: 'contentChanged',
- value: function contentChanged() {
- if (_get(ContentItems.prototype.__proto__ || Object.getPrototypeOf(ContentItems.prototype), 'contentChanged', this)) {
- _get(ContentItems.prototype.__proto__ || Object.getPrototypeOf(ContentItems.prototype), 'contentChanged', this).call(this);
- }
-
- // Since we got the contentChanged call, we'll assume we'll be notified if
- // the set of items changes later. We turn on memoization of the items
- // property by setting our internal property to null (instead of
- // undefined).
- this[itemsSymbol] = null;
-
- this[_symbols2.default.itemsChanged]();
- }
-
- /**
- * This method is invoked whenever a new item is added to the list.
- *
- * The default implementation of this method does nothing. You can override
- * this to perform per-item initialization.
- *
- * @param {HTMLElement} item - The item that was added.
- */
-
- }, {
- key: _symbols2.default.itemAdded,
- value: function value(item) {
- if (_get(ContentItems.prototype.__proto__ || Object.getPrototypeOf(ContentItems.prototype), _symbols2.default.itemAdded, this)) {
- _get(ContentItems.prototype.__proto__ || Object.getPrototypeOf(ContentItems.prototype), _symbols2.default.itemAdded, this).call(this, item);
- }
- }
-
- /**
- * The selection state for a single item has changed.
- *
- * Invoke this method to signal that the selected state of the indicated item
- * has changed. By default, this applies a `selected` CSS class if the item
- * is selected, and removed it if not selected.
- *
- * @param {HTMLElement} item - The item whose selection state has changed.
- * @param {boolean} selected - True if the item is selected, false if not.
- */
-
- }, {
- key: _symbols2.default.itemSelected,
- value: function value(item, selected) {
- if (_get(ContentItems.prototype.__proto__ || Object.getPrototypeOf(ContentItems.prototype), _symbols2.default.itemSelected, this)) {
- _get(ContentItems.prototype.__proto__ || Object.getPrototypeOf(ContentItems.prototype), _symbols2.default.itemSelected, this).call(this, item, selected);
- }
- (0, _toggleClass2.default)(item, 'selected', selected);
- }
-
- /**
- * The current set of items in the list. See the top-level documentation for
- * mixin for a description of how items differ from plain content.
- *
- * @type {HTMLElement[]}
- */
-
- }, {
- key: _symbols2.default.itemsChanged,
-
-
- /**
- * This method is invoked when the underlying contents change. It is also
- * invoked on component initialization – since the items have "changed" from
- * being nothing.
- */
- value: function value() {
- var _this2 = this;
-
- if (_get(ContentItems.prototype.__proto__ || Object.getPrototypeOf(ContentItems.prototype), _symbols2.default.itemsChanged, this)) {
- _get(ContentItems.prototype.__proto__ || Object.getPrototypeOf(ContentItems.prototype), _symbols2.default.itemsChanged, this).call(this);
- }
-
- // Perform per-item initialization.
- Array.prototype.forEach.call(this.items, function (item) {
- if (!item[itemInitializedSymbol]) {
- _this2[_symbols2.default.itemAdded](item);
- item[itemInitializedSymbol] = true;
- }
- });
-
- this.dispatchEvent(new CustomEvent('items-changed'));
- }
-
- /**
- * Fires when the items in the list change.
- *
- * @memberof ContentItems
- * @event items-changed
- */
-
- }, {
- key: 'items',
- get: function get() {
- var items = void 0;
- if (this[itemsSymbol] == null) {
- items = filterAuxiliaryElements(this.content);
- // Note: test for *equality* with null; don't treat undefined as a match.
- if (this[itemsSymbol] === null) {
- // Memoize the set of items.
- this[itemsSymbol] = items;
- }
- } else {
- // Return the memoized items.
- items = this[itemsSymbol];
- }
- return items;
- }
- }]);
-
- return ContentItems;
- }(base);
-
- return ContentItems;
-};
-
-// Return the given elements, filtering out auxiliary elements that aren't
-// typically visible. Items which are not elements are returned as is.
-
-
-function filterAuxiliaryElements(items) {
- var auxiliaryTags = ['link', 'script', 'style', 'template'];
- return [].filter.call(items, function (item) {
- return !item.localName || auxiliaryTags.indexOf(item.localName) < 0;
- });
-}
-
-},{"./createSymbol":14,"./symbols":17,"./toggleClass":18}],4:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
-
-var _set = function set(object, property, value, receiver) { var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent !== null) { set(parent, property, value, receiver); } } else if ("value" in desc && desc.writable) { desc.value = value; } else { var setter = desc.set; if (setter !== undefined) { setter.call(receiver, value); } } return value; };
-
-var _get = function get(object, property, receiver) { if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { return get(parent, property, receiver); } } else if ("value" in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } };
-
-var _microtask = require('./microtask');
-
-var _microtask2 = _interopRequireDefault(_microtask);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-/* Exported function extends a base class with DistributedChildrenContent. */
-exports.default = function (base) {
-
- /**
- * Mixin which defines a component's content as its children, expanding any
- * nodes distributed to the component's slots.
- *
- * This also provides notification of changes to a component's content. It
- * will invoke a `contentChanged` method when the component is first
- * instantiated, and whenever its distributed children change. This is an
- * easy way to satisfy the Gold Standard checklist item for monitoring
- * [Content Changes](https://github.com/webcomponents/gold-standard/wiki/Content-Changes).
- *
- * Example:
- *
- * ```
- * let base = DistributedChildrenContentMixin(DistributedChildrenMixin(HTMLElement));
- * class CountingElement extends base {
- *
- * constructor() {
- * super();
- * let root = this.attachShadow({ mode: 'open' });
- * root.innerHTML = ` `;
- * }
- *
- * contentChanged() {
- * // Count the component's children, both initially and when changed.
- * this.count = this.distributedChildren.length;
- * }
- *
- * }
- * ```
- *
- * Note that content change detection depends upon the element having at least
- * one `slot` element in its shadow subtree.
- *
- * This mixin is intended for use with the
- * [DistributedChildrenMixin](DistributedChildrenMixin.md). See that mixin for
- * a discussion of how that works. This DistributedChildrenContentMixin
- * provides an easy way of defining the "content" of a component as the
- * component's distributed children. That in turn lets mixins like
- * [ContentItemsMixin](ContentItemsMixin.md) manipulate the children as list
- * items.
- */
- var DistributedChildrenContent = function (_base) {
- _inherits(DistributedChildrenContent, _base);
-
- function DistributedChildrenContent() {
- _classCallCheck(this, DistributedChildrenContent);
-
- var _this = _possibleConstructorReturn(this, (DistributedChildrenContent.__proto__ || Object.getPrototypeOf(DistributedChildrenContent)).call(this));
-
- if (_this.shadowRoot) {
- // Listen to changes on all slots.
- var slots = _this.shadowRoot.querySelectorAll('slot');
- slots.forEach(function (slot) {
- return slot.addEventListener('slotchange', function (event) {
- _this.contentChanged();
- });
- });
- }
-
- // Make an initial call to contentChanged() so that the component can do
- // initialization that it normally does when content changes.
- //
- // This will invoke contentChanged() handlers in other mixins. In order
- // that those mixins have a chance to complete their own initialization,
- // we add the contentChanged() call to the microtask queue.
- (0, _microtask2.default)(function () {
- return _this.contentChanged();
- });
- return _this;
- }
-
- /**
- * Invoked when the contents of the component (including distributed
- * children) have changed.
- *
- * This method is also invoked when a component is first instantiated; the
- * contents have essentially "changed" from being nothing. This allows the
- * component to perform initial processing of its children.
- */
-
-
- _createClass(DistributedChildrenContent, [{
- key: 'contentChanged',
- value: function contentChanged() {
- if (_get(DistributedChildrenContent.prototype.__proto__ || Object.getPrototypeOf(DistributedChildrenContent.prototype), 'contentChanged', this)) {
- _get(DistributedChildrenContent.prototype.__proto__ || Object.getPrototypeOf(DistributedChildrenContent.prototype), 'contentChanged', this).call(this);
- }
- var event = new CustomEvent('content-changed');
- this.dispatchEvent(event);
- }
-
- /**
- * The content of this component, defined to be the flattened array of
- * children distributed to the component.
- *
- * @type {HTMLElement[]}
- */
-
- }, {
- key: 'content',
- get: function get() {
- var distributedChildren = this.distributedChildren;
- if (typeof distributedChildren === 'undefined') {
- console.warn('DistributedChildrenContentMixin expects the component to define a "distributedChildren" property.');
- }
- return distributedChildren;
- },
- set: function set(value) {
- if ('content' in base.prototype) {
- _set(DistributedChildrenContent.prototype.__proto__ || Object.getPrototypeOf(DistributedChildrenContent.prototype), 'content', value, this);
- }
- // TODO: Set the children to the given value (which should be an array of
- // elements)?
- }
-
- /**
- * This event is raised when the component's contents (including distributed
- * children) have changed.
- *
- * @memberof DistributedChildrenContent
- * @event content-changed
- */
-
- }]);
-
- return DistributedChildrenContent;
- }(base);
-
- return DistributedChildrenContent;
-};
-
-},{"./microtask":15}],5:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
-
-function _toConsumableArray(arr) { if (Array.isArray(arr)) { for (var i = 0, arr2 = Array(arr.length); i < arr.length; i++) { arr2[i] = arr[i]; } return arr2; } else { return Array.from(arr); } }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-/* Exported function extends a base class with DistributedChildren. */
-exports.default = function (base) {
-
- /**
- * Mixin which defines helpers for accessing a component's distributed
- * children as a flattened array or string.
- *
- * The standard DOM API provides several ways of accessing child content:
- * `children`, `childNodes`, and `textContent`. None of these functions are
- * Shadow DOM aware. This mixin defines variations of those functions that
- * *are* Shadow DOM aware.
- *
- * Example: you create a component `` that displays a number
- * equal to the number of children placed inside that component. If someone
- * instantiates your component like:
- *
- *
- *
- *
- *
- *
- *
- * Then the component should show "3", because there are three children. To
- * calculate the number of children, the component can just calculate
- * `this.children.length`. However, suppose someone instantiates your
- * component inside one of their own components, and puts a `` element
- * inside your component:
- *
- *
- *
- *
- *
- * If your component only looks at `this.children`, it will always see exactly
- * one child — the `` element. But the user looking at the page will
- * *see* any nodes distributed to that slot. To match what the user sees, your
- * component should expand any `` elements it contains.
- *
- * That is the problem this mixin solves. After applying this mixin, your
- * component code has access to `this.distributedChildren`, whose `length`
- * will return the total number of all children distributed to your component
- * in the composed tree.
- *
- * Note: The latest Custom Elements API design calls for a new function,
- * `getAssignedNodes` that takes an optional `deep` parameter, that will solve
- * this problem at the API level.
- */
- var DistributedChildren = function (_base) {
- _inherits(DistributedChildren, _base);
-
- function DistributedChildren() {
- _classCallCheck(this, DistributedChildren);
-
- return _possibleConstructorReturn(this, (DistributedChildren.__proto__ || Object.getPrototypeOf(DistributedChildren)).apply(this, arguments));
- }
-
- _createClass(DistributedChildren, [{
- key: 'distributedChildren',
-
-
- /**
- * An in-order collection of distributed children, expanding any slot
- * elements. Like the standard children property, this skips text nodes.
- *
- * @type {HTMLElement[]}
- */
- get: function get() {
- return expandContentElements(this.children, false);
- }
-
- /**
- * An in-order collection of distributed child nodes, expanding any slot
- * elements. Like the standard childNodes property, this includes text
- * nodes.
- *
- * @type {Node[]}
- */
-
- }, {
- key: 'distributedChildNodes',
- get: function get() {
- return expandContentElements(this.childNodes, true);
- }
-
- /**
- * The concatenated text content of all distributed child nodes, expanding
- * any slot elements.
- *
- * @type {string}
- */
-
- }, {
- key: 'distributedTextContent',
- get: function get() {
- var strings = this.distributedChildNodes.map(function (child) {
- return child.textContent;
- });
- return strings.join('');
- }
- }]);
-
- return DistributedChildren;
- }(base);
-
- return DistributedChildren;
-};
-
-/*
- * Given a array of nodes, return a new array with any content elements expanded
- * to the nodes distributed to that content element. This rule is applied
- * recursively.
- *
- * If includeTextNodes is true, text nodes will be included, as in the
- * standard childNodes property; by default, this skips text nodes, like the
- * standard children property.
- */
-
-
-function expandContentElements(nodes, includeTextNodes) {
- var _ref;
-
- var expanded = Array.prototype.map.call(nodes, function (node) {
- // We want to see if the node is an instanceof HTMLSlotELement, but
- // that class won't exist if the browser that doesn't support native
- // Shadow DOM and if the Shadow DOM polyfill hasn't been loaded. Instead,
- // we do a simplistic check to see if the tag name is "slot".
- var isSlot = typeof HTMLSlotElement !== 'undefined' ? node instanceof HTMLSlotElement : node.localName === 'slot';
- if (isSlot) {
- // Use the nodes assigned to this node instead.
- var assignedNodes = node.assignedNodes({ flatten: true });
- return assignedNodes ? expandContentElements(assignedNodes, includeTextNodes) : [];
- } else if (node instanceof HTMLElement) {
- // Plain element; use as is.
- return [node];
- } else if (node instanceof Text && includeTextNodes) {
- // Text node.
- return [node];
- } else {
- // Comment, processing instruction, etc.; skip.
- return [];
- }
- });
- var flattened = (_ref = []).concat.apply(_ref, _toConsumableArray(expanded));
- return flattened;
-}
-
-},{}],6:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
-
-var _set = function set(object, property, value, receiver) { var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent !== null) { set(parent, property, value, receiver); } } else if ("value" in desc && desc.writable) { desc.value = value; } else { var setter = desc.set; if (setter !== undefined) { setter.call(receiver, value); } } return value; };
-
-var _get = function get(object, property, receiver) { if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { return get(parent, property, receiver); } } else if ("value" in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } };
-
-exports.default = mixin;
-
-var _createSymbol = require('./createSymbol');
-
-var _createSymbol2 = _interopRequireDefault(_createSymbol);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-// Symbols for private data members on an element.
-var selectedFractionSymbol = (0, _createSymbol2.default)('selectedFraction');
-
-/* Exported function extends a base class with FractionalSelection. */
-function mixin(base) {
-
- /**
- * Adds support for fractional selection: treating a selection as a real
- * number that combines an integer portion (an index into a list), and a
- * fraction (indicating how far of the way we are to the next or previous
- * item).
- *
- * This is useful in components that support incremental operations during
- * dragging and swiping. Example: a carousel component has several items, and the
- * currently selected item is item 3. The user begins swiping to the left,
- * moving towards selecting item 4. Halfway through this operation, the
- * fractional selection value is 3.5.
- *
- * This value permits communication between mixins like
- * [SwipeDirectionMixin](./SwipeDirectionMixin.md) and
- * [TrackpadDirectionMixin](./TrackpadDirectionMixin.md), which generate
- * fractional selection values, and mixins like
- * [SelectionAnimationMixin](./SelectionAnimationMixin.md), which can render
- * selection at a fractional value.
- */
- var FractionalSelection = function (_base) {
- _inherits(FractionalSelection, _base);
-
- function FractionalSelection() {
- _classCallCheck(this, FractionalSelection);
-
- return _possibleConstructorReturn(this, (FractionalSelection.__proto__ || Object.getPrototypeOf(FractionalSelection)).apply(this, arguments));
- }
-
- _createClass(FractionalSelection, [{
- key: 'connectedCallback',
- value: function connectedCallback() {
- if (_get(FractionalSelection.prototype.__proto__ || Object.getPrototypeOf(FractionalSelection.prototype), 'connectedCallback', this)) {
- _get(FractionalSelection.prototype.__proto__ || Object.getPrototypeOf(FractionalSelection.prototype), 'connectedCallback', this).call(this);
- }
- this.selectedFraction = 0;
- }
-
- /**
- * A fractional value indicating how far the user has currently advanced to
- * the next/previous item. E.g., a `selectedFraction` of 3.5 indicates the
- * user is halfway between items 3 and 4.
- *
- * @type {number}
- */
-
- }, {
- key: 'selectedFraction',
- get: function get() {
- return this[selectedFractionSymbol];
- },
- set: function set(value) {
- this[selectedFractionSymbol] = value;
- if ('selectedFraction' in base.prototype) {
- _set(FractionalSelection.prototype.__proto__ || Object.getPrototypeOf(FractionalSelection.prototype), 'selectedFraction', value, this);
- }
- var event = new CustomEvent('selected-fraction-changed');
- this.dispatchEvent(event);
- }
- }]);
-
- return FractionalSelection;
- }(base);
-
- return FractionalSelection;
-}
-
-mixin.helpers = {
-
- /*
- * Dampen a selection that goes past the beginning or end of a list. This is
- * generally used to produce a visual effect of tension as the user tries to
- * go further in a direction that has no more items.
- *
- * Example: suppose `itemCount` is 5, indicating a list of 5 items. The index of
- * the last item is 4. If the `selection` parameter is 4.5, the user is trying
- * to go past this last item. When a damping function is applied, the resulting
- * value will be less than 4.5 (the actual value will be 4.25). When this
- * selection state is rendered, the user will see that, each unit distance the
- * drag travels has less and less visible effect. This is perceived as tension.
- *
- * @param {number} selection - A real number indicating a selection position
- * @param {number} itemCount - An integer for the number of items in the list
- * @returns {number} A real number representing the damped selection value.
- */
- dampedSelection: function dampedSelection(selection, itemCount) {
- var bound = itemCount - 1;
- var damped = void 0;
- if (selection < 0) {
- // Trying to go past beginning of list. Apply tension from the left edge.
- damped = -mixin.helpers.damping(-selection);
- } else if (selection >= bound) {
- // Trying to go past end of list. Apply tension from the right edge.
- damped = bound + mixin.helpers.damping(selection - bound);
- } else {
- // No damping required.
- damped = selection;
- }
- return damped;
- },
-
-
- /*
- * Calculate damping as a function of the distance past the minimum/maximum
- * values.
- *
- * We want to asymptotically approach an absolute minimum of 1 unit
- * below/above the actual minimum/maximum. This requires calculating a
- * hyperbolic function.
- *
- * See http://www.wolframalpha.com/input/?i=y+%3D+-1%2F%28x%2B1%29+%2B+1
- * for the one we use. The only portion of that function we care about is when
- * x is zero or greater. An important consideration is that the curve be
- * tangent to the diagonal line x=y at (0, 0). This ensures smooth continuity
- * with the normal drag behavior, in which the visible sliding is linear with
- * the distance the touchpoint has been dragged.
- */
- damping: function damping(x) {
- var y = -1 / (x + 1) + 1;
- return y;
- },
-
-
- /*
- * Return the current fractional selection value for the given element.
- *
- * This simply adds the element's `selectedIndex` and `selectedFraction`
- * properties.
- *
- * @param {HTMLElement} element - An element that supports selection
- */
- elementSelection: function elementSelection(element) {
- var selectedIndex = element.selectedIndex;
- if (selectedIndex < 0) {
- // No selection
- return;
- }
- var selectedFraction = element.selectedFraction || 0;
- return selectedIndex + selectedFraction;
- },
-
-
- /*
- * Breaks a fractional selection into its integer and fractional parts.
- *
- * Example: if passed 3.5, this returns { index: 3, fraction: 5 }.
- *
- * @param {number} selection – A real number representing a selection point
- * @returns {object} - An object with an `index` property holding the
- * selection's integer component, and a `fraction` property holding the
- * selection's fractional component.
- */
- selectionParts: function selectionParts(selection) {
- // Stupid IE doesn't have Math.trunc.
- // const index = Math.trunc(selection);
- var index = selection < 0 ? Math.ceil(selection) : Math.floor(selection);
- var fraction = selection - index;
- return { index: index, fraction: fraction };
- },
-
-
- /*
- * Returns a fractional selection point after accounting for wrapping, ensuring
- * that the integer portion of the selection stays between 0 and `itemCount`-1.
- * That is, the integer portion will always be a valid index into the list.
- *
- * Example of wrapping past the end of the list: if `selection` is 5.5 and
- * `itemCount` is 5, this returns 0.5. Example of wrapping past the beginning of
- * the list: if `selection` is 0.5 and `itemCount` is 5, this returns 4.5.
- *
- * @param {number} selection - A real number representing a selection point
- * @param {number} itemCount - The number of items in the list
- * @returns {number} - The result of wrapping the selection point
- */
- wrappedSelection: function wrappedSelection(selection, itemCount) {
- // Handles possibility of negative mod.
- // See http://stackoverflow.com/a/18618250/76472
- return (selection % itemCount + itemCount) % itemCount;
- },
-
-
- /*
- * Return the parts of a selection, first wrapping if necessary.
- *
- * @param {number} selection – A real number representing a selection point
- * @param {number} itemCount - The number of items in the list
- * @param {boolean} wrap – True if the selection should wrap to stay within the
- * list
- * @returns {object} – The parts of the selection, using the same format as
- * `selectionParts`.
- */
- wrappedSelectionParts: function wrappedSelectionParts(selection, itemCount, wrap) {
- if (wrap) {
- selection = mixin.helpers.wrappedSelection(selection, itemCount);
- }
- return mixin.helpers.selectionParts(selection);
- }
-};
-
-},{"./createSymbol":14}],7:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
-
-var _set = function set(object, property, value, receiver) { var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent !== null) { set(parent, property, value, receiver); } } else if ("value" in desc && desc.writable) { desc.value = value; } else { var setter = desc.set; if (setter !== undefined) { setter.call(receiver, value); } } return value; };
-
-var _get = function get(object, property, receiver) { if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { return get(parent, property, receiver); } } else if ("value" in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } };
-
-var _safeAttributes = require('../../basic-component-mixins/src/safeAttributes');
-
-var _safeAttributes2 = _interopRequireDefault(_safeAttributes);
-
-var _symbols = require('../../basic-component-mixins/src/symbols');
-
-var _symbols2 = _interopRequireDefault(_symbols);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-/* Exported function extends a base class with PlayControls. */
-exports.default = function (base) {
-
- /**
- * Template mixin which adds buttons for managing playback of a slideshow,
- * audio playlist, etc.
- *
- * Typical usage:
- *
- * class SlideshowWithControls extends PlayControlsMixin(Slideshow) {}
- * customElements.define('slideshow-with-controls', SlideshowWithControls);
- *
- */
- var PlayControls = function (_base) {
- _inherits(PlayControls, _base);
-
- function PlayControls() {
- _classCallCheck(this, PlayControls);
-
- var _this = _possibleConstructorReturn(this, (PlayControls.__proto__ || Object.getPrototypeOf(PlayControls)).call(this));
-
- _this.$.previousButton.addEventListener('click', function (event) {
- _this.selectPrevious();
- });
- _this.$.playButton.addEventListener('click', function (event) {
- _this.playing = !_this.playing;
- });
- _this.$.nextButton.addEventListener('click', function (event) {
- _this.selectNext();
- });
- return _this;
- }
-
- _createClass(PlayControls, [{
- key: 'connectedCallback',
- value: function connectedCallback() {
- if (_get(PlayControls.prototype.__proto__ || Object.getPrototypeOf(PlayControls.prototype), 'connectedCallback', this)) {
- _get(PlayControls.prototype.__proto__ || Object.getPrototypeOf(PlayControls.prototype), 'connectedCallback', this).call(this);
- }
- _safeAttributes2.default.connected(this);
- }
- }, {
- key: _symbols2.default.keydown,
- value: function value(event) {
- var handled = void 0;
-
- switch (event.keyCode) {
- case 32:
- /* Space */
- this.playing = !this.playing;
- handled = true;
- break;
- }
-
- // Prefer mixin result if it's defined, otherwise use base result.
- return handled || _get(PlayControls.prototype.__proto__ || Object.getPrototypeOf(PlayControls.prototype), _symbols2.default.keydown, this) && _get(PlayControls.prototype.__proto__ || Object.getPrototypeOf(PlayControls.prototype), _symbols2.default.keydown, this).call(this, event);
- }
- }, {
- key: 'playing',
- get: function get() {
- return _get(PlayControls.prototype.__proto__ || Object.getPrototypeOf(PlayControls.prototype), 'playing', this);
- },
- set: function set(value) {
- if ('playing' in base.prototype) {
- _set(PlayControls.prototype.__proto__ || Object.getPrototypeOf(PlayControls.prototype), 'playing', value, this);
- }
- _safeAttributes2.default.toggleClass(this, 'playing', value);
- }
- }, {
- key: _symbols2.default.template,
- get: function get() {
- var baseTemplate = _get(PlayControls.prototype.__proto__ || Object.getPrototypeOf(PlayControls.prototype), _symbols2.default.template, this) || '';
- return '\n \n\n \n\n \n ' + baseTemplate + '\n
\n ';
- }
- }]);
-
- return PlayControls;
- }(base);
-
- return PlayControls;
-};
-
-},{"../../basic-component-mixins/src/safeAttributes":16,"../../basic-component-mixins/src/symbols":17}],8:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
-
-var _set = function set(object, property, value, receiver) { var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent !== null) { set(parent, property, value, receiver); } } else if ("value" in desc && desc.writable) { desc.value = value; } else { var setter = desc.set; if (setter !== undefined) { setter.call(receiver, value); } } return value; };
-
-var _get = function get(object, property, receiver) { if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { return get(parent, property, receiver); } } else if ("value" in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } };
-
-exports.default = mixin;
-
-var _createSymbol = require('./createSymbol');
-
-var _createSymbol2 = _interopRequireDefault(_createSymbol);
-
-var _FractionalSelectionMixin = require('./FractionalSelectionMixin');
-
-var _FractionalSelectionMixin2 = _interopRequireDefault(_FractionalSelectionMixin);
-
-var _symbols = require('./symbols');
-
-var _symbols2 = _interopRequireDefault(_symbols);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-// Symbols for private data members on an element.
-var animationSymbol = (0, _createSymbol2.default)('animation');
-var draggingSymbol = (0, _createSymbol2.default)('dragging');
-var lastAnimationSymbol = (0, _createSymbol2.default)('lastAnimation');
-var playingAnimationSymbol = (0, _createSymbol2.default)('animatingSelection');
-var previousSelectionSymbol = (0, _createSymbol2.default)('previousSelection');
-var selectionAnimationDurationSymbol = (0, _createSymbol2.default)('selectionAnimationDuration');
-var selectionAnimationEffectSymbol = (0, _createSymbol2.default)('selectionAnimationEffect');
-var selectionAnimationKeyframesSymbol = (0, _createSymbol2.default)('selectionAnimationKeyframes');
-var resetAnimationsOnNextRenderSymbol = (0, _createSymbol2.default)('resetAnimationsOnNextRender');
-
-/* Exported function extends a base class with SelectionAnimation. */
-function mixin(base) {
-
- /**
- * Mixin which uses animation to show transitions between selection states.
- *
- * This mixin can be used by components that want to provide visible
- * animations when changing the selection. For example, a carousel component
- * may want to define a sliding animation effect shown when moving between
- * items.
- *
- * The animation is defined by a `selectionAnimationKeyframes` property; see
- * that property for details on how to define these keyframes. This animation
- * will be used in two ways. First, when moving strictly between items, the
- * animation will play smoothly to show the selection changing. Second, the
- * animation can be used to render the selection at a fixed point in the
- * transition between states. E.g., if the user pauses halfway through
- * dragging an element using [SwipeDirectionMixin](SwipeDirectionMixin.md)
- * or [TrackpadDirectionMixin](TrackpadDirectionMixin.md)s, then the selection
- * animation will be shown at the point exactly halfway through.
- *
- * This mixin expects a component to provide an `items` array of all elements
- * in the list, which can be provided via
- * [ContentItemsMixin](ContentItemsMixin.md). This mixin also expects
- * `selectedIndex` and `selectedItem` properties, which can be provided via
- * [SingleSelectionMixin](SingleSelectionMixin.md).
- *
- * This mixin supports a `selectionWraps` property. When true, the user can
- * navigate forward from the last item in the list and wrap around to the
- * first item, or navigate backward from the first item and wrap around to the
- * last item.
- *
- * This mixin uses the Web Animations API. For use on browsers which
- * do not support that API natively, you will need to load the
- * [Web Animations polyfill](https://github.com/web-animations/web-animations-js).
- */
- var SelectionAnimation = function (_base) {
- _inherits(SelectionAnimation, _base);
-
- function SelectionAnimation() {
- _classCallCheck(this, SelectionAnimation);
-
- // Set defaults.
- var _this = _possibleConstructorReturn(this, (SelectionAnimation.__proto__ || Object.getPrototypeOf(SelectionAnimation)).call(this));
-
- if (typeof _this.selectionAnimationDuration === 'undefined') {
- _this.selectionAnimationDuration = _this[_symbols2.default.defaults].selectionAnimationDuration;
- }
- if (typeof _this.selectionAnimationEffect === 'undefined' && _this.selectionAnimationKeyframes == null) {
- _this.selectionAnimationEffect = _this[_symbols2.default.defaults].selectionAnimationEffect;
- }
-
- _this[_symbols2.default.dragging] = false;
- return _this;
- }
-
- _createClass(SelectionAnimation, [{
- key: _symbols2.default.itemAdded,
- value: function value(item) {
- // We mark new items in the list as explicitly visible to ARIA. Otherwise,
- // when an item isn't visible on the screen, ARIA will assume the item is
- // of no interest to the user, and leave it out of the accessibility tree.
- // If the list contains 10 items, but only 3 are visible, a screen reader
- // might then announce the list only has 3 items. To ensure that screen
- // readers and other assistive technologies announce the correct total
- // number of items, we explicitly mark all items as not hidden. This will
- // expose them all in the accessibility tree, even the items which are
- // currently not rendered.
- //
- // TODO: Generally speaking, this entire mixin assumes that the user can
- // navigate through all items in a list. But an app could style an item as
- // display:none or visibility:hidden because the user is not allowed to
- // interact with that item at the moment. Support for this scenario should
- // be added. This would entail changing all locations where a mixin
- // function is counting items, iterating over the (visible) items, and
- // showing or hiding items. Among other things, the code below to make
- // items visible to ARIA would need to discriminate between items which
- // are invisible because of animation state, or invisible because the user
- // shouldn't interact with them.
- item.setAttribute('aria-hidden', false);
- }
- }, {
- key: _symbols2.default.itemsChanged,
- value: function value() {
- if (_get(SelectionAnimation.prototype.__proto__ || Object.getPrototypeOf(SelectionAnimation.prototype), _symbols2.default.itemsChanged, this)) {
- _get(SelectionAnimation.prototype.__proto__ || Object.getPrototypeOf(SelectionAnimation.prototype), _symbols2.default.itemsChanged, this).call(this);
- }
-
- _resetAnimations(this);
-
- // TODO: Also reset our notion of the last rendered selection? This comes
- // up when a DOM removal causes the selected item to change position.
- // this[previousSelectionSymbol] = null;
-
- renderSelection(this);
- }
- }, {
- key: 'resetAnimations',
- value: function resetAnimations() {
- _resetAnimations(this);
- }
-
- /**
- * A fractional value indicating how far the user has currently advanced to
- * the next/previous item. E.g., a `selectedFraction` of 3.5 indicates the
- * user is halfway between items 3 and 4.
- *
- * For more details, see [FractionalSelectionMixin](FractionalSelectionMixin.md)
- * mixin.
- *
- * @type {number}
- */
-
- }, {
- key: _symbols2.default.defaults,
- get: function get() {
- var defaults = _get(SelectionAnimation.prototype.__proto__ || Object.getPrototypeOf(SelectionAnimation.prototype), _symbols2.default.defaults, this) || {};
- defaults.selectionAnimationDuration = 250;
- defaults.selectionAnimationEffect = 'slide';
- return defaults;
- }
-
- /*
- * Provide backing for the dragging property.
- * Also, when a drag begins, reset the animations.
- */
-
- }, {
- key: _symbols2.default.dragging,
- get: function get() {
- return this[draggingSymbol];
- },
- set: function set(value) {
- var previousValue = this[_symbols2.default.dragging];
- this[draggingSymbol] = value;
- if (_symbols2.default.dragging in base.prototype) {
- _set(SelectionAnimation.prototype.__proto__ || Object.getPrototypeOf(SelectionAnimation.prototype), _symbols2.default.dragging, value, this);
- }
- if (value && !previousValue) {
- // Have begun a drag.
- this[resetAnimationsOnNextRenderSymbol] = true;
- }
- }
- }, {
- key: 'selectedFraction',
- get: function get() {
- return _get(SelectionAnimation.prototype.__proto__ || Object.getPrototypeOf(SelectionAnimation.prototype), 'selectedFraction', this) || 0;
- },
- set: function set(value) {
- if ('selectedFraction' in base.prototype) {
- _set(SelectionAnimation.prototype.__proto__ || Object.getPrototypeOf(SelectionAnimation.prototype), 'selectedFraction', value, this);
- }
- renderSelection(this, this.selectedIndex, value);
- }
- }, {
- key: 'selectedIndex',
- get: function get() {
- return _get(SelectionAnimation.prototype.__proto__ || Object.getPrototypeOf(SelectionAnimation.prototype), 'selectedIndex', this);
- },
- set: function set(index) {
- if ('selectedIndex' in base.prototype) {
- _set(SelectionAnimation.prototype.__proto__ || Object.getPrototypeOf(SelectionAnimation.prototype), 'selectedIndex', index, this);
- }
- renderSelection(this, index, 0);
- }
-
- /**
- * The duration of a selection animation in milliseconds.
- *
- * This measures the amount of time required for a selection animation to
- * complete. This number remains constant, even if the number of items being
- * animated increases.
- *
- * The default value is 250 milliseconds (a quarter a second).
- *
- * @type {number}
- * @default 250
- */
-
- }, {
- key: 'selectionAnimationDuration',
- get: function get() {
- return this[selectionAnimationDurationSymbol];
- },
- set: function set(value) {
- this[selectionAnimationDurationSymbol] = value;
- if ('selectionAnimationDuration' in base.prototype) {
- _set(SelectionAnimation.prototype.__proto__ || Object.getPrototypeOf(SelectionAnimation.prototype), 'selectionAnimationDuration', value, this);
- }
- }
-
- /**
- * The name of a standard selection animation effect.
- *
- * This is a shorthand for setting the `selectionAnimationKeyframes`
- * property to standard keyframes. Supported string values:
- *
- * * "crossfade"
- * * "reveal"
- * * "revealWithFade"
- * * "showAdjacent"
- * * "slide"
- * * "slideWithGap"
- *
- * @type {string}
- * @default "slide"
- */
-
- }, {
- key: 'selectionAnimationEffect',
- get: function get() {
- return this[selectionAnimationEffectSymbol];
- },
- set: function set(value) {
- this[selectionAnimationEffectSymbol] = value;
- if ('selectionAnimationEffect' in base.prototype) {
- _set(SelectionAnimation.prototype.__proto__ || Object.getPrototypeOf(SelectionAnimation.prototype), 'selectionAnimationEffect', value, this);
- }
- this.selectionAnimationKeyframes = mixin.standardEffectKeyframes[value];
- }
-
- /**
- * The keyframes that define an animation that plays for an item when moving
- * forward in the sequence.
- *
- * This is an array of CSS rules that will be applied. These are used as
- * [keyframes](http://w3c.github.io/web-animations/#keyframes-section)
- * to animate the item with the
- * [Web Animations API](https://developer.mozilla.org/en-US/docs/Web/API/animation).
- *
- * The animation represents the state of the next item as it moves from
- * completely unselected (offstage, usually right), to selected (center
- * stage), to completely unselected (offstage, usually left). The center time
- * of the animation should correspond to the item's quiscent selected state,
- * typically in the center of the stage and at the item's largest size.
- *
- * The default forward animation is a smooth slide at full size from right to
- * left.
- *
- * When moving the selection backward, this animation is played in reverse.
- *
- * @type {cssRules[]}
- */
-
- }, {
- key: 'selectionAnimationKeyframes',
- get: function get() {
- // Standard animation slides left/right, keeps adjacent items out of view.
- return this[selectionAnimationKeyframesSymbol];
- },
- set: function set(value) {
- this[selectionAnimationKeyframesSymbol] = value;
- if ('selectionAnimationKeyframes' in base.prototype) {
- _set(SelectionAnimation.prototype.__proto__ || Object.getPrototypeOf(SelectionAnimation.prototype), 'selectionAnimationKeyframes', value, this);
- }
- _resetAnimations(this);
- renderSelection(this);
- }
- }, {
- key: 'selectionWraps',
- get: function get() {
- return _get(SelectionAnimation.prototype.__proto__ || Object.getPrototypeOf(SelectionAnimation.prototype), 'selectionWraps', this);
- },
- set: function set(value) {
- if ('selectionWraps' in base.prototype) {
- _set(SelectionAnimation.prototype.__proto__ || Object.getPrototypeOf(SelectionAnimation.prototype), 'selectionWraps', value, this);
- }
- _resetAnimations(this);
- renderSelection(this);
- }
- }]);
-
- return SelectionAnimation;
- }(base);
-
- return SelectionAnimation;
-}
-
-// We expose helpers on the mixin function that we want to be able to unit test.
-// Since these are on the function, not on the class emitted by the function,
-// they don't end up getting exposed on actual element instances.
-mixin.helpers = {
-
- /*
- * Calculate the animation fractions for an element's items at the given
- * selection point. This is used when rendering the element's selection state
- * instantaneously.
- *
- * This function considers the selectedIndex parameter, which can be a whole
- * or fractional number, and determines which items will be visible at that
- * index. This function then calculates a corresponding animation fraction: a
- * number between 0 and 1 indicating how far through the selection animation
- * an item should be shown, or null if the item should not be visible at that
- * selection index. These fractions are returned as an array, where the
- * animation fraction at position N corresponds to how item N should be shown.
- */
- animationFractionsForSelection: function animationFractionsForSelection(element, selection) {
-
- var items = element.items;
- if (!items) {
- return;
- }
-
- var itemCount = items.length;
- var selectionWraps = element.selectionWraps;
-
- return items.map(function (item, itemIndex) {
- // How many steps from the selection point to this item?
- var steps = stepsToIndex(itemCount, selectionWraps, selection, itemIndex);
- // To convert steps to animation fraction:
- // steps animation fraction
- // 1 0 (stage right)
- // 0 0.5 (center stage)
- // -1 1 (stage left)
- var animationFraction = (1 - steps) / 2;
- return animationFraction >= 0 && animationFraction <= 1 ? animationFraction : null; // Outside animation range
- });
- },
-
-
- /*
- * Calculate the animation timings that should be used to smoothly animate the
- * element's items from one selection state to another.
- *
- * This returns an array of timings, where the timing at position N should be
- * used to animate item N. If an item's timing is null, then that item should
- * not take place in the animation, and should be hidden instead.
- */
- effectTimingsForSelectionAnimation: function effectTimingsForSelectionAnimation(element, fromSelection, toSelection) {
-
- var items = element.items;
- if (!items) {
- return;
- }
- var itemCount = items.length;
- var selectionWraps = element.selectionWraps;
- var toIndex = _FractionalSelectionMixin2.default.helpers.wrappedSelectionParts(toSelection, itemCount, selectionWraps).index;
- var totalSteps = stepsToIndex(itemCount, selectionWraps, fromSelection, toSelection);
- var direction = totalSteps >= 0 ? 'normal' : 'reverse';
- var fill = 'both';
- var totalDuration = element.selectionAnimationDuration;
- var stepDuration = totalSteps !== 0 ? totalDuration * 2 / Math.ceil(Math.abs(totalSteps)) : 0; // No steps required, animation will be instantenous.
-
- var timings = items.map(function (item, itemIndex) {
- var steps = stepsToIndex(itemCount, selectionWraps, itemIndex, toSelection);
- // If we include this item in the staggered sequence of animations we're
- // creating, where would the item appear in the sequence?
- var positionInSequence = totalSteps - steps;
- if (totalSteps < 0) {
- positionInSequence = -positionInSequence;
- }
- // So, is this item really included in the sequence?
- if (Math.ceil(positionInSequence) >= 0 && positionInSequence <= Math.abs(totalSteps)) {
- // Note that delay for first item will be negative. That will cause
- // the animation to start halfway through, which is what we want.
- var delay = stepDuration * (positionInSequence - 1) / 2;
- var endDelay = itemIndex === toIndex ? -stepDuration / 2 : // Stop halfway through.
- 0; // Play animation until end.
- return { duration: stepDuration, direction: direction, fill: fill, delay: delay, endDelay: endDelay };
- } else {
- return null;
- }
- });
-
- return timings;
- }
-};
-
-// Keyframes for standard selection animation effects.
-mixin.standardEffectKeyframes = {
-
- // Simple crossfade
- crossfade: [{ opacity: 0 }, { opacity: 1 }, { opacity: 0 }],
-
- // Reveal, as if sliding the top card off a deck of cards
- reveal: [{ transform: 'translateX(0%)', zIndex: 0 }, { transform: 'translateX(0%)', zIndex: 1 }, { transform: 'translateX(-100%)', zIndex: 2 }],
-
- // Google Photos-style reveal-with-fade animation
- revealWithFade: [{ transform: 'translateX(0%) scale(0.75)', opacity: 0, zIndex: 0 }, { transform: 'translateX(0%) scale(1.0)', opacity: 1, zIndex: 1 }, { transform: 'translateX(-100%) scale(1.0)', opacity: 1, zIndex: 2 }],
-
- // Carousel variant with a bit of off-stage elements showing
- showAdjacent: [{ transform: 'translateX(78%) scale(0.7)', zIndex: 0 }, { transform: 'translateX(0%) scale(0.82)', zIndex: 1 }, { transform: 'translateX(-78%) scale(0.7)', zIndex: 0 }],
-
- // Simple slide
- slide: [{ transform: 'translateX(100%)' }, { transform: 'translateX(-100%)' }],
-
- // Slide, with a gap between
- slideWithGap: [{ transform: 'translateX(110%)' }, { transform: 'translateX(-110%)' }]
-
-};
-
-/*
- * Smoothly animate the selection between the indicated "from" and "to"
- * indices. The former can be a fraction, e.g., when the user releases a finger
- * to complete a touch drag, and the selection will snap to the closest whole
- * index.
- */
-function animateSelection(element, fromSelection, toSelection) {
-
- _resetAnimations(element);
-
- // Calculate the animation timings.
- var items = element.items;
- var keyframes = element.selectionAnimationKeyframes;
- element[playingAnimationSymbol] = true;
- var timings = mixin.helpers.effectTimingsForSelectionAnimation(element, fromSelection, toSelection);
-
- // Figure out which item will be the one *after* the one we're selecting.
- var itemCount = items.length;
- var selectionWraps = element.selectionWraps;
- var selectionIndex = _FractionalSelectionMixin2.default.helpers.selectionParts(toSelection, itemCount, selectionWraps).index;
- var totalSteps = stepsToIndex(itemCount, selectionWraps, fromSelection, toSelection);
- var forward = totalSteps >= 0;
- var nextUpIndex = selectionIndex + (forward ? 1 : -1);
- if (selectionWraps) {
- nextUpIndex = _FractionalSelectionMixin2.default.helpers.wrappedSelection(nextUpIndex, itemCount);
- } else if (!isItemIndexInBounds(element, nextUpIndex)) {
- nextUpIndex = null; // At start/end of list; don't have a next item to show.
- }
-
- // Play the animations using those timings.
- var lastAnimationDetails = void 0;
- timings.forEach(function (timing, index) {
- var item = items[index];
- if (timing) {
- showItem(item, true);
- var animation = item.animate(keyframes, timing);
- element[animationSymbol][index] = animation;
- if (index === nextUpIndex) {
- // This item will be animated, so will already be in the desired state
- // after the animation completes.
- nextUpIndex = null;
- }
- if (timing.endDelay !== 0) {
- // This is the animation for the item that will be left selected.
- // We want to clean up when this animation completes.
- lastAnimationDetails = { animation: animation, index: index, timing: timing, forward: forward };
- }
- } else {
- // This item doesn't participate in the animation.
- showItem(item, false);
- }
- });
-
- if (lastAnimationDetails != null) {
- // Arrange for clean-up work to be performed.
- lastAnimationDetails.nextUpIndex = nextUpIndex;
- lastAnimationDetails.animation.onfinish = function (event) {
- return selectionAnimationFinished(element, lastAnimationDetails);
- };
- element[lastAnimationSymbol] = lastAnimationDetails.animation;
- } else {
- // Shouldn't happen -- we should always have at least one animation.
- element[playingAnimationSymbol] = false;
- }
-}
-
-function getAnimationForItemIndex(element, index) {
- if (element[animationSymbol] == null) {
- // Not ready yet;
- return null;
- }
- var animation = element[animationSymbol][index];
- if (!animation) {
- var item = element.items[index];
- animation = item.animate(element.selectionAnimationKeyframes, {
- duration: element.selectionAnimationDuration,
- fill: 'both'
- });
- animation.pause();
- element[animationSymbol][index] = animation;
- }
- return animation;
-}
-
-function isItemIndexInBounds(element, index) {
- return index >= 0 && element.items && index < element.items.length;
-}
-
-/*
- * Render the selection state of the element.
- *
- * This can be used to re-render a previous selection state (if the
- * selectedIndex param is omitted), render the selection instantly at a given
- * whole or fractional selection index, or animate to a given selection index.
- *
- * There are several distinct scenarios we need to cover:
- *
- * 1. Initial positioning, or repositioning after changing a property like
- * selectionAnimationKeyframes that affects rendering.
- * 2. Animate on selectedIndex change. This should override any animation/swipe
- * already in progress.
- * 3. Instantly render the current position of a drag operation in progress.
- * 4. Complete a drag operation. If the drag wasn't far enough to affect
- * selection, we'll just be restoring the selectedFraction to 0.
- *
- * If the list does not wrap, any selection position outside the list's bounds
- * will be damped to produce a visual effect of tension.
- */
-function renderSelection(element) {
- var selectedIndex = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : element.selectedIndex;
- var selectedFraction = arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : element.selectedFraction;
-
- var itemCount = element.items ? element.items.length : 0;
- if (itemCount === 0) {
- // Nothing to render.
- return;
- }
- if (selectedIndex < 0) {
- // TODO: Handle no selection.
- return;
- }
- var selection = selectedIndex + selectedFraction;
- if (element.selectionWraps) {
- // Apply wrapping to ensure consistent representation of selection.
- selection = _FractionalSelectionMixin2.default.helpers.wrappedSelection(selection, itemCount);
- } else {
- // Apply damping if necessary.
- selection = _FractionalSelectionMixin2.default.helpers.dampedSelection(selection, itemCount);
- }
- var previousSelection = element[previousSelectionSymbol];
- // TODO: If an item changes position in the DOM, we end up animating from
- // its old index to its new index, but we really don't want to animate at all.
- if (!element[_symbols2.default.dragging] && previousSelection != null && previousSelection !== selection) {
- // Animate selection from previous state to new state.
- animateSelection(element, previousSelection, selection);
- } else if (selectedFraction === 0 && element[playingAnimationSymbol]) {
- // Already in process of animating to fraction 0. During that process,
- // ignore subsequent attempts to renderSelection to fraction 0.
- return;
- } else {
- // Render current selection state instantly.
- renderSelectionInstantly(element, selection);
- }
- element[previousSelectionSymbol] = selection;
-}
-
-/*
- * Instantly render (don't animate) the element's items at the given whole or
- * fractional selection index.
- */
-function renderSelectionInstantly(element, toSelection) {
- if (element[resetAnimationsOnNextRenderSymbol]) {
- _resetAnimations(element);
- element[resetAnimationsOnNextRenderSymbol] = false;
- }
- var animationFractions = mixin.helpers.animationFractionsForSelection(element, toSelection);
- animationFractions.map(function (animationFraction, index) {
- var item = element.items[index];
- if (animationFraction != null) {
- showItem(item, true);
- setAnimationFraction(element, index, animationFraction);
- } else {
- showItem(item, false);
- }
- });
-}
-
-/*
- * We maintain an array containing an animation per item. This is used for two
- * reasons:
- *
- * * During a drag operation, we want to be able to reuse animations between
- * drag updates.
- * * When a selection animation completes, we need to be able to leave the
- * visibile items in a paused state. Later, we'll want to be able to clean up
- * those animations.
- *
- * Note that this array is sparse: it will only hold up from 0–3 animations at
- * any given point.
- */
-function _resetAnimations(element) {
- var animations = element[animationSymbol];
- if (animations) {
- // Cancel existing animations to remove the effects they're applying.
- animations.forEach(function (animation, index) {
- if (animation) {
- animation.cancel();
- animations[index] = null;
- }
- });
- }
- var itemCount = element.items ? element.items.length : 0;
- if (!animations || animations.length !== itemCount) {
- // Haven't animated before with this number of items; (re)create array.
- element[animationSymbol] = new Array(itemCount);
- }
-}
-
-/*
- * The last animation in our selection animation has completed. Clean up.
- */
-function selectionAnimationFinished(element, details) {
-
- // When the last animation completes, show the next item in the direction
- // we're going. Waiting to that until this point is a bit of a hack to avoid
- // having a next item that's higher in the natural z-order obscure other items
- // during animation.
- var nextUpIndex = details.nextUpIndex;
- if (nextUpIndex != null) {
- if (element[animationSymbol][nextUpIndex]) {
- // Cancel existing selection animation so we can construct a new one.
- element[animationSymbol][nextUpIndex].cancel();
- element[animationSymbol][nextUpIndex] = null;
- }
- var animationFraction = details.forward ? 0 : 1;
- setAnimationFraction(element, nextUpIndex, animationFraction);
- showItem(element.items[nextUpIndex], true);
- }
-
- element[lastAnimationSymbol].onfinish = null;
- element[playingAnimationSymbol] = false;
-}
-
-/*
- * Pause the indicated animation and have it show the animation at the given
- * fraction (between 0 and 1) of the way through the animation.
- */
-function setAnimationFraction(element, itemIndex, fraction) {
- var animation = getAnimationForItemIndex(element, itemIndex);
- if (animation) {
- var duration = element.selectionAnimationDuration;
- if (duration) {
- animation.currentTime = fraction * duration;
- }
- }
-}
-
-function showItem(item, flag) {
- item.style.visibility = flag ? 'visible' : 'hidden';
-}
-
-/*
- * Figure out how many steps it will take to go from fromSelection to
- * toSelection. To go from item 3 to item 4 is one step.
- *
- * If wrapping is allowed, then going from the last item to the first will take
- * one step (forward), and going from the first item to the last will take one
- * step (backward).
- */
-function stepsToIndex(length, allowWrap, fromSelection, toSelection) {
- var steps = toSelection - fromSelection;
- // Wrapping only kicks in when list has more than 1 item.
- if (allowWrap && length > 1) {
- var wrapSteps = length - Math.abs(steps);
- if (wrapSteps <= 1) {
- // Special case
- steps = steps < 0 ? wrapSteps : // Wrap forward from last item to first.
- -wrapSteps; // Wrap backward from first item to last.
- }
- }
- return steps;
-}
-
-},{"./FractionalSelectionMixin":6,"./createSymbol":14,"./symbols":17}],9:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
-
-var _set = function set(object, property, value, receiver) { var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent !== null) { set(parent, property, value, receiver); } } else if ("value" in desc && desc.writable) { desc.value = value; } else { var setter = desc.set; if (setter !== undefined) { setter.call(receiver, value); } } return value; };
-
-var _get = function get(object, property, receiver) { if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { return get(parent, property, receiver); } } else if ("value" in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } };
-
-var _symbols = require('./symbols');
-
-var _symbols2 = _interopRequireDefault(_symbols);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-// Used to assign unique IDs to item elements without IDs.
-var idCount = 0;
-
-/* Exported function extends a base class with SelectionAriaActive. */
-
-exports.default = function (base) {
-
- /**
- * Mixin which treats the selected item in a list as the active item in ARIA
- * accessibility terms.
- *
- * Handling ARIA selection state properly is actually quite complex:
- *
- * * The items in the list need to be indicated as possible items via an ARIA
- * `role` attribute value such as "option".
- * * The selected item need to be marked as selected by setting the item's
- * `aria-selected` attribute to true *and* the other items need be marked as
- * *not* selected by setting `aria-selected` to false.
- * * The outermost element with the keyboard focus needs to have attributes
- * set on it so that the selection is knowable at the list level via the
- * `aria-activedescendant` attribute.
- * * Use of `aria-activedescendant` in turn requires that all items in the
- * list have ID attributes assigned to them.
- *
- * This mixin tries to address all of the above requirements. To that end,
- * this mixin will assign generated IDs to any item that doesn't already have
- * an ID.
- *
- * ARIA relies on elements to provide `role` attributes. This mixin will apply
- * a default role of "listbox" on the outer list if it doesn't already have an
- * explicit role. Similarly, this mixin will apply a default role of "option"
- * to any list item that does not already have a role specified.
- *
- * This mixin expects a set of members that manage the state of the selection:
- * `[symbols.itemSelected]`, `itemAdded`, and `selectedIndex`. You can
- * supply these yourself, or do so via
- * [SingleSelectionMixin](SingleSelectionMixin.md).
- */
- var SelectionAriaActive = function (_base) {
- _inherits(SelectionAriaActive, _base);
-
- function SelectionAriaActive() {
- _classCallCheck(this, SelectionAriaActive);
-
- return _possibleConstructorReturn(this, (SelectionAriaActive.__proto__ || Object.getPrototypeOf(SelectionAriaActive)).apply(this, arguments));
- }
-
- _createClass(SelectionAriaActive, [{
- key: 'connectedCallback',
- value: function connectedCallback() {
- if (_get(SelectionAriaActive.prototype.__proto__ || Object.getPrototypeOf(SelectionAriaActive.prototype), 'connectedCallback', this)) {
- _get(SelectionAriaActive.prototype.__proto__ || Object.getPrototypeOf(SelectionAriaActive.prototype), 'connectedCallback', this).call(this);
- }
- // Set default ARIA role.
- if (this.getAttribute('role') == null && this[_symbols2.default.defaults].role) {
- this.setAttribute('role', this[_symbols2.default.defaults].role);
- }
- }
- }, {
- key: _symbols2.default.itemAdded,
- value: function value(item) {
- if (_get(SelectionAriaActive.prototype.__proto__ || Object.getPrototypeOf(SelectionAriaActive.prototype), _symbols2.default.itemAdded, this)) {
- _get(SelectionAriaActive.prototype.__proto__ || Object.getPrototypeOf(SelectionAriaActive.prototype), _symbols2.default.itemAdded, this).call(this, item);
- }
-
- if (!item.getAttribute('role')) {
- // Assign a default ARIA role.
- item.setAttribute('role', 'option');
- }
-
- // Ensure each item has an ID so we can set aria-activedescendant on the
- // overall list whenever the selection changes.
- //
- // The ID will take the form of a base ID plus a unique integer. The base
- // ID will be incorporate the component's own ID. E.g., if a component has
- // ID "foo", then its items will have IDs that look like "_fooOption1". If
- // the compnent has no ID itself, its items will get IDs that look like
- // "_option1". Item IDs are prefixed with an underscore to differentiate
- // them from manually-assigned IDs, and to minimize the potential for ID
- // conflicts.
- if (!item.id) {
- var baseId = this.id ? "_" + this.id + "Option" : "_option";
- item.id = baseId + idCount++;
- }
- }
- }, {
- key: _symbols2.default.itemSelected,
- value: function value(item, selected) {
- if (_get(SelectionAriaActive.prototype.__proto__ || Object.getPrototypeOf(SelectionAriaActive.prototype), _symbols2.default.itemSelected, this)) {
- _get(SelectionAriaActive.prototype.__proto__ || Object.getPrototypeOf(SelectionAriaActive.prototype), _symbols2.default.itemSelected, this).call(this, item, selected);
- }
- item.setAttribute('aria-selected', selected);
- var itemId = item.id;
- if (itemId && selected) {
- this.setAttribute('aria-activedescendant', itemId);
- }
- }
- }, {
- key: _symbols2.default.defaults,
- get: function get() {
- var defaults = _get(SelectionAriaActive.prototype.__proto__ || Object.getPrototypeOf(SelectionAriaActive.prototype), _symbols2.default.defaults, this) || {};
- defaults.role = 'listbox';
- return defaults;
- }
- }, {
- key: 'selectedItem',
- get: function get() {
- return _get(SelectionAriaActive.prototype.__proto__ || Object.getPrototypeOf(SelectionAriaActive.prototype), 'selectedItem', this);
- },
- set: function set(item) {
- if ('selectedItem' in base.prototype) {
- _set(SelectionAriaActive.prototype.__proto__ || Object.getPrototypeOf(SelectionAriaActive.prototype), 'selectedItem', item, this);
- }
- if (item == null) {
- // Selection was removed.
- this.removeAttribute('aria-activedescendant');
- }
- }
- }]);
-
- return SelectionAriaActive;
- }(base);
-
- return SelectionAriaActive;
-};
-
-},{"./symbols":17}],10:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-/* Exported function extends a base class with ShadowElementReferences. */
-exports.default = function (base) {
-
- /**
- * Mixin to create references to elements in a component's Shadow DOM subtree.
- *
- * This adds a member on the component called `this.$` that can be used to
- * reference shadow elements with IDs. E.g., if component's shadow contains an
- * element ``, then this mixin will create a member
- * `this.$.foo` that points to that button.
- *
- * Such references simplify a component's access to its own elements. In
- * exchange, this mixin trades off a one-time cost of querying all elements in
- * the shadow tree instead of paying an ongoing cost to query for an element
- * each time the component wants to inspect or manipulate it.
- *
- * This mixin expects the component to define a Shadow DOM subtree. You can
- * create that tree yourself, or make use of
- * [ShadowTemplateMixin](ShadowTemplateMixin.md).
- *
- * This mixin is inspired by Polymer's [automatic
- * node finding](https://www.polymer-project.org/1.0/docs/devguide/local-dom.html#node-finding)
- * feature.
- */
- var ShadowElementReferences = function (_base) {
- _inherits(ShadowElementReferences, _base);
-
- function ShadowElementReferences() {
- _classCallCheck(this, ShadowElementReferences);
-
- var _this = _possibleConstructorReturn(this, (ShadowElementReferences.__proto__ || Object.getPrototypeOf(ShadowElementReferences)).call(this));
-
- if (_this.shadowRoot) {
- // Look for elements in the shadow subtree that have id attributes.
- // An alternatively implementation of this mixin would be to just define
- // a this.$ getter that lazily does this search the first time someone
- // tries to access this.$. That might introduce some complexity – if the
- // the tree changed after it was first populated, the result of
- // searching for a node might be somewhat unpredictable.
- _this.$ = {};
- var nodesWithIds = _this.shadowRoot.querySelectorAll('[id]');
- [].forEach.call(nodesWithIds, function (node) {
- var id = node.getAttribute('id');
- _this.$[id] = node;
- });
- }
- return _this;
- }
-
- /**
- * The collection of references to the elements with IDs in a component's
- * Shadow DOM subtree.
- *
- * @type {object}
- * @member $
- */
-
-
- return ShadowElementReferences;
- }(base);
-
- return ShadowElementReferences;
-};
-
-},{}],11:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _symbols = require('../src/symbols');
-
-var _symbols2 = _interopRequireDefault(_symbols);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-/* Exported function extends a base class with ShadowTemplate. */
-exports.default = function (base) {
-
- /**
- * Mixin for stamping a template into a Shadow DOM subtree upon component
- * instantiation.
- *
- * To use this mixin, define a `template` property as a string or HTML
- * `` element:
- *
- * class MyElement extends ShadowTemplateMixin(HTMLElement) {
- * get [symbols.template]() {
- * return `Hello, world .`;
- * }
- * }
- *
- * When your component class is instantiated, a shadow root will be created on
- * the instance, and the contents of the template will be cloned into the
- * shadow root. If your component does not define a `template` property, this
- * mixin has no effect.
- *
- * For the time being, this extension retains support for Shadow DOM v0. That
- * will eventually be deprecated as browsers (and the Shadow DOM polyfill)
- * implement Shadow DOM v1.
- */
- var ShadowTemplate = function (_base) {
- _inherits(ShadowTemplate, _base);
-
- /*
- * If the component defines a template, a shadow root will be created on the
- * component instance, and the template stamped into it.
- */
- function ShadowTemplate() {
- _classCallCheck(this, ShadowTemplate);
-
- var _this = _possibleConstructorReturn(this, (ShadowTemplate.__proto__ || Object.getPrototypeOf(ShadowTemplate)).call(this));
-
- var template = _this[_symbols2.default.template];
- // TODO: Save the processed template with the component's class prototype
- // so it doesn't need to be processed with every instantiation.
- if (template) {
-
- if (typeof template === 'string') {
- // Upgrade plain string to real template.
- template = createTemplateWithInnerHTML(template);
- }
-
- if (window.ShadowDOMPolyfill) {
- shimTemplateStyles(template, _this.localName);
- }
-
- var root = _this.attachShadow({ mode: 'open' });
- var clone = document.importNode(template.content, true);
- root.appendChild(clone);
- }
- return _this;
- }
-
- return ShadowTemplate;
- }(base);
-
- return ShadowTemplate;
-};
-
-// Convert a plain string of HTML into a real template element.
-
-
-function createTemplateWithInnerHTML(innerHTML) {
- var template = document.createElement('template');
- // REVIEW: Is there an easier way to do this?
- // We'd like to just set innerHTML on the template content, but since it's
- // a DocumentFragment, that doesn't work.
- var div = document.createElement('div');
- div.innerHTML = innerHTML;
- while (div.childNodes.length > 0) {
- template.content.appendChild(div.childNodes[0]);
- }
- return template;
-}
-
-// Invoke basic style shimming with ShadowCSS.
-function shimTemplateStyles(template, tag) {
- window.WebComponents.ShadowCSS.shimStyling(template.content, tag);
-}
-
-},{"../src/symbols":17}],12:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
-
-var _get = function get(object, property, receiver) { if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { return get(parent, property, receiver); } } else if ("value" in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } };
-
-var _set = function set(object, property, value, receiver) { var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent !== null) { set(parent, property, value, receiver); } } else if ("value" in desc && desc.writable) { desc.value = value; } else { var setter = desc.set; if (setter !== undefined) { setter.call(receiver, value); } } return value; };
-
-var _createSymbol = require('./createSymbol');
-
-var _createSymbol2 = _interopRequireDefault(_createSymbol);
-
-var _symbols = require('./symbols');
-
-var _symbols2 = _interopRequireDefault(_symbols);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-// Symbols for private data members on an element.
-var canSelectNextSymbol = (0, _createSymbol2.default)('canSelectNext');
-var canSelectPreviousSymbol = (0, _createSymbol2.default)('canSelectPrevious');
-var selectionRequiredSymbol = (0, _createSymbol2.default)('selectionRequired');
-var selectionWrapsSymbol = (0, _createSymbol2.default)('selectionWraps');
-
-// We want to expose both selectedIndex and selectedItem as independent
-// properties but keep them in sync. This allows a component user to reference
-// the selection by whatever means is most natural for their situation.
-//
-// To efficiently keep these properties in sync, we track "external" and
-// "internal" references for each property:
-//
-// The external index or item is the one we report to the outside world when
-// asked for selection. When handling a change to index or item, we update the
-// external reference as soon as possible, so that if anyone immediately asks
-// for the current selection, they will receive a stable answer.
-//
-// The internal index or item tracks whichever index or item last received the
-// full set of processing. Processing includes raising a change event for the
-// new value. Once we've begun that processing, we store the new value as the
-// internal value to indicate we've handled it.
-//
-var externalSelectedIndexSymbol = (0, _createSymbol2.default)('externalSelectedIndex');
-var externalSelectedItemSymbol = (0, _createSymbol2.default)('externalSelectedItem');
-var internalSelectedIndexSymbol = (0, _createSymbol2.default)('internalSelectedIndex');
-var internalSelectedItemSymbol = (0, _createSymbol2.default)('internalSelectedItem');
-
-/* Exported function extends a base class with SingleSelection. */
-
-exports.default = function (base) {
-
- /**
- * Mixin which manages single-selection semantics for items in a list.
- *
- * This mixin expects a component to provide an `items` Array or NodeList of
- * all elements in the list. A standard way to do that with is the
- * [ContentItemsMixin](ContentItemsMixin.md), which takes a component's
- * content (typically its distributed children) as the set of list items; see
- * that mixin for details.
- *
- * This mixin tracks a single selected item in the list, and provides means to
- * get and set that state by item position (`selectedIndex`) or item identity
- * (`selectedItem`). The selection can be moved in the list via the methods
- * `selectFirst`, `selectLast`, `selectNext`, and `selectPrevious`.
- *
- * This mixin does not produce any user-visible effects to represent
- * selection. Other mixins, such as
- * [SelectionAriaActiveMixin](SelectionAriaActiveMixin.md),
- * [SelectionHighlightMixin](SelectionHighlightMixin.md) and
- * [SelectionInViewMixin](SelectionInViewMixin.md), modify the selected item
- * in common ways to let the user know a given item is selected or not
- * selected.
- */
- var SingleSelection = function (_base) {
- _inherits(SingleSelection, _base);
-
- function SingleSelection() {
- _classCallCheck(this, SingleSelection);
-
- // Set defaults.
- var _this = _possibleConstructorReturn(this, (SingleSelection.__proto__ || Object.getPrototypeOf(SingleSelection)).call(this));
-
- if (typeof _this.selectionRequired === 'undefined') {
- _this.selectionRequired = _this[_symbols2.default.defaults].selectionRequired;
- }
- if (typeof _this.selectionWraps === 'undefined') {
- _this.selectionWraps = _this[_symbols2.default.defaults].selectionWraps;
- }
- return _this;
- }
-
- /**
- * True if the selection can be moved to the next item, false if not (the
- * selected item is the last item in the list).
- *
- * @type {boolean}
- */
-
-
- _createClass(SingleSelection, [{
- key: _symbols2.default.itemAdded,
-
-
- /**
- * Handle a new item being added to the list.
- *
- * The default implementation of this method simply sets the item's
- * selection state to false.
- *
- * @param {HTMLElement} item - the item being added
- */
- value: function value(item) {
- if (_get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), _symbols2.default.itemAdded, this)) {
- _get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), _symbols2.default.itemAdded, this).call(this, item);
- }
- this[_symbols2.default.itemSelected](item, item === this.selectedItem);
- }
- }, {
- key: _symbols2.default.itemsChanged,
- value: function value() {
- if (_get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), _symbols2.default.itemsChanged, this)) {
- _get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), _symbols2.default.itemsChanged, this).call(this);
- }
-
- // In case selected item changed position or was removed.
- trackSelectedItem(this);
-
- // In case the change in items affected which navigations are possible.
- updatePossibleNavigations(this);
- }
-
- /**
- * Apply the indicate selection state to the item.
- *
- * The default implementation of this method does nothing. User-visible
- * effects will typically be handled by other mixins.
- *
- * @param {HTMLElement} item - the item being selected/deselected
- * @param {boolean} selected - true if the item is selected, false if not
- */
-
- }, {
- key: _symbols2.default.itemSelected,
- value: function value(item, selected) {
- if (_get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), _symbols2.default.itemSelected, this)) {
- _get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), _symbols2.default.itemSelected, this).call(this, item, selected);
- }
- }
-
- /**
- * The index of the item which is currently selected.
- *
- * A `selectedIndex` of -1 indicates there is no selection. Setting this
- * property to -1 will remove any existing selection.
- *
- * @type {number}
- */
-
- }, {
- key: 'selectFirst',
-
-
- /**
- * Select the first item in the list.
- */
- value: function selectFirst() {
- if (_get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), 'selectFirst', this)) {
- _get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), 'selectFirst', this).call(this);
- }
- return selectIndex(this, 0);
- }
-
- /**
- * True if the list should always have a selection (if it has items).
- *
- * @type {boolean}
- * @default false
- */
-
- }, {
- key: 'selectLast',
-
-
- /**
- * Select the last item in the list.
- */
- value: function selectLast() {
- if (_get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), 'selectLast', this)) {
- _get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), 'selectLast', this).call(this);
- }
- return selectIndex(this, this.items.length - 1);
- }
-
- /**
- * Select the next item in the list.
- */
-
- }, {
- key: 'selectNext',
- value: function selectNext() {
- if (_get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), 'selectNext', this)) {
- _get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), 'selectNext', this).call(this);
- }
- return selectIndex(this, this.selectedIndex + 1);
- }
-
- /**
- * Select the previous item in the list.
- *
- * If the list has no selection, the last item will be selected.
- */
-
- }, {
- key: 'selectPrevious',
- value: function selectPrevious() {
- if (_get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), 'selectPrevious', this)) {
- _get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), 'selectPrevious', this).call(this);
- }
- var newIndex = this.selectedIndex < 0 ? this.items.length - 1 : // No selection yet; select last item.
- this.selectedIndex - 1;
- return selectIndex(this, newIndex);
- }
-
- /**
- * Fires when the selectedItem property changes.
- *
- * @memberof SingleSelection
- * @event selected-item-changed
- * @param {HTMLElement} detail.selectedItem The new selected item.
- * @param {HTMLElement} detail.previousItem The previously selected item.
- */
-
- /**
- * Fires when the selectedIndex property changes.
- *
- * @memberof SingleSelection
- * @event selected-index-changed
- * @param {number} detail.selectedIndex The new selected index.
- */
-
- }, {
- key: 'canSelectNext',
- get: function get() {
- return this[canSelectNextSymbol];
- },
- set: function set(canSelectNext) {
- var previousCanSelectNext = this[canSelectNextSymbol];
- this[canSelectNextSymbol] = canSelectNext;
- if ('canSelectNext' in base.prototype) {
- _set(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), 'canSelectNext', canSelectNext, this);
- }
- if (canSelectNext !== previousCanSelectNext) {
- this.dispatchEvent(new CustomEvent('can-select-next-changed'));
- }
- }
-
- /**
- * True if the selection can be moved to the previous item, false if not
- * (the selected item is the first one in the list).
- *
- * @type {boolean}
- */
-
- }, {
- key: 'canSelectPrevious',
- get: function get() {
- return this[canSelectPreviousSymbol];
- },
- set: function set(canSelectPrevious) {
- var previousCanSelectPrevious = this[canSelectPreviousSymbol];
- this[canSelectPreviousSymbol] = canSelectPrevious;
- if ('canSelectPrevious' in base.prototype) {
- _set(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), 'canSelectPrevious', canSelectPrevious, this);
- }
- if (canSelectPrevious !== previousCanSelectPrevious) {
- this.dispatchEvent(new CustomEvent('can-select-previous-changed'));
- }
- }
- }, {
- key: _symbols2.default.defaults,
- get: function get() {
- var defaults = _get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), _symbols2.default.defaults, this) || {};
- defaults.selectionRequired = false;
- defaults.selectionWraps = false;
- return defaults;
- }
- }, {
- key: 'selectedIndex',
- get: function get() {
- return this[externalSelectedIndexSymbol] != null ? this[externalSelectedIndexSymbol] : -1;
- },
- set: function set(index) {
- // See notes at top about internal vs. external copies of this property.
- var previousSelectedIndex = this[internalSelectedIndexSymbol];
- var item = void 0;
- if (index !== this[externalSelectedIndexSymbol]) {
- // Store the new index and the corresponding item.
- var items = this.items;
- var hasItems = items && items.length > 0;
- if (!(hasItems && index >= 0 && index < items.length)) {
- index = -1; // No item at that index.
- }
- this[externalSelectedIndexSymbol] = index;
- item = hasItems && index >= 0 ? items[index] : null;
- this[externalSelectedItemSymbol] = item;
- } else {
- item = this[externalSelectedItemSymbol];
- }
-
- // Now let super do any work.
- if ('selectedIndex' in base.prototype) {
- _set(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), 'selectedIndex', index, this);
- }
-
- if (index !== previousSelectedIndex) {
- // The selected index changed.
- this[internalSelectedIndexSymbol] = index;
-
- var event = new CustomEvent('selected-index-changed', {
- detail: {
- selectedIndex: index,
- value: index // for Polymer binding. TODO: Verify still necessary
- }
- });
- this.dispatchEvent(event);
- }
-
- if (this[internalSelectedItemSymbol] !== item) {
- // Update selectedItem property so it can have its own effects.
- this.selectedItem = item;
- }
- }
-
- /**
- * The currently selected item, or null if there is no selection.
- *
- * Setting this property to null deselects any currently-selected item.
- * Setting this property to an object that is not in the list has no effect.
- *
- * TODO: Even if selectionRequired, can still explicitly set selectedItem to null.
- * TODO: If selectionRequired, leave selection alone?
- *
- * @type {object}
- */
-
- }, {
- key: 'selectedItem',
- get: function get() {
- return this[externalSelectedItemSymbol] || null;
- },
- set: function set(item) {
- // See notes at top about internal vs. external copies of this property.
- var previousSelectedItem = this[internalSelectedItemSymbol];
- var index = void 0;
- if (item !== this[externalSelectedItemSymbol]) {
- // Store item and look up corresponding index.
- var items = this.items;
- var hasItems = items && items.length > 0;
- index = hasItems ? Array.prototype.indexOf.call(items, item) : -1;
- this[externalSelectedIndexSymbol] = index;
- if (index < 0) {
- item = null; // The indicated item isn't actually in `items`.
- }
- this[externalSelectedItemSymbol] = item;
- } else {
- index = this[externalSelectedIndexSymbol];
- }
-
- // Now let super do any work.
- if ('selectedItem' in base.prototype) {
- _set(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), 'selectedItem', item, this);
- }
-
- if (item !== previousSelectedItem) {
- // The selected item changed.
- this[internalSelectedItemSymbol] = item;
-
- if (previousSelectedItem) {
- // Update selection state of old item.
- this[_symbols2.default.itemSelected](previousSelectedItem, false);
- }
- if (item) {
- // Update selection state to new item.
- this[_symbols2.default.itemSelected](item, true);
- }
-
- updatePossibleNavigations(this);
-
- var event = new CustomEvent('selected-item-changed', {
- detail: {
- selectedItem: item,
- value: item // for Polymer binding
- }
- });
- this.dispatchEvent(event);
- }
-
- if (this[internalSelectedIndexSymbol] !== index) {
- // Update selectedIndex property so it can have its own effects.
- this.selectedIndex = index;
- }
- }
- }, {
- key: 'selectionRequired',
- get: function get() {
- return this[selectionRequiredSymbol];
- },
- set: function set(selectionRequired) {
- this[selectionRequiredSymbol] = selectionRequired;
- if ('selectionRequired' in base.prototype) {
- _set(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), 'selectionRequired', selectionRequired, this);
- }
- trackSelectedItem(this);
- }
-
- /**
- * True if selection navigations wrap from last to first, and vice versa.
- *
- * @type {boolean}
- * @default false
- */
-
- }, {
- key: 'selectionWraps',
- get: function get() {
- return this[selectionWrapsSymbol];
- },
- set: function set(value) {
- this[selectionWrapsSymbol] = String(value) === 'true';
- if ('selectionWraps' in base.prototype) {
- _set(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), 'selectionWraps', value, this);
- }
- updatePossibleNavigations(this);
- }
- }]);
-
- return SingleSelection;
- }(base);
-
- return SingleSelection;
-};
-
-// Ensure the given index is within bounds, and select it if it's not already
-// selected.
-
-
-function selectIndex(element, index) {
- var count = element.items.length;
-
- var boundedIndex = element.selectionWraps ?
- // JavaScript mod doesn't handle negative numbers the way we want to wrap.
- // See http://stackoverflow.com/a/18618250/76472
- (index % count + count) % count :
-
- // Keep index within bounds of array.
- Math.max(Math.min(index, count - 1), 0);
-
- var previousIndex = element.selectedIndex;
- if (previousIndex !== boundedIndex) {
- element.selectedIndex = boundedIndex;
- return true;
- } else {
- return false;
- }
-}
-
-// Following a change in the set of items, or in the value of the
-// `selectionRequired` property, reacquire the selected item. If it's moved,
-// update `selectedIndex`. If it's been removed, and a selection is required,
-// try to select another item.
-function trackSelectedItem(element) {
-
- var items = element.items;
- var itemCount = items ? items.length : 0;
-
- var previousSelectedItem = element.selectedItem;
- if (!previousSelectedItem) {
- // No item was previously selected.
- if (element.selectionRequired) {
- // Select the first item by default.
- element.selectedIndex = 0;
- }
- } else if (itemCount === 0) {
- // We've lost the selection, and there's nothing left to select.
- element.selectedItem = null;
- } else {
- // Try to find the previously-selected item in the current set of items.
- var indexInCurrentItems = Array.prototype.indexOf.call(items, previousSelectedItem);
- var previousSelectedIndex = element.selectedIndex;
- if (indexInCurrentItems < 0) {
- // Previously-selected item was removed from the items.
- // Select the item at the same index (if it exists) or as close as possible.
- var newSelectedIndex = Math.min(previousSelectedIndex, itemCount - 1);
- // Select by item, since index may be the same, and we want to raise the
- // selected-item-changed event.
- element.selectedItem = items[newSelectedIndex];
- } else if (indexInCurrentItems !== previousSelectedIndex) {
- // Previously-selected item still there, but changed position.
- element.selectedIndex = indexInCurrentItems;
- }
- }
-}
-
-// Following a change in selection, report whether it's now possible to
-// go next/previous from the given index.
-function updatePossibleNavigations(element) {
- var canSelectNext = void 0;
- var canSelectPrevious = void 0;
- var items = element.items;
- if (items == null || items.length === 0) {
- // No items to select.
- canSelectNext = false;
- canSelectPrevious = false;
- }if (element.selectionWraps) {
- // Since there are items, can always go next/previous.
- canSelectNext = true;
- canSelectPrevious = true;
- } else {
- var index = element.selectedIndex;
- if (index < 0 && items.length > 0) {
- // Special case. If there are items but no selection, declare that it's
- // always possible to go next/previous to create a selection.
- canSelectNext = true;
- canSelectPrevious = true;
- } else {
- // Normal case: we have an index in a list that has items.
- canSelectPrevious = index > 0;
- canSelectNext = index < items.length - 1;
- }
- }
- if (element.canSelectNext !== canSelectNext) {
- element.canSelectNext = canSelectNext;
- }
- if (element.canSelectPrevious !== canSelectPrevious) {
- element.canSelectPrevious = canSelectPrevious;
- }
-}
-
-},{"./createSymbol":14,"./symbols":17}],13:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
-
-var _set = function set(object, property, value, receiver) { var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent !== null) { set(parent, property, value, receiver); } } else if ("value" in desc && desc.writable) { desc.value = value; } else { var setter = desc.set; if (setter !== undefined) { setter.call(receiver, value); } } return value; };
-
-var _get = function get(object, property, receiver) { if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { return get(parent, property, receiver); } } else if ("value" in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } };
-
-var _createSymbol = require('./createSymbol');
-
-var _createSymbol2 = _interopRequireDefault(_createSymbol);
-
-var _symbols = require('./symbols');
-
-var _symbols2 = _interopRequireDefault(_symbols);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-var playingSymbol = (0, _createSymbol2.default)('playing');
-var selectionTimerDurationSymbol = (0, _createSymbol2.default)('selectionTimerDuration');
-var timerTimeoutSymbol = (0, _createSymbol2.default)('timerTimeout');
-
-/* Exported function extends a base class with TimerSelection. */
-
-exports.default = function (base) {
-
- /**
- * Mixin which provides for automatic timed changes in selection.
- *
- * This mixin is useful for creating slideshow-like elements such as
- * [basic-slideshow](../packages/basic-slideshow) and
- * [basic-slideshow-with-controls](../packages/basic-slideshow-with-controls).
- *
- * Typical usage:
- *
- * class CarouselWithTimer extends TimerSelectionMixin(Carousel) {}
- * customElements.define('carousel-with-arrows', CarouselWithTimer);
- *
- * This mixin expects the component to define an `items` property, as well as
- * `selectFirst` and `selectNext` methods. You can implement those yourself,
- * or use [ContentItemsMixin](ContentItemsMixin.md) and
- * [SingleSelectionMixin](SingleSelectionMixin.md).
- */
- var TimerSelection = function (_base) {
- _inherits(TimerSelection, _base);
-
- function TimerSelection() {
- _classCallCheck(this, TimerSelection);
-
- // Set defaults.
- var _this = _possibleConstructorReturn(this, (TimerSelection.__proto__ || Object.getPrototypeOf(TimerSelection)).call(this));
-
- if (typeof _this.playing === 'undefined') {
- _this.playing = _this[_symbols2.default.defaults].playing;
- }
- if (typeof _this.selectionTimerDuration === 'undefined') {
- _this.selectionTimerDuration = _this[_symbols2.default.defaults].selectionTimerDuration;
- }
- return _this;
- }
-
- _createClass(TimerSelection, [{
- key: 'contentChanged',
- value: function contentChanged() {
- if (_get(TimerSelection.prototype.__proto__ || Object.getPrototypeOf(TimerSelection.prototype), 'contentChanged', this)) {
- _get(TimerSelection.prototype.__proto__ || Object.getPrototypeOf(TimerSelection.prototype), 'contentChanged', this).call(this);
- }
- restartTimer(this);
- }
- }, {
- key: 'play',
-
-
- /**
- * Begin automatic progression of the selection.
- */
- value: function play() {
- if (_get(TimerSelection.prototype.__proto__ || Object.getPrototypeOf(TimerSelection.prototype), 'play', this)) {
- _get(TimerSelection.prototype.__proto__ || Object.getPrototypeOf(TimerSelection.prototype), 'play', this).call(this);
- }
- startTimer(this);
- this[playingSymbol] = true;
- }
-
- /**
- * Pause automatic progression of the selection.
- */
-
- }, {
- key: 'pause',
- value: function pause() {
- if (_get(TimerSelection.prototype.__proto__ || Object.getPrototypeOf(TimerSelection.prototype), 'pause', this)) {
- _get(TimerSelection.prototype.__proto__ || Object.getPrototypeOf(TimerSelection.prototype), 'pause', this).call(this);
- }
- clearTimer(this);
- this[playingSymbol] = false;
- }
-
- /**
- * True if the selection is being automatically advanced.
- *
- * @type {boolean}
- * @default false
- */
-
- }, {
- key: _symbols2.default.defaults,
- get: function get() {
- var defaults = _get(TimerSelection.prototype.__proto__ || Object.getPrototypeOf(TimerSelection.prototype), _symbols2.default.defaults, this) || {};
- defaults.playing = false;
- defaults.selectionTimerDuration = 1000;
- return defaults;
- }
- }, {
- key: 'playing',
- get: function get() {
- return this[playingSymbol];
- },
- set: function set(playing) {
- var previousPlaying = this[playingSymbol];
- var parsed = String(playing) === 'true'; // Cast to boolean
- if ('playing' in base.prototype) {
- _set(TimerSelection.prototype.__proto__ || Object.getPrototypeOf(TimerSelection.prototype), 'playing', playing, this);
- }
- if (parsed !== previousPlaying) {
- if (playing) {
- this.play();
- } else {
- this.pause();
- }
- }
- }
-
- /*
- * When the selected item changes (because of something this mixin did, or
- * was changed by an outside agent like the user), we wait before advancing
- * to the next item. By triggering the next item this way, we implicitly get
- * a desirable behavior: if the user changes the selection (e.g., in a
- * carousel), we let them see that selection state for a while before
- * advancing the selection ourselves.
- */
-
- }, {
- key: 'selectedItem',
- get: function get() {
- return _get(TimerSelection.prototype.__proto__ || Object.getPrototypeOf(TimerSelection.prototype), 'selectedItem', this);
- },
- set: function set(item) {
- if ('selectedItem' in base.prototype) {
- _set(TimerSelection.prototype.__proto__ || Object.getPrototypeOf(TimerSelection.prototype), 'selectedItem', item, this);
- }
- restartTimer(this);
- }
-
- /**
- * The time in milliseconds that will elapse after the selection changes
- * before the selection will be advanced to the next item in the list.
- *
- * @type {number} - Time in milliseconds
- * @default 1000 (1 second)
- */
-
- }, {
- key: 'selectionTimerDuration',
- get: function get() {
- return this[selectionTimerDurationSymbol];
- },
- set: function set(value) {
- this[selectionTimerDurationSymbol] = parseInt(value);
- if ('selectionTimerDuration' in base.prototype) {
- _set(TimerSelection.prototype.__proto__ || Object.getPrototypeOf(TimerSelection.prototype), 'selectionTimerDuration', value, this);
- }
- }
- }]);
-
- return TimerSelection;
- }(base);
-
- return TimerSelection;
-};
-
-function clearTimer(element) {
- if (element[timerTimeoutSymbol]) {
- clearTimeout(element[timerTimeoutSymbol]);
- element[timerTimeoutSymbol] = null;
- }
-}
-
-function restartTimer(element) {
- clearTimer(element);
- if (element.playing && element.items && element.items.length > 0) {
- startTimer(element);
- }
-}
-
-function startTimer(element) {
- // If play() is called more than once, cancel any existing timer.
- clearTimer(element);
- element[timerTimeoutSymbol] = setTimeout(function () {
- selectNextWithWrap(element);
- }, element.selectionTimerDuration);
-}
-
-// Select the next item, wrapping to first item if necessary.
-function selectNextWithWrap(element) {
- var items = element.items;
- if (items && items.length > 0) {
- if (element.selectedIndex == null || element.selectedIndex === items.length - 1) {
- element.selectFirst();
- } else {
- element.selectNext();
- }
- }
-}
-
-},{"./createSymbol":14,"./symbols":17}],14:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-exports.default = createSymbol;
-/**
- * Helper function to create a symbol that can be used for associating private
- * data with an element.
- *
- * Mixins and component classes often want to associate private data with an
- * element instance, but JavaScript does not have direct support for true
- * private properties. One approach is to use the
- * [Symbol](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Symbol)
- * data type to set and retrieve data on an element.
- *
- * Unfortunately, the Symbol type is not available in Internet Explorer 11. The
- * `createSymbol` helper function exists as a workaround for IE 11. Rather than
- * returning a true Symbol, it simply returns an underscore-prefixed string.
- *
- * Usage:
- *
- * const fooSymbol = createSymbol('foo');
- *
- * class MyElement extends HTMLElement {
- * get foo() {
- * return this[fooSymbol];
- * }
- * set foo(value) {
- * this[fooSymbol] = value;
- * }
- * }
- *
- * In IE 11, this sample will "hide" data behind an instance property this._foo.
- * The use of the underscore is meant to reduce (not eliminate) the potential
- * for name conflicts, and discourage (not prevent) external access to this
- * data. In modern browsers, the above code will eliminate the potential of
- * naming conflicts, and better hide the data behind a real Symbol.
- *
- * @function createSymbol
- * @param {string} description - A string to identify the symbol when debugging
- */
-function createSymbol(description) {
- return typeof Symbol === 'function' ? Symbol(description) : '_' + description;
-}
-
-},{}],15:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-exports.default = microtask;
-/*
- * Microtask helper for IE 11.
- *
- * Executing a function as a microtask is trivial in browsers that support
- * promises, whose then() clauses use microtask timing. IE 11 doesn't support
- * promises, but does support MutationObservers, which are also executed as
- * microtasks. So this helper uses an MutationObserver to achieve microtask
- * timing.
- *
- * See https://jakearchibald.com/2015/tasks-microtasks-queues-and-schedules/
- *
- * Inspired by Polymer's async() function.
- */
-
-// The queue of pending callbacks to be executed as microtasks.
-var callbacks = [];
-
-// Create an element that we will modify to force observable mutations.
-var element = document.createTextNode('');
-
-// A monotonically-increasing value.
-var counter = 0;
-
-/**
- * Add a callback to the microtask queue.
- *
- * This uses a MutationObserver so that it works on IE 11.
- *
- * NOTE: IE 11 may actually use timeout timing with MutationObservers. This
- * needs more investigation.
- *
- * @function microtask
- * @param {function} callback
- */
-function microtask(callback) {
- callbacks.push(callback);
- // Force a mutation.
- element.textContent = ++counter;
-}
-
-// Execute any pending callbacks.
-function executeCallbacks() {
- while (callbacks.length > 0) {
- var callback = callbacks.shift();
- callback();
- }
-}
-
-// Create the observer.
-var observer = new MutationObserver(executeCallbacks);
-observer.observe(element, {
- characterData: true
-});
-
-},{}],16:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createSymbol = require('./createSymbol');
-
-var _createSymbol2 = _interopRequireDefault(_createSymbol);
-
-var _toggleClass2 = require('./toggleClass');
-
-var _toggleClass3 = _interopRequireDefault(_toggleClass2);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-// Symbols for private data members on an element.
-var safeToSetAttributesSymbol = (0, _createSymbol2.default)('safeToSetAttributes');
-var pendingAttributesSymbol = (0, _createSymbol2.default)('pendingAttributes');
-var pendingClassesSymbol = (0, _createSymbol2.default)('pendingClasses');
-
-/**
- * Helper functions for updating attributes, including the `class` attribute.
- */
-exports.default = {
-
- /**
- * Perform any pending updates to attributes and classes.
- *
- * This writes any `setAttribute` or `toggleClass` values that were performed
- * before an element was attached to the document for the first time.
- *
- * This method should be called by mixins/components in their
- * `connectedCallback`. If mulitple mixins/components invoke this during the
- * same `connectedCallback`, only the first call will have any effect. The
- * subsequent calls will be harmless.
- *
- * @param {HTMLElement} element - The element being added to the document.
- */
- connected: function connected(element) {
- element[safeToSetAttributesSymbol] = true;
-
- // Set any pending attributes.
- if (element[pendingAttributesSymbol]) {
- for (var attribute in element[pendingAttributesSymbol]) {
- var value = element[pendingAttributesSymbol][attribute];
- setAttributeToElement(element, attribute, value);
- }
- element[pendingAttributesSymbol] = null;
- }
-
- // Set any pending classes.
- if (element[pendingClassesSymbol]) {
- for (var className in element[pendingClassesSymbol]) {
- var _value = element[pendingClassesSymbol][className];
- (0, _toggleClass3.default)(element, className, _value);
- }
- element[pendingClassesSymbol] = null;
- }
- },
-
-
- /**
- * Set/unset the attribute with the indicated name.
- *
- * This method exists primarily to handle the case where an element wants to
- * set a default property value that should be reflected as an attribute. An
- * important limitation of custom element consturctors is that they cannot
- * set attributes. A call to `setAttribute` during the constructor will
- * be deferred until the element is connected to the document.
- *
- * @param {string} attribute - The name of the *attribute* (not property) to set.
- * @param {object} value - The value to set. If null, the attribute will be removed.
- */
- setAttribute: function setAttribute(element, attribute, value) {
- if (element[safeToSetAttributesSymbol]) {
- // Safe to set attributes immediately.
- setAttributeToElement(element, attribute, value);
- } else {
- // Defer setting attributes until the first time we're connected.
- if (!element[pendingAttributesSymbol]) {
- element[pendingAttributesSymbol] = {};
- }
- element[pendingAttributesSymbol][attribute] = value;
- }
- },
-
-
- /**
- * Set/unset the class with the indicated name.
- *
- * This method exists primarily to handle the case where an element wants to
- * set a default property value that should be reflected as as class. An
- * important limitation of custom element consturctors is that they cannot
- * set attributes, including the `class` attribute. A call to
- * `toggleClass` during the constructor will be deferred until the element
- * is connected to the document.
- *
- * @param {string} className - The name of the class to set.
- * @param {object} value - True to set the class, false to remove it.
- */
- toggleClass: function toggleClass(element, className, value) {
- if (element[safeToSetAttributesSymbol]) {
- // Safe to set class immediately.
- (0, _toggleClass3.default)(element, className, value);
- } else {
- // Defer setting class until the first time we're connected.
- if (!element[pendingClassesSymbol]) {
- element[pendingClassesSymbol] = {};
- }
- element[pendingClassesSymbol][className] = value;
- }
- }
-};
-
-// Reflect the attribute to the given element.
-// If the value is null, remove the attribute.
-
-function setAttributeToElement(element, attributeName, value) {
- if (value === null || typeof value === 'undefined') {
- element.removeAttribute(attributeName);
- } else {
- var text = String(value);
- // Avoid recursive attributeChangedCallback calls.
- if (element.getAttribute(attributeName) !== text) {
- element.setAttribute(attributeName, value);
- }
- }
-}
-
-},{"./createSymbol":14,"./toggleClass":18}],17:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createSymbol = require('./createSymbol');
-
-var _createSymbol2 = _interopRequireDefault(_createSymbol);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-/**
- * A collection of Symbol objects for standard component properties and methods.
- *
- * These Symbol objects are used to allow mixins and a component to internally
- * communicate, without exposing these properties and methods in the component's
- * public API.
- *
- * To use these Symbol objects in your own component, include this module and
- * then create a property or method whose key is the desired Symbol.
- *
- * import 'SingleSelectionMixin' from 'basic-component-mixins/src/SingleSelectionMixin';
- * import 'symbols' from 'basic-component-mixins/src/symbols';
- *
- * class MyElement extends SingleSelectionMixin(HTMLElement) {
- * [symbols.itemSelected](item, selected) {
- * // This will be invoked whenever an item is selected/deselected.
- * }
- * }
- *
- * @module symbols
- */
-var symbols = {
-
- /**
- * Symbol for the `defaults` property.
- *
- * This property can be used to set or override defaults that will be applied
- * to a new component instance. When implementing this property, take care to
- * first acquire any defaults defined by the superclass. The standard idiom is
- * as follows:
- *
- * get [symbols.defaults]() {
- * const defaults = super[symbols.defaults] || {};
- * // Set or override default values here
- * defaults.customProperty = false;
- * return defaults;
- * }
- *
- * @var {object} defaults
- */
- defaults: (0, _createSymbol2.default)('defaults'),
-
- /**
- * Symbol for the `dragging` property.
- *
- * Components like carousels often define animated CSS transitions for
- * sliding effects. Such a transition should usually *not* be applied while
- * the user is dragging, because a CSS animation will introduce a lag that
- * makes the swipe feel sluggish. Instead, as long as the user is dragging
- * with their finger down, the transition should be suppressed. When the
- * user releases their finger, the transition can be restored, allowing the
- * animation to show the carousel sliding into its final position.
- *
- * @type {boolean} true if a drag is in progress, false if not.
- */
- dragging: (0, _createSymbol2.default)('dragging'),
-
- /**
- * Symbol for the `goDown` method.
- *
- * This method is invoked when the user wants to go/navigate down.
- *
- * @function goDown
- */
- goDown: (0, _createSymbol2.default)('goDown'),
-
- /**
- * Symbol for the `goEnd` method.
- *
- * This method is invoked when the user wants to go/navigate to the end (e.g.,
- * of a list).
- *
- * @function goEnd
- */
- goEnd: (0, _createSymbol2.default)('goEnd'),
-
- /**
- * Symbol for the `goLeft` method.
- *
- * This method is invoked when the user wants to go/navigate left.
- *
- * @function goLeft
- */
- goLeft: (0, _createSymbol2.default)('goLeft'),
-
- /**
- * Symbol for the `goRight` method.
- *
- * This method is invoked when the user wants to go/navigate right.
- *
- * @function goRight
- */
- goRight: (0, _createSymbol2.default)('goRight'),
-
- /**
- * Symbol for the `goStart` method.
- *
- * This method is invoked when the user wants to go/navigate to the start
- * (e.g., of a list).
- *
- * @function goStart
- */
- goStart: (0, _createSymbol2.default)('goStart'),
-
- /**
- * Symbol for the `goUp` method.
- *
- * This method is invoked when the user wants to go/navigate up.
- *
- * @function goUp
- */
- goUp: (0, _createSymbol2.default)('goUp'),
-
- /**
- * Symbol for the `itemAdded` method.
- *
- * This method is invoked when a new item is added to a list.
- *
- * @function itemAdded
- * @param {HTMLElement} item - the item being selected/deselected
- */
- itemAdded: (0, _createSymbol2.default)('itemAdded'),
-
- /**
- * Symbol for the `itemsChanged` method.
- *
- * This method is invoked when the underlying contents change. It is also
- * invoked on component initialization – since the items have "changed" from
- * being nothing.
- */
- itemsChanged: (0, _createSymbol2.default)('itemsChanged'),
-
- /**
- * Symbol for the `itemSelected` method.
- *
- * This method is invoked when an item becomes selected or deselected.
- *
- * @function itemSelected
- * @param {HTMLElement} item - the item being selected/deselected
- * @param {boolean} selected - true if the item is selected, false if not
- */
- itemSelected: (0, _createSymbol2.default)('itemSelected'),
-
- /**
- * Symbol for the `keydown` method.
- *
- * This method is invoked when an element receives a `keydown` event.
- *
- * @function keydown
- * @param {KeyboardEvent} event - the event being processed
- */
- keydown: (0, _createSymbol2.default)('keydown'),
-
- /**
- * Symbol for the `template` property.
- *
- * This property returns a component's template.
- *
- * @type {string|HTMLElement}
- */
- template: (0, _createSymbol2.default)('template')
-};
-
-exports.default = symbols;
-
-},{"./createSymbol":14}],18:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-exports.default = toggleClass;
-/**
- * Helper function for standard classList.toggle() behavior on old browsers,
- * namely IE 11.
- *
- * The standard
- * [classlist](https://developer.mozilla.org/en-US/docs/Web/API/Element/classList)
- * object has a `toggle()` function that supports a second Boolean parameter
- * that can be used to succinctly turn a class on or off. This feature is often
- * useful in designing custom elements, which may want to externally reflect
- * component state in a CSS class that can be used for styling purposes.
- *
- * Unfortunately, IE 11 does not support the Boolean parameter to
- * `classList.toggle()`. This helper function behaves like the standard
- * `toggle()`, including support for the Boolean parameter, so that it can be
- * used even on IE 11.
- *
- * @function toggleClass
- * @param {HTMLElement} element - The element to modify
- * @param {string} className - The class to add/remove
- * @param {boolean} [force] - Force the class to be added (if true) or removed
- * (if false)
- */
-function toggleClass(element, className, force) {
- var classList = element.classList;
- var addClass = typeof force === 'undefined' ? !classList.contains(className) : force;
- if (addClass) {
- classList.add(className);
- } else {
- classList.remove(className);
- }
- return addClass;
-}
-
-},{}],19:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _AttributeMarshallingMixin = require('../../basic-component-mixins/src/AttributeMarshallingMixin');
-
-var _AttributeMarshallingMixin2 = _interopRequireDefault(_AttributeMarshallingMixin);
-
-var _ComposableMixin = require('../../basic-component-mixins/src/ComposableMixin');
-
-var _ComposableMixin2 = _interopRequireDefault(_ComposableMixin);
-
-var _DistributedChildrenMixin = require('../../basic-component-mixins/src/DistributedChildrenMixin');
-
-var _DistributedChildrenMixin2 = _interopRequireDefault(_DistributedChildrenMixin);
-
-var _ShadowElementReferencesMixin = require('../../basic-component-mixins/src/ShadowElementReferencesMixin');
-
-var _ShadowElementReferencesMixin2 = _interopRequireDefault(_ShadowElementReferencesMixin);
-
-var _ShadowTemplateMixin = require('../../basic-component-mixins/src/ShadowTemplateMixin');
-
-var _ShadowTemplateMixin2 = _interopRequireDefault(_ShadowTemplateMixin);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-/**
- * A sample general-purpose base class for defining custom elements that mixes
- * in some common features: template stamping into a shadow root, shadow element
- * references, marshalling attributes to properties, and retrieving the children
- * distributed to a component.
- *
- * This base class is not special in any way, and is defined only as a
- * convenient shorthand for applying the mixins listed above. You can use this
- * class as a base class for your own elements, or easily create your own base
- * class by applying the same set of mixins.
- *
- * The ElementBase base class does not register itself as a custom element with
- * the browser, and hence cannot be independently instantiated.
- *
- * @mixes AttributeMarshallingMixin
- * @mixes ComposableMixin
- * @mixes DistributedChildrenMixin
- * @mixes ShadowElementReferencesMixin
- * @mixes ShadowTemplateMixin
- */
-var ElementBase = function (_ComposableMixin$comp) {
- _inherits(ElementBase, _ComposableMixin$comp);
-
- function ElementBase() {
- _classCallCheck(this, ElementBase);
-
- return _possibleConstructorReturn(this, (ElementBase.__proto__ || Object.getPrototypeOf(ElementBase)).apply(this, arguments));
- }
-
- return ElementBase;
-}((0, _ComposableMixin2.default)(HTMLElement).compose(_ShadowTemplateMixin2.default, // before node finding, so shadow root is populated
-_ShadowElementReferencesMixin2.default, // before marshalling, so properties can use refs
-_AttributeMarshallingMixin2.default, _DistributedChildrenMixin2.default));
-
-exports.default = ElementBase;
-
-},{"../../basic-component-mixins/src/AttributeMarshallingMixin":1,"../../basic-component-mixins/src/ComposableMixin":2,"../../basic-component-mixins/src/DistributedChildrenMixin":5,"../../basic-component-mixins/src/ShadowElementReferencesMixin":10,"../../basic-component-mixins/src/ShadowTemplateMixin":11}],20:[function(require,module,exports){
-'use strict';
-
-var _SlideshowWithControls = require('./src/SlideshowWithControls');
-
-var _SlideshowWithControls2 = _interopRequireDefault(_SlideshowWithControls);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-window.Basic = window.Basic || {}; /*
- * This file is transpiled to create an ES5-compatible distribution in which
- * the package's main feature(s) are available via the window.Basic global.
- * If you're already using ES6 yourself, ignore this file, and instead import
- * the source file(s) you want from the src folder.
- */
-
-window.Basic.SlideshowWithControls = _SlideshowWithControls2.default;
-
-},{"./src/SlideshowWithControls":21}],21:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _Slideshow = require('../../basic-slideshow/src/Slideshow');
-
-var _Slideshow2 = _interopRequireDefault(_Slideshow);
-
-var _PlayControlsMixin2 = require('../../basic-component-mixins/src/PlayControlsMixin');
-
-var _PlayControlsMixin3 = _interopRequireDefault(_PlayControlsMixin2);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-/**
- * An extension of
- * [basic-slideshow](../basic-slideshow) that adds play controls
- * via [PlayControlsMixin](../basic-component-mixins/docs/PlayControlsMixin.md).
- *
- * @extends Slideshow
- * @mixes PlayControlsMixin
- */
-var SlideshowWithControls = function (_PlayControlsMixin) {
- _inherits(SlideshowWithControls, _PlayControlsMixin);
-
- function SlideshowWithControls() {
- _classCallCheck(this, SlideshowWithControls);
-
- return _possibleConstructorReturn(this, (SlideshowWithControls.__proto__ || Object.getPrototypeOf(SlideshowWithControls)).apply(this, arguments));
- }
-
- return SlideshowWithControls;
-}((0, _PlayControlsMixin3.default)(_Slideshow2.default));
-
-customElements.define('basic-slideshow-with-controls', SlideshowWithControls);
-
-exports.default = SlideshowWithControls;
-
-},{"../../basic-component-mixins/src/PlayControlsMixin":7,"../../basic-slideshow/src/Slideshow":22}],22:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
-
-var _get = function get(object, property, receiver) { if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { return get(parent, property, receiver); } } else if ("value" in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } };
-
-var _ElementBase = require('../../basic-element-base/src/ElementBase');
-
-var _ElementBase2 = _interopRequireDefault(_ElementBase);
-
-var _ContentItemsMixin = require('../../basic-component-mixins/src/ContentItemsMixin');
-
-var _ContentItemsMixin2 = _interopRequireDefault(_ContentItemsMixin);
-
-var _DistributedChildrenContentMixin = require('../../basic-component-mixins/src/DistributedChildrenContentMixin');
-
-var _DistributedChildrenContentMixin2 = _interopRequireDefault(_DistributedChildrenContentMixin);
-
-var _FractionalSelectionMixin = require('../../basic-component-mixins/src/FractionalSelectionMixin');
-
-var _FractionalSelectionMixin2 = _interopRequireDefault(_FractionalSelectionMixin);
-
-var _SelectionAnimationMixin = require('../../basic-component-mixins/src/SelectionAnimationMixin');
-
-var _SelectionAnimationMixin2 = _interopRequireDefault(_SelectionAnimationMixin);
-
-var _SelectionAriaActiveMixin = require('../../basic-component-mixins/src/SelectionAriaActiveMixin');
-
-var _SelectionAriaActiveMixin2 = _interopRequireDefault(_SelectionAriaActiveMixin);
-
-var _SingleSelectionMixin = require('../../basic-component-mixins/src/SingleSelectionMixin');
-
-var _SingleSelectionMixin2 = _interopRequireDefault(_SingleSelectionMixin);
-
-var _symbols = require('../../basic-component-mixins/src/symbols');
-
-var _symbols2 = _interopRequireDefault(_symbols);
-
-var _TimerSelectionMixin = require('../../basic-component-mixins/src/TimerSelectionMixin');
-
-var _TimerSelectionMixin2 = _interopRequireDefault(_TimerSelectionMixin);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-var base = _ElementBase2.default.compose(_ContentItemsMixin2.default, _DistributedChildrenContentMixin2.default, _FractionalSelectionMixin2.default, _SelectionAnimationMixin2.default, _SelectionAriaActiveMixin2.default, _SingleSelectionMixin2.default, _TimerSelectionMixin2.default);
-
-/**
- * Slideshow with animated transitions.
- *
- * By default the slideshow will immediately begin playing when it is connected
- * to the document, advance every 3000 ms (3 seconds), and use a simple
- * crossfade effect.
- *
- * This component can be used on its own. To incorporate slideshow behavior into
- * a component of your own, apply the
- * [TimerSelectionMixin](../basic-component-mixins/docs/TimerSelectionMixin.md).
- *
- * @extends ElementBase
- * @mixes ContentItemsMixin
- * @mixes DistributedChildrenContentMixin
- * @mixes FractionalSelectionMixin
- * @mixes SelectionAnimationMixin
- * @mixes SelectionAriaActiveMixin
- * @mixes SingleSelectionMixin
- * @mixes TimerSelectionMixin
- */
-
-var Slideshow = function (_base) {
- _inherits(Slideshow, _base);
-
- function Slideshow() {
- _classCallCheck(this, Slideshow);
-
- return _possibleConstructorReturn(this, (Slideshow.__proto__ || Object.getPrototypeOf(Slideshow)).apply(this, arguments));
- }
-
- _createClass(Slideshow, [{
- key: _symbols2.default.defaults,
- get: function get() {
- var defaults = _get(Slideshow.prototype.__proto__ || Object.getPrototypeOf(Slideshow.prototype), _symbols2.default.defaults, this) || {};
- defaults.playing = true;
- defaults.selectionAnimationDuration = 500;
- defaults.selectionAnimationEffect = 'crossfade';
- defaults.selectionRequired = true;
- defaults.selectionTimerDuration = 3000;
- defaults.selectionWraps = true;
- return defaults;
- }
- }, {
- key: _symbols2.default.template,
- get: function get() {
- return '\n \n\n \n \n
\n ';
- }
- }]);
-
- return Slideshow;
-}(base);
-
-customElements.define('basic-slideshow', Slideshow);
-exports.default = Slideshow;
-
-},{"../../basic-component-mixins/src/ContentItemsMixin":3,"../../basic-component-mixins/src/DistributedChildrenContentMixin":4,"../../basic-component-mixins/src/FractionalSelectionMixin":6,"../../basic-component-mixins/src/SelectionAnimationMixin":8,"../../basic-component-mixins/src/SelectionAriaActiveMixin":9,"../../basic-component-mixins/src/SingleSelectionMixin":12,"../../basic-component-mixins/src/TimerSelectionMixin":13,"../../basic-component-mixins/src/symbols":17,"../../basic-element-base/src/ElementBase":19}]},{},[20])
-//# sourceMappingURL=data:application/json;charset:utf-8;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbIm5vZGVfbW9kdWxlcy9ncnVudC1icm93c2VyaWZ5L25vZGVfbW9kdWxlcy9icm93c2VyLXBhY2svX3ByZWx1ZGUuanMiLCJwYWNrYWdlcy9iYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy9BdHRyaWJ1dGVNYXJzaGFsbGluZ01peGluLmpzIiwicGFja2FnZXMvYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvQ29tcG9zYWJsZU1peGluLmpzIiwicGFja2FnZXMvYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvQ29udGVudEl0ZW1zTWl4aW4uanMiLCJwYWNrYWdlcy9iYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy9EaXN0cmlidXRlZENoaWxkcmVuQ29udGVudE1peGluLmpzIiwicGFja2FnZXMvYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvRGlzdHJpYnV0ZWRDaGlsZHJlbk1peGluLmpzIiwicGFja2FnZXMvYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvRnJhY3Rpb25hbFNlbGVjdGlvbk1peGluLmpzIiwicGFja2FnZXMvYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvUGxheUNvbnRyb2xzTWl4aW4uanMiLCJwYWNrYWdlcy9iYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy9TZWxlY3Rpb25BbmltYXRpb25NaXhpbi5qcyIsInBhY2thZ2VzL2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL1NlbGVjdGlvbkFyaWFBY3RpdmVNaXhpbi5qcyIsInBhY2thZ2VzL2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL1NoYWRvd0VsZW1lbnRSZWZlcmVuY2VzTWl4aW4uanMiLCJwYWNrYWdlcy9iYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy9TaGFkb3dUZW1wbGF0ZU1peGluLmpzIiwicGFja2FnZXMvYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvU2luZ2xlU2VsZWN0aW9uTWl4aW4uanMiLCJwYWNrYWdlcy9iYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy9UaW1lclNlbGVjdGlvbk1peGluLmpzIiwicGFja2FnZXMvYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvY3JlYXRlU3ltYm9sLmpzIiwicGFja2FnZXMvYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvbWljcm90YXNrLmpzIiwicGFja2FnZXMvYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvc2FmZUF0dHJpYnV0ZXMuanMiLCJwYWNrYWdlcy9iYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy9zeW1ib2xzLmpzIiwicGFja2FnZXMvYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvdG9nZ2xlQ2xhc3MuanMiLCJwYWNrYWdlcy9iYXNpYy1lbGVtZW50LWJhc2Uvc3JjL0VsZW1lbnRCYXNlLmpzIiwicGFja2FnZXMvYmFzaWMtc2xpZGVzaG93LXdpdGgtY29udHJvbHMvZ2xvYmFscy5qcyIsInBhY2thZ2VzL2Jhc2ljLXNsaWRlc2hvdy13aXRoLWNvbnRyb2xzL3NyYy9TbGlkZXNob3dXaXRoQ29udHJvbHMuanMiLCJwYWNrYWdlcy9iYXNpYy1zbGlkZXNob3cvc3JjL1NsaWRlc2hvdy5qcyJdLCJuYW1lcyI6W10sIm1hcHBpbmdzIjoiQUFBQTs7Ozs7Ozs7Ozs7QUNBQTs7Ozs7Ozs7Ozs7O0FBR0E7QUFDQSxJQUFNLDJCQUEyQixFQUFqQztBQUNBLElBQU0sNEJBQTRCLEVBQWxDOztBQUdBOztrQkFDZSxVQUFDLElBQUQsRUFBVTs7QUFFdkI7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7O0FBRnVCLE1BcUNqQixvQkFyQ2lCO0FBQUE7O0FBQUE7QUFBQTs7QUFBQTtBQUFBOztBQUFBO0FBQUE7OztBQXVDckI7OztBQXZDcUIsK0NBMENJLGFBMUNKLEVBMENtQixRQTFDbkIsRUEwQzZCLFFBMUM3QixFQTBDdUM7QUFDMUQsdUpBQW9DO0FBQUU7QUFBbUM7QUFDekUsWUFBTSxlQUFlLHdCQUF3QixhQUF4QixDQUFyQjtBQUNBO0FBQ0E7QUFDQSxZQUFJLGdCQUFnQixJQUFoQixJQUF3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LCJmaWxlIjoiZ2VuZXJhdGVkLmpzIiwic291cmNlUm9vdCI6IiIsInNvdXJjZXNDb250ZW50IjpbIihmdW5jdGlvbiBlKHQsbixyKXtmdW5jdGlvbiBzKG8sdSl7aWYoIW5bb10pe2lmKCF0W29dKXt2YXIgYT10eXBlb2YgcmVxdWlyZT09XCJmdW5jdGlvblwiJiZyZXF1aXJlO2lmKCF1JiZhKXJldHVybiBhKG8sITApO2lmKGkpcmV0dXJuIGkobywhMCk7dmFyIGY9bmV3IEVycm9yKFwiQ2Fubm90IGZpbmQgbW9kdWxlICdcIitvK1wiJ1wiKTt0aHJvdyBmLmNvZGU9XCJNT0RVTEVfTk9UX0ZPVU5EXCIsZn12YXIgbD1uW29dPXtleHBvcnRzOnt9fTt0W29dWzBdLmNhbGwobC5leHBvcnRzLGZ1bmN0aW9uKGUpe3ZhciBuPXRbb11bMV1bZV07cmV0dXJuIHMobj9uOmUpfSxsLGwuZXhwb3J0cyxlLHQsbixyKX1yZXR1cm4gbltvXS5leHBvcnRzfXZhciBpPXR5cGVvZiByZXF1aXJlPT1cImZ1bmN0aW9uXCImJnJlcXVpcmU7Zm9yKHZhciBvPTA7bzxyLmxlbmd0aDtvKyspcyhyW29dKTtyZXR1cm4gc30pIiwiaW1wb3J0IHNhZmVBdHRyaWJ1dGVzIGZyb20gJy4vc2FmZUF0dHJpYnV0ZXMnO1xuXG5cbi8vIE1lbW9pemVkIG1hcHMgb2YgYXR0cmlidXRlIHRvIHByb3BlcnR5IG5hbWVzIGFuZCB2aWNlIHZlcnNhLlxuY29uc3QgYXR0cmlidXRlVG9Qcm9wZXJ0eU5hbWVzID0ge307XG5jb25zdCBwcm9wZXJ0eU5hbWVzVG9BdHRyaWJ1dGVzID0ge307XG5cblxuLyogRXhwb3J0ZWQgZnVuY3Rpb24gZXh0ZW5kcyBhIGJhc2UgY2xhc3Mgd2l0aCBBdHRyaWJ1dGVNYXJzaGFsbGluZy4gKi9cbmV4cG9ydCBkZWZhdWx0IChiYXNlKSA9PiB7XG5cbiAgLyoqXG4gICAqIE1peGluIHdoaWNoIG1hcnNoYWxscyBhdHRyaWJ1dGVzIHRvIHByb3BlcnRpZXMgYW5kIHZpY2UgdmVyc2EuXG4gICAqXG4gICAqIElmIHlvdXIgY29tcG9uZW50IGV4cG9zZXMgYSBzZXR0ZXIgZm9yIGEgcHJvcGVydHksIGl0J3MgZ2VuZXJhbGx5IGEgZ29vZFxuICAgKiBpZGVhIHRvIGxldCBkZXZzIHVzaW5nIHlvdXIgY29tcG9uZW50IGJlIGFibGUgdG8gc2V0IHRoYXQgcHJvcGVydHkgaW4gSFRNTFxuICAgKiB2aWEgYW4gZWxlbWVudCBhdHRyaWJ1dGUuIFlvdSBjYW4gY29kZSB0aGF0IHlvdXJzZWxmIGJ5IHdyaXRpbmcgYW5cbiAgICogYGF0dHJpYnV0ZUNoYW5nZWRDYWxsYmFja2AsIG9yIHlvdSBjYW4gdXNlIHRoaXMgbWl4aW4gdG8gZ2V0IGEgZGVncmVlIG9mXG4gICAqIGF1dG9tYXRpYyBzdXBwb3J0LlxuICAgKlxuICAgKiBUaGlzIG1peGluIGltcGxlbWVudHMgYW4gYGF0dHJpYnV0ZUNoYW5nZWRDYWxsYmFja2AgdGhhdCB3aWxsIGF0dGVtcHQgdG9cbiAgICogY29udmVydCBhIGNoYW5nZSBpbiBhbiBlbGVtZW50IGF0dHJpYnV0ZSBpbnRvIGEgY2FsbCB0byB0aGUgY29ycmVzcG9uZGluZ1xuICAgKiBwcm9wZXJ0eSBzZXR0ZXIuIEF0dHJpYnV0ZXMgdHlwaWNhbGx5IGZvbGxvdyBoeXBoZW5hdGVkIG5hbWVzIChcImZvby1iYXJcIiksXG4gICAqIHdoZXJlYXMgcHJvcGVydGllcyB0eXBpY2FsbHkgdXNlIGNhbWVsQ2FzZSBuYW1lcyAoXCJmb29CYXJcIikuIFRoaXMgbWl4aW5cbiAgICogcmVzcGVjdHMgdGhhdCBjb252ZW50aW9uLCBhdXRvbWF0aWNhbGx5IG1hcHBpbmcgdGhlIGh5cGhlbmF0ZWQgYXR0cmlidXRlXG4gICAqIG5hbWUgdG8gdGhlIGNvcnJlc3BvbmRpbmcgY2FtZWxDYXNlIHByb3BlcnR5IG5hbWUuXG4gICAqXG4gICAqIEV4YW1wbGU6IFlvdSBkZWZpbmUgYSBjb21wb25lbnQgdXNpbmcgdGhpcyBtaXhpbjpcbiAgICpcbiAgICogICAgIGNsYXNzIE15RWxlbWVudCBleHRlbmRzIEF0dHJpYnV0ZU1hcnNoYWxsaW5nTWl4aW4oSFRNTEVsZW1lbnQpIHtcbiAgICogICAgICAgZ2V0IGZvb0JhcigpIHsgcmV0dXJuIHRoaXMuX2Zvb0JhcjsgfVxuICAgKiAgICAgICBzZXQgZm9vQmFyKHZhbHVlKSB7IHRoaXMuX2Zvb0JhciA9IHZhbHVlOyB9XG4gICAqICAgICB9XG4gICAqICAgICBjdXN0b21FbGVtZW50cy5kZWZpbmUoJ215LWVsZW1lbnQnLCBNeUVsZW1lbnQpO1xuICAgKlxuICAgKiBJZiBzb21lb25lIHRoZW4gaW5zdGFudGlhdGVzIHlvdXIgY29tcG9uZW50IGluIEhUTUw6XG4gICAqXG4gICAqICAgICA8bXktZWxlbWVudCBmb28tYmFyPVwiSGVsbG9cIj48L215LWVsZW1lbnQ+XG4gICAqXG4gICAqIFRoZW4sIGFmdGVyIHRoZSBlbGVtZW50IGhhcyBiZWVuIHVwZ3JhZGVkLCB0aGUgYGZvb0JhcmAgc2V0dGVyIHdpbGxcbiAgICogYXV0b21hdGljYWxseSBiZSBpbnZva2VkIHdpdGggdGhlIGluaXRpYWwgdmFsdWUgXCJIZWxsb1wiLlxuICAgKlxuICAgKiBGb3IgdGhlIHRpbWUgYmVpbmcsIHRoaXMgbWl4aW4gb25seSBzdXBwb3J0cyBzdHJpbmctdmFsdWVkIHByb3BlcnRpZXMuXG4gICAqIElmIHlvdSdkIGxpa2UgdG8gY29udmVydCBzdHJpbmcgYXR0cmlidXRlcyB0byBvdGhlciB0eXBlcyAobnVtYmVycyxcbiAgICogYm9vbGVhbnMpLCB5b3UgbmVlZCB0byBpbXBsZW1lbnQgYGF0dHJpYnV0ZUNoYW5nZWRDYWxsYmFja2AgeW91cnNlbGYuXG4gICAqL1xuICBjbGFzcyBBdHRyaWJ1dGVNYXJzaGFsbGluZyBleHRlbmRzIGJhc2Uge1xuXG4gICAgLypcbiAgICAgKiBIYW5kbGUgYSBjaGFuZ2UgdG8gdGhlIGF0dHJpYnV0ZSB3aXRoIHRoZSBnaXZlbiBuYW1lLlxuICAgICAqL1xuICAgIGF0dHJpYnV0ZUNoYW5nZWRDYWxsYmFjayhhdHRyaWJ1dGVOYW1lLCBvbGRWYWx1ZSwgbmV3VmFsdWUpIHtcbiAgICAgIGlmIChzdXBlci5hdHRyaWJ1dGVDaGFuZ2VkQ2FsbGJhY2spIHsgc3VwZXIuYXR0cmlidXRlQ2hhbmdlZENhbGxiYWNrKCk7IH1cbiAgICAgIGNvbnN0IHByb3BlcnR5TmFtZSA9IGF0dHJpYnV0ZVRvUHJvcGVydHlOYW1lKGF0dHJpYnV0ZU5hbWUpO1xuICAgICAgLy8gSWYgdGhlIGF0dHJpYnV0ZSBuYW1lIGNvcnJlc3BvbmRzIHRvIGEgcHJvcGVydHkgbmFtZSwgc2V0IHRoZSBwcm9wZXJ0eS5cbiAgICAgIC8vIElnbm9yZSBzdGFuZGFyZCBIVE1MRWxlbWVudCBwcm9wZXJ0aWVzIGhhbmRsZWQgYnkgdGhlIERPTS5cbiAgICAgIGlmIChwcm9wZXJ0eU5hbWUgaW4gdGhpcyAmJiAhKHByb3BlcnR5TmFtZSBpbiBIVE1MRWxlbWVudC5wcm90b3R5cGUpKSB7XG4gICAgICAgIHRoaXNbcHJvcGVydHlOYW1lXSA9IG5ld1ZhbHVlO1xuICAgICAgfVxuICAgIH1cblxuICAgIGNvbm5lY3RlZENhbGxiYWNrKCkge1xuICAgICAgaWYgKHN1cGVyLmNvbm5lY3RlZENhbGxiYWNrKSB7IHN1cGVyLmNvbm5lY3RlZENhbGxiYWNrKCk7IH1cbiAgICAgIHNhZmVBdHRyaWJ1dGVzLmNvbm5lY3RlZCh0aGlzKTtcbiAgICB9XG5cbiAgICBzdGF0aWMgZ2V0IG9ic2VydmVkQXR0cmlidXRlcygpIHtcbiAgICAgIHJldHVybiBhdHRyaWJ1dGVzRm9yQ2xhc3ModGhpcyk7XG4gICAgfVxuXG4gICAgLyoqXG4gICAgICogU2V0L3Vuc2V0IHRoZSBhdHRyaWJ1dGUgd2l0aCB0aGUgaW5kaWNhdGVkIG5hbWUuXG4gICAgICpcbiAgICAgKiBUaGlzIG1ldGhvZCBleGlzdHMgcHJpbWFyaWx5IHRvIGhhbmRsZSB0aGUgY2FzZSB3aGVyZSBhbiBlbGVtZW50IHdhbnRzIHRvXG4gICAgICogc2V0IGEgZGVmYXVsdCBwcm9wZXJ0eSB2YWx1ZSB0aGF0IHNob3VsZCBiZSByZWZsZWN0ZWQgYXMgYW4gYXR0cmlidXRlLiBBblxuICAgICAqIGltcG9ydGFudCBsaW1pdGF0aW9uIG9mIGN1c3RvbSBlbGVtZW50IGNvbnN0dXJjdG9ycyBpcyB0aGF0IHRoZXkgY2Fubm90XG4gICAgICogc2V0IGF0dHJpYnV0ZXMuIEEgY2FsbCB0byBgcmVmbGVjdEF0dHJpYnV0ZWAgZHVyaW5nIHRoZSBjb25zdHJ1Y3RvciB3aWxsXG4gICAgICogYmUgZGVmZXJyZWQgdW50aWwgdGhlIGVsZW1lbnQgaXMgY29ubmVjdGVkIHRvIHRoZSBkb2N1bWVudC5cbiAgICAgKlxuICAgICAqIEBwYXJhbSB7c3RyaW5nfSBhdHRyaWJ1dGUgLSBUaGUgbmFtZSBvZiB0aGUgKmF0dHJpYnV0ZSogKG5vdCBwcm9wZXJ0eSkgdG8gc2V0LlxuICAgICAqIEBwYXJhbSB7b2JqZWN0fSB2YWx1ZSAtIFRoZSB2YWx1ZSB0byBzZXQuIElmIG51bGwsIHRoZSBhdHRyaWJ1dGUgd2lsbCBiZSByZW1vdmVkLlxuICAgICAqL1xuICAgIHJlZmxlY3RBdHRyaWJ1dGUoYXR0cmlidXRlLCB2YWx1ZSkge1xuICAgICAgcmV0dXJuIHNhZmVBdHRyaWJ1dGVzLnNldEF0dHJpYnV0ZSh0aGlzLCBhdHRyaWJ1dGUsIHZhbHVlKTtcbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBTZXQvdW5zZXQgdGhlIGNsYXNzIHdpdGggdGhlIGluZGljYXRlZCBuYW1lLlxuICAgICAqXG4gICAgICogVGhpcyBtZXRob2QgZXhpc3RzIHByaW1hcmlseSB0byBoYW5kbGUgdGhlIGNhc2Ugd2hlcmUgYW4gZWxlbWVudCB3YW50cyB0b1xuICAgICAqIHNldCBhIGRlZmF1bHQgcHJvcGVydHkgdmFsdWUgdGhhdCBzaG91bGQgYmUgcmVmbGVjdGVkIGFzIGFzIGNsYXNzLiBBblxuICAgICAqIGltcG9ydGFudCBsaW1pdGF0aW9uIG9mIGN1c3RvbSBlbGVtZW50IGNvbnN0dXJjdG9ycyBpcyB0aGF0IHRoZXkgY2Fubm90XG4gICAgICogc2V0IGF0dHJpYnV0ZXMsIGluY2x1ZGluZyB0aGUgYGNsYXNzYCBhdHRyaWJ1dGUuIEEgY2FsbCB0b1xuICAgICAqIGByZWZsZWN0Q2xhc3NgIGR1cmluZyB0aGUgY29uc3RydWN0b3Igd2lsbCBiZSBkZWZlcnJlZCB1bnRpbCB0aGUgZWxlbWVudFxuICAgICAqIGlzIGNvbm5lY3RlZCB0byB0aGUgZG9jdW1lbnQuXG4gICAgICpcbiAgICAgKiBAcGFyYW0ge3N0cmluZ30gY2xhc3NOYW1lIC0gVGhlIG5hbWUgb2YgdGhlIGNsYXNzIHRvIHNldC5cbiAgICAgKiBAcGFyYW0ge29iamVjdH0gdmFsdWUgLSBUcnVlIHRvIHNldCB0aGUgY2xhc3MsIGZhbHNlIHRvIHJlbW92ZSBpdC5cbiAgICAgKi9cbiAgICByZWZsZWN0Q2xhc3MoY2xhc3NOYW1lLCB2YWx1ZSkge1xuICAgICAgcmV0dXJuIHNhZmVBdHRyaWJ1dGVzLnRvZ2dsZUNsYXNzKHRoaXMsIGNsYXNzTmFtZSwgdmFsdWUpO1xuICAgIH1cblxuICB9XG5cbiAgcmV0dXJuIEF0dHJpYnV0ZU1hcnNoYWxsaW5nO1xufTtcblxuXG4vLyBDb252ZXJ0IGh5cGhlbmF0ZWQgZm9vLWJhciBhdHRyaWJ1dGUgbmFtZSB0byBjYW1lbCBjYXNlIGZvb0JhciBwcm9wZXJ0eSBuYW1lLlxuZnVuY3Rpb24gYXR0cmlidXRlVG9Qcm9wZXJ0eU5hbWUoYXR0cmlidXRlTmFtZSkge1xuICBsZXQgcHJvcGVydHlOYW1lID0gYXR0cmlidXRlVG9Qcm9wZXJ0eU5hbWVzW2F0dHJpYnV0ZU5hbWVdO1xuICBpZiAoIXByb3BlcnR5TmFtZSkge1xuICAgIC8vIENvbnZlcnQgYW5kIG1lbW9pemUuXG4gICAgY29uc3QgaHlwZW5SZWdFeCA9IC8tKFthLXpdKS9nO1xuICAgIHByb3BlcnR5TmFtZSA9IGF0dHJpYnV0ZU5hbWUucmVwbGFjZShoeXBlblJlZ0V4LFxuICAgICAgICBtYXRjaCA9PiBtYXRjaFsxXS50b1VwcGVyQ2FzZSgpKTtcbiAgICBhdHRyaWJ1dGVUb1Byb3BlcnR5TmFtZXNbYXR0cmlidXRlTmFtZV0gPSBwcm9wZXJ0eU5hbWU7XG4gIH1cbiAgcmV0dXJuIHByb3BlcnR5TmFtZTtcbn1cblxuZnVuY3Rpb24gYXR0cmlidXRlc0ZvckNsYXNzKGNsYXNzRm4pIHtcblxuICAvLyBXZSB0cmVhdCB0aGUgZWxlbWVudCBiYXNlIGNsYXNzZXMgYXMgaWYgdGhleSBoYXZlIG5vIGF0dHJpYnV0ZXMsIHNpbmNlIHdlXG4gIC8vIGRvbid0IHdhbnQgdG8gcmVjZWl2ZSBhdHRyaWJ1dGVDaGFuZ2VkQ2FsbGJhY2sgZm9yIHRoZW0uXG4gIGlmIChjbGFzc0ZuID09PSBIVE1MRWxlbWVudCB8fCBjbGFzc0ZuID09PSBPYmplY3QpIHtcbiAgICByZXR1cm4gW107XG4gIH1cblxuICAvLyBHZXQgYXR0cmlidXRlcyBmb3IgcGFyZW50IGNsYXNzLlxuICBjb25zdCBiYXNlQ2xhc3MgPSBPYmplY3QuZ2V0UHJvdG90eXBlT2YoY2xhc3NGbi5wcm90b3R5cGUpLmNvbnN0cnVjdG9yO1xuICBjb25zdCBiYXNlQXR0cmlidXRlcyA9IGF0dHJpYnV0ZXNGb3JDbGFzcyhiYXNlQ2xhc3MpO1xuXG4gIC8vIEdldCBhdHRyaWJ1dGVzIGZvciB0aGlzIGNsYXNzLlxuICBjb25zdCBwcm9wZXJ0eU5hbWVzID0gT2JqZWN0LmdldE93blByb3BlcnR5TmFtZXMoY2xhc3NGbi5wcm90b3R5cGUpO1xuICBjb25zdCBzZXR0ZXJOYW1lcyA9IHByb3BlcnR5TmFtZXMuZmlsdGVyKHByb3BlcnR5TmFtZSA9PlxuICAgIHR5cGVvZiBPYmplY3QuZ2V0T3duUHJvcGVydHlEZXNjcmlwdG9yKFxuICAgICAgICBjbGFzc0ZuLnByb3RvdHlwZSwgcHJvcGVydHlOYW1lKS5zZXQgPT09ICdmdW5jdGlvbicpO1xuICBjb25zdCBhdHRyaWJ1dGVzID0gc2V0dGVyTmFtZXMubWFwKHNldHRlck5hbWUgPT5cbiAgICAgIHByb3BlcnR5TmFtZVRvQXR0cmlidXRlKHNldHRlck5hbWUpKTtcblxuICAvLyBNZXJnZS5cbiAgY29uc3QgZGlmZiA9IGF0dHJpYnV0ZXMuZmlsdGVyKGF0dHJpYnV0ZSA9PlxuICAgICAgYmFzZUF0dHJpYnV0ZXMuaW5kZXhPZihhdHRyaWJ1dGUpIDwgMCk7XG4gIHJldHVybiBiYXNlQXR0cmlidXRlcy5jb25jYXQoZGlmZik7XG59XG5cbi8vIENvbnZlcnQgYSBjYW1lbCBjYXNlIGZvb0JhciBwcm9wZXJ0eSBuYW1lIHRvIGEgaHlwaGVuYXRlZCBmb28tYmFyIGF0dHJpYnV0ZS5cbmZ1bmN0aW9uIHByb3BlcnR5TmFtZVRvQXR0cmlidXRlKHByb3BlcnR5TmFtZSkge1xuICBsZXQgYXR0cmlidXRlID0gcHJvcGVydHlOYW1lc1RvQXR0cmlidXRlc1twcm9wZXJ0eU5hbWVdO1xuICBpZiAoIWF0dHJpYnV0ZSkge1xuICAgIC8vIENvbnZlcnQgYW5kIG1lbW9pemUuXG4gICAgY29uc3QgdXBwZXJjYXNlUmVnRXggPSAvKFtBLVpdKS9nO1xuICAgIGF0dHJpYnV0ZSA9IHByb3BlcnR5TmFtZS5yZXBsYWNlKHVwcGVyY2FzZVJlZ0V4LCAnLSQxJykudG9Mb3dlckNhc2UoKTtcbiAgfVxuICByZXR1cm4gYXR0cmlidXRlO1xufVxuIiwiLyogRXhwb3J0ZWQgZnVuY3Rpb24gZXh0ZW5kcyBhIGJhc2UgY2xhc3Mgd2l0aCBDb21wb3NhYmxlLiAqL1xuZXhwb3J0IGRlZmF1bHQgKGJhc2UpID0+IHtcblxuICAvKipcbiAgICogTWl4aW4gdG8gbWFrZSBhIGNsYXNzIG1vcmUgZWFzaWx5IGNvbXBvc2FibGUgd2l0aCBvdGhlciBtaXhpbnMuXG4gICAqXG4gICAqIFRoaXMgbWl4aW4gY29udHJpYnV0ZXMgYSBgY29tcG9zZWAgbWV0aG9kIHRoYXQgYXBwbGllcyBhIHNldCBvZiBtaXhpblxuICAgKiBmdW5jdGlvbnMgYW5kIHJldHVybnMgdGhlIHJlc3VsdGluZyBuZXcgY2xhc3MuIFRoaXMgc3VnYXIgY2FuIG1ha2UgdGhlXG4gICAqIGFwcGxpY2F0aW9uIG9mIG1hbnkgbWl4aW5zIGF0IG9uY2UgZWFzaWVyIHRvIHJlYWQuXG4gICAqL1xuICBjbGFzcyBDb21wb3NhYmxlIGV4dGVuZHMgYmFzZSB7XG5cbiAgICAvKipcbiAgICAgKiBBcHBseSBhIHNldCBvZiBtaXhpbiBmdW5jdGlvbnMgb3IgbWl4aW4gb2JqZWN0cyB0byB0aGUgcHJlc2VudCBjbGFzcyBhbmRcbiAgICAgKiByZXR1cm4gdGhlIG5ldyBjbGFzcy5cbiAgICAgKlxuICAgICAqIEluc3RlYWQgb2Ygd3JpdGluZzpcbiAgICAgKlxuICAgICAqICAgICBsZXQgTXlDbGFzcyA9IE1peGluMShNaXhpbjIoTWl4aW4zKE1peGluNChNaXhpbjUoQmFzZUNsYXNzKSkpKSk7XG4gICAgICpcbiAgICAgKiBZb3UgY2FuIHdyaXRlOlxuICAgICAqXG4gICAgICogICAgIGxldCBNeUNsYXNzID0gQ29tcG9zYWJsZU1peGluKEJhc2VDbGFzcykuY29tcG9zZShcbiAgICAgKiAgICAgICBNaXhpbjEsXG4gICAgICogICAgICAgTWl4aW4yLFxuICAgICAqICAgICAgIE1peGluMyxcbiAgICAgKiAgICAgICBNaXhpbjQsXG4gICAgICogICAgICAgTWl4aW41XG4gICAgICogICAgICk7XG4gICAgICpcbiAgICAgKiBUaGlzIGZ1bmN0aW9uIGNhbiBhbHNvIHRha2UgbWl4aW4gb2JqZWN0cy4gQSBtaXhpbiBvYmplY3QgaXMganVzdCBhXG4gICAgICogc2hvcnRoYW5kIGZvciBhIG1peGluIGZ1bmN0aW9uIHRoYXQgY3JlYXRlcyBhIG5ldyBzdWJjbGFzcyB3aXRoIHRoZSBnaXZlblxuICAgICAqIG1lbWJlcnMuIFRoZSBtaXhpbiBvYmplY3QncyBtZW1iZXJzIGFyZSAqbm90KiBjb3BpZWQgZGlyZWN0bHkgb250byB0aGVcbiAgICAgKiBwcm90b3R5cGUgb2YgdGhlIGJhc2UgY2xhc3MsIGFzIHdpdGggdHJhZGl0aW9uYWwgbWl4aW5zLlxuICAgICAqXG4gICAgICogSW4gYWRkaXRpb24gdG8gcHJvdmlkaW5nIHN5bnRhY3RpYyBzdWdhciwgdGhpcyBtaXhpbiBjYW4gYmUgdXNlZCB0b1xuICAgICAqIGRlZmluZSBhIGNsYXNzIGluIEVTNSwgd2hpY2ggbGFja3MgRVM2J3MgYGNsYXNzYCBrZXl3b3JkLlxuICAgICAqXG4gICAgICogQHBhcmFtIHsuLi5taXhpbnN9IG1peGlucyAtIEEgc2V0IG9mIG1peGluIGZ1bmN0aW9ucyBvciBvYmplY3RzIHRvIGFwcGx5LlxuICAgICAqL1xuICAgIHN0YXRpYyBjb21wb3NlKC4uLm1peGlucykge1xuICAgICAgLy8gV2UgY3JlYXRlIGEgbmV3IHN1YmNsYXNzIGZvciBlYWNoIG1peGluIGluIHR1cm4uIFRoZSByZXN1bHQgYmVjb21lc1xuICAgICAgLy8gdGhlIGJhc2UgY2xhc3MgZXh0ZW5kZWQgYnkgYW55IHN1YnNlcXVlbnQgbWl4aW5zLiBJdCB0dXJucyBvdXQgdGhhdFxuICAgICAgLy8gd2UgY2FuIHVzZSBBcnJheS5yZWR1Y2UoKSB0byBjb25jaXNlbHkgZXhwcmVzcyB0aGlzLCB1c2luZyB0aGUgY3VycmVudFxuICAgICAgLy8gb2JqZWN0IGFzIHRoZSBzZWVkIGZvciByZWR1Y2UoKS5cbiAgICAgIHJldHVybiBtaXhpbnMucmVkdWNlKGNvbXBvc2VDbGFzcywgdGhpcyk7XG4gICAgfVxuXG4gIH1cblxuICByZXR1cm4gQ29tcG9zYWJsZTtcbn07XG5cblxuLy8gUHJvcGVydGllcyBkZWZpbmVkIGJ5IE9iamVjdCB0aGF0IHdlIGRvbid0IHdhbnQgdG8gbWl4aW4uXG5jb25zdCBOT05fTUlYQUJMRV9PQkpFQ1RfUFJPUEVSVElFUyA9IFtcbiAgJ2NvbnN0cnVjdG9yJ1xuXTtcblxuLypcbiAqIEFwcGx5IHRoZSBtaXhpbiB0byB0aGUgZ2l2ZW4gYmFzZSBjbGFzcyB0byByZXR1cm4gYSBuZXcgY2xhc3MuXG4gKiBUaGUgbWl4aW4gY2FuIGVpdGhlciBiZSBhIGZ1bmN0aW9uIHRoYXQgcmV0dXJucyB0aGUgbW9kaWZpZWQgY2xhc3MsIG9yIGFcbiAqIHBsYWluIG9iamVjdCB3aG9zZSBtZW1iZXJzIHdpbGwgYmUgY29waWVkIHRvIHRoZSBuZXcgY2xhc3MnIHByb3RvdHlwZS5cbiAqL1xuZnVuY3Rpb24gY29tcG9zZUNsYXNzKGJhc2UsIG1peGluKSB7XG4gIGlmICh0eXBlb2YgbWl4aW4gPT09ICdmdW5jdGlvbicpIHtcbiAgICAvLyBNaXhpbiBmdW5jdGlvblxuICAgIHJldHVybiBtaXhpbihiYXNlKTtcbiAgfSBlbHNlIHtcbiAgICAvLyBNaXhpbiBvYmplY3RcbiAgICBjbGFzcyBTdWJjbGFzcyBleHRlbmRzIGJhc2Uge31cbiAgICBjb3B5T3duUHJvcGVydGllcyhtaXhpbiwgU3ViY2xhc3MucHJvdG90eXBlLCBOT05fTUlYQUJMRV9PQkpFQ1RfUFJPUEVSVElFUyk7XG4gICAgcmV0dXJuIFN1YmNsYXNzO1xuICB9XG59XG5cblxuLypcbiAqIENvcHkgdGhlIGdpdmVuIHByb3BlcnRpZXMvbWV0aG9kcyB0byB0aGUgdGFyZ2V0LlxuICogUmV0dXJuIHRoZSB1cGRhdGVkIHRhcmdldC5cbiAqL1xuZnVuY3Rpb24gY29weU93blByb3BlcnRpZXMoc291cmNlLCB0YXJnZXQsIGlnbm9yZVByb3BlcnR5TmFtZXMgPSBbXSkge1xuICBPYmplY3QuZ2V0T3duUHJvcGVydHlOYW1lcyhzb3VyY2UpLmZvckVhY2gobmFtZSA9PiB7XG4gICAgaWYgKGlnbm9yZVByb3BlcnR5TmFtZXMuaW5kZXhPZihuYW1lKSA8IDApIHtcbiAgICAgIGNvbnN0IGRlc2NyaXB0b3IgPSBPYmplY3QuZ2V0T3duUHJvcGVydHlEZXNjcmlwdG9yKHNvdXJjZSwgbmFtZSk7XG4gICAgICBPYmplY3QuZGVmaW5lUHJvcGVydHkodGFyZ2V0LCBuYW1lLCBkZXNjcmlwdG9yKTtcbiAgICB9XG4gIH0pO1xuICByZXR1cm4gdGFyZ2V0O1xufVxuIiwiaW1wb3J0IGNyZWF0ZVN5bWJvbCBmcm9tICcuL2NyZWF0ZVN5bWJvbCc7XG5pbXBvcnQgdG9nZ2xlQ2xhc3MgZnJvbSAnLi90b2dnbGVDbGFzcyc7XG5pbXBvcnQgc3ltYm9scyBmcm9tICcuL3N5bWJvbHMnO1xuXG5cbi8vIFN5bWJvbHMgZm9yIHByaXZhdGUgZGF0YSBtZW1iZXJzIG9uIGFuIGVsZW1lbnQuXG5jb25zdCBpdGVtc1N5bWJvbCA9IGNyZWF0ZVN5bWJvbCgnaXRlbXMnKTtcbmNvbnN0IGl0ZW1Jbml0aWFsaXplZFN5bWJvbCA9IGNyZWF0ZVN5bWJvbCgnaXRlbUluaXRpYWxpemVkJyk7XG5cblxuLyogRXhwb3J0ZWQgZnVuY3Rpb24gZXh0ZW5kcyBhIGJhc2UgY2xhc3Mgd2l0aCBDb250ZW50SXRlbXMuICovXG5leHBvcnQgZGVmYXVsdCAoYmFzZSkgPT4ge1xuXG4gIC8qKlxuICAgKiBNaXhpbiB3aGljaCBtYXBzIGNvbnRlbnQgc2VtYW50aWNzIChlbGVtZW50cykgdG8gbGlzdCBpdGVtIHNlbWFudGljcy5cbiAgICpcbiAgICogSXRlbXMgZGlmZmVyIGZyb20gZWxlbWVudCBjb250ZW50cyBpbiBzZXZlcmFsIHdheXM6XG4gICAqXG4gICAqICogVGhleSBhcmUgb2Z0ZW4gcmVmZXJlbmNlZCB2aWEgaW5kZXguXG4gICAqICogVGhleSBtYXkgaGF2ZSBhIHNlbGVjdGlvbiBzdGF0ZS5cbiAgICogKiBJdCdzIGNvbW1vbiB0byBkbyB3b3JrIHRvIGluaXRpYWxpemUgdGhlIGFwcGVhcmFuY2Ugb3Igc3RhdGUgb2YgYSBuZXdcbiAgICogICBpdGVtLlxuICAgKiAqIEF1eGlsaWFyeSBpbnZpc2libGUgY2hpbGQgZWxlbWVudHMgYXJlIGZpbHRlcmVkIG91dCBhbmQgbm90IGNvdW50ZWQgYXNcbiAgICogICBpdGVtcy4gQXV4aWxpYXJ5IGVsZW1lbnRzIGluY2x1ZGUgbGluaywgc2NyaXB0LCBzdHlsZSwgYW5kIHRlbXBsYXRlXG4gICAqICAgZWxlbWVudHMuIFRoaXMgZmlsdGVyaW5nIGVuc3VyZXMgdGhhdCB0aG9zZSBhdXhpbGlhcnkgZWxlbWVudHMgY2FuIGJlXG4gICAqICAgdXNlZCBpbiBtYXJrdXAgaW5zaWRlIG9mIGEgbGlzdCB3aXRob3V0IGJlaW5nIHRyZWF0ZWQgYXMgbGlzdCBpdGVtcy5cbiAgICpcbiAgICogVGhpcyBtaXhpbiBleHBlY3RzIGEgY29tcG9uZW50IHRvIHByb3ZpZGUgYSBgY29udGVudGAgcHJvcGVydHkgcmV0dXJuaW5nIGFcbiAgICogcmF3IHNldCBvZiBlbGVtZW50cy4gWW91IGNhbiBwcm92aWRlIHRoYXQgeW91cnNlbGYsIG9yIHVzZVxuICAgKiBbRGlzdHJpYnV0ZWRDaGlsZHJlbkNvbnRlbnRNaXhpbl0oRGlzdHJpYnV0ZWRDaGlsZHJlbkNvbnRlbnRNaXhpbi5tZCkuXG4gICAqXG4gICAqIFRoZSBtb3N0IGNvbW1vbmx5IHJlZmVyZW5jZWQgcHJvcGVydHkgZGVmaW5lZCBieSB0aGlzIG1peGluIGlzIHRoZSBgaXRlbXNgXG4gICAqIHByb3BlcnR5LiBUbyBhdm9pZCBoYXZpbmcgdG8gZG8gd29yayBlYWNoIHRpbWUgdGhhdCBwcm9wZXJ0eSBpcyByZXF1ZXN0ZWQsXG4gICAqIHRoaXMgbWl4aW4gc3VwcG9ydHMgYW4gb3B0aW1pemVkIG1vZGUuIElmIHlvdSBpbnZva2UgdGhlIGBjb250ZW50Q2hhbmdlZGBcbiAgICogbWV0aG9kIHdoZW4gdGhlIHNldCBvZiBpdGVtcyBjaGFuZ2VzLCB0aGUgbWl4aW4gY29uY2x1ZGVzIHRoYXQgeW91J2xsIHRha2VcbiAgICogY2FyZSBvZiBub3RpZnlpbmcgaXQgb2YgZnV0dXJlIGNoYW5nZXMsIGFuZCB0dXJucyBvbiB0aGUgb3B0aW1pemF0aW9uLiBXaXRoXG4gICAqIHRoYXQgb24sIHRoZSBtaXhpbiBzYXZlcyBhIHJlZmVyZW5jZSB0byB0aGUgY29tcHV0ZWQgc2V0IG9mIGl0ZW1zLCBhbmQgd2lsbFxuICAgKiByZXR1cm4gdGhhdCBpbW1lZGlhdGVseSBvbiBzdWJzZXF1ZW50IGNhbGxzIHRvIHRoZSBgaXRlbXNgIHByb3BlcnR5LiBJZiB5b3VcbiAgICogdXNlIHRoaXMgbWl4aW4gaW4gY29uanVuY3Rpb24gd2l0aFxuICAgKiBbRGlzdHJpYnV0ZWRDaGlsZHJlbkNvbnRlbnRNaXhpbl0oRGlzdHJpYnV0ZWRDaGlsZHJlbkNvbnRlbnRNaXhpbi5tZCksIHRoZVxuICAgKiBgY29udGVudENoYW5nZWRgIG1ldGhvZCB3aWxsIGJlIGludm9rZWQgZm9yIHlvdSB3aGVuIHRoZSBlbGVtZW50J3MgY2hpbGRyZW5cbiAgICogY2hhbmdlLCB0dXJuaW5nIG9uIHRoZSBvcHRpbWl6YXRpb24gYXV0b21hdGljYWxseS5cbiAgICovXG4gIGNsYXNzIENvbnRlbnRJdGVtcyBleHRlbmRzIGJhc2Uge1xuXG4gICAgY29udGVudENoYW5nZWQoKSB7XG4gICAgICBpZiAoc3VwZXIuY29udGVudENoYW5nZWQpIHsgc3VwZXIuY29udGVudENoYW5nZWQoKTsgfVxuXG4gICAgICAvLyBTaW5jZSB3ZSBnb3QgdGhlIGNvbnRlbnRDaGFuZ2VkIGNhbGwsIHdlJ2xsIGFzc3VtZSB3ZSdsbCBiZSBub3RpZmllZCBpZlxuICAgICAgLy8gdGhlIHNldCBvZiBpdGVtcyBjaGFuZ2VzIGxhdGVyLiBXZSB0dXJuIG9uIG1lbW9pemF0aW9uIG9mIHRoZSBpdGVtc1xuICAgICAgLy8gcHJvcGVydHkgYnkgc2V0dGluZyBvdXIgaW50ZXJuYWwgcHJvcGVydHkgdG8gbnVsbCAoaW5zdGVhZCBvZlxuICAgICAgLy8gdW5kZWZpbmVkKS5cbiAgICAgIHRoaXNbaXRlbXNTeW1ib2xdID0gbnVsbDtcblxuICAgICAgdGhpc1tzeW1ib2xzLml0ZW1zQ2hhbmdlZF0oKTtcbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBUaGlzIG1ldGhvZCBpcyBpbnZva2VkIHdoZW5ldmVyIGEgbmV3IGl0ZW0gaXMgYWRkZWQgdG8gdGhlIGxpc3QuXG4gICAgICpcbiAgICAgKiBUaGUgZGVmYXVsdCBpbXBsZW1lbnRhdGlvbiBvZiB0aGlzIG1ldGhvZCBkb2VzIG5vdGhpbmcuIFlvdSBjYW4gb3ZlcnJpZGVcbiAgICAgKiB0aGlzIHRvIHBlcmZvcm0gcGVyLWl0ZW0gaW5pdGlhbGl6YXRpb24uXG4gICAgICpcbiAgICAgKiBAcGFyYW0ge0hUTUxFbGVtZW50fSBpdGVtIC0gVGhlIGl0ZW0gdGhhdCB3YXMgYWRkZWQuXG4gICAgICovXG4gICAgW3N5bWJvbHMuaXRlbUFkZGVkXShpdGVtKSB7XG4gICAgICBpZiAoc3VwZXJbc3ltYm9scy5pdGVtQWRkZWRdKSB7IHN1cGVyW3N5bWJvbHMuaXRlbUFkZGVkXShpdGVtKTsgfVxuICAgIH1cblxuICAgIC8qKlxuICAgICAqIFRoZSBzZWxlY3Rpb24gc3RhdGUgZm9yIGEgc2luZ2xlIGl0ZW0gaGFzIGNoYW5nZWQuXG4gICAgICpcbiAgICAgKiBJbnZva2UgdGhpcyBtZXRob2QgdG8gc2lnbmFsIHRoYXQgdGhlIHNlbGVjdGVkIHN0YXRlIG9mIHRoZSBpbmRpY2F0ZWQgaXRlbVxuICAgICAqIGhhcyBjaGFuZ2VkLiBCeSBkZWZhdWx0LCB0aGlzIGFwcGxpZXMgYSBgc2VsZWN0ZWRgIENTUyBjbGFzcyBpZiB0aGUgaXRlbVxuICAgICAqIGlzIHNlbGVjdGVkLCBhbmQgcmVtb3ZlZCBpdCBpZiBub3Qgc2VsZWN0ZWQuXG4gICAgICpcbiAgICAgKiBAcGFyYW0ge0hUTUxFbGVtZW50fSBpdGVtIC0gVGhlIGl0ZW0gd2hvc2Ugc2VsZWN0aW9uIHN0YXRlIGhhcyBjaGFuZ2VkLlxuICAgICAqIEBwYXJhbSB7Ym9vbGVhbn0gc2VsZWN0ZWQgLSBUcnVlIGlmIHRoZSBpdGVtIGlzIHNlbGVjdGVkLCBmYWxzZSBpZiBub3QuXG4gICAgICovXG4gICAgW3N5bWJvbHMuaXRlbVNlbGVjdGVkXShpdGVtLCBzZWxlY3RlZCkge1xuICAgICAgaWYgKHN1cGVyW3N5bWJvbHMuaXRlbVNlbGVjdGVkXSkgeyBzdXBlcltzeW1ib2xzLml0ZW1TZWxlY3RlZF0oaXRlbSwgc2VsZWN0ZWQpOyB9XG4gICAgICB0b2dnbGVDbGFzcyhpdGVtLCAnc2VsZWN0ZWQnLCBzZWxlY3RlZCk7XG4gICAgfVxuXG4gICAgLyoqXG4gICAgICogVGhlIGN1cnJlbnQgc2V0IG9mIGl0ZW1zIGluIHRoZSBsaXN0LiBTZWUgdGhlIHRvcC1sZXZlbCBkb2N1bWVudGF0aW9uIGZvclxuICAgICAqIG1peGluIGZvciBhIGRlc2NyaXB0aW9uIG9mIGhvdyBpdGVtcyBkaWZmZXIgZnJvbSBwbGFpbiBjb250ZW50LlxuICAgICAqXG4gICAgICogQHR5cGUge0hUTUxFbGVtZW50W119XG4gICAgICovXG4gICAgZ2V0IGl0ZW1zKCkge1xuICAgICAgbGV0IGl0ZW1zO1xuICAgICAgaWYgKHRoaXNbaXRlbXNTeW1ib2xdID09IG51bGwpIHtcbiAgICAgICAgaXRlbXMgPSBmaWx0ZXJBdXhpbGlhcnlFbGVtZW50cyh0aGlzLmNvbnRlbnQpO1xuICAgICAgICAvLyBOb3RlOiB0ZXN0IGZvciAqZXF1YWxpdHkqIHdpdGggbnVsbDsgZG9uJ3QgdHJlYXQgdW5kZWZpbmVkIGFzIGEgbWF0Y2guXG4gICAgICAgIGlmICh0aGlzW2l0ZW1zU3ltYm9sXSA9PT0gbnVsbCkge1xuICAgICAgICAgIC8vIE1lbW9pemUgdGhlIHNldCBvZiBpdGVtcy5cbiAgICAgICAgICB0aGlzW2l0ZW1zU3ltYm9sXSA9IGl0ZW1zO1xuICAgICAgICB9XG4gICAgICB9IGVsc2Uge1xuICAgICAgICAvLyBSZXR1cm4gdGhlIG1lbW9pemVkIGl0ZW1zLlxuICAgICAgICBpdGVtcyA9IHRoaXNbaXRlbXNTeW1ib2xdO1xuICAgICAgfVxuICAgICAgcmV0dXJuIGl0ZW1zO1xuICAgIH1cblxuICAgIC8qKlxuICAgICAqIFRoaXMgbWV0aG9kIGlzIGludm9rZWQgd2hlbiB0aGUgdW5kZXJseWluZyBjb250ZW50cyBjaGFuZ2UuIEl0IGlzIGFsc29cbiAgICAgKiBpbnZva2VkIG9uIGNvbXBvbmVudCBpbml0aWFsaXphdGlvbiDigJMgc2luY2UgdGhlIGl0ZW1zIGhhdmUgXCJjaGFuZ2VkXCIgZnJvbVxuICAgICAqIGJlaW5nIG5vdGhpbmcuXG4gICAgICovXG4gICAgW3N5bWJvbHMuaXRlbXNDaGFuZ2VkXSgpIHtcbiAgICAgIGlmIChzdXBlcltzeW1ib2xzLml0ZW1zQ2hhbmdlZF0pIHsgc3VwZXJbc3ltYm9scy5pdGVtc0NoYW5nZWRdKCk7IH1cblxuICAgICAgLy8gUGVyZm9ybSBwZXItaXRlbSBpbml0aWFsaXphdGlvbi5cbiAgICAgIEFycmF5LnByb3RvdHlwZS5mb3JFYWNoLmNhbGwodGhpcy5pdGVtcywgaXRlbSA9PiB7XG4gICAgICAgIGlmICghaXRlbVtpdGVtSW5pdGlhbGl6ZWRTeW1ib2xdKSB7XG4gICAgICAgICAgdGhpc1tzeW1ib2xzLml0ZW1BZGRlZF0oaXRlbSk7XG4gICAgICAgICAgaXRlbVtpdGVtSW5pdGlhbGl6ZWRTeW1ib2xdID0gdHJ1ZTtcbiAgICAgICAgfVxuICAgICAgfSk7XG5cbiAgICAgIHRoaXMuZGlzcGF0Y2hFdmVudChuZXcgQ3VzdG9tRXZlbnQoJ2l0ZW1zLWNoYW5nZWQnKSk7XG4gICAgfVxuXG4gICAgLyoqXG4gICAgICogRmlyZXMgd2hlbiB0aGUgaXRlbXMgaW4gdGhlIGxpc3QgY2hhbmdlLlxuICAgICAqXG4gICAgICogQG1lbWJlcm9mIENvbnRlbnRJdGVtc1xuICAgICAqIEBldmVudCBpdGVtcy1jaGFuZ2VkXG4gICAgICovXG4gIH1cblxuICByZXR1cm4gQ29udGVudEl0ZW1zO1xufTtcblxuXG4vLyBSZXR1cm4gdGhlIGdpdmVuIGVsZW1lbnRzLCBmaWx0ZXJpbmcgb3V0IGF1eGlsaWFyeSBlbGVtZW50cyB0aGF0IGFyZW4ndFxuLy8gdHlwaWNhbGx5IHZpc2libGUuIEl0ZW1zIHdoaWNoIGFyZSBub3QgZWxlbWVudHMgYXJlIHJldHVybmVkIGFzIGlzLlxuZnVuY3Rpb24gZmlsdGVyQXV4aWxpYXJ5RWxlbWVudHMoaXRlbXMpIHtcbiAgY29uc3QgYXV4aWxpYXJ5VGFncyA9IFtcbiAgICAnbGluaycsXG4gICAgJ3NjcmlwdCcsXG4gICAgJ3N0eWxlJyxcbiAgICAndGVtcGxhdGUnXG4gIF07XG4gIHJldHVybiBbXS5maWx0ZXIuY2FsbChpdGVtcywgZnVuY3Rpb24oaXRlbSkge1xuICAgIHJldHVybiAhaXRlbS5sb2NhbE5hbWUgfHwgYXV4aWxpYXJ5VGFncy5pbmRleE9mKGl0ZW0ubG9jYWxOYW1lKSA8IDA7XG4gIH0pO1xufVxuIiwiaW1wb3J0IG1pY3JvdGFzayBmcm9tICcuL21pY3JvdGFzayc7XG5cblxuLyogRXhwb3J0ZWQgZnVuY3Rpb24gZXh0ZW5kcyBhIGJhc2UgY2xhc3Mgd2l0aCBEaXN0cmlidXRlZENoaWxkcmVuQ29udGVudC4gKi9cbmV4cG9ydCBkZWZhdWx0IChiYXNlKSA9PiB7XG5cbiAgLyoqXG4gICAqIE1peGluIHdoaWNoIGRlZmluZXMgYSBjb21wb25lbnQncyBjb250ZW50IGFzIGl0cyBjaGlsZHJlbiwgZXhwYW5kaW5nIGFueVxuICAgKiBub2RlcyBkaXN0cmlidXRlZCB0byB0aGUgY29tcG9uZW50J3Mgc2xvdHMuXG4gICAqXG4gICAqIFRoaXMgYWxzbyBwcm92aWRlcyBub3RpZmljYXRpb24gb2YgY2hhbmdlcyB0byBhIGNvbXBvbmVudCdzIGNvbnRlbnQuIEl0XG4gICAqIHdpbGwgaW52b2tlIGEgYGNvbnRlbnRDaGFuZ2VkYCBtZXRob2Qgd2hlbiB0aGUgY29tcG9uZW50IGlzIGZpcnN0XG4gICAqIGluc3RhbnRpYXRlZCwgYW5kIHdoZW5ldmVyIGl0cyBkaXN0cmlidXRlZCBjaGlsZHJlbiBjaGFuZ2UuIFRoaXMgaXMgYW5cbiAgICogZWFzeSB3YXkgdG8gc2F0aXNmeSB0aGUgR29sZCBTdGFuZGFyZCBjaGVja2xpc3QgaXRlbSBmb3IgbW9uaXRvcmluZ1xuICAgKiBbQ29udGVudCBDaGFuZ2VzXShodHRwczovL2dpdGh1Yi5jb20vd2ViY29tcG9uZW50cy9nb2xkLXN0YW5kYXJkL3dpa2kvQ29udGVudC1DaGFuZ2VzKS5cbiAgICpcbiAgICogRXhhbXBsZTpcbiAgICpcbiAgICogYGBgXG4gICAqIGxldCBiYXNlID0gRGlzdHJpYnV0ZWRDaGlsZHJlbkNvbnRlbnRNaXhpbihEaXN0cmlidXRlZENoaWxkcmVuTWl4aW4oSFRNTEVsZW1lbnQpKTtcbiAgICogY2xhc3MgQ291bnRpbmdFbGVtZW50IGV4dGVuZHMgYmFzZSB7XG4gICAqXG4gICAqICAgY29uc3RydWN0b3IoKSB7XG4gICAqICAgICBzdXBlcigpO1xuICAgKiAgICAgbGV0IHJvb3QgPSB0aGlzLmF0dGFjaFNoYWRvdyh7IG1vZGU6ICdvcGVuJyB9KTtcbiAgICogICAgIHJvb3QuaW5uZXJIVE1MID0gYDxzbG90Pjwvc2xvdD5gO1xuICAgKiAgIH1cbiAgICpcbiAgICogICBjb250ZW50Q2hhbmdlZCgpIHtcbiAgICogICAgIC8vIENvdW50IHRoZSBjb21wb25lbnQncyBjaGlsZHJlbiwgYm90aCBpbml0aWFsbHkgYW5kIHdoZW4gY2hhbmdlZC5cbiAgICogICAgIHRoaXMuY291bnQgPSB0aGlzLmRpc3RyaWJ1dGVkQ2hpbGRyZW4ubGVuZ3RoO1xuICAgKiAgIH1cbiAgICpcbiAgICogfVxuICAgKiBgYGBcbiAgICpcbiAgICogTm90ZSB0aGF0IGNvbnRlbnQgY2hhbmdlIGRldGVjdGlvbiBkZXBlbmRzIHVwb24gdGhlIGVsZW1lbnQgaGF2aW5nIGF0IGxlYXN0XG4gICAqIG9uZSBgc2xvdGAgZWxlbWVudCBpbiBpdHMgc2hhZG93IHN1YnRyZWUuXG4gICAqXG4gICAqIFRoaXMgbWl4aW4gaXMgaW50ZW5kZWQgZm9yIHVzZSB3aXRoIHRoZVxuICAgKiBbRGlzdHJpYnV0ZWRDaGlsZHJlbk1peGluXShEaXN0cmlidXRlZENoaWxkcmVuTWl4aW4ubWQpLiBTZWUgdGhhdCBtaXhpbiBmb3JcbiAgICogYSBkaXNjdXNzaW9uIG9mIGhvdyB0aGF0IHdvcmtzLiBUaGlzIERpc3RyaWJ1dGVkQ2hpbGRyZW5Db250ZW50TWl4aW5cbiAgICogcHJvdmlkZXMgYW4gZWFzeSB3YXkgb2YgZGVmaW5pbmcgdGhlIFwiY29udGVudFwiIG9mIGEgY29tcG9uZW50IGFzIHRoZVxuICAgKiBjb21wb25lbnQncyBkaXN0cmlidXRlZCBjaGlsZHJlbi4gVGhhdCBpbiB0dXJuIGxldHMgbWl4aW5zIGxpa2VcbiAgICogW0NvbnRlbnRJdGVtc01peGluXShDb250ZW50SXRlbXNNaXhpbi5tZCkgbWFuaXB1bGF0ZSB0aGUgY2hpbGRyZW4gYXMgbGlzdFxuICAgKiBpdGVtcy5cbiAgICovXG4gIGNsYXNzIERpc3RyaWJ1dGVkQ2hpbGRyZW5Db250ZW50IGV4dGVuZHMgYmFzZSB7XG5cbiAgICBjb25zdHJ1Y3RvcigpIHtcbiAgICAgIHN1cGVyKCk7XG5cbiAgICAgIGlmICh0aGlzLnNoYWRvd1Jvb3QpIHtcbiAgICAgICAgLy8gTGlzdGVuIHRvIGNoYW5nZXMgb24gYWxsIHNsb3RzLlxuICAgICAgICBjb25zdCBzbG90cyA9IHRoaXMuc2hhZG93Um9vdC5xdWVyeVNlbGVjdG9yQWxsKCdzbG90Jyk7XG4gICAgICAgIHNsb3RzLmZvckVhY2goc2xvdCA9PiBzbG90LmFkZEV2ZW50TGlzdGVuZXIoJ3Nsb3RjaGFuZ2UnLCBldmVudCA9PiB7XG4gICAgICAgICAgdGhpcy5jb250ZW50Q2hhbmdlZCgpO1xuICAgICAgICB9KSk7XG4gICAgICB9XG5cbiAgICAgIC8vIE1ha2UgYW4gaW5pdGlhbCBjYWxsIHRvIGNvbnRlbnRDaGFuZ2VkKCkgc28gdGhhdCB0aGUgY29tcG9uZW50IGNhbiBkb1xuICAgICAgLy8gaW5pdGlhbGl6YXRpb24gdGhhdCBpdCBub3JtYWxseSBkb2VzIHdoZW4gY29udGVudCBjaGFuZ2VzLlxuICAgICAgLy9cbiAgICAgIC8vIFRoaXMgd2lsbCBpbnZva2UgY29udGVudENoYW5nZWQoKSBoYW5kbGVycyBpbiBvdGhlciBtaXhpbnMuIEluIG9yZGVyXG4gICAgICAvLyB0aGF0IHRob3NlIG1peGlucyBoYXZlIGEgY2hhbmNlIHRvIGNvbXBsZXRlIHRoZWlyIG93biBpbml0aWFsaXphdGlvbixcbiAgICAgIC8vIHdlIGFkZCB0aGUgY29udGVudENoYW5nZWQoKSBjYWxsIHRvIHRoZSBtaWNyb3Rhc2sgcXVldWUuXG4gICAgICBtaWNyb3Rhc2soKCkgPT4gdGhpcy5jb250ZW50Q2hhbmdlZCgpKTtcbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBJbnZva2VkIHdoZW4gdGhlIGNvbnRlbnRzIG9mIHRoZSBjb21wb25lbnQgKGluY2x1ZGluZyBkaXN0cmlidXRlZFxuICAgICAqIGNoaWxkcmVuKSBoYXZlIGNoYW5nZWQuXG4gICAgICpcbiAgICAgKiBUaGlzIG1ldGhvZCBpcyBhbHNvIGludm9rZWQgd2hlbiBhIGNvbXBvbmVudCBpcyBmaXJzdCBpbnN0YW50aWF0ZWQ7IHRoZVxuICAgICAqIGNvbnRlbnRzIGhhdmUgZXNzZW50aWFsbHkgXCJjaGFuZ2VkXCIgZnJvbSBiZWluZyBub3RoaW5nLiBUaGlzIGFsbG93cyB0aGVcbiAgICAgKiBjb21wb25lbnQgdG8gcGVyZm9ybSBpbml0aWFsIHByb2Nlc3Npbmcgb2YgaXRzIGNoaWxkcmVuLlxuICAgICAqL1xuICAgIGNvbnRlbnRDaGFuZ2VkKCkge1xuICAgICAgaWYgKHN1cGVyLmNvbnRlbnRDaGFuZ2VkKSB7IHN1cGVyLmNvbnRlbnRDaGFuZ2VkKCk7IH1cbiAgICAgIGNvbnN0IGV2ZW50ID0gbmV3IEN1c3RvbUV2ZW50KCdjb250ZW50LWNoYW5nZWQnKTtcbiAgICAgIHRoaXMuZGlzcGF0Y2hFdmVudChldmVudCk7XG4gICAgfVxuXG4gICAgLyoqXG4gICAgICogVGhlIGNvbnRlbnQgb2YgdGhpcyBjb21wb25lbnQsIGRlZmluZWQgdG8gYmUgdGhlIGZsYXR0ZW5lZCBhcnJheSBvZlxuICAgICAqIGNoaWxkcmVuIGRpc3RyaWJ1dGVkIHRvIHRoZSBjb21wb25lbnQuXG4gICAgICpcbiAgICAgKiBAdHlwZSB7SFRNTEVsZW1lbnRbXX1cbiAgICAgKi9cbiAgICBnZXQgY29udGVudCgpIHtcbiAgICAgIGNvbnN0IGRpc3RyaWJ1dGVkQ2hpbGRyZW4gPSB0aGlzLmRpc3RyaWJ1dGVkQ2hpbGRyZW47XG4gICAgICBpZiAodHlwZW9mIGRpc3RyaWJ1dGVkQ2hpbGRyZW4gPT09ICd1bmRlZmluZWQnKSB7XG4gICAgICAgIGNvbnNvbGUud2FybihgRGlzdHJpYnV0ZWRDaGlsZHJlbkNvbnRlbnRNaXhpbiBleHBlY3RzIHRoZSBjb21wb25lbnQgdG8gZGVmaW5lIGEgXCJkaXN0cmlidXRlZENoaWxkcmVuXCIgcHJvcGVydHkuYCk7XG4gICAgICB9XG4gICAgICByZXR1cm4gZGlzdHJpYnV0ZWRDaGlsZHJlbjtcbiAgICB9XG4gICAgc2V0IGNvbnRlbnQodmFsdWUpIHtcbiAgICAgIGlmICgnY29udGVudCcgaW4gYmFzZS5wcm90b3R5cGUpIHsgc3VwZXIuY29udGVudCA9IHZhbHVlOyB9XG4gICAgICAvLyBUT0RPOiBTZXQgdGhlIGNoaWxkcmVuIHRvIHRoZSBnaXZlbiB2YWx1ZSAod2hpY2ggc2hvdWxkIGJlIGFuIGFycmF5IG9mXG4gICAgICAvLyBlbGVtZW50cyk/XG4gICAgfVxuXG4gICAgLyoqXG4gICAgICogVGhpcyBldmVudCBpcyByYWlzZWQgd2hlbiB0aGUgY29tcG9uZW50J3MgY29udGVudHMgKGluY2x1ZGluZyBkaXN0cmlidXRlZFxuICAgICAqIGNoaWxkcmVuKSBoYXZlIGNoYW5nZWQuXG4gICAgICpcbiAgICAgKiBAbWVtYmVyb2YgRGlzdHJpYnV0ZWRDaGlsZHJlbkNvbnRlbnRcbiAgICAgKiBAZXZlbnQgY29udGVudC1jaGFuZ2VkXG4gICAgICovXG4gIH1cblxuICByZXR1cm4gRGlzdHJpYnV0ZWRDaGlsZHJlbkNvbnRlbnQ7XG59O1xuIiwiLyogRXhwb3J0ZWQgZnVuY3Rpb24gZXh0ZW5kcyBhIGJhc2UgY2xhc3Mgd2l0aCBEaXN0cmlidXRlZENoaWxkcmVuLiAqL1xuZXhwb3J0IGRlZmF1bHQgKGJhc2UpID0+IHtcblxuICAvKipcbiAgICogTWl4aW4gd2hpY2ggZGVmaW5lcyBoZWxwZXJzIGZvciBhY2Nlc3NpbmcgYSBjb21wb25lbnQncyBkaXN0cmlidXRlZFxuICAgKiBjaGlsZHJlbiBhcyBhIGZsYXR0ZW5lZCBhcnJheSBvciBzdHJpbmcuXG4gICAqXG4gICAqIFRoZSBzdGFuZGFyZCBET00gQVBJIHByb3ZpZGVzIHNldmVyYWwgd2F5cyBvZiBhY2Nlc3NpbmcgY2hpbGQgY29udGVudDpcbiAgICogYGNoaWxkcmVuYCwgYGNoaWxkTm9kZXNgLCBhbmQgYHRleHRDb250ZW50YC4gTm9uZSBvZiB0aGVzZSBmdW5jdGlvbnMgYXJlXG4gICAqIFNoYWRvdyBET00gYXdhcmUuIFRoaXMgbWl4aW4gZGVmaW5lcyB2YXJpYXRpb25zIG9mIHRob3NlIGZ1bmN0aW9ucyB0aGF0XG4gICAqICphcmUqIFNoYWRvdyBET00gYXdhcmUuXG4gICAqXG4gICAqIEV4YW1wbGU6IHlvdSBjcmVhdGUgYSBjb21wb25lbnQgYDxjb3VudC1jaGlsZHJlbj5gIHRoYXQgZGlzcGxheXMgYSBudW1iZXJcbiAgICogZXF1YWwgdG8gdGhlIG51bWJlciBvZiBjaGlsZHJlbiBwbGFjZWQgaW5zaWRlIHRoYXQgY29tcG9uZW50LiBJZiBzb21lb25lXG4gICAqIGluc3RhbnRpYXRlcyB5b3VyIGNvbXBvbmVudCBsaWtlOlxuICAgKlxuICAgKiAgICAgPGNvdW50LWNoaWxkcmVuPlxuICAgKiAgICAgICA8ZGl2PjwvZGl2PlxuICAgKiAgICAgICA8ZGl2PjwvZGl2PlxuICAgKiAgICAgICA8ZGl2PjwvZGl2PlxuICAgKiAgICAgPC9jb3VudC1jaGlsZHJlbj5cbiAgICpcbiAgICogVGhlbiB0aGUgY29tcG9uZW50IHNob3VsZCBzaG93IFwiM1wiLCBiZWNhdXNlIHRoZXJlIGFyZSB0aHJlZSBjaGlsZHJlbi4gVG9cbiAgICogY2FsY3VsYXRlIHRoZSBudW1iZXIgb2YgY2hpbGRyZW4sIHRoZSBjb21wb25lbnQgY2FuIGp1c3QgY2FsY3VsYXRlXG4gICAqIGB0aGlzLmNoaWxkcmVuLmxlbmd0aGAuIEhvd2V2ZXIsIHN1cHBvc2Ugc29tZW9uZSBpbnN0YW50aWF0ZXMgeW91clxuICAgKiBjb21wb25lbnQgaW5zaWRlIG9uZSBvZiB0aGVpciBvd24gY29tcG9uZW50cywgYW5kIHB1dHMgYSBgPHNsb3Q+YCBlbGVtZW50XG4gICAqIGluc2lkZSB5b3VyIGNvbXBvbmVudDpcbiAgICpcbiAgICogICAgIDxjb3VudC1jaGlsZHJlbj5cbiAgICogICAgICAgPHNsb3Q+PC9zbG90PlxuICAgKiAgICAgPC9jb3VudC1jaGlsZHJlbj5cbiAgICpcbiAgICogSWYgeW91ciBjb21wb25lbnQgb25seSBsb29rcyBhdCBgdGhpcy5jaGlsZHJlbmAsIGl0IHdpbGwgYWx3YXlzIHNlZSBleGFjdGx5XG4gICAqIG9uZSBjaGlsZCDigJTCoHRoZSBgPHNsb3Q+YCBlbGVtZW50LiBCdXQgdGhlIHVzZXIgbG9va2luZyBhdCB0aGUgcGFnZSB3aWxsXG4gICAqICpzZWUqIGFueSBub2RlcyBkaXN0cmlidXRlZCB0byB0aGF0IHNsb3QuIFRvIG1hdGNoIHdoYXQgdGhlIHVzZXIgc2VlcywgeW91clxuICAgKiBjb21wb25lbnQgc2hvdWxkIGV4cGFuZCBhbnkgYDxzbG90PmAgZWxlbWVudHMgaXQgY29udGFpbnMuXG4gICAqXG4gICAqIFRoYXQgaXMgdGhlIHByb2JsZW0gdGhpcyBtaXhpbiBzb2x2ZXMuIEFmdGVyIGFwcGx5aW5nIHRoaXMgbWl4aW4sIHlvdXJcbiAgICogY29tcG9uZW50IGNvZGUgaGFzIGFjY2VzcyB0byBgdGhpcy5kaXN0cmlidXRlZENoaWxkcmVuYCwgd2hvc2UgYGxlbmd0aGBcbiAgICogd2lsbCByZXR1cm4gdGhlIHRvdGFsIG51bWJlciBvZiBhbGwgY2hpbGRyZW4gZGlzdHJpYnV0ZWQgdG8geW91ciBjb21wb25lbnRcbiAgICogaW4gdGhlIGNvbXBvc2VkIHRyZWUuXG4gICAqXG4gICAqIE5vdGU6IFRoZSBsYXRlc3QgQ3VzdG9tIEVsZW1lbnRzIEFQSSBkZXNpZ24gY2FsbHMgZm9yIGEgbmV3IGZ1bmN0aW9uLFxuICAgKiBgZ2V0QXNzaWduZWROb2Rlc2AgdGhhdCB0YWtlcyBhbiBvcHRpb25hbCBgZGVlcGAgcGFyYW1ldGVyLCB0aGF0IHdpbGwgc29sdmVcbiAgICogdGhpcyBwcm9ibGVtIGF0IHRoZSBBUEkgbGV2ZWwuXG4gICAqL1xuICBjbGFzcyBEaXN0cmlidXRlZENoaWxkcmVuIGV4dGVuZHMgYmFzZSB7XG5cbiAgICAvKipcbiAgICAgKiBBbiBpbi1vcmRlciBjb2xsZWN0aW9uIG9mIGRpc3RyaWJ1dGVkIGNoaWxkcmVuLCBleHBhbmRpbmcgYW55IHNsb3RcbiAgICAgKiBlbGVtZW50cy4gTGlrZSB0aGUgc3RhbmRhcmQgY2hpbGRyZW4gcHJvcGVydHksIHRoaXMgc2tpcHMgdGV4dCBub2Rlcy5cbiAgICAgKlxuICAgICAqIEB0eXBlIHtIVE1MRWxlbWVudFtdfVxuICAgICAqL1xuICAgIGdldCBkaXN0cmlidXRlZENoaWxkcmVuKCkge1xuICAgICAgcmV0dXJuIGV4cGFuZENvbnRlbnRFbGVtZW50cyh0aGlzLmNoaWxkcmVuLCBmYWxzZSk7XG4gICAgfVxuXG4gICAgLyoqXG4gICAgICogQW4gaW4tb3JkZXIgY29sbGVjdGlvbiBvZiBkaXN0cmlidXRlZCBjaGlsZCBub2RlcywgZXhwYW5kaW5nIGFueSBzbG90XG4gICAgICogZWxlbWVudHMuIExpa2UgdGhlIHN0YW5kYXJkIGNoaWxkTm9kZXMgcHJvcGVydHksIHRoaXMgaW5jbHVkZXMgdGV4dFxuICAgICAqIG5vZGVzLlxuICAgICAqXG4gICAgICogQHR5cGUge05vZGVbXX1cbiAgICAgKi9cbiAgICBnZXQgZGlzdHJpYnV0ZWRDaGlsZE5vZGVzKCkge1xuICAgICAgcmV0dXJuIGV4cGFuZENvbnRlbnRFbGVtZW50cyh0aGlzLmNoaWxkTm9kZXMsIHRydWUpO1xuICAgIH1cblxuICAgIC8qKlxuICAgICAqIFRoZSBjb25jYXRlbmF0ZWQgdGV4dCBjb250ZW50IG9mIGFsbCBkaXN0cmlidXRlZCBjaGlsZCBub2RlcywgZXhwYW5kaW5nXG4gICAgICogYW55IHNsb3QgZWxlbWVudHMuXG4gICAgICpcbiAgICAgKiBAdHlwZSB7c3RyaW5nfVxuICAgICAqL1xuICAgIGdldCBkaXN0cmlidXRlZFRleHRDb250ZW50KCkge1xuICAgICAgY29uc3Qgc3RyaW5ncyA9IHRoaXMuZGlzdHJpYnV0ZWRDaGlsZE5vZGVzLm1hcChmdW5jdGlvbihjaGlsZCkge1xuICAgICAgICByZXR1cm4gY2hpbGQudGV4dENvbnRlbnQ7XG4gICAgICB9KTtcbiAgICAgIHJldHVybiBzdHJpbmdzLmpvaW4oJycpO1xuICAgIH1cblxuICB9XG5cbiAgcmV0dXJuIERpc3RyaWJ1dGVkQ2hpbGRyZW47XG59O1xuXG5cbi8qXG4gKiBHaXZlbiBhIGFycmF5IG9mIG5vZGVzLCByZXR1cm4gYSBuZXcgYXJyYXkgd2l0aCBhbnkgY29udGVudCBlbGVtZW50cyBleHBhbmRlZFxuICogdG8gdGhlIG5vZGVzIGRpc3RyaWJ1dGVkIHRvIHRoYXQgY29udGVudCBlbGVtZW50LiBUaGlzIHJ1bGUgaXMgYXBwbGllZFxuICogcmVjdXJzaXZlbHkuXG4gKlxuICogSWYgaW5jbHVkZVRleHROb2RlcyBpcyB0cnVlLCB0ZXh0IG5vZGVzIHdpbGwgYmUgaW5jbHVkZWQsIGFzIGluIHRoZVxuICogc3RhbmRhcmQgY2hpbGROb2RlcyBwcm9wZXJ0eTsgYnkgZGVmYXVsdCwgdGhpcyBza2lwcyB0ZXh0IG5vZGVzLCBsaWtlIHRoZVxuICogc3RhbmRhcmQgY2hpbGRyZW4gcHJvcGVydHkuXG4gKi9cbmZ1bmN0aW9uIGV4cGFuZENvbnRlbnRFbGVtZW50cyhub2RlcywgaW5jbHVkZVRleHROb2Rlcykge1xuICBjb25zdCBleHBhbmRlZCA9IEFycmF5LnByb3RvdHlwZS5tYXAuY2FsbChub2Rlcywgbm9kZSA9PiB7XG4gICAgLy8gV2Ugd2FudCB0byBzZWUgaWYgdGhlIG5vZGUgaXMgYW4gaW5zdGFuY2VvZiBIVE1MU2xvdEVMZW1lbnQsIGJ1dFxuICAgIC8vIHRoYXQgY2xhc3Mgd29uJ3QgZXhpc3QgaWYgdGhlIGJyb3dzZXIgdGhhdCBkb2Vzbid0IHN1cHBvcnQgbmF0aXZlXG4gICAgLy8gU2hhZG93IERPTSBhbmQgaWYgdGhlIFNoYWRvdyBET00gcG9seWZpbGwgaGFzbid0IGJlZW4gbG9hZGVkLiBJbnN0ZWFkLFxuICAgIC8vIHdlIGRvIGEgc2ltcGxpc3RpYyBjaGVjayB0byBzZWUgaWYgdGhlIHRhZyBuYW1lIGlzIFwic2xvdFwiLlxuICAgIGNvbnN0IGlzU2xvdCA9IHR5cGVvZiBIVE1MU2xvdEVsZW1lbnQgIT09ICd1bmRlZmluZWQnID9cbiAgICAgIG5vZGUgaW5zdGFuY2VvZiBIVE1MU2xvdEVsZW1lbnQgOlxuICAgICAgbm9kZS5sb2NhbE5hbWUgPT09ICdzbG90JztcbiAgICBpZiAoaXNTbG90KSB7XG4gICAgICAvLyBVc2UgdGhlIG5vZGVzIGFzc2lnbmVkIHRvIHRoaXMgbm9kZSBpbnN0ZWFkLlxuICAgICAgY29uc3QgYXNzaWduZWROb2RlcyA9IG5vZGUuYXNzaWduZWROb2Rlcyh7IGZsYXR0ZW46IHRydWUgfSk7XG4gICAgICByZXR1cm4gYXNzaWduZWROb2RlcyA/XG4gICAgICAgIGV4cGFuZENvbnRlbnRFbGVtZW50cyhhc3NpZ25lZE5vZGVzLCBpbmNsdWRlVGV4dE5vZGVzKSA6XG4gICAgICAgIFtdO1xuICAgIH0gZWxzZSBpZiAobm9kZSBpbnN0YW5jZW9mIEhUTUxFbGVtZW50KSB7XG4gICAgICAvLyBQbGFpbiBlbGVtZW50OyB1c2UgYXMgaXMuXG4gICAgICByZXR1cm4gW25vZGVdO1xuICAgIH0gZWxzZSBpZiAobm9kZSBpbnN0YW5jZW9mIFRleHQgJiYgaW5jbHVkZVRleHROb2Rlcykge1xuICAgICAgLy8gVGV4dCBub2RlLlxuICAgICAgcmV0dXJuIFtub2RlXTtcbiAgICB9IGVsc2Uge1xuICAgICAgLy8gQ29tbWVudCwgcHJvY2Vzc2luZyBpbnN0cnVjdGlvbiwgZXRjLjsgc2tpcC5cbiAgICAgIHJldHVybiBbXTtcbiAgICB9XG4gIH0pO1xuICBjb25zdCBmbGF0dGVuZWQgPSBbXS5jb25jYXQoLi4uZXhwYW5kZWQpO1xuICByZXR1cm4gZmxhdHRlbmVkO1xufVxuIiwiaW1wb3J0IGNyZWF0ZVN5bWJvbCBmcm9tICcuL2NyZWF0ZVN5bWJvbCc7XG5cblxuLy8gU3ltYm9scyBmb3IgcHJpdmF0ZSBkYXRhIG1lbWJlcnMgb24gYW4gZWxlbWVudC5cbmNvbnN0IHNlbGVjdGVkRnJhY3Rpb25TeW1ib2wgPSBjcmVhdGVTeW1ib2woJ3NlbGVjdGVkRnJhY3Rpb24nKTtcblxuXG4vKiBFeHBvcnRlZCBmdW5jdGlvbiBleHRlbmRzIGEgYmFzZSBjbGFzcyB3aXRoIEZyYWN0aW9uYWxTZWxlY3Rpb24uICovXG5leHBvcnQgZGVmYXVsdCBmdW5jdGlvbiBtaXhpbihiYXNlKSB7XG5cbiAgLyoqXG4gICAqIEFkZHMgc3VwcG9ydCBmb3IgZnJhY3Rpb25hbCBzZWxlY3Rpb246IHRyZWF0aW5nIGEgc2VsZWN0aW9uIGFzIGEgcmVhbFxuICAgKiBudW1iZXIgdGhhdCBjb21iaW5lcyBhbiBpbnRlZ2VyIHBvcnRpb24gKGFuIGluZGV4IGludG8gYSBsaXN0KSwgYW5kIGFcbiAgICogZnJhY3Rpb24gKGluZGljYXRpbmcgaG93IGZhciBvZiB0aGUgd2F5IHdlIGFyZSB0byB0aGUgbmV4dCBvciBwcmV2aW91c1xuICAgKiBpdGVtKS5cbiAgICpcbiAgICogVGhpcyBpcyB1c2VmdWwgaW4gY29tcG9uZW50cyB0aGF0IHN1cHBvcnQgaW5jcmVtZW50YWwgb3BlcmF0aW9ucyBkdXJpbmdcbiAgICogZHJhZ2dpbmcgYW5kIHN3aXBpbmcuIEV4YW1wbGU6IGEgY2Fyb3VzZWwgY29tcG9uZW50IGhhcyBzZXZlcmFsIGl0ZW1zLCBhbmQgdGhlXG4gICAqIGN1cnJlbnRseSBzZWxlY3RlZCBpdGVtIGlzIGl0ZW0gMy4gVGhlIHVzZXIgYmVnaW5zIHN3aXBpbmcgdG8gdGhlIGxlZnQsXG4gICAqIG1vdmluZyB0b3dhcmRzIHNlbGVjdGluZyBpdGVtIDQuIEhhbGZ3YXkgdGhyb3VnaCB0aGlzIG9wZXJhdGlvbiwgdGhlXG4gICAqIGZyYWN0aW9uYWwgc2VsZWN0aW9uIHZhbHVlIGlzIDMuNS5cbiAgICpcbiAgICogVGhpcyB2YWx1ZSBwZXJtaXRzIGNvbW11bmljYXRpb24gYmV0d2VlbiBtaXhpbnMgbGlrZVxuICAgKiBbU3dpcGVEaXJlY3Rpb25NaXhpbl0oLi9Td2lwZURpcmVjdGlvbk1peGluLm1kKSBhbmRcbiAgICogW1RyYWNrcGFkRGlyZWN0aW9uTWl4aW5dKC4vVHJhY2twYWREaXJlY3Rpb25NaXhpbi5tZCksIHdoaWNoIGdlbmVyYXRlXG4gICAqIGZyYWN0aW9uYWwgc2VsZWN0aW9uIHZhbHVlcywgYW5kIG1peGlucyBsaWtlXG4gICAqIFtTZWxlY3Rpb25BbmltYXRpb25NaXhpbl0oLi9TZWxlY3Rpb25BbmltYXRpb25NaXhpbi5tZCksIHdoaWNoIGNhbiByZW5kZXJcbiAgICogc2VsZWN0aW9uIGF0IGEgZnJhY3Rpb25hbCB2YWx1ZS5cbiAgICovXG4gIGNsYXNzIEZyYWN0aW9uYWxTZWxlY3Rpb24gZXh0ZW5kcyBiYXNlIHtcblxuICAgIGNvbm5lY3RlZENhbGxiYWNrKCkge1xuICAgICAgaWYgKHN1cGVyLmNvbm5lY3RlZENhbGxiYWNrKSB7IHN1cGVyLmNvbm5lY3RlZENhbGxiYWNrKCk7IH1cbiAgICAgIHRoaXMuc2VsZWN0ZWRGcmFjdGlvbiA9IDA7XG4gICAgfVxuXG4gICAgLyoqXG4gICAgICogQSBmcmFjdGlvbmFsIHZhbHVlIGluZGljYXRpbmcgaG93IGZhciB0aGUgdXNlciBoYXMgY3VycmVudGx5IGFkdmFuY2VkIHRvXG4gICAgICogdGhlIG5leHQvcHJldmlvdXMgaXRlbS4gRS5nLiwgYSBgc2VsZWN0ZWRGcmFjdGlvbmAgb2YgMy41IGluZGljYXRlcyB0aGVcbiAgICAgKiB1c2VyIGlzIGhhbGZ3YXkgYmV0d2VlbiBpdGVtcyAzIGFuZCA0LlxuICAgICAqXG4gICAgICogQHR5cGUge251bWJlcn1cbiAgICAgKi9cbiAgICBnZXQgc2VsZWN0ZWRGcmFjdGlvbigpIHtcbiAgICAgIHJldHVybiB0aGlzW3NlbGVjdGVkRnJhY3Rpb25TeW1ib2xdO1xuICAgIH1cbiAgICBzZXQgc2VsZWN0ZWRGcmFjdGlvbih2YWx1ZSkge1xuICAgICAgdGhpc1tzZWxlY3RlZEZyYWN0aW9uU3ltYm9sXSA9IHZhbHVlO1xuICAgICAgaWYgKCdzZWxlY3RlZEZyYWN0aW9uJyBpbiBiYXNlLnByb3RvdHlwZSkgeyBzdXBlci5zZWxlY3RlZEZyYWN0aW9uID0gdmFsdWU7IH1cbiAgICAgIGNvbnN0IGV2ZW50ID0gbmV3IEN1c3RvbUV2ZW50KCdzZWxlY3RlZC1mcmFjdGlvbi1jaGFuZ2VkJyk7XG4gICAgICB0aGlzLmRpc3BhdGNoRXZlbnQoZXZlbnQpO1xuICAgIH1cblxuICB9XG5cbiAgcmV0dXJuIEZyYWN0aW9uYWxTZWxlY3Rpb247XG59XG5cblxubWl4aW4uaGVscGVycyA9IHtcblxuICAvKlxuICAgKiBEYW1wZW4gYSBzZWxlY3Rpb24gdGhhdCBnb2VzIHBhc3QgdGhlIGJlZ2lubmluZyBvciBlbmQgb2YgYSBsaXN0LiBUaGlzIGlzXG4gICAqIGdlbmVyYWxseSB1c2VkIHRvIHByb2R1Y2UgYSB2aXN1YWwgZWZmZWN0IG9mIHRlbnNpb24gYXMgdGhlIHVzZXIgdHJpZXMgdG9cbiAgICogZ28gZnVydGhlciBpbiBhIGRpcmVjdGlvbiB0aGF0IGhhcyBubyBtb3JlIGl0ZW1zLlxuICAgKlxuICAgKiBFeGFtcGxlOiBzdXBwb3NlIGBpdGVtQ291bnRgIGlzIDUsIGluZGljYXRpbmcgYSBsaXN0IG9mIDUgaXRlbXMuIFRoZSBpbmRleCBvZlxuICAgKiB0aGUgbGFzdCBpdGVtIGlzIDQuIElmIHRoZSBgc2VsZWN0aW9uYCBwYXJhbWV0ZXIgaXMgNC41LCB0aGUgdXNlciBpcyB0cnlpbmdcbiAgICogdG8gZ28gcGFzdCB0aGlzIGxhc3QgaXRlbS4gV2hlbiBhIGRhbXBpbmcgZnVuY3Rpb24gaXMgYXBwbGllZCwgdGhlIHJlc3VsdGluZ1xuICAgKiB2YWx1ZSB3aWxsIGJlIGxlc3MgdGhhbiA0LjUgKHRoZSBhY3R1YWwgdmFsdWUgd2lsbCBiZSA0LjI1KS4gV2hlbiB0aGlzXG4gICAqIHNlbGVjdGlvbiBzdGF0ZSBpcyByZW5kZXJlZCwgdGhlIHVzZXIgd2lsbCBzZWUgdGhhdCwgZWFjaCB1bml0IGRpc3RhbmNlIHRoZVxuICAgKiBkcmFnIHRyYXZlbHMgaGFzIGxlc3MgYW5kIGxlc3MgdmlzaWJsZSBlZmZlY3QuIFRoaXMgaXMgcGVyY2VpdmVkIGFzIHRlbnNpb24uXG4gICAqXG4gICAqIEBwYXJhbSB7bnVtYmVyfSBzZWxlY3Rpb24gLSBBIHJlYWwgbnVtYmVyIGluZGljYXRpbmcgYSBzZWxlY3Rpb24gcG9zaXRpb25cbiAgICogQHBhcmFtIHtudW1iZXJ9IGl0ZW1Db3VudCAtIEFuIGludGVnZXIgZm9yIHRoZSBudW1iZXIgb2YgaXRlbXMgaW4gdGhlIGxpc3RcbiAgICogQHJldHVybnMge251bWJlcn0gQSByZWFsIG51bWJlciByZXByZXNlbnRpbmcgdGhlIGRhbXBlZCBzZWxlY3Rpb24gdmFsdWUuXG4gICAqL1xuICBkYW1wZWRTZWxlY3Rpb24oc2VsZWN0aW9uLCBpdGVtQ291bnQpIHtcbiAgICBjb25zdCBib3VuZCA9IGl0ZW1Db3VudCAtIDE7XG4gICAgbGV0IGRhbXBlZDtcbiAgICBpZiAoc2VsZWN0aW9uIDwgMCkge1xuICAgICAgLy8gVHJ5aW5nIHRvIGdvIHBhc3QgYmVnaW5uaW5nIG9mIGxpc3QuIEFwcGx5IHRlbnNpb24gZnJvbSB0aGUgbGVmdCBlZGdlLlxuICAgICAgZGFtcGVkID0gLW1peGluLmhlbHBlcnMuZGFtcGluZygtc2VsZWN0aW9uKTtcbiAgICB9IGVsc2UgaWYgKHNlbGVjdGlvbiA+PSBib3VuZCkge1xuICAgICAgLy8gVHJ5aW5nIHRvIGdvIHBhc3QgZW5kIG9mIGxpc3QuIEFwcGx5IHRlbnNpb24gZnJvbSB0aGUgcmlnaHQgZWRnZS5cbiAgICAgIGRhbXBlZCA9IGJvdW5kICsgbWl4aW4uaGVscGVycy5kYW1waW5nKHNlbGVjdGlvbiAtIGJvdW5kKTtcbiAgICB9IGVsc2Uge1xuICAgICAgLy8gTm8gZGFtcGluZyByZXF1aXJlZC5cbiAgICAgIGRhbXBlZCA9IHNlbGVjdGlvbjtcbiAgICB9XG4gICAgcmV0dXJuIGRhbXBlZDtcbiAgfSxcblxuICAvKlxuICAgKiBDYWxjdWxhdGUgZGFtcGluZyBhcyBhIGZ1bmN0aW9uIG9mIHRoZSBkaXN0YW5jZSBwYXN0IHRoZSBtaW5pbXVtL21heGltdW1cbiAgICogdmFsdWVzLlxuICAgKlxuICAgKiBXZSB3YW50IHRvIGFzeW1wdG90aWNhbGx5IGFwcHJvYWNoIGFuIGFic29sdXRlIG1pbmltdW0gb2YgMSB1bml0XG4gICAqIGJlbG93L2Fib3ZlIHRoZSBhY3R1YWwgbWluaW11bS9tYXhpbXVtLiBUaGlzIHJlcXVpcmVzIGNhbGN1bGF0aW5nIGFcbiAgICogaHlwZXJib2xpYyBmdW5jdGlvbi5cbiAgICpcbiAgICogU2VlIGh0dHA6Ly93d3cud29sZnJhbWFscGhhLmNvbS9pbnB1dC8/aT15KyUzRCstMSUyRiUyOHglMkIxJTI5KyUyQisxXG4gICAqIGZvciB0aGUgb25lIHdlIHVzZS4gVGhlIG9ubHkgcG9ydGlvbiBvZiB0aGF0IGZ1bmN0aW9uIHdlIGNhcmUgYWJvdXQgaXMgd2hlblxuICAgKiB4IGlzIHplcm8gb3IgZ3JlYXRlci4gQW4gaW1wb3J0YW50IGNvbnNpZGVyYXRpb24gaXMgdGhhdCB0aGUgY3VydmUgYmVcbiAgICogdGFuZ2VudCB0byB0aGUgZGlhZ29uYWwgbGluZSB4PXkgYXQgKDAsIDApLiBUaGlzIGVuc3VyZXMgc21vb3RoIGNvbnRpbnVpdHlcbiAgICogd2l0aCB0aGUgbm9ybWFsIGRyYWcgYmVoYXZpb3IsIGluIHdoaWNoIHRoZSB2aXNpYmxlIHNsaWRpbmcgaXMgbGluZWFyIHdpdGhcbiAgICogdGhlIGRpc3RhbmNlIHRoZSB0b3VjaHBvaW50IGhhcyBiZWVuIGRyYWdnZWQuXG4gICAqL1xuICBkYW1waW5nKHgpIHtcbiAgICBjb25zdCB5ID0gKC0xIC8gKHggKyAxKSkgKyAxO1xuICAgIHJldHVybiB5O1xuICB9LFxuXG4gIC8qXG4gICAqIFJldHVybiB0aGUgY3VycmVudCBmcmFjdGlvbmFsIHNlbGVjdGlvbiB2YWx1ZSBmb3IgdGhlIGdpdmVuIGVsZW1lbnQuXG4gICAqXG4gICAqIFRoaXMgc2ltcGx5IGFkZHMgdGhlIGVsZW1lbnQncyBgc2VsZWN0ZWRJbmRleGAgYW5kIGBzZWxlY3RlZEZyYWN0aW9uYFxuICAgKiBwcm9wZXJ0aWVzLlxuICAgKlxuICAgKiBAcGFyYW0ge0hUTUxFbGVtZW50fSBlbGVtZW50IC0gQW4gZWxlbWVudCB0aGF0IHN1cHBvcnRzIHNlbGVjdGlvblxuICAgKi9cbiAgZWxlbWVudFNlbGVjdGlvbihlbGVtZW50KSB7XG4gICAgY29uc3Qgc2VsZWN0ZWRJbmRleCA9IGVsZW1lbnQuc2VsZWN0ZWRJbmRleDtcbiAgICBpZiAoc2VsZWN0ZWRJbmRleCA8IDApIHtcbiAgICAgIC8vIE5vIHNlbGVjdGlvblxuICAgICAgcmV0dXJuO1xuICAgIH1cbiAgICBjb25zdCBzZWxlY3RlZEZyYWN0aW9uID0gZWxlbWVudC5zZWxlY3RlZEZyYWN0aW9uIHx8IDA7XG4gICAgcmV0dXJuIHNlbGVjdGVkSW5kZXggKyBzZWxlY3RlZEZyYWN0aW9uO1xuICB9LFxuXG4gIC8qXG4gICAqIEJyZWFrcyBhIGZyYWN0aW9uYWwgc2VsZWN0aW9uIGludG8gaXRzIGludGVnZXIgYW5kIGZyYWN0aW9uYWwgcGFydHMuXG4gICAqXG4gICAqIEV4YW1wbGU6IGlmIHBhc3NlZCAzLjUsIHRoaXMgcmV0dXJucyB7IGluZGV4OiAzLCBmcmFjdGlvbjogNSB9LlxuICAgKlxuICAgKiBAcGFyYW0ge251bWJlcn0gc2VsZWN0aW9uIOKAk8KgQSByZWFsIG51bWJlciByZXByZXNlbnRpbmcgYSBzZWxlY3Rpb24gcG9pbnRcbiAgICogQHJldHVybnMge29iamVjdH0gLSBBbiBvYmplY3Qgd2l0aCBhbiBgaW5kZXhgIHByb3BlcnR5IGhvbGRpbmcgdGhlXG4gICAqIHNlbGVjdGlvbidzIGludGVnZXIgY29tcG9uZW50LCBhbmQgYSBgZnJhY3Rpb25gIHByb3BlcnR5IGhvbGRpbmcgdGhlXG4gICAqIHNlbGVjdGlvbidzIGZyYWN0aW9uYWwgY29tcG9uZW50LlxuICAgKi9cbiAgc2VsZWN0aW9uUGFydHMoc2VsZWN0aW9uKSB7XG4gICAgLy8gU3R1cGlkIElFIGRvZXNuJ3QgaGF2ZSBNYXRoLnRydW5jLlxuICAgIC8vIGNvbnN0IGluZGV4ID0gTWF0aC50cnVuYyhzZWxlY3Rpb24pO1xuICAgIGNvbnN0IGluZGV4ID0gc2VsZWN0aW9uIDwgMCA/IE1hdGguY2VpbChzZWxlY3Rpb24pIDogTWF0aC5mbG9vcihzZWxlY3Rpb24pO1xuICAgIGNvbnN0IGZyYWN0aW9uID0gc2VsZWN0aW9uIC0gaW5kZXg7XG4gICAgcmV0dXJuIHsgaW5kZXgsIGZyYWN0aW9uIH07XG4gIH0sXG5cbiAgLypcbiAgICogUmV0dXJucyBhIGZyYWN0aW9uYWwgc2VsZWN0aW9uIHBvaW50IGFmdGVyIGFjY291bnRpbmcgZm9yIHdyYXBwaW5nLCBlbnN1cmluZ1xuICAgKiB0aGF0IHRoZSBpbnRlZ2VyIHBvcnRpb24gb2YgdGhlIHNlbGVjdGlvbiBzdGF5cyBiZXR3ZWVuIDAgYW5kIGBpdGVtQ291bnRgLTEuXG4gICAqIFRoYXQgaXMsIHRoZSBpbnRlZ2VyIHBvcnRpb24gd2lsbCBhbHdheXMgYmUgYSB2YWxpZCBpbmRleCBpbnRvIHRoZSBsaXN0LlxuICAgKlxuICAgKiBFeGFtcGxlIG9mIHdyYXBwaW5nIHBhc3QgdGhlIGVuZCBvZiB0aGUgbGlzdDogaWYgYHNlbGVjdGlvbmAgaXMgNS41IGFuZFxuICAgKiBgaXRlbUNvdW50YCBpcyA1LCB0aGlzIHJldHVybnMgMC41LiBFeGFtcGxlIG9mIHdyYXBwaW5nIHBhc3QgdGhlIGJlZ2lubmluZyBvZlxuICAgKiB0aGUgbGlzdDogaWYgYHNlbGVjdGlvbmAgaXMgMC41IGFuZCBgaXRlbUNvdW50YCBpcyA1LCB0aGlzIHJldHVybnMgNC41LlxuICAgKlxuICAgKiBAcGFyYW0ge251bWJlcn0gc2VsZWN0aW9uIC0gQSByZWFsIG51bWJlciByZXByZXNlbnRpbmcgYSBzZWxlY3Rpb24gcG9pbnRcbiAgICogQHBhcmFtIHtudW1iZXJ9IGl0ZW1Db3VudCAtIFRoZSBudW1iZXIgb2YgaXRlbXMgaW4gdGhlIGxpc3RcbiAgICogQHJldHVybnMge251bWJlcn0gLSBUaGUgcmVzdWx0IG9mIHdyYXBwaW5nIHRoZSBzZWxlY3Rpb24gcG9pbnRcbiAgICovXG4gIHdyYXBwZWRTZWxlY3Rpb24oc2VsZWN0aW9uLCBpdGVtQ291bnQpIHtcbiAgICAvLyBIYW5kbGVzIHBvc3NpYmlsaXR5IG9mIG5lZ2F0aXZlIG1vZC5cbiAgICAvLyBTZWUgaHR0cDovL3N0YWNrb3ZlcmZsb3cuY29tL2EvMTg2MTgyNTAvNzY0NzJcbiAgICByZXR1cm4gKChzZWxlY3Rpb24gJSBpdGVtQ291bnQpICsgaXRlbUNvdW50KSAlIGl0ZW1Db3VudDtcbiAgfSxcblxuICAvKlxuICAgKiBSZXR1cm4gdGhlIHBhcnRzIG9mIGEgc2VsZWN0aW9uLCBmaXJzdCB3cmFwcGluZyBpZiBuZWNlc3NhcnkuXG4gICAqXG4gICAqIEBwYXJhbSB7bnVtYmVyfSBzZWxlY3Rpb24g4oCTIEEgcmVhbCBudW1iZXIgcmVwcmVzZW50aW5nIGEgc2VsZWN0aW9uIHBvaW50XG4gICAqIEBwYXJhbSB7bnVtYmVyfSBpdGVtQ291bnQgLSBUaGUgbnVtYmVyIG9mIGl0ZW1zIGluIHRoZSBsaXN0XG4gICAqIEBwYXJhbSB7Ym9vbGVhbn0gd3JhcCDigJMgVHJ1ZSBpZiB0aGUgc2VsZWN0aW9uIHNob3VsZCB3cmFwIHRvIHN0YXkgd2l0aGluIHRoZVxuICAgKiBsaXN0XG4gICAqIEByZXR1cm5zIHtvYmplY3R9IOKAkyBUaGUgcGFydHMgb2YgdGhlIHNlbGVjdGlvbiwgdXNpbmcgdGhlIHNhbWUgZm9ybWF0IGFzXG4gICAqIGBzZWxlY3Rpb25QYXJ0c2AuXG4gICAqL1xuICB3cmFwcGVkU2VsZWN0aW9uUGFydHMoc2VsZWN0aW9uLCBpdGVtQ291bnQsIHdyYXApIHtcbiAgICBpZiAod3JhcCkge1xuICAgICAgc2VsZWN0aW9uID0gbWl4aW4uaGVscGVycy53cmFwcGVkU2VsZWN0aW9uKHNlbGVjdGlvbiwgaXRlbUNvdW50KTtcbiAgICB9XG4gICAgcmV0dXJuIG1peGluLmhlbHBlcnMuc2VsZWN0aW9uUGFydHMoc2VsZWN0aW9uKTtcbiAgfVxuXG59O1xuIiwiaW1wb3J0IHNhZmVBdHRyaWJ1dGVzIGZyb20gJy4uLy4uL2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL3NhZmVBdHRyaWJ1dGVzJztcbmltcG9ydCBzeW1ib2xzIGZyb20gJy4uLy4uL2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL3N5bWJvbHMnO1xuXG5cbi8qIEV4cG9ydGVkIGZ1bmN0aW9uIGV4dGVuZHMgYSBiYXNlIGNsYXNzIHdpdGggUGxheUNvbnRyb2xzLiAqL1xuZXhwb3J0IGRlZmF1bHQgKGJhc2UpID0+IHtcblxuICAvKipcbiAgICogVGVtcGxhdGUgbWl4aW4gd2hpY2ggYWRkcyBidXR0b25zIGZvciBtYW5hZ2luZyBwbGF5YmFjayBvZiBhIHNsaWRlc2hvdyxcbiAgICogYXVkaW8gcGxheWxpc3QsIGV0Yy5cbiAgICpcbiAgICogVHlwaWNhbCB1c2FnZTpcbiAgICpcbiAgICogICAgIGNsYXNzIFNsaWRlc2hvd1dpdGhDb250cm9scyBleHRlbmRzIFBsYXlDb250cm9sc01peGluKFNsaWRlc2hvdykge31cbiAgICogICAgIGN1c3RvbUVsZW1lbnRzLmRlZmluZSgnc2xpZGVzaG93LXdpdGgtY29udHJvbHMnLCBTbGlkZXNob3dXaXRoQ29udHJvbHMpO1xuICAgKlxuICAgKi9cbiAgY2xhc3MgUGxheUNvbnRyb2xzIGV4dGVuZHMgYmFzZSB7XG5cbiAgICBjb25zdHJ1Y3RvcigpIHtcbiAgICAgIHN1cGVyKCk7XG4gICAgICB0aGlzLiQucHJldmlvdXNCdXR0b24uYWRkRXZlbnRMaXN0ZW5lcignY2xpY2snLCBldmVudCA9PiB7XG4gICAgICAgIHRoaXMuc2VsZWN0UHJldmlvdXMoKTtcbiAgICAgIH0pO1xuICAgICAgdGhpcy4kLnBsYXlCdXR0b24uYWRkRXZlbnRMaXN0ZW5lcignY2xpY2snLCBldmVudCA9PiB7XG4gICAgICAgIHRoaXMucGxheWluZyA9ICF0aGlzLnBsYXlpbmc7XG4gICAgICB9KTtcbiAgICAgIHRoaXMuJC5uZXh0QnV0dG9uLmFkZEV2ZW50TGlzdGVuZXIoJ2NsaWNrJywgZXZlbnQgPT4ge1xuICAgICAgICB0aGlzLnNlbGVjdE5leHQoKTtcbiAgICAgIH0pO1xuICAgIH1cblxuICAgIGNvbm5lY3RlZENhbGxiYWNrKCkge1xuICAgICAgaWYgKHN1cGVyLmNvbm5lY3RlZENhbGxiYWNrKSB7IHN1cGVyLmNvbm5lY3RlZENhbGxiYWNrKCk7IH1cbiAgICAgIHNhZmVBdHRyaWJ1dGVzLmNvbm5lY3RlZCh0aGlzKTtcbiAgICB9XG5cbiAgICBbc3ltYm9scy5rZXlkb3duXShldmVudCkge1xuICAgICAgbGV0IGhhbmRsZWQ7XG5cbiAgICAgIHN3aXRjaCAoZXZlbnQua2V5Q29kZSkge1xuICAgICAgICBjYXNlIDMyOiAvKiBTcGFjZSAqL1xuICAgICAgICAgIHRoaXMucGxheWluZyA9ICF0aGlzLnBsYXlpbmc7XG4gICAgICAgICAgaGFuZGxlZCA9IHRydWU7XG4gICAgICAgICAgYnJlYWs7XG4gICAgICB9XG5cbiAgICAgIC8vIFByZWZlciBtaXhpbiByZXN1bHQgaWYgaXQncyBkZWZpbmVkLCBvdGhlcndpc2UgdXNlIGJhc2UgcmVzdWx0LlxuICAgICAgcmV0dXJuIGhhbmRsZWQgfHwgKHN1cGVyW3N5bWJvbHMua2V5ZG93bl0gJiYgc3VwZXJbc3ltYm9scy5rZXlkb3duXShldmVudCkpO1xuICAgIH1cblxuICAgIGdldCBwbGF5aW5nKCkge1xuICAgICAgcmV0dXJuIHN1cGVyLnBsYXlpbmc7XG4gICAgfVxuICAgIHNldCBwbGF5aW5nKHZhbHVlKSB7XG4gICAgICBpZiAoJ3BsYXlpbmcnIGluIGJhc2UucHJvdG90eXBlKSB7IHN1cGVyLnBsYXlpbmcgPSB2YWx1ZTsgfVxuICAgICAgc2FmZUF0dHJpYnV0ZXMudG9nZ2xlQ2xhc3ModGhpcywgJ3BsYXlpbmcnLCB2YWx1ZSk7XG4gICAgfVxuXG4gICAgZ2V0IFtzeW1ib2xzLnRlbXBsYXRlXSgpIHtcbiAgICAgIGNvbnN0IGJhc2VUZW1wbGF0ZSA9IHN1cGVyW3N5bWJvbHMudGVtcGxhdGVdIHx8ICcnO1xuICAgICAgcmV0dXJuIGBcbiAgICAgICAgPHN0eWxlPlxuICAgICAgICA6aG9zdCB7XG4gICAgICAgICAgZGlzcGxheTogLXdlYmtpdC1mbGV4O1xuICAgICAgICAgIGRpc3BsYXk6IGZsZXg7XG4gICAgICAgICAgcG9zaXRpb246IHJlbGF0aXZlO1xuICAgICAgICB9XG5cbiAgICAgICAgI2J1dHRvbnMge1xuICAgICAgICAgIGJvdHRvbTogMDtcbiAgICAgICAgICBib3gtc2l6aW5nOiBib3JkZXItYm94O1xuICAgICAgICAgIHBhZGRpbmc6IDAuNWVtO1xuICAgICAgICAgIHBvc2l0aW9uOiBhYnNvbHV0ZTtcbiAgICAgICAgICB0ZXh0LWFsaWduOiBjZW50ZXI7XG4gICAgICAgICAgd2lkdGg6IDEwMCU7XG4gICAgICAgICAgei1pbmRleDogMTtcbiAgICAgICAgfVxuXG4gICAgICAgIGJ1dHRvbiB7XG4gICAgICAgICAgYmFja2dyb3VuZDogdHJhbnNwYXJlbnQ7XG4gICAgICAgICAgYm9yZGVyOiBub25lO1xuICAgICAgICAgIGZpbGw6IHJnYmEoMjU1LCAyNTUsIDI1NSwgMC41KTtcbiAgICAgICAgICBwYWRkaW5nOiAwO1xuICAgICAgICAgIHRyYW5zaXRpb246IGZpbGwgMC41cztcbiAgICAgICAgICB2ZXJ0aWNhbC1hbGlnbjogbWlkZGxlO1xuICAgICAgICB9XG4gICAgICAgIDpob3N0KDpob3ZlcikgYnV0dG9uIHtcbiAgICAgICAgICBmaWxsOiByZ2JhKDI1NSwgMjU1LCAyNTUsIDAuNyk7XG4gICAgICAgIH1cbiAgICAgICAgYnV0dG9uOmhvdmVyIHtcbiAgICAgICAgICBmaWxsOiByZ2JhKDI1NSwgMjU1LCAyNTUsIDAuODUpO1xuICAgICAgICB9XG4gICAgICAgIGJ1dHRvbjphY3RpdmUge1xuICAgICAgICAgIGZpbGw6IHdoaXRlO1xuICAgICAgICB9XG5cbiAgICAgICAgLmljb24ge1xuICAgICAgICAgIGhlaWdodDogMzBweDtcbiAgICAgICAgICB3aWR0aDogMzBweDtcbiAgICAgICAgfVxuICAgICAgICAjcGxheUJ1dHRvbiAuaWNvbiB7XG4gICAgICAgICAgaGVpZ2h0OiA0MHB4O1xuICAgICAgICAgIHdpZHRoOiA0MHB4O1xuICAgICAgICB9XG5cbiAgICAgICAgOmhvc3QoLnBsYXlpbmcpIC5wYXVzZWRDb250cm9sIHtcbiAgICAgICAgICBkaXNwbGF5OiBub25lO1xuICAgICAgICB9XG4gICAgICAgIDpob3N0KDpub3QoLnBsYXlpbmcpKSAucGxheWluZ0NvbnRyb2wge1xuICAgICAgICAgIGRpc3BsYXk6IG5vbmU7XG4gICAgICAgIH1cblxuICAgICAgICAjY29udGFpbmVyIHtcbiAgICAgICAgICBkaXNwbGF5OiAtd2Via2l0LWZsZXg7XG4gICAgICAgICAgZGlzcGxheTogZmxleDtcbiAgICAgICAgICAtd2Via2l0LWZsZXg6IDE7XG4gICAgICAgICAgZmxleDogMTtcbiAgICAgICAgfVxuXG4gICAgICAgICNjb250YWluZXIgOjpzbG90dGVkKCopIHtcbiAgICAgICAgICAtd2Via2l0LWZsZXg6IDE7XG4gICAgICAgICAgZmxleDogMTtcbiAgICAgICAgfVxuICAgICAgICA8L3N0eWxlPlxuXG4gICAgICAgIDxkaXYgaWQ9XCJidXR0b25zXCI+XG4gICAgICAgICAgPGJ1dHRvbiBpZD1cInByZXZpb3VzQnV0dG9uXCI+XG4gICAgICAgICAgICA8c3ZnIGNsYXNzPVwiaWNvblwiIHZpZXdCb3g9XCIwIDAgMjQgMjRcIiBwcmVzZXJ2ZUFzcGVjdFJhdGlvPVwieE1pZFlNaWQgbWVldFwiPlxuICAgICAgICAgICAgICA8ZyBpZD1cInNraXAtcHJldmlvdXNcIj5cbiAgICAgICAgICAgICAgICA8cGF0aCBkPVwiTTYgNmgydjEySDZ6bTMuNSA2bDguNSA2VjZ6XCIvPlxuICAgICAgICAgICAgICA8L2c+XG4gICAgICAgICAgICA8L3N2Zz5cbiAgICAgICAgICA8L2J1dHRvbj5cbiAgICAgICAgICA8YnV0dG9uIGlkPVwicGxheUJ1dHRvblwiPlxuICAgICAgICAgICAgPHN2ZyBjbGFzcz1cImljb24gcGxheWluZ0NvbnRyb2xcIiB2aWV3Qm94PVwiMCAwIDI0IDI0XCIgcHJlc2VydmVBc3BlY3RSYXRpbz1cInhNaWRZTWlkIG1lZXRcIj5cbiAgICAgICAgICAgICAgPGcgaWQ9XCJwYXVzZS1jaXJjbGUtb3V0bGluZVwiPlxuICAgICAgICAgICAgICAgIDxwYXRoIGQ9XCJNOSAxNmgyVjhIOXY4em0zLTE0QzYuNDggMiAyIDYuNDggMiAxMnM0LjQ4IDEwIDEwIDEwIDEwLTQuNDggMTAtMTBTMTcuNTIgMiAxMiAyem0wIDE4Yy00LjQxIDAtOC0zLjU5LTgtOHMzLjU5LTggOC04IDggMy41OSA4IDgtMy41OSA4LTggOHptMS00aDJWOGgtMnY4elwiPjwvcGF0aD5cbiAgICAgICAgICAgICAgPC9nPlxuICAgICAgICAgICAgPC9zdmc+XG4gICAgICAgICAgICA8c3ZnIGNsYXNzPVwiaWNvbiBwYXVzZWRDb250cm9sXCIgdmlld0JveD1cIjAgMCAyNCAyNFwiIHByZXNlcnZlQXNwZWN0UmF0aW89XCJ4TWlkWU1pZCBtZWV0XCI+XG4gICAgICAgICAgICAgIDxnIGlkPVwicGxheS1jaXJjbGUtb3V0bGluZVwiPlxuICAgICAgICAgICAgICAgIDxwYXRoIGQ9XCJNMTAgMTYuNWw2LTQuNS02LTQuNXY5ek0xMiAyQzYuNDggMiAyIDYuNDggMiAxMnM0LjQ4IDEwIDEwIDEwIDEwLTQuNDggMTAtMTBTMTcuNTIgMiAxMiAyem0wIDE4Yy00LjQxIDAtOC0zLjU5LTgtOHMzLjU5LTggOC04IDggMy41OSA4IDgtMy41OSA4LTggOHpcIj48L3BhdGg+XG4gICAgICAgICAgICAgIDwvZz5cbiAgICAgICAgICAgIDwvc3ZnPlxuICAgICAgICAgIDwvYnV0dG9uPlxuICAgICAgICAgIDxidXR0b24gaWQ9XCJuZXh0QnV0dG9uXCI+XG4gICAgICAgICAgICA8c3ZnIGNsYXNzPVwiaWNvblwiIHZpZXdCb3g9XCIwIDAgMjQgMjRcIiBwcmVzZXJ2ZUFzcGVjdFJhdGlvPVwieE1pZFlNaWQgbWVldFwiPlxuICAgICAgICAgICAgICA8ZyBpZD1cInNraXAtbmV4dFwiPlxuICAgICAgICAgICAgICAgIDxwYXRoIGQ9XCJNNiAxOGw4LjUtNkw2IDZ2MTJ6TTE2IDZ2MTJoMlY2aC0yelwiLz5cbiAgICAgICAgICAgICAgPC9nPlxuICAgICAgICAgICAgPC9zdmc+XG4gICAgICAgICAgPC9idXR0b24+XG4gICAgICAgIDwvZGl2PlxuXG4gICAgICAgIDxkaXYgaWQ9XCJjb250YWluZXJcIiByb2xlPVwibm9uZVwiPlxuICAgICAgICAgICR7YmFzZVRlbXBsYXRlfVxuICAgICAgICA8L2Rpdj5cbiAgICAgIGA7XG4gICAgfVxuXG4gIH1cblxuICByZXR1cm4gUGxheUNvbnRyb2xzO1xufTtcbiIsImltcG9ydCBjcmVhdGVTeW1ib2wgZnJvbSAnLi9jcmVhdGVTeW1ib2wnO1xuaW1wb3J0IEZyYWN0aW9uYWxTZWxlY3Rpb25NaXhpbiBmcm9tICcuL0ZyYWN0aW9uYWxTZWxlY3Rpb25NaXhpbic7XG5pbXBvcnQgc3ltYm9scyBmcm9tICcuL3N5bWJvbHMnO1xuXG5cbi8vIFN5bWJvbHMgZm9yIHByaXZhdGUgZGF0YSBtZW1iZXJzIG9uIGFuIGVsZW1lbnQuXG5jb25zdCBhbmltYXRpb25TeW1ib2wgPSBjcmVhdGVTeW1ib2woJ2FuaW1hdGlvbicpO1xuY29uc3QgZHJhZ2dpbmdTeW1ib2wgPSBjcmVhdGVTeW1ib2woJ2RyYWdnaW5nJyk7XG5jb25zdCBsYXN0QW5pbWF0aW9uU3ltYm9sID0gY3JlYXRlU3ltYm9sKCdsYXN0QW5pbWF0aW9uJyk7XG5jb25zdCBwbGF5aW5nQW5pbWF0aW9uU3ltYm9sID0gY3JlYXRlU3ltYm9sKCdhbmltYXRpbmdTZWxlY3Rpb24nKTtcbmNvbnN0IHByZXZpb3VzU2VsZWN0aW9uU3ltYm9sID0gY3JlYXRlU3ltYm9sKCdwcmV2aW91c1NlbGVjdGlvbicpO1xuY29uc3Qgc2VsZWN0aW9uQW5pbWF0aW9uRHVyYXRpb25TeW1ib2wgPSBjcmVhdGVTeW1ib2woJ3NlbGVjdGlvbkFuaW1hdGlvbkR1cmF0aW9uJyk7XG5jb25zdCBzZWxlY3Rpb25BbmltYXRpb25FZmZlY3RTeW1ib2wgPSBjcmVhdGVTeW1ib2woJ3NlbGVjdGlvbkFuaW1hdGlvbkVmZmVjdCcpO1xuY29uc3Qgc2VsZWN0aW9uQW5pbWF0aW9uS2V5ZnJhbWVzU3ltYm9sID0gY3JlYXRlU3ltYm9sKCdzZWxlY3Rpb25BbmltYXRpb25LZXlmcmFtZXMnKTtcbmNvbnN0IHJlc2V0QW5pbWF0aW9uc09uTmV4dFJlbmRlclN5bWJvbCA9IGNyZWF0ZVN5bWJvbCgncmVzZXRBbmltYXRpb25zT25OZXh0UmVuZGVyJyk7XG5cblxuLyogRXhwb3J0ZWQgZnVuY3Rpb24gZXh0ZW5kcyBhIGJhc2UgY2xhc3Mgd2l0aCBTZWxlY3Rpb25BbmltYXRpb24uICovXG5leHBvcnQgZGVmYXVsdCBmdW5jdGlvbiBtaXhpbihiYXNlKSB7XG5cbiAgLyoqXG4gICAqIE1peGluIHdoaWNoIHVzZXMgYW5pbWF0aW9uIHRvIHNob3cgdHJhbnNpdGlvbnMgYmV0d2VlbiBzZWxlY3Rpb24gc3RhdGVzLlxuICAgKlxuICAgKiBUaGlzIG1peGluIGNhbiBiZSB1c2VkIGJ5IGNvbXBvbmVudHMgdGhhdCB3YW50IHRvIHByb3ZpZGUgdmlzaWJsZVxuICAgKiBhbmltYXRpb25zIHdoZW4gY2hhbmdpbmcgdGhlIHNlbGVjdGlvbi4gRm9yIGV4YW1wbGUsIGEgY2Fyb3VzZWwgY29tcG9uZW50XG4gICAqIG1heSB3YW50IHRvIGRlZmluZSBhIHNsaWRpbmcgYW5pbWF0aW9uIGVmZmVjdCBzaG93biB3aGVuIG1vdmluZyBiZXR3ZWVuXG4gICAqIGl0ZW1zLlxuICAgKlxuICAgKiBUaGUgYW5pbWF0aW9uIGlzIGRlZmluZWQgYnkgYSBgc2VsZWN0aW9uQW5pbWF0aW9uS2V5ZnJhbWVzYCBwcm9wZXJ0eTsgc2VlXG4gICAqIHRoYXQgcHJvcGVydHkgZm9yIGRldGFpbHMgb24gaG93IHRvIGRlZmluZSB0aGVzZSBrZXlmcmFtZXMuIFRoaXMgYW5pbWF0aW9uXG4gICAqIHdpbGwgYmUgdXNlZCBpbiB0d28gd2F5cy4gRmlyc3QsIHdoZW4gbW92aW5nIHN0cmljdGx5IGJldHdlZW4gaXRlbXMsIHRoZVxuICAgKiBhbmltYXRpb24gd2lsbCBwbGF5IHNtb290aGx5IHRvIHNob3cgdGhlIHNlbGVjdGlvbiBjaGFuZ2luZy4gU2Vjb25kLCB0aGVcbiAgICogYW5pbWF0aW9uIGNhbiBiZSB1c2VkIHRvIHJlbmRlciB0aGUgc2VsZWN0aW9uIGF0IGEgZml4ZWQgcG9pbnQgaW4gdGhlXG4gICAqIHRyYW5zaXRpb24gYmV0d2VlbiBzdGF0ZXMuIEUuZy4sIGlmIHRoZSB1c2VyIHBhdXNlcyBoYWxmd2F5IHRocm91Z2hcbiAgICogZHJhZ2dpbmcgYW4gZWxlbWVudCB1c2luZyBbU3dpcGVEaXJlY3Rpb25NaXhpbl0oU3dpcGVEaXJlY3Rpb25NaXhpbi5tZClcbiAgICogb3IgW1RyYWNrcGFkRGlyZWN0aW9uTWl4aW5dKFRyYWNrcGFkRGlyZWN0aW9uTWl4aW4ubWQpcywgdGhlbiB0aGUgc2VsZWN0aW9uXG4gICAqIGFuaW1hdGlvbiB3aWxsIGJlIHNob3duIGF0IHRoZSBwb2ludCBleGFjdGx5IGhhbGZ3YXkgdGhyb3VnaC5cbiAgICpcbiAgICogVGhpcyBtaXhpbiBleHBlY3RzIGEgY29tcG9uZW50IHRvIHByb3ZpZGUgYW4gYGl0ZW1zYCBhcnJheSBvZiBhbGwgZWxlbWVudHNcbiAgICogaW4gdGhlIGxpc3QsIHdoaWNoIGNhbiBiZSBwcm92aWRlZCB2aWFcbiAgICogW0NvbnRlbnRJdGVtc01peGluXShDb250ZW50SXRlbXNNaXhpbi5tZCkuIFRoaXMgbWl4aW4gYWxzbyBleHBlY3RzXG4gICAqIGBzZWxlY3RlZEluZGV4YCBhbmQgYHNlbGVjdGVkSXRlbWAgcHJvcGVydGllcywgd2hpY2ggY2FuIGJlIHByb3ZpZGVkIHZpYVxuICAgKiBbU2luZ2xlU2VsZWN0aW9uTWl4aW5dKFNpbmdsZVNlbGVjdGlvbk1peGluLm1kKS5cbiAgICpcbiAgICogVGhpcyBtaXhpbiBzdXBwb3J0cyBhIGBzZWxlY3Rpb25XcmFwc2AgcHJvcGVydHkuIFdoZW4gdHJ1ZSwgdGhlIHVzZXIgY2FuXG4gICAqIG5hdmlnYXRlIGZvcndhcmQgZnJvbSB0aGUgbGFzdCBpdGVtIGluIHRoZSBsaXN0IGFuZCB3cmFwIGFyb3VuZCB0byB0aGVcbiAgICogZmlyc3QgaXRlbSwgb3IgbmF2aWdhdGUgYmFja3dhcmQgZnJvbSB0aGUgZmlyc3QgaXRlbSBhbmQgd3JhcCBhcm91bmQgdG8gdGhlXG4gICAqIGxhc3QgaXRlbS5cbiAgICpcbiAgICogVGhpcyBtaXhpbiB1c2VzIHRoZSBXZWIgQW5pbWF0aW9ucyBBUEkuIEZvciB1c2Ugb24gYnJvd3NlcnMgd2hpY2hcbiAgICogZG8gbm90IHN1cHBvcnQgdGhhdCBBUEkgbmF0aXZlbHksIHlvdSB3aWxsIG5lZWQgdG8gbG9hZCB0aGVcbiAgICogW1dlYiBBbmltYXRpb25zIHBvbHlmaWxsXShodHRwczovL2dpdGh1Yi5jb20vd2ViLWFuaW1hdGlvbnMvd2ViLWFuaW1hdGlvbnMtanMpLlxuICAgKi9cbiAgY2xhc3MgU2VsZWN0aW9uQW5pbWF0aW9uIGV4dGVuZHMgYmFzZSB7XG5cbiAgICBjb25zdHJ1Y3RvcigpIHtcbiAgICAgIHN1cGVyKCk7XG5cbiAgICAgIC8vIFNldCBkZWZhdWx0cy5cbiAgICAgIGlmICh0eXBlb2YgdGhpcy5zZWxlY3Rpb25BbmltYXRpb25EdXJhdGlvbiA9PT0gJ3VuZGVmaW5lZCcpIHtcbiAgICAgICAgdGhpcy5zZWxlY3Rpb25BbmltYXRpb25EdXJhdGlvbiA9IHRoaXNbc3ltYm9scy5kZWZhdWx0c10uc2VsZWN0aW9uQW5pbWF0aW9uRHVyYXRpb247XG4gICAgICB9XG4gICAgICBpZiAodHlwZW9mIHRoaXMuc2VsZWN0aW9uQW5pbWF0aW9uRWZmZWN0ID09PSAndW5kZWZpbmVkJyAmJiB0aGlzLnNlbGVjdGlvbkFuaW1hdGlvbktleWZyYW1lcyA9PSBudWxsKSB7XG4gICAgICAgIHRoaXMuc2VsZWN0aW9uQW5pbWF0aW9uRWZmZWN0ID0gdGhpc1tzeW1ib2xzLmRlZmF1bHRzXS5zZWxlY3Rpb25BbmltYXRpb25FZmZlY3Q7XG4gICAgICB9XG5cbiAgICAgIHRoaXNbc3ltYm9scy5kcmFnZ2luZ10gPSBmYWxzZTtcbiAgICB9XG5cbiAgICBnZXQgW3N5bWJvbHMuZGVmYXVsdHNdKCkge1xuICAgICAgY29uc3QgZGVmYXVsdHMgPSBzdXBlcltzeW1ib2xzLmRlZmF1bHRzXSB8fCB7fTtcbiAgICAgIGRlZmF1bHRzLnNlbGVjdGlvbkFuaW1hdGlvbkR1cmF0aW9uID0gMjUwO1xuICAgICAgZGVmYXVsdHMuc2VsZWN0aW9uQW5pbWF0aW9uRWZmZWN0ID0gJ3NsaWRlJztcbiAgICAgIHJldHVybiBkZWZhdWx0cztcbiAgICB9XG5cbiAgICAvKlxuICAgICAqIFByb3ZpZGUgYmFja2luZyBmb3IgdGhlIGRyYWdnaW5nIHByb3BlcnR5LlxuICAgICAqIEFsc28sIHdoZW4gYSBkcmFnIGJlZ2lucywgcmVzZXQgdGhlIGFuaW1hdGlvbnMuXG4gICAgICovXG4gICAgZ2V0IFtzeW1ib2xzLmRyYWdnaW5nXSgpIHtcbiAgICAgIHJldHVybiB0aGlzW2RyYWdnaW5nU3ltYm9sXTtcbiAgICB9XG4gICAgc2V0IFtzeW1ib2xzLmRyYWdnaW5nXSh2YWx1ZSkge1xuICAgICAgY29uc3QgcHJldmlvdXNWYWx1ZSA9IHRoaXNbc3ltYm9scy5kcmFnZ2luZ107XG4gICAgICB0aGlzW2RyYWdnaW5nU3ltYm9sXSA9IHZhbHVlO1xuICAgICAgaWYgKHN5bWJvbHMuZHJhZ2dpbmcgaW4gYmFzZS5wcm90b3R5cGUpIHsgc3VwZXJbc3ltYm9scy5kcmFnZ2luZ10gPSB2YWx1ZTsgfVxuICAgICAgaWYgKHZhbHVlICYmICFwcmV2aW91c1ZhbHVlKSB7XG4gICAgICAgIC8vIEhhdmUgYmVndW4gYSBkcmFnLlxuICAgICAgICB0aGlzW3Jlc2V0QW5pbWF0aW9uc09uTmV4dFJlbmRlclN5bWJvbF0gPSB0cnVlO1xuICAgICAgfVxuICAgIH1cblxuICAgIFtzeW1ib2xzLml0ZW1BZGRlZF0oaXRlbSkge1xuICAgICAgLy8gV2UgbWFyayBuZXcgaXRlbXMgaW4gdGhlIGxpc3QgYXMgZXhwbGljaXRseSB2aXNpYmxlIHRvIEFSSUEuIE90aGVyd2lzZSxcbiAgICAgIC8vIHdoZW4gYW4gaXRlbSBpc24ndCB2aXNpYmxlIG9uIHRoZSBzY3JlZW4sIEFSSUEgd2lsbCBhc3N1bWUgdGhlIGl0ZW0gaXNcbiAgICAgIC8vIG9mIG5vIGludGVyZXN0IHRvIHRoZSB1c2VyLCBhbmQgbGVhdmUgaXQgb3V0IG9mIHRoZSBhY2Nlc3NpYmlsaXR5IHRyZWUuXG4gICAgICAvLyBJZiB0aGUgbGlzdCBjb250YWlucyAxMCBpdGVtcywgYnV0IG9ubHkgMyBhcmUgdmlzaWJsZSwgYSBzY3JlZW4gcmVhZGVyXG4gICAgICAvLyBtaWdodCB0aGVuIGFubm91bmNlIHRoZSBsaXN0IG9ubHkgaGFzIDMgaXRlbXMuIFRvIGVuc3VyZSB0aGF0IHNjcmVlblxuICAgICAgLy8gcmVhZGVycyBhbmQgb3RoZXIgYXNzaXN0aXZlIHRlY2hub2xvZ2llcyBhbm5vdW5jZSB0aGUgY29ycmVjdCB0b3RhbFxuICAgICAgLy8gbnVtYmVyIG9mIGl0ZW1zLCB3ZSBleHBsaWNpdGx5IG1hcmsgYWxsIGl0ZW1zIGFzIG5vdCBoaWRkZW4uIFRoaXMgd2lsbFxuICAgICAgLy8gZXhwb3NlIHRoZW0gYWxsIGluIHRoZSBhY2Nlc3NpYmlsaXR5IHRyZWUsIGV2ZW4gdGhlIGl0ZW1zIHdoaWNoIGFyZVxuICAgICAgLy8gY3VycmVudGx5IG5vdCByZW5kZXJlZC5cbiAgICAgIC8vXG4gICAgICAvLyBUT0RPOiBHZW5lcmFsbHkgc3BlYWtpbmcsIHRoaXMgZW50aXJlIG1peGluIGFzc3VtZXMgdGhhdCB0aGUgdXNlciBjYW5cbiAgICAgIC8vIG5hdmlnYXRlIHRocm91Z2ggYWxsIGl0ZW1zIGluIGEgbGlzdC4gQnV0IGFuIGFwcCBjb3VsZCBzdHlsZSBhbiBpdGVtIGFzXG4gICAgICAvLyBkaXNwbGF5Om5vbmUgb3IgdmlzaWJpbGl0eTpoaWRkZW4gYmVjYXVzZSB0aGUgdXNlciBpcyBub3QgYWxsb3dlZCB0b1xuICAgICAgLy8gaW50ZXJhY3Qgd2l0aCB0aGF0IGl0ZW0gYXQgdGhlIG1vbWVudC4gU3VwcG9ydCBmb3IgdGhpcyBzY2VuYXJpbyBzaG91bGRcbiAgICAgIC8vIGJlIGFkZGVkLiBUaGlzIHdvdWxkIGVudGFpbCBjaGFuZ2luZyBhbGwgbG9jYXRpb25zIHdoZXJlIGEgbWl4aW5cbiAgICAgIC8vIGZ1bmN0aW9uIGlzIGNvdW50aW5nIGl0ZW1zLCBpdGVyYXRpbmcgb3ZlciB0aGUgKHZpc2libGUpIGl0ZW1zLCBhbmRcbiAgICAgIC8vIHNob3dpbmcgb3IgaGlkaW5nIGl0ZW1zLiBBbW9uZyBvdGhlciB0aGluZ3MsIHRoZSBjb2RlIGJlbG93IHRvIG1ha2VcbiAgICAgIC8vIGl0ZW1zIHZpc2libGUgdG8gQVJJQSB3b3VsZCBuZWVkIHRvIGRpc2NyaW1pbmF0ZSBiZXR3ZWVuIGl0ZW1zIHdoaWNoXG4gICAgICAvLyBhcmUgaW52aXNpYmxlIGJlY2F1c2Ugb2YgYW5pbWF0aW9uIHN0YXRlLCBvciBpbnZpc2libGUgYmVjYXVzZSB0aGUgdXNlclxuICAgICAgLy8gc2hvdWxkbid0IGludGVyYWN0IHdpdGggdGhlbS5cbiAgICAgIGl0ZW0uc2V0QXR0cmlidXRlKCdhcmlhLWhpZGRlbicsIGZhbHNlKTtcbiAgICB9XG5cbiAgICBbc3ltYm9scy5pdGVtc0NoYW5nZWRdKCkge1xuICAgICAgaWYgKHN1cGVyW3N5bWJvbHMuaXRlbXNDaGFuZ2VkXSkgeyBzdXBlcltzeW1ib2xzLml0ZW1zQ2hhbmdlZF0oKTsgfVxuXG4gICAgICByZXNldEFuaW1hdGlvbnModGhpcyk7XG5cbiAgICAgIC8vIFRPRE86IEFsc28gcmVzZXQgb3VyIG5vdGlvbiBvZiB0aGUgbGFzdCByZW5kZXJlZCBzZWxlY3Rpb24/IFRoaXMgY29tZXNcbiAgICAgIC8vIHVwIHdoZW4gYSBET00gcmVtb3ZhbCBjYXVzZXMgdGhlIHNlbGVjdGVkIGl0ZW0gdG8gY2hhbmdlIHBvc2l0aW9uLlxuICAgICAgLy8gdGhpc1twcmV2aW91c1NlbGVjdGlvblN5bWJvbF0gPSBudWxsO1xuXG4gICAgICByZW5kZXJTZWxlY3Rpb24odGhpcyk7XG4gICAgfVxuXG4gICAgcmVzZXRBbmltYXRpb25zKCkge1xuICAgICAgcmVzZXRBbmltYXRpb25zKHRoaXMpO1xuICAgIH1cblxuICAgIC8qKlxuICAgICAqIEEgZnJhY3Rpb25hbCB2YWx1ZSBpbmRpY2F0aW5nIGhvdyBmYXIgdGhlIHVzZXIgaGFzIGN1cnJlbnRseSBhZHZhbmNlZCB0b1xuICAgICAqIHRoZSBuZXh0L3ByZXZpb3VzIGl0ZW0uIEUuZy4sIGEgYHNlbGVjdGVkRnJhY3Rpb25gIG9mIDMuNSBpbmRpY2F0ZXMgdGhlXG4gICAgICogdXNlciBpcyBoYWxmd2F5IGJldHdlZW4gaXRlbXMgMyBhbmQgNC5cbiAgICAgKlxuICAgICAqIEZvciBtb3JlIGRldGFpbHMsIHNlZSBbRnJhY3Rpb25hbFNlbGVjdGlvbk1peGluXShGcmFjdGlvbmFsU2VsZWN0aW9uTWl4aW4ubWQpXG4gICAgICogbWl4aW4uXG4gICAgICpcbiAgICAgKiBAdHlwZSB7bnVtYmVyfVxuICAgICAqL1xuICAgIGdldCBzZWxlY3RlZEZyYWN0aW9uKCkge1xuICAgICAgcmV0dXJuIHN1cGVyLnNlbGVjdGVkRnJhY3Rpb24gfHwgMDtcbiAgICB9XG4gICAgc2V0IHNlbGVjdGVkRnJhY3Rpb24odmFsdWUpIHtcbiAgICAgIGlmICgnc2VsZWN0ZWRGcmFjdGlvbicgaW4gYmFzZS5wcm90b3R5cGUpIHsgc3VwZXIuc2VsZWN0ZWRGcmFjdGlvbiA9IHZhbHVlOyB9XG4gICAgICByZW5kZXJTZWxlY3Rpb24odGhpcywgdGhpcy5zZWxlY3RlZEluZGV4LCB2YWx1ZSk7XG4gICAgfVxuXG4gICAgZ2V0IHNlbGVjdGVkSW5kZXgoKSB7XG4gICAgICByZXR1cm4gc3VwZXIuc2VsZWN0ZWRJbmRleDtcbiAgICB9XG4gICAgc2V0IHNlbGVjdGVkSW5kZXgoaW5kZXgpIHtcbiAgICAgIGlmICgnc2VsZWN0ZWRJbmRleCcgaW4gYmFzZS5wcm90b3R5cGUpIHsgc3VwZXIuc2VsZWN0ZWRJbmRleCA9IGluZGV4OyB9XG4gICAgICByZW5kZXJTZWxlY3Rpb24odGhpcywgaW5kZXgsIDApO1xuICAgIH1cblxuICAgIC8qKlxuICAgICAqIFRoZSBkdXJhdGlvbiBvZiBhIHNlbGVjdGlvbiBhbmltYXRpb24gaW4gbWlsbGlzZWNvbmRzLlxuICAgICAqXG4gICAgICogVGhpcyBtZWFzdXJlcyB0aGUgYW1vdW50IG9mIHRpbWUgcmVxdWlyZWQgZm9yIGEgc2VsZWN0aW9uIGFuaW1hdGlvbiB0b1xuICAgICAqIGNvbXBsZXRlLiBUaGlzIG51bWJlciByZW1haW5zIGNvbnN0YW50LCBldmVuIGlmIHRoZSBudW1iZXIgb2YgaXRlbXMgYmVpbmdcbiAgICAgKiBhbmltYXRlZCBpbmNyZWFzZXMuXG4gICAgICpcbiAgICAgKiBUaGUgZGVmYXVsdCB2YWx1ZSBpcyAyNTAgbWlsbGlzZWNvbmRzIChhIHF1YXJ0ZXIgYSBzZWNvbmQpLlxuICAgICAqXG4gICAgICogQHR5cGUge251bWJlcn1cbiAgICAgKiBAZGVmYXVsdCAyNTBcbiAgICAgKi9cbiAgICBnZXQgc2VsZWN0aW9uQW5pbWF0aW9uRHVyYXRpb24oKSB7XG4gICAgICByZXR1cm4gdGhpc1tzZWxlY3Rpb25BbmltYXRpb25EdXJhdGlvblN5bWJvbF07XG4gICAgfVxuICAgIHNldCBzZWxlY3Rpb25BbmltYXRpb25EdXJhdGlvbih2YWx1ZSkge1xuICAgICAgdGhpc1tzZWxlY3Rpb25BbmltYXRpb25EdXJhdGlvblN5bWJvbF0gPSB2YWx1ZTtcbiAgICAgIGlmICgnc2VsZWN0aW9uQW5pbWF0aW9uRHVyYXRpb24nIGluIGJhc2UucHJvdG90eXBlKSB7IHN1cGVyLnNlbGVjdGlvbkFuaW1hdGlvbkR1cmF0aW9uID0gdmFsdWU7IH1cbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBUaGUgbmFtZSBvZiBhIHN0YW5kYXJkIHNlbGVjdGlvbiBhbmltYXRpb24gZWZmZWN0LlxuICAgICAqXG4gICAgICogVGhpcyBpcyBhIHNob3J0aGFuZCBmb3Igc2V0dGluZyB0aGUgYHNlbGVjdGlvbkFuaW1hdGlvbktleWZyYW1lc2BcbiAgICAgKiBwcm9wZXJ0eSB0byBzdGFuZGFyZCBrZXlmcmFtZXMuIFN1cHBvcnRlZCBzdHJpbmcgdmFsdWVzOlxuICAgICAqXG4gICAgICogKiBcImNyb3NzZmFkZVwiXG4gICAgICogKiBcInJldmVhbFwiXG4gICAgICogKiBcInJldmVhbFdpdGhGYWRlXCJcbiAgICAgKiAqIFwic2hvd0FkamFjZW50XCJcbiAgICAgKiAqIFwic2xpZGVcIlxuICAgICAqICogXCJzbGlkZVdpdGhHYXBcIlxuICAgICAqXG4gICAgICogQHR5cGUge3N0cmluZ31cbiAgICAgKiBAZGVmYXVsdCBcInNsaWRlXCJcbiAgICAgKi9cbiAgICBnZXQgc2VsZWN0aW9uQW5pbWF0aW9uRWZmZWN0KCkge1xuICAgICAgcmV0dXJuIHRoaXNbc2VsZWN0aW9uQW5pbWF0aW9uRWZmZWN0U3ltYm9sXTtcbiAgICB9XG4gICAgc2V0IHNlbGVjdGlvbkFuaW1hdGlvbkVmZmVjdCh2YWx1ZSkge1xuICAgICAgdGhpc1tzZWxlY3Rpb25BbmltYXRpb25FZmZlY3RTeW1ib2xdID0gdmFsdWU7XG4gICAgICBpZiAoJ3NlbGVjdGlvbkFuaW1hdGlvbkVmZmVjdCcgaW4gYmFzZS5wcm90b3R5cGUpIHsgc3VwZXIuc2VsZWN0aW9uQW5pbWF0aW9uRWZmZWN0ID0gdmFsdWU7IH1cbiAgICAgIHRoaXMuc2VsZWN0aW9uQW5pbWF0aW9uS2V5ZnJhbWVzID0gbWl4aW4uc3RhbmRhcmRFZmZlY3RLZXlmcmFtZXNbdmFsdWVdO1xuICAgIH1cblxuICAgIC8qKlxuICAgICAqIFRoZSBrZXlmcmFtZXMgdGhhdCBkZWZpbmUgYW4gYW5pbWF0aW9uIHRoYXQgcGxheXMgZm9yIGFuIGl0ZW0gd2hlbiBtb3ZpbmdcbiAgICAgKiBmb3J3YXJkIGluIHRoZSBzZXF1ZW5jZS5cbiAgICAgKlxuICAgICAqIFRoaXMgaXMgYW4gYXJyYXkgb2YgQ1NTIHJ1bGVzIHRoYXQgd2lsbCBiZSBhcHBsaWVkLiBUaGVzZSBhcmUgdXNlZCBhc1xuICAgICAqIFtrZXlmcmFtZXNdKGh0dHA6Ly93M2MuZ2l0aHViLmlvL3dlYi1hbmltYXRpb25zLyNrZXlmcmFtZXMtc2VjdGlvbilcbiAgICAgKiB0byBhbmltYXRlIHRoZSBpdGVtIHdpdGggdGhlXG4gICAgICogW1dlYiBBbmltYXRpb25zIEFQSV0oaHR0cHM6Ly9kZXZlbG9wZXIubW96aWxsYS5vcmcvZW4tVVMvZG9jcy9XZWIvQVBJL2FuaW1hdGlvbikuXG4gICAgICpcbiAgICAgKiBUaGUgYW5pbWF0aW9uIHJlcHJlc2VudHMgdGhlIHN0YXRlIG9mIHRoZSBuZXh0IGl0ZW0gYXMgaXQgbW92ZXMgZnJvbVxuICAgICAqIGNvbXBsZXRlbHkgdW5zZWxlY3RlZCAob2Zmc3RhZ2UsIHVzdWFsbHkgcmlnaHQpLCB0byBzZWxlY3RlZCAoY2VudGVyXG4gICAgICogc3RhZ2UpLCB0byBjb21wbGV0ZWx5IHVuc2VsZWN0ZWQgKG9mZnN0YWdlLCB1c3VhbGx5IGxlZnQpLiBUaGUgY2VudGVyIHRpbWVcbiAgICAgKiBvZiB0aGUgYW5pbWF0aW9uIHNob3VsZCBjb3JyZXNwb25kIHRvIHRoZSBpdGVtJ3MgcXVpc2NlbnQgc2VsZWN0ZWQgc3RhdGUsXG4gICAgICogdHlwaWNhbGx5IGluIHRoZSBjZW50ZXIgb2YgdGhlIHN0YWdlIGFuZCBhdCB0aGUgaXRlbSdzIGxhcmdlc3Qgc2l6ZS5cbiAgICAgKlxuICAgICAqIFRoZSBkZWZhdWx0IGZvcndhcmQgYW5pbWF0aW9uIGlzIGEgc21vb3RoIHNsaWRlIGF0IGZ1bGwgc2l6ZSBmcm9tIHJpZ2h0IHRvXG4gICAgICogbGVmdC5cbiAgICAgKlxuICAgICAqIFdoZW4gbW92aW5nIHRoZSBzZWxlY3Rpb24gYmFja3dhcmQsIHRoaXMgYW5pbWF0aW9uIGlzIHBsYXllZCBpbiByZXZlcnNlLlxuICAgICAqXG4gICAgICogQHR5cGUge2Nzc1J1bGVzW119XG4gICAgICovXG4gICAgZ2V0IHNlbGVjdGlvbkFuaW1hdGlvbktleWZyYW1lcygpIHtcbiAgICAgIC8vIFN0YW5kYXJkIGFuaW1hdGlvbiBzbGlkZXMgbGVmdC9yaWdodCwga2VlcHMgYWRqYWNlbnQgaXRlbXMgb3V0IG9mIHZpZXcuXG4gICAgICByZXR1cm4gdGhpc1tzZWxlY3Rpb25BbmltYXRpb25LZXlmcmFtZXNTeW1ib2xdO1xuICAgIH1cbiAgICBzZXQgc2VsZWN0aW9uQW5pbWF0aW9uS2V5ZnJhbWVzKHZhbHVlKSB7XG4gICAgICB0aGlzW3NlbGVjdGlvbkFuaW1hdGlvbktleWZyYW1lc1N5bWJvbF0gPSB2YWx1ZTtcbiAgICAgIGlmICgnc2VsZWN0aW9uQW5pbWF0aW9uS2V5ZnJhbWVzJyBpbiBiYXNlLnByb3RvdHlwZSkgeyBzdXBlci5zZWxlY3Rpb25BbmltYXRpb25LZXlmcmFtZXMgPSB2YWx1ZTsgfVxuICAgICAgcmVzZXRBbmltYXRpb25zKHRoaXMpO1xuICAgICAgcmVuZGVyU2VsZWN0aW9uKHRoaXMpO1xuICAgIH1cblxuICAgIGdldCBzZWxlY3Rpb25XcmFwcygpIHtcbiAgICAgIHJldHVybiBzdXBlci5zZWxlY3Rpb25XcmFwcztcbiAgICB9XG4gICAgc2V0IHNlbGVjdGlvbldyYXBzKHZhbHVlKSB7XG4gICAgICBpZiAoJ3NlbGVjdGlvbldyYXBzJyBpbiBiYXNlLnByb3RvdHlwZSkgeyBzdXBlci5zZWxlY3Rpb25XcmFwcyA9IHZhbHVlOyB9XG4gICAgICByZXNldEFuaW1hdGlvbnModGhpcyk7XG4gICAgICByZW5kZXJTZWxlY3Rpb24odGhpcyk7XG4gICAgfVxuICB9XG5cbiAgcmV0dXJuIFNlbGVjdGlvbkFuaW1hdGlvbjtcbn1cblxuXG4vLyBXZSBleHBvc2UgaGVscGVycyBvbiB0aGUgbWl4aW4gZnVuY3Rpb24gdGhhdCB3ZSB3YW50IHRvIGJlIGFibGUgdG8gdW5pdCB0ZXN0LlxuLy8gU2luY2UgdGhlc2UgYXJlIG9uIHRoZSBmdW5jdGlvbiwgbm90IG9uIHRoZSBjbGFzcyBlbWl0dGVkIGJ5IHRoZSBmdW5jdGlvbixcbi8vIHRoZXkgZG9uJ3QgZW5kIHVwIGdldHRpbmcgZXhwb3NlZCBvbiBhY3R1YWwgZWxlbWVudCBpbnN0YW5jZXMuXG5taXhpbi5oZWxwZXJzID0ge1xuXG4gIC8qXG4gICAqIENhbGN1bGF0ZSB0aGUgYW5pbWF0aW9uIGZyYWN0aW9ucyBmb3IgYW4gZWxlbWVudCdzIGl0ZW1zIGF0IHRoZSBnaXZlblxuICAgKiBzZWxlY3Rpb24gcG9pbnQuIFRoaXMgaXMgdXNlZCB3aGVuIHJlbmRlcmluZyB0aGUgZWxlbWVudCdzIHNlbGVjdGlvbiBzdGF0ZVxuICAgKiBpbnN0YW50YW5lb3VzbHkuXG4gICAqXG4gICAqIFRoaXMgZnVuY3Rpb24gY29uc2lkZXJzIHRoZSBzZWxlY3RlZEluZGV4IHBhcmFtZXRlciwgd2hpY2ggY2FuIGJlIGEgd2hvbGVcbiAgICogb3IgZnJhY3Rpb25hbCBudW1iZXIsIGFuZCBkZXRlcm1pbmVzIHdoaWNoIGl0ZW1zIHdpbGwgYmUgdmlzaWJsZSBhdCB0aGF0XG4gICAqIGluZGV4LiBUaGlzIGZ1bmN0aW9uIHRoZW4gY2FsY3VsYXRlcyBhIGNvcnJlc3BvbmRpbmcgYW5pbWF0aW9uIGZyYWN0aW9uOiBhXG4gICAqIG51bWJlciBiZXR3ZWVuIDAgYW5kIDEgaW5kaWNhdGluZyBob3cgZmFyIHRocm91Z2ggdGhlIHNlbGVjdGlvbiBhbmltYXRpb25cbiAgICogYW4gaXRlbSBzaG91bGQgYmUgc2hvd24sIG9yIG51bGwgaWYgdGhlIGl0ZW0gc2hvdWxkIG5vdCBiZSB2aXNpYmxlIGF0IHRoYXRcbiAgICogc2VsZWN0aW9uIGluZGV4LiBUaGVzZSBmcmFjdGlvbnMgYXJlIHJldHVybmVkIGFzIGFuIGFycmF5LCB3aGVyZSB0aGVcbiAgICogYW5pbWF0aW9uIGZyYWN0aW9uIGF0IHBvc2l0aW9uIE4gY29ycmVzcG9uZHMgdG8gaG93IGl0ZW0gTiBzaG91bGQgYmUgc2hvd24uXG4gICAqL1xuICBhbmltYXRpb25GcmFjdGlvbnNGb3JTZWxlY3Rpb24oZWxlbWVudCwgc2VsZWN0aW9uKSB7XG5cbiAgICBjb25zdCBpdGVtcyA9IGVsZW1lbnQuaXRlbXM7XG4gICAgaWYgKCFpdGVtcykge1xuICAgICAgcmV0dXJuO1xuICAgIH1cblxuICAgIGNvbnN0IGl0ZW1Db3VudCA9IGl0ZW1zLmxlbmd0aDtcbiAgICBjb25zdCBzZWxlY3Rpb25XcmFwcyA9IGVsZW1lbnQuc2VsZWN0aW9uV3JhcHM7XG5cbiAgICByZXR1cm4gaXRlbXMubWFwKChpdGVtLCBpdGVtSW5kZXgpID0+IHtcbiAgICAgIC8vIEhvdyBtYW55IHN0ZXBzIGZyb20gdGhlIHNlbGVjdGlvbiBwb2ludCB0byB0aGlzIGl0ZW0/XG4gICAgICBjb25zdCBzdGVwcyA9IHN0ZXBzVG9JbmRleChpdGVtQ291bnQsIHNlbGVjdGlvbldyYXBzLCBzZWxlY3Rpb24sIGl0ZW1JbmRleCk7XG4gICAgICAvLyBUbyBjb252ZXJ0IHN0ZXBzIHRvIGFuaW1hdGlvbiBmcmFjdGlvbjpcbiAgICAgIC8vIHN0ZXBzICAgICAgYW5pbWF0aW9uIGZyYWN0aW9uXG4gICAgICAvLyAgMSAgICAgICAgIDAgICAgIChzdGFnZSByaWdodClcbiAgICAgIC8vICAwICAgICAgICAgMC41ICAgKGNlbnRlciBzdGFnZSlcbiAgICAgIC8vIC0xICAgICAgICAgMSAgICAgKHN0YWdlIGxlZnQpXG4gICAgICBjb25zdCBhbmltYXRpb25GcmFjdGlvbiA9ICgxIC0gc3RlcHMpIC8gMjtcbiAgICAgIHJldHVybiAoYW5pbWF0aW9uRnJhY3Rpb24gPj0gMCAmJiBhbmltYXRpb25GcmFjdGlvbiA8PSAxKSA/XG4gICAgICAgIGFuaW1hdGlvbkZyYWN0aW9uIDpcbiAgICAgICAgbnVsbDsgLy8gT3V0c2lkZSBhbmltYXRpb24gcmFuZ2VcbiAgICB9KTtcbiAgfSxcblxuICAvKlxuICAgKiBDYWxjdWxhdGUgdGhlIGFuaW1hdGlvbiB0aW1pbmdzIHRoYXQgc2hvdWxkIGJlIHVzZWQgdG8gc21vb3RobHkgYW5pbWF0ZSB0aGVcbiAgICogZWxlbWVudCdzIGl0ZW1zIGZyb20gb25lIHNlbGVjdGlvbiBzdGF0ZSB0byBhbm90aGVyLlxuICAgKlxuICAgKiBUaGlzIHJldHVybnMgYW4gYXJyYXkgb2YgdGltaW5ncywgd2hlcmUgdGhlIHRpbWluZyBhdCBwb3NpdGlvbiBOIHNob3VsZCBiZVxuICAgKiB1c2VkIHRvIGFuaW1hdGUgaXRlbSBOLiBJZiBhbiBpdGVtJ3MgdGltaW5nIGlzIG51bGwsIHRoZW4gdGhhdCBpdGVtIHNob3VsZFxuICAgKiBub3QgdGFrZSBwbGFjZSBpbiB0aGUgYW5pbWF0aW9uLCBhbmQgc2hvdWxkIGJlIGhpZGRlbiBpbnN0ZWFkLlxuICAgKi9cbiAgZWZmZWN0VGltaW5nc0ZvclNlbGVjdGlvbkFuaW1hdGlvbihlbGVtZW50LCBmcm9tU2VsZWN0aW9uLCB0b1NlbGVjdGlvbikge1xuXG4gICAgY29uc3QgaXRlbXMgPSBlbGVtZW50Lml0ZW1zO1xuICAgIGlmICghaXRlbXMpIHtcbiAgICAgIHJldHVybjtcbiAgICB9XG4gICAgY29uc3QgaXRlbUNvdW50ID0gaXRlbXMubGVuZ3RoO1xuICAgIGNvbnN0IHNlbGVjdGlvbldyYXBzID0gZWxlbWVudC5zZWxlY3Rpb25XcmFwcztcbiAgICBjb25zdCB0b0luZGV4ID0gRnJhY3Rpb25hbFNlbGVjdGlvbk1peGluLmhlbHBlcnMud3JhcHBlZFNlbGVjdGlvblBhcnRzKHRvU2VsZWN0aW9uLCBpdGVtQ291bnQsIHNlbGVjdGlvbldyYXBzKS5pbmRleDtcbiAgICBjb25zdCB0b3RhbFN0ZXBzID0gc3RlcHNUb0luZGV4KGl0ZW1Db3VudCwgc2VsZWN0aW9uV3JhcHMsIGZyb21TZWxlY3Rpb24sIHRvU2VsZWN0aW9uKTtcbiAgICBjb25zdCBkaXJlY3Rpb24gPSB0b3RhbFN0ZXBzID49IDAgPyAnbm9ybWFsJzogJ3JldmVyc2UnO1xuICAgIGNvbnN0IGZpbGwgPSAnYm90aCc7XG4gICAgY29uc3QgdG90YWxEdXJhdGlvbiA9IGVsZW1lbnQuc2VsZWN0aW9uQW5pbWF0aW9uRHVyYXRpb247XG4gICAgY29uc3Qgc3RlcER1cmF0aW9uID0gdG90YWxTdGVwcyAhPT0gMCA/XG4gICAgICB0b3RhbER1cmF0aW9uICogMiAvIE1hdGguY2VpbChNYXRoLmFicyh0b3RhbFN0ZXBzKSkgOlxuICAgICAgMDsgIC8vIE5vIHN0ZXBzIHJlcXVpcmVkLCBhbmltYXRpb24gd2lsbCBiZSBpbnN0YW50ZW5vdXMuXG5cbiAgICBjb25zdCB0aW1pbmdzID0gaXRlbXMubWFwKChpdGVtLCBpdGVtSW5kZXgpID0+IHtcbiAgICAgIGNvbnN0IHN0ZXBzID0gc3RlcHNUb0luZGV4KGl0ZW1Db3VudCwgc2VsZWN0aW9uV3JhcHMsIGl0ZW1JbmRleCwgdG9TZWxlY3Rpb24pO1xuICAgICAgLy8gSWYgd2UgaW5jbHVkZSB0aGlzIGl0ZW0gaW4gdGhlIHN0YWdnZXJlZCBzZXF1ZW5jZSBvZiBhbmltYXRpb25zIHdlJ3JlXG4gICAgICAvLyBjcmVhdGluZywgd2hlcmUgd291bGQgdGhlIGl0ZW0gYXBwZWFyIGluIHRoZSBzZXF1ZW5jZT9cbiAgICAgIGxldCBwb3NpdGlvbkluU2VxdWVuY2UgPSB0b3RhbFN0ZXBzIC0gc3RlcHM7XG4gICAgICBpZiAodG90YWxTdGVwcyA8IDApIHtcbiAgICAgICAgcG9zaXRpb25JblNlcXVlbmNlID0gLXBvc2l0aW9uSW5TZXF1ZW5jZTtcbiAgICAgIH1cbiAgICAgIC8vIFNvLCBpcyB0aGlzIGl0ZW0gcmVhbGx5IGluY2x1ZGVkIGluIHRoZSBzZXF1ZW5jZT9cbiAgICAgIGlmIChNYXRoLmNlaWwocG9zaXRpb25JblNlcXVlbmNlKSA+PSAwICYmIHBvc2l0aW9uSW5TZXF1ZW5jZSA8PSBNYXRoLmFicyh0b3RhbFN0ZXBzKSkge1xuICAgICAgICAvLyBOb3RlIHRoYXQgZGVsYXkgZm9yIGZpcnN0IGl0ZW0gd2lsbCBiZSBuZWdhdGl2ZS4gVGhhdCB3aWxsIGNhdXNlXG4gICAgICAgIC8vIHRoZSBhbmltYXRpb24gdG8gc3RhcnQgaGFsZndheSB0aHJvdWdoLCB3aGljaCBpcyB3aGF0IHdlIHdhbnQuXG4gICAgICAgIGNvbnN0IGRlbGF5ID0gc3RlcER1cmF0aW9uICogKHBvc2l0aW9uSW5TZXF1ZW5jZSAtIDEpLzI7XG4gICAgICAgIGNvbnN0IGVuZERlbGF5ID0gaXRlbUluZGV4ID09PSB0b0luZGV4ID9cbiAgICAgICAgICAtc3RlcER1cmF0aW9uLzIgOiAgIC8vIFN0b3AgaGFsZndheSB0aHJvdWdoLlxuICAgICAgICAgIDA7ICAgICAgICAgICAgICAvLyBQbGF5IGFuaW1hdGlvbiB1bnRpbCBlbmQuXG4gICAgICAgIHJldHVybiB7IGR1cmF0aW9uOiBzdGVwRHVyYXRpb24sIGRpcmVjdGlvbiwgZmlsbCwgZGVsYXksIGVuZERlbGF5IH07XG4gICAgICB9IGVsc2Uge1xuICAgICAgICByZXR1cm4gbnVsbDtcbiAgICAgIH1cbiAgICB9KTtcblxuICAgIHJldHVybiB0aW1pbmdzO1xuICB9XG5cbn07XG5cblxuLy8gS2V5ZnJhbWVzIGZvciBzdGFuZGFyZCBzZWxlY3Rpb24gYW5pbWF0aW9uIGVmZmVjdHMuXG5taXhpbi5zdGFuZGFyZEVmZmVjdEtleWZyYW1lcyA9IHtcblxuICAvLyBTaW1wbGUgY3Jvc3NmYWRlXG4gIGNyb3NzZmFkZTogW1xuICAgIHsgb3BhY2l0eTogMCB9LFxuICAgIHsgb3BhY2l0eTogMSB9LFxuICAgIHsgb3BhY2l0eTogMCB9XG4gIF0sXG5cbiAgLy8gUmV2ZWFsLCBhcyBpZiBzbGlkaW5nIHRoZSB0b3AgY2FyZCBvZmYgYSBkZWNrIG9mIGNhcmRzXG4gIHJldmVhbDogW1xuICAgIHsgdHJhbnNmb3JtOiAndHJhbnNsYXRlWCgwJSknLCB6SW5kZXg6IDAgfSxcbiAgICB7IHRyYW5zZm9ybTogJ3RyYW5zbGF0ZVgoMCUpJywgekluZGV4OiAxIH0sXG4gICAgeyB0cmFuc2Zvcm06ICd0cmFuc2xhdGVYKC0xMDAlKScsIHpJbmRleDogMiB9XG4gIF0sXG5cbiAgLy8gR29vZ2xlIFBob3Rvcy1zdHlsZSByZXZlYWwtd2l0aC1mYWRlIGFuaW1hdGlvblxuICByZXZlYWxXaXRoRmFkZTogW1xuICAgIHsgdHJhbnNmb3JtOiAndHJhbnNsYXRlWCgwJSkgc2NhbGUoMC43NSknLCBvcGFjaXR5OiAwLCB6SW5kZXg6IDAgfSxcbiAgICB7IHRyYW5zZm9ybTogJ3RyYW5zbGF0ZVgoMCUpIHNjYWxlKDEuMCknLCBvcGFjaXR5OiAxLCB6SW5kZXg6IDEgfSxcbiAgICB7IHRyYW5zZm9ybTogJ3RyYW5zbGF0ZVgoLTEwMCUpIHNjYWxlKDEuMCknLCBvcGFjaXR5OiAxLCB6SW5kZXg6IDIgfVxuICBdLFxuXG4gIC8vIENhcm91c2VsIHZhcmlhbnQgd2l0aCBhIGJpdCBvZiBvZmYtc3RhZ2UgZWxlbWVudHMgc2hvd2luZ1xuICBzaG93QWRqYWNlbnQ6IFtcbiAgICB7IHRyYW5zZm9ybTogJ3RyYW5zbGF0ZVgoNzglKSBzY2FsZSgwLjcpJywgekluZGV4OiAwIH0sXG4gICAgeyB0cmFuc2Zvcm06ICd0cmFuc2xhdGVYKDAlKSBzY2FsZSgwLjgyKScsIHpJbmRleDogMSB9LFxuICAgIHsgdHJhbnNmb3JtOiAndHJhbnNsYXRlWCgtNzglKSBzY2FsZSgwLjcpJywgekluZGV4OiAwIH1cbiAgXSxcblxuICAvLyBTaW1wbGUgc2xpZGVcbiAgc2xpZGU6IFtcbiAgICB7IHRyYW5zZm9ybTogJ3RyYW5zbGF0ZVgoMTAwJSknIH0sXG4gICAgeyB0cmFuc2Zvcm06ICd0cmFuc2xhdGVYKC0xMDAlKScgfVxuICBdLFxuXG4gIC8vIFNsaWRlLCB3aXRoIGEgZ2FwIGJldHdlZW5cbiAgc2xpZGVXaXRoR2FwOiBbXG4gICAgeyB0cmFuc2Zvcm06ICd0cmFuc2xhdGVYKDExMCUpJyB9LFxuICAgIHsgdHJhbnNmb3JtOiAndHJhbnNsYXRlWCgtMTEwJSknIH1cbiAgXVxuXG59O1xuXG5cbi8qXG4gKiBTbW9vdGhseSBhbmltYXRlIHRoZSBzZWxlY3Rpb24gYmV0d2VlbiB0aGUgaW5kaWNhdGVkIFwiZnJvbVwiIGFuZCBcInRvXCJcbiAqIGluZGljZXMuIFRoZSBmb3JtZXIgY2FuIGJlIGEgZnJhY3Rpb24sIGUuZy4sIHdoZW4gdGhlIHVzZXIgcmVsZWFzZXMgYSBmaW5nZXJcbiAqIHRvIGNvbXBsZXRlIGEgdG91Y2ggZHJhZywgYW5kIHRoZSBzZWxlY3Rpb24gd2lsbCBzbmFwIHRvIHRoZSBjbG9zZXN0IHdob2xlXG4gKiBpbmRleC5cbiAqL1xuZnVuY3Rpb24gYW5pbWF0ZVNlbGVjdGlvbihlbGVtZW50LCBmcm9tU2VsZWN0aW9uLCB0b1NlbGVjdGlvbikge1xuXG4gIHJlc2V0QW5pbWF0aW9ucyhlbGVtZW50KTtcblxuICAvLyBDYWxjdWxhdGUgdGhlIGFuaW1hdGlvbiB0aW1pbmdzLlxuICBjb25zdCBpdGVtcyA9IGVsZW1lbnQuaXRlbXM7XG4gIGNvbnN0IGtleWZyYW1lcyA9IGVsZW1lbnQuc2VsZWN0aW9uQW5pbWF0aW9uS2V5ZnJhbWVzO1xuICBlbGVtZW50W3BsYXlpbmdBbmltYXRpb25TeW1ib2xdID0gdHJ1ZTtcbiAgY29uc3QgdGltaW5ncyA9IG1peGluLmhlbHBlcnMuZWZmZWN0VGltaW5nc0ZvclNlbGVjdGlvbkFuaW1hdGlvbihlbGVtZW50LCBmcm9tU2VsZWN0aW9uLCB0b1NlbGVjdGlvbik7XG5cbiAgLy8gRmlndXJlIG91dCB3aGljaCBpdGVtIHdpbGwgYmUgdGhlIG9uZSAqYWZ0ZXIqIHRoZSBvbmUgd2UncmUgc2VsZWN0aW5nLlxuICBjb25zdCBpdGVtQ291bnQgPSBpdGVtcy5sZW5ndGg7XG4gIGNvbnN0IHNlbGVjdGlvbldyYXBzID0gZWxlbWVudC5zZWxlY3Rpb25XcmFwcztcbiAgY29uc3Qgc2VsZWN0aW9uSW5kZXggPSBGcmFjdGlvbmFsU2VsZWN0aW9uTWl4aW4uaGVscGVycy5zZWxlY3Rpb25QYXJ0cyh0b1NlbGVjdGlvbiwgaXRlbUNvdW50LCBzZWxlY3Rpb25XcmFwcykuaW5kZXg7XG4gIGNvbnN0IHRvdGFsU3RlcHMgPSBzdGVwc1RvSW5kZXgoaXRlbUNvdW50LCBzZWxlY3Rpb25XcmFwcywgZnJvbVNlbGVjdGlvbiwgdG9TZWxlY3Rpb24pO1xuICBjb25zdCBmb3J3YXJkID0gdG90YWxTdGVwcyA+PSAwO1xuICBsZXQgbmV4dFVwSW5kZXggPSBzZWxlY3Rpb25JbmRleCArIChmb3J3YXJkID8gMSA6IC0gMSk7XG4gIGlmIChzZWxlY3Rpb25XcmFwcykge1xuICAgIG5leHRVcEluZGV4ID0gRnJhY3Rpb25hbFNlbGVjdGlvbk1peGluLmhlbHBlcnMud3JhcHBlZFNlbGVjdGlvbihuZXh0VXBJbmRleCwgaXRlbUNvdW50KTtcbiAgfSBlbHNlIGlmICghaXNJdGVtSW5kZXhJbkJvdW5kcyhlbGVtZW50LCBuZXh0VXBJbmRleCkpIHtcbiAgICBuZXh0VXBJbmRleCA9IG51bGw7IC8vIEF0IHN0YXJ0L2VuZCBvZiBsaXN0OyBkb24ndCBoYXZlIGEgbmV4dCBpdGVtIHRvIHNob3cuXG4gIH1cblxuICAvLyBQbGF5IHRoZSBhbmltYXRpb25zIHVzaW5nIHRob3NlIHRpbWluZ3MuXG4gIGxldCBsYXN0QW5pbWF0aW9uRGV0YWlscztcbiAgdGltaW5ncy5mb3JFYWNoKCh0aW1pbmcsIGluZGV4KSA9PiB7XG4gICAgY29uc3QgaXRlbSA9IGl0ZW1zW2luZGV4XTtcbiAgICBpZiAodGltaW5nKSB7XG4gICAgICBzaG93SXRlbShpdGVtLCB0cnVlKTtcbiAgICAgIGNvbnN0IGFuaW1hdGlvbiA9IGl0ZW0uYW5pbWF0ZShrZXlmcmFtZXMsIHRpbWluZyk7XG4gICAgICBlbGVtZW50W2FuaW1hdGlvblN5bWJvbF1baW5kZXhdID0gYW5pbWF0aW9uO1xuICAgICAgaWYgKGluZGV4ID09PSBuZXh0VXBJbmRleCkge1xuICAgICAgICAvLyBUaGlzIGl0ZW0gd2lsbCBiZSBhbmltYXRlZCwgc28gd2lsbCBhbHJlYWR5IGJlIGluIHRoZSBkZXNpcmVkIHN0YXRlXG4gICAgICAgIC8vIGFmdGVyIHRoZSBhbmltYXRpb24gY29tcGxldGVzLlxuICAgICAgICBuZXh0VXBJbmRleCA9IG51bGw7XG4gICAgICB9XG4gICAgICBpZiAodGltaW5nLmVuZERlbGF5ICE9PSAwKSB7XG4gICAgICAgIC8vIFRoaXMgaXMgdGhlIGFuaW1hdGlvbiBmb3IgdGhlIGl0ZW0gdGhhdCB3aWxsIGJlIGxlZnQgc2VsZWN0ZWQuXG4gICAgICAgIC8vIFdlIHdhbnQgdG8gY2xlYW4gdXAgd2hlbiB0aGlzIGFuaW1hdGlvbiBjb21wbGV0ZXMuXG4gICAgICAgIGxhc3RBbmltYXRpb25EZXRhaWxzID0geyBhbmltYXRpb24sIGluZGV4LCB0aW1pbmcsIGZvcndhcmQgfTtcbiAgICAgIH1cbiAgICB9IGVsc2Uge1xuICAgICAgLy8gVGhpcyBpdGVtIGRvZXNuJ3QgcGFydGljaXBhdGUgaW4gdGhlIGFuaW1hdGlvbi5cbiAgICAgIHNob3dJdGVtKGl0ZW0sIGZhbHNlKTtcbiAgICB9XG4gIH0pO1xuXG4gIGlmIChsYXN0QW5pbWF0aW9uRGV0YWlscyAhPSBudWxsKSB7XG4gICAgLy8gQXJyYW5nZSBmb3IgY2xlYW4tdXAgd29yayB0byBiZSBwZXJmb3JtZWQuXG4gICAgbGFzdEFuaW1hdGlvbkRldGFpbHMubmV4dFVwSW5kZXggPSBuZXh0VXBJbmRleDtcbiAgICBsYXN0QW5pbWF0aW9uRGV0YWlscy5hbmltYXRpb24ub25maW5pc2ggPSBldmVudCA9PiBzZWxlY3Rpb25BbmltYXRpb25GaW5pc2hlZChlbGVtZW50LCBsYXN0QW5pbWF0aW9uRGV0YWlscyk7XG4gICAgZWxlbWVudFtsYXN0QW5pbWF0aW9uU3ltYm9sXSA9IGxhc3RBbmltYXRpb25EZXRhaWxzLmFuaW1hdGlvbjtcbiAgfSBlbHNlIHtcbiAgICAvLyBTaG91bGRuJ3QgaGFwcGVuIC0tIHdlIHNob3VsZCBhbHdheXMgaGF2ZSBhdCBsZWFzdCBvbmUgYW5pbWF0aW9uLlxuICAgIGVsZW1lbnRbcGxheWluZ0FuaW1hdGlvblN5bWJvbF0gPSBmYWxzZTtcbiAgfVxufVxuXG5cbmZ1bmN0aW9uIGdldEFuaW1hdGlvbkZvckl0ZW1JbmRleChlbGVtZW50LCBpbmRleCkge1xuICBpZiAoZWxlbWVudFthbmltYXRpb25TeW1ib2xdID09IG51bGwpIHtcbiAgICAvLyBOb3QgcmVhZHkgeWV0O1xuICAgIHJldHVybiBudWxsO1xuICB9XG4gIGxldCBhbmltYXRpb24gPSBlbGVtZW50W2FuaW1hdGlvblN5bWJvbF1baW5kZXhdO1xuICBpZiAoIWFuaW1hdGlvbikge1xuICAgIGNvbnN0IGl0ZW0gPSBlbGVtZW50Lml0ZW1zW2luZGV4XTtcbiAgICBhbmltYXRpb24gPSBpdGVtLmFuaW1hdGUoZWxlbWVudC5zZWxlY3Rpb25BbmltYXRpb25LZXlmcmFtZXMsIHtcbiAgICAgIGR1cmF0aW9uOiBlbGVtZW50LnNlbGVjdGlvbkFuaW1hdGlvbkR1cmF0aW9uLFxuICAgICAgZmlsbDogJ2JvdGgnXG4gICAgfSk7XG4gICAgYW5pbWF0aW9uLnBhdXNlKCk7XG4gICAgZWxlbWVudFthbmltYXRpb25TeW1ib2xdW2luZGV4XSA9IGFuaW1hdGlvbjtcbiAgfVxuICByZXR1cm4gYW5pbWF0aW9uO1xufVxuXG5mdW5jdGlvbiBpc0l0ZW1JbmRleEluQm91bmRzKGVsZW1lbnQsIGluZGV4KSB7XG4gIHJldHVybiBpbmRleCA+PSAwICYmIGVsZW1lbnQuaXRlbXMgJiYgaW5kZXggPCBlbGVtZW50Lml0ZW1zLmxlbmd0aDtcbn1cblxuLypcbiAqIFJlbmRlciB0aGUgc2VsZWN0aW9uIHN0YXRlIG9mIHRoZSBlbGVtZW50LlxuICpcbiAqIFRoaXMgY2FuIGJlIHVzZWQgdG8gcmUtcmVuZGVyIGEgcHJldmlvdXMgc2VsZWN0aW9uIHN0YXRlIChpZiB0aGVcbiAqIHNlbGVjdGVkSW5kZXggcGFyYW0gaXMgb21pdHRlZCksIHJlbmRlciB0aGUgc2VsZWN0aW9uIGluc3RhbnRseSBhdCBhIGdpdmVuXG4gKiB3aG9sZSBvciBmcmFjdGlvbmFsIHNlbGVjdGlvbiBpbmRleCwgb3IgYW5pbWF0ZSB0byBhIGdpdmVuIHNlbGVjdGlvbiBpbmRleC5cbiAqXG4gKiBUaGVyZSBhcmUgc2V2ZXJhbCBkaXN0aW5jdCBzY2VuYXJpb3Mgd2UgbmVlZCB0byBjb3ZlcjpcbiAqXG4gKiAxLiBJbml0aWFsIHBvc2l0aW9uaW5nLCBvciByZXBvc2l0aW9uaW5nIGFmdGVyIGNoYW5naW5nIGEgcHJvcGVydHkgbGlrZVxuICogICAgc2VsZWN0aW9uQW5pbWF0aW9uS2V5ZnJhbWVzIHRoYXQgYWZmZWN0cyByZW5kZXJpbmcuXG4gKiAyLiBBbmltYXRlIG9uIHNlbGVjdGVkSW5kZXggY2hhbmdlLiBUaGlzIHNob3VsZCBvdmVycmlkZSBhbnkgYW5pbWF0aW9uL3N3aXBlXG4gKiAgICBhbHJlYWR5IGluIHByb2dyZXNzLlxuICogMy4gSW5zdGFudGx5IHJlbmRlciB0aGUgY3VycmVudCBwb3NpdGlvbiBvZiBhIGRyYWcgb3BlcmF0aW9uIGluIHByb2dyZXNzLlxuICogNC4gQ29tcGxldGUgYSBkcmFnIG9wZXJhdGlvbi4gSWYgdGhlIGRyYWcgd2Fzbid0IGZhciBlbm91Z2ggdG8gYWZmZWN0XG4gKiAgICBzZWxlY3Rpb24sIHdlJ2xsIGp1c3QgYmUgcmVzdG9yaW5nIHRoZSBzZWxlY3RlZEZyYWN0aW9uIHRvIDAuXG4gKlxuICogSWYgdGhlIGxpc3QgZG9lcyBub3Qgd3JhcCwgYW55IHNlbGVjdGlvbiBwb3NpdGlvbiBvdXRzaWRlIHRoZSBsaXN0J3MgYm91bmRzXG4gKiB3aWxsIGJlIGRhbXBlZCB0byBwcm9kdWNlIGEgdmlzdWFsIGVmZmVjdCBvZiB0ZW5zaW9uLlxuICovXG5mdW5jdGlvbiByZW5kZXJTZWxlY3Rpb24oZWxlbWVudCwgc2VsZWN0ZWRJbmRleD1lbGVtZW50LnNlbGVjdGVkSW5kZXgsIHNlbGVjdGVkRnJhY3Rpb249ZWxlbWVudC5zZWxlY3RlZEZyYWN0aW9uKSB7XG4gIGNvbnN0IGl0ZW1Db3VudCA9IGVsZW1lbnQuaXRlbXMgPyBlbGVtZW50Lml0ZW1zLmxlbmd0aCA6IDA7XG4gIGlmIChpdGVtQ291bnQgPT09IDApIHtcbiAgICAvLyBOb3RoaW5nIHRvIHJlbmRlci5cbiAgICByZXR1cm47XG4gIH1cbiAgaWYgKHNlbGVjdGVkSW5kZXggPCAwKSB7XG4gICAgLy8gVE9ETzogSGFuZGxlIG5vIHNlbGVjdGlvbi5cbiAgICByZXR1cm47XG4gIH1cbiAgbGV0IHNlbGVjdGlvbiA9IHNlbGVjdGVkSW5kZXggKyBzZWxlY3RlZEZyYWN0aW9uO1xuICBpZiAoZWxlbWVudC5zZWxlY3Rpb25XcmFwcykge1xuICAgIC8vIEFwcGx5IHdyYXBwaW5nIHRvIGVuc3VyZSBjb25zaXN0ZW50IHJlcHJlc2VudGF0aW9uIG9mIHNlbGVjdGlvbi5cbiAgICBzZWxlY3Rpb24gPSBGcmFjdGlvbmFsU2VsZWN0aW9uTWl4aW4uaGVscGVycy53cmFwcGVkU2VsZWN0aW9uKHNlbGVjdGlvbiwgaXRlbUNvdW50KTtcbiAgfSBlbHNlIHtcbiAgICAvLyBBcHBseSBkYW1waW5nIGlmIG5lY2Vzc2FyeS5cbiAgICBzZWxlY3Rpb24gPSBGcmFjdGlvbmFsU2VsZWN0aW9uTWl4aW4uaGVscGVycy5kYW1wZWRTZWxlY3Rpb24oc2VsZWN0aW9uLCBpdGVtQ291bnQpO1xuICB9XG4gIGNvbnN0IHByZXZpb3VzU2VsZWN0aW9uID0gZWxlbWVudFtwcmV2aW91c1NlbGVjdGlvblN5bWJvbF07XG4gIC8vIFRPRE86IElmIGFuIGl0ZW0gY2hhbmdlcyBwb3NpdGlvbiBpbiB0aGUgRE9NLCB3ZSBlbmQgdXAgYW5pbWF0aW5nIGZyb21cbiAgLy8gaXRzIG9sZCBpbmRleCB0byBpdHMgbmV3IGluZGV4LCBidXQgd2UgcmVhbGx5IGRvbid0IHdhbnQgdG8gYW5pbWF0ZSBhdCBhbGwuXG4gIGlmICghZWxlbWVudFtzeW1ib2xzLmRyYWdnaW5nXSAmJiBwcmV2aW91c1NlbGVjdGlvbiAhPSBudWxsICYmXG4gICAgICBwcmV2aW91c1NlbGVjdGlvbiAhPT0gc2VsZWN0aW9uKSB7XG4gICAgLy8gQW5pbWF0ZSBzZWxlY3Rpb24gZnJvbSBwcmV2aW91cyBzdGF0ZSB0byBuZXcgc3RhdGUuXG4gICAgYW5pbWF0ZVNlbGVjdGlvbihlbGVtZW50LCBwcmV2aW91c1NlbGVjdGlvbiwgc2VsZWN0aW9uKTtcbiAgfSBlbHNlIGlmIChzZWxlY3RlZEZyYWN0aW9uID09PSAwICYmIGVsZW1lbnRbcGxheWluZ0FuaW1hdGlvblN5bWJvbF0pIHtcbiAgICAvLyBBbHJlYWR5IGluIHByb2Nlc3Mgb2YgYW5pbWF0aW5nIHRvIGZyYWN0aW9uIDAuIER1cmluZyB0aGF0IHByb2Nlc3MsXG4gICAgLy8gaWdub3JlIHN1YnNlcXVlbnQgYXR0ZW1wdHMgdG8gcmVuZGVyU2VsZWN0aW9uIHRvIGZyYWN0aW9uIDAuXG4gICAgcmV0dXJuO1xuICB9IGVsc2Uge1xuICAgIC8vIFJlbmRlciBjdXJyZW50IHNlbGVjdGlvbiBzdGF0ZSBpbnN0YW50bHkuXG4gICAgcmVuZGVyU2VsZWN0aW9uSW5zdGFudGx5KGVsZW1lbnQsIHNlbGVjdGlvbik7XG4gIH1cbiAgZWxlbWVudFtwcmV2aW91c1NlbGVjdGlvblN5bWJvbF0gPSBzZWxlY3Rpb247XG59XG5cbi8qXG4gKiBJbnN0YW50bHkgcmVuZGVyIChkb24ndCBhbmltYXRlKSB0aGUgZWxlbWVudCdzIGl0ZW1zIGF0IHRoZSBnaXZlbiB3aG9sZSBvclxuICogZnJhY3Rpb25hbCBzZWxlY3Rpb24gaW5kZXguXG4gKi9cbmZ1bmN0aW9uIHJlbmRlclNlbGVjdGlvbkluc3RhbnRseShlbGVtZW50LCB0b1NlbGVjdGlvbikge1xuICBpZiAoZWxlbWVudFtyZXNldEFuaW1hdGlvbnNPbk5leHRSZW5kZXJTeW1ib2xdKSB7XG4gICAgcmVzZXRBbmltYXRpb25zKGVsZW1lbnQpO1xuICAgIGVsZW1lbnRbcmVzZXRBbmltYXRpb25zT25OZXh0UmVuZGVyU3ltYm9sXSA9IGZhbHNlO1xuICB9XG4gIGNvbnN0IGFuaW1hdGlvbkZyYWN0aW9ucyA9IG1peGluLmhlbHBlcnMuYW5pbWF0aW9uRnJhY3Rpb25zRm9yU2VsZWN0aW9uKGVsZW1lbnQsIHRvU2VsZWN0aW9uKTtcbiAgYW5pbWF0aW9uRnJhY3Rpb25zLm1hcCgoYW5pbWF0aW9uRnJhY3Rpb24sIGluZGV4KSA9PiB7XG4gICAgY29uc3QgaXRlbSA9IGVsZW1lbnQuaXRlbXNbaW5kZXhdO1xuICAgIGlmIChhbmltYXRpb25GcmFjdGlvbiAhPSBudWxsKSB7XG4gICAgICBzaG93SXRlbShpdGVtLCB0cnVlKTtcbiAgICAgIHNldEFuaW1hdGlvbkZyYWN0aW9uKGVsZW1lbnQsIGluZGV4LCBhbmltYXRpb25GcmFjdGlvbik7XG4gICAgfSBlbHNlIHtcbiAgICAgIHNob3dJdGVtKGl0ZW0sIGZhbHNlKTtcbiAgICB9XG4gIH0pO1xufVxuXG4vKlxuICogV2UgbWFpbnRhaW4gYW4gYXJyYXkgY29udGFpbmluZyBhbiBhbmltYXRpb24gcGVyIGl0ZW0uIFRoaXMgaXMgdXNlZCBmb3IgdHdvXG4gKiByZWFzb25zOlxuICpcbiAqICogRHVyaW5nIGEgZHJhZyBvcGVyYXRpb24sIHdlIHdhbnQgdG8gYmUgYWJsZSB0byByZXVzZSBhbmltYXRpb25zIGJldHdlZW5cbiAqICAgZHJhZyB1cGRhdGVzLlxuICogKiBXaGVuIGEgc2VsZWN0aW9uIGFuaW1hdGlvbiBjb21wbGV0ZXMsIHdlIG5lZWQgdG8gYmUgYWJsZSB0byBsZWF2ZSB0aGVcbiAqICAgdmlzaWJpbGUgaXRlbXMgaW4gYSBwYXVzZWQgc3RhdGUuIExhdGVyLCB3ZSdsbCB3YW50IHRvIGJlIGFibGUgdG8gY2xlYW4gdXBcbiAqICAgdGhvc2UgYW5pbWF0aW9ucy5cbiAqXG4gKiBOb3RlIHRoYXQgdGhpcyBhcnJheSBpcyBzcGFyc2U6IGl0IHdpbGwgb25seSBob2xkIHVwIGZyb20gMOKAkzMgYW5pbWF0aW9ucyBhdFxuICogYW55IGdpdmVuIHBvaW50LlxuICovXG5mdW5jdGlvbiByZXNldEFuaW1hdGlvbnMoZWxlbWVudCkge1xuICBjb25zdCBhbmltYXRpb25zID0gZWxlbWVudFthbmltYXRpb25TeW1ib2xdO1xuICBpZiAoYW5pbWF0aW9ucykge1xuICAgIC8vIENhbmNlbCBleGlzdGluZyBhbmltYXRpb25zIHRvIHJlbW92ZSB0aGUgZWZmZWN0cyB0aGV5J3JlIGFwcGx5aW5nLlxuICAgIGFuaW1hdGlvbnMuZm9yRWFjaCgoYW5pbWF0aW9uLCBpbmRleCkgPT4ge1xuICAgICAgaWYgKGFuaW1hdGlvbikge1xuICAgICAgICBhbmltYXRpb24uY2FuY2VsKCk7XG4gICAgICAgIGFuaW1hdGlvbnNbaW5kZXhdID0gbnVsbDtcbiAgICAgIH1cbiAgICB9KTtcbiAgfVxuICBjb25zdCBpdGVtQ291bnQgPSBlbGVtZW50Lml0ZW1zID8gZWxlbWVudC5pdGVtcy5sZW5ndGggOiAwO1xuICBpZiAoIWFuaW1hdGlvbnMgfHwgYW5pbWF0aW9ucy5sZW5ndGggIT09IGl0ZW1Db3VudCkge1xuICAgIC8vIEhhdmVuJ3QgYW5pbWF0ZWQgYmVmb3JlIHdpdGggdGhpcyBudW1iZXIgb2YgaXRlbXM7IChyZSljcmVhdGUgYXJyYXkuXG4gICAgZWxlbWVudFthbmltYXRpb25TeW1ib2xdID0gbmV3IEFycmF5KGl0ZW1Db3VudCk7XG4gIH1cbn1cblxuLypcbiAqIFRoZSBsYXN0IGFuaW1hdGlvbiBpbiBvdXIgc2VsZWN0aW9uIGFuaW1hdGlvbiBoYXMgY29tcGxldGVkLiBDbGVhbiB1cC5cbiAqL1xuZnVuY3Rpb24gc2VsZWN0aW9uQW5pbWF0aW9uRmluaXNoZWQoZWxlbWVudCwgZGV0YWlscykge1xuXG4gIC8vIFdoZW4gdGhlIGxhc3QgYW5pbWF0aW9uIGNvbXBsZXRlcywgc2hvdyB0aGUgbmV4dCBpdGVtIGluIHRoZSBkaXJlY3Rpb25cbiAgLy8gd2UncmUgZ29pbmcuIFdhaXRpbmcgdG8gdGhhdCB1bnRpbCB0aGlzIHBvaW50IGlzIGEgYml0IG9mIGEgaGFjayB0byBhdm9pZFxuICAvLyBoYXZpbmcgYSBuZXh0IGl0ZW0gdGhhdCdzIGhpZ2hlciBpbiB0aGUgbmF0dXJhbCB6LW9yZGVyIG9ic2N1cmUgb3RoZXIgaXRlbXNcbiAgLy8gZHVyaW5nIGFuaW1hdGlvbi5cbiAgY29uc3QgbmV4dFVwSW5kZXggPSBkZXRhaWxzLm5leHRVcEluZGV4O1xuICBpZiAobmV4dFVwSW5kZXggIT0gbnVsbCkge1xuICAgIGlmIChlbGVtZW50W2FuaW1hdGlvblN5bWJvbF1bbmV4dFVwSW5kZXhdKSB7XG4gICAgICAvLyBDYW5jZWwgZXhpc3Rpbmcgc2VsZWN0aW9uIGFuaW1hdGlvbiBzbyB3ZSBjYW4gY29uc3RydWN0IGEgbmV3IG9uZS5cbiAgICAgIGVsZW1lbnRbYW5pbWF0aW9uU3ltYm9sXVtuZXh0VXBJbmRleF0uY2FuY2VsKCk7XG4gICAgICBlbGVtZW50W2FuaW1hdGlvblN5bWJvbF1bbmV4dFVwSW5kZXhdID0gbnVsbDtcbiAgICB9XG4gICAgY29uc3QgYW5pbWF0aW9uRnJhY3Rpb24gPSBkZXRhaWxzLmZvcndhcmQgPyAwIDogMTtcbiAgICBzZXRBbmltYXRpb25GcmFjdGlvbihlbGVtZW50LCBuZXh0VXBJbmRleCwgYW5pbWF0aW9uRnJhY3Rpb24pO1xuICAgIHNob3dJdGVtKGVsZW1lbnQuaXRlbXNbbmV4dFVwSW5kZXhdLCB0cnVlKTtcbiAgfVxuXG4gIGVsZW1lbnRbbGFzdEFuaW1hdGlvblN5bWJvbF0ub25maW5pc2ggPSBudWxsO1xuICBlbGVtZW50W3BsYXlpbmdBbmltYXRpb25TeW1ib2xdID0gZmFsc2U7XG59XG5cbi8qXG4gKiBQYXVzZSB0aGUgaW5kaWNhdGVkIGFuaW1hdGlvbiBhbmQgaGF2ZSBpdCBzaG93IHRoZSBhbmltYXRpb24gYXQgdGhlIGdpdmVuXG4gKiBmcmFjdGlvbiAoYmV0d2VlbiAwIGFuZCAxKSBvZiB0aGUgd2F5IHRocm91Z2ggdGhlIGFuaW1hdGlvbi5cbiAqL1xuZnVuY3Rpb24gc2V0QW5pbWF0aW9uRnJhY3Rpb24oZWxlbWVudCwgaXRlbUluZGV4LCBmcmFjdGlvbikge1xuICBjb25zdCBhbmltYXRpb24gPSBnZXRBbmltYXRpb25Gb3JJdGVtSW5kZXgoZWxlbWVudCwgaXRlbUluZGV4KTtcbiAgaWYgKGFuaW1hdGlvbikge1xuICAgIGNvbnN0IGR1cmF0aW9uID0gZWxlbWVudC5zZWxlY3Rpb25BbmltYXRpb25EdXJhdGlvbjtcbiAgICBpZiAoZHVyYXRpb24pIHtcbiAgICAgIGFuaW1hdGlvbi5jdXJyZW50VGltZSA9IGZyYWN0aW9uICogZHVyYXRpb247XG4gICAgfVxuICB9XG59XG5cbmZ1bmN0aW9uIHNob3dJdGVtKGl0ZW0sIGZsYWcpIHtcbiAgaXRlbS5zdHlsZS52aXNpYmlsaXR5ID0gZmxhZyA/ICd2aXNpYmxlJyA6ICdoaWRkZW4nO1xufVxuXG4vKlxuICogRmlndXJlIG91dCBob3cgbWFueSBzdGVwcyBpdCB3aWxsIHRha2UgdG8gZ28gZnJvbSBmcm9tU2VsZWN0aW9uIHRvXG4gKiB0b1NlbGVjdGlvbi4gVG8gZ28gZnJvbSBpdGVtIDMgdG8gaXRlbSA0IGlzIG9uZSBzdGVwLlxuICpcbiAqIElmIHdyYXBwaW5nIGlzIGFsbG93ZWQsIHRoZW4gZ29pbmcgZnJvbSB0aGUgbGFzdCBpdGVtIHRvIHRoZSBmaXJzdCB3aWxsIHRha2VcbiAqIG9uZSBzdGVwIChmb3J3YXJkKSwgYW5kIGdvaW5nIGZyb20gdGhlIGZpcnN0IGl0ZW0gdG8gdGhlIGxhc3Qgd2lsbCB0YWtlIG9uZVxuICogc3RlcCAoYmFja3dhcmQpLlxuICovXG5mdW5jdGlvbiBzdGVwc1RvSW5kZXgobGVuZ3RoLCBhbGxvd1dyYXAsIGZyb21TZWxlY3Rpb24sIHRvU2VsZWN0aW9uKSB7XG4gIGxldCBzdGVwcyA9IHRvU2VsZWN0aW9uIC0gZnJvbVNlbGVjdGlvbjtcbiAgLy8gV3JhcHBpbmcgb25seSBraWNrcyBpbiB3aGVuIGxpc3QgaGFzIG1vcmUgdGhhbiAxIGl0ZW0uXG4gIGlmIChhbGxvd1dyYXAgJiYgbGVuZ3RoID4gMSkge1xuICAgIGNvbnN0IHdyYXBTdGVwcyA9IGxlbmd0aCAtIE1hdGguYWJzKHN0ZXBzKTtcbiAgICBpZiAod3JhcFN0ZXBzIDw9IDEpIHtcbiAgICAgIC8vIFNwZWNpYWwgY2FzZVxuICAgICAgc3RlcHMgPSBzdGVwcyA8IDAgP1xuICAgICAgICB3cmFwU3RlcHMgOiAgIC8vIFdyYXAgZm9yd2FyZCBmcm9tIGxhc3QgaXRlbSB0byBmaXJzdC5cbiAgICAgICAgLXdyYXBTdGVwczsgICAvLyBXcmFwIGJhY2t3YXJkIGZyb20gZmlyc3QgaXRlbSB0byBsYXN0LlxuICAgIH1cbiAgfVxuICByZXR1cm4gc3RlcHM7XG59XG4iLCJpbXBvcnQgc3ltYm9scyBmcm9tICcuL3N5bWJvbHMnO1xuXG5cbi8vIFVzZWQgdG8gYXNzaWduIHVuaXF1ZSBJRHMgdG8gaXRlbSBlbGVtZW50cyB3aXRob3V0IElEcy5cbmxldCBpZENvdW50ID0gMDtcblxuXG4vKiBFeHBvcnRlZCBmdW5jdGlvbiBleHRlbmRzIGEgYmFzZSBjbGFzcyB3aXRoIFNlbGVjdGlvbkFyaWFBY3RpdmUuICovXG5leHBvcnQgZGVmYXVsdCAoYmFzZSkgPT4ge1xuXG4gIC8qKlxuICAgKiBNaXhpbiB3aGljaCB0cmVhdHMgdGhlIHNlbGVjdGVkIGl0ZW0gaW4gYSBsaXN0IGFzIHRoZSBhY3RpdmUgaXRlbSBpbiBBUklBXG4gICAqIGFjY2Vzc2liaWxpdHkgdGVybXMuXG4gICAqXG4gICAqIEhhbmRsaW5nIEFSSUEgc2VsZWN0aW9uIHN0YXRlIHByb3Blcmx5IGlzIGFjdHVhbGx5IHF1aXRlIGNvbXBsZXg6XG4gICAqXG4gICAqICogVGhlIGl0ZW1zIGluIHRoZSBsaXN0IG5lZWQgdG8gYmUgaW5kaWNhdGVkIGFzIHBvc3NpYmxlIGl0ZW1zIHZpYSBhbiBBUklBXG4gICAqICAgYHJvbGVgIGF0dHJpYnV0ZSB2YWx1ZSBzdWNoIGFzIFwib3B0aW9uXCIuXG4gICAqICogVGhlIHNlbGVjdGVkIGl0ZW0gbmVlZCB0byBiZSBtYXJrZWQgYXMgc2VsZWN0ZWQgYnkgc2V0dGluZyB0aGUgaXRlbSdzXG4gICAqICAgYGFyaWEtc2VsZWN0ZWRgIGF0dHJpYnV0ZSB0byB0cnVlICphbmQqIHRoZSBvdGhlciBpdGVtcyBuZWVkIGJlIG1hcmtlZCBhc1xuICAgKiAgICpub3QqIHNlbGVjdGVkIGJ5IHNldHRpbmcgYGFyaWEtc2VsZWN0ZWRgIHRvIGZhbHNlLlxuICAgKiAqIFRoZSBvdXRlcm1vc3QgZWxlbWVudCB3aXRoIHRoZSBrZXlib2FyZCBmb2N1cyBuZWVkcyB0byBoYXZlIGF0dHJpYnV0ZXNcbiAgICogICBzZXQgb24gaXQgc28gdGhhdCB0aGUgc2VsZWN0aW9uIGlzIGtub3dhYmxlIGF0IHRoZSBsaXN0IGxldmVsIHZpYSB0aGVcbiAgICogICBgYXJpYS1hY3RpdmVkZXNjZW5kYW50YCBhdHRyaWJ1dGUuXG4gICAqICogVXNlIG9mIGBhcmlhLWFjdGl2ZWRlc2NlbmRhbnRgIGluIHR1cm4gcmVxdWlyZXMgdGhhdCBhbGwgaXRlbXMgaW4gdGhlXG4gICAqICAgbGlzdCBoYXZlIElEIGF0dHJpYnV0ZXMgYXNzaWduZWQgdG8gdGhlbS5cbiAgICpcbiAgICogVGhpcyBtaXhpbiB0cmllcyB0byBhZGRyZXNzIGFsbCBvZiB0aGUgYWJvdmUgcmVxdWlyZW1lbnRzLiBUbyB0aGF0IGVuZCxcbiAgICogdGhpcyBtaXhpbiB3aWxsIGFzc2lnbiBnZW5lcmF0ZWQgSURzIHRvIGFueSBpdGVtIHRoYXQgZG9lc24ndCBhbHJlYWR5IGhhdmVcbiAgICogYW4gSUQuXG4gICAqXG4gICAqIEFSSUEgcmVsaWVzIG9uIGVsZW1lbnRzIHRvIHByb3ZpZGUgYHJvbGVgIGF0dHJpYnV0ZXMuIFRoaXMgbWl4aW4gd2lsbCBhcHBseVxuICAgKiBhIGRlZmF1bHQgcm9sZSBvZiBcImxpc3Rib3hcIiBvbiB0aGUgb3V0ZXIgbGlzdCBpZiBpdCBkb2Vzbid0IGFscmVhZHkgaGF2ZSBhblxuICAgKiBleHBsaWNpdCByb2xlLiBTaW1pbGFybHksIHRoaXMgbWl4aW4gd2lsbCBhcHBseSBhIGRlZmF1bHQgcm9sZSBvZiBcIm9wdGlvblwiXG4gICAqIHRvIGFueSBsaXN0IGl0ZW0gdGhhdCBkb2VzIG5vdCBhbHJlYWR5IGhhdmUgYSByb2xlIHNwZWNpZmllZC5cbiAgICpcbiAgICogVGhpcyBtaXhpbiBleHBlY3RzIGEgc2V0IG9mIG1lbWJlcnMgdGhhdCBtYW5hZ2UgdGhlIHN0YXRlIG9mIHRoZSBzZWxlY3Rpb246XG4gICAqIGBbc3ltYm9scy5pdGVtU2VsZWN0ZWRdYCwgYGl0ZW1BZGRlZGAsIGFuZCBgc2VsZWN0ZWRJbmRleGAuIFlvdSBjYW5cbiAgICogc3VwcGx5IHRoZXNlIHlvdXJzZWxmLCBvciBkbyBzbyB2aWFcbiAgICogW1NpbmdsZVNlbGVjdGlvbk1peGluXShTaW5nbGVTZWxlY3Rpb25NaXhpbi5tZCkuXG4gICAqL1xuICBjbGFzcyBTZWxlY3Rpb25BcmlhQWN0aXZlIGV4dGVuZHMgYmFzZSB7XG5cbiAgICBjb25uZWN0ZWRDYWxsYmFjaygpIHtcbiAgICAgIGlmIChzdXBlci5jb25uZWN0ZWRDYWxsYmFjaykgeyBzdXBlci5jb25uZWN0ZWRDYWxsYmFjaygpOyB9XG4gICAgICAvLyBTZXQgZGVmYXVsdCBBUklBIHJvbGUuXG4gICAgICBpZiAodGhpcy5nZXRBdHRyaWJ1dGUoJ3JvbGUnKSA9PSBudWxsICYmIHRoaXNbc3ltYm9scy5kZWZhdWx0c10ucm9sZSkge1xuICAgICAgICB0aGlzLnNldEF0dHJpYnV0ZSgncm9sZScsIHRoaXNbc3ltYm9scy5kZWZhdWx0c10ucm9sZSk7XG4gICAgICB9XG4gICAgfVxuXG4gICAgZ2V0IFtzeW1ib2xzLmRlZmF1bHRzXSgpIHtcbiAgICAgIGNvbnN0IGRlZmF1bHRzID0gc3VwZXJbc3ltYm9scy5kZWZhdWx0c10gfHwge307XG4gICAgICBkZWZhdWx0cy5yb2xlID0gJ2xpc3Rib3gnO1xuICAgICAgcmV0dXJuIGRlZmF1bHRzO1xuICAgIH1cblxuICAgIFtzeW1ib2xzLml0ZW1BZGRlZF0oaXRlbSkge1xuICAgICAgaWYgKHN1cGVyW3N5bWJvbHMuaXRlbUFkZGVkXSkgeyBzdXBlcltzeW1ib2xzLml0ZW1BZGRlZF0oaXRlbSk7IH1cblxuICAgICAgaWYgKCFpdGVtLmdldEF0dHJpYnV0ZSgncm9sZScpKSB7XG4gICAgICAgIC8vIEFzc2lnbiBhIGRlZmF1bHQgQVJJQSByb2xlLlxuICAgICAgICBpdGVtLnNldEF0dHJpYnV0ZSgncm9sZScsICdvcHRpb24nKTtcbiAgICAgIH1cblxuICAgICAgLy8gRW5zdXJlIGVhY2ggaXRlbSBoYXMgYW4gSUQgc28gd2UgY2FuIHNldCBhcmlhLWFjdGl2ZWRlc2NlbmRhbnQgb24gdGhlXG4gICAgICAvLyBvdmVyYWxsIGxpc3Qgd2hlbmV2ZXIgdGhlIHNlbGVjdGlvbiBjaGFuZ2VzLlxuICAgICAgLy9cbiAgICAgIC8vIFRoZSBJRCB3aWxsIHRha2UgdGhlIGZvcm0gb2YgYSBiYXNlIElEIHBsdXMgYSB1bmlxdWUgaW50ZWdlci4gVGhlIGJhc2VcbiAgICAgIC8vIElEIHdpbGwgYmUgaW5jb3Jwb3JhdGUgdGhlIGNvbXBvbmVudCdzIG93biBJRC4gRS5nLiwgaWYgYSBjb21wb25lbnQgaGFzXG4gICAgICAvLyBJRCBcImZvb1wiLCB0aGVuIGl0cyBpdGVtcyB3aWxsIGhhdmUgSURzIHRoYXQgbG9vayBsaWtlIFwiX2Zvb09wdGlvbjFcIi4gSWZcbiAgICAgIC8vIHRoZSBjb21wbmVudCBoYXMgbm8gSUQgaXRzZWxmLCBpdHMgaXRlbXMgd2lsbCBnZXQgSURzIHRoYXQgbG9vayBsaWtlXG4gICAgICAvLyBcIl9vcHRpb24xXCIuIEl0ZW0gSURzIGFyZSBwcmVmaXhlZCB3aXRoIGFuIHVuZGVyc2NvcmUgdG8gZGlmZmVyZW50aWF0ZVxuICAgICAgLy8gdGhlbSBmcm9tIG1hbnVhbGx5LWFzc2lnbmVkIElEcywgYW5kIHRvIG1pbmltaXplIHRoZSBwb3RlbnRpYWwgZm9yIElEXG4gICAgICAvLyBjb25mbGljdHMuXG4gICAgICBpZiAoIWl0ZW0uaWQpIHtcbiAgICAgICAgY29uc3QgYmFzZUlkID0gdGhpcy5pZCA/XG4gICAgICAgICAgICBcIl9cIiArIHRoaXMuaWQgKyBcIk9wdGlvblwiIDpcbiAgICAgICAgICAgIFwiX29wdGlvblwiO1xuICAgICAgICBpdGVtLmlkID0gYmFzZUlkICsgaWRDb3VudCsrO1xuICAgICAgfVxuICAgIH1cblxuICAgIFtzeW1ib2xzLml0ZW1TZWxlY3RlZF0oaXRlbSwgc2VsZWN0ZWQpIHtcbiAgICAgIGlmIChzdXBlcltzeW1ib2xzLml0ZW1TZWxlY3RlZF0pIHsgc3VwZXJbc3ltYm9scy5pdGVtU2VsZWN0ZWRdKGl0ZW0sIHNlbGVjdGVkKTsgfVxuICAgICAgaXRlbS5zZXRBdHRyaWJ1dGUoJ2FyaWEtc2VsZWN0ZWQnLCBzZWxlY3RlZCk7XG4gICAgICBjb25zdCBpdGVtSWQgPSBpdGVtLmlkO1xuICAgICAgaWYgKGl0ZW1JZCAmJiBzZWxlY3RlZCkge1xuICAgICAgICB0aGlzLnNldEF0dHJpYnV0ZSgnYXJpYS1hY3RpdmVkZXNjZW5kYW50JywgaXRlbUlkKTtcbiAgICAgIH1cbiAgICB9XG5cbiAgICBnZXQgc2VsZWN0ZWRJdGVtKCkge1xuICAgICAgcmV0dXJuIHN1cGVyLnNlbGVjdGVkSXRlbTtcbiAgICB9XG4gICAgc2V0IHNlbGVjdGVkSXRlbShpdGVtKSB7XG4gICAgICBpZiAoJ3NlbGVjdGVkSXRlbScgaW4gYmFzZS5wcm90b3R5cGUpIHsgc3VwZXIuc2VsZWN0ZWRJdGVtID0gaXRlbTsgfVxuICAgICAgaWYgKGl0ZW0gPT0gbnVsbCkge1xuICAgICAgICAvLyBTZWxlY3Rpb24gd2FzIHJlbW92ZWQuXG4gICAgICAgIHRoaXMucmVtb3ZlQXR0cmlidXRlKCdhcmlhLWFjdGl2ZWRlc2NlbmRhbnQnKTtcbiAgICAgIH1cbiAgICB9XG5cbiAgfVxuXG4gIHJldHVybiBTZWxlY3Rpb25BcmlhQWN0aXZlO1xufTtcbiIsIi8qIEV4cG9ydGVkIGZ1bmN0aW9uIGV4dGVuZHMgYSBiYXNlIGNsYXNzIHdpdGggU2hhZG93RWxlbWVudFJlZmVyZW5jZXMuICovXG5leHBvcnQgZGVmYXVsdCAoYmFzZSkgPT4ge1xuXG4gIC8qKlxuICAgKiBNaXhpbiB0byBjcmVhdGUgcmVmZXJlbmNlcyB0byBlbGVtZW50cyBpbiBhIGNvbXBvbmVudCdzIFNoYWRvdyBET00gc3VidHJlZS5cbiAgICpcbiAgICogVGhpcyBhZGRzIGEgbWVtYmVyIG9uIHRoZSBjb21wb25lbnQgY2FsbGVkIGB0aGlzLiRgIHRoYXQgY2FuIGJlIHVzZWQgdG9cbiAgICogcmVmZXJlbmNlIHNoYWRvdyBlbGVtZW50cyB3aXRoIElEcy4gRS5nLiwgaWYgY29tcG9uZW50J3Mgc2hhZG93IGNvbnRhaW5zIGFuXG4gICAqIGVsZW1lbnQgYDxidXR0b24gaWQ9XCJmb29cIj5gLCB0aGVuIHRoaXMgbWl4aW4gd2lsbCBjcmVhdGUgYSBtZW1iZXJcbiAgICogYHRoaXMuJC5mb29gIHRoYXQgcG9pbnRzIHRvIHRoYXQgYnV0dG9uLlxuICAgKlxuICAgKiBTdWNoIHJlZmVyZW5jZXMgc2ltcGxpZnkgYSBjb21wb25lbnQncyBhY2Nlc3MgdG8gaXRzIG93biBlbGVtZW50cy4gSW5cbiAgICogZXhjaGFuZ2UsIHRoaXMgbWl4aW4gdHJhZGVzIG9mZiBhIG9uZS10aW1lIGNvc3Qgb2YgcXVlcnlpbmcgYWxsIGVsZW1lbnRzIGluXG4gICAqIHRoZSBzaGFkb3cgdHJlZSBpbnN0ZWFkIG9mIHBheWluZyBhbiBvbmdvaW5nIGNvc3QgdG8gcXVlcnkgZm9yIGFuIGVsZW1lbnRcbiAgICogZWFjaCB0aW1lIHRoZSBjb21wb25lbnQgd2FudHMgdG8gaW5zcGVjdCBvciBtYW5pcHVsYXRlIGl0LlxuICAgKlxuICAgKiBUaGlzIG1peGluIGV4cGVjdHMgdGhlIGNvbXBvbmVudCB0byBkZWZpbmUgYSBTaGFkb3cgRE9NIHN1YnRyZWUuIFlvdSBjYW5cbiAgICogY3JlYXRlIHRoYXQgdHJlZSB5b3Vyc2VsZiwgb3IgbWFrZSB1c2Ugb2ZcbiAgICogW1NoYWRvd1RlbXBsYXRlTWl4aW5dKFNoYWRvd1RlbXBsYXRlTWl4aW4ubWQpLlxuICAgKlxuICAgKiBUaGlzIG1peGluIGlzIGluc3BpcmVkIGJ5IFBvbHltZXIncyBbYXV0b21hdGljXG4gICAqIG5vZGUgZmluZGluZ10oaHR0cHM6Ly93d3cucG9seW1lci1wcm9qZWN0Lm9yZy8xLjAvZG9jcy9kZXZndWlkZS9sb2NhbC1kb20uaHRtbCNub2RlLWZpbmRpbmcpXG4gICAqIGZlYXR1cmUuXG4gICAqL1xuICBjbGFzcyBTaGFkb3dFbGVtZW50UmVmZXJlbmNlcyBleHRlbmRzIGJhc2Uge1xuXG4gICAgY29uc3RydWN0b3IoKSB7XG4gICAgICBzdXBlcigpO1xuICAgICAgaWYgKHRoaXMuc2hhZG93Um9vdCkge1xuICAgICAgICAvLyBMb29rIGZvciBlbGVtZW50cyBpbiB0aGUgc2hhZG93IHN1YnRyZWUgdGhhdCBoYXZlIGlkIGF0dHJpYnV0ZXMuXG4gICAgICAgIC8vIEFuIGFsdGVybmF0aXZlbHkgaW1wbGVtZW50YXRpb24gb2YgdGhpcyBtaXhpbiB3b3VsZCBiZSB0byBqdXN0IGRlZmluZVxuICAgICAgICAvLyBhIHRoaXMuJCBnZXR0ZXIgdGhhdCBsYXppbHkgZG9lcyB0aGlzIHNlYXJjaCB0aGUgZmlyc3QgdGltZSBzb21lb25lXG4gICAgICAgIC8vIHRyaWVzIHRvIGFjY2VzcyB0aGlzLiQuIFRoYXQgbWlnaHQgaW50cm9kdWNlIHNvbWUgY29tcGxleGl0eSDigJMgaWYgdGhlXG4gICAgICAgIC8vIHRoZSB0cmVlIGNoYW5nZWQgYWZ0ZXIgaXQgd2FzIGZpcnN0IHBvcHVsYXRlZCwgdGhlIHJlc3VsdCBvZlxuICAgICAgICAvLyBzZWFyY2hpbmcgZm9yIGEgbm9kZSBtaWdodCBiZSBzb21ld2hhdCB1bnByZWRpY3RhYmxlLlxuICAgICAgICB0aGlzLiQgPSB7fTtcbiAgICAgICAgY29uc3Qgbm9kZXNXaXRoSWRzID0gdGhpcy5zaGFkb3dSb290LnF1ZXJ5U2VsZWN0b3JBbGwoJ1tpZF0nKTtcbiAgICAgICAgW10uZm9yRWFjaC5jYWxsKG5vZGVzV2l0aElkcywgbm9kZSA9PiB7XG4gICAgICAgICAgY29uc3QgaWQgPSBub2RlLmdldEF0dHJpYnV0ZSgnaWQnKTtcbiAgICAgICAgICB0aGlzLiRbaWRdID0gbm9kZTtcbiAgICAgICAgfSk7XG4gICAgICB9XG4gICAgfVxuXG4gICAgLyoqXG4gICAgICogVGhlIGNvbGxlY3Rpb24gb2YgcmVmZXJlbmNlcyB0byB0aGUgZWxlbWVudHMgd2l0aCBJRHMgaW4gYSBjb21wb25lbnQnc1xuICAgICAqIFNoYWRvdyBET00gc3VidHJlZS5cbiAgICAgKlxuICAgICAqIEB0eXBlIHtvYmplY3R9XG4gICAgICogQG1lbWJlciAkXG4gICAgICovXG4gIH1cblxuICByZXR1cm4gU2hhZG93RWxlbWVudFJlZmVyZW5jZXM7XG59O1xuIiwiaW1wb3J0IHN5bWJvbHMgZnJvbSAnLi4vc3JjL3N5bWJvbHMnO1xuXG5cbi8qIEV4cG9ydGVkIGZ1bmN0aW9uIGV4dGVuZHMgYSBiYXNlIGNsYXNzIHdpdGggU2hhZG93VGVtcGxhdGUuICovXG5leHBvcnQgZGVmYXVsdCAoYmFzZSkgPT4ge1xuXG4gIC8qKlxuICAgKiBNaXhpbiBmb3Igc3RhbXBpbmcgYSB0ZW1wbGF0ZSBpbnRvIGEgU2hhZG93IERPTSBzdWJ0cmVlIHVwb24gY29tcG9uZW50XG4gICAqIGluc3RhbnRpYXRpb24uXG4gICAqXG4gICAqIFRvIHVzZSB0aGlzIG1peGluLCBkZWZpbmUgYSBgdGVtcGxhdGVgIHByb3BlcnR5IGFzIGEgc3RyaW5nIG9yIEhUTUxcbiAgICogYDx0ZW1wbGF0ZT5gIGVsZW1lbnQ6XG4gICAqXG4gICAqICAgICBjbGFzcyBNeUVsZW1lbnQgZXh0ZW5kcyBTaGFkb3dUZW1wbGF0ZU1peGluKEhUTUxFbGVtZW50KSB7XG4gICAqICAgICAgIGdldCBbc3ltYm9scy50ZW1wbGF0ZV0oKSB7XG4gICAqICAgICAgICAgcmV0dXJuIGBIZWxsbywgPGVtPndvcmxkPC9lbT4uYDtcbiAgICogICAgICAgfVxuICAgKiAgICAgfVxuICAgKlxuICAgKiBXaGVuIHlvdXIgY29tcG9uZW50IGNsYXNzIGlzIGluc3RhbnRpYXRlZCwgYSBzaGFkb3cgcm9vdCB3aWxsIGJlIGNyZWF0ZWQgb25cbiAgICogdGhlIGluc3RhbmNlLCBhbmQgdGhlIGNvbnRlbnRzIG9mIHRoZSB0ZW1wbGF0ZSB3aWxsIGJlIGNsb25lZCBpbnRvIHRoZVxuICAgKiBzaGFkb3cgcm9vdC4gSWYgeW91ciBjb21wb25lbnQgZG9lcyBub3QgZGVmaW5lIGEgYHRlbXBsYXRlYCBwcm9wZXJ0eSwgdGhpc1xuICAgKiBtaXhpbiBoYXMgbm8gZWZmZWN0LlxuICAgKlxuICAgKiBGb3IgdGhlIHRpbWUgYmVpbmcsIHRoaXMgZXh0ZW5zaW9uIHJldGFpbnMgc3VwcG9ydCBmb3IgU2hhZG93IERPTSB2MC4gVGhhdFxuICAgKiB3aWxsIGV2ZW50dWFsbHkgYmUgZGVwcmVjYXRlZCBhcyBicm93c2VycyAoYW5kIHRoZSBTaGFkb3cgRE9NIHBvbHlmaWxsKVxuICAgKiBpbXBsZW1lbnQgU2hhZG93IERPTSB2MS5cbiAgICovXG4gIGNsYXNzIFNoYWRvd1RlbXBsYXRlIGV4dGVuZHMgYmFzZSB7XG5cbiAgICAvKlxuICAgICAqIElmIHRoZSBjb21wb25lbnQgZGVmaW5lcyBhIHRlbXBsYXRlLCBhIHNoYWRvdyByb290IHdpbGwgYmUgY3JlYXRlZCBvbiB0aGVcbiAgICAgKiBjb21wb25lbnQgaW5zdGFuY2UsIGFuZCB0aGUgdGVtcGxhdGUgc3RhbXBlZCBpbnRvIGl0LlxuICAgICAqL1xuICAgIGNvbnN0cnVjdG9yKCkge1xuICAgICAgc3VwZXIoKTtcbiAgICAgIGxldCB0ZW1wbGF0ZSA9IHRoaXNbc3ltYm9scy50ZW1wbGF0ZV07XG4gICAgICAvLyBUT0RPOiBTYXZlIHRoZSBwcm9jZXNzZWQgdGVtcGxhdGUgd2l0aCB0aGUgY29tcG9uZW50J3MgY2xhc3MgcHJvdG90eXBlXG4gICAgICAvLyBzbyBpdCBkb2Vzbid0IG5lZWQgdG8gYmUgcHJvY2Vzc2VkIHdpdGggZXZlcnkgaW5zdGFudGlhdGlvbi5cbiAgICAgIGlmICh0ZW1wbGF0ZSkge1xuXG4gICAgICAgIGlmICh0eXBlb2YgdGVtcGxhdGUgPT09ICdzdHJpbmcnKSB7XG4gICAgICAgICAgLy8gVXBncmFkZSBwbGFpbiBzdHJpbmcgdG8gcmVhbCB0ZW1wbGF0ZS5cbiAgICAgICAgICB0ZW1wbGF0ZSA9IGNyZWF0ZVRlbXBsYXRlV2l0aElubmVySFRNTCh0ZW1wbGF0ZSk7XG4gICAgICAgIH1cblxuICAgICAgICBpZiAod2luZG93LlNoYWRvd0RPTVBvbHlmaWxsKSB7XG4gICAgICAgICAgc2hpbVRlbXBsYXRlU3R5bGVzKHRlbXBsYXRlLCB0aGlzLmxvY2FsTmFtZSk7XG4gICAgICAgIH1cblxuICAgICAgICBjb25zdCByb290ID0gdGhpcy5hdHRhY2hTaGFkb3coeyBtb2RlOiAnb3BlbicgfSk7XG4gICAgICAgIGNvbnN0IGNsb25lID0gZG9jdW1lbnQuaW1wb3J0Tm9kZSh0ZW1wbGF0ZS5jb250ZW50LCB0cnVlKTtcbiAgICAgICAgcm9vdC5hcHBlbmRDaGlsZChjbG9uZSk7XG4gICAgICB9XG4gICAgfVxuXG4gIH1cblxuICByZXR1cm4gU2hhZG93VGVtcGxhdGU7XG59O1xuXG5cbi8vIENvbnZlcnQgYSBwbGFpbiBzdHJpbmcgb2YgSFRNTCBpbnRvIGEgcmVhbCB0ZW1wbGF0ZSBlbGVtZW50LlxuZnVuY3Rpb24gY3JlYXRlVGVtcGxhdGVXaXRoSW5uZXJIVE1MKGlubmVySFRNTCkge1xuICBjb25zdCB0ZW1wbGF0ZSA9IGRvY3VtZW50LmNyZWF0ZUVsZW1lbnQoJ3RlbXBsYXRlJyk7XG4gIC8vIFJFVklFVzogSXMgdGhlcmUgYW4gZWFzaWVyIHdheSB0byBkbyB0aGlzP1xuICAvLyBXZSdkIGxpa2UgdG8ganVzdCBzZXQgaW5uZXJIVE1MIG9uIHRoZSB0ZW1wbGF0ZSBjb250ZW50LCBidXQgc2luY2UgaXQnc1xuICAvLyBhIERvY3VtZW50RnJhZ21lbnQsIHRoYXQgZG9lc24ndCB3b3JrLlxuICBjb25zdCBkaXYgPSBkb2N1bWVudC5jcmVhdGVFbGVtZW50KCdkaXYnKTtcbiAgZGl2LmlubmVySFRNTCA9IGlubmVySFRNTDtcbiAgd2hpbGUgKGRpdi5jaGlsZE5vZGVzLmxlbmd0aCA+IDApIHtcbiAgICB0ZW1wbGF0ZS5jb250ZW50LmFwcGVuZENoaWxkKGRpdi5jaGlsZE5vZGVzWzBdKTtcbiAgfVxuICByZXR1cm4gdGVtcGxhdGU7XG59XG5cbi8vIEludm9rZSBiYXNpYyBzdHlsZSBzaGltbWluZyB3aXRoIFNoYWRvd0NTUy5cbmZ1bmN0aW9uIHNoaW1UZW1wbGF0ZVN0eWxlcyh0ZW1wbGF0ZSwgdGFnKSB7XG4gIHdpbmRvdy5XZWJDb21wb25lbnRzLlNoYWRvd0NTUy5zaGltU3R5bGluZyh0ZW1wbGF0ZS5jb250ZW50LCB0YWcpO1xufVxuIiwiaW1wb3J0IGNyZWF0ZVN5bWJvbCBmcm9tICcuL2NyZWF0ZVN5bWJvbCc7XG5pbXBvcnQgc3ltYm9scyBmcm9tICcuL3N5bWJvbHMnO1xuXG5cbi8vIFN5bWJvbHMgZm9yIHByaXZhdGUgZGF0YSBtZW1iZXJzIG9uIGFuIGVsZW1lbnQuXG5jb25zdCBjYW5TZWxlY3ROZXh0U3ltYm9sID0gY3JlYXRlU3ltYm9sKCdjYW5TZWxlY3ROZXh0Jyk7XG5jb25zdCBjYW5TZWxlY3RQcmV2aW91c1N5bWJvbCA9IGNyZWF0ZVN5bWJvbCgnY2FuU2VsZWN0UHJldmlvdXMnKTtcbmNvbnN0IHNlbGVjdGlvblJlcXVpcmVkU3ltYm9sID0gY3JlYXRlU3ltYm9sKCdzZWxlY3Rpb25SZXF1aXJlZCcpO1xuY29uc3Qgc2VsZWN0aW9uV3JhcHNTeW1ib2wgPSBjcmVhdGVTeW1ib2woJ3NlbGVjdGlvbldyYXBzJyk7XG5cbi8vIFdlIHdhbnQgdG8gZXhwb3NlIGJvdGggc2VsZWN0ZWRJbmRleCBhbmQgc2VsZWN0ZWRJdGVtIGFzIGluZGVwZW5kZW50XG4vLyBwcm9wZXJ0aWVzIGJ1dCBrZWVwIHRoZW0gaW4gc3luYy4gVGhpcyBhbGxvd3MgYSBjb21wb25lbnQgdXNlciB0byByZWZlcmVuY2Vcbi8vIHRoZSBzZWxlY3Rpb24gYnkgd2hhdGV2ZXIgbWVhbnMgaXMgbW9zdCBuYXR1cmFsIGZvciB0aGVpciBzaXR1YXRpb24uXG4vL1xuLy8gVG8gZWZmaWNpZW50bHkga2VlcCB0aGVzZSBwcm9wZXJ0aWVzIGluIHN5bmMsIHdlIHRyYWNrIFwiZXh0ZXJuYWxcIiBhbmRcbi8vIFwiaW50ZXJuYWxcIiByZWZlcmVuY2VzIGZvciBlYWNoIHByb3BlcnR5OlxuLy9cbi8vIFRoZSBleHRlcm5hbCBpbmRleCBvciBpdGVtIGlzIHRoZSBvbmUgd2UgcmVwb3J0IHRvIHRoZSBvdXRzaWRlIHdvcmxkIHdoZW5cbi8vIGFza2VkIGZvciBzZWxlY3Rpb24uICBXaGVuIGhhbmRsaW5nIGEgY2hhbmdlIHRvIGluZGV4IG9yIGl0ZW0sIHdlIHVwZGF0ZSB0aGVcbi8vIGV4dGVybmFsIHJlZmVyZW5jZSBhcyBzb29uIGFzIHBvc3NpYmxlLCBzbyB0aGF0IGlmIGFueW9uZSBpbW1lZGlhdGVseSBhc2tzXG4vLyBmb3IgdGhlIGN1cnJlbnQgc2VsZWN0aW9uLCB0aGV5IHdpbGwgcmVjZWl2ZSBhIHN0YWJsZSBhbnN3ZXIuXG4vL1xuLy8gVGhlIGludGVybmFsIGluZGV4IG9yIGl0ZW0gdHJhY2tzIHdoaWNoZXZlciBpbmRleCBvciBpdGVtIGxhc3QgcmVjZWl2ZWQgdGhlXG4vLyBmdWxsIHNldCBvZiBwcm9jZXNzaW5nLiBQcm9jZXNzaW5nIGluY2x1ZGVzIHJhaXNpbmcgYSBjaGFuZ2UgZXZlbnQgZm9yIHRoZVxuLy8gbmV3IHZhbHVlLiBPbmNlIHdlJ3ZlIGJlZ3VuIHRoYXQgcHJvY2Vzc2luZywgd2Ugc3RvcmUgdGhlIG5ldyB2YWx1ZSBhcyB0aGVcbi8vIGludGVybmFsIHZhbHVlIHRvIGluZGljYXRlIHdlJ3ZlIGhhbmRsZWQgaXQuXG4vL1xuY29uc3QgZXh0ZXJuYWxTZWxlY3RlZEluZGV4U3ltYm9sID0gY3JlYXRlU3ltYm9sKCdleHRlcm5hbFNlbGVjdGVkSW5kZXgnKTtcbmNvbnN0IGV4dGVybmFsU2VsZWN0ZWRJdGVtU3ltYm9sID0gY3JlYXRlU3ltYm9sKCdleHRlcm5hbFNlbGVjdGVkSXRlbScpO1xuY29uc3QgaW50ZXJuYWxTZWxlY3RlZEluZGV4U3ltYm9sID0gY3JlYXRlU3ltYm9sKCdpbnRlcm5hbFNlbGVjdGVkSW5kZXgnKTtcbmNvbnN0IGludGVybmFsU2VsZWN0ZWRJdGVtU3ltYm9sID0gY3JlYXRlU3ltYm9sKCdpbnRlcm5hbFNlbGVjdGVkSXRlbScpO1xuXG5cbi8qIEV4cG9ydGVkIGZ1bmN0aW9uIGV4dGVuZHMgYSBiYXNlIGNsYXNzIHdpdGggU2luZ2xlU2VsZWN0aW9uLiAqL1xuZXhwb3J0IGRlZmF1bHQgKGJhc2UpID0+IHtcblxuICAvKipcbiAgICogTWl4aW4gd2hpY2ggbWFuYWdlcyBzaW5nbGUtc2VsZWN0aW9uIHNlbWFudGljcyBmb3IgaXRlbXMgaW4gYSBsaXN0LlxuICAgKlxuICAgKiBUaGlzIG1peGluIGV4cGVjdHMgYSBjb21wb25lbnQgdG8gcHJvdmlkZSBhbiBgaXRlbXNgIEFycmF5IG9yIE5vZGVMaXN0IG9mXG4gICAqIGFsbCBlbGVtZW50cyBpbiB0aGUgbGlzdC4gQSBzdGFuZGFyZCB3YXkgdG8gZG8gdGhhdCB3aXRoIGlzIHRoZVxuICAgKiBbQ29udGVudEl0ZW1zTWl4aW5dKENvbnRlbnRJdGVtc01peGluLm1kKSwgd2hpY2ggdGFrZXMgYSBjb21wb25lbnQnc1xuICAgKiBjb250ZW50ICh0eXBpY2FsbHkgaXRzIGRpc3RyaWJ1dGVkIGNoaWxkcmVuKSBhcyB0aGUgc2V0IG9mIGxpc3QgaXRlbXM7IHNlZVxuICAgKiB0aGF0IG1peGluIGZvciBkZXRhaWxzLlxuICAgKlxuICAgKiBUaGlzIG1peGluIHRyYWNrcyBhIHNpbmdsZSBzZWxlY3RlZCBpdGVtIGluIHRoZSBsaXN0LCBhbmQgcHJvdmlkZXMgbWVhbnMgdG9cbiAgICogZ2V0IGFuZCBzZXQgdGhhdCBzdGF0ZSBieSBpdGVtIHBvc2l0aW9uIChgc2VsZWN0ZWRJbmRleGApIG9yIGl0ZW0gaWRlbnRpdHlcbiAgICogKGBzZWxlY3RlZEl0ZW1gKS4gVGhlIHNlbGVjdGlvbiBjYW4gYmUgbW92ZWQgaW4gdGhlIGxpc3QgdmlhIHRoZSBtZXRob2RzXG4gICAqIGBzZWxlY3RGaXJzdGAsIGBzZWxlY3RMYXN0YCwgYHNlbGVjdE5leHRgLCBhbmQgYHNlbGVjdFByZXZpb3VzYC5cbiAgICpcbiAgICogVGhpcyBtaXhpbiBkb2VzIG5vdCBwcm9kdWNlIGFueSB1c2VyLXZpc2libGUgZWZmZWN0cyB0byByZXByZXNlbnRcbiAgICogc2VsZWN0aW9uLiBPdGhlciBtaXhpbnMsIHN1Y2ggYXNcbiAgICogW1NlbGVjdGlvbkFyaWFBY3RpdmVNaXhpbl0oU2VsZWN0aW9uQXJpYUFjdGl2ZU1peGluLm1kKSxcbiAgICogW1NlbGVjdGlvbkhpZ2hsaWdodE1peGluXShTZWxlY3Rpb25IaWdobGlnaHRNaXhpbi5tZCkgYW5kXG4gICAqIFtTZWxlY3Rpb25JblZpZXdNaXhpbl0oU2VsZWN0aW9uSW5WaWV3TWl4aW4ubWQpLCBtb2RpZnkgdGhlIHNlbGVjdGVkIGl0ZW1cbiAgICogaW4gY29tbW9uIHdheXMgdG8gbGV0IHRoZSB1c2VyIGtub3cgYSBnaXZlbiBpdGVtIGlzIHNlbGVjdGVkIG9yIG5vdFxuICAgKiBzZWxlY3RlZC5cbiAgICovXG4gIGNsYXNzIFNpbmdsZVNlbGVjdGlvbiBleHRlbmRzIGJhc2Uge1xuXG4gICAgY29uc3RydWN0b3IoKSB7XG4gICAgICBzdXBlcigpO1xuICAgICAgLy8gU2V0IGRlZmF1bHRzLlxuICAgICAgaWYgKHR5cGVvZiB0aGlzLnNlbGVjdGlvblJlcXVpcmVkID09PSAndW5kZWZpbmVkJykge1xuICAgICAgICB0aGlzLnNlbGVjdGlvblJlcXVpcmVkID0gdGhpc1tzeW1ib2xzLmRlZmF1bHRzXS5zZWxlY3Rpb25SZXF1aXJlZDtcbiAgICAgIH1cbiAgICAgIGlmICh0eXBlb2YgdGhpcy5zZWxlY3Rpb25XcmFwcyA9PT0gJ3VuZGVmaW5lZCcpIHtcbiAgICAgICAgdGhpcy5zZWxlY3Rpb25XcmFwcyA9IHRoaXNbc3ltYm9scy5kZWZhdWx0c10uc2VsZWN0aW9uV3JhcHM7XG4gICAgICB9XG4gICAgfVxuXG4gICAgLyoqXG4gICAgICogVHJ1ZSBpZiB0aGUgc2VsZWN0aW9uIGNhbiBiZSBtb3ZlZCB0byB0aGUgbmV4dCBpdGVtLCBmYWxzZSBpZiBub3QgKHRoZVxuICAgICAqIHNlbGVjdGVkIGl0ZW0gaXMgdGhlIGxhc3QgaXRlbSBpbiB0aGUgbGlzdCkuXG4gICAgICpcbiAgICAgKiBAdHlwZSB7Ym9vbGVhbn1cbiAgICAgKi9cbiAgICBnZXQgY2FuU2VsZWN0TmV4dCgpIHtcbiAgICAgIHJldHVybiB0aGlzW2NhblNlbGVjdE5leHRTeW1ib2xdO1xuICAgIH1cbiAgICBzZXQgY2FuU2VsZWN0TmV4dChjYW5TZWxlY3ROZXh0KSB7XG4gICAgICBjb25zdCBwcmV2aW91c0NhblNlbGVjdE5leHQgPSB0aGlzW2NhblNlbGVjdE5leHRTeW1ib2xdO1xuICAgICAgdGhpc1tjYW5TZWxlY3ROZXh0U3ltYm9sXSA9IGNhblNlbGVjdE5leHQ7XG4gICAgICBpZiAoJ2NhblNlbGVjdE5leHQnIGluIGJhc2UucHJvdG90eXBlKSB7IHN1cGVyLmNhblNlbGVjdE5leHQgPSBjYW5TZWxlY3ROZXh0OyB9XG4gICAgICBpZiAoY2FuU2VsZWN0TmV4dCAhPT0gcHJldmlvdXNDYW5TZWxlY3ROZXh0KSB7XG4gICAgICAgIHRoaXMuZGlzcGF0Y2hFdmVudChuZXcgQ3VzdG9tRXZlbnQoJ2Nhbi1zZWxlY3QtbmV4dC1jaGFuZ2VkJykpO1xuICAgICAgfVxuICAgIH1cblxuICAgIC8qKlxuICAgICAqIFRydWUgaWYgdGhlIHNlbGVjdGlvbiBjYW4gYmUgbW92ZWQgdG8gdGhlIHByZXZpb3VzIGl0ZW0sIGZhbHNlIGlmIG5vdFxuICAgICAqICh0aGUgc2VsZWN0ZWQgaXRlbSBpcyB0aGUgZmlyc3Qgb25lIGluIHRoZSBsaXN0KS5cbiAgICAgKlxuICAgICAqIEB0eXBlIHtib29sZWFufVxuICAgICAqL1xuICAgIGdldCBjYW5TZWxlY3RQcmV2aW91cygpIHtcbiAgICAgIHJldHVybiB0aGlzW2NhblNlbGVjdFByZXZpb3VzU3ltYm9sXTtcbiAgICB9XG4gICAgc2V0IGNhblNlbGVjdFByZXZpb3VzKGNhblNlbGVjdFByZXZpb3VzKSB7XG4gICAgICBjb25zdCBwcmV2aW91c0NhblNlbGVjdFByZXZpb3VzID0gdGhpc1tjYW5TZWxlY3RQcmV2aW91c1N5bWJvbF07XG4gICAgICB0aGlzW2NhblNlbGVjdFByZXZpb3VzU3ltYm9sXSA9IGNhblNlbGVjdFByZXZpb3VzO1xuICAgICAgaWYgKCdjYW5TZWxlY3RQcmV2aW91cycgaW4gYmFzZS5wcm90b3R5cGUpIHsgc3VwZXIuY2FuU2VsZWN0UHJldmlvdXMgPSBjYW5TZWxlY3RQcmV2aW91czsgfVxuICAgICAgaWYgKGNhblNlbGVjdFByZXZpb3VzICE9PSBwcmV2aW91c0NhblNlbGVjdFByZXZpb3VzKSB7XG4gICAgICAgIHRoaXMuZGlzcGF0Y2hFdmVudChuZXcgQ3VzdG9tRXZlbnQoJ2Nhbi1zZWxlY3QtcHJldmlvdXMtY2hhbmdlZCcpKTtcbiAgICAgIH1cbiAgICB9XG5cbiAgICBnZXQgW3N5bWJvbHMuZGVmYXVsdHNdKCkge1xuICAgICAgY29uc3QgZGVmYXVsdHMgPSBzdXBlcltzeW1ib2xzLmRlZmF1bHRzXSB8fCB7fTtcbiAgICAgIGRlZmF1bHRzLnNlbGVjdGlvblJlcXVpcmVkID0gZmFsc2U7XG4gICAgICBkZWZhdWx0cy5zZWxlY3Rpb25XcmFwcyA9IGZhbHNlO1xuICAgICAgcmV0dXJuIGRlZmF1bHRzO1xuICAgIH1cblxuICAgIC8qKlxuICAgICAqIEhhbmRsZSBhIG5ldyBpdGVtIGJlaW5nIGFkZGVkIHRvIHRoZSBsaXN0LlxuICAgICAqXG4gICAgICogVGhlIGRlZmF1bHQgaW1wbGVtZW50YXRpb24gb2YgdGhpcyBtZXRob2Qgc2ltcGx5IHNldHMgdGhlIGl0ZW0nc1xuICAgICAqIHNlbGVjdGlvbiBzdGF0ZSB0byBmYWxzZS5cbiAgICAgKlxuICAgICAqIEBwYXJhbSB7SFRNTEVsZW1lbnR9IGl0ZW0gLSB0aGUgaXRlbSBiZWluZyBhZGRlZFxuICAgICAqL1xuICAgIFtzeW1ib2xzLml0ZW1BZGRlZF0oaXRlbSkge1xuICAgICAgaWYgKHN1cGVyW3N5bWJvbHMuaXRlbUFkZGVkXSkgeyBzdXBlcltzeW1ib2xzLml0ZW1BZGRlZF0oaXRlbSk7IH1cbiAgICAgIHRoaXNbc3ltYm9scy5pdGVtU2VsZWN0ZWRdKGl0ZW0sIGl0ZW0gPT09IHRoaXMuc2VsZWN0ZWRJdGVtKTtcbiAgICB9XG5cbiAgICBbc3ltYm9scy5pdGVtc0NoYW5nZWRdKCkge1xuICAgICAgaWYgKHN1cGVyW3N5bWJvbHMuaXRlbXNDaGFuZ2VkXSkgeyBzdXBlcltzeW1ib2xzLml0ZW1zQ2hhbmdlZF0oKTsgfVxuXG4gICAgICAvLyBJbiBjYXNlIHNlbGVjdGVkIGl0ZW0gY2hhbmdlZCBwb3NpdGlvbiBvciB3YXMgcmVtb3ZlZC5cbiAgICAgIHRyYWNrU2VsZWN0ZWRJdGVtKHRoaXMpO1xuXG4gICAgICAvLyBJbiBjYXNlIHRoZSBjaGFuZ2UgaW4gaXRlbXMgYWZmZWN0ZWQgd2hpY2ggbmF2aWdhdGlvbnMgYXJlIHBvc3NpYmxlLlxuICAgICAgdXBkYXRlUG9zc2libGVOYXZpZ2F0aW9ucyh0aGlzKTtcbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBBcHBseSB0aGUgaW5kaWNhdGUgc2VsZWN0aW9uIHN0YXRlIHRvIHRoZSBpdGVtLlxuICAgICAqXG4gICAgICogVGhlIGRlZmF1bHQgaW1wbGVtZW50YXRpb24gb2YgdGhpcyBtZXRob2QgZG9lcyBub3RoaW5nLiBVc2VyLXZpc2libGVcbiAgICAgKiBlZmZlY3RzIHdpbGwgdHlwaWNhbGx5IGJlIGhhbmRsZWQgYnkgb3RoZXIgbWl4aW5zLlxuICAgICAqXG4gICAgICogQHBhcmFtIHtIVE1MRWxlbWVudH0gaXRlbSAtIHRoZSBpdGVtIGJlaW5nIHNlbGVjdGVkL2Rlc2VsZWN0ZWRcbiAgICAgKiBAcGFyYW0ge2Jvb2xlYW59IHNlbGVjdGVkIC0gdHJ1ZSBpZiB0aGUgaXRlbSBpcyBzZWxlY3RlZCwgZmFsc2UgaWYgbm90XG4gICAgICovXG4gICAgW3N5bWJvbHMuaXRlbVNlbGVjdGVkXShpdGVtLCBzZWxlY3RlZCkge1xuICAgICAgaWYgKHN1cGVyW3N5bWJvbHMuaXRlbVNlbGVjdGVkXSkgeyBzdXBlcltzeW1ib2xzLml0ZW1TZWxlY3RlZF0oaXRlbSwgc2VsZWN0ZWQpOyB9XG4gICAgfVxuXG4gICAgLyoqXG4gICAgICogVGhlIGluZGV4IG9mIHRoZSBpdGVtIHdoaWNoIGlzIGN1cnJlbnRseSBzZWxlY3RlZC5cbiAgICAgKlxuICAgICAqIEEgYHNlbGVjdGVkSW5kZXhgIG9mIC0xIGluZGljYXRlcyB0aGVyZSBpcyBubyBzZWxlY3Rpb24uIFNldHRpbmcgdGhpc1xuICAgICAqIHByb3BlcnR5IHRvIC0xIHdpbGwgcmVtb3ZlIGFueSBleGlzdGluZyBzZWxlY3Rpb24uXG4gICAgICpcbiAgICAgKiBAdHlwZSB7bnVtYmVyfVxuICAgICAqL1xuICAgIGdldCBzZWxlY3RlZEluZGV4KCkge1xuICAgICAgcmV0dXJuIHRoaXNbZXh0ZXJuYWxTZWxlY3RlZEluZGV4U3ltYm9sXSAhPSBudWxsID9cbiAgICAgICAgdGhpc1tleHRlcm5hbFNlbGVjdGVkSW5kZXhTeW1ib2xdIDpcbiAgICAgICAgLTE7XG4gICAgfVxuICAgIHNldCBzZWxlY3RlZEluZGV4KGluZGV4KSB7XG4gICAgICAvLyBTZWUgbm90ZXMgYXQgdG9wIGFib3V0IGludGVybmFsIHZzLiBleHRlcm5hbCBjb3BpZXMgb2YgdGhpcyBwcm9wZXJ0eS5cbiAgICAgIGNvbnN0IHByZXZpb3VzU2VsZWN0ZWRJbmRleCA9IHRoaXNbaW50ZXJuYWxTZWxlY3RlZEluZGV4U3ltYm9sXTtcbiAgICAgIGxldCBpdGVtO1xuICAgICAgaWYgKGluZGV4ICE9PSB0aGlzW2V4dGVybmFsU2VsZWN0ZWRJbmRleFN5bWJvbF0pIHtcbiAgICAgICAgLy8gU3RvcmUgdGhlIG5ldyBpbmRleCBhbmQgdGhlIGNvcnJlc3BvbmRpbmcgaXRlbS5cbiAgICAgICAgY29uc3QgaXRlbXMgPSB0aGlzLml0ZW1zO1xuICAgICAgICBjb25zdCBoYXNJdGVtcyA9IGl0ZW1zICYmIGl0ZW1zLmxlbmd0aCA+IDA7XG4gICAgICAgIGlmICghKGhhc0l0ZW1zICYmIGluZGV4ID49IDAgJiYgaW5kZXggPCBpdGVtcy5sZW5ndGgpKSB7XG4gICAgICAgICAgaW5kZXggPSAtMTsgLy8gTm8gaXRlbSBhdCB0aGF0IGluZGV4LlxuICAgICAgICB9XG4gICAgICAgIHRoaXNbZXh0ZXJuYWxTZWxlY3RlZEluZGV4U3ltYm9sXSA9IGluZGV4O1xuICAgICAgICBpdGVtID0gaGFzSXRlbXMgJiYgaW5kZXggPj0gMCA/IGl0ZW1zW2luZGV4XSA6IG51bGw7XG4gICAgICAgIHRoaXNbZXh0ZXJuYWxTZWxlY3RlZEl0ZW1TeW1ib2xdID0gaXRlbTtcbiAgICAgIH0gZWxzZSB7XG4gICAgICAgIGl0ZW0gPSB0aGlzW2V4dGVybmFsU2VsZWN0ZWRJdGVtU3ltYm9sXTtcbiAgICAgIH1cblxuICAgICAgLy8gTm93IGxldCBzdXBlciBkbyBhbnkgd29yay5cbiAgICAgIGlmICgnc2VsZWN0ZWRJbmRleCcgaW4gYmFzZS5wcm90b3R5cGUpIHsgc3VwZXIuc2VsZWN0ZWRJbmRleCA9IGluZGV4OyB9XG5cbiAgICAgIGlmIChpbmRleCAhPT0gcHJldmlvdXNTZWxlY3RlZEluZGV4KSB7XG4gICAgICAgIC8vIFRoZSBzZWxlY3RlZCBpbmRleCBjaGFuZ2VkLlxuICAgICAgICB0aGlzW2ludGVybmFsU2VsZWN0ZWRJbmRleFN5bWJvbF0gPSBpbmRleDtcblxuICAgICAgICBjb25zdCBldmVudCA9IG5ldyBDdXN0b21FdmVudCgnc2VsZWN0ZWQtaW5kZXgtY2hhbmdlZCcsIHtcbiAgICAgICAgICBkZXRhaWw6IHtcbiAgICAgICAgICAgIHNlbGVjdGVkSW5kZXg6IGluZGV4LFxuICAgICAgICAgICAgdmFsdWU6IGluZGV4IC8vIGZvciBQb2x5bWVyIGJpbmRpbmcuIFRPRE86IFZlcmlmeSBzdGlsbCBuZWNlc3NhcnlcbiAgICAgICAgICB9XG4gICAgICAgIH0pO1xuICAgICAgICB0aGlzLmRpc3BhdGNoRXZlbnQoZXZlbnQpO1xuICAgICAgfVxuXG4gICAgICBpZiAodGhpc1tpbnRlcm5hbFNlbGVjdGVkSXRlbVN5bWJvbF0gIT09IGl0ZW0pIHtcbiAgICAgICAgLy8gVXBkYXRlIHNlbGVjdGVkSXRlbSBwcm9wZXJ0eSBzbyBpdCBjYW4gaGF2ZSBpdHMgb3duIGVmZmVjdHMuXG4gICAgICAgIHRoaXMuc2VsZWN0ZWRJdGVtID0gaXRlbTtcbiAgICAgIH1cbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBUaGUgY3VycmVudGx5IHNlbGVjdGVkIGl0ZW0sIG9yIG51bGwgaWYgdGhlcmUgaXMgbm8gc2VsZWN0aW9uLlxuICAgICAqXG4gICAgICogU2V0dGluZyB0aGlzIHByb3BlcnR5IHRvIG51bGwgZGVzZWxlY3RzIGFueSBjdXJyZW50bHktc2VsZWN0ZWQgaXRlbS5cbiAgICAgKiBTZXR0aW5nIHRoaXMgcHJvcGVydHkgdG8gYW4gb2JqZWN0IHRoYXQgaXMgbm90IGluIHRoZSBsaXN0IGhhcyBubyBlZmZlY3QuXG4gICAgICpcbiAgICAgKiBUT0RPOiBFdmVuIGlmIHNlbGVjdGlvblJlcXVpcmVkLCBjYW4gc3RpbGwgZXhwbGljaXRseSBzZXQgc2VsZWN0ZWRJdGVtIHRvIG51bGwuXG4gICAgICogVE9ETzogSWYgc2VsZWN0aW9uUmVxdWlyZWQsIGxlYXZlIHNlbGVjdGlvbiBhbG9uZT9cbiAgICAgKlxuICAgICAqIEB0eXBlIHtvYmplY3R9XG4gICAgICovXG4gICAgZ2V0IHNlbGVjdGVkSXRlbSgpIHtcbiAgICAgIHJldHVybiB0aGlzW2V4dGVybmFsU2VsZWN0ZWRJdGVtU3ltYm9sXSB8fCBudWxsO1xuICAgIH1cbiAgICBzZXQgc2VsZWN0ZWRJdGVtKGl0ZW0pIHtcbiAgICAgIC8vIFNlZSBub3RlcyBhdCB0b3AgYWJvdXQgaW50ZXJuYWwgdnMuIGV4dGVybmFsIGNvcGllcyBvZiB0aGlzIHByb3BlcnR5LlxuICAgICAgY29uc3QgcHJldmlvdXNTZWxlY3RlZEl0ZW0gPSB0aGlzW2ludGVybmFsU2VsZWN0ZWRJdGVtU3ltYm9sXTtcbiAgICAgIGxldCBpbmRleDtcbiAgICAgIGlmIChpdGVtICE9PSB0aGlzW2V4dGVybmFsU2VsZWN0ZWRJdGVtU3ltYm9sXSkge1xuICAgICAgICAvLyBTdG9yZSBpdGVtIGFuZCBsb29rIHVwIGNvcnJlc3BvbmRpbmcgaW5kZXguXG4gICAgICAgIGNvbnN0IGl0ZW1zID0gdGhpcy5pdGVtcztcbiAgICAgICAgY29uc3QgaGFzSXRlbXMgPSBpdGVtcyAmJiBpdGVtcy5sZW5ndGggPiAwO1xuICAgICAgICBpbmRleCA9IGhhc0l0ZW1zID8gQXJyYXkucHJvdG90eXBlLmluZGV4T2YuY2FsbChpdGVtcywgaXRlbSkgOiAtMTtcbiAgICAgICAgdGhpc1tleHRlcm5hbFNlbGVjdGVkSW5kZXhTeW1ib2xdID0gaW5kZXg7XG4gICAgICAgIGlmIChpbmRleCA8IDApIHtcbiAgICAgICAgICBpdGVtID0gbnVsbDsgLy8gVGhlIGluZGljYXRlZCBpdGVtIGlzbid0IGFjdHVhbGx5IGluIGBpdGVtc2AuXG4gICAgICAgIH1cbiAgICAgICAgdGhpc1tleHRlcm5hbFNlbGVjdGVkSXRlbVN5bWJvbF0gPSBpdGVtO1xuICAgICAgfSBlbHNlIHtcbiAgICAgICAgaW5kZXggPSB0aGlzW2V4dGVybmFsU2VsZWN0ZWRJbmRleFN5bWJvbF07XG4gICAgICB9XG5cbiAgICAgIC8vIE5vdyBsZXQgc3VwZXIgZG8gYW55IHdvcmsuXG4gICAgICBpZiAoJ3NlbGVjdGVkSXRlbScgaW4gYmFzZS5wcm90b3R5cGUpIHsgc3VwZXIuc2VsZWN0ZWRJdGVtID0gaXRlbTsgfVxuXG4gICAgICBpZiAoaXRlbSAhPT0gcHJldmlvdXNTZWxlY3RlZEl0ZW0pIHtcbiAgICAgICAgLy8gVGhlIHNlbGVjdGVkIGl0ZW0gY2hhbmdlZC5cbiAgICAgICAgdGhpc1tpbnRlcm5hbFNlbGVjdGVkSXRlbVN5bWJvbF0gPSBpdGVtO1xuXG4gICAgICAgIGlmIChwcmV2aW91c1NlbGVjdGVkSXRlbSkge1xuICAgICAgICAgIC8vIFVwZGF0ZSBzZWxlY3Rpb24gc3RhdGUgb2Ygb2xkIGl0ZW0uXG4gICAgICAgICAgdGhpc1tzeW1ib2xzLml0ZW1TZWxlY3RlZF0ocHJldmlvdXNTZWxlY3RlZEl0ZW0sIGZhbHNlKTtcbiAgICAgICAgfVxuICAgICAgICBpZiAoaXRlbSkge1xuICAgICAgICAgIC8vIFVwZGF0ZSBzZWxlY3Rpb24gc3RhdGUgdG8gbmV3IGl0ZW0uXG4gICAgICAgICAgdGhpc1tzeW1ib2xzLml0ZW1TZWxlY3RlZF0oaXRlbSwgdHJ1ZSk7XG4gICAgICAgIH1cblxuICAgICAgICB1cGRhdGVQb3NzaWJsZU5hdmlnYXRpb25zKHRoaXMpO1xuXG4gICAgICAgIGNvbnN0IGV2ZW50ID0gbmV3IEN1c3RvbUV2ZW50KCdzZWxlY3RlZC1pdGVtLWNoYW5nZWQnLCB7XG4gICAgICAgICAgZGV0YWlsOiB7XG4gICAgICAgICAgICBzZWxlY3RlZEl0ZW06IGl0ZW0sXG4gICAgICAgICAgICB2YWx1ZTogaXRlbSAvLyBmb3IgUG9seW1lciBiaW5kaW5nXG4gICAgICAgICAgfVxuICAgICAgICB9KTtcbiAgICAgICAgdGhpcy5kaXNwYXRjaEV2ZW50KGV2ZW50KTtcbiAgICAgIH1cblxuICAgICAgaWYgKHRoaXNbaW50ZXJuYWxTZWxlY3RlZEluZGV4U3ltYm9sXSAhPT0gaW5kZXgpIHtcbiAgICAgICAgLy8gVXBkYXRlIHNlbGVjdGVkSW5kZXggcHJvcGVydHkgc28gaXQgY2FuIGhhdmUgaXRzIG93biBlZmZlY3RzLlxuICAgICAgICB0aGlzLnNlbGVjdGVkSW5kZXggPSBpbmRleDtcbiAgICAgIH1cbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBTZWxlY3QgdGhlIGZpcnN0IGl0ZW0gaW4gdGhlIGxpc3QuXG4gICAgICovXG4gICAgc2VsZWN0Rmlyc3QoKSB7XG4gICAgICBpZiAoc3VwZXIuc2VsZWN0Rmlyc3QpIHsgc3VwZXIuc2VsZWN0Rmlyc3QoKTsgfVxuICAgICAgcmV0dXJuIHNlbGVjdEluZGV4KHRoaXMsIDApO1xuICAgIH1cblxuICAgIC8qKlxuICAgICAqIFRydWUgaWYgdGhlIGxpc3Qgc2hvdWxkIGFsd2F5cyBoYXZlIGEgc2VsZWN0aW9uIChpZiBpdCBoYXMgaXRlbXMpLlxuICAgICAqXG4gICAgICogQHR5cGUge2Jvb2xlYW59XG4gICAgICogQGRlZmF1bHQgZmFsc2VcbiAgICAgKi9cbiAgICBnZXQgc2VsZWN0aW9uUmVxdWlyZWQoKSB7XG4gICAgICByZXR1cm4gdGhpc1tzZWxlY3Rpb25SZXF1aXJlZFN5bWJvbF07XG4gICAgfVxuICAgIHNldCBzZWxlY3Rpb25SZXF1aXJlZChzZWxlY3Rpb25SZXF1aXJlZCkge1xuICAgICAgdGhpc1tzZWxlY3Rpb25SZXF1aXJlZFN5bWJvbF0gPSBzZWxlY3Rpb25SZXF1aXJlZDtcbiAgICAgIGlmICgnc2VsZWN0aW9uUmVxdWlyZWQnIGluIGJhc2UucHJvdG90eXBlKSB7IHN1cGVyLnNlbGVjdGlvblJlcXVpcmVkID0gc2VsZWN0aW9uUmVxdWlyZWQ7IH1cbiAgICAgIHRyYWNrU2VsZWN0ZWRJdGVtKHRoaXMpO1xuICAgIH1cblxuICAgIC8qKlxuICAgICAqIFRydWUgaWYgc2VsZWN0aW9uIG5hdmlnYXRpb25zIHdyYXAgZnJvbSBsYXN0IHRvIGZpcnN0LCBhbmQgdmljZSB2ZXJzYS5cbiAgICAgKlxuICAgICAqIEB0eXBlIHtib29sZWFufVxuICAgICAqIEBkZWZhdWx0IGZhbHNlXG4gICAgICovXG4gICAgZ2V0IHNlbGVjdGlvbldyYXBzKCkge1xuICAgICAgcmV0dXJuIHRoaXNbc2VsZWN0aW9uV3JhcHNTeW1ib2xdO1xuICAgIH1cbiAgICBzZXQgc2VsZWN0aW9uV3JhcHModmFsdWUpIHtcbiAgICAgIHRoaXNbc2VsZWN0aW9uV3JhcHNTeW1ib2xdID0gU3RyaW5nKHZhbHVlKSA9PT0gJ3RydWUnO1xuICAgICAgaWYgKCdzZWxlY3Rpb25XcmFwcycgaW4gYmFzZS5wcm90b3R5cGUpIHsgc3VwZXIuc2VsZWN0aW9uV3JhcHMgPSB2YWx1ZTsgfVxuICAgICAgdXBkYXRlUG9zc2libGVOYXZpZ2F0aW9ucyh0aGlzKTtcbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBTZWxlY3QgdGhlIGxhc3QgaXRlbSBpbiB0aGUgbGlzdC5cbiAgICAgKi9cbiAgICBzZWxlY3RMYXN0KCkge1xuICAgICAgaWYgKHN1cGVyLnNlbGVjdExhc3QpIHsgc3VwZXIuc2VsZWN0TGFzdCgpOyB9XG4gICAgICByZXR1cm4gc2VsZWN0SW5kZXgodGhpcywgdGhpcy5pdGVtcy5sZW5ndGggLSAxKTtcbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBTZWxlY3QgdGhlIG5leHQgaXRlbSBpbiB0aGUgbGlzdC5cbiAgICAgKi9cbiAgICBzZWxlY3ROZXh0KCkge1xuICAgICAgaWYgKHN1cGVyLnNlbGVjdE5leHQpIHsgc3VwZXIuc2VsZWN0TmV4dCgpOyB9XG4gICAgICByZXR1cm4gc2VsZWN0SW5kZXgodGhpcywgdGhpcy5zZWxlY3RlZEluZGV4ICsgMSk7XG4gICAgfVxuXG4gICAgLyoqXG4gICAgICogU2VsZWN0IHRoZSBwcmV2aW91cyBpdGVtIGluIHRoZSBsaXN0LlxuICAgICAqXG4gICAgICogSWYgdGhlIGxpc3QgaGFzIG5vIHNlbGVjdGlvbiwgdGhlIGxhc3QgaXRlbSB3aWxsIGJlIHNlbGVjdGVkLlxuICAgICAqL1xuICAgIHNlbGVjdFByZXZpb3VzKCkge1xuICAgICAgaWYgKHN1cGVyLnNlbGVjdFByZXZpb3VzKSB7IHN1cGVyLnNlbGVjdFByZXZpb3VzKCk7IH1cbiAgICAgIGNvbnN0IG5ld0luZGV4ID0gdGhpcy5zZWxlY3RlZEluZGV4IDwgMCA/XG4gICAgICAgIHRoaXMuaXRlbXMubGVuZ3RoIC0gMSA6ICAgICAvLyBObyBzZWxlY3Rpb24geWV0OyBzZWxlY3QgbGFzdCBpdGVtLlxuICAgICAgICB0aGlzLnNlbGVjdGVkSW5kZXggLSAxO1xuICAgICAgcmV0dXJuIHNlbGVjdEluZGV4KHRoaXMsIG5ld0luZGV4KTtcbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBGaXJlcyB3aGVuIHRoZSBzZWxlY3RlZEl0ZW0gcHJvcGVydHkgY2hhbmdlcy5cbiAgICAgKlxuICAgICAqIEBtZW1iZXJvZiBTaW5nbGVTZWxlY3Rpb25cbiAgICAgKiBAZXZlbnQgc2VsZWN0ZWQtaXRlbS1jaGFuZ2VkXG4gICAgICogQHBhcmFtIHtIVE1MRWxlbWVudH0gZGV0YWlsLnNlbGVjdGVkSXRlbSBUaGUgbmV3IHNlbGVjdGVkIGl0ZW0uXG4gICAgICogQHBhcmFtIHtIVE1MRWxlbWVudH0gZGV0YWlsLnByZXZpb3VzSXRlbSBUaGUgcHJldmlvdXNseSBzZWxlY3RlZCBpdGVtLlxuICAgICAqL1xuXG4gICAgLyoqXG4gICAgICogRmlyZXMgd2hlbiB0aGUgc2VsZWN0ZWRJbmRleCBwcm9wZXJ0eSBjaGFuZ2VzLlxuICAgICAqXG4gICAgICogQG1lbWJlcm9mIFNpbmdsZVNlbGVjdGlvblxuICAgICAqIEBldmVudCBzZWxlY3RlZC1pbmRleC1jaGFuZ2VkXG4gICAgICogQHBhcmFtIHtudW1iZXJ9IGRldGFpbC5zZWxlY3RlZEluZGV4IFRoZSBuZXcgc2VsZWN0ZWQgaW5kZXguXG4gICAgICovXG5cbiAgfVxuXG4gIHJldHVybiBTaW5nbGVTZWxlY3Rpb247XG59O1xuXG5cbi8vIEVuc3VyZSB0aGUgZ2l2ZW4gaW5kZXggaXMgd2l0aGluIGJvdW5kcywgYW5kIHNlbGVjdCBpdCBpZiBpdCdzIG5vdCBhbHJlYWR5XG4vLyBzZWxlY3RlZC5cbmZ1bmN0aW9uIHNlbGVjdEluZGV4KGVsZW1lbnQsIGluZGV4KSB7XG4gIGNvbnN0IGNvdW50ID0gZWxlbWVudC5pdGVtcy5sZW5ndGg7XG5cbiAgY29uc3QgYm91bmRlZEluZGV4ID0gKGVsZW1lbnQuc2VsZWN0aW9uV3JhcHMpID9cbiAgICAvLyBKYXZhU2NyaXB0IG1vZCBkb2Vzbid0IGhhbmRsZSBuZWdhdGl2ZSBudW1iZXJzIHRoZSB3YXkgd2Ugd2FudCB0byB3cmFwLlxuICAgIC8vIFNlZSBodHRwOi8vc3RhY2tvdmVyZmxvdy5jb20vYS8xODYxODI1MC83NjQ3MlxuICAgICgoaW5kZXggJSBjb3VudCkgKyBjb3VudCkgJSBjb3VudCA6XG5cbiAgICAvLyBLZWVwIGluZGV4IHdpdGhpbiBib3VuZHMgb2YgYXJyYXkuXG4gICAgTWF0aC5tYXgoTWF0aC5taW4oaW5kZXgsIGNvdW50IC0gMSksIDApO1xuXG4gIGNvbnN0IHByZXZpb3VzSW5kZXggPSBlbGVtZW50LnNlbGVjdGVkSW5kZXg7XG4gIGlmIChwcmV2aW91c0luZGV4ICE9PSBib3VuZGVkSW5kZXgpIHtcbiAgICBlbGVtZW50LnNlbGVjdGVkSW5kZXggPSBib3VuZGVkSW5kZXg7XG4gICAgcmV0dXJuIHRydWU7XG4gIH0gZWxzZSB7XG4gICAgcmV0dXJuIGZhbHNlO1xuICB9XG59XG5cbi8vIEZvbGxvd2luZyBhIGNoYW5nZSBpbiB0aGUgc2V0IG9mIGl0ZW1zLCBvciBpbiB0aGUgdmFsdWUgb2YgdGhlXG4vLyBgc2VsZWN0aW9uUmVxdWlyZWRgIHByb3BlcnR5LCByZWFjcXVpcmUgdGhlIHNlbGVjdGVkIGl0ZW0uIElmIGl0J3MgbW92ZWQsXG4vLyB1cGRhdGUgYHNlbGVjdGVkSW5kZXhgLiBJZiBpdCdzIGJlZW4gcmVtb3ZlZCwgYW5kIGEgc2VsZWN0aW9uIGlzIHJlcXVpcmVkLFxuLy8gdHJ5IHRvIHNlbGVjdCBhbm90aGVyIGl0ZW0uXG5mdW5jdGlvbiB0cmFja1NlbGVjdGVkSXRlbShlbGVtZW50KSB7XG5cbiAgY29uc3QgaXRlbXMgPSBlbGVtZW50Lml0ZW1zO1xuICBjb25zdCBpdGVtQ291bnQgPSBpdGVtcyA/IGl0ZW1zLmxlbmd0aCA6IDA7XG5cbiAgY29uc3QgcHJldmlvdXNTZWxlY3RlZEl0ZW0gPSBlbGVtZW50LnNlbGVjdGVkSXRlbTtcbiAgaWYgKCFwcmV2aW91c1NlbGVjdGVkSXRlbSkge1xuICAgIC8vIE5vIGl0ZW0gd2FzIHByZXZpb3VzbHkgc2VsZWN0ZWQuXG4gICAgaWYgKGVsZW1lbnQuc2VsZWN0aW9uUmVxdWlyZWQpIHtcbiAgICAgIC8vIFNlbGVjdCB0aGUgZmlyc3QgaXRlbSBieSBkZWZhdWx0LlxuICAgICAgZWxlbWVudC5zZWxlY3RlZEluZGV4ID0gMDtcbiAgICB9XG4gIH0gZWxzZSBpZiAoaXRlbUNvdW50ID09PSAwKSB7XG4gICAgLy8gV2UndmUgbG9zdCB0aGUgc2VsZWN0aW9uLCBhbmQgdGhlcmUncyBub3RoaW5nIGxlZnQgdG8gc2VsZWN0LlxuICAgIGVsZW1lbnQuc2VsZWN0ZWRJdGVtID0gbnVsbDtcbiAgfSBlbHNlIHtcbiAgICAvLyBUcnkgdG8gZmluZCB0aGUgcHJldmlvdXNseS1zZWxlY3RlZCBpdGVtIGluIHRoZSBjdXJyZW50IHNldCBvZiBpdGVtcy5cbiAgICBjb25zdCBpbmRleEluQ3VycmVudEl0ZW1zID0gQXJyYXkucHJvdG90eXBlLmluZGV4T2YuY2FsbChpdGVtcywgcHJldmlvdXNTZWxlY3RlZEl0ZW0pO1xuICAgIGNvbnN0IHByZXZpb3VzU2VsZWN0ZWRJbmRleCA9IGVsZW1lbnQuc2VsZWN0ZWRJbmRleDtcbiAgICBpZiAoaW5kZXhJbkN1cnJlbnRJdGVtcyA8IDApIHtcbiAgICAgIC8vIFByZXZpb3VzbHktc2VsZWN0ZWQgaXRlbSB3YXMgcmVtb3ZlZCBmcm9tIHRoZSBpdGVtcy5cbiAgICAgIC8vIFNlbGVjdCB0aGUgaXRlbSBhdCB0aGUgc2FtZSBpbmRleCAoaWYgaXQgZXhpc3RzKSBvciBhcyBjbG9zZSBhcyBwb3NzaWJsZS5cbiAgICAgIGNvbnN0IG5ld1NlbGVjdGVkSW5kZXggPSBNYXRoLm1pbihwcmV2aW91c1NlbGVjdGVkSW5kZXgsIGl0ZW1Db3VudCAtIDEpO1xuICAgICAgLy8gU2VsZWN0IGJ5IGl0ZW0sIHNpbmNlIGluZGV4IG1heSBiZSB0aGUgc2FtZSwgYW5kIHdlIHdhbnQgdG8gcmFpc2UgdGhlXG4gICAgICAvLyBzZWxlY3RlZC1pdGVtLWNoYW5nZWQgZXZlbnQuXG4gICAgICBlbGVtZW50LnNlbGVjdGVkSXRlbSA9IGl0ZW1zW25ld1NlbGVjdGVkSW5kZXhdO1xuICAgIH0gZWxzZSBpZiAoaW5kZXhJbkN1cnJlbnRJdGVtcyAhPT0gcHJldmlvdXNTZWxlY3RlZEluZGV4KSB7XG4gICAgICAvLyBQcmV2aW91c2x5LXNlbGVjdGVkIGl0ZW0gc3RpbGwgdGhlcmUsIGJ1dCBjaGFuZ2VkIHBvc2l0aW9uLlxuICAgICAgZWxlbWVudC5zZWxlY3RlZEluZGV4ID0gaW5kZXhJbkN1cnJlbnRJdGVtcztcbiAgICB9XG4gIH1cbn1cblxuLy8gRm9sbG93aW5nIGEgY2hhbmdlIGluIHNlbGVjdGlvbiwgcmVwb3J0IHdoZXRoZXIgaXQncyBub3cgcG9zc2libGUgdG9cbi8vIGdvIG5leHQvcHJldmlvdXMgZnJvbSB0aGUgZ2l2ZW4gaW5kZXguXG5mdW5jdGlvbiB1cGRhdGVQb3NzaWJsZU5hdmlnYXRpb25zKGVsZW1lbnQpIHtcbiAgbGV0IGNhblNlbGVjdE5leHQ7XG4gIGxldCBjYW5TZWxlY3RQcmV2aW91cztcbiAgY29uc3QgaXRlbXMgPSBlbGVtZW50Lml0ZW1zO1xuICBpZiAoaXRlbXMgPT0gbnVsbCB8fCBpdGVtcy5sZW5ndGggPT09IDApIHtcbiAgICAvLyBObyBpdGVtcyB0byBzZWxlY3QuXG4gICAgY2FuU2VsZWN0TmV4dCA9IGZhbHNlO1xuICAgIGNhblNlbGVjdFByZXZpb3VzID0gZmFsc2U7XG4gIH0gaWYgKGVsZW1lbnQuc2VsZWN0aW9uV3JhcHMpIHtcbiAgICAvLyBTaW5jZSB0aGVyZSBhcmUgaXRlbXMsIGNhbiBhbHdheXMgZ28gbmV4dC9wcmV2aW91cy5cbiAgICBjYW5TZWxlY3ROZXh0ID0gdHJ1ZTtcbiAgICBjYW5TZWxlY3RQcmV2aW91cyA9IHRydWU7XG4gIH0gZWxzZSB7XG4gICAgY29uc3QgaW5kZXggPSBlbGVtZW50LnNlbGVjdGVkSW5kZXg7XG4gICAgaWYgKGluZGV4IDwgMCAmJiBpdGVtcy5sZW5ndGggPiAwKSB7XG4gICAgICAvLyBTcGVjaWFsIGNhc2UuIElmIHRoZXJlIGFyZSBpdGVtcyBidXQgbm8gc2VsZWN0aW9uLCBkZWNsYXJlIHRoYXQgaXQnc1xuICAgICAgLy8gYWx3YXlzIHBvc3NpYmxlIHRvIGdvIG5leHQvcHJldmlvdXMgdG8gY3JlYXRlIGEgc2VsZWN0aW9uLlxuICAgICAgY2FuU2VsZWN0TmV4dCA9IHRydWU7XG4gICAgICBjYW5TZWxlY3RQcmV2aW91cyA9IHRydWU7XG4gICAgfSBlbHNlIHtcbiAgICAgIC8vIE5vcm1hbCBjYXNlOiB3ZSBoYXZlIGFuIGluZGV4IGluIGEgbGlzdCB0aGF0IGhhcyBpdGVtcy5cbiAgICAgIGNhblNlbGVjdFByZXZpb3VzID0gKGluZGV4ID4gMCk7XG4gICAgICBjYW5TZWxlY3ROZXh0ID0gKGluZGV4IDwgaXRlbXMubGVuZ3RoIC0gMSk7XG4gICAgfVxuICB9XG4gIGlmIChlbGVtZW50LmNhblNlbGVjdE5leHQgIT09IGNhblNlbGVjdE5leHQpIHtcbiAgICBlbGVtZW50LmNhblNlbGVjdE5leHQgPSBjYW5TZWxlY3ROZXh0O1xuICB9XG4gIGlmIChlbGVtZW50LmNhblNlbGVjdFByZXZpb3VzICE9PSBjYW5TZWxlY3RQcmV2aW91cykge1xuICAgIGVsZW1lbnQuY2FuU2VsZWN0UHJldmlvdXMgPSBjYW5TZWxlY3RQcmV2aW91cztcbiAgfVxufVxuIiwiaW1wb3J0IGNyZWF0ZVN5bWJvbCBmcm9tICcuL2NyZWF0ZVN5bWJvbCc7XG5pbXBvcnQgc3ltYm9scyBmcm9tICcuL3N5bWJvbHMnO1xuXG5cbmNvbnN0IHBsYXlpbmdTeW1ib2wgPSBjcmVhdGVTeW1ib2woJ3BsYXlpbmcnKTtcbmNvbnN0IHNlbGVjdGlvblRpbWVyRHVyYXRpb25TeW1ib2wgPSBjcmVhdGVTeW1ib2woJ3NlbGVjdGlvblRpbWVyRHVyYXRpb24nKTtcbmNvbnN0IHRpbWVyVGltZW91dFN5bWJvbCA9IGNyZWF0ZVN5bWJvbCgndGltZXJUaW1lb3V0Jyk7XG5cblxuLyogRXhwb3J0ZWQgZnVuY3Rpb24gZXh0ZW5kcyBhIGJhc2UgY2xhc3Mgd2l0aCBUaW1lclNlbGVjdGlvbi4gKi9cbmV4cG9ydCBkZWZhdWx0IChiYXNlKSA9PiB7XG5cbiAgLyoqXG4gICAqIE1peGluIHdoaWNoIHByb3ZpZGVzIGZvciBhdXRvbWF0aWMgdGltZWQgY2hhbmdlcyBpbiBzZWxlY3Rpb24uXG4gICAqXG4gICAqIFRoaXMgbWl4aW4gaXMgdXNlZnVsIGZvciBjcmVhdGluZyBzbGlkZXNob3ctbGlrZSBlbGVtZW50cyBzdWNoIGFzXG4gICAqIFtiYXNpYy1zbGlkZXNob3ddKC4uL3BhY2thZ2VzL2Jhc2ljLXNsaWRlc2hvdykgYW5kXG4gICAqIFtiYXNpYy1zbGlkZXNob3ctd2l0aC1jb250cm9sc10oLi4vcGFja2FnZXMvYmFzaWMtc2xpZGVzaG93LXdpdGgtY29udHJvbHMpLlxuICAgKlxuICAgKiBUeXBpY2FsIHVzYWdlOlxuICAgKlxuICAgKiAgICAgY2xhc3MgQ2Fyb3VzZWxXaXRoVGltZXIgZXh0ZW5kcyBUaW1lclNlbGVjdGlvbk1peGluKENhcm91c2VsKSB7fVxuICAgKiAgICAgY3VzdG9tRWxlbWVudHMuZGVmaW5lKCdjYXJvdXNlbC13aXRoLWFycm93cycsIENhcm91c2VsV2l0aFRpbWVyKTtcbiAgICpcbiAgICogVGhpcyBtaXhpbiBleHBlY3RzIHRoZSBjb21wb25lbnQgdG8gZGVmaW5lIGFuIGBpdGVtc2AgcHJvcGVydHksIGFzIHdlbGwgYXNcbiAgICogYHNlbGVjdEZpcnN0YCBhbmQgYHNlbGVjdE5leHRgIG1ldGhvZHMuIFlvdSBjYW4gaW1wbGVtZW50IHRob3NlIHlvdXJzZWxmLFxuICAgKiBvciB1c2UgW0NvbnRlbnRJdGVtc01peGluXShDb250ZW50SXRlbXNNaXhpbi5tZCkgYW5kXG4gICAqIFtTaW5nbGVTZWxlY3Rpb25NaXhpbl0oU2luZ2xlU2VsZWN0aW9uTWl4aW4ubWQpLlxuICAgKi9cbiAgY2xhc3MgVGltZXJTZWxlY3Rpb24gZXh0ZW5kcyBiYXNlIHtcblxuICAgIGNvbnN0cnVjdG9yKCkge1xuICAgICAgc3VwZXIoKTtcbiAgICAgIC8vIFNldCBkZWZhdWx0cy5cbiAgICAgIGlmICh0eXBlb2YgdGhpcy5wbGF5aW5nID09PSAndW5kZWZpbmVkJykge1xuICAgICAgICB0aGlzLnBsYXlpbmcgPSB0aGlzW3N5bWJvbHMuZGVmYXVsdHNdLnBsYXlpbmc7XG4gICAgICB9XG4gICAgICBpZiAodHlwZW9mIHRoaXMuc2VsZWN0aW9uVGltZXJEdXJhdGlvbiA9PT0gJ3VuZGVmaW5lZCcpIHtcbiAgICAgICAgdGhpcy5zZWxlY3Rpb25UaW1lckR1cmF0aW9uID0gdGhpc1tzeW1ib2xzLmRlZmF1bHRzXS5zZWxlY3Rpb25UaW1lckR1cmF0aW9uO1xuICAgICAgfVxuICAgIH1cblxuICAgIGNvbnRlbnRDaGFuZ2VkKCkge1xuICAgICAgaWYgKHN1cGVyLmNvbnRlbnRDaGFuZ2VkKSB7IHN1cGVyLmNvbnRlbnRDaGFuZ2VkKCk7IH1cbiAgICAgIHJlc3RhcnRUaW1lcih0aGlzKTtcbiAgICB9XG5cbiAgICBnZXQgW3N5bWJvbHMuZGVmYXVsdHNdKCkge1xuICAgICAgY29uc3QgZGVmYXVsdHMgPSBzdXBlcltzeW1ib2xzLmRlZmF1bHRzXSB8fCB7fTtcbiAgICAgIGRlZmF1bHRzLnBsYXlpbmcgPSBmYWxzZTtcbiAgICAgIGRlZmF1bHRzLnNlbGVjdGlvblRpbWVyRHVyYXRpb24gPSAxMDAwO1xuICAgICAgcmV0dXJuIGRlZmF1bHRzO1xuICAgIH1cblxuICAgIC8qKlxuICAgICAqIEJlZ2luIGF1dG9tYXRpYyBwcm9ncmVzc2lvbiBvZiB0aGUgc2VsZWN0aW9uLlxuICAgICAqL1xuICAgIHBsYXkoKSB7XG4gICAgICBpZiAoc3VwZXIucGxheSkgeyBzdXBlci5wbGF5KCk7IH1cbiAgICAgIHN0YXJ0VGltZXIodGhpcyk7XG4gICAgICB0aGlzW3BsYXlpbmdTeW1ib2xdID0gdHJ1ZTtcbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBQYXVzZSBhdXRvbWF0aWMgcHJvZ3Jlc3Npb24gb2YgdGhlIHNlbGVjdGlvbi5cbiAgICAgKi9cbiAgICBwYXVzZSgpIHtcbiAgICAgIGlmIChzdXBlci5wYXVzZSkgeyBzdXBlci5wYXVzZSgpOyB9XG4gICAgICBjbGVhclRpbWVyKHRoaXMpO1xuICAgICAgdGhpc1twbGF5aW5nU3ltYm9sXSA9IGZhbHNlO1xuICAgIH1cblxuICAgIC8qKlxuICAgICAqIFRydWUgaWYgdGhlIHNlbGVjdGlvbiBpcyBiZWluZyBhdXRvbWF0aWNhbGx5IGFkdmFuY2VkLlxuICAgICAqXG4gICAgICogQHR5cGUge2Jvb2xlYW59XG4gICAgICogQGRlZmF1bHQgZmFsc2VcbiAgICAgKi9cbiAgICBnZXQgcGxheWluZygpIHtcbiAgICAgIHJldHVybiB0aGlzW3BsYXlpbmdTeW1ib2xdO1xuICAgIH1cbiAgICBzZXQgcGxheWluZyhwbGF5aW5nKSB7XG4gICAgICBjb25zdCBwcmV2aW91c1BsYXlpbmcgPSB0aGlzW3BsYXlpbmdTeW1ib2xdO1xuICAgICAgY29uc3QgcGFyc2VkID0gU3RyaW5nKHBsYXlpbmcpID09PSAndHJ1ZSc7IC8vIENhc3QgdG8gYm9vbGVhblxuICAgICAgaWYgKCdwbGF5aW5nJyBpbiBiYXNlLnByb3RvdHlwZSkgeyBzdXBlci5wbGF5aW5nID0gcGxheWluZzsgfVxuICAgICAgaWYgKHBhcnNlZCAhPT0gcHJldmlvdXNQbGF5aW5nKSB7XG4gICAgICAgIGlmIChwbGF5aW5nKSB7XG4gICAgICAgICAgdGhpcy5wbGF5KCk7XG4gICAgICAgIH0gZWxzZSB7XG4gICAgICAgICAgdGhpcy5wYXVzZSgpO1xuICAgICAgICB9XG4gICAgICB9XG4gICAgfVxuXG4gICAgLypcbiAgICAgKiBXaGVuIHRoZSBzZWxlY3RlZCBpdGVtIGNoYW5nZXMgKGJlY2F1c2Ugb2Ygc29tZXRoaW5nIHRoaXMgbWl4aW4gZGlkLCBvclxuICAgICAqIHdhcyBjaGFuZ2VkIGJ5IGFuIG91dHNpZGUgYWdlbnQgbGlrZSB0aGUgdXNlciksIHdlIHdhaXQgYmVmb3JlIGFkdmFuY2luZ1xuICAgICAqIHRvIHRoZSBuZXh0IGl0ZW0uIEJ5IHRyaWdnZXJpbmcgdGhlIG5leHQgaXRlbSB0aGlzIHdheSwgd2UgaW1wbGljaXRseSBnZXRcbiAgICAgKiBhIGRlc2lyYWJsZSBiZWhhdmlvcjogaWYgdGhlIHVzZXIgY2hhbmdlcyB0aGUgc2VsZWN0aW9uIChlLmcuLCBpbiBhXG4gICAgICogY2Fyb3VzZWwpLCB3ZSBsZXQgdGhlbSBzZWUgdGhhdCBzZWxlY3Rpb24gc3RhdGUgZm9yIGEgd2hpbGUgYmVmb3JlXG4gICAgICogYWR2YW5jaW5nIHRoZSBzZWxlY3Rpb24gb3Vyc2VsdmVzLlxuICAgICAqL1xuICAgIGdldCBzZWxlY3RlZEl0ZW0oKSB7XG4gICAgICByZXR1cm4gc3VwZXIuc2VsZWN0ZWRJdGVtO1xuICAgIH1cbiAgICBzZXQgc2VsZWN0ZWRJdGVtKGl0ZW0pIHtcbiAgICAgIGlmICgnc2VsZWN0ZWRJdGVtJyBpbiBiYXNlLnByb3RvdHlwZSkgeyBzdXBlci5zZWxlY3RlZEl0ZW0gPSBpdGVtOyB9XG4gICAgICByZXN0YXJ0VGltZXIodGhpcyk7XG4gICAgfVxuXG4gICAgLyoqXG4gICAgICogVGhlIHRpbWUgaW4gbWlsbGlzZWNvbmRzIHRoYXQgd2lsbCBlbGFwc2UgYWZ0ZXIgdGhlIHNlbGVjdGlvbiBjaGFuZ2VzXG4gICAgICogYmVmb3JlIHRoZSBzZWxlY3Rpb24gd2lsbCBiZSBhZHZhbmNlZCB0byB0aGUgbmV4dCBpdGVtIGluIHRoZSBsaXN0LlxuICAgICAqXG4gICAgICogQHR5cGUge251bWJlcn0gLSBUaW1lIGluIG1pbGxpc2Vjb25kc1xuICAgICAqIEBkZWZhdWx0IDEwMDAgKDEgc2Vjb25kKVxuICAgICAqL1xuICAgIGdldCBzZWxlY3Rpb25UaW1lckR1cmF0aW9uKCkge1xuICAgICAgcmV0dXJuIHRoaXNbc2VsZWN0aW9uVGltZXJEdXJhdGlvblN5bWJvbF07XG4gICAgfVxuICAgIHNldCBzZWxlY3Rpb25UaW1lckR1cmF0aW9uKHZhbHVlKSB7XG4gICAgICB0aGlzW3NlbGVjdGlvblRpbWVyRHVyYXRpb25TeW1ib2xdID0gcGFyc2VJbnQodmFsdWUpO1xuICAgICAgaWYgKCdzZWxlY3Rpb25UaW1lckR1cmF0aW9uJyBpbiBiYXNlLnByb3RvdHlwZSkgeyBzdXBlci5zZWxlY3Rpb25UaW1lckR1cmF0aW9uID0gdmFsdWU7IH1cbiAgICB9XG5cbiAgfVxuXG4gIHJldHVybiBUaW1lclNlbGVjdGlvbjtcbn07XG5cblxuZnVuY3Rpb24gY2xlYXJUaW1lcihlbGVtZW50KSB7XG4gIGlmIChlbGVtZW50W3RpbWVyVGltZW91dFN5bWJvbF0pIHtcbiAgICBjbGVhclRpbWVvdXQoZWxlbWVudFt0aW1lclRpbWVvdXRTeW1ib2xdKTtcbiAgICBlbGVtZW50W3RpbWVyVGltZW91dFN5bWJvbF0gPSBudWxsO1xuICB9XG59XG5cbmZ1bmN0aW9uIHJlc3RhcnRUaW1lcihlbGVtZW50KSB7XG4gIGNsZWFyVGltZXIoZWxlbWVudCk7XG4gIGlmIChlbGVtZW50LnBsYXlpbmcgJiYgZWxlbWVudC5pdGVtcyAmJiBlbGVtZW50Lml0ZW1zLmxlbmd0aCA+IDApIHtcbiAgICBzdGFydFRpbWVyKGVsZW1lbnQpO1xuICB9XG59XG5cbmZ1bmN0aW9uIHN0YXJ0VGltZXIoZWxlbWVudCkge1xuICAvLyBJZiBwbGF5KCkgaXMgY2FsbGVkIG1vcmUgdGhhbiBvbmNlLCBjYW5jZWwgYW55IGV4aXN0aW5nIHRpbWVyLlxuICBjbGVhclRpbWVyKGVsZW1lbnQpO1xuICBlbGVtZW50W3RpbWVyVGltZW91dFN5bWJvbF0gPSBzZXRUaW1lb3V0KCgpID0+IHtcbiAgICBzZWxlY3ROZXh0V2l0aFdyYXAoZWxlbWVudCk7XG4gIH0sIGVsZW1lbnQuc2VsZWN0aW9uVGltZXJEdXJhdGlvbik7XG59XG5cbi8vIFNlbGVjdCB0aGUgbmV4dCBpdGVtLCB3cmFwcGluZyB0byBmaXJzdCBpdGVtIGlmIG5lY2Vzc2FyeS5cbmZ1bmN0aW9uIHNlbGVjdE5leHRXaXRoV3JhcChlbGVtZW50KSB7XG4gIGNvbnN0IGl0ZW1zID0gZWxlbWVudC5pdGVtcztcbiAgaWYgKGl0ZW1zICYmIGl0ZW1zLmxlbmd0aCA+IDApIHtcbiAgICBpZiAoZWxlbWVudC5zZWxlY3RlZEluZGV4ID09IG51bGwgfHwgZWxlbWVudC5zZWxlY3RlZEluZGV4ID09PSBpdGVtcy5sZW5ndGggLSAxKSB7XG4gICAgICBlbGVtZW50LnNlbGVjdEZpcnN0KCk7XG4gICAgfSBlbHNlIHtcbiAgICAgIGVsZW1lbnQuc2VsZWN0TmV4dCgpO1xuICAgIH1cbiAgfVxufVxuIiwiLyoqXG4gKiBIZWxwZXIgZnVuY3Rpb24gdG8gY3JlYXRlIGEgc3ltYm9sIHRoYXQgY2FuIGJlIHVzZWQgZm9yIGFzc29jaWF0aW5nIHByaXZhdGVcbiAqIGRhdGEgd2l0aCBhbiBlbGVtZW50LlxuICpcbiAqIE1peGlucyBhbmQgY29tcG9uZW50IGNsYXNzZXMgb2Z0ZW4gd2FudCB0byBhc3NvY2lhdGUgcHJpdmF0ZSBkYXRhIHdpdGggYW5cbiAqIGVsZW1lbnQgaW5zdGFuY2UsIGJ1dCBKYXZhU2NyaXB0IGRvZXMgbm90IGhhdmUgZGlyZWN0IHN1cHBvcnQgZm9yIHRydWVcbiAqIHByaXZhdGUgcHJvcGVydGllcy4gT25lIGFwcHJvYWNoIGlzIHRvIHVzZSB0aGVcbiAqIFtTeW1ib2xdKGh0dHBzOi8vZGV2ZWxvcGVyLm1vemlsbGEub3JnL2VuLVVTL2RvY3MvV2ViL0phdmFTY3JpcHQvUmVmZXJlbmNlL0dsb2JhbF9PYmplY3RzL1N5bWJvbClcbiAqIGRhdGEgdHlwZSB0byBzZXQgYW5kIHJldHJpZXZlIGRhdGEgb24gYW4gZWxlbWVudC5cbiAqXG4gKiBVbmZvcnR1bmF0ZWx5LCB0aGUgU3ltYm9sIHR5cGUgaXMgbm90IGF2YWlsYWJsZSBpbiBJbnRlcm5ldCBFeHBsb3JlciAxMS4gVGhlXG4gKiBgY3JlYXRlU3ltYm9sYCBoZWxwZXIgZnVuY3Rpb24gZXhpc3RzIGFzIGEgd29ya2Fyb3VuZCBmb3IgSUUgMTEuIFJhdGhlciB0aGFuXG4gKiByZXR1cm5pbmcgYSB0cnVlIFN5bWJvbCwgaXQgc2ltcGx5IHJldHVybnMgYW4gdW5kZXJzY29yZS1wcmVmaXhlZCBzdHJpbmcuXG4gKlxuICogVXNhZ2U6XG4gKlxuICogICAgIGNvbnN0IGZvb1N5bWJvbCA9IGNyZWF0ZVN5bWJvbCgnZm9vJyk7XG4gKlxuICogICAgIGNsYXNzIE15RWxlbWVudCBleHRlbmRzIEhUTUxFbGVtZW50IHtcbiAqICAgICAgIGdldCBmb28oKSB7XG4gKiAgICAgICAgIHJldHVybiB0aGlzW2Zvb1N5bWJvbF07XG4gKiAgICAgICB9XG4gKiAgICAgICBzZXQgZm9vKHZhbHVlKSB7XG4gKiAgICAgICAgIHRoaXNbZm9vU3ltYm9sXSA9IHZhbHVlO1xuICogICAgICAgfVxuICogICAgIH1cbiAqXG4gKiBJbiBJRSAxMSwgdGhpcyBzYW1wbGUgd2lsbCBcImhpZGVcIiBkYXRhIGJlaGluZCBhbiBpbnN0YW5jZSBwcm9wZXJ0eSB0aGlzLl9mb28uXG4gKiBUaGUgdXNlIG9mIHRoZSB1bmRlcnNjb3JlIGlzIG1lYW50IHRvIHJlZHVjZSAobm90IGVsaW1pbmF0ZSkgdGhlIHBvdGVudGlhbFxuICogZm9yIG5hbWUgY29uZmxpY3RzLCBhbmQgZGlzY291cmFnZSAobm90IHByZXZlbnQpIGV4dGVybmFsIGFjY2VzcyB0byB0aGlzXG4gKiBkYXRhLiBJbiBtb2Rlcm4gYnJvd3NlcnMsIHRoZSBhYm92ZSBjb2RlIHdpbGwgZWxpbWluYXRlIHRoZSBwb3RlbnRpYWwgb2ZcbiAqIG5hbWluZyBjb25mbGljdHMsIGFuZCBiZXR0ZXIgaGlkZSB0aGUgZGF0YSBiZWhpbmQgYSByZWFsIFN5bWJvbC5cbiAqXG4gKiBAZnVuY3Rpb24gY3JlYXRlU3ltYm9sXG4gKiBAcGFyYW0ge3N0cmluZ30gZGVzY3JpcHRpb24gLSBBIHN0cmluZyB0byBpZGVudGlmeSB0aGUgc3ltYm9sIHdoZW4gZGVidWdnaW5nXG4gKi9cbmV4cG9ydCBkZWZhdWx0IGZ1bmN0aW9uIGNyZWF0ZVN5bWJvbChkZXNjcmlwdGlvbikge1xuICByZXR1cm4gdHlwZW9mIFN5bWJvbCA9PT0gJ2Z1bmN0aW9uJyA/XG4gICAgU3ltYm9sKGRlc2NyaXB0aW9uKSA6XG4gICAgYF8ke2Rlc2NyaXB0aW9ufWA7XG59XG4iLCIvKlxuICogTWljcm90YXNrIGhlbHBlciBmb3IgSUUgMTEuXG4gKlxuICogRXhlY3V0aW5nIGEgZnVuY3Rpb24gYXMgYSBtaWNyb3Rhc2sgaXMgdHJpdmlhbCBpbiBicm93c2VycyB0aGF0IHN1cHBvcnRcbiAqIHByb21pc2VzLCB3aG9zZSB0aGVuKCkgY2xhdXNlcyB1c2UgbWljcm90YXNrIHRpbWluZy4gSUUgMTEgZG9lc24ndCBzdXBwb3J0XG4gKiBwcm9taXNlcywgYnV0IGRvZXMgc3VwcG9ydCBNdXRhdGlvbk9ic2VydmVycywgd2hpY2ggYXJlIGFsc28gZXhlY3V0ZWQgYXNcbiAqIG1pY3JvdGFza3MuIFNvIHRoaXMgaGVscGVyIHVzZXMgYW4gTXV0YXRpb25PYnNlcnZlciB0byBhY2hpZXZlIG1pY3JvdGFza1xuICogdGltaW5nLlxuICpcbiAqIFNlZSBodHRwczovL2pha2VhcmNoaWJhbGQuY29tLzIwMTUvdGFza3MtbWljcm90YXNrcy1xdWV1ZXMtYW5kLXNjaGVkdWxlcy9cbiAqXG4gKiBJbnNwaXJlZCBieSBQb2x5bWVyJ3MgYXN5bmMoKSBmdW5jdGlvbi5cbiAqL1xuXG5cbi8vIFRoZSBxdWV1ZSBvZiBwZW5kaW5nIGNhbGxiYWNrcyB0byBiZSBleGVjdXRlZCBhcyBtaWNyb3Rhc2tzLlxuY29uc3QgY2FsbGJhY2tzID0gW107XG5cbi8vIENyZWF0ZSBhbiBlbGVtZW50IHRoYXQgd2Ugd2lsbCBtb2RpZnkgdG8gZm9yY2Ugb2JzZXJ2YWJsZSBtdXRhdGlvbnMuXG5jb25zdCBlbGVtZW50ID0gZG9jdW1lbnQuY3JlYXRlVGV4dE5vZGUoJycpO1xuXG4vLyBBIG1vbm90b25pY2FsbHktaW5jcmVhc2luZyB2YWx1ZS5cbmxldCBjb3VudGVyID0gMDtcblxuXG4vKipcbiAqIEFkZCBhIGNhbGxiYWNrIHRvIHRoZSBtaWNyb3Rhc2sgcXVldWUuXG4gKlxuICogVGhpcyB1c2VzIGEgTXV0YXRpb25PYnNlcnZlciBzbyB0aGF0IGl0IHdvcmtzIG9uIElFIDExLlxuICpcbiAqIE5PVEU6IElFIDExIG1heSBhY3R1YWxseSB1c2UgdGltZW91dCB0aW1pbmcgd2l0aCBNdXRhdGlvbk9ic2VydmVycy4gVGhpc1xuICogbmVlZHMgbW9yZSBpbnZlc3RpZ2F0aW9uLlxuICpcbiAqIEBmdW5jdGlvbiBtaWNyb3Rhc2tcbiAqIEBwYXJhbSB7ZnVuY3Rpb259IGNhbGxiYWNrXG4gKi9cbmV4cG9ydCBkZWZhdWx0IGZ1bmN0aW9uIG1pY3JvdGFzayhjYWxsYmFjaykge1xuICBjYWxsYmFja3MucHVzaChjYWxsYmFjayk7XG4gIC8vIEZvcmNlIGEgbXV0YXRpb24uXG4gIGVsZW1lbnQudGV4dENvbnRlbnQgPSArK2NvdW50ZXI7XG59XG5cblxuLy8gRXhlY3V0ZSBhbnkgcGVuZGluZyBjYWxsYmFja3MuXG5mdW5jdGlvbiBleGVjdXRlQ2FsbGJhY2tzKCkge1xuICB3aGlsZSAoY2FsbGJhY2tzLmxlbmd0aCA+IDApIHtcbiAgICBjb25zdCBjYWxsYmFjayA9IGNhbGxiYWNrcy5zaGlmdCgpO1xuICAgIGNhbGxiYWNrKCk7XG4gIH1cbn1cblxuXG4vLyBDcmVhdGUgdGhlIG9ic2VydmVyLlxuY29uc3Qgb2JzZXJ2ZXIgPSBuZXcgTXV0YXRpb25PYnNlcnZlcihleGVjdXRlQ2FsbGJhY2tzKTtcbm9ic2VydmVyLm9ic2VydmUoZWxlbWVudCwge1xuICBjaGFyYWN0ZXJEYXRhOiB0cnVlXG59KTtcbiIsImltcG9ydCBjcmVhdGVTeW1ib2wgZnJvbSAnLi9jcmVhdGVTeW1ib2wnO1xuaW1wb3J0IHRvZ2dsZUNsYXNzIGZyb20gJy4vdG9nZ2xlQ2xhc3MnO1xuXG5cbi8vIFN5bWJvbHMgZm9yIHByaXZhdGUgZGF0YSBtZW1iZXJzIG9uIGFuIGVsZW1lbnQuXG5jb25zdCBzYWZlVG9TZXRBdHRyaWJ1dGVzU3ltYm9sID0gY3JlYXRlU3ltYm9sKCdzYWZlVG9TZXRBdHRyaWJ1dGVzJyk7XG5jb25zdCBwZW5kaW5nQXR0cmlidXRlc1N5bWJvbCA9IGNyZWF0ZVN5bWJvbCgncGVuZGluZ0F0dHJpYnV0ZXMnKTtcbmNvbnN0IHBlbmRpbmdDbGFzc2VzU3ltYm9sID0gY3JlYXRlU3ltYm9sKCdwZW5kaW5nQ2xhc3NlcycpO1xuXG5cbi8qKlxuICogSGVscGVyIGZ1bmN0aW9ucyBmb3IgdXBkYXRpbmcgYXR0cmlidXRlcywgaW5jbHVkaW5nIHRoZSBgY2xhc3NgIGF0dHJpYnV0ZS5cbiAqL1xuZXhwb3J0IGRlZmF1bHQge1xuXG4gIC8qKlxuICAgKiBQZXJmb3JtIGFueSBwZW5kaW5nIHVwZGF0ZXMgdG8gYXR0cmlidXRlcyBhbmQgY2xhc3Nlcy5cbiAgICpcbiAgICogVGhpcyB3cml0ZXMgYW55IGBzZXRBdHRyaWJ1dGVgIG9yIGB0b2dnbGVDbGFzc2AgdmFsdWVzIHRoYXQgd2VyZSBwZXJmb3JtZWRcbiAgICogYmVmb3JlIGFuIGVsZW1lbnQgd2FzIGF0dGFjaGVkIHRvIHRoZSBkb2N1bWVudCBmb3IgdGhlIGZpcnN0IHRpbWUuXG4gICAqXG4gICAqIFRoaXMgbWV0aG9kIHNob3VsZCBiZSBjYWxsZWQgYnkgbWl4aW5zL2NvbXBvbmVudHMgaW4gdGhlaXJcbiAgICogYGNvbm5lY3RlZENhbGxiYWNrYC4gSWYgbXVsaXRwbGUgbWl4aW5zL2NvbXBvbmVudHMgaW52b2tlIHRoaXMgZHVyaW5nIHRoZVxuICAgKiBzYW1lIGBjb25uZWN0ZWRDYWxsYmFja2AsIG9ubHkgdGhlIGZpcnN0IGNhbGwgd2lsbCBoYXZlIGFueSBlZmZlY3QuIFRoZVxuICAgKiBzdWJzZXF1ZW50IGNhbGxzIHdpbGwgYmUgaGFybWxlc3MuXG4gICAqXG4gICAqIEBwYXJhbSB7SFRNTEVsZW1lbnR9IGVsZW1lbnQgLSBUaGUgZWxlbWVudCBiZWluZyBhZGRlZCB0byB0aGUgZG9jdW1lbnQuXG4gICAqL1xuICBjb25uZWN0ZWQoZWxlbWVudCkge1xuICAgIGVsZW1lbnRbc2FmZVRvU2V0QXR0cmlidXRlc1N5bWJvbF0gPSB0cnVlO1xuXG4gICAgLy8gU2V0IGFueSBwZW5kaW5nIGF0dHJpYnV0ZXMuXG4gICAgaWYgKGVsZW1lbnRbcGVuZGluZ0F0dHJpYnV0ZXNTeW1ib2xdKSB7XG4gICAgICBmb3IgKGxldCBhdHRyaWJ1dGUgaW4gZWxlbWVudFtwZW5kaW5nQXR0cmlidXRlc1N5bWJvbF0pIHtcbiAgICAgICAgY29uc3QgdmFsdWUgPSBlbGVtZW50W3BlbmRpbmdBdHRyaWJ1dGVzU3ltYm9sXVthdHRyaWJ1dGVdO1xuICAgICAgICBzZXRBdHRyaWJ1dGVUb0VsZW1lbnQoZWxlbWVudCwgYXR0cmlidXRlLCB2YWx1ZSk7XG4gICAgICB9XG4gICAgICBlbGVtZW50W3BlbmRpbmdBdHRyaWJ1dGVzU3ltYm9sXSA9IG51bGw7XG4gICAgfVxuXG4gICAgLy8gU2V0IGFueSBwZW5kaW5nIGNsYXNzZXMuXG4gICAgaWYgKGVsZW1lbnRbcGVuZGluZ0NsYXNzZXNTeW1ib2xdKSB7XG4gICAgICBmb3IgKGxldCBjbGFzc05hbWUgaW4gZWxlbWVudFtwZW5kaW5nQ2xhc3Nlc1N5bWJvbF0pIHtcbiAgICAgICAgY29uc3QgdmFsdWUgPSBlbGVtZW50W3BlbmRpbmdDbGFzc2VzU3ltYm9sXVtjbGFzc05hbWVdO1xuICAgICAgICB0b2dnbGVDbGFzcyhlbGVtZW50LCBjbGFzc05hbWUsIHZhbHVlKTtcbiAgICAgIH1cbiAgICAgIGVsZW1lbnRbcGVuZGluZ0NsYXNzZXNTeW1ib2xdID0gbnVsbDtcbiAgICB9XG4gIH0sXG5cbiAgLyoqXG4gICAqIFNldC91bnNldCB0aGUgYXR0cmlidXRlIHdpdGggdGhlIGluZGljYXRlZCBuYW1lLlxuICAgKlxuICAgKiBUaGlzIG1ldGhvZCBleGlzdHMgcHJpbWFyaWx5IHRvIGhhbmRsZSB0aGUgY2FzZSB3aGVyZSBhbiBlbGVtZW50IHdhbnRzIHRvXG4gICAqIHNldCBhIGRlZmF1bHQgcHJvcGVydHkgdmFsdWUgdGhhdCBzaG91bGQgYmUgcmVmbGVjdGVkIGFzIGFuIGF0dHJpYnV0ZS4gQW5cbiAgICogaW1wb3J0YW50IGxpbWl0YXRpb24gb2YgY3VzdG9tIGVsZW1lbnQgY29uc3R1cmN0b3JzIGlzIHRoYXQgdGhleSBjYW5ub3RcbiAgICogc2V0IGF0dHJpYnV0ZXMuIEEgY2FsbCB0byBgc2V0QXR0cmlidXRlYCBkdXJpbmcgdGhlIGNvbnN0cnVjdG9yIHdpbGxcbiAgICogYmUgZGVmZXJyZWQgdW50aWwgdGhlIGVsZW1lbnQgaXMgY29ubmVjdGVkIHRvIHRoZSBkb2N1bWVudC5cbiAgICpcbiAgICogQHBhcmFtIHtzdHJpbmd9IGF0dHJpYnV0ZSAtIFRoZSBuYW1lIG9mIHRoZSAqYXR0cmlidXRlKiAobm90IHByb3BlcnR5KSB0byBzZXQuXG4gICAqIEBwYXJhbSB7b2JqZWN0fSB2YWx1ZSAtIFRoZSB2YWx1ZSB0byBzZXQuIElmIG51bGwsIHRoZSBhdHRyaWJ1dGUgd2lsbCBiZSByZW1vdmVkLlxuICAgKi9cbiAgc2V0QXR0cmlidXRlKGVsZW1lbnQsIGF0dHJpYnV0ZSwgdmFsdWUpIHtcbiAgICBpZiAoZWxlbWVudFtzYWZlVG9TZXRBdHRyaWJ1dGVzU3ltYm9sXSkge1xuICAgICAgLy8gU2FmZSB0byBzZXQgYXR0cmlidXRlcyBpbW1lZGlhdGVseS5cbiAgICAgIHNldEF0dHJpYnV0ZVRvRWxlbWVudChlbGVtZW50LCBhdHRyaWJ1dGUsIHZhbHVlKTtcbiAgICB9IGVsc2Uge1xuICAgICAgLy8gRGVmZXIgc2V0dGluZyBhdHRyaWJ1dGVzIHVudGlsIHRoZSBmaXJzdCB0aW1lIHdlJ3JlIGNvbm5lY3RlZC5cbiAgICAgIGlmICghZWxlbWVudFtwZW5kaW5nQXR0cmlidXRlc1N5bWJvbF0pIHtcbiAgICAgICAgZWxlbWVudFtwZW5kaW5nQXR0cmlidXRlc1N5bWJvbF0gPSB7fTtcbiAgICAgIH1cbiAgICAgIGVsZW1lbnRbcGVuZGluZ0F0dHJpYnV0ZXNTeW1ib2xdW2F0dHJpYnV0ZV0gPSB2YWx1ZTtcbiAgICB9XG4gIH0sXG5cbiAgLyoqXG4gICAqIFNldC91bnNldCB0aGUgY2xhc3Mgd2l0aCB0aGUgaW5kaWNhdGVkIG5hbWUuXG4gICAqXG4gICAqIFRoaXMgbWV0aG9kIGV4aXN0cyBwcmltYXJpbHkgdG8gaGFuZGxlIHRoZSBjYXNlIHdoZXJlIGFuIGVsZW1lbnQgd2FudHMgdG9cbiAgICogc2V0IGEgZGVmYXVsdCBwcm9wZXJ0eSB2YWx1ZSB0aGF0IHNob3VsZCBiZSByZWZsZWN0ZWQgYXMgYXMgY2xhc3MuIEFuXG4gICAqIGltcG9ydGFudCBsaW1pdGF0aW9uIG9mIGN1c3RvbSBlbGVtZW50IGNvbnN0dXJjdG9ycyBpcyB0aGF0IHRoZXkgY2Fubm90XG4gICAqIHNldCBhdHRyaWJ1dGVzLCBpbmNsdWRpbmcgdGhlIGBjbGFzc2AgYXR0cmlidXRlLiBBIGNhbGwgdG9cbiAgICogYHRvZ2dsZUNsYXNzYCBkdXJpbmcgdGhlIGNvbnN0cnVjdG9yIHdpbGwgYmUgZGVmZXJyZWQgdW50aWwgdGhlIGVsZW1lbnRcbiAgICogaXMgY29ubmVjdGVkIHRvIHRoZSBkb2N1bWVudC5cbiAgICpcbiAgICogQHBhcmFtIHtzdHJpbmd9IGNsYXNzTmFtZSAtIFRoZSBuYW1lIG9mIHRoZSBjbGFzcyB0byBzZXQuXG4gICAqIEBwYXJhbSB7b2JqZWN0fSB2YWx1ZSAtIFRydWUgdG8gc2V0IHRoZSBjbGFzcywgZmFsc2UgdG8gcmVtb3ZlIGl0LlxuICAgKi9cbiAgdG9nZ2xlQ2xhc3MoZWxlbWVudCwgY2xhc3NOYW1lLCB2YWx1ZSkge1xuICAgIGlmIChlbGVtZW50W3NhZmVUb1NldEF0dHJpYnV0ZXNTeW1ib2xdKSB7XG4gICAgICAvLyBTYWZlIHRvIHNldCBjbGFzcyBpbW1lZGlhdGVseS5cbiAgICAgIHRvZ2dsZUNsYXNzKGVsZW1lbnQsIGNsYXNzTmFtZSwgdmFsdWUpO1xuICAgIH0gZWxzZSB7XG4gICAgICAvLyBEZWZlciBzZXR0aW5nIGNsYXNzIHVudGlsIHRoZSBmaXJzdCB0aW1lIHdlJ3JlIGNvbm5lY3RlZC5cbiAgICAgIGlmICghZWxlbWVudFtwZW5kaW5nQ2xhc3Nlc1N5bWJvbF0pIHtcbiAgICAgICAgZWxlbWVudFtwZW5kaW5nQ2xhc3Nlc1N5bWJvbF0gPSB7fTtcbiAgICAgIH1cbiAgICAgIGVsZW1lbnRbcGVuZGluZ0NsYXNzZXNTeW1ib2xdW2NsYXNzTmFtZV0gPSB2YWx1ZTtcbiAgICB9XG4gIH1cblxufTtcblxuXG4vLyBSZWZsZWN0IHRoZSBhdHRyaWJ1dGUgdG8gdGhlIGdpdmVuIGVsZW1lbnQuXG4vLyBJZiB0aGUgdmFsdWUgaXMgbnVsbCwgcmVtb3ZlIHRoZSBhdHRyaWJ1dGUuXG5mdW5jdGlvbiBzZXRBdHRyaWJ1dGVUb0VsZW1lbnQoZWxlbWVudCwgYXR0cmlidXRlTmFtZSwgdmFsdWUpIHtcbiAgaWYgKHZhbHVlID09PSBudWxsIHx8IHR5cGVvZiB2YWx1ZSA9PT0gJ3VuZGVmaW5lZCcpIHtcbiAgICBlbGVtZW50LnJlbW92ZUF0dHJpYnV0ZShhdHRyaWJ1dGVOYW1lKTtcbiAgfSBlbHNlIHtcbiAgICBjb25zdCB0ZXh0ID0gU3RyaW5nKHZhbHVlKTtcbiAgICAvLyBBdm9pZCByZWN1cnNpdmUgYXR0cmlidXRlQ2hhbmdlZENhbGxiYWNrIGNhbGxzLlxuICAgIGlmIChlbGVtZW50LmdldEF0dHJpYnV0ZShhdHRyaWJ1dGVOYW1lKSAhPT0gdGV4dCkge1xuICAgICAgZWxlbWVudC5zZXRBdHRyaWJ1dGUoYXR0cmlidXRlTmFtZSwgdmFsdWUpO1xuICAgIH1cbiAgfVxufVxuIiwiaW1wb3J0IGNyZWF0ZVN5bWJvbCBmcm9tICcuL2NyZWF0ZVN5bWJvbCc7XG5cbi8qKlxuICogQSBjb2xsZWN0aW9uIG9mIFN5bWJvbCBvYmplY3RzIGZvciBzdGFuZGFyZCBjb21wb25lbnQgcHJvcGVydGllcyBhbmQgbWV0aG9kcy5cbiAqXG4gKiBUaGVzZSBTeW1ib2wgb2JqZWN0cyBhcmUgdXNlZCB0byBhbGxvdyBtaXhpbnMgYW5kIGEgY29tcG9uZW50IHRvIGludGVybmFsbHlcbiAqIGNvbW11bmljYXRlLCB3aXRob3V0IGV4cG9zaW5nIHRoZXNlIHByb3BlcnRpZXMgYW5kIG1ldGhvZHMgaW4gdGhlIGNvbXBvbmVudCdzXG4gKiBwdWJsaWMgQVBJLlxuICpcbiAqIFRvIHVzZSB0aGVzZSBTeW1ib2wgb2JqZWN0cyBpbiB5b3VyIG93biBjb21wb25lbnQsIGluY2x1ZGUgdGhpcyBtb2R1bGUgYW5kXG4gKiB0aGVuIGNyZWF0ZSBhIHByb3BlcnR5IG9yIG1ldGhvZCB3aG9zZSBrZXkgaXMgdGhlIGRlc2lyZWQgU3ltYm9sLlxuICpcbiAqICAgICBpbXBvcnQgJ1NpbmdsZVNlbGVjdGlvbk1peGluJyBmcm9tICdiYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy9TaW5nbGVTZWxlY3Rpb25NaXhpbic7XG4gKiAgICAgaW1wb3J0ICdzeW1ib2xzJyBmcm9tICdiYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy9zeW1ib2xzJztcbiAqXG4gKiAgICAgY2xhc3MgTXlFbGVtZW50IGV4dGVuZHMgU2luZ2xlU2VsZWN0aW9uTWl4aW4oSFRNTEVsZW1lbnQpIHtcbiAqICAgICAgIFtzeW1ib2xzLml0ZW1TZWxlY3RlZF0oaXRlbSwgc2VsZWN0ZWQpIHtcbiAqICAgICAgICAgLy8gVGhpcyB3aWxsIGJlIGludm9rZWQgd2hlbmV2ZXIgYW4gaXRlbSBpcyBzZWxlY3RlZC9kZXNlbGVjdGVkLlxuICogICAgICAgfVxuICogICAgIH1cbiAqXG4gKiBAbW9kdWxlIHN5bWJvbHNcbiAqL1xuY29uc3Qgc3ltYm9scyA9IHtcblxuICAvKipcbiAgICogU3ltYm9sIGZvciB0aGUgYGRlZmF1bHRzYCBwcm9wZXJ0eS5cbiAgICpcbiAgICogVGhpcyBwcm9wZXJ0eSBjYW4gYmUgdXNlZCB0byBzZXQgb3Igb3ZlcnJpZGUgZGVmYXVsdHMgdGhhdCB3aWxsIGJlIGFwcGxpZWRcbiAgICogdG8gYSBuZXcgY29tcG9uZW50IGluc3RhbmNlLiBXaGVuIGltcGxlbWVudGluZyB0aGlzIHByb3BlcnR5LCB0YWtlIGNhcmUgdG9cbiAgICogZmlyc3QgYWNxdWlyZSBhbnkgZGVmYXVsdHMgZGVmaW5lZCBieSB0aGUgc3VwZXJjbGFzcy4gVGhlIHN0YW5kYXJkIGlkaW9tIGlzXG4gICAqIGFzIGZvbGxvd3M6XG4gICAqXG4gICAqICAgICBnZXQgW3N5bWJvbHMuZGVmYXVsdHNdKCkge1xuICAgKiAgICAgICBjb25zdCBkZWZhdWx0cyA9IHN1cGVyW3N5bWJvbHMuZGVmYXVsdHNdIHx8IHt9O1xuICAgKiAgICAgICAvLyBTZXQgb3Igb3ZlcnJpZGUgZGVmYXVsdCB2YWx1ZXMgaGVyZVxuICAgKiAgICAgICBkZWZhdWx0cy5jdXN0b21Qcm9wZXJ0eSA9IGZhbHNlO1xuICAgKiAgICAgICByZXR1cm4gZGVmYXVsdHM7XG4gICAqICAgICB9XG4gICAqXG4gICAqIEB2YXIge29iamVjdH0gZGVmYXVsdHNcbiAgICovXG4gIGRlZmF1bHRzOiBjcmVhdGVTeW1ib2woJ2RlZmF1bHRzJyksXG5cbiAgLyoqXG4gICAqIFN5bWJvbCBmb3IgdGhlIGBkcmFnZ2luZ2AgcHJvcGVydHkuXG4gICAqXG4gICAqIENvbXBvbmVudHMgbGlrZSBjYXJvdXNlbHMgb2Z0ZW4gZGVmaW5lIGFuaW1hdGVkIENTUyB0cmFuc2l0aW9ucyBmb3JcbiAgICogc2xpZGluZyBlZmZlY3RzLiBTdWNoIGEgdHJhbnNpdGlvbiBzaG91bGQgdXN1YWxseSAqbm90KiBiZSBhcHBsaWVkIHdoaWxlXG4gICAqIHRoZSB1c2VyIGlzIGRyYWdnaW5nLCBiZWNhdXNlIGEgQ1NTIGFuaW1hdGlvbiB3aWxsIGludHJvZHVjZSBhIGxhZyB0aGF0XG4gICAqIG1ha2VzIHRoZSBzd2lwZSBmZWVsIHNsdWdnaXNoLiBJbnN0ZWFkLCBhcyBsb25nIGFzIHRoZSB1c2VyIGlzIGRyYWdnaW5nXG4gICAqIHdpdGggdGhlaXIgZmluZ2VyIGRvd24sIHRoZSB0cmFuc2l0aW9uIHNob3VsZCBiZSBzdXBwcmVzc2VkLiBXaGVuIHRoZVxuICAgKiB1c2VyIHJlbGVhc2VzIHRoZWlyIGZpbmdlciwgdGhlIHRyYW5zaXRpb24gY2FuIGJlIHJlc3RvcmVkLCBhbGxvd2luZyB0aGVcbiAgICogYW5pbWF0aW9uIHRvIHNob3cgdGhlIGNhcm91c2VsIHNsaWRpbmcgaW50byBpdHMgZmluYWwgcG9zaXRpb24uXG4gICAqXG4gICAqIEB0eXBlIHtib29sZWFufSB0cnVlIGlmIGEgZHJhZyBpcyBpbiBwcm9ncmVzcywgZmFsc2UgaWYgbm90LlxuICAgKi9cbiAgZHJhZ2dpbmc6IGNyZWF0ZVN5bWJvbCgnZHJhZ2dpbmcnKSxcblxuICAvKipcbiAgICogU3ltYm9sIGZvciB0aGUgYGdvRG93bmAgbWV0aG9kLlxuICAgKlxuICAgKiBUaGlzIG1ldGhvZCBpcyBpbnZva2VkIHdoZW4gdGhlIHVzZXIgd2FudHMgdG8gZ28vbmF2aWdhdGUgZG93bi5cbiAgICpcbiAgICogQGZ1bmN0aW9uIGdvRG93blxuICAgKi9cbiAgZ29Eb3duOiBjcmVhdGVTeW1ib2woJ2dvRG93bicpLFxuXG4gIC8qKlxuICAgKiBTeW1ib2wgZm9yIHRoZSBgZ29FbmRgIG1ldGhvZC5cbiAgICpcbiAgICogVGhpcyBtZXRob2QgaXMgaW52b2tlZCB3aGVuIHRoZSB1c2VyIHdhbnRzIHRvIGdvL25hdmlnYXRlIHRvIHRoZSBlbmQgKGUuZy4sXG4gICAqIG9mIGEgbGlzdCkuXG4gICAqXG4gICAqIEBmdW5jdGlvbiBnb0VuZFxuICAgKi9cbiAgZ29FbmQ6IGNyZWF0ZVN5bWJvbCgnZ29FbmQnKSxcblxuICAvKipcbiAgICogU3ltYm9sIGZvciB0aGUgYGdvTGVmdGAgbWV0aG9kLlxuICAgKlxuICAgKiBUaGlzIG1ldGhvZCBpcyBpbnZva2VkIHdoZW4gdGhlIHVzZXIgd2FudHMgdG8gZ28vbmF2aWdhdGUgbGVmdC5cbiAgICpcbiAgICogQGZ1bmN0aW9uIGdvTGVmdFxuICAgKi9cbiAgZ29MZWZ0OiBjcmVhdGVTeW1ib2woJ2dvTGVmdCcpLFxuXG4gIC8qKlxuICAgKiBTeW1ib2wgZm9yIHRoZSBgZ29SaWdodGAgbWV0aG9kLlxuICAgKlxuICAgKiBUaGlzIG1ldGhvZCBpcyBpbnZva2VkIHdoZW4gdGhlIHVzZXIgd2FudHMgdG8gZ28vbmF2aWdhdGUgcmlnaHQuXG4gICAqXG4gICAqIEBmdW5jdGlvbiBnb1JpZ2h0XG4gICAqL1xuICBnb1JpZ2h0OiBjcmVhdGVTeW1ib2woJ2dvUmlnaHQnKSxcblxuICAvKipcbiAgICogU3ltYm9sIGZvciB0aGUgYGdvU3RhcnRgIG1ldGhvZC5cbiAgICpcbiAgICogVGhpcyBtZXRob2QgaXMgaW52b2tlZCB3aGVuIHRoZSB1c2VyIHdhbnRzIHRvIGdvL25hdmlnYXRlIHRvIHRoZSBzdGFydFxuICAgKiAoZS5nLiwgb2YgYSBsaXN0KS5cbiAgICpcbiAgICogQGZ1bmN0aW9uIGdvU3RhcnRcbiAgICovXG4gIGdvU3RhcnQ6IGNyZWF0ZVN5bWJvbCgnZ29TdGFydCcpLFxuXG4gIC8qKlxuICAgKiBTeW1ib2wgZm9yIHRoZSBgZ29VcGAgbWV0aG9kLlxuICAgKlxuICAgKiBUaGlzIG1ldGhvZCBpcyBpbnZva2VkIHdoZW4gdGhlIHVzZXIgd2FudHMgdG8gZ28vbmF2aWdhdGUgdXAuXG4gICAqXG4gICAqIEBmdW5jdGlvbiBnb1VwXG4gICAqL1xuICBnb1VwOiBjcmVhdGVTeW1ib2woJ2dvVXAnKSxcblxuICAvKipcbiAgICogU3ltYm9sIGZvciB0aGUgYGl0ZW1BZGRlZGAgbWV0aG9kLlxuICAgKlxuICAgKiBUaGlzIG1ldGhvZCBpcyBpbnZva2VkIHdoZW4gYSBuZXcgaXRlbSBpcyBhZGRlZCB0byBhIGxpc3QuXG4gICAqXG4gICAqIEBmdW5jdGlvbiBpdGVtQWRkZWRcbiAgICogQHBhcmFtIHtIVE1MRWxlbWVudH0gaXRlbSAtIHRoZSBpdGVtIGJlaW5nIHNlbGVjdGVkL2Rlc2VsZWN0ZWRcbiAgICovXG4gIGl0ZW1BZGRlZDogY3JlYXRlU3ltYm9sKCdpdGVtQWRkZWQnKSxcblxuXG4gIC8qKlxuICAgKiBTeW1ib2wgZm9yIHRoZSBgaXRlbXNDaGFuZ2VkYCBtZXRob2QuXG4gICAqXG4gICAqIFRoaXMgbWV0aG9kIGlzIGludm9rZWQgd2hlbiB0aGUgdW5kZXJseWluZyBjb250ZW50cyBjaGFuZ2UuIEl0IGlzIGFsc29cbiAgICogaW52b2tlZCBvbiBjb21wb25lbnQgaW5pdGlhbGl6YXRpb24g4oCTIHNpbmNlIHRoZSBpdGVtcyBoYXZlIFwiY2hhbmdlZFwiIGZyb21cbiAgICogYmVpbmcgbm90aGluZy5cbiAgICovXG4gIGl0ZW1zQ2hhbmdlZDogY3JlYXRlU3ltYm9sKCdpdGVtc0NoYW5nZWQnKSxcblxuICAvKipcbiAgICogU3ltYm9sIGZvciB0aGUgYGl0ZW1TZWxlY3RlZGAgbWV0aG9kLlxuICAgKlxuICAgKiBUaGlzIG1ldGhvZCBpcyBpbnZva2VkIHdoZW4gYW4gaXRlbSBiZWNvbWVzIHNlbGVjdGVkIG9yIGRlc2VsZWN0ZWQuXG4gICAqXG4gICAqIEBmdW5jdGlvbiBpdGVtU2VsZWN0ZWRcbiAgICogQHBhcmFtIHtIVE1MRWxlbWVudH0gaXRlbSAtIHRoZSBpdGVtIGJlaW5nIHNlbGVjdGVkL2Rlc2VsZWN0ZWRcbiAgICogQHBhcmFtIHtib29sZWFufSBzZWxlY3RlZCAtIHRydWUgaWYgdGhlIGl0ZW0gaXMgc2VsZWN0ZWQsIGZhbHNlIGlmIG5vdFxuICAgKi9cbiAgaXRlbVNlbGVjdGVkOiBjcmVhdGVTeW1ib2woJ2l0ZW1TZWxlY3RlZCcpLFxuXG4gIC8qKlxuICAgKiBTeW1ib2wgZm9yIHRoZSBga2V5ZG93bmAgbWV0aG9kLlxuICAgKlxuICAgKiBUaGlzIG1ldGhvZCBpcyBpbnZva2VkIHdoZW4gYW4gZWxlbWVudCByZWNlaXZlcyBhIGBrZXlkb3duYCBldmVudC5cbiAgICpcbiAgICogQGZ1bmN0aW9uIGtleWRvd25cbiAgICogQHBhcmFtIHtLZXlib2FyZEV2ZW50fSBldmVudCAtIHRoZSBldmVudCBiZWluZyBwcm9jZXNzZWRcbiAgICovXG4gIGtleWRvd246IGNyZWF0ZVN5bWJvbCgna2V5ZG93bicpLFxuXG4gIC8qKlxuICAgKiBTeW1ib2wgZm9yIHRoZSBgdGVtcGxhdGVgIHByb3BlcnR5LlxuICAgKlxuICAgKiBUaGlzIHByb3BlcnR5IHJldHVybnMgYSBjb21wb25lbnQncyB0ZW1wbGF0ZS5cbiAgICpcbiAgICogQHR5cGUge3N0cmluZ3xIVE1MRWxlbWVudH1cbiAgICovXG4gIHRlbXBsYXRlOiBjcmVhdGVTeW1ib2woJ3RlbXBsYXRlJylcbn07XG5cbmV4cG9ydCBkZWZhdWx0IHN5bWJvbHM7XG4iLCIvKipcbiAqIEhlbHBlciBmdW5jdGlvbiBmb3Igc3RhbmRhcmQgY2xhc3NMaXN0LnRvZ2dsZSgpIGJlaGF2aW9yIG9uIG9sZCBicm93c2VycyxcbiAqIG5hbWVseSBJRSAxMS5cbiAqXG4gKiBUaGUgc3RhbmRhcmRcbiAqIFtjbGFzc2xpc3RdKGh0dHBzOi8vZGV2ZWxvcGVyLm1vemlsbGEub3JnL2VuLVVTL2RvY3MvV2ViL0FQSS9FbGVtZW50L2NsYXNzTGlzdClcbiAqIG9iamVjdCBoYXMgYSBgdG9nZ2xlKClgIGZ1bmN0aW9uIHRoYXQgc3VwcG9ydHMgYSBzZWNvbmQgQm9vbGVhbiBwYXJhbWV0ZXJcbiAqIHRoYXQgY2FuIGJlIHVzZWQgdG8gc3VjY2luY3RseSB0dXJuIGEgY2xhc3Mgb24gb3Igb2ZmLiBUaGlzIGZlYXR1cmUgaXMgb2Z0ZW5cbiAqIHVzZWZ1bCBpbiBkZXNpZ25pbmcgY3VzdG9tIGVsZW1lbnRzLCB3aGljaCBtYXkgd2FudCB0byBleHRlcm5hbGx5IHJlZmxlY3RcbiAqIGNvbXBvbmVudCBzdGF0ZSBpbiBhIENTUyBjbGFzcyB0aGF0IGNhbiBiZSB1c2VkIGZvciBzdHlsaW5nIHB1cnBvc2VzLlxuICpcbiAqIFVuZm9ydHVuYXRlbHksIElFIDExIGRvZXMgbm90IHN1cHBvcnQgdGhlIEJvb2xlYW4gcGFyYW1ldGVyIHRvXG4gKiBgY2xhc3NMaXN0LnRvZ2dsZSgpYC4gVGhpcyBoZWxwZXIgZnVuY3Rpb24gYmVoYXZlcyBsaWtlIHRoZSBzdGFuZGFyZFxuICogYHRvZ2dsZSgpYCwgaW5jbHVkaW5nIHN1cHBvcnQgZm9yIHRoZSBCb29sZWFuIHBhcmFtZXRlciwgc28gdGhhdCBpdCBjYW4gYmVcbiAqIHVzZWQgZXZlbiBvbiBJRSAxMS5cbiAqXG4gKiBAZnVuY3Rpb24gdG9nZ2xlQ2xhc3NcbiAqIEBwYXJhbSB7SFRNTEVsZW1lbnR9IGVsZW1lbnQgLSBUaGUgZWxlbWVudCB0byBtb2RpZnlcbiAqIEBwYXJhbSB7c3RyaW5nfSBjbGFzc05hbWUgLSBUaGUgY2xhc3MgdG8gYWRkL3JlbW92ZVxuICogQHBhcmFtIHtib29sZWFufSBbZm9yY2VdIC0gRm9yY2UgdGhlIGNsYXNzIHRvIGJlIGFkZGVkIChpZiB0cnVlKSBvciByZW1vdmVkXG4gKiAgICAgICAgICAgICAgICAgICAgICAgICAgICAoaWYgZmFsc2UpXG4gKi9cbmV4cG9ydCBkZWZhdWx0IGZ1bmN0aW9uIHRvZ2dsZUNsYXNzKGVsZW1lbnQsIGNsYXNzTmFtZSwgZm9yY2UpIHtcbiAgY29uc3QgY2xhc3NMaXN0ID0gZWxlbWVudC5jbGFzc0xpc3Q7XG4gIGNvbnN0IGFkZENsYXNzID0gKHR5cGVvZiBmb3JjZSA9PT0gJ3VuZGVmaW5lZCcpID9cbiAgICAhY2xhc3NMaXN0LmNvbnRhaW5zKGNsYXNzTmFtZSkgOlxuICAgIGZvcmNlO1xuICBpZiAoYWRkQ2xhc3MpIHtcbiAgICBjbGFzc0xpc3QuYWRkKGNsYXNzTmFtZSk7XG4gIH0gZWxzZSB7XG4gICAgY2xhc3NMaXN0LnJlbW92ZShjbGFzc05hbWUpO1xuICB9XG4gIHJldHVybiBhZGRDbGFzcztcbn1cbiIsImltcG9ydCBBdHRyaWJ1dGVNYXJzaGFsbGluZ01peGluIGZyb20gJy4uLy4uL2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL0F0dHJpYnV0ZU1hcnNoYWxsaW5nTWl4aW4nO1xuaW1wb3J0IENvbXBvc2FibGVNaXhpbiBmcm9tICcuLi8uLi9iYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy9Db21wb3NhYmxlTWl4aW4nO1xuaW1wb3J0IERpc3RyaWJ1dGVkQ2hpbGRyZW5NaXhpbiBmcm9tICcuLi8uLi9iYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy9EaXN0cmlidXRlZENoaWxkcmVuTWl4aW4nO1xuaW1wb3J0IFNoYWRvd0VsZW1lbnRSZWZlcmVuY2VzTWl4aW4gZnJvbSAnLi4vLi4vYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvU2hhZG93RWxlbWVudFJlZmVyZW5jZXNNaXhpbic7XG5pbXBvcnQgU2hhZG93VGVtcGxhdGVNaXhpbiBmcm9tICcuLi8uLi9iYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy9TaGFkb3dUZW1wbGF0ZU1peGluJztcblxuXG4vKipcbiAqIEEgc2FtcGxlIGdlbmVyYWwtcHVycG9zZSBiYXNlIGNsYXNzIGZvciBkZWZpbmluZyBjdXN0b20gZWxlbWVudHMgdGhhdCBtaXhlc1xuICogaW4gc29tZSBjb21tb24gZmVhdHVyZXM6IHRlbXBsYXRlIHN0YW1waW5nIGludG8gYSBzaGFkb3cgcm9vdCwgc2hhZG93IGVsZW1lbnRcbiAqIHJlZmVyZW5jZXMsIG1hcnNoYWxsaW5nIGF0dHJpYnV0ZXMgdG8gcHJvcGVydGllcywgYW5kIHJldHJpZXZpbmcgdGhlIGNoaWxkcmVuXG4gKiBkaXN0cmlidXRlZCB0byBhIGNvbXBvbmVudC5cbiAqXG4gKiBUaGlzIGJhc2UgY2xhc3MgaXMgbm90IHNwZWNpYWwgaW4gYW55IHdheSwgYW5kIGlzIGRlZmluZWQgb25seSBhcyBhXG4gKiBjb252ZW5pZW50IHNob3J0aGFuZCBmb3IgYXBwbHlpbmcgdGhlIG1peGlucyBsaXN0ZWQgYWJvdmUuIFlvdSBjYW4gdXNlIHRoaXNcbiAqIGNsYXNzIGFzIGEgYmFzZSBjbGFzcyBmb3IgeW91ciBvd24gZWxlbWVudHMsIG9yIGVhc2lseSBjcmVhdGUgeW91ciBvd24gYmFzZVxuICogY2xhc3MgYnkgYXBwbHlpbmcgdGhlIHNhbWUgc2V0IG9mIG1peGlucy5cbiAqXG4gKiBUaGUgRWxlbWVudEJhc2UgYmFzZSBjbGFzcyBkb2VzIG5vdCByZWdpc3RlciBpdHNlbGYgYXMgYSBjdXN0b20gZWxlbWVudCB3aXRoXG4gKiB0aGUgYnJvd3NlciwgYW5kIGhlbmNlIGNhbm5vdCBiZSBpbmRlcGVuZGVudGx5IGluc3RhbnRpYXRlZC5cbiAqXG4gKiBAbWl4ZXMgQXR0cmlidXRlTWFyc2hhbGxpbmdNaXhpblxuICogQG1peGVzIENvbXBvc2FibGVNaXhpblxuICogQG1peGVzIERpc3RyaWJ1dGVkQ2hpbGRyZW5NaXhpblxuICogQG1peGVzIFNoYWRvd0VsZW1lbnRSZWZlcmVuY2VzTWl4aW5cbiAqIEBtaXhlcyBTaGFkb3dUZW1wbGF0ZU1peGluXG4gKi9cbmNsYXNzIEVsZW1lbnRCYXNlIGV4dGVuZHMgQ29tcG9zYWJsZU1peGluKEhUTUxFbGVtZW50KS5jb21wb3NlKFxuICBTaGFkb3dUZW1wbGF0ZU1peGluLCAgICAgICAgICAvLyBiZWZvcmUgbm9kZSBmaW5kaW5nLCBzbyBzaGFkb3cgcm9vdCBpcyBwb3B1bGF0ZWRcbiAgU2hhZG93RWxlbWVudFJlZmVyZW5jZXNNaXhpbiwgLy8gYmVmb3JlIG1hcnNoYWxsaW5nLCBzbyBwcm9wZXJ0aWVzIGNhbiB1c2UgcmVmc1xuICBBdHRyaWJ1dGVNYXJzaGFsbGluZ01peGluLFxuICBEaXN0cmlidXRlZENoaWxkcmVuTWl4aW5cbikge31cblxuZXhwb3J0IGRlZmF1bHQgRWxlbWVudEJhc2U7XG4iLCIvKlxuICogVGhpcyBmaWxlIGlzIHRyYW5zcGlsZWQgdG8gY3JlYXRlIGFuIEVTNS1jb21wYXRpYmxlIGRpc3RyaWJ1dGlvbiBpbiB3aGljaFxuICogdGhlIHBhY2thZ2UncyBtYWluIGZlYXR1cmUocykgYXJlIGF2YWlsYWJsZSB2aWEgdGhlIHdpbmRvdy5CYXNpYyBnbG9iYWwuXG4gKiBJZiB5b3UncmUgYWxyZWFkeSB1c2luZyBFUzYgeW91cnNlbGYsIGlnbm9yZSB0aGlzIGZpbGUsIGFuZCBpbnN0ZWFkIGltcG9ydFxuICogdGhlIHNvdXJjZSBmaWxlKHMpIHlvdSB3YW50IGZyb20gdGhlIHNyYyBmb2xkZXIuXG4gKi9cblxuaW1wb3J0IFNsaWRlc2hvd1dpdGhDb250cm9scyBmcm9tICcuL3NyYy9TbGlkZXNob3dXaXRoQ29udHJvbHMnO1xuXG53aW5kb3cuQmFzaWMgPSB3aW5kb3cuQmFzaWMgfHwge307XG53aW5kb3cuQmFzaWMuU2xpZGVzaG93V2l0aENvbnRyb2xzID0gU2xpZGVzaG93V2l0aENvbnRyb2xzO1xuIiwiaW1wb3J0IFNsaWRlc2hvdyBmcm9tICcuLi8uLi9iYXNpYy1zbGlkZXNob3cvc3JjL1NsaWRlc2hvdyc7XG5pbXBvcnQgUGxheUNvbnRyb2xzTWl4aW4gZnJvbSAnLi4vLi4vYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvUGxheUNvbnRyb2xzTWl4aW4nO1xuXG4vKipcbiAqIEFuIGV4dGVuc2lvbiBvZlxuICogW2Jhc2ljLXNsaWRlc2hvd10oLi4vYmFzaWMtc2xpZGVzaG93KSB0aGF0IGFkZHMgcGxheSBjb250cm9sc1xuICogdmlhIFtQbGF5Q29udHJvbHNNaXhpbl0oLi4vYmFzaWMtY29tcG9uZW50LW1peGlucy9kb2NzL1BsYXlDb250cm9sc01peGluLm1kKS5cbiAqXG4gKiBAZXh0ZW5kcyBTbGlkZXNob3dcbiAqIEBtaXhlcyBQbGF5Q29udHJvbHNNaXhpblxuICovXG5jbGFzcyBTbGlkZXNob3dXaXRoQ29udHJvbHMgZXh0ZW5kcyBQbGF5Q29udHJvbHNNaXhpbihTbGlkZXNob3cpIHt9XG5jdXN0b21FbGVtZW50cy5kZWZpbmUoJ2Jhc2ljLXNsaWRlc2hvdy13aXRoLWNvbnRyb2xzJywgU2xpZGVzaG93V2l0aENvbnRyb2xzKTtcblxuZXhwb3J0IGRlZmF1bHQgU2xpZGVzaG93V2l0aENvbnRyb2xzO1xuIiwiaW1wb3J0IEVsZW1lbnRCYXNlIGZyb20gJy4uLy4uL2Jhc2ljLWVsZW1lbnQtYmFzZS9zcmMvRWxlbWVudEJhc2UnO1xuaW1wb3J0IENvbnRlbnRJdGVtc01peGluIGZyb20gJy4uLy4uL2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL0NvbnRlbnRJdGVtc01peGluJztcbmltcG9ydCBEaXN0cmlidXRlZENoaWxkcmVuQ29udGVudE1peGluIGZyb20gJy4uLy4uL2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL0Rpc3RyaWJ1dGVkQ2hpbGRyZW5Db250ZW50TWl4aW4nO1xuaW1wb3J0IEZyYWN0aW9uYWxTZWxlY3Rpb25NaXhpbiBmcm9tICcuLi8uLi9iYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy9GcmFjdGlvbmFsU2VsZWN0aW9uTWl4aW4nO1xuaW1wb3J0IFNlbGVjdGlvbkFuaW1hdGlvbk1peGluIGZyb20gJy4uLy4uL2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL1NlbGVjdGlvbkFuaW1hdGlvbk1peGluJztcbmltcG9ydCBTZWxlY3Rpb25BcmlhQWN0aXZlTWl4aW4gZnJvbSAnLi4vLi4vYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvU2VsZWN0aW9uQXJpYUFjdGl2ZU1peGluJztcbmltcG9ydCBTaW5nbGVTZWxlY3Rpb25NaXhpbiBmcm9tICcuLi8uLi9iYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy9TaW5nbGVTZWxlY3Rpb25NaXhpbic7XG5pbXBvcnQgc3ltYm9scyBmcm9tICcuLi8uLi9iYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy9zeW1ib2xzJztcbmltcG9ydCBUaW1lclNlbGVjdGlvbk1peGluIGZyb20gJy4uLy4uL2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL1RpbWVyU2VsZWN0aW9uTWl4aW4nO1xuXG5cbmNvbnN0IGJhc2UgPSBFbGVtZW50QmFzZS5jb21wb3NlKFxuICBDb250ZW50SXRlbXNNaXhpbixcbiAgRGlzdHJpYnV0ZWRDaGlsZHJlbkNvbnRlbnRNaXhpbixcbiAgRnJhY3Rpb25hbFNlbGVjdGlvbk1peGluLFxuICBTZWxlY3Rpb25BbmltYXRpb25NaXhpbixcbiAgU2VsZWN0aW9uQXJpYUFjdGl2ZU1peGluLFxuICBTaW5nbGVTZWxlY3Rpb25NaXhpbixcbiAgVGltZXJTZWxlY3Rpb25NaXhpblxuKTtcblxuXG4vKipcbiAqIFNsaWRlc2hvdyB3aXRoIGFuaW1hdGVkIHRyYW5zaXRpb25zLlxuICpcbiAqIEJ5IGRlZmF1bHQgdGhlIHNsaWRlc2hvdyB3aWxsIGltbWVkaWF0ZWx5IGJlZ2luIHBsYXlpbmcgd2hlbiBpdCBpcyBjb25uZWN0ZWRcbiAqIHRvIHRoZSBkb2N1bWVudCwgYWR2YW5jZSBldmVyeSAzMDAwIG1zICgzIHNlY29uZHMpLCBhbmQgdXNlIGEgc2ltcGxlXG4gKiBjcm9zc2ZhZGUgZWZmZWN0LlxuICpcbiAqIFRoaXMgY29tcG9uZW50IGNhbiBiZSB1c2VkIG9uIGl0cyBvd24uIFRvIGluY29ycG9yYXRlIHNsaWRlc2hvdyBiZWhhdmlvciBpbnRvXG4gKiBhIGNvbXBvbmVudCBvZiB5b3VyIG93biwgYXBwbHkgdGhlXG4gKiBbVGltZXJTZWxlY3Rpb25NaXhpbl0oLi4vYmFzaWMtY29tcG9uZW50LW1peGlucy9kb2NzL1RpbWVyU2VsZWN0aW9uTWl4aW4ubWQpLlxuICpcbiAqIEBleHRlbmRzIEVsZW1lbnRCYXNlXG4gKiBAbWl4ZXMgQ29udGVudEl0ZW1zTWl4aW5cbiAqIEBtaXhlcyBEaXN0cmlidXRlZENoaWxkcmVuQ29udGVudE1peGluXG4gKiBAbWl4ZXMgRnJhY3Rpb25hbFNlbGVjdGlvbk1peGluXG4gKiBAbWl4ZXMgU2VsZWN0aW9uQW5pbWF0aW9uTWl4aW5cbiAqIEBtaXhlcyBTZWxlY3Rpb25BcmlhQWN0aXZlTWl4aW5cbiAqIEBtaXhlcyBTaW5nbGVTZWxlY3Rpb25NaXhpblxuICogQG1peGVzIFRpbWVyU2VsZWN0aW9uTWl4aW5cbiAqL1xuY2xhc3MgU2xpZGVzaG93IGV4dGVuZHMgYmFzZSB7XG5cbiAgZ2V0IFtzeW1ib2xzLmRlZmF1bHRzXSgpIHtcbiAgICBjb25zdCBkZWZhdWx0cyA9IHN1cGVyW3N5bWJvbHMuZGVmYXVsdHNdIHx8IHt9O1xuICAgIGRlZmF1bHRzLnBsYXlpbmcgPSB0cnVlO1xuICAgIGRlZmF1bHRzLnNlbGVjdGlvbkFuaW1hdGlvbkR1cmF0aW9uID0gNTAwO1xuICAgIGRlZmF1bHRzLnNlbGVjdGlvbkFuaW1hdGlvbkVmZmVjdCA9ICdjcm9zc2ZhZGUnO1xuICAgIGRlZmF1bHRzLnNlbGVjdGlvblJlcXVpcmVkID0gdHJ1ZTtcbiAgICBkZWZhdWx0cy5zZWxlY3Rpb25UaW1lckR1cmF0aW9uID0gMzAwMDtcbiAgICBkZWZhdWx0cy5zZWxlY3Rpb25XcmFwcyA9IHRydWU7XG4gICAgcmV0dXJuIGRlZmF1bHRzO1xuICB9XG5cbiAgZ2V0IFtzeW1ib2xzLnRlbXBsYXRlXSgpIHtcbiAgICByZXR1cm4gYFxuICAgICAgPHN0eWxlPlxuICAgICAgOmhvc3Qge1xuICAgICAgICBkaXNwbGF5OiAtd2Via2l0LWZsZXg7XG4gICAgICAgIGRpc3BsYXk6IGZsZXg7XG4gICAgICAgIG92ZXJmbG93OiBoaWRkZW47XG4gICAgICAgIHBvc2l0aW9uOiByZWxhdGl2ZTtcbiAgICAgIH1cblxuICAgICAgI2NvbnRhaW5lciA6OnNsb3R0ZWQoKikge1xuICAgICAgICBoZWlnaHQ6IDEwMCU7XG4gICAgICAgIG9iamVjdC1maXQ6IGNvbnRhaW47XG4gICAgICAgIHBvc2l0aW9uOiBhYnNvbHV0ZTtcbiAgICAgICAgd2lkdGg6IDEwMCU7XG4gICAgICAgIHdpbGwtY2hhbmdlOiB0cmFuc2Zvcm07XG4gICAgICB9XG4gICAgICA8L3N0eWxlPlxuXG4gICAgICA8ZGl2IGlkPVwiY29udGFpbmVyXCIgcm9sZT1cIm5vbmVcIj5cbiAgICAgICAgPHNsb3Q+PC9zbG90PlxuICAgICAgPC9kaXY+XG4gICAgYDtcbiAgfVxuXG59XG5cblxuY3VzdG9tRWxlbWVudHMuZGVmaW5lKCdiYXNpYy1zbGlkZXNob3cnLCBTbGlkZXNob3cpO1xuZXhwb3J0IGRlZmF1bHQgU2xpZGVzaG93O1xuIl19
+!function t(e,n,o){function r(a,c){if(!n[a]){if(!e[a]){var l="function"==typeof require&&require;if(!c&&l)return l(a,!0);if(i)return i(a,!0);var u=new Error("Cannot find module '"+a+"'");throw u.code="MODULE_NOT_FOUND",u}var s=n[a]={exports:{}};e[a][0].call(s.exports,function(t){var n=e[a][1][t];return r(n?n:t)},s,s.exports,t,e,n,o)}return n[a].exports}for(var i="function"==typeof require&&require,a=0;a\n :host {\n overflow: hidden;\n position: relative;\n }\n\n #container ::slotted(*) {\n height: 100%;\n object-fit: contain;\n position: absolute;\n width: 100%;\n will-change: transform;\n }\n \n\n \n \n
\n '}}]),e}(x);customElements.define("basic-animation-stage",S),n.default=S},{"../../basic-component-mixins/src/ContentItemsMixin":4,"../../basic-component-mixins/src/DistributedChildrenContentMixin":5,"../../basic-component-mixins/src/FractionalSelectionMixin":7,"../../basic-component-mixins/src/SelectionAnimationMixin":9,"../../basic-component-mixins/src/SelectionAriaActiveMixin":10,"../../basic-component-mixins/src/SingleSelectionMixin":13,"../../basic-component-mixins/src/symbols":18,"../../basic-element-base/src/ElementBase":20}],2:[function(t,e,n){"use strict";function o(t){return t&&t.__esModule?t:{default:t}}function r(t,e){if(!(t instanceof e))throw new TypeError("Cannot call a class as a function")}function i(t,e){if(!t)throw new ReferenceError("this hasn't been initialised - super() hasn't been called");return!e||"object"!=typeof e&&"function"!=typeof e?t:e}function a(t,e){if("function"!=typeof e&&null!==e)throw new TypeError("Super expression must either be null or a function, not "+typeof e);t.prototype=Object.create(e&&e.prototype,{constructor:{value:t,enumerable:!1,writable:!0,configurable:!0}}),e&&(Object.setPrototypeOf?Object.setPrototypeOf(t,e):t.__proto__=e)}function c(t){var e=y[t];if(!e){var n=/-([a-z])/g;e=t.replace(n,function(t){return t[1].toUpperCase()}),y[t]=e}return e}function l(t){if(t===HTMLElement||t===Object)return[];var e=Object.getPrototypeOf(t.prototype).constructor,n=l(e),o=Object.getOwnPropertyNames(t.prototype),r=o.filter(function(e){return"function"==typeof Object.getOwnPropertyDescriptor(t.prototype,e).set}),i=r.map(function(t){return u(t)}),a=i.filter(function(t){return n.indexOf(t)<0});return n.concat(a)}function u(t){var e=h[t];if(!e){var n=/([A-Z])/g;e=t.replace(n,"-$1").toLowerCase()}return e}Object.defineProperty(n,"__esModule",{value:!0});var s=function(){function t(t,e){for(var n=0;n2&&void 0!==arguments[2]?arguments[2]:[];return Object.getOwnPropertyNames(t).forEach(function(o){if(n.indexOf(o)<0){var r=Object.getOwnPropertyDescriptor(t,o);Object.defineProperty(e,o,r)}}),e}Object.defineProperty(n,"__esModule",{value:!0});var l=function(){function t(t,e){for(var n=0;n=n?n+c.helpers.damping(t-n):t},damping:function(t){var e=-1/(t+1)+1;return e},elementSelection:function(t){var e=t.selectedIndex;if(!(e<0)){var n=t.selectedFraction||0;return e+n}},selectionParts:function(t){var e=t<0?Math.ceil(t):Math.floor(t),n=t-e;return{index:e,fraction:n}},wrappedSelection:function(t,e){return(t%e+e)%e},wrappedSelectionParts:function(t,e,n){return n&&(t=c.helpers.wrappedSelection(t,e)),c.helpers.selectionParts(t)}}},{"./createSymbol":15}],8:[function(t,e,n){"use strict";function o(t){return t&&t.__esModule?t:{default:t}}function r(t,e){if(!(t instanceof e))throw new TypeError("Cannot call a class as a function")}function i(t,e){if(!t)throw new ReferenceError("this hasn't been initialised - super() hasn't been called");return!e||"object"!=typeof e&&"function"!=typeof e?t:e}function a(t,e){if("function"!=typeof e&&null!==e)throw new TypeError("Super expression must either be null or a function, not "+typeof e);t.prototype=Object.create(e&&e.prototype,{constructor:{value:t,enumerable:!1,writable:!0,configurable:!0}}),e&&(Object.setPrototypeOf?Object.setPrototypeOf(t,e):t.__proto__=e)}Object.defineProperty(n,"__esModule",{value:!0});var c=function(){function t(t,e){for(var n=0;n\n :host {\n display: -webkit-flex;\n display: flex;\n position: relative;\n }\n\n #buttons {\n bottom: 0;\n box-sizing: border-box;\n padding: 0.5em;\n position: absolute;\n text-align: center;\n width: 100%;\n z-index: 1;\n }\n\n button {\n background: transparent;\n border: none;\n fill: rgba(255, 255, 255, 0.5);\n padding: 0;\n transition: fill 0.5s;\n vertical-align: middle;\n }\n :host(:hover) button {\n fill: rgba(255, 255, 255, 0.7);\n }\n button:hover {\n fill: rgba(255, 255, 255, 0.85);\n }\n button:active {\n fill: white;\n }\n\n .icon {\n height: 30px;\n width: 30px;\n }\n #playButton .icon {\n height: 40px;\n width: 40px;\n }\n\n :host(.playing) .pausedControl {\n display: none;\n }\n :host(:not(.playing)) .playingControl {\n display: none;\n }\n\n #container {\n display: -webkit-flex;\n display: flex;\n -webkit-flex: 1;\n flex: 1;\n }\n\n #container ::slotted(*) {\n -webkit-flex: 1;\n flex: 1;\n }\n \n\n \n\n \n '+t+"\n
\n "}}]),n}(t);return e}},{"../../basic-component-mixins/src/safeAttributes":17,"../../basic-component-mixins/src/symbols":18}],9:[function(t,e,n){"use strict";function o(t){return t&&t.__esModule?t:{default:t}}function r(t,e){if(!(t instanceof e))throw new TypeError("Cannot call a class as a function")}function i(t,e){if(!t)throw new ReferenceError("this hasn't been initialised - super() hasn't been called");return!e||"object"!=typeof e&&"function"!=typeof e?t:e}function a(t,e){if("function"!=typeof e&&null!==e)throw new TypeError("Super expression must either be null or a function, not "+typeof e);t.prototype=Object.create(e&&e.prototype,{constructor:{value:t,enumerable:!1,writable:!0,configurable:!0}}),e&&(Object.setPrototypeOf?Object.setPrototypeOf(t,e):t.__proto__=e)}function c(t){var e=function(e){function n(){r(this,n);var t=i(this,(n.__proto__||Object.getPrototypeOf(n)).call(this));return"undefined"==typeof t.selectionAnimationDuration&&(t.selectionAnimationDuration=t[S.default.defaults].selectionAnimationDuration),"undefined"==typeof t.selectionAnimationEffect&&null==t.selectionAnimationKeyframes&&(t.selectionAnimationEffect=t[S.default.defaults].selectionAnimationEffect),t[S.default.dragging]=!1,t}return a(n,e),v(n,[{key:S.default.itemAdded,value:function(t){t.setAttribute("aria-hidden",!1)}},{key:S.default.itemsChanged,value:function(){g(n.prototype.__proto__||Object.getPrototypeOf(n.prototype),S.default.itemsChanged,this)&&g(n.prototype.__proto__||Object.getPrototypeOf(n.prototype),S.default.itemsChanged,this).call(this),d(this),p(this)}},{key:"resetAnimations",value:function(){d(this)}},{key:S.default.defaults,get:function(){var t=g(n.prototype.__proto__||Object.getPrototypeOf(n.prototype),S.default.defaults,this)||{};return t.selectionAnimationDuration=250,t.selectionAnimationEffect="slide",t}},{key:S.default.dragging,get:function(){return this[k]},set:function(e){var o=this[S.default.dragging];this[k]=e,S.default.dragging in t.prototype&&m(n.prototype.__proto__||Object.getPrototypeOf(n.prototype),S.default.dragging,e,this),e&&!o&&(this[R]=!0)}},{key:"selectedFraction",get:function(){return g(n.prototype.__proto__||Object.getPrototypeOf(n.prototype),"selectedFraction",this)||0},set:function(e){"selectedFraction"in t.prototype&&m(n.prototype.__proto__||Object.getPrototypeOf(n.prototype),"selectedFraction",e,this),p(this,this.selectedIndex,e)}},{key:"selectedIndex",get:function(){return g(n.prototype.__proto__||Object.getPrototypeOf(n.prototype),"selectedIndex",this)},set:function(e){"selectedIndex"in t.prototype&&m(n.prototype.__proto__||Object.getPrototypeOf(n.prototype),"selectedIndex",e,this),p(this,e,0)}},{key:"selectionAnimationDuration",get:function(){return this[T]},set:function(e){this[T]=e,"selectionAnimationDuration"in t.prototype&&m(n.prototype.__proto__||Object.getPrototypeOf(n.prototype),"selectionAnimationDuration",e,this)}},{key:"selectionAnimationEffect",get:function(){return this[I]},set:function(e){this[I]=e,"selectionAnimationEffect"in t.prototype&&m(n.prototype.__proto__||Object.getPrototypeOf(n.prototype),"selectionAnimationEffect",e,this),this.selectionAnimationKeyframes=c.standardEffectKeyframes[e]}},{key:"selectionAnimationKeyframes",get:function(){return this[D]},set:function(e){this[D]=e,"selectionAnimationKeyframes"in t.prototype&&m(n.prototype.__proto__||Object.getPrototypeOf(n.prototype),"selectionAnimationKeyframes",e,this),d(this),p(this)}},{key:"selectionWraps",get:function(){return g(n.prototype.__proto__||Object.getPrototypeOf(n.prototype),"selectionWraps",this)},set:function(e){"selectionWraps"in t.prototype&&m(n.prototype.__proto__||Object.getPrototypeOf(n.prototype),"selectionWraps",e,this),d(this),p(this)}}]),n}(t);return e}function l(t,e,n){d(t);var o=t.items,r=t.selectionAnimationKeyframes;t[M]=!0;var i=c.helpers.effectTimingsForSelectionAnimation(t,e,n),a=o.length,l=t.selectionWraps,u=P.default.helpers.selectionParts(n,a,l).index,p=_(a,l,e,n),f=p>=0,h=u+(f?1:-1);l?h=P.default.helpers.wrappedSelection(h,a):s(t,h)||(h=null);var v=void 0;i.forEach(function(e,n){var i=o[n];if(e){b(i,!0);var a=i.animate(r,e);t[C][n]=a,n===h&&(h=null),0!==e.endDelay&&(v={animation:a,index:n,timing:e,forward:f})}else b(i,!1)}),null!=v?(v.nextUpIndex=h,v.animation.onfinish=function(e){return y(t,v)},t[E]=v.animation):t[M]=!1}function u(t,e){if(null==t[C])return null;var n=t[C][e];if(!n){var o=t.items[e];n=o.animate(t.selectionAnimationKeyframes,{duration:t.selectionAnimationDuration,fill:"both"}),n.pause(),t[C][e]=n}return n}function s(t,e){return e>=0&&t.items&&e1&&void 0!==arguments[1]?arguments[1]:t.selectedIndex,n=arguments.length>2&&void 0!==arguments[2]?arguments[2]:t.selectedFraction,o=t.items?t.items.length:0;if(0!==o&&!(e<0)){var r=e+n;r=t.selectionWraps?P.default.helpers.wrappedSelection(r,o):P.default.helpers.dampedSelection(r,o);var i=t[A];if(t[S.default.dragging]||null==i||i===r){if(0===n&&t[M])return;f(t,r)}else l(t,i,r);t[A]=r}}function f(t,e){t[R]&&(d(t),t[R]=!1);var n=c.helpers.animationFractionsForSelection(t,e);n.map(function(e,n){var o=t.items[n];null!=e?(b(o,!0),h(t,n,e)):b(o,!1)})}function d(t){var e=t[C];e&&e.forEach(function(t,n){t&&(t.cancel(),e[n]=null)});var n=t.items?t.items.length:0;e&&e.length===n||(t[C]=new Array(n))}function y(t,e){var n=e.nextUpIndex;if(null!=n){t[C][n]&&(t[C][n].cancel(),t[C][n]=null);var o=e.forward?0:1;h(t,n,o),b(t.items[n],!0)}t[E].onfinish=null,t[M]=!1}function h(t,e,n){var o=u(t,e);if(o){var r=t.selectionAnimationDuration;r&&(o.currentTime=n*r)}}function b(t,e){t.style.visibility=e?"visible":"hidden"}function _(t,e,n,o){var r=o-n;if(e&&t>1){var i=t-Math.abs(r);i<=1&&(r=r<0?i:-i)}return r}Object.defineProperty(n,"__esModule",{value:!0});var v=function(){function t(t,e){for(var n=0;n=0&&a<=1?a:null})}},effectTimingsForSelectionAnimation:function(t,e,n){var o=t.items;if(o){var r=o.length,i=t.selectionWraps,a=P.default.helpers.wrappedSelectionParts(n,r,i).index,c=_(r,i,e,n),l=c>=0?"normal":"reverse",u="both",s=t.selectionAnimationDuration,p=0!==c?2*s/Math.ceil(Math.abs(c)):0,f=o.map(function(t,e){var o=_(r,i,e,n),s=c-o;if(c<0&&(s=-s),Math.ceil(s)>=0&&s<=Math.abs(c)){var f=p*(s-1)/2,d=e===a?-p/2:0;return{duration:p,direction:l,fill:u,delay:f,endDelay:d}}return null});return f}}},c.standardEffectKeyframes={crossfade:[{opacity:0},{opacity:1},{opacity:0}],reveal:[{transform:"translateX(0%)",zIndex:0},{transform:"translateX(0%)",zIndex:1},{transform:"translateX(-100%)",zIndex:2}],revealWithFade:[{transform:"translateX(0%) scale(0.75)",opacity:0,zIndex:0},{transform:"translateX(0%) scale(1.0)",opacity:1,zIndex:1},{transform:"translateX(-100%) scale(1.0)",opacity:1,zIndex:2}],showAdjacent:[{transform:"translateX(78%) scale(0.7)",zIndex:0},{transform:"translateX(0%) scale(0.82)",
+zIndex:1},{transform:"translateX(-78%) scale(0.7)",zIndex:0}],slide:[{transform:"translateX(100%)"},{transform:"translateX(-100%)"}],slideWithGap:[{transform:"translateX(110%)"},{transform:"translateX(-110%)"}]}},{"./FractionalSelectionMixin":7,"./createSymbol":15,"./symbols":18}],10:[function(t,e,n){"use strict";function o(t){return t&&t.__esModule?t:{default:t}}function r(t,e){if(!(t instanceof e))throw new TypeError("Cannot call a class as a function")}function i(t,e){if(!t)throw new ReferenceError("this hasn't been initialised - super() hasn't been called");return!e||"object"!=typeof e&&"function"!=typeof e?t:e}function a(t,e){if("function"!=typeof e&&null!==e)throw new TypeError("Super expression must either be null or a function, not "+typeof e);t.prototype=Object.create(e&&e.prototype,{constructor:{value:t,enumerable:!1,writable:!0,configurable:!0}}),e&&(Object.setPrototypeOf?Object.setPrototypeOf(t,e):t.__proto__=e)}Object.defineProperty(n,"__esModule",{value:!0});var c=function(){function t(t,e){for(var n=0;n0;)e.content.appendChild(n.childNodes[0]);return e}function l(t,e){window.WebComponents.ShadowCSS.shimStyling(t.content,e)}Object.defineProperty(n,"__esModule",{value:!0});var u=t("../src/symbols"),s=o(u);n.default=function(t){var e=function(t){function e(){r(this,e);var t=i(this,(e.__proto__||Object.getPrototypeOf(e)).call(this)),n=t[s.default.template];if(n){"string"==typeof n&&(n=c(n)),window.ShadowDOMPolyfill&&l(n,t.localName);var o=t.attachShadow({mode:"open"}),a=document.importNode(n.content,!0);o.appendChild(a)}return t}return a(e,t),e}(t);return e}},{"../src/symbols":18}],13:[function(t,e,n){"use strict";function o(t){return t&&t.__esModule?t:{default:t}}function r(t,e){if(!(t instanceof e))throw new TypeError("Cannot call a class as a function")}function i(t,e){if(!t)throw new ReferenceError("this hasn't been initialised - super() hasn't been called");return!e||"object"!=typeof e&&"function"!=typeof e?t:e}function a(t,e){if("function"!=typeof e&&null!==e)throw new TypeError("Super expression must either be null or a function, not "+typeof e);t.prototype=Object.create(e&&e.prototype,{constructor:{value:t,enumerable:!1,writable:!0,configurable:!0}}),e&&(Object.setPrototypeOf?Object.setPrototypeOf(t,e):t.__proto__=e)}function c(t,e){var n=t.items.length,o=t.selectionWraps?(e%n+n)%n:Math.max(Math.min(e,n-1),0),r=t.selectedIndex;return r!==o&&(t.selectedIndex=o,!0)}function l(t){var e=t.items,n=e?e.length:0,o=t.selectedItem;if(o)if(0===n)t.selectedItem=null;else{var r=Array.prototype.indexOf.call(e,o),i=t.selectedIndex;if(r<0){var a=Math.min(i,n-1);t.selectedItem=e[a]}else r!==i&&(t.selectedIndex=r)}else t.selectionRequired&&(t.selectedIndex=0)}function u(t){var e=void 0,n=void 0,o=t.items;if(null!=o&&0!==o.length||(e=!1,n=!1),t.selectionWraps)e=!0,n=!0;else{var r=t.selectedIndex;r<0&&o.length>0?(e=!0,n=!0):(n=r>0,e=r0;a&&e>=0&&e=0?i[e]:null,this[j]=r}else r=this[j];if("selectedIndex"in t.prototype&&f(n.prototype.__proto__||Object.getPrototypeOf(n.prototype),"selectedIndex",e,this),e!==o){this[w]=e;var c=new CustomEvent("selected-index-changed",{detail:{selectedIndex:e,value:e}});this.dispatchEvent(c)}this[P]!==r&&(this.selectedItem=r)}},{key:"selectedItem",get:function(){return this[j]||null},set:function(e){var o=this[P],r=void 0;if(e!==this[j]){var i=this.items,a=i&&i.length>0;r=a?Array.prototype.indexOf.call(i,e):-1,this[O]=r,r<0&&(e=null),this[j]=e}else r=this[O];if("selectedItem"in t.prototype&&f(n.prototype.__proto__||Object.getPrototypeOf(n.prototype),"selectedItem",e,this),e!==o){this[P]=e,o&&this[b.default.itemSelected](o,!1),e&&this[b.default.itemSelected](e,!0),u(this);var c=new CustomEvent("selected-item-changed",{detail:{selectedItem:e,value:e}});this.dispatchEvent(c)}this[w]!==r&&(this.selectedIndex=r)}},{key:"selectionRequired",get:function(){return this[m]},set:function(e){this[m]=e,"selectionRequired"in t.prototype&&f(n.prototype.__proto__||Object.getPrototypeOf(n.prototype),"selectionRequired",e,this),l(this)}},{key:"selectionWraps",get:function(){return this[g]},set:function(e){this[g]="true"===String(e),"selectionWraps"in t.prototype&&f(n.prototype.__proto__||Object.getPrototypeOf(n.prototype),"selectionWraps",e,this),u(this)}}]),n}(t);return e}},{"./createSymbol":15,"./symbols":18}],14:[function(t,e,n){"use strict";function o(t){return t&&t.__esModule?t:{default:t}}function r(t,e){if(!(t instanceof e))throw new TypeError("Cannot call a class as a function")}function i(t,e){if(!t)throw new ReferenceError("this hasn't been initialised - super() hasn't been called");return!e||"object"!=typeof e&&"function"!=typeof e?t:e}function a(t,e){if("function"!=typeof e&&null!==e)throw new TypeError("Super expression must either be null or a function, not "+typeof e);t.prototype=Object.create(e&&e.prototype,{constructor:{value:t,enumerable:!1,writable:!0,configurable:!0}}),e&&(Object.setPrototypeOf?Object.setPrototypeOf(t,e):t.__proto__=e)}function c(t){t[g]&&(clearTimeout(t[g]),t[g]=null)}function l(t){c(t),t.playing&&t.items&&t.items.length>0&&u(t)}function u(t){c(t),t[g]=setTimeout(function(){s(t)},t.selectionTimerDuration)}function s(t){var e=t.items;e&&e.length>0&&(null==t.selectedIndex||t.selectedIndex===e.length-1?t.selectFirst():t.selectNext())}Object.defineProperty(n,"__esModule",{value:!0});var p=function(){function t(t,e){for(var n=0;n0;){var t=i.shift();t()}}Object.defineProperty(n,"__esModule",{value:!0}),n.default=o;var i=[],a=document.createTextNode(""),c=0,l=new MutationObserver(r);l.observe(a,{characterData:!0})},{}],17:[function(t,e,n){"use strict";function o(t){return t&&t.__esModule?t:{default:t}}function r(t,e,n){if(null===n||"undefined"==typeof n)t.removeAttribute(e);else{var o=String(n);t.getAttribute(e)!==o&&t.setAttribute(e,n)}}Object.defineProperty(n,"__esModule",{value:!0});var i=t("./createSymbol"),a=o(i),c=t("./toggleClass"),l=o(c),u=(0,a.default)("safeToSetAttributes"),s=(0,a.default)("pendingAttributes"),p=(0,a.default)("pendingClasses");n.default={connected:function(t){if(t[u]=!0,t[s]){for(var e in t[s]){var n=t[s][e];r(t,e,n)}t[s]=null}if(t[p]){for(var o in t[p]){var i=t[p][o];(0,l.default)(t,o,i)}t[p]=null}},setAttribute:function(t,e,n){t[u]?r(t,e,n):(t[s]||(t[s]={}),t[s][e]=n)},toggleClass:function(t,e,n){t[u]?(0,l.default)(t,e,n):(t[p]||(t[p]={}),t[p][e]=n)}}},{"./createSymbol":15,"./toggleClass":19}],18:[function(t,e,n){"use strict";function o(t){return t&&t.__esModule?t:{default:t}}Object.defineProperty(n,"__esModule",{value:!0});var r=t("./createSymbol"),i=o(r),a={defaults:(0,i.default)("defaults"),dragging:(0,i.default)("dragging"),goDown:(0,i.default)("goDown"),goEnd:(0,i.default)("goEnd"),goLeft:(0,i.default)("goLeft"),goRight:(0,i.default)("goRight"),goStart:(0,i.default)("goStart"),goUp:(0,i.default)("goUp"),itemAdded:(0,i.default)("itemAdded"),itemsChanged:(0,i.default)("itemsChanged"),itemSelected:(0,i.default)("itemSelected"),keydown:(0,i.default)("keydown"),template:(0,i.default)("template")};n.default=a},{"./createSymbol":15}],19:[function(t,e,n){"use strict";function o(t,e,n){var o=t.classList,r="undefined"==typeof n?!o.contains(e):n;return r?o.add(e):o.remove(e),r}Object.defineProperty(n,"__esModule",{value:!0}),n.default=o},{}],20:[function(t,e,n){"use strict";function o(t){return t&&t.__esModule?t:{default:t}}function r(t,e){if(!(t instanceof e))throw new TypeError("Cannot call a class as a function")}function i(t,e){if(!t)throw new ReferenceError("this hasn't been initialised - super() hasn't been called");return!e||"object"!=typeof e&&"function"!=typeof e?t:e}function a(t,e){if("function"!=typeof e&&null!==e)throw new TypeError("Super expression must either be null or a function, not "+typeof e);t.prototype=Object.create(e&&e.prototype,{constructor:{value:t,enumerable:!1,writable:!0,configurable:!0}}),e&&(Object.setPrototypeOf?Object.setPrototypeOf(t,e):t.__proto__=e)}Object.defineProperty(n,"__esModule",{value:!0});var c=t("../../basic-component-mixins/src/AttributeMarshallingMixin"),l=o(c),u=t("../../basic-component-mixins/src/ComposableMixin"),s=o(u),p=t("../../basic-component-mixins/src/DistributedChildrenMixin"),f=o(p),d=t("../../basic-component-mixins/src/ShadowElementReferencesMixin"),y=o(d),h=t("../../basic-component-mixins/src/ShadowTemplateMixin"),b=o(h),_=function(t){function e(){return r(this,e),i(this,(e.__proto__||Object.getPrototypeOf(e)).apply(this,arguments))}return a(e,t),e}((0,s.default)(HTMLElement).compose(b.default,y.default,l.default,f.default));n.default=_},{"../../basic-component-mixins/src/AttributeMarshallingMixin":2,"../../basic-component-mixins/src/ComposableMixin":3,"../../basic-component-mixins/src/DistributedChildrenMixin":6,"../../basic-component-mixins/src/ShadowElementReferencesMixin":11,"../../basic-component-mixins/src/ShadowTemplateMixin":12}],21:[function(t,e,n){"use strict";function o(t){return t&&t.__esModule?t:{default:t}}var r=t("./src/SlideshowWithControls"),i=o(r);window.Basic=window.Basic||{},window.Basic.SlideshowWithControls=i.default},{"./src/SlideshowWithControls":22}],22:[function(t,e,n){"use strict";function o(t){return t&&t.__esModule?t:{default:t}}function r(t,e){if(!(t instanceof e))throw new TypeError("Cannot call a class as a function")}function i(t,e){if(!t)throw new ReferenceError("this hasn't been initialised - super() hasn't been called");return!e||"object"!=typeof e&&"function"!=typeof e?t:e}function a(t,e){if("function"!=typeof e&&null!==e)throw new TypeError("Super expression must either be null or a function, not "+typeof e);t.prototype=Object.create(e&&e.prototype,{constructor:{value:t,enumerable:!1,writable:!0,configurable:!0}}),e&&(Object.setPrototypeOf?Object.setPrototypeOf(t,e):t.__proto__=e)}Object.defineProperty(n,"__esModule",{value:!0});var c=t("../../basic-slideshow/src/Slideshow"),l=o(c),u=t("../../basic-component-mixins/src/PlayControlsMixin"),s=o(u),p=function(t){function e(){return r(this,e),i(this,(e.__proto__||Object.getPrototypeOf(e)).apply(this,arguments))}return a(e,t),e}((0,s.default)(l.default));customElements.define("basic-slideshow-with-controls",p),n.default=p},{"../../basic-component-mixins/src/PlayControlsMixin":8,"../../basic-slideshow/src/Slideshow":23}],23:[function(t,e,n){"use strict";function o(t){return t&&t.__esModule?t:{default:t}}function r(t,e){if(!(t instanceof e))throw new TypeError("Cannot call a class as a function")}function i(t,e){if(!t)throw new ReferenceError("this hasn't been initialised - super() hasn't been called");return!e||"object"!=typeof e&&"function"!=typeof e?t:e}function a(t,e){if("function"!=typeof e&&null!==e)throw new TypeError("Super expression must either be null or a function, not "+typeof e);t.prototype=Object.create(e&&e.prototype,{constructor:{value:t,enumerable:!1,writable:!0,configurable:!0}}),e&&(Object.setPrototypeOf?Object.setPrototypeOf(t,e):t.__proto__=e)}Object.defineProperty(n,"__esModule",{value:!0});var c=function(){function t(t,e){for(var n=0;n\n :host {\n overflow: hidden;\n position: relative;\n }\n\n #container ::slotted(*) {\n height: 100%;\n object-fit: contain;\n position: absolute;\n width: 100%;\n will-change: transform;\n }\n \n\n \n \n
\n `;\n }\n\n}\n\n\ncustomElements.define('basic-animation-stage', AnimationStage);\nexport default AnimationStage;\n","import safeAttributes from './safeAttributes';\n\n\n// Memoized maps of attribute to property names and vice versa.\nconst attributeToPropertyNames = {};\nconst propertyNamesToAttributes = {};\n\n\n/* Exported function extends a base class with AttributeMarshalling. */\nexport default (base) => {\n\n /**\n * Mixin which marshalls attributes to properties and vice versa.\n *\n * If your component exposes a setter for a property, it's generally a good\n * idea to let devs using your component be able to set that property in HTML\n * via an element attribute. You can code that yourself by writing an\n * `attributeChangedCallback`, or you can use this mixin to get a degree of\n * automatic support.\n *\n * This mixin implements an `attributeChangedCallback` that will attempt to\n * convert a change in an element attribute into a call to the corresponding\n * property setter. Attributes typically follow hyphenated names (\"foo-bar\"),\n * whereas properties typically use camelCase names (\"fooBar\"). This mixin\n * respects that convention, automatically mapping the hyphenated attribute\n * name to the corresponding camelCase property name.\n *\n * Example: You define a component using this mixin:\n *\n * class MyElement extends AttributeMarshallingMixin(HTMLElement) {\n * get fooBar() { return this._fooBar; }\n * set fooBar(value) { this._fooBar = value; }\n * }\n * customElements.define('my-element', MyElement);\n *\n * If someone then instantiates your component in HTML:\n *\n * \n *\n * Then, after the element has been upgraded, the `fooBar` setter will\n * automatically be invoked with the initial value \"Hello\".\n *\n * For the time being, this mixin only supports string-valued properties.\n * If you'd like to convert string attributes to other types (numbers,\n * booleans), you need to implement `attributeChangedCallback` yourself.\n */\n class AttributeMarshalling extends base {\n\n /*\n * Handle a change to the attribute with the given name.\n */\n attributeChangedCallback(attributeName, oldValue, newValue) {\n if (super.attributeChangedCallback) { super.attributeChangedCallback(); }\n const propertyName = attributeToPropertyName(attributeName);\n // If the attribute name corresponds to a property name, set the property.\n // Ignore standard HTMLElement properties handled by the DOM.\n if (propertyName in this && !(propertyName in HTMLElement.prototype)) {\n this[propertyName] = newValue;\n }\n }\n\n connectedCallback() {\n if (super.connectedCallback) { super.connectedCallback(); }\n safeAttributes.connected(this);\n }\n\n static get observedAttributes() {\n return attributesForClass(this);\n }\n\n /**\n * Set/unset the attribute with the indicated name.\n *\n * This method exists primarily to handle the case where an element wants to\n * set a default property value that should be reflected as an attribute. An\n * important limitation of custom element consturctors is that they cannot\n * set attributes. A call to `reflectAttribute` during the constructor will\n * be deferred until the element is connected to the document.\n *\n * @param {string} attribute - The name of the *attribute* (not property) to set.\n * @param {object} value - The value to set. If null, the attribute will be removed.\n */\n reflectAttribute(attribute, value) {\n return safeAttributes.setAttribute(this, attribute, value);\n }\n\n /**\n * Set/unset the class with the indicated name.\n *\n * This method exists primarily to handle the case where an element wants to\n * set a default property value that should be reflected as as class. An\n * important limitation of custom element consturctors is that they cannot\n * set attributes, including the `class` attribute. A call to\n * `reflectClass` during the constructor will be deferred until the element\n * is connected to the document.\n *\n * @param {string} className - The name of the class to set.\n * @param {object} value - True to set the class, false to remove it.\n */\n reflectClass(className, value) {\n return safeAttributes.toggleClass(this, className, value);\n }\n\n }\n\n return AttributeMarshalling;\n};\n\n\n// Convert hyphenated foo-bar attribute name to camel case fooBar property name.\nfunction attributeToPropertyName(attributeName) {\n let propertyName = attributeToPropertyNames[attributeName];\n if (!propertyName) {\n // Convert and memoize.\n const hypenRegEx = /-([a-z])/g;\n propertyName = attributeName.replace(hypenRegEx,\n match => match[1].toUpperCase());\n attributeToPropertyNames[attributeName] = propertyName;\n }\n return propertyName;\n}\n\nfunction attributesForClass(classFn) {\n\n // We treat the element base classes as if they have no attributes, since we\n // don't want to receive attributeChangedCallback for them.\n if (classFn === HTMLElement || classFn === Object) {\n return [];\n }\n\n // Get attributes for parent class.\n const baseClass = Object.getPrototypeOf(classFn.prototype).constructor;\n const baseAttributes = attributesForClass(baseClass);\n\n // Get attributes for this class.\n const propertyNames = Object.getOwnPropertyNames(classFn.prototype);\n const setterNames = propertyNames.filter(propertyName =>\n typeof Object.getOwnPropertyDescriptor(\n classFn.prototype, propertyName).set === 'function');\n const attributes = setterNames.map(setterName =>\n propertyNameToAttribute(setterName));\n\n // Merge.\n const diff = attributes.filter(attribute =>\n baseAttributes.indexOf(attribute) < 0);\n return baseAttributes.concat(diff);\n}\n\n// Convert a camel case fooBar property name to a hyphenated foo-bar attribute.\nfunction propertyNameToAttribute(propertyName) {\n let attribute = propertyNamesToAttributes[propertyName];\n if (!attribute) {\n // Convert and memoize.\n const uppercaseRegEx = /([A-Z])/g;\n attribute = propertyName.replace(uppercaseRegEx, '-$1').toLowerCase();\n }\n return attribute;\n}\n","/* Exported function extends a base class with Composable. */\nexport default (base) => {\n\n /**\n * Mixin to make a class more easily composable with other mixins.\n *\n * This mixin contributes a `compose` method that applies a set of mixin\n * functions and returns the resulting new class. This sugar can make the\n * application of many mixins at once easier to read.\n */\n class Composable extends base {\n\n /**\n * Apply a set of mixin functions or mixin objects to the present class and\n * return the new class.\n *\n * Instead of writing:\n *\n * let MyClass = Mixin1(Mixin2(Mixin3(Mixin4(Mixin5(BaseClass)))));\n *\n * You can write:\n *\n * let MyClass = ComposableMixin(BaseClass).compose(\n * Mixin1,\n * Mixin2,\n * Mixin3,\n * Mixin4,\n * Mixin5\n * );\n *\n * This function can also take mixin objects. A mixin object is just a\n * shorthand for a mixin function that creates a new subclass with the given\n * members. The mixin object's members are *not* copied directly onto the\n * prototype of the base class, as with traditional mixins.\n *\n * In addition to providing syntactic sugar, this mixin can be used to\n * define a class in ES5, which lacks ES6's `class` keyword.\n *\n * @param {...mixins} mixins - A set of mixin functions or objects to apply.\n */\n static compose(...mixins) {\n // We create a new subclass for each mixin in turn. The result becomes\n // the base class extended by any subsequent mixins. It turns out that\n // we can use Array.reduce() to concisely express this, using the current\n // object as the seed for reduce().\n return mixins.reduce(composeClass, this);\n }\n\n }\n\n return Composable;\n};\n\n\n// Properties defined by Object that we don't want to mixin.\nconst NON_MIXABLE_OBJECT_PROPERTIES = [\n 'constructor'\n];\n\n/*\n * Apply the mixin to the given base class to return a new class.\n * The mixin can either be a function that returns the modified class, or a\n * plain object whose members will be copied to the new class' prototype.\n */\nfunction composeClass(base, mixin) {\n if (typeof mixin === 'function') {\n // Mixin function\n return mixin(base);\n } else {\n // Mixin object\n class Subclass extends base {}\n copyOwnProperties(mixin, Subclass.prototype, NON_MIXABLE_OBJECT_PROPERTIES);\n return Subclass;\n }\n}\n\n\n/*\n * Copy the given properties/methods to the target.\n * Return the updated target.\n */\nfunction copyOwnProperties(source, target, ignorePropertyNames = []) {\n Object.getOwnPropertyNames(source).forEach(name => {\n if (ignorePropertyNames.indexOf(name) < 0) {\n const descriptor = Object.getOwnPropertyDescriptor(source, name);\n Object.defineProperty(target, name, descriptor);\n }\n });\n return target;\n}\n","import createSymbol from './createSymbol';\nimport toggleClass from './toggleClass';\nimport symbols from './symbols';\n\n\n// Symbols for private data members on an element.\nconst itemsSymbol = createSymbol('items');\nconst itemInitializedSymbol = createSymbol('itemInitialized');\n\n\n/* Exported function extends a base class with ContentItems. */\nexport default (base) => {\n\n /**\n * Mixin which maps content semantics (elements) to list item semantics.\n *\n * Items differ from element contents in several ways:\n *\n * * They are often referenced via index.\n * * They may have a selection state.\n * * It's common to do work to initialize the appearance or state of a new\n * item.\n * * Auxiliary invisible child elements are filtered out and not counted as\n * items. Auxiliary elements include link, script, style, and template\n * elements. This filtering ensures that those auxiliary elements can be\n * used in markup inside of a list without being treated as list items.\n *\n * This mixin expects a component to provide a `content` property returning a\n * raw set of elements. You can provide that yourself, or use\n * [DistributedChildrenContentMixin](DistributedChildrenContentMixin.md).\n *\n * The most commonly referenced property defined by this mixin is the `items`\n * property. To avoid having to do work each time that property is requested,\n * this mixin supports an optimized mode. If you invoke the `contentChanged`\n * method when the set of items changes, the mixin concludes that you'll take\n * care of notifying it of future changes, and turns on the optimization. With\n * that on, the mixin saves a reference to the computed set of items, and will\n * return that immediately on subsequent calls to the `items` property. If you\n * use this mixin in conjunction with\n * [DistributedChildrenContentMixin](DistributedChildrenContentMixin.md), the\n * `contentChanged` method will be invoked for you when the element's children\n * change, turning on the optimization automatically.\n */\n class ContentItems extends base {\n\n contentChanged() {\n if (super.contentChanged) { super.contentChanged(); }\n\n // Since we got the contentChanged call, we'll assume we'll be notified if\n // the set of items changes later. We turn on memoization of the items\n // property by setting our internal property to null (instead of\n // undefined).\n this[itemsSymbol] = null;\n\n this[symbols.itemsChanged]();\n }\n\n /**\n * This method is invoked whenever a new item is added to the list.\n *\n * The default implementation of this method does nothing. You can override\n * this to perform per-item initialization.\n *\n * @param {HTMLElement} item - The item that was added.\n */\n [symbols.itemAdded](item) {\n if (super[symbols.itemAdded]) { super[symbols.itemAdded](item); }\n }\n\n /**\n * The selection state for a single item has changed.\n *\n * Invoke this method to signal that the selected state of the indicated item\n * has changed. By default, this applies a `selected` CSS class if the item\n * is selected, and removed it if not selected.\n *\n * @param {HTMLElement} item - The item whose selection state has changed.\n * @param {boolean} selected - True if the item is selected, false if not.\n */\n [symbols.itemSelected](item, selected) {\n if (super[symbols.itemSelected]) { super[symbols.itemSelected](item, selected); }\n toggleClass(item, 'selected', selected);\n }\n\n /**\n * The current set of items in the list. See the top-level documentation for\n * mixin for a description of how items differ from plain content.\n *\n * @type {HTMLElement[]}\n */\n get items() {\n let items;\n if (this[itemsSymbol] == null) {\n items = filterAuxiliaryElements(this.content);\n // Note: test for *equality* with null; don't treat undefined as a match.\n if (this[itemsSymbol] === null) {\n // Memoize the set of items.\n this[itemsSymbol] = items;\n }\n } else {\n // Return the memoized items.\n items = this[itemsSymbol];\n }\n return items;\n }\n\n /**\n * This method is invoked when the underlying contents change. It is also\n * invoked on component initialization – since the items have \"changed\" from\n * being nothing.\n */\n [symbols.itemsChanged]() {\n if (super[symbols.itemsChanged]) { super[symbols.itemsChanged](); }\n\n // Perform per-item initialization.\n Array.prototype.forEach.call(this.items, item => {\n if (!item[itemInitializedSymbol]) {\n this[symbols.itemAdded](item);\n item[itemInitializedSymbol] = true;\n }\n });\n\n this.dispatchEvent(new CustomEvent('items-changed'));\n }\n\n /**\n * Fires when the items in the list change.\n *\n * @memberof ContentItems\n * @event items-changed\n */\n }\n\n return ContentItems;\n};\n\n\n// Return the given elements, filtering out auxiliary elements that aren't\n// typically visible. Items which are not elements are returned as is.\nfunction filterAuxiliaryElements(items) {\n const auxiliaryTags = [\n 'link',\n 'script',\n 'style',\n 'template'\n ];\n return [].filter.call(items, function(item) {\n return !item.localName || auxiliaryTags.indexOf(item.localName) < 0;\n });\n}\n","import microtask from './microtask';\n\n\n/* Exported function extends a base class with DistributedChildrenContent. */\nexport default (base) => {\n\n /**\n * Mixin which defines a component's content as its children, expanding any\n * nodes distributed to the component's slots.\n *\n * This also provides notification of changes to a component's content. It\n * will invoke a `contentChanged` method when the component is first\n * instantiated, and whenever its distributed children change. This is an\n * easy way to satisfy the Gold Standard checklist item for monitoring\n * [Content Changes](https://github.com/webcomponents/gold-standard/wiki/Content-Changes).\n *\n * Example:\n *\n * ```\n * let base = DistributedChildrenContentMixin(DistributedChildrenMixin(HTMLElement));\n * class CountingElement extends base {\n *\n * constructor() {\n * super();\n * let root = this.attachShadow({ mode: 'open' });\n * root.innerHTML = ` `;\n * }\n *\n * contentChanged() {\n * // Count the component's children, both initially and when changed.\n * this.count = this.distributedChildren.length;\n * }\n *\n * }\n * ```\n *\n * Note that content change detection depends upon the element having at least\n * one `slot` element in its shadow subtree.\n *\n * This mixin is intended for use with the\n * [DistributedChildrenMixin](DistributedChildrenMixin.md). See that mixin for\n * a discussion of how that works. This DistributedChildrenContentMixin\n * provides an easy way of defining the \"content\" of a component as the\n * component's distributed children. That in turn lets mixins like\n * [ContentItemsMixin](ContentItemsMixin.md) manipulate the children as list\n * items.\n */\n class DistributedChildrenContent extends base {\n\n constructor() {\n super();\n\n if (this.shadowRoot) {\n // Listen to changes on all slots.\n const slots = this.shadowRoot.querySelectorAll('slot');\n slots.forEach(slot => slot.addEventListener('slotchange', event => {\n this.contentChanged();\n }));\n }\n\n // Make an initial call to contentChanged() so that the component can do\n // initialization that it normally does when content changes.\n //\n // This will invoke contentChanged() handlers in other mixins. In order\n // that those mixins have a chance to complete their own initialization,\n // we add the contentChanged() call to the microtask queue.\n microtask(() => this.contentChanged());\n }\n\n /**\n * Invoked when the contents of the component (including distributed\n * children) have changed.\n *\n * This method is also invoked when a component is first instantiated; the\n * contents have essentially \"changed\" from being nothing. This allows the\n * component to perform initial processing of its children.\n */\n contentChanged() {\n if (super.contentChanged) { super.contentChanged(); }\n const event = new CustomEvent('content-changed');\n this.dispatchEvent(event);\n }\n\n /**\n * The content of this component, defined to be the flattened array of\n * children distributed to the component.\n *\n * @type {HTMLElement[]}\n */\n get content() {\n const distributedChildren = this.distributedChildren;\n if (typeof distributedChildren === 'undefined') {\n console.warn(`DistributedChildrenContentMixin expects the component to define a \"distributedChildren\" property.`);\n }\n return distributedChildren;\n }\n set content(value) {\n if ('content' in base.prototype) { super.content = value; }\n // TODO: Set the children to the given value (which should be an array of\n // elements)?\n }\n\n /**\n * This event is raised when the component's contents (including distributed\n * children) have changed.\n *\n * @memberof DistributedChildrenContent\n * @event content-changed\n */\n }\n\n return DistributedChildrenContent;\n};\n","/* Exported function extends a base class with DistributedChildren. */\nexport default (base) => {\n\n /**\n * Mixin which defines helpers for accessing a component's distributed\n * children as a flattened array or string.\n *\n * The standard DOM API provides several ways of accessing child content:\n * `children`, `childNodes`, and `textContent`. None of these functions are\n * Shadow DOM aware. This mixin defines variations of those functions that\n * *are* Shadow DOM aware.\n *\n * Example: you create a component `` that displays a number\n * equal to the number of children placed inside that component. If someone\n * instantiates your component like:\n *\n * \n *
\n *
\n *
\n * \n *\n * Then the component should show \"3\", because there are three children. To\n * calculate the number of children, the component can just calculate\n * `this.children.length`. However, suppose someone instantiates your\n * component inside one of their own components, and puts a `` element\n * inside your component:\n *\n * \n * \n * \n *\n * If your component only looks at `this.children`, it will always see exactly\n * one child — the `` element. But the user looking at the page will\n * *see* any nodes distributed to that slot. To match what the user sees, your\n * component should expand any `` elements it contains.\n *\n * That is the problem this mixin solves. After applying this mixin, your\n * component code has access to `this.distributedChildren`, whose `length`\n * will return the total number of all children distributed to your component\n * in the composed tree.\n *\n * Note: The latest Custom Elements API design calls for a new function,\n * `getAssignedNodes` that takes an optional `deep` parameter, that will solve\n * this problem at the API level.\n */\n class DistributedChildren extends base {\n\n /**\n * An in-order collection of distributed children, expanding any slot\n * elements. Like the standard children property, this skips text nodes.\n *\n * @type {HTMLElement[]}\n */\n get distributedChildren() {\n return expandContentElements(this.children, false);\n }\n\n /**\n * An in-order collection of distributed child nodes, expanding any slot\n * elements. Like the standard childNodes property, this includes text\n * nodes.\n *\n * @type {Node[]}\n */\n get distributedChildNodes() {\n return expandContentElements(this.childNodes, true);\n }\n\n /**\n * The concatenated text content of all distributed child nodes, expanding\n * any slot elements.\n *\n * @type {string}\n */\n get distributedTextContent() {\n const strings = this.distributedChildNodes.map(function(child) {\n return child.textContent;\n });\n return strings.join('');\n }\n\n }\n\n return DistributedChildren;\n};\n\n\n/*\n * Given a array of nodes, return a new array with any content elements expanded\n * to the nodes distributed to that content element. This rule is applied\n * recursively.\n *\n * If includeTextNodes is true, text nodes will be included, as in the\n * standard childNodes property; by default, this skips text nodes, like the\n * standard children property.\n */\nfunction expandContentElements(nodes, includeTextNodes) {\n const expanded = Array.prototype.map.call(nodes, node => {\n // We want to see if the node is an instanceof HTMLSlotELement, but\n // that class won't exist if the browser that doesn't support native\n // Shadow DOM and if the Shadow DOM polyfill hasn't been loaded. Instead,\n // we do a simplistic check to see if the tag name is \"slot\".\n const isSlot = typeof HTMLSlotElement !== 'undefined' ?\n node instanceof HTMLSlotElement :\n node.localName === 'slot';\n if (isSlot) {\n // Use the nodes assigned to this node instead.\n const assignedNodes = node.assignedNodes({ flatten: true });\n return assignedNodes ?\n expandContentElements(assignedNodes, includeTextNodes) :\n [];\n } else if (node instanceof HTMLElement) {\n // Plain element; use as is.\n return [node];\n } else if (node instanceof Text && includeTextNodes) {\n // Text node.\n return [node];\n } else {\n // Comment, processing instruction, etc.; skip.\n return [];\n }\n });\n const flattened = [].concat(...expanded);\n return flattened;\n}\n","import createSymbol from './createSymbol';\n\n\n// Symbols for private data members on an element.\nconst selectedFractionSymbol = createSymbol('selectedFraction');\n\n\n/* Exported function extends a base class with FractionalSelection. */\nexport default function mixin(base) {\n\n /**\n * Adds support for fractional selection: treating a selection as a real\n * number that combines an integer portion (an index into a list), and a\n * fraction (indicating how far of the way we are to the next or previous\n * item).\n *\n * This is useful in components that support incremental operations during\n * dragging and swiping. Example: a carousel component has several items, and the\n * currently selected item is item 3. The user begins swiping to the left,\n * moving towards selecting item 4. Halfway through this operation, the\n * fractional selection value is 3.5.\n *\n * This value permits communication between mixins like\n * [SwipeDirectionMixin](./SwipeDirectionMixin.md) and\n * [TrackpadDirectionMixin](./TrackpadDirectionMixin.md), which generate\n * fractional selection values, and mixins like\n * [SelectionAnimationMixin](./SelectionAnimationMixin.md), which can render\n * selection at a fractional value.\n */\n class FractionalSelection extends base {\n\n connectedCallback() {\n if (super.connectedCallback) { super.connectedCallback(); }\n this.selectedFraction = 0;\n }\n\n /**\n * A fractional value indicating how far the user has currently advanced to\n * the next/previous item. E.g., a `selectedFraction` of 3.5 indicates the\n * user is halfway between items 3 and 4.\n *\n * @type {number}\n */\n get selectedFraction() {\n return this[selectedFractionSymbol];\n }\n set selectedFraction(value) {\n this[selectedFractionSymbol] = value;\n if ('selectedFraction' in base.prototype) { super.selectedFraction = value; }\n const event = new CustomEvent('selected-fraction-changed');\n this.dispatchEvent(event);\n }\n\n }\n\n return FractionalSelection;\n}\n\n\nmixin.helpers = {\n\n /*\n * Dampen a selection that goes past the beginning or end of a list. This is\n * generally used to produce a visual effect of tension as the user tries to\n * go further in a direction that has no more items.\n *\n * Example: suppose `itemCount` is 5, indicating a list of 5 items. The index of\n * the last item is 4. If the `selection` parameter is 4.5, the user is trying\n * to go past this last item. When a damping function is applied, the resulting\n * value will be less than 4.5 (the actual value will be 4.25). When this\n * selection state is rendered, the user will see that, each unit distance the\n * drag travels has less and less visible effect. This is perceived as tension.\n *\n * @param {number} selection - A real number indicating a selection position\n * @param {number} itemCount - An integer for the number of items in the list\n * @returns {number} A real number representing the damped selection value.\n */\n dampedSelection(selection, itemCount) {\n const bound = itemCount - 1;\n let damped;\n if (selection < 0) {\n // Trying to go past beginning of list. Apply tension from the left edge.\n damped = -mixin.helpers.damping(-selection);\n } else if (selection >= bound) {\n // Trying to go past end of list. Apply tension from the right edge.\n damped = bound + mixin.helpers.damping(selection - bound);\n } else {\n // No damping required.\n damped = selection;\n }\n return damped;\n },\n\n /*\n * Calculate damping as a function of the distance past the minimum/maximum\n * values.\n *\n * We want to asymptotically approach an absolute minimum of 1 unit\n * below/above the actual minimum/maximum. This requires calculating a\n * hyperbolic function.\n *\n * See http://www.wolframalpha.com/input/?i=y+%3D+-1%2F%28x%2B1%29+%2B+1\n * for the one we use. The only portion of that function we care about is when\n * x is zero or greater. An important consideration is that the curve be\n * tangent to the diagonal line x=y at (0, 0). This ensures smooth continuity\n * with the normal drag behavior, in which the visible sliding is linear with\n * the distance the touchpoint has been dragged.\n */\n damping(x) {\n const y = (-1 / (x + 1)) + 1;\n return y;\n },\n\n /*\n * Return the current fractional selection value for the given element.\n *\n * This simply adds the element's `selectedIndex` and `selectedFraction`\n * properties.\n *\n * @param {HTMLElement} element - An element that supports selection\n */\n elementSelection(element) {\n const selectedIndex = element.selectedIndex;\n if (selectedIndex < 0) {\n // No selection\n return;\n }\n const selectedFraction = element.selectedFraction || 0;\n return selectedIndex + selectedFraction;\n },\n\n /*\n * Breaks a fractional selection into its integer and fractional parts.\n *\n * Example: if passed 3.5, this returns { index: 3, fraction: 5 }.\n *\n * @param {number} selection – A real number representing a selection point\n * @returns {object} - An object with an `index` property holding the\n * selection's integer component, and a `fraction` property holding the\n * selection's fractional component.\n */\n selectionParts(selection) {\n // Stupid IE doesn't have Math.trunc.\n // const index = Math.trunc(selection);\n const index = selection < 0 ? Math.ceil(selection) : Math.floor(selection);\n const fraction = selection - index;\n return { index, fraction };\n },\n\n /*\n * Returns a fractional selection point after accounting for wrapping, ensuring\n * that the integer portion of the selection stays between 0 and `itemCount`-1.\n * That is, the integer portion will always be a valid index into the list.\n *\n * Example of wrapping past the end of the list: if `selection` is 5.5 and\n * `itemCount` is 5, this returns 0.5. Example of wrapping past the beginning of\n * the list: if `selection` is 0.5 and `itemCount` is 5, this returns 4.5.\n *\n * @param {number} selection - A real number representing a selection point\n * @param {number} itemCount - The number of items in the list\n * @returns {number} - The result of wrapping the selection point\n */\n wrappedSelection(selection, itemCount) {\n // Handles possibility of negative mod.\n // See http://stackoverflow.com/a/18618250/76472\n return ((selection % itemCount) + itemCount) % itemCount;\n },\n\n /*\n * Return the parts of a selection, first wrapping if necessary.\n *\n * @param {number} selection – A real number representing a selection point\n * @param {number} itemCount - The number of items in the list\n * @param {boolean} wrap – True if the selection should wrap to stay within the\n * list\n * @returns {object} – The parts of the selection, using the same format as\n * `selectionParts`.\n */\n wrappedSelectionParts(selection, itemCount, wrap) {\n if (wrap) {\n selection = mixin.helpers.wrappedSelection(selection, itemCount);\n }\n return mixin.helpers.selectionParts(selection);\n }\n\n};\n","import safeAttributes from '../../basic-component-mixins/src/safeAttributes';\nimport symbols from '../../basic-component-mixins/src/symbols';\n\n\n/* Exported function extends a base class with PlayControls. */\nexport default (base) => {\n\n /**\n * Template mixin which adds buttons for managing playback of a slideshow,\n * audio playlist, etc.\n *\n * Typical usage:\n *\n * class SlideshowWithControls extends PlayControlsMixin(Slideshow) {}\n * customElements.define('slideshow-with-controls', SlideshowWithControls);\n *\n */\n class PlayControls extends base {\n\n constructor() {\n super();\n this.$.previousButton.addEventListener('click', event => {\n this.selectPrevious();\n });\n this.$.playButton.addEventListener('click', event => {\n this.playing = !this.playing;\n });\n this.$.nextButton.addEventListener('click', event => {\n this.selectNext();\n });\n }\n\n connectedCallback() {\n if (super.connectedCallback) { super.connectedCallback(); }\n safeAttributes.connected(this);\n }\n\n [symbols.keydown](event) {\n let handled;\n\n switch (event.keyCode) {\n case 32: /* Space */\n this.playing = !this.playing;\n handled = true;\n break;\n }\n\n // Prefer mixin result if it's defined, otherwise use base result.\n return handled || (super[symbols.keydown] && super[symbols.keydown](event));\n }\n\n get playing() {\n return super.playing;\n }\n set playing(value) {\n if ('playing' in base.prototype) { super.playing = value; }\n safeAttributes.toggleClass(this, 'playing', value);\n }\n\n get [symbols.template]() {\n const baseTemplate = super[symbols.template] || '';\n return `\n \n\n \n\n \n ${baseTemplate}\n
\n `;\n }\n\n }\n\n return PlayControls;\n};\n","import createSymbol from './createSymbol';\nimport FractionalSelectionMixin from './FractionalSelectionMixin';\nimport symbols from './symbols';\n\n\n// Symbols for private data members on an element.\nconst animationSymbol = createSymbol('animation');\nconst draggingSymbol = createSymbol('dragging');\nconst lastAnimationSymbol = createSymbol('lastAnimation');\nconst playingAnimationSymbol = createSymbol('animatingSelection');\nconst previousSelectionSymbol = createSymbol('previousSelection');\nconst selectionAnimationDurationSymbol = createSymbol('selectionAnimationDuration');\nconst selectionAnimationEffectSymbol = createSymbol('selectionAnimationEffect');\nconst selectionAnimationKeyframesSymbol = createSymbol('selectionAnimationKeyframes');\nconst resetAnimationsOnNextRenderSymbol = createSymbol('resetAnimationsOnNextRender');\n\n\n/* Exported function extends a base class with SelectionAnimation. */\nexport default function mixin(base) {\n\n /**\n * Mixin which uses animation to show transitions between selection states.\n *\n * This mixin can be used by components that want to provide visible\n * animations when changing the selection. For example, a carousel component\n * may want to define a sliding animation effect shown when moving between\n * items.\n *\n * The animation is defined by a `selectionAnimationKeyframes` property; see\n * that property for details on how to define these keyframes. This animation\n * will be used in two ways. First, when moving strictly between items, the\n * animation will play smoothly to show the selection changing. Second, the\n * animation can be used to render the selection at a fixed point in the\n * transition between states. E.g., if the user pauses halfway through\n * dragging an element using [SwipeDirectionMixin](SwipeDirectionMixin.md)\n * or [TrackpadDirectionMixin](TrackpadDirectionMixin.md)s, then the selection\n * animation will be shown at the point exactly halfway through.\n *\n * This mixin expects a component to provide an `items` array of all elements\n * in the list, which can be provided via\n * [ContentItemsMixin](ContentItemsMixin.md). This mixin also expects\n * `selectedIndex` and `selectedItem` properties, which can be provided via\n * [SingleSelectionMixin](SingleSelectionMixin.md).\n *\n * This mixin supports a `selectionWraps` property. When true, the user can\n * navigate forward from the last item in the list and wrap around to the\n * first item, or navigate backward from the first item and wrap around to the\n * last item.\n *\n * This mixin uses the Web Animations API. For use on browsers which\n * do not support that API natively, you will need to load the\n * [Web Animations polyfill](https://github.com/web-animations/web-animations-js).\n */\n class SelectionAnimation extends base {\n\n constructor() {\n super();\n\n // Set defaults.\n if (typeof this.selectionAnimationDuration === 'undefined') {\n this.selectionAnimationDuration = this[symbols.defaults].selectionAnimationDuration;\n }\n if (typeof this.selectionAnimationEffect === 'undefined' && this.selectionAnimationKeyframes == null) {\n this.selectionAnimationEffect = this[symbols.defaults].selectionAnimationEffect;\n }\n\n this[symbols.dragging] = false;\n }\n\n get [symbols.defaults]() {\n const defaults = super[symbols.defaults] || {};\n defaults.selectionAnimationDuration = 250;\n defaults.selectionAnimationEffect = 'slide';\n return defaults;\n }\n\n /*\n * Provide backing for the dragging property.\n * Also, when a drag begins, reset the animations.\n */\n get [symbols.dragging]() {\n return this[draggingSymbol];\n }\n set [symbols.dragging](value) {\n const previousValue = this[symbols.dragging];\n this[draggingSymbol] = value;\n if (symbols.dragging in base.prototype) { super[symbols.dragging] = value; }\n if (value && !previousValue) {\n // Have begun a drag.\n this[resetAnimationsOnNextRenderSymbol] = true;\n }\n }\n\n [symbols.itemAdded](item) {\n // We mark new items in the list as explicitly visible to ARIA. Otherwise,\n // when an item isn't visible on the screen, ARIA will assume the item is\n // of no interest to the user, and leave it out of the accessibility tree.\n // If the list contains 10 items, but only 3 are visible, a screen reader\n // might then announce the list only has 3 items. To ensure that screen\n // readers and other assistive technologies announce the correct total\n // number of items, we explicitly mark all items as not hidden. This will\n // expose them all in the accessibility tree, even the items which are\n // currently not rendered.\n //\n // TODO: Generally speaking, this entire mixin assumes that the user can\n // navigate through all items in a list. But an app could style an item as\n // display:none or visibility:hidden because the user is not allowed to\n // interact with that item at the moment. Support for this scenario should\n // be added. This would entail changing all locations where a mixin\n // function is counting items, iterating over the (visible) items, and\n // showing or hiding items. Among other things, the code below to make\n // items visible to ARIA would need to discriminate between items which\n // are invisible because of animation state, or invisible because the user\n // shouldn't interact with them.\n item.setAttribute('aria-hidden', false);\n }\n\n [symbols.itemsChanged]() {\n if (super[symbols.itemsChanged]) { super[symbols.itemsChanged](); }\n\n resetAnimations(this);\n\n // TODO: Also reset our notion of the last rendered selection? This comes\n // up when a DOM removal causes the selected item to change position.\n // this[previousSelectionSymbol] = null;\n\n renderSelection(this);\n }\n\n resetAnimations() {\n resetAnimations(this);\n }\n\n /**\n * A fractional value indicating how far the user has currently advanced to\n * the next/previous item. E.g., a `selectedFraction` of 3.5 indicates the\n * user is halfway between items 3 and 4.\n *\n * For more details, see [FractionalSelectionMixin](FractionalSelectionMixin.md)\n * mixin.\n *\n * @type {number}\n */\n get selectedFraction() {\n return super.selectedFraction || 0;\n }\n set selectedFraction(value) {\n if ('selectedFraction' in base.prototype) { super.selectedFraction = value; }\n renderSelection(this, this.selectedIndex, value);\n }\n\n get selectedIndex() {\n return super.selectedIndex;\n }\n set selectedIndex(index) {\n if ('selectedIndex' in base.prototype) { super.selectedIndex = index; }\n renderSelection(this, index, 0);\n }\n\n /**\n * The duration of a selection animation in milliseconds.\n *\n * This measures the amount of time required for a selection animation to\n * complete. This number remains constant, even if the number of items being\n * animated increases.\n *\n * The default value is 250 milliseconds (a quarter a second).\n *\n * @type {number}\n * @default 250\n */\n get selectionAnimationDuration() {\n return this[selectionAnimationDurationSymbol];\n }\n set selectionAnimationDuration(value) {\n this[selectionAnimationDurationSymbol] = value;\n if ('selectionAnimationDuration' in base.prototype) { super.selectionAnimationDuration = value; }\n }\n\n /**\n * The name of a standard selection animation effect.\n *\n * This is a shorthand for setting the `selectionAnimationKeyframes`\n * property to standard keyframes. Supported string values:\n *\n * * \"crossfade\"\n * * \"reveal\"\n * * \"revealWithFade\"\n * * \"showAdjacent\"\n * * \"slide\"\n * * \"slideWithGap\"\n *\n * @type {string}\n * @default \"slide\"\n */\n get selectionAnimationEffect() {\n return this[selectionAnimationEffectSymbol];\n }\n set selectionAnimationEffect(value) {\n this[selectionAnimationEffectSymbol] = value;\n if ('selectionAnimationEffect' in base.prototype) { super.selectionAnimationEffect = value; }\n this.selectionAnimationKeyframes = mixin.standardEffectKeyframes[value];\n }\n\n /**\n * The keyframes that define an animation that plays for an item when moving\n * forward in the sequence.\n *\n * This is an array of CSS rules that will be applied. These are used as\n * [keyframes](http://w3c.github.io/web-animations/#keyframes-section)\n * to animate the item with the\n * [Web Animations API](https://developer.mozilla.org/en-US/docs/Web/API/animation).\n *\n * The animation represents the state of the next item as it moves from\n * completely unselected (offstage, usually right), to selected (center\n * stage), to completely unselected (offstage, usually left). The center time\n * of the animation should correspond to the item's quiscent selected state,\n * typically in the center of the stage and at the item's largest size.\n *\n * The default forward animation is a smooth slide at full size from right to\n * left.\n *\n * When moving the selection backward, this animation is played in reverse.\n *\n * @type {cssRules[]}\n */\n get selectionAnimationKeyframes() {\n // Standard animation slides left/right, keeps adjacent items out of view.\n return this[selectionAnimationKeyframesSymbol];\n }\n set selectionAnimationKeyframes(value) {\n this[selectionAnimationKeyframesSymbol] = value;\n if ('selectionAnimationKeyframes' in base.prototype) { super.selectionAnimationKeyframes = value; }\n resetAnimations(this);\n renderSelection(this);\n }\n\n get selectionWraps() {\n return super.selectionWraps;\n }\n set selectionWraps(value) {\n if ('selectionWraps' in base.prototype) { super.selectionWraps = value; }\n resetAnimations(this);\n renderSelection(this);\n }\n }\n\n return SelectionAnimation;\n}\n\n\n// We expose helpers on the mixin function that we want to be able to unit test.\n// Since these are on the function, not on the class emitted by the function,\n// they don't end up getting exposed on actual element instances.\nmixin.helpers = {\n\n /*\n * Calculate the animation fractions for an element's items at the given\n * selection point. This is used when rendering the element's selection state\n * instantaneously.\n *\n * This function considers the selectedIndex parameter, which can be a whole\n * or fractional number, and determines which items will be visible at that\n * index. This function then calculates a corresponding animation fraction: a\n * number between 0 and 1 indicating how far through the selection animation\n * an item should be shown, or null if the item should not be visible at that\n * selection index. These fractions are returned as an array, where the\n * animation fraction at position N corresponds to how item N should be shown.\n */\n animationFractionsForSelection(element, selection) {\n\n const items = element.items;\n if (!items) {\n return;\n }\n\n const itemCount = items.length;\n const selectionWraps = element.selectionWraps;\n\n return items.map((item, itemIndex) => {\n // How many steps from the selection point to this item?\n const steps = stepsToIndex(itemCount, selectionWraps, selection, itemIndex);\n // To convert steps to animation fraction:\n // steps animation fraction\n // 1 0 (stage right)\n // 0 0.5 (center stage)\n // -1 1 (stage left)\n const animationFraction = (1 - steps) / 2;\n return (animationFraction >= 0 && animationFraction <= 1) ?\n animationFraction :\n null; // Outside animation range\n });\n },\n\n /*\n * Calculate the animation timings that should be used to smoothly animate the\n * element's items from one selection state to another.\n *\n * This returns an array of timings, where the timing at position N should be\n * used to animate item N. If an item's timing is null, then that item should\n * not take place in the animation, and should be hidden instead.\n */\n effectTimingsForSelectionAnimation(element, fromSelection, toSelection) {\n\n const items = element.items;\n if (!items) {\n return;\n }\n const itemCount = items.length;\n const selectionWraps = element.selectionWraps;\n const toIndex = FractionalSelectionMixin.helpers.wrappedSelectionParts(toSelection, itemCount, selectionWraps).index;\n const totalSteps = stepsToIndex(itemCount, selectionWraps, fromSelection, toSelection);\n const direction = totalSteps >= 0 ? 'normal': 'reverse';\n const fill = 'both';\n const totalDuration = element.selectionAnimationDuration;\n const stepDuration = totalSteps !== 0 ?\n totalDuration * 2 / Math.ceil(Math.abs(totalSteps)) :\n 0; // No steps required, animation will be instantenous.\n\n const timings = items.map((item, itemIndex) => {\n const steps = stepsToIndex(itemCount, selectionWraps, itemIndex, toSelection);\n // If we include this item in the staggered sequence of animations we're\n // creating, where would the item appear in the sequence?\n let positionInSequence = totalSteps - steps;\n if (totalSteps < 0) {\n positionInSequence = -positionInSequence;\n }\n // So, is this item really included in the sequence?\n if (Math.ceil(positionInSequence) >= 0 && positionInSequence <= Math.abs(totalSteps)) {\n // Note that delay for first item will be negative. That will cause\n // the animation to start halfway through, which is what we want.\n const delay = stepDuration * (positionInSequence - 1)/2;\n const endDelay = itemIndex === toIndex ?\n -stepDuration/2 : // Stop halfway through.\n 0; // Play animation until end.\n return { duration: stepDuration, direction, fill, delay, endDelay };\n } else {\n return null;\n }\n });\n\n return timings;\n }\n\n};\n\n\n// Keyframes for standard selection animation effects.\nmixin.standardEffectKeyframes = {\n\n // Simple crossfade\n crossfade: [\n { opacity: 0 },\n { opacity: 1 },\n { opacity: 0 }\n ],\n\n // Reveal, as if sliding the top card off a deck of cards\n reveal: [\n { transform: 'translateX(0%)', zIndex: 0 },\n { transform: 'translateX(0%)', zIndex: 1 },\n { transform: 'translateX(-100%)', zIndex: 2 }\n ],\n\n // Google Photos-style reveal-with-fade animation\n revealWithFade: [\n { transform: 'translateX(0%) scale(0.75)', opacity: 0, zIndex: 0 },\n { transform: 'translateX(0%) scale(1.0)', opacity: 1, zIndex: 1 },\n { transform: 'translateX(-100%) scale(1.0)', opacity: 1, zIndex: 2 }\n ],\n\n // Carousel variant with a bit of off-stage elements showing\n showAdjacent: [\n { transform: 'translateX(78%) scale(0.7)', zIndex: 0 },\n { transform: 'translateX(0%) scale(0.82)', zIndex: 1 },\n { transform: 'translateX(-78%) scale(0.7)', zIndex: 0 }\n ],\n\n // Simple slide\n slide: [\n { transform: 'translateX(100%)' },\n { transform: 'translateX(-100%)' }\n ],\n\n // Slide, with a gap between\n slideWithGap: [\n { transform: 'translateX(110%)' },\n { transform: 'translateX(-110%)' }\n ]\n\n};\n\n\n/*\n * Smoothly animate the selection between the indicated \"from\" and \"to\"\n * indices. The former can be a fraction, e.g., when the user releases a finger\n * to complete a touch drag, and the selection will snap to the closest whole\n * index.\n */\nfunction animateSelection(element, fromSelection, toSelection) {\n\n resetAnimations(element);\n\n // Calculate the animation timings.\n const items = element.items;\n const keyframes = element.selectionAnimationKeyframes;\n element[playingAnimationSymbol] = true;\n const timings = mixin.helpers.effectTimingsForSelectionAnimation(element, fromSelection, toSelection);\n\n // Figure out which item will be the one *after* the one we're selecting.\n const itemCount = items.length;\n const selectionWraps = element.selectionWraps;\n const selectionIndex = FractionalSelectionMixin.helpers.selectionParts(toSelection, itemCount, selectionWraps).index;\n const totalSteps = stepsToIndex(itemCount, selectionWraps, fromSelection, toSelection);\n const forward = totalSteps >= 0;\n let nextUpIndex = selectionIndex + (forward ? 1 : - 1);\n if (selectionWraps) {\n nextUpIndex = FractionalSelectionMixin.helpers.wrappedSelection(nextUpIndex, itemCount);\n } else if (!isItemIndexInBounds(element, nextUpIndex)) {\n nextUpIndex = null; // At start/end of list; don't have a next item to show.\n }\n\n // Play the animations using those timings.\n let lastAnimationDetails;\n timings.forEach((timing, index) => {\n const item = items[index];\n if (timing) {\n showItem(item, true);\n const animation = item.animate(keyframes, timing);\n element[animationSymbol][index] = animation;\n if (index === nextUpIndex) {\n // This item will be animated, so will already be in the desired state\n // after the animation completes.\n nextUpIndex = null;\n }\n if (timing.endDelay !== 0) {\n // This is the animation for the item that will be left selected.\n // We want to clean up when this animation completes.\n lastAnimationDetails = { animation, index, timing, forward };\n }\n } else {\n // This item doesn't participate in the animation.\n showItem(item, false);\n }\n });\n\n if (lastAnimationDetails != null) {\n // Arrange for clean-up work to be performed.\n lastAnimationDetails.nextUpIndex = nextUpIndex;\n lastAnimationDetails.animation.onfinish = event => selectionAnimationFinished(element, lastAnimationDetails);\n element[lastAnimationSymbol] = lastAnimationDetails.animation;\n } else {\n // Shouldn't happen -- we should always have at least one animation.\n element[playingAnimationSymbol] = false;\n }\n}\n\n\nfunction getAnimationForItemIndex(element, index) {\n if (element[animationSymbol] == null) {\n // Not ready yet;\n return null;\n }\n let animation = element[animationSymbol][index];\n if (!animation) {\n const item = element.items[index];\n animation = item.animate(element.selectionAnimationKeyframes, {\n duration: element.selectionAnimationDuration,\n fill: 'both'\n });\n animation.pause();\n element[animationSymbol][index] = animation;\n }\n return animation;\n}\n\nfunction isItemIndexInBounds(element, index) {\n return index >= 0 && element.items && index < element.items.length;\n}\n\n/*\n * Render the selection state of the element.\n *\n * This can be used to re-render a previous selection state (if the\n * selectedIndex param is omitted), render the selection instantly at a given\n * whole or fractional selection index, or animate to a given selection index.\n *\n * There are several distinct scenarios we need to cover:\n *\n * 1. Initial positioning, or repositioning after changing a property like\n * selectionAnimationKeyframes that affects rendering.\n * 2. Animate on selectedIndex change. This should override any animation/swipe\n * already in progress.\n * 3. Instantly render the current position of a drag operation in progress.\n * 4. Complete a drag operation. If the drag wasn't far enough to affect\n * selection, we'll just be restoring the selectedFraction to 0.\n *\n * If the list does not wrap, any selection position outside the list's bounds\n * will be damped to produce a visual effect of tension.\n */\nfunction renderSelection(element, selectedIndex=element.selectedIndex, selectedFraction=element.selectedFraction) {\n const itemCount = element.items ? element.items.length : 0;\n if (itemCount === 0) {\n // Nothing to render.\n return;\n }\n if (selectedIndex < 0) {\n // TODO: Handle no selection.\n return;\n }\n let selection = selectedIndex + selectedFraction;\n if (element.selectionWraps) {\n // Apply wrapping to ensure consistent representation of selection.\n selection = FractionalSelectionMixin.helpers.wrappedSelection(selection, itemCount);\n } else {\n // Apply damping if necessary.\n selection = FractionalSelectionMixin.helpers.dampedSelection(selection, itemCount);\n }\n const previousSelection = element[previousSelectionSymbol];\n // TODO: If an item changes position in the DOM, we end up animating from\n // its old index to its new index, but we really don't want to animate at all.\n if (!element[symbols.dragging] && previousSelection != null &&\n previousSelection !== selection) {\n // Animate selection from previous state to new state.\n animateSelection(element, previousSelection, selection);\n } else if (selectedFraction === 0 && element[playingAnimationSymbol]) {\n // Already in process of animating to fraction 0. During that process,\n // ignore subsequent attempts to renderSelection to fraction 0.\n return;\n } else {\n // Render current selection state instantly.\n renderSelectionInstantly(element, selection);\n }\n element[previousSelectionSymbol] = selection;\n}\n\n/*\n * Instantly render (don't animate) the element's items at the given whole or\n * fractional selection index.\n */\nfunction renderSelectionInstantly(element, toSelection) {\n if (element[resetAnimationsOnNextRenderSymbol]) {\n resetAnimations(element);\n element[resetAnimationsOnNextRenderSymbol] = false;\n }\n const animationFractions = mixin.helpers.animationFractionsForSelection(element, toSelection);\n animationFractions.map((animationFraction, index) => {\n const item = element.items[index];\n if (animationFraction != null) {\n showItem(item, true);\n setAnimationFraction(element, index, animationFraction);\n } else {\n showItem(item, false);\n }\n });\n}\n\n/*\n * We maintain an array containing an animation per item. This is used for two\n * reasons:\n *\n * * During a drag operation, we want to be able to reuse animations between\n * drag updates.\n * * When a selection animation completes, we need to be able to leave the\n * visibile items in a paused state. Later, we'll want to be able to clean up\n * those animations.\n *\n * Note that this array is sparse: it will only hold up from 0–3 animations at\n * any given point.\n */\nfunction resetAnimations(element) {\n const animations = element[animationSymbol];\n if (animations) {\n // Cancel existing animations to remove the effects they're applying.\n animations.forEach((animation, index) => {\n if (animation) {\n animation.cancel();\n animations[index] = null;\n }\n });\n }\n const itemCount = element.items ? element.items.length : 0;\n if (!animations || animations.length !== itemCount) {\n // Haven't animated before with this number of items; (re)create array.\n element[animationSymbol] = new Array(itemCount);\n }\n}\n\n/*\n * The last animation in our selection animation has completed. Clean up.\n */\nfunction selectionAnimationFinished(element, details) {\n\n // When the last animation completes, show the next item in the direction\n // we're going. Waiting to that until this point is a bit of a hack to avoid\n // having a next item that's higher in the natural z-order obscure other items\n // during animation.\n const nextUpIndex = details.nextUpIndex;\n if (nextUpIndex != null) {\n if (element[animationSymbol][nextUpIndex]) {\n // Cancel existing selection animation so we can construct a new one.\n element[animationSymbol][nextUpIndex].cancel();\n element[animationSymbol][nextUpIndex] = null;\n }\n const animationFraction = details.forward ? 0 : 1;\n setAnimationFraction(element, nextUpIndex, animationFraction);\n showItem(element.items[nextUpIndex], true);\n }\n\n element[lastAnimationSymbol].onfinish = null;\n element[playingAnimationSymbol] = false;\n}\n\n/*\n * Pause the indicated animation and have it show the animation at the given\n * fraction (between 0 and 1) of the way through the animation.\n */\nfunction setAnimationFraction(element, itemIndex, fraction) {\n const animation = getAnimationForItemIndex(element, itemIndex);\n if (animation) {\n const duration = element.selectionAnimationDuration;\n if (duration) {\n animation.currentTime = fraction * duration;\n }\n }\n}\n\nfunction showItem(item, flag) {\n item.style.visibility = flag ? 'visible' : 'hidden';\n}\n\n/*\n * Figure out how many steps it will take to go from fromSelection to\n * toSelection. To go from item 3 to item 4 is one step.\n *\n * If wrapping is allowed, then going from the last item to the first will take\n * one step (forward), and going from the first item to the last will take one\n * step (backward).\n */\nfunction stepsToIndex(length, allowWrap, fromSelection, toSelection) {\n let steps = toSelection - fromSelection;\n // Wrapping only kicks in when list has more than 1 item.\n if (allowWrap && length > 1) {\n const wrapSteps = length - Math.abs(steps);\n if (wrapSteps <= 1) {\n // Special case\n steps = steps < 0 ?\n wrapSteps : // Wrap forward from last item to first.\n -wrapSteps; // Wrap backward from first item to last.\n }\n }\n return steps;\n}\n","import symbols from './symbols';\n\n\n// Used to assign unique IDs to item elements without IDs.\nlet idCount = 0;\n\n\n/* Exported function extends a base class with SelectionAriaActive. */\nexport default (base) => {\n\n /**\n * Mixin which treats the selected item in a list as the active item in ARIA\n * accessibility terms.\n *\n * Handling ARIA selection state properly is actually quite complex:\n *\n * * The items in the list need to be indicated as possible items via an ARIA\n * `role` attribute value such as \"option\".\n * * The selected item need to be marked as selected by setting the item's\n * `aria-selected` attribute to true *and* the other items need be marked as\n * *not* selected by setting `aria-selected` to false.\n * * The outermost element with the keyboard focus needs to have attributes\n * set on it so that the selection is knowable at the list level via the\n * `aria-activedescendant` attribute.\n * * Use of `aria-activedescendant` in turn requires that all items in the\n * list have ID attributes assigned to them.\n *\n * This mixin tries to address all of the above requirements. To that end,\n * this mixin will assign generated IDs to any item that doesn't already have\n * an ID.\n *\n * ARIA relies on elements to provide `role` attributes. This mixin will apply\n * a default role of \"listbox\" on the outer list if it doesn't already have an\n * explicit role. Similarly, this mixin will apply a default role of \"option\"\n * to any list item that does not already have a role specified.\n *\n * This mixin expects a set of members that manage the state of the selection:\n * `[symbols.itemSelected]`, `itemAdded`, and `selectedIndex`. You can\n * supply these yourself, or do so via\n * [SingleSelectionMixin](SingleSelectionMixin.md).\n */\n class SelectionAriaActive extends base {\n\n connectedCallback() {\n if (super.connectedCallback) { super.connectedCallback(); }\n // Set default ARIA role.\n if (this.getAttribute('role') == null && this[symbols.defaults].role) {\n this.setAttribute('role', this[symbols.defaults].role);\n }\n }\n\n get [symbols.defaults]() {\n const defaults = super[symbols.defaults] || {};\n defaults.role = 'listbox';\n return defaults;\n }\n\n [symbols.itemAdded](item) {\n if (super[symbols.itemAdded]) { super[symbols.itemAdded](item); }\n\n if (!item.getAttribute('role')) {\n // Assign a default ARIA role.\n item.setAttribute('role', 'option');\n }\n\n // Ensure each item has an ID so we can set aria-activedescendant on the\n // overall list whenever the selection changes.\n //\n // The ID will take the form of a base ID plus a unique integer. The base\n // ID will be incorporate the component's own ID. E.g., if a component has\n // ID \"foo\", then its items will have IDs that look like \"_fooOption1\". If\n // the compnent has no ID itself, its items will get IDs that look like\n // \"_option1\". Item IDs are prefixed with an underscore to differentiate\n // them from manually-assigned IDs, and to minimize the potential for ID\n // conflicts.\n if (!item.id) {\n const baseId = this.id ?\n \"_\" + this.id + \"Option\" :\n \"_option\";\n item.id = baseId + idCount++;\n }\n }\n\n [symbols.itemSelected](item, selected) {\n if (super[symbols.itemSelected]) { super[symbols.itemSelected](item, selected); }\n item.setAttribute('aria-selected', selected);\n const itemId = item.id;\n if (itemId && selected) {\n this.setAttribute('aria-activedescendant', itemId);\n }\n }\n\n get selectedItem() {\n return super.selectedItem;\n }\n set selectedItem(item) {\n if ('selectedItem' in base.prototype) { super.selectedItem = item; }\n if (item == null) {\n // Selection was removed.\n this.removeAttribute('aria-activedescendant');\n }\n }\n\n }\n\n return SelectionAriaActive;\n};\n","/* Exported function extends a base class with ShadowElementReferences. */\nexport default (base) => {\n\n /**\n * Mixin to create references to elements in a component's Shadow DOM subtree.\n *\n * This adds a member on the component called `this.$` that can be used to\n * reference shadow elements with IDs. E.g., if component's shadow contains an\n * element ``, then this mixin will create a member\n * `this.$.foo` that points to that button.\n *\n * Such references simplify a component's access to its own elements. In\n * exchange, this mixin trades off a one-time cost of querying all elements in\n * the shadow tree instead of paying an ongoing cost to query for an element\n * each time the component wants to inspect or manipulate it.\n *\n * This mixin expects the component to define a Shadow DOM subtree. You can\n * create that tree yourself, or make use of\n * [ShadowTemplateMixin](ShadowTemplateMixin.md).\n *\n * This mixin is inspired by Polymer's [automatic\n * node finding](https://www.polymer-project.org/1.0/docs/devguide/local-dom.html#node-finding)\n * feature.\n */\n class ShadowElementReferences extends base {\n\n constructor() {\n super();\n if (this.shadowRoot) {\n // Look for elements in the shadow subtree that have id attributes.\n // An alternatively implementation of this mixin would be to just define\n // a this.$ getter that lazily does this search the first time someone\n // tries to access this.$. That might introduce some complexity – if the\n // the tree changed after it was first populated, the result of\n // searching for a node might be somewhat unpredictable.\n this.$ = {};\n const nodesWithIds = this.shadowRoot.querySelectorAll('[id]');\n [].forEach.call(nodesWithIds, node => {\n const id = node.getAttribute('id');\n this.$[id] = node;\n });\n }\n }\n\n /**\n * The collection of references to the elements with IDs in a component's\n * Shadow DOM subtree.\n *\n * @type {object}\n * @member $\n */\n }\n\n return ShadowElementReferences;\n};\n","import symbols from '../src/symbols';\n\n\n/* Exported function extends a base class with ShadowTemplate. */\nexport default (base) => {\n\n /**\n * Mixin for stamping a template into a Shadow DOM subtree upon component\n * instantiation.\n *\n * To use this mixin, define a `template` property as a string or HTML\n * `` element:\n *\n * class MyElement extends ShadowTemplateMixin(HTMLElement) {\n * get [symbols.template]() {\n * return `Hello, world .`;\n * }\n * }\n *\n * When your component class is instantiated, a shadow root will be created on\n * the instance, and the contents of the template will be cloned into the\n * shadow root. If your component does not define a `template` property, this\n * mixin has no effect.\n *\n * For the time being, this extension retains support for Shadow DOM v0. That\n * will eventually be deprecated as browsers (and the Shadow DOM polyfill)\n * implement Shadow DOM v1.\n */\n class ShadowTemplate extends base {\n\n /*\n * If the component defines a template, a shadow root will be created on the\n * component instance, and the template stamped into it.\n */\n constructor() {\n super();\n let template = this[symbols.template];\n // TODO: Save the processed template with the component's class prototype\n // so it doesn't need to be processed with every instantiation.\n if (template) {\n\n if (typeof template === 'string') {\n // Upgrade plain string to real template.\n template = createTemplateWithInnerHTML(template);\n }\n\n if (window.ShadowDOMPolyfill) {\n shimTemplateStyles(template, this.localName);\n }\n\n const root = this.attachShadow({ mode: 'open' });\n const clone = document.importNode(template.content, true);\n root.appendChild(clone);\n }\n }\n\n }\n\n return ShadowTemplate;\n};\n\n\n// Convert a plain string of HTML into a real template element.\nfunction createTemplateWithInnerHTML(innerHTML) {\n const template = document.createElement('template');\n // REVIEW: Is there an easier way to do this?\n // We'd like to just set innerHTML on the template content, but since it's\n // a DocumentFragment, that doesn't work.\n const div = document.createElement('div');\n div.innerHTML = innerHTML;\n while (div.childNodes.length > 0) {\n template.content.appendChild(div.childNodes[0]);\n }\n return template;\n}\n\n// Invoke basic style shimming with ShadowCSS.\nfunction shimTemplateStyles(template, tag) {\n window.WebComponents.ShadowCSS.shimStyling(template.content, tag);\n}\n","import createSymbol from './createSymbol';\nimport symbols from './symbols';\n\n\n// Symbols for private data members on an element.\nconst canSelectNextSymbol = createSymbol('canSelectNext');\nconst canSelectPreviousSymbol = createSymbol('canSelectPrevious');\nconst selectionRequiredSymbol = createSymbol('selectionRequired');\nconst selectionWrapsSymbol = createSymbol('selectionWraps');\n\n// We want to expose both selectedIndex and selectedItem as independent\n// properties but keep them in sync. This allows a component user to reference\n// the selection by whatever means is most natural for their situation.\n//\n// To efficiently keep these properties in sync, we track \"external\" and\n// \"internal\" references for each property:\n//\n// The external index or item is the one we report to the outside world when\n// asked for selection. When handling a change to index or item, we update the\n// external reference as soon as possible, so that if anyone immediately asks\n// for the current selection, they will receive a stable answer.\n//\n// The internal index or item tracks whichever index or item last received the\n// full set of processing. Processing includes raising a change event for the\n// new value. Once we've begun that processing, we store the new value as the\n// internal value to indicate we've handled it.\n//\nconst externalSelectedIndexSymbol = createSymbol('externalSelectedIndex');\nconst externalSelectedItemSymbol = createSymbol('externalSelectedItem');\nconst internalSelectedIndexSymbol = createSymbol('internalSelectedIndex');\nconst internalSelectedItemSymbol = createSymbol('internalSelectedItem');\n\n\n/* Exported function extends a base class with SingleSelection. */\nexport default (base) => {\n\n /**\n * Mixin which manages single-selection semantics for items in a list.\n *\n * This mixin expects a component to provide an `items` Array or NodeList of\n * all elements in the list. A standard way to do that with is the\n * [ContentItemsMixin](ContentItemsMixin.md), which takes a component's\n * content (typically its distributed children) as the set of list items; see\n * that mixin for details.\n *\n * This mixin tracks a single selected item in the list, and provides means to\n * get and set that state by item position (`selectedIndex`) or item identity\n * (`selectedItem`). The selection can be moved in the list via the methods\n * `selectFirst`, `selectLast`, `selectNext`, and `selectPrevious`.\n *\n * This mixin does not produce any user-visible effects to represent\n * selection. Other mixins, such as\n * [SelectionAriaActiveMixin](SelectionAriaActiveMixin.md),\n * [SelectionHighlightMixin](SelectionHighlightMixin.md) and\n * [SelectionInViewMixin](SelectionInViewMixin.md), modify the selected item\n * in common ways to let the user know a given item is selected or not\n * selected.\n */\n class SingleSelection extends base {\n\n constructor() {\n super();\n // Set defaults.\n if (typeof this.selectionRequired === 'undefined') {\n this.selectionRequired = this[symbols.defaults].selectionRequired;\n }\n if (typeof this.selectionWraps === 'undefined') {\n this.selectionWraps = this[symbols.defaults].selectionWraps;\n }\n }\n\n /**\n * True if the selection can be moved to the next item, false if not (the\n * selected item is the last item in the list).\n *\n * @type {boolean}\n */\n get canSelectNext() {\n return this[canSelectNextSymbol];\n }\n set canSelectNext(canSelectNext) {\n const previousCanSelectNext = this[canSelectNextSymbol];\n this[canSelectNextSymbol] = canSelectNext;\n if ('canSelectNext' in base.prototype) { super.canSelectNext = canSelectNext; }\n if (canSelectNext !== previousCanSelectNext) {\n this.dispatchEvent(new CustomEvent('can-select-next-changed'));\n }\n }\n\n /**\n * True if the selection can be moved to the previous item, false if not\n * (the selected item is the first one in the list).\n *\n * @type {boolean}\n */\n get canSelectPrevious() {\n return this[canSelectPreviousSymbol];\n }\n set canSelectPrevious(canSelectPrevious) {\n const previousCanSelectPrevious = this[canSelectPreviousSymbol];\n this[canSelectPreviousSymbol] = canSelectPrevious;\n if ('canSelectPrevious' in base.prototype) { super.canSelectPrevious = canSelectPrevious; }\n if (canSelectPrevious !== previousCanSelectPrevious) {\n this.dispatchEvent(new CustomEvent('can-select-previous-changed'));\n }\n }\n\n get [symbols.defaults]() {\n const defaults = super[symbols.defaults] || {};\n defaults.selectionRequired = false;\n defaults.selectionWraps = false;\n return defaults;\n }\n\n /**\n * Handle a new item being added to the list.\n *\n * The default implementation of this method simply sets the item's\n * selection state to false.\n *\n * @param {HTMLElement} item - the item being added\n */\n [symbols.itemAdded](item) {\n if (super[symbols.itemAdded]) { super[symbols.itemAdded](item); }\n this[symbols.itemSelected](item, item === this.selectedItem);\n }\n\n [symbols.itemsChanged]() {\n if (super[symbols.itemsChanged]) { super[symbols.itemsChanged](); }\n\n // In case selected item changed position or was removed.\n trackSelectedItem(this);\n\n // In case the change in items affected which navigations are possible.\n updatePossibleNavigations(this);\n }\n\n /**\n * Apply the indicate selection state to the item.\n *\n * The default implementation of this method does nothing. User-visible\n * effects will typically be handled by other mixins.\n *\n * @param {HTMLElement} item - the item being selected/deselected\n * @param {boolean} selected - true if the item is selected, false if not\n */\n [symbols.itemSelected](item, selected) {\n if (super[symbols.itemSelected]) { super[symbols.itemSelected](item, selected); }\n }\n\n /**\n * The index of the item which is currently selected.\n *\n * A `selectedIndex` of -1 indicates there is no selection. Setting this\n * property to -1 will remove any existing selection.\n *\n * @type {number}\n */\n get selectedIndex() {\n return this[externalSelectedIndexSymbol] != null ?\n this[externalSelectedIndexSymbol] :\n -1;\n }\n set selectedIndex(index) {\n // See notes at top about internal vs. external copies of this property.\n const previousSelectedIndex = this[internalSelectedIndexSymbol];\n let item;\n if (index !== this[externalSelectedIndexSymbol]) {\n // Store the new index and the corresponding item.\n const items = this.items;\n const hasItems = items && items.length > 0;\n if (!(hasItems && index >= 0 && index < items.length)) {\n index = -1; // No item at that index.\n }\n this[externalSelectedIndexSymbol] = index;\n item = hasItems && index >= 0 ? items[index] : null;\n this[externalSelectedItemSymbol] = item;\n } else {\n item = this[externalSelectedItemSymbol];\n }\n\n // Now let super do any work.\n if ('selectedIndex' in base.prototype) { super.selectedIndex = index; }\n\n if (index !== previousSelectedIndex) {\n // The selected index changed.\n this[internalSelectedIndexSymbol] = index;\n\n const event = new CustomEvent('selected-index-changed', {\n detail: {\n selectedIndex: index,\n value: index // for Polymer binding. TODO: Verify still necessary\n }\n });\n this.dispatchEvent(event);\n }\n\n if (this[internalSelectedItemSymbol] !== item) {\n // Update selectedItem property so it can have its own effects.\n this.selectedItem = item;\n }\n }\n\n /**\n * The currently selected item, or null if there is no selection.\n *\n * Setting this property to null deselects any currently-selected item.\n * Setting this property to an object that is not in the list has no effect.\n *\n * TODO: Even if selectionRequired, can still explicitly set selectedItem to null.\n * TODO: If selectionRequired, leave selection alone?\n *\n * @type {object}\n */\n get selectedItem() {\n return this[externalSelectedItemSymbol] || null;\n }\n set selectedItem(item) {\n // See notes at top about internal vs. external copies of this property.\n const previousSelectedItem = this[internalSelectedItemSymbol];\n let index;\n if (item !== this[externalSelectedItemSymbol]) {\n // Store item and look up corresponding index.\n const items = this.items;\n const hasItems = items && items.length > 0;\n index = hasItems ? Array.prototype.indexOf.call(items, item) : -1;\n this[externalSelectedIndexSymbol] = index;\n if (index < 0) {\n item = null; // The indicated item isn't actually in `items`.\n }\n this[externalSelectedItemSymbol] = item;\n } else {\n index = this[externalSelectedIndexSymbol];\n }\n\n // Now let super do any work.\n if ('selectedItem' in base.prototype) { super.selectedItem = item; }\n\n if (item !== previousSelectedItem) {\n // The selected item changed.\n this[internalSelectedItemSymbol] = item;\n\n if (previousSelectedItem) {\n // Update selection state of old item.\n this[symbols.itemSelected](previousSelectedItem, false);\n }\n if (item) {\n // Update selection state to new item.\n this[symbols.itemSelected](item, true);\n }\n\n updatePossibleNavigations(this);\n\n const event = new CustomEvent('selected-item-changed', {\n detail: {\n selectedItem: item,\n value: item // for Polymer binding\n }\n });\n this.dispatchEvent(event);\n }\n\n if (this[internalSelectedIndexSymbol] !== index) {\n // Update selectedIndex property so it can have its own effects.\n this.selectedIndex = index;\n }\n }\n\n /**\n * Select the first item in the list.\n */\n selectFirst() {\n if (super.selectFirst) { super.selectFirst(); }\n return selectIndex(this, 0);\n }\n\n /**\n * True if the list should always have a selection (if it has items).\n *\n * @type {boolean}\n * @default false\n */\n get selectionRequired() {\n return this[selectionRequiredSymbol];\n }\n set selectionRequired(selectionRequired) {\n this[selectionRequiredSymbol] = selectionRequired;\n if ('selectionRequired' in base.prototype) { super.selectionRequired = selectionRequired; }\n trackSelectedItem(this);\n }\n\n /**\n * True if selection navigations wrap from last to first, and vice versa.\n *\n * @type {boolean}\n * @default false\n */\n get selectionWraps() {\n return this[selectionWrapsSymbol];\n }\n set selectionWraps(value) {\n this[selectionWrapsSymbol] = String(value) === 'true';\n if ('selectionWraps' in base.prototype) { super.selectionWraps = value; }\n updatePossibleNavigations(this);\n }\n\n /**\n * Select the last item in the list.\n */\n selectLast() {\n if (super.selectLast) { super.selectLast(); }\n return selectIndex(this, this.items.length - 1);\n }\n\n /**\n * Select the next item in the list.\n */\n selectNext() {\n if (super.selectNext) { super.selectNext(); }\n return selectIndex(this, this.selectedIndex + 1);\n }\n\n /**\n * Select the previous item in the list.\n *\n * If the list has no selection, the last item will be selected.\n */\n selectPrevious() {\n if (super.selectPrevious) { super.selectPrevious(); }\n const newIndex = this.selectedIndex < 0 ?\n this.items.length - 1 : // No selection yet; select last item.\n this.selectedIndex - 1;\n return selectIndex(this, newIndex);\n }\n\n /**\n * Fires when the selectedItem property changes.\n *\n * @memberof SingleSelection\n * @event selected-item-changed\n * @param {HTMLElement} detail.selectedItem The new selected item.\n * @param {HTMLElement} detail.previousItem The previously selected item.\n */\n\n /**\n * Fires when the selectedIndex property changes.\n *\n * @memberof SingleSelection\n * @event selected-index-changed\n * @param {number} detail.selectedIndex The new selected index.\n */\n\n }\n\n return SingleSelection;\n};\n\n\n// Ensure the given index is within bounds, and select it if it's not already\n// selected.\nfunction selectIndex(element, index) {\n const count = element.items.length;\n\n const boundedIndex = (element.selectionWraps) ?\n // JavaScript mod doesn't handle negative numbers the way we want to wrap.\n // See http://stackoverflow.com/a/18618250/76472\n ((index % count) + count) % count :\n\n // Keep index within bounds of array.\n Math.max(Math.min(index, count - 1), 0);\n\n const previousIndex = element.selectedIndex;\n if (previousIndex !== boundedIndex) {\n element.selectedIndex = boundedIndex;\n return true;\n } else {\n return false;\n }\n}\n\n// Following a change in the set of items, or in the value of the\n// `selectionRequired` property, reacquire the selected item. If it's moved,\n// update `selectedIndex`. If it's been removed, and a selection is required,\n// try to select another item.\nfunction trackSelectedItem(element) {\n\n const items = element.items;\n const itemCount = items ? items.length : 0;\n\n const previousSelectedItem = element.selectedItem;\n if (!previousSelectedItem) {\n // No item was previously selected.\n if (element.selectionRequired) {\n // Select the first item by default.\n element.selectedIndex = 0;\n }\n } else if (itemCount === 0) {\n // We've lost the selection, and there's nothing left to select.\n element.selectedItem = null;\n } else {\n // Try to find the previously-selected item in the current set of items.\n const indexInCurrentItems = Array.prototype.indexOf.call(items, previousSelectedItem);\n const previousSelectedIndex = element.selectedIndex;\n if (indexInCurrentItems < 0) {\n // Previously-selected item was removed from the items.\n // Select the item at the same index (if it exists) or as close as possible.\n const newSelectedIndex = Math.min(previousSelectedIndex, itemCount - 1);\n // Select by item, since index may be the same, and we want to raise the\n // selected-item-changed event.\n element.selectedItem = items[newSelectedIndex];\n } else if (indexInCurrentItems !== previousSelectedIndex) {\n // Previously-selected item still there, but changed position.\n element.selectedIndex = indexInCurrentItems;\n }\n }\n}\n\n// Following a change in selection, report whether it's now possible to\n// go next/previous from the given index.\nfunction updatePossibleNavigations(element) {\n let canSelectNext;\n let canSelectPrevious;\n const items = element.items;\n if (items == null || items.length === 0) {\n // No items to select.\n canSelectNext = false;\n canSelectPrevious = false;\n } if (element.selectionWraps) {\n // Since there are items, can always go next/previous.\n canSelectNext = true;\n canSelectPrevious = true;\n } else {\n const index = element.selectedIndex;\n if (index < 0 && items.length > 0) {\n // Special case. If there are items but no selection, declare that it's\n // always possible to go next/previous to create a selection.\n canSelectNext = true;\n canSelectPrevious = true;\n } else {\n // Normal case: we have an index in a list that has items.\n canSelectPrevious = (index > 0);\n canSelectNext = (index < items.length - 1);\n }\n }\n if (element.canSelectNext !== canSelectNext) {\n element.canSelectNext = canSelectNext;\n }\n if (element.canSelectPrevious !== canSelectPrevious) {\n element.canSelectPrevious = canSelectPrevious;\n }\n}\n","import createSymbol from './createSymbol';\nimport symbols from './symbols';\n\n\nconst playingSymbol = createSymbol('playing');\nconst selectionTimerDurationSymbol = createSymbol('selectionTimerDuration');\nconst timerTimeoutSymbol = createSymbol('timerTimeout');\n\n\n/* Exported function extends a base class with TimerSelection. */\nexport default (base) => {\n\n /**\n * Mixin which provides for automatic timed changes in selection.\n *\n * This mixin is useful for creating slideshow-like elements such as\n * [basic-slideshow](../../basic-slideshow) and\n * [basic-slideshow-with-controls](../../basic-slideshow-with-controls).\n *\n * Typical usage:\n *\n * class CarouselWithTimer extends TimerSelectionMixin(Carousel) {}\n * customElements.define('carousel-with-arrows', CarouselWithTimer);\n *\n * This mixin expects the component to define an `items` property, as well as\n * `selectFirst` and `selectNext` methods. You can implement those yourself,\n * or use [ContentItemsMixin](ContentItemsMixin.md) and\n * [SingleSelectionMixin](SingleSelectionMixin.md).\n */\n class TimerSelection extends base {\n\n constructor() {\n super();\n // Set defaults.\n if (typeof this.playing === 'undefined') {\n this.playing = this[symbols.defaults].playing;\n }\n if (typeof this.selectionTimerDuration === 'undefined') {\n this.selectionTimerDuration = this[symbols.defaults].selectionTimerDuration;\n }\n }\n\n contentChanged() {\n if (super.contentChanged) { super.contentChanged(); }\n restartTimer(this);\n }\n\n get [symbols.defaults]() {\n const defaults = super[symbols.defaults] || {};\n defaults.playing = false;\n defaults.selectionTimerDuration = 1000;\n return defaults;\n }\n\n /**\n * Begin automatic progression of the selection.\n */\n play() {\n if (super.play) { super.play(); }\n startTimer(this);\n this[playingSymbol] = true;\n }\n\n /**\n * Pause automatic progression of the selection.\n */\n pause() {\n if (super.pause) { super.pause(); }\n clearTimer(this);\n this[playingSymbol] = false;\n }\n\n /**\n * True if the selection is being automatically advanced.\n *\n * @type {boolean}\n * @default false\n */\n get playing() {\n return this[playingSymbol];\n }\n set playing(playing) {\n const previousPlaying = this[playingSymbol];\n const parsed = String(playing) === 'true'; // Cast to boolean\n if ('playing' in base.prototype) { super.playing = playing; }\n if (parsed !== previousPlaying) {\n if (playing) {\n this.play();\n } else {\n this.pause();\n }\n }\n }\n\n /*\n * When the selected item changes (because of something this mixin did, or\n * was changed by an outside agent like the user), we wait before advancing\n * to the next item. By triggering the next item this way, we implicitly get\n * a desirable behavior: if the user changes the selection (e.g., in a\n * carousel), we let them see that selection state for a while before\n * advancing the selection ourselves.\n */\n get selectedItem() {\n return super.selectedItem;\n }\n set selectedItem(item) {\n if ('selectedItem' in base.prototype) { super.selectedItem = item; }\n restartTimer(this);\n }\n\n /**\n * The time in milliseconds that will elapse after the selection changes\n * before the selection will be advanced to the next item in the list.\n *\n * @type {number} - Time in milliseconds\n * @default 1000 (1 second)\n */\n get selectionTimerDuration() {\n return this[selectionTimerDurationSymbol];\n }\n set selectionTimerDuration(value) {\n this[selectionTimerDurationSymbol] = parseInt(value);\n if ('selectionTimerDuration' in base.prototype) { super.selectionTimerDuration = value; }\n }\n\n }\n\n return TimerSelection;\n};\n\n\nfunction clearTimer(element) {\n if (element[timerTimeoutSymbol]) {\n clearTimeout(element[timerTimeoutSymbol]);\n element[timerTimeoutSymbol] = null;\n }\n}\n\nfunction restartTimer(element) {\n clearTimer(element);\n if (element.playing && element.items && element.items.length > 0) {\n startTimer(element);\n }\n}\n\nfunction startTimer(element) {\n // If play() is called more than once, cancel any existing timer.\n clearTimer(element);\n element[timerTimeoutSymbol] = setTimeout(() => {\n selectNextWithWrap(element);\n }, element.selectionTimerDuration);\n}\n\n// Select the next item, wrapping to first item if necessary.\nfunction selectNextWithWrap(element) {\n const items = element.items;\n if (items && items.length > 0) {\n if (element.selectedIndex == null || element.selectedIndex === items.length - 1) {\n element.selectFirst();\n } else {\n element.selectNext();\n }\n }\n}\n","/**\n * Helper function to create a symbol that can be used for associating private\n * data with an element.\n *\n * Mixins and component classes often want to associate private data with an\n * element instance, but JavaScript does not have direct support for true\n * private properties. One approach is to use the\n * [Symbol](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Symbol)\n * data type to set and retrieve data on an element.\n *\n * Unfortunately, the Symbol type is not available in Internet Explorer 11. The\n * `createSymbol` helper function exists as a workaround for IE 11. Rather than\n * returning a true Symbol, it simply returns an underscore-prefixed string.\n *\n * Usage:\n *\n * const fooSymbol = createSymbol('foo');\n *\n * class MyElement extends HTMLElement {\n * get foo() {\n * return this[fooSymbol];\n * }\n * set foo(value) {\n * this[fooSymbol] = value;\n * }\n * }\n *\n * In IE 11, this sample will \"hide\" data behind an instance property this._foo.\n * The use of the underscore is meant to reduce (not eliminate) the potential\n * for name conflicts, and discourage (not prevent) external access to this\n * data. In modern browsers, the above code will eliminate the potential of\n * naming conflicts, and better hide the data behind a real Symbol.\n *\n * @function createSymbol\n * @param {string} description - A string to identify the symbol when debugging\n */\nexport default function createSymbol(description) {\n return typeof Symbol === 'function' ?\n Symbol(description) :\n `_${description}`;\n}\n","/*\n * Microtask helper for IE 11.\n *\n * Executing a function as a microtask is trivial in browsers that support\n * promises, whose then() clauses use microtask timing. IE 11 doesn't support\n * promises, but does support MutationObservers, which are also executed as\n * microtasks. So this helper uses an MutationObserver to achieve microtask\n * timing.\n *\n * See https://jakearchibald.com/2015/tasks-microtasks-queues-and-schedules/\n *\n * Inspired by Polymer's async() function.\n */\n\n\n// The queue of pending callbacks to be executed as microtasks.\nconst callbacks = [];\n\n// Create an element that we will modify to force observable mutations.\nconst element = document.createTextNode('');\n\n// A monotonically-increasing value.\nlet counter = 0;\n\n\n/**\n * Add a callback to the microtask queue.\n *\n * This uses a MutationObserver so that it works on IE 11.\n *\n * NOTE: IE 11 may actually use timeout timing with MutationObservers. This\n * needs more investigation.\n *\n * @function microtask\n * @param {function} callback\n */\nexport default function microtask(callback) {\n callbacks.push(callback);\n // Force a mutation.\n element.textContent = ++counter;\n}\n\n\n// Execute any pending callbacks.\nfunction executeCallbacks() {\n while (callbacks.length > 0) {\n const callback = callbacks.shift();\n callback();\n }\n}\n\n\n// Create the observer.\nconst observer = new MutationObserver(executeCallbacks);\nobserver.observe(element, {\n characterData: true\n});\n","import createSymbol from './createSymbol';\nimport toggleClass from './toggleClass';\n\n\n// Symbols for private data members on an element.\nconst safeToSetAttributesSymbol = createSymbol('safeToSetAttributes');\nconst pendingAttributesSymbol = createSymbol('pendingAttributes');\nconst pendingClassesSymbol = createSymbol('pendingClasses');\n\n\n/**\n * Helper functions for updating attributes, including the `class` attribute.\n */\nexport default {\n\n /**\n * Perform any pending updates to attributes and classes.\n *\n * This writes any `setAttribute` or `toggleClass` values that were performed\n * before an element was attached to the document for the first time.\n *\n * This method should be called by mixins/components in their\n * `connectedCallback`. If mulitple mixins/components invoke this during the\n * same `connectedCallback`, only the first call will have any effect. The\n * subsequent calls will be harmless.\n *\n * @param {HTMLElement} element - The element being added to the document.\n */\n connected(element) {\n element[safeToSetAttributesSymbol] = true;\n\n // Set any pending attributes.\n if (element[pendingAttributesSymbol]) {\n for (let attribute in element[pendingAttributesSymbol]) {\n const value = element[pendingAttributesSymbol][attribute];\n setAttributeToElement(element, attribute, value);\n }\n element[pendingAttributesSymbol] = null;\n }\n\n // Set any pending classes.\n if (element[pendingClassesSymbol]) {\n for (let className in element[pendingClassesSymbol]) {\n const value = element[pendingClassesSymbol][className];\n toggleClass(element, className, value);\n }\n element[pendingClassesSymbol] = null;\n }\n },\n\n /**\n * Set/unset the attribute with the indicated name.\n *\n * This method exists primarily to handle the case where an element wants to\n * set a default property value that should be reflected as an attribute. An\n * important limitation of custom element consturctors is that they cannot\n * set attributes. A call to `setAttribute` during the constructor will\n * be deferred until the element is connected to the document.\n *\n * @param {string} attribute - The name of the *attribute* (not property) to set.\n * @param {object} value - The value to set. If null, the attribute will be removed.\n */\n setAttribute(element, attribute, value) {\n if (element[safeToSetAttributesSymbol]) {\n // Safe to set attributes immediately.\n setAttributeToElement(element, attribute, value);\n } else {\n // Defer setting attributes until the first time we're connected.\n if (!element[pendingAttributesSymbol]) {\n element[pendingAttributesSymbol] = {};\n }\n element[pendingAttributesSymbol][attribute] = value;\n }\n },\n\n /**\n * Set/unset the class with the indicated name.\n *\n * This method exists primarily to handle the case where an element wants to\n * set a default property value that should be reflected as as class. An\n * important limitation of custom element consturctors is that they cannot\n * set attributes, including the `class` attribute. A call to\n * `toggleClass` during the constructor will be deferred until the element\n * is connected to the document.\n *\n * @param {string} className - The name of the class to set.\n * @param {object} value - True to set the class, false to remove it.\n */\n toggleClass(element, className, value) {\n if (element[safeToSetAttributesSymbol]) {\n // Safe to set class immediately.\n toggleClass(element, className, value);\n } else {\n // Defer setting class until the first time we're connected.\n if (!element[pendingClassesSymbol]) {\n element[pendingClassesSymbol] = {};\n }\n element[pendingClassesSymbol][className] = value;\n }\n }\n\n};\n\n\n// Reflect the attribute to the given element.\n// If the value is null, remove the attribute.\nfunction setAttributeToElement(element, attributeName, value) {\n if (value === null || typeof value === 'undefined') {\n element.removeAttribute(attributeName);\n } else {\n const text = String(value);\n // Avoid recursive attributeChangedCallback calls.\n if (element.getAttribute(attributeName) !== text) {\n element.setAttribute(attributeName, value);\n }\n }\n}\n","import createSymbol from './createSymbol';\n\n/**\n * A collection of Symbol objects for standard component properties and methods.\n *\n * These Symbol objects are used to allow mixins and a component to internally\n * communicate, without exposing these properties and methods in the component's\n * public API.\n *\n * To use these Symbol objects in your own component, include this module and\n * then create a property or method whose key is the desired Symbol.\n *\n * import 'SingleSelectionMixin' from 'basic-component-mixins/src/SingleSelectionMixin';\n * import 'symbols' from 'basic-component-mixins/src/symbols';\n *\n * class MyElement extends SingleSelectionMixin(HTMLElement) {\n * [symbols.itemSelected](item, selected) {\n * // This will be invoked whenever an item is selected/deselected.\n * }\n * }\n *\n * @module symbols\n */\nconst symbols = {\n\n /**\n * Symbol for the `defaults` property.\n *\n * This property can be used to set or override defaults that will be applied\n * to a new component instance. When implementing this property, take care to\n * first acquire any defaults defined by the superclass. The standard idiom is\n * as follows:\n *\n * get [symbols.defaults]() {\n * const defaults = super[symbols.defaults] || {};\n * // Set or override default values here\n * defaults.customProperty = false;\n * return defaults;\n * }\n *\n * @var {object} defaults\n */\n defaults: createSymbol('defaults'),\n\n /**\n * Symbol for the `dragging` property.\n *\n * Components like carousels often define animated CSS transitions for\n * sliding effects. Such a transition should usually *not* be applied while\n * the user is dragging, because a CSS animation will introduce a lag that\n * makes the swipe feel sluggish. Instead, as long as the user is dragging\n * with their finger down, the transition should be suppressed. When the\n * user releases their finger, the transition can be restored, allowing the\n * animation to show the carousel sliding into its final position.\n *\n * @type {boolean} true if a drag is in progress, false if not.\n */\n dragging: createSymbol('dragging'),\n\n /**\n * Symbol for the `goDown` method.\n *\n * This method is invoked when the user wants to go/navigate down.\n *\n * @function goDown\n */\n goDown: createSymbol('goDown'),\n\n /**\n * Symbol for the `goEnd` method.\n *\n * This method is invoked when the user wants to go/navigate to the end (e.g.,\n * of a list).\n *\n * @function goEnd\n */\n goEnd: createSymbol('goEnd'),\n\n /**\n * Symbol for the `goLeft` method.\n *\n * This method is invoked when the user wants to go/navigate left.\n *\n * @function goLeft\n */\n goLeft: createSymbol('goLeft'),\n\n /**\n * Symbol for the `goRight` method.\n *\n * This method is invoked when the user wants to go/navigate right.\n *\n * @function goRight\n */\n goRight: createSymbol('goRight'),\n\n /**\n * Symbol for the `goStart` method.\n *\n * This method is invoked when the user wants to go/navigate to the start\n * (e.g., of a list).\n *\n * @function goStart\n */\n goStart: createSymbol('goStart'),\n\n /**\n * Symbol for the `goUp` method.\n *\n * This method is invoked when the user wants to go/navigate up.\n *\n * @function goUp\n */\n goUp: createSymbol('goUp'),\n\n /**\n * Symbol for the `itemAdded` method.\n *\n * This method is invoked when a new item is added to a list.\n *\n * @function itemAdded\n * @param {HTMLElement} item - the item being selected/deselected\n */\n itemAdded: createSymbol('itemAdded'),\n\n\n /**\n * Symbol for the `itemsChanged` method.\n *\n * This method is invoked when the underlying contents change. It is also\n * invoked on component initialization – since the items have \"changed\" from\n * being nothing.\n */\n itemsChanged: createSymbol('itemsChanged'),\n\n /**\n * Symbol for the `itemSelected` method.\n *\n * This method is invoked when an item becomes selected or deselected.\n *\n * @function itemSelected\n * @param {HTMLElement} item - the item being selected/deselected\n * @param {boolean} selected - true if the item is selected, false if not\n */\n itemSelected: createSymbol('itemSelected'),\n\n /**\n * Symbol for the `keydown` method.\n *\n * This method is invoked when an element receives a `keydown` event.\n *\n * @function keydown\n * @param {KeyboardEvent} event - the event being processed\n */\n keydown: createSymbol('keydown'),\n\n /**\n * Symbol for the `template` property.\n *\n * This property returns a component's template.\n *\n * @type {string|HTMLElement}\n */\n template: createSymbol('template')\n};\n\nexport default symbols;\n","/**\n * Helper function for standard classList.toggle() behavior on old browsers,\n * namely IE 11.\n *\n * The standard\n * [classlist](https://developer.mozilla.org/en-US/docs/Web/API/Element/classList)\n * object has a `toggle()` function that supports a second Boolean parameter\n * that can be used to succinctly turn a class on or off. This feature is often\n * useful in designing custom elements, which may want to externally reflect\n * component state in a CSS class that can be used for styling purposes.\n *\n * Unfortunately, IE 11 does not support the Boolean parameter to\n * `classList.toggle()`. This helper function behaves like the standard\n * `toggle()`, including support for the Boolean parameter, so that it can be\n * used even on IE 11.\n *\n * @function toggleClass\n * @param {HTMLElement} element - The element to modify\n * @param {string} className - The class to add/remove\n * @param {boolean} [force] - Force the class to be added (if true) or removed\n * (if false)\n */\nexport default function toggleClass(element, className, force) {\n const classList = element.classList;\n const addClass = (typeof force === 'undefined') ?\n !classList.contains(className) :\n force;\n if (addClass) {\n classList.add(className);\n } else {\n classList.remove(className);\n }\n return addClass;\n}\n","import AttributeMarshallingMixin from '../../basic-component-mixins/src/AttributeMarshallingMixin';\nimport ComposableMixin from '../../basic-component-mixins/src/ComposableMixin';\nimport DistributedChildrenMixin from '../../basic-component-mixins/src/DistributedChildrenMixin';\nimport ShadowElementReferencesMixin from '../../basic-component-mixins/src/ShadowElementReferencesMixin';\nimport ShadowTemplateMixin from '../../basic-component-mixins/src/ShadowTemplateMixin';\n\n\n/**\n * A sample general-purpose base class for defining custom elements that mixes\n * in some common features: template stamping into a shadow root, shadow element\n * references, marshalling attributes to properties, and retrieving the children\n * distributed to a component.\n *\n * This base class is not special in any way, and is defined only as a\n * convenient shorthand for applying the mixins listed above. You can use this\n * class as a base class for your own elements, or easily create your own base\n * class by applying the same set of mixins.\n *\n * The ElementBase base class does not register itself as a custom element with\n * the browser, and hence cannot be independently instantiated.\n *\n * @mixes AttributeMarshallingMixin\n * @mixes ComposableMixin\n * @mixes DistributedChildrenMixin\n * @mixes ShadowElementReferencesMixin\n * @mixes ShadowTemplateMixin\n */\nclass ElementBase extends ComposableMixin(HTMLElement).compose(\n ShadowTemplateMixin, // before node finding, so shadow root is populated\n ShadowElementReferencesMixin, // before marshalling, so properties can use refs\n AttributeMarshallingMixin,\n DistributedChildrenMixin\n) {}\n\nexport default ElementBase;\n","/*\n * This file is transpiled to create an ES5-compatible distribution in which\n * the package's main feature(s) are available via the window.Basic global.\n * If you're already using ES6 yourself, ignore this file, and instead import\n * the source file(s) you want from the src folder.\n */\n\nimport SlideshowWithControls from './src/SlideshowWithControls';\n\nwindow.Basic = window.Basic || {};\nwindow.Basic.SlideshowWithControls = SlideshowWithControls;\n","import Slideshow from '../../basic-slideshow/src/Slideshow';\nimport PlayControlsMixin from '../../basic-component-mixins/src/PlayControlsMixin';\n\n/**\n * An extension of\n * [basic-slideshow](../basic-slideshow) that adds play controls\n * via [PlayControlsMixin](../basic-component-mixins/docs/PlayControlsMixin.md).\n *\n * [Live demo](http://basicwebcomponents.org/basic-web-components/packages/basic-slideshow-with-controls/)\n *\n * @extends Slideshow\n * @mixes PlayControlsMixin\n */\nclass SlideshowWithControls extends PlayControlsMixin(Slideshow) {}\ncustomElements.define('basic-slideshow-with-controls', SlideshowWithControls);\n\nexport default SlideshowWithControls;\n","import AnimationStage from '../../basic-animation-stage/src/AnimationStage';\nimport symbols from '../../basic-component-mixins/src/symbols';\nimport TimerSelectionMixin from '../../basic-component-mixins/src/TimerSelectionMixin';\n\n\nconst base = AnimationStage.compose(\n TimerSelectionMixin\n);\n\n\n/**\n * Slideshow with animated transitions.\n *\n * [Live demo](http://basicwebcomponents.org/basic-web-components/packages/basic-slideshow/)\n *\n * By default the slideshow will immediately begin playing when it is connected\n * to the document, advance every 3000 ms (3 seconds), and use a simple\n * crossfade effect. For a variation with play controls, see\n * [basic-slideshow-with-controls](../basic-slideshow-with-controls).\n *\n * This component can be used on its own. To incorporate slideshow behavior into\n * a component of your own, apply the\n * [TimerSelectionMixin](../basic-component-mixins/docs/TimerSelectionMixin.md).\n *\n * @extends AnimationStage\n * @mixes TimerSelectionMixin\n */\nclass Slideshow extends base {\n\n get [symbols.defaults]() {\n const defaults = super[symbols.defaults] || {};\n defaults.playing = true;\n defaults.selectionAnimationDuration = 500;\n defaults.selectionAnimationEffect = 'crossfade';\n defaults.selectionRequired = true;\n defaults.selectionTimerDuration = 3000;\n defaults.selectionWraps = true;\n return defaults;\n }\n\n}\n\n\ncustomElements.define('basic-slideshow', Slideshow);\nexport default Slideshow;\n"]}
\ No newline at end of file
diff --git a/packages/basic-slideshow-with-controls/index.html b/packages/basic-slideshow-with-controls/index.html
index 7525e3c8..7a3ee4c6 100644
--- a/packages/basic-slideshow-with-controls/index.html
+++ b/packages/basic-slideshow-with-controls/index.html
@@ -8,7 +8,8 @@
-
+
+
diff --git a/packages/basic-slideshow/README.md b/packages/basic-slideshow/README.md
index d7339924..286b40a3 100644
--- a/packages/basic-slideshow/README.md
+++ b/packages/basic-slideshow/README.md
@@ -1,179 +1,30 @@
# API Documentation
-## Slideshow ⇐ ElementBase
+## Slideshow ⇐ AnimationStage
Slideshow with animated transitions.
+[Live demo](http://basicwebcomponents.org/basic-web-components/packages/basic-slideshow/)
+
By default the slideshow will immediately begin playing when it is connected
to the document, advance every 3000 ms (3 seconds), and use a simple
-crossfade effect.
+crossfade effect. For a variation with play controls, see
+[basic-slideshow-with-controls](../basic-slideshow-with-controls).
This component can be used on its own. To incorporate slideshow behavior into
a component of your own, apply the
[TimerSelectionMixin](../basic-component-mixins/docs/TimerSelectionMixin.md).
**Kind**: global class
-**Extends:** ElementBase
-**Mixes**: [ContentItemsMixin](../basic-component-mixins/docs/ContentItemsMixin.md)
- , [DistributedChildrenContentMixin](../basic-component-mixins/docs/DistributedChildrenContentMixin.md)
- , [FractionalSelectionMixin](../basic-component-mixins/docs/FractionalSelectionMixin.md)
- , [SelectionAnimationMixin](../basic-component-mixins/docs/SelectionAnimationMixin.md)
- , [SelectionAriaActiveMixin](../basic-component-mixins/docs/SelectionAriaActiveMixin.md)
- , [SingleSelectionMixin](../basic-component-mixins/docs/SingleSelectionMixin.md)
- , [TimerSelectionMixin](../basic-component-mixins/docs/TimerSelectionMixin.md)
+**Extends:** AnimationStage
+**Mixes**: [TimerSelectionMixin](../basic-component-mixins/docs/TimerSelectionMixin.md)
-* [Slideshow](#Slideshow) ⇐ ElementBase
- * [.canSelectNext](#SingleSelection+canSelectNext) : boolean
- * [.canSelectPrevious](#SingleSelection+canSelectPrevious) : boolean
- * [.content](#DistributedChildrenContent+content) : Array.<HTMLElement>
- * ["content-changed"](#DistributedChildrenContent.event_content-changed)
- * [.contentChanged()](#DistributedChildrenContent+contentChanged)
- * [.itemAdded(item)](#ContentItems+symbols.itemAdded)
- * [.itemAdded(item)](#SingleSelection+symbols.itemAdded)
- * [.items](#ContentItems+items) : Array.<HTMLElement>
- * ["items-changed"](#ContentItems.event_items-changed)
- * [.itemsChanged()](#ContentItems+symbols.itemsChanged)
- * [.itemSelected(item, selected)](#SingleSelection+symbols.itemSelected)
- * [.itemSelected(item, selected)](#ContentItems+symbols.itemSelected)
+* [Slideshow](#Slideshow) ⇐ AnimationStage
* [.pause()](#TimerSelection+pause)
* [.play()](#TimerSelection+play)
* [.playing](#TimerSelection+playing) : boolean
- * ["selected-index-changed"](#SingleSelection.event_selected-index-changed)
- * ["selected-item-changed"](#SingleSelection.event_selected-item-changed)
- * [.selectedFraction](#FractionalSelection+selectedFraction) : number
- * [.selectedFraction](#SelectionAnimation+selectedFraction) : number
- * [.selectedIndex](#SingleSelection+selectedIndex) : number
- * [.selectedItem](#SingleSelection+selectedItem) : object
- * [.selectFirst()](#SingleSelection+selectFirst)
- * [.selectionAnimationDuration](#SelectionAnimation+selectionAnimationDuration) : number
- * [.selectionAnimationEffect](#SelectionAnimation+selectionAnimationEffect) : string
- * [.selectionAnimationKeyframes](#SelectionAnimation+selectionAnimationKeyframes) : Array.<cssRules>
- * [.selectionRequired](#SingleSelection+selectionRequired) : boolean
* [.selectionTimerDuration](#TimerSelection+selectionTimerDuration) : number
- * [.selectionWraps](#SingleSelection+selectionWraps) : boolean
- * [.selectLast()](#SingleSelection+selectLast)
- * [.selectNext()](#SingleSelection+selectNext)
- * [.selectPrevious()](#SingleSelection+selectPrevious)
-
-
-
-### slideshow.canSelectNext : boolean
-True if the selection can be moved to the next item, false if not (the
-selected item is the last item in the list).
-
- **Kind**: instance property of [Slideshow](#Slideshow). Defined by [SingleSelection](../basic-component-mixins/docs/SingleSelection.md) mixin.
-
-
-### slideshow.canSelectPrevious : boolean
-True if the selection can be moved to the previous item, false if not
-(the selected item is the first one in the list).
-
- **Kind**: instance property of [Slideshow](#Slideshow). Defined by [SingleSelection](../basic-component-mixins/docs/SingleSelection.md) mixin.
-
-
-### slideshow.content : Array.<HTMLElement>
-The content of this component, defined to be the flattened array of
-children distributed to the component.
-
- **Kind**: instance property of [Slideshow](#Slideshow). Defined by [DistributedChildrenContent](../basic-component-mixins/docs/DistributedChildrenContent.md) mixin.
-
-
-### "content-changed"
-This event is raised when the component's contents (including distributed
-children) have changed.
-
- **Kind**: event emitted by [Slideshow](#Slideshow). Defined by [DistributedChildrenContent](../basic-component-mixins/docs/DistributedChildrenContent.md) mixin.
-
-
-### slideshow.contentChanged()
-Invoked when the contents of the component (including distributed
-children) have changed.
-
-This method is also invoked when a component is first instantiated; the
-contents have essentially "changed" from being nothing. This allows the
-component to perform initial processing of its children.
-
- **Kind**: instance method of [Slideshow](#Slideshow). Defined by [DistributedChildrenContent](../basic-component-mixins/docs/DistributedChildrenContent.md) mixin.
-
-
-### Slideshow.itemAdded(item)
-This method is invoked whenever a new item is added to the list.
-
-The default implementation of this method does nothing. You can override
-this to perform per-item initialization.
-
- **Kind**: static method of [Slideshow](#Slideshow). Defined by [ContentItems#symbols](../basic-component-mixins/docs/ContentItems#symbols.md) mixin.
-
-| Param | Type | Description |
-| --- | --- | --- |
-| item | HTMLElement | The item that was added. |
-
-
-
-### Slideshow.itemAdded(item)
-Handle a new item being added to the list.
-
-The default implementation of this method simply sets the item's
-selection state to false.
-
- **Kind**: static method of [Slideshow](#Slideshow). Defined by [SingleSelection#symbols](../basic-component-mixins/docs/SingleSelection#symbols.md) mixin.
-
-| Param | Type | Description |
-| --- | --- | --- |
-| item | HTMLElement | the item being added |
-
-
-
-### slideshow.items : Array.<HTMLElement>
-The current set of items in the list. See the top-level documentation for
-mixin for a description of how items differ from plain content.
-
- **Kind**: instance property of [Slideshow](#Slideshow). Defined by [ContentItems](../basic-component-mixins/docs/ContentItems.md) mixin.
-
-
-### "items-changed"
-Fires when the items in the list change.
-
- **Kind**: event emitted by [Slideshow](#Slideshow). Defined by [ContentItems](../basic-component-mixins/docs/ContentItems.md) mixin.
-
-
-### Slideshow.itemsChanged()
-This method is invoked when the underlying contents change. It is also
-invoked on component initialization – since the items have "changed" from
-being nothing.
-
- **Kind**: static method of [Slideshow](#Slideshow). Defined by [ContentItems#symbols](../basic-component-mixins/docs/ContentItems#symbols.md) mixin.
-
-
-### Slideshow.itemSelected(item, selected)
-Apply the indicate selection state to the item.
-
-The default implementation of this method does nothing. User-visible
-effects will typically be handled by other mixins.
-
- **Kind**: static method of [Slideshow](#Slideshow). Defined by [SingleSelection#symbols](../basic-component-mixins/docs/SingleSelection#symbols.md) mixin.
-
-| Param | Type | Description |
-| --- | --- | --- |
-| item | HTMLElement | the item being selected/deselected |
-| selected | boolean | true if the item is selected, false if not |
-
-
-
-### Slideshow.itemSelected(item, selected)
-The selection state for a single item has changed.
-
-Invoke this method to signal that the selected state of the indicated item
-has changed. By default, this applies a `selected` CSS class if the item
-is selected, and removed it if not selected.
-
- **Kind**: static method of [Slideshow](#Slideshow). Defined by [ContentItems#symbols](../basic-component-mixins/docs/ContentItems#symbols.md) mixin.
-
-| Param | Type | Description |
-| --- | --- | --- |
-| item | HTMLElement | The item whose selection state has changed. |
-| selected | boolean | True if the item is selected, false if not. |
@@ -194,135 +45,6 @@ True if the selection is being automatically advanced.
**Kind**: instance property of [Slideshow](#Slideshow). Defined by [TimerSelection](../basic-component-mixins/docs/TimerSelection.md) mixin.
**Default**: false
-
-
-### "selected-index-changed"
-Fires when the selectedIndex property changes.
-
- **Kind**: event emitted by [Slideshow](#Slideshow). Defined by [SingleSelection](../basic-component-mixins/docs/SingleSelection.md) mixin.
-
-| Param | Type | Description |
-| --- | --- | --- |
-| detail.selectedIndex | number | The new selected index. |
-
-
-
-### "selected-item-changed"
-Fires when the selectedItem property changes.
-
- **Kind**: event emitted by [Slideshow](#Slideshow). Defined by [SingleSelection](../basic-component-mixins/docs/SingleSelection.md) mixin.
-
-| Param | Type | Description |
-| --- | --- | --- |
-| detail.selectedItem | HTMLElement | The new selected item. |
-| detail.previousItem | HTMLElement | The previously selected item. |
-
-
-
-### slideshow.selectedFraction : number
-A fractional value indicating how far the user has currently advanced to
-the next/previous item. E.g., a `selectedFraction` of 3.5 indicates the
-user is halfway between items 3 and 4.
-
- **Kind**: instance property of [Slideshow](#Slideshow). Defined by [FractionalSelection](../basic-component-mixins/docs/FractionalSelection.md) mixin.
-
-
-### slideshow.selectedFraction : number
-A fractional value indicating how far the user has currently advanced to
-the next/previous item. E.g., a `selectedFraction` of 3.5 indicates the
-user is halfway between items 3 and 4.
-
-For more details, see [FractionalSelectionMixin](FractionalSelectionMixin.md)
-mixin.
-
- **Kind**: instance property of [Slideshow](#Slideshow). Defined by [SelectionAnimation](../basic-component-mixins/docs/SelectionAnimation.md) mixin.
-
-
-### slideshow.selectedIndex : number
-The index of the item which is currently selected.
-
-A `selectedIndex` of -1 indicates there is no selection. Setting this
-property to -1 will remove any existing selection.
-
- **Kind**: instance property of [Slideshow](#Slideshow). Defined by [SingleSelection](../basic-component-mixins/docs/SingleSelection.md) mixin.
-
-
-### slideshow.selectedItem : object
-The currently selected item, or null if there is no selection.
-
-Setting this property to null deselects any currently-selected item.
-Setting this property to an object that is not in the list has no effect.
-
-TODO: Even if selectionRequired, can still explicitly set selectedItem to null.
-TODO: If selectionRequired, leave selection alone?
-
- **Kind**: instance property of [Slideshow](#Slideshow). Defined by [SingleSelection](../basic-component-mixins/docs/SingleSelection.md) mixin.
-
-
-### slideshow.selectFirst()
-Select the first item in the list.
-
- **Kind**: instance method of [Slideshow](#Slideshow). Defined by [SingleSelection](../basic-component-mixins/docs/SingleSelection.md) mixin.
-
-
-### slideshow.selectionAnimationDuration : number
-The duration of a selection animation in milliseconds.
-
-This measures the amount of time required for a selection animation to
-complete. This number remains constant, even if the number of items being
-animated increases.
-
-The default value is 250 milliseconds (a quarter a second).
-
- **Kind**: instance property of [Slideshow](#Slideshow). Defined by [SelectionAnimation](../basic-component-mixins/docs/SelectionAnimation.md) mixin.
-**Default**: 250
-
-
-### slideshow.selectionAnimationEffect : string
-The name of a standard selection animation effect.
-
-This is a shorthand for setting the `selectionAnimationKeyframes`
-property to standard keyframes. Supported string values:
-
-* "crossfade"
-* "reveal"
-* "revealWithFade"
-* "showAdjacent"
-* "slide"
-* "slideWithGap"
-
- **Kind**: instance property of [Slideshow](#Slideshow). Defined by [SelectionAnimation](../basic-component-mixins/docs/SelectionAnimation.md) mixin.
-**Default**: "\"slide\""
-
-
-### slideshow.selectionAnimationKeyframes : Array.<cssRules>
-The keyframes that define an animation that plays for an item when moving
-forward in the sequence.
-
-This is an array of CSS rules that will be applied. These are used as
-[keyframes](http://w3c.github.io/web-animations/#keyframes-section)
-to animate the item with the
-[Web Animations API](https://developer.mozilla.org/en-US/docs/Web/API/animation).
-
-The animation represents the state of the next item as it moves from
-completely unselected (offstage, usually right), to selected (center
-stage), to completely unselected (offstage, usually left). The center time
-of the animation should correspond to the item's quiscent selected state,
-typically in the center of the stage and at the item's largest size.
-
-The default forward animation is a smooth slide at full size from right to
-left.
-
-When moving the selection backward, this animation is played in reverse.
-
- **Kind**: instance property of [Slideshow](#Slideshow). Defined by [SelectionAnimation](../basic-component-mixins/docs/SelectionAnimation.md) mixin.
-
-
-### slideshow.selectionRequired : boolean
-True if the list should always have a selection (if it has items).
-
- **Kind**: instance property of [Slideshow](#Slideshow). Defined by [SingleSelection](../basic-component-mixins/docs/SingleSelection.md) mixin.
-**Default**: false
### slideshow.selectionTimerDuration : number
@@ -331,30 +53,3 @@ before the selection will be advanced to the next item in the list.
**Kind**: instance property of [Slideshow](#Slideshow). Defined by [TimerSelection](../basic-component-mixins/docs/TimerSelection.md) mixin.
**Default**: 1000 (1 second)
-
-
-### slideshow.selectionWraps : boolean
-True if selection navigations wrap from last to first, and vice versa.
-
- **Kind**: instance property of [Slideshow](#Slideshow). Defined by [SingleSelection](../basic-component-mixins/docs/SingleSelection.md) mixin.
-**Default**: false
-
-
-### slideshow.selectLast()
-Select the last item in the list.
-
- **Kind**: instance method of [Slideshow](#Slideshow). Defined by [SingleSelection](../basic-component-mixins/docs/SingleSelection.md) mixin.
-
-
-### slideshow.selectNext()
-Select the next item in the list.
-
- **Kind**: instance method of [Slideshow](#Slideshow). Defined by [SingleSelection](../basic-component-mixins/docs/SingleSelection.md) mixin.
-
-
-### slideshow.selectPrevious()
-Select the previous item in the list.
-
-If the list has no selection, the last item will be selected.
-
- **Kind**: instance method of [Slideshow](#Slideshow). Defined by [SingleSelection](../basic-component-mixins/docs/SingleSelection.md) mixin.
diff --git a/packages/basic-slideshow/dist/basic-slideshow.js b/packages/basic-slideshow/dist/basic-slideshow.js
index 628cf427..036d782c 100644
--- a/packages/basic-slideshow/dist/basic-slideshow.js
+++ b/packages/basic-slideshow/dist/basic-slideshow.js
@@ -1,3568 +1,3 @@
-(function e(t,n,r){function s(o,u){if(!n[o]){if(!t[o]){var a=typeof require=="function"&&require;if(!u&&a)return a(o,!0);if(i)return i(o,!0);var f=new Error("Cannot find module '"+o+"'");throw f.code="MODULE_NOT_FOUND",f}var l=n[o]={exports:{}};t[o][0].call(l.exports,function(e){var n=t[o][1][e];return s(n?n:e)},l,l.exports,e,t,n,r)}return n[o].exports}var i=typeof require=="function"&&require;for(var o=0;o
- *
- * Then, after the element has been upgraded, the `fooBar` setter will
- * automatically be invoked with the initial value "Hello".
- *
- * For the time being, this mixin only supports string-valued properties.
- * If you'd like to convert string attributes to other types (numbers,
- * booleans), you need to implement `attributeChangedCallback` yourself.
- */
- var AttributeMarshalling = function (_base) {
- _inherits(AttributeMarshalling, _base);
-
- function AttributeMarshalling() {
- _classCallCheck(this, AttributeMarshalling);
-
- return _possibleConstructorReturn(this, (AttributeMarshalling.__proto__ || Object.getPrototypeOf(AttributeMarshalling)).apply(this, arguments));
- }
-
- _createClass(AttributeMarshalling, [{
- key: 'attributeChangedCallback',
-
-
- /*
- * Handle a change to the attribute with the given name.
- */
- value: function attributeChangedCallback(attributeName, oldValue, newValue) {
- if (_get(AttributeMarshalling.prototype.__proto__ || Object.getPrototypeOf(AttributeMarshalling.prototype), 'attributeChangedCallback', this)) {
- _get(AttributeMarshalling.prototype.__proto__ || Object.getPrototypeOf(AttributeMarshalling.prototype), 'attributeChangedCallback', this).call(this);
- }
- var propertyName = attributeToPropertyName(attributeName);
- // If the attribute name corresponds to a property name, set the property.
- // Ignore standard HTMLElement properties handled by the DOM.
- if (propertyName in this && !(propertyName in HTMLElement.prototype)) {
- this[propertyName] = newValue;
- }
- }
- }, {
- key: 'connectedCallback',
- value: function connectedCallback() {
- if (_get(AttributeMarshalling.prototype.__proto__ || Object.getPrototypeOf(AttributeMarshalling.prototype), 'connectedCallback', this)) {
- _get(AttributeMarshalling.prototype.__proto__ || Object.getPrototypeOf(AttributeMarshalling.prototype), 'connectedCallback', this).call(this);
- }
- _safeAttributes2.default.connected(this);
- }
- }, {
- key: 'reflectAttribute',
-
-
- /**
- * Set/unset the attribute with the indicated name.
- *
- * This method exists primarily to handle the case where an element wants to
- * set a default property value that should be reflected as an attribute. An
- * important limitation of custom element consturctors is that they cannot
- * set attributes. A call to `reflectAttribute` during the constructor will
- * be deferred until the element is connected to the document.
- *
- * @param {string} attribute - The name of the *attribute* (not property) to set.
- * @param {object} value - The value to set. If null, the attribute will be removed.
- */
- value: function reflectAttribute(attribute, value) {
- return _safeAttributes2.default.setAttribute(this, attribute, value);
- }
-
- /**
- * Set/unset the class with the indicated name.
- *
- * This method exists primarily to handle the case where an element wants to
- * set a default property value that should be reflected as as class. An
- * important limitation of custom element consturctors is that they cannot
- * set attributes, including the `class` attribute. A call to
- * `reflectClass` during the constructor will be deferred until the element
- * is connected to the document.
- *
- * @param {string} className - The name of the class to set.
- * @param {object} value - True to set the class, false to remove it.
- */
-
- }, {
- key: 'reflectClass',
- value: function reflectClass(className, value) {
- return _safeAttributes2.default.toggleClass(this, className, value);
- }
- }], [{
- key: 'observedAttributes',
- get: function get() {
- return attributesForClass(this);
- }
- }]);
-
- return AttributeMarshalling;
- }(base);
-
- return AttributeMarshalling;
-};
-
-// Convert hyphenated foo-bar attribute name to camel case fooBar property name.
-
-
-function attributeToPropertyName(attributeName) {
- var propertyName = attributeToPropertyNames[attributeName];
- if (!propertyName) {
- // Convert and memoize.
- var hypenRegEx = /-([a-z])/g;
- propertyName = attributeName.replace(hypenRegEx, function (match) {
- return match[1].toUpperCase();
- });
- attributeToPropertyNames[attributeName] = propertyName;
- }
- return propertyName;
-}
-
-function attributesForClass(classFn) {
-
- // We treat the element base classes as if they have no attributes, since we
- // don't want to receive attributeChangedCallback for them.
- if (classFn === HTMLElement || classFn === Object) {
- return [];
- }
-
- // Get attributes for parent class.
- var baseClass = Object.getPrototypeOf(classFn.prototype).constructor;
- var baseAttributes = attributesForClass(baseClass);
-
- // Get attributes for this class.
- var propertyNames = Object.getOwnPropertyNames(classFn.prototype);
- var setterNames = propertyNames.filter(function (propertyName) {
- return typeof Object.getOwnPropertyDescriptor(classFn.prototype, propertyName).set === 'function';
- });
- var attributes = setterNames.map(function (setterName) {
- return propertyNameToAttribute(setterName);
- });
-
- // Merge.
- var diff = attributes.filter(function (attribute) {
- return baseAttributes.indexOf(attribute) < 0;
- });
- return baseAttributes.concat(diff);
-}
-
-// Convert a camel case fooBar property name to a hyphenated foo-bar attribute.
-function propertyNameToAttribute(propertyName) {
- var attribute = propertyNamesToAttributes[propertyName];
- if (!attribute) {
- // Convert and memoize.
- var uppercaseRegEx = /([A-Z])/g;
- attribute = propertyName.replace(uppercaseRegEx, '-$1').toLowerCase();
- }
- return attribute;
-}
-
-},{"./safeAttributes":15}],2:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-/* Exported function extends a base class with Composable. */
-exports.default = function (base) {
-
- /**
- * Mixin to make a class more easily composable with other mixins.
- *
- * This mixin contributes a `compose` method that applies a set of mixin
- * functions and returns the resulting new class. This sugar can make the
- * application of many mixins at once easier to read.
- */
- var Composable = function (_base) {
- _inherits(Composable, _base);
-
- function Composable() {
- _classCallCheck(this, Composable);
-
- return _possibleConstructorReturn(this, (Composable.__proto__ || Object.getPrototypeOf(Composable)).apply(this, arguments));
- }
-
- _createClass(Composable, null, [{
- key: 'compose',
-
-
- /**
- * Apply a set of mixin functions or mixin objects to the present class and
- * return the new class.
- *
- * Instead of writing:
- *
- * let MyClass = Mixin1(Mixin2(Mixin3(Mixin4(Mixin5(BaseClass)))));
- *
- * You can write:
- *
- * let MyClass = ComposableMixin(BaseClass).compose(
- * Mixin1,
- * Mixin2,
- * Mixin3,
- * Mixin4,
- * Mixin5
- * );
- *
- * This function can also take mixin objects. A mixin object is just a
- * shorthand for a mixin function that creates a new subclass with the given
- * members. The mixin object's members are *not* copied directly onto the
- * prototype of the base class, as with traditional mixins.
- *
- * In addition to providing syntactic sugar, this mixin can be used to
- * define a class in ES5, which lacks ES6's `class` keyword.
- *
- * @param {...mixins} mixins - A set of mixin functions or objects to apply.
- */
- value: function compose() {
- for (var _len = arguments.length, mixins = Array(_len), _key = 0; _key < _len; _key++) {
- mixins[_key] = arguments[_key];
- }
-
- // We create a new subclass for each mixin in turn. The result becomes
- // the base class extended by any subsequent mixins. It turns out that
- // we can use Array.reduce() to concisely express this, using the current
- // object as the seed for reduce().
- return mixins.reduce(composeClass, this);
- }
- }]);
-
- return Composable;
- }(base);
-
- return Composable;
-};
-
-// Properties defined by Object that we don't want to mixin.
-
-
-var NON_MIXABLE_OBJECT_PROPERTIES = ['constructor'];
-
-/*
- * Apply the mixin to the given base class to return a new class.
- * The mixin can either be a function that returns the modified class, or a
- * plain object whose members will be copied to the new class' prototype.
- */
-function composeClass(base, mixin) {
- if (typeof mixin === 'function') {
- // Mixin function
- return mixin(base);
- } else {
- // Mixin object
- var Subclass = function (_base2) {
- _inherits(Subclass, _base2);
-
- function Subclass() {
- _classCallCheck(this, Subclass);
-
- return _possibleConstructorReturn(this, (Subclass.__proto__ || Object.getPrototypeOf(Subclass)).apply(this, arguments));
- }
-
- return Subclass;
- }(base);
-
- copyOwnProperties(mixin, Subclass.prototype, NON_MIXABLE_OBJECT_PROPERTIES);
- return Subclass;
- }
-}
-
-/*
- * Copy the given properties/methods to the target.
- * Return the updated target.
- */
-function copyOwnProperties(source, target) {
- var ignorePropertyNames = arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : [];
-
- Object.getOwnPropertyNames(source).forEach(function (name) {
- if (ignorePropertyNames.indexOf(name) < 0) {
- var descriptor = Object.getOwnPropertyDescriptor(source, name);
- Object.defineProperty(target, name, descriptor);
- }
- });
- return target;
-}
-
-},{}],3:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
-
-var _get = function get(object, property, receiver) { if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { return get(parent, property, receiver); } } else if ("value" in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } };
-
-var _createSymbol = require('./createSymbol');
-
-var _createSymbol2 = _interopRequireDefault(_createSymbol);
-
-var _toggleClass = require('./toggleClass');
-
-var _toggleClass2 = _interopRequireDefault(_toggleClass);
-
-var _symbols = require('./symbols');
-
-var _symbols2 = _interopRequireDefault(_symbols);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-// Symbols for private data members on an element.
-var itemsSymbol = (0, _createSymbol2.default)('items');
-var itemInitializedSymbol = (0, _createSymbol2.default)('itemInitialized');
-
-/* Exported function extends a base class with ContentItems. */
-
-exports.default = function (base) {
-
- /**
- * Mixin which maps content semantics (elements) to list item semantics.
- *
- * Items differ from element contents in several ways:
- *
- * * They are often referenced via index.
- * * They may have a selection state.
- * * It's common to do work to initialize the appearance or state of a new
- * item.
- * * Auxiliary invisible child elements are filtered out and not counted as
- * items. Auxiliary elements include link, script, style, and template
- * elements. This filtering ensures that those auxiliary elements can be
- * used in markup inside of a list without being treated as list items.
- *
- * This mixin expects a component to provide a `content` property returning a
- * raw set of elements. You can provide that yourself, or use
- * [DistributedChildrenContentMixin](DistributedChildrenContentMixin.md).
- *
- * The most commonly referenced property defined by this mixin is the `items`
- * property. To avoid having to do work each time that property is requested,
- * this mixin supports an optimized mode. If you invoke the `contentChanged`
- * method when the set of items changes, the mixin concludes that you'll take
- * care of notifying it of future changes, and turns on the optimization. With
- * that on, the mixin saves a reference to the computed set of items, and will
- * return that immediately on subsequent calls to the `items` property. If you
- * use this mixin in conjunction with
- * [DistributedChildrenContentMixin](DistributedChildrenContentMixin.md), the
- * `contentChanged` method will be invoked for you when the element's children
- * change, turning on the optimization automatically.
- */
- var ContentItems = function (_base) {
- _inherits(ContentItems, _base);
-
- function ContentItems() {
- _classCallCheck(this, ContentItems);
-
- return _possibleConstructorReturn(this, (ContentItems.__proto__ || Object.getPrototypeOf(ContentItems)).apply(this, arguments));
- }
-
- _createClass(ContentItems, [{
- key: 'contentChanged',
- value: function contentChanged() {
- if (_get(ContentItems.prototype.__proto__ || Object.getPrototypeOf(ContentItems.prototype), 'contentChanged', this)) {
- _get(ContentItems.prototype.__proto__ || Object.getPrototypeOf(ContentItems.prototype), 'contentChanged', this).call(this);
- }
-
- // Since we got the contentChanged call, we'll assume we'll be notified if
- // the set of items changes later. We turn on memoization of the items
- // property by setting our internal property to null (instead of
- // undefined).
- this[itemsSymbol] = null;
-
- this[_symbols2.default.itemsChanged]();
- }
-
- /**
- * This method is invoked whenever a new item is added to the list.
- *
- * The default implementation of this method does nothing. You can override
- * this to perform per-item initialization.
- *
- * @param {HTMLElement} item - The item that was added.
- */
-
- }, {
- key: _symbols2.default.itemAdded,
- value: function value(item) {
- if (_get(ContentItems.prototype.__proto__ || Object.getPrototypeOf(ContentItems.prototype), _symbols2.default.itemAdded, this)) {
- _get(ContentItems.prototype.__proto__ || Object.getPrototypeOf(ContentItems.prototype), _symbols2.default.itemAdded, this).call(this, item);
- }
- }
-
- /**
- * The selection state for a single item has changed.
- *
- * Invoke this method to signal that the selected state of the indicated item
- * has changed. By default, this applies a `selected` CSS class if the item
- * is selected, and removed it if not selected.
- *
- * @param {HTMLElement} item - The item whose selection state has changed.
- * @param {boolean} selected - True if the item is selected, false if not.
- */
-
- }, {
- key: _symbols2.default.itemSelected,
- value: function value(item, selected) {
- if (_get(ContentItems.prototype.__proto__ || Object.getPrototypeOf(ContentItems.prototype), _symbols2.default.itemSelected, this)) {
- _get(ContentItems.prototype.__proto__ || Object.getPrototypeOf(ContentItems.prototype), _symbols2.default.itemSelected, this).call(this, item, selected);
- }
- (0, _toggleClass2.default)(item, 'selected', selected);
- }
-
- /**
- * The current set of items in the list. See the top-level documentation for
- * mixin for a description of how items differ from plain content.
- *
- * @type {HTMLElement[]}
- */
-
- }, {
- key: _symbols2.default.itemsChanged,
-
-
- /**
- * This method is invoked when the underlying contents change. It is also
- * invoked on component initialization – since the items have "changed" from
- * being nothing.
- */
- value: function value() {
- var _this2 = this;
-
- if (_get(ContentItems.prototype.__proto__ || Object.getPrototypeOf(ContentItems.prototype), _symbols2.default.itemsChanged, this)) {
- _get(ContentItems.prototype.__proto__ || Object.getPrototypeOf(ContentItems.prototype), _symbols2.default.itemsChanged, this).call(this);
- }
-
- // Perform per-item initialization.
- Array.prototype.forEach.call(this.items, function (item) {
- if (!item[itemInitializedSymbol]) {
- _this2[_symbols2.default.itemAdded](item);
- item[itemInitializedSymbol] = true;
- }
- });
-
- this.dispatchEvent(new CustomEvent('items-changed'));
- }
-
- /**
- * Fires when the items in the list change.
- *
- * @memberof ContentItems
- * @event items-changed
- */
-
- }, {
- key: 'items',
- get: function get() {
- var items = void 0;
- if (this[itemsSymbol] == null) {
- items = filterAuxiliaryElements(this.content);
- // Note: test for *equality* with null; don't treat undefined as a match.
- if (this[itemsSymbol] === null) {
- // Memoize the set of items.
- this[itemsSymbol] = items;
- }
- } else {
- // Return the memoized items.
- items = this[itemsSymbol];
- }
- return items;
- }
- }]);
-
- return ContentItems;
- }(base);
-
- return ContentItems;
-};
-
-// Return the given elements, filtering out auxiliary elements that aren't
-// typically visible. Items which are not elements are returned as is.
-
-
-function filterAuxiliaryElements(items) {
- var auxiliaryTags = ['link', 'script', 'style', 'template'];
- return [].filter.call(items, function (item) {
- return !item.localName || auxiliaryTags.indexOf(item.localName) < 0;
- });
-}
-
-},{"./createSymbol":13,"./symbols":16,"./toggleClass":17}],4:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
-
-var _set = function set(object, property, value, receiver) { var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent !== null) { set(parent, property, value, receiver); } } else if ("value" in desc && desc.writable) { desc.value = value; } else { var setter = desc.set; if (setter !== undefined) { setter.call(receiver, value); } } return value; };
-
-var _get = function get(object, property, receiver) { if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { return get(parent, property, receiver); } } else if ("value" in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } };
-
-var _microtask = require('./microtask');
-
-var _microtask2 = _interopRequireDefault(_microtask);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-/* Exported function extends a base class with DistributedChildrenContent. */
-exports.default = function (base) {
-
- /**
- * Mixin which defines a component's content as its children, expanding any
- * nodes distributed to the component's slots.
- *
- * This also provides notification of changes to a component's content. It
- * will invoke a `contentChanged` method when the component is first
- * instantiated, and whenever its distributed children change. This is an
- * easy way to satisfy the Gold Standard checklist item for monitoring
- * [Content Changes](https://github.com/webcomponents/gold-standard/wiki/Content-Changes).
- *
- * Example:
- *
- * ```
- * let base = DistributedChildrenContentMixin(DistributedChildrenMixin(HTMLElement));
- * class CountingElement extends base {
- *
- * constructor() {
- * super();
- * let root = this.attachShadow({ mode: 'open' });
- * root.innerHTML = ` `;
- * }
- *
- * contentChanged() {
- * // Count the component's children, both initially and when changed.
- * this.count = this.distributedChildren.length;
- * }
- *
- * }
- * ```
- *
- * Note that content change detection depends upon the element having at least
- * one `slot` element in its shadow subtree.
- *
- * This mixin is intended for use with the
- * [DistributedChildrenMixin](DistributedChildrenMixin.md). See that mixin for
- * a discussion of how that works. This DistributedChildrenContentMixin
- * provides an easy way of defining the "content" of a component as the
- * component's distributed children. That in turn lets mixins like
- * [ContentItemsMixin](ContentItemsMixin.md) manipulate the children as list
- * items.
- */
- var DistributedChildrenContent = function (_base) {
- _inherits(DistributedChildrenContent, _base);
-
- function DistributedChildrenContent() {
- _classCallCheck(this, DistributedChildrenContent);
-
- var _this = _possibleConstructorReturn(this, (DistributedChildrenContent.__proto__ || Object.getPrototypeOf(DistributedChildrenContent)).call(this));
-
- if (_this.shadowRoot) {
- // Listen to changes on all slots.
- var slots = _this.shadowRoot.querySelectorAll('slot');
- slots.forEach(function (slot) {
- return slot.addEventListener('slotchange', function (event) {
- _this.contentChanged();
- });
- });
- }
-
- // Make an initial call to contentChanged() so that the component can do
- // initialization that it normally does when content changes.
- //
- // This will invoke contentChanged() handlers in other mixins. In order
- // that those mixins have a chance to complete their own initialization,
- // we add the contentChanged() call to the microtask queue.
- (0, _microtask2.default)(function () {
- return _this.contentChanged();
- });
- return _this;
- }
-
- /**
- * Invoked when the contents of the component (including distributed
- * children) have changed.
- *
- * This method is also invoked when a component is first instantiated; the
- * contents have essentially "changed" from being nothing. This allows the
- * component to perform initial processing of its children.
- */
-
-
- _createClass(DistributedChildrenContent, [{
- key: 'contentChanged',
- value: function contentChanged() {
- if (_get(DistributedChildrenContent.prototype.__proto__ || Object.getPrototypeOf(DistributedChildrenContent.prototype), 'contentChanged', this)) {
- _get(DistributedChildrenContent.prototype.__proto__ || Object.getPrototypeOf(DistributedChildrenContent.prototype), 'contentChanged', this).call(this);
- }
- var event = new CustomEvent('content-changed');
- this.dispatchEvent(event);
- }
-
- /**
- * The content of this component, defined to be the flattened array of
- * children distributed to the component.
- *
- * @type {HTMLElement[]}
- */
-
- }, {
- key: 'content',
- get: function get() {
- var distributedChildren = this.distributedChildren;
- if (typeof distributedChildren === 'undefined') {
- console.warn('DistributedChildrenContentMixin expects the component to define a "distributedChildren" property.');
- }
- return distributedChildren;
- },
- set: function set(value) {
- if ('content' in base.prototype) {
- _set(DistributedChildrenContent.prototype.__proto__ || Object.getPrototypeOf(DistributedChildrenContent.prototype), 'content', value, this);
- }
- // TODO: Set the children to the given value (which should be an array of
- // elements)?
- }
-
- /**
- * This event is raised when the component's contents (including distributed
- * children) have changed.
- *
- * @memberof DistributedChildrenContent
- * @event content-changed
- */
-
- }]);
-
- return DistributedChildrenContent;
- }(base);
-
- return DistributedChildrenContent;
-};
-
-},{"./microtask":14}],5:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
-
-function _toConsumableArray(arr) { if (Array.isArray(arr)) { for (var i = 0, arr2 = Array(arr.length); i < arr.length; i++) { arr2[i] = arr[i]; } return arr2; } else { return Array.from(arr); } }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-/* Exported function extends a base class with DistributedChildren. */
-exports.default = function (base) {
-
- /**
- * Mixin which defines helpers for accessing a component's distributed
- * children as a flattened array or string.
- *
- * The standard DOM API provides several ways of accessing child content:
- * `children`, `childNodes`, and `textContent`. None of these functions are
- * Shadow DOM aware. This mixin defines variations of those functions that
- * *are* Shadow DOM aware.
- *
- * Example: you create a component `` that displays a number
- * equal to the number of children placed inside that component. If someone
- * instantiates your component like:
- *
- *
- *
- *
- *
- *
- *
- * Then the component should show "3", because there are three children. To
- * calculate the number of children, the component can just calculate
- * `this.children.length`. However, suppose someone instantiates your
- * component inside one of their own components, and puts a `` element
- * inside your component:
- *
- *
- *
- *
- *
- * If your component only looks at `this.children`, it will always see exactly
- * one child — the `` element. But the user looking at the page will
- * *see* any nodes distributed to that slot. To match what the user sees, your
- * component should expand any `` elements it contains.
- *
- * That is the problem this mixin solves. After applying this mixin, your
- * component code has access to `this.distributedChildren`, whose `length`
- * will return the total number of all children distributed to your component
- * in the composed tree.
- *
- * Note: The latest Custom Elements API design calls for a new function,
- * `getAssignedNodes` that takes an optional `deep` parameter, that will solve
- * this problem at the API level.
- */
- var DistributedChildren = function (_base) {
- _inherits(DistributedChildren, _base);
-
- function DistributedChildren() {
- _classCallCheck(this, DistributedChildren);
-
- return _possibleConstructorReturn(this, (DistributedChildren.__proto__ || Object.getPrototypeOf(DistributedChildren)).apply(this, arguments));
- }
-
- _createClass(DistributedChildren, [{
- key: 'distributedChildren',
-
-
- /**
- * An in-order collection of distributed children, expanding any slot
- * elements. Like the standard children property, this skips text nodes.
- *
- * @type {HTMLElement[]}
- */
- get: function get() {
- return expandContentElements(this.children, false);
- }
-
- /**
- * An in-order collection of distributed child nodes, expanding any slot
- * elements. Like the standard childNodes property, this includes text
- * nodes.
- *
- * @type {Node[]}
- */
-
- }, {
- key: 'distributedChildNodes',
- get: function get() {
- return expandContentElements(this.childNodes, true);
- }
-
- /**
- * The concatenated text content of all distributed child nodes, expanding
- * any slot elements.
- *
- * @type {string}
- */
-
- }, {
- key: 'distributedTextContent',
- get: function get() {
- var strings = this.distributedChildNodes.map(function (child) {
- return child.textContent;
- });
- return strings.join('');
- }
- }]);
-
- return DistributedChildren;
- }(base);
-
- return DistributedChildren;
-};
-
-/*
- * Given a array of nodes, return a new array with any content elements expanded
- * to the nodes distributed to that content element. This rule is applied
- * recursively.
- *
- * If includeTextNodes is true, text nodes will be included, as in the
- * standard childNodes property; by default, this skips text nodes, like the
- * standard children property.
- */
-
-
-function expandContentElements(nodes, includeTextNodes) {
- var _ref;
-
- var expanded = Array.prototype.map.call(nodes, function (node) {
- // We want to see if the node is an instanceof HTMLSlotELement, but
- // that class won't exist if the browser that doesn't support native
- // Shadow DOM and if the Shadow DOM polyfill hasn't been loaded. Instead,
- // we do a simplistic check to see if the tag name is "slot".
- var isSlot = typeof HTMLSlotElement !== 'undefined' ? node instanceof HTMLSlotElement : node.localName === 'slot';
- if (isSlot) {
- // Use the nodes assigned to this node instead.
- var assignedNodes = node.assignedNodes({ flatten: true });
- return assignedNodes ? expandContentElements(assignedNodes, includeTextNodes) : [];
- } else if (node instanceof HTMLElement) {
- // Plain element; use as is.
- return [node];
- } else if (node instanceof Text && includeTextNodes) {
- // Text node.
- return [node];
- } else {
- // Comment, processing instruction, etc.; skip.
- return [];
- }
- });
- var flattened = (_ref = []).concat.apply(_ref, _toConsumableArray(expanded));
- return flattened;
-}
-
-},{}],6:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
-
-var _set = function set(object, property, value, receiver) { var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent !== null) { set(parent, property, value, receiver); } } else if ("value" in desc && desc.writable) { desc.value = value; } else { var setter = desc.set; if (setter !== undefined) { setter.call(receiver, value); } } return value; };
-
-var _get = function get(object, property, receiver) { if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { return get(parent, property, receiver); } } else if ("value" in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } };
-
-exports.default = mixin;
-
-var _createSymbol = require('./createSymbol');
-
-var _createSymbol2 = _interopRequireDefault(_createSymbol);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-// Symbols for private data members on an element.
-var selectedFractionSymbol = (0, _createSymbol2.default)('selectedFraction');
-
-/* Exported function extends a base class with FractionalSelection. */
-function mixin(base) {
-
- /**
- * Adds support for fractional selection: treating a selection as a real
- * number that combines an integer portion (an index into a list), and a
- * fraction (indicating how far of the way we are to the next or previous
- * item).
- *
- * This is useful in components that support incremental operations during
- * dragging and swiping. Example: a carousel component has several items, and the
- * currently selected item is item 3. The user begins swiping to the left,
- * moving towards selecting item 4. Halfway through this operation, the
- * fractional selection value is 3.5.
- *
- * This value permits communication between mixins like
- * [SwipeDirectionMixin](./SwipeDirectionMixin.md) and
- * [TrackpadDirectionMixin](./TrackpadDirectionMixin.md), which generate
- * fractional selection values, and mixins like
- * [SelectionAnimationMixin](./SelectionAnimationMixin.md), which can render
- * selection at a fractional value.
- */
- var FractionalSelection = function (_base) {
- _inherits(FractionalSelection, _base);
-
- function FractionalSelection() {
- _classCallCheck(this, FractionalSelection);
-
- return _possibleConstructorReturn(this, (FractionalSelection.__proto__ || Object.getPrototypeOf(FractionalSelection)).apply(this, arguments));
- }
-
- _createClass(FractionalSelection, [{
- key: 'connectedCallback',
- value: function connectedCallback() {
- if (_get(FractionalSelection.prototype.__proto__ || Object.getPrototypeOf(FractionalSelection.prototype), 'connectedCallback', this)) {
- _get(FractionalSelection.prototype.__proto__ || Object.getPrototypeOf(FractionalSelection.prototype), 'connectedCallback', this).call(this);
- }
- this.selectedFraction = 0;
- }
-
- /**
- * A fractional value indicating how far the user has currently advanced to
- * the next/previous item. E.g., a `selectedFraction` of 3.5 indicates the
- * user is halfway between items 3 and 4.
- *
- * @type {number}
- */
-
- }, {
- key: 'selectedFraction',
- get: function get() {
- return this[selectedFractionSymbol];
- },
- set: function set(value) {
- this[selectedFractionSymbol] = value;
- if ('selectedFraction' in base.prototype) {
- _set(FractionalSelection.prototype.__proto__ || Object.getPrototypeOf(FractionalSelection.prototype), 'selectedFraction', value, this);
- }
- var event = new CustomEvent('selected-fraction-changed');
- this.dispatchEvent(event);
- }
- }]);
-
- return FractionalSelection;
- }(base);
-
- return FractionalSelection;
-}
-
-mixin.helpers = {
-
- /*
- * Dampen a selection that goes past the beginning or end of a list. This is
- * generally used to produce a visual effect of tension as the user tries to
- * go further in a direction that has no more items.
- *
- * Example: suppose `itemCount` is 5, indicating a list of 5 items. The index of
- * the last item is 4. If the `selection` parameter is 4.5, the user is trying
- * to go past this last item. When a damping function is applied, the resulting
- * value will be less than 4.5 (the actual value will be 4.25). When this
- * selection state is rendered, the user will see that, each unit distance the
- * drag travels has less and less visible effect. This is perceived as tension.
- *
- * @param {number} selection - A real number indicating a selection position
- * @param {number} itemCount - An integer for the number of items in the list
- * @returns {number} A real number representing the damped selection value.
- */
- dampedSelection: function dampedSelection(selection, itemCount) {
- var bound = itemCount - 1;
- var damped = void 0;
- if (selection < 0) {
- // Trying to go past beginning of list. Apply tension from the left edge.
- damped = -mixin.helpers.damping(-selection);
- } else if (selection >= bound) {
- // Trying to go past end of list. Apply tension from the right edge.
- damped = bound + mixin.helpers.damping(selection - bound);
- } else {
- // No damping required.
- damped = selection;
- }
- return damped;
- },
-
-
- /*
- * Calculate damping as a function of the distance past the minimum/maximum
- * values.
- *
- * We want to asymptotically approach an absolute minimum of 1 unit
- * below/above the actual minimum/maximum. This requires calculating a
- * hyperbolic function.
- *
- * See http://www.wolframalpha.com/input/?i=y+%3D+-1%2F%28x%2B1%29+%2B+1
- * for the one we use. The only portion of that function we care about is when
- * x is zero or greater. An important consideration is that the curve be
- * tangent to the diagonal line x=y at (0, 0). This ensures smooth continuity
- * with the normal drag behavior, in which the visible sliding is linear with
- * the distance the touchpoint has been dragged.
- */
- damping: function damping(x) {
- var y = -1 / (x + 1) + 1;
- return y;
- },
-
-
- /*
- * Return the current fractional selection value for the given element.
- *
- * This simply adds the element's `selectedIndex` and `selectedFraction`
- * properties.
- *
- * @param {HTMLElement} element - An element that supports selection
- */
- elementSelection: function elementSelection(element) {
- var selectedIndex = element.selectedIndex;
- if (selectedIndex < 0) {
- // No selection
- return;
- }
- var selectedFraction = element.selectedFraction || 0;
- return selectedIndex + selectedFraction;
- },
-
-
- /*
- * Breaks a fractional selection into its integer and fractional parts.
- *
- * Example: if passed 3.5, this returns { index: 3, fraction: 5 }.
- *
- * @param {number} selection – A real number representing a selection point
- * @returns {object} - An object with an `index` property holding the
- * selection's integer component, and a `fraction` property holding the
- * selection's fractional component.
- */
- selectionParts: function selectionParts(selection) {
- // Stupid IE doesn't have Math.trunc.
- // const index = Math.trunc(selection);
- var index = selection < 0 ? Math.ceil(selection) : Math.floor(selection);
- var fraction = selection - index;
- return { index: index, fraction: fraction };
- },
-
-
- /*
- * Returns a fractional selection point after accounting for wrapping, ensuring
- * that the integer portion of the selection stays between 0 and `itemCount`-1.
- * That is, the integer portion will always be a valid index into the list.
- *
- * Example of wrapping past the end of the list: if `selection` is 5.5 and
- * `itemCount` is 5, this returns 0.5. Example of wrapping past the beginning of
- * the list: if `selection` is 0.5 and `itemCount` is 5, this returns 4.5.
- *
- * @param {number} selection - A real number representing a selection point
- * @param {number} itemCount - The number of items in the list
- * @returns {number} - The result of wrapping the selection point
- */
- wrappedSelection: function wrappedSelection(selection, itemCount) {
- // Handles possibility of negative mod.
- // See http://stackoverflow.com/a/18618250/76472
- return (selection % itemCount + itemCount) % itemCount;
- },
-
-
- /*
- * Return the parts of a selection, first wrapping if necessary.
- *
- * @param {number} selection – A real number representing a selection point
- * @param {number} itemCount - The number of items in the list
- * @param {boolean} wrap – True if the selection should wrap to stay within the
- * list
- * @returns {object} – The parts of the selection, using the same format as
- * `selectionParts`.
- */
- wrappedSelectionParts: function wrappedSelectionParts(selection, itemCount, wrap) {
- if (wrap) {
- selection = mixin.helpers.wrappedSelection(selection, itemCount);
- }
- return mixin.helpers.selectionParts(selection);
- }
-};
-
-},{"./createSymbol":13}],7:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
-
-var _set = function set(object, property, value, receiver) { var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent !== null) { set(parent, property, value, receiver); } } else if ("value" in desc && desc.writable) { desc.value = value; } else { var setter = desc.set; if (setter !== undefined) { setter.call(receiver, value); } } return value; };
-
-var _get = function get(object, property, receiver) { if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { return get(parent, property, receiver); } } else if ("value" in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } };
-
-exports.default = mixin;
-
-var _createSymbol = require('./createSymbol');
-
-var _createSymbol2 = _interopRequireDefault(_createSymbol);
-
-var _FractionalSelectionMixin = require('./FractionalSelectionMixin');
-
-var _FractionalSelectionMixin2 = _interopRequireDefault(_FractionalSelectionMixin);
-
-var _symbols = require('./symbols');
-
-var _symbols2 = _interopRequireDefault(_symbols);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-// Symbols for private data members on an element.
-var animationSymbol = (0, _createSymbol2.default)('animation');
-var draggingSymbol = (0, _createSymbol2.default)('dragging');
-var lastAnimationSymbol = (0, _createSymbol2.default)('lastAnimation');
-var playingAnimationSymbol = (0, _createSymbol2.default)('animatingSelection');
-var previousSelectionSymbol = (0, _createSymbol2.default)('previousSelection');
-var selectionAnimationDurationSymbol = (0, _createSymbol2.default)('selectionAnimationDuration');
-var selectionAnimationEffectSymbol = (0, _createSymbol2.default)('selectionAnimationEffect');
-var selectionAnimationKeyframesSymbol = (0, _createSymbol2.default)('selectionAnimationKeyframes');
-var resetAnimationsOnNextRenderSymbol = (0, _createSymbol2.default)('resetAnimationsOnNextRender');
-
-/* Exported function extends a base class with SelectionAnimation. */
-function mixin(base) {
-
- /**
- * Mixin which uses animation to show transitions between selection states.
- *
- * This mixin can be used by components that want to provide visible
- * animations when changing the selection. For example, a carousel component
- * may want to define a sliding animation effect shown when moving between
- * items.
- *
- * The animation is defined by a `selectionAnimationKeyframes` property; see
- * that property for details on how to define these keyframes. This animation
- * will be used in two ways. First, when moving strictly between items, the
- * animation will play smoothly to show the selection changing. Second, the
- * animation can be used to render the selection at a fixed point in the
- * transition between states. E.g., if the user pauses halfway through
- * dragging an element using [SwipeDirectionMixin](SwipeDirectionMixin.md)
- * or [TrackpadDirectionMixin](TrackpadDirectionMixin.md)s, then the selection
- * animation will be shown at the point exactly halfway through.
- *
- * This mixin expects a component to provide an `items` array of all elements
- * in the list, which can be provided via
- * [ContentItemsMixin](ContentItemsMixin.md). This mixin also expects
- * `selectedIndex` and `selectedItem` properties, which can be provided via
- * [SingleSelectionMixin](SingleSelectionMixin.md).
- *
- * This mixin supports a `selectionWraps` property. When true, the user can
- * navigate forward from the last item in the list and wrap around to the
- * first item, or navigate backward from the first item and wrap around to the
- * last item.
- *
- * This mixin uses the Web Animations API. For use on browsers which
- * do not support that API natively, you will need to load the
- * [Web Animations polyfill](https://github.com/web-animations/web-animations-js).
- */
- var SelectionAnimation = function (_base) {
- _inherits(SelectionAnimation, _base);
-
- function SelectionAnimation() {
- _classCallCheck(this, SelectionAnimation);
-
- // Set defaults.
- var _this = _possibleConstructorReturn(this, (SelectionAnimation.__proto__ || Object.getPrototypeOf(SelectionAnimation)).call(this));
-
- if (typeof _this.selectionAnimationDuration === 'undefined') {
- _this.selectionAnimationDuration = _this[_symbols2.default.defaults].selectionAnimationDuration;
- }
- if (typeof _this.selectionAnimationEffect === 'undefined' && _this.selectionAnimationKeyframes == null) {
- _this.selectionAnimationEffect = _this[_symbols2.default.defaults].selectionAnimationEffect;
- }
-
- _this[_symbols2.default.dragging] = false;
- return _this;
- }
-
- _createClass(SelectionAnimation, [{
- key: _symbols2.default.itemAdded,
- value: function value(item) {
- // We mark new items in the list as explicitly visible to ARIA. Otherwise,
- // when an item isn't visible on the screen, ARIA will assume the item is
- // of no interest to the user, and leave it out of the accessibility tree.
- // If the list contains 10 items, but only 3 are visible, a screen reader
- // might then announce the list only has 3 items. To ensure that screen
- // readers and other assistive technologies announce the correct total
- // number of items, we explicitly mark all items as not hidden. This will
- // expose them all in the accessibility tree, even the items which are
- // currently not rendered.
- //
- // TODO: Generally speaking, this entire mixin assumes that the user can
- // navigate through all items in a list. But an app could style an item as
- // display:none or visibility:hidden because the user is not allowed to
- // interact with that item at the moment. Support for this scenario should
- // be added. This would entail changing all locations where a mixin
- // function is counting items, iterating over the (visible) items, and
- // showing or hiding items. Among other things, the code below to make
- // items visible to ARIA would need to discriminate between items which
- // are invisible because of animation state, or invisible because the user
- // shouldn't interact with them.
- item.setAttribute('aria-hidden', false);
- }
- }, {
- key: _symbols2.default.itemsChanged,
- value: function value() {
- if (_get(SelectionAnimation.prototype.__proto__ || Object.getPrototypeOf(SelectionAnimation.prototype), _symbols2.default.itemsChanged, this)) {
- _get(SelectionAnimation.prototype.__proto__ || Object.getPrototypeOf(SelectionAnimation.prototype), _symbols2.default.itemsChanged, this).call(this);
- }
-
- _resetAnimations(this);
-
- // TODO: Also reset our notion of the last rendered selection? This comes
- // up when a DOM removal causes the selected item to change position.
- // this[previousSelectionSymbol] = null;
-
- renderSelection(this);
- }
- }, {
- key: 'resetAnimations',
- value: function resetAnimations() {
- _resetAnimations(this);
- }
-
- /**
- * A fractional value indicating how far the user has currently advanced to
- * the next/previous item. E.g., a `selectedFraction` of 3.5 indicates the
- * user is halfway between items 3 and 4.
- *
- * For more details, see [FractionalSelectionMixin](FractionalSelectionMixin.md)
- * mixin.
- *
- * @type {number}
- */
-
- }, {
- key: _symbols2.default.defaults,
- get: function get() {
- var defaults = _get(SelectionAnimation.prototype.__proto__ || Object.getPrototypeOf(SelectionAnimation.prototype), _symbols2.default.defaults, this) || {};
- defaults.selectionAnimationDuration = 250;
- defaults.selectionAnimationEffect = 'slide';
- return defaults;
- }
-
- /*
- * Provide backing for the dragging property.
- * Also, when a drag begins, reset the animations.
- */
-
- }, {
- key: _symbols2.default.dragging,
- get: function get() {
- return this[draggingSymbol];
- },
- set: function set(value) {
- var previousValue = this[_symbols2.default.dragging];
- this[draggingSymbol] = value;
- if (_symbols2.default.dragging in base.prototype) {
- _set(SelectionAnimation.prototype.__proto__ || Object.getPrototypeOf(SelectionAnimation.prototype), _symbols2.default.dragging, value, this);
- }
- if (value && !previousValue) {
- // Have begun a drag.
- this[resetAnimationsOnNextRenderSymbol] = true;
- }
- }
- }, {
- key: 'selectedFraction',
- get: function get() {
- return _get(SelectionAnimation.prototype.__proto__ || Object.getPrototypeOf(SelectionAnimation.prototype), 'selectedFraction', this) || 0;
- },
- set: function set(value) {
- if ('selectedFraction' in base.prototype) {
- _set(SelectionAnimation.prototype.__proto__ || Object.getPrototypeOf(SelectionAnimation.prototype), 'selectedFraction', value, this);
- }
- renderSelection(this, this.selectedIndex, value);
- }
- }, {
- key: 'selectedIndex',
- get: function get() {
- return _get(SelectionAnimation.prototype.__proto__ || Object.getPrototypeOf(SelectionAnimation.prototype), 'selectedIndex', this);
- },
- set: function set(index) {
- if ('selectedIndex' in base.prototype) {
- _set(SelectionAnimation.prototype.__proto__ || Object.getPrototypeOf(SelectionAnimation.prototype), 'selectedIndex', index, this);
- }
- renderSelection(this, index, 0);
- }
-
- /**
- * The duration of a selection animation in milliseconds.
- *
- * This measures the amount of time required for a selection animation to
- * complete. This number remains constant, even if the number of items being
- * animated increases.
- *
- * The default value is 250 milliseconds (a quarter a second).
- *
- * @type {number}
- * @default 250
- */
-
- }, {
- key: 'selectionAnimationDuration',
- get: function get() {
- return this[selectionAnimationDurationSymbol];
- },
- set: function set(value) {
- this[selectionAnimationDurationSymbol] = value;
- if ('selectionAnimationDuration' in base.prototype) {
- _set(SelectionAnimation.prototype.__proto__ || Object.getPrototypeOf(SelectionAnimation.prototype), 'selectionAnimationDuration', value, this);
- }
- }
-
- /**
- * The name of a standard selection animation effect.
- *
- * This is a shorthand for setting the `selectionAnimationKeyframes`
- * property to standard keyframes. Supported string values:
- *
- * * "crossfade"
- * * "reveal"
- * * "revealWithFade"
- * * "showAdjacent"
- * * "slide"
- * * "slideWithGap"
- *
- * @type {string}
- * @default "slide"
- */
-
- }, {
- key: 'selectionAnimationEffect',
- get: function get() {
- return this[selectionAnimationEffectSymbol];
- },
- set: function set(value) {
- this[selectionAnimationEffectSymbol] = value;
- if ('selectionAnimationEffect' in base.prototype) {
- _set(SelectionAnimation.prototype.__proto__ || Object.getPrototypeOf(SelectionAnimation.prototype), 'selectionAnimationEffect', value, this);
- }
- this.selectionAnimationKeyframes = mixin.standardEffectKeyframes[value];
- }
-
- /**
- * The keyframes that define an animation that plays for an item when moving
- * forward in the sequence.
- *
- * This is an array of CSS rules that will be applied. These are used as
- * [keyframes](http://w3c.github.io/web-animations/#keyframes-section)
- * to animate the item with the
- * [Web Animations API](https://developer.mozilla.org/en-US/docs/Web/API/animation).
- *
- * The animation represents the state of the next item as it moves from
- * completely unselected (offstage, usually right), to selected (center
- * stage), to completely unselected (offstage, usually left). The center time
- * of the animation should correspond to the item's quiscent selected state,
- * typically in the center of the stage and at the item's largest size.
- *
- * The default forward animation is a smooth slide at full size from right to
- * left.
- *
- * When moving the selection backward, this animation is played in reverse.
- *
- * @type {cssRules[]}
- */
-
- }, {
- key: 'selectionAnimationKeyframes',
- get: function get() {
- // Standard animation slides left/right, keeps adjacent items out of view.
- return this[selectionAnimationKeyframesSymbol];
- },
- set: function set(value) {
- this[selectionAnimationKeyframesSymbol] = value;
- if ('selectionAnimationKeyframes' in base.prototype) {
- _set(SelectionAnimation.prototype.__proto__ || Object.getPrototypeOf(SelectionAnimation.prototype), 'selectionAnimationKeyframes', value, this);
- }
- _resetAnimations(this);
- renderSelection(this);
- }
- }, {
- key: 'selectionWraps',
- get: function get() {
- return _get(SelectionAnimation.prototype.__proto__ || Object.getPrototypeOf(SelectionAnimation.prototype), 'selectionWraps', this);
- },
- set: function set(value) {
- if ('selectionWraps' in base.prototype) {
- _set(SelectionAnimation.prototype.__proto__ || Object.getPrototypeOf(SelectionAnimation.prototype), 'selectionWraps', value, this);
- }
- _resetAnimations(this);
- renderSelection(this);
- }
- }]);
-
- return SelectionAnimation;
- }(base);
-
- return SelectionAnimation;
-}
-
-// We expose helpers on the mixin function that we want to be able to unit test.
-// Since these are on the function, not on the class emitted by the function,
-// they don't end up getting exposed on actual element instances.
-mixin.helpers = {
-
- /*
- * Calculate the animation fractions for an element's items at the given
- * selection point. This is used when rendering the element's selection state
- * instantaneously.
- *
- * This function considers the selectedIndex parameter, which can be a whole
- * or fractional number, and determines which items will be visible at that
- * index. This function then calculates a corresponding animation fraction: a
- * number between 0 and 1 indicating how far through the selection animation
- * an item should be shown, or null if the item should not be visible at that
- * selection index. These fractions are returned as an array, where the
- * animation fraction at position N corresponds to how item N should be shown.
- */
- animationFractionsForSelection: function animationFractionsForSelection(element, selection) {
-
- var items = element.items;
- if (!items) {
- return;
- }
-
- var itemCount = items.length;
- var selectionWraps = element.selectionWraps;
-
- return items.map(function (item, itemIndex) {
- // How many steps from the selection point to this item?
- var steps = stepsToIndex(itemCount, selectionWraps, selection, itemIndex);
- // To convert steps to animation fraction:
- // steps animation fraction
- // 1 0 (stage right)
- // 0 0.5 (center stage)
- // -1 1 (stage left)
- var animationFraction = (1 - steps) / 2;
- return animationFraction >= 0 && animationFraction <= 1 ? animationFraction : null; // Outside animation range
- });
- },
-
-
- /*
- * Calculate the animation timings that should be used to smoothly animate the
- * element's items from one selection state to another.
- *
- * This returns an array of timings, where the timing at position N should be
- * used to animate item N. If an item's timing is null, then that item should
- * not take place in the animation, and should be hidden instead.
- */
- effectTimingsForSelectionAnimation: function effectTimingsForSelectionAnimation(element, fromSelection, toSelection) {
-
- var items = element.items;
- if (!items) {
- return;
- }
- var itemCount = items.length;
- var selectionWraps = element.selectionWraps;
- var toIndex = _FractionalSelectionMixin2.default.helpers.wrappedSelectionParts(toSelection, itemCount, selectionWraps).index;
- var totalSteps = stepsToIndex(itemCount, selectionWraps, fromSelection, toSelection);
- var direction = totalSteps >= 0 ? 'normal' : 'reverse';
- var fill = 'both';
- var totalDuration = element.selectionAnimationDuration;
- var stepDuration = totalSteps !== 0 ? totalDuration * 2 / Math.ceil(Math.abs(totalSteps)) : 0; // No steps required, animation will be instantenous.
-
- var timings = items.map(function (item, itemIndex) {
- var steps = stepsToIndex(itemCount, selectionWraps, itemIndex, toSelection);
- // If we include this item in the staggered sequence of animations we're
- // creating, where would the item appear in the sequence?
- var positionInSequence = totalSteps - steps;
- if (totalSteps < 0) {
- positionInSequence = -positionInSequence;
- }
- // So, is this item really included in the sequence?
- if (Math.ceil(positionInSequence) >= 0 && positionInSequence <= Math.abs(totalSteps)) {
- // Note that delay for first item will be negative. That will cause
- // the animation to start halfway through, which is what we want.
- var delay = stepDuration * (positionInSequence - 1) / 2;
- var endDelay = itemIndex === toIndex ? -stepDuration / 2 : // Stop halfway through.
- 0; // Play animation until end.
- return { duration: stepDuration, direction: direction, fill: fill, delay: delay, endDelay: endDelay };
- } else {
- return null;
- }
- });
-
- return timings;
- }
-};
-
-// Keyframes for standard selection animation effects.
-mixin.standardEffectKeyframes = {
-
- // Simple crossfade
- crossfade: [{ opacity: 0 }, { opacity: 1 }, { opacity: 0 }],
-
- // Reveal, as if sliding the top card off a deck of cards
- reveal: [{ transform: 'translateX(0%)', zIndex: 0 }, { transform: 'translateX(0%)', zIndex: 1 }, { transform: 'translateX(-100%)', zIndex: 2 }],
-
- // Google Photos-style reveal-with-fade animation
- revealWithFade: [{ transform: 'translateX(0%) scale(0.75)', opacity: 0, zIndex: 0 }, { transform: 'translateX(0%) scale(1.0)', opacity: 1, zIndex: 1 }, { transform: 'translateX(-100%) scale(1.0)', opacity: 1, zIndex: 2 }],
-
- // Carousel variant with a bit of off-stage elements showing
- showAdjacent: [{ transform: 'translateX(78%) scale(0.7)', zIndex: 0 }, { transform: 'translateX(0%) scale(0.82)', zIndex: 1 }, { transform: 'translateX(-78%) scale(0.7)', zIndex: 0 }],
-
- // Simple slide
- slide: [{ transform: 'translateX(100%)' }, { transform: 'translateX(-100%)' }],
-
- // Slide, with a gap between
- slideWithGap: [{ transform: 'translateX(110%)' }, { transform: 'translateX(-110%)' }]
-
-};
-
-/*
- * Smoothly animate the selection between the indicated "from" and "to"
- * indices. The former can be a fraction, e.g., when the user releases a finger
- * to complete a touch drag, and the selection will snap to the closest whole
- * index.
- */
-function animateSelection(element, fromSelection, toSelection) {
-
- _resetAnimations(element);
-
- // Calculate the animation timings.
- var items = element.items;
- var keyframes = element.selectionAnimationKeyframes;
- element[playingAnimationSymbol] = true;
- var timings = mixin.helpers.effectTimingsForSelectionAnimation(element, fromSelection, toSelection);
-
- // Figure out which item will be the one *after* the one we're selecting.
- var itemCount = items.length;
- var selectionWraps = element.selectionWraps;
- var selectionIndex = _FractionalSelectionMixin2.default.helpers.selectionParts(toSelection, itemCount, selectionWraps).index;
- var totalSteps = stepsToIndex(itemCount, selectionWraps, fromSelection, toSelection);
- var forward = totalSteps >= 0;
- var nextUpIndex = selectionIndex + (forward ? 1 : -1);
- if (selectionWraps) {
- nextUpIndex = _FractionalSelectionMixin2.default.helpers.wrappedSelection(nextUpIndex, itemCount);
- } else if (!isItemIndexInBounds(element, nextUpIndex)) {
- nextUpIndex = null; // At start/end of list; don't have a next item to show.
- }
-
- // Play the animations using those timings.
- var lastAnimationDetails = void 0;
- timings.forEach(function (timing, index) {
- var item = items[index];
- if (timing) {
- showItem(item, true);
- var animation = item.animate(keyframes, timing);
- element[animationSymbol][index] = animation;
- if (index === nextUpIndex) {
- // This item will be animated, so will already be in the desired state
- // after the animation completes.
- nextUpIndex = null;
- }
- if (timing.endDelay !== 0) {
- // This is the animation for the item that will be left selected.
- // We want to clean up when this animation completes.
- lastAnimationDetails = { animation: animation, index: index, timing: timing, forward: forward };
- }
- } else {
- // This item doesn't participate in the animation.
- showItem(item, false);
- }
- });
-
- if (lastAnimationDetails != null) {
- // Arrange for clean-up work to be performed.
- lastAnimationDetails.nextUpIndex = nextUpIndex;
- lastAnimationDetails.animation.onfinish = function (event) {
- return selectionAnimationFinished(element, lastAnimationDetails);
- };
- element[lastAnimationSymbol] = lastAnimationDetails.animation;
- } else {
- // Shouldn't happen -- we should always have at least one animation.
- element[playingAnimationSymbol] = false;
- }
-}
-
-function getAnimationForItemIndex(element, index) {
- if (element[animationSymbol] == null) {
- // Not ready yet;
- return null;
- }
- var animation = element[animationSymbol][index];
- if (!animation) {
- var item = element.items[index];
- animation = item.animate(element.selectionAnimationKeyframes, {
- duration: element.selectionAnimationDuration,
- fill: 'both'
- });
- animation.pause();
- element[animationSymbol][index] = animation;
- }
- return animation;
-}
-
-function isItemIndexInBounds(element, index) {
- return index >= 0 && element.items && index < element.items.length;
-}
-
-/*
- * Render the selection state of the element.
- *
- * This can be used to re-render a previous selection state (if the
- * selectedIndex param is omitted), render the selection instantly at a given
- * whole or fractional selection index, or animate to a given selection index.
- *
- * There are several distinct scenarios we need to cover:
- *
- * 1. Initial positioning, or repositioning after changing a property like
- * selectionAnimationKeyframes that affects rendering.
- * 2. Animate on selectedIndex change. This should override any animation/swipe
- * already in progress.
- * 3. Instantly render the current position of a drag operation in progress.
- * 4. Complete a drag operation. If the drag wasn't far enough to affect
- * selection, we'll just be restoring the selectedFraction to 0.
- *
- * If the list does not wrap, any selection position outside the list's bounds
- * will be damped to produce a visual effect of tension.
- */
-function renderSelection(element) {
- var selectedIndex = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : element.selectedIndex;
- var selectedFraction = arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : element.selectedFraction;
-
- var itemCount = element.items ? element.items.length : 0;
- if (itemCount === 0) {
- // Nothing to render.
- return;
- }
- if (selectedIndex < 0) {
- // TODO: Handle no selection.
- return;
- }
- var selection = selectedIndex + selectedFraction;
- if (element.selectionWraps) {
- // Apply wrapping to ensure consistent representation of selection.
- selection = _FractionalSelectionMixin2.default.helpers.wrappedSelection(selection, itemCount);
- } else {
- // Apply damping if necessary.
- selection = _FractionalSelectionMixin2.default.helpers.dampedSelection(selection, itemCount);
- }
- var previousSelection = element[previousSelectionSymbol];
- // TODO: If an item changes position in the DOM, we end up animating from
- // its old index to its new index, but we really don't want to animate at all.
- if (!element[_symbols2.default.dragging] && previousSelection != null && previousSelection !== selection) {
- // Animate selection from previous state to new state.
- animateSelection(element, previousSelection, selection);
- } else if (selectedFraction === 0 && element[playingAnimationSymbol]) {
- // Already in process of animating to fraction 0. During that process,
- // ignore subsequent attempts to renderSelection to fraction 0.
- return;
- } else {
- // Render current selection state instantly.
- renderSelectionInstantly(element, selection);
- }
- element[previousSelectionSymbol] = selection;
-}
-
-/*
- * Instantly render (don't animate) the element's items at the given whole or
- * fractional selection index.
- */
-function renderSelectionInstantly(element, toSelection) {
- if (element[resetAnimationsOnNextRenderSymbol]) {
- _resetAnimations(element);
- element[resetAnimationsOnNextRenderSymbol] = false;
- }
- var animationFractions = mixin.helpers.animationFractionsForSelection(element, toSelection);
- animationFractions.map(function (animationFraction, index) {
- var item = element.items[index];
- if (animationFraction != null) {
- showItem(item, true);
- setAnimationFraction(element, index, animationFraction);
- } else {
- showItem(item, false);
- }
- });
-}
-
-/*
- * We maintain an array containing an animation per item. This is used for two
- * reasons:
- *
- * * During a drag operation, we want to be able to reuse animations between
- * drag updates.
- * * When a selection animation completes, we need to be able to leave the
- * visibile items in a paused state. Later, we'll want to be able to clean up
- * those animations.
- *
- * Note that this array is sparse: it will only hold up from 0–3 animations at
- * any given point.
- */
-function _resetAnimations(element) {
- var animations = element[animationSymbol];
- if (animations) {
- // Cancel existing animations to remove the effects they're applying.
- animations.forEach(function (animation, index) {
- if (animation) {
- animation.cancel();
- animations[index] = null;
- }
- });
- }
- var itemCount = element.items ? element.items.length : 0;
- if (!animations || animations.length !== itemCount) {
- // Haven't animated before with this number of items; (re)create array.
- element[animationSymbol] = new Array(itemCount);
- }
-}
-
-/*
- * The last animation in our selection animation has completed. Clean up.
- */
-function selectionAnimationFinished(element, details) {
-
- // When the last animation completes, show the next item in the direction
- // we're going. Waiting to that until this point is a bit of a hack to avoid
- // having a next item that's higher in the natural z-order obscure other items
- // during animation.
- var nextUpIndex = details.nextUpIndex;
- if (nextUpIndex != null) {
- if (element[animationSymbol][nextUpIndex]) {
- // Cancel existing selection animation so we can construct a new one.
- element[animationSymbol][nextUpIndex].cancel();
- element[animationSymbol][nextUpIndex] = null;
- }
- var animationFraction = details.forward ? 0 : 1;
- setAnimationFraction(element, nextUpIndex, animationFraction);
- showItem(element.items[nextUpIndex], true);
- }
-
- element[lastAnimationSymbol].onfinish = null;
- element[playingAnimationSymbol] = false;
-}
-
-/*
- * Pause the indicated animation and have it show the animation at the given
- * fraction (between 0 and 1) of the way through the animation.
- */
-function setAnimationFraction(element, itemIndex, fraction) {
- var animation = getAnimationForItemIndex(element, itemIndex);
- if (animation) {
- var duration = element.selectionAnimationDuration;
- if (duration) {
- animation.currentTime = fraction * duration;
- }
- }
-}
-
-function showItem(item, flag) {
- item.style.visibility = flag ? 'visible' : 'hidden';
-}
-
-/*
- * Figure out how many steps it will take to go from fromSelection to
- * toSelection. To go from item 3 to item 4 is one step.
- *
- * If wrapping is allowed, then going from the last item to the first will take
- * one step (forward), and going from the first item to the last will take one
- * step (backward).
- */
-function stepsToIndex(length, allowWrap, fromSelection, toSelection) {
- var steps = toSelection - fromSelection;
- // Wrapping only kicks in when list has more than 1 item.
- if (allowWrap && length > 1) {
- var wrapSteps = length - Math.abs(steps);
- if (wrapSteps <= 1) {
- // Special case
- steps = steps < 0 ? wrapSteps : // Wrap forward from last item to first.
- -wrapSteps; // Wrap backward from first item to last.
- }
- }
- return steps;
-}
-
-},{"./FractionalSelectionMixin":6,"./createSymbol":13,"./symbols":16}],8:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
-
-var _set = function set(object, property, value, receiver) { var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent !== null) { set(parent, property, value, receiver); } } else if ("value" in desc && desc.writable) { desc.value = value; } else { var setter = desc.set; if (setter !== undefined) { setter.call(receiver, value); } } return value; };
-
-var _get = function get(object, property, receiver) { if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { return get(parent, property, receiver); } } else if ("value" in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } };
-
-var _symbols = require('./symbols');
-
-var _symbols2 = _interopRequireDefault(_symbols);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-// Used to assign unique IDs to item elements without IDs.
-var idCount = 0;
-
-/* Exported function extends a base class with SelectionAriaActive. */
-
-exports.default = function (base) {
-
- /**
- * Mixin which treats the selected item in a list as the active item in ARIA
- * accessibility terms.
- *
- * Handling ARIA selection state properly is actually quite complex:
- *
- * * The items in the list need to be indicated as possible items via an ARIA
- * `role` attribute value such as "option".
- * * The selected item need to be marked as selected by setting the item's
- * `aria-selected` attribute to true *and* the other items need be marked as
- * *not* selected by setting `aria-selected` to false.
- * * The outermost element with the keyboard focus needs to have attributes
- * set on it so that the selection is knowable at the list level via the
- * `aria-activedescendant` attribute.
- * * Use of `aria-activedescendant` in turn requires that all items in the
- * list have ID attributes assigned to them.
- *
- * This mixin tries to address all of the above requirements. To that end,
- * this mixin will assign generated IDs to any item that doesn't already have
- * an ID.
- *
- * ARIA relies on elements to provide `role` attributes. This mixin will apply
- * a default role of "listbox" on the outer list if it doesn't already have an
- * explicit role. Similarly, this mixin will apply a default role of "option"
- * to any list item that does not already have a role specified.
- *
- * This mixin expects a set of members that manage the state of the selection:
- * `[symbols.itemSelected]`, `itemAdded`, and `selectedIndex`. You can
- * supply these yourself, or do so via
- * [SingleSelectionMixin](SingleSelectionMixin.md).
- */
- var SelectionAriaActive = function (_base) {
- _inherits(SelectionAriaActive, _base);
-
- function SelectionAriaActive() {
- _classCallCheck(this, SelectionAriaActive);
-
- return _possibleConstructorReturn(this, (SelectionAriaActive.__proto__ || Object.getPrototypeOf(SelectionAriaActive)).apply(this, arguments));
- }
-
- _createClass(SelectionAriaActive, [{
- key: 'connectedCallback',
- value: function connectedCallback() {
- if (_get(SelectionAriaActive.prototype.__proto__ || Object.getPrototypeOf(SelectionAriaActive.prototype), 'connectedCallback', this)) {
- _get(SelectionAriaActive.prototype.__proto__ || Object.getPrototypeOf(SelectionAriaActive.prototype), 'connectedCallback', this).call(this);
- }
- // Set default ARIA role.
- if (this.getAttribute('role') == null && this[_symbols2.default.defaults].role) {
- this.setAttribute('role', this[_symbols2.default.defaults].role);
- }
- }
- }, {
- key: _symbols2.default.itemAdded,
- value: function value(item) {
- if (_get(SelectionAriaActive.prototype.__proto__ || Object.getPrototypeOf(SelectionAriaActive.prototype), _symbols2.default.itemAdded, this)) {
- _get(SelectionAriaActive.prototype.__proto__ || Object.getPrototypeOf(SelectionAriaActive.prototype), _symbols2.default.itemAdded, this).call(this, item);
- }
-
- if (!item.getAttribute('role')) {
- // Assign a default ARIA role.
- item.setAttribute('role', 'option');
- }
-
- // Ensure each item has an ID so we can set aria-activedescendant on the
- // overall list whenever the selection changes.
- //
- // The ID will take the form of a base ID plus a unique integer. The base
- // ID will be incorporate the component's own ID. E.g., if a component has
- // ID "foo", then its items will have IDs that look like "_fooOption1". If
- // the compnent has no ID itself, its items will get IDs that look like
- // "_option1". Item IDs are prefixed with an underscore to differentiate
- // them from manually-assigned IDs, and to minimize the potential for ID
- // conflicts.
- if (!item.id) {
- var baseId = this.id ? "_" + this.id + "Option" : "_option";
- item.id = baseId + idCount++;
- }
- }
- }, {
- key: _symbols2.default.itemSelected,
- value: function value(item, selected) {
- if (_get(SelectionAriaActive.prototype.__proto__ || Object.getPrototypeOf(SelectionAriaActive.prototype), _symbols2.default.itemSelected, this)) {
- _get(SelectionAriaActive.prototype.__proto__ || Object.getPrototypeOf(SelectionAriaActive.prototype), _symbols2.default.itemSelected, this).call(this, item, selected);
- }
- item.setAttribute('aria-selected', selected);
- var itemId = item.id;
- if (itemId && selected) {
- this.setAttribute('aria-activedescendant', itemId);
- }
- }
- }, {
- key: _symbols2.default.defaults,
- get: function get() {
- var defaults = _get(SelectionAriaActive.prototype.__proto__ || Object.getPrototypeOf(SelectionAriaActive.prototype), _symbols2.default.defaults, this) || {};
- defaults.role = 'listbox';
- return defaults;
- }
- }, {
- key: 'selectedItem',
- get: function get() {
- return _get(SelectionAriaActive.prototype.__proto__ || Object.getPrototypeOf(SelectionAriaActive.prototype), 'selectedItem', this);
- },
- set: function set(item) {
- if ('selectedItem' in base.prototype) {
- _set(SelectionAriaActive.prototype.__proto__ || Object.getPrototypeOf(SelectionAriaActive.prototype), 'selectedItem', item, this);
- }
- if (item == null) {
- // Selection was removed.
- this.removeAttribute('aria-activedescendant');
- }
- }
- }]);
-
- return SelectionAriaActive;
- }(base);
-
- return SelectionAriaActive;
-};
-
-},{"./symbols":16}],9:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-/* Exported function extends a base class with ShadowElementReferences. */
-exports.default = function (base) {
-
- /**
- * Mixin to create references to elements in a component's Shadow DOM subtree.
- *
- * This adds a member on the component called `this.$` that can be used to
- * reference shadow elements with IDs. E.g., if component's shadow contains an
- * element ``, then this mixin will create a member
- * `this.$.foo` that points to that button.
- *
- * Such references simplify a component's access to its own elements. In
- * exchange, this mixin trades off a one-time cost of querying all elements in
- * the shadow tree instead of paying an ongoing cost to query for an element
- * each time the component wants to inspect or manipulate it.
- *
- * This mixin expects the component to define a Shadow DOM subtree. You can
- * create that tree yourself, or make use of
- * [ShadowTemplateMixin](ShadowTemplateMixin.md).
- *
- * This mixin is inspired by Polymer's [automatic
- * node finding](https://www.polymer-project.org/1.0/docs/devguide/local-dom.html#node-finding)
- * feature.
- */
- var ShadowElementReferences = function (_base) {
- _inherits(ShadowElementReferences, _base);
-
- function ShadowElementReferences() {
- _classCallCheck(this, ShadowElementReferences);
-
- var _this = _possibleConstructorReturn(this, (ShadowElementReferences.__proto__ || Object.getPrototypeOf(ShadowElementReferences)).call(this));
-
- if (_this.shadowRoot) {
- // Look for elements in the shadow subtree that have id attributes.
- // An alternatively implementation of this mixin would be to just define
- // a this.$ getter that lazily does this search the first time someone
- // tries to access this.$. That might introduce some complexity – if the
- // the tree changed after it was first populated, the result of
- // searching for a node might be somewhat unpredictable.
- _this.$ = {};
- var nodesWithIds = _this.shadowRoot.querySelectorAll('[id]');
- [].forEach.call(nodesWithIds, function (node) {
- var id = node.getAttribute('id');
- _this.$[id] = node;
- });
- }
- return _this;
- }
-
- /**
- * The collection of references to the elements with IDs in a component's
- * Shadow DOM subtree.
- *
- * @type {object}
- * @member $
- */
-
-
- return ShadowElementReferences;
- }(base);
-
- return ShadowElementReferences;
-};
-
-},{}],10:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _symbols = require('../src/symbols');
-
-var _symbols2 = _interopRequireDefault(_symbols);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-/* Exported function extends a base class with ShadowTemplate. */
-exports.default = function (base) {
-
- /**
- * Mixin for stamping a template into a Shadow DOM subtree upon component
- * instantiation.
- *
- * To use this mixin, define a `template` property as a string or HTML
- * `` element:
- *
- * class MyElement extends ShadowTemplateMixin(HTMLElement) {
- * get [symbols.template]() {
- * return `Hello, world .`;
- * }
- * }
- *
- * When your component class is instantiated, a shadow root will be created on
- * the instance, and the contents of the template will be cloned into the
- * shadow root. If your component does not define a `template` property, this
- * mixin has no effect.
- *
- * For the time being, this extension retains support for Shadow DOM v0. That
- * will eventually be deprecated as browsers (and the Shadow DOM polyfill)
- * implement Shadow DOM v1.
- */
- var ShadowTemplate = function (_base) {
- _inherits(ShadowTemplate, _base);
-
- /*
- * If the component defines a template, a shadow root will be created on the
- * component instance, and the template stamped into it.
- */
- function ShadowTemplate() {
- _classCallCheck(this, ShadowTemplate);
-
- var _this = _possibleConstructorReturn(this, (ShadowTemplate.__proto__ || Object.getPrototypeOf(ShadowTemplate)).call(this));
-
- var template = _this[_symbols2.default.template];
- // TODO: Save the processed template with the component's class prototype
- // so it doesn't need to be processed with every instantiation.
- if (template) {
-
- if (typeof template === 'string') {
- // Upgrade plain string to real template.
- template = createTemplateWithInnerHTML(template);
- }
-
- if (window.ShadowDOMPolyfill) {
- shimTemplateStyles(template, _this.localName);
- }
-
- var root = _this.attachShadow({ mode: 'open' });
- var clone = document.importNode(template.content, true);
- root.appendChild(clone);
- }
- return _this;
- }
-
- return ShadowTemplate;
- }(base);
-
- return ShadowTemplate;
-};
-
-// Convert a plain string of HTML into a real template element.
-
-
-function createTemplateWithInnerHTML(innerHTML) {
- var template = document.createElement('template');
- // REVIEW: Is there an easier way to do this?
- // We'd like to just set innerHTML on the template content, but since it's
- // a DocumentFragment, that doesn't work.
- var div = document.createElement('div');
- div.innerHTML = innerHTML;
- while (div.childNodes.length > 0) {
- template.content.appendChild(div.childNodes[0]);
- }
- return template;
-}
-
-// Invoke basic style shimming with ShadowCSS.
-function shimTemplateStyles(template, tag) {
- window.WebComponents.ShadowCSS.shimStyling(template.content, tag);
-}
-
-},{"../src/symbols":16}],11:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
-
-var _get = function get(object, property, receiver) { if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { return get(parent, property, receiver); } } else if ("value" in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } };
-
-var _set = function set(object, property, value, receiver) { var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent !== null) { set(parent, property, value, receiver); } } else if ("value" in desc && desc.writable) { desc.value = value; } else { var setter = desc.set; if (setter !== undefined) { setter.call(receiver, value); } } return value; };
-
-var _createSymbol = require('./createSymbol');
-
-var _createSymbol2 = _interopRequireDefault(_createSymbol);
-
-var _symbols = require('./symbols');
-
-var _symbols2 = _interopRequireDefault(_symbols);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-// Symbols for private data members on an element.
-var canSelectNextSymbol = (0, _createSymbol2.default)('canSelectNext');
-var canSelectPreviousSymbol = (0, _createSymbol2.default)('canSelectPrevious');
-var selectionRequiredSymbol = (0, _createSymbol2.default)('selectionRequired');
-var selectionWrapsSymbol = (0, _createSymbol2.default)('selectionWraps');
-
-// We want to expose both selectedIndex and selectedItem as independent
-// properties but keep them in sync. This allows a component user to reference
-// the selection by whatever means is most natural for their situation.
-//
-// To efficiently keep these properties in sync, we track "external" and
-// "internal" references for each property:
-//
-// The external index or item is the one we report to the outside world when
-// asked for selection. When handling a change to index or item, we update the
-// external reference as soon as possible, so that if anyone immediately asks
-// for the current selection, they will receive a stable answer.
-//
-// The internal index or item tracks whichever index or item last received the
-// full set of processing. Processing includes raising a change event for the
-// new value. Once we've begun that processing, we store the new value as the
-// internal value to indicate we've handled it.
-//
-var externalSelectedIndexSymbol = (0, _createSymbol2.default)('externalSelectedIndex');
-var externalSelectedItemSymbol = (0, _createSymbol2.default)('externalSelectedItem');
-var internalSelectedIndexSymbol = (0, _createSymbol2.default)('internalSelectedIndex');
-var internalSelectedItemSymbol = (0, _createSymbol2.default)('internalSelectedItem');
-
-/* Exported function extends a base class with SingleSelection. */
-
-exports.default = function (base) {
-
- /**
- * Mixin which manages single-selection semantics for items in a list.
- *
- * This mixin expects a component to provide an `items` Array or NodeList of
- * all elements in the list. A standard way to do that with is the
- * [ContentItemsMixin](ContentItemsMixin.md), which takes a component's
- * content (typically its distributed children) as the set of list items; see
- * that mixin for details.
- *
- * This mixin tracks a single selected item in the list, and provides means to
- * get and set that state by item position (`selectedIndex`) or item identity
- * (`selectedItem`). The selection can be moved in the list via the methods
- * `selectFirst`, `selectLast`, `selectNext`, and `selectPrevious`.
- *
- * This mixin does not produce any user-visible effects to represent
- * selection. Other mixins, such as
- * [SelectionAriaActiveMixin](SelectionAriaActiveMixin.md),
- * [SelectionHighlightMixin](SelectionHighlightMixin.md) and
- * [SelectionInViewMixin](SelectionInViewMixin.md), modify the selected item
- * in common ways to let the user know a given item is selected or not
- * selected.
- */
- var SingleSelection = function (_base) {
- _inherits(SingleSelection, _base);
-
- function SingleSelection() {
- _classCallCheck(this, SingleSelection);
-
- // Set defaults.
- var _this = _possibleConstructorReturn(this, (SingleSelection.__proto__ || Object.getPrototypeOf(SingleSelection)).call(this));
-
- if (typeof _this.selectionRequired === 'undefined') {
- _this.selectionRequired = _this[_symbols2.default.defaults].selectionRequired;
- }
- if (typeof _this.selectionWraps === 'undefined') {
- _this.selectionWraps = _this[_symbols2.default.defaults].selectionWraps;
- }
- return _this;
- }
-
- /**
- * True if the selection can be moved to the next item, false if not (the
- * selected item is the last item in the list).
- *
- * @type {boolean}
- */
-
-
- _createClass(SingleSelection, [{
- key: _symbols2.default.itemAdded,
-
-
- /**
- * Handle a new item being added to the list.
- *
- * The default implementation of this method simply sets the item's
- * selection state to false.
- *
- * @param {HTMLElement} item - the item being added
- */
- value: function value(item) {
- if (_get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), _symbols2.default.itemAdded, this)) {
- _get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), _symbols2.default.itemAdded, this).call(this, item);
- }
- this[_symbols2.default.itemSelected](item, item === this.selectedItem);
- }
- }, {
- key: _symbols2.default.itemsChanged,
- value: function value() {
- if (_get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), _symbols2.default.itemsChanged, this)) {
- _get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), _symbols2.default.itemsChanged, this).call(this);
- }
-
- // In case selected item changed position or was removed.
- trackSelectedItem(this);
-
- // In case the change in items affected which navigations are possible.
- updatePossibleNavigations(this);
- }
-
- /**
- * Apply the indicate selection state to the item.
- *
- * The default implementation of this method does nothing. User-visible
- * effects will typically be handled by other mixins.
- *
- * @param {HTMLElement} item - the item being selected/deselected
- * @param {boolean} selected - true if the item is selected, false if not
- */
-
- }, {
- key: _symbols2.default.itemSelected,
- value: function value(item, selected) {
- if (_get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), _symbols2.default.itemSelected, this)) {
- _get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), _symbols2.default.itemSelected, this).call(this, item, selected);
- }
- }
-
- /**
- * The index of the item which is currently selected.
- *
- * A `selectedIndex` of -1 indicates there is no selection. Setting this
- * property to -1 will remove any existing selection.
- *
- * @type {number}
- */
-
- }, {
- key: 'selectFirst',
-
-
- /**
- * Select the first item in the list.
- */
- value: function selectFirst() {
- if (_get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), 'selectFirst', this)) {
- _get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), 'selectFirst', this).call(this);
- }
- return selectIndex(this, 0);
- }
-
- /**
- * True if the list should always have a selection (if it has items).
- *
- * @type {boolean}
- * @default false
- */
-
- }, {
- key: 'selectLast',
-
-
- /**
- * Select the last item in the list.
- */
- value: function selectLast() {
- if (_get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), 'selectLast', this)) {
- _get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), 'selectLast', this).call(this);
- }
- return selectIndex(this, this.items.length - 1);
- }
-
- /**
- * Select the next item in the list.
- */
-
- }, {
- key: 'selectNext',
- value: function selectNext() {
- if (_get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), 'selectNext', this)) {
- _get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), 'selectNext', this).call(this);
- }
- return selectIndex(this, this.selectedIndex + 1);
- }
-
- /**
- * Select the previous item in the list.
- *
- * If the list has no selection, the last item will be selected.
- */
-
- }, {
- key: 'selectPrevious',
- value: function selectPrevious() {
- if (_get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), 'selectPrevious', this)) {
- _get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), 'selectPrevious', this).call(this);
- }
- var newIndex = this.selectedIndex < 0 ? this.items.length - 1 : // No selection yet; select last item.
- this.selectedIndex - 1;
- return selectIndex(this, newIndex);
- }
-
- /**
- * Fires when the selectedItem property changes.
- *
- * @memberof SingleSelection
- * @event selected-item-changed
- * @param {HTMLElement} detail.selectedItem The new selected item.
- * @param {HTMLElement} detail.previousItem The previously selected item.
- */
-
- /**
- * Fires when the selectedIndex property changes.
- *
- * @memberof SingleSelection
- * @event selected-index-changed
- * @param {number} detail.selectedIndex The new selected index.
- */
-
- }, {
- key: 'canSelectNext',
- get: function get() {
- return this[canSelectNextSymbol];
- },
- set: function set(canSelectNext) {
- var previousCanSelectNext = this[canSelectNextSymbol];
- this[canSelectNextSymbol] = canSelectNext;
- if ('canSelectNext' in base.prototype) {
- _set(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), 'canSelectNext', canSelectNext, this);
- }
- if (canSelectNext !== previousCanSelectNext) {
- this.dispatchEvent(new CustomEvent('can-select-next-changed'));
- }
- }
-
- /**
- * True if the selection can be moved to the previous item, false if not
- * (the selected item is the first one in the list).
- *
- * @type {boolean}
- */
-
- }, {
- key: 'canSelectPrevious',
- get: function get() {
- return this[canSelectPreviousSymbol];
- },
- set: function set(canSelectPrevious) {
- var previousCanSelectPrevious = this[canSelectPreviousSymbol];
- this[canSelectPreviousSymbol] = canSelectPrevious;
- if ('canSelectPrevious' in base.prototype) {
- _set(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), 'canSelectPrevious', canSelectPrevious, this);
- }
- if (canSelectPrevious !== previousCanSelectPrevious) {
- this.dispatchEvent(new CustomEvent('can-select-previous-changed'));
- }
- }
- }, {
- key: _symbols2.default.defaults,
- get: function get() {
- var defaults = _get(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), _symbols2.default.defaults, this) || {};
- defaults.selectionRequired = false;
- defaults.selectionWraps = false;
- return defaults;
- }
- }, {
- key: 'selectedIndex',
- get: function get() {
- return this[externalSelectedIndexSymbol] != null ? this[externalSelectedIndexSymbol] : -1;
- },
- set: function set(index) {
- // See notes at top about internal vs. external copies of this property.
- var previousSelectedIndex = this[internalSelectedIndexSymbol];
- var item = void 0;
- if (index !== this[externalSelectedIndexSymbol]) {
- // Store the new index and the corresponding item.
- var items = this.items;
- var hasItems = items && items.length > 0;
- if (!(hasItems && index >= 0 && index < items.length)) {
- index = -1; // No item at that index.
- }
- this[externalSelectedIndexSymbol] = index;
- item = hasItems && index >= 0 ? items[index] : null;
- this[externalSelectedItemSymbol] = item;
- } else {
- item = this[externalSelectedItemSymbol];
- }
-
- // Now let super do any work.
- if ('selectedIndex' in base.prototype) {
- _set(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), 'selectedIndex', index, this);
- }
-
- if (index !== previousSelectedIndex) {
- // The selected index changed.
- this[internalSelectedIndexSymbol] = index;
-
- var event = new CustomEvent('selected-index-changed', {
- detail: {
- selectedIndex: index,
- value: index // for Polymer binding. TODO: Verify still necessary
- }
- });
- this.dispatchEvent(event);
- }
-
- if (this[internalSelectedItemSymbol] !== item) {
- // Update selectedItem property so it can have its own effects.
- this.selectedItem = item;
- }
- }
-
- /**
- * The currently selected item, or null if there is no selection.
- *
- * Setting this property to null deselects any currently-selected item.
- * Setting this property to an object that is not in the list has no effect.
- *
- * TODO: Even if selectionRequired, can still explicitly set selectedItem to null.
- * TODO: If selectionRequired, leave selection alone?
- *
- * @type {object}
- */
-
- }, {
- key: 'selectedItem',
- get: function get() {
- return this[externalSelectedItemSymbol] || null;
- },
- set: function set(item) {
- // See notes at top about internal vs. external copies of this property.
- var previousSelectedItem = this[internalSelectedItemSymbol];
- var index = void 0;
- if (item !== this[externalSelectedItemSymbol]) {
- // Store item and look up corresponding index.
- var items = this.items;
- var hasItems = items && items.length > 0;
- index = hasItems ? Array.prototype.indexOf.call(items, item) : -1;
- this[externalSelectedIndexSymbol] = index;
- if (index < 0) {
- item = null; // The indicated item isn't actually in `items`.
- }
- this[externalSelectedItemSymbol] = item;
- } else {
- index = this[externalSelectedIndexSymbol];
- }
-
- // Now let super do any work.
- if ('selectedItem' in base.prototype) {
- _set(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), 'selectedItem', item, this);
- }
-
- if (item !== previousSelectedItem) {
- // The selected item changed.
- this[internalSelectedItemSymbol] = item;
-
- if (previousSelectedItem) {
- // Update selection state of old item.
- this[_symbols2.default.itemSelected](previousSelectedItem, false);
- }
- if (item) {
- // Update selection state to new item.
- this[_symbols2.default.itemSelected](item, true);
- }
-
- updatePossibleNavigations(this);
-
- var event = new CustomEvent('selected-item-changed', {
- detail: {
- selectedItem: item,
- value: item // for Polymer binding
- }
- });
- this.dispatchEvent(event);
- }
-
- if (this[internalSelectedIndexSymbol] !== index) {
- // Update selectedIndex property so it can have its own effects.
- this.selectedIndex = index;
- }
- }
- }, {
- key: 'selectionRequired',
- get: function get() {
- return this[selectionRequiredSymbol];
- },
- set: function set(selectionRequired) {
- this[selectionRequiredSymbol] = selectionRequired;
- if ('selectionRequired' in base.prototype) {
- _set(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), 'selectionRequired', selectionRequired, this);
- }
- trackSelectedItem(this);
- }
-
- /**
- * True if selection navigations wrap from last to first, and vice versa.
- *
- * @type {boolean}
- * @default false
- */
-
- }, {
- key: 'selectionWraps',
- get: function get() {
- return this[selectionWrapsSymbol];
- },
- set: function set(value) {
- this[selectionWrapsSymbol] = String(value) === 'true';
- if ('selectionWraps' in base.prototype) {
- _set(SingleSelection.prototype.__proto__ || Object.getPrototypeOf(SingleSelection.prototype), 'selectionWraps', value, this);
- }
- updatePossibleNavigations(this);
- }
- }]);
-
- return SingleSelection;
- }(base);
-
- return SingleSelection;
-};
-
-// Ensure the given index is within bounds, and select it if it's not already
-// selected.
-
-
-function selectIndex(element, index) {
- var count = element.items.length;
-
- var boundedIndex = element.selectionWraps ?
- // JavaScript mod doesn't handle negative numbers the way we want to wrap.
- // See http://stackoverflow.com/a/18618250/76472
- (index % count + count) % count :
-
- // Keep index within bounds of array.
- Math.max(Math.min(index, count - 1), 0);
-
- var previousIndex = element.selectedIndex;
- if (previousIndex !== boundedIndex) {
- element.selectedIndex = boundedIndex;
- return true;
- } else {
- return false;
- }
-}
-
-// Following a change in the set of items, or in the value of the
-// `selectionRequired` property, reacquire the selected item. If it's moved,
-// update `selectedIndex`. If it's been removed, and a selection is required,
-// try to select another item.
-function trackSelectedItem(element) {
-
- var items = element.items;
- var itemCount = items ? items.length : 0;
-
- var previousSelectedItem = element.selectedItem;
- if (!previousSelectedItem) {
- // No item was previously selected.
- if (element.selectionRequired) {
- // Select the first item by default.
- element.selectedIndex = 0;
- }
- } else if (itemCount === 0) {
- // We've lost the selection, and there's nothing left to select.
- element.selectedItem = null;
- } else {
- // Try to find the previously-selected item in the current set of items.
- var indexInCurrentItems = Array.prototype.indexOf.call(items, previousSelectedItem);
- var previousSelectedIndex = element.selectedIndex;
- if (indexInCurrentItems < 0) {
- // Previously-selected item was removed from the items.
- // Select the item at the same index (if it exists) or as close as possible.
- var newSelectedIndex = Math.min(previousSelectedIndex, itemCount - 1);
- // Select by item, since index may be the same, and we want to raise the
- // selected-item-changed event.
- element.selectedItem = items[newSelectedIndex];
- } else if (indexInCurrentItems !== previousSelectedIndex) {
- // Previously-selected item still there, but changed position.
- element.selectedIndex = indexInCurrentItems;
- }
- }
-}
-
-// Following a change in selection, report whether it's now possible to
-// go next/previous from the given index.
-function updatePossibleNavigations(element) {
- var canSelectNext = void 0;
- var canSelectPrevious = void 0;
- var items = element.items;
- if (items == null || items.length === 0) {
- // No items to select.
- canSelectNext = false;
- canSelectPrevious = false;
- }if (element.selectionWraps) {
- // Since there are items, can always go next/previous.
- canSelectNext = true;
- canSelectPrevious = true;
- } else {
- var index = element.selectedIndex;
- if (index < 0 && items.length > 0) {
- // Special case. If there are items but no selection, declare that it's
- // always possible to go next/previous to create a selection.
- canSelectNext = true;
- canSelectPrevious = true;
- } else {
- // Normal case: we have an index in a list that has items.
- canSelectPrevious = index > 0;
- canSelectNext = index < items.length - 1;
- }
- }
- if (element.canSelectNext !== canSelectNext) {
- element.canSelectNext = canSelectNext;
- }
- if (element.canSelectPrevious !== canSelectPrevious) {
- element.canSelectPrevious = canSelectPrevious;
- }
-}
-
-},{"./createSymbol":13,"./symbols":16}],12:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
-
-var _set = function set(object, property, value, receiver) { var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent !== null) { set(parent, property, value, receiver); } } else if ("value" in desc && desc.writable) { desc.value = value; } else { var setter = desc.set; if (setter !== undefined) { setter.call(receiver, value); } } return value; };
-
-var _get = function get(object, property, receiver) { if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { return get(parent, property, receiver); } } else if ("value" in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } };
-
-var _createSymbol = require('./createSymbol');
-
-var _createSymbol2 = _interopRequireDefault(_createSymbol);
-
-var _symbols = require('./symbols');
-
-var _symbols2 = _interopRequireDefault(_symbols);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-var playingSymbol = (0, _createSymbol2.default)('playing');
-var selectionTimerDurationSymbol = (0, _createSymbol2.default)('selectionTimerDuration');
-var timerTimeoutSymbol = (0, _createSymbol2.default)('timerTimeout');
-
-/* Exported function extends a base class with TimerSelection. */
-
-exports.default = function (base) {
-
- /**
- * Mixin which provides for automatic timed changes in selection.
- *
- * This mixin is useful for creating slideshow-like elements such as
- * [basic-slideshow](../packages/basic-slideshow) and
- * [basic-slideshow-with-controls](../packages/basic-slideshow-with-controls).
- *
- * Typical usage:
- *
- * class CarouselWithTimer extends TimerSelectionMixin(Carousel) {}
- * customElements.define('carousel-with-arrows', CarouselWithTimer);
- *
- * This mixin expects the component to define an `items` property, as well as
- * `selectFirst` and `selectNext` methods. You can implement those yourself,
- * or use [ContentItemsMixin](ContentItemsMixin.md) and
- * [SingleSelectionMixin](SingleSelectionMixin.md).
- */
- var TimerSelection = function (_base) {
- _inherits(TimerSelection, _base);
-
- function TimerSelection() {
- _classCallCheck(this, TimerSelection);
-
- // Set defaults.
- var _this = _possibleConstructorReturn(this, (TimerSelection.__proto__ || Object.getPrototypeOf(TimerSelection)).call(this));
-
- if (typeof _this.playing === 'undefined') {
- _this.playing = _this[_symbols2.default.defaults].playing;
- }
- if (typeof _this.selectionTimerDuration === 'undefined') {
- _this.selectionTimerDuration = _this[_symbols2.default.defaults].selectionTimerDuration;
- }
- return _this;
- }
-
- _createClass(TimerSelection, [{
- key: 'contentChanged',
- value: function contentChanged() {
- if (_get(TimerSelection.prototype.__proto__ || Object.getPrototypeOf(TimerSelection.prototype), 'contentChanged', this)) {
- _get(TimerSelection.prototype.__proto__ || Object.getPrototypeOf(TimerSelection.prototype), 'contentChanged', this).call(this);
- }
- restartTimer(this);
- }
- }, {
- key: 'play',
-
-
- /**
- * Begin automatic progression of the selection.
- */
- value: function play() {
- if (_get(TimerSelection.prototype.__proto__ || Object.getPrototypeOf(TimerSelection.prototype), 'play', this)) {
- _get(TimerSelection.prototype.__proto__ || Object.getPrototypeOf(TimerSelection.prototype), 'play', this).call(this);
- }
- startTimer(this);
- this[playingSymbol] = true;
- }
-
- /**
- * Pause automatic progression of the selection.
- */
-
- }, {
- key: 'pause',
- value: function pause() {
- if (_get(TimerSelection.prototype.__proto__ || Object.getPrototypeOf(TimerSelection.prototype), 'pause', this)) {
- _get(TimerSelection.prototype.__proto__ || Object.getPrototypeOf(TimerSelection.prototype), 'pause', this).call(this);
- }
- clearTimer(this);
- this[playingSymbol] = false;
- }
-
- /**
- * True if the selection is being automatically advanced.
- *
- * @type {boolean}
- * @default false
- */
-
- }, {
- key: _symbols2.default.defaults,
- get: function get() {
- var defaults = _get(TimerSelection.prototype.__proto__ || Object.getPrototypeOf(TimerSelection.prototype), _symbols2.default.defaults, this) || {};
- defaults.playing = false;
- defaults.selectionTimerDuration = 1000;
- return defaults;
- }
- }, {
- key: 'playing',
- get: function get() {
- return this[playingSymbol];
- },
- set: function set(playing) {
- var previousPlaying = this[playingSymbol];
- var parsed = String(playing) === 'true'; // Cast to boolean
- if ('playing' in base.prototype) {
- _set(TimerSelection.prototype.__proto__ || Object.getPrototypeOf(TimerSelection.prototype), 'playing', playing, this);
- }
- if (parsed !== previousPlaying) {
- if (playing) {
- this.play();
- } else {
- this.pause();
- }
- }
- }
-
- /*
- * When the selected item changes (because of something this mixin did, or
- * was changed by an outside agent like the user), we wait before advancing
- * to the next item. By triggering the next item this way, we implicitly get
- * a desirable behavior: if the user changes the selection (e.g., in a
- * carousel), we let them see that selection state for a while before
- * advancing the selection ourselves.
- */
-
- }, {
- key: 'selectedItem',
- get: function get() {
- return _get(TimerSelection.prototype.__proto__ || Object.getPrototypeOf(TimerSelection.prototype), 'selectedItem', this);
- },
- set: function set(item) {
- if ('selectedItem' in base.prototype) {
- _set(TimerSelection.prototype.__proto__ || Object.getPrototypeOf(TimerSelection.prototype), 'selectedItem', item, this);
- }
- restartTimer(this);
- }
-
- /**
- * The time in milliseconds that will elapse after the selection changes
- * before the selection will be advanced to the next item in the list.
- *
- * @type {number} - Time in milliseconds
- * @default 1000 (1 second)
- */
-
- }, {
- key: 'selectionTimerDuration',
- get: function get() {
- return this[selectionTimerDurationSymbol];
- },
- set: function set(value) {
- this[selectionTimerDurationSymbol] = parseInt(value);
- if ('selectionTimerDuration' in base.prototype) {
- _set(TimerSelection.prototype.__proto__ || Object.getPrototypeOf(TimerSelection.prototype), 'selectionTimerDuration', value, this);
- }
- }
- }]);
-
- return TimerSelection;
- }(base);
-
- return TimerSelection;
-};
-
-function clearTimer(element) {
- if (element[timerTimeoutSymbol]) {
- clearTimeout(element[timerTimeoutSymbol]);
- element[timerTimeoutSymbol] = null;
- }
-}
-
-function restartTimer(element) {
- clearTimer(element);
- if (element.playing && element.items && element.items.length > 0) {
- startTimer(element);
- }
-}
-
-function startTimer(element) {
- // If play() is called more than once, cancel any existing timer.
- clearTimer(element);
- element[timerTimeoutSymbol] = setTimeout(function () {
- selectNextWithWrap(element);
- }, element.selectionTimerDuration);
-}
-
-// Select the next item, wrapping to first item if necessary.
-function selectNextWithWrap(element) {
- var items = element.items;
- if (items && items.length > 0) {
- if (element.selectedIndex == null || element.selectedIndex === items.length - 1) {
- element.selectFirst();
- } else {
- element.selectNext();
- }
- }
-}
-
-},{"./createSymbol":13,"./symbols":16}],13:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-exports.default = createSymbol;
-/**
- * Helper function to create a symbol that can be used for associating private
- * data with an element.
- *
- * Mixins and component classes often want to associate private data with an
- * element instance, but JavaScript does not have direct support for true
- * private properties. One approach is to use the
- * [Symbol](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Symbol)
- * data type to set and retrieve data on an element.
- *
- * Unfortunately, the Symbol type is not available in Internet Explorer 11. The
- * `createSymbol` helper function exists as a workaround for IE 11. Rather than
- * returning a true Symbol, it simply returns an underscore-prefixed string.
- *
- * Usage:
- *
- * const fooSymbol = createSymbol('foo');
- *
- * class MyElement extends HTMLElement {
- * get foo() {
- * return this[fooSymbol];
- * }
- * set foo(value) {
- * this[fooSymbol] = value;
- * }
- * }
- *
- * In IE 11, this sample will "hide" data behind an instance property this._foo.
- * The use of the underscore is meant to reduce (not eliminate) the potential
- * for name conflicts, and discourage (not prevent) external access to this
- * data. In modern browsers, the above code will eliminate the potential of
- * naming conflicts, and better hide the data behind a real Symbol.
- *
- * @function createSymbol
- * @param {string} description - A string to identify the symbol when debugging
- */
-function createSymbol(description) {
- return typeof Symbol === 'function' ? Symbol(description) : '_' + description;
-}
-
-},{}],14:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-exports.default = microtask;
-/*
- * Microtask helper for IE 11.
- *
- * Executing a function as a microtask is trivial in browsers that support
- * promises, whose then() clauses use microtask timing. IE 11 doesn't support
- * promises, but does support MutationObservers, which are also executed as
- * microtasks. So this helper uses an MutationObserver to achieve microtask
- * timing.
- *
- * See https://jakearchibald.com/2015/tasks-microtasks-queues-and-schedules/
- *
- * Inspired by Polymer's async() function.
- */
-
-// The queue of pending callbacks to be executed as microtasks.
-var callbacks = [];
-
-// Create an element that we will modify to force observable mutations.
-var element = document.createTextNode('');
-
-// A monotonically-increasing value.
-var counter = 0;
-
-/**
- * Add a callback to the microtask queue.
- *
- * This uses a MutationObserver so that it works on IE 11.
- *
- * NOTE: IE 11 may actually use timeout timing with MutationObservers. This
- * needs more investigation.
- *
- * @function microtask
- * @param {function} callback
- */
-function microtask(callback) {
- callbacks.push(callback);
- // Force a mutation.
- element.textContent = ++counter;
-}
-
-// Execute any pending callbacks.
-function executeCallbacks() {
- while (callbacks.length > 0) {
- var callback = callbacks.shift();
- callback();
- }
-}
-
-// Create the observer.
-var observer = new MutationObserver(executeCallbacks);
-observer.observe(element, {
- characterData: true
-});
-
-},{}],15:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createSymbol = require('./createSymbol');
-
-var _createSymbol2 = _interopRequireDefault(_createSymbol);
-
-var _toggleClass2 = require('./toggleClass');
-
-var _toggleClass3 = _interopRequireDefault(_toggleClass2);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-// Symbols for private data members on an element.
-var safeToSetAttributesSymbol = (0, _createSymbol2.default)('safeToSetAttributes');
-var pendingAttributesSymbol = (0, _createSymbol2.default)('pendingAttributes');
-var pendingClassesSymbol = (0, _createSymbol2.default)('pendingClasses');
-
-/**
- * Helper functions for updating attributes, including the `class` attribute.
- */
-exports.default = {
-
- /**
- * Perform any pending updates to attributes and classes.
- *
- * This writes any `setAttribute` or `toggleClass` values that were performed
- * before an element was attached to the document for the first time.
- *
- * This method should be called by mixins/components in their
- * `connectedCallback`. If mulitple mixins/components invoke this during the
- * same `connectedCallback`, only the first call will have any effect. The
- * subsequent calls will be harmless.
- *
- * @param {HTMLElement} element - The element being added to the document.
- */
- connected: function connected(element) {
- element[safeToSetAttributesSymbol] = true;
-
- // Set any pending attributes.
- if (element[pendingAttributesSymbol]) {
- for (var attribute in element[pendingAttributesSymbol]) {
- var value = element[pendingAttributesSymbol][attribute];
- setAttributeToElement(element, attribute, value);
- }
- element[pendingAttributesSymbol] = null;
- }
-
- // Set any pending classes.
- if (element[pendingClassesSymbol]) {
- for (var className in element[pendingClassesSymbol]) {
- var _value = element[pendingClassesSymbol][className];
- (0, _toggleClass3.default)(element, className, _value);
- }
- element[pendingClassesSymbol] = null;
- }
- },
-
-
- /**
- * Set/unset the attribute with the indicated name.
- *
- * This method exists primarily to handle the case where an element wants to
- * set a default property value that should be reflected as an attribute. An
- * important limitation of custom element consturctors is that they cannot
- * set attributes. A call to `setAttribute` during the constructor will
- * be deferred until the element is connected to the document.
- *
- * @param {string} attribute - The name of the *attribute* (not property) to set.
- * @param {object} value - The value to set. If null, the attribute will be removed.
- */
- setAttribute: function setAttribute(element, attribute, value) {
- if (element[safeToSetAttributesSymbol]) {
- // Safe to set attributes immediately.
- setAttributeToElement(element, attribute, value);
- } else {
- // Defer setting attributes until the first time we're connected.
- if (!element[pendingAttributesSymbol]) {
- element[pendingAttributesSymbol] = {};
- }
- element[pendingAttributesSymbol][attribute] = value;
- }
- },
-
-
- /**
- * Set/unset the class with the indicated name.
- *
- * This method exists primarily to handle the case where an element wants to
- * set a default property value that should be reflected as as class. An
- * important limitation of custom element consturctors is that they cannot
- * set attributes, including the `class` attribute. A call to
- * `toggleClass` during the constructor will be deferred until the element
- * is connected to the document.
- *
- * @param {string} className - The name of the class to set.
- * @param {object} value - True to set the class, false to remove it.
- */
- toggleClass: function toggleClass(element, className, value) {
- if (element[safeToSetAttributesSymbol]) {
- // Safe to set class immediately.
- (0, _toggleClass3.default)(element, className, value);
- } else {
- // Defer setting class until the first time we're connected.
- if (!element[pendingClassesSymbol]) {
- element[pendingClassesSymbol] = {};
- }
- element[pendingClassesSymbol][className] = value;
- }
- }
-};
-
-// Reflect the attribute to the given element.
-// If the value is null, remove the attribute.
-
-function setAttributeToElement(element, attributeName, value) {
- if (value === null || typeof value === 'undefined') {
- element.removeAttribute(attributeName);
- } else {
- var text = String(value);
- // Avoid recursive attributeChangedCallback calls.
- if (element.getAttribute(attributeName) !== text) {
- element.setAttribute(attributeName, value);
- }
- }
-}
-
-},{"./createSymbol":13,"./toggleClass":17}],16:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createSymbol = require('./createSymbol');
-
-var _createSymbol2 = _interopRequireDefault(_createSymbol);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-/**
- * A collection of Symbol objects for standard component properties and methods.
- *
- * These Symbol objects are used to allow mixins and a component to internally
- * communicate, without exposing these properties and methods in the component's
- * public API.
- *
- * To use these Symbol objects in your own component, include this module and
- * then create a property or method whose key is the desired Symbol.
- *
- * import 'SingleSelectionMixin' from 'basic-component-mixins/src/SingleSelectionMixin';
- * import 'symbols' from 'basic-component-mixins/src/symbols';
- *
- * class MyElement extends SingleSelectionMixin(HTMLElement) {
- * [symbols.itemSelected](item, selected) {
- * // This will be invoked whenever an item is selected/deselected.
- * }
- * }
- *
- * @module symbols
- */
-var symbols = {
-
- /**
- * Symbol for the `defaults` property.
- *
- * This property can be used to set or override defaults that will be applied
- * to a new component instance. When implementing this property, take care to
- * first acquire any defaults defined by the superclass. The standard idiom is
- * as follows:
- *
- * get [symbols.defaults]() {
- * const defaults = super[symbols.defaults] || {};
- * // Set or override default values here
- * defaults.customProperty = false;
- * return defaults;
- * }
- *
- * @var {object} defaults
- */
- defaults: (0, _createSymbol2.default)('defaults'),
-
- /**
- * Symbol for the `dragging` property.
- *
- * Components like carousels often define animated CSS transitions for
- * sliding effects. Such a transition should usually *not* be applied while
- * the user is dragging, because a CSS animation will introduce a lag that
- * makes the swipe feel sluggish. Instead, as long as the user is dragging
- * with their finger down, the transition should be suppressed. When the
- * user releases their finger, the transition can be restored, allowing the
- * animation to show the carousel sliding into its final position.
- *
- * @type {boolean} true if a drag is in progress, false if not.
- */
- dragging: (0, _createSymbol2.default)('dragging'),
-
- /**
- * Symbol for the `goDown` method.
- *
- * This method is invoked when the user wants to go/navigate down.
- *
- * @function goDown
- */
- goDown: (0, _createSymbol2.default)('goDown'),
-
- /**
- * Symbol for the `goEnd` method.
- *
- * This method is invoked when the user wants to go/navigate to the end (e.g.,
- * of a list).
- *
- * @function goEnd
- */
- goEnd: (0, _createSymbol2.default)('goEnd'),
-
- /**
- * Symbol for the `goLeft` method.
- *
- * This method is invoked when the user wants to go/navigate left.
- *
- * @function goLeft
- */
- goLeft: (0, _createSymbol2.default)('goLeft'),
-
- /**
- * Symbol for the `goRight` method.
- *
- * This method is invoked when the user wants to go/navigate right.
- *
- * @function goRight
- */
- goRight: (0, _createSymbol2.default)('goRight'),
-
- /**
- * Symbol for the `goStart` method.
- *
- * This method is invoked when the user wants to go/navigate to the start
- * (e.g., of a list).
- *
- * @function goStart
- */
- goStart: (0, _createSymbol2.default)('goStart'),
-
- /**
- * Symbol for the `goUp` method.
- *
- * This method is invoked when the user wants to go/navigate up.
- *
- * @function goUp
- */
- goUp: (0, _createSymbol2.default)('goUp'),
-
- /**
- * Symbol for the `itemAdded` method.
- *
- * This method is invoked when a new item is added to a list.
- *
- * @function itemAdded
- * @param {HTMLElement} item - the item being selected/deselected
- */
- itemAdded: (0, _createSymbol2.default)('itemAdded'),
-
- /**
- * Symbol for the `itemsChanged` method.
- *
- * This method is invoked when the underlying contents change. It is also
- * invoked on component initialization – since the items have "changed" from
- * being nothing.
- */
- itemsChanged: (0, _createSymbol2.default)('itemsChanged'),
-
- /**
- * Symbol for the `itemSelected` method.
- *
- * This method is invoked when an item becomes selected or deselected.
- *
- * @function itemSelected
- * @param {HTMLElement} item - the item being selected/deselected
- * @param {boolean} selected - true if the item is selected, false if not
- */
- itemSelected: (0, _createSymbol2.default)('itemSelected'),
-
- /**
- * Symbol for the `keydown` method.
- *
- * This method is invoked when an element receives a `keydown` event.
- *
- * @function keydown
- * @param {KeyboardEvent} event - the event being processed
- */
- keydown: (0, _createSymbol2.default)('keydown'),
-
- /**
- * Symbol for the `template` property.
- *
- * This property returns a component's template.
- *
- * @type {string|HTMLElement}
- */
- template: (0, _createSymbol2.default)('template')
-};
-
-exports.default = symbols;
-
-},{"./createSymbol":13}],17:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-exports.default = toggleClass;
-/**
- * Helper function for standard classList.toggle() behavior on old browsers,
- * namely IE 11.
- *
- * The standard
- * [classlist](https://developer.mozilla.org/en-US/docs/Web/API/Element/classList)
- * object has a `toggle()` function that supports a second Boolean parameter
- * that can be used to succinctly turn a class on or off. This feature is often
- * useful in designing custom elements, which may want to externally reflect
- * component state in a CSS class that can be used for styling purposes.
- *
- * Unfortunately, IE 11 does not support the Boolean parameter to
- * `classList.toggle()`. This helper function behaves like the standard
- * `toggle()`, including support for the Boolean parameter, so that it can be
- * used even on IE 11.
- *
- * @function toggleClass
- * @param {HTMLElement} element - The element to modify
- * @param {string} className - The class to add/remove
- * @param {boolean} [force] - Force the class to be added (if true) or removed
- * (if false)
- */
-function toggleClass(element, className, force) {
- var classList = element.classList;
- var addClass = typeof force === 'undefined' ? !classList.contains(className) : force;
- if (addClass) {
- classList.add(className);
- } else {
- classList.remove(className);
- }
- return addClass;
-}
-
-},{}],18:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _AttributeMarshallingMixin = require('../../basic-component-mixins/src/AttributeMarshallingMixin');
-
-var _AttributeMarshallingMixin2 = _interopRequireDefault(_AttributeMarshallingMixin);
-
-var _ComposableMixin = require('../../basic-component-mixins/src/ComposableMixin');
-
-var _ComposableMixin2 = _interopRequireDefault(_ComposableMixin);
-
-var _DistributedChildrenMixin = require('../../basic-component-mixins/src/DistributedChildrenMixin');
-
-var _DistributedChildrenMixin2 = _interopRequireDefault(_DistributedChildrenMixin);
-
-var _ShadowElementReferencesMixin = require('../../basic-component-mixins/src/ShadowElementReferencesMixin');
-
-var _ShadowElementReferencesMixin2 = _interopRequireDefault(_ShadowElementReferencesMixin);
-
-var _ShadowTemplateMixin = require('../../basic-component-mixins/src/ShadowTemplateMixin');
-
-var _ShadowTemplateMixin2 = _interopRequireDefault(_ShadowTemplateMixin);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-/**
- * A sample general-purpose base class for defining custom elements that mixes
- * in some common features: template stamping into a shadow root, shadow element
- * references, marshalling attributes to properties, and retrieving the children
- * distributed to a component.
- *
- * This base class is not special in any way, and is defined only as a
- * convenient shorthand for applying the mixins listed above. You can use this
- * class as a base class for your own elements, or easily create your own base
- * class by applying the same set of mixins.
- *
- * The ElementBase base class does not register itself as a custom element with
- * the browser, and hence cannot be independently instantiated.
- *
- * @mixes AttributeMarshallingMixin
- * @mixes ComposableMixin
- * @mixes DistributedChildrenMixin
- * @mixes ShadowElementReferencesMixin
- * @mixes ShadowTemplateMixin
- */
-var ElementBase = function (_ComposableMixin$comp) {
- _inherits(ElementBase, _ComposableMixin$comp);
-
- function ElementBase() {
- _classCallCheck(this, ElementBase);
-
- return _possibleConstructorReturn(this, (ElementBase.__proto__ || Object.getPrototypeOf(ElementBase)).apply(this, arguments));
- }
-
- return ElementBase;
-}((0, _ComposableMixin2.default)(HTMLElement).compose(_ShadowTemplateMixin2.default, // before node finding, so shadow root is populated
-_ShadowElementReferencesMixin2.default, // before marshalling, so properties can use refs
-_AttributeMarshallingMixin2.default, _DistributedChildrenMixin2.default));
-
-exports.default = ElementBase;
-
-},{"../../basic-component-mixins/src/AttributeMarshallingMixin":1,"../../basic-component-mixins/src/ComposableMixin":2,"../../basic-component-mixins/src/DistributedChildrenMixin":5,"../../basic-component-mixins/src/ShadowElementReferencesMixin":9,"../../basic-component-mixins/src/ShadowTemplateMixin":10}],19:[function(require,module,exports){
-'use strict';
-
-var _Slideshow = require('./src/Slideshow');
-
-var _Slideshow2 = _interopRequireDefault(_Slideshow);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-window.Basic = window.Basic || {}; /*
- * This file is transpiled to create an ES5-compatible distribution in which
- * the package's main feature(s) are available via the window.Basic global.
- * If you're already using ES6 yourself, ignore this file, and instead import
- * the source file(s) you want from the src folder.
- */
-
-window.Basic.Slideshow = _Slideshow2.default;
-
-},{"./src/Slideshow":20}],20:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
-
-var _get = function get(object, property, receiver) { if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { return get(parent, property, receiver); } } else if ("value" in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } };
-
-var _ElementBase = require('../../basic-element-base/src/ElementBase');
-
-var _ElementBase2 = _interopRequireDefault(_ElementBase);
-
-var _ContentItemsMixin = require('../../basic-component-mixins/src/ContentItemsMixin');
-
-var _ContentItemsMixin2 = _interopRequireDefault(_ContentItemsMixin);
-
-var _DistributedChildrenContentMixin = require('../../basic-component-mixins/src/DistributedChildrenContentMixin');
-
-var _DistributedChildrenContentMixin2 = _interopRequireDefault(_DistributedChildrenContentMixin);
-
-var _FractionalSelectionMixin = require('../../basic-component-mixins/src/FractionalSelectionMixin');
-
-var _FractionalSelectionMixin2 = _interopRequireDefault(_FractionalSelectionMixin);
-
-var _SelectionAnimationMixin = require('../../basic-component-mixins/src/SelectionAnimationMixin');
-
-var _SelectionAnimationMixin2 = _interopRequireDefault(_SelectionAnimationMixin);
-
-var _SelectionAriaActiveMixin = require('../../basic-component-mixins/src/SelectionAriaActiveMixin');
-
-var _SelectionAriaActiveMixin2 = _interopRequireDefault(_SelectionAriaActiveMixin);
-
-var _SingleSelectionMixin = require('../../basic-component-mixins/src/SingleSelectionMixin');
-
-var _SingleSelectionMixin2 = _interopRequireDefault(_SingleSelectionMixin);
-
-var _symbols = require('../../basic-component-mixins/src/symbols');
-
-var _symbols2 = _interopRequireDefault(_symbols);
-
-var _TimerSelectionMixin = require('../../basic-component-mixins/src/TimerSelectionMixin');
-
-var _TimerSelectionMixin2 = _interopRequireDefault(_TimerSelectionMixin);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-var base = _ElementBase2.default.compose(_ContentItemsMixin2.default, _DistributedChildrenContentMixin2.default, _FractionalSelectionMixin2.default, _SelectionAnimationMixin2.default, _SelectionAriaActiveMixin2.default, _SingleSelectionMixin2.default, _TimerSelectionMixin2.default);
-
-/**
- * Slideshow with animated transitions.
- *
- * By default the slideshow will immediately begin playing when it is connected
- * to the document, advance every 3000 ms (3 seconds), and use a simple
- * crossfade effect.
- *
- * This component can be used on its own. To incorporate slideshow behavior into
- * a component of your own, apply the
- * [TimerSelectionMixin](../basic-component-mixins/docs/TimerSelectionMixin.md).
- *
- * @extends ElementBase
- * @mixes ContentItemsMixin
- * @mixes DistributedChildrenContentMixin
- * @mixes FractionalSelectionMixin
- * @mixes SelectionAnimationMixin
- * @mixes SelectionAriaActiveMixin
- * @mixes SingleSelectionMixin
- * @mixes TimerSelectionMixin
- */
-
-var Slideshow = function (_base) {
- _inherits(Slideshow, _base);
-
- function Slideshow() {
- _classCallCheck(this, Slideshow);
-
- return _possibleConstructorReturn(this, (Slideshow.__proto__ || Object.getPrototypeOf(Slideshow)).apply(this, arguments));
- }
-
- _createClass(Slideshow, [{
- key: _symbols2.default.defaults,
- get: function get() {
- var defaults = _get(Slideshow.prototype.__proto__ || Object.getPrototypeOf(Slideshow.prototype), _symbols2.default.defaults, this) || {};
- defaults.playing = true;
- defaults.selectionAnimationDuration = 500;
- defaults.selectionAnimationEffect = 'crossfade';
- defaults.selectionRequired = true;
- defaults.selectionTimerDuration = 3000;
- defaults.selectionWraps = true;
- return defaults;
- }
- }, {
- key: _symbols2.default.template,
- get: function get() {
- return '\n \n\n \n \n
\n ';
- }
- }]);
-
- return Slideshow;
-}(base);
-
-customElements.define('basic-slideshow', Slideshow);
-exports.default = Slideshow;
-
-},{"../../basic-component-mixins/src/ContentItemsMixin":3,"../../basic-component-mixins/src/DistributedChildrenContentMixin":4,"../../basic-component-mixins/src/FractionalSelectionMixin":6,"../../basic-component-mixins/src/SelectionAnimationMixin":7,"../../basic-component-mixins/src/SelectionAriaActiveMixin":8,"../../basic-component-mixins/src/SingleSelectionMixin":11,"../../basic-component-mixins/src/TimerSelectionMixin":12,"../../basic-component-mixins/src/symbols":16,"../../basic-element-base/src/ElementBase":18}]},{},[19])
-//# sourceMappingURL=data:application/json;charset:utf-8;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbIm5vZGVfbW9kdWxlcy9ncnVudC1icm93c2VyaWZ5L25vZGVfbW9kdWxlcy9icm93c2VyLXBhY2svX3ByZWx1ZGUuanMiLCJwYWNrYWdlcy9iYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy9BdHRyaWJ1dGVNYXJzaGFsbGluZ01peGluLmpzIiwicGFja2FnZXMvYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvQ29tcG9zYWJsZU1peGluLmpzIiwicGFja2FnZXMvYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvQ29udGVudEl0ZW1zTWl4aW4uanMiLCJwYWNrYWdlcy9iYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy9EaXN0cmlidXRlZENoaWxkcmVuQ29udGVudE1peGluLmpzIiwicGFja2FnZXMvYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvRGlzdHJpYnV0ZWRDaGlsZHJlbk1peGluLmpzIiwicGFja2FnZXMvYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvRnJhY3Rpb25hbFNlbGVjdGlvbk1peGluLmpzIiwicGFja2FnZXMvYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvU2VsZWN0aW9uQW5pbWF0aW9uTWl4aW4uanMiLCJwYWNrYWdlcy9iYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy9TZWxlY3Rpb25BcmlhQWN0aXZlTWl4aW4uanMiLCJwYWNrYWdlcy9iYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy9TaGFkb3dFbGVtZW50UmVmZXJlbmNlc01peGluLmpzIiwicGFja2FnZXMvYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvU2hhZG93VGVtcGxhdGVNaXhpbi5qcyIsInBhY2thZ2VzL2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL1NpbmdsZVNlbGVjdGlvbk1peGluLmpzIiwicGFja2FnZXMvYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvVGltZXJTZWxlY3Rpb25NaXhpbi5qcyIsInBhY2thZ2VzL2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL2NyZWF0ZVN5bWJvbC5qcyIsInBhY2thZ2VzL2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL21pY3JvdGFzay5qcyIsInBhY2thZ2VzL2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL3NhZmVBdHRyaWJ1dGVzLmpzIiwicGFja2FnZXMvYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvc3ltYm9scy5qcyIsInBhY2thZ2VzL2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL3RvZ2dsZUNsYXNzLmpzIiwicGFja2FnZXMvYmFzaWMtZWxlbWVudC1iYXNlL3NyYy9FbGVtZW50QmFzZS5qcyIsInBhY2thZ2VzL2Jhc2ljLXNsaWRlc2hvdy9nbG9iYWxzLmpzIiwicGFja2FnZXMvYmFzaWMtc2xpZGVzaG93L3NyYy9TbGlkZXNob3cuanMiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6IkFBQUE7Ozs7Ozs7Ozs7O0FDQUE7Ozs7Ozs7Ozs7OztBQUdBO0FBQ0EsSUFBTSwyQkFBMkIsRUFBakM7QUFDQSxJQUFNLDRCQUE0QixFQUFsQzs7QUFHQTs7a0JBQ2UsVUFBQyxJQUFELEVBQVU7O0FBRXZCOzs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7OztBQUZ1QixNQXFDakIsb0JBckNpQjtBQUFBOztBQUFBO0FBQUE7O0FBQUE7QUFBQTs7QUFBQTtBQUFBOzs7QUF1Q3JCOzs7QUF2Q3FCLCtDQTBDSSxhQTFDSixFQTBDbUIsUUExQ25CLEVBMEM2QixRQTFDN0IsRUEwQ3VDO0FBQzFELHVKQUFvQztBQUFFO0FBQW1DO0FBQ3pFLFlBQU0sZUFBZSx3QkFBd0IsYUFBeEIsQ0FBckI7QUFDQTtBQUNBO0FBQ0EsWUFBSSxnQkFBZ0IsSUFBaEIsSUFBd0IsRUFBRSxnQkFBZ0IsWUFBWSxTQUE5QixDQUE1QixFQUFzRTtBQUNwRSxlQUFLLFlBQUwsSUFBcUIsUUFBckI7QUFDRDtBQUNGO0FBbERvQjtBQUFBO0FBQUEsMENBb0REO0FBQ2xCLGdKQUE2QjtBQUFFO0FBQTRCO0FBQzNELGlDQUFlLFNBQWYsQ0FBeUIsSUFBekI7QUFDRDtBQXZEb0I7QUFBQTs7O0FBNkRyQjs7Ozs7Ozs7Ozs7O0FBN0RxQix1Q0F5RUosU0F6RUksRUF5RU8sS0F6RVAsRUF5RWM7QUFDakMsZUFBTyx5QkFBZSxZQUFmLENBQTRCLElBQTVCLEVBQWtDLFNBQWxDLEVBQTZDLEtBQTdDLENBQVA7QUFDRDs7QUFFRDs7Ozs7Ozs7Ozs7Ozs7QUE3RXFCO0FBQUE7QUFBQSxtQ0EwRlIsU0ExRlEsRUEwRkcsS0ExRkgsRUEwRlU7QUFDN0IsZUFBTyx5QkFBZSxXQUFmLENBQTJCLElBQTNCLEVBQWlDLFNBQWpDLEVBQTRDLEtBQTVDLENBQVA7QUFDRDtBQTVGb0I7QUFBQTtBQUFBLDBCQXlEVztBQUM5QixlQUFPLG1CQUFtQixJQUFuQixDQUFQO0FBQ0Q7QUEzRG9COztBQUFBO0FBQUEsSUFxQ1ksSUFyQ1o7O0FBZ0d2QixTQUFPLG9CQUFQO0FBQ0QsQzs7QUFHRDs7O0FBQ0EsU0FBUyx1QkFBVCxDQUFpQyxhQUFqQyxFQUFnRDtBQUM5QyxNQUFJLGVBQWUseUJBQXlCLGFBQXpCLENBQW5CO0FBQ0EsTUFBSSxDQUFDLFlBQUwsRUFBbUI7QUFDakI7QUFDQSxRQUFNLGFBQWEsV0FBbkI7QUFDQSxtQkFBZSxjQUFjLE9BQWQsQ0FBc0IsVUFBdEIsRUFDWDtBQUFBLGFBQVMsTUFBTSxDQUFOLEVBQVMsV0FBVCxFQUFUO0FBQUEsS0FEVyxDQUFmO0FBRUEsNkJBQXlCLGFBQXpCLElBQTBDLFlBQTFDO0FBQ0Q7QUFDRCxTQUFPLFlBQVA7QUFDRDs7QUFFRCxTQUFTLGtCQUFULENBQTRCLE9BQTVCLEVBQXFDOztBQUVuQztBQUNBO0FBQ0EsTUFBSSxZQUFZLFdBQVosSUFBMkIsWUFBWSxNQUEzQyxFQUFtRDtBQUNqRCxXQUFPLEVBQVA7QUFDRDs7QUFFRDtBQUNBLE1BQU0sWUFBWSxPQUFPLGNBQVAsQ0FBc0IsUUFBUSxTQUE5QixFQUF5QyxXQUEzRDtBQUNBLE1BQU0saUJBQWlCLG1CQUFtQixTQUFuQixDQUF2Qjs7QUFFQTtBQUNBLE1BQU0sZ0JBQWdCLE9BQU8sbUJBQVAsQ0FBMkIsUUFBUSxTQUFuQyxDQUF0QjtBQUNBLE1BQU0sY0FBYyxjQUFjLE1BQWQsQ0FBcUI7QUFBQSxXQUN2QyxPQUFPLE9BQU8sd0JBQVAsQ0FDSCxRQUFRLFNBREwsRUFDZ0IsWUFEaEIsRUFDOEIsR0FEckMsS0FDNkMsVUFGTjtBQUFBLEdBQXJCLENBQXBCO0FBR0EsTUFBTSxhQUFhLFlBQVksR0FBWixDQUFnQjtBQUFBLFdBQy9CLHdCQUF3QixVQUF4QixDQUQrQjtBQUFBLEdBQWhCLENBQW5COztBQUdBO0FBQ0EsTUFBTSxPQUFPLFdBQVcsTUFBWCxDQUFrQjtBQUFBLFdBQzNCLGVBQWUsT0FBZixDQUF1QixTQUF2QixJQUFvQyxDQURUO0FBQUEsR0FBbEIsQ0FBYjtBQUVBLFNBQU8sZUFBZSxNQUFmLENBQXNCLElBQXRCLENBQVA7QUFDRDs7QUFFRDtBQUNBLFNBQVMsdUJBQVQsQ0FBaUMsWUFBakMsRUFBK0M7QUFDN0MsTUFBSSxZQUFZLDBCQUEwQixZQUExQixDQUFoQjtBQUNBLE1BQUksQ0FBQyxTQUFMLEVBQWdCO0FBQ2Q7QUFDQSxRQUFNLGlCQUFpQixVQUF2QjtBQUNBLGdCQUFZLGFBQWEsT0FBYixDQUFxQixjQUFyQixFQUFxQyxLQUFyQyxFQUE0QyxXQUE1QyxFQUFaO0FBQ0Q7QUFDRCxTQUFPLFNBQVA7QUFDRDs7Ozs7Ozs7Ozs7Ozs7Ozs7QUM3SkQ7a0JBQ2UsVUFBQyxJQUFELEVBQVU7O0FBRXZCOzs7Ozs7O0FBRnVCLE1BU2pCLFVBVGlCO0FBQUE7O0FBQUE7QUFBQTs7QUFBQTtBQUFBOztBQUFBO0FBQUE7OztBQVdyQjs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7OztBQVhxQixnQ0F1Q0s7QUFBQSwwQ0FBUixNQUFRO0FBQVIsZ0JBQVE7QUFBQTs7QUFDeEI7QUFDQTtBQUNBO0FBQ0E7QUFDQSxlQUFPLE9BQU8sTUFBUCxDQUFjLFlBQWQsRUFBNEIsSUFBNUIsQ0FBUDtBQUNEO0FBN0NvQjs7QUFBQTtBQUFBLElBU0UsSUFURjs7QUFpRHZCLFNBQU8sVUFBUDtBQUNELEM7O0FBR0Q7OztBQUNBLElBQU0sZ0NBQWdDLENBQ3BDLGFBRG9DLENBQXRDOztBQUlBOzs7OztBQUtBLFNBQVMsWUFBVCxDQUFzQixJQUF0QixFQUE0QixLQUE1QixFQUFtQztBQUNqQyxNQUFJLE9BQU8sS0FBUCxLQUFpQixVQUFyQixFQUFpQztBQUMvQjtBQUNBLFdBQU8sTUFBTSxJQUFOLENBQVA7QUFDRCxHQUhELE1BR087QUFDTDtBQURLLFFBRUMsUUFGRDtBQUFBOztBQUFBO0FBQUE7O0FBQUE7QUFBQTs7QUFBQTtBQUFBLE1BRWtCLElBRmxCOztBQUdMLHNCQUFrQixLQUFsQixFQUF5QixTQUFTLFNBQWxDLEVBQTZDLDZCQUE3QztBQUNBLFdBQU8sUUFBUDtBQUNEO0FBQ0Y7O0FBR0Q7Ozs7QUFJQSxTQUFTLGlCQUFULENBQTJCLE1BQTNCLEVBQW1DLE1BQW5DLEVBQXFFO0FBQUEsTUFBMUIsbUJBQTBCLHVFQUFKLEVBQUk7O0FBQ25FLFNBQU8sbUJBQVAsQ0FBMkIsTUFBM0IsRUFBbUMsT0FBbkMsQ0FBMkMsZ0JBQVE7QUFDakQsUUFBSSxvQkFBb0IsT0FBcEIsQ0FBNEIsSUFBNUIsSUFBb0MsQ0FBeEMsRUFBMkM7QUFDekMsVUFBTSxhQUFhLE9BQU8sd0JBQVAsQ0FBZ0MsTUFBaEMsRUFBd0MsSUFBeEMsQ0FBbkI7QUFDQSxhQUFPLGNBQVAsQ0FBc0IsTUFBdEIsRUFBOEIsSUFBOUIsRUFBb0MsVUFBcEM7QUFDRDtBQUNGLEdBTEQ7QUFNQSxTQUFPLE1BQVA7QUFDRDs7Ozs7Ozs7Ozs7OztBQ3pGRDs7OztBQUNBOzs7O0FBQ0E7Ozs7Ozs7Ozs7OztBQUdBO0FBQ0EsSUFBTSxjQUFjLDRCQUFhLE9BQWIsQ0FBcEI7QUFDQSxJQUFNLHdCQUF3Qiw0QkFBYSxpQkFBYixDQUE5Qjs7QUFHQTs7a0JBQ2UsVUFBQyxJQUFELEVBQVU7O0FBRXZCOzs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7QUFGdUIsTUFnQ2pCLFlBaENpQjtBQUFBOztBQUFBO0FBQUE7O0FBQUE7QUFBQTs7QUFBQTtBQUFBO0FBQUEsdUNBa0NKO0FBQ2YsNkhBQTBCO0FBQUU7QUFBeUI7O0FBRXJEO0FBQ0E7QUFDQTtBQUNBO0FBQ0EsYUFBSyxXQUFMLElBQW9CLElBQXBCOztBQUVBLGFBQUssa0JBQVEsWUFBYjtBQUNEOztBQUVEOzs7Ozs7Ozs7QUE5Q3FCO0FBQUEsV0FzRHBCLGtCQUFRLFNBdERZO0FBQUEsNEJBc0RELElBdERDLEVBc0RLO0FBQ3hCLG9HQUFVLGtCQUFRLFNBQWxCLFNBQThCO0FBQUUsa0dBQU0sa0JBQVEsU0FBZCxtQkFBeUIsSUFBekI7QUFBaUM7QUFDbEU7O0FBRUQ7Ozs7Ozs7Ozs7O0FBMURxQjtBQUFBLFdBb0VwQixrQkFBUSxZQXBFWTtBQUFBLDRCQW9FRSxJQXBFRixFQW9FUSxRQXBFUixFQW9Fa0I7QUFDckMsb0dBQVUsa0JBQVEsWUFBbEIsU0FBaUM7QUFBRSxrR0FBTSxrQkFBUSxZQUFkLG1CQUE0QixJQUE1QixFQUFrQyxRQUFsQztBQUE4QztBQUNqRixtQ0FBWSxJQUFaLEVBQWtCLFVBQWxCLEVBQThCLFFBQTlCO0FBQ0Q7O0FBRUQ7Ozs7Ozs7QUF6RXFCO0FBQUEsV0FvR3BCLGtCQUFRLFlBcEdZOzs7QUErRnJCOzs7OztBQS9GcUIsOEJBb0dJO0FBQUE7O0FBQ3ZCLG9HQUFVLGtCQUFRLFlBQWxCLFNBQWlDO0FBQUUsa0dBQU0sa0JBQVEsWUFBZDtBQUFnQzs7QUFFbkU7QUFDQSxjQUFNLFNBQU4sQ0FBZ0IsT0FBaEIsQ0FBd0IsSUFBeEIsQ0FBNkIsS0FBSyxLQUFsQyxFQUF5QyxnQkFBUTtBQUMvQyxjQUFJLENBQUMsS0FBSyxxQkFBTCxDQUFMLEVBQWtDO0FBQ2hDLG1CQUFLLGtCQUFRLFNBQWIsRUFBd0IsSUFBeEI7QUFDQSxpQkFBSyxxQkFBTCxJQUE4QixJQUE5QjtBQUNEO0FBQ0YsU0FMRDs7QUFPQSxhQUFLLGFBQUwsQ0FBbUIsSUFBSSxXQUFKLENBQWdCLGVBQWhCLENBQW5CO0FBQ0Q7O0FBRUQ7Ozs7Ozs7QUFsSHFCO0FBQUE7QUFBQSwwQkErRVQ7QUFDVixZQUFJLGNBQUo7QUFDQSxZQUFJLEtBQUssV0FBTCxLQUFxQixJQUF6QixFQUErQjtBQUM3QixrQkFBUSx3QkFBd0IsS0FBSyxPQUE3QixDQUFSO0FBQ0E7QUFDQSxjQUFJLEtBQUssV0FBTCxNQUFzQixJQUExQixFQUFnQztBQUM5QjtBQUNBLGlCQUFLLFdBQUwsSUFBb0IsS0FBcEI7QUFDRDtBQUNGLFNBUEQsTUFPTztBQUNMO0FBQ0Esa0JBQVEsS0FBSyxXQUFMLENBQVI7QUFDRDtBQUNELGVBQU8sS0FBUDtBQUNEO0FBN0ZvQjs7QUFBQTtBQUFBLElBZ0NJLElBaENKOztBQTBIdkIsU0FBTyxZQUFQO0FBQ0QsQzs7QUFHRDtBQUNBOzs7QUFDQSxTQUFTLHVCQUFULENBQWlDLEtBQWpDLEVBQXdDO0FBQ3RDLE1BQU0sZ0JBQWdCLENBQ3BCLE1BRG9CLEVBRXBCLFFBRm9CLEVBR3BCLE9BSG9CLEVBSXBCLFVBSm9CLENBQXRCO0FBTUEsU0FBTyxHQUFHLE1BQUgsQ0FBVSxJQUFWLENBQWUsS0FBZixFQUFzQixVQUFTLElBQVQsRUFBZTtBQUMxQyxXQUFPLENBQUMsS0FBSyxTQUFOLElBQW1CLGNBQWMsT0FBZCxDQUFzQixLQUFLLFNBQTNCLElBQXdDLENBQWxFO0FBQ0QsR0FGTSxDQUFQO0FBR0Q7Ozs7Ozs7Ozs7Ozs7OztBQ3JKRDs7Ozs7Ozs7Ozs7O0FBR0E7a0JBQ2UsVUFBQyxJQUFELEVBQVU7O0FBRXZCOzs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7OztBQUZ1QixNQTJDakIsMEJBM0NpQjtBQUFBOztBQTZDckIsMENBQWM7QUFBQTs7QUFBQTs7QUFHWixVQUFJLE1BQUssVUFBVCxFQUFxQjtBQUNuQjtBQUNBLFlBQU0sUUFBUSxNQUFLLFVBQUwsQ0FBZ0IsZ0JBQWhCLENBQWlDLE1BQWpDLENBQWQ7QUFDQSxjQUFNLE9BQU4sQ0FBYztBQUFBLGlCQUFRLEtBQUssZ0JBQUwsQ0FBc0IsWUFBdEIsRUFBb0MsaUJBQVM7QUFDakUsa0JBQUssY0FBTDtBQUNELFdBRnFCLENBQVI7QUFBQSxTQUFkO0FBR0Q7O0FBRUQ7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0EsK0JBQVU7QUFBQSxlQUFNLE1BQUssY0FBTCxFQUFOO0FBQUEsT0FBVjtBQWpCWTtBQWtCYjs7QUFFRDs7Ozs7Ozs7OztBQWpFcUI7QUFBQTtBQUFBLHVDQXlFSjtBQUNmLHlKQUEwQjtBQUFFO0FBQXlCO0FBQ3JELFlBQU0sUUFBUSxJQUFJLFdBQUosQ0FBZ0IsaUJBQWhCLENBQWQ7QUFDQSxhQUFLLGFBQUwsQ0FBbUIsS0FBbkI7QUFDRDs7QUFFRDs7Ozs7OztBQS9FcUI7QUFBQTtBQUFBLDBCQXFGUDtBQUNaLFlBQU0sc0JBQXNCLEtBQUssbUJBQWpDO0FBQ0EsWUFBSSxPQUFPLG1CQUFQLEtBQStCLFdBQW5DLEVBQWdEO0FBQzlDLGtCQUFRLElBQVI7QUFDRDtBQUNELGVBQU8sbUJBQVA7QUFDRCxPQTNGb0I7QUFBQSx3QkE0RlQsS0E1RlMsRUE0RkY7QUFDakIsWUFBSSxhQUFhLEtBQUssU0FBdEIsRUFBaUM7QUFBRSx5SUFBZ0IsS0FBaEI7QUFBd0I7QUFDM0Q7QUFDQTtBQUNEOztBQUVEOzs7Ozs7OztBQWxHcUI7O0FBQUE7QUFBQSxJQTJDa0IsSUEzQ2xCOztBQTJHdkIsU0FBTywwQkFBUDtBQUNELEM7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7QUNoSEQ7a0JBQ2UsVUFBQyxJQUFELEVBQVU7O0FBRXZCOzs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7O0FBRnVCLE1BNkNqQixtQkE3Q2lCO0FBQUE7O0FBQUE7QUFBQTs7QUFBQTtBQUFBOztBQUFBO0FBQUE7OztBQStDckI7Ozs7OztBQS9DcUIsMEJBcURLO0FBQ3hCLGVBQU8sc0JBQXNCLEtBQUssUUFBM0IsRUFBcUMsS0FBckMsQ0FBUDtBQUNEOztBQUVEOzs7Ozs7OztBQXpEcUI7QUFBQTtBQUFBLDBCQWdFTztBQUMxQixlQUFPLHNCQUFzQixLQUFLLFVBQTNCLEVBQXVDLElBQXZDLENBQVA7QUFDRDs7QUFFRDs7Ozs7OztBQXBFcUI7QUFBQTtBQUFBLDBCQTBFUTtBQUMzQixZQUFNLFVBQVUsS0FBSyxxQkFBTCxDQUEyQixHQUEzQixDQUErQixVQUFTLEtBQVQsRUFBZ0I7QUFDN0QsaUJBQU8sTUFBTSxXQUFiO0FBQ0QsU0FGZSxDQUFoQjtBQUdBLGVBQU8sUUFBUSxJQUFSLENBQWEsRUFBYixDQUFQO0FBQ0Q7QUEvRW9COztBQUFBO0FBQUEsSUE2Q1csSUE3Q1g7O0FBbUZ2QixTQUFPLG1CQUFQO0FBQ0QsQzs7QUFHRDs7Ozs7Ozs7Ozs7QUFTQSxTQUFTLHFCQUFULENBQStCLEtBQS9CLEVBQXNDLGdCQUF0QyxFQUF3RDtBQUFBOztBQUN0RCxNQUFNLFdBQVcsTUFBTSxTQUFOLENBQWdCLEdBQWhCLENBQW9CLElBQXBCLENBQXlCLEtBQXpCLEVBQWdDLGdCQUFRO0FBQ3ZEO0FBQ0E7QUFDQTtBQUNBO0FBQ0EsUUFBTSxTQUFTLE9BQU8sZUFBUCxLQUEyQixXQUEzQixHQUNiLGdCQUFnQixlQURILEdBRWIsS0FBSyxTQUFMLEtBQW1CLE1BRnJCO0FBR0EsUUFBSSxNQUFKLEVBQVk7QUFDVjtBQUNBLFVBQU0sZ0JBQWdCLEtBQUssYUFBTCxDQUFtQixFQUFFLFNBQVMsSUFBWCxFQUFuQixDQUF0QjtBQUNBLGFBQU8sZ0JBQ0wsc0JBQXNCLGFBQXRCLEVBQXFDLGdCQUFyQyxDQURLLEdBRUwsRUFGRjtBQUdELEtBTkQsTUFNTyxJQUFJLGdCQUFnQixXQUFwQixFQUFpQztBQUN0QztBQUNBLGFBQU8sQ0FBQyxJQUFELENBQVA7QUFDRCxLQUhNLE1BR0EsSUFBSSxnQkFBZ0IsSUFBaEIsSUFBd0IsZ0JBQTVCLEVBQThDO0FBQ25EO0FBQ0EsYUFBTyxDQUFDLElBQUQsQ0FBUDtBQUNELEtBSE0sTUFHQTtBQUNMO0FBQ0EsYUFBTyxFQUFQO0FBQ0Q7QUFDRixHQXhCZ0IsQ0FBakI7QUF5QkEsTUFBTSxZQUFZLFlBQUcsTUFBSCxnQ0FBYSxRQUFiLEVBQWxCO0FBQ0EsU0FBTyxTQUFQO0FBQ0Q7Ozs7Ozs7Ozs7Ozs7OztrQkNySHVCLEs7O0FBUnhCOzs7Ozs7Ozs7Ozs7QUFHQTtBQUNBLElBQU0seUJBQXlCLDRCQUFhLGtCQUFiLENBQS9COztBQUdBO0FBQ2UsU0FBUyxLQUFULENBQWUsSUFBZixFQUFxQjs7QUFFbEM7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7QUFGa0MsTUFxQjVCLG1CQXJCNEI7QUFBQTs7QUFBQTtBQUFBOztBQUFBO0FBQUE7O0FBQUE7QUFBQTtBQUFBLDBDQXVCWjtBQUNsQiw4SUFBNkI7QUFBRTtBQUE0QjtBQUMzRCxhQUFLLGdCQUFMLEdBQXdCLENBQXhCO0FBQ0Q7O0FBRUQ7Ozs7Ozs7O0FBNUJnQztBQUFBO0FBQUEsMEJBbUNUO0FBQ3JCLGVBQU8sS0FBSyxzQkFBTCxDQUFQO0FBQ0QsT0FyQytCO0FBQUEsd0JBc0NYLEtBdENXLEVBc0NKO0FBQzFCLGFBQUssc0JBQUwsSUFBK0IsS0FBL0I7QUFDQSxZQUFJLHNCQUFzQixLQUFLLFNBQS9CLEVBQTBDO0FBQUUsb0lBQXlCLEtBQXpCO0FBQWlDO0FBQzdFLFlBQU0sUUFBUSxJQUFJLFdBQUosQ0FBZ0IsMkJBQWhCLENBQWQ7QUFDQSxhQUFLLGFBQUwsQ0FBbUIsS0FBbkI7QUFDRDtBQTNDK0I7O0FBQUE7QUFBQSxJQXFCQSxJQXJCQTs7QUErQ2xDLFNBQU8sbUJBQVA7QUFDRDs7QUFHRCxNQUFNLE9BQU4sR0FBZ0I7O0FBRWQ7Ozs7Ozs7Ozs7Ozs7Ozs7QUFnQkEsaUJBbEJjLDJCQWtCRSxTQWxCRixFQWtCYSxTQWxCYixFQWtCd0I7QUFDcEMsUUFBTSxRQUFRLFlBQVksQ0FBMUI7QUFDQSxRQUFJLGVBQUo7QUFDQSxRQUFJLFlBQVksQ0FBaEIsRUFBbUI7QUFDakI7QUFDQSxlQUFTLENBQUMsTUFBTSxPQUFOLENBQWMsT0FBZCxDQUFzQixDQUFDLFNBQXZCLENBQVY7QUFDRCxLQUhELE1BR08sSUFBSSxhQUFhLEtBQWpCLEVBQXdCO0FBQzdCO0FBQ0EsZUFBUyxRQUFRLE1BQU0sT0FBTixDQUFjLE9BQWQsQ0FBc0IsWUFBWSxLQUFsQyxDQUFqQjtBQUNELEtBSE0sTUFHQTtBQUNMO0FBQ0EsZUFBUyxTQUFUO0FBQ0Q7QUFDRCxXQUFPLE1BQVA7QUFDRCxHQWhDYTs7O0FBa0NkOzs7Ozs7Ozs7Ozs7Ozs7QUFlQSxTQWpEYyxtQkFpRE4sQ0FqRE0sRUFpREg7QUFDVCxRQUFNLElBQUssQ0FBQyxDQUFELElBQU0sSUFBSSxDQUFWLENBQUQsR0FBaUIsQ0FBM0I7QUFDQSxXQUFPLENBQVA7QUFDRCxHQXBEYTs7O0FBc0RkOzs7Ozs7OztBQVFBLGtCQTlEYyw0QkE4REcsT0E5REgsRUE4RFk7QUFDeEIsUUFBTSxnQkFBZ0IsUUFBUSxhQUE5QjtBQUNBLFFBQUksZ0JBQWdCLENBQXBCLEVBQXVCO0FBQ3JCO0FBQ0E7QUFDRDtBQUNELFFBQU0sbUJBQW1CLFFBQVEsZ0JBQVIsSUFBNEIsQ0FBckQ7QUFDQSxXQUFPLGdCQUFnQixnQkFBdkI7QUFDRCxHQXRFYTs7O0FBd0VkOzs7Ozs7Ozs7O0FBVUEsZ0JBbEZjLDBCQWtGQyxTQWxGRCxFQWtGWTtBQUN4QjtBQUNBO0FBQ0EsUUFBTSxRQUFRLFlBQVksQ0FBWixHQUFnQixLQUFLLElBQUwsQ0FBVSxTQUFWLENBQWhCLEdBQXVDLEtBQUssS0FBTCxDQUFXLFNBQVgsQ0FBckQ7QUFDQSxRQUFNLFdBQVcsWUFBWSxLQUE3QjtBQUNBLFdBQU8sRUFBRSxZQUFGLEVBQVMsa0JBQVQsRUFBUDtBQUNELEdBeEZhOzs7QUEwRmQ7Ozs7Ozs7Ozs7Ozs7QUFhQSxrQkF2R2MsNEJBdUdHLFNBdkdILEVBdUdjLFNBdkdkLEVBdUd5QjtBQUNyQztBQUNBO0FBQ0EsV0FBTyxDQUFFLFlBQVksU0FBYixHQUEwQixTQUEzQixJQUF3QyxTQUEvQztBQUNELEdBM0dhOzs7QUE2R2Q7Ozs7Ozs7Ozs7QUFVQSx1QkF2SGMsaUNBdUhRLFNBdkhSLEVBdUhtQixTQXZIbkIsRUF1SDhCLElBdkg5QixFQXVIb0M7QUFDaEQsUUFBSSxJQUFKLEVBQVU7QUFDUixrQkFBWSxNQUFNLE9BQU4sQ0FBYyxnQkFBZCxDQUErQixTQUEvQixFQUEwQyxTQUExQyxDQUFaO0FBQ0Q7QUFDRCxXQUFPLE1BQU0sT0FBTixDQUFjLGNBQWQsQ0FBNkIsU0FBN0IsQ0FBUDtBQUNEO0FBNUhhLENBQWhCOzs7Ozs7Ozs7Ozs7Ozs7a0JDekN3QixLOztBQWxCeEI7Ozs7QUFDQTs7OztBQUNBOzs7Ozs7Ozs7Ozs7QUFHQTtBQUNBLElBQU0sa0JBQWtCLDRCQUFhLFdBQWIsQ0FBeEI7QUFDQSxJQUFNLGlCQUFpQiw0QkFBYSxVQUFiLENBQXZCO0FBQ0EsSUFBTSxzQkFBc0IsNEJBQWEsZUFBYixDQUE1QjtBQUNBLElBQU0seUJBQXlCLDRCQUFhLG9CQUFiLENBQS9CO0FBQ0EsSUFBTSwwQkFBMEIsNEJBQWEsbUJBQWIsQ0FBaEM7QUFDQSxJQUFNLG1DQUFtQyw0QkFBYSw0QkFBYixDQUF6QztBQUNBLElBQU0saUNBQWlDLDRCQUFhLDBCQUFiLENBQXZDO0FBQ0EsSUFBTSxvQ0FBb0MsNEJBQWEsNkJBQWIsQ0FBMUM7QUFDQSxJQUFNLG9DQUFvQyw0QkFBYSw2QkFBYixDQUExQzs7QUFHQTtBQUNlLFNBQVMsS0FBVCxDQUFlLElBQWYsRUFBcUI7O0FBRWxDOzs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7QUFGa0MsTUFtQzVCLGtCQW5DNEI7QUFBQTs7QUFxQ2hDLGtDQUFjO0FBQUE7O0FBR1o7QUFIWTs7QUFJWixVQUFJLE9BQU8sTUFBSywwQkFBWixLQUEyQyxXQUEvQyxFQUE0RDtBQUMxRCxjQUFLLDBCQUFMLEdBQWtDLE1BQUssa0JBQVEsUUFBYixFQUF1QiwwQkFBekQ7QUFDRDtBQUNELFVBQUksT0FBTyxNQUFLLHdCQUFaLEtBQXlDLFdBQXpDLElBQXdELE1BQUssMkJBQUwsSUFBb0MsSUFBaEcsRUFBc0c7QUFDcEcsY0FBSyx3QkFBTCxHQUFnQyxNQUFLLGtCQUFRLFFBQWIsRUFBdUIsd0JBQXZEO0FBQ0Q7O0FBRUQsWUFBSyxrQkFBUSxRQUFiLElBQXlCLEtBQXpCO0FBWFk7QUFZYjs7QUFqRCtCO0FBQUEsV0EyRS9CLGtCQUFRLFNBM0V1QjtBQUFBLDRCQTJFWixJQTNFWSxFQTJFTjtBQUN4QjtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0EsYUFBSyxZQUFMLENBQWtCLGFBQWxCLEVBQWlDLEtBQWpDO0FBQ0Q7QUFqRytCO0FBQUEsV0FtRy9CLGtCQUFRLFlBbkd1QjtBQUFBLDhCQW1HUDtBQUN2QixnSEFBVSxrQkFBUSxZQUFsQixTQUFpQztBQUFFLDhHQUFNLGtCQUFRLFlBQWQ7QUFBZ0M7O0FBRW5FLHlCQUFnQixJQUFoQjs7QUFFQTtBQUNBO0FBQ0E7O0FBRUEsd0JBQWdCLElBQWhCO0FBQ0Q7QUE3RytCO0FBQUE7QUFBQSx3Q0ErR2Q7QUFDaEIseUJBQWdCLElBQWhCO0FBQ0Q7O0FBRUQ7Ozs7Ozs7Ozs7O0FBbkhnQztBQUFBLFdBbUQzQixrQkFBUSxRQW5EbUI7QUFBQSwwQkFtRFA7QUFDdkIsWUFBTSxXQUFXLG9HQUFNLGtCQUFRLFFBQWQsV0FBMkIsRUFBNUM7QUFDQSxpQkFBUywwQkFBVCxHQUFzQyxHQUF0QztBQUNBLGlCQUFTLHdCQUFULEdBQW9DLE9BQXBDO0FBQ0EsZUFBTyxRQUFQO0FBQ0Q7O0FBRUQ7Ozs7O0FBMURnQztBQUFBLFdBaUUzQixrQkFBUSxRQWpFbUI7QUFBQSwwQkE4RFA7QUFDdkIsZUFBTyxLQUFLLGNBQUwsQ0FBUDtBQUNELE9BaEUrQjtBQUFBLHdCQWlFVCxLQWpFUyxFQWlFRjtBQUM1QixZQUFNLGdCQUFnQixLQUFLLGtCQUFRLFFBQWIsQ0FBdEI7QUFDQSxhQUFLLGNBQUwsSUFBdUIsS0FBdkI7QUFDQSxZQUFJLGtCQUFRLFFBQVIsSUFBb0IsS0FBSyxTQUE3QixFQUF3QztBQUFFLDhHQUFNLGtCQUFRLFFBQWQsRUFBMEIsS0FBMUI7QUFBa0M7QUFDNUUsWUFBSSxTQUFTLENBQUMsYUFBZCxFQUE2QjtBQUMzQjtBQUNBLGVBQUssaUNBQUwsSUFBMEMsSUFBMUM7QUFDRDtBQUNGO0FBekUrQjtBQUFBO0FBQUEsMEJBNkhUO0FBQ3JCLGVBQU8saUlBQTBCLENBQWpDO0FBQ0QsT0EvSCtCO0FBQUEsd0JBZ0lYLEtBaElXLEVBZ0lKO0FBQzFCLFlBQUksc0JBQXNCLEtBQUssU0FBL0IsRUFBMEM7QUFBRSxrSUFBeUIsS0FBekI7QUFBaUM7QUFDN0Usd0JBQWdCLElBQWhCLEVBQXNCLEtBQUssYUFBM0IsRUFBMEMsS0FBMUM7QUFDRDtBQW5JK0I7QUFBQTtBQUFBLDBCQXFJWjtBQUNsQjtBQUNELE9BdkkrQjtBQUFBLHdCQXdJZCxLQXhJYyxFQXdJUDtBQUN2QixZQUFJLG1CQUFtQixLQUFLLFNBQTVCLEVBQXVDO0FBQUUsK0hBQXNCLEtBQXRCO0FBQThCO0FBQ3ZFLHdCQUFnQixJQUFoQixFQUFzQixLQUF0QixFQUE2QixDQUE3QjtBQUNEOztBQUVEOzs7Ozs7Ozs7Ozs7O0FBN0lnQztBQUFBO0FBQUEsMEJBeUpDO0FBQy9CLGVBQU8sS0FBSyxnQ0FBTCxDQUFQO0FBQ0QsT0EzSitCO0FBQUEsd0JBNEpELEtBNUpDLEVBNEpNO0FBQ3BDLGFBQUssZ0NBQUwsSUFBeUMsS0FBekM7QUFDQSxZQUFJLGdDQUFnQyxLQUFLLFNBQXpDLEVBQW9EO0FBQUUsNElBQW1DLEtBQW5DO0FBQTJDO0FBQ2xHOztBQUVEOzs7Ozs7Ozs7Ozs7Ozs7OztBQWpLZ0M7QUFBQTtBQUFBLDBCQWlMRDtBQUM3QixlQUFPLEtBQUssOEJBQUwsQ0FBUDtBQUNELE9BbkwrQjtBQUFBLHdCQW9MSCxLQXBMRyxFQW9MSTtBQUNsQyxhQUFLLDhCQUFMLElBQXVDLEtBQXZDO0FBQ0EsWUFBSSw4QkFBOEIsS0FBSyxTQUF2QyxFQUFrRDtBQUFFLDBJQUFpQyxLQUFqQztBQUF5QztBQUM3RixhQUFLLDJCQUFMLEdBQW1DLE1BQU0sdUJBQU4sQ0FBOEIsS0FBOUIsQ0FBbkM7QUFDRDs7QUFFRDs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7QUExTGdDO0FBQUE7QUFBQSwwQkFnTkU7QUFDaEM7QUFDQSxlQUFPLEtBQUssaUNBQUwsQ0FBUDtBQUNELE9Bbk4rQjtBQUFBLHdCQW9OQSxLQXBOQSxFQW9OTztBQUNyQyxhQUFLLGlDQUFMLElBQTBDLEtBQTFDO0FBQ0EsWUFBSSxpQ0FBaUMsS0FBSyxTQUExQyxFQUFxRDtBQUFFLDZJQUFvQyxLQUFwQztBQUE0QztBQUNuRyx5QkFBZ0IsSUFBaEI7QUFDQSx3QkFBZ0IsSUFBaEI7QUFDRDtBQXpOK0I7QUFBQTtBQUFBLDBCQTJOWDtBQUNuQjtBQUNELE9BN04rQjtBQUFBLHdCQThOYixLQTlOYSxFQThOTjtBQUN4QixZQUFJLG9CQUFvQixLQUFLLFNBQTdCLEVBQXdDO0FBQUUsZ0lBQXVCLEtBQXZCO0FBQStCO0FBQ3pFLHlCQUFnQixJQUFoQjtBQUNBLHdCQUFnQixJQUFoQjtBQUNEO0FBbE8rQjs7QUFBQTtBQUFBLElBbUNELElBbkNDOztBQXFPbEMsU0FBTyxrQkFBUDtBQUNEOztBQUdEO0FBQ0E7QUFDQTtBQUNBLE1BQU0sT0FBTixHQUFnQjs7QUFFZDs7Ozs7Ozs7Ozs7OztBQWFBLGdDQWZjLDBDQWVpQixPQWZqQixFQWUwQixTQWYxQixFQWVxQzs7QUFFakQsUUFBTSxRQUFRLFFBQVEsS0FBdEI7QUFDQSxRQUFJLENBQUMsS0FBTCxFQUFZO0FBQ1Y7QUFDRDs7QUFFRCxRQUFNLFlBQVksTUFBTSxNQUF4QjtBQUNBLFFBQU0saUJBQWlCLFFBQVEsY0FBL0I7O0FBRUEsV0FBTyxNQUFNLEdBQU4sQ0FBVSxVQUFDLElBQUQsRUFBTyxTQUFQLEVBQXFCO0FBQ3BDO0FBQ0EsVUFBTSxRQUFRLGFBQWEsU0FBYixFQUF3QixjQUF4QixFQUF3QyxTQUF4QyxFQUFtRCxTQUFuRCxDQUFkO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBLFVBQU0sb0JBQW9CLENBQUMsSUFBSSxLQUFMLElBQWMsQ0FBeEM7QUFDQSxhQUFRLHFCQUFxQixDQUFyQixJQUEwQixxQkFBcUIsQ0FBaEQsR0FDTCxpQkFESyxHQUVMLElBRkYsQ0FUb0MsQ0FXNUI7QUFDVCxLQVpNLENBQVA7QUFhRCxHQXRDYTs7O0FBd0NkOzs7Ozs7OztBQVFBLG9DQWhEYyw4Q0FnRHFCLE9BaERyQixFQWdEOEIsYUFoRDlCLEVBZ0Q2QyxXQWhEN0MsRUFnRDBEOztBQUV0RSxRQUFNLFFBQVEsUUFBUSxLQUF0QjtBQUNBLFFBQUksQ0FBQyxLQUFMLEVBQVk7QUFDVjtBQUNEO0FBQ0QsUUFBTSxZQUFZLE1BQU0sTUFBeEI7QUFDQSxRQUFNLGlCQUFpQixRQUFRLGNBQS9CO0FBQ0EsUUFBTSxVQUFVLG1DQUF5QixPQUF6QixDQUFpQyxxQkFBakMsQ0FBdUQsV0FBdkQsRUFBb0UsU0FBcEUsRUFBK0UsY0FBL0UsRUFBK0YsS0FBL0c7QUFDQSxRQUFNLGFBQWEsYUFBYSxTQUFiLEVBQXdCLGNBQXhCLEVBQXdDLGFBQXhDLEVBQXVELFdBQXZELENBQW5CO0FBQ0EsUUFBTSxZQUFZLGNBQWMsQ0FBZCxHQUFrQixRQUFsQixHQUE0QixTQUE5QztBQUNBLFFBQU0sT0FBTyxNQUFiO0FBQ0EsUUFBTSxnQkFBZ0IsUUFBUSwwQkFBOUI7QUFDQSxRQUFNLGVBQWUsZUFBZSxDQUFmLEdBQ25CLGdCQUFnQixDQUFoQixHQUFvQixLQUFLLElBQUwsQ0FBVSxLQUFLLEdBQUwsQ0FBUyxVQUFULENBQVYsQ0FERCxHQUVuQixDQUZGLENBYnNFLENBZWhFOztBQUVOLFFBQU0sVUFBVSxNQUFNLEdBQU4sQ0FBVSxVQUFDLElBQUQsRUFBTyxTQUFQLEVBQXFCO0FBQzdDLFVBQU0sUUFBUSxhQUFhLFNBQWIsRUFBd0IsY0FBeEIsRUFBd0MsU0FBeEMsRUFBbUQsV0FBbkQsQ0FBZDtBQUNBO0FBQ0E7QUFDQSxVQUFJLHFCQUFxQixhQUFhLEtBQXRDO0FBQ0EsVUFBSSxhQUFhLENBQWpCLEVBQW9CO0FBQ2xCLDZCQUFxQixDQUFDLGtCQUF0QjtBQUNEO0FBQ0Q7QUFDQSxVQUFJLEtBQUssSUFBTCxDQUFVLGtCQUFWLEtBQWlDLENBQWpDLElBQXNDLHNCQUFzQixLQUFLLEdBQUwsQ0FBUyxVQUFULENBQWhFLEVBQXNGO0FBQ3BGO0FBQ0E7QUFDQSxZQUFNLFFBQVEsZ0JBQWdCLHFCQUFxQixDQUFyQyxJQUF3QyxDQUF0RDtBQUNBLFlBQU0sV0FBVyxjQUFjLE9BQWQsR0FDZixDQUFDLFlBQUQsR0FBYyxDQURDLEdBQ0s7QUFDcEIsU0FGRixDQUpvRixDQU1sRTtBQUNsQixlQUFPLEVBQUUsVUFBVSxZQUFaLEVBQTBCLG9CQUExQixFQUFxQyxVQUFyQyxFQUEyQyxZQUEzQyxFQUFrRCxrQkFBbEQsRUFBUDtBQUNELE9BUkQsTUFRTztBQUNMLGVBQU8sSUFBUDtBQUNEO0FBQ0YsS0FwQmUsQ0FBaEI7O0FBc0JBLFdBQU8sT0FBUDtBQUNEO0FBeEZhLENBQWhCOztBQTZGQTtBQUNBLE1BQU0sdUJBQU4sR0FBZ0M7O0FBRTlCO0FBQ0EsYUFBVyxDQUNULEVBQUUsU0FBUyxDQUFYLEVBRFMsRUFFVCxFQUFFLFNBQVMsQ0FBWCxFQUZTLEVBR1QsRUFBRSxTQUFTLENBQVgsRUFIUyxDQUhtQjs7QUFTOUI7QUFDQSxVQUFRLENBQ04sRUFBRSxXQUFXLGdCQUFiLEVBQStCLFFBQVEsQ0FBdkMsRUFETSxFQUVOLEVBQUUsV0FBVyxnQkFBYixFQUErQixRQUFRLENBQXZDLEVBRk0sRUFHTixFQUFFLFdBQVcsbUJBQWIsRUFBa0MsUUFBUSxDQUExQyxFQUhNLENBVnNCOztBQWdCOUI7QUFDQSxrQkFBZ0IsQ0FDZCxFQUFFLFdBQVcsNEJBQWIsRUFBMkMsU0FBUyxDQUFwRCxFQUF1RCxRQUFRLENBQS9ELEVBRGMsRUFFZCxFQUFFLFdBQVcsMkJBQWIsRUFBMEMsU0FBUyxDQUFuRCxFQUFzRCxRQUFRLENBQTlELEVBRmMsRUFHZCxFQUFFLFdBQVcsOEJBQWIsRUFBNkMsU0FBUyxDQUF0RCxFQUF5RCxRQUFRLENBQWpFLEVBSGMsQ0FqQmM7O0FBdUI5QjtBQUNBLGdCQUFjLENBQ1osRUFBRSxXQUFXLDRCQUFiLEVBQTJDLFFBQVEsQ0FBbkQsRUFEWSxFQUVaLEVBQUUsV0FBVyw0QkFBYixFQUEyQyxRQUFRLENBQW5ELEVBRlksRUFHWixFQUFFLFdBQVcsNkJBQWIsRUFBNEMsUUFBUSxDQUFwRCxFQUhZLENBeEJnQjs7QUE4QjlCO0FBQ0EsU0FBTyxDQUNMLEVBQUUsV0FBVyxrQkFBYixFQURLLEVBRUwsRUFBRSxXQUFXLG1CQUFiLEVBRkssQ0EvQnVCOztBQW9DOUI7QUFDQSxnQkFBYyxDQUNaLEVBQUUsV0FBVyxrQkFBYixFQURZLEVBRVosRUFBRSxXQUFXLG1CQUFiLEVBRlk7O0FBckNnQixDQUFoQzs7QUE2Q0E7Ozs7OztBQU1BLFNBQVMsZ0JBQVQsQ0FBMEIsT0FBMUIsRUFBbUMsYUFBbkMsRUFBa0QsV0FBbEQsRUFBK0Q7O0FBRTdELG1CQUFnQixPQUFoQjs7QUFFQTtBQUNBLE1BQU0sUUFBUSxRQUFRLEtBQXRCO0FBQ0EsTUFBTSxZQUFZLFFBQVEsMkJBQTFCO0FBQ0EsVUFBUSxzQkFBUixJQUFrQyxJQUFsQztBQUNBLE1BQU0sVUFBVSxNQUFNLE9BQU4sQ0FBYyxrQ0FBZCxDQUFpRCxPQUFqRCxFQUEwRCxhQUExRCxFQUF5RSxXQUF6RSxDQUFoQjs7QUFFQTtBQUNBLE1BQU0sWUFBWSxNQUFNLE1BQXhCO0FBQ0EsTUFBTSxpQkFBaUIsUUFBUSxjQUEvQjtBQUNBLE1BQU0saUJBQWlCLG1DQUF5QixPQUF6QixDQUFpQyxjQUFqQyxDQUFnRCxXQUFoRCxFQUE2RCxTQUE3RCxFQUF3RSxjQUF4RSxFQUF3RixLQUEvRztBQUNBLE1BQU0sYUFBYSxhQUFhLFNBQWIsRUFBd0IsY0FBeEIsRUFBd0MsYUFBeEMsRUFBdUQsV0FBdkQsQ0FBbkI7QUFDQSxNQUFNLFVBQVUsY0FBYyxDQUE5QjtBQUNBLE1BQUksY0FBYyxrQkFBa0IsVUFBVSxDQUFWLEdBQWMsQ0FBRSxDQUFsQyxDQUFsQjtBQUNBLE1BQUksY0FBSixFQUFvQjtBQUNsQixrQkFBYyxtQ0FBeUIsT0FBekIsQ0FBaUMsZ0JBQWpDLENBQWtELFdBQWxELEVBQStELFNBQS9ELENBQWQ7QUFDRCxHQUZELE1BRU8sSUFBSSxDQUFDLG9CQUFvQixPQUFwQixFQUE2QixXQUE3QixDQUFMLEVBQWdEO0FBQ3JELGtCQUFjLElBQWQsQ0FEcUQsQ0FDakM7QUFDckI7O0FBRUQ7QUFDQSxNQUFJLDZCQUFKO0FBQ0EsVUFBUSxPQUFSLENBQWdCLFVBQUMsTUFBRCxFQUFTLEtBQVQsRUFBbUI7QUFDakMsUUFBTSxPQUFPLE1BQU0sS0FBTixDQUFiO0FBQ0EsUUFBSSxNQUFKLEVBQVk7QUFDVixlQUFTLElBQVQsRUFBZSxJQUFmO0FBQ0EsVUFBTSxZQUFZLEtBQUssT0FBTCxDQUFhLFNBQWIsRUFBd0IsTUFBeEIsQ0FBbEI7QUFDQSxjQUFRLGVBQVIsRUFBeUIsS0FBekIsSUFBa0MsU0FBbEM7QUFDQSxVQUFJLFVBQVUsV0FBZCxFQUEyQjtBQUN6QjtBQUNBO0FBQ0Esc0JBQWMsSUFBZDtBQUNEO0FBQ0QsVUFBSSxPQUFPLFFBQVAsS0FBb0IsQ0FBeEIsRUFBMkI7QUFDekI7QUFDQTtBQUNBLCtCQUF1QixFQUFFLG9CQUFGLEVBQWEsWUFBYixFQUFvQixjQUFwQixFQUE0QixnQkFBNUIsRUFBdkI7QUFDRDtBQUNGLEtBZEQsTUFjTztBQUNMO0FBQ0EsZUFBUyxJQUFULEVBQWUsS0FBZjtBQUNEO0FBQ0YsR0FwQkQ7O0FBc0JBLE1BQUksd0JBQXdCLElBQTVCLEVBQWtDO0FBQ2hDO0FBQ0EseUJBQXFCLFdBQXJCLEdBQW1DLFdBQW5DO0FBQ0EseUJBQXFCLFNBQXJCLENBQStCLFFBQS9CLEdBQTBDO0FBQUEsYUFBUywyQkFBMkIsT0FBM0IsRUFBb0Msb0JBQXBDLENBQVQ7QUFBQSxLQUExQztBQUNBLFlBQVEsbUJBQVIsSUFBK0IscUJBQXFCLFNBQXBEO0FBQ0QsR0FMRCxNQUtPO0FBQ0w7QUFDQSxZQUFRLHNCQUFSLElBQWtDLEtBQWxDO0FBQ0Q7QUFDRjs7QUFHRCxTQUFTLHdCQUFULENBQWtDLE9BQWxDLEVBQTJDLEtBQTNDLEVBQWtEO0FBQ2hELE1BQUksUUFBUSxlQUFSLEtBQTRCLElBQWhDLEVBQXNDO0FBQ3BDO0FBQ0EsV0FBTyxJQUFQO0FBQ0Q7QUFDRCxNQUFJLFlBQVksUUFBUSxlQUFSLEVBQXlCLEtBQXpCLENBQWhCO0FBQ0EsTUFBSSxDQUFDLFNBQUwsRUFBZ0I7QUFDZCxRQUFNLE9BQU8sUUFBUSxLQUFSLENBQWMsS0FBZCxDQUFiO0FBQ0EsZ0JBQVksS0FBSyxPQUFMLENBQWEsUUFBUSwyQkFBckIsRUFBa0Q7QUFDNUQsZ0JBQVUsUUFBUSwwQkFEMEM7QUFFNUQsWUFBTTtBQUZzRCxLQUFsRCxDQUFaO0FBSUEsY0FBVSxLQUFWO0FBQ0EsWUFBUSxlQUFSLEVBQXlCLEtBQXpCLElBQWtDLFNBQWxDO0FBQ0Q7QUFDRCxTQUFPLFNBQVA7QUFDRDs7QUFFRCxTQUFTLG1CQUFULENBQTZCLE9BQTdCLEVBQXNDLEtBQXRDLEVBQTZDO0FBQzNDLFNBQU8sU0FBUyxDQUFULElBQWMsUUFBUSxLQUF0QixJQUErQixRQUFRLFFBQVEsS0FBUixDQUFjLE1BQTVEO0FBQ0Q7O0FBRUQ7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7O0FBb0JBLFNBQVMsZUFBVCxDQUF5QixPQUF6QixFQUFrSDtBQUFBLE1BQWhGLGFBQWdGLHVFQUFsRSxRQUFRLGFBQTBEO0FBQUEsTUFBM0MsZ0JBQTJDLHVFQUExQixRQUFRLGdCQUFrQjs7QUFDaEgsTUFBTSxZQUFZLFFBQVEsS0FBUixHQUFnQixRQUFRLEtBQVIsQ0FBYyxNQUE5QixHQUF1QyxDQUF6RDtBQUNBLE1BQUksY0FBYyxDQUFsQixFQUFxQjtBQUNuQjtBQUNBO0FBQ0Q7QUFDRCxNQUFJLGdCQUFnQixDQUFwQixFQUF1QjtBQUNyQjtBQUNBO0FBQ0Q7QUFDRCxNQUFJLFlBQVksZ0JBQWdCLGdCQUFoQztBQUNBLE1BQUksUUFBUSxjQUFaLEVBQTRCO0FBQzFCO0FBQ0EsZ0JBQVksbUNBQXlCLE9BQXpCLENBQWlDLGdCQUFqQyxDQUFrRCxTQUFsRCxFQUE2RCxTQUE3RCxDQUFaO0FBQ0QsR0FIRCxNQUdPO0FBQ0w7QUFDQSxnQkFBWSxtQ0FBeUIsT0FBekIsQ0FBaUMsZUFBakMsQ0FBaUQsU0FBakQsRUFBNEQsU0FBNUQsQ0FBWjtBQUNEO0FBQ0QsTUFBTSxvQkFBb0IsUUFBUSx1QkFBUixDQUExQjtBQUNBO0FBQ0E7QUFDQSxNQUFJLENBQUMsUUFBUSxrQkFBUSxRQUFoQixDQUFELElBQThCLHFCQUFxQixJQUFuRCxJQUNBLHNCQUFzQixTQUQxQixFQUNxQztBQUNuQztBQUNBLHFCQUFpQixPQUFqQixFQUEwQixpQkFBMUIsRUFBNkMsU0FBN0M7QUFDRCxHQUpELE1BSU8sSUFBSSxxQkFBcUIsQ0FBckIsSUFBMEIsUUFBUSxzQkFBUixDQUE5QixFQUErRDtBQUNwRTtBQUNBO0FBQ0E7QUFDRCxHQUpNLE1BSUE7QUFDTDtBQUNBLDZCQUF5QixPQUF6QixFQUFrQyxTQUFsQztBQUNEO0FBQ0QsVUFBUSx1QkFBUixJQUFtQyxTQUFuQztBQUNEOztBQUVEOzs7O0FBSUEsU0FBUyx3QkFBVCxDQUFrQyxPQUFsQyxFQUEyQyxXQUEzQyxFQUF3RDtBQUN0RCxNQUFJLFFBQVEsaUNBQVIsQ0FBSixFQUFnRDtBQUM5QyxxQkFBZ0IsT0FBaEI7QUFDQSxZQUFRLGlDQUFSLElBQTZDLEtBQTdDO0FBQ0Q7QUFDRCxNQUFNLHFCQUFxQixNQUFNLE9BQU4sQ0FBYyw4QkFBZCxDQUE2QyxPQUE3QyxFQUFzRCxXQUF0RCxDQUEzQjtBQUNBLHFCQUFtQixHQUFuQixDQUF1QixVQUFDLGlCQUFELEVBQW9CLEtBQXBCLEVBQThCO0FBQ25ELFFBQU0sT0FBTyxRQUFRLEtBQVIsQ0FBYyxLQUFkLENBQWI7QUFDQSxRQUFJLHFCQUFxQixJQUF6QixFQUErQjtBQUM3QixlQUFTLElBQVQsRUFBZSxJQUFmO0FBQ0EsMkJBQXFCLE9BQXJCLEVBQThCLEtBQTlCLEVBQXFDLGlCQUFyQztBQUNELEtBSEQsTUFHTztBQUNMLGVBQVMsSUFBVCxFQUFlLEtBQWY7QUFDRDtBQUNGLEdBUkQ7QUFTRDs7QUFFRDs7Ozs7Ozs7Ozs7OztBQWFBLFNBQVMsZ0JBQVQsQ0FBeUIsT0FBekIsRUFBa0M7QUFDaEMsTUFBTSxhQUFhLFFBQVEsZUFBUixDQUFuQjtBQUNBLE1BQUksVUFBSixFQUFnQjtBQUNkO0FBQ0EsZUFBVyxPQUFYLENBQW1CLFVBQUMsU0FBRCxFQUFZLEtBQVosRUFBc0I7QUFDdkMsVUFBSSxTQUFKLEVBQWU7QUFDYixrQkFBVSxNQUFWO0FBQ0EsbUJBQVcsS0FBWCxJQUFvQixJQUFwQjtBQUNEO0FBQ0YsS0FMRDtBQU1EO0FBQ0QsTUFBTSxZQUFZLFFBQVEsS0FBUixHQUFnQixRQUFRLEtBQVIsQ0FBYyxNQUE5QixHQUF1QyxDQUF6RDtBQUNBLE1BQUksQ0FBQyxVQUFELElBQWUsV0FBVyxNQUFYLEtBQXNCLFNBQXpDLEVBQW9EO0FBQ2xEO0FBQ0EsWUFBUSxlQUFSLElBQTJCLElBQUksS0FBSixDQUFVLFNBQVYsQ0FBM0I7QUFDRDtBQUNGOztBQUVEOzs7QUFHQSxTQUFTLDBCQUFULENBQW9DLE9BQXBDLEVBQTZDLE9BQTdDLEVBQXNEOztBQUVwRDtBQUNBO0FBQ0E7QUFDQTtBQUNBLE1BQU0sY0FBYyxRQUFRLFdBQTVCO0FBQ0EsTUFBSSxlQUFlLElBQW5CLEVBQXlCO0FBQ3ZCLFFBQUksUUFBUSxlQUFSLEVBQXlCLFdBQXpCLENBQUosRUFBMkM7QUFDekM7QUFDQSxjQUFRLGVBQVIsRUFBeUIsV0FBekIsRUFBc0MsTUFBdEM7QUFDQSxjQUFRLGVBQVIsRUFBeUIsV0FBekIsSUFBd0MsSUFBeEM7QUFDRDtBQUNELFFBQU0sb0JBQW9CLFFBQVEsT0FBUixHQUFrQixDQUFsQixHQUFzQixDQUFoRDtBQUNBLHlCQUFxQixPQUFyQixFQUE4QixXQUE5QixFQUEyQyxpQkFBM0M7QUFDQSxhQUFTLFFBQVEsS0FBUixDQUFjLFdBQWQsQ0FBVCxFQUFxQyxJQUFyQztBQUNEOztBQUVELFVBQVEsbUJBQVIsRUFBNkIsUUFBN0IsR0FBd0MsSUFBeEM7QUFDQSxVQUFRLHNCQUFSLElBQWtDLEtBQWxDO0FBQ0Q7O0FBRUQ7Ozs7QUFJQSxTQUFTLG9CQUFULENBQThCLE9BQTlCLEVBQXVDLFNBQXZDLEVBQWtELFFBQWxELEVBQTREO0FBQzFELE1BQU0sWUFBWSx5QkFBeUIsT0FBekIsRUFBa0MsU0FBbEMsQ0FBbEI7QUFDQSxNQUFJLFNBQUosRUFBZTtBQUNiLFFBQU0sV0FBVyxRQUFRLDBCQUF6QjtBQUNBLFFBQUksUUFBSixFQUFjO0FBQ1osZ0JBQVUsV0FBVixHQUF3QixXQUFXLFFBQW5DO0FBQ0Q7QUFDRjtBQUNGOztBQUVELFNBQVMsUUFBVCxDQUFrQixJQUFsQixFQUF3QixJQUF4QixFQUE4QjtBQUM1QixPQUFLLEtBQUwsQ0FBVyxVQUFYLEdBQXdCLE9BQU8sU0FBUCxHQUFtQixRQUEzQztBQUNEOztBQUVEOzs7Ozs7OztBQVFBLFNBQVMsWUFBVCxDQUFzQixNQUF0QixFQUE4QixTQUE5QixFQUF5QyxhQUF6QyxFQUF3RCxXQUF4RCxFQUFxRTtBQUNuRSxNQUFJLFFBQVEsY0FBYyxhQUExQjtBQUNBO0FBQ0EsTUFBSSxhQUFhLFNBQVMsQ0FBMUIsRUFBNkI7QUFDM0IsUUFBTSxZQUFZLFNBQVMsS0FBSyxHQUFMLENBQVMsS0FBVCxDQUEzQjtBQUNBLFFBQUksYUFBYSxDQUFqQixFQUFvQjtBQUNsQjtBQUNBLGNBQVEsUUFBUSxDQUFSLEdBQ04sU0FETSxHQUNRO0FBQ2QsT0FBQyxTQUZILENBRmtCLENBSUY7QUFDakI7QUFDRjtBQUNELFNBQU8sS0FBUDtBQUNEOzs7Ozs7Ozs7Ozs7Ozs7QUM1b0JEOzs7Ozs7Ozs7Ozs7QUFHQTtBQUNBLElBQUksVUFBVSxDQUFkOztBQUdBOztrQkFDZSxVQUFDLElBQUQsRUFBVTs7QUFFdkI7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7QUFGdUIsTUFpQ2pCLG1CQWpDaUI7QUFBQTs7QUFBQTtBQUFBOztBQUFBO0FBQUE7O0FBQUE7QUFBQTtBQUFBLDBDQW1DRDtBQUNsQiw4SUFBNkI7QUFBRTtBQUE0QjtBQUMzRDtBQUNBLFlBQUksS0FBSyxZQUFMLENBQWtCLE1BQWxCLEtBQTZCLElBQTdCLElBQXFDLEtBQUssa0JBQVEsUUFBYixFQUF1QixJQUFoRSxFQUFzRTtBQUNwRSxlQUFLLFlBQUwsQ0FBa0IsTUFBbEIsRUFBMEIsS0FBSyxrQkFBUSxRQUFiLEVBQXVCLElBQWpEO0FBQ0Q7QUFDRjtBQXpDb0I7QUFBQSxXQWlEcEIsa0JBQVEsU0FqRFk7QUFBQSw0QkFpREQsSUFqREMsRUFpREs7QUFDeEIsa0hBQVUsa0JBQVEsU0FBbEIsU0FBOEI7QUFBRSxnSEFBTSxrQkFBUSxTQUFkLG1CQUF5QixJQUF6QjtBQUFpQzs7QUFFakUsWUFBSSxDQUFDLEtBQUssWUFBTCxDQUFrQixNQUFsQixDQUFMLEVBQWdDO0FBQzlCO0FBQ0EsZUFBSyxZQUFMLENBQWtCLE1BQWxCLEVBQTBCLFFBQTFCO0FBQ0Q7O0FBRUQ7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQSxZQUFJLENBQUMsS0FBSyxFQUFWLEVBQWM7QUFDWixjQUFNLFNBQVMsS0FBSyxFQUFMLEdBQ1gsTUFBTSxLQUFLLEVBQVgsR0FBZ0IsUUFETCxHQUVYLFNBRko7QUFHQSxlQUFLLEVBQUwsR0FBVSxTQUFTLFNBQW5CO0FBQ0Q7QUFDRjtBQXpFb0I7QUFBQSxXQTJFcEIsa0JBQVEsWUEzRVk7QUFBQSw0QkEyRUUsSUEzRUYsRUEyRVEsUUEzRVIsRUEyRWtCO0FBQ3JDLGtIQUFVLGtCQUFRLFlBQWxCLFNBQWlDO0FBQUUsZ0hBQU0sa0JBQVEsWUFBZCxtQkFBNEIsSUFBNUIsRUFBa0MsUUFBbEM7QUFBOEM7QUFDakYsYUFBSyxZQUFMLENBQWtCLGVBQWxCLEVBQW1DLFFBQW5DO0FBQ0EsWUFBTSxTQUFTLEtBQUssRUFBcEI7QUFDQSxZQUFJLFVBQVUsUUFBZCxFQUF3QjtBQUN0QixlQUFLLFlBQUwsQ0FBa0IsdUJBQWxCLEVBQTJDLE1BQTNDO0FBQ0Q7QUFDRjtBQWxGb0I7QUFBQSxXQTJDaEIsa0JBQVEsUUEzQ1E7QUFBQSwwQkEyQ0k7QUFDdkIsWUFBTSxXQUFXLHNHQUFNLGtCQUFRLFFBQWQsV0FBMkIsRUFBNUM7QUFDQSxpQkFBUyxJQUFULEdBQWdCLFNBQWhCO0FBQ0EsZUFBTyxRQUFQO0FBQ0Q7QUEvQ29CO0FBQUE7QUFBQSwwQkFvRkY7QUFDakI7QUFDRCxPQXRGb0I7QUFBQSx3QkF1RkosSUF2RkksRUF1RkU7QUFDckIsWUFBSSxrQkFBa0IsS0FBSyxTQUEzQixFQUFzQztBQUFFLGdJQUFxQixJQUFyQjtBQUE0QjtBQUNwRSxZQUFJLFFBQVEsSUFBWixFQUFrQjtBQUNoQjtBQUNBLGVBQUssZUFBTCxDQUFxQix1QkFBckI7QUFDRDtBQUNGO0FBN0ZvQjs7QUFBQTtBQUFBLElBaUNXLElBakNYOztBQWlHdkIsU0FBTyxtQkFBUDtBQUNELEM7Ozs7Ozs7Ozs7Ozs7OztBQzFHRDtrQkFDZSxVQUFDLElBQUQsRUFBVTs7QUFFdkI7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7OztBQUZ1QixNQXVCakIsdUJBdkJpQjtBQUFBOztBQXlCckIsdUNBQWM7QUFBQTs7QUFBQTs7QUFFWixVQUFJLE1BQUssVUFBVCxFQUFxQjtBQUNuQjtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQSxjQUFLLENBQUwsR0FBUyxFQUFUO0FBQ0EsWUFBTSxlQUFlLE1BQUssVUFBTCxDQUFnQixnQkFBaEIsQ0FBaUMsTUFBakMsQ0FBckI7QUFDQSxXQUFHLE9BQUgsQ0FBVyxJQUFYLENBQWdCLFlBQWhCLEVBQThCLGdCQUFRO0FBQ3BDLGNBQU0sS0FBSyxLQUFLLFlBQUwsQ0FBa0IsSUFBbEIsQ0FBWDtBQUNBLGdCQUFLLENBQUwsQ0FBTyxFQUFQLElBQWEsSUFBYjtBQUNELFNBSEQ7QUFJRDtBQWZXO0FBZ0JiOztBQUVEOzs7Ozs7Ozs7QUEzQ3FCO0FBQUEsSUF1QmUsSUF2QmY7O0FBb0R2QixTQUFPLHVCQUFQO0FBQ0QsQzs7Ozs7Ozs7O0FDdEREOzs7Ozs7Ozs7Ozs7QUFHQTtrQkFDZSxVQUFDLElBQUQsRUFBVTs7QUFFdkI7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7QUFGdUIsTUF3QmpCLGNBeEJpQjtBQUFBOztBQTBCckI7Ozs7QUFJQSw4QkFBYztBQUFBOztBQUFBOztBQUVaLFVBQUksV0FBVyxNQUFLLGtCQUFRLFFBQWIsQ0FBZjtBQUNBO0FBQ0E7QUFDQSxVQUFJLFFBQUosRUFBYzs7QUFFWixZQUFJLE9BQU8sUUFBUCxLQUFvQixRQUF4QixFQUFrQztBQUNoQztBQUNBLHFCQUFXLDRCQUE0QixRQUE1QixDQUFYO0FBQ0Q7O0FBRUQsWUFBSSxPQUFPLGlCQUFYLEVBQThCO0FBQzVCLDZCQUFtQixRQUFuQixFQUE2QixNQUFLLFNBQWxDO0FBQ0Q7O0FBRUQsWUFBTSxPQUFPLE1BQUssWUFBTCxDQUFrQixFQUFFLE1BQU0sTUFBUixFQUFsQixDQUFiO0FBQ0EsWUFBTSxRQUFRLFNBQVMsVUFBVCxDQUFvQixTQUFTLE9BQTdCLEVBQXNDLElBQXRDLENBQWQ7QUFDQSxhQUFLLFdBQUwsQ0FBaUIsS0FBakI7QUFDRDtBQW5CVztBQW9CYjs7QUFsRG9CO0FBQUEsSUF3Qk0sSUF4Qk47O0FBc0R2QixTQUFPLGNBQVA7QUFDRCxDOztBQUdEOzs7QUFDQSxTQUFTLDJCQUFULENBQXFDLFNBQXJDLEVBQWdEO0FBQzlDLE1BQU0sV0FBVyxTQUFTLGFBQVQsQ0FBdUIsVUFBdkIsQ0FBakI7QUFDQTtBQUNBO0FBQ0E7QUFDQSxNQUFNLE1BQU0sU0FBUyxhQUFULENBQXVCLEtBQXZCLENBQVo7QUFDQSxNQUFJLFNBQUosR0FBZ0IsU0FBaEI7QUFDQSxTQUFPLElBQUksVUFBSixDQUFlLE1BQWYsR0FBd0IsQ0FBL0IsRUFBa0M7QUFDaEMsYUFBUyxPQUFULENBQWlCLFdBQWpCLENBQTZCLElBQUksVUFBSixDQUFlLENBQWYsQ0FBN0I7QUFDRDtBQUNELFNBQU8sUUFBUDtBQUNEOztBQUVEO0FBQ0EsU0FBUyxrQkFBVCxDQUE0QixRQUE1QixFQUFzQyxHQUF0QyxFQUEyQztBQUN6QyxTQUFPLGFBQVAsQ0FBcUIsU0FBckIsQ0FBK0IsV0FBL0IsQ0FBMkMsU0FBUyxPQUFwRCxFQUE2RCxHQUE3RDtBQUNEOzs7Ozs7Ozs7Ozs7Ozs7QUMvRUQ7Ozs7QUFDQTs7Ozs7Ozs7Ozs7O0FBR0E7QUFDQSxJQUFNLHNCQUFzQiw0QkFBYSxlQUFiLENBQTVCO0FBQ0EsSUFBTSwwQkFBMEIsNEJBQWEsbUJBQWIsQ0FBaEM7QUFDQSxJQUFNLDBCQUEwQiw0QkFBYSxtQkFBYixDQUFoQztBQUNBLElBQU0sdUJBQXVCLDRCQUFhLGdCQUFiLENBQTdCOztBQUVBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQTtBQUNBO0FBQ0E7QUFDQSxJQUFNLDhCQUE4Qiw0QkFBYSx1QkFBYixDQUFwQztBQUNBLElBQU0sNkJBQTZCLDRCQUFhLHNCQUFiLENBQW5DO0FBQ0EsSUFBTSw4QkFBOEIsNEJBQWEsdUJBQWIsQ0FBcEM7QUFDQSxJQUFNLDZCQUE2Qiw0QkFBYSxzQkFBYixDQUFuQzs7QUFHQTs7a0JBQ2UsVUFBQyxJQUFELEVBQVU7O0FBRXZCOzs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7O0FBRnVCLE1Bd0JqQixlQXhCaUI7QUFBQTs7QUEwQnJCLCtCQUFjO0FBQUE7O0FBRVo7QUFGWTs7QUFHWixVQUFJLE9BQU8sTUFBSyxpQkFBWixLQUFrQyxXQUF0QyxFQUFtRDtBQUNqRCxjQUFLLGlCQUFMLEdBQXlCLE1BQUssa0JBQVEsUUFBYixFQUF1QixpQkFBaEQ7QUFDRDtBQUNELFVBQUksT0FBTyxNQUFLLGNBQVosS0FBK0IsV0FBbkMsRUFBZ0Q7QUFDOUMsY0FBSyxjQUFMLEdBQXNCLE1BQUssa0JBQVEsUUFBYixFQUF1QixjQUE3QztBQUNEO0FBUlc7QUFTYjs7QUFFRDs7Ozs7Ozs7QUFyQ3FCO0FBQUEsV0F3RnBCLGtCQUFRLFNBeEZZOzs7QUFnRnJCOzs7Ozs7OztBQWhGcUIsNEJBd0ZELElBeEZDLEVBd0ZLO0FBQ3hCLDBHQUFVLGtCQUFRLFNBQWxCLFNBQThCO0FBQUUsd0dBQU0sa0JBQVEsU0FBZCxtQkFBeUIsSUFBekI7QUFBaUM7QUFDakUsYUFBSyxrQkFBUSxZQUFiLEVBQTJCLElBQTNCLEVBQWlDLFNBQVMsS0FBSyxZQUEvQztBQUNEO0FBM0ZvQjtBQUFBLFdBNkZwQixrQkFBUSxZQTdGWTtBQUFBLDhCQTZGSTtBQUN2QiwwR0FBVSxrQkFBUSxZQUFsQixTQUFpQztBQUFFLHdHQUFNLGtCQUFRLFlBQWQ7QUFBZ0M7O0FBRW5FO0FBQ0EsMEJBQWtCLElBQWxCOztBQUVBO0FBQ0Esa0NBQTBCLElBQTFCO0FBQ0Q7O0FBRUQ7Ozs7Ozs7Ozs7QUF2R3FCO0FBQUEsV0FnSHBCLGtCQUFRLFlBaEhZO0FBQUEsNEJBZ0hFLElBaEhGLEVBZ0hRLFFBaEhSLEVBZ0hrQjtBQUNyQywwR0FBVSxrQkFBUSxZQUFsQixTQUFpQztBQUFFLHdHQUFNLGtCQUFRLFlBQWQsbUJBQTRCLElBQTVCLEVBQWtDLFFBQWxDO0FBQThDO0FBQ2xGOztBQUVEOzs7Ozs7Ozs7QUFwSHFCO0FBQUE7OztBQTBPckI7OztBQTFPcUIsb0NBNk9QO0FBQ1osZ0lBQXVCO0FBQUU7QUFBc0I7QUFDL0MsZUFBTyxZQUFZLElBQVosRUFBa0IsQ0FBbEIsQ0FBUDtBQUNEOztBQUVEOzs7Ozs7O0FBbFBxQjtBQUFBOzs7QUFnUnJCOzs7QUFoUnFCLG1DQW1SUjtBQUNYLCtIQUFzQjtBQUFFO0FBQXFCO0FBQzdDLGVBQU8sWUFBWSxJQUFaLEVBQWtCLEtBQUssS0FBTCxDQUFXLE1BQVgsR0FBb0IsQ0FBdEMsQ0FBUDtBQUNEOztBQUVEOzs7O0FBeFJxQjtBQUFBO0FBQUEsbUNBMlJSO0FBQ1gsK0hBQXNCO0FBQUU7QUFBcUI7QUFDN0MsZUFBTyxZQUFZLElBQVosRUFBa0IsS0FBSyxhQUFMLEdBQXFCLENBQXZDLENBQVA7QUFDRDs7QUFFRDs7Ozs7O0FBaFNxQjtBQUFBO0FBQUEsdUNBcVNKO0FBQ2YsbUlBQTBCO0FBQUU7QUFBeUI7QUFDckQsWUFBTSxXQUFXLEtBQUssYUFBTCxHQUFxQixDQUFyQixHQUNmLEtBQUssS0FBTCxDQUFXLE1BQVgsR0FBb0IsQ0FETCxHQUNhO0FBQzVCLGFBQUssYUFBTCxHQUFxQixDQUZ2QjtBQUdBLGVBQU8sWUFBWSxJQUFaLEVBQWtCLFFBQWxCLENBQVA7QUFDRDs7QUFFRDs7Ozs7Ozs7O0FBU0E7Ozs7Ozs7O0FBdFRxQjtBQUFBO0FBQUEsMEJBMkNEO0FBQ2xCLGVBQU8sS0FBSyxtQkFBTCxDQUFQO0FBQ0QsT0E3Q29CO0FBQUEsd0JBOENILGFBOUNHLEVBOENZO0FBQy9CLFlBQU0sd0JBQXdCLEtBQUssbUJBQUwsQ0FBOUI7QUFDQSxhQUFLLG1CQUFMLElBQTRCLGFBQTVCO0FBQ0EsWUFBSSxtQkFBbUIsS0FBSyxTQUE1QixFQUF1QztBQUFFLHlIQUFzQixhQUF0QjtBQUFzQztBQUMvRSxZQUFJLGtCQUFrQixxQkFBdEIsRUFBNkM7QUFDM0MsZUFBSyxhQUFMLENBQW1CLElBQUksV0FBSixDQUFnQix5QkFBaEIsQ0FBbkI7QUFDRDtBQUNGOztBQUVEOzs7Ozs7O0FBdkRxQjtBQUFBO0FBQUEsMEJBNkRHO0FBQ3RCLGVBQU8sS0FBSyx1QkFBTCxDQUFQO0FBQ0QsT0EvRG9CO0FBQUEsd0JBZ0VDLGlCQWhFRCxFQWdFb0I7QUFDdkMsWUFBTSw0QkFBNEIsS0FBSyx1QkFBTCxDQUFsQztBQUNBLGFBQUssdUJBQUwsSUFBZ0MsaUJBQWhDO0FBQ0EsWUFBSSx1QkFBdUIsS0FBSyxTQUFoQyxFQUEyQztBQUFFLDZIQUEwQixpQkFBMUI7QUFBOEM7QUFDM0YsWUFBSSxzQkFBc0IseUJBQTFCLEVBQXFEO0FBQ25ELGVBQUssYUFBTCxDQUFtQixJQUFJLFdBQUosQ0FBZ0IsNkJBQWhCLENBQW5CO0FBQ0Q7QUFDRjtBQXZFb0I7QUFBQSxXQXlFaEIsa0JBQVEsUUF6RVE7QUFBQSwwQkF5RUk7QUFDdkIsWUFBTSxXQUFXLDhGQUFNLGtCQUFRLFFBQWQsV0FBMkIsRUFBNUM7QUFDQSxpQkFBUyxpQkFBVCxHQUE2QixLQUE3QjtBQUNBLGlCQUFTLGNBQVQsR0FBMEIsS0FBMUI7QUFDQSxlQUFPLFFBQVA7QUFDRDtBQTlFb0I7QUFBQTtBQUFBLDBCQTRIRDtBQUNsQixlQUFPLEtBQUssMkJBQUwsS0FBcUMsSUFBckMsR0FDTCxLQUFLLDJCQUFMLENBREssR0FFTCxDQUFDLENBRkg7QUFHRCxPQWhJb0I7QUFBQSx3QkFpSUgsS0FqSUcsRUFpSUk7QUFDdkI7QUFDQSxZQUFNLHdCQUF3QixLQUFLLDJCQUFMLENBQTlCO0FBQ0EsWUFBSSxhQUFKO0FBQ0EsWUFBSSxVQUFVLEtBQUssMkJBQUwsQ0FBZCxFQUFpRDtBQUMvQztBQUNBLGNBQU0sUUFBUSxLQUFLLEtBQW5CO0FBQ0EsY0FBTSxXQUFXLFNBQVMsTUFBTSxNQUFOLEdBQWUsQ0FBekM7QUFDQSxjQUFJLEVBQUUsWUFBWSxTQUFTLENBQXJCLElBQTBCLFFBQVEsTUFBTSxNQUExQyxDQUFKLEVBQXVEO0FBQ3JELG9CQUFRLENBQUMsQ0FBVCxDQURxRCxDQUN6QztBQUNiO0FBQ0QsZUFBSywyQkFBTCxJQUFvQyxLQUFwQztBQUNBLGlCQUFPLFlBQVksU0FBUyxDQUFyQixHQUF5QixNQUFNLEtBQU4sQ0FBekIsR0FBd0MsSUFBL0M7QUFDQSxlQUFLLDBCQUFMLElBQW1DLElBQW5DO0FBQ0QsU0FWRCxNQVVPO0FBQ0wsaUJBQU8sS0FBSywwQkFBTCxDQUFQO0FBQ0Q7O0FBRUQ7QUFDQSxZQUFJLG1CQUFtQixLQUFLLFNBQTVCLEVBQXVDO0FBQUUseUhBQXNCLEtBQXRCO0FBQThCOztBQUV2RSxZQUFJLFVBQVUscUJBQWQsRUFBcUM7QUFDbkM7QUFDQSxlQUFLLDJCQUFMLElBQW9DLEtBQXBDOztBQUVBLGNBQU0sUUFBUSxJQUFJLFdBQUosQ0FBZ0Isd0JBQWhCLEVBQTBDO0FBQ3RELG9CQUFRO0FBQ04sNkJBQWUsS0FEVDtBQUVOLHFCQUFPLEtBRkQsQ0FFTztBQUZQO0FBRDhDLFdBQTFDLENBQWQ7QUFNQSxlQUFLLGFBQUwsQ0FBbUIsS0FBbkI7QUFDRDs7QUFFRCxZQUFJLEtBQUssMEJBQUwsTUFBcUMsSUFBekMsRUFBK0M7QUFDN0M7QUFDQSxlQUFLLFlBQUwsR0FBb0IsSUFBcEI7QUFDRDtBQUNGOztBQUVEOzs7Ozs7Ozs7Ozs7QUF6S3FCO0FBQUE7QUFBQSwwQkFvTEY7QUFDakIsZUFBTyxLQUFLLDBCQUFMLEtBQW9DLElBQTNDO0FBQ0QsT0F0TG9CO0FBQUEsd0JBdUxKLElBdkxJLEVBdUxFO0FBQ3JCO0FBQ0EsWUFBTSx1QkFBdUIsS0FBSywwQkFBTCxDQUE3QjtBQUNBLFlBQUksY0FBSjtBQUNBLFlBQUksU0FBUyxLQUFLLDBCQUFMLENBQWIsRUFBK0M7QUFDN0M7QUFDQSxjQUFNLFFBQVEsS0FBSyxLQUFuQjtBQUNBLGNBQU0sV0FBVyxTQUFTLE1BQU0sTUFBTixHQUFlLENBQXpDO0FBQ0Esa0JBQVEsV0FBVyxNQUFNLFNBQU4sQ0FBZ0IsT0FBaEIsQ0FBd0IsSUFBeEIsQ0FBNkIsS0FBN0IsRUFBb0MsSUFBcEMsQ0FBWCxHQUF1RCxDQUFDLENBQWhFO0FBQ0EsZUFBSywyQkFBTCxJQUFvQyxLQUFwQztBQUNBLGNBQUksUUFBUSxDQUFaLEVBQWU7QUFDYixtQkFBTyxJQUFQLENBRGEsQ0FDQTtBQUNkO0FBQ0QsZUFBSywwQkFBTCxJQUFtQyxJQUFuQztBQUNELFNBVkQsTUFVTztBQUNMLGtCQUFRLEtBQUssMkJBQUwsQ0FBUjtBQUNEOztBQUVEO0FBQ0EsWUFBSSxrQkFBa0IsS0FBSyxTQUEzQixFQUFzQztBQUFFLHdIQUFxQixJQUFyQjtBQUE0Qjs7QUFFcEUsWUFBSSxTQUFTLG9CQUFiLEVBQW1DO0FBQ2pDO0FBQ0EsZUFBSywwQkFBTCxJQUFtQyxJQUFuQzs7QUFFQSxjQUFJLG9CQUFKLEVBQTBCO0FBQ3hCO0FBQ0EsaUJBQUssa0JBQVEsWUFBYixFQUEyQixvQkFBM0IsRUFBaUQsS0FBakQ7QUFDRDtBQUNELGNBQUksSUFBSixFQUFVO0FBQ1I7QUFDQSxpQkFBSyxrQkFBUSxZQUFiLEVBQTJCLElBQTNCLEVBQWlDLElBQWpDO0FBQ0Q7O0FBRUQsb0NBQTBCLElBQTFCOztBQUVBLGNBQU0sUUFBUSxJQUFJLFdBQUosQ0FBZ0IsdUJBQWhCLEVBQXlDO0FBQ3JELG9CQUFRO0FBQ04sNEJBQWMsSUFEUjtBQUVOLHFCQUFPLElBRkQsQ0FFTTtBQUZOO0FBRDZDLFdBQXpDLENBQWQ7QUFNQSxlQUFLLGFBQUwsQ0FBbUIsS0FBbkI7QUFDRDs7QUFFRCxZQUFJLEtBQUssMkJBQUwsTUFBc0MsS0FBMUMsRUFBaUQ7QUFDL0M7QUFDQSxlQUFLLGFBQUwsR0FBcUIsS0FBckI7QUFDRDtBQUNGO0FBeE9vQjtBQUFBO0FBQUEsMEJBd1BHO0FBQ3RCLGVBQU8sS0FBSyx1QkFBTCxDQUFQO0FBQ0QsT0ExUG9CO0FBQUEsd0JBMlBDLGlCQTNQRCxFQTJQb0I7QUFDdkMsYUFBSyx1QkFBTCxJQUFnQyxpQkFBaEM7QUFDQSxZQUFJLHVCQUF1QixLQUFLLFNBQWhDLEVBQTJDO0FBQUUsNkhBQTBCLGlCQUExQjtBQUE4QztBQUMzRiwwQkFBa0IsSUFBbEI7QUFDRDs7QUFFRDs7Ozs7OztBQWpRcUI7QUFBQTtBQUFBLDBCQXVRQTtBQUNuQixlQUFPLEtBQUssb0JBQUwsQ0FBUDtBQUNELE9BelFvQjtBQUFBLHdCQTBRRixLQTFRRSxFQTBRSztBQUN4QixhQUFLLG9CQUFMLElBQTZCLE9BQU8sS0FBUCxNQUFrQixNQUEvQztBQUNBLFlBQUksb0JBQW9CLEtBQUssU0FBN0IsRUFBd0M7QUFBRSwwSEFBdUIsS0FBdkI7QUFBK0I7QUFDekUsa0NBQTBCLElBQTFCO0FBQ0Q7QUE5UW9COztBQUFBO0FBQUEsSUF3Qk8sSUF4QlA7O0FBZ1V2QixTQUFPLGVBQVA7QUFDRCxDOztBQUdEO0FBQ0E7OztBQUNBLFNBQVMsV0FBVCxDQUFxQixPQUFyQixFQUE4QixLQUE5QixFQUFxQztBQUNuQyxNQUFNLFFBQVEsUUFBUSxLQUFSLENBQWMsTUFBNUI7O0FBRUEsTUFBTSxlQUFnQixRQUFRLGNBQVQ7QUFDbkI7QUFDQTtBQUNBLEdBQUUsUUFBUSxLQUFULEdBQWtCLEtBQW5CLElBQTRCLEtBSFQ7O0FBS25CO0FBQ0EsT0FBSyxHQUFMLENBQVMsS0FBSyxHQUFMLENBQVMsS0FBVCxFQUFnQixRQUFRLENBQXhCLENBQVQsRUFBcUMsQ0FBckMsQ0FORjs7QUFRQSxNQUFNLGdCQUFnQixRQUFRLGFBQTlCO0FBQ0EsTUFBSSxrQkFBa0IsWUFBdEIsRUFBb0M7QUFDbEMsWUFBUSxhQUFSLEdBQXdCLFlBQXhCO0FBQ0EsV0FBTyxJQUFQO0FBQ0QsR0FIRCxNQUdPO0FBQ0wsV0FBTyxLQUFQO0FBQ0Q7QUFDRjs7QUFFRDtBQUNBO0FBQ0E7QUFDQTtBQUNBLFNBQVMsaUJBQVQsQ0FBMkIsT0FBM0IsRUFBb0M7O0FBRWxDLE1BQU0sUUFBUSxRQUFRLEtBQXRCO0FBQ0EsTUFBTSxZQUFZLFFBQVEsTUFBTSxNQUFkLEdBQXVCLENBQXpDOztBQUVBLE1BQU0sdUJBQXVCLFFBQVEsWUFBckM7QUFDQSxNQUFJLENBQUMsb0JBQUwsRUFBMkI7QUFDekI7QUFDQSxRQUFJLFFBQVEsaUJBQVosRUFBK0I7QUFDN0I7QUFDQSxjQUFRLGFBQVIsR0FBd0IsQ0FBeEI7QUFDRDtBQUNGLEdBTkQsTUFNTyxJQUFJLGNBQWMsQ0FBbEIsRUFBcUI7QUFDMUI7QUFDQSxZQUFRLFlBQVIsR0FBdUIsSUFBdkI7QUFDRCxHQUhNLE1BR0E7QUFDTDtBQUNBLFFBQU0sc0JBQXNCLE1BQU0sU0FBTixDQUFnQixPQUFoQixDQUF3QixJQUF4QixDQUE2QixLQUE3QixFQUFvQyxvQkFBcEMsQ0FBNUI7QUFDQSxRQUFNLHdCQUF3QixRQUFRLGFBQXRDO0FBQ0EsUUFBSSxzQkFBc0IsQ0FBMUIsRUFBNkI7QUFDM0I7QUFDQTtBQUNBLFVBQU0sbUJBQW1CLEtBQUssR0FBTCxDQUFTLHFCQUFULEVBQWdDLFlBQVksQ0FBNUMsQ0FBekI7QUFDQTtBQUNBO0FBQ0EsY0FBUSxZQUFSLEdBQXVCLE1BQU0sZ0JBQU4sQ0FBdkI7QUFDRCxLQVBELE1BT08sSUFBSSx3QkFBd0IscUJBQTVCLEVBQW1EO0FBQ3hEO0FBQ0EsY0FBUSxhQUFSLEdBQXdCLG1CQUF4QjtBQUNEO0FBQ0Y7QUFDRjs7QUFFRDtBQUNBO0FBQ0EsU0FBUyx5QkFBVCxDQUFtQyxPQUFuQyxFQUE0QztBQUMxQyxNQUFJLHNCQUFKO0FBQ0EsTUFBSSwwQkFBSjtBQUNBLE1BQU0sUUFBUSxRQUFRLEtBQXRCO0FBQ0EsTUFBSSxTQUFTLElBQVQsSUFBaUIsTUFBTSxNQUFOLEtBQWlCLENBQXRDLEVBQXlDO0FBQ3ZDO0FBQ0Esb0JBQWdCLEtBQWhCO0FBQ0Esd0JBQW9CLEtBQXBCO0FBQ0QsR0FBQyxJQUFJLFFBQVEsY0FBWixFQUE0QjtBQUM1QjtBQUNBLG9CQUFnQixJQUFoQjtBQUNBLHdCQUFvQixJQUFwQjtBQUNELEdBSkMsTUFJSztBQUNMLFFBQU0sUUFBUSxRQUFRLGFBQXRCO0FBQ0EsUUFBSSxRQUFRLENBQVIsSUFBYSxNQUFNLE1BQU4sR0FBZSxDQUFoQyxFQUFtQztBQUNqQztBQUNBO0FBQ0Esc0JBQWdCLElBQWhCO0FBQ0EsMEJBQW9CLElBQXBCO0FBQ0QsS0FMRCxNQUtPO0FBQ0w7QUFDQSwwQkFBcUIsUUFBUSxDQUE3QjtBQUNBLHNCQUFpQixRQUFRLE1BQU0sTUFBTixHQUFlLENBQXhDO0FBQ0Q7QUFDRjtBQUNELE1BQUksUUFBUSxhQUFSLEtBQTBCLGFBQTlCLEVBQTZDO0FBQzNDLFlBQVEsYUFBUixHQUF3QixhQUF4QjtBQUNEO0FBQ0QsTUFBSSxRQUFRLGlCQUFSLEtBQThCLGlCQUFsQyxFQUFxRDtBQUNuRCxZQUFRLGlCQUFSLEdBQTRCLGlCQUE1QjtBQUNEO0FBQ0Y7Ozs7Ozs7Ozs7Ozs7OztBQ2xjRDs7OztBQUNBOzs7Ozs7Ozs7Ozs7QUFHQSxJQUFNLGdCQUFnQiw0QkFBYSxTQUFiLENBQXRCO0FBQ0EsSUFBTSwrQkFBK0IsNEJBQWEsd0JBQWIsQ0FBckM7QUFDQSxJQUFNLHFCQUFxQiw0QkFBYSxjQUFiLENBQTNCOztBQUdBOztrQkFDZSxVQUFDLElBQUQsRUFBVTs7QUFFdkI7Ozs7Ozs7Ozs7Ozs7Ozs7O0FBRnVCLE1BbUJqQixjQW5CaUI7QUFBQTs7QUFxQnJCLDhCQUFjO0FBQUE7O0FBRVo7QUFGWTs7QUFHWixVQUFJLE9BQU8sTUFBSyxPQUFaLEtBQXdCLFdBQTVCLEVBQXlDO0FBQ3ZDLGNBQUssT0FBTCxHQUFlLE1BQUssa0JBQVEsUUFBYixFQUF1QixPQUF0QztBQUNEO0FBQ0QsVUFBSSxPQUFPLE1BQUssc0JBQVosS0FBdUMsV0FBM0MsRUFBd0Q7QUFDdEQsY0FBSyxzQkFBTCxHQUE4QixNQUFLLGtCQUFRLFFBQWIsRUFBdUIsc0JBQXJEO0FBQ0Q7QUFSVztBQVNiOztBQTlCb0I7QUFBQTtBQUFBLHVDQWdDSjtBQUNmLGlJQUEwQjtBQUFFO0FBQXlCO0FBQ3JELHFCQUFhLElBQWI7QUFDRDtBQW5Db0I7QUFBQTs7O0FBNENyQjs7O0FBNUNxQiw2QkErQ2Q7QUFDTCx1SEFBZ0I7QUFBRTtBQUFlO0FBQ2pDLG1CQUFXLElBQVg7QUFDQSxhQUFLLGFBQUwsSUFBc0IsSUFBdEI7QUFDRDs7QUFFRDs7OztBQXJEcUI7QUFBQTtBQUFBLDhCQXdEYjtBQUNOLHdIQUFpQjtBQUFFO0FBQWdCO0FBQ25DLG1CQUFXLElBQVg7QUFDQSxhQUFLLGFBQUwsSUFBc0IsS0FBdEI7QUFDRDs7QUFFRDs7Ozs7OztBQTlEcUI7QUFBQSxXQXFDaEIsa0JBQVEsUUFyQ1E7QUFBQSwwQkFxQ0k7QUFDdkIsWUFBTSxXQUFXLDRGQUFNLGtCQUFRLFFBQWQsV0FBMkIsRUFBNUM7QUFDQSxpQkFBUyxPQUFULEdBQW1CLEtBQW5CO0FBQ0EsaUJBQVMsc0JBQVQsR0FBa0MsSUFBbEM7QUFDQSxlQUFPLFFBQVA7QUFDRDtBQTFDb0I7QUFBQTtBQUFBLDBCQW9FUDtBQUNaLGVBQU8sS0FBSyxhQUFMLENBQVA7QUFDRCxPQXRFb0I7QUFBQSx3QkF1RVQsT0F2RVMsRUF1RUE7QUFDbkIsWUFBTSxrQkFBa0IsS0FBSyxhQUFMLENBQXhCO0FBQ0EsWUFBTSxTQUFTLE9BQU8sT0FBUCxNQUFvQixNQUFuQyxDQUZtQixDQUV3QjtBQUMzQyxZQUFJLGFBQWEsS0FBSyxTQUF0QixFQUFpQztBQUFFLGlIQUFnQixPQUFoQjtBQUEwQjtBQUM3RCxZQUFJLFdBQVcsZUFBZixFQUFnQztBQUM5QixjQUFJLE9BQUosRUFBYTtBQUNYLGlCQUFLLElBQUw7QUFDRCxXQUZELE1BRU87QUFDTCxpQkFBSyxLQUFMO0FBQ0Q7QUFDRjtBQUNGOztBQUVEOzs7Ozs7Ozs7QUFwRnFCO0FBQUE7QUFBQSwwQkE0RkY7QUFDakI7QUFDRCxPQTlGb0I7QUFBQSx3QkErRkosSUEvRkksRUErRkU7QUFDckIsWUFBSSxrQkFBa0IsS0FBSyxTQUEzQixFQUFzQztBQUFFLHNIQUFxQixJQUFyQjtBQUE0QjtBQUNwRSxxQkFBYSxJQUFiO0FBQ0Q7O0FBRUQ7Ozs7Ozs7O0FBcEdxQjtBQUFBO0FBQUEsMEJBMkdRO0FBQzNCLGVBQU8sS0FBSyw0QkFBTCxDQUFQO0FBQ0QsT0E3R29CO0FBQUEsd0JBOEdNLEtBOUdOLEVBOEdhO0FBQ2hDLGFBQUssNEJBQUwsSUFBcUMsU0FBUyxLQUFULENBQXJDO0FBQ0EsWUFBSSw0QkFBNEIsS0FBSyxTQUFyQyxFQUFnRDtBQUFFLGdJQUErQixLQUEvQjtBQUF1QztBQUMxRjtBQWpIb0I7O0FBQUE7QUFBQSxJQW1CTSxJQW5CTjs7QUFxSHZCLFNBQU8sY0FBUDtBQUNELEM7O0FBR0QsU0FBUyxVQUFULENBQW9CLE9BQXBCLEVBQTZCO0FBQzNCLE1BQUksUUFBUSxrQkFBUixDQUFKLEVBQWlDO0FBQy9CLGlCQUFhLFFBQVEsa0JBQVIsQ0FBYjtBQUNBLFlBQVEsa0JBQVIsSUFBOEIsSUFBOUI7QUFDRDtBQUNGOztBQUVELFNBQVMsWUFBVCxDQUFzQixPQUF0QixFQUErQjtBQUM3QixhQUFXLE9BQVg7QUFDQSxNQUFJLFFBQVEsT0FBUixJQUFtQixRQUFRLEtBQTNCLElBQW9DLFFBQVEsS0FBUixDQUFjLE1BQWQsR0FBdUIsQ0FBL0QsRUFBa0U7QUFDaEUsZUFBVyxPQUFYO0FBQ0Q7QUFDRjs7QUFFRCxTQUFTLFVBQVQsQ0FBb0IsT0FBcEIsRUFBNkI7QUFDM0I7QUFDQSxhQUFXLE9BQVg7QUFDQSxVQUFRLGtCQUFSLElBQThCLFdBQVcsWUFBTTtBQUM3Qyx1QkFBbUIsT0FBbkI7QUFDRCxHQUY2QixFQUUzQixRQUFRLHNCQUZtQixDQUE5QjtBQUdEOztBQUVEO0FBQ0EsU0FBUyxrQkFBVCxDQUE0QixPQUE1QixFQUFxQztBQUNuQyxNQUFNLFFBQVEsUUFBUSxLQUF0QjtBQUNBLE1BQUksU0FBUyxNQUFNLE1BQU4sR0FBZSxDQUE1QixFQUErQjtBQUM3QixRQUFJLFFBQVEsYUFBUixJQUF5QixJQUF6QixJQUFpQyxRQUFRLGFBQVIsS0FBMEIsTUFBTSxNQUFOLEdBQWUsQ0FBOUUsRUFBaUY7QUFDL0UsY0FBUSxXQUFSO0FBQ0QsS0FGRCxNQUVPO0FBQ0wsY0FBUSxVQUFSO0FBQ0Q7QUFDRjtBQUNGOzs7Ozs7OztrQkMvSHVCLFk7QUFwQ3hCOzs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7QUFvQ2UsU0FBUyxZQUFULENBQXNCLFdBQXRCLEVBQW1DO0FBQ2hELFNBQU8sT0FBTyxNQUFQLEtBQWtCLFVBQWxCLEdBQ0wsT0FBTyxXQUFQLENBREssU0FFRCxXQUZOO0FBR0Q7Ozs7Ozs7O2tCQ0p1QixTO0FBcEN4Qjs7Ozs7Ozs7Ozs7Ozs7QUFlQTtBQUNBLElBQU0sWUFBWSxFQUFsQjs7QUFFQTtBQUNBLElBQU0sVUFBVSxTQUFTLGNBQVQsQ0FBd0IsRUFBeEIsQ0FBaEI7O0FBRUE7QUFDQSxJQUFJLFVBQVUsQ0FBZDs7QUFHQTs7Ozs7Ozs7Ozs7QUFXZSxTQUFTLFNBQVQsQ0FBbUIsUUFBbkIsRUFBNkI7QUFDMUMsWUFBVSxJQUFWLENBQWUsUUFBZjtBQUNBO0FBQ0EsVUFBUSxXQUFSLEdBQXNCLEVBQUUsT0FBeEI7QUFDRDs7QUFHRDtBQUNBLFNBQVMsZ0JBQVQsR0FBNEI7QUFDMUIsU0FBTyxVQUFVLE1BQVYsR0FBbUIsQ0FBMUIsRUFBNkI7QUFDM0IsUUFBTSxXQUFXLFVBQVUsS0FBVixFQUFqQjtBQUNBO0FBQ0Q7QUFDRjs7QUFHRDtBQUNBLElBQU0sV0FBVyxJQUFJLGdCQUFKLENBQXFCLGdCQUFyQixDQUFqQjtBQUNBLFNBQVMsT0FBVCxDQUFpQixPQUFqQixFQUEwQjtBQUN4QixpQkFBZTtBQURTLENBQTFCOzs7Ozs7Ozs7QUN0REE7Ozs7QUFDQTs7Ozs7O0FBR0E7QUFDQSxJQUFNLDRCQUE0Qiw0QkFBYSxxQkFBYixDQUFsQztBQUNBLElBQU0sMEJBQTBCLDRCQUFhLG1CQUFiLENBQWhDO0FBQ0EsSUFBTSx1QkFBdUIsNEJBQWEsZ0JBQWIsQ0FBN0I7O0FBR0E7OztrQkFHZTs7QUFFYjs7Ozs7Ozs7Ozs7OztBQWFBLFdBZmEscUJBZUgsT0FmRyxFQWVNO0FBQ2pCLFlBQVEseUJBQVIsSUFBcUMsSUFBckM7O0FBRUE7QUFDQSxRQUFJLFFBQVEsdUJBQVIsQ0FBSixFQUFzQztBQUNwQyxXQUFLLElBQUksU0FBVCxJQUFzQixRQUFRLHVCQUFSLENBQXRCLEVBQXdEO0FBQ3RELFlBQU0sUUFBUSxRQUFRLHVCQUFSLEVBQWlDLFNBQWpDLENBQWQ7QUFDQSw4QkFBc0IsT0FBdEIsRUFBK0IsU0FBL0IsRUFBMEMsS0FBMUM7QUFDRDtBQUNELGNBQVEsdUJBQVIsSUFBbUMsSUFBbkM7QUFDRDs7QUFFRDtBQUNBLFFBQUksUUFBUSxvQkFBUixDQUFKLEVBQW1DO0FBQ2pDLFdBQUssSUFBSSxTQUFULElBQXNCLFFBQVEsb0JBQVIsQ0FBdEIsRUFBcUQ7QUFDbkQsWUFBTSxTQUFRLFFBQVEsb0JBQVIsRUFBOEIsU0FBOUIsQ0FBZDtBQUNBLG1DQUFZLE9BQVosRUFBcUIsU0FBckIsRUFBZ0MsTUFBaEM7QUFDRDtBQUNELGNBQVEsb0JBQVIsSUFBZ0MsSUFBaEM7QUFDRDtBQUNGLEdBbkNZOzs7QUFxQ2I7Ozs7Ozs7Ozs7OztBQVlBLGNBakRhLHdCQWlEQSxPQWpEQSxFQWlEUyxTQWpEVCxFQWlEb0IsS0FqRHBCLEVBaUQyQjtBQUN0QyxRQUFJLFFBQVEseUJBQVIsQ0FBSixFQUF3QztBQUN0QztBQUNBLDRCQUFzQixPQUF0QixFQUErQixTQUEvQixFQUEwQyxLQUExQztBQUNELEtBSEQsTUFHTztBQUNMO0FBQ0EsVUFBSSxDQUFDLFFBQVEsdUJBQVIsQ0FBTCxFQUF1QztBQUNyQyxnQkFBUSx1QkFBUixJQUFtQyxFQUFuQztBQUNEO0FBQ0QsY0FBUSx1QkFBUixFQUFpQyxTQUFqQyxJQUE4QyxLQUE5QztBQUNEO0FBQ0YsR0E1RFk7OztBQThEYjs7Ozs7Ozs7Ozs7OztBQWFBLGFBM0VhLHVCQTJFRCxPQTNFQyxFQTJFUSxTQTNFUixFQTJFbUIsS0EzRW5CLEVBMkUwQjtBQUNyQyxRQUFJLFFBQVEseUJBQVIsQ0FBSixFQUF3QztBQUN0QztBQUNBLGlDQUFZLE9BQVosRUFBcUIsU0FBckIsRUFBZ0MsS0FBaEM7QUFDRCxLQUhELE1BR087QUFDTDtBQUNBLFVBQUksQ0FBQyxRQUFRLG9CQUFSLENBQUwsRUFBb0M7QUFDbEMsZ0JBQVEsb0JBQVIsSUFBZ0MsRUFBaEM7QUFDRDtBQUNELGNBQVEsb0JBQVIsRUFBOEIsU0FBOUIsSUFBMkMsS0FBM0M7QUFDRDtBQUNGO0FBdEZZLEM7O0FBMkZmO0FBQ0E7O0FBQ0EsU0FBUyxxQkFBVCxDQUErQixPQUEvQixFQUF3QyxhQUF4QyxFQUF1RCxLQUF2RCxFQUE4RDtBQUM1RCxNQUFJLFVBQVUsSUFBVixJQUFrQixPQUFPLEtBQVAsS0FBaUIsV0FBdkMsRUFBb0Q7QUFDbEQsWUFBUSxlQUFSLENBQXdCLGFBQXhCO0FBQ0QsR0FGRCxNQUVPO0FBQ0wsUUFBTSxPQUFPLE9BQU8sS0FBUCxDQUFiO0FBQ0E7QUFDQSxRQUFJLFFBQVEsWUFBUixDQUFxQixhQUFyQixNQUF3QyxJQUE1QyxFQUFrRDtBQUNoRCxjQUFRLFlBQVIsQ0FBcUIsYUFBckIsRUFBb0MsS0FBcEM7QUFDRDtBQUNGO0FBQ0Y7Ozs7Ozs7OztBQ3BIRDs7Ozs7O0FBRUE7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7OztBQXFCQSxJQUFNLFVBQVU7O0FBRWQ7Ozs7Ozs7Ozs7Ozs7Ozs7O0FBaUJBLFlBQVUsNEJBQWEsVUFBYixDQW5CSTs7QUFxQmQ7Ozs7Ozs7Ozs7Ozs7QUFhQSxZQUFVLDRCQUFhLFVBQWIsQ0FsQ0k7O0FBb0NkOzs7Ozs7O0FBT0EsVUFBUSw0QkFBYSxRQUFiLENBM0NNOztBQTZDZDs7Ozs7Ozs7QUFRQSxTQUFPLDRCQUFhLE9BQWIsQ0FyRE87O0FBdURkOzs7Ozs7O0FBT0EsVUFBUSw0QkFBYSxRQUFiLENBOURNOztBQWdFZDs7Ozs7OztBQU9BLFdBQVMsNEJBQWEsU0FBYixDQXZFSzs7QUF5RWQ7Ozs7Ozs7O0FBUUEsV0FBUyw0QkFBYSxTQUFiLENBakZLOztBQW1GZDs7Ozs7OztBQU9BLFFBQU0sNEJBQWEsTUFBYixDQTFGUTs7QUE0RmQ7Ozs7Ozs7O0FBUUEsYUFBVyw0QkFBYSxXQUFiLENBcEdHOztBQXVHZDs7Ozs7OztBQU9BLGdCQUFjLDRCQUFhLGNBQWIsQ0E5R0E7O0FBZ0hkOzs7Ozs7Ozs7QUFTQSxnQkFBYyw0QkFBYSxjQUFiLENBekhBOztBQTJIZDs7Ozs7Ozs7QUFRQSxXQUFTLDRCQUFhLFNBQWIsQ0FuSUs7O0FBcUlkOzs7Ozs7O0FBT0EsWUFBVSw0QkFBYSxVQUFiO0FBNUlJLENBQWhCOztrQkErSWUsTzs7Ozs7Ozs7a0JDaEpTLFc7QUF0QnhCOzs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7O0FBc0JlLFNBQVMsV0FBVCxDQUFxQixPQUFyQixFQUE4QixTQUE5QixFQUF5QyxLQUF6QyxFQUFnRDtBQUM3RCxNQUFNLFlBQVksUUFBUSxTQUExQjtBQUNBLE1BQU0sV0FBWSxPQUFPLEtBQVAsS0FBaUIsV0FBbEIsR0FDZixDQUFDLFVBQVUsUUFBVixDQUFtQixTQUFuQixDQURjLEdBRWYsS0FGRjtBQUdBLE1BQUksUUFBSixFQUFjO0FBQ1osY0FBVSxHQUFWLENBQWMsU0FBZDtBQUNELEdBRkQsTUFFTztBQUNMLGNBQVUsTUFBVixDQUFpQixTQUFqQjtBQUNEO0FBQ0QsU0FBTyxRQUFQO0FBQ0Q7Ozs7Ozs7OztBQ2pDRDs7OztBQUNBOzs7O0FBQ0E7Ozs7QUFDQTs7OztBQUNBOzs7Ozs7Ozs7Ozs7QUFHQTs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7SUFvQk0sVzs7Ozs7Ozs7OztFQUFvQiwrQkFBZ0IsV0FBaEIsRUFBNkIsT0FBN0IsZ0NBQ007QUFETix3Q0FFTTtBQUZOLHdFOztrQkFPWCxXOzs7OztBQzNCZjs7Ozs7O0FBRUEsT0FBTyxLQUFQLEdBQWUsT0FBTyxLQUFQLElBQWdCLEVBQS9CLEMsQ0FUQTs7Ozs7OztBQVVBLE9BQU8sS0FBUCxDQUFhLFNBQWI7Ozs7Ozs7Ozs7Ozs7QUNWQTs7OztBQUNBOzs7O0FBQ0E7Ozs7QUFDQTs7OztBQUNBOzs7O0FBQ0E7Ozs7QUFDQTs7OztBQUNBOzs7O0FBQ0E7Ozs7Ozs7Ozs7OztBQUdBLElBQU0sT0FBTyxzQkFBWSxPQUFaLGtQQUFiOztBQVdBOzs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7SUFvQk0sUzs7Ozs7Ozs7OztTQUVDLGtCQUFRLFE7d0JBQVk7QUFDdkIsVUFBTSxXQUFXLGtGQUFNLGtCQUFRLFFBQWQsV0FBMkIsRUFBNUM7QUFDQSxlQUFTLE9BQVQsR0FBbUIsSUFBbkI7QUFDQSxlQUFTLDBCQUFULEdBQXNDLEdBQXRDO0FBQ0EsZUFBUyx3QkFBVCxHQUFvQyxXQUFwQztBQUNBLGVBQVMsaUJBQVQsR0FBNkIsSUFBN0I7QUFDQSxlQUFTLHNCQUFULEdBQWtDLElBQWxDO0FBQ0EsZUFBUyxjQUFULEdBQTBCLElBQTFCO0FBQ0EsYUFBTyxRQUFQO0FBQ0Q7O1NBRUksa0JBQVEsUTt3QkFBWTtBQUN2QjtBQXNCRDs7OztFQXBDcUIsSTs7QUF5Q3hCLGVBQWUsTUFBZixDQUFzQixpQkFBdEIsRUFBeUMsU0FBekM7a0JBQ2UsUyIsImZpbGUiOiJnZW5lcmF0ZWQuanMiLCJzb3VyY2VSb290IjoiIiwic291cmNlc0NvbnRlbnQiOlsiKGZ1bmN0aW9uIGUodCxuLHIpe2Z1bmN0aW9uIHMobyx1KXtpZighbltvXSl7aWYoIXRbb10pe3ZhciBhPXR5cGVvZiByZXF1aXJlPT1cImZ1bmN0aW9uXCImJnJlcXVpcmU7aWYoIXUmJmEpcmV0dXJuIGEobywhMCk7aWYoaSlyZXR1cm4gaShvLCEwKTt2YXIgZj1uZXcgRXJyb3IoXCJDYW5ub3QgZmluZCBtb2R1bGUgJ1wiK28rXCInXCIpO3Rocm93IGYuY29kZT1cIk1PRFVMRV9OT1RfRk9VTkRcIixmfXZhciBsPW5bb109e2V4cG9ydHM6e319O3Rbb11bMF0uY2FsbChsLmV4cG9ydHMsZnVuY3Rpb24oZSl7dmFyIG49dFtvXVsxXVtlXTtyZXR1cm4gcyhuP246ZSl9LGwsbC5leHBvcnRzLGUsdCxuLHIpfXJldHVybiBuW29dLmV4cG9ydHN9dmFyIGk9dHlwZW9mIHJlcXVpcmU9PVwiZnVuY3Rpb25cIiYmcmVxdWlyZTtmb3IodmFyIG89MDtvPHIubGVuZ3RoO28rKylzKHJbb10pO3JldHVybiBzfSkiLCJpbXBvcnQgc2FmZUF0dHJpYnV0ZXMgZnJvbSAnLi9zYWZlQXR0cmlidXRlcyc7XG5cblxuLy8gTWVtb2l6ZWQgbWFwcyBvZiBhdHRyaWJ1dGUgdG8gcHJvcGVydHkgbmFtZXMgYW5kIHZpY2UgdmVyc2EuXG5jb25zdCBhdHRyaWJ1dGVUb1Byb3BlcnR5TmFtZXMgPSB7fTtcbmNvbnN0IHByb3BlcnR5TmFtZXNUb0F0dHJpYnV0ZXMgPSB7fTtcblxuXG4vKiBFeHBvcnRlZCBmdW5jdGlvbiBleHRlbmRzIGEgYmFzZSBjbGFzcyB3aXRoIEF0dHJpYnV0ZU1hcnNoYWxsaW5nLiAqL1xuZXhwb3J0IGRlZmF1bHQgKGJhc2UpID0+IHtcblxuICAvKipcbiAgICogTWl4aW4gd2hpY2ggbWFyc2hhbGxzIGF0dHJpYnV0ZXMgdG8gcHJvcGVydGllcyBhbmQgdmljZSB2ZXJzYS5cbiAgICpcbiAgICogSWYgeW91ciBjb21wb25lbnQgZXhwb3NlcyBhIHNldHRlciBmb3IgYSBwcm9wZXJ0eSwgaXQncyBnZW5lcmFsbHkgYSBnb29kXG4gICAqIGlkZWEgdG8gbGV0IGRldnMgdXNpbmcgeW91ciBjb21wb25lbnQgYmUgYWJsZSB0byBzZXQgdGhhdCBwcm9wZXJ0eSBpbiBIVE1MXG4gICAqIHZpYSBhbiBlbGVtZW50IGF0dHJpYnV0ZS4gWW91IGNhbiBjb2RlIHRoYXQgeW91cnNlbGYgYnkgd3JpdGluZyBhblxuICAgKiBgYXR0cmlidXRlQ2hhbmdlZENhbGxiYWNrYCwgb3IgeW91IGNhbiB1c2UgdGhpcyBtaXhpbiB0byBnZXQgYSBkZWdyZWUgb2ZcbiAgICogYXV0b21hdGljIHN1cHBvcnQuXG4gICAqXG4gICAqIFRoaXMgbWl4aW4gaW1wbGVtZW50cyBhbiBgYXR0cmlidXRlQ2hhbmdlZENhbGxiYWNrYCB0aGF0IHdpbGwgYXR0ZW1wdCB0b1xuICAgKiBjb252ZXJ0IGEgY2hhbmdlIGluIGFuIGVsZW1lbnQgYXR0cmlidXRlIGludG8gYSBjYWxsIHRvIHRoZSBjb3JyZXNwb25kaW5nXG4gICAqIHByb3BlcnR5IHNldHRlci4gQXR0cmlidXRlcyB0eXBpY2FsbHkgZm9sbG93IGh5cGhlbmF0ZWQgbmFtZXMgKFwiZm9vLWJhclwiKSxcbiAgICogd2hlcmVhcyBwcm9wZXJ0aWVzIHR5cGljYWxseSB1c2UgY2FtZWxDYXNlIG5hbWVzIChcImZvb0JhclwiKS4gVGhpcyBtaXhpblxuICAgKiByZXNwZWN0cyB0aGF0IGNvbnZlbnRpb24sIGF1dG9tYXRpY2FsbHkgbWFwcGluZyB0aGUgaHlwaGVuYXRlZCBhdHRyaWJ1dGVcbiAgICogbmFtZSB0byB0aGUgY29ycmVzcG9uZGluZyBjYW1lbENhc2UgcHJvcGVydHkgbmFtZS5cbiAgICpcbiAgICogRXhhbXBsZTogWW91IGRlZmluZSBhIGNvbXBvbmVudCB1c2luZyB0aGlzIG1peGluOlxuICAgKlxuICAgKiAgICAgY2xhc3MgTXlFbGVtZW50IGV4dGVuZHMgQXR0cmlidXRlTWFyc2hhbGxpbmdNaXhpbihIVE1MRWxlbWVudCkge1xuICAgKiAgICAgICBnZXQgZm9vQmFyKCkgeyByZXR1cm4gdGhpcy5fZm9vQmFyOyB9XG4gICAqICAgICAgIHNldCBmb29CYXIodmFsdWUpIHsgdGhpcy5fZm9vQmFyID0gdmFsdWU7IH1cbiAgICogICAgIH1cbiAgICogICAgIGN1c3RvbUVsZW1lbnRzLmRlZmluZSgnbXktZWxlbWVudCcsIE15RWxlbWVudCk7XG4gICAqXG4gICAqIElmIHNvbWVvbmUgdGhlbiBpbnN0YW50aWF0ZXMgeW91ciBjb21wb25lbnQgaW4gSFRNTDpcbiAgICpcbiAgICogICAgIDxteS1lbGVtZW50IGZvby1iYXI9XCJIZWxsb1wiPjwvbXktZWxlbWVudD5cbiAgICpcbiAgICogVGhlbiwgYWZ0ZXIgdGhlIGVsZW1lbnQgaGFzIGJlZW4gdXBncmFkZWQsIHRoZSBgZm9vQmFyYCBzZXR0ZXIgd2lsbFxuICAgKiBhdXRvbWF0aWNhbGx5IGJlIGludm9rZWQgd2l0aCB0aGUgaW5pdGlhbCB2YWx1ZSBcIkhlbGxvXCIuXG4gICAqXG4gICAqIEZvciB0aGUgdGltZSBiZWluZywgdGhpcyBtaXhpbiBvbmx5IHN1cHBvcnRzIHN0cmluZy12YWx1ZWQgcHJvcGVydGllcy5cbiAgICogSWYgeW91J2QgbGlrZSB0byBjb252ZXJ0IHN0cmluZyBhdHRyaWJ1dGVzIHRvIG90aGVyIHR5cGVzIChudW1iZXJzLFxuICAgKiBib29sZWFucyksIHlvdSBuZWVkIHRvIGltcGxlbWVudCBgYXR0cmlidXRlQ2hhbmdlZENhbGxiYWNrYCB5b3Vyc2VsZi5cbiAgICovXG4gIGNsYXNzIEF0dHJpYnV0ZU1hcnNoYWxsaW5nIGV4dGVuZHMgYmFzZSB7XG5cbiAgICAvKlxuICAgICAqIEhhbmRsZSBhIGNoYW5nZSB0byB0aGUgYXR0cmlidXRlIHdpdGggdGhlIGdpdmVuIG5hbWUuXG4gICAgICovXG4gICAgYXR0cmlidXRlQ2hhbmdlZENhbGxiYWNrKGF0dHJpYnV0ZU5hbWUsIG9sZFZhbHVlLCBuZXdWYWx1ZSkge1xuICAgICAgaWYgKHN1cGVyLmF0dHJpYnV0ZUNoYW5nZWRDYWxsYmFjaykgeyBzdXBlci5hdHRyaWJ1dGVDaGFuZ2VkQ2FsbGJhY2soKTsgfVxuICAgICAgY29uc3QgcHJvcGVydHlOYW1lID0gYXR0cmlidXRlVG9Qcm9wZXJ0eU5hbWUoYXR0cmlidXRlTmFtZSk7XG4gICAgICAvLyBJZiB0aGUgYXR0cmlidXRlIG5hbWUgY29ycmVzcG9uZHMgdG8gYSBwcm9wZXJ0eSBuYW1lLCBzZXQgdGhlIHByb3BlcnR5LlxuICAgICAgLy8gSWdub3JlIHN0YW5kYXJkIEhUTUxFbGVtZW50IHByb3BlcnRpZXMgaGFuZGxlZCBieSB0aGUgRE9NLlxuICAgICAgaWYgKHByb3BlcnR5TmFtZSBpbiB0aGlzICYmICEocHJvcGVydHlOYW1lIGluIEhUTUxFbGVtZW50LnByb3RvdHlwZSkpIHtcbiAgICAgICAgdGhpc1twcm9wZXJ0eU5hbWVdID0gbmV3VmFsdWU7XG4gICAgICB9XG4gICAgfVxuXG4gICAgY29ubmVjdGVkQ2FsbGJhY2soKSB7XG4gICAgICBpZiAoc3VwZXIuY29ubmVjdGVkQ2FsbGJhY2spIHsgc3VwZXIuY29ubmVjdGVkQ2FsbGJhY2soKTsgfVxuICAgICAgc2FmZUF0dHJpYnV0ZXMuY29ubmVjdGVkKHRoaXMpO1xuICAgIH1cblxuICAgIHN0YXRpYyBnZXQgb2JzZXJ2ZWRBdHRyaWJ1dGVzKCkge1xuICAgICAgcmV0dXJuIGF0dHJpYnV0ZXNGb3JDbGFzcyh0aGlzKTtcbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBTZXQvdW5zZXQgdGhlIGF0dHJpYnV0ZSB3aXRoIHRoZSBpbmRpY2F0ZWQgbmFtZS5cbiAgICAgKlxuICAgICAqIFRoaXMgbWV0aG9kIGV4aXN0cyBwcmltYXJpbHkgdG8gaGFuZGxlIHRoZSBjYXNlIHdoZXJlIGFuIGVsZW1lbnQgd2FudHMgdG9cbiAgICAgKiBzZXQgYSBkZWZhdWx0IHByb3BlcnR5IHZhbHVlIHRoYXQgc2hvdWxkIGJlIHJlZmxlY3RlZCBhcyBhbiBhdHRyaWJ1dGUuIEFuXG4gICAgICogaW1wb3J0YW50IGxpbWl0YXRpb24gb2YgY3VzdG9tIGVsZW1lbnQgY29uc3R1cmN0b3JzIGlzIHRoYXQgdGhleSBjYW5ub3RcbiAgICAgKiBzZXQgYXR0cmlidXRlcy4gQSBjYWxsIHRvIGByZWZsZWN0QXR0cmlidXRlYCBkdXJpbmcgdGhlIGNvbnN0cnVjdG9yIHdpbGxcbiAgICAgKiBiZSBkZWZlcnJlZCB1bnRpbCB0aGUgZWxlbWVudCBpcyBjb25uZWN0ZWQgdG8gdGhlIGRvY3VtZW50LlxuICAgICAqXG4gICAgICogQHBhcmFtIHtzdHJpbmd9IGF0dHJpYnV0ZSAtIFRoZSBuYW1lIG9mIHRoZSAqYXR0cmlidXRlKiAobm90IHByb3BlcnR5KSB0byBzZXQuXG4gICAgICogQHBhcmFtIHtvYmplY3R9IHZhbHVlIC0gVGhlIHZhbHVlIHRvIHNldC4gSWYgbnVsbCwgdGhlIGF0dHJpYnV0ZSB3aWxsIGJlIHJlbW92ZWQuXG4gICAgICovXG4gICAgcmVmbGVjdEF0dHJpYnV0ZShhdHRyaWJ1dGUsIHZhbHVlKSB7XG4gICAgICByZXR1cm4gc2FmZUF0dHJpYnV0ZXMuc2V0QXR0cmlidXRlKHRoaXMsIGF0dHJpYnV0ZSwgdmFsdWUpO1xuICAgIH1cblxuICAgIC8qKlxuICAgICAqIFNldC91bnNldCB0aGUgY2xhc3Mgd2l0aCB0aGUgaW5kaWNhdGVkIG5hbWUuXG4gICAgICpcbiAgICAgKiBUaGlzIG1ldGhvZCBleGlzdHMgcHJpbWFyaWx5IHRvIGhhbmRsZSB0aGUgY2FzZSB3aGVyZSBhbiBlbGVtZW50IHdhbnRzIHRvXG4gICAgICogc2V0IGEgZGVmYXVsdCBwcm9wZXJ0eSB2YWx1ZSB0aGF0IHNob3VsZCBiZSByZWZsZWN0ZWQgYXMgYXMgY2xhc3MuIEFuXG4gICAgICogaW1wb3J0YW50IGxpbWl0YXRpb24gb2YgY3VzdG9tIGVsZW1lbnQgY29uc3R1cmN0b3JzIGlzIHRoYXQgdGhleSBjYW5ub3RcbiAgICAgKiBzZXQgYXR0cmlidXRlcywgaW5jbHVkaW5nIHRoZSBgY2xhc3NgIGF0dHJpYnV0ZS4gQSBjYWxsIHRvXG4gICAgICogYHJlZmxlY3RDbGFzc2AgZHVyaW5nIHRoZSBjb25zdHJ1Y3RvciB3aWxsIGJlIGRlZmVycmVkIHVudGlsIHRoZSBlbGVtZW50XG4gICAgICogaXMgY29ubmVjdGVkIHRvIHRoZSBkb2N1bWVudC5cbiAgICAgKlxuICAgICAqIEBwYXJhbSB7c3RyaW5nfSBjbGFzc05hbWUgLSBUaGUgbmFtZSBvZiB0aGUgY2xhc3MgdG8gc2V0LlxuICAgICAqIEBwYXJhbSB7b2JqZWN0fSB2YWx1ZSAtIFRydWUgdG8gc2V0IHRoZSBjbGFzcywgZmFsc2UgdG8gcmVtb3ZlIGl0LlxuICAgICAqL1xuICAgIHJlZmxlY3RDbGFzcyhjbGFzc05hbWUsIHZhbHVlKSB7XG4gICAgICByZXR1cm4gc2FmZUF0dHJpYnV0ZXMudG9nZ2xlQ2xhc3ModGhpcywgY2xhc3NOYW1lLCB2YWx1ZSk7XG4gICAgfVxuXG4gIH1cblxuICByZXR1cm4gQXR0cmlidXRlTWFyc2hhbGxpbmc7XG59O1xuXG5cbi8vIENvbnZlcnQgaHlwaGVuYXRlZCBmb28tYmFyIGF0dHJpYnV0ZSBuYW1lIHRvIGNhbWVsIGNhc2UgZm9vQmFyIHByb3BlcnR5IG5hbWUuXG5mdW5jdGlvbiBhdHRyaWJ1dGVUb1Byb3BlcnR5TmFtZShhdHRyaWJ1dGVOYW1lKSB7XG4gIGxldCBwcm9wZXJ0eU5hbWUgPSBhdHRyaWJ1dGVUb1Byb3BlcnR5TmFtZXNbYXR0cmlidXRlTmFtZV07XG4gIGlmICghcHJvcGVydHlOYW1lKSB7XG4gICAgLy8gQ29udmVydCBhbmQgbWVtb2l6ZS5cbiAgICBjb25zdCBoeXBlblJlZ0V4ID0gLy0oW2Etel0pL2c7XG4gICAgcHJvcGVydHlOYW1lID0gYXR0cmlidXRlTmFtZS5yZXBsYWNlKGh5cGVuUmVnRXgsXG4gICAgICAgIG1hdGNoID0+IG1hdGNoWzFdLnRvVXBwZXJDYXNlKCkpO1xuICAgIGF0dHJpYnV0ZVRvUHJvcGVydHlOYW1lc1thdHRyaWJ1dGVOYW1lXSA9IHByb3BlcnR5TmFtZTtcbiAgfVxuICByZXR1cm4gcHJvcGVydHlOYW1lO1xufVxuXG5mdW5jdGlvbiBhdHRyaWJ1dGVzRm9yQ2xhc3MoY2xhc3NGbikge1xuXG4gIC8vIFdlIHRyZWF0IHRoZSBlbGVtZW50IGJhc2UgY2xhc3NlcyBhcyBpZiB0aGV5IGhhdmUgbm8gYXR0cmlidXRlcywgc2luY2Ugd2VcbiAgLy8gZG9uJ3Qgd2FudCB0byByZWNlaXZlIGF0dHJpYnV0ZUNoYW5nZWRDYWxsYmFjayBmb3IgdGhlbS5cbiAgaWYgKGNsYXNzRm4gPT09IEhUTUxFbGVtZW50IHx8IGNsYXNzRm4gPT09IE9iamVjdCkge1xuICAgIHJldHVybiBbXTtcbiAgfVxuXG4gIC8vIEdldCBhdHRyaWJ1dGVzIGZvciBwYXJlbnQgY2xhc3MuXG4gIGNvbnN0IGJhc2VDbGFzcyA9IE9iamVjdC5nZXRQcm90b3R5cGVPZihjbGFzc0ZuLnByb3RvdHlwZSkuY29uc3RydWN0b3I7XG4gIGNvbnN0IGJhc2VBdHRyaWJ1dGVzID0gYXR0cmlidXRlc0ZvckNsYXNzKGJhc2VDbGFzcyk7XG5cbiAgLy8gR2V0IGF0dHJpYnV0ZXMgZm9yIHRoaXMgY2xhc3MuXG4gIGNvbnN0IHByb3BlcnR5TmFtZXMgPSBPYmplY3QuZ2V0T3duUHJvcGVydHlOYW1lcyhjbGFzc0ZuLnByb3RvdHlwZSk7XG4gIGNvbnN0IHNldHRlck5hbWVzID0gcHJvcGVydHlOYW1lcy5maWx0ZXIocHJvcGVydHlOYW1lID0+XG4gICAgdHlwZW9mIE9iamVjdC5nZXRPd25Qcm9wZXJ0eURlc2NyaXB0b3IoXG4gICAgICAgIGNsYXNzRm4ucHJvdG90eXBlLCBwcm9wZXJ0eU5hbWUpLnNldCA9PT0gJ2Z1bmN0aW9uJyk7XG4gIGNvbnN0IGF0dHJpYnV0ZXMgPSBzZXR0ZXJOYW1lcy5tYXAoc2V0dGVyTmFtZSA9PlxuICAgICAgcHJvcGVydHlOYW1lVG9BdHRyaWJ1dGUoc2V0dGVyTmFtZSkpO1xuXG4gIC8vIE1lcmdlLlxuICBjb25zdCBkaWZmID0gYXR0cmlidXRlcy5maWx0ZXIoYXR0cmlidXRlID0+XG4gICAgICBiYXNlQXR0cmlidXRlcy5pbmRleE9mKGF0dHJpYnV0ZSkgPCAwKTtcbiAgcmV0dXJuIGJhc2VBdHRyaWJ1dGVzLmNvbmNhdChkaWZmKTtcbn1cblxuLy8gQ29udmVydCBhIGNhbWVsIGNhc2UgZm9vQmFyIHByb3BlcnR5IG5hbWUgdG8gYSBoeXBoZW5hdGVkIGZvby1iYXIgYXR0cmlidXRlLlxuZnVuY3Rpb24gcHJvcGVydHlOYW1lVG9BdHRyaWJ1dGUocHJvcGVydHlOYW1lKSB7XG4gIGxldCBhdHRyaWJ1dGUgPSBwcm9wZXJ0eU5hbWVzVG9BdHRyaWJ1dGVzW3Byb3BlcnR5TmFtZV07XG4gIGlmICghYXR0cmlidXRlKSB7XG4gICAgLy8gQ29udmVydCBhbmQgbWVtb2l6ZS5cbiAgICBjb25zdCB1cHBlcmNhc2VSZWdFeCA9IC8oW0EtWl0pL2c7XG4gICAgYXR0cmlidXRlID0gcHJvcGVydHlOYW1lLnJlcGxhY2UodXBwZXJjYXNlUmVnRXgsICctJDEnKS50b0xvd2VyQ2FzZSgpO1xuICB9XG4gIHJldHVybiBhdHRyaWJ1dGU7XG59XG4iLCIvKiBFeHBvcnRlZCBmdW5jdGlvbiBleHRlbmRzIGEgYmFzZSBjbGFzcyB3aXRoIENvbXBvc2FibGUuICovXG5leHBvcnQgZGVmYXVsdCAoYmFzZSkgPT4ge1xuXG4gIC8qKlxuICAgKiBNaXhpbiB0byBtYWtlIGEgY2xhc3MgbW9yZSBlYXNpbHkgY29tcG9zYWJsZSB3aXRoIG90aGVyIG1peGlucy5cbiAgICpcbiAgICogVGhpcyBtaXhpbiBjb250cmlidXRlcyBhIGBjb21wb3NlYCBtZXRob2QgdGhhdCBhcHBsaWVzIGEgc2V0IG9mIG1peGluXG4gICAqIGZ1bmN0aW9ucyBhbmQgcmV0dXJucyB0aGUgcmVzdWx0aW5nIG5ldyBjbGFzcy4gVGhpcyBzdWdhciBjYW4gbWFrZSB0aGVcbiAgICogYXBwbGljYXRpb24gb2YgbWFueSBtaXhpbnMgYXQgb25jZSBlYXNpZXIgdG8gcmVhZC5cbiAgICovXG4gIGNsYXNzIENvbXBvc2FibGUgZXh0ZW5kcyBiYXNlIHtcblxuICAgIC8qKlxuICAgICAqIEFwcGx5IGEgc2V0IG9mIG1peGluIGZ1bmN0aW9ucyBvciBtaXhpbiBvYmplY3RzIHRvIHRoZSBwcmVzZW50IGNsYXNzIGFuZFxuICAgICAqIHJldHVybiB0aGUgbmV3IGNsYXNzLlxuICAgICAqXG4gICAgICogSW5zdGVhZCBvZiB3cml0aW5nOlxuICAgICAqXG4gICAgICogICAgIGxldCBNeUNsYXNzID0gTWl4aW4xKE1peGluMihNaXhpbjMoTWl4aW40KE1peGluNShCYXNlQ2xhc3MpKSkpKTtcbiAgICAgKlxuICAgICAqIFlvdSBjYW4gd3JpdGU6XG4gICAgICpcbiAgICAgKiAgICAgbGV0IE15Q2xhc3MgPSBDb21wb3NhYmxlTWl4aW4oQmFzZUNsYXNzKS5jb21wb3NlKFxuICAgICAqICAgICAgIE1peGluMSxcbiAgICAgKiAgICAgICBNaXhpbjIsXG4gICAgICogICAgICAgTWl4aW4zLFxuICAgICAqICAgICAgIE1peGluNCxcbiAgICAgKiAgICAgICBNaXhpbjVcbiAgICAgKiAgICAgKTtcbiAgICAgKlxuICAgICAqIFRoaXMgZnVuY3Rpb24gY2FuIGFsc28gdGFrZSBtaXhpbiBvYmplY3RzLiBBIG1peGluIG9iamVjdCBpcyBqdXN0IGFcbiAgICAgKiBzaG9ydGhhbmQgZm9yIGEgbWl4aW4gZnVuY3Rpb24gdGhhdCBjcmVhdGVzIGEgbmV3IHN1YmNsYXNzIHdpdGggdGhlIGdpdmVuXG4gICAgICogbWVtYmVycy4gVGhlIG1peGluIG9iamVjdCdzIG1lbWJlcnMgYXJlICpub3QqIGNvcGllZCBkaXJlY3RseSBvbnRvIHRoZVxuICAgICAqIHByb3RvdHlwZSBvZiB0aGUgYmFzZSBjbGFzcywgYXMgd2l0aCB0cmFkaXRpb25hbCBtaXhpbnMuXG4gICAgICpcbiAgICAgKiBJbiBhZGRpdGlvbiB0byBwcm92aWRpbmcgc3ludGFjdGljIHN1Z2FyLCB0aGlzIG1peGluIGNhbiBiZSB1c2VkIHRvXG4gICAgICogZGVmaW5lIGEgY2xhc3MgaW4gRVM1LCB3aGljaCBsYWNrcyBFUzYncyBgY2xhc3NgIGtleXdvcmQuXG4gICAgICpcbiAgICAgKiBAcGFyYW0gey4uLm1peGluc30gbWl4aW5zIC0gQSBzZXQgb2YgbWl4aW4gZnVuY3Rpb25zIG9yIG9iamVjdHMgdG8gYXBwbHkuXG4gICAgICovXG4gICAgc3RhdGljIGNvbXBvc2UoLi4ubWl4aW5zKSB7XG4gICAgICAvLyBXZSBjcmVhdGUgYSBuZXcgc3ViY2xhc3MgZm9yIGVhY2ggbWl4aW4gaW4gdHVybi4gVGhlIHJlc3VsdCBiZWNvbWVzXG4gICAgICAvLyB0aGUgYmFzZSBjbGFzcyBleHRlbmRlZCBieSBhbnkgc3Vic2VxdWVudCBtaXhpbnMuIEl0IHR1cm5zIG91dCB0aGF0XG4gICAgICAvLyB3ZSBjYW4gdXNlIEFycmF5LnJlZHVjZSgpIHRvIGNvbmNpc2VseSBleHByZXNzIHRoaXMsIHVzaW5nIHRoZSBjdXJyZW50XG4gICAgICAvLyBvYmplY3QgYXMgdGhlIHNlZWQgZm9yIHJlZHVjZSgpLlxuICAgICAgcmV0dXJuIG1peGlucy5yZWR1Y2UoY29tcG9zZUNsYXNzLCB0aGlzKTtcbiAgICB9XG5cbiAgfVxuXG4gIHJldHVybiBDb21wb3NhYmxlO1xufTtcblxuXG4vLyBQcm9wZXJ0aWVzIGRlZmluZWQgYnkgT2JqZWN0IHRoYXQgd2UgZG9uJ3Qgd2FudCB0byBtaXhpbi5cbmNvbnN0IE5PTl9NSVhBQkxFX09CSkVDVF9QUk9QRVJUSUVTID0gW1xuICAnY29uc3RydWN0b3InXG5dO1xuXG4vKlxuICogQXBwbHkgdGhlIG1peGluIHRvIHRoZSBnaXZlbiBiYXNlIGNsYXNzIHRvIHJldHVybiBhIG5ldyBjbGFzcy5cbiAqIFRoZSBtaXhpbiBjYW4gZWl0aGVyIGJlIGEgZnVuY3Rpb24gdGhhdCByZXR1cm5zIHRoZSBtb2RpZmllZCBjbGFzcywgb3IgYVxuICogcGxhaW4gb2JqZWN0IHdob3NlIG1lbWJlcnMgd2lsbCBiZSBjb3BpZWQgdG8gdGhlIG5ldyBjbGFzcycgcHJvdG90eXBlLlxuICovXG5mdW5jdGlvbiBjb21wb3NlQ2xhc3MoYmFzZSwgbWl4aW4pIHtcbiAgaWYgKHR5cGVvZiBtaXhpbiA9PT0gJ2Z1bmN0aW9uJykge1xuICAgIC8vIE1peGluIGZ1bmN0aW9uXG4gICAgcmV0dXJuIG1peGluKGJhc2UpO1xuICB9IGVsc2Uge1xuICAgIC8vIE1peGluIG9iamVjdFxuICAgIGNsYXNzIFN1YmNsYXNzIGV4dGVuZHMgYmFzZSB7fVxuICAgIGNvcHlPd25Qcm9wZXJ0aWVzKG1peGluLCBTdWJjbGFzcy5wcm90b3R5cGUsIE5PTl9NSVhBQkxFX09CSkVDVF9QUk9QRVJUSUVTKTtcbiAgICByZXR1cm4gU3ViY2xhc3M7XG4gIH1cbn1cblxuXG4vKlxuICogQ29weSB0aGUgZ2l2ZW4gcHJvcGVydGllcy9tZXRob2RzIHRvIHRoZSB0YXJnZXQuXG4gKiBSZXR1cm4gdGhlIHVwZGF0ZWQgdGFyZ2V0LlxuICovXG5mdW5jdGlvbiBjb3B5T3duUHJvcGVydGllcyhzb3VyY2UsIHRhcmdldCwgaWdub3JlUHJvcGVydHlOYW1lcyA9IFtdKSB7XG4gIE9iamVjdC5nZXRPd25Qcm9wZXJ0eU5hbWVzKHNvdXJjZSkuZm9yRWFjaChuYW1lID0+IHtcbiAgICBpZiAoaWdub3JlUHJvcGVydHlOYW1lcy5pbmRleE9mKG5hbWUpIDwgMCkge1xuICAgICAgY29uc3QgZGVzY3JpcHRvciA9IE9iamVjdC5nZXRPd25Qcm9wZXJ0eURlc2NyaXB0b3Ioc291cmNlLCBuYW1lKTtcbiAgICAgIE9iamVjdC5kZWZpbmVQcm9wZXJ0eSh0YXJnZXQsIG5hbWUsIGRlc2NyaXB0b3IpO1xuICAgIH1cbiAgfSk7XG4gIHJldHVybiB0YXJnZXQ7XG59XG4iLCJpbXBvcnQgY3JlYXRlU3ltYm9sIGZyb20gJy4vY3JlYXRlU3ltYm9sJztcbmltcG9ydCB0b2dnbGVDbGFzcyBmcm9tICcuL3RvZ2dsZUNsYXNzJztcbmltcG9ydCBzeW1ib2xzIGZyb20gJy4vc3ltYm9scyc7XG5cblxuLy8gU3ltYm9scyBmb3IgcHJpdmF0ZSBkYXRhIG1lbWJlcnMgb24gYW4gZWxlbWVudC5cbmNvbnN0IGl0ZW1zU3ltYm9sID0gY3JlYXRlU3ltYm9sKCdpdGVtcycpO1xuY29uc3QgaXRlbUluaXRpYWxpemVkU3ltYm9sID0gY3JlYXRlU3ltYm9sKCdpdGVtSW5pdGlhbGl6ZWQnKTtcblxuXG4vKiBFeHBvcnRlZCBmdW5jdGlvbiBleHRlbmRzIGEgYmFzZSBjbGFzcyB3aXRoIENvbnRlbnRJdGVtcy4gKi9cbmV4cG9ydCBkZWZhdWx0IChiYXNlKSA9PiB7XG5cbiAgLyoqXG4gICAqIE1peGluIHdoaWNoIG1hcHMgY29udGVudCBzZW1hbnRpY3MgKGVsZW1lbnRzKSB0byBsaXN0IGl0ZW0gc2VtYW50aWNzLlxuICAgKlxuICAgKiBJdGVtcyBkaWZmZXIgZnJvbSBlbGVtZW50IGNvbnRlbnRzIGluIHNldmVyYWwgd2F5czpcbiAgICpcbiAgICogKiBUaGV5IGFyZSBvZnRlbiByZWZlcmVuY2VkIHZpYSBpbmRleC5cbiAgICogKiBUaGV5IG1heSBoYXZlIGEgc2VsZWN0aW9uIHN0YXRlLlxuICAgKiAqIEl0J3MgY29tbW9uIHRvIGRvIHdvcmsgdG8gaW5pdGlhbGl6ZSB0aGUgYXBwZWFyYW5jZSBvciBzdGF0ZSBvZiBhIG5ld1xuICAgKiAgIGl0ZW0uXG4gICAqICogQXV4aWxpYXJ5IGludmlzaWJsZSBjaGlsZCBlbGVtZW50cyBhcmUgZmlsdGVyZWQgb3V0IGFuZCBub3QgY291bnRlZCBhc1xuICAgKiAgIGl0ZW1zLiBBdXhpbGlhcnkgZWxlbWVudHMgaW5jbHVkZSBsaW5rLCBzY3JpcHQsIHN0eWxlLCBhbmQgdGVtcGxhdGVcbiAgICogICBlbGVtZW50cy4gVGhpcyBmaWx0ZXJpbmcgZW5zdXJlcyB0aGF0IHRob3NlIGF1eGlsaWFyeSBlbGVtZW50cyBjYW4gYmVcbiAgICogICB1c2VkIGluIG1hcmt1cCBpbnNpZGUgb2YgYSBsaXN0IHdpdGhvdXQgYmVpbmcgdHJlYXRlZCBhcyBsaXN0IGl0ZW1zLlxuICAgKlxuICAgKiBUaGlzIG1peGluIGV4cGVjdHMgYSBjb21wb25lbnQgdG8gcHJvdmlkZSBhIGBjb250ZW50YCBwcm9wZXJ0eSByZXR1cm5pbmcgYVxuICAgKiByYXcgc2V0IG9mIGVsZW1lbnRzLiBZb3UgY2FuIHByb3ZpZGUgdGhhdCB5b3Vyc2VsZiwgb3IgdXNlXG4gICAqIFtEaXN0cmlidXRlZENoaWxkcmVuQ29udGVudE1peGluXShEaXN0cmlidXRlZENoaWxkcmVuQ29udGVudE1peGluLm1kKS5cbiAgICpcbiAgICogVGhlIG1vc3QgY29tbW9ubHkgcmVmZXJlbmNlZCBwcm9wZXJ0eSBkZWZpbmVkIGJ5IHRoaXMgbWl4aW4gaXMgdGhlIGBpdGVtc2BcbiAgICogcHJvcGVydHkuIFRvIGF2b2lkIGhhdmluZyB0byBkbyB3b3JrIGVhY2ggdGltZSB0aGF0IHByb3BlcnR5IGlzIHJlcXVlc3RlZCxcbiAgICogdGhpcyBtaXhpbiBzdXBwb3J0cyBhbiBvcHRpbWl6ZWQgbW9kZS4gSWYgeW91IGludm9rZSB0aGUgYGNvbnRlbnRDaGFuZ2VkYFxuICAgKiBtZXRob2Qgd2hlbiB0aGUgc2V0IG9mIGl0ZW1zIGNoYW5nZXMsIHRoZSBtaXhpbiBjb25jbHVkZXMgdGhhdCB5b3UnbGwgdGFrZVxuICAgKiBjYXJlIG9mIG5vdGlmeWluZyBpdCBvZiBmdXR1cmUgY2hhbmdlcywgYW5kIHR1cm5zIG9uIHRoZSBvcHRpbWl6YXRpb24uIFdpdGhcbiAgICogdGhhdCBvbiwgdGhlIG1peGluIHNhdmVzIGEgcmVmZXJlbmNlIHRvIHRoZSBjb21wdXRlZCBzZXQgb2YgaXRlbXMsIGFuZCB3aWxsXG4gICAqIHJldHVybiB0aGF0IGltbWVkaWF0ZWx5IG9uIHN1YnNlcXVlbnQgY2FsbHMgdG8gdGhlIGBpdGVtc2AgcHJvcGVydHkuIElmIHlvdVxuICAgKiB1c2UgdGhpcyBtaXhpbiBpbiBjb25qdW5jdGlvbiB3aXRoXG4gICAqIFtEaXN0cmlidXRlZENoaWxkcmVuQ29udGVudE1peGluXShEaXN0cmlidXRlZENoaWxkcmVuQ29udGVudE1peGluLm1kKSwgdGhlXG4gICAqIGBjb250ZW50Q2hhbmdlZGAgbWV0aG9kIHdpbGwgYmUgaW52b2tlZCBmb3IgeW91IHdoZW4gdGhlIGVsZW1lbnQncyBjaGlsZHJlblxuICAgKiBjaGFuZ2UsIHR1cm5pbmcgb24gdGhlIG9wdGltaXphdGlvbiBhdXRvbWF0aWNhbGx5LlxuICAgKi9cbiAgY2xhc3MgQ29udGVudEl0ZW1zIGV4dGVuZHMgYmFzZSB7XG5cbiAgICBjb250ZW50Q2hhbmdlZCgpIHtcbiAgICAgIGlmIChzdXBlci5jb250ZW50Q2hhbmdlZCkgeyBzdXBlci5jb250ZW50Q2hhbmdlZCgpOyB9XG5cbiAgICAgIC8vIFNpbmNlIHdlIGdvdCB0aGUgY29udGVudENoYW5nZWQgY2FsbCwgd2UnbGwgYXNzdW1lIHdlJ2xsIGJlIG5vdGlmaWVkIGlmXG4gICAgICAvLyB0aGUgc2V0IG9mIGl0ZW1zIGNoYW5nZXMgbGF0ZXIuIFdlIHR1cm4gb24gbWVtb2l6YXRpb24gb2YgdGhlIGl0ZW1zXG4gICAgICAvLyBwcm9wZXJ0eSBieSBzZXR0aW5nIG91ciBpbnRlcm5hbCBwcm9wZXJ0eSB0byBudWxsIChpbnN0ZWFkIG9mXG4gICAgICAvLyB1bmRlZmluZWQpLlxuICAgICAgdGhpc1tpdGVtc1N5bWJvbF0gPSBudWxsO1xuXG4gICAgICB0aGlzW3N5bWJvbHMuaXRlbXNDaGFuZ2VkXSgpO1xuICAgIH1cblxuICAgIC8qKlxuICAgICAqIFRoaXMgbWV0aG9kIGlzIGludm9rZWQgd2hlbmV2ZXIgYSBuZXcgaXRlbSBpcyBhZGRlZCB0byB0aGUgbGlzdC5cbiAgICAgKlxuICAgICAqIFRoZSBkZWZhdWx0IGltcGxlbWVudGF0aW9uIG9mIHRoaXMgbWV0aG9kIGRvZXMgbm90aGluZy4gWW91IGNhbiBvdmVycmlkZVxuICAgICAqIHRoaXMgdG8gcGVyZm9ybSBwZXItaXRlbSBpbml0aWFsaXphdGlvbi5cbiAgICAgKlxuICAgICAqIEBwYXJhbSB7SFRNTEVsZW1lbnR9IGl0ZW0gLSBUaGUgaXRlbSB0aGF0IHdhcyBhZGRlZC5cbiAgICAgKi9cbiAgICBbc3ltYm9scy5pdGVtQWRkZWRdKGl0ZW0pIHtcbiAgICAgIGlmIChzdXBlcltzeW1ib2xzLml0ZW1BZGRlZF0pIHsgc3VwZXJbc3ltYm9scy5pdGVtQWRkZWRdKGl0ZW0pOyB9XG4gICAgfVxuXG4gICAgLyoqXG4gICAgICogVGhlIHNlbGVjdGlvbiBzdGF0ZSBmb3IgYSBzaW5nbGUgaXRlbSBoYXMgY2hhbmdlZC5cbiAgICAgKlxuICAgICAqIEludm9rZSB0aGlzIG1ldGhvZCB0byBzaWduYWwgdGhhdCB0aGUgc2VsZWN0ZWQgc3RhdGUgb2YgdGhlIGluZGljYXRlZCBpdGVtXG4gICAgICogaGFzIGNoYW5nZWQuIEJ5IGRlZmF1bHQsIHRoaXMgYXBwbGllcyBhIGBzZWxlY3RlZGAgQ1NTIGNsYXNzIGlmIHRoZSBpdGVtXG4gICAgICogaXMgc2VsZWN0ZWQsIGFuZCByZW1vdmVkIGl0IGlmIG5vdCBzZWxlY3RlZC5cbiAgICAgKlxuICAgICAqIEBwYXJhbSB7SFRNTEVsZW1lbnR9IGl0ZW0gLSBUaGUgaXRlbSB3aG9zZSBzZWxlY3Rpb24gc3RhdGUgaGFzIGNoYW5nZWQuXG4gICAgICogQHBhcmFtIHtib29sZWFufSBzZWxlY3RlZCAtIFRydWUgaWYgdGhlIGl0ZW0gaXMgc2VsZWN0ZWQsIGZhbHNlIGlmIG5vdC5cbiAgICAgKi9cbiAgICBbc3ltYm9scy5pdGVtU2VsZWN0ZWRdKGl0ZW0sIHNlbGVjdGVkKSB7XG4gICAgICBpZiAoc3VwZXJbc3ltYm9scy5pdGVtU2VsZWN0ZWRdKSB7IHN1cGVyW3N5bWJvbHMuaXRlbVNlbGVjdGVkXShpdGVtLCBzZWxlY3RlZCk7IH1cbiAgICAgIHRvZ2dsZUNsYXNzKGl0ZW0sICdzZWxlY3RlZCcsIHNlbGVjdGVkKTtcbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBUaGUgY3VycmVudCBzZXQgb2YgaXRlbXMgaW4gdGhlIGxpc3QuIFNlZSB0aGUgdG9wLWxldmVsIGRvY3VtZW50YXRpb24gZm9yXG4gICAgICogbWl4aW4gZm9yIGEgZGVzY3JpcHRpb24gb2YgaG93IGl0ZW1zIGRpZmZlciBmcm9tIHBsYWluIGNvbnRlbnQuXG4gICAgICpcbiAgICAgKiBAdHlwZSB7SFRNTEVsZW1lbnRbXX1cbiAgICAgKi9cbiAgICBnZXQgaXRlbXMoKSB7XG4gICAgICBsZXQgaXRlbXM7XG4gICAgICBpZiAodGhpc1tpdGVtc1N5bWJvbF0gPT0gbnVsbCkge1xuICAgICAgICBpdGVtcyA9IGZpbHRlckF1eGlsaWFyeUVsZW1lbnRzKHRoaXMuY29udGVudCk7XG4gICAgICAgIC8vIE5vdGU6IHRlc3QgZm9yICplcXVhbGl0eSogd2l0aCBudWxsOyBkb24ndCB0cmVhdCB1bmRlZmluZWQgYXMgYSBtYXRjaC5cbiAgICAgICAgaWYgKHRoaXNbaXRlbXNTeW1ib2xdID09PSBudWxsKSB7XG4gICAgICAgICAgLy8gTWVtb2l6ZSB0aGUgc2V0IG9mIGl0ZW1zLlxuICAgICAgICAgIHRoaXNbaXRlbXNTeW1ib2xdID0gaXRlbXM7XG4gICAgICAgIH1cbiAgICAgIH0gZWxzZSB7XG4gICAgICAgIC8vIFJldHVybiB0aGUgbWVtb2l6ZWQgaXRlbXMuXG4gICAgICAgIGl0ZW1zID0gdGhpc1tpdGVtc1N5bWJvbF07XG4gICAgICB9XG4gICAgICByZXR1cm4gaXRlbXM7XG4gICAgfVxuXG4gICAgLyoqXG4gICAgICogVGhpcyBtZXRob2QgaXMgaW52b2tlZCB3aGVuIHRoZSB1bmRlcmx5aW5nIGNvbnRlbnRzIGNoYW5nZS4gSXQgaXMgYWxzb1xuICAgICAqIGludm9rZWQgb24gY29tcG9uZW50IGluaXRpYWxpemF0aW9uIOKAkyBzaW5jZSB0aGUgaXRlbXMgaGF2ZSBcImNoYW5nZWRcIiBmcm9tXG4gICAgICogYmVpbmcgbm90aGluZy5cbiAgICAgKi9cbiAgICBbc3ltYm9scy5pdGVtc0NoYW5nZWRdKCkge1xuICAgICAgaWYgKHN1cGVyW3N5bWJvbHMuaXRlbXNDaGFuZ2VkXSkgeyBzdXBlcltzeW1ib2xzLml0ZW1zQ2hhbmdlZF0oKTsgfVxuXG4gICAgICAvLyBQZXJmb3JtIHBlci1pdGVtIGluaXRpYWxpemF0aW9uLlxuICAgICAgQXJyYXkucHJvdG90eXBlLmZvckVhY2guY2FsbCh0aGlzLml0ZW1zLCBpdGVtID0+IHtcbiAgICAgICAgaWYgKCFpdGVtW2l0ZW1Jbml0aWFsaXplZFN5bWJvbF0pIHtcbiAgICAgICAgICB0aGlzW3N5bWJvbHMuaXRlbUFkZGVkXShpdGVtKTtcbiAgICAgICAgICBpdGVtW2l0ZW1Jbml0aWFsaXplZFN5bWJvbF0gPSB0cnVlO1xuICAgICAgICB9XG4gICAgICB9KTtcblxuICAgICAgdGhpcy5kaXNwYXRjaEV2ZW50KG5ldyBDdXN0b21FdmVudCgnaXRlbXMtY2hhbmdlZCcpKTtcbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBGaXJlcyB3aGVuIHRoZSBpdGVtcyBpbiB0aGUgbGlzdCBjaGFuZ2UuXG4gICAgICpcbiAgICAgKiBAbWVtYmVyb2YgQ29udGVudEl0ZW1zXG4gICAgICogQGV2ZW50IGl0ZW1zLWNoYW5nZWRcbiAgICAgKi9cbiAgfVxuXG4gIHJldHVybiBDb250ZW50SXRlbXM7XG59O1xuXG5cbi8vIFJldHVybiB0aGUgZ2l2ZW4gZWxlbWVudHMsIGZpbHRlcmluZyBvdXQgYXV4aWxpYXJ5IGVsZW1lbnRzIHRoYXQgYXJlbid0XG4vLyB0eXBpY2FsbHkgdmlzaWJsZS4gSXRlbXMgd2hpY2ggYXJlIG5vdCBlbGVtZW50cyBhcmUgcmV0dXJuZWQgYXMgaXMuXG5mdW5jdGlvbiBmaWx0ZXJBdXhpbGlhcnlFbGVtZW50cyhpdGVtcykge1xuICBjb25zdCBhdXhpbGlhcnlUYWdzID0gW1xuICAgICdsaW5rJyxcbiAgICAnc2NyaXB0JyxcbiAgICAnc3R5bGUnLFxuICAgICd0ZW1wbGF0ZSdcbiAgXTtcbiAgcmV0dXJuIFtdLmZpbHRlci5jYWxsKGl0ZW1zLCBmdW5jdGlvbihpdGVtKSB7XG4gICAgcmV0dXJuICFpdGVtLmxvY2FsTmFtZSB8fCBhdXhpbGlhcnlUYWdzLmluZGV4T2YoaXRlbS5sb2NhbE5hbWUpIDwgMDtcbiAgfSk7XG59XG4iLCJpbXBvcnQgbWljcm90YXNrIGZyb20gJy4vbWljcm90YXNrJztcblxuXG4vKiBFeHBvcnRlZCBmdW5jdGlvbiBleHRlbmRzIGEgYmFzZSBjbGFzcyB3aXRoIERpc3RyaWJ1dGVkQ2hpbGRyZW5Db250ZW50LiAqL1xuZXhwb3J0IGRlZmF1bHQgKGJhc2UpID0+IHtcblxuICAvKipcbiAgICogTWl4aW4gd2hpY2ggZGVmaW5lcyBhIGNvbXBvbmVudCdzIGNvbnRlbnQgYXMgaXRzIGNoaWxkcmVuLCBleHBhbmRpbmcgYW55XG4gICAqIG5vZGVzIGRpc3RyaWJ1dGVkIHRvIHRoZSBjb21wb25lbnQncyBzbG90cy5cbiAgICpcbiAgICogVGhpcyBhbHNvIHByb3ZpZGVzIG5vdGlmaWNhdGlvbiBvZiBjaGFuZ2VzIHRvIGEgY29tcG9uZW50J3MgY29udGVudC4gSXRcbiAgICogd2lsbCBpbnZva2UgYSBgY29udGVudENoYW5nZWRgIG1ldGhvZCB3aGVuIHRoZSBjb21wb25lbnQgaXMgZmlyc3RcbiAgICogaW5zdGFudGlhdGVkLCBhbmQgd2hlbmV2ZXIgaXRzIGRpc3RyaWJ1dGVkIGNoaWxkcmVuIGNoYW5nZS4gVGhpcyBpcyBhblxuICAgKiBlYXN5IHdheSB0byBzYXRpc2Z5IHRoZSBHb2xkIFN0YW5kYXJkIGNoZWNrbGlzdCBpdGVtIGZvciBtb25pdG9yaW5nXG4gICAqIFtDb250ZW50IENoYW5nZXNdKGh0dHBzOi8vZ2l0aHViLmNvbS93ZWJjb21wb25lbnRzL2dvbGQtc3RhbmRhcmQvd2lraS9Db250ZW50LUNoYW5nZXMpLlxuICAgKlxuICAgKiBFeGFtcGxlOlxuICAgKlxuICAgKiBgYGBcbiAgICogbGV0IGJhc2UgPSBEaXN0cmlidXRlZENoaWxkcmVuQ29udGVudE1peGluKERpc3RyaWJ1dGVkQ2hpbGRyZW5NaXhpbihIVE1MRWxlbWVudCkpO1xuICAgKiBjbGFzcyBDb3VudGluZ0VsZW1lbnQgZXh0ZW5kcyBiYXNlIHtcbiAgICpcbiAgICogICBjb25zdHJ1Y3RvcigpIHtcbiAgICogICAgIHN1cGVyKCk7XG4gICAqICAgICBsZXQgcm9vdCA9IHRoaXMuYXR0YWNoU2hhZG93KHsgbW9kZTogJ29wZW4nIH0pO1xuICAgKiAgICAgcm9vdC5pbm5lckhUTUwgPSBgPHNsb3Q+PC9zbG90PmA7XG4gICAqICAgfVxuICAgKlxuICAgKiAgIGNvbnRlbnRDaGFuZ2VkKCkge1xuICAgKiAgICAgLy8gQ291bnQgdGhlIGNvbXBvbmVudCdzIGNoaWxkcmVuLCBib3RoIGluaXRpYWxseSBhbmQgd2hlbiBjaGFuZ2VkLlxuICAgKiAgICAgdGhpcy5jb3VudCA9IHRoaXMuZGlzdHJpYnV0ZWRDaGlsZHJlbi5sZW5ndGg7XG4gICAqICAgfVxuICAgKlxuICAgKiB9XG4gICAqIGBgYFxuICAgKlxuICAgKiBOb3RlIHRoYXQgY29udGVudCBjaGFuZ2UgZGV0ZWN0aW9uIGRlcGVuZHMgdXBvbiB0aGUgZWxlbWVudCBoYXZpbmcgYXQgbGVhc3RcbiAgICogb25lIGBzbG90YCBlbGVtZW50IGluIGl0cyBzaGFkb3cgc3VidHJlZS5cbiAgICpcbiAgICogVGhpcyBtaXhpbiBpcyBpbnRlbmRlZCBmb3IgdXNlIHdpdGggdGhlXG4gICAqIFtEaXN0cmlidXRlZENoaWxkcmVuTWl4aW5dKERpc3RyaWJ1dGVkQ2hpbGRyZW5NaXhpbi5tZCkuIFNlZSB0aGF0IG1peGluIGZvclxuICAgKiBhIGRpc2N1c3Npb24gb2YgaG93IHRoYXQgd29ya3MuIFRoaXMgRGlzdHJpYnV0ZWRDaGlsZHJlbkNvbnRlbnRNaXhpblxuICAgKiBwcm92aWRlcyBhbiBlYXN5IHdheSBvZiBkZWZpbmluZyB0aGUgXCJjb250ZW50XCIgb2YgYSBjb21wb25lbnQgYXMgdGhlXG4gICAqIGNvbXBvbmVudCdzIGRpc3RyaWJ1dGVkIGNoaWxkcmVuLiBUaGF0IGluIHR1cm4gbGV0cyBtaXhpbnMgbGlrZVxuICAgKiBbQ29udGVudEl0ZW1zTWl4aW5dKENvbnRlbnRJdGVtc01peGluLm1kKSBtYW5pcHVsYXRlIHRoZSBjaGlsZHJlbiBhcyBsaXN0XG4gICAqIGl0ZW1zLlxuICAgKi9cbiAgY2xhc3MgRGlzdHJpYnV0ZWRDaGlsZHJlbkNvbnRlbnQgZXh0ZW5kcyBiYXNlIHtcblxuICAgIGNvbnN0cnVjdG9yKCkge1xuICAgICAgc3VwZXIoKTtcblxuICAgICAgaWYgKHRoaXMuc2hhZG93Um9vdCkge1xuICAgICAgICAvLyBMaXN0ZW4gdG8gY2hhbmdlcyBvbiBhbGwgc2xvdHMuXG4gICAgICAgIGNvbnN0IHNsb3RzID0gdGhpcy5zaGFkb3dSb290LnF1ZXJ5U2VsZWN0b3JBbGwoJ3Nsb3QnKTtcbiAgICAgICAgc2xvdHMuZm9yRWFjaChzbG90ID0+IHNsb3QuYWRkRXZlbnRMaXN0ZW5lcignc2xvdGNoYW5nZScsIGV2ZW50ID0+IHtcbiAgICAgICAgICB0aGlzLmNvbnRlbnRDaGFuZ2VkKCk7XG4gICAgICAgIH0pKTtcbiAgICAgIH1cblxuICAgICAgLy8gTWFrZSBhbiBpbml0aWFsIGNhbGwgdG8gY29udGVudENoYW5nZWQoKSBzbyB0aGF0IHRoZSBjb21wb25lbnQgY2FuIGRvXG4gICAgICAvLyBpbml0aWFsaXphdGlvbiB0aGF0IGl0IG5vcm1hbGx5IGRvZXMgd2hlbiBjb250ZW50IGNoYW5nZXMuXG4gICAgICAvL1xuICAgICAgLy8gVGhpcyB3aWxsIGludm9rZSBjb250ZW50Q2hhbmdlZCgpIGhhbmRsZXJzIGluIG90aGVyIG1peGlucy4gSW4gb3JkZXJcbiAgICAgIC8vIHRoYXQgdGhvc2UgbWl4aW5zIGhhdmUgYSBjaGFuY2UgdG8gY29tcGxldGUgdGhlaXIgb3duIGluaXRpYWxpemF0aW9uLFxuICAgICAgLy8gd2UgYWRkIHRoZSBjb250ZW50Q2hhbmdlZCgpIGNhbGwgdG8gdGhlIG1pY3JvdGFzayBxdWV1ZS5cbiAgICAgIG1pY3JvdGFzaygoKSA9PiB0aGlzLmNvbnRlbnRDaGFuZ2VkKCkpO1xuICAgIH1cblxuICAgIC8qKlxuICAgICAqIEludm9rZWQgd2hlbiB0aGUgY29udGVudHMgb2YgdGhlIGNvbXBvbmVudCAoaW5jbHVkaW5nIGRpc3RyaWJ1dGVkXG4gICAgICogY2hpbGRyZW4pIGhhdmUgY2hhbmdlZC5cbiAgICAgKlxuICAgICAqIFRoaXMgbWV0aG9kIGlzIGFsc28gaW52b2tlZCB3aGVuIGEgY29tcG9uZW50IGlzIGZpcnN0IGluc3RhbnRpYXRlZDsgdGhlXG4gICAgICogY29udGVudHMgaGF2ZSBlc3NlbnRpYWxseSBcImNoYW5nZWRcIiBmcm9tIGJlaW5nIG5vdGhpbmcuIFRoaXMgYWxsb3dzIHRoZVxuICAgICAqIGNvbXBvbmVudCB0byBwZXJmb3JtIGluaXRpYWwgcHJvY2Vzc2luZyBvZiBpdHMgY2hpbGRyZW4uXG4gICAgICovXG4gICAgY29udGVudENoYW5nZWQoKSB7XG4gICAgICBpZiAoc3VwZXIuY29udGVudENoYW5nZWQpIHsgc3VwZXIuY29udGVudENoYW5nZWQoKTsgfVxuICAgICAgY29uc3QgZXZlbnQgPSBuZXcgQ3VzdG9tRXZlbnQoJ2NvbnRlbnQtY2hhbmdlZCcpO1xuICAgICAgdGhpcy5kaXNwYXRjaEV2ZW50KGV2ZW50KTtcbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBUaGUgY29udGVudCBvZiB0aGlzIGNvbXBvbmVudCwgZGVmaW5lZCB0byBiZSB0aGUgZmxhdHRlbmVkIGFycmF5IG9mXG4gICAgICogY2hpbGRyZW4gZGlzdHJpYnV0ZWQgdG8gdGhlIGNvbXBvbmVudC5cbiAgICAgKlxuICAgICAqIEB0eXBlIHtIVE1MRWxlbWVudFtdfVxuICAgICAqL1xuICAgIGdldCBjb250ZW50KCkge1xuICAgICAgY29uc3QgZGlzdHJpYnV0ZWRDaGlsZHJlbiA9IHRoaXMuZGlzdHJpYnV0ZWRDaGlsZHJlbjtcbiAgICAgIGlmICh0eXBlb2YgZGlzdHJpYnV0ZWRDaGlsZHJlbiA9PT0gJ3VuZGVmaW5lZCcpIHtcbiAgICAgICAgY29uc29sZS53YXJuKGBEaXN0cmlidXRlZENoaWxkcmVuQ29udGVudE1peGluIGV4cGVjdHMgdGhlIGNvbXBvbmVudCB0byBkZWZpbmUgYSBcImRpc3RyaWJ1dGVkQ2hpbGRyZW5cIiBwcm9wZXJ0eS5gKTtcbiAgICAgIH1cbiAgICAgIHJldHVybiBkaXN0cmlidXRlZENoaWxkcmVuO1xuICAgIH1cbiAgICBzZXQgY29udGVudCh2YWx1ZSkge1xuICAgICAgaWYgKCdjb250ZW50JyBpbiBiYXNlLnByb3RvdHlwZSkgeyBzdXBlci5jb250ZW50ID0gdmFsdWU7IH1cbiAgICAgIC8vIFRPRE86IFNldCB0aGUgY2hpbGRyZW4gdG8gdGhlIGdpdmVuIHZhbHVlICh3aGljaCBzaG91bGQgYmUgYW4gYXJyYXkgb2ZcbiAgICAgIC8vIGVsZW1lbnRzKT9cbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBUaGlzIGV2ZW50IGlzIHJhaXNlZCB3aGVuIHRoZSBjb21wb25lbnQncyBjb250ZW50cyAoaW5jbHVkaW5nIGRpc3RyaWJ1dGVkXG4gICAgICogY2hpbGRyZW4pIGhhdmUgY2hhbmdlZC5cbiAgICAgKlxuICAgICAqIEBtZW1iZXJvZiBEaXN0cmlidXRlZENoaWxkcmVuQ29udGVudFxuICAgICAqIEBldmVudCBjb250ZW50LWNoYW5nZWRcbiAgICAgKi9cbiAgfVxuXG4gIHJldHVybiBEaXN0cmlidXRlZENoaWxkcmVuQ29udGVudDtcbn07XG4iLCIvKiBFeHBvcnRlZCBmdW5jdGlvbiBleHRlbmRzIGEgYmFzZSBjbGFzcyB3aXRoIERpc3RyaWJ1dGVkQ2hpbGRyZW4uICovXG5leHBvcnQgZGVmYXVsdCAoYmFzZSkgPT4ge1xuXG4gIC8qKlxuICAgKiBNaXhpbiB3aGljaCBkZWZpbmVzIGhlbHBlcnMgZm9yIGFjY2Vzc2luZyBhIGNvbXBvbmVudCdzIGRpc3RyaWJ1dGVkXG4gICAqIGNoaWxkcmVuIGFzIGEgZmxhdHRlbmVkIGFycmF5IG9yIHN0cmluZy5cbiAgICpcbiAgICogVGhlIHN0YW5kYXJkIERPTSBBUEkgcHJvdmlkZXMgc2V2ZXJhbCB3YXlzIG9mIGFjY2Vzc2luZyBjaGlsZCBjb250ZW50OlxuICAgKiBgY2hpbGRyZW5gLCBgY2hpbGROb2Rlc2AsIGFuZCBgdGV4dENvbnRlbnRgLiBOb25lIG9mIHRoZXNlIGZ1bmN0aW9ucyBhcmVcbiAgICogU2hhZG93IERPTSBhd2FyZS4gVGhpcyBtaXhpbiBkZWZpbmVzIHZhcmlhdGlvbnMgb2YgdGhvc2UgZnVuY3Rpb25zIHRoYXRcbiAgICogKmFyZSogU2hhZG93IERPTSBhd2FyZS5cbiAgICpcbiAgICogRXhhbXBsZTogeW91IGNyZWF0ZSBhIGNvbXBvbmVudCBgPGNvdW50LWNoaWxkcmVuPmAgdGhhdCBkaXNwbGF5cyBhIG51bWJlclxuICAgKiBlcXVhbCB0byB0aGUgbnVtYmVyIG9mIGNoaWxkcmVuIHBsYWNlZCBpbnNpZGUgdGhhdCBjb21wb25lbnQuIElmIHNvbWVvbmVcbiAgICogaW5zdGFudGlhdGVzIHlvdXIgY29tcG9uZW50IGxpa2U6XG4gICAqXG4gICAqICAgICA8Y291bnQtY2hpbGRyZW4+XG4gICAqICAgICAgIDxkaXY+PC9kaXY+XG4gICAqICAgICAgIDxkaXY+PC9kaXY+XG4gICAqICAgICAgIDxkaXY+PC9kaXY+XG4gICAqICAgICA8L2NvdW50LWNoaWxkcmVuPlxuICAgKlxuICAgKiBUaGVuIHRoZSBjb21wb25lbnQgc2hvdWxkIHNob3cgXCIzXCIsIGJlY2F1c2UgdGhlcmUgYXJlIHRocmVlIGNoaWxkcmVuLiBUb1xuICAgKiBjYWxjdWxhdGUgdGhlIG51bWJlciBvZiBjaGlsZHJlbiwgdGhlIGNvbXBvbmVudCBjYW4ganVzdCBjYWxjdWxhdGVcbiAgICogYHRoaXMuY2hpbGRyZW4ubGVuZ3RoYC4gSG93ZXZlciwgc3VwcG9zZSBzb21lb25lIGluc3RhbnRpYXRlcyB5b3VyXG4gICAqIGNvbXBvbmVudCBpbnNpZGUgb25lIG9mIHRoZWlyIG93biBjb21wb25lbnRzLCBhbmQgcHV0cyBhIGA8c2xvdD5gIGVsZW1lbnRcbiAgICogaW5zaWRlIHlvdXIgY29tcG9uZW50OlxuICAgKlxuICAgKiAgICAgPGNvdW50LWNoaWxkcmVuPlxuICAgKiAgICAgICA8c2xvdD48L3Nsb3Q+XG4gICAqICAgICA8L2NvdW50LWNoaWxkcmVuPlxuICAgKlxuICAgKiBJZiB5b3VyIGNvbXBvbmVudCBvbmx5IGxvb2tzIGF0IGB0aGlzLmNoaWxkcmVuYCwgaXQgd2lsbCBhbHdheXMgc2VlIGV4YWN0bHlcbiAgICogb25lIGNoaWxkIOKAlMKgdGhlIGA8c2xvdD5gIGVsZW1lbnQuIEJ1dCB0aGUgdXNlciBsb29raW5nIGF0IHRoZSBwYWdlIHdpbGxcbiAgICogKnNlZSogYW55IG5vZGVzIGRpc3RyaWJ1dGVkIHRvIHRoYXQgc2xvdC4gVG8gbWF0Y2ggd2hhdCB0aGUgdXNlciBzZWVzLCB5b3VyXG4gICAqIGNvbXBvbmVudCBzaG91bGQgZXhwYW5kIGFueSBgPHNsb3Q+YCBlbGVtZW50cyBpdCBjb250YWlucy5cbiAgICpcbiAgICogVGhhdCBpcyB0aGUgcHJvYmxlbSB0aGlzIG1peGluIHNvbHZlcy4gQWZ0ZXIgYXBwbHlpbmcgdGhpcyBtaXhpbiwgeW91clxuICAgKiBjb21wb25lbnQgY29kZSBoYXMgYWNjZXNzIHRvIGB0aGlzLmRpc3RyaWJ1dGVkQ2hpbGRyZW5gLCB3aG9zZSBgbGVuZ3RoYFxuICAgKiB3aWxsIHJldHVybiB0aGUgdG90YWwgbnVtYmVyIG9mIGFsbCBjaGlsZHJlbiBkaXN0cmlidXRlZCB0byB5b3VyIGNvbXBvbmVudFxuICAgKiBpbiB0aGUgY29tcG9zZWQgdHJlZS5cbiAgICpcbiAgICogTm90ZTogVGhlIGxhdGVzdCBDdXN0b20gRWxlbWVudHMgQVBJIGRlc2lnbiBjYWxscyBmb3IgYSBuZXcgZnVuY3Rpb24sXG4gICAqIGBnZXRBc3NpZ25lZE5vZGVzYCB0aGF0IHRha2VzIGFuIG9wdGlvbmFsIGBkZWVwYCBwYXJhbWV0ZXIsIHRoYXQgd2lsbCBzb2x2ZVxuICAgKiB0aGlzIHByb2JsZW0gYXQgdGhlIEFQSSBsZXZlbC5cbiAgICovXG4gIGNsYXNzIERpc3RyaWJ1dGVkQ2hpbGRyZW4gZXh0ZW5kcyBiYXNlIHtcblxuICAgIC8qKlxuICAgICAqIEFuIGluLW9yZGVyIGNvbGxlY3Rpb24gb2YgZGlzdHJpYnV0ZWQgY2hpbGRyZW4sIGV4cGFuZGluZyBhbnkgc2xvdFxuICAgICAqIGVsZW1lbnRzLiBMaWtlIHRoZSBzdGFuZGFyZCBjaGlsZHJlbiBwcm9wZXJ0eSwgdGhpcyBza2lwcyB0ZXh0IG5vZGVzLlxuICAgICAqXG4gICAgICogQHR5cGUge0hUTUxFbGVtZW50W119XG4gICAgICovXG4gICAgZ2V0IGRpc3RyaWJ1dGVkQ2hpbGRyZW4oKSB7XG4gICAgICByZXR1cm4gZXhwYW5kQ29udGVudEVsZW1lbnRzKHRoaXMuY2hpbGRyZW4sIGZhbHNlKTtcbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBBbiBpbi1vcmRlciBjb2xsZWN0aW9uIG9mIGRpc3RyaWJ1dGVkIGNoaWxkIG5vZGVzLCBleHBhbmRpbmcgYW55IHNsb3RcbiAgICAgKiBlbGVtZW50cy4gTGlrZSB0aGUgc3RhbmRhcmQgY2hpbGROb2RlcyBwcm9wZXJ0eSwgdGhpcyBpbmNsdWRlcyB0ZXh0XG4gICAgICogbm9kZXMuXG4gICAgICpcbiAgICAgKiBAdHlwZSB7Tm9kZVtdfVxuICAgICAqL1xuICAgIGdldCBkaXN0cmlidXRlZENoaWxkTm9kZXMoKSB7XG4gICAgICByZXR1cm4gZXhwYW5kQ29udGVudEVsZW1lbnRzKHRoaXMuY2hpbGROb2RlcywgdHJ1ZSk7XG4gICAgfVxuXG4gICAgLyoqXG4gICAgICogVGhlIGNvbmNhdGVuYXRlZCB0ZXh0IGNvbnRlbnQgb2YgYWxsIGRpc3RyaWJ1dGVkIGNoaWxkIG5vZGVzLCBleHBhbmRpbmdcbiAgICAgKiBhbnkgc2xvdCBlbGVtZW50cy5cbiAgICAgKlxuICAgICAqIEB0eXBlIHtzdHJpbmd9XG4gICAgICovXG4gICAgZ2V0IGRpc3RyaWJ1dGVkVGV4dENvbnRlbnQoKSB7XG4gICAgICBjb25zdCBzdHJpbmdzID0gdGhpcy5kaXN0cmlidXRlZENoaWxkTm9kZXMubWFwKGZ1bmN0aW9uKGNoaWxkKSB7XG4gICAgICAgIHJldHVybiBjaGlsZC50ZXh0Q29udGVudDtcbiAgICAgIH0pO1xuICAgICAgcmV0dXJuIHN0cmluZ3Muam9pbignJyk7XG4gICAgfVxuXG4gIH1cblxuICByZXR1cm4gRGlzdHJpYnV0ZWRDaGlsZHJlbjtcbn07XG5cblxuLypcbiAqIEdpdmVuIGEgYXJyYXkgb2Ygbm9kZXMsIHJldHVybiBhIG5ldyBhcnJheSB3aXRoIGFueSBjb250ZW50IGVsZW1lbnRzIGV4cGFuZGVkXG4gKiB0byB0aGUgbm9kZXMgZGlzdHJpYnV0ZWQgdG8gdGhhdCBjb250ZW50IGVsZW1lbnQuIFRoaXMgcnVsZSBpcyBhcHBsaWVkXG4gKiByZWN1cnNpdmVseS5cbiAqXG4gKiBJZiBpbmNsdWRlVGV4dE5vZGVzIGlzIHRydWUsIHRleHQgbm9kZXMgd2lsbCBiZSBpbmNsdWRlZCwgYXMgaW4gdGhlXG4gKiBzdGFuZGFyZCBjaGlsZE5vZGVzIHByb3BlcnR5OyBieSBkZWZhdWx0LCB0aGlzIHNraXBzIHRleHQgbm9kZXMsIGxpa2UgdGhlXG4gKiBzdGFuZGFyZCBjaGlsZHJlbiBwcm9wZXJ0eS5cbiAqL1xuZnVuY3Rpb24gZXhwYW5kQ29udGVudEVsZW1lbnRzKG5vZGVzLCBpbmNsdWRlVGV4dE5vZGVzKSB7XG4gIGNvbnN0IGV4cGFuZGVkID0gQXJyYXkucHJvdG90eXBlLm1hcC5jYWxsKG5vZGVzLCBub2RlID0+IHtcbiAgICAvLyBXZSB3YW50IHRvIHNlZSBpZiB0aGUgbm9kZSBpcyBhbiBpbnN0YW5jZW9mIEhUTUxTbG90RUxlbWVudCwgYnV0XG4gICAgLy8gdGhhdCBjbGFzcyB3b24ndCBleGlzdCBpZiB0aGUgYnJvd3NlciB0aGF0IGRvZXNuJ3Qgc3VwcG9ydCBuYXRpdmVcbiAgICAvLyBTaGFkb3cgRE9NIGFuZCBpZiB0aGUgU2hhZG93IERPTSBwb2x5ZmlsbCBoYXNuJ3QgYmVlbiBsb2FkZWQuIEluc3RlYWQsXG4gICAgLy8gd2UgZG8gYSBzaW1wbGlzdGljIGNoZWNrIHRvIHNlZSBpZiB0aGUgdGFnIG5hbWUgaXMgXCJzbG90XCIuXG4gICAgY29uc3QgaXNTbG90ID0gdHlwZW9mIEhUTUxTbG90RWxlbWVudCAhPT0gJ3VuZGVmaW5lZCcgP1xuICAgICAgbm9kZSBpbnN0YW5jZW9mIEhUTUxTbG90RWxlbWVudCA6XG4gICAgICBub2RlLmxvY2FsTmFtZSA9PT0gJ3Nsb3QnO1xuICAgIGlmIChpc1Nsb3QpIHtcbiAgICAgIC8vIFVzZSB0aGUgbm9kZXMgYXNzaWduZWQgdG8gdGhpcyBub2RlIGluc3RlYWQuXG4gICAgICBjb25zdCBhc3NpZ25lZE5vZGVzID0gbm9kZS5hc3NpZ25lZE5vZGVzKHsgZmxhdHRlbjogdHJ1ZSB9KTtcbiAgICAgIHJldHVybiBhc3NpZ25lZE5vZGVzID9cbiAgICAgICAgZXhwYW5kQ29udGVudEVsZW1lbnRzKGFzc2lnbmVkTm9kZXMsIGluY2x1ZGVUZXh0Tm9kZXMpIDpcbiAgICAgICAgW107XG4gICAgfSBlbHNlIGlmIChub2RlIGluc3RhbmNlb2YgSFRNTEVsZW1lbnQpIHtcbiAgICAgIC8vIFBsYWluIGVsZW1lbnQ7IHVzZSBhcyBpcy5cbiAgICAgIHJldHVybiBbbm9kZV07XG4gICAgfSBlbHNlIGlmIChub2RlIGluc3RhbmNlb2YgVGV4dCAmJiBpbmNsdWRlVGV4dE5vZGVzKSB7XG4gICAgICAvLyBUZXh0IG5vZGUuXG4gICAgICByZXR1cm4gW25vZGVdO1xuICAgIH0gZWxzZSB7XG4gICAgICAvLyBDb21tZW50LCBwcm9jZXNzaW5nIGluc3RydWN0aW9uLCBldGMuOyBza2lwLlxuICAgICAgcmV0dXJuIFtdO1xuICAgIH1cbiAgfSk7XG4gIGNvbnN0IGZsYXR0ZW5lZCA9IFtdLmNvbmNhdCguLi5leHBhbmRlZCk7XG4gIHJldHVybiBmbGF0dGVuZWQ7XG59XG4iLCJpbXBvcnQgY3JlYXRlU3ltYm9sIGZyb20gJy4vY3JlYXRlU3ltYm9sJztcblxuXG4vLyBTeW1ib2xzIGZvciBwcml2YXRlIGRhdGEgbWVtYmVycyBvbiBhbiBlbGVtZW50LlxuY29uc3Qgc2VsZWN0ZWRGcmFjdGlvblN5bWJvbCA9IGNyZWF0ZVN5bWJvbCgnc2VsZWN0ZWRGcmFjdGlvbicpO1xuXG5cbi8qIEV4cG9ydGVkIGZ1bmN0aW9uIGV4dGVuZHMgYSBiYXNlIGNsYXNzIHdpdGggRnJhY3Rpb25hbFNlbGVjdGlvbi4gKi9cbmV4cG9ydCBkZWZhdWx0IGZ1bmN0aW9uIG1peGluKGJhc2UpIHtcblxuICAvKipcbiAgICogQWRkcyBzdXBwb3J0IGZvciBmcmFjdGlvbmFsIHNlbGVjdGlvbjogdHJlYXRpbmcgYSBzZWxlY3Rpb24gYXMgYSByZWFsXG4gICAqIG51bWJlciB0aGF0IGNvbWJpbmVzIGFuIGludGVnZXIgcG9ydGlvbiAoYW4gaW5kZXggaW50byBhIGxpc3QpLCBhbmQgYVxuICAgKiBmcmFjdGlvbiAoaW5kaWNhdGluZyBob3cgZmFyIG9mIHRoZSB3YXkgd2UgYXJlIHRvIHRoZSBuZXh0IG9yIHByZXZpb3VzXG4gICAqIGl0ZW0pLlxuICAgKlxuICAgKiBUaGlzIGlzIHVzZWZ1bCBpbiBjb21wb25lbnRzIHRoYXQgc3VwcG9ydCBpbmNyZW1lbnRhbCBvcGVyYXRpb25zIGR1cmluZ1xuICAgKiBkcmFnZ2luZyBhbmQgc3dpcGluZy4gRXhhbXBsZTogYSBjYXJvdXNlbCBjb21wb25lbnQgaGFzIHNldmVyYWwgaXRlbXMsIGFuZCB0aGVcbiAgICogY3VycmVudGx5IHNlbGVjdGVkIGl0ZW0gaXMgaXRlbSAzLiBUaGUgdXNlciBiZWdpbnMgc3dpcGluZyB0byB0aGUgbGVmdCxcbiAgICogbW92aW5nIHRvd2FyZHMgc2VsZWN0aW5nIGl0ZW0gNC4gSGFsZndheSB0aHJvdWdoIHRoaXMgb3BlcmF0aW9uLCB0aGVcbiAgICogZnJhY3Rpb25hbCBzZWxlY3Rpb24gdmFsdWUgaXMgMy41LlxuICAgKlxuICAgKiBUaGlzIHZhbHVlIHBlcm1pdHMgY29tbXVuaWNhdGlvbiBiZXR3ZWVuIG1peGlucyBsaWtlXG4gICAqIFtTd2lwZURpcmVjdGlvbk1peGluXSguL1N3aXBlRGlyZWN0aW9uTWl4aW4ubWQpIGFuZFxuICAgKiBbVHJhY2twYWREaXJlY3Rpb25NaXhpbl0oLi9UcmFja3BhZERpcmVjdGlvbk1peGluLm1kKSwgd2hpY2ggZ2VuZXJhdGVcbiAgICogZnJhY3Rpb25hbCBzZWxlY3Rpb24gdmFsdWVzLCBhbmQgbWl4aW5zIGxpa2VcbiAgICogW1NlbGVjdGlvbkFuaW1hdGlvbk1peGluXSguL1NlbGVjdGlvbkFuaW1hdGlvbk1peGluLm1kKSwgd2hpY2ggY2FuIHJlbmRlclxuICAgKiBzZWxlY3Rpb24gYXQgYSBmcmFjdGlvbmFsIHZhbHVlLlxuICAgKi9cbiAgY2xhc3MgRnJhY3Rpb25hbFNlbGVjdGlvbiBleHRlbmRzIGJhc2Uge1xuXG4gICAgY29ubmVjdGVkQ2FsbGJhY2soKSB7XG4gICAgICBpZiAoc3VwZXIuY29ubmVjdGVkQ2FsbGJhY2spIHsgc3VwZXIuY29ubmVjdGVkQ2FsbGJhY2soKTsgfVxuICAgICAgdGhpcy5zZWxlY3RlZEZyYWN0aW9uID0gMDtcbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBBIGZyYWN0aW9uYWwgdmFsdWUgaW5kaWNhdGluZyBob3cgZmFyIHRoZSB1c2VyIGhhcyBjdXJyZW50bHkgYWR2YW5jZWQgdG9cbiAgICAgKiB0aGUgbmV4dC9wcmV2aW91cyBpdGVtLiBFLmcuLCBhIGBzZWxlY3RlZEZyYWN0aW9uYCBvZiAzLjUgaW5kaWNhdGVzIHRoZVxuICAgICAqIHVzZXIgaXMgaGFsZndheSBiZXR3ZWVuIGl0ZW1zIDMgYW5kIDQuXG4gICAgICpcbiAgICAgKiBAdHlwZSB7bnVtYmVyfVxuICAgICAqL1xuICAgIGdldCBzZWxlY3RlZEZyYWN0aW9uKCkge1xuICAgICAgcmV0dXJuIHRoaXNbc2VsZWN0ZWRGcmFjdGlvblN5bWJvbF07XG4gICAgfVxuICAgIHNldCBzZWxlY3RlZEZyYWN0aW9uKHZhbHVlKSB7XG4gICAgICB0aGlzW3NlbGVjdGVkRnJhY3Rpb25TeW1ib2xdID0gdmFsdWU7XG4gICAgICBpZiAoJ3NlbGVjdGVkRnJhY3Rpb24nIGluIGJhc2UucHJvdG90eXBlKSB7IHN1cGVyLnNlbGVjdGVkRnJhY3Rpb24gPSB2YWx1ZTsgfVxuICAgICAgY29uc3QgZXZlbnQgPSBuZXcgQ3VzdG9tRXZlbnQoJ3NlbGVjdGVkLWZyYWN0aW9uLWNoYW5nZWQnKTtcbiAgICAgIHRoaXMuZGlzcGF0Y2hFdmVudChldmVudCk7XG4gICAgfVxuXG4gIH1cblxuICByZXR1cm4gRnJhY3Rpb25hbFNlbGVjdGlvbjtcbn1cblxuXG5taXhpbi5oZWxwZXJzID0ge1xuXG4gIC8qXG4gICAqIERhbXBlbiBhIHNlbGVjdGlvbiB0aGF0IGdvZXMgcGFzdCB0aGUgYmVnaW5uaW5nIG9yIGVuZCBvZiBhIGxpc3QuIFRoaXMgaXNcbiAgICogZ2VuZXJhbGx5IHVzZWQgdG8gcHJvZHVjZSBhIHZpc3VhbCBlZmZlY3Qgb2YgdGVuc2lvbiBhcyB0aGUgdXNlciB0cmllcyB0b1xuICAgKiBnbyBmdXJ0aGVyIGluIGEgZGlyZWN0aW9uIHRoYXQgaGFzIG5vIG1vcmUgaXRlbXMuXG4gICAqXG4gICAqIEV4YW1wbGU6IHN1cHBvc2UgYGl0ZW1Db3VudGAgaXMgNSwgaW5kaWNhdGluZyBhIGxpc3Qgb2YgNSBpdGVtcy4gVGhlIGluZGV4IG9mXG4gICAqIHRoZSBsYXN0IGl0ZW0gaXMgNC4gSWYgdGhlIGBzZWxlY3Rpb25gIHBhcmFtZXRlciBpcyA0LjUsIHRoZSB1c2VyIGlzIHRyeWluZ1xuICAgKiB0byBnbyBwYXN0IHRoaXMgbGFzdCBpdGVtLiBXaGVuIGEgZGFtcGluZyBmdW5jdGlvbiBpcyBhcHBsaWVkLCB0aGUgcmVzdWx0aW5nXG4gICAqIHZhbHVlIHdpbGwgYmUgbGVzcyB0aGFuIDQuNSAodGhlIGFjdHVhbCB2YWx1ZSB3aWxsIGJlIDQuMjUpLiBXaGVuIHRoaXNcbiAgICogc2VsZWN0aW9uIHN0YXRlIGlzIHJlbmRlcmVkLCB0aGUgdXNlciB3aWxsIHNlZSB0aGF0LCBlYWNoIHVuaXQgZGlzdGFuY2UgdGhlXG4gICAqIGRyYWcgdHJhdmVscyBoYXMgbGVzcyBhbmQgbGVzcyB2aXNpYmxlIGVmZmVjdC4gVGhpcyBpcyBwZXJjZWl2ZWQgYXMgdGVuc2lvbi5cbiAgICpcbiAgICogQHBhcmFtIHtudW1iZXJ9IHNlbGVjdGlvbiAtIEEgcmVhbCBudW1iZXIgaW5kaWNhdGluZyBhIHNlbGVjdGlvbiBwb3NpdGlvblxuICAgKiBAcGFyYW0ge251bWJlcn0gaXRlbUNvdW50IC0gQW4gaW50ZWdlciBmb3IgdGhlIG51bWJlciBvZiBpdGVtcyBpbiB0aGUgbGlzdFxuICAgKiBAcmV0dXJucyB7bnVtYmVyfSBBIHJlYWwgbnVtYmVyIHJlcHJlc2VudGluZyB0aGUgZGFtcGVkIHNlbGVjdGlvbiB2YWx1ZS5cbiAgICovXG4gIGRhbXBlZFNlbGVjdGlvbihzZWxlY3Rpb24sIGl0ZW1Db3VudCkge1xuICAgIGNvbnN0IGJvdW5kID0gaXRlbUNvdW50IC0gMTtcbiAgICBsZXQgZGFtcGVkO1xuICAgIGlmIChzZWxlY3Rpb24gPCAwKSB7XG4gICAgICAvLyBUcnlpbmcgdG8gZ28gcGFzdCBiZWdpbm5pbmcgb2YgbGlzdC4gQXBwbHkgdGVuc2lvbiBmcm9tIHRoZSBsZWZ0IGVkZ2UuXG4gICAgICBkYW1wZWQgPSAtbWl4aW4uaGVscGVycy5kYW1waW5nKC1zZWxlY3Rpb24pO1xuICAgIH0gZWxzZSBpZiAoc2VsZWN0aW9uID49IGJvdW5kKSB7XG4gICAgICAvLyBUcnlpbmcgdG8gZ28gcGFzdCBlbmQgb2YgbGlzdC4gQXBwbHkgdGVuc2lvbiBmcm9tIHRoZSByaWdodCBlZGdlLlxuICAgICAgZGFtcGVkID0gYm91bmQgKyBtaXhpbi5oZWxwZXJzLmRhbXBpbmcoc2VsZWN0aW9uIC0gYm91bmQpO1xuICAgIH0gZWxzZSB7XG4gICAgICAvLyBObyBkYW1waW5nIHJlcXVpcmVkLlxuICAgICAgZGFtcGVkID0gc2VsZWN0aW9uO1xuICAgIH1cbiAgICByZXR1cm4gZGFtcGVkO1xuICB9LFxuXG4gIC8qXG4gICAqIENhbGN1bGF0ZSBkYW1waW5nIGFzIGEgZnVuY3Rpb24gb2YgdGhlIGRpc3RhbmNlIHBhc3QgdGhlIG1pbmltdW0vbWF4aW11bVxuICAgKiB2YWx1ZXMuXG4gICAqXG4gICAqIFdlIHdhbnQgdG8gYXN5bXB0b3RpY2FsbHkgYXBwcm9hY2ggYW4gYWJzb2x1dGUgbWluaW11bSBvZiAxIHVuaXRcbiAgICogYmVsb3cvYWJvdmUgdGhlIGFjdHVhbCBtaW5pbXVtL21heGltdW0uIFRoaXMgcmVxdWlyZXMgY2FsY3VsYXRpbmcgYVxuICAgKiBoeXBlcmJvbGljIGZ1bmN0aW9uLlxuICAgKlxuICAgKiBTZWUgaHR0cDovL3d3dy53b2xmcmFtYWxwaGEuY29tL2lucHV0Lz9pPXkrJTNEKy0xJTJGJTI4eCUyQjElMjkrJTJCKzFcbiAgICogZm9yIHRoZSBvbmUgd2UgdXNlLiBUaGUgb25seSBwb3J0aW9uIG9mIHRoYXQgZnVuY3Rpb24gd2UgY2FyZSBhYm91dCBpcyB3aGVuXG4gICAqIHggaXMgemVybyBvciBncmVhdGVyLiBBbiBpbXBvcnRhbnQgY29uc2lkZXJhdGlvbiBpcyB0aGF0IHRoZSBjdXJ2ZSBiZVxuICAgKiB0YW5nZW50IHRvIHRoZSBkaWFnb25hbCBsaW5lIHg9eSBhdCAoMCwgMCkuIFRoaXMgZW5zdXJlcyBzbW9vdGggY29udGludWl0eVxuICAgKiB3aXRoIHRoZSBub3JtYWwgZHJhZyBiZWhhdmlvciwgaW4gd2hpY2ggdGhlIHZpc2libGUgc2xpZGluZyBpcyBsaW5lYXIgd2l0aFxuICAgKiB0aGUgZGlzdGFuY2UgdGhlIHRvdWNocG9pbnQgaGFzIGJlZW4gZHJhZ2dlZC5cbiAgICovXG4gIGRhbXBpbmcoeCkge1xuICAgIGNvbnN0IHkgPSAoLTEgLyAoeCArIDEpKSArIDE7XG4gICAgcmV0dXJuIHk7XG4gIH0sXG5cbiAgLypcbiAgICogUmV0dXJuIHRoZSBjdXJyZW50IGZyYWN0aW9uYWwgc2VsZWN0aW9uIHZhbHVlIGZvciB0aGUgZ2l2ZW4gZWxlbWVudC5cbiAgICpcbiAgICogVGhpcyBzaW1wbHkgYWRkcyB0aGUgZWxlbWVudCdzIGBzZWxlY3RlZEluZGV4YCBhbmQgYHNlbGVjdGVkRnJhY3Rpb25gXG4gICAqIHByb3BlcnRpZXMuXG4gICAqXG4gICAqIEBwYXJhbSB7SFRNTEVsZW1lbnR9IGVsZW1lbnQgLSBBbiBlbGVtZW50IHRoYXQgc3VwcG9ydHMgc2VsZWN0aW9uXG4gICAqL1xuICBlbGVtZW50U2VsZWN0aW9uKGVsZW1lbnQpIHtcbiAgICBjb25zdCBzZWxlY3RlZEluZGV4ID0gZWxlbWVudC5zZWxlY3RlZEluZGV4O1xuICAgIGlmIChzZWxlY3RlZEluZGV4IDwgMCkge1xuICAgICAgLy8gTm8gc2VsZWN0aW9uXG4gICAgICByZXR1cm47XG4gICAgfVxuICAgIGNvbnN0IHNlbGVjdGVkRnJhY3Rpb24gPSBlbGVtZW50LnNlbGVjdGVkRnJhY3Rpb24gfHwgMDtcbiAgICByZXR1cm4gc2VsZWN0ZWRJbmRleCArIHNlbGVjdGVkRnJhY3Rpb247XG4gIH0sXG5cbiAgLypcbiAgICogQnJlYWtzIGEgZnJhY3Rpb25hbCBzZWxlY3Rpb24gaW50byBpdHMgaW50ZWdlciBhbmQgZnJhY3Rpb25hbCBwYXJ0cy5cbiAgICpcbiAgICogRXhhbXBsZTogaWYgcGFzc2VkIDMuNSwgdGhpcyByZXR1cm5zIHsgaW5kZXg6IDMsIGZyYWN0aW9uOiA1IH0uXG4gICAqXG4gICAqIEBwYXJhbSB7bnVtYmVyfSBzZWxlY3Rpb24g4oCTwqBBIHJlYWwgbnVtYmVyIHJlcHJlc2VudGluZyBhIHNlbGVjdGlvbiBwb2ludFxuICAgKiBAcmV0dXJucyB7b2JqZWN0fSAtIEFuIG9iamVjdCB3aXRoIGFuIGBpbmRleGAgcHJvcGVydHkgaG9sZGluZyB0aGVcbiAgICogc2VsZWN0aW9uJ3MgaW50ZWdlciBjb21wb25lbnQsIGFuZCBhIGBmcmFjdGlvbmAgcHJvcGVydHkgaG9sZGluZyB0aGVcbiAgICogc2VsZWN0aW9uJ3MgZnJhY3Rpb25hbCBjb21wb25lbnQuXG4gICAqL1xuICBzZWxlY3Rpb25QYXJ0cyhzZWxlY3Rpb24pIHtcbiAgICAvLyBTdHVwaWQgSUUgZG9lc24ndCBoYXZlIE1hdGgudHJ1bmMuXG4gICAgLy8gY29uc3QgaW5kZXggPSBNYXRoLnRydW5jKHNlbGVjdGlvbik7XG4gICAgY29uc3QgaW5kZXggPSBzZWxlY3Rpb24gPCAwID8gTWF0aC5jZWlsKHNlbGVjdGlvbikgOiBNYXRoLmZsb29yKHNlbGVjdGlvbik7XG4gICAgY29uc3QgZnJhY3Rpb24gPSBzZWxlY3Rpb24gLSBpbmRleDtcbiAgICByZXR1cm4geyBpbmRleCwgZnJhY3Rpb24gfTtcbiAgfSxcblxuICAvKlxuICAgKiBSZXR1cm5zIGEgZnJhY3Rpb25hbCBzZWxlY3Rpb24gcG9pbnQgYWZ0ZXIgYWNjb3VudGluZyBmb3Igd3JhcHBpbmcsIGVuc3VyaW5nXG4gICAqIHRoYXQgdGhlIGludGVnZXIgcG9ydGlvbiBvZiB0aGUgc2VsZWN0aW9uIHN0YXlzIGJldHdlZW4gMCBhbmQgYGl0ZW1Db3VudGAtMS5cbiAgICogVGhhdCBpcywgdGhlIGludGVnZXIgcG9ydGlvbiB3aWxsIGFsd2F5cyBiZSBhIHZhbGlkIGluZGV4IGludG8gdGhlIGxpc3QuXG4gICAqXG4gICAqIEV4YW1wbGUgb2Ygd3JhcHBpbmcgcGFzdCB0aGUgZW5kIG9mIHRoZSBsaXN0OiBpZiBgc2VsZWN0aW9uYCBpcyA1LjUgYW5kXG4gICAqIGBpdGVtQ291bnRgIGlzIDUsIHRoaXMgcmV0dXJucyAwLjUuIEV4YW1wbGUgb2Ygd3JhcHBpbmcgcGFzdCB0aGUgYmVnaW5uaW5nIG9mXG4gICAqIHRoZSBsaXN0OiBpZiBgc2VsZWN0aW9uYCBpcyAwLjUgYW5kIGBpdGVtQ291bnRgIGlzIDUsIHRoaXMgcmV0dXJucyA0LjUuXG4gICAqXG4gICAqIEBwYXJhbSB7bnVtYmVyfSBzZWxlY3Rpb24gLSBBIHJlYWwgbnVtYmVyIHJlcHJlc2VudGluZyBhIHNlbGVjdGlvbiBwb2ludFxuICAgKiBAcGFyYW0ge251bWJlcn0gaXRlbUNvdW50IC0gVGhlIG51bWJlciBvZiBpdGVtcyBpbiB0aGUgbGlzdFxuICAgKiBAcmV0dXJucyB7bnVtYmVyfSAtIFRoZSByZXN1bHQgb2Ygd3JhcHBpbmcgdGhlIHNlbGVjdGlvbiBwb2ludFxuICAgKi9cbiAgd3JhcHBlZFNlbGVjdGlvbihzZWxlY3Rpb24sIGl0ZW1Db3VudCkge1xuICAgIC8vIEhhbmRsZXMgcG9zc2liaWxpdHkgb2YgbmVnYXRpdmUgbW9kLlxuICAgIC8vIFNlZSBodHRwOi8vc3RhY2tvdmVyZmxvdy5jb20vYS8xODYxODI1MC83NjQ3MlxuICAgIHJldHVybiAoKHNlbGVjdGlvbiAlIGl0ZW1Db3VudCkgKyBpdGVtQ291bnQpICUgaXRlbUNvdW50O1xuICB9LFxuXG4gIC8qXG4gICAqIFJldHVybiB0aGUgcGFydHMgb2YgYSBzZWxlY3Rpb24sIGZpcnN0IHdyYXBwaW5nIGlmIG5lY2Vzc2FyeS5cbiAgICpcbiAgICogQHBhcmFtIHtudW1iZXJ9IHNlbGVjdGlvbiDigJMgQSByZWFsIG51bWJlciByZXByZXNlbnRpbmcgYSBzZWxlY3Rpb24gcG9pbnRcbiAgICogQHBhcmFtIHtudW1iZXJ9IGl0ZW1Db3VudCAtIFRoZSBudW1iZXIgb2YgaXRlbXMgaW4gdGhlIGxpc3RcbiAgICogQHBhcmFtIHtib29sZWFufSB3cmFwIOKAkyBUcnVlIGlmIHRoZSBzZWxlY3Rpb24gc2hvdWxkIHdyYXAgdG8gc3RheSB3aXRoaW4gdGhlXG4gICAqIGxpc3RcbiAgICogQHJldHVybnMge29iamVjdH0g4oCTIFRoZSBwYXJ0cyBvZiB0aGUgc2VsZWN0aW9uLCB1c2luZyB0aGUgc2FtZSBmb3JtYXQgYXNcbiAgICogYHNlbGVjdGlvblBhcnRzYC5cbiAgICovXG4gIHdyYXBwZWRTZWxlY3Rpb25QYXJ0cyhzZWxlY3Rpb24sIGl0ZW1Db3VudCwgd3JhcCkge1xuICAgIGlmICh3cmFwKSB7XG4gICAgICBzZWxlY3Rpb24gPSBtaXhpbi5oZWxwZXJzLndyYXBwZWRTZWxlY3Rpb24oc2VsZWN0aW9uLCBpdGVtQ291bnQpO1xuICAgIH1cbiAgICByZXR1cm4gbWl4aW4uaGVscGVycy5zZWxlY3Rpb25QYXJ0cyhzZWxlY3Rpb24pO1xuICB9XG5cbn07XG4iLCJpbXBvcnQgY3JlYXRlU3ltYm9sIGZyb20gJy4vY3JlYXRlU3ltYm9sJztcbmltcG9ydCBGcmFjdGlvbmFsU2VsZWN0aW9uTWl4aW4gZnJvbSAnLi9GcmFjdGlvbmFsU2VsZWN0aW9uTWl4aW4nO1xuaW1wb3J0IHN5bWJvbHMgZnJvbSAnLi9zeW1ib2xzJztcblxuXG4vLyBTeW1ib2xzIGZvciBwcml2YXRlIGRhdGEgbWVtYmVycyBvbiBhbiBlbGVtZW50LlxuY29uc3QgYW5pbWF0aW9uU3ltYm9sID0gY3JlYXRlU3ltYm9sKCdhbmltYXRpb24nKTtcbmNvbnN0IGRyYWdnaW5nU3ltYm9sID0gY3JlYXRlU3ltYm9sKCdkcmFnZ2luZycpO1xuY29uc3QgbGFzdEFuaW1hdGlvblN5bWJvbCA9IGNyZWF0ZVN5bWJvbCgnbGFzdEFuaW1hdGlvbicpO1xuY29uc3QgcGxheWluZ0FuaW1hdGlvblN5bWJvbCA9IGNyZWF0ZVN5bWJvbCgnYW5pbWF0aW5nU2VsZWN0aW9uJyk7XG5jb25zdCBwcmV2aW91c1NlbGVjdGlvblN5bWJvbCA9IGNyZWF0ZVN5bWJvbCgncHJldmlvdXNTZWxlY3Rpb24nKTtcbmNvbnN0IHNlbGVjdGlvbkFuaW1hdGlvbkR1cmF0aW9uU3ltYm9sID0gY3JlYXRlU3ltYm9sKCdzZWxlY3Rpb25BbmltYXRpb25EdXJhdGlvbicpO1xuY29uc3Qgc2VsZWN0aW9uQW5pbWF0aW9uRWZmZWN0U3ltYm9sID0gY3JlYXRlU3ltYm9sKCdzZWxlY3Rpb25BbmltYXRpb25FZmZlY3QnKTtcbmNvbnN0IHNlbGVjdGlvbkFuaW1hdGlvbktleWZyYW1lc1N5bWJvbCA9IGNyZWF0ZVN5bWJvbCgnc2VsZWN0aW9uQW5pbWF0aW9uS2V5ZnJhbWVzJyk7XG5jb25zdCByZXNldEFuaW1hdGlvbnNPbk5leHRSZW5kZXJTeW1ib2wgPSBjcmVhdGVTeW1ib2woJ3Jlc2V0QW5pbWF0aW9uc09uTmV4dFJlbmRlcicpO1xuXG5cbi8qIEV4cG9ydGVkIGZ1bmN0aW9uIGV4dGVuZHMgYSBiYXNlIGNsYXNzIHdpdGggU2VsZWN0aW9uQW5pbWF0aW9uLiAqL1xuZXhwb3J0IGRlZmF1bHQgZnVuY3Rpb24gbWl4aW4oYmFzZSkge1xuXG4gIC8qKlxuICAgKiBNaXhpbiB3aGljaCB1c2VzIGFuaW1hdGlvbiB0byBzaG93IHRyYW5zaXRpb25zIGJldHdlZW4gc2VsZWN0aW9uIHN0YXRlcy5cbiAgICpcbiAgICogVGhpcyBtaXhpbiBjYW4gYmUgdXNlZCBieSBjb21wb25lbnRzIHRoYXQgd2FudCB0byBwcm92aWRlIHZpc2libGVcbiAgICogYW5pbWF0aW9ucyB3aGVuIGNoYW5naW5nIHRoZSBzZWxlY3Rpb24uIEZvciBleGFtcGxlLCBhIGNhcm91c2VsIGNvbXBvbmVudFxuICAgKiBtYXkgd2FudCB0byBkZWZpbmUgYSBzbGlkaW5nIGFuaW1hdGlvbiBlZmZlY3Qgc2hvd24gd2hlbiBtb3ZpbmcgYmV0d2VlblxuICAgKiBpdGVtcy5cbiAgICpcbiAgICogVGhlIGFuaW1hdGlvbiBpcyBkZWZpbmVkIGJ5IGEgYHNlbGVjdGlvbkFuaW1hdGlvbktleWZyYW1lc2AgcHJvcGVydHk7IHNlZVxuICAgKiB0aGF0IHByb3BlcnR5IGZvciBkZXRhaWxzIG9uIGhvdyB0byBkZWZpbmUgdGhlc2Uga2V5ZnJhbWVzLiBUaGlzIGFuaW1hdGlvblxuICAgKiB3aWxsIGJlIHVzZWQgaW4gdHdvIHdheXMuIEZpcnN0LCB3aGVuIG1vdmluZyBzdHJpY3RseSBiZXR3ZWVuIGl0ZW1zLCB0aGVcbiAgICogYW5pbWF0aW9uIHdpbGwgcGxheSBzbW9vdGhseSB0byBzaG93IHRoZSBzZWxlY3Rpb24gY2hhbmdpbmcuIFNlY29uZCwgdGhlXG4gICAqIGFuaW1hdGlvbiBjYW4gYmUgdXNlZCB0byByZW5kZXIgdGhlIHNlbGVjdGlvbiBhdCBhIGZpeGVkIHBvaW50IGluIHRoZVxuICAgKiB0cmFuc2l0aW9uIGJldHdlZW4gc3RhdGVzLiBFLmcuLCBpZiB0aGUgdXNlciBwYXVzZXMgaGFsZndheSB0aHJvdWdoXG4gICAqIGRyYWdnaW5nIGFuIGVsZW1lbnQgdXNpbmcgW1N3aXBlRGlyZWN0aW9uTWl4aW5dKFN3aXBlRGlyZWN0aW9uTWl4aW4ubWQpXG4gICAqIG9yIFtUcmFja3BhZERpcmVjdGlvbk1peGluXShUcmFja3BhZERpcmVjdGlvbk1peGluLm1kKXMsIHRoZW4gdGhlIHNlbGVjdGlvblxuICAgKiBhbmltYXRpb24gd2lsbCBiZSBzaG93biBhdCB0aGUgcG9pbnQgZXhhY3RseSBoYWxmd2F5IHRocm91Z2guXG4gICAqXG4gICAqIFRoaXMgbWl4aW4gZXhwZWN0cyBhIGNvbXBvbmVudCB0byBwcm92aWRlIGFuIGBpdGVtc2AgYXJyYXkgb2YgYWxsIGVsZW1lbnRzXG4gICAqIGluIHRoZSBsaXN0LCB3aGljaCBjYW4gYmUgcHJvdmlkZWQgdmlhXG4gICAqIFtDb250ZW50SXRlbXNNaXhpbl0oQ29udGVudEl0ZW1zTWl4aW4ubWQpLiBUaGlzIG1peGluIGFsc28gZXhwZWN0c1xuICAgKiBgc2VsZWN0ZWRJbmRleGAgYW5kIGBzZWxlY3RlZEl0ZW1gIHByb3BlcnRpZXMsIHdoaWNoIGNhbiBiZSBwcm92aWRlZCB2aWFcbiAgICogW1NpbmdsZVNlbGVjdGlvbk1peGluXShTaW5nbGVTZWxlY3Rpb25NaXhpbi5tZCkuXG4gICAqXG4gICAqIFRoaXMgbWl4aW4gc3VwcG9ydHMgYSBgc2VsZWN0aW9uV3JhcHNgIHByb3BlcnR5LiBXaGVuIHRydWUsIHRoZSB1c2VyIGNhblxuICAgKiBuYXZpZ2F0ZSBmb3J3YXJkIGZyb20gdGhlIGxhc3QgaXRlbSBpbiB0aGUgbGlzdCBhbmQgd3JhcCBhcm91bmQgdG8gdGhlXG4gICAqIGZpcnN0IGl0ZW0sIG9yIG5hdmlnYXRlIGJhY2t3YXJkIGZyb20gdGhlIGZpcnN0IGl0ZW0gYW5kIHdyYXAgYXJvdW5kIHRvIHRoZVxuICAgKiBsYXN0IGl0ZW0uXG4gICAqXG4gICAqIFRoaXMgbWl4aW4gdXNlcyB0aGUgV2ViIEFuaW1hdGlvbnMgQVBJLiBGb3IgdXNlIG9uIGJyb3dzZXJzIHdoaWNoXG4gICAqIGRvIG5vdCBzdXBwb3J0IHRoYXQgQVBJIG5hdGl2ZWx5LCB5b3Ugd2lsbCBuZWVkIHRvIGxvYWQgdGhlXG4gICAqIFtXZWIgQW5pbWF0aW9ucyBwb2x5ZmlsbF0oaHR0cHM6Ly9naXRodWIuY29tL3dlYi1hbmltYXRpb25zL3dlYi1hbmltYXRpb25zLWpzKS5cbiAgICovXG4gIGNsYXNzIFNlbGVjdGlvbkFuaW1hdGlvbiBleHRlbmRzIGJhc2Uge1xuXG4gICAgY29uc3RydWN0b3IoKSB7XG4gICAgICBzdXBlcigpO1xuXG4gICAgICAvLyBTZXQgZGVmYXVsdHMuXG4gICAgICBpZiAodHlwZW9mIHRoaXMuc2VsZWN0aW9uQW5pbWF0aW9uRHVyYXRpb24gPT09ICd1bmRlZmluZWQnKSB7XG4gICAgICAgIHRoaXMuc2VsZWN0aW9uQW5pbWF0aW9uRHVyYXRpb24gPSB0aGlzW3N5bWJvbHMuZGVmYXVsdHNdLnNlbGVjdGlvbkFuaW1hdGlvbkR1cmF0aW9uO1xuICAgICAgfVxuICAgICAgaWYgKHR5cGVvZiB0aGlzLnNlbGVjdGlvbkFuaW1hdGlvbkVmZmVjdCA9PT0gJ3VuZGVmaW5lZCcgJiYgdGhpcy5zZWxlY3Rpb25BbmltYXRpb25LZXlmcmFtZXMgPT0gbnVsbCkge1xuICAgICAgICB0aGlzLnNlbGVjdGlvbkFuaW1hdGlvbkVmZmVjdCA9IHRoaXNbc3ltYm9scy5kZWZhdWx0c10uc2VsZWN0aW9uQW5pbWF0aW9uRWZmZWN0O1xuICAgICAgfVxuXG4gICAgICB0aGlzW3N5bWJvbHMuZHJhZ2dpbmddID0gZmFsc2U7XG4gICAgfVxuXG4gICAgZ2V0IFtzeW1ib2xzLmRlZmF1bHRzXSgpIHtcbiAgICAgIGNvbnN0IGRlZmF1bHRzID0gc3VwZXJbc3ltYm9scy5kZWZhdWx0c10gfHwge307XG4gICAgICBkZWZhdWx0cy5zZWxlY3Rpb25BbmltYXRpb25EdXJhdGlvbiA9IDI1MDtcbiAgICAgIGRlZmF1bHRzLnNlbGVjdGlvbkFuaW1hdGlvbkVmZmVjdCA9ICdzbGlkZSc7XG4gICAgICByZXR1cm4gZGVmYXVsdHM7XG4gICAgfVxuXG4gICAgLypcbiAgICAgKiBQcm92aWRlIGJhY2tpbmcgZm9yIHRoZSBkcmFnZ2luZyBwcm9wZXJ0eS5cbiAgICAgKiBBbHNvLCB3aGVuIGEgZHJhZyBiZWdpbnMsIHJlc2V0IHRoZSBhbmltYXRpb25zLlxuICAgICAqL1xuICAgIGdldCBbc3ltYm9scy5kcmFnZ2luZ10oKSB7XG4gICAgICByZXR1cm4gdGhpc1tkcmFnZ2luZ1N5bWJvbF07XG4gICAgfVxuICAgIHNldCBbc3ltYm9scy5kcmFnZ2luZ10odmFsdWUpIHtcbiAgICAgIGNvbnN0IHByZXZpb3VzVmFsdWUgPSB0aGlzW3N5bWJvbHMuZHJhZ2dpbmddO1xuICAgICAgdGhpc1tkcmFnZ2luZ1N5bWJvbF0gPSB2YWx1ZTtcbiAgICAgIGlmIChzeW1ib2xzLmRyYWdnaW5nIGluIGJhc2UucHJvdG90eXBlKSB7IHN1cGVyW3N5bWJvbHMuZHJhZ2dpbmddID0gdmFsdWU7IH1cbiAgICAgIGlmICh2YWx1ZSAmJiAhcHJldmlvdXNWYWx1ZSkge1xuICAgICAgICAvLyBIYXZlIGJlZ3VuIGEgZHJhZy5cbiAgICAgICAgdGhpc1tyZXNldEFuaW1hdGlvbnNPbk5leHRSZW5kZXJTeW1ib2xdID0gdHJ1ZTtcbiAgICAgIH1cbiAgICB9XG5cbiAgICBbc3ltYm9scy5pdGVtQWRkZWRdKGl0ZW0pIHtcbiAgICAgIC8vIFdlIG1hcmsgbmV3IGl0ZW1zIGluIHRoZSBsaXN0IGFzIGV4cGxpY2l0bHkgdmlzaWJsZSB0byBBUklBLiBPdGhlcndpc2UsXG4gICAgICAvLyB3aGVuIGFuIGl0ZW0gaXNuJ3QgdmlzaWJsZSBvbiB0aGUgc2NyZWVuLCBBUklBIHdpbGwgYXNzdW1lIHRoZSBpdGVtIGlzXG4gICAgICAvLyBvZiBubyBpbnRlcmVzdCB0byB0aGUgdXNlciwgYW5kIGxlYXZlIGl0IG91dCBvZiB0aGUgYWNjZXNzaWJpbGl0eSB0cmVlLlxuICAgICAgLy8gSWYgdGhlIGxpc3QgY29udGFpbnMgMTAgaXRlbXMsIGJ1dCBvbmx5IDMgYXJlIHZpc2libGUsIGEgc2NyZWVuIHJlYWRlclxuICAgICAgLy8gbWlnaHQgdGhlbiBhbm5vdW5jZSB0aGUgbGlzdCBvbmx5IGhhcyAzIGl0ZW1zLiBUbyBlbnN1cmUgdGhhdCBzY3JlZW5cbiAgICAgIC8vIHJlYWRlcnMgYW5kIG90aGVyIGFzc2lzdGl2ZSB0ZWNobm9sb2dpZXMgYW5ub3VuY2UgdGhlIGNvcnJlY3QgdG90YWxcbiAgICAgIC8vIG51bWJlciBvZiBpdGVtcywgd2UgZXhwbGljaXRseSBtYXJrIGFsbCBpdGVtcyBhcyBub3QgaGlkZGVuLiBUaGlzIHdpbGxcbiAgICAgIC8vIGV4cG9zZSB0aGVtIGFsbCBpbiB0aGUgYWNjZXNzaWJpbGl0eSB0cmVlLCBldmVuIHRoZSBpdGVtcyB3aGljaCBhcmVcbiAgICAgIC8vIGN1cnJlbnRseSBub3QgcmVuZGVyZWQuXG4gICAgICAvL1xuICAgICAgLy8gVE9ETzogR2VuZXJhbGx5IHNwZWFraW5nLCB0aGlzIGVudGlyZSBtaXhpbiBhc3N1bWVzIHRoYXQgdGhlIHVzZXIgY2FuXG4gICAgICAvLyBuYXZpZ2F0ZSB0aHJvdWdoIGFsbCBpdGVtcyBpbiBhIGxpc3QuIEJ1dCBhbiBhcHAgY291bGQgc3R5bGUgYW4gaXRlbSBhc1xuICAgICAgLy8gZGlzcGxheTpub25lIG9yIHZpc2liaWxpdHk6aGlkZGVuIGJlY2F1c2UgdGhlIHVzZXIgaXMgbm90IGFsbG93ZWQgdG9cbiAgICAgIC8vIGludGVyYWN0IHdpdGggdGhhdCBpdGVtIGF0IHRoZSBtb21lbnQuIFN1cHBvcnQgZm9yIHRoaXMgc2NlbmFyaW8gc2hvdWxkXG4gICAgICAvLyBiZSBhZGRlZC4gVGhpcyB3b3VsZCBlbnRhaWwgY2hhbmdpbmcgYWxsIGxvY2F0aW9ucyB3aGVyZSBhIG1peGluXG4gICAgICAvLyBmdW5jdGlvbiBpcyBjb3VudGluZyBpdGVtcywgaXRlcmF0aW5nIG92ZXIgdGhlICh2aXNpYmxlKSBpdGVtcywgYW5kXG4gICAgICAvLyBzaG93aW5nIG9yIGhpZGluZyBpdGVtcy4gQW1vbmcgb3RoZXIgdGhpbmdzLCB0aGUgY29kZSBiZWxvdyB0byBtYWtlXG4gICAgICAvLyBpdGVtcyB2aXNpYmxlIHRvIEFSSUEgd291bGQgbmVlZCB0byBkaXNjcmltaW5hdGUgYmV0d2VlbiBpdGVtcyB3aGljaFxuICAgICAgLy8gYXJlIGludmlzaWJsZSBiZWNhdXNlIG9mIGFuaW1hdGlvbiBzdGF0ZSwgb3IgaW52aXNpYmxlIGJlY2F1c2UgdGhlIHVzZXJcbiAgICAgIC8vIHNob3VsZG4ndCBpbnRlcmFjdCB3aXRoIHRoZW0uXG4gICAgICBpdGVtLnNldEF0dHJpYnV0ZSgnYXJpYS1oaWRkZW4nLCBmYWxzZSk7XG4gICAgfVxuXG4gICAgW3N5bWJvbHMuaXRlbXNDaGFuZ2VkXSgpIHtcbiAgICAgIGlmIChzdXBlcltzeW1ib2xzLml0ZW1zQ2hhbmdlZF0pIHsgc3VwZXJbc3ltYm9scy5pdGVtc0NoYW5nZWRdKCk7IH1cblxuICAgICAgcmVzZXRBbmltYXRpb25zKHRoaXMpO1xuXG4gICAgICAvLyBUT0RPOiBBbHNvIHJlc2V0IG91ciBub3Rpb24gb2YgdGhlIGxhc3QgcmVuZGVyZWQgc2VsZWN0aW9uPyBUaGlzIGNvbWVzXG4gICAgICAvLyB1cCB3aGVuIGEgRE9NIHJlbW92YWwgY2F1c2VzIHRoZSBzZWxlY3RlZCBpdGVtIHRvIGNoYW5nZSBwb3NpdGlvbi5cbiAgICAgIC8vIHRoaXNbcHJldmlvdXNTZWxlY3Rpb25TeW1ib2xdID0gbnVsbDtcblxuICAgICAgcmVuZGVyU2VsZWN0aW9uKHRoaXMpO1xuICAgIH1cblxuICAgIHJlc2V0QW5pbWF0aW9ucygpIHtcbiAgICAgIHJlc2V0QW5pbWF0aW9ucyh0aGlzKTtcbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBBIGZyYWN0aW9uYWwgdmFsdWUgaW5kaWNhdGluZyBob3cgZmFyIHRoZSB1c2VyIGhhcyBjdXJyZW50bHkgYWR2YW5jZWQgdG9cbiAgICAgKiB0aGUgbmV4dC9wcmV2aW91cyBpdGVtLiBFLmcuLCBhIGBzZWxlY3RlZEZyYWN0aW9uYCBvZiAzLjUgaW5kaWNhdGVzIHRoZVxuICAgICAqIHVzZXIgaXMgaGFsZndheSBiZXR3ZWVuIGl0ZW1zIDMgYW5kIDQuXG4gICAgICpcbiAgICAgKiBGb3IgbW9yZSBkZXRhaWxzLCBzZWUgW0ZyYWN0aW9uYWxTZWxlY3Rpb25NaXhpbl0oRnJhY3Rpb25hbFNlbGVjdGlvbk1peGluLm1kKVxuICAgICAqIG1peGluLlxuICAgICAqXG4gICAgICogQHR5cGUge251bWJlcn1cbiAgICAgKi9cbiAgICBnZXQgc2VsZWN0ZWRGcmFjdGlvbigpIHtcbiAgICAgIHJldHVybiBzdXBlci5zZWxlY3RlZEZyYWN0aW9uIHx8IDA7XG4gICAgfVxuICAgIHNldCBzZWxlY3RlZEZyYWN0aW9uKHZhbHVlKSB7XG4gICAgICBpZiAoJ3NlbGVjdGVkRnJhY3Rpb24nIGluIGJhc2UucHJvdG90eXBlKSB7IHN1cGVyLnNlbGVjdGVkRnJhY3Rpb24gPSB2YWx1ZTsgfVxuICAgICAgcmVuZGVyU2VsZWN0aW9uKHRoaXMsIHRoaXMuc2VsZWN0ZWRJbmRleCwgdmFsdWUpO1xuICAgIH1cblxuICAgIGdldCBzZWxlY3RlZEluZGV4KCkge1xuICAgICAgcmV0dXJuIHN1cGVyLnNlbGVjdGVkSW5kZXg7XG4gICAgfVxuICAgIHNldCBzZWxlY3RlZEluZGV4KGluZGV4KSB7XG4gICAgICBpZiAoJ3NlbGVjdGVkSW5kZXgnIGluIGJhc2UucHJvdG90eXBlKSB7IHN1cGVyLnNlbGVjdGVkSW5kZXggPSBpbmRleDsgfVxuICAgICAgcmVuZGVyU2VsZWN0aW9uKHRoaXMsIGluZGV4LCAwKTtcbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBUaGUgZHVyYXRpb24gb2YgYSBzZWxlY3Rpb24gYW5pbWF0aW9uIGluIG1pbGxpc2Vjb25kcy5cbiAgICAgKlxuICAgICAqIFRoaXMgbWVhc3VyZXMgdGhlIGFtb3VudCBvZiB0aW1lIHJlcXVpcmVkIGZvciBhIHNlbGVjdGlvbiBhbmltYXRpb24gdG9cbiAgICAgKiBjb21wbGV0ZS4gVGhpcyBudW1iZXIgcmVtYWlucyBjb25zdGFudCwgZXZlbiBpZiB0aGUgbnVtYmVyIG9mIGl0ZW1zIGJlaW5nXG4gICAgICogYW5pbWF0ZWQgaW5jcmVhc2VzLlxuICAgICAqXG4gICAgICogVGhlIGRlZmF1bHQgdmFsdWUgaXMgMjUwIG1pbGxpc2Vjb25kcyAoYSBxdWFydGVyIGEgc2Vjb25kKS5cbiAgICAgKlxuICAgICAqIEB0eXBlIHtudW1iZXJ9XG4gICAgICogQGRlZmF1bHQgMjUwXG4gICAgICovXG4gICAgZ2V0IHNlbGVjdGlvbkFuaW1hdGlvbkR1cmF0aW9uKCkge1xuICAgICAgcmV0dXJuIHRoaXNbc2VsZWN0aW9uQW5pbWF0aW9uRHVyYXRpb25TeW1ib2xdO1xuICAgIH1cbiAgICBzZXQgc2VsZWN0aW9uQW5pbWF0aW9uRHVyYXRpb24odmFsdWUpIHtcbiAgICAgIHRoaXNbc2VsZWN0aW9uQW5pbWF0aW9uRHVyYXRpb25TeW1ib2xdID0gdmFsdWU7XG4gICAgICBpZiAoJ3NlbGVjdGlvbkFuaW1hdGlvbkR1cmF0aW9uJyBpbiBiYXNlLnByb3RvdHlwZSkgeyBzdXBlci5zZWxlY3Rpb25BbmltYXRpb25EdXJhdGlvbiA9IHZhbHVlOyB9XG4gICAgfVxuXG4gICAgLyoqXG4gICAgICogVGhlIG5hbWUgb2YgYSBzdGFuZGFyZCBzZWxlY3Rpb24gYW5pbWF0aW9uIGVmZmVjdC5cbiAgICAgKlxuICAgICAqIFRoaXMgaXMgYSBzaG9ydGhhbmQgZm9yIHNldHRpbmcgdGhlIGBzZWxlY3Rpb25BbmltYXRpb25LZXlmcmFtZXNgXG4gICAgICogcHJvcGVydHkgdG8gc3RhbmRhcmQga2V5ZnJhbWVzLiBTdXBwb3J0ZWQgc3RyaW5nIHZhbHVlczpcbiAgICAgKlxuICAgICAqICogXCJjcm9zc2ZhZGVcIlxuICAgICAqICogXCJyZXZlYWxcIlxuICAgICAqICogXCJyZXZlYWxXaXRoRmFkZVwiXG4gICAgICogKiBcInNob3dBZGphY2VudFwiXG4gICAgICogKiBcInNsaWRlXCJcbiAgICAgKiAqIFwic2xpZGVXaXRoR2FwXCJcbiAgICAgKlxuICAgICAqIEB0eXBlIHtzdHJpbmd9XG4gICAgICogQGRlZmF1bHQgXCJzbGlkZVwiXG4gICAgICovXG4gICAgZ2V0IHNlbGVjdGlvbkFuaW1hdGlvbkVmZmVjdCgpIHtcbiAgICAgIHJldHVybiB0aGlzW3NlbGVjdGlvbkFuaW1hdGlvbkVmZmVjdFN5bWJvbF07XG4gICAgfVxuICAgIHNldCBzZWxlY3Rpb25BbmltYXRpb25FZmZlY3QodmFsdWUpIHtcbiAgICAgIHRoaXNbc2VsZWN0aW9uQW5pbWF0aW9uRWZmZWN0U3ltYm9sXSA9IHZhbHVlO1xuICAgICAgaWYgKCdzZWxlY3Rpb25BbmltYXRpb25FZmZlY3QnIGluIGJhc2UucHJvdG90eXBlKSB7IHN1cGVyLnNlbGVjdGlvbkFuaW1hdGlvbkVmZmVjdCA9IHZhbHVlOyB9XG4gICAgICB0aGlzLnNlbGVjdGlvbkFuaW1hdGlvbktleWZyYW1lcyA9IG1peGluLnN0YW5kYXJkRWZmZWN0S2V5ZnJhbWVzW3ZhbHVlXTtcbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBUaGUga2V5ZnJhbWVzIHRoYXQgZGVmaW5lIGFuIGFuaW1hdGlvbiB0aGF0IHBsYXlzIGZvciBhbiBpdGVtIHdoZW4gbW92aW5nXG4gICAgICogZm9yd2FyZCBpbiB0aGUgc2VxdWVuY2UuXG4gICAgICpcbiAgICAgKiBUaGlzIGlzIGFuIGFycmF5IG9mIENTUyBydWxlcyB0aGF0IHdpbGwgYmUgYXBwbGllZC4gVGhlc2UgYXJlIHVzZWQgYXNcbiAgICAgKiBba2V5ZnJhbWVzXShodHRwOi8vdzNjLmdpdGh1Yi5pby93ZWItYW5pbWF0aW9ucy8ja2V5ZnJhbWVzLXNlY3Rpb24pXG4gICAgICogdG8gYW5pbWF0ZSB0aGUgaXRlbSB3aXRoIHRoZVxuICAgICAqIFtXZWIgQW5pbWF0aW9ucyBBUEldKGh0dHBzOi8vZGV2ZWxvcGVyLm1vemlsbGEub3JnL2VuLVVTL2RvY3MvV2ViL0FQSS9hbmltYXRpb24pLlxuICAgICAqXG4gICAgICogVGhlIGFuaW1hdGlvbiByZXByZXNlbnRzIHRoZSBzdGF0ZSBvZiB0aGUgbmV4dCBpdGVtIGFzIGl0IG1vdmVzIGZyb21cbiAgICAgKiBjb21wbGV0ZWx5IHVuc2VsZWN0ZWQgKG9mZnN0YWdlLCB1c3VhbGx5IHJpZ2h0KSwgdG8gc2VsZWN0ZWQgKGNlbnRlclxuICAgICAqIHN0YWdlKSwgdG8gY29tcGxldGVseSB1bnNlbGVjdGVkIChvZmZzdGFnZSwgdXN1YWxseSBsZWZ0KS4gVGhlIGNlbnRlciB0aW1lXG4gICAgICogb2YgdGhlIGFuaW1hdGlvbiBzaG91bGQgY29ycmVzcG9uZCB0byB0aGUgaXRlbSdzIHF1aXNjZW50IHNlbGVjdGVkIHN0YXRlLFxuICAgICAqIHR5cGljYWxseSBpbiB0aGUgY2VudGVyIG9mIHRoZSBzdGFnZSBhbmQgYXQgdGhlIGl0ZW0ncyBsYXJnZXN0IHNpemUuXG4gICAgICpcbiAgICAgKiBUaGUgZGVmYXVsdCBmb3J3YXJkIGFuaW1hdGlvbiBpcyBhIHNtb290aCBzbGlkZSBhdCBmdWxsIHNpemUgZnJvbSByaWdodCB0b1xuICAgICAqIGxlZnQuXG4gICAgICpcbiAgICAgKiBXaGVuIG1vdmluZyB0aGUgc2VsZWN0aW9uIGJhY2t3YXJkLCB0aGlzIGFuaW1hdGlvbiBpcyBwbGF5ZWQgaW4gcmV2ZXJzZS5cbiAgICAgKlxuICAgICAqIEB0eXBlIHtjc3NSdWxlc1tdfVxuICAgICAqL1xuICAgIGdldCBzZWxlY3Rpb25BbmltYXRpb25LZXlmcmFtZXMoKSB7XG4gICAgICAvLyBTdGFuZGFyZCBhbmltYXRpb24gc2xpZGVzIGxlZnQvcmlnaHQsIGtlZXBzIGFkamFjZW50IGl0ZW1zIG91dCBvZiB2aWV3LlxuICAgICAgcmV0dXJuIHRoaXNbc2VsZWN0aW9uQW5pbWF0aW9uS2V5ZnJhbWVzU3ltYm9sXTtcbiAgICB9XG4gICAgc2V0IHNlbGVjdGlvbkFuaW1hdGlvbktleWZyYW1lcyh2YWx1ZSkge1xuICAgICAgdGhpc1tzZWxlY3Rpb25BbmltYXRpb25LZXlmcmFtZXNTeW1ib2xdID0gdmFsdWU7XG4gICAgICBpZiAoJ3NlbGVjdGlvbkFuaW1hdGlvbktleWZyYW1lcycgaW4gYmFzZS5wcm90b3R5cGUpIHsgc3VwZXIuc2VsZWN0aW9uQW5pbWF0aW9uS2V5ZnJhbWVzID0gdmFsdWU7IH1cbiAgICAgIHJlc2V0QW5pbWF0aW9ucyh0aGlzKTtcbiAgICAgIHJlbmRlclNlbGVjdGlvbih0aGlzKTtcbiAgICB9XG5cbiAgICBnZXQgc2VsZWN0aW9uV3JhcHMoKSB7XG4gICAgICByZXR1cm4gc3VwZXIuc2VsZWN0aW9uV3JhcHM7XG4gICAgfVxuICAgIHNldCBzZWxlY3Rpb25XcmFwcyh2YWx1ZSkge1xuICAgICAgaWYgKCdzZWxlY3Rpb25XcmFwcycgaW4gYmFzZS5wcm90b3R5cGUpIHsgc3VwZXIuc2VsZWN0aW9uV3JhcHMgPSB2YWx1ZTsgfVxuICAgICAgcmVzZXRBbmltYXRpb25zKHRoaXMpO1xuICAgICAgcmVuZGVyU2VsZWN0aW9uKHRoaXMpO1xuICAgIH1cbiAgfVxuXG4gIHJldHVybiBTZWxlY3Rpb25BbmltYXRpb247XG59XG5cblxuLy8gV2UgZXhwb3NlIGhlbHBlcnMgb24gdGhlIG1peGluIGZ1bmN0aW9uIHRoYXQgd2Ugd2FudCB0byBiZSBhYmxlIHRvIHVuaXQgdGVzdC5cbi8vIFNpbmNlIHRoZXNlIGFyZSBvbiB0aGUgZnVuY3Rpb24sIG5vdCBvbiB0aGUgY2xhc3MgZW1pdHRlZCBieSB0aGUgZnVuY3Rpb24sXG4vLyB0aGV5IGRvbid0IGVuZCB1cCBnZXR0aW5nIGV4cG9zZWQgb24gYWN0dWFsIGVsZW1lbnQgaW5zdGFuY2VzLlxubWl4aW4uaGVscGVycyA9IHtcblxuICAvKlxuICAgKiBDYWxjdWxhdGUgdGhlIGFuaW1hdGlvbiBmcmFjdGlvbnMgZm9yIGFuIGVsZW1lbnQncyBpdGVtcyBhdCB0aGUgZ2l2ZW5cbiAgICogc2VsZWN0aW9uIHBvaW50LiBUaGlzIGlzIHVzZWQgd2hlbiByZW5kZXJpbmcgdGhlIGVsZW1lbnQncyBzZWxlY3Rpb24gc3RhdGVcbiAgICogaW5zdGFudGFuZW91c2x5LlxuICAgKlxuICAgKiBUaGlzIGZ1bmN0aW9uIGNvbnNpZGVycyB0aGUgc2VsZWN0ZWRJbmRleCBwYXJhbWV0ZXIsIHdoaWNoIGNhbiBiZSBhIHdob2xlXG4gICAqIG9yIGZyYWN0aW9uYWwgbnVtYmVyLCBhbmQgZGV0ZXJtaW5lcyB3aGljaCBpdGVtcyB3aWxsIGJlIHZpc2libGUgYXQgdGhhdFxuICAgKiBpbmRleC4gVGhpcyBmdW5jdGlvbiB0aGVuIGNhbGN1bGF0ZXMgYSBjb3JyZXNwb25kaW5nIGFuaW1hdGlvbiBmcmFjdGlvbjogYVxuICAgKiBudW1iZXIgYmV0d2VlbiAwIGFuZCAxIGluZGljYXRpbmcgaG93IGZhciB0aHJvdWdoIHRoZSBzZWxlY3Rpb24gYW5pbWF0aW9uXG4gICAqIGFuIGl0ZW0gc2hvdWxkIGJlIHNob3duLCBvciBudWxsIGlmIHRoZSBpdGVtIHNob3VsZCBub3QgYmUgdmlzaWJsZSBhdCB0aGF0XG4gICAqIHNlbGVjdGlvbiBpbmRleC4gVGhlc2UgZnJhY3Rpb25zIGFyZSByZXR1cm5lZCBhcyBhbiBhcnJheSwgd2hlcmUgdGhlXG4gICAqIGFuaW1hdGlvbiBmcmFjdGlvbiBhdCBwb3NpdGlvbiBOIGNvcnJlc3BvbmRzIHRvIGhvdyBpdGVtIE4gc2hvdWxkIGJlIHNob3duLlxuICAgKi9cbiAgYW5pbWF0aW9uRnJhY3Rpb25zRm9yU2VsZWN0aW9uKGVsZW1lbnQsIHNlbGVjdGlvbikge1xuXG4gICAgY29uc3QgaXRlbXMgPSBlbGVtZW50Lml0ZW1zO1xuICAgIGlmICghaXRlbXMpIHtcbiAgICAgIHJldHVybjtcbiAgICB9XG5cbiAgICBjb25zdCBpdGVtQ291bnQgPSBpdGVtcy5sZW5ndGg7XG4gICAgY29uc3Qgc2VsZWN0aW9uV3JhcHMgPSBlbGVtZW50LnNlbGVjdGlvbldyYXBzO1xuXG4gICAgcmV0dXJuIGl0ZW1zLm1hcCgoaXRlbSwgaXRlbUluZGV4KSA9PiB7XG4gICAgICAvLyBIb3cgbWFueSBzdGVwcyBmcm9tIHRoZSBzZWxlY3Rpb24gcG9pbnQgdG8gdGhpcyBpdGVtP1xuICAgICAgY29uc3Qgc3RlcHMgPSBzdGVwc1RvSW5kZXgoaXRlbUNvdW50LCBzZWxlY3Rpb25XcmFwcywgc2VsZWN0aW9uLCBpdGVtSW5kZXgpO1xuICAgICAgLy8gVG8gY29udmVydCBzdGVwcyB0byBhbmltYXRpb24gZnJhY3Rpb246XG4gICAgICAvLyBzdGVwcyAgICAgIGFuaW1hdGlvbiBmcmFjdGlvblxuICAgICAgLy8gIDEgICAgICAgICAwICAgICAoc3RhZ2UgcmlnaHQpXG4gICAgICAvLyAgMCAgICAgICAgIDAuNSAgIChjZW50ZXIgc3RhZ2UpXG4gICAgICAvLyAtMSAgICAgICAgIDEgICAgIChzdGFnZSBsZWZ0KVxuICAgICAgY29uc3QgYW5pbWF0aW9uRnJhY3Rpb24gPSAoMSAtIHN0ZXBzKSAvIDI7XG4gICAgICByZXR1cm4gKGFuaW1hdGlvbkZyYWN0aW9uID49IDAgJiYgYW5pbWF0aW9uRnJhY3Rpb24gPD0gMSkgP1xuICAgICAgICBhbmltYXRpb25GcmFjdGlvbiA6XG4gICAgICAgIG51bGw7IC8vIE91dHNpZGUgYW5pbWF0aW9uIHJhbmdlXG4gICAgfSk7XG4gIH0sXG5cbiAgLypcbiAgICogQ2FsY3VsYXRlIHRoZSBhbmltYXRpb24gdGltaW5ncyB0aGF0IHNob3VsZCBiZSB1c2VkIHRvIHNtb290aGx5IGFuaW1hdGUgdGhlXG4gICAqIGVsZW1lbnQncyBpdGVtcyBmcm9tIG9uZSBzZWxlY3Rpb24gc3RhdGUgdG8gYW5vdGhlci5cbiAgICpcbiAgICogVGhpcyByZXR1cm5zIGFuIGFycmF5IG9mIHRpbWluZ3MsIHdoZXJlIHRoZSB0aW1pbmcgYXQgcG9zaXRpb24gTiBzaG91bGQgYmVcbiAgICogdXNlZCB0byBhbmltYXRlIGl0ZW0gTi4gSWYgYW4gaXRlbSdzIHRpbWluZyBpcyBudWxsLCB0aGVuIHRoYXQgaXRlbSBzaG91bGRcbiAgICogbm90IHRha2UgcGxhY2UgaW4gdGhlIGFuaW1hdGlvbiwgYW5kIHNob3VsZCBiZSBoaWRkZW4gaW5zdGVhZC5cbiAgICovXG4gIGVmZmVjdFRpbWluZ3NGb3JTZWxlY3Rpb25BbmltYXRpb24oZWxlbWVudCwgZnJvbVNlbGVjdGlvbiwgdG9TZWxlY3Rpb24pIHtcblxuICAgIGNvbnN0IGl0ZW1zID0gZWxlbWVudC5pdGVtcztcbiAgICBpZiAoIWl0ZW1zKSB7XG4gICAgICByZXR1cm47XG4gICAgfVxuICAgIGNvbnN0IGl0ZW1Db3VudCA9IGl0ZW1zLmxlbmd0aDtcbiAgICBjb25zdCBzZWxlY3Rpb25XcmFwcyA9IGVsZW1lbnQuc2VsZWN0aW9uV3JhcHM7XG4gICAgY29uc3QgdG9JbmRleCA9IEZyYWN0aW9uYWxTZWxlY3Rpb25NaXhpbi5oZWxwZXJzLndyYXBwZWRTZWxlY3Rpb25QYXJ0cyh0b1NlbGVjdGlvbiwgaXRlbUNvdW50LCBzZWxlY3Rpb25XcmFwcykuaW5kZXg7XG4gICAgY29uc3QgdG90YWxTdGVwcyA9IHN0ZXBzVG9JbmRleChpdGVtQ291bnQsIHNlbGVjdGlvbldyYXBzLCBmcm9tU2VsZWN0aW9uLCB0b1NlbGVjdGlvbik7XG4gICAgY29uc3QgZGlyZWN0aW9uID0gdG90YWxTdGVwcyA+PSAwID8gJ25vcm1hbCc6ICdyZXZlcnNlJztcbiAgICBjb25zdCBmaWxsID0gJ2JvdGgnO1xuICAgIGNvbnN0IHRvdGFsRHVyYXRpb24gPSBlbGVtZW50LnNlbGVjdGlvbkFuaW1hdGlvbkR1cmF0aW9uO1xuICAgIGNvbnN0IHN0ZXBEdXJhdGlvbiA9IHRvdGFsU3RlcHMgIT09IDAgP1xuICAgICAgdG90YWxEdXJhdGlvbiAqIDIgLyBNYXRoLmNlaWwoTWF0aC5hYnModG90YWxTdGVwcykpIDpcbiAgICAgIDA7ICAvLyBObyBzdGVwcyByZXF1aXJlZCwgYW5pbWF0aW9uIHdpbGwgYmUgaW5zdGFudGVub3VzLlxuXG4gICAgY29uc3QgdGltaW5ncyA9IGl0ZW1zLm1hcCgoaXRlbSwgaXRlbUluZGV4KSA9PiB7XG4gICAgICBjb25zdCBzdGVwcyA9IHN0ZXBzVG9JbmRleChpdGVtQ291bnQsIHNlbGVjdGlvbldyYXBzLCBpdGVtSW5kZXgsIHRvU2VsZWN0aW9uKTtcbiAgICAgIC8vIElmIHdlIGluY2x1ZGUgdGhpcyBpdGVtIGluIHRoZSBzdGFnZ2VyZWQgc2VxdWVuY2Ugb2YgYW5pbWF0aW9ucyB3ZSdyZVxuICAgICAgLy8gY3JlYXRpbmcsIHdoZXJlIHdvdWxkIHRoZSBpdGVtIGFwcGVhciBpbiB0aGUgc2VxdWVuY2U/XG4gICAgICBsZXQgcG9zaXRpb25JblNlcXVlbmNlID0gdG90YWxTdGVwcyAtIHN0ZXBzO1xuICAgICAgaWYgKHRvdGFsU3RlcHMgPCAwKSB7XG4gICAgICAgIHBvc2l0aW9uSW5TZXF1ZW5jZSA9IC1wb3NpdGlvbkluU2VxdWVuY2U7XG4gICAgICB9XG4gICAgICAvLyBTbywgaXMgdGhpcyBpdGVtIHJlYWxseSBpbmNsdWRlZCBpbiB0aGUgc2VxdWVuY2U/XG4gICAgICBpZiAoTWF0aC5jZWlsKHBvc2l0aW9uSW5TZXF1ZW5jZSkgPj0gMCAmJiBwb3NpdGlvbkluU2VxdWVuY2UgPD0gTWF0aC5hYnModG90YWxTdGVwcykpIHtcbiAgICAgICAgLy8gTm90ZSB0aGF0IGRlbGF5IGZvciBmaXJzdCBpdGVtIHdpbGwgYmUgbmVnYXRpdmUuIFRoYXQgd2lsbCBjYXVzZVxuICAgICAgICAvLyB0aGUgYW5pbWF0aW9uIHRvIHN0YXJ0IGhhbGZ3YXkgdGhyb3VnaCwgd2hpY2ggaXMgd2hhdCB3ZSB3YW50LlxuICAgICAgICBjb25zdCBkZWxheSA9IHN0ZXBEdXJhdGlvbiAqIChwb3NpdGlvbkluU2VxdWVuY2UgLSAxKS8yO1xuICAgICAgICBjb25zdCBlbmREZWxheSA9IGl0ZW1JbmRleCA9PT0gdG9JbmRleCA/XG4gICAgICAgICAgLXN0ZXBEdXJhdGlvbi8yIDogICAvLyBTdG9wIGhhbGZ3YXkgdGhyb3VnaC5cbiAgICAgICAgICAwOyAgICAgICAgICAgICAgLy8gUGxheSBhbmltYXRpb24gdW50aWwgZW5kLlxuICAgICAgICByZXR1cm4geyBkdXJhdGlvbjogc3RlcER1cmF0aW9uLCBkaXJlY3Rpb24sIGZpbGwsIGRlbGF5LCBlbmREZWxheSB9O1xuICAgICAgfSBlbHNlIHtcbiAgICAgICAgcmV0dXJuIG51bGw7XG4gICAgICB9XG4gICAgfSk7XG5cbiAgICByZXR1cm4gdGltaW5ncztcbiAgfVxuXG59O1xuXG5cbi8vIEtleWZyYW1lcyBmb3Igc3RhbmRhcmQgc2VsZWN0aW9uIGFuaW1hdGlvbiBlZmZlY3RzLlxubWl4aW4uc3RhbmRhcmRFZmZlY3RLZXlmcmFtZXMgPSB7XG5cbiAgLy8gU2ltcGxlIGNyb3NzZmFkZVxuICBjcm9zc2ZhZGU6IFtcbiAgICB7IG9wYWNpdHk6IDAgfSxcbiAgICB7IG9wYWNpdHk6IDEgfSxcbiAgICB7IG9wYWNpdHk6IDAgfVxuICBdLFxuXG4gIC8vIFJldmVhbCwgYXMgaWYgc2xpZGluZyB0aGUgdG9wIGNhcmQgb2ZmIGEgZGVjayBvZiBjYXJkc1xuICByZXZlYWw6IFtcbiAgICB7IHRyYW5zZm9ybTogJ3RyYW5zbGF0ZVgoMCUpJywgekluZGV4OiAwIH0sXG4gICAgeyB0cmFuc2Zvcm06ICd0cmFuc2xhdGVYKDAlKScsIHpJbmRleDogMSB9LFxuICAgIHsgdHJhbnNmb3JtOiAndHJhbnNsYXRlWCgtMTAwJSknLCB6SW5kZXg6IDIgfVxuICBdLFxuXG4gIC8vIEdvb2dsZSBQaG90b3Mtc3R5bGUgcmV2ZWFsLXdpdGgtZmFkZSBhbmltYXRpb25cbiAgcmV2ZWFsV2l0aEZhZGU6IFtcbiAgICB7IHRyYW5zZm9ybTogJ3RyYW5zbGF0ZVgoMCUpIHNjYWxlKDAuNzUpJywgb3BhY2l0eTogMCwgekluZGV4OiAwIH0sXG4gICAgeyB0cmFuc2Zvcm06ICd0cmFuc2xhdGVYKDAlKSBzY2FsZSgxLjApJywgb3BhY2l0eTogMSwgekluZGV4OiAxIH0sXG4gICAgeyB0cmFuc2Zvcm06ICd0cmFuc2xhdGVYKC0xMDAlKSBzY2FsZSgxLjApJywgb3BhY2l0eTogMSwgekluZGV4OiAyIH1cbiAgXSxcblxuICAvLyBDYXJvdXNlbCB2YXJpYW50IHdpdGggYSBiaXQgb2Ygb2ZmLXN0YWdlIGVsZW1lbnRzIHNob3dpbmdcbiAgc2hvd0FkamFjZW50OiBbXG4gICAgeyB0cmFuc2Zvcm06ICd0cmFuc2xhdGVYKDc4JSkgc2NhbGUoMC43KScsIHpJbmRleDogMCB9LFxuICAgIHsgdHJhbnNmb3JtOiAndHJhbnNsYXRlWCgwJSkgc2NhbGUoMC44MiknLCB6SW5kZXg6IDEgfSxcbiAgICB7IHRyYW5zZm9ybTogJ3RyYW5zbGF0ZVgoLTc4JSkgc2NhbGUoMC43KScsIHpJbmRleDogMCB9XG4gIF0sXG5cbiAgLy8gU2ltcGxlIHNsaWRlXG4gIHNsaWRlOiBbXG4gICAgeyB0cmFuc2Zvcm06ICd0cmFuc2xhdGVYKDEwMCUpJyB9LFxuICAgIHsgdHJhbnNmb3JtOiAndHJhbnNsYXRlWCgtMTAwJSknIH1cbiAgXSxcblxuICAvLyBTbGlkZSwgd2l0aCBhIGdhcCBiZXR3ZWVuXG4gIHNsaWRlV2l0aEdhcDogW1xuICAgIHsgdHJhbnNmb3JtOiAndHJhbnNsYXRlWCgxMTAlKScgfSxcbiAgICB7IHRyYW5zZm9ybTogJ3RyYW5zbGF0ZVgoLTExMCUpJyB9XG4gIF1cblxufTtcblxuXG4vKlxuICogU21vb3RobHkgYW5pbWF0ZSB0aGUgc2VsZWN0aW9uIGJldHdlZW4gdGhlIGluZGljYXRlZCBcImZyb21cIiBhbmQgXCJ0b1wiXG4gKiBpbmRpY2VzLiBUaGUgZm9ybWVyIGNhbiBiZSBhIGZyYWN0aW9uLCBlLmcuLCB3aGVuIHRoZSB1c2VyIHJlbGVhc2VzIGEgZmluZ2VyXG4gKiB0byBjb21wbGV0ZSBhIHRvdWNoIGRyYWcsIGFuZCB0aGUgc2VsZWN0aW9uIHdpbGwgc25hcCB0byB0aGUgY2xvc2VzdCB3aG9sZVxuICogaW5kZXguXG4gKi9cbmZ1bmN0aW9uIGFuaW1hdGVTZWxlY3Rpb24oZWxlbWVudCwgZnJvbVNlbGVjdGlvbiwgdG9TZWxlY3Rpb24pIHtcblxuICByZXNldEFuaW1hdGlvbnMoZWxlbWVudCk7XG5cbiAgLy8gQ2FsY3VsYXRlIHRoZSBhbmltYXRpb24gdGltaW5ncy5cbiAgY29uc3QgaXRlbXMgPSBlbGVtZW50Lml0ZW1zO1xuICBjb25zdCBrZXlmcmFtZXMgPSBlbGVtZW50LnNlbGVjdGlvbkFuaW1hdGlvbktleWZyYW1lcztcbiAgZWxlbWVudFtwbGF5aW5nQW5pbWF0aW9uU3ltYm9sXSA9IHRydWU7XG4gIGNvbnN0IHRpbWluZ3MgPSBtaXhpbi5oZWxwZXJzLmVmZmVjdFRpbWluZ3NGb3JTZWxlY3Rpb25BbmltYXRpb24oZWxlbWVudCwgZnJvbVNlbGVjdGlvbiwgdG9TZWxlY3Rpb24pO1xuXG4gIC8vIEZpZ3VyZSBvdXQgd2hpY2ggaXRlbSB3aWxsIGJlIHRoZSBvbmUgKmFmdGVyKiB0aGUgb25lIHdlJ3JlIHNlbGVjdGluZy5cbiAgY29uc3QgaXRlbUNvdW50ID0gaXRlbXMubGVuZ3RoO1xuICBjb25zdCBzZWxlY3Rpb25XcmFwcyA9IGVsZW1lbnQuc2VsZWN0aW9uV3JhcHM7XG4gIGNvbnN0IHNlbGVjdGlvbkluZGV4ID0gRnJhY3Rpb25hbFNlbGVjdGlvbk1peGluLmhlbHBlcnMuc2VsZWN0aW9uUGFydHModG9TZWxlY3Rpb24sIGl0ZW1Db3VudCwgc2VsZWN0aW9uV3JhcHMpLmluZGV4O1xuICBjb25zdCB0b3RhbFN0ZXBzID0gc3RlcHNUb0luZGV4KGl0ZW1Db3VudCwgc2VsZWN0aW9uV3JhcHMsIGZyb21TZWxlY3Rpb24sIHRvU2VsZWN0aW9uKTtcbiAgY29uc3QgZm9yd2FyZCA9IHRvdGFsU3RlcHMgPj0gMDtcbiAgbGV0IG5leHRVcEluZGV4ID0gc2VsZWN0aW9uSW5kZXggKyAoZm9yd2FyZCA/IDEgOiAtIDEpO1xuICBpZiAoc2VsZWN0aW9uV3JhcHMpIHtcbiAgICBuZXh0VXBJbmRleCA9IEZyYWN0aW9uYWxTZWxlY3Rpb25NaXhpbi5oZWxwZXJzLndyYXBwZWRTZWxlY3Rpb24obmV4dFVwSW5kZXgsIGl0ZW1Db3VudCk7XG4gIH0gZWxzZSBpZiAoIWlzSXRlbUluZGV4SW5Cb3VuZHMoZWxlbWVudCwgbmV4dFVwSW5kZXgpKSB7XG4gICAgbmV4dFVwSW5kZXggPSBudWxsOyAvLyBBdCBzdGFydC9lbmQgb2YgbGlzdDsgZG9uJ3QgaGF2ZSBhIG5leHQgaXRlbSB0byBzaG93LlxuICB9XG5cbiAgLy8gUGxheSB0aGUgYW5pbWF0aW9ucyB1c2luZyB0aG9zZSB0aW1pbmdzLlxuICBsZXQgbGFzdEFuaW1hdGlvbkRldGFpbHM7XG4gIHRpbWluZ3MuZm9yRWFjaCgodGltaW5nLCBpbmRleCkgPT4ge1xuICAgIGNvbnN0IGl0ZW0gPSBpdGVtc1tpbmRleF07XG4gICAgaWYgKHRpbWluZykge1xuICAgICAgc2hvd0l0ZW0oaXRlbSwgdHJ1ZSk7XG4gICAgICBjb25zdCBhbmltYXRpb24gPSBpdGVtLmFuaW1hdGUoa2V5ZnJhbWVzLCB0aW1pbmcpO1xuICAgICAgZWxlbWVudFthbmltYXRpb25TeW1ib2xdW2luZGV4XSA9IGFuaW1hdGlvbjtcbiAgICAgIGlmIChpbmRleCA9PT0gbmV4dFVwSW5kZXgpIHtcbiAgICAgICAgLy8gVGhpcyBpdGVtIHdpbGwgYmUgYW5pbWF0ZWQsIHNvIHdpbGwgYWxyZWFkeSBiZSBpbiB0aGUgZGVzaXJlZCBzdGF0ZVxuICAgICAgICAvLyBhZnRlciB0aGUgYW5pbWF0aW9uIGNvbXBsZXRlcy5cbiAgICAgICAgbmV4dFVwSW5kZXggPSBudWxsO1xuICAgICAgfVxuICAgICAgaWYgKHRpbWluZy5lbmREZWxheSAhPT0gMCkge1xuICAgICAgICAvLyBUaGlzIGlzIHRoZSBhbmltYXRpb24gZm9yIHRoZSBpdGVtIHRoYXQgd2lsbCBiZSBsZWZ0IHNlbGVjdGVkLlxuICAgICAgICAvLyBXZSB3YW50IHRvIGNsZWFuIHVwIHdoZW4gdGhpcyBhbmltYXRpb24gY29tcGxldGVzLlxuICAgICAgICBsYXN0QW5pbWF0aW9uRGV0YWlscyA9IHsgYW5pbWF0aW9uLCBpbmRleCwgdGltaW5nLCBmb3J3YXJkIH07XG4gICAgICB9XG4gICAgfSBlbHNlIHtcbiAgICAgIC8vIFRoaXMgaXRlbSBkb2Vzbid0IHBhcnRpY2lwYXRlIGluIHRoZSBhbmltYXRpb24uXG4gICAgICBzaG93SXRlbShpdGVtLCBmYWxzZSk7XG4gICAgfVxuICB9KTtcblxuICBpZiAobGFzdEFuaW1hdGlvbkRldGFpbHMgIT0gbnVsbCkge1xuICAgIC8vIEFycmFuZ2UgZm9yIGNsZWFuLXVwIHdvcmsgdG8gYmUgcGVyZm9ybWVkLlxuICAgIGxhc3RBbmltYXRpb25EZXRhaWxzLm5leHRVcEluZGV4ID0gbmV4dFVwSW5kZXg7XG4gICAgbGFzdEFuaW1hdGlvbkRldGFpbHMuYW5pbWF0aW9uLm9uZmluaXNoID0gZXZlbnQgPT4gc2VsZWN0aW9uQW5pbWF0aW9uRmluaXNoZWQoZWxlbWVudCwgbGFzdEFuaW1hdGlvbkRldGFpbHMpO1xuICAgIGVsZW1lbnRbbGFzdEFuaW1hdGlvblN5bWJvbF0gPSBsYXN0QW5pbWF0aW9uRGV0YWlscy5hbmltYXRpb247XG4gIH0gZWxzZSB7XG4gICAgLy8gU2hvdWxkbid0IGhhcHBlbiAtLSB3ZSBzaG91bGQgYWx3YXlzIGhhdmUgYXQgbGVhc3Qgb25lIGFuaW1hdGlvbi5cbiAgICBlbGVtZW50W3BsYXlpbmdBbmltYXRpb25TeW1ib2xdID0gZmFsc2U7XG4gIH1cbn1cblxuXG5mdW5jdGlvbiBnZXRBbmltYXRpb25Gb3JJdGVtSW5kZXgoZWxlbWVudCwgaW5kZXgpIHtcbiAgaWYgKGVsZW1lbnRbYW5pbWF0aW9uU3ltYm9sXSA9PSBudWxsKSB7XG4gICAgLy8gTm90IHJlYWR5IHlldDtcbiAgICByZXR1cm4gbnVsbDtcbiAgfVxuICBsZXQgYW5pbWF0aW9uID0gZWxlbWVudFthbmltYXRpb25TeW1ib2xdW2luZGV4XTtcbiAgaWYgKCFhbmltYXRpb24pIHtcbiAgICBjb25zdCBpdGVtID0gZWxlbWVudC5pdGVtc1tpbmRleF07XG4gICAgYW5pbWF0aW9uID0gaXRlbS5hbmltYXRlKGVsZW1lbnQuc2VsZWN0aW9uQW5pbWF0aW9uS2V5ZnJhbWVzLCB7XG4gICAgICBkdXJhdGlvbjogZWxlbWVudC5zZWxlY3Rpb25BbmltYXRpb25EdXJhdGlvbixcbiAgICAgIGZpbGw6ICdib3RoJ1xuICAgIH0pO1xuICAgIGFuaW1hdGlvbi5wYXVzZSgpO1xuICAgIGVsZW1lbnRbYW5pbWF0aW9uU3ltYm9sXVtpbmRleF0gPSBhbmltYXRpb247XG4gIH1cbiAgcmV0dXJuIGFuaW1hdGlvbjtcbn1cblxuZnVuY3Rpb24gaXNJdGVtSW5kZXhJbkJvdW5kcyhlbGVtZW50LCBpbmRleCkge1xuICByZXR1cm4gaW5kZXggPj0gMCAmJiBlbGVtZW50Lml0ZW1zICYmIGluZGV4IDwgZWxlbWVudC5pdGVtcy5sZW5ndGg7XG59XG5cbi8qXG4gKiBSZW5kZXIgdGhlIHNlbGVjdGlvbiBzdGF0ZSBvZiB0aGUgZWxlbWVudC5cbiAqXG4gKiBUaGlzIGNhbiBiZSB1c2VkIHRvIHJlLXJlbmRlciBhIHByZXZpb3VzIHNlbGVjdGlvbiBzdGF0ZSAoaWYgdGhlXG4gKiBzZWxlY3RlZEluZGV4IHBhcmFtIGlzIG9taXR0ZWQpLCByZW5kZXIgdGhlIHNlbGVjdGlvbiBpbnN0YW50bHkgYXQgYSBnaXZlblxuICogd2hvbGUgb3IgZnJhY3Rpb25hbCBzZWxlY3Rpb24gaW5kZXgsIG9yIGFuaW1hdGUgdG8gYSBnaXZlbiBzZWxlY3Rpb24gaW5kZXguXG4gKlxuICogVGhlcmUgYXJlIHNldmVyYWwgZGlzdGluY3Qgc2NlbmFyaW9zIHdlIG5lZWQgdG8gY292ZXI6XG4gKlxuICogMS4gSW5pdGlhbCBwb3NpdGlvbmluZywgb3IgcmVwb3NpdGlvbmluZyBhZnRlciBjaGFuZ2luZyBhIHByb3BlcnR5IGxpa2VcbiAqICAgIHNlbGVjdGlvbkFuaW1hdGlvbktleWZyYW1lcyB0aGF0IGFmZmVjdHMgcmVuZGVyaW5nLlxuICogMi4gQW5pbWF0ZSBvbiBzZWxlY3RlZEluZGV4IGNoYW5nZS4gVGhpcyBzaG91bGQgb3ZlcnJpZGUgYW55IGFuaW1hdGlvbi9zd2lwZVxuICogICAgYWxyZWFkeSBpbiBwcm9ncmVzcy5cbiAqIDMuIEluc3RhbnRseSByZW5kZXIgdGhlIGN1cnJlbnQgcG9zaXRpb24gb2YgYSBkcmFnIG9wZXJhdGlvbiBpbiBwcm9ncmVzcy5cbiAqIDQuIENvbXBsZXRlIGEgZHJhZyBvcGVyYXRpb24uIElmIHRoZSBkcmFnIHdhc24ndCBmYXIgZW5vdWdoIHRvIGFmZmVjdFxuICogICAgc2VsZWN0aW9uLCB3ZSdsbCBqdXN0IGJlIHJlc3RvcmluZyB0aGUgc2VsZWN0ZWRGcmFjdGlvbiB0byAwLlxuICpcbiAqIElmIHRoZSBsaXN0IGRvZXMgbm90IHdyYXAsIGFueSBzZWxlY3Rpb24gcG9zaXRpb24gb3V0c2lkZSB0aGUgbGlzdCdzIGJvdW5kc1xuICogd2lsbCBiZSBkYW1wZWQgdG8gcHJvZHVjZSBhIHZpc3VhbCBlZmZlY3Qgb2YgdGVuc2lvbi5cbiAqL1xuZnVuY3Rpb24gcmVuZGVyU2VsZWN0aW9uKGVsZW1lbnQsIHNlbGVjdGVkSW5kZXg9ZWxlbWVudC5zZWxlY3RlZEluZGV4LCBzZWxlY3RlZEZyYWN0aW9uPWVsZW1lbnQuc2VsZWN0ZWRGcmFjdGlvbikge1xuICBjb25zdCBpdGVtQ291bnQgPSBlbGVtZW50Lml0ZW1zID8gZWxlbWVudC5pdGVtcy5sZW5ndGggOiAwO1xuICBpZiAoaXRlbUNvdW50ID09PSAwKSB7XG4gICAgLy8gTm90aGluZyB0byByZW5kZXIuXG4gICAgcmV0dXJuO1xuICB9XG4gIGlmIChzZWxlY3RlZEluZGV4IDwgMCkge1xuICAgIC8vIFRPRE86IEhhbmRsZSBubyBzZWxlY3Rpb24uXG4gICAgcmV0dXJuO1xuICB9XG4gIGxldCBzZWxlY3Rpb24gPSBzZWxlY3RlZEluZGV4ICsgc2VsZWN0ZWRGcmFjdGlvbjtcbiAgaWYgKGVsZW1lbnQuc2VsZWN0aW9uV3JhcHMpIHtcbiAgICAvLyBBcHBseSB3cmFwcGluZyB0byBlbnN1cmUgY29uc2lzdGVudCByZXByZXNlbnRhdGlvbiBvZiBzZWxlY3Rpb24uXG4gICAgc2VsZWN0aW9uID0gRnJhY3Rpb25hbFNlbGVjdGlvbk1peGluLmhlbHBlcnMud3JhcHBlZFNlbGVjdGlvbihzZWxlY3Rpb24sIGl0ZW1Db3VudCk7XG4gIH0gZWxzZSB7XG4gICAgLy8gQXBwbHkgZGFtcGluZyBpZiBuZWNlc3NhcnkuXG4gICAgc2VsZWN0aW9uID0gRnJhY3Rpb25hbFNlbGVjdGlvbk1peGluLmhlbHBlcnMuZGFtcGVkU2VsZWN0aW9uKHNlbGVjdGlvbiwgaXRlbUNvdW50KTtcbiAgfVxuICBjb25zdCBwcmV2aW91c1NlbGVjdGlvbiA9IGVsZW1lbnRbcHJldmlvdXNTZWxlY3Rpb25TeW1ib2xdO1xuICAvLyBUT0RPOiBJZiBhbiBpdGVtIGNoYW5nZXMgcG9zaXRpb24gaW4gdGhlIERPTSwgd2UgZW5kIHVwIGFuaW1hdGluZyBmcm9tXG4gIC8vIGl0cyBvbGQgaW5kZXggdG8gaXRzIG5ldyBpbmRleCwgYnV0IHdlIHJlYWxseSBkb24ndCB3YW50IHRvIGFuaW1hdGUgYXQgYWxsLlxuICBpZiAoIWVsZW1lbnRbc3ltYm9scy5kcmFnZ2luZ10gJiYgcHJldmlvdXNTZWxlY3Rpb24gIT0gbnVsbCAmJlxuICAgICAgcHJldmlvdXNTZWxlY3Rpb24gIT09IHNlbGVjdGlvbikge1xuICAgIC8vIEFuaW1hdGUgc2VsZWN0aW9uIGZyb20gcHJldmlvdXMgc3RhdGUgdG8gbmV3IHN0YXRlLlxuICAgIGFuaW1hdGVTZWxlY3Rpb24oZWxlbWVudCwgcHJldmlvdXNTZWxlY3Rpb24sIHNlbGVjdGlvbik7XG4gIH0gZWxzZSBpZiAoc2VsZWN0ZWRGcmFjdGlvbiA9PT0gMCAmJiBlbGVtZW50W3BsYXlpbmdBbmltYXRpb25TeW1ib2xdKSB7XG4gICAgLy8gQWxyZWFkeSBpbiBwcm9jZXNzIG9mIGFuaW1hdGluZyB0byBmcmFjdGlvbiAwLiBEdXJpbmcgdGhhdCBwcm9jZXNzLFxuICAgIC8vIGlnbm9yZSBzdWJzZXF1ZW50IGF0dGVtcHRzIHRvIHJlbmRlclNlbGVjdGlvbiB0byBmcmFjdGlvbiAwLlxuICAgIHJldHVybjtcbiAgfSBlbHNlIHtcbiAgICAvLyBSZW5kZXIgY3VycmVudCBzZWxlY3Rpb24gc3RhdGUgaW5zdGFudGx5LlxuICAgIHJlbmRlclNlbGVjdGlvbkluc3RhbnRseShlbGVtZW50LCBzZWxlY3Rpb24pO1xuICB9XG4gIGVsZW1lbnRbcHJldmlvdXNTZWxlY3Rpb25TeW1ib2xdID0gc2VsZWN0aW9uO1xufVxuXG4vKlxuICogSW5zdGFudGx5IHJlbmRlciAoZG9uJ3QgYW5pbWF0ZSkgdGhlIGVsZW1lbnQncyBpdGVtcyBhdCB0aGUgZ2l2ZW4gd2hvbGUgb3JcbiAqIGZyYWN0aW9uYWwgc2VsZWN0aW9uIGluZGV4LlxuICovXG5mdW5jdGlvbiByZW5kZXJTZWxlY3Rpb25JbnN0YW50bHkoZWxlbWVudCwgdG9TZWxlY3Rpb24pIHtcbiAgaWYgKGVsZW1lbnRbcmVzZXRBbmltYXRpb25zT25OZXh0UmVuZGVyU3ltYm9sXSkge1xuICAgIHJlc2V0QW5pbWF0aW9ucyhlbGVtZW50KTtcbiAgICBlbGVtZW50W3Jlc2V0QW5pbWF0aW9uc09uTmV4dFJlbmRlclN5bWJvbF0gPSBmYWxzZTtcbiAgfVxuICBjb25zdCBhbmltYXRpb25GcmFjdGlvbnMgPSBtaXhpbi5oZWxwZXJzLmFuaW1hdGlvbkZyYWN0aW9uc0ZvclNlbGVjdGlvbihlbGVtZW50LCB0b1NlbGVjdGlvbik7XG4gIGFuaW1hdGlvbkZyYWN0aW9ucy5tYXAoKGFuaW1hdGlvbkZyYWN0aW9uLCBpbmRleCkgPT4ge1xuICAgIGNvbnN0IGl0ZW0gPSBlbGVtZW50Lml0ZW1zW2luZGV4XTtcbiAgICBpZiAoYW5pbWF0aW9uRnJhY3Rpb24gIT0gbnVsbCkge1xuICAgICAgc2hvd0l0ZW0oaXRlbSwgdHJ1ZSk7XG4gICAgICBzZXRBbmltYXRpb25GcmFjdGlvbihlbGVtZW50LCBpbmRleCwgYW5pbWF0aW9uRnJhY3Rpb24pO1xuICAgIH0gZWxzZSB7XG4gICAgICBzaG93SXRlbShpdGVtLCBmYWxzZSk7XG4gICAgfVxuICB9KTtcbn1cblxuLypcbiAqIFdlIG1haW50YWluIGFuIGFycmF5IGNvbnRhaW5pbmcgYW4gYW5pbWF0aW9uIHBlciBpdGVtLiBUaGlzIGlzIHVzZWQgZm9yIHR3b1xuICogcmVhc29uczpcbiAqXG4gKiAqIER1cmluZyBhIGRyYWcgb3BlcmF0aW9uLCB3ZSB3YW50IHRvIGJlIGFibGUgdG8gcmV1c2UgYW5pbWF0aW9ucyBiZXR3ZWVuXG4gKiAgIGRyYWcgdXBkYXRlcy5cbiAqICogV2hlbiBhIHNlbGVjdGlvbiBhbmltYXRpb24gY29tcGxldGVzLCB3ZSBuZWVkIHRvIGJlIGFibGUgdG8gbGVhdmUgdGhlXG4gKiAgIHZpc2liaWxlIGl0ZW1zIGluIGEgcGF1c2VkIHN0YXRlLiBMYXRlciwgd2UnbGwgd2FudCB0byBiZSBhYmxlIHRvIGNsZWFuIHVwXG4gKiAgIHRob3NlIGFuaW1hdGlvbnMuXG4gKlxuICogTm90ZSB0aGF0IHRoaXMgYXJyYXkgaXMgc3BhcnNlOiBpdCB3aWxsIG9ubHkgaG9sZCB1cCBmcm9tIDDigJMzIGFuaW1hdGlvbnMgYXRcbiAqIGFueSBnaXZlbiBwb2ludC5cbiAqL1xuZnVuY3Rpb24gcmVzZXRBbmltYXRpb25zKGVsZW1lbnQpIHtcbiAgY29uc3QgYW5pbWF0aW9ucyA9IGVsZW1lbnRbYW5pbWF0aW9uU3ltYm9sXTtcbiAgaWYgKGFuaW1hdGlvbnMpIHtcbiAgICAvLyBDYW5jZWwgZXhpc3RpbmcgYW5pbWF0aW9ucyB0byByZW1vdmUgdGhlIGVmZmVjdHMgdGhleSdyZSBhcHBseWluZy5cbiAgICBhbmltYXRpb25zLmZvckVhY2goKGFuaW1hdGlvbiwgaW5kZXgpID0+IHtcbiAgICAgIGlmIChhbmltYXRpb24pIHtcbiAgICAgICAgYW5pbWF0aW9uLmNhbmNlbCgpO1xuICAgICAgICBhbmltYXRpb25zW2luZGV4XSA9IG51bGw7XG4gICAgICB9XG4gICAgfSk7XG4gIH1cbiAgY29uc3QgaXRlbUNvdW50ID0gZWxlbWVudC5pdGVtcyA/IGVsZW1lbnQuaXRlbXMubGVuZ3RoIDogMDtcbiAgaWYgKCFhbmltYXRpb25zIHx8IGFuaW1hdGlvbnMubGVuZ3RoICE9PSBpdGVtQ291bnQpIHtcbiAgICAvLyBIYXZlbid0IGFuaW1hdGVkIGJlZm9yZSB3aXRoIHRoaXMgbnVtYmVyIG9mIGl0ZW1zOyAocmUpY3JlYXRlIGFycmF5LlxuICAgIGVsZW1lbnRbYW5pbWF0aW9uU3ltYm9sXSA9IG5ldyBBcnJheShpdGVtQ291bnQpO1xuICB9XG59XG5cbi8qXG4gKiBUaGUgbGFzdCBhbmltYXRpb24gaW4gb3VyIHNlbGVjdGlvbiBhbmltYXRpb24gaGFzIGNvbXBsZXRlZC4gQ2xlYW4gdXAuXG4gKi9cbmZ1bmN0aW9uIHNlbGVjdGlvbkFuaW1hdGlvbkZpbmlzaGVkKGVsZW1lbnQsIGRldGFpbHMpIHtcblxuICAvLyBXaGVuIHRoZSBsYXN0IGFuaW1hdGlvbiBjb21wbGV0ZXMsIHNob3cgdGhlIG5leHQgaXRlbSBpbiB0aGUgZGlyZWN0aW9uXG4gIC8vIHdlJ3JlIGdvaW5nLiBXYWl0aW5nIHRvIHRoYXQgdW50aWwgdGhpcyBwb2ludCBpcyBhIGJpdCBvZiBhIGhhY2sgdG8gYXZvaWRcbiAgLy8gaGF2aW5nIGEgbmV4dCBpdGVtIHRoYXQncyBoaWdoZXIgaW4gdGhlIG5hdHVyYWwgei1vcmRlciBvYnNjdXJlIG90aGVyIGl0ZW1zXG4gIC8vIGR1cmluZyBhbmltYXRpb24uXG4gIGNvbnN0IG5leHRVcEluZGV4ID0gZGV0YWlscy5uZXh0VXBJbmRleDtcbiAgaWYgKG5leHRVcEluZGV4ICE9IG51bGwpIHtcbiAgICBpZiAoZWxlbWVudFthbmltYXRpb25TeW1ib2xdW25leHRVcEluZGV4XSkge1xuICAgICAgLy8gQ2FuY2VsIGV4aXN0aW5nIHNlbGVjdGlvbiBhbmltYXRpb24gc28gd2UgY2FuIGNvbnN0cnVjdCBhIG5ldyBvbmUuXG4gICAgICBlbGVtZW50W2FuaW1hdGlvblN5bWJvbF1bbmV4dFVwSW5kZXhdLmNhbmNlbCgpO1xuICAgICAgZWxlbWVudFthbmltYXRpb25TeW1ib2xdW25leHRVcEluZGV4XSA9IG51bGw7XG4gICAgfVxuICAgIGNvbnN0IGFuaW1hdGlvbkZyYWN0aW9uID0gZGV0YWlscy5mb3J3YXJkID8gMCA6IDE7XG4gICAgc2V0QW5pbWF0aW9uRnJhY3Rpb24oZWxlbWVudCwgbmV4dFVwSW5kZXgsIGFuaW1hdGlvbkZyYWN0aW9uKTtcbiAgICBzaG93SXRlbShlbGVtZW50Lml0ZW1zW25leHRVcEluZGV4XSwgdHJ1ZSk7XG4gIH1cblxuICBlbGVtZW50W2xhc3RBbmltYXRpb25TeW1ib2xdLm9uZmluaXNoID0gbnVsbDtcbiAgZWxlbWVudFtwbGF5aW5nQW5pbWF0aW9uU3ltYm9sXSA9IGZhbHNlO1xufVxuXG4vKlxuICogUGF1c2UgdGhlIGluZGljYXRlZCBhbmltYXRpb24gYW5kIGhhdmUgaXQgc2hvdyB0aGUgYW5pbWF0aW9uIGF0IHRoZSBnaXZlblxuICogZnJhY3Rpb24gKGJldHdlZW4gMCBhbmQgMSkgb2YgdGhlIHdheSB0aHJvdWdoIHRoZSBhbmltYXRpb24uXG4gKi9cbmZ1bmN0aW9uIHNldEFuaW1hdGlvbkZyYWN0aW9uKGVsZW1lbnQsIGl0ZW1JbmRleCwgZnJhY3Rpb24pIHtcbiAgY29uc3QgYW5pbWF0aW9uID0gZ2V0QW5pbWF0aW9uRm9ySXRlbUluZGV4KGVsZW1lbnQsIGl0ZW1JbmRleCk7XG4gIGlmIChhbmltYXRpb24pIHtcbiAgICBjb25zdCBkdXJhdGlvbiA9IGVsZW1lbnQuc2VsZWN0aW9uQW5pbWF0aW9uRHVyYXRpb247XG4gICAgaWYgKGR1cmF0aW9uKSB7XG4gICAgICBhbmltYXRpb24uY3VycmVudFRpbWUgPSBmcmFjdGlvbiAqIGR1cmF0aW9uO1xuICAgIH1cbiAgfVxufVxuXG5mdW5jdGlvbiBzaG93SXRlbShpdGVtLCBmbGFnKSB7XG4gIGl0ZW0uc3R5bGUudmlzaWJpbGl0eSA9IGZsYWcgPyAndmlzaWJsZScgOiAnaGlkZGVuJztcbn1cblxuLypcbiAqIEZpZ3VyZSBvdXQgaG93IG1hbnkgc3RlcHMgaXQgd2lsbCB0YWtlIHRvIGdvIGZyb20gZnJvbVNlbGVjdGlvbiB0b1xuICogdG9TZWxlY3Rpb24uIFRvIGdvIGZyb20gaXRlbSAzIHRvIGl0ZW0gNCBpcyBvbmUgc3RlcC5cbiAqXG4gKiBJZiB3cmFwcGluZyBpcyBhbGxvd2VkLCB0aGVuIGdvaW5nIGZyb20gdGhlIGxhc3QgaXRlbSB0byB0aGUgZmlyc3Qgd2lsbCB0YWtlXG4gKiBvbmUgc3RlcCAoZm9yd2FyZCksIGFuZCBnb2luZyBmcm9tIHRoZSBmaXJzdCBpdGVtIHRvIHRoZSBsYXN0IHdpbGwgdGFrZSBvbmVcbiAqIHN0ZXAgKGJhY2t3YXJkKS5cbiAqL1xuZnVuY3Rpb24gc3RlcHNUb0luZGV4KGxlbmd0aCwgYWxsb3dXcmFwLCBmcm9tU2VsZWN0aW9uLCB0b1NlbGVjdGlvbikge1xuICBsZXQgc3RlcHMgPSB0b1NlbGVjdGlvbiAtIGZyb21TZWxlY3Rpb247XG4gIC8vIFdyYXBwaW5nIG9ubHkga2lja3MgaW4gd2hlbiBsaXN0IGhhcyBtb3JlIHRoYW4gMSBpdGVtLlxuICBpZiAoYWxsb3dXcmFwICYmIGxlbmd0aCA+IDEpIHtcbiAgICBjb25zdCB3cmFwU3RlcHMgPSBsZW5ndGggLSBNYXRoLmFicyhzdGVwcyk7XG4gICAgaWYgKHdyYXBTdGVwcyA8PSAxKSB7XG4gICAgICAvLyBTcGVjaWFsIGNhc2VcbiAgICAgIHN0ZXBzID0gc3RlcHMgPCAwID9cbiAgICAgICAgd3JhcFN0ZXBzIDogICAvLyBXcmFwIGZvcndhcmQgZnJvbSBsYXN0IGl0ZW0gdG8gZmlyc3QuXG4gICAgICAgIC13cmFwU3RlcHM7ICAgLy8gV3JhcCBiYWNrd2FyZCBmcm9tIGZpcnN0IGl0ZW0gdG8gbGFzdC5cbiAgICB9XG4gIH1cbiAgcmV0dXJuIHN0ZXBzO1xufVxuIiwiaW1wb3J0IHN5bWJvbHMgZnJvbSAnLi9zeW1ib2xzJztcblxuXG4vLyBVc2VkIHRvIGFzc2lnbiB1bmlxdWUgSURzIHRvIGl0ZW0gZWxlbWVudHMgd2l0aG91dCBJRHMuXG5sZXQgaWRDb3VudCA9IDA7XG5cblxuLyogRXhwb3J0ZWQgZnVuY3Rpb24gZXh0ZW5kcyBhIGJhc2UgY2xhc3Mgd2l0aCBTZWxlY3Rpb25BcmlhQWN0aXZlLiAqL1xuZXhwb3J0IGRlZmF1bHQgKGJhc2UpID0+IHtcblxuICAvKipcbiAgICogTWl4aW4gd2hpY2ggdHJlYXRzIHRoZSBzZWxlY3RlZCBpdGVtIGluIGEgbGlzdCBhcyB0aGUgYWN0aXZlIGl0ZW0gaW4gQVJJQVxuICAgKiBhY2Nlc3NpYmlsaXR5IHRlcm1zLlxuICAgKlxuICAgKiBIYW5kbGluZyBBUklBIHNlbGVjdGlvbiBzdGF0ZSBwcm9wZXJseSBpcyBhY3R1YWxseSBxdWl0ZSBjb21wbGV4OlxuICAgKlxuICAgKiAqIFRoZSBpdGVtcyBpbiB0aGUgbGlzdCBuZWVkIHRvIGJlIGluZGljYXRlZCBhcyBwb3NzaWJsZSBpdGVtcyB2aWEgYW4gQVJJQVxuICAgKiAgIGByb2xlYCBhdHRyaWJ1dGUgdmFsdWUgc3VjaCBhcyBcIm9wdGlvblwiLlxuICAgKiAqIFRoZSBzZWxlY3RlZCBpdGVtIG5lZWQgdG8gYmUgbWFya2VkIGFzIHNlbGVjdGVkIGJ5IHNldHRpbmcgdGhlIGl0ZW0nc1xuICAgKiAgIGBhcmlhLXNlbGVjdGVkYCBhdHRyaWJ1dGUgdG8gdHJ1ZSAqYW5kKiB0aGUgb3RoZXIgaXRlbXMgbmVlZCBiZSBtYXJrZWQgYXNcbiAgICogICAqbm90KiBzZWxlY3RlZCBieSBzZXR0aW5nIGBhcmlhLXNlbGVjdGVkYCB0byBmYWxzZS5cbiAgICogKiBUaGUgb3V0ZXJtb3N0IGVsZW1lbnQgd2l0aCB0aGUga2V5Ym9hcmQgZm9jdXMgbmVlZHMgdG8gaGF2ZSBhdHRyaWJ1dGVzXG4gICAqICAgc2V0IG9uIGl0IHNvIHRoYXQgdGhlIHNlbGVjdGlvbiBpcyBrbm93YWJsZSBhdCB0aGUgbGlzdCBsZXZlbCB2aWEgdGhlXG4gICAqICAgYGFyaWEtYWN0aXZlZGVzY2VuZGFudGAgYXR0cmlidXRlLlxuICAgKiAqIFVzZSBvZiBgYXJpYS1hY3RpdmVkZXNjZW5kYW50YCBpbiB0dXJuIHJlcXVpcmVzIHRoYXQgYWxsIGl0ZW1zIGluIHRoZVxuICAgKiAgIGxpc3QgaGF2ZSBJRCBhdHRyaWJ1dGVzIGFzc2lnbmVkIHRvIHRoZW0uXG4gICAqXG4gICAqIFRoaXMgbWl4aW4gdHJpZXMgdG8gYWRkcmVzcyBhbGwgb2YgdGhlIGFib3ZlIHJlcXVpcmVtZW50cy4gVG8gdGhhdCBlbmQsXG4gICAqIHRoaXMgbWl4aW4gd2lsbCBhc3NpZ24gZ2VuZXJhdGVkIElEcyB0byBhbnkgaXRlbSB0aGF0IGRvZXNuJ3QgYWxyZWFkeSBoYXZlXG4gICAqIGFuIElELlxuICAgKlxuICAgKiBBUklBIHJlbGllcyBvbiBlbGVtZW50cyB0byBwcm92aWRlIGByb2xlYCBhdHRyaWJ1dGVzLiBUaGlzIG1peGluIHdpbGwgYXBwbHlcbiAgICogYSBkZWZhdWx0IHJvbGUgb2YgXCJsaXN0Ym94XCIgb24gdGhlIG91dGVyIGxpc3QgaWYgaXQgZG9lc24ndCBhbHJlYWR5IGhhdmUgYW5cbiAgICogZXhwbGljaXQgcm9sZS4gU2ltaWxhcmx5LCB0aGlzIG1peGluIHdpbGwgYXBwbHkgYSBkZWZhdWx0IHJvbGUgb2YgXCJvcHRpb25cIlxuICAgKiB0byBhbnkgbGlzdCBpdGVtIHRoYXQgZG9lcyBub3QgYWxyZWFkeSBoYXZlIGEgcm9sZSBzcGVjaWZpZWQuXG4gICAqXG4gICAqIFRoaXMgbWl4aW4gZXhwZWN0cyBhIHNldCBvZiBtZW1iZXJzIHRoYXQgbWFuYWdlIHRoZSBzdGF0ZSBvZiB0aGUgc2VsZWN0aW9uOlxuICAgKiBgW3N5bWJvbHMuaXRlbVNlbGVjdGVkXWAsIGBpdGVtQWRkZWRgLCBhbmQgYHNlbGVjdGVkSW5kZXhgLiBZb3UgY2FuXG4gICAqIHN1cHBseSB0aGVzZSB5b3Vyc2VsZiwgb3IgZG8gc28gdmlhXG4gICAqIFtTaW5nbGVTZWxlY3Rpb25NaXhpbl0oU2luZ2xlU2VsZWN0aW9uTWl4aW4ubWQpLlxuICAgKi9cbiAgY2xhc3MgU2VsZWN0aW9uQXJpYUFjdGl2ZSBleHRlbmRzIGJhc2Uge1xuXG4gICAgY29ubmVjdGVkQ2FsbGJhY2soKSB7XG4gICAgICBpZiAoc3VwZXIuY29ubmVjdGVkQ2FsbGJhY2spIHsgc3VwZXIuY29ubmVjdGVkQ2FsbGJhY2soKTsgfVxuICAgICAgLy8gU2V0IGRlZmF1bHQgQVJJQSByb2xlLlxuICAgICAgaWYgKHRoaXMuZ2V0QXR0cmlidXRlKCdyb2xlJykgPT0gbnVsbCAmJiB0aGlzW3N5bWJvbHMuZGVmYXVsdHNdLnJvbGUpIHtcbiAgICAgICAgdGhpcy5zZXRBdHRyaWJ1dGUoJ3JvbGUnLCB0aGlzW3N5bWJvbHMuZGVmYXVsdHNdLnJvbGUpO1xuICAgICAgfVxuICAgIH1cblxuICAgIGdldCBbc3ltYm9scy5kZWZhdWx0c10oKSB7XG4gICAgICBjb25zdCBkZWZhdWx0cyA9IHN1cGVyW3N5bWJvbHMuZGVmYXVsdHNdIHx8IHt9O1xuICAgICAgZGVmYXVsdHMucm9sZSA9ICdsaXN0Ym94JztcbiAgICAgIHJldHVybiBkZWZhdWx0cztcbiAgICB9XG5cbiAgICBbc3ltYm9scy5pdGVtQWRkZWRdKGl0ZW0pIHtcbiAgICAgIGlmIChzdXBlcltzeW1ib2xzLml0ZW1BZGRlZF0pIHsgc3VwZXJbc3ltYm9scy5pdGVtQWRkZWRdKGl0ZW0pOyB9XG5cbiAgICAgIGlmICghaXRlbS5nZXRBdHRyaWJ1dGUoJ3JvbGUnKSkge1xuICAgICAgICAvLyBBc3NpZ24gYSBkZWZhdWx0IEFSSUEgcm9sZS5cbiAgICAgICAgaXRlbS5zZXRBdHRyaWJ1dGUoJ3JvbGUnLCAnb3B0aW9uJyk7XG4gICAgICB9XG5cbiAgICAgIC8vIEVuc3VyZSBlYWNoIGl0ZW0gaGFzIGFuIElEIHNvIHdlIGNhbiBzZXQgYXJpYS1hY3RpdmVkZXNjZW5kYW50IG9uIHRoZVxuICAgICAgLy8gb3ZlcmFsbCBsaXN0IHdoZW5ldmVyIHRoZSBzZWxlY3Rpb24gY2hhbmdlcy5cbiAgICAgIC8vXG4gICAgICAvLyBUaGUgSUQgd2lsbCB0YWtlIHRoZSBmb3JtIG9mIGEgYmFzZSBJRCBwbHVzIGEgdW5pcXVlIGludGVnZXIuIFRoZSBiYXNlXG4gICAgICAvLyBJRCB3aWxsIGJlIGluY29ycG9yYXRlIHRoZSBjb21wb25lbnQncyBvd24gSUQuIEUuZy4sIGlmIGEgY29tcG9uZW50IGhhc1xuICAgICAgLy8gSUQgXCJmb29cIiwgdGhlbiBpdHMgaXRlbXMgd2lsbCBoYXZlIElEcyB0aGF0IGxvb2sgbGlrZSBcIl9mb29PcHRpb24xXCIuIElmXG4gICAgICAvLyB0aGUgY29tcG5lbnQgaGFzIG5vIElEIGl0c2VsZiwgaXRzIGl0ZW1zIHdpbGwgZ2V0IElEcyB0aGF0IGxvb2sgbGlrZVxuICAgICAgLy8gXCJfb3B0aW9uMVwiLiBJdGVtIElEcyBhcmUgcHJlZml4ZWQgd2l0aCBhbiB1bmRlcnNjb3JlIHRvIGRpZmZlcmVudGlhdGVcbiAgICAgIC8vIHRoZW0gZnJvbSBtYW51YWxseS1hc3NpZ25lZCBJRHMsIGFuZCB0byBtaW5pbWl6ZSB0aGUgcG90ZW50aWFsIGZvciBJRFxuICAgICAgLy8gY29uZmxpY3RzLlxuICAgICAgaWYgKCFpdGVtLmlkKSB7XG4gICAgICAgIGNvbnN0IGJhc2VJZCA9IHRoaXMuaWQgP1xuICAgICAgICAgICAgXCJfXCIgKyB0aGlzLmlkICsgXCJPcHRpb25cIiA6XG4gICAgICAgICAgICBcIl9vcHRpb25cIjtcbiAgICAgICAgaXRlbS5pZCA9IGJhc2VJZCArIGlkQ291bnQrKztcbiAgICAgIH1cbiAgICB9XG5cbiAgICBbc3ltYm9scy5pdGVtU2VsZWN0ZWRdKGl0ZW0sIHNlbGVjdGVkKSB7XG4gICAgICBpZiAoc3VwZXJbc3ltYm9scy5pdGVtU2VsZWN0ZWRdKSB7IHN1cGVyW3N5bWJvbHMuaXRlbVNlbGVjdGVkXShpdGVtLCBzZWxlY3RlZCk7IH1cbiAgICAgIGl0ZW0uc2V0QXR0cmlidXRlKCdhcmlhLXNlbGVjdGVkJywgc2VsZWN0ZWQpO1xuICAgICAgY29uc3QgaXRlbUlkID0gaXRlbS5pZDtcbiAgICAgIGlmIChpdGVtSWQgJiYgc2VsZWN0ZWQpIHtcbiAgICAgICAgdGhpcy5zZXRBdHRyaWJ1dGUoJ2FyaWEtYWN0aXZlZGVzY2VuZGFudCcsIGl0ZW1JZCk7XG4gICAgICB9XG4gICAgfVxuXG4gICAgZ2V0IHNlbGVjdGVkSXRlbSgpIHtcbiAgICAgIHJldHVybiBzdXBlci5zZWxlY3RlZEl0ZW07XG4gICAgfVxuICAgIHNldCBzZWxlY3RlZEl0ZW0oaXRlbSkge1xuICAgICAgaWYgKCdzZWxlY3RlZEl0ZW0nIGluIGJhc2UucHJvdG90eXBlKSB7IHN1cGVyLnNlbGVjdGVkSXRlbSA9IGl0ZW07IH1cbiAgICAgIGlmIChpdGVtID09IG51bGwpIHtcbiAgICAgICAgLy8gU2VsZWN0aW9uIHdhcyByZW1vdmVkLlxuICAgICAgICB0aGlzLnJlbW92ZUF0dHJpYnV0ZSgnYXJpYS1hY3RpdmVkZXNjZW5kYW50Jyk7XG4gICAgICB9XG4gICAgfVxuXG4gIH1cblxuICByZXR1cm4gU2VsZWN0aW9uQXJpYUFjdGl2ZTtcbn07XG4iLCIvKiBFeHBvcnRlZCBmdW5jdGlvbiBleHRlbmRzIGEgYmFzZSBjbGFzcyB3aXRoIFNoYWRvd0VsZW1lbnRSZWZlcmVuY2VzLiAqL1xuZXhwb3J0IGRlZmF1bHQgKGJhc2UpID0+IHtcblxuICAvKipcbiAgICogTWl4aW4gdG8gY3JlYXRlIHJlZmVyZW5jZXMgdG8gZWxlbWVudHMgaW4gYSBjb21wb25lbnQncyBTaGFkb3cgRE9NIHN1YnRyZWUuXG4gICAqXG4gICAqIFRoaXMgYWRkcyBhIG1lbWJlciBvbiB0aGUgY29tcG9uZW50IGNhbGxlZCBgdGhpcy4kYCB0aGF0IGNhbiBiZSB1c2VkIHRvXG4gICAqIHJlZmVyZW5jZSBzaGFkb3cgZWxlbWVudHMgd2l0aCBJRHMuIEUuZy4sIGlmIGNvbXBvbmVudCdzIHNoYWRvdyBjb250YWlucyBhblxuICAgKiBlbGVtZW50IGA8YnV0dG9uIGlkPVwiZm9vXCI+YCwgdGhlbiB0aGlzIG1peGluIHdpbGwgY3JlYXRlIGEgbWVtYmVyXG4gICAqIGB0aGlzLiQuZm9vYCB0aGF0IHBvaW50cyB0byB0aGF0IGJ1dHRvbi5cbiAgICpcbiAgICogU3VjaCByZWZlcmVuY2VzIHNpbXBsaWZ5IGEgY29tcG9uZW50J3MgYWNjZXNzIHRvIGl0cyBvd24gZWxlbWVudHMuIEluXG4gICAqIGV4Y2hhbmdlLCB0aGlzIG1peGluIHRyYWRlcyBvZmYgYSBvbmUtdGltZSBjb3N0IG9mIHF1ZXJ5aW5nIGFsbCBlbGVtZW50cyBpblxuICAgKiB0aGUgc2hhZG93IHRyZWUgaW5zdGVhZCBvZiBwYXlpbmcgYW4gb25nb2luZyBjb3N0IHRvIHF1ZXJ5IGZvciBhbiBlbGVtZW50XG4gICAqIGVhY2ggdGltZSB0aGUgY29tcG9uZW50IHdhbnRzIHRvIGluc3BlY3Qgb3IgbWFuaXB1bGF0ZSBpdC5cbiAgICpcbiAgICogVGhpcyBtaXhpbiBleHBlY3RzIHRoZSBjb21wb25lbnQgdG8gZGVmaW5lIGEgU2hhZG93IERPTSBzdWJ0cmVlLiBZb3UgY2FuXG4gICAqIGNyZWF0ZSB0aGF0IHRyZWUgeW91cnNlbGYsIG9yIG1ha2UgdXNlIG9mXG4gICAqIFtTaGFkb3dUZW1wbGF0ZU1peGluXShTaGFkb3dUZW1wbGF0ZU1peGluLm1kKS5cbiAgICpcbiAgICogVGhpcyBtaXhpbiBpcyBpbnNwaXJlZCBieSBQb2x5bWVyJ3MgW2F1dG9tYXRpY1xuICAgKiBub2RlIGZpbmRpbmddKGh0dHBzOi8vd3d3LnBvbHltZXItcHJvamVjdC5vcmcvMS4wL2RvY3MvZGV2Z3VpZGUvbG9jYWwtZG9tLmh0bWwjbm9kZS1maW5kaW5nKVxuICAgKiBmZWF0dXJlLlxuICAgKi9cbiAgY2xhc3MgU2hhZG93RWxlbWVudFJlZmVyZW5jZXMgZXh0ZW5kcyBiYXNlIHtcblxuICAgIGNvbnN0cnVjdG9yKCkge1xuICAgICAgc3VwZXIoKTtcbiAgICAgIGlmICh0aGlzLnNoYWRvd1Jvb3QpIHtcbiAgICAgICAgLy8gTG9vayBmb3IgZWxlbWVudHMgaW4gdGhlIHNoYWRvdyBzdWJ0cmVlIHRoYXQgaGF2ZSBpZCBhdHRyaWJ1dGVzLlxuICAgICAgICAvLyBBbiBhbHRlcm5hdGl2ZWx5IGltcGxlbWVudGF0aW9uIG9mIHRoaXMgbWl4aW4gd291bGQgYmUgdG8ganVzdCBkZWZpbmVcbiAgICAgICAgLy8gYSB0aGlzLiQgZ2V0dGVyIHRoYXQgbGF6aWx5IGRvZXMgdGhpcyBzZWFyY2ggdGhlIGZpcnN0IHRpbWUgc29tZW9uZVxuICAgICAgICAvLyB0cmllcyB0byBhY2Nlc3MgdGhpcy4kLiBUaGF0IG1pZ2h0IGludHJvZHVjZSBzb21lIGNvbXBsZXhpdHkg4oCTIGlmIHRoZVxuICAgICAgICAvLyB0aGUgdHJlZSBjaGFuZ2VkIGFmdGVyIGl0IHdhcyBmaXJzdCBwb3B1bGF0ZWQsIHRoZSByZXN1bHQgb2ZcbiAgICAgICAgLy8gc2VhcmNoaW5nIGZvciBhIG5vZGUgbWlnaHQgYmUgc29tZXdoYXQgdW5wcmVkaWN0YWJsZS5cbiAgICAgICAgdGhpcy4kID0ge307XG4gICAgICAgIGNvbnN0IG5vZGVzV2l0aElkcyA9IHRoaXMuc2hhZG93Um9vdC5xdWVyeVNlbGVjdG9yQWxsKCdbaWRdJyk7XG4gICAgICAgIFtdLmZvckVhY2guY2FsbChub2Rlc1dpdGhJZHMsIG5vZGUgPT4ge1xuICAgICAgICAgIGNvbnN0IGlkID0gbm9kZS5nZXRBdHRyaWJ1dGUoJ2lkJyk7XG4gICAgICAgICAgdGhpcy4kW2lkXSA9IG5vZGU7XG4gICAgICAgIH0pO1xuICAgICAgfVxuICAgIH1cblxuICAgIC8qKlxuICAgICAqIFRoZSBjb2xsZWN0aW9uIG9mIHJlZmVyZW5jZXMgdG8gdGhlIGVsZW1lbnRzIHdpdGggSURzIGluIGEgY29tcG9uZW50J3NcbiAgICAgKiBTaGFkb3cgRE9NIHN1YnRyZWUuXG4gICAgICpcbiAgICAgKiBAdHlwZSB7b2JqZWN0fVxuICAgICAqIEBtZW1iZXIgJFxuICAgICAqL1xuICB9XG5cbiAgcmV0dXJuIFNoYWRvd0VsZW1lbnRSZWZlcmVuY2VzO1xufTtcbiIsImltcG9ydCBzeW1ib2xzIGZyb20gJy4uL3NyYy9zeW1ib2xzJztcblxuXG4vKiBFeHBvcnRlZCBmdW5jdGlvbiBleHRlbmRzIGEgYmFzZSBjbGFzcyB3aXRoIFNoYWRvd1RlbXBsYXRlLiAqL1xuZXhwb3J0IGRlZmF1bHQgKGJhc2UpID0+IHtcblxuICAvKipcbiAgICogTWl4aW4gZm9yIHN0YW1waW5nIGEgdGVtcGxhdGUgaW50byBhIFNoYWRvdyBET00gc3VidHJlZSB1cG9uIGNvbXBvbmVudFxuICAgKiBpbnN0YW50aWF0aW9uLlxuICAgKlxuICAgKiBUbyB1c2UgdGhpcyBtaXhpbiwgZGVmaW5lIGEgYHRlbXBsYXRlYCBwcm9wZXJ0eSBhcyBhIHN0cmluZyBvciBIVE1MXG4gICAqIGA8dGVtcGxhdGU+YCBlbGVtZW50OlxuICAgKlxuICAgKiAgICAgY2xhc3MgTXlFbGVtZW50IGV4dGVuZHMgU2hhZG93VGVtcGxhdGVNaXhpbihIVE1MRWxlbWVudCkge1xuICAgKiAgICAgICBnZXQgW3N5bWJvbHMudGVtcGxhdGVdKCkge1xuICAgKiAgICAgICAgIHJldHVybiBgSGVsbG8sIDxlbT53b3JsZDwvZW0+LmA7XG4gICAqICAgICAgIH1cbiAgICogICAgIH1cbiAgICpcbiAgICogV2hlbiB5b3VyIGNvbXBvbmVudCBjbGFzcyBpcyBpbnN0YW50aWF0ZWQsIGEgc2hhZG93IHJvb3Qgd2lsbCBiZSBjcmVhdGVkIG9uXG4gICAqIHRoZSBpbnN0YW5jZSwgYW5kIHRoZSBjb250ZW50cyBvZiB0aGUgdGVtcGxhdGUgd2lsbCBiZSBjbG9uZWQgaW50byB0aGVcbiAgICogc2hhZG93IHJvb3QuIElmIHlvdXIgY29tcG9uZW50IGRvZXMgbm90IGRlZmluZSBhIGB0ZW1wbGF0ZWAgcHJvcGVydHksIHRoaXNcbiAgICogbWl4aW4gaGFzIG5vIGVmZmVjdC5cbiAgICpcbiAgICogRm9yIHRoZSB0aW1lIGJlaW5nLCB0aGlzIGV4dGVuc2lvbiByZXRhaW5zIHN1cHBvcnQgZm9yIFNoYWRvdyBET00gdjAuIFRoYXRcbiAgICogd2lsbCBldmVudHVhbGx5IGJlIGRlcHJlY2F0ZWQgYXMgYnJvd3NlcnMgKGFuZCB0aGUgU2hhZG93IERPTSBwb2x5ZmlsbClcbiAgICogaW1wbGVtZW50IFNoYWRvdyBET00gdjEuXG4gICAqL1xuICBjbGFzcyBTaGFkb3dUZW1wbGF0ZSBleHRlbmRzIGJhc2Uge1xuXG4gICAgLypcbiAgICAgKiBJZiB0aGUgY29tcG9uZW50IGRlZmluZXMgYSB0ZW1wbGF0ZSwgYSBzaGFkb3cgcm9vdCB3aWxsIGJlIGNyZWF0ZWQgb24gdGhlXG4gICAgICogY29tcG9uZW50IGluc3RhbmNlLCBhbmQgdGhlIHRlbXBsYXRlIHN0YW1wZWQgaW50byBpdC5cbiAgICAgKi9cbiAgICBjb25zdHJ1Y3RvcigpIHtcbiAgICAgIHN1cGVyKCk7XG4gICAgICBsZXQgdGVtcGxhdGUgPSB0aGlzW3N5bWJvbHMudGVtcGxhdGVdO1xuICAgICAgLy8gVE9ETzogU2F2ZSB0aGUgcHJvY2Vzc2VkIHRlbXBsYXRlIHdpdGggdGhlIGNvbXBvbmVudCdzIGNsYXNzIHByb3RvdHlwZVxuICAgICAgLy8gc28gaXQgZG9lc24ndCBuZWVkIHRvIGJlIHByb2Nlc3NlZCB3aXRoIGV2ZXJ5IGluc3RhbnRpYXRpb24uXG4gICAgICBpZiAodGVtcGxhdGUpIHtcblxuICAgICAgICBpZiAodHlwZW9mIHRlbXBsYXRlID09PSAnc3RyaW5nJykge1xuICAgICAgICAgIC8vIFVwZ3JhZGUgcGxhaW4gc3RyaW5nIHRvIHJlYWwgdGVtcGxhdGUuXG4gICAgICAgICAgdGVtcGxhdGUgPSBjcmVhdGVUZW1wbGF0ZVdpdGhJbm5lckhUTUwodGVtcGxhdGUpO1xuICAgICAgICB9XG5cbiAgICAgICAgaWYgKHdpbmRvdy5TaGFkb3dET01Qb2x5ZmlsbCkge1xuICAgICAgICAgIHNoaW1UZW1wbGF0ZVN0eWxlcyh0ZW1wbGF0ZSwgdGhpcy5sb2NhbE5hbWUpO1xuICAgICAgICB9XG5cbiAgICAgICAgY29uc3Qgcm9vdCA9IHRoaXMuYXR0YWNoU2hhZG93KHsgbW9kZTogJ29wZW4nIH0pO1xuICAgICAgICBjb25zdCBjbG9uZSA9IGRvY3VtZW50LmltcG9ydE5vZGUodGVtcGxhdGUuY29udGVudCwgdHJ1ZSk7XG4gICAgICAgIHJvb3QuYXBwZW5kQ2hpbGQoY2xvbmUpO1xuICAgICAgfVxuICAgIH1cblxuICB9XG5cbiAgcmV0dXJuIFNoYWRvd1RlbXBsYXRlO1xufTtcblxuXG4vLyBDb252ZXJ0IGEgcGxhaW4gc3RyaW5nIG9mIEhUTUwgaW50byBhIHJlYWwgdGVtcGxhdGUgZWxlbWVudC5cbmZ1bmN0aW9uIGNyZWF0ZVRlbXBsYXRlV2l0aElubmVySFRNTChpbm5lckhUTUwpIHtcbiAgY29uc3QgdGVtcGxhdGUgPSBkb2N1bWVudC5jcmVhdGVFbGVtZW50KCd0ZW1wbGF0ZScpO1xuICAvLyBSRVZJRVc6IElzIHRoZXJlIGFuIGVhc2llciB3YXkgdG8gZG8gdGhpcz9cbiAgLy8gV2UnZCBsaWtlIHRvIGp1c3Qgc2V0IGlubmVySFRNTCBvbiB0aGUgdGVtcGxhdGUgY29udGVudCwgYnV0IHNpbmNlIGl0J3NcbiAgLy8gYSBEb2N1bWVudEZyYWdtZW50LCB0aGF0IGRvZXNuJ3Qgd29yay5cbiAgY29uc3QgZGl2ID0gZG9jdW1lbnQuY3JlYXRlRWxlbWVudCgnZGl2Jyk7XG4gIGRpdi5pbm5lckhUTUwgPSBpbm5lckhUTUw7XG4gIHdoaWxlIChkaXYuY2hpbGROb2Rlcy5sZW5ndGggPiAwKSB7XG4gICAgdGVtcGxhdGUuY29udGVudC5hcHBlbmRDaGlsZChkaXYuY2hpbGROb2Rlc1swXSk7XG4gIH1cbiAgcmV0dXJuIHRlbXBsYXRlO1xufVxuXG4vLyBJbnZva2UgYmFzaWMgc3R5bGUgc2hpbW1pbmcgd2l0aCBTaGFkb3dDU1MuXG5mdW5jdGlvbiBzaGltVGVtcGxhdGVTdHlsZXModGVtcGxhdGUsIHRhZykge1xuICB3aW5kb3cuV2ViQ29tcG9uZW50cy5TaGFkb3dDU1Muc2hpbVN0eWxpbmcodGVtcGxhdGUuY29udGVudCwgdGFnKTtcbn1cbiIsImltcG9ydCBjcmVhdGVTeW1ib2wgZnJvbSAnLi9jcmVhdGVTeW1ib2wnO1xuaW1wb3J0IHN5bWJvbHMgZnJvbSAnLi9zeW1ib2xzJztcblxuXG4vLyBTeW1ib2xzIGZvciBwcml2YXRlIGRhdGEgbWVtYmVycyBvbiBhbiBlbGVtZW50LlxuY29uc3QgY2FuU2VsZWN0TmV4dFN5bWJvbCA9IGNyZWF0ZVN5bWJvbCgnY2FuU2VsZWN0TmV4dCcpO1xuY29uc3QgY2FuU2VsZWN0UHJldmlvdXNTeW1ib2wgPSBjcmVhdGVTeW1ib2woJ2NhblNlbGVjdFByZXZpb3VzJyk7XG5jb25zdCBzZWxlY3Rpb25SZXF1aXJlZFN5bWJvbCA9IGNyZWF0ZVN5bWJvbCgnc2VsZWN0aW9uUmVxdWlyZWQnKTtcbmNvbnN0IHNlbGVjdGlvbldyYXBzU3ltYm9sID0gY3JlYXRlU3ltYm9sKCdzZWxlY3Rpb25XcmFwcycpO1xuXG4vLyBXZSB3YW50IHRvIGV4cG9zZSBib3RoIHNlbGVjdGVkSW5kZXggYW5kIHNlbGVjdGVkSXRlbSBhcyBpbmRlcGVuZGVudFxuLy8gcHJvcGVydGllcyBidXQga2VlcCB0aGVtIGluIHN5bmMuIFRoaXMgYWxsb3dzIGEgY29tcG9uZW50IHVzZXIgdG8gcmVmZXJlbmNlXG4vLyB0aGUgc2VsZWN0aW9uIGJ5IHdoYXRldmVyIG1lYW5zIGlzIG1vc3QgbmF0dXJhbCBmb3IgdGhlaXIgc2l0dWF0aW9uLlxuLy9cbi8vIFRvIGVmZmljaWVudGx5IGtlZXAgdGhlc2UgcHJvcGVydGllcyBpbiBzeW5jLCB3ZSB0cmFjayBcImV4dGVybmFsXCIgYW5kXG4vLyBcImludGVybmFsXCIgcmVmZXJlbmNlcyBmb3IgZWFjaCBwcm9wZXJ0eTpcbi8vXG4vLyBUaGUgZXh0ZXJuYWwgaW5kZXggb3IgaXRlbSBpcyB0aGUgb25lIHdlIHJlcG9ydCB0byB0aGUgb3V0c2lkZSB3b3JsZCB3aGVuXG4vLyBhc2tlZCBmb3Igc2VsZWN0aW9uLiAgV2hlbiBoYW5kbGluZyBhIGNoYW5nZSB0byBpbmRleCBvciBpdGVtLCB3ZSB1cGRhdGUgdGhlXG4vLyBleHRlcm5hbCByZWZlcmVuY2UgYXMgc29vbiBhcyBwb3NzaWJsZSwgc28gdGhhdCBpZiBhbnlvbmUgaW1tZWRpYXRlbHkgYXNrc1xuLy8gZm9yIHRoZSBjdXJyZW50IHNlbGVjdGlvbiwgdGhleSB3aWxsIHJlY2VpdmUgYSBzdGFibGUgYW5zd2VyLlxuLy9cbi8vIFRoZSBpbnRlcm5hbCBpbmRleCBvciBpdGVtIHRyYWNrcyB3aGljaGV2ZXIgaW5kZXggb3IgaXRlbSBsYXN0IHJlY2VpdmVkIHRoZVxuLy8gZnVsbCBzZXQgb2YgcHJvY2Vzc2luZy4gUHJvY2Vzc2luZyBpbmNsdWRlcyByYWlzaW5nIGEgY2hhbmdlIGV2ZW50IGZvciB0aGVcbi8vIG5ldyB2YWx1ZS4gT25jZSB3ZSd2ZSBiZWd1biB0aGF0IHByb2Nlc3NpbmcsIHdlIHN0b3JlIHRoZSBuZXcgdmFsdWUgYXMgdGhlXG4vLyBpbnRlcm5hbCB2YWx1ZSB0byBpbmRpY2F0ZSB3ZSd2ZSBoYW5kbGVkIGl0LlxuLy9cbmNvbnN0IGV4dGVybmFsU2VsZWN0ZWRJbmRleFN5bWJvbCA9IGNyZWF0ZVN5bWJvbCgnZXh0ZXJuYWxTZWxlY3RlZEluZGV4Jyk7XG5jb25zdCBleHRlcm5hbFNlbGVjdGVkSXRlbVN5bWJvbCA9IGNyZWF0ZVN5bWJvbCgnZXh0ZXJuYWxTZWxlY3RlZEl0ZW0nKTtcbmNvbnN0IGludGVybmFsU2VsZWN0ZWRJbmRleFN5bWJvbCA9IGNyZWF0ZVN5bWJvbCgnaW50ZXJuYWxTZWxlY3RlZEluZGV4Jyk7XG5jb25zdCBpbnRlcm5hbFNlbGVjdGVkSXRlbVN5bWJvbCA9IGNyZWF0ZVN5bWJvbCgnaW50ZXJuYWxTZWxlY3RlZEl0ZW0nKTtcblxuXG4vKiBFeHBvcnRlZCBmdW5jdGlvbiBleHRlbmRzIGEgYmFzZSBjbGFzcyB3aXRoIFNpbmdsZVNlbGVjdGlvbi4gKi9cbmV4cG9ydCBkZWZhdWx0IChiYXNlKSA9PiB7XG5cbiAgLyoqXG4gICAqIE1peGluIHdoaWNoIG1hbmFnZXMgc2luZ2xlLXNlbGVjdGlvbiBzZW1hbnRpY3MgZm9yIGl0ZW1zIGluIGEgbGlzdC5cbiAgICpcbiAgICogVGhpcyBtaXhpbiBleHBlY3RzIGEgY29tcG9uZW50IHRvIHByb3ZpZGUgYW4gYGl0ZW1zYCBBcnJheSBvciBOb2RlTGlzdCBvZlxuICAgKiBhbGwgZWxlbWVudHMgaW4gdGhlIGxpc3QuIEEgc3RhbmRhcmQgd2F5IHRvIGRvIHRoYXQgd2l0aCBpcyB0aGVcbiAgICogW0NvbnRlbnRJdGVtc01peGluXShDb250ZW50SXRlbXNNaXhpbi5tZCksIHdoaWNoIHRha2VzIGEgY29tcG9uZW50J3NcbiAgICogY29udGVudCAodHlwaWNhbGx5IGl0cyBkaXN0cmlidXRlZCBjaGlsZHJlbikgYXMgdGhlIHNldCBvZiBsaXN0IGl0ZW1zOyBzZWVcbiAgICogdGhhdCBtaXhpbiBmb3IgZGV0YWlscy5cbiAgICpcbiAgICogVGhpcyBtaXhpbiB0cmFja3MgYSBzaW5nbGUgc2VsZWN0ZWQgaXRlbSBpbiB0aGUgbGlzdCwgYW5kIHByb3ZpZGVzIG1lYW5zIHRvXG4gICAqIGdldCBhbmQgc2V0IHRoYXQgc3RhdGUgYnkgaXRlbSBwb3NpdGlvbiAoYHNlbGVjdGVkSW5kZXhgKSBvciBpdGVtIGlkZW50aXR5XG4gICAqIChgc2VsZWN0ZWRJdGVtYCkuIFRoZSBzZWxlY3Rpb24gY2FuIGJlIG1vdmVkIGluIHRoZSBsaXN0IHZpYSB0aGUgbWV0aG9kc1xuICAgKiBgc2VsZWN0Rmlyc3RgLCBgc2VsZWN0TGFzdGAsIGBzZWxlY3ROZXh0YCwgYW5kIGBzZWxlY3RQcmV2aW91c2AuXG4gICAqXG4gICAqIFRoaXMgbWl4aW4gZG9lcyBub3QgcHJvZHVjZSBhbnkgdXNlci12aXNpYmxlIGVmZmVjdHMgdG8gcmVwcmVzZW50XG4gICAqIHNlbGVjdGlvbi4gT3RoZXIgbWl4aW5zLCBzdWNoIGFzXG4gICAqIFtTZWxlY3Rpb25BcmlhQWN0aXZlTWl4aW5dKFNlbGVjdGlvbkFyaWFBY3RpdmVNaXhpbi5tZCksXG4gICAqIFtTZWxlY3Rpb25IaWdobGlnaHRNaXhpbl0oU2VsZWN0aW9uSGlnaGxpZ2h0TWl4aW4ubWQpIGFuZFxuICAgKiBbU2VsZWN0aW9uSW5WaWV3TWl4aW5dKFNlbGVjdGlvbkluVmlld01peGluLm1kKSwgbW9kaWZ5IHRoZSBzZWxlY3RlZCBpdGVtXG4gICAqIGluIGNvbW1vbiB3YXlzIHRvIGxldCB0aGUgdXNlciBrbm93IGEgZ2l2ZW4gaXRlbSBpcyBzZWxlY3RlZCBvciBub3RcbiAgICogc2VsZWN0ZWQuXG4gICAqL1xuICBjbGFzcyBTaW5nbGVTZWxlY3Rpb24gZXh0ZW5kcyBiYXNlIHtcblxuICAgIGNvbnN0cnVjdG9yKCkge1xuICAgICAgc3VwZXIoKTtcbiAgICAgIC8vIFNldCBkZWZhdWx0cy5cbiAgICAgIGlmICh0eXBlb2YgdGhpcy5zZWxlY3Rpb25SZXF1aXJlZCA9PT0gJ3VuZGVmaW5lZCcpIHtcbiAgICAgICAgdGhpcy5zZWxlY3Rpb25SZXF1aXJlZCA9IHRoaXNbc3ltYm9scy5kZWZhdWx0c10uc2VsZWN0aW9uUmVxdWlyZWQ7XG4gICAgICB9XG4gICAgICBpZiAodHlwZW9mIHRoaXMuc2VsZWN0aW9uV3JhcHMgPT09ICd1bmRlZmluZWQnKSB7XG4gICAgICAgIHRoaXMuc2VsZWN0aW9uV3JhcHMgPSB0aGlzW3N5bWJvbHMuZGVmYXVsdHNdLnNlbGVjdGlvbldyYXBzO1xuICAgICAgfVxuICAgIH1cblxuICAgIC8qKlxuICAgICAqIFRydWUgaWYgdGhlIHNlbGVjdGlvbiBjYW4gYmUgbW92ZWQgdG8gdGhlIG5leHQgaXRlbSwgZmFsc2UgaWYgbm90ICh0aGVcbiAgICAgKiBzZWxlY3RlZCBpdGVtIGlzIHRoZSBsYXN0IGl0ZW0gaW4gdGhlIGxpc3QpLlxuICAgICAqXG4gICAgICogQHR5cGUge2Jvb2xlYW59XG4gICAgICovXG4gICAgZ2V0IGNhblNlbGVjdE5leHQoKSB7XG4gICAgICByZXR1cm4gdGhpc1tjYW5TZWxlY3ROZXh0U3ltYm9sXTtcbiAgICB9XG4gICAgc2V0IGNhblNlbGVjdE5leHQoY2FuU2VsZWN0TmV4dCkge1xuICAgICAgY29uc3QgcHJldmlvdXNDYW5TZWxlY3ROZXh0ID0gdGhpc1tjYW5TZWxlY3ROZXh0U3ltYm9sXTtcbiAgICAgIHRoaXNbY2FuU2VsZWN0TmV4dFN5bWJvbF0gPSBjYW5TZWxlY3ROZXh0O1xuICAgICAgaWYgKCdjYW5TZWxlY3ROZXh0JyBpbiBiYXNlLnByb3RvdHlwZSkgeyBzdXBlci5jYW5TZWxlY3ROZXh0ID0gY2FuU2VsZWN0TmV4dDsgfVxuICAgICAgaWYgKGNhblNlbGVjdE5leHQgIT09IHByZXZpb3VzQ2FuU2VsZWN0TmV4dCkge1xuICAgICAgICB0aGlzLmRpc3BhdGNoRXZlbnQobmV3IEN1c3RvbUV2ZW50KCdjYW4tc2VsZWN0LW5leHQtY2hhbmdlZCcpKTtcbiAgICAgIH1cbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBUcnVlIGlmIHRoZSBzZWxlY3Rpb24gY2FuIGJlIG1vdmVkIHRvIHRoZSBwcmV2aW91cyBpdGVtLCBmYWxzZSBpZiBub3RcbiAgICAgKiAodGhlIHNlbGVjdGVkIGl0ZW0gaXMgdGhlIGZpcnN0IG9uZSBpbiB0aGUgbGlzdCkuXG4gICAgICpcbiAgICAgKiBAdHlwZSB7Ym9vbGVhbn1cbiAgICAgKi9cbiAgICBnZXQgY2FuU2VsZWN0UHJldmlvdXMoKSB7XG4gICAgICByZXR1cm4gdGhpc1tjYW5TZWxlY3RQcmV2aW91c1N5bWJvbF07XG4gICAgfVxuICAgIHNldCBjYW5TZWxlY3RQcmV2aW91cyhjYW5TZWxlY3RQcmV2aW91cykge1xuICAgICAgY29uc3QgcHJldmlvdXNDYW5TZWxlY3RQcmV2aW91cyA9IHRoaXNbY2FuU2VsZWN0UHJldmlvdXNTeW1ib2xdO1xuICAgICAgdGhpc1tjYW5TZWxlY3RQcmV2aW91c1N5bWJvbF0gPSBjYW5TZWxlY3RQcmV2aW91cztcbiAgICAgIGlmICgnY2FuU2VsZWN0UHJldmlvdXMnIGluIGJhc2UucHJvdG90eXBlKSB7IHN1cGVyLmNhblNlbGVjdFByZXZpb3VzID0gY2FuU2VsZWN0UHJldmlvdXM7IH1cbiAgICAgIGlmIChjYW5TZWxlY3RQcmV2aW91cyAhPT0gcHJldmlvdXNDYW5TZWxlY3RQcmV2aW91cykge1xuICAgICAgICB0aGlzLmRpc3BhdGNoRXZlbnQobmV3IEN1c3RvbUV2ZW50KCdjYW4tc2VsZWN0LXByZXZpb3VzLWNoYW5nZWQnKSk7XG4gICAgICB9XG4gICAgfVxuXG4gICAgZ2V0IFtzeW1ib2xzLmRlZmF1bHRzXSgpIHtcbiAgICAgIGNvbnN0IGRlZmF1bHRzID0gc3VwZXJbc3ltYm9scy5kZWZhdWx0c10gfHwge307XG4gICAgICBkZWZhdWx0cy5zZWxlY3Rpb25SZXF1aXJlZCA9IGZhbHNlO1xuICAgICAgZGVmYXVsdHMuc2VsZWN0aW9uV3JhcHMgPSBmYWxzZTtcbiAgICAgIHJldHVybiBkZWZhdWx0cztcbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBIYW5kbGUgYSBuZXcgaXRlbSBiZWluZyBhZGRlZCB0byB0aGUgbGlzdC5cbiAgICAgKlxuICAgICAqIFRoZSBkZWZhdWx0IGltcGxlbWVudGF0aW9uIG9mIHRoaXMgbWV0aG9kIHNpbXBseSBzZXRzIHRoZSBpdGVtJ3NcbiAgICAgKiBzZWxlY3Rpb24gc3RhdGUgdG8gZmFsc2UuXG4gICAgICpcbiAgICAgKiBAcGFyYW0ge0hUTUxFbGVtZW50fSBpdGVtIC0gdGhlIGl0ZW0gYmVpbmcgYWRkZWRcbiAgICAgKi9cbiAgICBbc3ltYm9scy5pdGVtQWRkZWRdKGl0ZW0pIHtcbiAgICAgIGlmIChzdXBlcltzeW1ib2xzLml0ZW1BZGRlZF0pIHsgc3VwZXJbc3ltYm9scy5pdGVtQWRkZWRdKGl0ZW0pOyB9XG4gICAgICB0aGlzW3N5bWJvbHMuaXRlbVNlbGVjdGVkXShpdGVtLCBpdGVtID09PSB0aGlzLnNlbGVjdGVkSXRlbSk7XG4gICAgfVxuXG4gICAgW3N5bWJvbHMuaXRlbXNDaGFuZ2VkXSgpIHtcbiAgICAgIGlmIChzdXBlcltzeW1ib2xzLml0ZW1zQ2hhbmdlZF0pIHsgc3VwZXJbc3ltYm9scy5pdGVtc0NoYW5nZWRdKCk7IH1cblxuICAgICAgLy8gSW4gY2FzZSBzZWxlY3RlZCBpdGVtIGNoYW5nZWQgcG9zaXRpb24gb3Igd2FzIHJlbW92ZWQuXG4gICAgICB0cmFja1NlbGVjdGVkSXRlbSh0aGlzKTtcblxuICAgICAgLy8gSW4gY2FzZSB0aGUgY2hhbmdlIGluIGl0ZW1zIGFmZmVjdGVkIHdoaWNoIG5hdmlnYXRpb25zIGFyZSBwb3NzaWJsZS5cbiAgICAgIHVwZGF0ZVBvc3NpYmxlTmF2aWdhdGlvbnModGhpcyk7XG4gICAgfVxuXG4gICAgLyoqXG4gICAgICogQXBwbHkgdGhlIGluZGljYXRlIHNlbGVjdGlvbiBzdGF0ZSB0byB0aGUgaXRlbS5cbiAgICAgKlxuICAgICAqIFRoZSBkZWZhdWx0IGltcGxlbWVudGF0aW9uIG9mIHRoaXMgbWV0aG9kIGRvZXMgbm90aGluZy4gVXNlci12aXNpYmxlXG4gICAgICogZWZmZWN0cyB3aWxsIHR5cGljYWxseSBiZSBoYW5kbGVkIGJ5IG90aGVyIG1peGlucy5cbiAgICAgKlxuICAgICAqIEBwYXJhbSB7SFRNTEVsZW1lbnR9IGl0ZW0gLSB0aGUgaXRlbSBiZWluZyBzZWxlY3RlZC9kZXNlbGVjdGVkXG4gICAgICogQHBhcmFtIHtib29sZWFufSBzZWxlY3RlZCAtIHRydWUgaWYgdGhlIGl0ZW0gaXMgc2VsZWN0ZWQsIGZhbHNlIGlmIG5vdFxuICAgICAqL1xuICAgIFtzeW1ib2xzLml0ZW1TZWxlY3RlZF0oaXRlbSwgc2VsZWN0ZWQpIHtcbiAgICAgIGlmIChzdXBlcltzeW1ib2xzLml0ZW1TZWxlY3RlZF0pIHsgc3VwZXJbc3ltYm9scy5pdGVtU2VsZWN0ZWRdKGl0ZW0sIHNlbGVjdGVkKTsgfVxuICAgIH1cblxuICAgIC8qKlxuICAgICAqIFRoZSBpbmRleCBvZiB0aGUgaXRlbSB3aGljaCBpcyBjdXJyZW50bHkgc2VsZWN0ZWQuXG4gICAgICpcbiAgICAgKiBBIGBzZWxlY3RlZEluZGV4YCBvZiAtMSBpbmRpY2F0ZXMgdGhlcmUgaXMgbm8gc2VsZWN0aW9uLiBTZXR0aW5nIHRoaXNcbiAgICAgKiBwcm9wZXJ0eSB0byAtMSB3aWxsIHJlbW92ZSBhbnkgZXhpc3Rpbmcgc2VsZWN0aW9uLlxuICAgICAqXG4gICAgICogQHR5cGUge251bWJlcn1cbiAgICAgKi9cbiAgICBnZXQgc2VsZWN0ZWRJbmRleCgpIHtcbiAgICAgIHJldHVybiB0aGlzW2V4dGVybmFsU2VsZWN0ZWRJbmRleFN5bWJvbF0gIT0gbnVsbCA/XG4gICAgICAgIHRoaXNbZXh0ZXJuYWxTZWxlY3RlZEluZGV4U3ltYm9sXSA6XG4gICAgICAgIC0xO1xuICAgIH1cbiAgICBzZXQgc2VsZWN0ZWRJbmRleChpbmRleCkge1xuICAgICAgLy8gU2VlIG5vdGVzIGF0IHRvcCBhYm91dCBpbnRlcm5hbCB2cy4gZXh0ZXJuYWwgY29waWVzIG9mIHRoaXMgcHJvcGVydHkuXG4gICAgICBjb25zdCBwcmV2aW91c1NlbGVjdGVkSW5kZXggPSB0aGlzW2ludGVybmFsU2VsZWN0ZWRJbmRleFN5bWJvbF07XG4gICAgICBsZXQgaXRlbTtcbiAgICAgIGlmIChpbmRleCAhPT0gdGhpc1tleHRlcm5hbFNlbGVjdGVkSW5kZXhTeW1ib2xdKSB7XG4gICAgICAgIC8vIFN0b3JlIHRoZSBuZXcgaW5kZXggYW5kIHRoZSBjb3JyZXNwb25kaW5nIGl0ZW0uXG4gICAgICAgIGNvbnN0IGl0ZW1zID0gdGhpcy5pdGVtcztcbiAgICAgICAgY29uc3QgaGFzSXRlbXMgPSBpdGVtcyAmJiBpdGVtcy5sZW5ndGggPiAwO1xuICAgICAgICBpZiAoIShoYXNJdGVtcyAmJiBpbmRleCA+PSAwICYmIGluZGV4IDwgaXRlbXMubGVuZ3RoKSkge1xuICAgICAgICAgIGluZGV4ID0gLTE7IC8vIE5vIGl0ZW0gYXQgdGhhdCBpbmRleC5cbiAgICAgICAgfVxuICAgICAgICB0aGlzW2V4dGVybmFsU2VsZWN0ZWRJbmRleFN5bWJvbF0gPSBpbmRleDtcbiAgICAgICAgaXRlbSA9IGhhc0l0ZW1zICYmIGluZGV4ID49IDAgPyBpdGVtc1tpbmRleF0gOiBudWxsO1xuICAgICAgICB0aGlzW2V4dGVybmFsU2VsZWN0ZWRJdGVtU3ltYm9sXSA9IGl0ZW07XG4gICAgICB9IGVsc2Uge1xuICAgICAgICBpdGVtID0gdGhpc1tleHRlcm5hbFNlbGVjdGVkSXRlbVN5bWJvbF07XG4gICAgICB9XG5cbiAgICAgIC8vIE5vdyBsZXQgc3VwZXIgZG8gYW55IHdvcmsuXG4gICAgICBpZiAoJ3NlbGVjdGVkSW5kZXgnIGluIGJhc2UucHJvdG90eXBlKSB7IHN1cGVyLnNlbGVjdGVkSW5kZXggPSBpbmRleDsgfVxuXG4gICAgICBpZiAoaW5kZXggIT09IHByZXZpb3VzU2VsZWN0ZWRJbmRleCkge1xuICAgICAgICAvLyBUaGUgc2VsZWN0ZWQgaW5kZXggY2hhbmdlZC5cbiAgICAgICAgdGhpc1tpbnRlcm5hbFNlbGVjdGVkSW5kZXhTeW1ib2xdID0gaW5kZXg7XG5cbiAgICAgICAgY29uc3QgZXZlbnQgPSBuZXcgQ3VzdG9tRXZlbnQoJ3NlbGVjdGVkLWluZGV4LWNoYW5nZWQnLCB7XG4gICAgICAgICAgZGV0YWlsOiB7XG4gICAgICAgICAgICBzZWxlY3RlZEluZGV4OiBpbmRleCxcbiAgICAgICAgICAgIHZhbHVlOiBpbmRleCAvLyBmb3IgUG9seW1lciBiaW5kaW5nLiBUT0RPOiBWZXJpZnkgc3RpbGwgbmVjZXNzYXJ5XG4gICAgICAgICAgfVxuICAgICAgICB9KTtcbiAgICAgICAgdGhpcy5kaXNwYXRjaEV2ZW50KGV2ZW50KTtcbiAgICAgIH1cblxuICAgICAgaWYgKHRoaXNbaW50ZXJuYWxTZWxlY3RlZEl0ZW1TeW1ib2xdICE9PSBpdGVtKSB7XG4gICAgICAgIC8vIFVwZGF0ZSBzZWxlY3RlZEl0ZW0gcHJvcGVydHkgc28gaXQgY2FuIGhhdmUgaXRzIG93biBlZmZlY3RzLlxuICAgICAgICB0aGlzLnNlbGVjdGVkSXRlbSA9IGl0ZW07XG4gICAgICB9XG4gICAgfVxuXG4gICAgLyoqXG4gICAgICogVGhlIGN1cnJlbnRseSBzZWxlY3RlZCBpdGVtLCBvciBudWxsIGlmIHRoZXJlIGlzIG5vIHNlbGVjdGlvbi5cbiAgICAgKlxuICAgICAqIFNldHRpbmcgdGhpcyBwcm9wZXJ0eSB0byBudWxsIGRlc2VsZWN0cyBhbnkgY3VycmVudGx5LXNlbGVjdGVkIGl0ZW0uXG4gICAgICogU2V0dGluZyB0aGlzIHByb3BlcnR5IHRvIGFuIG9iamVjdCB0aGF0IGlzIG5vdCBpbiB0aGUgbGlzdCBoYXMgbm8gZWZmZWN0LlxuICAgICAqXG4gICAgICogVE9ETzogRXZlbiBpZiBzZWxlY3Rpb25SZXF1aXJlZCwgY2FuIHN0aWxsIGV4cGxpY2l0bHkgc2V0IHNlbGVjdGVkSXRlbSB0byBudWxsLlxuICAgICAqIFRPRE86IElmIHNlbGVjdGlvblJlcXVpcmVkLCBsZWF2ZSBzZWxlY3Rpb24gYWxvbmU/XG4gICAgICpcbiAgICAgKiBAdHlwZSB7b2JqZWN0fVxuICAgICAqL1xuICAgIGdldCBzZWxlY3RlZEl0ZW0oKSB7XG4gICAgICByZXR1cm4gdGhpc1tleHRlcm5hbFNlbGVjdGVkSXRlbVN5bWJvbF0gfHwgbnVsbDtcbiAgICB9XG4gICAgc2V0IHNlbGVjdGVkSXRlbShpdGVtKSB7XG4gICAgICAvLyBTZWUgbm90ZXMgYXQgdG9wIGFib3V0IGludGVybmFsIHZzLiBleHRlcm5hbCBjb3BpZXMgb2YgdGhpcyBwcm9wZXJ0eS5cbiAgICAgIGNvbnN0IHByZXZpb3VzU2VsZWN0ZWRJdGVtID0gdGhpc1tpbnRlcm5hbFNlbGVjdGVkSXRlbVN5bWJvbF07XG4gICAgICBsZXQgaW5kZXg7XG4gICAgICBpZiAoaXRlbSAhPT0gdGhpc1tleHRlcm5hbFNlbGVjdGVkSXRlbVN5bWJvbF0pIHtcbiAgICAgICAgLy8gU3RvcmUgaXRlbSBhbmQgbG9vayB1cCBjb3JyZXNwb25kaW5nIGluZGV4LlxuICAgICAgICBjb25zdCBpdGVtcyA9IHRoaXMuaXRlbXM7XG4gICAgICAgIGNvbnN0IGhhc0l0ZW1zID0gaXRlbXMgJiYgaXRlbXMubGVuZ3RoID4gMDtcbiAgICAgICAgaW5kZXggPSBoYXNJdGVtcyA/IEFycmF5LnByb3RvdHlwZS5pbmRleE9mLmNhbGwoaXRlbXMsIGl0ZW0pIDogLTE7XG4gICAgICAgIHRoaXNbZXh0ZXJuYWxTZWxlY3RlZEluZGV4U3ltYm9sXSA9IGluZGV4O1xuICAgICAgICBpZiAoaW5kZXggPCAwKSB7XG4gICAgICAgICAgaXRlbSA9IG51bGw7IC8vIFRoZSBpbmRpY2F0ZWQgaXRlbSBpc24ndCBhY3R1YWxseSBpbiBgaXRlbXNgLlxuICAgICAgICB9XG4gICAgICAgIHRoaXNbZXh0ZXJuYWxTZWxlY3RlZEl0ZW1TeW1ib2xdID0gaXRlbTtcbiAgICAgIH0gZWxzZSB7XG4gICAgICAgIGluZGV4ID0gdGhpc1tleHRlcm5hbFNlbGVjdGVkSW5kZXhTeW1ib2xdO1xuICAgICAgfVxuXG4gICAgICAvLyBOb3cgbGV0IHN1cGVyIGRvIGFueSB3b3JrLlxuICAgICAgaWYgKCdzZWxlY3RlZEl0ZW0nIGluIGJhc2UucHJvdG90eXBlKSB7IHN1cGVyLnNlbGVjdGVkSXRlbSA9IGl0ZW07IH1cblxuICAgICAgaWYgKGl0ZW0gIT09IHByZXZpb3VzU2VsZWN0ZWRJdGVtKSB7XG4gICAgICAgIC8vIFRoZSBzZWxlY3RlZCBpdGVtIGNoYW5nZWQuXG4gICAgICAgIHRoaXNbaW50ZXJuYWxTZWxlY3RlZEl0ZW1TeW1ib2xdID0gaXRlbTtcblxuICAgICAgICBpZiAocHJldmlvdXNTZWxlY3RlZEl0ZW0pIHtcbiAgICAgICAgICAvLyBVcGRhdGUgc2VsZWN0aW9uIHN0YXRlIG9mIG9sZCBpdGVtLlxuICAgICAgICAgIHRoaXNbc3ltYm9scy5pdGVtU2VsZWN0ZWRdKHByZXZpb3VzU2VsZWN0ZWRJdGVtLCBmYWxzZSk7XG4gICAgICAgIH1cbiAgICAgICAgaWYgKGl0ZW0pIHtcbiAgICAgICAgICAvLyBVcGRhdGUgc2VsZWN0aW9uIHN0YXRlIHRvIG5ldyBpdGVtLlxuICAgICAgICAgIHRoaXNbc3ltYm9scy5pdGVtU2VsZWN0ZWRdKGl0ZW0sIHRydWUpO1xuICAgICAgICB9XG5cbiAgICAgICAgdXBkYXRlUG9zc2libGVOYXZpZ2F0aW9ucyh0aGlzKTtcblxuICAgICAgICBjb25zdCBldmVudCA9IG5ldyBDdXN0b21FdmVudCgnc2VsZWN0ZWQtaXRlbS1jaGFuZ2VkJywge1xuICAgICAgICAgIGRldGFpbDoge1xuICAgICAgICAgICAgc2VsZWN0ZWRJdGVtOiBpdGVtLFxuICAgICAgICAgICAgdmFsdWU6IGl0ZW0gLy8gZm9yIFBvbHltZXIgYmluZGluZ1xuICAgICAgICAgIH1cbiAgICAgICAgfSk7XG4gICAgICAgIHRoaXMuZGlzcGF0Y2hFdmVudChldmVudCk7XG4gICAgICB9XG5cbiAgICAgIGlmICh0aGlzW2ludGVybmFsU2VsZWN0ZWRJbmRleFN5bWJvbF0gIT09IGluZGV4KSB7XG4gICAgICAgIC8vIFVwZGF0ZSBzZWxlY3RlZEluZGV4IHByb3BlcnR5IHNvIGl0IGNhbiBoYXZlIGl0cyBvd24gZWZmZWN0cy5cbiAgICAgICAgdGhpcy5zZWxlY3RlZEluZGV4ID0gaW5kZXg7XG4gICAgICB9XG4gICAgfVxuXG4gICAgLyoqXG4gICAgICogU2VsZWN0IHRoZSBmaXJzdCBpdGVtIGluIHRoZSBsaXN0LlxuICAgICAqL1xuICAgIHNlbGVjdEZpcnN0KCkge1xuICAgICAgaWYgKHN1cGVyLnNlbGVjdEZpcnN0KSB7IHN1cGVyLnNlbGVjdEZpcnN0KCk7IH1cbiAgICAgIHJldHVybiBzZWxlY3RJbmRleCh0aGlzLCAwKTtcbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBUcnVlIGlmIHRoZSBsaXN0IHNob3VsZCBhbHdheXMgaGF2ZSBhIHNlbGVjdGlvbiAoaWYgaXQgaGFzIGl0ZW1zKS5cbiAgICAgKlxuICAgICAqIEB0eXBlIHtib29sZWFufVxuICAgICAqIEBkZWZhdWx0IGZhbHNlXG4gICAgICovXG4gICAgZ2V0IHNlbGVjdGlvblJlcXVpcmVkKCkge1xuICAgICAgcmV0dXJuIHRoaXNbc2VsZWN0aW9uUmVxdWlyZWRTeW1ib2xdO1xuICAgIH1cbiAgICBzZXQgc2VsZWN0aW9uUmVxdWlyZWQoc2VsZWN0aW9uUmVxdWlyZWQpIHtcbiAgICAgIHRoaXNbc2VsZWN0aW9uUmVxdWlyZWRTeW1ib2xdID0gc2VsZWN0aW9uUmVxdWlyZWQ7XG4gICAgICBpZiAoJ3NlbGVjdGlvblJlcXVpcmVkJyBpbiBiYXNlLnByb3RvdHlwZSkgeyBzdXBlci5zZWxlY3Rpb25SZXF1aXJlZCA9IHNlbGVjdGlvblJlcXVpcmVkOyB9XG4gICAgICB0cmFja1NlbGVjdGVkSXRlbSh0aGlzKTtcbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBUcnVlIGlmIHNlbGVjdGlvbiBuYXZpZ2F0aW9ucyB3cmFwIGZyb20gbGFzdCB0byBmaXJzdCwgYW5kIHZpY2UgdmVyc2EuXG4gICAgICpcbiAgICAgKiBAdHlwZSB7Ym9vbGVhbn1cbiAgICAgKiBAZGVmYXVsdCBmYWxzZVxuICAgICAqL1xuICAgIGdldCBzZWxlY3Rpb25XcmFwcygpIHtcbiAgICAgIHJldHVybiB0aGlzW3NlbGVjdGlvbldyYXBzU3ltYm9sXTtcbiAgICB9XG4gICAgc2V0IHNlbGVjdGlvbldyYXBzKHZhbHVlKSB7XG4gICAgICB0aGlzW3NlbGVjdGlvbldyYXBzU3ltYm9sXSA9IFN0cmluZyh2YWx1ZSkgPT09ICd0cnVlJztcbiAgICAgIGlmICgnc2VsZWN0aW9uV3JhcHMnIGluIGJhc2UucHJvdG90eXBlKSB7IHN1cGVyLnNlbGVjdGlvbldyYXBzID0gdmFsdWU7IH1cbiAgICAgIHVwZGF0ZVBvc3NpYmxlTmF2aWdhdGlvbnModGhpcyk7XG4gICAgfVxuXG4gICAgLyoqXG4gICAgICogU2VsZWN0IHRoZSBsYXN0IGl0ZW0gaW4gdGhlIGxpc3QuXG4gICAgICovXG4gICAgc2VsZWN0TGFzdCgpIHtcbiAgICAgIGlmIChzdXBlci5zZWxlY3RMYXN0KSB7IHN1cGVyLnNlbGVjdExhc3QoKTsgfVxuICAgICAgcmV0dXJuIHNlbGVjdEluZGV4KHRoaXMsIHRoaXMuaXRlbXMubGVuZ3RoIC0gMSk7XG4gICAgfVxuXG4gICAgLyoqXG4gICAgICogU2VsZWN0IHRoZSBuZXh0IGl0ZW0gaW4gdGhlIGxpc3QuXG4gICAgICovXG4gICAgc2VsZWN0TmV4dCgpIHtcbiAgICAgIGlmIChzdXBlci5zZWxlY3ROZXh0KSB7IHN1cGVyLnNlbGVjdE5leHQoKTsgfVxuICAgICAgcmV0dXJuIHNlbGVjdEluZGV4KHRoaXMsIHRoaXMuc2VsZWN0ZWRJbmRleCArIDEpO1xuICAgIH1cblxuICAgIC8qKlxuICAgICAqIFNlbGVjdCB0aGUgcHJldmlvdXMgaXRlbSBpbiB0aGUgbGlzdC5cbiAgICAgKlxuICAgICAqIElmIHRoZSBsaXN0IGhhcyBubyBzZWxlY3Rpb24sIHRoZSBsYXN0IGl0ZW0gd2lsbCBiZSBzZWxlY3RlZC5cbiAgICAgKi9cbiAgICBzZWxlY3RQcmV2aW91cygpIHtcbiAgICAgIGlmIChzdXBlci5zZWxlY3RQcmV2aW91cykgeyBzdXBlci5zZWxlY3RQcmV2aW91cygpOyB9XG4gICAgICBjb25zdCBuZXdJbmRleCA9IHRoaXMuc2VsZWN0ZWRJbmRleCA8IDAgP1xuICAgICAgICB0aGlzLml0ZW1zLmxlbmd0aCAtIDEgOiAgICAgLy8gTm8gc2VsZWN0aW9uIHlldDsgc2VsZWN0IGxhc3QgaXRlbS5cbiAgICAgICAgdGhpcy5zZWxlY3RlZEluZGV4IC0gMTtcbiAgICAgIHJldHVybiBzZWxlY3RJbmRleCh0aGlzLCBuZXdJbmRleCk7XG4gICAgfVxuXG4gICAgLyoqXG4gICAgICogRmlyZXMgd2hlbiB0aGUgc2VsZWN0ZWRJdGVtIHByb3BlcnR5IGNoYW5nZXMuXG4gICAgICpcbiAgICAgKiBAbWVtYmVyb2YgU2luZ2xlU2VsZWN0aW9uXG4gICAgICogQGV2ZW50IHNlbGVjdGVkLWl0ZW0tY2hhbmdlZFxuICAgICAqIEBwYXJhbSB7SFRNTEVsZW1lbnR9IGRldGFpbC5zZWxlY3RlZEl0ZW0gVGhlIG5ldyBzZWxlY3RlZCBpdGVtLlxuICAgICAqIEBwYXJhbSB7SFRNTEVsZW1lbnR9IGRldGFpbC5wcmV2aW91c0l0ZW0gVGhlIHByZXZpb3VzbHkgc2VsZWN0ZWQgaXRlbS5cbiAgICAgKi9cblxuICAgIC8qKlxuICAgICAqIEZpcmVzIHdoZW4gdGhlIHNlbGVjdGVkSW5kZXggcHJvcGVydHkgY2hhbmdlcy5cbiAgICAgKlxuICAgICAqIEBtZW1iZXJvZiBTaW5nbGVTZWxlY3Rpb25cbiAgICAgKiBAZXZlbnQgc2VsZWN0ZWQtaW5kZXgtY2hhbmdlZFxuICAgICAqIEBwYXJhbSB7bnVtYmVyfSBkZXRhaWwuc2VsZWN0ZWRJbmRleCBUaGUgbmV3IHNlbGVjdGVkIGluZGV4LlxuICAgICAqL1xuXG4gIH1cblxuICByZXR1cm4gU2luZ2xlU2VsZWN0aW9uO1xufTtcblxuXG4vLyBFbnN1cmUgdGhlIGdpdmVuIGluZGV4IGlzIHdpdGhpbiBib3VuZHMsIGFuZCBzZWxlY3QgaXQgaWYgaXQncyBub3QgYWxyZWFkeVxuLy8gc2VsZWN0ZWQuXG5mdW5jdGlvbiBzZWxlY3RJbmRleChlbGVtZW50LCBpbmRleCkge1xuICBjb25zdCBjb3VudCA9IGVsZW1lbnQuaXRlbXMubGVuZ3RoO1xuXG4gIGNvbnN0IGJvdW5kZWRJbmRleCA9IChlbGVtZW50LnNlbGVjdGlvbldyYXBzKSA/XG4gICAgLy8gSmF2YVNjcmlwdCBtb2QgZG9lc24ndCBoYW5kbGUgbmVnYXRpdmUgbnVtYmVycyB0aGUgd2F5IHdlIHdhbnQgdG8gd3JhcC5cbiAgICAvLyBTZWUgaHR0cDovL3N0YWNrb3ZlcmZsb3cuY29tL2EvMTg2MTgyNTAvNzY0NzJcbiAgICAoKGluZGV4ICUgY291bnQpICsgY291bnQpICUgY291bnQgOlxuXG4gICAgLy8gS2VlcCBpbmRleCB3aXRoaW4gYm91bmRzIG9mIGFycmF5LlxuICAgIE1hdGgubWF4KE1hdGgubWluKGluZGV4LCBjb3VudCAtIDEpLCAwKTtcblxuICBjb25zdCBwcmV2aW91c0luZGV4ID0gZWxlbWVudC5zZWxlY3RlZEluZGV4O1xuICBpZiAocHJldmlvdXNJbmRleCAhPT0gYm91bmRlZEluZGV4KSB7XG4gICAgZWxlbWVudC5zZWxlY3RlZEluZGV4ID0gYm91bmRlZEluZGV4O1xuICAgIHJldHVybiB0cnVlO1xuICB9IGVsc2Uge1xuICAgIHJldHVybiBmYWxzZTtcbiAgfVxufVxuXG4vLyBGb2xsb3dpbmcgYSBjaGFuZ2UgaW4gdGhlIHNldCBvZiBpdGVtcywgb3IgaW4gdGhlIHZhbHVlIG9mIHRoZVxuLy8gYHNlbGVjdGlvblJlcXVpcmVkYCBwcm9wZXJ0eSwgcmVhY3F1aXJlIHRoZSBzZWxlY3RlZCBpdGVtLiBJZiBpdCdzIG1vdmVkLFxuLy8gdXBkYXRlIGBzZWxlY3RlZEluZGV4YC4gSWYgaXQncyBiZWVuIHJlbW92ZWQsIGFuZCBhIHNlbGVjdGlvbiBpcyByZXF1aXJlZCxcbi8vIHRyeSB0byBzZWxlY3QgYW5vdGhlciBpdGVtLlxuZnVuY3Rpb24gdHJhY2tTZWxlY3RlZEl0ZW0oZWxlbWVudCkge1xuXG4gIGNvbnN0IGl0ZW1zID0gZWxlbWVudC5pdGVtcztcbiAgY29uc3QgaXRlbUNvdW50ID0gaXRlbXMgPyBpdGVtcy5sZW5ndGggOiAwO1xuXG4gIGNvbnN0IHByZXZpb3VzU2VsZWN0ZWRJdGVtID0gZWxlbWVudC5zZWxlY3RlZEl0ZW07XG4gIGlmICghcHJldmlvdXNTZWxlY3RlZEl0ZW0pIHtcbiAgICAvLyBObyBpdGVtIHdhcyBwcmV2aW91c2x5IHNlbGVjdGVkLlxuICAgIGlmIChlbGVtZW50LnNlbGVjdGlvblJlcXVpcmVkKSB7XG4gICAgICAvLyBTZWxlY3QgdGhlIGZpcnN0IGl0ZW0gYnkgZGVmYXVsdC5cbiAgICAgIGVsZW1lbnQuc2VsZWN0ZWRJbmRleCA9IDA7XG4gICAgfVxuICB9IGVsc2UgaWYgKGl0ZW1Db3VudCA9PT0gMCkge1xuICAgIC8vIFdlJ3ZlIGxvc3QgdGhlIHNlbGVjdGlvbiwgYW5kIHRoZXJlJ3Mgbm90aGluZyBsZWZ0IHRvIHNlbGVjdC5cbiAgICBlbGVtZW50LnNlbGVjdGVkSXRlbSA9IG51bGw7XG4gIH0gZWxzZSB7XG4gICAgLy8gVHJ5IHRvIGZpbmQgdGhlIHByZXZpb3VzbHktc2VsZWN0ZWQgaXRlbSBpbiB0aGUgY3VycmVudCBzZXQgb2YgaXRlbXMuXG4gICAgY29uc3QgaW5kZXhJbkN1cnJlbnRJdGVtcyA9IEFycmF5LnByb3RvdHlwZS5pbmRleE9mLmNhbGwoaXRlbXMsIHByZXZpb3VzU2VsZWN0ZWRJdGVtKTtcbiAgICBjb25zdCBwcmV2aW91c1NlbGVjdGVkSW5kZXggPSBlbGVtZW50LnNlbGVjdGVkSW5kZXg7XG4gICAgaWYgKGluZGV4SW5DdXJyZW50SXRlbXMgPCAwKSB7XG4gICAgICAvLyBQcmV2aW91c2x5LXNlbGVjdGVkIGl0ZW0gd2FzIHJlbW92ZWQgZnJvbSB0aGUgaXRlbXMuXG4gICAgICAvLyBTZWxlY3QgdGhlIGl0ZW0gYXQgdGhlIHNhbWUgaW5kZXggKGlmIGl0IGV4aXN0cykgb3IgYXMgY2xvc2UgYXMgcG9zc2libGUuXG4gICAgICBjb25zdCBuZXdTZWxlY3RlZEluZGV4ID0gTWF0aC5taW4ocHJldmlvdXNTZWxlY3RlZEluZGV4LCBpdGVtQ291bnQgLSAxKTtcbiAgICAgIC8vIFNlbGVjdCBieSBpdGVtLCBzaW5jZSBpbmRleCBtYXkgYmUgdGhlIHNhbWUsIGFuZCB3ZSB3YW50IHRvIHJhaXNlIHRoZVxuICAgICAgLy8gc2VsZWN0ZWQtaXRlbS1jaGFuZ2VkIGV2ZW50LlxuICAgICAgZWxlbWVudC5zZWxlY3RlZEl0ZW0gPSBpdGVtc1tuZXdTZWxlY3RlZEluZGV4XTtcbiAgICB9IGVsc2UgaWYgKGluZGV4SW5DdXJyZW50SXRlbXMgIT09IHByZXZpb3VzU2VsZWN0ZWRJbmRleCkge1xuICAgICAgLy8gUHJldmlvdXNseS1zZWxlY3RlZCBpdGVtIHN0aWxsIHRoZXJlLCBidXQgY2hhbmdlZCBwb3NpdGlvbi5cbiAgICAgIGVsZW1lbnQuc2VsZWN0ZWRJbmRleCA9IGluZGV4SW5DdXJyZW50SXRlbXM7XG4gICAgfVxuICB9XG59XG5cbi8vIEZvbGxvd2luZyBhIGNoYW5nZSBpbiBzZWxlY3Rpb24sIHJlcG9ydCB3aGV0aGVyIGl0J3Mgbm93IHBvc3NpYmxlIHRvXG4vLyBnbyBuZXh0L3ByZXZpb3VzIGZyb20gdGhlIGdpdmVuIGluZGV4LlxuZnVuY3Rpb24gdXBkYXRlUG9zc2libGVOYXZpZ2F0aW9ucyhlbGVtZW50KSB7XG4gIGxldCBjYW5TZWxlY3ROZXh0O1xuICBsZXQgY2FuU2VsZWN0UHJldmlvdXM7XG4gIGNvbnN0IGl0ZW1zID0gZWxlbWVudC5pdGVtcztcbiAgaWYgKGl0ZW1zID09IG51bGwgfHwgaXRlbXMubGVuZ3RoID09PSAwKSB7XG4gICAgLy8gTm8gaXRlbXMgdG8gc2VsZWN0LlxuICAgIGNhblNlbGVjdE5leHQgPSBmYWxzZTtcbiAgICBjYW5TZWxlY3RQcmV2aW91cyA9IGZhbHNlO1xuICB9IGlmIChlbGVtZW50LnNlbGVjdGlvbldyYXBzKSB7XG4gICAgLy8gU2luY2UgdGhlcmUgYXJlIGl0ZW1zLCBjYW4gYWx3YXlzIGdvIG5leHQvcHJldmlvdXMuXG4gICAgY2FuU2VsZWN0TmV4dCA9IHRydWU7XG4gICAgY2FuU2VsZWN0UHJldmlvdXMgPSB0cnVlO1xuICB9IGVsc2Uge1xuICAgIGNvbnN0IGluZGV4ID0gZWxlbWVudC5zZWxlY3RlZEluZGV4O1xuICAgIGlmIChpbmRleCA8IDAgJiYgaXRlbXMubGVuZ3RoID4gMCkge1xuICAgICAgLy8gU3BlY2lhbCBjYXNlLiBJZiB0aGVyZSBhcmUgaXRlbXMgYnV0IG5vIHNlbGVjdGlvbiwgZGVjbGFyZSB0aGF0IGl0J3NcbiAgICAgIC8vIGFsd2F5cyBwb3NzaWJsZSB0byBnbyBuZXh0L3ByZXZpb3VzIHRvIGNyZWF0ZSBhIHNlbGVjdGlvbi5cbiAgICAgIGNhblNlbGVjdE5leHQgPSB0cnVlO1xuICAgICAgY2FuU2VsZWN0UHJldmlvdXMgPSB0cnVlO1xuICAgIH0gZWxzZSB7XG4gICAgICAvLyBOb3JtYWwgY2FzZTogd2UgaGF2ZSBhbiBpbmRleCBpbiBhIGxpc3QgdGhhdCBoYXMgaXRlbXMuXG4gICAgICBjYW5TZWxlY3RQcmV2aW91cyA9IChpbmRleCA+IDApO1xuICAgICAgY2FuU2VsZWN0TmV4dCA9IChpbmRleCA8IGl0ZW1zLmxlbmd0aCAtIDEpO1xuICAgIH1cbiAgfVxuICBpZiAoZWxlbWVudC5jYW5TZWxlY3ROZXh0ICE9PSBjYW5TZWxlY3ROZXh0KSB7XG4gICAgZWxlbWVudC5jYW5TZWxlY3ROZXh0ID0gY2FuU2VsZWN0TmV4dDtcbiAgfVxuICBpZiAoZWxlbWVudC5jYW5TZWxlY3RQcmV2aW91cyAhPT0gY2FuU2VsZWN0UHJldmlvdXMpIHtcbiAgICBlbGVtZW50LmNhblNlbGVjdFByZXZpb3VzID0gY2FuU2VsZWN0UHJldmlvdXM7XG4gIH1cbn1cbiIsImltcG9ydCBjcmVhdGVTeW1ib2wgZnJvbSAnLi9jcmVhdGVTeW1ib2wnO1xuaW1wb3J0IHN5bWJvbHMgZnJvbSAnLi9zeW1ib2xzJztcblxuXG5jb25zdCBwbGF5aW5nU3ltYm9sID0gY3JlYXRlU3ltYm9sKCdwbGF5aW5nJyk7XG5jb25zdCBzZWxlY3Rpb25UaW1lckR1cmF0aW9uU3ltYm9sID0gY3JlYXRlU3ltYm9sKCdzZWxlY3Rpb25UaW1lckR1cmF0aW9uJyk7XG5jb25zdCB0aW1lclRpbWVvdXRTeW1ib2wgPSBjcmVhdGVTeW1ib2woJ3RpbWVyVGltZW91dCcpO1xuXG5cbi8qIEV4cG9ydGVkIGZ1bmN0aW9uIGV4dGVuZHMgYSBiYXNlIGNsYXNzIHdpdGggVGltZXJTZWxlY3Rpb24uICovXG5leHBvcnQgZGVmYXVsdCAoYmFzZSkgPT4ge1xuXG4gIC8qKlxuICAgKiBNaXhpbiB3aGljaCBwcm92aWRlcyBmb3IgYXV0b21hdGljIHRpbWVkIGNoYW5nZXMgaW4gc2VsZWN0aW9uLlxuICAgKlxuICAgKiBUaGlzIG1peGluIGlzIHVzZWZ1bCBmb3IgY3JlYXRpbmcgc2xpZGVzaG93LWxpa2UgZWxlbWVudHMgc3VjaCBhc1xuICAgKiBbYmFzaWMtc2xpZGVzaG93XSguLi9wYWNrYWdlcy9iYXNpYy1zbGlkZXNob3cpIGFuZFxuICAgKiBbYmFzaWMtc2xpZGVzaG93LXdpdGgtY29udHJvbHNdKC4uL3BhY2thZ2VzL2Jhc2ljLXNsaWRlc2hvdy13aXRoLWNvbnRyb2xzKS5cbiAgICpcbiAgICogVHlwaWNhbCB1c2FnZTpcbiAgICpcbiAgICogICAgIGNsYXNzIENhcm91c2VsV2l0aFRpbWVyIGV4dGVuZHMgVGltZXJTZWxlY3Rpb25NaXhpbihDYXJvdXNlbCkge31cbiAgICogICAgIGN1c3RvbUVsZW1lbnRzLmRlZmluZSgnY2Fyb3VzZWwtd2l0aC1hcnJvd3MnLCBDYXJvdXNlbFdpdGhUaW1lcik7XG4gICAqXG4gICAqIFRoaXMgbWl4aW4gZXhwZWN0cyB0aGUgY29tcG9uZW50IHRvIGRlZmluZSBhbiBgaXRlbXNgIHByb3BlcnR5LCBhcyB3ZWxsIGFzXG4gICAqIGBzZWxlY3RGaXJzdGAgYW5kIGBzZWxlY3ROZXh0YCBtZXRob2RzLiBZb3UgY2FuIGltcGxlbWVudCB0aG9zZSB5b3Vyc2VsZixcbiAgICogb3IgdXNlIFtDb250ZW50SXRlbXNNaXhpbl0oQ29udGVudEl0ZW1zTWl4aW4ubWQpIGFuZFxuICAgKiBbU2luZ2xlU2VsZWN0aW9uTWl4aW5dKFNpbmdsZVNlbGVjdGlvbk1peGluLm1kKS5cbiAgICovXG4gIGNsYXNzIFRpbWVyU2VsZWN0aW9uIGV4dGVuZHMgYmFzZSB7XG5cbiAgICBjb25zdHJ1Y3RvcigpIHtcbiAgICAgIHN1cGVyKCk7XG4gICAgICAvLyBTZXQgZGVmYXVsdHMuXG4gICAgICBpZiAodHlwZW9mIHRoaXMucGxheWluZyA9PT0gJ3VuZGVmaW5lZCcpIHtcbiAgICAgICAgdGhpcy5wbGF5aW5nID0gdGhpc1tzeW1ib2xzLmRlZmF1bHRzXS5wbGF5aW5nO1xuICAgICAgfVxuICAgICAgaWYgKHR5cGVvZiB0aGlzLnNlbGVjdGlvblRpbWVyRHVyYXRpb24gPT09ICd1bmRlZmluZWQnKSB7XG4gICAgICAgIHRoaXMuc2VsZWN0aW9uVGltZXJEdXJhdGlvbiA9IHRoaXNbc3ltYm9scy5kZWZhdWx0c10uc2VsZWN0aW9uVGltZXJEdXJhdGlvbjtcbiAgICAgIH1cbiAgICB9XG5cbiAgICBjb250ZW50Q2hhbmdlZCgpIHtcbiAgICAgIGlmIChzdXBlci5jb250ZW50Q2hhbmdlZCkgeyBzdXBlci5jb250ZW50Q2hhbmdlZCgpOyB9XG4gICAgICByZXN0YXJ0VGltZXIodGhpcyk7XG4gICAgfVxuXG4gICAgZ2V0IFtzeW1ib2xzLmRlZmF1bHRzXSgpIHtcbiAgICAgIGNvbnN0IGRlZmF1bHRzID0gc3VwZXJbc3ltYm9scy5kZWZhdWx0c10gfHwge307XG4gICAgICBkZWZhdWx0cy5wbGF5aW5nID0gZmFsc2U7XG4gICAgICBkZWZhdWx0cy5zZWxlY3Rpb25UaW1lckR1cmF0aW9uID0gMTAwMDtcbiAgICAgIHJldHVybiBkZWZhdWx0cztcbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBCZWdpbiBhdXRvbWF0aWMgcHJvZ3Jlc3Npb24gb2YgdGhlIHNlbGVjdGlvbi5cbiAgICAgKi9cbiAgICBwbGF5KCkge1xuICAgICAgaWYgKHN1cGVyLnBsYXkpIHsgc3VwZXIucGxheSgpOyB9XG4gICAgICBzdGFydFRpbWVyKHRoaXMpO1xuICAgICAgdGhpc1twbGF5aW5nU3ltYm9sXSA9IHRydWU7XG4gICAgfVxuXG4gICAgLyoqXG4gICAgICogUGF1c2UgYXV0b21hdGljIHByb2dyZXNzaW9uIG9mIHRoZSBzZWxlY3Rpb24uXG4gICAgICovXG4gICAgcGF1c2UoKSB7XG4gICAgICBpZiAoc3VwZXIucGF1c2UpIHsgc3VwZXIucGF1c2UoKTsgfVxuICAgICAgY2xlYXJUaW1lcih0aGlzKTtcbiAgICAgIHRoaXNbcGxheWluZ1N5bWJvbF0gPSBmYWxzZTtcbiAgICB9XG5cbiAgICAvKipcbiAgICAgKiBUcnVlIGlmIHRoZSBzZWxlY3Rpb24gaXMgYmVpbmcgYXV0b21hdGljYWxseSBhZHZhbmNlZC5cbiAgICAgKlxuICAgICAqIEB0eXBlIHtib29sZWFufVxuICAgICAqIEBkZWZhdWx0IGZhbHNlXG4gICAgICovXG4gICAgZ2V0IHBsYXlpbmcoKSB7XG4gICAgICByZXR1cm4gdGhpc1twbGF5aW5nU3ltYm9sXTtcbiAgICB9XG4gICAgc2V0IHBsYXlpbmcocGxheWluZykge1xuICAgICAgY29uc3QgcHJldmlvdXNQbGF5aW5nID0gdGhpc1twbGF5aW5nU3ltYm9sXTtcbiAgICAgIGNvbnN0IHBhcnNlZCA9IFN0cmluZyhwbGF5aW5nKSA9PT0gJ3RydWUnOyAvLyBDYXN0IHRvIGJvb2xlYW5cbiAgICAgIGlmICgncGxheWluZycgaW4gYmFzZS5wcm90b3R5cGUpIHsgc3VwZXIucGxheWluZyA9IHBsYXlpbmc7IH1cbiAgICAgIGlmIChwYXJzZWQgIT09IHByZXZpb3VzUGxheWluZykge1xuICAgICAgICBpZiAocGxheWluZykge1xuICAgICAgICAgIHRoaXMucGxheSgpO1xuICAgICAgICB9IGVsc2Uge1xuICAgICAgICAgIHRoaXMucGF1c2UoKTtcbiAgICAgICAgfVxuICAgICAgfVxuICAgIH1cblxuICAgIC8qXG4gICAgICogV2hlbiB0aGUgc2VsZWN0ZWQgaXRlbSBjaGFuZ2VzIChiZWNhdXNlIG9mIHNvbWV0aGluZyB0aGlzIG1peGluIGRpZCwgb3JcbiAgICAgKiB3YXMgY2hhbmdlZCBieSBhbiBvdXRzaWRlIGFnZW50IGxpa2UgdGhlIHVzZXIpLCB3ZSB3YWl0IGJlZm9yZSBhZHZhbmNpbmdcbiAgICAgKiB0byB0aGUgbmV4dCBpdGVtLiBCeSB0cmlnZ2VyaW5nIHRoZSBuZXh0IGl0ZW0gdGhpcyB3YXksIHdlIGltcGxpY2l0bHkgZ2V0XG4gICAgICogYSBkZXNpcmFibGUgYmVoYXZpb3I6IGlmIHRoZSB1c2VyIGNoYW5nZXMgdGhlIHNlbGVjdGlvbiAoZS5nLiwgaW4gYVxuICAgICAqIGNhcm91c2VsKSwgd2UgbGV0IHRoZW0gc2VlIHRoYXQgc2VsZWN0aW9uIHN0YXRlIGZvciBhIHdoaWxlIGJlZm9yZVxuICAgICAqIGFkdmFuY2luZyB0aGUgc2VsZWN0aW9uIG91cnNlbHZlcy5cbiAgICAgKi9cbiAgICBnZXQgc2VsZWN0ZWRJdGVtKCkge1xuICAgICAgcmV0dXJuIHN1cGVyLnNlbGVjdGVkSXRlbTtcbiAgICB9XG4gICAgc2V0IHNlbGVjdGVkSXRlbShpdGVtKSB7XG4gICAgICBpZiAoJ3NlbGVjdGVkSXRlbScgaW4gYmFzZS5wcm90b3R5cGUpIHsgc3VwZXIuc2VsZWN0ZWRJdGVtID0gaXRlbTsgfVxuICAgICAgcmVzdGFydFRpbWVyKHRoaXMpO1xuICAgIH1cblxuICAgIC8qKlxuICAgICAqIFRoZSB0aW1lIGluIG1pbGxpc2Vjb25kcyB0aGF0IHdpbGwgZWxhcHNlIGFmdGVyIHRoZSBzZWxlY3Rpb24gY2hhbmdlc1xuICAgICAqIGJlZm9yZSB0aGUgc2VsZWN0aW9uIHdpbGwgYmUgYWR2YW5jZWQgdG8gdGhlIG5leHQgaXRlbSBpbiB0aGUgbGlzdC5cbiAgICAgKlxuICAgICAqIEB0eXBlIHtudW1iZXJ9IC0gVGltZSBpbiBtaWxsaXNlY29uZHNcbiAgICAgKiBAZGVmYXVsdCAxMDAwICgxIHNlY29uZClcbiAgICAgKi9cbiAgICBnZXQgc2VsZWN0aW9uVGltZXJEdXJhdGlvbigpIHtcbiAgICAgIHJldHVybiB0aGlzW3NlbGVjdGlvblRpbWVyRHVyYXRpb25TeW1ib2xdO1xuICAgIH1cbiAgICBzZXQgc2VsZWN0aW9uVGltZXJEdXJhdGlvbih2YWx1ZSkge1xuICAgICAgdGhpc1tzZWxlY3Rpb25UaW1lckR1cmF0aW9uU3ltYm9sXSA9IHBhcnNlSW50KHZhbHVlKTtcbiAgICAgIGlmICgnc2VsZWN0aW9uVGltZXJEdXJhdGlvbicgaW4gYmFzZS5wcm90b3R5cGUpIHsgc3VwZXIuc2VsZWN0aW9uVGltZXJEdXJhdGlvbiA9IHZhbHVlOyB9XG4gICAgfVxuXG4gIH1cblxuICByZXR1cm4gVGltZXJTZWxlY3Rpb247XG59O1xuXG5cbmZ1bmN0aW9uIGNsZWFyVGltZXIoZWxlbWVudCkge1xuICBpZiAoZWxlbWVudFt0aW1lclRpbWVvdXRTeW1ib2xdKSB7XG4gICAgY2xlYXJUaW1lb3V0KGVsZW1lbnRbdGltZXJUaW1lb3V0U3ltYm9sXSk7XG4gICAgZWxlbWVudFt0aW1lclRpbWVvdXRTeW1ib2xdID0gbnVsbDtcbiAgfVxufVxuXG5mdW5jdGlvbiByZXN0YXJ0VGltZXIoZWxlbWVudCkge1xuICBjbGVhclRpbWVyKGVsZW1lbnQpO1xuICBpZiAoZWxlbWVudC5wbGF5aW5nICYmIGVsZW1lbnQuaXRlbXMgJiYgZWxlbWVudC5pdGVtcy5sZW5ndGggPiAwKSB7XG4gICAgc3RhcnRUaW1lcihlbGVtZW50KTtcbiAgfVxufVxuXG5mdW5jdGlvbiBzdGFydFRpbWVyKGVsZW1lbnQpIHtcbiAgLy8gSWYgcGxheSgpIGlzIGNhbGxlZCBtb3JlIHRoYW4gb25jZSwgY2FuY2VsIGFueSBleGlzdGluZyB0aW1lci5cbiAgY2xlYXJUaW1lcihlbGVtZW50KTtcbiAgZWxlbWVudFt0aW1lclRpbWVvdXRTeW1ib2xdID0gc2V0VGltZW91dCgoKSA9PiB7XG4gICAgc2VsZWN0TmV4dFdpdGhXcmFwKGVsZW1lbnQpO1xuICB9LCBlbGVtZW50LnNlbGVjdGlvblRpbWVyRHVyYXRpb24pO1xufVxuXG4vLyBTZWxlY3QgdGhlIG5leHQgaXRlbSwgd3JhcHBpbmcgdG8gZmlyc3QgaXRlbSBpZiBuZWNlc3NhcnkuXG5mdW5jdGlvbiBzZWxlY3ROZXh0V2l0aFdyYXAoZWxlbWVudCkge1xuICBjb25zdCBpdGVtcyA9IGVsZW1lbnQuaXRlbXM7XG4gIGlmIChpdGVtcyAmJiBpdGVtcy5sZW5ndGggPiAwKSB7XG4gICAgaWYgKGVsZW1lbnQuc2VsZWN0ZWRJbmRleCA9PSBudWxsIHx8IGVsZW1lbnQuc2VsZWN0ZWRJbmRleCA9PT0gaXRlbXMubGVuZ3RoIC0gMSkge1xuICAgICAgZWxlbWVudC5zZWxlY3RGaXJzdCgpO1xuICAgIH0gZWxzZSB7XG4gICAgICBlbGVtZW50LnNlbGVjdE5leHQoKTtcbiAgICB9XG4gIH1cbn1cbiIsIi8qKlxuICogSGVscGVyIGZ1bmN0aW9uIHRvIGNyZWF0ZSBhIHN5bWJvbCB0aGF0IGNhbiBiZSB1c2VkIGZvciBhc3NvY2lhdGluZyBwcml2YXRlXG4gKiBkYXRhIHdpdGggYW4gZWxlbWVudC5cbiAqXG4gKiBNaXhpbnMgYW5kIGNvbXBvbmVudCBjbGFzc2VzIG9mdGVuIHdhbnQgdG8gYXNzb2NpYXRlIHByaXZhdGUgZGF0YSB3aXRoIGFuXG4gKiBlbGVtZW50IGluc3RhbmNlLCBidXQgSmF2YVNjcmlwdCBkb2VzIG5vdCBoYXZlIGRpcmVjdCBzdXBwb3J0IGZvciB0cnVlXG4gKiBwcml2YXRlIHByb3BlcnRpZXMuIE9uZSBhcHByb2FjaCBpcyB0byB1c2UgdGhlXG4gKiBbU3ltYm9sXShodHRwczovL2RldmVsb3Blci5tb3ppbGxhLm9yZy9lbi1VUy9kb2NzL1dlYi9KYXZhU2NyaXB0L1JlZmVyZW5jZS9HbG9iYWxfT2JqZWN0cy9TeW1ib2wpXG4gKiBkYXRhIHR5cGUgdG8gc2V0IGFuZCByZXRyaWV2ZSBkYXRhIG9uIGFuIGVsZW1lbnQuXG4gKlxuICogVW5mb3J0dW5hdGVseSwgdGhlIFN5bWJvbCB0eXBlIGlzIG5vdCBhdmFpbGFibGUgaW4gSW50ZXJuZXQgRXhwbG9yZXIgMTEuIFRoZVxuICogYGNyZWF0ZVN5bWJvbGAgaGVscGVyIGZ1bmN0aW9uIGV4aXN0cyBhcyBhIHdvcmthcm91bmQgZm9yIElFIDExLiBSYXRoZXIgdGhhblxuICogcmV0dXJuaW5nIGEgdHJ1ZSBTeW1ib2wsIGl0IHNpbXBseSByZXR1cm5zIGFuIHVuZGVyc2NvcmUtcHJlZml4ZWQgc3RyaW5nLlxuICpcbiAqIFVzYWdlOlxuICpcbiAqICAgICBjb25zdCBmb29TeW1ib2wgPSBjcmVhdGVTeW1ib2woJ2ZvbycpO1xuICpcbiAqICAgICBjbGFzcyBNeUVsZW1lbnQgZXh0ZW5kcyBIVE1MRWxlbWVudCB7XG4gKiAgICAgICBnZXQgZm9vKCkge1xuICogICAgICAgICByZXR1cm4gdGhpc1tmb29TeW1ib2xdO1xuICogICAgICAgfVxuICogICAgICAgc2V0IGZvbyh2YWx1ZSkge1xuICogICAgICAgICB0aGlzW2Zvb1N5bWJvbF0gPSB2YWx1ZTtcbiAqICAgICAgIH1cbiAqICAgICB9XG4gKlxuICogSW4gSUUgMTEsIHRoaXMgc2FtcGxlIHdpbGwgXCJoaWRlXCIgZGF0YSBiZWhpbmQgYW4gaW5zdGFuY2UgcHJvcGVydHkgdGhpcy5fZm9vLlxuICogVGhlIHVzZSBvZiB0aGUgdW5kZXJzY29yZSBpcyBtZWFudCB0byByZWR1Y2UgKG5vdCBlbGltaW5hdGUpIHRoZSBwb3RlbnRpYWxcbiAqIGZvciBuYW1lIGNvbmZsaWN0cywgYW5kIGRpc2NvdXJhZ2UgKG5vdCBwcmV2ZW50KSBleHRlcm5hbCBhY2Nlc3MgdG8gdGhpc1xuICogZGF0YS4gSW4gbW9kZXJuIGJyb3dzZXJzLCB0aGUgYWJvdmUgY29kZSB3aWxsIGVsaW1pbmF0ZSB0aGUgcG90ZW50aWFsIG9mXG4gKiBuYW1pbmcgY29uZmxpY3RzLCBhbmQgYmV0dGVyIGhpZGUgdGhlIGRhdGEgYmVoaW5kIGEgcmVhbCBTeW1ib2wuXG4gKlxuICogQGZ1bmN0aW9uIGNyZWF0ZVN5bWJvbFxuICogQHBhcmFtIHtzdHJpbmd9IGRlc2NyaXB0aW9uIC0gQSBzdHJpbmcgdG8gaWRlbnRpZnkgdGhlIHN5bWJvbCB3aGVuIGRlYnVnZ2luZ1xuICovXG5leHBvcnQgZGVmYXVsdCBmdW5jdGlvbiBjcmVhdGVTeW1ib2woZGVzY3JpcHRpb24pIHtcbiAgcmV0dXJuIHR5cGVvZiBTeW1ib2wgPT09ICdmdW5jdGlvbicgP1xuICAgIFN5bWJvbChkZXNjcmlwdGlvbikgOlxuICAgIGBfJHtkZXNjcmlwdGlvbn1gO1xufVxuIiwiLypcbiAqIE1pY3JvdGFzayBoZWxwZXIgZm9yIElFIDExLlxuICpcbiAqIEV4ZWN1dGluZyBhIGZ1bmN0aW9uIGFzIGEgbWljcm90YXNrIGlzIHRyaXZpYWwgaW4gYnJvd3NlcnMgdGhhdCBzdXBwb3J0XG4gKiBwcm9taXNlcywgd2hvc2UgdGhlbigpIGNsYXVzZXMgdXNlIG1pY3JvdGFzayB0aW1pbmcuIElFIDExIGRvZXNuJ3Qgc3VwcG9ydFxuICogcHJvbWlzZXMsIGJ1dCBkb2VzIHN1cHBvcnQgTXV0YXRpb25PYnNlcnZlcnMsIHdoaWNoIGFyZSBhbHNvIGV4ZWN1dGVkIGFzXG4gKiBtaWNyb3Rhc2tzLiBTbyB0aGlzIGhlbHBlciB1c2VzIGFuIE11dGF0aW9uT2JzZXJ2ZXIgdG8gYWNoaWV2ZSBtaWNyb3Rhc2tcbiAqIHRpbWluZy5cbiAqXG4gKiBTZWUgaHR0cHM6Ly9qYWtlYXJjaGliYWxkLmNvbS8yMDE1L3Rhc2tzLW1pY3JvdGFza3MtcXVldWVzLWFuZC1zY2hlZHVsZXMvXG4gKlxuICogSW5zcGlyZWQgYnkgUG9seW1lcidzIGFzeW5jKCkgZnVuY3Rpb24uXG4gKi9cblxuXG4vLyBUaGUgcXVldWUgb2YgcGVuZGluZyBjYWxsYmFja3MgdG8gYmUgZXhlY3V0ZWQgYXMgbWljcm90YXNrcy5cbmNvbnN0IGNhbGxiYWNrcyA9IFtdO1xuXG4vLyBDcmVhdGUgYW4gZWxlbWVudCB0aGF0IHdlIHdpbGwgbW9kaWZ5IHRvIGZvcmNlIG9ic2VydmFibGUgbXV0YXRpb25zLlxuY29uc3QgZWxlbWVudCA9IGRvY3VtZW50LmNyZWF0ZVRleHROb2RlKCcnKTtcblxuLy8gQSBtb25vdG9uaWNhbGx5LWluY3JlYXNpbmcgdmFsdWUuXG5sZXQgY291bnRlciA9IDA7XG5cblxuLyoqXG4gKiBBZGQgYSBjYWxsYmFjayB0byB0aGUgbWljcm90YXNrIHF1ZXVlLlxuICpcbiAqIFRoaXMgdXNlcyBhIE11dGF0aW9uT2JzZXJ2ZXIgc28gdGhhdCBpdCB3b3JrcyBvbiBJRSAxMS5cbiAqXG4gKiBOT1RFOiBJRSAxMSBtYXkgYWN0dWFsbHkgdXNlIHRpbWVvdXQgdGltaW5nIHdpdGggTXV0YXRpb25PYnNlcnZlcnMuIFRoaXNcbiAqIG5lZWRzIG1vcmUgaW52ZXN0aWdhdGlvbi5cbiAqXG4gKiBAZnVuY3Rpb24gbWljcm90YXNrXG4gKiBAcGFyYW0ge2Z1bmN0aW9ufSBjYWxsYmFja1xuICovXG5leHBvcnQgZGVmYXVsdCBmdW5jdGlvbiBtaWNyb3Rhc2soY2FsbGJhY2spIHtcbiAgY2FsbGJhY2tzLnB1c2goY2FsbGJhY2spO1xuICAvLyBGb3JjZSBhIG11dGF0aW9uLlxuICBlbGVtZW50LnRleHRDb250ZW50ID0gKytjb3VudGVyO1xufVxuXG5cbi8vIEV4ZWN1dGUgYW55IHBlbmRpbmcgY2FsbGJhY2tzLlxuZnVuY3Rpb24gZXhlY3V0ZUNhbGxiYWNrcygpIHtcbiAgd2hpbGUgKGNhbGxiYWNrcy5sZW5ndGggPiAwKSB7XG4gICAgY29uc3QgY2FsbGJhY2sgPSBjYWxsYmFja3Muc2hpZnQoKTtcbiAgICBjYWxsYmFjaygpO1xuICB9XG59XG5cblxuLy8gQ3JlYXRlIHRoZSBvYnNlcnZlci5cbmNvbnN0IG9ic2VydmVyID0gbmV3IE11dGF0aW9uT2JzZXJ2ZXIoZXhlY3V0ZUNhbGxiYWNrcyk7XG5vYnNlcnZlci5vYnNlcnZlKGVsZW1lbnQsIHtcbiAgY2hhcmFjdGVyRGF0YTogdHJ1ZVxufSk7XG4iLCJpbXBvcnQgY3JlYXRlU3ltYm9sIGZyb20gJy4vY3JlYXRlU3ltYm9sJztcbmltcG9ydCB0b2dnbGVDbGFzcyBmcm9tICcuL3RvZ2dsZUNsYXNzJztcblxuXG4vLyBTeW1ib2xzIGZvciBwcml2YXRlIGRhdGEgbWVtYmVycyBvbiBhbiBlbGVtZW50LlxuY29uc3Qgc2FmZVRvU2V0QXR0cmlidXRlc1N5bWJvbCA9IGNyZWF0ZVN5bWJvbCgnc2FmZVRvU2V0QXR0cmlidXRlcycpO1xuY29uc3QgcGVuZGluZ0F0dHJpYnV0ZXNTeW1ib2wgPSBjcmVhdGVTeW1ib2woJ3BlbmRpbmdBdHRyaWJ1dGVzJyk7XG5jb25zdCBwZW5kaW5nQ2xhc3Nlc1N5bWJvbCA9IGNyZWF0ZVN5bWJvbCgncGVuZGluZ0NsYXNzZXMnKTtcblxuXG4vKipcbiAqIEhlbHBlciBmdW5jdGlvbnMgZm9yIHVwZGF0aW5nIGF0dHJpYnV0ZXMsIGluY2x1ZGluZyB0aGUgYGNsYXNzYCBhdHRyaWJ1dGUuXG4gKi9cbmV4cG9ydCBkZWZhdWx0IHtcblxuICAvKipcbiAgICogUGVyZm9ybSBhbnkgcGVuZGluZyB1cGRhdGVzIHRvIGF0dHJpYnV0ZXMgYW5kIGNsYXNzZXMuXG4gICAqXG4gICAqIFRoaXMgd3JpdGVzIGFueSBgc2V0QXR0cmlidXRlYCBvciBgdG9nZ2xlQ2xhc3NgIHZhbHVlcyB0aGF0IHdlcmUgcGVyZm9ybWVkXG4gICAqIGJlZm9yZSBhbiBlbGVtZW50IHdhcyBhdHRhY2hlZCB0byB0aGUgZG9jdW1lbnQgZm9yIHRoZSBmaXJzdCB0aW1lLlxuICAgKlxuICAgKiBUaGlzIG1ldGhvZCBzaG91bGQgYmUgY2FsbGVkIGJ5IG1peGlucy9jb21wb25lbnRzIGluIHRoZWlyXG4gICAqIGBjb25uZWN0ZWRDYWxsYmFja2AuIElmIG11bGl0cGxlIG1peGlucy9jb21wb25lbnRzIGludm9rZSB0aGlzIGR1cmluZyB0aGVcbiAgICogc2FtZSBgY29ubmVjdGVkQ2FsbGJhY2tgLCBvbmx5IHRoZSBmaXJzdCBjYWxsIHdpbGwgaGF2ZSBhbnkgZWZmZWN0LiBUaGVcbiAgICogc3Vic2VxdWVudCBjYWxscyB3aWxsIGJlIGhhcm1sZXNzLlxuICAgKlxuICAgKiBAcGFyYW0ge0hUTUxFbGVtZW50fSBlbGVtZW50IC0gVGhlIGVsZW1lbnQgYmVpbmcgYWRkZWQgdG8gdGhlIGRvY3VtZW50LlxuICAgKi9cbiAgY29ubmVjdGVkKGVsZW1lbnQpIHtcbiAgICBlbGVtZW50W3NhZmVUb1NldEF0dHJpYnV0ZXNTeW1ib2xdID0gdHJ1ZTtcblxuICAgIC8vIFNldCBhbnkgcGVuZGluZyBhdHRyaWJ1dGVzLlxuICAgIGlmIChlbGVtZW50W3BlbmRpbmdBdHRyaWJ1dGVzU3ltYm9sXSkge1xuICAgICAgZm9yIChsZXQgYXR0cmlidXRlIGluIGVsZW1lbnRbcGVuZGluZ0F0dHJpYnV0ZXNTeW1ib2xdKSB7XG4gICAgICAgIGNvbnN0IHZhbHVlID0gZWxlbWVudFtwZW5kaW5nQXR0cmlidXRlc1N5bWJvbF1bYXR0cmlidXRlXTtcbiAgICAgICAgc2V0QXR0cmlidXRlVG9FbGVtZW50KGVsZW1lbnQsIGF0dHJpYnV0ZSwgdmFsdWUpO1xuICAgICAgfVxuICAgICAgZWxlbWVudFtwZW5kaW5nQXR0cmlidXRlc1N5bWJvbF0gPSBudWxsO1xuICAgIH1cblxuICAgIC8vIFNldCBhbnkgcGVuZGluZyBjbGFzc2VzLlxuICAgIGlmIChlbGVtZW50W3BlbmRpbmdDbGFzc2VzU3ltYm9sXSkge1xuICAgICAgZm9yIChsZXQgY2xhc3NOYW1lIGluIGVsZW1lbnRbcGVuZGluZ0NsYXNzZXNTeW1ib2xdKSB7XG4gICAgICAgIGNvbnN0IHZhbHVlID0gZWxlbWVudFtwZW5kaW5nQ2xhc3Nlc1N5bWJvbF1bY2xhc3NOYW1lXTtcbiAgICAgICAgdG9nZ2xlQ2xhc3MoZWxlbWVudCwgY2xhc3NOYW1lLCB2YWx1ZSk7XG4gICAgICB9XG4gICAgICBlbGVtZW50W3BlbmRpbmdDbGFzc2VzU3ltYm9sXSA9IG51bGw7XG4gICAgfVxuICB9LFxuXG4gIC8qKlxuICAgKiBTZXQvdW5zZXQgdGhlIGF0dHJpYnV0ZSB3aXRoIHRoZSBpbmRpY2F0ZWQgbmFtZS5cbiAgICpcbiAgICogVGhpcyBtZXRob2QgZXhpc3RzIHByaW1hcmlseSB0byBoYW5kbGUgdGhlIGNhc2Ugd2hlcmUgYW4gZWxlbWVudCB3YW50cyB0b1xuICAgKiBzZXQgYSBkZWZhdWx0IHByb3BlcnR5IHZhbHVlIHRoYXQgc2hvdWxkIGJlIHJlZmxlY3RlZCBhcyBhbiBhdHRyaWJ1dGUuIEFuXG4gICAqIGltcG9ydGFudCBsaW1pdGF0aW9uIG9mIGN1c3RvbSBlbGVtZW50IGNvbnN0dXJjdG9ycyBpcyB0aGF0IHRoZXkgY2Fubm90XG4gICAqIHNldCBhdHRyaWJ1dGVzLiBBIGNhbGwgdG8gYHNldEF0dHJpYnV0ZWAgZHVyaW5nIHRoZSBjb25zdHJ1Y3RvciB3aWxsXG4gICAqIGJlIGRlZmVycmVkIHVudGlsIHRoZSBlbGVtZW50IGlzIGNvbm5lY3RlZCB0byB0aGUgZG9jdW1lbnQuXG4gICAqXG4gICAqIEBwYXJhbSB7c3RyaW5nfSBhdHRyaWJ1dGUgLSBUaGUgbmFtZSBvZiB0aGUgKmF0dHJpYnV0ZSogKG5vdCBwcm9wZXJ0eSkgdG8gc2V0LlxuICAgKiBAcGFyYW0ge29iamVjdH0gdmFsdWUgLSBUaGUgdmFsdWUgdG8gc2V0LiBJZiBudWxsLCB0aGUgYXR0cmlidXRlIHdpbGwgYmUgcmVtb3ZlZC5cbiAgICovXG4gIHNldEF0dHJpYnV0ZShlbGVtZW50LCBhdHRyaWJ1dGUsIHZhbHVlKSB7XG4gICAgaWYgKGVsZW1lbnRbc2FmZVRvU2V0QXR0cmlidXRlc1N5bWJvbF0pIHtcbiAgICAgIC8vIFNhZmUgdG8gc2V0IGF0dHJpYnV0ZXMgaW1tZWRpYXRlbHkuXG4gICAgICBzZXRBdHRyaWJ1dGVUb0VsZW1lbnQoZWxlbWVudCwgYXR0cmlidXRlLCB2YWx1ZSk7XG4gICAgfSBlbHNlIHtcbiAgICAgIC8vIERlZmVyIHNldHRpbmcgYXR0cmlidXRlcyB1bnRpbCB0aGUgZmlyc3QgdGltZSB3ZSdyZSBjb25uZWN0ZWQuXG4gICAgICBpZiAoIWVsZW1lbnRbcGVuZGluZ0F0dHJpYnV0ZXNTeW1ib2xdKSB7XG4gICAgICAgIGVsZW1lbnRbcGVuZGluZ0F0dHJpYnV0ZXNTeW1ib2xdID0ge307XG4gICAgICB9XG4gICAgICBlbGVtZW50W3BlbmRpbmdBdHRyaWJ1dGVzU3ltYm9sXVthdHRyaWJ1dGVdID0gdmFsdWU7XG4gICAgfVxuICB9LFxuXG4gIC8qKlxuICAgKiBTZXQvdW5zZXQgdGhlIGNsYXNzIHdpdGggdGhlIGluZGljYXRlZCBuYW1lLlxuICAgKlxuICAgKiBUaGlzIG1ldGhvZCBleGlzdHMgcHJpbWFyaWx5IHRvIGhhbmRsZSB0aGUgY2FzZSB3aGVyZSBhbiBlbGVtZW50IHdhbnRzIHRvXG4gICAqIHNldCBhIGRlZmF1bHQgcHJvcGVydHkgdmFsdWUgdGhhdCBzaG91bGQgYmUgcmVmbGVjdGVkIGFzIGFzIGNsYXNzLiBBblxuICAgKiBpbXBvcnRhbnQgbGltaXRhdGlvbiBvZiBjdXN0b20gZWxlbWVudCBjb25zdHVyY3RvcnMgaXMgdGhhdCB0aGV5IGNhbm5vdFxuICAgKiBzZXQgYXR0cmlidXRlcywgaW5jbHVkaW5nIHRoZSBgY2xhc3NgIGF0dHJpYnV0ZS4gQSBjYWxsIHRvXG4gICAqIGB0b2dnbGVDbGFzc2AgZHVyaW5nIHRoZSBjb25zdHJ1Y3RvciB3aWxsIGJlIGRlZmVycmVkIHVudGlsIHRoZSBlbGVtZW50XG4gICAqIGlzIGNvbm5lY3RlZCB0byB0aGUgZG9jdW1lbnQuXG4gICAqXG4gICAqIEBwYXJhbSB7c3RyaW5nfSBjbGFzc05hbWUgLSBUaGUgbmFtZSBvZiB0aGUgY2xhc3MgdG8gc2V0LlxuICAgKiBAcGFyYW0ge29iamVjdH0gdmFsdWUgLSBUcnVlIHRvIHNldCB0aGUgY2xhc3MsIGZhbHNlIHRvIHJlbW92ZSBpdC5cbiAgICovXG4gIHRvZ2dsZUNsYXNzKGVsZW1lbnQsIGNsYXNzTmFtZSwgdmFsdWUpIHtcbiAgICBpZiAoZWxlbWVudFtzYWZlVG9TZXRBdHRyaWJ1dGVzU3ltYm9sXSkge1xuICAgICAgLy8gU2FmZSB0byBzZXQgY2xhc3MgaW1tZWRpYXRlbHkuXG4gICAgICB0b2dnbGVDbGFzcyhlbGVtZW50LCBjbGFzc05hbWUsIHZhbHVlKTtcbiAgICB9IGVsc2Uge1xuICAgICAgLy8gRGVmZXIgc2V0dGluZyBjbGFzcyB1bnRpbCB0aGUgZmlyc3QgdGltZSB3ZSdyZSBjb25uZWN0ZWQuXG4gICAgICBpZiAoIWVsZW1lbnRbcGVuZGluZ0NsYXNzZXNTeW1ib2xdKSB7XG4gICAgICAgIGVsZW1lbnRbcGVuZGluZ0NsYXNzZXNTeW1ib2xdID0ge307XG4gICAgICB9XG4gICAgICBlbGVtZW50W3BlbmRpbmdDbGFzc2VzU3ltYm9sXVtjbGFzc05hbWVdID0gdmFsdWU7XG4gICAgfVxuICB9XG5cbn07XG5cblxuLy8gUmVmbGVjdCB0aGUgYXR0cmlidXRlIHRvIHRoZSBnaXZlbiBlbGVtZW50LlxuLy8gSWYgdGhlIHZhbHVlIGlzIG51bGwsIHJlbW92ZSB0aGUgYXR0cmlidXRlLlxuZnVuY3Rpb24gc2V0QXR0cmlidXRlVG9FbGVtZW50KGVsZW1lbnQsIGF0dHJpYnV0ZU5hbWUsIHZhbHVlKSB7XG4gIGlmICh2YWx1ZSA9PT0gbnVsbCB8fCB0eXBlb2YgdmFsdWUgPT09ICd1bmRlZmluZWQnKSB7XG4gICAgZWxlbWVudC5yZW1vdmVBdHRyaWJ1dGUoYXR0cmlidXRlTmFtZSk7XG4gIH0gZWxzZSB7XG4gICAgY29uc3QgdGV4dCA9IFN0cmluZyh2YWx1ZSk7XG4gICAgLy8gQXZvaWQgcmVjdXJzaXZlIGF0dHJpYnV0ZUNoYW5nZWRDYWxsYmFjayBjYWxscy5cbiAgICBpZiAoZWxlbWVudC5nZXRBdHRyaWJ1dGUoYXR0cmlidXRlTmFtZSkgIT09IHRleHQpIHtcbiAgICAgIGVsZW1lbnQuc2V0QXR0cmlidXRlKGF0dHJpYnV0ZU5hbWUsIHZhbHVlKTtcbiAgICB9XG4gIH1cbn1cbiIsImltcG9ydCBjcmVhdGVTeW1ib2wgZnJvbSAnLi9jcmVhdGVTeW1ib2wnO1xuXG4vKipcbiAqIEEgY29sbGVjdGlvbiBvZiBTeW1ib2wgb2JqZWN0cyBmb3Igc3RhbmRhcmQgY29tcG9uZW50IHByb3BlcnRpZXMgYW5kIG1ldGhvZHMuXG4gKlxuICogVGhlc2UgU3ltYm9sIG9iamVjdHMgYXJlIHVzZWQgdG8gYWxsb3cgbWl4aW5zIGFuZCBhIGNvbXBvbmVudCB0byBpbnRlcm5hbGx5XG4gKiBjb21tdW5pY2F0ZSwgd2l0aG91dCBleHBvc2luZyB0aGVzZSBwcm9wZXJ0aWVzIGFuZCBtZXRob2RzIGluIHRoZSBjb21wb25lbnQnc1xuICogcHVibGljIEFQSS5cbiAqXG4gKiBUbyB1c2UgdGhlc2UgU3ltYm9sIG9iamVjdHMgaW4geW91ciBvd24gY29tcG9uZW50LCBpbmNsdWRlIHRoaXMgbW9kdWxlIGFuZFxuICogdGhlbiBjcmVhdGUgYSBwcm9wZXJ0eSBvciBtZXRob2Qgd2hvc2Uga2V5IGlzIHRoZSBkZXNpcmVkIFN5bWJvbC5cbiAqXG4gKiAgICAgaW1wb3J0ICdTaW5nbGVTZWxlY3Rpb25NaXhpbicgZnJvbSAnYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvU2luZ2xlU2VsZWN0aW9uTWl4aW4nO1xuICogICAgIGltcG9ydCAnc3ltYm9scycgZnJvbSAnYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvc3ltYm9scyc7XG4gKlxuICogICAgIGNsYXNzIE15RWxlbWVudCBleHRlbmRzIFNpbmdsZVNlbGVjdGlvbk1peGluKEhUTUxFbGVtZW50KSB7XG4gKiAgICAgICBbc3ltYm9scy5pdGVtU2VsZWN0ZWRdKGl0ZW0sIHNlbGVjdGVkKSB7XG4gKiAgICAgICAgIC8vIFRoaXMgd2lsbCBiZSBpbnZva2VkIHdoZW5ldmVyIGFuIGl0ZW0gaXMgc2VsZWN0ZWQvZGVzZWxlY3RlZC5cbiAqICAgICAgIH1cbiAqICAgICB9XG4gKlxuICogQG1vZHVsZSBzeW1ib2xzXG4gKi9cbmNvbnN0IHN5bWJvbHMgPSB7XG5cbiAgLyoqXG4gICAqIFN5bWJvbCBmb3IgdGhlIGBkZWZhdWx0c2AgcHJvcGVydHkuXG4gICAqXG4gICAqIFRoaXMgcHJvcGVydHkgY2FuIGJlIHVzZWQgdG8gc2V0IG9yIG92ZXJyaWRlIGRlZmF1bHRzIHRoYXQgd2lsbCBiZSBhcHBsaWVkXG4gICAqIHRvIGEgbmV3IGNvbXBvbmVudCBpbnN0YW5jZS4gV2hlbiBpbXBsZW1lbnRpbmcgdGhpcyBwcm9wZXJ0eSwgdGFrZSBjYXJlIHRvXG4gICAqIGZpcnN0IGFjcXVpcmUgYW55IGRlZmF1bHRzIGRlZmluZWQgYnkgdGhlIHN1cGVyY2xhc3MuIFRoZSBzdGFuZGFyZCBpZGlvbSBpc1xuICAgKiBhcyBmb2xsb3dzOlxuICAgKlxuICAgKiAgICAgZ2V0IFtzeW1ib2xzLmRlZmF1bHRzXSgpIHtcbiAgICogICAgICAgY29uc3QgZGVmYXVsdHMgPSBzdXBlcltzeW1ib2xzLmRlZmF1bHRzXSB8fCB7fTtcbiAgICogICAgICAgLy8gU2V0IG9yIG92ZXJyaWRlIGRlZmF1bHQgdmFsdWVzIGhlcmVcbiAgICogICAgICAgZGVmYXVsdHMuY3VzdG9tUHJvcGVydHkgPSBmYWxzZTtcbiAgICogICAgICAgcmV0dXJuIGRlZmF1bHRzO1xuICAgKiAgICAgfVxuICAgKlxuICAgKiBAdmFyIHtvYmplY3R9IGRlZmF1bHRzXG4gICAqL1xuICBkZWZhdWx0czogY3JlYXRlU3ltYm9sKCdkZWZhdWx0cycpLFxuXG4gIC8qKlxuICAgKiBTeW1ib2wgZm9yIHRoZSBgZHJhZ2dpbmdgIHByb3BlcnR5LlxuICAgKlxuICAgKiBDb21wb25lbnRzIGxpa2UgY2Fyb3VzZWxzIG9mdGVuIGRlZmluZSBhbmltYXRlZCBDU1MgdHJhbnNpdGlvbnMgZm9yXG4gICAqIHNsaWRpbmcgZWZmZWN0cy4gU3VjaCBhIHRyYW5zaXRpb24gc2hvdWxkIHVzdWFsbHkgKm5vdCogYmUgYXBwbGllZCB3aGlsZVxuICAgKiB0aGUgdXNlciBpcyBkcmFnZ2luZywgYmVjYXVzZSBhIENTUyBhbmltYXRpb24gd2lsbCBpbnRyb2R1Y2UgYSBsYWcgdGhhdFxuICAgKiBtYWtlcyB0aGUgc3dpcGUgZmVlbCBzbHVnZ2lzaC4gSW5zdGVhZCwgYXMgbG9uZyBhcyB0aGUgdXNlciBpcyBkcmFnZ2luZ1xuICAgKiB3aXRoIHRoZWlyIGZpbmdlciBkb3duLCB0aGUgdHJhbnNpdGlvbiBzaG91bGQgYmUgc3VwcHJlc3NlZC4gV2hlbiB0aGVcbiAgICogdXNlciByZWxlYXNlcyB0aGVpciBmaW5nZXIsIHRoZSB0cmFuc2l0aW9uIGNhbiBiZSByZXN0b3JlZCwgYWxsb3dpbmcgdGhlXG4gICAqIGFuaW1hdGlvbiB0byBzaG93IHRoZSBjYXJvdXNlbCBzbGlkaW5nIGludG8gaXRzIGZpbmFsIHBvc2l0aW9uLlxuICAgKlxuICAgKiBAdHlwZSB7Ym9vbGVhbn0gdHJ1ZSBpZiBhIGRyYWcgaXMgaW4gcHJvZ3Jlc3MsIGZhbHNlIGlmIG5vdC5cbiAgICovXG4gIGRyYWdnaW5nOiBjcmVhdGVTeW1ib2woJ2RyYWdnaW5nJyksXG5cbiAgLyoqXG4gICAqIFN5bWJvbCBmb3IgdGhlIGBnb0Rvd25gIG1ldGhvZC5cbiAgICpcbiAgICogVGhpcyBtZXRob2QgaXMgaW52b2tlZCB3aGVuIHRoZSB1c2VyIHdhbnRzIHRvIGdvL25hdmlnYXRlIGRvd24uXG4gICAqXG4gICAqIEBmdW5jdGlvbiBnb0Rvd25cbiAgICovXG4gIGdvRG93bjogY3JlYXRlU3ltYm9sKCdnb0Rvd24nKSxcblxuICAvKipcbiAgICogU3ltYm9sIGZvciB0aGUgYGdvRW5kYCBtZXRob2QuXG4gICAqXG4gICAqIFRoaXMgbWV0aG9kIGlzIGludm9rZWQgd2hlbiB0aGUgdXNlciB3YW50cyB0byBnby9uYXZpZ2F0ZSB0byB0aGUgZW5kIChlLmcuLFxuICAgKiBvZiBhIGxpc3QpLlxuICAgKlxuICAgKiBAZnVuY3Rpb24gZ29FbmRcbiAgICovXG4gIGdvRW5kOiBjcmVhdGVTeW1ib2woJ2dvRW5kJyksXG5cbiAgLyoqXG4gICAqIFN5bWJvbCBmb3IgdGhlIGBnb0xlZnRgIG1ldGhvZC5cbiAgICpcbiAgICogVGhpcyBtZXRob2QgaXMgaW52b2tlZCB3aGVuIHRoZSB1c2VyIHdhbnRzIHRvIGdvL25hdmlnYXRlIGxlZnQuXG4gICAqXG4gICAqIEBmdW5jdGlvbiBnb0xlZnRcbiAgICovXG4gIGdvTGVmdDogY3JlYXRlU3ltYm9sKCdnb0xlZnQnKSxcblxuICAvKipcbiAgICogU3ltYm9sIGZvciB0aGUgYGdvUmlnaHRgIG1ldGhvZC5cbiAgICpcbiAgICogVGhpcyBtZXRob2QgaXMgaW52b2tlZCB3aGVuIHRoZSB1c2VyIHdhbnRzIHRvIGdvL25hdmlnYXRlIHJpZ2h0LlxuICAgKlxuICAgKiBAZnVuY3Rpb24gZ29SaWdodFxuICAgKi9cbiAgZ29SaWdodDogY3JlYXRlU3ltYm9sKCdnb1JpZ2h0JyksXG5cbiAgLyoqXG4gICAqIFN5bWJvbCBmb3IgdGhlIGBnb1N0YXJ0YCBtZXRob2QuXG4gICAqXG4gICAqIFRoaXMgbWV0aG9kIGlzIGludm9rZWQgd2hlbiB0aGUgdXNlciB3YW50cyB0byBnby9uYXZpZ2F0ZSB0byB0aGUgc3RhcnRcbiAgICogKGUuZy4sIG9mIGEgbGlzdCkuXG4gICAqXG4gICAqIEBmdW5jdGlvbiBnb1N0YXJ0XG4gICAqL1xuICBnb1N0YXJ0OiBjcmVhdGVTeW1ib2woJ2dvU3RhcnQnKSxcblxuICAvKipcbiAgICogU3ltYm9sIGZvciB0aGUgYGdvVXBgIG1ldGhvZC5cbiAgICpcbiAgICogVGhpcyBtZXRob2QgaXMgaW52b2tlZCB3aGVuIHRoZSB1c2VyIHdhbnRzIHRvIGdvL25hdmlnYXRlIHVwLlxuICAgKlxuICAgKiBAZnVuY3Rpb24gZ29VcFxuICAgKi9cbiAgZ29VcDogY3JlYXRlU3ltYm9sKCdnb1VwJyksXG5cbiAgLyoqXG4gICAqIFN5bWJvbCBmb3IgdGhlIGBpdGVtQWRkZWRgIG1ldGhvZC5cbiAgICpcbiAgICogVGhpcyBtZXRob2QgaXMgaW52b2tlZCB3aGVuIGEgbmV3IGl0ZW0gaXMgYWRkZWQgdG8gYSBsaXN0LlxuICAgKlxuICAgKiBAZnVuY3Rpb24gaXRlbUFkZGVkXG4gICAqIEBwYXJhbSB7SFRNTEVsZW1lbnR9IGl0ZW0gLSB0aGUgaXRlbSBiZWluZyBzZWxlY3RlZC9kZXNlbGVjdGVkXG4gICAqL1xuICBpdGVtQWRkZWQ6IGNyZWF0ZVN5bWJvbCgnaXRlbUFkZGVkJyksXG5cblxuICAvKipcbiAgICogU3ltYm9sIGZvciB0aGUgYGl0ZW1zQ2hhbmdlZGAgbWV0aG9kLlxuICAgKlxuICAgKiBUaGlzIG1ldGhvZCBpcyBpbnZva2VkIHdoZW4gdGhlIHVuZGVybHlpbmcgY29udGVudHMgY2hhbmdlLiBJdCBpcyBhbHNvXG4gICAqIGludm9rZWQgb24gY29tcG9uZW50IGluaXRpYWxpemF0aW9uIOKAkyBzaW5jZSB0aGUgaXRlbXMgaGF2ZSBcImNoYW5nZWRcIiBmcm9tXG4gICAqIGJlaW5nIG5vdGhpbmcuXG4gICAqL1xuICBpdGVtc0NoYW5nZWQ6IGNyZWF0ZVN5bWJvbCgnaXRlbXNDaGFuZ2VkJyksXG5cbiAgLyoqXG4gICAqIFN5bWJvbCBmb3IgdGhlIGBpdGVtU2VsZWN0ZWRgIG1ldGhvZC5cbiAgICpcbiAgICogVGhpcyBtZXRob2QgaXMgaW52b2tlZCB3aGVuIGFuIGl0ZW0gYmVjb21lcyBzZWxlY3RlZCBvciBkZXNlbGVjdGVkLlxuICAgKlxuICAgKiBAZnVuY3Rpb24gaXRlbVNlbGVjdGVkXG4gICAqIEBwYXJhbSB7SFRNTEVsZW1lbnR9IGl0ZW0gLSB0aGUgaXRlbSBiZWluZyBzZWxlY3RlZC9kZXNlbGVjdGVkXG4gICAqIEBwYXJhbSB7Ym9vbGVhbn0gc2VsZWN0ZWQgLSB0cnVlIGlmIHRoZSBpdGVtIGlzIHNlbGVjdGVkLCBmYWxzZSBpZiBub3RcbiAgICovXG4gIGl0ZW1TZWxlY3RlZDogY3JlYXRlU3ltYm9sKCdpdGVtU2VsZWN0ZWQnKSxcblxuICAvKipcbiAgICogU3ltYm9sIGZvciB0aGUgYGtleWRvd25gIG1ldGhvZC5cbiAgICpcbiAgICogVGhpcyBtZXRob2QgaXMgaW52b2tlZCB3aGVuIGFuIGVsZW1lbnQgcmVjZWl2ZXMgYSBga2V5ZG93bmAgZXZlbnQuXG4gICAqXG4gICAqIEBmdW5jdGlvbiBrZXlkb3duXG4gICAqIEBwYXJhbSB7S2V5Ym9hcmRFdmVudH0gZXZlbnQgLSB0aGUgZXZlbnQgYmVpbmcgcHJvY2Vzc2VkXG4gICAqL1xuICBrZXlkb3duOiBjcmVhdGVTeW1ib2woJ2tleWRvd24nKSxcblxuICAvKipcbiAgICogU3ltYm9sIGZvciB0aGUgYHRlbXBsYXRlYCBwcm9wZXJ0eS5cbiAgICpcbiAgICogVGhpcyBwcm9wZXJ0eSByZXR1cm5zIGEgY29tcG9uZW50J3MgdGVtcGxhdGUuXG4gICAqXG4gICAqIEB0eXBlIHtzdHJpbmd8SFRNTEVsZW1lbnR9XG4gICAqL1xuICB0ZW1wbGF0ZTogY3JlYXRlU3ltYm9sKCd0ZW1wbGF0ZScpXG59O1xuXG5leHBvcnQgZGVmYXVsdCBzeW1ib2xzO1xuIiwiLyoqXG4gKiBIZWxwZXIgZnVuY3Rpb24gZm9yIHN0YW5kYXJkIGNsYXNzTGlzdC50b2dnbGUoKSBiZWhhdmlvciBvbiBvbGQgYnJvd3NlcnMsXG4gKiBuYW1lbHkgSUUgMTEuXG4gKlxuICogVGhlIHN0YW5kYXJkXG4gKiBbY2xhc3NsaXN0XShodHRwczovL2RldmVsb3Blci5tb3ppbGxhLm9yZy9lbi1VUy9kb2NzL1dlYi9BUEkvRWxlbWVudC9jbGFzc0xpc3QpXG4gKiBvYmplY3QgaGFzIGEgYHRvZ2dsZSgpYCBmdW5jdGlvbiB0aGF0IHN1cHBvcnRzIGEgc2Vjb25kIEJvb2xlYW4gcGFyYW1ldGVyXG4gKiB0aGF0IGNhbiBiZSB1c2VkIHRvIHN1Y2NpbmN0bHkgdHVybiBhIGNsYXNzIG9uIG9yIG9mZi4gVGhpcyBmZWF0dXJlIGlzIG9mdGVuXG4gKiB1c2VmdWwgaW4gZGVzaWduaW5nIGN1c3RvbSBlbGVtZW50cywgd2hpY2ggbWF5IHdhbnQgdG8gZXh0ZXJuYWxseSByZWZsZWN0XG4gKiBjb21wb25lbnQgc3RhdGUgaW4gYSBDU1MgY2xhc3MgdGhhdCBjYW4gYmUgdXNlZCBmb3Igc3R5bGluZyBwdXJwb3Nlcy5cbiAqXG4gKiBVbmZvcnR1bmF0ZWx5LCBJRSAxMSBkb2VzIG5vdCBzdXBwb3J0IHRoZSBCb29sZWFuIHBhcmFtZXRlciB0b1xuICogYGNsYXNzTGlzdC50b2dnbGUoKWAuIFRoaXMgaGVscGVyIGZ1bmN0aW9uIGJlaGF2ZXMgbGlrZSB0aGUgc3RhbmRhcmRcbiAqIGB0b2dnbGUoKWAsIGluY2x1ZGluZyBzdXBwb3J0IGZvciB0aGUgQm9vbGVhbiBwYXJhbWV0ZXIsIHNvIHRoYXQgaXQgY2FuIGJlXG4gKiB1c2VkIGV2ZW4gb24gSUUgMTEuXG4gKlxuICogQGZ1bmN0aW9uIHRvZ2dsZUNsYXNzXG4gKiBAcGFyYW0ge0hUTUxFbGVtZW50fSBlbGVtZW50IC0gVGhlIGVsZW1lbnQgdG8gbW9kaWZ5XG4gKiBAcGFyYW0ge3N0cmluZ30gY2xhc3NOYW1lIC0gVGhlIGNsYXNzIHRvIGFkZC9yZW1vdmVcbiAqIEBwYXJhbSB7Ym9vbGVhbn0gW2ZvcmNlXSAtIEZvcmNlIHRoZSBjbGFzcyB0byBiZSBhZGRlZCAoaWYgdHJ1ZSkgb3IgcmVtb3ZlZFxuICogICAgICAgICAgICAgICAgICAgICAgICAgICAgKGlmIGZhbHNlKVxuICovXG5leHBvcnQgZGVmYXVsdCBmdW5jdGlvbiB0b2dnbGVDbGFzcyhlbGVtZW50LCBjbGFzc05hbWUsIGZvcmNlKSB7XG4gIGNvbnN0IGNsYXNzTGlzdCA9IGVsZW1lbnQuY2xhc3NMaXN0O1xuICBjb25zdCBhZGRDbGFzcyA9ICh0eXBlb2YgZm9yY2UgPT09ICd1bmRlZmluZWQnKSA/XG4gICAgIWNsYXNzTGlzdC5jb250YWlucyhjbGFzc05hbWUpIDpcbiAgICBmb3JjZTtcbiAgaWYgKGFkZENsYXNzKSB7XG4gICAgY2xhc3NMaXN0LmFkZChjbGFzc05hbWUpO1xuICB9IGVsc2Uge1xuICAgIGNsYXNzTGlzdC5yZW1vdmUoY2xhc3NOYW1lKTtcbiAgfVxuICByZXR1cm4gYWRkQ2xhc3M7XG59XG4iLCJpbXBvcnQgQXR0cmlidXRlTWFyc2hhbGxpbmdNaXhpbiBmcm9tICcuLi8uLi9iYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy9BdHRyaWJ1dGVNYXJzaGFsbGluZ01peGluJztcbmltcG9ydCBDb21wb3NhYmxlTWl4aW4gZnJvbSAnLi4vLi4vYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvQ29tcG9zYWJsZU1peGluJztcbmltcG9ydCBEaXN0cmlidXRlZENoaWxkcmVuTWl4aW4gZnJvbSAnLi4vLi4vYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvRGlzdHJpYnV0ZWRDaGlsZHJlbk1peGluJztcbmltcG9ydCBTaGFkb3dFbGVtZW50UmVmZXJlbmNlc01peGluIGZyb20gJy4uLy4uL2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL1NoYWRvd0VsZW1lbnRSZWZlcmVuY2VzTWl4aW4nO1xuaW1wb3J0IFNoYWRvd1RlbXBsYXRlTWl4aW4gZnJvbSAnLi4vLi4vYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvU2hhZG93VGVtcGxhdGVNaXhpbic7XG5cblxuLyoqXG4gKiBBIHNhbXBsZSBnZW5lcmFsLXB1cnBvc2UgYmFzZSBjbGFzcyBmb3IgZGVmaW5pbmcgY3VzdG9tIGVsZW1lbnRzIHRoYXQgbWl4ZXNcbiAqIGluIHNvbWUgY29tbW9uIGZlYXR1cmVzOiB0ZW1wbGF0ZSBzdGFtcGluZyBpbnRvIGEgc2hhZG93IHJvb3QsIHNoYWRvdyBlbGVtZW50XG4gKiByZWZlcmVuY2VzLCBtYXJzaGFsbGluZyBhdHRyaWJ1dGVzIHRvIHByb3BlcnRpZXMsIGFuZCByZXRyaWV2aW5nIHRoZSBjaGlsZHJlblxuICogZGlzdHJpYnV0ZWQgdG8gYSBjb21wb25lbnQuXG4gKlxuICogVGhpcyBiYXNlIGNsYXNzIGlzIG5vdCBzcGVjaWFsIGluIGFueSB3YXksIGFuZCBpcyBkZWZpbmVkIG9ubHkgYXMgYVxuICogY29udmVuaWVudCBzaG9ydGhhbmQgZm9yIGFwcGx5aW5nIHRoZSBtaXhpbnMgbGlzdGVkIGFib3ZlLiBZb3UgY2FuIHVzZSB0aGlzXG4gKiBjbGFzcyBhcyBhIGJhc2UgY2xhc3MgZm9yIHlvdXIgb3duIGVsZW1lbnRzLCBvciBlYXNpbHkgY3JlYXRlIHlvdXIgb3duIGJhc2VcbiAqIGNsYXNzIGJ5IGFwcGx5aW5nIHRoZSBzYW1lIHNldCBvZiBtaXhpbnMuXG4gKlxuICogVGhlIEVsZW1lbnRCYXNlIGJhc2UgY2xhc3MgZG9lcyBub3QgcmVnaXN0ZXIgaXRzZWxmIGFzIGEgY3VzdG9tIGVsZW1lbnQgd2l0aFxuICogdGhlIGJyb3dzZXIsIGFuZCBoZW5jZSBjYW5ub3QgYmUgaW5kZXBlbmRlbnRseSBpbnN0YW50aWF0ZWQuXG4gKlxuICogQG1peGVzIEF0dHJpYnV0ZU1hcnNoYWxsaW5nTWl4aW5cbiAqIEBtaXhlcyBDb21wb3NhYmxlTWl4aW5cbiAqIEBtaXhlcyBEaXN0cmlidXRlZENoaWxkcmVuTWl4aW5cbiAqIEBtaXhlcyBTaGFkb3dFbGVtZW50UmVmZXJlbmNlc01peGluXG4gKiBAbWl4ZXMgU2hhZG93VGVtcGxhdGVNaXhpblxuICovXG5jbGFzcyBFbGVtZW50QmFzZSBleHRlbmRzIENvbXBvc2FibGVNaXhpbihIVE1MRWxlbWVudCkuY29tcG9zZShcbiAgU2hhZG93VGVtcGxhdGVNaXhpbiwgICAgICAgICAgLy8gYmVmb3JlIG5vZGUgZmluZGluZywgc28gc2hhZG93IHJvb3QgaXMgcG9wdWxhdGVkXG4gIFNoYWRvd0VsZW1lbnRSZWZlcmVuY2VzTWl4aW4sIC8vIGJlZm9yZSBtYXJzaGFsbGluZywgc28gcHJvcGVydGllcyBjYW4gdXNlIHJlZnNcbiAgQXR0cmlidXRlTWFyc2hhbGxpbmdNaXhpbixcbiAgRGlzdHJpYnV0ZWRDaGlsZHJlbk1peGluXG4pIHt9XG5cbmV4cG9ydCBkZWZhdWx0IEVsZW1lbnRCYXNlO1xuIiwiLypcbiAqIFRoaXMgZmlsZSBpcyB0cmFuc3BpbGVkIHRvIGNyZWF0ZSBhbiBFUzUtY29tcGF0aWJsZSBkaXN0cmlidXRpb24gaW4gd2hpY2hcbiAqIHRoZSBwYWNrYWdlJ3MgbWFpbiBmZWF0dXJlKHMpIGFyZSBhdmFpbGFibGUgdmlhIHRoZSB3aW5kb3cuQmFzaWMgZ2xvYmFsLlxuICogSWYgeW91J3JlIGFscmVhZHkgdXNpbmcgRVM2IHlvdXJzZWxmLCBpZ25vcmUgdGhpcyBmaWxlLCBhbmQgaW5zdGVhZCBpbXBvcnRcbiAqIHRoZSBzb3VyY2UgZmlsZShzKSB5b3Ugd2FudCBmcm9tIHRoZSBzcmMgZm9sZGVyLlxuICovXG5cbmltcG9ydCBTbGlkZXNob3cgZnJvbSAnLi9zcmMvU2xpZGVzaG93Jztcblxud2luZG93LkJhc2ljID0gd2luZG93LkJhc2ljIHx8IHt9O1xud2luZG93LkJhc2ljLlNsaWRlc2hvdyA9IFNsaWRlc2hvdztcbiIsImltcG9ydCBFbGVtZW50QmFzZSBmcm9tICcuLi8uLi9iYXNpYy1lbGVtZW50LWJhc2Uvc3JjL0VsZW1lbnRCYXNlJztcbmltcG9ydCBDb250ZW50SXRlbXNNaXhpbiBmcm9tICcuLi8uLi9iYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy9Db250ZW50SXRlbXNNaXhpbic7XG5pbXBvcnQgRGlzdHJpYnV0ZWRDaGlsZHJlbkNvbnRlbnRNaXhpbiBmcm9tICcuLi8uLi9iYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy9EaXN0cmlidXRlZENoaWxkcmVuQ29udGVudE1peGluJztcbmltcG9ydCBGcmFjdGlvbmFsU2VsZWN0aW9uTWl4aW4gZnJvbSAnLi4vLi4vYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvRnJhY3Rpb25hbFNlbGVjdGlvbk1peGluJztcbmltcG9ydCBTZWxlY3Rpb25BbmltYXRpb25NaXhpbiBmcm9tICcuLi8uLi9iYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy9TZWxlY3Rpb25BbmltYXRpb25NaXhpbic7XG5pbXBvcnQgU2VsZWN0aW9uQXJpYUFjdGl2ZU1peGluIGZyb20gJy4uLy4uL2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvc3JjL1NlbGVjdGlvbkFyaWFBY3RpdmVNaXhpbic7XG5pbXBvcnQgU2luZ2xlU2VsZWN0aW9uTWl4aW4gZnJvbSAnLi4vLi4vYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvU2luZ2xlU2VsZWN0aW9uTWl4aW4nO1xuaW1wb3J0IHN5bWJvbHMgZnJvbSAnLi4vLi4vYmFzaWMtY29tcG9uZW50LW1peGlucy9zcmMvc3ltYm9scyc7XG5pbXBvcnQgVGltZXJTZWxlY3Rpb25NaXhpbiBmcm9tICcuLi8uLi9iYXNpYy1jb21wb25lbnQtbWl4aW5zL3NyYy9UaW1lclNlbGVjdGlvbk1peGluJztcblxuXG5jb25zdCBiYXNlID0gRWxlbWVudEJhc2UuY29tcG9zZShcbiAgQ29udGVudEl0ZW1zTWl4aW4sXG4gIERpc3RyaWJ1dGVkQ2hpbGRyZW5Db250ZW50TWl4aW4sXG4gIEZyYWN0aW9uYWxTZWxlY3Rpb25NaXhpbixcbiAgU2VsZWN0aW9uQW5pbWF0aW9uTWl4aW4sXG4gIFNlbGVjdGlvbkFyaWFBY3RpdmVNaXhpbixcbiAgU2luZ2xlU2VsZWN0aW9uTWl4aW4sXG4gIFRpbWVyU2VsZWN0aW9uTWl4aW5cbik7XG5cblxuLyoqXG4gKiBTbGlkZXNob3cgd2l0aCBhbmltYXRlZCB0cmFuc2l0aW9ucy5cbiAqXG4gKiBCeSBkZWZhdWx0IHRoZSBzbGlkZXNob3cgd2lsbCBpbW1lZGlhdGVseSBiZWdpbiBwbGF5aW5nIHdoZW4gaXQgaXMgY29ubmVjdGVkXG4gKiB0byB0aGUgZG9jdW1lbnQsIGFkdmFuY2UgZXZlcnkgMzAwMCBtcyAoMyBzZWNvbmRzKSwgYW5kIHVzZSBhIHNpbXBsZVxuICogY3Jvc3NmYWRlIGVmZmVjdC5cbiAqXG4gKiBUaGlzIGNvbXBvbmVudCBjYW4gYmUgdXNlZCBvbiBpdHMgb3duLiBUbyBpbmNvcnBvcmF0ZSBzbGlkZXNob3cgYmVoYXZpb3IgaW50b1xuICogYSBjb21wb25lbnQgb2YgeW91ciBvd24sIGFwcGx5IHRoZVxuICogW1RpbWVyU2VsZWN0aW9uTWl4aW5dKC4uL2Jhc2ljLWNvbXBvbmVudC1taXhpbnMvZG9jcy9UaW1lclNlbGVjdGlvbk1peGluLm1kKS5cbiAqXG4gKiBAZXh0ZW5kcyBFbGVtZW50QmFzZVxuICogQG1peGVzIENvbnRlbnRJdGVtc01peGluXG4gKiBAbWl4ZXMgRGlzdHJpYnV0ZWRDaGlsZHJlbkNvbnRlbnRNaXhpblxuICogQG1peGVzIEZyYWN0aW9uYWxTZWxlY3Rpb25NaXhpblxuICogQG1peGVzIFNlbGVjdGlvbkFuaW1hdGlvbk1peGluXG4gKiBAbWl4ZXMgU2VsZWN0aW9uQXJpYUFjdGl2ZU1peGluXG4gKiBAbWl4ZXMgU2luZ2xlU2VsZWN0aW9uTWl4aW5cbiAqIEBtaXhlcyBUaW1lclNlbGVjdGlvbk1peGluXG4gKi9cbmNsYXNzIFNsaWRlc2hvdyBleHRlbmRzIGJhc2Uge1xuXG4gIGdldCBbc3ltYm9scy5kZWZhdWx0c10oKSB7XG4gICAgY29uc3QgZGVmYXVsdHMgPSBzdXBlcltzeW1ib2xzLmRlZmF1bHRzXSB8fCB7fTtcbiAgICBkZWZhdWx0cy5wbGF5aW5nID0gdHJ1ZTtcbiAgICBkZWZhdWx0cy5zZWxlY3Rpb25BbmltYXRpb25EdXJhdGlvbiA9IDUwMDtcbiAgICBkZWZhdWx0cy5zZWxlY3Rpb25BbmltYXRpb25FZmZlY3QgPSAnY3Jvc3NmYWRlJztcbiAgICBkZWZhdWx0cy5zZWxlY3Rpb25SZXF1aXJlZCA9IHRydWU7XG4gICAgZGVmYXVsdHMuc2VsZWN0aW9uVGltZXJEdXJhdGlvbiA9IDMwMDA7XG4gICAgZGVmYXVsdHMuc2VsZWN0aW9uV3JhcHMgPSB0cnVlO1xuICAgIHJldHVybiBkZWZhdWx0cztcbiAgfVxuXG4gIGdldCBbc3ltYm9scy50ZW1wbGF0ZV0oKSB7XG4gICAgcmV0dXJuIGBcbiAgICAgIDxzdHlsZT5cbiAgICAgIDpob3N0IHtcbiAgICAgICAgZGlzcGxheTogLXdlYmtpdC1mbGV4O1xuICAgICAgICBkaXNwbGF5OiBmbGV4O1xuICAgICAgICBvdmVyZmxvdzogaGlkZGVuO1xuICAgICAgICBwb3NpdGlvbjogcmVsYXRpdmU7XG4gICAgICB9XG5cbiAgICAgICNjb250YWluZXIgOjpzbG90dGVkKCopIHtcbiAgICAgICAgaGVpZ2h0OiAxMDAlO1xuICAgICAgICBvYmplY3QtZml0OiBjb250YWluO1xuICAgICAgICBwb3NpdGlvbjogYWJzb2x1dGU7XG4gICAgICAgIHdpZHRoOiAxMDAlO1xuICAgICAgICB3aWxsLWNoYW5nZTogdHJhbnNmb3JtO1xuICAgICAgfVxuICAgICAgPC9zdHlsZT5cblxuICAgICAgPGRpdiBpZD1cImNvbnRhaW5lclwiIHJvbGU9XCJub25lXCI+XG4gICAgICAgIDxzbG90Pjwvc2xvdD5cbiAgICAgIDwvZGl2PlxuICAgIGA7XG4gIH1cblxufVxuXG5cbmN1c3RvbUVsZW1lbnRzLmRlZmluZSgnYmFzaWMtc2xpZGVzaG93JywgU2xpZGVzaG93KTtcbmV4cG9ydCBkZWZhdWx0IFNsaWRlc2hvdztcbiJdfQ==
+!function t(e,o,n){function r(a,c){if(!o[a]){if(!e[a]){var l="function"==typeof require&&require;if(!c&&l)return l(a,!0);if(i)return i(a,!0);var u=new Error("Cannot find module '"+a+"'");throw u.code="MODULE_NOT_FOUND",u}var s=o[a]={exports:{}};e[a][0].call(s.exports,function(t){var o=e[a][1][t];return r(o?o:t)},s,s.exports,t,e,o,n)}return o[a].exports}for(var i="function"==typeof require&&require,a=0;a\n :host {\n overflow: hidden;\n position: relative;\n }\n\n #container ::slotted(*) {\n height: 100%;\n object-fit: contain;\n position: absolute;\n width: 100%;\n will-change: transform;\n }\n \n\n \n \n
\n '}}]),e}(x);customElements.define("basic-animation-stage",S),o.default=S},{"../../basic-component-mixins/src/ContentItemsMixin":4,"../../basic-component-mixins/src/DistributedChildrenContentMixin":5,"../../basic-component-mixins/src/FractionalSelectionMixin":7,"../../basic-component-mixins/src/SelectionAnimationMixin":8,"../../basic-component-mixins/src/SelectionAriaActiveMixin":9,"../../basic-component-mixins/src/SingleSelectionMixin":12,"../../basic-component-mixins/src/symbols":17,"../../basic-element-base/src/ElementBase":19}],2:[function(t,e,o){"use strict";function n(t){return t&&t.__esModule?t:{default:t}}function r(t,e){if(!(t instanceof e))throw new TypeError("Cannot call a class as a function")}function i(t,e){if(!t)throw new ReferenceError("this hasn't been initialised - super() hasn't been called");return!e||"object"!=typeof e&&"function"!=typeof e?t:e}function a(t,e){if("function"!=typeof e&&null!==e)throw new TypeError("Super expression must either be null or a function, not "+typeof e);t.prototype=Object.create(e&&e.prototype,{constructor:{value:t,enumerable:!1,writable:!0,configurable:!0}}),e&&(Object.setPrototypeOf?Object.setPrototypeOf(t,e):t.__proto__=e)}function c(t){var e=y[t];if(!e){var o=/-([a-z])/g;e=t.replace(o,function(t){return t[1].toUpperCase()}),y[t]=e}return e}function l(t){if(t===HTMLElement||t===Object)return[];var e=Object.getPrototypeOf(t.prototype).constructor,o=l(e),n=Object.getOwnPropertyNames(t.prototype),r=n.filter(function(e){return"function"==typeof Object.getOwnPropertyDescriptor(t.prototype,e).set}),i=r.map(function(t){return u(t)}),a=i.filter(function(t){return o.indexOf(t)<0});return o.concat(a)}function u(t){var e=h[t];if(!e){var o=/([A-Z])/g;e=t.replace(o,"-$1").toLowerCase()}return e}Object.defineProperty(o,"__esModule",{value:!0});var s=function(){function t(t,e){for(var o=0;o2&&void 0!==arguments[2]?arguments[2]:[];return Object.getOwnPropertyNames(t).forEach(function(n){if(o.indexOf(n)<0){var r=Object.getOwnPropertyDescriptor(t,n);Object.defineProperty(e,n,r)}}),e}Object.defineProperty(o,"__esModule",{value:!0});var l=function(){function t(t,e){for(var o=0;o=o?o+c.helpers.damping(t-o):t},damping:function(t){var e=-1/(t+1)+1;return e},elementSelection:function(t){var e=t.selectedIndex;if(!(e<0)){var o=t.selectedFraction||0;return e+o}},selectionParts:function(t){var e=t<0?Math.ceil(t):Math.floor(t),o=t-e;return{index:e,fraction:o}},wrappedSelection:function(t,e){return(t%e+e)%e},wrappedSelectionParts:function(t,e,o){return o&&(t=c.helpers.wrappedSelection(t,e)),c.helpers.selectionParts(t)}}},{"./createSymbol":14}],8:[function(t,e,o){"use strict";function n(t){return t&&t.__esModule?t:{default:t}}function r(t,e){if(!(t instanceof e))throw new TypeError("Cannot call a class as a function")}function i(t,e){if(!t)throw new ReferenceError("this hasn't been initialised - super() hasn't been called");return!e||"object"!=typeof e&&"function"!=typeof e?t:e}function a(t,e){if("function"!=typeof e&&null!==e)throw new TypeError("Super expression must either be null or a function, not "+typeof e);t.prototype=Object.create(e&&e.prototype,{constructor:{value:t,enumerable:!1,writable:!0,configurable:!0}}),e&&(Object.setPrototypeOf?Object.setPrototypeOf(t,e):t.__proto__=e)}function c(t){var e=function(e){function o(){r(this,o);var t=i(this,(o.__proto__||Object.getPrototypeOf(o)).call(this));return"undefined"==typeof t.selectionAnimationDuration&&(t.selectionAnimationDuration=t[S.default.defaults].selectionAnimationDuration),"undefined"==typeof t.selectionAnimationEffect&&null==t.selectionAnimationKeyframes&&(t.selectionAnimationEffect=t[S.default.defaults].selectionAnimationEffect),t[S.default.dragging]=!1,t}return a(o,e),v(o,[{key:S.default.itemAdded,value:function(t){t.setAttribute("aria-hidden",!1)}},{key:S.default.itemsChanged,value:function(){O(o.prototype.__proto__||Object.getPrototypeOf(o.prototype),S.default.itemsChanged,this)&&O(o.prototype.__proto__||Object.getPrototypeOf(o.prototype),S.default.itemsChanged,this).call(this),d(this),f(this)}},{key:"resetAnimations",value:function(){d(this)}},{key:S.default.defaults,get:function(){var t=O(o.prototype.__proto__||Object.getPrototypeOf(o.prototype),S.default.defaults,this)||{};return t.selectionAnimationDuration=250,t.selectionAnimationEffect="slide",t}},{key:S.default.dragging,get:function(){return this[E]},set:function(e){var n=this[S.default.dragging];this[E]=e,S.default.dragging in t.prototype&&m(o.prototype.__proto__||Object.getPrototypeOf(o.prototype),S.default.dragging,e,this),e&&!n&&(this[F]=!0)}},{key:"selectedFraction",get:function(){return O(o.prototype.__proto__||Object.getPrototypeOf(o.prototype),"selectedFraction",this)||0},set:function(e){"selectedFraction"in t.prototype&&m(o.prototype.__proto__||Object.getPrototypeOf(o.prototype),"selectedFraction",e,this),f(this,this.selectedIndex,e)}},{key:"selectedIndex",get:function(){return O(o.prototype.__proto__||Object.getPrototypeOf(o.prototype),"selectedIndex",this)},set:function(e){"selectedIndex"in t.prototype&&m(o.prototype.__proto__||Object.getPrototypeOf(o.prototype),"selectedIndex",e,this),f(this,e,0)}},{key:"selectionAnimationDuration",get:function(){return this[T]},set:function(e){this[T]=e,"selectionAnimationDuration"in t.prototype&&m(o.prototype.__proto__||Object.getPrototypeOf(o.prototype),"selectionAnimationDuration",e,this)}},{key:"selectionAnimationEffect",get:function(){return this[I]},set:function(e){this[I]=e,"selectionAnimationEffect"in t.prototype&&m(o.prototype.__proto__||Object.getPrototypeOf(o.prototype),"selectionAnimationEffect",e,this),this.selectionAnimationKeyframes=c.standardEffectKeyframes[e]}},{key:"selectionAnimationKeyframes",get:function(){return this[D]},set:function(e){this[D]=e,"selectionAnimationKeyframes"in t.prototype&&m(o.prototype.__proto__||Object.getPrototypeOf(o.prototype),"selectionAnimationKeyframes",e,this),d(this),f(this)}},{key:"selectionWraps",get:function(){return O(o.prototype.__proto__||Object.getPrototypeOf(o.prototype),"selectionWraps",this)},set:function(e){"selectionWraps"in t.prototype&&m(o.prototype.__proto__||Object.getPrototypeOf(o.prototype),"selectionWraps",e,this),d(this),f(this)}}]),o}(t);return e}function l(t,e,o){d(t);var n=t.items,r=t.selectionAnimationKeyframes;t[k]=!0;var i=c.helpers.effectTimingsForSelectionAnimation(t,e,o),a=n.length,l=t.selectionWraps,u=w.default.helpers.selectionParts(o,a,l).index,f=_(a,l,e,o),p=f>=0,h=u+(p?1:-1);l?h=w.default.helpers.wrappedSelection(h,a):s(t,h)||(h=null);var v=void 0;i.forEach(function(e,o){var i=n[o];if(e){b(i,!0);var a=i.animate(r,e);t[C][o]=a,o===h&&(h=null),0!==e.endDelay&&(v={animation:a,index:o,timing:e,forward:p})}else b(i,!1)}),null!=v?(v.nextUpIndex=h,v.animation.onfinish=function(e){return y(t,v)},t[A]=v.animation):t[k]=!1}function u(t,e){if(null==t[C])return null;var o=t[C][e];if(!o){var n=t.items[e];o=n.animate(t.selectionAnimationKeyframes,{duration:t.selectionAnimationDuration,fill:"both"}),o.pause(),t[C][e]=o}return o}function s(t,e){return e>=0&&t.items&&e1&&void 0!==arguments[1]?arguments[1]:t.selectedIndex,o=arguments.length>2&&void 0!==arguments[2]?arguments[2]:t.selectedFraction,n=t.items?t.items.length:0;if(0!==n&&!(e<0)){var r=e+o;r=t.selectionWraps?w.default.helpers.wrappedSelection(r,n):w.default.helpers.dampedSelection(r,n);var i=t[M];if(t[S.default.dragging]||null==i||i===r){if(0===o&&t[k])return;p(t,r)}else l(t,i,r);t[M]=r}}function p(t,e){t[F]&&(d(t),t[F]=!1);var o=c.helpers.animationFractionsForSelection(t,e);o.map(function(e,o){var n=t.items[o];null!=e?(b(n,!0),h(t,o,e)):b(n,!1)})}function d(t){var e=t[C];e&&e.forEach(function(t,o){t&&(t.cancel(),e[o]=null)});var o=t.items?t.items.length:0;e&&e.length===o||(t[C]=new Array(o))}function y(t,e){var o=e.nextUpIndex;if(null!=o){t[C][o]&&(t[C][o].cancel(),t[C][o]=null);var n=e.forward?0:1;h(t,o,n),b(t.items[o],!0)}t[A].onfinish=null,t[k]=!1}function h(t,e,o){var n=u(t,e);if(n){var r=t.selectionAnimationDuration;r&&(n.currentTime=o*r)}}function b(t,e){t.style.visibility=e?"visible":"hidden"}function _(t,e,o,n){var r=n-o;if(e&&t>1){var i=t-Math.abs(r);i<=1&&(r=r<0?i:-i)}return r}Object.defineProperty(o,"__esModule",{value:!0});var v=function(){function t(t,e){for(var o=0;o=0&&a<=1?a:null})}},effectTimingsForSelectionAnimation:function(t,e,o){var n=t.items;if(n){var r=n.length,i=t.selectionWraps,a=w.default.helpers.wrappedSelectionParts(o,r,i).index,c=_(r,i,e,o),l=c>=0?"normal":"reverse",u="both",s=t.selectionAnimationDuration,f=0!==c?2*s/Math.ceil(Math.abs(c)):0,p=n.map(function(t,e){var n=_(r,i,e,o),s=c-n;if(c<0&&(s=-s),Math.ceil(s)>=0&&s<=Math.abs(c)){var p=f*(s-1)/2,d=e===a?-f/2:0;return{duration:f,direction:l,fill:u,delay:p,endDelay:d}}return null});return p}}},c.standardEffectKeyframes={crossfade:[{opacity:0},{opacity:1},{opacity:0}],reveal:[{transform:"translateX(0%)",zIndex:0},{transform:"translateX(0%)",zIndex:1},{transform:"translateX(-100%)",zIndex:2}],revealWithFade:[{transform:"translateX(0%) scale(0.75)",opacity:0,zIndex:0},{transform:"translateX(0%) scale(1.0)",opacity:1,zIndex:1},{transform:"translateX(-100%) scale(1.0)",opacity:1,zIndex:2}],showAdjacent:[{transform:"translateX(78%) scale(0.7)",zIndex:0},{transform:"translateX(0%) scale(0.82)",zIndex:1},{transform:"translateX(-78%) scale(0.7)",zIndex:0}],slide:[{transform:"translateX(100%)"},{transform:"translateX(-100%)"}],slideWithGap:[{transform:"translateX(110%)"},{transform:"translateX(-110%)"}]}},{"./FractionalSelectionMixin":7,"./createSymbol":14,"./symbols":17}],9:[function(t,e,o){"use strict";function n(t){return t&&t.__esModule?t:{default:t}}function r(t,e){if(!(t instanceof e))throw new TypeError("Cannot call a class as a function")}function i(t,e){if(!t)throw new ReferenceError("this hasn't been initialised - super() hasn't been called");return!e||"object"!=typeof e&&"function"!=typeof e?t:e}function a(t,e){if("function"!=typeof e&&null!==e)throw new TypeError("Super expression must either be null or a function, not "+typeof e);t.prototype=Object.create(e&&e.prototype,{constructor:{value:t,enumerable:!1,writable:!0,configurable:!0}}),e&&(Object.setPrototypeOf?Object.setPrototypeOf(t,e):t.__proto__=e)}Object.defineProperty(o,"__esModule",{value:!0});var c=function(){function t(t,e){for(var o=0;o0;)e.content.appendChild(o.childNodes[0]);return e}function l(t,e){window.WebComponents.ShadowCSS.shimStyling(t.content,e)}Object.defineProperty(o,"__esModule",{value:!0});var u=t("../src/symbols"),s=n(u);o.default=function(t){var e=function(t){function e(){r(this,e);var t=i(this,(e.__proto__||Object.getPrototypeOf(e)).call(this)),o=t[s.default.template];if(o){"string"==typeof o&&(o=c(o)),window.ShadowDOMPolyfill&&l(o,t.localName);var n=t.attachShadow({mode:"open"}),a=document.importNode(o.content,!0);n.appendChild(a)}return t}return a(e,t),e}(t);return e}},{"../src/symbols":17}],12:[function(t,e,o){"use strict";function n(t){return t&&t.__esModule?t:{default:t}}function r(t,e){if(!(t instanceof e))throw new TypeError("Cannot call a class as a function");
+}function i(t,e){if(!t)throw new ReferenceError("this hasn't been initialised - super() hasn't been called");return!e||"object"!=typeof e&&"function"!=typeof e?t:e}function a(t,e){if("function"!=typeof e&&null!==e)throw new TypeError("Super expression must either be null or a function, not "+typeof e);t.prototype=Object.create(e&&e.prototype,{constructor:{value:t,enumerable:!1,writable:!0,configurable:!0}}),e&&(Object.setPrototypeOf?Object.setPrototypeOf(t,e):t.__proto__=e)}function c(t,e){var o=t.items.length,n=t.selectionWraps?(e%o+o)%o:Math.max(Math.min(e,o-1),0),r=t.selectedIndex;return r!==n&&(t.selectedIndex=n,!0)}function l(t){var e=t.items,o=e?e.length:0,n=t.selectedItem;if(n)if(0===o)t.selectedItem=null;else{var r=Array.prototype.indexOf.call(e,n),i=t.selectedIndex;if(r<0){var a=Math.min(i,o-1);t.selectedItem=e[a]}else r!==i&&(t.selectedIndex=r)}else t.selectionRequired&&(t.selectedIndex=0)}function u(t){var e=void 0,o=void 0,n=t.items;if(null!=n&&0!==n.length||(e=!1,o=!1),t.selectionWraps)e=!0,o=!0;else{var r=t.selectedIndex;r<0&&n.length>0?(e=!0,o=!0):(o=r>0,e=r0;a&&e>=0&&e=0?i[e]:null,this[j]=r}else r=this[j];if("selectedIndex"in t.prototype&&p(o.prototype.__proto__||Object.getPrototypeOf(o.prototype),"selectedIndex",e,this),e!==n){this[P]=e;var c=new CustomEvent("selected-index-changed",{detail:{selectedIndex:e,value:e}});this.dispatchEvent(c)}this[w]!==r&&(this.selectedItem=r)}},{key:"selectedItem",get:function(){return this[j]||null},set:function(e){var n=this[w],r=void 0;if(e!==this[j]){var i=this.items,a=i&&i.length>0;r=a?Array.prototype.indexOf.call(i,e):-1,this[g]=r,r<0&&(e=null),this[j]=e}else r=this[g];if("selectedItem"in t.prototype&&p(o.prototype.__proto__||Object.getPrototypeOf(o.prototype),"selectedItem",e,this),e!==n){this[w]=e,n&&this[b.default.itemSelected](n,!1),e&&this[b.default.itemSelected](e,!0),u(this);var c=new CustomEvent("selected-item-changed",{detail:{selectedItem:e,value:e}});this.dispatchEvent(c)}this[P]!==r&&(this.selectedIndex=r)}},{key:"selectionRequired",get:function(){return this[m]},set:function(e){this[m]=e,"selectionRequired"in t.prototype&&p(o.prototype.__proto__||Object.getPrototypeOf(o.prototype),"selectionRequired",e,this),l(this)}},{key:"selectionWraps",get:function(){return this[O]},set:function(e){this[O]="true"===String(e),"selectionWraps"in t.prototype&&p(o.prototype.__proto__||Object.getPrototypeOf(o.prototype),"selectionWraps",e,this),u(this)}}]),o}(t);return e}},{"./createSymbol":14,"./symbols":17}],13:[function(t,e,o){"use strict";function n(t){return t&&t.__esModule?t:{default:t}}function r(t,e){if(!(t instanceof e))throw new TypeError("Cannot call a class as a function")}function i(t,e){if(!t)throw new ReferenceError("this hasn't been initialised - super() hasn't been called");return!e||"object"!=typeof e&&"function"!=typeof e?t:e}function a(t,e){if("function"!=typeof e&&null!==e)throw new TypeError("Super expression must either be null or a function, not "+typeof e);t.prototype=Object.create(e&&e.prototype,{constructor:{value:t,enumerable:!1,writable:!0,configurable:!0}}),e&&(Object.setPrototypeOf?Object.setPrototypeOf(t,e):t.__proto__=e)}function c(t){t[O]&&(clearTimeout(t[O]),t[O]=null)}function l(t){c(t),t.playing&&t.items&&t.items.length>0&&u(t)}function u(t){c(t),t[O]=setTimeout(function(){s(t)},t.selectionTimerDuration)}function s(t){var e=t.items;e&&e.length>0&&(null==t.selectedIndex||t.selectedIndex===e.length-1?t.selectFirst():t.selectNext())}Object.defineProperty(o,"__esModule",{value:!0});var f=function(){function t(t,e){for(var o=0;o0;){var t=i.shift();t()}}Object.defineProperty(o,"__esModule",{value:!0}),o.default=n;var i=[],a=document.createTextNode(""),c=0,l=new MutationObserver(r);l.observe(a,{characterData:!0})},{}],16:[function(t,e,o){"use strict";function n(t){return t&&t.__esModule?t:{default:t}}function r(t,e,o){if(null===o||"undefined"==typeof o)t.removeAttribute(e);else{var n=String(o);t.getAttribute(e)!==n&&t.setAttribute(e,o)}}Object.defineProperty(o,"__esModule",{value:!0});var i=t("./createSymbol"),a=n(i),c=t("./toggleClass"),l=n(c),u=(0,a.default)("safeToSetAttributes"),s=(0,a.default)("pendingAttributes"),f=(0,a.default)("pendingClasses");o.default={connected:function(t){if(t[u]=!0,t[s]){for(var e in t[s]){var o=t[s][e];r(t,e,o)}t[s]=null}if(t[f]){for(var n in t[f]){var i=t[f][n];(0,l.default)(t,n,i)}t[f]=null}},setAttribute:function(t,e,o){t[u]?r(t,e,o):(t[s]||(t[s]={}),t[s][e]=o)},toggleClass:function(t,e,o){t[u]?(0,l.default)(t,e,o):(t[f]||(t[f]={}),t[f][e]=o)}}},{"./createSymbol":14,"./toggleClass":18}],17:[function(t,e,o){"use strict";function n(t){return t&&t.__esModule?t:{default:t}}Object.defineProperty(o,"__esModule",{value:!0});var r=t("./createSymbol"),i=n(r),a={defaults:(0,i.default)("defaults"),dragging:(0,i.default)("dragging"),goDown:(0,i.default)("goDown"),goEnd:(0,i.default)("goEnd"),goLeft:(0,i.default)("goLeft"),goRight:(0,i.default)("goRight"),goStart:(0,i.default)("goStart"),goUp:(0,i.default)("goUp"),itemAdded:(0,i.default)("itemAdded"),itemsChanged:(0,i.default)("itemsChanged"),itemSelected:(0,i.default)("itemSelected"),keydown:(0,i.default)("keydown"),template:(0,i.default)("template")};o.default=a},{"./createSymbol":14}],18:[function(t,e,o){"use strict";function n(t,e,o){var n=t.classList,r="undefined"==typeof o?!n.contains(e):o;return r?n.add(e):n.remove(e),r}Object.defineProperty(o,"__esModule",{value:!0}),o.default=n},{}],19:[function(t,e,o){"use strict";function n(t){return t&&t.__esModule?t:{default:t}}function r(t,e){if(!(t instanceof e))throw new TypeError("Cannot call a class as a function")}function i(t,e){if(!t)throw new ReferenceError("this hasn't been initialised - super() hasn't been called");return!e||"object"!=typeof e&&"function"!=typeof e?t:e}function a(t,e){if("function"!=typeof e&&null!==e)throw new TypeError("Super expression must either be null or a function, not "+typeof e);t.prototype=Object.create(e&&e.prototype,{constructor:{value:t,enumerable:!1,writable:!0,configurable:!0}}),e&&(Object.setPrototypeOf?Object.setPrototypeOf(t,e):t.__proto__=e)}Object.defineProperty(o,"__esModule",{value:!0});var c=t("../../basic-component-mixins/src/AttributeMarshallingMixin"),l=n(c),u=t("../../basic-component-mixins/src/ComposableMixin"),s=n(u),f=t("../../basic-component-mixins/src/DistributedChildrenMixin"),p=n(f),d=t("../../basic-component-mixins/src/ShadowElementReferencesMixin"),y=n(d),h=t("../../basic-component-mixins/src/ShadowTemplateMixin"),b=n(h),_=function(t){function e(){return r(this,e),i(this,(e.__proto__||Object.getPrototypeOf(e)).apply(this,arguments))}return a(e,t),e}((0,s.default)(HTMLElement).compose(b.default,y.default,l.default,p.default));o.default=_},{"../../basic-component-mixins/src/AttributeMarshallingMixin":2,"../../basic-component-mixins/src/ComposableMixin":3,"../../basic-component-mixins/src/DistributedChildrenMixin":6,"../../basic-component-mixins/src/ShadowElementReferencesMixin":10,"../../basic-component-mixins/src/ShadowTemplateMixin":11}],20:[function(t,e,o){"use strict";function n(t){return t&&t.__esModule?t:{default:t}}var r=t("./src/Slideshow"),i=n(r);window.Basic=window.Basic||{},window.Basic.Slideshow=i.default},{"./src/Slideshow":21}],21:[function(t,e,o){"use strict";function n(t){return t&&t.__esModule?t:{default:t}}function r(t,e){if(!(t instanceof e))throw new TypeError("Cannot call a class as a function")}function i(t,e){if(!t)throw new ReferenceError("this hasn't been initialised - super() hasn't been called");return!e||"object"!=typeof e&&"function"!=typeof e?t:e}function a(t,e){if("function"!=typeof e&&null!==e)throw new TypeError("Super expression must either be null or a function, not "+typeof e);t.prototype=Object.create(e&&e.prototype,{constructor:{value:t,enumerable:!1,writable:!0,configurable:!0}}),e&&(Object.setPrototypeOf?Object.setPrototypeOf(t,e):t.__proto__=e)}Object.defineProperty(o,"__esModule",{value:!0});var c=function(){function t(t,e){for(var o=0;o\n :host {\n overflow: hidden;\n position: relative;\n }\n\n #container ::slotted(*) {\n height: 100%;\n object-fit: contain;\n position: absolute;\n width: 100%;\n will-change: transform;\n }\n \n\n \n \n
\n `;\n }\n\n}\n\n\ncustomElements.define('basic-animation-stage', AnimationStage);\nexport default AnimationStage;\n","import safeAttributes from './safeAttributes';\n\n\n// Memoized maps of attribute to property names and vice versa.\nconst attributeToPropertyNames = {};\nconst propertyNamesToAttributes = {};\n\n\n/* Exported function extends a base class with AttributeMarshalling. */\nexport default (base) => {\n\n /**\n * Mixin which marshalls attributes to properties and vice versa.\n *\n * If your component exposes a setter for a property, it's generally a good\n * idea to let devs using your component be able to set that property in HTML\n * via an element attribute. You can code that yourself by writing an\n * `attributeChangedCallback`, or you can use this mixin to get a degree of\n * automatic support.\n *\n * This mixin implements an `attributeChangedCallback` that will attempt to\n * convert a change in an element attribute into a call to the corresponding\n * property setter. Attributes typically follow hyphenated names (\"foo-bar\"),\n * whereas properties typically use camelCase names (\"fooBar\"). This mixin\n * respects that convention, automatically mapping the hyphenated attribute\n * name to the corresponding camelCase property name.\n *\n * Example: You define a component using this mixin:\n *\n * class MyElement extends AttributeMarshallingMixin(HTMLElement) {\n * get fooBar() { return this._fooBar; }\n * set fooBar(value) { this._fooBar = value; }\n * }\n * customElements.define('my-element', MyElement);\n *\n * If someone then instantiates your component in HTML:\n *\n * \n *\n * Then, after the element has been upgraded, the `fooBar` setter will\n * automatically be invoked with the initial value \"Hello\".\n *\n * For the time being, this mixin only supports string-valued properties.\n * If you'd like to convert string attributes to other types (numbers,\n * booleans), you need to implement `attributeChangedCallback` yourself.\n */\n class AttributeMarshalling extends base {\n\n /*\n * Handle a change to the attribute with the given name.\n */\n attributeChangedCallback(attributeName, oldValue, newValue) {\n if (super.attributeChangedCallback) { super.attributeChangedCallback(); }\n const propertyName = attributeToPropertyName(attributeName);\n // If the attribute name corresponds to a property name, set the property.\n // Ignore standard HTMLElement properties handled by the DOM.\n if (propertyName in this && !(propertyName in HTMLElement.prototype)) {\n this[propertyName] = newValue;\n }\n }\n\n connectedCallback() {\n if (super.connectedCallback) { super.connectedCallback(); }\n safeAttributes.connected(this);\n }\n\n static get observedAttributes() {\n return attributesForClass(this);\n }\n\n /**\n * Set/unset the attribute with the indicated name.\n *\n * This method exists primarily to handle the case where an element wants to\n * set a default property value that should be reflected as an attribute. An\n * important limitation of custom element consturctors is that they cannot\n * set attributes. A call to `reflectAttribute` during the constructor will\n * be deferred until the element is connected to the document.\n *\n * @param {string} attribute - The name of the *attribute* (not property) to set.\n * @param {object} value - The value to set. If null, the attribute will be removed.\n */\n reflectAttribute(attribute, value) {\n return safeAttributes.setAttribute(this, attribute, value);\n }\n\n /**\n * Set/unset the class with the indicated name.\n *\n * This method exists primarily to handle the case where an element wants to\n * set a default property value that should be reflected as as class. An\n * important limitation of custom element consturctors is that they cannot\n * set attributes, including the `class` attribute. A call to\n * `reflectClass` during the constructor will be deferred until the element\n * is connected to the document.\n *\n * @param {string} className - The name of the class to set.\n * @param {object} value - True to set the class, false to remove it.\n */\n reflectClass(className, value) {\n return safeAttributes.toggleClass(this, className, value);\n }\n\n }\n\n return AttributeMarshalling;\n};\n\n\n// Convert hyphenated foo-bar attribute name to camel case fooBar property name.\nfunction attributeToPropertyName(attributeName) {\n let propertyName = attributeToPropertyNames[attributeName];\n if (!propertyName) {\n // Convert and memoize.\n const hypenRegEx = /-([a-z])/g;\n propertyName = attributeName.replace(hypenRegEx,\n match => match[1].toUpperCase());\n attributeToPropertyNames[attributeName] = propertyName;\n }\n return propertyName;\n}\n\nfunction attributesForClass(classFn) {\n\n // We treat the element base classes as if they have no attributes, since we\n // don't want to receive attributeChangedCallback for them.\n if (classFn === HTMLElement || classFn === Object) {\n return [];\n }\n\n // Get attributes for parent class.\n const baseClass = Object.getPrototypeOf(classFn.prototype).constructor;\n const baseAttributes = attributesForClass(baseClass);\n\n // Get attributes for this class.\n const propertyNames = Object.getOwnPropertyNames(classFn.prototype);\n const setterNames = propertyNames.filter(propertyName =>\n typeof Object.getOwnPropertyDescriptor(\n classFn.prototype, propertyName).set === 'function');\n const attributes = setterNames.map(setterName =>\n propertyNameToAttribute(setterName));\n\n // Merge.\n const diff = attributes.filter(attribute =>\n baseAttributes.indexOf(attribute) < 0);\n return baseAttributes.concat(diff);\n}\n\n// Convert a camel case fooBar property name to a hyphenated foo-bar attribute.\nfunction propertyNameToAttribute(propertyName) {\n let attribute = propertyNamesToAttributes[propertyName];\n if (!attribute) {\n // Convert and memoize.\n const uppercaseRegEx = /([A-Z])/g;\n attribute = propertyName.replace(uppercaseRegEx, '-$1').toLowerCase();\n }\n return attribute;\n}\n","/* Exported function extends a base class with Composable. */\nexport default (base) => {\n\n /**\n * Mixin to make a class more easily composable with other mixins.\n *\n * This mixin contributes a `compose` method that applies a set of mixin\n * functions and returns the resulting new class. This sugar can make the\n * application of many mixins at once easier to read.\n */\n class Composable extends base {\n\n /**\n * Apply a set of mixin functions or mixin objects to the present class and\n * return the new class.\n *\n * Instead of writing:\n *\n * let MyClass = Mixin1(Mixin2(Mixin3(Mixin4(Mixin5(BaseClass)))));\n *\n * You can write:\n *\n * let MyClass = ComposableMixin(BaseClass).compose(\n * Mixin1,\n * Mixin2,\n * Mixin3,\n * Mixin4,\n * Mixin5\n * );\n *\n * This function can also take mixin objects. A mixin object is just a\n * shorthand for a mixin function that creates a new subclass with the given\n * members. The mixin object's members are *not* copied directly onto the\n * prototype of the base class, as with traditional mixins.\n *\n * In addition to providing syntactic sugar, this mixin can be used to\n * define a class in ES5, which lacks ES6's `class` keyword.\n *\n * @param {...mixins} mixins - A set of mixin functions or objects to apply.\n */\n static compose(...mixins) {\n // We create a new subclass for each mixin in turn. The result becomes\n // the base class extended by any subsequent mixins. It turns out that\n // we can use Array.reduce() to concisely express this, using the current\n // object as the seed for reduce().\n return mixins.reduce(composeClass, this);\n }\n\n }\n\n return Composable;\n};\n\n\n// Properties defined by Object that we don't want to mixin.\nconst NON_MIXABLE_OBJECT_PROPERTIES = [\n 'constructor'\n];\n\n/*\n * Apply the mixin to the given base class to return a new class.\n * The mixin can either be a function that returns the modified class, or a\n * plain object whose members will be copied to the new class' prototype.\n */\nfunction composeClass(base, mixin) {\n if (typeof mixin === 'function') {\n // Mixin function\n return mixin(base);\n } else {\n // Mixin object\n class Subclass extends base {}\n copyOwnProperties(mixin, Subclass.prototype, NON_MIXABLE_OBJECT_PROPERTIES);\n return Subclass;\n }\n}\n\n\n/*\n * Copy the given properties/methods to the target.\n * Return the updated target.\n */\nfunction copyOwnProperties(source, target, ignorePropertyNames = []) {\n Object.getOwnPropertyNames(source).forEach(name => {\n if (ignorePropertyNames.indexOf(name) < 0) {\n const descriptor = Object.getOwnPropertyDescriptor(source, name);\n Object.defineProperty(target, name, descriptor);\n }\n });\n return target;\n}\n","import createSymbol from './createSymbol';\nimport toggleClass from './toggleClass';\nimport symbols from './symbols';\n\n\n// Symbols for private data members on an element.\nconst itemsSymbol = createSymbol('items');\nconst itemInitializedSymbol = createSymbol('itemInitialized');\n\n\n/* Exported function extends a base class with ContentItems. */\nexport default (base) => {\n\n /**\n * Mixin which maps content semantics (elements) to list item semantics.\n *\n * Items differ from element contents in several ways:\n *\n * * They are often referenced via index.\n * * They may have a selection state.\n * * It's common to do work to initialize the appearance or state of a new\n * item.\n * * Auxiliary invisible child elements are filtered out and not counted as\n * items. Auxiliary elements include link, script, style, and template\n * elements. This filtering ensures that those auxiliary elements can be\n * used in markup inside of a list without being treated as list items.\n *\n * This mixin expects a component to provide a `content` property returning a\n * raw set of elements. You can provide that yourself, or use\n * [DistributedChildrenContentMixin](DistributedChildrenContentMixin.md).\n *\n * The most commonly referenced property defined by this mixin is the `items`\n * property. To avoid having to do work each time that property is requested,\n * this mixin supports an optimized mode. If you invoke the `contentChanged`\n * method when the set of items changes, the mixin concludes that you'll take\n * care of notifying it of future changes, and turns on the optimization. With\n * that on, the mixin saves a reference to the computed set of items, and will\n * return that immediately on subsequent calls to the `items` property. If you\n * use this mixin in conjunction with\n * [DistributedChildrenContentMixin](DistributedChildrenContentMixin.md), the\n * `contentChanged` method will be invoked for you when the element's children\n * change, turning on the optimization automatically.\n */\n class ContentItems extends base {\n\n contentChanged() {\n if (super.contentChanged) { super.contentChanged(); }\n\n // Since we got the contentChanged call, we'll assume we'll be notified if\n // the set of items changes later. We turn on memoization of the items\n // property by setting our internal property to null (instead of\n // undefined).\n this[itemsSymbol] = null;\n\n this[symbols.itemsChanged]();\n }\n\n /**\n * This method is invoked whenever a new item is added to the list.\n *\n * The default implementation of this method does nothing. You can override\n * this to perform per-item initialization.\n *\n * @param {HTMLElement} item - The item that was added.\n */\n [symbols.itemAdded](item) {\n if (super[symbols.itemAdded]) { super[symbols.itemAdded](item); }\n }\n\n /**\n * The selection state for a single item has changed.\n *\n * Invoke this method to signal that the selected state of the indicated item\n * has changed. By default, this applies a `selected` CSS class if the item\n * is selected, and removed it if not selected.\n *\n * @param {HTMLElement} item - The item whose selection state has changed.\n * @param {boolean} selected - True if the item is selected, false if not.\n */\n [symbols.itemSelected](item, selected) {\n if (super[symbols.itemSelected]) { super[symbols.itemSelected](item, selected); }\n toggleClass(item, 'selected', selected);\n }\n\n /**\n * The current set of items in the list. See the top-level documentation for\n * mixin for a description of how items differ from plain content.\n *\n * @type {HTMLElement[]}\n */\n get items() {\n let items;\n if (this[itemsSymbol] == null) {\n items = filterAuxiliaryElements(this.content);\n // Note: test for *equality* with null; don't treat undefined as a match.\n if (this[itemsSymbol] === null) {\n // Memoize the set of items.\n this[itemsSymbol] = items;\n }\n } else {\n // Return the memoized items.\n items = this[itemsSymbol];\n }\n return items;\n }\n\n /**\n * This method is invoked when the underlying contents change. It is also\n * invoked on component initialization – since the items have \"changed\" from\n * being nothing.\n */\n [symbols.itemsChanged]() {\n if (super[symbols.itemsChanged]) { super[symbols.itemsChanged](); }\n\n // Perform per-item initialization.\n Array.prototype.forEach.call(this.items, item => {\n if (!item[itemInitializedSymbol]) {\n this[symbols.itemAdded](item);\n item[itemInitializedSymbol] = true;\n }\n });\n\n this.dispatchEvent(new CustomEvent('items-changed'));\n }\n\n /**\n * Fires when the items in the list change.\n *\n * @memberof ContentItems\n * @event items-changed\n */\n }\n\n return ContentItems;\n};\n\n\n// Return the given elements, filtering out auxiliary elements that aren't\n// typically visible. Items which are not elements are returned as is.\nfunction filterAuxiliaryElements(items) {\n const auxiliaryTags = [\n 'link',\n 'script',\n 'style',\n 'template'\n ];\n return [].filter.call(items, function(item) {\n return !item.localName || auxiliaryTags.indexOf(item.localName) < 0;\n });\n}\n","import microtask from './microtask';\n\n\n/* Exported function extends a base class with DistributedChildrenContent. */\nexport default (base) => {\n\n /**\n * Mixin which defines a component's content as its children, expanding any\n * nodes distributed to the component's slots.\n *\n * This also provides notification of changes to a component's content. It\n * will invoke a `contentChanged` method when the component is first\n * instantiated, and whenever its distributed children change. This is an\n * easy way to satisfy the Gold Standard checklist item for monitoring\n * [Content Changes](https://github.com/webcomponents/gold-standard/wiki/Content-Changes).\n *\n * Example:\n *\n * ```\n * let base = DistributedChildrenContentMixin(DistributedChildrenMixin(HTMLElement));\n * class CountingElement extends base {\n *\n * constructor() {\n * super();\n * let root = this.attachShadow({ mode: 'open' });\n * root.innerHTML = ` `;\n * }\n *\n * contentChanged() {\n * // Count the component's children, both initially and when changed.\n * this.count = this.distributedChildren.length;\n * }\n *\n * }\n * ```\n *\n * Note that content change detection depends upon the element having at least\n * one `slot` element in its shadow subtree.\n *\n * This mixin is intended for use with the\n * [DistributedChildrenMixin](DistributedChildrenMixin.md). See that mixin for\n * a discussion of how that works. This DistributedChildrenContentMixin\n * provides an easy way of defining the \"content\" of a component as the\n * component's distributed children. That in turn lets mixins like\n * [ContentItemsMixin](ContentItemsMixin.md) manipulate the children as list\n * items.\n */\n class DistributedChildrenContent extends base {\n\n constructor() {\n super();\n\n if (this.shadowRoot) {\n // Listen to changes on all slots.\n const slots = this.shadowRoot.querySelectorAll('slot');\n slots.forEach(slot => slot.addEventListener('slotchange', event => {\n this.contentChanged();\n }));\n }\n\n // Make an initial call to contentChanged() so that the component can do\n // initialization that it normally does when content changes.\n //\n // This will invoke contentChanged() handlers in other mixins. In order\n // that those mixins have a chance to complete their own initialization,\n // we add the contentChanged() call to the microtask queue.\n microtask(() => this.contentChanged());\n }\n\n /**\n * Invoked when the contents of the component (including distributed\n * children) have changed.\n *\n * This method is also invoked when a component is first instantiated; the\n * contents have essentially \"changed\" from being nothing. This allows the\n * component to perform initial processing of its children.\n */\n contentChanged() {\n if (super.contentChanged) { super.contentChanged(); }\n const event = new CustomEvent('content-changed');\n this.dispatchEvent(event);\n }\n\n /**\n * The content of this component, defined to be the flattened array of\n * children distributed to the component.\n *\n * @type {HTMLElement[]}\n */\n get content() {\n const distributedChildren = this.distributedChildren;\n if (typeof distributedChildren === 'undefined') {\n console.warn(`DistributedChildrenContentMixin expects the component to define a \"distributedChildren\" property.`);\n }\n return distributedChildren;\n }\n set content(value) {\n if ('content' in base.prototype) { super.content = value; }\n // TODO: Set the children to the given value (which should be an array of\n // elements)?\n }\n\n /**\n * This event is raised when the component's contents (including distributed\n * children) have changed.\n *\n * @memberof DistributedChildrenContent\n * @event content-changed\n */\n }\n\n return DistributedChildrenContent;\n};\n","/* Exported function extends a base class with DistributedChildren. */\nexport default (base) => {\n\n /**\n * Mixin which defines helpers for accessing a component's distributed\n * children as a flattened array or string.\n *\n * The standard DOM API provides several ways of accessing child content:\n * `children`, `childNodes`, and `textContent`. None of these functions are\n * Shadow DOM aware. This mixin defines variations of those functions that\n * *are* Shadow DOM aware.\n *\n * Example: you create a component `` that displays a number\n * equal to the number of children placed inside that component. If someone\n * instantiates your component like:\n *\n * \n *
\n *
\n *
\n * \n *\n * Then the component should show \"3\", because there are three children. To\n * calculate the number of children, the component can just calculate\n * `this.children.length`. However, suppose someone instantiates your\n * component inside one of their own components, and puts a `` element\n * inside your component:\n *\n * \n * \n * \n *\n * If your component only looks at `this.children`, it will always see exactly\n * one child — the `` element. But the user looking at the page will\n * *see* any nodes distributed to that slot. To match what the user sees, your\n * component should expand any `` elements it contains.\n *\n * That is the problem this mixin solves. After applying this mixin, your\n * component code has access to `this.distributedChildren`, whose `length`\n * will return the total number of all children distributed to your component\n * in the composed tree.\n *\n * Note: The latest Custom Elements API design calls for a new function,\n * `getAssignedNodes` that takes an optional `deep` parameter, that will solve\n * this problem at the API level.\n */\n class DistributedChildren extends base {\n\n /**\n * An in-order collection of distributed children, expanding any slot\n * elements. Like the standard children property, this skips text nodes.\n *\n * @type {HTMLElement[]}\n */\n get distributedChildren() {\n return expandContentElements(this.children, false);\n }\n\n /**\n * An in-order collection of distributed child nodes, expanding any slot\n * elements. Like the standard childNodes property, this includes text\n * nodes.\n *\n * @type {Node[]}\n */\n get distributedChildNodes() {\n return expandContentElements(this.childNodes, true);\n }\n\n /**\n * The concatenated text content of all distributed child nodes, expanding\n * any slot elements.\n *\n * @type {string}\n */\n get distributedTextContent() {\n const strings = this.distributedChildNodes.map(function(child) {\n return child.textContent;\n });\n return strings.join('');\n }\n\n }\n\n return DistributedChildren;\n};\n\n\n/*\n * Given a array of nodes, return a new array with any content elements expanded\n * to the nodes distributed to that content element. This rule is applied\n * recursively.\n *\n * If includeTextNodes is true, text nodes will be included, as in the\n * standard childNodes property; by default, this skips text nodes, like the\n * standard children property.\n */\nfunction expandContentElements(nodes, includeTextNodes) {\n const expanded = Array.prototype.map.call(nodes, node => {\n // We want to see if the node is an instanceof HTMLSlotELement, but\n // that class won't exist if the browser that doesn't support native\n // Shadow DOM and if the Shadow DOM polyfill hasn't been loaded. Instead,\n // we do a simplistic check to see if the tag name is \"slot\".\n const isSlot = typeof HTMLSlotElement !== 'undefined' ?\n node instanceof HTMLSlotElement :\n node.localName === 'slot';\n if (isSlot) {\n // Use the nodes assigned to this node instead.\n const assignedNodes = node.assignedNodes({ flatten: true });\n return assignedNodes ?\n expandContentElements(assignedNodes, includeTextNodes) :\n [];\n } else if (node instanceof HTMLElement) {\n // Plain element; use as is.\n return [node];\n } else if (node instanceof Text && includeTextNodes) {\n // Text node.\n return [node];\n } else {\n // Comment, processing instruction, etc.; skip.\n return [];\n }\n });\n const flattened = [].concat(...expanded);\n return flattened;\n}\n","import createSymbol from './createSymbol';\n\n\n// Symbols for private data members on an element.\nconst selectedFractionSymbol = createSymbol('selectedFraction');\n\n\n/* Exported function extends a base class with FractionalSelection. */\nexport default function mixin(base) {\n\n /**\n * Adds support for fractional selection: treating a selection as a real\n * number that combines an integer portion (an index into a list), and a\n * fraction (indicating how far of the way we are to the next or previous\n * item).\n *\n * This is useful in components that support incremental operations during\n * dragging and swiping. Example: a carousel component has several items, and the\n * currently selected item is item 3. The user begins swiping to the left,\n * moving towards selecting item 4. Halfway through this operation, the\n * fractional selection value is 3.5.\n *\n * This value permits communication between mixins like\n * [SwipeDirectionMixin](./SwipeDirectionMixin.md) and\n * [TrackpadDirectionMixin](./TrackpadDirectionMixin.md), which generate\n * fractional selection values, and mixins like\n * [SelectionAnimationMixin](./SelectionAnimationMixin.md), which can render\n * selection at a fractional value.\n */\n class FractionalSelection extends base {\n\n connectedCallback() {\n if (super.connectedCallback) { super.connectedCallback(); }\n this.selectedFraction = 0;\n }\n\n /**\n * A fractional value indicating how far the user has currently advanced to\n * the next/previous item. E.g., a `selectedFraction` of 3.5 indicates the\n * user is halfway between items 3 and 4.\n *\n * @type {number}\n */\n get selectedFraction() {\n return this[selectedFractionSymbol];\n }\n set selectedFraction(value) {\n this[selectedFractionSymbol] = value;\n if ('selectedFraction' in base.prototype) { super.selectedFraction = value; }\n const event = new CustomEvent('selected-fraction-changed');\n this.dispatchEvent(event);\n }\n\n }\n\n return FractionalSelection;\n}\n\n\nmixin.helpers = {\n\n /*\n * Dampen a selection that goes past the beginning or end of a list. This is\n * generally used to produce a visual effect of tension as the user tries to\n * go further in a direction that has no more items.\n *\n * Example: suppose `itemCount` is 5, indicating a list of 5 items. The index of\n * the last item is 4. If the `selection` parameter is 4.5, the user is trying\n * to go past this last item. When a damping function is applied, the resulting\n * value will be less than 4.5 (the actual value will be 4.25). When this\n * selection state is rendered, the user will see that, each unit distance the\n * drag travels has less and less visible effect. This is perceived as tension.\n *\n * @param {number} selection - A real number indicating a selection position\n * @param {number} itemCount - An integer for the number of items in the list\n * @returns {number} A real number representing the damped selection value.\n */\n dampedSelection(selection, itemCount) {\n const bound = itemCount - 1;\n let damped;\n if (selection < 0) {\n // Trying to go past beginning of list. Apply tension from the left edge.\n damped = -mixin.helpers.damping(-selection);\n } else if (selection >= bound) {\n // Trying to go past end of list. Apply tension from the right edge.\n damped = bound + mixin.helpers.damping(selection - bound);\n } else {\n // No damping required.\n damped = selection;\n }\n return damped;\n },\n\n /*\n * Calculate damping as a function of the distance past the minimum/maximum\n * values.\n *\n * We want to asymptotically approach an absolute minimum of 1 unit\n * below/above the actual minimum/maximum. This requires calculating a\n * hyperbolic function.\n *\n * See http://www.wolframalpha.com/input/?i=y+%3D+-1%2F%28x%2B1%29+%2B+1\n * for the one we use. The only portion of that function we care about is when\n * x is zero or greater. An important consideration is that the curve be\n * tangent to the diagonal line x=y at (0, 0). This ensures smooth continuity\n * with the normal drag behavior, in which the visible sliding is linear with\n * the distance the touchpoint has been dragged.\n */\n damping(x) {\n const y = (-1 / (x + 1)) + 1;\n return y;\n },\n\n /*\n * Return the current fractional selection value for the given element.\n *\n * This simply adds the element's `selectedIndex` and `selectedFraction`\n * properties.\n *\n * @param {HTMLElement} element - An element that supports selection\n */\n elementSelection(element) {\n const selectedIndex = element.selectedIndex;\n if (selectedIndex < 0) {\n // No selection\n return;\n }\n const selectedFraction = element.selectedFraction || 0;\n return selectedIndex + selectedFraction;\n },\n\n /*\n * Breaks a fractional selection into its integer and fractional parts.\n *\n * Example: if passed 3.5, this returns { index: 3, fraction: 5 }.\n *\n * @param {number} selection – A real number representing a selection point\n * @returns {object} - An object with an `index` property holding the\n * selection's integer component, and a `fraction` property holding the\n * selection's fractional component.\n */\n selectionParts(selection) {\n // Stupid IE doesn't have Math.trunc.\n // const index = Math.trunc(selection);\n const index = selection < 0 ? Math.ceil(selection) : Math.floor(selection);\n const fraction = selection - index;\n return { index, fraction };\n },\n\n /*\n * Returns a fractional selection point after accounting for wrapping, ensuring\n * that the integer portion of the selection stays between 0 and `itemCount`-1.\n * That is, the integer portion will always be a valid index into the list.\n *\n * Example of wrapping past the end of the list: if `selection` is 5.5 and\n * `itemCount` is 5, this returns 0.5. Example of wrapping past the beginning of\n * the list: if `selection` is 0.5 and `itemCount` is 5, this returns 4.5.\n *\n * @param {number} selection - A real number representing a selection point\n * @param {number} itemCount - The number of items in the list\n * @returns {number} - The result of wrapping the selection point\n */\n wrappedSelection(selection, itemCount) {\n // Handles possibility of negative mod.\n // See http://stackoverflow.com/a/18618250/76472\n return ((selection % itemCount) + itemCount) % itemCount;\n },\n\n /*\n * Return the parts of a selection, first wrapping if necessary.\n *\n * @param {number} selection – A real number representing a selection point\n * @param {number} itemCount - The number of items in the list\n * @param {boolean} wrap – True if the selection should wrap to stay within the\n * list\n * @returns {object} – The parts of the selection, using the same format as\n * `selectionParts`.\n */\n wrappedSelectionParts(selection, itemCount, wrap) {\n if (wrap) {\n selection = mixin.helpers.wrappedSelection(selection, itemCount);\n }\n return mixin.helpers.selectionParts(selection);\n }\n\n};\n","import createSymbol from './createSymbol';\nimport FractionalSelectionMixin from './FractionalSelectionMixin';\nimport symbols from './symbols';\n\n\n// Symbols for private data members on an element.\nconst animationSymbol = createSymbol('animation');\nconst draggingSymbol = createSymbol('dragging');\nconst lastAnimationSymbol = createSymbol('lastAnimation');\nconst playingAnimationSymbol = createSymbol('animatingSelection');\nconst previousSelectionSymbol = createSymbol('previousSelection');\nconst selectionAnimationDurationSymbol = createSymbol('selectionAnimationDuration');\nconst selectionAnimationEffectSymbol = createSymbol('selectionAnimationEffect');\nconst selectionAnimationKeyframesSymbol = createSymbol('selectionAnimationKeyframes');\nconst resetAnimationsOnNextRenderSymbol = createSymbol('resetAnimationsOnNextRender');\n\n\n/* Exported function extends a base class with SelectionAnimation. */\nexport default function mixin(base) {\n\n /**\n * Mixin which uses animation to show transitions between selection states.\n *\n * This mixin can be used by components that want to provide visible\n * animations when changing the selection. For example, a carousel component\n * may want to define a sliding animation effect shown when moving between\n * items.\n *\n * The animation is defined by a `selectionAnimationKeyframes` property; see\n * that property for details on how to define these keyframes. This animation\n * will be used in two ways. First, when moving strictly between items, the\n * animation will play smoothly to show the selection changing. Second, the\n * animation can be used to render the selection at a fixed point in the\n * transition between states. E.g., if the user pauses halfway through\n * dragging an element using [SwipeDirectionMixin](SwipeDirectionMixin.md)\n * or [TrackpadDirectionMixin](TrackpadDirectionMixin.md)s, then the selection\n * animation will be shown at the point exactly halfway through.\n *\n * This mixin expects a component to provide an `items` array of all elements\n * in the list, which can be provided via\n * [ContentItemsMixin](ContentItemsMixin.md). This mixin also expects\n * `selectedIndex` and `selectedItem` properties, which can be provided via\n * [SingleSelectionMixin](SingleSelectionMixin.md).\n *\n * This mixin supports a `selectionWraps` property. When true, the user can\n * navigate forward from the last item in the list and wrap around to the\n * first item, or navigate backward from the first item and wrap around to the\n * last item.\n *\n * This mixin uses the Web Animations API. For use on browsers which\n * do not support that API natively, you will need to load the\n * [Web Animations polyfill](https://github.com/web-animations/web-animations-js).\n */\n class SelectionAnimation extends base {\n\n constructor() {\n super();\n\n // Set defaults.\n if (typeof this.selectionAnimationDuration === 'undefined') {\n this.selectionAnimationDuration = this[symbols.defaults].selectionAnimationDuration;\n }\n if (typeof this.selectionAnimationEffect === 'undefined' && this.selectionAnimationKeyframes == null) {\n this.selectionAnimationEffect = this[symbols.defaults].selectionAnimationEffect;\n }\n\n this[symbols.dragging] = false;\n }\n\n get [symbols.defaults]() {\n const defaults = super[symbols.defaults] || {};\n defaults.selectionAnimationDuration = 250;\n defaults.selectionAnimationEffect = 'slide';\n return defaults;\n }\n\n /*\n * Provide backing for the dragging property.\n * Also, when a drag begins, reset the animations.\n */\n get [symbols.dragging]() {\n return this[draggingSymbol];\n }\n set [symbols.dragging](value) {\n const previousValue = this[symbols.dragging];\n this[draggingSymbol] = value;\n if (symbols.dragging in base.prototype) { super[symbols.dragging] = value; }\n if (value && !previousValue) {\n // Have begun a drag.\n this[resetAnimationsOnNextRenderSymbol] = true;\n }\n }\n\n [symbols.itemAdded](item) {\n // We mark new items in the list as explicitly visible to ARIA. Otherwise,\n // when an item isn't visible on the screen, ARIA will assume the item is\n // of no interest to the user, and leave it out of the accessibility tree.\n // If the list contains 10 items, but only 3 are visible, a screen reader\n // might then announce the list only has 3 items. To ensure that screen\n // readers and other assistive technologies announce the correct total\n // number of items, we explicitly mark all items as not hidden. This will\n // expose them all in the accessibility tree, even the items which are\n // currently not rendered.\n //\n // TODO: Generally speaking, this entire mixin assumes that the user can\n // navigate through all items in a list. But an app could style an item as\n // display:none or visibility:hidden because the user is not allowed to\n // interact with that item at the moment. Support for this scenario should\n // be added. This would entail changing all locations where a mixin\n // function is counting items, iterating over the (visible) items, and\n // showing or hiding items. Among other things, the code below to make\n // items visible to ARIA would need to discriminate between items which\n // are invisible because of animation state, or invisible because the user\n // shouldn't interact with them.\n item.setAttribute('aria-hidden', false);\n }\n\n [symbols.itemsChanged]() {\n if (super[symbols.itemsChanged]) { super[symbols.itemsChanged](); }\n\n resetAnimations(this);\n\n // TODO: Also reset our notion of the last rendered selection? This comes\n // up when a DOM removal causes the selected item to change position.\n // this[previousSelectionSymbol] = null;\n\n renderSelection(this);\n }\n\n resetAnimations() {\n resetAnimations(this);\n }\n\n /**\n * A fractional value indicating how far the user has currently advanced to\n * the next/previous item. E.g., a `selectedFraction` of 3.5 indicates the\n * user is halfway between items 3 and 4.\n *\n * For more details, see [FractionalSelectionMixin](FractionalSelectionMixin.md)\n * mixin.\n *\n * @type {number}\n */\n get selectedFraction() {\n return super.selectedFraction || 0;\n }\n set selectedFraction(value) {\n if ('selectedFraction' in base.prototype) { super.selectedFraction = value; }\n renderSelection(this, this.selectedIndex, value);\n }\n\n get selectedIndex() {\n return super.selectedIndex;\n }\n set selectedIndex(index) {\n if ('selectedIndex' in base.prototype) { super.selectedIndex = index; }\n renderSelection(this, index, 0);\n }\n\n /**\n * The duration of a selection animation in milliseconds.\n *\n * This measures the amount of time required for a selection animation to\n * complete. This number remains constant, even if the number of items being\n * animated increases.\n *\n * The default value is 250 milliseconds (a quarter a second).\n *\n * @type {number}\n * @default 250\n */\n get selectionAnimationDuration() {\n return this[selectionAnimationDurationSymbol];\n }\n set selectionAnimationDuration(value) {\n this[selectionAnimationDurationSymbol] = value;\n if ('selectionAnimationDuration' in base.prototype) { super.selectionAnimationDuration = value; }\n }\n\n /**\n * The name of a standard selection animation effect.\n *\n * This is a shorthand for setting the `selectionAnimationKeyframes`\n * property to standard keyframes. Supported string values:\n *\n * * \"crossfade\"\n * * \"reveal\"\n * * \"revealWithFade\"\n * * \"showAdjacent\"\n * * \"slide\"\n * * \"slideWithGap\"\n *\n * @type {string}\n * @default \"slide\"\n */\n get selectionAnimationEffect() {\n return this[selectionAnimationEffectSymbol];\n }\n set selectionAnimationEffect(value) {\n this[selectionAnimationEffectSymbol] = value;\n if ('selectionAnimationEffect' in base.prototype) { super.selectionAnimationEffect = value; }\n this.selectionAnimationKeyframes = mixin.standardEffectKeyframes[value];\n }\n\n /**\n * The keyframes that define an animation that plays for an item when moving\n * forward in the sequence.\n *\n * This is an array of CSS rules that will be applied. These are used as\n * [keyframes](http://w3c.github.io/web-animations/#keyframes-section)\n * to animate the item with the\n * [Web Animations API](https://developer.mozilla.org/en-US/docs/Web/API/animation).\n *\n * The animation represents the state of the next item as it moves from\n * completely unselected (offstage, usually right), to selected (center\n * stage), to completely unselected (offstage, usually left). The center time\n * of the animation should correspond to the item's quiscent selected state,\n * typically in the center of the stage and at the item's largest size.\n *\n * The default forward animation is a smooth slide at full size from right to\n * left.\n *\n * When moving the selection backward, this animation is played in reverse.\n *\n * @type {cssRules[]}\n */\n get selectionAnimationKeyframes() {\n // Standard animation slides left/right, keeps adjacent items out of view.\n return this[selectionAnimationKeyframesSymbol];\n }\n set selectionAnimationKeyframes(value) {\n this[selectionAnimationKeyframesSymbol] = value;\n if ('selectionAnimationKeyframes' in base.prototype) { super.selectionAnimationKeyframes = value; }\n resetAnimations(this);\n renderSelection(this);\n }\n\n get selectionWraps() {\n return super.selectionWraps;\n }\n set selectionWraps(value) {\n if ('selectionWraps' in base.prototype) { super.selectionWraps = value; }\n resetAnimations(this);\n renderSelection(this);\n }\n }\n\n return SelectionAnimation;\n}\n\n\n// We expose helpers on the mixin function that we want to be able to unit test.\n// Since these are on the function, not on the class emitted by the function,\n// they don't end up getting exposed on actual element instances.\nmixin.helpers = {\n\n /*\n * Calculate the animation fractions for an element's items at the given\n * selection point. This is used when rendering the element's selection state\n * instantaneously.\n *\n * This function considers the selectedIndex parameter, which can be a whole\n * or fractional number, and determines which items will be visible at that\n * index. This function then calculates a corresponding animation fraction: a\n * number between 0 and 1 indicating how far through the selection animation\n * an item should be shown, or null if the item should not be visible at that\n * selection index. These fractions are returned as an array, where the\n * animation fraction at position N corresponds to how item N should be shown.\n */\n animationFractionsForSelection(element, selection) {\n\n const items = element.items;\n if (!items) {\n return;\n }\n\n const itemCount = items.length;\n const selectionWraps = element.selectionWraps;\n\n return items.map((item, itemIndex) => {\n // How many steps from the selection point to this item?\n const steps = stepsToIndex(itemCount, selectionWraps, selection, itemIndex);\n // To convert steps to animation fraction:\n // steps animation fraction\n // 1 0 (stage right)\n // 0 0.5 (center stage)\n // -1 1 (stage left)\n const animationFraction = (1 - steps) / 2;\n return (animationFraction >= 0 && animationFraction <= 1) ?\n animationFraction :\n null; // Outside animation range\n });\n },\n\n /*\n * Calculate the animation timings that should be used to smoothly animate the\n * element's items from one selection state to another.\n *\n * This returns an array of timings, where the timing at position N should be\n * used to animate item N. If an item's timing is null, then that item should\n * not take place in the animation, and should be hidden instead.\n */\n effectTimingsForSelectionAnimation(element, fromSelection, toSelection) {\n\n const items = element.items;\n if (!items) {\n return;\n }\n const itemCount = items.length;\n const selectionWraps = element.selectionWraps;\n const toIndex = FractionalSelectionMixin.helpers.wrappedSelectionParts(toSelection, itemCount, selectionWraps).index;\n const totalSteps = stepsToIndex(itemCount, selectionWraps, fromSelection, toSelection);\n const direction = totalSteps >= 0 ? 'normal': 'reverse';\n const fill = 'both';\n const totalDuration = element.selectionAnimationDuration;\n const stepDuration = totalSteps !== 0 ?\n totalDuration * 2 / Math.ceil(Math.abs(totalSteps)) :\n 0; // No steps required, animation will be instantenous.\n\n const timings = items.map((item, itemIndex) => {\n const steps = stepsToIndex(itemCount, selectionWraps, itemIndex, toSelection);\n // If we include this item in the staggered sequence of animations we're\n // creating, where would the item appear in the sequence?\n let positionInSequence = totalSteps - steps;\n if (totalSteps < 0) {\n positionInSequence = -positionInSequence;\n }\n // So, is this item really included in the sequence?\n if (Math.ceil(positionInSequence) >= 0 && positionInSequence <= Math.abs(totalSteps)) {\n // Note that delay for first item will be negative. That will cause\n // the animation to start halfway through, which is what we want.\n const delay = stepDuration * (positionInSequence - 1)/2;\n const endDelay = itemIndex === toIndex ?\n -stepDuration/2 : // Stop halfway through.\n 0; // Play animation until end.\n return { duration: stepDuration, direction, fill, delay, endDelay };\n } else {\n return null;\n }\n });\n\n return timings;\n }\n\n};\n\n\n// Keyframes for standard selection animation effects.\nmixin.standardEffectKeyframes = {\n\n // Simple crossfade\n crossfade: [\n { opacity: 0 },\n { opacity: 1 },\n { opacity: 0 }\n ],\n\n // Reveal, as if sliding the top card off a deck of cards\n reveal: [\n { transform: 'translateX(0%)', zIndex: 0 },\n { transform: 'translateX(0%)', zIndex: 1 },\n { transform: 'translateX(-100%)', zIndex: 2 }\n ],\n\n // Google Photos-style reveal-with-fade animation\n revealWithFade: [\n { transform: 'translateX(0%) scale(0.75)', opacity: 0, zIndex: 0 },\n { transform: 'translateX(0%) scale(1.0)', opacity: 1, zIndex: 1 },\n { transform: 'translateX(-100%) scale(1.0)', opacity: 1, zIndex: 2 }\n ],\n\n // Carousel variant with a bit of off-stage elements showing\n showAdjacent: [\n { transform: 'translateX(78%) scale(0.7)', zIndex: 0 },\n { transform: 'translateX(0%) scale(0.82)', zIndex: 1 },\n { transform: 'translateX(-78%) scale(0.7)', zIndex: 0 }\n ],\n\n // Simple slide\n slide: [\n { transform: 'translateX(100%)' },\n { transform: 'translateX(-100%)' }\n ],\n\n // Slide, with a gap between\n slideWithGap: [\n { transform: 'translateX(110%)' },\n { transform: 'translateX(-110%)' }\n ]\n\n};\n\n\n/*\n * Smoothly animate the selection between the indicated \"from\" and \"to\"\n * indices. The former can be a fraction, e.g., when the user releases a finger\n * to complete a touch drag, and the selection will snap to the closest whole\n * index.\n */\nfunction animateSelection(element, fromSelection, toSelection) {\n\n resetAnimations(element);\n\n // Calculate the animation timings.\n const items = element.items;\n const keyframes = element.selectionAnimationKeyframes;\n element[playingAnimationSymbol] = true;\n const timings = mixin.helpers.effectTimingsForSelectionAnimation(element, fromSelection, toSelection);\n\n // Figure out which item will be the one *after* the one we're selecting.\n const itemCount = items.length;\n const selectionWraps = element.selectionWraps;\n const selectionIndex = FractionalSelectionMixin.helpers.selectionParts(toSelection, itemCount, selectionWraps).index;\n const totalSteps = stepsToIndex(itemCount, selectionWraps, fromSelection, toSelection);\n const forward = totalSteps >= 0;\n let nextUpIndex = selectionIndex + (forward ? 1 : - 1);\n if (selectionWraps) {\n nextUpIndex = FractionalSelectionMixin.helpers.wrappedSelection(nextUpIndex, itemCount);\n } else if (!isItemIndexInBounds(element, nextUpIndex)) {\n nextUpIndex = null; // At start/end of list; don't have a next item to show.\n }\n\n // Play the animations using those timings.\n let lastAnimationDetails;\n timings.forEach((timing, index) => {\n const item = items[index];\n if (timing) {\n showItem(item, true);\n const animation = item.animate(keyframes, timing);\n element[animationSymbol][index] = animation;\n if (index === nextUpIndex) {\n // This item will be animated, so will already be in the desired state\n // after the animation completes.\n nextUpIndex = null;\n }\n if (timing.endDelay !== 0) {\n // This is the animation for the item that will be left selected.\n // We want to clean up when this animation completes.\n lastAnimationDetails = { animation, index, timing, forward };\n }\n } else {\n // This item doesn't participate in the animation.\n showItem(item, false);\n }\n });\n\n if (lastAnimationDetails != null) {\n // Arrange for clean-up work to be performed.\n lastAnimationDetails.nextUpIndex = nextUpIndex;\n lastAnimationDetails.animation.onfinish = event => selectionAnimationFinished(element, lastAnimationDetails);\n element[lastAnimationSymbol] = lastAnimationDetails.animation;\n } else {\n // Shouldn't happen -- we should always have at least one animation.\n element[playingAnimationSymbol] = false;\n }\n}\n\n\nfunction getAnimationForItemIndex(element, index) {\n if (element[animationSymbol] == null) {\n // Not ready yet;\n return null;\n }\n let animation = element[animationSymbol][index];\n if (!animation) {\n const item = element.items[index];\n animation = item.animate(element.selectionAnimationKeyframes, {\n duration: element.selectionAnimationDuration,\n fill: 'both'\n });\n animation.pause();\n element[animationSymbol][index] = animation;\n }\n return animation;\n}\n\nfunction isItemIndexInBounds(element, index) {\n return index >= 0 && element.items && index < element.items.length;\n}\n\n/*\n * Render the selection state of the element.\n *\n * This can be used to re-render a previous selection state (if the\n * selectedIndex param is omitted), render the selection instantly at a given\n * whole or fractional selection index, or animate to a given selection index.\n *\n * There are several distinct scenarios we need to cover:\n *\n * 1. Initial positioning, or repositioning after changing a property like\n * selectionAnimationKeyframes that affects rendering.\n * 2. Animate on selectedIndex change. This should override any animation/swipe\n * already in progress.\n * 3. Instantly render the current position of a drag operation in progress.\n * 4. Complete a drag operation. If the drag wasn't far enough to affect\n * selection, we'll just be restoring the selectedFraction to 0.\n *\n * If the list does not wrap, any selection position outside the list's bounds\n * will be damped to produce a visual effect of tension.\n */\nfunction renderSelection(element, selectedIndex=element.selectedIndex, selectedFraction=element.selectedFraction) {\n const itemCount = element.items ? element.items.length : 0;\n if (itemCount === 0) {\n // Nothing to render.\n return;\n }\n if (selectedIndex < 0) {\n // TODO: Handle no selection.\n return;\n }\n let selection = selectedIndex + selectedFraction;\n if (element.selectionWraps) {\n // Apply wrapping to ensure consistent representation of selection.\n selection = FractionalSelectionMixin.helpers.wrappedSelection(selection, itemCount);\n } else {\n // Apply damping if necessary.\n selection = FractionalSelectionMixin.helpers.dampedSelection(selection, itemCount);\n }\n const previousSelection = element[previousSelectionSymbol];\n // TODO: If an item changes position in the DOM, we end up animating from\n // its old index to its new index, but we really don't want to animate at all.\n if (!element[symbols.dragging] && previousSelection != null &&\n previousSelection !== selection) {\n // Animate selection from previous state to new state.\n animateSelection(element, previousSelection, selection);\n } else if (selectedFraction === 0 && element[playingAnimationSymbol]) {\n // Already in process of animating to fraction 0. During that process,\n // ignore subsequent attempts to renderSelection to fraction 0.\n return;\n } else {\n // Render current selection state instantly.\n renderSelectionInstantly(element, selection);\n }\n element[previousSelectionSymbol] = selection;\n}\n\n/*\n * Instantly render (don't animate) the element's items at the given whole or\n * fractional selection index.\n */\nfunction renderSelectionInstantly(element, toSelection) {\n if (element[resetAnimationsOnNextRenderSymbol]) {\n resetAnimations(element);\n element[resetAnimationsOnNextRenderSymbol] = false;\n }\n const animationFractions = mixin.helpers.animationFractionsForSelection(element, toSelection);\n animationFractions.map((animationFraction, index) => {\n const item = element.items[index];\n if (animationFraction != null) {\n showItem(item, true);\n setAnimationFraction(element, index, animationFraction);\n } else {\n showItem(item, false);\n }\n });\n}\n\n/*\n * We maintain an array containing an animation per item. This is used for two\n * reasons:\n *\n * * During a drag operation, we want to be able to reuse animations between\n * drag updates.\n * * When a selection animation completes, we need to be able to leave the\n * visibile items in a paused state. Later, we'll want to be able to clean up\n * those animations.\n *\n * Note that this array is sparse: it will only hold up from 0–3 animations at\n * any given point.\n */\nfunction resetAnimations(element) {\n const animations = element[animationSymbol];\n if (animations) {\n // Cancel existing animations to remove the effects they're applying.\n animations.forEach((animation, index) => {\n if (animation) {\n animation.cancel();\n animations[index] = null;\n }\n });\n }\n const itemCount = element.items ? element.items.length : 0;\n if (!animations || animations.length !== itemCount) {\n // Haven't animated before with this number of items; (re)create array.\n element[animationSymbol] = new Array(itemCount);\n }\n}\n\n/*\n * The last animation in our selection animation has completed. Clean up.\n */\nfunction selectionAnimationFinished(element, details) {\n\n // When the last animation completes, show the next item in the direction\n // we're going. Waiting to that until this point is a bit of a hack to avoid\n // having a next item that's higher in the natural z-order obscure other items\n // during animation.\n const nextUpIndex = details.nextUpIndex;\n if (nextUpIndex != null) {\n if (element[animationSymbol][nextUpIndex]) {\n // Cancel existing selection animation so we can construct a new one.\n element[animationSymbol][nextUpIndex].cancel();\n element[animationSymbol][nextUpIndex] = null;\n }\n const animationFraction = details.forward ? 0 : 1;\n setAnimationFraction(element, nextUpIndex, animationFraction);\n showItem(element.items[nextUpIndex], true);\n }\n\n element[lastAnimationSymbol].onfinish = null;\n element[playingAnimationSymbol] = false;\n}\n\n/*\n * Pause the indicated animation and have it show the animation at the given\n * fraction (between 0 and 1) of the way through the animation.\n */\nfunction setAnimationFraction(element, itemIndex, fraction) {\n const animation = getAnimationForItemIndex(element, itemIndex);\n if (animation) {\n const duration = element.selectionAnimationDuration;\n if (duration) {\n animation.currentTime = fraction * duration;\n }\n }\n}\n\nfunction showItem(item, flag) {\n item.style.visibility = flag ? 'visible' : 'hidden';\n}\n\n/*\n * Figure out how many steps it will take to go from fromSelection to\n * toSelection. To go from item 3 to item 4 is one step.\n *\n * If wrapping is allowed, then going from the last item to the first will take\n * one step (forward), and going from the first item to the last will take one\n * step (backward).\n */\nfunction stepsToIndex(length, allowWrap, fromSelection, toSelection) {\n let steps = toSelection - fromSelection;\n // Wrapping only kicks in when list has more than 1 item.\n if (allowWrap && length > 1) {\n const wrapSteps = length - Math.abs(steps);\n if (wrapSteps <= 1) {\n // Special case\n steps = steps < 0 ?\n wrapSteps : // Wrap forward from last item to first.\n -wrapSteps; // Wrap backward from first item to last.\n }\n }\n return steps;\n}\n","import symbols from './symbols';\n\n\n// Used to assign unique IDs to item elements without IDs.\nlet idCount = 0;\n\n\n/* Exported function extends a base class with SelectionAriaActive. */\nexport default (base) => {\n\n /**\n * Mixin which treats the selected item in a list as the active item in ARIA\n * accessibility terms.\n *\n * Handling ARIA selection state properly is actually quite complex:\n *\n * * The items in the list need to be indicated as possible items via an ARIA\n * `role` attribute value such as \"option\".\n * * The selected item need to be marked as selected by setting the item's\n * `aria-selected` attribute to true *and* the other items need be marked as\n * *not* selected by setting `aria-selected` to false.\n * * The outermost element with the keyboard focus needs to have attributes\n * set on it so that the selection is knowable at the list level via the\n * `aria-activedescendant` attribute.\n * * Use of `aria-activedescendant` in turn requires that all items in the\n * list have ID attributes assigned to them.\n *\n * This mixin tries to address all of the above requirements. To that end,\n * this mixin will assign generated IDs to any item that doesn't already have\n * an ID.\n *\n * ARIA relies on elements to provide `role` attributes. This mixin will apply\n * a default role of \"listbox\" on the outer list if it doesn't already have an\n * explicit role. Similarly, this mixin will apply a default role of \"option\"\n * to any list item that does not already have a role specified.\n *\n * This mixin expects a set of members that manage the state of the selection:\n * `[symbols.itemSelected]`, `itemAdded`, and `selectedIndex`. You can\n * supply these yourself, or do so via\n * [SingleSelectionMixin](SingleSelectionMixin.md).\n */\n class SelectionAriaActive extends base {\n\n connectedCallback() {\n if (super.connectedCallback) { super.connectedCallback(); }\n // Set default ARIA role.\n if (this.getAttribute('role') == null && this[symbols.defaults].role) {\n this.setAttribute('role', this[symbols.defaults].role);\n }\n }\n\n get [symbols.defaults]() {\n const defaults = super[symbols.defaults] || {};\n defaults.role = 'listbox';\n return defaults;\n }\n\n [symbols.itemAdded](item) {\n if (super[symbols.itemAdded]) { super[symbols.itemAdded](item); }\n\n if (!item.getAttribute('role')) {\n // Assign a default ARIA role.\n item.setAttribute('role', 'option');\n }\n\n // Ensure each item has an ID so we can set aria-activedescendant on the\n // overall list whenever the selection changes.\n //\n // The ID will take the form of a base ID plus a unique integer. The base\n // ID will be incorporate the component's own ID. E.g., if a component has\n // ID \"foo\", then its items will have IDs that look like \"_fooOption1\". If\n // the compnent has no ID itself, its items will get IDs that look like\n // \"_option1\". Item IDs are prefixed with an underscore to differentiate\n // them from manually-assigned IDs, and to minimize the potential for ID\n // conflicts.\n if (!item.id) {\n const baseId = this.id ?\n \"_\" + this.id + \"Option\" :\n \"_option\";\n item.id = baseId + idCount++;\n }\n }\n\n [symbols.itemSelected](item, selected) {\n if (super[symbols.itemSelected]) { super[symbols.itemSelected](item, selected); }\n item.setAttribute('aria-selected', selected);\n const itemId = item.id;\n if (itemId && selected) {\n this.setAttribute('aria-activedescendant', itemId);\n }\n }\n\n get selectedItem() {\n return super.selectedItem;\n }\n set selectedItem(item) {\n if ('selectedItem' in base.prototype) { super.selectedItem = item; }\n if (item == null) {\n // Selection was removed.\n this.removeAttribute('aria-activedescendant');\n }\n }\n\n }\n\n return SelectionAriaActive;\n};\n","/* Exported function extends a base class with ShadowElementReferences. */\nexport default (base) => {\n\n /**\n * Mixin to create references to elements in a component's Shadow DOM subtree.\n *\n * This adds a member on the component called `this.$` that can be used to\n * reference shadow elements with IDs. E.g., if component's shadow contains an\n * element ``, then this mixin will create a member\n * `this.$.foo` that points to that button.\n *\n * Such references simplify a component's access to its own elements. In\n * exchange, this mixin trades off a one-time cost of querying all elements in\n * the shadow tree instead of paying an ongoing cost to query for an element\n * each time the component wants to inspect or manipulate it.\n *\n * This mixin expects the component to define a Shadow DOM subtree. You can\n * create that tree yourself, or make use of\n * [ShadowTemplateMixin](ShadowTemplateMixin.md).\n *\n * This mixin is inspired by Polymer's [automatic\n * node finding](https://www.polymer-project.org/1.0/docs/devguide/local-dom.html#node-finding)\n * feature.\n */\n class ShadowElementReferences extends base {\n\n constructor() {\n super();\n if (this.shadowRoot) {\n // Look for elements in the shadow subtree that have id attributes.\n // An alternatively implementation of this mixin would be to just define\n // a this.$ getter that lazily does this search the first time someone\n // tries to access this.$. That might introduce some complexity – if the\n // the tree changed after it was first populated, the result of\n // searching for a node might be somewhat unpredictable.\n this.$ = {};\n const nodesWithIds = this.shadowRoot.querySelectorAll('[id]');\n [].forEach.call(nodesWithIds, node => {\n const id = node.getAttribute('id');\n this.$[id] = node;\n });\n }\n }\n\n /**\n * The collection of references to the elements with IDs in a component's\n * Shadow DOM subtree.\n *\n * @type {object}\n * @member $\n */\n }\n\n return ShadowElementReferences;\n};\n","import symbols from '../src/symbols';\n\n\n/* Exported function extends a base class with ShadowTemplate. */\nexport default (base) => {\n\n /**\n * Mixin for stamping a template into a Shadow DOM subtree upon component\n * instantiation.\n *\n * To use this mixin, define a `template` property as a string or HTML\n * `` element:\n *\n * class MyElement extends ShadowTemplateMixin(HTMLElement) {\n * get [symbols.template]() {\n * return `Hello, world .`;\n * }\n * }\n *\n * When your component class is instantiated, a shadow root will be created on\n * the instance, and the contents of the template will be cloned into the\n * shadow root. If your component does not define a `template` property, this\n * mixin has no effect.\n *\n * For the time being, this extension retains support for Shadow DOM v0. That\n * will eventually be deprecated as browsers (and the Shadow DOM polyfill)\n * implement Shadow DOM v1.\n */\n class ShadowTemplate extends base {\n\n /*\n * If the component defines a template, a shadow root will be created on the\n * component instance, and the template stamped into it.\n */\n constructor() {\n super();\n let template = this[symbols.template];\n // TODO: Save the processed template with the component's class prototype\n // so it doesn't need to be processed with every instantiation.\n if (template) {\n\n if (typeof template === 'string') {\n // Upgrade plain string to real template.\n template = createTemplateWithInnerHTML(template);\n }\n\n if (window.ShadowDOMPolyfill) {\n shimTemplateStyles(template, this.localName);\n }\n\n const root = this.attachShadow({ mode: 'open' });\n const clone = document.importNode(template.content, true);\n root.appendChild(clone);\n }\n }\n\n }\n\n return ShadowTemplate;\n};\n\n\n// Convert a plain string of HTML into a real template element.\nfunction createTemplateWithInnerHTML(innerHTML) {\n const template = document.createElement('template');\n // REVIEW: Is there an easier way to do this?\n // We'd like to just set innerHTML on the template content, but since it's\n // a DocumentFragment, that doesn't work.\n const div = document.createElement('div');\n div.innerHTML = innerHTML;\n while (div.childNodes.length > 0) {\n template.content.appendChild(div.childNodes[0]);\n }\n return template;\n}\n\n// Invoke basic style shimming with ShadowCSS.\nfunction shimTemplateStyles(template, tag) {\n window.WebComponents.ShadowCSS.shimStyling(template.content, tag);\n}\n","import createSymbol from './createSymbol';\nimport symbols from './symbols';\n\n\n// Symbols for private data members on an element.\nconst canSelectNextSymbol = createSymbol('canSelectNext');\nconst canSelectPreviousSymbol = createSymbol('canSelectPrevious');\nconst selectionRequiredSymbol = createSymbol('selectionRequired');\nconst selectionWrapsSymbol = createSymbol('selectionWraps');\n\n// We want to expose both selectedIndex and selectedItem as independent\n// properties but keep them in sync. This allows a component user to reference\n// the selection by whatever means is most natural for their situation.\n//\n// To efficiently keep these properties in sync, we track \"external\" and\n// \"internal\" references for each property:\n//\n// The external index or item is the one we report to the outside world when\n// asked for selection. When handling a change to index or item, we update the\n// external reference as soon as possible, so that if anyone immediately asks\n// for the current selection, they will receive a stable answer.\n//\n// The internal index or item tracks whichever index or item last received the\n// full set of processing. Processing includes raising a change event for the\n// new value. Once we've begun that processing, we store the new value as the\n// internal value to indicate we've handled it.\n//\nconst externalSelectedIndexSymbol = createSymbol('externalSelectedIndex');\nconst externalSelectedItemSymbol = createSymbol('externalSelectedItem');\nconst internalSelectedIndexSymbol = createSymbol('internalSelectedIndex');\nconst internalSelectedItemSymbol = createSymbol('internalSelectedItem');\n\n\n/* Exported function extends a base class with SingleSelection. */\nexport default (base) => {\n\n /**\n * Mixin which manages single-selection semantics for items in a list.\n *\n * This mixin expects a component to provide an `items` Array or NodeList of\n * all elements in the list. A standard way to do that with is the\n * [ContentItemsMixin](ContentItemsMixin.md), which takes a component's\n * content (typically its distributed children) as the set of list items; see\n * that mixin for details.\n *\n * This mixin tracks a single selected item in the list, and provides means to\n * get and set that state by item position (`selectedIndex`) or item identity\n * (`selectedItem`). The selection can be moved in the list via the methods\n * `selectFirst`, `selectLast`, `selectNext`, and `selectPrevious`.\n *\n * This mixin does not produce any user-visible effects to represent\n * selection. Other mixins, such as\n * [SelectionAriaActiveMixin](SelectionAriaActiveMixin.md),\n * [SelectionHighlightMixin](SelectionHighlightMixin.md) and\n * [SelectionInViewMixin](SelectionInViewMixin.md), modify the selected item\n * in common ways to let the user know a given item is selected or not\n * selected.\n */\n class SingleSelection extends base {\n\n constructor() {\n super();\n // Set defaults.\n if (typeof this.selectionRequired === 'undefined') {\n this.selectionRequired = this[symbols.defaults].selectionRequired;\n }\n if (typeof this.selectionWraps === 'undefined') {\n this.selectionWraps = this[symbols.defaults].selectionWraps;\n }\n }\n\n /**\n * True if the selection can be moved to the next item, false if not (the\n * selected item is the last item in the list).\n *\n * @type {boolean}\n */\n get canSelectNext() {\n return this[canSelectNextSymbol];\n }\n set canSelectNext(canSelectNext) {\n const previousCanSelectNext = this[canSelectNextSymbol];\n this[canSelectNextSymbol] = canSelectNext;\n if ('canSelectNext' in base.prototype) { super.canSelectNext = canSelectNext; }\n if (canSelectNext !== previousCanSelectNext) {\n this.dispatchEvent(new CustomEvent('can-select-next-changed'));\n }\n }\n\n /**\n * True if the selection can be moved to the previous item, false if not\n * (the selected item is the first one in the list).\n *\n * @type {boolean}\n */\n get canSelectPrevious() {\n return this[canSelectPreviousSymbol];\n }\n set canSelectPrevious(canSelectPrevious) {\n const previousCanSelectPrevious = this[canSelectPreviousSymbol];\n this[canSelectPreviousSymbol] = canSelectPrevious;\n if ('canSelectPrevious' in base.prototype) { super.canSelectPrevious = canSelectPrevious; }\n if (canSelectPrevious !== previousCanSelectPrevious) {\n this.dispatchEvent(new CustomEvent('can-select-previous-changed'));\n }\n }\n\n get [symbols.defaults]() {\n const defaults = super[symbols.defaults] || {};\n defaults.selectionRequired = false;\n defaults.selectionWraps = false;\n return defaults;\n }\n\n /**\n * Handle a new item being added to the list.\n *\n * The default implementation of this method simply sets the item's\n * selection state to false.\n *\n * @param {HTMLElement} item - the item being added\n */\n [symbols.itemAdded](item) {\n if (super[symbols.itemAdded]) { super[symbols.itemAdded](item); }\n this[symbols.itemSelected](item, item === this.selectedItem);\n }\n\n [symbols.itemsChanged]() {\n if (super[symbols.itemsChanged]) { super[symbols.itemsChanged](); }\n\n // In case selected item changed position or was removed.\n trackSelectedItem(this);\n\n // In case the change in items affected which navigations are possible.\n updatePossibleNavigations(this);\n }\n\n /**\n * Apply the indicate selection state to the item.\n *\n * The default implementation of this method does nothing. User-visible\n * effects will typically be handled by other mixins.\n *\n * @param {HTMLElement} item - the item being selected/deselected\n * @param {boolean} selected - true if the item is selected, false if not\n */\n [symbols.itemSelected](item, selected) {\n if (super[symbols.itemSelected]) { super[symbols.itemSelected](item, selected); }\n }\n\n /**\n * The index of the item which is currently selected.\n *\n * A `selectedIndex` of -1 indicates there is no selection. Setting this\n * property to -1 will remove any existing selection.\n *\n * @type {number}\n */\n get selectedIndex() {\n return this[externalSelectedIndexSymbol] != null ?\n this[externalSelectedIndexSymbol] :\n -1;\n }\n set selectedIndex(index) {\n // See notes at top about internal vs. external copies of this property.\n const previousSelectedIndex = this[internalSelectedIndexSymbol];\n let item;\n if (index !== this[externalSelectedIndexSymbol]) {\n // Store the new index and the corresponding item.\n const items = this.items;\n const hasItems = items && items.length > 0;\n if (!(hasItems && index >= 0 && index < items.length)) {\n index = -1; // No item at that index.\n }\n this[externalSelectedIndexSymbol] = index;\n item = hasItems && index >= 0 ? items[index] : null;\n this[externalSelectedItemSymbol] = item;\n } else {\n item = this[externalSelectedItemSymbol];\n }\n\n // Now let super do any work.\n if ('selectedIndex' in base.prototype) { super.selectedIndex = index; }\n\n if (index !== previousSelectedIndex) {\n // The selected index changed.\n this[internalSelectedIndexSymbol] = index;\n\n const event = new CustomEvent('selected-index-changed', {\n detail: {\n selectedIndex: index,\n value: index // for Polymer binding. TODO: Verify still necessary\n }\n });\n this.dispatchEvent(event);\n }\n\n if (this[internalSelectedItemSymbol] !== item) {\n // Update selectedItem property so it can have its own effects.\n this.selectedItem = item;\n }\n }\n\n /**\n * The currently selected item, or null if there is no selection.\n *\n * Setting this property to null deselects any currently-selected item.\n * Setting this property to an object that is not in the list has no effect.\n *\n * TODO: Even if selectionRequired, can still explicitly set selectedItem to null.\n * TODO: If selectionRequired, leave selection alone?\n *\n * @type {object}\n */\n get selectedItem() {\n return this[externalSelectedItemSymbol] || null;\n }\n set selectedItem(item) {\n // See notes at top about internal vs. external copies of this property.\n const previousSelectedItem = this[internalSelectedItemSymbol];\n let index;\n if (item !== this[externalSelectedItemSymbol]) {\n // Store item and look up corresponding index.\n const items = this.items;\n const hasItems = items && items.length > 0;\n index = hasItems ? Array.prototype.indexOf.call(items, item) : -1;\n this[externalSelectedIndexSymbol] = index;\n if (index < 0) {\n item = null; // The indicated item isn't actually in `items`.\n }\n this[externalSelectedItemSymbol] = item;\n } else {\n index = this[externalSelectedIndexSymbol];\n }\n\n // Now let super do any work.\n if ('selectedItem' in base.prototype) { super.selectedItem = item; }\n\n if (item !== previousSelectedItem) {\n // The selected item changed.\n this[internalSelectedItemSymbol] = item;\n\n if (previousSelectedItem) {\n // Update selection state of old item.\n this[symbols.itemSelected](previousSelectedItem, false);\n }\n if (item) {\n // Update selection state to new item.\n this[symbols.itemSelected](item, true);\n }\n\n updatePossibleNavigations(this);\n\n const event = new CustomEvent('selected-item-changed', {\n detail: {\n selectedItem: item,\n value: item // for Polymer binding\n }\n });\n this.dispatchEvent(event);\n }\n\n if (this[internalSelectedIndexSymbol] !== index) {\n // Update selectedIndex property so it can have its own effects.\n this.selectedIndex = index;\n }\n }\n\n /**\n * Select the first item in the list.\n */\n selectFirst() {\n if (super.selectFirst) { super.selectFirst(); }\n return selectIndex(this, 0);\n }\n\n /**\n * True if the list should always have a selection (if it has items).\n *\n * @type {boolean}\n * @default false\n */\n get selectionRequired() {\n return this[selectionRequiredSymbol];\n }\n set selectionRequired(selectionRequired) {\n this[selectionRequiredSymbol] = selectionRequired;\n if ('selectionRequired' in base.prototype) { super.selectionRequired = selectionRequired; }\n trackSelectedItem(this);\n }\n\n /**\n * True if selection navigations wrap from last to first, and vice versa.\n *\n * @type {boolean}\n * @default false\n */\n get selectionWraps() {\n return this[selectionWrapsSymbol];\n }\n set selectionWraps(value) {\n this[selectionWrapsSymbol] = String(value) === 'true';\n if ('selectionWraps' in base.prototype) { super.selectionWraps = value; }\n updatePossibleNavigations(this);\n }\n\n /**\n * Select the last item in the list.\n */\n selectLast() {\n if (super.selectLast) { super.selectLast(); }\n return selectIndex(this, this.items.length - 1);\n }\n\n /**\n * Select the next item in the list.\n */\n selectNext() {\n if (super.selectNext) { super.selectNext(); }\n return selectIndex(this, this.selectedIndex + 1);\n }\n\n /**\n * Select the previous item in the list.\n *\n * If the list has no selection, the last item will be selected.\n */\n selectPrevious() {\n if (super.selectPrevious) { super.selectPrevious(); }\n const newIndex = this.selectedIndex < 0 ?\n this.items.length - 1 : // No selection yet; select last item.\n this.selectedIndex - 1;\n return selectIndex(this, newIndex);\n }\n\n /**\n * Fires when the selectedItem property changes.\n *\n * @memberof SingleSelection\n * @event selected-item-changed\n * @param {HTMLElement} detail.selectedItem The new selected item.\n * @param {HTMLElement} detail.previousItem The previously selected item.\n */\n\n /**\n * Fires when the selectedIndex property changes.\n *\n * @memberof SingleSelection\n * @event selected-index-changed\n * @param {number} detail.selectedIndex The new selected index.\n */\n\n }\n\n return SingleSelection;\n};\n\n\n// Ensure the given index is within bounds, and select it if it's not already\n// selected.\nfunction selectIndex(element, index) {\n const count = element.items.length;\n\n const boundedIndex = (element.selectionWraps) ?\n // JavaScript mod doesn't handle negative numbers the way we want to wrap.\n // See http://stackoverflow.com/a/18618250/76472\n ((index % count) + count) % count :\n\n // Keep index within bounds of array.\n Math.max(Math.min(index, count - 1), 0);\n\n const previousIndex = element.selectedIndex;\n if (previousIndex !== boundedIndex) {\n element.selectedIndex = boundedIndex;\n return true;\n } else {\n return false;\n }\n}\n\n// Following a change in the set of items, or in the value of the\n// `selectionRequired` property, reacquire the selected item. If it's moved,\n// update `selectedIndex`. If it's been removed, and a selection is required,\n// try to select another item.\nfunction trackSelectedItem(element) {\n\n const items = element.items;\n const itemCount = items ? items.length : 0;\n\n const previousSelectedItem = element.selectedItem;\n if (!previousSelectedItem) {\n // No item was previously selected.\n if (element.selectionRequired) {\n // Select the first item by default.\n element.selectedIndex = 0;\n }\n } else if (itemCount === 0) {\n // We've lost the selection, and there's nothing left to select.\n element.selectedItem = null;\n } else {\n // Try to find the previously-selected item in the current set of items.\n const indexInCurrentItems = Array.prototype.indexOf.call(items, previousSelectedItem);\n const previousSelectedIndex = element.selectedIndex;\n if (indexInCurrentItems < 0) {\n // Previously-selected item was removed from the items.\n // Select the item at the same index (if it exists) or as close as possible.\n const newSelectedIndex = Math.min(previousSelectedIndex, itemCount - 1);\n // Select by item, since index may be the same, and we want to raise the\n // selected-item-changed event.\n element.selectedItem = items[newSelectedIndex];\n } else if (indexInCurrentItems !== previousSelectedIndex) {\n // Previously-selected item still there, but changed position.\n element.selectedIndex = indexInCurrentItems;\n }\n }\n}\n\n// Following a change in selection, report whether it's now possible to\n// go next/previous from the given index.\nfunction updatePossibleNavigations(element) {\n let canSelectNext;\n let canSelectPrevious;\n const items = element.items;\n if (items == null || items.length === 0) {\n // No items to select.\n canSelectNext = false;\n canSelectPrevious = false;\n } if (element.selectionWraps) {\n // Since there are items, can always go next/previous.\n canSelectNext = true;\n canSelectPrevious = true;\n } else {\n const index = element.selectedIndex;\n if (index < 0 && items.length > 0) {\n // Special case. If there are items but no selection, declare that it's\n // always possible to go next/previous to create a selection.\n canSelectNext = true;\n canSelectPrevious = true;\n } else {\n // Normal case: we have an index in a list that has items.\n canSelectPrevious = (index > 0);\n canSelectNext = (index < items.length - 1);\n }\n }\n if (element.canSelectNext !== canSelectNext) {\n element.canSelectNext = canSelectNext;\n }\n if (element.canSelectPrevious !== canSelectPrevious) {\n element.canSelectPrevious = canSelectPrevious;\n }\n}\n","import createSymbol from './createSymbol';\nimport symbols from './symbols';\n\n\nconst playingSymbol = createSymbol('playing');\nconst selectionTimerDurationSymbol = createSymbol('selectionTimerDuration');\nconst timerTimeoutSymbol = createSymbol('timerTimeout');\n\n\n/* Exported function extends a base class with TimerSelection. */\nexport default (base) => {\n\n /**\n * Mixin which provides for automatic timed changes in selection.\n *\n * This mixin is useful for creating slideshow-like elements such as\n * [basic-slideshow](../../basic-slideshow) and\n * [basic-slideshow-with-controls](../../basic-slideshow-with-controls).\n *\n * Typical usage:\n *\n * class CarouselWithTimer extends TimerSelectionMixin(Carousel) {}\n * customElements.define('carousel-with-arrows', CarouselWithTimer);\n *\n * This mixin expects the component to define an `items` property, as well as\n * `selectFirst` and `selectNext` methods. You can implement those yourself,\n * or use [ContentItemsMixin](ContentItemsMixin.md) and\n * [SingleSelectionMixin](SingleSelectionMixin.md).\n */\n class TimerSelection extends base {\n\n constructor() {\n super();\n // Set defaults.\n if (typeof this.playing === 'undefined') {\n this.playing = this[symbols.defaults].playing;\n }\n if (typeof this.selectionTimerDuration === 'undefined') {\n this.selectionTimerDuration = this[symbols.defaults].selectionTimerDuration;\n }\n }\n\n contentChanged() {\n if (super.contentChanged) { super.contentChanged(); }\n restartTimer(this);\n }\n\n get [symbols.defaults]() {\n const defaults = super[symbols.defaults] || {};\n defaults.playing = false;\n defaults.selectionTimerDuration = 1000;\n return defaults;\n }\n\n /**\n * Begin automatic progression of the selection.\n */\n play() {\n if (super.play) { super.play(); }\n startTimer(this);\n this[playingSymbol] = true;\n }\n\n /**\n * Pause automatic progression of the selection.\n */\n pause() {\n if (super.pause) { super.pause(); }\n clearTimer(this);\n this[playingSymbol] = false;\n }\n\n /**\n * True if the selection is being automatically advanced.\n *\n * @type {boolean}\n * @default false\n */\n get playing() {\n return this[playingSymbol];\n }\n set playing(playing) {\n const previousPlaying = this[playingSymbol];\n const parsed = String(playing) === 'true'; // Cast to boolean\n if ('playing' in base.prototype) { super.playing = playing; }\n if (parsed !== previousPlaying) {\n if (playing) {\n this.play();\n } else {\n this.pause();\n }\n }\n }\n\n /*\n * When the selected item changes (because of something this mixin did, or\n * was changed by an outside agent like the user), we wait before advancing\n * to the next item. By triggering the next item this way, we implicitly get\n * a desirable behavior: if the user changes the selection (e.g., in a\n * carousel), we let them see that selection state for a while before\n * advancing the selection ourselves.\n */\n get selectedItem() {\n return super.selectedItem;\n }\n set selectedItem(item) {\n if ('selectedItem' in base.prototype) { super.selectedItem = item; }\n restartTimer(this);\n }\n\n /**\n * The time in milliseconds that will elapse after the selection changes\n * before the selection will be advanced to the next item in the list.\n *\n * @type {number} - Time in milliseconds\n * @default 1000 (1 second)\n */\n get selectionTimerDuration() {\n return this[selectionTimerDurationSymbol];\n }\n set selectionTimerDuration(value) {\n this[selectionTimerDurationSymbol] = parseInt(value);\n if ('selectionTimerDuration' in base.prototype) { super.selectionTimerDuration = value; }\n }\n\n }\n\n return TimerSelection;\n};\n\n\nfunction clearTimer(element) {\n if (element[timerTimeoutSymbol]) {\n clearTimeout(element[timerTimeoutSymbol]);\n element[timerTimeoutSymbol] = null;\n }\n}\n\nfunction restartTimer(element) {\n clearTimer(element);\n if (element.playing && element.items && element.items.length > 0) {\n startTimer(element);\n }\n}\n\nfunction startTimer(element) {\n // If play() is called more than once, cancel any existing timer.\n clearTimer(element);\n element[timerTimeoutSymbol] = setTimeout(() => {\n selectNextWithWrap(element);\n }, element.selectionTimerDuration);\n}\n\n// Select the next item, wrapping to first item if necessary.\nfunction selectNextWithWrap(element) {\n const items = element.items;\n if (items && items.length > 0) {\n if (element.selectedIndex == null || element.selectedIndex === items.length - 1) {\n element.selectFirst();\n } else {\n element.selectNext();\n }\n }\n}\n","/**\n * Helper function to create a symbol that can be used for associating private\n * data with an element.\n *\n * Mixins and component classes often want to associate private data with an\n * element instance, but JavaScript does not have direct support for true\n * private properties. One approach is to use the\n * [Symbol](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Symbol)\n * data type to set and retrieve data on an element.\n *\n * Unfortunately, the Symbol type is not available in Internet Explorer 11. The\n * `createSymbol` helper function exists as a workaround for IE 11. Rather than\n * returning a true Symbol, it simply returns an underscore-prefixed string.\n *\n * Usage:\n *\n * const fooSymbol = createSymbol('foo');\n *\n * class MyElement extends HTMLElement {\n * get foo() {\n * return this[fooSymbol];\n * }\n * set foo(value) {\n * this[fooSymbol] = value;\n * }\n * }\n *\n * In IE 11, this sample will \"hide\" data behind an instance property this._foo.\n * The use of the underscore is meant to reduce (not eliminate) the potential\n * for name conflicts, and discourage (not prevent) external access to this\n * data. In modern browsers, the above code will eliminate the potential of\n * naming conflicts, and better hide the data behind a real Symbol.\n *\n * @function createSymbol\n * @param {string} description - A string to identify the symbol when debugging\n */\nexport default function createSymbol(description) {\n return typeof Symbol === 'function' ?\n Symbol(description) :\n `_${description}`;\n}\n","/*\n * Microtask helper for IE 11.\n *\n * Executing a function as a microtask is trivial in browsers that support\n * promises, whose then() clauses use microtask timing. IE 11 doesn't support\n * promises, but does support MutationObservers, which are also executed as\n * microtasks. So this helper uses an MutationObserver to achieve microtask\n * timing.\n *\n * See https://jakearchibald.com/2015/tasks-microtasks-queues-and-schedules/\n *\n * Inspired by Polymer's async() function.\n */\n\n\n// The queue of pending callbacks to be executed as microtasks.\nconst callbacks = [];\n\n// Create an element that we will modify to force observable mutations.\nconst element = document.createTextNode('');\n\n// A monotonically-increasing value.\nlet counter = 0;\n\n\n/**\n * Add a callback to the microtask queue.\n *\n * This uses a MutationObserver so that it works on IE 11.\n *\n * NOTE: IE 11 may actually use timeout timing with MutationObservers. This\n * needs more investigation.\n *\n * @function microtask\n * @param {function} callback\n */\nexport default function microtask(callback) {\n callbacks.push(callback);\n // Force a mutation.\n element.textContent = ++counter;\n}\n\n\n// Execute any pending callbacks.\nfunction executeCallbacks() {\n while (callbacks.length > 0) {\n const callback = callbacks.shift();\n callback();\n }\n}\n\n\n// Create the observer.\nconst observer = new MutationObserver(executeCallbacks);\nobserver.observe(element, {\n characterData: true\n});\n","import createSymbol from './createSymbol';\nimport toggleClass from './toggleClass';\n\n\n// Symbols for private data members on an element.\nconst safeToSetAttributesSymbol = createSymbol('safeToSetAttributes');\nconst pendingAttributesSymbol = createSymbol('pendingAttributes');\nconst pendingClassesSymbol = createSymbol('pendingClasses');\n\n\n/**\n * Helper functions for updating attributes, including the `class` attribute.\n */\nexport default {\n\n /**\n * Perform any pending updates to attributes and classes.\n *\n * This writes any `setAttribute` or `toggleClass` values that were performed\n * before an element was attached to the document for the first time.\n *\n * This method should be called by mixins/components in their\n * `connectedCallback`. If mulitple mixins/components invoke this during the\n * same `connectedCallback`, only the first call will have any effect. The\n * subsequent calls will be harmless.\n *\n * @param {HTMLElement} element - The element being added to the document.\n */\n connected(element) {\n element[safeToSetAttributesSymbol] = true;\n\n // Set any pending attributes.\n if (element[pendingAttributesSymbol]) {\n for (let attribute in element[pendingAttributesSymbol]) {\n const value = element[pendingAttributesSymbol][attribute];\n setAttributeToElement(element, attribute, value);\n }\n element[pendingAttributesSymbol] = null;\n }\n\n // Set any pending classes.\n if (element[pendingClassesSymbol]) {\n for (let className in element[pendingClassesSymbol]) {\n const value = element[pendingClassesSymbol][className];\n toggleClass(element, className, value);\n }\n element[pendingClassesSymbol] = null;\n }\n },\n\n /**\n * Set/unset the attribute with the indicated name.\n *\n * This method exists primarily to handle the case where an element wants to\n * set a default property value that should be reflected as an attribute. An\n * important limitation of custom element consturctors is that they cannot\n * set attributes. A call to `setAttribute` during the constructor will\n * be deferred until the element is connected to the document.\n *\n * @param {string} attribute - The name of the *attribute* (not property) to set.\n * @param {object} value - The value to set. If null, the attribute will be removed.\n */\n setAttribute(element, attribute, value) {\n if (element[safeToSetAttributesSymbol]) {\n // Safe to set attributes immediately.\n setAttributeToElement(element, attribute, value);\n } else {\n // Defer setting attributes until the first time we're connected.\n if (!element[pendingAttributesSymbol]) {\n element[pendingAttributesSymbol] = {};\n }\n element[pendingAttributesSymbol][attribute] = value;\n }\n },\n\n /**\n * Set/unset the class with the indicated name.\n *\n * This method exists primarily to handle the case where an element wants to\n * set a default property value that should be reflected as as class. An\n * important limitation of custom element consturctors is that they cannot\n * set attributes, including the `class` attribute. A call to\n * `toggleClass` during the constructor will be deferred until the element\n * is connected to the document.\n *\n * @param {string} className - The name of the class to set.\n * @param {object} value - True to set the class, false to remove it.\n */\n toggleClass(element, className, value) {\n if (element[safeToSetAttributesSymbol]) {\n // Safe to set class immediately.\n toggleClass(element, className, value);\n } else {\n // Defer setting class until the first time we're connected.\n if (!element[pendingClassesSymbol]) {\n element[pendingClassesSymbol] = {};\n }\n element[pendingClassesSymbol][className] = value;\n }\n }\n\n};\n\n\n// Reflect the attribute to the given element.\n// If the value is null, remove the attribute.\nfunction setAttributeToElement(element, attributeName, value) {\n if (value === null || typeof value === 'undefined') {\n element.removeAttribute(attributeName);\n } else {\n const text = String(value);\n // Avoid recursive attributeChangedCallback calls.\n if (element.getAttribute(attributeName) !== text) {\n element.setAttribute(attributeName, value);\n }\n }\n}\n","import createSymbol from './createSymbol';\n\n/**\n * A collection of Symbol objects for standard component properties and methods.\n *\n * These Symbol objects are used to allow mixins and a component to internally\n * communicate, without exposing these properties and methods in the component's\n * public API.\n *\n * To use these Symbol objects in your own component, include this module and\n * then create a property or method whose key is the desired Symbol.\n *\n * import 'SingleSelectionMixin' from 'basic-component-mixins/src/SingleSelectionMixin';\n * import 'symbols' from 'basic-component-mixins/src/symbols';\n *\n * class MyElement extends SingleSelectionMixin(HTMLElement) {\n * [symbols.itemSelected](item, selected) {\n * // This will be invoked whenever an item is selected/deselected.\n * }\n * }\n *\n * @module symbols\n */\nconst symbols = {\n\n /**\n * Symbol for the `defaults` property.\n *\n * This property can be used to set or override defaults that will be applied\n * to a new component instance. When implementing this property, take care to\n * first acquire any defaults defined by the superclass. The standard idiom is\n * as follows:\n *\n * get [symbols.defaults]() {\n * const defaults = super[symbols.defaults] || {};\n * // Set or override default values here\n * defaults.customProperty = false;\n * return defaults;\n * }\n *\n * @var {object} defaults\n */\n defaults: createSymbol('defaults'),\n\n /**\n * Symbol for the `dragging` property.\n *\n * Components like carousels often define animated CSS transitions for\n * sliding effects. Such a transition should usually *not* be applied while\n * the user is dragging, because a CSS animation will introduce a lag that\n * makes the swipe feel sluggish. Instead, as long as the user is dragging\n * with their finger down, the transition should be suppressed. When the\n * user releases their finger, the transition can be restored, allowing the\n * animation to show the carousel sliding into its final position.\n *\n * @type {boolean} true if a drag is in progress, false if not.\n */\n dragging: createSymbol('dragging'),\n\n /**\n * Symbol for the `goDown` method.\n *\n * This method is invoked when the user wants to go/navigate down.\n *\n * @function goDown\n */\n goDown: createSymbol('goDown'),\n\n /**\n * Symbol for the `goEnd` method.\n *\n * This method is invoked when the user wants to go/navigate to the end (e.g.,\n * of a list).\n *\n * @function goEnd\n */\n goEnd: createSymbol('goEnd'),\n\n /**\n * Symbol for the `goLeft` method.\n *\n * This method is invoked when the user wants to go/navigate left.\n *\n * @function goLeft\n */\n goLeft: createSymbol('goLeft'),\n\n /**\n * Symbol for the `goRight` method.\n *\n * This method is invoked when the user wants to go/navigate right.\n *\n * @function goRight\n */\n goRight: createSymbol('goRight'),\n\n /**\n * Symbol for the `goStart` method.\n *\n * This method is invoked when the user wants to go/navigate to the start\n * (e.g., of a list).\n *\n * @function goStart\n */\n goStart: createSymbol('goStart'),\n\n /**\n * Symbol for the `goUp` method.\n *\n * This method is invoked when the user wants to go/navigate up.\n *\n * @function goUp\n */\n goUp: createSymbol('goUp'),\n\n /**\n * Symbol for the `itemAdded` method.\n *\n * This method is invoked when a new item is added to a list.\n *\n * @function itemAdded\n * @param {HTMLElement} item - the item being selected/deselected\n */\n itemAdded: createSymbol('itemAdded'),\n\n\n /**\n * Symbol for the `itemsChanged` method.\n *\n * This method is invoked when the underlying contents change. It is also\n * invoked on component initialization – since the items have \"changed\" from\n * being nothing.\n */\n itemsChanged: createSymbol('itemsChanged'),\n\n /**\n * Symbol for the `itemSelected` method.\n *\n * This method is invoked when an item becomes selected or deselected.\n *\n * @function itemSelected\n * @param {HTMLElement} item - the item being selected/deselected\n * @param {boolean} selected - true if the item is selected, false if not\n */\n itemSelected: createSymbol('itemSelected'),\n\n /**\n * Symbol for the `keydown` method.\n *\n * This method is invoked when an element receives a `keydown` event.\n *\n * @function keydown\n * @param {KeyboardEvent} event - the event being processed\n */\n keydown: createSymbol('keydown'),\n\n /**\n * Symbol for the `template` property.\n *\n * This property returns a component's template.\n *\n * @type {string|HTMLElement}\n */\n template: createSymbol('template')\n};\n\nexport default symbols;\n","/**\n * Helper function for standard classList.toggle() behavior on old browsers,\n * namely IE 11.\n *\n * The standard\n * [classlist](https://developer.mozilla.org/en-US/docs/Web/API/Element/classList)\n * object has a `toggle()` function that supports a second Boolean parameter\n * that can be used to succinctly turn a class on or off. This feature is often\n * useful in designing custom elements, which may want to externally reflect\n * component state in a CSS class that can be used for styling purposes.\n *\n * Unfortunately, IE 11 does not support the Boolean parameter to\n * `classList.toggle()`. This helper function behaves like the standard\n * `toggle()`, including support for the Boolean parameter, so that it can be\n * used even on IE 11.\n *\n * @function toggleClass\n * @param {HTMLElement} element - The element to modify\n * @param {string} className - The class to add/remove\n * @param {boolean} [force] - Force the class to be added (if true) or removed\n * (if false)\n */\nexport default function toggleClass(element, className, force) {\n const classList = element.classList;\n const addClass = (typeof force === 'undefined') ?\n !classList.contains(className) :\n force;\n if (addClass) {\n classList.add(className);\n } else {\n classList.remove(className);\n }\n return addClass;\n}\n","import AttributeMarshallingMixin from '../../basic-component-mixins/src/AttributeMarshallingMixin';\nimport ComposableMixin from '../../basic-component-mixins/src/ComposableMixin';\nimport DistributedChildrenMixin from '../../basic-component-mixins/src/DistributedChildrenMixin';\nimport ShadowElementReferencesMixin from '../../basic-component-mixins/src/ShadowElementReferencesMixin';\nimport ShadowTemplateMixin from '../../basic-component-mixins/src/ShadowTemplateMixin';\n\n\n/**\n * A sample general-purpose base class for defining custom elements that mixes\n * in some common features: template stamping into a shadow root, shadow element\n * references, marshalling attributes to properties, and retrieving the children\n * distributed to a component.\n *\n * This base class is not special in any way, and is defined only as a\n * convenient shorthand for applying the mixins listed above. You can use this\n * class as a base class for your own elements, or easily create your own base\n * class by applying the same set of mixins.\n *\n * The ElementBase base class does not register itself as a custom element with\n * the browser, and hence cannot be independently instantiated.\n *\n * @mixes AttributeMarshallingMixin\n * @mixes ComposableMixin\n * @mixes DistributedChildrenMixin\n * @mixes ShadowElementReferencesMixin\n * @mixes ShadowTemplateMixin\n */\nclass ElementBase extends ComposableMixin(HTMLElement).compose(\n ShadowTemplateMixin, // before node finding, so shadow root is populated\n ShadowElementReferencesMixin, // before marshalling, so properties can use refs\n AttributeMarshallingMixin,\n DistributedChildrenMixin\n) {}\n\nexport default ElementBase;\n","/*\n * This file is transpiled to create an ES5-compatible distribution in which\n * the package's main feature(s) are available via the window.Basic global.\n * If you're already using ES6 yourself, ignore this file, and instead import\n * the source file(s) you want from the src folder.\n */\n\nimport Slideshow from './src/Slideshow';\n\nwindow.Basic = window.Basic || {};\nwindow.Basic.Slideshow = Slideshow;\n","import AnimationStage from '../../basic-animation-stage/src/AnimationStage';\nimport symbols from '../../basic-component-mixins/src/symbols';\nimport TimerSelectionMixin from '../../basic-component-mixins/src/TimerSelectionMixin';\n\n\nconst base = AnimationStage.compose(\n TimerSelectionMixin\n);\n\n\n/**\n * Slideshow with animated transitions.\n *\n * [Live demo](http://basicwebcomponents.org/basic-web-components/packages/basic-slideshow/)\n *\n * By default the slideshow will immediately begin playing when it is connected\n * to the document, advance every 3000 ms (3 seconds), and use a simple\n * crossfade effect. For a variation with play controls, see\n * [basic-slideshow-with-controls](../basic-slideshow-with-controls).\n *\n * This component can be used on its own. To incorporate slideshow behavior into\n * a component of your own, apply the\n * [TimerSelectionMixin](../basic-component-mixins/docs/TimerSelectionMixin.md).\n *\n * @extends AnimationStage\n * @mixes TimerSelectionMixin\n */\nclass Slideshow extends base {\n\n get [symbols.defaults]() {\n const defaults = super[symbols.defaults] || {};\n defaults.playing = true;\n defaults.selectionAnimationDuration = 500;\n defaults.selectionAnimationEffect = 'crossfade';\n defaults.selectionRequired = true;\n defaults.selectionTimerDuration = 3000;\n defaults.selectionWraps = true;\n return defaults;\n }\n\n}\n\n\ncustomElements.define('basic-slideshow', Slideshow);\nexport default Slideshow;\n"]}
\ No newline at end of file
diff --git a/packages/basic-slideshow/index.html b/packages/basic-slideshow/index.html
index 0cb4c1cd..c737aed3 100644
--- a/packages/basic-slideshow/index.html
+++ b/packages/basic-slideshow/index.html
@@ -8,7 +8,8 @@
-
+
+
diff --git a/packages/basic-slideshow/src/Slideshow.js b/packages/basic-slideshow/src/Slideshow.js
index b08f448d..9e18401c 100644
--- a/packages/basic-slideshow/src/Slideshow.js
+++ b/packages/basic-slideshow/src/Slideshow.js
@@ -1,21 +1,9 @@
-import ElementBase from '../../basic-element-base/src/ElementBase';
-import ContentItemsMixin from '../../basic-component-mixins/src/ContentItemsMixin';
-import DistributedChildrenContentMixin from '../../basic-component-mixins/src/DistributedChildrenContentMixin';
-import FractionalSelectionMixin from '../../basic-component-mixins/src/FractionalSelectionMixin';
-import SelectionAnimationMixin from '../../basic-component-mixins/src/SelectionAnimationMixin';
-import SelectionAriaActiveMixin from '../../basic-component-mixins/src/SelectionAriaActiveMixin';
-import SingleSelectionMixin from '../../basic-component-mixins/src/SingleSelectionMixin';
+import AnimationStage from '../../basic-animation-stage/src/AnimationStage';
import symbols from '../../basic-component-mixins/src/symbols';
import TimerSelectionMixin from '../../basic-component-mixins/src/TimerSelectionMixin';
-const base = ElementBase.compose(
- ContentItemsMixin,
- DistributedChildrenContentMixin,
- FractionalSelectionMixin,
- SelectionAnimationMixin,
- SelectionAriaActiveMixin,
- SingleSelectionMixin,
+const base = AnimationStage.compose(
TimerSelectionMixin
);
@@ -34,13 +22,7 @@ const base = ElementBase.compose(
* a component of your own, apply the
* [TimerSelectionMixin](../basic-component-mixins/docs/TimerSelectionMixin.md).
*
- * @extends ElementBase
- * @mixes ContentItemsMixin
- * @mixes DistributedChildrenContentMixin
- * @mixes FractionalSelectionMixin
- * @mixes SelectionAnimationMixin
- * @mixes SelectionAriaActiveMixin
- * @mixes SingleSelectionMixin
+ * @extends AnimationStage
* @mixes TimerSelectionMixin
*/
class Slideshow extends base {
@@ -56,31 +38,6 @@ class Slideshow extends base {
return defaults;
}
- get [symbols.template]() {
- return `
-
-
-
-
-
- `;
- }
-
}
diff --git a/packages/basic-sliding-carousel/README.md b/packages/basic-sliding-carousel/README.md
index f05d7769..e36cdedc 100644
--- a/packages/basic-sliding-carousel/README.md
+++ b/packages/basic-sliding-carousel/README.md
@@ -1,22 +1,23 @@
# API Documentation
-## SlidingCarousel ⇐ ElementBase
-Lets the user navigate laterally through a sequence of child elements.
+## SlidingCarousel ⇐ SlidingViewport
+Lets the user navigate laterally through a sequence of child elements
+using a simple CSS transition effect to show horizontal movement.
-[Live demo](http://basicwebcomponents.org/basic-web-components/packages/basic-carousel/)
+[Live demo](http://basicwebcomponents.org/basic-web-components/packages/basic-sliding-carousel/)
-basic-sliding-carousel is an implementation of the carousel user interface pattern,
-commonly used for navigating between images, pages, and other elements. This
-pattern presents the user with a linear sequence of elements, only one of
-which is shown at a time. The user can navigate to the next/previous element
-with a variety of input methods.
+basic-sliding-carousel is an implementation of the carousel user interface
+pattern, commonly used for navigating between images, pages, and other
+elements. This pattern presents the user with a linear sequence of elements,
+only one of which is shown at a time. The user can navigate to the
+next/previous element with a variety of input methods.
basic-sliding-carousel is a simpler variation of the more sophisticated
[basic-carousel](../basic-carousel) component. The latter includes support
-for _wrapping_ (going forward from the last item to the first, and vice versa),
-and more complex visual transitions. Those transitions entail use of the
-Web Animation API, which requires a polyfill in older browsers. Hence, the
+for wrapping (going forward from the last item to the first, and vice versa),
+and more complex visual transitions. Those transitions entail use of the Web
+Animation API, which requires a polyfill in older browsers. Hence, the
simpler basic-sliding-carousel may be a more appropriate choice if factors
such as download size are critical.
@@ -25,380 +26,6 @@ recommendations, and support for keyboard/touch/mouse and assistive devices.
See that component for more details on use.
**Kind**: global class
-**Extends:** ElementBase
-**Mixes**: [ContentItemsMixin](../basic-component-mixins/docs/ContentItemsMixin.md)
- , [DirectionSelectionMixin](../basic-component-mixins/docs/DirectionSelectionMixin.md)
- , [DistributedChildrenContentMixin](../basic-component-mixins/docs/DistributedChildrenContentMixin.md)
- , [GenericMixin](../basic-component-mixins/docs/GenericMixin.md)
- , [KeyboardMixin](../basic-component-mixins/docs/KeyboardMixin.md)
- , [KeyboardDirectionMixin](../basic-component-mixins/docs/KeyboardDirectionMixin.md)
- , [SelectionAriaActiveMixin](../basic-component-mixins/docs/SelectionAriaActiveMixin.md)
- , [SingleSelectionMixin](../basic-component-mixins/docs/SingleSelectionMixin.md)
- , [SwipeDirectionMixin](../basic-component-mixins/docs/SwipeDirectionMixin.md)
- , [TrackpadDirectionMixin](../basic-component-mixins/docs/TrackpadDirectionMixin.md)
+**Extends:** SlidingViewport
+**Mixes**: [HorizontalNavigationMixin](../basic-component-mixins/docs/HorizontalNavigationMixin.md)
-
-* [SlidingCarousel](#SlidingCarousel) ⇐ ElementBase
- * [.canSelectNext](#SingleSelection+canSelectNext) : boolean
- * [.canSelectPrevious](#SingleSelection+canSelectPrevious) : boolean
- * [.content](#DistributedChildrenContent+content) : Array.<HTMLElement>
- * ["content-changed"](#DistributedChildrenContent.event_content-changed)
- * [.contentChanged()](#DistributedChildrenContent+contentChanged)
- * [.generic](#Generic+generic) : Boolean
- * [.goDown()](#KeyboardDirection+symbols.goDown)
- * [.goEnd()](#KeyboardDirection+symbols.goEnd)
- * [.goLeft()](#TrackpadDirection+symbols.goLeft)
- * [.goLeft()](#SwipeDirection+symbols.goLeft)
- * [.goLeft()](#KeyboardDirection+symbols.goLeft)
- * [.goRight()](#SwipeDirection+symbols.goRight)
- * [.goRight()](#TrackpadDirection+symbols.goRight)
- * [.goRight()](#KeyboardDirection+symbols.goRight)
- * [.goStart()](#KeyboardDirection+symbols.goStart)
- * [.goUp()](#KeyboardDirection+symbols.goUp)
- * [.itemAdded(item)](#ContentItems+symbols.itemAdded)
- * [.itemAdded(item)](#SingleSelection+symbols.itemAdded)
- * [.items](#ContentItems+items) : Array.<HTMLElement>
- * ["items-changed"](#ContentItems.event_items-changed)
- * [.itemsChanged()](#ContentItems+symbols.itemsChanged)
- * [.itemSelected(item, selected)](#SingleSelection+symbols.itemSelected)
- * [.itemSelected(item, selected)](#ContentItems+symbols.itemSelected)
- * [.keydown(event)](#Keyboard+symbols.keydown) ⇒ boolean
- * [.navigationAxis](#KeyboardDirection+navigationAxis) : string
- * ["selected-index-changed"](#SingleSelection.event_selected-index-changed)
- * ["selected-item-changed"](#SingleSelection.event_selected-item-changed)
- * [.selectedIndex](#SingleSelection+selectedIndex) : number
- * [.selectedItem](#SingleSelection+selectedItem) : object
- * [.selectFirst()](#SingleSelection+selectFirst)
- * [.selectionRequired](#SingleSelection+selectionRequired) : boolean
- * [.selectionWraps](#SingleSelection+selectionWraps) : boolean
- * [.selectLast()](#SingleSelection+selectLast)
- * [.selectNext()](#SingleSelection+selectNext)
- * [.selectPrevious()](#SingleSelection+selectPrevious)
- * [.travelFraction](#SwipeDirection+travelFraction) : number
- * [.travelFraction](#TrackpadDirection+travelFraction) : number
-
-
-
-### slidingCarousel.canSelectNext : boolean
-True if the selection can be moved to the next item, false if not (the
-selected item is the last item in the list).
-
- **Kind**: instance property of [SlidingCarousel](#SlidingCarousel). Defined by [SingleSelection](../basic-component-mixins/docs/SingleSelection.md) mixin.
-
-
-### slidingCarousel.canSelectPrevious : boolean
-True if the selection can be moved to the previous item, false if not
-(the selected item is the first one in the list).
-
- **Kind**: instance property of [SlidingCarousel](#SlidingCarousel). Defined by [SingleSelection](../basic-component-mixins/docs/SingleSelection.md) mixin.
-
-
-### slidingCarousel.content : Array.<HTMLElement>
-The content of this component, defined to be the flattened array of
-children distributed to the component.
-
- **Kind**: instance property of [SlidingCarousel](#SlidingCarousel). Defined by [DistributedChildrenContent](../basic-component-mixins/docs/DistributedChildrenContent.md) mixin.
-
-
-### "content-changed"
-This event is raised when the component's contents (including distributed
-children) have changed.
-
- **Kind**: event emitted by [SlidingCarousel](#SlidingCarousel). Defined by [DistributedChildrenContent](../basic-component-mixins/docs/DistributedChildrenContent.md) mixin.
-
-
-### slidingCarousel.contentChanged()
-Invoked when the contents of the component (including distributed
-children) have changed.
-
-This method is also invoked when a component is first instantiated; the
-contents have essentially "changed" from being nothing. This allows the
-component to perform initial processing of its children.
-
- **Kind**: instance method of [SlidingCarousel](#SlidingCarousel). Defined by [DistributedChildrenContent](../basic-component-mixins/docs/DistributedChildrenContent.md) mixin.
-
-
-### slidingCarousel.generic : Boolean
-True if the component would like to receive generic styling.
-
-This property is true by default — set it to false to turn off all
-generic styles. This makes it easier to apply custom styling; you won't
-have to explicitly override styling you don't want.
-
- **Kind**: instance property of [SlidingCarousel](#SlidingCarousel). Defined by [Generic](../basic-component-mixins/docs/Generic.md) mixin.
-**Default**: true
-
-
-### SlidingCarousel.goDown()
-Invoked when the user wants to go/navigate down.
-The default implementation of this method does nothing.
-
- **Kind**: static method of [SlidingCarousel](#SlidingCarousel). Defined by [KeyboardDirection#symbols](../basic-component-mixins/docs/KeyboardDirection#symbols.md) mixin.
-
-
-### SlidingCarousel.goEnd()
-Invoked when the user wants to go/navigate to the end (e.g., of a list).
-The default implementation of this method does nothing.
-
- **Kind**: static method of [SlidingCarousel](#SlidingCarousel). Defined by [KeyboardDirection#symbols](../basic-component-mixins/docs/KeyboardDirection#symbols.md) mixin.
-
-
-### SlidingCarousel.goLeft()
-Invoked when the user wants to go/navigate left.
-The default implementation of this method does nothing.
-
- **Kind**: static method of [SlidingCarousel](#SlidingCarousel). Defined by [TrackpadDirection#symbols](../basic-component-mixins/docs/TrackpadDirection#symbols.md) mixin.
-
-
-### SlidingCarousel.goLeft()
-Invoked when the user wants to go/navigate left.
-The default implementation of this method does nothing.
-
- **Kind**: static method of [SlidingCarousel](#SlidingCarousel). Defined by [SwipeDirection#symbols](../basic-component-mixins/docs/SwipeDirection#symbols.md) mixin.
-
-
-### SlidingCarousel.goLeft()
-Invoked when the user wants to go/navigate left.
-The default implementation of this method does nothing.
-
- **Kind**: static method of [SlidingCarousel](#SlidingCarousel). Defined by [KeyboardDirection#symbols](../basic-component-mixins/docs/KeyboardDirection#symbols.md) mixin.
-
-
-### SlidingCarousel.goRight()
-Invoked when the user wants to go/navigate right.
-The default implementation of this method does nothing.
-
- **Kind**: static method of [SlidingCarousel](#SlidingCarousel). Defined by [SwipeDirection#symbols](../basic-component-mixins/docs/SwipeDirection#symbols.md) mixin.
-
-
-### SlidingCarousel.goRight()
-Invoked when the user wants to go/navigate right.
-The default implementation of this method does nothing.
-
- **Kind**: static method of [SlidingCarousel](#SlidingCarousel). Defined by [TrackpadDirection#symbols](../basic-component-mixins/docs/TrackpadDirection#symbols.md) mixin.
-
-
-### SlidingCarousel.goRight()
-Invoked when the user wants to go/navigate right.
-The default implementation of this method does nothing.
-
- **Kind**: static method of [SlidingCarousel](#SlidingCarousel). Defined by [KeyboardDirection#symbols](../basic-component-mixins/docs/KeyboardDirection#symbols.md) mixin.
-
-
-### SlidingCarousel.goStart()
-Invoked when the user wants to go/navigate to the start (e.g., of a
-list). The default implementation of this method does nothing.
-
- **Kind**: static method of [SlidingCarousel](#SlidingCarousel). Defined by [KeyboardDirection#symbols](../basic-component-mixins/docs/KeyboardDirection#symbols.md) mixin.
-
-
-### SlidingCarousel.goUp()
-Invoked when the user wants to go/navigate up.
-The default implementation of this method does nothing.
-
- **Kind**: static method of [SlidingCarousel](#SlidingCarousel). Defined by [KeyboardDirection#symbols](../basic-component-mixins/docs/KeyboardDirection#symbols.md) mixin.
-
-
-### SlidingCarousel.itemAdded(item)
-This method is invoked whenever a new item is added to the list.
-
-The default implementation of this method does nothing. You can override
-this to perform per-item initialization.
-
- **Kind**: static method of [SlidingCarousel](#SlidingCarousel). Defined by [ContentItems#symbols](../basic-component-mixins/docs/ContentItems#symbols.md) mixin.
-
-| Param | Type | Description |
-| --- | --- | --- |
-| item | HTMLElement | The item that was added. |
-
-
-
-### SlidingCarousel.itemAdded(item)
-Handle a new item being added to the list.
-
-The default implementation of this method simply sets the item's
-selection state to false.
-
- **Kind**: static method of [SlidingCarousel](#SlidingCarousel). Defined by [SingleSelection#symbols](../basic-component-mixins/docs/SingleSelection#symbols.md) mixin.
-
-| Param | Type | Description |
-| --- | --- | --- |
-| item | HTMLElement | the item being added |
-
-
-
-### slidingCarousel.items : Array.<HTMLElement>
-The current set of items in the list. See the top-level documentation for
-mixin for a description of how items differ from plain content.
-
- **Kind**: instance property of [SlidingCarousel](#SlidingCarousel). Defined by [ContentItems](../basic-component-mixins/docs/ContentItems.md) mixin.
-
-
-### "items-changed"
-Fires when the items in the list change.
-
- **Kind**: event emitted by [SlidingCarousel](#SlidingCarousel). Defined by [ContentItems](../basic-component-mixins/docs/ContentItems.md) mixin.
-
-
-### SlidingCarousel.itemsChanged()
-This method is invoked when the underlying contents change. It is also
-invoked on component initialization – since the items have "changed" from
-being nothing.
-
- **Kind**: static method of [SlidingCarousel](#SlidingCarousel). Defined by [ContentItems#symbols](../basic-component-mixins/docs/ContentItems#symbols.md) mixin.
-
-
-### SlidingCarousel.itemSelected(item, selected)
-Apply the indicate selection state to the item.
-
-The default implementation of this method does nothing. User-visible
-effects will typically be handled by other mixins.
-
- **Kind**: static method of [SlidingCarousel](#SlidingCarousel). Defined by [SingleSelection#symbols](../basic-component-mixins/docs/SingleSelection#symbols.md) mixin.
-
-| Param | Type | Description |
-| --- | --- | --- |
-| item | HTMLElement | the item being selected/deselected |
-| selected | boolean | true if the item is selected, false if not |
-
-
-
-### SlidingCarousel.itemSelected(item, selected)
-The selection state for a single item has changed.
-
-Invoke this method to signal that the selected state of the indicated item
-has changed. By default, this applies a `selected` CSS class if the item
-is selected, and removed it if not selected.
-
- **Kind**: static method of [SlidingCarousel](#SlidingCarousel). Defined by [ContentItems#symbols](../basic-component-mixins/docs/ContentItems#symbols.md) mixin.
-
-| Param | Type | Description |
-| --- | --- | --- |
-| item | HTMLElement | The item whose selection state has changed. |
-| selected | boolean | True if the item is selected, false if not. |
-
-
-
-### SlidingCarousel.keydown(event) ⇒ boolean
-Handle the indicated keyboard event.
-
-The default implementation of this method does nothing. This will
-typically be handled by other mixins.
-
- **Kind**: static method of [SlidingCarousel](#SlidingCarousel). Defined by [Keyboard#symbols](../basic-component-mixins/docs/Keyboard#symbols.md) mixin.
-**Returns**: boolean - true if the event was handled
-
-| Param | Type | Description |
-| --- | --- | --- |
-| event | KeyboardEvent | the keyboard event |
-
-
-
-### slidingCarousel.navigationAxis : string
-Indicates the direction of permitted navigation with the keyboard.
-
-Accepted values are "horizontal", "vertical", or "both" (the default).
-If this property is "horizontal", the Up Arrow and Down Arrow keys will
-be ignored. Conversely, if this is "vertical", the Left Arrow and Right
-Arrow keys will be ignored.
-
- **Kind**: instance property of [SlidingCarousel](#SlidingCarousel). Defined by [KeyboardDirection](../basic-component-mixins/docs/KeyboardDirection.md) mixin.
-
-
-### "selected-index-changed"
-Fires when the selectedIndex property changes.
-
- **Kind**: event emitted by [SlidingCarousel](#SlidingCarousel). Defined by [SingleSelection](../basic-component-mixins/docs/SingleSelection.md) mixin.
-
-| Param | Type | Description |
-| --- | --- | --- |
-| detail.selectedIndex | number | The new selected index. |
-
-
-
-### "selected-item-changed"
-Fires when the selectedItem property changes.
-
- **Kind**: event emitted by [SlidingCarousel](#SlidingCarousel). Defined by [SingleSelection](../basic-component-mixins/docs/SingleSelection.md) mixin.
-
-| Param | Type | Description |
-| --- | --- | --- |
-| detail.selectedItem | HTMLElement | The new selected item. |
-| detail.previousItem | HTMLElement | The previously selected item. |
-
-
-
-### slidingCarousel.selectedIndex : number
-The index of the item which is currently selected.
-
-A `selectedIndex` of -1 indicates there is no selection. Setting this
-property to -1 will remove any existing selection.
-
- **Kind**: instance property of [SlidingCarousel](#SlidingCarousel). Defined by [SingleSelection](../basic-component-mixins/docs/SingleSelection.md) mixin.
-
-
-### slidingCarousel.selectedItem : object
-The currently selected item, or null if there is no selection.
-
-Setting this property to null deselects any currently-selected item.
-Setting this property to an object that is not in the list has no effect.
-
-TODO: Even if selectionRequired, can still explicitly set selectedItem to null.
-TODO: If selectionRequired, leave selection alone?
-
- **Kind**: instance property of [SlidingCarousel](#SlidingCarousel). Defined by [SingleSelection](../basic-component-mixins/docs/SingleSelection.md) mixin.
-
-
-### slidingCarousel.selectFirst()
-Select the first item in the list.
-
- **Kind**: instance method of [SlidingCarousel](#SlidingCarousel). Defined by [SingleSelection](../basic-component-mixins/docs/SingleSelection.md) mixin.
-
-
-### slidingCarousel.selectionRequired : boolean
-True if the list should always have a selection (if it has items).
-
- **Kind**: instance property of [SlidingCarousel](#SlidingCarousel). Defined by [SingleSelection](../basic-component-mixins/docs/SingleSelection.md) mixin.
-**Default**: false
-
-
-### slidingCarousel.selectionWraps : boolean
-True if selection navigations wrap from last to first, and vice versa.
-
- **Kind**: instance property of [SlidingCarousel](#SlidingCarousel). Defined by [SingleSelection](../basic-component-mixins/docs/SingleSelection.md) mixin.
-**Default**: false
-
-
-### slidingCarousel.selectLast()
-Select the last item in the list.
-
- **Kind**: instance method of [SlidingCarousel](#SlidingCarousel). Defined by [SingleSelection](../basic-component-mixins/docs/SingleSelection.md) mixin.
-
-
-### slidingCarousel.selectNext()
-Select the next item in the list.
-
- **Kind**: instance method of [SlidingCarousel](#SlidingCarousel). Defined by [SingleSelection](../basic-component-mixins/docs/SingleSelection.md) mixin.
-
-
-### slidingCarousel.selectPrevious()
-Select the previous item in the list.
-
-If the list has no selection, the last item will be selected.
-
- **Kind**: instance method of [SlidingCarousel](#SlidingCarousel). Defined by [SingleSelection](../basic-component-mixins/docs/SingleSelection.md) mixin.
-
-
-### slidingCarousel.travelFraction : number
-The distance the first touchpoint has traveled since the beginning of a
-drag, expressed as a fraction of the element's width.
-
- **Kind**: instance property of [SlidingCarousel](#SlidingCarousel). Defined by [SwipeDirection](../basic-component-mixins/docs/SwipeDirection.md) mixin.
-
-
-### slidingCarousel.travelFraction : number
-The distance the user has moved the first touchpoint since the beginning
-of a trackpad/wheel operation, expressed as a fraction of the element's
-width.
-
- **Kind**: instance property of [SlidingCarousel](#SlidingCarousel). Defined by [TrackpadDirection](../basic-component-mixins/docs/TrackpadDirection.md) mixin.
diff --git a/packages/basic-sliding-carousel/dist/basic-sliding-carousel.js b/packages/basic-sliding-carousel/dist/basic-sliding-carousel.js
index 1fa59489..98520e08 100644
--- a/packages/basic-sliding-carousel/dist/basic-sliding-carousel.js
+++ b/packages/basic-sliding-carousel/dist/basic-sliding-carousel.js
@@ -1,4103 +1,3 @@
-(function e(t,n,r){function s(o,u){if(!n[o]){if(!t[o]){var a=typeof require=="function"&&require;if(!u&&a)return a(o,!0);if(i)return i(o,!0);var f=new Error("Cannot find module '"+o+"'");throw f.code="MODULE_NOT_FOUND",f}var l=n[o]={exports:{}};t[o][0].call(l.exports,function(e){var n=t[o][1][e];return s(n?n:e)},l,l.exports,e,t,n,r)}return n[o].exports}var i=typeof require=="function"&&require;for(var o=0;o
- *
- * Then, after the element has been upgraded, the `fooBar` setter will
- * automatically be invoked with the initial value "Hello".
- *
- * For the time being, this mixin only supports string-valued properties.
- * If you'd like to convert string attributes to other types (numbers,
- * booleans), you need to implement `attributeChangedCallback` yourself.
- */
- var AttributeMarshalling = function (_base) {
- _inherits(AttributeMarshalling, _base);
-
- function AttributeMarshalling() {
- _classCallCheck(this, AttributeMarshalling);
-
- return _possibleConstructorReturn(this, (AttributeMarshalling.__proto__ || Object.getPrototypeOf(AttributeMarshalling)).apply(this, arguments));
- }
-
- _createClass(AttributeMarshalling, [{
- key: 'attributeChangedCallback',
-
-
- /*
- * Handle a change to the attribute with the given name.
- */
- value: function attributeChangedCallback(attributeName, oldValue, newValue) {
- if (_get(AttributeMarshalling.prototype.__proto__ || Object.getPrototypeOf(AttributeMarshalling.prototype), 'attributeChangedCallback', this)) {
- _get(AttributeMarshalling.prototype.__proto__ || Object.getPrototypeOf(AttributeMarshalling.prototype), 'attributeChangedCallback', this).call(this);
- }
- var propertyName = attributeToPropertyName(attributeName);
- // If the attribute name corresponds to a property name, set the property.
- // Ignore standard HTMLElement properties handled by the DOM.
- if (propertyName in this && !(propertyName in HTMLElement.prototype)) {
- this[propertyName] = newValue;
- }
- }
- }, {
- key: 'connectedCallback',
- value: function connectedCallback() {
- if (_get(AttributeMarshalling.prototype.__proto__ || Object.getPrototypeOf(AttributeMarshalling.prototype), 'connectedCallback', this)) {
- _get(AttributeMarshalling.prototype.__proto__ || Object.getPrototypeOf(AttributeMarshalling.prototype), 'connectedCallback', this).call(this);
- }
- _safeAttributes2.default.connected(this);
- }
- }, {
- key: 'reflectAttribute',
-
-
- /**
- * Set/unset the attribute with the indicated name.
- *
- * This method exists primarily to handle the case where an element wants to
- * set a default property value that should be reflected as an attribute. An
- * important limitation of custom element consturctors is that they cannot
- * set attributes. A call to `reflectAttribute` during the constructor will
- * be deferred until the element is connected to the document.
- *
- * @param {string} attribute - The name of the *attribute* (not property) to set.
- * @param {object} value - The value to set. If null, the attribute will be removed.
- */
- value: function reflectAttribute(attribute, value) {
- return _safeAttributes2.default.setAttribute(this, attribute, value);
- }
-
- /**
- * Set/unset the class with the indicated name.
- *
- * This method exists primarily to handle the case where an element wants to
- * set a default property value that should be reflected as as class. An
- * important limitation of custom element consturctors is that they cannot
- * set attributes, including the `class` attribute. A call to
- * `reflectClass` during the constructor will be deferred until the element
- * is connected to the document.
- *
- * @param {string} className - The name of the class to set.
- * @param {object} value - True to set the class, false to remove it.
- */
-
- }, {
- key: 'reflectClass',
- value: function reflectClass(className, value) {
- return _safeAttributes2.default.toggleClass(this, className, value);
- }
- }], [{
- key: 'observedAttributes',
- get: function get() {
- return attributesForClass(this);
- }
- }]);
-
- return AttributeMarshalling;
- }(base);
-
- return AttributeMarshalling;
-};
-
-// Convert hyphenated foo-bar attribute name to camel case fooBar property name.
-
-
-function attributeToPropertyName(attributeName) {
- var propertyName = attributeToPropertyNames[attributeName];
- if (!propertyName) {
- // Convert and memoize.
- var hypenRegEx = /-([a-z])/g;
- propertyName = attributeName.replace(hypenRegEx, function (match) {
- return match[1].toUpperCase();
- });
- attributeToPropertyNames[attributeName] = propertyName;
- }
- return propertyName;
-}
-
-function attributesForClass(classFn) {
-
- // We treat the element base classes as if they have no attributes, since we
- // don't want to receive attributeChangedCallback for them.
- if (classFn === HTMLElement || classFn === Object) {
- return [];
- }
-
- // Get attributes for parent class.
- var baseClass = Object.getPrototypeOf(classFn.prototype).constructor;
- var baseAttributes = attributesForClass(baseClass);
-
- // Get attributes for this class.
- var propertyNames = Object.getOwnPropertyNames(classFn.prototype);
- var setterNames = propertyNames.filter(function (propertyName) {
- return typeof Object.getOwnPropertyDescriptor(classFn.prototype, propertyName).set === 'function';
- });
- var attributes = setterNames.map(function (setterName) {
- return propertyNameToAttribute(setterName);
- });
-
- // Merge.
- var diff = attributes.filter(function (attribute) {
- return baseAttributes.indexOf(attribute) < 0;
- });
- return baseAttributes.concat(diff);
-}
-
-// Convert a camel case fooBar property name to a hyphenated foo-bar attribute.
-function propertyNameToAttribute(propertyName) {
- var attribute = propertyNamesToAttributes[propertyName];
- if (!attribute) {
- // Convert and memoize.
- var uppercaseRegEx = /([A-Z])/g;
- attribute = propertyName.replace(uppercaseRegEx, '-$1').toLowerCase();
- }
- return attribute;
-}
-
-},{"./safeAttributes":18}],2:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-/* Exported function extends a base class with Composable. */
-exports.default = function (base) {
-
- /**
- * Mixin to make a class more easily composable with other mixins.
- *
- * This mixin contributes a `compose` method that applies a set of mixin
- * functions and returns the resulting new class. This sugar can make the
- * application of many mixins at once easier to read.
- */
- var Composable = function (_base) {
- _inherits(Composable, _base);
-
- function Composable() {
- _classCallCheck(this, Composable);
-
- return _possibleConstructorReturn(this, (Composable.__proto__ || Object.getPrototypeOf(Composable)).apply(this, arguments));
- }
-
- _createClass(Composable, null, [{
- key: 'compose',
-
-
- /**
- * Apply a set of mixin functions or mixin objects to the present class and
- * return the new class.
- *
- * Instead of writing:
- *
- * let MyClass = Mixin1(Mixin2(Mixin3(Mixin4(Mixin5(BaseClass)))));
- *
- * You can write:
- *
- * let MyClass = ComposableMixin(BaseClass).compose(
- * Mixin1,
- * Mixin2,
- * Mixin3,
- * Mixin4,
- * Mixin5
- * );
- *
- * This function can also take mixin objects. A mixin object is just a
- * shorthand for a mixin function that creates a new subclass with the given
- * members. The mixin object's members are *not* copied directly onto the
- * prototype of the base class, as with traditional mixins.
- *
- * In addition to providing syntactic sugar, this mixin can be used to
- * define a class in ES5, which lacks ES6's `class` keyword.
- *
- * @param {...mixins} mixins - A set of mixin functions or objects to apply.
- */
- value: function compose() {
- for (var _len = arguments.length, mixins = Array(_len), _key = 0; _key < _len; _key++) {
- mixins[_key] = arguments[_key];
- }
-
- // We create a new subclass for each mixin in turn. The result becomes
- // the base class extended by any subsequent mixins. It turns out that
- // we can use Array.reduce() to concisely express this, using the current
- // object as the seed for reduce().
- return mixins.reduce(composeClass, this);
- }
- }]);
-
- return Composable;
- }(base);
-
- return Composable;
-};
-
-// Properties defined by Object that we don't want to mixin.
-
-
-var NON_MIXABLE_OBJECT_PROPERTIES = ['constructor'];
-
-/*
- * Apply the mixin to the given base class to return a new class.
- * The mixin can either be a function that returns the modified class, or a
- * plain object whose members will be copied to the new class' prototype.
- */
-function composeClass(base, mixin) {
- if (typeof mixin === 'function') {
- // Mixin function
- return mixin(base);
- } else {
- // Mixin object
- var Subclass = function (_base2) {
- _inherits(Subclass, _base2);
-
- function Subclass() {
- _classCallCheck(this, Subclass);
-
- return _possibleConstructorReturn(this, (Subclass.__proto__ || Object.getPrototypeOf(Subclass)).apply(this, arguments));
- }
-
- return Subclass;
- }(base);
-
- copyOwnProperties(mixin, Subclass.prototype, NON_MIXABLE_OBJECT_PROPERTIES);
- return Subclass;
- }
-}
-
-/*
- * Copy the given properties/methods to the target.
- * Return the updated target.
- */
-function copyOwnProperties(source, target) {
- var ignorePropertyNames = arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : [];
-
- Object.getOwnPropertyNames(source).forEach(function (name) {
- if (ignorePropertyNames.indexOf(name) < 0) {
- var descriptor = Object.getOwnPropertyDescriptor(source, name);
- Object.defineProperty(target, name, descriptor);
- }
- });
- return target;
-}
-
-},{}],3:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
-
-var _get = function get(object, property, receiver) { if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { return get(parent, property, receiver); } } else if ("value" in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } };
-
-var _createSymbol = require('./createSymbol');
-
-var _createSymbol2 = _interopRequireDefault(_createSymbol);
-
-var _toggleClass = require('./toggleClass');
-
-var _toggleClass2 = _interopRequireDefault(_toggleClass);
-
-var _symbols = require('./symbols');
-
-var _symbols2 = _interopRequireDefault(_symbols);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-// Symbols for private data members on an element.
-var itemsSymbol = (0, _createSymbol2.default)('items');
-var itemInitializedSymbol = (0, _createSymbol2.default)('itemInitialized');
-
-/* Exported function extends a base class with ContentItems. */
-
-exports.default = function (base) {
-
- /**
- * Mixin which maps content semantics (elements) to list item semantics.
- *
- * Items differ from element contents in several ways:
- *
- * * They are often referenced via index.
- * * They may have a selection state.
- * * It's common to do work to initialize the appearance or state of a new
- * item.
- * * Auxiliary invisible child elements are filtered out and not counted as
- * items. Auxiliary elements include link, script, style, and template
- * elements. This filtering ensures that those auxiliary elements can be
- * used in markup inside of a list without being treated as list items.
- *
- * This mixin expects a component to provide a `content` property returning a
- * raw set of elements. You can provide that yourself, or use
- * [DistributedChildrenContentMixin](DistributedChildrenContentMixin.md).
- *
- * The most commonly referenced property defined by this mixin is the `items`
- * property. To avoid having to do work each time that property is requested,
- * this mixin supports an optimized mode. If you invoke the `contentChanged`
- * method when the set of items changes, the mixin concludes that you'll take
- * care of notifying it of future changes, and turns on the optimization. With
- * that on, the mixin saves a reference to the computed set of items, and will
- * return that immediately on subsequent calls to the `items` property. If you
- * use this mixin in conjunction with
- * [DistributedChildrenContentMixin](DistributedChildrenContentMixin.md), the
- * `contentChanged` method will be invoked for you when the element's children
- * change, turning on the optimization automatically.
- */
- var ContentItems = function (_base) {
- _inherits(ContentItems, _base);
-
- function ContentItems() {
- _classCallCheck(this, ContentItems);
-
- return _possibleConstructorReturn(this, (ContentItems.__proto__ || Object.getPrototypeOf(ContentItems)).apply(this, arguments));
- }
-
- _createClass(ContentItems, [{
- key: 'contentChanged',
- value: function contentChanged() {
- if (_get(ContentItems.prototype.__proto__ || Object.getPrototypeOf(ContentItems.prototype), 'contentChanged', this)) {
- _get(ContentItems.prototype.__proto__ || Object.getPrototypeOf(ContentItems.prototype), 'contentChanged', this).call(this);
- }
-
- // Since we got the contentChanged call, we'll assume we'll be notified if
- // the set of items changes later. We turn on memoization of the items
- // property by setting our internal property to null (instead of
- // undefined).
- this[itemsSymbol] = null;
-
- this[_symbols2.default.itemsChanged]();
- }
-
- /**
- * This method is invoked whenever a new item is added to the list.
- *
- * The default implementation of this method does nothing. You can override
- * this to perform per-item initialization.
- *
- * @param {HTMLElement} item - The item that was added.
- */
-
- }, {
- key: _symbols2.default.itemAdded,
- value: function value(item) {
- if (_get(ContentItems.prototype.__proto__ || Object.getPrototypeOf(ContentItems.prototype), _symbols2.default.itemAdded, this)) {
- _get(ContentItems.prototype.__proto__ || Object.getPrototypeOf(ContentItems.prototype), _symbols2.default.itemAdded, this).call(this, item);
- }
- }
-
- /**
- * The selection state for a single item has changed.
- *
- * Invoke this method to signal that the selected state of the indicated item
- * has changed. By default, this applies a `selected` CSS class if the item
- * is selected, and removed it if not selected.
- *
- * @param {HTMLElement} item - The item whose selection state has changed.
- * @param {boolean} selected - True if the item is selected, false if not.
- */
-
- }, {
- key: _symbols2.default.itemSelected,
- value: function value(item, selected) {
- if (_get(ContentItems.prototype.__proto__ || Object.getPrototypeOf(ContentItems.prototype), _symbols2.default.itemSelected, this)) {
- _get(ContentItems.prototype.__proto__ || Object.getPrototypeOf(ContentItems.prototype), _symbols2.default.itemSelected, this).call(this, item, selected);
- }
- (0, _toggleClass2.default)(item, 'selected', selected);
- }
-
- /**
- * The current set of items in the list. See the top-level documentation for
- * mixin for a description of how items differ from plain content.
- *
- * @type {HTMLElement[]}
- */
-
- }, {
- key: _symbols2.default.itemsChanged,
-
-
- /**
- * This method is invoked when the underlying contents change. It is also
- * invoked on component initialization – since the items have "changed" from
- * being nothing.
- */
- value: function value() {
- var _this2 = this;
-
- if (_get(ContentItems.prototype.__proto__ || Object.getPrototypeOf(ContentItems.prototype), _symbols2.default.itemsChanged, this)) {
- _get(ContentItems.prototype.__proto__ || Object.getPrototypeOf(ContentItems.prototype), _symbols2.default.itemsChanged, this).call(this);
- }
-
- // Perform per-item initialization.
- Array.prototype.forEach.call(this.items, function (item) {
- if (!item[itemInitializedSymbol]) {
- _this2[_symbols2.default.itemAdded](item);
- item[itemInitializedSymbol] = true;
- }
- });
-
- this.dispatchEvent(new CustomEvent('items-changed'));
- }
-
- /**
- * Fires when the items in the list change.
- *
- * @memberof ContentItems
- * @event items-changed
- */
-
- }, {
- key: 'items',
- get: function get() {
- var items = void 0;
- if (this[itemsSymbol] == null) {
- items = filterAuxiliaryElements(this.content);
- // Note: test for *equality* with null; don't treat undefined as a match.
- if (this[itemsSymbol] === null) {
- // Memoize the set of items.
- this[itemsSymbol] = items;
- }
- } else {
- // Return the memoized items.
- items = this[itemsSymbol];
- }
- return items;
- }
- }]);
-
- return ContentItems;
- }(base);
-
- return ContentItems;
-};
-
-// Return the given elements, filtering out auxiliary elements that aren't
-// typically visible. Items which are not elements are returned as is.
-
-
-function filterAuxiliaryElements(items) {
- var auxiliaryTags = ['link', 'script', 'style', 'template'];
- return [].filter.call(items, function (item) {
- return !item.localName || auxiliaryTags.indexOf(item.localName) < 0;
- });
-}
-
-},{"./createSymbol":16,"./symbols":19,"./toggleClass":20}],4:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
-
-var _set = function set(object, property, value, receiver) { var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent !== null) { set(parent, property, value, receiver); } } else if ("value" in desc && desc.writable) { desc.value = value; } else { var setter = desc.set; if (setter !== undefined) { setter.call(receiver, value); } } return value; };
-
-var _get = function get(object, property, receiver) { if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { return get(parent, property, receiver); } } else if ("value" in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } };
-
-var _symbols = require('./symbols');
-
-var _symbols2 = _interopRequireDefault(_symbols);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-/* Exported function extends a base class with DirectionSelection. */
-exports.default = function (base) {
-
- /**
- * Mixin which maps direction semantics (goLeft, goRight, etc.) to selection
- * semantics (selectPrevious, selectNext, etc.).
- *
- * This mixin can be used in conjunction with
- * [KeyboardDirectionMixin](KeyboardDirectionMixin.md) (which maps keyboard
- * events to directions) and a mixin that handles selection like
- * [SingleSelectionMixin](SingleSelectionMixin.md).
- */
- var DirectionSelection = function (_base) {
- _inherits(DirectionSelection, _base);
-
- function DirectionSelection() {
- _classCallCheck(this, DirectionSelection);
-
- return _possibleConstructorReturn(this, (DirectionSelection.__proto__ || Object.getPrototypeOf(DirectionSelection)).apply(this, arguments));
- }
-
- _createClass(DirectionSelection, [{
- key: _symbols2.default.goDown,
- value: function value() {
- if (_get(DirectionSelection.prototype.__proto__ || Object.getPrototypeOf(DirectionSelection.prototype), _symbols2.default.goDown, this)) {
- _get(DirectionSelection.prototype.__proto__ || Object.getPrototypeOf(DirectionSelection.prototype), _symbols2.default.goDown, this).call(this);
- }
- return this.selectNext();
- }
- }, {
- key: _symbols2.default.goEnd,
- value: function value() {
- if (_get(DirectionSelection.prototype.__proto__ || Object.getPrototypeOf(DirectionSelection.prototype), _symbols2.default.goEnd, this)) {
- _get(DirectionSelection.prototype.__proto__ || Object.getPrototypeOf(DirectionSelection.prototype), _symbols2.default.goEnd, this).call(this);
- }
- return this.selectLast();
- }
- }, {
- key: _symbols2.default.goLeft,
- value: function value() {
- if (_get(DirectionSelection.prototype.__proto__ || Object.getPrototypeOf(DirectionSelection.prototype), _symbols2.default.goLeft, this)) {
- _get(DirectionSelection.prototype.__proto__ || Object.getPrototypeOf(DirectionSelection.prototype), _symbols2.default.goLeft, this).call(this);
- }
- return this.selectPrevious();
- }
- }, {
- key: _symbols2.default.goRight,
- value: function value() {
- if (_get(DirectionSelection.prototype.__proto__ || Object.getPrototypeOf(DirectionSelection.prototype), _symbols2.default.goRight, this)) {
- _get(DirectionSelection.prototype.__proto__ || Object.getPrototypeOf(DirectionSelection.prototype), _symbols2.default.goRight, this).call(this);
- }
- return this.selectNext();
- }
- }, {
- key: _symbols2.default.goStart,
- value: function value() {
- if (_get(DirectionSelection.prototype.__proto__ || Object.getPrototypeOf(DirectionSelection.prototype), _symbols2.default.goStart, this)) {
- _get(DirectionSelection.prototype.__proto__ || Object.getPrototypeOf(DirectionSelection.prototype), _symbols2.default.goStart, this).call(this);
- }
- return this.selectFirst();
- }
- }, {
- key: _symbols2.default.goUp,
- value: function value() {
- if (_get(DirectionSelection.prototype.__proto__ || Object.getPrototypeOf(DirectionSelection.prototype), _symbols2.default.goUp, this)) {
- _get(DirectionSelection.prototype.__proto__ || Object.getPrototypeOf(DirectionSelection.prototype), _symbols2.default.goUp, this).call(this);
- }
- return this.selectPrevious();
- }
-
- // Default implementation. This will typically be handled by other mixins.
-
- }, {
- key: 'selectFirst',
-
-
- // Default implementation. This will typically be handled by other mixins.
- value: function selectFirst() {
- if (_get(DirectionSelection.prototype.__proto__ || Object.getPrototypeOf(DirectionSelection.prototype), 'selectFirst', this)) {
- return _get(DirectionSelection.prototype.__proto__ || Object.getPrototypeOf(DirectionSelection.prototype), 'selectFirst', this).call(this);
- }
- }
-
- // Default implementation. This will typically be handled by other mixins.
-
- }, {
- key: 'selectLast',
- value: function selectLast() {
- if (_get(DirectionSelection.prototype.__proto__ || Object.getPrototypeOf(DirectionSelection.prototype), 'selectLast', this)) {
- return _get(DirectionSelection.prototype.__proto__ || Object.getPrototypeOf(DirectionSelection.prototype), 'selectLast', this).call(this);
- }
- }
-
- // Default implementation. This will typically be handled by other mixins.
-
- }, {
- key: 'selectNext',
- value: function selectNext() {
- if (_get(DirectionSelection.prototype.__proto__ || Object.getPrototypeOf(DirectionSelection.prototype), 'selectNext', this)) {
- return _get(DirectionSelection.prototype.__proto__ || Object.getPrototypeOf(DirectionSelection.prototype), 'selectNext', this).call(this);
- }
- }
-
- // Default implementation. This will typically be handled by other mixins.
-
- }, {
- key: 'selectPrevious',
- value: function selectPrevious() {
- if (_get(DirectionSelection.prototype.__proto__ || Object.getPrototypeOf(DirectionSelection.prototype), 'selectPrevious', this)) {
- return _get(DirectionSelection.prototype.__proto__ || Object.getPrototypeOf(DirectionSelection.prototype), 'selectPrevious', this).call(this);
- }
- }
-
- // Map drag travel fraction to selection fraction.
-
- }, {
- key: 'selectedFraction',
- get: function get() {
- return _get(DirectionSelection.prototype.__proto__ || Object.getPrototypeOf(DirectionSelection.prototype), 'selectedFraction', this);
- },
- set: function set(value) {
- if ('selectedFraction' in base.prototype) {
- _set(DirectionSelection.prototype.__proto__ || Object.getPrototypeOf(DirectionSelection.prototype), 'selectedFraction', value, this);
- }
- }
- }, {
- key: 'travelFraction',
- get: function get() {
- return _get(DirectionSelection.prototype.__proto__ || Object.getPrototypeOf(DirectionSelection.prototype), 'travelFraction', this);
- },
- set: function set(value) {
- if ('travelFraction' in base.prototype) {
- _set(DirectionSelection.prototype.__proto__ || Object.getPrototypeOf(DirectionSelection.prototype), 'travelFraction', value, this);
- }
- this.selectedFraction = value;
- }
- }]);
-
- return DirectionSelection;
- }(base);
-
- return DirectionSelection;
-};
-
-},{"./symbols":19}],5:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
-
-var _set = function set(object, property, value, receiver) { var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent !== null) { set(parent, property, value, receiver); } } else if ("value" in desc && desc.writable) { desc.value = value; } else { var setter = desc.set; if (setter !== undefined) { setter.call(receiver, value); } } return value; };
-
-var _get = function get(object, property, receiver) { if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { return get(parent, property, receiver); } } else if ("value" in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } };
-
-var _microtask = require('./microtask');
-
-var _microtask2 = _interopRequireDefault(_microtask);
-
-function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-/* Exported function extends a base class with DistributedChildrenContent. */
-exports.default = function (base) {
-
- /**
- * Mixin which defines a component's content as its children, expanding any
- * nodes distributed to the component's slots.
- *
- * This also provides notification of changes to a component's content. It
- * will invoke a `contentChanged` method when the component is first
- * instantiated, and whenever its distributed children change. This is an
- * easy way to satisfy the Gold Standard checklist item for monitoring
- * [Content Changes](https://github.com/webcomponents/gold-standard/wiki/Content-Changes).
- *
- * Example:
- *
- * ```
- * let base = DistributedChildrenContentMixin(DistributedChildrenMixin(HTMLElement));
- * class CountingElement extends base {
- *
- * constructor() {
- * super();
- * let root = this.attachShadow({ mode: 'open' });
- * root.innerHTML = ` `;
- * }
- *
- * contentChanged() {
- * // Count the component's children, both initially and when changed.
- * this.count = this.distributedChildren.length;
- * }
- *
- * }
- * ```
- *
- * Note that content change detection depends upon the element having at least
- * one `slot` element in its shadow subtree.
- *
- * This mixin is intended for use with the
- * [DistributedChildrenMixin](DistributedChildrenMixin.md). See that mixin for
- * a discussion of how that works. This DistributedChildrenContentMixin
- * provides an easy way of defining the "content" of a component as the
- * component's distributed children. That in turn lets mixins like
- * [ContentItemsMixin](ContentItemsMixin.md) manipulate the children as list
- * items.
- */
- var DistributedChildrenContent = function (_base) {
- _inherits(DistributedChildrenContent, _base);
-
- function DistributedChildrenContent() {
- _classCallCheck(this, DistributedChildrenContent);
-
- var _this = _possibleConstructorReturn(this, (DistributedChildrenContent.__proto__ || Object.getPrototypeOf(DistributedChildrenContent)).call(this));
-
- if (_this.shadowRoot) {
- // Listen to changes on all slots.
- var slots = _this.shadowRoot.querySelectorAll('slot');
- slots.forEach(function (slot) {
- return slot.addEventListener('slotchange', function (event) {
- _this.contentChanged();
- });
- });
- }
-
- // Make an initial call to contentChanged() so that the component can do
- // initialization that it normally does when content changes.
- //
- // This will invoke contentChanged() handlers in other mixins. In order
- // that those mixins have a chance to complete their own initialization,
- // we add the contentChanged() call to the microtask queue.
- (0, _microtask2.default)(function () {
- return _this.contentChanged();
- });
- return _this;
- }
-
- /**
- * Invoked when the contents of the component (including distributed
- * children) have changed.
- *
- * This method is also invoked when a component is first instantiated; the
- * contents have essentially "changed" from being nothing. This allows the
- * component to perform initial processing of its children.
- */
-
-
- _createClass(DistributedChildrenContent, [{
- key: 'contentChanged',
- value: function contentChanged() {
- if (_get(DistributedChildrenContent.prototype.__proto__ || Object.getPrototypeOf(DistributedChildrenContent.prototype), 'contentChanged', this)) {
- _get(DistributedChildrenContent.prototype.__proto__ || Object.getPrototypeOf(DistributedChildrenContent.prototype), 'contentChanged', this).call(this);
- }
- var event = new CustomEvent('content-changed');
- this.dispatchEvent(event);
- }
-
- /**
- * The content of this component, defined to be the flattened array of
- * children distributed to the component.
- *
- * @type {HTMLElement[]}
- */
-
- }, {
- key: 'content',
- get: function get() {
- var distributedChildren = this.distributedChildren;
- if (typeof distributedChildren === 'undefined') {
- console.warn('DistributedChildrenContentMixin expects the component to define a "distributedChildren" property.');
- }
- return distributedChildren;
- },
- set: function set(value) {
- if ('content' in base.prototype) {
- _set(DistributedChildrenContent.prototype.__proto__ || Object.getPrototypeOf(DistributedChildrenContent.prototype), 'content', value, this);
- }
- // TODO: Set the children to the given value (which should be an array of
- // elements)?
- }
-
- /**
- * This event is raised when the component's contents (including distributed
- * children) have changed.
- *
- * @memberof DistributedChildrenContent
- * @event content-changed
- */
-
- }]);
-
- return DistributedChildrenContent;
- }(base);
-
- return DistributedChildrenContent;
-};
-
-},{"./microtask":17}],6:[function(require,module,exports){
-'use strict';
-
-Object.defineProperty(exports, "__esModule", {
- value: true
-});
-
-var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
-
-function _toConsumableArray(arr) { if (Array.isArray(arr)) { for (var i = 0, arr2 = Array(arr.length); i < arr.length; i++) { arr2[i] = arr[i]; } return arr2; } else { return Array.from(arr); } }
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
-
-function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
-
-/* Exported function extends a base class with DistributedChildren. */
-exports.default = function (base) {
-
- /**
- * Mixin which defines helpers for accessing a component's distributed
- * children as a flattened array or string.
- *
- * The standard DOM API provides several ways of accessing child content:
- * `children`, `childNodes`, and `textContent`. None of these functions are
- * Shadow DOM aware. This mixin defines variations of those functions that
- * *are* Shadow DOM aware.
- *
- * Example: you create a component `` that displays a number
- * equal to the number of children placed inside that component. If someone
- * instantiates your component like:
- *
- *
- *
- *
- *
- *
- *
- * Then the component should show "3", because there are three children. To
- * calculate the number of children, the component can just calculate
- * `this.children.length`. However, suppose someone instantiates your
- * component inside one of their own components, and puts a `` element
- * inside your component:
- *
- *
- *