Ext4+Servlet+HTML5实现实时获取文件上传进度、本地预览、文件拖拽上传的相册实例

81 篇文章 1 订阅
59 篇文章 0 订阅
 

Ext4+Servlet+HTML5实现实时获取文件上传进度、本地预览、文件拖拽上传的相册实例

分类: Web开发 ExtJS HTML5 Java   3125人阅读  评论(14)  收藏  举报


今天晚上花了几个小时的功夫做了一个相册,类似于QQ空间的文件上传,不过我用的Ext+HTML5等新的技术,结合Servlet上传文件。有几个特点:

  • 文件拖拽上传
  • 实时获取上传进度
  • 本地预览
  • 与Ext结合起来
说了这么多,还是贴几张图给大家吧!!

这个是没有做任何操作时候的窗口

拖动图片的时候,提示将图片拖动到指定的区域

这个是拖拽进去后,生成了本地预览,并有相应的详细信息

这个是上传成功后显示的信息。这里可能是本地的原因,一下子就上传完了,没有体现出百分比来。大概就是这个样子了!下面说下实现:
首先构建Ext窗口:
[javascript]  view plain copy
  1. //创建相册窗口  
  2.     var win = Ext.create('Ext.window.Window', {  
  3.                 title : 'Ext相册',  
  4.                 width : 700,  
  5.                 height : 400,  
  6.                 iconCls : 'ablum',  
  7.                 layout : 'fit',  
  8.                 plain : false,  
  9.                 items : [view],  
  10.                 buttons : [{  
  11.                             text : '上传'//上传按钮  
  12.                             handler : upload,  
  13.                             iconCls : 'upload'  
  14.                         }, {  
  15.                             text : '清空',  
  16.                             handler : function() {  
  17.                                 store.removeAll();  
  18.                             },  
  19.                             iconCls : 'clear'  
  20.                         }]  
  21.             });  
  22.     win.show();  

创建像是图片的容器:
[javascript]  view plain copy
  1. //创建图片数据模型 ,数据源需要  
  2.     var PhotoModel = Ext.define('ImageModel', {  
  3.                 extend : 'Ext.data.Model',  
  4.                 fields : [{name : 'name'},  
  5.                         {name : 'type'},   
  6.                         {name : 'size', type : 'float'},  
  7.                         {name : 'lastmod', type : 'date',dateFormat : 'timestamp'},  
  8.                         {name : 'file'},  
  9.                         {name : 'src'}]  
  10.             });  
  11.   
  12.     //创建数据源  
  13.     var store = Ext.create("Ext.data.Store", {  
  14.                 model : PhotoModel  
  15.             });  
  16.   
  17.     var ddtip;  
  18.       
  19.     //图片提示模板  
  20.     var tiptpl = '名      称:{0}<br/>' +  
  21.               '类      型:{1}<br/>' +  
  22.              '大      小:{2}<br/>' +   
  23.              '修改时间:{3}<br/>'  
  24.       
  25.     //创建图片存放的容器  
  26.     var view = Ext.create('Ext.view.View', {  
  27.                 store : store, //指定数据源  
  28.                 tpl : [ //设置展示模板  
  29.                         '<tpl for=".">',  
  30.                         '<div class="thumb-wrap" id="{name}">',  
  31.                         '<div class="upload-progress">0%</div>',  
  32.                         '<div class="thumb"><img src="{src}"></div>',  
  33.                         '<span>{name}</span></div>''</tpl>',  
  34.                         '<div class="x-clear"></div>'],  
  35.                 style : {  
  36.                     backgroundColor : '#FFFFFF',  
  37.                     fontFamily : '微软雅黑'  
  38.                 },  
  39.                 multiSelect : true,  
  40.                 trackOver : true,  
  41.                 overItemCls : 'x-item-over',  
  42.                 itemSelector : 'div.thumb-wrap',  
  43.                 emptyText : '没有显示的相片',  
  44.                 autoScroll : true,  
  45.                 listeners : {  
  46.                     'afterrender' : function() {  
  47.                         //创建用户拖拽提示  
  48.                         ddtip = view.el.createChild({  
  49.                                     tag : 'div',  
  50.                                     cls : 'dd-tip',  
  51.                                     html : '请将图片拖动到这里'  
  52.                                 });  
  53.                         //创建相片浮动提示  
  54.                         Ext.create('Ext.tip.ToolTip', {  
  55.                                 target : view.el,  
  56.                                 delegate : view.itemSelector,  
  57.                                 trackMouse : true,  
  58.                                 renderTo : Ext.getBody(),  
  59.                                 anchor : 'right',  
  60.                                 listeners : {  
  61.                                     beforeshow : function(tip) {  
  62.                                         var record = view  
  63.                                                     .getRecord(tip.triggerElement);  
  64.                                             tip.update(Ext.String.format(  
  65.                                                     tiptpl, record  
  66.                                                             .get('name'),  
  67.                                                     record.get('type'), record  
  68.                                                             .get('size'),  
  69.                                                     Ext.Date.format(  
  70.                                                             record.get('lastmod'),  
  71.                                                             'Y年m月d日 H时i分')));  
  72.                                            
  73.                                     }  
  74.                                 }  
  75.                             });  
  76.                     }  
  77.                 }  
  78.             });  

