@launchpad-ui/form 0.8.13 → 0.8.15

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.
package/dist/index.es.js CHANGED
@@ -1,37 +1,42 @@
1
1
  import './style.css';
2
- import { forwardRef, useState, useRef, Children, isValidElement, cloneElement } from "react";
3
- import { cx } from "classix";
4
2
  import { jsx, jsxs, Fragment } from "react/jsx-runtime";
5
- import { AlertRhombus } from "@launchpad-ui/icons";
3
+ import { forwardRef, useRef, useMemo, useState, Children, isValidElement, cloneElement } from "react";
4
+ import { cx } from "classix";
5
+ import { AlertRhombus, ExpandLess, ExpandMore } from "@launchpad-ui/icons";
6
6
  import { VisuallyHidden } from "@react-aria/visually-hidden";
7
- const formGroup = "_formGroup_p76jo_10";
8
- const formIncreasedErrorMargin = "_formIncreasedErrorMargin_p76jo_18";
9
- const formInline = "_formInline_p76jo_22";
10
- const form = "_form_p76jo_10";
11
- const formInput = "_formInput_p76jo_36";
12
- const isFocused = "_isFocused_p76jo_56";
13
- const iconField = "_iconField_p76jo_73";
14
- const suffixContainer = "_suffixContainer_p76jo_77";
15
- const isInvalid = "_isInvalid_p76jo_82";
16
- const inlineForm = "_inlineForm_p76jo_93";
17
- const label = "_label_p76jo_98";
18
- const labelDisabled = "_labelDisabled_p76jo_104";
19
- const labelOptional = "_labelOptional_p76jo_108";
20
- const compactTextField = "_compactTextField_p76jo_114";
21
- const fieldError = "_fieldError_p76jo_138";
22
- const hint = "_hint_p76jo_184";
23
- const field = "_field_p76jo_138";
24
- const fieldErrorMessage = "_fieldErrorMessage_p76jo_204";
25
- const isDisabled = "_isDisabled_p76jo_217";
26
- const checkbox = "_checkbox_p76jo_284";
27
- const radio = "_radio_p76jo_291";
28
- const number = "_number_p76jo_295";
29
- const suffix = "_suffix_p76jo_77";
30
- const iconFieldIcon = "_iconFieldIcon_p76jo_333";
31
- const formInputTiny = "_formInputTiny_p76jo_341";
32
- const requiredAsterisk = "_requiredAsterisk_p76jo_350";
33
- const fieldSet = "_fieldSet_p76jo_354";
34
- const isActive = "_isActive_p76jo_365";
7
+ import { useButton } from "@react-aria/button";
8
+ import { useLocale } from "@react-aria/i18n";
9
+ import { useNumberField as useNumberField$1 } from "@react-aria/numberfield";
10
+ import { useNumberFieldState } from "@react-stately/numberfield";
11
+ const formGroup = "_formGroup_1u9hb_10";
12
+ const formIncreasedErrorMargin = "_formIncreasedErrorMargin_1u9hb_18";
13
+ const formInline = "_formInline_1u9hb_22";
14
+ const form = "_form_1u9hb_10";
15
+ const formInput = "_formInput_1u9hb_36";
16
+ const isFocused = "_isFocused_1u9hb_56";
17
+ const iconField = "_iconField_1u9hb_73";
18
+ const suffixContainer = "_suffixContainer_1u9hb_77";
19
+ const isInvalid = "_isInvalid_1u9hb_82";
20
+ const inlineForm = "_inlineForm_1u9hb_93";
21
+ const label = "_label_1u9hb_98";
22
+ const labelDisabled = "_labelDisabled_1u9hb_104";
23
+ const labelOptional = "_labelOptional_1u9hb_108";
24
+ const compactTextField = "_compactTextField_1u9hb_114";
25
+ const fieldError = "_fieldError_1u9hb_138";
26
+ const hint = "_hint_1u9hb_184";
27
+ const field = "_field_1u9hb_138";
28
+ const fieldErrorMessage = "_fieldErrorMessage_1u9hb_204";
29
+ const isDisabled = "_isDisabled_1u9hb_217";
30
+ const checkbox = "_checkbox_1u9hb_284";
31
+ const radio = "_radio_1u9hb_291";
32
+ const number = "_number_1u9hb_295";
33
+ const suffix = "_suffix_1u9hb_77";
34
+ const iconFieldIcon = "_iconFieldIcon_1u9hb_333";
35
+ const formInputTiny = "_formInputTiny_1u9hb_341";
36
+ const requiredAsterisk = "_requiredAsterisk_1u9hb_350";
37
+ const fieldSet = "_fieldSet_1u9hb_354";
38
+ const isActive = "_isActive_1u9hb_365";
39
+ const numberField = "_numberField_1u9hb_372";
35
40
  const styles = {
36
41
  formGroup,
37
42
  formIncreasedErrorMargin,
@@ -60,7 +65,11 @@ const styles = {
60
65
  formInputTiny,
61
66
  requiredAsterisk,
62
67
  fieldSet,
63
- isActive
68
+ isActive,
69
+ numberField,
70
+ "numberField-input": "_numberField-input_1u9hb_376",
71
+ "numberField-stepperContainer": "_numberField-stepperContainer_1u9hb_380",
72
+ "numberField-stepper": "_numberField-stepper_1u9hb_380"
64
73
  };
65
74
  const RequiredAsterisk = ({
66
75
  className,
@@ -68,12 +77,7 @@ const RequiredAsterisk = ({
68
77
  ...rest
69
78
  }) => {
70
79
  const classes = cx(styles.requiredAsterisk, className);
71
- return /* @__PURE__ */ jsx("span", {
72
- ...rest,
73
- "data-test-id": testId,
74
- className: classes,
75
- children: "*"
76
- });
80
+ return /* @__PURE__ */ jsx("span", { ...rest, "data-test-id": testId, className: classes, children: "*" });
77
81
  };
78
82
  const Label = ({
79
83
  disabled,
@@ -85,141 +89,164 @@ const Label = ({
85
89
  ...rest
86
90
  }) => {
87
91
  const classes = cx(styles.label, className, disabled && styles.labelDisabled);
88
- return /* @__PURE__ */ jsxs("label", {
89
- ...rest,
90
- "data-test-id": testId,
91
- className: classes,
92
- children: [children, optional && !required && /* @__PURE__ */ jsx("small", {
93
- className: styles.labelOptional,
94
- children: "(optional)"
95
- }), required && !optional && /* @__PURE__ */ jsx(RequiredAsterisk, {})]
96
- });
92
+ return /* @__PURE__ */ jsxs("label", { ...rest, "data-test-id": testId, className: classes, children: [
93
+ children,
94
+ optional && !required && /* @__PURE__ */ jsx("small", { className: styles.labelOptional, children: "(optional)" }),
95
+ required && !optional && /* @__PURE__ */ jsx(RequiredAsterisk, {})
96
+ ] });
97
97
  };
98
- const Checkbox = forwardRef(({
99
- "aria-label": ariaLabel,
100
- "aria-labelledby": ariaLabelledby,
101
- children,
102
- disabled,
103
- checked,
104
- labelClassName,
105
- "data-test-id": testId = "checkbox",
106
- ...rest
107
- }, ref) => {
108
- const hasAriaLabel = ariaLabel !== void 0 || ariaLabelledby !== void 0;
109
- if (!children && !hasAriaLabel) {
110
- console.warn("If you do not provide children, you must specify an aria-label for accessibility");
98
+ const Checkbox = forwardRef(
99
+ ({
100
+ "aria-label": ariaLabel,
101
+ "aria-labelledby": ariaLabelledby,
102
+ children,
103
+ disabled,
104
+ checked,
105
+ labelClassName,
106
+ "data-test-id": testId = "checkbox",
107
+ ...rest
108
+ }, ref) => {
109
+ const hasAriaLabel = ariaLabel !== void 0 || ariaLabelledby !== void 0;
110
+ if (!children && !hasAriaLabel) {
111
+ console.warn(
112
+ "If you do not provide children, you must specify an aria-label for accessibility"
113
+ );
114
+ }
115
+ return /* @__PURE__ */ jsxs(Label, { className: labelClassName, children: [
116
+ /* @__PURE__ */ jsx(
117
+ "input",
118
+ {
119
+ ...rest,
120
+ ref,
121
+ checked,
122
+ "aria-checked": checked ? "true" : "false",
123
+ "aria-label": ariaLabel,
124
+ "aria-labelledby": ariaLabelledby,
125
+ className: styles.checkbox,
126
+ disabled,
127
+ type: "checkbox",
128
+ "data-test-id": testId
129
+ }
130
+ ),
131
+ " ",
132
+ disabled ? /* @__PURE__ */ jsx("span", { className: styles.labelDisabled, children }) : children
133
+ ] });
111
134
  }
112
- return /* @__PURE__ */ jsxs(Label, {
113
- className: labelClassName,
114
- children: [/* @__PURE__ */ jsx("input", {
115
- ...rest,
116
- ref,
117
- checked,
118
- "aria-checked": checked ? "true" : "false",
119
- "aria-label": ariaLabel,
120
- "aria-labelledby": ariaLabelledby,
121
- className: styles.checkbox,
122
- disabled,
123
- type: "checkbox",
124
- "data-test-id": testId
125
- }), " ", disabled ? /* @__PURE__ */ jsx("span", {
126
- className: styles.labelDisabled,
127
- children
128
- }) : children]
129
- });
130
- });
135
+ );
131
136
  Checkbox.displayName = "Checkbox";
132
137
  const createFieldErrorId = (fieldIdentifier) => fieldIdentifier ? `${[...fieldIdentifier].join("")}-err` : void 0;
133
- const TextField = forwardRef(({
134
- className,
135
- type = "text",
136
- tiny = false,
137
- readOnly,
138
- tabIndex = 0,
139
- suffix: suffix2,
140
- overrideWidth,
141
- "data-test-id": testId = "text-field",
142
- ...rest
143
- }, ref) => {
144
- const classes = overrideWidth ? className : cx(styles.formInput, tiny && styles.formInputTiny, className);
145
- if (suffix2) {
146
- return /* @__PURE__ */ jsxs("div", {
147
- className: styles.suffixContainer,
148
- children: [/* @__PURE__ */ jsx("input", {
138
+ function hasObjectChanged(obj1, obj2) {
139
+ return Object.keys(obj1).length !== Object.keys(obj2).length || Object.keys(obj1).some((k) => {
140
+ const key = k;
141
+ return typeof obj1[key] === "object" && typeof obj2[key] === "object" ? hasObjectChanged(obj1[key], obj2[key]) : obj1[key] !== obj2[key];
142
+ });
143
+ }
144
+ function useObjectMemo(obj) {
145
+ const objRef = useRef(obj);
146
+ return useMemo(() => {
147
+ if (hasObjectChanged(obj, objRef.current)) {
148
+ objRef.current = obj;
149
+ }
150
+ return objRef.current;
151
+ }, [obj]);
152
+ }
153
+ const TextField = forwardRef(
154
+ ({
155
+ className,
156
+ type = "text",
157
+ tiny = false,
158
+ readOnly,
159
+ tabIndex = 0,
160
+ suffix: suffix2,
161
+ overrideWidth,
162
+ "data-test-id": testId = "text-field",
163
+ ...rest
164
+ }, ref) => {
165
+ const classes = overrideWidth ? className : cx(styles.formInput, tiny && styles.formInputTiny, className);
166
+ if (suffix2) {
167
+ return /* @__PURE__ */ jsxs("div", { className: styles.suffixContainer, children: [
168
+ /* @__PURE__ */ jsx(
169
+ "input",
170
+ {
171
+ ...rest,
172
+ type,
173
+ "data-test-id": testId,
174
+ className: classes,
175
+ readOnly,
176
+ ref,
177
+ "aria-describedby": rest["aria-describedby"] || createFieldErrorId(rest.id)
178
+ }
179
+ ),
180
+ /* @__PURE__ */ jsx("label", { className: styles.suffix, htmlFor: rest.id, children: suffix2 })
181
+ ] });
182
+ }
183
+ return /* @__PURE__ */ jsx(
184
+ "input",
185
+ {
149
186
  ...rest,
150
187
  type,
151
- "data-test-id": testId,
152
188
  className: classes,
153
189
  readOnly,
190
+ tabIndex,
154
191
  ref,
192
+ "data-test-id": testId,
193
+ style: overrideWidth ? {
194
+ width: overrideWidth
195
+ } : void 0,
155
196
  "aria-describedby": rest["aria-describedby"] || createFieldErrorId(rest.id)
156
- }), /* @__PURE__ */ jsx("label", {
157
- className: styles.suffix,
158
- htmlFor: rest.id,
159
- children: suffix2
160
- })]
161
- });
197
+ }
198
+ );
162
199
  }
163
- return /* @__PURE__ */ jsx("input", {
164
- ...rest,
165
- type,
166
- className: classes,
167
- readOnly,
168
- tabIndex,
169
- ref,
170
- "data-test-id": testId,
171
- style: overrideWidth ? {
172
- width: overrideWidth
173
- } : void 0,
174
- "aria-describedby": rest["aria-describedby"] || createFieldErrorId(rest.id)
175
- });
176
- });
200
+ );
177
201
  TextField.displayName = "TextField";
178
- const CompactTextField = forwardRef(({
179
- className,
180
- id,
181
- label: label2,
182
- needsErrorFeedback,
183
- value,
184
- onFocus,
185
- onBlur,
186
- "data-test-id": testId = "compact-text-field",
187
- ...rest
188
- }, ref) => {
189
- const [isActive2, setIsActive] = useState((typeof value === "boolean" || value ? value.toString() : "").trim().length !== 0);
190
- const isActiveState = isActive2 || needsErrorFeedback;
191
- const classes = cx(styles.compactTextField, className, isActiveState && styles.isActive);
192
- const placeholder = isActiveState ? "" : label2;
193
- const handleFocus = (event) => {
194
- setIsActive(true);
195
- if (onFocus) {
196
- onFocus(event);
197
- }
198
- };
199
- const handleBlur = (event) => {
200
- const value2 = event.target.value || "";
201
- setIsActive(value2.trim().length !== 0);
202
- if (onBlur) {
203
- onBlur(event);
204
- }
205
- };
206
- return /* @__PURE__ */ jsxs("div", {
207
- className: classes,
208
- "data-test-id": testId,
209
- children: [/* @__PURE__ */ jsx(Label, {
210
- htmlFor: id,
211
- children: label2
212
- }), /* @__PURE__ */ jsx(TextField, {
213
- ...rest,
214
- id,
215
- placeholder,
216
- value,
217
- ref,
218
- onFocus: handleFocus,
219
- onBlur: handleBlur
220
- })]
221
- });
222
- });
202
+ const CompactTextField = forwardRef(
203
+ ({
204
+ className,
205
+ id,
206
+ label: label2,
207
+ needsErrorFeedback,
208
+ value,
209
+ onFocus,
210
+ onBlur,
211
+ "data-test-id": testId = "compact-text-field",
212
+ ...rest
213
+ }, ref) => {
214
+ const [isActive2, setIsActive] = useState(
215
+ (typeof value === "boolean" || value ? value.toString() : "").trim().length !== 0
216
+ );
217
+ const isActiveState = isActive2 || needsErrorFeedback;
218
+ const classes = cx(styles.compactTextField, className, isActiveState && styles.isActive);
219
+ const placeholder = isActiveState ? "" : label2;
220
+ const handleFocus = (event) => {
221
+ setIsActive(true);
222
+ if (onFocus) {
223
+ onFocus(event);
224
+ }
225
+ };
226
+ const handleBlur = (event) => {
227
+ const value2 = event.target.value || "";
228
+ setIsActive(value2.trim().length !== 0);
229
+ if (onBlur) {
230
+ onBlur(event);
231
+ }
232
+ };
233
+ return /* @__PURE__ */ jsxs("div", { className: classes, "data-test-id": testId, children: [
234
+ /* @__PURE__ */ jsx(Label, { htmlFor: id, children: label2 }),
235
+ /* @__PURE__ */ jsx(
236
+ TextField,
237
+ {
238
+ ...rest,
239
+ id,
240
+ placeholder,
241
+ value,
242
+ ref,
243
+ onFocus: handleFocus,
244
+ onBlur: handleBlur
245
+ }
246
+ )
247
+ ] });
248
+ }
249
+ );
223
250
  CompactTextField.displayName = "CompactTextField";
224
251
  const FieldError = ({
225
252
  name,
@@ -231,17 +258,22 @@ const FieldError = ({
231
258
  if (!errorMessage) {
232
259
  return null;
233
260
  }
234
- return /* @__PURE__ */ jsxs("span", {
235
- ...rest,
236
- className: cx(styles.fieldError, className),
237
- "aria-live": "polite",
238
- "data-test-id": testId,
239
- "aria-label": "Error",
240
- id: createFieldErrorId(name),
241
- children: [/* @__PURE__ */ jsx(AlertRhombus, {
242
- size: "small"
243
- }), " ", errorMessage]
244
- });
261
+ return /* @__PURE__ */ jsxs(
262
+ "span",
263
+ {
264
+ ...rest,
265
+ className: cx(styles.fieldError, className),
266
+ "aria-live": "polite",
267
+ "data-test-id": testId,
268
+ "aria-label": "Error",
269
+ id: createFieldErrorId(name),
270
+ children: [
271
+ /* @__PURE__ */ jsx(AlertRhombus, { size: "small" }),
272
+ " ",
273
+ errorMessage
274
+ ]
275
+ }
276
+ );
245
277
  };
246
278
  const FieldSet = ({
247
279
  children,
@@ -250,12 +282,7 @@ const FieldSet = ({
250
282
  ...rest
251
283
  }) => {
252
284
  const classes = cx(styles.fieldSet, className);
253
- return /* @__PURE__ */ jsx("fieldset", {
254
- "data-test-id": testId,
255
- className: classes,
256
- ...rest,
257
- children
258
- });
285
+ return /* @__PURE__ */ jsx("fieldset", { "data-test-id": testId, className: classes, ...rest, children });
259
286
  };
260
287
  const Form = (props) => {
261
288
  const {
@@ -266,13 +293,13 @@ const Form = (props) => {
266
293
  "data-test-id": testId = "form",
267
294
  ...rest
268
295
  } = props;
269
- const classes = cx(styles.form, className, inline && styles.formInline, !!hasIncreasedErrorMargin && styles.formIncreasedErrorMargin);
270
- return /* @__PURE__ */ jsx("form", {
271
- ...rest,
272
- "data-test-id": testId,
273
- className: classes,
274
- children
275
- });
296
+ const classes = cx(
297
+ styles.form,
298
+ className,
299
+ inline && styles.formInline,
300
+ !!hasIncreasedErrorMargin && styles.formIncreasedErrorMargin
301
+ );
302
+ return /* @__PURE__ */ jsx("form", { ...rest, "data-test-id": testId, className: classes, children });
276
303
  };
277
304
  const FormGroup = (props) => {
278
305
  const {
@@ -284,13 +311,12 @@ const FormGroup = (props) => {
284
311
  "data-test-id": testId = "form-group",
285
312
  ...rest
286
313
  } = props;
287
- const classes = cx(styles.formGroup, className, !ignoreValidation && isInvalid2 && styles.isInvalid);
288
- return /* @__PURE__ */ jsx("fieldset", {
289
- className: classes,
290
- "data-test-id": testId,
291
- ...rest,
292
- children
293
- });
314
+ const classes = cx(
315
+ styles.formGroup,
316
+ className,
317
+ !ignoreValidation && isInvalid2 && styles.isInvalid
318
+ );
319
+ return /* @__PURE__ */ jsx("fieldset", { className: classes, "data-test-id": testId, ...rest, children });
294
320
  };
295
321
  const FormHint = ({
296
322
  className,
@@ -299,12 +325,7 @@ const FormHint = ({
299
325
  ...rest
300
326
  }) => {
301
327
  const classes = cx(styles.hint, className);
302
- return /* @__PURE__ */ jsx("div", {
303
- ...rest,
304
- "data-test-id": testId,
305
- className: classes,
306
- children
307
- });
328
+ return /* @__PURE__ */ jsx("div", { ...rest, "data-test-id": testId, className: classes, children });
308
329
  };
309
330
  const FormField = ({
310
331
  isRequired,
@@ -318,31 +339,39 @@ const FormField = ({
318
339
  children,
319
340
  className,
320
341
  onBlur,
321
- "data-test-id": testId = "form-field"
342
+ "data-test-id": testId = "form-field",
343
+ LabelProps = {},
344
+ FormHintProps = {},
345
+ FieldErrorProps = {}
322
346
  }) => {
323
347
  const handleBlur = () => {
324
348
  onBlur && onBlur(name);
325
349
  };
326
- return /* @__PURE__ */ jsxs(FormGroup, {
327
- className: cx(styles.field, className),
328
- name,
329
- ignoreValidation,
330
- isInvalid: isInvalid2,
331
- onBlur: handleBlur,
332
- "data-test-id": testId,
333
- children: [label2 && /* @__PURE__ */ jsx(Label, {
334
- htmlFor,
335
- required: isRequired,
336
- children: label2
337
- }), hint2 && /* @__PURE__ */ jsx(FormHint, {
338
- className: styles.hint,
339
- children: hint2
340
- }), children, /* @__PURE__ */ jsx(FieldError, {
341
- className: styles.fieldErrorMessage,
350
+ return /* @__PURE__ */ jsxs(
351
+ FormGroup,
352
+ {
353
+ className: cx(styles.field, className),
342
354
  name,
343
- errorMessage
344
- })]
345
- });
355
+ ignoreValidation,
356
+ isInvalid: isInvalid2,
357
+ onBlur: handleBlur,
358
+ "data-test-id": testId,
359
+ children: [
360
+ label2 && /* @__PURE__ */ jsx(Label, { htmlFor, required: isRequired, ...LabelProps, children: label2 }),
361
+ hint2 && /* @__PURE__ */ jsx(FormHint, { className: styles.hint, ...FormHintProps, children: hint2 }),
362
+ children,
363
+ /* @__PURE__ */ jsx(
364
+ FieldError,
365
+ {
366
+ className: styles.fieldErrorMessage,
367
+ name,
368
+ errorMessage,
369
+ ...FieldErrorProps
370
+ }
371
+ )
372
+ ]
373
+ }
374
+ );
346
375
  };
347
376
  const IconField = ({
348
377
  icon,
@@ -353,15 +382,10 @@ const IconField = ({
353
382
  }) => {
354
383
  const Icon = icon;
355
384
  const classes = cx(styles.iconField, className);
356
- return /* @__PURE__ */ jsxs("div", {
357
- className: classes,
358
- "data-test-id": testId,
359
- ...rest,
360
- children: [children, /* @__PURE__ */ jsx(Icon, {
361
- size: "small",
362
- className: styles.iconFieldIcon
363
- })]
364
- });
385
+ return /* @__PURE__ */ jsxs("div", { className: classes, "data-test-id": testId, ...rest, children: [
386
+ children,
387
+ /* @__PURE__ */ jsx(Icon, { size: "small", className: styles.iconFieldIcon })
388
+ ] });
365
389
  };
366
390
  const Radio = ({
367
391
  "aria-label": ariaLabel,
@@ -378,29 +402,27 @@ const Radio = ({
378
402
  }) => {
379
403
  const hasAriaLabel = ariaLabel !== void 0 || ariaLabelledby !== void 0;
380
404
  if (!children && !hasAriaLabel) {
381
- console.warn("If you do not provide children, you must specify an aria-label for accessibility");
405
+ console.warn(
406
+ "If you do not provide children, you must specify an aria-label for accessibility"
407
+ );
382
408
  }
383
- return /* @__PURE__ */ jsxs(Fragment, {
384
- children: [/* @__PURE__ */ jsx("input", {
385
- ...rest,
386
- "aria-label": ariaLabel,
387
- "aria-labelledby": ariaLabelledby,
388
- className: cx(styles.radio, className),
389
- checked,
390
- disabled,
391
- id,
392
- "data-test-id": testId,
393
- type: "radio"
394
- }), /* @__PURE__ */ jsx(Label, {
395
- className: labelClassName,
396
- htmlFor: id,
397
- style: labelStyle,
398
- children: disabled ? /* @__PURE__ */ jsx("span", {
399
- className: styles.labelDisabled,
400
- children
401
- }) : children
402
- })]
403
- });
409
+ return /* @__PURE__ */ jsxs(Fragment, { children: [
410
+ /* @__PURE__ */ jsx(
411
+ "input",
412
+ {
413
+ ...rest,
414
+ "aria-label": ariaLabel,
415
+ "aria-labelledby": ariaLabelledby,
416
+ className: cx(styles.radio, className),
417
+ checked,
418
+ disabled,
419
+ id,
420
+ "data-test-id": testId,
421
+ type: "radio"
422
+ }
423
+ ),
424
+ /* @__PURE__ */ jsx(Label, { className: labelClassName, htmlFor: id, style: labelStyle, children: disabled ? /* @__PURE__ */ jsx("span", { className: styles.labelDisabled, children }) : children })
425
+ ] });
404
426
  };
405
427
  const RadioGroup = (props) => {
406
428
  const {
@@ -453,56 +475,95 @@ const RadioGroup = (props) => {
453
475
  return null;
454
476
  }
455
477
  const radios = Children.map(children, (child) => updateRadioElems(child));
456
- return /* @__PURE__ */ jsxs("fieldset", {
457
- "data-test-id": testId,
458
- ref: fieldsetRef,
459
- children: [legend && /* @__PURE__ */ jsx("legend", {
460
- children: /* @__PURE__ */ jsx(VisuallyHidden, {
461
- children: legend
462
- })
463
- }), /* @__PURE__ */ jsx("div", {
464
- ...rest,
465
- children: radios
466
- })]
467
- });
478
+ return /* @__PURE__ */ jsxs("fieldset", { "data-test-id": testId, ref: fieldsetRef, children: [
479
+ legend && /* @__PURE__ */ jsx("legend", { children: /* @__PURE__ */ jsx(VisuallyHidden, { children: legend }) }),
480
+ /* @__PURE__ */ jsx("div", { ...rest, children: radios })
481
+ ] });
468
482
  };
469
- const SelectField = ({
470
- className,
471
- children,
472
- "data-test-id": testId = "select",
473
- ...rest
474
- }) => {
475
- const classes = cx(styles.formInput, className);
476
- return /* @__PURE__ */ jsx("select", {
477
- ...rest,
478
- "data-test-id": testId,
479
- className: classes,
480
- children
481
- });
483
+ const SelectField = forwardRef(
484
+ ({ className, children, "data-test-id": testId = "select", ...rest }, ref) => {
485
+ const classes = cx(styles.formInput, className);
486
+ return /* @__PURE__ */ jsx("select", { ...rest, "data-test-id": testId, className: classes, ref, children });
487
+ }
488
+ );
489
+ SelectField.displayName = "SelectField";
490
+ const TextArea = forwardRef(
491
+ ({ className, "data-test-id": testId = "text-area", ...props }, ref) => {
492
+ const onKeyDown = (e) => {
493
+ if (e.key === "ArrowRight" || e.key === "ArrowDown" || e.key === "ArrowUp" || e.key === "ArrowLeft") {
494
+ e.stopPropagation();
495
+ }
496
+ if (e.key === "Escape") {
497
+ e.nativeEvent.stopImmediatePropagation();
498
+ }
499
+ };
500
+ return /* @__PURE__ */ jsx(
501
+ "textarea",
502
+ {
503
+ ...props,
504
+ className: cx(styles.formInput, className),
505
+ ref,
506
+ "data-test-id": testId,
507
+ "aria-describedby": props["aria-describedby"] || createFieldErrorId(props.id),
508
+ onKeyDown
509
+ }
510
+ );
511
+ }
512
+ );
513
+ TextArea.displayName = "TextArea";
514
+ const defaultFormatOptions = {
515
+ maximumFractionDigits: 6
482
516
  };
483
- const TextArea = forwardRef(({
484
- className,
485
- "data-test-id": testId = "text-area",
486
- ...props
487
- }, ref) => {
488
- const onKeyDown = (e) => {
489
- if (e.key === "ArrowRight" || e.key === "ArrowDown" || e.key === "ArrowUp" || e.key === "ArrowLeft") {
490
- e.stopPropagation();
491
- }
492
- if (e.key === "Escape") {
493
- e.nativeEvent.stopImmediatePropagation();
494
- }
495
- };
496
- return /* @__PURE__ */ jsx("textarea", {
497
- ...props,
498
- className: cx(styles.formInput, className),
499
- ref,
500
- "data-test-id": testId,
501
- "aria-describedby": props["aria-describedby"] || createFieldErrorId(props.id),
502
- onKeyDown
517
+ const useNumberField = ({
518
+ className: rootClassName,
519
+ "data-test-id": testId = "input",
520
+ id,
521
+ name,
522
+ ...otherProps
523
+ } = {}) => {
524
+ const formatOptions = useObjectMemo({
525
+ ...defaultFormatOptions,
526
+ ...otherProps.formatOptions
503
527
  });
504
- });
505
- TextArea.displayName = "TextArea";
528
+ const { locale } = useLocale();
529
+ const numberFieldState = useNumberFieldState({ ...otherProps, locale, formatOptions });
530
+ const inputRef = useRef(null);
531
+ const {
532
+ descriptionProps: formHintProps,
533
+ errorMessageProps: fieldErrorProps,
534
+ labelProps,
535
+ groupProps,
536
+ inputProps,
537
+ incrementButtonProps,
538
+ decrementButtonProps
539
+ } = useNumberField$1({ ...otherProps, formatOptions, id }, numberFieldState, inputRef);
540
+ return {
541
+ fieldErrorProps,
542
+ formHintProps,
543
+ labelProps,
544
+ renderNumberField: () => /* @__PURE__ */ jsxs("div", { ...groupProps, className: styles.numberField, children: [
545
+ /* @__PURE__ */ jsx(
546
+ "input",
547
+ {
548
+ ...inputProps,
549
+ className: cx(styles.formInput, styles["numberField-input"]),
550
+ "data-test-id": testId,
551
+ name,
552
+ ref: inputRef
553
+ }
554
+ ),
555
+ /* @__PURE__ */ jsxs("div", { className: styles["numberField-stepperContainer"], children: [
556
+ /* @__PURE__ */ jsx(Stepper, { ...incrementButtonProps, children: /* @__PURE__ */ jsx(ExpandLess, {}) }),
557
+ /* @__PURE__ */ jsx(Stepper, { ...decrementButtonProps, children: /* @__PURE__ */ jsx(ExpandMore, {}) })
558
+ ] })
559
+ ] })
560
+ };
561
+ };
562
+ const Stepper = (props) => {
563
+ const buttonRef = useRef(null);
564
+ const { buttonProps } = useButton(props, buttonRef);
565
+ return /* @__PURE__ */ jsx("button", { ...buttonProps, className: styles["numberField-stepper"], ref: buttonRef, children: props.children });
566
+ };
506
567
  export {
507
568
  Checkbox,
508
569
  CompactTextField,
@@ -519,6 +580,7 @@ export {
519
580
  RequiredAsterisk,
520
581
  SelectField,
521
582
  TextArea,
522
- TextField
583
+ TextField,
584
+ useNumberField
523
585
  };
524
586
  //# sourceMappingURL=index.es.js.map