HTML-in-Canvas API 彌補了 DOM 的互動式和無障礙世界,與 <canvas> 的高效能、像素級控制之間的差距。這項 API 可讓您直接將即時 DOM 子樹繪製到 2D、WebGL 或 WebGPU 畫布內容中,同時瀏覽器會保留互動性、無障礙樹狀結構和瀏覽器層級整合。
如要瞭解 HTML-in-Canvas 的優點、如何改善先前的解決方法,以及最適合的使用案例,請參閱「Chrome 157 中的 HTML-in-Canvas:2D、WebGL 和 WebGPU 中的互動式 DOM」。
使用 HTML-in-Canvas 實作 UI
如要將 HTML-in-Canvas 整合至應用程式,您可以:
- 使用瀏覽器 API 建立直接導入。
- 使用支援 HTML-in-Canvas 的框架。
您也可以使用程式設計代理協助。瞭解如何運用 Modern Web Guidance 提升程式設計代理的使用體驗。
直接導入
導入方式取決於您使用的情境。開始前,請先複習所有情境通用的技術概念,例如 drawable 內容和 paint 事件。
瞭解如何將元素圖片繪製到畫布中,並在下列情境中更新元素的幾何圖形:
程式庫和架構支援
多個熱門程式庫已新增實驗性的 HTML-in-Canvas 支援,適用於 WebGL 和 WebGPU 紋理,以及 2D 畫布效果。請參閱各程式庫的說明文件,瞭解目前的支援狀態和實作詳情。
Three.js
手動更新矩陣可能很繁瑣,因此架構會新增內建支援。舉例來說,Three.js 使用 THREE.HTMLTexture 提供實驗性支援:
const material = new THREE.MeshBasicMaterial();
material.map = new THREE.HTMLTexture(uiElement); // Pass the DOM element
const geometry = new THREE.BoxGeometry(1, 1, 1);
const mesh = new THREE.Mesh(geometry, material);
scene.add(mesh);
PlayCanvas
PlayCanvas 也支援使用其紋理 API 在 Canvas 中嵌入 HTML:
// Wait for the 'paint' event to set the source
canvas.addEventListener('paint', () => {
htmlTexture.setSource(htmlElement);
}, { once: true });
canvas.requestPaint();
// Keep up to date
canvas.addEventListener('paint', onPaintUpload);
const material = new pc.StandardMaterial();
material.diffuseMap = htmlTexture;
material.update();
Babylon.js
Babylon.js 透過 BABYLON.HtmlTexture 類別支援 HTML-in-Canvas:
// 2. Wrap the DOM element in an HtmlTexture
const htmlTexture = new BABYLON.HtmlTexture("htmlTexture", uiElement, scene);
// 3. Assign the texture to a material
const material = new BABYLON.StandardMaterial("hudMaterial", scene);
material.diffuseTexture = htmlTexture;
// 4. Apply material to 3D mesh
const plane = BABYLON.MeshBuilder.CreatePlane("hudPlane", { width: 1.6, height: 0.9 }, scene);
plane.material = material;
// 5. Start Render Loop
engine.runRenderLoop(() => {
scene.render();
});
PixiJS
PixiJS 在 v8.19.0 中推出 HTML-in-Canvas 支援:
import { HTMLSource } from 'pixi.js/html-source';
// ... Initialize the app
// Append the HTML element as a direct child of the Pixi canvas
app.canvas.appendChild(htmlElement);
// Create the HTML-in-Canvas source and wrap it in a Sprite
const sprite = Sprite.from(new HTMLSource({ resource: form, autoUpdate: true }));
app.stage.addChild(sprite);
app.ticker.add(() => {
// Make sure to align the HTML element by updating its transform
const syncT = app.canvas.getElementTransform(htmlElement, finalTransform);
if (syncT) {
htmlElement.style.transform = syncT.toString();
}
});
CanvasUI
CanvasUI 是開放原始碼程式庫,內含使用 HTML-in-Canvas 的 UI 元件。
使用程式設計代理在 Canvas 中實作 HTML
如果您使用程式碼代理,請安裝 Modern Web Guidance,其中包含 HTML-in-Canvas 的最新導入操作說明。除了 HTML-in-Canvas,Modern Web Guidance 也涵蓋其他新式瀏覽器 API 和最佳做法。
後續步驟
- 瞭解 HTML-in-Canvas 的核心技術概念。
- 瞭解如何在 2D 情境中算繪 HTML。
- 瞭解如何在 WebGL 畫布中算繪 HTML。
- 瞭解如何在 WebGPU 畫布中算繪 HTML。
- 瞭解備用策略。
- 歡迎在 GitHub 回報問題,分享您的意見。
- 請參閱社群提供的 HTML-in-Canvas 示範集合。