Skip to content

Canvas Extension Layers

Canvas Extension Layers are a Html5 Canvas framework that enables hit detection, layering, pixel ratio management, exports, and downloads for either 2d or webgl canvas modes.

CEL

viewports

Return an array of instantiated viewports

const viewports = CEL.viewports;

CEL.Viewport

The viewport hosts the layer stack and renders this into the final HTML canvas element visible to the end user.

constructor

Create a multi-layered canvas.

const viewport = new CEL.Viewport();

scene

Return the viewport scene which all of the layers are composited into.

const scene = viewport.scene;

index

const index = viewport.index;

add()

Add a layer to the viewport.

viewport.add(layer);

render()

Render the viewport by compositing all layers into a single viewport scene canvas which is visible to the end user.

viewport.render();

setSize()

Set the viewport size in pixels and all layers in the stack which are composited into the viewport. This also includes each associated hit detection layer. This can be utilized for pointer events.

viewport.setSize(600, 300);

getIntersection()

Return the layer index, if any, for the supplied x and y coordinates. If none (transparent) then return a value of -1. This can be used for pointer detection.

const key = viewport.getIntersection(20, 30);

destroy()

// goodbye forever
viewport.destroy();

CEL.Layer

A CEL layer provides a scene and hit, both of which contain a HTML canvas element. The scene canvases composited into the final viewport canvas that the end user can see. The hit canvas remains hidden from the end user, and is used for pointer interaction detection.

constructor

const layer = new CEL.Layer();

scene

Draw a rectangle on the scene canvas. This will be visible to the end user.

layer.scene.context.fillStyle = 'red';
layer.scene.context.fillRect(0, 0, 100, 50);

hit

Draw a rectangle on the hit canvas for hit detection. This is not visible to the end user.

layer.hit.context.fillStyle = layer.hit.getIndexValue(0);
layer.hit.context.fillRect(0, 0, 100, 50);

visible

Set the layer visibility: true, false.

// hide layer
layer.visible=false;
viewport.render();

// show layer
layer.visible=true;
viewport.render();

setPosition()

Set the layer position relative to the viewport.

layer.setPosition(50, 50);

setSize()

Set layer size and associated hit detection layer

layer.setSize(600, 200);

setComposition()

Set layer composition / blending mode.

layer.setCompositin("multiply");
ValueDescription
source-overDefault
Displays the source over the destination
source-atopDisplays the source on top of the destination. The part of the source image that is outside the destination is not shown
source-inDisplays the source in the destination. Only the part of the source that is INSIDE the destination is shown, and the destination is transparent
source-outDisplays the source out of the destination. Only the part of the source that is OUTSIDE the destination is shown, and the destination is transparent
destination-overDisplays the destination over the source
destination-atopDisplays the destination on top of the source. The part of the destination that is outside the source is not shown
destination-inDisplays the destination in the source. Only the part of the destination that is INSIDE the source is shown, and the source is transparent
destination-outDisplays the destination out of the source. Only the part of the destination that is OUTSIDE the source is shown, and the source is transparent
lighterDisplays the source + the destination
copyDisplays the source. The destination is ignored
xorThe source is combined by using an exclusive OR with the destination
multiply
screen
overlay
darken
lighten
color-dodge
color-burn
hard-light
soft-light
difference
exclusion
hue
saturation
color
luminosity

move()

Change the stacking order of the layer. It accepts one parameter of type string from the following values: "up", "down", "top", "bottom" or of type number specifying which layer order to set it to with the lowest layer having a value of zero. Negative values will position the layer after the topmost layer.

// move to top of layer stack
layer.move("top");

moveUp()

Move layer on position up the stack.

layer.moveUp();

moveDown()

Move layer on position down the stack.

layer.moveDown();

moveToTop()

Place the layer on the top of the stack, giving it the highest index value.

layer.moveToTop();

moveToBottom()

Place the layer at the bottom of the stack, giving it an index value of zero.

layer.moveToBottom();

getIndex()

Return the index of the layer in the stack order. A value of zero is the bottom of the layer stack with the layer order being ascending.

const index = layer.getIndex();

destroy()

Remove the layer.

layer.destroy();

CEL.Scene

constructor

const scene = new CEL.Scene();

context

Return canvas context for drawing operations.

const context = scene.context;

canvas

Return canvas element

const canvas = scene.canvas;

setSize()

scene.setSize(600, 200);

clear()

scene.clear();

toImage()

ParameterTypeDescriptionRequired
typestringimage type, “image/png” (default), “image/jpg”, “image/webp”false
qualitynumberimage qualityfalse
cbfunctioncallback to receive the data URLtrue
const cb = function(imageURL) {
  // do something with the image
}
scene.toImage(type, quality, cb);

A callback function is required to receive the data URL. toImage will export a .png image by default.

export()

export() will trigger a file download, exporting a .png image snapshot of the scene.

ParameterTypeDescriptionRequired
cfgobject{fileName}false
cbfunctionalternative handlerfalse
typestringimage type, “image/png” (default), “image/jpg”, “image/webp”false
qualitynumberimage qualityfalse
// download the canvas as an image to your computer.
const cfg = {fileName: 'my-file.png'}
scene.export(cfg, null, type, quality);

By default, export() will export a .png image for download. If no file name is supplied, it will use the chart id by default.

Hit Detection

Canvas Extension Layers provides an API for pixel perfect hit detection of pointers.

const layer = new CEL.Layer(cfg);
const hit = layer.hit

See Hit Detection for information on how to implement it.

constructor

const hit = new CEL.Hit();

canvas

Return canvas HTML element

const canvas = hit.canvas;

context

Return canvas index for drawing operations.

const context = hit.context;

setSize()

Set the hit detection layer.

hit.setSize(600, 200);

clear()

Clear the hit detection layer.

hit.clear();

getIndexValue()

Get hit value (colour) from index. This value is used as the fill or stroke value for the hit mask which is used for pointer detection.

function drawHitCircle(config) {
  var hit = config.layer.hit,
      context = hit.context;

  hit.clear();
  context.save();
  context.beginPath();
  context.arc(config.x, config.y, 60, 0, Math.PI*2, false);
  context.fillStyle = hit.getIndexValue(config.key);
  context.fill();
  context.restore();
}

getIntersection()

getIntersection(x, y) tests if a hit for coordinates. This can be used for pointer interactivity. Returns the associated layer index value or -1 if not hit.

const dataIndex = hit.getIntersection(20, 30);