web-dev-qa-db-fra.com

Compatibilité du navigateur du constructeur d'objets blob

Je développe une application où je reçois des données d'image stockées dans un uint8Array. Je transforme ensuite ces données en un Blob, puis je crée l'URL de l'image.

Code simplifié pour obtenir des données du serveur:

var array;

var req = new XMLHttpRequest();
var url = "img/" + uuid + "_" +segmentNumber+".jpg";
req.open("GET", url, true);
req.responseType = "arraybuffer";
req.onload = function(oEvent) {
    var data = req.response;    
    array = new Int8Array(data);      
};

Constructeur:

out = new Blob([data], {type : datatype} );

Le destructeur Blob est à l'origine du problème. Cela fonctionne très bien sur tous les navigateurs sauf Chrome sur les appareils mobiles et de bureau.

Utilisation de Blob:

// Receive Uint8Array using AJAX here
// array = ...
// Create BLOB
var jpeg = new Blob( [array.buffer], {type : "image/jpeg"});
var url = DOMURL.createObjectURL(jpeg);
img.src = url;

Chrome de burea me donne un avertissement: ArrayBuffer values are deprecated in Blob Constructor. Use ArrayBufferView instead.

Chrome mobile me donne un erreur: illegal constructor

Si je change le constructeur pour travailler sur Chrome il échoue sur les autres navigateurs.

33
Jacob

Je l'ai fait fonctionner avec votre code. Je n'ai eu qu'à changer un petit détail:

if(e.name == 'TypeError' && window.BlobBuilder){
        var bb = new BlobBuilder();
        bb.append(data);
        out = bb.getBlob(datatype);
        console.debug("case 2");
    }

bb.append (données); // les données doivent être sans parenthèses

Ma fonction (constructeur) qui fonctionne maintenant pour tous les navigateurs:

var NewBlob = function(data, datatype)
{
    var out;

    try {
        out = new Blob([data], {type: datatype});
        console.debug("case 1");
    }
    catch (e) {
        window.BlobBuilder = window.BlobBuilder ||
                window.WebKitBlobBuilder ||
                window.MozBlobBuilder ||
                window.MSBlobBuilder;

        if (e.name == 'TypeError' && window.BlobBuilder) {
            var bb = new BlobBuilder();
            bb.append(data);
            out = bb.getBlob(datatype);
            console.debug("case 2");
        }
        else if (e.name == "InvalidStateError") {
            // InvalidStateError (tested on FF13 WinXP)
            out = new Blob([data], {type: datatype});
            console.debug("case 3");
        }
        else {
            // We're screwed, blob constructor unsupported entirely   
            console.debug("Errore");
        }
    }
    return out;
}
1
Jacob

Donc, ce sont en fait deux problèmes différents. Le bureau Chrome était un bug dans chrome qui est corrigé depuis le 2013-03-21).

Mobile Chrome vous donne une TypeError car le constructeur de blob n'est pas pris en charge. À la place, vous devez utiliser l'ancienne API BlobBuilder. L'API BlobBuilder a spécifique au navigateur constructeurs BlobBuilder. Cette c'est le cas pour FF6 - 12, Chrome 8-19, Mobile Chrome, IE10 et Android 3.0-4.2.

var array = new Int8Array([17, -45.3]);

try{
  var jpeg = new Blob( [array], {type : "image/jpeg"});
}
catch(e){
    // TypeError old chrome and FF
    window.BlobBuilder = window.BlobBuilder || 
                         window.WebKitBlobBuilder || 
                         window.MozBlobBuilder || 
                         window.MSBlobBuilder;
    if(e.name == 'TypeError' && window.BlobBuilder){
        var bb = new BlobBuilder();
        bb.append(array.buffer);
        var jpeg = bb.getBlob("image/jpeg");
    }
    else if(e.name == "InvalidStateError"){
        // InvalidStateError (tested on FF13 WinXP)
        var jpeg = new Blob( [array.buffer], {type : "image/jpeg"});
    }
    else{
        // We're screwed, blob constructor unsupported entirely   
    }
}

Violon: http://jsfiddle.net/Jz8U3/13/

29
JoeyP