X6 进阶指南:使用 Shape.HTML 渲染与更新 HTML 节点(原理与实战) X6 进阶指南使用 Shape.HTML 渲染与更新 HTML 节点原理与实战【免费下载链接】X6 JavaScript diagramming library that uses SVG and HTML for rendering.项目地址: https://gitcode.com/GitHub_Trending/x6/X6本指南基于 X6 内置的Shape.HTML能力系统讲解如何用 HTML 渲染节点内容、如何通过effect机制响应节点属性变化并自动更新节点 DOM。读完本文你将掌握 HTML 节点的注册、三种内容形态、默认 DOM 结构与更新触发原理并能复现悬浮动画与定时刷新两类实战案例。为什么需要 HTML 节点X6 是一个使用 SVG 与 HTML 进行渲染的 JavaScript 图编辑库。常规节点基于 SVG 绘制但对交互复杂、样式多变的内容如富文本、图表、输入框、悬浮动画而言SVG 实现成本很高。X6 在Shape命名空间下内置了HTML节点类型把节点内容直接交给浏览器 DOM 渲染从而获得 HTML/CSS 的全部表达能力。从源码看HTML节点本身是Node的子类src/shape/html.ts并在Node.registry中以html为键注册真正负责渲染 DOM 的视图html-view也被注册到NodeView.registrysrc/shape/html.ts。也就是说使用HTML节点不需要额外引入插件或依赖开箱即用。快速开始注册并渲染 HTML 节点注册一个 HTML 节点只需要调用Shape.HTML.register并为其提供唯一的shape名称和一个返回 DOM 的html方法import { Shape } from antv/x6 Shape.HTML.register({ shape: custom-html, width: 160, height: 80, html() { const div document.createElement(div) div.className custom-html return div }, }) graph.addNode({ shape: custom-html, x: 60, y: 100, })要点说明shape必填节点类型标识addNode时通过shape引用它。源码中若未指定shape会直接抛出HTML.register should specify shape in config.错误src/shape/html.ts。width/height节点默认尺寸addNode时可按节点实例覆盖。html节点内容的生产函数返回一个HTMLElement。注册本质上是在调用Graph.registerNode(shape, { inherit: html, ...others }, true)src/shape/html.ts测试用例 html.spec.ts 对这条注册链路做了完整断言。html 字段的三种形态html字段在源码中被定义为HTMLComponent联合类型src/shape/html.tstype HTMLComponent | string // HTML 字符串 | HTMLElement // 现成的 DOM 元素 | ((cell: Cell) HTMLElement | string) // 函数接收节点 cell视图在渲染时按类型分支处理src/shape/html.ts字符串直接写入容器的innerHTMLHTMLElement通过Dom.append追加进容器函数先以当前节点 cell 为参数调用再按返回值字符串或元素处理。因此你可以这样注册一个最简节点Shape.HTML.register({ shape: static-html, html: div stylepadding:8pxHello X6/div, })对应的字符串、元素、函数三种形态以及空字符串、函数返回 null、缺少容器等边界情况在测试 html.spec.ts 中都有覆盖验证。HTML 节点的默认 DOM 结构HTML类通过HTML.config声明了默认 markup 与 attrssrc/shape/html.ts节点内部结构如下rectselector:body铺满节点的透明底板fill: none、stroke: none、refWidth/refHeight: 100%foreignObjectselector:fo承载 HTML 内容的外来对象容器同样refWidth/refHeight: 100%textselector:label节点标签文本层。foreignObject的完整子结构由Markup.getForeignObjectMarkup()生成src/view/markup.tsforeignObject(fo) → body(foBodyxhtml 命名空间) → div(foContent)其中foContent才是html方法返回内容真正挂载的容器。视图渲染时会清空foContent再写入新内容Dom.empty(container)避免旧内容残留。理解了这套结构你就知道HTML 节点仍是可选中、可拖动、可连线的正常节点只是节点视觉主体由 DOM 呈现。更新节点内容effect 机制注册节点时提供effect字段——它是当前节点的prop数组。当其中任一 prop 变化时html方法会重新执行并返回新 DOM从而更新节点内容Shape.HTML.register({ shape: custom-html, width: 160, height: 80, effect: [data], html(cell) { const { color } cell.getData() const div document.createElement(div) div.className custom-html div.style.background color return div }, })这里的html(cell)可以读取节点数据如cell.getData()来动态生成内容。底层原理HTML 节点的视图在初始化时监听节点的change:*事件src/shape/html.ts。任意 prop 变化时处理器会取该节点注册时保存的effect列表若effect存在且包含当前变化的 key则调用renderHTMLComponent()重渲染若effect存在但不包含该 key则不重渲染若未设置effect则任何 prop 变化都会触发重渲染。测试 html.spec.ts 精确验证了这一行为effect: [size]时resize()会触发重渲染、setPosition()不会不设effect时setPosition()也会触发重渲染。因此当节点内容只依赖data时把effect收敛为[data]可以避免因位置、尺寸等变化引发的无意义 DOM 重建是控制重渲染开销的实用手段。实战一CSS 悬浮动画完整示例见 site/src/tutorial/intermediate/html/basic/index.tsx 与配套样式 index.less。示例注册了custom-html节点并在图中添加一个实例配合graph.centerContent()居中显示。节点内容只是一个div其翻转动画完全用 CSS 实现.custom-html::before默认rotateX(180deg)隐藏:hover::before时rotateX(0)展开并带transition: 0.7s ease-in-out transform。这类效果若用 SVG 实现需要复杂的路径与滤镜而 HTML 节点只需几行 CSS——这正是 HTML 节点的典型优势场景。实战二定时刷新节点内容完整示例见 site/src/tutorial/intermediate/html/update/index.tsx。示例注册custom-update-htmlhtml(cell)从cell.getData().color读取颜色并写入背景样式添加节点时通过data: { color: #333232 }初始化数据随后用setInterval每 2 秒调用node.setData({ color: Color.randomHex() })Color同样从antv/x6导出。由于注册时声明了effect: [data]每次setData改变dataprop 都会触发html(cell)重新执行节点背景色随之更新。这条「数据驱动 → effect 匹配 → DOM 重建」的链路与上一节的原理部分完全对应。常见边界与注意事项结合源码与测试使用 HTML 节点时还需留意内容为空html返回空字符串或函数返回 null 时容器内容保持为空不会报错html.spec.ts容器缺失视图未就绪时foContent可能不存在渲染逻辑会静默跳过html.spec.ts重渲染前清空每次渲染前容器都会被Dom.empty因此不要在html返回的元素上挂接需要持久化的状态跨渲染的状态应放在节点data中事件监听释放视图销毁时会解除change:*监听src/shape/html.ts避免内存泄漏。延伸阅读HTML 节点中文文档核心实现src/shape/html.ts默认 markup 生成src/view/markup.ts行为验证tests/shape/html.spec.ts若需更进一步可结合 X6 教程中关于节点与节点样式的内容将 HTML 节点与普通 SVG 节点在同一图中混合使用。【免费下载链接】X6 JavaScript diagramming library that uses SVG and HTML for rendering.项目地址: https://gitcode.com/GitHub_Trending/x6/X6创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考