日韩无码专区无码一级三级片|91人人爱网站中日韩无码电影|厨房大战丰满熟妇|AV高清无码在线免费观看|另类AV日韩少妇熟女|中文日本大黄一级黄色片|色情在线视频免费|亚洲成人特黄a片|黄片wwwav色图欧美|欧亚乱色一区二区三区

RELATEED CONSULTING
相關(guān)咨詢
選擇下列產(chǎn)品馬上在線溝通
服務(wù)時間:8:30-17:00
你可能遇到了下面的問題
關(guān)閉右側(cè)工具欄

新聞中心

這里有您想知道的互聯(lián)網(wǎng)營銷解決方案
你不知道的Blob

如果你允許用戶從你的網(wǎng)站上下載某些文件,那你可能會遇到 Blob 類型。為了實現(xiàn)上述的功能,你可以很容易從網(wǎng)上找到相關(guān)的示例,并根據(jù)實際需求進行適當(dāng)?shù)恼{(diào)整。對于部分開發(fā)者來說,在完成上述功能之后,他們并不會繼續(xù)思考 Blob 是什么?

成都創(chuàng)新互聯(lián)公司是一家專注于成都網(wǎng)站制作、成都網(wǎng)站設(shè)計、外貿(mào)營銷網(wǎng)站建設(shè)與策劃設(shè)計,競秀網(wǎng)站建設(shè)哪家好?成都創(chuàng)新互聯(lián)公司做網(wǎng)站,專注于網(wǎng)站建設(shè)十載,網(wǎng)設(shè)計領(lǐng)域的專業(yè)建站公司;建站業(yè)務(wù)涵蓋:競秀等地區(qū)。競秀做網(wǎng)站價格咨詢:13518219792

這就導(dǎo)致了一些開發(fā)者,還是停留在熟練使用 API 的層面,當(dāng)遇到比較棘手的問題時,就束手無策。換句話說,如果當(dāng)你在熟悉 API 的使用之后,還能繼續(xù)多問幾個為什么,繼續(xù)探究下去,不僅能加深對知識的理解,還能觸類旁通,拓展自己的知識面提高自己。

好了,如果你想繼續(xù)了解什么是 Blob,那么就跟上我的腳步,來一個 Blob Web API 探索之旅。還在猶豫什么,Let's go!

讀完本文你將了解到以下內(nèi)容:

  •  Blob 是什么
  •  Blob API 簡介
    •   構(gòu)造函數(shù)
    •   屬性和方法
  •  Blob 使用場景
    •   分片上傳
    •   從互聯(lián)網(wǎng)下載數(shù)據(jù)
    •   Blob 用作 URL
    •   Blob 轉(zhuǎn)換為 Base64
    •   圖片壓縮
    •   生成 PDF
  •  Blob 與 ArrayBuffer 的區(qū)別

一、Blob 是什么

Blob(Binary Large Object)表示二進制類型的大對象。在數(shù)據(jù)庫管理系統(tǒng)中,將二進制數(shù)據(jù)存儲為一個單一個體的集合。Blob 通常是影像、聲音或多媒體文件。在 JavaScript 中 Blob 類型的對象表示不可變的類似文件對象的原始數(shù)據(jù)。 為了更直觀的感受 Blob 對象,我們先來使用 Blob 構(gòu)造函數(shù),創(chuàng)建一個 myBlob 對象,具體如下圖所示:

如你所見,myBlob 對象含有兩個屬性:size 和 type。其中 size 屬性用于表示數(shù)據(jù)的大?。ㄒ宰止?jié)為單位),type 是 MIME 類型的字符串。Blob 表示的不一定是 JavaScript 原生格式的數(shù)據(jù)。比如 File 接口基于 Blob,繼承了 blob 的功能并將其擴展使其支持用戶系統(tǒng)上的文件。

二、Blob API 簡介

Blob 由一個可選的字符串 type(通常是 MIME 類型)和 blobParts 組成:

MIME(Multipurpose Internet Mail Extensions)多用途互聯(lián)網(wǎng)郵件擴展類型,是設(shè)定某種擴展名的文件用一種應(yīng)用程序來打開的方式類型,當(dāng)該擴展名文件被訪問的時候,瀏覽器會自動使用指定應(yīng)用程序來打開。多用于指定一些客戶端自定義的文件名,以及一些媒體文件打開方式。

常見的 MIME 類型有:超文本標(biāo)記語言文本 .html text/html、PNG圖像 .png image/png、普通文本 .txt text/plain 等。

2.1 構(gòu)造函數(shù)

Blob 構(gòu)造函數(shù)的語法為: 

 
 
 
 
  1. var aBlob = new Blob(blobParts, options); 

相關(guān)的參數(shù)說明如下:

  •  blobParts:它是一個由 ArrayBuffer,ArrayBufferView,Blob,DOMString 等對象構(gòu)成的數(shù)組。DOMStrings 會被編碼為 UTF-8。
  •  options:一個可選的對象,包含以下兩個屬性:
    •   type —— 默認值為 "",它代表了將會被放入到 blob 中的數(shù)組內(nèi)容的 MIME 類型。
    •   endings —— 默認值為 "transparent",用于指定包含行結(jié)束符 \n 的字符串如何被寫入。它是以下兩個值中的一個:"native",代表行結(jié)束符會被更改為適合宿主操作系統(tǒng)文件系統(tǒng)的換行符,或者 "transparent",代表會保持 blob 中保存的結(jié)束符不變。

