layui手动上传多张图片文件预览并限制上传文件数量

(碎碎念:layui都关站了,要不是维护旧项目,谁还会想用layui和JQ啊!!!)

Layui版本2.6.8
JQuery版本3.6.0

由于layui的上传功能做的比较简单,若仅仅用来上传单张图片那还是挺方便的,但如果是上传多张图片,那么就会发现很不好操作。本文将展示如何使用layui实现上传多张图片预览图片删除选择图片限制上传数量等功能,希望可以帮助各位同学(文末附源码)。

1. 创建上传按钮,并实例化上传组件
<button type="button" id="uploader-choose">选择文件</button>
<button type="button" id="uploader-submit">点击上传</button>
<!--文件列表-->
<div class="file-list"></div>
<script>
    layui.use('upload', function(){
        var upload = layui.upload;
        // 上传文件队列
        var uploadList = {};
        // 文件列表dom
        var fileListDom = $('.file-list');
        //执行实例
        var uploadInst = upload.render({
            elem: '#uploader-choose', //绑定元素
            url: '/index/upload', //上传接口
            accept:'images',
            acceptMime:'image/*',
            exts:'jpg|png|gif|bmp|jpeg',
            auto: false,
            bindAction: '#uploader-submit',
            multiple: true,
            number: 10,
            // 选择文件的回调
            choose: function(obj){ },
            // 上传接口请求成功的回调
            before: function(obj){ },
            //上传完毕回调
            done: function(res){ },
            //当文件全部被提交后,才触发
            allDone: function (obj) { },
            //请求异常回调
            error: function(){ }
        });
    });
</script>

效果图
在这里插入图片描述

  • 我们关闭了自动上传功能(auto:false)所以需要绑定(bindAction)一个按钮来实现提交上传,关闭自动上传可以更方便的控制上传文件数量。
  • 由于我们是上传图片,所以配置了accept、acceptMime、exts参数,对格式做了相应的限制,若是其他文件,修改成对应格式即可。
  • 开启可选多个文件 (multiple:true),并配置 number:10。这里需要注意!number 参数表示打开选择文件窗口时可选的文件数量,并不是整个文件队列的文件数量,所以整个文件队列的数量是要手动进行控制的。
  • 特别提醒一下,若使用了 $(function(){ … }) ,那么在 function() 中的变量,在外部是无法获取的,因为它的作用域只在function()中。如果必须要使用,需要在 function() 传递过去。(后面会有相关例子说明)
2. 增加选择文件的回调事件 choose(),并实现文件预览与删除
var uploadInst = upload.render({
	...
	choose: function(obj){
		// 展示上传按钮
        $('#uploader-submit').show();
         // 将每次选择的文件追加到文件队列
         uploadList = obj.pushFile();
         const len = fileListDom.find('.file-list-item').length;
         // 还可以上传的文件数量
         const limit = 10 - len;
         var number = 0;
         // 预读本地文件,如果是多文件,则会遍历。(不支持ie8/9)
         obj.preview(function(index, file, result){
             if (number < limit){
                 number++;
                 appendFile(index, file.name, result);
             }else{
                 deleteTempFile(index)
             }
         })
	})
	...
})
// 预览选择的文件
function appendFile(index, name, result) {
    const dom = '<div class="file-list-item file-temp" data-index="'+index+'"><div><img src="'+result+'" alt="'+name+'"><span class="layui-badge layui-bg-blue">待上传</span></div>' +
        '<div><input type="button" class="file-cancel" value="取消"></div></div>';
    fileListDom.append(dom);
    fileCancelEvent();
}
// 为待上传文件【取消】按钮添加点击事件
function fileCancelEvent() {
    fileListDom.find('.file-cancel').each(function () {
        const event = $._data($(this)[0],"events");
        // 仅对未绑定事件的按钮进行绑定
        if (!event || !event["click"]){
            $(this).click(function () {
                var fileDom = $(this).parent().parent();
                var index = fileDom.data('index');
                if (index){
                    deleteTempFile(index);
                }
                fileDom.remove();
            })
        }
    })
}
// 删除待上传的文件(从文件队列中删除文件)
function deleteTempFile(index){
    if (index === 0){
        // 清空文件队列中所有数据
        for (const key in uploadList) {
            delete uploadList[key];
        }
        // 隐藏上传按钮
        $('#uploader-submit').hide();
    }else{
        delete uploadList[index];
        var number = Object.keys(uploadList).length;
        // 若上传文件队列中无数据则隐藏上传按钮
        if (number <= 0){
            $('#uploader-submit').hide();
        }
    }
}

