WICG Specification
Render HTML into Canvas — natively
The spec adds three primitives that draw fully-styled, accessible
HTML straight into <canvas> — no
html2canvas, no screenshots, no libraries.
- Chrome Canary or Brave Stable
- Flag is dev-only
- No install
Enable the flag (30 seconds)
Works in Chrome Canary and Brave Stable (Chromium 147+). No install if you already have one of these.
- Paste this URL into your address bar
Chrome blocks direct links to
chrome://pages for security, so copy-paste is required. Brave users:brave://also works. - Set Enable the new drawElement API for Canvas to Enabled
- Relaunch the browser
Hit Relaunch at the bottom of the flags page, then reload this site.
Three Primitives, One New Superpower
The spec introduces a minimal, composable API surface — each piece solves a distinct problem.
layoutsubtree
Add this attribute to a <canvas> to opt its
children into layout and hit testing — they behave like normal DOM
elements but remain invisible until drawn.
<canvas layoutsubtree>
<div id="content">
Laid out, accessible,
ready to draw.
</div>
</canvas> drawElementImage()
Draws a child element into the canvas with the current transform applied. Works across 2D, WebGL, and WebGPU contexts.
const t = ctx.drawElementImage(
element, x, y
);
// Sync DOM position
element.style.transform =
t.toString(); paint event
Fires whenever a child element's rendering changes — clear the canvas and redraw in one efficient callback, once per frame.
canvas.onpaint = (e) => {
ctx.reset();
for (const el of e.changedElements) {
ctx.drawElementImage(el, 0, 0);
}
}; Why This Matters
Accessibility built in
Drawn elements are the fallback content — the accessibility tree always matches what's on screen.
Real CSS rendering
Fonts, ligatures, RTL, subpixel rendering — the browser does the hard work, not a polyfill.
No hacks required
Replace html2canvas-style workarounds with a native API
that's fast, correct, and privacy-preserving.
2D, WebGL & WebGPU
One API surface that works across all three canvas contexts — render HTML as 3D textures, apply shaders, and more.
Featured Demos
View all demos3D Room with Live Web Content
A Three.js first-person 3D room where live HTML elements are rendered as textures on surfaces — a monitor dashboard, a styled poster, and a TV playing CSS animations.
Accessible Charts
Bar and pie charts with real HTML labels, ARIA roles, keyboard navigation, and hand-drawn focus rings.
CSS-to-Shader Pipeline
Pick a source (live form, article, or CSS-painted scene) and a fragment shader (CRT, chromatic, halftone, ASCII, and more). The DOM lives under the shader — type, Tab, and hover all still work.
Elastic Bulge
Mouse-driven elastic displacement effect: a WebGL2 shader warps laid-out HTML content with a radial bulge and soft drop-shadow that follow the pointer.
Frosted Glass Backdrop
Draggable frosted glass panel with custom gaussian, directional, and tilt-shift blur effects composited between HTML rendering layers.
Hello World
The simplest HTML-in-Canvas demo — a styled div drawn into canvas with drawElementImage, showing the minimal boilerplate with annotated code.
Get Started
The HTML-in-Canvas API is available today in
Chrome Canary and
Brave Stable (Chromium 147+) behind the
canvas-draw-element flag. Enable it, open a demo,
and start experimenting.
Track the spec at github.com/WICG/html-in-canvas