@itwin/itwinui-react 2.8.2 → 2.9.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.
Files changed (54) hide show
  1. package/CHANGELOG.md +22 -0
  2. package/cjs/core/ColorPicker/ColorBuilder.js +3 -0
  3. package/cjs/core/ColorPicker/ColorPalette.js +3 -0
  4. package/cjs/core/ComboBox/ComboBox.js +6 -0
  5. package/cjs/core/ComboBox/ComboBoxInput.js +17 -16
  6. package/cjs/core/ComboBox/ComboBoxMenuItem.js +1 -1
  7. package/cjs/core/DatePicker/DatePicker.js +3 -0
  8. package/cjs/core/Dialog/DialogMain.js +3 -0
  9. package/cjs/core/ExpandableBlock/ExpandableBlock.js +3 -0
  10. package/cjs/core/List/List.d.ts +6 -0
  11. package/cjs/core/List/List.js +19 -0
  12. package/cjs/core/List/ListItem.d.ts +79 -0
  13. package/cjs/core/List/ListItem.js +77 -0
  14. package/cjs/core/List/index.d.ts +4 -0
  15. package/cjs/core/List/index.js +11 -0
  16. package/cjs/core/Menu/Menu.js +3 -0
  17. package/cjs/core/Select/Select.js +3 -0
  18. package/cjs/core/Stepper/StepperStep.js +3 -0
  19. package/cjs/core/Table/filters/DateRangeFilter/DateRangeFilter.js +3 -0
  20. package/cjs/core/Table/filters/NumberRangeFilter/NumberRangeFilter.js +3 -0
  21. package/cjs/core/Table/filters/TextFilter/TextFilter.js +3 -0
  22. package/cjs/core/TimePicker/TimePicker.js +3 -0
  23. package/cjs/core/Tree/Tree.js +3 -0
  24. package/cjs/core/Tree/TreeNode.js +3 -0
  25. package/cjs/core/index.d.ts +2 -0
  26. package/cjs/core/index.js +6 -3
  27. package/cjs/core/utils/components/Popover.js +4 -1
  28. package/esm/core/ColorPicker/ColorBuilder.js +3 -0
  29. package/esm/core/ColorPicker/ColorPalette.js +3 -0
  30. package/esm/core/ComboBox/ComboBox.js +6 -0
  31. package/esm/core/ComboBox/ComboBoxInput.js +17 -16
  32. package/esm/core/ComboBox/ComboBoxMenuItem.js +1 -1
  33. package/esm/core/DatePicker/DatePicker.js +3 -0
  34. package/esm/core/Dialog/DialogMain.js +3 -0
  35. package/esm/core/ExpandableBlock/ExpandableBlock.js +3 -0
  36. package/esm/core/List/List.d.ts +6 -0
  37. package/esm/core/List/List.js +13 -0
  38. package/esm/core/List/ListItem.d.ts +79 -0
  39. package/esm/core/List/ListItem.js +71 -0
  40. package/esm/core/List/index.d.ts +4 -0
  41. package/esm/core/List/index.js +6 -0
  42. package/esm/core/Menu/Menu.js +3 -0
  43. package/esm/core/Select/Select.js +3 -0
  44. package/esm/core/Stepper/StepperStep.js +3 -0
  45. package/esm/core/Table/filters/DateRangeFilter/DateRangeFilter.js +3 -0
  46. package/esm/core/Table/filters/NumberRangeFilter/NumberRangeFilter.js +3 -0
  47. package/esm/core/Table/filters/TextFilter/TextFilter.js +3 -0
  48. package/esm/core/TimePicker/TimePicker.js +3 -0
  49. package/esm/core/Tree/Tree.js +3 -0
  50. package/esm/core/Tree/TreeNode.js +3 -0
  51. package/esm/core/index.d.ts +2 -0
  52. package/esm/core/index.js +1 -0
  53. package/esm/core/utils/components/Popover.js +4 -1
  54. package/package.json +2 -2
package/CHANGELOG.md CHANGED
@@ -1,5 +1,27 @@
1
1
  # Changelog
2
2
 
