skip to main content
Diagrammer > Programmer's documentation > Using graph layout algorithms > Nested layouts > Multiple layout
 
Multiple layout
Describes Multiple Layout.
*General information
*Describes the multiple layout facility.
*Features
*Lists the features of multiple layout and shows the class diagram.
*Generic features and parameters
*Describes the generic features and parameters of multiple layout.
*Specific parameters
*Describes the specific parameters of multiple layout.
*Accessing sublayouts
*Describes how to access sublayouts of a multiple layout.
*For experts: attaching graph and labeling models
*Describes how to attach graph and labeling models.
*Combining multiple and recursive layout
*Describes how to combine a multiple layout with a recursive layout.
*For experts: the reference labeling model
*Describes the reference labeling model for a recursive multiple layout.
General information
What is multiple layout?
The Multiple Layout class, class IlvMultipleLayout from the package ilog.views.graphlayout.multiple, is useful mainly when applying layout in Java™ code. The class is also internally used by the graph layout renderer of a diagram component, but in the diagram component, the rendering mechanism is transparent so that you seldom need to deal with the class IlvMultipleLayout.
Important The Multiple Layout can be used only in Java code. No CSS syntax is available for this layout.
The Multiple Layout class is not a layout algorithm but rather a facility to compose multiple layout algorithms and treat them as one algorithm object.
This is necessary in particular when dealing with the recursive layout of nested submanagers, because performing the layouts recursively one after the other has a different effect than combining the layouts into one algorithm object and applying this object all at once.
See Recursive layout and Layout of nested graphs in code. Multiple Layout should also be used to combine a normal layout with a Link Layout that routes intergraph links. This is shown in the following sample.
Java code sample
You can, for instance, combine a Tree Layout, a Link Layout, and an Annealing Label Layout into one object of type IlvGraphLayout in the following way:
 
 ...
import ilog.views.*;
import ilog.views.graphlayout.*;
import ilog.views.graphlayout.multiple.*;
import ilog.views.graphlayout.tree.*;
import ilog.views.graphlayout.link.*;
import ilog.views.graphlayout.labellayout.annealing.*;
 
IlvTreeLayout treeLayout = new IlvTreeLayout();
IlvLinkLayout linkLayout = new IlvLinkLayout();
IlvAnnealingLabelLayout labelLayout = new IlvAnnealingLabelLayout();
IlvMultipleLayout multipleLayout =
        new IlvMultipleLayout(treeLayout, linkLayout, labelLayout);
 
IlvGrapher grapher = ...
layout.attach(grapher);
 
... /* Fill in code to set the layout parameters of treeLayout,
     * linkLayout and labelLayout.
     */
linkLayout.setInterGraphLinksMode(true);
...
By constructing a Multiple Layout instance in this way, the Tree Layout, Link Layout, and Label Layout become sublayouts of the Multiple Layout instance. Attaching the Multiple Layout will automatically attach its sublayouts.
The Multiple Layout has two slots for graph layouts and one slot for the label layout. Not all slots need to be used. You can pass null as the sublayout for unused slots. If you need more slots, you can compose a Multiple Layout that contains another Multiple Layout as a sublayout.
To perform the composed layout you use one of:
*Simple layout
*Recursive layout
Simple layout
You can perform the composed layout on a flat grapher (one which contains no submanagers) in the following way:
 
try {
        IlvMultipleLayoutReport layoutReport =
              (IlvMultipleLayoutReport)multipleLayout.performLayout();
 
        int code = layoutReport.getCode();
 
        System.out.println("Layout completed (" +
          layoutReport.codeToString(code) + ")");
}
catch (IlvGraphLayoutException e) {
        System.err.println(e.getMessage());
}
The statement with multipleLayout.performLayout() in this case has the same effect as the following sequence of statements:
 
treeLayout.performLayout();
linkLayout.performLayout();
 
