]> gerrit.simantics Code Review - simantics/platform.git/blob - bundles/org.simantics.diagram/src/org/simantics/diagram/profile/ButtonNode.java
Fixed multiple issues causing dangling references to discarded queries
[simantics/platform.git] / bundles / org.simantics.diagram / src / org / simantics / diagram / profile / ButtonNode.java
1 package org.simantics.diagram.profile;
2
3 import java.awt.Graphics2D;
4 import java.awt.geom.AffineTransform;
5 import java.awt.geom.Point2D;
6 import java.awt.geom.Rectangle2D;
7
8 import org.simantics.datatypes.literal.RGB;
9 import org.simantics.datatypes.literal.Vec2d;
10 import org.simantics.diagram.elements.DiagramNodeUtil;
11 import org.simantics.diagram.elements.SVGNode;
12 import org.simantics.diagram.internal.Activator;
13 import org.simantics.diagram.profile.ButtonResult.A;
14 import org.simantics.diagram.profile.ButtonResult.B;
15 import org.simantics.scenegraph.g2d.G2DNode;
16 import org.simantics.scenegraph.g2d.events.EventTypes;
17 import org.simantics.scenegraph.g2d.events.MouseEvent;
18 import org.simantics.scenegraph.g2d.events.MouseEvent.MouseButtonPressedEvent;
19 import org.simantics.scenegraph.g2d.events.MouseEvent.MouseButtonReleasedEvent;
20 import org.simantics.scenegraph.utils.NodeUtil;
21 import org.simantics.scl.runtime.function.Function1;
22
23 public class ButtonNode extends IconButtonNode {
24         
25         private static final long serialVersionUID = -1963362069190362275L;
26         
27         private B config;
28         private boolean isDown = false;
29         private Function1<Boolean, Boolean> pressed;
30         
31         private static SVGNode ON = new SVGNode();
32         private static SVGNode OFF = new SVGNode();
33         private static boolean initialized = false;
34         
35     Rectangle2D EMPTY = new Rectangle2D.Double(0, 0, 0, 0);
36         
37         private SVGNode current = OFF;
38         private Rectangle2D lastBounds = EMPTY; 
39
40         public void staticInit() {
41                 if(!initialized) {
42                         ON.setData(createSVG("BUTTON_ON"));
43                         OFF.setData(createSVG("BUTTON_OFF"));
44                         initialized = true;
45                 }
46         }
47         
48         @Override
49         public void init() {
50                 staticInit();
51         addEventHandler(this);
52         }
53         
54     @Override
55     public void cleanup() {
56         removeEventHandler(this);
57         super.cleanup();
58     }
59         
60         private void setValue(double value) {
61                 
62                 // Value does not affect LATCH buttons
63                 if(ButtonMode.LATCH.equals(config.mode)) return;
64                 
65                 if(value < 0.5) {
66                         current = OFF;
67                 } else {
68                         current = ON;
69                 } 
70                 
71         }
72         
73         private void setConfig(B config) {
74
75                 if(this.config == config) return;
76         this.config = config;
77                 
78         }
79         
80         public void setA(A data) {
81
82                 setConfig(data.config);
83         setValue(data.value);
84                 
85         }
86         
87     @Override
88     public void render(Graphics2D g2d) {
89
90                 AffineTransform ot = null;
91                 if (!transform.isIdentity()) {
92                         ot = g2d.getTransform();
93                         g2d.transform(transform);
94                 }
95         
96                 current.render(g2d);
97                 lastBounds = current.getBounds();
98
99                 if (ot != null)
100                         g2d.setTransform(ot);
101         
102     }
103
104         @Override
105         public Rectangle2D getBoundsInLocal() {
106                 return lastBounds;
107         }
108
109         @Override
110         void setData(IconButtonResult state) {
111                 ButtonResult br = (ButtonResult)state;
112                 setA(br.getA());
113                 pressed = br.getPressed();
114         }
115
116     private boolean hitTest(MouseEvent event) {
117         Rectangle2D bounds = getBounds();
118         if (bounds == null)
119             return false;
120         Point2D localPos = NodeUtil.worldToLocal(this, event.controlPosition, new Point2D.Double());
121         double x = localPos.getX();
122         double y = localPos.getY();
123         return bounds.contains(x, y);
124     }
125         
126         @Override
127     protected boolean mouseButtonPressed(MouseButtonPressedEvent e) {
128                 if(!e.hasAnyButton(MouseEvent.LEFT_BUTTON)) return false;
129                 if(!hitTest(e)) return false; 
130                 if(pressed != null) {
131                         pressed.apply(true);
132                         isDown = true;
133                         if(ButtonMode.LATCH.equals(config.mode)) {
134                                 current = ON;
135                                 DiagramNodeUtil.getCanvasContext((G2DNode)this).getContentContext().setDirty();
136                         }
137                 }
138         return true;
139     }
140
141         @Override
142     protected boolean mouseButtonReleased(MouseButtonReleasedEvent e) {
143                 if(e.hasAnyButton(MouseEvent.LEFT_BUTTON)) return false;
144                 if(!hitTest(e) && !isDown) return false; 
145                 if(pressed != null) {
146                         pressed.apply(false);
147                         isDown = false;
148                         if(ButtonMode.LATCH.equals(config.mode)) {
149                                 current = OFF;
150                                 DiagramNodeUtil.getCanvasContext((G2DNode)this).getContentContext().setDirty();
151                         }
152                 }
153         return true;
154     }
155         
156     @Override
157     public int getEventMask() {
158         return EventTypes.MouseButtonPressedMask
159                 | EventTypes.MouseButtonReleasedMask
160                 ;
161     }   
162     
163     public String createSVG(String iconName) {
164         return Activator.ICON_PROVIDER.apply(iconName, new RGB.Integer(0,  0, 0), new Vec2d(1,1));
165     }
166     
167 }