Class LocalizationGridBuilder
 Object

 TransformBuilder

 LocalizationGridBuilder

public class LocalizationGridBuilder extends TransformBuilder
Creates an "almost linear" transform mapping the given source points to the given target points. The transform is backed by a grid of localization, a twodimensional array of coordinate points. Grid size iswidth
×height
and input coordinates are (i,j) indices in the grid, where i must be in the [0…width
1] range and j in the [0…height
1] range inclusive. Output coordinates are the values stored in the grid of localization at the specified index. After aLocalizationGridBuilder
instance has been fully populated (i.e. real world coordinates have been specified for all grid cells), a transformation from grid coordinates to "real world" coordinates can be obtained with thecreate(MathTransformFactory)
method. If this transform is close enough to an affine transform, then an instance ofLinearTransform
is returned. Otherwise, a transform backed by the localization grid is returned.This builder performs the following steps:
 Compute a linear approximation of the transformation using
LinearTransformBuilder
.  Compute
DatumShiftGrid
with the residuals.  Create a
InterpolatedTransform
with the above shift grid.  If a linearizer has been applied, concatenate the inverse transform of that linearizer.
create(MathTransformFactory)
has been invoked.LinearizersIf the localization grid is not close enough to a linear transform,InterpolatedTransform
may not converge. To improve the speed and reliability of the transform, a nonlinear step can be specified. Many candidates can be specified in case the exact form of that nonlinear step is unknown;LocalizationGridBuilder
will select the nonlinear step that provides the best improvement, if any. See the Linearizers section inLinearTransformBuilder
for more discussion. Since:
 0.8
 See Also:
InterpolatedTransform
,LinearTransform
,DatumShiftGrid
Defined in the
sisreferencing
module  Compute a linear approximation of the transformation using


Constructor Summary
Constructors Constructor Description LocalizationGridBuilder(int width, int height)
Creates a new, initially empty, builder for a localization grid of the given size.LocalizationGridBuilder(Vector sourceX, Vector sourceY)
Creates a new, initially empty, builder for a localization grid of a size inferred from the given points.LocalizationGridBuilder(LinearTransformBuilder localizations)
Creates a new builder for a localization grid inferred from the given provider of control points.

Method Summary
All Methods Instance Methods Concrete Methods Modifier and Type Method Description void
addLinearizers(Map<String,MathTransform> projections, int... dimensions)
Adds transforms to potentially apply on target coordinates before to compute the transform.MathTransform
create(MathTransformFactory factory)
Creates a transform from the source points to the target points.Statistics[]
error(MathTransform mt)
Returns statistics of differences between values calculated by the given transform and actual values.Vector
getColumn(int dimension, int column)
Returns a column of coordinate values in the given dimension.double[]
getControlPoint(int gridX, int gridY)
Returns a single target coordinate for the given source coordinate, ornull
if none.double
getDesiredPrecision()
Returns the desired precision of inverse transformations, in units of source coordinates.Vector
getRow(int dimension, int row)
Returns a row of coordinate values in the given dimension.Envelope
getSourceEnvelope(boolean fullArea)
Returns the envelope of source coordinates.LinearTransform
getSourceToGrid()
Returns the current relationship between "realworld" source coordinates and grid coordinates.NumberRange<Double>
resolveWraparoundAxis(int dimension, int direction, double period)
Tries to remove discontinuities in coordinates values caused by antimeridian crossing.void
setControlPoint(int gridX, int gridY, double... target)
Sets a single matching control point pair.void
setControlPoints(Vector... coordinates)
Sets all control points.void
setDesiredPrecision(double precision)
Sets the desired precision of inverse transformations, in units of source coordinates.void
setSourceToGrid(LinearTransform sourceToGrid)
Defines relationship between "realworld" source coordinates and grid coordinates.String
toString()
Returns a string representation of this builder for debugging purpose.String
toString(Locale locale)
Returns a string representation of this builder in the given locale.



Constructor Detail

LocalizationGridBuilder
public LocalizationGridBuilder(int width, int height)
Creates a new, initially empty, builder for a localization grid of the given size. Parameters:
width
 the number of columns in the grid of target positions.height
 the number of rows in the grid of target positions.

