Engine v2.18.0 has been released.
This release is available as an RC build in the Editor, please test your projects and report any issues. We’re planning to promote this version to be the default V2 version in the Editor on or after Wednesday 22 April 2026.
To stay updated on Engine development, hit Watch on the repo . Support us by hitting Star too!
main ← mv-html-in-canvas-v2
opened 09:51AM - 11 Mar 26 UTC
Adds support for the [HTML-in-Canvas](https://github.com/WICG/html-in-canvas) pr… oposal, allowing HTML elements to be used as live WebGL texture sources with full interactive hit testing.
**Changes:**
- Add `GraphicsDevice.supportsHtmlTextures` public API to detect HTML-in-Canvas support
- Add `_isHTMLElementInterface()` to distinguish generic HTML elements from image/canvas/video
- Support `texElementImage2D` in the WebGL texture upload path for HTML element sources
- Update `Texture.setSource()` to accept HTML elements and read dimensions via `getBoundingClientRect`
**Note:**
- The HTML-in-Canvas API is currently experimental and only available in [Chrome Canary](https://www.google.com/chrome/canary/) with the chrome://flags/#canvas-draw-element flag enabled. It has not shipped in any stable browser. The engine changes are backwards-compatible — when the API is unavailable, device.supportsHtmlTextures returns false and both examples gracefully fall back.
---
**API Usage — Simple (HTML as texture):**
```javascript
canvas.setAttribute('layoutsubtree', 'true');
// ... create device, app ...
if (device.supportsHtmlTextures) {
const htmlElement = document.createElement('div');
htmlElement.innerHTML = '<h1>Hello 3D</h1>';
canvas.appendChild(htmlElement);
const texture = new pc.Texture(device, { width: 512, height: 512 });
canvas.addEventListener('paint', () => texture.setSource(htmlElement), { once: true });
canvas.requestPaint();
canvas.addEventListener('paint', () => texture.upload());
}
```
**API Usage — Interactive (hit testing with getElementTransform):**
```javascript
// HtmlSync projects the 3D plane into screen space so the browser
// can hit-test clicks/hovers on the HTML element.
const sync = new HtmlSync(canvas, htmlElement, planeEntity, width, height);
// every frame:
sync.update(camera.camera);
// clicks and hovers work via standard DOM events
htmlElement.addEventListener('click', (e) => { /* handle click */ });
```
---
**Examples:**
### html-texture
<img width="1228" height="1230" alt="Screenshot 2026-03-11 at 09 52 38" src="https://github.com/user-attachments/assets/15703d53-4980-4f6d-8f2b-cb23ece363a2" />
### html-texture-configurator
<img width="1227" height="1232" alt="Screenshot 2026-03-11 at 09 52 24" src="https://github.com/user-attachments/assets/d4b33594-b0e5-421f-a0e5-1a669a4d508e" />
Ooooo, that will be fun for XR/VR projects
2 Likes
It should land in Chrome next month.
1 Like