如今現代的瀏覽器已經有很多支援拖曳文件讀取操作,其優點不再複述。前端時間利用拖曳改進了一下網站的頭像上傳流程,對其中的要點和實作體會做一點總結。
先看一下整體視圖:
1、 文件拖曳接受區域要有明顯的標示,並且要盡可能的大(由於版面的原因,這個界面的拖放盒子並不大)。可以用虛線框盒子等樣式吸引使用者拖曳文件。最好有明顯的文字提示和圖標配合。
2、 在互動體驗上當檔案拖入瀏覽器視窗時,可以用拖放區變換背景顏色等向使用者發起放置操作邀請。
實作程式碼:
doc.bind({ 'dragenter':function(e){ $("#brsbox").addClass("dragbrowse"); dropbox.addClass("shine"); return false; }, 'dragleave':function(e){ dropbox.removeClass("shine"); return false; }, 'drop':function(e){ stopdft(e);} }); dropbox.bind({ 'dragenter':function(e){ dropbox.addClass("candrop"); stopdft(e);}, 'dragleave':function(e){ dropbox.removeClass("candrop"); stopdft(e);}, 'dragover':function(e){ stopdft(e);}, 'drop':function(e){ }
對於不支援拖曳的瀏覽器:
可惜的是 某些瀏覽器並不支援檔案拖曳讀取,這包括IE9等較現代的瀏覽器。所以我們必須為不支援拖曳的瀏覽器準備普通文件瀏覽上傳作為備用方案。
當不支援拖曳文件讀取時,介面如下:
實作偵測的程式碼如下:
it.detectDragable = function(){ filedrag = !!window.FileReader; if(!filedrag) return; $("#avtcnt").addClass('dragable');
檔案放置時的處理:
檔案放置到可接受區域時,請注意這可接受時候無論你拖放在滑鼠上的檔案是單一還是多個,在瀏覽器和作業系統之間傳送的e.dataTransefer.files總是複數。也就是多個文件。這也意味著你需要循環處理滑鼠上所攜帶的文件。
程式碼如下:
dropdom.addEventListener('drop',function(e){ it.handlefile(e.dataTransfer.files); stopdft(e);},false); }; it.handlefile = function(files){ var noimg = 0; for(var i=0; i<files.length; i++){ var file = files[i]; if(!file.type.match(/image*/)){ noimg ++; if(noimg ==files.length){ QSL.optTips('请选择jpg, png, gif 等格式的图片'); return false; } continue; } var reader = new FileReader(); reader.onload = function(e){ var img = document.createElement('img'); img.src = reader.result; setTimeout(function(){ it.imgSize = { w:img.width, h:img.height }; },500); dropdom.innerHTML=""; img.className ='localimg'; it.imgData = reader.result; dropdom.appendChild(img); imagedata.empty().val(reader.result); dropbox.addClass("droped"); clearner.show(); }; reader.readAsDataURL(file); }
處理拖曳到瀏覽器的檔案
其中 stopdft(e) 是為了防止瀏覽器預設操作,不以瀏覽器開啟檔案。而轉由腳本來處理拖放的檔案。
這個流程中,我們需要的是圖片文件,所以便利操作 e.dataTransfer.files 對象,找出類型為image的文件。
如果沒有,則會提示。
讀取檔案的關鍵程式碼:
var reader = new FileReader();
reader.onload = function(e){
var img = document.createElement('img'); result;
};
reader.readAsDataURL(file);
本例中我們需要讀取圖片的高度和寬度屬性。所以我們做了以下操作
setTimeout(function(){
it.imgSize = {
w:img.width,
h:img.height
};
},500);img.height
};
},500);仍然要延時來保證圖片確實讀取完畢。否則在某些瀏覽器中會取不到寬高的值。 (可否有其他簡單方法?望指出)
刪除現有圖片,重置拖曳區域:
瀏覽讀取本地圖片之後,要給用戶刪除和重置的選項。 (如果是直接上傳當然比較簡單)
it.resetDropbox = function(){ dropbox.attr("class","dropbox") .empty() .text("将文件拖拽至此区域"); imgData = ''; it.imgData = ''; it.imgSize = {w:0,h:0}; picsub.removeClass("uploading") .find("button").removeAttr("disabled") .text("上传"); imagedata.val(''); clearner.hide();
重置拖曳區域
到這裡拖曳讀取檔案的流程基本上結束。
利用拖放,讀取本地文件的其他優點:
普通的上傳更改圖片流程是:選擇圖片-上傳圖片-上傳成功-伺服器返回圖片-客戶端瀏覽效果
而如果利用拖放讀取本地文件則可省去伺服器回傳圖片的步驟,直接利用reader.result回傳的資料。
這樣就節省了從伺服器讀取圖片的延遲,並且節省了往返的資料流量。所以只要確認伺服器端圖片上傳成功,圖片預覽調取本地資料即可:
程式碼:
function initImageCrop(url){ var t = document.getElementById("target"), p = document.getElementById("preview"), b = browseImage, s = [], ts = []; if(url=='data'){ t.src = b.imgData; p.src = b.imgData; posImage(b.imgSize.w,b.imgSize.h); }else{ var cutimg = new Image(); cutimg.onload = function(){ t.src = url; p.src = url; posImage(cutimg.width,cutimg.height); } cutimg.src = url;
圖片上傳成功後的處理
更多關於js拖曳上傳[一個拖曳上傳修改頭像的流程]相關文章請關注PHP中文網!