简体   繁体   English

在JavaScript中将base64图像转换为文件对象

[英]Converting base64 Image to file object in JavaScript

I am trying to create a file object from a base64 image which was cut from another image. 我试图从base64图像创建一个文件对象,该图像是从另一个图像切割而来的。 I am able to do it but the resulting file size is almost thrice the actual size. 我能够做到但是生成的文件大小几乎是实际大小的三倍。 Below is the function that I am using: 以下是我正在使用的功能:

convertDataURItoFile(dataURI, fileName) {
    // convert base64 to raw binary data held in a string
    // doesn't handle URLEncoded DataURIs - see SO answer #6850276 for code that does this
    var byteString = atob(dataURI.split(',')[1]);

    // separate out the mime component
    var mimeString = dataURI.split(',')[0].split(':')[1].split(';')[0]

    // write the bytes of the string to an ArrayBuffer
    var ab = new ArrayBuffer(byteString.length);

    var ia = new Uint8Array(ab);
    for (var i = 0; i < byteString.length; i++) {
      ia[i] = byteString.charCodeAt(i);
    }
    // write the ArrayBuffer to a blob, and you're done
    var blob: any = new Blob([ia], { type: mimeString });

    //A Blob() is almost a File() - it's just missing the two properties below which we will add
    blob.lastModifiedDate = new Date();
    blob.name = fileName;
    //Cast to a File() type
    return <File>blob;
  }

Any idea on why the file size increasing so drastically? 有没有想过为什么文件大小如此急剧增加? How can I compress it? 我怎么压缩它? Thanks in advance. 提前致谢。

I am trying to create a file object from a base64 image which was cut from another image. 我试图从base64图像创建一个文件对象,该图像是从另一个图像切割而来的。 I am able to do it but the resulting file size is almost thrice the actual size. 我能够做到但是生成的文件大小几乎是实际大小的三倍。

Cannot reproduce resulting .size of Blob being thrice the size of the content of input data URI . 无法重现Blob结果.size三倍于输入data URI内容的大小。 Do you mean the data URI .length can be thrice the size of Blob .size ? 你的意思是data URI .length可以是Blob .size大小的三倍吗?

 function convertDataURItoFile(dataURI, fileName) { // convert base64 to raw binary data held in a string // doesn't handle URLEncoded DataURIs - see SO answer #6850276 for code that does this var byteString = atob(dataURI.split(',')[1]); // separate out the mime component var mimeString = dataURI.split(',')[0].split(':')[1].split(';')[0] // write the bytes of the string to an ArrayBuffer var ab = new ArrayBuffer(byteString.length); var ia = new Uint8Array(ab); for (var i = 0; i < byteString.length; i++) { ia[i] = byteString.charCodeAt(i); } // write the ArrayBuffer to a blob, and you're done var blob = new Blob([ia], { type: mimeString }); //A Blob() is almost a File() - it's just missing the two properties below which we will add blob.lastModifiedDate = new Date(); blob.name = fileName; //Cast to a File() type console.log(`input data size: ${datauriLength} Blob.size: ${blob.size}`); return blob; } const [datauri, filename] = ["data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAASoAAADCCAYAAAD+Wo90AAAABHNCSVQICAgIfAhkiAAAApVJREFUeJzt1DEBACAMwLCBf88ggZMeiYJeXTPnDEDY/=", "filename.png"]; const datauriLength = datauri.length; const reader = new FileReader; reader.onload = () => { console.log(`data URI: ${reader.result}`) document.querySelector("iframe").src = reader.result; }; reader.readAsDataURL(convertDataURItoFile(datauri, filename)); 
 <iframe></iframe> 

If .name and .lastModifiedDate need to be added to Blob , you can substitute using File constructor for Blob , which expects file name parameter to be set at second parameter to File constructor, and optionally expected .lastModidied and or .lastModifiedDate parameters at third parameter to constructor. 如果需要将.name.lastModifiedDate添加到Blob ,则可以使用File构造函数替换Blob ,它希望将文件名参数设置为File构造函数的第二个参数,并在第三个参数中选择预期的.lastModidied.lastModifiedDate参数到构造函数。

 function convertDataURItoFile(dataURI, fileName) { // convert base64 to raw binary data held in a string // doesn't handle URLEncoded DataURIs - see SO answer #6850276 for code that does this var byteString = atob(dataURI.split(',')[1]); // separate out the mime component var mimeString = dataURI.split(',')[0].split(':')[1].split(';')[0] // write the bytes of the string to an ArrayBuffer var ab = new ArrayBuffer(byteString.length); var ia = new Uint8Array(ab); for (var i = 0; i < byteString.length; i++) { ia[i] = byteString.charCodeAt(i); } // write the ArrayBuffer to a blob, and you're done // use `File` constructor here var blob = new File([ia], fileName, { type: mimeString, lastModifiedDate: new Date() }); //A Blob() is almost a File() - it's just missing the two properties below which we will add // blob.lastModifiedDate = new Date(); // blob.name = fileName; //Cast to a File() type console.log(`input data size: ${datauriLength} Blob.size: ${blob.size}`); return blob; } const [datauri, filename] = ["data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAASoAAADCCAYAAAD+Wo90AAAABHNCSVQICAgIfAhkiAAAApVJREFUeJzt1DEBACAMwLCBf88ggZMeiYJeXTPnDEDY/=", "filename.png"]; const datauriLength = datauri.length; const reader = new FileReader; reader.onload = () => { console.log(`data URI: ${reader.result}`) document.querySelector("iframe").src = reader.result; }; reader.readAsDataURL(convertDataURItoFile(datauri, filename)); 
 <iframe></iframe> 

You can also utilize fetch() to create and get Blob representation of data URI , see Answer by @Endless at Creating a Blob from a base64 string in JavaScript 您还可以使用fetch()创建并获取data URI Blob表示,请参阅@Endless 在JavaScript中从base64字符串创建Blob时的答案

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM