<template>
  <wrapper
    fill
    margin
    padding
    background
  >
    <schema-table
      ref="table"
      :schema="schema"
    />
    <confirm-dialog
      ref="editDialog"
      title="新增素材包"
      @confirm="onSave"
    >
      <div class="c-grid-form u-align-self--center">
        <span class="c-grid-form__label u-required">名称</span>
        <el-input
          v-model.trim="dataset.name"
          placeholder="最多30个字符"
          maxlength="30"
          clearable
        />
      </div>
    </confirm-dialog>
    <table-dialog
      ref="assetDialog"
      title="上播内容"
      :schema="assetSchema"
    />
    <selection-table-dialog
      ref="assetTableDialog"
      title="上播内容选择"
      message="请选择上播内容"
      :schema="assetTableSchema"
      @confirm="onChoosenAsset"
    />
    <table-dialog
      ref="deviceDialog"
      title="关联的设备"
      :schema="deviceSchema"
      @row-click="onToggleSelection"
      @selection-change="onSelectionChange"
    />
    <radio-table-dialog
      ref="devicesDialog"
      title="绑定设备"
      message="请选择设备"
      :schema="devicesSchema"
      append-to-body
      @confirm="onChoosenDevice"
    />
    <preview-dialog ref="previewDialog" />
  </wrapper>
</template>

<script>
import {
  AssetTagInfo,
  AssetType,
  AssetTypeInfo
} from '@/constant'
import {
  parseDuration,
  getAssetThumb,
  getAssetDuration
} from '@/utils'
import { getDevices } from '@/api/device'
import {
  getDatasets,
  addDataset,
  updateDataset,
  getDataset,
  deleteDataset,
  bindAssetsToDataset,
  unbindAssetsFromDataset,
  updateDatasetAssetDuration,
  getDevicesByDataset,
  bindDatasetToDevice,
  unbindDatasetByDevices,
  unbindDatasetByDevice
} from './api'
import { assetPublicTableMixin } from '@/mixins/asset-table'

