import { createVNode as _createVNode } from "vue";
import { isLeaf, scrollIntoParentView, toPathKey } from '../utils/commonUtil';
import Checkbox from './Checkbox';
import { SEARCH_MARK } from '../hooks/useSearchOptions';
import { useInjectCascader } from '../context';
import { cloneElement } from '../../_util/vnode';
import { computed, defineComponent, ref, watch } from 'vue';
export const FIX_LABEL = '__cascader_fix_label__';
export const columnProps = () => ({
  prefixCls: String,
  multiple: Boolean,
  options: Array,
  activeValue: [String, Number],
  prevValuePath: Array,
  onToggleOpen: Function,
  onSelect: Function,
  onActive: Function,
  checkedSet: Object,
  halfCheckedSet: Object,
  loadingKeys: Array,
  isSelectable: Function
});
const Column = defineComponent({
  name: 'Column',
  inheritAttrs: false,
  props: columnProps(),
  setup(props) {
    const menuPrefixCls = computed(() => `${props.prefixCls}-menu`);
    const menuItemPrefixCls = computed(() => `${props.prefixCls}-menu-item`);
    const menuRef = ref();
    const {
      fieldNames,
      changeOnSelect,
      expandTrigger,
      expandIcon: expandIconRef,
      loadingIcon: loadingIconRef,
      dropdownMenuColumnStyle,
      customSlots
    } = useInjectCascader();
    watch([() => props.activeValue, () => menuItemPrefixCls.value, () => menuRef.value], () => {
      setTimeout(() => {
        if (menuRef.value) {
          const selector = `.${menuItemPrefixCls.value}-active`;
          const activeElement = menuRef.value.querySelector(selector);
          if (activeElement) {
            scrollIntoParentView(activeElement);
          }
        }
      }, 0);
    }, {
      immediate: true
    });
    // ============================ Render ============================
    return () => {
      var _a, _b, _c, _d, _e, _f;
      const {
        prefixCls,
        multiple,
        options,
        activeValue,
        prevValuePath,
        onToggleOpen,
        onSelect,
        onActive,
        checkedSet,
        halfCheckedSet,
        loadingKeys,
        isSelectable
      } = props;
      const expandIcon = (_a = expandIconRef.value) !== null && _a !== void 0 ? _a : (_c = (_b = customSlots.value).expandIcon) === null || _c === void 0 ? void 0 : _c.call(_b);
      const loadingIcon = (_d = loadingIconRef.value) !== null && _d !== void 0 ? _d : (_f = (_e = customSlots.value).loadingIcon) === null || _f === void 0 ? void 0 : _f.call(_e);
      const hoverOpen = expandTrigger.value === 'hover';
      return _createVNode("ul", {
        "class": menuPrefixCls.value,
        "role": "menu",
        "ref": menuRef
      }, [options.map(option => {
        var _a, _b;
        const {
          disabled
        } = option;
        const searchOptions = option[SEARCH_MARK];
        const label = (_a = option[FIX_LABEL]) !== null && _a !== void 0 ? _a : option[fieldNames.value.label];
        const value = option[fieldNames.value.value];
        const isMergedLeaf = isLeaf(option, fieldNames.value);
        // Get real value of option. Search option is different way.
        const fullPath = searchOptions ? searchOptions.map(opt => opt[fieldNames.value.value]) : [...prevValuePath, value];
        const fullPathKey = toPathKey(fullPath);
        const isLoading = loadingKeys.includes(fullPathKey);
        // >>>>> checked
        const checked = checkedSet.has(fullPathKey);
        // >>>>> halfChecked
        const halfChecked = halfCheckedSet.has(fullPathKey);
        // >>>>> Open
        const triggerOpenPath = () => {
          if (!disabled && (!hoverOpen || !isMergedLeaf)) {
            onActive(fullPath);
          }
        };
        // >>>>> Selection
        const triggerSelect = () => {
          if (isSelectable(option)) {
            onSelect(fullPath, isMergedLeaf);
          }
        };
        // >>>>> Title
        let title;
        if (typeof option.title === 'string') {
          title = option.title;
        } else if (typeof label === 'string') {
          title = label;
        }
        // >>>>> Render
        return _createVNode("li", {
          "key": fullPathKey,
          "class": [menuItemPrefixCls.value, {
            [`${menuItemPrefixCls.value}-expand`]: !isMergedLeaf,
            [`${menuItemPrefixCls.value}-active`]: activeValue === value,
            [`${menuItemPrefixCls.value}-disabled`]: disabled,
            [`${menuItemPrefixCls.value}-loading`]: isLoading
          }],
          "style": dropdownMenuColumnStyle.value,
          "role": "menuitemcheckbox",
          "title": title,
          "aria-checked": checked,
          "data-path-key": fullPathKey,
          "onClick": () => {
            triggerOpenPath();
            if (!multiple || isMergedLeaf) {
              triggerSelect();
            }
          },
          "onDblclick": () => {
            if (changeOnSelect.value) {
              onToggleOpen(false);
            }
          },
          "onMouseenter": () => {
            if (hoverOpen) {
              triggerOpenPath();
            }
          },
          "onMousedown": e => {
            // Prevent selector from blurring
            e.preventDefault();
          }
        }, [multiple && _createVNode(Checkbox, {
          "prefixCls": `${prefixCls}-checkbox`,
          "checked": checked,
          "halfChecked": halfChecked,
          "disabled": disabled,
          "onClick": e => {
            e.stopPropagation();
            triggerSelect();
          }
        }, null), _createVNode("div", {
          "class": `${menuItemPrefixCls.value}-content`
        }, [((_b = customSlots.value) === null || _b === void 0 ? void 0 : _b.optionRender) ? customSlots.value.optionRender(option) : label]), !isLoading && expandIcon && !isMergedLeaf && _createVNode("div", {
          "class": `${menuItemPrefixCls.value}-expand-icon`
        }, [cloneElement(expandIcon)]), isLoading && loadingIcon && _createVNode("div", {
          "class": `${menuItemPrefixCls.value}-loading-icon`
        }, [cloneElement(loadingIcon)])]);
      })]);
    };
  }
});
export default Column;