function _typeof(obj) { if (typeof Symbol === "function" && typeof Symbol.iterator === "symbol") { _typeof = function _typeof(obj) { return typeof obj; }; } else { _typeof = function _typeof(obj) { return obj && typeof Symbol === "function" && obj.constructor === Symbol && obj !== Symbol.prototype ? "symbol" : typeof obj; }; } return _typeof(obj); }

function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }

function _defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } }

function _createClass(Constructor, protoProps, staticProps) { if (protoProps) _defineProperties(Constructor.prototype, protoProps); if (staticProps) _defineProperties(Constructor, staticProps); return Constructor; }

function _possibleConstructorReturn(self, call) { if (call && (_typeof(call) === "object" || typeof call === "function")) { return call; } return _assertThisInitialized(self); }

function _getPrototypeOf(o) { _getPrototypeOf = Object.setPrototypeOf ? Object.getPrototypeOf : function _getPrototypeOf(o) { return o.__proto__ || Object.getPrototypeOf(o); }; return _getPrototypeOf(o); }

function _assertThisInitialized(self) { if (self === void 0) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return self; }

function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function"); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, writable: true, configurable: true } }); if (superClass) _setPrototypeOf(subClass, superClass); }

function _setPrototypeOf(o, p) { _setPrototypeOf = Object.setPrototypeOf || function _setPrototypeOf(o, p) { o.__proto__ = p; return o; }; return _setPrototypeOf(o, p); }

function _defineProperty(obj, key, value) { if (key in obj) { Object.defineProperty(obj, key, { value: value, enumerable: true, configurable: true, writable: true }); } else { obj[key] = value; } return obj; }

import React from 'react';
import ReactDOM from 'react-dom';
import PropTypes from 'prop-types';
import ConfigProvider from '../config-provider';
import cls from 'classnames';
import Button from '../button';
import Input from '../input';
import Switch from '../switch';
import Balloon from '../balloon';
import { events, KEYCODE } from '../util';
var Tooltip = Balloon.Tooltip;

var Modal =
/*#__PURE__*/
function (_React$Component) {
  _inherits(Modal, _React$Component);

  function Modal(props) {
    var _this;

    _classCallCheck(this, Modal);

    _this = _possibleConstructorReturn(this, _getPrototypeOf(Modal).call(this, props));

    _defineProperty(_assertThisInitialized(_this), "addDocumentEvents", function () {
      if (_this.props.canCloseByEsc) {
        _this._keydownEvents = events.on(document, 'keydown', _this.handleDocumentKeyDown);
      }
    });

    _defineProperty(_assertThisInitialized(_this), "handleDocumentKeyDown", function (e) {
      if (_this.state.visible && e.keyCode === KEYCODE.ESC) {
        _this.setState({
          visible: false
        });
      }
    });

    _defineProperty(_assertThisInitialized(_this), "removeDocumentEvents", function () {
      if (_this._keydownEvents) {
        _this._keydownEvents.off();

        _this._keydownEvents = null;
      }
    });

    _defineProperty(_assertThisInitialized(_this), "onSideDrawerVisibleChange", function (checked) {
      _this.props.onSideDrawerVisibleChange(checked);
    });

    _defineProperty(_assertThisInitialized(_this), "onEditTitleChange", function (value) {
      _this.props.onEditTitleChange(value);
    });

    _defineProperty(_assertThisInitialized(_this), "onEnterEditing", function () {
      _this.setState({
        isEditing: true
      });
    });

    _defineProperty(_assertThisInitialized(_this), "onLeaveEditing", function () {
      _this.setState({
        isEditing: false
      });
    });

    _defineProperty(_assertThisInitialized(_this), "onClose", function () {
      var onClose = _this.props.onClose;

      if (!('visible' in _this.props)) {
        _this.setState({
          visible: false
        });
      }

      onClose();
    });

    _defineProperty(_assertThisInitialized(_this), "renderTitle", function () {
      var _this$props = _this.props,
          prefix = _this$props.prefix,
          title = _this$props.title,
          titleEditable = _this$props.titleEditable,
          titleEditTooltip = _this$props.titleEditTooltip,
          titleInputWidth = _this$props.titleInputWidth;
      var isEditing = _this.state.isEditing;
      var editTitle = isEditing ? React.createElement(Input, {
        size: "xs",
        autoFocus: true,
        value: title,
        onChange: _this.onEditTitleChange,
        onBlur: _this.onLeaveEditing,
        onPressEnter: _this.onLeaveEditing,
        style: {
          width: titleInputWidth
        }
      }) : React.createElement("span", null, React.createElement("span", {
        className: "edit-title"
      }, title), React.createElement(Tooltip, {
        trigger: React.createElement(Button.Icon, {
          className: "".concat(prefix, "modal-edit-icon"),
          type: "secondary",
          color: "gray",
          name: "pencil",
          onClick: _this.onEnterEditing
        }),
        align: "r"
      }, titleEditTooltip));
      return React.createElement("div", {
        className: "".concat(prefix, "modal-title")
      }, titleEditable ? editTitle : title);
    });

    _defineProperty(_assertThisInitialized(_this), "renderHeader", function () {
      var _this$props2 = _this.props,
          prefix = _this$props2.prefix,
          description = _this$props2.description,
          operations = _this$props2.operations,
          sideDrawer = _this$props2.sideDrawer,
          sideDrawerLabel = _this$props2.sideDrawerLabel,
          sideDrawerVisible = _this$props2.sideDrawerVisible;

      var title = _this.renderTitle();

      return React.createElement("div", {
        className: "".concat(prefix, "modal-header")
      }, React.createElement("div", {
        className: "left-part"
      }, title, React.createElement("div", {
        className: "".concat(prefix, "modal-description")
      }, description)), React.createElement("div", {
        className: "right-part"
      }, React.createElement("div", {
        className: "".concat(prefix, "modal-operations")
      }, operations), sideDrawer ? React.createElement("div", {
        className: "".concat(prefix, "modal-side-drawer-switch")
      }, React.createElement("span", {
        className: "".concat(prefix, "modal-side-drawer-switch-label")
      }, sideDrawerLabel), React.createElement(Switch, {
        size: "small",
        checked: sideDrawerVisible,
        onChange: _this.onSideDrawerVisibleChange
      })) : null, React.createElement(Button.Icon, {
        className: "".concat(prefix, "modal-close"),
        name: "remove",
        color: "gray",
        onClick: _this.onClose
      })));
    });

    _defineProperty(_assertThisInitialized(_this), "renderBody", function () {
      var _cls;

      var _this$props3 = _this.props,
          prefix = _this$props3.prefix,
          sideDrawer = _this$props3.sideDrawer,
          sideDrawerVisible = _this$props3.sideDrawerVisible,
          sideDrawerWidth = _this$props3.sideDrawerWidth,
          children = _this$props3.children;
      return React.createElement("div", {
        className: "".concat(prefix, "modal-body")
      }, React.createElement("div", {
        className: "".concat(prefix, "modal-children")
      }, children), sideDrawer ? React.createElement("div", {
        className: cls((_cls = {}, _defineProperty(_cls, "".concat(prefix, "modal-side-drawer"), true), _defineProperty(_cls, "".concat(prefix, "modal-side-drawer-visible"), sideDrawerVisible), _cls)),
        style: {
          width: sideDrawerVisible ? sideDrawerWidth : 0
        }
      }, sideDrawer) : null);
    });

    _defineProperty(_assertThisInitialized(_this), "renderModal", function () {
      var _cls2;

      var _this$props4 = _this.props,
          prefix = _this$props4.prefix,
          className = _this$props4.className,
          style = _this$props4.style;

      var header = _this.renderHeader();

      var body = _this.renderBody();

      return React.createElement("div", {
        className: cls((_cls2 = {}, _defineProperty(_cls2, "".concat(prefix, "modal"), true), _defineProperty(_cls2, className, !!className), _cls2)),
        style: style
      }, header, body);
    });

    _this.state = {
      visible: 'visible' in props ? props.visible : props.defaultVisible || false,
      isEditing: false
    };
    _this.container = document.createElement('div');
    return _this;
  }

  _createClass(Modal, [{
    key: "componentDidMount",
    value: function componentDidMount() {
      document.body.appendChild(this.container);

      if (this.state.visible) {
        document.body.classList.add('next-modal-open');
      }

      this.addDocumentEvents();
    }
  }, {
    key: "UNSAFE_componentWillReceiveProps",
    value: function UNSAFE_componentWillReceiveProps(nextProps) {
      if (nextProps.visible !== this.props.visible) {
        this.setState({
          visible: nextProps.visible
        });
      }
    }
  }, {
    key: "componentDidUpdate",
    value: function componentDidUpdate() {
      if (this.state.visible === false) {
        document.body.classList.remove('next-modal-open');
      }
    }
  }, {
    key: "componentWillUnmount",
    value: function componentWillUnmount() {
      document.body.removeChild(this.container);
      document.body.classList.remove('next-modal-open');
      this.container = null;
      this.removeDocumentEvents();
    }
  }, {
    key: "render",
    value: function render() {
      var visible = this.state.visible;

      if (visible) {
        return ReactDOM.createPortal(this.renderModal(), this.container);
      }

      return null;
    }
  }]);

  return Modal;
}(React.Component);