export default {
  name: 'DatasetTenant',
  mixins: [assetPublicTableMixin],
  data () {
    return {
      schema: {
        buttons: [
          { type: 'add', on: this.onAdd }
        ],
        list: getDatasets,
        cols: [
          { prop: 'name', label: '名称', render: (data, h) => h('edit-input', {
            props: {
              value: `${data.name}`
            },
            on: { edit: val => this.onEditName(data, val) }
          }), 'class-name': 'c-edit-column' },
          // { label: '使用情况', type: 'tag', render: ({ delFlag }) => {
          //   return {
          //     type: ['primary', 'success'][delFlag],
          //     label: ['暂未使用', '已使用'][delFlag]
          //   }
          // }, align: 'center' },
          { type: 'invoke', render: [
            { label: '上播内容', on: this.onEdit },
            { label: '关联设备', on: this.onViewDevices },
            { label: '删除', on: this.onDel }
          ], width: 240 }
        ]
      },
      assetSchema: {
        nonPagination: true,
        list: this.getAssetsByDataset,
        transform: this.transformDatasetAsset,
        buttons: [
          { type: 'add', on: this.onAddAsset }
        ],
        cols: [
          { prop: 'tagInfo', label: '类型', align: 'center', width: 80 },
          { prop: 'typeName', label: '文件', align: 'center', width: 80 },
          { prop: 'file', label: '', type: 'asset', on: this.onViewAsset },
          { prop: 'name', label: '' },
          { label: '上播时长(s)', render: (data, h) => data.type === AssetType.IMAGE
            ? h('edit-input', {
              staticClass: 'border',
              props: {
                value: `${data.adDuration}`,
                align: 'center'
              },
              on: {
                edit: val => this.onEditAssetDuration(data, val)
              }
            })
            : parseDuration(data.adDuration), width: 100, align: 'center' },
          { type: 'invoke', render: [
            { label: '查看', on: this.onViewAsset },
            { label: '移除', on: this.onDelAsset }
          ] }
        ]
      },
      deviceSchema: {
        list: getDevicesByDataset,
        buttons: [
          { type: 'add', label: '绑定设备', on: this.onBindDevice },
          { icon: 'el-icon-scissors', label: '解绑', on: this.onUnbindDevices }
        ],
        cols: [
          { type: 'selection' },
          { prop: 'name', label: '名称' },
          { prop: 'address', label: '地址', 'min-width': 120 },
          { type: 'invoke', render: [
            { label: '解绑', on: this.onUnbind }
          ] }
        ]
      },
      devicesSchema: {
        list: getDevices,
        filters: [
          { key: 'name', type: 'search', placeholder: '设备名称' }
        ],
        cols: [
          { prop: 'name', label: '设备名称' },
          { prop: 'address', label: '地址' }
        ]
      },
      dataset: {}
    }
  },
  methods: {
    onAdd () {
      this.dataset = { name: '' }
      this.$refs.editDialog.show()
    },
    onSave (done) {
      const { name } = this.dataset
      if (!name) {
        this.$message({
          type: 'warning',
          message: '请填写素材包名称'
        })
        return
      }
      addDataset({ name }).then(({ data }) => {
        done()
        this.onEdit({ id: data })
        this.$refs.table.pageTo(1)
      })
    },
    onEditName (dataset, { newVal, oldVal }) {
      if (newVal === oldVal) {
        return
      }
      if (!newVal) {
        this.$message({
          type: 'warning',
          message: '请填写素材包名称'
        })
        return
      }
      dataset.name = newVal
      updateDataset({
        id: dataset.id,
        name: newVal
      }).catch(() => {
        dataset.name = oldVal
      })
    },
    onEdit ({ id }) {
      this.$datasetId = id
      this.$refs.assetDialog.show()
    },
    getAssetsByDataset () {
      return getDataset(this.$datasetId).then(({ data: { mediaList } }) => {
        return {
          data: mediaList
        }
      })
    },
    transformDatasetAsset (asset) {
      asset.tagInfo = AssetTagInfo[asset.tag]
      asset.typeName = AssetTypeInfo[asset.type]
      asset.file = {
        type: asset.type,
        url: asset.keyName,
        thumb: getAssetThumb(asset.minioData)
      }
      asset.name = asset.minioData.originalName
      return asset
    },
    onAddAsset () {
      this.$refs.assetTableDialog.show()
    },
    onChoosenAsset ({ value, done }) {
      bindAssetsToDataset(this.$datasetId, value.map(asset => {
        const { tag, type, keyName } = asset
        return {
          tag,
          type,
          keyName,
          adDuration: getAssetDuration(asset)
        }
      })).then(() => {
        done()
        this.$refs.assetDialog.getTable().pageTo()
      })
    },
    onEditAssetDuration (asset, { newVal, oldVal }) {
      if (!newVal || !/^\d+$/.test(newVal) || Number(newVal) < 1) {
        return
      }
      if (newVal !== oldVal) {
        asset.adDuration = Number(newVal)
        updateDatasetAssetDuration(asset.relationId, asset.adDuration).catch(() => {
          asset.adDuration = oldVal
        })
      }
    },
    onDelAsset ({ keyName }) {
      unbindAssetsFromDataset(this.$datasetId, [keyName]).then(() => {
        this.$refs.assetDialog.getTable().pageTo()
      })
    },
    onViewDevices ({ id }) {
      this.$datasetId = id
      this.$selectionItems = null
      this.$refs.deviceDialog.show({ datasetId: id })
    },
    onDel (dataset) {
      deleteDataset(dataset).then(() => {
        this.$refs.table.decrease(1)
      })
    },
    onUnbind (device) {
      unbindDatasetByDevice(device).then(() => {
        this.$refs.deviceDialog.getTable().decrease(1)
      })
    },
    onUnbindDevices () {
      if (this.$selectionItems?.length) {
        unbindDatasetByDevices(this.$selectionItems.map(({ id }) => id)).then(() => {
          this.$refs.deviceDialog.getTable().decrease(this.$selectionItems.length)
          this.$selectionItems = null
        })
      } else {
        this.$message({
          type: 'warning',
          message: '请先选择需要解绑的设备'
        })
      }
    },
    onToggleSelection (row) {
      this.$refs.table.getInst().toggleRowSelection(row)
    },
    onSelectionChange (val) {
      this.$selectionItems = val
    },
    onBindDevice () {
      this.$refs.devicesDialog.show()
    },
    onChoosenDevice ({ value, done }) {
      bindDatasetToDevice({
        deviceId: value.id,
        datasetId: this.$datasetId
      }).then(() => {
        done()
        this.$refs.deviceDialog.getTable().pageTo(1)
      })
    }
  }
}
</script>
