注意事项
主要需要注意【修改】的时候,删除文件时需要考虑删除的是已经上传过的文件,还是修改时新上传的文件(代码 onRemoveHandler 方法中展示逻辑处理)
页面展示
代码
<!-- 记分管理: 新增、修改、详情 -->
<template>
<el-dialog
:title="title"
:visible.sync="dialogVisible"
width="60%"
top="8vh"
:before-close="handleClose"
:close-on-click-modal="dialogType === 'detail'"
>
<ele-form
ref="submitRef"
inline
form-btn-size="mini"
:disabled="dialogType === 'detail'"
:form-data="formData"
:form-desc="formDesc"
:is-show-back-btn="false"
>
<template v-if="['add', 'edit'].includes(dialogType)" #attachmentList>
<el-upload
ref="ElUploadRef"
class="upload_demo"
list-type="picture-card"
:accept="fileTypeList.join(',')"
action="/supervise_basic/upload/oss/fileupload"
name="files"
multiple
:file-list="fileList"
:headers="{ 'X-Token': getToken() }"
:data="{ relativePath: 'XGZJ/' }"
:on-success="onSuccessHandler"
:on-error="onErrorHandler"
:on-remove="onRemoveHandler"
:before-upload="beforeUploadHandler"
>
<i class="el-icon-plus" />
<!-- 展示文件 -->
<div slot="file" slot-scope="{ file }" class="file_container">
<!-- 展示图片文件 -->
<el-image
v-if="['.png', '.jpg', '.jpeg'].includes(file.name.slice(file.name.lastIndexOf('.')))"
:src="file.url"
:preview-src-list="[file.url]"
fit="cover"
/>
<!-- 展示非图片文件 -->
<div v-else class="file_name">
{{ file.name }}
</div>
<!-- 按钮区域 -->
<span class="el-upload-list__item-actions">
<!-- 删除按钮(也可在此区域添加文件预览按钮等) -->
<span class="el-upload-list__item-delete" @click="onRemoveHandler(file)">
<i class="el-icon-delete" />
</span>
</span>
</div>
</el-upload>
</template>
</ele-form>
<span v-if="dialogType !== 'detail'" slot="footer" class="dialog-footer">
<el-button type="primary" size="mini" @click="submitHandler">提交</el-button>
<el-button size="mini" @click="handleClose">关闭</el-button>
</span>
</el-dialog>
</template>
<script>
import { mapGetters } from 'vuex'
import _ from 'lodash.clonedeep'
import { getToken } from '@/utils/tool'
import { addScore, editScore, getScore } from '@/api/twelve-points'
import { operationFormDesc } from '../constant/formList'
export default {
name: 'OperationDialog',
components: {},
data() {
return {
dialogVisible: false,
dialogType: '',
rowData: {},
formData: {
attachmentList: []
},
getToken,
fileList: [],
fileTypeList: ['.png', '.jpg', '.jpeg', '.doc'],
fileMaxSize: 5
}
},
computed: {
...mapGetters(['glbmOptions', 'sysConfigData']),
title() {
const obj = {
add: '新增记分',
edit: '修改记分',
detail: '记分详情'
}
return obj[this.dialogType]
},
formDesc() {
// 防止某些表单项条件展示时顺序错乱
return this.dialogVisible ? operationFormDesc(this) : {}
},
submitAx() {
const obj = {
add: addScore,
edit: editScore
}
return obj[this.dialogType]
}
},
watch: {
dialogVisible() {
this.$refs.submitRef &&
this.$refs.submitRef.$refs.form &&
this.$refs.submitRef.$refs.form.clearValidate()
}
},
created() {
this.fileTypeList.push(...this.fileTypeList.map((item) => item.toUpperCase()))
},
methods: {
open(type, rowData = {}) {
this.rowData = _(rowData)
this.dialogType = type
if (type !== 'add') {
this.getDetail(rowData.jfbh)
}
this.dialogVisible = true
},
getDetail(jfbh) {
getScore(jfbh).then((res) => {
this.$common.CheckCode(res, null, () => {
const { data = {} } = res
for (const key in this.formDesc) {
this.$set(this.formData, key, data[key])
// 编辑时要回显已有文件
key === 'attachmentList' &&
(this.fileList = data[key].map((item) => {
return {
name: item.wjmc,
url: this.sysConfigData.mon_sys_ossurl + item.wjlj,
type: item.wjgs
}
}))
}
})
})
},
beforeUploadHandler(file) {
const ext = file.name.substring(file.name.lastIndexOf('.'))
console.log('ext----打印', ext)
const isLt = file.size / 1024 / 1024 < this.fileMaxSize
if (!this.fileTypeList.includes(ext)) {
this.$message.error(`请上传${this.fileTypeList.map((item) => item)}格式的文件!`)
return false
} else if (!isLt) {
this.$message.error(`上传文件大小不能超过 ${this.fileMaxSize}MB!`)
return false
} else {
return true
}
},
onRemoveHandler(file) {
console.log('file----', file)
/**
* 新上传的文件 → file.response?.data?.fileUploadInfoList[0].path
* 编辑时已有的文件 → file.url (通过文件路径匹配文件时需将 open 方法中给文件路径拼接的前缀去掉,即 file.url.replace(this.sysConfigData.mon_sys_ossurl, ''))
*/
const filePath =
file.response?.data?.fileUploadInfoList[0].path ||
file.url.replace(this.sysConfigData.mon_sys_ossurl, '')
// 根据文件路径和文件名共同匹配当前删除文件的索引
const index = this.formData.attachmentList.findIndex(
(item) => item.wjlj === filePath && item.wjmc === file.name
)
/**
* 删除文件
* 1. 要删除 el-upload 中文件信息
* 2. 要删除表单中记录的文件信息
*/
const { uploadFiles } = this.$refs.ElUploadRef
uploadFiles.splice(index, 1) // 删除 el-upload 中文件信息
this.formData.attachmentList.splice(index, 1) // 删除表单中记录的文件信息
},
// eslint-disable-next-line handle-callback-err
onErrorHandler(err, file, fileList) {
this.$message.error(`${file.name}文件上传失败,请重新上传!`)
},
// 文件上传成功
onSuccessHandler(response) {
console.log('response----', response)
const fileList = response.data.fileUploadInfoList
? response.data.fileUploadInfoList.map((item) => {
return {
wjmc: item.filename,
wjlj: item.path,
wjgs: item.fileType
}
})
: []
this.formData.attachmentList.push(...fileList)
},
submitHandler() {
this.$refs.submitRef.validate().then((valid) => {
this.submitAx(this.formData).then((res) => {
this.$common.CheckCode(res, '提交成功', () => {
this.$emit('update')
this.handleClose()
})
})
})
},
handleClose() {
this.rowData = {}
this.fileList = []
for (const key in this.formData) {
if (this.formData[key] && this.formData[key].constructor === Array) {
this.formData[key] = []
} else if (this.formData[key] && this.formData[key].constructor === Object) {
this.formData[key] = {}
} else {
this.formData[key] = ''
}
}
this.dialogVisible = false
}
}
}
</script>
<style lang='scss' scoped>
@import '@/styles/dialog-scss.scss';
>>> .ele-form {
.el-upload {
margin-bottom: 10px;
}
}
// 新增/编辑:文件上传时展示文件样式
.file_container {
width: 100%;
height: 100%;
text-align: center;
.el-image {
width: 100%;
height: 100%;
}
.file_name {
width: 100%;
height: 100%;
display: flex;
justify-content: center;
align-items: center;
}
}
// 详情:文件预览样式
>>> .form_file_wrapper {
color: #333;
.form_file_image {
width: 100px;
height: 100px;
border: 1px solid #c0ccda;
border-radius: 6px;
cursor: pointer;
margin-right: 10px;
}
.form_file_link {
margin-right: 10px;
}
}
</style>
formList.js
export const operationFormDesc = (_this) => {
return {
// ...
attachmentList: {
type: 'upload',
label: '相关证据',
layout: 24,
render: (h, content, value) => {
return _this.$common.formShowFiles(h, content, value, _this, 'wjmc', 'wjlj', {
type: 'primary'
})
}
}
}
}
formShowFiles 公共方法
export default {
/**
* 表单回显文件
*/
formShowFiles(h, content, value, _this, wjmc = 'filename', wjlj = 'saved_filename', linkAttrs = {}) {
return h(
'div',
{ staticClass: 'form_file_wrapper' },
value && value.length
? value.map((item, index) => {
if (/\.(gif|jpg|jpeg|png|GIF|JPG|JPEG|PNG)$/.test(item[wjmc])) {
// 判断是否为图片
return h('el-image', {
key: index,
staticClass: 'form_file_image',
attrs: {
src: _this.sysConfigData.mon_sys_ossurl + item[wjlj],
fit: 'cover',
'preview-src-list': [_this.sysConfigData.mon_sys_ossurl + item[wjlj]]
}
})
} else {
// 不是图片的以链接的形式展示
return h('el-link', {
key: index,
staticClass: 'form_file_link',
attrs: {
href: _this.sysConfigData.mon_sys_ossurl + item[wjlj],
underline: false,
target: '_blank',
download: item[wjmc],
...linkAttrs
},
domProps: { innerText: item[wjmc] }
})
}
})
: '暂无'
)
},
}