feat: update tooltip

pull/2386/head
tanjinzhou 2020-06-09 18:30:18 +08:00
parent 24ef11afb9
commit 69a53b303d
8 changed files with 150 additions and 183 deletions

View File

@ -1,14 +1,14 @@
import { cloneElement } from '../_util/vnode'; import { inject, cloneVNode, isVNode } from 'vue';
import VcTooltip from '../vc-tooltip'; import VcTooltip from '../vc-tooltip';
import getPlacements from './placements'; import getPlacements from './placements';
import PropTypes from '../_util/vue-types'; import PropTypes from '../_util/vue-types';
import { import {
hasProp, hasProp,
getComponentFromProp, getComponent,
getClass, getClass,
getStyle, getStyle,
isValidElement, filterEmpty,
getListeners, getSlot,
} from '../_util/props-util'; } from '../_util/props-util';
import { ConfigConsumerProps } from '../config-provider'; import { ConfigConsumerProps } from '../config-provider';
import abstractTooltipProps from './abstractTooltipProps'; import abstractTooltipProps from './abstractTooltipProps';
@ -35,8 +35,10 @@ export default {
...props, ...props,
title: PropTypes.any, title: PropTypes.any,
}, },
inject: { setup() {
configProvider: { default: () => ConfigConsumerProps }, return {
configProvider: inject('configProvider', ConfigConsumerProps),
};
}, },
data() { data() {
return { return {
@ -107,14 +109,14 @@ export default {
display: 'inline-block', // default inline-block is important display: 'inline-block', // default inline-block is important
...picked, ...picked,
cursor: 'not-allowed', cursor: 'not-allowed',
width: ele.componentOptions.propsData.block ? '100%' : null, width: ele.props && ele.props.block ? '100%' : null,
}; };
const buttonStyle = { const buttonStyle = {
...omitted, ...omitted,
pointerEvents: 'none', pointerEvents: 'none',
}; };
const spanCls = getClass(ele); const spanCls = getClass(ele);
const child = cloneElement(ele, { const child = cloneVNode(ele, {
style: buttonStyle, style: buttonStyle,
class: null, class: null,
}); });
@ -128,12 +130,12 @@ export default {
}, },
isNoTitle() { isNoTitle() {
const title = getComponentFromProp(this, 'title'); const title = getComponent(this, 'title');
return !title && title !== 0; return !title && title !== 0;
}, },
getOverlay() { getOverlay() {
const title = getComponentFromProp(this, 'title'); const title = getComponent(this, 'title');
if (title === 0) { if (title === 0) {
return title; return title;
} }
@ -173,12 +175,12 @@ export default {
}, },
render() { render() {
const { $props, $data, $slots } = this; const { $props, $data, $attrs } = this;
const { prefixCls: customizePrefixCls, openClassName, getPopupContainer } = $props; const { prefixCls: customizePrefixCls, openClassName, getPopupContainer } = $props;
const { getPopupContainer: getContextPopupContainer } = this.configProvider; const { getPopupContainer: getContextPopupContainer } = this.configProvider;
const getPrefixCls = this.configProvider.getPrefixCls; const getPrefixCls = this.configProvider.getPrefixCls;
const prefixCls = getPrefixCls('tooltip', customizePrefixCls); const prefixCls = getPrefixCls('tooltip', customizePrefixCls);
let children = ($slots.default || []).filter(c => c.tag || c.text.trim() !== ''); let children = filterEmpty(getSlot(this));
children = children.length === 1 ? children[0] : children; children = children.length === 1 ? children[0] : children;
let sVisible = $data.sVisible; let sVisible = $data.sVisible;
// Hide tooltip when there is no title // Hide tooltip when there is no title
@ -189,30 +191,26 @@ export default {
return null; return null;
} }
const child = this.getDisabledCompatibleChildren( const child = this.getDisabledCompatibleChildren(
isValidElement(children) ? children : <span>{children}</span>, isVNode(children) ? children : <span>{children}</span>,
); );
const childCls = { const childCls = {
[openClassName || `${prefixCls}-open`]: true, [openClassName || `${prefixCls}-open`]: true,
}; };
const tooltipProps = { const tooltipProps = {
props: { ...$attrs,
...$props, ...$props,
prefixCls, prefixCls,
getTooltipContainer: getPopupContainer || getContextPopupContainer, getTooltipContainer: getPopupContainer || getContextPopupContainer,
builtinPlacements: this.getPlacements(), builtinPlacements: this.getPlacements(),
overlay: this.getOverlay(), overlay: this.getOverlay(),
visible: sVisible, visible: sVisible,
},
ref: 'tooltip', ref: 'tooltip',
on: { onVisibleChange: this.onVisibleChange,
...getListeners(this), onPopupAlign: this.onPopupAlign,
visibleChange: this.onVisibleChange,
popupAlign: this.onPopupAlign,
},
}; };
return ( return (
<VcTooltip {...tooltipProps}> <VcTooltip {...tooltipProps}>
{sVisible ? cloneElement(child, { class: childCls }) : child} {sVisible ? cloneVNode(child, { class: childCls }) : child}
</VcTooltip> </VcTooltip>
); );
}, },

View File

@ -1,10 +1,8 @@
import ToolTip from './Tooltip'; import ToolTip from './Tooltip';
import Base from '../base';
/* istanbul ignore next */ /* istanbul ignore next */
ToolTip.install = function(Vue) { ToolTip.install = function(app) {
Vue.use(Base); app.component(ToolTip.name, ToolTip);
Vue.component(ToolTip.name, ToolTip);
}; };
export default ToolTip; export default ToolTip;

View File

@ -2,7 +2,7 @@ import PropTypes from '../_util/vue-types';
import Trigger from '../vc-trigger'; import Trigger from '../vc-trigger';
import { placements } from './placements'; import { placements } from './placements';
import Content from './Content'; import Content from './Content';
import { hasProp, getComponentFromProp, getOptionProps, getListeners } from '../_util/props-util'; import { hasProp, getComponent, getOptionProps } from '../_util/props-util';
function noop() {} function noop() {}
export default { export default {
props: { props: {
@ -31,14 +31,14 @@ export default {
const { prefixCls, tipId } = this.$props; const { prefixCls, tipId } = this.$props;
return [ return [
<div class={`${prefixCls}-arrow`} key="arrow"> <div class={`${prefixCls}-arrow`} key="arrow">
{getComponentFromProp(this, 'arrowContent')} {getComponent(this, 'arrowContent')}
</div>, </div>,
<Content <Content
key="content" key="content"
trigger={this.$refs.trigger} trigger={this.$refs.trigger}
prefixCls={prefixCls} prefixCls={prefixCls}
id={tipId} id={tipId}
overlay={getComponentFromProp(this, 'overlay')} overlay={getComponent(this, 'overlay')}
/>, />,
]; ];
}, },
@ -69,9 +69,8 @@ export default {
if (hasProp(this, 'visible')) { if (hasProp(this, 'visible')) {
extraProps.popupVisible = this.$props.visible; extraProps.popupVisible = this.$props.visible;
} }
const listeners = getListeners(this); const { $attrs } = this;
const triggerProps = { const triggerProps = {
props: {
popupClassName: overlayClassName, popupClassName: overlayClassName,
prefixCls, prefixCls,
action: trigger, action: trigger,
@ -88,18 +87,15 @@ export default {
popupStyle: overlayStyle, popupStyle: overlayStyle,
mouseEnterDelay, mouseEnterDelay,
...extraProps, ...extraProps,
}, ...$attrs,
on: { onPopupVisibleChange: $attrs.onVisibleChange || noop,
...listeners, onPopupAlign: $attrs.onPopupAlign || noop,
popupVisibleChange: listeners.visibleChange || noop,
popupAlign: listeners.popupAlign || noop,
},
ref: 'trigger', ref: 'trigger',
}; };
return ( return (
<Trigger {...triggerProps}> <Trigger {...triggerProps}>
<template slot="popup">{this.getPopupElement(h)}</template> <template slot="popup">{this.getPopupElement()}</template>
{this.$slots.default} {this.$slots.default && this.$slots.default()}
</Trigger> </Trigger>
); );
}, },

View File

@ -7,16 +7,14 @@ export default {
}, },
render() { render() {
const { hiddenClassName, visible } = this.$props; const { hiddenClassName, visible } = this.$props;
let children = null; const child = this.$slots.default && this.$slots.default();
if (hiddenClassName || !this.$slots.default || this.$slots.default.length > 1) { if (hiddenClassName || (child && child.length > 1)) {
const cls = ''; const cls = '';
if (!visible && hiddenClassName) { if (!visible && hiddenClassName) {
// cls += ` ${hiddenClassName}` // cls += ` ${hiddenClassName}`
} }
children = <div class={cls}>{this.$slots.default}</div>; return <div class={cls}>{child}</div>;
} else {
children = this.$slots.default[0];
} }
return children; return child;
}, },
}; };

View File

@ -1,3 +1,4 @@
import { Transition } from 'vue';
import PropTypes from '../_util/vue-types'; import PropTypes from '../_util/vue-types';
import Align from '../vc-align'; import Align from '../vc-align';
import PopupInner from './PopupInner'; import PopupInner from './PopupInner';
@ -9,6 +10,7 @@ import { getListeners } from '../_util/props-util';
export default { export default {
name: 'VCTriggerPopup', name: 'VCTriggerPopup',
mixins: [BaseMixin], mixins: [BaseMixin],
inheritAttrs: false,
props: { props: {
visible: PropTypes.bool, visible: PropTypes.bool,
getClassNameFromAlign: PropTypes.func, getClassNameFromAlign: PropTypes.func,
@ -255,7 +257,7 @@ export default {
} }
if (destroyPopupOnHide) { if (destroyPopupOnHide) {
return ( return (
<transition {...transitionProps}> <Transition {...transitionProps}>
{visible ? ( {visible ? (
<Align <Align
target={this.getAlignTarget()} target={this.getAlignTarget()}
@ -268,11 +270,11 @@ export default {
<PopupInner {...popupInnerProps}>{$slots.default}</PopupInner> <PopupInner {...popupInnerProps}>{$slots.default}</PopupInner>
</Align> </Align>
) : null} ) : null}
</transition> </Transition>
); );
} }
return ( return (
<transition {...transitionProps}> <Transition {...transitionProps}>
<Align <Align
v-show={visible} v-show={visible}
target={this.getAlignTarget()} target={this.getAlignTarget()}
@ -285,7 +287,7 @@ export default {
> >
<PopupInner {...popupInnerProps}>{$slots.default}</PopupInner> <PopupInner {...popupInnerProps}>{$slots.default}</PopupInner>
</Align> </Align>
</transition> </Transition>
); );
}, },
@ -314,9 +316,9 @@ export default {
); );
if (maskTransition) { if (maskTransition) {
maskElement = ( maskElement = (
<transition appear name={maskTransition}> <Transition appear name={maskTransition}>
{maskElement} {maskElement}
</transition> </Transition>
); );
} }
} }

View File

@ -1,6 +1,5 @@
import PropTypes from '../_util/vue-types'; import PropTypes from '../_util/vue-types';
import LazyRenderBox from './LazyRenderBox'; import LazyRenderBox from './LazyRenderBox';
import { getListeners } from '../_util/props-util';
export default { export default {
props: { props: {
@ -10,14 +9,11 @@ export default {
}, },
render() { render() {
const { prefixCls, visible, hiddenClassName } = this.$props; const { prefixCls, visible, hiddenClassName } = this.$props;
const divProps = {
on: getListeners(this),
};
return ( return (
<div {...divProps} class={!visible ? hiddenClassName : ''}> <div class={!visible ? hiddenClassName : ''}>
<LazyRenderBox class={`${prefixCls}-content`} visible={visible}> <LazyRenderBox class={`${prefixCls}-content`} visible={visible}>
{this.$slots.default} {this.$slots.default && this.$slots.default()}
</LazyRenderBox> </LazyRenderBox>
</div> </div>
); );

View File

@ -1,12 +1,13 @@
import Vue from 'vue'; import { cloneVNode, inject, provide } from 'vue';
import ref from 'vue-ref'; import ref from 'vue-ref';
import PropTypes from '../_util/vue-types'; import PropTypes from '../_util/vue-types';
import contains from '../vc-util/Dom/contains'; import contains from '../vc-util/Dom/contains';
import { import {
hasProp, hasProp,
getComponentFromProp, getComponentFromProp,
getDataEvents, getEvents,
filterEmpty, filterEmpty,
getSlot,
getListeners, getListeners,
} from '../_util/props-util'; } from '../_util/props-util';
import { requestAnimationTimeout, cancelAnimationTimeout } from '../_util/requestAnimationTimeout'; import { requestAnimationTimeout, cancelAnimationTimeout } from '../_util/requestAnimationTimeout';
@ -15,10 +16,7 @@ import warning from '../_util/warning';
import Popup from './Popup'; import Popup from './Popup';
import { getAlignFromPlacement, getAlignPopupClassName, noop } from './utils'; import { getAlignFromPlacement, getAlignPopupClassName, noop } from './utils';
import BaseMixin from '../_util/BaseMixin'; import BaseMixin from '../_util/BaseMixin';
import { cloneElement } from '../_util/vnode'; import Portal from '../_util/Portal';
import ContainerRender from '../_util/ContainerRender';
Vue.use(ref, { name: 'ant-ref' });
function returnEmptyString() { function returnEmptyString() {
return ''; return '';
@ -40,7 +38,9 @@ const ALL_HANDLERS = [
export default { export default {
name: 'Trigger', name: 'Trigger',
directives: { 'ant-ref': ref },
mixins: [BaseMixin], mixins: [BaseMixin],
inheritAttrs: false,
props: { props: {
action: PropTypes.oneOfType([PropTypes.string, PropTypes.arrayOf(PropTypes.string)]).def([]), action: PropTypes.oneOfType([PropTypes.string, PropTypes.arrayOf(PropTypes.string)]).def([]),
showAction: PropTypes.any.def([]), showAction: PropTypes.any.def([]),
@ -76,16 +76,6 @@ export default {
stretch: PropTypes.string, stretch: PropTypes.string,
alignPoint: PropTypes.bool, // Maybe we can support user pass position in the future alignPoint: PropTypes.bool, // Maybe we can support user pass position in the future
}, },
provide() {
return {
vcTriggerContext: this,
};
},
inject: {
vcTriggerContext: { default: () => ({}) },
savePopupRef: { default: () => noop },
dialogContext: { default: () => null },
},
data() { data() {
const props = this.$props; const props = this.$props;
let popupVisible; let popupVisible;
@ -113,24 +103,26 @@ export default {
} }
}, },
}, },
created() {
provide('vcTriggerContext', this);
},
setup() {
return {
vcTriggerContext: inject('configProvider', {}),
savePopupRef: inject('vcTriggerContext', noop),
dialogContext: inject('dialogContext', null),
};
},
deactivated() { deactivated() {
this.setPopupVisible(false); this.setPopupVisible(false);
}, },
mounted() { mounted() {
this.$nextTick(() => { this.$nextTick(() => {
this.renderComponent(null);
this.updatedCal(); this.updatedCal();
}); });
}, },
updated() { updated() {
const triggerAfterPopupVisibleChange = () => {
if (this.sPopupVisible !== this.prevPopupVisible) {
this.afterPopupVisibleChange(this.sPopupVisible);
}
this.prevPopupVisible = this.sPopupVisible;
};
this.renderComponent(null, triggerAfterPopupVisibleChange);
this.$nextTick(() => { this.$nextTick(() => {
this.updatedCal(); this.updatedCal();
}); });
@ -425,14 +417,12 @@ export default {
align: getListeners(this).popupAlign || noop, align: getListeners(this).popupAlign || noop,
...mouseProps, ...mouseProps,
}, },
directives: [
{
name: 'ant-ref',
value: this.savePopup,
},
],
}; };
return <Popup {...popupProps}>{getComponentFromProp(self, 'popup')}</Popup>; return (
<Popup v-ant-ref={this.savePopup} {...popupProps}>
{getComponentFromProp(self, 'popup')}
</Popup>
);
}, },
getContainer() { getContainer() {
@ -453,7 +443,7 @@ export default {
}, },
setPopupVisible(sPopupVisible, event) { setPopupVisible(sPopupVisible, event) {
const { alignPoint, sPopupVisible: prevPopupVisible } = this; const { alignPoint, sPopupVisible: prevPopupVisible, $attrs } = this;
this.clearDelayTimer(); this.clearDelayTimer();
if (prevPopupVisible !== sPopupVisible) { if (prevPopupVisible !== sPopupVisible) {
if (!hasProp(this, 'popupVisible')) { if (!hasProp(this, 'popupVisible')) {
@ -462,8 +452,7 @@ export default {
prevPopupVisible, prevPopupVisible,
}); });
} }
const listeners = getListeners(this); $attrs.onPopupVisibleChange && $attrs.onPopupVisibleChange(sPopupVisible);
listeners.popupVisibleChange && listeners.popupVisibleChange(sPopupVisible);
} }
// Always record the point position since mouseEnterDelay will delay the show // Always record the point position since mouseEnterDelay will delay the show
if (alignPoint && event) { if (alignPoint && event) {
@ -482,7 +471,11 @@ export default {
}, },
}); });
}, },
handlePortalUpdate() {
if (this.prevPopupVisible !== this.sPopupVisible) {
this.afterPopupVisibleChange(this.sPopupVisible);
}
},
delaySetPopupVisible(visible, delayS, event) { delaySetPopupVisible(visible, delayS, event) {
const delay = delayS * 1000; const delay = delayS * 1000;
this.clearDelayTimer(); this.clearDelayTimer();
@ -587,77 +580,74 @@ export default {
}, },
}, },
render() { render() {
const { sPopupVisible } = this; const { sPopupVisible, $attrs } = this;
const children = filterEmpty(this.$slots.default); const children = filterEmpty(getSlot(this));
const { forceRender, alignPoint } = this.$props; const { forceRender, alignPoint } = this.$props;
if (children.length > 1) { if (children.length > 1) {
warning(false, 'Trigger $slots.default.length > 1, just support only one default', true); warning(false, 'Trigger $slots.default.length > 1, just support only one default', true);
} }
const child = children[0]; const child = children[0];
this.childOriginEvents = getDataEvents(child); this.childOriginEvents = getEvents(this);
const newChildProps = { const newChildProps = {
props: {},
nativeOn: {},
key: 'trigger', key: 'trigger',
class: $attrs.class,
}; };
if (this.isContextmenuToShow()) { if (this.isContextmenuToShow()) {
newChildProps.nativeOn.contextmenu = this.onContextmenu; newChildProps.onContextmenu = this.onContextmenu;
} else { } else {
newChildProps.nativeOn.contextmenu = this.createTwoChains('contextmenu'); newChildProps.onContextmenu = this.createTwoChains('contextmenu');
} }
if (this.isClickToHide() || this.isClickToShow()) { if (this.isClickToHide() || this.isClickToShow()) {
newChildProps.nativeOn.click = this.onClick; newChildProps.onClick = this.onClick;
newChildProps.nativeOn.mousedown = this.onMousedown; newChildProps.onMousedown = this.onMousedown;
newChildProps.nativeOn.touchstart = this.onTouchstart; newChildProps.onTouchstart = this.onTouchstart;
} else { } else {
newChildProps.nativeOn.click = this.createTwoChains('click'); newChildProps.onClick = this.createTwoChains('click');
newChildProps.nativeOn.mousedown = this.createTwoChains('mousedown'); newChildProps.onMousedown = this.createTwoChains('mousedown');
newChildProps.nativeOn.touchstart = this.createTwoChains('onTouchstart'); newChildProps.onTouchstart = this.createTwoChains('onTouchstart');
} }
if (this.isMouseEnterToShow()) { if (this.isMouseEnterToShow()) {
newChildProps.nativeOn.mouseenter = this.onMouseenter; newChildProps.onMouseenter = this.onMouseenter;
if (alignPoint) { if (alignPoint) {
newChildProps.nativeOn.mousemove = this.onMouseMove; newChildProps.onMousemove = this.onMouseMove;
} }
} else { } else {
newChildProps.nativeOn.mouseenter = this.createTwoChains('mouseenter'); newChildProps.onMouseenter = this.createTwoChains('mouseenter');
} }
if (this.isMouseLeaveToHide()) { if (this.isMouseLeaveToHide()) {
newChildProps.nativeOn.mouseleave = this.onMouseleave; newChildProps.onMouseleave = this.onMouseleave;
} else { } else {
newChildProps.nativeOn.mouseleave = this.createTwoChains('mouseleave'); newChildProps.onMouseleave = this.createTwoChains('mouseleave');
} }
if (this.isFocusToShow() || this.isBlurToHide()) { if (this.isFocusToShow() || this.isBlurToHide()) {
newChildProps.nativeOn.focus = this.onFocus; newChildProps.onFocus = this.onFocus;
newChildProps.nativeOn.blur = this.onBlur; newChildProps.onBlur = this.onBlur;
} else { } else {
newChildProps.nativeOn.focus = this.createTwoChains('focus'); newChildProps.onFocus = this.createTwoChains('focus');
newChildProps.nativeOn.blur = e => { newChildProps.onBlur = e => {
if (e && (!e.relatedTarget || !contains(e.target, e.relatedTarget))) { if (e && (!e.relatedTarget || !contains(e.target, e.relatedTarget))) {
this.createTwoChains('blur')(e); this.createTwoChains('blur')(e);
} }
}; };
} }
this.trigger = cloneElement(child, newChildProps); const trigger = cloneVNode(child, newChildProps);
let portal;
return ( // prevent unmounting after it's rendered
<ContainerRender if (sPopupVisible || this._component || forceRender) {
parent={this} portal = (
visible={sPopupVisible} <Portal
autoMount={false} key="portal"
forceRender={forceRender} children={this.getComponent()}
getComponent={this.getComponent}
getContainer={this.getContainer} getContainer={this.getContainer}
children={({ renderComponent }) => { didUpdate={this.handlePortalUpdate}
this.renderComponent = renderComponent; ></Portal>
return this.trigger;
}}
/>
); );
}
return [portal, trigger];
}, },
}; };

