Hello,
I've been experimenting with JLayeredMapPane and believe I've uncovered an
issue in StreamingRenderer tied to Java 7. I observed
LabelCacheImpl.paintLabels throwing InvalidState exceptions and traced it to
StreamingRenderer.paint()'s use of localThreadPool.shutdown() to wait for
render processing to complete. In Java 7, shutdown's behavior has changed
from Java 6 as follows:
"This method does not wait for previously submitted tasks to complete
execution. Use
<http://docs.oracle.com/javase/7/docs/api/java/util/concurrent/ExecutorServi
ce.html#awaitTermination%28long,%20java.util.concurrent.TimeUnit%29>
awaitTermination to do that."
After changing StreamingRenderer.paint() to use awaitTermination
<http://docs.oracle.com/javase/7/docs/api/java/util/concurrent/ExecutorServi
ce.html#awaitTermination%28long,%20java.util.concurrent.TimeUnit%29>
instead of shutdown the exceptions do not occur.
I'm using geotools 12.2. Here's a snippit from StreamingRenderer.paint()
showing the modification I made:
Future painterFuture = localThreadPool.submit(painterThread);
try {
if(mapContent == null) {
throw new IllegalStateException("Cannot call paint, you did
not set a MapContent in this renderer");
}
//
////////////////////////////////////////////////////////////////////
//
// Processing all the map layers in the context using the
accompaining
// styles
//
//
////////////////////////////////////////////////////////////////////
labelCache.start();
if(labelCache instanceof LabelCacheImpl) {
((LabelCacheImpl)
labelCache).setLabelRenderingMode(LabelRenderingMode.valueOf(getTextRenderin
gMethod()));
}
final int layersNumber = mapContent.layers().size();
for (int i = 0; i < layersNumber; i++) // DJB: for each layer
(ie. one
{
Layer layer = mapContent.layers().get(i);
if (!layer.isVisible()) {
// Only render layer when layer is visible
continue;
}
if (renderingStopRequested) {
return;
}
labelCache.startLayer(i+"");
if (layer instanceof DirectLayer) {
RenderingRequest request = new RenderDirectLayerRequest(
graphics, (DirectLayer) layer);
try {
requests.put(request);
} catch (InterruptedException e) {
fireErrorEvent(e);
}
} else {
MapLayer currLayer = new MapLayer(layer);
try {
// extract the feature type stylers from the style
object
// and process them
processStylers(graphics, currLayer,
worldToScreenTransform,
destinationCrs, mapExtent, screenSize, i +
"");
} catch (Throwable t) {
fireErrorEvent(t);
}
}
labelCache.endLayer(i+"", graphics, screenSize);
}
} finally {
try {
if(!renderingStopRequested) {
requests.put(new EndRequest());
painterFuture.get();
}
} catch(Exception e) {
painterFuture.cancel(true);
fireErrorEvent(e);
} finally {
if(localPool) {
try {
localThreadPool.awaitTermination(100,
TimeUnit.MILLISECONDS);
}
catch (Exception e) {
fireErrorEvent(e);
}
}
}
}
This fix seems to be brittle partly because of the timeout value. A
rendering 'hint' could be used to make the timeout a tunable parameter. Any
suggestions?
Hal
------------------------------------------------------------------------------
Dive into the World of Parallel Programming The Go Parallel Website, sponsored
by Intel and developed in partnership with Slashdot Media, is your hub for all
things parallel software development, from weekly thought leadership blogs to
news, videos, case studies, tutorials and more. Take a look and join the
conversation now. http://goparallel.sourceforge.net/
_______________________________________________
GeoTools-GT2-Users mailing list
GeoTools-GT2-Users@lists.sourceforge.net
https://lists.sourceforge.net/lists/listinfo/geotools-gt2-users