Skip to content

Commit

Permalink
refactor: use token instead of constant in size (ant-design#44598)
Browse files Browse the repository at this point in the history
* refactor: use token instead of constant in size

* fix: fix

* fix: fix

* test: update snap

* fix: update snap

* test: fix test case

* fix: fix

* fix: fix

* fix: fix

* fix: fix tast cov

* fix: fix test case

* chore: add comment

* chore: add comment

* chore: add comment

* chore: rename

* chore: rename

* fix: fix test case

* fix: fix test case

* fix: fix

* fix: fix

* fix: fix

* fix: fix

* test: add test case

* fix: fix

* test: update snap

* fix: fix

* fix: fix

* test: update

* test: update

* chore: fix

* fix: type

* test: remove test
  • Loading branch information
li-jia-nan authored Sep 4, 2023
1 parent b284648 commit 4c91896
Show file tree
Hide file tree
Showing 9 changed files with 162 additions and 92 deletions.
5 changes: 4 additions & 1 deletion components/space/Item.tsx
Original file line number Diff line number Diff line change
@@ -1,5 +1,7 @@
import * as React from 'react';

import { SpaceContext } from './context';
import type { SpaceContextType } from './context';

export interface ItemProps {
className: string;
Expand All @@ -23,7 +25,7 @@ const Item: React.FC<ItemProps> = ({
style: customStyle,
}) => {
const { horizontalSize, verticalSize, latestIndex, supportFlexGap } =
React.useContext(SpaceContext);
React.useContext<SpaceContextType>(SpaceContext);

let style: React.CSSProperties = {};

Expand All @@ -34,6 +36,7 @@ const Item: React.FC<ItemProps> = ({
}
} else {
style = {
// Compatible IE, cannot use `marginInlineEnd`
...(index < latestIndex && { [marginDirection]: horizontalSize / (split ? 2 : 1) }),
...(wrap && { paddingBottom: verticalSize }),
};
Expand Down
37 changes: 27 additions & 10 deletions components/space/__tests__/gap.test.tsx
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
import React from 'react';

import Space from '..';
import { render } from '../../../tests/utils';

Expand All @@ -16,15 +17,31 @@ describe('flex gap', () => {
<span />
</Space>,
);
expect(
container.querySelector<HTMLDivElement>('div.ant-space')?.style[
'column-gap' as keyof CSSStyleDeclaration
],
).toBe('8px');
expect(
container.querySelector<HTMLDivElement>('div.ant-space')?.style[
'row-gap' as keyof CSSStyleDeclaration
],
).toBe('8px');
expect(container.querySelector<HTMLDivElement>('div.ant-space')).toHaveClass(
'ant-space-gap-row-small',
);
expect(container.querySelector<HTMLDivElement>('div.ant-space')).toHaveClass(
'ant-space-gap-col-small',
);
});

it('should size work', () => {
const { container } = render(
<Space size={10}>
<span>test</span>
</Space>,
);
const element = container.querySelector<HTMLDivElement>('div.ant-space');
expect(element).toHaveStyle({ rowGap: '10px', columnGap: '10px' });
});

it('should NaN work', () => {
expect(() => {
render(
<Space size={[NaN, NaN]}>
<span>test</span>
</Space>,
);
}).not.toThrow();
});
});
58 changes: 16 additions & 42 deletions components/space/__tests__/index.test.tsx
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
/* eslint-disable no-console */
import React, { useState } from 'react';

import Space from '..';
import mountTest from '../../../tests/shared/mountTest';
import rtlTest from '../../../tests/shared/rtlTest';
Expand Down Expand Up @@ -66,25 +67,9 @@ describe('Space', () => {
</Space>,
);

expect(container.querySelector<HTMLDivElement>('div.ant-space-item')?.style.marginRight).toBe(
'10px',
);
expect(
container.querySelectorAll<HTMLDivElement>('div.ant-space-item')[1]?.style.marginRight,
).toBe('');
});

it('should render width size 0', () => {
const { container } = render(
<Space size={NaN}>
<span>1</span>
<span>2</span>
</Space>,
);

expect(container.querySelector<HTMLDivElement>('div.ant-space-item')?.style.marginRight).toBe(
'0px',
);
const items = container.querySelectorAll<HTMLDivElement>('div.ant-space-item');
expect(items[0]?.style.marginRight).toBe('10px');
expect(items[1]?.style.marginRight).toBe('');
});

