JS與二進位相關的一切

來源:互聯網
上載者:User

【串連】

本文轉自豆瓣社區http://www.douban.com/note/225494734/

1、http://www.html5rocks.com/en/tutorials/webgl/typed_arrays/
這篇寫得比我好。

2、至於一些很方便庫,可以直接看aurora.js這個項目,為瞭解析音頻檔案,這個項目下了很大功夫...

https://github.com/ofmlabs/aurora.js

【前言】
JS其實是眾所周知的弱類型語言。所以一般來說不屬於嚴肅編程領域,直到近年才受到關注,WEB 2.0以及很多新技術的興起。把它抬上了嚴肅編程的範疇。

這裡主要記錄最近碰到的JS,學術一些來說應該說是EMSCRIPT標準、W3C、HTML5、GOOGLE推出的一系列,對這個語言庫層級的改進。

對二進位的需求與日俱增的原因如下:WEBSCOKET的傳輸需求,FILE API對檔案、二進位BLOB對象的處理,WEBGL對於大量位元據的需求,CAVANS對二進位的處理的迫切需求、XHR2對新的二進位對象的處理需求,也會敘述與NODE.JS的二進位有關的事宜。

*PS:強烈建議去閱讀原草案,以及標準文檔,當然這裡會給出草案的地址

【目錄】
一、XHR2
二、FILE API
       1、FILE LIST
       2、FILE
       3、FILEREADER
三、BLOB URL
四、TYPED ARRAY
      1、BUFFER
      2、ArrayView
      3、DataView
      4、Blob 與 arraybuffer
      5、arraybuffer 與 arraybufferView
五、WEBSCOKET
六、WEBGL

【XHR2】
http://www.html5rocks.com/en/tutorials/file/xhr2/
http://www.w3.org/TR/XMLHttpRequest/#the-responsetype-attribute

新的XHR2文法上有很多改進,細節部分不詳述,可以參見草案。
//得到某個檔案的串列
vargetArrayBuffer=function(url){
                var resourceUrl = url || "http://img1.douban.com/pics/nav/lg_main_a10.png";
                var deferred = $.Deferred();
                var promise = deferred.promise();
            var xhr = new XMLHttpRequest();
            xhr.open('GET', resourceUrl, true);

            // Response type arraybuffer - XMLHttpRequest 2
            xhr.responseType = 'arraybuffer';
            xhr.onerror = function(e) {
                        deferred.reject(xhr, e);
        }

            xhr.onload = function(e) {
                if (xhr.status == 200) {
                    deferred.resolve(xhr);
                }
            };
            xhr.send();
            return promise;
        }
這裡使用了JQ的defferd對象,可以無視,主要修改在於返回xhr.responseType可以設定成arraybuffer或者blob。

【FILE API】

1、主要有File List來表述任何<input type='file'>裡的對象,File繼承與Blob父類,對了長度以及檔案名稱屬性,繼承了Slice操作。

2、File表述一個<input type=file>裡的檔案對象,注意,這裡的File似乎必須是來自於使用者輸入,暫時沒有找到憑空構造的方式。

3、Blob對象是File的父類,主要會感興趣的操作為Slice,分割操作。

4、FileReader()讀寫類,主要負責File|Blob對象的讀寫
http://www.w3.org/TR/FileAPI/#readAsDataURL

var loadBlobToBase64=function(blob){
                var deferred = $.Deferred();
                var promise = deferred.promise();

                var reader = new FileReader();
                reader.onload = function() {
                          deferred.resolve(reader.result);
        }
               reader.readAsDataURL(blob);
               return promise;
}
比較有用的操作為將File或Blob對象讀寫成為BASE64編碼的DataURL,readAsText(),以及readAsArrayBuffer()

【URL API/BLOB URI】
http://www.w3.org/TR/FileAPI/#url

這個理解起來較為簡單,在標準裡,也位於FILE API草案中描述。

