<template>
  <div class="table-box">
    <ProTable ref="proTable" :columns="columns" row-key="id" :request-api="listDataAugmentationApi">
      <!-- 表格 header 按钮 -->
      <template #tableHeader="scope">
        <el-button type="primary" v-auth="['demo:DataAugmentation:add']" icon="CirclePlus" @click="openDialog(1, '视频去抖动新增')"> 新增 </el-button>
        <!--        <el-button type="primary" v-auth="['demo:DataAugmentation:import']" icon="Upload" plain @click="batchAdd"> 导入</el-button>-->
        <!--        <el-button type="primary" v-auth="['demo:DataAugmentation:export']" icon="Download" plain @click="downloadFile"> 导出 </el-button>-->
        <el-button
          type="danger"
          v-auth="['demo:DataAugmentation:remove']"
          icon="Delete"
          plain
          :disabled="!scope.isSelected"
          @click="batchDelete(scope.selectedListIds)"
        >
          批量删除
        </el-button>
      </template>
      <!-- 表格操作 -->
      <template #operation="scope">
        <el-button
          type="primary"
          link
          icon="View"
          @click="startDataAugmentation(scope.row)"
          v-if="scope.row.status == '0' || scope.row.status == '3' || scope.row.status == '4'"
        >
          开始
        </el-button>
        <el-popconfirm title="确定终止此任务吗?" @confirm="stopDataAugmentation(scope.row)" v-if="scope.row.status == '1'">
          <template #reference>
            <el-button type="primary" link icon="View"> 终止 </el-button>
          </template>
        </el-popconfirm>
        <el-button type="primary" link icon="View" @click="compareDataAugmentation(scope.row)" v-if="scope.row.status == '2'"> 预览 </el-button>
        <el-button type="primary" link icon="View" v-auth="['demo:DataAugmentation:query']" @click="openDialog(3, '视频去抖动查看', scope.row)">
          查看
        </el-button>
        <!-- <el-button type="primary" link icon="EditPen" v-auth="['demo:DataAugmentation:edit']" @click="openDialog(2, '视频去抖动编辑', scope.row)">
            编辑
          </el-button> -->
        <el-button type="primary" link icon="Delete" v-auth="['demo:DataAugmentation:remove']" @click="deleteDataAugmentation(scope.row)">
          删除
        </el-button>
      </template>
    </ProTable>
    <FormDialog ref="formDialogRef" />
    <ImportExcel ref="dialogRef" />
    <el-dialog v-model="dialogVisible" :title="dialogTitle" width="80%">
      <el-form>
        <el-form-item label="帧率">
          <el-select v-model="imageFps" placeholder="选择帧率" style="width: 200px" @change="changeFps">
            <el-option label="0" value="0"></el-option>
            <el-option label="5" value="5"></el-option>
            <el-option label="15" value="15"></el-option>
            <el-option label="30" value="30"></el-option>
            <el-option label="60" value="60"></el-option>
          </el-select>
        </el-form-item>
      </el-form>
      <div class="image-dialog" v-if="imageIdx > 0">
        <el-image :src="'data:image/png;base64,' + cacheImages[imageIdx].origin" style="width: 45%"></el-image>
        <el-image :src="'data:image/png;base64,' + cacheImages[imageIdx].stable" style="width: 45%"></el-image>
      </div>
      <div class="image-dialog-btn" v-if="imageFps == 0">
        <el-button type="primary" @click="pre_picture" :disabled="imageIdx <= 1">上一个</el-button>
        <el-button type="primary" @click="next_picture" :disabled="imageIdx >= fileCount">下一个</el-button>
      </div>
    </el-dialog>
  </div>
</template>

