001/*
002 *    GeoAPI - Java interfaces for OGC/ISO standards
003 *    Copyright © 2003-2024 Open Geospatial Consortium, Inc.
004 *    http://www.geoapi.org
005 *
006 *    Licensed under the Apache License, Version 2.0 (the "License");
007 *    you may not use this file except in compliance with the License.
008 *    You may obtain a copy of the License at
009 *
010 *        http://www.apache.org/licenses/LICENSE-2.0
011 *
012 *    Unless required by applicable law or agreed to in writing, software
013 *    distributed under the License is distributed on an "AS IS" BASIS,
014 *    WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
015 *    See the License for the specific language governing permissions and
016 *    limitations under the License.
017 */
018package org.opengis.referencing.crs;
019
020import java.util.Map;
021import org.opengis.referencing.cs.CartesianCS;
022import org.opengis.referencing.datum.DatumEnsemble;
023import org.opengis.referencing.datum.GeodeticDatum;
024import org.opengis.referencing.operation.Conversion;
025import org.opengis.referencing.operation.Projection;
026import org.opengis.annotation.UML;
027
028import static org.opengis.annotation.Obligation.*;
029import static org.opengis.annotation.Specification.*;
030
031
032/**
033 * A 2- or 3-dimensional <abbr>CRS</abbr> based on an approximation of the shape of the planet's surface by a plane.
034 * It is done in such a way that the distortion that is inherent to the approximation is carefully controlled and known.
035 * Distortion correction is commonly applied to calculated bearings and distances
036 * to produce values that are a close match to actual field values.
037 *
038 * <h2>Permitted coordinate systems</h2>
039 * This type of <abbr>CRS</abbr> can be used with coordinate systems of type {@link CartesianCS} only.
040 *
041 * @author  OGC Topic 2 (for abstract model and documentation)
042 * @author  Martin Desruisseaux (IRD, Geomatys)
043 * @version 3.1
044 * @since   1.0
045 *
046 * @see CRSAuthorityFactory#createProjectedCRS(String)
047 * @see CRSFactory#createProjectedCRS(Map, GeographicCRS, Conversion, CartesianCS)
048 */
049@UML(identifier="ProjectedCRS", specification=ISO_19111)
050public interface ProjectedCRS extends DerivedCRS {
051    /**
052     * Returns the <abbr>CRS</abbr> that is the base for this projected <abbr>CRS</abbr>.
053     * This is the {@linkplain Conversion#getSourceCRS() source <abbr>CRS</abbr>}
054     * of the {@linkplain #getConversionFromBase() deriving conversion}.
055     *
056     * <div class="warning"><b>Upcoming API change — conformance</b><br>
057     * The <abbr>CRS</abbr> type should be {@link GeodeticCRS} according ISO 19111:2019.
058     * This change may be applied in GeoAPI 4.0. In preparation for this possible change,
059     * users should assign the returned value to {@code GeodeticCRS} only.</div>
060     *
061     * @return the <abbr>CRS</abbr> that is the base for this projected <abbr>CRS</abbr>.
062     */
063    @Override
064    GeographicCRS getBaseCRS();
065
066    /**
067     * Returns the map projection from the base CRS to this projected CRS.
068     * The source <abbr>CRS</abbr> of the conversion, if non null, shall be the {@linkplain #getBaseCRS() base <abbr>CRS</abbr>}.
069     * The target <abbr>CRS</abbr> of the conversion, if non-null, shall be this <abbr>CRS</abbr>.
070     *
071     * <div class="warning"><b>Upcoming API change — conformance</b><br>
072     * The {@code Projection} type is not part of OGC/ISO abstract specification.
073     * This change may be applied in GeoAPI 4.0. In preparation for this possible change,
074     * users should assign the returned value to {@code Conversion} only.</div>
075     *
076     * @return the map projection from the base <abbr>CRS</abbr> to this projected <abbr>CRS</abbr>.
077     */
078    @Override
079    Projection getConversionFromBase();
080
081    /**
082     * Returns the coordinate system, which shall be Cartesian.
083     * In the 3D case the ellipsoidal height from the base <abbr>CRS</abbr>
084     * is retained to form a three-dimensional Cartesian coordinate system.
085     *
086     * @return the Cartesian coordinate system associated to this projected <abbr>CRS</abbr>.
087     */
088    @Override
089    @UML(identifier="coordinateSystem", obligation=MANDATORY, specification=ISO_19111)
090    CartesianCS getCoordinateSystem();
091
092    /**
093     * Returns the same datum as the base geodetic <abbr>CRS</abbr>.
094     * This property may be null if the base <abbr>CRS</abbr> is related to an object
095     * identified only by a {@linkplain #getDatumEnsemble() datum ensemble}.
096     *
097     * @return the datum of the base geodetic <abbr>CRS</abbr>, or {@code null} if the base is related
098     *         to an object identified only by a {@linkplain #getDatumEnsemble() datum ensemble}.
099     */
100    @Override
101    @UML(identifier="datum", obligation=MANDATORY, specification=ISO_19111)
102    default GeodeticDatum getDatum() {
103        return getBaseCRS().getDatum();
104    }
105
106    /**
107     * Returns the same datum ensemble as the base geodetic <abbr>CRS</abbr>.
108     * This property may be null if the base <abbr>CRS</abbr> is related to an object
109     * identified only by a single {@linkplain #getDatum() datum}.
110     *
111     * @return the datum ensemble of the base geodetic <abbr>CRS</abbr>, or {@code null} if the base
112     *         is related to an object identified only by a single {@linkplain #getDatum() datum}.
113     *
114     * @since 3.1
115     */
116    @Override
117    default DatumEnsemble<GeodeticDatum> getDatumEnsemble() {
118        return getBaseCRS().getDatumEnsemble();
119    }
120}