@geotab/zenith 3.7.0-beta.0 → 3.7.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/README.md +1 -0
- package/dist/checkbox/checkbox.d.ts +3 -1
- package/dist/checkbox/checkbox.js +5 -8
- package/dist/checkboxListWithAction/checkboxListWithAction.d.ts +3 -1
- package/dist/checkboxListWithAction/checkboxListWithAction.js +185 -3
- package/dist/dropdown/dropdownPopup.d.ts +1 -1
- package/dist/dropdown/dropdownTrigger.d.ts +1 -1
- package/dist/dropdownRaw/dropdownList.d.ts +2 -1
- package/dist/dropdownRaw/dropdownList.js +15 -4
- package/dist/dropdownRaw/dropdownPopup.d.ts +3 -1
- package/dist/dropdownRaw/dropdownPopup.js +35 -5
- package/dist/dropdownRaw/dropdownRaw.js +82 -7
- package/dist/dropdownRaw/dropdownSearchableTrigger.d.ts +2 -1
- package/dist/dropdownRaw/dropdownSearchableTrigger.js +7 -2
- package/dist/dropdownRaw/dropdownTrigger.d.ts +2 -1
- package/dist/dropdownRaw/dropdownTrigger.js +3 -5
- package/dist/footerButtons/footerButtons.d.ts +6 -4
- package/dist/footerButtons/footerButtons.js +3 -8
- package/dist/groupsFilterRaw/groupsFilterInitialState.js +16 -0
- package/dist/groupsFilterRaw/groupsFilterTrigger.js +4 -0
- package/dist/index.css +14 -0
- package/dist/nav/navItem/navItem.d.ts +1 -0
- package/dist/nav/navItem/navItem.js +4 -1
- package/dist/utils/localization/translations/cs.json +2 -1
- package/dist/utils/localization/translations/de.json +2 -1
- package/dist/utils/localization/translations/en.json +2 -1
- package/dist/utils/localization/translations/es.json +2 -1
- package/dist/utils/localization/translations/fr-FR.json +2 -1
- package/dist/utils/localization/translations/fr.json +2 -1
- package/dist/utils/localization/translations/id.json +2 -1
- package/dist/utils/localization/translations/it.json +2 -1
- package/dist/utils/localization/translations/ja.json +2 -1
- package/dist/utils/localization/translations/ms.json +2 -1
- package/dist/utils/localization/translations/nl.json +2 -1
- package/dist/utils/localization/translations/pl.json +2 -1
- package/dist/utils/localization/translations/pt-BR.json +2 -1
- package/dist/utils/localization/translations/sv.json +2 -1
- package/dist/utils/localization/translations/th.json +2 -1
- package/dist/utils/localization/translations/tr.json +2 -1
- package/dist/utils/localization/translations/zh-Hans.json +2 -1
- package/esm/checkbox/checkbox.d.ts +3 -1
- package/esm/checkbox/checkbox.js +5 -8
- package/esm/checkboxListWithAction/checkboxListWithAction.d.ts +3 -1
- package/esm/checkboxListWithAction/checkboxListWithAction.js +186 -4
- package/esm/dropdown/dropdownPopup.d.ts +1 -1
- package/esm/dropdown/dropdownTrigger.d.ts +1 -1
- package/esm/dropdownRaw/dropdownList.d.ts +2 -1
- package/esm/dropdownRaw/dropdownList.js +16 -5
- package/esm/dropdownRaw/dropdownPopup.d.ts +3 -1
- package/esm/dropdownRaw/dropdownPopup.js +37 -7
- package/esm/dropdownRaw/dropdownRaw.js +82 -7
- package/esm/dropdownRaw/dropdownSearchableTrigger.d.ts +2 -1
- package/esm/dropdownRaw/dropdownSearchableTrigger.js +7 -2
- package/esm/dropdownRaw/dropdownTrigger.d.ts +2 -1
- package/esm/dropdownRaw/dropdownTrigger.js +3 -5
- package/esm/footerButtons/footerButtons.d.ts +6 -4
- package/esm/footerButtons/footerButtons.js +3 -8
- package/esm/groupsFilterRaw/groupsFilterInitialState.js +16 -0
- package/esm/groupsFilterRaw/groupsFilterTrigger.js +4 -0
- package/esm/nav/navItem/navItem.d.ts +1 -0
- package/esm/nav/navItem/navItem.js +5 -2
- package/esm/utils/localization/translations/cs.json +2 -1
- package/esm/utils/localization/translations/de.json +2 -1
- package/esm/utils/localization/translations/en.json +2 -1
- package/esm/utils/localization/translations/es.json +2 -1
- package/esm/utils/localization/translations/fr-FR.json +2 -1
- package/esm/utils/localization/translations/fr.json +2 -1
- package/esm/utils/localization/translations/id.json +2 -1
- package/esm/utils/localization/translations/it.json +2 -1
- package/esm/utils/localization/translations/ja.json +2 -1
- package/esm/utils/localization/translations/ms.json +2 -1
- package/esm/utils/localization/translations/nl.json +2 -1
- package/esm/utils/localization/translations/pl.json +2 -1
- package/esm/utils/localization/translations/pt-BR.json +2 -1
- package/esm/utils/localization/translations/sv.json +2 -1
- package/esm/utils/localization/translations/th.json +2 -1
- package/esm/utils/localization/translations/tr.json +2 -1
- package/esm/utils/localization/translations/zh-Hans.json +2 -1
- package/package.json +1 -4
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import { injectString } from "../utils/localization/translationsDictionary";
|
|
2
2
|
import { jsx as _jsx, jsxs as _jsxs, Fragment as _Fragment } from "react/jsx-runtime";
|
|
3
|
-
import { Fragment, useId } from "react";
|
|
3
|
+
import { Fragment, useCallback, useEffect, useId, useRef, useState } from "react";
|
|
4
4
|
import { Checkbox } from "../checkbox/checkbox";
|
|
5
5
|
import { classNames } from "../commonHelpers/classNames/classNames";
|
|
6
6
|
import { IconChevronRight } from "../icons/iconChevronRight";
|
|
@@ -84,13 +84,15 @@ injectString("tr", "Toggle {groupName} filter", "{groupName} filtresini de\u011F
|
|
|
84
84
|
injectString("zh-Hans", "Toggle {groupName} filter", "\u5207\u6362 {groupName} \u7B5B\u9009\u5668");
|
|
85
85
|
injectString("zh-TW", "Toggle {groupName} filter", "\u5207\u63DB\u300C{groupName}\u300D\u7BE9\u9078\u689D\u4EF6");
|
|
86
86
|
injectString("ro-RO", "Toggle {groupName} filter", "Activa\u021Bi filtrul {groupName}");
|
|
87
|
+
injectString("en", "Has additional actions. Use right arrow to access button, left arrow to return.", "Has additional actions. Use right arrow to access button, left arrow to return.");
|
|
87
88
|
export const CheckboxListWithAction = ({
|
|
88
89
|
label,
|
|
89
90
|
options,
|
|
90
91
|
onChange,
|
|
91
92
|
onClick,
|
|
92
93
|
search = [],
|
|
93
|
-
className
|
|
94
|
+
className,
|
|
95
|
+
handleTab
|
|
94
96
|
}) => {
|
|
95
97
|
const {
|
|
96
98
|
translate
|
|
@@ -98,6 +100,11 @@ export const CheckboxListWithAction = ({
|
|
|
98
100
|
const driveComponentClass = useDriveClassName("zen-checkbox-list-with-action");
|
|
99
101
|
const listId = useId();
|
|
100
102
|
const checkboxId = `${listId}_check_list-item_`;
|
|
103
|
+
const navigationInstructionsId = `${listId}_navigation_instructions`;
|
|
104
|
+
const listRef = useRef(null);
|
|
105
|
+
const [focusedRowIndex, setFocusedRowIndex] = useState(0);
|
|
106
|
+
const [focusedElementType, setFocusedElementType] = useState("checkbox");
|
|
107
|
+
const isInitialized = useRef(false);
|
|
101
108
|
const handleChange = e => {
|
|
102
109
|
const evtTarget = e.target;
|
|
103
110
|
const elId = evtTarget.getAttribute("id").replace(checkboxId, "");
|
|
@@ -112,7 +119,171 @@ export const CheckboxListWithAction = ({
|
|
|
112
119
|
const evtTarget = e.target;
|
|
113
120
|
const elId = evtTarget.getAttribute("data-btn") || ((_a = evtTarget.parentElement) === null || _a === void 0 ? void 0 : _a.getAttribute("data-btn")) || "";
|
|
114
121
|
onClick(elId);
|
|
122
|
+
setFocusedElementType("checkbox");
|
|
115
123
|
};
|
|
124
|
+
const getFocusableElements = useCallback(() => {
|
|
125
|
+
if (!listRef.current || !options) return [];
|
|
126
|
+
const elements = [];
|
|
127
|
+
options.forEach((opt, rowIndex) => {
|
|
128
|
+
var _a;
|
|
129
|
+
const listItem = (_a = listRef.current) === null || _a === void 0 ? void 0 : _a.querySelector(`li[data-item="${opt.property}"]`);
|
|
130
|
+
// eslint-disable-next-line @typescript-eslint/no-unnecessary-condition
|
|
131
|
+
if (listItem) {
|
|
132
|
+
const checkbox = listItem.querySelector('input[type="checkbox"]');
|
|
133
|
+
// eslint-disable-next-line @typescript-eslint/no-unnecessary-condition
|
|
134
|
+
if (checkbox) {
|
|
135
|
+
elements.push({
|
|
136
|
+
element: checkbox,
|
|
137
|
+
rowIndex,
|
|
138
|
+
type: "checkbox",
|
|
139
|
+
blocked: opt.blocked
|
|
140
|
+
});
|
|
141
|
+
}
|
|
142
|
+
if (opt.isWithAction) {
|
|
143
|
+
const button = listItem.querySelector("button[data-btn]");
|
|
144
|
+
// eslint-disable-next-line @typescript-eslint/no-unnecessary-condition
|
|
145
|
+
if (button) {
|
|
146
|
+
elements.push({
|
|
147
|
+
element: button,
|
|
148
|
+
rowIndex,
|
|
149
|
+
type: "button",
|
|
150
|
+
blocked: opt.blocked
|
|
151
|
+
});
|
|
152
|
+
}
|
|
153
|
+
}
|
|
154
|
+
}
|
|
155
|
+
});
|
|
156
|
+
return elements;
|
|
157
|
+
}, [options]);
|
|
158
|
+
const updateTabIndex = useCallback((newRowIndex, newElementType) => {
|
|
159
|
+
const elements = getFocusableElements();
|
|
160
|
+
elements.forEach(({
|
|
161
|
+
element,
|
|
162
|
+
rowIndex,
|
|
163
|
+
type,
|
|
164
|
+
blocked
|
|
165
|
+
}) => {
|
|
166
|
+
const isActive = rowIndex === newRowIndex && type === newElementType && !blocked;
|
|
167
|
+
element.setAttribute("tabindex", isActive ? "0" : "-1");
|
|
168
|
+
});
|
|
169
|
+
}, [getFocusableElements]);
|
|
170
|
+
const handleKeyDown = useCallback(
|
|
171
|
+
// eslint-disable-next-line complexity
|
|
172
|
+
e => {
|
|
173
|
+
var _a;
|
|
174
|
+
const elements = getFocusableElements();
|
|
175
|
+
if (elements.length === 0 || !options) return;
|
|
176
|
+
let newRowIndex = focusedRowIndex;
|
|
177
|
+
let newElementType = focusedElementType;
|
|
178
|
+
let preventDefault = false;
|
|
179
|
+
if (e.key === "Enter") {
|
|
180
|
+
const evtTarget = e.target;
|
|
181
|
+
const elId = ((_a = evtTarget.getAttribute("id")) === null || _a === void 0 ? void 0 : _a.replace(checkboxId, "")) || "";
|
|
182
|
+
elId && onChange({
|
|
183
|
+
id: elId,
|
|
184
|
+
state: evtTarget.checked,
|
|
185
|
+
partial: evtTarget.dataset.indeterminate === "true"
|
|
186
|
+
});
|
|
187
|
+
return;
|
|
188
|
+
}
|
|
189
|
+
if (e.key === "ArrowDown") {
|
|
190
|
+
// Go to next row
|
|
191
|
+
do {
|
|
192
|
+
newRowIndex = (newRowIndex + 1) % options.length;
|
|
193
|
+
} while (options[newRowIndex].blocked && newRowIndex !== focusedRowIndex);
|
|
194
|
+
preventDefault = true;
|
|
195
|
+
} else if (e.key === "ArrowUp") {
|
|
196
|
+
// Go to previous row
|
|
197
|
+
do {
|
|
198
|
+
newRowIndex = (newRowIndex - 1 + options.length) % options.length;
|
|
199
|
+
} while (options[newRowIndex].blocked && newRowIndex !== focusedRowIndex);
|
|
200
|
+
preventDefault = true;
|
|
201
|
+
} else if (e.key === "ArrowRight") {
|
|
202
|
+
// Go to button if exists in current row and not blocked
|
|
203
|
+
if (options[focusedRowIndex].isWithAction && focusedElementType === "checkbox" && !options[focusedRowIndex].blocked) {
|
|
204
|
+
newElementType = "button";
|
|
205
|
+
preventDefault = true;
|
|
206
|
+
}
|
|
207
|
+
} else if (e.key === "ArrowLeft") {
|
|
208
|
+
// Go to checkbox if currently on button and checkbox not blocked
|
|
209
|
+
if (focusedElementType === "button" && !options[focusedRowIndex].blocked) {
|
|
210
|
+
newElementType = "checkbox";
|
|
211
|
+
preventDefault = true;
|
|
212
|
+
}
|
|
213
|
+
} else if (e.key === "Home") {
|
|
214
|
+
// Go to first non-blocked row
|
|
215
|
+
newRowIndex = 0;
|
|
216
|
+
while (newRowIndex < options.length && options[newRowIndex].blocked) {
|
|
217
|
+
newRowIndex++;
|
|
218
|
+
}
|
|
219
|
+
if (newRowIndex < options.length) {
|
|
220
|
+
newElementType = "checkbox";
|
|
221
|
+
preventDefault = true;
|
|
222
|
+
}
|
|
223
|
+
} else if (e.key === "End") {
|
|
224
|
+
// Go to last non-blocked row
|
|
225
|
+
newRowIndex = options.length - 1;
|
|
226
|
+
while (newRowIndex >= 0 && options[newRowIndex].blocked) {
|
|
227
|
+
newRowIndex--;
|
|
228
|
+
}
|
|
229
|
+
if (newRowIndex >= 0) {
|
|
230
|
+
newElementType = "checkbox";
|
|
231
|
+
preventDefault = true;
|
|
232
|
+
}
|
|
233
|
+
} else if (e.key === "Tab") {
|
|
234
|
+
if (handleTab) {
|
|
235
|
+
handleTab(e, e.shiftKey);
|
|
236
|
+
return;
|
|
237
|
+
}
|
|
238
|
+
}
|
|
239
|
+
if (preventDefault) {
|
|
240
|
+
e.preventDefault();
|
|
241
|
+
setFocusedRowIndex(newRowIndex);
|
|
242
|
+
setFocusedElementType(newElementType);
|
|
243
|
+
updateTabIndex(newRowIndex, newElementType);
|
|
244
|
+
// Find and focus the target element
|
|
245
|
+
const targetElement = elements.find(({
|
|
246
|
+
rowIndex,
|
|
247
|
+
type,
|
|
248
|
+
blocked
|
|
249
|
+
}) => rowIndex === newRowIndex && type === newElementType && !blocked);
|
|
250
|
+
targetElement === null || targetElement === void 0 ? void 0 : targetElement.element.focus();
|
|
251
|
+
}
|
|
252
|
+
}, [getFocusableElements, options, focusedRowIndex, focusedElementType, checkboxId, onChange, handleTab, updateTabIndex]);
|
|
253
|
+
const handleFocus = useCallback(e => {
|
|
254
|
+
const elements = getFocusableElements();
|
|
255
|
+
const focusedElement = e.target;
|
|
256
|
+
const targetElementInfo = elements.find(({
|
|
257
|
+
element
|
|
258
|
+
}) => element === focusedElement);
|
|
259
|
+
if (targetElementInfo && !targetElementInfo.blocked && (targetElementInfo.rowIndex !== focusedRowIndex || targetElementInfo.type !== focusedElementType)) {
|
|
260
|
+
setFocusedRowIndex(targetElementInfo.rowIndex);
|
|
261
|
+
setFocusedElementType(targetElementInfo.type);
|
|
262
|
+
updateTabIndex(targetElementInfo.rowIndex, targetElementInfo.type);
|
|
263
|
+
}
|
|
264
|
+
}, [focusedRowIndex, focusedElementType, getFocusableElements, updateTabIndex]);
|
|
265
|
+
// Initialize tabindex when options first become available
|
|
266
|
+
useEffect(() => {
|
|
267
|
+
if (options && options.length > 0 && !isInitialized.current) {
|
|
268
|
+
// Find first non-blocked row
|
|
269
|
+
let firstValidRow = 0;
|
|
270
|
+
while (firstValidRow < options.length && options[firstValidRow].blocked) {
|
|
271
|
+
firstValidRow++;
|
|
272
|
+
}
|
|
273
|
+
if (firstValidRow < options.length) {
|
|
274
|
+
setFocusedRowIndex(firstValidRow);
|
|
275
|
+
setFocusedElementType("checkbox");
|
|
276
|
+
updateTabIndex(firstValidRow, "checkbox");
|
|
277
|
+
isInitialized.current = true;
|
|
278
|
+
}
|
|
279
|
+
}
|
|
280
|
+
}, [options, updateTabIndex]);
|
|
281
|
+
// Update tabindex when focused position changes (only after initialization)
|
|
282
|
+
useEffect(() => {
|
|
283
|
+
if (isInitialized.current) {
|
|
284
|
+
updateTabIndex(focusedRowIndex, focusedElementType);
|
|
285
|
+
}
|
|
286
|
+
}, [focusedRowIndex, focusedElementType, updateTabIndex]);
|
|
116
287
|
const getLabelColorInfo = (color, withRightPadding, isHidden, extraArgs) => {
|
|
117
288
|
if (!color) {
|
|
118
289
|
return null;
|
|
@@ -170,7 +341,8 @@ export const CheckboxListWithAction = ({
|
|
|
170
341
|
type: "button",
|
|
171
342
|
onClick: handleClick,
|
|
172
343
|
title: title,
|
|
173
|
-
className: classN
|
|
344
|
+
className: classN,
|
|
345
|
+
tabIndex: -1
|
|
174
346
|
}, otherArgs, {
|
|
175
347
|
children: childEl
|
|
176
348
|
})) : _jsx("div", {
|
|
@@ -200,6 +372,9 @@ export const CheckboxListWithAction = ({
|
|
|
200
372
|
};
|
|
201
373
|
return optionsArr ? _jsx("ul", {
|
|
202
374
|
className: "zen-checkbox-list-with-action__list",
|
|
375
|
+
ref: listRef,
|
|
376
|
+
onKeyDown: handleKeyDown,
|
|
377
|
+
onFocus: handleFocus,
|
|
203
378
|
children: optionsArr.map((opt, ind) => {
|
|
204
379
|
const titleForRender = opt.title || opt.label;
|
|
205
380
|
const labelForRender = selectSearchTerm(opt.label);
|
|
@@ -215,7 +390,9 @@ export const CheckboxListWithAction = ({
|
|
|
215
390
|
checked: opt.checked,
|
|
216
391
|
disabled: opt.blocked,
|
|
217
392
|
title: translate("Toggle {groupName} filter").replace("{groupName}", titleForRender),
|
|
393
|
+
describedBy: opt.isWithAction ? navigationInstructionsId : undefined,
|
|
218
394
|
"data-indeterminate": opt.partialChecked,
|
|
395
|
+
tabIndex: -1,
|
|
219
396
|
children: opt.isWithAction ? null : labelElement
|
|
220
397
|
}), opt.isWithAction && labelElement]
|
|
221
398
|
}, `li_${ind}_${opt.property}`);
|
|
@@ -227,7 +404,12 @@ export const CheckboxListWithAction = ({
|
|
|
227
404
|
children: [label ? _jsx("div", {
|
|
228
405
|
className: "zen-checkbox-list-with-action__title",
|
|
229
406
|
children: label
|
|
230
|
-
}) : null, build(options)
|
|
407
|
+
}) : null, build(options), _jsx("div", {
|
|
408
|
+
id: navigationInstructionsId,
|
|
409
|
+
className: "zen-checkbox-list-with-action__sr-only",
|
|
410
|
+
"aria-hidden": "true",
|
|
411
|
+
children: translate("Has additional actions. Use right arrow to access button, left arrow to return.")
|
|
412
|
+
})]
|
|
231
413
|
});
|
|
232
414
|
};
|
|
233
415
|
export const TRANSLATIONS = ["View {groupName} children", "Toggle {groupName} filter", "Number of selected child groups - {count}"];
|
|
@@ -1,3 +1,3 @@
|
|
|
1
1
|
import { IDropdownPopup as IDropdownPopupRaw } from "../dropdownRaw/dropdownPopup";
|
|
2
|
-
export declare const DropdownPopup: ({ alignment, triggerRef, classNamePopup, isMobile, inputValue, dialogAriaLabel, disabled, filterName, handleApplyClick, handleClearClick, handleTriggerClick, mobileSheetStackingClassName, onInputChange, hasApplyButton, inputId, isClearButtonDisabled, isWithFooter, placeholder, searchField, isSearchInPopup, isApplyButtonDisabled, isOpenCombo, inputRef, contentRef, children, onReadyForFocus, handleCheckboxChange, checkboxLabel, isChecked, popupId }: IDropdownPopupRaw) => import("react/jsx-runtime").JSX.Element;
|
|
2
|
+
export declare const DropdownPopup: ({ alignment, triggerRef, classNamePopup, isMobile, inputValue, dialogAriaLabel, disabled, filterName, handleApplyClick, handleClearClick, handleTriggerClick, mobileSheetStackingClassName, onInputChange, hasApplyButton, inputId, isClearButtonDisabled, isWithFooter, placeholder, searchField, isSearchInPopup, isApplyButtonDisabled, isOpenCombo, inputRef, contentRef, children, onReadyForFocus, handleCheckboxChange, checkboxLabel, isChecked, popupId, handleKeydown, handleFocusOnSentinelItem }: IDropdownPopupRaw) => import("react/jsx-runtime").JSX.Element;
|
|
3
3
|
export type IDropdownPopup = IDropdownPopupRaw;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
export declare const DropdownTrigger: ({ name, onBlur, isActive, id, triggerRef, searchField, placeholder, disabled, fullWidth, currentSelection, handleClick, inputValue, className, onSearchChange, width, title, triggerAriaLabel, count, inputRef, buttonType, isError, popupId, ...otherProps }: import("../dropdownRaw/dropdownTrigger").IDropdownTrigger) => import("react/jsx-runtime").JSX.Element;
|
|
1
|
+
export declare const DropdownTrigger: ({ name, onBlur, isActive, id, triggerRef, searchField, placeholder, disabled, fullWidth, currentSelection, handleClick, inputValue, className, onSearchChange, width, title, triggerAriaLabel, count, inputRef, buttonType, isError, popupId, handleFocusOnPopup, ...otherProps }: import("../dropdownRaw/dropdownTrigger").IDropdownTrigger) => import("react/jsx-runtime").JSX.Element;
|
|
@@ -32,11 +32,12 @@ export interface IDropdownList extends IZenComponentProps {
|
|
|
32
32
|
handleCheckboxChange?: (event: React.ChangeEvent<HTMLInputElement>) => void;
|
|
33
33
|
checkboxLabel?: string;
|
|
34
34
|
isChecked?: boolean;
|
|
35
|
+
listElementRef?: React.RefObject<HTMLDivElement>;
|
|
35
36
|
}
|
|
36
37
|
interface IDropdownEmptyList extends Pick<IDropdownList, "className" | "width" | "onClearClick" | "onApplyClick" | "onCancelClick" | "hasApplyButton" | "isApplyDisabled" | "isClearButtonDisabled" | "isWithFooter"> {
|
|
37
38
|
hasError: boolean;
|
|
38
39
|
}
|
|
39
40
|
export declare const EmptyList: ({ className, width, onClearClick, onApplyClick, onCancelClick, hasApplyButton, isApplyDisabled, isClearButtonDisabled, isWithFooter, hasError }: IDropdownEmptyList) => import("react/jsx-runtime").JSX.Element;
|
|
40
|
-
export declare const DropdownList: ({ onBackButtonClick, onSelectAllClick, onClearClick, onApplyClick, onCancelClick, onChange, onSelect, onSingleSelect, listData, isAllSelected, backButtonName, width, minWidth, isSelectAllButtonDisable, hasSelectAllButton, filterName, isMultiselect, hasApplyButton, isApplyDisabled, isClearButtonDisabled, activeValue, forceSelection, isWithFooter, isMobile, handleCheckboxChange, checkboxLabel, isChecked }: IDropdownList) => import("react/jsx-runtime").JSX.Element;
|
|
41
|
+
export declare const DropdownList: ({ onBackButtonClick, onSelectAllClick, onClearClick, onApplyClick, onCancelClick, onChange, onSelect, onSingleSelect, listData, isAllSelected, backButtonName, width, minWidth, isSelectAllButtonDisable, hasSelectAllButton, filterName, isMultiselect, hasApplyButton, isApplyDisabled, isClearButtonDisabled, activeValue, forceSelection, isWithFooter, isMobile, handleCheckboxChange, checkboxLabel, isChecked, listElementRef }: IDropdownList) => import("react/jsx-runtime").JSX.Element;
|
|
41
42
|
export declare const TRANSLATIONS: string[];
|
|
42
43
|
export {};
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import { injectString } from "../utils/localization/translationsDictionary";
|
|
2
2
|
import { jsx as _jsx, jsxs as _jsxs, Fragment as _Fragment } from "react/jsx-runtime";
|
|
3
|
-
import React, { useCallback, useId, useMemo } from "react";
|
|
3
|
+
import React, { useCallback, useId, useMemo, useRef } from "react";
|
|
4
4
|
import { CheckboxListWithAction } from "../checkboxListWithAction/checkboxListWithAction";
|
|
5
5
|
import { classNames } from "../commonHelpers/classNames/classNames";
|
|
6
6
|
import { IconBackArrow } from "../icons/deprecated/iconBackArrow";
|
|
@@ -309,7 +309,8 @@ export const DropdownList = ({
|
|
|
309
309
|
isMobile,
|
|
310
310
|
handleCheckboxChange,
|
|
311
311
|
checkboxLabel,
|
|
312
|
-
isChecked
|
|
312
|
+
isChecked,
|
|
313
|
+
listElementRef
|
|
313
314
|
}) => {
|
|
314
315
|
const {
|
|
315
316
|
translate
|
|
@@ -320,6 +321,13 @@ export const DropdownList = ({
|
|
|
320
321
|
const handleSelectAllClick = () => {
|
|
321
322
|
onSelectAllClick(isAllSelected);
|
|
322
323
|
};
|
|
324
|
+
const handleBackButtonKeyDown = useCallback(event => {
|
|
325
|
+
if (event.key === "ArrowLeft") {
|
|
326
|
+
event.preventDefault();
|
|
327
|
+
onBackButtonClick();
|
|
328
|
+
}
|
|
329
|
+
}, [onBackButtonClick]);
|
|
330
|
+
const componentRef = useRef(null);
|
|
323
331
|
const handleChange = useCallback(value => {
|
|
324
332
|
onChange(value);
|
|
325
333
|
}, [onChange]);
|
|
@@ -340,10 +348,11 @@ export const DropdownList = ({
|
|
|
340
348
|
forceSelection ? onSingleSelect(false, newActiveEl || activeValue) : onSingleSelect(false, newActiveEl);
|
|
341
349
|
}, [activeValue, forceSelection, onSingleSelect]);
|
|
342
350
|
const selectButtonLabel = isAllSelected ? translate("Deselect all") : translate("Select all");
|
|
343
|
-
const getActionButton = (label, title, icon, isDisabled, clickHandler, size) => _jsx("button", {
|
|
351
|
+
const getActionButton = (label, title, icon, isDisabled, clickHandler, size, onKeyDown) => _jsx("button", {
|
|
344
352
|
type: "button",
|
|
345
353
|
disabled: isDisabled,
|
|
346
354
|
onClick: clickHandler,
|
|
355
|
+
onKeyDown: onKeyDown,
|
|
347
356
|
className: "zen-dropdown-list__item zen-dropdown-list__item--interactive zen-dropdown-list__action-button zen-dropdown-list__action-button-back",
|
|
348
357
|
title: title,
|
|
349
358
|
children: _jsxs(_Fragment, {
|
|
@@ -382,6 +391,7 @@ export const DropdownList = ({
|
|
|
382
391
|
};
|
|
383
392
|
return _jsx("div", {
|
|
384
393
|
className: "zen-dropdown-list__elements",
|
|
394
|
+
ref: listElementRef,
|
|
385
395
|
children: isMultiselect ? _jsx(CheckboxListWithAction, {
|
|
386
396
|
options: listData,
|
|
387
397
|
label: "",
|
|
@@ -399,10 +409,11 @@ export const DropdownList = ({
|
|
|
399
409
|
value: createValue(listData, activeValue)
|
|
400
410
|
})
|
|
401
411
|
});
|
|
402
|
-
}, [isMultiselect, listData, handleChange, handleClick, handleSingleChange, translate, listId, forceSelection, activeValue]);
|
|
412
|
+
}, [listElementRef, isMultiselect, listData, handleChange, handleClick, handleSingleChange, translate, listId, forceSelection, activeValue]);
|
|
403
413
|
return _jsxs("div", Object.assign({
|
|
404
414
|
className: classNames(["zen-dropdown-list", driveComponentClass || ""])
|
|
405
415
|
}, styleWidth, {
|
|
416
|
+
ref: componentRef,
|
|
406
417
|
children: [filterName ? _jsx("div", {
|
|
407
418
|
className: "zen-dropdown-list__label",
|
|
408
419
|
children: filterName
|
|
@@ -415,7 +426,7 @@ export const DropdownList = ({
|
|
|
415
426
|
})
|
|
416
427
|
}) : null, backButtonName ? _jsx("div", {
|
|
417
428
|
className: "zen-dropdown-list__item-wrapper",
|
|
418
|
-
children: getActionButton(backButtonName, translate("Back"), IconBackArrow, false, onBackButtonClick, "large")
|
|
429
|
+
children: getActionButton(backButtonName, translate("Back"), IconBackArrow, false, onBackButtonClick, "large", handleBackButtonKeyDown)
|
|
419
430
|
}) : null, hasSelectAllButton ? getActionButton(selectButtonLabel, selectButtonLabel, IconCheckRadio, !!isSelectAllButtonDisable, handleSelectAllClick, isDrive ? "huger" : "huge") : null, listDataComponent, isWithFooter ? _jsxs("div", {
|
|
420
431
|
className: "zen-dropdown-list__footer",
|
|
421
432
|
children: [_jsx(Button, {
|
|
@@ -31,5 +31,7 @@ export interface IDropdownPopup extends IZenComponentProps {
|
|
|
31
31
|
checkboxLabel?: string;
|
|
32
32
|
isChecked?: boolean;
|
|
33
33
|
isSearchInPopup?: boolean;
|
|
34
|
+
handleKeydown: (event: React.KeyboardEvent<HTMLDivElement>) => void;
|
|
35
|
+
handleFocusOnSentinelItem?: () => void;
|
|
34
36
|
}
|
|
35
|
-
export declare const DropdownPopup: ({ alignment, triggerRef, classNamePopup, isMobile, inputValue, dialogAriaLabel, disabled, filterName, handleApplyClick, handleClearClick, handleTriggerClick, mobileSheetStackingClassName, onInputChange, hasApplyButton, inputId, isClearButtonDisabled, isWithFooter, placeholder, searchField, isSearchInPopup, isApplyButtonDisabled, isOpenCombo, inputRef, contentRef, children, onReadyForFocus, handleCheckboxChange, checkboxLabel, isChecked, popupId }: IDropdownPopup) => import("react/jsx-runtime").JSX.Element;
|
|
37
|
+
export declare const DropdownPopup: ({ alignment, triggerRef, classNamePopup, isMobile, inputValue, dialogAriaLabel, disabled, filterName, handleApplyClick, handleClearClick, handleTriggerClick, mobileSheetStackingClassName, onInputChange, hasApplyButton, inputId, isClearButtonDisabled, isWithFooter, placeholder, searchField, isSearchInPopup, isApplyButtonDisabled, isOpenCombo, inputRef, contentRef, children, onReadyForFocus, handleCheckboxChange, checkboxLabel, isChecked, popupId, handleKeydown, handleFocusOnSentinelItem }: IDropdownPopup) => import("react/jsx-runtime").JSX.Element;
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import { injectString } from "../utils/localization/translationsDictionary";
|
|
2
|
-
import { jsx as _jsx,
|
|
3
|
-
import { useCallback, useId, useMemo } from "react";
|
|
2
|
+
import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
|
|
3
|
+
import { useCallback, useId, useMemo, useRef } from "react";
|
|
4
4
|
import { MobileSheet } from "../mobileSheet/mobileSheet";
|
|
5
5
|
import { Button } from "../button/button";
|
|
6
6
|
import { ButtonType } from "../button/buttonType";
|
|
@@ -11,6 +11,7 @@ import { useLanguage } from "../utils/localization/useLanguage";
|
|
|
11
11
|
import { FooterButtons } from "../footerButtons/footerButtons";
|
|
12
12
|
import { Checkbox } from "../checkbox/checkbox";
|
|
13
13
|
import { useScrollWithAndroidKeyboard } from "../utils/useScrollWithAndroidKeyboard";
|
|
14
|
+
import { getFirstFocusableItem } from "../utils/keyboardHelpers";
|
|
14
15
|
injectString("cs", "Filter by group", "Filtrovat podle skupiny");
|
|
15
16
|
injectString("da-DK", "Filter by group", "Filtrer efter gruppe");
|
|
16
17
|
injectString("de", "Filter by group", "Nach Gruppe filtern");
|
|
@@ -119,12 +120,16 @@ export const DropdownPopup = ({
|
|
|
119
120
|
handleCheckboxChange,
|
|
120
121
|
checkboxLabel,
|
|
121
122
|
isChecked,
|
|
122
|
-
popupId
|
|
123
|
+
popupId,
|
|
124
|
+
handleKeydown,
|
|
125
|
+
handleFocusOnSentinelItem
|
|
123
126
|
}) => {
|
|
124
127
|
const {
|
|
125
128
|
translate
|
|
126
129
|
} = useLanguage();
|
|
127
130
|
const triggerId = useId();
|
|
131
|
+
const footerButtonsRef = useRef(null);
|
|
132
|
+
const mobileContentRef = useRef(null);
|
|
128
133
|
const {
|
|
129
134
|
handleFocus,
|
|
130
135
|
handleBlur,
|
|
@@ -133,7 +138,22 @@ export const DropdownPopup = ({
|
|
|
133
138
|
const memoizedHandleHide = useCallback(() => {
|
|
134
139
|
handleTriggerClick(false);
|
|
135
140
|
}, [handleTriggerClick]);
|
|
136
|
-
const
|
|
141
|
+
const handleMobileFocusOnSentinelItem = useCallback(() => {
|
|
142
|
+
if (!isMobile) {
|
|
143
|
+
return;
|
|
144
|
+
}
|
|
145
|
+
let nextFocusableElement = footerButtonsRef.current ? getFirstFocusableItem(footerButtonsRef.current) : null;
|
|
146
|
+
if (nextFocusableElement) {
|
|
147
|
+
nextFocusableElement.focus();
|
|
148
|
+
return;
|
|
149
|
+
}
|
|
150
|
+
nextFocusableElement = getFirstFocusableItem(mobileContentRef.current);
|
|
151
|
+
nextFocusableElement === null || nextFocusableElement === void 0 ? void 0 : nextFocusableElement.focus();
|
|
152
|
+
return;
|
|
153
|
+
}, [isMobile, footerButtonsRef, mobileContentRef]);
|
|
154
|
+
const memoizedMobileContent = useMemo(() => _jsxs("div", {
|
|
155
|
+
onKeyDown: handleKeydown,
|
|
156
|
+
ref: mobileContentRef,
|
|
137
157
|
children: [searchField ? _jsx("div", {
|
|
138
158
|
className: "zen-dropdown-mobile-sheet__search-container",
|
|
139
159
|
children: _jsx(SearchInput, {
|
|
@@ -157,13 +177,18 @@ export const DropdownPopup = ({
|
|
|
157
177
|
}) : null, _jsx("div", {
|
|
158
178
|
ref: contentRef,
|
|
159
179
|
children: children
|
|
180
|
+
}), _jsx("div", {
|
|
181
|
+
tabIndex: 0,
|
|
182
|
+
onFocus: handleMobileFocusOnSentinelItem,
|
|
183
|
+
className: "zen-dropdown-list__sentinel-item"
|
|
160
184
|
})]
|
|
161
|
-
}), [searchField, onInputChange, handleBlur, handleFocus, inputValue, inputRef, inputId, triggerId, disabled, placeholder, translate, handleCheckboxChange, isChecked, checkboxLabel, contentRef, children]);
|
|
185
|
+
}), [handleKeydown, searchField, onInputChange, handleBlur, handleFocus, inputValue, inputRef, inputId, triggerId, disabled, placeholder, translate, handleCheckboxChange, isChecked, checkboxLabel, contentRef, children, handleMobileFocusOnSentinelItem]);
|
|
162
186
|
const memoizedMobileFooter = useMemo(() => {
|
|
163
187
|
if (!isWithFooter) {
|
|
164
188
|
return null;
|
|
165
189
|
}
|
|
166
190
|
return _jsxs(FooterButtons, {
|
|
191
|
+
ref: footerButtonsRef,
|
|
167
192
|
children: [hasApplyButton ? _jsx(Button, {
|
|
168
193
|
onClick: handleApplyClick,
|
|
169
194
|
type: ButtonType.Primary,
|
|
@@ -216,6 +241,7 @@ export const DropdownPopup = ({
|
|
|
216
241
|
recalculateOnScroll: true,
|
|
217
242
|
children: _jsxs("div", {
|
|
218
243
|
ref: contentRef,
|
|
244
|
+
onKeyDown: handleKeydown,
|
|
219
245
|
children: [searchField && isSearchInPopup ? _jsx("div", {
|
|
220
246
|
className: "zen-dropdown-popup__search-container",
|
|
221
247
|
children: _jsx(SearchInput, {
|
|
@@ -227,8 +253,12 @@ export const DropdownPopup = ({
|
|
|
227
253
|
disabled: disabled,
|
|
228
254
|
placeholder: placeholder || translate("Filter by group")
|
|
229
255
|
})
|
|
230
|
-
}) : null, children
|
|
256
|
+
}) : null, children, _jsx("div", {
|
|
257
|
+
tabIndex: 0,
|
|
258
|
+
onFocus: handleFocusOnSentinelItem,
|
|
259
|
+
className: "zen-dropdown-list__sentinel-item"
|
|
260
|
+
})]
|
|
231
261
|
})
|
|
232
|
-
}), [alignment, children, classNamePopup, contentRef, dialogAriaLabel, disabled, handleTriggerClick, inputId, inputRef, inputValue, isOpenCombo, isSearchInPopup, onInputChange, placeholder, popupId, searchField, translate, triggerId, triggerRef]);
|
|
262
|
+
}), [alignment, children, classNamePopup, contentRef, dialogAriaLabel, disabled, handleFocusOnSentinelItem, handleKeydown, handleTriggerClick, inputId, inputRef, inputValue, isOpenCombo, isSearchInPopup, onInputChange, placeholder, popupId, searchField, translate, triggerId, triggerRef]);
|
|
233
263
|
return isMobile ? memoizedMobileView : memoizedDesktopView;
|
|
234
264
|
};
|
|
@@ -28,6 +28,8 @@ import { useFormFieldValues } from "../commonHelpers/hooks/useFormFieldValues/us
|
|
|
28
28
|
import { FormSectionContext } from "../formSection/utils/formSectionProvider";
|
|
29
29
|
import { LIST_LIMIT } from "../dropdown/dropdown";
|
|
30
30
|
import { zen } from "../utils/zen";
|
|
31
|
+
import { isChildOf } from "../utils/isChildOf";
|
|
32
|
+
import { getFirstFocusableItem } from "../utils/keyboardHelpers";
|
|
31
33
|
injectString("cs", "Filter by group", "Filtrovat podle skupiny");
|
|
32
34
|
injectString("da-DK", "Filter by group", "Filtrer efter gruppe");
|
|
33
35
|
injectString("de", "Filter by group", "Nach Gruppe filtern");
|
|
@@ -134,6 +136,8 @@ export const DropdownRaw = props => {
|
|
|
134
136
|
const popupId = useId();
|
|
135
137
|
const abortToken = useRef(new AbortController());
|
|
136
138
|
const triggerRef = useRef(null);
|
|
139
|
+
const listElementRef = useRef(null);
|
|
140
|
+
const nextFocusableItemRef = useRef(false);
|
|
137
141
|
const comboboxRef = useRef(null);
|
|
138
142
|
const inputRef = useRef(null);
|
|
139
143
|
const contentRef = useRef(null);
|
|
@@ -301,6 +305,9 @@ export const DropdownRaw = props => {
|
|
|
301
305
|
type: StateActionType.SetCurrentId,
|
|
302
306
|
payload: newCurrentId === state.rootId || state.inputValue ? undefined : newCurrentId
|
|
303
307
|
});
|
|
308
|
+
// const focusableElements = contentRef.current?.querySelectorAll<HTMLElement>(FOCUSABLE_SELECTOR);
|
|
309
|
+
// focusableElements?.[0]?.focus();
|
|
310
|
+
nextFocusableItemRef.current = state.currentId ? `button[data-btn='${state.currentId}']` : true;
|
|
304
311
|
}, [state.currentId, state.groupsMap, state.inputValue, state.rootId]);
|
|
305
312
|
const handleSelect = useCallback(val => {
|
|
306
313
|
if (isFullSelectionMode && state.isAllSelected) {
|
|
@@ -400,11 +407,14 @@ export const DropdownRaw = props => {
|
|
|
400
407
|
});
|
|
401
408
|
}, [isFullSelectionMode, state.isAllSelected, state.listData, state.isNestedList, state.selectedIds]);
|
|
402
409
|
const handleClearClick = useCallback(() => {
|
|
410
|
+
var _a, _b;
|
|
403
411
|
dispatchState({
|
|
404
412
|
type: StateActionType.ResetSelection,
|
|
405
413
|
payload: undefined
|
|
406
414
|
});
|
|
407
|
-
|
|
415
|
+
const focusableElements = (_a = contentRef.current) === null || _a === void 0 ? void 0 : _a.querySelectorAll(FOCUSABLE_SELECTOR);
|
|
416
|
+
(_b = focusableElements === null || focusableElements === void 0 ? void 0 : focusableElements[0]) === null || _b === void 0 ? void 0 : _b.focus();
|
|
417
|
+
}, [contentRef]);
|
|
408
418
|
const handleCancelClick = useCallback(() => {
|
|
409
419
|
dispatchState({
|
|
410
420
|
type: StateActionType.ResetStateToGlobal,
|
|
@@ -664,6 +674,7 @@ export const DropdownRaw = props => {
|
|
|
664
674
|
payload: isChecked
|
|
665
675
|
});
|
|
666
676
|
prevIsChecked.current = isChecked;
|
|
677
|
+
nextFocusableItemRef.current = `.zen-dropdown-list__checkbox-container input`;
|
|
667
678
|
const currentAbort = abortToken.current;
|
|
668
679
|
controlData(currentAbort.signal, state.inputValue, isChecked);
|
|
669
680
|
}, [controlData, state.inputValue]);
|
|
@@ -700,18 +711,27 @@ export const DropdownRaw = props => {
|
|
|
700
711
|
}
|
|
701
712
|
}, [searchField, state.currentId, state.showList, contentRef]);
|
|
702
713
|
useEffect(() => {
|
|
703
|
-
var _a;
|
|
714
|
+
var _a, _b;
|
|
704
715
|
if (!state.isOpenCombo || !state.showList) {
|
|
705
716
|
return;
|
|
706
717
|
}
|
|
707
|
-
|
|
708
|
-
|
|
718
|
+
if (nextFocusableItemRef.current && typeof nextFocusableItemRef.current === "string") {
|
|
719
|
+
const nextFocusable = (_a = contentRef.current) === null || _a === void 0 ? void 0 : _a.querySelector(nextFocusableItemRef.current);
|
|
720
|
+
if (nextFocusable) {
|
|
721
|
+
nextFocusable.focus();
|
|
722
|
+
nextFocusableItemRef.current = false;
|
|
723
|
+
return;
|
|
724
|
+
}
|
|
725
|
+
}
|
|
726
|
+
const firstFocusable = (_b = contentRef.current) === null || _b === void 0 ? void 0 : _b.querySelector(FOCUSABLE_SELECTOR);
|
|
727
|
+
if (firstFocusable && (!searchField || state.currentId || nextFocusableItemRef.current)) {
|
|
728
|
+
nextFocusableItemRef.current = false;
|
|
709
729
|
firstFocusable.focus();
|
|
710
730
|
} else {
|
|
711
731
|
// eslint-disable-next-line @typescript-eslint/no-unnecessary-condition
|
|
712
732
|
(inputRef === null || inputRef === void 0 ? void 0 : inputRef.current) && inputRef.current.focus();
|
|
713
733
|
}
|
|
714
|
-
}, [state.isOpenCombo, state.currentId, state.showList, searchField]);
|
|
734
|
+
}, [state.isOpenCombo, state.currentId, state.showList, searchField, contentRef]);
|
|
715
735
|
useEffect(() => {
|
|
716
736
|
const shouldExit = !getNamedItems || Object.keys(state.groupsMap).length === 0 && Object.keys(state.groupsMapSelected).length === 0 || getNamedItemsHasBeenCalled.current || state.groupsMapSelected.size === 0;
|
|
717
737
|
if (shouldExit) {
|
|
@@ -743,6 +763,57 @@ export const DropdownRaw = props => {
|
|
|
743
763
|
return currentAllSelected !== undefined ? state.defaultValueIsAllSelected === currentAllSelected && isStringsTheSame && isCheckedEqualDefault : isStringsTheSame && isCheckedEqualDefault;
|
|
744
764
|
}, [currentAllSelected, currentIsChecked, forceSelection, multiselect, state.defaultValue, state.defaultValueIsAllSelected, state.defaultValueIsChecked, state.selectedIds]);
|
|
745
765
|
const memoizedIsApplyButtonDisabled = useMemo(() => compareStringsArrays(state.globalSelectedIds, state.selectedIds) && (isFullSelectionMode ? state.globalIsAllSelected === state.isAllSelected : true) && (isCheckboxMode ? state.globalIsChecked === state.isChecked : true), [isCheckboxMode, isFullSelectionMode, state.globalIsAllSelected, state.globalIsChecked, state.globalSelectedIds, state.isAllSelected, state.isChecked, state.selectedIds]);
|
|
766
|
+
const handleKeydown = useCallback(e => {
|
|
767
|
+
const isChildOfListElements = listElementRef.current && e.target instanceof Node ? isChildOf(e.target, listElementRef.current) : false;
|
|
768
|
+
if (isChildOfListElements) {
|
|
769
|
+
return;
|
|
770
|
+
}
|
|
771
|
+
if (e.key === "ArrowDown" || e.key === "ArrowUp") {
|
|
772
|
+
if (!contentRef.current) {
|
|
773
|
+
return;
|
|
774
|
+
}
|
|
775
|
+
const focusableElements = contentRef.current.querySelectorAll(FOCUSABLE_SELECTOR);
|
|
776
|
+
if (focusableElements.length === 0) {
|
|
777
|
+
return;
|
|
778
|
+
}
|
|
779
|
+
const currentIndex = Array.from(focusableElements).indexOf(e.target);
|
|
780
|
+
let nextIndex;
|
|
781
|
+
// eslint-disable-next-line @typescript-eslint/no-unnecessary-condition
|
|
782
|
+
if (currentIndex === 0 && e.key === "ArrowUp" && inputRef.current) {
|
|
783
|
+
inputRef.current.focus();
|
|
784
|
+
return;
|
|
785
|
+
}
|
|
786
|
+
if (e.key === "ArrowDown") {
|
|
787
|
+
e.preventDefault();
|
|
788
|
+
nextIndex = currentIndex === -1 ? 0 : (currentIndex + 1) % focusableElements.length;
|
|
789
|
+
} else {
|
|
790
|
+
e.preventDefault();
|
|
791
|
+
nextIndex = currentIndex === -1 ? focusableElements.length - 1 : (currentIndex - 1 + focusableElements.length) % focusableElements.length;
|
|
792
|
+
}
|
|
793
|
+
focusableElements[nextIndex].focus();
|
|
794
|
+
}
|
|
795
|
+
}, []);
|
|
796
|
+
const handleFocusOnSentinelItem = useCallback(() => {
|
|
797
|
+
var _a;
|
|
798
|
+
if (isMobile) {
|
|
799
|
+
return;
|
|
800
|
+
}
|
|
801
|
+
const firstFocusable = getFirstFocusableItem(contentRef.current);
|
|
802
|
+
if (firstFocusable && listElementRef.current && isChildOf(firstFocusable, listElementRef.current)) {
|
|
803
|
+
// eslint-disable-next-line @typescript-eslint/no-unnecessary-condition
|
|
804
|
+
(_a = inputRef.current) === null || _a === void 0 ? void 0 : _a.focus();
|
|
805
|
+
} else {
|
|
806
|
+
firstFocusable === null || firstFocusable === void 0 ? void 0 : firstFocusable.focus();
|
|
807
|
+
}
|
|
808
|
+
}, [contentRef, isMobile, listElementRef]);
|
|
809
|
+
const handleFocusOnPopup = useCallback(() => {
|
|
810
|
+
var _a;
|
|
811
|
+
if (!state.showList) {
|
|
812
|
+
return;
|
|
813
|
+
}
|
|
814
|
+
const firstFocusable = (_a = contentRef.current) === null || _a === void 0 ? void 0 : _a.querySelector(FOCUSABLE_SELECTOR);
|
|
815
|
+
firstFocusable === null || firstFocusable === void 0 ? void 0 : firstFocusable.focus();
|
|
816
|
+
}, [state.showList, contentRef]);
|
|
746
817
|
const countSelected = useMemo(() => {
|
|
747
818
|
var _a, _b;
|
|
748
819
|
if (hasApplyButton && state.globalIsAllSelected || !hasApplyButton && state.isAllSelected) {
|
|
@@ -812,7 +883,8 @@ export const DropdownRaw = props => {
|
|
|
812
883
|
isMobile: isMobile,
|
|
813
884
|
handleCheckboxChange: isCheckboxMode && !isMobile ? handleCheckboxChange : undefined,
|
|
814
885
|
checkboxLabel: checkboxLabel,
|
|
815
|
-
isChecked: state.isChecked
|
|
886
|
+
isChecked: state.isChecked,
|
|
887
|
+
listElementRef: listElementRef
|
|
816
888
|
});
|
|
817
889
|
}
|
|
818
890
|
return null;
|
|
@@ -862,7 +934,8 @@ export const DropdownRaw = props => {
|
|
|
862
934
|
triggerRef: triggerRef,
|
|
863
935
|
inputRef: inputRef,
|
|
864
936
|
buttonType: buttonType,
|
|
865
|
-
popupId: popupId
|
|
937
|
+
popupId: popupId,
|
|
938
|
+
handleFocusOnPopup: handleFocusOnPopup
|
|
866
939
|
}, accessibilityProps)), _jsx(DropdownPopup, {
|
|
867
940
|
alignment: alignment,
|
|
868
941
|
triggerRef: triggerRef,
|
|
@@ -885,6 +958,7 @@ export const DropdownRaw = props => {
|
|
|
885
958
|
handleClearClick: multiselect ? handleClearClick : handleSingleSelection.bind(this, true),
|
|
886
959
|
handleTriggerClick: handleTriggerClick,
|
|
887
960
|
onInputChange: onInputChange,
|
|
961
|
+
handleKeydown: handleKeydown,
|
|
888
962
|
inputRef: inputRef,
|
|
889
963
|
contentRef: contentRef,
|
|
890
964
|
onReadyForFocus: handleReadyForFocus,
|
|
@@ -893,6 +967,7 @@ export const DropdownRaw = props => {
|
|
|
893
967
|
isChecked: state.isChecked,
|
|
894
968
|
isSearchInPopup: chip,
|
|
895
969
|
mobileSheetStackingClassName: mobileSheetStackingClassName,
|
|
970
|
+
handleFocusOnSentinelItem: handleFocusOnSentinelItem,
|
|
896
971
|
children: getPopupContent
|
|
897
972
|
})]
|
|
898
973
|
});
|
|
@@ -20,9 +20,10 @@ interface IDropdownSearchableTrigger {
|
|
|
20
20
|
name?: string;
|
|
21
21
|
onBlur?: () => void;
|
|
22
22
|
popupId?: string;
|
|
23
|
+
handleFocusOnPopup?: () => void;
|
|
23
24
|
}
|
|
24
25
|
export declare const DropdownSearchableTrigger: {
|
|
25
|
-
({ value, className, onChange, placeholder, isOpenPopup, inputRef, handleClick, width, title, id, disabled, count, currentSelection, isError, fullWidth, ref, name, onBlur, popupId, ...otherProps }: IDropdownSearchableTrigger): import("react/jsx-runtime").JSX.Element;
|
|
26
|
+
({ value, className, onChange, placeholder, isOpenPopup, inputRef, handleClick, width, title, id, disabled, count, currentSelection, isError, fullWidth, ref, name, onBlur, popupId, handleFocusOnPopup, ...otherProps }: IDropdownSearchableTrigger): import("react/jsx-runtime").JSX.Element;
|
|
26
27
|
displayName: string;
|
|
27
28
|
};
|
|
28
29
|
export declare const TRANSLATIONS: string[];
|