/* * PIPELineWithTextEdgePainter.java */ package pipe.gui.reachability; import net.sourceforge.jpowergraph.SubGraphHighlighter; import net.sourceforge.jpowergraph.painters.edge.LineEdgePainter; import net.sourceforge.jpowergraph.pane.JGraphPane; import net.sourceforge.jpowergraph.swtswinginteraction.JPowerGraphGraphics; import net.sourceforge.jpowergraph.swtswinginteraction.color.JPowerGraphColor; import net.sourceforge.jpowergraph.swtswinginteraction.geometry.JPowerGraphPoint; import java.awt.geom.Point2D; //REMARK: this class extends a jpowergraph's class which is LGPL /** * This class defines the edge painter for edges with text used in the reachability graph */ public class PIPELineWithTextEdgePainter<T extends DirectedTextEdge> extends LineEdgePainter<T> { /** * Constructor * @param dragging dragging * @param normal normal * @param isDashedLine true if dashed */ public PIPELineWithTextEdgePainter(JPowerGraphColor dragging, JPowerGraphColor normal, boolean isDashedLine) { super(dragging, normal, isDashedLine); } /** * Displays the edge and text on the graph * @param graphPane graph pane * @param g graphics * @param edge edge * @param theSubGraphHighlighter highlighter */ @Override public void paintEdge(JGraphPane graphPane, JPowerGraphGraphics g, T edge, SubGraphHighlighter theSubGraphHighlighter) { JPowerGraphPoint from = graphPane.getScreenPointForNode(edge.getFrom()); JPowerGraphPoint to = graphPane.getScreenPointForNode(edge.getTo()); JPowerGraphColor oldFGColor = g.getForeground(); JPowerGraphColor oldBGColor = g.getBackground(); g.setForeground(getEdgeColor(edge, graphPane, false, theSubGraphHighlighter)); g.setBackground(getEdgeColor(edge, graphPane, false, theSubGraphHighlighter)); paintArrow(g, from.x, from.y, to.x, to.y, false); g.setForeground(oldFGColor); g.setBackground(oldBGColor); String text = edge.getText(); Point2D midpoint = new Point2D.Double((from.x + 2 * to.x) / 3, (from.y + 2 * to.y) / 3); double slopeTop = from.y - to.y; double slopeBottom = from.x - to.x; double slope = Double.POSITIVE_INFINITY; if (slopeBottom != 0) { slope = slopeTop / slopeBottom; } int stringWidth = g.getStringWidth(text); if (slope > 2.0) { double xDiff = -(stringWidth + 10); double yDiff = -10; if (from.y < to.y) { yDiff = -5; } midpoint.setLocation(midpoint.getX() + xDiff, midpoint.getY() + yDiff); } else if (slope < -2.0) { double xDiff = 10; double yDiff = -10; if (from.y < to.y) { yDiff = -5; } midpoint.setLocation(midpoint.getX() + xDiff, midpoint.getY() + yDiff); } else if (slope > 0.4 || slope < -0.4) { double xDiff = 10; double yDiff = -10; if (from.x > to.x) { xDiff = -(stringWidth + 10); } if (from.y < to.y) { yDiff = -5; } midpoint.setLocation(midpoint.getX() + xDiff, midpoint.getY() + yDiff); } else { double xDiff = -stringWidth / 2; double yDiff = -20; midpoint.setLocation(midpoint.getX() + xDiff, midpoint.getY() + yDiff); } g.setForeground(getEdgeColor(edge, graphPane, false, theSubGraphHighlighter)); g.drawString(text, (int) midpoint.getX(), (int) midpoint.getY(), 1); g.setForeground(oldFGColor); } /** * Paints an arrow in the correct direction * @param g graphics * @param x1 coordinate * @param y1 coordinate * @param x2 coordinate * @param y2 coordinate * @param isDashedLine true if dashed */ public static void paintArrow(JPowerGraphGraphics g, int x1, int y1, int x2, int y2, boolean isDashedLine) { double middleX = (x1 + 2 * x2) / 3; double middleY = (y1 + 2 * y2) / 3; double slope = Math.atan2(y2 - y1, x2 - x1); double pinnacleX = middleX + SQUARE_ROOT_OF_3_OVER_2 * ARROW_BASE_LENGTH * Math.cos(slope); double pinnacleY = middleY + SQUARE_ROOT_OF_3_OVER_2 * ARROW_BASE_LENGTH * Math.sin(slope); double backwardX = pinnacleX + ARROW_BASE_LENGTH * Math.cos(slope + Math.PI + Math.PI / 6.0); double backwardY = pinnacleY + ARROW_BASE_LENGTH * Math.sin(slope + Math.PI + Math.PI / 6.0); double forwardX = pinnacleX + ARROW_BASE_LENGTH * Math.cos(slope + Math.PI - Math.PI / 6.0); double forwardY = pinnacleY + ARROW_BASE_LENGTH * Math.sin(slope + Math.PI - Math.PI / 6.0); double baseX = (forwardX + backwardX) / 2.0; double baseY = (forwardY + backwardY) / 2.0; g.setLineDashed(isDashedLine); g.drawLine(x1, y1, (int) baseX, (int) baseY); g.drawLine((int) pinnacleX, (int) pinnacleY, x2, y2); g.setLineDashed(false); g.fillPolygon(new int[]{(int) backwardX, (int) backwardY, (int) pinnacleX, (int) pinnacleY, (int) forwardX, (int) forwardY}); } }