svn-gvsig-desktop / trunk / extensions / extSymbology / src / org / gvsig / symbology / fmap / styles / SimpleLabelStyle.java @ 25807
History | View | Annotate | Download (12.3 KB)
1 | 22833 | vcaballero | /* gvSIG. Sistema de Informaci?n Geogr?fica de la Generalitat Valenciana
|
---|---|---|---|
2 | *
|
||
3 | * Copyright (C) 2005 IVER T.I. and Generalitat Valenciana.
|
||
4 | *
|
||
5 | * This program is free software; you can redistribute it and/or
|
||
6 | * modify it under the terms of the GNU General Public License
|
||
7 | * as published by the Free Software Foundation; either version 2
|
||
8 | * of the License, or (at your option) any later version.
|
||
9 | *
|
||
10 | * This program is distributed in the hope that it will be useful,
|
||
11 | * but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||
12 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||
13 | * GNU General Public License for more details.
|
||
14 | *
|
||
15 | * You should have received a copy of the GNU General Public License
|
||
16 | * along with this program; if not, write to the Free Software
|
||
17 | * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307,USA.
|
||
18 | *
|
||
19 | * For more information, contact:
|
||
20 | *
|
||
21 | * Generalitat Valenciana
|
||
22 | * Conselleria d'Infraestructures i Transport
|
||
23 | * Av. Blasco Ib??ez, 50
|
||
24 | * 46010 VALENCIA
|
||
25 | * SPAIN
|
||
26 | *
|
||
27 | * +34 963862235
|
||
28 | * gvsig@gva.es
|
||
29 | * www.gvsig.gva.es
|
||
30 | *
|
||
31 | * or
|
||
32 | *
|
||
33 | * IVER T.I. S.A
|
||
34 | * Salamanca 50
|
||
35 | * 46005 Valencia
|
||
36 | * Spain
|
||
37 | *
|
||
38 | * +34 963163400
|
||
39 | * dac@iver.es
|
||
40 | */
|
||
41 | |||
42 | /* CVS MESSAGES:
|
||
43 | *
|
||
44 | * $Id: SimpleLabelStyle.java 13953 2007-09-21 12:26:04Z jaume $
|
||
45 | * $Log$
|
||
46 | * Revision 1.18 2007-09-21 12:22:36 jaume
|
||
47 | * cancellation support extended down to the IGeometry and ISymbol level
|
||
48 | *
|
||
49 | * Revision 1.17 2007/09/17 09:32:52 jaume
|
||
50 | * removed system.out....
|
||
51 | *
|
||
52 | * Revision 1.16 2007/08/21 09:30:42 jvidal
|
||
53 | * javadoc
|
||
54 | *
|
||
55 | * Revision 1.15 2007/05/08 08:47:39 jaume
|
||
56 | * *** empty log message ***
|
||
57 | *
|
||
58 | * Revision 1.14 2007/04/19 14:21:30 jaume
|
||
59 | * *** empty log message ***
|
||
60 | *
|
||
61 | * Revision 1.12 2007/04/18 15:35:11 jaume
|
||
62 | * *** empty log message ***
|
||
63 | *
|
||
64 | * Revision 1.11 2007/04/12 14:28:43 jaume
|
||
65 | * basic labeling support for lines
|
||
66 | *
|
||
67 | * Revision 1.10 2007/04/11 16:01:34 jaume
|
||
68 | * try to fit the text in the correct place
|
||
69 | *
|
||
70 | * Revision 1.9 2007/04/10 16:34:01 jaume
|
||
71 | * towards a styled labeling
|
||
72 | *
|
||
73 | * Revision 1.8 2007/04/05 16:07:14 jaume
|
||
74 | * Styled labeling stuff
|
||
75 | *
|
||
76 | * Revision 1.7 2007/04/04 15:42:03 jaume
|
||
77 | * *** empty log message ***
|
||
78 | *
|
||
79 | * Revision 1.6 2007/04/04 15:41:05 jaume
|
||
80 | * *** empty log message ***
|
||
81 | *
|
||
82 | * Revision 1.5 2007/04/02 16:34:56 jaume
|
||
83 | * Styled labeling (start commiting)
|
||
84 | *
|
||
85 | * Revision 1.4 2007/04/02 00:10:04 jaume
|
||
86 | * *** empty log message ***
|
||
87 | *
|
||
88 | * Revision 1.3 2007/03/29 16:02:01 jaume
|
||
89 | * *** empty log message ***
|
||
90 | *
|
||
91 | * Revision 1.2 2007/03/09 11:20:56 jaume
|
||
92 | * Advanced symbology (start committing)
|
||
93 | *
|
||
94 | * Revision 1.1.2.2 2007/02/15 16:23:44 jaume
|
||
95 | * *** empty log message ***
|
||
96 | *
|
||
97 | * Revision 1.1.2.1 2007/02/09 07:47:04 jaume
|
||
98 | * Isymbol moved
|
||
99 | *
|
||
100 | *
|
||
101 | */
|
||
102 | package org.gvsig.symbology.fmap.styles; |
||
103 | |||
104 | import java.awt.Color; |
||
105 | import java.awt.Dimension; |
||
106 | import java.awt.Graphics2D; |
||
107 | import java.awt.Rectangle; |
||
108 | import java.awt.geom.Point2D; |
||
109 | import java.awt.geom.Rectangle2D; |
||
110 | import java.util.ArrayList; |
||
111 | |||
112 | import org.apache.log4j.Logger; |
||
113 | |||
114 | 23125 | vcaballero | import com.iver.andami.PluginServices; |
115 | 22833 | vcaballero | import com.iver.cit.gvsig.fmap.Messages; |
116 | import com.iver.cit.gvsig.fmap.core.FPolygon2D; |
||
117 | import com.iver.cit.gvsig.fmap.core.FShape; |
||
118 | import com.iver.cit.gvsig.fmap.core.GeneralPathX; |
||
119 | import com.iver.cit.gvsig.fmap.core.SymbologyFactory; |
||
120 | import com.iver.cit.gvsig.fmap.core.styles.AbstractStyle; |
||
121 | import com.iver.cit.gvsig.fmap.core.styles.ILabelStyle; |
||
122 | import com.iver.cit.gvsig.fmap.core.symbols.ISymbol; |
||
123 | import com.iver.cit.gvsig.fmap.core.symbols.SimpleFillSymbol; |
||
124 | import com.iver.cit.gvsig.fmap.core.symbols.SimpleLineSymbol; |
||
125 | import com.iver.cit.gvsig.fmap.core.symbols.SymbolDrawingException; |
||
126 | import com.iver.utiles.XMLEntity; |
||
127 | |||
128 | |||
129 | /**
|
||
130 | * Implements a style for the creation of simple labels.
|
||
131 | *
|
||
132 | * @author jaume dominguez faus - jaume.dominguez@iver.es
|
||
133 | */
|
||
134 | public class SimpleLabelStyle extends AbstractStyle implements ILabelStyle { |
||
135 | private Point2D markerPoint = new Point2D.Double(); |
||
136 | // conertir a?? a Rectangle2D[] ja que pot arribar a gastar-se massivament
|
||
137 | // en el pintat
|
||
138 | private ArrayList<Rectangle2D> textFieldAreas = new ArrayList<Rectangle2D>(); |
||
139 | private BackgroundFileStyle background;
|
||
140 | 23125 | vcaballero | private Dimension defaultSize = new Dimension(32,32); |
141 | 22833 | vcaballero | private Dimension sz; |
142 | |||
143 | |||
144 | |||
145 | public int getFieldCount() { |
||
146 | return textFieldAreas.size();
|
||
147 | } |
||
148 | |||
149 | public void setTextFields(String[] texts) { |
||
150 | StringBuffer sb = new StringBuffer(); |
||
151 | for (int i = 0; texts != null && i < texts.length; i++) { |
||
152 | sb.append(texts[i]); |
||
153 | if (i<texts.length)
|
||
154 | sb.append(" ");
|
||
155 | } |
||
156 | } |
||
157 | |||
158 | public boolean isSuitableFor(ISymbol symbol) { |
||
159 | return true; |
||
160 | } |
||
161 | |||
162 | public String getClassName() { |
||
163 | return getClass().getName();
|
||
164 | } |
||
165 | |||
166 | public XMLEntity getXMLEntity() {
|
||
167 | XMLEntity xml = new XMLEntity();
|
||
168 | xml.putProperty("className", getClassName());
|
||
169 | xml.putProperty("desc", getDescription());
|
||
170 | xml.putProperty("markerPointX", markerPoint.getX());
|
||
171 | xml.putProperty("markerPointY", markerPoint.getY());
|
||
172 | |||
173 | int size = getFieldCount();
|
||
174 | String[] minx = new String[size]; |
||
175 | String[] miny = new String[size]; |
||
176 | String[] widths = new String[size]; |
||
177 | String[] heights = new String[size]; |
||
178 | |||
179 | Rectangle2D[] rects = getTextBounds(); |
||
180 | for (int i = 0; i < rects.length; i++) { |
||
181 | minx[i] = String.valueOf(rects[i].getMinX());
|
||
182 | miny[i] = String.valueOf(rects[i].getMinY());
|
||
183 | widths[i] = String.valueOf(rects[i].getWidth());
|
||
184 | heights[i] = String.valueOf(rects[i].getHeight());
|
||
185 | } |
||
186 | |||
187 | xml.putProperty("minXArray", minx);
|
||
188 | xml.putProperty("minYArray", miny);
|
||
189 | xml.putProperty("widthArray", widths);
|
||
190 | xml.putProperty("heightArray", heights);
|
||
191 | 23417 | vcaballero | if(getBackgroundFileStyle() != null){ |
192 | XMLEntity bgXML = getBackgroundFileStyle().getXMLEntity(); |
||
193 | 22953 | vcaballero | bgXML.putProperty("id", "LabelStyle"); |
194 | xml.addChild(bgXML); |
||
195 | } |
||
196 | 25457 | vcaballero | if (sz!=null){ |
197 | xml.putProperty("sizeW",(int)sz.getWidth()); |
||
198 | xml.putProperty("sizeH",(int)sz.getHeight()); |
||
199 | } |
||
200 | 22833 | vcaballero | return xml;
|
201 | } |
||
202 | |||
203 | public void setXMLEntity(XMLEntity xml) { |
||
204 | setDescription(xml.getStringProperty("desc"));
|
||
205 | |||
206 | double x = xml.getDoubleProperty("markerPointX"); |
||
207 | double y = xml.getDoubleProperty("markerPointY"); |
||
208 | |||
209 | double[] minx = xml.getDoubleArrayProperty("minXArray"); |
||
210 | double[] miny = xml.getDoubleArrayProperty("minYArray"); |
||
211 | double[] widths = xml.getDoubleArrayProperty("widthArray"); |
||
212 | double[] heights = xml.getDoubleArrayProperty("heightArray"); |
||
213 | 23417 | vcaballero | |
214 | textFieldAreas.clear(); |
||
215 | 22833 | vcaballero | for (int i = 0; i < minx.length; i++) { |
216 | addTextFieldArea(new Rectangle2D.Double( |
||
217 | minx[i], |
||
218 | miny[i], |
||
219 | widths[i], |
||
220 | heights[i])); |
||
221 | } |
||
222 | markerPoint.setLocation(x, y); |
||
223 | XMLEntity bgXML = xml.firstChild("id", "LabelStyle"); |
||
224 | if (bgXML!=null) { |
||
225 | background = (BackgroundFileStyle) SymbologyFactory.createStyleFromXML(xml.getChild(0), null); |
||
226 | } |
||
227 | 25243 | vcaballero | if (xml.contains("sizeW")) |
228 | sz=new Dimension(xml.getIntProperty("sizeW"),xml.getIntProperty("sizeH")); |
||
229 | 25807 | vcaballero | } |
230 | 22833 | vcaballero | |
231 | public Rectangle2D[] getTextBounds() { |
||
232 | return (Rectangle2D[]) textFieldAreas.toArray(new Rectangle2D[textFieldAreas.size()]); |
||
233 | } |
||
234 | |||
235 | public void drawInsideRectangle(Graphics2D g, Rectangle r) throws SymbolDrawingException { |
||
236 | 23417 | vcaballero | if(getBackgroundFileStyle() != null) |
237 | getBackgroundFileStyle().drawInsideRectangle(g, r); |
||
238 | 22833 | vcaballero | } |
239 | |||
240 | |||
241 | public Dimension getSize() { |
||
242 | 23417 | vcaballero | if (sz == null && getBackgroundFileStyle() != null) { |
243 | Rectangle bgBounds = getBackgroundFileStyle().getBounds();
|
||
244 | 22833 | vcaballero | setSize(bgBounds.getWidth(), bgBounds.getHeight()); |
245 | 25243 | vcaballero | }else if (sz==null) |
246 | sz = defaultSize; |
||
247 | 22833 | vcaballero | return sz;
|
248 | } |
||
249 | |||
250 | public Point2D getMarkerPoint() { |
||
251 | return markerPoint;
|
||
252 | } |
||
253 | |||
254 | public void setMarkerPoint(Point2D p) throws IllegalArgumentException { |
||
255 | if (p.getX()<0 || p.getX()>1) |
||
256 | throw new IllegalArgumentException("X must be >=0 and <=1 ("+p.getX()+")"); |
||
257 | if (p.getY()<0 || p.getY()>1) |
||
258 | throw new IllegalArgumentException("Y must be >=0 and <=1 ("+p.getY()+")"); |
||
259 | // the marker represents the point labeled in relative percent units
|
||
260 | this.markerPoint = p;
|
||
261 | } |
||
262 | |||
263 | |||
264 | 22953 | vcaballero | public void drawOutline(Graphics2D g, Rectangle r) throws SymbolDrawingException { |
265 | 23417 | vcaballero | if(getBackgroundFileStyle() != null) |
266 | getBackgroundFileStyle().drawOutline(g, r); |
||
267 | 22833 | vcaballero | |
268 | final double[] xy = new double[2]; |
||
269 | // draw the pointer
|
||
270 | { |
||
271 | xy[0] = markerPoint.getX();
|
||
272 | xy[1] = markerPoint.getY();
|
||
273 | |||
274 | 22953 | vcaballero | int x = (int) Math.round(r.width * xy[0]); |
275 | int y = (int) Math.round(r.height * xy[1]); |
||
276 | |||
277 | 22833 | vcaballero | int size = 7; |
278 | g.setColor(Color.ORANGE.darker());
|
||
279 | g.fillOval(x, y, size, size); |
||
280 | g.setColor(Color.BLACK.brighter());
|
||
281 | g.drawString(Messages.getString("labeled_point"), x + size + 10, y + size); |
||
282 | g.setColor(Color.BLACK);
|
||
283 | g.drawLine(x-size, (int) (y+(size*0.5)), x+2*size-1, (int) (y+(size*0.5))); |
||
284 | g.drawLine((int) (x+(size*0.5)), y-size, (int) (x+(size*0.5)), y+2*size-1); |
||
285 | } |
||
286 | |||
287 | // draw the text fields
|
||
288 | if (textFieldAreas.size() > 0) { |
||
289 | SimpleFillSymbol sym = new SimpleFillSymbol();
|
||
290 | Color c = Color.blue.brighter().brighter(); |
||
291 | |||
292 | sym.setFillColor(new Color(c.getRed(), c.getGreen(), c.getBlue(), 100)); |
||
293 | SimpleLineSymbol outline = new SimpleLineSymbol();
|
||
294 | c = Color.BLACK;
|
||
295 | outline.setLineColor(new Color(c.getRed(), c.getGreen(), c.getBlue(), 100)); |
||
296 | sym.setOutline(outline); |
||
297 | for (int i = 0; i < textFieldAreas.size(); i++) { |
||
298 | 25807 | vcaballero | //FIXME: Esto es un parche, habr?a que cambiar el API de los simbolos y/o estilos
|
299 | //pero mientras tanto
|
||
300 | if(getBackgroundFileStyle() == null){ |
||
301 | Rectangle2D textFieldArea = (Rectangle2D) textFieldAreas.get(i); |
||
302 | xy[0] = textFieldArea.getX();
|
||
303 | xy[1] = textFieldArea.getY();
|
||
304 | 22833 | vcaballero | |
305 | 25807 | vcaballero | int x = (int) Math.round(((r.width) * xy[0])); |
306 | int y = (int) Math.round((r.height) * xy[1]); |
||
307 | 22953 | vcaballero | |
308 | 25807 | vcaballero | xy[0] = textFieldArea.getMaxX();
|
309 | xy[1] = textFieldArea.getMaxY();
|
||
310 | 22833 | vcaballero | |
311 | 25807 | vcaballero | int width = (int) Math.round((r.width * xy[0]) -x); |
312 | int height = (int) Math.round((r.height * xy[1]) - y) ; |
||
313 | 22953 | vcaballero | |
314 | 25807 | vcaballero | Rectangle aux = new Rectangle(x, y, width, height); |
315 | FShape shp = new FPolygon2D(new GeneralPathX(aux)); |
||
316 | sym.draw(g, null, shp, null); |
||
317 | g.setColor(Color.BLACK);
|
||
318 | g.drawString(String.valueOf(i+1), x+5, y + 10); // start with 1 |
||
319 | } else {
|
||
320 | double xOffset = 0; |
||
321 | double yOffset = 0; |
||
322 | double scale = 1; |
||
323 | Dimension backgroundBounds = getSize();
|
||
324 | if (backgroundBounds.getWidth()>backgroundBounds.getHeight()) {
|
||
325 | scale = r.getWidth()/backgroundBounds.getWidth(); |
||
326 | yOffset = 0.5*(r.getHeight() - backgroundBounds.getHeight()*scale);
|
||
327 | } else {
|
||
328 | scale = r.getHeight()/backgroundBounds.getHeight(); |
||
329 | xOffset = 0.5*(r.getWidth() - backgroundBounds.getWidth()*scale);
|
||
330 | } |
||
331 | |||
332 | Rectangle2D textFieldArea = (Rectangle2D) textFieldAreas.get(i); |
||
333 | xy[0] = textFieldArea.getX();
|
||
334 | xy[1] = textFieldArea.getY();
|
||
335 | |||
336 | int x = (int) Math.round(xy[0]*backgroundBounds.getWidth()*scale+xOffset); |
||
337 | int y = (int) Math.round(xy[1]*backgroundBounds.getHeight()*scale+yOffset); |
||
338 | |||
339 | xy[0] = textFieldArea.getMaxX();
|
||
340 | xy[1] = textFieldArea.getMaxY();
|
||
341 | |||
342 | int width = (int) Math.round((xy[0]*backgroundBounds.getWidth()*scale+xOffset)-x); |
||
343 | int height = (int) Math.round((xy[1]*backgroundBounds.getHeight()*scale+yOffset)-y); |
||
344 | |||
345 | Rectangle aux = new Rectangle(x, y, width, height); |
||
346 | FShape shp = new FPolygon2D(new GeneralPathX(aux)); |
||
347 | sym.draw(g, null, shp, null); |
||
348 | g.setColor(Color.BLACK);
|
||
349 | g.drawString(String.valueOf(i+1), x+5, y + 10); // start with 1 |
||
350 | |||
351 | } |
||
352 | 22833 | vcaballero | } |
353 | } |
||
354 | } |
||
355 | |||
356 | public void setTextFieldArea(int index, Rectangle2D rect) { |
||
357 | textFieldAreas.set(index, rect); |
||
358 | } |
||
359 | |||
360 | public void addTextFieldArea(Rectangle2D rect) { |
||
361 | textFieldAreas.add(rect); |
||
362 | } |
||
363 | |||
364 | public void deleteTextFieldArea(int index) { |
||
365 | textFieldAreas.remove(index); |
||
366 | } |
||
367 | |||
368 | public void setSize(double width, double height) { |
||
369 | sz = new Dimension( (int) Math.round(width), (int) Math.round(height)); |
||
370 | } |
||
371 | 22953 | vcaballero | |
372 | 23417 | vcaballero | public BackgroundFileStyle getBackgroundFileStyle() {
|
373 | 22953 | vcaballero | return background;
|
374 | } |
||
375 | |||
376 | 23417 | vcaballero | public void setBackgroundFileStyle(BackgroundFileStyle background) { |
377 | 22953 | vcaballero | this.background = background;
|
378 | } |
||
379 | 23417 | vcaballero | |
380 | public void setBackground(XMLEntity background) { |
||
381 | XMLEntity xml = getXMLEntity(); |
||
382 | |||
383 | if (xml.firstChild("id", "LabelStyle") != null) { |
||
384 | xml.removeChild(xml.firstIndexOfChild("id", "LabelStyle")); |
||
385 | } |
||
386 | XMLEntity xmlBG = background; |
||
387 | xmlBG.putProperty("id", "LabelStyle"); |
||
388 | xml.addChild(xmlBG); |
||
389 | setXMLEntity(xml); |
||
390 | } |
||
391 | |||
392 | public XMLEntity getBackground() {
|
||
393 | return this.background.getXMLEntity(); |
||
394 | } |
||
395 | 22833 | vcaballero | } |