index.vue 3.42 KB
<template>
  <n-upload
    v-model:file-list="fileList"
    :show-file-list="true"
    :customRequest="customRequest"
    :onBeforeUpload="beforeUploadHandle"
    :onRemove="remove"
  >
    <n-upload-dragger>
      <img v-if="uploadImageUrl" class="upload-show" :src="uploadImageUrl" :alt="t('common.uploadImage.alt')" />
      <div class="upload-img" v-show="!uploadImageUrl">
        <img src="@/assets/images/canvas/noImage.png" />
        <n-text class="upload-desc" depth="3">
          {{t('common.uploadImage.uploadDesc1')}} {{ uploadSizeFormat.size }}M ,{{t('common.uploadImage.uploadDesc2')}} {{ uploadSizeFormat.format }} {{t('common.uploadImage.uploadDesc3')}}
        </n-text>
      </div>
    </n-upload-dragger>
  </n-upload>
</template>

<script lang="ts" setup name="TKUpload">
import { ref, PropType, nextTick } from 'vue'
import type { UploadCustomRequestOptions, UploadFileInfo } from 'naive-ui'
import { fetchRouteParamsLocation } from '@/utils'
import { uploadFile } from '@/api/external/contentSave/content'
import { FileTypeEnum } from '@/enums/external/fileTypeEnum'

interface uploadSizeFormatIF {
  size: number
  format: string
}

const props = defineProps({
  uploadIndex: Number,
  uploadImageUrl: {
    type: String as PropType<string>,
    default: ''
  },
  uploadSizeFormat: {
    type: Object as PropType<uploadSizeFormatIF>,
    default: () => ({
      size: 5,
      format: 'png/jpg/jpeg/gif'
    })
  }
})

const t = window['$t']

const emit = defineEmits(['sendFile', 'removeFile'])

const fileList = ref<UploadFileInfo[]>()

// 自定义上传操作
const customRequest = (options: UploadCustomRequestOptions) => {
  const { file } = options
  nextTick(async () => {
    if (file.file) {
      const newNameFile = new File([file.file], `${fetchRouteParamsLocation()}_index_upload.png`, {
        type: file.file.type
      })
      let uploadParams = new FormData()
      uploadParams.append('file', newNameFile)
      const uploadRes = await uploadFile(uploadParams)
      if (!uploadRes) return
      emit('sendFile', uploadRes?.fileStaticUri, props.uploadIndex)
      window['$message'].success(t('common.uploadImage.uploadSuccess'))
    } else {
      window['$message'].error(t('common.uploadImage.uploadFail'))
    }
  })
}

// 文件上传前置处理
const beforeUploadHandle = (file: UploadFileInfo) => {
  fileList.value = []
  const type = file.file?.type
  const size = file.file?.size as number
  const typeSuffix = type?.split('/')?.at(-1)?.toUpperCase() as keyof typeof FileTypeEnum
  if (size > 1024 * 1024 * props.uploadSizeFormat.size) {
    window['$message'].warning(`t('common.uploadImage.uploadDesc4') ${props.uploadSizeFormat.size}t('common.uploadImage.uploadDesc5'),t('common.uploadImage.uploadDesc6')`)
    return false
  }
  if (!FileTypeEnum[typeSuffix]) {
    window['$message'].warning(t('common.uploadImage.uploadFileError'))
    return false
  }
  return true
}

//单个点击删除
const remove = () => {
  fileList.value = []
  emit('removeFile', true, props.uploadIndex)
}
</script>

<style lang="scss" scoped>
$uploadHeight: 193px;
@include deep() {
  .n-card__content {
    padding: 0;
    overflow: hidden;
  }
  .n-upload-dragger {
    padding: 5px;
  }
}
.upload-show {
  width: -webkit-fill-available;
  height: $uploadHeight;
  border-radius: 5px;
}
.upload-img {
  display: flex;
  flex-direction: column;
  align-items: center;
  img {
    height: 150px;
  }
  .upload-desc {
    padding: 10px 0;
  }
}
</style>