主题思路
1.引用可拖拽属性。
2.使用el-upload进行二次封装。
一、引用可拖拽属性
使用npm进行安装
代码如下(示例):
npm install vuedraggable --save
二、使用el-upload进行二次封装,并引用vuedraggable
代码如下(示例):
<template>
<div class="upda fx">
<!-- 图片可拖拽 -->
<div class="col" v-if="imglisted.length != 0" style="margin-left: 10px">
<draggable
:disabled="disabled"
v-model="imglisted"
filter=".forbid"
animation="300"
@update="onMove"
>
<transition-group>
<div
v-for="(item, index) in imglisted"
:key="index"
style="display: inline-block; margin-right: 10px"
>
<div class="img-hover img_div">
<img
:src="nourl ? item : item.url"
style="width: 100px; height: 100px"
class="imgCSSS"
/>
<div class="mask">
<h3 style="line-height: 50px">
<span
v-show="!disabled"
class="el-icon-delete click_fly"
@click="handleRemove(index)"
></span>
<span
class="el-icon-zoom-in click_fly"
style="margin-left: 10px"
@click="handlePreview(index)"
></span>
</h3>
</div>
</div>
</div>
</transition-group>
</draggable>
</div>
<el-upload
ref="upload"
accept="image/*"
:before-upload="handleBeforeUpload"
v-if="imglisted.length != imgnumber && !loading"
:disabled="disabled"
:action="Url + '/common/fileUpload'"
list-type="picture-card"
name="file"
:headers="token"
:auto-upload="true"
:show-file-list="false"
:on-progress="handleExceed"
:on-success="
(response, file) => {
onSuccess(response, file);
}
"
>
<i slot="default" class="el-icon-plus" />
</el-upload>
<div
v-loading="loading"
element-loading-text="上传中"
element-loading-spinner="el-icon-loading"
element-loading-background="rgba(0, 0, 0, 0.6)"
class="loadse"
v-if="loading"
></div>
<!-- 图片放大弹窗 -->
<el-dialog
:visible.sync="dialogVisible"
custom-class="el-dialog-s"
append-to-body
>
<img width="100%" :src="dialogImageUrl" alt="" />
</el-dialog>
</div>
</template>
<script>
import draggable from "vuedraggable";
import { getToken } from "@/utils/auth";
import { mapGetters } from "vuex";
export default {
name: "UpimgList",
components: { draggable },
props: {
// 最多上传照片数量
imgnumber: {
type: Number,
default: null
},
//是否禁用
disabled: {
type: Boolean,
default: null
},
//
nourl: {
type: Boolean,
default: false
},
//图片回显列表
imglist: {
type: Array,
default() {
return [];
}
},
//限制上传图片大小
imageSize: {
type: Number,
default: 3
}
},
computed: {
},
data() {
return {
loading: false,
Url: '',
token: { token: getToken() },
// 图片放大显示
dialogImageUrl: "",
// 图片放大显示弹窗
dialogVisible: false,
imglisted: this.imglist
};
},
watch: {
imglist() {
this.imglisted = this.imglist;
}
},
methods: {
handleExceed(file) {
if (file.loaded > 1000000 * this.imageSize) {
// this.$message.error(`上传图片最大不能超过${this.imageSize}MB`);
this.$refs.upload.abort();
}
},
// 图片下载回显
onSuccess(response, file) {
this.loading = false;
if (this.nourl) {
this.imglist.push(response.content[0]);
} else {
this.imglist.push({ url: response.content[0] });
}
console.log(this.imglist);
// this.$emit("deleUpimges", this.imglisted);
this.$emit("changeimge");
},
//拖拽图片
onMove() {
this.$emit("Upimgsun", this.imglisted);
console.log(this.imglisted);
// this.imglist = [...this.imglisted];
},
//删除图片
handleRemove(index) {
this.imglist.splice(index, 1);
this.$emit("changeimge");
// this.$emit("deleUpimg", index);
},
//放大图片
handlePreview(i) {
this.dialogImageUrl = this.imglisted[i].url;
if (this.dialogImageUrl == undefined) {
this.dialogImageUrl = this.imglisted[i];
}
this.dialogVisible = true;
},
// 判断上传的是否为图片
handleBeforeUpload(file) {
if (file.size > 1000000 * this.imageSize) {
this.$message.error(`上传图片最大不能超过${this.imageSize}MB`);
return false;
}
var img = file.name.substring(file.name.lastIndexOf(".") + 1);
const suffix = img.toLowerCase() === "jpg";
const suffix2 = img.toLowerCase() === "png";
const suffix3 = img.toLowerCase() === "jpeg";
if (!suffix && !suffix2 && !suffix3) {
this.$message.error("上传图片仅支持JPG,PNG,JPEG图片格式!");
return false;
}
this.loading = true;
// return suffix || suffix2 || suffix3;
}
}
};
</script>
<style lang="scss" scoped>
/deep/ .el-upload-list--picture-card .el-upload-list__item {
width: 100px;
height: 100px;
}
/deep/ .el-upload--picture-card {
width: 100px;
height: 100px;
line-height: 100px;
}
.mask {
position: absolute;
background: rgba(101, 101, 101, 0.6);
color: #ffffff;
opacity: 0;
top: 0;
left: 0;
width: 100px;
height: 100px;
border-radius: 10px;
// pointer-events: none;
}
.mask h3 {
text-align: center;
margin-top: 25%;
}
.img_div:hover .mask {
opacity: 1;
}
.img_div {
border-radius: 10px;
display: block;
position: relative;
}
.loadse {
width: 100px;
height: 100px;
border-radius: 10px;
border: 1px dashed #c0ccda;
}
</style>