@jobber/components 8.26.3 → 8.27.1

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 (65) hide show
  1. package/Select.d.ts +1 -0
  2. package/Select.js +17 -0
  3. package/dist/BottomSheet-cjs.js +8 -7
  4. package/dist/BottomSheet-es.js +9 -8
  5. package/dist/ComboboxChipRemove-cjs.js +2 -1
  6. package/dist/ComboboxChipRemove-es.js +4 -3
  7. package/dist/DrawerDescription-cjs.js +4 -97
  8. package/dist/DrawerDescription-es.js +6 -98
  9. package/dist/FieldDescription-cjs.js +880 -0
  10. package/dist/FieldDescription-es.js +856 -0
  11. package/dist/InputNumberExperimental-cjs.js +5 -875
  12. package/dist/InputNumberExperimental-es.js +2 -854
  13. package/dist/MenuSubmenuTrigger-es.js +4 -4
  14. package/dist/Modal/index.cjs +12 -2
  15. package/dist/Modal/index.mjs +13 -3
  16. package/dist/NumberFieldInput-cjs.js +2 -2
  17. package/dist/NumberFieldInput-es.js +1 -1
  18. package/dist/ScrollAreaViewport-cjs.js +2122 -12
  19. package/dist/ScrollAreaViewport-es.js +2118 -13
  20. package/dist/Select/Select.d.ts +31 -0
  21. package/dist/Select/Select.types.d.ts +145 -0
  22. package/dist/Select/SelectBottomSheet.d.ts +4 -0
  23. package/dist/Select/SelectDropdown.d.ts +4 -0
  24. package/dist/Select/index.cjs +41 -0
  25. package/dist/Select/index.d.ts +2 -0
  26. package/dist/Select/index.mjs +35 -0
  27. package/dist/Select-cjs.js +231 -0
  28. package/dist/Select-es.js +229 -0
  29. package/dist/SelectPrimitive-cjs.js +20 -3
  30. package/dist/SelectPrimitive-es.js +20 -3
  31. package/dist/dialogReturnFocus-cjs.js +8 -5
  32. package/dist/dialogReturnFocus-es.js +9 -6
  33. package/dist/docs/Dialog/Dialog.md +74 -21
  34. package/dist/docs/Select/Select.md +428 -0
  35. package/dist/docs/SelectPrimitive/SelectPrimitive.md +14 -1
  36. package/dist/docs/index.md +1 -0
  37. package/dist/floating-ui.react-dom-es.js +1 -1
  38. package/dist/floating-ui.react-es.js +1 -1
  39. package/dist/floating-ui.utils.dom-es.js +1 -1
  40. package/dist/index.cjs +9 -0
  41. package/dist/index.d.mts +1 -0
  42. package/dist/index.d.ts +1 -0
  43. package/dist/index.mjs +8 -0
  44. package/dist/primitives/ComboboxPrimitive/index.cjs +1 -0
  45. package/dist/primitives/ComboboxPrimitive/index.mjs +1 -0
  46. package/dist/primitives/HelperText/HelperText.d.ts +2 -1
  47. package/dist/primitives/InputNumberExperimental/index.cjs +3 -1
  48. package/dist/primitives/InputNumberExperimental/index.mjs +3 -1
  49. package/dist/primitives/SelectPrimitive/SelectPrimitive.d.ts +11 -0
  50. package/dist/primitives/SelectPrimitive/index.d.ts +1 -1
  51. package/dist/primitives/SelectPrimitive/types.d.ts +15 -0
  52. package/dist/primitives/index.cjs +2 -0
  53. package/dist/primitives/index.mjs +2 -0
  54. package/dist/stringifyLocale-cjs.js +13 -0
  55. package/dist/stringifyLocale-es.js +11 -0
  56. package/dist/styles.css +300 -10
  57. package/dist/unstyledPrimitives/index.cjs +219 -2230
  58. package/dist/unstyledPrimitives/index.mjs +225 -2236
  59. package/dist/useButton-es.js +2 -2
  60. package/dist/useCompositeListItem-es.js +1 -1
  61. package/dist/useLabel-cjs.js +0 -11
  62. package/dist/useLabel-es.js +2 -12
  63. package/dist/useScrollLock-es.js +3 -3
  64. package/dist/utils/meta/meta.json +5 -0
  65. package/package.json +7 -2
