You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@sis.apache.org by "Johann Sorel (Jira)" <ji...@apache.org> on 2021/06/25 08:23:00 UTC
[jira] [Commented] (SIS-514) GridGeometry.subgrid(…) should accept an area of interest with less dimensions than the base grid
[ https://issues.apache.org/jira/browse/SIS-514?page=com.atlassian.jira.plugin.system.issuetabpanels:comment-tabpanel&focusedCommentId=17369335#comment-17369335 ]
Johann Sorel commented on SIS-514:
----------------------------------
Here are some functions I made which can bypasse the problem by spliting the intersection on each single crs of the resource GridGeometry
{code:java}
private GridGeometry intersect(GridGeometry resource, GridGeometry query, GridRoundingMode mode) throws FactoryException {
try {
return resource.derive().subgrid(query).build();
} catch (Exception ex) {
//do nothing
}
//fallback solution
final CoordinateReferenceSystem resourceCrs = resource.getCoordinateReferenceSystem();
final CoordinateReferenceSystem queryCrs = query.getCoordinateReferenceSystem();
//find compatible axis
final List<SingleCRS> resourceCrsComps = CRS.getSingleComponents(resourceCrs);
final List<SingleCRS> queryCrsComps = CRS.getSingleComponents(queryCrs);
final int[] resourceCrsCompsOffset = new int[resourceCrsComps.size()];
final int[] queryCrsCompsOffset = new int[resourceCrsComps.size()];
for (int i = 0, k = 0, n = resourceCrsComps.size(); i < n; i++) {
final SingleCRS s = resourceCrsComps.get(i);
resourceCrsCompsOffset[i] = k;
k+= s.getCoordinateSystem().getDimension();
}
for (int i = 0, k = 0, n = queryCrsComps.size(); i < n; i++) {
final SingleCRS s = queryCrsComps.get(i);
queryCrsCompsOffset[i] = k;
k+= s.getCoordinateSystem().getDimension();
}
final Map<SingleCRS,SingleCRS> map = new HashMap<>();
final Map<SingleCRS,SingleCRS> rmap = new HashMap<>();
for (SingleCRS s : queryCrsComps) {
for (SingleCRS t : resourceCrsComps) {
try {
CRS.findOperation(s, t, null);
if (map.put(s, t) != null) {
throw new IllegalArgumentException("Multiple axis can be mapped for " + s);
}
rmap.put(t, s);
} catch (FactoryException ex) {
//do nothing
}
}
}
// reduce
final GridExtent extent = resource.getExtent();
final long[] low = extent.getLow().getCoordinateValues();
final long[] high = extent.getHigh().getCoordinateValues();
for (int resIdx = 0; resIdx < resourceCrsCompsOffset.length; resIdx++) {
final SingleCRS resourceCrsComp = resourceCrsComps.get(resIdx);
final SingleCRS queryCrsComp = rmap.get(resourceCrsComp);
if (queryCrsComp != null) {
final int qryIdx = queryCrsComps.indexOf(queryCrsComp);
//intersect with original grid
final GridGeometry querySlice = reduce(query, queryCrsCompsOffset[qryIdx], queryCrsComp.getCoordinateSystem().getDimension());
final GridGeometry resourceSlice = reduce(resource, resourceCrsCompsOffset[resIdx], resourceCrsComp.getCoordinateSystem().getDimension());
final GridExtent intersection = resourceSlice.derive().rounding(mode).subgrid(querySlice).getIntersection();
for (int i = 0, n = intersection.getDimension(), k = resourceCrsCompsOffset[resIdx]; i < n; i++) {
low[k + i] = intersection.getLow(i);
high[k + i] = intersection.getHigh(i);
}
}
}
return resource.derive().resize(new GridExtent(null, low, high, true)).build();
}
{code}
{code:java}
private static GridGeometry reduce(GridGeometry grid, int offset, int size) {
final int[] range = new int[size];
for (int i = 0; i < range.length; i++) {
range[i] = offset + i;
}
return grid.reduce(range);
}
{code}
{code:java}
private static GridGeometry compound(GridGeometry first, GridGeometry second) throws FactoryException {
//compound crs
final CoordinateReferenceSystem compoundCrs = CRS.compound(
first.getCoordinateReferenceSystem(),
second.getCoordinateReferenceSystem());
//compound exents
final GridExtent secondExtent = second.getExtent();
GridExtent compoundExtent = first.getExtent();
for (int i = 0; i < secondExtent.getDimension(); i++) {
compoundExtent = compoundExtent.insert(
compoundExtent.getDimension(),
secondExtent.getAxisType(i).orElse(null),
secondExtent.getLow(i),
secondExtent.getHigh(i),
true);
}
//compound grid to crs
final MathTransform compoundTrs = MathTransforms.compound(
first.getGridToCRS(PixelInCell.CELL_CENTER),
second.getGridToCRS(PixelInCell.CELL_CENTER));
//compound grid geometry
return new GridGeometry(compoundExtent, PixelInCell.CELL_CENTER, compoundTrs, compoundCrs);
}
{code}
> GridGeometry.subgrid(…) should accept an area of interest with less dimensions than the base grid
> -------------------------------------------------------------------------------------------------
>
> Key: SIS-514
> URL: https://issues.apache.org/jira/browse/SIS-514
> Project: Spatial Information Systems
> Issue Type: Task
> Components: Coverage
> Affects Versions: 1.0
> Reporter: Martin Desruisseaux
> Assignee: Martin Desruisseaux
> Priority: Major
>
> If {{grid}} is a 4-dimensional grid geometry, for example with the following content:
> {noformat}
> GridGeometry
> ├─Grid extent
> │ ├─Column: [0 … 4499] (4500 cellules)
> │ ├─Row: [0 … 4250] (4251 cellules)
> │ ├─Vertical: [0 … 39] (40 cellules)
> │ └─Time: [0 … 0] (1 cellules)
> ├─Geographic extent
> │ ├─Lower: 80°00′00″S 180°00′00″W 2021-03-02T00:00:00Z
> │ └─Upper: 90°00′00″N 180°00′00″E
> {noformat}
> and if {{areaOfInterest}} is a two-dimensional grid, for example with the following content:
> {noformat}
> GridGeometry
> ├─Grid extent
> │ ├─Dimension 0: [0 … 255] (256 cellules)
> │ └─Dimension 1: [0 … 255] (256 cellules)
> ├─Geographic extent
> │ ├─Lower : 01°23′41″N 07°52′24″W
> │ └─Upper : 46°29′05″N 37°12′59″E
> {noformat}
> A call to {{grid.derive().subgrid(areaOfInterest)}} causes an {{OperationNotFoundException}} to be thrown from the {{org.apache.sis.coverage.grid.CoordinateOperationFinder.changeOfCRS}} method because a transform from 2D to 4D can not be found.
> The {{subgrid}} operation should be more tolerant, by leaving untouched the grid in the dimensions not covered by {{areaOfInterest}}.
--
This message was sent by Atlassian Jira
(v8.3.4#803005)