3
+ ## 2.9.0
4
+
5
+ ### Minor Changes
6
+
7
+ - [#1106](https://github.com/iTwin/iTwinUI/pull/1106): Added new List and ListItem components.
8
+
9
+ ```jsx
10
+ <List>
11
+ <ListItem>item 1</ListItem>
12
+ <ListItem>item 2</ListItem>
13
+ <ListItem>item 3</ListItem>
14
+ </List>
15
+ ```
16
+
17
+ ### Patch Changes
18
+
19
+ - [#1210](https://github.com/iTwin/iTwinUI/pull/1210): Removed incorrect `role=tooltip` from Popover, DropdownMenu, Select and ComboBox.
20
+ - [#1209](https://github.com/iTwin/iTwinUI/pull/1209): Fixed an issue in ComboBox where disabled items didn't have a proper focus outline and were still selectable with keyboard.
21
+ - [#1149](https://github.com/iTwin/iTwinUI/pull/1149): added event.altKey to file with handleKeyDown and onKeyDown function
22
+ - Updated dependencies:
23
+ - @itwin/itwinui-css@1.10.0
24
+
3
25
  ## 2.8.2
4
26
 
5
27
  ### Patch Changes
@@ -121,6 +121,9 @@ exports.ColorBuilder = react_1.default.forwardRef((props, ref) => {
121
121
  const keysPressed = react_1.default.useRef({}); // keep track of which keys are currently pressed
122
122
  // Arrow key navigation for color dot
123
123
  const handleColorDotKeyDown = (event) => {
124
+ if (event.altKey) {
125
+ return;
126
+ }
124
127
  let x = squareLeft;
125
128
  let y = squareTop;
126
129
  keysPressed.current[event.key] = true;
@@ -42,6 +42,9 @@ exports.ColorPalette = react_1.default.forwardRef((props, ref) => {
42
42
  const paletteRefs = (0, utils_1.useMergedRefs)(paletteRef, setDefaultTabIndex);
43
43
  // Color palette arrow key navigation
44
44
  const handleKeyDown = (event) => {
45
+ if (event.altKey) {
46
+ return;
47
+ }
45
48
  const swatches = (0, utils_1.getFocusableElements)(paletteRef.current);
46
49
  if (!swatches.length) {
47
50
  return;
@@ -218,6 +218,11 @@ const ComboBox = (props) => {
218
218
  }
219
219
  }, [multiple, onChangeProp, optionsRef]);
220
220
  const onClickHandler = react_1.default.useCallback((__originalIndex) => {
221
+ var _a, _b;
222
+ (_a = inputRef.current) === null || _a === void 0 ? void 0 : _a.focus({ preventScroll: true }); // return focus to input
223
+ if ((_b = optionsRef.current[__originalIndex]) === null || _b === void 0 ? void 0 : _b.disabled) {
224
+ return;
225
+ }
221
226
  if (isMultipleEnabled(selected, multiple)) {
222
227
  const actionType = isMenuItemSelected(__originalIndex)
223
228
  ? 'removed'
@@ -237,6 +242,7 @@ const ComboBox = (props) => {
237
242
  multiple,
238
243
  onChangeHandler,
239
244
  selected,
245
+ optionsRef,
240
246
  ]);
241
247
  const getMenuItem = react_1.default.useCallback((option, filteredIndex) => {
242
248
  const optionId = getOptionId(option, id);
@@ -14,7 +14,7 @@ const utils_1 = require("../utils");
14
14
  const ComboBoxMultipleContainer_1 = require("./ComboBoxMultipleContainer");
15
15
  const helpers_1 = require("./helpers");
16
16
  exports.ComboBoxInput = react_1.default.forwardRef((props, forwardedRef) => {
17
- const { onKeyDown: onKeyDownProp, onFocus: onFocusProp, selectTags, ...rest } = props;
17
+ const { onKeyDown: onKeyDownProp, onFocus: onFocusProp, onClick: onClickProp, selectTags, ...rest } = props;
18
18
  const { isOpen, id, focusedIndex, enableVirtualization, multiple, onClickHandler, } = (0, utils_1.useSafeContext)(helpers_1.ComboBoxStateContext);
19
19
  const dispatch = (0, utils_1.useSafeContext)(helpers_1.ComboBoxActionContext);
20
20
  const { inputRef, menuRef, optionsExtraInfoRef } = (0, utils_1.useSafeContext)(helpers_1.ComboBoxRefsContext);
@@ -31,6 +31,9 @@ exports.ComboBoxInput = react_1.default.forwardRef((props, forwardedRef) => {
31
31
  var _a, _b, _c, _d, _e, _f, _g, _h, _j, _k, _l, _m, _o, _p, _q;
32
32
  onKeyDownProp === null || onKeyDownProp === void 0 ? void 0 : onKeyDownProp(event);
33
33
  const length = (_a = Object.keys(optionsExtraInfoRef.current).length) !== null && _a !== void 0 ? _a : 0;
34
+ if (event.altKey) {
35
+ return;
36
+ }
34
37
  switch (event.key) {
35
38
  case 'ArrowDown': {
36
39
  event.preventDefault();
@@ -57,7 +60,7 @@ exports.ComboBoxInput = react_1.default.forwardRef((props, forwardedRef) => {
57
60
  const currentElement = (_f = menuRef.current) === null || _f === void 0 ? void 0 : _f.querySelector(`[data-iui-index="${nextIndex}"]`);
58
61
  const nextElement = (_g = currentElement === null || currentElement === void 0 ? void 0 : currentElement.nextElementSibling) !== null && _g !== void 0 ? _g : (_h = menuRef.current) === null || _h === void 0 ? void 0 : _h.querySelector('[data-iui-index]');
59
62
  nextIndex = Number(nextElement === null || nextElement === void 0 ? void 0 : nextElement.getAttribute('data-iui-index'));
60
- if ((nextElement === null || nextElement === void 0 ? void 0 : nextElement.ariaDisabled) !== 'true') {
63
+ if (nextElement) {
61
64
  return dispatch({ type: 'focus', value: nextIndex });
62
65
  }
63
66
  } while (nextIndex !== focusedIndexRef.current);
@@ -87,7 +90,7 @@ exports.ComboBoxInput = react_1.default.forwardRef((props, forwardedRef) => {
87
90
  const currentElement = (_o = menuRef.current) === null || _o === void 0 ? void 0 : _o.querySelector(`[data-iui-index="${prevIndex}"]`);
88
91
  const prevElement = (_p = currentElement === null || currentElement === void 0 ? void 0 : currentElement.previousElementSibling) !== null && _p !== void 0 ? _p : (_q = menuRef.current) === null || _q === void 0 ? void 0 : _q.querySelector('[data-iui-index]:last-of-type');
89
92
  prevIndex = Number(prevElement === null || prevElement === void 0 ? void 0 : prevElement.getAttribute('data-iui-index'));
90
- if ((prevElement === null || prevElement === void 0 ? void 0 : prevElement.ariaDisabled) !== 'true') {
93
+ if (prevElement) {
91
94
  return dispatch({ type: 'focus', value: prevIndex });
92
95
  }
93
96
  } while (prevIndex !== focusedIndexRef.current);
@@ -96,18 +99,8 @@ exports.ComboBoxInput = react_1.default.forwardRef((props, forwardedRef) => {
96
99
  case 'Enter': {
97
100
  event.preventDefault();
98
101
  if (isOpen) {
99
- if (multiple) {
100
- // Keep menu open when multiselect is enabled and user selects an item
101
- if (focusedIndexRef.current > -1) {
102
- onClickHandler === null || onClickHandler === void 0 ? void 0 : onClickHandler(focusedIndexRef.current);
103
- }
104
- else {
105
- dispatch({ type: 'close' });
106
- }
107
- }
108
- else {
102
+ if (focusedIndexRef.current > -1) {
109
103
  onClickHandler === null || onClickHandler === void 0 ? void 0 : onClickHandler(focusedIndexRef.current);
110
- dispatch({ type: 'close' });
111
104
  }
112
105
  }
113
106
  else {
@@ -129,7 +122,6 @@ exports.ComboBoxInput = react_1.default.forwardRef((props, forwardedRef) => {
129
122
  enableVirtualization,
130
123
  isOpen,
131
124
  menuRef,
132
- multiple,
133
125
  onClickHandler,
134
126
  onKeyDownProp,
135
127
  optionsExtraInfoRef,
@@ -138,9 +130,18 @@ exports.ComboBoxInput = react_1.default.forwardRef((props, forwardedRef) => {
138
130
  dispatch({ type: 'open' });
139
131
  onFocusProp === null || onFocusProp === void 0 ? void 0 : onFocusProp(event);
140
132
  }, [dispatch, onFocusProp]);
133
+ const handleClick = react_1.default.useCallback((e) => {
134
+ onClickProp === null || onClickProp === void 0 ? void 0 : onClickProp(e);
135
+ if (e.isDefaultPrevented()) {
136
+ return;
137
+ }
138
+ if (!isOpen) {
139
+ dispatch({ type: 'open' });
140
+ }
141
+ }, [dispatch, isOpen, onClickProp]);
141
142
  const [tagContainerWidthRef, tagContainerWidth] = (0, utils_1.useContainerWidth)();
142
143
  return (react_1.default.createElement(react_1.default.Fragment, null,
143
- react_1.default.createElement(Input_1.Input, { ref: refs, onKeyDown: handleKeyDown, onFocus: handleFocus, "aria-activedescendant": isOpen && focusedIndex != undefined && focusedIndex > -1
144
+ react_1.default.createElement(Input_1.Input, { ref: refs, onKeyDown: handleKeyDown, onClick: handleClick, onFocus: handleFocus, "aria-activedescendant": isOpen && focusedIndex != undefined && focusedIndex > -1
144
145
  ? getIdFromIndex(focusedIndex)
145
146
  : undefined, role: 'combobox', "aria-controls": isOpen ? `${id}-list` : undefined, "aria-autocomplete": 'list', spellCheck: false, autoCapitalize: 'none', autoCorrect: 'off', style: multiple ? { paddingLeft: tagContainerWidth + 18 } : {}, ...rest }),
146
147
  multiple && selectTags && (react_1.default.createElement(ComboBoxMultipleContainer_1.ComboBoxMultipleContainer, { ref: tagContainerWidthRef, selectedItems: selectTags }))));
@@ -26,7 +26,7 @@ exports.ComboBoxMenuItem = react_1.default.memo(react_1.default.forwardRef((prop
26
26
  'iui-active': isSelected,
27
27
  'iui-disabled': disabled,
28
28
  'iui-focused': focusedIndex === index,
29
- }, className), ref: refs, onClick: () => !disabled && (onClick === null || onClick === void 0 ? void 0 : onClick(value)), role: role, tabIndex: disabled || role === 'presentation' ? undefined : -1, "aria-selected": isSelected, "aria-disabled": disabled, "data-iui-index": index, ...rest },
29
+ }, className), ref: refs, onClick: () => onClick === null || onClick === void 0 ? void 0 : onClick(value), role: role, tabIndex: role === 'presentation' ? undefined : -1, "aria-selected": isSelected, "aria-disabled": disabled, "data-iui-index": index, ...rest },
30
30
  icon &&
31
31
  react_1.default.cloneElement(icon, {
32
32
  className: (0, classnames_1.default)(icon.props.className, 'iui-icon'),
@@ -272,6 +272,9 @@ const DatePicker = (props) => {
272
272
  const isPreviousYearDisabled = isDateDisabled === null || isDateDisabled === void 0 ? void 0 : isDateDisabled(new Date(displayedYear - 1, 11, 31));
273
273
  const isNextYearDisabled = isDateDisabled === null || isDateDisabled === void 0 ? void 0 : isDateDisabled(new Date(displayedYear + 1, 0, 1));
274
274
  const handleCalendarKeyDown = (event) => {
275
+ if (event.altKey) {
276
+ return;
277
+ }
275
278
  if (!focusedDay) {
276
279
  return;
277
280
  }
@@ -73,6 +73,9 @@ exports.DialogMain = react_1.default.forwardRef((props, ref) => {
73
73
  };
74
74
  }, [isOpen, preventDocumentScroll]);
75
75
  const handleKeyDown = (event) => {
76
+ if (event.altKey) {
77
+ return;
78
+ }
76
79
  // Prevents React from resetting its properties
77
80
  event.persist();
78
81
  if (isDismissible && closeOnEsc && event.key === 'Escape' && onClose) {
@@ -34,6 +34,9 @@ const ExpandableBlock = (props) => {
34
34
  onToggle === null || onToggle === void 0 ? void 0 : onToggle(!expanded);
35
35
  };
36
36
  const onKeyDown = (event) => {
37
+ if (event.altKey) {
38
+ return;
39
+ }
37
40
  if (event.key === 'Enter' ||
38
41
  event.key === ' ' ||
39
42
  event.key === 'Spacebar') {
@@ -0,0 +1,6 @@
1
+ import type { PolymorphicForwardRefComponent, PolymorphicComponentProps } from '../utils';
2
+ import '@itwin/itwinui-css/css/menu.css';
3
+ export declare const List: PolymorphicForwardRefComponent<"ul", ListOwnProps>;
4
+ declare type ListOwnProps = {};
5
+ export declare type ListProps = PolymorphicComponentProps<'ul', ListOwnProps>;
6
+ export {};
@@ -0,0 +1,19 @@
1
+ "use strict";
2
+ var __importDefault = (this && this.__importDefault) || function (mod) {
3
+ return (mod && mod.__esModule) ? mod : { "default": mod };
4
+ };
5
+ Object.defineProperty(exports, "__esModule", { value: true });
6
+ exports.List = void 0;
7
+ /*---------------------------------------------------------------------------------------------
8
+ * Copyright (c) Bentley Systems, Incorporated. All rights reserved.
9
+ * See LICENSE.md in the project root for license terms and full copyright notice.
10
+ *--------------------------------------------------------------------------------------------*/
11
+ const react_1 = __importDefault(require("react"));
12
+ const classnames_1 = __importDefault(require("classnames"));
13
+ const utils_1 = require("../utils");
14
+ require("@itwin/itwinui-css/css/menu.css");
15
+ exports.List = react_1.default.forwardRef((props, ref) => {
16
+ const { as: Element = 'ul', className, ...rest } = props;
17
+ (0, utils_1.useTheme)();
18
+ return (react_1.default.createElement(Element, { className: (0, classnames_1.default)('iui-list', className), ref: ref, role: 'list', ...rest }));
19
+ });
@@ -0,0 +1,79 @@
1
+ import type { PolymorphicForwardRefComponent, PolymorphicComponentProps } from '../utils';
2
+ import '@itwin/itwinui-css/css/menu.css';
3
+ declare type ListItemOwnProps = {
4
+ /**
5
+ * Size of the ListItem. Can be explicitly specified to be 'large',
6
+ * but if a description is included in addition to the label, then
7
+ * it will automatically become large.
8
+ */
9
+ size?: 'default' | 'large';
10
+ /**
11
+ * If true, the ListItem has disabled (dimmed) styling.
12
+ */
13
+ disabled?: boolean;
14
+ /**
15
+ * If true, the ListItem has active (selected) styling.
16
+ */
17
+ active?: boolean;
18
+ /**
19
+ * If true, the ListItem will get actionable styling, such as hover styling and cursor.
20
+ */
21
+ actionable?: boolean;
22
+ /**
23
+ * If true, the ListItem has focus styling.
24
+ *
25
+ * By default, focus styling is automatically applied if the item is
26
+ * focused, or if the item contains a `LinkAction` and it is focused.
27
+ * This prop is useful for custom focus management (e.g. using `aria-activedescendant`).
28
+ */
29
+ focused?: boolean;
30
+ };
31
+ declare type ListItemIconOwnProps = {};
32
+ declare type ListItemContentOwnProps = {};
33
+ declare type ListItemDescriptionOwnProps = {};
34
+ /**
35
+ * A generic ListItem component that can be used simply for displaying data, or as a base
36
+ * for the list items in a more complex component (e.g. a custom Select).
37
+ *
38
+ * Includes support for left/right icons, multiple lines of text, and hover/focus/active/disabled styling.
39
+ *
40
+ * @example
41
+ * <List>
42
+ * <ListItem>item 1</ListItem>
43
+ * <ListItem>item 2</ListItem>
44
+ * <ListItem>item 3</ListItem>
45
+ * </List>
46
+ */
47
+ export declare const ListItem: PolymorphicForwardRefComponent<"li", ListItemOwnProps> & {
48
+ /**
49
+ * Icon to be placed at the beginning or end of the ListItem.
50
+ */
51
+ Icon: PolymorphicForwardRefComponent<"div", ListItemIconOwnProps>;
52
+ /**
53
+ * Wrapper for the main content of the ListItem.
54
+ *
55
+ * For basic list items, this wrapper is not needed, but it can be useful for two cases:
56
+ * - When using an end icon. The `ListItem.Content` will fill the available space
57
+ * and push the icon to the end
58
+ * - When using `ListItem.Description`.
59
+ */
60
+ Content: PolymorphicForwardRefComponent<"div", ListItemContentOwnProps>;
61
+ /**
62
+ * Description to be used in addition to the main label of the ListItem.
63
+ * Should be used as a child of `ListItem.Content`.
64
+ *
65
+ * @example
66
+ * <ListItem>
67
+ * <ListItem.Content>
68
+ * <div>some list item</div>
69
+ * <ListItem.Description>description for this item</ListItem.Description>
70
+ * </ListItem.Content>
71
+ * </ListItem>
72
+ */
73
+ Description: PolymorphicForwardRefComponent<"div", ListItemDescriptionOwnProps>;
74
+ };
75
+ export declare type ListItemProps = PolymorphicComponentProps<'li', ListItemOwnProps>;
76
+ export declare type ListItemIconProps = PolymorphicComponentProps<'li', ListItemIconOwnProps>;
77
+ export declare type ListItemContentProps = PolymorphicComponentProps<'li', ListItemContentOwnProps>;
78
+ export declare type ListItemDescriptionProps = PolymorphicComponentProps<'li', ListItemDescriptionOwnProps>;
79
+ export {};
@@ -0,0 +1,77 @@
1
+ "use strict";
2
+ var __importDefault = (this && this.__importDefault) || function (mod) {
3
+ return (mod && mod.__esModule) ? mod : { "default": mod };
4
+ };
5
+ Object.defineProperty(exports, "__esModule", { value: true });
6
+ exports.ListItem = void 0;
7
+ /*---------------------------------------------------------------------------------------------
8
+ * Copyright (c) Bentley Systems, Incorporated. All rights reserved.
9
+ * See LICENSE.md in the project root for license terms and full copyright notice.
10
+ *--------------------------------------------------------------------------------------------*/
11
+ const react_1 = __importDefault(require("react"));
12
+ const classnames_1 = __importDefault(require("classnames"));
13
+ const utils_1 = require("../utils");
14
+ require("@itwin/itwinui-css/css/menu.css");
15
+ const ListItemComponent = react_1.default.forwardRef((props, ref) => {
16
+ const { as: Element = 'li', size = 'default', disabled = false, active = false, actionable = false, focused = false, className, ...rest } = props;
17
+ (0, utils_1.useTheme)();
18
+ return (react_1.default.createElement(Element, { className: (0, classnames_1.default)('iui-list-item', className), "data-iui-active": active ? 'true' : undefined, "data-iui-disabled": disabled ? 'true' : undefined, "data-iui-size": size === 'large' ? 'large' : undefined, "data-iui-actionable": actionable ? 'true' : undefined, "data-iui-focused": focused ? 'true' : undefined, ref: ref, ...rest }));
19
+ });
20
+ // ----------------------------------------------------------------------------
21
+ const ListItemIcon = react_1.default.forwardRef((props, ref) => {
22
+ const { as: Element = 'div', className, ...rest } = props;
23
+ return (react_1.default.createElement(Element, { className: (0, classnames_1.default)('iui-list-item-icon', className), ref: ref, ...rest }));
24
+ });
25
+ // ----------------------------------------------------------------------------
26
+ const ListItemContent = react_1.default.forwardRef((props, ref) => {
27
+ const { as: Element = 'div', className, ...rest } = props;
28
+ return (react_1.default.createElement(Element, { className: (0, classnames_1.default)('iui-list-item-content', className), ref: ref, ...rest }));
29
+ });
30
+ // ----------------------------------------------------------------------------
31
+ const ListItemDescription = react_1.default.forwardRef((props, ref) => {
32
+ const { as: Element = 'div', className, ...rest } = props;
33
+ return (react_1.default.createElement(Element, { className: (0, classnames_1.default)('iui-list-item-description', className), ref: ref, ...rest }));
34
+ });
35
+ // ----------------------------------------------------------------------------
36
+ // Exported compound component
37
+ /**
38
+ * A generic ListItem component that can be used simply for displaying data, or as a base
39
+ * for the list items in a more complex component (e.g. a custom Select).
40
+ *
41
+ * Includes support for left/right icons, multiple lines of text, and hover/focus/active/disabled styling.
42
+ *
43
+ * @example
44
+ * <List>
45
+ * <ListItem>item 1</ListItem>
46
+ * <ListItem>item 2</ListItem>
47
+ * <ListItem>item 3</ListItem>
48
+ * </List>
49
+ */
50
+ exports.ListItem = Object.assign(ListItemComponent, {
51
+ /**
52
+ * Icon to be placed at the beginning or end of the ListItem.
53
+ */
54
+ Icon: ListItemIcon,
55
+ /**
56
+ * Wrapper for the main content of the ListItem.
57
+ *
58
+ * For basic list items, this wrapper is not needed, but it can be useful for two cases:
59
+ * - When using an end icon. The `ListItem.Content` will fill the available space
60
+ * and push the icon to the end
61
+ * - When using `ListItem.Description`.
62
+ */
63
+ Content: ListItemContent,
64
+ /**
65
+ * Description to be used in addition to the main label of the ListItem.
66
+ * Should be used as a child of `ListItem.Content`.
67
+ *
68
+ * @example
69
+ * <ListItem>
70
+ * <ListItem.Content>
71
+ * <div>some list item</div>
72
+ * <ListItem.Description>description for this item</ListItem.Description>
73
+ * </ListItem.Content>
74
+ * </ListItem>
75
+ */
76
+ Description: ListItemDescription,
77
+ });
@@ -0,0 +1,4 @@
1
+ export { List } from './List';
2
+ export type { ListProps } from './List';
3
+ export { ListItem } from './ListItem';
4
+ export type { ListItemProps, ListItemIconProps, ListItemContentProps, ListItemDescriptionProps, } from './ListItem';
@@ -0,0 +1,11 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.ListItem = exports.List = void 0;
4
+ /*---------------------------------------------------------------------------------------------
5
+ * Copyright (c) Bentley Systems, Incorporated. All rights reserved.
6
+ * See LICENSE.md in the project root for license terms and full copyright notice.
7
+ *--------------------------------------------------------------------------------------------*/
8
+ var List_1 = require("./List");
9
+ Object.defineProperty(exports, "List", { enumerable: true, get: function () { return List_1.List; } });
10
+ var ListItem_1 = require("./ListItem");
11
+ Object.defineProperty(exports, "ListItem", { enumerable: true, get: function () { return ListItem_1.ListItem; } });
@@ -39,6 +39,9 @@ exports.Menu = react_1.default.forwardRef((props, ref) => {
39
39
  }
40
40
  }, [setFocus, focusedIndex, getFocusableNodes]);
41
41
  const onKeyDown = (event) => {
42
+ if (event.altKey) {
43
+ return;
44
+ }
42
45
  const items = getFocusableNodes();
43
46
  if (!(items === null || items === void 0 ? void 0 : items.length)) {
44
47
  return;
@@ -103,6 +103,9 @@ const Select = (props) => {
103
103
  }
104
104
  }, [isOpen]);
105
105
  const onKeyDown = (event, toggle) => {
106
+ if (event.altKey) {
107
+ return;
108
+ }
106
109
  switch (event.key) {
107
110
  case 'Enter':
108
111
  case ' ':
@@ -22,6 +22,9 @@ const StepperStep = (props) => {
22
22
  }
23
23
  };
24
24
  const onKeyDown = (e) => {
25
+ if (e.altKey) {
26
+ return;
27
+ }
25
28
  if (!isClickable) {
26
29
  return;
27
30
  }
@@ -57,6 +57,9 @@ const DateRangeFilter = (props) => {
57
57
  });
58
58
  }, []);
59
59
  const onKeyDown = (event) => {
60
+ if (event.altKey) {
61
+ return;
62
+ }
60
63
  if (event.key === 'Enter') {
61
64
  setFilter([from, to]);
62
65
  }
@@ -29,6 +29,9 @@ const NumberRangeFilter = (props) => {
29
29
  return !value || isNaN(Number(value)) ? undefined : Number(value);
30
30
  };
31
31
  const onKeyDown = (event) => {
32
+ if (event.altKey) {
33
+ return;
34
+ }
32
35
  if (event.key === 'Enter') {
33
36
  setFilter([parseInputValue(from), parseInputValue(to)]);
34
37
  }
@@ -20,6 +20,9 @@ const TextFilter = (props) => {
20
20
  (0, utils_1.useTheme)();
21
21
  const [text, setText] = react_1.default.useState((_a = column.filterValue) !== null && _a !== void 0 ? _a : '');
22
22
  const onKeyDown = (event) => {
23
+ if (event.altKey) {
24
+ return;
25
+ }
23
26
  if (event.key === 'Enter') {
24
27
  setFilter(text);
25
28
  }
@@ -227,6 +227,9 @@ const TimePickerColumn = (props) => {
227
227
  isSame && (ref === null || ref === void 0 ? void 0 : ref.scrollIntoView({ block: 'nearest', inline: 'nearest' }));
228
228
  };
229
229
  const handleTimeKeyDown = (event, maxValue, onFocus, onSelect, currentValue) => {
230
+ if (event.altKey) {
231
+ return;
232
+ }
230
233
  switch (event.key) {
231
234
  case 'ArrowDown':
232
235
  if (currentValue + 1 > maxValue) {
@@ -77,6 +77,9 @@ const Tree = (props) => {
77
77
  return focusableItems.filter((i) => !focusableItems.some((p) => p.contains(i.parentElement)));
78
78
  }, []);
79
79
  const handleKeyDown = (event) => {
80
+ if (event.altKey) {
81
+ return;
82
+ }
80
83
  const items = getFocusableNodes();
81
84
  if (!(items === null || items === void 0 ? void 0 : items.length)) {
82
85
  return;
@@ -41,6 +41,9 @@ const TreeNode = (props) => {
41
41
  const nodeRef = react_1.default.useRef(null);
42
42
  const onKeyDown = (event) => {
43
43
  var _a, _b, _c, _d, _e, _f;
44
+ if (event.altKey) {
45
+ return;
46
+ }
44
47
  const isNodeFocused = nodeRef.current === ((_a = nodeRef.current) === null || _a === void 0 ? void 0 : _a.ownerDocument.activeElement);
45
48
  switch (event.key) {
46
49
  case 'ArrowLeft': {
@@ -40,6 +40,8 @@ export { Footer, defaultFooterElements } from './Footer';
40
40
  export type { FooterProps, FooterElement, TitleTranslations } from './Footer';
41
41
  export { Header, HeaderBreadcrumbs, HeaderButton, HeaderLogo } from './Header';
42
42
  export type { HeaderProps, HeaderBreadcrumbsProps, HeaderButtonProps, HeaderLogoProps, } from './Header';
43
+ export { List, ListItem } from './List';
44
+ export type { ListProps, ListItemProps, ListItemIconProps, ListItemContentProps, ListItemDescriptionProps, } from './List';
43
45
  export { VerticalTabs, Tabs, Tab, HorizontalTabs } from './Tabs';
44
46
  export type { VerticalTabsProps, TabProps, HorizontalTabsProps } from './Tabs';
45
47
  export { InformationPanel, InformationPanelWrapper, InformationPanelHeader, InformationPanelBody, InformationPanelContent, } from './InformationPanel';
package/cjs/core/index.js CHANGED
@@ -3,9 +3,9 @@ var __importDefault = (this && this.__importDefault) || function (mod) {
3
3
  return (mod && mod.__esModule) ? mod : { "default": mod };
4
4
  };
5
5
  Object.defineProperty(exports, "__esModule", { value: true });
6
- exports.Input = exports.InformationPanelContent = exports.InformationPanelBody = exports.InformationPanelHeader = exports.InformationPanelWrapper = exports.InformationPanel = exports.HorizontalTabs = exports.Tab = exports.Tabs = exports.VerticalTabs = exports.HeaderLogo = exports.HeaderButton = exports.HeaderBreadcrumbs = exports.Header = exports.defaultFooterElements = exports.Footer = exports.FileEmptyCard = exports.FileUploadCard = exports.FileUploadTemplate = exports.FileUpload = exports.Fieldset = exports.ExpandableBlock = exports.NonIdealState = exports.ErrorPage = exports.DropdownMenu = exports.Dialog = exports.generateLocalizedStrings = exports.DatePicker = exports.ComboBox = exports.ColorPalette = exports.ColorInputPanel = exports.ColorBuilder = exports.ColorSwatch = exports.ColorPicker = exports.Checkbox = exports.Carousel = exports.ButtonGroup = exports.SplitButton = exports.IdeasButton = exports.IconButton = exports.DropdownButton = exports.Button = exports.Breadcrumbs = exports.Badge = exports.Backdrop = exports.UserIconGroup = exports.AvatarGroup = exports.UserIcon = exports.Avatar = exports.Alert = void 0;
7
- exports.TreeNodeExpander = exports.TreeNode = exports.Tree = exports.Tooltip = exports.ToggleSwitch = exports.ThemeProvider = exports.toaster = exports.TimePicker = exports.Tile = exports.Textarea = exports.TagContainer = exports.Tag = exports.SelectionColumn = exports.ExpanderColumn = exports.ActionColumn = exports.TablePaginator = exports.EditableCell = exports.DefaultCell = exports.FilterButtonBar = exports.BaseFilter = exports.tableFilters = exports.Table = exports.Surface = exports.StatusMessage = exports.Slider = exports.SkipToContentLink = exports.SidenavSubmenuHeader = exports.SidenavSubmenu = exports.SidenavButton = exports.SideNavigation = exports.Select = exports.RadioTileGroup = exports.RadioTile = exports.Radio = exports.ProgressRadial = exports.ProgressLinear = exports.NotificationMarker = exports.ModalContent = exports.ModalButtonBar = exports.Modal = exports.MenuItemSkeleton = exports.MenuExtraContent = exports.MenuDivider = exports.MenuItem = exports.Menu = exports.LabeledTextarea = exports.LabeledSelect = exports.InputGroup = exports.LabeledInput = exports.Label = void 0;
8
- exports.Divider = exports.VisuallyHidden = exports.Flex = exports.Icon = exports.LinkAction = exports.LinkBox = exports.MiddleTextTruncation = exports.ColorValue = exports.useTheme = exports.getUserColor = exports.WorkflowDiagram = exports.Stepper = exports.Wizard = exports.Text = exports.KbdKeys = exports.Kbd = exports.Code = exports.Blockquote = exports.Title = exports.Subheading = exports.Small = exports.Leading = exports.Headline = exports.Body = exports.Anchor = void 0;
6
+ exports.InformationPanelBody = exports.InformationPanelHeader = exports.InformationPanelWrapper = exports.InformationPanel = exports.HorizontalTabs = exports.Tab = exports.Tabs = exports.VerticalTabs = exports.ListItem = exports.List = exports.HeaderLogo = exports.HeaderButton = exports.HeaderBreadcrumbs = exports.Header = exports.defaultFooterElements = exports.Footer = exports.FileEmptyCard = exports.FileUploadCard = exports.FileUploadTemplate = exports.FileUpload = exports.Fieldset = exports.ExpandableBlock = exports.NonIdealState = exports.ErrorPage = exports.DropdownMenu = exports.Dialog = exports.generateLocalizedStrings = exports.DatePicker = exports.ComboBox = exports.ColorPalette = exports.ColorInputPanel = exports.ColorBuilder = exports.ColorSwatch = exports.ColorPicker = exports.Checkbox = exports.Carousel = exports.ButtonGroup = exports.SplitButton = exports.IdeasButton = exports.IconButton = exports.DropdownButton = exports.Button = exports.Breadcrumbs = exports.Badge = exports.Backdrop = exports.UserIconGroup = exports.AvatarGroup = exports.UserIcon = exports.Avatar = exports.Alert = void 0;
7
+ exports.Tree = exports.Tooltip = exports.ToggleSwitch = exports.ThemeProvider = exports.toaster = exports.TimePicker = exports.Tile = exports.Textarea = exports.TagContainer = exports.Tag = exports.SelectionColumn = exports.ExpanderColumn = exports.ActionColumn = exports.TablePaginator = exports.EditableCell = exports.DefaultCell = exports.FilterButtonBar = exports.BaseFilter = exports.tableFilters = exports.Table = exports.Surface = exports.StatusMessage = exports.Slider = exports.SkipToContentLink = exports.SidenavSubmenuHeader = exports.SidenavSubmenu = exports.SidenavButton = exports.SideNavigation = exports.Select = exports.RadioTileGroup = exports.RadioTile = exports.Radio = exports.ProgressRadial = exports.ProgressLinear = exports.NotificationMarker = exports.ModalContent = exports.ModalButtonBar = exports.Modal = exports.MenuItemSkeleton = exports.MenuExtraContent = exports.MenuDivider = exports.MenuItem = exports.Menu = exports.LabeledTextarea = exports.LabeledSelect = exports.InputGroup = exports.LabeledInput = exports.Label = exports.Input = exports.InformationPanelContent = void 0;
8
+ exports.Divider = exports.VisuallyHidden = exports.Flex = exports.Icon = exports.LinkAction = exports.LinkBox = exports.MiddleTextTruncation = exports.ColorValue = exports.useTheme = exports.getUserColor = exports.WorkflowDiagram = exports.Stepper = exports.Wizard = exports.Text = exports.KbdKeys = exports.Kbd = exports.Code = exports.Blockquote = exports.Title = exports.Subheading = exports.Small = exports.Leading = exports.Headline = exports.Body = exports.Anchor = exports.TreeNodeExpander = exports.TreeNode = void 0;
9
9
  /*---------------------------------------------------------------------------------------------
10
10
  * Copyright (c) Bentley Systems, Incorporated. All rights reserved.
11
11
  * See LICENSE.md in the project root for license terms and full copyright notice.
@@ -71,6 +71,9 @@ Object.defineProperty(exports, "Header", { enumerable: true, get: function () {
71
71
  Object.defineProperty(exports, "HeaderBreadcrumbs", { enumerable: true, get: function () { return Header_1.HeaderBreadcrumbs; } });
72
72
  Object.defineProperty(exports, "HeaderButton", { enumerable: true, get: function () { return Header_1.HeaderButton; } });
73
73
  Object.defineProperty(exports, "HeaderLogo", { enumerable: true, get: function () { return Header_1.HeaderLogo; } });
74
+ var List_1 = require("./List");
75
+ Object.defineProperty(exports, "List", { enumerable: true, get: function () { return List_1.List; } });
76
+ Object.defineProperty(exports, "ListItem", { enumerable: true, get: function () { return List_1.ListItem; } });
74
77
  var Tabs_1 = require("./Tabs");
75
78
  Object.defineProperty(exports, "VerticalTabs", { enumerable: true, get: function () { return Tabs_1.VerticalTabs; } });
76
79
  Object.defineProperty(exports, "Tabs", { enumerable: true, get: function () { return Tabs_1.Tabs; } });
@@ -48,7 +48,7 @@ exports.Popover = react_1.default.forwardRef((props, ref) => {
48
48
  arrow: false,
49
49
  duration: 0,
50
50
  interactive: true,
51
- role: undefined,
51
+ role: '',
52
52
  offset: [0, 0],
53
53
  maxWidth: '',
54
54
  zIndex: 99999,
@@ -103,6 +103,9 @@ exports.hideOnEscOrTab = {
103
103
  return !descendents.some((el) => (el === null || el === void 0 ? void 0 : el.tabIndex) >= 0);
104
104
  };
105
105
  const onKeyDown = (event) => {
106
+ if (event.altKey) {
107
+ return;
108
+ }
106
109
  switch (event.key) {
107
110
  case 'Escape':
108
111
  instance.hide();
@@ -115,6 +115,9 @@ export const ColorBuilder = React.forwardRef((props, ref) => {
115
115
  const keysPressed = React.useRef({}); // keep track of which keys are currently pressed
116
116
  // Arrow key navigation for color dot
117
117
  const handleColorDotKeyDown = (event) => {
118
+ if (event.altKey) {
119
+ return;
120
+ }
118
121
  let x = squareLeft;
119
122
  let y = squareTop;
120
123
  keysPressed.current[event.key] = true;
@@ -36,6 +36,9 @@ export const ColorPalette = React.forwardRef((props, ref) => {
36
36
  const paletteRefs = useMergedRefs(paletteRef, setDefaultTabIndex);
37
37
  // Color palette arrow key navigation
38
38
  const handleKeyDown = (event) => {
39
+ if (event.altKey) {
40
+ return;
41
+ }
39
42
  const swatches = getFocusableElements(paletteRef.current);
40
43
  if (!swatches.length) {
41
44
  return;
@@ -212,6 +212,11 @@ export const ComboBox = (props) => {
212
212
  }
213
213
  }, [multiple, onChangeProp, optionsRef]);
214
214
  const onClickHandler = React.useCallback((__originalIndex) => {
215
+ var _a, _b;
216
+ (_a = inputRef.current) === null || _a === void 0 ? void 0 : _a.focus({ preventScroll: true }); // return focus to input
217
+ if ((_b = optionsRef.current[__originalIndex]) === null || _b === void 0 ? void 0 : _b.disabled) {
218
+ return;
219
+ }
215
220
  if (isMultipleEnabled(selected, multiple)) {
216
221
  const actionType = isMenuItemSelected(__originalIndex)
217
222
  ? 'removed'
@@ -231,6 +236,7 @@ export const ComboBox = (props) => {
231
236
  multiple,
232
237
  onChangeHandler,
233
238
  selected,
239
+ optionsRef,
234
240
  ]);
235
241
  const getMenuItem = React.useCallback((option, filteredIndex) => {
236
242
  const optionId = getOptionId(option, id);
@@ -8,7 +8,7 @@ import { useSafeContext, useMergedRefs, useContainerWidth } from '../utils';
8
8
  import { ComboBoxMultipleContainer } from './ComboBoxMultipleContainer';
9
9
  import { ComboBoxStateContext, ComboBoxActionContext, ComboBoxRefsContext, } from './helpers';
10
10
  export const ComboBoxInput = React.forwardRef((props, forwardedRef) => {
11
- const { onKeyDown: onKeyDownProp, onFocus: onFocusProp, selectTags, ...rest } = props;
11
+ const { onKeyDown: onKeyDownProp, onFocus: onFocusProp, onClick: onClickProp, selectTags, ...rest } = props;
12
12
  const { isOpen, id, focusedIndex, enableVirtualization, multiple, onClickHandler, } = useSafeContext(ComboBoxStateContext);
13
13
  const dispatch = useSafeContext(ComboBoxActionContext);
14
14
  const { inputRef, menuRef, optionsExtraInfoRef } = useSafeContext(ComboBoxRefsContext);
@@ -25,6 +25,9 @@ export const ComboBoxInput = React.forwardRef((props, forwardedRef) => {
25
25
  var _a, _b, _c, _d, _e, _f, _g, _h, _j, _k, _l, _m, _o, _p, _q;
26
26
  onKeyDownProp === null || onKeyDownProp === void 0 ? void 0 : onKeyDownProp(event);
27
27
  const length = (_a = Object.keys(optionsExtraInfoRef.current).length) !== null && _a !== void 0 ? _a : 0;
28
+ if (event.altKey) {
29
+ return;
30
+ }
28
31
  switch (event.key) {
29
32
  case 'ArrowDown': {
30
33
  event.preventDefault();
@@ -51,7 +54,7 @@ export const ComboBoxInput = React.forwardRef((props, forwardedRef) => {
51
54
  const currentElement = (_f = menuRef.current) === null || _f === void 0 ? void 0 : _f.querySelector(`[data-iui-index="${nextIndex}"]`);
52
55
  const nextElement = (_g = currentElement === null || currentElement === void 0 ? void 0 : currentElement.nextElementSibling) !== null && _g !== void 0 ? _g : (_h = menuRef.current) === null || _h === void 0 ? void 0 : _h.querySelector('[data-iui-index]');
53
56
  nextIndex = Number(nextElement === null || nextElement === void 0 ? void 0 : nextElement.getAttribute('data-iui-index'));
54
- if ((nextElement === null || nextElement === void 0 ? void 0 : nextElement.ariaDisabled) !== 'true') {
57
+ if (nextElement) {
55
58
  return dispatch({ type: 'focus', value: nextIndex });
56
59
  }
57
60
  } while (nextIndex !== focusedIndexRef.current);
@@ -81,7 +84,7 @@ export const ComboBoxInput = React.forwardRef((props, forwardedRef) => {
81
84
  const currentElement = (_o = menuRef.current) === null || _o === void 0 ? void 0 : _o.querySelector(`[data-iui-index="${prevIndex}"]`);
82
85
  const prevElement = (_p = currentElement === null || currentElement === void 0 ? void 0 : currentElement.previousElementSibling) !== null && _p !== void 0 ? _p : (_q = menuRef.current) === null || _q === void 0 ? void 0 : _q.querySelector('[data-iui-index]:last-of-type');
83
86
  prevIndex = Number(prevElement === null || prevElement === void 0 ? void 0 : prevElement.getAttribute('data-iui-index'));
84
- if ((prevElement === null || prevElement === void 0 ? void 0 : prevElement.ariaDisabled) !== 'true') {
87
+ if (prevElement) {
85
88
  return dispatch({ type: 'focus', value: prevIndex });
86
89
  }
87
90
  } while (prevIndex !== focusedIndexRef.current);
@@ -90,18 +93,8 @@ export const ComboBoxInput = React.forwardRef((props, forwardedRef) => {
90
93
  case 'Enter': {
91
94
  event.preventDefault();
92
95
  if (isOpen) {
93
- if (multiple) {
94
- // Keep menu open when multiselect is enabled and user selects an item
95
- if (focusedIndexRef.current > -1) {
96
- onClickHandler === null || onClickHandler === void 0 ? void 0 : onClickHandler(focusedIndexRef.current);
97
- }
98
- else {
99
- dispatch({ type: 'close' });
100
- }
101
- }
102
- else {
96
+ if (focusedIndexRef.current > -1) {
103
97
  onClickHandler === null || onClickHandler === void 0 ? void 0 : onClickHandler(focusedIndexRef.current);
104
- dispatch({ type: 'close' });
105
98
  }
106
99
  }
107
100
  else {
@@ -123,7 +116,6 @@ export const ComboBoxInput = React.forwardRef((props, forwardedRef) => {
123
116
  enableVirtualization,
124
117
  isOpen,
125
118
  menuRef,
126
- multiple,
127
119
  onClickHandler,
128
120
  onKeyDownProp,
129
121
  optionsExtraInfoRef,
@@ -132,9 +124,18 @@ export const ComboBoxInput = React.forwardRef((props, forwardedRef) => {
132
124
  dispatch({ type: 'open' });
133
125
  onFocusProp === null || onFocusProp === void 0 ? void 0 : onFocusProp(event);
134
126
  }, [dispatch, onFocusProp]);
127
+ const handleClick = React.useCallback((e) => {
128
+ onClickProp === null || onClickProp === void 0 ? void 0 : onClickProp(e);
129
+ if (e.isDefaultPrevented()) {
130
+ return;
131
+ }
132
+ if (!isOpen) {
133
+ dispatch({ type: 'open' });
134
+ }
135
+ }, [dispatch, isOpen, onClickProp]);
135
136
  const [tagContainerWidthRef, tagContainerWidth] = useContainerWidth();
136
137
  return (React.createElement(React.Fragment, null,
137
- React.createElement(Input, { ref: refs, onKeyDown: handleKeyDown, onFocus: handleFocus, "aria-activedescendant": isOpen && focusedIndex != undefined && focusedIndex > -1
138
+ React.createElement(Input, { ref: refs, onKeyDown: handleKeyDown, onClick: handleClick, onFocus: handleFocus, "aria-activedescendant": isOpen && focusedIndex != undefined && focusedIndex > -1
138
139
  ? getIdFromIndex(focusedIndex)
139
140
  : undefined, role: 'combobox', "aria-controls": isOpen ? `${id}-list` : undefined, "aria-autocomplete": 'list', spellCheck: false, autoCapitalize: 'none', autoCorrect: 'off', style: multiple ? { paddingLeft: tagContainerWidth + 18 } : {}, ...rest }),
140
141
  multiple && selectTags && (React.createElement(ComboBoxMultipleContainer, { ref: tagContainerWidthRef, selectedItems: selectTags }))));
@@ -20,7 +20,7 @@ export const ComboBoxMenuItem = React.memo(React.forwardRef((props, forwardedRef
20
20
  'iui-active': isSelected,
21
21
  'iui-disabled': disabled,
22
22
  'iui-focused': focusedIndex === index,
23
- }, className), ref: refs, onClick: () => !disabled && (onClick === null || onClick === void 0 ? void 0 : onClick(value)), role: role, tabIndex: disabled || role === 'presentation' ? undefined : -1, "aria-selected": isSelected, "aria-disabled": disabled, "data-iui-index": index, ...rest },
23
+ }, className), ref: refs, onClick: () => onClick === null || onClick === void 0 ? void 0 : onClick(value), role: role, tabIndex: role === 'presentation' ? undefined : -1, "aria-selected": isSelected, "aria-disabled": disabled, "data-iui-index": index, ...rest },
24
24
  icon &&
25
25
  React.cloneElement(icon, {
26
26
  className: cx(icon.props.className, 'iui-icon'),
@@ -265,6 +265,9 @@ export const DatePicker = (props) => {
265
265
  const isPreviousYearDisabled = isDateDisabled === null || isDateDisabled === void 0 ? void 0 : isDateDisabled(new Date(displayedYear - 1, 11, 31));
266
266
  const isNextYearDisabled = isDateDisabled === null || isDateDisabled === void 0 ? void 0 : isDateDisabled(new Date(displayedYear + 1, 0, 1));
267
267
  const handleCalendarKeyDown = (event) => {
268
+ if (event.altKey) {
269
+ return;
270
+ }
268
271
  if (!focusedDay) {
269
272
  return;
270
273
  }
@@ -67,6 +67,9 @@ export const DialogMain = React.forwardRef((props, ref) => {
67
67
  };
68
68
  }, [isOpen, preventDocumentScroll]);
69
69
  const handleKeyDown = (event) => {
70
+ if (event.altKey) {
71
+ return;
72
+ }
70
73
  // Prevents React from resetting its properties
71
74
  event.persist();
72
75
  if (isDismissible && closeOnEsc && event.key === 'Escape' && onClose) {
@@ -28,6 +28,9 @@ export const ExpandableBlock = (props) => {
28
28
  onToggle === null || onToggle === void 0 ? void 0 : onToggle(!expanded);
29
29
  };
30
30
  const onKeyDown = (event) => {
31
+ if (event.altKey) {
32
+ return;
33
+ }
31
34
  if (event.key === 'Enter' ||
32
35
  event.key === ' ' ||
33
36
  event.key === 'Spacebar') {
@@ -0,0 +1,6 @@
1
+ import type { PolymorphicForwardRefComponent, PolymorphicComponentProps } from '../utils';
2
+ import '@itwin/itwinui-css/css/menu.css';
3
+ export declare const List: PolymorphicForwardRefComponent<"ul", ListOwnProps>;
4
+ declare type ListOwnProps = {};
5
+ export declare type ListProps = PolymorphicComponentProps<'ul', ListOwnProps>;
6
+ export {};
@@ -0,0 +1,13 @@
1
+ /*---------------------------------------------------------------------------------------------
2
+ * Copyright (c) Bentley Systems, Incorporated. All rights reserved.
3
+ * See LICENSE.md in the project root for license terms and full copyright notice.
4
+ *--------------------------------------------------------------------------------------------*/
5
+ import React from 'react';
6
+ import cx from 'classnames';
7
+ import { useTheme } from '../utils';
8
+ import '@itwin/itwinui-css/css/menu.css';
9
+ export const List = React.forwardRef((props, ref) => {
10
+ const { as: Element = 'ul', className, ...rest } = props;
11
+ useTheme();
12
+ return (React.createElement(Element, { className: cx('iui-list', className), ref: ref, role: 'list', ...rest }));
13
+ });
@@ -0,0 +1,79 @@
1
+ import type { PolymorphicForwardRefComponent, PolymorphicComponentProps } from '../utils';
2
+ import '@itwin/itwinui-css/css/menu.css';
3
+ declare type ListItemOwnProps = {
4
+ /**
5
+ * Size of the ListItem. Can be explicitly specified to be 'large',
6
+ * but if a description is included in addition to the label, then
7
+ * it will automatically become large.
8
+ */
9
+ size?: 'default' | 'large';
10
+ /**
11
+ * If true, the ListItem has disabled (dimmed) styling.
12
+ */
13
+ disabled?: boolean;
14
+ /**
15
+ * If true, the ListItem has active (selected) styling.
16
+ */
17
+ active?: boolean;
18
+ /**
19
+ * If true, the ListItem will get actionable styling, such as hover styling and cursor.
20
+ */
21
+ actionable?: boolean;
22
+ /**
23
+ * If true, the ListItem has focus styling.
24
+ *
25
+ * By default, focus styling is automatically applied if the item is
26
+ * focused, or if the item contains a `LinkAction` and it is focused.
27
+ * This prop is useful for custom focus management (e.g. using `aria-activedescendant`).
28
+ */
29
+ focused?: boolean;
30
+ };
31
+ declare type ListItemIconOwnProps = {};
32
+ declare type ListItemContentOwnProps = {};
33
+ declare type ListItemDescriptionOwnProps = {};
34
+ /**
35
+ * A generic ListItem component that can be used simply for displaying data, or as a base
36
+ * for the list items in a more complex component (e.g. a custom Select).
37
+ *
38
+ * Includes support for left/right icons, multiple lines of text, and hover/focus/active/disabled styling.
39
+ *
40
+ * @example
41
+ * <List>
42
+ * <ListItem>item 1</ListItem>
43
+ * <ListItem>item 2</ListItem>
44
+ * <ListItem>item 3</ListItem>
45
+ * </List>
46
+ */
47
+ export declare const ListItem: PolymorphicForwardRefComponent<"li", ListItemOwnProps> & {
48
+ /**
49
+ * Icon to be placed at the beginning or end of the ListItem.
50
+ */
51
+ Icon: PolymorphicForwardRefComponent<"div", ListItemIconOwnProps>;
52
+ /**
53
+ * Wrapper for the main content of the ListItem.
54
+ *
55
+ * For basic list items, this wrapper is not needed, but it can be useful for two cases:
56
+ * - When using an end icon. The `ListItem.Content` will fill the available space
57
+ * and push the icon to the end
58
+ * - When using `ListItem.Description`.
59
+ */
60
+ Content: PolymorphicForwardRefComponent<"div", ListItemContentOwnProps>;
61
+ /**
62
+ * Description to be used in addition to the main label of the ListItem.
63
+ * Should be used as a child of `ListItem.Content`.
64
+ *
65
+ * @example
66
+ * <ListItem>
67
+ * <ListItem.Content>
68
+ * <div>some list item</div>
69
+ * <ListItem.Description>description for this item</ListItem.Description>
70
+ * </ListItem.Content>
71
+ * </ListItem>
72
+ */
73
+ Description: PolymorphicForwardRefComponent<"div", ListItemDescriptionOwnProps>;
74
+ };
75
+ export declare type ListItemProps = PolymorphicComponentProps<'li', ListItemOwnProps>;
76
+ export declare type ListItemIconProps = PolymorphicComponentProps<'li', ListItemIconOwnProps>;
77
+ export declare type ListItemContentProps = PolymorphicComponentProps<'li', ListItemContentOwnProps>;
78
+ export declare type ListItemDescriptionProps = PolymorphicComponentProps<'li', ListItemDescriptionOwnProps>;
79
+ export {};
@@ -0,0 +1,71 @@
1
+ /*---------------------------------------------------------------------------------------------
2
+ * Copyright (c) Bentley Systems, Incorporated. All rights reserved.
3
+ * See LICENSE.md in the project root for license terms and full copyright notice.
4
+ *--------------------------------------------------------------------------------------------*/
5
+ import React from 'react';
6
+ import cx from 'classnames';
7
+ import { useTheme } from '../utils';
8
+ import '@itwin/itwinui-css/css/menu.css';
9
+ const ListItemComponent = React.forwardRef((props, ref) => {
10
+ const { as: Element = 'li', size = 'default', disabled = false, active = false, actionable = false, focused = false, className, ...rest } = props;
11
+ useTheme();
12
+ return (React.createElement(Element, { className: cx('iui-list-item', className), "data-iui-active": active ? 'true' : undefined, "data-iui-disabled": disabled ? 'true' : undefined, "data-iui-size": size === 'large' ? 'large' : undefined, "data-iui-actionable": actionable ? 'true' : undefined, "data-iui-focused": focused ? 'true' : undefined, ref: ref, ...rest }));
13
+ });
14
+ // ----------------------------------------------------------------------------
15
+ const ListItemIcon = React.forwardRef((props, ref) => {
16
+ const { as: Element = 'div', className, ...rest } = props;
17
+ return (React.createElement(Element, { className: cx('iui-list-item-icon', className), ref: ref, ...rest }));
18
+ });
19
+ // ----------------------------------------------------------------------------
20
+ const ListItemContent = React.forwardRef((props, ref) => {
21
+ const { as: Element = 'div', className, ...rest } = props;
22
+ return (React.createElement(Element, { className: cx('iui-list-item-content', className), ref: ref, ...rest }));
23
+ });
24
+ // ----------------------------------------------------------------------------
25
+ const ListItemDescription = React.forwardRef((props, ref) => {
26
+ const { as: Element = 'div', className, ...rest } = props;
27
+ return (React.createElement(Element, { className: cx('iui-list-item-description', className), ref: ref, ...rest }));
28
+ });
29
+ // ----------------------------------------------------------------------------
30
+ // Exported compound component
31
+ /**
32
+ * A generic ListItem component that can be used simply for displaying data, or as a base
33
+ * for the list items in a more complex component (e.g. a custom Select).
34
+ *
35
+ * Includes support for left/right icons, multiple lines of text, and hover/focus/active/disabled styling.
36
+ *
37
+ * @example
38
+ * <List>
39
+ * <ListItem>item 1</ListItem>
40
+ * <ListItem>item 2</ListItem>
41
+ * <ListItem>item 3</ListItem>
42
+ * </List>
43
+ */
44
+ export const ListItem = Object.assign(ListItemComponent, {
45
+ /**
46
+ * Icon to be placed at the beginning or end of the ListItem.
47
+ */
48
+ Icon: ListItemIcon,
49
+ /**
50
+ * Wrapper for the main content of the ListItem.
51
+ *
52
+ * For basic list items, this wrapper is not needed, but it can be useful for two cases:
53
+ * - When using an end icon. The `ListItem.Content` will fill the available space
54
+ * and push the icon to the end
55
+ * - When using `ListItem.Description`.
56
+ */
57
+ Content: ListItemContent,
58
+ /**
59
+ * Description to be used in addition to the main label of the ListItem.
60
+ * Should be used as a child of `ListItem.Content`.
61
+ *
62
+ * @example
63
+ * <ListItem>
64
+ * <ListItem.Content>
65
+ * <div>some list item</div>
66
+ * <ListItem.Description>description for this item</ListItem.Description>
67
+ * </ListItem.Content>
68
+ * </ListItem>
69
+ */
70
+ Description: ListItemDescription,
71
+ });
@@ -0,0 +1,4 @@
1
+ export { List } from './List';
2
+ export type { ListProps } from './List';
3
+ export { ListItem } from './ListItem';
4
+ export type { ListItemProps, ListItemIconProps, ListItemContentProps, ListItemDescriptionProps, } from './ListItem';
@@ -0,0 +1,6 @@
1
+ /*---------------------------------------------------------------------------------------------
2
+ * Copyright (c) Bentley Systems, Incorporated. All rights reserved.
3
+ * See LICENSE.md in the project root for license terms and full copyright notice.
4
+ *--------------------------------------------------------------------------------------------*/
5
+ export { List } from './List';
6
+ export { ListItem } from './ListItem';
@@ -33,6 +33,9 @@ export const Menu = React.forwardRef((props, ref) => {
33
33
  }
34
34
  }, [setFocus, focusedIndex, getFocusableNodes]);
35
35
  const onKeyDown = (event) => {
36
+ if (event.altKey) {
37
+ return;
38
+ }
36
39
  const items = getFocusableNodes();
37
40
  if (!(items === null || items === void 0 ? void 0 : items.length)) {
38
41
  return;
@@ -97,6 +97,9 @@ export const Select = (props) => {
97
97
  }
98
98
  }, [isOpen]);
99
99
  const onKeyDown = (event, toggle) => {
100
+ if (event.altKey) {
101
+ return;
102
+ }
100
103
  switch (event.key) {
101
104
  case 'Enter':
102
105
  case ' ':
@@ -16,6 +16,9 @@ export const StepperStep = (props) => {
16
16
  }
17
17
  };
18
18
  const onKeyDown = (e) => {
19
+ if (e.altKey) {
20
+ return;
21
+ }
19
22
  if (!isClickable) {
20
23
  return;
21
24
  }
@@ -51,6 +51,9 @@ export const DateRangeFilter = (props) => {
51
51
  });
52
52
  }, []);
53
53
  const onKeyDown = (event) => {
54
+ if (event.altKey) {
55
+ return;
56
+ }
54
57
  if (event.key === 'Enter') {
55
58
  setFilter([from, to]);
56
59
  }
@@ -23,6 +23,9 @@ export const NumberRangeFilter = (props) => {
23
23
  return !value || isNaN(Number(value)) ? undefined : Number(value);
24
24
  };
25
25
  const onKeyDown = (event) => {
26
+ if (event.altKey) {
27
+ return;
28
+ }
26
29
  if (event.key === 'Enter') {
27
30
  setFilter([parseInputValue(from), parseInputValue(to)]);
28
31
  }
@@ -14,6 +14,9 @@ export const TextFilter = (props) => {
14
14
  useTheme();
15
15
  const [text, setText] = React.useState((_a = column.filterValue) !== null && _a !== void 0 ? _a : '');
16
16
  const onKeyDown = (event) => {
17
+ if (event.altKey) {
18
+ return;
19
+ }
17
20
  if (event.key === 'Enter') {
18
21
  setFilter(text);
19
22
  }
@@ -220,6 +220,9 @@ const TimePickerColumn = (props) => {
220
220
  isSame && (ref === null || ref === void 0 ? void 0 : ref.scrollIntoView({ block: 'nearest', inline: 'nearest' }));
221
221
  };
222
222
  const handleTimeKeyDown = (event, maxValue, onFocus, onSelect, currentValue) => {
223
+ if (event.altKey) {
224
+ return;
225
+ }
223
226
  switch (event.key) {
224
227
  case 'ArrowDown':
225
228
  if (currentValue + 1 > maxValue) {
@@ -71,6 +71,9 @@ export const Tree = (props) => {
71
71
  return focusableItems.filter((i) => !focusableItems.some((p) => p.contains(i.parentElement)));
72
72
  }, []);
73
73
  const handleKeyDown = (event) => {
74
+ if (event.altKey) {
75
+ return;
76
+ }
74
77
  const items = getFocusableNodes();
75
78
  if (!(items === null || items === void 0 ? void 0 : items.length)) {
76
79
  return;
@@ -35,6 +35,9 @@ export const TreeNode = (props) => {
35
35
  const nodeRef = React.useRef(null);
36
36
  const onKeyDown = (event) => {
37
37
  var _a, _b, _c, _d, _e, _f;
38
+ if (event.altKey) {
39
+ return;
40
+ }
38
41
  const isNodeFocused = nodeRef.current === ((_a = nodeRef.current) === null || _a === void 0 ? void 0 : _a.ownerDocument.activeElement);
39
42
  switch (event.key) {
40
43
  case 'ArrowLeft': {
@@ -40,6 +40,8 @@ export { Footer, defaultFooterElements } from './Footer';
40
40
  export type { FooterProps, FooterElement, TitleTranslations } from './Footer';
41
41
  export { Header, HeaderBreadcrumbs, HeaderButton, HeaderLogo } from './Header';
42
42
  export type { HeaderProps, HeaderBreadcrumbsProps, HeaderButtonProps, HeaderLogoProps, } from './Header';
43
+ export { List, ListItem } from './List';
44
+ export type { ListProps, ListItemProps, ListItemIconProps, ListItemContentProps, ListItemDescriptionProps, } from './List';
43
45
  export { VerticalTabs, Tabs, Tab, HorizontalTabs } from './Tabs';
44
46
  export type { VerticalTabsProps, TabProps, HorizontalTabsProps } from './Tabs';
45
47
  export { InformationPanel, InformationPanelWrapper, InformationPanelHeader, InformationPanelBody, InformationPanelContent, } from './InformationPanel';
package/esm/core/index.js CHANGED
@@ -23,6 +23,7 @@ export { Fieldset } from './Fieldset';
23
23
  export { FileUpload, FileUploadTemplate, FileUploadCard, FileEmptyCard, } from './FileUpload';
24
24
  export { Footer, defaultFooterElements } from './Footer';
25
25
  export { Header, HeaderBreadcrumbs, HeaderButton, HeaderLogo } from './Header';
26
+ export { List, ListItem } from './List';
26
27
  export { VerticalTabs, Tabs, Tab, HorizontalTabs } from './Tabs';
27
28
  export { InformationPanel, InformationPanelWrapper, InformationPanelHeader, InformationPanelBody, InformationPanelContent, } from './InformationPanel';
28
29
  export { Input } from './Input';
@@ -42,7 +42,7 @@ export const Popover = React.forwardRef((props, ref) => {
42
42
  arrow: false,
43
43
  duration: 0,
44
44
  interactive: true,
45
- role: undefined,
45
+ role: '',
46
46
  offset: [0, 0],
47
47
  maxWidth: '',
48
48
  zIndex: 99999,
@@ -97,6 +97,9 @@ export const hideOnEscOrTab = {
97
97
  return !descendents.some((el) => (el === null || el === void 0 ? void 0 : el.tabIndex) >= 0);
98
98
  };
99
99
  const onKeyDown = (event) => {
100
+ if (event.altKey) {
101
+ return;
102
+ }
100
103
  switch (event.key) {
101
104
  case 'Escape':
102
105
  instance.hide();
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@itwin/itwinui-react",
3
- "version": "2.8.2",
3
+ "version": "2.9.0",
4
4
  "author": "Bentley Systems",
5
5
  "license": "MIT",
6
6
  "main": "cjs/index.js",
@@ -62,7 +62,7 @@
62
62
  "dev:types": "concurrently \"tsc -p tsconfig.cjs.json --emitDeclarationOnly --watch --preserveWatchOutput\" \"tsc -p tsconfig.esm.json --emitDeclarationOnly --watch --preserveWatchOutput\""
63
63
  },
64
64
  "dependencies": {
65
- "@itwin/itwinui-css": "^1.9.0",
65
+ "@itwin/itwinui-css": "^1.10.0",
66
66
  "@itwin/itwinui-illustrations-react": "^2.0.0",
67
67
  "@itwin/itwinui-variables": "^2.0.0",
68
68
  "@tippyjs/react": "^4.2.6",