LocalizationGridBuilder
public LocalizationGridBuilder(Vector sourceX, Vector sourceY)
Creates a new, initially empty, builder for a localization grid of a size inferred from the given points. This constructor uses the given vectors for computing a grid size and the following initial conversion:(
Above conversion can be obtained bysourceX
,sourceY
) → (gridX
,gridY
)getSourceToGrid()
.Values in the given vectors should be integers, but this constructor is tolerant to noninteger values if they have a constant offset (typically 0.5) relative to integer values. The two vectors do not need to have the same length (i.e.
sourceX[i]
are not necessarily related tosourceY[i]
). Parameters:
sourceX
 all possible x inputs before conversion to grid coordinates.sourceY
 all possible y inputs before conversion to grid coordinates. Throws:
ArithmeticException
 if this constructor can not infer a reasonable grid size from the given vectors.

LocalizationGridBuilder
public LocalizationGridBuilder(LinearTransformBuilder localizations)
Creates a new builder for a localization grid inferred from the given provider of control points. The number of source dimensions in the givenlocalizations
argument shall be 2. Thelocalization
can be used in two ways: If the
localizations
instance has been created with a fixed grid size, then that instance is used asis — it is not copied. It is okay to specify an empty instance and to provide control points later by calls tosetControlPoint(int, int, double...)
.  If the
localizations
instance has been created for a grid of unknown size, then this constructor tries to infer a grid size by inspection of the control points present inlocalizations
at the time this constructor is invoked. Changes inlocalizations
after construction will not be reflected in this new builder.
 Parameters:
localizations
 the provider of control points for which to create a localization grid. Throws:
ArithmeticException
 if this constructor can not infer a reasonable grid size from the given localizations. Since:
 1.0
 If the


Method Detail

setDesiredPrecision
public void setDesiredPrecision(double precision)
Sets the desired precision of inverse transformations, in units of source coordinates. If a conversion from "real world" to grid coordinates has been specified, then the given precision is in "real world" units. Otherwise the precision is in units of grid cells (i.e. a value of 1 is the size of one grid cell).Note: there is no method for setting the desired target precision because forward transformations precision (not to be confused with accuracy) are limited only by rounding errors. Of course the accuracy of both forward and inverse transformations still limited by the accuracy of given control points and the grid resolution. Parameters:
precision
 desired precision of the results of inverse transformations. Throws:
IllegalStateException
 ifcreate(…)
has already been invoked. See Also:
DatumShiftGrid.getCellPrecision()

getDesiredPrecision
public double getDesiredPrecision()
Returns the desired precision of inverse transformations, in units of source coordinates. This is the precision sets by the last call tosetDesiredPrecision(double)
. Returns:
 desired precision of the results of inverse transformations.

setSourceToGrid
public void setSourceToGrid(LinearTransform sourceToGrid)
Defines relationship between "realworld" source coordinates and grid coordinates. The given transform is usually twodimensional, in which case conversions from (x,y) source coordinates to (gridX
,gridY
) indices can be done with the following formulas: gridX = (x  x₀) / Δx
 gridY = (y  y₀) / Δy
 (x₀, y₀) is the coordinate of the center of the cell at grid index (0,0).
 Δx and Δy are the distances between two cells on the x and y
axes respectively, in the same unit of measurement than the one documented in the
setDesiredPrecision(double)
method.
coordinateToGrid
transform for the above formulas can be represented by the following matrix:
If this method is never invoked, then the default conversion is identity. If a desired precision has been specified before this method call, it is caller's responsibility to convert that value to new source units if needed.┌ ┐ │ 1/Δx 0 x₀/Δx │ │ 0 1/Δy y₀/Δy │ │ 0 0 1 │ └ ┘
 Parameters:
sourceToGrid
 conversion from the "real world" source coordinates to grid indices including fractional parts. Throws:
IllegalStateException
 ifcreate(…)
has already been invoked. See Also:
DatumShiftGrid.getCoordinateToGrid()

getSourceToGrid
public LinearTransform getSourceToGrid()
Returns the current relationship between "realworld" source coordinates and grid coordinates. This is the value set by the last call tosetSourceToGrid(LinearTransform)
. If that setter method has never been invoked, then this is an automatically computed transform if the grid coordinates have been specified to the constructor, or the identity transform otherwise. Returns:
 the current relationship between "realworld" source coordinates and grid coordinates.

