<template> <el-row class="el-upload-self"> <el-upload ref="upload" :multiple="multiple" :class="[ 'avatar-uploader', value.length > 0 ? 'textUpload' : '', accept == 'application/pdf' ? 'pdfUpload' : '', ]" :action="action" :headers="headers" :list-type="listType" :on-preview="handlePreview" :on-remove="handleRemove" :on-success="handleSuccess" :on-exceed="handleExceed" :on-change="handleSelectFile" :before-upload="beforeUpload" :before-remove="beforeRemove" :file-list="fileList" :show-file-list="showFileList" :accept="accept" :limit="limit" :drag="drag" :disabled="disabled" > <template v-if="drag"> <i class="el-icon-upload"></i> <div class="el-upload__text">将文件拖到此处,或<em>点击上传</em></div> </template> <template v-else-if="value.length"> <el-button size="middle" type="text">点击更换</el-button> </template> <template v-else-if="listType === 'picture-card' && !value.length"> <el-button size="middle" type="text">点击上传</el-button> </template> <template v-else> <!-- <el-button size="middle" :type="btnType">点击上传</el-button> --> <!-- <img v-if="imageUrl" :src="imageUrl" class="avatar" /> --> <el-button size="middle" type="text">点击上传</el-button> </template> <div slot="file" slot-scope="{ file }"> <img v-if="accept == 'image/*'" class="el-upload-list__item-thumbnail" :src="file.url" alt="" /> <span v-if="accept == 'image/*'" class="el-upload-list__item-actions"> <span class="el-upload-list__item-preview" @click="handlePreview(file)" > <i class="el-icon-download"></i> </span> </span> <el-tooltip class="item" effect="dark" :content="file.name" placement="top" > <div v-if="accept != 'image/*'" style="cursor: pointer" class="fileNameText" @click="handlePreview(file)" > {{ file.name }} </div> </el-tooltip> </div> <!-- <div slot="tip" class="el-upload__tip">{{ tip }}</div> --> </el-upload> <el-image ref="image" style="display: none" :src="imgUrl" :preview-src-list="previewList" > </el-image> </el-row> </template> <script> import { getAccessToken } from "@/utils/accessToken" import { delFile } from "@/api/file" export default { name: "ElUploadSelf", props: { accept: { type: String, default: "image/*" }, disabled: { type: Boolean, default: false, }, uploadQuery: { type: Object, default: () => { return {} }, }, //后端上传文件路径(参数) listType: String, tip: String, multiple: Boolean, limit: { type: Number, default: 9, }, fileSize: { type: Number, default: 10 * 1024 * 1024 }, loadText: String, showFileList: { type: Boolean, default: true, }, drag: { type: Boolean, default: false, }, btnType: { type: String, default: "primary", }, value: { type: Array, default: () => [], }, //上传文件数组 绑定数组 }, data() { return { imgUrl: "", title: "", uploadPrefix: process.env.VUE_APP_UPLOAD_API, httpPrefix: process.env.NODE_ENV === "development" ? "/api" : process.env.VUE_APP_BASE_API, fileList: [], } }, computed: { headers() { return { Authorization: `Bearer ${getAccessToken()}`, } }, action() { return this.httpPrefix + `/cloud-upms/file/upload` }, // 预览list previewList() { console.log(this.value) if (!this.value.length || this.accept != "image/*") return [] return this.value.map((_) => { return _.url || this.uploadPrefix + `${_.bucketName}/${_.uuidName}` }) }, }, watch: { value: { handler(newValue, oldValue) { if (newValue === oldValue) return this.fileList = newValue.map((_) => { return { name: _.fileName, url: this.uploadPrefix + `${_.bucketName}/${_.uuidName}`, } }) }, immediate: true, }, }, methods: { handleSelectFile(file, fileList) { if (fileList.length > 1) { this.value.shift() fileList.shift() } }, // 上传前回调 beforeUpload(file) { return new Promise((resolve, reject) => { const size = this.fileSize console.log(file.size) if (size && file.size > size) { this.$message.error("文件大小超出限制,请上传10M以下的文件") reject() } resolve() }) }, // 超出限制 handleExceed(files, fileList) { this.$message.error(`最多可上传${this.limit}个文件!`) }, // 上传成功 handleSuccess(res, file, fileList) { const { data } = res if (data) { this.value.push({ ...data, url: file.url }) // 上传成功 this.$emit("input", this.value) this.$emit("fileSuccess") } else { this.$message.warning(res.msg) this.$refs.upload.clearFiles() } }, // 移除提醒 beforeRemove(file, fileList) { // return this.$confirm(`确定移除 ${file.file_name || file.name}?`) }, // 移除 handleRemove({ url }, fileList) { if (fileList.length > 1) { fileList.shift() } this.value = [] this.$emit("input", this.value) // const i = this.value.findIndex((_) => url.endsWith(_.uuid_name)) // if (i > -1) this.value.splice(i, 1) // 静态移除 }, // 查看 handlePreview(file) { const name = file.fileName || file.name this.title = name let responseUrl if (file.response) { const _ = file.response.data responseUrl = this.uploadPrefix + `${_.bucketName}/${_.uuidName}` } try { if (name.match(/\.(png|jpg|jpeg)/)) { this.imgUrl = file.url || responseUrl this.$refs.image.clickHandler() } else { const elink = document.createElement("a") elink.download = name elink.style.display = "none" elink.href = file.url || responseUrl document.body.appendChild(elink) elink.click() URL.revokeObjectURL(elink.href) // 释放URL 对象 document.body.removeChild(elink) } } catch { const elink = document.createElement("a") elink.download = name elink.style.display = "none" elink.href = file.url || responseUrl document.body.appendChild(elink) elink.click() URL.revokeObjectURL(elink.href) // 释放URL 对象 document.body.removeChild(elink) } }, }, } </script> <style lang="scss"> .el-upload-self { .el-upload { position: relative; } } </style> <style lang="scss" scoped> .el-upload-self { font-size: 14px; } ::v-deep .avatar-uploader { display: flex; align-items: center; .el-upload--picture-card { height: 20px; transform: translateY(-4px); } } ::v-deep .pdfUpload { display: flex; flex-direction: row-reverse; justify-content: flex-end; .el-upload--text { height: 20px; transform: translateY(-4px); } .el-upload-list__item { transform: translateY(-6px); // width: 158px; height: 20px; } } ::v-deep .avatar-uploader .el-upload { border: none; width: 80px; height: 30px; line-height: 0px; } ::v-deep .textUpload { align-items: flex-start; .el-upload { border: none; width: 80px; height: 30px; line-height: 0px; } .el-upload--text { height: 20px; transform: translateY(-4px); } } ::v-deep .avatar-uploader .el-upload:hover { border-color: #409eff; } ::v-deep .el-upload-list__item { width: 88px; height: 88px; &:hover { background-color: #fff; } } .avatar-uploader-icon { font-size: 28px; color: #8c939d; width: 88px; height: 88px; line-height: 88px; text-align: center; } .avatar { width: 88px; height: 88px; display: block; } .fileNameText { width: 100px; white-space: nowrap; overflow: hidden; text-overflow: ellipsis; } // ::v-deep .el-upload--picture-card { // width: none; // height: none; // line-height: 0px; // border: none; // } </style>