示例一:從字符串創(chuàng)建 Blob 

 
 
 
 
  1. let myBlobParts = ['

    Hello Semlinker

    ']; // an array consisting of a single DOMString 
  2. let myBlob = new Blob(myBlobParts, {type : 'text/html', endings: "transparent"}); // the blob  
  3. console.log(myBlob.size + " bytes size");  
  4. // Output: 37 bytes size  
  5. console.log(myBlob.type + " is the type");  
  6. // Output: text/html is the type 

示例二:從類型化數(shù)組和字符串創(chuàng)建 Blob 

 
 
 
 
  1. let hello = new Uint8Array([72, 101, 108, 108, 111]); // 二進制格式的 "hello"  
  2. let blob = new Blob([hello, ' ', 'semlinker'], {type: 'text/plain'}); 

介紹完 Blob 構(gòu)造函數(shù),接下來我們來分別介紹 Blob 類的屬性和方法:

2.2 屬性

前面我們已經(jīng)知道 Blob 對象包含兩個屬性:

  •  size(只讀):表示 Blob 對象中所包含數(shù)據(jù)的大小(以字節(jié)為單位)。
  •  type(只讀):一個字符串,表明該 Blob 對象所包含數(shù)據(jù)的 MIME 類型。如果類型未知,則該值為空字符串。

2.3 方法

  •  slice([start[, end[, contentType]]]):返回一個新的 Blob 對象,包含了源 Blob 對象中指定范圍內(nèi)的數(shù)據(jù)。
  •  stream():返回一個能讀取 blob 內(nèi)容的 ReadableStream。
  •  text():返回一個 Promise 對象且包含 blob 所有內(nèi)容的 UTF-8 格式的 USVString。
  •  arrayBuffer():返回一個 Promise 對象且包含 blob 所有內(nèi)容的二進制格式的 ArrayBuffer。

這里我們需要注意的是,Blob 對象是不可改變的。我們不能直接在一個 Blob 中更改數(shù)據(jù),但是我們可以對一個 Blob 進行分割,從其中創(chuàng)建新的 Blob 對象,將它們混合到一個新的 Blob 中。這種行為類似于 JavaScript 字符串:我們無法更改字符串中的字符,但可以創(chuàng)建新的更正后的字符串。

三、Blob 使用場景

3.1 分片上傳

File 對象是特殊類型的 Blob,且可以用在任意的 Blob 類型的上下文中。所以針對大文件傳輸?shù)膱鼍?,我們可以使?slice 方法對大文件進行切割,然后分片進行上傳,具體示例如下: 

 
 
 
 
  1. const file = new File(["a".repeat(1000000)], "test.txt");  
  2. const chunkSize = 40000;  
  3. const url = "https://httpbin.org/post";  
  4. async function chunkedUpload() {  
  5.   for (let start = 0; start < file.size; start += chunkSize) {  
  6.       const chunk = file.slice(start, start + chunkSize + 1);  
  7.       const fd = new FormData();  
  8.       fd.append("data", chunk);  
  9.       await fetch(url, { method: "post", body: fd }).then((res) =>  
  10.         res.text()  
  11.       );  
  12.   }  

3.2 從互聯(lián)網(wǎng)下載數(shù)據(jù) 

 
 
 
 
  1. 我們可以使用以下方法從互聯(lián)網(wǎng)上下載數(shù)據(jù)并將數(shù)據(jù)存儲到 Blob 對象中,比如:  
  2. const downloadBlob = (url, callback) => {  
  3.  const xhr = new XMLHttpRequest()  
  4.  xhr.open('GET', url)  
  5.  xhr.responseType = 'blob'  
  6.  xhr.onload = () => {  
  7.     callback(xhr.response)  
  8.  }  
  9.  xhr.send(null)  

當(dāng)然除了使用 XMLHttpRequest API 之外,我們也可以使用 fetch API 來實現(xiàn)以流的方式獲取二進制數(shù)據(jù)。這里我們來看一下如何使用 fetch API 獲取線上圖片并本地顯示,具體實現(xiàn)如下: 

 
 
 
 
  1. const myImage = document.querySelector('img');  
  2. const myRequest = new Request('flowers.jpg');  
  3. fetch(myRequest)  
  4.   .then(function(response) {  
  5.     return response.blob();  
  6.   })  
  7.  .then(function(myBlob) {  
  8.    let objectURL = URL.createObjectURL(myBlob);  
  9.    myImage.src = objectURL;  
  10. }); 

當(dāng) fetch 請求成功的時候,我們調(diào)用 response 對象的 blob() 方法,從 response 對象中讀取一個 Blob 對象,然后使用 createObjectURL() 方法創(chuàng)建一個 objectURL,然后把它賦值給 img 元素的 src 屬性從而顯示這張圖片。

3.3 Blob 用作 URL

Blob 可以很容易的作為 、 或其他標(biāo)簽的 URL,多虧了 type 屬性,我們也可以上傳/下載 Blob 對象。下面我們將舉一個 Blob 文件下載的示例,不過在看具體示例前我們得簡單介紹一下 Blob URL。

1.Blob URL/Object URL

Blob URL/Object URL 是一種偽協(xié)議,允許 Blob 和 File 對象用作圖像,下載二進制數(shù)據(jù)鏈接等的 URL 源。在瀏覽器中,我們使用 URL.createObjectURL 方法來創(chuàng)建 Blob URL,該方法接收一個 Blob 對象,并為其創(chuàng)建一個唯一的 URL,其形式為 blob:/,對應(yīng)的示例如下: 

 
 
 
 
  1. blob:https://example.org/40a5fb5a-d56d-4a33-b4e2-0acf6a8e5f641 

瀏覽器內(nèi)部為每個通過 URL.createObjectURL 生成的 URL 存儲了一個 URL → Blob 映射。因此,此類 URL 較短,但可以訪問 Blob。生成的 URL 僅在當(dāng)前文檔打開的狀態(tài)下才有效。它允許引用 、 中的 Blob,但如果你訪問的 Blob URL 不再存在,則會從瀏覽器中收到 404 錯誤。

上述的 Blob URL 看似很不錯,但實際上它也有副作用。雖然存儲了 URL → Blob 的映射,但 Blob 本身仍駐留在內(nèi)存中,瀏覽器無法釋放它。映射在文檔卸載時自動清除,因此 Blob 對象隨后被釋放。

但是,如果應(yīng)用程序壽命很長,那不會很快發(fā)生。因此,如果我們創(chuàng)建一個 Blob URL,即使不再需要該 Blob,它也會存在內(nèi)存中。

針對這個問題,我們可以調(diào)用 URL.revokeObjectURL(url) 方法,從內(nèi)部映射中刪除引用,從而允許刪除 Blob(如果沒有其他引用),并釋放內(nèi)存。接下來,我們來看一下 Blob 文件下載的具體示例。

2.Blob 文件下載示例

index.html 

 
 
 
 
  1.   
  2.   
  3.     
  4.       
  5.     Blob 文件下載示例  
  6.     
  7.     
  8.     文件下載  
  9.       
  10.     
  11.  

index.js 

 
 
 
 
  1. const download = (fileName, blob) => {  
  2.   const link = document.createElement("a");  
  3.   link.href = URL.createObjectURL(blob);  
  4.   link.download = fileName;  
  5.   link.click();  
  6.   link.remove();  
  7.   URL.revokeObjectURL(link.href);  
  8. };  
  9. const downloadBtn = document.querySelector("#downloadBtn");  
  10. downloadBtn.addEventListener("click", (event) => {  
  11.   const fileName = "blob.txt";  
  12.   const myBlob = new Blob(["一文徹底掌握 Blob Web API"], { type: "text/plain" });  
  13.   download(fileName, myBlob);  
  14. }); 

在示例中,我們通過調(diào)用 Blob 的構(gòu)造函數(shù)來創(chuàng)建類型為 "text/plain" 的 Blob 對象,然后通過動態(tài)創(chuàng)建 a 標(biāo)簽來實現(xiàn)文件的下載。

3.4 Blob 轉(zhuǎn)換為 Base64

URL.createObjectURL 的一個替代方法是,將 Blob 轉(zhuǎn)換為 base64 編碼的字符串。Base64 是一種基于 64 個可打印字符來表示二進制數(shù)據(jù)的表示方法,它常用于在處理文本數(shù)據(jù)的場合,表示、傳輸、存儲一些二進制數(shù)據(jù),包括 MIME 的電子郵件及 XML 的一些復(fù)雜數(shù)據(jù)。

在 MIME 格式的電子郵件中,base64 可以用來將二進制的字節(jié)序列數(shù)據(jù)編碼成 ASCII 字符序列構(gòu)成的文本。使用時,在傳輸編碼方式中指定 base64。使用的字符包括大小寫拉丁字母各 26 個、數(shù)字 10 個、加號 + 和斜杠 /,共 64 個字符,等號 = 用來作為后綴用途。

下面我們來介紹如何在 HTML 中嵌入 base64 編碼的圖片。在編寫 HTML 網(wǎng)頁時,對于一些簡單圖片,通常會選擇將圖片內(nèi)容直接內(nèi)嵌在網(wǎng)頁中,從而減少不必要的網(wǎng)絡(luò)請求,但是圖片數(shù)據(jù)是二進制數(shù)據(jù),該怎么嵌入呢?絕大多數(shù)現(xiàn)代瀏覽器都支持一種名為 Data URLs 的特性,允許使用 base64 對圖片或其他文件的二進制數(shù)據(jù)進行編碼,將其作為文本字符串嵌入網(wǎng)頁中。

Data URLs 由四個部分組成:前綴(data:)、指示數(shù)據(jù)類型的 MIME 類型、如果非文本則為可選的 base64 標(biāo)記、數(shù)據(jù)本身: 

 
 
 
 
  1. data:[][;base64], 

mediatype 是個 MIME 類型的字符串,例如 "image/jpeg" 表示 JPEG 圖像文件。如果被省略,則默認值為 text/plain;charset=US-ASCII。如果數(shù)據(jù)是文本類型,你可以直接將文本嵌入(根據(jù)文檔類型,使用合適的實體字符或轉(zhuǎn)義字符)。如果是二進制數(shù)據(jù),你可以將數(shù)據(jù)進行 base64 編碼之后再進行嵌入。比如嵌入一張圖片: 

 
 
 
 
  1.  

但需要注意的是:如果圖片較大,圖片的色彩層次比較豐富,則不適合使用這種方式,因為該圖片經(jīng)過 base64 編碼后的字符串非常大,會明顯增大 HTML 頁面的大小,從而影響加載速度。 除此之外,利用 FileReader API,我們也可以方便的實現(xiàn)圖片本地預(yù)覽功能,具體代碼如下: 

 
 
 
 
  1.   
  2.   
  3.  

在以上示例中,我們?yōu)?file 類型輸入框綁定 onchange 事件處理函數(shù) loadFile,在該函數(shù)中,我們創(chuàng)建了一個 FileReader 對象并為該對象綁定 onload 相應(yīng)的事件處理函數(shù),然后調(diào)用 FileReader 對象的 readAsDataURL() 方法,把本地圖片對應(yīng)的 File 對象轉(zhuǎn)換為 Data URL。

在完成本地圖片預(yù)覽之后,我們可以直接把圖片對應(yīng)的 Data URLs 數(shù)據(jù)提交到服務(wù)器。針對這種情形,服務(wù)端需要做一些相關(guān)處理,才能正常保存上傳的圖片,這里以 Express 為例,具體處理代碼如下: 

 
 
 
 
  1. const app = require('express')();  
  2. app.post('/upload', function(req, res){  
  3.     let imgData = req.body.imgData; // 獲取POST請求中的base64圖片數(shù)據(jù)  
  4.     let base64Data = imgData.replace(/^data:image\/\w+;base64,/, "");  
  5.     let dataBuffer = Buffer.from(base64Data, 'base64');  
  6.     fs.writeFile("image.png", dataBuffer, function(err) {  
  7.         if(err){  
  8.           res.send(err);  
  9.         }else{  
  10.           res.send("圖片上傳成功!");  
  11.         }  
  12.     });  
  13. }); 

對于 FileReader 對象來說,除了支持把 Blob/File 對象轉(zhuǎn)換為 Data URL 之外,它還提供了 readAsArrayBuffer() 和 readAsText() 方法,用于把 Blob/File 對象轉(zhuǎn)換為其它的數(shù)據(jù)格式。這里我們來看個 readAsArrayBuffer() 的使用示例: 

 
 
 
 
  1. // 從 blob 獲取 arrayBuffer  
  2. let fileReader = new FileReader(); 
  3. fileReader.onload = function(event) {  
  4.   let arrayBuffer = fileReader.result;  
  5. };  
  6. fileReader.readAsArrayBuffer(blob); 

3.5 圖片壓縮

在一些場合中,我們希望在上傳本地圖片時,先對圖片進行一定的壓縮,然后再提交到服務(wù)器,從而減少傳輸?shù)臄?shù)據(jù)量。在前端要實現(xiàn)圖片壓縮,我們可以利用 Canvas 對象提供的 toDataURL() 方法,該方法接收 type 和 encoderOptions 兩個可選參數(shù)。

