* Fixes the control points
* @param cell
*/
protected void setEdgePosition(mxGraphAbstractHierarchyCell cell)
{
mxGraphHierarchyEdge edge = (mxGraphHierarchyEdge) cell;
// For parallel edges we need to separate out the points a
// little
double offsetX = 0.0;
// Only set the edge control points once
if (edge.temp[0] != 101207)
{
int maxRank = edge.maxRank;
int minRank = edge.minRank;
if (maxRank == minRank)
{
maxRank = edge.source.maxRank;
minRank = edge.target.minRank;
}
Iterator<Object> parallelEdges = edge.edges.iterator();
int parallelEdgeCount = 0;
double[] jettys = jettyPositions.get(edge);
Object source = edge.isReversed() ? edge.target.cell : edge.source.cell;
while (parallelEdges.hasNext())
{
Object realEdge = parallelEdges.next();
Object realSource = layout.getGraph().getView().getVisibleTerminal(realEdge, true);
List<mxPoint> newPoints = new ArrayList<mxPoint>(edge.x.length);
// Single length reversed edges end up with the jettys in the wrong
// places. Since single length edges only have jettys, not segment
// control points, we just say the edge isn't reversed in this section
boolean reversed = edge.isReversed();
if (realSource != source)
{
// The real edges include all core model edges and these can go
// in both directions. If the source of the hierarchical model edge
// isn't the source of the specific real edge in this iteration
// treat if as reversed
reversed = !reversed;
}
// First jetty of edge
if (jettys != null)
{
int arrayOffset = reversed ? 2 : 0;
double y = reversed ? rankTopY[minRank] : rankBottomY[maxRank];
double jetty = jettys[parallelEdgeCount * 4 + 1 + arrayOffset];
// If the edge is reversed invert the y position within the channel,
// unless it is a single length edge
if (reversed)
{
jetty = -jetty;
}
y += jetty;
double x = jettys[parallelEdgeCount * 4 + arrayOffset];
if (orientation == SwingConstants.NORTH
|| orientation == SwingConstants.SOUTH)
{
newPoints.add(new mxPoint(x, y));
}
else
{
newPoints.add(new mxPoint(y, x));
}
}
// Declare variables to define loop through edge points and
// change direction if edge is reversed
int loopStart = edge.x.length - 1;
int loopLimit = -1;
int loopDelta = -1;
int currentRank = edge.maxRank - 1;
if (reversed)
{
loopStart = 0;
loopLimit = edge.x.length;
loopDelta = 1;
currentRank = edge.minRank + 1;
}
// Reversed edges need the points inserted in
// reverse order
for (int j = loopStart; (edge.maxRank != edge.minRank) && j != loopLimit; j += loopDelta)
{
// The horizontal position in a vertical layout
double positionX = edge.x[j] + offsetX;
// Work out the vertical positions in a vertical layout
// in the edge buffer channels above and below this rank
double topChannelY = (rankTopY[currentRank] + rankBottomY[currentRank + 1]) / 2.0;
double bottomChannelY = (rankTopY[currentRank - 1] + rankBottomY[currentRank]) / 2.0;
if (reversed)
{
double tmp = topChannelY;
topChannelY = bottomChannelY;
bottomChannelY = tmp;
}
if (orientation == SwingConstants.NORTH
|| orientation == SwingConstants.SOUTH)
{
newPoints.add(new mxPoint(positionX, topChannelY));
newPoints.add(new mxPoint(positionX, bottomChannelY));
}
else
{
newPoints.add(new mxPoint(topChannelY, positionX));
newPoints.add(new mxPoint(bottomChannelY, positionX));
}
limitX = Math.max(limitX, positionX);
// double currentY = (rankTopY[currentRank] + rankBottomY[currentRank]) / 2.0;
// System.out.println("topChannelY = " + topChannelY + " , "
// + "exact Y = " + edge.y[j]);
currentRank += loopDelta;
}
// Second jetty of edge
if (jettys != null)
{
int arrayOffset = reversed ? 2 : 0;
double rankY = reversed ? rankBottomY[maxRank] : rankTopY[minRank];
double jetty = jettys[parallelEdgeCount * 4 + 3 - arrayOffset];
if (reversed)
{
jetty = -jetty;
}
double y = rankY - jetty;
double x = jettys[parallelEdgeCount * 4 + 2 - arrayOffset];
if (orientation == SwingConstants.NORTH
|| orientation == SwingConstants.SOUTH)
{
newPoints.add(new mxPoint(x, y));
}
else
{
newPoints.add(new mxPoint(y, x));
}
}
if (edge.isReversed())
{
processReversedEdge(edge, realEdge);
}
layout.setEdgePoints(realEdge, newPoints);