<template>
  <div class="hoo-select pos-rel"
       id="hoo-select"
       :class="theme==='dark'?'dark-select-wrap':''"
       @click.stop.prevent="selectClickHandler"
       :style="dropdownStyle">
    <el-input v-model.trim="search"
              :clearable="clearable"
              @input="inputHandler"
              :placeholder="$t('ht.common.pleaseSelect')">
      <div slot="prefix"
           ref="prefixRef">
        <slot name="showInputPrefix">
          <i class="el-icon-user"></i>
        </slot>
      </div>
      <i slot="suffix"
         class="el-icon-arrow-down"></i>
    </el-input>
    <div class="hoo-dropdown hoo-light-scrollbar pos-as"
         ref="downRef"
         id="hoo-dropdown">
      <slot>
        <div class="dropdown-input"
             v-if="isShowSearch">
          <el-input v-model.trim="listFilter"
                    :clearable="clearable"
                    :placeholder="$t('ht.common.selectSearch')">
            <template slot="prefix">
              <slot class="dropdownSearchInputPrefix">
                <i class="el-icon-search"></i>
              </slot>
            </template>
          </el-input>
        </div>

        <ul class="dropdown-list">
          <li v-for="(item,index) in listFormat"
              @click.stop.prevent="selectRow(item)"
              :key="String(index)+index">
            <slot name="dropdownListRowPrefix"><i class="el-icon-user"></i></slot>
            {{item&&item[showField]}}
          </li>
          <li v-if="isRichBottom"
              class="more-text">{{$t(richBottomText)}}</li>
        </ul>
      </slot>
    </div>
  </div>
</template>

<script>
export default {
  name: 'ht-select',
  data () {
    return {
      search: '',
      isRichBottom: false,
      listFilter: '',
      selectDom: '',
      curSelectRow: {}
    }
  },
  props: {
    // 分页总数据
    total: {
      type: [Number, String],
      default: 10,
      validate: (value) => {
        return typeof value === 'string' || typeof value === 'number'
      }
    },
    // 距离底部多少触发触底事件
    richBottom: {
      type: [String, Number],
      default: 10
    },
    // 是否显示搜索
    isShowSearch: {
      type: Boolean,
      default: true
    },
    // 需要展示的字段
    showField: {
      type: String,
      default: 'name'
    },
    // 列表数据
    list: {
      type: Array,
      default: () => {
        return [
          {
            id: 1,
            name: '技术中台1'
          },
          {
            id: 2,
            name: '技术中台2'
          },
          {
            id: 3,
            name: '技术中台3'
          },
          {
            id: 4,
            name: '技术中台4'
          },
          {
            id: 5,
            name: '技术中台5'
          }
        ]
      }
    },
    // 触发下拉方式
    trigger: {
      type: String,
      default: 'click',
      validator: (value) => {
        const arr = ['click', 'hover']
        return arr && arr.includes(value)
      }
    },
    clearable: {
      type: Boolean,
      default: true
    },
    curValue: {
      type: String,
      default: ''
    },
    // 主题色
    theme: {
      type: String,
      default: 'light',
      validate: value => {
        return ['light', 'dark'].includes(value)
      }
    },
    // 传入下拉列表高度
    height: {
      type: Number,
      default: 150
    }
  },
  computed: {
    richBottomText () {
      let total = this.total
      let listLength = this.list?.length
      if (+total === +listLength) {
        return 'ht.common.selectSearch_2'
      }
      return 'ht.common.selectSearch_1'
    },
    listFormat () {
      if (!this.list || !this.list.length) return
      if (this.listFilter) {
        return (
          this.list &&
          this.list.filter((item) => {
            let regex = new RegExp(this.listFilter, 'gi')
            const { name } = item || {}
            return regex.test(name)
          })
        )
      }
      return this.list
    },

    dropdownStyle () {
      let height = this.trigger === 'click' ? 0 : this.height
      let theme = this.theme === 'light' ? '#fff' : '#000'
      return {
        '--height': `${height}px`,
        '--theme-bg': theme
      }
    }
  },
  watch: {
    curValue: {
      handler () {
        this.search = this.curValue
      },
      immediate: true
    }
  },
  methods: {
    async selectRow (row) {
      this.search = row && row[this.showField]
      this.curSelectRow = row || {}
      this.hiddenDropdown()
      this.inputHandler()
    },
    async clickOutHiden (e) {
      let target = e.target
      if (!target) return
      const hooSearch = target && target.getAttribute('id')
      // 点击的目标元素不需要关闭的return
      if (hooSearch === 'hoo-select') return
      while (target) {
        target = target.parentNode ? target.parentNode : '' // 不断取父节点来替换target
        const id = target && target.getAttribute && target.getAttribute('id')
        // 点击的目标元素不需要关闭的return
        if (id === 'hoo-select') {
          return
        }
      }
      // 发送关闭popup事件
      this.hiddenDropdown()
    },
    async showDropdown (downDom) {
      let dom = this.selectDom
      if (!dom) return
      dom.style.height = `${this.height}px`
    },
    async hiddenDropdown () {
      let dom = this.selectDom
      if (!dom) return
      dom.style.height = 0
    },
    async selectClickHandler (e) {
      this.selectDom =
        e.target.parentNode &&
        e.target.parentNode.parentNode &&
        e.target.parentNode.parentNode.children[1]
      this.showDropdown()
    },
    inputHandler () {
      this.$emit('select', this.curSelectRow)
      this.$emit('update:curValue', this.search)
    },
    async scrollHandler () {
      let downRef = this.$refs?.['downRef']
      if (!downRef) return
      let domTop = downRef.scrollTop
      let cHeight = downRef.clientHeight
      let sHegiht = downRef.scrollHeight
      let limitCopare = domTop + cHeight
      if (limitCopare > sHegiht - this.richBottom) {
        console.log('触底了')
        this.isRichBottom = true
        this.$emit('onRichBottom')
      } else {
        this.isRichBottom = false
      }
    },
    async addScroll () {
      let dom = this.$refs?.['downRef']
      dom.addEventListener('scroll', this.scrollHandler)
    }
  },
  mounted () {
    document.addEventListener('click', this.clickOutHiden)
    this.addScroll()
  },
  beforeDestroy () {
    document.removeEventListener('scroll', this.scrollHandler)
    document.removeEventListener('click', this.clickOutHiden)
  }
}
</script>