<script setup lang="tsx" name="DataAugmentation">
import { ref, reactive, onMounted } from 'vue'
import { useHandleData } from '@/hooks/useHandleData'
import { useDownload } from '@/hooks/useDownload'
import { ElMessageBox, ElMessage } from 'element-plus'
import ProTable from '@/components/ProTable/index.vue'
import ImportExcel from '@/components/ImportExcel/index.vue'
import FormDialog from '@/components/FormDialog/index.vue'
import { ProTableInstance, ColumnProps, EnumProps } from '@/components/ProTable/interface'
import {
  listDataAugmentationApi,
  delDataAugmentationApi,
  addDataAugmentationApi,
  updateDataAugmentationApi,
  importTemplateApi,
  importDataAugmentationDataApi,
  exportDataAugmentationApi,
  getDataAugmentationApi,
  startDataAugmentationApi,
  stopDataAugmentationApi,
  getCompareImageApi,
  getCompareImageCountApi
} from '@/api/modules/demo/dataAugmentation'
import { listDataApi } from '@/api/modules/system/dictData'
const dialogVisible = ref(false)
const taskId = ref('')
const imageIdx = ref(0)
const imageBase64List = ref({
  origin: '',
  stable: ''
})
const inFileCount = ref(0)
const outFileCount = ref(0)
// 直接缓存所有图片
const cacheImages = ref({ 0: { origin: '', stable: '' } })
const dialogTitle = ref('')
const fileCount = ref(0)
const imageFps = ref(0)
const intervalChangeFps: any = ref()
const taskType = ref([])
const taskTypeEnums: EnumProps[] = []

const hyperparameterConfiguration = []
const hyperparameter = ref('')
const getTaskType = async () => {
  const res: any = await listDataApi({
    dictName: '',
    dictType: 'biz_data_augmentation',
    dictLabel: '任务类型',
    pageNum: 0,
    pageSize: 1000
  })
  if (res.data.list.length != 0) {
    taskType.value = res.data.list.map(item => ({
      label: item.dictValue,
      value: item.dictValue
    }))
    res.data.list.forEach(item => {
      taskTypeEnums.push({
        label: item.dictValue,
        value: item.dictValue,
        disabled: false,
        tagType: 'default'
      })
    })
    for (let i = 0; i < taskType.value.length; i++) {
      let dictValue = taskType.value[i].value
      const res: any = await listDataApi({
        dictName: '',
        dictType: 'biz_data_augmentation',
        dictLabel: dictValue + '超参配置',
        pageNum: 0,
        pageSize: 1000
      })
      if (res.data.list.length != 0) {
        //console.log(res.data.list[0].dictValue)
        let obj = {}
        obj[dictValue] = res.data.list[0].dictValue
        hyperparameterConfiguration.push(obj)
      } else {
        ElMessage.error('${dictValue}未在数据字典中设置超参！')
      }
    }
  } else {
    ElMessage.error('task_type为空，请在数据字典中设置具体的任务类型！')
  }

  // console.log(taskType.value)
}
onMounted(() => {
  getTaskType()
})
const changeFps = () => {
  console.log('changeFps')
  if (intervalChangeFps.value) {
    clearInterval(intervalChangeFps.value)
  }

  if (imageFps.value == 0) {
    return
  }
  imageIdx.value = 1
  intervalChangeFps.value = setInterval(() => {
    next_picture()
  }, 1000 / imageFps.value)
}

const startDataAugmentation = async (params: any) => {
  const res = await startDataAugmentationApi(params.id)
  if (res.code === 200) {
    ElMessage.success('任务已经开始，请等待')
  } else {
    ElMessage.error('任务开始失败，请检查！')
  }
  proTable.value?.getTableList()
}

const stopDataAugmentation = async (params: any) => {
  const res = await stopDataAugmentationApi(params.id)
  if (res.code === 200) {
    ElMessage.success('任务终止成功')
  } else {
    ElMessage.error('任务终止失败！')
  }
  proTable.value?.getTableList()
}

const loadImageData = async (taskId: string, imageIdx: number) => {
  const res: any = await getCompareImageApi(taskId, imageIdx)
  imageBase64List.value.origin = res.origin
  imageBase64List.value.stable = res.stable
}

