layui.upload.js 拖拽文件/文件夹上传下载

  • 前言
    • js代码
    • 页面使用(我这里用的是uploader.jsp)
    • CSS文件
    • 上传效果
    • 总结

前言

项目需求完成文件上传,可以拖拽上传文件/文件夹,基于layui的upload.js增强完成该需求

js代码

layui的引入和使用就不说了,懂的都懂,不懂去学习一下,废话不多说,直接上代码.基于upload.js自定义uploadFile.js用于实现需求功能

/*** author: wz* referenceAddress:文件,文件夹上传*/
layui.define(["layer", "upload",'element','table'], function (e) {"use strict";var $ = layui.$, layer = layui.layer, upload = layui.upload,element=layui.element,table=layui.table,tableArr=[],datas=[],model={},unfinishedList=[],beingList=[],timer=null,beingCount=10,beingFlag=false,timerTable=null,keepTime=0;//配置server tokenvar conf = JSON.parse(localStorage.conf);var server = conf.file.server;var token = conf.file.token;function renderFile(option) {var uploadInst=upload.render({elem: '#' + option.id,auto: option.auto||false,accept: option.accept,acceptMime: option.acceptMime,exts: option.exts,size: option.size||0,multiple: option.multiple||true,number: option.number||0,choose:function (obj) {var loadingIndex = layer.load(2, { //icon支持传入0-2shade: [0.5, 'gray'], //0.5透明度的灰色背景content: '读取文件...',success: function (layero) {}});obj.preview(function (index, file) {loadingIndex="";layer.closeAll();var fileUuid=uuid();uploadServer(file,fileUuid,"0",file.webkitRelativePath,option);});setTimeout(function () {if(loadingIndex){layer.closeAll();layer.msg("上传类型错误,请检查!", {icon: 5});}},20000);}});selectEvent(option.id);}function selectEvent(id) {$('#' + id).bind("dragover",function (e) {$(this).css("background","#e9f5fe");})$('#' + id).bind("dragleave",function (e) {$(this).css("background","");})$('#' + id).bind("mouseover",function (e) {$(this).css("background","#e9f5fe");})$('#' + id).bind("mouseout",function (e) {$(this).css("background","");})}//上传中转站function uploadServer(file,fileUuid,type,path,option,serialNumber) {var parentId=option.parentId;if(type=='0'){//文件上传tableData(file,fileUuid,option.parentId,option.nodeId,"0");}else {//文件夹上传if(path){var split=path.split("/");for (var i = 0; i < split.length; i++) {if(i<=split.length-2){parentId=folderLoading(split[i],parentId,option.nodeId,serialNumber);}else {tableData(file,fileUuid,parentId,option.nodeId,"1");}}}}unfinishedList.push({file:file,//文件对象type:type,//文件上传path:path,//文件路径uuid:fileUuid,//唯一标识parentId:parentId});if(timer==null){timer=setInterval(function (d) {if(unfinishedList.length>0){if(beingList.length<beingCount){//控制同时上传个数var diff=beingCount-beingList.length;for (let i = 0; i <diff ; i++) {if(unfinishedList.length>i){beingList.push(unfinishedList[i].uuid);uploadDone(option,unfinishedList[i].file,unfinishedList[i].uuid,unfinishedList[i].parentId);}}for (let i = 0; i <diff; i++) {if(unfinishedList.length>0){unfinishedList.splice(0,1);}}}}else {//上传完成if(timer!=null){clearInterval(timer);timer=null;}}},500);}if(timerTable==null){timerTable=setInterval(function (d) {keepTime++;//计时if(unfinishedList.length==0&&beingList.length==0){reloadTable(option,true);clearInterval(timerTable);timerTable=null;}else {reloadTable(option,false);}},1000);}}/*文件夹拖拽上传在 drop 事件中获取 e.dataTransfer.items ,是一个 DataTransferItemList 对象,遍历得到 DataTransferItem 对象用 webkitGetAsEntry 方法得到 FileSystemEntry 对象根据 isFile 属性判断 entry 是文件还是文件夹。是文件的话,用 file 方法获取 File 对象;是文件夹的话,递归地用 reader 读取包含的文件原文链接:https://blog.csdn.net/tangran0526/article/details/104156857* */function scanFiles(e,option) {e.preventDefault();//var files=[];var item=e.dataTransfer.items;//获取DataTransferItemList 对象if(item&&item.length>0){var serialNumber=uuid();//同一上传批次序列号下的同名文件夹不重复添加for (var it of item) {var entry=it.webkitGetAsEntry();//获取 FileSystemEntry 对象fileReader(entry,function (file, path) {uploadServer(file,uuid(),"1",path,option,serialNumber);});}}}function fileReader(entry,succ) {if (entry.isFile) {entry.file(file => {// 这里的 file.webkitRelativePath 都是 "" ,不是我们想要的.// entry.fullPath 是前面带斜杠的,要把斜杠去掉的let path = entry.fullPath.substring(1);succ(file,path);});} else {getEntryDirectoryFiles(entry).then(data=>{data.forEach(_this=>{fileReader(_this,succ);});});}}// 获取文件夹所有子集function getEntryDirectoryFiles(entry) {const reader = entry.createReader()// 一次最多只能读100,防止出现文件夹内文件个数过多,加一个变量收集最新的结果let res = []return read();async function read() {const files = await new Promise((resolve, reject) =>reader.readEntries((entries) => {// 只上传一层文件,过滤文件夹中包含的文件夹//const fileEntries = entries.filter((entry) => entry.isFile)const filesPromise = entries.map((e) => new Promise((resolve) =>resolve(e)))Promise.all(filesPromise).then(resolve)}, reject))// 保存当前读取文件res = [...res, ...files]// chrome浏览器一次读取最多获取100个文件,多于100个需要再次读取if (files.length < 100) {return res}return read()}}async function read(entry,res) {const reader = entry.createReader();for (let i = 0; i < 3; i++) {await new Promise((resolve, reject) =>{debugger;reader.readEntries((entries) => {debugger;console.log(entries.length);// 只上传一层文件,过滤文件夹中包含的文件夹})})}}function renderDrop(option) {$("#"+option.dropId).click(function (e) {$("#"+option.id).click();});// 获取文件夹document.getElementById(option.dropId).ondrop =  (e) => {scanFiles(e,option);}selectEvent(option.dropId);}function renderFolder(option) {//上传文件夹$("#"+option.id).change(function(){var files = this.files,serialNumber=uuid();for (var file of files) {uploadServer(file,uuid(),"1",file.webkitRelativePath,option,serialNumber)}files=null;});}function uploadDone(option,file,fileUuid,parentId) {//if(option.tableId)reloadTable(option,false);burstUpload(option,file,fileUuid,function (fileID, res, name) {//文件上传完成回调resLoading(res,fileID,option,parentId);if(option.tableId){var fin=tableArr.findIndex(a=>{return a.fileUuid==fileID});if(fin>=0){tableArr[fin].percent="100.00";tableArr[fin].fileurl=res.url;// if(unfinishedList.length==0&&beingList.length==0){//     reloadTable(option,true);// }else {//     reloadTable(option,false);// }}}if (typeof option.allBurst != 'undefined' && option.allBurst instanceof Function) {option.allBurst(fileID, res, name);//每次单个文件上传成功以后的回调}});}function resLoading(res,fileID,option,parentId) {//装载文件柜对象model['filetype']=getFileType(res.name);model['fileurl']=res.url;model['filename']=res.name;model['fileshuffix']=res.type;model['filesize']=res.size;model['thumbnail']=res.thumbnailPath;model['sizeDes']=res.sizeDes;model['publishtime']=res.timeDes;model['parentId']=parentId;model['fileUuid']=fileID;model['nodeId']=option.nodeId;datas.push(model);model={};//计算文件夹大小// if(parentId){//     getFileSize(parentId,res.size||0);// }if (typeof option.onChange != 'undefined' && option.onChange instanceof Function) {option.onChange(datas);}}function getFileType(fileName) {//根据文件后缀判断文件类型var docReg = /(doc|docx|rtf|xls|xlsx|ppt|pptx|pdf)$/;var imgReg = /(jpg|jpeg|png|gif|cad)$/;var mp3Reg = /(mp3)$/;var mp4Reg = /(mp4|avi)$/;var zipReg = /(zip|rar|war)$/;var fileReg = /(bak|txt|sql|exe|bat|md|htm|html)$/;if (fileName) {var name = fileName.toLocaleLowerCase();if (docReg.test(name)) {return 1;} else if (imgReg.test(name)) {return 2;} else if (mp3Reg.test(name)) {return 3;} else if (mp4Reg.test(name)) {return 4;} else if (zipReg.test(name)) {return 5;} else if (fileReg.test(name)) {return 6;} else {return 7;}} else {return 7;}}//生成文件夹function folderLoading(filename,parentId,nodeId,serialNumber) {var fileUuid=parentId;var fin=datas.findIndex(a=>{return a.filename==filename&&a.parentId==parentId&&a.nodeId==nodeId});if(fin>=0){if(datas[fin].serialNumber!=serialNumber){filename=filename+"(1)";fileUuid=folderLoading(filename,parentId,nodeId,serialNumber);}else {fileUuid=datas[fin].fileUuid;}}else {fileUuid=uuid();model['filetype']=0;model['fileurl']='';model['filename']=filename;model['fileshuffix']='';model['filesize']=0;model['thumbnail']='';model['sizeDes']='';model['publishtime']=null;model['parentId']=parentId;model['fileUuid']=fileUuid;model['nodeId']=nodeId;model['serialNumber']=serialNumber;datas.push(model);model={};}return fileUuid;}function tableData(file,fileUuid,parentId,nodeId,filewar) {model.fileUuid=fileUuid;model.filename=file.name||"/";model.filesize=file.size||0;model.filetype=file.type||"/";model.percent="0";model.filewar=filewar;//上传方式model.fileurl='';//文件路径model.parentId=parentId;model.nodeId=nodeId;model.file=file;if(tableArr&&tableArr.length>0){tableArr.unshift(model);}else {tableArr.push(model);}model={};}//计算文件夹大小function getFileSize(parentId,fileSize) {var fin=datas.findIndex(a=>{return a.fileUuid==parentId});if(fin>=0){datas[fin].filesize=parseInt(datas[fin].filesize)+parseInt(fileSize);getFileSize(datas[fin].parentId,datas[fin].filesize);}}function uuid() {var s = [];var hexDigits = "0123456789abcdef";for (var i = 0; i < 36; i++) {s[i] = hexDigits.substr(Math.floor(Math.random() * 0x10), 1);}s[14] = "4";  // bits 12-15 of the time_hi_and_version field to 0010s[19] = hexDigits.substr((s[19] & 0x3) | 0x8, 1);  // bits 6-7 of the clock_seq_hi_and_reserved to 01s[8] = s[13] = s[18] = s[23] = "-";return s.join("");}function picTime(val) {var hh = parseInt(val/3600);if(hh<10) hh = "0" + hh;var mm = parseInt((val-hh*3600)/60);if(mm<10) mm = "0" + mm;var ss = parseInt((val-hh*3600)%60);if(ss<10) ss = "0" + ss;var length = hh + ":" + mm + ":" + ss;if(val>0){return length;}else{return "0秒";}}//移除文件夹,移除依据:如果是该文件是该目录下唯一文件则移除该目录function removeDatas(index,option) {var data=datas[index];datas.splice(index,1);var pin=datas.findIndex(a=>a.fileUuid==data.parentId);var pData=datas[pin];if(pin>=0){//查询是否还有子节点var cin=datas.findIndex(a=>a.parentId==pData.fileUuid);if(cin<0){//没有子节点,也要被删除removeDatas(pin,option);}}if (typeof option.onChange != 'undefined' && option.onChange instanceof Function) {option.onChange(datas);}}function reloadTable(option,flag) {var str='<script type="text/html" id="toolbar"><button class="layui-btn layui-btn-danger layui-btn-sm" lay-event="del">删除</button></script>'var allCount=tableArr.length,successCount=0,failCount=0;table.render({elem: '#'+option.tableId,data:tableArr,toolbar : str//,height : 'full-200',cols: [[ //表头{type:'checkbox'},{type:'numbers',title: '序号'},{field: 'fileUuid', title: 'uuid', hide: true,align:'center'},{field: 'filewar', title: '上传方式',align:'center',templet:function (d) {if(d.filewar=='1')return "文件夹上传";return "文件上传";}},{field: 'filename', title: '文件名称',align:'center'},{field: 'filesize', title: '文件大小',align:'center'},{field: 'filetype', title: '文件类型',align:'center'},{field: 'percent', title: '上传进度',align:'center',width:"20%",templet:function (d) {//layui-bg-blueif(d.percent=="100.00"){return '<div class="layui-progress layui-progress-big layui-progress-rate" lay-filter="process'+d.fileUuid+'" lay-showPercent="true">' +'<div class="layui-progress-bar layui-bg-blue" lay-percent="'+d.percent+'%" id="procent'+d.fileUuid+'"></div></div>'}else {return '<div class="layui-progress layui-progress-big layui-progress-rate" lay-filter="process'+d.fileUuid+'" lay-showPercent="true">' +'<div class="layui-progress-bar" lay-percent="'+d.percent+'%" id="procent'+d.fileUuid+'"></div></div>'}}},{title: '操作',align:'center',width:"10%",templet : function (d) {if(d.percent=="100.00"){successCount++;return '<a class="layui-btn layui-btn-danger layui-btn-xs" lay-event="del">删除</a>';}else if(d.percent=="0"&&flag){failCount++;return '<a class="layui-btn layui-btn-normal layui-btn-xs" lay-event="tautology">重试</a>';}else {return '';}}}]],limit:9999999,done:function (res, curr, count) {if(option.detailsId){var ps=successCount==0?0:((successCount*100)/allCount).toFixed();var detailStr='<div class="layui-fluid" style="padding: 0"><div class="file_upload_title">' +'<span>共&nbsp;<b>'+allCount+'</b>&nbsp;个文件,上传完成:<b>'+successCount+'</b>,' +'正在上传:<b>'+beingList.length+'</b>,上传失败:<b>'+failCount+'</b>,总进度:<b>'+ps+'%</b>,' +'总用时:<b>'+picTime(keepTime)+'</b></span></div></div>';$("#"+option.detailsId).html(detailStr);}var h=$(document).height();var pss=1-(ps/100);$(document).scrollTop((h*pss).toFixed(2));element.render('progress');}});//头工具栏事件table.on('toolbar('+option.tableId+')', function(obj) {var checkStatus = table.checkStatus(obj.config.id);var data = checkStatus.data;switch (obj.event) {case 'del':if (data.length == 0) {layer.alert('请选择您想要移除的数据!');break;}var urls = "";for (var i = 0; i < data.length; i++) {if(data[i].fileurl)urls += data[i].fileurl + "&;&";}layer.confirm("确定移除文件?", {icon : 3,title : '移除',btn: ["确定","取消"] //按钮}, function(index) {$.ajax({url: server + 'del',headers: {Authorization: token},type: "POST",data: {url:urls,decollator:"&;&"},success: function (res) {if (res.code === 0) {for (var datum of data) {var fin=tableArr.findIndex(a=>{return a.fileUuid==datum.fileUuid});if(fin>=0){tableArr.splice(fin,1);}var din=datas.findIndex(a=>{return a.fileUuid==datum.fileUuid});if(din>=0){removeDatas(din,option);}}reloadTable(option);layer.msg("移除成功", {icon: 6});} else {layer.msg("移除失败", {icon: 5});}},error: function (msg) {layer.msg("移除失败", {icon: 5});return false;}});});break;}});//行工具条table.on('tool('+option.tableId+')', function(obj) {var data = obj.data;switch (obj.event) {case 'del':layer.confirm("确定移除文件?", {icon : 3,title : '移除'}, function(index) {$.ajax({url: server + '/del',headers: {Authorization: token},type: "POST",data: {url:data.fileurl,decollator:"&;&"},success: function (res) {if (res.code === 0) {var fin=tableArr.findIndex(a=>{return a.fileUuid==data.fileUuid});if(fin>=0){tableArr.splice(fin,1);reloadTable(option);}var din=datas.findIndex(a=>{return a.fileUuid==data.fileUuid});if(din>=0){removeDatas(din,option);}layer.msg("移除成功", {icon: 6});} else {layer.msg("移除失败", {icon: 5});}},error: function (msg) {layer.msg("移除失败", {icon: 5});return false;}});});break;case 'tautology':uploadDone(option,data.file,data.fileUuid,data.parentId);break;}});}function uploadFail(option,fileID) {if(fileID){//上传完成移除正在上传标记var fin=beingList.findIndex(a=>{return a==fileID});if(fin>=0) beingList.splice(fin,1);// var uin=tableArr.findIndex(a=>{return a.fileUuid==fileID});// if(uin>=0) tableArr.splice(uin,1);}//reloadTable(option,false);}function burstUpload(option, file, fileID, succ) {//文件上传//var TMap = new Map();var arrayAJAX = [];var timer = setTimeout(function () {//每个文件异步处理var name = file.name,        //文件名size = file.size,        //总大小succeed = 0;var shardSize = 5 * 1024 * 1024;    //以5MB为一个分片var shardCount = Math.ceil(size / shardSize);   //总片数var uuid = fileID;//文件idvar time = new Date().getTime();//时间戳for (var i = 0; i < shardCount; ++i) {//文件分块上传// setTimeout(function () {//每个分块异步处理//计算每一片的起始与结束位置var start = i * shardSize, end = Math.min(size, start + shardSize);var objf = file.slice(start, end);//构造一个表单,FormData是HTML5新增的var form = new FormData();form.append("name", name);  //文件名form.append("size", size);  //大小form.append("uuid", uuid);//上传idform.append("time", time);//时间form.append("file", objf);  //slice方法用于切出文件的一部分form.append("chunks", shardCount);   //总片数form.append("chunk", i);        //当前是第几片//Ajax提交arrayAJAX.push($.ajax({url: server + 'upload',headers: {Authorization: token},type: "POST",data: form,//async: false,         //异步processData: false,  //很重要,告诉jquery不要对form进行处理contentType: false,  //很重要,指定为false才能形成正确的Content-TypedataType: "json",mimeType: "multipart/form-data",success: function (res) {if (res.code === 0) {++succeed;var percent = succeed / shardCount * 100;var progress = percent.toFixed(2);$("#procent"+fileID).attr('lay-percent',progress+'%');element.init();element.progress('process' + fileID, progress + "%");//更新进度条if (typeof option.burst != 'undefined' && option.burst instanceof Function) {option.burst(uuid, progress, res, name);//每次分片上传成功以后的回调}//Uploader.proFile(option, uuid, progress);//列表进度更新if (succeed === shardCount) {//每完成一个 修改完成样式$("#procent"+fileID).attr('class',"layui-progress-bar layui-bg-blue");if(fileID){//上传完成移除正在上传标记var fin=beingList.findIndex(a=>{return a==fileID});if(fin>=0) beingList.splice(fin,1);}succ(uuid, res, name);//成功回调}} else {layer.msg(res.msg);uploadFail(option,fileID);}},error: function (msg,textStatus) {if(msg.readyState==0){layer.msg("文件读取失败,请检查!");}else {layer.msg("文件服务器异常,请联系管理员!");}uploadFail(option,fileID);return false;}}));}}, 10);//文件上传,异步处理TMap.set(fileID, arrayAJAX);option.timer = TMap;}var uploadFile = {initFile:function (option) {if (option.hasOwnProperty('id')&&option.hasOwnProperty('parentId')&&option.hasOwnProperty('nodeId')){renderFile(option);}else {layer.msg("文件上传组件初始化参数丢失,请检查", {icon: 5});}},initFolder:function (option) {if (option.hasOwnProperty('id')&&option.hasOwnProperty('parentId')&&option.hasOwnProperty('nodeId')&&option.hasOwnProperty('dropId')){renderDrop(option);renderFolder(option);}else {layer.msg("文件夹上传组件初始化参数丢失,请检查", {icon: 5});}},downFile:function (url, params,async) {if (url != null) {if(async){//异步下载if (params != null) {Object.keys(params).forEach(function (item, i, arr) {if(i==0){url+="?"+item+"="+params[item];}else {url+="&"+item+"="+params[item];}})}var xhr = new XMLHttpRequest();xhr.open('POST', url, true);        // 也可以使用POST方式,根据接口xhr.responseType = "blob";    // 返回类型blobxhr.onload = function () {if (this.status === 200) {var blob = this.response;var filename=xhr.getResponseHeader("Content-Disposition").split(";")[1].split("filename=")[1];//从响应头中获取文件名称var reader = new FileReader();reader.readAsDataURL(blob);    // 转换为base64,可以直接放入a表情hrefreader.onload = function (e) {var a = document.createElement('a');a.download = filename;//下载文件名a.href = e.target.result;$("body").append(a);    // 修复firefox中无法触发clicka.click();$(a).remove();}}};// 发送ajax请求xhr.send()}else{//同步提交,form默认提交方式var form = $("<form></form>").attr("action", url).attr("method", "post");if (params != null) {for (var key in params) {form.append($("<input/>").attr("type", "hidden").attr("name", key).attr("value", params[key]));}form.appendTo('body').submit().remove();}}return false;}else {layer.msg("未找到下载连接,请检查!", {icon: 5});}}};//输出test接口e('uploadFile', uploadFile);
});

