html5 Canvas getImageData或toDataURL的结果 - 哪个占用更多内存?

时间:2012-08-10 06:47:19

标签: javascript html5 canvas

我的应用程序的一部分包括使用标准的2d上下文画布和webGL混合的html5照片编辑。

无论如何,当用户操纵他们的照片时,我正在保存“撤消”状态。这些都作为base64图像数据存储在Javascript对象中。

一切正常,表现也很好。

但是我想知道从getImageData存储数据是否会占用更少的内存或提供更好的性能?

总结一下我的问题是:

在内存中占用更多空间,由toDataURL()生成的base64 jpeg还是getImageData()的结果?两者之间是否有任何性能差异(关于加载到画布上,以及从画布中提取数据)

提前致谢。

3 个答案:

答案 0 :(得分:15)

getImageData()占用的内存多于toDataURL()

  • ImageData 是像素数组,有关图像的最大信息,像素数组的长度为widthOfImage * heightOfImage * 4,例如图像尺寸为100的图像的数据长度为var imageDataArrayLenth = 100 * 100 * 4 = 40 000 (bytes);
  • BLOB(JPG或PNG)是使用jpg或png算法压缩的imageData,其大小可能比imageData小10或20倍(取决于图像内容)。
  • DataURL(BASE64)是将imageData压缩为JPG或PNG,然后转换为字符串,此字符串比BLOB大37%(info)。

结论:更好的方法是使用 BLOB info)。

//Example of using blob with objectURL
var canvas = document.getElementById("canvas");

canvas.toBlob((blob) => {
  let img = new Image();
  img.onload = () =>  URL.revokeObjectURL(img.src);  // no longer need to read the blob so it's revoked
  img.src = URL.createObjectURL(blob);
  document.body.appendChild(img);
});

答案 1 :(得分:8)

好问题!我不确定对象本身的真实大小,它应该在JS的实现之间有所不同,但这并不意味着我们不能做出一些有根据的猜测。

首先,我们可以使用此问题的近似函数:JavaScript object size

举一个例子:http://jsfiddle.net/g39uz/

字符串可能是80116字节,与ImageData的720056字节相比。或者左右。

这里有一个数量级的差异,如果图像很简单,差异会更加明显。值得记住的是,Base64表示可以被压缩(并且它是)。让我们通过使用空白画布将它带到极限片刻:

http://jsfiddle.net/g39uz/2/

在空白画布上,dataURL字符串只是1996字节(或左右),但图像数据,当然仍然尽职尽责地描述了刻薄的阵列细节中的每一个像素,仍然是720056.

简而言之,如果你要存储它,base64字符串可能占用的空间更少。一个数量级。

答案 2 :(得分:1)

前几天我刚刚完成了这个... getImageData方法返回一个图像对象,其中实际数据存储在uint8array中...你必须将数据转换为数据库可以管理的东西,而不是值得的是,最终输出远大于toDataURL方法

将toDataURL base64字符串放回到画布上也很简单...你只是实例化一个新图像并给src指定base64字符串