import _objectSpread from "@babel/runtime/helpers/esm/objectSpread2";
var __rest = this && this.__rest || function (s, e) {
  var t = {};
  for (var p in s) if (Object.prototype.hasOwnProperty.call(s, p) && e.indexOf(p) < 0) t[p] = s[p];
  if (s != null && typeof Object.getOwnPropertySymbols === "function") for (var i = 0, p = Object.getOwnPropertySymbols(s); i < p.length; i++) {
    if (e.indexOf(p[i]) < 0 && Object.prototype.propertyIsEnumerable.call(s, p[i])) t[p[i]] = s[p[i]];
  }
  return t;
};
import { computed, defineComponent, ref, toRef, createVNode as _createVNode } from 'vue';
import { colorPickerProps } from './interface';
import { initDefaultProps } from '../_util/props-util';
import useConfigInject from '../config-provider/hooks/useConfigInject';
import useMergedState from '../_util/hooks/useMergedState';
import useModeColor from './hooks/useModeColor';
import { genAlphaColor, generateColor, getColorAlpha } from './util';
import { AggregationColor } from './color';
import { FormItemInputContext } from '../form/FormItemContext';
import { getMergedStatus, getStatusClassNames } from '../_util/statusUtils';
import { useCompactItemContext } from '../space/Compact';
import useSize from '../config-provider/hooks/useSize';
import classNames from '../_util/classNames';
import Popover from '../popover';
import ColorPickerPanel from './ColorPickerPanel';
import ColorTrigger from './components/ColorTrigger';
import useStyle from './style';
import { withInstall } from '../_util/type';
const ColorPicker = defineComponent({
  name: 'AColorPicker',
  props: initDefaultProps(colorPickerProps(), {
    trigger: 'click',
    placement: 'bottomLeft',
    open: undefined,
    arrow: true
  }),
  setup(props, {
    slots
  }) {
    const {
      prefixCls,
      direction,
      disabled
    } = useConfigInject('color-picker', props);
    const mergedDisabled = computed(() => {
      var _a;
      return (_a = props.disabled) !== null && _a !== void 0 ? _a : disabled.value;
    });
    const [popupOpen, setPopupOpen] = useMergedState(false, {
      value: toRef(props, 'open'),
      postState: openData => !mergedDisabled.value && openData,
      onChange: props.onOpenChange
    });
    const [formatValue, setFormatValue] = useMergedState(props.format, {
      value: toRef(props, 'format'),
      defaultValue: props.defaultFormat,
      onChange: props.onFormatChange
    });
    // ================== Value & Mode =================
    const {
      postColor: mergedColor,
      setColor,
      postMode: modeState,
      setModeState,
      modeOptionList: modeOptions
    } = useModeColor(props.defaultValue, toRef(props, 'value'), toRef(props, 'mode'));
    const isAlphaColor = computed(() => getColorAlpha(mergedColor.value) < 100);
    // ==================== Change =====================
    // To enhance user experience, we cache the gradient color when switch from gradient to single
    // If user not modify single color, we will use the cached gradient color.
    const cachedGradientColor = ref(null);
    const onInternalChangeComplete = color => {
      if (props.onChangeComplete) {
        let changeColor = generateColor(color);
        if (props.disabledAlpha && isAlphaColor.value) {
          changeColor = genAlphaColor(color);
        }
        props.onChangeComplete(changeColor);
      }
    };
    const onInternalChange = (data, changeFromPickerDrag) => {
      var _a, _b;
      let color = generateColor(data);
      if (props.disabledAlpha && isAlphaColor.value) {
        color = genAlphaColor(color);
      }
      setColor(color);
      cachedGradientColor.value = null;
      (_a = props.onChange) === null || _a === void 0 ? void 0 : _a.call(props, color, color.toCssString());
      (_b = props['onUpdate:value']) === null || _b === void 0 ? void 0 : _b.call(props, color);
      if (!changeFromPickerDrag) {
        onInternalChangeComplete(color);
      }
    };
    // =================== Gradient ====================
    const activeIndex = ref(0);
    const gradientDragging = ref(false);
    const onInternalModeChange = newMode => {
      setModeState(newMode);
      if (newMode === 'single' && mergedColor.value.isGradient()) {
        activeIndex.value = 0;
        onInternalChange(new AggregationColor(mergedColor.value.getColors()[0].color));
        cachedGradientColor.value = mergedColor.value;
      } else if (newMode === 'gradient' && !mergedColor.value.isGradient()) {
        const baseColor = isAlphaColor.value ? genAlphaColor(mergedColor.value) : mergedColor.value;
        onInternalChange(new AggregationColor(cachedGradientColor.value || [{
          percent: 0,
          color: baseColor
        }, {
          percent: 100,
          color: baseColor
        }]));
      }
    };
    // ================== Form Status ==================
    const formItemInputContext = FormItemInputContext.useInject();
    const mergedStatus = computed(() => getMergedStatus(formItemInputContext.status));
    // ==================== Compact ====================
    const {
      compactSize,
      compactItemClassnames
    } = useCompactItemContext(toRef(props, 'prefixCls'), direction);
    // ===================== Style =====================
    const [wrapSSR, hashId] = useStyle(prefixCls);
    const mergedSize = useSize(ctx => {
      var _a, _b;
      return (_b = (_a = props.size) !== null && _a !== void 0 ? _a : compactSize.value) !== null && _b !== void 0 ? _b : ctx;
    });
    return () => {
      var _a;
      const {
          mode,
          value,
          defaultValue,
          format,
          defaultFormat,
          allowClear = false,
          presets,
          trigger = 'click',
          open,
          disabled,
          placement = 'bottomLeft',
          arrow = true,
          panelRender,
          showText,
          style,
          className,
          size: customizeSize,
          rootClassName,
          prefixCls: customizePrefixCls,
          styles,
          disabledAlpha = false,
          onFormatChange,
          onChange,
          onClear,
          onOpenChange,
          onChangeComplete,
          getPopupContainer,
          autoAdjustOverflow = true,
          destroyTooltipOnHide,
          disabledFormat
        } = props,
        rest = __rest(props, ["mode", "value", "defaultValue", "format", "defaultFormat", "allowClear", "presets", "trigger", "open", "disabled", "placement", "arrow", "panelRender", "showText", "style", "className", "size", "rootClassName", "prefixCls", "styles", "disabledAlpha", "onFormatChange", "onChange", "onClear", "onOpenChange", "onChangeComplete", "getPopupContainer", "autoAdjustOverflow", "destroyTooltipOnHide", "disabledFormat"]);
      const rtlCls = {
        [`${prefixCls.value}-rtl`]: direction.value
      };
      const mergedRootCls = classNames(props.rootClassName, rtlCls);
      const mergedCls = classNames(getStatusClassNames(prefixCls.value, mergedStatus.value), {
        [`${prefixCls.value}-sm`]: mergedSize.value === 'small',
        [`${prefixCls.value}-lg`]: mergedSize.value === 'large'
      }, compactItemClassnames.value, mergedRootCls, className, hashId.value);
      const mergedPopupCls = classNames(prefixCls.value, mergedRootCls);
      const popoverProps = {
        open: popupOpen.value,
        trigger,
        placement,
        arrow,
        getPopupContainer,
        autoAdjustOverflow,
        destroyTooltipOnHide
      };
      return wrapSSR(_createVNode(Popover, _objectSpread({
        "style": styles === null || styles === void 0 ? void 0 : styles.popup,
        "overlayInnerStyle": styles === null || styles === void 0 ? void 0 : styles.popupOverlayInner,
        "onOpenChange": visible => {
          if (!visible || !mergedDisabled.value) {
            setPopupOpen(visible);
          }
        },
        "overlayClassName": mergedPopupCls,
        "class": rootClassName,
        "content": _createVNode(ColorPickerPanel, {
          "mode": modeState.value,
          "onModeChange": onInternalModeChange,
          "modeOptions": modeOptions.value,
          "prefixCls": prefixCls.value,
          "value": mergedColor.value,
          "allowClear": allowClear,
          "disabled": mergedDisabled.value,
          "disabledAlpha": disabledAlpha,
          "presets": presets,
          "panelRender": panelRender,
          "format": formatValue.value,
          "onFormatChange": setFormatValue,
          "onChange": onInternalChange,
          "onChangeComplete": onInternalChangeComplete,
          "onClear": onClear,
          "activeIndex": activeIndex.value,
          "onActive": nextVal => activeIndex.value = nextVal,
          "gradientDragging": gradientDragging.value,
          "onGradientDragging": dragging => gradientDragging.value = dragging,
          "disabledFormat": disabledFormat
        }, null)
      }, popoverProps), {
        default: () => [((_a = slots.default) === null || _a === void 0 ? void 0 : _a.call(slots)) || _createVNode(ColorTrigger, _objectSpread(_objectSpread({
          "activeIndex": popupOpen.value ? activeIndex.value : -1,
          "open": popupOpen.value,
          "className": mergedCls,
          "style": style,
          "prefixCls": prefixCls.value,
          "disabled": mergedDisabled.value,
          "showText": showText
        }, rest), {}, {
          "color": mergedColor.value
        }), null)]
      }));
    };
  }
});
export default withInstall(ColorPicker);