From e457817c680bb31e7dcc34fea4e193f5d83111a6 Mon Sep 17 00:00:00 2001 From: Rylan Date: Sun, 21 Sep 2025 06:52:06 +0800 Subject: [PATCH 1/8] fix(Tree): update checked state logic to consider indeterminate nodes --- packages/components/tree/Tree.tsx | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/packages/components/tree/Tree.tsx b/packages/components/tree/Tree.tsx index 70a90b055c..e7aeb50d5f 100644 --- a/packages/components/tree/Tree.tsx +++ b/packages/components/tree/Tree.tsx @@ -182,7 +182,7 @@ const Tree = forwardRef, TreeProps>((origi if (!node || disabled || node.disabled) { return; } - setChecked(node, !node.isChecked(), { ...ctx, trigger: 'node-click' }); + setChecked(node, !node.isChecked() && !node.isIndeterminate(), { ...ctx, trigger: 'node-click' }); }; const handleScrollToElement = useCallback( (params: ComponentScrollToElementParams) => { From 4f039a0b5a500ad2f79e7115e3a6a744eba1857e Mon Sep 17 00:00:00 2001 From: Rylan Date: Wed, 24 Sep 2025 03:33:16 +0800 Subject: [PATCH 2/8] chore: update demo --- .../components/tree/_example/operations.tsx | 127 +++++++++--------- 1 file changed, 66 insertions(+), 61 deletions(-) diff --git a/packages/components/tree/_example/operations.tsx b/packages/components/tree/_example/operations.tsx index ff21525af4..83b997695a 100644 --- a/packages/components/tree/_example/operations.tsx +++ b/packages/components/tree/_example/operations.tsx @@ -1,17 +1,7 @@ import React, { useRef, useState } from 'react'; -import { - InputAdornment, - Button, - Input, - Tree, - Form, - Switch, - Space, - TreeNodeModel, - TreeInstanceFunctions, -} from 'tdesign-react'; - -import type { TreeProps, TreeNodeValue } from 'tdesign-react'; + +import type { TreeInstanceFunctions, TreeNodeModel } from 'tdesign-react'; +import { Button, Input, InputAdornment, Space, Switch, Tree, TreeNodeValue, TreeProps } from 'tdesign-react'; const items = [ { @@ -19,14 +9,17 @@ const items = [ }, { value: 'node2', + disabled: true, }, ]; let index = 2; export default () => { + const treeRef = useRef>(null); + const [useActived, setUseActived] = useState(false); - const [expandParent, setExpandParent] = useState(false); + const [expandParent, setExpandParent] = useState(true); const [filterText, setFilterText] = useState(''); const [activeId, setActiveId] = useState(''); const [activeIds, setActiveIds] = useState([]); @@ -45,8 +38,6 @@ export default () => { return label; }; - const renderOperations: TreeProps['operations'] = (node) => `value: ${node.value}`; - const handleInputChange = (value: string) => { setFilterText(value); console.info('on input:', value); @@ -72,9 +63,6 @@ export default () => { setActiveId(vals[0] || ''); }; - /* ======== 操作 api ======= */ - const treeRef = useRef>(null); - const setLabel = (value: string) => { const node = treeRef.current.getItem(value); const label = getLabelContent(node); @@ -96,6 +84,7 @@ export default () => { }; return item; }; + const append = (node?: TreeNodeModel) => { const item = getInsertItem(); if (item) { @@ -104,7 +93,6 @@ export default () => { } else { treeRef.current.appendTo(node.value, item); } - // setLabel(item.value); if (useActived) { setActiveIds((v) => [...v, item.value]); } @@ -127,28 +115,52 @@ export default () => { } }; + const canToggleDisable = (node: TreeNodeModel) => { + const parent = node.getParent?.(); + const isCheckStrictly = false; // 默认关闭 + if (!isCheckStrictly && parent?.disabled) { + return false; // 父节点被禁用时,子节点状态不支持手动改变 + } + return true; + }; + + const toggleDisable = (node: TreeNodeModel) => { + treeRef.current.setItem(node.value, { + disabled: !node.disabled, + }); + console.log(treeRef.current.getItems(node.value)); + }; + const remove = (node: TreeNodeModel) => { treeRef.current.remove(node.value); }; - const renderOperations2 = (node: TreeNodeModel) => ( - <> - - - - + - + ); - /* ======== API ======= */ const getItem = () => { const node = treeRef.current.getItem('node1'); console.info('getItem:', node.value); @@ -279,24 +291,17 @@ export default () => { return ( -

render:

- -

api:

-
-
- - onChange={setUseActived} /> - - - onChange={setExpandParent} /> - -
-
-
- - - -
+ + 插入节点使用高亮节点 + onChange={setUseActived} /> + + + 子节点展开触发父节点展开 + onChange={setExpandParent} /> + + + + { label={getLabel} expandParent={expandParent} filter={filterByText} - operations={renderOperations2} + operations={renderOperations} onExpand={handleExpand} onChange={handleChange} onActive={handleActive} /> -

api:

- - - - - - - - - - - - + * 相关信息通过控制台输出
); }; From 432dfeb2dabc076428a226816503036f1df3ebb7 Mon Sep 17 00:00:00 2001 From: Rylan Date: Wed, 24 Sep 2025 03:34:42 +0800 Subject: [PATCH 3/8] fix(Tree): update disableCheck logic --- packages/components/tree/TreeItem.tsx | 17 ++--------------- packages/components/tree/hooks/useStore.ts | 4 ++++ 2 files changed, 6 insertions(+), 15 deletions(-) diff --git a/packages/components/tree/TreeItem.tsx b/packages/components/tree/TreeItem.tsx index fed4f0d1b3..72e91d5227 100644 --- a/packages/components/tree/TreeItem.tsx +++ b/packages/components/tree/TreeItem.tsx @@ -50,7 +50,6 @@ const TreeItem = forwardRef( expandOnClickNode, activable, checkProps, - disableCheck, operations, onClick, onChange, @@ -242,32 +241,20 @@ const TreeItem = forwardRef( }); if (node.isCheckable()) { - let checkboxDisabled: boolean; - if (typeof disableCheck === 'function') { - checkboxDisabled = disableCheck(node.getModel()); - } else { - checkboxDisabled = !!disableCheck; - } - - if (node.isDisabled()) { - checkboxDisabled = true; - } - let checkboxProps: CheckboxProps; if (typeof checkProps === 'function') { checkboxProps = checkProps(node.getModel()); } else { checkboxProps = checkProps; } - return ( onChange(node, ctx)} + onChange={(_, ctx) => onChange(node, ctx)} className={labelClasses} stopLabelTrigger={expandOnClickNode && !!node.children} {...checkboxProps} diff --git a/packages/components/tree/hooks/useStore.ts b/packages/components/tree/hooks/useStore.ts index ec93d224b4..79128f66cd 100644 --- a/packages/components/tree/hooks/useStore.ts +++ b/packages/components/tree/hooks/useStore.ts @@ -29,6 +29,7 @@ export function useStore( activeMultiple, actived, disabled, + disableCheck, draggable, checkable, value, @@ -109,6 +110,7 @@ export function useStore( expandMutex, expandParent, disabled, + disableCheck, draggable, load, lazy, @@ -185,6 +187,7 @@ export function useStore( activable, activeMultiple, disabled, + disableCheck, checkable, draggable, checkStrictly, @@ -201,6 +204,7 @@ export function useStore( draggable, checkable, disabled, + disableCheck, expandAll, expandLevel, expandMutex, From 72a399cd4da770cdbc44431b2596133c7964c4d1 Mon Sep 17 00:00:00 2001 From: Rylan Date: Wed, 24 Sep 2025 03:37:40 +0800 Subject: [PATCH 4/8] chore: update snapshots --- .../components/tree/_example/operations.tsx | 2 +- test/snap/__snapshots__/csr.test.jsx.snap | 222 +++++++----------- test/snap/__snapshots__/ssr.test.jsx.snap | 2 +- 3 files changed, 91 insertions(+), 135 deletions(-) diff --git a/packages/components/tree/_example/operations.tsx b/packages/components/tree/_example/operations.tsx index 83b997695a..5e5f78b7e5 100644 --- a/packages/components/tree/_example/operations.tsx +++ b/packages/components/tree/_example/operations.tsx @@ -19,7 +19,7 @@ export default () => { const treeRef = useRef>(null); const [useActived, setUseActived] = useState(false); - const [expandParent, setExpandParent] = useState(true); + const [expandParent, setExpandParent] = useState(false); const [filterText, setFilterText] = useState(''); const [activeId, setActiveId] = useState(''); const [activeIds, setActiveIds] = useState([]); diff --git a/test/snap/__snapshots__/csr.test.jsx.snap b/test/snap/__snapshots__/csr.test.jsx.snap index c2cf0ddd76..ad78afbf3f 100644 --- a/test/snap/__snapshots__/csr.test.jsx.snap +++ b/test/snap/__snapshots__/csr.test.jsx.snap @@ -144387,144 +144387,95 @@ exports[`csr snapshot test > csr test packages/components/tree/_example/operatio class="t-space t-space-vertical" style="gap: 16px;" > -
-

- render: -

-
- 暂无数据 +
+ 插入节点使用高亮节点 +
+
+ +
-
-

- api: -

-
-
-
-
- -
-
-
- -
-
-
-
+
+ -
-
-
- + class="t-switch__content" + /> + +
-
- - filter: - + filter: + +
-
- -
+
@@ -144538,15 +144489,6 @@ exports[`csr snapshot test > csr test packages/components/tree/_example/operatio 暂无数据
-
-

- api: -

-
@@ -144558,13 +144500,13 @@ exports[`csr snapshot test > csr test packages/components/tree/_example/operatio class="t-space-item" >
@@ -144572,7 +144514,7 @@ exports[`csr snapshot test > csr test packages/components/tree/_example/operatio class="t-space-item" >
filter:
暂无数据

api:

"`; +exports[`ssr snapshot test > ssr test packages/components/tree/_example/operations.tsx 1`] = `"
插入节点使用高亮节点
子节点展开触发父节点展开
filter:
暂无数据
* 相关信息通过控制台输出
"`; exports[`ssr snapshot test > ssr test packages/components/tree/_example/state.tsx 1`] = `"

state:

暂无数据

api:

"`; diff --git a/test/snap/__snapshots__/ssr.test.jsx.snap b/test/snap/__snapshots__/ssr.test.jsx.snap index 0543b94473..a607a5d7cf 100644 --- a/test/snap/__snapshots__/ssr.test.jsx.snap +++ b/test/snap/__snapshots__/ssr.test.jsx.snap @@ -1216,7 +1216,7 @@ exports[`ssr snapshot test > ssr test packages/components/tree/_example/line.tsx exports[`ssr snapshot test > ssr test packages/components/tree/_example/load.tsx 1`] = `"
暂无数据
"`; -exports[`ssr snapshot test > ssr test packages/components/tree/_example/operations.tsx 1`] = `"

render:

暂无数据

api:

filter:
暂无数据

api:

"`; +exports[`ssr snapshot test > ssr test packages/components/tree/_example/operations.tsx 1`] = `"
插入节点使用高亮节点
子节点展开触发父节点展开
filter:
暂无数据
* 相关信息通过控制台输出
"`; exports[`ssr snapshot test > ssr test packages/components/tree/_example/state.tsx 1`] = `"

state:

暂无数据

api:

"`; From d1dad767e93e8ecbfdf5d92cb5501c9f45310635 Mon Sep 17 00:00:00 2001 From: Rylan Date: Wed, 24 Sep 2025 05:10:38 +0800 Subject: [PATCH 5/8] chore: update CHANGELOG.md --- packages/tdesign-react/CHANGELOG.md | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/packages/tdesign-react/CHANGELOG.md b/packages/tdesign-react/CHANGELOG.md index ab9e6b1450..25e2cac85a 100644 --- a/packages/tdesign-react/CHANGELOG.md +++ b/packages/tdesign-react/CHANGELOG.md @@ -17,8 +17,9 @@ spline: explain - 按需加载方式使用的图标资源支持多色填充功能,通过 `strokeColor` 和 `fillColor` 属性进行配置 - `DatePicker`: 支持通过覆盖 `popupProps`,使点击 `preset` 时不关闭弹窗 @RylanBot ([#3798](https://github.com/Tencent/tdesign-react/pull/3798)) ### 🐞 Bug Fixes -- `Tree`: 修复拖拽后展开收起图标展示异常的问题 @RylanBot ([#3756](https://github.com/Tencent/tdesign-react/pull/3756)) -- `TreeItem`: 修正节点属性 `date-target` 单词拼写为 `data-target`,之前有使用该属性的业务请注意此变更 ⚠️ @RylanBot ([#3756](https://github.com/Tencent/tdesign-react/pull/3756)) +- `Tree`: @RylanBot ([#3756](https://github.com/Tencent/tdesign-react/pull/3756)) + - 修正节点属性 `date-target` 单词拼写为 `data-target`,之前有使用该属性的业务请注意此变更 ⚠️ + - 修复拖拽后展开收起图标展示异常的问题 - `MessagePlugin`: 修复 `content` 为 `''` / `undefined` / `null` 时产生的报错 @RylanBot ([#3778](https://github.com/Tencent/tdesign-react/pull/3778)) - `Table`: 修复未开启 `` 时,`Loading` 挂载导致的页面闪烁问题 @RylanBot ([#3775](https://github.com/Tencent/tdesign-react/pull/3775)) - `Upload`: 修复拖拽模式下 `status` 更新错误 @RSS1102 ([#3801](https://github.com/Tencent/tdesign-react/pull/3801)) @@ -75,7 +76,6 @@ spline: explain - 修复 `draggable` 在 `disabled` 状态下依旧生效的异常,此前有依赖此错误的业务请注意此变动 ⚠️ ([#3740](https://github.com/Tencent/tdesign-react/pull/3740)) - 修复 `checkStrictly` 默认为 false 时,父子节点 `disabled` 状态没有关联的问题 ([#3739](https://github.com/Tencent/tdesign-react/pull/3739)) - 修复 Drag 相关事件的回调中 `node` 为 null 的异常 ([#3728](https://github.com/Tencent/tdesign-react/pull/3728)) - - 修复 `size='small'` 的 `firstFullRow` 尺寸比 `size='medium'` 大的异常 ([#common2253](https://github.com/Tencent/tdesign-common/pull/2253)) - `Form`: @uyarn - 修复嵌套表单受外层 `FormList` 影响数据构造的问题 ([#3715](https://github.com/Tencent/tdesign-react/pull/3715)) - 修复嵌套表单中内层表单受外层表单影响校验结果字段的问题 ([#3738](https://github.com/Tencent/tdesign-react/pull/3738)) From 2da4be3b6f5c89a7f5703b90fabd10ef17083bd2 Mon Sep 17 00:00:00 2001 From: Rylan Date: Wed, 24 Sep 2025 20:09:25 +0800 Subject: [PATCH 6/8] docs: add checkable and strictly mode switches to lazy example --- packages/components/tree/_example/lazy.tsx | 27 +++++++- test/snap/__snapshots__/csr.test.jsx.snap | 75 +++++++++++++++++++++- test/snap/__snapshots__/ssr.test.jsx.snap | 2 +- 3 files changed, 97 insertions(+), 7 deletions(-) diff --git a/packages/components/tree/_example/lazy.tsx b/packages/components/tree/_example/lazy.tsx index f45bfea118..66d5ce8997 100644 --- a/packages/components/tree/_example/lazy.tsx +++ b/packages/components/tree/_example/lazy.tsx @@ -1,5 +1,5 @@ -import React from 'react'; -import { Tree } from 'tdesign-react'; +import React, { useState } from 'react'; +import { Space, Switch, Tree } from 'tdesign-react'; import type { TreeProps } from 'tdesign-react'; const items = [ @@ -14,6 +14,9 @@ const items = [ ]; export default () => { + const [checkable, setCheckable] = useState(true); + const [strictly, setStrictly] = useState(false); + const load: TreeProps['load'] = (node) => new Promise((resolve) => { setTimeout(() => { @@ -38,5 +41,23 @@ export default () => { console.log('on load:', state); }; - return ; + return ( + + + 可选: setCheckable(value)} /> + + + 严格模式: setStrictly(value)} /> + + + + ); }; diff --git a/test/snap/__snapshots__/csr.test.jsx.snap b/test/snap/__snapshots__/csr.test.jsx.snap index ad78afbf3f..cb1d2f236e 100644 --- a/test/snap/__snapshots__/csr.test.jsx.snap +++ b/test/snap/__snapshots__/csr.test.jsx.snap @@ -144255,9 +144255,78 @@ exports[`csr snapshot test > csr test packages/components/tree/_example/label.ts exports[`csr snapshot test > csr test packages/components/tree/_example/lazy.tsx 1`] = `
- 暂无数据 +
+
+
+ 可选: +
+
+ +
+
+
+
+
+
+ 严格模式: +
+
+ +
+
+
+
+
+ 暂无数据 +
+
`; @@ -150734,7 +150803,7 @@ exports[`ssr snapshot test > ssr test packages/components/tree/_example/icon.tsx exports[`ssr snapshot test > ssr test packages/components/tree/_example/label.tsx 1`] = `"
暂无数据
"`; -exports[`ssr snapshot test > ssr test packages/components/tree/_example/lazy.tsx 1`] = `"
暂无数据
"`; +exports[`ssr snapshot test > ssr test packages/components/tree/_example/lazy.tsx 1`] = `"
可选:
严格模式:
暂无数据
"`; exports[`ssr snapshot test > ssr test packages/components/tree/_example/line.tsx 1`] = `"
暂无数据

render

暂无数据
"`; diff --git a/test/snap/__snapshots__/ssr.test.jsx.snap b/test/snap/__snapshots__/ssr.test.jsx.snap index a607a5d7cf..f37a4435d3 100644 --- a/test/snap/__snapshots__/ssr.test.jsx.snap +++ b/test/snap/__snapshots__/ssr.test.jsx.snap @@ -1210,7 +1210,7 @@ exports[`ssr snapshot test > ssr test packages/components/tree/_example/icon.tsx exports[`ssr snapshot test > ssr test packages/components/tree/_example/label.tsx 1`] = `"
暂无数据
"`; -exports[`ssr snapshot test > ssr test packages/components/tree/_example/lazy.tsx 1`] = `"
暂无数据
"`; +exports[`ssr snapshot test > ssr test packages/components/tree/_example/lazy.tsx 1`] = `"
可选:
严格模式:
暂无数据
"`; exports[`ssr snapshot test > ssr test packages/components/tree/_example/line.tsx 1`] = `"
暂无数据

render

暂无数据
"`; From a6bc0a4661b68c04b3f8e34226e69e984ac3abbb Mon Sep 17 00:00:00 2001 From: Rylan Date: Thu, 25 Sep 2025 20:32:29 +0800 Subject: [PATCH 7/8] chore: update CHANGELOG.md --- packages/tdesign-react/CHANGELOG.md | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/packages/tdesign-react/CHANGELOG.md b/packages/tdesign-react/CHANGELOG.md index 25e2cac85a..d5d7d0a99e 100644 --- a/packages/tdesign-react/CHANGELOG.md +++ b/packages/tdesign-react/CHANGELOG.md @@ -21,7 +21,9 @@ spline: explain - 修正节点属性 `date-target` 单词拼写为 `data-target`,之前有使用该属性的业务请注意此变更 ⚠️ - 修复拖拽后展开收起图标展示异常的问题 - `MessagePlugin`: 修复 `content` 为 `''` / `undefined` / `null` 时产生的报错 @RylanBot ([#3778](https://github.com/Tencent/tdesign-react/pull/3778)) -- `Table`: 修复未开启 `` 时,`Loading` 挂载导致的页面闪烁问题 @RylanBot ([#3775](https://github.com/Tencent/tdesign-react/pull/3775)) +- `Table`: + - 修复未开启 `` 时,`Loading` 挂载导致的页面闪烁问题 @RylanBot ([#3775](https://github.com/Tencent/tdesign-react/pull/3775)) + - 修复 `size='small'` 的 `firstFullRow` 尺寸比 `size='medium'` 大的异常 ([#common2253](https://github.com/Tencent/tdesign-common/pull/2253)) - `Upload`: 修复拖拽模式下 `status` 更新错误 @RSS1102 ([#3801](https://github.com/Tencent/tdesign-react/pull/3801)) - `Input`: 修复在开启 `readonly` 或者禁用 `allowInput` 情况下没有触发 `onFocus` 和 `onBlur` 的问题 @RylanBot ([#3800](https://github.com/Tencent/tdesign-react/pull/3800)) - `Cascader`: From a39a44f80923be8dccacb4fb86c5ad553cc572ce Mon Sep 17 00:00:00 2001 From: Rylan Date: Wed, 29 Oct 2025 16:07:22 +0800 Subject: [PATCH 8/8] chore: sync common --- packages/common | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/packages/common b/packages/common index 30800118e4..218c177de0 160000 --- a/packages/common +++ b/packages/common @@ -1 +1 @@ -Subproject commit 30800118e41c7e37fcb710febd3ff3ae58e06a1b +Subproject commit 218c177de0f6fd1d46671d3739cf2c531895e5a3