el-upload上传多张图片,可以拖动图片排序

el-upload上传图片后,可以预览,拖动图片改变位置和排序。效果如下:
在这里插入图片描述

安装插件

npm install vuedraggable --save
<template>
  <div class="upload-preview-wrapper">
    <el-upload
      v-bind="$attrs"
      class="postingUpload"
      ref="upload"
      :on-remove="handleRemove"
      :http-request="uploadFile"
      :before-upload="beforeUpload"
      :show-file-list="false"
      :file-list="uploadFileList"
      :on-exceed="handleExceed"
      action="javascript:void(0)"
    >
    </el-upload>
    <div class="image-list-box">
      <!-- el-upload-list--picture-card 是el-upload的picture-card类型的样式,这里直接拿来用 -->
      <ul class="file-list-container el-upload-list--picture-card">
       <!-- 使用vue-draggable,配置v-model为列表,draggable设置为可选dom的样式选择器代码 -->
        <vue-draggable v-model="uploadFileList" @update="update" @end="end" draggable=".img-item-odiv" class="draggable">
          <transition-group>
            <li
              v-for="(file, index) in uploadFileList"
              :key="file.uid"
              class="img-item-odiv el-upload-list__item"
            >
              <img
                class="el-upload-list__item-thumbnail"
                @load="handleImgLoad(file)"
                :src="file.url" alt=""
              />
              <span class="el-upload-list__item-actions">
                <span
                    class="el-upload-list__item-preview"
                    @click="handlePictureCardPreview(file)"
                >
                  <i class="el-icon-zoom-in"></i>
                </span>
                <span
                    class="el-upload-list__item-edit"
                    @click="handlePictureEdit(file)"
                >
                  <i class="el-icon-edit-outline"></i>
                </span>
                <span
                    class="el-upload-list__item-delete"
                    @click="handleSingleRemove(file)"
                >
                  <i class="el-icon-delete"></i>
                </span>
              </span>
            </li>
          </transition-group>
        </vue-draggable>
      </ul>
      <!-- 上传按钮,点击时打开文件选择器 -->
      <div tabindex="0" class="upload-btn el-upload el-upload--picture-card" @click="clickUploadFile">
        <i class="el-icon-plus"></i>
      </div>
    </div>
  </div>
</template>

<script>
import VueDraggable from 'vuedraggable'
export default {
  components: {
    VueDraggable
  },
  props: {
    fileList: {
      type: Array,
      default: () => {
        return []
      }
    },
  },
  data(){
    return {
      uploadFileList: []
    }
  },
  watch: {
    uploadFileList: {
      handler(val) {
        this.$emit('update:fileList', val)
      },
      deep: true
    }
  },
  methods: {
    handlePictureCardPreview(file) {
    },
    handleSingleRemove(file){
      this.$refs.upload.handleRemove(file)
    },
    handlePictureEdit(file){

    },
    async handleImgLoad(file){
      console.log(file)
      let _this = this;
      let img = new Image();
      img.src = file.url;
      img.onload = function () {
        file.width = img.width;
        file.height = img.height;
        _this.$set(file, 'width', img.width);
        _this.$set(file, 'height', img.height);
        _this.uploadFileList = [].concat(_this.uploadFileList);
      }
    },
    handleRemove(file, fileList) {
      this.uploadFileList = [].concat(fileList);
    },
    /**上传文件的事件*/
    uploadFile(item) {
      //上传文件的代码
    },
    /**上传文件之前*/
    beforeUpload(file) {
      if (file.type != "" || file.type != null || file.type != undefined) {
        //截取文件的后缀,判断文件类型
        const FileExt = file.name.replace(/.+\./, "").toLowerCase();
        let num;
        if (FileExt == 'mp4' || FileExt == 'avi' || FileExt == 'mov') {
            num = 1024;
        } else {
            num = 4;
        }
        //计算文件的大小
        const isLt5M = file.size / 1024 / 1024 < num; //这里做文件大小限制
        //如果大于100M
        if (!isLt5M) {
            if (FileExt == 'mp4' || FileExt == 'avi' || FileExt == 'mov') {
                this.$message.warning('上传视频格式大小不能超过 1GB!');
            } else {
                this.$message.warning('上传图片格式大小不能超过 4MB!');
            }
            return false;
        }
      }
      // 生成文件url
      const reader = new FileReader();
      reader.onload = (e) => {
        file.url = e.target.result;
        this.uploadFileList.push(file)
      };
      reader.readAsDataURL(file);
    },
    handleExceed() {
      this.$message.warning('超出最大上传文件数量的限制!');
      return
    },
    //点击打开文件选择器
    clickUploadFile(){
      this.$refs.upload.$refs["upload-inner"].handleClick()
    },
    // 拖动排序 位置改变时触发
    update(){
      console.log(this.fileList)
    },
    // 拖动结束后触发
    end(){
      console.log(this.fileList)
    }
  }
}
</script>

<style lang="scss">
.upload-preview-wrapper {
  .file-list-container{
    display: inline-flex;
    .img-item-odiv{
      max-width: 400px;
      overflow: hidden;
      position: relative;
    }
    img{
      width: auto;
      height: auto;
    }
  }
  .upload-btn{
    display: inline-block;
  }
  .image-list-box, .draggable >span{
    display: flex;
    flex-wrap: wrap;
  }
  .image-size{
    position: absolute;
    bottom: -20px;
    left: 0px;
    width: 100%;
    text-align: center;
    font-size: 12px;
    color: #606266;
    zoom:0.9
  }
  .warn-color{
    color: #606266;
    font-size: 12px;
    font-weight: 400;
    &.red{
      color: #f56c6c;
    }
  }
}
</style>
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值