Skip to content

Commit

Permalink
feat: refactor descriptions (#4219)
Browse files Browse the repository at this point in the history
  • Loading branch information
zkwolf authored Jun 18, 2021
1 parent 3557e01 commit 8e078d1
Show file tree
Hide file tree
Showing 7 changed files with 231 additions and 77 deletions.
52 changes: 36 additions & 16 deletions components/descriptions/Cell.tsx
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
import { VNodeTypes, HTMLAttributes, FunctionalComponent } from 'vue';
import { VNodeTypes, HTMLAttributes, FunctionalComponent, CSSProperties } from 'vue';

function notEmpty(val: any) {
return val !== undefined && val !== null;
Expand All @@ -8,14 +8,26 @@ interface CellProps extends HTMLAttributes {
itemPrefixCls: string;
span: number;
component: string;
labelStyle?: CSSProperties;
contentStyle?: CSSProperties;
bordered?: boolean;
label?: VNodeTypes;
content?: VNodeTypes;
colon?: boolean;
}

const Cell: FunctionalComponent<CellProps> = props => {
const { itemPrefixCls, component, span, bordered, label, content, colon } = props;
const {
itemPrefixCls,
component,
span,
labelStyle,
contentStyle,
bordered,
label,
content,
colon,
} = props;
const Component = component as any;
if (bordered) {
return (
Expand All @@ -28,26 +40,34 @@ const Cell: FunctionalComponent<CellProps> = props => {
]}
colSpan={span}
>
{notEmpty(label) ? label : content}
{notEmpty(label) && <span style={labelStyle}>{label}</span>}
{notEmpty(content) && <span style={contentStyle}>{content}</span>}
</Component>
);
}

return (
<Component class={[`${itemPrefixCls}-item`]} colSpan={span}>
{label && (
<span
class={[
`${itemPrefixCls}-item-label`,
{
[`${itemPrefixCls}-item-no-colon`]: !colon,
},
]}
>
{label}
</span>
)}
{content && <span class={`${itemPrefixCls}-item-content`}>{content}</span>}
<div class={`${itemPrefixCls}-item-container`}>
{label && (
<span
class={[
`${itemPrefixCls}-item-label`,
{
[`${itemPrefixCls}-item-no-colon`]: !colon,
},
]}
style={labelStyle}
>
{label}
</span>
)}
{content && (
<span class={`${itemPrefixCls}-item-content`} style={contentStyle}>
{content}
</span>
)}
</div>
</Component>
);
};
Expand Down
41 changes: 35 additions & 6 deletions components/descriptions/Row.tsx
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
import Cell from './Cell';
import { getOptionProps, getSlot, getClass, getStyle, getComponent } from '../_util/props-util';
import { FunctionalComponent, VNode } from 'vue';
import { FunctionalComponent, VNode, inject } from 'vue';
import { descriptionsContext, DescriptionsContextProp } from './index';

interface CellConfig {
component: string | [string, string];
Expand All @@ -22,10 +23,22 @@ const Row: FunctionalComponent<RowProps> = props => {
const renderCells = (
items: VNode[],
{ colon, prefixCls, bordered },
{ component, type, showLabel, showContent }: CellConfig,
{
component,
type,
showLabel,
showContent,
labelStyle: rootLabelStyle,
contentStyle: rootContentStyle,
}: CellConfig & DescriptionsContextProp,
) => {
return items.map((item, index) => {
const { prefixCls: itemPrefixCls = prefixCls, span = 1 } = getOptionProps(item);
const {
prefixCls: itemPrefixCls = prefixCls,
span = 1,
labelStyle,
contentStyle,
} = getOptionProps(item);
const label = getComponent(item, 'label');

const children = getSlot(item);
Expand All @@ -39,6 +52,8 @@ const Row: FunctionalComponent<RowProps> = props => {
key={`${type}-${key || index}`}
class={className}
style={style}
labelStyle={{ ...rootLabelStyle, ...labelStyle }}
contentStyle={{ ...rootContentStyle, ...contentStyle }}
span={span}
colon={colon}
component={component}
Expand All @@ -54,7 +69,7 @@ const Row: FunctionalComponent<RowProps> = props => {
<Cell
key={`label-${key || index}`}
class={className}
style={style}
style={{ ...rootLabelStyle, ...style, ...labelStyle }}
span={1}
colon={colon}
component={component[0]}
Expand All @@ -65,7 +80,7 @@ const Row: FunctionalComponent<RowProps> = props => {
<Cell
key={`content-${key || index}`}
class={className}
style={style}
style={{ ...rootContentStyle, ...style, ...contentStyle }}
span={span * 2 - 1}
component={component[1]}
itemPrefixCls={itemPrefixCls}
Expand All @@ -77,17 +92,29 @@ const Row: FunctionalComponent<RowProps> = props => {
};

const { prefixCls, vertical, row, index, bordered } = props;
const { labelStyle, contentStyle } = inject(descriptionsContext, {
labelStyle: undefined,
contentStyle: undefined,
});
if (vertical) {
return (
<>
<tr key={`label-${index}`} class={`${prefixCls}-row`}>
{renderCells(row, props, { component: 'th', type: 'label', showLabel: true })}
{renderCells(row, props, {
component: 'th',
type: 'label',
showLabel: true,
labelStyle: labelStyle.value,
contentStyle: contentStyle.value,
})}
</tr>
<tr key={`content-${index}`} class={`${prefixCls}-row`}>
{renderCells(row, props, {
component: 'td',
type: 'content',
showContent: true,
labelStyle: labelStyle.value,
contentStyle: contentStyle.value,
})}
</tr>
</>
Expand All @@ -101,6 +128,8 @@ const Row: FunctionalComponent<RowProps> = props => {
type: 'item',
showLabel: true,
showContent: true,
labelStyle: labelStyle.value,
contentStyle: contentStyle.value,
})}
</tr>
);
Expand Down
84 changes: 61 additions & 23 deletions components/descriptions/__tests__/__snapshots__/index.test.js.snap
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,9 @@ exports[`Descriptions Descriptions support colon 1`] = `
<table>
<tbody>
<tr class="ant-descriptions-row">
<td class="ant-descriptions-item" colspan="3"><span class="ant-descriptions-item-label ant-descriptions-item-no-colon">Product</span><span class="ant-descriptions-item-content">Cloud Database</span></td>
<td class="ant-descriptions-item" colspan="3">
<div class="ant-descriptions-item-container"><span class="ant-descriptions-item-label ant-descriptions-item-no-colon">Product</span><span class="ant-descriptions-item-content">Cloud Database</span></div>
</td>
</tr>
</tbody>
</table>
Expand All @@ -23,7 +25,9 @@ exports[`Descriptions Descriptions support style 1`] = `
<tbody>
<tr class="ant-descriptions-row">
<td class="ant-descriptions-item" colspan="3">
<!----><span class="ant-descriptions-item-content">Cloud Database</span>
<div class="ant-descriptions-item-container">
<!----><span class="ant-descriptions-item-content">Cloud Database</span>
</div>
</td>
</tr>
</tbody>
Expand All @@ -39,7 +43,9 @@ exports[`Descriptions Descriptions.Item support className 1`] = `
<table>
<tbody>
<tr class="ant-descriptions-row">
<td class="ant-descriptions-item my-class" colspan="3"><span class="ant-descriptions-item-label">Product</span><span class="ant-descriptions-item-content">Cloud Database</span></td>
<td class="ant-descriptions-item my-class" colspan="3">
<div class="ant-descriptions-item-container"><span class="ant-descriptions-item-label">Product</span><span class="ant-descriptions-item-content">Cloud Database</span></div>
</td>
</tr>
</tbody>
</table>
Expand All @@ -54,12 +60,20 @@ exports[`Descriptions column is number 1`] = `
<table>
<tbody>
<tr class="ant-descriptions-row">
<td class="ant-descriptions-item" colspan="1"><span class="ant-descriptions-item-label">Product</span><span class="ant-descriptions-item-content">Cloud Database</span></td>
<td class="ant-descriptions-item" colspan="1"><span class="ant-descriptions-item-label">Billing</span><span class="ant-descriptions-item-content">Prepaid</span></td>
<td class="ant-descriptions-item" colspan="1"><span class="ant-descriptions-item-label">time</span><span class="ant-descriptions-item-content">18:00:00</span></td>
<td class="ant-descriptions-item" colspan="1">
<div class="ant-descriptions-item-container"><span class="ant-descriptions-item-label">Product</span><span class="ant-descriptions-item-content">Cloud Database</span></div>
</td>
<td class="ant-descriptions-item" colspan="1">
<div class="ant-descriptions-item-container"><span class="ant-descriptions-item-label">Billing</span><span class="ant-descriptions-item-content">Prepaid</span></div>
</td>
<td class="ant-descriptions-item" colspan="1">
<div class="ant-descriptions-item-container"><span class="ant-descriptions-item-label">time</span><span class="ant-descriptions-item-content">18:00:00</span></div>
</td>
</tr>
<tr class="ant-descriptions-row">
<td class="ant-descriptions-item" colspan="3"><span class="ant-descriptions-item-label">Amount</span><span class="ant-descriptions-item-content">$80.00</span></td>
<td class="ant-descriptions-item" colspan="3">
<div class="ant-descriptions-item-container"><span class="ant-descriptions-item-label">Amount</span><span class="ant-descriptions-item-content">$80.00</span></div>
</td>
</tr>
</tbody>
</table>
Expand All @@ -74,35 +88,51 @@ exports[`Descriptions vertical layout 1`] = `
<table>
<tbody>
<tr class="ant-descriptions-row">
<th class="ant-descriptions-item" colspan="1"><span class="ant-descriptions-item-label">Product</span>
<!---->
<th class="ant-descriptions-item" colspan="1">
<div class="ant-descriptions-item-container"><span class="ant-descriptions-item-label">Product</span>
<!---->
</div>
</th>
<th class="ant-descriptions-item" colspan="1"><span class="ant-descriptions-item-label">Billing</span>
<!---->
<th class="ant-descriptions-item" colspan="1">
<div class="ant-descriptions-item-container"><span class="ant-descriptions-item-label">Billing</span>
<!---->
</div>
</th>
<th class="ant-descriptions-item" colspan="1"><span class="ant-descriptions-item-label">time</span>
<!---->
<th class="ant-descriptions-item" colspan="1">
<div class="ant-descriptions-item-container"><span class="ant-descriptions-item-label">time</span>
<!---->
</div>
</th>
</tr>
<tr class="ant-descriptions-row">
<td class="ant-descriptions-item" colspan="1">
<!----><span class="ant-descriptions-item-content">Cloud Database</span>
<div class="ant-descriptions-item-container">
<!----><span class="ant-descriptions-item-content">Cloud Database</span>
</div>
</td>
<td class="ant-descriptions-item" colspan="1">
<!----><span class="ant-descriptions-item-content">Prepaid</span>
<div class="ant-descriptions-item-container">
<!----><span class="ant-descriptions-item-content">Prepaid</span>
</div>
</td>
<td class="ant-descriptions-item" colspan="1">
<!----><span class="ant-descriptions-item-content">18:00:00</span>
<div class="ant-descriptions-item-container">
<!----><span class="ant-descriptions-item-content">18:00:00</span>
</div>
</td>
</tr>
<tr class="ant-descriptions-row">
<th class="ant-descriptions-item" colspan="3"><span class="ant-descriptions-item-label">Amount</span>
<!---->
<th class="ant-descriptions-item" colspan="3">
<div class="ant-descriptions-item-container"><span class="ant-descriptions-item-label">Amount</span>
<!---->
</div>
</th>
</tr>
<tr class="ant-descriptions-row">
<td class="ant-descriptions-item" colspan="3">
<!----><span class="ant-descriptions-item-content">$80.00</span>
<div class="ant-descriptions-item-container">
<!----><span class="ant-descriptions-item-content">$80.00</span>
</div>
</td>
</tr>
</tbody>
Expand All @@ -118,12 +148,20 @@ exports[`Descriptions when item is rendered conditionally 1`] = `
<table>
<tbody>
<tr class="ant-descriptions-row">
<td class="ant-descriptions-item" colspan="1"><span class="ant-descriptions-item-label">Product</span><span class="ant-descriptions-item-content">Cloud Database</span></td>
<td class="ant-descriptions-item" colspan="1"><span class="ant-descriptions-item-label">Billing</span><span class="ant-descriptions-item-content">Prepaid</span></td>
<td class="ant-descriptions-item" colspan="1"><span class="ant-descriptions-item-label">time</span><span class="ant-descriptions-item-content">18:00:00</span></td>
<td class="ant-descriptions-item" colspan="1">
<div class="ant-descriptions-item-container"><span class="ant-descriptions-item-label">Product</span><span class="ant-descriptions-item-content">Cloud Database</span></div>
</td>
<td class="ant-descriptions-item" colspan="1">
<div class="ant-descriptions-item-container"><span class="ant-descriptions-item-label">Billing</span><span class="ant-descriptions-item-content">Prepaid</span></div>
</td>
<td class="ant-descriptions-item" colspan="1">
<div class="ant-descriptions-item-container"><span class="ant-descriptions-item-label">time</span><span class="ant-descriptions-item-content">18:00:00</span></div>
</td>
</tr>
<tr class="ant-descriptions-row">
<td class="ant-descriptions-item" colspan="3"><span class="ant-descriptions-item-label">Amount</span><span class="ant-descriptions-item-content">$80.00</span></td>
<td class="ant-descriptions-item" colspan="3">
<div class="ant-descriptions-item-container"><span class="ant-descriptions-item-label">Amount</span><span class="ant-descriptions-item-content">$80.00</span></div>
</td>
</tr>
</tbody>
</table>
Expand Down
23 changes: 15 additions & 8 deletions components/descriptions/__tests__/index.test.js
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
import { mount } from '@vue/test-utils';
import { h } from 'vue';
import MockDate from 'mockdate';
import Descriptions from '..';
import { resetWarned } from '../../_util/warning';
Expand Down Expand Up @@ -263,21 +264,27 @@ describe('Descriptions', () => {
});

it('Descriptions support extra', async () => {
const wrapper = mount({
render() {
return (
<Descriptions extra="Edit">
<Descriptions.Item label="UserName">Zhou Maomao</Descriptions.Item>
</Descriptions>
);
const wrapper = mount(Descriptions, {
props: {
extra: 'Edit',
},
slots: {
default: h(
Descriptions.Item,
{
label: 'UserName',
},
'Zhou Maomao',
),
},
});

await asyncExpect(() => {
expect(wrapper.find('.ant-descriptions-extra').exists()).toBe(true);
wrapper.setProps({ extra: undefined });
});

wrapper.setProps({ extra: undefined });

await asyncExpect(() => {
expect(wrapper.find('.ant-descriptions-extra').exists()).toBe(false);
});
Expand Down
Loading

0 comments on commit 8e078d1

Please sign in to comment.