Simone Giannecchini a écrit :
Coudl you spend 5 minutes and take a look? I am trying to improve the
rendering of raster in our GeoServer and all this confusion about axis
order is a real pain for me. I fixed the problem writing a new
worldToScreenTransform method which takes into account the CRS without
making any assumptions.
I looked at RenderUtilities.worldToScreenTransform and you are right,
this method do not take axis order in account. This method expect a JTS
envelope, which do not carry CRS information, so this method had to
assumes a (longitude,latitude) order (unless we had an explicit CRS
argument to this method).
Proposed solutions lower in this email.
I think the source of all my problems is the usage of the JTS envelope
plus epsg_wkt. The JTS envelope does not carry along a crs while the
espg_wkt uses lon,lat instead of lat,lon. In the version of the WCS we
are building right now we have removed dependecies from JTS.Envelope
everywhere but a lot of them remain in the WMS for features. The point
of all this discussion is see if we can reamove this depency and adopt
the GeneralEnvelope as we do in the WCS.
I believe too that JTS + epsg-wkt is contributing to the axis order
mismatch. Using the OpenGIS envelope instead of JTS would probably be
safer. If a user need interoperability between JTS Envelope and GeoAPI
Envelope, he may consider ReferencedEnvelope, which is a JTS envelope
implementing the GeoAPI interface:
http://javadoc.geotools.fr/2.2/org/geotools/geometry/jts/ReferencedEnvelope.html
So if we don't want to break our JTS dependency right now, we could
replace JTS envelope by ReferencedEnvelope as a migration path.
Note that we should encourage usage of GeoAPI's Envelope interface when
possible instead of some specific implementation like GeneralEnvelope.
If the GeoAPI interface need to be expanded with some more API in order
to make it more usable, the timing is good for proposing it. We can
expand section 3.3 in the document attached there:
http://jira.codehaus.org/browse/GEO-76
All the test I have done were performed using epsg-hsql. I can
confidently state that if the crs is EPSG:4326 and comes from
ESPG-HSQL the actual worldToScreen Transform failes. Let's see how
this happens:
public static AffineTransform worldToScreenTransform(Envelope mapExtent,
Rectangle paintArea) {
[...snip...]
This is the incriminated method. As you can easily see from the
computation of scaleX, the assumption that the CRS for the supplied
mapExtent (a JTS Envelope) is LON,LAT hence this method fails if the
CRS is LAT,LON.
Right. Possible fixes are:
1) Add a CoordinateReferenceSystem argument (or replace the Envelope
argument by ReferencedEnvelope). Inspect the coordinate system axis.
If an axis with AxisOrientation.SOUTH | NORTH appears before an axis
with AxisOrientation.EAST | WEST, replace the following line:
new AffineTransform(scaleX, 0.0d, 0.0d, -scaleY, tx, ty);
by
new AffineTransform(0.0d, -scaleY, scaleX, 0.0d, tx, ty);
2) Add a CoordinateReferenceSystem argument for *both* the Envelope and
the Rectangle arguments. This is closer to the GO-1 specification.
In GO-1 vocabulary, the Envelope CRS is the "objective CRS" while
the Rectangle CRS is the "display CRS". Axis swapping can be
determined by the following code:
CoordinateSytsem objectiveCS = objectiveCRS.getCoordinateSystem();
CoordinateSystem displayCS = displayCRS.getCoordinateSystem();
Matrix swap = AbstractCS.swapAndScaleAxis(objectiveCS, displayCS);
This is more generic than #1 above; it work for an arbitrary number
of dimensions, can handle non-geographic cases like (latitude,time)
axis (we sometime use that in oceanography), and can performs unit
conversions as well as axis swaping. In the specific case of 2D CRS,
the matrix need to be converted into an AffineTransform (Matrix3 in
the org.geotools.referencing.operation.matrix may be of some help)
and concatenated with the AffineTransform computed by
worldToScreenTransform. Note that the later should be renamed
objectiveToDisplayTransform for GO-1 compliance.
The drawnback is that this approach requires that the renderer carry
around the concept of display CRS as well as objective CRS. I'm not
sure that the StreamingRenderer do that.
3) An other possible approach is to help me with the implementation of
GO-1 renderer. The GO-1 renderer (in ext/go module) is a refactoring
of the old J2D-renderer, which was fast (except for startup time) and
have some features not found in StreamingRenderer (like displaying a
map scale), but had a number of inconvenient like complexity, lack of
SLD support, memory usage, etc. This renderer was designed with great
attention to CRS (understandably, since it was wrote by the same
author than the referencing module) and was handling axis swapping
right. Javadoc for the GO-1 port:
http://javadoc.geotools.fr/2.2/org/geotools/display/canvas/package-summary.html
Note that the base classes are designed for supporting 3D rendering
engines as well as 2D :). The inconvenient of working on GO-1
renderer is that it may take a while before it get the same set of
functionalities than StreamingRenderer for non-rasters graphics.
I plan to "steal" code for StreamingRenderer, but help from someone
who know the StreamingRenderer would certainly make the work faster.
Martin.
-------------------------------------------------------
This SF.net email is sponsored by: Splunk Inc. Do you grep through log files
for problems? Stop! Download the new AJAX search engine that makes
searching your log files as easy as surfing the web. DOWNLOAD SPLUNK!
http://sel.as-us.falkag.net/sel?cmd=lnk&kid3432&bid#0486&dat1642
_______________________________________________
Geotools-devel mailing list
[email protected]
https://lists.sourceforge.net/lists/listinfo/geotools-devel