import { __rest } from "tslib";
import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
/* eslint-disable react-hooks/exhaustive-deps */

import { useContext, useMemo, useRef } from 'react';
import cls from 'clsx';
import { CSSTransition } from 'react-transition-group';
import { getZIndexStyle, noop, stopPropagation } from '../utils';
import NumberKeyboardKey from './NumberKeyboardKey';
import { useUpdateEffect } from '../hooks';
import useClickAway from '../hooks/use-click-away';
import ConfigProviderContext from '../config-provider/ConfigProviderContext';

const NumberKeyboard = _a => {
  var {
    className,
    style
  } = _a,
      props = __rest(_a, ["className", "style"]);

  const {
    prefixCls,
    createNamespace
  } = useContext(ConfigProviderContext);
  const [bem] = createNamespace('number-keyboard', prefixCls);
  const root = useRef();

  const genBasicKeys = () => {
    const keys = Array(9).fill('').map((_, i) => ({
      text: i + 1
    }));

    if (props.randomKeyOrder) {
      keys.sort(() => Math.random() > 0.5 ? 1 : -1);
    }

    return keys;
  };

  const genDefaultKeys = () => [...genBasicKeys(), {
    text: props.extraKey,
    type: 'extra'
  }, {
    text: 0
  }, {
    text: props.showDeleteKey ? props.deleteButtonText : '',
    type: props.showDeleteKey ? 'delete' : ''
  }];

  const genCustomKeys = () => {
    const keys = genBasicKeys();
    const {
      extraKey
    } = props;
    const extraKeys = Array.isArray(extraKey) ? extraKey : [extraKey];

    if (extraKeys.length === 1) {
      keys.push({
        text: 0,
        wider: true
      }, {
        text: extraKeys[0],
        type: 'extra'
      });
    } else if (extraKeys.length === 2) {
      keys.push({
        text: extraKeys[0],
        type: 'extra'
      }, {
        text: 0
      }, {
        text: extraKeys[1],
        type: 'extra'
      });
    }

    return keys;
  };

  const keys = useMemo(() => props.theme === 'custom' ? genCustomKeys() : genDefaultKeys(), [props.theme, genCustomKeys, genDefaultKeys]);

  const onBlur = () => {
    var _a;

    if (props.visible) {
      (_a = props.onBlur) === null || _a === void 0 ? void 0 : _a.call(props);
    }
  };

  const onClose = () => {
    var _a;

    (_a = props.onClose) === null || _a === void 0 ? void 0 : _a.call(props);

    if (props.blurOnClose) {
      onBlur();
    }
  };

  const onAnimationEnd = () => {
    var _a;

    (_a = props[props.visible ? 'onShow' : 'onHide']) === null || _a === void 0 ? void 0 : _a.call(props);
  };

  const onPress = (text, type) => {
    var _a, _b, _c, _d;

    if (text === '') {
      if (type === 'extra') {
        onBlur();
      }

      return;
    }

    const {
      value
    } = props;

    if (type === 'delete') {
      (_a = props.onDelete) === null || _a === void 0 ? void 0 : _a.call(props);
      (_b = props.onChange) === null || _b === void 0 ? void 0 : _b.call(props, value.slice(0, value.length - 1));
    } else if (type === 'close') {
      onClose();
    } else if (value.length < props.maxlength) {
      (_c = props.onInput) === null || _c === void 0 ? void 0 : _c.call(props, text);
      (_d = props.onChange) === null || _d === void 0 ? void 0 : _d.call(props, value + text);
    }
  };

  const renderTitle = () => {
    const {
      title,
      theme,
      closeButtonText
    } = props;
    const showClose = closeButtonText && theme === 'default';
    const showTitle = title || showClose;

    if (!showTitle) {
      return null;
    }

    return _jsxs("div", Object.assign({
      className: cls(bem('header'))
    }, {
      children: [title && _jsx("h2", Object.assign({
        className: cls(bem('title'))
      }, {
        children: title
      })), showClose && _jsx("button", Object.assign({
        type: "button",
        className: cls(bem('close')),
        onClick: onClose
      }, {
        children: closeButtonText
      }))]
    }));
  };

  const renderKeys = () => keys.map((key, i) => {
    var _a, _b, _c;

    let keySlots = null;

    if (!key.type) {
      keySlots = (_a = props.numberKeyRender) === null || _a === void 0 ? void 0 : _a.call(props, key);
    }

    if (key.type === 'delete') {
      keySlots = (_b = props.deleteRender) === null || _b === void 0 ? void 0 : _b.call(props);
    }

    if (key.type === 'extra') {
      keySlots = (_c = props.extraKeyRender) === null || _c === void 0 ? void 0 : _c.call(props);
    }

    return _jsx(NumberKeyboardKey // eslint-disable-next-line react/no-array-index-key
    , {
      text: key.text,
      type: key.type,
      wider: key.wider,
      color: key.color,
      onPress: onPress,
      // eslint-disable-next-line react/no-children-prop
      children: keySlots
    }, i);
  });

  const renderSidebar = () => {
    if (props.theme === 'custom') {
      return _jsxs("div", Object.assign({
        className: cls(bem('sidebar'))
      }, {
        children: [props.showDeleteKey && _jsx(NumberKeyboardKey, {
          large: true,
          text: props.deleteButtonText,
          type: "delete",
          onPress: onPress
        }), _jsx(NumberKeyboardKey, {
          large: true,
          text: props.closeButtonText,
          type: "close",
          color: "blue",
          loading: props.closeButtonLoading,
          onPress: onPress
        })]
      }));
    }

    return null;
  };

  useUpdateEffect(() => {
    var _a;

    if (!props.transition) {
      (_a = props[props.visible ? 'onShow' : 'onHide']) === null || _a === void 0 ? void 0 : _a.call(props);
    }
  }, [props.visible]);
  useClickAway(root, props.hideOnClickOutside ? onBlur : noop, 'touchstart');
  const Title = renderTitle();

  const Content = _jsx(CSSTransition, Object.assign({
    mountOnEnter: true,
    unmountOnExit: true,
    nodeRef: root,
    in: props.visible,
    timeout: 300,
    classNames: props.transition ? 'rv-slide-up' : '',
    onExited: onAnimationEnd
  }, {
    children: _jsxs("div", Object.assign({
      ref: root,
      style: Object.assign(Object.assign({}, style), getZIndexStyle(props.zIndex)),
      className: cls(className, bem({
        unfit: !props.safeAreaInsetBottom,
        'with-title': !!Title
      })),
      onTouchStart: stopPropagation
    }, {
      children: [Title, _jsxs("div", Object.assign({
        className: cls(bem('body'))
      }, {
        children: [_jsx("div", Object.assign({
          className: cls(bem('keys'))
        }, {
          children: renderKeys()
        })), renderSidebar()]
      }))]
    }))
  }));

  return Content;
};

NumberKeyboard.defaultProps = {
  transition: true,
  blurOnClose: true,
  showDeleteKey: true,
  hideOnClickOutside: true,
  safeAreaInsetBottom: true,
  theme: 'default',
  value: '',
  extraKey: '',
  maxlength: Number.MAX_VALUE
};
export default NumberKeyboard;