@usefui/components 1.7.1 → 1.7.2
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 +6 -0
- package/dist/index.d.mts +14 -124
- package/dist/index.d.ts +14 -124
- package/dist/index.js +128 -326
- package/dist/index.mjs +127 -318
- package/package.json +3 -3
- package/src/badge/Badge.stories.tsx +32 -0
- package/src/badge/index.tsx +4 -0
- package/src/badge/styles/index.ts +26 -0
- package/src/button/Button.stories.tsx +93 -0
- package/src/button/styles/index.ts +23 -31
- package/src/dialog/index.tsx +17 -20
- package/src/dropdown/Dropdown.stories.tsx +87 -0
- package/src/dropdown/index.tsx +13 -1
- package/src/dropdown/styles/index.ts +14 -6
- package/src/field/styles/index.ts +7 -21
- package/src/index.ts +0 -3
- package/src/message-bubble/MessageBubble.stories.tsx +27 -7
- package/src/message-bubble/index.tsx +6 -2
- package/src/resizable/Resizable.stories.tsx +19 -22
- package/src/resizable/index.tsx +9 -5
- package/src/resizable/styles/index.ts +5 -2
- package/src/__tests__/Tree.test.tsx +0 -275
- package/src/tree/Tree.stories.tsx +0 -141
- package/src/tree/hooks/tree-node-provider.tsx +0 -50
- package/src/tree/hooks/tree-provider.tsx +0 -75
- package/src/tree/index.tsx +0 -231
- package/src/tree/styles/index.ts +0 -23
|
@@ -1,141 +0,0 @@
|
|
|
1
|
-
import React from "react";
|
|
2
|
-
import type { Meta, StoryObj } from "@storybook/react";
|
|
3
|
-
|
|
4
|
-
import { Page, Tree } from "..";
|
|
5
|
-
import { ComponentSizeEnum, ComponentVariantEnum } from "../../../../types";
|
|
6
|
-
|
|
7
|
-
const meta = {
|
|
8
|
-
title: "Components/Tree",
|
|
9
|
-
component: Tree,
|
|
10
|
-
tags: ["autodocs"],
|
|
11
|
-
decorators: [
|
|
12
|
-
(Story) => (
|
|
13
|
-
<Page>
|
|
14
|
-
<Page.Content className="p-medium-30">
|
|
15
|
-
<Story />
|
|
16
|
-
</Page.Content>
|
|
17
|
-
</Page>
|
|
18
|
-
),
|
|
19
|
-
],
|
|
20
|
-
} satisfies Meta<typeof Tree>;
|
|
21
|
-
export default meta;
|
|
22
|
-
|
|
23
|
-
type Story = StoryObj<typeof meta>;
|
|
24
|
-
|
|
25
|
-
export const Default: Story = {
|
|
26
|
-
argTypes: {
|
|
27
|
-
spacing: {
|
|
28
|
-
options: [
|
|
29
|
-
ComponentSizeEnum.Small,
|
|
30
|
-
ComponentSizeEnum.Medium,
|
|
31
|
-
ComponentSizeEnum.Large,
|
|
32
|
-
],
|
|
33
|
-
control: { type: "radio" },
|
|
34
|
-
},
|
|
35
|
-
variant: {
|
|
36
|
-
options: [
|
|
37
|
-
ComponentVariantEnum.Primary,
|
|
38
|
-
ComponentVariantEnum.Secondary,
|
|
39
|
-
ComponentVariantEnum.Tertiary,
|
|
40
|
-
ComponentVariantEnum.Mono,
|
|
41
|
-
ComponentVariantEnum.Border,
|
|
42
|
-
ComponentVariantEnum.Ghost,
|
|
43
|
-
],
|
|
44
|
-
control: { type: "radio" },
|
|
45
|
-
},
|
|
46
|
-
sizing: {
|
|
47
|
-
options: [
|
|
48
|
-
ComponentSizeEnum.Small,
|
|
49
|
-
ComponentSizeEnum.Medium,
|
|
50
|
-
ComponentSizeEnum.Large,
|
|
51
|
-
],
|
|
52
|
-
control: { type: "radio" },
|
|
53
|
-
},
|
|
54
|
-
},
|
|
55
|
-
render: ({ ...args }) => (
|
|
56
|
-
<Tree.Root>
|
|
57
|
-
<Tree>
|
|
58
|
-
<Tree.Node nodeId="src">
|
|
59
|
-
<Tree.Trigger nodeId="src">src</Tree.Trigger>
|
|
60
|
-
<Tree.Content nodeId="src">
|
|
61
|
-
<Tree.Node level={1} nodeId="index.ts">
|
|
62
|
-
<Tree.Trigger nodeId="index.ts">index.ts</Tree.Trigger>
|
|
63
|
-
</Tree.Node>
|
|
64
|
-
</Tree.Content>
|
|
65
|
-
</Tree.Node>
|
|
66
|
-
</Tree>
|
|
67
|
-
</Tree.Root>
|
|
68
|
-
),
|
|
69
|
-
};
|
|
70
|
-
|
|
71
|
-
export const DefaultOpen: Story = {
|
|
72
|
-
render: ({ ...args }) => (
|
|
73
|
-
<Tree.Root>
|
|
74
|
-
<Tree>
|
|
75
|
-
<Tree.Node nodeId="src">
|
|
76
|
-
<Tree.Trigger nodeId="src">src</Tree.Trigger>
|
|
77
|
-
<Tree.Content nodeId="src" defaultOpen>
|
|
78
|
-
<Tree.Node level={1} nodeId="index.ts">
|
|
79
|
-
<Tree.Trigger nodeId="index.ts">index.ts</Tree.Trigger>
|
|
80
|
-
</Tree.Node>
|
|
81
|
-
</Tree.Content>
|
|
82
|
-
</Tree.Node>
|
|
83
|
-
</Tree>
|
|
84
|
-
</Tree.Root>
|
|
85
|
-
),
|
|
86
|
-
};
|
|
87
|
-
|
|
88
|
-
export const Nested: Story = {
|
|
89
|
-
render: ({ ...args }) => (
|
|
90
|
-
<Tree.Root>
|
|
91
|
-
<Tree>
|
|
92
|
-
<Tree.Node nodeId="src">
|
|
93
|
-
<Tree.Trigger nodeId="src">src</Tree.Trigger>
|
|
94
|
-
<Tree.Content nodeId="src" defaultOpen>
|
|
95
|
-
<Tree.Node level={1} nodeId="components">
|
|
96
|
-
<Tree.Trigger nodeId="components">components</Tree.Trigger>
|
|
97
|
-
<Tree.Content nodeId="components" defaultOpen>
|
|
98
|
-
<Tree.Node level={2} nodeId="button.ts">
|
|
99
|
-
<Tree.Trigger nodeId="button.ts">button.ts</Tree.Trigger>
|
|
100
|
-
</Tree.Node>
|
|
101
|
-
<Tree.Node level={2} nodeId="card.ts" isLast>
|
|
102
|
-
<Tree.Trigger nodeId="card.ts">card.ts</Tree.Trigger>
|
|
103
|
-
</Tree.Node>
|
|
104
|
-
</Tree.Content>
|
|
105
|
-
</Tree.Node>
|
|
106
|
-
<Tree.Node level={1} nodeId="index.ts" isLast>
|
|
107
|
-
<Tree.Trigger nodeId="index.ts">index.ts</Tree.Trigger>
|
|
108
|
-
</Tree.Node>
|
|
109
|
-
</Tree.Content>
|
|
110
|
-
</Tree.Node>
|
|
111
|
-
</Tree>
|
|
112
|
-
</Tree.Root>
|
|
113
|
-
),
|
|
114
|
-
};
|
|
115
|
-
|
|
116
|
-
export const Group: Story = {
|
|
117
|
-
render: ({ ...args }) => (
|
|
118
|
-
<Tree.Root>
|
|
119
|
-
<Tree>
|
|
120
|
-
{["src", "public", "tests", "docs", "config"].map(
|
|
121
|
-
(item, index, array) => (
|
|
122
|
-
<Tree.Node
|
|
123
|
-
key={item}
|
|
124
|
-
nodeId={item}
|
|
125
|
-
isLast={index === array.length - 1}
|
|
126
|
-
>
|
|
127
|
-
<Tree.Trigger nodeId={item}>{item}</Tree.Trigger>
|
|
128
|
-
<Tree.Content nodeId={item}>
|
|
129
|
-
<Tree.Node level={1} nodeId={`${item}/index.ts`} isLast>
|
|
130
|
-
<Tree.Trigger nodeId={`${item}/index.ts`}>
|
|
131
|
-
index.ts
|
|
132
|
-
</Tree.Trigger>
|
|
133
|
-
</Tree.Node>
|
|
134
|
-
</Tree.Content>
|
|
135
|
-
</Tree.Node>
|
|
136
|
-
),
|
|
137
|
-
)}
|
|
138
|
-
</Tree>
|
|
139
|
-
</Tree.Root>
|
|
140
|
-
),
|
|
141
|
-
};
|
|
@@ -1,50 +0,0 @@
|
|
|
1
|
-
"use client";
|
|
2
|
-
|
|
3
|
-
import React, { createContext, useContext } from "react";
|
|
4
|
-
import { IReactChildren, IComponentAPI } from "../../../../../types";
|
|
5
|
-
|
|
6
|
-
const defaultTreeNodeAPI: IComponentAPI = {
|
|
7
|
-
id: "",
|
|
8
|
-
states: {},
|
|
9
|
-
methods: {},
|
|
10
|
-
};
|
|
11
|
-
|
|
12
|
-
const TreeNodeContext = createContext<IComponentAPI>(defaultTreeNodeAPI);
|
|
13
|
-
export const useTreeNode = () => useContext(TreeNodeContext);
|
|
14
|
-
|
|
15
|
-
export interface ITreeNodeProviderProperties extends IReactChildren {
|
|
16
|
-
nodeId: string;
|
|
17
|
-
level: number;
|
|
18
|
-
isLast: boolean;
|
|
19
|
-
}
|
|
20
|
-
|
|
21
|
-
export const TreeNodeProvider = ({
|
|
22
|
-
children,
|
|
23
|
-
nodeId,
|
|
24
|
-
level,
|
|
25
|
-
isLast,
|
|
26
|
-
}: ITreeNodeProviderProperties): React.JSX.Element => {
|
|
27
|
-
const context = useTreeNodeProviderContext({ nodeId, level, isLast });
|
|
28
|
-
|
|
29
|
-
return (
|
|
30
|
-
<TreeNodeContext.Provider value={context}>
|
|
31
|
-
{children}
|
|
32
|
-
</TreeNodeContext.Provider>
|
|
33
|
-
);
|
|
34
|
-
};
|
|
35
|
-
|
|
36
|
-
function useTreeNodeProviderContext({
|
|
37
|
-
nodeId,
|
|
38
|
-
level,
|
|
39
|
-
isLast,
|
|
40
|
-
}: Omit<ITreeNodeProviderProperties, "children">): IComponentAPI {
|
|
41
|
-
return {
|
|
42
|
-
id: nodeId,
|
|
43
|
-
states: {
|
|
44
|
-
nodeId,
|
|
45
|
-
level,
|
|
46
|
-
isLast,
|
|
47
|
-
},
|
|
48
|
-
methods: {},
|
|
49
|
-
};
|
|
50
|
-
}
|
|
@@ -1,75 +0,0 @@
|
|
|
1
|
-
"use client";
|
|
2
|
-
|
|
3
|
-
import React, { useState, createContext, useContext } from "react";
|
|
4
|
-
import { IReactChildren, IComponentAPI } from "../../../../../types";
|
|
5
|
-
|
|
6
|
-
// ─── Tree Context ─────────────────────────────────────────────────────────────
|
|
7
|
-
|
|
8
|
-
const defaultTreeAPI: IComponentAPI = {
|
|
9
|
-
id: "",
|
|
10
|
-
states: {},
|
|
11
|
-
methods: {},
|
|
12
|
-
};
|
|
13
|
-
|
|
14
|
-
const TreeContext = createContext<IComponentAPI>(defaultTreeAPI);
|
|
15
|
-
export const useTree = () => useContext(TreeContext);
|
|
16
|
-
|
|
17
|
-
export interface ITreeProviderProperties extends IReactChildren {
|
|
18
|
-
defaultExpandedIds?: string[];
|
|
19
|
-
onSelectionChange?: (ids: string[]) => void;
|
|
20
|
-
}
|
|
21
|
-
|
|
22
|
-
export const TreeProvider = ({
|
|
23
|
-
children,
|
|
24
|
-
defaultExpandedIds = [],
|
|
25
|
-
onSelectionChange,
|
|
26
|
-
}: ITreeProviderProperties): React.JSX.Element => {
|
|
27
|
-
const context = useTreeProviderContext({
|
|
28
|
-
defaultExpandedIds,
|
|
29
|
-
onSelectionChange,
|
|
30
|
-
});
|
|
31
|
-
|
|
32
|
-
return (
|
|
33
|
-
<TreeContext.Provider value={context}>{children}</TreeContext.Provider>
|
|
34
|
-
);
|
|
35
|
-
};
|
|
36
|
-
|
|
37
|
-
function useTreeProviderContext({
|
|
38
|
-
defaultExpandedIds,
|
|
39
|
-
onSelectionChange,
|
|
40
|
-
}: Omit<ITreeProviderProperties, "children">): IComponentAPI {
|
|
41
|
-
const treeId = React.useId();
|
|
42
|
-
const [expandedIds, setExpandedIds] = useState<Set<string>>(
|
|
43
|
-
() => new Set(defaultExpandedIds),
|
|
44
|
-
);
|
|
45
|
-
const [selectedIds, setSelectedIds] = useState<Set<string>>(() => new Set());
|
|
46
|
-
|
|
47
|
-
return {
|
|
48
|
-
id: treeId,
|
|
49
|
-
states: {
|
|
50
|
-
expandedIds,
|
|
51
|
-
selectedIds,
|
|
52
|
-
},
|
|
53
|
-
methods: {
|
|
54
|
-
isExpanded: (id: string): boolean => expandedIds.has(id),
|
|
55
|
-
isSelected: (id: string): boolean => selectedIds.has(id),
|
|
56
|
-
toggleExpanded: (id: string): void => {
|
|
57
|
-
setExpandedIds((prev) => {
|
|
58
|
-
const next = new Set(prev);
|
|
59
|
-
next.has(id) ? next.delete(id) : next.add(id);
|
|
60
|
-
return next;
|
|
61
|
-
});
|
|
62
|
-
},
|
|
63
|
-
toggleSelected: (id: string): void => {
|
|
64
|
-
setSelectedIds((prev) => {
|
|
65
|
-
const next = new Set(prev);
|
|
66
|
-
next.has(id) ? next.delete(id) : next.add(id);
|
|
67
|
-
onSelectionChange?.(Array.from(next));
|
|
68
|
-
return next;
|
|
69
|
-
});
|
|
70
|
-
},
|
|
71
|
-
getTreeId: ({ nodeId, type }: Record<string, string>): string =>
|
|
72
|
-
`${treeId}-${type}-${nodeId}`,
|
|
73
|
-
},
|
|
74
|
-
};
|
|
75
|
-
}
|
package/src/tree/index.tsx
DELETED
|
@@ -1,231 +0,0 @@
|
|
|
1
|
-
"use client";
|
|
2
|
-
|
|
3
|
-
import React from "react";
|
|
4
|
-
|
|
5
|
-
import { TreeProvider, useTree } from "./hooks/tree-provider";
|
|
6
|
-
import { TreeNodeProvider, useTreeNode } from "./hooks/tree-node-provider";
|
|
7
|
-
|
|
8
|
-
import { Button, IButtonProperties } from "../button";
|
|
9
|
-
import { TreeView, TreeItem, TreeNodeContent } from "./styles";
|
|
10
|
-
|
|
11
|
-
import {
|
|
12
|
-
IReactChildren,
|
|
13
|
-
IComponentSpacing,
|
|
14
|
-
ComponentVariantEnum,
|
|
15
|
-
} from "../../../../types";
|
|
16
|
-
|
|
17
|
-
export interface ITreeComposition {
|
|
18
|
-
Root: typeof TreeRoot;
|
|
19
|
-
Node: typeof TreeNode;
|
|
20
|
-
Trigger: typeof TreeTrigger;
|
|
21
|
-
Content: typeof TreeContent;
|
|
22
|
-
}
|
|
23
|
-
|
|
24
|
-
export interface ITreeProperties
|
|
25
|
-
extends IComponentSpacing, React.ComponentProps<"ul"> {}
|
|
26
|
-
|
|
27
|
-
export interface ITreeRootProperties extends IReactChildren {
|
|
28
|
-
defaultExpandedIds?: string[];
|
|
29
|
-
onSelectionChange?: (ids: string[]) => void;
|
|
30
|
-
}
|
|
31
|
-
|
|
32
|
-
export interface ITreeNodeProperties
|
|
33
|
-
extends IComponentSpacing, React.ComponentProps<"li"> {
|
|
34
|
-
nodeId: string;
|
|
35
|
-
level?: number;
|
|
36
|
-
isLast?: boolean;
|
|
37
|
-
}
|
|
38
|
-
|
|
39
|
-
export interface ITreeTriggerProperties extends Omit<
|
|
40
|
-
IButtonProperties,
|
|
41
|
-
"value"
|
|
42
|
-
> {
|
|
43
|
-
nodeId: string;
|
|
44
|
-
}
|
|
45
|
-
|
|
46
|
-
export interface ITreeContentProperties
|
|
47
|
-
extends IComponentSpacing, React.ComponentProps<"ul"> {
|
|
48
|
-
nodeId: string;
|
|
49
|
-
defaultOpen?: boolean;
|
|
50
|
-
}
|
|
51
|
-
|
|
52
|
-
/**
|
|
53
|
-
* Tree is used to display a hierarchical list of items.
|
|
54
|
-
*
|
|
55
|
-
* **Best practices:**
|
|
56
|
-
*
|
|
57
|
-
* - Use a clear and descriptive label for each tree node.
|
|
58
|
-
* - Ensure that the tree can be operated using only the keyboard.
|
|
59
|
-
* - Ensure that the focus is properly managed when nodes are expanded/collapsed.
|
|
60
|
-
*
|
|
61
|
-
* @param {ITreeProperties} props - The props for the Tree component.
|
|
62
|
-
* @param {ReactNode} props.children - The content to be rendered inside the tree.
|
|
63
|
-
* @returns {ReactElement} The Tree component.
|
|
64
|
-
*/
|
|
65
|
-
const Tree = (props: ITreeProperties) => {
|
|
66
|
-
const { children, ...restProps } = props;
|
|
67
|
-
const { id } = useTree();
|
|
68
|
-
|
|
69
|
-
return (
|
|
70
|
-
<TreeView id={id} role="tree" {...restProps}>
|
|
71
|
-
{children}
|
|
72
|
-
</TreeView>
|
|
73
|
-
);
|
|
74
|
-
};
|
|
75
|
-
Tree.displayName = "Tree";
|
|
76
|
-
|
|
77
|
-
const TreeRoot = ({
|
|
78
|
-
children,
|
|
79
|
-
defaultExpandedIds,
|
|
80
|
-
onSelectionChange,
|
|
81
|
-
}: ITreeRootProperties) => {
|
|
82
|
-
return (
|
|
83
|
-
<TreeProvider
|
|
84
|
-
defaultExpandedIds={defaultExpandedIds}
|
|
85
|
-
onSelectionChange={onSelectionChange}
|
|
86
|
-
>
|
|
87
|
-
{children}
|
|
88
|
-
</TreeProvider>
|
|
89
|
-
);
|
|
90
|
-
};
|
|
91
|
-
TreeRoot.displayName = "Tree.Root";
|
|
92
|
-
|
|
93
|
-
/**
|
|
94
|
-
* Tree.Node is used to wrap each node of the tree.
|
|
95
|
-
*
|
|
96
|
-
* **Best practices:**
|
|
97
|
-
*
|
|
98
|
-
* - Provide a unique nodeId for each node.
|
|
99
|
-
* - Use the level prop to indicate the depth of the node in the hierarchy.
|
|
100
|
-
*
|
|
101
|
-
* @param {ITreeNodeProperties} props - The props for the Tree.Node component.
|
|
102
|
-
* @param {string} props.nodeId - The unique identifier for the node.
|
|
103
|
-
* @param {number} props.level - The depth level of the node. Defaults to 0.
|
|
104
|
-
* @param {boolean} props.isLast - Whether the node is the last in its siblings. Defaults to false.
|
|
105
|
-
* @param {ReactNode} props.children - The content to be rendered inside the node.
|
|
106
|
-
* @returns {ReactElement} The Tree.Node component.
|
|
107
|
-
*/
|
|
108
|
-
const TreeNode = (props: ITreeNodeProperties) => {
|
|
109
|
-
const { nodeId, level = 0, isLast = false, children, ...restProps } = props;
|
|
110
|
-
|
|
111
|
-
return (
|
|
112
|
-
<TreeNodeProvider nodeId={nodeId} level={level} isLast={isLast}>
|
|
113
|
-
<TreeItem role="treeitem" aria-level={level + 1} {...restProps}>
|
|
114
|
-
{children}
|
|
115
|
-
</TreeItem>
|
|
116
|
-
</TreeNodeProvider>
|
|
117
|
-
);
|
|
118
|
-
};
|
|
119
|
-
TreeNode.displayName = "Tree.Node";
|
|
120
|
-
|
|
121
|
-
/**
|
|
122
|
-
* Tree.Trigger is used to trigger the expansion and collapse of the associated Tree.Content component.
|
|
123
|
-
*
|
|
124
|
-
* **Best practices:**
|
|
125
|
-
*
|
|
126
|
-
* - Use a clear and descriptive label for the trigger.
|
|
127
|
-
* - Ensure that the trigger can be operated using only the keyboard.
|
|
128
|
-
* - Ensure that the focus is properly managed when the trigger is activated.
|
|
129
|
-
*
|
|
130
|
-
* @param {ITreeTriggerProperties} props - The props for the Tree.Trigger component.
|
|
131
|
-
* @param {string} props.nodeId - The value used to bind the Tree.Trigger and Tree.Content components.
|
|
132
|
-
* @param {ReactNode} props.children - The content to be rendered inside the trigger.
|
|
133
|
-
* @returns {ReactElement} The Tree.Trigger component.
|
|
134
|
-
*/
|
|
135
|
-
const TreeTrigger = (props: ITreeTriggerProperties) => {
|
|
136
|
-
const { nodeId, disabled, onClick, children, ...restProps } = props;
|
|
137
|
-
|
|
138
|
-
const { methods } = useTree();
|
|
139
|
-
const { getTreeId, toggleExpanded, toggleSelected } = methods;
|
|
140
|
-
|
|
141
|
-
const isExpanded = methods.isExpanded && methods.isExpanded(nodeId);
|
|
142
|
-
const isSelected = methods.isSelected && methods.isSelected(nodeId);
|
|
143
|
-
|
|
144
|
-
const IdHandler = {
|
|
145
|
-
trigger: getTreeId && getTreeId({ nodeId, type: "trigger" }),
|
|
146
|
-
content: getTreeId && getTreeId({ nodeId, type: "content" }),
|
|
147
|
-
};
|
|
148
|
-
|
|
149
|
-
const { states: nodeStates } = useTreeNode();
|
|
150
|
-
const level = nodeStates.level ?? 0;
|
|
151
|
-
|
|
152
|
-
const handleClick = (event: React.MouseEvent<HTMLButtonElement>) => {
|
|
153
|
-
if (!disabled) {
|
|
154
|
-
onClick && onClick(event);
|
|
155
|
-
toggleExpanded && toggleExpanded(nodeId);
|
|
156
|
-
toggleSelected && toggleSelected(nodeId);
|
|
157
|
-
}
|
|
158
|
-
};
|
|
159
|
-
|
|
160
|
-
return (
|
|
161
|
-
<Button
|
|
162
|
-
id={String(IdHandler.trigger)}
|
|
163
|
-
disabled={disabled ?? false}
|
|
164
|
-
onClick={handleClick}
|
|
165
|
-
data-state={isExpanded ? "expanded" : "collapsed"}
|
|
166
|
-
data-selected={isSelected || undefined}
|
|
167
|
-
variant={props.variant ?? ComponentVariantEnum.Ghost}
|
|
168
|
-
style={{ paddingLeft: `calc(${level} * 1rem + 0.5rem)` }}
|
|
169
|
-
rawicon
|
|
170
|
-
{...restProps}
|
|
171
|
-
>
|
|
172
|
-
{children}
|
|
173
|
-
</Button>
|
|
174
|
-
);
|
|
175
|
-
};
|
|
176
|
-
TreeTrigger.displayName = "Tree.Trigger";
|
|
177
|
-
|
|
178
|
-
/**
|
|
179
|
-
* Tree.Content is used to contain the children of the associated Tree.Trigger component.
|
|
180
|
-
*
|
|
181
|
-
* **Best practices:**
|
|
182
|
-
*
|
|
183
|
-
* - Ensure that the content is hidden when the associated node is collapsed.
|
|
184
|
-
* - Ensure that the content is properly focused when the associated node is expanded.
|
|
185
|
-
*
|
|
186
|
-
* @param {ITreeContentProperties} props - The props for the Tree.Content component.
|
|
187
|
-
* @param {string} props.nodeId - The value used to bind the Tree.Content and Tree.Trigger components.
|
|
188
|
-
* @param {boolean} props.defaultOpen - The initial open state of the content. Defaults to false.
|
|
189
|
-
* @param {ReactNode} props.children - The content to be rendered inside the node content.
|
|
190
|
-
* @returns {ReactElement} The Tree.Content component.
|
|
191
|
-
*/
|
|
192
|
-
const TreeContent = (props: ITreeContentProperties) => {
|
|
193
|
-
const { nodeId, defaultOpen = false, children, ...restProps } = props;
|
|
194
|
-
|
|
195
|
-
const { methods } = useTree();
|
|
196
|
-
const { getTreeId, toggleExpanded } = methods;
|
|
197
|
-
|
|
198
|
-
const isExpanded = methods.isExpanded && methods.isExpanded(nodeId);
|
|
199
|
-
|
|
200
|
-
const IdHandler = {
|
|
201
|
-
trigger: getTreeId && getTreeId({ nodeId, type: "trigger" }),
|
|
202
|
-
content: getTreeId && getTreeId({ nodeId, type: "content" }),
|
|
203
|
-
};
|
|
204
|
-
|
|
205
|
-
React.useEffect(() => {
|
|
206
|
-
if (defaultOpen && !isExpanded && toggleExpanded) toggleExpanded(nodeId);
|
|
207
|
-
}, []);
|
|
208
|
-
|
|
209
|
-
if (isExpanded)
|
|
210
|
-
return (
|
|
211
|
-
<TreeNodeContent
|
|
212
|
-
role="group"
|
|
213
|
-
id={String(IdHandler.content)}
|
|
214
|
-
aria-labelledby={String(IdHandler.trigger)}
|
|
215
|
-
data-nodeId={nodeId}
|
|
216
|
-
{...restProps}
|
|
217
|
-
>
|
|
218
|
-
{children}
|
|
219
|
-
</TreeNodeContent>
|
|
220
|
-
);
|
|
221
|
-
|
|
222
|
-
return <React.Fragment />;
|
|
223
|
-
};
|
|
224
|
-
TreeContent.displayName = "Tree.Content";
|
|
225
|
-
|
|
226
|
-
Tree.Root = TreeRoot;
|
|
227
|
-
Tree.Node = TreeNode;
|
|
228
|
-
Tree.Trigger = TreeTrigger;
|
|
229
|
-
Tree.Content = TreeContent;
|
|
230
|
-
|
|
231
|
-
export { Tree, TreeRoot, TreeNode, TreeTrigger, TreeContent };
|
package/src/tree/styles/index.ts
DELETED
|
@@ -1,23 +0,0 @@
|
|
|
1
|
-
import styled from "styled-components";
|
|
2
|
-
|
|
3
|
-
export const TreeView = styled.ul<any>`
|
|
4
|
-
display: flex;
|
|
5
|
-
flex-direction: column;
|
|
6
|
-
list-style: none;
|
|
7
|
-
margin: 0;
|
|
8
|
-
padding: 0;
|
|
9
|
-
`;
|
|
10
|
-
|
|
11
|
-
export const TreeItem = styled.li<any>`
|
|
12
|
-
display: flex;
|
|
13
|
-
flex-direction: column;
|
|
14
|
-
list-style: none;
|
|
15
|
-
`;
|
|
16
|
-
|
|
17
|
-
export const TreeNodeContent = styled.ul<any>`
|
|
18
|
-
display: flex;
|
|
19
|
-
flex-direction: column;
|
|
20
|
-
list-style: none;
|
|
21
|
-
margin: 0;
|
|
22
|
-
padding: 0;
|
|
23
|
-
`;
|