@hzab/list-render 1.10.21-alpha.4 → 1.10.21-alpha.6
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/package.json +2 -1
- package/src/DetailModal/index.jsx +120 -120
- package/src/FormModal/index.tsx +210 -210
- package/src/components/CellEditTable/Template/ExpandListTemplate/index.tsx +34 -57
- package/src/components/CellEditTable/Template/GetBaseTemplate.tsx +33 -0
- package/src/components/CellEditTable/Template/widthWrap.tsx +25 -11
- package/src/components/CellEditTable/common/WidthWrapHoc.tsx +215 -0
- package/src/components/CellEditTable/common/childAntdComponent.ts +14 -0
- package/src/components/CellEditTable/common/utils.ts +257 -0
- package/src/components/CellEditTable/index.less +18 -0
- package/src/components/CellEditTable/index.tsx +94 -122
- package/src/table-render/index.jsx +124 -119
- package/src/components/CellEditTable/Template/SelectCellTemplate.tsx +0 -202
|
@@ -0,0 +1,257 @@
|
|
|
1
|
+
export const getNavigatorLanguage = (): string => navigator.language || "en-US";
|
|
2
|
+
|
|
3
|
+
function getLocaleSeparators(locale: string) {
|
|
4
|
+
const testNumber = 123456.789;
|
|
5
|
+
const localeFormattedNumber = Intl.NumberFormat(locale).format(testNumber);
|
|
6
|
+
|
|
7
|
+
// Get the thousands separator of the locale
|
|
8
|
+
const thousandsSeparator = localeFormattedNumber.split("123")[1][0];
|
|
9
|
+
|
|
10
|
+
// Get the decimal separator of the locale
|
|
11
|
+
const decimalSeparator = localeFormattedNumber.split("123")[1][4];
|
|
12
|
+
return { thousandsSeparator, decimalSeparator };
|
|
13
|
+
}
|
|
14
|
+
export function parseLocaleNumber(stringNumber: string, locale = getNavigatorLanguage()): number {
|
|
15
|
+
if (!stringNumber.trim()) return NaN;
|
|
16
|
+
const { thousandsSeparator, decimalSeparator } = getLocaleSeparators(locale);
|
|
17
|
+
const normalizedStringNumber = stringNumber.replace(/\u00A0/g, " "); // Replace non-breaking space with normal space
|
|
18
|
+
const numberString = normalizedStringNumber
|
|
19
|
+
.replace(new RegExp(`[${thousandsSeparator}\\s]`, "g"), "") // Replace thousands separator and white-space
|
|
20
|
+
.replace(new RegExp(`\\${decimalSeparator}`, "g"), "."); // Replace decimal separator
|
|
21
|
+
|
|
22
|
+
const trimmedNumberString = numberString.replace(/^(?!-)\D+|\D+$/g, ""); // Remove characters before first and after last number, but keep negative sign
|
|
23
|
+
if (trimmedNumberString === null || trimmedNumberString.trim().length === 0) {
|
|
24
|
+
return NaN;
|
|
25
|
+
}
|
|
26
|
+
return Number(trimmedNumberString);
|
|
27
|
+
}
|
|
28
|
+
|
|
29
|
+
|
|
30
|
+
function isReactElement(value) {
|
|
31
|
+
return value !== null && typeof value === "object";
|
|
32
|
+
}
|
|
33
|
+
const getTitle = (item) => {
|
|
34
|
+
return typeof item?.title == "function"
|
|
35
|
+
? isReactElement(item?.title())
|
|
36
|
+
? item?.title()?.props.children
|
|
37
|
+
: String(item?.title()) || ""
|
|
38
|
+
: String(item?.title) || ""
|
|
39
|
+
}
|
|
40
|
+
|
|
41
|
+
export function convertColumnsToRows(columns, headerRowHeight = 40) {
|
|
42
|
+
// 获取所有叶子节点
|
|
43
|
+
const getLeaves = (cols) => {
|
|
44
|
+
return cols.reduce((acc, col) => {
|
|
45
|
+
if (col.children?.length) {
|
|
46
|
+
return [...acc, ...getLeaves(col.children)];
|
|
47
|
+
}
|
|
48
|
+
return [...acc, col];
|
|
49
|
+
}, []);
|
|
50
|
+
};
|
|
51
|
+
|
|
52
|
+
// 计算最大深度
|
|
53
|
+
const getDepth = (cols, depth = 1) => {
|
|
54
|
+
return cols.reduce((max, col) => {
|
|
55
|
+
if (col.children?.length) {
|
|
56
|
+
return Math.max(max, getDepth(col.children, depth + 1));
|
|
57
|
+
}
|
|
58
|
+
return Math.max(max, depth);
|
|
59
|
+
}, depth);
|
|
60
|
+
};
|
|
61
|
+
|
|
62
|
+
const leafColumns = getLeaves(columns);
|
|
63
|
+
const totalDepth = getDepth(columns);
|
|
64
|
+
const totalCols = leafColumns.length;
|
|
65
|
+
|
|
66
|
+
// 构建表头树
|
|
67
|
+
const buildTree = (cols, depth = 0) => {
|
|
68
|
+
return cols.map((col) => {
|
|
69
|
+
const hasChildren = col.children?.length > 0;
|
|
70
|
+
if (!hasChildren) {
|
|
71
|
+
return {
|
|
72
|
+
...col,
|
|
73
|
+
rowspan: totalDepth - depth,
|
|
74
|
+
colspan: 1,
|
|
75
|
+
_depth: depth,
|
|
76
|
+
_isLeaf: true,
|
|
77
|
+
};
|
|
78
|
+
}
|
|
79
|
+
const leafCount = getLeaves(col.children).length;
|
|
80
|
+
return {
|
|
81
|
+
...col,
|
|
82
|
+
rowspan: 1,
|
|
83
|
+
colspan: leafCount,
|
|
84
|
+
_depth: depth,
|
|
85
|
+
_isLeaf: false,
|
|
86
|
+
children: buildTree(col.children, depth + 1),
|
|
87
|
+
};
|
|
88
|
+
});
|
|
89
|
+
};
|
|
90
|
+
|
|
91
|
+
const tree = buildTree(columns, 0);
|
|
92
|
+
|
|
93
|
+
// 初始化行
|
|
94
|
+
const rows: any = Array.from({ length: totalDepth }, (_, i) => ({
|
|
95
|
+
rowId: `header-${i}`,
|
|
96
|
+
height: headerRowHeight,
|
|
97
|
+
cells: [],
|
|
98
|
+
}));
|
|
99
|
+
|
|
100
|
+
|
|
101
|
+
// 递归填充行
|
|
102
|
+
const fillRow = (nodes, rowIndex = 0) => {
|
|
103
|
+
nodes.forEach((node) => {
|
|
104
|
+
if (node._isLeaf) {
|
|
105
|
+
const cell = {
|
|
106
|
+
...node,
|
|
107
|
+
type: node?.type == "rowSelection" ? "rowSelection" : "header",
|
|
108
|
+
text: getTitle(node),
|
|
109
|
+
dataIndex: node.dataIndex,
|
|
110
|
+
width: node.width,
|
|
111
|
+
rowspan: node.rowspan,
|
|
112
|
+
style: node?.type == "rowSelection" ? node?.style : {},
|
|
113
|
+
};
|
|
114
|
+
if (node.sorter) cell.sorter = node.sorter;
|
|
115
|
+
if (node.key) cell.key = node.key;
|
|
116
|
+
rows[rowIndex].cells.push(cell);
|
|
117
|
+
} else {
|
|
118
|
+
// 父节点:添加colspan
|
|
119
|
+
rows[rowIndex].cells.push({
|
|
120
|
+
...node,
|
|
121
|
+
type: node?.type == "rowSelection" ? "rowSelection" : "header",
|
|
122
|
+
text: getTitle(node),
|
|
123
|
+
colspan: node.colspan,
|
|
124
|
+
});
|
|
125
|
+
if (node.children) {
|
|
126
|
+
fillRow(node.children, rowIndex + 1);
|
|
127
|
+
}
|
|
128
|
+
}
|
|
129
|
+
});
|
|
130
|
+
};
|
|
131
|
+
|
|
132
|
+
fillRow(tree, 0);
|
|
133
|
+
|
|
134
|
+
// 补全每一行的cell,使长度一致
|
|
135
|
+
rows.forEach((row, rowIndex) => {
|
|
136
|
+
const newCells = [];
|
|
137
|
+
let colIndex = 0;
|
|
138
|
+
let cellIndex = 0;
|
|
139
|
+
|
|
140
|
+
while (colIndex < totalCols) {
|
|
141
|
+
const currentCell = row.cells[cellIndex];
|
|
142
|
+
|
|
143
|
+
if (!currentCell) {
|
|
144
|
+
// 如果当前行没有足够的cell,从叶子节点补充
|
|
145
|
+
const leaf = leafColumns[colIndex];
|
|
146
|
+
newCells.push({
|
|
147
|
+
...leaf,
|
|
148
|
+
type: leaf?.type == "rowSelection" ? "rowSelection" : "header",
|
|
149
|
+
text: getTitle(leaf),
|
|
150
|
+
dataIndex: leaf.dataIndex,
|
|
151
|
+
width: leaf.width,
|
|
152
|
+
rowspan: rowIndex === totalDepth - 1 ? 1 : undefined,
|
|
153
|
+
});
|
|
154
|
+
colIndex++;
|
|
155
|
+
cellIndex++;
|
|
156
|
+
continue;
|
|
157
|
+
}
|
|
158
|
+
|
|
159
|
+
const colspan = currentCell.colspan || 1;
|
|
160
|
+
const rowspan = currentCell.rowspan || 1;
|
|
161
|
+
|
|
162
|
+
// 检查当前cell是否应该出现在这一行
|
|
163
|
+
// 如果rowspan > 1,表示它跨多行,但只在第一行出现
|
|
164
|
+
if (rowspan > 1 && rowIndex > 0) {
|
|
165
|
+
// 这个cell不应该出现在当前行,跳过
|
|
166
|
+
colIndex += colspan;
|
|
167
|
+
cellIndex++;
|
|
168
|
+
continue;
|
|
169
|
+
}
|
|
170
|
+
|
|
171
|
+
// 如果当前cell有colspan,需要补全后面的空cell
|
|
172
|
+
newCells.push(currentCell);
|
|
173
|
+
colIndex += colspan;
|
|
174
|
+
cellIndex++;
|
|
175
|
+
|
|
176
|
+
// 如果colspan > 1,后面补充空cell
|
|
177
|
+
for (let i = 1; i < colspan; i++) {
|
|
178
|
+
newCells.push({
|
|
179
|
+
type: "header",
|
|
180
|
+
text: "",
|
|
181
|
+
});
|
|
182
|
+
}
|
|
183
|
+
}
|
|
184
|
+
|
|
185
|
+
row.cells = newCells;
|
|
186
|
+
});
|
|
187
|
+
|
|
188
|
+
// 最后一行的特殊处理:确保所有叶子节点都有对应的cell
|
|
189
|
+
const lastRow = rows[totalDepth - 1];
|
|
190
|
+
const lastRowCells = [];
|
|
191
|
+
let leafIndex = 0;
|
|
192
|
+
|
|
193
|
+
// 遍历所有叶子节点
|
|
194
|
+
leafColumns.forEach((leaf, index) => {
|
|
195
|
+
// 检查是否已经在lastRow中有对应的cell
|
|
196
|
+
const existingCell = lastRow.cells.find((cell) => cell.dataIndex === leaf.dataIndex && cell.text === leaf.title);
|
|
197
|
+
|
|
198
|
+
if (existingCell) {
|
|
199
|
+
lastRowCells.push(existingCell);
|
|
200
|
+
} else {
|
|
201
|
+
// 创建新的cell
|
|
202
|
+
lastRowCells.push({
|
|
203
|
+
...leaf,
|
|
204
|
+
type: leaf?.type == "rowSelection" ? "rowSelection" : "header",
|
|
205
|
+
text: getTitle(leaf),
|
|
206
|
+
dataIndex: leaf.dataIndex,
|
|
207
|
+
width: leaf.width,
|
|
208
|
+
rowspan: 1,
|
|
209
|
+
});
|
|
210
|
+
}
|
|
211
|
+
});
|
|
212
|
+
|
|
213
|
+
lastRow.cells = lastRowCells;
|
|
214
|
+
|
|
215
|
+
// 确保所有行的cell数量等于totalCols
|
|
216
|
+
rows.forEach((row) => {
|
|
217
|
+
// 如果cell数量少于totalCols,补充空cell
|
|
218
|
+
while (row.cells.length < totalCols) {
|
|
219
|
+
row.cells.push({
|
|
220
|
+
type: "header",
|
|
221
|
+
text: "",
|
|
222
|
+
});
|
|
223
|
+
}
|
|
224
|
+
});
|
|
225
|
+
|
|
226
|
+
return rows;
|
|
227
|
+
}
|
|
228
|
+
|
|
229
|
+
|
|
230
|
+
export function flattenColumns(columns: any[]) {
|
|
231
|
+
const result: any[] = [];
|
|
232
|
+
|
|
233
|
+
function traverse(cols) {
|
|
234
|
+
cols.forEach((col) => {
|
|
235
|
+
if (col.children && col.children.length > 0) {
|
|
236
|
+
traverse(col.children);
|
|
237
|
+
} else {
|
|
238
|
+
// 创建新对象,只保留需要的属性
|
|
239
|
+
const { title, dataIndex, key, width, sorter, k, ...rest } = col;
|
|
240
|
+
result.push({
|
|
241
|
+
type: "Input",
|
|
242
|
+
dataIndex,
|
|
243
|
+
title,
|
|
244
|
+
...(key && { key }),
|
|
245
|
+
...(width && { width }),
|
|
246
|
+
...(sorter && { sorter }),
|
|
247
|
+
...(k && { k }),
|
|
248
|
+
// 如果需要保留其他属性
|
|
249
|
+
...rest,
|
|
250
|
+
});
|
|
251
|
+
}
|
|
252
|
+
});
|
|
253
|
+
}
|
|
254
|
+
|
|
255
|
+
traverse(columns);
|
|
256
|
+
return result;
|
|
257
|
+
}
|
|
@@ -1,10 +1,28 @@
|
|
|
1
1
|
.grid-container {
|
|
2
2
|
overflow: auto;
|
|
3
3
|
position: relative;
|
|
4
|
+
max-height: 80vh;
|
|
4
5
|
|
|
5
6
|
|
|
6
7
|
|
|
7
8
|
.ant-select {
|
|
8
9
|
width: 100% !important;
|
|
9
10
|
}
|
|
11
|
+
|
|
12
|
+
|
|
13
|
+
.reactgrid-content .rg-pane .rg-cell {
|
|
14
|
+
padding: 0;
|
|
15
|
+
|
|
16
|
+
>div:nth-child(1) {
|
|
17
|
+
padding: 0 4px;
|
|
18
|
+
}
|
|
19
|
+
}
|
|
10
20
|
}
|
|
21
|
+
|
|
22
|
+
.base-hoc {
|
|
23
|
+
width: 100%;
|
|
24
|
+
height: 100%;
|
|
25
|
+
display: flex;
|
|
26
|
+
align-items: center;
|
|
27
|
+
justify-content: center;
|
|
28
|
+
}
|
|
@@ -1,15 +1,16 @@
|
|
|
1
|
-
import React, { useEffect, useMemo, useState } from "react";
|
|
1
|
+
import React, { memo, useEffect, useMemo, useRef, useState } from "react";
|
|
2
2
|
import { ReactGrid, Column, Row, CellChange, Cell, CellTemplate } from "@silevis/reactgrid";
|
|
3
3
|
import "@silevis/reactgrid/styles.css";
|
|
4
|
-
import _ from "lodash";
|
|
5
|
-
import "./index.less";
|
|
6
4
|
import { TextTemplate } from "./Template/TextCellTemplate";
|
|
7
5
|
import { antdComponents, customComponents } from "@hzab/form-render/src/index";
|
|
8
|
-
import {
|
|
6
|
+
import { WidthWrapHoc } from "./common/WidthWrapHoc";
|
|
9
7
|
import { NumberTemplate } from "./Template/NumberCellTemplate";
|
|
10
|
-
import { Checkbox } from "antd";
|
|
8
|
+
import { Checkbox, Spin } from "antd";
|
|
11
9
|
import { ExpandListTemplate } from "./Template/ExpandListTemplate";
|
|
12
|
-
import { convertColumnsToRows, flattenColumns } from "./
|
|
10
|
+
import { convertColumnsToRows, flattenColumns } from "./common/utils";
|
|
11
|
+
import { childAntdComponent } from "./common/childAntdComponent";
|
|
12
|
+
import { GetBaseTemplate } from "./Template/GetBaseTemplate";
|
|
13
|
+
import "./index.less";
|
|
13
14
|
|
|
14
15
|
export default function CellEditTable(props: any) {
|
|
15
16
|
const {
|
|
@@ -27,6 +28,7 @@ export default function CellEditTable(props: any) {
|
|
|
27
28
|
rowSelection,
|
|
28
29
|
rowKey,
|
|
29
30
|
query,
|
|
31
|
+
loading,
|
|
30
32
|
} = props;
|
|
31
33
|
|
|
32
34
|
const [headerList, setHeaderList] = useState<any>([]);
|
|
@@ -35,6 +37,7 @@ export default function CellEditTable(props: any) {
|
|
|
35
37
|
const [selectedRowKeys, setSelectedRowKeys] = useState<any>([]);
|
|
36
38
|
const [newDataSource, setNewDataSource] = useState<any>([]);
|
|
37
39
|
const [expandKeys, setExpandKeys] = useState<any>([]);
|
|
40
|
+
const gridRef = useRef<any>();
|
|
38
41
|
useEffect(() => {
|
|
39
42
|
setNewDataSource(dataSource);
|
|
40
43
|
}, [dataSource]);
|
|
@@ -71,19 +74,6 @@ export default function CellEditTable(props: any) {
|
|
|
71
74
|
},
|
|
72
75
|
});
|
|
73
76
|
}
|
|
74
|
-
// const cells = columns?.map((item, index) => {
|
|
75
|
-
// return {
|
|
76
|
-
// type: item?.type == "rowSelection" ? "rowSelection" : "header",
|
|
77
|
-
// text:
|
|
78
|
-
// typeof item?.title == "function"
|
|
79
|
-
// ? isReactElement(item?.title())
|
|
80
|
-
// ? item?.title()?.props.children
|
|
81
|
-
// : String(item?.title()) || ""
|
|
82
|
-
// : String(item?.title) || "",
|
|
83
|
-
// style: item?.type == "rowSelection" ? item?.style : {},
|
|
84
|
-
// onCell: item?.onCell,
|
|
85
|
-
// };
|
|
86
|
-
// });
|
|
87
77
|
setHeaderList(convertColumnsToRows(columns, headerRowHeight));
|
|
88
78
|
const newColumns = flattenColumns(columns);
|
|
89
79
|
setTableColumns(
|
|
@@ -107,13 +97,14 @@ export default function CellEditTable(props: any) {
|
|
|
107
97
|
const columnsItem = tableColumns[ind];
|
|
108
98
|
const cellItem = item[el];
|
|
109
99
|
let type: any = columnsItem?.type ?? "text";
|
|
100
|
+
/** 是否有复选框 */
|
|
110
101
|
if (!rowSelection && ind == 0) {
|
|
111
102
|
type = "ExpandListTemplate";
|
|
112
103
|
}
|
|
113
104
|
if (rowSelection && ind == 1) {
|
|
114
105
|
type = "ExpandListTemplate";
|
|
115
106
|
}
|
|
116
|
-
|
|
107
|
+
//设置单元格颜色及回显
|
|
117
108
|
if (formulaConfig) {
|
|
118
109
|
for (let key in formulaConfig) {
|
|
119
110
|
if (key == el) {
|
|
@@ -136,33 +127,37 @@ export default function CellEditTable(props: any) {
|
|
|
136
127
|
text: String(cellItem || ""),
|
|
137
128
|
value: cellItem,
|
|
138
129
|
selectedValue: cellItem || "",
|
|
139
|
-
// rowspan: item?.extendedConfig?.name == el ? item?.extendedConfig?.rowspan || 0 : 0,
|
|
140
|
-
// colspan: item?.extendedConfig?.name == el ? item?.extendedConfig?.colspan || 0 : 0,
|
|
141
130
|
style: columnsItem?.type == "rowSelection" ? { display: "flex", justifyContent: "center" } : {},
|
|
142
131
|
...((columnsItem?.onCell && columnsItem?.onCell(item, index, ind)) || {}),
|
|
143
132
|
...(columnsItem?.cellProps || {}),
|
|
144
133
|
setNewDataSource,
|
|
145
134
|
setExpandKeys,
|
|
135
|
+
rowKey,
|
|
146
136
|
expandKeys,
|
|
147
137
|
Slots,
|
|
148
138
|
...newCell,
|
|
149
|
-
|
|
150
|
-
// style:item?.extendedConfig?.name==el?item?.extendedConfig?.style||{}:{}
|
|
151
|
-
// ...handleType(item[el],tableColumns[ind]),
|
|
152
139
|
};
|
|
153
140
|
}),
|
|
154
141
|
};
|
|
155
142
|
});
|
|
156
|
-
setRows(
|
|
157
|
-
}, [newDataSource, tableColumns
|
|
143
|
+
setRows([...headerList, ...tempDataSource]);
|
|
144
|
+
}, [newDataSource, tableColumns]);
|
|
158
145
|
|
|
159
146
|
// 单元格编辑回调
|
|
160
147
|
const handleCellsChanged = (changes) => {
|
|
148
|
+
if (!Array.isArray(changes) || changes.length === 0) return;
|
|
149
|
+
/** 批量提交 */
|
|
150
|
+
let isBatchSubmit = false;
|
|
151
|
+
if (changes?.length > 1) {
|
|
152
|
+
isBatchSubmit = true;
|
|
153
|
+
}
|
|
161
154
|
setRows((prevRows) => {
|
|
162
155
|
changes.forEach((change) => {
|
|
156
|
+
const hasDiff = JSON.stringify((window as any).preCell?.text) != JSON.stringify(change.newCell?.text);
|
|
157
|
+
if (!hasDiff) return;
|
|
163
158
|
const changeRowIdx = prevRows.findIndex((el) => el.rowId == change.rowId);
|
|
164
159
|
const changeColumnIdx = tableColumns.findIndex((el) => el.columnId == change.columnId);
|
|
165
|
-
prevRows[changeRowIdx].cells[changeColumnIdx] = change.newCell;
|
|
160
|
+
prevRows[changeRowIdx].cells[changeColumnIdx] = { ...change.newCell };
|
|
166
161
|
if (formulaConfig) {
|
|
167
162
|
for (let key in formulaConfig) {
|
|
168
163
|
const item = formulaConfig[key];
|
|
@@ -176,39 +171,23 @@ export default function CellEditTable(props: any) {
|
|
|
176
171
|
prevRows[changeRowIdx].cells[resultColumnIdx] = newCell;
|
|
177
172
|
}
|
|
178
173
|
}
|
|
179
|
-
|
|
174
|
+
if (change?.newCell?.commit == "submit") {
|
|
175
|
+
onEditSubmit && onEditSubmit(handleArrayToObj(prevRows[changeRowIdx]));
|
|
176
|
+
}
|
|
180
177
|
onChange && onChange(prevRows[changeRowIdx]);
|
|
181
178
|
});
|
|
182
179
|
return [...prevRows];
|
|
183
180
|
});
|
|
184
181
|
};
|
|
185
|
-
|
|
186
|
-
/**提取组件内部子组件 */
|
|
187
|
-
function extractSubComponents(comp, compName): any {
|
|
188
|
-
if (!comp || typeof comp !== "object") return {};
|
|
189
|
-
|
|
190
|
-
return Object.entries(comp).reduce((result, [key, value]) => {
|
|
191
|
-
// 匹配 antd 规范子组件命名:XXPicker / XX / 驼峰组件名
|
|
192
|
-
// 排除普通函数、数字、布尔、内部私有属性(带下划线)、原型上的方法
|
|
193
|
-
const isNativeFunc = ["render", "defaultProps", "propTypes", "displayName", "Group", "$$typeof"].includes(key);
|
|
194
|
-
// 判定为子组件:值是函数(React组件本质是函数/类),且不是内部方法
|
|
195
|
-
const isSubComponent = typeof comp == "object" && !isNativeFunc;
|
|
196
|
-
|
|
197
|
-
if (isSubComponent) {
|
|
198
|
-
result[`${compName}.${key}`] = value;
|
|
199
|
-
}
|
|
200
|
-
return result;
|
|
201
|
-
}, {});
|
|
202
|
-
}
|
|
203
182
|
/** 自定义组件注册 */
|
|
204
183
|
const baseTemplate = useMemo(() => {
|
|
205
|
-
const mergeTemplate: any = { ...(antdComponents || {}), ...(customComponents || {}) };
|
|
184
|
+
const mergeTemplate: any = { ...(antdComponents || {}), ...(customComponents || {}), ...childAntdComponent };
|
|
206
185
|
const newMergeTemplate: any = {};
|
|
207
186
|
for (let key in mergeTemplate) {
|
|
208
|
-
|
|
209
|
-
|
|
210
|
-
}
|
|
211
|
-
newMergeTemplate[key] =
|
|
187
|
+
const NewCom = (props) => {
|
|
188
|
+
return <GetBaseTemplate {...props} Com={mergeTemplate[key]} />;
|
|
189
|
+
};
|
|
190
|
+
newMergeTemplate[key] = WidthWrapHoc(NewCom);
|
|
212
191
|
}
|
|
213
192
|
return newMergeTemplate;
|
|
214
193
|
}, [antdComponents, customComponents]);
|
|
@@ -216,42 +195,43 @@ export default function CellEditTable(props: any) {
|
|
|
216
195
|
const ActionDom = (props) => {
|
|
217
196
|
return (
|
|
218
197
|
<div onPointerDown={(e) => e.stopPropagation()}>
|
|
219
|
-
{Slots?.tableActionsSlot && <Slots.tableActionsSlot {...props} />}
|
|
220
|
-
{Slots?.actionPrefixSlot && <Slots.actionPrefixSlot {...props} />}
|
|
221
|
-
{Slots?.actionCenterSlot && <Slots.actionCenterSlot {...props} />}
|
|
222
|
-
{Slots?.actionSuffixSlot && <Slots.actionSuffixSlot {...props} />}
|
|
198
|
+
{Slots?.tableActionsSlot && <Slots.tableActionsSlot {...props?.cell} />}
|
|
199
|
+
{Slots?.actionPrefixSlot && <Slots.actionPrefixSlot {...props?.cell} />}
|
|
200
|
+
{Slots?.actionCenterSlot && <Slots.actionCenterSlot {...props?.cell} />}
|
|
201
|
+
{Slots?.actionSuffixSlot && <Slots.actionSuffixSlot {...props?.cell} />}
|
|
223
202
|
</div>
|
|
224
203
|
);
|
|
225
204
|
};
|
|
226
205
|
|
|
227
206
|
const CheckBoxDom = (props) => {
|
|
207
|
+
const { record, rowId } = props?.cell;
|
|
228
208
|
return (
|
|
229
209
|
<Checkbox
|
|
230
|
-
{...props}
|
|
210
|
+
{...props?.componentProps}
|
|
231
211
|
checked={
|
|
232
|
-
rowSelection?.selectedRowKeys?.includes((
|
|
233
|
-
rowSelection?.selectedRowKeys?.length == dataSource?.length
|
|
212
|
+
rowSelection?.selectedRowKeys?.includes((record && record[rowKey]) || "") ||
|
|
213
|
+
(rowSelection?.selectedRowKeys?.length == dataSource?.length && dataSource?.length > 0)
|
|
234
214
|
}
|
|
235
215
|
indeterminate={
|
|
236
|
-
!
|
|
216
|
+
!rowId &&
|
|
237
217
|
rowSelection?.selectedRowKeys?.length > 0 &&
|
|
238
218
|
rowSelection?.selectedRowKeys?.length < dataSource?.length
|
|
239
219
|
}
|
|
240
220
|
onChange={(e) => {
|
|
241
|
-
if (e.target.checked &&
|
|
242
|
-
const newSelectedRowKeys = [...rowSelection?.selectedRowKeys,
|
|
221
|
+
if (e.target.checked && rowId) {
|
|
222
|
+
const newSelectedRowKeys = [...rowSelection?.selectedRowKeys, record[rowKey]];
|
|
243
223
|
const rows = dataSource?.filter((el) => newSelectedRowKeys?.includes(el[rowKey]));
|
|
244
224
|
|
|
245
225
|
rowSelection?.onChange(newSelectedRowKeys, rows);
|
|
246
|
-
} else if (!e.target.checked &&
|
|
247
|
-
const newSelectedRowKeys = rowSelection?.selectedRowKeys?.filter((el) => el !=
|
|
226
|
+
} else if (!e.target.checked && rowId) {
|
|
227
|
+
const newSelectedRowKeys = rowSelection?.selectedRowKeys?.filter((el) => el != record[rowKey]);
|
|
248
228
|
const rows = dataSource?.filter((el) => newSelectedRowKeys?.includes(el[rowKey]));
|
|
249
229
|
|
|
250
230
|
rowSelection?.onChange(
|
|
251
|
-
rowSelection?.selectedRowKeys?.filter((el) => el !=
|
|
231
|
+
rowSelection?.selectedRowKeys?.filter((el) => el != record[rowKey]),
|
|
252
232
|
rows,
|
|
253
233
|
);
|
|
254
|
-
} else if (e.target.checked && !
|
|
234
|
+
} else if (e.target.checked && !rowId) {
|
|
255
235
|
const newSelectedRowKeys = dataSource?.map((el) => el[rowKey]);
|
|
256
236
|
const rows = dataSource?.filter((el) => newSelectedRowKeys?.includes(el[rowKey]));
|
|
257
237
|
|
|
@@ -259,7 +239,7 @@ export default function CellEditTable(props: any) {
|
|
|
259
239
|
dataSource?.map((el) => el[rowKey]),
|
|
260
240
|
rows,
|
|
261
241
|
);
|
|
262
|
-
} else if (!e.target.checked && !
|
|
242
|
+
} else if (!e.target.checked && !rowId) {
|
|
263
243
|
rowSelection?.onChange([], []);
|
|
264
244
|
}
|
|
265
245
|
}}
|
|
@@ -276,62 +256,54 @@ export default function CellEditTable(props: any) {
|
|
|
276
256
|
setSelectedRowKeys([]);
|
|
277
257
|
}, [query?.pageNum]);
|
|
278
258
|
|
|
279
|
-
|
|
280
|
-
|
|
281
|
-
|
|
282
|
-
|
|
283
|
-
|
|
284
|
-
|
|
285
|
-
|
|
286
|
-
|
|
287
|
-
horizontalStickyBreakpoint={120}
|
|
288
|
-
// stickyLeftColumns={1}
|
|
289
|
-
// onFocusLocationChanging={(location) => {
|
|
290
|
-
// return false;
|
|
291
|
-
// }}
|
|
292
|
-
{...reactGridProps}
|
|
293
|
-
onFocusLocationChanging={(cell: any) => {
|
|
294
|
-
const datatypeId = cell?.columnId + cell?.rowId;
|
|
295
|
-
window.gridEditId = datatypeId;
|
|
296
|
-
|
|
297
|
-
if (["_$actions", "rowSelection"]?.includes(cell?.columnId)) {
|
|
298
|
-
return false;
|
|
299
|
-
}
|
|
259
|
+
const customCellTemplates = useMemo(() => {
|
|
260
|
+
const templatesObj: any = {};
|
|
261
|
+
for (let key in reactGridProps?.customCellTemplates) {
|
|
262
|
+
const item = reactGridProps?.customCellTemplates[key];
|
|
263
|
+
templatesObj[key] = WidthWrapHoc(item);
|
|
264
|
+
}
|
|
265
|
+
return templatesObj;
|
|
266
|
+
}, [reactGridProps?.customCellTemplates]);
|
|
300
267
|
|
|
301
|
-
|
|
302
|
-
|
|
303
|
-
|
|
304
|
-
|
|
305
|
-
|
|
306
|
-
|
|
307
|
-
|
|
308
|
-
|
|
309
|
-
|
|
310
|
-
|
|
311
|
-
|
|
312
|
-
|
|
313
|
-
|
|
314
|
-
|
|
315
|
-
|
|
316
|
-
{
|
|
317
|
-
|
|
318
|
-
}
|
|
319
|
-
|
|
320
|
-
|
|
321
|
-
|
|
322
|
-
|
|
323
|
-
|
|
324
|
-
|
|
325
|
-
|
|
326
|
-
|
|
327
|
-
|
|
328
|
-
|
|
329
|
-
|
|
268
|
+
return (
|
|
269
|
+
<Spin spinning={loading}>
|
|
270
|
+
<div className={`grid-container ${className}`} style={reactGridStyle}>
|
|
271
|
+
<ReactGrid
|
|
272
|
+
ref={gridRef}
|
|
273
|
+
rows={rows}
|
|
274
|
+
columns={tableColumns}
|
|
275
|
+
onCellsChanged={handleCellsChanged}
|
|
276
|
+
enableFillHandle={true}
|
|
277
|
+
enableRangeSelection={true}
|
|
278
|
+
horizontalStickyBreakpoint={120}
|
|
279
|
+
{...reactGridProps}
|
|
280
|
+
onFocusLocationChanging={(cell: any) => {
|
|
281
|
+
const datatypeId = cell?.columnId + cell?.rowId;
|
|
282
|
+
(window as any).gridEditId = datatypeId;
|
|
283
|
+
if (["_$actions", "rowSelection"]?.includes(cell?.columnId)) {
|
|
284
|
+
return false;
|
|
285
|
+
}
|
|
286
|
+
if (reactGridProps?.onFocusLocationChanging) {
|
|
287
|
+
return reactGridProps?.onFocusLocationChanging(cell, rows);
|
|
288
|
+
}
|
|
289
|
+
return cell;
|
|
290
|
+
}}
|
|
291
|
+
customCellTemplates={{
|
|
292
|
+
ExpandListTemplate: WidthWrapHoc(ExpandListTemplate),
|
|
293
|
+
...baseTemplate,
|
|
294
|
+
...customCellTemplates,
|
|
295
|
+
_$actions: WidthWrapHoc(ActionDom),
|
|
296
|
+
rowSelection: WidthWrapHoc(CheckBoxDom),
|
|
297
|
+
Input: TextTemplate,
|
|
298
|
+
Number: NumberTemplate,
|
|
299
|
+
// ExpandListTemplate: WidthWrap({ WrapComponent: ExpandListTemplate }, true),
|
|
300
|
+
}}
|
|
330
301
|
|
|
331
|
-
|
|
332
|
-
|
|
333
|
-
|
|
334
|
-
|
|
335
|
-
|
|
302
|
+
// onSelectionChanged={(newSelection) => {
|
|
303
|
+
// console.log("选区发生变化", newSelection[0]);
|
|
304
|
+
// }}
|
|
305
|
+
/>
|
|
306
|
+
</div>
|
|
307
|
+
</Spin>
|
|
336
308
|
);
|
|
337
309
|
}
|