把文件從桌面拖拽到瀏覽器是Web應用程序集成的最終目標之一。本教程共四篇文章(本文是第一篇),主要介紹了:
1.實現將文件拖放到頁面元素上
2.在JavaScript中分析被拖放的文件
3.在客戶端上加載和解析文件
4.使用XMLHttpRequest2將文件異步上傳到服務器
5.上傳時,顯示圖形進度條
6.使用進程增強( progressive enhancement)以確保文件上傳表單在所有瀏覽器正常工作
7.純JavaScript代碼,不使用其它庫。
咻,開始吧!
糟糕的瀏覽器支持
在開始之前說明一下,這個教程使用了一些HTML5的最新技術,可能以后會被修正。目前代碼可以正常工作,但是很可能隨着API的變化或者瀏覽器升級而受到影響。
§Firefox和Chrome的最新版本支持所有的功能並且可以完美運行。
§Opera可以用JavaScript解析文件,但未實現拖放文件和XMLHttpRequest2上傳。
§IE瀏覽器和桌面版本的Safari不支持所有的API。
§蘋果已禁用Safari瀏覽器的iPhone和iPad版本的HTML文件上傳表單。有誰知道為什么嗎?
最后,請注意我的代碼只是演示了基本概念,幾乎沒有錯誤檢查,因此需要進行修改以適應你的工作需要。
HTML和CSS
這是我們的帶有文件輸入類型的標准表單。唯一的HTML5特性是“multiple”屬性,它允許用戶選擇任意數量的文件。
我們將上傳文件到運行PHP的服務器上,但是無論你在服務器端使用什么技術,代碼是大致相同的。隱藏的MAX_FILE_SIZE值指定為300,000個字節,這是PHP使用的,但我們還會在瀏覽器端用它進行檢查,以防止大文件上傳。
#filedrag元素將被用作接收拖放文件的位置。元素是通過CSS隱藏的,但如果瀏覽器支持拖拽的話,它會在JavaScript中被顯示:
我們還定義了一個.hover類,當用戶拖動文件到相應區域元素時,改變元素的顯示風格。瀏覽器不支持在那種情況下的:hover風格,但當事件觸發時,我們可以用JavaScript添加類。
文件操作API
W3C 文件操作API
提供了一些對象,我們使用了:
§FileList:代表選定的文件數組。
§File:代表一個單獨的文件。
§FileReader:支持JavaScript的客戶端讀取文件數據的接口。
Javascript事件
是時候處理JavaScript代碼了。我們不使用任何JavaScript庫,為了節省時間,我們將創建一個輔助函數返回元素的ID和輸出狀態消息:
我們將在Init()函數里檢查文件操作API是否有效:
Init()函數說明:
1.給文件輸入元素設置一個“change”事件監聽器。
2.顯示#filedrag元素。
3.設置“dragover”和“dragleave”事件監聽器,以改變的#filedrag元素的風格。
4.給#filedrag元素設置一個“drop”的事件監聽器。
5.隱藏表單的提交按鈕 - 它不是必需的,因為當文件被選中時我們將進行分析和上傳,而不是提交表單。
或者,當瀏覽器支持文件拖動時,你可以隱藏文件輸入元素。就個人而言,我更願意同時提供兩種選擇,因為拖放實際上會帶來實用性的問題。
XMLHttpRequest.upload方法檢查防止在Opera中的問題。瀏覽器支持File,FileList和FileReader,但不支持拖放事件或XMLHttpRequest2。因此,它可以顯示文件信息,但我們不希望顯示#filedrag的元素或刪除submit按鈕。
改變文件拖放風格
很少人在瀏覽器中進行過文件拖放。事實上,經驗豐富的網絡用戶也不太考慮是否可行。因此,我們使用了標有“drop files here”的元素。當文件拖到#filedrag上時,我們還通過改變元素的風格來進行顯示。
分析放下或被選中的文件
無論是使用“Browse”按鈕來選中一個或多個文件,或者將文件拖放到拖#filedrag的位置上,我們使用的的相同FileSelectHandler()函數來進行處理:
函數說明:
1.調用FileDragHover()刪除hover風格和取消瀏覽器的事件。這是必不可少的,否則瀏覽器可能會嘗試顯示該文件。
2.獲取一個FileList對象,無論是從文件輸入框(e.target.files)或#filedrag元素(例如dataTransfer.files)。
3.最后,函數遍歷FileList的所有File對象,並把它作為一個參數傳遞給ParseFile()函數...
該函數輸出的信息是File對象提供的三個主要的只讀屬性:
§.name: 文件名 (不包含文件路徑)。
§.type: MIME類型, 例如 image/jpeg,text/plain等等。
§.size: 文件大小(字節).
請在火狐,Chrome或者Opera(不支持拖放)查看演示頁
,。你可以下載源代碼