You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@sis.apache.org by de...@apache.org on 2020/03/31 17:19:16 UTC
[sis] 01/02: Add an offset to default "grid to CRS" transform so
that grid coordinates near the point of interest are integers in both
grids.
This is an automated email from the ASF dual-hosted git repository.
desruisseaux pushed a commit to branch geoapi-4.0
in repository https://gitbox.apache.org/repos/asf/sis.git
commit 2e525a8975db9e12884399485b9da2e67ae86ff9
Author: Martin Desruisseaux <ma...@geomatys.com>
AuthorDate: Tue Mar 31 12:11:32 2020 +0200
Add an offset to default "grid to CRS" transform so that grid coordinates near the point of interest are integers in both grids.
---
.../sis/coverage/grid/ResampledGridCoverage.java | 46 +++++++++++++++-------
1 file changed, 31 insertions(+), 15 deletions(-)
diff --git a/core/sis-feature/src/main/java/org/apache/sis/coverage/grid/ResampledGridCoverage.java b/core/sis-feature/src/main/java/org/apache/sis/coverage/grid/ResampledGridCoverage.java
index 6a06d63..b8f3762 100644
--- a/core/sis-feature/src/main/java/org/apache/sis/coverage/grid/ResampledGridCoverage.java
+++ b/core/sis-feature/src/main/java/org/apache/sis/coverage/grid/ResampledGridCoverage.java
@@ -35,7 +35,6 @@ import org.apache.sis.coverage.SampleDimension;
import org.apache.sis.geometry.GeneralEnvelope;
import org.apache.sis.internal.util.DoubleDouble;
import org.apache.sis.internal.coverage.j2d.ImageUtilities;
-import org.apache.sis.internal.referencing.DirectPositionView;
import org.apache.sis.internal.referencing.ExtendedPrecisionMatrix;
import org.apache.sis.metadata.iso.extent.DefaultGeographicBoundingBox;
import org.apache.sis.referencing.operation.transform.MathTransforms;
@@ -202,18 +201,24 @@ final class ResampledGridCoverage extends GridCoverage {
}
} else {
/*
- * The first column below gives the displacement in target CRS when moving is the source grid by one cell
- * toward right, and the second column gives the displacement when moving one cell toward up (positive y).
- * More columns may exist in 3D, 4D, etc. cases.
+ * We will try to preserve resolution at the point of interest, which is typically in the center.
+ * We will also try to align the grids in such a way that integer coordinates close to the point
+ * of interest are integers in both grids. This correction is given by the `translation` vector.
*/
final GridExtent sourceExtent = sourceGG.getExtent();
- final MatrixSIS vectors = MatrixSIS.castOrCopy(sourceCenterToCRS.derivative(
- new DirectPositionView.Double(sourceExtent.getPointOfInterest())));
+ final double[] sourcePOI = sourceExtent.getPointOfInterest();
+ final double[] targetPOI = new double[sourceCenterToCRS.getTargetDimensions()];
+ final MatrixSIS vectors = MatrixSIS.castOrCopy(MathTransforms.derivativeAndTransform(
+ sourceCenterToCRS, sourcePOI, 0, targetPOI, 0));
+ final double[] originToPOI = vectors.multiply(sourcePOI);
/*
- * We will retain only the magnitudes of those vectors, in order to have directions parallel with target
- * grid axes. There is one magnitude value for each target CRS dimension. If there is more target grid
- * dimensions than magnitude values (unusual, but not forbidden), some grid dimensions will be ignored
- * provided that their size is 1 (otherwise a SubspaceNotSpecifiedException is thrown).
+ * The first column above gives the displacement in target CRS when moving is the source grid by one cell
+ * toward right, and the second column gives the displacement when moving one cell toward up (positive y).
+ * More columns may exist in 3D, 4D, etc. cases. We retain only the magnitudes of those vectors, in order
+ * to build new vectors with directions parallel with target grid axes. There is one magnitude value for
+ * each target CRS dimension. If there is more target grid dimensions than the amount of magnitude values
+ * (unusual, but not forbidden), some grid dimensions will be ignored provided that their size is 1
+ * (otherwise a SubspaceNotSpecifiedException is thrown).
*/
final MatrixSIS magnitudes = vectors.normalizeColumns(); // Length is dimension of source grid.
final int crsDim = vectors.getNumRow(); // Number of dimensions of target CRS.
@@ -261,7 +266,14 @@ final class ResampledGridCoverage extends GridCoverage {
}
final DoubleDouble m = DoubleDouble.castOrCopy(magnitudes.getNumber(0, tgDim));
m.inverseDivide(1);
- crsToGrid.setNumber(tgDim, tcDim, m);
+ crsToGrid.setNumber(tgDim, tcDim, m); // Scale factor from CRS coordinates to grid coordinates.
+ /*
+ * Move the point of interest in a place where conversion to source grid coordinates
+ * will be close to integer. The exact location does not matter; an additional shift
+ * will be applied later for translating to target grid extent.
+ */
+ m.multiply(originToPOI[tcDim] - targetPOI[tcDim]);
+ crsToGrid.setNumber(tgDim, crsDim, m);
}
crsToGrid.setElement(gridDim, crsDim, 1);
/*
@@ -273,11 +285,15 @@ final class ResampledGridCoverage extends GridCoverage {
MathTransforms.linear(crsToGrid), true);
if (targetExtent == null) {
// Create an extent of same size but with lower coordinates set to 0.
- final long[] coordinates = new long[gridDim * 2];
- for (int i=0; i<gridDim; i++) {
- coordinates[i + gridDim] = tentative.getSize(i) - 1;
+ if (tentative.startsAtZero()) {
+ targetExtent = tentative;
+ } else {
+ final long[] coordinates = new long[gridDim * 2];
+ for (int i=0; i<gridDim; i++) {
+ coordinates[i + gridDim] = tentative.getSize(i) - 1;
+ }
+ targetExtent = new GridExtent(tentative, coordinates);
}
- targetExtent = new GridExtent(tentative, coordinates);
}
/*
* At this point we have the desired target extent and the extent that we actually got by applying