其中 type 表示圖片格式,默認為 image/png。而 encoderOptions 用于表示圖片的質(zhì)量,在指定圖片格式為 image/jpeg 或 image/webp 的情況下,可以從 0 到 1 的區(qū)間內(nèi)選擇圖片的質(zhì)量。如果超出取值范圍,將會使用默認值 0.92,其他參數(shù)會被忽略。

下面我們來看一下具體如何實現(xiàn)圖片壓縮: 

 
 
 
 
  1. // compress.js  
  2. const MAX_WIDTH = 800; // 圖片最大寬度  
  3. function compress(base64, quality, mimeType) {  
  4.   let canvas = document.createElement("canvas");  
  5.   let img = document.createElement("img");  
  6.   img.crossOrigin = "anonymous";  
  7.   return new Promise((resolve, reject) => {  
  8.     img.src = base64;  
  9.     img.onload = () => {  
  10.       let targetWidth, targetHeight;  
  11.       if (img.width > MAX_WIDTH) {  
  12.         targetWidth = MAX_WIDTH;  
  13.         targetHeight = (img.height * MAX_WIDTH) / img.width;  
  14.       } else {  
  15.         targetWidth = img.width;  
  16.         targetHeight = img.height;  
  17.       }  
  18.       canvas.width = targetWidth;  
  19.       canvas.height = targetHeight;  
  20.       let ctx = canvas.getContext("2d");  
  21.       ctx.clearRect(0, 0, targetWidth, targetHeight); // 清除畫布  
  22.       ctx.drawImage(img, 0, 0, canvas.width, canvas.height);  
  23.       let imageData = canvas.toDataURL(mimeType, quality / 100);  
  24.       resolve(imageData);  
  25.     };  
  26.   });  

對于返回的 Data URL 格式的圖片數(shù)據(jù),為了進一步減少傳輸?shù)臄?shù)據(jù)量,我們可以把它轉(zhuǎn)換為 Blob 對象: 

 
 
 
 
  1. function dataUrlToBlob(base64, mimeType) {  
  2.   let bytes = window.atob(base64.split(",")[1]);  
  3.   let ab = new ArrayBuffer(bytes.length);  
  4.   let ia = new Uint8Array(ab);  
  5.   for (let i = 0; i < bytes.length; i++) {  
  6.     ia[i] = bytes.charCodeAt(i);  
  7.   }  
  8.   return new Blob([ab], { type: mimeType });  

在轉(zhuǎn)換完成后,我們就可以壓縮后的圖片對應(yīng)的 Blob 對象封裝在 FormData 對象中,然后再通過 AJAX 提交到服務(wù)器上: 

 
 
 
 
  1. function uploadFile(url, blob) {  
  2.   let formData = new FormData(); 
  3.   let request = new XMLHttpRequest();  
  4.   formData.append("image", blob);  
  5.   request.open("POST", url, true);  
  6.   request.send(formData);  

其實 Canvas 對象除了提供 toDataURL() 方法之外,它還提供了一個 toBlob() 方法,該方法的語法如下:   

 
 
 
 
  1. canvas.toBlob(callback, mimeType, qualityArgument) 

和 toDataURL() 方法相比,toBlob() 方法是異步的,因此多了個 callback 參數(shù),這個 callback 回調(diào)方法默認的第一個參數(shù)就是轉(zhuǎn)換好的 blob文件信息。

介紹完上述的內(nèi)容,我們來看一下本地圖片壓縮完整的示例: 

 
 
 
 
  1.   
  2.   
  3.     
  4.       
  5.       
  6.     本地圖片壓縮  
  7.     
  8.     
  9.       
  10.       
  11.       
  12.     
  13.  

3.6 生成 PDF 文檔

PDF(便攜式文件格式,Portable Document Format)是由 Adobe Systems 在 1993 年用于文件交換所發(fā)展出的文件格式。在瀏覽器端,利用一些現(xiàn)成的開源庫,比如 jsPDF,我們也可以方便地生成 PDF 文檔。 

 
 
 
 
  1.   
  2.   
  3.     
  4.       
  5.       
  6.     客戶端生成 PDF 示例  
  7.     
  8.     
  9.     

    客戶端生成 PDF 示例

      
  10.       
  11.       
  12.     
  13.  

在以上示例中,我們首先創(chuàng)建 PDF 文檔對象,然后調(diào)用該對象上的 text() 方法在指定的坐標(biāo)點上添加 Hello semlinker! 文本,然后我們利用生成的 PDF 內(nèi)容來創(chuàng)建對應(yīng)的 Blob 對象,需要注意的是我們設(shè)置 Blob 的類型為 application/pdf,最后我們把 Blob 對象中保存的內(nèi)容轉(zhuǎn)換為文本并輸出到控制臺。由于內(nèi)容較多,這里我們只列出少部分輸出結(jié)果: 

 
 
 
 
  1. %PDF-1.3  
  2. %o??à  
  3. 3 0 obj  
  4. <
  5. /Parent 1 0 R  
  6. /Resources 2 0 R  
  7. /MediaBox [0 0 595.28 841.89]  
  8. /Contents 4 0 R  
  9. >>  
  10. endobj  
  11. .... 

其實 jsPDF 除了支持純文本之外,它也可以生成帶圖片的 PDF 文檔,比如: 

 
 
 
 
  1. let imgData = 'data:image/jpeg;base64,/9j/4AAQSkZJRgABAQEASABIAAD/...'  
  2. let doc = new jsPDF();  
  3. doc.setFontSize(40)  
  4. doc.text(35, 25, 'Paranyan loves jsPDF')  
  5. doc.addImage(imgData, 'JPEG', 15, 40, 180, 160) 

Blob 的應(yīng)用場景還很多,這里我們就不一一列舉了,感興趣的小伙伴可以自行查閱相關(guān)資料。

四、Blob 與 ArrayBuffer 的區(qū)別

ArrayBuffer 對象用于表示通用的,固定長度的原始二進制數(shù)據(jù)緩沖區(qū)。你不能直接操縱 ArrayBuffer 的內(nèi)容,而是需要創(chuàng)建一個類型化數(shù)組對象或 DataView 對象,該對象以特定格式表示緩沖區(qū),并使用該對象讀取和寫入緩沖區(qū)的內(nèi)容。

Blob 類型的對象表示不可變的類似文件對象的原始數(shù)據(jù)。Blob 表示的不一定是 JavaScript 原生格式的數(shù)據(jù)。File 接口基于 Blob,繼承了Blob 功能并將其擴展為支持用戶系統(tǒng)上的文件。

4.1 Blob vs ArrayBuffer

  •  除非你需要使用 ArrayBuffer 提供的寫入/編輯的能力,否則 Blob 格式可能是最好的。
  •  Blob 對象是不可變的,而 ArrayBuffer 是可以通過 TypedArrays 或 DataView 來操作。
  •  ArrayBuffer 是存在內(nèi)存中的,可以直接操作。而 Blob 可以位于磁盤、高速緩存內(nèi)存和其他不可用的位置。
  •  雖然 Blob 可以直接作為參數(shù)傳遞給其他函數(shù),比如 window.URL.createObjectURL()。但是,你可能仍需要 FileReader 之類的 File API 才能與 Blob 一起使用。
  •  Blob 與 ArrayBuffer 對象之間是可以相互轉(zhuǎn)化的:
    •   使用 FileReader 的 readAsArrayBuffer() 方法,可以把 Blob 對象轉(zhuǎn)換為 ArrayBuffer 對象;
    •   使用 Blob 構(gòu)造函數(shù),如 new Blob([new Uint8Array(data]);,可以把 ArrayBuffer 對象轉(zhuǎn)換為 Blob 對象。

對于 HTTP 的場景,比如在 AJAX 場景下,Blob 和 ArrayBuffer 可以通過以下方式來使用: 

 
 
 
 
  1. function GET(url, callback) {  
  2.   let xhr = new XMLHttpRequest();  
  3.   xhr.open('GET', url, true);  
  4.   xhr.responseType = 'arraybuffer'; // or xhr.responseType = "blob";  
  5.   xhr.send();  
  6.   xhr.onload = function(e) {  
  7.     if (xhr.status != 200) {  
  8.       alert("Unexpected status code " + xhr.status + " for " + url);  
  9.       return false;  
  10.     }  
  11.     callback(new Uint8Array(xhr.response)); // or new Blob([xhr.response]);  
  12.   };  

對于 ArrayBuffer 和 Uint8Array 感興趣的讀者,可以閱讀Deno bytes 模塊全解析這篇文章。

了解完上述的內(nèi)容,相信有的讀者可能會覺得意猶未盡。那么,對于 Blob 來說還有哪些內(nèi)容可以繼續(xù)深入學(xué)習(xí)的呢?本人下一步的計劃是基于 Deno 的源碼,來逐步分析 DenoBlob 的具體實現(xiàn)。當(dāng)然也會順便分析一下 URL.createObjectURL() 方法和 revokeObjectURL() 方法的實現(xiàn)。

五、參考資源

  •  MDN - Blob
  •  MDN - Data URLs
  •  javascript.info - blob
  •  flaviocopes - blob
  •  arraybuffer-vs-blob
  •  javascript-interview-question-what-is-a-blob 

本文題目:你不知道的Blob
本文鏈接:
http://www.5511xx.com/article/cdppihj.html