// **********************************************************************
//
// <copyright>
//
// BBN Technologies
// 10 Moulton Street
// Cambridge, MA 02138
// (617) 873-8000
//
// Copyright (C) BBNT Solutions LLC. All rights reserved.
//
// </copyright>
// **********************************************************************
//
// $Source: /cvs/distapps/openmap/src/openmap/com/bbn/openmap/omGraphics/OMArc.java,v $
// $RCSfile: OMArc.java,v $
// $Revision: 1.5.2.6 $
// $Date: 2009/03/02 18:13:42 $
// $Author: dietrick $
//
// **********************************************************************
package com.bbn.openmap.omGraphics;
import java.awt.Graphics;
import java.awt.Graphics2D;
import java.awt.Point;
import java.awt.Shape;
import java.awt.geom.AffineTransform;
import java.awt.geom.Arc2D;
import java.awt.geom.GeneralPath;
import java.awt.geom.PathIterator;
import java.io.Serializable;
import java.util.ArrayList;
import com.bbn.openmap.LatLonPoint;
import com.bbn.openmap.proj.Cylindrical;
import com.bbn.openmap.proj.Length;
import com.bbn.openmap.proj.ProjMath;
import com.bbn.openmap.proj.Projection;
import com.bbn.openmap.util.Debug;
/**
* Graphic object that represents an arc.
* <p>
* <h3>NOTE:</h3>
* See the <a
* href="com.bbn.openmap.proj.Projection.html#poly_restrictions">
* RESTRICTIONS </a> on Lat/Lon polygons/polylines which apply to arcs
* as well. Not following the guidelines listed may result in
* ambiguous/undefined shapes! Similar assumptions apply to the other
* vector graphics that we define: polys, rects, lines.
* <p>
* These assumptions are virtually the same as those on the more
* generic OMPoly graphic type.
* <p>
*
* @see OMPoly
*/
public class OMArc extends OMGraphic implements Serializable {
/** Horizontal pixel location of the center. */
protected int x1 = 0;
/** Vertical pixel location of the center. */
protected int y1 = 0;
/** Horizontal pixel offset. */
protected int off_x = 0;
/** Vertical pixel offset. */
protected int off_y = 0;
/**
* Center point.
*/
protected LatLonPoint center;
/**
* Radius of arc in radians. For LATLON arc. Note that the methods
* for this class use Decimal Degrees, or ask for a Length object
* to use for units. The radius is converted to radians for
* internal use.
*/
protected float radius = 0.0f;
/**
* The pixel horizontal diameter of the arc. For XY and OFFSET
* arcs.
*/
protected int width = 0;
/**
* The pixel vertical diameter of the arc. For XY and OFFSET arcs.
*/
protected int height = 0;
/**
* The starting angle of the arc in decimal degrees. This is
* defined in decimal degrees because the java.awt.geom.Arc object
* wants it in decimal degrees. 0 is North?
*/
protected float start = 0.0f;
/**
* The angular extent of the arc in decimal degrees.
*/
protected float extent = 360.0f;
/**
* For Arcs, how the arc should be closed when rendered.
* Arc2D.OPEN is the default, Arc2D.PIE and Arc2D.CHORD are
* options.
*
* @see java.awt.geom.Arc2D
*/
protected int arcType = Arc2D.OPEN;
/**
* Used to render arc in Cylindrical projections when the arc
* encompases a pole.
*/
private transient GeneralPath polarShapeLine = null;
/**
* Indicates that the polarShapeLine should be used for rendering.
*/
private transient boolean correctFill = false;
/** Force the correct polar hack. */
private transient boolean correctPolar = false;
/**
* Number of vertices to draw for lat/lon poly-arcs.
*/
protected int nverts;
/**
* The angle by which the circle/ellipse is to be rotated, in
* radians
*/
protected double rotationAngle = DEFAULT_ROTATIONANGLE;
/**
* The simplest constructor for an OMArc, and it expects that all
* fields will be filled in later. Rendertype is
* RENDERTYPE_UNKNOWN.
*/
public OMArc() {
super(RENDERTYPE_UNKNOWN, LINETYPE_UNKNOWN, DECLUTTERTYPE_NONE);
}
/**
* Create an OMArc, positioned with a lat-lon center and x-y axis.
* Rendertype is RENDERTYPE_OFFSET.
*
* @param latPoint latitude of center point, decimal degrees
* @param lonPoint longitude of center point, decimal degrees
* @param w horizontal diameter of arc, pixels
* @param h vertical diameter of arc, pixels
* @param s starting angle of arc, decimal degrees
* @param e angular extent of arc, decimal degrees
*/
public OMArc(float latPoint, float lonPoint, int w, int h, float s, float e) {
this(latPoint, lonPoint, 0, 0, w, h, s, e);
}
/**
* Create a OMArc, positioned with a x-y center with x-y axis.
* Rendertype is RENDERTYPE_XY.
*
* @param x1 window position of center point from left of window,
* in pixels
* @param y1 window position of center point from top of window,
* in pixels
* @param w horizontal diameter of arc, pixels
* @param h vertical diameter of arc, pixels
* @param s starting angle of arc, decimal degrees
* @param e angular extent of arc, decimal degrees. For XY
* rendertype arcs, positive extents go in the
* counter-clockwise direction, matching the
* java.awt.geom.Arc2D convention.
*/
public OMArc(int x1, int y1, int w, int h, float s, float e) {
super(RENDERTYPE_XY, LINETYPE_UNKNOWN, DECLUTTERTYPE_NONE);
this.x1 = x1;
this.y1 = y1;
width = w;
height = h;
start = s;
extent = e;
}
/**
* Create a OMArc, positioned at a Lat-lon location, x-y offset,
* x-y axis. Rendertype is RENDERTYPE_OFFSET.
*
* @param latPoint latitude of center of arc.
* @param lonPoint longitude of center of arc.
* @param offset_x1 # pixels to the right the center will be moved
* from lonPoint.
* @param offset_y1 # pixels down that the center will be moved
* from latPoint.
* @param w horizontal diameter of arc, pixels.
* @param h vertical diameter of arc, pixels.
* @param s starting angle of arc, decimal degrees.
* @param e angular extent of arc, decimal degrees. For Offset
* rendertype arcs, positive extents go in the
* counter-clockwise direction, matching the
* java.awt.geom.Arc2D convention.
*/
public OMArc(float latPoint, float lonPoint, int offset_x1, int offset_y1,
int w, int h, float s, float e) {
super(RENDERTYPE_OFFSET, LINETYPE_UNKNOWN, DECLUTTERTYPE_NONE);
center = new LatLonPoint(latPoint, lonPoint);
off_x = offset_x1;
off_y = offset_y1;
width = w;
height = h;
start = s;
extent = e;
}
/**
* Creates an OMArc with a Lat-lon center and a lat-lon axis.
* Rendertype is RENDERTYPE_LATLON.
*
* @param latPoint latitude of center point, decimal degrees
* @param lonPoint longitude of center point, decimal degrees
* @param radius distance in decimal degrees (converted to radians
* internally).
* @param s starting angle of arc, decimal degrees
* @param e angular extent of arc, decimal degrees. For LATLON
* rendertype arcs, positive extents go in the clockwise
* direction, matching the OpenMap convention in coordinate
* space.
*/
public OMArc(float latPoint, float lonPoint, float radius, float s, float e) {
this(new LatLonPoint(latPoint, lonPoint),
radius,
Length.DECIMAL_DEGREE,
-1,
s,
e);
}
/**
* Create an OMArc with a lat/lon center and a physical distance
* radius. Rendertype is RENDERTYPE_LATLON.
*
* @param latPoint latitude of center of arc in decimal degrees
* @param lonPoint longitude of center of arc in decimal degrees
* @param radius distance
* @param units com.bbn.openmap.proj.Length object.
* @param s starting angle of arc, decimal degrees.
* @param e angular extent of arc, decimal degrees. For LATLON
* rendertype arcs, positive extents go in the clockwise
* direction, matching the OpenMap convention in coordinate
* space.
*/
public OMArc(float latPoint, float lonPoint, float radius, Length units,
float s, float e) {
this(new LatLonPoint(latPoint, lonPoint), radius, units, -1, s, e);
}
/**
* Create an OMArc with a lat/lon center and a physical distance
* radius. Rendertype is RENDERTYPE_LATLON.
*
* @param latPoint latitude of center of arc in decimal degrees
* @param lonPoint longitude of center of arc in decimal degrees
* @param radius distance
* @param units com.bbn.openmap.proj.Length object specifying
* units.
* @param nverts number of vertices for the poly-arc (if < 3,
* value is generated internally)
* @param s starting angle of arc, decimal degrees.
* @param e angular extent of arc, decimal degrees. For LATLON
* rendertype arcs, positive extents go in the clockwise
* direction, matching the OpenMap convention in coordinate
* space.
*/
public OMArc(float latPoint, float lonPoint, float radius, Length units,
int nverts, float s, float e) {
this(new LatLonPoint(latPoint, lonPoint), radius, units, nverts, s, e);
}
/**
* Create an OMArc with a lat/lon center and a physical distance
* radius. Rendertype is RENDERTYPE_LATLON.
*
* @param center LatLon center of arc
* @param radius distance
* @param units com.bbn.openmap.proj.Length object specifying
* units for distance.
* @param nverts number of vertices for the poly-arc(if < 3,
* value is generated internally)
* @param s starting angle of arc, decimal degrees.
* @param e angular extent of arc, decimal degrees. For LATLON
* rendertype arcs, positive extents go in the clockwise
* direction, matching the OpenMap convention in coordinate
* space.
*/
public OMArc(LatLonPoint center, float radius, Length units, int nverts,
float s, float e) {
super(RENDERTYPE_LATLON, LINETYPE_UNKNOWN, DECLUTTERTYPE_NONE);
this.radius = units.toRadians(radius);
this.center = center;
this.nverts = nverts;
this.start = s;
this.extent = e;
}
/**
* Get the x position of the center. This is always meaningful
* only if the render type is RENDERTYPE_XY or RENDERTYPE_OFFSET,
* and meaningful after generation if the RENDERTYPE_LATLON.
*
* @return x position of center.
*/
public int getX() {
return x1;
}
/**
* Get the y position of the center. This is always meaningful
* only if the render type is RENDERTYPE_XY or RENDERTYPE_OFFSET,
* and meaningful after generation if the RENDERTYPE_LATLON.
*
* @return y position of center.
*/
public int getY() {
return y1;
}
/**
* Get the x offset from the center. This is meaningful only if
* the render type is RENDERTYPE_OFFSET.
*
* @return x offset from center.
*/
public int getOffX() {
return off_x;
}
/**
* Get the y position of the center. This is meaningful only if
* the render type is RENDERTYPE_OFFSET.
*
* @return y offset from center.
*/
public int getOffY() {
return off_y;
}
/**
* Get the center LatLonPoint. This is meaningful only if the
* rendertype is RENDERTYPE_LATLON or RENDERTYPE_OFFSET.
*
* @return LatLonPoint position of center.
*/
public LatLonPoint getLatLon() {
return center;
}
/**
* Get the radius. This is meaningful only if the render type is
* RENDERTYPE_LATLON.
*
* @return float radius in decimal degrees
*/
public float getRadius() {
return Length.DECIMAL_DEGREE.fromRadians(radius);
}
/**
* Get the horizontal pixel diameter of the arc. This is
* meaningful only if the render type is RENDERTYPE_XY or
* RENDERTYPE_OFFSET.
*
* @return the horizontal pixel diameter of the arc.
*/
public int getWidth() {
return width;
}
/**
* Get the vertical pixel diameter of the arc. This is meaningful
* only if the render type is RENDERTYPE_XY or RENDERTYPE_OFFSET.
*
* @return the vertical pixel diameter of the arc.
*/
public int getHeight() {
return height;
}
/**
* Get the starting angle of the arc.
*
* @return the starting angle of the arc in decimal degrees.
*/
public float getStartAngle() {
return start;
}
/**
* Get the extent angle of the arc.
*
* @return the angular extent of the arc in decimal degrees. For
* LATLON rendertype arcs, positive extents go in the
* clockwise direction, matching the OpenMap convention in
* coordinate space. For XY and OFFSET rendertype arcs,
* positive extents go in the clockwise direction,
* matching the java.awt.geom.Arc2D convention.
*/
public float getExtentAngle() {
return extent;
}
/**
* Get the number of vertices of the lat/lon arc. This will be
* meaningful only if the render type is RENDERTYPE_XY or
* RENDERTYPE_OFFSET and for LINETYPE_GREATARC or LINETYPE_RHUMB
* line types.
*
* @return int number of segment points
*/
public int getNumVerts() {
return nverts;
}
/**
* Set the x position of the center. This will be meaningful only
* if the render type is RENDERTYPE_XY.
*
* @param value the x position of center.
*/
public void setX(int value) {
if (x1 == value)
return;
x1 = value;
setNeedToRegenerate(true);
}
/**
* Set the y position of the center. This will be meaningful only
* if the render type is RENDERTYPE_XY.
*
* @param value the y position of center.
*/
public void setY(int value) {
if (y1 == value)
return;
y1 = value;
setNeedToRegenerate(true);
}
/**
* Set the x offset from the center. This will be meaningful only
* if the render type is RENDERTYPE_OFFSET.
*
* @param value the x position of center.
*/
public void setOffX(int value) {
if (off_x == value)
return;
off_x = value;
setNeedToRegenerate(true);
}
/**
* Set the y offset from the center. This will be meaningful only
* if the render type is RENDERTYPE_OFFSET.
*
* @param value the y position of center.
*/
public void setOffY(int value) {
if (off_y == value)
return;
off_y = value;
setNeedToRegenerate(true);
}
/**
* Set the latitude and longitude of the center point. This is
* meaningful only if the rendertype is RENDERTYPE_LATLON or
* RENDERTYPE_OFFSET.
*
* @param lat latitude in decimal degrees
* @param lon longitude in decimal degrees
*/
public void setLatLon(float lat, float lon) {
setCenter(new LatLonPoint(lat, lon));
}
/**
* Set the latitude and longitude of the center point. This is
* meaningful only if the rendertype is RENDERTYPE_LATLON or
* RENDERTYPE_OFFSET.
*
* @param p LatLonPoint of center.
*/
public void setCenter(LatLonPoint p) {
if (p.equals(center))
return;
center = p;
setNeedToRegenerate(true);
}
/**
* Get the center LatLonPoint.
*/
public LatLonPoint getCenter() {
return center;
}
/**
* Set the radius. This is meaningful only if the render type is
* RENDERTYPE_LATLON. Note that while the radius is specified as
* decimal degrees, it only means the distance along the ground
* that that number of degrees represents at the equator, *NOT* a
* radius of a number of degrees around a certain location. There
* is a difference.
*
* @param radius float radius in decimal degrees
*/
public void setRadius(float radius) {
this.radius = Length.DECIMAL_DEGREE.toRadians(radius);
setNeedToRegenerate(true);
}
/**
* Set the radius with units. This is meaningful only if the
* render type is RENDERTYPE_LATLON.
*
* @param radius float radius
* @param units Length specifying unit type.
*/
public void setRadius(float radius, Length units) {
this.radius = units.toRadians(radius);
setNeedToRegenerate(true);
}
/**
* Set the horizontal pixel diameter of the arc. This is
* meaningful only if the render type is RENDERTYPE_XY or
* RENDERTYPE_OFFSET.
*
* @param value the horizontial pixel diamter of the arc.
*/
public void setWidth(int value) {
if (width == value)
return;
width = value;
setNeedToRegenerate(true);
}
/**
* Set the vertical pixel diameter of the arc. This is meaningful
* only if the render type is RENDERTYPE_XY or RENDERTYPE_OFFSET.
*
* @param value the vertical pixel diameter of the arc.
*/
public void setHeight(int value) {
if (height == value)
return;
height = value;
setNeedToRegenerate(true);
}
/**
* Set the starting angle the arc.
*
* @param value the starting angle of the arc in decimal degrees.
*/
public void setStart(float value) {
if (start == value)
return;
start = value;
setNeedToRegenerate(true);
}
/**
* Set the angular extent of the arc.
*
* @param value the angular extent of the arc in decimal degrees.
* For LATLON rendertype arcs, positive extents go in the
* clockwise direction, matching the OpenMap convention in
* coordinate space. For XY and OFFSET rendertype arcs,
* positive extents go in the clockwise direction, matching
* the java.awt.geom.Arc2D convention.
*/
public void setExtent(float value) {
if (extent == value)
return;
extent = value;
setNeedToRegenerate(true);
}
/**
* Set the number of vertices of the lat/lon arc. This is
* meaningful only if the render type is RENDERTYPE_LATLON and for
* LINETYPE_GREATARC or LINETYPE_RHUMB line types. If < 1, this
* value is generated internally.
*
* @param nverts number of segment points
*/
public void setNumVerts(int nverts) {
this.nverts = nverts;
}
/**
* Set the ArcType, either Arc2D.OPEN (default), Arc2D.PIE or
* Arc2D.CHORD.
*
* @see java.awt.geom.Arc2D
*/
public void setArcType(int type) {
if (type == Arc2D.PIE || type == Arc2D.CHORD) {
arcType = type;
} else {
arcType = Arc2D.OPEN;
}
}
/**
* Get the ArcType.
*
* @see java.awt.geom.Arc2D
*/
public int getArcType() {
return arcType;
}
/**
* Set the angle by which the arc is to rotated.
*
* @param angle the number of radians the arc is to be rotated.
* Measured clockwise from horizontal. Positive numbers
* move the positive x axis toward the positive y axis.
*/
public void setRotationAngle(double angle) {
this.rotationAngle = angle;
setNeedToRegenerate(true);
}
/**
* Get the current rotation of the arc.
*
* @return the arc rotation.
*/
public double getRotationAngle() {
return rotationAngle;
}
public void setNeedToRegenerate(boolean value) {
super.setNeedToRegenerate(value);
if (value) {
polarShapeLine = null;
correctFill = false;
}
}
/**
* Get the polar-fill-correction-flag.
*
* @return boolean
* @see #setPolarCorrection
*/
public boolean getPolarCorrection() {
return correctPolar;
}
/**
* Set the polar-fill-correction-flag. We don't correctly render
* *filled* arcs/polygons which encompass a pole in Cylindrical
* projections. This method will toggle support for correcting
* this problem. You should only set this on arcs that encompass a
* pole and are drawn with a fill color. You do not need to set
* this if you're only drawing the arc outline.
*
* @param value boolean
* @see OMGraphic#setLineColor
* @see OMGraphic#setFillColor
*/
public void setPolarCorrection(boolean value) {
correctPolar = value;
setNeedToRegenerate(true);
}
/**
* Helper function that helps the generate method figure out if
* the center point should be in the generate shape - if it's not,
* the code knows that there is a problem with the poles, and the
* polar correction code needs to be run.
*/
protected boolean shouldCenterBeInShape() {
// It won't be for CHORD or OPEN arcs
return arcType == Arc2D.PIE;
}
/**
* Prepare the arc for rendering.
*
* @param proj Projection
* @return true if generate was successful
*/
public boolean generate(Projection proj) {
setShape(null);
polarShapeLine = null;
correctFill = false;
if (proj == null) {
Debug.message("omgraphic", "OMArc: null projection in generate!");
return false;
}
GeneralPath gp, gp1, gp2;
PathIterator pi;
AffineTransform af = null;
switch (renderType) {
case RENDERTYPE_OFFSET:
if (!proj.isPlotable(center)) {
setNeedToRegenerate(true);//HMMM not the best flag
return false;
}
Point p1 = proj.forward(center.radlat_,
center.radlon_,
new Point(),
true);
x1 = p1.x + off_x;
y1 = p1.y + off_y;
case RENDERTYPE_XY:
float fwidth = (float) width;
float fheight = (float) height;
float transx = (float) x1;
float transy = (float) y1;
float x = transx - fwidth / 2f;
float y = transy - fheight / 2f;
Shape arcShape = createArcShape(x, y, fwidth, fheight);
if (rotationAngle != DEFAULT_ROTATIONANGLE) {
af = new AffineTransform();
af.rotate(rotationAngle, transx, transy);
}
pi = arcShape.getPathIterator(af);
gp = new GeneralPath();
gp.append(pi, false);
// In X/Y or Offset RenderType, there is only one shape.
setShape(gp);
break;
case RENDERTYPE_LATLON:
ArrayList coordLists = getCoordLists(proj, center, radius, nverts);
Point p = proj.forward(center.radlat_,
center.radlon_,
new Point(),
true);
x1 = p.x;
y1 = p.y;
int size = coordLists.size();
GeneralPath tempShape = null;
for (int i = 0; i < size; i += 2) {
int[] xpoints = (int[]) coordLists.get(i);
int[] ypoints = (int[]) coordLists.get(i + 1);
gp = createShape(xpoints,
ypoints,
(arcType != Arc2D.OPEN || (arcType == Arc2D.OPEN && !isClear(fillPaint))));
if (shape == null) {
setShape(gp);
} else {
((GeneralPath) shape).append(gp, false);
}
correctFill = proj instanceof Cylindrical
&& ((shouldCenterBeInShape() && shape != null && !shape.contains(x1, y1)) || correctPolar);
if (correctFill) {
int[][] alts = doPolarFillCorrection(xpoints,
ypoints,
(center.radlat_ > 0f) ? -1 : proj.getWidth() + 1);
int gp2length = alts[0].length - 2;
gp1 = createShape(alts[0], alts[1], true);
gp2 = createShape(alts[0], alts[1], 0, gp2length, false);
if (tempShape == null || polarShapeLine == null) {
tempShape = gp1;
polarShapeLine = gp2;
} else {
tempShape.append(gp1, false);
polarShapeLine.append(gp2, false);
}
}
}
if (tempShape != null) {
setShape(tempShape);
}
break;
case RENDERTYPE_UNKNOWN:
System.err.println("OMArc.generate(): invalid RenderType");
return false;
}
setNeedToRegenerate(false);
return true;
}
/**
* An internal method designed to fetch the Shape to be used for
* an XY or OFFSET OMArc. This method is smart enough to take the
* calculated position information and make a call to Arc2D.Float
* with start, extent and arcType information.
*/
protected Shape createArcShape(float x, float y, float fwidth, float fheight) {
return new Arc2D.Float(x, y, fwidth, fheight, start, extent, arcType);
}
/**
* An internal method designed to fetch the ArrayList for LATLON
* OMArcs. This method is smart enough to take the calculated
* position information and make a call to Projection.forwardArc()
* with start, extent and arcType information.
*/
protected ArrayList getCoordLists(Projection proj, LatLonPoint center,
float radius, int nverts) {
int at = (arcType == Arc2D.OPEN && !isClear(fillPaint) ? Arc2D.CHORD
: arcType);
return proj.forwardArc(center, /* radians */
true,
radius,
nverts,
ProjMath.degToRad(start),
ProjMath.degToRad(extent),
at);
}
/**
* Return the java.awt.Shape (GeneralPath) that reflects a arc
* that encompases a pole. Used when the projection is
* Cylindrical.
*
* @return a GeneralPath object, or null if it's not needed (which
* is probably most of the time, if the arc doesn't
* include a pole or the projection isn't Cylindrical).
*/
public GeneralPath getPolarShapeLine() {
return polarShapeLine;
}
/**
* Create alternate x,y coordinate arrays for rendering graphics
* the encompass a pole in the Cylindrical projection.
*
* @return a two dimensional array of points. The [0] array is the
* x points, the [1] is the y points.
*/
private int[][] doPolarFillCorrection(int[] xpoints, int[] ypoints, int y1) {
int[][] ret = new int[2][];
int len = xpoints.length;
int[] alt_xpts = new int[len + 2];
int[] alt_ypts = new int[len + 2];
System.arraycopy(xpoints, 0, alt_xpts, 0, len);
System.arraycopy(ypoints, 0, alt_ypts, 0, len);
alt_xpts[len] = alt_xpts[len - 1];
alt_xpts[len + 1] = alt_xpts[0];
alt_ypts[len] = y1;
alt_ypts[len + 1] = alt_ypts[len];
ret[0] = alt_xpts;
ret[1] = alt_ypts;
return ret;
}
/**
* Paint the arc.
*
* @param g Graphics context to render into
*/
public void render(Graphics g) {
if (!isRenderable())
return;
if (!correctFill) {
// super will catch a null shape...
super.render(g);
} else {
// The polarShapeLine will be there only if a shape was
// generated.
// This is getting kicked off because the arc is
// encompassing a pole, so we need to handle it a little
// differently.
if (shouldRenderFill()) {
setGraphicsForFill(g);
fill(g);
//draw texture
if (textureMask != null && textureMask != fillPaint) {
setGraphicsColor(g, textureMask);
fill(g);
}
}
// BUG There is still a bug apparent when, in a
// cylindrical projection, and drawing a arc around the
// south pole. If the center of the arc is below any
// part of the edge of the arc, with the left lower dip
// of the arc on the screen, you get a line drawn from
// the right dip to the left dip. Not sure why. It's an
// unusual case, however.
if (shouldRenderEdge()) {
setGraphicsForEdge(g);
((Graphics2D) g).draw(polarShapeLine);
}
}
}
/**
* @see com.bbn.openmap.omGraphics.OMGraphic#clone()
*/
public Object clone() {
OMArc clone = (OMArc) super.clone();
clone.setNeedToRegenerate(true);
if (center != null)
clone.center = (LatLonPoint) center.clone();
return clone;
}
}