@creekjs/web-components 1.0.4 → 1.0.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/.turbo/turbo-father$colon$build.log +33 -17
- package/README.md +97 -18
- package/dist/creek-config-provider/CreekConfigContext.d.ts +4 -0
- package/dist/creek-config-provider/CreekConfigContext.d.ts.map +1 -0
- package/dist/creek-config-provider/CreekConfigContext.js.map +2 -2
- package/dist/creek-config-provider/CreekI18nProvider.d.ts +22 -0
- package/dist/creek-config-provider/CreekI18nProvider.d.ts.map +1 -0
- package/dist/creek-config-provider/CreekI18nProvider.js +92 -0
- package/dist/creek-config-provider/CreekI18nProvider.js.map +7 -0
- package/dist/creek-config-provider/index.d.ts +5 -3
- package/dist/creek-config-provider/index.d.ts.map +1 -0
- package/dist/creek-config-provider/index.js +47 -4
- package/dist/creek-config-provider/index.js.map +3 -3
- package/dist/creek-hooks/index.d.ts.map +1 -0
- package/dist/creek-hooks/useApp/DrawerHelper.d.ts.map +1 -0
- package/dist/creek-hooks/useApp/ModalHelper.d.ts.map +1 -0
- package/dist/creek-hooks/useApp/index.d.ts +3 -3
- package/dist/creek-hooks/useApp/index.d.ts.map +1 -0
- package/dist/creek-hooks/useApp/types.d.ts.map +1 -0
- package/dist/creek-hooks/useViewportHeight.d.ts.map +1 -0
- package/dist/creek-icon/index.d.ts.map +1 -0
- package/dist/creek-keep-alive/index.d.ts +24 -1
- package/dist/creek-keep-alive/index.d.ts.map +1 -0
- package/dist/creek-keep-alive/index.js +141 -4
- package/dist/creek-keep-alive/index.js.map +2 -2
- package/dist/creek-layout/ActionRender/FullScreen.d.ts.map +1 -0
- package/dist/creek-layout/{HeaderContent → ActionRender}/FullScreen.js +4 -2
- package/dist/creek-layout/ActionRender/FullScreen.js.map +7 -0
- package/dist/creek-layout/ActionRender/LayoutSettings.d.ts +5 -0
- package/dist/creek-layout/ActionRender/LayoutSettings.d.ts.map +1 -0
- package/dist/creek-layout/ActionRender/LayoutSettings.js +73 -0
- package/dist/creek-layout/ActionRender/LayoutSettings.js.map +7 -0
- package/dist/creek-layout/ActionRender/UserInfo.d.ts +8 -0
- package/dist/creek-layout/ActionRender/UserInfo.d.ts.map +1 -0
- package/dist/creek-layout/{HeaderContent → ActionRender}/UserInfo.js +7 -29
- package/dist/creek-layout/ActionRender/UserInfo.js.map +7 -0
- package/dist/creek-layout/ActionRender/index.d.ts +3 -0
- package/dist/creek-layout/ActionRender/index.d.ts.map +1 -0
- package/dist/creek-layout/ActionRender/index.js +36 -0
- package/dist/creek-layout/ActionRender/index.js.map +7 -0
- package/dist/creek-layout/CollapseButton.d.ts.map +1 -0
- package/dist/creek-layout/Exception/NotFound.d.ts.map +1 -0
- package/dist/creek-layout/Exception/NotFoundPage.d.ts.map +1 -0
- package/dist/creek-layout/Exception/index.d.ts.map +1 -0
- package/dist/creek-layout/index.d.ts +9 -2
- package/dist/creek-layout/index.d.ts.map +1 -0
- package/dist/creek-layout/index.js +96 -39
- package/dist/creek-layout/index.js.map +3 -3
- package/dist/creek-layout/useLayoutSettingsStore.d.ts +20 -0
- package/dist/creek-layout/useLayoutSettingsStore.d.ts.map +1 -0
- package/dist/creek-layout/useLayoutSettingsStore.js +45 -0
- package/dist/creek-layout/useLayoutSettingsStore.js.map +7 -0
- package/dist/creek-loading/index.d.ts.map +1 -0
- package/dist/creek-locale-button/index.d.ts +1 -0
- package/dist/creek-locale-button/index.d.ts.map +1 -0
- package/dist/creek-locale-button/index.js +66 -0
- package/dist/creek-locale-button/index.js.map +7 -0
- package/dist/creek-page-container/index.d.ts +4 -0
- package/dist/creek-page-container/index.d.ts.map +1 -0
- package/dist/creek-page-container/index.js +68 -0
- package/dist/creek-page-container/index.js.map +7 -0
- package/dist/creek-style/index.d.ts +1 -0
- package/dist/creek-style/index.d.ts.map +1 -0
- package/dist/creek-style/index.js +24 -0
- package/dist/creek-style/index.js.map +7 -0
- package/dist/creek-style/scrollbar.d.ts +2 -0
- package/dist/creek-style/scrollbar.d.ts.map +1 -0
- package/dist/creek-style/scrollbar.js +55 -0
- package/dist/creek-style/scrollbar.js.map +7 -0
- package/dist/creek-table/SearchTable.d.ts +9 -0
- package/dist/creek-table/SearchTable.d.ts.map +1 -0
- package/dist/creek-table/SearchTable.js +109 -72
- package/dist/creek-table/SearchTable.js.map +3 -3
- package/dist/creek-table/components/DensityIcon.d.ts +9 -0
- package/dist/creek-table/components/DensityIcon.d.ts.map +1 -0
- package/dist/creek-table/components/DensityIcon.js +77 -0
- package/dist/creek-table/components/DensityIcon.js.map +7 -0
- package/dist/creek-table/components/EllipsisTooltip.d.ts +9 -0
- package/dist/creek-table/components/EllipsisTooltip.d.ts.map +1 -0
- package/dist/creek-table/components/EllipsisTooltip.js +122 -0
- package/dist/creek-table/components/EllipsisTooltip.js.map +7 -0
- package/dist/creek-table/components/index.d.ts +2 -0
- package/dist/creek-table/components/index.d.ts.map +1 -0
- package/dist/creek-table/components/index.js +26 -0
- package/dist/creek-table/components/index.js.map +7 -0
- package/dist/creek-table/hooks/index.d.ts +5 -0
- package/dist/creek-table/hooks/index.d.ts.map +1 -0
- package/dist/creek-table/hooks/index.js +10 -0
- package/dist/creek-table/hooks/index.js.map +2 -2
- package/dist/creek-table/hooks/useAdaptiveToolBar.d.ts.map +1 -0
- package/dist/creek-table/hooks/useAutoWidthColumns.d.ts +1 -1
- package/dist/creek-table/hooks/useAutoWidthColumns.d.ts.map +1 -0
- package/dist/creek-table/hooks/useAutoWidthColumns.js +76 -17
- package/dist/creek-table/hooks/useAutoWidthColumns.js.map +2 -2
- package/dist/creek-table/hooks/useElementDistance.d.ts.map +1 -0
- package/dist/creek-table/hooks/useEllipsisColumns.d.ts +8 -0
- package/dist/creek-table/hooks/useEllipsisColumns.d.ts.map +1 -0
- package/dist/creek-table/hooks/useEllipsisColumns.js +58 -0
- package/dist/creek-table/hooks/useEllipsisColumns.js.map +7 -0
- package/dist/creek-table/hooks/useIndexColumn.d.ts +2 -0
- package/dist/creek-table/hooks/useIndexColumn.d.ts.map +1 -0
- package/dist/creek-table/hooks/useIndexColumn.js +52 -0
- package/dist/creek-table/hooks/useIndexColumn.js.map +7 -0
- package/dist/creek-table/hooks/useResizableColumns.d.ts +20 -0
- package/dist/creek-table/hooks/useResizableColumns.d.ts.map +1 -0
- package/dist/creek-table/hooks/useResizableColumns.js +279 -0
- package/dist/creek-table/hooks/useResizableColumns.js.map +7 -0
- package/dist/creek-table/hooks/useStatusColumns.d.ts +2 -0
- package/dist/creek-table/hooks/useStatusColumns.d.ts.map +1 -0
- package/dist/creek-table/hooks/useStatusColumns.js +215 -0
- package/dist/creek-table/hooks/useStatusColumns.js.map +7 -0
- package/dist/creek-table/hooks/useTableOptions.d.ts +15 -0
- package/dist/creek-table/hooks/useTableOptions.d.ts.map +1 -0
- package/dist/creek-table/hooks/useTableOptions.js +78 -0
- package/dist/creek-table/hooks/useTableOptions.js.map +7 -0
- package/dist/creek-table/hooks/useTableScrollHeight.d.ts +6 -1
- package/dist/creek-table/hooks/useTableScrollHeight.d.ts.map +1 -0
- package/dist/creek-table/hooks/useTableScrollHeight.js +44 -5
- package/dist/creek-table/hooks/useTableScrollHeight.js.map +2 -2
- package/dist/creek-table/index.d.ts.map +1 -0
- package/dist/creek-table/type.d.ts +4 -6
- package/dist/creek-table/type.d.ts.map +1 -0
- package/dist/creek-table/type.js.map +1 -1
- package/dist/index.d.ts +4 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +8 -0
- package/dist/index.js.map +2 -2
- package/dist/locales/en-US.d.ts +25 -0
- package/dist/locales/en-US.d.ts.map +1 -0
- package/dist/locales/en-US.js +49 -0
- package/dist/locales/en-US.js.map +7 -0
- package/dist/locales/zh-CN.d.ts +25 -0
- package/dist/locales/zh-CN.d.ts.map +1 -0
- package/dist/locales/zh-CN.js +49 -0
- package/dist/locales/zh-CN.js.map +7 -0
- package/dist/utils/i18n.d.ts +2 -0
- package/dist/utils/i18n.d.ts.map +1 -0
- package/dist/utils/i18n.js +34 -0
- package/dist/utils/i18n.js.map +7 -0
- package/i18n.config.ts +27 -0
- package/package.json +17 -3
- package/src/creek-config-provider/CreekConfigContext.tsx +5 -1
- package/src/creek-config-provider/CreekI18nProvider.tsx +87 -0
- package/src/creek-config-provider/index.tsx +53 -4
- package/src/creek-keep-alive/index.tsx +225 -6
- package/src/creek-layout/{HeaderContent → ActionRender}/FullScreen.tsx +10 -6
- package/src/creek-layout/ActionRender/LayoutSettings.tsx +67 -0
- package/src/creek-layout/ActionRender/UserInfo.tsx +43 -0
- package/src/creek-layout/ActionRender/index.tsx +4 -0
- package/src/creek-layout/index.tsx +121 -53
- package/src/creek-layout/useLayoutSettingsStore.ts +25 -0
- package/src/creek-locale-button/index.tsx +42 -0
- package/src/creek-page-container/index.tsx +32 -0
- package/src/creek-style/index.ts +1 -0
- package/src/creek-style/scrollbar.ts +29 -0
- package/src/creek-table/SearchTable.tsx +125 -72
- package/src/creek-table/components/DensityIcon.tsx +63 -0
- package/src/creek-table/components/EllipsisTooltip.tsx +116 -0
- package/src/creek-table/components/index.tsx +3 -0
- package/src/creek-table/hooks/index.ts +5 -1
- package/src/creek-table/hooks/useAutoWidthColumns.tsx +93 -19
- package/src/creek-table/hooks/useEllipsisColumns.tsx +47 -0
- package/src/creek-table/hooks/useIndexColumn.tsx +27 -0
- package/src/creek-table/hooks/useResizableColumns.tsx +323 -0
- package/src/creek-table/hooks/useStatusColumns.tsx +252 -0
- package/src/creek-table/hooks/useTableOptions.tsx +81 -0
- package/src/creek-table/hooks/useTableScrollHeight.tsx +61 -6
- package/src/creek-table/type.ts +5 -7
- package/src/index.tsx +4 -0
- package/src/locales/en-US.ts +24 -0
- package/src/locales/zh-CN.ts +24 -0
- package/src/utils/i18n.ts +4 -0
- package/dist/creek-layout/HeaderContent/FullScreen.js.map +0 -7
- package/dist/creek-layout/HeaderContent/UserInfo.d.ts +0 -1
- package/dist/creek-layout/HeaderContent/UserInfo.js.map +0 -7
- package/dist/creek-layout/HeaderContent/index.d.ts +0 -1
- package/dist/creek-layout/HeaderContent/index.js +0 -49
- package/dist/creek-layout/HeaderContent/index.js.map +0 -7
- package/dist/creek-table/TableOptionRender.d.ts +0 -9
- package/dist/creek-table/TableOptionRender.js +0 -74
- package/dist/creek-table/TableOptionRender.js.map +0 -7
- package/dist/creek-table/toolBarRender.d.ts +0 -5
- package/dist/creek-table/toolBarRender.js +0 -58
- package/dist/creek-table/toolBarRender.js.map +0 -7
- package/src/creek-layout/HeaderContent/UserInfo.tsx +0 -54
- package/src/creek-layout/HeaderContent/index.tsx +0 -24
- package/src/creek-table/TableOptionRender.tsx +0 -57
- package/src/creek-table/toolBarRender.tsx +0 -28
- /package/dist/creek-layout/{HeaderContent → ActionRender}/FullScreen.d.ts +0 -0
|
@@ -0,0 +1,116 @@
|
|
|
1
|
+
import { CopyOutlined } from '@ant-design/icons';
|
|
2
|
+
import { ConfigProvider, Flex, Tooltip, Typography, message } from 'antd';
|
|
3
|
+
import { createStyles } from 'antd-style';
|
|
4
|
+
import React, { useContext, useEffect, useRef, useState } from 'react';
|
|
5
|
+
|
|
6
|
+
import { useT } from '@/utils/i18n';
|
|
7
|
+
|
|
8
|
+
const useStyles = createStyles(({ css, token }) => {
|
|
9
|
+
return {
|
|
10
|
+
text: css`
|
|
11
|
+
width: 100%;
|
|
12
|
+
margin: 0;
|
|
13
|
+
padding: 0;
|
|
14
|
+
// Ensure the wrapper behaves like a block/inline-block that can have width
|
|
15
|
+
display: block;
|
|
16
|
+
overflow: hidden;
|
|
17
|
+
`,
|
|
18
|
+
tooltipContent: css`
|
|
19
|
+
max-width: 500px;
|
|
20
|
+
max-height: 300px;
|
|
21
|
+
overflow-y: auto;
|
|
22
|
+
`,
|
|
23
|
+
tooltipText: css`
|
|
24
|
+
word-break: break-all;
|
|
25
|
+
white-space: pre-wrap;
|
|
26
|
+
`,
|
|
27
|
+
copyIcon: css`
|
|
28
|
+
cursor: pointer;
|
|
29
|
+
color: inherit;
|
|
30
|
+
transition: color 0.2s;
|
|
31
|
+
|
|
32
|
+
&:hover {
|
|
33
|
+
color: ${token.colorPrimary};
|
|
34
|
+
}
|
|
35
|
+
`,
|
|
36
|
+
};
|
|
37
|
+
});
|
|
38
|
+
|
|
39
|
+
/**
|
|
40
|
+
* 使用 Antd Typography 组件实现省略提示
|
|
41
|
+
* 修复了 findDOMNode 警告问题:通过显式使用 Tooltip 包裹 div 容器
|
|
42
|
+
* 实现了智能提示:只有内容实际溢出时才显示 Tooltip
|
|
43
|
+
*/
|
|
44
|
+
export const EllipsisTooltip = ({ children }: { children: React.ReactNode }) => {
|
|
45
|
+
const t = useT();
|
|
46
|
+
|
|
47
|
+
const { styles } = useStyles();
|
|
48
|
+
const { getPrefixCls } = useContext(ConfigProvider.ConfigContext);
|
|
49
|
+
const textRef = useRef<HTMLDivElement>(null);
|
|
50
|
+
const [isEllipsis, setIsEllipsis] = useState(false);
|
|
51
|
+
const isSimpleContent = typeof children === 'string' || typeof children === 'number';
|
|
52
|
+
|
|
53
|
+
useEffect(() => {
|
|
54
|
+
const checkEllipsis = () => {
|
|
55
|
+
if (textRef.current) {
|
|
56
|
+
const prefixCls = getPrefixCls('typography');
|
|
57
|
+
// Typography.Text renders a span or div with .ant-typography
|
|
58
|
+
const typographyEl = textRef.current.querySelector(`.${prefixCls}`);
|
|
59
|
+
if (typographyEl) {
|
|
60
|
+
// For simple ellipsis={true}, Antd uses CSS ellipsis.
|
|
61
|
+
// We can detect if it's truncated by comparing scrollWidth and clientWidth
|
|
62
|
+
// We add a small buffer (1px) for browser sub-pixel rendering differences
|
|
63
|
+
setIsEllipsis(typographyEl.scrollWidth > typographyEl.clientWidth + 1);
|
|
64
|
+
}
|
|
65
|
+
}
|
|
66
|
+
};
|
|
67
|
+
|
|
68
|
+
// Initial check
|
|
69
|
+
checkEllipsis();
|
|
70
|
+
// Use ResizeObserver for more robust size change detection
|
|
71
|
+
const observer = new ResizeObserver(checkEllipsis);
|
|
72
|
+
if (textRef.current) {
|
|
73
|
+
observer.observe(textRef.current);
|
|
74
|
+
}
|
|
75
|
+
|
|
76
|
+
return () => {
|
|
77
|
+
observer.disconnect();
|
|
78
|
+
};
|
|
79
|
+
}, [children]);
|
|
80
|
+
|
|
81
|
+
const text = String(children);
|
|
82
|
+
|
|
83
|
+
const handleCopy = (e: React.MouseEvent) => {
|
|
84
|
+
e.stopPropagation();
|
|
85
|
+
e.preventDefault();
|
|
86
|
+
navigator.clipboard
|
|
87
|
+
.writeText(text)
|
|
88
|
+
.then(() => {
|
|
89
|
+
message.success(t('creek-table.components.EllipsisTooltip.fuZhiChengGong', '复制成功'));
|
|
90
|
+
})
|
|
91
|
+
.catch(() => {
|
|
92
|
+
message.error(t('creek-table.components.EllipsisTooltip.fuZhiShiBai', '复制失败'));
|
|
93
|
+
});
|
|
94
|
+
};
|
|
95
|
+
|
|
96
|
+
// Memoize tooltip title content
|
|
97
|
+
const tooltipTitle = React.useMemo(() => {
|
|
98
|
+
if (!isSimpleContent) {
|
|
99
|
+
return children;
|
|
100
|
+
}
|
|
101
|
+
return (
|
|
102
|
+
<Flex align="center" gap={8} className={styles.tooltipContent}>
|
|
103
|
+
<span className={styles.tooltipText}>{children}</span>
|
|
104
|
+
<CopyOutlined onClick={handleCopy} className={styles.copyIcon} title={t('creek-table.components.EllipsisTooltip.fuZhi', '复制')} />
|
|
105
|
+
</Flex>
|
|
106
|
+
);
|
|
107
|
+
}, [children, isSimpleContent]);
|
|
108
|
+
|
|
109
|
+
return (
|
|
110
|
+
<Tooltip title={isEllipsis ? tooltipTitle : undefined} placement="topLeft" mouseLeaveDelay={0.2} getPopupContainer={() => document.body}>
|
|
111
|
+
<div ref={textRef} className={styles.text}>
|
|
112
|
+
<Typography.Text ellipsis={true}>{children}</Typography.Text>
|
|
113
|
+
</div>
|
|
114
|
+
</Tooltip>
|
|
115
|
+
);
|
|
116
|
+
};
|
|
@@ -1,6 +1,10 @@
|
|
|
1
1
|
export * from './useAdaptiveToolBar';
|
|
2
2
|
export * from './useAutoWidthColumns';
|
|
3
3
|
export * from './useElementDistance';
|
|
4
|
+
export * from './useEllipsisColumns';
|
|
5
|
+
export * from './useIndexColumn';
|
|
6
|
+
export * from './useResizableColumns';
|
|
7
|
+
export * from './useStatusColumns';
|
|
8
|
+
export * from './useTableOptions';
|
|
4
9
|
export * from './useTableScrollHeight';
|
|
5
10
|
|
|
6
|
-
|
|
@@ -3,12 +3,13 @@ import { useMemoizedFn } from 'ahooks';
|
|
|
3
3
|
import { Space } from 'antd';
|
|
4
4
|
import { RefObject, useEffect, useMemo, useRef, useState } from 'react';
|
|
5
5
|
|
|
6
|
-
const
|
|
6
|
+
const DEFAULT_PADDING_WIDTH_SMALL = 16; // small size (compact)
|
|
7
|
+
const DEFAULT_PADDING_WIDTH_LARGE = 24; // large size (default)
|
|
7
8
|
|
|
8
9
|
/**
|
|
9
|
-
* 估算字符串宽度(简单估算:汉字 14px,非汉字 8px
|
|
10
|
+
* 估算字符串宽度(简单估算:汉字 14px,非汉字 8px)
|
|
10
11
|
*/
|
|
11
|
-
const estimateWidth = (text: string) => {
|
|
12
|
+
const estimateWidth = (text: string, padding: number) => {
|
|
12
13
|
let width = 0;
|
|
13
14
|
for (const char of text) {
|
|
14
15
|
if (/[\u4e00-\u9fa5]/.test(char)) {
|
|
@@ -17,7 +18,7 @@ const estimateWidth = (text: string) => {
|
|
|
17
18
|
width += 8;
|
|
18
19
|
}
|
|
19
20
|
}
|
|
20
|
-
return width +
|
|
21
|
+
return width + padding;
|
|
21
22
|
};
|
|
22
23
|
|
|
23
24
|
/**
|
|
@@ -63,7 +64,9 @@ const MeasureWrapper = ({ children, onResize }: { children: React.ReactNode; onR
|
|
|
63
64
|
// 监听变化
|
|
64
65
|
const observer = new ResizeObserver((entries) => {
|
|
65
66
|
for (const entry of entries) {
|
|
66
|
-
|
|
67
|
+
// 使用 scrollWidth 来获取完整内容宽度,防止被截断时的测量误差
|
|
68
|
+
const width = (entry.target as HTMLElement).scrollWidth;
|
|
69
|
+
onResize(width);
|
|
67
70
|
}
|
|
68
71
|
});
|
|
69
72
|
|
|
@@ -74,29 +77,56 @@ const MeasureWrapper = ({ children, onResize }: { children: React.ReactNode; onR
|
|
|
74
77
|
};
|
|
75
78
|
}, []); // 依赖为空,只在挂载时设置监听
|
|
76
79
|
|
|
77
|
-
|
|
80
|
+
// 使用 inline-block 和 nowrap 防止内容被父容器宽度挤压导致测量不准
|
|
81
|
+
return (
|
|
82
|
+
<div
|
|
83
|
+
ref={ref}
|
|
84
|
+
style={{
|
|
85
|
+
display: 'inline-block',
|
|
86
|
+
whiteSpace: 'nowrap',
|
|
87
|
+
width: 'max-content', // 确保宽度由内容决定
|
|
88
|
+
minWidth: 'min-content',
|
|
89
|
+
}}
|
|
90
|
+
>
|
|
91
|
+
<Space>{children}</Space>
|
|
92
|
+
</div>
|
|
93
|
+
);
|
|
78
94
|
};
|
|
79
95
|
|
|
80
96
|
export const useAutoWidthColumns = <T, ValueType>(
|
|
81
97
|
columns: ProColumns<T, ValueType>[] | undefined,
|
|
82
98
|
tableRef: RefObject<HTMLDivElement>,
|
|
99
|
+
resizedWidths?: Record<string, number>,
|
|
100
|
+
bordered?: boolean,
|
|
101
|
+
size?: 'large' | 'middle' | 'small' | 'medium',
|
|
83
102
|
): { columns: ProColumns<T, ValueType>[] | undefined; totalWidth: number | undefined } => {
|
|
84
103
|
// 存储每个列的最大宽度:key 是 dataIndex 或 title,value 是最大宽度
|
|
85
104
|
const [columnWidths, setColumnWidths] = useState<Record<string, number>>({});
|
|
86
|
-
|
|
105
|
+
// 初始时尝试直接获取宽度,如果 tableRef 已经有值
|
|
106
|
+
const [tableWidth, setTableWidth] = useState<number>(() => {
|
|
107
|
+
if (tableRef.current) {
|
|
108
|
+
return tableRef.current.offsetWidth;
|
|
109
|
+
}
|
|
110
|
+
return 0;
|
|
111
|
+
});
|
|
87
112
|
|
|
88
113
|
// 监听 table 容器宽度变化
|
|
89
114
|
useEffect(() => {
|
|
90
115
|
if (!tableRef.current) return;
|
|
91
|
-
|
|
92
|
-
//
|
|
93
|
-
|
|
116
|
+
|
|
117
|
+
// 如果初始状态是0(因为ref.current可能在render时为null),这里补救一下
|
|
118
|
+
if (tableWidth === 0) {
|
|
119
|
+
setTableWidth(tableRef.current.offsetWidth);
|
|
120
|
+
}
|
|
94
121
|
|
|
95
122
|
// 使用 requestAnimationFrame + setTimeout 防抖
|
|
96
123
|
let rafId: number;
|
|
97
124
|
let timerId: NodeJS.Timeout;
|
|
98
125
|
|
|
99
126
|
const updateWidth = (width: number) => {
|
|
127
|
+
// 忽略 0 宽度的更新(通常是由于 display: none 引起的)
|
|
128
|
+
if (width === 0) return;
|
|
129
|
+
|
|
100
130
|
cancelAnimationFrame(rafId);
|
|
101
131
|
clearTimeout(timerId);
|
|
102
132
|
|
|
@@ -146,20 +176,35 @@ export const useAutoWidthColumns = <T, ValueType>(
|
|
|
146
176
|
|
|
147
177
|
// 1. 先计算所有列的理想宽度(不考虑 table 宽度)
|
|
148
178
|
const calculatedColumns = columns.map((col, index) => {
|
|
149
|
-
const colKey = (col.
|
|
179
|
+
const colKey = (col.key as string) || (col.dataIndex as string) || `col-${index}`;
|
|
150
180
|
const measuredWidth = columnWidths[colKey];
|
|
151
|
-
|
|
181
|
+
|
|
182
|
+
// 根据 size 确定 padding
|
|
183
|
+
let padding = DEFAULT_PADDING_WIDTH_SMALL;
|
|
184
|
+
if (size === 'large') {
|
|
185
|
+
padding = DEFAULT_PADDING_WIDTH_LARGE;
|
|
186
|
+
}
|
|
187
|
+
|
|
188
|
+
let baseWidth: number;
|
|
152
189
|
if (col.width) {
|
|
153
|
-
|
|
190
|
+
baseWidth = typeof col.width === 'number' ? col.width : 100; // 暂时给个默认值如果手动设了 string width
|
|
154
191
|
} else if (col.valueType === 'option' && measuredWidth) {
|
|
155
|
-
|
|
192
|
+
// bordered 模式下,需要额外的宽度来容纳边框和视觉间距,避免换行
|
|
193
|
+
const extraPadding = bordered ? 4: 0;
|
|
194
|
+
baseWidth = measuredWidth + padding + extraPadding;
|
|
156
195
|
} else {
|
|
157
|
-
|
|
196
|
+
baseWidth = Math.max(estimateWidth(col.title as string, padding), getValueTypeWidth(col.valueType as string));
|
|
197
|
+
}
|
|
198
|
+
|
|
199
|
+
let width = baseWidth;
|
|
200
|
+
if (resizedWidths && resizedWidths[colKey]) {
|
|
201
|
+
width = resizedWidths[colKey];
|
|
158
202
|
}
|
|
159
203
|
|
|
160
204
|
return {
|
|
161
205
|
...col,
|
|
162
206
|
_calculatedWidth: width,
|
|
207
|
+
_baseWidth: baseWidth, // 新增 _baseWidth 用于后续 minWidth 限制
|
|
163
208
|
_colKey: colKey,
|
|
164
209
|
};
|
|
165
210
|
});
|
|
@@ -169,11 +214,18 @@ export const useAutoWidthColumns = <T, ValueType>(
|
|
|
169
214
|
|
|
170
215
|
// 3. 判断是否需要自适应
|
|
171
216
|
// 如果总宽度小于 table 宽度,说明空间足够,除了 option 列,其他列可以不设宽度让 table 自动撑开
|
|
172
|
-
|
|
217
|
+
// 但如果有任何列被用户手动 resize 了,我们认为用户希望精确控制,此时也应该返回 totalWidth
|
|
218
|
+
const hasResized = resizedWidths && Object.keys(resizedWidths).length > 0;
|
|
219
|
+
const isOverflow = totalCalculatedWidth > tableWidth || hasResized;
|
|
220
|
+
|
|
221
|
+
// 只有在内容真实溢出(即总宽度 > 容器宽度)时,才强制给未设置宽度的列设置最小估算宽度。
|
|
222
|
+
// 如果仅仅是用户调整了某列宽度但总宽度仍小于容器宽度,此时不应该限制其他列的宽度,
|
|
223
|
+
// 而是利用 table 的自动布局特性让它们填充剩余空间。
|
|
224
|
+
const shouldForceWidth = totalCalculatedWidth > tableWidth;
|
|
173
225
|
|
|
174
226
|
const processedColumns = calculatedColumns.map((col) => {
|
|
175
227
|
// 提取内部使用的字段
|
|
176
|
-
const { _calculatedWidth, _colKey, ...originalCol } = col;
|
|
228
|
+
const { _calculatedWidth, _baseWidth, _colKey, ...originalCol } = col;
|
|
177
229
|
|
|
178
230
|
// 针对 valueType === 'option' (操作列),始终需要特殊处理(包裹测量组件)
|
|
179
231
|
if (col.valueType === 'option') {
|
|
@@ -195,7 +247,29 @@ export const useAutoWidthColumns = <T, ValueType>(
|
|
|
195
247
|
...originalCol,
|
|
196
248
|
// 只有当内容溢出(需要滚动)或者手动设置了宽度时,才应用计算出的宽度
|
|
197
249
|
// 否则不设置 width,让 Antd Table 自动布局占满剩余空间
|
|
198
|
-
width:
|
|
250
|
+
width: shouldForceWidth || col.width || (resizedWidths && resizedWidths[_colKey]) ? _calculatedWidth : undefined,
|
|
251
|
+
// 添加 calculatedWidth 以供后续 useResizableColumns 使用,这里使用 _baseWidth (即不受 resize 影响的宽度)
|
|
252
|
+
calculatedWidth: _baseWidth,
|
|
253
|
+
onHeaderCell: (column: any) => {
|
|
254
|
+
const originalProps = originalCol.onHeaderCell ? originalCol.onHeaderCell(column) : {};
|
|
255
|
+
return {
|
|
256
|
+
...originalProps,
|
|
257
|
+
style: {
|
|
258
|
+
...originalProps.style,
|
|
259
|
+
minWidth: _calculatedWidth,
|
|
260
|
+
},
|
|
261
|
+
};
|
|
262
|
+
},
|
|
263
|
+
onCell: (record: any, index: any) => {
|
|
264
|
+
const originalProps = originalCol.onCell ? originalCol.onCell(record, index) : {};
|
|
265
|
+
return {
|
|
266
|
+
...originalProps,
|
|
267
|
+
style: {
|
|
268
|
+
...originalProps.style,
|
|
269
|
+
minWidth: _calculatedWidth,
|
|
270
|
+
},
|
|
271
|
+
};
|
|
272
|
+
},
|
|
199
273
|
};
|
|
200
274
|
});
|
|
201
275
|
|
|
@@ -203,7 +277,7 @@ export const useAutoWidthColumns = <T, ValueType>(
|
|
|
203
277
|
columns: processedColumns,
|
|
204
278
|
totalWidth: isOverflow ? totalCalculatedWidth : undefined,
|
|
205
279
|
};
|
|
206
|
-
}, [columns, columnWidths, tableWidth]);
|
|
280
|
+
}, [columns, columnWidths, tableWidth, resizedWidths]);
|
|
207
281
|
|
|
208
282
|
return {
|
|
209
283
|
columns: finalColumns,
|
|
@@ -0,0 +1,47 @@
|
|
|
1
|
+
import type { ParamsType, ProColumns } from '@ant-design/pro-components';
|
|
2
|
+
import React, { useMemo } from 'react';
|
|
3
|
+
import { EllipsisTooltip } from '../components';
|
|
4
|
+
|
|
5
|
+
/**
|
|
6
|
+
* 默认开启 ellipsis 的 Hook
|
|
7
|
+
* 1. 如果用户未配置 ellipsis,默认开启,并使用 Tooltip 显示完整内容
|
|
8
|
+
* 2. 如果是 option 列,默认不开启
|
|
9
|
+
* 3. 尊重用户配置
|
|
10
|
+
*/
|
|
11
|
+
export const useEllipsisColumns = <T extends ParamsType, ValueType = 'text'>(
|
|
12
|
+
columns: ProColumns<T, ValueType>[] | undefined,
|
|
13
|
+
) => {
|
|
14
|
+
const processedColumns = useMemo(() => {
|
|
15
|
+
return columns?.map((col) => {
|
|
16
|
+
// 对于操作列,默认不开启 ellipsis
|
|
17
|
+
if (col.valueType === 'option') {
|
|
18
|
+
return col;
|
|
19
|
+
}
|
|
20
|
+
// 其他列默认开启 ellipsis,并使用自定义渲染
|
|
21
|
+
return {
|
|
22
|
+
...col,
|
|
23
|
+
// 关闭 Table 自带的 ellipsis title,因为我们要用自己的 Tooltip
|
|
24
|
+
// 但保留 ellipsis 属性以确保 Table 传递正确的样式给 cell(虽然我们的 EllipsisTooltip 也有样式)
|
|
25
|
+
// 实际上,为了让 EllipsisTooltip 占据 100% 宽度并生效,最好让 Table cell 也保持一定的约束
|
|
26
|
+
ellipsis: {
|
|
27
|
+
showTitle: false,
|
|
28
|
+
},
|
|
29
|
+
render: (dom: React.ReactNode, entity: T, index: number, action: any, schema: any) => {
|
|
30
|
+
const originalRenderResult = col.render ? (col.render(dom, entity, index, action, schema) as React.ReactNode) : dom;
|
|
31
|
+
|
|
32
|
+
// 如果内容为空,直接返回
|
|
33
|
+
if (originalRenderResult === null || originalRenderResult === undefined || originalRenderResult === '') {
|
|
34
|
+
return originalRenderResult;
|
|
35
|
+
}
|
|
36
|
+
|
|
37
|
+
// 如果是简单的文本或数字,使用 EllipsisTooltip 包裹
|
|
38
|
+
return (
|
|
39
|
+
<EllipsisTooltip>{originalRenderResult}</EllipsisTooltip>
|
|
40
|
+
);
|
|
41
|
+
},
|
|
42
|
+
} as ProColumns<T, ValueType>;
|
|
43
|
+
});
|
|
44
|
+
}, [columns]);
|
|
45
|
+
|
|
46
|
+
return processedColumns;
|
|
47
|
+
};
|
|
@@ -0,0 +1,27 @@
|
|
|
1
|
+
import { ProColumns } from '@ant-design/pro-components';
|
|
2
|
+
import { useMemo } from 'react';
|
|
3
|
+
|
|
4
|
+
import { useT } from '@/utils/i18n';
|
|
5
|
+
|
|
6
|
+
export const useIndexColumn = <T = any, ValueType = 'text'>(columns: ProColumns<T, ValueType>[] = [], showIndex: boolean = true) => {
|
|
7
|
+
const t = useT();
|
|
8
|
+
|
|
9
|
+
return useMemo(() => {
|
|
10
|
+
if (!showIndex) {
|
|
11
|
+
return columns;
|
|
12
|
+
}
|
|
13
|
+
const indexColumn: ProColumns<T, ValueType> = {
|
|
14
|
+
title: t('creek-table.hooks.useIndexColumn.xuHao', '序号'),
|
|
15
|
+
dataIndex: 'index',
|
|
16
|
+
width: 48,
|
|
17
|
+
fixed: 'left',
|
|
18
|
+
disable: true,
|
|
19
|
+
hideInSearch: true,
|
|
20
|
+
render: (dom, entity, index, action, schema) => {
|
|
21
|
+
const { current = 1, pageSize = 20 } = action?.pageInfo || {};
|
|
22
|
+
return (current - 1) * pageSize + index + 1;
|
|
23
|
+
},
|
|
24
|
+
};
|
|
25
|
+
return [indexColumn, ...columns];
|
|
26
|
+
}, [columns, showIndex, t]);
|
|
27
|
+
};
|