文件下载是一个Web中很是经常使用的功能,不过你是作内部管理系统仍是作面向公众的互联网公司都会遇到这个问题,对于下载通常有点实际开发经验的都会本身解决,上周弄了一下多文件下载,业务场景就是一条数据详细信息一个附件原来只须要一个pdf就行,如今要求添加两张图片,一次性的下载出来,以前没遇到这种问题。网上找了找,有了思路,就是须要隐藏一个iframe,而后设置src,大概的原理是这样的,以后本身开始动手撸代码去了:javascript
业务场景来源于公司的一个客户管理系统,为了之后其余地方也能调用,扩展了一下方法:html
(function($) { var methods = { _download: function(options) { var triggerDelay = (options && options.delay) || 100; var removeDelay = (options && options.removeDelay) || 1000; this.each(function(index, item) { methods._createIFrame(item, index * triggerDelay, removeDelay); }); }, _createIFrame: function(url, triggerDelay, removeDelay) { //动态添加iframe,设置src,而后删除 setTimeout(function() { var frame = $('<iframe style="display: none;" class="multi-download"></iframe>'); frame.attr('src', url); $(document.body).after(frame); setTimeout(function() { frame.remove(); }, removeDelay); }, triggerDelay); } }; $.fn.multiDownload = function(options) { methods._download.apply(this, arguments); }; })(jQuery);
上面的代码没什么注释,iframe会加载src的内容,以上的程序调用很简单,这个数组的里面的地址放的是服务器请求的地址,须要保证一点的就是服务器的原来这个地址是能够下载文件的:前端
var downloadUrl=['服务器请求地址1','服务器请求地址2']; $(downloadUrl).multiDownload();
当时完成这个功能很顺利,而后前天我想写篇博客记录一下,但我比较懒,懒的写服务端代码,直接把文件放在本地,去请求一下,企图得到一样的结果,失败了,先来看行代码:java
<a href="Content/keso1.zip">zip文件</a>
这个连接咱们点击一下直接下载了zip文件,可是若是你改为xx.jpg,xx.txt,由于浏览器根据 MIME TYPE(资源的媒体类型),若是请求的是后台服务器须要指定一下Content-type,处理本地的文件,无法告诉浏览器某个文件的 MIME Type 的状况下,浏览器也会作一些默认的处理,这和我的的操做系统中给文件配置的 MIME Type 有关。本人电脑是Window,若是须要看具体Content-type,详细地址以下:jquery
因此一般图片和文本有的时候就直接打开显示,而rar,zip文件浏览器不识别Content-type当作文件下载;数组
为了能直接下载这个图片,找到了Html5中有一个download属性,若是你将一个a标签加上一个download属性,jpg文件直接当作文件下载了,href就是图片地址,浏览器兼容没有测试,毕竟5来日方长:浏览器
<a download="keso.jpg" href="keso.jpg">Html5下载</a>
这个时候就能够动手该原来的代码,若是点击的时候直接这个方法是能够自动下载文件的,单文件下载以后就能够进行多文件下载啦:服务器
function downloadHtml5(url){ var aLink = document.createElement('a'); , evt = document.createEvent("HTMLEvents"); evt.initEvent("click"); aLink.download =""; aLink.href =url; aLink.dispatchEvent(evt); }
修改扩展方法:app
(function($) { var methods = { _download: function(options) { var triggerDelay = (options && options.delay) || 100; var removeDelay = (options && options.removeDelay) || 1000; if (options.source === "server") { this.each(function(index, item) { methods._createIFrame(item, index * triggerDelay, removeDelay); }); }; if (options.source === "local") { this.each(function(index, item) { methods._createLink(item, index * triggerDelay, removeDelay); }); }; }, _createIFrame: function(url, triggerDelay, removeDelay) { //动态添加iframe,设置src,而后删除 setTimeout(function() { var frame = $('<iframe style="display: none;" class="multi-download"></iframe>'); frame.attr('src', url); $(document.body).after(frame); setTimeout(function() { frame.remove(); }, removeDelay); }, triggerDelay); }, //download属性设置 _createLink: function(url, triggerDelay, removeDelay) { var aLink = document.createElement("a"), evt = document.createEvent("HTMLEvents"); evt.initEvent("click"); //须要添加属性,不须要设置文件名,我的测试就是原文件名,设为空没有问题,具体状况具体分析 aLink.download = ""; aLink.href = url; aLink.dispatchEvent(evt); } }; $.fn.multiDownload = function(options) { methods._download.apply(this, arguments); }; })(jQuery);
最终代码调用,六个文件均可如下载:测试
<html> <head> <meta http-equiv="Content-Type" content="text/html; charset=utf-8" /> <title>JQuery文件下载</title> <script type="text/javascript" src="jquery-1.11.1.js"></script> <script type="text/javascript" src="jquery.multidownload-FlyElephant.js"></script> <script type="text/javascript"> $(function() { $("#download").click(function() { var downloadUrl = ['Content/keso1.jpg','Content/keso2.jpg','Content/keso1.txt','Content/keso2.txt','Content/keso1.zip','Content/keso2.zip']; $(downloadUrl).multiDownload({"source":"local"}); }); }); </script> </head> <body> <a id='download' href="#">下载</a> <a download="keso.jpg" href="keso.jpg">Html5下载</a> <a href="Content/keso1.zip">zip文件</a> <div> <Image src="keso.jpg" /> <Image src="FlyElephant.jpg" /> </div> </body> </html>
我的非专业前端,不免有遗漏或不到位的地方,若有不当请多多指正,多谢~
参考资料: 在浏览器端用JS建立和下载文件 AlloyTeam