@gobrand/calendar-core 0.0.16 → 0.0.18
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/index.cjs +41 -27
- package/dist/index.d.cts +117 -34
- package/dist/index.d.ts +117 -34
- package/dist/index.js +41 -27
- package/package.json +1 -1
package/dist/index.cjs
CHANGED
|
@@ -82,16 +82,6 @@ function goToToday() {
|
|
|
82
82
|
const today = import_polyfill.Temporal.Now.plainDateISO();
|
|
83
83
|
return { year: today.year, month: today.month };
|
|
84
84
|
}
|
|
85
|
-
function getWeekdays(weekStartsOn = 1, locale = "en-US", format = "short") {
|
|
86
|
-
const referenceDate = import_polyfill.Temporal.PlainDate.from("2023-01-02");
|
|
87
|
-
const days = [];
|
|
88
|
-
for (let i = 0; i < 7; i++) {
|
|
89
|
-
const offset = (weekStartsOn - 1 + i + 7) % 7;
|
|
90
|
-
const date = referenceDate.add({ days: offset });
|
|
91
|
-
days.push(date.toLocaleString(locale, { weekday: format }));
|
|
92
|
-
}
|
|
93
|
-
return days;
|
|
94
|
-
}
|
|
95
85
|
function getMonthName(month, locale = "en-US") {
|
|
96
86
|
return month.toPlainDate({ day: 1 }).toLocaleString(locale, { month: "long" });
|
|
97
87
|
}
|
|
@@ -214,7 +204,7 @@ var import_polyfill3 = require("@js-temporal/polyfill");
|
|
|
214
204
|
function buildDay(date, options) {
|
|
215
205
|
const startHour = options?.startHour ?? 0;
|
|
216
206
|
const endHour = options?.endHour ?? 24;
|
|
217
|
-
const slotDuration = options?.slotDuration ??
|
|
207
|
+
const slotDuration = options?.slotDuration ?? 60;
|
|
218
208
|
const today = options?.today ?? import_polyfill3.Temporal.Now.plainDateISO();
|
|
219
209
|
const data = options?.data ?? [];
|
|
220
210
|
const accessor = options?.accessor;
|
|
@@ -384,8 +374,20 @@ function getDayDateRange(date, timeZone) {
|
|
|
384
374
|
return { start: startZoned, end: endZoned };
|
|
385
375
|
}
|
|
386
376
|
|
|
387
|
-
// src/
|
|
377
|
+
// src/utils/getWeekdays.ts
|
|
388
378
|
var import_polyfill6 = require("@js-temporal/polyfill");
|
|
379
|
+
function getWeekdays(weekStartsOn = 1, locale = "en-US", format = "short") {
|
|
380
|
+
const sunday = import_polyfill6.Temporal.PlainDate.from("2023-01-01");
|
|
381
|
+
const days = [];
|
|
382
|
+
for (let i = 0; i < 7; i++) {
|
|
383
|
+
const date = sunday.add({ days: (weekStartsOn + i) % 7 });
|
|
384
|
+
days.push(date.toLocaleString(locale, { weekday: format }));
|
|
385
|
+
}
|
|
386
|
+
return days;
|
|
387
|
+
}
|
|
388
|
+
|
|
389
|
+
// src/core/calendar.ts
|
|
390
|
+
var import_polyfill7 = require("@js-temporal/polyfill");
|
|
389
391
|
var import_store = require("@tanstack/store");
|
|
390
392
|
function computeDateRange(view, referenceDate, timeZone, weekStartsOn = 1) {
|
|
391
393
|
let start;
|
|
@@ -410,22 +412,22 @@ function computeDateRange(view, referenceDate, timeZone, weekStartsOn = 1) {
|
|
|
410
412
|
}
|
|
411
413
|
const startZoned = start.toZonedDateTime({
|
|
412
414
|
timeZone,
|
|
413
|
-
plainTime:
|
|
415
|
+
plainTime: import_polyfill7.Temporal.PlainTime.from("00:00:00")
|
|
414
416
|
});
|
|
415
417
|
const endZoned = end.toZonedDateTime({
|
|
416
418
|
timeZone,
|
|
417
|
-
plainTime:
|
|
419
|
+
plainTime: import_polyfill7.Temporal.PlainTime.from("23:59:59.999")
|
|
418
420
|
});
|
|
419
421
|
return { start: startZoned, end: endZoned };
|
|
420
422
|
}
|
|
421
423
|
function createCalendar(options) {
|
|
422
424
|
const configuredViews = Object.keys(options.views);
|
|
423
425
|
const defaultView = configuredViews[0];
|
|
424
|
-
const timeZone = options.timeZone ||
|
|
426
|
+
const timeZone = options.timeZone || import_polyfill7.Temporal.Now.timeZoneId();
|
|
425
427
|
const monthView = options.views.month;
|
|
426
428
|
const weekView = options.views.week;
|
|
427
429
|
const weekStartsOn = monthView?.weekStartsOn ?? weekView?.weekStartsOn ?? 1;
|
|
428
|
-
const initialReferenceDate = options.state?.referenceDate ||
|
|
430
|
+
const initialReferenceDate = options.state?.referenceDate || import_polyfill7.Temporal.Now.plainDateISO();
|
|
429
431
|
const initialView = options.state?.currentView || defaultView;
|
|
430
432
|
const initialDateRange = computeDateRange(
|
|
431
433
|
initialView,
|
|
@@ -450,18 +452,18 @@ function createCalendar(options) {
|
|
|
450
452
|
dateRange: initialDateRange,
|
|
451
453
|
...resolvedOptions.state
|
|
452
454
|
});
|
|
453
|
-
const getMonthImpl = () => {
|
|
455
|
+
const getMonthImpl = (data = []) => {
|
|
454
456
|
const state = store.state;
|
|
455
457
|
const { year, month } = state.referenceDate;
|
|
456
458
|
const monthView2 = _options.views.month;
|
|
457
459
|
if (!monthView2) throw new Error("Month view not configured");
|
|
458
460
|
return buildMonth(year, month, {
|
|
459
461
|
weekStartsOn: monthView2.weekStartsOn,
|
|
460
|
-
data
|
|
462
|
+
data,
|
|
461
463
|
accessor: monthView2.accessor
|
|
462
464
|
});
|
|
463
465
|
};
|
|
464
|
-
const getWeekImpl = () => {
|
|
466
|
+
const getWeekImpl = (data = []) => {
|
|
465
467
|
const state = store.state;
|
|
466
468
|
const weekView2 = _options.views.week;
|
|
467
469
|
if (!weekView2) throw new Error("Week view not configured");
|
|
@@ -470,11 +472,11 @@ function createCalendar(options) {
|
|
|
470
472
|
startHour: weekView2.startHour,
|
|
471
473
|
endHour: weekView2.endHour,
|
|
472
474
|
slotDuration: weekView2.slotDuration,
|
|
473
|
-
data
|
|
475
|
+
data,
|
|
474
476
|
accessor: weekView2.accessor
|
|
475
477
|
});
|
|
476
478
|
};
|
|
477
|
-
const getDayImpl = () => {
|
|
479
|
+
const getDayImpl = (data = []) => {
|
|
478
480
|
const state = store.state;
|
|
479
481
|
const dayView = _options.views.day;
|
|
480
482
|
if (!dayView) throw new Error("Day view not configured");
|
|
@@ -482,7 +484,7 @@ function createCalendar(options) {
|
|
|
482
484
|
startHour: dayView.startHour,
|
|
483
485
|
endHour: dayView.endHour,
|
|
484
486
|
slotDuration: dayView.slotDuration,
|
|
485
|
-
data
|
|
487
|
+
data,
|
|
486
488
|
accessor: dayView.accessor
|
|
487
489
|
});
|
|
488
490
|
};
|
|
@@ -510,7 +512,7 @@ function createCalendar(options) {
|
|
|
510
512
|
};
|
|
511
513
|
const nextMonthImpl = () => {
|
|
512
514
|
setStateImpl((old) => {
|
|
513
|
-
const current =
|
|
515
|
+
const current = import_polyfill7.Temporal.PlainYearMonth.from({
|
|
514
516
|
year: old.referenceDate.year,
|
|
515
517
|
month: old.referenceDate.month
|
|
516
518
|
});
|
|
@@ -522,7 +524,7 @@ function createCalendar(options) {
|
|
|
522
524
|
};
|
|
523
525
|
const previousMonthImpl = () => {
|
|
524
526
|
setStateImpl((old) => {
|
|
525
|
-
const current =
|
|
527
|
+
const current = import_polyfill7.Temporal.PlainYearMonth.from({
|
|
526
528
|
year: old.referenceDate.year,
|
|
527
529
|
month: old.referenceDate.month
|
|
528
530
|
});
|
|
@@ -557,7 +559,8 @@ function createCalendar(options) {
|
|
|
557
559
|
getWeek: getWeekImpl,
|
|
558
560
|
getDay: getDayImpl,
|
|
559
561
|
getTitle(view, locales, options2) {
|
|
560
|
-
|
|
562
|
+
const effectiveView = view ?? store.state.currentView ?? defaultView;
|
|
563
|
+
switch (effectiveView) {
|
|
561
564
|
case "month": {
|
|
562
565
|
const month = getMonthImpl();
|
|
563
566
|
const date = month.month.toPlainDate({ day: 1 });
|
|
@@ -594,6 +597,8 @@ function createCalendar(options) {
|
|
|
594
597
|
...options2
|
|
595
598
|
});
|
|
596
599
|
}
|
|
600
|
+
default:
|
|
601
|
+
throw new Error(`Unknown view: ${effectiveView}`);
|
|
597
602
|
}
|
|
598
603
|
},
|
|
599
604
|
getState() {
|
|
@@ -604,7 +609,7 @@ function createCalendar(options) {
|
|
|
604
609
|
previousMonth: previousMonthImpl,
|
|
605
610
|
goToMonth(year, month) {
|
|
606
611
|
setStateImpl(() => ({
|
|
607
|
-
referenceDate:
|
|
612
|
+
referenceDate: import_polyfill7.Temporal.PlainDate.from({ year, month, day: 1 })
|
|
608
613
|
}));
|
|
609
614
|
},
|
|
610
615
|
nextWeek: nextWeekImpl,
|
|
@@ -613,7 +618,7 @@ function createCalendar(options) {
|
|
|
613
618
|
previousDay: previousDayImpl,
|
|
614
619
|
goToToday() {
|
|
615
620
|
setStateImpl(() => ({
|
|
616
|
-
referenceDate:
|
|
621
|
+
referenceDate: import_polyfill7.Temporal.Now.plainDateISO()
|
|
617
622
|
}));
|
|
618
623
|
},
|
|
619
624
|
goToDate(date) {
|
|
@@ -664,6 +669,15 @@ function createCalendar(options) {
|
|
|
664
669
|
get dateRange() {
|
|
665
670
|
return store.state.dateRange;
|
|
666
671
|
},
|
|
672
|
+
getDateRange(view) {
|
|
673
|
+
const effectiveView = view ?? store.state.currentView ?? defaultView;
|
|
674
|
+
return computeDateRange(
|
|
675
|
+
effectiveView,
|
|
676
|
+
store.state.referenceDate,
|
|
677
|
+
timeZone,
|
|
678
|
+
weekStartsOn
|
|
679
|
+
);
|
|
680
|
+
},
|
|
667
681
|
get options() {
|
|
668
682
|
return _options;
|
|
669
683
|
},
|
package/dist/index.d.cts
CHANGED
|
@@ -73,17 +73,16 @@ type CalendarViewOptions<TItem> = {
|
|
|
73
73
|
day?: DayViewOptions<TItem>;
|
|
74
74
|
};
|
|
75
75
|
type CalendarOptions<TItem> = {
|
|
76
|
-
data: TItem[];
|
|
77
76
|
views: CalendarViewOptions<TItem>;
|
|
78
77
|
timeZone?: 'UTC' | string;
|
|
79
78
|
state?: Partial<CalendarState>;
|
|
80
|
-
onStateChange?: (
|
|
79
|
+
onStateChange?: (state: CalendarState) => void;
|
|
81
80
|
};
|
|
82
81
|
type HasView<Options, View extends 'month' | 'week' | 'day'> = Options extends {
|
|
83
82
|
views: infer V;
|
|
84
83
|
} ? V extends Record<View, unknown> ? V[View] extends undefined ? false : true : false : false;
|
|
85
84
|
type MonthMethods<TItem, TOptions> = HasView<TOptions, 'month'> extends true ? {
|
|
86
|
-
getMonth(): CalendarMonth<TItem>;
|
|
85
|
+
getMonth(data?: TItem[]): CalendarMonth<TItem>;
|
|
87
86
|
nextMonth(): void;
|
|
88
87
|
previousMonth(): void;
|
|
89
88
|
goToMonth(year: number, month: number): void;
|
|
@@ -94,7 +93,7 @@ type MonthMethods<TItem, TOptions> = HasView<TOptions, 'month'> extends true ? {
|
|
|
94
93
|
goToMonth?: never;
|
|
95
94
|
};
|
|
96
95
|
type WeekMethods<TItem, TOptions> = HasView<TOptions, 'week'> extends true ? {
|
|
97
|
-
getWeek(): CalendarWeekView<TItem>;
|
|
96
|
+
getWeek(data?: TItem[]): CalendarWeekView<TItem>;
|
|
98
97
|
nextWeek(): void;
|
|
99
98
|
previousWeek(): void;
|
|
100
99
|
} : {
|
|
@@ -103,7 +102,7 @@ type WeekMethods<TItem, TOptions> = HasView<TOptions, 'week'> extends true ? {
|
|
|
103
102
|
previousWeek?: never;
|
|
104
103
|
};
|
|
105
104
|
type DayMethods<TItem, TOptions> = HasView<TOptions, 'day'> extends true ? {
|
|
106
|
-
getDay(): CalendarDayView<TItem>;
|
|
105
|
+
getDay(data?: TItem[]): CalendarDayView<TItem>;
|
|
107
106
|
nextDay(): void;
|
|
108
107
|
previousDay(): void;
|
|
109
108
|
} : {
|
|
@@ -115,7 +114,7 @@ type ValidViews<Options> = Options extends {
|
|
|
115
114
|
views: infer V;
|
|
116
115
|
} ? keyof V & string : never;
|
|
117
116
|
type BaseCalendarMethods<Options> = {
|
|
118
|
-
getTitle(view
|
|
117
|
+
getTitle(view?: ValidViews<Options>, locales?: Temporal.LocalesArgument, options?: globalThis.Intl.DateTimeFormatOptions): string;
|
|
119
118
|
getState(): CalendarState;
|
|
120
119
|
setState(updater: CalendarState | ((old: CalendarState) => Partial<CalendarState>)): void;
|
|
121
120
|
goToToday(): void;
|
|
@@ -126,6 +125,7 @@ type BaseCalendarMethods<Options> = {
|
|
|
126
125
|
currentView: ValidViews<Options>;
|
|
127
126
|
setCurrentView(view: ValidViews<Options>): void;
|
|
128
127
|
dateRange: DateRange;
|
|
128
|
+
getDateRange(view?: ValidViews<Options>): DateRange;
|
|
129
129
|
options: Options;
|
|
130
130
|
setOptions(updater: (old: Options) => Options): void;
|
|
131
131
|
store: _tanstack_store.Store<CalendarState>;
|
|
@@ -133,71 +133,145 @@ type BaseCalendarMethods<Options> = {
|
|
|
133
133
|
hasWeekView(): boolean;
|
|
134
134
|
hasDayView(): boolean;
|
|
135
135
|
};
|
|
136
|
-
|
|
137
|
-
|
|
138
|
-
|
|
136
|
+
/**
|
|
137
|
+
* Unified calendar type with conditional methods based on configured views.
|
|
138
|
+
*
|
|
139
|
+
* @example
|
|
140
|
+
* // Calendar with specific options - methods are conditional
|
|
141
|
+
* const calendar = createCalendar<Post, typeof options>(options);
|
|
142
|
+
* calendar.getMonth([]); // Only available if month view configured
|
|
143
|
+
*
|
|
144
|
+
* @example
|
|
145
|
+
* // Generic calendar type - all methods available
|
|
146
|
+
* type AnyPostCalendar = Calendar<Post>;
|
|
147
|
+
*/
|
|
148
|
+
type Calendar<TItem, TOptions extends CalendarOptions<TItem> = CalendarOptions<TItem>> = BaseCalendarMethods<TOptions> & MonthMethods<TItem, TOptions> & WeekMethods<TItem, TOptions> & DayMethods<TItem, TOptions>;
|
|
149
|
+
/**
|
|
150
|
+
* Calendar instance with all view methods available and typed items.
|
|
151
|
+
* Use this for contexts where the specific view configuration is unknown at compile time,
|
|
152
|
+
* but you still want type-safe item data.
|
|
153
|
+
*
|
|
154
|
+
* @example
|
|
155
|
+
* // In React context - store with unknown, consume with specific type
|
|
156
|
+
* const context = createContext<CalendarInstance<unknown> | null>(null);
|
|
157
|
+
*
|
|
158
|
+
* // Consumer gets typed data
|
|
159
|
+
* function useCalendar<TItem>(): CalendarInstance<TItem> {
|
|
160
|
+
* return useContext(context) as CalendarInstance<TItem>;
|
|
161
|
+
* }
|
|
162
|
+
*/
|
|
163
|
+
type CalendarInstance<TItem = unknown> = {
|
|
164
|
+
getMonth(data?: TItem[]): CalendarMonth<TItem>;
|
|
165
|
+
getWeek(data?: TItem[]): CalendarWeekView<TItem>;
|
|
166
|
+
getDay(data?: TItem[]): CalendarDayView<TItem>;
|
|
167
|
+
getTitle(view?: ViewType, locales?: Temporal.LocalesArgument, options?: globalThis.Intl.DateTimeFormatOptions): string;
|
|
168
|
+
getState(): CalendarState;
|
|
169
|
+
setState(updater: CalendarState | ((old: CalendarState) => Partial<CalendarState>)): void;
|
|
170
|
+
goToToday(): void;
|
|
171
|
+
goToDate(date: Temporal.PlainDate): void;
|
|
172
|
+
next(view?: ViewType): void;
|
|
173
|
+
previous(view?: ViewType): void;
|
|
174
|
+
views: ReadonlyArray<string>;
|
|
175
|
+
currentView: string;
|
|
176
|
+
setCurrentView(view: string): void;
|
|
177
|
+
dateRange: DateRange;
|
|
178
|
+
getDateRange(view?: ViewType): DateRange;
|
|
179
|
+
options: CalendarOptions<TItem>;
|
|
180
|
+
setOptions(updater: (old: CalendarOptions<TItem>) => CalendarOptions<TItem>): void;
|
|
181
|
+
store: _tanstack_store.Store<CalendarState>;
|
|
182
|
+
nextMonth(): void;
|
|
183
|
+
previousMonth(): void;
|
|
184
|
+
goToMonth(year: number, month: number): void;
|
|
185
|
+
nextWeek(): void;
|
|
186
|
+
previousWeek(): void;
|
|
187
|
+
nextDay(): void;
|
|
188
|
+
previousDay(): void;
|
|
189
|
+
hasMonthView(): boolean;
|
|
190
|
+
hasWeekView(): boolean;
|
|
191
|
+
hasDayView(): boolean;
|
|
139
192
|
};
|
|
140
|
-
type Calendar<TItem, TOptionsOrViews = CalendarOptions<TItem>> = TOptionsOrViews extends CalendarOptions<TItem> ? BaseCalendarMethods<TOptionsOrViews> & MonthMethods<TItem, TOptionsOrViews> & WeekMethods<TItem, TOptionsOrViews> & DayMethods<TItem, TOptionsOrViews> : TOptionsOrViews extends CalendarViewOptions<TItem> ? BaseCalendarMethods<ViewsToOptions<TItem, TOptionsOrViews>> & MonthMethods<TItem, ViewsToOptions<TItem, TOptionsOrViews>> & WeekMethods<TItem, ViewsToOptions<TItem, TOptionsOrViews>> & DayMethods<TItem, ViewsToOptions<TItem, TOptionsOrViews>> : BaseCalendarMethods<CalendarOptions<TItem>> & MonthMethods<TItem, CalendarOptions<TItem>> & WeekMethods<TItem, CalendarOptions<TItem>> & DayMethods<TItem, CalendarOptions<TItem>>;
|
|
141
|
-
type InferViewNames<V extends CalendarViewOptions<unknown>> = keyof V & string;
|
|
142
|
-
type InferViewConfig<V extends CalendarViewOptions<unknown>, Name extends keyof V> = V[Name] extends infer Config ? {
|
|
143
|
-
name: Name;
|
|
144
|
-
config: Config;
|
|
145
|
-
} : never;
|
|
146
193
|
/**
|
|
147
|
-
* Extract the item type from a Calendar
|
|
194
|
+
* Extract the item type from a Calendar's options
|
|
148
195
|
* @example type Item = CalendarItemType<typeof calendar>; // Post
|
|
149
196
|
*/
|
|
150
|
-
type CalendarItemType<C extends
|
|
197
|
+
type CalendarItemType<C extends CalendarInstance> = C['options'] extends CalendarOptions<infer TItem> ? TItem : never;
|
|
151
198
|
/**
|
|
152
199
|
* Extract the views configuration from a Calendar type
|
|
153
200
|
* @example type Views = CalendarViewsConfig<typeof calendar>;
|
|
154
201
|
*/
|
|
155
|
-
type CalendarViewsConfig<C extends
|
|
202
|
+
type CalendarViewsConfig<C extends CalendarInstance> = C['options'] extends {
|
|
156
203
|
views: infer V;
|
|
157
|
-
} ? V :
|
|
204
|
+
} ? V : never;
|
|
158
205
|
/**
|
|
159
206
|
* Check if a Calendar has a specific view configured
|
|
160
207
|
* @example type HasMonth = HasViewType<typeof calendar, 'month'>; // true | false
|
|
161
208
|
*/
|
|
162
|
-
type HasViewType<C extends
|
|
209
|
+
type HasViewType<C extends CalendarInstance, V extends 'month' | 'week' | 'day'> = C['options'] extends CalendarOptions<infer TItem> ? HasView<C['options'], V> : false;
|
|
163
210
|
/**
|
|
164
211
|
* Extract valid view names as a union from a Calendar
|
|
165
212
|
* @example type Views = ValidViewNames<typeof calendar>; // 'month' | 'week'
|
|
166
213
|
*/
|
|
167
|
-
type ValidViewNames<C extends
|
|
168
|
-
/**
|
|
169
|
-
* Extract the item type from CalendarOptions before creating a calendar
|
|
170
|
-
* @example type Item = ItemTypeFromOptions<typeof options>; // Post
|
|
171
|
-
*/
|
|
172
|
-
type ItemTypeFromOptions<O extends CalendarOptions<any>> = O extends CalendarOptions<infer TItem> ? TItem : never;
|
|
214
|
+
type ValidViewNames<C extends CalendarInstance> = C['options'] extends CalendarOptions<infer TItem> ? ValidViews<C['options']> : never;
|
|
173
215
|
/**
|
|
174
216
|
* Base props for components that receive a Calendar
|
|
175
217
|
* @example
|
|
176
|
-
* function MyComponent<C extends
|
|
218
|
+
* function MyComponent<C extends CalendarInstance>(
|
|
177
219
|
* props: CalendarComponentProps<C>
|
|
178
220
|
* ) { ... }
|
|
179
221
|
*/
|
|
180
|
-
type CalendarComponentProps<C extends
|
|
222
|
+
type CalendarComponentProps<C extends CalendarInstance> = {
|
|
181
223
|
calendar: C;
|
|
182
224
|
};
|
|
183
225
|
/**
|
|
184
226
|
* Require that a Calendar has month view configured
|
|
185
227
|
* @example
|
|
186
|
-
* function MonthView<C extends
|
|
228
|
+
* function MonthView<C extends CalendarInstance>(
|
|
187
229
|
* props: { calendar: RequireMonthView<C> }
|
|
188
230
|
* ) {
|
|
189
231
|
* // calendar.getMonth() is guaranteed to exist
|
|
190
232
|
* }
|
|
191
233
|
*/
|
|
192
|
-
type RequireMonthView<C extends
|
|
234
|
+
type RequireMonthView<C extends CalendarInstance> = HasViewType<C, 'month'> extends true ? C : never;
|
|
193
235
|
/**
|
|
194
236
|
* Require that a Calendar has week view configured
|
|
195
237
|
*/
|
|
196
|
-
type RequireWeekView<C extends
|
|
238
|
+
type RequireWeekView<C extends CalendarInstance> = HasViewType<C, 'week'> extends true ? C : never;
|
|
197
239
|
/**
|
|
198
240
|
* Require that a Calendar has day view configured
|
|
199
241
|
*/
|
|
200
|
-
type RequireDayView<C extends
|
|
242
|
+
type RequireDayView<C extends CalendarInstance> = HasViewType<C, 'day'> extends true ? C : never;
|
|
243
|
+
/**
|
|
244
|
+
* Built-in view types
|
|
245
|
+
*/
|
|
246
|
+
type ViewType = 'month' | 'week' | 'day';
|
|
247
|
+
/**
|
|
248
|
+
* Discriminated union of all view results
|
|
249
|
+
*/
|
|
250
|
+
type ViewResult<TItem> = {
|
|
251
|
+
type: 'month';
|
|
252
|
+
data: CalendarMonth<TItem>;
|
|
253
|
+
} | {
|
|
254
|
+
type: 'week';
|
|
255
|
+
data: CalendarWeekView<TItem>;
|
|
256
|
+
} | {
|
|
257
|
+
type: 'day';
|
|
258
|
+
data: CalendarDayView<TItem>;
|
|
259
|
+
};
|
|
260
|
+
/**
|
|
261
|
+
* Conditional type that narrows ViewResult based on view name
|
|
262
|
+
* - If V is a specific view type, returns that specific result
|
|
263
|
+
* - If V is undefined, returns the full discriminated union
|
|
264
|
+
*/
|
|
265
|
+
type ViewResultFor<TItem, V extends ViewType | undefined> = V extends 'month' ? {
|
|
266
|
+
type: 'month';
|
|
267
|
+
data: CalendarMonth<TItem>;
|
|
268
|
+
} : V extends 'week' ? {
|
|
269
|
+
type: 'week';
|
|
270
|
+
data: CalendarWeekView<TItem>;
|
|
271
|
+
} : V extends 'day' ? {
|
|
272
|
+
type: 'day';
|
|
273
|
+
data: CalendarDayView<TItem>;
|
|
274
|
+
} : ViewResult<TItem>;
|
|
201
275
|
|
|
202
276
|
declare function functionalUpdate<T>(updater: T | ((old: T) => T), input: T): T;
|
|
203
277
|
declare function createCalendarAccessor<T, A extends CalendarAccessor<T> = CalendarAccessor<T>>(accessor: A): A;
|
|
@@ -211,7 +285,6 @@ declare function goToToday(): {
|
|
|
211
285
|
year: number;
|
|
212
286
|
month: number;
|
|
213
287
|
};
|
|
214
|
-
declare function getWeekdays(weekStartsOn?: 0 | 1 | 2 | 3 | 4 | 5 | 6, locale?: string | string[], format?: 'short' | 'long' | 'narrow'): string[];
|
|
215
288
|
declare function getMonthName(month: Temporal.PlainYearMonth, locale?: string): string;
|
|
216
289
|
declare function formatTime(time: Temporal.PlainTime, locale?: string): string;
|
|
217
290
|
declare function getTimeSlotHeight(slotDuration: number, hourHeight: number): number;
|
|
@@ -292,6 +365,16 @@ declare function getWeekDateRange(date: Temporal.PlainDate, timeZone: string, op
|
|
|
292
365
|
*/
|
|
293
366
|
declare function getDayDateRange(date: Temporal.PlainDate, timeZone: string): DateRange;
|
|
294
367
|
|
|
368
|
+
/**
|
|
369
|
+
* Returns an array of weekday names starting from the specified day.
|
|
370
|
+
*
|
|
371
|
+
* @param weekStartsOn - Day the week starts on (0=Sunday, 1=Monday, ..., 6=Saturday). Defaults to 1 (Monday).
|
|
372
|
+
* @param locale - Locale for formatting weekday names. Defaults to 'en-US'.
|
|
373
|
+
* @param format - Format for weekday names: 'short' (Mon), 'long' (Monday), or 'narrow' (M). Defaults to 'short'.
|
|
374
|
+
* @returns Array of 7 weekday names starting from weekStartsOn.
|
|
375
|
+
*/
|
|
376
|
+
declare function getWeekdays(weekStartsOn?: 0 | 1 | 2 | 3 | 4 | 5 | 6, locale?: string | string[], format?: 'short' | 'long' | 'narrow'): string[];
|
|
377
|
+
|
|
295
378
|
declare function createCalendar<TItem, TOptions extends CalendarOptions<TItem>>(options: TOptions): Calendar<TItem, TOptions>;
|
|
296
379
|
|
|
297
380
|
declare function createCalendarViews<TItem>(): <const TViews extends {
|
|
@@ -300,4 +383,4 @@ declare function createCalendarViews<TItem>(): <const TViews extends {
|
|
|
300
383
|
day?: DayViewOptions<TItem>;
|
|
301
384
|
}>(views: TViews) => TViews;
|
|
302
385
|
|
|
303
|
-
export { type Calendar, type CalendarAccessor, type CalendarComponentProps, type CalendarDay, type CalendarDayView, type CalendarItemType, type CalendarMonth, type CalendarOptions, type CalendarState, type CalendarViewOptions, type CalendarViewsConfig, type CalendarWeek, type CalendarWeekView, type DateRange, type DateRangeBounds, type DayViewOptions, type HasViewType, type
|
|
386
|
+
export { type Calendar, type CalendarAccessor, type CalendarComponentProps, type CalendarDay, type CalendarDayView, type CalendarInstance, type CalendarItemType, type CalendarMonth, type CalendarOptions, type CalendarState, type CalendarViewOptions, type CalendarViewsConfig, type CalendarWeek, type CalendarWeekView, type DateRange, type DateRangeBounds, type DayViewOptions, type HasViewType, type MonthViewOptions, type RequireDayView, type RequireMonthView, type RequireWeekView, type TimeSlot, type Updater, type ValidViewNames, type ViewResult, type ViewResultFor, type ViewType, type WeekDay, type WeekViewOptions, buildDay, buildMonth, buildWeek, convertToTimezone, createCalendar, createCalendarAccessor, createCalendarViews, createZonedDateTime, formatTime, functionalUpdate, getCurrentTimeZone, getDayDateRange, getDayRange, getEventPosition, getMonthDateRange, getMonthName, getMonthRange, getTimeSlotHeight, getTimezoneOffset, getWeekDateRange, getWeekRange, getWeekdays, goToToday, nextDay, nextMonth, nextWeek, previousDay, previousMonth, previousWeek };
|
package/dist/index.d.ts
CHANGED
|
@@ -73,17 +73,16 @@ type CalendarViewOptions<TItem> = {
|
|
|
73
73
|
day?: DayViewOptions<TItem>;
|
|
74
74
|
};
|
|
75
75
|
type CalendarOptions<TItem> = {
|
|
76
|
-
data: TItem[];
|
|
77
76
|
views: CalendarViewOptions<TItem>;
|
|
78
77
|
timeZone?: 'UTC' | string;
|
|
79
78
|
state?: Partial<CalendarState>;
|
|
80
|
-
onStateChange?: (
|
|
79
|
+
onStateChange?: (state: CalendarState) => void;
|
|
81
80
|
};
|
|
82
81
|
type HasView<Options, View extends 'month' | 'week' | 'day'> = Options extends {
|
|
83
82
|
views: infer V;
|
|
84
83
|
} ? V extends Record<View, unknown> ? V[View] extends undefined ? false : true : false : false;
|
|
85
84
|
type MonthMethods<TItem, TOptions> = HasView<TOptions, 'month'> extends true ? {
|
|
86
|
-
getMonth(): CalendarMonth<TItem>;
|
|
85
|
+
getMonth(data?: TItem[]): CalendarMonth<TItem>;
|
|
87
86
|
nextMonth(): void;
|
|
88
87
|
previousMonth(): void;
|
|
89
88
|
goToMonth(year: number, month: number): void;
|
|
@@ -94,7 +93,7 @@ type MonthMethods<TItem, TOptions> = HasView<TOptions, 'month'> extends true ? {
|
|
|
94
93
|
goToMonth?: never;
|
|
95
94
|
};
|
|
96
95
|
type WeekMethods<TItem, TOptions> = HasView<TOptions, 'week'> extends true ? {
|
|
97
|
-
getWeek(): CalendarWeekView<TItem>;
|
|
96
|
+
getWeek(data?: TItem[]): CalendarWeekView<TItem>;
|
|
98
97
|
nextWeek(): void;
|
|
99
98
|
previousWeek(): void;
|
|
100
99
|
} : {
|
|
@@ -103,7 +102,7 @@ type WeekMethods<TItem, TOptions> = HasView<TOptions, 'week'> extends true ? {
|
|
|
103
102
|
previousWeek?: never;
|
|
104
103
|
};
|
|
105
104
|
type DayMethods<TItem, TOptions> = HasView<TOptions, 'day'> extends true ? {
|
|
106
|
-
getDay(): CalendarDayView<TItem>;
|
|
105
|
+
getDay(data?: TItem[]): CalendarDayView<TItem>;
|
|
107
106
|
nextDay(): void;
|
|
108
107
|
previousDay(): void;
|
|
109
108
|
} : {
|
|
@@ -115,7 +114,7 @@ type ValidViews<Options> = Options extends {
|
|
|
115
114
|
views: infer V;
|
|
116
115
|
} ? keyof V & string : never;
|
|
117
116
|
type BaseCalendarMethods<Options> = {
|
|
118
|
-
getTitle(view
|
|
117
|
+
getTitle(view?: ValidViews<Options>, locales?: Temporal.LocalesArgument, options?: globalThis.Intl.DateTimeFormatOptions): string;
|
|
119
118
|
getState(): CalendarState;
|
|
120
119
|
setState(updater: CalendarState | ((old: CalendarState) => Partial<CalendarState>)): void;
|
|
121
120
|
goToToday(): void;
|
|
@@ -126,6 +125,7 @@ type BaseCalendarMethods<Options> = {
|
|
|
126
125
|
currentView: ValidViews<Options>;
|
|
127
126
|
setCurrentView(view: ValidViews<Options>): void;
|
|
128
127
|
dateRange: DateRange;
|
|
128
|
+
getDateRange(view?: ValidViews<Options>): DateRange;
|
|
129
129
|
options: Options;
|
|
130
130
|
setOptions(updater: (old: Options) => Options): void;
|
|
131
131
|
store: _tanstack_store.Store<CalendarState>;
|
|
@@ -133,71 +133,145 @@ type BaseCalendarMethods<Options> = {
|
|
|
133
133
|
hasWeekView(): boolean;
|
|
134
134
|
hasDayView(): boolean;
|
|
135
135
|
};
|
|
136
|
-
|
|
137
|
-
|
|
138
|
-
|
|
136
|
+
/**
|
|
137
|
+
* Unified calendar type with conditional methods based on configured views.
|
|
138
|
+
*
|
|
139
|
+
* @example
|
|
140
|
+
* // Calendar with specific options - methods are conditional
|
|
141
|
+
* const calendar = createCalendar<Post, typeof options>(options);
|
|
142
|
+
* calendar.getMonth([]); // Only available if month view configured
|
|
143
|
+
*
|
|
144
|
+
* @example
|
|
145
|
+
* // Generic calendar type - all methods available
|
|
146
|
+
* type AnyPostCalendar = Calendar<Post>;
|
|
147
|
+
*/
|
|
148
|
+
type Calendar<TItem, TOptions extends CalendarOptions<TItem> = CalendarOptions<TItem>> = BaseCalendarMethods<TOptions> & MonthMethods<TItem, TOptions> & WeekMethods<TItem, TOptions> & DayMethods<TItem, TOptions>;
|
|
149
|
+
/**
|
|
150
|
+
* Calendar instance with all view methods available and typed items.
|
|
151
|
+
* Use this for contexts where the specific view configuration is unknown at compile time,
|
|
152
|
+
* but you still want type-safe item data.
|
|
153
|
+
*
|
|
154
|
+
* @example
|
|
155
|
+
* // In React context - store with unknown, consume with specific type
|
|
156
|
+
* const context = createContext<CalendarInstance<unknown> | null>(null);
|
|
157
|
+
*
|
|
158
|
+
* // Consumer gets typed data
|
|
159
|
+
* function useCalendar<TItem>(): CalendarInstance<TItem> {
|
|
160
|
+
* return useContext(context) as CalendarInstance<TItem>;
|
|
161
|
+
* }
|
|
162
|
+
*/
|
|
163
|
+
type CalendarInstance<TItem = unknown> = {
|
|
164
|
+
getMonth(data?: TItem[]): CalendarMonth<TItem>;
|
|
165
|
+
getWeek(data?: TItem[]): CalendarWeekView<TItem>;
|
|
166
|
+
getDay(data?: TItem[]): CalendarDayView<TItem>;
|
|
167
|
+
getTitle(view?: ViewType, locales?: Temporal.LocalesArgument, options?: globalThis.Intl.DateTimeFormatOptions): string;
|
|
168
|
+
getState(): CalendarState;
|
|
169
|
+
setState(updater: CalendarState | ((old: CalendarState) => Partial<CalendarState>)): void;
|
|
170
|
+
goToToday(): void;
|
|
171
|
+
goToDate(date: Temporal.PlainDate): void;
|
|
172
|
+
next(view?: ViewType): void;
|
|
173
|
+
previous(view?: ViewType): void;
|
|
174
|
+
views: ReadonlyArray<string>;
|
|
175
|
+
currentView: string;
|
|
176
|
+
setCurrentView(view: string): void;
|
|
177
|
+
dateRange: DateRange;
|
|
178
|
+
getDateRange(view?: ViewType): DateRange;
|
|
179
|
+
options: CalendarOptions<TItem>;
|
|
180
|
+
setOptions(updater: (old: CalendarOptions<TItem>) => CalendarOptions<TItem>): void;
|
|
181
|
+
store: _tanstack_store.Store<CalendarState>;
|
|
182
|
+
nextMonth(): void;
|
|
183
|
+
previousMonth(): void;
|
|
184
|
+
goToMonth(year: number, month: number): void;
|
|
185
|
+
nextWeek(): void;
|
|
186
|
+
previousWeek(): void;
|
|
187
|
+
nextDay(): void;
|
|
188
|
+
previousDay(): void;
|
|
189
|
+
hasMonthView(): boolean;
|
|
190
|
+
hasWeekView(): boolean;
|
|
191
|
+
hasDayView(): boolean;
|
|
139
192
|
};
|
|
140
|
-
type Calendar<TItem, TOptionsOrViews = CalendarOptions<TItem>> = TOptionsOrViews extends CalendarOptions<TItem> ? BaseCalendarMethods<TOptionsOrViews> & MonthMethods<TItem, TOptionsOrViews> & WeekMethods<TItem, TOptionsOrViews> & DayMethods<TItem, TOptionsOrViews> : TOptionsOrViews extends CalendarViewOptions<TItem> ? BaseCalendarMethods<ViewsToOptions<TItem, TOptionsOrViews>> & MonthMethods<TItem, ViewsToOptions<TItem, TOptionsOrViews>> & WeekMethods<TItem, ViewsToOptions<TItem, TOptionsOrViews>> & DayMethods<TItem, ViewsToOptions<TItem, TOptionsOrViews>> : BaseCalendarMethods<CalendarOptions<TItem>> & MonthMethods<TItem, CalendarOptions<TItem>> & WeekMethods<TItem, CalendarOptions<TItem>> & DayMethods<TItem, CalendarOptions<TItem>>;
|
|
141
|
-
type InferViewNames<V extends CalendarViewOptions<unknown>> = keyof V & string;
|
|
142
|
-
type InferViewConfig<V extends CalendarViewOptions<unknown>, Name extends keyof V> = V[Name] extends infer Config ? {
|
|
143
|
-
name: Name;
|
|
144
|
-
config: Config;
|
|
145
|
-
} : never;
|
|
146
193
|
/**
|
|
147
|
-
* Extract the item type from a Calendar
|
|
194
|
+
* Extract the item type from a Calendar's options
|
|
148
195
|
* @example type Item = CalendarItemType<typeof calendar>; // Post
|
|
149
196
|
*/
|
|
150
|
-
type CalendarItemType<C extends
|
|
197
|
+
type CalendarItemType<C extends CalendarInstance> = C['options'] extends CalendarOptions<infer TItem> ? TItem : never;
|
|
151
198
|
/**
|
|
152
199
|
* Extract the views configuration from a Calendar type
|
|
153
200
|
* @example type Views = CalendarViewsConfig<typeof calendar>;
|
|
154
201
|
*/
|
|
155
|
-
type CalendarViewsConfig<C extends
|
|
202
|
+
type CalendarViewsConfig<C extends CalendarInstance> = C['options'] extends {
|
|
156
203
|
views: infer V;
|
|
157
|
-
} ? V :
|
|
204
|
+
} ? V : never;
|
|
158
205
|
/**
|
|
159
206
|
* Check if a Calendar has a specific view configured
|
|
160
207
|
* @example type HasMonth = HasViewType<typeof calendar, 'month'>; // true | false
|
|
161
208
|
*/
|
|
162
|
-
type HasViewType<C extends
|
|
209
|
+
type HasViewType<C extends CalendarInstance, V extends 'month' | 'week' | 'day'> = C['options'] extends CalendarOptions<infer TItem> ? HasView<C['options'], V> : false;
|
|
163
210
|
/**
|
|
164
211
|
* Extract valid view names as a union from a Calendar
|
|
165
212
|
* @example type Views = ValidViewNames<typeof calendar>; // 'month' | 'week'
|
|
166
213
|
*/
|
|
167
|
-
type ValidViewNames<C extends
|
|
168
|
-
/**
|
|
169
|
-
* Extract the item type from CalendarOptions before creating a calendar
|
|
170
|
-
* @example type Item = ItemTypeFromOptions<typeof options>; // Post
|
|
171
|
-
*/
|
|
172
|
-
type ItemTypeFromOptions<O extends CalendarOptions<any>> = O extends CalendarOptions<infer TItem> ? TItem : never;
|
|
214
|
+
type ValidViewNames<C extends CalendarInstance> = C['options'] extends CalendarOptions<infer TItem> ? ValidViews<C['options']> : never;
|
|
173
215
|
/**
|
|
174
216
|
* Base props for components that receive a Calendar
|
|
175
217
|
* @example
|
|
176
|
-
* function MyComponent<C extends
|
|
218
|
+
* function MyComponent<C extends CalendarInstance>(
|
|
177
219
|
* props: CalendarComponentProps<C>
|
|
178
220
|
* ) { ... }
|
|
179
221
|
*/
|
|
180
|
-
type CalendarComponentProps<C extends
|
|
222
|
+
type CalendarComponentProps<C extends CalendarInstance> = {
|
|
181
223
|
calendar: C;
|
|
182
224
|
};
|
|
183
225
|
/**
|
|
184
226
|
* Require that a Calendar has month view configured
|
|
185
227
|
* @example
|
|
186
|
-
* function MonthView<C extends
|
|
228
|
+
* function MonthView<C extends CalendarInstance>(
|
|
187
229
|
* props: { calendar: RequireMonthView<C> }
|
|
188
230
|
* ) {
|
|
189
231
|
* // calendar.getMonth() is guaranteed to exist
|
|
190
232
|
* }
|
|
191
233
|
*/
|
|
192
|
-
type RequireMonthView<C extends
|
|
234
|
+
type RequireMonthView<C extends CalendarInstance> = HasViewType<C, 'month'> extends true ? C : never;
|
|
193
235
|
/**
|
|
194
236
|
* Require that a Calendar has week view configured
|
|
195
237
|
*/
|
|
196
|
-
type RequireWeekView<C extends
|
|
238
|
+
type RequireWeekView<C extends CalendarInstance> = HasViewType<C, 'week'> extends true ? C : never;
|
|
197
239
|
/**
|
|
198
240
|
* Require that a Calendar has day view configured
|
|
199
241
|
*/
|
|
200
|
-
type RequireDayView<C extends
|
|
242
|
+
type RequireDayView<C extends CalendarInstance> = HasViewType<C, 'day'> extends true ? C : never;
|
|
243
|
+
/**
|
|
244
|
+
* Built-in view types
|
|
245
|
+
*/
|
|
246
|
+
type ViewType = 'month' | 'week' | 'day';
|
|
247
|
+
/**
|
|
248
|
+
* Discriminated union of all view results
|
|
249
|
+
*/
|
|
250
|
+
type ViewResult<TItem> = {
|
|
251
|
+
type: 'month';
|
|
252
|
+
data: CalendarMonth<TItem>;
|
|
253
|
+
} | {
|
|
254
|
+
type: 'week';
|
|
255
|
+
data: CalendarWeekView<TItem>;
|
|
256
|
+
} | {
|
|
257
|
+
type: 'day';
|
|
258
|
+
data: CalendarDayView<TItem>;
|
|
259
|
+
};
|
|
260
|
+
/**
|
|
261
|
+
* Conditional type that narrows ViewResult based on view name
|
|
262
|
+
* - If V is a specific view type, returns that specific result
|
|
263
|
+
* - If V is undefined, returns the full discriminated union
|
|
264
|
+
*/
|
|
265
|
+
type ViewResultFor<TItem, V extends ViewType | undefined> = V extends 'month' ? {
|
|
266
|
+
type: 'month';
|
|
267
|
+
data: CalendarMonth<TItem>;
|
|
268
|
+
} : V extends 'week' ? {
|
|
269
|
+
type: 'week';
|
|
270
|
+
data: CalendarWeekView<TItem>;
|
|
271
|
+
} : V extends 'day' ? {
|
|
272
|
+
type: 'day';
|
|
273
|
+
data: CalendarDayView<TItem>;
|
|
274
|
+
} : ViewResult<TItem>;
|
|
201
275
|
|
|
202
276
|
declare function functionalUpdate<T>(updater: T | ((old: T) => T), input: T): T;
|
|
203
277
|
declare function createCalendarAccessor<T, A extends CalendarAccessor<T> = CalendarAccessor<T>>(accessor: A): A;
|
|
@@ -211,7 +285,6 @@ declare function goToToday(): {
|
|
|
211
285
|
year: number;
|
|
212
286
|
month: number;
|
|
213
287
|
};
|
|
214
|
-
declare function getWeekdays(weekStartsOn?: 0 | 1 | 2 | 3 | 4 | 5 | 6, locale?: string | string[], format?: 'short' | 'long' | 'narrow'): string[];
|
|
215
288
|
declare function getMonthName(month: Temporal.PlainYearMonth, locale?: string): string;
|
|
216
289
|
declare function formatTime(time: Temporal.PlainTime, locale?: string): string;
|
|
217
290
|
declare function getTimeSlotHeight(slotDuration: number, hourHeight: number): number;
|
|
@@ -292,6 +365,16 @@ declare function getWeekDateRange(date: Temporal.PlainDate, timeZone: string, op
|
|
|
292
365
|
*/
|
|
293
366
|
declare function getDayDateRange(date: Temporal.PlainDate, timeZone: string): DateRange;
|
|
294
367
|
|
|
368
|
+
/**
|
|
369
|
+
* Returns an array of weekday names starting from the specified day.
|
|
370
|
+
*
|
|
371
|
+
* @param weekStartsOn - Day the week starts on (0=Sunday, 1=Monday, ..., 6=Saturday). Defaults to 1 (Monday).
|
|
372
|
+
* @param locale - Locale for formatting weekday names. Defaults to 'en-US'.
|
|
373
|
+
* @param format - Format for weekday names: 'short' (Mon), 'long' (Monday), or 'narrow' (M). Defaults to 'short'.
|
|
374
|
+
* @returns Array of 7 weekday names starting from weekStartsOn.
|
|
375
|
+
*/
|
|
376
|
+
declare function getWeekdays(weekStartsOn?: 0 | 1 | 2 | 3 | 4 | 5 | 6, locale?: string | string[], format?: 'short' | 'long' | 'narrow'): string[];
|
|
377
|
+
|
|
295
378
|
declare function createCalendar<TItem, TOptions extends CalendarOptions<TItem>>(options: TOptions): Calendar<TItem, TOptions>;
|
|
296
379
|
|
|
297
380
|
declare function createCalendarViews<TItem>(): <const TViews extends {
|
|
@@ -300,4 +383,4 @@ declare function createCalendarViews<TItem>(): <const TViews extends {
|
|
|
300
383
|
day?: DayViewOptions<TItem>;
|
|
301
384
|
}>(views: TViews) => TViews;
|
|
302
385
|
|
|
303
|
-
export { type Calendar, type CalendarAccessor, type CalendarComponentProps, type CalendarDay, type CalendarDayView, type CalendarItemType, type CalendarMonth, type CalendarOptions, type CalendarState, type CalendarViewOptions, type CalendarViewsConfig, type CalendarWeek, type CalendarWeekView, type DateRange, type DateRangeBounds, type DayViewOptions, type HasViewType, type
|
|
386
|
+
export { type Calendar, type CalendarAccessor, type CalendarComponentProps, type CalendarDay, type CalendarDayView, type CalendarInstance, type CalendarItemType, type CalendarMonth, type CalendarOptions, type CalendarState, type CalendarViewOptions, type CalendarViewsConfig, type CalendarWeek, type CalendarWeekView, type DateRange, type DateRangeBounds, type DayViewOptions, type HasViewType, type MonthViewOptions, type RequireDayView, type RequireMonthView, type RequireWeekView, type TimeSlot, type Updater, type ValidViewNames, type ViewResult, type ViewResultFor, type ViewType, type WeekDay, type WeekViewOptions, buildDay, buildMonth, buildWeek, convertToTimezone, createCalendar, createCalendarAccessor, createCalendarViews, createZonedDateTime, formatTime, functionalUpdate, getCurrentTimeZone, getDayDateRange, getDayRange, getEventPosition, getMonthDateRange, getMonthName, getMonthRange, getTimeSlotHeight, getTimezoneOffset, getWeekDateRange, getWeekRange, getWeekdays, goToToday, nextDay, nextMonth, nextWeek, previousDay, previousMonth, previousWeek };
|
package/dist/index.js
CHANGED
|
@@ -28,16 +28,6 @@ function goToToday() {
|
|
|
28
28
|
const today = Temporal.Now.plainDateISO();
|
|
29
29
|
return { year: today.year, month: today.month };
|
|
30
30
|
}
|
|
31
|
-
function getWeekdays(weekStartsOn = 1, locale = "en-US", format = "short") {
|
|
32
|
-
const referenceDate = Temporal.PlainDate.from("2023-01-02");
|
|
33
|
-
const days = [];
|
|
34
|
-
for (let i = 0; i < 7; i++) {
|
|
35
|
-
const offset = (weekStartsOn - 1 + i + 7) % 7;
|
|
36
|
-
const date = referenceDate.add({ days: offset });
|
|
37
|
-
days.push(date.toLocaleString(locale, { weekday: format }));
|
|
38
|
-
}
|
|
39
|
-
return days;
|
|
40
|
-
}
|
|
41
31
|
function getMonthName(month, locale = "en-US") {
|
|
42
32
|
return month.toPlainDate({ day: 1 }).toLocaleString(locale, { month: "long" });
|
|
43
33
|
}
|
|
@@ -160,7 +150,7 @@ import { Temporal as Temporal3 } from "@js-temporal/polyfill";
|
|
|
160
150
|
function buildDay(date, options) {
|
|
161
151
|
const startHour = options?.startHour ?? 0;
|
|
162
152
|
const endHour = options?.endHour ?? 24;
|
|
163
|
-
const slotDuration = options?.slotDuration ??
|
|
153
|
+
const slotDuration = options?.slotDuration ?? 60;
|
|
164
154
|
const today = options?.today ?? Temporal3.Now.plainDateISO();
|
|
165
155
|
const data = options?.data ?? [];
|
|
166
156
|
const accessor = options?.accessor;
|
|
@@ -330,8 +320,20 @@ function getDayDateRange(date, timeZone) {
|
|
|
330
320
|
return { start: startZoned, end: endZoned };
|
|
331
321
|
}
|
|
332
322
|
|
|
333
|
-
// src/
|
|
323
|
+
// src/utils/getWeekdays.ts
|
|
334
324
|
import { Temporal as Temporal6 } from "@js-temporal/polyfill";
|
|
325
|
+
function getWeekdays(weekStartsOn = 1, locale = "en-US", format = "short") {
|
|
326
|
+
const sunday = Temporal6.PlainDate.from("2023-01-01");
|
|
327
|
+
const days = [];
|
|
328
|
+
for (let i = 0; i < 7; i++) {
|
|
329
|
+
const date = sunday.add({ days: (weekStartsOn + i) % 7 });
|
|
330
|
+
days.push(date.toLocaleString(locale, { weekday: format }));
|
|
331
|
+
}
|
|
332
|
+
return days;
|
|
333
|
+
}
|
|
334
|
+
|
|
335
|
+
// src/core/calendar.ts
|
|
336
|
+
import { Temporal as Temporal7 } from "@js-temporal/polyfill";
|
|
335
337
|
import { Store } from "@tanstack/store";
|
|
336
338
|
function computeDateRange(view, referenceDate, timeZone, weekStartsOn = 1) {
|
|
337
339
|
let start;
|
|
@@ -356,22 +358,22 @@ function computeDateRange(view, referenceDate, timeZone, weekStartsOn = 1) {
|
|
|
356
358
|
}
|
|
357
359
|
const startZoned = start.toZonedDateTime({
|
|
358
360
|
timeZone,
|
|
359
|
-
plainTime:
|
|
361
|
+
plainTime: Temporal7.PlainTime.from("00:00:00")
|
|
360
362
|
});
|
|
361
363
|
const endZoned = end.toZonedDateTime({
|
|
362
364
|
timeZone,
|
|
363
|
-
plainTime:
|
|
365
|
+
plainTime: Temporal7.PlainTime.from("23:59:59.999")
|
|
364
366
|
});
|
|
365
367
|
return { start: startZoned, end: endZoned };
|
|
366
368
|
}
|
|
367
369
|
function createCalendar(options) {
|
|
368
370
|
const configuredViews = Object.keys(options.views);
|
|
369
371
|
const defaultView = configuredViews[0];
|
|
370
|
-
const timeZone = options.timeZone ||
|
|
372
|
+
const timeZone = options.timeZone || Temporal7.Now.timeZoneId();
|
|
371
373
|
const monthView = options.views.month;
|
|
372
374
|
const weekView = options.views.week;
|
|
373
375
|
const weekStartsOn = monthView?.weekStartsOn ?? weekView?.weekStartsOn ?? 1;
|
|
374
|
-
const initialReferenceDate = options.state?.referenceDate ||
|
|
376
|
+
const initialReferenceDate = options.state?.referenceDate || Temporal7.Now.plainDateISO();
|
|
375
377
|
const initialView = options.state?.currentView || defaultView;
|
|
376
378
|
const initialDateRange = computeDateRange(
|
|
377
379
|
initialView,
|
|
@@ -396,18 +398,18 @@ function createCalendar(options) {
|
|
|
396
398
|
dateRange: initialDateRange,
|
|
397
399
|
...resolvedOptions.state
|
|
398
400
|
});
|
|
399
|
-
const getMonthImpl = () => {
|
|
401
|
+
const getMonthImpl = (data = []) => {
|
|
400
402
|
const state = store.state;
|
|
401
403
|
const { year, month } = state.referenceDate;
|
|
402
404
|
const monthView2 = _options.views.month;
|
|
403
405
|
if (!monthView2) throw new Error("Month view not configured");
|
|
404
406
|
return buildMonth(year, month, {
|
|
405
407
|
weekStartsOn: monthView2.weekStartsOn,
|
|
406
|
-
data
|
|
408
|
+
data,
|
|
407
409
|
accessor: monthView2.accessor
|
|
408
410
|
});
|
|
409
411
|
};
|
|
410
|
-
const getWeekImpl = () => {
|
|
412
|
+
const getWeekImpl = (data = []) => {
|
|
411
413
|
const state = store.state;
|
|
412
414
|
const weekView2 = _options.views.week;
|
|
413
415
|
if (!weekView2) throw new Error("Week view not configured");
|
|
@@ -416,11 +418,11 @@ function createCalendar(options) {
|
|
|
416
418
|
startHour: weekView2.startHour,
|
|
417
419
|
endHour: weekView2.endHour,
|
|
418
420
|
slotDuration: weekView2.slotDuration,
|
|
419
|
-
data
|
|
421
|
+
data,
|
|
420
422
|
accessor: weekView2.accessor
|
|
421
423
|
});
|
|
422
424
|
};
|
|
423
|
-
const getDayImpl = () => {
|
|
425
|
+
const getDayImpl = (data = []) => {
|
|
424
426
|
const state = store.state;
|
|
425
427
|
const dayView = _options.views.day;
|
|
426
428
|
if (!dayView) throw new Error("Day view not configured");
|
|
@@ -428,7 +430,7 @@ function createCalendar(options) {
|
|
|
428
430
|
startHour: dayView.startHour,
|
|
429
431
|
endHour: dayView.endHour,
|
|
430
432
|
slotDuration: dayView.slotDuration,
|
|
431
|
-
data
|
|
433
|
+
data,
|
|
432
434
|
accessor: dayView.accessor
|
|
433
435
|
});
|
|
434
436
|
};
|
|
@@ -456,7 +458,7 @@ function createCalendar(options) {
|
|
|
456
458
|
};
|
|
457
459
|
const nextMonthImpl = () => {
|
|
458
460
|
setStateImpl((old) => {
|
|
459
|
-
const current =
|
|
461
|
+
const current = Temporal7.PlainYearMonth.from({
|
|
460
462
|
year: old.referenceDate.year,
|
|
461
463
|
month: old.referenceDate.month
|
|
462
464
|
});
|
|
@@ -468,7 +470,7 @@ function createCalendar(options) {
|
|
|
468
470
|
};
|
|
469
471
|
const previousMonthImpl = () => {
|
|
470
472
|
setStateImpl((old) => {
|
|
471
|
-
const current =
|
|
473
|
+
const current = Temporal7.PlainYearMonth.from({
|
|
472
474
|
year: old.referenceDate.year,
|
|
473
475
|
month: old.referenceDate.month
|
|
474
476
|
});
|
|
@@ -503,7 +505,8 @@ function createCalendar(options) {
|
|
|
503
505
|
getWeek: getWeekImpl,
|
|
504
506
|
getDay: getDayImpl,
|
|
505
507
|
getTitle(view, locales, options2) {
|
|
506
|
-
|
|
508
|
+
const effectiveView = view ?? store.state.currentView ?? defaultView;
|
|
509
|
+
switch (effectiveView) {
|
|
507
510
|
case "month": {
|
|
508
511
|
const month = getMonthImpl();
|
|
509
512
|
const date = month.month.toPlainDate({ day: 1 });
|
|
@@ -540,6 +543,8 @@ function createCalendar(options) {
|
|
|
540
543
|
...options2
|
|
541
544
|
});
|
|
542
545
|
}
|
|
546
|
+
default:
|
|
547
|
+
throw new Error(`Unknown view: ${effectiveView}`);
|
|
543
548
|
}
|
|
544
549
|
},
|
|
545
550
|
getState() {
|
|
@@ -550,7 +555,7 @@ function createCalendar(options) {
|
|
|
550
555
|
previousMonth: previousMonthImpl,
|
|
551
556
|
goToMonth(year, month) {
|
|
552
557
|
setStateImpl(() => ({
|
|
553
|
-
referenceDate:
|
|
558
|
+
referenceDate: Temporal7.PlainDate.from({ year, month, day: 1 })
|
|
554
559
|
}));
|
|
555
560
|
},
|
|
556
561
|
nextWeek: nextWeekImpl,
|
|
@@ -559,7 +564,7 @@ function createCalendar(options) {
|
|
|
559
564
|
previousDay: previousDayImpl,
|
|
560
565
|
goToToday() {
|
|
561
566
|
setStateImpl(() => ({
|
|
562
|
-
referenceDate:
|
|
567
|
+
referenceDate: Temporal7.Now.plainDateISO()
|
|
563
568
|
}));
|
|
564
569
|
},
|
|
565
570
|
goToDate(date) {
|
|
@@ -610,6 +615,15 @@ function createCalendar(options) {
|
|
|
610
615
|
get dateRange() {
|
|
611
616
|
return store.state.dateRange;
|
|
612
617
|
},
|
|
618
|
+
getDateRange(view) {
|
|
619
|
+
const effectiveView = view ?? store.state.currentView ?? defaultView;
|
|
620
|
+
return computeDateRange(
|
|
621
|
+
effectiveView,
|
|
622
|
+
store.state.referenceDate,
|
|
623
|
+
timeZone,
|
|
624
|
+
weekStartsOn
|
|
625
|
+
);
|
|
626
|
+
},
|
|
613
627
|
get options() {
|
|
614
628
|
return _options;
|
|
615
629
|
},
|