svn-gvsig-desktop / trunk / org.gvsig.desktop / org.gvsig.desktop.plugin / org.gvsig.labeling.app / org.gvsig.labeling.app.mainplugin / src / main / java / org / gvsig / labeling / symbol / SmartTextSymbol.java @ 45526
History | View | Annotate | Download (20 KB)
1 |
package org.gvsig.labeling.symbol; |
---|---|
2 |
|
3 |
import java.awt.BasicStroke; |
4 |
import java.awt.Color; |
5 |
import java.awt.Font; |
6 |
import java.awt.Graphics2D; |
7 |
import java.awt.Rectangle; |
8 |
import java.awt.RenderingHints; |
9 |
import java.awt.Shape; |
10 |
import java.awt.font.FontRenderContext; |
11 |
import java.awt.font.GlyphVector; |
12 |
import java.awt.font.LineMetrics; |
13 |
import java.awt.geom.AffineTransform; |
14 |
import org.apache.commons.lang3.StringUtils; |
15 |
|
16 |
import org.gvsig.compat.print.PrintAttributes; |
17 |
import org.gvsig.fmap.dal.feature.Feature; |
18 |
import org.gvsig.fmap.geom.Geometry; |
19 |
import org.gvsig.fmap.geom.Geometry.SUBTYPES; |
20 |
import org.gvsig.fmap.geom.Geometry.TYPES; |
21 |
import org.gvsig.fmap.geom.GeometryLocator; |
22 |
import org.gvsig.fmap.geom.GeometryManager; |
23 |
import org.gvsig.fmap.geom.exception.CreateGeometryException; |
24 |
import org.gvsig.fmap.geom.primitive.Envelope; |
25 |
import org.gvsig.fmap.geom.primitive.GeneralPathX; |
26 |
import org.gvsig.fmap.geom.primitive.Point; |
27 |
import org.gvsig.fmap.geom.primitive.Surface; |
28 |
import org.gvsig.fmap.mapcontext.MapContextLocator; |
29 |
import org.gvsig.fmap.mapcontext.ViewPort; |
30 |
import org.gvsig.fmap.mapcontext.rendering.legend.styling.IPlacementConstraints; |
31 |
import org.gvsig.fmap.mapcontext.rendering.symbols.CartographicSupport; |
32 |
import org.gvsig.fmap.mapcontext.rendering.symbols.ISymbol; |
33 |
import org.gvsig.fmap.mapcontext.rendering.symbols.ITextSymbol; |
34 |
import org.gvsig.fmap.mapcontext.rendering.symbols.SymbolDrawingException; |
35 |
import org.gvsig.fmap.mapcontext.rendering.symbols.SymbolPreferences; |
36 |
import org.gvsig.labeling.placements.PointPlacementConstraints; |
37 |
import org.gvsig.symbology.fmap.mapcontext.rendering.symbol.fill.IFillSymbol; |
38 |
import org.gvsig.symbology.fmap.mapcontext.rendering.symbol.text.ISimpleTextSymbol; |
39 |
import org.gvsig.tools.ToolsLocator; |
40 |
import org.gvsig.tools.dynobject.DynStruct; |
41 |
import org.gvsig.tools.persistence.PersistenceManager; |
42 |
import org.gvsig.tools.persistence.PersistentState; |
43 |
import org.gvsig.tools.persistence.exception.PersistenceException; |
44 |
import org.gvsig.tools.task.Cancellable; |
45 |
import org.slf4j.Logger; |
46 |
import org.slf4j.LoggerFactory; |
47 |
|
48 |
import org.gvsig.symbology.fmap.mapcontext.rendering.legend.styling.TextPath; |
49 |
|
50 |
|
51 |
/**
|
52 |
* Class used to create symbols composed using a text defined by
|
53 |
* the user.This text can be edited (changing the color, the font of the characters, and
|
54 |
* the rotation of the text)and has the property that can follow a path.If this path
|
55 |
* does not exist, the text is treated as a simpletextsymbol (when is drawn).
|
56 |
* @author jaume dominguez faus - jaume.dominguez@iver.es
|
57 |
*/
|
58 |
public class SmartTextSymbol implements ISimpleTextSymbol, CartographicSupport { |
59 |
|
60 |
private static final Logger logger = LoggerFactory.getLogger( |
61 |
SmartTextSymbol.class); |
62 |
// ===========================
|
63 |
public static final String SMART_TEXT_SYMBOL_PERSISTENCE_DEFINITION_NAME = |
64 |
"SMART_TEXT_SYMBOL_PERSISTENCE_DEFINITION_NAME";
|
65 |
|
66 |
private static final String FIELD_UNIT = "unit"; |
67 |
private static final String FIELD_REFERENCE_SYSTEM = "referenceSystem"; |
68 |
private static final String FIELD_IS_SHAPE_VISIBLE = "isShapeVisible"; |
69 |
private static final String FIELD_DESCRIPTION = "description"; |
70 |
private static final String FIELD_TEXT = "text"; |
71 |
private static final String FIELD_FONT = "font"; |
72 |
private static final String FIELD_TEXT_COLOR = "textColor"; |
73 |
private static final String FIELD_ROTATION = "rotation"; |
74 |
private static final String FIELD_AUTO_RESIZE = "autoResize"; |
75 |
// ====================================
|
76 |
private static final String FIELD_HAS_HALO = "hasHalo"; |
77 |
private static final String FIELD_HALO_COLOR = "haloColor"; |
78 |
private static final String FIELD_HALO_WIDTH = "haloWidth"; |
79 |
// ====================================
|
80 |
/*
|
81 |
public static final int SYMBOL_STYLE_TEXTALIGNMENT_LEFT = 0;
|
82 |
public static final int SYMBOL_STYLE_TEXTALIGNMENT_RIGHT = 1;
|
83 |
public static final int SYMBOL_STYLE_TEXTALIGNMENT_CENTERED = 2;
|
84 |
*/
|
85 |
|
86 |
// ===========================
|
87 |
private static GeometryManager geoman = GeometryLocator.getGeometryManager(); |
88 |
|
89 |
private String text; |
90 |
private FontRenderContext frc = new FontRenderContext( |
91 |
new AffineTransform(), false, true); |
92 |
|
93 |
// Background: ITextBackground
|
94 |
// Case
|
95 |
private double characterSpacing; |
96 |
private double characterWidth; |
97 |
// Direction
|
98 |
private IFillSymbol fillSymbol;
|
99 |
private double flipAngle; |
100 |
// boolean kerning;
|
101 |
private double leading; |
102 |
// Position: textPosition
|
103 |
private Color ShadowColor; |
104 |
private double ShadowXOffset; |
105 |
private double ShadowYOffset; |
106 |
// TypeSetting: Boolean
|
107 |
private double wordSpacing; |
108 |
// ISimpleTextSymbol : ITextSymbol
|
109 |
// BreakCharacter: Long
|
110 |
// Clip: Boolean
|
111 |
private TextPath textPath;
|
112 |
private double xOffset; |
113 |
private double yOffset; |
114 |
private double angle; |
115 |
// Color: IColor
|
116 |
|
117 |
// HorizontalAlignment:
|
118 |
// esriTextHorizontalAlignment
|
119 |
private boolean rightToLeft; |
120 |
// VerticalAlignment
|
121 |
private double maskSize; |
122 |
// MaskStyle
|
123 |
private IFillSymbol maskSymbol;
|
124 |
private double margin; |
125 |
private int alignment; |
126 |
private boolean kerning = false; |
127 |
private TextPath tp;
|
128 |
private IPlacementConstraints constraints;
|
129 |
|
130 |
private boolean shapeVisible = true; |
131 |
private int unit = -1; |
132 |
private int referenceSystem = CartographicSupport.WORLD; |
133 |
private double rotation = 0; |
134 |
private String desc = ""; |
135 |
private Color textColor = Color.BLACK; |
136 |
private Font font; |
137 |
private boolean autoresize = false; |
138 |
|
139 |
// =======================
|
140 |
|
141 |
private boolean hasHalo = false; |
142 |
private Color haloColor = Color.WHITE; |
143 |
private float haloWidth = 3; |
144 |
private BasicStroke haloStroke = new BasicStroke( |
145 |
6, BasicStroke.CAP_ROUND, BasicStroke.JOIN_ROUND); |
146 |
|
147 |
// =======================
|
148 |
|
149 |
|
150 |
public SmartTextSymbol(ITextSymbol sym, IPlacementConstraints constraints) {
|
151 |
|
152 |
// if(sym instanceof SimpleTextSymbol){
|
153 |
// SimpleTextSymbol mySym = (SimpleTextSymbol)sym;
|
154 |
|
155 |
this.setAutoresizeEnabled(sym.isAutoresizeEnabled());
|
156 |
this.setDescription(sym.getDescription());
|
157 |
this.setFont(sym.getFont());
|
158 |
this.setFontSize(sym.getFont().getSize());
|
159 |
this.setIsShapeVisible(sym.isShapeVisible());
|
160 |
this.setText(sym.getText());
|
161 |
this.setTextColor(sym.getTextColor());
|
162 |
|
163 |
this.setDrawWithHalo(sym.isDrawWithHalo());
|
164 |
this.setHaloColor(sym.getHaloColor());
|
165 |
this.setHaloWidth(sym.getHaloWidth());
|
166 |
|
167 |
this.constraints = constraints;
|
168 |
|
169 |
setCharacterSpacing(2); //??? |
170 |
setWordSpacing(TextPath.DEFAULT_WORD_SPACING); |
171 |
boolean rtl = false; // right to left text |
172 |
if (constraints.isAtTheBeginingOfLine()) {
|
173 |
if (rtl) {
|
174 |
|
175 |
setAlignment(ITextSymbol.SYMBOL_STYLE_ALIGNMENT_RIGHT); |
176 |
} |
177 |
else {
|
178 |
setAlignment(ITextSymbol.SYMBOL_STYLE_ALIGNMENT_LEFT); |
179 |
} |
180 |
} |
181 |
else if (constraints.isAtTheEndOfLine()) { |
182 |
if (rtl) {
|
183 |
setAlignment(ITextSymbol.SYMBOL_STYLE_ALIGNMENT_LEFT); |
184 |
} |
185 |
else {
|
186 |
setAlignment(ITextSymbol.SYMBOL_STYLE_ALIGNMENT_RIGHT); |
187 |
} |
188 |
} |
189 |
else { //constraints.isInTheMiddleOfLine() or constraints.isAtBestOfLine() |
190 |
setAlignment(ITextSymbol.SYMBOL_STYLE_ALIGNMENT_CENTERED); |
191 |
} |
192 |
setKerning(false);
|
193 |
setRightToLeft(rtl); |
194 |
// }
|
195 |
} |
196 |
|
197 |
|
198 |
public void setIsShapeVisible(boolean v) { |
199 |
this.shapeVisible = v;
|
200 |
} |
201 |
|
202 |
public boolean isShapeVisible() { |
203 |
return shapeVisible;
|
204 |
} |
205 |
|
206 |
|
207 |
|
208 |
public SmartTextSymbol() {
|
209 |
PointPlacementConstraints pc = new PointPlacementConstraints();
|
210 |
this.constraints = pc;
|
211 |
|
212 |
SymbolPreferences preferences = |
213 |
MapContextLocator.getSymbolManager().getSymbolPreferences(); |
214 |
font = preferences.getDefaultSymbolFont(); |
215 |
textColor = preferences.getDefaultSymbolColor(); |
216 |
} |
217 |
|
218 |
/**
|
219 |
* Draws the text according. If this symbol has the text path set, then
|
220 |
* it is used as the text line, otherwise shp <b>must be an FPoint2D</b>
|
221 |
* indicating the starting point of the text and then the text will
|
222 |
* be rendered from there and following the rotation previously set.
|
223 |
*/
|
224 |
|
225 |
public void draw(Graphics2D g, AffineTransform affineTransform, |
226 |
Geometry geom, Feature f, Cancellable cancel) { |
227 |
|
228 |
if (!isShapeVisible()) return; |
229 |
|
230 |
setMargin(0);
|
231 |
if ( StringUtils.isEmpty(text) ) {
|
232 |
return;
|
233 |
} |
234 |
|
235 |
char[] text_chars = text.toCharArray(); |
236 |
tp = new TextPath(g, geom, text_chars, getFont(),
|
237 |
(float) characterSpacing, (float) characterWidth, kerning, |
238 |
(float) leading, alignment, (float) wordSpacing, (float) margin, rightToLeft); |
239 |
Font font = getFont();
|
240 |
g.setFont(font); |
241 |
FontRenderContext frc = g.getFontRenderContext();
|
242 |
LineMetrics lineMetrics = font.getLineMetrics(getText(), frc);
|
243 |
|
244 |
// GlyphVector glyph = font.layoutGlyphVector(frc, charText, 0, charText.length, Font.LAYOUT_NO_START_CONTEXT);
|
245 |
double cons = 0; |
246 |
|
247 |
/* Repartimos el leading (espacio de separaci?n entre lineas)
|
248 |
* arriba y abajo para que exista la misma separaci?n entre la
|
249 |
* caja de la letra y la linea tanto si se dibuja por abajo como
|
250 |
* si se dibuja por arriba.
|
251 |
*/
|
252 |
if(this.constraints.isAboveTheLine()) { |
253 |
cons = lineMetrics.getDescent()+lineMetrics.getLeading()/2;
|
254 |
} |
255 |
else if (this.constraints.isBelowTheLine()) { |
256 |
cons = -(lineMetrics.getAscent()+lineMetrics.getLeading()/2);
|
257 |
} |
258 |
/* Dibujamos la letra de tal manera que el centro de la caja de letra
|
259 |
* coincida con la linea
|
260 |
*/
|
261 |
else if(this.constraints.isOnTheLine()) { |
262 |
// cons = lineMetrics.getDescent()+(lineMetrics.getLeading()/2)-(lineMetrics.getHeight()/2);
|
263 |
cons = lineMetrics.getDescent()+lineMetrics.getLeading()-(lineMetrics.getHeight()/2);
|
264 |
} |
265 |
|
266 |
double[] coords = null; // tp.nextPosForGlyph(0); |
267 |
|
268 |
for (int i = 0; i < tp.getGlyphCount(); i++) { |
269 |
coords = tp.nextPosForGlyph(i); |
270 |
if (coords[0] == TextPath.NO_POS || coords[1] == TextPath.NO_POS) |
271 |
continue;
|
272 |
|
273 |
// move the label 'cons" units above/below the line
|
274 |
double xOffset = cons * Math.sin(coords[2]); |
275 |
double yOffset = cons * Math.cos(coords[2]); |
276 |
|
277 |
g.translate(coords[0]+xOffset, coords[1]-yOffset); |
278 |
g.rotate(coords[2]);
|
279 |
|
280 |
char[] aux = new char[1]; |
281 |
aux[0] = text_chars[i];
|
282 |
if (isDrawWithHalo()) {
|
283 |
GlyphVector glyph = font.createGlyphVector(frc, aux);
|
284 |
Shape outlineChar = glyph.getOutline();
|
285 |
g.setStroke(haloStroke); |
286 |
g.setColor(getHaloColor()); |
287 |
|
288 |
g.setRenderingHint(RenderingHints.KEY_ANTIALIASING,
|
289 |
RenderingHints.VALUE_ANTIALIAS_ON);
|
290 |
g.setRenderingHint(RenderingHints.KEY_INTERPOLATION,
|
291 |
RenderingHints.VALUE_INTERPOLATION_BILINEAR);
|
292 |
// =============================
|
293 |
g.draw(outlineChar); |
294 |
// =============================
|
295 |
g.setRenderingHint(RenderingHints.KEY_ANTIALIASING,
|
296 |
RenderingHints.VALUE_ANTIALIAS_OFF);
|
297 |
} |
298 |
|
299 |
g.setColor(this.getTextColor());
|
300 |
g.drawString(String.valueOf(text_chars[i]), 0, 0); |
301 |
g.rotate(-coords[2]);
|
302 |
g.translate(-coords[0]-xOffset, -coords[1]+yOffset); |
303 |
} |
304 |
} |
305 |
|
306 |
public void getPixExtentPlus( |
307 |
Geometry shp, float[] distances, ViewPort viewPort, int dpi) { |
308 |
|
309 |
/*
|
310 |
* TODO Is this used?
|
311 |
*/
|
312 |
distances[0] = 0; |
313 |
distances[1] = 0; |
314 |
// throw new RuntimeException("Not yet implemented!");
|
315 |
} |
316 |
|
317 |
public int getOnePointRgb() { |
318 |
return getTextColor().getRGB();
|
319 |
} |
320 |
|
321 |
/*
|
322 |
public XMLEntity getXMLEntity() {
|
323 |
XMLEntity xml = new XMLEntity();
|
324 |
xml.putProperty("className", getClassName());
|
325 |
xml.putProperty("desc", getDescription());
|
326 |
xml.putProperty("isShapeVisible", isShapeVisible());
|
327 |
return xml;
|
328 |
}
|
329 |
*/
|
330 |
|
331 |
public int getSymbolType() { |
332 |
return Geometry.TYPES.GEOMETRY;
|
333 |
} |
334 |
|
335 |
public boolean isSuitableFor(Geometry geom) { |
336 |
return geom.getGeometryType().isTypeOf(TYPES.CURVE);
|
337 |
} |
338 |
|
339 |
public void drawInsideRectangle( |
340 |
Graphics2D g,
|
341 |
AffineTransform scaleInstance,
|
342 |
Rectangle r,
|
343 |
PrintAttributes properties) throws SymbolDrawingException {
|
344 |
// let's take the bottom segment of the rectangle as the line
|
345 |
|
346 |
Surface surf = null;
|
347 |
try {
|
348 |
surf = geoman.createSurface(SUBTYPES.GEOM2D); |
349 |
} catch (CreateGeometryException e) {
|
350 |
logger.info("Error while creating surface.", e);
|
351 |
throw new SymbolDrawingException( |
352 |
SymbolDrawingException.UNSUPPORTED_SET_OF_SETTINGS); |
353 |
} |
354 |
surf.addVertex(r.getX(), r.getY()); |
355 |
surf.addVertex(r.getX() + r.getWidth(), r.getY()); |
356 |
|
357 |
if (properties == null) { |
358 |
draw(g, scaleInstance, surf, null, null); |
359 |
} else {
|
360 |
print(g, scaleInstance, surf, properties); |
361 |
} |
362 |
} |
363 |
|
364 |
|
365 |
/*
|
366 |
public void setXMLEntity(XMLEntity xml) {
|
367 |
setFont(new Font("Arial", Font.PLAIN, 18));
|
368 |
setText("this is my TEST text that follows a line");
|
369 |
setDescription(xml.getStringProperty("desc"));
|
370 |
setIsShapeVisible(xml.getBooleanProperty("isShapeVisible"));
|
371 |
|
372 |
}
|
373 |
*/
|
374 |
|
375 |
public void setText(String txt) { |
376 |
this.text = txt;
|
377 |
} |
378 |
|
379 |
public String getText() { |
380 |
return text;
|
381 |
} |
382 |
|
383 |
public void setCharacterSpacing(double charSpacing) { |
384 |
this.characterSpacing = charSpacing;
|
385 |
} |
386 |
|
387 |
public void setWordSpacing(double wordSpacing) { |
388 |
this.wordSpacing = wordSpacing;
|
389 |
} |
390 |
|
391 |
public void setAlignment(int alignment) { |
392 |
this.alignment = alignment;
|
393 |
} |
394 |
|
395 |
public void setKerning(boolean kerning) { |
396 |
this.kerning = kerning;
|
397 |
} |
398 |
|
399 |
public void setMargin(double margin) { |
400 |
this.margin = margin;
|
401 |
} |
402 |
|
403 |
public void setRightToLeft(boolean rightToLeft) { |
404 |
this.rightToLeft = rightToLeft;
|
405 |
} |
406 |
|
407 |
// ==============================================
|
408 |
// ==============================================
|
409 |
// ==============================================
|
410 |
|
411 |
|
412 |
public ISymbol getSymbolForSelection() {
|
413 |
return this; |
414 |
} |
415 |
|
416 |
public boolean isOneDotOrPixel(Geometry geom, |
417 |
double[] positionOfDotOrPixel, ViewPort viewPort, int dpi) { |
418 |
|
419 |
int type = geom.getType();
|
420 |
switch (type) {
|
421 |
case Geometry.TYPES.NULL:
|
422 |
case Geometry.TYPES.POINT:
|
423 |
case Geometry.TYPES.MULTIPOINT:
|
424 |
return false; |
425 |
default:
|
426 |
Envelope geomBounds = geom.getEnvelope(); |
427 |
double dist1Pixel = viewPort.getDist1pixel();
|
428 |
|
429 |
float[] distances = new float[2]; |
430 |
this.getPixExtentPlus(geom, distances, viewPort, dpi);
|
431 |
|
432 |
boolean onePoint =
|
433 |
((geomBounds.getLength(0) + distances[0] <= dist1Pixel) |
434 |
&& (geomBounds.getLength(1) + distances[1] <= dist1Pixel)); |
435 |
|
436 |
if (onePoint) {
|
437 |
positionOfDotOrPixel[0] = geomBounds.getMinimum(0); |
438 |
positionOfDotOrPixel[1] = geomBounds.getMinimum(1); |
439 |
} |
440 |
return onePoint;
|
441 |
} |
442 |
} |
443 |
|
444 |
|
445 |
|
446 |
public String getDescription() { |
447 |
return desc;
|
448 |
} |
449 |
|
450 |
|
451 |
public void setDescription(String d) { |
452 |
desc = d; |
453 |
} |
454 |
|
455 |
|
456 |
public Color getColor() { |
457 |
return this.getTextColor(); |
458 |
} |
459 |
|
460 |
|
461 |
public void setColor(Color color) { |
462 |
this.setTextColor(color);
|
463 |
} |
464 |
|
465 |
|
466 |
public void print(Graphics2D g, AffineTransform at, Geometry geom, |
467 |
PrintAttributes properties) { |
468 |
|
469 |
/*
|
470 |
* TODO Use properties
|
471 |
* (perhaps when using things of CartographicSupport)
|
472 |
*/
|
473 |
this.draw(g, at, geom, null, null); |
474 |
} |
475 |
|
476 |
|
477 |
public void setFont(Font fnt) { |
478 |
this.font = fnt;
|
479 |
} |
480 |
|
481 |
|
482 |
public Font getFont() { |
483 |
return font;
|
484 |
} |
485 |
|
486 |
|
487 |
public Color getTextColor() { |
488 |
return this.textColor; |
489 |
} |
490 |
|
491 |
|
492 |
public void setTextColor(Color color) { |
493 |
this.textColor = color;
|
494 |
} |
495 |
|
496 |
|
497 |
public void setFontSize(double d) { |
498 |
Font newFont = new Font( |
499 |
font.getName(), |
500 |
font.getStyle(), |
501 |
Math.round((float) d)); |
502 |
this.font = newFont;
|
503 |
} |
504 |
|
505 |
|
506 |
public Geometry getTextWrappingShape(Point p) { |
507 |
|
508 |
Font font = getFont();
|
509 |
GlyphVector gv = font.createGlyphVector(frc, text);
|
510 |
|
511 |
Shape shape = gv.getOutline((float) p.getX(), (float) p.getY()); |
512 |
Geometry myFShape; |
513 |
try {
|
514 |
myFShape = geoman.createSurface(new GeneralPathX(shape
|
515 |
.getBounds2D().getPathIterator(null)), SUBTYPES.GEOM2D);
|
516 |
myFShape.transform(AffineTransform.getTranslateInstance(p.getX(), p.getY()));
|
517 |
|
518 |
if (rotation != 0) { |
519 |
myFShape.transform(AffineTransform.getRotateInstance(rotation));
|
520 |
} |
521 |
return myFShape;
|
522 |
} catch (CreateGeometryException e) {
|
523 |
logger.error("Error creating a surface", e);
|
524 |
} |
525 |
return null; |
526 |
} |
527 |
|
528 |
|
529 |
public Rectangle getBounds() { |
530 |
|
531 |
Rectangle bounds = null; |
532 |
try {
|
533 |
Geometry aux = getTextWrappingShape(geoman.createPoint(0,0, SUBTYPES.GEOM2D)); |
534 |
Envelope env = aux.getEnvelope(); |
535 |
bounds = new Rectangle( |
536 |
(int) env.getMinimum(0), |
537 |
(int) env.getMinimum(1), |
538 |
(int) env.getLength(0), |
539 |
(int) env.getLength(1)); |
540 |
} catch (CreateGeometryException e) {
|
541 |
logger.error("Error creating a point", e);
|
542 |
} |
543 |
return bounds;
|
544 |
} |
545 |
|
546 |
public double getRotation() { |
547 |
return this.rotation; |
548 |
} |
549 |
|
550 |
|
551 |
public void setRotation(double rot) { |
552 |
this.rotation = rot;
|
553 |
} |
554 |
|
555 |
public void setAutoresizeEnabled(boolean ar) { |
556 |
autoresize = ar; |
557 |
} |
558 |
|
559 |
|
560 |
public boolean isAutoresizeEnabled() { |
561 |
return autoresize;
|
562 |
} |
563 |
|
564 |
|
565 |
public Color getHaloColor() { |
566 |
return this.haloColor; |
567 |
} |
568 |
|
569 |
|
570 |
public void setHaloColor(Color co) { |
571 |
this.haloColor = co;
|
572 |
} |
573 |
|
574 |
|
575 |
public float getHaloWidth() { |
576 |
return this.haloWidth; |
577 |
} |
578 |
|
579 |
|
580 |
public void setHaloWidth(float w) { |
581 |
this.haloWidth = w;
|
582 |
this.haloStroke = new BasicStroke( |
583 |
2*haloWidth, BasicStroke.CAP_ROUND, BasicStroke.JOIN_ROUND); |
584 |
} |
585 |
|
586 |
|
587 |
public boolean isDrawWithHalo() { |
588 |
return this.hasHalo; |
589 |
} |
590 |
|
591 |
|
592 |
public void setDrawWithHalo(boolean h) { |
593 |
this.hasHalo = h;
|
594 |
} |
595 |
|
596 |
// ==============================
|
597 |
|
598 |
|
599 |
public void setUnit(int unitIndex) { |
600 |
unit = unitIndex; |
601 |
} |
602 |
|
603 |
|
604 |
public int getUnit() { |
605 |
return unit;
|
606 |
} |
607 |
|
608 |
|
609 |
public int getReferenceSystem() { |
610 |
return this.referenceSystem; |
611 |
} |
612 |
|
613 |
|
614 |
public void setReferenceSystem(int rs) { |
615 |
this.referenceSystem = rs;
|
616 |
} |
617 |
|
618 |
|
619 |
public void setCartographicSize(double cartographicSize, Geometry geom) { |
620 |
setFontSize(cartographicSize); |
621 |
} |
622 |
|
623 |
public double toCartographicSize(ViewPort viewPort, double dpi, Geometry geom) { |
624 |
double oldSize = getFont().getSize();
|
625 |
setCartographicSize(getCartographicSize(viewPort, dpi, geom), geom); |
626 |
return oldSize;
|
627 |
} |
628 |
|
629 |
public double getCartographicSize(ViewPort viewPort, double dpi, Geometry geom) { |
630 |
return SymbolUtils. getCartographicLength(
|
631 |
this, getFont().getSize(), viewPort, dpi);
|
632 |
} |
633 |
|
634 |
// ========================
|
635 |
|
636 |
public Object clone() throws CloneNotSupportedException { |
637 |
return super.clone(); |
638 |
} |
639 |
|
640 |
// ==========================
|
641 |
|
642 |
public static void registerPersistent() { |
643 |
PersistenceManager manager = ToolsLocator.getPersistenceManager(); |
644 |
if( manager.getDefinition(SMART_TEXT_SYMBOL_PERSISTENCE_DEFINITION_NAME)==null ) { |
645 |
DynStruct definition = manager.addDefinition( |
646 |
SmartTextSymbol.class, |
647 |
SMART_TEXT_SYMBOL_PERSISTENCE_DEFINITION_NAME, |
648 |
SMART_TEXT_SYMBOL_PERSISTENCE_DEFINITION_NAME+" Persistence definition",
|
649 |
null,
|
650 |
null
|
651 |
); |
652 |
|
653 |
definition.addDynFieldString(FIELD_DESCRIPTION).setMandatory(true);
|
654 |
definition.addDynFieldBoolean(FIELD_IS_SHAPE_VISIBLE).setMandatory(true);
|
655 |
definition.addDynFieldInt(FIELD_REFERENCE_SYSTEM).setMandatory(true);
|
656 |
definition.addDynFieldInt(FIELD_UNIT).setMandatory(true);
|
657 |
definition.addDynFieldBoolean(FIELD_AUTO_RESIZE).setMandatory(true);
|
658 |
definition.addDynFieldObject(FIELD_FONT).setClassOfValue(Font.class).setMandatory(true); |
659 |
definition.addDynFieldDouble(FIELD_ROTATION).setMandatory(true);
|
660 |
definition.addDynFieldString(FIELD_TEXT).setMandatory(true);
|
661 |
definition.addDynFieldObject(FIELD_TEXT_COLOR).setClassOfValue(Color.class).setMandatory(true); |
662 |
// halo
|
663 |
definition.addDynFieldBoolean(FIELD_HAS_HALO).setMandatory(true);
|
664 |
definition.addDynFieldObject(FIELD_HALO_COLOR).setClassOfValue( |
665 |
Color.class).setMandatory(true); |
666 |
definition.addDynFieldFloat(FIELD_HALO_WIDTH).setMandatory(true);
|
667 |
} |
668 |
|
669 |
} |
670 |
|
671 |
public void loadFromState(PersistentState state) |
672 |
throws PersistenceException {
|
673 |
setDescription(state.getString(FIELD_DESCRIPTION)); |
674 |
setIsShapeVisible(state.getBoolean(FIELD_IS_SHAPE_VISIBLE)); |
675 |
setReferenceSystem(state.getInt(FIELD_REFERENCE_SYSTEM)); |
676 |
setUnit(state.getInt(FIELD_UNIT)); |
677 |
|
678 |
setAutoresizeEnabled(state.getBoolean(FIELD_AUTO_RESIZE)); |
679 |
setFont((Font) state.get(FIELD_FONT));
|
680 |
setRotation(state.getDouble(FIELD_ROTATION)); |
681 |
setText(state.getString(FIELD_TEXT)); |
682 |
setTextColor((Color) state.get(FIELD_TEXT_COLOR));
|
683 |
// halo
|
684 |
this.setDrawWithHalo(state.getBoolean(FIELD_HAS_HALO));
|
685 |
this.setHaloColor((Color) state.get(FIELD_HALO_COLOR)); |
686 |
this.setHaloWidth(state.getFloat(FIELD_HALO_WIDTH));
|
687 |
} |
688 |
|
689 |
public void saveToState(PersistentState state) throws PersistenceException { |
690 |
state.set(FIELD_DESCRIPTION, getDescription()); |
691 |
state.set(FIELD_IS_SHAPE_VISIBLE, isShapeVisible()); |
692 |
state.set(FIELD_REFERENCE_SYSTEM, getReferenceSystem()); |
693 |
state.set(FIELD_UNIT, getUnit()); |
694 |
|
695 |
state.set(FIELD_AUTO_RESIZE, isAutoresizeEnabled()); |
696 |
state.set(FIELD_FONT, getFont()); |
697 |
state.set(FIELD_ROTATION, getRotation()); |
698 |
state.set(FIELD_TEXT, getText()); |
699 |
state.set(FIELD_TEXT_COLOR, getTextColor()); |
700 |
// halo
|
701 |
state.set(FIELD_HAS_HALO, this.isDrawWithHalo());
|
702 |
state.set(FIELD_HALO_COLOR, this.getHaloColor());
|
703 |
state.set(FIELD_HALO_WIDTH, this.getHaloWidth());
|
704 |
} |
705 |
|
706 |
|
707 |
|
708 |
|
709 |
|
710 |
} |