zoukankan      html  css  js  c++  java
  • HTML5托拽上传(XMLHttpRequest和Google Gears)

          HTML5的拖拽上传功能可拆分为两个部分实现,一个是对象的拖拽功能,另一个是上传功能。拖拽功能的实现基于HTML5 DOM对象的拖拽事件 ,FF3.6+和Chrome7+都实现了该功能,所以不用做特别的兼容,代码如下:

     
    拖拽功能代码
        var uploadZone=$("uploadZone"),
            iptFile,
            file,
            ffUpload
    =new FirefoxFileUpload("http://localhost/upload/a.php"); 
            
    //chromeUpload=new ChromeFileUpload("http://localhost/upload/a.php");
            
        
    function focus(state){
            uploadZone.style.backgroundColor
    =state?"#f0ab0c":"";
        }



        uploadZone.addEventListener(
    "dragenter",function(e){
            focus(
    true);
            e.stopPropagation();
            e.preventDefault();
        },
    false);

        uploadZone.addEventListener(
    "dragleave",function(e){
            focus(
    false);

        },
    false);

        uploadZone.addEventListener(
    "dragover",function(e){
            e.stopPropagation();
            e.preventDefault();
        },
    false);

        uploadZone.addEventListener(
    "drop",function(e){
            e.stopPropagation();
            e.preventDefault();
            focus(
    false);
            
            
    //Firefox上传
            ffUpload.xhr.upload.onprogress=function(e){
                
    var w=$("pgBorder").offsetWidth;
                
                $(
    "progress").style.width=e.loaded/e.total*w+"px";
            };
            ffUpload.xhr.upload.onload
    =function(){
                $(
    "progress").style.width=$("pgBorder").offsetWidth+"px";
            };
            ffUpload.upload(ffUpload.getFile(e));

            
            
    //Chrome上传
        //    chromeUpload.xhr.upload.onprogress=function(e){
        //        console.log(e.loaded/e.total*100+"%");
        //    };
        //    chromeUpload.upload(chromeUpload.getFile(e));
            
        },
    false);

    而HTML5的文件传输功能则是基于两套实现方式:
        firefox:
            fileReader.readAsBinaryString 读取二进制串
            XMLHttpRequest.sendAsBinary 以二进制的格式发送给服务器端(真给力)
        
        chrome:
            gears API

    因为XMLHttpRequest.sendAsBinary目前还没有被w3c列为标准,所以只能在Firefox中私有地使用。

    以下是简单封装的两个浏览器的上传类
          
    Firefox 上传类
     var FirefoxFileUpload=function(url,dataName){
                    
    this.xhr=new XMLHttpRequest();
                    
                    
    this.__file=null;
                    
    this.__fileReader=new FileReader();
                    
    this.__url=url;
                    
    this.__dataName=dataName || "FileData";
                    
                    
    this.__initReader();
                };
                FirefoxFileUpload.prototype
    ={
                    upload:
    function(file){
                        
    if(!file){
                            
    return;
                        }
                        
                        
    this.__file=file;
                        
    this.__fileReader.readAsBinaryString(this.__file);
                    },
                    
                    getFile:
    function(e){
                        
    return e.dataTransfer.files[0];
                    },
                    
                    __send:
    function(){
                        
    var xhr=this.xhr,
                            boundary
    ="----------BOUNDARY"+(new Date()).getTime(),
                            body
    =this.__getBody(this.__fileReader.result,boundary);
                        
                        xhr.open(
    "post",this.__url,true);
                        xhr.setRequestHeader(
    "Content-Type","multipart/form-data, boundary="+boundary);
                        xhr.setRequestHeader(
    "Content-Length",this.__file.size);

                        xhr.sendAsBinary(body);
                    },
                    
                    __initReader:
    function(){
                        
    var me=this;
                        
    this.__fileReader.addEventListener("load",function(){
                            me.__send();
                        },
    false);
                    },
                    
                    __getBody:
    function(readerResult,boundary){
                        
    return ['--',boundary,'\r\n',
                                
    'content-disposition: form-data; name="',this.__dataName,'"; filename="',encodeURI(this.__file.name),'"\r\n',
                                
    'Content-Type: ',this.__file.type,'\r\n\r\n',
                                 readerResult,
    "\r\n",
                                
    '--',boundary,'--\r\n'
                            ].join(
    "");
                    }
                    
                };

    Chrome 上传类
    var ChromeFileUpload=function(url,dataName){
                    
    this.xhr=google.gears.factory.create("beta.httprequest");
                    
                    
    this.__url=url;
                    
    this.__file=null;
                    
    this.__builder=google.gears.factory.create("beta.blobbuilder");
                    
    this.__dataName=dataName || "FileData";
                };
                ChromeFileUpload.prototype
    ={
                    upload:
    function(file){
                        
    this.__file=file;
                        
    this.__send();
                    },
                    
                    getFile:
    function(e){
                        
    var desktop=google.gears.factory.create("beta.desktop");
                        
    return desktop.getDragData(e,"application/x-gears-files").files[0];
                    },
                    
                    __send:
    function(){
                        
    var xhr=this.xhr,
                            boundary
    ="----------BOUNDARY"+(new Date()).getTime();
                        
                        xhr.open(
    "post",this.__url,true);
                        xhr.setRequestHeader(
    "Content-Type","multipart/form-data, boundary="+boundary);
                        
                        
    this.__updateBuilder(boundary);
                        xhr.send(
    this.__builder.getAsBlob());
                    },
                    
                    __updateBuilder:
    function(boundary){
                        
    var bdr=this.__builder;
                        
                        bdr.append([
    '--',boundary,'\r\n',
                                    
    'content-disposition: form-data; name="',this.__dataName,'"; filename="',encodeURI(this.__file.name),'"\r\n',
                                    
    'Content-Type: ',this.__file.type,'\r\n\r\n'].join(""));
                        bdr.append(
    this.__file.blob);
                        bdr.append([
    "\r\n",
                                    
    '--',boundary,'--\r\n'
                                    ].join(
    ""));
                    }
                };

    两种上传方式都是用的基于表单的文件传输协议 RFC-1867  (RFC-1867 中文版)。

    这两个类配合前面的拖拽代码即可实现HTML5版的拖拽上传。。。。。有了标准才是真的方便啊。。。。

  • 相关阅读:
    Java实现 LeetCode 382 链表随机节点
    Java实现 LeetCode 382 链表随机节点
    Java实现 LeetCode 381 O(1) 时间插入、删除和获取随机元素
    Java实现 LeetCode 381 O(1) 时间插入、删除和获取随机元素
    Java实现 LeetCode 381 O(1) 时间插入、删除和获取随机元素
    Java实现 LeetCode 380 常数时间插入、删除和获取随机元素
    Java实现 LeetCode 380 常数时间插入、删除和获取随机元素
    Linux下的iwpriv(iwlist、iwconfig)的简单应用
    OCX控件的注册卸载,以及判断是否注册
    .OCX、.dll文件注册命令Regsvr32的使用
  • 原文地址:https://www.cnblogs.com/Random/p/1967411.html
Copyright © 2011-2022 走看看