<script>
import { REFER } from "../popover-select/api/index";

export default {
  name: "PopoverSelectV2",
  props: {
    // v-model
    value: {
      type: [Array, String, Number],
      require: true,
    },
    // 参照类型 ，对应后端
    referName: {
      type: String,
      require: true,
    },
    // 作为 value 唯一标识的键名，绑定值
    valueKey: {
      type: String,
      dafault: () => {
        return "code";
      },
    },
    // 默认查询参数
    queryParams: {
      type: Function,
      default: () => {},
    },
    // 需映射源数据
    source: {
      type: Object,
      default: () => ({}),
    },
    // 参照内外映射
    dataMapping: {
      type: Object,
      default: () => ({}),
    },
    // 多选
    checkbox: {
      type: Boolean,
      default: false,
    },
    // 参照弹窗标题
    title: {
      type: String,
      dafault: () => {
        return "TITEL";
      },
    },
    // 赋值
    copy: {
      type: Boolean,
      default: () => {
        return false;
      },
    },
    clearable: {
      type: Boolean,
      default: true,
    },
  },
  components: {
    ElSuperTable: () => import("@/components/super-table/index.vue"),
  },
  data() {
    return {
      size: "mini",
      width: "50%",
      page: { pageNum: 1, pageSize: 10, total: 0 },
      visible: false,
      loading: false,
      model: {
        search: "",
        isPage: true,
      },
      data: [],
      selectData: [],
    };
  },
  computed: {
    innerValue: {
      get() {
        return this.value;
      },
      set(value) {
        // const {
        //   $props: { source, dataMapping },
        // } = this;

        // for (let key in dataMapping) {
        //   if (dataMapping[key] === "id" || dataMapping[key] === "code") {
        //     if (source[key] && source[key] !== "") {
        //       source[key] = undefined;
        //     }
        //   }
        // }
        this.$emit("input", value);
      },
    },
    TableColumns() {
      const { referName } = this.$props;
      return require(`../popover-select/components/${referName}`).default;
    },
  },
  watch: {
    innerValue: {
      handler: function (newValue) {
        if (!newValue) {
          const {
            $props: { source, dataMapping },
          } = this;
          for (let key in dataMapping) {
            source[key] = undefined;
          }
          this.$emit("update:source", source);
        }
      },
    },
  },
  methods: {
    // open dialog
    async open() {
      let { disabled } = this.$attrs;
      if (!disabled) {
        this.visible = true;
        await this.useReset();
      }
    },
    // hide dialog
    async hide() {
      this.visible = false;
    },
    // fetch list
    async fetchList(prop, page) {
      try {
        // try
        this.loading = true;
        const { pageNum, pageSize } = page;
        const { referName: type, source, queryParams } = this.$props;
        const { code, rows, total } = await REFER(
          {
            ...prop,
            ...queryParams(source),
            type: type,
          },
          {
            pageNum,
            pageSize,
          }
        );
        if (code === 200) {
          this.data = rows;

          // 处理新增字段无法映射
          let that = this;

          this.TableColumns.forEach(({ item, attr }) => {
            that.data = that.data.map((d) => {
              if (!attr.is && attr.formatter) {
                d[item.key] = attr.formatter(d);
              }

              return d;
            });
          });

          this.page.total = total;
        }
      } catch (err) {
        // catch
        console.error(err);
      } finally {
        // finally
        this.loading = false;
      }
    },
    // reset
    async useReset() {
      this.data = [];
      this.page.pageNum = 1;
      this.page.pageSize = 10;
      this.model.search = null;
      await this.fetchList(this.model, this.page);
    },
    // query
    async useQuery() {
      await this.fetchList(this.model, this.page);
    },
    // auto
    async useAutocomplete(prop, cb) {
      if (prop) {
        this.page.pageSize = 10;
        this.model.search = prop;
        await this.fetchList(this.model, this.page);
        await cb(this.data);
      } else {
        cb([]);
      }
    },
    // select
    useSelect(prop) {
      this.selectData = prop;
    },
    // confirm
    useConfirm(prop) {
      this.hide();

      const {
        $props: { source, checkbox, valueKey, dataMapping },
      } = this;

      if (checkbox) {
        this.selectData = [...prop];
        this.$emit(
          "change",
          this.selectData.map((item) => {
            for (let key in dataMapping) {
              item[key] = item[dataMapping[key]];
            }
            return item;
          }),
          this.$props
        );
      } else {
        for (let key in dataMapping) {
          source[key] = prop[0][dataMapping[key]];
        }
        this.innerValue = prop[0][valueKey];
        this.$emit("update:source", source);
        this.$emit("change", prop[0], this.$props);
      }
    },
    async handleChange() {
      const { referName } = this.$props;
      this.$emit("copyChange", this.innerValue.split(/,|，|\s+/));
    },
    useBlur() {
      const {
        $props: { source, dataMapping },
      } = this;

      for (let key in dataMapping) {
        if (dataMapping[key] === "id" || dataMapping[key] === "code") {
          if (!source[key] || source[key] === "") {
            this.innerValue = "";
          }
        }
      }
    },
    handleClear() {
      this.innerValue = "";
      this.$emit("clear");
    },
    handleKeyupDel() {
      console.log("focus");
      const {
        $props: { source, dataMapping },
      } = this;

      for (let key in dataMapping) {
        if (dataMapping[key] === "id" || dataMapping[key] === "code") {
          if (source[key] && source[key] !== "") {
            source[key] = undefined;
          }
        }
      }
    },
  },
  created() {},
  mounted() {},
  destroyed() {},
};
</script>