View File

@ -1,4 +1,4 @@
import Vue from 'vue'; import { cloneVNode, inject, provide } from 'vue';
import ref from 'vue-ref'; import ref from 'vue-ref';
import PropTypes from '../_util/vue-types'; import PropTypes from '../_util/vue-types';
import contains from '../vc-util/Dom/contains'; import contains from '../vc-util/Dom/contains';
@ -7,6 +7,7 @@ import {
getComponentFromProp, getComponentFromProp,
getEvents, getEvents,
filterEmpty, filterEmpty,
getSlot,
getListeners, getListeners,
} from '../_util/props-util'; } from '../_util/props-util';
import { requestAnimationTimeout, cancelAnimationTimeout } from '../_util/requestAnimationTimeout'; import { requestAnimationTimeout, cancelAnimationTimeout } from '../_util/requestAnimationTimeout';
@ -15,11 +16,8 @@ import warning from '../_util/warning';
import Popup from './Popup'; import Popup from './Popup';
import { getAlignFromPlacement, getAlignPopupClassName, noop } from './utils'; import { getAlignFromPlacement, getAlignPopupClassName, noop } from './utils';
import BaseMixin from '../_util/BaseMixin'; import BaseMixin from '../_util/BaseMixin';
import { cloneElement } from '../_util/vnode';
import Portal from '../_util/Portal'; import Portal from '../_util/Portal';
Vue.use(ref, { name: 'ant-ref' });
function returnEmptyString() { function returnEmptyString() {
return ''; return '';
} }
@ -40,6 +38,7 @@ const ALL_HANDLERS = [
export default { export default {
name: 'Trigger', name: 'Trigger',
directives: { 'ant-ref': ref },
mixins: [BaseMixin], mixins: [BaseMixin],
props: { props: {
action: PropTypes.oneOfType([PropTypes.string, PropTypes.arrayOf(PropTypes.string)]).def([]), action: PropTypes.oneOfType([PropTypes.string, PropTypes.arrayOf(PropTypes.string)]).def([]),
@ -76,16 +75,6 @@ export default {
stretch: PropTypes.string, stretch: PropTypes.string,
alignPoint: PropTypes.bool, // Maybe we can support user pass position in the future alignPoint: PropTypes.bool, // Maybe we can support user pass position in the future
}, },
provide() {
return {
vcTriggerContext: this,
};
},
inject: {
vcTriggerContext: { default: () => ({}) },
savePopupRef: { default: () => noop },
dialogContext: { default: () => null },
},
data() { data() {
const props = this.$props; const props = this.$props;
let popupVisible; let popupVisible;
@ -113,6 +102,16 @@ export default {
} }
}, },
}, },
created() {
provide('vcTriggerContext', this);
},
setup() {
return {
vcTriggerContext: inject('configProvider', {}),
savePopupRef: inject('vcTriggerContext', noop),
dialogContext: inject('dialogContext', null),
};
},
deactivated() { deactivated() {
this.setPopupVisible(false); this.setPopupVisible(false);
}, },
@ -417,14 +416,12 @@ export default {
align: getListeners(this).popupAlign || noop, align: getListeners(this).popupAlign || noop,
...mouseProps, ...mouseProps,
}, },
directives: [
{
name: 'ant-ref',
value: this.savePopup,
},
],
}; };
return <Popup {...popupProps}>{getComponentFromProp(self, 'popup')}</Popup>; return (
<Popup v-ant-ref={this.savePopup} {...popupProps}>
{getComponentFromProp(self, 'popup')}
</Popup>
);
}, },
getContainer() { getContainer() {
@ -584,7 +581,7 @@ export default {
}, },
render() { render() {
const { sPopupVisible } = this; const { sPopupVisible } = this;
const children = filterEmpty(this.$slots.default); const children = filterEmpty(getSlot(this));
const { forceRender, alignPoint } = this.$props; const { forceRender, alignPoint } = this.$props;
if (children.length > 1) { if (children.length > 1) {
@ -639,7 +636,7 @@ export default {
}; };
} }
const trigger = cloneElement(child, newChildProps); const trigger = cloneVNode(child, newChildProps);
let portal; let portal;
// prevent unmounting after it's rendered // prevent unmounting after it's rendered
if (sPopupVisible || this._component || forceRender) { if (sPopupVisible || this._component || forceRender) {
@ -652,14 +649,6 @@ export default {
></Portal> ></Portal>
); );
} }
return portal return [portal, trigger];
? cloneElement(trigger, {
children: [
...((trigger.componentOptions ? trigger.componentOptions.children : trigger.children) ||
[]),
portal,
],
})
: trigger;
}, },
}; };