"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
exports.Menu = void 0;
const tslib_1 = require("tslib");
const classnames_1 = tslib_1.__importDefault(require("classnames"));
const rc_menu_1 = tslib_1.__importStar(require("rc-menu"));
const react_1 = tslib_1.__importDefault(require("react"));
const react_lifecycles_compat_1 = require("react-lifecycles-compat");
const motion_1 = require("../utils/motion");
const raf_1 = require("../utils/raf");
const warning_1 = require("../utils/warning");
const MenuContext_1 = tslib_1.__importDefault(require("./MenuContext"));
const MenuItem_1 = tslib_1.__importDefault(require("./MenuItem"));
const SubMenu_1 = tslib_1.__importDefault(require("./SubMenu"));
require("./style.less");
class InternalMenu extends react_1.default.Component {
    static getDerivedStateFromProps(nextProps, prevState) {
        const { prevProps } = prevState;
        const newState = {
            prevProps: nextProps,
        };
        if (prevProps.mode === 'inline' && nextProps.mode !== 'inline') {
            newState.switchingModeFromInline = true;
        }
        if ('openKeys' in nextProps) {
            newState.openKeys = nextProps.openKeys;
        }
        else {
            // [Legacy] Old code will return after `openKeys` changed.
            // Not sure the reason, we should keep this logic still.
            if (nextProps.inlineCollapsed && !prevProps.inlineCollapsed) {
                newState.switchingModeFromInline = true;
                newState.inlineOpenKeys = prevState.openKeys;
                newState.openKeys = [];
            }
            if (!nextProps.inlineCollapsed && prevProps.inlineCollapsed) {
                newState.openKeys = prevState.inlineOpenKeys;
                newState.inlineOpenKeys = [];
            }
        }
        return newState;
    }
    constructor(props) {
        super(props);
        // Restore vertical mode when menu is collapsed responsively when mounted
        // https://github.com/ant-design/ant-design/issues/13104
        // not a perfect solution, looking a new way to avoid setting switchingModeFromInline in this situation
        this.handleMouseEnter = (e) => {
            this.restoreModeVerticalFromInline();
            const { onMouseEnter } = this.props;
            if (onMouseEnter) {
                onMouseEnter(e);
            }
        };
        this.handleTransitionEnd = (e) => {
            // when inlineCollapsed menu width animation finished
            // https://github.com/ant-design/ant-design/issues/12864
            const widthCollapsed = e.propertyName === 'width' && e.target === e.currentTarget;
            // Fix SVGElement e.target.className.indexOf is not a function
            // https://github.com/ant-design/ant-design/issues/15699
            const { className } = e.target;
            // SVGAnimatedString.animVal should be identical to SVGAnimatedString.baseVal, unless during an animation.
            const classNameValue = Object.prototype.toString.call(className) === '[object SVGAnimatedString]' ? className.animVal : className;
            // Fix for <Menu style={{ width: '100%' }} />, the width transition won't trigger when menu is collapsed
            // https://github.com/ant-design/ant-design-pro/issues/2783
            const iconScaled = e.propertyName === 'font-size' && classNameValue.indexOf('anticon') >= 0;
            if (widthCollapsed || iconScaled) {
                this.restoreModeVerticalFromInline();
            }
        };
        this.handleClick = (e) => {
            this.handleOpenChange([]);
            const { onClick } = this.props;
            if (onClick) {
                onClick(e);
            }
        };
        this.handleOpenChange = (openKeys) => {
            this.setOpenKeys(openKeys);
            const { onOpenChange } = this.props;
            if (onOpenChange) {
                onOpenChange(openKeys);
            }
        };
        this.renderMenu = () => {
            const { prefixCls: customizePrefixCls, className } = this.props;
            const menuMode = this.getRealMenuMode();
            const menuOpenMotion = this.getOpenMotionProps(menuMode);
            const prefixCls = customizePrefixCls || 'kt-inner-menu';
            const menuClassName = (0, classnames_1.default)(className, {
                [`${prefixCls}-inline-collapsed`]: this.getInlineCollapsed(),
            });
            const menuProps = {
                openKeys: this.state.openKeys,
                onOpenChange: this.handleOpenChange,
                className: menuClassName,
                mode: menuMode,
                // Motion
                ...menuOpenMotion,
            };
            if (menuMode !== 'inline') {
                // closing vertical popup submenu after click it
                menuProps.onClick = this.handleClick;
            }
            const hideMenu = this.getInlineCollapsed();
            if (hideMenu) {
                menuProps.openKeys = [];
            }
            return (react_1.default.createElement(rc_menu_1.default, { ...this.props, ...menuProps, prefixCls: prefixCls, 
                // @ts-ignore
                onTransitionEnd: this.handleTransitionEnd, onMouseEnter: this.handleMouseEnter }));
        };
        (0, warning_1.warning)(!('onOpen' in props || 'onClose' in props), '[Menu] `onOpen` and `onClose` are removed, please use `onOpenChange` instead, ' +
            'see: https://u.ant.design/menu-on-open-change.');
        (0, warning_1.warning)(!('inlineCollapsed' in props && props.mode !== 'inline'), '[Menu] `inlineCollapsed` should only be used when `mode` is inline.');
        let openKeys;
        if ('openKeys' in props) {
            openKeys = props.openKeys;
        }
        else if ('defaultOpenKeys' in props) {
            openKeys = props.defaultOpenKeys;
        }
        this.state = {
            openKeys: openKeys || [],
            switchingModeFromInline: false,
            inlineOpenKeys: [],
            prevProps: props,
        };
    }
    componentWillUnmount() {
        raf_1.wrapperRaf.cancel(this.mountRafId);
    }
    setOpenKeys(openKeys) {
        if (!('openKeys' in this.props)) {
            this.setState({ openKeys });
        }
    }
    getRealMenuMode() {
        const inlineCollapsed = this.getInlineCollapsed();
        if (this.state.switchingModeFromInline && inlineCollapsed) {
            return 'inline';
        }
        const { mode } = this.props;
        return inlineCollapsed ? 'vertical' : mode;
    }
    getInlineCollapsed() {
        const { inlineCollapsed } = this.props;
        return inlineCollapsed;
    }
    getOpenMotionProps(menuMode) {
        const { openTransitionName, openAnimation, motion } = this.props;
        // Provides by user
        if (motion) {
            return { motion };
        }
        if (openAnimation) {
            (0, warning_1.warning)(typeof openAnimation === 'string', '[Menu] `openAnimation` do not support object. Please use `motion` instead.');
            return { openAnimation };
        }
        if (openTransitionName) {
            return { openTransitionName };
        }
        // Default logic
        if (menuMode === 'horizontal') {
            return { motion: { motionName: 'slide-up' } };
        }
        if (menuMode === 'inline') {
            return { motion: motion_1.collapseMotion };
        }
        // When mode switch from inline
        // submenu should hide without animation
        return {
            motion: {
                motionName: '',
            },
        };
    }
    restoreModeVerticalFromInline() {
        const { switchingModeFromInline } = this.state;
        if (switchingModeFromInline) {
            this.setState({
                switchingModeFromInline: false,
            });
        }
    }
    render() {
        return (react_1.default.createElement(MenuContext_1.default.Provider, { value: {
                inlineCollapsed: this.getInlineCollapsed() || false,
            } }, this.renderMenu()));
    }
}
InternalMenu.defaultProps = {
    className: '',
    focusable: false,
};
(0, react_lifecycles_compat_1.polyfill)(InternalMenu);
// We should keep this as ref-able
class Menu extends react_1.default.Component {
    render() {
        return react_1.default.createElement(InternalMenu, { ...this.props });
    }
}
exports.Menu = Menu;
Menu.Divider = rc_menu_1.Divider;
Menu.Item = MenuItem_1.default;
Menu.SubMenu = SubMenu_1.default;
Menu.ItemGroup = rc_menu_1.ItemGroup;
//# sourceMappingURL=index.js.map