Skip to content

Commit

Permalink
[TreeView] Add getItemTree and getItemOrderedChildrenIds methods …
Browse files Browse the repository at this point in the history
…to the public API (#13804)
  • Loading branch information
flaviendelangle authored Jul 11, 2024
1 parent 6fb7cb0 commit 4306689
Show file tree
Hide file tree
Showing 17 changed files with 488 additions and 23 deletions.
Original file line number Diff line number Diff line change
@@ -0,0 +1,68 @@
import * as React from 'react';
import Box from '@mui/material/Box';
import Stack from '@mui/material/Stack';
import Typography from '@mui/material/Typography';
import { RichTreeView } from '@mui/x-tree-view/RichTreeView';

import { useTreeViewApiRef } from '@mui/x-tree-view/hooks';

const MUI_X_PRODUCTS = [
{
id: 'grid',
label: 'Data Grid',
children: [
{ id: 'grid-community', label: '@mui/x-data-grid' },
{ id: 'grid-pro', label: '@mui/x-data-grid-pro' },
{ id: 'grid-premium', label: '@mui/x-data-grid-premium' },
],
},
{
id: 'pickers',
label: 'Date and Time Pickers',
children: [
{ id: 'pickers-community', label: '@mui/x-date-pickers' },
{ id: 'pickers-pro', label: '@mui/x-date-pickers-pro' },
],
},
{
id: 'charts',
label: 'Charts',
children: [{ id: 'charts-community', label: '@mui/x-charts' }],
},
{
id: 'tree-view',
label: 'Tree View',
children: [{ id: 'tree-view-community', label: '@mui/x-tree-view' }],
},
];

export default function ApiMethodGetItemOrderedChildrenIds() {
const apiRef = useTreeViewApiRef();
const [isSelectedItemLeaf, setIsSelectedItemLeaf] = React.useState(null);

const handleSelectedItemsChange = (event, itemId) => {
if (itemId == null) {
setIsSelectedItemLeaf(null);
} else {
const children = apiRef.current.getItemOrderedChildrenIds(itemId);
setIsSelectedItemLeaf(children.length === 0);
}
};

return (
<Stack spacing={2}>
<Typography>
{isSelectedItemLeaf == null && 'No item selected'}
{isSelectedItemLeaf === true && 'The selected item is a leaf'}
{isSelectedItemLeaf === false && 'The selected item is a node with children'}
</Typography>
<Box sx={{ minHeight: 352, minWidth: 300 }}>
<RichTreeView
items={MUI_X_PRODUCTS}
apiRef={apiRef}
onSelectedItemsChange={handleSelectedItemsChange}
/>
</Box>
</Stack>
);
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,73 @@
import * as React from 'react';
import Box from '@mui/material/Box';
import Stack from '@mui/material/Stack';
import Typography from '@mui/material/Typography';
import { RichTreeView } from '@mui/x-tree-view/RichTreeView';
import { TreeViewBaseItem } from '@mui/x-tree-view/models';
import { useTreeViewApiRef } from '@mui/x-tree-view/hooks';

const MUI_X_PRODUCTS: TreeViewBaseItem[] = [
{
id: 'grid',
label: 'Data Grid',
children: [
{ id: 'grid-community', label: '@mui/x-data-grid' },
{ id: 'grid-pro', label: '@mui/x-data-grid-pro' },
{ id: 'grid-premium', label: '@mui/x-data-grid-premium' },
],
},
{
id: 'pickers',
label: 'Date and Time Pickers',
children: [
{ id: 'pickers-community', label: '@mui/x-date-pickers' },
{ id: 'pickers-pro', label: '@mui/x-date-pickers-pro' },
],
},
{
id: 'charts',
label: 'Charts',
children: [{ id: 'charts-community', label: '@mui/x-charts' }],
},
{
id: 'tree-view',
label: 'Tree View',
children: [{ id: 'tree-view-community', label: '@mui/x-tree-view' }],
},
];

export default function ApiMethodGetItemOrderedChildrenIds() {
const apiRef = useTreeViewApiRef();
const [isSelectedItemLeaf, setIsSelectedItemLeaf] = React.useState<boolean | null>(
null,
);

const handleSelectedItemsChange = (
event: React.SyntheticEvent,
itemId: string | null,
) => {
if (itemId == null) {
setIsSelectedItemLeaf(null);
} else {
const children = apiRef.current!.getItemOrderedChildrenIds(itemId);
setIsSelectedItemLeaf(children.length === 0);
}
};

return (
<Stack spacing={2}>
<Typography>
{isSelectedItemLeaf == null && 'No item selected'}
{isSelectedItemLeaf === true && 'The selected item is a leaf'}
{isSelectedItemLeaf === false && 'The selected item is a node with children'}
</Typography>
<Box sx={{ minHeight: 352, minWidth: 300 }}>
<RichTreeView
items={MUI_X_PRODUCTS}
apiRef={apiRef}
onSelectedItemsChange={handleSelectedItemsChange}
/>
</Box>
</Stack>
);
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
<Typography>
{isSelectedItemLeaf == null && 'No item selected'}
{isSelectedItemLeaf === true && 'The selected item is a leaf'}
{isSelectedItemLeaf === false && 'The selected item is a node with children'}
</Typography>
<Box sx={{ minHeight: 352, minWidth: 300 }}>
<RichTreeView
items={MUI_X_PRODUCTS}
apiRef={apiRef}
onSelectedItemsChange={handleSelectedItemsChange}
/>
</Box>
66 changes: 66 additions & 0 deletions docs/data/tree-view/rich-tree-view/items/ApiMethodGetItemTree.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,66 @@
import * as React from 'react';
import Box from '@mui/material/Box';
import Stack from '@mui/material/Stack';
import Button from '@mui/material/Button';
import Typography from '@mui/material/Typography';
import { RichTreeView } from '@mui/x-tree-view/RichTreeView';

import { useTreeViewApiRef } from '@mui/x-tree-view/hooks';

const MUI_X_PRODUCTS = [
{
id: 'grid',
label: 'Data Grid',
children: [
{ id: 'grid-community', label: '@mui/x-data-grid' },
{ id: 'grid-pro', label: '@mui/x-data-grid-pro' },
{ id: 'grid-premium', label: '@mui/x-data-grid-premium' },
],
},
{
id: 'pickers',
label: 'Date and Time Pickers',
children: [
{ id: 'pickers-community', label: '@mui/x-date-pickers' },
{ id: 'pickers-pro', label: '@mui/x-date-pickers-pro' },
],
},
{
id: 'charts',
label: 'Charts',
children: [{ id: 'charts-community', label: '@mui/x-charts' }],
},
{
id: 'tree-view',
label: 'Tree View',
children: [{ id: 'tree-view-community', label: '@mui/x-tree-view' }],
},
];

export default function ApiMethodGetItemTree() {
const apiRef = useTreeViewApiRef();

const [items, setItems] = React.useState(MUI_X_PRODUCTS);
const [itemOnTop, setItemOnTop] = React.useState(items[0].label);

const handleInvertItems = () => {
setItems((prevItems) => [...prevItems].reverse());
};

const handleUpdateItemOnTop = () => {
setItemOnTop(apiRef.current.getItemTree()[0].label);
};

return (
<Stack spacing={2}>
<Stack direction="row" spacing={2}>
<Button onClick={handleInvertItems}>Invert first tree</Button>
<Button onClick={handleUpdateItemOnTop}>Update item on top</Button>
</Stack>
<Typography>Item on top: {itemOnTop}</Typography>
<Box sx={{ minHeight: 352, minWidth: 300 }}>
<RichTreeView apiRef={apiRef} items={items} />
</Box>
</Stack>
);
}
66 changes: 66 additions & 0 deletions docs/data/tree-view/rich-tree-view/items/ApiMethodGetItemTree.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,66 @@
import * as React from 'react';
import Box from '@mui/material/Box';
import Stack from '@mui/material/Stack';
import Button from '@mui/material/Button';
import Typography from '@mui/material/Typography';
import { RichTreeView } from '@mui/x-tree-view/RichTreeView';
import { TreeViewBaseItem } from '@mui/x-tree-view/models';
import { useTreeViewApiRef } from '@mui/x-tree-view/hooks';

const MUI_X_PRODUCTS: TreeViewBaseItem[] = [
{
id: 'grid',
label: 'Data Grid',
children: [
{ id: 'grid-community', label: '@mui/x-data-grid' },
{ id: 'grid-pro', label: '@mui/x-data-grid-pro' },
{ id: 'grid-premium', label: '@mui/x-data-grid-premium' },
],
},
{
id: 'pickers',
label: 'Date and Time Pickers',
children: [
{ id: 'pickers-community', label: '@mui/x-date-pickers' },
{ id: 'pickers-pro', label: '@mui/x-date-pickers-pro' },
],
},
{
id: 'charts',
label: 'Charts',
children: [{ id: 'charts-community', label: '@mui/x-charts' }],
},
{
id: 'tree-view',
label: 'Tree View',
children: [{ id: 'tree-view-community', label: '@mui/x-tree-view' }],
},
];

export default function ApiMethodGetItemTree() {
const apiRef = useTreeViewApiRef();

const [items, setItems] = React.useState(MUI_X_PRODUCTS);
const [itemOnTop, setItemOnTop] = React.useState(items[0].label);

const handleInvertItems = () => {
setItems((prevItems) => [...prevItems].reverse());
};

const handleUpdateItemOnTop = () => {
setItemOnTop(apiRef.current!.getItemTree()[0].label);
};

return (
<Stack spacing={2}>
<Stack direction="row" spacing={2}>
<Button onClick={handleInvertItems}>Invert first tree</Button>
<Button onClick={handleUpdateItemOnTop}>Update item on top</Button>
</Stack>
<Typography>Item on top: {itemOnTop}</Typography>
<Box sx={{ minHeight: 352, minWidth: 300 }}>
<RichTreeView apiRef={apiRef} items={items} />
</Box>
</Stack>
);
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
<Stack direction="row" spacing={2}>
<Button onClick={handleInvertItems}>Invert first tree</Button>
<Button onClick={handleUpdateItemOnTop}>Update item on top</Button>
</Stack>
<Typography>Item on top: {itemOnTop}</Typography>
<Box sx={{ minHeight: 352, minWidth: 300 }}>
<RichTreeView apiRef={apiRef} items={items} />
</Box>
23 changes: 23 additions & 0 deletions docs/data/tree-view/rich-tree-view/items/items.md
Original file line number Diff line number Diff line change
Expand Up @@ -170,3 +170,26 @@ const itemElement = apiRef.current.getItemDOMElement(
```

{{"demo": "ApiMethodGetItemDOMElement.js", "defaultCodeOpen": false}}

### Get the current item tree

Use the `getItemTree` API method to get the current item tree.

```ts
const itemTree = apiRef.current.getItemTree();
```

{{"demo": "ApiMethodGetItemTree.js", "defaultCodeOpen": false}}

### Get an item's children by ID

Use the `getItemOrderedChildrenIds` API method to get an item's children by its ID.

```ts
const childrenIds = apiRef.current.getItemOrderedChildrenIds(
// The id of the item to retrieve the children from
itemId,
);
```

{{"demo": "ApiMethodGetItemOrderedChildrenIds.js", "defaultCodeOpen": false}}
2 changes: 1 addition & 1 deletion docs/pages/x/api/tree-view/rich-tree-view.json
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@
"apiRef": {
"type": {
"name": "shape",
"description": "{ current?: { focusItem: func, getItem: func, getItemDOMElement: func, selectItem: func, setItemExpansion: func } }"
"description": "{ current?: { focusItem: func, getItem: func, getItemDOMElement: func, getItemOrderedChildrenIds: func, getItemTree: func, selectItem: func, setItemExpansion: func } }"
}
},
"checkboxSelection": { "type": { "name": "bool" }, "default": "false" },
Expand Down
2 changes: 1 addition & 1 deletion docs/pages/x/api/tree-view/simple-tree-view.json
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@
"apiRef": {
"type": {
"name": "shape",
"description": "{ current?: { focusItem: func, getItem: func, getItemDOMElement: func, selectItem: func, setItemExpansion: func } }"
"description": "{ current?: { focusItem: func, getItem: func, getItemDOMElement: func, getItemOrderedChildrenIds: func, getItemTree: func, selectItem: func, setItemExpansion: func } }"
}
},
"checkboxSelection": { "type": { "name": "bool" }, "default": "false" },
Expand Down
2 changes: 1 addition & 1 deletion docs/pages/x/api/tree-view/tree-view.json
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@
"apiRef": {
"type": {
"name": "shape",
"description": "{ current?: { focusItem: func, getItem: func, getItemDOMElement: func, selectItem: func, setItemExpansion: func } }"
"description": "{ current?: { focusItem: func, getItem: func, getItemDOMElement: func, getItemOrderedChildrenIds: func, getItemTree: func, selectItem: func, setItemExpansion: func } }"
}
},
"checkboxSelection": { "type": { "name": "bool" }, "default": "false" },
Expand Down
2 changes: 2 additions & 0 deletions packages/x-tree-view/src/RichTreeView/RichTreeView.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -152,6 +152,8 @@ RichTreeView.propTypes = {
focusItem: PropTypes.func.isRequired,
getItem: PropTypes.func.isRequired,
getItemDOMElement: PropTypes.func.isRequired,
getItemOrderedChildrenIds: PropTypes.func.isRequired,
getItemTree: PropTypes.func.isRequired,
selectItem: PropTypes.func.isRequired,
setItemExpansion: PropTypes.func.isRequired,
}),
Expand Down
2 changes: 2 additions & 0 deletions packages/x-tree-view/src/SimpleTreeView/SimpleTreeView.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -111,6 +111,8 @@ SimpleTreeView.propTypes = {
focusItem: PropTypes.func.isRequired,
getItem: PropTypes.func.isRequired,
getItemDOMElement: PropTypes.func.isRequired,
getItemOrderedChildrenIds: PropTypes.func.isRequired,
getItemTree: PropTypes.func.isRequired,
selectItem: PropTypes.func.isRequired,
setItemExpansion: PropTypes.func.isRequired,
}),
Expand Down
2 changes: 2 additions & 0 deletions packages/x-tree-view/src/TreeView/TreeView.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -96,6 +96,8 @@ TreeView.propTypes = {
focusItem: PropTypes.func.isRequired,
getItem: PropTypes.func.isRequired,
getItemDOMElement: PropTypes.func.isRequired,
getItemOrderedChildrenIds: PropTypes.func.isRequired,
getItemTree: PropTypes.func.isRequired,
selectItem: PropTypes.func.isRequired,
setItemExpansion: PropTypes.func.isRequired,
}),
Expand Down
Loading

0 comments on commit 4306689

Please sign in to comment.