/** * @fileoverview added by tsickle * @suppress {checkTypes,constantProperty,extraRequire,missingOverride,missingReturn,unusedPrivateMembers,uselessCode} checked by tsc */ import { NgbDate } from './ngb-date'; import { Injectable } from '@angular/core'; import { isInteger } from '../util/util'; import * as i0 from "@angular/core"; /** * @param {?} jsDate * @return {?} */ export function fromJSDate(jsDate) { return new NgbDate(jsDate.getFullYear(), jsDate.getMonth() + 1, jsDate.getDate()); } /** * @param {?} date * @return {?} */ export function toJSDate(date) { /** @type {?} */ const jsDate = new Date(date.year, date.month - 1, date.day, 12); // this is done avoid 30 -> 1930 conversion if (!isNaN(jsDate.getTime())) { jsDate.setFullYear(date.year); } return jsDate; } /** * @return {?} */ export function NGB_DATEPICKER_CALENDAR_FACTORY() { return new NgbCalendarGregorian(); } /** * A service that represents the calendar used by the datepicker. * * The default implementation uses the Gregorian calendar. You can inject it in your own * implementations if necessary to simplify `NgbDate` calculations. * @abstract */ export class NgbCalendar { } NgbCalendar.decorators = [ { type: Injectable, args: [{ providedIn: 'root', useFactory: NGB_DATEPICKER_CALENDAR_FACTORY },] } ]; /** @nocollapse */ NgbCalendar.ngInjectableDef = i0.ɵɵdefineInjectable({ factory: NGB_DATEPICKER_CALENDAR_FACTORY, token: NgbCalendar, providedIn: "root" }); if (false) { /** * Returns the number of days per week. * @abstract * @return {?} */ NgbCalendar.prototype.getDaysPerWeek = function () { }; /** * Returns an array of months per year. * * With default calendar we use ISO 8601 and return [1, 2, ..., 12]; * @abstract * @param {?=} year * @return {?} */ NgbCalendar.prototype.getMonths = function (year) { }; /** * Returns the number of weeks per month. * @abstract * @return {?} */ NgbCalendar.prototype.getWeeksPerMonth = function () { }; /** * Returns the weekday number for a given day. * * With the default calendar we use ISO 8601: 'weekday' is 1=Mon ... 7=Sun * @abstract * @param {?} date * @return {?} */ NgbCalendar.prototype.getWeekday = function (date) { }; /** * Adds a number of years, months or days to a given date. * * * `period` can be `y`, `m` or `d` and defaults to day. * * `number` defaults to 1. * * Always returns a new date. * @abstract * @param {?} date * @param {?=} period * @param {?=} number * @return {?} */ NgbCalendar.prototype.getNext = function (date, period, number) { }; /** * Subtracts a number of years, months or days from a given date. * * * `period` can be `y`, `m` or `d` and defaults to day. * * `number` defaults to 1. * * Always returns a new date. * @abstract * @param {?} date * @param {?=} period * @param {?=} number * @return {?} */ NgbCalendar.prototype.getPrev = function (date, period, number) { }; /** * Returns the week number for a given week. * @abstract * @param {?} week * @param {?} firstDayOfWeek * @return {?} */ NgbCalendar.prototype.getWeekNumber = function (week, firstDayOfWeek) { }; /** * Returns the today's date. * @abstract * @return {?} */ NgbCalendar.prototype.getToday = function () { }; /** * Checks if a date is valid in the current calendar. * @abstract * @param {?} date * @return {?} */ NgbCalendar.prototype.isValid = function (date) { }; } export class NgbCalendarGregorian extends NgbCalendar { /** * @return {?} */ getDaysPerWeek() { return 7; } /** * @return {?} */ getMonths() { return [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12]; } /** * @return {?} */ getWeeksPerMonth() { return 6; } /** * @param {?} date * @param {?=} period * @param {?=} number * @return {?} */ getNext(date, period = 'd', number = 1) { /** @type {?} */ let jsDate = toJSDate(date); /** @type {?} */ let checkMonth = true; /** @type {?} */ let expectedMonth = jsDate.getMonth(); switch (period) { case 'y': jsDate.setFullYear(jsDate.getFullYear() + number); break; case 'm': expectedMonth += number; jsDate.setMonth(expectedMonth); expectedMonth = expectedMonth % 12; if (expectedMonth < 0) { expectedMonth = expectedMonth + 12; } break; case 'd': jsDate.setDate(jsDate.getDate() + number); checkMonth = false; break; default: return date; } if (checkMonth && jsDate.getMonth() !== expectedMonth) { // this means the destination month has less days than the initial month // let's go back to the end of the previous month: jsDate.setDate(0); } return fromJSDate(jsDate); } /** * @param {?} date * @param {?=} period * @param {?=} number * @return {?} */ getPrev(date, period = 'd', number = 1) { return this.getNext(date, period, -number); } /** * @param {?} date * @return {?} */ getWeekday(date) { /** @type {?} */ let jsDate = toJSDate(date); /** @type {?} */ let day = jsDate.getDay(); // in JS Date Sun=0, in ISO 8601 Sun=7 return day === 0 ? 7 : day; } /** * @param {?} week * @param {?} firstDayOfWeek * @return {?} */ getWeekNumber(week, firstDayOfWeek) { // in JS Date Sun=0, in ISO 8601 Sun=7 if (firstDayOfWeek === 7) { firstDayOfWeek = 0; } /** @type {?} */ const thursdayIndex = (4 + 7 - firstDayOfWeek) % 7; /** @type {?} */ let date = week[thursdayIndex]; /** @type {?} */ const jsDate = toJSDate(date); jsDate.setDate(jsDate.getDate() + 4 - (jsDate.getDay() || 7)); // Thursday // Thursday /** @type {?} */ const time = jsDate.getTime(); jsDate.setMonth(0); // Compare with Jan 1 jsDate.setDate(1); return Math.floor(Math.round((time - jsDate.getTime()) / 86400000) / 7) + 1; } /** * @return {?} */ getToday() { return fromJSDate(new Date()); } /** * @param {?} date * @return {?} */ isValid(date) { if (!date || !isInteger(date.year) || !isInteger(date.month) || !isInteger(date.day)) { return false; } // year 0 doesn't exist in Gregorian calendar if (date.year === 0) { return false; } /** @type {?} */ const jsDate = toJSDate(date); return !isNaN(jsDate.getTime()) && jsDate.getFullYear() === date.year && jsDate.getMonth() + 1 === date.month && jsDate.getDate() === date.day; } } NgbCalendarGregorian.decorators = [ { type: Injectable } ]; //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoibmdiLWNhbGVuZGFyLmpzIiwic291cmNlUm9vdCI6Im5nOi8vQG5nLWJvb3RzdHJhcC9uZy1ib290c3RyYXAvIiwic291cmNlcyI6WyJkYXRlcGlja2VyL25nYi1jYWxlbmRhci50cyJdLCJuYW1lcyI6W10sIm1hcHBpbmdzIjoiOzs7O0FBQUEsT0FBTyxFQUFDLE9BQU8sRUFBQyxNQUFNLFlBQVksQ0FBQztBQUNuQyxPQUFPLEVBQUMsVUFBVSxFQUFDLE1BQU0sZUFBZSxDQUFDO0FBQ3pDLE9BQU8sRUFBQyxTQUFTLEVBQUMsTUFBTSxjQUFjLENBQUM7Ozs7OztBQUV2QyxNQUFNLFVBQVUsVUFBVSxDQUFDLE1BQVk7SUFDckMsT0FBTyxJQUFJLE9BQU8sQ0FBQyxNQUFNLENBQUMsV0FBVyxFQUFFLEVBQUUsTUFBTSxDQUFDLFFBQVEsRUFBRSxHQUFHLENBQUMsRUFBRSxNQUFNLENBQUMsT0FBTyxFQUFFLENBQUMsQ0FBQztBQUNwRixDQUFDOzs7OztBQUNELE1BQU0sVUFBVSxRQUFRLENBQUMsSUFBYTs7VUFDOUIsTUFBTSxHQUFHLElBQUksSUFBSSxDQUFDLElBQUksQ0FBQyxJQUFJLEVBQUUsSUFBSSxDQUFDLEtBQUssR0FBRyxDQUFDLEVBQUUsSUFBSSxDQUFDLEdBQUcsRUFBRSxFQUFFLENBQUM7SUFDaEUsMkNBQTJDO0lBQzNDLElBQUksQ0FBQyxLQUFLLENBQUMsTUFBTSxDQUFDLE9BQU8sRUFBRSxDQUFDLEVBQUU7UUFDNUIsTUFBTSxDQUFDLFdBQVcsQ0FBQyxJQUFJLENBQUMsSUFBSSxDQUFDLENBQUM7S0FDL0I7SUFDRCxPQUFPLE1BQU0sQ0FBQztBQUNoQixDQUFDOzs7O0FBSUQsTUFBTSxVQUFVLCtCQUErQjtJQUM3QyxPQUFPLElBQUksb0JBQW9CLEVBQUUsQ0FBQztBQUNwQyxDQUFDOzs7Ozs7OztBQVNELE1BQU0sT0FBZ0IsV0FBVzs7O1lBRGhDLFVBQVUsU0FBQyxFQUFDLFVBQVUsRUFBRSxNQUFNLEVBQUUsVUFBVSxFQUFFLCtCQUErQixF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QyxJQUFJLE1BQU0sQ0FBQyxXQUFXLEVBQUUsS0FBSyxJQUFJLENBQUMsSUFBSSxJQUFJLE1BQU0sQ0FBQyxRQUFRLEVBQUUsR0FBRyxDQUFDLEtBQUssSUFBSSxDQUFDLEtBQUs7WUFDekcsTUFBTSxDQUFDLE9BQU8sRUFBRSxLQUFLLElBQUksQ0FBQyxHQUFHLENBQUM7SUFDcEMsQ0FBQzs7O1lBcEZGLFVBQVUiLCJzb3VyY2VzQ29udGVudCI6WyJpbXBvcnQge05nYkRhdGV9IGZyb20gJy4vbmdiLWRhdGUnO1xuaW1wb3J0IHtJbmplY3RhYmxlfSBmcm9tICdAYW5ndWxhci9jb3JlJztcbmltcG9ydCB7aXNJbnRlZ2VyfSBmcm9tICcuLi91dGlsL3V0aWwnO1xuXG5leHBvcnQgZnVuY3Rpb24gZnJvbUpTRGF0ZShqc0RhdGU6IERhdGUpIHtcbiAgcmV0dXJuIG5ldyBOZ2JEYXRlKGpzRGF0ZS5nZXRGdWxsWWVhcigpLCBqc0RhdGUuZ2V0TW9udGgoKSArIDEsIGpzRGF0ZS5nZXREYXRlKCkpO1xufVxuZXhwb3J0IGZ1bmN0aW9uIHRvSlNEYXRlKGRhdGU6IE5nYkRhdGUpIHtcbiAgY29uc3QganNEYXRlID0gbmV3IERhdGUoZGF0ZS55ZWFyLCBkYXRlLm1vbnRoIC0gMSwgZGF0ZS5kYXksIDEyKTtcbiAgLy8gdGhpcyBpcyBkb25lIGF2b2lkIDMwIC0+IDE5MzAgY29udmVyc2lvblxuICBpZiAoIWlzTmFOKGpzRGF0ZS5nZXRUaW1lKCkpKSB7XG4gICAganNEYXRlLnNldEZ1bGxZZWFyKGRhdGUueWVhcik7XG4gIH1cbiAgcmV0dXJuIGpzRGF0ZTtcbn1cblxuZXhwb3J0IHR5cGUgTmdiUGVyaW9kID0gJ3knIHwgJ20nIHwgJ2QnO1xuXG5leHBvcnQgZnVuY3Rpb24gTkdCX0RBVEVQSUNLRVJfQ0FMRU5EQVJfRkFDVE9SWSgpIHtcbiAgcmV0dXJuIG5ldyBOZ2JDYWxlbmRhckdyZWdvcmlhbigpO1xufVxuXG4vKipcbiAqIEEgc2VydmljZSB0aGF0IHJlcHJlc2VudHMgdGhlIGNhbGVuZGFyIHVzZWQgYnkgdGhlIGRhdGVwaWNrZXIuXG4gKlxuICogVGhlIGRlZmF1bHQgaW1wbGVtZW50YXRpb24gdXNlcyB0aGUgR3JlZ29yaWFuIGNhbGVuZGFyLiBZb3UgY2FuIGluamVjdCBpdCBpbiB5b3VyIG93blxuICogaW1wbGVtZW50YXRpb25zIGlmIG5lY2Vzc2FyeSB0byBzaW1wbGlmeSBgTmdiRGF0ZWAgY2FsY3VsYXRpb25zLlxuICovXG5ASW5qZWN0YWJsZSh7cHJvdmlkZWRJbjogJ3Jvb3QnLCB1c2VGYWN0b3J5OiBOR0JfREFURVBJQ0tFUl9DQUxFTkRBUl9GQUNUT1JZfSlcbmV4cG9ydCBhYnN0cmFjdCBjbGFzcyBOZ2JDYWxlbmRhciB7XG4gIC8qKlxuICAgKiBSZXR1cm5zIHRoZSBudW1iZXIgb2YgZGF5cyBwZXIgd2Vlay5cbiAgICovXG4gIGFic3RyYWN0IGdldERheXNQZXJXZWVrKCk6IG51bWJlcjtcblxuICAvKipcbiAgICogUmV0dXJucyBhbiBhcnJheSBvZiBtb250aHMgcGVyIHllYXIuXG4gICAqXG4gICAqIFdpdGggZGVmYXVsdCBjYWxlbmRhciB3ZSB1c2UgSVNPIDg2MDEgYW5kIHJldHVybiBbMSwgMiwgLi4uLCAxMl07XG4gICAqL1xuICBhYnN0cmFjdCBnZXRNb250aHMoeWVhcj86IG51bWJlcik6IG51bWJlcltdO1xuXG4gIC8qKlxuICAgKiBSZXR1cm5zIHRoZSBudW1iZXIgb2Ygd2Vla3MgcGVyIG1vbnRoLlxuICAgKi9cbiAgYWJzdHJhY3QgZ2V0V2Vla3NQZXJNb250aCgpOiBudW1iZXI7XG5cbiAgLyoqXG4gICAqIFJldHVybnMgdGhlIHdlZWtkYXkgbnVtYmVyIGZvciBhIGdpdmVuIGRheS5cbiAgICpcbiAgICogV2l0aCB0aGUgZGVmYXVsdCBjYWxlbmRhciB3ZSB1c2UgSVNPIDg2MDE6ICd3ZWVrZGF5JyBpcyAxPU1vbiAuLi4gNz1TdW5cbiAgICovXG4gIGFic3RyYWN0IGdldFdlZWtkYXkoZGF0ZTogTmdiRGF0ZSk6IG51bWJlcjtcblxuICAvKipcbiAgICogQWRkcyBhIG51bWJlciBvZiB5ZWFycywgbW9udGhzIG9yIGRheXMgdG8gYSBnaXZlbiBkYXRlLlxuICAgKlxuICAgKiAqIGBwZXJpb2RgIGNhbiBiZSBgeWAsIGBtYCBvciBgZGAgYW5kIGRlZmF1bHRzIHRvIGRheS5cbiAgICogKiBgbnVtYmVyYCBkZWZhdWx0cyB0byAxLlxuICAgKlxuICAgKiBBbHdheXMgcmV0dXJucyBhIG5ldyBkYXRlLlxuICAgKi9cbiAgYWJzdHJhY3QgZ2V0TmV4dChkYXRlOiBOZ2JEYXRlLCBwZXJpb2Q/OiBOZ2JQZXJpb2QsIG51bWJlcj86IG51bWJlcik6IE5nYkRhdGU7XG5cbiAgLyoqXG4gICAqIFN1YnRyYWN0cyBhIG51bWJlciBvZiB5ZWFycywgbW9udGhzIG9yIGRheXMgZnJvbSBhIGdpdmVuIGRhdGUuXG4gICAqXG4gICAqICogYHBlcmlvZGAgY2FuIGJlIGB5YCwgYG1gIG9yIGBkYCBhbmQgZGVmYXVsdHMgdG8gZGF5LlxuICAgKiAqIGBudW1iZXJgIGRlZmF1bHRzIHRvIDEuXG4gICAqXG4gICAqIEFsd2F5cyByZXR1cm5zIGEgbmV3IGRhdGUuXG4gICAqL1xuICBhYnN0cmFjdCBnZXRQcmV2KGRhdGU6IE5nYkRhdGUsIHBlcmlvZD86IE5nYlBlcmlvZCwgbnVtYmVyPzogbnVtYmVyKTogTmdiRGF0ZTtcblxuICAvKipcbiAgICogUmV0dXJucyB0aGUgd2VlayBudW1iZXIgZm9yIGEgZ2l2ZW4gd2Vlay5cbiAgICovXG4gIGFic3RyYWN0IGdldFdlZWtOdW1iZXIod2VlazogcmVhZG9ubHkgTmdiRGF0ZVtdLCBmaXJzdERheU9mV2VlazogbnVtYmVyKTogbnVtYmVyO1xuXG4gIC8qKlxuICAgKiBSZXR1cm5zIHRoZSB0b2RheSdzIGRhdGUuXG4gICAqL1xuICBhYnN0cmFjdCBnZXRUb2RheSgpOiBOZ2JEYXRlO1xuXG4gIC8qKlxuICAgKiBDaGVja3MgaWYgYSBkYXRlIGlzIHZhbGlkIGluIHRoZSBjdXJyZW50IGNhbGVuZGFyLlxuICAgKi9cbiAgYWJzdHJhY3QgaXNWYWxpZChkYXRlOiBOZ2JEYXRlKTogYm9vbGVhbjtcbn1cblxuQEluamVjdGFibGUoKVxuZXhwb3J0IGNsYXNzIE5nYkNhbGVuZGFyR3JlZ29yaWFuIGV4dGVuZHMgTmdiQ2FsZW5kYXIge1xuICBnZXREYXlzUGVyV2VlaygpIHsgcmV0dXJuIDc7IH1cblxuICBnZXRNb250aHMoKSB7IHJldHVybiBbMSwgMiwgMywgNCwgNSwgNiwgNywgOCwgOSwgMTAsIDExLCAxMl07IH1cblxuICBnZXRXZWVrc1Blck1vbnRoKCkgeyByZXR1cm4gNjsgfVxuXG4gIGdldE5leHQoZGF0ZTogTmdiRGF0ZSwgcGVyaW9kOiBOZ2JQZXJpb2QgPSAnZCcsIG51bWJlciA9IDEpIHtcbiAgICBsZXQganNEYXRlID0gdG9KU0RhdGUoZGF0ZSk7XG4gICAgbGV0IGNoZWNrTW9udGggPSB0cnVlO1xuICAgIGxldCBleHBlY3RlZE1vbnRoID0ganNEYXRlLmdldE1vbnRoKCk7XG5cbiAgICBzd2l0Y2ggKHBlcmlvZCkge1xuICAgICAgY2FzZSAneSc6XG4gICAgICAgIGpzRGF0ZS5zZXRGdWxsWWVhcihqc0RhdGUuZ2V0RnVsbFllYXIoKSArIG51bWJlcik7XG4gICAgICAgIGJyZWFrO1xuICAgICAgY2FzZSAnbSc6XG4gICAgICAgIGV4cGVjdGVkTW9udGggKz0gbnVtYmVyO1xuICAgICAgICBqc0RhdGUuc2V0TW9udGgoZXhwZWN0ZWRNb250aCk7XG4gICAgICAgIGV4cGVjdGVkTW9udGggPSBleHBlY3RlZE1vbnRoICUgMTI7XG4gICAgICAgIGlmIChleHBlY3RlZE1vbnRoIDwgMCkge1xuICAgICAgICAgIGV4cGVjdGVkTW9udGggPSBleHBlY3RlZE1vbnRoICsgMTI7XG4gICAgICAgIH1cbiAgICAgICAgYnJlYWs7XG4gICAgICBjYXNlICdkJzpcbiAgICAgICAganNEYXRlLnNldERhdGUoanNEYXRlLmdldERhdGUoKSArIG51bWJlcik7XG4gICAgICAgIGNoZWNrTW9udGggPSBmYWxzZTtcbiAgICAgICAgYnJlYWs7XG4gICAgICBkZWZhdWx0OlxuICAgICAgICByZXR1cm4gZGF0ZTtcbiAgICB9XG5cbiAgICBpZiAoY2hlY2tNb250aCAmJiBqc0RhdGUuZ2V0TW9udGgoKSAhPT0gZXhwZWN0ZWRNb250aCkge1xuICAgICAgLy8gdGhpcyBtZWFucyB0aGUgZGVzdGluYXRpb24gbW9udGggaGFzIGxlc3MgZGF5cyB0aGFuIHRoZSBpbml0aWFsIG1vbnRoXG4gICAgICAvLyBsZXQncyBnbyBiYWNrIHRvIHRoZSBlbmQgb2YgdGhlIHByZXZpb3VzIG1vbnRoOlxuICAgICAganNEYXRlLnNldERhdGUoMCk7XG4gICAgfVxuXG4gICAgcmV0dXJuIGZyb21KU0RhdGUoanNEYXRlKTtcbiAgfVxuXG4gIGdldFByZXYoZGF0ZTogTmdiRGF0ZSwgcGVyaW9kOiBOZ2JQZXJpb2QgPSAnZCcsIG51bWJlciA9IDEpIHsgcmV0dXJuIHRoaXMuZ2V0TmV4dChkYXRlLCBwZXJpb2QsIC1udW1iZXIpOyB9XG5cbiAgZ2V0V2Vla2RheShkYXRlOiBOZ2JEYXRlKSB7XG4gICAgbGV0IGpzRGF0ZSA9IHRvSlNEYXRlKGRhdGUpO1xuICAgIGxldCBkYXkgPSBqc0RhdGUuZ2V0RGF5KCk7XG4gICAgLy8gaW4gSlMgRGF0ZSBTdW49MCwgaW4gSVNPIDg2MDEgU3VuPTdcbiAgICByZXR1cm4gZGF5ID09PSAwID8gNyA6IGRheTtcbiAgfVxuXG4gIGdldFdlZWtOdW1iZXIod2VlazogcmVhZG9ubHkgTmdiRGF0ZVtdLCBmaXJzdERheU9mV2VlazogbnVtYmVyKSB7XG4gICAgLy8gaW4gSlMgRGF0ZSBTdW49MCwgaW4gSVNPIDg2MDEgU3VuPTdcbiAgICBpZiAoZmlyc3REYXlPZldlZWsgPT09IDcpIHtcbiAgICAgIGZpcnN0RGF5T2ZXZWVrID0gMDtcbiAgICB9XG5cbiAgICBjb25zdCB0aHVyc2RheUluZGV4ID0gKDQgKyA3IC0gZmlyc3REYXlPZldlZWspICUgNztcbiAgICBsZXQgZGF0ZSA9IHdlZWtbdGh1cnNkYXlJbmRleF07XG5cbiAgICBjb25zdCBqc0RhdGUgPSB0b0pTRGF0ZShkYXRlKTtcbiAgICBqc0RhdGUuc2V0RGF0ZShqc0RhdGUuZ2V0RGF0ZSgpICsgNCAtIChqc0RhdGUuZ2V0RGF5KCkgfHwgNykpOyAgLy8gVGh1cnNkYXlcbiAgICBjb25zdCB0aW1lID0ganNEYXRlLmdldFRpbWUoKTtcbiAgICBqc0RhdGUuc2V0TW9udGgoMCk7ICAvLyBDb21wYXJlIHdpdGggSmFuIDFcbiAgICBqc0RhdGUuc2V0RGF0ZSgxKTtcbiAgICByZXR1cm4gTWF0aC5mbG9vcihNYXRoLnJvdW5kKCh0aW1lIC0ganNEYXRlLmdldFRpbWUoKSkgLyA4NjQwMDAwMCkgLyA3KSArIDE7XG4gIH1cblxuICBnZXRUb2RheSgpOiBOZ2JEYXRlIHsgcmV0dXJuIGZyb21KU0RhdGUobmV3IERhdGUoKSk7IH1cblxuICBpc1ZhbGlkKGRhdGU6IE5nYkRhdGUpOiBib29sZWFuIHtcbiAgICBpZiAoIWRhdGUgfHwgIWlzSW50ZWdlcihkYXRlLnllYXIpIHx8ICFpc0ludGVnZXIoZGF0ZS5tb250aCkgfHwgIWlzSW50ZWdlcihkYXRlLmRheSkpIHtcbiAgICAgIHJldHVybiBmYWxzZTtcbiAgICB9XG5cbiAgICAvLyB5ZWFyIDAgZG9lc24ndCBleGlzdCBpbiBHcmVnb3JpYW4gY2FsZW5kYXJcbiAgICBpZiAoZGF0ZS55ZWFyID09PSAwKSB7XG4gICAgICByZXR1cm4gZmFsc2U7XG4gICAgfVxuXG4gICAgY29uc3QganNEYXRlID0gdG9KU0RhdGUoZGF0ZSk7XG5cbiAgICByZXR1cm4gIWlzTmFOKGpzRGF0ZS5nZXRUaW1lKCkpICYmIGpzRGF0ZS5nZXRGdWxsWWVhcigpID09PSBkYXRlLnllYXIgJiYganNEYXRlLmdldE1vbnRoKCkgKyAxID09PSBkYXRlLm1vbnRoICYmXG4gICAgICAgIGpzRGF0ZS5nZXREYXRlKCkgPT09IGRhdGUuZGF5O1xuICB9XG59XG4iXX0=