labelLayout.performLayout();
Recursive layout
If you perform the Multiple Layout on a grapher that contains submanagers, there is a difference in the order of the layout (see Order of layouts in recursive layouts. You apply a recursive layout on the grapher and its submanagers in the following way:
 
IlvRecursiveLayout recursiveLayout = new IlvRecursiveLayout(multipleLayout);
try {
        IlvGraphLayoutReport layoutReport = recursiveLayout.performLayout();
        ...
}
catch (IlvGraphLayoutException e) {
        System.err.println(e.getMessage());
}
or alternatively, in the following way (both ways are equivalent):
 
try {
        int layoutCode =
                (IlvMultipleLayoutReport)multipleLayout.performLayout(
                                                        true, true, true);
        ...
}
catch (IlvGraphLayoutException e) {
        System.err.println(e.getMessage());
}
Assume the attached grapher A contains a subgrapher B.
The combined Multiple Layout applies its sublayouts in reverse order, as follows:
1. Tree Layout on B
2. Link Layout on B
3. Label Layout on B
4. Tree Layout on A
5. Link Layout on A
6. Label Layout on A
This means that all layouts of subgrapher B have finished before the layout of grapher A starts. It is the correct order for a recursive layout.
If you do not combine the three component layouts into a Multiple Layout, you can only apply them sequentially:
 
treeLayout.performLayout(true, true, true);
linkLayout.performLayout(true, true, true);
labelLayout.performLayout(true, true, true);
The effect of these statements is slightly different than the effect of the Multiple Layout. The layouts are now applied in the following order:
1. Tree Layout on B
2. Tree Layout on A
3. Link Layout on B
4. Link Layout on A
5. Label Layout on B
6. Label Layout on A
This order is not usually suitable for the layout of nested graphers because the Tree Layout of grapher A is started too early. The Label Layout on grapher B in Step 5 may change the position of grapher B within grapher A, invalidating the result of the Tree Layout in Step 2. Hence, it is recommended that you combine multiple layout algorithms into one Multiple Layout object and apply this object as a whole to a nested grapher.
Features
By using this layout, you can:
*Compose two graph layout algorithms and one label layout algorithm into one layout object.
*Achieve the correct layout order when dealing with nested graphers.
Layout features, speed, and quality depend on the features, speed, and quality of the sublayouts.
The class IlvMultipleLayout can contain two sublayouts and one label layout
Generic features and parameters
Depending on the support of its sublayouts, Multiple Layout can support the following generic parameters and features defined in the IlvGraphLayout class.
See Generic parameters and features.
*Allowed time
*Layout of connected components
*Percentage completion calculation
*Stop immediately
Extra feature for JViews Diagrammer:
*Save parameters to named properties
The following paragraphs describe the particular way in which these parameters are used by this subclass.
Allowed time
A Multiple Layout instance supports this feature if all of its sublayouts support the feature. If the allowed time setting has elapsed, the Multiple Layout stops; that means it stops the currently running sublayout and skips the subsequent sublayouts that have not yet been started. If the layout stops early because the allowed time has elapsed, the result code in the layout report is:
IlvGraphLayoutReport.STOPPED_AND_INVALID
Layout of connected components
The Multiple Layout instance can use the generic mechanism to lay out connected components if the sublayouts of type IlvGraphLayout support this feature. The sublayout of type IlvLabelLayout does not need special handling of connected components.
For more information about this mechanism, see Layout of connected components.
Percentage completion calculation
The Multiple Layout calculates the percentage of completion. This value can be obtained from the layout report during the run of the layout. The value is, however, a very rough estimation. If the sublayouts do not support the calculation of the percentage completion, the Multiple Layout can report the percentage based only on the information that the sublayout has already finished. For example, if there are three sublayouts, the mechanism reports 33% after the first sublayout has finished, 66%after the second sublayout has finished, and 100% after all three sublayouts have finished. If the sublayouts support the calculation of the percentage completion, the Multiple Layout calculates a more detailed percentage. For a detailed description of this feature, see Percentage of completion calculation and Graph layout event listeners.
Save parameters to named properties
The Multiple Layout instance can save its layout parameters to named properties if all its sublayouts support this feature. This can be used to save layout parameters to .ivl files. (For a detailed description of this feature, see Save parameters to named propertiesand Saving layout parameters and preferred layouts.)
Stop immediately
The Multiple Layout instance supports this feature if all its sublayouts support this feature.
It stops the currently running sublayout after cleanup if the method stopImmediately is called and skips the subsequent sublayouts that have not yet been started. For a description of this method in the IlvGraphLayout class, see Stop immediately. If the layout stops before completion, the result code in the layout report is IlvGraphLayoutReport.STOPPED_AND_INVALID.
Specific parameters
Multiple Layout does not provide any specific layout parameters. However, you can set the generic and specific layout parameters of the sublayouts individually. For example, you can construct a Multiple Layout instance from two graph layouts. Even though the Multiple Layout does not support setting fixed nodes on itself, you can fix nodes for the sublayouts individually by applying setFixed to the sublayout instances if the sublayouts support this feature.
 
IlvMultipleLayout multipleLayout =
        new IlvMultipleLayout(layout1, layout2, null);
multipleLayout.attach(grapher);
if (layout1.supportsPreserveFixedNodes()) {
        layout1.setFixed(node1, true);
        ...
}
if (layout2.supportsPreserveFixedNodes()) {
        layout2.setFixed(node2, true);
        ...
}
try {
        // perform a multiple layout: node1 is fixed while layout1 runs
        // and node2 is fixed while layout2 runs
        IlvMultipleLayoutReport layoutReport =
                (IlvMultipleLayoutReport)multipleLayout.performLayout(
                                                        true, true, true);
        ...
}
catch (IlvGraphLayoutException e) {
        System.err.println(e.getMessage());
}
Accessing sublayouts
You can obtain the sublayouts of a Multiple Layout instance by the following methods:
*getFirstGraphLayout
which returns the graph layout that is applied first.
*getSecondGraphLayout
which returns the graph layout that is applied second.
*getLabelLayout
which returns the label layout that is applied last.
You can also change the sublayouts. Of course, you should not change the sublayouts while the Multiple Layout instance is attached to a graph. You should detach the graph first.
To set the sublayouts, the following methods are available:
 
void setFirstGraphLayout(IlvGraphLayout layout)
 
void setSecondGraphLayout(IlvGraphLayout layout)
 
void setLabelLayout(IlvLabelLayout layout)
For experts: attaching graph and labeling models
If a graph model is attached to the Multiple Layout instance, the same graph model is automatically attached to the sublayouts of type IlvGraphModel. For the sublayout of type IlvLabelLayout, a default labeling model is used when possible ( IlvDefaultLabelingModel, see Labels and obstacles in Java). This works if the nodes, links, and labels are stored in an IlvGrapher.
If you implement your own labeling model (subclass of IlvLabelingModel ), you can force the Multiple Layout to use this labeling model instead of the default labeling model. Before you attach the graph model, you call the method setLabelingModel in the following way:
 
multipleLayout.setLabelingModel(myLabelingModel);
multipleLayout.attach(myGraphModel);
You must specify the labeling model in this way if your nodes, links, and labels are not stored in an IlvGrapher but in your own data structures, because the default labeling model is designed to handle only an IlvGrapher.
If the Multiple Layout instance is detached from the graph model, all sublayouts are automatically detached as well.
Combining multiple and recursive layout
Often, the Multiple Layout is used inside a Recursive Layout. For convenience, Rogue Wave® JViews provides a layout algorithm that combines both mechanisms: the Recursive Multiple Layout. This is a Recursive Layout (see Recursive layout) that uses an instance of Multiple Layout for each subgraph.
To apply a Tree Layout, a Link Layout, and an Annealing Label Layout recursively on a nested graph, you can use:
 
IlvRecursiveMultipleLayout layout = new IlvRecursiveMultipleLayout(
                                  new IlvTreeLayout(),
                                  new IlvLinkLayout(),
                                           new IlvAnnealingLabelLayout());
This is in principle the same as a Recursive Layout that has a Multiple Layout as a reference layout:
 
IlvRecursiveLayout layout = new IlvRecursiveLayout(
                            new IlvMultipleLayout(
                            new IlvTreeLayout(),
                            new IlvLinkLayout(),
                                   new IlvAnnealingLabelLayout()));
The Recursive Multiple Layout has a first and second graph layout instance per subgraph, and a label layout instance per subgraph. You access these instances by the following methods:
*IlvGraphLayout getFirstGraphLayout(Object subgraph)
which returns the graph layout that is applied first to the subgraph.
*IlvGraphLayout getSecondGraphLayout(Object subgraph)
which returns the graph layout that is applied secondly to the subgraph.
*IlvLabelLayout getLabelLayout(Object subgraph)
which returns the label layout that is applied last to the subgraph.
If the subgraph parameter is null in these methods, the layout instances of the top-level graph are returned.
For experts: the reference labeling model
The Recursive Multiple Layout must be used when the label layout should use a specified labeling model that is not the default labeling model ( IlvDefaultLabelingModel, see Labels and obstacles in Java). The Multiple Layout allows you to specify a particular labeling model by using the method setLabelingModel, but when you encapsulate the Multiple Layout into a Recursive Layout, this specification would need to be repeated for each layout instance of each subgraph. This would be inconvenient. However, the Recursive Multiple Layout takes care of this mechanism automatically.
If you implement your own labeling model (subclass of IlvLabelingModel ), you must implement the method:
 
IlvLabelingModel createLabelingModel(Object subgraph)
This method should return a new instance of your own labeling model for the input subgraph. The Recursive Multiple Layout uses this method to generate all labeling models for all subgraph from a reference labeling model. Before attaching the Recursive Multiple Layout instance, you can set the reference labeling model in the following way:
 
recursiveMultipleLayout.setReferenceLabelingModel(myLabelingModel);
recursiveMultipleLayout.attach(myGraphModel);
The reference labeling model is used for the label layout of the top-level grapher. Clones of the reference labeling model obtained by createLabelingModel are used for the label layouts of the subgraphers.
Here is a simple way to perform a label layout recursively:
 
IlvRecursiveMultipleLayout layout =
    new IlvRecursiveMultipleLayout(labelLayout);
layout.setReferenceLabelingModel(myLabelingModel);
layout.attach(topLevelGraph);
try {
        IlvGraphLayoutReport layoutReport = layout.performLayout();
        ...
}
catch (IlvGraphLayoutException e) {
        System.err.println(e.getMessage());
}
layout.detach();
If the Recursive Multiple Layout instance is detached from the top level graph model, all sublayouts are automatically detached as well and all labeling models of subgraphs (including the reference labeling model) are disposed of.

Copyright © 2018, Rogue Wave Software, Inc. All Rights Reserved.