import { __assign, __rest } from "tslib";
import React, { useCallback, useContext, useEffect, useRef, useState } from 'react';
import classNames from 'classnames';
import { createPopper } from '@popperjs/core';
import Transition from '../transition';
import Portal from '../portal';
import { ConfigContext } from '../config-provider/config-context';
import { getPrefixCls } from '../_utils/general';
var Popup = function (props) {
    var _a = props.disabled, disabled = _a === void 0 ? false : _a, _b = props.trigger, trigger = _b === void 0 ? 'click' : _b, _c = props.placement, placement = _c === void 0 ? 'top' : _c, _d = props.defaultVisible, defaultVisible = _d === void 0 ? false : _d, _e = props.arrow, arrow = _e === void 0 ? true : _e, _f = props.flip, flip = _f === void 0 ? true : _f, _g = props.offset, offset = _g === void 0 ? 0 : _g, _h = props.theme, theme = _h === void 0 ? 'light' : _h, _j = props.usePortal, usePortal = _j === void 0 ? true : _j, _k = props.mouseEnterDelay, mouseEnterDelay = _k === void 0 ? 100 : _k, _l = props.mouseLeaveDelay, mouseLeaveDelay = _l === void 0 ? 100 : _l, _m = props.biZoom, biZoom = _m === void 0 ? true : _m, customisedCls = props.prefixCls, content = props.content, visible = props.visible, onVisibleChange = props.onVisibleChange, className = props.className, children = props.children, otherProps = __rest(props, ["disabled", "trigger", "placement", "defaultVisible", "arrow", "flip", "offset", "theme", "usePortal", "mouseEnterDelay", "mouseLeaveDelay", "biZoom", "prefixCls", "content", "visible", "onVisibleChange", "className", "children"]);
    var configContext = useContext(ConfigContext);
    var prefixCls = getPrefixCls('popup', configContext.prefixCls, customisedCls);
    var cls = classNames(className, prefixCls, prefixCls + "_" + placement, prefixCls + "_" + theme);
    var _o = useState('visible' in props ? visible : defaultVisible), popupVisible = _o[0], setPopupVisible = _o[1];
    var targetRef = useRef(null);
    var popupRef = useRef(null);
    var delayDisplayPopupTimer = useRef(undefined);
    var delayHidePopupTimer = useRef(undefined);
    var popperRef = useRef(undefined);
    var displayPopup = useCallback(function () {
        setPopupVisible(true);
        onVisibleChange && onVisibleChange(true);
    }, [onVisibleChange]);
    var hidePopup = useCallback(function () {
        setPopupVisible(false);
        onVisibleChange && onVisibleChange(false);
    }, [onVisibleChange]);
    var delayDisplayPopup = useCallback(function () {
        delayDisplayPopupTimer.current = window.setTimeout(function () {
            displayPopup();
        }, mouseEnterDelay);
    }, [mouseEnterDelay, displayPopup]);
    var delayHidePopup = useCallback(function () {
        delayHidePopupTimer.current = window.setTimeout(function () {
            hidePopup();
        }, mouseLeaveDelay);
    }, [mouseLeaveDelay, hidePopup]);
    var handlePopupOnMouseEnter = function () {
        if (trigger === 'hover') {
            displayPopup();
            window.clearTimeout(delayHidePopupTimer.current);
        }
    };
    var handlePopupOnMouseLeave = function () {
        if (trigger === 'hover') {
            delayHidePopup();
            window.clearTimeout(delayDisplayPopupTimer.current);
        }
    };
    var handleTargetOnMouseEnter = useCallback(function () {
        delayDisplayPopup();
        window.clearTimeout(delayHidePopupTimer.current);
    }, [delayDisplayPopup]);
    var handleTargetOnMouseLeave = useCallback(function () {
        delayHidePopup();
        window.clearTimeout(delayDisplayPopupTimer.current);
    }, [delayHidePopup]);
    var documentOnClick = useCallback(function (e) {
        var target = targetRef.current;
        var popup = popupRef.current;
        if (!target ||
            target.contains(e.target) ||
            !popup ||
            popup.contains(e.target))
            return;
        hidePopup();
    }, [targetRef, hidePopup]);
    var handleTargetOnMouseClick = useCallback(function (e) {
        e.preventDefault();
        if (popupVisible) {
            hidePopup();
        }
        else {
            displayPopup();
            document.addEventListener('click', documentOnClick, true);
        }
    }, [popupVisible, hidePopup, displayPopup, documentOnClick]);
    var transitionOnEnter = function () {
        var instance = createPopper(targetRef.current, popupRef.current, {
            placement: placement,
            modifiers: [
                {
                    name: 'flip',
                    enabled: flip,
                },
                {
                    name: 'offset',
                    options: {
                        offset: [0, arrow ? 10 + offset : 3 + offset],
                    },
                },
                {
                    name: 'computeStyles',
                    options: {
                        gpuAcceleration: false,
                        adaptive: false,
                    },
                },
            ],
        });
        if (trigger === 'hover') {
            instance.state.elements.popper.addEventListener('mouseenter', handlePopupOnMouseEnter);
            instance.state.elements.popper.addEventListener('mouseleave', handlePopupOnMouseLeave);
        }
        popperRef.current = instance;
    };
    var transitionOnExited = function () {
        var popperInstance = popperRef.current;
        if (popperInstance) {
            if (trigger === 'hover') {
                popperInstance.state.elements.popper.removeEventListener('mouseenter', handlePopupOnMouseEnter);
                popperInstance.state.elements.popper.removeEventListener('mouseleave', handlePopupOnMouseLeave);
            }
            popperInstance.destroy();
        }
    };
    var getAnimationName = function () {
        var mapping = {
            'top-start': biZoom ? 'top-start' : 'center-top',
            top: biZoom ? 'top' : 'center-top',
            'top-end': biZoom ? 'top-end' : 'center-top',
            'bottom-start': biZoom ? 'bottom-start' : 'center-bottom',
            bottom: biZoom ? 'bottom' : 'center-bottom',
            'bottom-end': biZoom ? 'bottom-end' : 'center-bottom',
            'left-start': biZoom ? 'bottom-end' : 'center-left',
            left: biZoom ? 'left' : 'center-left',
            'left-end': biZoom ? 'top-end' : 'center-left',
            'right-start': biZoom ? 'bottom-start' : 'center-right',
            right: biZoom ? 'right' : 'center-right',
            'right-end': biZoom ? 'top-start' : 'center-right',
        };
        return "zoom-" + mapping[placement];
    };
    useEffect(function () {
        if (disabled)
            return;
        var target = targetRef.current;
        if (!target)
            return;
        if (trigger === 'hover') {
            target.addEventListener('mouseenter', handleTargetOnMouseEnter);
            target.addEventListener('mouseleave', handleTargetOnMouseLeave);
        }
        else if (trigger === 'click') {
            target.addEventListener('click', handleTargetOnMouseClick);
        }
        else if (trigger === 'focus') {
            if (target.nodeName === 'INPUT' || target.nodeName === 'TEXTAREA') {
                target.addEventListener('focus', displayPopup);
                target.addEventListener('blur', hidePopup);
            }
            else {
                target.addEventListener('mousedown', displayPopup);
                target.addEventListener('mouseup', hidePopup);
            }
        }
        else if (trigger === 'contextmenu') {
            target.addEventListener('contextmenu', handleTargetOnMouseClick);
        }
        else if (trigger === 'manual') {
            setPopupVisible(props.visible);
        }
        return function () {
            target.removeEventListener('mouseenter', handleTargetOnMouseEnter);
            target.removeEventListener('mouseleave', handleTargetOnMouseLeave);
            target.removeEventListener('click', handleTargetOnMouseClick);
            target.removeEventListener('focus', displayPopup);
            target.removeEventListener('blur', hidePopup);
            target.removeEventListener('mousedown', displayPopup);
            target.removeEventListener('mouseup', hidePopup);
            target.removeEventListener('contextmenu', handleTargetOnMouseClick);
        };
    }, [
        props.visible,
        disabled,
        targetRef,
        trigger,
        handleTargetOnMouseClick,
        handleTargetOnMouseEnter,
        handleTargetOnMouseLeave,
        displayPopup,
        hidePopup,
    ]);
    useEffect(function () {
        if ('visible' in props) {
            props.visible ? displayPopup() : hidePopup();
        }
    }, [props, displayPopup, hidePopup]);
    var renderContent = function () { return (React.createElement(Transition, { in: popupVisible, onEnter: transitionOnEnter, onExited: transitionOnExited, animation: getAnimationName() },
        React.createElement("div", __assign({}, otherProps, { className: cls, ref: popupRef }),
            content && arrow && React.createElement("div", { "data-popper-arrow": true, className: prefixCls + "__arrow" }),
            content))); };
    var elementProps = {
        ref: function (ref) { return (targetRef.current = ref); },
    };
    return (React.createElement(React.Fragment, null,
        React.cloneElement(children, elementProps),
        usePortal ? React.createElement(Portal, null, renderContent()) : renderContent()));
};
export default Popup;
//# sourceMappingURL=index.js.map