Drawing complex gradients on the canvas

desired_effect

While on my way to build this awesome lightbox plugin, I thought a coloured backlight effect would spice up the things. But drawing it was not an easy task.

Canvas complexity

While the canvas element is pretty good at drawing simple gradients it doesn’t provide an easy way to stretch or deform things. Or to blur them. So, drawing a radial gradient and then applying some warping was not easily achievable. Nor blurring of some simple shapes.

Photoshop inspiration

The simplest way I could draw that thing on the canvas was using a transparency mask like Photoshop uses. Masking is also the right way to do it, because a transparent PNG with a background color will overlay a color. Masking changes the alpha channel so it can be shown over anything.

Advantages:

  • Easy to use
  • Only 813 bytes minified
  • Masks anything

Known Flaws:

  • IE lacks canvas support ( only IE 9 and above )
  • Slow drawing times
  • Mask and source images must have the exact same size

Examples

var canvas = document.getElementById( 'canvas_id' ), image = new Image();
image.onload = function(){
	
	var mask = new CanvasMask( canvas, this ), photo = new Image();
	photo.onload = function(){
	
		mask.context.drawImage( this, 0, 0 );
		mask.mask();
		
	};
	photo.src = 'photo.jpg';

};
image.src = 'mask.jpg';

inna

The mask is applied to the canvas and then the container background is changed. Note that the code doesn’t include the coloring algorithm and creating a mask erases the canvas.