W3C home > Mailing lists > Public > public-html@w3.org > February 2008

Re: Review of 3.14.11. The canvas element

From: Ian Hickson <ian@hixie.ch>
Date: Fri, 1 Feb 2008 04:58:27 +0000 (UTC)
To: Mihai Sucan <mihai.sucan@gmail.com>
Cc: public-html <public-html@w3.org>
Message-ID: <Pine.LNX.4.62.0802010334440.3212@hixie.dreamhostps.com>

On Tue, 21 Aug 2007, Mihai Sucan wrote:
> 1. "Whenever the width and height attributes are set (whether to a new 
> value or to the previous value), the bitmap and any associated contexts 
> must be cleared back to their initial state and reinitialised with the 
> newly specified coordinate space dimensions."
> Why must the canvas image be cleared when the width/height changes?

Because the coordinate space will have changed.

> Things as resizing the canvas are made harder, when one wants to keep 
> the image.

You can resize the canvas itself without changing the coordinate space. 
Use CSS to set the display size.

> Changing the width/height should be defined such that setting a higher 
> value only adds transparent black pixels. For lower values, the image is 
> truncated.

Why change the value at all?

> Applications like games and painting tools would benefit from not 
> clearing the image when changing the canvas size. Games would only need 
> to draw in the "new pixels". As defined, such applications would have to 
> completely redraw the image on the canvas, making things slower.

I would imagine that most games would have to redraw everything anyway, 
since they likely want to keep everything centered, and will likely have 
HUD-like displays that will need repainting. Painting tools might benefit 
in certain cases (like when resizing the canvas means merely adding pixels 
to the right and bottom), but not in others (like when resizing the canvas 
means adding pixels to the left and bottom, or when scaling, etc).

In practice, it's easy to work around. Just create a new canvas using 
cloneNode(), drawImage() the first to the second, change your coordinate 
space units, and drawImage() the image back.

> 2. There's a typo after the first code example (the one which shows how 
> changing the width/height of the canvas clears the image):
> "This specification only defines one context, with the name "2d". If 
> getContext() is called with that exact string for *tis* contextId 
> argument, then the UA must return a reference to an object implementing 
> CanvasRenderingContext2D. Other specifications may define their own 
> contexts, which would return different objects."
> Correction: tis = this.

This got fixed at some point already.

> 3. The getContext() method should be defined such that any number of 
> additional arguments are allowed, just like toDataURL() is defined. This 
> is forward thinking about initializing various contexts with any 
> settings.


> 4. In the "Pixel manipulation" section [2] one can read:
> "The data returned by getImageData() is at the resolution of the canvas 
> backing store, which is likely to not be one device pixel to each CSS 
> pixel if the display used is a high resolution display. Thus, while one 
> could create an ImageData object, one would *net* necessarily know what 
> resolution the canvas expected (how many pixels the canvas wants to 
> paint over one coordinate space unit pixel)."
> This is the first paragraph found in the provded example.
> Correction: one would need to know what...

Couldn't find "already net" -- already fixed, it seems.

> 5. Drawing states should be saveable with IDs, and for easier restoring.
> save(id)
> restore(id)
> If id is not provided, then save() works as defined now. The same for 
> restore().
> Currently, it's not trivial to save and restore a specific state.

Noted for v3.

> 6. I do not "like" the save/restore() method names.
> It's ambiguous what they do. I initially believed they do what's 
> suggested in the next point.
> I would suggest renaming the methods to: saveState() and restoreState().
> I don't believe it can be argued that such changes break (too many) 
> applications. Today's applications using canvas are experiments. The 
> entire spec is subject to change, and as such nobody should complain.

Sadly, this is not the case. I am already hearing browser vendors tell me 
they can't (won't) implement parts of the spec because they are concerned 
about compatibility with deployed content. Indeed, I have had to change a 
major part of the canvas spec (the way paths respond to transforms) in 
response to vendor feedback of this nature. So we can't change the method 
names now.

> 7. On the basis of save()/restore() state, I think it would be a good 
> idea (performance-wise, for various applications), to be able to do 
> something like this:
> saveImage(id)
> restoreImage(id)
> This wold allow caching images drawn by the application, in the memory 
> provided by the UA. Currently, one could use a data URI, or an ImageData 
> object, but such solutions are far from ideal since they are not as fast 
> as native UA methods, plus they use more memory than a native 
> implementation.

getImageData should be native-fast. You can also copy to another canvas.

> The saveImage and restoreImage methods could also allow four optional 
> arguments: x, y, w and h. Obviously, these define where to start from 
> and where to end saving/restoring the image.

I think this should be already dealt with pretty well by getImageData(). 
(We'll ba making some changes to make that even faster, too.)

> 8. I would add my "two cents" about providing a way to render text, but 
> this has already been over-discussed. Yes, something that would be 
> needed.

Agreed. There's a whole separate set of issues for that.


This will probably be done for v3.

> 9. I would propose something different, a different idea. Why not define 
> an optional method for the 2d context, which allows authors to say 
> something like importNodeRender()? Here's the "funky" idea:
> importNodeRender(node)
> ... where node is any DOM node, e.g. 
> document.getElementById('whatever'). The way "captures" the rendered 
> image of that element, irrespective what it is (maybe it's SVG, Flash, 
> simple HTML+CSS, whatever).
> importDocument(x, y, w, h)
> This method could allow the author to capture a part of the rendered 
> document page. x and y positions are taken from the entire document, not 
> just the visible page, in the current window size.
> This capability would allow authors to "hack" a way to render text in 
> the canvas view. Of course, this would allow much more than that.
> Would this be overly complex? Popular UAs already have ways to generate 
> page thumbs.

Yeah, this is something we'll probably do in due course. There are a 
number of issues with exposing it to Web content though. For example, how 
to safely handle cross-domain content (e.g. with iframes present), how to 
handle rendering pages when the actual rendering has dimensions different 
than what the author expects, how to handle rendering nodes that aren't in 
a DOM, etc. I imagine we'll revisit this for v3 or v4.

Ian Hickson               U+1047E                )\._.,--....,'``.    fL
http://ln.hixie.ch/       U+263A                /,   _.. \   _\  ;`._ ,.
Things that are impossible just take longer.   `._.-(,_..'--(,_..'`-.;.'
Received on Friday, 1 February 2008 04:58:44 UTC

This archive was generated by hypermail 2.3.1 : Thursday, 29 October 2015 10:15:30 UTC