
|
If you were logged in you would be able to see more operations.
|
|
|
|
File Attachments:
|
1.
imageloaderbug.log (42 kB)
|
|
Environment:
|
Experienced under Windows, Linux, Java 1.5
|
|
Issue Links:
|
Duplicate
|
|
|
|
This issue is duplicated by:
|
|
GEOT-611
ImageLoader in LiteRenderer is static, not threadsafe
|
|
|
|
|
|
|
I have been developing an Eclipse RCP application based on uDig plugins. I have discovered a bug in the way ExternalGraphic images are loaded by the StreamingRenderer when rendering a layer with more than approx. 150 features and lots of SLD rules.
Now, clarification time:
- The layer is a WFS layer
- It's data source has about 200 features in it at the moment, although the issue appears randomly as the numbers increase from 0
- The SLD has around 8 rules in it, each one displaying a different icon of 25x25 depending on filtering of attributes of each feature
- Each time the application is run the map is rendered with different outcomes:
o One of the icons may not load (meaning that multiple features of the same type do not render)
o Multiple icons may not display (meaning that multiple features of the same type do not render)
o One of the icons may be loaded for two or more other icons (meaning that every feature can be rendered, but with the wrong icon)
My findings:
- org.geotools.renderer.style.SLDStyleFactory contains a static instace of org.geotools.renderer.style.ImageLoader
- That image loader is used to load ExternalGraphic images from SLDStyleFactory.getImage(ExternalGraphic, int)
- ImageLoader caches loaded images and will return an existing instance if it has already been loaded
- If it has not been loaded, it will then spawn a new Thread with itself as the Runnable
- The thread then loads the image with the help of a static instance of a java.awt.MediaTracker
- Sometimes when the get method is called multiple times it is likely that the cache gets set with a null value for the url key and that is always returned, even though the logging shows that the image loaded correctly
- Loading images from http:// (remote server) or file://
urls makes no difference to the problem (ie, latency/loading time isn't a factor)
- Making the ImageLoader.get(URL, boolean) method synchronized fixes all the image loading problems
Adding the "synchronized" to the method certainly works, but I am not clear on the performance impact this may have if the number of features is very large. It does not seem to affect our application significantly enough to notice, based on several hundred features. It would pay for someone to put some thought around what other components use this mechanism for loading images, as I have not got as deep as how the render actually works.
As this is based on uDig 1.1.x plugins, this problem exists in the 2.2.x branch. I don't know whether it has been resolved in the latest code. An SVN diff between 2.2.x and trunk show no differences in ImageLoader.java.
I have attached a log file which shows the Level.FINEST output for the logger used by ImageLoader class. In this case only 2 out of 3 (or 4) images loaded correctly. The rest of the time the get() method returns null for the features of that type.
Searching shows up GEOT-611 (http://jira.codehaus.org/browse/GEOT-611 ) created in Jul 2005 that appears to be the same thing, but nothing has been done about it.
|
|
Description
|
I have been developing an Eclipse RCP application based on uDig plugins. I have discovered a bug in the way ExternalGraphic images are loaded by the StreamingRenderer when rendering a layer with more than approx. 150 features and lots of SLD rules.
Now, clarification time:
- The layer is a WFS layer
- It's data source has about 200 features in it at the moment, although the issue appears randomly as the numbers increase from 0
- The SLD has around 8 rules in it, each one displaying a different icon of 25x25 depending on filtering of attributes of each feature
- Each time the application is run the map is rendered with different outcomes:
o One of the icons may not load (meaning that multiple features of the same type do not render)
o Multiple icons may not display (meaning that multiple features of the same type do not render)
o One of the icons may be loaded for two or more other icons (meaning that every feature can be rendered, but with the wrong icon)
My findings:
- org.geotools.renderer.style.SLDStyleFactory contains a static instace of org.geotools.renderer.style.ImageLoader
- That image loader is used to load ExternalGraphic images from SLDStyleFactory.getImage(ExternalGraphic, int)
- ImageLoader caches loaded images and will return an existing instance if it has already been loaded
- If it has not been loaded, it will then spawn a new Thread with itself as the Runnable
- The thread then loads the image with the help of a static instance of a java.awt.MediaTracker
- Sometimes when the get method is called multiple times it is likely that the cache gets set with a null value for the url key and that is always returned, even though the logging shows that the image loaded correctly
- Loading images from http:// (remote server) or file://
urls makes no difference to the problem (ie, latency/loading time isn't a factor)
- Making the ImageLoader.get(URL, boolean) method synchronized fixes all the image loading problems
Adding the "synchronized" to the method certainly works, but I am not clear on the performance impact this may have if the number of features is very large. It does not seem to affect our application significantly enough to notice, based on several hundred features. It would pay for someone to put some thought around what other components use this mechanism for loading images, as I have not got as deep as how the render actually works.
As this is based on uDig 1.1.x plugins, this problem exists in the 2.2.x branch. I don't know whether it has been resolved in the latest code. An SVN diff between 2.2.x and trunk show no differences in ImageLoader.java.
I have attached a log file which shows the Level.FINEST output for the logger used by ImageLoader class. In this case only 2 out of 3 (or 4) images loaded correctly. The rest of the time the get() method returns null for the features of that type.
Searching shows up GEOT-611 ( http://jira.codehaus.org/browse/GEOT-611 ) created in Jul 2005 that appears to be the same thing, but nothing has been done about it. |
Show » |
|