今天晚上花了几个小时的功夫做了一个相册,类似于QQ空间的文件上传,不过我用的Ext+HTML5等新的技术,结合Servlet上传文件。有几个特点:
- 文件拖拽上传
- 实时获取上传进度
- 本地预览
- 与Ext结合起来
说了这么多,还是贴几张图给大家吧!!
这个是没有做任何操作时候的窗口
拖动图片的时候,提示将图片拖动到指定的区域
这个是拖拽进去后,生成了本地预览,并有相应的详细信息
这个是上传成功后显示的信息。这里可能是本地的原因,一下子就上传完了,没有体现出百分比来。大概就是这个样子了!下面说下实现:
首先构建Ext窗口:
-
- var win = Ext.create('Ext.window.Window', {
- title : 'Ext相册',
- width : 700,
- height : 400,
- iconCls : 'ablum',
- layout : 'fit',
- plain : false,
- items : [view],
- buttons : [{
- text : '上传',
- handler : upload,
- iconCls : 'upload'
- }, {
- text : '清空',
- handler : function() {
- store.removeAll();
- },
- iconCls : 'clear'
- }]
- });
- win.show();
创建像是图片的容器:
-
- var PhotoModel = Ext.define('ImageModel', {
- extend : 'Ext.data.Model',
- fields : [{name : 'name'},
- {name : 'type'},
- {name : 'size', type : 'float'},
- {name : 'lastmod', type : 'date',dateFormat : 'timestamp'},
- {name : 'file'},
- {name : 'src'}]
- });
-
-
- var store = Ext.create("Ext.data.Store", {
- model : PhotoModel
- });
-
- var ddtip;
-
-
- var tiptpl = '名 称:{0}<br/>' +
- '类 型:{1}<br/>' +
- '大 小:{2}<br/>' +
- '修改时间:{3}<br/>'
-
-
- var view = Ext.create('Ext.view.View', {
- store : store,
- tpl : [
- '<tpl for=".">',
- '<div class="thumb-wrap" id="{name}">',
- '<div class="upload-progress">0%</div>',
- '<div class="thumb"><img src="{src}"></div>',
- '<span>{name}</span></div>', '</tpl>',
- '<div class="x-clear"></div>'],
- style : {
- backgroundColor : '#FFFFFF',
- fontFamily : '微软雅黑'
- },
- multiSelect : true,
- trackOver : true,
- overItemCls : 'x-item-over',
- itemSelector : 'div.thumb-wrap',
- emptyText : '没有显示的相片',
- autoScroll : true,
- listeners : {
- 'afterrender' : function() {
-
- ddtip = view.el.createChild({
- tag : 'div',
- cls : 'dd-tip',
- html : '请将图片拖动到这里'
- });
-
- Ext.create('Ext.tip.ToolTip', {
- target : view.el,
- delegate : view.itemSelector,
- trackMouse : true,
- renderTo : Ext.getBody(),
- anchor : 'right',
- listeners : {
- beforeshow : function(tip) {
- var record = view
- .getRecord(tip.triggerElement);
- tip.update(Ext.String.format(
- tiptpl, record
- .get('name'),
- record.get('type'), record
- .get('size'),
- Ext.Date.format(
- record.get('lastmod'),
- 'Y年m月d日 H时i分')));
-
- }
- }
- });
- }
- }
- });
添加监听页面拖拽事件:
-
- Ext.getBody().on('dragover', function(e) {
- ddtip.show();
- });
-
- Ext.getBody().on('dragleave', function(e) {
- ddtip.hide();
- });
-
- view.el.on('dragenter', function(e) {
- e.stopPropagation();
- e.preventDefault();
- ddtip.hide();
- view.el.highlight();
- });
-
-
- view.el.on('dragleave', function(e) {
- e.stopPropagation();
- e.preventDefault();
- ddtip.show();
- });
-
-
- view.el.dom.ondrop = function(e) {
- e.stopPropagation();
- e.preventDefault();
- ddtip.hide();
-
- process(e.dataTransfer.files);
- };
处理用户拖拽过来的文件:
- function process(files) {
- var count = 0;
- for (var i = 0; i < files.length; i++) {
- var file = files[i];
-
- var photo = Ext.ModelManager.create({
- name : file.fileName,
- size : file.fileSize,
- type : file.type,
- file : file,
- lastmod : file.lastModifiedDate
- }, PhotoModel);
-
- store.add(photo);
-
- var reader = new FileReader();
-
- reader.onload = (function(p) {
- return function() {
- count++;
-
- p.data.src = this.result;
- if (count == files.length) {
-
- view.refresh();
- }
- }
- })(photo);
-
- reader.readAsDataURL(file);
- }
- }
-
处理上传方法:
- function upload(){
- store.each(function(photo){
- var progress = Ext.get(view.getNode(photo)).down('div.upload-progress');
- progress.show();
- var xhr = new XMLHttpRequest();
- xhr.open('post', 'upload', true);
- xhr.upload.onprogress = function(p) {
- return function(e) {
- if (e.lengthComputable) {
- var percentage = Math.round((e.loaded * 100) / e.total);
- progress.update(percentage + "%");
- }
- }
- }(progress);
- xhr.upload.onload = function(p) {
- return function(e) {
- progress.update("上传成功!");
- }
- }(progress);
- var fd = new FormData();
- fd.append("file", photo.data.file);
- xhr.send(fd);
- });
- }
Servlet实现文件上传的代码:
- @SuppressWarnings("unchecked")
- public void doPost(HttpServletRequest request, HttpServletResponse response)
- throws ServletException, IOException {
- String path = request.getSession().getServletContext().getRealPath("\\upload");
- DiskFileItemFactory factory = new DiskFileItemFactory();
- ServletFileUpload upload = new ServletFileUpload(factory);
-
- try {
- List<FileItem> list = (List<FileItem>) upload.parseRequest(request);
- for (FileItem fileItem : list) {
- String fileName = fileItem.getName();
- File file = new File(path + "\\" + fileName);
- fileItem.write(file);
- fileItem.delete();
- }
- } catch (Exception e) {
- e.printStackTrace();
- }
- }
就这样,这个相册实例就完成了!
------------------------------------------------------------------------------分割线---------------------------------------------------------------------------------
2012-05-14更新:
- 增加了通过资源管理器选择文件功能
- 修复上传进度显示BUG
- 增加相片右键菜单
- 上传更改为上传全部项和上传选中项
- 增加图片浏览器功能
- 图片浏览器支持拖动、双击最大化/还原、更改尺寸
- 图片浏览器支持对数据源里面的图片进行导航
- 图片浏览器图片的放大和缩小
由于更新的比较仓促,写的代码质量不是很高,应该将图片浏览器封装成一个对象,并且图片旋转的功能没有完成。这些工作就留给大家伙自己实现吧,图片旋转的代码网上都有。贴图给大家:
通过点击添加按钮选取文件
相片右键菜单
图片查看器,双击相片可以启动。支持图片放大,导航!
确定只能在chrome下运行,在firefox下运行有错,不是不能调,只是懒得调了!
源码等会会放到下载区里面,只是CSDN有延迟,找不到链接!
---------------------------------------------------------------------------------------------分割线-------------------------------------------------------------------------------------------
大家测试最好用最新版的Google Chrome浏览器。
在chrome下运行有效,firefox还在测试,IE忽略不计!!讨厌IE!!
最后打下小广告,
看文章评论一下是美德,你的评论是我最大的动力!!