Playing With Canvas

a presentation by Geoffrey Roberts

g.roberts@blackicemedia.com

Thursday, 17th February 2011

What is the Canvas API?

Canvas is a JavaScript API for drawing arbitrary graphics onto a website

W3C Editor's Draft as of October 2009

Bounds of this talk

You need to know a little JavaScript

We'll keep it short

We'll cover 2D context only

Origin

Canvas was introduced by apple to power dashboard widgets & extra stuff in webkit

Safari & Chrome 3 introduced it

Later adopted by Mozilla (FF3+) & Opera (10+)

Now finally in IE9!

Examples of usage

Ace

ImpactJS

The Wilderness Downtown

Ambilight

RGraph

and I do too...

Canvas element

If you can see this your browser doesn't support canvas.

A 2d region defined in html markup <canvas />

Takes width and height attributes

JS api to draw to it

Defining context

To do any drawing you first need to get its context

document.getElementById(elem).getContext('2d')

Drawing lines

If you can see this your browser doesn't support canvas.
context.beginPath();
context.moveTo(50, 100);
context.lineTo(200, 300);
context.strokeStyle = "#fff";
context.lineWidth = 5;
context.stroke();

Fills

If you can see this your browser doesn't support canvas.
context.fillStyle = "#900";
context.fillRect(10, 10, 50, 50);

var my_gradient = context.createLinearGradient(0, 0, 300, 0);
my_gradient.addColorStop(0, "green");
my_gradient.addColorStop(1, "white");
context.fillStyle = my_gradient;
context.fillRect(100, 100, 200, 200);

context.clearRect(150, 150, 50, 50);

context.fillStyle = "rgba(255, 255, 200, 0.5)";
context.arc(300, 300, 100, 0, (2*Math.PI), true);
context.fill();

Images

If you can see this your browser doesn't support canvas.
var kar1 = document.getElementById("kar1");
context.drawImage(kar1, 0, 0);

var kar2 = new Image();
kar2.src = "images/karkat-trans.png";
kar2.onload = function() {
	for (var i = 0; i < 400; i += 50) {
		context.drawImage(kar2, i, 350, 50, 50);
	}
};

Compositing

If you can see this your browser doesn't support canvas.
context.fillStyle = "#900";
context.fillRect(10, 10, 200, 200);
context.globalCompositeOperation = 'source-over';
context.fillStyle = "#090";
context.fillRect(150, 150, 200, 200);

Pixel manipulation

If you can see this your browser doesn't support canvas.

getImageData, putImageData

array of pixel data [r,g,b,a,r,g,b,a...]

createImageData

var myImageData = context.getImageData(0, 0, 200, 150);
for(var i = 0; i < myImageData.length; i++)
{
	if(i % 4 != 3)
	{
		myImageData[i] = Math.abs(256-myImageData[i]);
	}
}
context.putImageData(myImageData, 200, 0);

Text

If you can see this your browser doesn't support canvas.
context.font = "normal 36px sans-serif";
context.fillStyle = "#aea";
context.fillText("x", 248, 43);
context.fillText("y", 58, 165);

context.font = "bold 160px sans-serif";
context.fillStyle = "#f00";
context.fillText("A", 300, 300);

context.font = "normal 20px sans-serif";
context.fillStyle = "#fff";
context.fillText("Lorem ipsum dolor sit amet.", 20, 20);

Export to file

canvas.toDataURL()

nihilogic.dk/labs/canvas2image

mikechambers.com/blog/2011/02/01/detecting-canvas-todataurl-support-in-browsers

Compatibility

As with other HTML elements, anything inside the element is the fallback

IE <= 8 doesn't support canvas at all

ExplorerCanvas adequate replacement but doesn't support everything

excanvas.sourceforge.net

flashcanvas.net

Accessibility

Concerns over access by blind

Marks on canvas not defined in markup

When authors use the canvas element, they must also provide content that, when presented to the user, conveys essentially the same function or purpose as the bitmap canvas

Some extreme positions on how to handle it

Accessibility: Opinion/Editorial

Consider who your users are and how they will use your site

Best position? probably to provide data that expresses intent.

How you do it? up to you

3D

If you can see this your browser doesn't support canvas.

WebGL: Chrome supports this now, Firefox v4 maybe?

3D context is hard, but if you know OpenGL you can get started now

glge.org

scenejs.org

Relation to Drupal

New ways of presenting information

Achieve interesting effects without using Flash

More possibilities for enhancing UX

See also

diveintohtml5.org/canvas.html

developer.mozilla.org/en/Canvas_tutorial

paciellogroup.com/blog/?p=362

...and here's one I made earlier