diff --git a/projects/demo/src/modules/components/calendar-range/calendar-range.component.ts b/projects/demo/src/modules/components/calendar-range/calendar-range.component.ts index 5bcc4aa9a3e2..f4cfbadeefb0 100644 --- a/projects/demo/src/modules/components/calendar-range/calendar-range.component.ts +++ b/projects/demo/src/modules/components/calendar-range/calendar-range.component.ts @@ -44,6 +44,11 @@ export class ExampleTuiCalendarRangeComponent { HTML: import('./examples/4/index.html?raw'), }; + readonly example5: TuiDocExample = { + TypeScript: import('./examples/5/index.ts?raw'), + HTML: import('./examples/5/index.html?raw'), + }; + readonly minVariants = [ TUI_FIRST_DAY, new TuiDay(2017, 2, 5), diff --git a/projects/demo/src/modules/components/calendar-range/calendar-range.module.ts b/projects/demo/src/modules/components/calendar-range/calendar-range.module.ts index 85d72e450a7a..3ef0a6cafa88 100644 --- a/projects/demo/src/modules/components/calendar-range/calendar-range.module.ts +++ b/projects/demo/src/modules/components/calendar-range/calendar-range.module.ts @@ -2,7 +2,7 @@ import {CommonModule} from '@angular/common'; import {NgModule} from '@angular/core'; import {RouterModule} from '@angular/router'; import {TuiAddonDocModule, tuiGenerateRoutes} from '@taiga-ui/addon-doc'; -import {TuiLinkModule} from '@taiga-ui/core'; +import {TuiButtonModule, TuiLinkModule} from '@taiga-ui/core'; import {TuiCalendarRangeModule} from '@taiga-ui/kit'; import {ExampleTuiCalendarRangeComponent} from './calendar-range.component'; @@ -10,6 +10,7 @@ import {TuiCalendarRangeExample1} from './examples/1'; import {TuiCalendarRangeExample2} from './examples/2'; import {TuiCalendarRangeExample3} from './examples/3'; import {TuiCalendarRangeExample4} from './examples/4'; +import {TuiCalendarRangeExample5} from './examples/5'; @NgModule({ imports: [ @@ -17,6 +18,7 @@ import {TuiCalendarRangeExample4} from './examples/4'; CommonModule, TuiAddonDocModule, TuiLinkModule, + TuiButtonModule, RouterModule.forChild(tuiGenerateRoutes(ExampleTuiCalendarRangeComponent)), ], declarations: [ @@ -25,6 +27,7 @@ import {TuiCalendarRangeExample4} from './examples/4'; TuiCalendarRangeExample2, TuiCalendarRangeExample3, TuiCalendarRangeExample4, + TuiCalendarRangeExample5, ], exports: [ExampleTuiCalendarRangeComponent], }) diff --git a/projects/demo/src/modules/components/calendar-range/calendar-range.template.html b/projects/demo/src/modules/components/calendar-range/calendar-range.template.html index c9a6fa8ce6f3..70a8c6246f16 100644 --- a/projects/demo/src/modules/components/calendar-range/calendar-range.template.html +++ b/projects/demo/src/modules/components/calendar-range/calendar-range.template.html @@ -49,6 +49,14 @@ + + + + diff --git a/projects/demo/src/modules/components/calendar-range/examples/5/index.html b/projects/demo/src/modules/components/calendar-range/examples/5/index.html new file mode 100644 index 000000000000..61834ba374a6 --- /dev/null +++ b/projects/demo/src/modules/components/calendar-range/examples/5/index.html @@ -0,0 +1,26 @@ + + +

+ +

+ +

+ You are seeing {{ selected }}. + +

diff --git a/projects/demo/src/modules/components/calendar-range/examples/5/index.ts b/projects/demo/src/modules/components/calendar-range/examples/5/index.ts new file mode 100644 index 000000000000..d22fd6064097 --- /dev/null +++ b/projects/demo/src/modules/components/calendar-range/examples/5/index.ts @@ -0,0 +1,80 @@ +import {Component} from '@angular/core'; +import {changeDetection} from '@demo/emulate/change-detection'; +import {encapsulation} from '@demo/emulate/encapsulation'; +import {TuiDay, TuiDayRange} from '@taiga-ui/cdk'; +import {TuiDayRangePeriod} from '@taiga-ui/kit'; + +const today = TuiDay.currentLocal(); +const startOfWeek = today.append({day: -today.dayOfWeek()}); +const startOfMonth = today.append({day: 1 - today.day}); +const startOfQuarter = startOfMonth.append({month: -(startOfMonth.month % 3)}); + +@Component({ + selector: 'tui-calendar-range-example-5', + templateUrl: './index.html', + encapsulation, + changeDetection, +}) +export class TuiCalendarRangeExample5 { + readonly items = [ + new TuiDayRangePeriod( + new TuiDayRange(today.append({day: -30}), today), + 'Default', + ), + new TuiDayRangePeriod(new TuiDayRange(startOfWeek, today), 'Week'), + new TuiDayRangePeriod(new TuiDayRange(startOfMonth, today), 'Month'), + new TuiDayRangePeriod(new TuiDayRange(startOfQuarter, today), 'Quarter'), + ]; + + selected: TuiDayRangePeriod | null = this.default; + value: TuiDayRange | null = this.default.range; + + get default(): TuiDayRangePeriod { + return this.items[0]; + } + + get isDefault(): boolean { + return this.selected === this.default; + } + + get isSelected(): boolean { + return !!this.items.find(item => item === this.selected); + } + + get isLastVisible(): boolean { + return this.selected === this.items[this.items.length - 1]; + } + + get opposite(): TuiDayRangePeriod | null { + if (!this.isSelected) { + return null; + } + + switch (this.selected) { + case this.default: + return null; + case this.items[1]: + return this.items[2]; + case this.items[2]: + return this.items[3]; + case this.items[3]: + return null; + default: + return null; + } + } + + onValue(value: TuiDayRange | null): void { + this.value = value; + } + + reset(): void { + this.selected = this.default; + this.value = this.selected.range; + } + + toggle(): void { + this.selected = this.opposite; + this.value = this.selected?.range ?? null; + } +} diff --git a/projects/kit/components/calendar-range/calendar-range.component.ts b/projects/kit/components/calendar-range/calendar-range.component.ts index e6ac62dcbd77..a90d55d8e29d 100644 --- a/projects/kit/components/calendar-range/calendar-range.component.ts +++ b/projects/kit/components/calendar-range/calendar-range.component.ts @@ -48,6 +48,11 @@ import {takeUntil} from 'rxjs/operators'; providers: [TuiDestroyService], }) export class TuiCalendarRangeComponent implements TuiWithOptionalMinMax { + /** + * @deprecated use `item` + */ + private selectedPeriod: TuiDayRangePeriod | null = null; + @Input() defaultViewedMonth: TuiMonth = TuiMonth.currentLocal(); @@ -75,14 +80,18 @@ export class TuiCalendarRangeComponent implements TuiWithOptionalMinMax @Input() value: TuiDayRange | null = null; + @Input() + item: TuiDayRangePeriod | null = null; + @Output() readonly valueChange = new EventEmitter(); + @Output() + readonly itemChange = new EventEmitter(); + availableRange: TuiDayRange | null = null; previousValue: TuiDayRange | null = null; - selectedActivePeriod: TuiDayRangePeriod | null = null; - readonly maxLengthMapper = MAX_DAY_RANGE_LENGTH_MAPPER; get computedMin(): TuiDay { @@ -93,6 +102,20 @@ export class TuiCalendarRangeComponent implements TuiWithOptionalMinMax return this.max ?? TUI_LAST_DAY; } + /** + * @deprecated use `item` + */ + get selectedActivePeriod(): TuiDayRangePeriod | null { + return this.selectedPeriod; + } + + /** + * @deprecated use `item` + */ + set selectedActivePeriod(period: TuiDayRangePeriod | null) { + this.selectedPeriod = period; + } + constructor( @Optional() @Inject(TUI_CALENDAR_DATE_STREAM) @@ -180,17 +203,22 @@ export class TuiCalendarRangeComponent implements TuiWithOptionalMinMax if (value === null || !value.isSingleDay) { this.value = new TuiDayRange(day, day); this.availableRange = this.findAvailableRange(); + this.itemChange.emit(this.findItemByDayRange(this.value)); return; } - this.updateValue(TuiDayRange.sort(value.from, day)); + const sortedDayRange = TuiDayRange.sort(value.from, day); + + this.updateValue(sortedDayRange); + this.itemChange.emit(this.findItemByDayRange(sortedDayRange)); } onItemSelect(item: TuiDayRangePeriod | string): void { if (!tuiIsString(item)) { this.selectedActivePeriod = item; this.updateValue(item.range.dayLimit(this.min, this.max)); + this.itemChange.emit(item); return; } @@ -198,6 +226,7 @@ export class TuiCalendarRangeComponent implements TuiWithOptionalMinMax if (this.activePeriod !== null) { this.selectedActivePeriod = null; this.updateValue(null); + this.itemChange.emit(null); } } @@ -208,6 +237,7 @@ export class TuiCalendarRangeComponent implements TuiWithOptionalMinMax private get activePeriod(): TuiDayRangePeriod | null { return ( + this.item ?? this.selectedActivePeriod ?? (this.items.find(item => tuiNullableSame( @@ -297,4 +327,8 @@ export class TuiCalendarRangeComponent implements TuiWithOptionalMinMax return new TuiDayRange(from, to); } + + private findItemByDayRange(dayRange: TuiDayRange): TuiDayRangePeriod | null { + return this.items.find(item => dayRange.daySame(item.range)) ?? null; + } }