页面使用(我这里用的是uploader.jsp)

<%@page language="java" contentType="text/html; charset=UTF-8" pageEncoding="UTF-8"%>
<%@taglib prefix="shiro" uri="http://shiro.apache.org/tags"%>
<%@taglib uri="http://java.sun.com/jsp/jstl/core" prefix="c"%>
<%@taglib uri="http://java.sun.com/jsp/jstl/fmt" prefix="fmt"%>
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>模块系统</title>
<meta name="renderer" content="webkit">
<meta http-equiv="X-UA-Compatible" content="IE=edge,chrome=1">
<meta name="viewport"content="width=device-width, initial-scale=1.0, minimum-scale=1.0, maximum-scale=1.0, user-scalable=0">
<link rel="stylesheet" href="../static/layui/css/layui.css" media="all">
<link rel="stylesheet" href="../static/layuiadmin/style/admin.css" media="all">
<link rel="stylesheet" href="../static/library.css" media="all">
<link rel="stylesheet" href="../static/modules/icon/iconfont.css" media="all"><style>html{ background-color: #fff;}body{ padding: 0 15px;}.layui-upload-drag{ width: 100%; padding: 5px 10px; box-sizing: border-box; border: dashed 1px #ccc;}.layui-upload-drag p{ height: 26px; line-height: 26px;}.layui-upload{ position: relative; width: 100px;}.layui-upload input{ width: 100%; height: 100%; position: absolute; top: 0; left: 0; z-index: 99; opacity: 0;}#upload-btn{ width: 100%; height: 35px; line-height: 35px; color: #fff; background: linear-gradient(to right, #1E9FFF,#60a0ff);border-radius: 5px; border: 0;}#upload-btn span{ font-size: 14px; color: #fff;}#upload-btn i{ display: inline-block; margin-right: 2px; font-size: 13px; color: #fff;}</style>
</head>
<body><div class="file_locat"><div class="file_tab"><ul><li class="file_tab_active"><p>文件上传</p></li><li><p>文件夹上传</p></li></ul><div class="file_tab_line"></div></div><div class="file_contain"><ul><li class="file_act"><div class="layui-fluid" style="padding: 0"><div class="file_upload_title">文件上传:</div><div class="layui-inline" style="width: 50%"><div class="layui-upload-drag" id="fileUpload"><p style="font-weight: bold; font-family: arial, sans-serif; font-size: 12px">点击上传,或将文件拖拽到此处</p></div></div></div></li><li><input height="100%" type='file' id="folderUpload" hidden webkitdirectory multiple="multiple"><div class="layui-fluid" style="padding: 0"><div class="file_upload_title">文件夹上传:</div><div class="layui-inline" style="width: 50%"><div class="layui-upload-drag" id="folderUp"><p style="font-weight: bold; font-family: arial, sans-serif; font-size: 12px">点击上传,或将文件夹拖拽到此处</p></div></div></div></li></ul><div id="uploadDetails"></div></div></div><table id="fileTable" lay-filter="fileTable"></table><script src="../static/layui/layui.js"></script><script>var uploadFile = [];var uploadImg =[];var parentId='${parentId}';var nodeId='${nodeId}';var files = [];// 阻止浏览器打开新标签,ondrop/ondragover/ondragenter(最好加上这个防兼容问题)window.ondragover = (e) => e.preventDefault();layui.config({base: '../static/modules/'}).extend({uploadFile: 'uploader/uploadFile'}).use(['element','form','uploadFile','upload'], function () {var $ = layui.$;var element = layui.element;var form = layui.form;var uploadFile = layui.uploadFile;uploadFile.initFile({id: 'fileUpload',accept: 'file',acceptMime: '',exts: '',size: 0,multiple:true,number:0,tableId:'fileTable',detailsId:'uploadDetails',//上传详情parentId:parentId,nodeId:nodeId,onChange:function (param) {files=param;}});uploadFile.initFolder({id: 'folderUpload',tableId:'fileTable',dropId:'folderUp',detailsId:'uploadDetails',//上传详情parentId:parentId,nodeId:nodeId,onChange:function (param) {files=param;}});var _aW = $(".file_tab ul").find(".file_tab_active").width();var _aP = $(".file_tab .file_tab_active").position();$(".file_tab .file_tab_line").css({ left: _aP, width: _aW});$(".file_tab li").on("click", function(){var aP = $(this).position();var aW = $(this).width();var fileIndex = $(this).index();// var text=$(this).text();// if(text.replace(/" "/g,"")=="文件夹上传"){//     initFolder();// }else {//   initFile();// }$(".file_tab li").removeClass("file_tab_active");$(this).addClass("file_tab_active");$(".file_tab .file_tab_line").css({left: aP.left, width: aW})$(".file_contain li").hide();$(".file_contain li").eq(fileIndex).show();});});function getFiles() {return files;}</script>
</body>
</html>

CSS文件

.layui-layer-title{display: flex;align-items: center;
}
.file_locat{position: fixed;left: 0;top: 0;z-index: 1000;box-sizing: border-box;width: 100%;padding: 0 15px 7px;background: #fff;
}
.file_upload_title{display: inline-block;line-height: 34px;margin-right: 5px;
}
.file_tab{border-bottom: solid 1px #e5e5e5;margin-bottom: 18px;position: relative;
}
.file_tab ul{overflow: hidden;
}
.file_tab li{float: left;padding: 15px 0;margin-right: 30px;cursor: pointer;position: relative;
}
.file_tab .file_tab_line{display: block;position: absolute;left: 0;bottom: 0;z-index: 9;height: 3px;background: #2492ef;transition: all 0.3s;
}
.file_tab .file_tab_active p{font-weight: bold;color: #2492ef;
}
.file_contain li{display: none;
}
.file_contain .file_act{display: block;
}
#uploadDetails{margin-top: 10px;
}
.file_upload_title span{color: #666;
}
.layui-progress-rate{margin-top: 5px;
}
.layui-table-view{margin: 170px 0 10px;background: #f9f9f9;
}
.layui-table-view .layui-table{width: 100%;
}
.layui-layer-btn{background-color: #f8f8f8;border-top: solid 1px #e1e1e1;
}
.layui-form-checked[lay-skin=primary] i{border-color: #7cc2fc !important;background-color: #57a1fd;
}
.layui-form-checkbox[lay-skin=primary]:hover i{border-color: #7cc2fc;
}