it('should render vertical space width customize size', () => {
Expand All @@ -95,12 +80,9 @@ describe('Space', () => {
</Space>,
);

expect(container.querySelector<HTMLDivElement>('div.ant-space-item')?.style.marginBottom).toBe(
'10px',
);
expect(
container.querySelectorAll<HTMLDivElement>('div.ant-space-item')[1]?.style.marginBottom,
).toBe('');
const items = container.querySelectorAll<HTMLDivElement>('div.ant-space-item');
expect(items[0]?.style.marginBottom).toBe('10px');
expect(items[1]?.style.marginBottom).toBe('');
});

it('should render correct with children', () => {
Expand Down Expand Up @@ -199,16 +181,15 @@ describe('Space', () => {
});

it('should render the hidden empty item wrapper', () => {
const Null = () => null;
const Null: React.FC = () => null;
const { container } = render(
<Space>
<Null />
</Space>,
);
const item = container.querySelector('div.ant-space-item') as HTMLElement;

expect(item).toBeEmptyDOMElement();
expect(getComputedStyle(item).display).toBe('none');
const element = container.querySelector<HTMLDivElement>('div.ant-space-item')!;
expect(element).toBeEmptyDOMElement();
expect(getComputedStyle(element).display).toBe('none');
});

it('should ref work', () => {
Expand All @@ -231,25 +212,18 @@ describe('Space', () => {
</Space>,
);

expect(container.querySelector('.ant-space-item.test-classNames')).toBeTruthy();
expect(container.querySelector<HTMLDivElement>('.ant-space-item.test-classNames')).toBeTruthy();
});

it('should styles work', () => {
const { container } = render(
<Space
styles={{
item: {
color: 'red',
},
}}
>
<Space styles={{ item: { color: 'red' } }}>
<span>Text1</span>
<span>Text2</span>
</Space>,
);

expect(container.querySelector('.ant-space-item')?.getAttribute('style')).toEqual(
'margin-right: 8px; color: red;',
);
expect(
container.querySelector<HTMLDivElement>('.ant-space-item')?.getAttribute('style'),
).toEqual('margin-right: 8px; color: red;');
});
});
9 changes: 8 additions & 1 deletion components/space/context.ts
Original file line number Diff line number Diff line change
@@ -1,6 +1,13 @@
import React from 'react';

export const SpaceContext = React.createContext({
export interface SpaceContextType {
latestIndex: number;
horizontalSize: number;
verticalSize: number;
supportFlexGap: boolean;
}

export const SpaceContext = React.createContext<SpaceContextType>({
latestIndex: 0,
horizontalSize: 0,
verticalSize: 0,
Expand Down
2 changes: 1 addition & 1 deletion components/space/demo/base.tsx
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
import { UploadOutlined } from '@ant-design/icons';
import React from 'react';
import { UploadOutlined } from '@ant-design/icons';
import { Button, Popconfirm, Space, Upload } from 'antd';

const App: React.FC = () => (
Expand Down
70 changes: 36 additions & 34 deletions components/space/index.tsx
Original file line number Diff line number Diff line change
@@ -1,16 +1,19 @@
'use client';

import * as React from 'react';
import classNames from 'classnames';
import toArray from 'rc-util/lib/Children/toArray';
import * as React from 'react';

import useFlexGapSupport from '../_util/hooks/useFlexGapSupport';
import { ConfigContext } from '../config-provider';
import type { SizeType } from '../config-provider/SizeContext';
import { useToken } from '../theme/internal';
import Compact from './Compact';
import Item from './Item';

import { SpaceContextProvider } from './context';
import type { SpaceContextType } from './context';
import Item from './Item';
import useStyle from './style';
import { getRealSize, isPresetSize } from './utils';

export { SpaceContext } from './context';

Expand All @@ -31,16 +34,6 @@ export interface SpaceProps extends React.HTMLAttributes<HTMLDivElement> {
styles?: { item: React.CSSProperties };
}

const spaceSize = {
small: 8,
middle: 16,
large: 24,
};

function getNumberSize(size: SpaceSize) {
return typeof size === 'string' ? spaceSize[size] : size || 0;
}

const Space = React.forwardRef<HTMLDivElement, SpaceProps>((props, ref) => {
const { getPrefixCls, space, direction: directionConfig } = React.useContext(ConfigContext);

Expand All @@ -60,30 +53,38 @@ const Space = React.forwardRef<HTMLDivElement, SpaceProps>((props, ref) => {
...otherProps
} = props;

const supportFlexGap = useFlexGapSupport();
const [, token] = useToken();

const [horizontalSize, verticalSize] = React.useMemo(
() =>
((Array.isArray(size) ? size : [size, size]) as [SpaceSize, SpaceSize]).map((item) =>
getNumberSize(item),
),
[size],
);
const spaceSizeMap = {
small: token.paddingXS,
middle: token.padding,
large: token.paddingLG,
} as const;

const [horizontalSize, verticalSize] = Array.isArray(size) ? size : ([size, size] as const);

const realHorizontalSize = getRealSize(spaceSizeMap, horizontalSize);

const realVerticalSize = getRealSize(spaceSizeMap, verticalSize);

const childNodes = toArray(children, { keepEmpty: true });

const supportFlexGap = useFlexGapSupport();

const mergedAlign = align === undefined && direction === 'horizontal' ? 'center' : align;
const prefixCls = getPrefixCls('space', customizePrefixCls);
const [wrapSSR, hashId] = useStyle(prefixCls);

const cn = classNames(
const cls = classNames(
prefixCls,
space?.className,
hashId,
`${prefixCls}-${direction}`,
{
[`${prefixCls}-rtl`]: directionConfig === 'rtl',
[`${prefixCls}-align-${mergedAlign}`]: mergedAlign,
[`${prefixCls}-gap-row-${verticalSize}`]: supportFlexGap && isPresetSize(verticalSize),
[`${prefixCls}-gap-col-${horizontalSize}`]: supportFlexGap && isPresetSize(horizontalSize),
},
className,
rootClassName,
Expand All @@ -98,7 +99,7 @@ const Space = React.forwardRef<HTMLDivElement, SpaceProps>((props, ref) => {

// Calculate latest one
let latestIndex = 0;
const nodes = childNodes.map((child, i) => {
const nodes = childNodes.map<React.ReactNode>((child, i) => {
if (child !== null && child !== undefined) {
latestIndex = i;
}
Expand All @@ -121,8 +122,13 @@ const Space = React.forwardRef<HTMLDivElement, SpaceProps>((props, ref) => {
);
});

const spaceContext = React.useMemo(
() => ({ horizontalSize, verticalSize, latestIndex, supportFlexGap }),
const spaceContext = React.useMemo<SpaceContextType>(
() => ({
horizontalSize: realHorizontalSize,
verticalSize: realVerticalSize,
latestIndex,
supportFlexGap,
}),
[horizontalSize, verticalSize, latestIndex, supportFlexGap],
);

Expand All @@ -138,24 +144,20 @@ const Space = React.forwardRef<HTMLDivElement, SpaceProps>((props, ref) => {

// Patch for gap not support
if (!supportFlexGap) {
gapStyle.marginBottom = -verticalSize;
gapStyle.marginBottom = -realVerticalSize;
}
}

if (supportFlexGap) {
gapStyle.columnGap = horizontalSize;
gapStyle.rowGap = verticalSize;
gapStyle.columnGap = realHorizontalSize;
gapStyle.rowGap = realVerticalSize;
}

return wrapSSR(
<div
ref={ref}
className={cn}
style={{
...gapStyle,
...space?.style,
...style,
}}
className={cls}
style={{ ...gapStyle, ...space?.style, ...style }}
{...otherProps}
>
<SpaceContextProvider value={spaceContext}>{nodes}</SpaceContextProvider>
Expand Down
1 change: 1 addition & 0 deletions components/space/style/compact.tsx
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
import type { FullToken, GenerateStyle } from '../../theme/internal';

/** Component only token. Which will handle additional calculation of alias token */
export interface ComponentToken {
// Component token here
Expand Down
Loading

0 comments on commit 4c91896

Please sign in to comment.