<style lang="scss" scoped>
.dark-select-wrap {
  /deep/.el-input__inner {
    color: #fff;
    border: 1px solid #7e7676 !important;
  }
  /deep/ input::-webkit-input-placeholder {
    -webkit-text-fill-color: #fff;
  }
  /deep/ input::-moz-input-placeholder {
    -webkit-text-fill-color: #fff;
  }
  /deep/ input::-ms-input-placeholder {
    -webkit-text-fill-color: #fff;
  }
  .dropdown-list li:hover {
    background: #7e7676 !important;
  }
  #hoo-dropdown {
    color: #fff;
  }
  .dropdown-input {
    border-bottom: 1px solid #7e7676 !important;
  }
}
.hoo-select {
  ::-webkit-scrollbar {
    background-color: transparent;
    width: 12px;
  }
  ::-webkit-scrollbar-thumb {
    background-color: rgba(0, 0, 0, 0.5);
    border-radius: 8px;
    background-clip: content-box;
    border: 2px solid transparent;
  }

  &.prefix-select {
    /deep/.el-input__inner {
      padding-left: 60px;
    }
  }
  .select-coin-icon {
    width: 25px;
    height: 25px;
    display: block;
    border-radius: 50%;
    &:nth-child(2) {
      position: relative;
      left: -5px;
    }
  }
  .more-text {
    text-align: center;
    font-size: 12px;
    color: #e5e5e5;
  }
  /deep/.el-input__prefix {
    display: flex;
    align-items: center;
  }
  /deep/.el-input__inner {
    background: var(--theme-bg);
    border-radius: 4px;
    border: 1px solid #dcdfe6;
    height: 30px;
  }
  /deep/.el-input__inner::placeholder {
    font-family: 'PingFang SC';
    font-style: normal;
    font-weight: 400;
    font-size: 14px;
    line-height: 20px;
    color: #7a8793;
  }
  .arrow-down {
    width: 8.66px;
    height: 5.5px;
    vertical-align: middle;
    padding-right: 15px;
  }

  /deep/.dropdown-input {
    padding: 10px 20px;
    box-sizing: border-box;
    border-bottom: 1px solid #dcdfe6;

    .divide {
      border-bottom: 1px solid #dcdfe6;
      margin-top: 10px;
    }
  }
  /deep/.el-input__suffix {
    display: flex;
    align-items: center;
  }
  &:hover {
    .hoo-dropdown {
      height: var(--height);
      overflow-y: auto;
    }
  }
  .hoo-dropdown {
    transition: all 0.3s;
    z-index: 3000;
    left: 0;
    right: 0;
    top: 47px;
    overflow: hidden;
    background: var(--theme-bg);
    box-shadow: 0px 0px 8px rgba(0, 0, 0, 0.15);
    border-radius: 4px;
    height: 0;

    .dropdown-list {
      list-style: none;
      padding: 0 20px 0;
      li {
        line-height: 30px;
        cursor: pointer;
        &:hover {
          background: #f5f5f5;
        }
      }
    }
  }
}
</style>
