datepicker-input.js 61 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763
  1. /**
  2. * @fileoverview added by tsickle
  3. * @suppress {checkTypes,constantProperty,extraRequire,missingOverride,missingReturn,unusedPrivateMembers,uselessCode} checked by tsc
  4. */
  5. import { ChangeDetectorRef, ComponentFactoryResolver, Directive, ElementRef, EventEmitter, forwardRef, Inject, Input, NgZone, Output, Renderer2, TemplateRef, ViewContainerRef } from '@angular/core';
  6. import { DOCUMENT } from '@angular/common';
  7. import { NG_VALIDATORS, NG_VALUE_ACCESSOR } from '@angular/forms';
  8. import { ngbAutoClose } from '../util/autoclose';
  9. import { ngbFocusTrap } from '../util/focus-trap';
  10. import { positionElements } from '../util/positioning';
  11. import { NgbDateAdapter } from './adapters/ngb-date-adapter';
  12. import { NgbDatepicker } from './datepicker';
  13. import { NgbCalendar } from './ngb-calendar';
  14. import { NgbDate } from './ngb-date';
  15. import { NgbDateParserFormatter } from './ngb-date-parser-formatter';
  16. import { NgbInputDatepickerConfig } from './datepicker-input-config';
  17. import { NgbDatepickerConfig } from './datepicker-config';
  18. import { isString } from '../util/util';
  19. /** @type {?} */
  20. const NGB_DATEPICKER_VALUE_ACCESSOR = {
  21. provide: NG_VALUE_ACCESSOR,
  22. useExisting: forwardRef((/**
  23. * @return {?}
  24. */
  25. () => NgbInputDatepicker)),
  26. multi: true
  27. };
  28. /** @type {?} */
  29. const NGB_DATEPICKER_VALIDATOR = {
  30. provide: NG_VALIDATORS,
  31. useExisting: forwardRef((/**
  32. * @return {?}
  33. */
  34. () => NgbInputDatepicker)),
  35. multi: true
  36. };
  37. /**
  38. * A directive that allows to stick a datepicker popup to an input field.
  39. *
  40. * Manages interaction with the input field itself, does value formatting and provides forms integration.
  41. */
  42. export class NgbInputDatepicker {
  43. /**
  44. * @param {?} _parserFormatter
  45. * @param {?} _elRef
  46. * @param {?} _vcRef
  47. * @param {?} _renderer
  48. * @param {?} _cfr
  49. * @param {?} _ngZone
  50. * @param {?} _calendar
  51. * @param {?} _dateAdapter
  52. * @param {?} _document
  53. * @param {?} _changeDetector
  54. * @param {?} config
  55. */
  56. constructor(_parserFormatter, _elRef, _vcRef, _renderer, _cfr, _ngZone, _calendar, _dateAdapter, _document, _changeDetector, config) {
  57. this._parserFormatter = _parserFormatter;
  58. this._elRef = _elRef;
  59. this._vcRef = _vcRef;
  60. this._renderer = _renderer;
  61. this._cfr = _cfr;
  62. this._ngZone = _ngZone;
  63. this._calendar = _calendar;
  64. this._dateAdapter = _dateAdapter;
  65. this._document = _document;
  66. this._changeDetector = _changeDetector;
  67. this._cRef = null;
  68. this._disabled = false;
  69. this._elWithFocus = null;
  70. /**
  71. * An event emitted when user selects a date using keyboard or mouse.
  72. *
  73. * The payload of the event is currently selected `NgbDate`.
  74. *
  75. * \@since 1.1.1
  76. */
  77. this.dateSelect = new EventEmitter();
  78. /**
  79. * Event emitted right after the navigation happens and displayed month changes.
  80. *
  81. * See [`NgbDatepickerNavigateEvent`](#/components/datepicker/api#NgbDatepickerNavigateEvent) for the payload info.
  82. */
  83. this.navigate = new EventEmitter();
  84. /**
  85. * An event fired after closing datepicker window.
  86. *
  87. * \@since 4.2.0
  88. */
  89. this.closed = new EventEmitter();
  90. this._onChange = (/**
  91. * @param {?} _
  92. * @return {?}
  93. */
  94. (_) => { });
  95. this._onTouched = (/**
  96. * @return {?}
  97. */
  98. () => { });
  99. this._validatorChange = (/**
  100. * @return {?}
  101. */
  102. () => { });
  103. ['autoClose', 'container', 'positionTarget', 'placement'].forEach((/**
  104. * @param {?} input
  105. * @return {?}
  106. */
  107. input => this[input] = config[input]));
  108. this._zoneSubscription = _ngZone.onStable.subscribe((/**
  109. * @return {?}
  110. */
  111. () => this._updatePopupPosition()));
  112. }
  113. /**
  114. * @return {?}
  115. */
  116. get disabled() {
  117. return this._disabled;
  118. }
  119. /**
  120. * @param {?} value
  121. * @return {?}
  122. */
  123. set disabled(value) {
  124. this._disabled = value === '' || (value && value !== 'false');
  125. if (this.isOpen()) {
  126. this._cRef.instance.setDisabledState(this._disabled);
  127. }
  128. }
  129. /**
  130. * @param {?} fn
  131. * @return {?}
  132. */
  133. registerOnChange(fn) { this._onChange = fn; }
  134. /**
  135. * @param {?} fn
  136. * @return {?}
  137. */
  138. registerOnTouched(fn) { this._onTouched = fn; }
  139. /**
  140. * @param {?} fn
  141. * @return {?}
  142. */
  143. registerOnValidatorChange(fn) { this._validatorChange = fn; }
  144. /**
  145. * @param {?} isDisabled
  146. * @return {?}
  147. */
  148. setDisabledState(isDisabled) { this.disabled = isDisabled; }
  149. /**
  150. * @param {?} c
  151. * @return {?}
  152. */
  153. validate(c) {
  154. /** @type {?} */
  155. const value = c.value;
  156. if (value === null || value === undefined) {
  157. return null;
  158. }
  159. /** @type {?} */
  160. const ngbDate = this._fromDateStruct(this._dateAdapter.fromModel(value));
  161. if (!this._calendar.isValid(ngbDate)) {
  162. return { 'ngbDate': { invalid: c.value } };
  163. }
  164. if (this.minDate && ngbDate.before(NgbDate.from(this.minDate))) {
  165. return { 'ngbDate': { requiredBefore: this.minDate } };
  166. }
  167. if (this.maxDate && ngbDate.after(NgbDate.from(this.maxDate))) {
  168. return { 'ngbDate': { requiredAfter: this.maxDate } };
  169. }
  170. }
  171. /**
  172. * @param {?} value
  173. * @return {?}
  174. */
  175. writeValue(value) {
  176. this._model = this._fromDateStruct(this._dateAdapter.fromModel(value));
  177. this._writeModelValue(this._model);
  178. }
  179. /**
  180. * @param {?} value
  181. * @param {?=} updateView
  182. * @return {?}
  183. */
  184. manualDateChange(value, updateView = false) {
  185. /** @type {?} */
  186. const inputValueChanged = value !== this._inputValue;
  187. if (inputValueChanged) {
  188. this._inputValue = value;
  189. this._model = this._fromDateStruct(this._parserFormatter.parse(value));
  190. }
  191. if (inputValueChanged || !updateView) {
  192. this._onChange(this._model ? this._dateAdapter.toModel(this._model) : (value === '' ? null : value));
  193. }
  194. if (updateView && this._model) {
  195. this._writeModelValue(this._model);
  196. }
  197. }
  198. /**
  199. * @return {?}
  200. */
  201. isOpen() { return !!this._cRef; }
  202. /**
  203. * Opens the datepicker popup.
  204. *
  205. * If the related form control contains a valid date, the corresponding month will be opened.
  206. * @return {?}
  207. */
  208. open() {
  209. if (!this.isOpen()) {
  210. /** @type {?} */
  211. const cf = this._cfr.resolveComponentFactory(NgbDatepicker);
  212. this._cRef = this._vcRef.createComponent(cf);
  213. this._applyPopupStyling(this._cRef.location.nativeElement);
  214. this._applyDatepickerInputs(this._cRef.instance);
  215. this._subscribeForDatepickerOutputs(this._cRef.instance);
  216. this._cRef.instance.ngOnInit();
  217. this._cRef.instance.writeValue(this._dateAdapter.toModel(this._model));
  218. // date selection event handling
  219. this._cRef.instance.registerOnChange((/**
  220. * @param {?} selectedDate
  221. * @return {?}
  222. */
  223. (selectedDate) => {
  224. this.writeValue(selectedDate);
  225. this._onChange(selectedDate);
  226. this._onTouched();
  227. }));
  228. this._cRef.changeDetectorRef.detectChanges();
  229. this._cRef.instance.setDisabledState(this.disabled);
  230. if (this.container === 'body') {
  231. window.document.querySelector(this.container).appendChild(this._cRef.location.nativeElement);
  232. }
  233. // focus handling
  234. this._elWithFocus = this._document.activeElement;
  235. ngbFocusTrap(this._ngZone, this._cRef.location.nativeElement, this.closed, true);
  236. this._cRef.instance.focus();
  237. ngbAutoClose(this._ngZone, this._document, this.autoClose, (/**
  238. * @return {?}
  239. */
  240. () => this.close()), this.closed, [], [this._elRef.nativeElement, this._cRef.location.nativeElement]);
  241. }
  242. }
  243. /**
  244. * Closes the datepicker popup.
  245. * @return {?}
  246. */
  247. close() {
  248. if (this.isOpen()) {
  249. this._vcRef.remove(this._vcRef.indexOf(this._cRef.hostView));
  250. this._cRef = null;
  251. this.closed.emit();
  252. this._changeDetector.markForCheck();
  253. // restore focus
  254. /** @type {?} */
  255. let elementToFocus = this._elWithFocus;
  256. if (isString(this.restoreFocus)) {
  257. elementToFocus = this._document.querySelector(this.restoreFocus);
  258. }
  259. else if (this.restoreFocus !== undefined) {
  260. elementToFocus = this.restoreFocus;
  261. }
  262. // in IE document.activeElement can contain an object without 'focus()' sometimes
  263. if (elementToFocus && elementToFocus['focus']) {
  264. elementToFocus.focus();
  265. }
  266. else {
  267. this._document.body.focus();
  268. }
  269. }
  270. }
  271. /**
  272. * Toggles the datepicker popup.
  273. * @return {?}
  274. */
  275. toggle() {
  276. if (this.isOpen()) {
  277. this.close();
  278. }
  279. else {
  280. this.open();
  281. }
  282. }
  283. /**
  284. * Navigates to the provided date.
  285. *
  286. * With the default calendar we use ISO 8601: 'month' is 1=Jan ... 12=Dec.
  287. * If nothing or invalid date provided calendar will open current month.
  288. *
  289. * Use the `[startDate]` input as an alternative.
  290. * @param {?=} date
  291. * @return {?}
  292. */
  293. navigateTo(date) {
  294. if (this.isOpen()) {
  295. this._cRef.instance.navigateTo(date);
  296. }
  297. }
  298. /**
  299. * @return {?}
  300. */
  301. onBlur() { this._onTouched(); }
  302. /**
  303. * @return {?}
  304. */
  305. onFocus() { this._elWithFocus = this._elRef.nativeElement; }
  306. /**
  307. * @param {?} changes
  308. * @return {?}
  309. */
  310. ngOnChanges(changes) {
  311. if (changes['minDate'] || changes['maxDate']) {
  312. this._validatorChange();
  313. if (this.isOpen()) {
  314. if (changes['minDate']) {
  315. this._cRef.instance.minDate = this._dateAdapter.toModel(changes.minDate.currentValue);
  316. }
  317. if (changes['maxDate']) {
  318. this._cRef.instance.maxDate = this._dateAdapter.toModel(changes.maxDate.currentValue);
  319. }
  320. this._cRef.instance.ngOnChanges(changes);
  321. }
  322. }
  323. }
  324. /**
  325. * @return {?}
  326. */
  327. ngOnDestroy() {
  328. this.close();
  329. this._zoneSubscription.unsubscribe();
  330. }
  331. /**
  332. * @private
  333. * @param {?} datepickerInstance
  334. * @return {?}
  335. */
  336. _applyDatepickerInputs(datepickerInstance) {
  337. ['dayTemplate', 'dayTemplateData', 'displayMonths', 'firstDayOfWeek', 'footerTemplate', 'markDisabled', 'minDate',
  338. 'maxDate', 'navigation', 'outsideDays', 'showNavigation', 'showWeekdays', 'showWeekNumbers']
  339. .forEach((/**
  340. * @param {?} optionName
  341. * @return {?}
  342. */
  343. (optionName) => {
  344. if (this[optionName] !== undefined) {
  345. datepickerInstance[optionName] = this[optionName];
  346. }
  347. }));
  348. datepickerInstance.startDate = this.startDate || this._model;
  349. }
  350. /**
  351. * @private
  352. * @param {?} nativeElement
  353. * @return {?}
  354. */
  355. _applyPopupStyling(nativeElement) {
  356. this._renderer.addClass(nativeElement, 'dropdown-menu');
  357. this._renderer.addClass(nativeElement, 'show');
  358. if (this.container === 'body') {
  359. this._renderer.addClass(nativeElement, 'ngb-dp-body');
  360. }
  361. }
  362. /**
  363. * @private
  364. * @param {?} datepickerInstance
  365. * @return {?}
  366. */
  367. _subscribeForDatepickerOutputs(datepickerInstance) {
  368. datepickerInstance.navigate.subscribe((/**
  369. * @param {?} navigateEvent
  370. * @return {?}
  371. */
  372. navigateEvent => this.navigate.emit(navigateEvent)));
  373. datepickerInstance.dateSelect.subscribe((/**
  374. * @param {?} date
  375. * @return {?}
  376. */
  377. date => {
  378. this.dateSelect.emit(date);
  379. if (this.autoClose === true || this.autoClose === 'inside') {
  380. this.close();
  381. }
  382. }));
  383. }
  384. /**
  385. * @private
  386. * @param {?} model
  387. * @return {?}
  388. */
  389. _writeModelValue(model) {
  390. /** @type {?} */
  391. const value = this._parserFormatter.format(model);
  392. this._inputValue = value;
  393. this._renderer.setProperty(this._elRef.nativeElement, 'value', value);
  394. if (this.isOpen()) {
  395. this._cRef.instance.writeValue(this._dateAdapter.toModel(model));
  396. this._onTouched();
  397. }
  398. }
  399. /**
  400. * @private
  401. * @param {?} date
  402. * @return {?}
  403. */
  404. _fromDateStruct(date) {
  405. /** @type {?} */
  406. const ngbDate = date ? new NgbDate(date.year, date.month, date.day) : null;
  407. return this._calendar.isValid(ngbDate) ? ngbDate : null;
  408. }
  409. /**
  410. * @private
  411. * @return {?}
  412. */
  413. _updatePopupPosition() {
  414. if (!this._cRef) {
  415. return;
  416. }
  417. /** @type {?} */
  418. let hostElement;
  419. if (isString(this.positionTarget)) {
  420. hostElement = this._document.querySelector(this.positionTarget);
  421. }
  422. else if (this.positionTarget instanceof HTMLElement) {
  423. hostElement = this.positionTarget;
  424. }
  425. else {
  426. hostElement = this._elRef.nativeElement;
  427. }
  428. if (this.positionTarget && !hostElement) {
  429. throw new Error('ngbDatepicker could not find element declared in [positionTarget] to position against.');
  430. }
  431. positionElements(hostElement, this._cRef.location.nativeElement, this.placement, this.container === 'body');
  432. }
  433. }
  434. NgbInputDatepicker.decorators = [
  435. { type: Directive, args: [{
  436. selector: 'input[ngbDatepicker]',
  437. exportAs: 'ngbDatepicker',
  438. host: {
  439. '(input)': 'manualDateChange($event.target.value)',
  440. '(change)': 'manualDateChange($event.target.value, true)',
  441. '(focus)': 'onFocus()',
  442. '(blur)': 'onBlur()',
  443. '[disabled]': 'disabled'
  444. },
  445. providers: [
  446. NGB_DATEPICKER_VALUE_ACCESSOR, NGB_DATEPICKER_VALIDATOR,
  447. { provide: NgbDatepickerConfig, useExisting: NgbInputDatepickerConfig }
  448. ],
  449. },] }
  450. ];
  451. /** @nocollapse */
  452. NgbInputDatepicker.ctorParameters = () => [
  453. { type: NgbDateParserFormatter },
  454. { type: ElementRef },
  455. { type: ViewContainerRef },
  456. { type: Renderer2 },
  457. { type: ComponentFactoryResolver },
  458. { type: NgZone },
  459. { type: NgbCalendar },
  460. { type: NgbDateAdapter },
  461. { type: undefined, decorators: [{ type: Inject, args: [DOCUMENT,] }] },
  462. { type: ChangeDetectorRef },
  463. { type: NgbInputDatepickerConfig }
  464. ];
  465. NgbInputDatepicker.propDecorators = {
  466. autoClose: [{ type: Input }],
  467. dayTemplate: [{ type: Input }],
  468. dayTemplateData: [{ type: Input }],
  469. displayMonths: [{ type: Input }],
  470. firstDayOfWeek: [{ type: Input }],
  471. footerTemplate: [{ type: Input }],
  472. markDisabled: [{ type: Input }],
  473. minDate: [{ type: Input }],
  474. maxDate: [{ type: Input }],
  475. navigation: [{ type: Input }],
  476. outsideDays: [{ type: Input }],
  477. placement: [{ type: Input }],
  478. restoreFocus: [{ type: Input }],
  479. showWeekdays: [{ type: Input }],
  480. showWeekNumbers: [{ type: Input }],
  481. startDate: [{ type: Input }],
  482. container: [{ type: Input }],
  483. positionTarget: [{ type: Input }],
  484. dateSelect: [{ type: Output }],
  485. navigate: [{ type: Output }],
  486. closed: [{ type: Output }],
  487. disabled: [{ type: Input }]
  488. };
  489. if (false) {
  490. /**
  491. * @type {?}
  492. * @private
  493. */
  494. NgbInputDatepicker.prototype._cRef;
  495. /**
  496. * @type {?}
  497. * @private
  498. */
  499. NgbInputDatepicker.prototype._disabled;
  500. /**
  501. * @type {?}
  502. * @private
  503. */
  504. NgbInputDatepicker.prototype._elWithFocus;
  505. /**
  506. * @type {?}
  507. * @private
  508. */
  509. NgbInputDatepicker.prototype._model;
  510. /**
  511. * @type {?}
  512. * @private
  513. */
  514. NgbInputDatepicker.prototype._inputValue;
  515. /**
  516. * @type {?}
  517. * @private
  518. */
  519. NgbInputDatepicker.prototype._zoneSubscription;
  520. /**
  521. * Indicates whether the datepicker popup should be closed automatically after date selection / outside click or not.
  522. *
  523. * * `true` - the popup will close on both date selection and outside click.
  524. * * `false` - the popup can only be closed manually via `close()` or `toggle()` methods.
  525. * * `"inside"` - the popup will close on date selection, but not outside clicks.
  526. * * `"outside"` - the popup will close only on the outside click and not on date selection/inside clicks.
  527. *
  528. * \@since 3.0.0
  529. * @type {?}
  530. */
  531. NgbInputDatepicker.prototype.autoClose;
  532. /**
  533. * The reference to a custom template for the day.
  534. *
  535. * Allows to completely override the way a day 'cell' in the calendar is displayed.
  536. *
  537. * See [`DayTemplateContext`](#/components/datepicker/api#DayTemplateContext) for the data you get inside.
  538. * @type {?}
  539. */
  540. NgbInputDatepicker.prototype.dayTemplate;
  541. /**
  542. * The callback to pass any arbitrary data to the template cell via the
  543. * [`DayTemplateContext`](#/components/datepicker/api#DayTemplateContext)'s `data` parameter.
  544. *
  545. * `current` is the month that is currently displayed by the datepicker.
  546. *
  547. * \@since 3.3.0
  548. * @type {?}
  549. */
  550. NgbInputDatepicker.prototype.dayTemplateData;
  551. /**
  552. * The number of months to display.
  553. * @type {?}
  554. */
  555. NgbInputDatepicker.prototype.displayMonths;
  556. /**
  557. * The first day of the week.
  558. *
  559. * With default calendar we use ISO 8601: 'weekday' is 1=Mon ... 7=Sun.
  560. * @type {?}
  561. */
  562. NgbInputDatepicker.prototype.firstDayOfWeek;
  563. /**
  564. * The reference to the custom template for the datepicker footer.
  565. *
  566. * \@since 3.3.0
  567. * @type {?}
  568. */
  569. NgbInputDatepicker.prototype.footerTemplate;
  570. /**
  571. * The callback to mark some dates as disabled.
  572. *
  573. * It is called for each new date when navigating to a different month.
  574. *
  575. * `current` is the month that is currently displayed by the datepicker.
  576. * @type {?}
  577. */
  578. NgbInputDatepicker.prototype.markDisabled;
  579. /**
  580. * The earliest date that can be displayed or selected. Also used for form validation.
  581. *
  582. * If not provided, 'year' select box will display 10 years before the current month.
  583. * @type {?}
  584. */
  585. NgbInputDatepicker.prototype.minDate;
  586. /**
  587. * The latest date that can be displayed or selected. Also used for form validation.
  588. *
  589. * If not provided, 'year' select box will display 10 years after the current month.
  590. * @type {?}
  591. */
  592. NgbInputDatepicker.prototype.maxDate;
  593. /**
  594. * Navigation type.
  595. *
  596. * * `"select"` - select boxes for month and navigation arrows
  597. * * `"arrows"` - only navigation arrows
  598. * * `"none"` - no navigation visible at all
  599. * @type {?}
  600. */
  601. NgbInputDatepicker.prototype.navigation;
  602. /**
  603. * The way of displaying days that don't belong to the current month.
  604. *
  605. * * `"visible"` - days are visible
  606. * * `"hidden"` - days are hidden, white space preserved
  607. * * `"collapsed"` - days are collapsed, so the datepicker height might change between months
  608. *
  609. * For the 2+ months view, days in between months are never shown.
  610. * @type {?}
  611. */
  612. NgbInputDatepicker.prototype.outsideDays;
  613. /**
  614. * The preferred placement of the datepicker popup.
  615. *
  616. * Possible values are `"top"`, `"top-left"`, `"top-right"`, `"bottom"`, `"bottom-left"`,
  617. * `"bottom-right"`, `"left"`, `"left-top"`, `"left-bottom"`, `"right"`, `"right-top"`,
  618. * `"right-bottom"`
  619. *
  620. * Accepts an array of strings or a string with space separated possible values.
  621. *
  622. * The default order of preference is `"bottom-left bottom-right top-left top-right"`
  623. *
  624. * Please see the [positioning overview](#/positioning) for more details.
  625. * @type {?}
  626. */
  627. NgbInputDatepicker.prototype.placement;
  628. /**
  629. * If `true`, when closing datepicker will focus element that was focused before datepicker was opened.
  630. *
  631. * Alternatively you could provide a selector or an `HTMLElement` to focus. If the element doesn't exist or invalid,
  632. * we'll fallback to focus document body.
  633. *
  634. * \@since 5.2.0
  635. * @type {?}
  636. */
  637. NgbInputDatepicker.prototype.restoreFocus;
  638. /**
  639. * If `true`, weekdays will be displayed.
  640. * @type {?}
  641. */
  642. NgbInputDatepicker.prototype.showWeekdays;
  643. /**
  644. * If `true`, week numbers will be displayed.
  645. * @type {?}
  646. */
  647. NgbInputDatepicker.prototype.showWeekNumbers;
  648. /**
  649. * The date to open calendar with.
  650. *
  651. * With the default calendar we use ISO 8601: 'month' is 1=Jan ... 12=Dec.
  652. * If nothing or invalid date is provided, calendar will open with current month.
  653. *
  654. * You could use `navigateTo(date)` method as an alternative.
  655. * @type {?}
  656. */
  657. NgbInputDatepicker.prototype.startDate;
  658. /**
  659. * A selector specifying the element the datepicker popup should be appended to.
  660. *
  661. * Currently only supports `"body"`.
  662. * @type {?}
  663. */
  664. NgbInputDatepicker.prototype.container;
  665. /**
  666. * A css selector or html element specifying the element the datepicker popup should be positioned against.
  667. *
  668. * By default the input is used as a target.
  669. *
  670. * \@since 4.2.0
  671. * @type {?}
  672. */
  673. NgbInputDatepicker.prototype.positionTarget;
  674. /**
  675. * An event emitted when user selects a date using keyboard or mouse.
  676. *
  677. * The payload of the event is currently selected `NgbDate`.
  678. *
  679. * \@since 1.1.1
  680. * @type {?}
  681. */
  682. NgbInputDatepicker.prototype.dateSelect;
  683. /**
  684. * Event emitted right after the navigation happens and displayed month changes.
  685. *
  686. * See [`NgbDatepickerNavigateEvent`](#/components/datepicker/api#NgbDatepickerNavigateEvent) for the payload info.
  687. * @type {?}
  688. */
  689. NgbInputDatepicker.prototype.navigate;
  690. /**
  691. * An event fired after closing datepicker window.
  692. *
  693. * \@since 4.2.0
  694. * @type {?}
  695. */
  696. NgbInputDatepicker.prototype.closed;
  697. /**
  698. * @type {?}
  699. * @private
  700. */
  701. NgbInputDatepicker.prototype._onChange;
  702. /**
  703. * @type {?}
  704. * @private
  705. */
  706. NgbInputDatepicker.prototype._onTouched;
  707. /**
  708. * @type {?}
  709. * @private
  710. */
  711. NgbInputDatepicker.prototype._validatorChange;
  712. /**
  713. * @type {?}
  714. * @private
  715. */
  716. NgbInputDatepicker.prototype._parserFormatter;
  717. /**
  718. * @type {?}
  719. * @private
  720. */
  721. NgbInputDatepicker.prototype._elRef;
  722. /**
  723. * @type {?}
  724. * @private
  725. */
  726. NgbInputDatepicker.prototype._vcRef;
  727. /**
  728. * @type {?}
  729. * @private
  730. */
  731. NgbInputDatepicker.prototype._renderer;
  732. /**
  733. * @type {?}
  734. * @private
  735. */
  736. NgbInputDatepicker.prototype._cfr;
  737. /**
  738. * @type {?}
  739. * @private
  740. */
  741. NgbInputDatepicker.prototype._ngZone;
  742. /**
  743. * @type {?}
  744. * @private
  745. */
  746. NgbInputDatepicker.prototype._calendar;
  747. /**
  748. * @type {?}
  749. * @private
  750. */
  751. NgbInputDatepicker.prototype._dateAdapter;
  752. /**
  753. * @type {?}
  754. * @private
  755. */
  756. NgbInputDatepicker.prototype._document;
  757. /**
  758. * @type {?}
  759. * @private
  760. */
  761. NgbInputDatepicker.prototype._changeDetector;
  762. }
  763. //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiZGF0ZXBpY2tlci1pbnB1dC5qcyIsInNvdXJjZVJvb3QiOiJuZzovL0BuZy1ib290c3RyYXAvbmctYm9vdHN0cmFwLyIsInNvdXJjZXMiOlsiZGF0ZXBpY2tlci9kYXRlcGlja2VyLWlucHV0LnRzIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiI7Ozs7QUFBQSxPQUFPLEVBQ0wsaUJBQWlCLEVBQ2pCLHdCQUF3QixFQUV4QixTQUFTLEVBQ1QsVUFBVSxFQUNWLFlBQVksRUFDWixVQUFVLEVBQ1YsTUFBTSxFQUNOLEtBQUssRUFDTCxNQUFNLEVBR04sTUFBTSxFQUNOLFNBQVMsRUFFVCxXQUFXLEVBQ1gsZ0JBQWdCLEVBQ2pCLE1BQU0sZUFBZSxDQUFDO0FBQ3ZCLE9BQU8sRUFBQyxRQUFRLEVBQUMsTUFBTSxpQkFBaUIsQ0FBQztBQUN6QyxPQUFPLEVBQXdDLGFBQWEsRUFBRSxpQkFBaUIsRUFBWSxNQUFNLGdCQUFnQixDQUFDO0FBRWxILE9BQU8sRUFBQyxZQUFZLEVBQUMsTUFBTSxtQkFBbUIsQ0FBQztBQUMvQyxPQUFPLEVBQUMsWUFBWSxFQUFDLE1BQU0sb0JBQW9CLENBQUM7QUFDaEQsT0FBTyxFQUFpQixnQkFBZ0IsRUFBQyxNQUFNLHFCQUFxQixDQUFDO0FBRXJFLE9BQU8sRUFBQyxjQUFjLEVBQUMsTUFBTSw2QkFBNkIsQ0FBQztBQUMzRCxPQUFPLEVBQUMsYUFBYSxFQUE2QixNQUFNLGNBQWMsQ0FBQztBQUV2RSxPQUFPLEVBQUMsV0FBVyxFQUFDLE1BQU0sZ0JBQWdCLENBQUM7QUFDM0MsT0FBTyxFQUFDLE9BQU8sRUFBQyxNQUFNLFlBQVksQ0FBQztBQUNuQyxPQUFPLEVBQUMsc0JBQXNCLEVBQUMsTUFBTSw2QkFBNkIsQ0FBQztBQUVuRSxPQUFPLEVBQUMsd0JBQXdCLEVBQUMsTUFBTSwyQkFBMkIsQ0FBQztBQUNuRSxPQUFPLEVBQUMsbUJBQW1CLEVBQUMsTUFBTSxxQkFBcUIsQ0FBQztBQUN4RCxPQUFPLEVBQUMsUUFBUSxFQUFDLE1BQU0sY0FB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Ozs7SUFVdEQsNkNBQXlGOzs7OztJQUt6RiwyQ0FBK0I7Ozs7Ozs7SUFPL0IsNENBQWdDOzs7Ozs7O0lBT2hDLDRDQUEwQzs7Ozs7Ozs7O0lBUzFDLDBDQUEwRjs7Ozs7OztJQU8xRixxQ0FBZ0M7Ozs7Ozs7SUFPaEMscUNBQWdDOzs7Ozs7Ozs7SUFTaEMsd0NBQWtEOzs7Ozs7Ozs7OztJQVdsRCx5Q0FBeUQ7Ozs7Ozs7Ozs7Ozs7OztJQWV6RCx1Q0FBbUM7Ozs7Ozs7Ozs7SUFVbkMsMENBQW1EOzs7OztJQUtuRCwwQ0FBK0I7Ozs7O0lBSy9CLDZDQUFrQzs7Ozs7Ozs7OztJQVVsQyx1Q0FBZ0U7Ozs7Ozs7SUFPaEUsdUNBQTJCOzs7Ozs7Ozs7SUFTM0IsNENBQThDOzs7Ozs7Ozs7SUFTOUMsd0NBQW1EOzs7Ozs7O0lBT25ELHNDQUFvRTs7Ozs7OztJQU9wRSxvQ0FBNEM7Ozs7O0lBYzVDLHVDQUFtQzs7Ozs7SUFDbkMsd0NBQThCOzs7OztJQUM5Qiw4Q0FBb0M7Ozs7O0lBSWhDLDhDQUFnRDs7Ozs7SUFBRSxvQ0FBNEM7Ozs7O0lBQzlGLG9DQUFnQzs7Ozs7SUFBRSx1Q0FBNEI7Ozs7O0lBQUUsa0NBQXNDOzs7OztJQUN0RyxxQ0FBdUI7Ozs7O0lBQUUsdUNBQThCOzs7OztJQUFFLDBDQUF5Qzs7Ozs7SUFDbEcsdUNBQXdDOzs7OztJQUFFLDZDQUEwQyIsInNvdXJjZXNDb250ZW50IjpbImltcG9ydCB7XG4gIENoYW5nZURldGVjdG9yUmVmLFxuICBDb21wb25lbnRGYWN0b3J5UmVzb2x2ZXIsXG4gIENvbXBvbmVudFJlZixcbiAgRGlyZWN0aXZlLFxuICBFbGVtZW50UmVmLFxuICBFdmVudEVtaXR0ZXIsXG4gIGZvcndhcmRSZWYsXG4gIEluamVjdCxcbiAgSW5wdXQsXG4gIE5nWm9uZSxcbiAgT25DaGFuZ2VzLFxuICBPbkRlc3Ryb3ksXG4gIE91dHB1dCxcbiAgUmVuZGVyZXIyLFxuICBTaW1wbGVDaGFuZ2VzLFxuICBUZW1wbGF0ZVJlZixcbiAgVmlld0NvbnRhaW5lclJlZlxufSBmcm9tICdAYW5ndWxhci9jb3JlJztcbmltcG9ydCB7RE9DVU1FTlR9IGZyb20gJ0Bhbmd1bGFyL2NvbW1vbic7XG5pbXBvcnQge0Fic3RyYWN0Q29udHJvbCwgQ29udHJvbFZhbHVlQWNjZXNzb3IsIE5HX1ZBTElEQVRPUlMsIE5HX1ZBTFVFX0FDQ0VTU09SLCBWYWxpZGF0b3J9IGZyb20gJ0Bhbmd1bGFyL2Zvcm1zJztcblxuaW1wb3J0IHtuZ2JBdXRvQ2xvc2V9IGZyb20gJy4uL3V0aWwvYXV0b2Nsb3NlJztcbmltcG9ydCB7bmdiRm9jdXNUcmFwfSBmcm9tICcuLi91dGlsL2ZvY3VzLXRyYXAnO1xuaW1wb3J0IHtQbGFjZW1lbnRBcnJheSwgcG9zaXRpb25FbGVtZW50c30gZnJvbSAnLi4vdXRpbC9wb3NpdGlvbmluZyc7XG5cbmltcG9ydCB7TmdiRGF0ZUFkYXB0ZXJ9IGZyb20gJy4vYWRhcHRlcnMvbmdiLWRhdGUtYWRhcHRlcic7XG5pbXBvcnQge05nYkRhdGVwaWNrZXIsIE5nYkRhdGVwaWNrZXJOYXZpZ2F0ZUV2ZW50fSBmcm9tICcuL2RhdGVwaWNrZXInO1xuaW1wb3J0IHtEYXlUZW1wbGF0ZUNvbnRleHR9IGZyb20gJy4vZGF0ZXBpY2tlci1kYXktdGVtcGxhdGUtY29udGV4dCc7XG5pbXBvcnQge05nYkNhbGVuZGFyfSBmcm9tICcuL25nYi1jYWxlbmRhcic7XG5pbXBvcnQge05nYkRhdGV9IGZyb20gJy4vbmdiLWRhdGUnO1xuaW1wb3J0IHtOZ2JEYXRlUGFyc2VyRm9ybWF0dGVyfSBmcm9tICcuL25nYi1kYXRlLXBhcnNlci1mb3JtYXR0ZXInO1xuaW1wb3J0IHtOZ2JEYXRlU3RydWN0fSBmcm9tICcuL25nYi1kYXRlLXN0cnVjdCc7XG5pbXBvcnQge05nYklucHV0RGF0ZXBpY2tlckNvbmZpZ30gZnJvbSAnLi9kYXRlcGlja2VyLWlucHV0LWNvbmZpZyc7XG5pbXBvcnQge05nYkRhdGVwaWNrZXJDb25maWd9IGZyb20gJy4vZGF0ZXBpY2tlci1jb25maWcnO1xuaW1wb3J0IHtpc1N0cmluZ30gZnJvbSAnLi4vdXRpbC91dGlsJztcblxuY29uc3QgTkdCX0RBVEVQSUNLRVJfVkFMVUVfQUNDRVNTT1IgPSB7XG4gIHByb3ZpZGU6IE5HX1ZBTFVFX0FDQ0VTU09SLFxuICB1c2VFeGlzdGluZzogZm9yd2FyZFJlZigoKSA9PiBOZ2JJbnB1dERhdGVwaWNrZXIpLFxuICBtdWx0aTogdHJ1ZVxufTtcblxuY29uc3QgTkdCX0RBVEVQSUNLRVJfVkFMSURBVE9SID0ge1xuICBwcm92aWRlOiBOR19WQUxJREFUT1JTLFxuICB1c2VFeGlzdGluZzogZm9yd2FyZFJlZigoKSA9PiBOZ2JJbnB1dERhdGVwaWNrZXIpLFxuICBtdWx0aTogdHJ1ZVxufTtcblxuLyoqXG4gKiBBIGRpcmVjdGl2ZSB0aGF0IGFsbG93cyB0byBzdGljayBhIGRhdGVwaWNrZXIgcG9wdXAgdG8gYW4gaW5wdXQgZmllbGQuXG4gKlxuICogTWFuYWdlcyBpbnRlcmFjdGlvbiB3aXRoIHRoZSBpbnB1dCBmaWVsZCBpdHNlbGYsIGRvZXMgdmFsdWUgZm9ybWF0dGluZyBhbmQgcHJvdmlkZXMgZm9ybXMgaW50ZWdyYXRpb24uXG4gKi9cbkBEaXJlY3RpdmUoe1xuICBzZWxlY3RvcjogJ2lucHV0W25nYkRhdGVwaWNrZXJdJyxcbiAgZXhwb3J0QXM6ICduZ2JEYXRlcGlja2VyJyxcbiAgaG9zdDoge1xuICAgICcoaW5wdXQpJzogJ21hbnVhbERhdGVDaGFuZ2UoJGV2ZW50LnRhcmdldC52YWx1ZSknLFxuICAgICcoY2hhbmdlKSc6ICdtYW51YWxEYXRlQ2hhbmdlKCRldmVudC50YXJnZXQudmFsdWUsIHRydWUpJyxcbiAgICAnKGZvY3VzKSc6ICdvbkZvY3VzKCknLFxuICAgICcoYmx1ciknOiAnb25CbHVyKCknLFxuICAgICdbZGlzYWJsZWRdJzogJ2Rpc2FibGVkJ1xuICB9LFxuICBwcm92aWRlcnM6IFtcbiAgICBOR0JfREFURVBJQ0tFUl9WQUxVRV9BQ0NFU1NPUiwgTkdCX0RBVEVQSUNLRVJfVkFMSURBVE9SLFxuICAgIHtwcm92aWRlOiBOZ2JEYXRlcGlja2VyQ29uZmlnLCB1c2VFeGlzdGluZzogTmdiSW5wdXREYXRlcGlja2VyQ29uZmlnfVxuICBdLFxufSlcbmV4cG9ydCBjbGFzcyBOZ2JJbnB1dERhdGVwaWNrZXIgaW1wbGVtZW50cyBPbkNoYW5nZXMsXG4gICAgT25EZXN0cm95LCBDb250cm9sVmFsdWVBY2Nlc3NvciwgVmFsaWRhdG9yIHtcbiAgcHJpdmF0ZSBfY1JlZjogQ29tcG9uZW50UmVmPE5nYkRhdGVwaWNrZXI+ID0gbnVsbDtcbiAgcHJpdmF0ZSBfZGlzYWJsZWQgPSBmYWxzZTtcbiAgcHJpdmF0ZSBfZWxXaXRoRm9jdXMgPSBudWxsO1xuICBwcml2YXRlIF9tb2RlbDogTmdiRGF0ZTtcbiAgcHJpdmF0ZSBfaW5wdXRWYWx1ZTogc3RyaW5nO1xuICBwcml2YXRlIF96b25lU3Vic2NyaXB0aW9uOiBhbnk7XG5cbiAgLyoqXG4gICAqIEluZGljYXRlcyB3aGV0aGVyIHRoZSBkYXRlcGlja2VyIHBvcHVwIHNob3VsZCBiZSBjbG9zZWQgYXV0b21hdGljYWxseSBhZnRlciBkYXRlIHNlbGVjdGlvbiAvIG91dHNpZGUgY2xpY2sgb3Igbm90LlxuICAgKlxuICAgKiAqIGB0cnVlYCAtIHRoZSBwb3B1cCB3aWxsIGNsb3NlIG9uIGJvdGggZGF0ZSBzZWxlY3Rpb24gYW5kIG91dHNpZGUgY2xpY2suXG4gICAqICogYGZhbHNlYCAtIHRoZSBwb3B1cCBjYW4gb25seSBiZSBjbG9zZWQgbWFudWFsbHkgdmlhIGBjbG9zZSgpYCBvciBgdG9nZ2xlKClgIG1ldGhvZHMuXG4gICAqICogYFwiaW5zaWRlXCJgIC0gdGhlIHBvcHVwIHdpbGwgY2xvc2Ugb24gZGF0ZSBzZWxlY3Rpb24sIGJ1dCBub3Qgb3V0c2lkZSBjbGlja3MuXG4gICAqICogYFwib3V0c2lkZVwiYCAtIHRoZSBwb3B1cCB3aWxsIGNsb3NlIG9ubHkgb24gdGhlIG91dHNpZGUgY2xpY2sgYW5kIG5vdCBvbiBkYXRlIHNlbGVjdGlvbi9pbnNpZGUgY2xpY2tzLlxuICAgKlxuICAgKiBAc2luY2UgMy4wLjBcbiAgICovXG4gIEBJbnB1dCgpIGF1dG9DbG9zZTogYm9vbGVhbiB8ICdpbnNpZGUnIHwgJ291dHNpZGUnO1xuXG4gIC8qKlxuICAgKiBUaGUgcmVmZXJlbmNlIHRvIGEgY3VzdG9tIHRlbXBsYXRlIGZvciB0aGUgZGF5LlxuICAgKlxuICAgKiBBbGxvd3MgdG8gY29tcGxldGVseSBvdmVycmlkZSB0aGUgd2F5IGEgZGF5ICdjZWxsJyBpbiB0aGUgY2FsZW5kYXIgaXMgZGlzcGxheWVkLlxuICAgKlxuICAgKiBTZWUgW2BEYXlUZW1wbGF0ZUNvbnRleHRgXSgjL2NvbXBvbmVudHMvZGF0ZXBpY2tlci9hcGkjRGF5VGVtcGxhdGVDb250ZXh0KSBmb3IgdGhlIGRhdGEgeW91IGdldCBpbnNpZGUuXG4gICAqL1xuICBASW5wdXQoKSBkYXlUZW1wbGF0ZTogVGVtcGxhdGVSZWY8RGF5VGVtcGxhdGVDb250ZXh0PjtcblxuICAvKipcbiAgICogVGhlIGNhbGxiYWNrIHRvIHBhc3MgYW55IGFyYml0cmFyeSBkYXRhIHRvIHRoZSB0ZW1wbGF0ZSBjZWxsIHZpYSB0aGVcbiAgICogW2BEYXlUZW1wbGF0ZUNvbnRleHRgXSgjL2NvbXBvbmVudHMvZGF0ZXBpY2tlci9hcGkjRGF5VGVtcGxhdGVDb250ZXh0KSdzIGBkYXRhYCBwYXJhbWV0ZXIuXG4gICAqXG4gICAqIGBjdXJyZW50YCBpcyB0aGUgbW9udGggdGhhdCBpcyBjdXJyZW50bHkgZGlzcGxheWVkIGJ5IHRoZSBkYXRlcGlja2VyLlxuICAgKlxuICAgKiBAc2luY2UgMy4zLjBcbiAgICovXG4gIEBJbnB1dCgpIGRheVRlbXBsYXRlRGF0YTogKGRhdGU6IE5nYkRhdGUsIGN1cnJlbnQ6IHt5ZWFyOiBudW1iZXIsIG1vbnRoOiBudW1iZXJ9KSA9PiBhbnk7XG5cbiAgLyoqXG4gICAqIFRoZSBudW1iZXIgb2YgbW9udGhzIHRvIGRpc3BsYXkuXG4gICAqL1xuICBASW5wdXQoKSBkaXNwbGF5TW9udGhzOiBudW1iZXI7XG5cbiAgLyoqXG4gICAqIFRoZSBmaXJzdCBkYXkgb2YgdGhlIHdlZWsuXG4gICAqXG4gICAqIFdpdGggZGVmYXVsdCBjYWxlbmRhciB3ZSB1c2UgSVNPIDg2MDE6ICd3ZWVrZGF5JyBpcyAxPU1vbiAuLi4gNz1TdW4uXG4gICAqL1xuICBASW5wdXQoKSBmaXJzdERheU9mV2VlazogbnVtYmVyO1xuXG4gIC8qKlxuICAgKiBUaGUgcmVmZXJlbmNlIHRvIHRoZSBjdXN0b20gdGVtcGxhdGUgZm9yIHRoZSBkYXRlcGlja2VyIGZvb3Rlci5cbiAgICpcbiAgICogQHNpbmNlIDMuMy4wXG4gICAqL1xuICBASW5wdXQoKSBmb290ZXJUZW1wbGF0ZTogVGVtcGxhdGVSZWY8YW55PjtcblxuICAvKipcbiAgICogVGhlIGNhbGxiYWNrIHRvIG1hcmsgc29tZSBkYXRlcyBhcyBkaXNhYmxlZC5cbiAgICpcbiAgICogSXQgaXMgY2FsbGVkIGZvciBlYWNoIG5ldyBkYXRlIHdoZW4gbmF2aWdhdGluZyB0byBhIGRpZmZlcmVudCBtb250aC5cbiAgICpcbiAgICogYGN1cnJlbnRgIGlzIHRoZSBtb250aCB0aGF0IGlzIGN1cnJlbnRseSBkaXNwbGF5ZWQgYnkgdGhlIGRhdGVwaWNrZXIuXG4gICAqL1xuICBASW5wdXQoKSBtYXJrRGlzYWJsZWQ6IChkYXRlOiBOZ2JEYXRlLCBjdXJyZW50OiB7eWVhcjogbnVtYmVyLCBtb250aDogbnVtYmVyfSkgPT4gYm9vbGVhbjtcblxuICAvKipcbiAgICogVGhlIGVhcmxpZXN0IGRhdGUgdGhhdCBjYW4gYmUgZGlzcGxheWVkIG9yIHNlbGVjdGVkLiBBbHNvIHVzZWQgZm9yIGZvcm0gdmFsaWRhdGlvbi5cbiAgICpcbiAgICogSWYgbm90IHByb3ZpZGVkLCAneWVhcicgc2VsZWN0IGJveCB3aWxsIGRpc3BsYXkgMTAgeWVhcnMgYmVmb3JlIHRoZSBjdXJyZW50IG1vbnRoLlxuICAgKi9cbiAgQElucHV0KCkgbWluRGF0ZTogTmdiRGF0ZVN0cnVjdDtcblxuICAvKipcbiAgICogVGhlIGxhdGVzdCBkYXRlIHRoYXQgY2FuIGJlIGRpc3BsYXllZCBvciBzZWxlY3RlZC4gQWxzbyB1c2VkIGZvciBmb3JtIHZhbGlkYXRpb24uXG4gICAqXG4gICAqIElmIG5vdCBwcm92aWRlZCwgJ3llYXInIHNlbGVjdCBib3ggd2lsbCBkaXNwbGF5IDEwIHllYXJzIGFmdGVyIHRoZSBjdXJyZW50IG1vbnRoLlxuICAgKi9cbiAgQElucHV0KCkgbWF4RGF0ZTogTmdiRGF0ZVN0cnVjdDtcblxuICAvKipcbiAgICogTmF2aWdhdGlvbiB0eXBlLlxuICAgKlxuICAgKiAqIGBcInNlbGVjdFwiYCAtIHNlbGVjdCBib3hlcyBmb3IgbW9udGggYW5kIG5hdmlnYXRpb24gYXJyb3dzXG4gICAqICogYFwiYXJyb3dzXCJgIC0gb25seSBuYXZpZ2F0aW9uIGFycm93c1xuICAgKiAqIGBcIm5vbmVcImAgLSBubyBuYXZpZ2F0aW9uIHZpc2libGUgYXQgYWxsXG4gICAqL1xuICBASW5wdXQoKSBuYXZpZ2F0aW9uOiAnc2VsZWN0JyB8ICdhcnJvd3MnIHwgJ25vbmUnO1xuXG4gIC8qKlxuICAgKiBUaGUgd2F5IG9mIGRpc3BsYXlpbmcgZGF5cyB0aGF0IGRvbid0IGJlbG9uZyB0byB0aGUgY3VycmVudCBtb250aC5cbiAgICpcbiAgICogKiBgXCJ2aXNpYmxlXCJgIC0gZGF5cyBhcmUgdmlzaWJsZVxuICAgKiAqIGBcImhpZGRlblwiYCAtIGRheXMgYXJlIGhpZGRlbiwgd2hpdGUgc3BhY2UgcHJlc2VydmVkXG4gICAqICogYFwiY29sbGFwc2VkXCJgIC0gZGF5cyBhcmUgY29sbGFwc2VkLCBzbyB0aGUgZGF0ZXBpY2tlciBoZWlnaHQgbWlnaHQgY2hhbmdlIGJldHdlZW4gbW9udGhzXG4gICAqXG4gICAqIEZvciB0aGUgMisgbW9udGhzIHZpZXcsIGRheXMgaW4gYmV0d2VlbiBtb250aHMgYXJlIG5ldmVyIHNob3duLlxuICAgKi9cbiAgQElucHV0KCkgb3V0c2lkZURheXM6ICd2aXNpYmxlJyB8ICdjb2xsYXBzZWQnIHwgJ2hpZGRlbic7XG5cbiAgLyoqXG4gICAqIFRoZSBwcmVmZXJyZWQgcGxhY2VtZW50IG9mIHRoZSBkYXRlcGlja2VyIHBvcHVwLlxuICAgKlxuICAgKiBQb3NzaWJsZSB2YWx1ZXMgYXJlIGBcInRvcFwiYCwgYFwidG9wLWxlZnRcImAsIGBcInRvcC1yaWdodFwiYCwgYFwiYm90dG9tXCJgLCBgXCJib3R0b20tbGVmdFwiYCxcbiAgICogYFwiYm90dG9tLXJpZ2h0XCJgLCBgXCJsZWZ0XCJgLCBgXCJsZWZ0LXRvcFwiYCwgYFwibGVmdC1ib3R0b21cImAsIGBcInJpZ2h0XCJgLCBgXCJyaWdodC10b3BcImAsXG4gICAqIGBcInJpZ2h0LWJvdHRvbVwiYFxuICAgKlxuICAgKiBBY2NlcHRzIGFuIGFycmF5IG9mIHN0cmluZ3Mgb3IgYSBzdHJpbmcgd2l0aCBzcGFjZSBzZXBhcmF0ZWQgcG9zc2libGUgdmFsdWVzLlxuICAgKlxuICAgKiBUaGUgZGVmYXVsdCBvcmRlciBvZiBwcmVmZXJlbmNlIGlzIGBcImJvdHRvbS1sZWZ0IGJvdHRvbS1yaWdodCB0b3AtbGVmdCB0b3AtcmlnaHRcImBcbiAgICpcbiAgICogUGxlYXNlIHNlZSB0aGUgW3Bvc2l0aW9uaW5nIG92ZXJ2aWV3XSgjL3Bvc2l0aW9uaW5nKSBmb3IgbW9yZSBkZXRhaWxzLlxuICAgKi9cbiAgQElucHV0KCkgcGxhY2VtZW50OiBQbGFjZW1lbnRBcnJheTtcblxuICAvKipcbiAgICogSWYgYHRydWVgLCB3aGVuIGNsb3NpbmcgZGF0ZXBpY2tlciB3aWxsIGZvY3VzIGVsZW1lbnQgdGhhdCB3YXMgZm9jdXNlZCBiZWZvcmUgZGF0ZXBpY2tlciB3YXMgb3BlbmVkLlxuICAgKlxuICAgKiBBbHRlcm5hdGl2ZWx5IHlvdSBjb3VsZCBwcm92aWRlIGEgc2VsZWN0b3Igb3IgYW4gYEhUTUxFbGVtZW50YCB0byBmb2N1cy4gSWYgdGhlIGVsZW1lbnQgZG9lc24ndCBleGlzdCBvciBpbnZhbGlkLFxuICAgKiB3ZSdsbCBmYWxsYmFjayB0byBmb2N1cyBkb2N1bWVudCBib2R5LlxuICAgKlxuICAgKiBAc2luY2UgNS4yLjBcbiAgICovXG4gIEBJbnB1dCgpIHJlc3RvcmVGb2N1czogdHJ1ZSB8IHN0cmluZyB8IEhUTUxFbGVtZW50O1xuXG4gIC8qKlxuICAgKiBJZiBgdHJ1ZWAsIHdlZWtkYXlzIHdpbGwgYmUgZGlzcGxheWVkLlxuICAgKi9cbiAgQElucHV0KCkgc2hvd1dlZWtkYXlzOiBib29sZWFuO1xuXG4gIC8qKlxuICAgKiBJZiBgdHJ1ZWAsIHdlZWsgbnVtYmVycyB3aWxsIGJlIGRpc3BsYXllZC5cbiAgICovXG4gIEBJbnB1dCgpIHNob3dXZWVrTnVtYmVyczogYm9vbGVhbjtcblxuICAvKipcbiAgICogVGhlIGRhdGUgdG8gb3BlbiBjYWxlbmRhciB3aXRoLlxuICAgKlxuICAgKiBXaXRoIHRoZSBkZWZhdWx0IGNhbGVuZGFyIHdlIHVzZSBJU08gODYwMTogJ21vbnRoJyBpcyAxPUphbiAuLi4gMTI9RGVjLlxuICAgKiBJZiBub3RoaW5nIG9yIGludmFsaWQgZGF0ZSBpcyBwcm92aWRlZCwgY2FsZW5kYXIgd2lsbCBvcGVuIHdpdGggY3VycmVudCBtb250aC5cbiAgICpcbiAgICogWW91IGNvdWxkIHVzZSBgbmF2aWdhdGVUbyhkYXRlKWAgbWV0aG9kIGFzIGFuIGFsdGVybmF0aXZlLlxuICAgKi9cbiAgQElucHV0KCkgc3RhcnREYXRlOiB7eWVhcjogbnVtYmVyLCBtb250aDogbnVtYmVyLCBkYXk/OiBudW1iZXJ9O1xuXG4gIC8qKlxuICAgKiBBIHNlbGVjdG9yIHNwZWNpZnlpbmcgdGhlIGVsZW1lbnQgdGhlIGRhdGVwaWNrZXIgcG9wdXAgc2hvdWxkIGJlIGFwcGVuZGVkIHRvLlxuICAgKlxuICAgKiBDdXJyZW50bHkgb25seSBzdXBwb3J0cyBgXCJib2R5XCJgLlxuICAgKi9cbiAgQElucHV0KCkgY29udGFpbmVyOiBzdHJpbmc7XG5cbiAgLyoqXG4gICAqIEEgY3NzIHNlbGVjdG9yIG9yIGh0bWwgZWxlbWVudCBzcGVjaWZ5aW5nIHRoZSBlbGVtZW50IHRoZSBkYXRlcGlja2VyIHBvcHVwIHNob3VsZCBiZSBwb3NpdGlvbmVkIGFnYWluc3QuXG4gICAqXG4gICAqIEJ5IGRlZmF1bHQgdGhlIGlucHV0IGlzIHVzZWQgYXMgYSB0YXJnZXQuXG4gICAqXG4gICAqIEBzaW5jZSA0LjIuMFxuICAgKi9cbiAgQElucHV0KCkgcG9zaXRpb25UYXJnZXQ6IHN0cmluZyB8IEhUTUxFbGVtZW50O1xuXG4gIC8qKlxuICAgKiBBbiBldmVudCBlbWl0dGVkIHdoZW4gdXNlciBzZWxlY3RzIGEgZGF0ZSB1c2luZyBrZXlib2FyZCBvciBtb3VzZS5cbiAgICpcbiAgICogVGhlIHBheWxvYWQgb2YgdGhlIGV2ZW50IGlzIGN1cnJlbnRseSBzZWxlY3RlZCBgTmdiRGF0ZWAuXG4gICAqXG4gICAqIEBzaW5jZSAxLjEuMVxuICAgKi9cbiAgQE91dHB1dCgpIGRhdGVTZWxlY3QgPSBuZXcgRXZlbnRFbWl0dGVyPE5nYkRhdGU+KCk7XG5cbiAgLyoqXG4gICAqIEV2ZW50IGVtaXR0ZWQgcmlnaHQgYWZ0ZXIgdGhlIG5hdmlnYXRpb24gaGFwcGVucyBhbmQgZGlzcGxheWVkIG1vbnRoIGNoYW5nZXMuXG4gICAqXG4gICAqIFNlZSBbYE5nYkRhdGVwaWNrZXJOYXZpZ2F0ZUV2ZW50YF0oIy9jb21wb25lbnRzL2RhdGVwaWNrZXIvYXBpI05nYkRhdGVwaWNrZXJOYXZpZ2F0ZUV2ZW50KSBmb3IgdGhlIHBheWxvYWQgaW5mby5cbiAgICovXG4gIEBPdXRwdXQoKSBuYXZpZ2F0ZSA9IG5ldyBFdmVudEVtaXR0ZXI8TmdiRGF0ZXBpY2tlck5hdmlnYXRlRXZlbnQ+KCk7XG5cbiAgLyoqXG4gICAqIEFuIGV2ZW50IGZpcmVkIGFmdGVyIGNsb3NpbmcgZGF0ZXBpY2tlciB3aW5kb3cuXG4gICAqXG4gICAqIEBzaW5jZSA0LjIuMFxuICAgKi9cbiAgQE91dHB1dCgpIGNsb3NlZCA9IG5ldyBFdmVudEVtaXR0ZXI8dm9pZD4oKTtcblxuICBASW5wdXQoKVxuICBnZXQgZGlzYWJsZWQoKSB7XG4gICAgcmV0dXJuIHRoaXMuX2Rpc2FibGVkO1xuICB9XG4gIHNldCBkaXNhYmxlZCh2YWx1ZTogYW55KSB7XG4gICAgdGhpcy5fZGlzYWJsZWQgPSB2YWx1ZSA9PT0gJycgfHwgKHZhbHVlICYmIHZhbHVlICE9PSAnZmFsc2UnKTtcblxuICAgIGlmICh0aGlzLmlzT3BlbigpKSB7XG4gICAgICB0aGlzLl9jUmVmLmluc3RhbmNlLnNldERpc2FibGVkU3RhdGUodGhpcy5fZGlzYWJsZWQpO1xuICAgIH1cbiAgfVxuXG4gIHByaXZhdGUgX29uQ2hhbmdlID0gKF86IGFueSkgPT4ge307XG4gIHByaXZhdGUgX29uVG91Y2hlZCA9ICgpID0+IHt9O1xuICBwcml2YXRlIF92YWxpZGF0b3JDaGFuZ2UgPSAoKSA9PiB7fTtcblxuXG4gIGNvbnN0cnVjdG9yKFxuICAgICAgcHJpdmF0ZSBfcGFyc2VyRm9ybWF0dGVyOiBOZ2JEYXRlUGFyc2VyRm9ybWF0dGVyLCBwcml2YXRlIF9lbFJlZjogRWxlbWVudFJlZjxIVE1MSW5wdXRFbGVtZW50PixcbiAgICAgIHByaXZhdGUgX3ZjUmVmOiBWaWV3Q29udGFpbmVyUmVmLCBwcml2YXRlIF9yZW5kZXJlcjogUmVuZGVyZXIyLCBwcml2YXRlIF9jZnI6IENvbXBvbmVudEZhY3RvcnlSZXNvbHZlcixcbiAgICAgIHByaXZhdGUgX25nWm9uZTogTmdab25lLCBwcml2YXRlIF9jYWxlbmRhcjogTmdiQ2FsZW5kYXIsIHByaXZhdGUgX2RhdGVBZGFwdGVyOiBOZ2JEYXRlQWRhcHRlcjxhbnk+LFxuICAgICAgQEluamVjdChET0NVTUVOVCkgcHJpdmF0ZSBfZG9jdW1lbnQ6IGFueSwgcHJpdmF0ZSBfY2hhbmdlRGV0ZWN0b3I6IENoYW5nZURldGVjdG9yUmVmLFxuICAgICAgY29uZmlnOiBOZ2JJbnB1dERhdGVwaWNrZXJDb25maWcpIHtcbiAgICBbJ2F1dG9DbG9zZScsICdjb250YWluZXInLCAncG9zaXRpb25UYXJnZXQnLCAncGxhY2VtZW50J10uZm9yRWFjaChpbnB1dCA9PiB0aGlzW2lucHV0XSA9IGNvbmZpZ1tpbnB1dF0pO1xuICAgIHRoaXMuX3pvbmVTdWJzY3JpcHRpb24gPSBfbmdab25lLm9uU3RhYmxlLnN1YnNjcmliZSgoKSA9PiB0aGlzLl91cGRhdGVQb3B1cFBvc2l0aW9uKCkpO1xuICB9XG5cbiAgcmVnaXN0ZXJPbkNoYW5nZShmbjogKHZhbHVlOiBhbnkpID0+IGFueSk6IHZvaWQgeyB0aGlzLl9vbkNoYW5nZSA9IGZuOyB9XG5cbiAgcmVnaXN0ZXJPblRvdWNoZWQoZm46ICgpID0+IGFueSk6IHZvaWQgeyB0aGlzLl9vblRvdWNoZWQgPSBmbjsgfVxuXG4gIHJlZ2lzdGVyT25WYWxpZGF0b3JDaGFuZ2UoZm46ICgpID0+IHZvaWQpOiB2b2lkIHsgdGhpcy5fdmFsaWRhdG9yQ2hhbmdlID0gZm47IH1cblxuICBzZXREaXNhYmxlZFN0YXRlKGlzRGlzYWJsZWQ6IGJvb2xlYW4pOiB2b2lkIHsgdGhpcy5kaXNhYmxlZCA9IGlzRGlzYWJsZWQ7IH1cblxuICB2YWxpZGF0ZShjOiBBYnN0cmFjdENvbnRyb2wpOiB7W2tleTogc3RyaW5nXTogYW55fSB7XG4gICAgY29uc3QgdmFsdWUgPSBjLnZhbHVlO1xuXG4gICAgaWYgKHZhbHVlID09PSBudWxsIHx8IHZhbHVlID09PSB1bmRlZmluZWQpIHtcbiAgICAgIHJldHVybiBudWxsO1xuICAgIH1cblxuICAgIGNvbnN0IG5nYkRhdGUgPSB0aGlzLl9mcm9tRGF0ZVN0cnVjdCh0aGlzLl9kYXRlQWRhcHRlci5mcm9tTW9kZWwodmFsdWUpKTtcblxuICAgIGlmICghdGhpcy5fY2FsZW5kYXIuaXNWYWxpZChuZ2JEYXRlKSkge1xuICAgICAgcmV0dXJuIHsnbmdiRGF0ZSc6IHtpbnZhbGlkOiBjLnZhbHVlfX07XG4gICAgfVxuXG4gICAgaWYgKHRoaXMubWluRGF0ZSAmJiBuZ2JEYXRlLmJlZm9yZShOZ2JEYXRlLmZyb20odGhpcy5taW5EYXRlKSkpIHtcbiAgICAgIHJldHVybiB7J25nYkRhdGUnOiB7cmVxdWlyZWRCZWZvcmU6IHRoaXMubWluRGF0ZX19O1xuICAgIH1cblxuICAgIGlmICh0aGlzLm1heERhdGUgJiYgbmdiRGF0ZS5hZnRlcihOZ2JEYXRlLmZyb20odGhpcy5tYXhEYXRlKSkpIHtcbiAgICAgIHJldHVybiB7J25nYkRhdGUnOiB7cmVxdWlyZWRBZnRlcjogdGhpcy5tYXhEYXRlfX07XG4gICAgfVxuICB9XG5cbiAgd3JpdGVWYWx1ZSh2YWx1ZSkge1xuICAgIHRoaXMuX21vZGVsID0gdGhpcy5fZnJvbURhdGVTdHJ1Y3QodGhpcy5fZGF0ZUFkYXB0ZXIuZnJvbU1vZGVsKHZhbHVlKSk7XG4gICAgdGhpcy5fd3JpdGVNb2RlbFZhbHVlKHRoaXMuX21vZGVsKTtcbiAgfVxuXG4gIG1hbnVhbERhdGVDaGFuZ2UodmFsdWU6IHN0cmluZywgdXBkYXRlVmlldyA9IGZhbHNlKSB7XG4gICAgY29uc3QgaW5wdXRWYWx1ZUNoYW5nZWQgPSB2YWx1ZSAhPT0gdGhpcy5faW5wdXRWYWx1ZTtcbiAgICBpZiAoaW5wdXRWYWx1ZUNoYW5nZWQpIHtcbiAgICAgIHRoaXMuX2lucHV0VmFsdWUgPSB2YWx1ZTtcbiAgICAgIHRoaXMuX21vZGVsID0gdGhpcy5fZnJvbURhdGVTdHJ1Y3QodGhpcy5fcGFyc2VyRm9ybWF0dGVyLnBhcnNlKHZhbHVlKSk7XG4gICAgfVxuICAgIGlmIChpbnB1dFZhbHVlQ2hhbmdlZCB8fCAhdXBkYXRlVmlldykge1xuICAgICAgdGhpcy5fb25DaGFuZ2UodGhpcy5fbW9kZWwgPyB0aGlzLl9kYXRlQWRhcHRlci50b01vZGVsKHRoaXMuX21vZGVsKSA6ICh2YWx1ZSA9PT0gJycgPyBudWxsIDogdmFsdWUpKTtcbiAgICB9XG4gICAgaWYgKHVwZGF0ZVZpZXcgJiYgdGhpcy5fbW9kZWwpIHtcbiAgICAgIHRoaXMuX3dyaXRlTW9kZWxWYWx1ZSh0aGlzLl9tb2RlbCk7XG4gICAgfVxuICB9XG5cbiAgaXNPcGVuKCkgeyByZXR1cm4gISF0aGlzLl9jUmVmOyB9XG5cbiAgLyoqXG4gICAqIE9wZW5zIHRoZSBkYXRlcGlja2VyIHBvcHVwLlxuICAgKlxuICAgKiBJZiB0aGUgcmVsYXRlZCBmb3JtIGNvbnRyb2wgY29udGFpbnMgYSB2YWxpZCBkYXRlLCB0aGUgY29ycmVzcG9uZGluZyBtb250aCB3aWxsIGJlIG9wZW5lZC5cbiAgICovXG4gIG9wZW4oKSB7XG4gICAgaWYgKCF0aGlzLmlzT3BlbigpKSB7XG4gICAgICBjb25zdCBjZiA9IHRoaXMuX2Nmci5yZXNvbHZlQ29tcG9uZW50RmFjdG9yeShOZ2JEYXRlcGlja2VyKTtcbiAgICAgIHRoaXMuX2NSZWYgPSB0aGlzLl92Y1JlZi5jcmVhdGVDb21wb25lbnQoY2YpO1xuXG4gICAgICB0aGlzLl9hcHBseVBvcHVwU3R5bGluZyh0aGlzLl9jUmVmLmxvY2F0aW9uLm5hdGl2ZUVsZW1lbnQpO1xuICAgICAgdGhpcy5fYXBwbHlEYXRlcGlja2VySW5wdXRzKHRoaXMuX2NSZWYuaW5zdGFuY2UpO1xuICAgICAgdGhpcy5fc3Vic2NyaWJlRm9yRGF0ZXBpY2tlck91dHB1dHModGhpcy5fY1JlZi5pbnN0YW5jZSk7XG4gICAgICB0aGlzLl9jUmVmLmluc3RhbmNlLm5nT25Jbml0KCk7XG4gICAgICB0aGlzLl9jUmVmLmluc3RhbmNlLndyaXRlVmFsdWUodGhpcy5fZGF0ZUFkYXB0ZXIudG9Nb2RlbCh0aGlzLl9tb2RlbCkpO1xuXG4gICAgICAvLyBkYXRlIHNlbGVjdGlvbiBldmVudCBoYW5kbGluZ1xuICAgICAgdGhpcy5fY1JlZi5pbnN0YW5jZS5yZWdpc3Rlck9uQ2hhbmdlKChzZWxlY3RlZERhdGUpID0+IHtcbiAgICAgICAgdGhpcy53cml0ZVZhbHVlKHNlbGVjdGVkRGF0ZSk7XG4gICAgICAgIHRoaXMuX29uQ2hhbmdlKHNlbGVjdGVkRGF0ZSk7XG4gICAgICAgIHRoaXMuX29uVG91Y2hlZCgpO1xuICAgICAgfSk7XG5cbiAgICAgIHRoaXMuX2NSZWYuY2hhbmdlRGV0ZWN0b3JSZWYuZGV0ZWN0Q2hhbmdlcygpO1xuXG4gICAgICB0aGlzLl9jUmVmLmluc3RhbmNlLnNldERpc2FibGVkU3RhdGUodGhpcy5kaXNhYmxlZCk7XG5cbiAgICAgIGlmICh0aGlzLmNvbnRhaW5lciA9PT0gJ2JvZHknKSB7XG4gICAgICAgIHdpbmRvdy5kb2N1bWVudC5xdWVyeVNlbGVjdG9yKHRoaXMuY29udGFpbmVyKS5hcHBlbmRDaGlsZCh0aGlzLl9jUmVmLmxvY2F0aW9uLm5hdGl2ZUVsZW1lbnQpO1xuICAgICAgfVxuXG4gICAgICAvLyBmb2N1cyBoYW5kbGluZ1xuICAgICAgdGhpcy5fZWxXaXRoRm9jdXMgPSB0aGlzLl9kb2N1bWVudC5hY3RpdmVFbGVtZW50O1xuICAgICAgbmdiRm9jdXNUcmFwKHRoaXMuX25nWm9uZSwgdGhpcy5fY1JlZi5sb2NhdGlvbi5uYXRpdmVFbGVtZW50LCB0aGlzLmNsb3NlZCwgdHJ1ZSk7XG4gICAgICB0aGlzLl9jUmVmLmluc3RhbmNlLmZvY3VzKCk7XG5cbiAgICAgIG5nYkF1dG9DbG9zZShcbiAgICAgICAgICB0aGlzLl9uZ1pvbmUsIHRoaXMuX2RvY3VtZW50LCB0aGlzLmF1dG9DbG9zZSwgKCkgPT4gdGhpcy5jbG9zZSgpLCB0aGlzLmNsb3NlZCwgW10sXG4gICAgICAgICAgW3RoaXMuX2VsUmVmLm5hdGl2ZUVsZW1lbnQsIHRoaXMuX2NSZWYubG9jYXRpb24ubmF0aXZlRWxlbWVudF0pO1xuICAgIH1cbiAgfVxuXG4gIC8qKlxuICAgKiBDbG9zZXMgdGhlIGRhdGVwaWNrZXIgcG9wdXAuXG4gICAqL1xuICBjbG9zZSgpIHtcbiAgICBpZiAodGhpcy5pc09wZW4oKSkge1xuICAgICAgdGhpcy5fdmNSZWYucmVtb3ZlKHRoaXMuX3ZjUmVmLmluZGV4T2YodGhpcy5fY1JlZi5ob3N0VmlldykpO1xuICAgICAgdGhpcy5fY1JlZiA9IG51bGw7XG4gICAgICB0aGlzLmNsb3NlZC5lbWl0KCk7XG4gICAgICB0aGlzLl9jaGFuZ2VEZXRlY3Rvci5tYXJrRm9yQ2hlY2soKTtcblxuICAgICAgLy8gcmVzdG9yZSBmb2N1c1xuICAgICAgbGV0IGVsZW1lbnRUb0ZvY3VzID0gdGhpcy5fZWxXaXRoRm9jdXM7XG4gICAgICBpZiAoaXNTdHJpbmcodGhpcy5yZXN0b3JlRm9jdXMpKSB7XG4gICAgICAgIGVsZW1lbnRUb0ZvY3VzID0gdGhpcy5fZG9jdW1lbnQucXVlcnlTZWxlY3Rvcih0aGlzLnJlc3RvcmVGb2N1cyk7XG4gICAgICB9IGVsc2UgaWYgKHRoaXMucmVzdG9yZUZvY3VzICE9PSB1bmRlZmluZWQpIHtcbiAgICAgICAgZWxlbWVudFRvRm9jdXMgPSB0aGlzLnJlc3RvcmVGb2N1cztcbiAgICAgIH1cblxuICAgICAgLy8gaW4gSUUgZG9jdW1lbnQuYWN0aXZlRWxlbWVudCBjYW4gY29udGFpbiBhbiBvYmplY3Qgd2l0aG91dCAnZm9jdXMoKScgc29tZXRpbWVzXG4gICAgICBpZiAoZWxlbWVudFRvRm9jdXMgJiYgZWxlbWVudFRvRm9jdXNbJ2ZvY3VzJ10pIHtcbiAgICAgICAgZWxlbWVudFRvRm9jdXMuZm9jdXMoKTtcbiAgICAgIH0gZWxzZSB7XG4gICAgICAgIHRoaXMuX2RvY3VtZW50LmJvZHkuZm9jdXMoKTtcbiAgICAgIH1cbiAgICB9XG4gIH1cblxuICAvKipcbiAgICogVG9nZ2xlcyB0aGUgZGF0ZXBpY2tlciBwb3B1cC5cbiAgICovXG4gIHRvZ2dsZSgpIHtcbiAgICBpZiAodGhpcy5pc09wZW4oKSkge1xuICAgICAgdGhpcy5jbG9zZSgpO1xuICAgIH0gZWxzZSB7XG4gICAgICB0aGlzLm9wZW4oKTtcbiAgICB9XG4gIH1cblxuICAvKipcbiAgICogTmF2aWdhdGVzIHRvIHRoZSBwcm92aWRlZCBkYXRlLlxuICAgKlxuICAgKiBXaXRoIHRoZSBkZWZhdWx0IGNhbGVuZGFyIHdlIHVzZSBJU08gODYwMTogJ21vbnRoJyBpcyAxPUphbiAuLi4gMTI9RGVjLlxuICAgKiBJZiBub3RoaW5nIG9yIGludmFsaWQgZGF0ZSBwcm92aWRlZCBjYWxlbmRhciB3aWxsIG9wZW4gY3VycmVudCBtb250aC5cbiAgICpcbiAgICogVXNlIHRoZSBgW3N0YXJ0RGF0ZV1gIGlucHV0IGFzIGFuIGFsdGVybmF0aXZlLlxuICAgKi9cbiAgbmF2aWdhdGVUbyhkYXRlPzoge3llYXI6IG51bWJlciwgbW9udGg6IG51bWJlciwgZGF5PzogbnVtYmVyfSkge1xuICAgIGlmICh0aGlzLmlzT3BlbigpKSB7XG4gICAgICB0aGlzLl9jUmVmLmluc3RhbmNlLm5hdmlnYXRlVG8oZGF0ZSk7XG4gICAgfVxuICB9XG5cbiAgb25CbHVyKCkgeyB0aGlzLl9vblRvdWNoZWQoKTsgfVxuXG4gIG9uRm9jdXMoKSB7IHRoaXMuX2VsV2l0aEZvY3VzID0gdGhpcy5fZWxSZWYubmF0aXZlRWxlbWVudDsgfVxuXG4gIG5nT25DaGFuZ2VzKGNoYW5nZXM6IFNpbXBsZUNoYW5nZXMpIHtcbiAgICBpZiAoY2hhbmdlc1snbWluRGF0ZSddIHx8IGNoYW5nZXNbJ21heERhdGUnXSkge1xuICAgICAgdGhpcy5fdmFsaWRhdG9yQ2hhbmdlKCk7XG5cbiAgICAgIGlmICh0aGlzLmlzT3BlbigpKSB7XG4gICAgICAgIGlmIChjaGFuZ2VzWydtaW5EYXRlJ10pIHtcbiAgICAgICAgICB0aGlzLl9jUmVmLmluc3RhbmNlLm1pbkRhdGUgPSB0aGlzLl9kYXRlQWRhcHRlci50b01vZGVsKGNoYW5nZXMubWluRGF0ZS5jdXJyZW50VmFsdWUpO1xuICAgICAgICB9XG4gICAgICAgIGlmIChjaGFuZ2VzWydtYXhEYXRlJ10pIHtcbiAgICAgICAgICB0aGlzLl9jUmVmLmluc3RhbmNlLm1heERhdGUgPSB0aGlzLl9kYXRlQWRhcHRlci50b01vZGVsKGNoYW5nZXMubWF4RGF0ZS5jdXJyZW50VmFsdWUpO1xuICAgICAgICB9XG4gICAgICAgIHRoaXMuX2NSZWYuaW5zdGFuY2UubmdPbkNoYW5nZXMoY2hhbmdlcyk7XG4gICAgICB9XG4gICAgfVxuICB9XG5cbiAgbmdPbkRlc3Ryb3koKSB7XG4gICAgdGhpcy5jbG9zZSgpO1xuICAgIHRoaXMuX3pvbmVTdWJzY3JpcHRpb24udW5zdWJzY3JpYmUoKTtcbiAgfVxuXG4gIHByaXZhdGUgX2FwcGx5RGF0ZXBpY2tlcklucHV0cyhkYXRlcGlja2VySW5zdGFuY2U6IE5nYkRhdGVwaWNrZXIpOiB2b2lkIHtcbiAgICBbJ2RheVRlbXBsYXRlJywgJ2RheVRlbXBsYXRlRGF0YScsICdkaXNwbGF5TW9udGhzJywgJ2ZpcnN0RGF5T2ZXZWVrJywgJ2Zvb3RlclRlbXBsYXRlJywgJ21hcmtEaXNhYmxlZCcsICdtaW5EYXRlJyxcbiAgICAgJ21heERhdGUnLCAnbmF2aWdhdGlvbicsICdvdXRzaWRlRGF5cycsICdzaG93TmF2aWdhdGlvbicsICdzaG93V2Vla2RheXMnLCAnc2hvd1dlZWtOdW1iZXJzJ11cbiAgICAgICAgLmZvckVhY2goKG9wdGlvbk5hbWU6IHN0cmluZykgPT4ge1xuICAgICAgICAgIGlmICh0aGlzW29wdGlvbk5hbWVdICE9PSB1bmRlZmluZWQpIHtcbiAgICAgICAgICAgIGRhdGVwaWNrZXJJbnN0YW5jZVtvcHRpb25OYW1lXSA9IHRoaXNbb3B0aW9uTmFtZV07XG4gICAgICAgICAgfVxuICAgICAgICB9KTtcbiAgICBkYXRlcGlja2VySW5zdGFuY2Uuc3RhcnREYXRlID0gdGhpcy5zdGFydERhdGUgfHwgdGhpcy5fbW9kZWw7XG4gIH1cblxuICBwcml2YXRlIF9hcHBseVBvcHVwU3R5bGluZyhuYXRpdmVFbGVtZW50OiBhbnkpIHtcbiAgICB0aGlzLl9yZW5kZXJlci5hZGRDbGFzcyhuYXRpdmVFbGVtZW50LCAnZHJvcGRvd24tbWVudScpO1xuICAgIHRoaXMuX3JlbmRlcmVyLmFkZENsYXNzKG5hdGl2ZUVsZW1lbnQsICdzaG93Jyk7XG5cbiAgICBpZiAodGhpcy5jb250YWluZXIgPT09ICdib2R5Jykge1xuICAgICAgdGhpcy5fcmVuZGVyZXIuYWRkQ2xhc3MobmF0aXZlRWxlbWVudCwgJ25nYi1kcC1ib2R5Jyk7XG4gICAgfVxuICB9XG5cbiAgcHJpdmF0ZSBfc3Vic2NyaWJlRm9yRGF0ZXBpY2tlck91dHB1dHMoZGF0ZXBpY2tlckluc3RhbmNlOiBOZ2JEYXRlcGlja2VyKSB7XG4gICAgZGF0ZXBpY2tlckluc3RhbmNlLm5hdmlnYXRlLnN1YnNjcmliZShuYXZpZ2F0ZUV2ZW50ID0+IHRoaXMubmF2aWdhdGUuZW1pdChuYXZpZ2F0ZUV2ZW50KSk7XG4gICAgZGF0ZXBpY2tlckluc3RhbmNlLmRhdGVTZWxlY3Quc3Vic2NyaWJlKGRhdGUgPT4ge1xuICAgICAgdGhpcy5kYXRlU2VsZWN0LmVtaXQoZGF0ZSk7XG4gICAgICBpZiAodGhpcy5hdXRvQ2xvc2UgPT09IHRydWUgfHwgdGhpcy5hdXRvQ2xvc2UgPT09ICdpbnNpZGUnKSB7XG4gICAgICAgIHRoaXMuY2xvc2UoKTtcbiAgICAgIH1cbiAgICB9KTtcbiAgfVxuXG4gIHByaXZhdGUgX3dyaXRlTW9kZWxWYWx1ZShtb2RlbDogTmdiRGF0ZSkge1xuICAgIGNvbnN0IHZhbHVlID0gdGhpcy5fcGFyc2VyRm9ybWF0dGVyLmZvcm1hdChtb2RlbCk7XG4gICAgdGhpcy5faW5wdXRWYWx1ZSA9IHZhbHVlO1xuICAgIHRoaXMuX3JlbmRlcmVyLnNldFByb3BlcnR5KHRoaXMuX2VsUmVmLm5hdGl2ZUVsZW1lbnQsICd2YWx1ZScsIHZhbHVlKTtcbiAgICBpZiAodGhpcy5pc09wZW4oKSkge1xuICAgICAgdGhpcy5fY1JlZi5pbnN0YW5jZS53cml0ZVZhbHVlKHRoaXMuX2RhdGVBZGFwdGVyLnRvTW9kZWwobW9kZWwpKTtcbiAgICAgIHRoaXMuX29uVG91Y2hlZCgpO1xuICAgIH1cbiAgfVxuXG4gIHByaXZhdGUgX2Zyb21EYXRlU3RydWN0KGRhdGU6IE5nYkRhdGVTdHJ1Y3QpOiBOZ2JEYXRlIHtcbiAgICBjb25zdCBuZ2JEYXRlID0gZGF0ZSA/IG5ldyBOZ2JEYXRlKGRhdGUueWVhciwgZGF0ZS5tb250aCwgZGF0ZS5kYXkpIDogbnVsbDtcbiAgICByZXR1cm4gdGhpcy5fY2FsZW5kYXIuaXNWYWxpZChuZ2JEYXRlKSA/IG5nYkRhdGUgOiBudWxsO1xuICB9XG5cbiAgcHJpdmF0ZSBfdXBkYXRlUG9wdXBQb3NpdGlvbigpIHtcbiAgICBpZiAoIXRoaXMuX2NSZWYpIHtcbiAgICAgIHJldHVybjtcbiAgICB9XG5cbiAgICBsZXQgaG9zdEVsZW1lbnQ6IEhUTUxFbGVtZW50O1xuICAgIGlmIChpc1N0cmluZyh0aGlzLnBvc2l0aW9uVGFyZ2V0KSkge1xuICAgICAgaG9zdEVsZW1lbnQgPSB0aGlzLl9kb2N1bWVudC5xdWVyeVNlbGVjdG9yKHRoaXMucG9zaXRpb25UYXJnZXQpO1xuICAgIH0gZWxzZSBpZiAodGhpcy5wb3NpdGlvblRhcmdldCBpbnN0YW5jZW9mIEhUTUxFbGVtZW50KSB7XG4gICAgICBob3N0RWxlbWVudCA9IHRoaXMucG9zaXRpb25UYXJnZXQ7XG4gICAgfSBlbHNlIHtcbiAgICAgIGhvc3RFbGVtZW50ID0gdGhpcy5fZWxSZWYubmF0aXZlRWxlbWVudDtcbiAgICB9XG5cbiAgICBpZiAodGhpcy5wb3NpdGlvblRhcmdldCAmJiAhaG9zdEVsZW1lbnQpIHtcbiAgICAgIHRocm93IG5ldyBFcnJvcignbmdiRGF0ZXBpY2tlciBjb3VsZCBub3QgZmluZCBlbGVtZW50IGRlY2xhcmVkIGluIFtwb3NpdGlvblRhcmdldF0gdG8gcG9zaXRpb24gYWdhaW5zdC4nKTtcbiAgICB9XG5cbiAgICBwb3NpdGlvbkVsZW1lbnRzKGhvc3RFbGVtZW50LCB0aGlzLl9jUmVmLmxvY2F0aW9uLm5hdGl2ZUVsZW1lbnQsIHRoaXMucGxhY2VtZW50LCB0aGlzLmNvbnRhaW5lciA9PT0gJ2JvZHknKTtcbiAgfVxufVxuIl19