Permalink
Browse files

Careful adjustment of StreamingRenderer, basically duplicate the loop…

…s once for collection/iterator and once for featureCollection/FeatureIterator
  • Loading branch information...
1 parent 3cfbb24 commit ca5779503643a987c5e3c282eecc5d75ef22776d @jodygarnett jodygarnett committed Oct 30, 2012
@@ -25,6 +25,7 @@
import org.geotools.data.simple.SimpleFeatureCollection;
import org.geotools.data.simple.SimpleFeatureIterator;
import org.geotools.data.store.DataFeatureCollection;
+import org.geotools.feature.DefaultFeatureCollection;
import org.geotools.feature.FeatureCollections;
import org.geotools.feature.IllegalAttributeException;
import org.geotools.geometry.jts.ReferencedEnvelope;
@@ -132,7 +133,7 @@ public int getCount() throws IOException {
* @see org.geotools.data.FeatureResults#collection()
*/
public SimpleFeatureCollection collection() throws IOException {
- SimpleFeatureCollection fc = FeatureCollections.newCollection();
+ DefaultFeatureCollection fc = new DefaultFeatureCollection();
List<SimpleFeature> results = index.query(bounds);
for (Iterator<SimpleFeature> it = results.iterator(); it.hasNext();) {
fc.add(it.next());
@@ -28,6 +28,7 @@
import java.awt.geom.Point2D;
import java.awt.image.BufferedImage;
import java.awt.image.RenderedImage;
+import java.io.Closeable;
import java.io.IOException;
import java.text.NumberFormat;
import java.util.ArrayList;
@@ -68,6 +69,7 @@
import org.geotools.factory.CommonFactoryFinder;
import org.geotools.factory.Hints;
import org.geotools.feature.FeatureCollection;
+import org.geotools.feature.FeatureIterator;
import org.geotools.feature.FeatureTypes;
import org.geotools.feature.SchemaException;
import org.geotools.filter.IllegalFilterException;
@@ -2488,14 +2490,85 @@ private void drawPlain(final Graphics2D graphics, MapLayer currLayer, AffineTran
// for each lite feature type style, scan the whole collection and draw
for (LiteFeatureTypeStyle liteFeatureTypeStyle : fts_array) {
- Iterator iterator = null;
- if (collection != null)
- iterator = collection.iterator();
- if (features != null)
- iterator = features.iterator();
+
+ if (collection != null){
+ Iterator iterator = collection.iterator();
+ if (iterator == null ){
+ return; // nothing to do
+ }
+ try {
+ boolean clone = isCloningRequired(currLayer, fts_array);
+ RenderableFeature rf = new RenderableFeature(currLayer, clone);
+ // loop exit condition tested inside try catch
+ // make sure we test hasNext() outside of the try/cath that follows, as that
+ // one is there to make sure a single feature error does not ruin the rendering
+ // (best effort) whilst an exception in hasNext() + ignoring catch results in
+ // an infinite loop
+ while (iterator.hasNext() && !renderingStopRequested) {
+ try {
+ rf.setFeature(iterator.next());
+ process(rf, liteFeatureTypeStyle, scaleRange, at, destinationCrs, layerId);
+ } catch (Throwable tr) {
+ fireErrorEvent(tr);
+ }
+ }
+ } finally {
+ if( iterator instanceof Closeable ){
+ try {
+ ((Closeable)iterator).close();
+ } catch (IOException e) {
+ LOGGER.log(Level.FINER, e.getMessage(), e);
+ }
+ }
+ }
+ }
+
+
+ if( features != null ){
+ FeatureIterator<?> iterator = features.features();
+ if (iterator == null ){
+ return; // nothing to do
+ }
+ try {
+ boolean clone = isCloningRequired(currLayer, fts_array);
+ RenderableFeature rf = new RenderableFeature(currLayer, clone);
+ // loop exit condition tested inside try catch
+ // make sure we test hasNext() outside of the try/cath that follows, as that
+ // one is there to make sure a single feature error does not ruin the rendering
+ // (best effort) whilst an exception in hasNext() + ignoring catch results in
+ // an infinite loop
+ while (iterator.hasNext() && !renderingStopRequested) {
+ try {
+ rf.setFeature(iterator.next());
+ process(rf, liteFeatureTypeStyle, scaleRange, at, destinationCrs, layerId);
+ } catch (Throwable tr) {
+ fireErrorEvent(tr);
+ }
+ }
+ } finally {
+ iterator.close();
+ }
+ }
+ }
+ }
- if (iterator == null)
- return; // nothing to do
+ /**
+ * Performs rendering so that the collection is scanned only once even in presence
+ * of multiple feature type styles, using the in memory buffer for each feature type
+ * style other than the first one (that uses the graphics provided by the user)s
+ */
+ private void drawOptimized(final Graphics2D graphics, MapLayer currLayer, AffineTransform at,
+ CoordinateReferenceSystem destinationCrs, String layerId, Collection collection,
+ FeatureCollection features, final NumberRange scaleRange, final List lfts) {
+
+
+ final LiteFeatureTypeStyle[] fts_array = (LiteFeatureTypeStyle[]) lfts
+ .toArray(new LiteFeatureTypeStyle[lfts.size()]);
+
+
+ if( collection != null ) {
+ Iterator iterator = collection.iterator();
+ if( iterator == null ) return; // nothing to do
try {
boolean clone = isCloningRequired(currLayer, fts_array);
@@ -2505,76 +2578,65 @@ private void drawPlain(final Graphics2D graphics, MapLayer currLayer, AffineTran
// one is there to make sure a single feature error does not ruin the rendering
// (best effort) whilst an exception in hasNext() + ignoring catch results in
// an infinite loop
- while (iterator.hasNext() && !renderingStopRequested) {
+ while (iterator.hasNext() && !renderingStopRequested) {
try {
rf.setFeature(iterator.next());
- process(rf, liteFeatureTypeStyle, scaleRange, at, destinationCrs, layerId);
+ // draw the feature on the main graphics and on the eventual extra image buffers
+ for (LiteFeatureTypeStyle liteFeatureTypeStyle : fts_array) {
+ rf.setScreenMap(liteFeatureTypeStyle.screenMap);
+ process(rf, liteFeatureTypeStyle, scaleRange, at, destinationCrs, layerId);
+ }
} catch (Throwable tr) {
fireErrorEvent(tr);
}
}
+ // submit the merge request
+ requests.put(new MergeLayersRequest(graphics, fts_array));
+ } catch(InterruptedException e) {
+ fireErrorEvent(e);
} finally {
- if (collection instanceof FeatureCollection) {
- FeatureCollection resource = (FeatureCollection) collection;
- resource.close(iterator);
- } else if (features != null) {
- features.close(iterator);
+ if( iterator instanceof Closeable ){
+ try {
+ ((Closeable)iterator).close();
+ } catch (IOException e) {
+ LOGGER.log(Level.FINER, e.getMessage(), e);
+ }
}
- }
+ }
}
- }
-
- /**
- * Performs rendering so that the collection is scanned only once even in presence
- * of multiple feature type styles, using the in memory buffer for each feature type
- * style other than the first one (that uses the graphics provided by the user)s
- */
- private void drawOptimized(final Graphics2D graphics, MapLayer currLayer, AffineTransform at,
- CoordinateReferenceSystem destinationCrs, String layerId, Collection collection,
- FeatureCollection features, final NumberRange scaleRange, final List lfts) {
- Iterator iterator = null;
- if( collection != null ) iterator = collection.iterator();
- if( features != null ) iterator = features.iterator();
-
- if( iterator == null ) return; // nothing to do
-
- final LiteFeatureTypeStyle[] fts_array = (LiteFeatureTypeStyle[]) lfts
- .toArray(new LiteFeatureTypeStyle[lfts.size()]);
-
- try {
- boolean clone = isCloningRequired(currLayer, fts_array);
- RenderableFeature rf = new RenderableFeature(currLayer, clone);
- // loop exit condition tested inside try catch
- // make sure we test hasNext() outside of the try/cath that follows, as that
- // one is there to make sure a single feature error does not ruin the rendering
- // (best effort) whilst an exception in hasNext() + ignoring catch results in
- // an infinite loop
- while (iterator.hasNext() && !renderingStopRequested) {
- try {
- rf.setFeature(iterator.next());
- // draw the feature on the main graphics and on the eventual extra image buffers
- for (LiteFeatureTypeStyle liteFeatureTypeStyle : fts_array) {
- rf.setScreenMap(liteFeatureTypeStyle.screenMap);
- process(rf, liteFeatureTypeStyle, scaleRange, at, destinationCrs, layerId);
+ if( features != null ) {
+ FeatureIterator<?> iterator = features.features();
+ if( iterator == null ) return; // nothing to do
+ try {
+ boolean clone = isCloningRequired(currLayer, fts_array);
+ RenderableFeature rf = new RenderableFeature(currLayer, clone);
+ // loop exit condition tested inside try catch
+ // make sure we test hasNext() outside of the try/cath that follows, as that
+ // one is there to make sure a single feature error does not ruin the rendering
+ // (best effort) whilst an exception in hasNext() + ignoring catch results in
+ // an infinite loop
+ while (iterator.hasNext() && !renderingStopRequested) {
+ try {
+ rf.setFeature(iterator.next());
+ // draw the feature on the main graphics and on the eventual extra image buffers
+ for (LiteFeatureTypeStyle liteFeatureTypeStyle : fts_array) {
+ rf.setScreenMap(liteFeatureTypeStyle.screenMap);
+ process(rf, liteFeatureTypeStyle, scaleRange, at, destinationCrs, layerId);
+
+ }
+ } catch (Throwable tr) {
+ fireErrorEvent(tr);
}
- } catch (Throwable tr) {
- fireErrorEvent(tr);
}
- }
-
- // submit the merge request
- requests.put(new MergeLayersRequest(graphics, fts_array));
- }catch(InterruptedException e) {
- fireErrorEvent(e);
- } finally {
- if( collection instanceof FeatureCollection ){
- FeatureCollection resource = (FeatureCollection ) collection;
- resource.close( iterator );
- } else if(features != null) {
- features.close( iterator );
- }
- }
+ // submit the merge request
+ requests.put(new MergeLayersRequest(graphics, fts_array));
+ }catch(InterruptedException e) {
+ fireErrorEvent(e);
+ } finally {
+ iterator.close();
+ }
+ }
}
/**
@@ -24,6 +24,7 @@
import junit.framework.TestCase;
import org.geotools.data.simple.SimpleFeatureCollection;
+import org.geotools.feature.DefaultFeatureCollection;
import org.geotools.feature.FeatureCollections;
import org.geotools.feature.IllegalAttributeException;
import org.geotools.feature.simple.SimpleFeatureBuilder;
@@ -73,7 +74,7 @@ protected void setUp() throws Exception {
}
public SimpleFeatureCollection createLineCollection() throws Exception {
- SimpleFeatureCollection fc = FeatureCollections.newCollection();
+ DefaultFeatureCollection fc = new DefaultFeatureCollection();
fc.add(createLine(-177, 0, -177, 10));
fc.add(createLine(-177, 0, -200, 0));
fc.add(createLine(-177, 0, -177, 100));
@@ -32,8 +32,12 @@
import org.geotools.data.Query;
import org.geotools.data.simple.SimpleFeatureCollection;
+import org.geotools.data.simple.SimpleFeatureIterator;
import org.geotools.data.simple.SimpleFeatureSource;
+import org.geotools.feature.DefaultFeatureCollection;
+import org.geotools.feature.FeatureCollection;
import org.geotools.feature.FeatureCollections;
+import org.geotools.feature.FeatureIterator;
import org.geotools.feature.simple.SimpleFeatureBuilder;
import org.geotools.feature.simple.SimpleFeatureTypeBuilder;
import org.geotools.geometry.jts.ReferencedEnvelope;
@@ -88,7 +92,7 @@ protected void setUp() throws Exception {
}
public SimpleFeatureCollection createLineCollection() throws Exception {
- SimpleFeatureCollection fc = FeatureCollections.newCollection();
+ DefaultFeatureCollection fc = new DefaultFeatureCollection();
fc.add(createLine(-177, 0, -177, 10));
fc.add(createLine(-177, 0, -200, 0));
fc.add(createLine(-177, 0, -177, 100));
@@ -156,12 +160,12 @@ public void testInfiniteLoopAvoidance() throws Exception {
final Exception sentinel = new RuntimeException("This is the one that should be thrown in hasNext()");
// setup the mock necessary to have the renderer hit into the exception in hasNext()
- Iterator it2 = createNiceMock(Iterator.class);
+ SimpleFeatureIterator it2 = createNiceMock(SimpleFeatureIterator.class);
expect(it2.hasNext()).andThrow(sentinel).anyTimes();
replay(it2);
SimpleFeatureCollection fc = createNiceMock(SimpleFeatureCollection.class);
- expect(fc.iterator()).andReturn(it2);
+ expect(fc.features()).andReturn(it2);
expect(fc.size()).andReturn(200);
expect(fc.getSchema()).andReturn(testFeatureType).anyTimes();
replay(fc);
@@ -223,11 +227,11 @@ public void testRotatedTransform() throws Exception {
final Rectangle screen = new Rectangle(0, 0, 100, 50);
final Envelope world = new Envelope(0, 50, 0, -100);
final AffineTransform worldToScreen = AffineTransform.getRotateInstance(Math.toRadians(90), 0, 0);
- SimpleFeatureCollection fc = FeatureCollections.newCollection();
+ DefaultFeatureCollection fc = new DefaultFeatureCollection();
fc.add(createPoint(0, 0));
fc.add(createPoint(world.getMaxX(), world.getMinY()));
MapContext mapContext = new DefaultMapContext(DefaultGeographicCRS.WGS84);
- mapContext.addLayer(fc, createPointStyle());
+ mapContext.addLayer((FeatureCollection)fc, createPointStyle());
BufferedImage image = new BufferedImage(screen.width, screen.height,
BufferedImage.TYPE_4BYTE_ABGR);
final StreamingRenderer sr = new StreamingRenderer();

0 comments on commit ca57795

Please sign in to comment.