ng-alertbar
Version:
A configurable alertbar for Angular
349 lines • 26.8 kB
JavaScript
/**
* @fileoverview added by tsickle
* @suppress {checkTypes,extraRequire,missingOverride,missingReturn,unusedPrivateMembers,uselessCode} checked by tsc
*/
import { Component, EventEmitter, Input, Output } from '@angular/core';
import { DomSanitizer } from '@angular/platform-browser';
import { Subject, timer } from 'rxjs';
import { filter, mapTo, switchMap, take, takeUntil } from 'rxjs/operators';
import { slide } from './animations';
import { defaults } from './defaults';
import { NgAlertbarService } from './ng-alertbar.service';
/** @type {?} */
const ALERT_LEAVE_ANIMATION_DURATION = 200;
export class NgAlertbarComponent {
/**
* @param {?} alertBarService
* @param {?} domSanitizer
*/
constructor(alertBarService, domSanitizer) {
this.alertBarService = alertBarService;
this.domSanitizer = domSanitizer;
this.queue = [];
this.queuePop = new Subject();
this.queueing = defaults.queueingEnabled;
this.lifeTime = defaults.lifeTimeMs;
this.showDelay = defaults.showDelayMs;
this.backgroundColor = defaults.backgroundColor;
this.borderColor = defaults.borderColor;
this.textColor = defaults.textColor;
this.widthMode = defaults.widthMode;
this.closeButton = defaults.closeButtonEnabled;
this.html = defaults.useHtml;
this.open = new EventEmitter();
this.close = new EventEmitter();
this.show = false;
this.destroy = new Subject();
}
/**
* @return {?}
*/
get isFullWidth() {
if (this.tempWidthMode) {
return this.tempWidthMode === 'full';
}
return this.widthMode === 'full';
}
/**
* @return {?}
*/
get showCloseButton() {
if (this.tempCloseButton != null) {
return this.tempCloseButton;
}
return this.closeButton;
}
/**
* @return {?}
*/
get useHtml() {
if (this.tempHtml != null) {
return this.tempHtml;
}
return this.html;
}
/**
* @return {?}
*/
get htmlMessage() {
return this.domSanitizer.bypassSecurityTrustHtml(this.message);
}
/**
* The trigger stream after waiting the specified showDelay since the alert was triggered
* @return {?}
*/
get openTriggerPostDelay$() {
return this.alertBarService.trigger$.pipe(switchMap((/**
* @param {?} trigger
* @return {?}
*/
trigger => {
/** @type {?} */
const options = trigger.options;
/** @type {?} */
const showDelay = (options && options.showDelay) || this.showDelay;
return timer(showDelay).pipe(mapTo(trigger));
})), takeUntil(this.destroy));
}
/**
* The trigger stream after waiting the specified lifetime since the alert opened
* @return {?}
*/
get postAlertLifetime$() {
return this.open.pipe(filter((/**
* @param {?} __0
* @return {?}
*/
({ options }) => this.shouldAlertAutoClose(options))), switchMap((/**
* @param {?} __0
* @return {?}
*/
({ options }) => {
/** @type {?} */
const lifeTime = (options && options.lifeTime) || this.lifeTime;
return timer(lifeTime);
})), takeUntil(this.destroy));
}
/**
* The service cancel trigger
* @return {?}
*/
get cancelTrigger$() {
return this.alertBarService.cancel$.pipe(takeUntil(this.destroy));
}
/**
* Timer representing the delay taken for an alert to animate when exiting
* @return {?}
*/
get alertLeaveTimer() {
return timer(ALERT_LEAVE_ANIMATION_DURATION).pipe(take(1));
}
/**
* @return {?}
*/
ngOnInit() {
this.openTriggerPostDelay$.subscribe((/**
* @param {?} trigger
* @return {?}
*/
trigger => this.onTrigger(trigger)));
this.queuePop.subscribe((/**
* @param {?} trigger
* @return {?}
*/
trigger => this.showAlert(trigger)));
this.postAlertLifetime$.subscribe((/**
* @return {?}
*/
() => this.onClose()));
this.cancelTrigger$.subscribe((/**
* @return {?}
*/
() => this.onClose()));
}
/**
* @return {?}
*/
ngOnDestroy() {
this.destroy.next();
}
/**
* @private
* @param {?} trigger
* @return {?}
*/
onTrigger(trigger) {
if (this.queueing && !(trigger.options && trigger.options.bypassQueue) && this.show) {
this.queue.push(trigger);
return;
}
this.showAlert(trigger);
}
/**
* Sets up temp variables and shows the alert
* @private
* @param {?} trigger The trigger to display
* @return {?}
*/
showAlert(trigger) {
this.clearTempOptions(); // Clear previous temporary options
this.assignTempOptions(trigger.options);
this.message = trigger.message;
this.show = true;
this.open.emit(trigger);
}
/**
* Closes any open alert. If there are any alerts waiting in the queue,
* the alert is popped off the queue and emitted for opening
* @return {?}
*/
onClose() {
this.closeAlert();
if (this.queue.length > 0) {
this.alertLeaveTimer.subscribe((/**
* @return {?}
*/
() => {
this.queuePop.next(this.queue.shift());
}));
}
}
/**
* @private
* @return {?}
*/
closeAlert() {
this.show = false;
this.close.emit();
}
/**
* Clears out any temporary config options so that they
* do not persist beyond their single use
* @private
* @return {?}
*/
clearTempOptions() {
this.tempBackgroundColor = null;
this.tempBorderColor = null;
this.tempTextColor = null;
this.tempWidthMode = null;
this.tempCloseButton = null;
this.tempHtml = null;
}
/**
* Assigns the options included in the trigger to the temporary
* config variables so they can apply for the upcoming alert
* @private
* @param {?} options The options passed in the trigger
* @return {?}
*/
assignTempOptions(options) {
if (!options) {
return;
}
this.tempBackgroundColor = options.backgroundColor;
this.tempBorderColor = options.borderColor;
this.tempTextColor = options.textColor;
this.tempWidthMode = options.widthMode;
this.tempCloseButton = options.closeButton;
this.tempHtml = options.html;
}
/**
* @private
* @param {?} options
* @return {?}
*/
shouldAlertAutoClose(options) {
if (options && options.lifeTime != null) {
return options.lifeTime > 0;
}
return this.lifeTime > 0; // Fallback to component setting
}
}
NgAlertbarComponent.decorators = [
{ type: Component, args: [{
selector: 'ng-alertbar',
template: `
<div *ngIf="show" [] class="ng-alert-bar-wrapper">
<div
class="ng-alert-bar"
[class.full-width]="isFullWidth"
[style.background]="tempBackgroundColor || backgroundColor"
[style.border-color]="tempBorderColor || borderColor"
>
<span class="ng-alert-bar-text" [style.color]="tempTextColor || textColor">
<span *ngIf="!useHtml; else htmlMessageContainer">{{ message }}</span>
<ng-template #htmlMessageContainer><span [innerHTML]="htmlMessage"></span></ng-template>
<span *ngIf="showCloseButton" class="ng-alert-close" (click)="onClose()">×</span>
</span>
</div>
</div>
`,
animations: [slide],
styles: [".ng-alert-bar-wrapper{position:absolute;top:0;left:0;width:100%;text-align:center;pointer-events:none}.ng-alert-bar{pointer-events:all}.ng-alert-bar:not(.full-width){display:inline-block}.ng-alert-close{font-size:1.1em;margin-left:.25rem;vertical-align:middle;cursor:pointer}"]
}] }
];
/** @nocollapse */
NgAlertbarComponent.ctorParameters = () => [
{ type: NgAlertbarService },
{ type: DomSanitizer }
];
NgAlertbarComponent.propDecorators = {
queueing: [{ type: Input }],
lifeTime: [{ type: Input }],
showDelay: [{ type: Input }],
backgroundColor: [{ type: Input }],
borderColor: [{ type: Input }],
textColor: [{ type: Input }],
widthMode: [{ type: Input }],
closeButton: [{ type: Input }],
html: [{ type: Input }],
open: [{ type: Output }],
close: [{ type: Output }]
};
if (false) {
/**
* @type {?}
* @private
*/
NgAlertbarComponent.prototype.queue;
/**
* @type {?}
* @private
*/
NgAlertbarComponent.prototype.queuePop;
/** @type {?} */
NgAlertbarComponent.prototype.queueing;
/** @type {?} */
NgAlertbarComponent.prototype.lifeTime;
/** @type {?} */
NgAlertbarComponent.prototype.showDelay;
/** @type {?} */
NgAlertbarComponent.prototype.backgroundColor;
/** @type {?} */
NgAlertbarComponent.prototype.tempBackgroundColor;
/** @type {?} */
NgAlertbarComponent.prototype.borderColor;
/** @type {?} */
NgAlertbarComponent.prototype.tempBorderColor;
/** @type {?} */
NgAlertbarComponent.prototype.textColor;
/** @type {?} */
NgAlertbarComponent.prototype.tempTextColor;
/** @type {?} */
NgAlertbarComponent.prototype.widthMode;
/** @type {?} */
NgAlertbarComponent.prototype.tempWidthMode;
/** @type {?} */
NgAlertbarComponent.prototype.closeButton;
/** @type {?} */
NgAlertbarComponent.prototype.tempCloseButton;
/** @type {?} */
NgAlertbarComponent.prototype.html;
/** @type {?} */
NgAlertbarComponent.prototype.tempHtml;
/** @type {?} */
NgAlertbarComponent.prototype.open;
/** @type {?} */
NgAlertbarComponent.prototype.close;
/** @type {?} */
NgAlertbarComponent.prototype.show;
/** @type {?} */
NgAlertbarComponent.prototype.message;
/**
* @type {?}
* @private
*/
NgAlertbarComponent.prototype.destroy;
/**
* @type {?}
* @private
*/
NgAlertbarComponent.prototype.alertBarService;
/**
* @type {?}
* @private
*/
NgAlertbarComponent.prototype.domSanitizer;
}
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoibmctYWxlcnRiYXIuY29tcG9uZW50LmpzIiwic291cmNlUm9vdCI6Im5nOi8vbmctYWxlcnRiYXIvIiwic291cmNlcyI6WyJsaWIvbmctYWxlcnRiYXIuY29tcG9uZW50LnRzIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiI7Ozs7QUFBQSxPQUFPLEVBQUUsU0FBUyxFQUFFLFlBQVksRUFBRSxLQUFLLEVBQXFCLE1BQU0sRUFBRSxNQUFNLGVBQWUsQ0FBQztBQUMxRixPQUFPLEVBQUUsWUFBWSxFQUFFLE1BQU0sMkJBQTJCLENBQUM7QUFDekQsT0FBTyxFQUFFLE9BQU8sRUFBRSxLQUFLLEVBQUUsTUFBTSxNQUFNLENBQUM7QUFDdEMsT0FBTyxFQUFFLE1BQU0sRUFBRSxLQUFLLEVBQUUsU0FBUyxFQUFFLElBQUksRUFBRSxTQUFTLEVBQUUsTUFBTSxnQkFBZ0IsQ0FBQztBQUMzRSxPQUFPLEVBQUUsS0FBSyxFQUFFLE1BQU0sY0FBYyxDQUFDO0FBQ3JDLE9BQU8sRUFBRSxRQUFRLEVBQUUsTUFBTSxZQUFZLENBQUM7QUFFdEMsT0FBTyxFQUFFLGlCQUFpQixFQUFFLE1BQU0sdUJBQXVCLENBQUM7O01BRXBELDhCQUE4QixHQUFHLEdBQUc7QUF1QjFDLE1BQU0sT0FBTyxtQkFBbUI7Ozs7O0lBZ0c5QixZQUFvQixlQUFrQyxFQUFVLFlBQTBCO1FBQXRFLG9CQUFlLEdBQWYsZUFBZSxDQUFtQjtRQUFVLGlCQUFZLEdBQVosWUFBWSxDQUFjO1FBL0ZsRixVQUFLLEdBQW1CLEVBQUUsQ0FBQztRQUMzQixhQUFRLEdBQUcsSUFBSSxPQUFPLEVBQWdCLENBQUM7UUFFdEMsYUFBUSxHQUFHLFFBQVEsQ0FBQyxlQUFlLENBQUM7UUFDcEMsYUFBUSxHQUFHLFFBQVEsQ0FBQyxVQUFVLENBQUM7UUFDL0IsY0FBUyxHQUFHLFFBQVEsQ0FBQyxXQUFXLENBQUM7UUFFakMsb0JBQWUsR0FBRyxRQUFRLENBQUMsZUFBZSxDQUFDO1FBRTNDLGdCQUFXLEdBQUcsUUFBUSxDQUFDLFdB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Ozs7SUFxRTFCLDhDQUEwQzs7Ozs7SUFBRSwyQ0FBa0MiLCJzb3VyY2VzQ29udGVudCI6WyJpbXBvcnQgeyBDb21wb25lbnQsIEV2ZW50RW1pdHRlciwgSW5wdXQsIE9uRGVzdHJveSwgT25Jbml0LCBPdXRwdXQgfSBmcm9tICdAYW5ndWxhci9jb3JlJztcbmltcG9ydCB7IERvbVNhbml0aXplciB9IGZyb20gJ0Bhbmd1bGFyL3BsYXRmb3JtLWJyb3dzZXInO1xuaW1wb3J0IHsgU3ViamVjdCwgdGltZXIgfSBmcm9tICdyeGpzJztcbmltcG9ydCB7IGZpbHRlciwgbWFwVG8sIHN3aXRjaE1hcCwgdGFrZSwgdGFrZVVudGlsIH0gZnJvbSAncnhqcy9vcGVyYXRvcnMnO1xuaW1wb3J0IHsgc2xpZGUgfSBmcm9tICcuL2FuaW1hdGlvbnMnO1xuaW1wb3J0IHsgZGVmYXVsdHMgfSBmcm9tICcuL2RlZmF1bHRzJztcbmltcG9ydCB7IEFsZXJ0T3B0aW9ucywgQWxlcnRUcmlnZ2VyIH0gZnJvbSAnLi9pbnRlcmZhY2UnO1xuaW1wb3J0IHsgTmdBbGVydGJhclNlcnZpY2UgfSBmcm9tICcuL25nLWFsZXJ0YmFyLnNlcnZpY2UnO1xuXG5jb25zdCBBTEVSVF9MRUFWRV9BTklNQVRJT05fRFVSQVRJT04gPSAyMDA7XG5cbkBDb21wb25lbnQoe1xuICBzZWxlY3RvcjogJ25nLWFsZXJ0YmFyJyxcbiAgdGVtcGxhdGU6IGBcbiAgICA8ZGl2ICpuZ0lmPVwic2hvd1wiIFtAc2xpZGVdIGNsYXNzPVwibmctYWxlcnQtYmFyLXdyYXBwZXJcIj5cbiAgICAgIDxkaXZcbiAgICAgICAgY2xhc3M9XCJuZy1hbGVydC1iYXJcIlxuICAgICAgICBbY2xhc3MuZnVsbC13aWR0aF09XCJpc0Z1bGxXaWR0aFwiXG4gICAgICAgIFtzdHlsZS5iYWNrZ3JvdW5kXT1cInRlbXBCYWNrZ3JvdW5kQ29sb3IgfHwgYmFja2dyb3VuZENvbG9yXCJcbiAgICAgICAgW3N0eWxlLmJvcmRlci1jb2xvcl09XCJ0ZW1wQm9yZGVyQ29sb3IgfHwgYm9yZGVyQ29sb3JcIlxuICAgICAgPlxuICAgICAgICA8c3BhbiBjbGFzcz1cIm5nLWFsZXJ0LWJhci10ZXh0XCIgW3N0eWxlLmNvbG9yXT1cInRlbXBUZXh0Q29sb3IgfHwgdGV4dENvbG9yXCI+XG4gICAgICAgICAgPHNwYW4gKm5nSWY9XCIhdXNlSHRtbDsgZWxzZSBodG1sTWVzc2FnZUNvbnRhaW5lclwiPnt7IG1lc3NhZ2UgfX08L3NwYW4+XG4gICAgICAgICAgPG5nLXRlbXBsYXRlICNodG1sTWVzc2FnZUNvbnRhaW5lcj48c3BhbiBbaW5uZXJIVE1MXT1cImh0bWxNZXNzYWdlXCI+PC9zcGFuPjwvbmctdGVtcGxhdGU+XG4gICAgICAgICAgPHNwYW4gKm5nSWY9XCJzaG93Q2xvc2VCdXR0b25cIiBjbGFzcz1cIm5nLWFsZXJ0LWNsb3NlXCIgKGNsaWNrKT1cIm9uQ2xvc2UoKVwiPiZ0aW1lczs8L3NwYW4+XG4gICAgICAgIDwvc3Bhbj5cbiAgICAgIDwvZGl2PlxuICAgIDwvZGl2PlxuICBgLFxuICBzdHlsZVVybHM6IFsnLi9uZy1hbGVydGJhci5jb21wb25lbnQuY3NzJ10sXG4gIGFuaW1hdGlvbnM6IFtzbGlkZV1cbn0pXG5leHBvcnQgY2xhc3MgTmdBbGVydGJhckNvbXBvbmVudCBpbXBsZW1lbnRzIE9uSW5pdCwgT25EZXN0cm95IHtcbiAgcHJpdmF0ZSBxdWV1ZTogQWxlcnRUcmlnZ2VyW10gPSBbXTtcbiAgcHJpdmF0ZSBxdWV1ZVBvcCA9IG5ldyBTdWJqZWN0PEFsZXJ0VHJpZ2dlcj4oKTtcblxuICBASW5wdXQoKSBxdWV1ZWluZyA9IGRlZmF1bHRzLnF1ZXVlaW5nRW5hYmxlZDtcbiAgQElucHV0KCkgbGlmZVRpbWUgPSBkZWZhdWx0cy5saWZlVGltZU1zO1xuICBASW5wdXQoKSBzaG93RGVsYXkgPSBkZWZhdWx0cy5zaG93RGVsYXlNcztcblxuICBASW5wdXQoKSBiYWNrZ3JvdW5kQ29sb3IgPSBkZWZhdWx0cy5iYWNrZ3JvdW5kQ29sb3I7XG4gIHRlbXBCYWNrZ3JvdW5kQ29sb3I6IHN0cmluZztcbiAgQElucHV0KCkgYm9yZGVyQ29sb3IgPSBkZWZhdWx0cy5ib3JkZXJDb2xvcjtcbiAgdGVtcEJvcmRlckNvbG9yOiBzdHJpbmc7XG4gIEBJbnB1dCgpIHRleHRDb2xvciA9IGRlZmF1bHRzLnRleHRDb2xvcjtcbiAgdGVtcFRleHRDb2xvcjogc3RyaW5nO1xuXG4gIEBJbnB1dCgpIHdpZHRoTW9kZSA9IGRlZmF1bHRzLndpZHRoTW9kZTtcbiAgdGVtcFdpZHRoTW9kZTogJ2Z1bGwnIHwgJ3BhcnRpYWwnO1xuICBASW5wdXQoKSBjbG9zZUJ1dHRvbiA9IGRlZmF1bHRzLmNsb3NlQnV0dG9uRW5hYmxlZDtcbiAgdGVtcENsb3NlQnV0dG9uOiBib29sZWFuO1xuICBASW5wdXQoKSBodG1sID0gZGVmYXVsdHMudXNlSHRtbDtcbiAgdGVtcEh0bWw6IGJvb2xlYW47XG5cbiAgQE91dHB1dCgpIG9wZW4gPSBuZXcgRXZlbnRFbWl0dGVyPEFsZXJ0VHJpZ2dlcj4oKTtcbiAgQE91dHB1dCgpIGNsb3NlID0gbmV3IEV2ZW50RW1pdHRlcjx2b2lkPigpO1xuXG4gIHNob3cgPSBmYWxzZTtcbiAgbWVzc2FnZTogc3RyaW5nO1xuICBwcml2YXRlIGRlc3Ryb3kgPSBuZXcgU3ViamVjdDx2b2lkPigpO1xuXG4gIGdldCBpc0Z1bGxXaWR0aCgpIHtcbiAgICBpZiAodGhpcy50ZW1wV2lkdGhNb2RlKSB7XG4gICAgICByZXR1cm4gdGhpcy50ZW1wV2lkdGhNb2RlID09PSAnZnVsbCc7XG4gICAgfVxuICAgIHJldHVybiB0aGlzLndpZHRoTW9kZSA9PT0gJ2Z1bGwnO1xuICB9XG5cbiAgZ2V0IHNob3dDbG9zZUJ1dHRvbigpIHtcbiAgICBpZiAodGhpcy50ZW1wQ2xvc2VCdXR0b24gIT0gbnVsbCkge1xuICAgICAgcmV0dXJuIHRoaXMudGVtcENsb3NlQnV0dG9uO1xuICAgIH1cbiAgICByZXR1cm4gdGhpcy5jbG9zZUJ1dHRvbjtcbiAgfVxuXG4gIGdldCB1c2VIdG1sKCkge1xuICAgIGlmICh0aGlzLnRlbXBIdG1sICE9IG51bGwpIHtcbiAgICAgIHJldHVybiB0aGlzLnRlbXBIdG1sO1xuICAgIH1cbiAgICByZXR1cm4gdGhpcy5odG1sO1xuICB9XG5cbiAgZ2V0IGh0bWxNZXNzYWdlKCkge1xuICAgIHJldHVybiB0aGlzLmRvbVNhbml0aXplci5ieXBhc3NTZWN1cml0eVRydXN0SHRtbCh0aGlzLm1lc3NhZ2UpO1xuICB9XG5cbiAgLyoqXG4gICAqIFRoZSB0cmlnZ2VyIHN0cmVhbSBhZnRlciB3YWl0aW5nIHRoZSBzcGVjaWZpZWQgc2hvd0RlbGF5IHNpbmNlIHRoZSBhbGVydCB3YXMgdHJpZ2dlcmVkXG4gICAqL1xuICBnZXQgb3BlblRyaWdnZXJQb3N0RGVsYXkkKCkge1xuICAgIHJldHVybiB0aGlzLmFsZXJ0QmFyU2VydmljZS50cmlnZ2VyJC5waXBlKFxuICAgICAgc3dpdGNoTWFwKHRyaWdnZXIgPT4ge1xuICAgICAgICBjb25zdCBvcHRpb25zID0gdHJpZ2dlci5vcHRpb25zO1xuICAgICAgICBjb25zdCBzaG93RGVsYXkgPSAob3B0aW9ucyAmJiBvcHRpb25zLnNob3dEZWxheSkgfHwgdGhpcy5zaG93RGVsYXk7XG4gICAgICAgIHJldHVybiB0aW1lcihzaG93RGVsYXkpLnBpcGUobWFwVG8odHJpZ2dlcikpO1xuICAgICAgfSksXG4gICAgICB0YWtlVW50aWwodGhpcy5kZXN0cm95KVxuICAgICk7XG4gIH1cblxuICAvKipcbiAgICogVGhlIHRyaWdnZXIgc3RyZWFtIGFmdGVyIHdhaXRpbmcgdGhlIHNwZWNpZmllZCBsaWZldGltZSBzaW5jZSB0aGUgYWxlcnQgb3BlbmVkXG4gICAqL1xuICBnZXQgcG9zdEFsZXJ0TGlmZXRpbWUkKCkge1xuICAgIHJldHVybiB0aGlzLm9wZW4ucGlwZShcbiAgICAgIGZpbHRlcigoeyBvcHRpb25zIH0pID0+IHRoaXMuc2hvdWxkQWxlcnRBdXRvQ2xvc2Uob3B0aW9ucykpLFxuICAgICAgc3dpdGNoTWFwKCh7IG9wdGlvbnMgfSkgPT4ge1xuICAgICAgICBjb25zdCBsaWZlVGltZSA9IChvcHRpb25zICYmIG9wdGlvbnMubGlmZVRpbWUpIHx8IHRoaXMubGlmZVRpbWU7XG4gICAgICAgIHJldHVybiB0aW1lcihsaWZlVGltZSk7XG4gICAgICB9KSxcbiAgICAgIHRha2VVbnRpbCh0aGlzLmRlc3Ryb3kpXG4gICAgKTtcbiAgfVxuXG4gIC8qKlxuICAgKiBUaGUgc2VydmljZSBjYW5jZWwgdHJpZ2dlclxuICAgKi9cbiAgZ2V0IGNhbmNlbFRyaWdnZXIkKCkge1xuICAgIHJldHVybiB0aGlzLmFsZXJ0QmFyU2VydmljZS5jYW5jZWwkLnBpcGUodGFrZVVudGlsKHRoaXMuZGVzdHJveSkpO1xuICB9XG5cbiAgLyoqXG4gICAqIFRpbWVyIHJlcHJlc2VudGluZyB0aGUgZGVsYXkgdGFrZW4gZm9yIGFuIGFsZXJ0IHRvIGFuaW1hdGUgd2hlbiBleGl0aW5nXG4gICAqL1xuICBnZXQgYWxlcnRMZWF2ZVRpbWVyKCkge1xuICAgIHJldHVybiB0aW1lcihBTEVSVF9MRUFWRV9BTklNQVRJT05fRFVSQVRJT04pLnBpcGUodGFrZSgxKSk7XG4gIH1cblxuICBjb25zdHJ1Y3Rvcihwcml2YXRlIGFsZXJ0QmFyU2VydmljZTogTmdBbGVydGJhclNlcnZpY2UsIHByaXZhdGUgZG9tU2FuaXRpemVyOiBEb21TYW5pdGl6ZXIpIHt9XG5cbiAgbmdPbkluaXQoKSB7XG4gICAgdGhpcy5vcGVuVHJpZ2dlclBvc3REZWxheSQuc3Vic2NyaWJlKHRyaWdnZXIgPT4gdGhpcy5vblRyaWdnZXIodHJpZ2dlcikpO1xuICAgIHRoaXMucXVldWVQb3Auc3Vic2NyaWJlKHRyaWdnZXIgPT4gdGhpcy5zaG93QWxlcnQodHJpZ2dlcikpO1xuICAgIHRoaXMucG9zdEFsZXJ0TGlmZXRpbWUkLnN1YnNjcmliZSgoKSA9PiB0aGlzLm9uQ2xvc2UoKSk7XG4gICAgdGhpcy5jYW5jZWxUcmlnZ2VyJC5zdWJzY3JpYmUoKCkgPT4gdGhpcy5vbkNsb3NlKCkpO1xuICB9XG5cbiAgbmdPbkRlc3Ryb3koKSB7XG4gICAgdGhpcy5kZXN0cm95Lm5leHQoKTtcbiAgfVxuXG4gIHByaXZhdGUgb25UcmlnZ2VyKHRyaWdnZXI6IEFsZXJ0VHJpZ2dlcikge1xuICAgIGlmICh0aGlzLnF1ZXVlaW5nICYmICEodHJpZ2dlci5vcHRpb25zICYmIHRyaWdnZXIub3B0aW9ucy5ieXBhc3NRdWV1ZSkgJiYgdGhpcy5zaG93KSB7XG4gICAgICB0aGlzLnF1ZXVlLnB1c2godHJpZ2dlcik7XG4gICAgICByZXR1cm47XG4gICAgfVxuICAgIHRoaXMuc2hvd0FsZXJ0KHRyaWdnZXIpO1xuICB9XG5cbiAgLyoqXG4gICAqIFNldHMgdXAgdGVtcCB2YXJpYWJsZXMgYW5kIHNob3dzIHRoZSBhbGVydFxuICAgKiBAcGFyYW0gdHJpZ2dlciBUaGUgdHJpZ2dlciB0byBkaXNwbGF5XG4gICAqL1xuICBwcml2YXRlIHNob3dBbGVydCh0cmlnZ2VyOiBBbGVydFRyaWdnZXIpIHtcbiAgICB0aGlzLmNsZWFyVGVtcE9wdGlvbnMoKTsgLy8gQ2xlYXIgcHJldmlvdXMgdGVtcG9yYXJ5IG9wdGlvbnNcbiAgICB0aGlzLmFzc2lnblRlbXBPcHRpb25zKHRyaWdnZXIub3B0aW9ucyk7XG4gICAgdGhpcy5tZXNzYWdlID0gdHJpZ2dlci5tZXNzYWdlO1xuICAgIHRoaXMuc2hvdyA9IHRydWU7XG4gICAgdGhpcy5vcGVuLmVtaXQodHJpZ2dlcik7XG4gIH1cblxuICAvKipcbiAgICogQ2xvc2VzIGFueSBvcGVuIGFsZXJ0LiBJZiB0aGVyZSBhcmUgYW55IGFsZXJ0cyB3YWl0aW5nIGluIHRoZSBxdWV1ZSxcbiAgICogdGhlIGFsZXJ0IGlzIHBvcHBlZCBvZmYgdGhlIHF1ZXVlIGFuZCBlbWl0dGVkIGZvciBvcGVuaW5nXG4gICAqL1xuICBvbkNsb3NlKCkge1xuICAgIHRoaXMuY2xvc2VBbGVydCgpO1xuICAgIGlmICh0aGlzLnF1ZXVlLmxlbmd0aCA+IDApIHtcbiAgICAgIHRoaXMuYWxlcnRMZWF2ZVRpbWVyLnN1YnNjcmliZSgoKSA9PiB7XG4gICAgICAgIHRoaXMucXVldWVQb3AubmV4dCh0aGlzLnF1ZXVlLnNoaWZ0KCkpO1xuICAgICAgfSk7XG4gICAgfVxuICB9XG5cbiAgcHJpdmF0ZSBjbG9zZUFsZXJ0KCkge1xuICAgIHRoaXMuc2hvdyA9IGZhbHNlO1xuICAgIHRoaXMuY2xvc2UuZW1pdCgpO1xuICB9XG5cbiAgLyoqXG4gICAqIENsZWFycyBvdXQgYW55IHRlbXBvcmFyeSBjb25maWcgb3B0aW9ucyBzbyB0aGF0IHRoZXlcbiAgICogZG8gbm90IHBlcnNpc3QgYmV5b25kIHRoZWlyIHNpbmdsZSB1c2VcbiAgICovXG4gIHByaXZhdGUgY2xlYXJUZW1wT3B0aW9ucygpOiB2b2lkIHtcbiAgICB0aGlzLnRlbXBCYWNrZ3JvdW5kQ29sb3IgPSBudWxsO1xuICAgIHRoaXMudGVtcEJvcmRlckNvbG9yID0gbnVsbDtcbiAgICB0aGlzLnRlbXBUZXh0Q29sb3IgPSBudWxsO1xuICAgIHRoaXMudGVtcFdpZHRoTW9kZSA9IG51bGw7XG4gICAgdGhpcy50ZW1wQ2xvc2VCdXR0b24gPSBudWxsO1xuICAgIHRoaXMudGVtcEh0bWwgPSBudWxsO1xuICB9XG5cbiAgLyoqXG4gICAqIEFzc2lnbnMgdGhlIG9wdGlvbnMgaW5jbHVkZWQgaW4gdGhlIHRyaWdnZXIgdG8gdGhlIHRlbXBvcmFyeVxuICAgKiBjb25maWcgdmFyaWFibGVzIHNvIHRoZXkgY2FuIGFwcGx5IGZvciB0aGUgdXBjb21pbmcgYWxlcnRcbiAgICogQHBhcmFtIG9wdGlvbnMgVGhlIG9wdGlvbnMgcGFzc2VkIGluIHRoZSB0cmlnZ2VyXG4gICAqL1xuICBwcml2YXRlIGFzc2lnblRlbXBPcHRpb25zKG9wdGlvbnM6IEFsZXJ0T3B0aW9ucykge1xuICAgIGlmICghb3B0aW9ucykge1xuICAgICAgcmV0dXJuO1xuICAgIH1cbiAgICB0aGlzLnRlbXBCYWNrZ3JvdW5kQ29sb3IgPSBvcHRpb25zLmJhY2tncm91bmRDb2xvcjtcbiAgICB0aGlzLnRlbXBCb3JkZXJDb2xvciA9IG9wdGlvbnMuYm9yZGVyQ29sb3I7XG4gICAgdGhpcy50ZW1wVGV4dENvbG9yID0gb3B0aW9ucy50ZXh0Q29sb3I7XG4gICAgdGhpcy50ZW1wV2lkdGhNb2RlID0gb3B0aW9ucy53aWR0aE1vZGU7XG4gICAgdGhpcy50ZW1wQ2xvc2VCdXR0b24gPSBvcHRpb25zLmNsb3NlQnV0dG9uO1xuICAgIHRoaXMudGVtcEh0bWwgPSBvcHRpb25zLmh0bWw7XG4gIH1cblxuICBwcml2YXRlIHNob3VsZEFsZXJ0QXV0b0Nsb3NlKG9wdGlvbnM6IEFsZXJ0T3B0aW9ucykge1xuICAgIGlmIChvcHRpb25zICYmIG9wdGlvbnMubGlmZVRpbWUgIT0gbnVsbCkge1xuICAgICAgcmV0dXJuIG9wdGlvbnMubGlmZVRpbWUgPiAwO1xuICAgIH1cbiAgICByZXR1cm4gdGhpcy5saWZlVGltZSA+IDA7IC8vIEZhbGxiYWNrIHRvIGNvbXBvbmVudCBzZXR0aW5nXG4gIH1cbn1cbiJdfQ==