W3C home > Mailing lists > Public > whatwg@whatwg.org > May 2011

[whatwg] Proposing <canvas>.toBlob(contentType)

From: Ian Hickson <ian@hixie.ch>
Date: Thu, 12 May 2011 20:49:43 +0000 (UTC)
Message-ID: <Pine.LNX.4.64.1105121909030.19153@ps20323.dreamhostps.com>
On Wed, 13 Apr 2011, Kyle Huey wrote:
> 
> Gecko 2.0 ships with a non-standard method on <canvas> named 
> mozGetAsFile(contentType, fileName).  We added this for internal use in 
> our UI.  It retrieves the contents of the canvas as a File object (at 
> the time Gecko did not supports Blobs) encoded in the contentType 
> according to the same rules toDataURL uses.
> 
> I propose adding a toBlob(contentType) method to the canvas element in 
> the style of toDataURL.  This would greatly increase the options 
> available to developers for extracting data from a canvas element (a 
> Blob can be saved to disk, XHRed, etc.)

I've added toBlob(). However, I made it asynchronous, so that it doesn't 
block while generating the Blob.


On Wed, 13 Apr 2011, Glenn Maynard wrote:
> 
> r = canvas.getReader();
> r.onload = function(blob) { blob = r.result; }
> r.readBlob();
> 
> following the pattern of FileReader

That seems a bit more verbose than necessary. I've gone with:

   canvas.toBlob(function(result) { blob = result; });


> This allows browsers to optionally thread compression or (more likely) 
> run it in slices, and this API would allow Progress Events (onprogress) 
> to be supported later on, useful when compressing large images (which 
> may take several seconds).

It's true that on the long term if we want to expose progress events the 
more verbose API would be more useful, but if we ever decide that's an 
important use case to consider, we can always make the method return an 
object on which progress events get fired.


On Wed, 13 Apr 2011, Kyle Huey wrote:
> 
> The problem here is that Blob.size is broken.  The point of the File API 
> is to do reads asynchronously without blocking the main thread on 
> something slow.  This is why the only way to get at a Blob's contents is 
> through something like FileReader which is asynchronous and event 
> driven.  Blob.size goes totally against all of this.  I wonder if it's 
> possible to remove size entirely?  Jonas?  It's been shipped in Firefox 
> since 3.5 though, and Chrome since some version from quite a while ago, 
> so I fear it's here to stay.
> 
> Assuming that Blob.size is here to stay, web developers are just going 
> to have to cope with the fact that it's broken and causes synchronous 
> slow things to happen.  I believe (though I haven't verified) that in 
> Gecko we avoid statting a file on the disk that backs a Blob until 
> Blob.size is called (or somebody passes it to a FileReader and we can 
> touch the disk asynchronously, etc).  In this case the UA could 
> optimize, for example, by encoding on a background thread and simply 
> blocking inside a size call when the encoding has not completed.
> 
> The main drawback of making it asynchronous is that (AIUI, please 
> correct me if I'm wrong) everything else about the canvas element and 
> the 2d rendering context is synchronous.  This adds cognitive overhead 
> both for developers and actual code complexity for implementations.  
> I'll assert, however, that the "behind the scenes" complexities of 
> presenting an asynchronous API for getting a blob and presenting a 
> synchronous API that performs the optimization above are the same.  In 
> particular, in both cases the UA must handle:modifications to the canvas 
> after the Blob Getting API is called. Given this, and that providing an 
> asynchronous API to get an object that is supposed to be inherently 
> asynchronous seems silly, I would prefer the synchronous version here.

On Wed, 27 Apr 2011, Jonas Sicking wrote:
>
> Yeah, I think the current Blob and File interfaces are here to stay. Not 
> just because they have shipped, but because in all other situations 
> access to the File/Blob object is asynchronous, and so providing 
> synchronous access to metadata makes a lot of sense.
> 
> However, we could possibly come up with something like a UnsizedBlob 
> interface. We could possibly even make that a base-class of the normal 
> Blob interface. However it would mean introducing a lot of complexity. 
> All functions that currently take Blob should be changed to take 
> UnsizedBlob. And how would something like BlobBuilder work? Would it 
> return an UnsizedBlob or a Blob?
> 
> Unless we can come up with other APIs where a UnsizedBlob would make 
> sense, I'm tempted to say that we should use an asynchronous callback 
> here.

That's what I've gone with.

-- 
Ian Hickson               U+1047E                )\._.,--....,'``.    fL
http://ln.hixie.ch/       U+263A                /,   _.. \   _\  ;`._ ,.
Things that are impossible just take longer.   `._.-(,_..'--(,_..'`-.;.'
Received on Thursday, 12 May 2011 13:49:43 UTC

This archive was generated by hypermail 2.4.0 : Wednesday, 22 January 2020 16:59:33 UTC