HTML5多图片拖拽上传带进度条
前言
昨天利用css2的clip属性实现了网页进度条觉得还不错,但是很多情况下,我们在那些时候用进度条呢,一般网页加载的时候如果有需要可以用,那么问题就来了,怎么才算整个加载完毕呢,是页面主要模块加载完毕,还是window.onload之后算呢,对这些方面,我真不敢随意回答,因业务需求而定,本文想要说的是在图片上传的时候用到的进度条。
效果展示
详细参考请移步至html5demo
HTML5 新增的拖拽相关事件说明
1.ondragover
效果图演示是所看见的可以将文件不仅仅是图片拖拽到该div上边,只要鼠标接触到该div就会触发该事件,演示效果图表现为拖拽区边框变为淡绿色
2.ondragleave
鼠标拖拽文件离开时触发的事件,演示效果图表现为拖拽区边框为灰色
3.ondrop
鼠标在拖拽区按键松开,在此函数内触发读取文件,预览效果,上传服务器操作
HTML5 新增的读取文件api之FileReader/FormData
拖拽区鼠标按键松开,那么就会读取文件流,如果是图片就直接可以看见图片,否则就只显示文件名,用js怎么读取文件流呢,就要用到FileReader对象了,
该对象的很多属性事件比如onload,readAsDataURL,abort,onprogress等详情点击
比如图片上传之后的预览代码如下
var reader = new FileReader(); reader.onload = function (event) {//文件加载完成之后从event对象的result取内容,不论成功失败都会将值放在result中的 var image = new Image(); image.src = event.target.result; image.width = 250; // a fake resize holder.appendChild(image); }; reader.readAsDataURL(file); //表示将文件读取为一段以data:开头的字符串,就是Data URL,它是将小文件直接嵌入 //文档的方案,如果你不写这句,那么就显示不出来因为文档中没有image.src的数据
通过这种方式文件就可以预览了,那么预览完了之后干啥呢,接着就post数据到服务器
那么问题就来了,怎么post数据呢,我这里又没有form表单,也没有iframe,此时就彻底一点都用HTML5的新特性
formData模拟表单数据然后用XMLHttpRequest提交同时可以利用XMLHttpRequest的upload.onprogress事件
实现进度条进度计算。
先上代码
function readfiles(files) { //debugger; var formData = tests.formdata ? new FormData() : null; for (var i = 0; i < files.length; i++) { if (tests.formdata) formData.append('file', files[i]);//添加表单元素 previewfile(files[i]); } // now post a new XHR request if (tests.formdata) { var xhr = new XMLHttpRequest(); if (tests.progress) {//上传进度事件 xhr.upload.onprogress = updateProgress; } else { console.log("不支持 upload in new XMLHttpRequest"); } xhr.open('POST', 'WebForm1.aspx');//提交服务器处理程序 xhr.onload = function () {//加载完成之后设置进度条值为100 progress.value = 100; progress.innerHTML = 100 + "%"; }; xhr.send(formData); xhr.onreadystatechange = function () { if (xhr.readyState == 4 && xhr.status == 200) { // alert(xhr.responseText); } }; function updateProgress(event) { //debugger; if (event.lengthComputable) { //event.loaded加载了多少字节 event.total总共多少字节 var complete = (event.loaded / event.total * 100 | 0); console.log("complete->", complete); progress.value = 100; progress.innerHTML = 100 + "%"; } }; } }
还是上后端WebForm1.aspx代码吧,后端处理请求代码
protected void Page_Load(object sender, EventArgs e) { HttpFileCollection files = Request.Files; for (int i = 0; i < files.Count; i++) { string r = new Random().Next(0, 9).ToString(); string filename = DateTime.Now.ToString("yyyyMMddhhmmsss") + r + files[i].FileName.Substring(files[i].FileName.LastIndexOf(".")); string path = Server.MapPath("~/images/") + filename; files[i].SaveAs(path); } Response.Write("upload is completed!"); //Thread.Sleep(1000); Response.End(); }
总结
该测试遇到一个问题,就是XMLHttpRequest的upload.onprogress事件不是想象中的那样有进度感,不知道是因为服务器是本地的缘故还是该方法调用的方式不对
总是发现只调用了一次然后就是加载的字节流和总的字节流都是一样的,没有一种轮询进度感。该拖拽要先检测浏览器兼容性,切记,如果浏览器没有支持拖拽属性还是
要做兼容处理。最后附上asp.net的HTML5拖拽上传图片带进度条的demo
本人水平有限,如果文中有错误或者需要提建议的,恳请指出,如果觉得还不错请支持一下。