001 //$HeadURL: svn+ssh://jwilden@svn.wald.intevation.org/deegree/base/branches/2.5_testing/src/org/deegree/model/spatialschema/AggregateImpl.java $ 002 /*---------------------------------------------------------------------------- 003 This file is part of deegree, http://deegree.org/ 004 Copyright (C) 2001-2009 by: 005 Department of Geography, University of Bonn 006 and 007 lat/lon GmbH 008 009 This library is free software; you can redistribute it and/or modify it under 010 the terms of the GNU Lesser General Public License as published by the Free 011 Software Foundation; either version 2.1 of the License, or (at your option) 012 any later version. 013 This library is distributed in the hope that it will be useful, but WITHOUT 014 ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS 015 FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more 016 details. 017 You should have received a copy of the GNU Lesser General Public License 018 along with this library; if not, write to the Free Software Foundation, Inc., 019 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA 020 021 Contact information: 022 023 lat/lon GmbH 024 Aennchenstr. 19, 53177 Bonn 025 Germany 026 http://lat-lon.de/ 027 028 Department of Geography, University of Bonn 029 Prof. Dr. Klaus Greve 030 Postfach 1147, 53001 Bonn 031 Germany 032 http://www.geographie.uni-bonn.de/deegree/ 033 034 e-mail: info@deegree.org 035 ----------------------------------------------------------------------------*/ 036 package org.deegree.model.spatialschema; 037 038 import java.io.Serializable; 039 import java.util.ArrayList; 040 import java.util.Iterator; 041 042 import org.deegree.framework.log.ILogger; 043 import org.deegree.framework.log.LoggerFactory; 044 import org.deegree.model.crs.CoordinateSystem; 045 046 /** 047 * default implementation of the Aggregate interface 048 * 049 * ------------------------------------------------------------ 050 * 051 * @version 8.6.2001 052 * @author Andreas Poth href="mailto:poth@lat-lon.de" 053 */ 054 public abstract class AggregateImpl extends GeometryImpl implements Aggregate, Serializable { 055 056 private static ILogger LOG = LoggerFactory.getLogger( AggregateImpl.class ); 057 058 /** Use serialVersionUID for interoperability. */ 059 private final static long serialVersionUID = 1161164609227432958L; 060 061 protected ArrayList<Geometry> aggregate = new ArrayList<Geometry>( 500 ); 062 063 /** 064 * Creates a new AggregateImpl object. 065 * 066 * @param crs 067 */ 068 protected AggregateImpl( CoordinateSystem crs ) { 069 super( crs ); 070 } 071 072 /** 073 * @return the number of Geometry within the aggregation 074 */ 075 public int getSize() { 076 return aggregate.size(); 077 } 078 079 /** 080 * merges this aggregation with another one 081 * 082 * @exception GeometryException 083 * a GeometryException will be thrown if the submitted isn't the same type as the recieving one. 084 */ 085 public void merge( Aggregate aggregate ) 086 throws GeometryException { 087 if ( !this.getClass().getName().equals( aggregate.getClass().getName() ) ) { 088 throw new GeometryException( "Aggregations are not of the same type!" ); 089 } 090 091 for ( int i = 0; i < this.getSize(); i++ ) { 092 this.add( aggregate.getObjectAt( i ) ); 093 } 094 095 setValid( false ); 096 } 097 098 /** 099 * adds an Geometry to the aggregation 100 */ 101 public void add( Geometry gmo ) { 102 aggregate.add( gmo ); 103 104 setValid( false ); 105 } 106 107 /** 108 * inserts a Geometry in the aggregation. all elements with an index equal or larger index will be moved. if index 109 * is larger then getSize() - 1 or smaller then 0 or gmo equals null an exception will be thrown. 110 * 111 * @param gmo 112 * Geometry to insert. 113 * @param index 114 * position where to insert the new Geometry 115 */ 116 public void insertObjectAt( Geometry gmo, int index ) 117 throws GeometryException { 118 if ( ( index < 0 ) || ( index > this.getSize() - 1 ) ) { 119 throw new GeometryException( "invalid index/position: " + index + " to insert a geometry!" ); 120 } 121 122 if ( gmo == null ) { 123 throw new GeometryException( "gmo == null. it isn't possible to insert a value" + " that equals null!" ); 124 } 125 126 aggregate.add( index, gmo ); 127 128 setValid( false ); 129 } 130 131 /** 132 * sets the submitted Geometry at the submitted index. the element at the position <code>index</code> will be 133 * removed. if index is larger then getSize() - 1 or smaller then 0 or gmo equals null an exception will be thrown. 134 * 135 * @param gmo 136 * Geometry to set. 137 * @param index 138 * position where to set the new Geometry 139 */ 140 public void setObjectAt( Geometry gmo, int index ) 141 throws GeometryException { 142 if ( ( index < 0 ) || ( index > this.getSize() - 1 ) ) { 143 throw new GeometryException( "invalid index/position: " + index + " to set a geometry!" ); 144 } 145 146 if ( gmo == null ) { 147 throw new GeometryException( "gmo == null. it isn't possible to set a value" + " that equals null!" ); 148 } 149 150 aggregate.set( index, gmo ); 151 152 setValid( false ); 153 } 154 155 /** 156 * removes the submitted Geometry from the aggregation 157 * 158 * @return the removed Geometry 159 */ 160 public Geometry removeObject( Geometry gmo ) { 161 if ( gmo == null ) { 162 return null; 163 } 164 165 int i = aggregate.indexOf( gmo ); 166 167 Geometry gmo_ = null; 168 169 try { 170 gmo_ = removeObjectAt( i ); 171 } catch ( GeometryException e ) { 172 LOG.logError( e.getMessage(), e ); 173 } 174 175 setValid( false ); 176 177 return gmo_; 178 } 179 180 /** 181 * removes the Geometry at the submitted index from the aggregation. if index is larger then getSize() - 1 or 182 * smaller then 0 an exception will be thrown. 183 * 184 * @return the removed Geometry 185 */ 186 public Geometry removeObjectAt( int index ) 187 throws GeometryException { 188 if ( index < 0 ) { 189 return null; 190 } 191 192 if ( index > ( this.getSize() - 1 ) ) { 193 throw new GeometryException( "invalid index/position: " + index + " to remove a geometry!" ); 194 } 195 196 Geometry gmo = aggregate.remove( index ); 197 198 setValid( false ); 199 200 return gmo; 201 } 202 203 /** 204 * removes all Geometry from the aggregation. 205 */ 206 public void removeAll() { 207 aggregate.clear(); 208 envelope = null; 209 setValid( false ); 210 } 211 212 /** 213 * returns the Geometry at the submitted index. if index is larger then getSize() - 1 or smaller then 0 an exception 214 * will be thrown. 215 */ 216 public Geometry getObjectAt( int index ) { 217 return aggregate.get( index ); 218 } 219 220 /** 221 * returns all Geometries as array 222 */ 223 public Geometry[] getAll() { 224 Geometry[] gmos = new Geometry[this.getSize()]; 225 226 return aggregate.toArray( gmos ); 227 } 228 229 public boolean isMember( Geometry gmo ) { 230 return aggregate.contains( gmo ); 231 } 232 233 public Iterator<Geometry> getIterator() { 234 return aggregate.iterator(); 235 } 236 237 @Override 238 public boolean isEmpty() { 239 return ( getSize() == 0 ); 240 } 241 242 @Override 243 public void setCoordinateSystem( CoordinateSystem crs ) { 244 super.setCoordinateSystem( crs ); 245 246 if ( aggregate != null ) { 247 for ( int i = 0; i < aggregate.size(); i++ ) { 248 ( (GeometryImpl) getObjectAt( i ) ).setCoordinateSystem( crs ); 249 } 250 setValid( false ); 251 } 252 } 253 254 /** 255 * translate the point by the submitted values. the <code>dz</code>- value will be ignored. 256 */ 257 @Override 258 public void translate( double[] d ) { 259 try { 260 for ( int i = 0; i < getSize(); i++ ) { 261 Geometry gmo = getObjectAt( i ); 262 gmo.translate( d ); 263 } 264 setValid( false ); 265 } catch ( Exception e ) { 266 LOG.logError( e.getMessage(), e ); 267 } 268 setValid( false ); 269 } 270 271 @Override 272 public boolean equals( Object other ) { 273 if ( envelope == null ) { 274 calculateParam(); 275 } 276 if ( !super.equals( other ) || !( other instanceof AggregateImpl ) 277 || !envelope.equals( ( (Geometry) other ).getEnvelope() ) 278 || ( getSize() != ( (Aggregate) other ).getSize() ) ) { 279 return false; 280 } 281 282 try { 283 for ( int i = 0; i < getSize(); i++ ) { 284 Object o1 = getObjectAt( i ); 285 Object o2 = ( (Aggregate) other ).getObjectAt( i ); 286 287 if ( !o1.equals( o2 ) ) { 288 return false; 289 } 290 } 291 } catch ( Exception ex ) { 292 return false; 293 } 294 295 return true; 296 } 297 298 /** 299 * The Boolean valued operation "intersects" shall return TRUE if this Geometry intersects another Geometry. Within 300 * a Complex, the Primitives do not intersect one another. In general, topologically structured data uses shared 301 * geometric objects to capture intersection information. 302 */ 303 @Override 304 public boolean intersects( Geometry gmo ) { 305 boolean inter = false; 306 307 try { 308 for ( int i = 0; i < aggregate.size(); i++ ) { 309 if ( this.getObjectAt( i ).intersects( gmo ) ) { 310 inter = true; 311 break; 312 } 313 } 314 } catch ( Exception e ) { 315 // nottin 316 } 317 318 return inter; 319 } 320 321 @Override 322 public String toString() { 323 String ret = null; 324 ret = "aggregate = " + aggregate + "\n"; 325 ret += ( "envelope = " + envelope + "\n" ); 326 return ret; 327 } 328 }