upload组件封装,支持拖拽文件上传

一、组件封装需要注意什么?

组件化思想:组件应该是独立的、可复用的部件,应该遵循单一职责原则,将组件的功能划分得尽可能细致。
API 设计:组件的 API 设计要合理,要考虑到组件的可定制性和易用性。应该尽可能的提供必要的配置项和事件回调,同时避免提供过多的 API,导致 API 过于复杂。
生命周期:组件的生命周期要合理地使用,尤其是对于需要与外部交互的组件,要注意生命周期的时机,以便在组件的不同阶段进行相应的操作。
组件通信:组件通信是组件化开发中的一个重要问题,Vue 中提供了多种通信方式,包括props、 e m i t 、 emit、 emitparent、$attrs、ref、vuex、provide/inject 等。在组件的设计中,需要考虑到组件之间的通信问题,合理地使用这些通信方式。
样式和布局:组件的样式和布局应该尽可能地与组件的功能分离,避免样式和布局影响到组件的功能和逻辑。
测试:组件封装完成后,需要进行充分的测试,包括单元测试和集成测试,以保证组件的质量和稳定性。
总的来说,组件封装可以达到代码的灵活和可复用性,但封装时要谨记上面提到的封装要点。

二、目标效果

在这里插入图片描述

组件可配置属性:

  • multiple是否为多文件上传;
  • filePostfix允许上传文件类型提示;
  • fileList底部文件列表;
  • loading加载数据时显示动效;

组件可配置方法:

  • upload文件上传触发的事件回调;
  • delete点击删除图标触发的事件回调;
  • download点击下载图标触发的事件回调;

三、封装步骤

1、从本地选取文件

1)方式一——点击按钮选取文件:

<input ref="inputfile" class="file-content" type="file" :multiple="multiple" @change="handelInputFile">

相关方法:

handelInputFile(e) {
   
    this.readFile(e.target.files)
    this.$refs.inputfile.value = null;
},

2)方式二——直接拖拽文件:

<div class="file-box"
     :class="dropType ? 'dropbox-shadow' : ''"
     type="file"
     v-i-loading.fullscreen="loading"
     @dragenter.stop.prevent="fileBoxDragenter(true)"
     @dragleave.stop.prevent="fileBoxDragleave"
     @drop.stop.prevent="fileBoxDrop($event, true)"
     @dragover.stop.prevent=""
     @click="openFile">
    <div>
        <div class="upload-icon"></div>
    </div>
    <div class="upload-text">
        <span>将文件拖到此处,或</span>
        <span>点击上传</span>
        <div class="el-upload__tip" slot="tip">只能上传{
  {filePostfix}}文件,且不超过100M</div>
    </div>
</div>

相关方法:

/**
 * dragenter源对象进入过程对象范围内
 */
fileBoxDragenter(flag) {
   
    // 传入10ms的延迟锁,让drapleave在enter延迟后触发
    this.boxLock = true
    setTimeout(() => {
   
        this.boxLock = false
    }, 10)
    // dropType文件拖拽进选中范围的高亮效果
    this.dropType = flag
},

/**
 * dragleave源对象离开过程对象范围
 */
fileBoxDragleave() {
   
    if (this.boxLock) return
    this.dropType = false
},
/**
 * drop文件拖拽落下
 */
fileBoxDrop(e) {
   
    this.dropType = false
    let fileList = e.dataTransfer.files
    this.readFile(fileList)
},

2、获取上传的文件

readFile(fileList) {
    if (!fileList || fileList.length < 1) return
    if(fileList.length > 1) {
        this.$Imessage({
            message: `不支持一次上传多文件`,
            type: 'warning'
        })
        return
    }
    if(!this.multiple && this.fileList.length >= 1) { // 仅允许单个附件上传
        this.$Imessage({
            message: `不支持上传多个附件`,
            type: 'warning'
        })
        return
    }
    let file = fileList[0]
    if(this.validFile(file)) {
        tempFile = file
        this.$refs['paramForm'].validate(valid => {
            if(valid) {
                this.$emit('upload', tempFile, this.multiple)
            }
        })
    }
},

3、已上传文件展示、删除、下载
<!--已上传文件展示-->
<ul v-show="fileList.length>0" class="file-list">
    <li v-for="(item, index) in fileList" class="item-content">
        <a :title="item.name">
            

最近更新

  1. TCP协议是安全的吗?

    2024-05-11 17:36:02       18 阅读
  2. 阿里云服务器执行yum,一直下载docker-ce-stable失败

    2024-05-11 17:36:02       19 阅读
  3. 【Python教程】压缩PDF文件大小

    2024-05-11 17:36:02       18 阅读
  4. 通过文章id递归查询所有评论(xml)

    2024-05-11 17:36:02       20 阅读

热门阅读

  1. linux的firmware和hal层

    2024-05-11 17:36:02       8 阅读
  2. 双向链表队列介绍

    2024-05-11 17:36:02       7 阅读
  3. Vue 3.x组件生命周期

    2024-05-11 17:36:02       10 阅读
  4. Symfony DomCrawler库在反爬虫应对中的应用

    2024-05-11 17:36:02       10 阅读