<template>
  <div class="erf-attachment-manager">
    <!-- 操作按钮 -->
    <div style="margin-bottom: 10px">
      <el-button
        type="primary"
        size="small"
        v-if="!disabled"
        @click="handleUpload">
        上传附件
      </el-button>
      <el-button
        type="primary"
        size="small"
        @click="handleDownload">
        下载
      </el-button>
    </div>

    <!-- 附件列表表格 -->
    <el-table
      :height="height"
      :data="dataList"
      ref="table"
      v-loading="queryLoading"
      border
      @selection-change="handleSelectionChange"
      style="width: 100%;">

      <el-table-column type="selection" width="55" align="center"/>

      <el-table-column
        prop="fileName"
        label="文件名"
        min-width="200"
        align="left"
        header-align="center"
        show-overflow-tooltip>
      </el-table-column>

      <el-table-column
        prop="fileType"
        label="文件类型"
        min-width="100"
        align="center"
        header-align="center">
      </el-table-column>

      <el-table-column
        prop="createdBy"
        label="上传人"
        min-width="100"
        align="center"
        header-align="center">
      </el-table-column>

      <el-table-column
        prop="createDate"
        label="上传时间"
        min-width="160"
        align="center"
        header-align="center">
      </el-table-column>

      <el-table-column
        prop="orderRef5"
        label="备注"
        min-width="160"
        align="center"
        header-align="center">
      </el-table-column>

      <el-table-column
        label="操作"
        width="150"
        align="center"
        header-align="center"
        fixed="right">
        <template slot-scope="{row}">
          <el-link
            style="cursor:pointer; margin-right: 10px;"
            @click="previewFile(row)">
            预览
          </el-link>
          <el-link
            style="cursor:pointer; color: #F56C6C;"
            v-if="!disabled"
            @click="handleRemove(row)">
            删除
          </el-link>
        </template>
      </el-table-column>
    </el-table>

    <!-- 上传对话框 -->
    <el-dialog
      title="上传附件"
      :visible.sync="ossVisible"
      width="380px"
      append-to-body
      :close-on-click-modal="false">

      <el-form :inline="true" label-position="top" label-width="80px">
        <el-row>
          <el-form-item label="申请单号">
            <el-input v-model="ossForm.orderRef2" readonly style="width: 310px"></el-input>
          </el-form-item>
        </el-row>
      </el-form>

      <!-- 文件上传区域 -->
      <div style="margin: 15px 0;">
        <div style="margin-bottom: 10px;">
          选择文件:
          <span style="color: #67C23A; font-size: 12px; margin-left: 10px;">
            <i class="el-icon-picture-outline"></i> 可支持直接 Ctrl+V 粘贴图片，不需要点击上传按钮
          </span>
        </div>
        <el-upload
          drag
          action="#"
          ref="upload"
          :file-list="fileList"
          :on-remove="onRemoveFile"
          :on-change="onChangeFile"
          multiple
          :auto-upload="false"
          style="text-align: left;">
          <i class="el-icon-upload"></i>
          <div class="el-upload__text">将文件拖到此处，或<em>点击上传</em>，或<em style="color: #67C23A;">Ctrl+V 粘贴图片</em></div>
          <div class="el-upload__tip" slot="tip">
            支持pdf、dwg、dxf、doc、docx、xls、xlsx、jpg、png格式
          </div>
        </el-upload>
      </div>

      <!-- 备注区域 -->
      <div style="margin: 15px 0;">
        <div style="margin-bottom: 10px;">备注:</div>
        <el-input
          type="textarea"
          v-model="ossForm.remark"
          resize="none"
          :autosize="{minRows: 2, maxRows: 2}">
        </el-input>
      </div>

      <span slot="footer" class="dialog-footer">
        <el-button type="primary" :loading="uploadLoading" @click="handleUploadFiles">保存</el-button>
        <el-button @click="ossVisible = false">关闭</el-button>
      </span>
    </el-dialog>
  </div>
</template>

<script>
import { ossUpload, queryOss, removeOss, previewOssFileById, previewOssFileById2 } from '@/api/oss/oss'

