UNPKG

@nova-ui/bits

Version:

SolarWinds Nova Framework

126 lines 26.6 kB
// © 2022 SolarWinds Worldwide, LLC. All rights reserved. // // Permission is hereby granted, free of charge, to any person obtaining a copy // of this software and associated documentation files (the "Software"), to // deal in the Software without restriction, including without limitation the // rights to use, copy, modify, merge, publish, distribute, sublicense, and/or // sell copies of the Software, and to permit persons to whom the Software is // furnished to do so, subject to the following conditions: // // The above copyright notice and this permission notice shall be included in // all copies or substantial portions of the Software. // // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR // IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, // FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE // AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER // LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, // OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN // THE SOFTWARE. import { Component, ContentChild, ContentChildren, forwardRef, Input, QueryList, TemplateRef, ViewEncapsulation, } from "@angular/core"; import { AbstractControl } from "@angular/forms"; import _forOwn from "lodash/forOwn"; import _isNull from "lodash/isNull"; import { merge } from "rxjs"; import { NuiFormFieldControl } from "./public-api"; import { extractTouchedChanges } from "./touched-changes-helper"; import { ValidationMessageComponent } from "../validation-message/validation-message.component"; import * as i0 from "@angular/core"; import * as i1 from "@angular/common"; import * as i2 from "../icon/icon.component"; import * as i3 from "../popover/popover.component"; // <example-url>./../examples/index.html#/form-field</example-url> export class FormFieldComponent { constructor() { /** * Ability to hide optional text (optional) near label if needed * @type {boolean} */ this.showOptionalText = true; this.controlIsOptional = false; } ngAfterContentChecked() { this.controlIsOptional = this.showOptionalText && !this.hasRequiredField(this.control); } ngAfterContentInit() { if (this.control) { merge(this.control.valueChanges, this.control.statusChanges, extractTouchedChanges(this.control)).subscribe(() => { this.validationMessages.forEach((message) => { if (_isNull(this.control.errors)) { message.show = false; } else { message.show = !!this.control.errors[message.for]; } }); if (this.nuiFormControl) { this.nuiFormControl.isInErrorState = this.control.invalid; } }); } if (this.nuiFormControl) { // using setTimeout to prevent "expression changed after it has been checked" error setTimeout(() => { this.nuiFormControl.ariaLabel = this.caption; }); } } getWidth() { return this.customBoxWidth || "100%"; } hasRequiredField(abstractControl) { if (!abstractControl) { return false; } // There is no way in Angular to understand if certain control has some validator // (not a certain error at this moment, but a validator even there are no errors). // Only way is to get validator function from the control, fire it and check the result. // Works for form group as well. // Credits: https://stackoverflow.com/questions/39819123/angular2-find-out-if-formcontrol-has-required-validator if (abstractControl.validator) { const validator = abstractControl.validator({}); if (validator && validator.required) { return true; } } // This also works for a form Group if (abstractControl["controls"]) { _forOwn(abstractControl["controls"], (control) => { if (control && this.hasRequiredField(control)) { return true; } }); } return false; } static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "17.3.12", ngImport: i0, type: FormFieldComponent, deps: [], target: i0.ɵɵFactoryTarget.Component }); } static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "14.0.0", version: "17.3.12", type: FormFieldComponent, selector: "nui-form-field", inputs: { control: "control", caption: "caption", info: "info", infoTemplate: "infoTemplate", hint: "hint", hintTemplate: "hintTemplate", customBoxWidth: "customBoxWidth", showOptionalText: "showOptionalText" }, queries: [{ propertyName: "nuiFormControl", first: true, predicate: i0.forwardRef(() => NuiFormFieldControl), descendants: true }, { propertyName: "validationMessages", predicate: ValidationMessageComponent }], ngImport: i0, template: "<ng-template #showOptional>\n <span *ngIf=\"showOptionalText\" class=\"nui-form-field__state-text\" i18n\n >(optional)</span\n >\n</ng-template>\n\n<div class=\"nui-form-field\" [ngStyle]=\"{ width: getWidth() }\">\n <div class=\"nui-form-field__control-label-container\" *ngIf=\"caption\">\n <div class=\"nui-form-field__control-label-container-description\">\n <label class=\"nui-form-field__control-label\">{{ caption }}</label>\n <span\n *ngIf=\"controlIsOptional\"\n class=\"nui-form-field__state-text\"\n i18n\n >(optional)</span\n >\n </div>\n <div\n *ngIf=\"info || infoTemplate\"\n class=\"nui-form-field__control-label-container-info\"\n >\n <nui-popover\n [template]=\"infoTemplatePlain\"\n class=\"d-inline-flex\"\n [unlimited]=\"true\"\n >\n <nui-icon [icon]=\"'severity_info'\"></nui-icon>\n </nui-popover>\n </div>\n </div>\n <ng-content></ng-content>\n <div class=\"nui-form-field__help\">\n <div>\n <ng-content select=\"nui-validation-message\"> </ng-content>\n </div>\n <span class=\"nui-help-hint\" *ngIf=\"hint || hintTemplate\">\n <ng-container *ngIf=\"hint && !hintTemplate\">{{\n hint\n }}</ng-container>\n <ng-container\n *ngIf=\"hintTemplate && !hint\"\n [ngTemplateOutlet]=\"hintTemplate\"\n ></ng-container>\n </span>\n </div>\n</div>\n\n<ng-template #infoTemplatePlain>\n <ng-container *ngIf=\"info; else infoTemplate\">\n {{ info }}\n </ng-container>\n</ng-template>\n", styles: [".nui .nui-form-field__control-label-container{clear:left;display:flex;justify-content:space-between}.nui .nui-form-field__control-label-container-description{display:flex;padding-right:5px;overflow:hidden}.nui .nui-form-field__control-label-container-info{display:flex;align-items:center;cursor:pointer}.nui .nui-form-field__help{display:block;clear:both;padding:0;line-height:18px;font-size:11px}.nui .nui-form-field__help--error{clear:both;padding:0;color:var(--nui-color-text-critical,#dd2c00);margin:0 0 7px;line-height:18px;font-size:11px;font-weight:600}.nui .nui-form-field__help--centered{text-align:center}.nui .nui-form-field__state-text{color:var(--nui-color-text-secondary,rgba(17, 17, 17, .6));cursor:default}.nui .nui-form-field__control-label{overflow:hidden;text-overflow:ellipsis;padding-right:5px}\n"], dependencies: [{ kind: "directive", type: i1.NgIf, selector: "[ngIf]", inputs: ["ngIf", "ngIfThen", "ngIfElse"] }, { kind: "directive", type: i1.NgTemplateOutlet, selector: "[ngTemplateOutlet]", inputs: ["ngTemplateOutletContext", "ngTemplateOutlet", "ngTemplateOutletInjector"] }, { kind: "directive", type: i1.NgStyle, selector: "[ngStyle]", inputs: ["ngStyle"] }, { kind: "component", type: i2.IconComponent, selector: "nui-icon", inputs: ["iconColor", "brushType", "iconHoverColor", "iconSize", "cssClass", "fillContainer", "status", "childStatus", "icon", "counter"] }, { kind: "component", type: i3.PopoverComponent, selector: "nui-popover", inputs: ["closePopover", "openPopover", "disabled", "trigger", "template", "placement", "popoverTitle", "icon", "modal", "container", "hasPadding", "preventClosing", "unlimited", "delay", "withGrowAfterOpen", "popoverOverlayPosition"], outputs: ["shown", "hidden"] }], encapsulation: i0.ViewEncapsulation.None }); } } i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "17.3.12", ngImport: i0, type: FormFieldComponent, decorators: [{ type: Component, args: [{ selector: "nui-form-field", encapsulation: ViewEncapsulation.None, template: "<ng-template #showOptional>\n <span *ngIf=\"showOptionalText\" class=\"nui-form-field__state-text\" i18n\n >(optional)</span\n >\n</ng-template>\n\n<div class=\"nui-form-field\" [ngStyle]=\"{ width: getWidth() }\">\n <div class=\"nui-form-field__control-label-container\" *ngIf=\"caption\">\n <div class=\"nui-form-field__control-label-container-description\">\n <label class=\"nui-form-field__control-label\">{{ caption }}</label>\n <span\n *ngIf=\"controlIsOptional\"\n class=\"nui-form-field__state-text\"\n i18n\n >(optional)</span\n >\n </div>\n <div\n *ngIf=\"info || infoTemplate\"\n class=\"nui-form-field__control-label-container-info\"\n >\n <nui-popover\n [template]=\"infoTemplatePlain\"\n class=\"d-inline-flex\"\n [unlimited]=\"true\"\n >\n <nui-icon [icon]=\"'severity_info'\"></nui-icon>\n </nui-popover>\n </div>\n </div>\n <ng-content></ng-content>\n <div class=\"nui-form-field__help\">\n <div>\n <ng-content select=\"nui-validation-message\"> </ng-content>\n </div>\n <span class=\"nui-help-hint\" *ngIf=\"hint || hintTemplate\">\n <ng-container *ngIf=\"hint && !hintTemplate\">{{\n hint\n }}</ng-container>\n <ng-container\n *ngIf=\"hintTemplate && !hint\"\n [ngTemplateOutlet]=\"hintTemplate\"\n ></ng-container>\n </span>\n </div>\n</div>\n\n<ng-template #infoTemplatePlain>\n <ng-container *ngIf=\"info; else infoTemplate\">\n {{ info }}\n </ng-container>\n</ng-template>\n", styles: [".nui .nui-form-field__control-label-container{clear:left;display:flex;justify-content:space-between}.nui .nui-form-field__control-label-container-description{display:flex;padding-right:5px;overflow:hidden}.nui .nui-form-field__control-label-container-info{display:flex;align-items:center;cursor:pointer}.nui .nui-form-field__help{display:block;clear:both;padding:0;line-height:18px;font-size:11px}.nui .nui-form-field__help--error{clear:both;padding:0;color:var(--nui-color-text-critical,#dd2c00);margin:0 0 7px;line-height:18px;font-size:11px;font-weight:600}.nui .nui-form-field__help--centered{text-align:center}.nui .nui-form-field__state-text{color:var(--nui-color-text-secondary,rgba(17, 17, 17, .6));cursor:default}.nui .nui-form-field__control-label{overflow:hidden;text-overflow:ellipsis;padding-right:5px}\n"] }] }], propDecorators: { control: [{ type: Input }], caption: [{ type: Input }], info: [{ type: Input }], infoTemplate: [{ type: Input }], hint: [{ type: Input }], hintTemplate: [{ type: Input }], customBoxWidth: [{ type: Input }], showOptionalText: [{ type: Input }], validationMessages: [{ type: ContentChildren, args: [ValidationMessageComponent] }], nuiFormControl: [{ type: ContentChild, args: [forwardRef(() => NuiFormFieldControl)] }] } }); //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiZm9ybS1maWVsZC5jb21wb25lbnQuanMiLCJzb3VyY2VSb290IjoiIiwic291cmNlcyI6WyIuLi8uLi8uLi8uLi9zcmMvbGliL2Zvcm0tZmllbGQvZm9ybS1maWVsZC5jb21wb25lbnQudHMiLCIuLi8uLi8uLi8uLi9zcmMvbGliL2Zvcm0tZmllbGQvZm9ybS1maWVsZC5jb21wb25lbnQuaHRtbCJdLCJuYW1lcyI6W10sIm1hcHBpbmdzIjoiQUFBQSx5REFBeUQ7QUFDekQsRUFBRTtBQUNGLCtFQUErRTtBQUMvRSw0RUFBNEU7QUFDNUUsOEVBQThFO0FBQzlFLCtFQUErRTtBQUMvRSw4RUFBOEU7QUFDOUUsNERBQTREO0FBQzVELEVBQUU7QUFDRiw2RUFBNkU7QUFDN0UsdURBQXVEO0FBQ3ZELEVBQUU7QUFDRiw2RUFBNkU7QUFDN0UsNEVBQTRFO0FBQzVFLCtFQUErRTtBQUMvRSwwRUFBMEU7QUFDMUUsaUZBQWlGO0FBQ2pGLDZFQUE2RTtBQUM3RSxpQkFBaUI7QUFFakIsT0FBTyxFQUdILFNBQVMsRUFDVCxZQUFZLEVBQ1osZUFBZSxFQUNmLFVBQVUsRUFDVixLQUFLLEVBQ0wsU0FBUyxFQUNULFdBQVcsRUFDWCxpQkFBaUIsR0FDcEIsTUFBTSxlQUFlLENBQUM7QUFDdkIsT0FBTyxFQUFFLGVBQWUsRUFBYSxNQUFNLGdCQUFnQixDQUFDO0FBQzVELE9BQU8sT0FBTyxNQUFNLGVBQWUsQ0FBQztBQUNwQyxPQUFPLE9BQU8sTUFBTSxlQUFlLENBQUM7QUFDcEMsT0FBTyxFQUFFLEtBQUssRUFBRSxNQUFNLE1BQU0sQ0FBQztBQUU3QixPQUFPLEVBQUUsbUJBQW1CLEVBQUUsTUFBTSxjQUFjLENBQUM7QUFDbkQsT0FBTyxFQUFFLHFCQUFxQixFQUFFLE1BQU0sMEJBQTBCLENBQUM7QUFDakUsT0FBTyxFQUFFLDBCQUEwQixFQUFFLE1BQU0sb0RBQW9ELENBQUM7Ozs7O0FBRWhHLGtFQUFrRTtBQU9sRSxNQUFNLE9BQU8sa0JBQWtCO0lBTi9CO1FBcUNJOzs7V0FH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STtzQkFBWixLQUFLO2dCQUlHLFlBQVk7c0JBQXBCLEtBQUs7Z0JBSUcsY0FBYztzQkFBdEIsS0FBSztnQkFLRyxnQkFBZ0I7c0JBQXhCLEtBQUs7Z0JBR04sa0JBQWtCO3NCQURqQixlQUFlO3VCQUFDLDBCQUEwQjtnQkFJM0MsY0FBYztzQkFEYixZQUFZO3VCQUFDLFVBQVUsQ0FBQyxHQUFHLEVBQUUsQ0FBQyxtQkFBbUIsQ0FBQyIsInNvdXJjZXNDb250ZW50IjpbIi8vIMKpIDIwMjIgU29sYXJXaW5kcyBXb3JsZHdpZGUsIExMQy4gQWxsIHJpZ2h0cyByZXNlcnZlZC5cbi8vXG4vLyBQZXJtaXNzaW9uIGlzIGhlcmVieSBncmFudGVkLCBmcmVlIG9mIGNoYXJnZSwgdG8gYW55IHBlcnNvbiBvYnRhaW5pbmcgYSBjb3B5XG4vLyAgb2YgdGhpcyBzb2Z0d2FyZSBhbmQgYXNzb2NpYXRlZCBkb2N1bWVudGF0aW9uIGZpbGVzICh0aGUgXCJTb2Z0d2FyZVwiKSwgdG9cbi8vICBkZWFsIGluIHRoZSBTb2Z0d2FyZSB3aXRob3V0IHJlc3RyaWN0aW9uLCBpbmNsdWRpbmcgd2l0aG91dCBsaW1pdGF0aW9uIHRoZVxuLy8gIHJpZ2h0cyB0byB1c2UsIGNvcHksIG1vZGlmeSwgbWVyZ2UsIHB1Ymxpc2gsIGRpc3RyaWJ1dGUsIHN1YmxpY2Vuc2UsIGFuZC9vclxuLy8gIHNlbGwgY29waWVzIG9mIHRoZSBTb2Z0d2FyZSwgYW5kIHRvIHBlcm1pdCBwZXJzb25zIHRvIHdob20gdGhlIFNvZnR3YXJlIGlzXG4vLyAgZnVybmlzaGVkIHRvIGRvIHNvLCBzdWJqZWN0IHRvIHRoZSBmb2xsb3dpbmcgY29uZGl0aW9uczpcbi8vXG4vLyBUaGUgYWJvdmUgY29weXJpZ2h0IG5vdGljZSBhbmQgdGhpcyBwZXJtaXNzaW9uIG5vdGljZSBzaGFsbCBiZSBpbmNsdWRlZCBpblxuLy8gIGFsbCBjb3BpZXMgb3Igc3Vic3RhbnRpYWwgcG9ydGlvbnMgb2YgdGhlIFNvZnR3YXJlLlxuLy9cbi8vIFRIRSBTT0ZUV0FSRSBJUyBQUk9WSURFRCBcIkFTIElTXCIsIFdJVEhPVVQgV0FSUkFOVFkgT0YgQU5ZIEtJTkQsIEVYUFJFU1MgT1Jcbi8vICBJTVBMSUVELCBJTkNMVURJTkcgQlVUIE5PVCBMSU1JVEVEIFRPIFRIRSBXQVJSQU5USUVTIE9GIE1FUkNIQU5UQUJJTElUWSxcbi8vICBGSVRORVNTIEZPUiBBIFBBUlRJQ1VMQVIgUFVSUE9TRSBBTkQgTk9OSU5GUklOR0VNRU5ULiBJTiBOTyBFVkVOVCBTSEFMTCBUSEVcbi8vICBBVVRIT1JTIE9SIENPUFlSSUdIVCBIT0xERVJTIEJFIExJQUJMRSBGT1IgQU5ZIENMQUlNLCBEQU1BR0VTIE9SIE9USEVSXG4vLyAgTElBQklMSVRZLCBXSEVUSEVSIElOIEFOIEFDVElPTiBPRiBDT05UUkFDVCwgVE9SVCBPUiBPVEhFUldJU0UsIEFSSVNJTkcgRlJPTSxcbi8vICBPVVQgT0YgT1IgSU4gQ09OTkVDVElPTiBXSVRIIFRIRSBTT0ZUV0FSRSBPUiBUSEUgVVNFIE9SIE9USEVSIERFQUxJTkdTIElOXG4vLyAgVEhFIFNPRlRXQVJFLlxuXG5pbXBvcnQge1xuICAgIEFmdGVyQ29udGVudENoZWNrZWQsXG4gICAgQWZ0ZXJDb250ZW50SW5pdCxcbiAgICBDb21wb25lbnQsXG4gICAgQ29udGVudENoaWxkLFxuICAgIENvbnRlbnRDaGlsZHJlbixcbiAgICBmb3J3YXJkUmVmLFxuICAgIElucHV0LFxuICAgIFF1ZXJ5TGlzdCxcbiAgICBUZW1wbGF0ZVJlZixcbiAgICBWaWV3RW5jYXBzdWxhdGlvbixcbn0gZnJvbSBcIkBhbmd1bGFyL2NvcmVcIjtcbmltcG9ydCB7IEFic3RyYWN0Q29udHJvbCwgRm9ybUdyb3VwIH0gZnJvbSBcIkBhbmd1bGFyL2Zvcm1zXCI7XG5pbXBvcnQgX2Zvck93biBmcm9tIFwibG9kYXNoL2Zvck93blwiO1xuaW1wb3J0IF9pc051bGwgZnJvbSBcImxvZGFzaC9pc051bGxcIjtcbmltcG9ydCB7IG1lcmdlIH0gZnJvbSBcInJ4anNcIjtcblxuaW1wb3J0IHsgTnVpRm9ybUZpZWxkQ29udHJvbCB9IGZyb20gXCIuL3B1YmxpYy1hcGlcIjtcbmltcG9ydCB7IGV4dHJhY3RUb3VjaGVkQ2hhbmdlcyB9IGZyb20gXCIuL3RvdWNoZWQtY2hhbmdlcy1oZWxwZXJcIjtcbmltcG9ydCB7IFZhbGlkYXRpb25NZXNzYWdlQ29tcG9uZW50IH0gZnJvbSBcIi4uL3ZhbGlkYXRpb24tbWVzc2FnZS92YWxpZGF0aW9uLW1lc3NhZ2UuY29tcG9uZW50XCI7XG5cbi8vIDxleGFtcGxlLXVybD4uLy4uL2V4YW1wbGVzL2luZGV4Lmh0bWwjL2Zvcm0tZmllbGQ8L2V4YW1wbGUtdXJsPlxuQENvbXBvbmVudCh7XG4gICAgc2VsZWN0b3I6IFwibnVpLWZvcm0tZmllbGRcIixcbiAgICB0ZW1wbGF0ZVVybDogXCIuL2Zvcm0tZmllbGQuY29tcG9uZW50Lmh0bWxcIixcbiAgICBzdHlsZVVybHM6IFtcIi4vZm9ybS1maWVsZC5jb21wb25lbnQubGVzc1wiXSxcbiAgICBlbmNhcHN1bGF0aW9uOiBWaWV3RW5jYXBzdWxhdGlvbi5Ob25lLFxufSlcbmV4cG9ydCBjbGFzcyBGb3JtRmllbGRDb21wb25lbnRcbiAgICBpbXBsZW1lbnRzIEFmdGVyQ29udGVudEluaXQsIEFmdGVyQ29udGVudENoZWNrZWRcbntcbiAgICAvKipcbiAgICAgKiBGb3JtIGNvbnRyb2wgb2J0YWluZWQgZnJvbSB0aGUgcGFyZW50IHJlYWN0aXZlIGZvcm1cbiAgICAgKi9cbiAgICBASW5wdXQoKSBjb250cm9sOiBBYnN0cmFjdENvbnRyb2w7XG4gICAgLyoqXG4gICAgICogVGV4dCBmb3IgYSBGb3JtIEZpZWxkIGxhYmVsXG4gICAgICovXG4gICAgQElucHV0KCkgY2FwdGlvbjogc3RyaW5nO1xuICAgIC8qKlxuICAgICAqIFRleHQgdG8gYmUgcGFzc2VkIHRvIGEgcG9wb3ZlciBmb3IgaW5mbyBpY29uXG4gICAgICovXG4gICAgQElucHV0KCkgaW5mbzogc3RyaW5nO1xuICAgIC8qKlxuICAgICAqIFRlbXBsYXRlIHRvIHVzZSBpbiBpbmZvJ3MgcG9wb3ZlclxuICAgICAqL1xuICAgIEBJbnB1dCgpIGluZm9UZW1wbGF0ZTogVGVtcGxhdGVSZWY8YW55PjtcbiAgICAvKipcbiAgICAgKiBUZXh0IGZvciBhIEZvcm0gRmllbGQgaGludFxuICAgICAqL1xuICAgIEBJbnB1dCgpIGhpbnQ6IHN0cmluZztcbiAgICAvKipcbiAgICAgKiBUZW1wbGF0ZSBmb3IgYSBGb3JtIEZpZWxkIGhpbnRcbiAgICAgKi9cbiAgICBASW5wdXQoKSBoaW50VGVtcGxhdGU6IFRlbXBsYXRlUmVmPHVua25vd24+O1xuICAgIC8qKlxuICAgICAqIFZhbHVlIGZvciB3aWR0aCBjc3MgcHJvcGVydHkgZm9yIHRoZSBmb3JtIGZpZWxkXG4gICAgICovXG4gICAgQElucHV0KCkgY3VzdG9tQm94V2lkdGg6IHN0cmluZztcbiAgICAvKipcbiAgICAgKiBBYmlsaXR5IHRvIGhpZGUgb3B0aW9uYWwgdGV4dCAob3B0aW9uYWwpIG5lYXIgbGFiZWwgaWYgbmVlZGVkXG4gICAgICogQHR5cGUge2Jvb2xlYW59XG4gICAgICovXG4gICAgQElucHV0KCkgc2hvd09wdGlvbmFsVGV4dCA9IHRydWU7XG5cbiAgICBAQ29udGVudENoaWxkcmVuKFZhbGlkYXRpb25NZXNzYWdlQ29tcG9uZW50KVxuICAgIHZhbGlkYXRpb25NZXNzYWdlczogUXVlcnlMaXN0PFZhbGlkYXRpb25NZXNzYWdlQ29tcG9uZW50PjtcblxuICAgIEBDb250ZW50Q2hpbGQoZm9yd2FyZFJlZigoKSA9PiBOdWlGb3JtRmllbGRDb250cm9sKSlcbiAgICBudWlGb3JtQ29udHJvbDogTnVpRm9ybUZpZWxkQ29udHJvbDtcblxuICAgIHB1YmxpYyBjb250cm9sSXNPcHRpb25hbDogYm9vbGVhbiA9IGZhbHNlO1xuXG4gICAgcHVibGljIG5nQWZ0ZXJDb250ZW50Q2hlY2tlZCgpOiB2b2lkIHtcbiAgICAgICAgdGhpcy5jb250cm9sSXNPcHRpb25hbCA9XG4gICAgICAgICAgICB0aGlzLnNob3dPcHRpb25hbFRleHQgJiYgIXRoaXMuaGFzUmVxdWlyZWRGaWVsZCh0aGlzLmNvbnRyb2wpO1xuICAgIH1cblxuICAgIHB1YmxpYyBuZ0FmdGVyQ29udGVudEluaXQoKTogdm9pZCB7XG4gICAgICAgIGlmICh0aGlzLmNvbnRyb2wpIHtcbiAgICAgICAgICAgIG1lcmdlKFxuICAgICAgICAgICAgICAgIHRoaXMuY29udHJvbC52YWx1ZUNoYW5nZXMsXG4gICAgICAgICAgICAgICAgdGhpcy5jb250cm9sLnN0YXR1c0NoYW5nZXMsXG4gICAgICAgICAgICAgICAgZXh0cmFjdFRvdWNoZWRDaGFuZ2VzKHRoaXMuY29udHJvbClcbiAgICAgICAgICAgICkuc3Vic2NyaWJlKCgpID0+IHtcbiAgICAgICAgICAgICAgICB0aGlzLnZhbGlkYXRpb25NZXNzYWdlcy5mb3JFYWNoKChtZXNzYWdlKSA9PiB7XG4gICAgICAgICAgICAgICAgICAgIGlmIChfaXNOdWxsKHRoaXMuY29udHJvbC5lcnJvcnMpKSB7XG4gICAgICAgICAgICAgICAgICAgICAgICBtZXNzYWdlLnNob3cgPSBmYWxzZTtcbiAgICAgICAgICAgICAgICAgICAgfSBlbHNlIHtcbiAgICAgICAgICAgICAgICAgICAgICAgIG1lc3NhZ2Uuc2hvdyA9ICEhdGhpcy5jb250cm9sLmVycm9yc1ttZXNzYWdlLmZvcl07XG4gICAgICAgICAgICAgICAgICAgIH1cbiAgICAgICAgICAgICAgICB9KTtcblxuICAgICAgICAgICAgICAgIGlmICh0aGlzLm51aUZvcm1Db250cm9sKSB7XG4gICAgICAgICAgICAgICAgICAgIHRoaXMubnVpRm9ybUNvbnRyb2wuaXNJbkVycm9yU3RhdGUgPSB0aGlzLmNvbnRyb2wuaW52YWxpZDtcbiAgICAgICAgICAgICAgICB9XG4gICAgICAgICAgICB9KTtcbiAgICAgICAgfVxuICAgICAgICBpZiAodGhpcy5udWlGb3JtQ29udHJvbCkge1xuICAgICAgICAgICAgLy8gdXNpbmcgc2V0VGltZW91dCB0byBwcmV2ZW50IFwiZXhwcmVzc2lvbiBjaGFuZ2VkIGFmdGVyIGl0IGhhcyBiZWVuIGNoZWNrZWRcIiBlcnJvclxuICAgICAgICAgICAgc2V0VGltZW91dCgoKSA9PiB7XG4gICAgICAgICAgICAgICAgdGhpcy5udWlGb3JtQ29udHJvbC5hcmlhTGFiZWwgPSB0aGlzLmNhcHRpb247XG4gICAgICAgICAgICB9KTtcbiAgICAgICAgfVxuICAgIH1cblxuICAgIHB1YmxpYyBnZXRXaWR0aCgpOiBzdHJpbmcge1xuICAgICAgICByZXR1cm4gdGhpcy5jdXN0b21Cb3hXaWR0aCB8fCBcIjEwMCVcIjtcbiAgICB9XG5cbiAgICBwcml2YXRlIGhhc1JlcXVpcmVkRmllbGQoYWJzdHJhY3RDb250cm9sOiBBYnN0cmFjdENvbnRyb2wpOiBib29sZWFuIHtcbiAgICAgICAgaWYgKCFhYnN0cmFjdENvbnRyb2wpIHtcbiAgICAgICAgICAgIHJldHVybiBmYWxzZTtcbiAgICAgICAgfVxuXG4gICAgICAgIC8vIFRoZXJlIGlzIG5vIHdheSBpbiBBbmd1bGFyIHRvIHVuZGVyc3RhbmQgaWYgY2VydGFpbiBjb250cm9sIGhhcyBzb21lIHZhbGlkYXRvclxuICAgICAgICAvLyAobm90IGEgY2VydGFpbiBlcnJvciBhdCB0aGlzIG1vbWVudCwgYnV0IGEgdmFsaWRhdG9yIGV2ZW4gdGhlcmUgYXJlIG5vIGVycm9ycykuXG4gICAgICAgIC8vIE9ubHkgd2F5IGlzIHRvIGdldCB2YWxpZGF0b3IgZnVuY3Rpb24gZnJvbSB0aGUgY29udHJvbCwgZmlyZSBpdCBhbmQgY2hlY2sgdGhlIHJlc3VsdC5cbiAgICAgICAgLy8gV29ya3MgZm9yIGZvcm0gZ3JvdXAgYXMgd2VsbC5cbiAgICAgICAgLy8gQ3JlZGl0czogaHR0cHM6Ly9zdGFja292ZXJmbG93LmNvbS9xdWVzdGlvbnMvMzk4MTkxMjMvYW5ndWxhcjItZmluZC1vdXQtaWYtZm9ybWNvbnRyb2wtaGFzLXJlcXVpcmVkLXZhbGlkYXRvclxuICAgICAgICBpZiAoYWJzdHJhY3RDb250cm9sLnZhbGlkYXRvcikge1xuICAgICAgICAgICAgY29uc3QgdmFsaWRhdG9yID0gYWJzdHJhY3RDb250cm9sLnZhbGlkYXRvcih7fSBhcyBBYnN0cmFjdENvbnRyb2wpO1xuICAgICAgICAgICAgaWYgKHZhbGlkYXRvciAmJiB2YWxpZGF0b3IucmVxdWlyZWQpIHtcbiAgICAgICAgICAgICAgICByZXR1cm4gdHJ1ZTtcbiAgICAgICAgICAgIH1cbiAgICAgICAgfVxuICAgICAgICAvLyBUaGlzIGFsc28gd29ya3MgZm9yIGEgZm9ybSBHcm91cFxuICAgICAgICBpZiAoKGFic3RyYWN0Q29udHJvbCBhcyBGb3JtR3JvdXApW1wiY29udHJvbHNcIl0pIHtcbiAgICAgICAgICAgIF9mb3JPd24oXG4gICAgICAgICAgICAgICAgKGFic3RyYWN0Q29udHJvbCBhcyBGb3JtR3JvdXApW1wiY29udHJvbHNcIl0sXG4gICAgICAgICAgICAgICAgKGNvbnRyb2w6IEFic3RyYWN0Q29udHJvbCkgPT4ge1xuICAgICAgICAgICAgICAgICAgICBpZiAoY29udHJvbCAmJiB0aGlzLmhhc1JlcXVpcmVkRmllbGQoY29udHJvbCkpIHtcbiAgICAgICAgICAgICAgICAgICAgICAgIHJldHVybiB0cnVlO1xuICAgICAgICAgICAgICAgICAgICB9XG4gICAgICAgICAgICAgICAgfVxuICAgICAgICAgICAgKTtcbiAgICAgICAgfVxuICAgICAgICByZXR1cm4gZmFsc2U7XG4gICAgfVxufVxuIiwiPG5nLXRlbXBsYXRlICNzaG93T3B0aW9uYWw+XG4gICAgPHNwYW4gKm5nSWY9XCJzaG93T3B0aW9uYWxUZXh0XCIgY2xhc3M9XCJudWktZm9ybS1maWVsZF9fc3RhdGUtdGV4dFwiIGkxOG5cbiAgICAgICAgPihvcHRpb25hbCk8L3NwYW5cbiAgICA+XG48L25nLXRlbXBsYXRlPlxuXG48ZGl2IGNsYXNzPVwibnVpLWZvcm0tZmllbGRcIiBbbmdTdHlsZV09XCJ7IHdpZHRoOiBnZXRXaWR0aCgpIH1cIj5cbiAgICA8ZGl2IGNsYXNzPVwibnVpLWZvcm0tZmllbGRfX2NvbnRyb2wtbGFiZWwtY29udGFpbmVyXCIgKm5nSWY9XCJjYXB0aW9uXCI+XG4gICAgICAgIDxkaXYgY2xhc3M9XCJudWktZm9ybS1maWVsZF9fY29udHJvbC1sYWJlbC1jb250YWluZXItZGVzY3JpcHRpb25cIj5cbiAgICAgICAgICAgIDxsYWJlbCBjbGFzcz1cIm51aS1mb3JtLWZpZWxkX19jb250cm9sLWxhYmVsXCI+e3sgY2FwdGlvbiB9fTwvbGFiZWw+XG4gICAgICAgICAgICA8c3BhblxuICAgICAgICAgICAgICAgICpuZ0lmPVwiY29udHJvbElzT3B0aW9uYWxcIlxuICAgICAgICAgICAgICAgIGNsYXNzPVwibnVpLWZvcm0tZmllbGRfX3N0YXRlLXRleHRcIlxuICAgICAgICAgICAgICAgIGkxOG5cbiAgICAgICAgICAgICAgICA+KG9wdGlvbmFsKTwvc3BhblxuICAgICAgICAgICAgPlxuICAgICAgICA8L2Rpdj5cbiAgICAgICAgPGRpdlxuICAgICAgICAgICAgKm5nSWY9XCJpbmZvIHx8IGluZm9UZW1wbGF0ZVwiXG4gICAgICAgICAgICBjbGFzcz1cIm51aS1mb3JtLWZpZWxkX19jb250cm9sLWxhYmVsLWNvbnRhaW5lci1pbmZvXCJcbiAgICAgICAgPlxuICAgICAgICAgICAgPG51aS1wb3BvdmVyXG4gICAgICAgICAgICAgICAgW3RlbXBsYXRlXT1cImluZm9UZW1wbGF0ZVBsYWluXCJcbiAgICAgICAgICAgICAgICBjbGFzcz1cImQtaW5saW5lLWZsZXhcIlxuICAgICAgICAgICAgICAgIFt1bmxpbWl0ZWRdPVwidHJ1ZVwiXG4gICAgICAgICAgICA+XG4gICAgICAgICAgICAgICAgPG51aS1pY29uIFtpY29uXT1cIidzZXZlcml0eV9pbmZvJ1wiPjwvbnVpLWljb24+XG4gICAgICAgICAgICA8L251aS1wb3BvdmVyPlxuICAgICAgICA8L2Rpdj5cbiAgICA8L2Rpdj5cbiAgICA8bmctY29udGVudD48L25nLWNvbnRlbnQ+XG4gICAgPGRpdiBjbGFzcz1cIm51aS1mb3JtLWZpZWxkX19oZWxwXCI+XG4gICAgICAgIDxkaXY+XG4gICAgICAgICAgICA8bmctY29udGVudCBzZWxlY3Q9XCJudWktdmFsaWRhdGlvbi1tZXNzYWdlXCI+IDwvbmctY29udGVudD5cbiAgICAgICAgPC9kaXY+XG4gICAgICAgIDxzcGFuIGNsYXNzPVwibnVpLWhlbHAtaGludFwiICpuZ0lmPVwiaGludCB8fCBoaW50VGVtcGxhdGVcIj5cbiAgICAgICAgICAgIDxuZy1jb250YWluZXIgKm5nSWY9XCJoaW50ICYmICFoaW50VGVtcGxhdGVcIj57e1xuICAgICAgICAgICAgICAgIGhpbnRcbiAgICAgICAgICAgIH19PC9uZy1jb250YWluZXI+XG4gICAgICAgICAgICA8bmctY29udGFpbmVyXG4gICAgICAgICAgICAgICAgKm5nSWY9XCJoaW50VGVtcGxhdGUgJiYgIWhpbnRcIlxuICAgICAgICAgICAgICAgIFtuZ1RlbXBsYXRlT3V0bGV0XT1cImhpbnRUZW1wbGF0ZVwiXG4gICAgICAgICAgICA+PC9uZy1jb250YWluZXI+XG4gICAgICAgIDwvc3Bhbj5cbiAgICA8L2Rpdj5cbjwvZGl2PlxuXG48bmctdGVtcGxhdGUgI2luZm9UZW1wbGF0ZVBsYWluPlxuICAgIDxuZy1jb250YWluZXIgKm5nSWY9XCJpbmZvOyBlbHNlIGluZm9UZW1wbGF0ZVwiPlxuICAgICAgICB7eyBpbmZvIH19XG4gICAgPC9uZy1jb250YWluZXI+XG48L25nLXRlbXBsYXRlPlxuIl19