添加监听页面拖拽事件:
[javascript]  view plain copy
  1. //给body添加事件,如果有拖拽的话提示用户拖拽到指定区域  
  2.     Ext.getBody().on('dragover'function(e) {  
  3.                 ddtip.show();  
  4.             });  
  5.     //当用户拖拽离开时隐藏提示信息  
  6.     Ext.getBody().on('dragleave'function(e) {  
  7.                 ddtip.hide();  
  8.             });  
  9.     //当用户拖拽到指定区域时,隐藏提示信息  
  10.     view.el.on('dragenter'function(e) {  
  11.                 e.stopPropagation();  
  12.                 e.preventDefault();  
  13.                 ddtip.hide();  
  14.                 view.el.highlight();  
  15.             });  
  16.   
  17.     //当用户拖拽离开指定区域时显示提示信息  
  18.     view.el.on('dragleave'function(e) {  
  19.                 e.stopPropagation();  
  20.                 e.preventDefault();  
  21.                 ddtip.show();  
  22.             });  
  23.   
  24.     //很关键!!当用户拖拽文件并放下的时候触发时间  
  25.     view.el.dom.ondrop = function(e) {  
  26.         e.stopPropagation();  
  27.         e.preventDefault();  
  28.         ddtip.hide();//隐藏提示信息  
  29.         //处理用户拖拽过来的文件  
  30.         process(e.dataTransfer.files);  
  31.     };  

处理用户拖拽过来的文件:
[javascript]  view plain copy
  1. function process(files) {  
  2.         var count = 0;  
  3.         for (var i = 0; i < files.length; i++) {  
  4.             var file = files[i];//这个一个File对象  
  5.             //创建一个相片数据实例,保存名称,大小,类型,修改日期,文件等信息  
  6.             var photo = Ext.ModelManager.create({  
  7.                         name : file.fileName,  
  8.                         size : file.fileSize,  
  9.                         type : file.type,  
  10.                         file : file,  
  11.                         lastmod : file.lastModifiedDate  
  12.                     }, PhotoModel);  
  13.             //添加到数据源中,这时候容易会发生相应的变化  
  14.             store.add(photo);  
  15.             //通过FileReader对象获取预览  
  16.             var reader = new FileReader();  
  17.             //当读取完成之后执行的回调  
  18.             reader.onload = (function(p) {  
  19.                 return function() {  
  20.                     count++;  
  21.                     //将获取到的Base64格式的图片数据,存放起来  
  22.                     p.data.src = this.result;  
  23.                     if (count == files.length) {  
  24.                         //当所有图片都加载完了之后,渲染图片  
  25.                         view.refresh();  
  26.                     }  
  27.                 }  
  28.             })(photo);//这个地方利用了JS的闭包原理  
  29.             //读取图片  
  30.             reader.readAsDataURL(file);  
  31.         }  
  32.     }  
  33.       

