ng-agm-core-lib
Version:
Angular components for Google Maps
314 lines • 34.4 kB
JavaScript
import { ContentChildren, Directive, EventEmitter, forwardRef, Input, Output, QueryList } from '@angular/core';
import { ReplaySubject } from 'rxjs';
import { FitBoundsAccessor } from '../services/fit-bounds';
import { AgmInfoWindow } from './info-window';
import * as i0 from "@angular/core";
import * as i1 from "../services/managers/marker-manager";
let markerId = 0;
/**
* AgmMarker renders a map marker inside a {@link AgmMap}.
*
* ### Example
* ```typescript
* import { Component } from '@angular/core';
*
* @Component({
* selector: 'my-map-cmp',
* styles: [`
* .agm-map-container {
* height: 300px;
* }
* `],
* template: `
* <agm-map [latitude]="lat" [longitude]="lng" [zoom]="zoom">
* <agm-marker [latitude]="lat" [longitude]="lng" [label]="'M'">
* </agm-marker>
* </agm-map>
* `
* })
* ```
*/
export class AgmMarker {
_markerManager;
/**
* The latitude position of the marker.
*/
latitude;
/**
* The longitude position of the marker.
*/
longitude;
/**
* The title of the marker.
*/
title;
/**
* The label (a single uppercase character) for the marker.
*/
label;
/**
* If true, the marker can be dragged. Default value is false.
*/
// tslint:disable-next-line:no-input-rename
draggable = false;
/**
* Icon (the URL of the image) for the foreground.
*/
iconUrl;
/**
* If true, the marker is visible
*/
visible = true;
/**
* Whether to automatically open the child info window when the marker is clicked.
*/
openInfoWindow = true;
/**
* The marker's opacity between 0.0 and 1.0.
*/
opacity = 1;
/**
* All markers are displayed on the map in order of their zIndex, with higher values displaying in
* front of markers with lower values. By default, markers are displayed according to their
* vertical position on screen, with lower markers appearing in front of markers further up the
* screen.
*/
zIndex = 1;
/**
* If true, the marker can be clicked. Default value is true.
*/
// tslint:disable-next-line:no-input-rename
clickable = true;
/**
* Which animation to play when marker is added to a map.
* This can be 'BOUNCE' or 'DROP'
*/
animation;
/**
* This event is fired when the marker's animation property changes.
*/
animationChange = new EventEmitter();
/**
* This event emitter gets emitted when the user clicks on the marker.
*/
markerClick = new EventEmitter();
/**
* This event emitter gets emitted when the user clicks twice on the marker.
*/
markerDblClick = new EventEmitter();
/**
* This event is fired when the user rightclicks on the marker.
*/
markerRightClick = new EventEmitter();
/**
* This event is fired when the user starts dragging the marker.
*/
dragStart = new EventEmitter();
/**
* This event is repeatedly fired while the user drags the marker.
*/
// tslint:disable-next-line: no-output-native
drag = new EventEmitter();
/**
* This event is fired when the user stops dragging the marker.
*/
dragEnd = new EventEmitter();
/**
* This event is fired when the user mouses over the marker.
*/
mouseOver = new EventEmitter();
/**
* This event is fired when the user mouses outside the marker.
*/
mouseOut = new EventEmitter();
/** @internal */
infoWindow = new QueryList();
_markerAddedToManger = false;
_id;
_observableSubscriptions = [];
_fitBoundsDetails$ = new ReplaySubject(1);
constructor(_markerManager) {
this._markerManager = _markerManager;
this._id = (markerId++).toString();
}
/* @internal */
ngAfterContentInit() {
this.handleInfoWindowUpdate();
this.infoWindow.changes.subscribe(() => this.handleInfoWindowUpdate());
}
handleInfoWindowUpdate() {
if (this.infoWindow.length > 1) {
throw new Error('Expected no more than one info window.');
}
this.infoWindow.forEach(marker => {
marker.hostMarker = this;
});
}
/** @internal */
ngOnChanges(changes) {
if (typeof this.latitude === 'string') {
this.latitude = Number(this.latitude);
}
if (typeof this.longitude === 'string') {
this.longitude = Number(this.longitude);
}
if (typeof this.latitude !== 'number' || typeof this.longitude !== 'number') {
return;
}
if (!this._markerAddedToManger) {
this._markerManager.addMarker(this);
this._updateFitBoundsDetails();
this._markerAddedToManger = true;
this._addEventListeners();
return;
}
// tslint:disable: no-string-literal
if (changes['latitude'] || changes['longitude']) {
this._markerManager.updateMarkerPosition(this);
this._updateFitBoundsDetails();
}
if (changes['title']) {
this._markerManager.updateTitle(this);
}
if (changes['label']) {
this._markerManager.updateLabel(this);
}
if (changes['draggable']) {
this._markerManager.updateDraggable(this);
}
if (changes['iconUrl']) {
this._markerManager.updateIcon(this);
}
if (changes['opacity']) {
this._markerManager.updateOpacity(this);
}
if (changes['visible']) {
this._markerManager.updateVisible(this);
}
if (changes['zIndex']) {
this._markerManager.updateZIndex(this);
}
if (changes['clickable']) {
this._markerManager.updateClickable(this);
}
if (changes['animation']) {
this._markerManager.updateAnimation(this);
}
// tslint:enable: no-string-literal
}
/** @internal */
getFitBoundsDetails$() {
return this._fitBoundsDetails$.asObservable();
}
_updateFitBoundsDetails() {
this._fitBoundsDetails$.next({ latLng: { lat: this.latitude, lng: this.longitude } });
}
_addEventListeners() {
const cs = this._markerManager.createEventObservable('click', this).subscribe(() => {
if (this.openInfoWindow) {
this.infoWindow.forEach(infoWindow => infoWindow.open());
}
this.markerClick.emit(this);
});
this._observableSubscriptions.push(cs);
const dcs = this._markerManager.createEventObservable('dblclick', this).subscribe(() => {
this.markerDblClick.emit(null);
});
this._observableSubscriptions.push(dcs);
const rc = this._markerManager.createEventObservable('rightclick', this).subscribe(() => {
this.markerRightClick.emit(null);
});
this._observableSubscriptions.push(rc);
const ds = this._markerManager.createEventObservable('dragstart', this)
.subscribe(e => this.dragStart.emit(e));
this._observableSubscriptions.push(ds);
const d = this._markerManager.createEventObservable('drag', this)
.subscribe(e => this.drag.emit(e));
this._observableSubscriptions.push(d);
const de = this._markerManager.createEventObservable('dragend', this)
.subscribe(e => this.dragEnd.emit(e));
this._observableSubscriptions.push(de);
const mover = this._markerManager.createEventObservable('mouseover', this)
.subscribe(e => this.mouseOver.emit(e));
this._observableSubscriptions.push(mover);
const mout = this._markerManager.createEventObservable('mouseout', this)
.subscribe(e => this.mouseOut.emit(e));
this._observableSubscriptions.push(mout);
const anChng = this._markerManager.createEventObservable('animation_changed', this)
.subscribe(() => {
this.animationChange.emit(this.animation);
});
this._observableSubscriptions.push(anChng);
}
/** @internal */
id() { return this._id; }
/** @internal */
toString() { return 'AgmMarker-' + this._id.toString(); }
/** @internal */
ngOnDestroy() {
this._markerManager.deleteMarker(this);
// unsubscribe all registered observable subscriptions
this._observableSubscriptions.forEach((s) => s.unsubscribe());
}
static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "17.3.12", ngImport: i0, type: AgmMarker, deps: [{ token: i1.MarkerManager }], target: i0.ɵɵFactoryTarget.Directive });
static ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "14.0.0", version: "17.3.12", type: AgmMarker, selector: "agm-marker", inputs: { latitude: "latitude", longitude: "longitude", title: "title", label: "label", draggable: ["markerDraggable", "draggable"], iconUrl: "iconUrl", visible: "visible", openInfoWindow: "openInfoWindow", opacity: "opacity", zIndex: "zIndex", clickable: ["markerClickable", "clickable"], animation: "animation" }, outputs: { animationChange: "animationChange", markerClick: "markerClick", markerDblClick: "markerDblClick", markerRightClick: "markerRightClick", dragStart: "dragStart", drag: "drag", dragEnd: "dragEnd", mouseOver: "mouseOver", mouseOut: "mouseOut" }, providers: [
{ provide: FitBoundsAccessor, useExisting: forwardRef(() => AgmMarker) },
], queries: [{ propertyName: "infoWindow", predicate: AgmInfoWindow }], usesOnChanges: true, ngImport: i0 });
}
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "17.3.12", ngImport: i0, type: AgmMarker, decorators: [{
type: Directive,
args: [{
selector: 'agm-marker',
providers: [
{ provide: FitBoundsAccessor, useExisting: forwardRef(() => AgmMarker) },
],
}]
}], ctorParameters: () => [{ type: i1.MarkerManager }], propDecorators: { latitude: [{
type: Input
}], longitude: [{
type: Input
}], title: [{
type: Input
}], label: [{
type: Input
}], draggable: [{
type: Input,
args: ['markerDraggable']
}], iconUrl: [{
type: Input
}], visible: [{
type: Input
}], openInfoWindow: [{
type: Input
}], opacity: [{
type: Input
}], zIndex: [{
type: Input
}], clickable: [{
type: Input,
args: ['markerClickable']
}], animation: [{
type: Input
}], animationChange: [{
type: Output
}], markerClick: [{
type: Output
}], markerDblClick: [{
type: Output
}], markerRightClick: [{
type: Output
}], dragStart: [{
type: Output
}], drag: [{
type: Output
}], dragEnd: [{
type: Output
}], mouseOver: [{
type: Output
}], mouseOut: [{
type: Output
}], infoWindow: [{
type: ContentChildren,
args: [AgmInfoWindow]
}] } });
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoibWFya2VyLmpzIiwic291cmNlUm9vdCI6IiIsInNvdXJjZXMiOlsiLi4vLi4vLi4vLi4vLi4vcGFja2FnZXMvY29yZS9zcmMvbGliL2RpcmVjdGl2ZXMvbWFya2VyLnRzIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiJBQUFBLE9BQU8sRUFBb0IsZUFBZSxFQUFFLFNBQVMsRUFBRSxZQUFZLEVBQUUsVUFBVSxFQUFFLEtBQUssRUFBd0IsTUFBTSxFQUFFLFNBQVMsRUFBZ0IsTUFBTSxlQUFlLENBQUM7QUFDckssT0FBTyxFQUFjLGFBQWEsRUFBZ0IsTUFBTSxNQUFNLENBQUM7QUFDL0QsT0FBTyxFQUFFLGlCQUFpQixFQUFvQixNQUFNLHdCQUF3QixDQUFDO0FBRTdFLE9BQU8sRUFBRSxhQUFhLEVBQUUsTUFBTSxlQUFlLENBQUM7OztBQUU5QyxJQUFJLFFBQVEsR0FBRyxDQUFDLENBQUM7QUFFakI7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7R0FzQkc7QUFPSCxNQUFNLE9BQU8sU0FBUztJQTBIQTtJQXpIcEI7O09BRUc7SUFDTSxRQUFRLENBQVM7SUFFMUI7O09BRUc7SUFDTSxTQUFTLENBQVM7SUFFM0I7O09BRUc7SUFDTSxLQUFLLENBQVM7SUFFdkI7O09BRUc7SUFDTSxLQUFLLENBQW1DO0lBRWpEOztPQUVHO0lBQ0gsMkNBQTJDO0lBQ2pCLFNBQVMsR0FBRyxLQUFLLENBQUM7SUFFNUM7O09BRUc7SUFDTSxPQUFPLENBQWlEO0lBRWpFOztPQUVHO0lBQ00sT0FBTyxHQUFHLElBQUksQ0FBQztJQUV4Qjs7T0FFRztJQUNNLGNBQWMsR0FBRyxJQUFJLENBQUM7SUFFL0I7O09BRUc7SUFDTSxPQUFPLEdBQUcsQ0FBQyxDQUFDO0lBRXJCOzs7OztPQUtHO0lBQ00sTUFBTSxHQUFHLENBQUMsQ0FBQztJQUVwQjs7T0FFRztJQUNILDJDQUEyQztJQUNqQixTQUFTLEdBQUcsSUFBSSxDQUFDO0lBRTNDOzs7T0FHRztJQUNNLFNBQVMsQ0FBcUM7SUFFdkQ7O09BRUc7SUFD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LE1BQU07Z0JBS0csU0FBUztzQkFBbEIsTUFBTTtnQkFLRyxRQUFRO3NCQUFqQixNQUFNO2dCQUd5QixVQUFVO3NCQUF6QyxlQUFlO3VCQUFDLGFBQWEiLCJzb3VyY2VzQ29udGVudCI6WyJpbXBvcnQgeyBBZnRlckNvbnRlbnRJbml0LCBDb250ZW50Q2hpbGRyZW4sIERpcmVjdGl2ZSwgRXZlbnRFbWl0dGVyLCBmb3J3YXJkUmVmLCBJbnB1dCwgT25DaGFuZ2VzLCBPbkRlc3Ryb3ksIE91dHB1dCwgUXVlcnlMaXN0LCBTaW1wbGVDaGFuZ2UgfSBmcm9tICdAYW5ndWxhci9jb3JlJztcbmltcG9ydCB7IE9ic2VydmFibGUsIFJlcGxheVN1YmplY3QsIFN1YnNjcmlwdGlvbiB9IGZyb20gJ3J4anMnO1xuaW1wb3J0IHsgRml0Qm91bmRzQWNjZXNzb3IsIEZpdEJvdW5kc0RldGFpbHMgfSBmcm9tICcuLi9zZXJ2aWNlcy9maXQtYm91bmRzJztcbmltcG9ydCB7IE1hcmtlck1hbmFnZXIgfSBmcm9tICcuLi9zZXJ2aWNlcy9tYW5hZ2Vycy9tYXJrZXItbWFuYWdlcic7XG5pbXBvcnQgeyBBZ21JbmZvV2luZG93IH0gZnJvbSAnLi9pbmZvLXdpbmRvdyc7XG5cbmxldCBtYXJrZXJJZCA9IDA7XG5cbi8qKlxuICogQWdtTWFya2VyIHJlbmRlcnMgYSBtYXAgbWFya2VyIGluc2lkZSBhIHtAbGluayBBZ21NYXB9LlxuICpcbiAqICMjIyBFeGFtcGxlXG4gKiBgYGB0eXBlc2NyaXB0XG4gKiBpbXBvcnQgeyBDb21wb25lbnQgfSBmcm9tICdAYW5ndWxhci9jb3JlJztcbiAqXG4gKiBAQ29tcG9uZW50KHtcbiAqICBzZWxlY3RvcjogJ215LW1hcC1jbXAnLFxuICogIHN0eWxlczogW2BcbiAqICAgIC5hZ20tbWFwLWNvbnRhaW5lciB7XG4gKiAgICAgIGhlaWdodDogMzAwcHg7XG4gKiAgICB9XG4gKiBgXSxcbiAqICB0ZW1wbGF0ZTogYFxuICogICAgPGFnbS1tYXAgW2xhdGl0dWRlXT1cImxhdFwiIFtsb25naXR1ZGVdPVwibG5nXCIgW3pvb21dPVwiem9vbVwiPlxuICogICAgICA8YWdtLW1hcmtlciBbbGF0aXR1ZGVdPVwibGF0XCIgW2xvbmdpdHVkZV09XCJsbmdcIiBbbGFiZWxdPVwiJ00nXCI+XG4gKiAgICAgIDwvYWdtLW1hcmtlcj5cbiAqICAgIDwvYWdtLW1hcD5cbiAqICBgXG4gKiB9KVxuICogYGBgXG4gKi9cbkBEaXJlY3RpdmUoe1xuICBzZWxlY3RvcjogJ2FnbS1tYXJrZXInLFxuICBwcm92aWRlcnM6IFtcbiAgICB7IHByb3ZpZGU6IEZpdEJvdW5kc0FjY2Vzc29yLCB1c2VFeGlzdGluZzogZm9yd2FyZFJlZigoKSA9PiBBZ21NYXJrZXIpIH0sXG4gIF0sXG59KVxuZXhwb3J0IGNsYXNzIEFnbU1hcmtlciBpbXBsZW1lbnRzIE9uRGVzdHJveSwgT25DaGFuZ2VzLCBBZnRlckNvbnRlbnRJbml0LCBGaXRCb3VuZHNBY2Nlc3NvciB7XG4gIC8qKlxuICAgKiBUaGUgbGF0aXR1ZGUgcG9zaXRpb24gb2YgdGhlIG1hcmtlci5cbiAgICovXG4gIEBJbnB1dCgpIGxhdGl0dWRlOiBudW1iZXI7XG5cbiAgLyoqXG4gICAqIFRoZSBsb25naXR1ZGUgcG9zaXRpb24gb2YgdGhlIG1hcmtlci5cbiAgICovXG4gIEBJbnB1dCgpIGxvbmdpdHVkZTogbnVtYmVyO1xuXG4gIC8qKlxuICAgKiBUaGUgdGl0bGUgb2YgdGhlIG1hcmtlci5cbiAgICovXG4gIEBJbnB1dCgpIHRpdGxlOiBzdHJpbmc7XG5cbiAgLyoqXG4gICAqIFRoZSBsYWJlbCAoYSBzaW5nbGUgdXBwZXJjYXNlIGNoYXJhY3RlcikgZm9yIHRoZSBtYXJrZXIuXG4gICAqL1xuICBASW5wdXQoKSBsYWJlbDogc3RyaW5nIHwgZ29vZ2xlLm1hcHMuTWFya2VyTGFiZWw7XG5cbiAgLyoqXG4gICAqIElmIHRydWUsIHRoZSBtYXJrZXIgY2FuIGJlIGRyYWdnZWQuIERlZmF1bHQgdmFsdWUgaXMgZmFsc2UuXG4gICAqL1xuICAvLyB0c2xpbnQ6ZGlzYWJsZS1uZXh0LWxpbmU6bm8taW5wdXQtcmVuYW1lXG4gIEBJbnB1dCgnbWFya2VyRHJhZ2dhYmxlJykgZHJhZ2dhYmxlID0gZmFsc2U7XG5cbiAgLyoqXG4gICAqIEljb24gKHRoZSBVUkwgb2YgdGhlIGltYWdlKSBmb3IgdGhlIGZvcmVncm91bmQuXG4gICAqL1xuICBASW5wdXQoKSBpY29uVXJsOiBzdHJpbmcgfCBnb29nbGUubWFwcy5JY29uIHwgZ29vZ2xlLm1hcHMuU3ltYm9sO1xuXG4gIC8qKlxuICAgKiBJZiB0cnVlLCB0aGUgbWFya2VyIGlzIHZpc2libGVcbiAgICovXG4gIEBJbnB1dCgpIHZpc2libGUgPSB0cnVlO1xuXG4gIC8qKlxuICAgKiBXaGV0aGVyIHRvIGF1dG9tYXRpY2FsbHkgb3BlbiB0aGUgY2hpbGQgaW5mbyB3aW5kb3cgd2hlbiB0aGUgbWFya2VyIGlzIGNsaWNrZWQuXG4gICAqL1xuICBASW5wdXQoKSBvcGVuSW5mb1dpbmRvdyA9IHRydWU7XG5cbiAgLyoqXG4gICAqIFRoZSBtYXJrZXIncyBvcGFjaXR5IGJldHdlZW4gMC4wIGFuZCAxLjAuXG4gICAqL1xuICBASW5wdXQoKSBvcGFjaXR5ID0gMTtcblxuICAvKipcbiAgICogQWxsIG1hcmtlcnMgYXJlIGRpc3BsYXllZCBvbiB0aGUgbWFwIGluIG9yZGVyIG9mIHRoZWlyIHpJbmRleCwgd2l0aCBoaWdoZXIgdmFsdWVzIGRpc3BsYXlpbmcgaW5cbiAgICogZnJvbnQgb2YgbWFya2VycyB3aXRoIGxvd2VyIHZhbHVlcy4gQnkgZGVmYXVsdCwgbWFya2VycyBhcmUgZGlzcGxheWVkIGFjY29yZGluZyB0byB0aGVpclxuICAgKiB2ZXJ0aWNhbCBwb3NpdGlvbiBvbiBzY3JlZW4sIHdpdGggbG93ZXIgbWFya2VycyBhcHBlYXJpbmcgaW4gZnJvbnQgb2YgbWFya2VycyBmdXJ0aGVyIHVwIHRoZVxuICAgKiBzY3JlZW4uXG4gICAqL1xuICBASW5wdXQoKSB6SW5kZXggPSAxO1xuXG4gIC8qKlxuICAgKiBJZiB0cnVlLCB0aGUgbWFya2VyIGNhbiBiZSBjbGlja2VkLiBEZWZhdWx0IHZhbHVlIGlzIHRydWUuXG4gICAqL1xuICAvLyB0c2xpbnQ6ZGlzYWJsZS1uZXh0LWxpbmU6bm8taW5wdXQtcmVuYW1lXG4gIEBJbnB1dCgnbWFya2VyQ2xpY2thYmxlJykgY2xpY2thYmxlID0gdHJ1ZTtcblxuICAvKipcbiAgICogV2hpY2ggYW5pbWF0aW9uIHRvIHBsYXkgd2hlbiBtYXJrZXIgaXMgYWRkZWQgdG8gYSBtYXAuXG4gICAqIFRoaXMgY2FuIGJlICdCT1VOQ0UnIG9yICdEUk9QJ1xuICAgKi9cbiAgQElucHV0KCkgYW5pbWF0aW9uOiBrZXlvZiB0eXBlb2YgZ29vZ2xlLm1hcHMuQW5pbWF0aW9uO1xuXG4gIC8qKlxuICAgKiBUaGlzIGV2ZW50IGlzIGZpcmVkIHdoZW4gdGhlIG1hcmtlcidzIGFuaW1hdGlvbiBwcm9wZXJ0eSBjaGFuZ2VzLlxuICAgKi9cbiAgQE91dHB1dCgpIGFuaW1hdGlvbkNoYW5nZSA9IG5ldyBFdmVudEVtaXR0ZXI8a2V5b2YgdHlwZW9mIGdvb2dsZS5tYXBzLkFuaW1hdGlvbj4oKTtcblxuICAvKipcbiAgICogVGhpcyBldmVudCBlbWl0dGVyIGdldHMgZW1pdHRlZCB3aGVuIHRoZSB1c2VyIGNsaWNrcyBvbiB0aGUgbWFya2VyLlxuICAgKi9cbiAgQE91dHB1dCgpIG1hcmtlckNsaWNrOiBFdmVudEVtaXR0ZXI8QWdtTWFya2VyPiA9IG5ldyBFdmVudEVtaXR0ZXI8QWdtTWFya2VyPigpO1xuXG4gIC8qKlxuICAgKiBUaGlzIGV2ZW50IGVtaXR0ZXIgZ2V0cyBlbWl0dGVkIHdoZW4gdGhlIHVzZXIgY2xpY2tzIHR3aWNlIG9uIHRoZSBtYXJrZXIuXG4gICAqL1xuICBAT3V0cHV0KCkgbWFya2VyRGJsQ2xpY2s6IEV2ZW50RW1pdHRlcjxBZ21NYXJrZXI+ID0gbmV3IEV2ZW50RW1pdHRlcjxBZ21NYXJrZXI+KCk7XG5cbiAgLyoqXG4gICAqIFRoaXMgZXZlbnQgaXMgZmlyZWQgd2hlbiB0aGUgdXNlciByaWdodGNsaWNrcyBvbiB0aGUgbWFya2VyLlxuICAgKi9cbiAgQE91dHB1dCgpIG1hcmtlclJpZ2h0Q2xpY2s6IEV2ZW50RW1pdHRlcjx2b2lkPiA9IG5ldyBFdmVudEVtaXR0ZXI8dm9pZD4oKTtcblxuICAvKipcbiAgICogVGhpcyBldmVudCBpcyBmaXJlZCB3aGVuIHRoZSB1c2VyIHN0YXJ0cyBkcmFnZ2luZyB0aGUgbWFya2VyLlxuICAgKi9cbiAgQE91dHB1dCgpIGRyYWdTdGFydDogRXZlbnRFbWl0dGVyPGdvb2dsZS5tYXBzLk1vdXNlRXZlbnQ+ID0gbmV3IEV2ZW50RW1pdHRlcjxnb29nbGUubWFwcy5Nb3VzZUV2ZW50PigpO1xuXG4gIC8qKlxuICAgKiBUaGlzIGV2ZW50IGlzIHJlcGVhdGVkbHkgZmlyZWQgd2hpbGUgdGhlIHVzZXIgZHJhZ3MgdGhlIG1hcmtlci5cbiAgICovXG4gIC8vIHRzbGludDpkaXNhYmxlLW5leHQtbGluZTogbm8tb3V0cHV0LW5hdGl2ZVxuICBAT3V0cHV0KCkgZHJhZzogRXZlbnRFbWl0dGVyPGdvb2dsZS5tYXBzLk1vdXNlRXZlbnQ+ID0gbmV3IEV2ZW50RW1pdHRlcjxnb29nbGUubWFwcy5Nb3VzZUV2ZW50PigpO1xuXG4gIC8qKlxuICAgKiBUaGlzIGV2ZW50IGlzIGZpcmVkIHdoZW4gdGhlIHVzZXIgc3RvcHMgZHJhZ2dpbmcgdGhlIG1hcmtlci5cbiAgICovXG4gIEBPdXRwdXQoKSBkcmFnRW5kOiBFdmVudEVtaXR0ZXI8Z29vZ2xlLm1hcHMuTW91c2VFdmVudD4gPSBuZXcgRXZlbnRFbWl0dGVyPGdvb2dsZS5tYXBzLk1vdXNlRXZlbnQ+KCk7XG5cbiAgLyoqXG4gICAqIFRoaXMgZXZlbnQgaXMgZmlyZWQgd2hlbiB0aGUgdXNlciBtb3VzZXMgb3ZlciB0aGUgbWFya2VyLlxuICAgKi9cbiAgQE91dHB1dCgpIG1vdXNlT3ZlcjogRXZlbnRFbWl0dGVyPGdvb2dsZS5tYXBzLk1vdXNlRXZlbnQ+ID0gbmV3IEV2ZW50RW1pdHRlcjxnb29nbGUubWFwcy5Nb3VzZUV2ZW50PigpO1xuXG4gIC8qKlxuICAgKiBUaGlzIGV2ZW50IGlzIGZpcmVkIHdoZW4gdGhlIHVzZXIgbW91c2VzIG91dHNpZGUgdGhlIG1hcmtlci5cbiAgICovXG4gIEBPdXRwdXQoKSBtb3VzZU91dDogRXZlbnRFbWl0dGVyPGdvb2dsZS5tYXBzLk1vdXNlRXZlbnQ+ID0gbmV3IEV2ZW50RW1pdHRlcjxnb29nbGUubWFwcy5Nb3VzZUV2ZW50PigpO1xuXG4gIC8qKiBAaW50ZXJuYWwgKi9cbiAgQENvbnRlbnRDaGlsZHJlbihBZ21JbmZvV2luZG93KSBpbmZvV2luZG93OiBRdWVyeUxpc3Q8QWdtSW5mb1dpbmRvdz4gPSBuZXcgUXVlcnlMaXN0PEFnbUluZm9XaW5kb3c+KCk7XG5cbiAgcHJpdmF0ZSBfbWFya2VyQWRkZWRUb01hbmdlciA9IGZhbHNlO1xuICBwcml2YXRlIF9pZDogc3RyaW5nO1xuICBwcml2YXRlIF9vYnNlcnZhYmxlU3Vic2NyaXB0aW9uczogU3Vic2NyaXB0aW9uW10gPSBbXTtcblxuICBwcm90ZWN0ZWQgcmVhZG9ubHkgX2ZpdEJvdW5kc0RldGFpbHMkOiBSZXBsYXlTdWJqZWN0PEZpdEJvdW5kc0RldGFpbHM+ID0gbmV3IFJlcGxheVN1YmplY3Q8Rml0Qm91bmRzRGV0YWlscz4oMSk7XG5cbiAgY29uc3RydWN0b3IocHJpdmF0ZSBfbWFya2VyTWFuYWdlcjogTWFya2VyTWFuYWdlcikgeyB0aGlzLl9pZCA9IChtYXJrZXJJZCsrKS50b1N0cmluZygpOyB9XG5cbiAgLyogQGludGVybmFsICovXG4gIG5nQWZ0ZXJDb250ZW50SW5pdCgpIHtcbiAgICB0aGlzLmhhbmRsZUluZm9XaW5kb3dVcGRhdGUoKTtcbiAgICB0aGlzLmluZm9XaW5kb3cuY2hhbmdlcy5zdWJzY3JpYmUoKCkgPT4gdGhpcy5oYW5kbGVJbmZvV2luZG93VXBkYXRlKCkpO1xuICB9XG5cbiAgcHJpdmF0ZSBoYW5kbGVJbmZvV2luZG93VXBkYXRlKCkge1xuICAgIGlmICh0aGlzLmluZm9XaW5kb3cubGVuZ3RoID4gMSkge1xuICAgICAgdGhyb3cgbmV3IEVycm9yKCdFeHBlY3RlZCBubyBtb3JlIHRoYW4gb25lIGluZm8gd2luZG93LicpO1xuICAgIH1cbiAgICB0aGlzLmluZm9XaW5kb3cuZm9yRWFjaChtYXJrZXIgPT4ge1xuICAgICAgbWFya2VyLmhvc3RNYXJrZXIgPSB0aGlzO1xuICAgIH0pO1xuICB9XG5cbiAgLyoqIEBpbnRlcm5hbCAqL1xuICBuZ09uQ2hhbmdlcyhjaGFuZ2VzOiB7IFtrZXk6IHN0cmluZ106IFNpbXBsZUNoYW5nZSB9KSB7XG4gICAgaWYgKHR5cGVvZiB0aGlzLmxhdGl0dWRlID09PSAnc3RyaW5nJykge1xuICAgICAgdGhpcy5sYXRpdHVkZSA9IE51bWJlcih0aGlzLmxhdGl0dWRlKTtcbiAgICB9XG4gICAgaWYgKHR5cGVvZiB0aGlzLmxvbmdpdHVkZSA9PT0gJ3N0cmluZycpIHtcbiAgICAgIHRoaXMubG9uZ2l0dWRlID0gTnVtYmVyKHRoaXMubG9uZ2l0dWRlKTtcbiAgICB9XG4gICAgaWYgKHR5cGVvZiB0aGlzLmxhdGl0dWRlICE9PSAnbnVtYmVyJyB8fCB0eXBlb2YgdGhpcy5sb25naXR1ZGUgIT09ICdudW1iZXInKSB7XG4gICAgICByZXR1cm47XG4gICAgfVxuICAgIGlmICghdGhpcy5fbWFya2VyQWRkZWRUb01hbmdlcikge1xuICAgICAgdGhpcy5fbWFya2VyTWFuYWdlci5hZGRNYXJrZXIodGhpcyk7XG4gICAgICB0aGlzLl91cGRhdGVGaXRCb3VuZHNEZXRhaWxzKCk7XG4gICAgICB0aGlzLl9tYXJrZXJBZGRlZFRvTWFuZ2VyID0gdHJ1ZTtcbiAgICAgIHRoaXMuX2FkZEV2ZW50TGlzdGVuZXJzKCk7XG4gICAgICByZXR1cm47XG4gICAgfVxuICAgIC8vIHRzbGludDpkaXNhYmxlOiBuby1zdHJpbmctbGl0ZXJhbFxuICAgIGlmIChjaGFuZ2VzWydsYXRpdHVkZSddIHx8IGNoYW5nZXNbJ2xvbmdpdHVkZSddKSB7XG4gICAgICB0aGlzLl9tYXJrZXJNYW5hZ2VyLnVwZGF0ZU1hcmtlclBvc2l0aW9uKHRoaXMpO1xuICAgICAgdGhpcy5fdXBkYXRlRml0Qm91bmRzRGV0YWlscygpO1xuICAgIH1cbiAgICBpZiAoY2hhbmdlc1sndGl0bGUnXSkge1xuICAgICAgdGhpcy5fbWFya2VyTWFuYWdlci51cGRhdGVUaXRsZSh0aGlzKTtcbiAgICB9XG4gICAgaWYgKGNoYW5nZXNbJ2xhYmVsJ10pIHtcbiAgICAgIHRoaXMuX21hcmtlck1hbmFnZXIudXBkYXRlTGFiZWwodGhpcyk7XG4gICAgfVxuICAgIGlmIChjaGFuZ2VzWydkcmFnZ2FibGUnXSkge1xuICAgICAgdGhpcy5fbWFya2VyTWFuYWdlci51cGRhdGVEcmFnZ2FibGUodGhpcyk7XG4gICAgfVxuICAgIGlmIChjaGFuZ2VzWydpY29uVXJsJ10pIHtcbiAgICAgIHRoaXMuX21hcmtlck1hbmFnZXIudXBkYXRlSWNvbih0aGlzKTtcbiAgICB9XG4gICAgaWYgKGNoYW5nZXNbJ29wYWNpdHknXSkge1xuICAgICAgdGhpcy5fbWFya2VyTWFuYWdlci51cGRhdGVPcGFjaXR5KHRoaXMpO1xuICAgIH1cbiAgICBpZiAoY2hhbmdlc1sndmlzaWJsZSddKSB7XG4gICAgICB0aGlzLl9tYXJrZXJNYW5hZ2VyLnVwZGF0ZVZpc2libGUodGhpcyk7XG4gICAgfVxuICAgIGlmIChjaGFuZ2VzWyd6SW5kZXgnXSkge1xuICAgICAgdGhpcy5fbWFya2VyTWFuYWdlci51cGRhdGVaSW5kZXgodGhpcyk7XG4gICAgfVxuICAgIGlmIChjaGFuZ2VzWydjbGlja2FibGUnXSkge1xuICAgICAgdGhpcy5fbWFya2VyTWFuYWdlci51cGRhdGVDbGlja2FibGUodGhpcyk7XG4gICAgfVxuICAgIGlmIChjaGFuZ2VzWydhbmltYXRpb24nXSkge1xuICAgICAgdGhpcy5fbWFya2VyTWFuYWdlci51cGRhdGVBbmltYXRpb24odGhpcyk7XG4gICAgfVxuICAgIC8vIHRzbGludDplbmFibGU6IG5vLXN0cmluZy1saXRlcmFsXG5cbiAgfVxuXG4gIC8qKiBAaW50ZXJuYWwgKi9cbiAgZ2V0Rml0Qm91bmRzRGV0YWlscyQoKTogT2JzZXJ2YWJsZTxGaXRCb3VuZHNEZXRhaWxzPiB7XG4gICAgcmV0dXJuIHRoaXMuX2ZpdEJvdW5kc0RldGFpbHMkLmFzT2JzZXJ2YWJsZSgpO1xuICB9XG5cbiAgcHJvdGVjdGVkIF91cGRhdGVGaXRCb3VuZHNEZXRhaWxzKCkge1xuICAgIHRoaXMuX2ZpdEJvdW5kc0RldGFpbHMkLm5leHQoeyBsYXRMbmc6IHsgbGF0OiB0aGlzLmxhdGl0dWRlLCBsbmc6IHRoaXMubG9uZ2l0dWRlIH0gfSk7XG4gIH1cblxuICBwcml2YXRlIF9hZGRFdmVudExpc3RlbmVycygpIHtcbiAgICBjb25zdCBjcyA9IHRoaXMuX21hcmtlck1hbmFnZXIuY3JlYXRlRXZlbnRPYnNlcnZhYmxlKCdjbGljaycsIHRoaXMpLnN1YnNjcmliZSgoKSA9PiB7XG4gICAgICBpZiAodGhpcy5vcGVuSW5mb1dpbmRvdykge1xuICAgICAgICB0aGlzLmluZm9XaW5kb3cuZm9yRWFjaChpbmZvV2luZG93ID0+IGluZm9XaW5kb3cub3BlbigpKTtcbiAgICAgIH1cbiAgICAgIHRoaXMubWFya2VyQ2xpY2suZW1pdCh0aGlzKTtcbiAgICB9KTtcbiAgICB0aGlzLl9vYnNlcnZhYmxlU3Vic2NyaXB0aW9ucy5wdXNoKGNzKTtcblxuICAgIGNvbnN0IGRjcyA9IHRoaXMuX21hcmtlck1hbmFnZXIuY3JlYXRlRXZlbnRPYnNlcnZhYmxlKCdkYmxjbGljaycsIHRoaXMpLnN1YnNjcmliZSgoKSA9PiB7XG4gICAgICB0aGlzLm1hcmtlckRibENsaWNrLmVtaXQobnVsbCk7XG4gICAgfSk7XG4gICAgdGhpcy5fb2JzZXJ2YWJsZVN1YnNjcmlwdGlvbnMucHVzaChkY3MpO1xuXG4gICAgY29uc3QgcmMgPSB0aGlzLl9tYXJrZXJNYW5hZ2VyLmNyZWF0ZUV2ZW50T2JzZXJ2YWJsZSgncmlnaHRjbGljaycsIHRoaXMpLnN1YnNjcmliZSgoKSA9PiB7XG4gICAgICB0aGlzLm1hcmtlclJpZ2h0Q2xpY2suZW1pdChudWxsKTtcbiAgICB9KTtcbiAgICB0aGlzLl9vYnNlcnZhYmxlU3Vic2NyaXB0aW9ucy5wdXNoKHJjKTtcblxuICAgIGNvbnN0IGRzID1cbiAgICAgICAgdGhpcy5fbWFya2VyTWFuYWdlci5jcmVhdGVFdmVudE9ic2VydmFibGU8Z29vZ2xlLm1hcHMuTW91c2VFdmVudD4oJ2RyYWdzdGFydCcsIHRoaXMpXG4gICAgICAgICAgICAuc3Vic2NyaWJlKGUgPT4gdGhpcy5kcmFnU3RhcnQuZW1pdChlKSk7XG4gICAgdGhpcy5fb2JzZXJ2YWJsZVN1YnNjcmlwdGlvbnMucHVzaChkcyk7XG5cbiAgICBjb25zdCBkID1cbiAgICAgICAgdGhpcy5fbWFya2VyTWFuYWdlci5jcmVhdGVFdmVudE9ic2VydmFibGU8Z29vZ2xlLm1hcHMuTW91c2VFdmVudD4oJ2RyYWcnLCB0aGlzKVxuICAgICAgICAgIC5zdWJzY3JpYmUoZSA9PiB0aGlzLmRyYWcuZW1pdChlKSk7XG4gICAgdGhpcy5fb2JzZXJ2YWJsZVN1YnNjcmlwdGlvbnMucHVzaChkKTtcblxuICAgIGNvbnN0IGRlID1cbiAgICAgICAgdGhpcy5fbWFya2VyTWFuYWdlci5jcmVhdGVFdmVudE9ic2VydmFibGU8Z29vZ2xlLm1hcHMuTW91c2VFdmVudD4oJ2RyYWdlbmQnLCB0aGlzKVxuICAgICAgICAgIC5zdWJzY3JpYmUoZSA9PiB0aGlzLmRyYWdFbmQuZW1pdChlKSk7XG4gICAgdGhpcy5fb2JzZXJ2YWJsZVN1YnNjcmlwdGlvbnMucHVzaChkZSk7XG5cbiAgICBjb25zdCBtb3ZlciA9XG4gICAgICAgIHRoaXMuX21hcmtlck1hbmFnZXIuY3JlYXRlRXZlbnRPYnNlcnZhYmxlPGdvb2dsZS5tYXBzLk1vdXNlRXZlbnQ+KCdtb3VzZW92ZXInLCB0aGlzKVxuICAgICAgICAgIC5zdWJzY3JpYmUoZSA9PiB0aGlzLm1vdXNlT3Zlci5lbWl0KGUpKTtcbiAgICB0aGlzLl9vYnNlcnZhYmxlU3Vic2NyaXB0aW9ucy5wdXNoKG1vdmVyKTtcblxuICAgIGNvbnN0IG1vdXQgPVxuICAgICAgICB0aGlzLl9tYXJrZXJNYW5hZ2VyLmNyZWF0ZUV2ZW50T2JzZXJ2YWJsZTxnb29nbGUubWFwcy5Nb3VzZUV2ZW50PignbW91c2VvdXQnLCB0aGlzKVxuICAgICAgICAgIC5zdWJzY3JpYmUoZSA9PiB0aGlzLm1vdXNlT3V0LmVtaXQoZSkpO1xuICAgIHRoaXMuX29ic2VydmFibGVTdWJzY3JpcHRpb25zLnB1c2gobW91dCk7XG5cbiAgICBjb25zdCBhbkNobmcgPVxuICAgICAgdGhpcy5fbWFya2VyTWFuYWdlci5jcmVhdGVFdmVudE9ic2VydmFibGU8dm9pZD4oJ2FuaW1hdGlvbl9jaGFuZ2VkJywgdGhpcylcbiAgICAgICAgLnN1YnNjcmliZSgoKSA9PiB7XG4gICAgICAgICAgdGhpcy5hbmltYXRpb25DaGFuZ2UuZW1pdCh0aGlzLmFuaW1hdGlvbik7XG4gICAgICAgIH0pO1xuICAgIHRoaXMuX29ic2VydmFibGVTdWJzY3JpcHRpb25zLnB1c2goYW5DaG5nKTtcbiAgfVxuXG4gIC8qKiBAaW50ZXJuYWwgKi9cbiAgaWQoKTogc3RyaW5nIHsgcmV0dXJuIHRoaXMuX2lkOyB9XG5cbiAgLyoqIEBpbnRlcm5hbCAqL1xuICB0b1N0cmluZygpOiBzdHJpbmcgeyByZXR1cm4gJ0FnbU1hcmtlci0nICsgdGhpcy5faWQudG9TdHJpbmcoKTsgfVxuXG4gIC8qKiBAaW50ZXJuYWwgKi9cbiAgbmdPbkRlc3Ryb3koKSB7XG4gICAgdGhpcy5fbWFya2VyTWFuYWdlci5kZWxldGVNYXJrZXIodGhpcyk7XG4gICAgLy8gdW5zdWJzY3JpYmUgYWxsIHJlZ2lzdGVyZWQgb2JzZXJ2YWJsZSBzdWJzY3JpcHRpb25zXG4gICAgdGhpcy5fb2JzZXJ2YWJsZVN1YnNjcmlwdGlvbnMuZm9yRWFjaCgocykgPT4gcy51bnN1YnNjcmliZSgpKTtcbiAgfVxufVxuIl19