getSourceEnvelope
public Envelope getSourceEnvelope(boolean fullArea) throws TransformException
Returns the envelope of source coordinates. ThefullArea
argument control whether the returned envelope shall encompass full surface of every cells or only their centers: If
true
, then the returned envelope encompasses full cell surfaces, from lower border to upper border. In other words, the returned envelope encompasses all cell corners.  If
false
, then the returned envelope encompasses only cell centers, inclusive.
gridX
andgridY
argument values in calls toget/setControlPoint(…)
methods) transformed as below: expanded by ½ cell on each side if
fullArea
istrue
 transformed by the inverse of source to grid transform.
 Parameters:
fullArea
 whether the the envelope shall encompass the full cell surfaces instead than only their centers. Returns:
 the envelope of grid points, from lower corner to upper corner.
 Throws:
IllegalStateException
 if the grid points are not yet known.TransformException
 if the envelope can not be calculated. Since:
 1.0
 See Also:
LinearTransformBuilder.getSourceEnvelope()
 If

setControlPoints
public void setControlPoints(Vector... coordinates)
Sets all control points. The length of given vectors must be equal to the total number of cells in the grid. The first vector provides the x coordinates; the second vector provides the y coordinates, etc.. Coordinates are stored in rowmajor order (column index varies faster, followed by row index). Parameters:
coordinates
 coordinates in each target dimensions, stored in rowmajor order. Throws:
IllegalStateException
 ifcreate(…)
has already been invoked. Since:
 1.0

setControlPoint
public void setControlPoint(int gridX, int gridY, double... target)
Sets a single matching control point pair. Source position is assumed precise and target position is assumed uncertain. If the given source position was already associated with another target position, then the old target position is discarded.If a source to grid conversion exists, it shall have been applied by the caller for computing the (
gridX
,gridY
) coordinates given to this method. Parameters:
gridX
 the column index in the grid where to store the given target position.gridY
 the row index in the grid where to store the given target position.target
 the target coordinates, assumed uncertain. Throws:
IllegalStateException
 ifcreate(…)
has already been invoked.IllegalArgumentException
 if thex
ory
coordinate value is out of grid range.MismatchedDimensionException
 if the target position does not have the expected number of dimensions.

getControlPoint
public double[] getControlPoint(int gridX, int gridY)
Returns a single target coordinate for the given source coordinate, ornull
if none. If linearizers have been specified andcreate(…)
has already been invoked, then the control points may be projected using one of the linearizers. Parameters:
gridX
 the column index in the grid where to read the target position.gridY
 the row index in the grid where to read the target position. Returns:
 the target coordinates associated to the given source, or
null
if none.  Throws:
IllegalArgumentException
 if thex
ory
coordinate value is out of grid range.

getRow
public Vector getRow(int dimension, int row)
Returns a row of coordinate values in the given dimension. The returned vector is a view; changes in the returned vector will be reflected in this builder. Parameters:
dimension
 the target dimension for which to get coordinate values.row
 index of the row to get. Returns:
 coordinate values of the specified row in the specified dimension.
 Since:
 1.0

getColumn
public Vector getColumn(int dimension, int column)
Returns a column of coordinate values in the given dimension. The returned vector is a view; changes in the returned vector will be reflected in this builder. Parameters:
dimension
 the target dimension for which to get coordinate values.column
 index of the column to get. Returns:
 coordinate values of the specified column in the specified dimension.
 Since:
 1.0

resolveWraparoundAxis
public NumberRange<Double> resolveWraparoundAxis(int dimension, int direction, double period)
Tries to remove discontinuities in coordinates values caused by antimeridian crossing. This method can be invoked when the localization grid may cross the antimeridian, where longitude values may suddenly jump from +180° to 180° or conversely. This method walks through the coordinate values of the given dimension (typically the longitudes dimension) in the given direction (grid rows or grid columns). If a difference greater thanperiod/2
(typically 180°) is found between two consecutive values, then a multiple ofperiod
(typically 360°) is added or subtracted in order to make a value as close as possible from its previous value.This method needs a direction to be specified:
 Direction 0 means that each value is compared with the value in the previous column, except the value in the first column which is compared to the value in previous row.
 Direction 1 means that each value is compared with the value in the previous row, except the value in the first row which is compared to the value in previous column.
Example: for a grid of (longitude, latitude) values in decimal degrees where longitude values vary (increase or decrease) with increasing column indices and latitude values vary (increase or decrease) with increasing row indices, the the following method should be invoked for protecting the grid against discontinuities on antimeridian:grid.resolveWraparoundAxis(0, 1, 360);
 Parameters:
