diff --git a/projects/kit/components/calendar-range/calendar-range.component.ts b/projects/kit/components/calendar-range/calendar-range.component.ts index 63920cfc7769..d34bece62ddd 100644 --- a/projects/kit/components/calendar-range/calendar-range.component.ts +++ b/projects/kit/components/calendar-range/calendar-range.component.ts @@ -78,6 +78,7 @@ export class TuiCalendarRangeComponent implements TuiWithOptionalMinMax @Output() readonly valueChange = new EventEmitter(); + availableRange: TuiDayRange | null = null; previousValue: TuiDayRange | null = null; selectedActivePeriod: TuiDayRangePeriod | null = null; @@ -171,6 +172,7 @@ export class TuiCalendarRangeComponent implements TuiWithOptionalMinMax if (value === null || !value.isSingleDay) { this.value = new TuiDayRange(day, day); + this.availableRange = this.findAvailableRange(); return; } @@ -245,28 +247,47 @@ export class TuiCalendarRangeComponent implements TuiWithOptionalMinMax ): boolean { return ( disabledItemHandler(item) || - (!!value?.isSingleDay && - this.isExternalDaysDisabled(disabledItemHandler, value.from, item)) + (!!value?.isSingleDay && !this.availableRangeContainsItem(item)) ); } - private isExternalDaysDisabled( - disabledItemHandler: TuiBooleanHandler, - startDay: TuiDay, - item: TuiDay, - ): boolean { - let temp = item; + private availableRangeContainsItem(item: TuiDay): boolean { + if (this.availableRange === null) { + return true; + } + + const {from, to} = this.availableRange; + + return from.daySameOrBefore(item) && to.daySameOrAfter(item); + } - while (temp.dayBefore(startDay) || temp.dayAfter(startDay)) { - if (disabledItemHandler(temp)) { - return true; + private findAvailableRange(): TuiDayRange | null { + const {disabledItemHandler, value} = this; + + if (!value?.isSingleDay || disabledItemHandler === ALWAYS_FALSE_HANDLER) { + return null; + } + + let from = value.from; + let to = value.from; + + let leftShift = true; + let rightShift = true; + + while (leftShift || rightShift) { + leftShift = !disabledItemHandler(from.append({day: -1})); + + if (leftShift) { + from = from.append({day: -1}); } - const day = temp.dayBefore(startDay) ? 1 : -1; + rightShift = !disabledItemHandler(to.append({day: 1})); - temp = temp.append({day}); + if (rightShift) { + to = to.append({day: 1}); + } } - return false; + return new TuiDayRange(from, to); } }