1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24 package org.dishevelled.piccolo.identify;
25
26 import java.awt.Color;
27 import java.awt.Shape;
28
29 import java.awt.geom.Point2D;
30 import java.awt.geom.Rectangle2D;
31
32 import java.beans.PropertyChangeEvent;
33 import java.beans.PropertyChangeListener;
34
35 import javax.swing.UIManager;
36
37 import org.piccolo2d.nodes.PPath;
38
39 import org.piccolo2d.util.PBounds;
40
41 import org.piccolo2d.extras.nodes.PShadow;
42
43 import org.dishevelled.iconbundle.IconSize;
44 import org.dishevelled.iconbundle.IconState;
45
46
47
48
49
50
51
52 public final class ExplorerIdNode
53 extends AbstractIdNode
54 {
55
56 private PPath textSelection;
57
58
59 private PShadow textShadow;
60
61
62 private final double iconTextGap = DEFAULT_ICON_TEXT_GAP;
63
64
65 private static final int BLUR_RADIUS = 4;
66
67
68 private static final double TEXT_SHADOW_OFFSET = 0.5d;
69
70
71 private static final double DEFAULT_ICON_TEXT_GAP = 2.0d;
72
73
74
75
76
77 public ExplorerIdNode()
78 {
79 this(null);
80 }
81
82
83
84
85
86
87 public ExplorerIdNode(final Object value)
88 {
89 super(value);
90 createNodes();
91 resetStateMachine();
92 }
93
94
95
96
97
98
99
100 public ExplorerIdNode(final Object value, final IconSize iconSize)
101 {
102 super(value);
103 setIconSize(iconSize);
104 createNodes();
105 resetStateMachine();
106 }
107
108
109
110
111
112 private void createNodes()
113 {
114 textSelection = new PPath.Double();
115 textShadow = new PShadow(getNameTextNode().toImage(), Color.BLACK, BLUR_RADIUS);
116 addChild(textSelection);
117 addChild(textShadow);
118 addChild(getIconBundleImageNode());
119 addChild(getNameTextNode());
120
121
122 PropertyChangeListener listener = new PropertyChangeListener()
123 {
124 @Override
125 public void propertyChange(final PropertyChangeEvent event)
126 {
127 updateTextShadow();
128 }
129 };
130 getNameTextNode().addPropertyChangeListener("font", listener);
131 getNameTextNode().addPropertyChangeListener("text", listener);
132 }
133
134
135
136
137 private void normal()
138 {
139 setTransparency(1.0f);
140 setIconState(IconState.NORMAL);
141 getNameTextNode().setTextPaint(Color.BLACK);
142 textSelection.setVisible(false);
143 textShadow.setVisible(false);
144 }
145
146
147
148
149 private void reverseNormal()
150 {
151 setTransparency(1.0f);
152 setIconState(IconState.NORMAL);
153 getNameTextNode().setTextPaint(Color.WHITE);
154 textSelection.setVisible(false);
155 textShadow.setVisible(true);
156 }
157
158
159
160
161 private void selected()
162 {
163 setTransparency(1.0f);
164 setIconState(IconState.SELECTED);
165 getNameTextNode().setTextPaint(Color.WHITE);
166 textSelection.setPaint(UIManager.getColor("List.selectionBackground"));
167 textSelection.setStrokePaint(UIManager.getColor("List.selectionBackground"));
168 textSelection.setVisible(true);
169 textShadow.setVisible(false);
170 }
171
172
173
174
175 private void selectedMouseover()
176 {
177 setTransparency(1.0f);
178 setIconState(IconState.SELECTED);
179 getNameTextNode().setTextPaint(Color.WHITE);
180 textSelection.setPaint(UIManager.getColor("List.selectionBackground"));
181 textSelection.setStrokePaint(UIManager.getColor("List.selectionBackground"));
182 textSelection.setVisible(true);
183 textShadow.setVisible(false);
184 }
185
186
187
188
189 private void reverseSelected()
190 {
191 selected();
192 }
193
194
195
196
197 private void reverseSelectedMouseover()
198 {
199 selected();
200 }
201
202
203
204
205 private void dragging()
206 {
207 setTransparency(0.66f);
208 }
209
210
211
212
213 private void reverseDragging()
214 {
215 setTransparency(0.66f);
216 }
217
218
219
220
221 private void updateTextShadow()
222 {
223 removeChild(textShadow);
224 boolean visible = textShadow.getVisible();
225 textShadow = new PShadow(getNameTextNode().toImage(), Color.BLACK, BLUR_RADIUS);
226 textShadow.setVisible(visible);
227 addChild(0, textShadow);
228 }
229
230 @Override
231 protected void layoutChildren()
232 {
233 PBounds iconBounds = getIconBundleImageNode().getBoundsReference();
234 Point2D iconCenter = iconBounds.getCenter2D();
235
236 PBounds textBounds = getNameTextNode().getBoundsReference();
237 Point2D textCenter = textBounds.getCenter2D();
238
239 double textSelectionWidthMargin = Math.min(0.2d * textBounds.getWidth(), 6.0d);
240 double textSelectionHeightMargin = Math.min(0.1d * textBounds.getHeight(), 0.5d);
241
242 Shape textSelectionRect = new Rectangle2D.Double(0.0d, 0.0d,
243 textBounds.getWidth() + 2 * textSelectionWidthMargin, textBounds.getHeight() + 2 * textSelectionHeightMargin);
244 textSelection.reset();
245 textSelection.append(textSelectionRect, false);
246
247 PBounds textSelectionBounds = textSelection.getBoundsReference();
248 Point2D textSelectionCenter = textSelectionBounds.getCenter2D();
249
250 getIconBundleImageNode().setOffset(-iconCenter.getX(), -iconCenter.getY());
251 textSelection.setOffset(-textSelectionCenter.getX(), iconCenter.getY() + iconTextGap);
252 getNameTextNode().setOffset(-textCenter.getX(), iconCenter.getY() + iconTextGap + textSelectionHeightMargin);
253 textShadow.setOffset(-textCenter.getX() - (2 * BLUR_RADIUS) + TEXT_SHADOW_OFFSET,
254 iconCenter.getY() + iconTextGap + textSelectionHeightMargin - (2 * BLUR_RADIUS) + TEXT_SHADOW_OFFSET);
255 }
256 }