<template>
  <ui-list v-on="$listeners" v-bind="$attrs">
    <template v-for="slot of otherSlots" v-slot:[slot]="scope">
      <slot :name="slot" v-bind="scope" />
    </template>

    <slot name="prepend" />

    <draggable
      v-model="valueWrap"
      :animation="150"
      handle=".sortable-handle"
      ghostClass="sortable-ghost"
    >
      <slot />
    </draggable>

    <slot name="append" />
  </ui-list>
</template>

<script lang="ts">
import { Component, Prop, Vue } from 'vue-property-decorator'
import UiList from './UiList.vue'
import Draggable from 'vuedraggable'

const USED_SLOTS = ['default', 'prepend', 'append']
function isSlotNonUsed(slot: string): boolean {
  return !USED_SLOTS.includes(slot)
}

@Component({ inheritAttrs: false, components: { UiList, Draggable } })
export default class UiSortableList<T> extends Vue {
  @Prop(Array) value?: T[]

  get valueWrap() {
    return this.value
  }
  set valueWrap(value) {
    this.$emit('input', value)
  }

  get otherSlots() {
    return Object.keys(this.$scopedSlots).filter(isSlotNonUsed)
  }
}
</script>

<style scoped>
::v-deep .sortable-ghost {
  opacity: 0;
}
</style>
