Using the graph model
Describes the graph model.
Gives an idea of the graph model and how it is used.
Explains the difference between the graph model and the SDM model.
Explains the graph model in more detail with a diagram of the classes.
Describes the graph model class in more detail.
Describes the grapher adapter class in more detail.
Describes how to wrap a graph model and provide a transformed coordinate space of the original graph model.
Overview of the graph model
The
IlvGraphModel class defines a suitable, generic API for graphs that have to be laid out with Rogue Wave®
JViews Diagrammer graph layout algorithms.
All the layout algorithms provided in Rogue Wave
JViews Diagrammer are designed to lay out a graph model. This allows applications to benefit from the graph layout algorithms whether or not they use the Rogue Wave JViews grapher (
IlvGrapher). However, to make things very simple for the common case of applications that manipulate an
IlvGrapher, it is not mandatory to work directly with the graph model except for some advanced features such as filtering (see
Using filtering to lay out a part of an IlvGrapher).
Graph model and SDM model
Defines the SDM model and the graph model.
There are two key concepts: the
graph model and the
SDM model of the diagram component (subclass of
IlvDiagrammer). It is important to avoid confusion between them.
The SDM model
The SDM model represents the application objects. Application objects typically have only logical properties, not graphic properties (position, size, shape, and so on). The rendering process produces graphic objects for the SDM model objects.
The graph model
The graph model of the layout algorithms is an abstraction of the graphic properties of these graphic objects., not an abstraction of the application objects.
The graph model concept
With a graph model, you can use already-built graphs, nodes, and links that have been developed without Rogue Wave® JViews and apply the layout algorithms of Rogue Wave JViews Diagrammer. The graph model provides the basic, generic operations for performing the layout.
A subclass must be written to adapt the graph model to specific graph, node, and link objects. This subclass plays the role of an “adapter” or bridge between the application objects and the graph model. This often makes it much easier to add graph features to existing applications.
The following figure shows the relationship between the graph model and graph layout algorithms, Rogue Wave JViews graphers, non-JViews graphers, and manager views.
Graph Model in the Rogue Wave JViews Diagrammer Graph Layout Framework
You can see from this diagram that instead of using a concrete graph class such as
IlvGrapher directly, the layout algorithms interact with the graph through the graph model. This is the key for achieving a truly generic graph layout framework. Note that the use of an
IlvManagerView to display the result of the layout is not mandatory.
The IlvGraphModel class
The
IlvGraphModel class is an abstract Java™ class. Because it does not provide a concrete implementation of a graph data structure, a complete implementation must be provided by “adapter” classes. The adapters extend the
IlvGraphModel class and must use an underlying graph data structure. A special adapter class called
IlvGrapherAdapter is provided so that an
IlvGrapher can be used as the underlying graph data structure.
NOTE If an application uses the
IlvGrapher class, the grapher can be attached directly to the layout instance without explicitly using a graph model, see the
attach method. In this case, the appropriate adapter (
IlvGrapherAdapter ) will be created internally. This adapter can be retrieved using the
getGraphModel method, which will return an instance of
IlvGrapherAdapter.
Most of the methods defined in the IlvGraphModel class have a name and definition very similar to the corresponding methods of the IlvGrapher class. The main difference is that the arguments of the IlvGraphModel methods are java.lang.Object instead of IlvGraphic or IlvLinkImage. The methods can be divided into several categories that provide information on the structure of the graph, the geometry of the graph, modification of the graph geometry, and notification of changes in the graph.
This section is divided as follows:
Information on the structure of the graph
The following methods of the
IlvGraphModel class allow the layout algorithms to retrieve information on the structure of the graph:
Enumeration getNodesAndLinks()
Enumeration getNodes()
int getNodesCount()
Enumeration getLinks()
int getLinksCount()
boolean isNode(Object obj)
boolean isLink(Object obj)
Enumeration getLinks(Object node)
int getLinksCount(Object node)
Enumeration getLinksFrom(Object node)
int getLinksFromCount(Object node)
Enumeration getLinksTo(Object node)
int getLinksToCount(Object node)
Enumeration getNeighbors(Object node)
int getNodeDegree(Object node)
Object getFrom(Object link)
Object getTo(Object link)
Object getOpposite(Object link, Object node)
boolean isLinkBetween(Object node1, Object node2)
The following methods are provided for use with nested graphs (see also
Nested layouts):
IlvGraphModel getParentModel()
IlvGraphModel getRootModel()
IlvGraphModel getGraphModel(Object subgraph)
IlvGraphModel createGraphModel(Object subgraph)
Enumeration getSubgraphs()
int getSubgraphsCount()
boolean isSubgraph(Object obj)
Enumeration getInterGraphLinks()
int getInterGraphLinksCount()
boolean isInterGraphLink(Object obj)
Information on the geometry of the graph
The following methods of the IlvGraphModel class allow the layout algorithms to retrieve information on the geometry of the graph:
IlvRect boundingBox(Object nodeOrLink)
IlvRect boundingBox()
IlvPoint[] getLinkPoints(Object link)
IlvPoint getLinkPointAt(Object link, int index)
int getLinkPointsCount(Object link)
float getLinkWidth(Object link)
The boundingBox method is called by a layout algorithm whenever it needs to get the position and the dimensions of a node or a link. The other methods are used mainly by link layout algorithms.
Modification of the geometry of the graph
The following methods of the IlvGraphModel class allow a layout algorithm to modify the geometry of the graph:
void moveNode(Object node, float x, float y, boolean redraw)
void reshapeLink(Object link, IlvPoint fromPoint, IlvPoint[] points, int
startIndex, int length, IlvPoint toPoint, boolean redraw)
void move(float x, float y, boolean redraw)
Layout algorithms that compute new coordinates for the nodes use the moveNode method. Link layout algorithms that compute new shapes for the links call one of the reshapeLink methods.
Notification of changes
The following methods of the IlvGraphModel class allow a layout algorithm to be notified of changes in the graph:
void addGraphModelListener(GraphModelListener listener)
void removeGraphModelListener(GraphModelListener listener)
void fireGraphModelEvent(GraphModelEvent event)
void fireGraphModelEvent(Object nodeOrLink, int type, boolean adjusting)
void adjustmentEnd()
A “change” in the graph can be a structure change (that is, a node or a link was added or removed) or a geometry change (that is, a node or a link was moved or reshaped). The graph model event listener mechanism provides a means to keep the layout algorithms informed of these changes. When the layout algorithm is restarted on the same graph, it is able to detect whether the graph has changed since the last time the layout was successfully performed. If necessary, the layout can be performed again. If there is no change in the graph, the layout algorithm can avoid unnecessary work by not performing the layout. To know whether the previous layout is still valid or it must be redone, the layout algorithms call the following method of the model:
boolean isLayoutNeeded()
The graph model event listener is defined by the
GraphModelListener interface. To receive the graph model events (that is, instances of the
GraphModelEventclass), a class must implement the
GraphModelListener interface and must register itself using the
addGraphModelListener method of the
IlvGraphModel class.
NOTE The creation of the graph model event listener is handled transparently by the
IlvGraphModel class. Therefore, there is usually no need to manipulate this listener directly.
Storing and retrieving data objects (“properties”)
The following methods of the IlvGraphModel class allow a layout algorithm to store data objects for each node, link, or graph:
void setProperty(Object nodeOrLink, String key, Object value)
Object getProperty(Object nodeOrLink, String key)
void setProperty(String key, Object value)
Object getProperty(String key)
The layout algorithm may need to associate a set of properties with the nodes and links of the graph or with the graph itself. Properties are a set of key-value pairs, where the key is a String object and the value can be any kind of information value.
NOTE Creating a property and associating it with a node, a link, or a graph is handled transparently by the layout algorithm whenever it is necessary. Therefore, there is usually no need to manipulate the properties directly. However, if needed, you can do this in your own subclass of
IlvGraphLayout.
Using the class IlvGrapherAdapter
The
IlvGrapherAdapter class is a concrete subclass of
IlvGraphModel that allows an
IlvGrapher to be laid out using the layout algorithms provided in Rogue Wave®
JViews Diagrammer. It provides an implementation for all the abstract methods of
IlvGraphModel. It also provides an overridden implementation of some nonabstract methods of
IlvGraphModel to improve efficiency by taking advantage of the characteristics of the
IlvGrapher.
If an application uses the
IlvGrapher class, the grapher can be attached directly to the layout instance without explicitly using the adapter, see the method
attach. In this case, an
IlvGrapherAdapter is created internally by the layout class. The adapter can be retrieved using the method
getGraphModel, which will return an instance of
IlvGrapherAdapter.
Notice that such an internally created adapter is not allowed to be attached to any other layout instance, nor to be used in any way once the method
detach IlvGraphLayout.detach() has been called on the layout instance.
In case you need to be able to do any of the above operations, directly create the instance of
IlvGrapherAdapter and attach it using
attach).
To know whether a specific
IlvGraphModel instance has been created using
attach), you can use the method
getOriginatingLayout. This method returns a non-
null object if the model has not been created using
IlvGraphLayout.attach(IlvGrapher).
Additionally, the
IlvGrapherAdapter class provides a way to filter the
IlvGrapher. By using the filtering mechanism, you specify a particular set of nodes and links that have to be taken into account by the layout algorithm, see
Using filtering to lay out a part of an IlvGrapher.
The
IlvGrapherAdapter class allows you to specify the order of nodes returned by the methods
getNodes IlvGrapherAdapter.getNodes() and
getNodesAndLinks. For this purpose you can provide your own implementation of a
java.util.Comparator that defines the order of the nodes. Then specify this comparator by using the method
setNodeComparator.
The
IlvGrapherAdapter class also allows you to specify the
IlvTransformer that has to be used for computing the geometry of the graph, see
Choosing the layout coordinate space.
Using the class IlvRotatedGraphModel
The
IlvRotatedGraphModel class is a concrete subclass of
IlvGraphModel. It wraps a graph model and provides a transformed coordinate space of the original graph model. This capability is useful, for example, when you want a Tree Layout or a Hierarchical Layout with a diagonal flow direction.
To allocate and attach a rotated graph model, call:
IlvGraphModel originalModel = ... any graph model ...
IlvRotatedGraphModel rotatedModel =
new IlvRotatedGraphModel(originalModel, owned, center, angle);
layout.attach(rotatedModel);
The graph layout is now performed in the coordinate space of the rotated model. The original model can be, for example, an
IlvGrapherAdapter object. The center point and angle define the rotation. The
owned parameter of
IlvRotatedGraphModel indicates whether the original model is owned by the rotated model or whether the lifetime of the original model is independent from the rotated model. If the original model is owned by the rotated model, it is automatically disposed when the rotated model is disposed.
The class IlvRotatedGraphModel can be used with any transform, but looks best with rotations or shear transforms. It transforms the node positions and the bend points of links, but it does not rotate the node shapes. If the node shapes must be transformed as well, it is more suitable to rotate the entire view instead of using IlvRotatedGraphModel. To allocate a rotated graph model with an arbitrary transform, call:
IlvRotatedGraphModel rotatedModel =
new IlvRotatedGraphModel(originalModel, owned, tranformer);
When the graph layout uses a clip link interface, node box, or link connection box interface, the implementations of these interfaces must take into account the rotation. The easiest way to obtain an appropriate implementation is to implement the interface for the original model and then obtain a rotated variant of the interface by calling:
IlvLinkClipInterface linkClipper = ... implementation for originalModel ...
IlvLinkClipInterface rotatedLinkClipper =
rotatedModel.getLinkClipInterface(linkClipper);
layout.attach(rotatedModel);
layout.setLinkClipInterface(rotatedLinkClipper);
The class IlvRotatedGraphModel is suitable for layout of flat graphs. It is not suitable for the recursive layout mode of Hierarchical Layout or Tree Layout for nested graphs.
Copyright © 2018, Rogue Wave Software, Inc. All Rights Reserved.