001: package org.geotools.feature.iso.attribute;
002:
003: import org.geotools.feature.iso.AttributeImpl;
004: import org.geotools.geometry.jts.ReferencedEnvelope;
005: import org.opengis.feature.GeometryAttribute;
006: import org.opengis.feature.type.AttributeDescriptor;
007: import org.opengis.feature.type.GeometryType;
008: import org.opengis.geometry.BoundingBox;
009: import org.opengis.referencing.crs.CoordinateReferenceSystem;
010:
011: import com.vividsolutions.jts.geom.Geometry;
012: import com.vividsolutions.jts.io.WKTReader;
013:
014: /**
015: * TODO: rename to GeometricAttribute Provides ...TODO summary sentence
016: * <p>
017: * TODO Description
018: * </p>
019: * <p>
020: * </p>
021: * <p>
022: * Example Use:
023: *
024: * <pre><code>
025: * GeometryAttributeType x = new GeometryAttributeType( ... );
026: * TODO code example
027: * </code></pre>
028: *
029: * </p>
030: *
031: * @author Leprosy
032: * @since 0.3 TODO: test wkt geometry parse.
033: */
034: public class GeometricAttribute extends AttributeImpl implements
035: GeometryAttribute {
036: /** CoordianteSystem used by this GeometryAttributeType */
037: protected CoordinateReferenceSystem coordinateSystem;
038: private BoundingBox bounds;
039:
040: public GeometricAttribute(Object content,
041: AttributeDescriptor descriptor, String id,
042: CoordinateReferenceSystem cs) {
043: super (content, descriptor, id);
044: coordinateSystem = cs;
045:
046: if (!(descriptor.type() instanceof GeometryType)) {
047: throw new IllegalArgumentException(
048: "Expected GeometryType, got " + descriptor);
049: }
050:
051: /*
052: * geometryFactory = cs == null ? CSGeometryFactory.DEFAULT : new
053: * CSGeometryFactory(cs);
054: */
055: /*
056: * coordinateSystem = (cs != null) ? cs :
057: * LocalCoordinateSystem.CARTESIAN; geometryFactory = (cs ==
058: * LocalCoordinateSystem.CARTESIAN) ? CSGeometryFactory.DEFAULT : new
059: * CSGeometryFactory(cs);
060: */
061: }
062:
063: public CoordinateReferenceSystem getCRS() {
064: return coordinateSystem;
065: }
066:
067: public void setCRS(CoordinateReferenceSystem coordinateSystem) {
068: this .coordinateSystem = coordinateSystem;
069: }
070:
071: /*
072: * public GeometryFactory getGeometryFactory() { return geometryFactory; }
073: */
074:
075: protected Object parse(Object value)
076: throws IllegalArgumentException {
077: if (value == null) {
078: return value;
079: }
080:
081: if (value instanceof Geometry) {
082: return value;
083: }
084:
085: if (value instanceof String) {
086: String wkt = (String) value;
087: WKTReader reader = new WKTReader();
088: try {
089: return reader.read(wkt);
090: } catch (com.vividsolutions.jts.io.ParseException pe) {
091: throw new IllegalArgumentException(
092: "Could not parse the " + "string: " + wkt
093: + " to well known text");
094: }
095: }
096: // consider wkb/gml support?
097: throw new IllegalArgumentException(getClass().getName()
098: + " cannot parse " + value);
099: }
100:
101: public Object /*Geometry*/getValue() {
102: return (Geometry) super .getValue();
103: }
104:
105: public void set(Geometry geometry) {
106: super .setValue(geometry);
107: }
108:
109: /**
110: * Set the bounds for the contained geometry.
111: */
112: public synchronized void setBounds(BoundingBox bbox) {
113: bounds = bbox;
114: }
115:
116: /**
117: * Returns the non null envelope of this attribute. If the attribute's
118: * geometry is <code>null</code> the returned Envelope
119: * <code>isNull()</code> is true.
120: *
121: * @return
122: */
123: public synchronized BoundingBox getBounds() {
124: if (bounds == null) {
125: ReferencedEnvelope bbox = new ReferencedEnvelope(
126: coordinateSystem);
127: Geometry geom = (Geometry) getValue();
128: if (geom != null) {
129: bbox.expandToInclude(geom.getEnvelopeInternal());
130: }
131: bounds = bbox;
132: }
133: return bounds;
134: }
135:
136: public boolean equals(Object o) {
137: if (!(o instanceof GeometricAttribute)) {
138: return false;
139: }
140: GeometricAttribute att = (GeometricAttribute) o;
141:
142: if (!(DESCRIPTOR.equals(att.DESCRIPTOR))) {
143: return false;
144: }
145:
146: if (ID == null) {
147: if (att.ID != null) {
148: return false;
149: }
150: } else if (!ID.equals(att.ID)) {
151: return false;
152: }
153:
154: if (content == null) {
155: if (att.content != null) {
156: return false;
157: }
158: } else {
159: // we need to special case Geometry
160: // as JTS is broken
161: // Geometry.equals( Object ) and Geometry.equals( Geometry )
162: // are different
163: // (We should fold this knowledge into AttributeType...)
164: //
165: if (!((Geometry) content).equals((Geometry) att.content)) {
166: return false;
167: }
168: }
169:
170: return true;
171: }
172:
173: public String toString() {
174: StringBuffer sb = new StringBuffer("GeometricAttribute[");
175: sb.append("id=").append(this .ID).append(", type=").append(
176: this .DESCRIPTOR.getName()).append(
177: ", content=" + this .content).append("]");
178: return sb.toString();
179: }
180: }
181:
182: /**
183: * Helper class used to force CS information on JTS Geometry
184: */
185: /*
186: * class CSGeometryFactory extends GeometryFactory {
187: *
188: * static public GeometryFactory DEFAULT = new GeometryFactory(); static public
189: * PrecisionModel DEFAULT_PRECISON_MODEL = new PrecisionModel();
190: *
191: * public CSGeometryFactory(CoordinateReferenceSystem cs) {
192: * super(toPrecisionModel(cs), toSRID(cs)); }
193: *
194: * public GeometryCollection createGeometryCollection(Geometry[] geometries) {
195: * GeometryCollection gc = super.createGeometryCollection(geometries); // JTS14
196: * //gc.setUserData( cs ); return gc; }
197: *
198: * public LinearRing createLinearRing(Coordinate[] coordinates) { LinearRing lr =
199: * super.createLinearRing(coordinates); // JTS14 //gc.setUserData( cs ); return
200: * lr; } // // And so on // Utility Functions private static int
201: * toSRID(CoordinateReferenceSystem cs) { if ((cs == null) || (cs ==
202: * DefaultGeocentricCRS.CARTESIAN)) { return 0; } // not sure how to tell SRID
203: * from CoordinateSystem? return 0; }
204: *
205: * private static PrecisionModel toPrecisionModel(CoordinateReferenceSystem cs) {
206: * if ((cs == null) || (cs == DefaultGeocentricCRS.CARTESIAN)) { return
207: * DEFAULT_PRECISON_MODEL; }
208: *
209: * return DEFAULT_PRECISON_MODEL; } }
210: */
|