UNPKG

carbon-components-angular

Version:
165 lines 19.9 kB
import { Component, HostListener, Optional } from "@angular/core"; import { Dialog } from "../dialog.component"; import { position } from "@carbon/utils-position"; import { isFocusInLastItem, isFocusInFirstItem } from "carbon-components-angular/common"; import { CloseReasons } from "../dialog-config.interface"; import { closestAttr } from "carbon-components-angular/utils"; import * as i0 from "@angular/core"; import * as i1 from "carbon-components-angular/i18n"; import * as i2 from "carbon-components-angular/experimental"; import * as i3 from "carbon-components-angular/utils"; import * as i4 from "@angular/common"; /** * Extend the `Dialog` component to create an overflow menu. * * Not used directly. See overflow-menu.component and overflow-menu.directive for more */ export class OverflowMenuPane extends Dialog { constructor(elementRef, i18n, experimental, animationFrameService = null, // mark `elementService` as optional since making it mandatory would be a breaking change elementService = null) { super(elementRef, elementService, animationFrameService); this.elementRef = elementRef; this.i18n = i18n; this.experimental = experimental; this.animationFrameService = animationFrameService; this.elementService = elementService; } onDialogInit() { const positionOverflowMenu = pos => { let offset; /* * 20 is half the width of the overflow menu trigger element. * we also move the element by half of it's own width, since * position service will try and center everything */ const closestRel = closestAttr("position", ["relative", "fixed", "absolute"], this.elementRef.nativeElement); const topFix = closestRel ? closestRel.getBoundingClientRect().top * -1 : 0; const leftFix = closestRel ? closestRel.getBoundingClientRect().left * -1 : 0; offset = Math.round(this.dialog.nativeElement.offsetWidth / 2) - 20; if (this.dialogConfig.flip) { return position.addOffset(pos, topFix, (-offset + leftFix)); } return position.addOffset(pos, topFix, (offset + leftFix)); }; this.addGap["bottom"] = positionOverflowMenu; this.addGap["top"] = positionOverflowMenu; if (!this.dialogConfig.menuLabel) { this.dialogConfig.menuLabel = this.i18n.get().OVERFLOW_MENU.OVERFLOW; } } hostkeys(event) { const listItems = this.listItems(); switch (event.key) { case "ArrowDown": event.preventDefault(); if (!isFocusInLastItem(event, listItems)) { const index = listItems.findIndex(item => item === event.target); listItems[index + 1].focus(); } else { listItems[0].focus(); } break; case "ArrowUp": event.preventDefault(); if (!isFocusInFirstItem(event, listItems)) { const index = listItems.findIndex(item => item === event.target); listItems[index - 1].focus(); } else { listItems[listItems.length - 1].focus(); } break; case "Home": event.preventDefault(); listItems[0].focus(); break; case "End": event.preventDefault(); listItems[listItems.length - 1].focus(); break; case "Escape": case "Tab": event.stopImmediatePropagation(); this.doClose({ reason: CloseReasons.interaction, target: event.target }); break; default: break; } } onClose(event) { this.doClose({ reason: CloseReasons.interaction, target: event.target }); } afterDialogViewInit() { const focusElementList = this.listItems(); focusElementList.forEach(button => { // Allows user to set tabindex to 0. if (button.getAttribute("tabindex") === null) { button.tabIndex = -1; } }); if (focusElementList[0]) { focusElementList[0].tabIndex = 0; focusElementList[0].focus(); } } listItems() { const selector = ".cds--overflow-menu-options__option:not([disabled]) .cds--overflow-menu-options__btn"; return Array.from(this.elementRef.nativeElement.querySelectorAll(selector)); } } OverflowMenuPane.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "14.3.0", ngImport: i0, type: OverflowMenuPane, deps: [{ token: i0.ElementRef }, { token: i1.I18n }, { token: i2.ExperimentalService }, { token: i3.AnimationFrameService, optional: true }, { token: i3.ElementService, optional: true }], target: i0.ɵɵFactoryTarget.Component }); OverflowMenuPane.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "14.0.0", version: "14.3.0", type: OverflowMenuPane, selector: "cds-overflow-menu-pane, ibm-overflow-menu-pane", host: { listeners: { "keydown": "hostkeys($event)" } }, usesInheritance: true, ngImport: i0, template: ` <ul [attr.id]="dialogConfig.compID" [attr.aria-label]="dialogConfig.menuLabel" [attr.data-floating-menu-direction]="placement ? placement : null" [ngClass]="{'cds--overflow-menu--flip': dialogConfig.flip}" role="menu" #dialog class="cds--overflow-menu-options cds--overflow-menu-options--open" (click)="onClose($event)" [attr.aria-label]="dialogConfig.menuLabel"> <ng-template [ngTemplateOutlet]="dialogConfig.content" [ngTemplateOutletContext]="{overflowMenu: this}"> </ng-template> </ul> `, isInline: true, dependencies: [{ kind: "directive", type: i4.NgClass, selector: "[ngClass]", inputs: ["class", "ngClass"] }, { kind: "directive", type: i4.NgTemplateOutlet, selector: "[ngTemplateOutlet]", inputs: ["ngTemplateOutletContext", "ngTemplateOutlet", "ngTemplateOutletInjector"] }] }); i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "14.3.0", ngImport: i0, type: OverflowMenuPane, decorators: [{ type: Component, args: [{ selector: "cds-overflow-menu-pane, ibm-overflow-menu-pane", template: ` <ul [attr.id]="dialogConfig.compID" [attr.aria-label]="dialogConfig.menuLabel" [attr.data-floating-menu-direction]="placement ? placement : null" [ngClass]="{'cds--overflow-menu--flip': dialogConfig.flip}" role="menu" #dialog class="cds--overflow-menu-options cds--overflow-menu-options--open" (click)="onClose($event)" [attr.aria-label]="dialogConfig.menuLabel"> <ng-template [ngTemplateOutlet]="dialogConfig.content" [ngTemplateOutletContext]="{overflowMenu: this}"> </ng-template> </ul> ` }] }], ctorParameters: function () { return [{ type: i0.ElementRef }, { type: i1.I18n }, { type: i2.ExperimentalService }, { type: i3.AnimationFrameService, decorators: [{ type: Optional }] }, { type: i3.ElementService, decorators: [{ type: Optional }] }]; }, propDecorators: { hostkeys: [{ type: HostListener, args: ["keydown", ["$event"]] }] } }); //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoib3ZlcmZsb3ctbWVudS1wYW5lLmNvbXBvbmVudC5qcyIsInNvdXJjZVJvb3QiOiIiLCJzb3VyY2VzIjpbIi4uLy4uLy4uLy4uL3NyYy9kaWFsb2cvb3ZlcmZsb3ctbWVudS9vdmVyZmxvdy1tZW51LXBhbmUuY29tcG9uZW50LnRzIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiJBQUFBLE9BQU8sRUFDTixTQUFTLEVBQ1QsWUFBWSxFQUdaLFFBQVEsRUFDUixNQUFNLGVBQWUsQ0FBQztBQUN2QixPQUFPLEVBQUUsTUFBTSxFQUFFLE1BQU0scUJBQXFCLENBQUM7QUFDN0MsT0FBTyxFQUFFLFFBQVEsRUFBRSxNQUFNLHdCQUF3QixDQUFDO0FBQ2xELE9BQU8sRUFBRSxpQkFBaUIsRUFBRSxrQkFBa0IsRUFBRSxNQUFNLGtDQUFrQyxDQUFDO0FBSXpGLE9BQU8sRUFBRSxZQUFZLEVBQUUsTUFBTSw0QkFBNEIsQ0FBQztBQUMxRCxPQUFPLEVBQUUsV0FBVyxFQUFFLE1BQU0saUNBQWlDLENBQUM7Ozs7OztBQUU5RDs7OztHQUlHO0FBcUJILE1BQU0sT0FBTyxnQkFBaUIsU0FBUSxNQUFNO0lBQzNDLFlBQ1csVUFBc0IsRUFDdEIsSUFBVSxFQUNWLFlBQWlDLEVBQ3JCLHdCQUErQyxJQUFJO0lBQ3pFLHlGQUF5RjtJQUNuRSxpQkFBaUMsSUFBSTtRQUMzRCxLQUFLLENBQUMsVUFBVSxFQUFFLGNBQWMsRUFBRSxxQkFBcUIsQ0FBQyxDQUFDO1FBTi9DLGVBQVUsR0FBVixVQUFVLENBQVk7UUFDdEIsU0FBSSxHQUFKLElBQUksQ0FBTTtRQUNWLGlCQUFZLEdBQVosWUFBWSxDQUFxQjtRQUNyQiwwQkFBcUIsR0FBckIscUJBQXFCLENBQThCO1FBRW5ELG1CQUFjLEdBQWQsY0FBYyxDQUF1QjtJQUU1RCxDQUFDO0lBRUQsWUFBWTtRQUNYLE1BQU0sb0JBQW9CLEdBQUcsR0FBRyxDQUFDLEVBQUU7WUFDbEMsSUFBSSxNQUFNLENBQUM7WUFDWDs7OztjQUlFO1lBQ0YsTUFBTSxV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UztRQUNsQixNQUFNLFFBQVEsR0FBRyxzRkFBc0YsQ0FBQztRQUN4RyxPQUFPLEtBQUssQ0FBQyxJQUFJLENBQWMsSUFBSSxDQUFDLFVBQVUsQ0FBQyxhQUFhLENBQUMsZ0JBQWdCLENBQUMsUUFBUSxDQUFDLENBQUMsQ0FBQztJQUMxRixDQUFDOzs2R0E5R1csZ0JBQWdCO2lHQUFoQixnQkFBZ0IscUtBbEJsQjs7Ozs7Ozs7Ozs7Ozs7OztFQWdCVDsyRkFFVyxnQkFBZ0I7a0JBcEI1QixTQUFTO21CQUFDO29CQUNWLFFBQVEsRUFBRSxnREFBZ0Q7b0JBQzFELFFBQVEsRUFBRTs7Ozs7Ozs7Ozs7Ozs7OztFQWdCVDtpQkFDRDs7MEJBTUUsUUFBUTs7MEJBRVIsUUFBUTs0Q0FpQ1YsUUFBUTtzQkFEUCxZQUFZO3VCQUFDLFNBQVMsRUFBRSxDQUFDLFFBQVEsQ0FBQyIsInNvdXJjZXNDb250ZW50IjpbImltcG9ydCB7XG5cdENvbXBvbmVudCxcblx0SG9zdExpc3RlbmVyLFxuXHRFbGVtZW50UmVmLFxuXHRBZnRlclZpZXdJbml0LFxuXHRPcHRpb25hbFxufSBmcm9tIFwiQGFuZ3VsYXIvY29yZVwiO1xuaW1wb3J0IHsgRGlhbG9nIH0gZnJvbSBcIi4uL2RpYWxvZy5jb21wb25lbnRcIjtcbmltcG9ydCB7IHBvc2l0aW9uIH0gZnJvbSBcIkBjYXJib24vdXRpbHMtcG9zaXRpb25cIjtcbmltcG9ydCB7IGlzRm9jdXNJbkxhc3RJdGVtLCBpc0ZvY3VzSW5GaXJzdEl0ZW0gfSBmcm9tIFwiY2FyYm9uLWNvbXBvbmVudHMtYW5ndWxhci9jb21tb25cIjtcbmltcG9ydCB7IEkxOG4gfSBmcm9tIFwiY2FyYm9uLWNvbXBvbmVudHMtYW5ndWxhci9pMThuXCI7XG5pbXBvcnQgeyBFeHBlcmltZW50YWxTZXJ2aWNlIH0gZnJvbSBcImNhcmJvbi1jb21wb25lbnRzLWFuZ3VsYXIvZXhwZXJpbWVudGFsXCI7XG5pbXBvcnQgeyBBbmltYXRpb25GcmFtZVNlcnZpY2UsIEVsZW1lbnRTZXJ2aWNlIH0gZnJvbSBcImNhcmJvbi1jb21wb25lbnRzLWFuZ3VsYXIvdXRpbHNcIjtcbmltcG9ydCB7IENsb3NlUmVhc29ucyB9IGZyb20gXCIuLi9kaWFsb2ctY29uZmlnLmludGVyZmFjZVwiO1xuaW1wb3J0IHsgY2xvc2VzdEF0dHIgfSBmcm9tIFwiY2FyYm9uLWNvbXBvbmVudHMtYW5ndWxhci91dGlsc1wiO1xuXG4vKipcbiAqIEV4dGVuZCB0aGUgYERpYWxvZ2AgY29tcG9uZW50IHRvIGNyZWF0ZSBhbiBvdmVyZmxvdyBtZW51LlxuICpcbiAqIE5vdCB1c2VkIGRpcmVjdGx5LiBTZWUgb3ZlcmZsb3ctbWVudS5jb21wb25lbnQgYW5kIG92ZXJmbG93LW1lbnUuZGlyZWN0aXZlIGZvciBtb3JlXG4gKi9cbkBDb21wb25lbnQoe1xuXHRzZWxlY3RvcjogXCJjZHMtb3ZlcmZsb3ctbWVudS1wYW5lLCBpYm0tb3ZlcmZsb3ctbWVudS1wYW5lXCIsXG5cdHRlbXBsYXRlOiBgXG5cdFx0PHVsXG5cdFx0XHRbYXR0ci5pZF09XCJkaWFsb2dDb25maWcuY29tcElEXCJcblx0XHRcdFthdHRyLmFyaWEtbGFiZWxdPVwiZGlhbG9nQ29uZmlnLm1lbnVMYWJlbFwiXG5cdFx0XHRbYXR0ci5kYXRhLWZsb2F0aW5nLW1lbnUtZGlyZWN0aW9uXT1cInBsYWNlbWVudCA/IHBsYWNlbWVudCA6IG51bGxcIlxuXHRcdFx0W25nQ2xhc3NdPVwieydjZHMtLW92ZXJmbG93LW1lbnUtLWZsaXAnOiBkaWFsb2dDb25maWcuZmxpcH1cIlxuXHRcdFx0cm9sZT1cIm1lbnVcIlxuXHRcdFx0I2RpYWxvZ1xuXHRcdFx0Y2xhc3M9XCJjZHMtLW92ZXJmbG93LW1lbnUtb3B0aW9ucyBjZHMtLW92ZXJmbG93LW1lbnUtb3B0aW9ucy0tb3BlblwiXG5cdFx0XHQoY2xpY2spPVwib25DbG9zZSgkZXZlbnQpXCJcblx0XHRcdFthdHRyLmFyaWEtbGFiZWxdPVwiZGlhbG9nQ29uZmlnLm1lbnVMYWJlbFwiPlxuXHRcdFx0PG5nLXRlbXBsYXRlXG5cdFx0XHRcdFtuZ1RlbXBsYXRlT3V0bGV0XT1cImRpYWxvZ0NvbmZpZy5jb250ZW50XCJcblx0XHRcdFx0W25nVGVtcGxhdGVPdXRsZXRDb250ZXh0XT1cIntvdmVyZmxvd01lbnU6IHRoaXN9XCI+XG5cdFx0XHQ8L25nLXRlbXBsYXRlPlxuXHRcdDwvdWw+XG5cdGBcbn0pXG5leHBvcnQgY2xhc3MgT3ZlcmZsb3dNZW51UGFuZSBleHRlbmRzIERpYWxvZyBpbXBsZW1lbnRzIEFmdGVyVmlld0luaXQge1xuXHRjb25zdHJ1Y3Rvcihcblx0XHRwcm90ZWN0ZWQgZWxlbWVudFJlZjogRWxlbWVudFJlZixcblx0XHRwcm90ZWN0ZWQgaTE4bjogSTE4bixcblx0XHRwcm90ZWN0ZWQgZXhwZXJpbWVudGFsOiBFeHBlcmltZW50YWxTZXJ2aWNlLFxuXHRcdEBPcHRpb25hbCgpIHByb3RlY3RlZCBhbmltYXRpb25GcmFtZVNlcnZpY2U6IEFuaW1hdGlvbkZyYW1lU2VydmljZSA9IG51bGwsXG5cdFx0Ly8gbWFyayBgZWxlbWVudFNlcnZpY2VgIGFzIG9wdGlvbmFsIHNpbmNlIG1ha2luZyBpdCBtYW5kYXRvcnkgd291bGQgYmUgYSBicmVha2luZyBjaGFuZ2Vcblx0XHRAT3B0aW9uYWwoKSBwcm90ZWN0ZWQgZWxlbWVudFNlcnZpY2U6IEVsZW1lbnRTZXJ2aWNlID0gbnVsbCkge1xuXHRcdHN1cGVyKGVsZW1lbnRSZWYsIGVsZW1lbnRTZXJ2aWNlLCBhbmltYXRpb25GcmFtZVNlcnZpY2UpO1xuXHR9XG5cblx0b25EaWFsb2dJbml0KCkge1xuXHRcdGNvbnN0IHBvc2l0aW9uT3ZlcmZsb3dNZW51ID0gcG9zID0+IHtcblx0XHRcdGxldCBvZmZzZXQ7XG5cdFx0XHQvKlxuXHRcdFx0KiAyMCBpcyBoYWxmIHRoZSB3aWR0aCBvZiB0aGUgb3ZlcmZsb3cgbWVudSB0cmlnZ2VyIGVsZW1lbnQuXG5cdFx0XHQqIHdlIGFsc28gbW92ZSB0aGUgZWxlbWVudCBieSBoYWxmIG9mIGl0J3Mgb3duIHdpZHRoLCBzaW5jZVxuXHRcdFx0KiBwb3NpdGlvbiBzZXJ2aWNlIHdpbGwgdHJ5IGFuZCBjZW50ZXIgZXZlcnl0aGluZ1xuXHRcdFx0Ki9cblx0XHRcdGNvbnN0IGNsb3Nlc3RSZWwgPSBjbG9zZXN0QXR0cihcInBvc2l0aW9uXCIsIFtcInJlbGF0aXZlXCIsIFwiZml4ZWRcIiwgXCJhYnNvbHV0ZVwiXSwgdGhpcy5lbGVtZW50UmVmLm5hdGl2ZUVsZW1lbnQpO1xuXHRcdFx0Y29uc3QgdG9wRml4ID0gY2xvc2VzdFJlbCA/IGNsb3Nlc3RSZWwuZ2V0Qm91bmRpbmdDbGllbnRSZWN0KCkudG9wICogLTEgOiAwO1xuXHRcdFx0Y29uc3QgbGVmdEZpeCA9IGNsb3Nlc3RSZWwgPyBjbG9zZXN0UmVsLmdldEJvdW5kaW5nQ2xpZW50UmVjdCgpLmxlZnQgKiAtMSA6IDA7XG5cblx0XHRcdG9mZnNldCA9IE1hdGgucm91bmQodGhpcy5kaWFsb2cubmF0aXZlRWxlbWVudC5vZmZzZXRXaWR0aCAvIDIpIC0gMjA7XG5cdFx0XHRpZiAodGhpcy5kaWFsb2dDb25maWcuZmxpcCkge1xuXHRcdFx0XHRyZXR1cm4gcG9zaXRpb24uYWRkT2Zmc2V0KHBvcywgdG9wRml4LCAoLW9mZnNldCArIGxlZnRGaXgpKTtcblx0XHRcdH1cblx0XHRcdHJldHVybiBwb3NpdGlvbi5hZGRPZmZzZXQocG9zLCB0b3BGaXgsIChvZmZzZXQgKyBsZWZ0Rml4KSk7XG5cdFx0fTtcblxuXHRcdHRoaXMuYWRkR2FwW1wiYm90dG9tXCJdID0gcG9zaXRpb25PdmVyZmxvd01lbnU7XG5cblx0XHR0aGlzLmFkZEdhcFtcInRvcFwiXSA9IHBvc2l0aW9uT3ZlcmZsb3dNZW51O1xuXG5cdFx0aWYgKCF0aGlzLmRpYWxvZ0NvbmZpZy5tZW51TGFiZWwpIHtcblx0XHRcdHRoaXMuZGlhbG9nQ29uZmlnLm1lbnVMYWJlbCA9IHRoaXMuaTE4bi5nZXQoKS5PVkVSRkxPV19NRU5VLk9WRVJGTE9XO1xuXHRcdH1cblx0fVxuXG5cdEBIb3N0TGlzdGVuZXIoXCJrZXlkb3duXCIsIFtcIiRldmVudFwiXSlcblx0aG9zdGtleXMoZXZlbnQ6IEtleWJvYXJkRXZlbnQpIHtcblx0XHRjb25zdCBsaXN0SXRlbXMgPSB0aGlzLmxpc3RJdGVtcygpO1xuXG5cdFx0c3dpdGNoIChldmVudC5rZXkpIHtcblx0XHRcdGNhc2UgXCJBcnJvd0Rvd25cIjpcblx0XHRcdFx0ZXZlbnQucHJldmVudERlZmF1bHQoKTtcblx0XHRcdFx0aWYgKCFpc0ZvY3VzSW5MYXN0SXRlbShldmVudCwgbGlzdEl0ZW1zKSkgIHtcblx0XHRcdFx0XHRjb25zdCBpbmRleCA9IGxpc3RJdGVtcy5maW5kSW5kZXgoaXRlbSA9PiBpdGVtID09PSBldmVudC50YXJnZXQpO1xuXHRcdFx0XHRcdGxpc3RJdGVtc1tpbmRleCArIDFdLmZvY3VzKCk7XG5cdFx0XHRcdH0gZWxzZSB7XG5cdFx0XHRcdFx0bGlzdEl0ZW1zWzBdLmZvY3VzKCk7XG5cdFx0XHRcdH1cblx0XHRcdFx0YnJlYWs7XG5cblx0XHRcdGNhc2UgXCJBcnJvd1VwXCI6XG5cdFx0XHRcdGV2ZW50LnByZXZlbnREZWZhdWx0KCk7XG5cdFx0XHRcdGlmICghaXNGb2N1c0luRmlyc3RJdGVtKGV2ZW50LCBsaXN0SXRlbXMpKSAge1xuXHRcdFx0XHRcdGNvbnN0IGluZGV4ID0gbGlzdEl0ZW1zLmZpbmRJbmRleChpdGVtID0+IGl0ZW0gPT09IGV2ZW50LnRhcmdldCk7XG5cdFx0XHRcdFx0bGlzdEl0ZW1zW2luZGV4IC0gMV0uZm9jdXMoKTtcblx0XHRcdFx0fSBlbHNlIHtcblx0XHRcdFx0XHRsaXN0SXRlbXNbbGlzdEl0ZW1zLmxlbmd0aCAtIDFdLmZvY3VzKCk7XG5cdFx0XHRcdH1cblx0XHRcdFx0YnJlYWs7XG5cblx0XHRcdGNhc2UgXCJIb21lXCI6XG5cdFx0XHRcdGV2ZW50LnByZXZlbnREZWZhdWx0KCk7XG5cdFx0XHRcdGxpc3RJdGVtc1swXS5mb2N1cygpO1xuXHRcdFx0XHRicmVhaztcblxuXHRcdFx0Y2FzZSBcIkVuZFwiOlxuXHRcdFx0XHRldmVudC5wcmV2ZW50RGVmYXVsdCgpO1xuXHRcdFx0XHRsaXN0SXRlbXNbbGlzdEl0ZW1zLmxlbmd0aCAtIDFdLmZvY3VzKCk7XG5cdFx0XHRcdGJyZWFrO1xuXG5cdFx0XHRjYXNlIFwiRXNjYXBlXCI6XG5cdFx0XHRjYXNlIFwiVGFiXCI6XG5cdFx0XHRcdGV2ZW50LnN0b3BJbW1lZGlhdGVQcm9wYWdhdGlvbigpO1xuXHRcdFx0XHR0aGlzLmRvQ2xvc2Uoe1xuXHRcdFx0XHRcdHJlYXNvbjogQ2xvc2VSZWFzb25zLmludGVyYWN0aW9uLFxuXHRcdFx0XHRcdHRhcmdldDogZXZlbnQudGFyZ2V0XG5cdFx0XHRcdH0pO1xuXHRcdFx0XHRicmVhaztcblx0XHRcdGRlZmF1bHQ6IGJyZWFrO1xuXHRcdH1cblx0fVxuXG5cdG9uQ2xvc2UoZXZlbnQpIHtcblx0XHR0aGlzLmRvQ2xvc2Uoe1xuXHRcdFx0cmVhc29uOiBDbG9zZVJlYXNvbnMuaW50ZXJhY3Rpb24sXG5cdFx0XHR0YXJnZXQ6IGV2ZW50LnRhcmdldFxuXHRcdH0pO1xuXHR9XG5cblx0YWZ0ZXJEaWFsb2dWaWV3SW5pdCgpIHtcblx0XHRjb25zdCBmb2N1c0VsZW1lbnRMaXN0ID0gdGhpcy5saXN0SXRlbXMoKTtcblx0XHRmb2N1c0VsZW1lbnRMaXN0LmZvckVhY2goYnV0dG9uID0+IHtcblx0XHRcdC8vIEFsbG93cyB1c2VyIHRvIHNldCB0YWJpbmRleCB0byAwLlxuXHRcdFx0aWYgKGJ1dHRvbi5nZXRBdHRyaWJ1dGUoXCJ0YWJpbmRleFwiKSA9PT0gbnVsbCkge1xuXHRcdFx0XHRidXR0b24udGFiSW5kZXggPSAtMTtcblx0XHRcdH1cblx0XHR9KTtcblx0XHRpZiAoZm9jdXNFbGVtZW50TGlzdFswXSkge1xuXHRcdFx0Zm9jdXNFbGVtZW50TGlzdFswXS50YWJJbmRleCA9IDA7XG5cdFx0XHRmb2N1c0VsZW1lbnRMaXN0WzBdLmZvY3VzKCk7XG5cdFx0fVxuXHR9XG5cblx0cHJvdGVjdGVkIGxpc3RJdGVtcygpIHtcblx0XHRjb25zdCBzZWxlY3RvciA9IFwiLmNkcy0tb3ZlcmZsb3ctbWVudS1vcHRpb25zX19vcHRpb246bm90KFtkaXNhYmxlZF0pIC5jZHMtLW92ZXJmbG93LW1lbnUtb3B0aW9uc19fYnRuXCI7XG5cdFx0cmV0dXJuIEFycmF5LmZyb208SFRNTEVsZW1lbnQ+KHRoaXMuZWxlbWVudFJlZi5uYXRpdmVFbGVtZW50LnF1ZXJ5U2VsZWN0b3JBbGwoc2VsZWN0b3IpKTtcblx0fVxufVxuIl19