<template>
  <div class="popover-select-v2">
    <el-input
      v-if="copy"
      :clearable="clearable"
      v-bind="$attrs"
      v-model="innerValue"
      :size="size"
      @clear="handleClear"
      @change="handleChange"
      @keyup.enter.native="handleChange"
      @keyup.delete.native="handleKeyupDel"
    >
      <i :size="size" class="el-icon-search" slot="suffix" @click="open"> </i>
    </el-input>
    <el-autocomplete
      v-else
      :clearable="clearable"
      v-bind="$attrs"
      v-model="innerValue"
      :value-key="valueKey"
      :fetch-suggestions="useAutocomplete"
      @keyup.delete.native="handleKeyupDel"
      @select="useConfirm([$event])"
      style="width: 100%"
      @blur="useBlur"
      @clear="handleClear"
    >
      <i class="el-icon-search" slot="suffix" @click="open"> </i>
      <template slot-scope="{ item }">
        <p
          style="
            text-overflow: ellipsis;
            overflow: hidden;
            line-height: 15px;
            margin: 5px 0;
          "
        >
          {{ item.name }}
        </p>
        <p
          style="
            font-size: 12px;
            color: #b4b4b4;
            line-height: 15px;
            margin: 5px 0;
          "
        >
          {{ item.code }}
        </p>
      </template>
    </el-autocomplete>
    <el-dialog
      :width="width"
      :visible.sync="visible"
      :show-close="false"
      :close-on-click-modal="false"
      :close-on-press-escape="false"
      append-to-body
    >
      <div slot="title" style="display: flex; justify-content: space-between">
        <el-form
          :size="size"
          :inline="true"
          :model="model"
          @submit.native.prevent
          style="display: flex; flex-direction: column"
        >
          <div>
            <el-form-item prop="search">
              <el-input
                v-model="model.search"
                @change="useQuery"
                @keydown.enter="useQuery"
              >
              </el-input>
            </el-form-item>
            <el-form-item>
              <el-button icon="el-icon-search" @click="useQuery"
                >搜索</el-button
              >
              <el-button icon="el-icon-refresh" @click="useReset"
                >重置</el-button
              >
            </el-form-item>
          </div>
        </el-form>
        <div>
          <el-button
            type="primary"
            :size="$attrs.size"
            :loading="loading"
            @click="useConfirm(selectData)"
          >
            确认
          </el-button>
          <el-button :size="$attrs.size" :loading="loading" @click="hide">
            取消
          </el-button>
        </div>
      </div>
      <div
        v-loading="loading"
        style="height: 40vh; display: flex; margin-top: -30px"
      >
        <el-super-table
          v-model="data"
          :size="size"
          :page="page"
          :columns="TableColumns"
          :radio="!checkbox"
          :checkbox="checkbox"
          pagination
          highlight-current-row
          @pagination="useQuery"
          @row-select="useSelect"
          @row-dblclick="useConfirm([$event])"
        >
        </el-super-table>
      </div>
    </el-dialog>
  </div>
</template>
<style scoped>
.popover-select-v2 .el-autocomplete {
  width: inherit;
}
.popover-select-v2 .el-autocomplete .el-icon-search {
  cursor: pointer;
}
::v-deep .el-table--mini .el-table__cell {
  height: 50px;
}
</style>
