import React from "react";
import classNames from "classnames";
import { StyledProps } from "../_type";
import { useDefault } from "../_util/use-default";
import { useConfig } from "../_util/config-context";
import { useOutsideClick } from "../util/outsideclick";
import { TriggerProps } from "../popover/trigger";
import { MediaObject } from "../mediaobject";
import { BubbleProps, Bubble } from "../bubble";

export interface PopConfirmProps
  extends Pick<
      BubbleProps,
      | "arrowPointAtCenter"
      | "placement"
      | "visible"
      | "onVisibleChange"
      | "closeOnScroll"
      | "popupContainer"
      | "destroyOnClose"
      | "onExited"
    >,
    StyledProps {
  /**
   * 提示标题
   */
  title?: React.ReactNode;

  /**
   * 提示信息
   */
  message?: React.ReactNode;

  /**
   * 底部渲染内容
   * @docType React.ReactNode | ((close: () => void) => React.ReactNode)
   */
  footer?: React.ReactNode | ((close: () => void) => React.ReactNode);

  /**
   * 需要被气泡包裹的内容
   */
  children?: React.ReactNode;

  /**
   * 是否可以跟随参考元素离开可视范围
   * @default false
   * @since 2.5.0
   */
  escapeWithReference?: BubbleProps["escapeWithReference"];

  /**
   * 是否阻止点击 Popconfirm 子元素时弹出确认框
   * @default false
   * @since 2.7.0
   */
  disabled?: boolean;
}

function PopConfirmClickTrigger({
  childrenElementRef,
  overlayElementRef,
  visible,
  setVisible,
  openDelay = 0,
  closeDelay = 0,
  render,
}: TriggerProps) {
  const { listen, ignoreProps } = useOutsideClick([
    childrenElementRef,
    overlayElementRef,
  ]);

  listen(() => visible && setVisible(false, closeDelay));

  return render({
    overlayProps: ignoreProps,
    childrenProps: {
      onClick: () => setVisible(!visible, openDelay),
    },
  });
}

PopConfirmClickTrigger.displayName = "PopConfirmClickTrigger";

export function PopConfirm({
  title,
  message,
  children,
  footer,
  className,
  disabled,
  visible: _visible,
  onVisibleChange: _onVisibleChange,
  ...props
}: PopConfirmProps) {
  const { classPrefix } = useConfig();
  const [visible, onVisibleChange] = useDefault(
    _visible,
    false,
    _onVisibleChange
  );

  const close = () => onVisibleChange(false);

  const handleVisibleChange = (value: boolean) => {
    if (disabled) {
      return;
    }
    onVisibleChange(value);
  };

  return (
    <Bubble
      {...props}
      visible={visible}
      onVisibleChange={handleVisibleChange}
      className={classNames(`${classPrefix}-popconfirm`, className)}
      trigger={PopConfirmClickTrigger}
      content={
        <>
          <div className={`${classPrefix}-popconfirm__body`}>
            <MediaObject>
              {title && (
                <h3 className={`${classPrefix}-popconfirm__messagetitle`}>
                  {title}
                </h3>
              )}
              {message && (
                <div className={`${classPrefix}-popconfirm__messagetext`}>
                  {message}
                </div>
              )}
            </MediaObject>
          </div>
          {footer && (
            <div className={`${classPrefix}-popconfirm__footer`}>
              {typeof footer === "function" ? footer.call(null, close) : footer}
            </div>
          )}
        </>
      }
    >
      {children}
    </Bubble>
  );
}

PopConfirm.displayName = "PopConfirm";