export default {
  name: 'ErfAttachmentManager',

  props: {
    // 申请单号
    applyNo: {
      type: String,
      required: true
    },
    // 是否禁用编辑
    disabled: {
      type: Boolean,
      default: false
    },
    // 表格高度
    height: {
      type: [String, Number],
      default: '30vh'
    }
  },

  data() {
    return {
      dataList: [],
      queryLoading: false,
      uploadLoading: false,
      selectionDataList: [],
      ossVisible: false,
      ossForm: {
        orderRef1: 'ERF', // 模块标识
        orderRef2: '', // 申请单号
        orderRef6: 'EXP_APPLY', // 业务类型标识
        remark: ''
      },
      fileList: [],
      pasteImageCounter: 0 // 粘贴图片计数器，用于生成文件名
    }
  },

  mounted() {
    this.handleQuery()
  },

  watch: {
    applyNo(newVal) {
      if (newVal) {
        this.handleQuery()
      }
    },
    // 监听对话框关闭，移除粘贴事件监听器
    ossVisible(newVal) {
      if (!newVal) {
        document.removeEventListener('paste', this.handlePaste)
      }
    }
  },

  beforeDestroy() {
    // 组件销毁时移除监听器
    document.removeEventListener('paste', this.handlePaste)
  },

  methods: {
    /**
     * 查询附件列表
     */
    handleQuery() {
      if (!this.applyNo) {
        return
      }

      let params = {
        orderRef1: 'ERF',
        orderRef2: this.applyNo,
        orderRef6: 'EXP_APPLY'
      }

      this.queryLoading = true
      queryOss(params).then(({data}) => {
        this.queryLoading = false
        if (data && data.code === 0) {
          this.dataList = data.rows || []
        } else {
          this.dataList = []
          this.$message.warning(data.msg || '查询失败')
        }
      }).catch(error => {
        this.queryLoading = false
        this.$message.error('查询异常')
      })
    },

    /**
     * 打开上传对话框
     */
    handleUpload() {
      this.$nextTick(() => {
        if (this.$refs.upload) {
          this.$refs.upload.clearFiles()
        }
      })
      this.fileList = []
      this.ossForm.orderRef2 = this.applyNo
      this.ossForm.remark = ''
      this.ossVisible = true
      this.pasteImageCounter = 0

      // 添加粘贴事件监听器
      this.$nextTick(() => {
        document.addEventListener('paste', this.handlePaste)
      })
    },

    /**
     * 文件选择变化
     */
    onRemoveFile(file, fileList) {
      this.fileList = fileList
    },

    onChangeFile(file, fileList) {
      this.fileList = fileList
    },

    /**
     * 处理粘贴事件（支持直接粘贴图片）
     */
    handlePaste(event) {
      // 只在对话框打开时处理粘贴
      if (!this.ossVisible) {
        return
      }

      const items = (event.clipboardData || event.originalEvent.clipboardData).items

      for (let i = 0; i < items.length; i++) {
        const item = items[i]

        // 检查是否为图片类型
        if (item.type.indexOf('image') !== -1) {
          event.preventDefault() // 阻止默认粘贴行为

          const blob = item.getAsFile()
          if (!blob) continue

          // 获取文件扩展名
          const extension = blob.type.split('/')[1] || 'png'

          // 尝试使用原始文件名，如果没有则使用简洁的默认名称
          let fileName = blob.name
          if (!fileName || fileName === 'image.png' || fileName === 'blob') {
            // 截图或无名称的情况，使用简洁的默认名称
            this.pasteImageCounter++
            fileName = `粘贴图片${this.pasteImageCounter}.${extension}`
          }

          // 创建 File 对象（保留原始文件名）
          const file = new File([blob], fileName, { type: blob.type })

          // 创建一个符合 el-upload 格式的文件对象
          const uploadFile = {
            name: fileName,
            size: file.size,
            type: file.type,
            raw: file,
            uid: Date.now() + this.pasteImageCounter,
            status: 'ready'
          }

          // 添加到文件列表
          this.fileList.push(uploadFile)

          // 手动触发 el-upload 的文件列表更新
          if (this.$refs.upload) {
            this.$refs.upload.uploadFiles.push(uploadFile)
          }

          this.$message.success(`已粘贴图片: ${fileName}`)

          break // 只处理第一张图片
        }
      }
    },

    /**
     * 执行上传
     */
    handleUploadFiles() {
      if (this.fileList.length === 0) {
        this.$message.error('请选择文件')
        return
      }

      let formData = new FormData()
      for (let i = 0; i < this.fileList.length; i++) {
        formData.append('file', this.fileList[i].raw)
      }
      formData.append('orderRef1', 'ERF')
      formData.append('orderRef2', this.ossForm.orderRef2)
      formData.append('orderRef6', 'EXP_APPLY')
      formData.append('createdBy', this.$store.state.user.name)
      formData.append('orderRef5', this.ossForm.remark)

      this.uploadLoading = true
      ossUpload(formData).then(({data}) => {
        this.uploadLoading = false
        if (data && data.code === 0) {
          this.$message.success('上传成功')
          this.handleQuery()
          this.ossVisible = false
        } else {
          this.$message.warning(data.msg || '上传失败')
        }
      }).catch(error => {
        this.uploadLoading = false
        this.$message.error('上传异常')
      })
    },

    /**
     * 删除附件
     */
    handleRemove(row) {
      this.$confirm('确认删除该附件吗？', '提示', {
        confirmButtonText: '确定',
        cancelButtonText: '取消',
        type: 'warning'
      }).then(() => {
        let ids = [row.id]
        removeOss(ids).then(({data}) => {
          if (data && data.code === 0) {
            this.$message.success('删除成功')
            this.handleQuery()
          } else {
            this.$message.warning(data.msg || '删除失败')
          }
        }).catch(error => {
          this.$message.error('删除异常')
        })
      }).catch(() => {})
    },

    /**
     * 预览文件
     */
    previewFile(row) {
      let type = ''
      let fileType = row.fileType.toLowerCase()

      // 图片类型
      let image = ['jpg', 'jpeg', 'png', 'gif', 'bmp']
      if (image.includes(fileType)) {
        type = 'image/' + fileType
      }

      // 视频类型
      let video = ['mp4', 'avi', 'mov', 'wmv', 'flv']
      if (video.includes(fileType)) {
        type = 'video/' + fileType
      }

      // 文本类型
      if (fileType === 'txt') {
        type = 'text/plain;charset=utf-8'
      }

      // Excel类型
      if (fileType === 'xlsx' || fileType === 'xls') {
        type = 'excel'
      }

      // Word类型
      if (fileType === 'docx') {
        type = 'word'
      }

      // PDF类型
      if (fileType === 'pdf') {
        type = 'application/pdf;charset-UTF-8'
      }

      // Office文件不支持预览
      if (fileType === 'doc' || fileType === 'ppt' || fileType === 'pptx') {
        this.$message.warning('该文件格式暂不支持预览，请下载后查看')
        return
      }

      // CAD文件不支持预览
      if (fileType === 'dwg' || fileType === 'dxf') {
        this.$message.warning('CAD文件暂不支持预览，请下载后使用CAD软件查看')
        return
      }

      if (type === '') {
        this.$message.warning('该文件格式暂不支持预览')
        return
      }

      let params = {
        id: row.id,
        fileType: type
      }

      previewOssFileById2(params).then(({data}) => {
        if (type === 'excel' || type === 'word') {
          type = 'application/pdf;charset=UTF-8'
        }
        const blob = new Blob([data], { type: type })
        const fileURL = URL.createObjectURL(blob)

        if (type === 'xls' || type === 'docx' || type === 'xlsx') {
          const { href } = this.$router.resolve({
            name: 'pre',
            query: {
              src: fileURL,
              type: 'pdf'
            }
          })
          window.open(href, '_blank')
        } else {
          // 在新标签页中打开文件预览
          window.open(fileURL, '_blank')
        }
      })
    },

    /**
     * 选择变化
     */
    handleSelectionChange(val) {
      this.selectionDataList = val
    },

    /**
     * 下载选中的附件
     */
    handleDownload() {
      if (this.selectionDataList.length === 0) {
        this.$message.warning('请选择要下载的附件')
        return
      }

      let selectList = this.selectionDataList.map(item => ({ ...item }))
      for (let i = 0; i < selectList.length; i++) {
        let params = {
          id: selectList[i].id
        }
        previewOssFileById(params).then((response) => {
          const blob = new Blob([response.data], { type: response.headers['content-type'] })
          const link = document.createElement('a')
          link.href = URL.createObjectURL(blob)
          link.setAttribute('download', selectList[i].fileName)
          link.target = '_blank'
          link.click()
          URL.revokeObjectURL(link.href)
        })
      }

      this.$refs.table.clearSelection()
    }
  }
}
</script>

<style scoped>
.erf-attachment-manager {

}
/* 表格样式优化 */
.el-table >>> .el-table__header th {
  background-color: #F5F7FA;
  color: #606266;
  font-weight: bold;
}

.el-table >>> .el-table__row td {
  padding: 8px 0;
}
</style>