var url=window.webkitURL.createObjectURL(blob);
console.log(url);

輸出為:blob:xxxx-xxx-xxx--xxx#frament...

簡單得說就是,你可以使用File API中的FileReader()類,將檔案或二進位的大塊Blob,readAsDataURL,然後賦予img src或其他。

也可以將blob轉儲為BLOB URL,官方的表述即ObjectURL

怎樣理解?

這個URL,是一個記憶體級的指標,但可以供網頁調用,其行為與普通的來自伺服器的檔案毫無二致。

有200狀態代碼,也有500狀態代碼,可以銷毀。

【Typed Array】
http://www.khronos.org/registry/typedarray/specs/latest/

這是這整一套API的核心部分,事實上,不理解這部分,就很難對資料進行任何有效操作與轉換。

暫時以我的理解來說。

1、Buffer
http://www.khronos.org/registry/typedarray/specs/latest/#5
var a=new ArrayBuffer(8);
建立一個新的ArrayBuffer(8);,8bit位為一個單位,uint8。我要了8個單位,即位元組。

這是一個記憶體層級的表達,一個buf.

2、View
http://www.khronos.org/registry/typedarray/specs/latest/#7
appendBuffer=function ( buffer1, buffer2 ) {
                  var tmp = new Uint8Array( buffer1.byteLength + buffer2.byteLength + 4);
                          tmp.set( new Uint8Array( buffer1 ), 0 );
                          tmp.set( new Uint8Array( buffer2 ), buffer1.byteLength );
                  return tmp;
        }

new Uint8Array實際上是建立了一個ref,指標。它可以指向一個已有的buf,那麼這裡建立了一個tem,其大小為兩個buf之和+4.

第二句話是,從0位移量開始,填入一個新的Typed ArrayView ,而這個指標是以buffer1初始化的。
第三句,是從剛才的結尾開始,填入buffer2的內容。

這裡待修改。

3、DataView
http://www.khronos.org/registry/typedarray/specs/latest/#8
https://developer.mozilla.org/en/JavaScript_typed_arrays/DataView

暫略

4、Blob 與 arraybuffer
http://www.w3.org/TR/FileAPI/#dfn-BlobPropertyBag
著名的文章,構造BLOB,別BUILD,指之前一個非廢止的API ,Blobuilder。那個方法效率很低,而且容易出錯(我就寫JS寫出藍屏...過....)

所以,正確的構造法為:

var blob = new Blob([new_buffer], { type: "image/png" });

傳入一個ArrayBuffer對象,並給出MIME TYPE之後,就可以構造恰當的對象。

var url = window.webkitURL.createObjectURL(blob);

接著可以用剛才提到的方式,構造BLOB URL,以供<img src>來調用。

5、arraybuffer 與 arraybufferView
http://www.khronos.org/registry/typedarray/specs/latest/#6
這個當初也讓我迷惑了一陣子,直到看到草案上的複雜資料結構的一個例子之後才理解了。

簡單的說:
appendBuffer=function ( buffer1, buffer2 ) {
                  var tmp = new Uint8Array( buffer1.byteLength + buffer2.byteLength + 4);
                          tmp.set( new Uint8Array( buffer1 ), 0 );
                          tmp.set( new Uint8Array( buffer2 ), buffer1.byteLength );
                  return tmp;
        }

剛才的例子裡,返回的這個tmp,實際上是一個arraybufferView對象,而非buffer本身。

在構造新的BLOB時發現的,所有的Uin8Array對象,都會有一個屬性,即buffer屬性。

要得到指標指的對象的內容,訪問這個屬性即可。
var blob = new Blob([tmp.buffer], { type: "image/png" });

如果你要操作tmp,並構造成BLOB對象,直接用arrayBuffer就可以了,如果傳入的是一個TypedArrayView?,也不用著急,訪問其.buffer屬性即得到背後的ArrayBuffer屬性。

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.