@mui/x-tree-view 8.0.0-alpha.13 → 8.0.0-alpha.14
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/CHANGELOG.md +131 -0
- package/RichTreeView/RichTreeView.js +24 -5
- package/SimpleTreeView/SimpleTreeView.js +8 -6
- package/TreeItem/TreeItem.d.ts +2 -0
- package/TreeItem/TreeItem.js +46 -5
- package/TreeItem/TreeItem.types.d.ts +14 -0
- package/TreeItemIcon/TreeItemIcon.js +2 -0
- package/esm/RichTreeView/RichTreeView.js +24 -5
- package/esm/SimpleTreeView/SimpleTreeView.js +8 -6
- package/esm/TreeItem/TreeItem.d.ts +2 -0
- package/esm/TreeItem/TreeItem.js +45 -4
- package/esm/TreeItem/TreeItem.types.d.ts +14 -0
- package/esm/TreeItemIcon/TreeItemIcon.js +2 -0
- package/esm/hooks/useTreeItemUtils/useTreeItemUtils.d.ts +3 -2
- package/esm/hooks/useTreeItemUtils/useTreeItemUtils.js +21 -9
- package/esm/hooks/useTreeViewApiRef.d.ts +1 -1
- package/esm/index.js +1 -1
- package/esm/internals/index.d.ts +6 -1
- package/esm/internals/index.js +4 -1
- package/esm/internals/plugins/useTreeViewExpansion/useTreeViewExpansion.js +35 -12
- package/esm/internals/plugins/useTreeViewExpansion/useTreeViewExpansion.selectors.d.ts +4 -0
- package/esm/internals/plugins/useTreeViewExpansion/useTreeViewExpansion.types.d.ts +40 -16
- package/esm/internals/plugins/useTreeViewItems/useTreeViewItems.js +157 -16
- package/esm/internals/plugins/useTreeViewItems/useTreeViewItems.selectors.d.ts +172 -0
- package/esm/internals/plugins/useTreeViewItems/useTreeViewItems.selectors.js +13 -0
- package/esm/internals/plugins/useTreeViewItems/useTreeViewItems.types.d.ts +49 -0
- package/esm/internals/plugins/useTreeViewJSXItems/useTreeViewJSXItems.js +2 -2
- package/esm/internals/plugins/useTreeViewKeyboardNavigation/useTreeViewKeyboardNavigation.js +16 -7
- package/esm/internals/plugins/useTreeViewKeyboardNavigation/useTreeViewKeyboardNavigation.types.d.ts +2 -1
- package/esm/internals/plugins/useTreeViewLazyLoading/index.d.ts +1 -0
- package/esm/internals/plugins/useTreeViewLazyLoading/index.js +1 -0
- package/esm/internals/plugins/useTreeViewLazyLoading/useTreeViewLazyLoading.selectors.d.ts +249 -0
- package/esm/internals/plugins/useTreeViewLazyLoading/useTreeViewLazyLoading.selectors.js +27 -0
- package/esm/internals/plugins/useTreeViewLazyLoading/useTreeViewLazyLoading.types.d.ts +83 -0
- package/esm/internals/plugins/useTreeViewLazyLoading/useTreeViewLazyLoading.types.js +1 -0
- package/esm/internals/plugins/useTreeViewSelection/useTreeViewSelection.js +4 -4
- package/esm/internals/plugins/useTreeViewSelection/useTreeViewSelection.types.d.ts +12 -12
- package/esm/internals/utils/selectors.d.ts +7 -0
- package/esm/internals/utils/selectors.js +9 -0
- package/esm/useTreeItem/useTreeItem.d.ts +1 -1
- package/esm/useTreeItem/useTreeItem.js +13 -0
- package/esm/useTreeItem/useTreeItem.types.d.ts +21 -0
- package/esm/utils/cache.d.ts +38 -0
- package/esm/utils/cache.js +31 -0
- package/esm/utils/index.d.ts +1 -0
- package/esm/utils/index.js +1 -0
- package/hooks/useTreeItemUtils/useTreeItemUtils.d.ts +3 -2
- package/hooks/useTreeItemUtils/useTreeItemUtils.js +22 -10
- package/hooks/useTreeViewApiRef.d.ts +1 -1
- package/index.js +1 -1
- package/internals/index.d.ts +6 -1
- package/internals/index.js +33 -0
- package/internals/plugins/useTreeViewExpansion/useTreeViewExpansion.js +35 -12
- package/internals/plugins/useTreeViewExpansion/useTreeViewExpansion.selectors.d.ts +4 -0
- package/internals/plugins/useTreeViewExpansion/useTreeViewExpansion.types.d.ts +40 -16
- package/internals/plugins/useTreeViewItems/useTreeViewItems.js +157 -16
- package/internals/plugins/useTreeViewItems/useTreeViewItems.selectors.d.ts +172 -0
- package/internals/plugins/useTreeViewItems/useTreeViewItems.selectors.js +14 -1
- package/internals/plugins/useTreeViewItems/useTreeViewItems.types.d.ts +49 -0
- package/internals/plugins/useTreeViewJSXItems/useTreeViewJSXItems.js +1 -1
- package/internals/plugins/useTreeViewKeyboardNavigation/useTreeViewKeyboardNavigation.js +16 -7
- package/internals/plugins/useTreeViewKeyboardNavigation/useTreeViewKeyboardNavigation.types.d.ts +2 -1
- package/internals/plugins/useTreeViewLazyLoading/index.d.ts +1 -0
- package/internals/plugins/useTreeViewLazyLoading/index.js +5 -0
- package/internals/plugins/useTreeViewLazyLoading/useTreeViewLazyLoading.selectors.d.ts +249 -0
- package/internals/plugins/useTreeViewLazyLoading/useTreeViewLazyLoading.selectors.js +33 -0
- package/internals/plugins/useTreeViewLazyLoading/useTreeViewLazyLoading.types.d.ts +83 -0
- package/internals/plugins/useTreeViewLazyLoading/useTreeViewLazyLoading.types.js +5 -0
- package/internals/plugins/useTreeViewSelection/useTreeViewSelection.js +4 -4
- package/internals/plugins/useTreeViewSelection/useTreeViewSelection.types.d.ts +12 -12
- package/internals/utils/selectors.d.ts +7 -0
- package/internals/utils/selectors.js +9 -0
- package/modern/RichTreeView/RichTreeView.js +24 -5
- package/modern/SimpleTreeView/SimpleTreeView.js +8 -6
- package/modern/TreeItem/TreeItem.d.ts +2 -0
- package/modern/TreeItem/TreeItem.js +45 -4
- package/modern/TreeItem/TreeItem.types.d.ts +14 -0
- package/modern/TreeItemIcon/TreeItemIcon.js +2 -0
- package/modern/hooks/useTreeItemUtils/useTreeItemUtils.d.ts +3 -2
- package/modern/hooks/useTreeItemUtils/useTreeItemUtils.js +21 -9
- package/modern/hooks/useTreeViewApiRef.d.ts +1 -1
- package/modern/index.js +1 -1
- package/modern/internals/index.d.ts +6 -1
- package/modern/internals/index.js +4 -1
- package/modern/internals/plugins/useTreeViewExpansion/useTreeViewExpansion.js +35 -12
- package/modern/internals/plugins/useTreeViewExpansion/useTreeViewExpansion.selectors.d.ts +4 -0
- package/modern/internals/plugins/useTreeViewExpansion/useTreeViewExpansion.types.d.ts +40 -16
- package/modern/internals/plugins/useTreeViewItems/useTreeViewItems.js +157 -16
- package/modern/internals/plugins/useTreeViewItems/useTreeViewItems.selectors.d.ts +172 -0
- package/modern/internals/plugins/useTreeViewItems/useTreeViewItems.selectors.js +13 -0
- package/modern/internals/plugins/useTreeViewItems/useTreeViewItems.types.d.ts +49 -0
- package/modern/internals/plugins/useTreeViewJSXItems/useTreeViewJSXItems.js +2 -2
- package/modern/internals/plugins/useTreeViewKeyboardNavigation/useTreeViewKeyboardNavigation.js +16 -7
- package/modern/internals/plugins/useTreeViewKeyboardNavigation/useTreeViewKeyboardNavigation.types.d.ts +2 -1
- package/modern/internals/plugins/useTreeViewLazyLoading/index.d.ts +1 -0
- package/modern/internals/plugins/useTreeViewLazyLoading/index.js +1 -0
- package/modern/internals/plugins/useTreeViewLazyLoading/useTreeViewLazyLoading.selectors.d.ts +249 -0
- package/modern/internals/plugins/useTreeViewLazyLoading/useTreeViewLazyLoading.selectors.js +27 -0
- package/modern/internals/plugins/useTreeViewLazyLoading/useTreeViewLazyLoading.types.d.ts +83 -0
- package/modern/internals/plugins/useTreeViewLazyLoading/useTreeViewLazyLoading.types.js +1 -0
- package/modern/internals/plugins/useTreeViewSelection/useTreeViewSelection.js +4 -4
- package/modern/internals/plugins/useTreeViewSelection/useTreeViewSelection.types.d.ts +12 -12
- package/modern/internals/utils/selectors.d.ts +7 -0
- package/modern/internals/utils/selectors.js +9 -0
- package/modern/useTreeItem/useTreeItem.d.ts +1 -1
- package/modern/useTreeItem/useTreeItem.js +13 -0
- package/modern/useTreeItem/useTreeItem.types.d.ts +21 -0
- package/modern/utils/cache.d.ts +38 -0
- package/modern/utils/cache.js +31 -0
- package/modern/utils/index.d.ts +1 -0
- package/modern/utils/index.js +1 -0
- package/package.json +1 -1
- package/tsconfig.build.tsbuildinfo +1 -1
- package/useTreeItem/useTreeItem.d.ts +1 -1
- package/useTreeItem/useTreeItem.js +13 -0
- package/useTreeItem/useTreeItem.types.d.ts +21 -0
- package/utils/cache.d.ts +38 -0
- package/utils/cache.js +38 -0
- package/utils/index.d.ts +1 -0
- package/utils/index.js +16 -0
package/esm/TreeItem/TreeItem.js
CHANGED
|
@@ -7,6 +7,7 @@ const _excluded = ["visible"],
|
|
|
7
7
|
import * as React from 'react';
|
|
8
8
|
import PropTypes from 'prop-types';
|
|
9
9
|
import clsx from 'clsx';
|
|
10
|
+
import CircularProgress from '@mui/material/CircularProgress';
|
|
10
11
|
import unsupportedProp from '@mui/utils/unsupportedProp';
|
|
11
12
|
import { alpha } from '@mui/material/styles';
|
|
12
13
|
import Collapse from '@mui/material/Collapse';
|
|
@@ -132,6 +133,7 @@ export const TreeItemIconContainer = styled('div', {
|
|
|
132
133
|
display: 'flex',
|
|
133
134
|
flexShrink: 0,
|
|
134
135
|
justifyContent: 'center',
|
|
136
|
+
position: 'relative',
|
|
135
137
|
'& svg': {
|
|
136
138
|
fontSize: 18
|
|
137
139
|
}
|
|
@@ -144,6 +146,25 @@ export const TreeItemGroupTransition = styled(Collapse, {
|
|
|
144
146
|
margin: 0,
|
|
145
147
|
padding: 0
|
|
146
148
|
});
|
|
149
|
+
export const TreeItemErrorContainer = styled('div', {
|
|
150
|
+
name: 'MuiTreeItem',
|
|
151
|
+
slot: 'ErrorIcon',
|
|
152
|
+
overridesResolver: (props, styles) => styles.errorIcon
|
|
153
|
+
})({
|
|
154
|
+
position: 'absolute',
|
|
155
|
+
right: -3,
|
|
156
|
+
width: 7,
|
|
157
|
+
height: 7,
|
|
158
|
+
borderRadius: '50%',
|
|
159
|
+
backgroundColor: 'red'
|
|
160
|
+
});
|
|
161
|
+
export const TreeItemLoadingContainer = styled(CircularProgress, {
|
|
162
|
+
name: 'MuiTreeItem',
|
|
163
|
+
slot: 'LoadingIcon',
|
|
164
|
+
overridesResolver: (props, styles) => styles.loadingIcon
|
|
165
|
+
})({
|
|
166
|
+
color: 'text.primary'
|
|
167
|
+
});
|
|
147
168
|
export const TreeItemCheckbox = styled(/*#__PURE__*/React.forwardRef((props, ref) => {
|
|
148
169
|
const {
|
|
149
170
|
visible
|
|
@@ -180,7 +201,9 @@ const useUtilityClasses = ownerState => {
|
|
|
180
201
|
label: ['label'],
|
|
181
202
|
groupTransition: ['groupTransition'],
|
|
182
203
|
labelInput: ['labelInput'],
|
|
183
|
-
dragAndDropOverlay: ['dragAndDropOverlay']
|
|
204
|
+
dragAndDropOverlay: ['dragAndDropOverlay'],
|
|
205
|
+
errorIcon: ['errorIcon'],
|
|
206
|
+
loadingIcon: ['loadingIcon']
|
|
184
207
|
};
|
|
185
208
|
return composeClasses(slots, getTreeItemUtilityClass, classes);
|
|
186
209
|
};
|
|
@@ -219,6 +242,8 @@ export const TreeItem = /*#__PURE__*/React.forwardRef(function TreeItem(inProps,
|
|
|
219
242
|
getGroupTransitionProps,
|
|
220
243
|
getLabelInputProps,
|
|
221
244
|
getDragAndDropOverlayProps,
|
|
245
|
+
getErrorContainerProps,
|
|
246
|
+
getLoadingContainerProps,
|
|
222
247
|
status
|
|
223
248
|
} = useTreeItem({
|
|
224
249
|
id,
|
|
@@ -297,15 +322,31 @@ export const TreeItem = /*#__PURE__*/React.forwardRef(function TreeItem(inProps,
|
|
|
297
322
|
ownerState: {},
|
|
298
323
|
className: classes.dragAndDropOverlay
|
|
299
324
|
});
|
|
325
|
+
const ErrorIcon = slots.errorIcon ?? TreeItemErrorContainer;
|
|
326
|
+
const errorContainerProps = useSlotProps({
|
|
327
|
+
elementType: ErrorIcon,
|
|
328
|
+
getSlotProps: getErrorContainerProps,
|
|
329
|
+
externalSlotProps: slotProps.errorIcon,
|
|
330
|
+
ownerState: {},
|
|
331
|
+
className: classes.errorIcon
|
|
332
|
+
});
|
|
333
|
+
const LoadingIcon = slots.loadingIcon ?? TreeItemLoadingContainer;
|
|
334
|
+
const loadingContainerProps = useSlotProps({
|
|
335
|
+
elementType: LoadingIcon,
|
|
336
|
+
getSlotProps: getLoadingContainerProps,
|
|
337
|
+
externalSlotProps: slotProps.loadingIcon,
|
|
338
|
+
ownerState: {},
|
|
339
|
+
className: classes.loadingIcon
|
|
340
|
+
});
|
|
300
341
|
return /*#__PURE__*/_jsx(TreeItemProvider, _extends({}, getContextProviderProps(), {
|
|
301
342
|
children: /*#__PURE__*/_jsxs(Root, _extends({}, rootProps, {
|
|
302
343
|
children: [/*#__PURE__*/_jsxs(Content, _extends({}, contentProps, {
|
|
303
|
-
children: [/*#__PURE__*/
|
|
304
|
-
children: /*#__PURE__*/_jsx(TreeItemIcon, {
|
|
344
|
+
children: [/*#__PURE__*/_jsxs(IconContainer, _extends({}, iconContainerProps, {
|
|
345
|
+
children: [status.error && /*#__PURE__*/_jsx(ErrorIcon, _extends({}, errorContainerProps)), status.loading ? /*#__PURE__*/_jsx(LoadingIcon, _extends({}, loadingContainerProps)) : /*#__PURE__*/_jsx(TreeItemIcon, {
|
|
305
346
|
status: status,
|
|
306
347
|
slots: slots,
|
|
307
348
|
slotProps: slotProps
|
|
308
|
-
})
|
|
349
|
+
})]
|
|
309
350
|
})), /*#__PURE__*/_jsx(Checkbox, _extends({}, checkboxProps)), status.editing ? /*#__PURE__*/_jsx(LabelInput, _extends({}, labelInputProps)) : /*#__PURE__*/_jsx(Label, _extends({}, labelProps)), /*#__PURE__*/_jsx(DragAndDropOverlay, _extends({}, dragAndDropOverlayProps))]
|
|
310
351
|
})), children && /*#__PURE__*/_jsx(TreeItemGroupTransition, _extends({
|
|
311
352
|
as: GroupTransition
|
|
@@ -49,6 +49,18 @@ export interface TreeItemSlots extends TreeItemIconSlots {
|
|
|
49
49
|
* @default TreeItemDragAndDropOverlay
|
|
50
50
|
*/
|
|
51
51
|
dragAndDropOverlay?: React.ElementType;
|
|
52
|
+
/**
|
|
53
|
+
* The component that is rendered when the item is in an error state.
|
|
54
|
+
* Warning: This slot is only useful when using the `<RichTreeViewPro />` component is lazy loading is enabled.
|
|
55
|
+
* @default TreeItemErrorContainer
|
|
56
|
+
*/
|
|
57
|
+
errorIcon?: React.ElementType;
|
|
58
|
+
/**
|
|
59
|
+
* The component that is rendered when the item is in an loading state.
|
|
60
|
+
* Warning: This slot is only useful when using the `<RichTreeViewPro />` component is lazy loading is enabled.
|
|
61
|
+
* @default TreeItemLoadingContainer
|
|
62
|
+
*/
|
|
63
|
+
loadingIcon?: React.ElementType;
|
|
52
64
|
}
|
|
53
65
|
export interface TreeItemSlotProps extends TreeItemIconSlotProps {
|
|
54
66
|
root?: SlotComponentProps<'li', {}, {}>;
|
|
@@ -59,6 +71,8 @@ export interface TreeItemSlotProps extends TreeItemIconSlotProps {
|
|
|
59
71
|
label?: SlotComponentProps<'div', {}, {}>;
|
|
60
72
|
labelInput?: SlotComponentProps<'input', {}, {}>;
|
|
61
73
|
dragAndDropOverlay?: SlotComponentProps<'div', {}, {}>;
|
|
74
|
+
errorIcon?: SlotComponentProps<'div', {}, {}>;
|
|
75
|
+
loadingIcon?: SlotComponentProps<'div', {}, {}>;
|
|
62
76
|
}
|
|
63
77
|
export interface TreeItemProps extends Omit<UseTreeItemParameters, 'rootRef'>, Omit<React.HTMLAttributes<HTMLLIElement>, 'onFocus'> {
|
|
64
78
|
className?: string;
|
|
@@ -63,9 +63,11 @@ process.env.NODE_ENV !== "production" ? TreeItemIcon.propTypes = {
|
|
|
63
63
|
disabled: PropTypes.bool.isRequired,
|
|
64
64
|
editable: PropTypes.bool.isRequired,
|
|
65
65
|
editing: PropTypes.bool.isRequired,
|
|
66
|
+
error: PropTypes.bool.isRequired,
|
|
66
67
|
expandable: PropTypes.bool.isRequired,
|
|
67
68
|
expanded: PropTypes.bool.isRequired,
|
|
68
69
|
focused: PropTypes.bool.isRequired,
|
|
70
|
+
loading: PropTypes.bool.isRequired,
|
|
69
71
|
selected: PropTypes.bool.isRequired
|
|
70
72
|
}).isRequired
|
|
71
73
|
} : void 0;
|
|
@@ -1,4 +1,5 @@
|
|
|
1
1
|
import * as React from 'react';
|
|
2
|
+
import type { UseTreeViewLazyLoadingSignature } from '../../internals/plugins/useTreeViewLazyLoading';
|
|
2
3
|
import type { UseTreeViewSelectionSignature } from '../../internals/plugins/useTreeViewSelection';
|
|
3
4
|
import type { UseTreeViewExpansionSignature } from '../../internals/plugins/useTreeViewExpansion';
|
|
4
5
|
import type { UseTreeViewItemsSignature } from '../../internals/plugins/useTreeViewItems';
|
|
@@ -21,7 +22,7 @@ type UseTreeItemUtilsMinimalPlugins = readonly [UseTreeViewSelectionSignature, U
|
|
|
21
22
|
/**
|
|
22
23
|
* Plugins that `useTreeItemUtils` can use if they are present, but are not required.
|
|
23
24
|
*/
|
|
24
|
-
export type UseTreeItemUtilsOptionalPlugins = readonly [UseTreeViewLabelSignature];
|
|
25
|
+
export type UseTreeItemUtilsOptionalPlugins = readonly [UseTreeViewLabelSignature, UseTreeViewLazyLoadingSignature];
|
|
25
26
|
interface UseTreeItemUtilsReturnValue<TSignatures extends UseTreeItemUtilsMinimalPlugins, TOptionalSignatures extends UseTreeItemUtilsOptionalPlugins> {
|
|
26
27
|
interactions: UseTreeItemInteractions;
|
|
27
28
|
status: UseTreeItemStatus;
|
|
@@ -30,7 +31,7 @@ interface UseTreeItemUtilsReturnValue<TSignatures extends UseTreeItemUtilsMinima
|
|
|
30
31
|
*/
|
|
31
32
|
publicAPI: TreeViewPublicAPI<TSignatures, TOptionalSignatures>;
|
|
32
33
|
}
|
|
33
|
-
export declare const
|
|
34
|
+
export declare const itemHasChildren: (reactChildren: React.ReactNode) => boolean;
|
|
34
35
|
export declare const useTreeItemUtils: <TSignatures extends UseTreeItemUtilsMinimalPlugins = UseTreeItemUtilsMinimalPlugins, TOptionalSignatures extends UseTreeItemUtilsOptionalPlugins = UseTreeItemUtilsOptionalPlugins>({
|
|
35
36
|
itemId,
|
|
36
37
|
children
|
|
@@ -4,10 +4,11 @@ import { useTreeViewContext } from "../../internals/TreeViewProvider/index.js";
|
|
|
4
4
|
import { useTreeViewLabel } from "../../internals/plugins/useTreeViewLabel/index.js";
|
|
5
5
|
import { hasPlugin } from "../../internals/utils/plugins.js";
|
|
6
6
|
import { useSelector } from "../../internals/hooks/useSelector.js";
|
|
7
|
-
import { selectorIsItemExpanded } from "../../internals/plugins/useTreeViewExpansion/useTreeViewExpansion.selectors.js";
|
|
7
|
+
import { selectorIsItemExpandable, selectorIsItemExpanded } from "../../internals/plugins/useTreeViewExpansion/useTreeViewExpansion.selectors.js";
|
|
8
8
|
import { selectorIsItemFocused } from "../../internals/plugins/useTreeViewFocus/useTreeViewFocus.selectors.js";
|
|
9
9
|
import { selectorIsItemDisabled } from "../../internals/plugins/useTreeViewItems/useTreeViewItems.selectors.js";
|
|
10
10
|
import { selectorIsItemSelected } from "../../internals/plugins/useTreeViewSelection/useTreeViewSelection.selectors.js";
|
|
11
|
+
import { selectorGetTreeItemError, selectorIsItemLoading, selectorIsLazyLoadingEnabled } from "../../internals/plugins/useTreeViewLazyLoading/useTreeViewLazyLoading.selectors.js";
|
|
11
12
|
import { selectorIsItemBeingEdited, selectorIsItemEditable } from "../../internals/plugins/useTreeViewLabel/useTreeViewLabel.selectors.js";
|
|
12
13
|
|
|
13
14
|
/**
|
|
@@ -18,9 +19,9 @@ import { selectorIsItemBeingEdited, selectorIsItemEditable } from "../../interna
|
|
|
18
19
|
* Plugins that `useTreeItemUtils` can use if they are present, but are not required.
|
|
19
20
|
*/
|
|
20
21
|
|
|
21
|
-
export const
|
|
22
|
+
export const itemHasChildren = reactChildren => {
|
|
22
23
|
if (Array.isArray(reactChildren)) {
|
|
23
|
-
return reactChildren.length > 0 && reactChildren.some(
|
|
24
|
+
return reactChildren.length > 0 && reactChildren.some(itemHasChildren);
|
|
24
25
|
}
|
|
25
26
|
return Boolean(reactChildren);
|
|
26
27
|
};
|
|
@@ -37,6 +38,11 @@ export const useTreeItemUtils = ({
|
|
|
37
38
|
},
|
|
38
39
|
publicAPI
|
|
39
40
|
} = useTreeViewContext();
|
|
41
|
+
const isItemExpandable = useSelector(store, selectorIsItemExpandable, itemId);
|
|
42
|
+
const isLazyLoadingEnabled = useSelector(store, selectorIsLazyLoadingEnabled);
|
|
43
|
+
const loading = useSelector(store, state => isLazyLoadingEnabled ? selectorIsItemLoading(state, itemId) : false);
|
|
44
|
+
const error = useSelector(store, state => isLazyLoadingEnabled ? Boolean(selectorGetTreeItemError(state, itemId)) : false);
|
|
45
|
+
const isExpandable = itemHasChildren(children) || isItemExpandable;
|
|
40
46
|
const isExpanded = useSelector(store, selectorIsItemExpanded, itemId);
|
|
41
47
|
const isFocused = useSelector(store, selectorIsItemFocused, itemId);
|
|
42
48
|
const isSelected = useSelector(store, selectorIsItemSelected, itemId);
|
|
@@ -47,13 +53,15 @@ export const useTreeItemUtils = ({
|
|
|
47
53
|
isItemEditable: label.isItemEditable
|
|
48
54
|
}));
|
|
49
55
|
const status = {
|
|
50
|
-
expandable:
|
|
56
|
+
expandable: isExpandable,
|
|
51
57
|
expanded: isExpanded,
|
|
52
58
|
focused: isFocused,
|
|
53
59
|
selected: isSelected,
|
|
54
60
|
disabled: isDisabled,
|
|
55
61
|
editing: isEditing,
|
|
56
|
-
editable: isEditable
|
|
62
|
+
editable: isEditable,
|
|
63
|
+
loading,
|
|
64
|
+
error
|
|
57
65
|
};
|
|
58
66
|
const handleExpansion = event => {
|
|
59
67
|
if (status.disabled) {
|
|
@@ -66,7 +74,11 @@ export const useTreeItemUtils = ({
|
|
|
66
74
|
|
|
67
75
|
// If already expanded and trying to toggle selection don't close
|
|
68
76
|
if (status.expandable && !(multiple && selectorIsItemExpanded(store.value, itemId))) {
|
|
69
|
-
|
|
77
|
+
// make sure the children selection is propagated again
|
|
78
|
+
instance.setItemExpansion({
|
|
79
|
+
event,
|
|
80
|
+
itemId
|
|
81
|
+
});
|
|
70
82
|
}
|
|
71
83
|
};
|
|
72
84
|
const handleSelection = event => {
|
|
@@ -81,14 +93,14 @@ export const useTreeItemUtils = ({
|
|
|
81
93
|
if (event.shiftKey) {
|
|
82
94
|
instance.expandSelectionRange(event, itemId);
|
|
83
95
|
} else {
|
|
84
|
-
instance.
|
|
96
|
+
instance.setItemSelection({
|
|
85
97
|
event,
|
|
86
98
|
itemId,
|
|
87
99
|
keepExistingSelection: true
|
|
88
100
|
});
|
|
89
101
|
}
|
|
90
102
|
} else {
|
|
91
|
-
instance.
|
|
103
|
+
instance.setItemSelection({
|
|
92
104
|
event,
|
|
93
105
|
itemId,
|
|
94
106
|
shouldBeSelected: true
|
|
@@ -100,7 +112,7 @@ export const useTreeItemUtils = ({
|
|
|
100
112
|
if (multiSelect && hasShift) {
|
|
101
113
|
instance.expandSelectionRange(event, itemId);
|
|
102
114
|
} else {
|
|
103
|
-
instance.
|
|
115
|
+
instance.setItemSelection({
|
|
104
116
|
event,
|
|
105
117
|
itemId,
|
|
106
118
|
keepExistingSelection: multiSelect,
|
|
@@ -4,4 +4,4 @@ import { RichTreeViewPluginSignatures } from "../RichTreeView/RichTreeView.plugi
|
|
|
4
4
|
/**
|
|
5
5
|
* Hook that instantiates a [[TreeViewApiRef]].
|
|
6
6
|
*/
|
|
7
|
-
export declare const useTreeViewApiRef: <TSignatures extends readonly TreeViewAnyPluginSignature[] =
|
|
7
|
+
export declare const useTreeViewApiRef: <TSignatures extends readonly TreeViewAnyPluginSignature[] = RichTreeViewPluginSignatures>() => React.RefObject<TreeViewPublicAPI<TSignatures> | undefined>;
|
package/esm/index.js
CHANGED
package/esm/internals/index.d.ts
CHANGED
|
@@ -2,7 +2,7 @@ export { useTreeView } from "./useTreeView/index.js";
|
|
|
2
2
|
export { TreeViewProvider, useTreeViewContext } from "./TreeViewProvider/index.js";
|
|
3
3
|
export { RichTreeViewItems } from "./components/RichTreeViewItems.js";
|
|
4
4
|
export type { RichTreeViewItemsSlots, RichTreeViewItemsSlotProps } from './components/RichTreeViewItems';
|
|
5
|
-
export { unstable_resetCleanupTracking } from "./hooks/useInstanceEventHandler.js";
|
|
5
|
+
export { unstable_resetCleanupTracking, useInstanceEventHandler } from "./hooks/useInstanceEventHandler.js";
|
|
6
6
|
export { useSelector } from "./hooks/useSelector.js";
|
|
7
7
|
export type { TreeViewPlugin, TreeViewPluginSignature, ConvertPluginsIntoSignatures, MergeSignaturesProperty, TreeViewPublicAPI, TreeViewState, TreeViewExperimentalFeatures, TreeViewItemMeta, TreeViewInstance, TreeViewItemPlugin, TreeViewUsedStore } from './models';
|
|
8
8
|
export type { TreeViewCorePluginParameters } from './corePlugins';
|
|
@@ -21,6 +21,11 @@ export { selectorItemMetaLookup, selectorItemMeta, selectorItemIndex, selectorIt
|
|
|
21
21
|
export type { UseTreeViewItemsSignature, UseTreeViewItemsParameters, UseTreeViewItemsState } from './plugins/useTreeViewItems';
|
|
22
22
|
export { useTreeViewLabel } from "./plugins/useTreeViewLabel/index.js";
|
|
23
23
|
export type { UseTreeViewLabelSignature, UseTreeViewLabelParameters } from './plugins/useTreeViewLabel';
|
|
24
|
+
export { selectorIsItemExpanded } from "./plugins/useTreeViewExpansion/useTreeViewExpansion.selectors.js";
|
|
25
|
+
export { selectorIsItemSelected } from "./plugins/useTreeViewSelection/useTreeViewSelection.selectors.js";
|
|
26
|
+
export { selectorDataSourceState, selectorGetTreeItemError } from "./plugins/useTreeViewLazyLoading/useTreeViewLazyLoading.selectors.js";
|
|
27
|
+
export type { UseTreeViewLazyLoadingSignature } from './plugins/useTreeViewLazyLoading';
|
|
28
|
+
export type { UseTreeViewLazyLoadingParameters } from './plugins/useTreeViewLazyLoading';
|
|
24
29
|
export { useTreeViewJSXItems } from "./plugins/useTreeViewJSXItems/index.js";
|
|
25
30
|
export type { UseTreeViewJSXItemsSignature, UseTreeViewJSXItemsParameters } from './plugins/useTreeViewJSXItems';
|
|
26
31
|
export { createSelector } from "./utils/selectors.js";
|
package/esm/internals/index.js
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
export { useTreeView } from "./useTreeView/index.js";
|
|
2
2
|
export { TreeViewProvider, useTreeViewContext } from "./TreeViewProvider/index.js";
|
|
3
3
|
export { RichTreeViewItems } from "./components/RichTreeViewItems.js";
|
|
4
|
-
export { unstable_resetCleanupTracking } from "./hooks/useInstanceEventHandler.js";
|
|
4
|
+
export { unstable_resetCleanupTracking, useInstanceEventHandler } from "./hooks/useInstanceEventHandler.js";
|
|
5
5
|
export { useSelector } from "./hooks/useSelector.js";
|
|
6
6
|
|
|
7
7
|
// Core plugins
|
|
@@ -15,6 +15,9 @@ export { useTreeViewIcons } from "./plugins/useTreeViewIcons/index.js";
|
|
|
15
15
|
export { useTreeViewItems, buildSiblingIndexes, TREE_VIEW_ROOT_PARENT_ID } from "./plugins/useTreeViewItems/index.js";
|
|
16
16
|
export { selectorItemMetaLookup, selectorItemMeta, selectorItemIndex, selectorItemOrderedChildrenIds } from "./plugins/useTreeViewItems/useTreeViewItems.selectors.js";
|
|
17
17
|
export { useTreeViewLabel } from "./plugins/useTreeViewLabel/index.js";
|
|
18
|
+
export { selectorIsItemExpanded } from "./plugins/useTreeViewExpansion/useTreeViewExpansion.selectors.js";
|
|
19
|
+
export { selectorIsItemSelected } from "./plugins/useTreeViewSelection/useTreeViewSelection.selectors.js";
|
|
20
|
+
export { selectorDataSourceState, selectorGetTreeItemError } from "./plugins/useTreeViewLazyLoading/useTreeViewLazyLoading.selectors.js";
|
|
18
21
|
export { useTreeViewJSXItems } from "./plugins/useTreeViewJSXItems/index.js";
|
|
19
22
|
export { createSelector } from "./utils/selectors.js";
|
|
20
23
|
export { isTargetInDescendants } from "./utils/tree.js";
|
|
@@ -4,6 +4,7 @@ import useEnhancedEffect from '@mui/utils/useEnhancedEffect';
|
|
|
4
4
|
import { selectorIsItemExpandable, selectorIsItemExpanded } from "./useTreeViewExpansion.selectors.js";
|
|
5
5
|
import { createExpandedItemsMap, getExpansionTrigger } from "./useTreeViewExpansion.utils.js";
|
|
6
6
|
import { selectorItemMeta, selectorItemOrderedChildrenIds } from "../useTreeViewItems/useTreeViewItems.selectors.js";
|
|
7
|
+
import { publishTreeViewEvent } from "../../utils/publishTreeViewEvent.js";
|
|
7
8
|
export const useTreeViewExpansion = ({
|
|
8
9
|
instance,
|
|
9
10
|
store,
|
|
@@ -37,26 +38,48 @@ export const useTreeViewExpansion = ({
|
|
|
37
38
|
params.onExpandedItemsChange?.(event, value);
|
|
38
39
|
models.expandedItems.setControlledValue(value);
|
|
39
40
|
};
|
|
40
|
-
const
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
const isExpandedBefore = selectorIsItemExpanded(store.value, itemId);
|
|
46
|
-
if (isExpandedBefore === isExpanded) {
|
|
47
|
-
return;
|
|
48
|
-
}
|
|
41
|
+
const applyItemExpansion = useEventCallback(({
|
|
42
|
+
itemId,
|
|
43
|
+
event,
|
|
44
|
+
shouldBeExpanded
|
|
45
|
+
}) => {
|
|
49
46
|
let newExpanded;
|
|
50
|
-
if (
|
|
47
|
+
if (shouldBeExpanded) {
|
|
51
48
|
newExpanded = [itemId].concat(models.expandedItems.value);
|
|
52
49
|
} else {
|
|
53
50
|
newExpanded = models.expandedItems.value.filter(id => id !== itemId);
|
|
54
51
|
}
|
|
55
52
|
if (params.onItemExpansionToggle) {
|
|
56
|
-
params.onItemExpansionToggle(event, itemId,
|
|
53
|
+
params.onItemExpansionToggle(event, itemId, shouldBeExpanded);
|
|
57
54
|
}
|
|
58
55
|
setExpandedItems(event, newExpanded);
|
|
59
56
|
});
|
|
57
|
+
const setItemExpansion = useEventCallback(({
|
|
58
|
+
itemId,
|
|
59
|
+
event = null,
|
|
60
|
+
shouldBeExpanded
|
|
61
|
+
}) => {
|
|
62
|
+
const isExpandedBefore = selectorIsItemExpanded(store.value, itemId);
|
|
63
|
+
const cleanShouldBeExpanded = shouldBeExpanded ?? !isExpandedBefore;
|
|
64
|
+
if (isExpandedBefore === cleanShouldBeExpanded) {
|
|
65
|
+
return;
|
|
66
|
+
}
|
|
67
|
+
const eventParameters = {
|
|
68
|
+
isExpansionPrevented: false,
|
|
69
|
+
shouldBeExpanded: cleanShouldBeExpanded,
|
|
70
|
+
event,
|
|
71
|
+
itemId
|
|
72
|
+
};
|
|
73
|
+
publishTreeViewEvent(instance, 'beforeItemToggleExpansion', eventParameters);
|
|
74
|
+
if (eventParameters.isExpansionPrevented) {
|
|
75
|
+
return;
|
|
76
|
+
}
|
|
77
|
+
instance.applyItemExpansion({
|
|
78
|
+
itemId,
|
|
79
|
+
event,
|
|
80
|
+
shouldBeExpanded: cleanShouldBeExpanded
|
|
81
|
+
});
|
|
82
|
+
});
|
|
60
83
|
const expandAllSiblings = (event, itemId) => {
|
|
61
84
|
const itemMeta = selectorItemMeta(store.value, itemId);
|
|
62
85
|
if (itemMeta == null) {
|
|
@@ -80,7 +103,7 @@ export const useTreeViewExpansion = ({
|
|
|
80
103
|
},
|
|
81
104
|
instance: {
|
|
82
105
|
setItemExpansion,
|
|
83
|
-
|
|
106
|
+
applyItemExpansion,
|
|
84
107
|
expandAllSiblings
|
|
85
108
|
}
|
|
86
109
|
};
|
|
@@ -90,6 +90,8 @@ export declare const selectorIsItemExpandable: ((state: any, itemId: string | nu
|
|
|
90
90
|
[itemId: string]: number;
|
|
91
91
|
};
|
|
92
92
|
};
|
|
93
|
+
loading: boolean;
|
|
94
|
+
error: Error | null;
|
|
93
95
|
}) => {
|
|
94
96
|
[itemId: string]: import("../..").TreeViewItemMeta;
|
|
95
97
|
};
|
|
@@ -109,6 +111,8 @@ export declare const selectorIsItemExpandable: ((state: any, itemId: string | nu
|
|
|
109
111
|
[itemId: string]: number;
|
|
110
112
|
};
|
|
111
113
|
};
|
|
114
|
+
loading: boolean;
|
|
115
|
+
error: Error | null;
|
|
112
116
|
}) => {
|
|
113
117
|
[itemId: string]: import("../..").TreeViewItemMeta;
|
|
114
118
|
}) & {
|
|
@@ -7,26 +7,38 @@ import { UseTreeViewLabelSignature } from "../useTreeViewLabel/index.js";
|
|
|
7
7
|
export interface UseTreeViewExpansionPublicAPI {
|
|
8
8
|
/**
|
|
9
9
|
* Change the expansion status of a given item.
|
|
10
|
-
* @param {
|
|
11
|
-
* @param {string} itemId The id of the item to expand of collapse.
|
|
12
|
-
* @param {
|
|
10
|
+
* @param {object} parameters The parameters of the method.
|
|
11
|
+
* @param {string} parameters.itemId The id of the item to expand of collapse.
|
|
12
|
+
* @param {React.SyntheticEvent} parameters.event The DOM event that triggered the change.
|
|
13
|
+
* @param {boolean} parameters.shouldBeExpanded If `true` the item will be expanded. If `false` the item will be collapsed. If not defined, the item's expansion status will be the toggled.
|
|
13
14
|
*/
|
|
14
|
-
setItemExpansion: (
|
|
15
|
+
setItemExpansion: (parameters: {
|
|
16
|
+
itemId: string;
|
|
17
|
+
event?: React.SyntheticEvent;
|
|
18
|
+
shouldBeExpanded?: boolean;
|
|
19
|
+
}) => void;
|
|
15
20
|
}
|
|
16
21
|
export interface UseTreeViewExpansionInstance extends UseTreeViewExpansionPublicAPI {
|
|
17
|
-
/**
|
|
18
|
-
* Toggle the current expansion of an item.
|
|
19
|
-
* If it is expanded, it will be collapsed, and vice versa.
|
|
20
|
-
* @param {React.SyntheticEvent} event The DOM event that triggered the change.
|
|
21
|
-
* @param {TreeViewItemId} itemId The id of the item to toggle.
|
|
22
|
-
*/
|
|
23
|
-
toggleItemExpansion: (event: React.SyntheticEvent, itemId: TreeViewItemId) => void;
|
|
24
22
|
/**
|
|
25
23
|
* Expand all the siblings (i.e.: the items that have the same parent) of a given item.
|
|
26
24
|
* @param {React.SyntheticEvent} event The DOM event that triggered the change.
|
|
27
25
|
* @param {TreeViewItemId} itemId The id of the item whose siblings will be expanded.
|
|
28
26
|
*/
|
|
29
27
|
expandAllSiblings: (event: React.KeyboardEvent, itemId: TreeViewItemId) => void;
|
|
28
|
+
/**
|
|
29
|
+
* APply the new expansion status of a given item.
|
|
30
|
+
* Is used by the `setItemExpansion` method and by the `useTreeViewLazyLoading` plugin.
|
|
31
|
+
* Unlike `setItemExpansion`, this method does not trigger the lazy loading.
|
|
32
|
+
* @param {object} parameters The parameters of the method.
|
|
33
|
+
* @param {string} parameters.itemId The id of the item to expand of collapse.
|
|
34
|
+
* @param {React.SyntheticEvent | null} parameters.event The DOM event that triggered the change.
|
|
35
|
+
* @param {boolean} parameters.shouldBeExpanded If `true` the item will be expanded. If `false` the item will be collapsed.
|
|
36
|
+
*/
|
|
37
|
+
applyItemExpansion: (parameters: {
|
|
38
|
+
itemId: string;
|
|
39
|
+
event: React.SyntheticEvent | null;
|
|
40
|
+
shouldBeExpanded: boolean;
|
|
41
|
+
}) => void;
|
|
30
42
|
}
|
|
31
43
|
export interface UseTreeViewExpansionParameters {
|
|
32
44
|
/**
|
|
@@ -42,17 +54,17 @@ export interface UseTreeViewExpansionParameters {
|
|
|
42
54
|
defaultExpandedItems?: string[];
|
|
43
55
|
/**
|
|
44
56
|
* Callback fired when Tree Items are expanded/collapsed.
|
|
45
|
-
* @param {React.SyntheticEvent} event The DOM event that triggered the change.
|
|
57
|
+
* @param {React.SyntheticEvent} event The DOM event that triggered the change. Can be null when the change is caused by the `publicAPI.setItemExpansion()` method.
|
|
46
58
|
* @param {array} itemIds The ids of the expanded items.
|
|
47
59
|
*/
|
|
48
|
-
onExpandedItemsChange?: (event: React.SyntheticEvent, itemIds: string[]) => void;
|
|
60
|
+
onExpandedItemsChange?: (event: React.SyntheticEvent | null, itemIds: string[]) => void;
|
|
49
61
|
/**
|
|
50
62
|
* Callback fired when a Tree Item is expanded or collapsed.
|
|
51
|
-
* @param {React.SyntheticEvent} event The DOM event that triggered the change.
|
|
63
|
+
* @param {React.SyntheticEvent | null} event The DOM event that triggered the change. Can be null when the change is caused by the `publicAPI.setItemExpansion()` method.
|
|
52
64
|
* @param {array} itemId The itemId of the modified item.
|
|
53
65
|
* @param {array} isExpanded `true` if the item has just been expanded, `false` if it has just been collapsed.
|
|
54
66
|
*/
|
|
55
|
-
onItemExpansionToggle?: (event: React.SyntheticEvent, itemId: string, isExpanded: boolean) => void;
|
|
67
|
+
onItemExpansionToggle?: (event: React.SyntheticEvent | null, itemId: string, isExpanded: boolean) => void;
|
|
56
68
|
/**
|
|
57
69
|
* The slot that triggers the item's expansion when clicked.
|
|
58
70
|
* @default 'content'
|
|
@@ -66,6 +78,16 @@ export interface UseTreeViewExpansionState {
|
|
|
66
78
|
expansionTrigger: 'content' | 'iconContainer';
|
|
67
79
|
};
|
|
68
80
|
}
|
|
81
|
+
interface UseTreeViewExpansionEventLookup {
|
|
82
|
+
beforeItemToggleExpansion: {
|
|
83
|
+
params: {
|
|
84
|
+
isExpansionPrevented: boolean;
|
|
85
|
+
shouldBeExpanded: boolean;
|
|
86
|
+
event: React.SyntheticEvent | null;
|
|
87
|
+
itemId: TreeViewItemId;
|
|
88
|
+
};
|
|
89
|
+
};
|
|
90
|
+
}
|
|
69
91
|
export type UseTreeViewExpansionSignature = TreeViewPluginSignature<{
|
|
70
92
|
params: UseTreeViewExpansionParameters;
|
|
71
93
|
defaultizedParams: UseTreeViewExpansionDefaultizedParameters;
|
|
@@ -75,4 +97,6 @@ export type UseTreeViewExpansionSignature = TreeViewPluginSignature<{
|
|
|
75
97
|
state: UseTreeViewExpansionState;
|
|
76
98
|
dependencies: [UseTreeViewItemsSignature];
|
|
77
99
|
optionalDependencies: [UseTreeViewLabelSignature];
|
|
78
|
-
|
|
100
|
+
events: UseTreeViewExpansionEventLookup;
|
|
101
|
+
}>;
|
|
102
|
+
export {};
|