UNPKG

@hitachivantara/uikit-react-core

Version:

Core React components for the NEXT Design System.

128 lines (127 loc) 4.63 kB
import { jsxs, jsx } from "react/jsx-runtime"; import { useContext, useState, useEffect } from "react"; import { useDefaultProps } from "@hitachivantara/uikit-react-utils"; import { isKey } from "../../utils/keyboardUtils.js"; import { setId } from "../../utils/setId.js"; import { DEFAULT_LOCALE, isRange, getLocaleDateFormat, isDate, getFormattedDate, getStringFromDate, parseDateString, isSameDay } from "../utils.js"; import { useClasses } from "./CalendarHeader.styles.js"; import { staticClasses } from "./CalendarHeader.styles.js"; import { HvInput } from "../../Input/Input.js"; import { HvFormElementContext, HvFormElementDescriptorsContext } from "../../FormElement/context.js"; import { HvTypography } from "../../Typography/Typography.js"; const HvCalendarHeader = (props) => { const { id: idProp, value: valueProp, locale = DEFAULT_LOCALE, classes: classesProp, onChange, showEndDate, showDayOfWeek = false, onFocus, invalidDateLabel = "Invalid Date" } = useDefaultProps("HvCalendarHeader", props); const { classes, cx } = useClasses(classesProp); const context = useContext(HvFormElementContext); const { label } = useContext(HvFormElementDescriptorsContext); const localValue = isRange(valueProp) ? showEndDate ? valueProp.endDate : valueProp.startDate : valueProp; const [dateValue, setDateValue] = useState(localValue); const [editedValue, setEditedValue] = useState(null); const [displayValue, setDisplayValue] = useState(""); const [weekdayDisplay, setWeekdayDisplay] = useState(""); const id = idProp ?? setId(context.id, "calendarHeader"); const inputValue = editedValue ?? displayValue; const localeFormat = getLocaleDateFormat(locale); const [isValidValue, setIsValidValue] = useState( inputValue.length === 0 || inputValue && isDate(new Date(inputValue)) ); useEffect(() => { const valid = !localValue || isDate(new Date(localValue)); setIsValidValue(valid); if (valid) { if (!localValue) { setDisplayValue(""); setEditedValue(null); setWeekdayDisplay(""); return; } const weekday = new Intl.DateTimeFormat(locale, { weekday: "short" }).format(isDate(localValue) ? localValue : 0); setDisplayValue(getFormattedDate(localValue, locale)); setEditedValue(null); setWeekdayDisplay(weekday); } }, [localValue, locale]); const handleNewDate = (event, date) => { const localeParsedDate = parseDateString(date, locale); const isValidInput = isDate(localeParsedDate); const dateParsed = isValidInput ? localeParsedDate : new Date(date); if (!isSameDay(dateParsed, dateValue)) { setDateValue(dateParsed); onChange?.(event, dateParsed); } setIsValidValue(isValidInput); if (isValidInput) { setEditedValue(null); } }; const onBlurHandler = (event) => { if (editedValue == null) return; if (editedValue === "") { setIsValidValue(true); setEditedValue(null); return; } handleNewDate(event, editedValue); }; const keyDownHandler = (event) => { if (!isKey(event, "Enter") || editedValue == null || editedValue === "") return; event.preventDefault(); handleNewDate(event, editedValue); }; const onFocusHandler = (event) => { if (!localValue) return; const formattedDate = isValidValue && isDate(localValue) ? getStringFromDate(localValue, locale) : editedValue; setEditedValue(formattedDate); onFocus?.(event, formattedDate); }; const onChangeHandler = (event, val) => { setEditedValue(val); }; const isInvalid = !isValidValue && inputValue !== ""; return /* @__PURE__ */ jsxs( "div", { id, className: cx(classes.root, { [classes.invalid]: isInvalid }), children: [ showDayOfWeek && /* @__PURE__ */ jsx(HvTypography, { className: classes.headerDayOfWeek, children: weekdayDisplay || " " }), /* @__PURE__ */ jsx( HvInput, { type: "text", id: setId(id, "header-input"), placeholder: localeFormat, value: inputValue, "aria-labelledby": label?.[0]?.id, onBlur: onBlurHandler, onFocus: onFocusHandler, onChange: onChangeHandler, onKeyDown: keyDownHandler, status: isInvalid ? "invalid" : "valid", statusMessage: invalidDateLabel } ) ] } ); }; HvCalendarHeader.formElementType = "HvCalendarHeader"; export { HvCalendarHeader, staticClasses as calendarHeaderClasses };