<template>
  <div
    class="ui-cascader"
    :class="[{'is-adaption': adaption, 'is-editable': editable}, 'ui-cascader--' + size]"
  >
    <template v-if="editable">
      <template v-if="adaption">
        <span class="ui-cascader__handle">
          <span v-if="!isEmpty" class="ui-cascader__current">{{ displayValue }}</span>
          <span v-else class="ui-cascader__placeholder">
            {{ placeholder }}
          </span>
          <span v-if="!isEmpty && clearable" class="ui-cascader__clear" @click="handleClearClick"></span>
          <span v-else class="ui-cascader__arrow"></span>
        </span>
      </template>
      <el-cascader
        ref="control"
        class="ui-cascader__control"
        :props="innerProps"
        :placeholder="placeholder"
        v-model="innerValue"
        :options="options"
      ></el-cascader>
    </template>
    <template v-else>
      {{ showText }}
    </template>
  </div>
</template>
<script>
import Cascader from 'element-ui/lib/cascader'
import 'element-ui/lib/theme-chalk/cascader.css'
import { getNodeByValue } from './utils'

export default {
  name: 'UiCascader',
  components: {
    ElCascader: Cascader
  },
  props: {
    adaption: {
      type: Boolean,
      default: false
    },
    editable: {
      type: Boolean,
      default: true
    },
    clearable: {
      type: Boolean,
      default: false
    },
    multiple: {
      type: Boolean,
      default: false
    },
    textField: {
      type: String,
      default: 'text'
    },
    valueField: {
      type: String,
      default: 'value'
    },
    childrenField: {
      type: String,
      default: 'children'
    },
    value: {
      type: [String, Array],
      default: undefined
    },
    size: {
      type: String,
      default: 'medium'
    },
    placeholder: {
      type: String
    },
    queryMethod: {
      type: Function
    }
  },
  data() {
    return {
      loading: false,
      options: [],
      displayValue: ''
    }
  },
  computed: {
    innerValue: {
      get() {
        return this.value
      },
      set(val) {
        this.$emit('input', val)
      }
    },
    innerProps() {
      return {
        label: this.textField,
        value: this.valueField,
        children: this.childrenField
      }
    },
    showText() {
      if (!this.innerValue) {
        return
      }
      if (!this.innerValue.length) {
        return
      }
      return this.innerValue.map(val => {
        const node = getNodeByValue(val, this.options, this.valueField, this.childrenField)
        if (!node) {
          return val
        } else {
          return node[this.textField]
        }
      }).join(' / ')
    },
    isEmpty() {
      return !this.value || !this.value.length
    }
  },
  created() {
    this.loadOptions()
  },
  mounted() {
    if (this.adaption) {
      this.$refs.control.$watch('presentText', (value) => {
        this.displayValue = value
      })
      this.displayValue = this.$refs.control.presentText
    }
  },
  methods: {
    loadOptions() {
      if (!this.queryMethod) {
        return Promise.reject()
      }
      this.loading = true
      this.queryMethod().then(rs => {
        this.options = rs
      }).finally(() => {
        this.loading = false
      })
    },
    handleClearClick() {
      this.innerValue = null
    }
  }
}
</script>
<style lang="less">
.ui-cascader__control{
  width: 100%;
}
.ui-cascader{
  font-size: 14px;
  &.is-adaption{
    display: inline-block;
    vertical-align: top;
    position: relative;
    overflow: hidden;
    &.ui-cascader--medium{
      height: 40px;
      line-height: 40px;
    }
    &.ui-cascader--small{
      height: 32px;
      line-height: 32px;
    }
    &.ui-cascader--mini{
      height: 28px;
      line-height: 28px;
    }
    .ui-cascader__handle{
      display: block;
      padding-right: 18px;
      position: relative;
    }
    .ui-cascader__arrow{
      position: absolute;
      top: 50%;
      right: 4px;
      transform: translateY(-50%);
      border: 4px solid #999;
      border-left-color: transparent;
      border-right-color: transparent;
      border-bottom: 0;
    }
    .ui-cascader__control{
      position: absolute;
      left: 0;
      top: 0;
      bottom: 0;
      overflow: hidden;
      z-index: 3;
      opacity: 0;
      .el-cascader__tags,
      .el-input{
        height: 100%;
      }
      &:after {
        content: '';
        position: absolute;
        left: 0;
        top: 0;
        bottom: 0;
        right: 0;
        z-index: 3;
      }
    }
    .ui-cascader__clear{
      display: inline-block;
      position: absolute;
      width: 14px;
      height: 14px;
      background-color: #ccc;
      border-radius: 50%;
      top: 50%;
      right: 0;
      margin-top: -7px;
      transform: rotate(45deg);
      z-index: 10;
      cursor: pointer;
      &:after,&:before{
        content: '';
        position: absolute;
        left: 50%;
        top: 50%;
        transform: translate(-50%, -50%);
        background-color: #fff;
      }
      &:after {
        width: 9px;
        height: 1px;
      }
      &:before {
        width: 1px;
        height: 9px;
      }
      &:hover {
        background-color: #999;
      }
    }
  }
}
</style>