const compareDataAugmentation = async (params: any) => {
  taskId.value = params.id
  imageIdx.value = 0

  const resCount: any = await getCompareImageCountApi(params.id)
  if (resCount.code === 200) {
    inFileCount.value = resCount.data.inFileCount
    outFileCount.value = resCount.data.outFileCount
  } else {
    ElMessage.error('获取图片对比数量失败')
    return
  }
  dialogVisible.value = true

  dialogTitle.value = '缓存图片中'
  fileCount.value = Math.min(inFileCount.value, outFileCount.value)
  for (let idx = 1; idx <= fileCount.value; idx++) {
    dialogTitle.value = '缓存图片中： 第' + idx + '张图片 共' + fileCount.value + '张图片'
    if (cacheImages.value[idx]) {
      continue
    }
    const res: any = await getCompareImageApi(taskId.value, idx)
    cacheImages.value[idx] = {
      origin: res.origin,
      stable: res.stable
    }
  }
  next_picture()
}
const next_picture = async () => {
  if (imageIdx.value < fileCount.value) {
    if (!cacheImages.value[imageIdx.value + 1]) {
      await loadImageData(taskId.value, imageIdx.value + 1)
    }
    imageIdx.value = imageIdx.value + 1
  }
  dialogTitle.value = '预览: 第' + imageIdx.value + '张图片 共' + fileCount.value + '张图片'
}
const pre_picture = async () => {
  if (imageIdx.value > 1) {
    if (!cacheImages.value[imageIdx.value - 1]) {
      await loadImageData(taskId.value, imageIdx.value - 1)
    }
    imageIdx.value = imageIdx.value - 1
  }
  dialogTitle.value = '预览: 第' + imageIdx.value + '张图片 共' + fileCount.value + '张图片'
}

// ProTable 实例
const proTable = ref<ProTableInstance>()

// 删除视频去抖动信息
const deleteDataAugmentation = async (params: any) => {
  await useHandleData(delDataAugmentationApi, params.id, '删除任务【' + params.name + '】？')
  proTable.value?.getTableList()
}

// 批量删除视频去抖动信息
const batchDelete = async (ids: string[]) => {
  await useHandleData(delDataAugmentationApi, ids, '删除所选任务？')
  proTable.value?.clearSelection()
  proTable.value?.getTableList()
}

// 导出视频去抖动列表
const downloadFile = async () => {
  ElMessageBox.confirm('确认导出视频去抖动数据?', '温馨提示', { type: 'warning' }).then(() =>
    useDownload(exportDataAugmentationApi, '视频去抖动列表', proTable.value?.searchParam)
  )
}

// 批量添加视频去抖动
const dialogRef = ref<InstanceType<typeof ImportExcel> | null>(null)
const batchAdd = () => {
  const params = {
    title: '视频去抖动',
    tempApi: importTemplateApi,
    importApi: importDataAugmentationDataApi,
    getTableList: proTable.value?.getTableList
  }
  dialogRef.value?.acceptParams(params)
}

const formDialogRef = ref<InstanceType<typeof FormDialog> | null>(null)
// 打开弹框的功能
const openDialog = async (type: number, title: string, row?: any) => {
  let res = { data: {} }
  if (row?.id) {
    res = await getDataAugmentationApi(row?.id || null)
  }
  // 重置表单
  setItemsOptions()
  const params = {
    title,
    width: 580,
    isEdit: type !== 3,
    itemsOptions: itemsOptions,
    model: type == 1 ? {} : res.data,
    api: type == 1 ? addDataAugmentationApi : updateDataAugmentationApi,
    getTableList: proTable.value?.getTableList
  }
  formDialogRef.value?.openDialog(params)
}
const statusEnums: EnumProps[] = [
  {
    label: '未开始',
    value: '0',
    disabled: false,
    tagType: 'default'
  },
  {
    label: '进行中',
    value: '1',
    disabled: false,
    tagType: 'primary'
  },
  {
    label: '完成',
    value: '2',
    disabled: false,
    tagType: 'success'
  },
  {
    label: '失败',
    value: '3',
    disabled: false,
    tagType: 'danger'
  },
  {
    label: '已中断',
    value: '4',
    disabled: false,
    tagType: 'default'
  }
]

