2022-12-21 14:16:41 +08:00
|
|
|
import React, { useState } from 'react';
|
|
|
|
import { act } from 'react-dom/test-utils';
|
2023-09-05 10:17:56 +08:00
|
|
|
|
2022-08-16 10:14:41 +08:00
|
|
|
import { Col, Row } from '..';
|
|
|
|
import mountTest from '../../../tests/shared/mountTest';
|
|
|
|
import rtlTest from '../../../tests/shared/rtlTest';
|
2023-04-06 19:43:32 +08:00
|
|
|
import { fireEvent, render } from '../../../tests/utils';
|
2022-08-16 10:14:41 +08:00
|
|
|
import useBreakpoint from '../hooks/useBreakpoint';
|
2022-12-15 14:14:07 +08:00
|
|
|
|
|
|
|
// Mock for `responsiveObserve` to test `unsubscribe` call
|
2023-06-07 21:59:21 +08:00
|
|
|
jest.mock('../../_util/responsiveObserver', () => {
|
|
|
|
const modules = jest.requireActual('../../_util/responsiveObserver');
|
2022-12-15 14:14:07 +08:00
|
|
|
const originHook = modules.default;
|
|
|
|
|
2023-06-07 21:59:21 +08:00
|
|
|
const useMockResponsiveObserver = (...args: any[]) => {
|
|
|
|
const entity = originHook(...args);
|
|
|
|
if (!entity.unsubscribe.mocked) {
|
2022-12-15 14:14:07 +08:00
|
|
|
const originUnsubscribe = entity.unsubscribe;
|
|
|
|
entity.unsubscribe = (...uArgs: any[]) => {
|
|
|
|
const inst = global as any;
|
|
|
|
inst.unsubscribeCnt = (inst.unsubscribeCnt || 0) + 1;
|
|
|
|
|
|
|
|
originUnsubscribe.call(entity, ...uArgs);
|
|
|
|
};
|
2023-06-07 21:59:21 +08:00
|
|
|
entity.unsubscribe.mocked = true;
|
2022-12-15 14:14:07 +08:00
|
|
|
}
|
|
|
|
|
|
|
|
return entity;
|
|
|
|
};
|
|
|
|
|
|
|
|
return {
|
|
|
|
...modules,
|
|
|
|
__esModule: true,
|
|
|
|
default: useMockResponsiveObserver,
|
|
|
|
};
|
|
|
|
});
|
2022-08-16 10:14:41 +08:00
|
|
|
|
|
|
|
describe('Grid', () => {
|
|
|
|
mountTest(Row);
|
|
|
|
mountTest(Col);
|
|
|
|
|
|
|
|
rtlTest(Row);
|
|
|
|
rtlTest(Col);
|
|
|
|
|
2022-12-15 14:14:07 +08:00
|
|
|
beforeEach(() => {
|
|
|
|
(global as any).unsubscribeCnt = 0;
|
2022-08-16 10:14:41 +08:00
|
|
|
});
|
|
|
|
|
|
|
|
it('should render Col', () => {
|
|
|
|
const { asFragment } = render(<Col span={2} />);
|
|
|
|
expect(asFragment().firstChild).toMatchSnapshot();
|
|
|
|
});
|
|
|
|
|
|
|
|
it('should render Row', () => {
|
|
|
|
const { asFragment } = render(<Row />);
|
|
|
|
expect(asFragment().firstChild).toMatchSnapshot();
|
|
|
|
});
|
|
|
|
|
|
|
|
it('when typeof gutter is object', () => {
|
|
|
|
const { container } = render(<Row gutter={{ xs: 8, sm: 16, md: 24 }} />);
|
|
|
|
expect(container.querySelector('div')!.style.marginLeft).toEqual('-4px');
|
|
|
|
expect(container.querySelector('div')!.style.marginRight).toEqual('-4px');
|
|
|
|
});
|
|
|
|
|
|
|
|
it('when typeof gutter is object array', () => {
|
|
|
|
const { container } = render(
|
|
|
|
<Row
|
|
|
|
gutter={[
|
|
|
|
{ xs: 8, sm: 16, md: 24, lg: 32, xl: 40 },
|
|
|
|
{ xs: 8, sm: 16, md: 24, lg: 32, xl: 40 },
|
|
|
|
]}
|
|
|
|
/>,
|
|
|
|
);
|
|
|
|
expect(container.querySelector('div')!.style.marginLeft).toEqual('-4px');
|
|
|
|
expect(container.querySelector('div')!.style.marginRight).toEqual('-4px');
|
|
|
|
});
|
|
|
|
|
|
|
|
it('when typeof gutter is object array in large screen', () => {
|
2023-06-07 21:59:21 +08:00
|
|
|
jest.spyOn(window, 'matchMedia').mockImplementation(
|
2022-11-19 13:47:33 +08:00
|
|
|
(query) =>
|
2022-08-16 10:14:41 +08:00
|
|
|
({
|
|
|
|
addListener: (cb: (e: { matches: boolean }) => void) => {
|
|
|
|
cb({ matches: query === '(min-width: 1200px)' });
|
|
|
|
},
|
2023-06-07 21:59:21 +08:00
|
|
|
removeListener: jest.fn(),
|
2022-08-16 10:14:41 +08:00
|
|
|
matches: query === '(min-width: 1200px)',
|
2023-09-05 10:17:56 +08:00
|
|
|
}) as any,
|
2022-08-16 10:14:41 +08:00
|
|
|
);
|
|
|
|
|
|
|
|
const { container, asFragment } = render(
|
|
|
|
<Row
|
|
|
|
gutter={[
|
|
|
|
{ xs: 8, sm: 16, md: 24, lg: 32, xl: 40 },
|
|
|
|
{ xs: 8, sm: 16, md: 24, lg: 100, xl: 400 },
|
|
|
|
]}
|
|
|
|
/>,
|
|
|
|
);
|
|
|
|
expect(asFragment().firstChild).toMatchSnapshot();
|
|
|
|
|
2023-09-05 10:17:56 +08:00
|
|
|
expect(container.querySelector('div')?.style.marginLeft).toBe('-20px');
|
|
|
|
expect(container.querySelector('div')?.style.marginRight).toBe('-20px');
|
|
|
|
expect(container.querySelector('div')?.style.marginTop).toBe('');
|
|
|
|
expect(container.querySelector('div')?.style.marginBottom).toBe('');
|
2022-08-16 10:14:41 +08:00
|
|
|
});
|
|
|
|
|
|
|
|
it('renders wrapped Col correctly', () => {
|
|
|
|
const MyCol = () => <Col span={12} />;
|
|
|
|
const { asFragment } = render(
|
|
|
|
<Row gutter={20}>
|
|
|
|
<div>
|
|
|
|
<Col span={12} />
|
|
|
|
</div>
|
|
|
|
<MyCol />
|
|
|
|
</Row>,
|
|
|
|
);
|
|
|
|
|
|
|
|
expect(asFragment().firstChild).toMatchSnapshot();
|
|
|
|
});
|
|
|
|
|
2022-12-22 10:11:08 +08:00
|
|
|
it('useResponsiveObserver.unsubscribe should be called when unmounted', () => {
|
2022-08-16 10:14:41 +08:00
|
|
|
const { unmount } = render(<Row gutter={{ xs: 20 }} />);
|
2022-12-15 14:14:07 +08:00
|
|
|
const called: number = (global as any).unsubscribeCnt;
|
|
|
|
|
|
|
|
unmount();
|
|
|
|
expect((global as any).unsubscribeCnt).toEqual(called + 1);
|
2022-08-16 10:14:41 +08:00
|
|
|
});
|
|
|
|
|
|
|
|
it('should work correct when gutter is object', () => {
|
|
|
|
const { container } = render(<Row gutter={{ xs: 20 }} />);
|
|
|
|
expect(container.querySelector('div')!.style.marginLeft).toEqual('-10px');
|
|
|
|
expect(container.querySelector('div')!.style.marginRight).toEqual('-10px');
|
|
|
|
});
|
|
|
|
|
|
|
|
it('should work current when gutter is array', () => {
|
|
|
|
const { container } = render(<Row gutter={[16, 20]} />);
|
2023-09-05 10:17:56 +08:00
|
|
|
expect(container.querySelector('div')?.style.marginLeft).toBe('-8px');
|
|
|
|
expect(container.querySelector('div')?.style.marginRight).toBe('-8px');
|
|
|
|
expect(container.querySelector('div')?.style.marginTop).toBe('');
|
|
|
|
expect(container.querySelector('div')?.style.marginBottom).toBe('');
|
2022-08-16 10:14:41 +08:00
|
|
|
});
|
|
|
|
|
|
|
|
// By jsdom mock, actual jsdom not implemented matchMedia
|
|
|
|
// https://jestjs.io/docs/en/manual-mocks#mocking-methods-which-are-not-implemented-in-jsdom
|
|
|
|
it('should work with useBreakpoint', () => {
|
2023-06-07 21:59:21 +08:00
|
|
|
const matchMediaSpy = jest.spyOn(window, 'matchMedia');
|
2022-08-16 10:14:41 +08:00
|
|
|
matchMediaSpy.mockImplementation(
|
2022-11-19 13:47:33 +08:00
|
|
|
(query) =>
|
2022-08-16 10:14:41 +08:00
|
|
|
({
|
|
|
|
addListener: (cb: (e: { matches: boolean }) => void) => {
|
|
|
|
cb({ matches: query === '(max-width: 575px)' });
|
|
|
|
},
|
2023-06-07 21:59:21 +08:00
|
|
|
removeListener: jest.fn(),
|
2022-08-16 10:14:41 +08:00
|
|
|
matches: query === '(max-width: 575px)',
|
2023-09-05 10:17:56 +08:00
|
|
|
}) as any,
|
2022-08-16 10:14:41 +08:00
|
|
|
);
|
|
|
|
|
|
|
|
let screensVar;
|
|
|
|
function Demo() {
|
|
|
|
const screens = useBreakpoint();
|
|
|
|
screensVar = screens;
|
|
|
|
return <div />;
|
|
|
|
}
|
|
|
|
render(<Demo />);
|
|
|
|
|
|
|
|
expect(screensVar).toEqual({
|
|
|
|
xs: true,
|
|
|
|
sm: false,
|
|
|
|
md: false,
|
|
|
|
lg: false,
|
|
|
|
xl: false,
|
|
|
|
xxl: false,
|
|
|
|
});
|
|
|
|
});
|
2022-10-12 23:52:29 +08:00
|
|
|
|
|
|
|
it('should align by responsive align prop', () => {
|
2023-06-07 21:59:21 +08:00
|
|
|
const matchMediaSpy = jest.spyOn(window, 'matchMedia');
|
2022-10-12 23:52:29 +08:00
|
|
|
matchMediaSpy.mockImplementation(
|
2022-11-19 13:47:33 +08:00
|
|
|
(query) =>
|
2022-10-12 23:52:29 +08:00
|
|
|
({
|
|
|
|
addListener: (cb: (e: { matches: boolean }) => void) => {
|
|
|
|
cb({ matches: query === '(max-width: 575px)' });
|
|
|
|
},
|
2023-06-07 21:59:21 +08:00
|
|
|
removeListener: jest.fn(),
|
2022-10-12 23:52:29 +08:00
|
|
|
matches: query === '(max-width: 575px)',
|
2023-09-05 10:17:56 +08:00
|
|
|
}) as any,
|
2022-10-12 23:52:29 +08:00
|
|
|
);
|
|
|
|
const { container } = render(<Row align="middle" />);
|
|
|
|
expect(container.innerHTML).toContain('ant-row-middle');
|
|
|
|
const { container: container2 } = render(<Row align={{ xs: 'middle' }} />);
|
|
|
|
expect(container2.innerHTML).toContain('ant-row-middle');
|
|
|
|
const { container: container3 } = render(<Row align={{ lg: 'middle' }} />);
|
|
|
|
expect(container3.innerHTML).not.toContain('ant-row-middle');
|
|
|
|
});
|
|
|
|
|
|
|
|
it('should justify by responsive justify prop', () => {
|
2023-06-07 21:59:21 +08:00
|
|
|
const matchMediaSpy = jest.spyOn(window, 'matchMedia');
|
2022-10-12 23:52:29 +08:00
|
|
|
matchMediaSpy.mockImplementation(
|
2022-11-19 13:47:33 +08:00
|
|
|
(query) =>
|
2022-10-12 23:52:29 +08:00
|
|
|
({
|
|
|
|
addListener: (cb: (e: { matches: boolean }) => void) => {
|
|
|
|
cb({ matches: query === '(max-width: 575px)' });
|
|
|
|
},
|
2023-06-07 21:59:21 +08:00
|
|
|
removeListener: jest.fn(),
|
2022-10-12 23:52:29 +08:00
|
|
|
matches: query === '(max-width: 575px)',
|
2023-09-05 10:17:56 +08:00
|
|
|
}) as any,
|
2022-10-12 23:52:29 +08:00
|
|
|
);
|
|
|
|
const { container } = render(<Row justify="center" />);
|
|
|
|
expect(container.innerHTML).toContain('ant-row-center');
|
|
|
|
const { container: container2 } = render(<Row justify={{ xs: 'center' }} />);
|
|
|
|
expect(container2.innerHTML).toContain('ant-row-center');
|
|
|
|
const { container: container3 } = render(<Row justify={{ lg: 'center' }} />);
|
|
|
|
expect(container3.innerHTML).not.toContain('ant-row-center');
|
|
|
|
});
|
2022-12-21 14:16:41 +08:00
|
|
|
|
|
|
|
// https://github.com/ant-design/ant-design/issues/39690
|
|
|
|
it('Justify and align properties should reactive for Row', () => {
|
|
|
|
const ReactiveTest = () => {
|
|
|
|
const [justify, setjustify] = useState<any>('start');
|
|
|
|
return (
|
|
|
|
<>
|
|
|
|
<Row justify={justify} align="bottom">
|
|
|
|
<div>button1</div>
|
|
|
|
<div>button</div>
|
|
|
|
</Row>
|
|
|
|
<span onClick={() => setjustify('end')} />
|
|
|
|
</>
|
|
|
|
);
|
|
|
|
};
|
|
|
|
const { container } = render(<ReactiveTest />);
|
|
|
|
expect(container.innerHTML).toContain('ant-row-start');
|
|
|
|
act(() => {
|
|
|
|
fireEvent.click(container.querySelector('span')!);
|
|
|
|
});
|
|
|
|
expect(container.innerHTML).toContain('ant-row-end');
|
|
|
|
});
|
2023-04-06 19:43:32 +08:00
|
|
|
|
|
|
|
it('The column spacing should be evenly spaced', () => {
|
|
|
|
const { container } = render(
|
|
|
|
<Row justify="space-evenly">
|
|
|
|
<Col span={4}>col-1</Col>
|
|
|
|
<Col span={4}>col-2</Col>
|
|
|
|
</Row>,
|
|
|
|
);
|
|
|
|
|
|
|
|
const row = container.querySelector('.ant-row-space-evenly');
|
|
|
|
expect(row).toBeTruthy();
|
|
|
|
expect(row && getComputedStyle(row).justifyContent).toEqual('space-evenly');
|
|
|
|
});
|
2022-08-16 10:14:41 +08:00
|
|
|
});
|