1. [HTML5] Blobオブジェクト
(1)前に書く:このセクションでは、主にBlobオブジェクトのプロパティと機能を紹介し、デモを通じてBlobオブジェクトのアプリケーションシナリオを紹介します。
Blobオブジェクト:ずっと、JSはバイナリーを直接処理するより良い方法はありません。blobの存在により、jsを介してバイナリデータを直接操作できます。
「ブロブオブジェクトは、読み取り専用の生データを含むファイルのようなオブジェクトです。ブロブオブジェクトのデータは、JavaScriptのネイティブ形式である必要はありません。ファイルインターフェースはブロブに基づいており、ブロブの機能を継承し、ユーザーコンピューターのサポートを拡張しますローカルファイル
Blobオブジェクトは、バイナリデータを格納するためのコンテナと見なすことができ、さらに、バイナリデータのMIMEタイプをblobを通じて設定できます。
(2)blobを作成する
方法1:コンストラクターを使用
var blob = new Blob(dataArr:Array <any>、opt:{type:string});
dataArr:配列。blobオブジェクトに追加されるデータを含みます。データは、任意の数のArrayBuffer、ArrayBufferView、blob、またはDOMStringオブジェクトにすることができます
opt:Blobオブジェクト(MIMEタイプなど)の属性を設定するために使用されるオブジェクト
MIME:各URLはリソースオブジェクトを表し、Webページを要求すると、1つのURI(ユニフォームリソース識別子)だけが要求されているようです。実際、このWebページには、画像リソースのURIなど、複数のURIが含まれている場合がありますそして、ビデオリソースのURI。このとき、ブラウザによっては、アクセス速度を上げるために、複数のスレッドを開いて同時にURIを要求する場合があります。つまり、すべてのURIが要求メッセージを送信します。ブラウザがこれらのリソースを表示または処理する場合、応答がどのタイプのデータかわからないため、これらのリソースタイプを区別するには、MIMEを使用する必要があります。HTTPは、Web経由で送信される各オブジェクトにMIMEタイプのデータ形式タグを追加します。対応する情報を読み込んだ後、ブラウザは対応するプログラムを呼び出して、対応するプログラムと必要な結果を処理します。
1つ目:DOMStringオブジェクトで満たされたblobオブジェクトを作成する
画像
2番目の種類:ArrayBufferオブジェクトで満たされたBlobオブジェクトを作成する
画像
3番目のタイプ:ArrayBufferViewオブジェクトで満たされたBlobオブジェクトを作成します(ArrayBufferViewはArrayBufferに基づいて作成でき、戻り値は配列のようです。次のように、8バイトのArrayBufferを作成し、それぞれに2バイトの配列要素を作成します。 「表示」)
画像
方法2:Blob.slice()を使用
このメソッドは、元のblobオブジェクトの指定された範囲のデータを含む新しいBlobオブジェクトを返します
Blob.slice(start:number、end:number、contentType:string)
start:開始インデックス、デフォルトは0
end:終了インデックス(endを除く)
contentType:新しいblobのMIMEタイプ。デフォルトは空の文字列です。
画像
方法3:canvas.toBlob()経由
var canvas = document.getElementById( "canvas");
canvas.toBlob(function(blob){
console.log(blob);
});
2.アプリケーションシナリオ
前述のように、ファイルインターフェイスはblobを継承し、blobの機能を継承して拡張しているため、BlobのようなFileオブジェクトを使用できます。
マルチパートアップロード
Blob.sliceメソッドを使用すると、大きなファイルを断片化し、各ファイルフラグメントをラウンドロビン方式でバックグラウンドに送信し、ファイルをスライスでアップロードできます。
フラグメントをアップロードするロジックは次のとおりです。
アップロードするファイルのFileオブジェクトを取得し、チャンク(各ピースサイズ)に従ってファイルを分割します
各ファイルは、postメソッドを介してラウンドロビン方式でアップロードされます。URLにステッチされたクエリ文字列は、現在アップロードされているファイルの情報を記述するために使用されます。ポストの本文には、アップロードされるバイナリデータフラグメントが格納されます
インターフェースは毎回オフセットを返し、次のアップロードを実行するために使用されます
以下は、マルチパートアップロードの簡単な実装です。
initUpload();//初始化上传functioninitUpload(){
var chunk = 100 * 1024; //每片大小 var input = document.getElementById("file"); //input file input.onchange = function(e){
var file = this.files[0];
var query = {};
var chunks = [];
if (!!file) {
var start = 0;
//文件分片 for (var i = 0; i < Math.ceil(file.size / chunk); i++) {
var end = start + chunk;
chunks[i] = file.slice(start , end);
start = end;
}
// 采用post方法上传文件 // url query上拼接以下参数,用于记录上传偏移 // post body中存放本次要上传的二进制数据 query = {
fileSize: file.size,
dataSize: chunk,
nextOffset: 0 }
upload(chunks, query, successPerUpload);
}
}
}// 执行上传functionupload(chunks, query, cb){
var queryStr = Object.getOwnPropertyNames(query).map(key=> {
return key + "=" + query[key];
}).join("&");
var xhr = new XMLHttpRequest();
xhr.open("POST", "http://xxxx/opload?" + queryStr);
xhr.overrideMimeType("application/octet-stream");
//获取post body中二进制数据 var index = Math.floor(query.nextOffset / query.dataSize);
getFileBinary(chunks[index], function(binary){
if (xhr.sendAsBinary) {
xhr.sendAsBinary(binary);
} else {
xhr.send(binary);
}
});
xhr.onreadystatechange = function(e){
if (xhr.readyState === 4) {
if (xhr.status === 200) {
var resp = JSON.parse(xhr.responseText);
// 接口返回nextoffset // resp = { // isFinish:false, // offset:100*1024 // } if (typeof cb === "function") {
cb.call(this, resp, chunks, query)
}
}
}
}
}// 每片上传成功后执行functionsuccessPerUpload(resp, chunks, query){
if (resp.isFinish === true) {
alert("上传成功");
} else {
//未上传完毕 query.offset = resp.offset;
upload(chunks, query, successPerUpload);
}
}// 获取文件二进制数据functiongetFileBinary(file, cb){
var reader = new FileReader();
reader.readAsArrayBuffer(file);
reader.onload = function(e){
if (typeof cb === "function") {
cb.call(this, this.result);
}
}
}