效果图
在这里插入图片描述

  • 为了实现预览功能,我们需要在 choose() 回调中生成图片节点,追加到列表中。参数 obj 为本次选择的文件信息。
  • 通过 pushFile() 可以得到文件列表对象,每次调用都会把本次选择的文件追加到列表中。
  • preview() 会遍历本次选择的文件,其中 result 为图片base64编码,我们可以直接在页面上展示出来。
  • 在生成预览图片时,我们并没有直接在按钮上添加onclick,而是选择了获取按钮,再添加。这是因为文件队列对象变量声明在 layui.use(function()) 中,若直接在按钮上添加删除事件,则会出现找不到队列变量的错误。如果需要直接添加删除事件,则可以把队列变量以及删除事件都移动到 function() 外。
3. 文件上传成功的处理
var uploadInst = upload.render({
	...
	// 上传接口请求成功的回调
    before: function(obj){
        layer.load(1);
    },
    //上传完毕回调
    done: function(res){
        fileListDom.find('.file-temp').each(function () {
            if (!res.res){
                // 若上传失败,则直接移除
                $(this).remove();
            }else{
                // 添加上传返回的数据到对应的文件中
                var hidden = '<input type="hidden" name="path[]" value="'+res.path+'"/>';
                $(this).append(hidden);
                // 修改预览文件样式
                $(this).removeClass('file-temp');
                $(this).find('.file-cancel').removeClass('layui-btn-primary');
                $(this).find('.file-cancel').addClass('layui-btn-danger');
                $(this).find('.file-cancel').val('删除');
                $(this).find('.layui-badge').remove();
            }
        })
    },
    //当文件全部被提交后,才触发
    allDone: function (obj) {
        layer.msg("已上传 "+obj.successful+" 个文件");
        layer.closeAll('loading');
        deleteTempFile(0)
    },
	...
})

效果图

在这里插入图片描述

  • 每个文件上传成功后都会触发 done() 事件,此时我们通过添加隐藏域的方式,保存返回的图片数据,然后再提交到后台(一般的上传图片都是在form表单中进行提交)。这里需要根据后端保存文件的方式进行变动,若上传图片后即整个业务流程结束,则无需添加隐藏域,直接修改预览图片样式即可。
  • 文件全部上传结束后,需要清空文件队列对象,否则再次上传时,还会附带之前的文件。
4. 补充:对上传组件添加选择图片数量限制

若还需要更人性化一点的话,可以对上传组件进行重载,修改配置中的 number 参数。这里就不再演示了。

const len = fileListDom.find('.file-list-item').length;
uploadInst.reload({
    number: 10-len
});

相关参考
图片/文件上传 - layui.upload
layui 文件上传upload.render清空已选择文件并重新选择同名文件

下载源码

  • 5
    点赞
  • 15
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
要将文件上传到MySQL数据库,需要先将文件转换成二进制数据,然后将其插入到数据库中的BLOB类型字段中。以下是使用Layui上传图片并将其存入MySQL数据库的示例: 1. 在HTML中添加文件上传表单: ```html <form class="layui-form" action="" enctype="multipart/form-data"> <div class="layui-form-item"> <div class="layui-upload"> <button type="button" class="layui-btn" id="uploadBtn">上传图片</button> <div class="layui-upload-list"> <img class="layui-upload-img" id="previewImg"> <p id="previewText"></p> </div> </div> </div> </form> ``` 2. 引入LayuijQuery库: ```html <link rel="stylesheet" href="https://cdn.staticfile.org/layui/2.5.6/css/layui.min.css"> <script src="https://cdn.staticfile.org/jquery/3.5.1/jquery.min.js"></script> <script src="https://cdn.staticfile.org/layui/2.5.6/layui.min.js"></script> ``` 3. 初始化Layui上传组件: ```javascript layui.use('upload', function(){ var upload = layui.upload; //执行上传 var uploadInst = upload.render({ elem: '#uploadBtn', //绑定元素 url: '/upload/', //上传接口 accept: 'images', //允许上传文件类型 size: 1024, //限制文件大小,单位KB done: function(res){ //上传成功回调 $('#previewImg').attr('src', res.data.src); //显示预览图 $('#previewText').html(res.data.title); //显示文件名 //将文件二进制数据存入数据库 $.ajax({ type: 'POST', url: '/saveToDB/', data: { imageData: res.data.imageData //文件的二进制数据 }, success: function(data){ console.log(data); }, error: function(){ console.log('上传失败'); } }); }, error: function(){ //上传失败回调 console.log('上传失败'); } }); }); ``` 4. 在服务器端处理上传文件,并将其存入MySQL数据库: ```php <?php //获取上传文件二进制数据 $imageData = file_get_contents($_FILES['file']['tmp_name']); //连接MySQL数据库 $servername = "localhost"; $username = "username"; $password = "password"; $dbname = "dbname"; $conn = new mysqli($servername, $username, $password, $dbname); //将文件二进制数据插入到数据库中 $stmt = $conn->prepare("INSERT INTO images (image_data) VALUES (?)"); $stmt->bind_param("b", $imageData); $stmt->execute(); $stmt->close(); $conn->close(); ?> ``` 注意:以上代码仅供参考,具体实现需要根据自己的实际情况进行调整。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值