Skip to content

Commit 8f606d7

Browse files
authored
feat(filterrules): support part disabled and part edit (#436)
* feat(filterrules): support part disabled and part edit * feat(filterrules): disabled line and RELATION when disabled one RELATION node
1 parent a7d3083 commit 8f606d7

File tree

6 files changed

+110
-26
lines changed

6 files changed

+110
-26
lines changed

src/filterRules/demos/constants.ts

+38
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,44 @@ export const INIT_DATA = {
1212
},
1313
};
1414

15+
export const INIT_CHECK_DATA = {
16+
key: shortid(),
17+
level: 0,
18+
type: 1,
19+
children: [
20+
{
21+
rowValues: {
22+
input: '',
23+
},
24+
disabled: true,
25+
key: shortid(),
26+
level: 1,
27+
},
28+
{
29+
key: shortid(),
30+
type: 1,
31+
level: 2,
32+
disabled: true,
33+
children: [
34+
{
35+
rowValues: {
36+
input: '',
37+
},
38+
key: shortid(),
39+
level: 2,
40+
},
41+
{
42+
key: shortid(),
43+
rowValues: {
44+
input: '',
45+
},
46+
level: 2,
47+
},
48+
],
49+
},
50+
],
51+
};
52+
1553
export const MORE_INIT_DATA = {
1654
key: shortid(),
1755
level: 1,

src/filterRules/demos/editCheck.tsx

+33
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,33 @@
1+
import React, { useState } from 'react';
2+
import { Alert, Input } from 'antd';
3+
import { FilterRules } from 'dt-react-component';
4+
import { IComponentProps } from 'dt-react-component/filterRules';
5+
6+
import { INIT_CHECK_DATA, INIT_ROW_VALUES, IRow } from './constants';
7+
8+
const MyInput = ({ rowValues: { input }, disabled, rowKey, onChange }: IComponentProps<IRow>) => (
9+
<Input
10+
value={input}
11+
disabled={disabled}
12+
onChange={(e) => onChange?.(rowKey, { input: e.target.value })}
13+
/>
14+
);
15+
16+
export default () => {
17+
const [data, setData] = useState(INIT_CHECK_DATA);
18+
19+
return (
20+
<>
21+
<Alert
22+
message="适用于部分数据禁用且可以编辑其他数据。常见业务情景:上一次保存的数据不可修改,但需要在当前基础上继续新增数据。"
23+
style={{ marginBottom: 16 }}
24+
/>
25+
<FilterRules<IRow>
26+
component={(props) => <MyInput {...props} />}
27+
value={data}
28+
onChange={(value: any) => setData(value)}
29+
initValues={INIT_ROW_VALUES}
30+
/>
31+
</>
32+
);
33+
};

src/filterRules/index.md

+9-7
Original file line numberDiff line numberDiff line change
@@ -21,6 +21,7 @@ demo:
2121
<code src="./demos/basicUnController.tsx" >非受控方式使用</code>
2222
<code src="./demos/basicCheck.tsx" >查看数据</code>
2323
<code src="./demos/basicMaxSize.tsx" >最大子节点示例</code>
24+
<code src="./demos/editCheck.tsx" >查看编辑示例</code>
2425

2526
## API
2627

@@ -39,13 +40,14 @@ demo:
3940

4041
### IFilterValue
4142

42-
| 参数 | 说明 | 类型 | 默认值 |
43-
| --------- | -------------------------- | ------------------- | ------ |
44-
| key | 唯一标识 | `string` | - |
45-
| level | 节点层级 | `boolean` | - |
46-
| type | 条件节点类型 | `1|2` | - |
47-
| rowValues | 节点数据 | `T` | - |
48-
| children | 子节点(存在条件节点时存在) | `IFilterValue<T>[]` | - |
43+
| 参数 | 说明 | 类型 | 默认值 |
44+
| --------- | -------------------------- | -------------------- | ------ |
45+
| key | 唯一标识 | `string` | - |
46+
| level | 节点层级 | `number` | - |
47+
| type | 条件节点类型 | `1|2(1: 且, 2: 或)` | |
48+
| disabled | 当前编辑/查看状态 | `boolean` | |
49+
| rowValues | 节点数据 | `T` | - |
50+
| children | 子节点(存在条件节点时存在) | `IFilterValue<T>[]` | - |
4951

5052
### IComponentProps
5153

src/filterRules/index.tsx

+7-6
Original file line numberDiff line numberDiff line change
@@ -27,6 +27,7 @@ export interface IFilterValue<T> {
2727
key: string;
2828
level?: number; // 当前节点的层级,用于判断一些按钮的展示
2929
type?: number; // 当前节点的条件关系,1 | 2
30+
disabled?: boolean; // 当前节点禁用
3031
rowValues?: T; // Form 节点的相关的信息(子节点无条件节点时才有)
3132
children?: IFilterValue<T>[]; // 子节点的信息(子节点存在条件节点时才有)
3233
}
@@ -65,7 +66,7 @@ const FilterRules = <T,>(props: IProps<T>) => {
6566
} = (!isDisabled(props) && props) as INormalProps<T>;
6667

6768
// 查找当前操作的节点
68-
const finRelationNode = (
69+
const findRelationNode = (
6970
parentData: IFilterValue<T>,
7071
targetKey: string,
7172
needCurrent?: boolean
@@ -76,7 +77,7 @@ const FilterRules = <T,>(props: IProps<T>) => {
7677
for (let i = 0; i < parentDataTemp.children.length; i++) {
7778
const current = parentDataTemp.children[i];
7879
if (current.key === targetKey) return needCurrent ? current : parentDataTemp;
79-
const node: IFilterValue<T> | null | undefined = finRelationNode(
80+
const node: IFilterValue<T> | null | undefined = findRelationNode(
8081
current,
8182
targetKey,
8283
needCurrent
@@ -87,7 +88,7 @@ const FilterRules = <T,>(props: IProps<T>) => {
8788

8889
const handleAddCondition = (keyObj: { key: string; isOut?: boolean }) => {
8990
const cloneData = clone(value);
90-
const appendNode = finRelationNode(cloneData as IFilterValue<T>, keyObj.key, keyObj.isOut);
91+
const appendNode = findRelationNode(cloneData as IFilterValue<T>, keyObj.key, keyObj.isOut);
9192
addCondition(appendNode, keyObj, initValues as T);
9293
onChange?.(cloneData);
9394
};
@@ -148,7 +149,7 @@ const FilterRules = <T,>(props: IProps<T>) => {
148149

149150
const handleDeleteCondition = (key: string) => {
150151
const cloneData = clone(value);
151-
const deleteNode = finRelationNode(cloneData as IFilterValue<T>, key, false);
152+
const deleteNode = findRelationNode(cloneData as IFilterValue<T>, key, false);
152153
if (notEmpty.data && !deleteNode?.children) return message.info(notEmpty.message);
153154
if (!notEmpty.data && !deleteNode?.children) {
154155
return onChange?.(undefined);
@@ -190,7 +191,7 @@ const FilterRules = <T,>(props: IProps<T>) => {
190191
// 更改条件节点的条件
191192
const handleChangeCondition = (key: string, type: ROW_PERMISSION_RELATION) => {
192193
const cloneData = clone(value);
193-
const changeNode = finRelationNode(
194+
const changeNode = findRelationNode(
194195
cloneData as IFilterValue<T>,
195196
key,
196197
true
@@ -205,7 +206,7 @@ const FilterRules = <T,>(props: IProps<T>) => {
205206
// 改变节点的的数据
206207
const handleChangeRowValues = (key: string, values: T) => {
207208
const cloneData = clone(value);
208-
const changeNode = finRelationNode(
209+
const changeNode = findRelationNode(
209210
cloneData as IFilterValue<T>,
210211
key,
211212
true

src/filterRules/ruleController/index.scss

+2-1
Original file line numberDiff line numberDiff line change
@@ -37,7 +37,7 @@
3737
color: #1D78FF;
3838
text-align: center;
3939
line-height: 26px;
40-
z-index: 10;
40+
z-index: 1;
4141
&.disabled {
4242
cursor: not-allowed;
4343
color: #3D446E;
@@ -90,6 +90,7 @@
9090
width: 10%;
9191
margin-left: 12px;
9292
margin-top: 7px;
93+
min-width: 55px;
9394
.icon {
9495
cursor: pointer;
9596
color: #1D78FF;

src/filterRules/ruleController/index.tsx

+21-12
Original file line numberDiff line numberDiff line change
@@ -48,13 +48,14 @@ export const RulesController = <T,>(props: IProps<T>) => {
4848

4949
// 计算每个节点的高度(height)/线条高度(lineHeight)/距离底部高度(bottom)
5050
const calculateTreeItemHeight = (item: IFilterValue<T>, disabled: boolean) => {
51+
const composeDisabled = disabled || !!item.disabled;
5152
if (!item?.children)
5253
return weakMap.set(item, { height: ITEM_HEIGHT + MARGIN, lineHeight: ITEM_HEIGHT });
53-
item.children.map((child) => calculateTreeItemHeight(child, disabled));
54+
item.children.map((child) => calculateTreeItemHeight(child, composeDisabled));
5455
const isLastCondition = !item.children.some(isCondition);
5556
const firstNodeIsCondition = isCondition(item.children[0]);
5657
// 编辑模式下计算
57-
if (!disabled) {
58+
if (!composeDisabled) {
5859
const height = item.children.reduce(
5960
(prev, curr) => prev + weakMap.get(curr).height,
6061
ITEM_HEIGHT
@@ -123,6 +124,8 @@ export const RulesController = <T,>(props: IProps<T>) => {
123124
namePath: InternalNamePath,
124125
disabled: boolean
125126
) => {
127+
const composeDisabled = disabled || !!item.disabled;
128+
126129
// 渲染条件节点和线条
127130
if (item?.children?.length) {
128131
const childrenPath = (index: number) => {
@@ -140,15 +143,16 @@ export const RulesController = <T,>(props: IProps<T>) => {
140143
>
141144
<div
142145
className={classnames('condition__box', {
143-
disabled,
146+
disabled: composeDisabled,
144147
})}
145148
style={{ height: lineHeight, bottom: bottom ?? MARGIN }}
146149
>
147150
<span
148151
className={classnames('condition__box--name', {
149-
disabled,
152+
disabled: composeDisabled,
150153
})}
151154
onClick={() =>
155+
!composeDisabled &&
152156
onChangeCondition(item.key, item?.type as ROW_PERMISSION_RELATION)
153157
}
154158
>
@@ -163,9 +167,9 @@ export const RulesController = <T,>(props: IProps<T>) => {
163167
)}
164168
</div>
165169
{item.children.map((d: IFilterValue<T>, index: number) =>
166-
renderCondition(d, childrenPath(index), disabled)
170+
renderCondition(d, childrenPath(index), composeDisabled)
167171
)}
168-
{!disabled && (
172+
{!composeDisabled && (
169173
<div className="condition__add">
170174
<span className="condition__add--line" />
171175
<PlusCircleOutlined
@@ -200,20 +204,18 @@ export const RulesController = <T,>(props: IProps<T>) => {
200204
<div className="ruleController__item--component">
201205
{component({
202206
rowKey: item.key,
203-
disabled,
207+
disabled: composeDisabled,
204208
name: [...namePath, 'rowValues'],
205209
rowValues: item.rowValues as T,
206210
onChange: onChangeRowValues,
207211
})}
208212
</div>
209-
{!disabled && (
213+
{!composeDisabled && (
210214
<div className="ruleController__item--operation">
211215
{item.level === maxLevel ? null : (
212216
<PlusCircleOutlined
213217
className="icon"
214-
onClick={() => {
215-
onAddCondition({ key: item.key });
216-
}}
218+
onClick={() => onAddCondition({ key: item.key })}
217219
/>
218220
)}
219221
<MinusCircleOutlined
@@ -225,7 +227,14 @@ export const RulesController = <T,>(props: IProps<T>) => {
225227
</div>
226228
);
227229
};
230+
228231
if (!value) return null;
232+
229233
calculateTreeItemHeight(value, !!disabled);
230-
return <div className="ruleController">{renderCondition(value, [], !!disabled)}</div>;
234+
235+
return (
236+
<div className="ruleController">
237+
{renderCondition(value, [], !!disabled || !!value.disabled)}
238+
</div>
239+
);
231240
};

0 commit comments

Comments
 (0)