antd 的 Table 默认 ellipsis: true 只能单行省略。实际项目中,我们常常需要:
- 多行文本超出时显示省略号
- 可自定义行数
- 仅在真正溢出时显示 Tooltip
1️⃣ EllipsisText.tsx(多行省略 + Tooltip 组件)
ini
import { Tooltip } from 'antd';
import classNames from 'classnames';
import React, { useEffect, useRef, useState } from 'react';
import './index.less';
interface EllipsisTextProps {
text: string | number;
lines?: number;
width?: number | string;
showTooltip?: boolean;
style?: React.CSSProperties;
className?: string;
}
const EllipsisText: React.FC<EllipsisTextProps> = ({
text,
lines = 1,
width = '100%',
showTooltip = true,
style = {},
className,
}) => {
const textRef = useRef<HTMLSpanElement>(null);
const [isOverflow, setIsOverflow] = useState(false);
const checkOverflow = () => {
const el = textRef.current;
if (!el) return;
setIsOverflow(el.scrollHeight > el.clientHeight + 2); // 防浮点误差
};
useEffect(() => {
checkOverflow();
const observer = new ResizeObserver(() => checkOverflow());
if (textRef.current) observer.observe(textRef.current);
return () => observer.disconnect();
}, [text, width, lines]);
const content = (
<span
ref={textRef}
className={classNames('ellipsis-text', className)}
style={{
WebkitLineClamp: lines,
width,
...style,
}}
>
{text}
</span>
);
return showTooltip && isOverflow ? (
<Tooltip title={text}>{content}</Tooltip>
) : (
content
);
};
export default EllipsisText;
2️⃣ EllipsisText.less(多行省略样式)
arduino
.ellipsis-text {
display: -webkit-box; // 多行省略必需
-webkit-box-orient: vertical; // 设置伸展方向
overflow: hidden; // 隐藏溢出文本
text-overflow: ellipsis; // 溢出显示省略号
word-break: break-word; // 防止长单词撑破容器
width: 100%; // 自适应父元素宽度
}
3️⃣ ProTable.tsx(封装 Table)
ini
import { EllipsisText } from '@pl/react-ui';
import { Table } from 'antd';
import type { ColumnsType, ColumnType, TableProps } from 'antd/es/table';
import React, { useMemo } from 'react';
interface CustomEllipsis {
lines?: number;
showTooltip?: boolean;
style?: React.CSSProperties;
className?: string;
}
interface ProColumnType<T> extends ColumnType<T> {
customEllipsis?: CustomEllipsis;
}
type ProTableProps<T> = TableProps<T> & {
columns: ProColumnType<T>[];
};
function ProTable<T extends object>({ columns, ...rest }: ProTableProps<T>) {
const enhancedColumns = useMemo(() => {
return columns.map((col: ProColumnType<T>) => {
if (!col.customEllipsis) return col;
const {
lines = 1,
showTooltip = true,
style = {},
className,
} = col.customEllipsis;
const originalRender = col.render;
return {
...col,
render: (text: any, record: T, index: number) => {
const content = originalRender
? originalRender(text, record, index)
: text;
return (
<EllipsisText
text={content}
lines={lines}
showTooltip={showTooltip}
width={col.width}
style={style}
className={className}
/>
);
},
};
});
}, [columns]);
return <Table {...rest} columns={enhancedColumns as ColumnsType<T>} />;
}
export default ProTable;
4️⃣ Demo 使用示例
typescript
import { ProTable } from '@pl/react-ui';
import React from 'react';
interface DataType {
key: string;
name: string;
description: string;
extra: string;
}
const data: DataType[] = [
{
key: '1',
name: 'Ant Design Table Component',
description:
'这是一个可以多行省略的示例文字,如果内容太长,会显示省略号,并通过 Tooltip 展示完整内容。',
extra: '这是额外信息,可以自定义 render。',
},
{
key: '2',
name: 'Another Row',
description: '短文字不需要省略。',
extra: '短信息',
},
];
const columns = [
{
title: 'Name(1行省略 + 显示Tooltip)',
dataIndex: 'name',
key: 'name',
customEllipsis: { lines: 1, showTooltip: true },
},
{
title: 'Description(2行省略 + 显示Tooltip)',
dataIndex: 'description',
key: 'description',
customEllipsis: { lines: 2, showTooltip: true },
},
{
title: 'Extra Info(1行省略 + 不显示Tooltip)',
dataIndex: 'extra',
key: 'extra',
customEllipsis: {
lines: 1,
showTooltip: false,
style: { background: 'pink' },
className: 'extra-class',
},
render: (text: string) => <span style={{ color: 'blue' }}>{text}</span>,
},
];
export default function Demo() {
return (
<ProTable<DataType>
columns={columns}
dataSource={data}
pagination={false}
bordered
/>
);
}
✅ 特性总结
- 多行文字省略,可自定义行数
- 动态溢出检测,自动显示 Tooltip
- 自定义样式和类名,可满足企业级表格需求
- 兼容自定义 render,保持原列功能