@@ -0,0 +1,428 @@
1
+ # Select
2
+
3
+ Select presents a defined list of options to choose from. It is a prop-driven,
4
+ labelled dropdown wrapped in a field structure that handles the label,
5
+ description, and error messaging for you.
6
+
7
+ ```tsx
8
+ import React, { useState } from "react";
9
+ import { Select } from "@jobber/components/Select";
10
+
11
+ export function SelectBasicExample() {
12
+ const [value, setValue] = useState<string | undefined>("active");
13
+
14
+ return (
15
+ <Select label="Status" value={value} onValueChange={setValue}>
16
+ <Select.Item value="active">Active</Select.Item>
17
+ <Select.Item value="archived">Archived</Select.Item>
18
+ <Select.Item value="draft">Draft</Select.Item>
19
+ </Select>
20
+ );
21
+ }
22
+ ```
23
+
24
+ ## Design & usage guidelines
25
+
26
+ Use Select when a user needs to pick a single value from a known, reasonably
27
+ short list of options. Each option is declared with `Select.Item`, where the
28
+ `value` is submitted and the children are shown as the label.
29
+
30
+ Select is controlled: pass the current `value` and an `onValueChange` handler to
31
+ keep your state in sync.
32
+
33
+ ## Empty state
34
+
35
+ The `label` doubles as the placeholder: while no value is selected it sits
36
+ centered inside the field, then rises to a floating mini-label once the user
37
+ picks an option. There is no separate `placeholder` prop — the label fills that
38
+ role.
39
+
40
+ ```tsx
41
+ import React, { useState } from "react";
42
+ import { Select } from "@jobber/components/Select";
43
+
44
+ export function SelectEmptyExample() {
45
+ const [value, setValue] = useState<string | undefined>();
46
+
47
+ return (
48
+ <Select label="Status" value={value} onValueChange={setValue}>
49
+ <Select.Item value="active">Active</Select.Item>
50
+ <Select.Item value="archived">Archived</Select.Item>
51
+ <Select.Item value="draft">Draft</Select.Item>
52
+ </Select>
53
+ );
54
+ }
55
+ ```
56
+
57
+ ## Description
58
+
59
+ Use `description` to add supporting help text beneath the field.
60
+
61
+ ```tsx
62
+ import React, { useState } from "react";
63
+ import { Select } from "@jobber/components/Select";
64
+
65
+ export function SelectDescriptionExample() {
66
+ const [value, setValue] = useState<string | undefined>();
67
+
68
+ return (
69
+ <Select
70
+ label="Status"
71
+ description="This controls who can see the record."
72
+ value={value}
73
+ onValueChange={setValue}
74
+ >
75
+ <Select.Item value="active">Active</Select.Item>
76
+ <Select.Item value="archived">Archived</Select.Item>
77
+ <Select.Item value="draft">Draft</Select.Item>
78
+ </Select>
79
+ );
80
+ }
81
+ ```
82
+
83
+ ## States
84
+
85
+ ### Error
86
+
87
+ Pass an `error` message to mark the field invalid and show the message beneath
88
+ the field. The error replaces the description while it is present. Use `invalid`
89
+ instead to apply the invalid styling without a message — for example when a form
90
+ library such as React Hook Form renders the error text itself.
91
+
92
+ ```tsx
93
+ import React, { useState } from "react";
94
+ import { Select } from "@jobber/components/Select";
95
+
96
+ export function SelectErrorExample() {
97
+ const [value, setValue] = useState<string | undefined>();
98
+
99
+ return (
100
+ <Select
101
+ label="Status"
102
+ description="This controls who can see the record."
103
+ error="Please choose a status."
104
+ value={value}
105
+ onValueChange={setValue}
106
+ >
107
+ <Select.Item value="active">Active</Select.Item>
108
+ <Select.Item value="archived">Archived</Select.Item>
109
+ <Select.Item value="draft">Draft</Select.Item>
110
+ </Select>
111
+ );
112
+ }
113
+ ```
114
+
115
+ ### Disabled
116
+
117
+ Set `disabled` to prevent interaction with the field.
118
+
119
+ ```tsx
120
+ import React from "react";
121
+ import { Select } from "@jobber/components/Select";
122
+
123
+ export function SelectDisabledExample() {
124
+ return (
125
+ <Select label="Status" disabled value="active">
126
+ <Select.Item value="active">Active</Select.Item>
127
+ <Select.Item value="archived">Archived</Select.Item>
128
+ <Select.Item value="draft">Draft</Select.Item>
129
+ </Select>
130
+ );
131
+ }
132
+ ```
133
+
134
+ ## Grouping
135
+
136
+ Organize related options under section headers with `Select.Group` and
137
+ `Select.GroupLabel`. Adjacent groups are divided automatically, so you don't
138
+ need to add a separator between them. `Select.Separator` is available for adding
139
+ a divider elsewhere in the list.
140
+
141
+ ```tsx
142
+ import React, { useState } from "react";
143
+ import { Select } from "@jobber/components/Select";
144
+
145
+ export function SelectGroupedExample() {
146
+ const [value, setValue] = useState<string | undefined>();
147
+
148
+ return (
149
+ <Select label="Produce" value={value} onValueChange={setValue}>
150
+ <Select.Group>
151
+ <Select.GroupLabel>Fruits</Select.GroupLabel>
152
+ <Select.Item value="apple">Apple</Select.Item>
153
+ <Select.Item value="banana">Banana</Select.Item>
154
+ </Select.Group>
155
+ <Select.Group>
156
+ <Select.GroupLabel>Vegetables</Select.GroupLabel>
157
+ <Select.Item value="carrot">Carrot</Select.Item>
158
+ <Select.Item value="spinach">Spinach</Select.Item>
159
+ </Select.Group>
160
+ </Select>
161
+ );
162
+ }
163
+ ```
164
+
165
+ ## Custom selected value
166
+
167
+ The closed trigger shows the selected value capitalized by default. Pass
168
+ `renderValue` to display something different from the option's label — here the
169
+ list shows short labels (`Low`, `Medium`, `High`) while the trigger shows the
170
+ full `"High priority"`. The open list always shows each `Select.Item`'s
171
+ children.
172
+
173
+ ```tsx
174
+ import React, { useState } from "react";
175
+ import { Select } from "@jobber/components/Select";
176
+
177
+ const PRIORITY_LABELS: Record<string, string> = {
178
+ low: "Low priority",
179
+ medium: "Medium priority",
180
+ high: "High priority",
181
+ };
182
+
183
+ export function SelectRenderValueExample() {
184
+ const [value, setValue] = useState<string | undefined>("high");
185
+
186
+ return (
187
+ <Select
188
+ label="Priority"
189
+ value={value}
190
+ onValueChange={setValue}
191
+ renderValue={selected => PRIORITY_LABELS[selected]}
192
+ >
193
+ <Select.Item value="low">Low</Select.Item>
194
+ <Select.Item value="medium">Medium</Select.Item>
195
+ <Select.Item value="high">High</Select.Item>
196
+ </Select>
197
+ );
198
+ }
199
+ ```
200
+
201
+ ## Sizes
202
+
203
+ Use the `size` prop to render a `small` control for tighter layouts. The
204
+ floating mini-label is hidden at the `small` size, so the compact control keeps
205
+ a single-line height.
206
+
207
+ ```tsx
208
+ import React, { useState } from "react";
209
+ import { Select } from "@jobber/components/Select";
210
+
211
+ export function SelectSizeExample() {
212
+ const [value, setValue] = useState<string | undefined>("active");
213
+
214
+ return (
215
+ <Select label="Status" size="small" value={value} onValueChange={setValue}>
216
+ <Select.Item value="active">Active</Select.Item>
217
+ <Select.Item value="archived">Archived</Select.Item>
218
+ <Select.Item value="draft">Draft</Select.Item>
219
+ </Select>
220
+ );
221
+ }
222
+ ```
223
+
224
+ ## Inline
225
+
226
+ Set `inline` to embed the Select within a line of text. The description and
227
+ error messaging are suppressed in inline mode.
228
+
229
+ ```tsx
230
+ import React, { useState } from "react";
231
+ import { Select } from "@jobber/components/Select";
232
+
233
+ export function SelectInlineExample() {
234
+ const [value, setValue] = useState<string | undefined>("active");
235
+
236
+ return (
237
+ <div>
238
+ Set the record to{" "}
239
+ <Select label="Status" inline value={value} onValueChange={setValue}>
240
+ <Select.Item value="active">Active</Select.Item>
241
+ <Select.Item value="archived">Archived</Select.Item>
242
+ <Select.Item value="draft">Draft</Select.Item>
243
+ </Select>{" "}
244
+ today.
245
+ </div>
246
+ );
247
+ }
248
+ ```
249
+
250
+ ## Mobile
251
+
252
+ On small (touch-sized) web screens — viewport widths of `490px` or less — the
253
+ options open as a bottom sheet instead of an anchored dropdown, matching the
254
+ mobile pattern used by `Menu` and `Dialog`. This is automatic and requires no
255
+ props; selection, keyboard, and focus behaviour are unchanged. Resize the
256
+ preview narrow (or open the examples above on a phone) to see the sheet.
257
+
258
+
259
+ ## Content
260
+
261
+ ### Options and labels
262
+
263
+ Declare each option with `Select.Item`. The `value` prop is what `onValueChange`
264
+ reports and what is submitted with a form; the children are the human-readable
265
+ label shown in the open list.
266
+
267
+ ### The selected value display
268
+
269
+ The closed trigger shows the selected **value**, capitalized by default (e.g.
270
+ `"active"` → `"Active"`). It does not read the option's children — so when the
271
+ label differs from the capitalized value, pass `renderValue` to control what the
272
+ trigger shows:
273
+
274
+ ```tsx
275
+ <Select
276
+ label="Status"
277
+ value={value}
278
+ onValueChange={setValue}
279
+ renderValue={value => STATUS_LABELS[value]}
280
+ >
281
+ {/* Select.Item options */}
282
+ </Select>
283
+ ```
284
+
285
+ ### Grouping
286
+
287
+ * `Select.Group`: wraps a set of related options.
288
+ * `Select.GroupLabel`: the section header text for a group.
289
+ * `Select.Separator`: an optional visual divider. Adjacent `Select.Group`s are
290
+ already divided automatically, so reach for this only to divide options
291
+ elsewhere in the list.
292
+
293
+ ## Component customization
294
+
295
+ Select is intentionally opinionated: it exposes a curated set of props rather
296
+ than the full underlying API. The subcomponents (`Select.Item`, `Select.Group`,
297
+ `Select.GroupLabel`, `Select.Separator`) accept `className` and `style` for
298
+ per-option styling; reach out to UXF if you need behaviour beyond what the props
299
+ provide.
300
+
301
+ ### Controlled usage
302
+
303
+ Select is controlled only. Always pass `value` and `onValueChange`; there is no
304
+ uncontrolled `defaultValue`. The `id` and `name` are generated for you and wired
305
+ to the label automatically.
306
+
307
+ The change handler is named `onValueChange` to stay isomorphic with Base UI, and
308
+ to encode the payload (the value, not an event) in its name.
309
+
310
+ ### Using with a form library
311
+
312
+ Select is form-library-agnostic — it exposes plain controlled props, so any
313
+ system (React Hook Form, Formik, TanStack Form, or plain `useState`) drives it
314
+ by wiring:
315
+
316
+ * `value` — the current value
317
+ * `onValueChange` — the library's value setter
318
+ * `onBlur` / `onFocus` — touched state and blur/focus-mode validation
319
+ * `error` (message) or `invalid` (styling only) — validation feedback
320
+ * `ref` — exposes `focus()`, so a form can focus this field on error
321
+
322
+ Because the change prop is `onValueChange` (not `onChange`), spreading a field
323
+ object whose handler is named `onChange` — for example React Hook Form's `field`
324
+ via `<Select {...field} />` — will **not** wire up the change handler.
325
+ `field.onChange` lands on a prop nothing reads, and JSX spread does not error,
326
+ so the field silently stops updating. Wire the props explicitly instead:
327
+
328
+ ```tsx
329
+ <Controller
330
+ control={control}
331
+ name="status"
332
+ render={({ field }) => (
333
+ <Select
334
+ label="Status"
335
+ name={field.name}
336
+ value={field.value}
337
+ onValueChange={field.onChange}
338
+ onBlur={field.onBlur}
339
+ ref={field.ref}
340
+ >
341
+ {/* Select.Item options */}
342
+ </Select>
343
+ )}
344
+ />
345
+ ```
346
+
347
+ If you want spread ergonomics, keep the remap in your own app — the design
348
+ system intentionally ships no form-library adapter:
349
+
350
+ ```tsx
351
+ // app-side helper, not part of @jobber/components
352
+ const toValueField = ({ onChange, ...field }) => ({
353
+ ...field,
354
+ onValueChange: onChange,
355
+ });
356
+
357
+ <Select label="Status" {...toValueField(field)}>
358
+ {/* Select.Item options */}
359
+ </Select>;
360
+ ```
361
+
362
+ > **Note:** Select is built on Base UI's `Field` primitive, but it is not yet
363
+ > wired to participate in a surrounding Base UI `<Form>` — the `Form` `errors`
364
+ > prop and `Form`-driven focus-on-error do not reach Select. Drive validation
365
+ > through the `error` / `invalid` props for now.
366
+
367
+ ## Related components
368
+
369
+ * [LegacySelect](../LegacySelect/LegacySelect.md): the previous native `<select>`-based
370
+ implementation.
371
+
372
+
373
+ ## Props
374
+
375
+ ### Web
376
+
377
+ #### Select
378
+
379
+ | Prop | Type | Required | Default | Description |
380
+ |------|------|----------|---------|-------------|
381
+ | `children` | `ReactNode` | No | — | `Select.Item`, `Select.Group`, `Select.GroupLabel`, and `Select.Separator` that make up the dropdown list. |
382
+ | `description` | `ReactNode` | No | — | Helper text rendered beneath the field. |
383
+ | `disabled` | `boolean` | No | — | Disables the whole field. |
384
+ | `error` | `string` | No | — | Error message. Shows the message beneath the field and applies invalid styling. Replaces the description while present. |
385
+ | `id` | `string` | No | — | Id applied to the field's trigger. Auto-generated when omitted. |
386
+ | `inline` | `boolean` | No | — | Renders the field inline and suppresses the description / error. |
387
+ | `invalid` | `boolean` | No | — | Applies invalid styling without rendering a message. Use when the message is rendered elsewhere (e.g. by React Hook F... |
388
+ | `label` | `string` | No | — | Floating label shown inside the field. It sits as the placeholder when no value is selected and rises to a mini-label... |
389
+ | `name` | `string` | No | — | Name used for the form field (FormData key, autofill, test selectors). |
390
+ | `onBlur` | `() => void` | No | — | Called when the field's trigger loses focus. Useful for touched state and blur-mode validation. |
391
+ | `onFocus` | `() => void` | No | — | Called when the field's trigger receives focus. |
392
+ | `onValueChange` | `(value: string) => void` | No | — | Called with the newly selected value. Named to match Base UI. Note: React Hook Form's `field.onChange` will not be wi... |
393
+ | `ref` | `Ref<SelectRef>` | No | — | Imperative handle exposing `focus()`. |
394
+ | `renderValue` | `(value: string) => ReactNode` | No | — | Renders the selected value shown in the closed trigger. When omitted, the value is shown capitalized (e.g. `"active"`... |
395
+ | `size` | `"large" | "small"` | No | — | Field size. |
396
+ | `value` | `string` | No | — | The controlled selected value. `null` (or `undefined`) when empty. |
397
+
398
+ #### Select.Group
399
+
400
+ | Prop | Type | Required | Default | Description |
401
+ |------|------|----------|---------|-------------|
402
+ | `children` | `ReactNode` | No | — | A `Select.GroupLabel` and the `Select.Item`s that belong to the group. |
403
+ | `className` | `string` | No | — | |
404
+ | `style` | `CSSProperties` | No | — | |
405
+
406
+ #### Select.GroupLabel
407
+
408
+ | Prop | Type | Required | Default | Description |
409
+ |------|------|----------|---------|-------------|
410
+ | `children` | `ReactNode` | No | — | The section heading shown above the group's options. |
411
+ | `className` | `string` | No | — | |
412
+ | `style` | `CSSProperties` | No | — | |
413
+
414
+ #### Select.Item
415
+
416
+ | Prop | Type | Required | Default | Description |
417
+ |------|------|----------|---------|-------------|
418
+ | `children` | `ReactNode` | Yes | — | The display label for the option. |
419
+ | `value` | `string` | Yes | — | The value submitted when this option is selected. |
420
+ | `className` | `string` | No | — | |
421
+ | `style` | `CSSProperties` | No | — | |
422
+
423
+ #### Select.Separator
424
+
425
+ | Prop | Type | Required | Default | Description |
426
+ |------|------|----------|---------|-------------|
427
+ | `className` | `string` | No | — | |
428
+ | `style` | `CSSProperties` | No | — | |
@@ -194,7 +194,7 @@ Base UI.
194
194
  |------|------|----------|---------|-------------|
195
195
  | `className` | `string | ((state: SelectPortalState) => string)` | No | — | CSS class applied to the element, or a function that returns a class based on the component's state. |
196
196
  | `container` | `HTMLElement | ShadowRoot | RefObject<HTMLElement | ShadowRoot>` | No | — | A parent element to render the portal element into. |
197
- | `ref` | `Ref<HTMLDivElement>` | No | — | Allows getting a ref to the component instance. Once the component unmounts, React will set `ref.current` to `null` (... |
197
+ | `ref` | `Ref<HTMLButtonElement>` | No | — | Allows getting a ref to the component instance. Once the component unmounts, React will set `ref.current` to `null` (... |
198
198
  | `render` | `ReactElement<unknown, string | JSXElementConstructor<any>> | ComponentRenderFn<HTMLProps, SelectPortalState>` | No | — | Allows you to replace the component's HTML element with a different tag, or compose it with another component. Accep... |
199
199
  | `style` | `CSSProperties | ((state: SelectPortalState) => CSSProperties)` | No | — | Style applied to the element, or a function that returns a style object based on the component's state. |
200
200
 
@@ -226,6 +226,13 @@ Base UI.
226
226
  | `required` | `boolean` | No | `false` | Whether the user must choose a value before submitting a form. |
227
227
  | `value` | `SelectValueType<Value, Multiple>` | No | — | The value of the select. Use when controlled. |
228
228
 
229
+ #### SelectPrimitiveFieldTrigger
230
+
231
+ | Prop | Type | Required | Default | Description |
232
+ |------|------|----------|---------|-------------|
233
+ | `ref` | `Ref<HTMLButtonElement>` | No | — | Allows getting a ref to the component instance. Once the component unmounts, React will set `ref.current` to `null` (... |
234
+ | `valueSlot` | `ReactNode` | No | — | The value/placeholder display element rendered before the chevron. |
235
+
229
236
  #### SelectPrimitiveGroup
230
237
 
231
238
  | Prop | Type | Required | Default | Description |
@@ -337,3 +344,9 @@ Base UI.
337
344
  | `placeholder` | `ReactNode` | No | — | The placeholder value to display when no value is selected. This is overridden by `children` if specified, or by a nu... |
338
345
  | `render` | `ReactElement<unknown, string | JSXElementConstructor<any>> | ComponentRenderFn<HTMLProps, SelectValueState>` | No | — | Allows you to replace the component's HTML element with a different tag, or compose it with another component. Accep... |
339
346
  | `style` | `CSSProperties | ((state: SelectValueState) => CSSProperties)` | No | — | Style applied to the element, or a function that returns a style object based on the component's state. |
347
+
348
+ #### SelectPrimitiveValueText
349
+
350
+ | Prop | Type | Required | Default | Description |
351
+ |------|------|----------|---------|-------------|
352
+ | `ref` | `Ref<HTMLButtonElement>` | No | — | Allows getting a ref to the component instance. Once the component unmounts, React will set `ref.current` to `null` (... |
@@ -81,6 +81,7 @@
81
81
  [ResponsiveSwitcher](./ResponsiveSwitcher/ResponsiveSwitcher.md)
82
82
  [scaffolding](./scaffolding/scaffolding.md)
83
83
  [SegmentedControl](./SegmentedControl/SegmentedControl.md)
84
+ [Select](./Select/Select.md)
84
85
  [SelectPrimitive](./SelectPrimitive/SelectPrimitive.md)
85
86
  [settings](./settings/settings.md)
86
87
  [SideDrawer](./SideDrawer/SideDrawer.md)
@@ -1,5 +1,5 @@
1
1
  import { g as getSideAxis, a as getAlignmentAxis, b as getSide, c as getAlignment, e as evaluate, d as getPaddingObject, r as rectToClientRect, h as getOppositePlacement, i as getExpandedPlacements, j as getOppositeAxisPlacements, k as getAlignmentSides, l as clamp, m as min, n as max, o as getAxisLength, s as sides, p as getOppositeAxis, q as placements, t as getOppositeAlignmentPlacement, u as createCoords, v as round, f as floor } from './floating-ui.utils-es.js';
2
- import { k as getDocumentElement, b as isElement, a as isHTMLElement, l as isTopLayer, g as getNodeName, m as isOverflowElement, n as getNodeScroll, o as getWindow, e as getParentNode, d as isLastTraversableNode, p as isTableElement, q as isContainingBlock, r as getContainingBlock, f as getComputedStyle$1, h as getOverflowAncestors, s as getFrameElement, j as isWebKit } from './floating-ui.utils.dom-es.js';
2
+ import { k as getDocumentElement, b as isElement, i as isHTMLElement, l as isTopLayer, g as getNodeName, m as isOverflowElement, n as getNodeScroll, o as getWindow, e as getParentNode, d as isLastTraversableNode, p as isTableElement, q as isContainingBlock, r as getContainingBlock, f as getComputedStyle$1, h as getOverflowAncestors, s as getFrameElement, j as isWebKit } from './floating-ui.utils.dom-es.js';
3
3
  import * as React from 'react';
4
4
  import { useLayoutEffect } from 'react';
5
5
  import * as ReactDOM from 'react-dom';
@@ -1,6 +1,6 @@
1
1
  import * as React from 'react';
2
2
  import { useLayoutEffect } from 'react';
3
- import { i as isShadowRoot, a as isHTMLElement, b as isElement, c as isNode, g as getNodeName, d as isLastTraversableNode, e as getParentNode, f as getComputedStyle$1, h as getOverflowAncestors, j as isWebKit } from './floating-ui.utils.dom-es.js';
3
+ import { a as isShadowRoot, i as isHTMLElement, b as isElement, c as isNode, g as getNodeName, d as isLastTraversableNode, e as getParentNode, f as getComputedStyle$1, h as getOverflowAncestors, j as isWebKit } from './floating-ui.utils.dom-es.js';
4
4
  import { f as floor } from './floating-ui.utils-es.js';
5
5
  import { jsx, jsxs, Fragment } from 'react/jsx-runtime';
6
6
  import * as ReactDOM from 'react-dom';
@@ -162,4 +162,4 @@ function getFrameElement(win) {
162
162
  return win.parent && Object.getPrototypeOf(win.parent) ? win.frameElement : null;
163
163
  }
164
164
 
165
- export { isHTMLElement as a, isElement as b, isNode as c, isLastTraversableNode as d, getParentNode as e, getComputedStyle as f, getNodeName as g, getOverflowAncestors as h, isShadowRoot as i, isWebKit as j, getDocumentElement as k, isTopLayer as l, isOverflowElement as m, getNodeScroll as n, getWindow as o, isTableElement as p, isContainingBlock as q, getContainingBlock as r, getFrameElement as s };
165
+ export { isShadowRoot as a, isElement as b, isNode as c, isLastTraversableNode as d, getParentNode as e, getComputedStyle as f, getNodeName as g, getOverflowAncestors as h, isHTMLElement as i, isWebKit as j, getDocumentElement as k, isTopLayer as l, isOverflowElement as m, getNodeScroll as n, getWindow as o, isTableElement as p, isContainingBlock as q, getContainingBlock as r, getFrameElement as s };
package/dist/index.cjs CHANGED
@@ -73,6 +73,7 @@ var RadioGroup = require('./RadioGroup-cjs.js');
73
73
  var ResponsiveSwitcher = require('./ResponsiveSwitcher-cjs.js');
74
74
  var LegacySelect = require('./LegacySelect-cjs.js');
75
75
  var SegmentedControl = require('./SegmentedControl-cjs.js');
76
+ var Select = require('./Select-cjs.js');
76
77
  var SideDrawer = require('./SideDrawer-cjs.js');
77
78
  var SideKick = require('./SideKick-cjs.js');
78
79
  var Spinner = require('./Spinner-cjs.js');
@@ -190,6 +191,13 @@ require('./MenuSubmenuTrigger-cjs.js');
190
191
  require('./useCompositeListItem-cjs.js');
191
192
  require('./isElementDisabled-cjs.js');
192
193
  require('./AtlantisPortalContent-cjs.js');
194
+ require('./SelectPrimitive-cjs.js');
195
+ require('./SelectGroupLabel-cjs.js');
196
+ require('./useLabelableId-cjs.js');
197
+ require('./resolveAriaLabelledBy-cjs.js');
198
+ require('./HelperText-cjs.js');
199
+ require('./FieldDescription-cjs.js');
200
+ require('./useLabel-cjs.js');
193
201
  require('@jobber/formatters');
194
202
  require('react-dom/client');
195
203
 
@@ -324,6 +332,7 @@ exports.SegmentedControl = SegmentedControl.SegmentedControl;
324
332
  exports.SegmentedControlContext = SegmentedControl.SegmentedControlContext;
325
333
  exports.SegmentedControlProvider = SegmentedControl.SegmentedControlProvider;
326
334
  exports.useSegmentedControl = SegmentedControl.useSegmentedControl;
335
+ exports.Select = Select.Select;
327
336
  exports.SideDrawer = SideDrawer.SideDrawer;
328
337
  exports.SideKick = SideKick.SideKick;
329
338
  exports.Spinner = Spinner.Spinner;
package/dist/index.d.mts CHANGED
@@ -64,6 +64,7 @@ export * from "./RadioGroup";
64
64
  export * from "./ResponsiveSwitcher";
65
65
  export * from "./LegacySelect";
66
66
  export * from "./SegmentedControl";
67
+ export * from "./Select";
67
68
  export * from "./SideDrawer";
68
69
  export * from "./SideKick";
69
70
  export * from "./Spinner";
package/dist/index.d.ts CHANGED
@@ -64,6 +64,7 @@ export * from "./RadioGroup";
64
64
  export * from "./ResponsiveSwitcher";
65
65
  export * from "./LegacySelect";
66
66
  export * from "./SegmentedControl";
67
+ export * from "./Select";
67
68
  export * from "./SideDrawer";
68
69
  export * from "./SideKick";
69
70
  export * from "./Spinner";
package/dist/index.mjs CHANGED
@@ -71,6 +71,7 @@ export { R as RadioGroup, a as RadioOption } from './RadioGroup-es.js';
71
71
  export { R as ResponsiveSwitcher } from './ResponsiveSwitcher-es.js';
72
72
  export { L as LegacySelect, S as Option } from './LegacySelect-es.js';
73
73
  export { S as SegmentedControl, a as SegmentedControlContext, b as SegmentedControlProvider, u as useSegmentedControl } from './SegmentedControl-es.js';
74
+ export { S as Select } from './Select-es.js';
74
75
  export { S as SideDrawer } from './SideDrawer-es.js';
75
76
  export { S as SideKick } from './SideKick-es.js';
76
77
  export { S as Spinner } from './Spinner-es.js';
@@ -188,6 +189,13 @@ import './MenuSubmenuTrigger-es.js';
188
189
  import './useCompositeListItem-es.js';
189
190
  import './isElementDisabled-es.js';
190
191
  import './AtlantisPortalContent-es.js';
192
+ import './SelectPrimitive-es.js';
193
+ import './SelectGroupLabel-es.js';
194
+ import './useLabelableId-es.js';
195
+ import './resolveAriaLabelledBy-es.js';
196
+ import './HelperText-es.js';
197
+ import './FieldDescription-es.js';
198
+ import './useLabel-es.js';
191
199
  import '@jobber/formatters';
192
200
  import 'react-dom/client';
193
201
 
@@ -22,6 +22,7 @@ require('react/jsx-runtime');
22
22
  require('../../floating-ui.utils-cjs.js');
23
23
  require('../../floating-ui.react-dom-cjs.js');
24
24
  require('../../resolveAriaLabelledBy-cjs.js');
25
+ require('../../stringifyLocale-cjs.js');
25
26
  require('../../useLabel-cjs.js');
26
27
  require('../../Separator-cjs.js');
27
28
 
@@ -20,5 +20,6 @@ import 'react/jsx-runtime';
20
20
  import '../../floating-ui.utils-es.js';
21
21
  import '../../floating-ui.react-dom-es.js';
22
22
  import '../../resolveAriaLabelledBy-es.js';
23
+ import '../../stringifyLocale-es.js';
23
24
  import '../../useLabel-es.js';
24
25
  import '../../Separator-es.js';
@@ -1,9 +1,10 @@
1
1
  import React from "react";
2
+ import type { ReactNode } from "react";
2
3
  export interface HelperTextProps {
3
4
  /**
4
5
  * The helper message.
5
6
  */
6
- readonly message: string;
7
+ readonly message: ReactNode;
7
8
  /**
8
9
  * `neutral` renders subdued text. `critical` renders an `alert` icon
9
10
  * followed by error-coloured text.
@@ -11,13 +11,15 @@ require('../../Icon-cjs.js');
11
11
  require('@jobber/design');
12
12
  require('../../Typography-cjs.js');
13
13
  require('../../useRenderElement-cjs.js');
14
+ require('../../FieldDescription-cjs.js');
14
15
  require('../../useButton-cjs.js');
15
16
  require('../../floating-ui.utils.dom-cjs.js');
16
17
  require('react-dom');
17
18
  require('../../useLabelableId-cjs.js');
18
19
  require('react/jsx-runtime');
19
- require('../../NumberFieldInput-cjs.js');
20
20
  require('../../useLabel-cjs.js');
21
+ require('../../NumberFieldInput-cjs.js');
22
+ require('../../stringifyLocale-cjs.js');
21
23
  require('../../clamp-cjs.js');
22
24
 
23
25
 
@@ -9,11 +9,13 @@ import '../../Icon-es.js';
9
9
  import '@jobber/design';
10
10
  import '../../Typography-es.js';
11
11
  import '../../useRenderElement-es.js';
12
+ import '../../FieldDescription-es.js';
12
13
  import '../../useButton-es.js';
13
14
  import '../../floating-ui.utils.dom-es.js';
14
15
  import 'react-dom';
15
16
  import '../../useLabelableId-es.js';
16
17
  import 'react/jsx-runtime';
17
- import '../../NumberFieldInput-es.js';
18
18
  import '../../useLabel-es.js';
19
+ import '../../NumberFieldInput-es.js';
20
+ import '../../stringifyLocale-es.js';
19
21
  import '../../clamp-es.js';
@@ -1,6 +1,11 @@
1
1
  import React from "react";
2
+ import type { SelectPrimitiveFieldTriggerProps, SelectPrimitiveValueTextProps } from "./types";
2
3
  import { Select } from "../../unstyledPrimitives";
3
4
  import { OverlaySeparator } from "../OverlaySeparator";
5
+ declare function SelectPrimitiveFieldTrigger({ valueSlot, className, ...props }: SelectPrimitiveFieldTriggerProps): React.JSX.Element;
6
+ declare namespace SelectPrimitiveFieldTrigger {
7
+ var displayName: string;
8
+ }
4
9
  declare function SelectPrimitiveTrigger({ className, children, ...props }: React.ComponentPropsWithoutRef<typeof Select.Trigger>): React.JSX.Element;
5
10
  declare namespace SelectPrimitiveTrigger {
6
11
  var displayName: string;
@@ -9,6 +14,10 @@ declare function SelectPrimitiveValue({ className, ...props }: React.ComponentPr
9
14
  declare namespace SelectPrimitiveValue {
10
15
  var displayName: string;
11
16
  }
17
+ declare function SelectPrimitiveValueText({ className, ...props }: SelectPrimitiveValueTextProps): React.JSX.Element;
18
+ declare namespace SelectPrimitiveValueText {
19
+ var displayName: string;
20
+ }
12
21
  declare function SelectPrimitivePositioner({ className, sideOffset, alignItemWithTrigger, ...props }: React.ComponentPropsWithoutRef<typeof Select.Positioner>): React.JSX.Element;
13
22
  declare namespace SelectPrimitivePositioner {
14
23
  var displayName: string;
@@ -48,7 +57,9 @@ declare namespace SelectPrimitiveSeparator {
48
57
  export declare const SelectPrimitive: {
49
58
  Root: typeof Select.Root;
50
59
  Trigger: typeof SelectPrimitiveTrigger;
60
+ FieldTrigger: typeof SelectPrimitiveFieldTrigger;
51
61
  Value: typeof SelectPrimitiveValue;
62
+ ValueText: typeof SelectPrimitiveValueText;
52
63
  Portal: React.ForwardRefExoticComponent<Omit<import("@base-ui/react").SelectPortalProps, "ref"> & React.RefAttributes<HTMLDivElement>>;
53
64
  Positioner: typeof SelectPrimitivePositioner;
54
65
  Popup: typeof SelectPrimitivePopup;
@@ -1,2 +1,2 @@
1
1
  export { SelectPrimitive } from "./SelectPrimitive";
2
- export type { SelectPrimitiveRootProps, SelectPrimitiveTriggerProps, SelectPrimitiveValueProps, SelectPrimitivePortalProps, SelectPrimitivePositionerProps, SelectPrimitivePopupProps, SelectPrimitiveListProps, SelectPrimitiveItemProps, SelectPrimitiveItemTextProps, SelectPrimitiveItemIndicatorProps, SelectPrimitiveGroupProps, SelectPrimitiveGroupLabelProps, SelectPrimitiveSeparatorProps, } from "./types";
2
+ export type { SelectPrimitiveRootProps, SelectPrimitiveTriggerProps, SelectPrimitiveFieldTriggerProps, SelectPrimitiveValueProps, SelectPrimitiveValueTextProps, SelectPrimitivePortalProps, SelectPrimitivePositionerProps, SelectPrimitivePopupProps, SelectPrimitiveListProps, SelectPrimitiveItemProps, SelectPrimitiveItemTextProps, SelectPrimitiveItemIndicatorProps, SelectPrimitiveGroupProps, SelectPrimitiveGroupLabelProps, SelectPrimitiveSeparatorProps, } from "./types";