001    /*
002     *    GeoAPI - Java interfaces for OGC/ISO standards
003     *    http://www.geoapi.org
004     *
005     *    Copyright (C) 2004-2012 Open Geospatial Consortium, Inc.
006     *    All Rights Reserved. http://www.opengeospatial.org/ogc/legal
007     *
008     *    Permission to use, copy, and modify this software and its documentation, with
009     *    or without modification, for any purpose and without fee or royalty is hereby
010     *    granted, provided that you include the following on ALL copies of the software
011     *    and documentation or portions thereof, including modifications, that you make:
012     *
013     *    1. The full text of this NOTICE in a location viewable to users of the
014     *       redistributed or derivative work.
015     *    2. Notice of any changes or modifications to the OGC files, including the
016     *       date changes were made.
017     *
018     *    THIS SOFTWARE AND DOCUMENTATION IS PROVIDED "AS IS," AND COPYRIGHT HOLDERS MAKE
019     *    NO REPRESENTATIONS OR WARRANTIES, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED
020     *    TO, WARRANTIES OF MERCHANTABILITY OR FITNESS FOR ANY PARTICULAR PURPOSE OR THAT
021     *    THE USE OF THE SOFTWARE OR DOCUMENTATION WILL NOT INFRINGE ANY THIRD PARTY
022     *    PATENTS, COPYRIGHTS, TRADEMARKS OR OTHER RIGHTS.
023     *
024     *    COPYRIGHT HOLDERS WILL NOT BE LIABLE FOR ANY DIRECT, INDIRECT, SPECIAL OR
025     *    CONSEQUENTIAL DAMAGES ARISING OUT OF ANY USE OF THE SOFTWARE OR DOCUMENTATION.
026     *
027     *    The name and trademarks of copyright holders may NOT be used in advertising or
028     *    publicity pertaining to the software without specific, written prior permission.
029     *    Title to copyright in this software and any associated documentation will at all
030     *    times remain with copyright holders.
031     */
032    package org.opengis.geometry.primitive;
033    
034    import java.util.List;
035    import java.util.ArrayList;
036    import org.opengis.util.CodeList;
037    import org.opengis.geometry.DirectPosition; // For javadoc
038    import org.opengis.annotation.UML;
039    
040    import static org.opengis.annotation.Obligation.*;
041    import static org.opengis.annotation.Specification.*;
042    
043    
044    /**
045     * List of codes that may be used to identify the interpolation mechanisms. As a code list,
046     * there is no intention of limiting the potential values of {@code CurveInterpolation}.
047     * Subtypes of {@link CurveSegment} can be spawned directly through subclassing, or indirectly
048     * by specifying an interpolation method and an associated control parameters record to support
049     * it.
050     *
051     * @version <A HREF="http://www.opengeospatial.org/standards/as">ISO 19107</A>
052     * @author Martin Desruisseaux (IRD)
053     * @since GeoAPI 1.0
054     */
055    @UML(identifier="GM_CurveInterpolation", specification=ISO_19107)
056    public final class CurveInterpolation extends CodeList<CurveInterpolation> {
057        /**
058         * Serial number for compatibility with different versions.
059         */
060        private static final long serialVersionUID = 170309206092641598L;
061    
062        /**
063         * List of all enumerations of this type.
064         * Must be declared before any enum declaration.
065         */
066        private static final List<CurveInterpolation> VALUES = new ArrayList<CurveInterpolation>(10);
067    
068        /**
069         * The interpolation mechanism shall return {@linkplain DirectPosition direct positions}
070         * on a straight line between each consecutive pair of control points.
071         */
072        @UML(identifier="linear", obligation=CONDITIONAL, specification=ISO_19107)
073        public static final CurveInterpolation LINEAR = new CurveInterpolation("LINEAR");
074    
075        /**
076         * The interpolation mechanism shall return {@linkplain DirectPosition direct positions} on a
077         * geodesic curve between each consecutive pair of control points. A geodesic curve is a curve
078         * of shortest length. The geodesic shall be determined in the coordinate reference system of
079         * the {@linkplain Curve curve} in which the {@linkplain CurveSegment curve segment} is used.
080         */
081        @UML(identifier="geodesic", obligation=CONDITIONAL, specification=ISO_19107)
082        public static final CurveInterpolation GEODESIC = new CurveInterpolation("GEODESIC");
083    
084        /**
085         * For each set of three consecutive control points, the middle one being an even offset from
086         * the beginning of the sequence of control points, the interpolation mechanism shall return
087         * {@linkplain DirectPosition direct positions} on a circular arc passing from the first point
088         * through the middle point to the third point. The sequence of control points shall have an
089         * odd number of elements. If the 3 points are co-linear, the circular arc becomes a straight
090         * line.
091         */
092        @UML(identifier="circularArc3Points", obligation=CONDITIONAL, specification=ISO_19107)
093        public static final CurveInterpolation CIRCULAR_ARC_3_POINTS = new CurveInterpolation(
094                                              "CIRCULAR_ARC_3_POINTS"); // Circular arc by 3 points
095    
096        /**
097         * For each consecutive pair of control points, the interpolation mechanism shall return
098         * {@linkplain DirectPosition direct positions} on a circular arc passing from the first
099         * control point to the second control point, such that the associated control parameter
100         * determines the offset of the center of the arc from the center point of the chord,
101         * positive for leftward and negative for rightward. This form shall only be used in
102         * 2 dimensions because of the restricted nature of the definition technique.
103         */
104        @UML(identifier="circularArc2PointWithBulge", obligation=CONDITIONAL, specification=ISO_19107)
105        public static final CurveInterpolation CIRCULAR_ARC_2_POINTS_WITH_BULGE = new CurveInterpolation(
106                                              "CIRCULAR_ARC_2_POINTS_WITH_BULGE"); // Circular arc by 2 points and bulge factor
107    
108        /**
109         * For each set of four consecutive control points, the interpolation mechanism shall return
110         * {@linkplain DirectPosition direct positions} on an elliptical arc passing from the first
111         * control point through the middle control points in order to the fourth control point. If
112         * the 4 control points are co-linear, the arc becomes a straight line. If the 4 control points
113         * are on the same circle, the arc becomes a circular one.
114         */
115        @UML(identifier="elliptical", obligation=CONDITIONAL, specification=ISO_19107)
116        public static final CurveInterpolation ELLIPTICAL = new CurveInterpolation(
117                                              "ELLIPTICAL"); // Elliptical arc
118    
119        /**
120         * Uses a Cornu's spiral or clothoid interpolation.
121         */
122        @UML(identifier="clothoid", obligation=CONDITIONAL, specification=ISO_19107)
123        public static final CurveInterpolation CLOTHOID = new CurveInterpolation(
124                                              "CLOTHOID");
125    
126        /**
127         * Same as {@linkplain #ELLIPTICAL elliptical arc} but using 5 consecutive control points
128         * to determine a conic section.
129         */
130        @UML(identifier="conic", obligation=CONDITIONAL, specification=ISO_19107)
131        public static final CurveInterpolation CONIC = new CurveInterpolation(
132                                              "CONIC"); // Conic arc
133        /**
134         * The control points are ordered as in a line-string, but they are spanned by a polynomial
135         * spline function. Normally, the degree of continuity is determined by the degree of the
136         * polynomials chosen.
137         */
138        @UML(identifier="polynomialSpline", obligation=CONDITIONAL, specification=ISO_19107)
139        public static final CurveInterpolation POLYNOMIAL_SPLINE = new CurveInterpolation(
140                                              "POLYNOMIAL_SPLINE"); // Polynomial Spline
141    
142        /**
143         * The control points are interpolated using initial tangents and cubic polynomials, a
144         * form of degree 3 polynomial spline.
145         */
146        @UML(identifier="cubicSpline", obligation=CONDITIONAL, specification=ISO_19107)
147        public static final CurveInterpolation CUBIC_SPLINE = new CurveInterpolation(
148                                              "CUBIC_SPLINE"); // Cubic Spline
149    
150        /**
151         * The control points are ordered as in a line string, but they are spanned by a
152         * rational (quotient of polynomials) spline function. Normally, the degree of continuity
153         * is determined by the degree of the polynomials chosen.
154         */
155        @UML(identifier="rationalSpline", obligation=CONDITIONAL, specification=ISO_19107)
156        public static final CurveInterpolation RATIONAL_SPLINE = new CurveInterpolation(
157                                              "RATIONAL_SPLINE"); // Rational Spline
158    
159        /**
160         * Constructs an enum with the given name. The new enum is
161         * automatically added to the list returned by {@link #values}.
162         *
163         * @param name The enum name. This name must not be in use by an other enum of this type.
164         */
165        private CurveInterpolation(final String name) {
166            super(name, VALUES);
167        }
168    
169        /**
170         * Returns the list of {@code CurveInterpolation}s.
171         *
172         * @return The list of codes declared in the current JVM.
173         */
174        public static CurveInterpolation[] values() {
175            synchronized (VALUES) {
176                return VALUES.toArray(new CurveInterpolation[VALUES.size()]);
177            }
178        }
179    
180        /**
181         * Returns the list of enumerations of the same kind than this enum.
182         */
183        public CurveInterpolation[] family() {
184            return values();
185        }
186    
187        /**
188         * Returns the curve interpolation that matches the given string, or returns a
189         * new one if none match it. More specifically, this methods returns the first instance for
190         * which <code>{@linkplain #name() name()}.{@linkplain String#equals equals}(code)</code>
191         * returns {@code true}. If no existing instance is found, then a new one is created for
192         * the given name.
193         *
194         * @param code The name of the code to fetch or to create.
195         * @return A code matching the given name.
196         */
197        public static CurveInterpolation valueOf(String code) {
198            return valueOf(CurveInterpolation.class, code);
199        }
200    }