@payfit/unity-components 2.21.12 → 2.21.14

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.
Files changed (27) hide show
  1. package/dist/esm/components/date-calendar/DateCalendar.js +87 -89
  2. package/dist/esm/components/date-calendar/DateCalendar.variants.d.ts +62 -0
  3. package/dist/esm/components/date-calendar/DateCalendar.variants.js +42 -0
  4. package/dist/esm/components/date-picker/parts/DateInput.d.ts +28 -0
  5. package/dist/esm/components/date-picker/parts/DateInput.js +6 -5
  6. package/dist/esm/components/date-range-calendar/DateRangeCalendar.d.ts +22 -0
  7. package/dist/esm/components/date-range-calendar/DateRangeCalendar.js +197 -0
  8. package/dist/esm/components/date-range-picker/DateRangePicker.d.ts +68 -0
  9. package/dist/esm/components/date-range-picker/DateRangePicker.js +174 -0
  10. package/dist/esm/components/date-range-picker/TanstackDateRangePicker.d.ts +22 -0
  11. package/dist/esm/components/date-range-picker/TanstackDateRangePicker.js +53 -0
  12. package/dist/esm/components/date-range-picker/parts/DateRangeInput.d.ts +16 -0
  13. package/dist/esm/components/date-range-picker/parts/DateRangeInput.js +98 -0
  14. package/dist/esm/components/date-range-picker-field/TanstackDateRangePickerField.d.ts +64 -0
  15. package/dist/esm/components/date-range-picker-field/TanstackDateRangePickerField.js +41 -0
  16. package/dist/esm/components/date-range-picker-field/test-utils.d.ts +19 -0
  17. package/dist/esm/components/date-range-picker-field/test-utils.js +66 -0
  18. package/dist/esm/hooks/use-tanstack-form.d.ts +36 -0
  19. package/dist/esm/hooks/use-tanstack-form.js +72 -60
  20. package/dist/esm/index.d.ts +2 -0
  21. package/dist/esm/index.js +462 -458
  22. package/dist/esm/index.storybook-testing.d.ts +1 -0
  23. package/dist/esm/storybook-testing.js +10 -8
  24. package/i18n/en-GB.json +1 -0
  25. package/i18n/es-ES.json +1 -0
  26. package/i18n/fr-FR.json +1 -0
  27. package/package.json +7 -7
