ELK Layout Algorithm in Mermaid: Configuring Node Placement and Cycle-Breaking Strategies
The ELK layout algorithm in Mermaid utilizes the Eclipse Layout Kernel (elkjs) to render complex hierarchical diagrams, allowing fine-grained control over node positioning and cycle resolution through the nodePlacementStrategy and cycleBreakingStrategy configuration options.
The mermaid-js/mermaid repository integrates the ELK (Eclipse Layout Kernel) engine via the @mermaid-js/layout-elk package, providing advanced layout capabilities for flowcharts, class diagrams, and ER diagrams. This integration translates Mermaid graph definitions into optimized visual structures by mapping configuration options directly to the underlying elkjs library. Mastering the nodePlacementStrategy and cycleBreakingStrategy settings enables you to optimize layout performance, minimize edge crossings, and preserve logical node ordering in cyclic graphs.
ELK Architecture in Mermaid
The ELK renderer is implemented in the standalone package @mermaid-js/layout-elk, which wraps the JavaScript port of the Eclipse Layout Kernel. In packages/mermaid-layout-elk/src/render.ts (lines 171–732), the rendering pipeline constructs an ELK graph object and populates it with layout options derived from the Mermaid configuration.
The core configuration mapping occurs where the renderer builds the layoutOptions object:
elkGraph = {
id: 'root',
layoutOptions: {
'elk.hierarchyHandling': 'INCLUDE_CHILDREN',
'elk.algorithm': algorithm,
'nodePlacement.strategy': data4Layout.config.elk?.nodePlacementStrategy,
'elk.layered.cycleBreaking.strategy': data4Layout.config.elk?.cycleBreakingStrategy,
},
children: [],
edges: [],
};
This code demonstrates how Mermaid passes your configuration values directly to the ELK engine's layered graph layout algorithm.
Node Placement Strategy Configuration
The nodePlacementStrategy option controls how the ELK algorithm positions nodes within the computed layout layers. Defined in packages/mermaid/src/config.type.ts (lines 99–101), this setting accepts four distinct strategies:
-
BRANDES_KOEPF— The default strategy defined inpackages/mermaid/src/defaultConfig.ts(lines 23–28). This advanced heuristic minimizes total edge length while respecting node ordering constraints, making it ideal for large, complex diagrams. -
SIMPLE— Places nodes on a coarse grid with minimal computational overhead. This strategy prioritizes layout speed over edge optimization, suitable for small diagrams or rapid prototyping scenarios. -
NETWORK_SIMPLEX— Employs a network simplex algorithm that respects topological relationships, producing balanced node distributions with improved edge routing for medium-sized graphs. -
LINEAR_SEGMENTS— Forces nodes onto linear segments within their layers, creating clean hierarchical visual flows particularly effective for flowcharts with strict level separations.
Cycle-Breaking Strategy Configuration
When diagrams contain directed cycles, ELK must temporarily reverse specific edges to create a valid hierarchical layout. The cycleBreakingStrategy determines which edges are selected for reversal. The available options, defined in packages/mermaid/src/config.type.ts (lines 103–111), include:
-
GREEDY— A fast heuristic that makes locally optimal decisions at each step. While computationally efficient, it may produce sub-optimal edge reversal sets in complex cyclic structures. -
GREEDY_MODEL_ORDER— Combines greedy selection with respect for the source model order, serving as the default in recent Mermaid releases when preserving definition sequence is important. -
DEPTH_FIRST— Uses depth-first search traversal to identify cycles, performing well when graphs contain shallow feedback loops. -
MODEL_ORDER— Strictly respects the order of node definitions as they appear in the source model, ensuring that the visual layout reflects the logical sequence of declarations. -
INTERACTIVE— Supports user interaction for cycle resolution, though this is rarely used in programmatic rendering contexts.
In packages/mermaid-layout-elk/src/render.ts (line 729), the renderer passes this configuration value directly to the elk.layered.cycleBreaking.strategy property.
Implementation Methods
You can configure these strategies through three primary methods: global initialization, per-diagram directives, or YAML front matter.
Global JavaScript Configuration
Set default ELK options for all diagrams on a page by initializing Mermaid with the elk configuration object:
import mermaid from 'mermaid';
import elkLayouts from '@mermaid-js/layout-elk';
mermaid.registerLayoutLoaders(elkLayouts);
mermaid.initialize({
startOnLoad: true,
defaultRenderer: 'elk',
elk: {
nodePlacementStrategy: 'LINEAR_SEGMENTS',
cycleBreakingStrategy: 'GREEDY_MODEL_ORDER'
}
});
The defaultRenderer: 'elk' directive activates the ELK layout engine, while the elk object maps directly to the options consumed in the render pipeline.
Diagram-Level Directives
Override global settings for individual diagrams using the init directive within your Mermaid code block:
%%{init: {
"defaultRenderer": "elk",
"elk": {
"nodePlacementStrategy": "SIMPLE",
"cycleBreakingStrategy": "MODEL_ORDER"
}
}}%%
flowchart TD
A --> B
B --> C
C --> A
This approach allows specific diagrams to use alternative strategies without affecting the global configuration.
YAML Front Matter
For static site generators and documentation platforms, specify ELK options in YAML front matter:
---
mermaid:
defaultRenderer: elk
elk:
nodePlacementStrategy: BRANDES_KOEPF
cycleBreakingStrategy: GREEDY
---
Mermaid merges these values into the runtime configuration, applying them to all diagrams rendered on the page.
Optimization Guidelines
Selecting appropriate strategies depends on your diagram's structural characteristics and performance requirements.
Node placement directly impacts visual compactness and readability. Complex diagrams with numerous interconnections benefit from BRANDES_KOEPF, while simpler graphs may render faster with SIMPLE or LINEAR_SEGMENTS without significant quality loss.
Cycle-breaking becomes critical when visualizing feedback loops or recursive relationships. If maintaining the source code's declaration order is essential—for instance, when the sequence reflects logical execution flow—choose MODEL_ORDER or GREEDY_MODEL_ORDER. For maximum layout speed in performance-critical applications, GREEDY provides the fastest computation at the potential cost of sub-optimal edge routing.
Summary
- The ELK layout algorithm in Mermaid is implemented in
packages/mermaid-layout-elk/src/render.tsand wraps theelkjslibrary to provide advanced graph layouts. - Node placement strategies (
SIMPLE,NETWORK_SIMPLEX,LINEAR_SEGMENTS,BRANDES_KOEPF) control how nodes are arranged within layers, withBRANDES_KOEPFserving as the default for complex diagrams. - Cycle-breaking strategies (
GREEDY,DEPTH_FIRST,MODEL_ORDER,GREEDY_MODEL_ORDER,INTERACTIVE) determine how directed cycles are resolved to create valid hierarchies. - Configuration occurs through
mermaid.initialize(), diagram-level%%{init}%%directives, or YAML front matter, with options defined inpackages/mermaid/src/config.type.ts. - The default configuration in
packages/mermaid/src/defaultConfig.tssetsnodePlacementStrategytoBRANDES_KOEPF, while cycle-breaking defaults toGREEDYorGREEDY_MODEL_ORDERdepending on the Mermaid version.
Frequently Asked Questions
What is the default node placement strategy in Mermaid's ELK layout?
The default strategy is BRANDES_KOEPF, as specified in packages/mermaid/src/defaultConfig.ts (lines 23–28). This algorithm uses an advanced heuristic to minimize total edge length while maintaining node ordering constraints, making it suitable for large and complex diagrams where visual clarity is paramount.
How does the cycle-breaking strategy affect diagram layout?
The cycle-breaking strategy determines which edges are temporarily reversed when ELK encounters directed cycles in your graph. This reversal creates a temporary acyclic structure required for hierarchical layout. The MODEL_ORDER strategy preserves your source code's declaration sequence, while GREEDY prioritizes computational speed. Your choice affects both the visual flow and the preservation of semantic relationships in cyclic graphs.
Can I use ELK layout for all Mermaid diagram types?
No, the ELK layout engine supports specific graph-based diagram types including flowcharts, class diagrams, and entity-relationship (ER) diagrams. You must explicitly enable the ELK renderer by setting defaultRenderer: 'elk' in your configuration or using the @mermaid-js/layout-elk package with mermaid.registerLayoutLoaders().
When should I use the SIMPLE node placement strategy versus BRANDES_KOEPF?
Use SIMPLE for small diagrams or development scenarios where layout computation speed matters more than edge optimization. It places nodes on a coarse grid with minimal overhead. Use BRANDES_KOEPF for production diagrams with complex interconnections, as it implements sophisticated heuristics to minimize edge crossings and total edge length, resulting in more readable layouts for large graphs.
Have a question about this repo?
These articles cover the highlights, but your codebase questions are specific. Give your agent direct access to the source. Share this with your agent to get started:
curl -s "https://instagit.com/install.md" Maintain an open-source project? Get it listed too →