Specifying east-west neighbors
You can specify that two unrelated nodes must be direct
neighbors in a direction perpendicular to the flow direction. In the
level and radial layout modes, the nodes are placed in the same level
next to each other. In the free layout and tip-over modes, the nodes
are placed aligned at the north border. Such nodes are called east-west neighbors because one node
is placed as the direct neighbor on the east side of the other node.
The other node becomes the direct neighbor on the west side of the
first node. (See also Using compass directions for positional layout parameters
(TL)).
Technically, the nodes are treated as parent and child,
even if there is no link between them. Therefore, one of the two nodes
can have a real parent, but the other node must not because its virtual
parent is its east-west neighbor.
The east-west neighbor feature can be used, for example,
for annotating nodes in a typed syntax tree occurring in compiler
construction. Annotated syntax tree of statement a[25] = b[24] +
0.5; shows an
example of such a tree.

Annotated syntax tree of statement a[25] = b[24] +
0.5;
To specify that two nodes are east-west neighbors, use
the method:
treeLayout.setEastWestNeighboring(eastNode, westNode);
You can also use the following function, which is identical
except for the reversed parameter order:
treeLayout.setWestEastNeighboring(westNode, eastNode);
If the flow direction is to the bottom, the latter method
might be easier to remember because, in this case, west is to the
left of east in the layout, which is similar to the text flow of the
parameters.
To obtain the node that is the east or west neighbor
of a node, use the calls:
var eastNode = treeLayout.getEastNeighbor(westNode);
var westNode = treeLayout.getWestNeighbor(eastNode);
Each node can have at most one east neighbor and one
west neighbor because they are direct neighbors.
If more than one direct neighbor is specified, it is partially ignored.
Cyclic specifications can cause conflict as well. For instance, if
node B is the east neighbor of node A and node C is the east neighbor
of B, then node A cannot be the east neighbor of C. (Strictly speaking,
such cycles could be technically possible in some situations in the
radial layout mode, but nonetheless they are not allowed in any layout
mode.)
If B is the east neighbor of A, then A is automatically
the west neighbor of B. The east neighbor of A can itself have another
east neighbor. You can thus create chains of east-west neighbors,
which is a common way to visualize lists of trees. Two examples are
shown in figure Chains of east-west neighbors to visualize lists of
trees.

Chains of east-west neighbors to visualize lists of
trees
Retrieving link categories
The Tree Layout algorithm works on a spanning tree, as
mentioned in a The TL algorithm. If the graph
to be laid out is not a pure tree, the algorithm ignores some links.
To treat such links in a special way, you can obtain a list of nontree
links.
Because there are parents and child nodes in the spanning
tree, the following link categories must be distinguished:
- A forward tree link is a link from a parent to its child.
- A backward tree link is a link from a child to its parent. If the link is drawn as a directed arrow, the arrow points in the opposite direction to the flow direction.
- A nontree link is a link between two unrelated nodes; neither one is a child of the other.

Link categories
The layout algorithm uses these link categories internally
but does not store them permanently to save time and ensure memory
efficiency. If you want to treat some link categories in a special
way (for example, to call the Link Layout on the nontree links), you
must specify before the layout that
you want to access the link categories after
the layout.
To do this, use the method setCategorizingLinks in the following way:
treeLayout.setCategorizingLinks(true); graph.setNodeLayout(treeLayout); graph.performGraphLayout(); var link; var forwardLinks = treeLayout.getCalcForwardTreeLinks(); console.log("forward links:"); while(forwardLinks.hasNext()){ link = forwardLinks.next(); console.log(link.getStartNode().getLabel() + " -> " + link.getEndNode().getLabel()); } var backwardLinks = treeLayout.getCalcBackwardTreeLinks(); console.log("backward links:"); while(backwardLinks.hasNext()){ link = backwardLinks.next(); console.log(link.getStartNode().getLabel() + " -> " + link.getEndNode().getLabel()); } var nonTreeLinks = treeLayout.getCalcNonTreeLinks(); console.log("non-tree links:"); while(nonTreeLinks.hasNext()){ link = nonTreeLinks.next(); console.log(link.getStartNode().getLabel() + " -> " + link.getEndNode().getLabel()); }
After you have run the layout, you can access the link
categories.
The link category data gets filled each time the layout
is called, unless you call the method setCategorizingLinks(false).
Sequences of layouts with incremental changes
You can work with trees that have become out-of-date,
for example, the trees that need to be extended with more child nodes.
If you perform a layout after an extension, you probably want to identify
the parts that had already been laid out in the original graph. The
Tree Layout algorithm supports these incremental changes in incremental
mode because it takes the previous positions of the nodes into account.
It preserves the relative order of the child nodes in the subsequent
layout.
In nonincremental mode, the Tree Layout algorithm calculates
the order of the child nodes from the node order given by the attached
graph model (or graph).
In this case, the layout is independent from the positions
of the nodes before the layout. It does not preserve the relative
order of the child nodes in subsequent layouts.
Incremental mode is enabled by default.
To disable incremental mode:
Call:
treeLayout.setIncrementalMode(false);
Interactive editing
The fact that the relative order of the layout is preserved
is useful during interactive editing. It allows you to correct the
layout easily. For instance, if the first layout places a node A left
to its sibling node B but you need to reverse the order, you can simply
move node A to the right of node B and start a new layout to clean
up the drawing. In the second layout, A remains to the right of B,
and the subtree of A “follows” node A.

Interactive editing to achieve a specific order of
child nodes
Specifying the order of child nodes
Some applications require a specific relative order of
the child nodes in the tree. This means that, for instance, when the
flow direction is to the bottom, which child must be placed to the
left of another child.
It can be achieved in non-incremental mode by specifying
a node comparator as follows:
treeLayout.setNodeComparator(function(node1, node2) { // for example: sort nodes by increasing width return node1.getBounds().width - node2.getBounds().width; });
The comparator specifies the order as defined in the
following table. For regular alignment, it results in increasing coordinates
for the children. For tip-over alignment, it results in increasing
distance from the parent. For balloon and radial modes, it results
in clockwise orderings.
Layout Mode | Alignment | Flow Direction | Order |
---|---|---|---|
Free, Level, Tip-over | no tip-over | Bottom | left to right |
Top | left to right | ||
Left | top to bottom | ||
Right | top to bottom | ||
Free, Level, Tip-over | tip-over | Bottom | top to bottom |
Top | bottom to top | ||
Left | right to left | ||
Right | left to right | ||
Radial, Balloon | any | any | clockwise |