@@ -0,0 +1,68 @@
1
+ import { CalendarDate } from '@internationalized/date';
2
+ import { DateRangePickerProps as AriaDateRangePickerProps } from 'react-aria-components';
3
+ type DateRange = {
4
+ start: CalendarDate;
5
+ end: CalendarDate;
6
+ };
7
+ export interface DateRangePickerProps extends Pick<AriaDateRangePickerProps<CalendarDate>, 'id' | 'firstDayOfWeek' | 'aria-label' | 'aria-labelledby' | 'aria-describedby' | 'aria-details'> {
8
+ /** The currently selected date range */
9
+ value?: DateRange | null;
10
+ /** The default selected date range (uncontrolled) */
11
+ defaultValue?: DateRange | null;
12
+ /** The minimum allowed date */
13
+ minValue?: CalendarDate;
14
+ /** The maximum allowed date */
15
+ maxValue?: CalendarDate;
16
+ /** Callback fired when the date range value changes */
17
+ onChange?: (value: DateRange | null) => void;
18
+ /** Callback fired when the clear button is clicked */
19
+ onClearButtonPress?: () => void;
20
+ /** Callback fired when the picker loses focus */
21
+ onBlur?: () => void;
22
+ /** Callback fired when the picker gains focus */
23
+ onFocus?: () => void;
24
+ /** Callback fired when the calendar overlay's open state changes */
25
+ onOpenChange?: (isOpen: boolean) => void;
26
+ /** Whether the picker is in an invalid state */
27
+ isInvalid?: boolean;
28
+ /** Whether the picker is in a loading state */
29
+ isLoading?: boolean;
30
+ /** Whether the picker is disabled */
31
+ isDisabled?: boolean;
32
+ /** Whether the picker is read-only */
33
+ isReadOnly?: boolean;
34
+ /** Function to determine if a date should be disabled */
35
+ isDateUnavailable?: (date: CalendarDate) => boolean;
36
+ /** Whether to force leading zeros for days and months */
37
+ shouldForceLeadingZeros?: boolean;
38
+ /** Whether to close the calendar after a date range is selected */
39
+ shouldCloseOnSelect?: boolean;
40
+ /** Whether to open the calendar by default */
41
+ defaultOpen?: boolean;
42
+ }
43
+ /**
44
+ * The DateRangePicker component allows users to select a date range either by typing it in directly or choosing from a calendar overlay.
45
+ * @param {DateRangePickerProps} props - Props for configuring the DateRangePicker's behavior and appearance
46
+ * @see {@link DateRangePickerProps} for all available props
47
+ * @example
48
+ * ```tsx
49
+ * import { DateRangePicker } from '@payfit/unity-components'
50
+ * import { CalendarDate } from '@internationalized/date'
51
+ *
52
+ * function Example() {
53
+ * const [range, setRange] = useState<{ start: CalendarDate; end: CalendarDate }>()
54
+ *
55
+ * return (
56
+ * <DateRangePicker
57
+ * value={range}
58
+ * onChange={setRange}
59
+ * minValue={new CalendarDate(2024, 1, 1)}
60
+ * />
61
+ * )
62
+ * }
63
+ * ```
64
+ * @note
65
+ * This component requires `@internationalized/date` as a peer dependency. Make sure to install it in your project: `yarn add @internationalized/date`
66
+ */
67
+ declare const DateRangePicker: import('react').ForwardRefExoticComponent<DateRangePickerProps & import('react').RefAttributes<HTMLDivElement>>;
68
+ export { DateRangePicker };
@@ -0,0 +1,174 @@
1
+ import { jsxs as f, jsx as a } from "react/jsx-runtime";
2
+ import { forwardRef as I } from "react";
3
+ import { uyTv as b } from "@payfit/unity-themes";
4
+ import { DateRangePicker as U, Group as B, Button as j, Popover as E, Dialog as M } from "react-aria-components";
5
+ import { useIntl as G } from "react-intl";
6
+ import { DateRangeCalendar as T } from "../date-range-calendar/DateRangeCalendar.js";
7
+ import { Icon as $ } from "../icon/Icon.js";
8
+ import { DateRangeInput as q } from "./parts/DateRangeInput.js";
9
+ const z = b({
10
+ slots: {
11
+ base: [
12
+ "uy:group uy:flex uy:h-5.5 uy:sm:h-500 uy:border uy:border-solid uy:rounded-100 uy:sm:rounded-75",
13
+ "uy:active:border-border-form-active uy:data-[focus-visible=true]:border-border-form-active"
14
+ ],
15
+ inputWrapper: [
16
+ "uy:flex uy:grow uy:rounded-100 uy:sm:rounded-75 uy:outline-none",
17
+ // Show focus styles when input wrapper is focused AND button is not focused
18
+ "uy:focus-within:outline-2 uy:focus-within:outline-solid uy:focus-within:outline-utility-focus-ring uy:focus-within:outline-offset-3",
19
+ // Hide focus styles when button is focused
20
+ "uy:group-[:has(button:focus)]:data-[focus-within]:outline-none uy:group-[:has(button:focus)]:data-[focus-within]:outline-offset-0 uy:group-[:has(button:focus)]:data-[focus-within]:outline-transparent"
21
+ ],
22
+ suffix: [
23
+ "uy:flex-grow-0 uy:content-center uy:p-125 uy:border-l uy:border-solid uy:rounded-r-100 uy:sm:rounded-r-75 uy:text-content-neutral-low",
24
+ "uy:hover:bg-surface-neutral-hover uy:active:bg-surface-neutral-pressed uy:active:border-border-form-active uy:data-[pressed=true]:bg-surface-neutral-pressed uy:data-[pressed=true]:not-group-data-[open=true]:border-border-form-active",
25
+ "uy:focus-visible:outline-2 uy:focus-visible:outline-utility-focus-ring uy:focus-visible:outline-offset-3"
26
+ ]
27
+ },
28
+ variants: {
29
+ isInvalid: {
30
+ true: {
31
+ base: "uy:border-border-form-error uy:bg-surface-form-error",
32
+ suffix: "uy:bg-surface-form-error uy:border-border-form-error"
33
+ }
34
+ },
35
+ isReadOnly: {
36
+ true: {
37
+ base: "uy:border-border-form-disabled uy:bg-surface-form-disabled",
38
+ inputWrapper: "uy:border-border-form-disabled uy:bg-surface-form-disabled",
39
+ suffix: "uy:bg-surface-form-disabled uy:border-border-form-disabled uy:text-content-form-disabled"
40
+ }
41
+ },
42
+ isDisabled: {
43
+ true: {
44
+ base: "uy:border-border-form-disabled uy:bg-surface-form-disabled",
45
+ inputWrapper: "uy:bg-surface-form-disabled uy:text-content-form-disabled",
46
+ suffix: "uy:bg-surface-form-disabled uy:border-border-form-disabled uy:text-content-form-disabled"
47
+ }
48
+ }
49
+ },
50
+ compoundVariants: [
51
+ {
52
+ isInvalid: !1,
53
+ isDisabled: !1,
54
+ isReadOnly: !1,
55
+ className: {
56
+ base: "uy:border-border-form-enabled uy:bg-surface-form-enabled",
57
+ suffix: "uy:border-border-form-enabled uy:bg-surface-neutral uy:text-content-neutral-low"
58
+ }
59
+ }
60
+ ]
61
+ }), A = b({
62
+ base: "uy:overflow-auto uy:shadow-300 uy:border uy:border-solid uy:border-border-neutral uy:bg-surface-neutral uy:rounded-md uy:sm:rounded-75",
63
+ variants: {
64
+ isEntering: {
65
+ true: "uy:animate-in uy:fade-in uy:data-[placement-bottom]:slide-in-from-top-1 uy:data-[placement-top]:slide-out-to-bottom-1 uy:duration-200 uy:ease-out"
66
+ },
67
+ isExiting: {
68
+ true: "uy:animate-out uy:fade-out uy:data-[placement-bottom]:slide-out-to-top-1 uy:data-[placement-top]:slide-out-to-bottom-1 uy:duration-150 uy:ease-in"
69
+ }
70
+ }
71
+ }), H = I(
72
+ ({
73
+ value: i,
74
+ defaultValue: n,
75
+ isInvalid: t,
76
+ isLoading: y,
77
+ isDisabled: o,
78
+ isReadOnly: u,
79
+ onClearButtonPress: c,
80
+ onBlur: d,
81
+ onFocus: s,
82
+ onChange: m,
83
+ onOpenChange: g,
84
+ id: p,
85
+ "aria-label": h,
86
+ "aria-labelledby": v,
87
+ "aria-describedby": x,
88
+ "aria-details": D,
89
+ ...e
90
+ }, w) => {
91
+ const k = G(), { base: C, inputWrapper: R, suffix: P } = z({
92
+ isInvalid: !!t,
93
+ isReadOnly: !!u,
94
+ isDisabled: !!o
95
+ }), l = (r) => {
96
+ m?.(r);
97
+ }, V = (r) => {
98
+ g?.(r), r ? s?.() : d?.();
99
+ }, N = (r) => e.isDateUnavailable ? e.isDateUnavailable(r) : !1, O = () => {
100
+ c?.();
101
+ };
102
+ return /* @__PURE__ */ f(
103
+ U,
104
+ {
105
+ ref: w,
106
+ "data-dd-privacy": "mask",
107
+ ...e,
108
+ className: C(),
109
+ value: i,
110
+ defaultValue: n,
111
+ minValue: e.minValue,
112
+ maxValue: e.maxValue,
113
+ isReadOnly: !!u,
114
+ isDisabled: !!o,
115
+ onChange: l,
116
+ onFocus: s,
117
+ onBlur: d,
118
+ onOpenChange: V,
119
+ isInvalid: !!t,
120
+ isDateUnavailable: N,
121
+ "aria-label": h,
122
+ "aria-labelledby": v,
123
+ "aria-describedby": x,
124
+ "aria-details": D,
125
+ children: [
126
+ /* @__PURE__ */ f(B, { className: R(), id: p, children: [
127
+ /* @__PURE__ */ a(
128
+ q,
129
+ {
130
+ isLoading: y,
131
+ isDisabled: o,
132
+ isReadOnly: u,
133
+ isInvalid: t,
134
+ onClearButtonPress: O
135
+ }
136
+ ),
137
+ /* @__PURE__ */ a(j, { className: P(), isDisabled: u || o, children: /* @__PURE__ */ a(
138
+ $,
139
+ {
140
+ src: "CalendarBlankOutlined",
141
+ color: "inherit",
142
+ alt: k.formatMessage({
143
+ id: "unity:component:form-field:date-range-picker:calendar-button",
144
+ defaultMessage: "Open Calendar"
145
+ })
146
+ }
147
+ ) })
148
+ ] }),
149
+ /* @__PURE__ */ a(
150
+ E,
151
+ {
152
+ className: ({ isEntering: r, isExiting: W }) => A({ isEntering: r, isExiting: W }),
153
+ children: /* @__PURE__ */ a(M, { className: "uy:p-150", "data-dd-privacy": "mask", children: /* @__PURE__ */ a(
154
+ T,
155
+ {
156
+ value: i,
157
+ defaultValue: n,
158
+ minValue: e.minValue,
159
+ maxValue: e.maxValue,
160
+ onChange: l,
161
+ firstDayOfWeek: e.firstDayOfWeek
162
+ }
163
+ ) })
164
+ }
165
+ )
166
+ ]
167
+ }
168
+ );
169
+ }
170
+ );
171
+ H.displayName = "DateRangePicker";
172
+ export {
173
+ H as DateRangePicker
174
+ };
@@ -0,0 +1,22 @@
1
+ import { DateRangePickerProps } from './DateRangePicker.js';
2
+ export type TanstackDateRangePickerProps = Omit<DateRangePickerProps, 'value' | 'defaultValue' | 'isInvalid'>;
3
+ /**
4
+ * `TanstackDateRangePicker` is a controlled date range picker wired to the TanStack Form field context.
5
+ * It is based on the Unity `DateRangePicker` component.
6
+ *
7
+ * Example:
8
+ * ```tsx
9
+ * function ExampleField() {
10
+ * const form = useTanstackUnityForm<{ period: DateRange | null }>({ validators: {} })
11
+ * return (
12
+ * <form>
13
+ * <form.AppField name="period">
14
+ * {() => <TanstackDateRangePicker />}
15
+ * </form.AppField>
16
+ * </form>
17
+ * )
18
+ * }
19
+ * ```
20
+ */
21
+ declare const TanstackDateRangePicker: import('react').ForwardRefExoticComponent<TanstackDateRangePickerProps & import('react').RefAttributes<HTMLDivElement>>;
22
+ export { TanstackDateRangePicker };
@@ -0,0 +1,53 @@
1
+ import { jsx as p } from "react/jsx-runtime";
2
+ import { forwardRef as h } from "react";
3
+ import { useFieldContext as b } from "../../hooks/tanstack-form-context.js";
4
+ import { useFieldA11yContext as g } from "../form-field/TanstackFormField.context.js";
5
+ import { DateRangePicker as k } from "./DateRangePicker.js";
6
+ const x = h(
7
+ ({
8
+ onClearButtonPress: o,
9
+ onBlur: i,
10
+ onFocus: r,
11
+ onChange: l,
12
+ onOpenChange: s,
13
+ isReadOnly: d,
14
+ isDisabled: c,
15
+ ...m
16
+ }, u) => {
17
+ const e = b(), a = g(), f = e.state.meta.isTouched && !e.state.meta.isValid, n = [a.helperTextId, a.feedbackTextId].filter(Boolean).join(" ");
18
+ return /* @__PURE__ */ p(
19
+ k,
20
+ {
21
+ ...m,
22
+ ref: u,
23
+ id: a.inputId,
24
+ value: e.state.value,
25
+ onChange: (t) => {
26
+ e.handleChange(t), l?.(t);
27
+ },
28
+ onBlur: () => {
29
+ e.handleBlur(), i?.();
30
+ },
31
+ onFocus: () => {
32
+ r?.();
33
+ },
34
+ onOpenChange: (t) => {
35
+ s?.(t);
36
+ },
37
+ onClearButtonPress: () => {
38
+ e.setValue(null), o?.();
39
+ },
40
+ isReadOnly: d,
41
+ isDisabled: c,
42
+ isInvalid: f,
43
+ "aria-labelledby": a.labelId,
44
+ "aria-describedby": n.length > 0 ? n : void 0,
45
+ "aria-details": a.contextualLinkId
46
+ }
47
+ );
48
+ }
49
+ );
50
+ x.displayName = "TanstackDateRangePicker";
51
+ export {
52
+ x as TanstackDateRangePicker
53
+ };
@@ -0,0 +1,16 @@
1
+ export interface DateRangeInputProps {
2
+ /** Whether the field is in an invalid state */
3
+ isInvalid?: boolean;
4
+ /** Whether the field is in a loading state */
5
+ isLoading?: boolean;
6
+ /** Whether the field is disabled */
7
+ isDisabled?: boolean;
8
+ /** Whether the field is read-only */
9
+ isReadOnly?: boolean;
10
+ /** Clear button click handler */
11
+ onClearButtonPress?: () => void;
12
+ }
13
+ export declare function DateRangeInput({ isLoading, isInvalid, isReadOnly, isDisabled, onClearButtonPress, }: DateRangeInputProps): import("react/jsx-runtime").JSX.Element;
14
+ export declare namespace DateRangeInput {
15
+ var displayName: string;
16
+ }
@@ -0,0 +1,98 @@
1
+ import { jsxs as o, jsx as e } from "react/jsx-runtime";
2
+ import { useContext as x } from "react";
3
+ import { uyTv as N } from "@payfit/unity-themes";
4
+ import { DateRangePickerStateContext as I, DateInput as m, DateSegment as u } from "react-aria-components";
5
+ import { useIntl as b } from "react-intl";
6
+ import { dateInput as v, dateSegment as d } from "../../date-picker/parts/DateInput.js";
7
+ import { CircularIconButton as C } from "../../icon-button/CircularIconButton.js";
8
+ import { Icon as P } from "../../icon/Icon.js";
9
+ import { Spinner as D } from "../../spinner/Spinner.js";
10
+ const M = N({
11
+ base: "uy:px-50 uy:flex uy:items-center",
12
+ variants: {
13
+ isDisabled: {
14
+ true: "uy:text-content-form-disabled",
15
+ false: "uy:text-content-neutral-lowest-enabled"
16
+ }
17
+ }
18
+ });
19
+ function S({
20
+ isLoading: n,
21
+ isInvalid: r,
22
+ isReadOnly: s,
23
+ isDisabled: a,
24
+ onClearButtonPress: p
25
+ }) {
26
+ const l = b(), i = x(I), { value: c } = i, { base: f, input: y, state: g } = v({
27
+ isInvalid: !!r,
28
+ isReadOnly: !!s,
29
+ isDisabled: !!a
30
+ }), h = c?.start && c?.end && !n && !s && !a;
31
+ return /* @__PURE__ */ o("div", { className: f(), children: [
32
+ /* @__PURE__ */ o("div", { className: y(), children: [
33
+ /* @__PURE__ */ e(m, { slot: "start", className: "uy:flex uy:gap-25", children: (t) => /* @__PURE__ */ e(
34
+ u,
35
+ {
36
+ segment: t,
37
+ className: d({
38
+ isPlaceholder: t.isPlaceholder,
39
+ isLiteral: t.type === "literal"
40
+ })
41
+ }
42
+ ) }),
43
+ /* @__PURE__ */ e("span", { className: M({ isDisabled: !!a }), children: "→" }),
44
+ /* @__PURE__ */ e(m, { slot: "end", className: "uy:flex uy:gap-25", children: (t) => /* @__PURE__ */ e(
45
+ u,
46
+ {
47
+ segment: t,
48
+ className: d({
49
+ isPlaceholder: t.isPlaceholder,
50
+ isLiteral: t.type === "literal"
51
+ })
52
+ }
53
+ ) })
54
+ ] }),
55
+ /* @__PURE__ */ o("div", { className: g(), children: [
56
+ n && /* @__PURE__ */ e(
57
+ D,
58
+ {
59
+ color: "inherit",
60
+ size: "small",
61
+ label: l.formatMessage({
62
+ id: "unity:component:common:loading:label",
63
+ defaultMessage: "Loading..."
64
+ })
65
+ }
66
+ ),
67
+ r && /* @__PURE__ */ e(
68
+ P,
69
+ {
70
+ src: "WarningCircleOutlined",
71
+ color: "content.form.invalid",
72
+ alt: l.formatMessage({
73
+ id: "unity:component:form-field:form-input:error:alt",
74
+ defaultMessage: "Error"
75
+ })
76
+ }
77
+ ),
78
+ h && /* @__PURE__ */ e(
79
+ C,
80
+ {
81
+ slot: null,
82
+ title: l.formatMessage({
83
+ id: "unity:component:common:clear:title",
84
+ defaultMessage: "Clear"
85
+ }),
86
+ icon: "CloseOutlined",
87
+ onPress: () => {
88
+ i?.setValue(null), p?.();
89
+ }
90
+ }
91
+ )
92
+ ] })
93
+ ] });
94
+ }
95
+ S.displayName = "DateRangeInput";
96
+ export {
97
+ S as DateRangeInput
98
+ };
@@ -0,0 +1,64 @@
1
+ import { ReactNode } from 'react';
2
+ import { TanstackDateRangePickerProps } from '../date-range-picker/TanstackDateRangePicker.js';
3
+ import { LabelProps } from '../label/Label.js';
4
+ export type TanstackDateRangePickerFieldProps = TanstackDateRangePickerProps & Pick<LabelProps, 'isRequired' | 'requiredVariant'> & {
5
+ /** The label for the date range picker field. */
6
+ label: string;
7
+ /** Helper text to display below the date range picker field. */
8
+ helperText?: ReactNode;
9
+ /** A contextual link to display below the date range picker field. */
10
+ contextualLink?: ReactNode;
11
+ };
12
+ /**
13
+ * The `TanstackDateRangePickerField` component renders a full field (label, date range picker)
14
+ * wired to the TanStack Form context. It manages state and accessibility via the
15
+ * context provided by `useTanstackUnityForm` and `<form.AppField name="…">`.
16
+ *
17
+ * Behavior:
18
+ * - Renders `TanstackDateRangePicker` with calendar overlay for date range selection.
19
+ * - Displays the label (`TanstackFormLabel`), helper text (`TanstackFormHelperText`),
20
+ * feedback messages (`TanstackFormFeedbackText`), and an optional contextual link.
21
+ *
22
+ * Accessibility:
23
+ * - Automatically wires `aria-labelledby`, `aria-describedby` (helper/feedback), and
24
+ * `aria-details` using identifiers from the `a11y` context.
25
+ *
26
+ * Example:
27
+ * ```tsx
28
+ * import { TanstackDateRangePickerField } from "@payfit/unity-components"
29
+ * import { useTanstackUnityForm } from "@payfit/unity-components"
30
+ * import { CalendarDate } from '@internationalized/date'
31
+ *
32
+ * function Example() {
33
+ * const schema = z.object({
34
+ * period: z.custom<{ start: CalendarDate; end: CalendarDate } | null>()
35
+ * .refine(range => range !== null, 'Date range is required'),
36
+ * })
37
+ *
38
+ * const form = useTanstackUnityForm({ validators: {
39
+ * onBlur: schema,
40
+ * } })
41
+ * return (
42
+ * <form>
43
+ * <form.AppField name="period">
44
+ * {() => (
45
+ * <TanstackDateRangePickerField
46
+ * label="Period"
47
+ * helperText="Select a date range"
48
+ * />
49
+ * )}
50
+ * </form.AppField>
51
+ * </form>
52
+ * )
53
+ * }
54
+ * ```
55
+ */
56
+ declare const TanstackDateRangePickerField: import('react').ForwardRefExoticComponent<TanstackDateRangePickerProps & Pick<LabelProps, "isRequired" | "requiredVariant"> & {
57
+ /** The label for the date range picker field. */
58
+ label: string;
59
+ /** Helper text to display below the date range picker field. */
60
+ helperText?: ReactNode;
61
+ /** A contextual link to display below the date range picker field. */
62
+ contextualLink?: ReactNode;
63
+ } & import('react').RefAttributes<HTMLDivElement>>;
64
+ export { TanstackDateRangePickerField };
@@ -0,0 +1,41 @@
1
+ import { jsxs as p, jsx as r } from "react/jsx-runtime";
2
+ import { forwardRef as d } from "react";
3
+ import { TanstackDateRangePicker as f } from "../date-range-picker/TanstackDateRangePicker.js";
4
+ import { TanstackFormFeedbackText as l } from "../form-field/parts/TanstackFormFeedbackText.js";
5
+ import { TanstackFormHelperText as F } from "../form-field/parts/TanstackFormHelperText.js";
6
+ import { TanstackFormLabel as T } from "../form-field/parts/TanstackFormLabel.js";
7
+ import { TanstackFormField as P } from "../form-field/TanstackFormField.js";
8
+ const x = d(
9
+ ({
10
+ label: a,
11
+ helperText: o,
12
+ contextualLink: e,
13
+ isRequired: m,
14
+ isLoading: t,
15
+ isDisabled: c,
16
+ isReadOnly: n,
17
+ requiredVariant: i,
18
+ ...s
19
+ }, k) => /* @__PURE__ */ p(P, { children: [
20
+ /* @__PURE__ */ r(
21
+ T,
22
+ {
23
+ requiredVariant: i,
24
+ isRequired: m,
25
+ children: a
26
+ }
27
+ ),
28
+ o && /* @__PURE__ */ r(F, { children: o }),
29
+ /* @__PURE__ */ r(f, { ref: k, ...{
30
+ isLoading: t,
31
+ isDisabled: c,
32
+ isReadOnly: n
33
+ }, ...s }),
34
+ /* @__PURE__ */ r(l, {}),
35
+ e
36
+ ] })
37
+ );
38
+ x.displayName = "TanstackDateRangePickerField";
39
+ export {
40
+ x as TanstackDateRangePickerField
41
+ };
@@ -0,0 +1,19 @@
1
+ import { PlayCtx } from '../../types/testing.js';
2
+ import { CalendarDate } from '@internationalized/date';
3
+ /**
4
+ * Factory to get date range picker testing utils
5
+ * @param context the story context
6
+ */
7
+ export declare const getTestingUtilsDateRangePicker: (context: PlayCtx) => {
8
+ fillCalendarDateRange: ({ labelText, startDate, endDate, }: {
9
+ labelText: string;
10
+ startDate: CalendarDate;
11
+ endDate: CalendarDate;
12
+ }) => Promise<void>;
13
+ getCalendarDateRangeValue: ({ labelText }: {
14
+ labelText: string;
15
+ }) => {
16
+ start: CalendarDate;
17
+ end: CalendarDate;
18
+ };
19
+ };
@@ -0,0 +1,66 @@
1
+ import { CalendarDate as l } from "@internationalized/date";
2
+ import { within as c, userEvent as r } from "storybook/test";
3
+ const m = (i) => {
4
+ const s = (e) => {
5
+ const t = c(i.canvasElement).getAllByLabelText(
6
+ e,
7
+ {
8
+ exact: !1,
9
+ selector: "span"
10
+ }
11
+ );
12
+ if (t.length !== 6)
13
+ throw new Error(
14
+ `Date range field for ${e} not found. Expected 6 segments, got ${t.length}`
15
+ );
16
+ return {
17
+ start: t.slice(0, 3),
18
+ end: t.slice(3, 6)
19
+ };
20
+ }, g = async (e, t) => {
21
+ await r.type(
22
+ // eslint-disable-next-line @typescript-eslint/no-non-null-assertion
23
+ e.find((a) => a.getAttribute("data-type") === "day"),
24
+ String(t.day)
25
+ ), await r.type(
26
+ // eslint-disable-next-line @typescript-eslint/no-non-null-assertion
27
+ e.find((a) => a.getAttribute("data-type") === "month"),
28
+ String(t.month)
29
+ ), await r.type(
30
+ // eslint-disable-next-line @typescript-eslint/no-non-null-assertion
31
+ e.find((a) => a.getAttribute("data-type") === "year"),
32
+ String(t.year)
33
+ );
34
+ }, d = (e) => {
35
+ const t = (a) => parseInt(
36
+ e.find((n) => n.getAttribute("data-type") === a)?.textContent ?? ""
37
+ );
38
+ return new l(
39
+ t("year"),
40
+ t("month"),
41
+ t("day")
42
+ );
43
+ };
44
+ return {
45
+ fillCalendarDateRange: async ({
46
+ labelText: e,
47
+ startDate: t,
48
+ endDate: a
49
+ }) => {
50
+ await i.step(`Fill date range picker ${e}`, async () => {
51
+ const { start: n, end: o } = s(e);
52
+ await g(n, t), await g(o, a);
53
+ });
54
+ },
55
+ getCalendarDateRangeValue: ({ labelText: e }) => {
56
+ const { start: t, end: a } = s(e);
57
+ return {
58
+ start: d(t),
59
+ end: d(a)
60
+ };
61
+ }
62
+ };
63
+ };
64
+ export {
65
+ m as getTestingUtilsDateRangePicker
66
+ };