_defineProperty(Modal, "propTypes", {
  prefix: PropTypes.string,
  style: PropTypes.object,
  className: PropTypes.string,

  /**
   * 是否默认可见，非受控
   */
  defaultVisible: PropTypes.bool,

  /**
   * 是否可见，受控
   */
  visible: PropTypes.bool,

  /**
   * 点击关闭按钮回调
   */
  onClose: PropTypes.func,

  /**
   * Modal标题
   */
  title: PropTypes.string.isRequired,

  /**
   * Modal标题是否可编辑
   */
  titleEditable: PropTypes.bool,

  /**
   * 标题编辑图标提示文案
   */
  titleEditTooltip: PropTypes.string,

  /**
   * 可编辑时标题输入框的宽度
   */
  titleInputWidth: PropTypes.oneOfType([PropTypes.string, PropTypes.number]),

  /**
   * 标题编辑回调
   */
  onEditTitleChange: PropTypes.func,

  /**
   * Modal描述
   */
  description: PropTypes.string,

  /**
   * 操作区
   */
  operations: PropTypes.element,

  /**
   * 侧边栏内容
   */
  sideDrawer: PropTypes.node,

  /**
   * 侧边栏内容宽度
   */
  sideDrawerWidth: PropTypes.number,

  /**
   * 侧边栏切换显示Switch前label
   */
  sideDrawerLabel: PropTypes.string,

  /**
   * 侧边栏内容是否可见
   */
  sideDrawerVisible: PropTypes.bool,

  /**
   * 侧边栏内容切换可见回调
   */
  onSideDrawerVisibleChange: PropTypes.func,

  /**
   * 是否支持 esc 按键关闭弹层
   */
  canCloseByEsc: PropTypes.bool
});

_defineProperty(Modal, "defaultProps", {
  prefix: 'next-',
  sideDrawerWidth: 400,
  titleEditTooltip: '点击即可编辑',
  onClose: function onClose() {},
  onSideDrawerVisibleChange: function onSideDrawerVisibleChange() {},
  onEditTitleChange: function onEditTitleChange() {},
  canCloseByEsc: true
});

export default ConfigProvider.config(Modal);