Skip to content

Commit daf3b4e

Browse files
authored
feat: support custom cell ellipsis tooltip (#474)
* feat: support custom ellipsis tooltip * feat: add showTitle api for ellipsis
1 parent 8f736e6 commit daf3b4e

File tree

7 files changed

+120
-4
lines changed

7 files changed

+120
-4
lines changed

.gitignore

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -33,4 +33,5 @@ es/
3333
.storybook
3434
.doc
3535
!tests/__mocks__/rc-util/lib
36-
examples/debug.tsx
36+
examples/debug.tsx
37+
.history
Lines changed: 71 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,71 @@
1+
import React from 'react';
2+
import Tooltip from 'rc-tooltip';
3+
import Table from '../src';
4+
import '../assets/index.less';
5+
import 'rc-tooltip/assets/bootstrap.css';
6+
7+
const createColumns = (length: number) => {
8+
return Array.from({ length }, (_, i) => ({
9+
title: 'description',
10+
dataIndex: 'description',
11+
key: `description ${i + 1}`,
12+
ellipsis: {
13+
showTitle: false,
14+
},
15+
...(i === 0 ? { width: 50 } : null),
16+
render(description: string) {
17+
return (
18+
<Tooltip placement="topLeft" overlay={description}>
19+
<span>{description}</span>
20+
</Tooltip>
21+
);
22+
},
23+
}));
24+
};
25+
26+
const columns = [
27+
{
28+
title: 'name',
29+
dataIndex: 'name',
30+
width: 100,
31+
ellipsis: {
32+
showTitle: false,
33+
},
34+
render: (name: string) => (
35+
<Tooltip placement="topLeft" overlay={name}>
36+
<span>{name}</span>
37+
</Tooltip>
38+
),
39+
},
40+
...createColumns(10),
41+
{
42+
title: 'Operations',
43+
key: 'operations',
44+
ellipsis: {
45+
showTitle: false,
46+
},
47+
render() {
48+
return (
49+
<Tooltip placement="topLeft" overlay="Operations">
50+
<a href="#">Operations</a>
51+
</Tooltip>
52+
);
53+
},
54+
},
55+
];
56+
57+
const data = [
58+
{ name: 'jack', description: 'description description', key: '1' },
59+
{ name: 'jackjackjackjackjackjack', description: 'description description', key: '2' },
60+
{ name: 'jack ma', description: 'description description', key: '3' },
61+
{ name: 'jack nickson', description: 'description description', key: '4' },
62+
];
63+
64+
const Demo = () => (
65+
<div>
66+
<h2>Table ellipsis custom tooltip</h2>
67+
<Table columns={columns} data={data} />
68+
</div>
69+
);
70+
71+
export default Demo;

package.json

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -74,6 +74,7 @@
7474
"rc-animate": "^3.0.0",
7575
"rc-dropdown": "~3.1.0",
7676
"rc-menu": "^8.0.2",
77+
"rc-tooltip": "^4.0.3",
7778
"react": "^16.0.0",
7879
"react-dnd": "^2.5.4",
7980
"react-dnd-html5-backend": "^2.5.4",

src/Cell/index.tsx

Lines changed: 7 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -9,6 +9,7 @@ import {
99
CellType,
1010
DefaultRecordType,
1111
AlignType,
12+
CellEllipsisType,
1213
} from '../interface';
1314
import { getPathValue } from '../utils/valueUtil';
1415

@@ -38,7 +39,7 @@ export interface CellProps<RecordType extends DefaultRecordType> {
3839
children?: React.ReactNode;
3940
colSpan?: number;
4041
rowSpan?: number;
41-
ellipsis?: boolean;
42+
ellipsis?: CellEllipsisType;
4243
align?: AlignType;
4344

4445
shouldCellUpdate?: (record: RecordType) => boolean;
@@ -55,6 +56,8 @@ export interface CellProps<RecordType extends DefaultRecordType> {
5556
/** @private Used for `expandable` with nest tree */
5657
appendNode?: React.ReactNode;
5758
additionalProps?: React.HTMLAttributes<HTMLElement>;
59+
60+
rowType?: 'header' | 'body' | 'footer';
5861
}
5962

6063
function Cell<RecordType extends DefaultRecordType>(
@@ -79,6 +82,7 @@ function Cell<RecordType extends DefaultRecordType>(
7982
additionalProps = {},
8083
ellipsis,
8184
align,
85+
rowType,
8286
}: CellProps<RecordType>,
8387
ref: React.Ref<any>,
8488
): React.ReactElement {
@@ -157,7 +161,8 @@ function Cell<RecordType extends DefaultRecordType>(
157161

158162
// ====================== Render ======================
159163
let title: string;
160-
if (ellipsis) {
164+
const ellipsisConfig: CellEllipsisType = ellipsis === true ? { showTitle: true } : ellipsis;
165+
if (ellipsisConfig && (ellipsisConfig.showTitle || rowType === 'header')) {
161166
if (typeof childNode === 'string' || typeof childNode === 'number') {
162167
title = childNode.toString();
163168
} else if (React.isValidElement(childNode) && typeof childNode.props.children === 'string') {

src/Header/HeaderRow.tsx

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -66,6 +66,7 @@ function HeaderRow<RecordType>({
6666
key={columnsKey[cellIndex]}
6767
{...fixedInfo}
6868
additionalProps={additionalProps}
69+
rowType="header"
6970
/>
7071
);
7172
})}

src/interface.ts

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -55,13 +55,15 @@ export interface RenderedCell<RecordType> {
5555

5656
export type DataIndex = string | number | (string | number)[];
5757

58+
export type CellEllipsisType = { showTitle?: boolean } | boolean;
59+
5860
interface ColumnSharedType<RecordType> {
5961
title?: React.ReactNode;
6062
key?: Key;
6163
className?: string;
6264
fixed?: FixedType;
6365
onHeaderCell?: GetComponentProps<ColumnsType<RecordType>[number]>;
64-
ellipsis?: boolean;
66+
ellipsis?: CellEllipsisType;
6567
align?: AlignType;
6668
}
6769

tests/Table.spec.js

Lines changed: 35 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -267,6 +267,41 @@ describe('Table.Basic', () => {
267267
});
268268
});
269269

270+
it('renders ellipsis by showTitle option', () => {
271+
const wrapper = mount(
272+
createTable({
273+
columns: [
274+
{ title: 'title', ellipsis: { showTitle: true } },
275+
{ title: 'node title', ellipsis: { showTitle: true }, render: () => <h1>233</h1> },
276+
],
277+
}),
278+
);
279+
280+
wrapper.find('td').forEach(td => {
281+
expect(td.hasClass('rc-table-cell-ellipsis')).toBeTruthy();
282+
});
283+
});
284+
285+
it('not renders ellipsis origin html title', () => {
286+
const columns = [
287+
{ title: 'title', ellipsis: { showTitle: false } },
288+
{ title: 'node title', ellipsis: { showTitle: false }, render: () => <h1>233</h1> },
289+
];
290+
const wrapper = mount(
291+
createTable({
292+
columns,
293+
}),
294+
);
295+
296+
wrapper.find('.rc-table-thead th').forEach(td => {
297+
expect(td.getDOMNode().attributes.getNamedItem('title')).toBeTruthy();
298+
});
299+
300+
wrapper.find('.rc-table-tbody td').forEach(td => {
301+
expect(td.getDOMNode().attributes.getNamedItem('title')).toBeFalsy();
302+
});
303+
});
304+
270305
it('renders column correctly', () => {
271306
const columns = [
272307
{

0 commit comments

Comments
 (0)