上传效果

总结

这个上传js中包含大量我认为值得记录的东西,所以写下来当备忘录,包括
上传文件夹获取文件及路径的处理,异/同步下载问题,上传分片问题,表格进度条问题,表格滚动条问题
,这些都是值得记录的

基于layui.upload.js 拖拽文件/文件夹上传下载相关推荐

  1. js拖拽图片到浏览器上传

    拖拽的事件有很多,这个懂的都懂不懂的就- <!doctype html> <html> <head> <meta charset="utf-8&qu ...

  2. 拖拽或点击上传(支持苹果safari浏览器)

    <input type="file" value="上传">  拖拽或点击上传(在safari浏览器不支持拖拽),主要解决safari浏览器的拖拽问 ...

  3. 如何在Webstorm/Phpstorm中设置连接FTP,并快速进行文件比较,上传下载,同步等操作...

    Phpstorm除了能直接打开localhost文件之外,还可以连接FTP,除了完成正常的数据传递任务之外,还可以进行本地文件与服务端文件 的异同比较,同一文件自动匹配目录上传,下载,这些功能是平常I ...

  4. java 文件下载 组件_java文件夹上传下载组件

    核心原理: 该项目核心就是文件分块上传.前后端要高度配合,需要双方约定好一些数据,才能完成大文件分块,我们在项目中要重点解决的以下问题. *如何分片: *如何合成一个文件: *中断了从哪个分片开始. ...

  5. ie11 java 下载文件_Javaweb实现上传下载文件的多种方法

    在Javaweb中,上传下载是经常用到的功能,对于文件上传,浏览器在上传的过程中是以流的过程将文件传给服务器,一般都是使用commons-fileupload这个包实现上传功能,因为commons-f ...

  6. Java实现七牛云文件或图片上传下载

    写在前面 前些天发现了一个巨牛的人工智能学习网站,通俗易懂,风趣幽默,忍不住分享一下给大家:人工智能学习网站 文章目录 写在前面 一.准备工作 1.1.为什么选择七牛云? 1.2.七牛云注册 二.ja ...

  7. C++ vs2017 - libcurl - http请求 代码大全(请求数据,上传下载文件,多线程上传下载文件)

    在网上搜寻各种libcurl的用法,将代码集合于此! 目录 一.配置curl项目 二.Curl 请求参数 1. CURLOPT_POST 2. CURLOPT_URL 3. CURLOPT_HTTPH ...

  8. linux curl 命令 http请求、下载文件、ftp上传下载

    1. curl 命令简介 cURL(CommandLine Uniform Resource Locator),是一个利用 URL 语法,在命令行终端下使用的网络请求工具,支持 HTTP.HTTPS. ...

  9. 使用Git工具从GitHub上文件代码进行上传下载(图文详细)

    1.注册一个GitHub账号 GitHub: Where the world builds software · GitHub  此链接为GitHub官网 由于GitHub是国外的网站,访问会很慢,又 ...