处理上传方法:
[javascript]  view plain copy
  1. function upload(){ //执行上传  
  2.         store.each(function(photo){//遍历数据源的数据  
  3.             var progress = Ext.get(view.getNode(photo)).down('div.upload-progress');//显示进度信息  
  4.             progress.show();  
  5.             var xhr = new XMLHttpRequest(); //初始化XMLHttpRequest  
  6.             xhr.open('post''upload'true);  
  7.             xhr.upload.onprogress = function(p) { //添加数据上传进度,获取实时的上传进度  
  8.                 return function(e) {  
  9.                     if (e.lengthComputable) {  
  10.                         var percentage = Math.round((e.loaded * 100) / e.total);  
  11.                         progress.update(percentage + "%");  
  12.                     }  
  13.                 }  
  14.             }(progress);  
  15.             xhr.upload.onload = function(p) { //当上传完之后执行的回调函数  
  16.                 return function(e) {  
  17.                     progress.update("上传成功!");  
  18.                 }  
  19.             }(progress);  
  20.             var fd = new FormData(); //这里很关键,初始化一个FormData,并将File文件发送到后台  
  21.             fd.append("file", photo.data.file);  
  22.             xhr.send(fd);  
  23.         });  
  24.     }  

Servlet实现文件上传的代码:
[java]  view plain copy
  1. @SuppressWarnings("unchecked")  
  2.     public void doPost(HttpServletRequest request, HttpServletResponse response)  
  3.             throws ServletException, IOException {  
  4.         String path = request.getSession().getServletContext().getRealPath("\\upload");  
  5.         DiskFileItemFactory factory = new DiskFileItemFactory();  
  6.         ServletFileUpload upload = new ServletFileUpload(factory);  
  7.   
  8.         try {  
  9.             List<FileItem> list = (List<FileItem>) upload.parseRequest(request);  
  10.             for (FileItem fileItem : list) {  
  11.                 String fileName = fileItem.getName();  
  12.                 File file = new File(path + "\\" + fileName);  
  13.                 fileItem.write(file);  
  14.                 fileItem.delete();  
  15.             }  
  16.         } catch (Exception e) {  
  17.             e.printStackTrace();  
  18.         }  
  19.     }  

就这样,这个相册实例就完成了!

------------------------------------------------------------------------------分割线---------------------------------------------------------------------------------

2012-05-14更新:
  • 增加了通过资源管理器选择文件功能
  • 修复上传进度显示BUG
  • 增加相片右键菜单
  • 上传更改为上传全部项和上传选中项
  • 增加图片浏览器功能
  • 图片浏览器支持拖动、双击最大化/还原、更改尺寸
  • 图片浏览器支持对数据源里面的图片进行导航
  • 图片浏览器图片的放大和缩小
由于更新的比较仓促,写的代码质量不是很高,应该将图片浏览器封装成一个对象,并且图片旋转的功能没有完成。这些工作就留给大家伙自己实现吧,图片旋转的代码网上都有。贴图给大家:

通过点击添加按钮选取文件

相片右键菜单

图片查看器,双击相片可以启动。支持图片放大,导航!
确定只能在chrome下运行,在firefox下运行有错,不是不能调,只是懒得调了!
源码等会会放到下载区里面,只是CSDN有延迟,找不到链接!

---------------------------------------------------------------------------------------------分割线-------------------------------------------------------------------------------------------

大家测试最好用最新版的Google Chrome浏览器。

Ext还能做什么?只有想不到的,没有做不到了,进入 http://blog.csdn.net/leecho571/article/details/8207102感受Ext带来的新的体验
在chrome下运行有效,firefox还在测试,IE忽略不计!!讨厌IE!!
最后打下小广告,
看文章评论一下是美德,你的评论是我最大的动力!!

  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值