diff --git a/geoapi-conformance/src/main/java/org/opengis/test/ToleranceModifier.java b/geoapi-conformance/src/main/java/org/opengis/test/ToleranceModifier.java index 045e8d95f..866a38d58 100644 --- a/geoapi-conformance/src/main/java/org/opengis/test/ToleranceModifier.java +++ b/geoapi-conformance/src/main/java/org/opengis/test/ToleranceModifier.java @@ -64,7 +64,7 @@ public interface ToleranceModifier { * geographic coordinates. This modifier is identical to the {@link #GEOGRAPHIC} tolerance * modifier, except that φ and λ axes are interchanged. This is the most common * modifier used when testing {@link GeographicCRS} instances created from the - * EPSG database. + * EPSG geodetic registry. * * @see ToleranceModifiers#geographic(int, int) */ @@ -88,7 +88,7 @@ public interface ToleranceModifier { * the result of an reverse projection. This modifier is identical to the * {@link #PROJECTION} tolerance modifier, except that φ and λ axes are * interchanged. This is the most common modifier used when testing {@link ProjectedCRS} - * instances created from the EPSG database. + * instances created from the EPSG geodetic registry. * * @see ToleranceModifiers#projection(int, int) */ diff --git a/geoapi-conformance/src/main/java/org/opengis/test/Validator.java b/geoapi-conformance/src/main/java/org/opengis/test/Validator.java index a867e38b1..691b8572e 100644 --- a/geoapi-conformance/src/main/java/org/opengis/test/Validator.java +++ b/geoapi-conformance/src/main/java/org/opengis/test/Validator.java @@ -20,6 +20,7 @@ import java.util.BitSet; import java.util.Objects; import java.util.Collection; +import java.util.function.BiConsumer; import java.util.logging.Logger; import org.opengis.annotation.Obligation; @@ -212,11 +213,11 @@ protected void conditional(final String message, final Object value, final boole } /** - * Ensures that the elements in the given collection are compliant with the {@link Object} - * {@code equals(Object)} and {@code hashCode()} contract. This method ensures that the - * {@code equals(Object)} methods implement reflexive, symmetric - * and transitive relations. It also ensures that if {@code A.equals(B)}, - * then {@code A.hashCode() == B.hashCode()}. + * Ensures that the elements in the given collection are compliant + * with the {@code equals(Object)} and {@code hashCode()} contract. + * This method ensures that the {@code equals(Object)} methods implement + * reflexive, symmetric and transitive relations. + * It also ensures that if {@code A.equals(B)}, then {@code A.hashCode() == B.hashCode()}. * *
If the given collection is null, then this method does nothing. * If the given collection contains null elements, then those elements are ignored.
@@ -228,6 +229,7 @@ protected void conditional(final String message, final Object value, final boole * * @since 3.1 */ + @SuppressWarnings("ObjectEqualsNull") protected void validate(final Collection> collection) { if (collection == null) { return; @@ -279,4 +281,43 @@ protected void validate(final Collection> collection) { assertEquals(hashCodes[i], elements[i].hashCode(), "The hash code value has changed."); } } + + /** + * Validates the given collection, then validates each element in that collection. + * This method invokes {@link #validate(Collection)} and adds the restriction that + * the collection and all its element shall be non-null. + * Then the given validate function is invoked for each element. + * Example: + * + * {@snippet lang="java" : + * validate("identifiers", object.getIdentifiers(), ValidatorContainer::validate, false); + * } + * + * @paramThis class is provided for users wanting to override the validation methods. When the default * behavior is sufficient, the {@link org.opengis.test.Validators} static methods provide a more diff --git a/geoapi-conformance/src/main/java/org/opengis/test/metadata/MaintenanceValidator.java b/geoapi-conformance/src/main/java/org/opengis/test/metadata/MaintenanceValidator.java new file mode 100644 index 000000000..f75477fb1 --- /dev/null +++ b/geoapi-conformance/src/main/java/org/opengis/test/metadata/MaintenanceValidator.java @@ -0,0 +1,78 @@ +/* + * GeoAPI - Java interfaces for OGC/ISO standards + * Copyright © 2008-2024 Open Geospatial Consortium, Inc. + * http://www.geoapi.org + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +package org.opengis.test.metadata; + +import org.opengis.metadata.citation.CitationDate; +import org.opengis.metadata.maintenance.MaintenanceInformation; +import org.opengis.metadata.maintenance.Scope; +import org.opengis.test.ValidatorContainer; + + + +/** + * Validates objects from the {@code org.opengis.metadata.maintenance} package. + * + *
This class is provided for users wanting to override the validation methods. + * When the default behavior is sufficient, the {@link org.opengis.test.Validators} + * static methods provide a more convenient way to validate various kinds of objects.
+ * + * @author Martin Desruisseaux (Geomatys) + * @version 3.1 + * @since 3.1 + */ +public class MaintenanceValidator extends MetadataValidator { + /** + * Creates a new validator instance. + * + * @param container the set of validators to use for validating other kinds of objects + * (see {@linkplain #container field javadoc}). + */ + public MaintenanceValidator(final ValidatorContainer container) { + super(container, "org.opengis.metadata.maintenance"); + } + + /** + * Validates the maintenance information. + * + * @param object the object to validate, or {@code null}. + */ + public void validate(final MaintenanceInformation object) { + if (object == null) { + return; + } + container.validate(toArray(CitationDate.class, object.getMaintenanceDates())); + for (Scope scope : toArray(Scope.class, object.getMaintenanceScopes())) { + validate(scope); + } + validate("maintenanceNote", object.getMaintenanceNotes(), ValidatorContainer::validate, false); + validate("contact", object.getContacts(), ValidatorContainer::validate, false); + } + + /** + * Validates the scope. + * + * @param object the object to validate, or {@code null}. + */ + public void validate(final Scope object) { + if (object == null) { + return; + } + mandatory("Scope: must have a level.", object.getLevel()); + validate("extent", object.getExtents(), ValidatorContainer::validate, false); + } +} diff --git a/geoapi-conformance/src/main/java/org/opengis/test/metadata/QualityValidator.java b/geoapi-conformance/src/main/java/org/opengis/test/metadata/QualityValidator.java new file mode 100644 index 000000000..f1618f3cf --- /dev/null +++ b/geoapi-conformance/src/main/java/org/opengis/test/metadata/QualityValidator.java @@ -0,0 +1,209 @@ +/* + * GeoAPI - Java interfaces for OGC/ISO standards + * Copyright © 2008-2024 Open Geospatial Consortium, Inc. + * http://www.geoapi.org + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +package org.opengis.test.metadata; + +import org.opengis.util.Record; +import org.opengis.metadata.citation.Citation; +import org.opengis.metadata.content.RangeDimension; +import org.opengis.metadata.quality.*; +import org.opengis.metadata.maintenance.Scope; +import org.opengis.test.ValidatorContainer; + +import static org.junit.jupiter.api.Assertions.*; + + +/** + * Validates {@link DataQuality} and related objects from the {@code org.opengis.metadata.quality} package. + * + *This class is provided for users wanting to override the validation methods. + * When the default behavior is sufficient, the {@link org.opengis.test.Validators} + * static methods provide a more convenient way to validate various kinds of objects.
+ * + * @author Martin Desruisseaux (Geomatys) + * @version 3.1 + * @since 3.1 + */ +public class QualityValidator extends MetadataValidator { + /** + * Creates a new validator instance. + * + * @param container the set of validators to use for validating other kinds of objects + * (see {@linkplain #container field javadoc}). + */ + public QualityValidator(final ValidatorContainer container) { + super(container, "org.opengis.metadata.quality"); + } + + /** + * For each interface implemented by the given object, invokes the corresponding + * {@code validate(…)} method defined in this class (if any). + * + * @param object the object to dispatch to {@code validate(…)} methods, or {@code null}. + * @return number of {@code validate(…)} methods invoked in this class for the given object. + */ + public int dispatch(final Element object) { + int n = 0; + if (object != null) { + if (object instanceof PositionalAccuracy) {validate((PositionalAccuracy) object); n++;} + if (n == 0) { + validateElement(object); + } + } + return n; + } + + /** + * For each interface implemented by the given object, invokes the corresponding + * {@code validate(…)} method defined in this class (if any). + * + * @param object the object to dispatch to {@code validate(…)} methods, or {@code null}. + * @return number of {@code validate(…)} methods invoked in this class for the given object. + */ + public int dispatch(final Result object) { + int n = 0; + if (object != null) { + if (object instanceof DescriptiveResult) {validate((DescriptiveResult) object); n++;} + if (object instanceof ConformanceResult) {validate((ConformanceResult) object); n++;} + if (object instanceof QuantitativeResult) {validate((QuantitativeResult) object); n++;} + if (object instanceof CoverageResult) {validate((CoverageResult) object); n++;} + if (n == 0) { + validateResult(object); + } + } + return n; + } + + /** + * Validates the data quality. + * + * @param object the object to validate, or {@code null}. + */ + public void validate(final DataQuality object) { + if (object == null) { + return; + } + final Scope scope = object.getScope(); + mandatory("DataQuality: must have a scope.", scope); + container.validate(scope); + final Element[] reports = toArray(Element.class, object.getReports()); + if (requireMandatoryAttributes) { + assertNotEquals(0, reports.length, "DataQuality: must have at least one report."); + } + for (final Element element : reports) { + dispatch(element); + } + } + + /** + * Validates the positional accuracy. + * + * @param object the object to validate, or {@code null}. + */ + public void validate(final PositionalAccuracy object) { + if (object == null) { + return; + } + validateElement(object); + } + + /** + * Validates the properties common to all elements. + * + * @param object the object to validate. + */ + private void validateElement(final Element object) { + container.validate(object.getStandaloneQualityReportDetails()); + for (final Result result : toArray(Result.class, object.getResults())) { + dispatch(result); + } + } + + /** + * Validates the descriptive result. + * + * @param object the object to validate, or {@code null}. + */ + public void validate(final DescriptiveResult object) { + if (object == null) { + return; + } + validateResult(object); + validateMandatory(object.getStatement()); + } + + /** + * Validates the conformance result. + * + * @param object the object to validate, or {@code null}. + */ + public void validate(final ConformanceResult object) { + if (object == null) { + return; + } + validateResult(object); + Citation specification = object.getSpecification(); + mandatory("ConformanceResult: must have a specification.", specification); + container.validate(specification); + container.validate(object.getExplanation()); + mandatory("ConformanceResult: must have a Boolean.", object.pass()); + } + + /** + * Validates the quantitative result. + * + * @param object the object to validate, or {@code null}. + */ + public void validate(final QuantitativeResult object) { + if (object == null) { + return; + } + validateResult(object); + int count = toArray(Record.class, object.getValues()).length; + if (requireMandatoryAttributes) { + assertNotEquals(0, count, "QuantitativeResult: must have at least one value."); + } + } + + /** + * Validates the coverage result. + * + * @param object the object to validate, or {@code null}. + */ + public void validate(final CoverageResult object) { + if (object == null) { + return; + } + validateResult(object); + mandatory("CoverageResult: must have a spatial representation type.", object.getSpatialRepresentationType()); + mandatory("CoverageResult: must have a result spatial representation.", object.getResultSpatialRepresentation()); + final RangeDimension[] ranges = toArray(RangeDimension.class, object.getResultContent()); + if (object.getResultFormat() == null && object.getResultFile() == null && requireMandatoryAttributes) { + assertNotEquals(0, ranges.length, "CoverageResult: must have at least one range dimension" + + " when result format and result file are not provided."); + } + } + + /** + * Validates the properties common to all results. + * + * @param object the object to validate. + */ + private void validateResult(final Result object) { + container.validate(object.getResultScope()); + } +} diff --git a/geoapi-conformance/src/main/java/org/opengis/test/referencing/AuthorityFactoryTest.java b/geoapi-conformance/src/main/java/org/opengis/test/referencing/AuthorityFactoryTest.java index 70e12b96f..d1a4b1bf9 100644 --- a/geoapi-conformance/src/main/java/org/opengis/test/referencing/AuthorityFactoryTest.java +++ b/geoapi-conformance/src/main/java/org/opengis/test/referencing/AuthorityFactoryTest.java @@ -313,7 +313,7 @@ public void testWGS84() throws NoSuchAuthorityCodeException, FactoryException { /** * Verifies the horizontal axis direction of the given coordinate system. The standard - * directions are (East,North), but the boolean argument allows to swap and flip those + * directions are (East,North), but the Boolean argument allows to swap and flip those * directions. * * @param message the message to report in case of error. diff --git a/geoapi-conformance/src/main/java/org/opengis/test/referencing/CRSValidator.java b/geoapi-conformance/src/main/java/org/opengis/test/referencing/CRSValidator.java index 43b8e07ff..77113d2a8 100644 --- a/geoapi-conformance/src/main/java/org/opengis/test/referencing/CRSValidator.java +++ b/geoapi-conformance/src/main/java/org/opengis/test/referencing/CRSValidator.java @@ -21,6 +21,7 @@ import java.util.List; import java.util.ArrayList; import java.util.LinkedHashSet; +import java.util.function.Supplier; import org.opengis.referencing.cs.*; import org.opengis.referencing.crs.*; @@ -48,13 +49,14 @@ public class CRSValidator extends ReferencingValidator { /** * The axis names mandated by ISO 19111 for some particular kind of CRS. - * See ISO 19111:2007 table 16 at page 25. + * See ISO 19111:2019 table 16 at page 27. */ private static final String[] GEOCENTRIC_AXIS_NAME = {"geocentric X", "geocentric Y", "geocentric Z"}, GEOGRAPHIC_AXIS_NAME = {"geodetic latitude", "geodetic longitude", "ellipsoidal height"}, - PROJECTED_AXIS_NAME = {"northing", "southing", "easting", "westing"}, - SPHERICAL_AXIS_NAME = {"spherical latitude", "spherical longitude", "geocentric radius"}, + PROJECTED_AXIS_NAME = {"northing", "southing", "easting", "westing", "ellipsoidal height"}, + SPHERICAL_AXIS_NAME = {"spherical latitude", "geocentric latitude", "geocentric co-latitude", + "spherical longitude", "geodetic longitude", "geocentric radius"}, VERTICAL_AXIS_NAME = {"depth", "gravity-related height", "gravity-related depth"}; /* * Note: the ISO table does not mention "gravity-related depth" as a standard name. @@ -63,10 +65,10 @@ public class CRSValidator extends ReferencingValidator { */ /** - * {@code true} if validation of the conversion by {@link #validateGeneralDerivedCRS} - * is under way. Used in order to avoid never-ending recursivity. + * {@code true} if validation of the conversion by {@link #validateGeneralDerivedCRS} is under way. + * Used in order to avoid never-ending recursivity. * - * @todo Replace by a more general mechanism straight in {@link ValidatorContainer}. + * @todo Replace by a more general mechanism in {@link ValidatorContainer}. */ private final ThreadLocalValue type | *Alternative types | *Value returned by | - * - *|
---|---|---|---|
{@value org.opengis.referencing.IdentifiedObject#NAME_KEY} | *{@link Identifier} | *{@link String} (see alternatives below) | *{@link IdentifiedObject#getName()} | - *
{@value org.opengis.referencing.IdentifiedObject#ALIAS_KEY} | *{@linkplain GenericName}[] |
* {@link GenericName}, {@link String} or {@linkplain String}[] |
* {@link IdentifiedObject#getAlias()} | - *
{@value org.opengis.referencing.IdentifiedObject#IDENTIFIERS_KEY} | *{@linkplain Identifier}[] |
* {@link Identifier} | *{@link IdentifiedObject#getIdentifiers()} | - *
{@value org.opengis.referencing.IdentifiedObject#DOMAINS_KEY} | *{@linkplain ObjectDomain}[] |
* {@link ObjectDomain} | *{@link IdentifiedObject#getDomains()} | - *
{@value org.opengis.referencing.IdentifiedObject#REMARKS_KEY} | *{@link InternationalString} | *{@link String} (see localization below) | diff --git a/geoapi/src/main/java/org/opengis/referencing/ReferenceSystem.java b/geoapi/src/main/java/org/opengis/referencing/ReferenceSystem.java index dae3af77c..229cdd5bf 100644 --- a/geoapi/src/main/java/org/opengis/referencing/ReferenceSystem.java +++ b/geoapi/src/main/java/org/opengis/referencing/ReferenceSystem.java @@ -27,7 +27,7 @@ /** - * Description of a spatial and temporal reference system used by a dataset. + * Base interface of reference systems by coordinates or by identifiers. * A reference system contains the metadata required to interpret spatial location information unambiguously. * Two methods to describe spatial location are distinguished: * @@ -63,7 +63,8 @@ * ISO 19115:2003 {@code RS_ReferenceSystem} than to * ISO 19115:2015 {@code MD_ReferenceSystem}. * - * @author Martin Desruisseaux (IRD) + * @author ISO 19115 (for abstract model and documentation) + * @author Martin Desruisseaux (IRD, Geomatys) * @version 3.1 * @since 1.0 * @@ -100,8 +101,8 @@ public interface ReferenceSystem extends IdentifiedObject { * * @deprecated Replaced by {@link #getDomains()} as of ISO 19111:2019. */ - @Deprecated(since="3.1", forRemoval=true) - @UML(identifier="domainOfValidity", obligation=OPTIONAL, specification=ISO_19111, version=2007) + @Deprecated(since="3.1") + @UML(identifier="SC_CRS.domainOfValidity", obligation=OPTIONAL, specification=ISO_19111, version=2007) default Extent getDomainOfValidity() { return Legacy.getDomainOfValidity(getDomains()); } @@ -114,7 +115,7 @@ default Extent getDomainOfValidity() { * * @deprecated Replaced by {@link #getDomains()} as of ISO 19111:2019. */ - @Deprecated(since="3.1", forRemoval=true) + @Deprecated(since="3.1") @UML(identifier="SC_CRS.scope", obligation=OPTIONAL, specification=ISO_19111, version=2007) default InternationalString getScope() { return Legacy.getScope(getDomains()); diff --git a/geoapi/src/main/java/org/opengis/referencing/ReferenceSystemType.java b/geoapi/src/main/java/org/opengis/referencing/ReferenceSystemType.java index 05a8f56fc..1c3579638 100644 --- a/geoapi/src/main/java/org/opengis/referencing/ReferenceSystemType.java +++ b/geoapi/src/main/java/org/opengis/referencing/ReferenceSystemType.java @@ -28,6 +28,7 @@ /** * Defines type of reference system used. * + * @author ISO 19115 (for abstract model and documentation) * @author Rémi Maréchal (Geomatys) * @version 3.1 * @since 3.1 @@ -300,8 +301,8 @@ public final class ReferenceSystemType extends CodeList
A coordinate system shall be composed of a non-repeating sequence of coordinate system axes. - * One {@link org.opengis.referencing.cs.CoordinateSystem} (CS) instance may be used by multiple - * {@linkplain org.opengis.referencing.crs.CoordinateReferenceSystem} (CRS) instances. - * The dimension of the coordinate space, the names, the units of measure, the directions - * and sequence of the axes shall be part of the coordinate system definition. - * The number of axes shall be equal to the dimension of the space of which it describes the geometry. - * It is therefore not permitted to supply a coordinate tuple with two heights of different definition.
+ *One {@link org.opengis.referencing.cs.CoordinateSystem} instance may be used by multiple + * {@link org.opengis.referencing.crs.CoordinateReferenceSystem} (CRS) instances. + * The {@linkplain org.opengis.geometry.DirectPosition#getDimension() number of coordinates} in a coordinate tuple + * shall be equal to the {@linkplain org.opengis.referencing.cs.CoordinateSystem#getDimension() number of coordinate axes} + * in the coordinate system. + * Coordinates in coordinate tuples shall be supplied in the order in which the coordinate system's axes are defined.
* - *The {@linkplain org.opengis.geometry.DirectPosition#getDimension() number of coordinates} in a coordinate tuple - * shall be equal to the {@linkplain org.opengis.referencing.cs.CoordinateSystem#getDimension() number of coordinate - * axes} in the coordinate system. Coordinates in coordinate tuples shall be supplied in the order in which - * the coordinate system's axes are defined.
+ *A coordinate system implies how coordinates are calculated from geometric elements such as distances - * and angles and vice versa. The calculus required to derive angles and distances from point coordinates - * and vice versa in a map plane is simple Euclidean 2D arithmetic. To do the same on the surface of an - * ellipsoid (curved 2D space) involves more complex ellipsoidal calculus. These rules cannot be specified - * in detail, but are implied in the geometric properties of the coordinate space.
- * - *Coordinate systems are divided into subtypes by the geometric properties of the coordinate space spanned - * and the geometric properties of the axes themselves (straight or curved; perpendicular or not). - * Certain subtypes of coordinate system shall be used only with specific subtypes of coordinate reference system. - * The restrictions are documented in the javadoc of each CRS subtype.
- * - *ISO 19111 defines three coordinate system unions in addition to the coordinate system types. - * Each union enumerates the coordinate system types that can be associated to a CRS type. - * However, the {@code union} construct found in some languages like C/C++ is not available in Java. - * GeoAPI workarounds this limitation in different ways:
- * - *Union | - *Types in the union | - *GeoAPI approach | - *
{@code GeodeticCS} | - *{@link org.opengis.referencing.cs.CartesianCS}, - * {@link org.opengis.referencing.cs.EllipsoidalCS}, - * {@link org.opengis.referencing.cs.SphericalCS} | - *Provides a {@link org.opengis.referencing.crs.GeographicCRS} type for the {@code EllipsoidalCS} case. - * Provides distinct {@link org.opengis.referencing.crs.CRSFactory} methods for the {@code CartesianCS} - * and {@code SphericalCS} cases. | - *
{@code EngineeringCS} | - *{@link org.opengis.referencing.cs.AffineCS}, - * {@link org.opengis.referencing.cs.CartesianCS}, - * {@link org.opengis.referencing.cs.CylindricalCS}, - * {@link org.opengis.referencing.cs.LinearCS}, - * {@link org.opengis.referencing.cs.PolarCS}, - * {@link org.opengis.referencing.cs.SphericalCS}, - * {@link org.opengis.referencing.cs.UserDefinedCS}. | - *No workaround in the API. Verified by the conformance tests. | - *
{@code ImageCS} | - *{@link org.opengis.referencing.cs.AffineCS}, - * {@link org.opengis.referencing.cs.CartesianCS} | - *Defines {@code CartesianCS} as a special case of {@code AffineCS}. | - *
Coordinate system interfaces should not be confused with coordinate system unions. + * The latter look similar to CS interfaces, but do not imply a specific set of mathematical rules. + * A CS union is only an enumeration of the CS interfaces that can be associated to a + * given CRS interface. Because the Java language has no direct support for unions, the CS + * unions defined by {@linkplain org.opengis.annotation.Specification#ISO_19111 ISO 19111} are not part of GeoAPI. + * They are replaced by Javadoc documenting the constraints.
* * @departure constraint - * ISO 19111 defines {@code GeodeticCS}, {@code EngineeringCS} and {@code ImageCS} unions. - * However, the {@code union} construct found in some languages like C/C++ is not available in Java. - * For each union, a different approach has been applied and documented in the {@code org.opengis.referencing.cs} - * package. In the particular case of {@code ImageCS}, the same type-safety objective can be obtained - * through a slight change in the interface hierarchy. + * The {@code GeodeticCS}, {@code EngineeringCS} and {@code DerivedProjectedCS} unions are omitted because unions + * are not directly supported in the Java language (they are supported in some other languages such as C/C++). + * Unions could be simulated, for example, by defining {@code GeodeticCS} as a parent interface of + * {@link org.opengis.referencing.cs.CartesianCS}, {@link org.opengis.referencing.cs.SphericalCS} and + * {@link org.opengis.referencing.cs.EllipsoidalCS} (the members of the {@code GeodeticCS} union). + * However, it would blur the semantics of subtyping as an “is type of” hierarchy. + * For example, a {@code CartesianCS} can be used in non-geodetic contexts. + * + * @departure harmonization + * The {@code OrdinalCS} and {@code TemporalCountCS} interfaces are omitted because they are about a type + * of coordinate values (integers) rather than the mathematical rules implied by the coordinate system. + * The {@code DateTimeTemporalCS} interface is omitted for similar reason. + * The {@code TemporalMeasureCS} interface is omitted because it behaves like most other axes, + * and therefor is adequately covered by the {@code TimeCS} parent interface. * - * @author Martin Desruisseaux (IRD) + * @author OGC Topic 2 (for abstract model and documentation) + * @author Martin Desruisseaux (IRD, Geomatys) * @version 3.1 * @since 1.0 */ diff --git a/geoapi/src/main/java/org/opengis/referencing/datum/Datum.java b/geoapi/src/main/java/org/opengis/referencing/datum/Datum.java index 3bd5bf7a2..0dbc20dac 100644 --- a/geoapi/src/main/java/org/opengis/referencing/datum/Datum.java +++ b/geoapi/src/main/java/org/opengis/referencing/datum/Datum.java @@ -18,8 +18,11 @@ package org.opengis.referencing.datum; import java.util.Date; +import java.util.Optional; +import java.time.temporal.Temporal; import org.opengis.referencing.IdentifiedObject; import org.opengis.metadata.extent.Extent; +import org.opengis.metadata.citation.CitationDate; import org.opengis.util.InternationalString; import org.opengis.annotation.UML; import org.opengis.annotation.Classifier; @@ -31,19 +34,19 @@ /** - * Specifies the relationship of a {@linkplain org.opengis.referencing.cs.CoordinateSystem coordinate system} - * to the earth, thus creating a {@linkplain org.opengis.referencing.crs.CoordinateReferenceSystem coordinate - * reference system}. For {@linkplain org.opengis.referencing.crs.GeocentricCRS geodetic} and - * {@linkplain org.opengis.referencing.crs.VerticalCRS vertical} coordinate reference systems, - * the datum relates the coordinate system to the Earth. With other types of coordinate reference systems, + * Specifies the relationship of a coordinate system to an object. + * For {@linkplain org.opengis.referencing.crs.GeocentricCRS geodetic} and + * {@linkplain org.opengis.referencing.crs.VerticalCRS vertical} coordinate reference systems (CRS), + * the datum relates the coordinate system to the Earth or other celestial body. + * With other types of CRSs, * the datum may relate the coordinate system to another physical or virtual object. * - *A datum uses a parameter or set of parameters that determine the location of the origin of the - * coordinate reference system. Each datum subtype can be associated with only specific types of - * {@linkplain org.opengis.referencing.cs.CoordinateSystem coordinate systems}, documented in their - * javadoc.
+ *A datum uses a parameter or set of parameters that determine the location of the origin of the CRS. + * Each datum subtype can be associated with only specific types of + * {@linkplain org.opengis.referencing.cs.CoordinateSystem coordinate systems}, documented in their javadoc.
* - * @author Martin Desruisseaux (IRD) + * @author OGC Topic 2 (for abstract model and documentation) + * @author Martin Desruisseaux (IRD, Geomatys) * @version 3.1 * @since 1.0 * @@ -51,18 +54,45 @@ * @see org.opengis.referencing.crs.CoordinateReferenceSystem */ @Classifier(Stereotype.ABSTRACT) -@UML(identifier="CD_Datum", specification=ISO_19111, version=2007) +@UML(identifier="Datum", specification=ISO_19111) public interface Datum extends IdentifiedObject { /** * Key for the{@value}
property to be given to the
* {@code DatumFactory.createFoo(Map, ...)} methods.
- * This is used for setting the value to be returned by {@link #getAnchorPoint()}.
+ * This is used for setting the value to be returned by {@link #getAnchorDefinition()}.
*
* @see DatumFactory
- * @see #getAnchorPoint()
+ * @see #getAnchorDefinition()
+ *
+ * @since 3.1
+ */
+ String ANCHOR_DEFINITION_KEY = "anchorDefinition";
+
+ /**
+ * Key for the {@value}
property to be given to the
+ * {@code DatumFactory.createFoo(Map, ...)} methods.
+ * This is used for setting the value to be returned by {@link #getAnchorDefinition()}.
+ *
+ * @see DatumFactory
+ * @see #getAnchorDefinition()
+ *
+ * @deprecated Renamed {@link #ANCHOR_DEFINITION_KEY} for conformance with ISO 19111:2019 revision.
*/
+ @Deprecated(since = "3.1")
String ANCHOR_POINT_KEY = "anchorPoint";
+ /**
+ * Key for the {@value}
property to be given to the
+ * {@code DatumFactory.createFoo(Map, ...)} methods.
+ * This is used for setting the value to be returned by {@link #getAnchorEpoch()}.
+ *
+ * @see DatumFactory
+ * @see #getAnchorEpoch()
+ *
+ * @since 3.1
+ */
+ String ANCHOR_EPOCH_KEY = "anchorEpoch";
+
/**
* Key for the {@value}
property to be given to the
* {@code DatumFactory.createFoo(Map, ...)} methods.
@@ -70,7 +100,10 @@ public interface Datum extends IdentifiedObject {
*
* @see DatumFactory
* @see #getRealizationEpoch()
+ *
+ * @deprecated Renamed {@link #ANCHOR_EPOCH_KEY} for conformance with ISO 19111:2019 revision.
*/
+ @Deprecated(since = "3.1")
String REALIZATION_EPOCH_KEY = "realizationEpoch";
/**
@@ -96,63 +129,104 @@ public interface Datum extends IdentifiedObject {
String SCOPE_KEY = "scope";
/**
- * A description, possibly including coordinates of an identified point or points, of the
- * relationship used to anchor the coordinate system to the Earth or alternate object.
- * Also known as the "origin", especially for Engineering and Image Datums.
+ * Key for the {@value}
property to be given to the
+ * {@code DatumFactory.createFoo(Map, ...)} methods.
+ * This is used for setting the value to be returned by {@link #getPublicationDate()}.
+ *
+ * @see DatumFactory
+ * @see #getPublicationDate()
+ *
+ * @since 3.1
+ */
+ String PUBLICATION_DATE_KEY = "publicationDate";
+
+ /**
+ * Key for the {@value}
property to be given to the
+ * {@code DatumFactory.createFoo(Map, ...)} methods.
+ * This is used for setting the value to be returned by {@link #getConventionalRS()}.
+ *
+ * @see DatumFactory
+ * @see #getConventionalRS()
+ *
+ * @since 3.1
+ */
+ String CONVENTIONAL_RS_KEY = "conventionalRS";
+
+ /**
+ * Returns a description of the relationship used to anchor the coordinate system to the Earth or alternate object.
+ * The definition may include coordinates of an identified point or points.
+ * Also known as the "origin", especially for {@link EngineeringDatum}s.
*
* This epoch should not be confused with the frame reference epoch of dynamic reference frames. + * Nor with the epoch at which a reference frame is defined to be aligned with another reference frame. + * this information should be included in the datum {@linkplain #getAnchorDefinition() anchor definition}.
* - *An old datum can remain valid after a new datum is defined. - * Alternatively, a datum may be superseded by a later datum, in which case the realization epoch - * for the new datum defines the upper limit for the validity of the superseded datum.
+ * @return epoch at which a static datum matches a dynamic datum from which it has been derived. * - *When used for a region on a planet, engineering CRSs use a flat-Earth approximation: + * corrections for planet-curvature are not applied. + * Typical applications are for civil engineering construction and building information management. + * Note that these applications are not restricted to using engineering CRSs: + * they often utilize projected and sometimes geodetic CRSs.
+ * + *When used for an image internal coordinates, the CRS is not georeferenced. + * The image can be georeferenced by relating the engineering CRS to a geodetic + * or projected CRS through a coordinate transformation.
+ * + * @author OGC Topic 2 (for abstract model and documentation) + * @author Martin Desruisseaux (IRD, Geomatys) + * @version 3.1 * @since 1.0 * * @see DatumAuthorityFactory#createEngineeringDatum(String) * @see DatumFactory#createEngineeringDatum(Map) */ -@UML(identifier="CD_EngineeringDatum", specification=ISO_19111, version=2007) +@UML(identifier="EngineeringDatum", specification=ISO_19111) public interface EngineeringDatum extends Datum { } diff --git a/geoapi/src/main/java/org/opengis/referencing/datum/GeodeticDatum.java b/geoapi/src/main/java/org/opengis/referencing/datum/GeodeticDatum.java index 1d242edd3..6847aea0e 100644 --- a/geoapi/src/main/java/org/opengis/referencing/datum/GeodeticDatum.java +++ b/geoapi/src/main/java/org/opengis/referencing/datum/GeodeticDatum.java @@ -25,12 +25,13 @@ /** - * Defines the location and precise orientation in 3-dimensional space of a defined ellipsoid - * (or sphere) that approximates the shape of the earth. Used also for Cartesian coordinate - * system centered in this ellipsoid (or sphere). + * Position, scale and orientation of a geocentric Cartesian 3D coordinate system relative to the planet. + * It may also identify a defined ellipsoid (or sphere) that approximates the shape of the planet + * and which is centred on and aligned to this geocentric coordinate system. * - * @author Martin Desruisseaux (IRD) - * @version 3.0 + * @author OGC Topic 2 (for abstract model and documentation) + * @author Martin Desruisseaux (IRD, Geomatys) + * @version 3.1 * @since 1.0 * * @see Ellipsoid @@ -39,20 +40,34 @@ * @see DatumAuthorityFactory#createGeodeticDatum(String) * @see DatumFactory#createGeodeticDatum(Map, Ellipsoid, PrimeMeridian) */ -@UML(identifier="CD_GeodeticDatum", specification=ISO_19111, version=2007) +@UML(identifier="GeodeticReferenceFram", specification=ISO_19111) public interface GeodeticDatum extends Datum { /** - * Returns the ellipsoid. + * Returns an approximation of the surface of the geoid. + * Because of the area for which the approximation is valid + * — traditionally regionally, but with the advent of satellite positioning often globally — + * the ellipsoid is typically associated with Geographic and Projected CRSs. * - * @return the ellipsoid. + *The image pixel grid is defined as the set of lines of constant integer coordinate values. + * The term "image grid" is often used in other standards to describe the concept of Image CRS. + * However, care must be taken to correctly interpret this term in the context in which it is used. + * The term "grid cell" is often used as a substitute for the term "pixel".
* - * @author Martin Desruisseaux (IRD) + *The grid lines of the image may be associated in two ways with the data attributes of the pixel or grid cell. + * The data attributes of the image usually represent an average or integrated value that is associated with the entire pixel. + * An image grid can be associated with this data in such a way that the grid lines run through the centres of the pixels. + * The cell centres will thus have integer coordinate values. + * In that case the attribute "pixel in cell" will have the value "cell centre". + * Alternatively, the image grid may be defined such that the grid lines + * associate with the cell or pixel corners rather than the cell centres. + * The cell centres will thus have noninteger coordinate values, the fractional parts always being 0.5. + * The attribute "pixel in cell" will now have the value "cell corner". + * This difference in perspective has no effect on the image interpretation, + * but is important for coordinate transformations involving this defined image.
+ * + * @author OGC Topic 2 (for abstract model and documentation) + * @author Martin Desruisseaux (IRD, Geomatys) * @version 3.0 * @since 1.0 * * @see DatumAuthorityFactory#createImageDatum(String) * @see DatumFactory#createImageDatum(Map, PixelInCell) + * + * @deprecated Replaced by {@link EngineeringDatum} as of ISO 19111:2019. */ +@Deprecated(since="3.1") @UML(identifier="CD_ImageDatum", specification=ISO_19111, version=2007) public interface ImageDatum extends Datum { /** diff --git a/geoapi/src/main/java/org/opengis/referencing/datum/ParametricDatum.java b/geoapi/src/main/java/org/opengis/referencing/datum/ParametricDatum.java index 60a32c950..eaef0c598 100644 --- a/geoapi/src/main/java/org/opengis/referencing/datum/ParametricDatum.java +++ b/geoapi/src/main/java/org/opengis/referencing/datum/ParametricDatum.java @@ -18,22 +18,43 @@ package org.opengis.referencing.datum; import java.util.Map; +import java.util.Optional; +import org.opengis.parameter.ParameterValueGroup; import org.opengis.annotation.UML; -import static org.opengis.annotation.Specification.ISO_19111_2; +import static org.opengis.annotation.Obligation.OPTIONAL; +import static org.opengis.annotation.Specification.ISO_19111; /** - * A textual description and/or a set of parameters identifying a particular reference surface used as - * the origin of a parametric coordinate system, including its position with respect to the Earth. + * Identification of a particular reference surface used as the origin of a parametric coordinate system. + * The identification includes the frame position with respect to the Earth or other planet. + * It may be a textual description and/or a set of parameters. * + * @author OGC Topic 2 (for abstract model and documentation) * @author Johann Sorel (Geomatys) + * @author Martin Desruisseaux (Geomatys) * @version 3.1 * @since 3.1 * * @see DatumAuthorityFactory#createParametricDatum(String) * @see DatumFactory#createParametricDatum(Map) */ -@UML(identifier="CD_ParametricDatum", specification=ISO_19111_2) +@UML(identifier="ParametricDatum", specification=ISO_19111) public interface ParametricDatum extends Datum { + /** + * Parameters used to define the parametric datum. + * Each parameter can be a parameter value, an ordered sequence of values, + * or a reference to a file of parameter values that define a parametric datum. + * + * @return parameter used to define the parametric datum. + * + * @departure harmonization + * ISO 19111 defines a {@code DefiningParameter} class. + * GeoAPI retrofits in the {@link org.opengis.parameter} framework. + */ + @UML(identifier="datumDefiningParameter", obligation=OPTIONAL, specification=ISO_19111) + default OptionalConstraints:
- *There are several types of Vertical Datums, and each may place constraints on the - * {@linkplain org.opengis.referencing.cs.CoordinateSystemAxis Coordinate Axis} with which + *
There are several types of vertical reference frames, and each may place constraints + * on the {@linkplain org.opengis.referencing.cs.CoordinateSystemAxis Coordinate Axis} with which * it is combined to create a {@linkplain org.opengis.referencing.crs.VerticalCRS Vertical CRS}.
* - * @author Martin Desruisseaux (IRD) - * @version 3.0 + * @author OGC Topic 2 (for abstract model and documentation) + * @author Martin Desruisseaux (IRD, Geomatys) + * @version 3.1 * @since 1.0 * * @see DatumAuthorityFactory#createVerticalDatum(String) * @see DatumFactory#createVerticalDatum(Map, VerticalDatumType) */ -@UML(identifier="CD_VerticalDatum", specification=ISO_19111, version=2007) +@UML(identifier="VerticalReferenceFrame", specification=ISO_19111) public interface VerticalDatum extends Datum { /** - * The type of this vertical datum. + * Method through which this vertical reference frame is realized. + * + * @return method through which this vertical reference frame is realized. * - * @todo Renamed {@code RealizationMethod} in ISO 19111:2019. + * @since 3.1 + */ + @UML(identifier="realizationMethod", obligation=OPTIONAL, specification=ISO_19111) + default OptionalDepths are measured in the direction perpendicular (approximately) to the actual equipotential + * surfaces of the planet's gravity field, using such procedures as echo-sounding.
*/ @UML(identifier="depth", obligation=CONDITIONAL, specification=ISO_19111) public static final VerticalDatumType DEPTH = new VerticalDatumType("DEPTH"); /** - * Atmospheric pressure is the basis for the definition of the origin of the - * associated vertical coordinate system axis. These are approximations of - * orthometric heights obtained with the help of a barometer or a barometric - * altimeter. These values are usually expressed in one of the following units: - * meters, feet, millibars (used to measure pressure levels), or theta value - * (units used to measure geopotential height). + * The origin of the vertical axis is based on atmospheric pressure. + * Atmospheric pressure may be used as the intermediary to determine height (barometric height determination) + * or it may be used directly as the vertical coordinate, against which other parameters are measured. + * Barometric values are usually expressed in one of the following units: + * meters, feet, millibars (used to measure pressure levels), + * or theta value (units used to measure geopotential height). */ @UML(identifier="barometric", obligation=CONDITIONAL, specification=ISO_19111) public static final VerticalDatumType BAROMETRIC = new VerticalDatumType("BAROMETRIC"); + /** + * Maps a realization method to a vertical datum type. + * + * @param method the realization method, or {@code null}. + * @return the vertical datum type. + */ + static VerticalDatumType from(RealizationMethod method) { + if (RealizationMethod.GEOID.equals(method)) return GEOIDAL; + if (RealizationMethod.TIDAL.equals(method)) return DEPTH; + return OTHER_SURFACE; + } + /** * Constructs an element of the given name. * diff --git a/geoapi/src/main/java/org/opengis/referencing/datum/package-info.java b/geoapi/src/main/java/org/opengis/referencing/datum/package-info.java index 559d58299..d63e8dddc 100644 --- a/geoapi/src/main/java/org/opengis/referencing/datum/package-info.java +++ b/geoapi/src/main/java/org/opengis/referencing/datum/package-info.java @@ -17,159 +17,28 @@ */ /** - * {@linkplain org.opengis.referencing.datum.Datum Geodetic datum} (the relationship of a - * {@linkplain org.opengis.referencing.cs.CoordinateSystem coordinate system} to the earth). - * The following is adapted from - * {@linkplain org.opengis.annotation.Specification#ISO_19111 OpenGIS® Spatial Referencing by - * Coordinates (Topic 2)} specification. - * - *A datum can be used as the basis for one-, two- or three-dimensional systems. + * Relationship of a Coordinate System (CS) to the Earth, another celestial body or a platform. * For {@linkplain org.opengis.referencing.crs.GeodeticCRS geodetic} - * and {@linkplain org.opengis.referencing.crs.VerticalCRS vertical} coordinate reference systems, - * the datum shall relate the coordinate system to the Earth. - * With other types of coordinate reference systems (CRS), the datum may relate the coordinate system - * to another physical or virtual object. In some applications of an - * {@linkplain org.opengis.referencing.crs.EngineeringCRS Engineering CRS}, the object may be a platform - * moving relative to the Earth. In these applications, the datum itself is not time-dependent, - * but any transformations of the associated coordinates to an Earth-fixed or other coordinate reference system - * shall contain time-dependent parameters.
- * - *Five subtypes of datum are specified: - * {@linkplain org.opengis.referencing.datum.GeodeticDatum geodetic}, - * {@linkplain org.opengis.referencing.datum.VerticalDatum vertical}, - * {@linkplain org.opengis.referencing.datum.EngineeringDatum engineering}, - * {@linkplain org.opengis.referencing.datum.ImageDatum image} and - * {@linkplain org.opengis.referencing.datum.TemporalDatum temporal}. - * Each datum subtype can be associated only with specific types of coordinate reference systems:
- * - *Further sub-typing is required to describe vertical datums adequately. - * The following types of vertical datum are distinguished:
- *Geoidal
- * The zero value of the associated (vertical) coordinate system axis is defined
- * to approximate a constant potential surface, usually the geoid. Such a reference
- * surface is usually determined by a national or scientific authority and is then
- * a well known, named datum. This is the default vertical datum type, because it is
- * the most common one encountered.
Depth
- * The zero point of the vertical axis is defined by a surface that has meaning for
- * the purpose the associated vertical measurements are used for. For hydrographic
- * charts, this is often a predicted nominal sea surface (i.e., without waves or
- * other wind and current effects) that occurs at low tide. Examples are Lowest
- * Astronomical Tide and Lowest Low Water Spring. A different example is a sloping
- * and undulating River Datum defined as the nominal river water surface occurring
- * at a quantified river discharge.
Barometric
- * A vertical datum is of type "barometric" if atmospheric pressure is the basis
- * for the definition of the origin. Atmospheric pressure may be used as the
- * intermediary to determine height (barometric height determination) or it may
- * be used directly as the vertical coordinate, against which other parameters are
- * measured. The latter case is applied routinely in meteorology.
Barometric height determination is routinely used in aircraft. - * The altimeter (barometer) on board is set to the altitude of the airfield at the - * time of take-off, which corrects simultaneously for instantaneous air pressure and - * altitude of the airfield. The measured height value is commonly named "altitude".
- * - *In some land surveying applications height differences between - * points are measured with barometers. To obtain absolute heights the measured height - * differences are added to the known heights of control points. In that case the vertical - * datum type is not barometric, but is the same as that of the vertical control network - * used to obtain the heights of the new points and its vertical datum type.
- * - *The accuracy of this technique is limited, as it is affected - * strongly by the spatial and temporal variability of atmospheric pressure. This - * accuracy limitation impacts the precision of the associated vertical datum definition. - * The datum is usually the surface of constant atmospheric pressure approximately - * equating to mean sea level (MSL). The origin or anchor point is usually a point - * of known MSL height. The instruments are calibrated at this point by correcting - * for the instantaneous atmospheric pressure at sea level and the height of the - * point above MSL.
- * - *In meteorology, atmospheric pressure routinely takes the role - * as vertical coordinate in a CRS that is used as a spatial reference frame for - * meteorological parameters in the upper atmosphere. The origin of the datum - * is in that case the (hypothetical) zero atmospheric pressure and the positive - * vertical axis points down (to increasing pressure).
Other surface
- * In some cases, e.g. oil exploration and production, geological features,
- * i.e., the top or bottom of a geologically identifiable and meaningful subsurface
- * layer, are sometimes used as a vertical datum. Other variations to the above three
- * vertical datum types may exist and are all bracketed in this category.
The image pixel grid is defined as the set of lines of constant - * integer coordinate values. The term "image grid" is often used in other standards to - * describe the concept of Image CRS. However, care must be taken to correctly interpret - * this term in the context in which it is used. The term "grid cell" is often used as a - * substitute for the term "pixel".
- * - *The grid lines of the image may be associated in two ways with - * the data attributes of the pixel or grid cell (ISO CD 19123). The data attributes - * of the image usually represent an average or integrated value that is associated - * with the entire pixel.
- * - *An image grid can be associated with this data in such a way - * that the grid lines run through the centres of the pixels. The cell centres will - * thus have integer coordinate values. In that case the attribute "pixel in cell" - * will have the value "cell centre".
- * - *Alternatively, the image grid may be defined such that the - * grid lines associate with the cell or pixel corners rather than the cell centres. - * The cell centres will thus have noninteger coordinate values, the fractional parts - * always being 0.5. ISO CD 19123 calls the grid points in this latter case "posts" - * and associated image data: "matrix data". The attribute "pixel in cell" will now - * have the value "cell corner".
- * - *This difference in perspective has no effect on the image - * interpretation, but is important for coordinate transformations involving this - * defined image.
- * - *A prime meridian defines the origin from which longitude values - * are specified. Most geodetic datums use Greenwich as their prime meridian. A prime - * meridian description is not needed for any datum type other than geodetic, or if the - * datum type is geodetic and the prime meridian is Greenwich. The prime meridian - * description is mandatory if the datum type is geodetic and its prime meridian - * is not Greenwich.
- * - *An ellipsoid is defined that approximates the surface of the - * geoid. Because of the area for which the approximation is valid - traditionally - * regionally, but with the advent of satellite positioning often globally - the - * ellipsoid is typically associated with Geographic and Projected CRSs. An ellipsoid - * specification shall not be provided if the datum type not geodetic.
- * - *One ellipsoid must be specified with every geodetic datum, - * even if the ellipsoid is not used computationally. The latter may be the case - * when a Geocentric CRS is used, e.g., in the calculation of satellite orbit and - * ground positions from satellite observations. Although use of a Geocentric CRS - * apparently obviates the need of an ellipsoid, the ellipsoid usually played a role - * in the determination of the associated geodetic datum. Furthermore, one or more - * Geographic CRSs may be based on the same geodetic datum, which requires the correct - * ellipsoid the associated with any given geodetic datum.
- * - *An ellipsoid is defined either by its semi-major axis and - * inverse flattening, or by its semi-major axis and semi-minor axis. For some - * applications, for example small-scale mapping in atlases, a spherical approximation - * of the geoid's surface is used, requiring only the radius of the sphere to be - * specified.
- * - * @author Martin Desruisseaux (IRD) + * and {@linkplain org.opengis.referencing.crs.VerticalCRS vertical} + * coordinate reference systems (CRS), the datum is known as reference frame + * and shall relate the coordinate system to the Earth or other celestial body. + * With other types of CRSs, the datum may relate the coordinate system + * to another physical or virtual object. It may be a moving platform such as a car. + * The datum itself is not time-dependent, but any transformations of the associated coordinates + * to an Earth-fixed or other coordinate reference system may contain time-dependent parameters. + * + *The concatenated coordinate operation class is primarily intended to provide a mechanism that forces + * application software to use a preferred path to go from source to target coordinate reference system, + * if a direct transformation between the two is not available.
+ * + * @author OGC Topic 2 (for abstract model and documentation) + * @author Martin Desruisseaux (IRD, Geomatys) + * @version 3.1 * @since 1.0 * * @see CoordinateOperationFactory#createConcatenatedOperation(Map, CoordinateOperation[]) */ -@UML(identifier="CC_ConcatenatedOperation", specification=ISO_19111, version=2007) +@UML(identifier="ConcatenatedOperation", specification=ISO_19111) public interface ConcatenatedOperation extends CoordinateOperation { /** - * Returns the sequence of operations. + * Returns the sequence of operations that are steps in this concatenated operation. * The sequence can contain {@link SingleOperation}s or {@link PassThroughOperation}s, * but should not contain other {@code ConcatenatedOperation}s. + * The sequence shall contain at least two elements. * *Note that some conversions have no parameters.
- * - * @author Martin Desruisseaux (IRD) - * @version 3.0 + * @author OGC Topic 2 (for abstract model and documentation) + * @author Martin Desruisseaux (IRD, Geomatys) + * @version 3.1 * @since 1.0 * * @see Transformation * @see CoordinateOperationFactory#createDefiningConversion(Map, OperationMethod, ParameterValueGroup) */ -@UML(identifier="CC_Conversion", specification=ISO_19111, version=2007) +@UML(identifier="Conversion", specification=ISO_19111) public interface Conversion extends SingleOperation { /** - * Returns the source CRS. Conversions may have a source CRS that - * is not specified here, but through - * {@link org.opengis.referencing.crs.GeneralDerivedCRS#getBaseCRS()} instead. + * Returns the CRS from which coordinates are changed. + * If this conversion is part of a derived CRS, then the source CRS + * (if not null) shall be the same as the {@link org.opengis.referencing.crs.DerivedCRS#getBaseCRS()} value. * - * @return the source CRS, or {@code null} if not available. + * @return the CRS from which coordinates are changed, or {@code null} if not available. */ @Override @UML(identifier="sourceCRS", obligation=OPTIONAL, specification=ISO_19111) CoordinateReferenceSystem getSourceCRS(); /** - * Returns the target CRS. {@linkplain Conversion Conversions} may have a target CRS - * that is not specified here, but through - * {@link org.opengis.referencing.crs.GeneralDerivedCRS} instead. + * Returns the CRS to which coordinates are changed. + * If this conversion is part of a derived CRS, then the target CRS + * (if not null) shall be the same as the {@link org.opengis.referencing.crs.DerivedCRS} instance. * - * @return the target CRS, or {@code null} if not available. + * @return the CRS to which coordinates are changed, or {@code null} if not available. */ @Override @UML(identifier="targetCRS", obligation=OPTIONAL, specification=ISO_19111) CoordinateReferenceSystem getTargetCRS(); /** - * This attribute is declared in {@link CoordinateOperation} but is not used in a conversion. + * This attribute is declared in {@code CoordinateOperation} but is not used in a conversion. * * @return usually {@code null}. */ diff --git a/geoapi/src/main/java/org/opengis/referencing/operation/CoordinateOperation.java b/geoapi/src/main/java/org/opengis/referencing/operation/CoordinateOperation.java index 3fd671d06..d815a6f35 100644 --- a/geoapi/src/main/java/org/opengis/referencing/operation/CoordinateOperation.java +++ b/geoapi/src/main/java/org/opengis/referencing/operation/CoordinateOperation.java @@ -17,8 +17,11 @@ */ package org.opengis.referencing.operation; +import java.util.Optional; import java.util.Collection; import java.util.Collections; +import java.time.temporal.Temporal; +import org.opengis.coordinate.CoordinateSet; import org.opengis.referencing.IdentifiedObject; import org.opengis.referencing.crs.CoordinateReferenceSystem; import org.opengis.metadata.quality.PositionalAccuracy; @@ -34,8 +37,12 @@ /** - * A mathematical operation on coordinates that transforms or converts coordinates to - * another coordinate reference system. + * A mathematical operation on coordinates that transforms or converts coordinates to another CRS or epoch. + * The {@linkplain #getSourceCRS() source CRS} and {@linkplain #getTargetCRS() target CRS} + * properties indicate the CRS from which coordinates are changed + * and the CRS to which coordinates are changed respectively. + * They are mandatory for all subtypes of coordinate operation except {@link Conversion}, + * but GeoAPI recommends to provide a value even in the latter case. * *{@value}
property.
@@ -72,8 +79,7 @@ public interface CoordinateOperation extends IdentifiedObject {
/**
* Key for the {@value}
property.
- * This property is kept for compatibility with ISO 19111:2007.
- * However as of ISO 19111:2019, {@link #DOMAINS_KEY} should be preferred.
+ * This is used for setting the value to be returned by {@link #getCoordinateOperationAccuracy()}.
*
* @see #getCoordinateOperationAccuracy()
*/
@@ -98,11 +104,16 @@ public interface CoordinateOperation extends IdentifiedObject {
String SCOPE_KEY = "scope";
/**
- * Returns the source CRS. The source CRS is mandatory for {@linkplain Transformation transformations} only.
- * {@linkplain Conversion Conversions} may have a source CRS that is not specified here, but through
- * {@link org.opengis.referencing.crs.GeneralDerivedCRS#getBaseCRS()} instead.
+ * Returns the CRS from which coordinates are changed. This property may be {@code null}
+ * for {@link CoordinateOperationFactory#createDefiningConversion defining conversions}, but otherwise
+ * should be specified for other conversions and shall be specified for transformations.
+ *
+ * This method operates on coordinate tuples and does not deal with interpolation of geometry types. + * When a coordinate set is subjected to a coordinate operation, its geometry might or might not be preserved.
+ * + *Implementations are free to compute the coordinate changes immediately or to delay the computation. + * For example, the coordinate changes may be computed on-the-fly during {@link CoordinateSet#stream()} consumption. + * In the latter case, invalid coordinates may not cause a {@link TransformException} to be thrown when this method + * is invoked, but instead cause an unchecked exception to be thrown later, + * typically during the stream terminal operation.
+ * + * @param data the coordinates to change. + * @return the result of changing coordinates. + * @throws TransformException if some coordinates cannot be changed. Note that an absence of exception during + * this method call is not a guarantee that the coordinate changes succeeded, because implementations + * may have deferred the actual computation. + * + * @since 3.1 + */ + @UML(identifier="transform", specification=ISO_19111) + CoordinateSet transform(CoordinateSet data) throws TransformException; } diff --git a/geoapi/src/main/java/org/opengis/referencing/operation/CoordinateOperationAuthorityFactory.java b/geoapi/src/main/java/org/opengis/referencing/operation/CoordinateOperationAuthorityFactory.java index fd4a75e09..7db4f1a6b 100644 --- a/geoapi/src/main/java/org/opengis/referencing/operation/CoordinateOperationAuthorityFactory.java +++ b/geoapi/src/main/java/org/opengis/referencing/operation/CoordinateOperationAuthorityFactory.java @@ -29,9 +29,8 @@ /** - * Creates coordinate transformation objects from codes. The codes are maintained by an - * external authority. A commonly used authority is EPSG, - * which is also used in the GeoTIFF standard. + * Creates coordinate transformation objects from codes. The codes are maintained by an external authority. + * A commonly used authority is the EPSG geodetic registry. * * @author Martin Desruisseaux (IRD) * @version 3.0 @@ -73,8 +72,8 @@ public interface CoordinateOperationAuthorityFactory extends AuthorityFactory { CoordinateOperation createCoordinateOperation(String code) throws FactoryException; /** - * Creates operations from {@linkplain CoordinateReferenceSystem coordinate reference system} - * codes. This method returns only the operations declared by the authority, with preferred + * Creates operations from Coordinate Reference System codes. + * This method returns only the operations declared by the authority, with preferred * operations first. This method doesn't need to compute operations from {@code source} to * {@code target} CRS if no such operations were explicitly defined in the authority database. * Computation of arbitrary operations can be performed by diff --git a/geoapi/src/main/java/org/opengis/referencing/operation/CoordinateOperationFactory.java b/geoapi/src/main/java/org/opengis/referencing/operation/CoordinateOperationFactory.java index 63fe951b0..9bee8491b 100644 --- a/geoapi/src/main/java/org/opengis/referencing/operation/CoordinateOperationFactory.java +++ b/geoapi/src/main/java/org/opengis/referencing/operation/CoordinateOperationFactory.java @@ -163,9 +163,8 @@ CoordinateOperation createConcatenatedOperation(MapMercator (variant A)(EPSG:9804) declares the following parameters: - *
Latitude of natural originin degrees.
Longitude of natural originin degrees.
Scale factor at natural originas a dimensionless number.
False eastingin metres.
False northingin metres.
As this class comes close to the heart of any coordinate transformation software, + * it is recommended to make extensive use of {@linkplain #getIdentifiers() identifiers}, + * referencing well-known datasets wherever possible. The {@linkplain #getName() name} may be ambiguous + * because there is yet no standard way of spelling or naming the various coordinate operation methods. + * Client software requesting a coordinate operation to be executed by a coordinate transformation implementation may + * therefore ask for an operation method this server doesn't recognise, although a perfectly valid method may be available. * Some recommended EPSG identifiers are reproduced below * (see {@linkplain org.opengis.annotation.Specification#ISO_19162 ISO 19162} - * or the EPSG repository for a more complete list): + * or the EPSG repository for a more complete list):
* *Transverse Mercator | Gauss-Boaga / Gauss-Krüger | 9807 |
Mercator (variant A)(EPSG:9804) declares the following parameters. + * Note that implementations can optionally assign + * {@linkplain org.opengis.parameter.ParameterDescriptor#getDefaultValue() default values} to those parameters. + *
Latitude of natural originin degrees.
Longitude of natural originin degrees.
Scale factor at natural originas a dimensionless number.
False eastingin metres.
False northingin metres.
An unofficial list of projections and their parameters can * be found there. diff --git a/geoapi/src/main/java/org/opengis/referencing/operation/RegisterOperations.java b/geoapi/src/main/java/org/opengis/referencing/operation/RegisterOperations.java new file mode 100644 index 000000000..700ed4375 --- /dev/null +++ b/geoapi/src/main/java/org/opengis/referencing/operation/RegisterOperations.java @@ -0,0 +1,114 @@ +/* + * GeoAPI - Java interfaces for OGC/ISO standards + * Copyright © 2009-2023 Open Geospatial Consortium, Inc. + * http://www.geoapi.org + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +package org.opengis.referencing.operation; + +import java.util.Set; +import org.opengis.util.FactoryException; +import org.opengis.referencing.AuthorityFactory; +import org.opengis.referencing.NoSuchAuthorityCodeException; +import org.opengis.referencing.crs.CoordinateReferenceSystem; +import org.opengis.referencing.datum.DatumEnsemble; +import org.opengis.annotation.UML; + +import static org.opengis.annotation.Specification.*; + + +/** + * Services supported by the coordinate operation packages. + * + * @author OGC Topic 2 (for abstract model and documentation) + * @author Martin Desruisseaux (Geomatys) + * @version 3.1 + * @since 3.1 + */ +@UML(identifier="RegisterOperations", specification=ISO_19111) +public interface RegisterOperations extends AuthorityFactory { + /** + * Extracts CRS details from the registry. + * + * @param code CRS identifier allocated by the authority. + * @return the CRS for the given authority code. + * @throws NoSuchAuthorityCodeException if the specified {@code code} was not found. + * @throws FactoryException if the object creation failed for some other reason. + */ + @UML(identifier="findCoordinateReferenceSystem", specification=ISO_19111) + CoordinateReferenceSystem findCoordinateReferenceSystem(String code) throws FactoryException; + + /** + * Extracts coordinate operation details from the registry. + * + * @param code operation identifier allocated by the authority. + * @return the operation for the given authority code. + * @throws NoSuchAuthorityCodeException if the specified {@code code} was not found. + * @throws FactoryException if the object creation failed for some other reason. + */ + @UML(identifier="findCoordinateOperation", specification=ISO_19111) + CoordinateOperation findCoordinateOperation(String code) throws FactoryException; + + /** + * Finds or infers any coordinate operations for which the given CRSs are the source and target, + * in that order. + * + *
Coordinate transformation services should also be able to derive or infer the inverse of any + * coordinate operation (from B to A) from its complementary forward operation + * (A to B). Geodetic datasets may record + * only one of the two operations that may exist between any two coordinate reference systems. + * The inverse operation is then inferred by the application software logic from the stored operation. + * In some cases, the algorithm for the inverse operation is the same as the forward algorithm, + * and only the signs of the parameter values reversed. + * In some other cases, the forward and inverse methods imply two algorithms, but the parameters values are the same. + * The latter situation generally applies to map projections.
+ * + *The implementation should apply meaningful constraints and validations to this process. + * For example, it may be mathematically possible to derive a concatenated coordinate operation + * that will transform North American Datum 1983 coordinates to Australian National Datum, + * but in a practical sense that operation would be meaningless. + * The operation can be determined as invalid with a comparison of the two areas of validity + * and the conclusion that there is no overlap between these.
+ * + * @param source the source CRS. + * @param target the target CRS. + * @return coordinate operations found or inferred between the given pair CRSs. May be an empty set. + * @throws FactoryException if an error occurred while searching for coordinate operations. + */ + @UML(identifier="findCoordinateOperations", specification=ISO_19111) + SetIf the relationship between any two coordinate reference - * systems is known, coordinates can be transformed or converted to another - * coordinate reference system. The UML model therefore specifies a source and - * a target coordinate reference system for such coordinate operations. For that - * reason, a coordinate operation is often popularly said to "transform coordinate - * reference system A into coordinate reference system B". - * Although this wording may be good enough for conversation, it should be realised - * that coordinate operations do not operate on coordinate reference systems, but - * on coordinates.
- * - *Coordinate operations are divided into two subtypes:
- *Coordinate conversion - - * mathematical operation on coordinates that does not include any change of - * Datum. The best-known example of a coordinate conversion is a map projection. - * The parameters describing coordinate conversions are defined rather than - * empirically derived. Note that some conversions have no parameters.
Coordinate transformation - - * mathematical operation on coordinates that usually includes a change of Datum. - * The parameters of a coordinate transformation are empirically derived from data - * containing the coordinates of a series of points in both coordinate reference - * systems. This computational process is usually 'over-determined', allowing - * derivation of error (or accuracy) estimates for the transformation. Also, the - * stochastic nature of the parameters may result in multiple (different) versions - * of the same coordinate transformation. Because of this several transformations - * may exist for a given pair of coordinate reference systems, differing in their - * transformation method, parameter values and accuracy characteristics.
A coordinate operation (transformation or conversion) can be - * time-varying, and must be time-varying if either the source or target CRS is time - * varying. When the coordinate operation is time-varying, the operation method used - * will also be time-varying, and some of the parameters used by that operation method - * will involve time. For example, some of the parameters may have time, velocity, and/or - * acceleration values and units.
- * - *Coordinate conversions are coordinate operations that make use - * of exact, defined (rather than measured or computed), and therefore error-free - * parameter values. Corresponding pairs of coordinate tuples in each of the two - * coordinate reference systems connected through a coordinate conversion have a - * fixed arithmetic relationship. Additionally one of the two tuples cannot exist - * without specification of the coordinate conversion and the 'source' coordinate - * reference system. Coordinate conversions are therefore intimately related to the - * concept of {@linkplain org.opengis.referencing.crs.DerivedCRS Derived CRS}.
- * - *The best-known example of this source-derived relationship - * is a {@linkplain org.opengis.referencing.crs.ProjectedCRS projected coordinate reference system}, - * which is always based on a source {@linkplain org.opengis.referencing.crs.GeographicCRS geographic - * coordinate reference system}. The associated map projection effectively defines the - * projected coordinate reference system from the geographic coordinate system.
- * - *A concatenated coordinate operation is an ordered sequence of - * coordinate operations. The sequence of operations is constrained by the requirement - * that the source coordinate reference system of step (n+1) must be the - * same as the target coordinate reference system of step (n). The source - * coordinate reference system of the first step and the target coordinate reference - * system of the last step are the source and target coordinate reference system - * associated with the concatenated operation.
- * - *The above constraint should not be interpreted as implying - * that only those coordinate operations can be used in a concatenated operation - * that have their source and a target coordinate reference system specified through - * the association pair between {@link org.opengis.referencing.operation.CoordinateOperation} and - * {@link org.opengis.referencing.crs.CoordinateReferenceSystem}. This would exclude coordinate - * conversions. Concatenated coordinate operations may contain coordinate transformations - * and/or coordinate conversions.
- * - *The source and target coordinate reference system of a - * coordinate conversion are defined in the {@link org.opengis.referencing.crs.GeneralDerivedCRS}, - * by specifying the base (i.e., source) CRS and the defining conversion. The derived - * coordinate reference system itself is the target CRS in this situation. When used - * in a concatenated operation, the conversion's source and target coordinate reference - * system are equally subject to the above constraint as the source and target of a - * transformation although they are specified in a different manner.
- * - *The concatenated coordinate operation class is primarily intended - * to provide a mechanism that forces application software to use a preferred path to go - * from source to target coordinate reference system, if a direct transformation between - * the two is not available.
- * - *Coordinate operations require input coordinate tuples of certain - * dimensions and produce output tuples of certain dimensions. The dimensions of these - * coordinate tuples and the dimensions of the coordinate reference system they are defined - * in must be the same.
- * - *The ability to define compound coordinate reference systems - * combining two or more other coordinate reference systems, not themselves compound, - * introduces a difficulty. For example, it may be required to transform only the - * horizontal or only the vertical component of a compound coordinate reference system, - * which will put them at odds with coordinate operations specified for either horizontal - * or vertical coordinates only. To the human mind this is a trivial problem, but not so - * for coordinate transformation software that ought to be capable of automatic operation, - * without human intervention; the software logic would be confronted with the problem of - * having to apply a 2-dimensional coordinate operation to 3-dimensional coordinate tuples.
- * - *This problem has been solved by defining a pass-through operation. - * This operation specifies what subset of a coordinate tuple is subject to a requested - * transformation. It takes the form of referencing another coordinate operation and specifying - * a sequence of numbers defining the positions in the coordinate tuple of the coordinates - * affected by that transformation. The order of the coordinates in a coordinate tuple - * shall agree with the order of the coordinate system axes as defined for the associated - * coordinate system.
- * - *The algorithm used to execute the coordinate operation is defined in the - * {@linkplain org.opengis.referencing.operation.OperationMethod operation method}. Concatenated operations - * and pass-through operations do not require a coordinate operation to be specified. Each - * {@linkplain org.opengis.referencing.operation.OperationMethod operation method} uses a number of - * {@linkplain org.opengis.parameter.ParameterValue parameters} (although some coordinate conversions - * use none), and each {@linkplain org.opengis.referencing.operation.CoordinateOperation coordinate operation} - * assigns value to these parameters.
- * - *As this class comes close to the heart of any coordinate transformation - * software, it is recommended to make extensive use of identifiers, referencing well-known - * datasets wherever possible. There is as yet no standard way of spelling or even naming the - * various coordinate operation methods. Client software requesting a coordinate operation to - * be executed by a coordinate transformation server implementation may therefore ask for an - * operation method this server doesn't recognise, although a perfectly valid method may be - * available. The same holds for coordinate operation parameters used by any coordinate - * operation method. To facilitate recognition and validation it is recommended that the - * operation formulae be included or referenced in the relevant object, and if possible a - * worked example.
- * - *This explanation is not complete without giving some thought to - * implementations. Coordinate transformation services should be able to automatically - * derive coordinate operations that are not stored explicitly in any permanent data store, - * in other words determine their own concatenated or inverse operations. The reason is that - * is practically impossible to store all possible pairs of coordinate reference systems in - * explicitly defined coordinate operations. The key to a successful software implementation - * is the ability to apply meaningful constraints and validations to this process. For example: - * it may be mathematically possible to derive a concatenated coordinate operation that will - * transform North American Datum 1983 coordinates to Australian National Datum; but in a - * practical sense that operation would be meaningless. The key validation that would flag - * such an operation as invalid would be a comparison of the two areas of validity and the - * conclusion that there is no overlap between these.
- * - *Coordinate transformation services should also be able to derive or - * infer the inverse of any coordinate operation (from B to A) - * from its complementary forward operation (A to B). Most - * permanent data stores for coordinate reference parameter data will record only - * one of the two operations that may exist between any two coordinate reference systems. - * The inverse operation is then inferred by the application software logic from the stored - * operation.
- * - *In some cases, the algorithm for the inverse operation is the same - * as the forward algorithm, and only the signs of the parameter values need to be reversed - * for the inverse operation to be fully defined. An example is the 7-parameter Helmert - * transformation (both position vector and coordinate frame rotation convention).
- * - *Some polynomial coordinate operations require the signs of only most, - * but not all, parameter values to be reversed. Other coordinate operation methods imply - * two algorithms, one for the forward and one for the inverse operation. The parameters - * are generally the same in that case. The latter situation generally applies to - * map projections.
- * - *Finally the same algorithm may be used for the inverse operation, - * with entirely different parameter values. This is the case with some polynomial and - * affine operations. In those cases the inverse operation cannot be inferred from the - * forward operation but must be explicitly defined.
- * - *The logic to derive the inverse transformation should be built - * into the application software, be it server or client, that performs the coordinate - * operation.
- * + * Coordinate operations (relationship between any two CRS). + * If the relationship between any two coordinate reference systems (CRS) is known, + * coordinates in one CRS can be transformed or converted to another CRS. + * If the CRS is dynamic, coordinates also may be referenced to a different coordinate epoch, + * or to both a different CRS and different coordinate epoch. + * + *The algorithm used to execute a + * {@linkplain org.opengis.referencing.operation.SingleOperation single coordinate operation} + * is defined in the {@linkplain org.opengis.referencing.operation.OperationMethod operation method}. + * Each operation method can use a number of {@linkplain org.opengis.parameter.ParameterValue parameters}, + * and each single coordinate operation assigns value to these parameters.
+ * + *A coordinate operation (transformation or conversion) can be time-varying, + * and must be time-varying if either the source or target CRS is time varying. + * When the coordinate operation is time-varying, the operation method used will also be time-varying, + * and some of the parameters used by that operation method will involve time. + * For example, some of the parameters may have time, velocity, and/or acceleration values and units.
+ * + * @author OGC Topic 2 (for abstract model and documentation) * @author Martin Desruisseaux (IRD, Geomatys) * @version 3.1 * @since 1.0 diff --git a/geoapi/src/main/java/org/opengis/referencing/package-info.java b/geoapi/src/main/java/org/opengis/referencing/package-info.java index 9081d3a48..825d2bb07 100644 --- a/geoapi/src/main/java/org/opengis/referencing/package-info.java +++ b/geoapi/src/main/java/org/opengis/referencing/package-info.java @@ -17,47 +17,39 @@ */ /** - * Base interfaces for {@linkplain org.opengis.referencing.ReferenceSystem reference systems}. The following - * is adapted from {@linkplain org.opengis.annotation.Specification#ISO_19111 OpenGIS® Spatial Referencing by - * Coordinates (Topic 2)} specification. - * - *A reference system contains the metadata required to interpret spatial location information unambiguously. - * The description of an object's attributes can be done
- * - *North American Datum - * of 1983. This may have alternative names or {@linkplain org.opengis.referencing.IdentifiedObject#getAlias() - * aliases}, for example the abbreviation “NAD83”. + * Base interfaces for reference systems by coordinates or by identifiers. + * A reference system contains the metadata required to interpret spatial location information unambiguously. + * Referencing can be done by coordinates with interfaces in the {@code crs} sub-package, + * or by identifiers with interfaces in the {@code gazetteer} sub-package. + * The {@link org.opengis.referencing.IdentifiedObject} interface in this package + * contains attributes common to several objects used in referencing by coordinates or by identifiers. + * For example, a reference frame {@linkplain org.opengis.referencing.IdentifiedObject#getName() primary name} + * might be
North American Datum of 1983. That reference frame may have alternative names or + * {@linkplain org.opengis.referencing.IdentifiedObject#getAlias() aliases}, + * for example, the abbreviation
NAD83. * *
Another attribute is {@linkplain org.opengis.referencing.IdentifiedObject#getIdentifiers() identifiers}. - * This is a unique code used to reference an object in a given place. For example, an external geodetic register might - * give the NAD83 datum a unique code of “6269”. Identifiers have a data type of {@link org.opengis.metadata.Identifier}. - * In addition to the use of an identifier as a reference to a definition in a remote register, it may also be included - * in an object definition to allow remote users to refer to the object.
- * - *Most interfaced objects are immutable. This means that implementations promise - * not to change an object's internal state once they have handed out an interface pointer. Since - * most interfaced objects are specified to be immutable, there do not need to be any constraints - * on operation sequencing. This means that these interfaces can be used in parallel computing - * environments (e.g. Internet servers).
+ * This is a unique code used to reference an object in a given place. + * For example, an external geodetic register might give the NAD83 reference frame a unique code of6269. + * Objects can be obtained from codes using sub-interfaces of {@link org.opengis.referencing.AuthorityFactory}. + * Identifiers have a data type of {@link org.opengis.metadata.Identifier}. * *
Many entities in this specification can be printed in a well-known text format. - * This allows objects to be stored in databases (persistence), and transmitted between - * interoperating computer programs. Well-Known Texts (WKT) may come in two formats: - * - *
org.opengis
® namespace, GeoAPI defines
+ * interfaces for metadata handling, for geodetic referencing (map projections),
+ * for the representation of features and for their filtering.
+ * The GeoAPI interfaces closely follow the abstract models published collaboratively by the
+ * International Organization for Standardization (ISO)
+ * in its 19100 series of documents and the Open
+ * Open Geospatial Consortium (OGC)
+ * in its abstract and implementation specifications.
+ * See the GeoAPI home page for more information.
*
* @version 3.1
* @since 1.0
@@ -67,6 +61,7 @@
exports org.opengis.referencing.cs;
exports org.opengis.referencing.crs;
exports org.opengis.referencing.operation;
+ exports org.opengis.coordinate;
exports org.opengis.geometry;
exports org.opengis.geometry.coordinate;
exports org.opengis.feature;
diff --git a/geoapi/src/shared/java/org/opengis/geoapi/Content.java b/geoapi/src/shared/java/org/opengis/geoapi/Content.java
index 7b50eafb0..1adc19265 100644
--- a/geoapi/src/shared/java/org/opengis/geoapi/Content.java
+++ b/geoapi/src/shared/java/org/opengis/geoapi/Content.java
@@ -115,6 +115,7 @@ public enum Content {
org.opengis.metadata.identification .ServiceIdentification .class,
org.opengis.referencing .ReferenceSystem .class, // Depends on Extent.
org.opengis.referencing.datum .Datum .class,
+ org.opengis.referencing.datum .DatumEnsemble .class,
org.opengis.referencing.cs .CoordinateSystemAxis .class,
org.opengis.referencing.cs .CoordinateSystem .class,
org.opengis.referencing.crs .CoordinateReferenceSystem .class,
@@ -122,6 +123,8 @@ public enum Content {
org.opengis.geometry .DirectPosition .class,
org.opengis.geometry .Envelope .class,
org.opengis.geometry .Geometry .class,
+ org.opengis.coordinate .CoordinateMetadata .class,
+ org.opengis.coordinate .CoordinateSet .class,
org.opengis.geometry.primitive .Point .class,
org.opengis.metadata.acquisition .Instrument .class,
org.opengis.metadata.acquisition .Platform .class,
@@ -223,6 +226,7 @@ public enum Content {
org.opengis.referencing.datum .ParametricDatum .class,
org.opengis.referencing.datum .TemporalDatum .class,
org.opengis.referencing.datum .VerticalDatum .class,
+ org.opengis.referencing.datum .DynamicReferenceFrame .class,
org.opengis.referencing.cs .AffineCS .class,
org.opengis.referencing.cs .CartesianCS .class,
org.opengis.referencing.cs .CylindricalCS .class,
@@ -256,6 +260,7 @@ public enum Content {
org.opengis.referencing.operation .Conversion .class,
org.opengis.referencing.operation .Projection .class,
org.opengis.referencing.operation .Transformation .class,
+ org.opengis.referencing.operation .PointMotionOperation .class,
org.opengis.referencing.operation .PassThroughOperation .class,
org.opengis.referencing.crs .GeneralDerivedCRS .class,
org.opengis.referencing.crs .DerivedCRS .class,
@@ -288,6 +293,7 @@ public enum Content {
org.opengis.referencing.operation .MathTransformFactory .class,
org.opengis.referencing.operation .CoordinateOperationFactory .class,
org.opengis.referencing.operation .CoordinateOperationAuthorityFactory .class,
+ org.opengis.referencing.operation .RegisterOperations .class,
org.opengis.filter .Expression .class,
org.opengis.filter .Literal .class,
org.opengis.filter .ValueReference .class,
@@ -363,9 +369,11 @@ public enum Content {
org.opengis.metadata.spatial .SpatialRepresentationType .class,
org.opengis.metadata.spatial .TopologyLevel .class,
org.opengis.referencing .ReferenceSystemType .class,
+ org.opengis.referencing.cs .CoordinateDataType .class,
org.opengis.referencing.cs .AxisDirection .class,
org.opengis.referencing.cs .RangeMeaning .class,
org.opengis.referencing.datum .PixelInCell .class,
+ org.opengis.referencing.datum .RealizationMethod .class,
org.opengis.referencing.datum .VerticalDatumType .class,
org.opengis.filter .ComparisonOperatorName .class,
org.opengis.filter .SpatialOperatorName .class,
diff --git a/geoapi/src/shared/java/org/opengis/geoapi/NameSpaces.java b/geoapi/src/shared/java/org/opengis/geoapi/NameSpaces.java
index be75a65d0..0a7cf3838 100644
--- a/geoapi/src/shared/java/org/opengis/geoapi/NameSpaces.java
+++ b/geoapi/src/shared/java/org/opengis/geoapi/NameSpaces.java
@@ -146,9 +146,15 @@ public QName name(final Class> type, final Map