简单的文件上传
1 | <form id="uploadForm" method="POST" action="upload" enctype="multipart/form-data"> |
这是一个最简单的文件上传。但是。。。ummmm,够胆你就提交这样的代码吧
常用的上传方式——FormData
通过在脚本里新建FormData对象,把file对象设置到表单项中,然后利用XMLHttpRequest异步上传到服务器:
1 | var xhr = new XMLHttpRequest() |
以上,可以完成最基本的需求
上传进度
XMLHttpRequest Level 2中,传送数据的时候,有一个progress事件,上传数据progress事件属于XMLHttpRequest.upload对象,上传数据过程中会触发,这个对象拥有下列方法:
这个对象拥有下列下列方法:
- onloadstart
- onprogress
- onabort
- onerror
- onload
- ontimeout
- onloadend
这些方法在XHR对象中都存在同名版本,区别是后者是用于加载资源时,而前者用于资源上传时。其中onprogress 事件回调方法可用于跟踪资源上传的进度,它的event参数对象包含两个重要的属性loaded和total。分别代表当前已上传的字节数(number of bytes)和文件的总字节数。比如我们可以这样计算进度百分比:
1 | xhr.upload.onprogress = function (e) { |
现代浏览器配合h5提供的progress
享用
1 | <progress id="myProgress" value="50" max="100"> |
其value属性绑定上面代码中的percent
的值即可。
因为xhr.upload.onprogress在上传阶段(即xhr.send()之后,xhr.readystate=2之前)触发,每50ms触发一次。所以文件太小网络环境好的时候是直接到100%的。
图片预览
普通青年的图片预览方式是待文件上传成功后,后台返回上传文件的url,然后把预览图片的img元素的src指向该url。这其实达不到预览的效果和目的。
属于文艺青年的现代浏览器又登场了:“使用HTML5的FileReader API吧!” 让我们直接上代码,直奔主题:
1 | function handleImageFile(file) { |
这里我们使用FileReader来处理图片的异步加载。在创建新的FileReader对象之后,我们建立了onload函数,然后调用readAsDataURL()开始在后台进行读取操作。当图像文件加载后,转换成一个 data: URL,并传递到onload回调函数中设置给img的src。
另外我们还可以通过使用对象URL来实现预览
1 | var img = document.createElement("img"); |
多文件上传
1 | <input type="file" id="myFile" multiple> |
此时代码里拿到的FileUpload对象的files属性就是一个选中的多文件的数组了
1 | var fileInput = document.getElementById("myFile"); |
FormData的append方法提供第三个可选参数用于指定文件名,这样就可以使用同一个表单项名,然后用文件名区分上传的多个文件。这样也方便前后台的循环操作。
拖拽选择文件
利用HTML5的drag & drop事件来实现对拖拽的支持。首先我们可能需要确定一个允许拖放的区域,然后绑定相应的事件进行处理。
1 | var dropArea |
这里可以把通过事件对象的dataTransfer拿到的files数组和之前相同处理,以实现预览上传等功能。有了这些事件回调,我们也可以在不同的事件给我们UI元素添加不同的class来实现更好交互效果。
end
此外上传还有二进制上传,借用iframe实现上传,详情请参考这篇文章