HTML Rendering
yFiles for HTML primarily uses SVG for rendering. SVG offers several advantages, including styling with CSS, sharp text rendering, and support for animations and hover effects. However, visualizations that involve complex visual layouts, numerous text elements with responsive wrapping, or interactive elements such as input or button elements, can be challenging to implement using SVG. These types of visualizations are often easier to create using HTML markup.
Using HTML markup also simplifies the styling of graph items to align with existing design frameworks, which typically operate on HTML.
Using HtmlVisual
The HtmlVisual works the same way as the SvgVisual and can be used in a similar fashion. When implementing the IVisualCreator interface, you can return an HtmlVisual that wraps HTML markup, just as an SvgVisual would wrap SVG content.
class SimpleHtmlNodeStyle extends NodeStyleBase {
protected createVisual(
context: IRenderContext,
node: INode
): Visual | null {
const div = document.createElement('div')
const { x, y, width, height } = node.layout
// size and positioning
const style = div.style
style.position = 'absolute'
style.left = `${x}px`
style.top = `${y}px`
style.width = `${width}px`
style.height = `${height}px`
// a sample text
div.innerHTML = `
<div style='box-sizing: border-box; height: 100%; overflow: hidden; border: 1px solid red;'>
<span>Hello World</span>
</div>
`
return new HtmlVisual(div)
}
}
There are convenience methods to properly arrange HTML elements according to a node’s layout. yFiles for HTML offers static
utility methods on HtmlVisual to achieve this. Using these utilities, a node style can be efficiently implemented with
a well-structured updateVisual
method:
class EfficientHtmlNodeStyle extends NodeStyleBase {
protected createVisual(
context: IRenderContext,
node: INode
): HtmlVisual {
const div = document.createElement('div')
div.innerHTML = `
<div style='box-sizing: border-box; width: 100%; height: 100%; overflow: hidden; border: 1px solid red;'>
<span>Hello World</span>
</div>
`
const visual = HtmlVisual.from(div)
HtmlVisual.setLayout(div, node.layout)
return visual
}
protected updateVisual(
context: IRenderContext,
oldVisual: HtmlVisual,
node: INode
): HtmlVisual {
HtmlVisual.setLayout(oldVisual.element, node.layout)
return oldVisual
}
}
Note
|
Consider setting box-sizing to border-box to ensure the visualization is contained within the node’s layout.
|
When should I use HTML rendering?
HTML rendering is well-suited for visualizations that consist mostly of text, or for integration with HTML-based front-end frameworks. For example, wrapping text or positioning elements based on their intrinsic sizes using CSS-based layouts is much easier with HTML. SVG does not offer input elements, scrollbars, or tables, all of which work natively in HTML.
Additionally, HTML often performs better than SVG text rendering for visualizations with large amounts of text.
When should I avoid HTML rendering?
While HTML works very well in browsers, yFiles for HTML primarily exports SVG images. SVG supports embedding non-SVG content
with the foreignObject
element, which is how HTML elements are exported as part of the SVG. The foreignObject
element, however, is
only supported by most browsers. If you need exported SVG images that work well in non-browser image editors, you can
either enable the rasterizeHtmlVisuals property, which will convert the HTML to bitmaps, or
avoid HTML-based visuals entirely.
While HTML-based visuals are well suited for the use cases described above, visualizations that are better implemented using actual image formats like SVG exist. This includes complex geometric content, and in general visualizations that are more image-like.
Browsers also aggressively optimize HTML and tend to restrict the size and positioning of HTML elements to integral coordinate values. This means that visualizations that should have fractional positions or sizes will be rounded to integral ones. This can sometimes be apparent when moving or resizing HTML nodes in a zoomed-in view.
Note
|
We recommend using SVG-based implementations whenever feasible. |