// 表格配置项
const columns = reactive<ColumnProps<any>[]>([
  { type: 'selection', fixed: 'left', width: 70 },
  { prop: 'id', label: '主键ID', width: 180 },
  {
    prop: 'name',
    label: '视频名称',
    search: {
      el: 'input'
    },
    width: 150
  },
  {
    prop: 'taskType',
    label: '任务类型',
    search: {
      el: 'select'
    },
    width: 100,
    tag: true,
    enum: taskTypeEnums
  },
  {
    prop: 'status',
    label: '任务状态',
    search: {
      el: 'select'
    },
    width: 100,
    tag: true,
    enum: statusEnums
  },
  {
    prop: 'startTime',
    label: '开始时间',
    // search: {
    //   el: 'date-picker',
    //   props: {
    //     type: 'datetimerange',
    //     valueFormat: 'YYYY-MM-DD HH:mm:ss'
    //   }
    // },
    width: 180
  },
  {
    prop: 'endTime',
    label: '结束时间',
    // search: {
    //   el: 'date-picker',
    //   props: {
    //     type: 'datetimerange',
    //     valueFormat: 'YYYY-MM-DD HH:mm:ss'
    //   }
    // },
    width: 180
  },
  {
    prop: 'costSecond',
    label: '耗时',
    search: {
      el: 'input'
    },
    width: 80
  },
  {
    prop: 'log',
    label: '日志',
    width: 120
  },

  {
    prop: 'algorithmPath',
    label: '算法路径',
    width: 120
  },
  {
    prop: 'hyperparameterConfiguration',
    label: '超参配置',
    width: 120
  },
  {
    prop: 'remarks',
    label: '备注',
    search: {
      el: 'input'
    },
    width: 120
  },
  {
    prop: 'operation',
    label: '操作',
    width: 230,
    fixed: 'right'
  }
])
// 表单配置项
let itemsOptions: ProForm.ItemsOptions[] = []
const setItemsOptions = () => {
  itemsOptions = [
    {
      label: '任务名称',
      prop: 'name',
      rules: [{ required: true, message: '任务名称不能为空', trigger: 'blur' }],
      compOptions: {
        placeholder: '请输入任务名称'
      }
    },
    {
      label: '任务类型',
      prop: 'taskType',
      rules: [{ required: true, message: '任务类型不能为空', trigger: 'change' }],
      compOptions: {
        elTagName: 'select', // 指定使用 el-select 组件
        placeholder: '请选择任务类型',
        enum: taskType,
        onChange: (value: string) => {
          hyperparameterConfiguration.forEach(obj => {
            if (value in obj) {
              hyperparameter.value = obj[value]
            }
          })
        }
      }
    },
    {
      label: '图片集压缩包',
      prop: 'inputOssId',
      rules: [{ required: true, message: '图片集压缩包不能为空', trigger: 'blur' }],
      compOptions: {
        elTagName: 'file-upload',
        fileSize: 4096,
        fileType: ['zip'],
        placeholder: '请上传图片集压缩包'
      }
    },
    {
      label: '算法路径',
      prop: 'algorithmPath',
      rules: [],
      compOptions: {
        type: 'input',
        clearable: true,
        placeholder: ''
      }
    },
    {
      label: '超参配置',
      prop: 'hyperparameterConfiguration',
      rules: [],
      compOptions: {
        type: 'input',
        clearable: true,
        // placeholder: hyperparameter,
        value: hyperparameter
        //value: hyperparameterConfiguration[itemsOptions.taskType]
      }
    },
    {
      label: '备注',
      prop: 'remarks',
      rules: [
        {
          required: false,
          message: '备注不能为空',
          trigger: 'blur'
        }
      ],
      compOptions: {
        placeholder: '请输入备注'
      }
    }
  ]
}
</script>

<style lang="scss" scoped>
.image-dialog {
  display: flex;
  justify-content: center;
  .el-image {
    margin-right: 20px;
    margin-bottom: 20px;
  }
}
.image-dialog-btn {
  display: flex;
  justify-content: center;
  margin-top: 20px;
}
</style>
