]> gerrit.simantics Code Review - simantics/district.git/blob - org.simantics.district.network.ui/src/org/simantics/district/network/ui/nodes/DistrictNetworkEdgeNode.java
First draft of vertex size adjusting district network diagram profiles
[simantics/district.git] / org.simantics.district.network.ui / src / org / simantics / district / network / ui / nodes / DistrictNetworkEdgeNode.java
1 package org.simantics.district.network.ui.nodes;
2
3 import java.awt.BasicStroke;
4 import java.awt.Color;
5 import java.awt.Graphics2D;
6 import java.awt.RenderingHints;
7 import java.awt.Stroke;
8 import java.awt.geom.AffineTransform;
9 import java.awt.geom.Line2D;
10 import java.awt.geom.Path2D;
11 import java.awt.geom.Rectangle2D;
12
13 import org.simantics.district.network.ModelledCRS;
14 import org.simantics.district.network.ui.DistrictNetworkEdge;
15 import org.simantics.scenegraph.ISelectionPainterNode;
16 import org.simantics.scenegraph.g2d.G2DNode;
17 import org.simantics.scenegraph.utils.GeometryUtils;
18 import org.simantics.scenegraph.utils.NodeUtil;
19
20 public class DistrictNetworkEdgeNode extends G2DNode implements ISelectionPainterNode {
21
22     private static final long serialVersionUID = 8049769475036519806L;
23
24     private static final Stroke     SELECTION_STROKE = new BasicStroke(1f, BasicStroke.CAP_BUTT, BasicStroke.JOIN_MITER);
25     private static final Color      SELECTION_COLOR  = new Color(255, 0, 255, 96);
26
27     private DistrictNetworkEdge edge;
28     private Rectangle2D bounds;
29     private Line2D path;
30
31     private static final BasicStroke STROKE = new BasicStroke(4, BasicStroke.CAP_ROUND, BasicStroke.JOIN_ROUND);
32     private boolean scaleStroke = true;
33
34     private Color color;
35
36     private Double stroke;
37
38     @Override
39     public void init() {
40     }
41
42     @Override
43     public void render(Graphics2D g2d) {
44         AffineTransform ot = null;
45         AffineTransform t = getTransform();
46         if (t != null && !t.isIdentity()) {
47             ot = g2d.getTransform();
48             g2d.transform(getTransform());
49         }
50
51         Object aaHint = g2d.getRenderingHint(RenderingHints.KEY_ANTIALIASING);
52         g2d.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON);
53
54         Color oldColor = g2d.getColor();
55         BasicStroke oldStroke = (BasicStroke) g2d.getStroke();
56
57         g2d.setColor(color);
58         BasicStroke bs = null;
59         if (scaleStroke) {
60             double scale = GeometryUtils.getScale(g2d.getTransform());
61             scale = Math.max(10000, Math.min(scale, 50000));
62             double str = stroke != null ? Math.abs(stroke) : 1.0;
63             bs = GeometryUtils.scaleStroke(STROKE, (float) (str / scale));
64         } else {
65             bs = STROKE;
66         }
67
68         path = calculateLine(edge, path);
69
70         if (isSelected()) {
71             g2d.setColor(SELECTION_COLOR);
72             g2d.setStroke(GeometryUtils.scaleStroke(bs, 4f));
73             g2d.draw(path);
74         }
75
76         g2d.setStroke(bs);
77         g2d.draw(path);
78
79         // Reset
80         g2d.setStroke(oldStroke);
81         g2d.setColor(oldColor);
82         g2d.setRenderingHint(RenderingHints.KEY_ANTIALIASING, aaHint);
83
84         if (ot != null)
85             g2d.setTransform(ot);
86     }
87
88     public static Line2D calculateLine(DistrictNetworkEdge edge, Line2D result) {
89         // Convert to screen coordinates
90         double startX = ModelledCRS.longitudeToX(edge.getStartPoint().getX());
91         double startY = ModelledCRS.latitudeToY(-edge.getStartPoint().getY()); // Invert for Simantics
92         double endX = ModelledCRS.longitudeToX(edge.getEndPoint().getX());
93         double endY = ModelledCRS.latitudeToY(-edge.getEndPoint().getY());// Invert for Simantics
94
95         if (result == null)
96             result = new Line2D.Double();
97         result.setLine(startX, startY, endX, endY);
98         return result;
99     }
100
101     public static Path2D calculatePath(DistrictNetworkEdge edge, Path2D result) {
102         // Convert to screen coordinates
103         double startX = ModelledCRS.longitudeToX(edge.getStartPoint().getX());
104         double startY = ModelledCRS.latitudeToY(-edge.getStartPoint().getY()); // Invert for Simantics
105         double endX = ModelledCRS.longitudeToX(edge.getEndPoint().getX());
106         double endY = ModelledCRS.latitudeToY(-edge.getEndPoint().getY());// Invert for Simantics
107
108         if (result == null) {
109              result = new Path2D.Double();
110         } else {
111              result.reset();
112         }
113         result.moveTo(startX, startY);
114         result.lineTo(endX, endY);
115         return result;
116     }
117
118     private boolean isSelected() {
119         return NodeUtil.isSelected(this, 1);
120     }
121
122     @Override
123     public Rectangle2D getBoundsInLocal() {
124         return bounds;
125     }
126
127     private void updateBounds() {
128         Rectangle2D oldBounds = bounds;
129         if (oldBounds == null)
130             oldBounds = new Rectangle2D.Double();
131         bounds = calculateBounds(oldBounds);
132     }
133
134     private Rectangle2D calculateBounds(Rectangle2D rect) {
135         return calculatePath(edge, null).getBounds2D();
136     }
137
138     public void setDNEdge(DistrictNetworkEdge edge) {
139         this.edge = edge;
140         updateBounds();
141     }
142
143     public void setColor(Color color) {
144         this.color = color;
145     }
146
147     public Color getColor() {
148         return color;
149     }
150
151     @PropertySetter(value = "stroke")
152     public void setStroke(Double stroke) {
153         this.stroke = stroke;
154     }
155
156 }