@frontify/fondue-components 26.0.2 → 27.0.0
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/fondue-components32.js +62 -60
- package/dist/fondue-components32.js.map +1 -1
- package/dist/fondue-components4.js +56 -48
- package/dist/fondue-components4.js.map +1 -1
- package/dist/fondue-components41.js +4 -2
- package/dist/fondue-components41.js.map +1 -1
- package/dist/fondue-components53.js +14 -12
- package/dist/fondue-components53.js.map +1 -1
- package/dist/fondue-components85.js +10 -10
- package/dist/fondue-components9.js +95 -83
- package/dist/fondue-components9.js.map +1 -1
- package/dist/fondue-components95.js +101 -95
- package/dist/fondue-components95.js.map +1 -1
- package/dist/fondue-components97.js +12 -15
- package/dist/fondue-components97.js.map +1 -1
- package/dist/index.d.ts +15 -3
- package/dist/style.css +1 -1
- package/package.json +3 -3
|
@@ -1,29 +1,29 @@
|
|
|
1
|
-
import { jsxs as
|
|
1
|
+
import { jsxs as g, jsx as n, Fragment as ue } from "react/jsx-runtime";
|
|
2
2
|
import { IconCaretDown as me } from "@frontify/fondue-icons";
|
|
3
3
|
import * as H from "@radix-ui/react-popover";
|
|
4
|
-
import { useMultipleSelection as
|
|
5
|
-
import { forwardRef as be, useRef as
|
|
4
|
+
import { useMultipleSelection as K, useCombobox as s } from "downshift";
|
|
5
|
+
import { forwardRef as be, useRef as he, useCallback as fe, useState as ge, useMemo as j } from "react";
|
|
6
6
|
import { LoadingCircle as pe } from "./fondue-components19.js";
|
|
7
7
|
import { useTranslation as Ce } from "./fondue-components39.js";
|
|
8
8
|
import { useBadgeItems as ye } from "./fondue-components100.js";
|
|
9
|
-
import { useFocusRing as
|
|
9
|
+
import { useFocusRing as Ie } from "./fondue-components101.js";
|
|
10
10
|
import { useSelectData as ve } from "./fondue-components102.js";
|
|
11
|
-
import { useSelectionDescription as
|
|
12
|
-
import
|
|
13
|
-
import { ClearButton as
|
|
11
|
+
import { useSelectionDescription as Be } from "./fondue-components103.js";
|
|
12
|
+
import c from "./fondue-components99.js";
|
|
13
|
+
import { ClearButton as xe } from "./fondue-components104.js";
|
|
14
14
|
import { CollapsibleBadges as Se } from "./fondue-components105.js";
|
|
15
|
-
import { SelectMenu as
|
|
15
|
+
import { SelectMenu as we } from "./fondue-components106.js";
|
|
16
16
|
import { ForwardedRefSelectSlot as De } from "./fondue-components76.js";
|
|
17
|
-
import { StatusIcons as
|
|
18
|
-
const
|
|
19
|
-
children:
|
|
17
|
+
import { StatusIcons as Re } from "./fondue-components107.js";
|
|
18
|
+
const z = ({
|
|
19
|
+
children: E,
|
|
20
20
|
selectedItemValues: i,
|
|
21
|
-
onItemSelect:
|
|
22
|
-
onClear:
|
|
23
|
-
placeholder:
|
|
21
|
+
onItemSelect: m,
|
|
22
|
+
onClear: $,
|
|
23
|
+
placeholder: x = "",
|
|
24
24
|
status: p = "neutral",
|
|
25
|
-
disabled:
|
|
26
|
-
"data-test-id":
|
|
25
|
+
disabled: b,
|
|
26
|
+
"data-test-id": d = "fondue-select-combobox",
|
|
27
27
|
alignMenu: _ = "start",
|
|
28
28
|
side: q = "bottom",
|
|
29
29
|
id: G,
|
|
@@ -31,97 +31,103 @@ const K = ({
|
|
|
31
31
|
getAsyncItems: C,
|
|
32
32
|
onEscapeKeyDown: Q,
|
|
33
33
|
multiple: o,
|
|
34
|
-
...
|
|
34
|
+
...a
|
|
35
35
|
}, U) => {
|
|
36
|
-
const
|
|
37
|
-
|
|
38
|
-
}, []), { t: X } = Ce(), { inputSlots: Y, menuSlots: Z, items: y, filterText: A, clearButton: S, getItemByValue:
|
|
36
|
+
const h = he(null), W = fe((e) => {
|
|
37
|
+
h.current = e;
|
|
38
|
+
}, []), { t: X } = Ce(), { inputSlots: Y, menuSlots: Z, items: y, filterText: A, clearButton: S, getItemByValue: r, setFilterText: I, asyncItemStatus: w } = ve(E, C), { wasClickedRef: V, onMouseDown: D, onFocus: R, onBlur: ee } = Ie(), { selectionDescriptionId: L, selectionDescription: O } = Be(
|
|
39
39
|
o,
|
|
40
40
|
i,
|
|
41
|
-
|
|
42
|
-
), te = ye(i,
|
|
41
|
+
r
|
|
42
|
+
), te = ye(i, r), [ae, k] = ge(!1), M = j(() => i.map((e) => r(e)).filter((e) => e !== void 0 && "value" in e && "label" in e), [i, r]), ne = K(
|
|
43
43
|
o ? {
|
|
44
|
-
selectedItems:
|
|
45
|
-
onStateChange({ selectedItems: e, type:
|
|
46
|
-
if (
|
|
47
|
-
const
|
|
48
|
-
|
|
44
|
+
selectedItems: M,
|
|
45
|
+
onStateChange({ selectedItems: e, type: l }) {
|
|
46
|
+
if (l === K.stateChangeTypes.SelectedItemKeyDownBackspace) {
|
|
47
|
+
const t = M.find((u) => !(e != null && e.includes(u)));
|
|
48
|
+
t && m(t.value);
|
|
49
49
|
}
|
|
50
50
|
}
|
|
51
51
|
} : { selectedItems: [] }
|
|
52
52
|
), oe = o ? ne.removeSelectedItem : () => {
|
|
53
53
|
}, {
|
|
54
|
-
getInputProps:
|
|
54
|
+
getInputProps: f,
|
|
55
55
|
getToggleButtonProps: ie,
|
|
56
|
-
getMenuProps:
|
|
57
|
-
getItemProps:
|
|
58
|
-
reset:
|
|
56
|
+
getMenuProps: le,
|
|
57
|
+
getItemProps: re,
|
|
58
|
+
reset: N,
|
|
59
59
|
selectedItem: v,
|
|
60
|
-
isOpen:
|
|
60
|
+
isOpen: T,
|
|
61
61
|
highlightedIndex: se,
|
|
62
|
-
inputValue:
|
|
63
|
-
} =
|
|
62
|
+
inputValue: B
|
|
63
|
+
} = s({
|
|
64
64
|
items: y,
|
|
65
|
-
selectedItem: o ? null :
|
|
65
|
+
selectedItem: o ? null : r(i[0]),
|
|
66
66
|
defaultHighlightedIndex: 0,
|
|
67
67
|
toggleButtonId: G,
|
|
68
68
|
// Only set labelId if aria-labelledby is explicitly provided, otherwise downshift generates an orphan ID
|
|
69
|
-
..."aria-labelledby" in
|
|
69
|
+
..."aria-labelledby" in a && a["aria-labelledby"] ? { labelId: a["aria-labelledby"] } : {},
|
|
70
70
|
onSelectedItemChange: ({ selectedItem: e }) => {
|
|
71
|
-
e &&
|
|
71
|
+
e && m(e.value), o && I("");
|
|
72
72
|
},
|
|
73
73
|
onInputValueChange: ({ inputValue: e }) => {
|
|
74
|
-
|
|
74
|
+
I(e);
|
|
75
75
|
},
|
|
76
76
|
onIsOpenChange: () => {
|
|
77
|
-
|
|
77
|
+
k(!1), I("");
|
|
78
78
|
},
|
|
79
79
|
onHighlightedIndexChange: () => {
|
|
80
|
-
|
|
80
|
+
k(!0);
|
|
81
81
|
},
|
|
82
82
|
itemToString: (e) => e ? e.label : "",
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
switch (
|
|
87
|
-
case
|
|
88
|
-
case
|
|
83
|
+
stateReducer: (e, l) => {
|
|
84
|
+
const { changes: t, type: u } = l;
|
|
85
|
+
if (o)
|
|
86
|
+
switch (u) {
|
|
87
|
+
case s.stateChangeTypes.InputKeyDownEnter:
|
|
88
|
+
case s.stateChangeTypes.ItemClick:
|
|
89
89
|
return {
|
|
90
|
-
...
|
|
90
|
+
...t,
|
|
91
91
|
isOpen: !0,
|
|
92
92
|
highlightedIndex: e.highlightedIndex,
|
|
93
93
|
inputValue: ""
|
|
94
94
|
};
|
|
95
|
-
case
|
|
95
|
+
case s.stateChangeTypes.InputBlur:
|
|
96
96
|
return {
|
|
97
|
-
...
|
|
97
|
+
...t,
|
|
98
98
|
inputValue: ""
|
|
99
99
|
};
|
|
100
100
|
}
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
|
|
101
|
+
else
|
|
102
|
+
switch (u) {
|
|
103
|
+
case s.stateChangeTypes.InputKeyDownEnter:
|
|
104
|
+
case s.stateChangeTypes.ItemClick:
|
|
105
|
+
t.selectedItem && e.selectedItem && t.selectedItem.value === e.selectedItem.value && m(t.selectedItem.value);
|
|
106
|
+
break;
|
|
107
|
+
}
|
|
108
|
+
return t;
|
|
109
|
+
}
|
|
110
|
+
}), F = j(() => o ? !1 : !C && !y.find((e) => e.label.toLowerCase().includes(B.toLowerCase())), [B, y, C, o]) || !!w.error || p === "error", ce = (e, l) => {
|
|
111
|
+
const t = r(e);
|
|
112
|
+
t && (oe(t), m(e), h.current && (h.current.focus(), l && (h.current.dataset.showFocusRing = "false")));
|
|
107
113
|
}, de = () => {
|
|
108
|
-
|
|
109
|
-
},
|
|
110
|
-
var
|
|
111
|
-
ee(e), o || ((v == null ? void 0 : v.label) ?? "").toLocaleLowerCase() !==
|
|
114
|
+
$(), N();
|
|
115
|
+
}, P = (e) => {
|
|
116
|
+
var l, t;
|
|
117
|
+
ee(e), o || ((v == null ? void 0 : v.label) ?? "").toLocaleLowerCase() !== B.toLocaleLowerCase() && N(), f().onBlur && ((t = (l = f()).onBlur) == null || t.call(l, e));
|
|
112
118
|
};
|
|
113
|
-
return /* @__PURE__ */
|
|
114
|
-
/* @__PURE__ */ n(H.Anchor, { asChild: !0, children: /* @__PURE__ */
|
|
119
|
+
return /* @__PURE__ */ g(H.Root, { open: T, children: [
|
|
120
|
+
/* @__PURE__ */ n(H.Anchor, { asChild: !0, children: /* @__PURE__ */ g(
|
|
115
121
|
"div",
|
|
116
122
|
{
|
|
117
123
|
ref: U,
|
|
118
|
-
className:
|
|
119
|
-
"data-status":
|
|
120
|
-
"data-disabled":
|
|
124
|
+
className: c.root,
|
|
125
|
+
"data-status": F ? "error" : p,
|
|
126
|
+
"data-disabled": b,
|
|
121
127
|
"data-empty": i.length === 0,
|
|
122
128
|
children: [
|
|
123
|
-
o ? /* @__PURE__ */
|
|
124
|
-
/* @__PURE__ */ n("span", { id: L, className:
|
|
129
|
+
o ? /* @__PURE__ */ g(ue, { children: [
|
|
130
|
+
/* @__PURE__ */ n("span", { id: L, className: c.srOnly, children: O }),
|
|
125
131
|
/* @__PURE__ */ n(
|
|
126
132
|
Se,
|
|
127
133
|
{
|
|
@@ -131,20 +137,20 @@ const K = ({
|
|
|
131
137
|
children: /* @__PURE__ */ n(
|
|
132
138
|
"input",
|
|
133
139
|
{
|
|
134
|
-
...
|
|
140
|
+
...f({
|
|
135
141
|
ref: W,
|
|
136
|
-
"aria-label": "aria-label" in
|
|
142
|
+
"aria-label": "aria-label" in a ? a["aria-label"] : void 0,
|
|
137
143
|
// Remove auto-generated aria-labelledby if not explicitly provided
|
|
138
|
-
"aria-labelledby": "aria-labelledby" in
|
|
144
|
+
"aria-labelledby": "aria-labelledby" in a && a["aria-labelledby"] ? a["aria-labelledby"] : void 0,
|
|
139
145
|
"aria-describedby": O ? L : void 0
|
|
140
146
|
}),
|
|
141
|
-
"data-test-id":
|
|
142
|
-
placeholder: i.length === 0 ?
|
|
143
|
-
className:
|
|
144
|
-
disabled:
|
|
147
|
+
"data-test-id": d,
|
|
148
|
+
placeholder: i.length === 0 ? x : "",
|
|
149
|
+
className: c.multiSelectInput,
|
|
150
|
+
disabled: b,
|
|
145
151
|
onMouseDown: D,
|
|
146
|
-
onFocus:
|
|
147
|
-
onBlur:
|
|
152
|
+
onFocus: R,
|
|
153
|
+
onBlur: P
|
|
148
154
|
}
|
|
149
155
|
)
|
|
150
156
|
}
|
|
@@ -152,51 +158,51 @@ const K = ({
|
|
|
152
158
|
] }) : /* @__PURE__ */ n(
|
|
153
159
|
"input",
|
|
154
160
|
{
|
|
155
|
-
...
|
|
156
|
-
"aria-label": "aria-label" in
|
|
161
|
+
...f({
|
|
162
|
+
"aria-label": "aria-label" in a ? a["aria-label"] : void 0,
|
|
157
163
|
// Remove auto-generated aria-labelledby if not explicitly provided
|
|
158
|
-
"aria-labelledby": "aria-labelledby" in
|
|
164
|
+
"aria-labelledby": "aria-labelledby" in a && a["aria-labelledby"] ? a["aria-labelledby"] : void 0
|
|
159
165
|
}),
|
|
160
|
-
"data-test-id":
|
|
161
|
-
placeholder:
|
|
162
|
-
className:
|
|
163
|
-
disabled:
|
|
166
|
+
"data-test-id": d,
|
|
167
|
+
placeholder: x,
|
|
168
|
+
className: c.input,
|
|
169
|
+
disabled: b,
|
|
164
170
|
onMouseDown: D,
|
|
165
|
-
onFocus:
|
|
166
|
-
onBlur:
|
|
171
|
+
onFocus: R,
|
|
172
|
+
onBlur: P
|
|
167
173
|
}
|
|
168
174
|
),
|
|
169
175
|
Y,
|
|
170
|
-
S ? /* @__PURE__ */ n(
|
|
171
|
-
|
|
172
|
-
/* @__PURE__ */
|
|
176
|
+
S ? /* @__PURE__ */ n(xe, { onClear: de, children: S }) : null,
|
|
177
|
+
w.isLoading && T ? /* @__PURE__ */ n(De, { name: "right", "data-test-id": `${d}-right-slot`, children: /* @__PURE__ */ n(pe, { size: "x-small", "data-test-id": `${d}-loading-circle` }) }) : null,
|
|
178
|
+
/* @__PURE__ */ g("div", { className: c.icons, children: [
|
|
173
179
|
/* @__PURE__ */ n(
|
|
174
180
|
"button",
|
|
175
181
|
{
|
|
176
182
|
"aria-label": X("Select_toggleMenu"),
|
|
177
183
|
...ie(),
|
|
178
184
|
type: "button",
|
|
179
|
-
disabled:
|
|
185
|
+
disabled: b,
|
|
180
186
|
onMouseDown: () => {
|
|
181
187
|
V.current = !0;
|
|
182
188
|
},
|
|
183
|
-
children: /* @__PURE__ */ n(me, { size: 16, className:
|
|
189
|
+
children: /* @__PURE__ */ n(me, { size: 16, className: c.caret })
|
|
184
190
|
}
|
|
185
191
|
),
|
|
186
|
-
/* @__PURE__ */ n(
|
|
192
|
+
/* @__PURE__ */ n(Re, { status: p, hasError: F, dataTestId: d })
|
|
187
193
|
] })
|
|
188
194
|
]
|
|
189
195
|
}
|
|
190
196
|
) }),
|
|
191
197
|
/* @__PURE__ */ n(
|
|
192
|
-
|
|
198
|
+
we,
|
|
193
199
|
{
|
|
194
200
|
align: _,
|
|
195
201
|
side: q,
|
|
196
202
|
highlightedIndex: se,
|
|
197
203
|
filterText: A,
|
|
198
|
-
getMenuProps:
|
|
199
|
-
getItemProps:
|
|
204
|
+
getMenuProps: le,
|
|
205
|
+
getItemProps: re,
|
|
200
206
|
selectedItemValues: i,
|
|
201
207
|
hasInteractedSinceOpening: ae,
|
|
202
208
|
viewportCollisionPadding: J,
|
|
@@ -206,8 +212,8 @@ const K = ({
|
|
|
206
212
|
)
|
|
207
213
|
] });
|
|
208
214
|
};
|
|
209
|
-
|
|
210
|
-
const Qe = be(
|
|
215
|
+
z.displayName = "Select.Combobox";
|
|
216
|
+
const Qe = be(z);
|
|
211
217
|
export {
|
|
212
218
|
Qe as ComboboxBase
|
|
213
219
|
};
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"fondue-components95.js","sources":["../src/components/Select/components/ComboboxBase.tsx"],"sourcesContent":["/* (c) Copyright Frontify Ltd., all rights reserved. */\n\nimport { IconCaretDown } from '@frontify/fondue-icons';\nimport * as RadixPopover from '@radix-ui/react-popover';\nimport { useCombobox, useMultipleSelection } from 'downshift';\nimport {\n forwardRef,\n useCallback,\n useMemo,\n useRef,\n useState,\n type FocusEvent,\n type ForwardedRef,\n type ReactNode,\n} from 'react';\n\nimport { LoadingCircle } from '#/components/LoadingCircle/LoadingCircle.tsx';\nimport { type CommonAriaProps } from '#/helpers/aria';\nimport { useTranslation } from '#/hooks/useTranslation';\n\nimport { useBadgeItems } from '../hooks/useBadgeItems';\nimport { useFocusRing } from '../hooks/useFocusRing';\nimport { useSelectData, type AsyncItemsFetcher } from '../hooks/useSelectData';\nimport { useSelectionDescription } from '../hooks/useSelectionDescription';\nimport styles from '../styles/select.module.scss';\n\nimport { ClearButton } from './ClearButton';\nimport { CollapsibleBadges } from './CollapsibleBadges';\nimport { SelectMenu, type SelectMenuViewportCollisionPadding } from './SelectMenu';\nimport { ForwardedRefSelectSlot } from './SelectSlot';\nimport { StatusIcons } from './StatusIcons';\n\ntype SelectItem = {\n value: string;\n label: string;\n children?: ReactNode;\n};\n\nexport type ComboboxSharedProps = {\n /**\n * Children of the Combobox component. This can contain the `Select.Slot` components for the label, decorators, clear action and menu\n */\n children?: ReactNode;\n /**\n * The placeholder in the combobox component\n */\n placeholder?: string;\n /**\n * Status of the text input\n * @default \"neutral\"\n */\n status?: 'neutral' | 'success' | 'error';\n /**\n * Disables the combobox component\n */\n disabled?: boolean;\n /**\n * The alignment of the menu\n * @default \"start\"\n */\n alignMenu?: 'start' | 'center' | 'end';\n /**\n * Defines the preferred side of the combobox. It will not be respected if there are collisions with the viewport\n * @default \"bottom\"\n */\n side?: 'left' | 'right' | 'bottom' | 'top';\n /**\n * Id of the combobox component\n */\n id?: string;\n /**\n * The data test id of the combobox component\n */\n 'data-test-id'?: string;\n /**\n * Define the minimum distance between the select menu and the viewport edge\n * @default 'compact'\n */\n viewportCollisionPadding?: SelectMenuViewportCollisionPadding;\n /**\n * Function to fetch items asynchronously\n */\n getAsyncItems?: AsyncItemsFetcher;\n /**\n * Event handler called when the escape key is pressed\n */\n onEscapeKeyDown?: (event: KeyboardEvent) => void;\n} & CommonAriaProps;\n\ntype ComboboxBaseProps = ComboboxSharedProps & {\n /**\n * The currently selected item values\n */\n selectedItemValues: string[];\n /**\n * Callback fired when an item is selected or deselected\n */\n onItemSelect: (value?: string) => void;\n /**\n * Callback fired when the selection is cleared\n */\n onClear: () => void;\n /**\n * Whether the combobox allows multiple selections\n */\n multiple: boolean;\n};\n\nconst ComboboxBaseInput = (\n {\n children,\n selectedItemValues,\n onItemSelect,\n onClear,\n placeholder = '',\n status = 'neutral',\n disabled,\n 'data-test-id': dataTestId = 'fondue-select-combobox',\n alignMenu = 'start',\n side = 'bottom',\n id,\n viewportCollisionPadding = 'compact',\n getAsyncItems,\n onEscapeKeyDown,\n multiple,\n ...props\n }: ComboboxBaseProps,\n forwardedRef: ForwardedRef<HTMLDivElement>,\n): ReactNode => {\n const inputRef = useRef<HTMLInputElement | null>(null);\n const inputCallbackRef = useCallback((node: HTMLInputElement | null): void => {\n inputRef.current = node;\n }, []);\n const { t } = useTranslation();\n const { inputSlots, menuSlots, items, filterText, clearButton, getItemByValue, setFilterText, asyncItemStatus } =\n useSelectData(children, getAsyncItems);\n const { wasClickedRef, onMouseDown, onFocus, onBlur } = useFocusRing();\n const { selectionDescriptionId, selectionDescription } = useSelectionDescription(\n multiple,\n selectedItemValues,\n getItemByValue,\n );\n const badgeItems = useBadgeItems(selectedItemValues, getItemByValue);\n\n const [hasInteractedSinceOpening, setHasInteractedSinceOpening] = useState(false);\n\n const selectedItems = useMemo((): SelectItem[] => {\n return selectedItemValues\n .map((value) => getItemByValue(value))\n .filter((item): item is SelectItem => item !== undefined && 'value' in item && 'label' in item);\n }, [selectedItemValues, getItemByValue]);\n\n const multipleSelectionResult = useMultipleSelection<SelectItem>(\n multiple\n ? {\n selectedItems,\n onStateChange({ selectedItems: newSelectedItems, type }) {\n if (type === useMultipleSelection.stateChangeTypes.SelectedItemKeyDownBackspace) {\n const removedItem = selectedItems.find((item) => !newSelectedItems?.includes(item));\n if (removedItem) {\n onItemSelect(removedItem.value);\n }\n }\n },\n }\n : { selectedItems: [] },\n );\n const removeSelectedItem = multiple ? multipleSelectionResult.removeSelectedItem : (): void => {};\n\n const {\n getInputProps,\n getToggleButtonProps,\n getMenuProps,\n getItemProps,\n reset,\n selectedItem,\n isOpen,\n highlightedIndex,\n inputValue,\n } = useCombobox<SelectItem>({\n items,\n selectedItem: multiple ? null : (getItemByValue(selectedItemValues[0]) as SelectItem | null | undefined),\n defaultHighlightedIndex: 0,\n toggleButtonId: id,\n // Only set labelId if aria-labelledby is explicitly provided, otherwise downshift generates an orphan ID\n ...('aria-labelledby' in props && props['aria-labelledby'] ? { labelId: props['aria-labelledby'] } : {}),\n onSelectedItemChange: ({ selectedItem }) => {\n if (selectedItem) {\n onItemSelect(selectedItem.value);\n }\n if (multiple) {\n setFilterText('');\n }\n },\n onInputValueChange: ({ inputValue }) => {\n setFilterText(inputValue);\n },\n onIsOpenChange: () => {\n setHasInteractedSinceOpening(false);\n setFilterText('');\n },\n onHighlightedIndexChange: () => {\n setHasInteractedSinceOpening(true);\n },\n itemToString: (item) => (item ? item.label : ''),\n ...(multiple\n ? {\n stateReducer: (state, actionAndChanges) => {\n const { changes, type } = actionAndChanges;\n switch (type) {\n case useCombobox.stateChangeTypes.InputKeyDownEnter:\n case useCombobox.stateChangeTypes.ItemClick:\n return {\n ...changes,\n isOpen: true,\n highlightedIndex: state.highlightedIndex,\n inputValue: '',\n };\n case useCombobox.stateChangeTypes.InputBlur:\n // Select item on blur (Tab key) but clear the input\n return {\n ...changes,\n inputValue: '',\n };\n }\n return changes;\n },\n }\n : {}),\n });\n\n const valueInvalid = useMemo(() => {\n if (multiple) {\n return false;\n }\n return !getAsyncItems && !items.find((item) => item.label.toLowerCase().includes(inputValue.toLowerCase()));\n }, [inputValue, items, getAsyncItems, multiple]);\n\n const hasError = valueInvalid || !!asyncItemStatus.error || status === 'error';\n\n const handleDismissBadge = (value: string, preventFocusRing: boolean): void => {\n const item = getItemByValue(value) as SelectItem | undefined;\n if (item) {\n removeSelectedItem(item);\n onItemSelect(value);\n if (inputRef.current) {\n inputRef.current.focus();\n if (preventFocusRing) {\n inputRef.current.dataset.showFocusRing = 'false';\n }\n }\n }\n };\n\n const handleClear = (): void => {\n onClear();\n reset();\n };\n\n const handleBlur = (blurEvent: FocusEvent<HTMLInputElement, Element>): void => {\n onBlur(blurEvent);\n\n if (!multiple) {\n const selectedItemLabel = selectedItem?.label ?? '';\n const isOutdated = selectedItemLabel.toLocaleLowerCase() !== inputValue.toLocaleLowerCase();\n\n if (isOutdated) {\n reset();\n }\n }\n\n if (getInputProps().onBlur) {\n getInputProps().onBlur?.(blurEvent);\n }\n };\n\n return (\n <RadixPopover.Root open={isOpen}>\n <RadixPopover.Anchor asChild>\n <div\n ref={forwardedRef}\n className={styles.root}\n data-status={hasError ? 'error' : status}\n data-disabled={disabled}\n data-empty={selectedItemValues.length === 0}\n >\n {multiple ? (\n <>\n {/* Hidden description for screen readers - announced on focus */}\n <span id={selectionDescriptionId} className={styles.srOnly}>\n {selectionDescription}\n </span>\n <CollapsibleBadges\n items={badgeItems}\n onDismiss={handleDismissBadge}\n selectedCount={selectedItemValues.length}\n >\n <input\n // eslint-disable-next-line react-hooks/refs\n {...getInputProps({\n ref: inputCallbackRef,\n 'aria-label': 'aria-label' in props ? props['aria-label'] : undefined,\n // Remove auto-generated aria-labelledby if not explicitly provided\n 'aria-labelledby':\n 'aria-labelledby' in props && props['aria-labelledby']\n ? props['aria-labelledby']\n : undefined,\n 'aria-describedby': selectionDescription ? selectionDescriptionId : undefined,\n })}\n data-test-id={dataTestId}\n placeholder={selectedItemValues.length === 0 ? placeholder : ''}\n className={styles.multiSelectInput}\n disabled={disabled}\n onMouseDown={onMouseDown}\n onFocus={onFocus}\n onBlur={handleBlur}\n />\n </CollapsibleBadges>\n </>\n ) : (\n <input\n {...getInputProps({\n 'aria-label': 'aria-label' in props ? props['aria-label'] : undefined,\n // Remove auto-generated aria-labelledby if not explicitly provided\n 'aria-labelledby':\n 'aria-labelledby' in props && props['aria-labelledby']\n ? props['aria-labelledby']\n : undefined,\n })}\n data-test-id={dataTestId}\n placeholder={placeholder}\n className={styles.input}\n disabled={disabled}\n onMouseDown={onMouseDown}\n onFocus={onFocus}\n onBlur={handleBlur}\n />\n )}\n {inputSlots}\n {clearButton ? <ClearButton onClear={handleClear}>{clearButton}</ClearButton> : null}\n {asyncItemStatus.isLoading && isOpen ? (\n <ForwardedRefSelectSlot name=\"right\" data-test-id={`${dataTestId}-right-slot`}>\n <LoadingCircle size=\"x-small\" data-test-id={`${dataTestId}-loading-circle`} />\n </ForwardedRefSelectSlot>\n ) : null}\n <div className={styles.icons}>\n <button\n aria-label={t('Select_toggleMenu')}\n {...getToggleButtonProps()}\n type=\"button\"\n disabled={disabled}\n onMouseDown={() => {\n wasClickedRef.current = true;\n }}\n >\n <IconCaretDown size={16} className={styles.caret} />\n </button>\n <StatusIcons status={status} hasError={hasError} dataTestId={dataTestId} />\n </div>\n </div>\n </RadixPopover.Anchor>\n\n <SelectMenu\n align={alignMenu}\n side={side}\n highlightedIndex={highlightedIndex}\n filterText={filterText}\n getMenuProps={getMenuProps}\n getItemProps={getItemProps}\n selectedItemValues={selectedItemValues}\n hasInteractedSinceOpening={hasInteractedSinceOpening}\n viewportCollisionPadding={viewportCollisionPadding}\n onEscapeKeyDown={onEscapeKeyDown}\n >\n {menuSlots}\n </SelectMenu>\n </RadixPopover.Root>\n );\n};\nComboboxBaseInput.displayName = 'Select.Combobox';\n\nexport const ComboboxBase = forwardRef<HTMLDivElement, ComboboxBaseProps>(ComboboxBaseInput);\n"],"names":["ComboboxBaseInput","children","selectedItemValues","onItemSelect","onClear","placeholder","status","disabled","dataTestId","alignMenu","side","id","viewportCollisionPadding","getAsyncItems","onEscapeKeyDown","multiple","props","forwardedRef","inputRef","useRef","inputCallbackRef","useCallback","node","t","useTranslation","inputSlots","menuSlots","items","filterText","clearButton","getItemByValue","setFilterText","asyncItemStatus","useSelectData","wasClickedRef","onMouseDown","onFocus","onBlur","useFocusRing","selectionDescriptionId","selectionDescription","useSelectionDescription","badgeItems","useBadgeItems","hasInteractedSinceOpening","setHasInteractedSinceOpening","useState","selectedItems","useMemo","value","item","multipleSelectionResult","useMultipleSelection","newSelectedItems","type","removedItem","removeSelectedItem","getInputProps","getToggleButtonProps","getMenuProps","getItemProps","reset","selectedItem","isOpen","highlightedIndex","inputValue","useCombobox","state","actionAndChanges","changes","hasError","handleDismissBadge","preventFocusRing","handleClear","handleBlur","blurEvent","_b","_a","jsxs","RadixPopover","jsx","styles","Fragment","CollapsibleBadges","ClearButton","ForwardedRefSelectSlot","LoadingCircle","IconCaretDown","StatusIcons","SelectMenu","ComboboxBase","forwardRef"],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"fondue-components95.js","sources":["../src/components/Select/components/ComboboxBase.tsx"],"sourcesContent":["/* (c) Copyright Frontify Ltd., all rights reserved. */\n\nimport { IconCaretDown } from '@frontify/fondue-icons';\nimport * as RadixPopover from '@radix-ui/react-popover';\nimport { useCombobox, useMultipleSelection } from 'downshift';\nimport {\n forwardRef,\n useCallback,\n useMemo,\n useRef,\n useState,\n type FocusEvent,\n type ForwardedRef,\n type ReactNode,\n} from 'react';\n\nimport { LoadingCircle } from '#/components/LoadingCircle/LoadingCircle.tsx';\nimport { type CommonAriaProps } from '#/helpers/aria';\nimport { useTranslation } from '#/hooks/useTranslation';\n\nimport { useBadgeItems } from '../hooks/useBadgeItems';\nimport { useFocusRing } from '../hooks/useFocusRing';\nimport { useSelectData, type AsyncItemsFetcher } from '../hooks/useSelectData';\nimport { useSelectionDescription } from '../hooks/useSelectionDescription';\nimport styles from '../styles/select.module.scss';\n\nimport { ClearButton } from './ClearButton';\nimport { CollapsibleBadges } from './CollapsibleBadges';\nimport { SelectMenu, type SelectMenuViewportCollisionPadding } from './SelectMenu';\nimport { ForwardedRefSelectSlot } from './SelectSlot';\nimport { StatusIcons } from './StatusIcons';\n\ntype SelectItem = {\n value: string;\n label: string;\n children?: ReactNode;\n};\n\nexport type ComboboxSharedProps = {\n /**\n * Children of the Combobox component. This can contain the `Select.Slot` components for the label, decorators, clear action and menu\n */\n children?: ReactNode;\n /**\n * The placeholder in the combobox component\n */\n placeholder?: string;\n /**\n * Status of the text input\n * @default \"neutral\"\n */\n status?: 'neutral' | 'success' | 'error';\n /**\n * Disables the combobox component\n */\n disabled?: boolean;\n /**\n * The alignment of the menu\n * @default \"start\"\n */\n alignMenu?: 'start' | 'center' | 'end';\n /**\n * Defines the preferred side of the combobox. It will not be respected if there are collisions with the viewport\n * @default \"bottom\"\n */\n side?: 'left' | 'right' | 'bottom' | 'top';\n /**\n * Id of the combobox component\n */\n id?: string;\n /**\n * The data test id of the combobox component\n */\n 'data-test-id'?: string;\n /**\n * Define the minimum distance between the select menu and the viewport edge\n * @default 'compact'\n */\n viewportCollisionPadding?: SelectMenuViewportCollisionPadding;\n /**\n * Function to fetch items asynchronously\n */\n getAsyncItems?: AsyncItemsFetcher;\n /**\n * Event handler called when the escape key is pressed\n */\n onEscapeKeyDown?: (event: KeyboardEvent) => void;\n} & CommonAriaProps;\n\ntype ComboboxBaseProps = ComboboxSharedProps & {\n /**\n * The currently selected item values\n */\n selectedItemValues: string[];\n /**\n * Callback fired when an item is selected or deselected\n */\n onItemSelect: (value?: string) => void;\n /**\n * Callback fired when the selection is cleared\n */\n onClear: () => void;\n /**\n * Whether the combobox allows multiple selections\n */\n multiple: boolean;\n};\n\nconst ComboboxBaseInput = (\n {\n children,\n selectedItemValues,\n onItemSelect,\n onClear,\n placeholder = '',\n status = 'neutral',\n disabled,\n 'data-test-id': dataTestId = 'fondue-select-combobox',\n alignMenu = 'start',\n side = 'bottom',\n id,\n viewportCollisionPadding = 'compact',\n getAsyncItems,\n onEscapeKeyDown,\n multiple,\n ...props\n }: ComboboxBaseProps,\n forwardedRef: ForwardedRef<HTMLDivElement>,\n): ReactNode => {\n const inputRef = useRef<HTMLInputElement | null>(null);\n const inputCallbackRef = useCallback((node: HTMLInputElement | null): void => {\n inputRef.current = node;\n }, []);\n const { t } = useTranslation();\n const { inputSlots, menuSlots, items, filterText, clearButton, getItemByValue, setFilterText, asyncItemStatus } =\n useSelectData(children, getAsyncItems);\n const { wasClickedRef, onMouseDown, onFocus, onBlur } = useFocusRing();\n const { selectionDescriptionId, selectionDescription } = useSelectionDescription(\n multiple,\n selectedItemValues,\n getItemByValue,\n );\n const badgeItems = useBadgeItems(selectedItemValues, getItemByValue);\n\n const [hasInteractedSinceOpening, setHasInteractedSinceOpening] = useState(false);\n\n const selectedItems = useMemo((): SelectItem[] => {\n return selectedItemValues\n .map((value) => getItemByValue(value))\n .filter((item): item is SelectItem => item !== undefined && 'value' in item && 'label' in item);\n }, [selectedItemValues, getItemByValue]);\n\n const multipleSelectionResult = useMultipleSelection<SelectItem>(\n multiple\n ? {\n selectedItems,\n onStateChange({ selectedItems: newSelectedItems, type }) {\n if (type === useMultipleSelection.stateChangeTypes.SelectedItemKeyDownBackspace) {\n const removedItem = selectedItems.find((item) => !newSelectedItems?.includes(item));\n if (removedItem) {\n onItemSelect(removedItem.value);\n }\n }\n },\n }\n : { selectedItems: [] },\n );\n const removeSelectedItem = multiple ? multipleSelectionResult.removeSelectedItem : (): void => {};\n\n const {\n getInputProps,\n getToggleButtonProps,\n getMenuProps,\n getItemProps,\n reset,\n selectedItem,\n isOpen,\n highlightedIndex,\n inputValue,\n } = useCombobox<SelectItem>({\n items,\n selectedItem: multiple ? null : (getItemByValue(selectedItemValues[0]) as SelectItem | null | undefined),\n defaultHighlightedIndex: 0,\n toggleButtonId: id,\n // Only set labelId if aria-labelledby is explicitly provided, otherwise downshift generates an orphan ID\n ...('aria-labelledby' in props && props['aria-labelledby'] ? { labelId: props['aria-labelledby'] } : {}),\n onSelectedItemChange: ({ selectedItem }) => {\n if (selectedItem) {\n onItemSelect(selectedItem.value);\n }\n if (multiple) {\n setFilterText('');\n }\n },\n onInputValueChange: ({ inputValue }) => {\n setFilterText(inputValue);\n },\n onIsOpenChange: () => {\n setHasInteractedSinceOpening(false);\n setFilterText('');\n },\n onHighlightedIndexChange: () => {\n setHasInteractedSinceOpening(true);\n },\n itemToString: (item) => (item ? item.label : ''),\n stateReducer: (state, actionAndChanges) => {\n const { changes, type } = actionAndChanges;\n if (multiple) {\n switch (type) {\n case useCombobox.stateChangeTypes.InputKeyDownEnter:\n case useCombobox.stateChangeTypes.ItemClick:\n return {\n ...changes,\n isOpen: true,\n highlightedIndex: state.highlightedIndex,\n inputValue: '',\n };\n case useCombobox.stateChangeTypes.InputBlur:\n // Select item on blur (Tab key) but clear the input\n return {\n ...changes,\n inputValue: '',\n };\n }\n } else {\n // For single select, handle re-selection of the same item\n // onSelectedItemChange doesn't fire when selecting the same item, so we call onItemSelect here\n switch (type) {\n case useCombobox.stateChangeTypes.InputKeyDownEnter:\n case useCombobox.stateChangeTypes.ItemClick:\n if (\n changes.selectedItem &&\n state.selectedItem &&\n changes.selectedItem.value === state.selectedItem.value\n ) {\n onItemSelect(changes.selectedItem.value);\n }\n break;\n }\n }\n return changes;\n },\n });\n\n const valueInvalid = useMemo(() => {\n if (multiple) {\n return false;\n }\n return !getAsyncItems && !items.find((item) => item.label.toLowerCase().includes(inputValue.toLowerCase()));\n }, [inputValue, items, getAsyncItems, multiple]);\n\n const hasError = valueInvalid || !!asyncItemStatus.error || status === 'error';\n\n const handleDismissBadge = (value: string, preventFocusRing: boolean): void => {\n const item = getItemByValue(value) as SelectItem | undefined;\n if (item) {\n removeSelectedItem(item);\n onItemSelect(value);\n if (inputRef.current) {\n inputRef.current.focus();\n if (preventFocusRing) {\n inputRef.current.dataset.showFocusRing = 'false';\n }\n }\n }\n };\n\n const handleClear = (): void => {\n onClear();\n reset();\n };\n\n const handleBlur = (blurEvent: FocusEvent<HTMLInputElement, Element>): void => {\n onBlur(blurEvent);\n\n if (!multiple) {\n const selectedItemLabel = selectedItem?.label ?? '';\n const isOutdated = selectedItemLabel.toLocaleLowerCase() !== inputValue.toLocaleLowerCase();\n\n if (isOutdated) {\n reset();\n }\n }\n\n if (getInputProps().onBlur) {\n getInputProps().onBlur?.(blurEvent);\n }\n };\n\n return (\n <RadixPopover.Root open={isOpen}>\n <RadixPopover.Anchor asChild>\n <div\n ref={forwardedRef}\n className={styles.root}\n data-status={hasError ? 'error' : status}\n data-disabled={disabled}\n data-empty={selectedItemValues.length === 0}\n >\n {multiple ? (\n <>\n {/* Hidden description for screen readers - announced on focus */}\n <span id={selectionDescriptionId} className={styles.srOnly}>\n {selectionDescription}\n </span>\n <CollapsibleBadges\n items={badgeItems}\n onDismiss={handleDismissBadge}\n selectedCount={selectedItemValues.length}\n >\n <input\n // eslint-disable-next-line react-hooks/refs\n {...getInputProps({\n ref: inputCallbackRef,\n 'aria-label': 'aria-label' in props ? props['aria-label'] : undefined,\n // Remove auto-generated aria-labelledby if not explicitly provided\n 'aria-labelledby':\n 'aria-labelledby' in props && props['aria-labelledby']\n ? props['aria-labelledby']\n : undefined,\n 'aria-describedby': selectionDescription ? selectionDescriptionId : undefined,\n })}\n data-test-id={dataTestId}\n placeholder={selectedItemValues.length === 0 ? placeholder : ''}\n className={styles.multiSelectInput}\n disabled={disabled}\n onMouseDown={onMouseDown}\n onFocus={onFocus}\n onBlur={handleBlur}\n />\n </CollapsibleBadges>\n </>\n ) : (\n <input\n {...getInputProps({\n 'aria-label': 'aria-label' in props ? props['aria-label'] : undefined,\n // Remove auto-generated aria-labelledby if not explicitly provided\n 'aria-labelledby':\n 'aria-labelledby' in props && props['aria-labelledby']\n ? props['aria-labelledby']\n : undefined,\n })}\n data-test-id={dataTestId}\n placeholder={placeholder}\n className={styles.input}\n disabled={disabled}\n onMouseDown={onMouseDown}\n onFocus={onFocus}\n onBlur={handleBlur}\n />\n )}\n {inputSlots}\n {clearButton ? <ClearButton onClear={handleClear}>{clearButton}</ClearButton> : null}\n {asyncItemStatus.isLoading && isOpen ? (\n <ForwardedRefSelectSlot name=\"right\" data-test-id={`${dataTestId}-right-slot`}>\n <LoadingCircle size=\"x-small\" data-test-id={`${dataTestId}-loading-circle`} />\n </ForwardedRefSelectSlot>\n ) : null}\n <div className={styles.icons}>\n <button\n aria-label={t('Select_toggleMenu')}\n {...getToggleButtonProps()}\n type=\"button\"\n disabled={disabled}\n onMouseDown={() => {\n wasClickedRef.current = true;\n }}\n >\n <IconCaretDown size={16} className={styles.caret} />\n </button>\n <StatusIcons status={status} hasError={hasError} dataTestId={dataTestId} />\n </div>\n </div>\n </RadixPopover.Anchor>\n\n <SelectMenu\n align={alignMenu}\n side={side}\n highlightedIndex={highlightedIndex}\n filterText={filterText}\n getMenuProps={getMenuProps}\n getItemProps={getItemProps}\n selectedItemValues={selectedItemValues}\n hasInteractedSinceOpening={hasInteractedSinceOpening}\n viewportCollisionPadding={viewportCollisionPadding}\n onEscapeKeyDown={onEscapeKeyDown}\n >\n {menuSlots}\n </SelectMenu>\n </RadixPopover.Root>\n );\n};\nComboboxBaseInput.displayName = 'Select.Combobox';\n\nexport const ComboboxBase = forwardRef<HTMLDivElement, ComboboxBaseProps>(ComboboxBaseInput);\n"],"names":["ComboboxBaseInput","children","selectedItemValues","onItemSelect","onClear","placeholder","status","disabled","dataTestId","alignMenu","side","id","viewportCollisionPadding","getAsyncItems","onEscapeKeyDown","multiple","props","forwardedRef","inputRef","useRef","inputCallbackRef","useCallback","node","t","useTranslation","inputSlots","menuSlots","items","filterText","clearButton","getItemByValue","setFilterText","asyncItemStatus","useSelectData","wasClickedRef","onMouseDown","onFocus","onBlur","useFocusRing","selectionDescriptionId","selectionDescription","useSelectionDescription","badgeItems","useBadgeItems","hasInteractedSinceOpening","setHasInteractedSinceOpening","useState","selectedItems","useMemo","value","item","multipleSelectionResult","useMultipleSelection","newSelectedItems","type","removedItem","removeSelectedItem","getInputProps","getToggleButtonProps","getMenuProps","getItemProps","reset","selectedItem","isOpen","highlightedIndex","inputValue","useCombobox","state","actionAndChanges","changes","hasError","handleDismissBadge","preventFocusRing","handleClear","handleBlur","blurEvent","_b","_a","jsxs","RadixPopover","jsx","styles","Fragment","CollapsibleBadges","ClearButton","ForwardedRefSelectSlot","LoadingCircle","IconCaretDown","StatusIcons","SelectMenu","ComboboxBase","forwardRef"],"mappings":";;;;;;;;;;;;;;;;;AA4GA,MAAMA,IAAoB,CACtB;AAAA,EACI,UAAAC;AAAA,EACA,oBAAAC;AAAA,EACA,cAAAC;AAAA,EACA,SAAAC;AAAA,EACA,aAAAC,IAAc;AAAA,EACd,QAAAC,IAAS;AAAA,EACT,UAAAC;AAAA,EACA,gBAAgBC,IAAa;AAAA,EAC7B,WAAAC,IAAY;AAAA,EACZ,MAAAC,IAAO;AAAA,EACP,IAAAC;AAAA,EACA,0BAAAC,IAA2B;AAAA,EAC3B,eAAAC;AAAA,EACA,iBAAAC;AAAA,EACA,UAAAC;AAAA,EACA,GAAGC;AACP,GACAC,MACY;AACZ,QAAMC,IAAWC,GAAgC,IAAI,GAC/CC,IAAmBC,GAAY,CAACC,MAAwC;AAC1E,IAAAJ,EAAS,UAAUI;AAAA,EACvB,GAAG,CAAA,CAAE,GACC,EAAE,GAAAC,EAAA,IAAMC,GAAA,GACR,EAAE,YAAAC,GAAY,WAAAC,GAAW,OAAAC,GAAO,YAAAC,GAAY,aAAAC,GAAa,gBAAAC,GAAgB,eAAAC,GAAe,iBAAAC,EAAA,IAC1FC,GAAchC,GAAUY,CAAa,GACnC,EAAE,eAAAqB,GAAe,aAAAC,GAAa,SAAAC,GAAS,QAAAC,GAAA,IAAWC,GAAA,GAClD,EAAE,wBAAAC,GAAwB,sBAAAC,EAAA,IAAyBC;AAAA,IACrD1B;AAAA,IACAb;AAAA,IACA4B;AAAA,EAAA,GAEEY,KAAaC,GAAczC,GAAoB4B,CAAc,GAE7D,CAACc,IAA2BC,CAA4B,IAAIC,GAAS,EAAK,GAE1EC,IAAgBC,EAAQ,MACnB9C,EACF,IAAI,CAAC+C,MAAUnB,EAAemB,CAAK,CAAC,EACpC,OAAO,CAACC,MAA6BA,MAAS,UAAa,WAAWA,KAAQ,WAAWA,CAAI,GACnG,CAAChD,GAAoB4B,CAAc,CAAC,GAEjCqB,KAA0BC;AAAA,IAC5BrC,IACM;AAAA,MACI,eAAAgC;AAAA,MACA,cAAc,EAAE,eAAeM,GAAkB,MAAAC,KAAQ;AACrD,YAAIA,MAASF,EAAqB,iBAAiB,8BAA8B;AAC7E,gBAAMG,IAAcR,EAAc,KAAK,CAACG,MAAS,EAACG,KAAA,QAAAA,EAAkB,SAASH,GAAK;AAClF,UAAIK,KACApD,EAAaoD,EAAY,KAAK;AAAA,QAEtC;AAAA,MACJ;AAAA,IAAA,IAEJ,EAAE,eAAe,CAAA,EAAC;AAAA,EAAE,GAExBC,KAAqBzC,IAAWoC,GAAwB,qBAAqB,MAAY;AAAA,EAAC,GAE1F;AAAA,IACF,eAAAM;AAAA,IACA,sBAAAC;AAAA,IACA,cAAAC;AAAA,IACA,cAAAC;AAAA,IACA,OAAAC;AAAA,IACA,cAAAC;AAAA,IACA,QAAAC;AAAA,IACA,kBAAAC;AAAA,IACA,YAAAC;AAAA,EAAA,IACAC,EAAwB;AAAA,IACxB,OAAAvC;AAAA,IACA,cAAcZ,IAAW,OAAQe,EAAe5B,EAAmB,CAAC,CAAC;AAAA,IACrE,yBAAyB;AAAA,IACzB,gBAAgBS;AAAA;AAAA,IAEhB,GAAI,qBAAqBK,KAASA,EAAM,iBAAiB,IAAI,EAAE,SAASA,EAAM,iBAAiB,EAAA,IAAM,CAAA;AAAA,IACrG,sBAAsB,CAAC,EAAE,cAAA8C,QAAmB;AACxC,MAAIA,KACA3D,EAAa2D,EAAa,KAAK,GAE/B/C,KACAgB,EAAc,EAAE;AAAA,IAExB;AAAA,IACA,oBAAoB,CAAC,EAAE,YAAAkC,QAAiB;AACpC,MAAAlC,EAAckC,CAAU;AAAA,IAC5B;AAAA,IACA,gBAAgB,MAAM;AAClB,MAAApB,EAA6B,EAAK,GAClCd,EAAc,EAAE;AAAA,IACpB;AAAA,IACA,0BAA0B,MAAM;AAC5B,MAAAc,EAA6B,EAAI;AAAA,IACrC;AAAA,IACA,cAAc,CAACK,MAAUA,IAAOA,EAAK,QAAQ;AAAA,IAC7C,cAAc,CAACiB,GAAOC,MAAqB;AACvC,YAAM,EAAE,SAAAC,GAAS,MAAAf,EAAA,IAASc;AAC1B,UAAIrD;AACA,gBAAQuC,GAAA;AAAA,UACJ,KAAKY,EAAY,iBAAiB;AAAA,UAClC,KAAKA,EAAY,iBAAiB;AAC9B,mBAAO;AAAA,cACH,GAAGG;AAAA,cACH,QAAQ;AAAA,cACR,kBAAkBF,EAAM;AAAA,cACxB,YAAY;AAAA,YAAA;AAAA,UAEpB,KAAKD,EAAY,iBAAiB;AAE9B,mBAAO;AAAA,cACH,GAAGG;AAAA,cACH,YAAY;AAAA,YAAA;AAAA,QAChB;AAAA;AAKR,gBAAQf,GAAA;AAAA,UACJ,KAAKY,EAAY,iBAAiB;AAAA,UAClC,KAAKA,EAAY,iBAAiB;AAC9B,YACIG,EAAQ,gBACRF,EAAM,gBACNE,EAAQ,aAAa,UAAUF,EAAM,aAAa,SAElDhE,EAAakE,EAAQ,aAAa,KAAK;AAE3C;AAAA,QAAA;AAGZ,aAAOA;AAAA,IACX;AAAA,EAAA,CACH,GASKC,IAPetB,EAAQ,MACrBjC,IACO,KAEJ,CAACF,KAAiB,CAACc,EAAM,KAAK,CAACuB,MAASA,EAAK,MAAM,cAAc,SAASe,EAAW,YAAA,CAAa,CAAC,GAC3G,CAACA,GAAYtC,GAAOd,GAAeE,CAAQ,CAAC,KAEd,CAAC,CAACiB,EAAgB,SAAS1B,MAAW,SAEjEiE,KAAqB,CAACtB,GAAeuB,MAAoC;AAC3E,UAAMtB,IAAOpB,EAAemB,CAAK;AACjC,IAAIC,MACAM,GAAmBN,CAAI,GACvB/C,EAAa8C,CAAK,GACd/B,EAAS,YACTA,EAAS,QAAQ,MAAA,GACbsD,MACAtD,EAAS,QAAQ,QAAQ,gBAAgB;AAAA,EAIzD,GAEMuD,KAAc,MAAY;AAC5B,IAAArE,EAAA,GACAyD,EAAA;AAAA,EACJ,GAEMa,IAAa,CAACC,MAA2D;;AAC3E,IAAAtC,GAAOsC,CAAS,GAEX5D,OACyB+C,KAAA,gBAAAA,EAAc,UAAS,IACZ,kBAAA,MAAwBG,EAAW,kBAAA,KAGpEJ,EAAA,GAIJJ,EAAA,EAAgB,YAChBmB,KAAAC,IAAApB,EAAA,GAAgB,WAAhB,QAAAmB,EAAA,KAAAC,GAAyBF;AAAA,EAEjC;AAEA,SACI,gBAAAG,EAACC,EAAa,MAAb,EAAkB,MAAMhB,GACrB,UAAA;AAAA,IAAA,gBAAAiB,EAACD,EAAa,QAAb,EAAoB,SAAO,IACxB,UAAA,gBAAAD;AAAA,MAAC;AAAA,MAAA;AAAA,QACG,KAAK7D;AAAA,QACL,WAAWgE,EAAO;AAAA,QAClB,eAAaX,IAAW,UAAUhE;AAAA,QAClC,iBAAeC;AAAA,QACf,cAAYL,EAAmB,WAAW;AAAA,QAEzC,UAAA;AAAA,UAAAa,IACG,gBAAA+D,EAAAI,IAAA,EAEI,UAAA;AAAA,YAAA,gBAAAF,EAAC,UAAK,IAAIzC,GAAwB,WAAW0C,EAAO,QAC/C,UAAAzC,GACL;AAAA,YACA,gBAAAwC;AAAA,cAACG;AAAA,cAAA;AAAA,gBACG,OAAOzC;AAAA,gBACP,WAAW6B;AAAA,gBACX,eAAerE,EAAmB;AAAA,gBAElC,UAAA,gBAAA8E;AAAA,kBAAC;AAAA,kBAAA;AAAA,oBAEI,GAAGvB,EAAc;AAAA,sBACd,KAAKrC;AAAA,sBACL,cAAc,gBAAgBJ,IAAQA,EAAM,YAAY,IAAI;AAAA;AAAA,sBAE5D,mBACI,qBAAqBA,KAASA,EAAM,iBAAiB,IAC/CA,EAAM,iBAAiB,IACvB;AAAA,sBACV,oBAAoBwB,IAAuBD,IAAyB;AAAA,oBAAA,CACvE;AAAA,oBACD,gBAAc/B;AAAA,oBACd,aAAaN,EAAmB,WAAW,IAAIG,IAAc;AAAA,oBAC7D,WAAW4E,EAAO;AAAA,oBAClB,UAAA1E;AAAA,oBACA,aAAA4B;AAAA,oBACA,SAAAC;AAAA,oBACA,QAAQsC;AAAA,kBAAA;AAAA,gBAAA;AAAA,cACZ;AAAA,YAAA;AAAA,UACJ,EAAA,CACJ,IAEA,gBAAAM;AAAA,YAAC;AAAA,YAAA;AAAA,cACI,GAAGvB,EAAc;AAAA,gBACd,cAAc,gBAAgBzC,IAAQA,EAAM,YAAY,IAAI;AAAA;AAAA,gBAE5D,mBACI,qBAAqBA,KAASA,EAAM,iBAAiB,IAC/CA,EAAM,iBAAiB,IACvB;AAAA,cAAA,CACb;AAAA,cACD,gBAAcR;AAAA,cACd,aAAAH;AAAA,cACA,WAAW4E,EAAO;AAAA,cAClB,UAAA1E;AAAA,cACA,aAAA4B;AAAA,cACA,SAAAC;AAAA,cACA,QAAQsC;AAAA,YAAA;AAAA,UAAA;AAAA,UAGfjD;AAAA,UACAI,IAAc,gBAAAmD,EAACI,IAAA,EAAY,SAASX,IAAc,aAAY,IAAiB;AAAA,UAC/EzC,EAAgB,aAAa+B,IAC1B,gBAAAiB,EAACK,MAAuB,MAAK,SAAQ,gBAAc,GAAG7E,CAAU,eAC5D,UAAA,gBAAAwE,EAACM,IAAA,EAAc,MAAK,WAAU,gBAAc,GAAG9E,CAAU,mBAAmB,GAChF,IACA;AAAA,UACJ,gBAAAsE,EAAC,OAAA,EAAI,WAAWG,EAAO,OACnB,UAAA;AAAA,YAAA,gBAAAD;AAAA,cAAC;AAAA,cAAA;AAAA,gBACG,cAAYzD,EAAE,mBAAmB;AAAA,gBAChC,GAAGmC,GAAA;AAAA,gBACJ,MAAK;AAAA,gBACL,UAAAnD;AAAA,gBACA,aAAa,MAAM;AACf,kBAAA2B,EAAc,UAAU;AAAA,gBAC5B;AAAA,gBAEA,4BAACqD,IAAA,EAAc,MAAM,IAAI,WAAWN,EAAO,MAAA,CAAO;AAAA,cAAA;AAAA,YAAA;AAAA,YAEtD,gBAAAD,EAACQ,IAAA,EAAY,QAAAlF,GAAgB,UAAAgE,GAAoB,YAAA9D,EAAA,CAAwB;AAAA,UAAA,EAAA,CAC7E;AAAA,QAAA;AAAA,MAAA;AAAA,IAAA,GAER;AAAA,IAEA,gBAAAwE;AAAA,MAACS;AAAA,MAAA;AAAA,QACG,OAAOhF;AAAA,QACP,MAAAC;AAAA,QACA,kBAAAsD;AAAA,QACA,YAAApC;AAAA,QACA,cAAA+B;AAAA,QACA,cAAAC;AAAA,QACA,oBAAA1D;AAAA,QACA,2BAAA0C;AAAA,QACA,0BAAAhC;AAAA,QACA,iBAAAE;AAAA,QAEC,UAAAY;AAAA,MAAA;AAAA,IAAA;AAAA,EACL,GACJ;AAER;AACA1B,EAAkB,cAAc;AAEzB,MAAM0F,KAAeC,GAA8C3F,CAAiB;"}
|
|
@@ -1,23 +1,20 @@
|
|
|
1
|
-
import { useState as
|
|
2
|
-
const
|
|
3
|
-
const [
|
|
4
|
-
(
|
|
5
|
-
|
|
6
|
-
return;
|
|
7
|
-
const e = d === r ? null : r;
|
|
8
|
-
t === void 0 && u(e), s == null || s(e);
|
|
1
|
+
import { useState as a, useCallback as u } from "react";
|
|
2
|
+
const n = (s, t, e) => {
|
|
3
|
+
const [f, r] = a(e ?? null), i = t !== void 0 ? t : f, l = i !== null ? [i] : [], m = u(
|
|
4
|
+
(d) => {
|
|
5
|
+
d !== void 0 && (t === void 0 && r(d), s == null || s(d));
|
|
9
6
|
},
|
|
10
|
-
[
|
|
11
|
-
),
|
|
12
|
-
t === void 0 &&
|
|
7
|
+
[t, s]
|
|
8
|
+
), I = u(() => {
|
|
9
|
+
t === void 0 && r(null), s == null || s(null);
|
|
13
10
|
}, [t, s]);
|
|
14
11
|
return {
|
|
15
|
-
selectedItemValues:
|
|
16
|
-
selectItem:
|
|
17
|
-
clear:
|
|
12
|
+
selectedItemValues: l,
|
|
13
|
+
selectItem: m,
|
|
14
|
+
clear: I
|
|
18
15
|
};
|
|
19
16
|
};
|
|
20
17
|
export {
|
|
21
|
-
|
|
18
|
+
n as useSingleSelect
|
|
22
19
|
};
|
|
23
20
|
//# sourceMappingURL=fondue-components97.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"fondue-components97.js","sources":["../src/components/Select/hooks/useSingleSelect.ts"],"sourcesContent":["/* (c) Copyright Frontify Ltd., all rights reserved. */\n\nimport { useCallback, useState } from 'react';\n\nexport const useSingleSelect = (\n onSelect?: (value: string | null) => void,\n value?: string | null,\n defaultValue?: string,\n) => {\n const [selectedItemState, setSelectedItemState] = useState<string | null>(defaultValue ?? null);\n\n const selectedValue = value !== undefined ? value : selectedItemState;\n const selectedItemValues = selectedValue !== null ? [selectedValue] : [];\n\n const selectItem = useCallback(\n (item?: string) => {\n if (item === undefined) {\n return;\n }\n
|
|
1
|
+
{"version":3,"file":"fondue-components97.js","sources":["../src/components/Select/hooks/useSingleSelect.ts"],"sourcesContent":["/* (c) Copyright Frontify Ltd., all rights reserved. */\n\nimport { useCallback, useState } from 'react';\n\nexport const useSingleSelect = (\n onSelect?: (value: string | null) => void,\n value?: string | null,\n defaultValue?: string,\n) => {\n const [selectedItemState, setSelectedItemState] = useState<string | null>(defaultValue ?? null);\n\n const selectedValue = value !== undefined ? value : selectedItemState;\n const selectedItemValues = selectedValue !== null ? [selectedValue] : [];\n\n const selectItem = useCallback(\n (item?: string) => {\n if (item === undefined) {\n return;\n }\n if (value === undefined) {\n setSelectedItemState(item);\n }\n onSelect?.(item);\n },\n [value, onSelect],\n );\n\n const clear = useCallback(() => {\n if (value === undefined) {\n setSelectedItemState(null);\n }\n onSelect?.(null);\n }, [value, onSelect]);\n\n return {\n selectedItemValues,\n selectItem,\n clear,\n };\n};\n"],"names":["useSingleSelect","onSelect","value","defaultValue","selectedItemState","setSelectedItemState","useState","selectedValue","selectedItemValues","selectItem","useCallback","item","clear"],"mappings":";AAIO,MAAMA,IAAkB,CAC3BC,GACAC,GACAC,MACC;AACD,QAAM,CAACC,GAAmBC,CAAoB,IAAIC,EAAwBH,KAAgB,IAAI,GAExFI,IAAgBL,MAAU,SAAYA,IAAQE,GAC9CI,IAAqBD,MAAkB,OAAO,CAACA,CAAa,IAAI,CAAA,GAEhEE,IAAaC;AAAA,IACf,CAACC,MAAkB;AACf,MAAIA,MAAS,WAGTT,MAAU,UACVG,EAAqBM,CAAI,GAE7BV,KAAA,QAAAA,EAAWU;AAAA,IACf;AAAA,IACA,CAACT,GAAOD,CAAQ;AAAA,EAAA,GAGdW,IAAQF,EAAY,MAAM;AAC5B,IAAIR,MAAU,UACVG,EAAqB,IAAI,GAE7BJ,KAAA,QAAAA,EAAW;AAAA,EACf,GAAG,CAACC,GAAOD,CAAQ,CAAC;AAEpB,SAAO;AAAA,IACH,oBAAAO;AAAA,IACA,YAAAC;AAAA,IACA,OAAAG;AAAA,EAAA;AAER;"}
|
package/dist/index.d.ts
CHANGED
|
@@ -519,11 +519,11 @@ export declare const Dialog: {
|
|
|
519
519
|
displayName: string;
|
|
520
520
|
};
|
|
521
521
|
Title: {
|
|
522
|
-
({ children, asChild }: DialogAnnouncementProps): JSX_2.Element;
|
|
522
|
+
({ children, asChild, screenReaderOnly }: DialogAnnouncementProps): JSX_2.Element;
|
|
523
523
|
displayName: string;
|
|
524
524
|
};
|
|
525
525
|
Description: {
|
|
526
|
-
({ children, asChild }: DialogAnnouncementProps): JSX_2.Element;
|
|
526
|
+
({ children, asChild, screenReaderOnly }: DialogAnnouncementProps): JSX_2.Element;
|
|
527
527
|
displayName: string;
|
|
528
528
|
};
|
|
529
529
|
Close: {
|
|
@@ -541,6 +541,11 @@ export declare const Dialog: {
|
|
|
541
541
|
declare type DialogAnnouncementProps = {
|
|
542
542
|
children?: ReactNode;
|
|
543
543
|
asChild?: boolean;
|
|
544
|
+
/**
|
|
545
|
+
* Visually hide the element while keeping it accessible to screen readers
|
|
546
|
+
* @default false
|
|
547
|
+
*/
|
|
548
|
+
screenReaderOnly?: boolean;
|
|
544
549
|
};
|
|
545
550
|
|
|
546
551
|
declare type DialogBodyProps = {
|
|
@@ -2226,9 +2231,16 @@ declare type TabsRootProps = {
|
|
|
2226
2231
|
onActiveTabChange?: (value: string) => void;
|
|
2227
2232
|
/**
|
|
2228
2233
|
* Select the used variant
|
|
2229
|
-
*
|
|
2234
|
+
* @default 'default'
|
|
2230
2235
|
*/
|
|
2231
2236
|
variant?: 'default' | 'pill';
|
|
2237
|
+
/**
|
|
2238
|
+
* Add a divider line below the tabs
|
|
2239
|
+
* Only available when variant is 'pill'
|
|
2240
|
+
* Useful for tabs placed inside Dialog content
|
|
2241
|
+
* @default false
|
|
2242
|
+
*/
|
|
2243
|
+
withDivider?: boolean;
|
|
2232
2244
|
};
|
|
2233
2245
|
|
|
2234
2246
|
declare type TabsTabProps = {
|