最新文章

  1. 利用Nginx轻松实现Ajax的跨域请求(前后端分离开发调试必备神技)
  2. 第三章-分布式文件系统HDFS
  3. 网工协议基础(3) IP地址
  4. lgg7深度详细参数_深度学习平均场理论第七讲:Batch Normalization会导致梯度爆炸?...
  5. 新网卡不能绑定“旧”IP故障的解决
  6. 技术动态 | 北京大学计算机所邹磊教授研究组开源面向 RDF 知识图谱的自然语言问答系统 gAnswer...
  7. 阿里千万实例可观测采集器-iLogtail正式开源
  8. (61)FPGA译码器实现(function)
  9. 【IDEA】Cause: invalid type code: 8D
  10. Monkey测试:日志信息分析
  11. 增强型绿植植被指数_MODIS增强型植被指数EVI与NDVI初步比较-中国科学院.PDF
  12. 在手机/平板上安装kali系统
  13. click与onclick的区别
  14. 《雨夜》 RocketMQ源码系列(一) NameServer 核心源码解析
  15. 现在的FM电台呀,什么玩艺儿
  16. python Deformation Transfer for Triangle Meshes
  17. php 超出整形范围,频率超出范围怎么办
  18. 使用data breakpoint 追踪地址寄存器被修改的问题
  19. vue+element下拉框实现二级联动
  20. kankan转载:Android实现3d翻转效果

热门文章

  1. Android-网络请求封装类-okhttp
  2. Gogs搭建git服务器
  3. 二分法查找---logn复杂度
  4. MAC下的切图神器!SLICY使用说明
  5. Cutterman切图神器安装
  6. 上,明天上班了???
  7. 常用的前端和服务器数据的传输方式
  8. 悬镜安全丨第三期全球一周安全情报(8.6-8.12)
  9. aiohttp mysql_python异步爬虫asyncio+aiohttp+aiomysql异步存入数据
  10. 【Axure视频教程】中继器表格——删除行内容