001: /*
002: * GeoTools - OpenSource mapping toolkit
003: * http://geotools.org
004: * (C) 2003-2006, Geotools Project Managment Committee (PMC)
005: * (C) 2002, Institut de Recherche pour le Développement
006: *
007: * This library is free software; you can redistribute it and/or
008: * modify it under the terms of the GNU Lesser General Public
009: * License as published by the Free Software Foundation; either
010: * version 2.1 of the License, or (at your option) any later version.
011: *
012: * This library is distributed in the hope that it will be useful,
013: * but WITHOUT ANY WARRANTY; without even the implied warranty of
014: * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
015: * Lesser General Public License for more details.
016: *
017: * This package contains documentation from OpenGIS specifications.
018: * OpenGIS consortium's work is fully acknowledged here.
019: */
020: package org.geotools.coverage.processing.operation;
021:
022: // JAI dependencies
023: import javax.media.jai.Interpolation;
024: import javax.media.jai.operator.WarpDescriptor; // For javadoc
025: import javax.media.jai.operator.AffineDescriptor; // For javadoc
026:
027: // OpenGIS dependencies
028: import org.opengis.coverage.Coverage;
029: import org.opengis.parameter.ParameterDescriptor;
030: import org.opengis.parameter.ParameterValueGroup;
031: import org.opengis.referencing.FactoryException;
032: import org.opengis.referencing.crs.CoordinateReferenceSystem;
033: import org.opengis.referencing.operation.TransformException;
034:
035: // Geotools dependencies
036: import org.geotools.coverage.grid.GridCoverage2D;
037: import org.geotools.coverage.grid.GridGeometry2D;
038: import org.geotools.coverage.processing.Operation2D;
039: import org.geotools.coverage.processing.CannotReprojectException;
040: import org.geotools.factory.Hints;
041: import org.geotools.metadata.iso.citation.Citations;
042: import org.geotools.parameter.DefaultParameterDescriptor;
043: import org.geotools.parameter.DefaultParameterDescriptorGroup;
044: import org.geotools.resources.i18n.Errors;
045: import org.geotools.resources.i18n.ErrorKeys;
046: import org.geotools.resources.image.ImageUtilities;
047:
048: /**
049: * Resample a grid coverage using a different grid geometry. This operation provides the following
050: * functionality:
051: * <p>
052: * <UL>
053: * <LI><strong>Resampling</strong><br>
054: * The grid coverage can be resampled at a different cell resolution. Some implementations
055: * may be able to do resampling efficiently at any resolution. Also a non-rectilinear grid
056: * coverage can be accessed as rectilinear grid coverage with this operation.</LI>
057: * <LI><strong>Reprojecting</strong><br>
058: * The new grid geometry can have a different coordinate reference system than the underlying
059: * grid geometry. For example, a grid coverage can be reprojected from a geodetic coordinate
060: * reference system to Universal Transverse Mercator CRS.</LI>
061: * <LI><strong>Subsetting</strong><br>
062: * A subset of a grid can be viewed as a separate coverage by using this operation with a
063: * grid geometry which as the same geoferencing and a region. Grid range in the grid geometry
064: * defines the region to subset in the grid coverage.</LI>
065: * </UL>
066: * <p>
067: * <strong>Geotools extension:</strong><br>
068: * The {@code "Resample"} operation use the default
069: * {@link org.opengis.referencing.operation.CoordinateOperationFactory} for creating a
070: * transformation from the source to the destination coordinate reference systems.
071: * If a custom factory is desired, it may be supplied as a rendering hint with the
072: * {@link org.geotools.factory.Hints#COORDINATE_OPERATION_FACTORY} key. Rendering
073: * hints can be supplied to {@link org.geotools.coverage.processing.DefaultProcessor}
074: * at construction time.
075: *
076: * <P><STRONG>Name:</STRONG> <CODE>"Resample"</CODE><BR>
077: * <STRONG>JAI operator:</STRONG> <CODE>"{@linkplain AffineDescriptor Affine}"</CODE>
078: * or <CODE>"{@linkplain WarpDescriptor Warp}"</CODE><BR>
079: * <STRONG>Parameters:</STRONG></P>
080: * <table border='3' cellpadding='6' bgcolor='F4F8FF'>
081: * <tr bgcolor='#B9DCFF'>
082: * <th>Name</th>
083: * <th>Class</th>
084: * <th>Default value</th>
085: * <th>Minimum value</th>
086: * <th>Maximum value</th>
087: * </tr>
088: * <tr>
089: * <td>{@code "Source"}</td>
090: * <td>{@link org.geotools.coverage.grid.GridCoverage2D}</td>
091: * <td align="center">N/A</td>
092: * <td align="center">N/A</td>
093: * <td align="center">N/A</td>
094: * </tr>
095: * <tr>
096: * <td>{@code "InterpolationType"}</td>
097: * <td>{@link java.lang.CharSequence}</td>
098: * <td>"NearestNieghbor"</td>
099: * <td align="center">N/A</td>
100: * <td align="center">N/A</td>
101: * </tr>
102: * <tr>
103: * <td>{@code "CoordinateReferenceSystem"}</td>
104: * <td>{@link org.opengis.referencing.crs.CoordinateReferenceSystem}</td>
105: * <td>Same as source grid coverage</td>
106: * <td align="center">N/A</td>
107: * <td align="center">N/A</td>
108: * </tr>
109: * <tr>
110: * <td>{@code "GridGeometry"}</td>
111: * <td>{@link org.geotools.coverage.grid.GridGeometry2D}</td>
112: * <td>(automatic)</td>
113: * <td align="center">N/A</td>
114: * <td align="center">N/A</td>
115: * </tr>
116: * </table>
117: *
118: * @since 2.2
119: * @source $URL: http://svn.geotools.org/geotools/tags/2.4.1/modules/library/coverage/src/main/java/org/geotools/coverage/processing/operation/Resample.java $
120: * @version $Id: Resample.java 20970 2006-08-11 07:53:22Z jgarnett $
121: * @author Martin Desruisseaux
122: *
123: * @see org.geotools.coverage.processing.Operations#resample
124: * @see WarpDescriptor
125: */
126: public class Resample extends Operation2D {
127: /**
128: * Serial number for interoperability with different versions.
129: */
130: private static final long serialVersionUID = -2022393087647420577L;
131:
132: /**
133: * The parameter descriptor for the interpolation type.
134: */
135: public static final ParameterDescriptor INTERPOLATION_TYPE = new DefaultParameterDescriptor(
136: Citations.OGC, "InterpolationType", Object.class, // Value class (mandatory)
137: null, // Array of valid values
138: "NearestNeighbor", // Default value
139: null, // Minimal value
140: null, // Maximal value
141: null, // Unit of measure
142: false); // Parameter is optional
143:
144: /**
145: * The parameter descriptor for the coordinate reference system.
146: */
147: public static final ParameterDescriptor COORDINATE_REFERENCE_SYSTEM = new DefaultParameterDescriptor(
148: Citations.OGC, "CoordinateReferenceSystem",
149: CoordinateReferenceSystem.class, // Value class (mandatory)
150: null, // Array of valid values
151: null, // Default value
152: null, // Minimal value
153: null, // Maximal value
154: null, // Unit of measure
155: false); // Parameter is optional
156:
157: /**
158: * The parameter descriptor for the grid geometry.
159: */
160: public static final ParameterDescriptor GRID_GEOMETRY = new DefaultParameterDescriptor(
161: Citations.OGC, "GridGeometry", GridGeometry2D.class, // Value class (mandatory)
162: null, // Array of valid values
163: null, // Default value
164: null, // Minimal value
165: null, // Maximal value
166: null, // Unit of measure
167: false); // Parameter is optional
168:
169: /**
170: * Constructs a {@code "Resample"} operation.
171: */
172: public Resample() {
173: super (new DefaultParameterDescriptorGroup(Citations.OGC,
174: "Resample", new ParameterDescriptor[] { SOURCE_0,
175: INTERPOLATION_TYPE,
176: COORDINATE_REFERENCE_SYSTEM, GRID_GEOMETRY }));
177: }
178:
179: /**
180: * Resample a grid coverage. This method is invoked by
181: * {@link org.geotools.coverage.processing.DefaultProcessor}
182: * for the {@code "Resample"} operation.
183: */
184: public Coverage doOperation(final ParameterValueGroup parameters,
185: final Hints hints) {
186: GridCoverage2D source = (GridCoverage2D) parameters.parameter(
187: "Source").getValue();
188: Interpolation interp = ImageUtilities
189: .toInterpolation(parameters.parameter(
190: "InterpolationType").getValue());
191: CoordinateReferenceSystem crs = (CoordinateReferenceSystem) parameters
192: .parameter("CoordinateReferenceSystem").getValue();
193: GridGeometry2D gridGeom = (GridGeometry2D) parameters
194: .parameter("GridGeometry").getValue();
195: GridCoverage2D coverage; // The result to be computed below.
196: if (crs == null) {
197: crs = source.getCoordinateReferenceSystem();
198: }
199: try {
200: coverage = Resampler2D.reproject(source, crs, gridGeom,
201: interp, (hints instanceof Hints) ? (Hints) hints
202: : new Hints(hints));
203: } catch (FactoryException exception) {
204: throw new CannotReprojectException(Errors.format(
205: ErrorKeys.CANT_REPROJECT_$1, source.getName()),
206: exception);
207: } catch (TransformException exception) {
208: throw new CannotReprojectException(Errors.format(
209: ErrorKeys.CANT_REPROJECT_$1, source.getName()),
210: exception);
211: }
212: return coverage;
213: }
214: }
|