mirror of
https://github.com/ant-design/ant-design.git
synced 2024-12-13 15:49:10 +08:00
fix: Popover display empty div when title and content is null (#42229)
* fix: Popover display empty div when title and content is null (#42217)
* fix: Popover display empty div when title and content is null
* test: Popover add test
* lint: remove useless block statement
---------
Co-authored-by: MaHui <mahuiyoung@cmbchina.com>
(cherry picked from commit 4271ff0976
)
* lint: fix Popover test lint error
* lint: fix Popover test lint error
* improvement: Popover overlay
* lint: fix Popover test lint error
* Update package.json
---------
Co-authored-by: MaHui <mahuiyoung@cmbchina.com>
Co-authored-by: afc163 <afc163@gmail.com>
This commit is contained in:
parent
0371a933bf
commit
19f8505d0c
@ -8,38 +8,34 @@ describe('Popover', () => {
|
|||||||
mountTest(Popover);
|
mountTest(Popover);
|
||||||
|
|
||||||
it('should show overlay when trigger is clicked', () => {
|
it('should show overlay when trigger is clicked', () => {
|
||||||
const ref = React.createRef<any>();
|
|
||||||
|
|
||||||
const popover = render(
|
const popover = render(
|
||||||
<Popover ref={ref} content="console.log('hello world')" title="code" trigger="click">
|
<Popover content="console.log('hello world')" title="code" trigger="click">
|
||||||
<span>show me your code</span>
|
<span>show me your code</span>
|
||||||
</Popover>,
|
</Popover>,
|
||||||
);
|
);
|
||||||
|
expect(document.querySelector('.ant-popover')).toBe(null);
|
||||||
expect(ref.current.getPopupDomNode()).toBe(null);
|
|
||||||
expect(popover.container.querySelector('.ant-popover-inner-content')).toBeFalsy();
|
|
||||||
fireEvent.click(popover.container.querySelector('span')!);
|
fireEvent.click(popover.container.querySelector('span')!);
|
||||||
expect(popover.container.querySelector('.ant-popover-inner-content')).toBeTruthy();
|
const popup = document.querySelector('.ant-popover');
|
||||||
|
expect(popup?.querySelector?.('.ant-popover-inner-content')).toBeTruthy();
|
||||||
});
|
});
|
||||||
|
|
||||||
it('shows content for render functions', () => {
|
it('shows content for render functions', () => {
|
||||||
const renderTitle = () => 'some-title';
|
const renderTitle = () => 'some-title';
|
||||||
const renderContent = () => 'some-content';
|
const renderContent = () => 'some-content';
|
||||||
const ref = React.createRef<any>();
|
|
||||||
|
|
||||||
const popover = render(
|
const popover = render(
|
||||||
<Popover ref={ref} content={renderContent} title={renderTitle} trigger="click">
|
<Popover content={renderContent} title={renderTitle} trigger="click">
|
||||||
<span>show me your code </span>
|
<span>show me your code </span>
|
||||||
</Popover>,
|
</Popover>,
|
||||||
);
|
);
|
||||||
|
|
||||||
fireEvent.click(popover.container.querySelector('span')!);
|
fireEvent.click(popover.container.querySelector('span')!);
|
||||||
|
|
||||||
const popup = ref.current.getPopupDomNode();
|
const popup = document.querySelector('.ant-popover');
|
||||||
expect(popup).not.toBe(null);
|
expect(popup).not.toBe(null);
|
||||||
expect(popup.innerHTML).toContain('some-title');
|
expect(popup?.innerHTML).toContain('some-title');
|
||||||
expect(popup.innerHTML).toContain('some-content');
|
expect(popup?.innerHTML).toContain('some-content');
|
||||||
expect(popup.innerHTML).toMatchSnapshot();
|
expect(popup?.innerHTML).toMatchSnapshot();
|
||||||
});
|
});
|
||||||
|
|
||||||
it('handles empty title/content props safely', () => {
|
it('handles empty title/content props safely', () => {
|
||||||
@ -50,8 +46,8 @@ describe('Popover', () => {
|
|||||||
);
|
);
|
||||||
fireEvent.click(container.querySelector('span')!);
|
fireEvent.click(container.querySelector('span')!);
|
||||||
|
|
||||||
expect(container.querySelector('.ant-popover-title')?.textContent).toBeFalsy();
|
const popup = document.querySelector('.ant-popover');
|
||||||
expect(container.querySelector('.ant-popover-inner-content')?.textContent).toBeFalsy();
|
expect(popup).toBe(null);
|
||||||
});
|
});
|
||||||
|
|
||||||
it('should not render popover when the title & content props is empty', () => {
|
it('should not render popover when the title & content props is empty', () => {
|
||||||
@ -62,8 +58,8 @@ describe('Popover', () => {
|
|||||||
);
|
);
|
||||||
fireEvent.click(container.querySelector('span')!);
|
fireEvent.click(container.querySelector('span')!);
|
||||||
|
|
||||||
expect(container.querySelector('.ant-popover-title')?.textContent).toBeFalsy();
|
const popup = document.querySelector('.ant-popover');
|
||||||
expect(container.querySelector('.ant-popover-inner-content')?.textContent).toBeFalsy();
|
expect(popup).toBe(null);
|
||||||
});
|
});
|
||||||
|
|
||||||
it('props#overlay do not warn anymore', () => {
|
it('props#overlay do not warn anymore', () => {
|
||||||
|
@ -1,10 +1,10 @@
|
|||||||
import * as React from 'react';
|
import * as React from 'react';
|
||||||
import { ConfigContext } from '../config-provider';
|
|
||||||
import type { AbstractTooltipProps } from '../tooltip';
|
|
||||||
import Tooltip from '../tooltip';
|
|
||||||
import type { RenderFunction } from '../_util/getRenderPropValue';
|
import type { RenderFunction } from '../_util/getRenderPropValue';
|
||||||
import { getRenderPropValue } from '../_util/getRenderPropValue';
|
import { getRenderPropValue } from '../_util/getRenderPropValue';
|
||||||
import { getTransitionName } from '../_util/motion';
|
import { getTransitionName } from '../_util/motion';
|
||||||
|
import { ConfigContext } from '../config-provider';
|
||||||
|
import type { AbstractTooltipProps } from '../tooltip';
|
||||||
|
import Tooltip from '../tooltip';
|
||||||
|
|
||||||
export interface PopoverProps extends AbstractTooltipProps {
|
export interface PopoverProps extends AbstractTooltipProps {
|
||||||
title?: React.ReactNode | RenderFunction;
|
title?: React.ReactNode | RenderFunction;
|
||||||
@ -19,17 +19,12 @@ interface OverlayPorps {
|
|||||||
content?: PopoverProps['content'];
|
content?: PopoverProps['content'];
|
||||||
}
|
}
|
||||||
|
|
||||||
const Overlay: React.FC<OverlayPorps> = ({ title, content, prefixCls }) => {
|
const Overlay: React.FC<OverlayPorps> = ({ title, content, prefixCls }) => (
|
||||||
if (!title && !content) {
|
<>
|
||||||
return null;
|
{title && <div className={`${prefixCls}-title`}>{getRenderPropValue(title)}</div>}
|
||||||
}
|
<div className={`${prefixCls}-inner-content`}>{getRenderPropValue(content)}</div>
|
||||||
return (
|
</>
|
||||||
<>
|
);
|
||||||
{title && <div className={`${prefixCls}-title`}>{getRenderPropValue(title)}</div>}
|
|
||||||
<div className={`${prefixCls}-inner-content`}>{getRenderPropValue(content)}</div>
|
|
||||||
</>
|
|
||||||
);
|
|
||||||
};
|
|
||||||
|
|
||||||
const Popover = React.forwardRef<unknown, PopoverProps>((props, ref) => {
|
const Popover = React.forwardRef<unknown, PopoverProps>((props, ref) => {
|
||||||
const {
|
const {
|
||||||
@ -49,6 +44,16 @@ const Popover = React.forwardRef<unknown, PopoverProps>((props, ref) => {
|
|||||||
const prefixCls = getPrefixCls('popover', customizePrefixCls);
|
const prefixCls = getPrefixCls('popover', customizePrefixCls);
|
||||||
const rootPrefixCls = getPrefixCls();
|
const rootPrefixCls = getPrefixCls();
|
||||||
|
|
||||||
|
const mergedOverlay = React.useMemo<React.ReactNode>(() => {
|
||||||
|
if (_overlay) {
|
||||||
|
return _overlay;
|
||||||
|
}
|
||||||
|
if (!title && !content) {
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
return <Overlay prefixCls={prefixCls} title={title} content={content} />;
|
||||||
|
}, [_overlay, title, content, prefixCls]);
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<Tooltip
|
<Tooltip
|
||||||
placement={placement}
|
placement={placement}
|
||||||
@ -59,7 +64,7 @@ const Popover = React.forwardRef<unknown, PopoverProps>((props, ref) => {
|
|||||||
{...otherProps}
|
{...otherProps}
|
||||||
prefixCls={prefixCls}
|
prefixCls={prefixCls}
|
||||||
ref={ref}
|
ref={ref}
|
||||||
overlay={_overlay || <Overlay prefixCls={prefixCls} title={title} content={content} />}
|
overlay={mergedOverlay}
|
||||||
transitionName={getTransitionName(rootPrefixCls, 'zoom-big', otherProps.transitionName)}
|
transitionName={getTransitionName(rootPrefixCls, 'zoom-big', otherProps.transitionName)}
|
||||||
/>
|
/>
|
||||||
);
|
);
|
||||||
|
@ -223,7 +223,7 @@
|
|||||||
"eslint-plugin-markdown": "^3.0.0",
|
"eslint-plugin-markdown": "^3.0.0",
|
||||||
"eslint-plugin-react": "^7.31.8",
|
"eslint-plugin-react": "^7.31.8",
|
||||||
"eslint-plugin-react-hooks": "^4.1.2",
|
"eslint-plugin-react-hooks": "^4.1.2",
|
||||||
"eslint-plugin-unicorn": "^44.0.0",
|
"eslint-plugin-unicorn": "^47.0.0",
|
||||||
"fast-glob": "^3.2.11",
|
"fast-glob": "^3.2.11",
|
||||||
"fetch-jsonp": "^1.1.3",
|
"fetch-jsonp": "^1.1.3",
|
||||||
"fs-extra": "^10.0.0",
|
"fs-extra": "^10.0.0",
|
||||||
|
Loading…
Reference in New Issue
Block a user