UNPKG

@navinc/base-react-components

Version:
162 lines (159 loc) 7.74 kB
var __rest = (this && this.__rest) || function (s, e) { var t = {}; for (var p in s) if (Object.prototype.hasOwnProperty.call(s, p) && e.indexOf(p) < 0) t[p] = s[p]; if (s != null && typeof Object.getOwnPropertySymbols === "function") for (var i = 0, p = Object.getOwnPropertySymbols(s); i < p.length; i++) { if (e.indexOf(p[i]) < 0 && Object.prototype.propertyIsEnumerable.call(s, p[i])) t[p[i]] = s[p[i]]; } return t; }; import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime"; import { inputPattern, noop } from '@navinc/utils'; import predictInputValue from '@wojtekmaj/predict-input-value'; import { useEffect, useRef, useState } from 'react'; import { styled } from 'styled-components'; import { Copy } from '../copy.js'; import { Err, Errors } from './shared.js'; import { Input } from '../input.js'; const DAYS_IN_MONTH = 31; const MONTHS_IN_YEAR = 12; const DAYS_PATTERN = '99'; const MONTHS_PATTERN = '99'; const YEARS_PATTERN = '9999'; const createBackspaceHandler = (ref) => (e) => { if (ref.current && e.currentTarget.value.length === 0 && e.key === 'Backspace') { ref.current.focus(); } }; const createMaxNumberJumper = (ref, maxNumber) => (e) => { if (ref.current && Number(predictInputValue(e.nativeEvent)) > maxNumber) { ref.current.focus(); ref.current.select(); } }; export const DatePickerWrapper = styled.div.withConfig({ displayName: "brc-sc-DatePickerWrapper", componentId: "brc-sc-109vq2j" }) ` div > ${Copy} { text-align: left; } `; const StyledCopy = styled(Copy).withConfig({ displayName: "brc-sc-StyledCopy", componentId: "brc-sc-ea84jp" }) ` margin-bottom: 8px; `; const InputWrapper = styled.div.withConfig({ displayName: "brc-sc-InputWrapper", componentId: "brc-sc-1gc17n1" }) ` display: flex; flex-direction: row; gap: 12px; ${Input} { &:nth-child(1), &:nth-child(2) { width: 25%; min-width: 3.5em; } &:nth-child(3) { width: 50%; min-width: 4.5em; } } ${Errors} { display: none; } `; /** * @deprecated This component is deprecated and will be removed in a future release. Avoid using it in new code. */ export const DateSegmentComponent = (_a) => { var { errors = [], hasSpaceForErrors, isInvalid, label, onBlur, onFocus, onChange = noop, value, isPrivate } = _a, rest = __rest(_a, ["errors", "hasSpaceForErrors", "isInvalid", "label", "onBlur", "onFocus", "onChange", "value", "isPrivate"]); const monthRef = useRef(null); const dayRef = useRef(null); const yearRef = useRef(null); const timerRef = useRef(null); const [focused, setFocused] = useState(false); const [year = '', month = '', day = ''] = value.split('-'); const forwardToDay = createMaxNumberJumper(dayRef, MONTHS_IN_YEAR); const backToDay = createBackspaceHandler(dayRef); const forwardToYear = createMaxNumberJumper(yearRef, DAYS_IN_MONTH); const backToMonth = createBackspaceHandler(monthRef); const handleMonthChange = (event) => { const monthValue = inputPattern(event.target, MONTHS_PATTERN); if (Number(monthValue) > MONTHS_IN_YEAR) { return; } onChange(`${year}-${monthValue}-${day}`); // eslint-disable-next-line @typescript-eslint/no-unnecessary-condition -- may not be defined if (dayRef.current && ((monthValue === null || monthValue === void 0 ? void 0 : monthValue.length) >= 2 || Number(monthValue) > 1)) { dayRef.current.focus(); dayRef.current.select(); } }; const handleDayChange = (event) => { const dayValue = inputPattern(event.target, DAYS_PATTERN); if (Number(dayValue) > DAYS_IN_MONTH) { return; } onChange(`${year}-${month}-${dayValue}`); // eslint-disable-next-line @typescript-eslint/no-unnecessary-condition -- may not be defined if (yearRef.current && ((dayValue === null || dayValue === void 0 ? void 0 : dayValue.length) >= 2 || Number(dayValue) > 3)) { yearRef.current.focus(); yearRef.current.select(); } }; const handleYearChange = (event) => { const yearValue = inputPattern(event.target, YEARS_PATTERN); onChange(`${yearValue}-${month}-${day}`); }; const isInvalidOrHasErrors = isInvalid || !!errors.length; const internalOnBlur = () => { if (timerRef.current) { clearTimeout(timerRef.current); } timerRef.current = setTimeout(() => { setFocused(false); }, 0); }; const handleMonthBlur = () => { if (monthRef.current) { const monthValue = monthRef.current.value; // eslint-disable-next-line @typescript-eslint/no-unnecessary-condition -- may not be defined if ((monthValue === null || monthValue === void 0 ? void 0 : monthValue.length) === 1) { const paddedMonthValue = monthValue.padStart(2, '0'); monthRef.current.value = paddedMonthValue; onChange(`${year}-${paddedMonthValue}-${day}`); } } internalOnBlur(); }; const handleDayBlur = () => { if (dayRef.current) { const dayValue = dayRef.current.value; // eslint-disable-next-line @typescript-eslint/no-unnecessary-condition -- may not be defined if ((dayValue === null || dayValue === void 0 ? void 0 : dayValue.length) === 1) { const paddedDayValue = dayValue.padStart(2, '0'); dayRef.current.value = paddedDayValue; onChange(`${year}-${month}-${paddedDayValue}`); } } internalOnBlur(); }; const internalOnFocus = () => { if (timerRef.current) { clearTimeout(timerRef.current); } setFocused(true); }; useEffect(() => { if (timerRef.current && !focused && onBlur) { onBlur(); } else if (focused && onFocus) { onFocus(); } // eslint-disable-next-line react-hooks/exhaustive-deps }, [focused]); return (_jsxs(DatePickerWrapper, Object.assign({}, rest, { children: [label && (_jsx("div", { children: _jsx(StyledCopy, { size: "sm", children: label }) })), _jsxs(InputWrapper, { children: [_jsx(Input, { "data-testid": "date-segment-component:month", isInvalid: isInvalidOrHasErrors, label: "MM", name: "month", maxLength: 2, innerRef: monthRef, onBlur: handleMonthBlur, onFocus: internalOnFocus, onChange: handleMonthChange, onKeyDown: forwardToDay, type: "text", inputMode: "numeric", value: month || '', isPrivate: isPrivate }), _jsx(Input, { "data-testid": "date-segment-component:day", isInvalid: isInvalidOrHasErrors, label: "DD", name: "day", maxLength: 2, innerRef: dayRef, onBlur: handleDayBlur, onFocus: internalOnFocus, onChange: handleDayChange, onKeyDown: (e) => { backToMonth(e); forwardToYear(e); }, type: "text", inputMode: "numeric", value: day || '', isPrivate: isPrivate }), _jsx(Input, { "data-testid": "date-segment-component:year", isInvalid: isInvalidOrHasErrors, label: "YYYY", name: "year", innerRef: yearRef, onBlur: internalOnBlur, onFocus: internalOnFocus, onChange: handleYearChange, onKeyDown: backToDay, type: "text", inputMode: "numeric", value: year || '', isPrivate: isPrivate })] }), _jsx(Errors, { hasSpaceForErrors: hasSpaceForErrors, "data-testid": "date-segment-component:errors", children: !!errors.length && errors.map((err, i) => _jsx(Err, { children: err }, `err-${i}`)) })] }))); }; //# sourceMappingURL=date-segment-component.js.map