dimension
 the dimension to process. This is 0 for longitude dimension in a (longitudes, latitudes) grid.direction
 the direction to walk through: 0 for columns or 1 for rows. The recommended direction is the direction of most stable values, typically 1 (rows) for longitudes.period
 that wraparound range (typically 360° for longitudes). Must be strictly positive. Returns:
 the range of coordinate values in the specified dimension after correction for wraparound values.
 Throws:
IllegalStateException
 ifcreate(…)
has already been invoked. Since:
 1.0

addLinearizers
public void addLinearizers(Map<String,MathTransform> projections, int... dimensions)
Adds transforms to potentially apply on target coordinates before to compute the transform. This method can be invoked if the departure from a linear transform is too large, resulting inInterpolatedTransform
to fail with "no convergence error" messages. If linearizers have been specified, then thecreate(MathTransformFactory)
method will try to apply each transform on target coordinates and check which one results in the best correlation coefficients. It may be none.The linearizers are specified as
MathTransform
s from current target coordinates to other spaces where sources to new targets transforms may be more linear. The keys in the map are arbitrary identifiers used intoString()
for debugging purpose. Thedimensions
argument specifies which target dimensions to project and can be null or omitted if the projections shall be applied on all target coordinates. It is possible to invoke this method many times with differentdimensions
argument values. Parameters:
projections
 projections from current target coordinates to other spaces which may result in more linear transforms.dimensions
 the target dimensions to project, or null or omitted for projecting all target dimensions. If nonnull and nonempty, then all transforms in theprojections
map shall have a number of source and target dimensions equals to the length of this array. Throws:
IllegalStateException
 ifcreate(…)
has already been invoked. Since:
 1.0
 See Also:
LinearTransformBuilder.addLinearizers(Map, int...)

create
public MathTransform create(MathTransformFactory factory) throws FactoryException
Creates a transform from the source points to the target points. This method assumes that source points are precise and all uncertainty is in the target points. If this transform is close enough to an affine transform, then an instance ofLinearTransform
is returned.If this method is invoked more than once, the previously created transform instance is returned.
 Specified by:
create
in classTransformBuilder
 Parameters:
factory
 the factory to use for creating the transform, ornull
for the default factory. TheMathTransformFactory.createAffineTransform(Matrix)
method of that factory shall returnLinearTransform
instances. Returns:
 the transform from source to target points.
 Throws:
FactoryException
 if the transform can not be created, for example because the target points have not be specified.

error
public Statistics[] error(MathTransform mt) throws NoninvertibleTransformException
Returns statistics of differences between values calculated by the given transform and actual values. The given math transform is typically the transform computed bycreate(MathTransformFactory)
, but not necessarily. The returned statistics are: One
Statistics
instance for each target dimension, containing statistics about the differences between coordinates computed by the given transform and expected coordinates. For each (i,j) indices in this grid, the indices are transformed by a call tomt.transform(…)
and the result is compared with the coordinates given bygetControlPoint(i,j)
. Those statistics are identified by labels like “P → x” and “P → y” where P stands for pixel coordinates.  One
Statistics
instance for each source dimension, containing statistics about the differences between coordinates computed by the inverse of the transform and expected coordinates. For each (x,y) control point in this grid, the points are transformed by a call tomt.inverse().transform(…)
and the result is compared with the pixel indices of that point. Those statistics are identified by labels like “i ← P′” and “j ← P′” where P′ stands for the control point.
 Parameters:
mt
 the transform to test. Returns:
 statistics of difference between computed values and expected values for each target dimension.
 Throws:
NoninvertibleTransformException
 if an error occurred while inverting a transform. Since:
 1.0
 One

toString
public String toString(Locale locale)
Returns a string representation of this builder in the given locale. Current implementation shows the following information: Number of points.
 Linearizers and their correlation coefficients (if available).
 The linear component of the transform.
 Error statistics, as documented in the
error(MathTransform)
method.
 Parameters:
locale
 the locale for formatting messages and some numbers, ornull
for the default. Returns:
 a string representation of this builder.
 Since:
 1.0

toString
public String toString()
Returns a string representation of this builder for debugging purpose. The string representation is for debugging purpose and may change in any future version. The default implementation delegates totoString(Locale)
with a null locale.

