一次說清楚!圖片上傳怎麼玩?原來咱們知道的都太簡單了

隨着我司的發展,前端開發同窗在公司企業級的中臺業務的重要性也在提升html

咱們正處在從IT時代到DT時代中的過渡階段,各個企業都要面臨信息化數字化的壓力,如何提升內效是目前都要面臨的一個問題,我司中臺業務走到今天,既要好體驗,也要高效率,給技術團隊提出了一個有趣的問題前端

在咱們平常項目開發中,圖片上傳是一個十分常見的場景。html5

而如今的各類UI框架都提供了本身的上傳組件,網上第三方的上傳組件也多如牛毛。可能你早已習慣了直接使用這些現成的組件,然而對於其具體的實現,卻並未深刻解析。瀏覽器

本文以圖片上傳爲入口,將經過簡單的代碼,爲你解析圖片上傳的各個知識點,讓你一次打通任督二脈服務器

孔子說過食不厭精、膾不厭細,他是說食物製做的越精細越好。在順德,有一魚八吃,各個都是經典味道,吃魚的心思巧,全魚宴的設計精妙,點點滴滴都是廚師的心血與驕傲!app

爲何忽然轉到吃了,多是臨近中午,有些餓了,開個玩笑,不過各位同窗不以爲食不厭精、膾不厭細也是在說咱們的技術開發態度嗎?框架

今天我給你們帶來一傳三精!異步


基本原理

  • Form表單提交
  • Ajax上傳

Form表單提交post

表單上傳須要注意如下幾點:編碼

(1).提供form表單,method必須是post。

(2).form表單的enctype必須是multipart/form-data。

屬性 說明
enctype 屬性規定在發送到服務器以前應該如何對錶單數據進行編碼。默認地,表單數據會編碼爲 "application/x-www-form-urlencoded"。就是說,在發送到服務器以前,全部字符都會進行編碼。HTML表單如何打包數據文件是由enctype這個屬性決定的。enctype有如下幾種取值:
application/x-www-form-urlencoded 在發送前編碼全部字符(默認)(空格被編碼爲’+’,特殊字符被編碼爲ASCII十六進制字符)。
multipart/form-data 不對字符編碼。在使用包含文件上傳控件的表單時,必須使用該值。
text/plain 空格轉換爲 「+」 加號,但不對特殊字符編碼。

默認enctype=application/x-www-form-urlencoded,因此表單的內容會按URL規則編碼,而後根據表單的提交方法:

Ajax上傳

FormData對象是html5的一個對象,目前的一些主流的瀏覽器都已經兼容。

經過FormData對象能夠更靈活方便的發送表單數據,由於能夠獨立於表單使用。若是你把表單的編碼類型設置爲multipart/form-data ,則經過FormData傳輸的數據格式和表單經過submit()方法傳輸的數據格式相同。

代碼以下:


拖拽上傳

主要是基於DataTransfer和FormData,經過藉助dataTransfer和formData實現從電腦的資源管理器直接拖拽圖片到網頁上傳,具體過程是從電腦拖拽圖片到網頁,js在drop的事件中取到當前事件對象的dataTransfer進而獲得文件對象,而後實例化formData對象,藉助xhr異步上傳圖片,這無疑是一個錦上添花的功能

實現代碼以下:

dropEffect 將基於用戶要求的動做被初始化設置:

監聽事件進行處理:

Demo效果:


粘貼上傳

這就今天要說的第三種吃法,剪切板圖片粘貼上傳

有三種方式能夠在元素中粘貼內容:

  • 按下 CTRL + V
  • 從瀏覽器的編輯菜單中選擇 "Paste(粘貼)"
  • 右擊鼠標按鈕在上下文菜單中選擇 "Paste(粘貼)" 命令

實現原理是:經過clipboardData對象訪問剪切板中的數據,專爲Base64進行預覽,使用FileReader對象,使用Bolb對象處理數據,添加到FormData中,經過AJAX傳給服務器端

整個實現過程當中,有幾個知識點須要肯定,且每一個點都有不小的坑須要兼容,分別爲

  • 監聽剪切板事件
  • clipboardData
  • FileReader
  • FormData

clipboardData

它其實是一個DataTransfer類型的對象,DataTransfer是拖動產生的一個對象,但實際上粘貼事件也是它。

clipboardData的屬性

屬性 類型 說明
dropEffect String 默認是 none
effectAllowed String 默認是 uninitialized
files FileList 粘貼操做爲空List
items DataTransferItemList 剪切板中的各項數據
types Array 剪切板中的數據類型

訪問剪貼板中的數據,能夠:在IE中,clipboardData對象是window對象的屬性;而在Chrome、Safari和Firefox 4+中,clipboardData對象是相應event對的屬性。可是,在Chrome、Safari和Firefox 4+中,只有在處理剪貼板事件期間,clipboardData對象纔有效,這是爲了防止對剪貼板的未受權訪問;在IE中,則能夠隨時訪問clipboardData對象。爲了確保跨瀏覽器兼容,最好只在發生剪貼板事件期間使用這個對象。

clipboardData對象有三個方法:getData()方法、setData()方法和clearData()方法。

getData()方法用於從剪貼板中獲取數據,它接收一個參數,即要取得的數據格式。在IE中,有兩種數據格式:’text」和」URL」。在Chrome、Safari和Firefox 4+中,這個參數是一種MIME類型;不過,能夠用」text」表明」text/plain」。

setData()方法的第一個參數也是數據類型,第二個參數是要放在剪貼板中的文字。對於第一個參數,IE照樣是支持」text」和」URL」,而在Chrome、Safari中,仍然支持MIME類型。可是與getData()方法不一樣的是,在Chrome、Safari中的setData()方法不能識別」text」類型。這兩個瀏覽器在成功將文本放到剪貼板中後,都會返回true;不然返回false。

FileReader

FileReader 對象容許Web應用程序異步讀取存儲在用戶計算機上的文件(或原始數據緩衝區)的內容,使用 File 或 Blob 對象指定要讀取的文件或數據。

事件處理
FileReader.onload處理load事件。該事件在讀取操做完成時觸發。

FileReader.onloadend處理loadend事件。該事件在讀取操做結束時(要麼成功,要麼失敗)觸發。

方法
FileReader.readAsDataURL()開始讀取指定的Blob中的內容。一旦完成,result屬性中將包含一個data: URL格式的字符串以表示所讀取文件的內容。

readAsDataURL: 該方法會讀取指定的 Blob 或 File 對象。讀取操做完成的時候,readyState 會變成已完成(DONE),並觸發 loadend 事件,同時 result 屬性將包含一個data:URL格式的字符串(base64編碼)以表示所讀取文件的內容。

實現代碼以下:

觸發粘貼事件後的操做:

base64轉二進制

Demo效果:


相關文章
相關標籤/搜索