♻️(react) revamp clear date picker button

Revamp DatePicker component to enhance range functionalities by elevating
the clear button, resulting in the utilization of a single button across
multiple DateField inputs.
This commit is contained in:
Lebaud Antoine
2023-06-14 16:58:23 +02:00
committed by aleb_the_flash
parent 0378b3fa0c
commit 87ec3a5061
4 changed files with 39 additions and 32 deletions

View File

@@ -52,37 +52,17 @@ export const DateField = (props: AriaDatePickerProps<DateValue>) => {
}); });
const ref = useRef<HTMLDivElement>(null); const ref = useRef<HTMLDivElement>(null);
const { fieldProps } = useDateField(props, state, ref); const { fieldProps } = useDateField(props, state, ref);
const { t } = useCunningham();
return ( return (
<> <div className="c__date-picker__inner__value" {...fieldProps} ref={ref}>
<div className="c__date-picker__inner__value" {...fieldProps} ref={ref}> {state.segments.map((segment, i, segments) => (
{state.segments.map((segment, i, segments) => ( <DateSegmentInput
<DateSegmentInput key={i}
key={i} currentSegment={segment}
currentSegment={segment} previousSegment={segments[i - 1]}
previousSegment={segments[i - 1]} state={state}
state={state}
/>
))}
</div>
{!props.isDisabled && (
<Button
className={classNames("c__date-picker__inner__action", {
"c__date-picker__inner__action--empty": !state.value,
})}
color="tertiary"
size="small"
icon={<span className="material-icons">cancel</span>}
onClick={() => {
// "era" option doesn't clear partially filled dataField.
state.clearSegment("day");
state.clearSegment("month");
state.clearSegment("year");
}}
aria-label={t("components.forms.date_picker.clear_button_aria_label")}
/> />
)} ))}
</> </div>
); );
}; };

View File

@@ -62,7 +62,9 @@
height: auto; height: auto;
&.c__button--small.c__button--icon-only { &.c__button--small.c__button--icon-only {
width: 1.25rem; width: fit-content;
height: fit-content;
margin: 1.65rem 0 0 0;
} }
&--empty { &--empty {
@@ -71,6 +73,13 @@
.material-icons { .material-icons {
font-size: 1rem; font-size: 1rem;
position: relative;
top: 0.06rem;
}
&--hidden {
visibility: hidden;
transition: none;
} }
} }
} }

View File

@@ -529,8 +529,10 @@ describe("<DatePicker/>", () => {
expect(input.getAttribute("aria-disabled")).eq("true"); expect(input.getAttribute("aria-disabled")).eq("true");
expect(button).toBeDisabled(); expect(button).toBeDisabled();
// Make sure the clear button is not rendered. // Make sure the clear button is not visible and disabled.
expect(screen.queryByRole("button", { name: "Clear date" })).toBeNull(); expect(
screen.queryByRole("button", { name: "Clear date", hidden: true })
).toBeDisabled();
// Make sure each segment of the date field is disabled. // Make sure each segment of the date field is disabled.
const dateFieldInputs = await screen.queryAllByRole("spinbutton"); const dateFieldInputs = await screen.queryAllByRole("spinbutton");

View File

@@ -160,6 +160,22 @@ export const DatePicker = ({
)} )}
</div> </div>
</LabelledBox> </LabelledBox>
<Button
className={classNames("c__date-picker__inner__action", {
"c__date-picker__inner__action--empty": !state.value,
"c__date-picker__inner__action--hidden":
labelAsPlaceholder || disabled,
})}
color="tertiary"
size="small"
icon={<span className="material-icons">cancel</span>}
// Intentionally pass a null value to reset date picker state
onClick={() => state.setValue(null as unknown as DateValue)}
aria-label={t(
"components.forms.date_picker.clear_button_aria_label"
)}
disabled={disabled}
/>
</div> </div>
{state.isOpen && ( {state.isOpen && (
<Popover <Popover