@yamada-ui/calendar
Version:
Yamada UI calendar component
201 lines (199 loc) • 5.55 kB
JavaScript
"use client"
import {
useCalendarContext
} from "./chunk-UMK6LUR5.mjs";
import {
disableAllTabIndex,
getFocused,
getFormattedLabel,
getRangeMonths,
isMonthInRange,
onShouldFocus
} from "./chunk-BPJGE3HG.mjs";
// src/use-month-list.tsx
import {
ariaAttr,
dataAttr,
handlerAll,
isArray,
isDisabled,
mergeRefs,
useUnmountEffect,
useUpdateEffect
} from "@yamada-ui/utils";
import { createRef, useCallback, useRef } from "react";
var useMonthList = () => {
const {
locale,
maxDate,
maxYear,
minDate,
minYear,
month,
monthFormat,
monthRefs,
setMonth,
setType,
setYear,
value: selectedValue,
year,
yearFormat,
__selectType
} = useCalendarContext();
const multi = isArray(selectedValue);
const beforeYear = useRef(null);
const rangeMonths = getRangeMonths(locale, monthFormat);
const label = getFormattedLabel(year, locale, yearFormat);
const onFocusPrev = useCallback(
(targetMonth) => {
if (targetMonth < 0) {
if (year <= minYear) return;
setYear((prev) => {
beforeYear.current = prev;
return prev - 1;
});
} else {
const ref = monthRefs.current.get(targetMonth);
if (ref == null ? void 0 : ref.current) {
ref.current.focus();
ref.current.tabIndex = 0;
}
}
},
[minYear, monthRefs, setYear, year]
);
const onFocusNext = useCallback(
(targetMonth) => {
if (11 < targetMonth) {
if (maxYear <= year) return;
setYear((prev) => {
beforeYear.current = prev;
return prev + 1;
});
} else {
const ref = monthRefs.current.get(targetMonth);
if (ref == null ? void 0 : ref.current) {
ref.current.focus();
ref.current.tabIndex = 0;
}
}
},
[maxYear, monthRefs, setYear, year]
);
const onKeyDown = useCallback(
(ev) => {
var _a;
const focusedMonth = (_a = getFocused(monthRefs)) != null ? _a : 0;
const actions = {
ArrowDown: () => focusedMonth + 3 <= 11 ? onFocusNext(focusedMonth + 3) : {},
ArrowLeft: () => onFocusPrev(focusedMonth - 1),
ArrowRight: () => onFocusNext(focusedMonth + 1),
ArrowUp: () => focusedMonth - 3 >= 0 ? onFocusPrev(focusedMonth - 3) : {},
End: () => onFocusNext(11),
Home: () => onFocusPrev(0)
};
const action = actions[ev.key];
if (!action) return;
ev.preventDefault();
ev.stopPropagation();
disableAllTabIndex(monthRefs);
action(ev);
},
[monthRefs, onFocusNext, onFocusPrev]
);
const onClick = useCallback(
(ev, month2) => {
ev.preventDefault();
ev.stopPropagation();
if (isDisabled(ev.target)) return;
setMonth(new Date(year, month2, 1));
setType("date", year, month2);
},
[year, setMonth, setType]
);
const getIsSelectedYear = useCallback(() => {
var _a;
if (__selectType === "date") {
return month.getFullYear() === year;
} else {
const selectedYear = !multi ? selectedValue == null ? void 0 : selectedValue.getFullYear() : (_a = selectedValue[0]) == null ? void 0 : _a.getFullYear();
return selectedYear === year;
}
}, [__selectType, multi, month, selectedValue, year]);
const getIsSelected = useCallback(
(value) => {
var _a;
if (__selectType === "date") {
return month.getMonth() === value;
} else {
const month2 = !multi ? selectedValue == null ? void 0 : selectedValue.getMonth() : (_a = selectedValue[0]) == null ? void 0 : _a.getMonth();
return month2 === value;
}
},
[__selectType, multi, month, selectedValue]
);
useUpdateEffect(() => {
if (typeof beforeYear.current !== "number") return;
onShouldFocus(monthRefs, () => false, beforeYear.current < year);
beforeYear.current = null;
}, [year]);
useUnmountEffect(() => {
monthRefs.current.clear();
});
const getGridProps = useCallback(
(props = {}) => ({
"aria-label": label,
role: "grid",
...props,
onKeyDown: handlerAll(onKeyDown, props.onKeyDown)
}),
[label, onKeyDown]
);
const getButtonProps = useCallback(
({ value, ...props }, ref = null) => {
const controlled = typeof beforeYear.current === "number";
const selectedYear = getIsSelectedYear();
const selected = selectedYear && getIsSelected(value);
const disabled = !isMonthInRange({
date: new Date(year, value),
maxDate,
minDate
});
monthRefs.current.set(value, createRef());
let tabIndex = -1;
if (controlled) {
tabIndex = -1;
} else if (!selectedYear && value === 0) {
tabIndex = 0;
} else if (selected) {
tabIndex = 0;
}
return {
ref: mergeRefs(ref, monthRefs.current.get(value)),
disabled,
...props,
"aria-disabled": ariaAttr(disabled),
"aria-selected": ariaAttr(selected),
"data-disabled": dataAttr(disabled),
"data-selected": dataAttr(selected),
"data-value": value,
tabIndex,
onClick: handlerAll(props.onClick, (ev) => onClick(ev, value))
};
},
[
getIsSelectedYear,
getIsSelected,
year,
minDate,
maxDate,
monthRefs,
onClick
]
);
return { label, rangeMonths, getButtonProps, getGridProps };
};
export {
useMonthList
};
//# sourceMappingURL=chunk-NLP6FHMB.mjs.map