Line data Source code
1 : /******************************************************************************
2 : *
3 : * Project: OpenGIS Simple Features Reference Implementation
4 : * Purpose: Classes for manipulating simple features that is not specific
5 : * to a particular interface technology.
6 : * Author: Frank Warmerdam, warmerdam@pobox.com
7 : *
8 : ******************************************************************************
9 : * Copyright (c) 1999, Frank Warmerdam
10 : * Copyright (c) 2008-2014, Even Rouault <even dot rouault at spatialys.com>
11 : *
12 : * SPDX-License-Identifier: MIT
13 : ****************************************************************************/
14 :
15 : #ifndef OGR_GEOMETRY_H_INCLUDED
16 : #define OGR_GEOMETRY_H_INCLUDED
17 :
18 : #include "cpl_conv.h"
19 : #include "cpl_json.h"
20 : #include "gdal_fwd.h"
21 : #include "ogr_core.h"
22 : #include "ogr_geomcoordinateprecision.h"
23 : #include "ogr_spatialref.h"
24 :
25 : #include <climits>
26 : #include <cmath>
27 : #include <memory>
28 : #include <utility>
29 :
30 : /**
31 : * \file ogr_geometry.h
32 : *
33 : * Simple feature geometry classes.
34 : */
35 :
36 : /// WKT Output formatting options.
37 : enum class OGRWktFormat
38 : {
39 : F, ///< F-type formatting.
40 : G, ///< G-type formatting.
41 : Default ///< Format as F when abs(value) < 1, otherwise as G.
42 : };
43 :
44 : /// Options for formatting WKT output
45 : struct CPL_DLL OGRWktOptions
46 : {
47 : public:
48 : /// Type of WKT output to produce.
49 : OGRwkbVariant variant = wkbVariantOldOgc;
50 : /// Precision of output for X,Y coordinates. Interpretation depends on \c format.
51 : int xyPrecision;
52 : /// Precision of output for Z coordinates. Interpretation depends on \c format.
53 : int zPrecision;
54 : /// Precision of output for M coordinates. Interpretation depends on \c format.
55 : int mPrecision;
56 : /// Whether GDAL-special rounding should be applied.
57 : bool round;
58 : /// Formatting type.
59 : OGRWktFormat format = OGRWktFormat::Default;
60 :
61 : /// Constructor.
62 10988 : OGRWktOptions()
63 21976 : : xyPrecision(getDefaultPrecision()), zPrecision(xyPrecision),
64 10988 : mPrecision(zPrecision), round(getDefaultRound())
65 : {
66 10988 : }
67 :
68 : /// Constructor.
69 23590 : OGRWktOptions(int xyPrecisionIn, bool roundIn)
70 23590 : : xyPrecision(xyPrecisionIn), zPrecision(xyPrecision),
71 23590 : mPrecision(zPrecision), round(roundIn)
72 : {
73 23590 : }
74 :
75 : /// Copy constructor
76 : OGRWktOptions(const OGRWktOptions &) = default;
77 :
78 : /// Return default precision
79 : static int getDefaultPrecision();
80 :
81 : /// Return default rounding mode.
82 : static bool getDefaultRound();
83 : };
84 :
85 : /**
86 : * Simple container for a position.
87 : */
88 : class OGRRawPoint
89 : {
90 : public:
91 : /** Constructor */
92 973 : OGRRawPoint() : x(0.0), y(0.0)
93 : {
94 973 : }
95 :
96 : /** Constructor */
97 80 : OGRRawPoint(double xIn, double yIn) : x(xIn), y(yIn)
98 : {
99 80 : }
100 :
101 : /** x */
102 : double x;
103 : /** y */
104 : double y;
105 : };
106 :
107 : /** GEOS geometry type */
108 : typedef struct GEOSGeom_t *GEOSGeom;
109 : /** GEOS context handle type */
110 : typedef struct GEOSContextHandle_HS *GEOSContextHandle_t;
111 : /** SFCGAL geometry type */
112 : typedef void sfcgal_geometry_t;
113 :
114 : class OGRPoint;
115 : class OGRCurve;
116 : class OGRCompoundCurve;
117 : class OGRSimpleCurve;
118 : class OGRLinearRing;
119 : class OGRLineString;
120 : class OGRCircularString;
121 : class OGRSurface;
122 : class OGRCurvePolygon;
123 : class OGRPolygon;
124 : class OGRMultiPoint;
125 : class OGRMultiSurface;
126 : class OGRMultiPolygon;
127 : class OGRMultiCurve;
128 : class OGRMultiLineString;
129 : class OGRGeometryCollection;
130 : class OGRTriangle;
131 : class OGRPolyhedralSurface;
132 : class OGRTriangulatedSurface;
133 :
134 : //! @cond Doxygen_Suppress
135 : typedef OGRLineString *(*OGRCurveCasterToLineString)(OGRCurve *);
136 : typedef OGRLinearRing *(*OGRCurveCasterToLinearRing)(OGRCurve *);
137 :
138 : typedef OGRPolygon *(*OGRSurfaceCasterToPolygon)(OGRSurface *);
139 : typedef OGRCurvePolygon *(*OGRSurfaceCasterToCurvePolygon)(OGRSurface *);
140 : typedef OGRMultiPolygon *(*OGRPolyhedralSurfaceCastToMultiPolygon)(
141 : OGRPolyhedralSurface *);
142 :
143 : //! @endcond
144 :
145 : /** OGRGeometry visitor interface.
146 : * @since GDAL 2.3
147 : */
148 : class CPL_DLL IOGRGeometryVisitor
149 : {
150 : public:
151 : /** Destructor/ */
152 86 : virtual ~IOGRGeometryVisitor() = default;
153 :
154 : /** Visit OGRPoint. */
155 : virtual void visit(OGRPoint *) = 0;
156 : /** Visit OGRLineString. */
157 : virtual void visit(OGRLineString *) = 0;
158 : /** Visit OGRLinearRing. */
159 : virtual void visit(OGRLinearRing *) = 0;
160 : /** Visit OGRPolygon. */
161 : virtual void visit(OGRPolygon *) = 0;
162 : /** Visit OGRMultiPoint. */
163 : virtual void visit(OGRMultiPoint *) = 0;
164 : /** Visit OGRMultiLineString. */
165 : virtual void visit(OGRMultiLineString *) = 0;
166 : /** Visit OGRMultiPolygon. */
167 : virtual void visit(OGRMultiPolygon *) = 0;
168 : /** Visit OGRGeometryCollection. */
169 : virtual void visit(OGRGeometryCollection *) = 0;
170 : /** Visit OGRCircularString. */
171 : virtual void visit(OGRCircularString *) = 0;
172 : /** Visit OGRCompoundCurve. */
173 : virtual void visit(OGRCompoundCurve *) = 0;
174 : /** Visit OGRCurvePolygon. */
175 : virtual void visit(OGRCurvePolygon *) = 0;
176 : /** Visit OGRMultiCurve. */
177 : virtual void visit(OGRMultiCurve *) = 0;
178 : /** Visit OGRMultiSurface. */
179 : virtual void visit(OGRMultiSurface *) = 0;
180 : /** Visit OGRTriangle. */
181 : virtual void visit(OGRTriangle *) = 0;
182 : /** Visit OGRPolyhedralSurface. */
183 : virtual void visit(OGRPolyhedralSurface *) = 0;
184 : /** Visit OGRTriangulatedSurface. */
185 : virtual void visit(OGRTriangulatedSurface *) = 0;
186 : };
187 :
188 : /** OGRGeometry visitor default implementation.
189 : *
190 : * This default implementation will recurse down to calling
191 : * visit(OGRPoint*) on each point.
192 : *
193 : * @since GDAL 2.3
194 : */
195 : class CPL_DLL OGRDefaultGeometryVisitor : public IOGRGeometryVisitor
196 : {
197 : void _visit(OGRSimpleCurve *poGeom);
198 :
199 : public:
200 0 : void visit(OGRPoint *) override
201 : {
202 0 : }
203 :
204 : void visit(OGRLineString *) override;
205 : void visit(OGRLinearRing *) override;
206 : void visit(OGRPolygon *) override;
207 : void visit(OGRMultiPoint *) override;
208 : void visit(OGRMultiLineString *) override;
209 : void visit(OGRMultiPolygon *) override;
210 : void visit(OGRGeometryCollection *) override;
211 : void visit(OGRCircularString *) override;
212 : void visit(OGRCompoundCurve *) override;
213 : void visit(OGRCurvePolygon *) override;
214 : void visit(OGRMultiCurve *) override;
215 : void visit(OGRMultiSurface *) override;
216 : void visit(OGRTriangle *) override;
217 : void visit(OGRPolyhedralSurface *) override;
218 : void visit(OGRTriangulatedSurface *) override;
219 : };
220 :
221 : /** OGRGeometry visitor interface.
222 : * @since GDAL 2.3
223 : */
224 : class CPL_DLL IOGRConstGeometryVisitor
225 : {
226 : public:
227 : /** Destructor/ */
228 118 : virtual ~IOGRConstGeometryVisitor() = default;
229 :
230 : /** Visit OGRPoint. */
231 : virtual void visit(const OGRPoint *) = 0;
232 : /** Visit OGRLineString. */
233 : virtual void visit(const OGRLineString *) = 0;
234 : /** Visit OGRLinearRing. */
235 : virtual void visit(const OGRLinearRing *) = 0;
236 : /** Visit OGRPolygon. */
237 : virtual void visit(const OGRPolygon *) = 0;
238 : /** Visit OGRMultiPoint. */
239 : virtual void visit(const OGRMultiPoint *) = 0;
240 : /** Visit OGRMultiLineString. */
241 : virtual void visit(const OGRMultiLineString *) = 0;
242 : /** Visit OGRMultiPolygon. */
243 : virtual void visit(const OGRMultiPolygon *) = 0;
244 : /** Visit OGRGeometryCollection. */
245 : virtual void visit(const OGRGeometryCollection *) = 0;
246 : /** Visit OGRCircularString. */
247 : virtual void visit(const OGRCircularString *) = 0;
248 : /** Visit OGRCompoundCurve. */
249 : virtual void visit(const OGRCompoundCurve *) = 0;
250 : /** Visit OGRCurvePolygon. */
251 : virtual void visit(const OGRCurvePolygon *) = 0;
252 : /** Visit OGRMultiCurve. */
253 : virtual void visit(const OGRMultiCurve *) = 0;
254 : /** Visit OGRMultiSurface. */
255 : virtual void visit(const OGRMultiSurface *) = 0;
256 : /** Visit OGRTriangle. */
257 : virtual void visit(const OGRTriangle *) = 0;
258 : /** Visit OGRPolyhedralSurface. */
259 : virtual void visit(const OGRPolyhedralSurface *) = 0;
260 : /** Visit OGRTriangulatedSurface. */
261 : virtual void visit(const OGRTriangulatedSurface *) = 0;
262 : };
263 :
264 : /** OGRGeometry visitor default implementation.
265 : *
266 : * This default implementation will recurse down to calling
267 : * visit(const OGRPoint*) on each point.
268 : *
269 : * @since GDAL 2.3
270 : */
271 : class CPL_DLL OGRDefaultConstGeometryVisitor : public IOGRConstGeometryVisitor
272 : {
273 : void _visit(const OGRSimpleCurve *poGeom);
274 :
275 : public:
276 0 : void visit(const OGRPoint *) override
277 : {
278 0 : }
279 :
280 : void visit(const OGRLineString *) override;
281 : void visit(const OGRLinearRing *) override;
282 : void visit(const OGRPolygon *) override;
283 : void visit(const OGRMultiPoint *) override;
284 : void visit(const OGRMultiLineString *) override;
285 : void visit(const OGRMultiPolygon *) override;
286 : void visit(const OGRGeometryCollection *) override;
287 : void visit(const OGRCircularString *) override;
288 : void visit(const OGRCompoundCurve *) override;
289 : void visit(const OGRCurvePolygon *) override;
290 : void visit(const OGRMultiCurve *) override;
291 : void visit(const OGRMultiSurface *) override;
292 : void visit(const OGRTriangle *) override;
293 : void visit(const OGRPolyhedralSurface *) override;
294 : void visit(const OGRTriangulatedSurface *) override;
295 : };
296 :
297 : /************************************************************************/
298 : /* OGRGeomCoordinateBinaryPrecision */
299 : /************************************************************************/
300 :
301 : /** Geometry coordinate precision for a binary representation.
302 : *
303 : * @since GDAL 3.9
304 : */
305 : struct CPL_DLL OGRGeomCoordinateBinaryPrecision
306 : {
307 : int nXYBitPrecision =
308 : INT_MIN; /**< Number of bits needed to achieved XY precision. Typically
309 : computed with SetFromResolution() */
310 : int nZBitPrecision =
311 : INT_MIN; /**< Number of bits needed to achieved Z precision. Typically
312 : computed with SetFromResolution() */
313 : int nMBitPrecision =
314 : INT_MIN; /**< Number of bits needed to achieved M precision. Typically
315 : computed with SetFromResolution() */
316 :
317 : void SetFrom(const OGRGeomCoordinatePrecision &);
318 : };
319 :
320 : /************************************************************************/
321 : /* OGRwkbExportOptions */
322 : /************************************************************************/
323 :
324 : /** WKB export options.
325 : *
326 : * @since GDAL 3.9
327 : */
328 : struct CPL_DLL OGRwkbExportOptions
329 : {
330 : OGRwkbByteOrder eByteOrder = wkbNDR; /**< Byte order */
331 : OGRwkbVariant eWkbVariant = wkbVariantOldOgc; /**< WKB variant. */
332 : OGRGeomCoordinateBinaryPrecision sPrecision{}; /**< Binary precision. */
333 : };
334 :
335 : /************************************************************************/
336 : /* OGRGeometry */
337 : /************************************************************************/
338 :
339 : /**
340 : * Abstract base class for all geometry classes.
341 : *
342 : * Some spatial analysis methods require that OGR is built on the GEOS library
343 : * to work properly. The precise meaning of methods that describe spatial
344 : * relationships between geometries is described in the SFCOM, or other simple
345 : * features interface specifications, like "OpenGISĀ® Implementation
346 : * Specification for Geographic information - Simple feature access - Part 1:
347 : * Common architecture":
348 : * <a href="http://www.opengeospatial.org/standards/sfa">OGC 06-103r4</a>
349 : *
350 : * In GDAL 2.0, the hierarchy of classes has been extended with
351 : * <a href="https://portal.opengeospatial.org/files/?artifact_id=32024">
352 : * (working draft) ISO SQL/MM Part 3 (ISO/IEC 13249-3)</a> curve geometries :
353 : * CIRCULARSTRING (OGRCircularString), COMPOUNDCURVE (OGRCompoundCurve),
354 : * CURVEPOLYGON (OGRCurvePolygon), MULTICURVE (OGRMultiCurve) and
355 : * MULTISURFACE (OGRMultiSurface).
356 : *
357 : */
358 :
359 10573900 : class CPL_DLL OGRGeometry
360 : {
361 : private:
362 : const OGRSpatialReference *poSRS = nullptr; // may be NULL
363 :
364 : protected:
365 : //! @cond Doxygen_Suppress
366 : friend class OGRCurveCollection;
367 :
368 : unsigned int flags = 0;
369 :
370 : OGRErr importPreambleFromWkt(const char **ppszInput, int *pbHasZ,
371 : int *pbHasM, bool *pbIsEmpty);
372 : OGRErr importCurveCollectionFromWkt(
373 : const char **ppszInput, int bAllowEmptyComponent, int bAllowLineString,
374 : int bAllowCurve, int bAllowCompoundCurve,
375 : OGRErr (*pfnAddCurveDirectly)(OGRGeometry *poSelf, OGRCurve *poCurve));
376 : OGRErr importPreambleFromWkb(const unsigned char *pabyData, size_t nSize,
377 : OGRwkbByteOrder &eByteOrder,
378 : OGRwkbVariant eWkbVariant);
379 : OGRErr importPreambleOfCollectionFromWkb(const unsigned char *pabyData,
380 : size_t &nSize, size_t &nDataOffset,
381 : OGRwkbByteOrder &eByteOrder,
382 : size_t nMinSubGeomSize,
383 : int &nGeomCount,
384 : OGRwkbVariant eWkbVariant);
385 : OGRErr PointOnSurfaceInternal(OGRPoint *poPoint) const;
386 : OGRBoolean IsSFCGALCompatible() const;
387 :
388 : void HomogenizeDimensionalityWith(OGRGeometry *poOtherGeom);
389 : std::string wktTypeString(OGRwkbVariant variant) const;
390 :
391 : //! @endcond
392 :
393 : public:
394 : /************************************************************************/
395 : /* Bit flags for OGRGeometry */
396 : /* The OGR_G_NOT_EMPTY_POINT is used *only* for points. */
397 : /* Do not use these outside of the core. */
398 : /* Use Is3D, IsMeasured, set3D, and setMeasured instead */
399 : /************************************************************************/
400 :
401 : //! @cond Doxygen_Suppress
402 : static const unsigned int OGR_G_NOT_EMPTY_POINT = 0x1;
403 : static const unsigned int OGR_G_3D = 0x2;
404 : static const unsigned int OGR_G_MEASURED = 0x4;
405 : //! @endcond
406 :
407 : OGRGeometry();
408 : OGRGeometry(const OGRGeometry &other);
409 : OGRGeometry(OGRGeometry &&other);
410 : virtual ~OGRGeometry();
411 :
412 : OGRGeometry &operator=(const OGRGeometry &other);
413 : OGRGeometry &operator=(OGRGeometry &&other);
414 :
415 : /** Returns if two geometries are equal. */
416 : bool operator==(const OGRGeometry &other) const
417 : {
418 : return CPL_TO_BOOL(Equals(&other));
419 : }
420 :
421 : /** Returns if two geometries are different. */
422 1331 : bool operator!=(const OGRGeometry &other) const
423 : {
424 1331 : return !CPL_TO_BOOL(Equals(&other));
425 : }
426 :
427 : // Standard IGeometry.
428 : virtual int getDimension() const = 0;
429 : virtual int getCoordinateDimension() const;
430 : int CoordinateDimension() const;
431 : virtual OGRBoolean IsEmpty() const = 0;
432 : virtual OGRBoolean IsValid() const;
433 : virtual OGRGeometry *MakeValid(CSLConstList papszOptions = nullptr) const;
434 : virtual OGRGeometry *Normalize() const;
435 : virtual OGRBoolean IsSimple() const;
436 :
437 : /*! Returns whether the geometry has a Z component. */
438 20621494 : OGRBoolean Is3D() const
439 : {
440 20621494 : return (flags & OGR_G_3D) != 0;
441 : }
442 :
443 : /*! Returns whether the geometry has a M component. */
444 14788500 : OGRBoolean IsMeasured() const
445 : {
446 14788500 : return (flags & OGR_G_MEASURED) != 0;
447 : }
448 :
449 : virtual OGRBoolean IsRing() const;
450 : virtual void empty() = 0;
451 : virtual OGRGeometry *clone() const CPL_WARN_UNUSED_RESULT = 0;
452 : virtual void getEnvelope(OGREnvelope *psEnvelope) const = 0;
453 : virtual void getEnvelope(OGREnvelope3D *psEnvelope) const = 0;
454 :
455 : // IWks Interface.
456 : virtual size_t WkbSize() const = 0;
457 : OGRErr importFromWkb(const GByte *, size_t = static_cast<size_t>(-1),
458 : OGRwkbVariant = wkbVariantOldOgc);
459 : virtual OGRErr importFromWkb(const unsigned char *, size_t, OGRwkbVariant,
460 : size_t &nBytesConsumedOut) = 0;
461 : OGRErr exportToWkb(OGRwkbByteOrder, unsigned char *,
462 : OGRwkbVariant = wkbVariantOldOgc) const;
463 : virtual OGRErr exportToWkb(unsigned char *,
464 : const OGRwkbExportOptions * = nullptr) const = 0;
465 : virtual OGRErr importFromWkt(const char **ppszInput) = 0;
466 :
467 : #ifndef DOXYGEN_XML
468 : /** Deprecated.
469 : * @deprecated in GDAL 2.3
470 : */
471 : OGRErr importFromWkt(char **ppszInput)
472 : /*! @cond Doxygen_Suppress */
473 : CPL_WARN_DEPRECATED("Use importFromWkt(const char**) instead")
474 : /*! @endcond */
475 : {
476 : return importFromWkt(const_cast<const char **>(ppszInput));
477 : }
478 : #endif
479 :
480 : OGRErr exportToWkt(char **ppszDstText,
481 : OGRwkbVariant = wkbVariantOldOgc) const;
482 :
483 : /// Export a WKT geometry.
484 : /// \param opts Output options.
485 : /// \param err Pointer to error code, if desired.
486 : /// \return WKT string representing this geometry.
487 : virtual std::string exportToWkt(const OGRWktOptions &opts = OGRWktOptions(),
488 : OGRErr *err = nullptr) const = 0;
489 :
490 : // Non-standard.
491 : virtual OGRwkbGeometryType getGeometryType() const = 0;
492 : OGRwkbGeometryType getIsoGeometryType() const;
493 : virtual const char *getGeometryName() const = 0;
494 : void dumpReadable(FILE *, const char * = nullptr,
495 : CSLConstList papszOptions = nullptr) const;
496 : std::string dumpReadable(const char * = nullptr,
497 : CSLConstList papszOptions = nullptr) const;
498 : virtual void flattenTo2D() = 0;
499 : virtual char *exportToGML(const char *const *papszOptions = nullptr) const;
500 : virtual char *exportToKML() const;
501 : virtual char *exportToJson(CSLConstList papszOptions = nullptr) const;
502 :
503 : /** Accept a visitor. */
504 : virtual void accept(IOGRGeometryVisitor *visitor) = 0;
505 :
506 : /** Accept a visitor. */
507 : virtual void accept(IOGRConstGeometryVisitor *visitor) const = 0;
508 :
509 : static GEOSContextHandle_t createGEOSContext();
510 : static void freeGEOSContext(GEOSContextHandle_t hGEOSCtxt);
511 : GEOSGeom
512 : exportToGEOS(GEOSContextHandle_t hGEOSCtxt,
513 : bool bRemoveEmptyParts = false) const CPL_WARN_UNUSED_RESULT;
514 : virtual OGRBoolean hasCurveGeometry(int bLookForNonLinear = FALSE) const;
515 : virtual OGRGeometry *getCurveGeometry(
516 : const char *const *papszOptions = nullptr) const CPL_WARN_UNUSED_RESULT;
517 : virtual OGRGeometry *getLinearGeometry(
518 : double dfMaxAngleStepSizeDegrees = 0,
519 : const char *const *papszOptions = nullptr) const CPL_WARN_UNUSED_RESULT;
520 :
521 : void roundCoordinates(const OGRGeomCoordinatePrecision &sPrecision);
522 : void
523 : roundCoordinatesIEEE754(const OGRGeomCoordinateBinaryPrecision &options);
524 :
525 : // SFCGAL interfacing methods.
526 : //! @cond Doxygen_Suppress
527 : static sfcgal_geometry_t *OGRexportToSFCGAL(const OGRGeometry *poGeom);
528 : static OGRGeometry *SFCGALexportToOGR(const sfcgal_geometry_t *_geometry);
529 : //! @endcond
530 : virtual void closeRings();
531 :
532 : virtual bool setCoordinateDimension(int nDimension);
533 : virtual bool set3D(OGRBoolean bIs3D);
534 : virtual bool setMeasured(OGRBoolean bIsMeasured);
535 :
536 : virtual void assignSpatialReference(const OGRSpatialReference *poSR);
537 :
538 1974122 : const OGRSpatialReference *getSpatialReference(void) const
539 : {
540 1974122 : return poSRS;
541 : }
542 :
543 : virtual OGRErr transform(OGRCoordinateTransformation *poCT) = 0;
544 : OGRErr transformTo(const OGRSpatialReference *poSR);
545 :
546 : virtual bool segmentize(double dfMaxLength);
547 :
548 : // ISpatialRelation
549 : virtual OGRBoolean Intersects(const OGRGeometry *) const;
550 : virtual OGRBoolean Equals(const OGRGeometry *) const = 0;
551 : virtual OGRBoolean Disjoint(const OGRGeometry *) const;
552 : virtual OGRBoolean Touches(const OGRGeometry *) const;
553 : virtual OGRBoolean Crosses(const OGRGeometry *) const;
554 : virtual OGRBoolean Within(const OGRGeometry *) const;
555 : virtual OGRBoolean Contains(const OGRGeometry *) const;
556 : virtual OGRBoolean Overlaps(const OGRGeometry *) const;
557 : // virtual OGRBoolean Relate( const OGRGeometry *, const char * ) const;
558 : // virtual OGRGeometry *LocateAlong( double mValue ) const;
559 : // virtual OGRGeometry *LocateBetween( double mStart, double mEnd )
560 : // const;
561 :
562 : virtual OGRGeometry *Boundary() const CPL_WARN_UNUSED_RESULT;
563 : virtual double Distance(const OGRGeometry *) const;
564 : virtual OGRGeometry *ConvexHull() const CPL_WARN_UNUSED_RESULT;
565 : virtual OGRGeometry *
566 : ConcaveHull(double dfRatio, bool bAllowHoles) const CPL_WARN_UNUSED_RESULT;
567 : virtual OGRGeometry *
568 : Buffer(double dfDist, int nQuadSegs = 30) const CPL_WARN_UNUSED_RESULT;
569 : virtual OGRGeometry *
570 : BufferEx(double dfDistance,
571 : CSLConstList papszOptions) const CPL_WARN_UNUSED_RESULT;
572 : virtual OGRGeometry *
573 : Intersection(const OGRGeometry *) const CPL_WARN_UNUSED_RESULT;
574 : virtual OGRGeometry *
575 : Union(const OGRGeometry *) const CPL_WARN_UNUSED_RESULT;
576 : virtual OGRGeometry *UnionCascaded() const CPL_WARN_UNUSED_RESULT;
577 : OGRGeometry *UnaryUnion() const CPL_WARN_UNUSED_RESULT;
578 : virtual OGRGeometry *
579 : Difference(const OGRGeometry *) const CPL_WARN_UNUSED_RESULT;
580 : virtual OGRGeometry *
581 : SymDifference(const OGRGeometry *) const CPL_WARN_UNUSED_RESULT;
582 : virtual OGRErr Centroid(OGRPoint *poPoint) const;
583 : virtual OGRGeometry *
584 : Simplify(double dTolerance) const CPL_WARN_UNUSED_RESULT;
585 : OGRGeometry *
586 : SimplifyPreserveTopology(double dTolerance) const CPL_WARN_UNUSED_RESULT;
587 : virtual OGRGeometry *
588 : DelaunayTriangulation(double dfTolerance,
589 : int bOnlyEdges) const CPL_WARN_UNUSED_RESULT;
590 :
591 : virtual OGRGeometry *Polygonize() const CPL_WARN_UNUSED_RESULT;
592 :
593 : virtual double Distance3D(const OGRGeometry *poOtherGeom) const;
594 :
595 : OGRGeometry *SetPrecision(double dfGridSize, int nFlags) const;
596 :
597 : virtual bool hasEmptyParts() const;
598 : virtual void removeEmptyParts();
599 :
600 : //! @cond Doxygen_Suppress
601 : // backward compatibility to non-standard method names.
602 : OGRBoolean Intersect(OGRGeometry *) const
603 : CPL_WARN_DEPRECATED("Non standard method. "
604 : "Use Intersects() instead");
605 : OGRBoolean Equal(OGRGeometry *) const
606 : CPL_WARN_DEPRECATED("Non standard method. "
607 : "Use Equals() instead");
608 : OGRGeometry *SymmetricDifference(const OGRGeometry *) const
609 : CPL_WARN_DEPRECATED("Non standard method. "
610 : "Use SymDifference() instead");
611 : OGRGeometry *getBoundary() const
612 : CPL_WARN_DEPRECATED("Non standard method. "
613 : "Use Boundary() instead");
614 : //! @endcond
615 :
616 : //! @cond Doxygen_Suppress
617 : // Special HACK for DB2 7.2 support
618 : static int bGenerate_DB2_V72_BYTE_ORDER;
619 : //! @endcond
620 :
621 : virtual void swapXY();
622 :
623 : bool IsRectangle() const;
624 :
625 : //! @cond Doxygen_Suppress
626 : static OGRGeometry *CastToIdentity(OGRGeometry *poGeom)
627 : {
628 : return poGeom;
629 : }
630 :
631 : static OGRGeometry *CastToError(OGRGeometry *poGeom);
632 :
633 : //! @endcond
634 :
635 : /** Convert a OGRGeometry* to a OGRGeometryH.
636 : * @since GDAL 2.3
637 : */
638 461947 : static inline OGRGeometryH ToHandle(OGRGeometry *poGeom)
639 : {
640 461947 : return reinterpret_cast<OGRGeometryH>(poGeom);
641 : }
642 :
643 : /** Convert a OGRGeometryH to a OGRGeometry*.
644 : * @since GDAL 2.3
645 : */
646 1780533 : static inline OGRGeometry *FromHandle(OGRGeometryH hGeom)
647 : {
648 1780533 : return reinterpret_cast<OGRGeometry *>(hGeom);
649 : }
650 :
651 : /** Down-cast to OGRPoint*.
652 : * Implies prior checking that wkbFlatten(getGeometryType()) == wkbPoint.
653 : * @since GDAL 2.3
654 : */
655 187335 : inline OGRPoint *toPoint()
656 : {
657 187335 : return cpl::down_cast<OGRPoint *>(this);
658 : }
659 :
660 : /** Down-cast to OGRPoint*.
661 : * Implies prior checking that wkbFlatten(getGeometryType()) == wkbPoint.
662 : * @since GDAL 2.3
663 : */
664 60438 : inline const OGRPoint *toPoint() const
665 : {
666 60438 : return cpl::down_cast<const OGRPoint *>(this);
667 : }
668 :
669 : /** Down-cast to OGRCurve*.
670 : * Implies prior checking that OGR_GT_IsSubClass(getGeometryType(),
671 : * wkbCurve).
672 : * @since GDAL 2.3
673 : */
674 11351 : inline OGRCurve *toCurve()
675 : {
676 11351 : return cpl::down_cast<OGRCurve *>(this);
677 : }
678 :
679 : /** Down-cast to OGRCurve*.
680 : * Implies prior checking that OGR_GT_IsSubClass(getGeometryType(),
681 : * wkbCurve).
682 : * @since GDAL 2.3
683 : */
684 37 : inline const OGRCurve *toCurve() const
685 : {
686 37 : return cpl::down_cast<const OGRCurve *>(this);
687 : }
688 :
689 : /** Down-cast to OGRSimpleCurve*.
690 : * Implies prior checking that getGeometryType() is wkbLineString,
691 : * wkbCircularString or a derived type.
692 : * @since GDAL 2.3
693 : */
694 398261 : inline OGRSimpleCurve *toSimpleCurve()
695 : {
696 398261 : return cpl::down_cast<OGRSimpleCurve *>(this);
697 : }
698 :
699 : /** Down-cast to OGRSimpleCurve*.
700 : * Implies prior checking that getGeometryType() is wkbLineString,
701 : * wkbCircularString or a derived type.
702 : * @since GDAL 2.3
703 : */
704 48092 : inline const OGRSimpleCurve *toSimpleCurve() const
705 : {
706 48092 : return cpl::down_cast<const OGRSimpleCurve *>(this);
707 : }
708 :
709 : /** Down-cast to OGRLineString*.
710 : * Implies prior checking that wkbFlatten(getGeometryType()) ==
711 : * wkbLineString.
712 : * @since GDAL 2.3
713 : */
714 35126 : inline OGRLineString *toLineString()
715 : {
716 35126 : return cpl::down_cast<OGRLineString *>(this);
717 : }
718 :
719 : /** Down-cast to OGRLineString*.
720 : * Implies prior checking that wkbFlatten(getGeometryType()) ==
721 : * wkbLineString.
722 : * @since GDAL 2.3
723 : */
724 10351 : inline const OGRLineString *toLineString() const
725 : {
726 10351 : return cpl::down_cast<const OGRLineString *>(this);
727 : }
728 :
729 : /** Down-cast to OGRLinearRing*.
730 : * Implies prior checking that EQUAL(getGeometryName(), "LINEARRING").
731 : * @since GDAL 2.3
732 : */
733 255759 : inline OGRLinearRing *toLinearRing()
734 : {
735 255759 : return cpl::down_cast<OGRLinearRing *>(this);
736 : }
737 :
738 : /** Down-cast to OGRLinearRing*.
739 : * Implies prior checking that EQUAL(getGeometryName(), "LINEARRING").
740 : * @since GDAL 2.3
741 : */
742 107 : inline const OGRLinearRing *toLinearRing() const
743 : {
744 107 : return cpl::down_cast<const OGRLinearRing *>(this);
745 : }
746 :
747 : /** Down-cast to OGRCircularString*.
748 : * Implies prior checking that wkbFlatten(getGeometryType()) ==
749 : * wkbCircularString.
750 : * @since GDAL 2.3
751 : */
752 3 : inline OGRCircularString *toCircularString()
753 : {
754 3 : return cpl::down_cast<OGRCircularString *>(this);
755 : }
756 :
757 : /** Down-cast to OGRCircularString*.
758 : * Implies prior checking that wkbFlatten(getGeometryType()) ==
759 : * wkbCircularString.
760 : * @since GDAL 2.3
761 : */
762 44 : inline const OGRCircularString *toCircularString() const
763 : {
764 44 : return cpl::down_cast<const OGRCircularString *>(this);
765 : }
766 :
767 : /** Down-cast to OGRCompoundCurve*.
768 : * Implies prior checking that wkbFlatten(getGeometryType()) ==
769 : * wkbCompoundCurve.
770 : * @since GDAL 2.3
771 : */
772 2715 : inline OGRCompoundCurve *toCompoundCurve()
773 : {
774 2715 : return cpl::down_cast<OGRCompoundCurve *>(this);
775 : }
776 :
777 : /** Down-cast to OGRCompoundCurve*.
778 : * Implies prior checking that wkbFlatten(getGeometryType()) ==
779 : * wkbCompoundCurve.
780 : * @since GDAL 2.3
781 : */
782 890 : inline const OGRCompoundCurve *toCompoundCurve() const
783 : {
784 890 : return cpl::down_cast<const OGRCompoundCurve *>(this);
785 : }
786 :
787 : /** Down-cast to OGRSurface*.
788 : * Implies prior checking that OGR_GT_IsSubClass(getGeometryType(),
789 : * wkbSurface).
790 : * @since GDAL 2.3
791 : */
792 1577 : inline OGRSurface *toSurface()
793 : {
794 1577 : return cpl::down_cast<OGRSurface *>(this);
795 : }
796 :
797 : /** Down-cast to OGRSurface*.
798 : * Implies prior checking that OGR_GT_IsSubClass(getGeometryType(),
799 : * wkbSurface).
800 : * @since GDAL 2.3
801 : */
802 57 : inline const OGRSurface *toSurface() const
803 : {
804 57 : return cpl::down_cast<const OGRSurface *>(this);
805 : }
806 :
807 : /** Down-cast to OGRPolygon*.
808 : * Implies prior checking that wkbFlatten(getGeometryType()) == wkbPolygon
809 : * or wkbTriangle.
810 : * @since GDAL 2.3
811 : */
812 56700 : inline OGRPolygon *toPolygon()
813 : {
814 56700 : return cpl::down_cast<OGRPolygon *>(this);
815 : }
816 :
817 : /** Down-cast to OGRPolygon*.
818 : * Implies prior checking that wkbFlatten(getGeometryType()) == wkbPolygon
819 : * or wkbTriangle.
820 : * @since GDAL 2.3
821 : */
822 238617 : inline const OGRPolygon *toPolygon() const
823 : {
824 238617 : return cpl::down_cast<const OGRPolygon *>(this);
825 : }
826 :
827 : /** Down-cast to OGRTriangle*.
828 : * Implies prior checking that wkbFlatten(getGeometryType()) == wkbTriangle.
829 : * @since GDAL 2.3
830 : */
831 52261 : inline OGRTriangle *toTriangle()
832 : {
833 52261 : return cpl::down_cast<OGRTriangle *>(this);
834 : }
835 :
836 : /** Down-cast to OGRTriangle*.
837 : * Implies prior checking that wkbFlatten(getGeometryType()) == wkbTriangle.
838 : * @since GDAL 2.3
839 : */
840 2 : inline const OGRTriangle *toTriangle() const
841 : {
842 2 : return cpl::down_cast<const OGRTriangle *>(this);
843 : }
844 :
845 : /** Down-cast to OGRCurvePolygon*.
846 : * Implies prior checking that wkbFlatten(getGeometryType()) ==
847 : * wkbCurvePolygon or wkbPolygon or wkbTriangle.
848 : * @since GDAL 2.3
849 : */
850 68101 : inline OGRCurvePolygon *toCurvePolygon()
851 : {
852 68101 : return cpl::down_cast<OGRCurvePolygon *>(this);
853 : }
854 :
855 : /** Down-cast to OGRCurvePolygon*.
856 : * Implies prior checking that wkbFlatten(getGeometryType()) ==
857 : * wkbCurvePolygon or wkbPolygon or wkbTriangle.
858 : * @since GDAL 2.3
859 : */
860 42710 : inline const OGRCurvePolygon *toCurvePolygon() const
861 : {
862 42710 : return cpl::down_cast<const OGRCurvePolygon *>(this);
863 : }
864 :
865 : /** Down-cast to OGRGeometryCollection*.
866 : * Implies prior checking that OGR_GT_IsSubClass(getGeometryType(),
867 : * wkbGeometryCollection).
868 : * @since GDAL 2.3
869 : */
870 9483 : inline OGRGeometryCollection *toGeometryCollection()
871 : {
872 9483 : return cpl::down_cast<OGRGeometryCollection *>(this);
873 : }
874 :
875 : /** Down-cast to OGRGeometryCollection*.
876 : * Implies prior checking that OGR_GT_IsSubClass(getGeometryType(),
877 : * wkbGeometryCollection).
878 : * @since GDAL 2.3
879 : */
880 6174 : inline const OGRGeometryCollection *toGeometryCollection() const
881 : {
882 6174 : return cpl::down_cast<const OGRGeometryCollection *>(this);
883 : }
884 :
885 : /** Down-cast to OGRMultiPoint*.
886 : * Implies prior checking that wkbFlatten(getGeometryType()) ==
887 : * wkbMultiPoint.
888 : * @since GDAL 2.3
889 : */
890 129 : inline OGRMultiPoint *toMultiPoint()
891 : {
892 129 : return cpl::down_cast<OGRMultiPoint *>(this);
893 : }
894 :
895 : /** Down-cast to OGRMultiPoint*.
896 : * Implies prior checking that wkbFlatten(getGeometryType()) ==
897 : * wkbMultiPoint.
898 : * @since GDAL 2.3
899 : */
900 285 : inline const OGRMultiPoint *toMultiPoint() const
901 : {
902 285 : return cpl::down_cast<const OGRMultiPoint *>(this);
903 : }
904 :
905 : /** Down-cast to OGRMultiLineString*.
906 : * Implies prior checking that wkbFlatten(getGeometryType()) ==
907 : * wkbMultiLineString.
908 : * @since GDAL 2.3
909 : */
910 169 : inline OGRMultiLineString *toMultiLineString()
911 : {
912 169 : return cpl::down_cast<OGRMultiLineString *>(this);
913 : }
914 :
915 : /** Down-cast to OGRMultiLineString*.
916 : * Implies prior checking that wkbFlatten(getGeometryType()) ==
917 : * wkbMultiLineString.
918 : * @since GDAL 2.3
919 : */
920 242 : inline const OGRMultiLineString *toMultiLineString() const
921 : {
922 242 : return cpl::down_cast<const OGRMultiLineString *>(this);
923 : }
924 :
925 : /** Down-cast to OGRMultiPolygon*.
926 : * Implies prior checking that wkbFlatten(getGeometryType()) ==
927 : * wkbMultiPolygon.
928 : * @since GDAL 2.3
929 : */
930 641 : inline OGRMultiPolygon *toMultiPolygon()
931 : {
932 641 : return cpl::down_cast<OGRMultiPolygon *>(this);
933 : }
934 :
935 : /** Down-cast to OGRMultiPolygon*.
936 : * Implies prior checking that wkbFlatten(getGeometryType()) ==
937 : * wkbMultiPolygon.
938 : * @since GDAL 2.3
939 : */
940 66739 : inline const OGRMultiPolygon *toMultiPolygon() const
941 : {
942 66739 : return cpl::down_cast<const OGRMultiPolygon *>(this);
943 : }
944 :
945 : /** Down-cast to OGRMultiCurve*.
946 : * Implies prior checking that wkbFlatten(getGeometryType()) ==
947 : * wkbMultiCurve and derived types.
948 : * @since GDAL 2.3
949 : */
950 1087 : inline OGRMultiCurve *toMultiCurve()
951 : {
952 1087 : return cpl::down_cast<OGRMultiCurve *>(this);
953 : }
954 :
955 : /** Down-cast to OGRMultiCurve*.
956 : * Implies prior checking that wkbFlatten(getGeometryType()) ==
957 : * wkbMultiCurve and derived types.
958 : * @since GDAL 2.3
959 : */
960 21 : inline const OGRMultiCurve *toMultiCurve() const
961 : {
962 21 : return cpl::down_cast<const OGRMultiCurve *>(this);
963 : }
964 :
965 : /** Down-cast to OGRMultiSurface*.
966 : * Implies prior checking that wkbFlatten(getGeometryType()) ==
967 : * wkbMultiSurface and derived types.
968 : * @since GDAL 2.3
969 : */
970 13 : inline OGRMultiSurface *toMultiSurface()
971 : {
972 13 : return cpl::down_cast<OGRMultiSurface *>(this);
973 : }
974 :
975 : /** Down-cast to OGRMultiSurface*.
976 : * Implies prior checking that wkbFlatten(getGeometryType()) ==
977 : * wkbMultiSurface and derived types.
978 : * @since GDAL 2.3
979 : */
980 29 : inline const OGRMultiSurface *toMultiSurface() const
981 : {
982 29 : return cpl::down_cast<const OGRMultiSurface *>(this);
983 : }
984 :
985 : /** Down-cast to OGRPolyhedralSurface*.
986 : * Implies prior checking that wkbFlatten(getGeometryType()) ==
987 : * wkbPolyhedralSurface or wkbTIN.
988 : * @since GDAL 2.3
989 : */
990 1314 : inline OGRPolyhedralSurface *toPolyhedralSurface()
991 : {
992 1314 : return cpl::down_cast<OGRPolyhedralSurface *>(this);
993 : }
994 :
995 : /** Down-cast to OGRPolyhedralSurface*.
996 : * Implies prior checking that wkbFlatten(getGeometryType()) ==
997 : * wkbPolyhedralSurface or wkbTIN.
998 : * @since GDAL 2.3
999 : */
1000 5766 : inline const OGRPolyhedralSurface *toPolyhedralSurface() const
1001 : {
1002 5766 : return cpl::down_cast<const OGRPolyhedralSurface *>(this);
1003 : }
1004 :
1005 : /** Down-cast to OGRTriangulatedSurface*.
1006 : * Implies prior checking that wkbFlatten(getGeometryType()) == wkbTIN.
1007 : * @since GDAL 2.3
1008 : */
1009 4 : inline OGRTriangulatedSurface *toTriangulatedSurface()
1010 : {
1011 4 : return cpl::down_cast<OGRTriangulatedSurface *>(this);
1012 : }
1013 :
1014 : /** Down-cast to OGRTriangulatedSurface*.
1015 : * Implies prior checking that wkbFlatten(getGeometryType()) == wkbTIN.
1016 : * @since GDAL 2.3
1017 : */
1018 2 : inline const OGRTriangulatedSurface *toTriangulatedSurface() const
1019 : {
1020 2 : return cpl::down_cast<const OGRTriangulatedSurface *>(this);
1021 : }
1022 : };
1023 :
1024 : //! @cond Doxygen_Suppress
1025 : struct CPL_DLL OGRGeometryUniquePtrDeleter
1026 : {
1027 : void operator()(OGRGeometry *) const;
1028 : };
1029 :
1030 : //! @endcond
1031 :
1032 : /** Unique pointer type for OGRGeometry.
1033 : * @since GDAL 2.3
1034 : */
1035 : typedef std::unique_ptr<OGRGeometry, OGRGeometryUniquePtrDeleter>
1036 : OGRGeometryUniquePtr;
1037 :
1038 : //! @cond Doxygen_Suppress
1039 : #define OGR_FORBID_DOWNCAST_TO(name) \
1040 : inline OGR##name *to##name() = delete; \
1041 : inline const OGR##name *to##name() const = delete;
1042 :
1043 : #define OGR_FORBID_DOWNCAST_TO_POINT OGR_FORBID_DOWNCAST_TO(Point)
1044 : #define OGR_FORBID_DOWNCAST_TO_CURVE OGR_FORBID_DOWNCAST_TO(Curve)
1045 : #define OGR_FORBID_DOWNCAST_TO_SIMPLE_CURVE OGR_FORBID_DOWNCAST_TO(SimpleCurve)
1046 : #define OGR_FORBID_DOWNCAST_TO_LINESTRING OGR_FORBID_DOWNCAST_TO(LineString)
1047 : #define OGR_FORBID_DOWNCAST_TO_LINEARRING OGR_FORBID_DOWNCAST_TO(LinearRing)
1048 : #define OGR_FORBID_DOWNCAST_TO_CIRCULARSTRING \
1049 : OGR_FORBID_DOWNCAST_TO(CircularString)
1050 : #define OGR_FORBID_DOWNCAST_TO_COMPOUNDCURVE \
1051 : OGR_FORBID_DOWNCAST_TO(CompoundCurve)
1052 : #define OGR_FORBID_DOWNCAST_TO_SURFACE OGR_FORBID_DOWNCAST_TO(Surface)
1053 : #define OGR_FORBID_DOWNCAST_TO_CURVEPOLYGON OGR_FORBID_DOWNCAST_TO(CurvePolygon)
1054 : #define OGR_FORBID_DOWNCAST_TO_POLYGON OGR_FORBID_DOWNCAST_TO(Polygon)
1055 : #define OGR_FORBID_DOWNCAST_TO_TRIANGLE OGR_FORBID_DOWNCAST_TO(Triangle)
1056 : #define OGR_FORBID_DOWNCAST_TO_MULTIPOINT OGR_FORBID_DOWNCAST_TO(MultiPoint)
1057 : #define OGR_FORBID_DOWNCAST_TO_MULTICURVE OGR_FORBID_DOWNCAST_TO(MultiCurve)
1058 : #define OGR_FORBID_DOWNCAST_TO_MULTILINESTRING \
1059 : OGR_FORBID_DOWNCAST_TO(MultiLineString)
1060 : #define OGR_FORBID_DOWNCAST_TO_MULTISURFACE OGR_FORBID_DOWNCAST_TO(MultiSurface)
1061 : #define OGR_FORBID_DOWNCAST_TO_MULTIPOLYGON OGR_FORBID_DOWNCAST_TO(MultiPolygon)
1062 : #define OGR_FORBID_DOWNCAST_TO_GEOMETRYCOLLECTION \
1063 : OGR_FORBID_DOWNCAST_TO(GeometryCollection)
1064 : #define OGR_FORBID_DOWNCAST_TO_POLYHEDRALSURFACE \
1065 : OGR_FORBID_DOWNCAST_TO(PolyhedralSurface)
1066 : #define OGR_FORBID_DOWNCAST_TO_TIN OGR_FORBID_DOWNCAST_TO(TriangulatedSurface)
1067 :
1068 : #define OGR_ALLOW_UPCAST_TO(name) \
1069 : inline OGR##name *to##name() \
1070 : { \
1071 : return this; \
1072 : } \
1073 : inline const OGR##name *to##name() const \
1074 : { \
1075 : return this; \
1076 : }
1077 :
1078 : #ifndef SUPPRESS_OGR_ALLOW_CAST_TO_THIS_WARNING
1079 : #define CAST_TO_THIS_WARNING CPL_WARN_DEPRECATED("Casting to this is useless")
1080 : #else
1081 : #define CAST_TO_THIS_WARNING
1082 : #endif
1083 :
1084 : #define OGR_ALLOW_CAST_TO_THIS(name) \
1085 : inline OGR##name *to##name() CAST_TO_THIS_WARNING \
1086 : { \
1087 : return this; \
1088 : } \
1089 : inline const OGR##name *to##name() const CAST_TO_THIS_WARNING \
1090 : { \
1091 : return this; \
1092 : }
1093 :
1094 : #define OGR_FORBID_DOWNCAST_TO_ALL_CURVES \
1095 : OGR_FORBID_DOWNCAST_TO_CURVE \
1096 : OGR_FORBID_DOWNCAST_TO_SIMPLE_CURVE \
1097 : OGR_FORBID_DOWNCAST_TO_LINESTRING \
1098 : OGR_FORBID_DOWNCAST_TO_LINEARRING \
1099 : OGR_FORBID_DOWNCAST_TO_CIRCULARSTRING \
1100 : OGR_FORBID_DOWNCAST_TO_COMPOUNDCURVE
1101 :
1102 : #define OGR_FORBID_DOWNCAST_TO_ALL_SURFACES \
1103 : OGR_FORBID_DOWNCAST_TO_SURFACE \
1104 : OGR_FORBID_DOWNCAST_TO_CURVEPOLYGON \
1105 : OGR_FORBID_DOWNCAST_TO_POLYGON \
1106 : OGR_FORBID_DOWNCAST_TO_TRIANGLE \
1107 : OGR_FORBID_DOWNCAST_TO_POLYHEDRALSURFACE \
1108 : OGR_FORBID_DOWNCAST_TO_TIN
1109 :
1110 : #define OGR_FORBID_DOWNCAST_TO_ALL_SINGLES \
1111 : OGR_FORBID_DOWNCAST_TO_POINT \
1112 : OGR_FORBID_DOWNCAST_TO_ALL_CURVES \
1113 : OGR_FORBID_DOWNCAST_TO_ALL_SURFACES
1114 :
1115 : #define OGR_FORBID_DOWNCAST_TO_ALL_MULTI \
1116 : OGR_FORBID_DOWNCAST_TO_GEOMETRYCOLLECTION \
1117 : OGR_FORBID_DOWNCAST_TO_MULTIPOINT \
1118 : OGR_FORBID_DOWNCAST_TO_MULTICURVE \
1119 : OGR_FORBID_DOWNCAST_TO_MULTILINESTRING \
1120 : OGR_FORBID_DOWNCAST_TO_MULTISURFACE \
1121 : OGR_FORBID_DOWNCAST_TO_MULTIPOLYGON
1122 :
1123 : //! @endcond
1124 :
1125 : /************************************************************************/
1126 : /* OGRPoint */
1127 : /************************************************************************/
1128 :
1129 : /**
1130 : * Point class.
1131 : *
1132 : * Implements SFCOM IPoint methods.
1133 : */
1134 :
1135 332997 : class CPL_DLL OGRPoint : public OGRGeometry
1136 : {
1137 : double x;
1138 : double y;
1139 : double z;
1140 : double m;
1141 :
1142 : public:
1143 : OGRPoint();
1144 : OGRPoint(double x, double y);
1145 : OGRPoint(double x, double y, double z);
1146 : OGRPoint(double x, double y, double z, double m);
1147 : OGRPoint(const OGRPoint &other);
1148 : /** Move constructor */
1149 112354 : OGRPoint(OGRPoint &&other) = default;
1150 : static OGRPoint *createXYM(double x, double y, double m);
1151 :
1152 : OGRPoint &operator=(const OGRPoint &other);
1153 : /** Move assignment operator */
1154 : OGRPoint &operator=(OGRPoint &&other) = default;
1155 :
1156 : // IWks Interface
1157 : size_t WkbSize() const override;
1158 : OGRErr importFromWkb(const unsigned char *, size_t, OGRwkbVariant,
1159 : size_t &nBytesConsumedOut) override;
1160 : OGRErr exportToWkb(unsigned char *,
1161 : const OGRwkbExportOptions * = nullptr) const override;
1162 :
1163 : #ifndef DOXYGEN_XML
1164 : using OGRGeometry::importFromWkt; /** deprecated */
1165 : #endif
1166 :
1167 : OGRErr importFromWkt(const char **) override;
1168 :
1169 : #ifndef DOXYGEN_XML
1170 : using OGRGeometry::exportToWkt;
1171 : #endif
1172 :
1173 : /// Export a point to WKT
1174 : /// \param opts Output options.
1175 : /// \param err Pointer to error code, if desired.
1176 : /// \return WKT string representing this point.
1177 : virtual std::string exportToWkt(const OGRWktOptions &opts = OGRWktOptions(),
1178 : OGRErr *err = nullptr) const override;
1179 :
1180 : // IGeometry
1181 : virtual int getDimension() const override;
1182 : virtual OGRPoint *clone() const override;
1183 : virtual void empty() override;
1184 : virtual void getEnvelope(OGREnvelope *psEnvelope) const override;
1185 : virtual void getEnvelope(OGREnvelope3D *psEnvelope) const override;
1186 :
1187 4297408 : virtual OGRBoolean IsEmpty() const override
1188 : {
1189 4297408 : return !(flags & OGR_G_NOT_EMPTY_POINT);
1190 : }
1191 :
1192 : // IPoint
1193 : /** Return x */
1194 13279889 : double getX() const
1195 : {
1196 13279889 : return x;
1197 : }
1198 :
1199 : /** Return y */
1200 13028230 : double getY() const
1201 : {
1202 13028230 : return y;
1203 : }
1204 :
1205 : /** Return z */
1206 5226797 : double getZ() const
1207 : {
1208 5226797 : return z;
1209 : }
1210 :
1211 : /** Return m */
1212 916 : double getM() const
1213 : {
1214 916 : return m;
1215 : }
1216 :
1217 : // Non standard
1218 : virtual bool setCoordinateDimension(int nDimension) override;
1219 :
1220 : /** Set x
1221 : * @param xIn x
1222 : */
1223 1964081 : void setX(double xIn)
1224 : {
1225 1964081 : x = xIn;
1226 1964081 : if (std::isnan(x) || std::isnan(y))
1227 5 : flags &= ~OGR_G_NOT_EMPTY_POINT;
1228 : else
1229 1964080 : flags |= OGR_G_NOT_EMPTY_POINT;
1230 1964081 : }
1231 :
1232 : /** Set y
1233 : * @param yIn y
1234 : */
1235 1964019 : void setY(double yIn)
1236 : {
1237 1964019 : y = yIn;
1238 1964019 : if (std::isnan(x) || std::isnan(y))
1239 7 : flags &= ~OGR_G_NOT_EMPTY_POINT;
1240 : else
1241 1964016 : flags |= OGR_G_NOT_EMPTY_POINT;
1242 1964019 : }
1243 :
1244 : /** Set z
1245 : * @param zIn z
1246 : */
1247 49891 : void setZ(double zIn)
1248 : {
1249 49891 : z = zIn;
1250 49891 : flags |= OGR_G_3D;
1251 49891 : }
1252 :
1253 : /** Set m
1254 : * @param mIn m
1255 : */
1256 28671 : void setM(double mIn)
1257 : {
1258 28671 : m = mIn;
1259 28671 : flags |= OGR_G_MEASURED;
1260 28671 : }
1261 :
1262 : // ISpatialRelation
1263 : virtual OGRBoolean Equals(const OGRGeometry *) const override;
1264 : virtual OGRBoolean Intersects(const OGRGeometry *) const override;
1265 : virtual OGRBoolean Within(const OGRGeometry *) const override;
1266 :
1267 : // Non standard from OGRGeometry
1268 : virtual const char *getGeometryName() const override;
1269 : virtual OGRwkbGeometryType getGeometryType() const override;
1270 : virtual OGRErr transform(OGRCoordinateTransformation *poCT) override;
1271 : virtual void flattenTo2D() override;
1272 :
1273 1150 : virtual void accept(IOGRGeometryVisitor *visitor) override
1274 : {
1275 1150 : visitor->visit(this);
1276 1150 : }
1277 :
1278 64959 : virtual void accept(IOGRConstGeometryVisitor *visitor) const override
1279 : {
1280 64959 : visitor->visit(this);
1281 64959 : }
1282 :
1283 : virtual void swapXY() override;
1284 :
1285 : OGR_ALLOW_CAST_TO_THIS(Point)
1286 : OGR_FORBID_DOWNCAST_TO_ALL_CURVES
1287 : OGR_FORBID_DOWNCAST_TO_ALL_SURFACES
1288 : OGR_FORBID_DOWNCAST_TO_ALL_MULTI
1289 : };
1290 :
1291 : /************************************************************************/
1292 : /* OGRPointIterator */
1293 : /************************************************************************/
1294 :
1295 : /**
1296 : * Interface for a point iterator.
1297 : *
1298 : * @since GDAL 2.0
1299 : */
1300 :
1301 256 : class CPL_DLL OGRPointIterator
1302 : {
1303 : public:
1304 : virtual ~OGRPointIterator();
1305 : virtual OGRBoolean getNextPoint(OGRPoint *p) = 0;
1306 :
1307 : static void destroy(OGRPointIterator *);
1308 : };
1309 :
1310 : /************************************************************************/
1311 : /* OGRCurve */
1312 : /************************************************************************/
1313 :
1314 : /**
1315 : * Abstract curve base class for OGRLineString, OGRCircularString and
1316 : * OGRCompoundCurve
1317 : */
1318 :
1319 8 : class CPL_DLL OGRCurve : public OGRGeometry
1320 : {
1321 : protected:
1322 : //! @cond Doxygen_Suppress
1323 3474103 : OGRCurve() = default;
1324 301550 : OGRCurve(const OGRCurve &other) = default;
1325 4 : OGRCurve(OGRCurve &&other) = default;
1326 :
1327 : virtual OGRCurveCasterToLineString GetCasterToLineString() const = 0;
1328 : virtual OGRCurveCasterToLinearRing GetCasterToLinearRing() const = 0;
1329 :
1330 : friend class OGRCurvePolygon;
1331 : friend class OGRCompoundCurve;
1332 : //! @endcond
1333 : virtual int ContainsPoint(const OGRPoint *p) const;
1334 : virtual int IntersectsPoint(const OGRPoint *p) const;
1335 : virtual double get_AreaOfCurveSegments() const = 0;
1336 :
1337 : private:
1338 38 : class CPL_DLL ConstIterator
1339 : {
1340 : struct Private;
1341 : std::unique_ptr<Private> m_poPrivate;
1342 :
1343 : public:
1344 : ConstIterator(const OGRCurve *poSelf, bool bStart);
1345 : ConstIterator(ConstIterator &&oOther) noexcept;
1346 : ConstIterator &operator=(ConstIterator &&oOther);
1347 : ~ConstIterator();
1348 : const OGRPoint &operator*() const;
1349 : ConstIterator &operator++();
1350 : bool operator!=(const ConstIterator &it) const;
1351 : };
1352 :
1353 : friend inline ConstIterator begin(const OGRCurve *);
1354 : friend inline ConstIterator end(const OGRCurve *);
1355 :
1356 : public:
1357 : //! @cond Doxygen_Suppress
1358 : OGRCurve &operator=(const OGRCurve &other);
1359 : OGRCurve &operator=(OGRCurve &&other) = default;
1360 : //! @endcond
1361 :
1362 : /** Type of child elements. */
1363 : typedef OGRPoint ChildType;
1364 :
1365 : /** Return begin of a point iterator.
1366 : *
1367 : * Using this iterator for standard range-based loops is safe, but
1368 : * due to implementation limitations, you shouldn't try to access
1369 : * (dereference) more than one iterator step at a time, since you will get
1370 : * a reference to the same OGRPoint& object.
1371 : * @since GDAL 2.3
1372 : */
1373 : ConstIterator begin() const;
1374 : /** Return end of a point iterator. */
1375 : ConstIterator end() const;
1376 :
1377 : // IGeometry
1378 : virtual OGRCurve *clone() const override = 0;
1379 :
1380 : // ICurve methods
1381 : virtual double get_Length() const = 0;
1382 : virtual void StartPoint(OGRPoint *) const = 0;
1383 : virtual void EndPoint(OGRPoint *) const = 0;
1384 : virtual int get_IsClosed() const;
1385 : virtual void Value(double, OGRPoint *) const = 0;
1386 : virtual OGRLineString *
1387 : CurveToLine(double dfMaxAngleStepSizeDegrees = 0,
1388 : const char *const *papszOptions = nullptr) const = 0;
1389 : virtual int getDimension() const override;
1390 :
1391 : // non standard
1392 : virtual int getNumPoints() const = 0;
1393 : virtual OGRPointIterator *getPointIterator() const = 0;
1394 : virtual OGRBoolean IsConvex() const;
1395 : virtual double get_Area() const = 0;
1396 : virtual double get_GeodesicArea(
1397 : const OGRSpatialReference *poSRSOverride = nullptr) const = 0;
1398 : virtual double get_GeodesicLength(
1399 : const OGRSpatialReference *poSRSOverride = nullptr) const = 0;
1400 : virtual int isClockwise() const;
1401 : virtual void reversePoints() = 0;
1402 :
1403 : /** Down-cast to OGRSimpleCurve*.
1404 : * Implies prior checking that wkbFlatten(getGeometryType()) ==
1405 : * wkbLineString or wkbCircularString. */
1406 492 : inline OGRSimpleCurve *toSimpleCurve()
1407 : {
1408 492 : return cpl::down_cast<OGRSimpleCurve *>(this);
1409 : }
1410 :
1411 : /** Down-cast to OGRSimpleCurve*.
1412 : * Implies prior checking that wkbFlatten(getGeometryType()) ==
1413 : * wkbLineString or wkbCircularString. */
1414 : inline const OGRSimpleCurve *toSimpleCurve() const
1415 : {
1416 : return cpl::down_cast<const OGRSimpleCurve *>(this);
1417 : }
1418 :
1419 : static OGRCompoundCurve *CastToCompoundCurve(OGRCurve *puCurve);
1420 : static OGRLineString *CastToLineString(OGRCurve *poCurve);
1421 : static OGRLinearRing *CastToLinearRing(OGRCurve *poCurve);
1422 :
1423 : OGR_FORBID_DOWNCAST_TO_POINT
1424 : OGR_ALLOW_CAST_TO_THIS(Curve)
1425 : OGR_FORBID_DOWNCAST_TO_ALL_SURFACES
1426 : OGR_FORBID_DOWNCAST_TO_ALL_MULTI
1427 : };
1428 :
1429 : //! @cond Doxygen_Suppress
1430 : /** @see OGRCurve::begin() const */
1431 8 : inline OGRCurve::ConstIterator begin(const OGRCurve *poCurve)
1432 : {
1433 8 : return poCurve->begin();
1434 : }
1435 :
1436 : /** @see OGRCurve::end() const */
1437 8 : inline OGRCurve::ConstIterator end(const OGRCurve *poCurve)
1438 : {
1439 8 : return poCurve->end();
1440 : }
1441 :
1442 : //! @endcond
1443 :
1444 : /************************************************************************/
1445 : /* OGRIteratedPoint */
1446 : /************************************************************************/
1447 :
1448 : /*!
1449 : Implementation detail of OGRSimpleCurve::Iterator.
1450 :
1451 : This class is a simple wrapper over OGRPoint, which shouldn't be directly
1452 : referenced by the user other than trough auto&& in an iteator
1453 : over a OGRSimpleCurve.
1454 :
1455 : Typical usage pattern is:
1456 : \verbatim
1457 : for (auto&& p: line)
1458 : {
1459 : p.setZ(100);
1460 : }
1461 : \endverbatim
1462 :
1463 : The lifetime of this object is coupled to the one of the curve on which it
1464 : was returned. It is thus also illegal to modify it once the curve has been
1465 : deleted.
1466 :
1467 : @since GDAL 3.6
1468 : */
1469 : class CPL_DLL OGRIteratedPoint : public OGRPoint
1470 : {
1471 : private:
1472 : friend class OGRSimpleCurve;
1473 :
1474 : OGRSimpleCurve *m_poCurve = nullptr;
1475 : int m_nPos = 0;
1476 :
1477 274 : OGRIteratedPoint() = default;
1478 :
1479 : CPL_DISALLOW_COPY_ASSIGN(OGRIteratedPoint)
1480 :
1481 : public:
1482 : /** Set x
1483 : * @param xIn x
1484 : */
1485 : void setX(double xIn);
1486 : /** Set y
1487 : * @param yIn y
1488 : */
1489 : void setY(double yIn);
1490 : /** Set z
1491 : * @param zIn z
1492 : */
1493 : void setZ(double zIn);
1494 : /** Set m
1495 : * @param mIn m
1496 : */
1497 : void setM(double mIn);
1498 : };
1499 :
1500 : /************************************************************************/
1501 : /* OGRSimpleCurve */
1502 : /************************************************************************/
1503 :
1504 : /**
1505 : * Abstract curve base class for OGRLineString and OGRCircularString
1506 : *
1507 : * Note: this class does not exist in SQL/MM standard and exists for
1508 : * implementation convenience.
1509 : *
1510 : * @since GDAL 2.0
1511 : */
1512 :
1513 : class CPL_DLL OGRSimpleCurve : public OGRCurve
1514 : {
1515 : protected:
1516 : //! @cond Doxygen_Suppress
1517 : friend class OGRGeometry;
1518 :
1519 : int nPointCount = 0;
1520 : int m_nPointCapacity = 0;
1521 : OGRRawPoint *paoPoints = nullptr;
1522 : double *padfZ = nullptr;
1523 : double *padfM = nullptr;
1524 :
1525 : bool Make3D();
1526 : void Make2D();
1527 : void RemoveM();
1528 : bool AddM();
1529 :
1530 : OGRErr importFromWKTListOnly(const char **ppszInput, int bHasZ, int bHasM,
1531 : OGRRawPoint *&paoPointsIn, int &nMaxPoints,
1532 : double *&padfZIn);
1533 : //! @endcond
1534 :
1535 : virtual double get_LinearArea() const;
1536 :
1537 : /** Constructor */
1538 3471362 : OGRSimpleCurve() = default;
1539 :
1540 : OGRSimpleCurve(const OGRSimpleCurve &other);
1541 :
1542 : OGRSimpleCurve(OGRSimpleCurve &&other);
1543 :
1544 : private:
1545 : class CPL_DLL Iterator
1546 : {
1547 : struct Private;
1548 : std::unique_ptr<Private> m_poPrivate;
1549 : void update();
1550 :
1551 : public:
1552 : Iterator(OGRSimpleCurve *poSelf, int nPos);
1553 : Iterator(Iterator &&oOther) noexcept; // declared but not defined.
1554 : // Needed for gcc 5.4 at least
1555 : ~Iterator();
1556 : OGRIteratedPoint &operator*();
1557 : Iterator &operator++();
1558 : bool operator!=(const Iterator &it) const;
1559 : };
1560 :
1561 : friend inline Iterator begin(OGRSimpleCurve *);
1562 : friend inline Iterator end(OGRSimpleCurve *);
1563 :
1564 46 : class CPL_DLL ConstIterator
1565 : {
1566 : struct Private;
1567 : std::unique_ptr<Private> m_poPrivate;
1568 :
1569 : public:
1570 : ConstIterator(const OGRSimpleCurve *poSelf, int nPos);
1571 : ConstIterator(
1572 : ConstIterator &&oOther) noexcept; // declared but not defined.
1573 : // Needed for gcc 5.4 at least
1574 : ~ConstIterator();
1575 : const OGRPoint &operator*() const;
1576 : ConstIterator &operator++();
1577 : bool operator!=(const ConstIterator &it) const;
1578 : };
1579 :
1580 : friend inline ConstIterator begin(const OGRSimpleCurve *);
1581 : friend inline ConstIterator end(const OGRSimpleCurve *);
1582 :
1583 : public:
1584 : ~OGRSimpleCurve() override;
1585 :
1586 : OGRSimpleCurve &operator=(const OGRSimpleCurve &other);
1587 :
1588 : OGRSimpleCurve &operator=(OGRSimpleCurve &&other);
1589 :
1590 : /** Type of child elements. */
1591 : typedef OGRPoint ChildType;
1592 :
1593 : /** Return begin of point iterator.
1594 : *
1595 : * Using this iterator for standard range-based loops is safe, but
1596 : * due to implementation limitations, you shouldn't try to access
1597 : * (dereference) more than one iterator step at a time, since you will get
1598 : * a reference to the same OGRPoint& object.
1599 : * @since GDAL 2.3
1600 : */
1601 : Iterator begin();
1602 : /** Return end of point iterator. */
1603 : Iterator end();
1604 : /** Return begin of point iterator.
1605 : *
1606 : * Using this iterator for standard range-based loops is safe, but
1607 : * due to implementation limitations, you shouldn't try to access
1608 : * (dereference) more than one iterator step at a time, since you will get
1609 : * a reference to the same OGRPoint& object.
1610 : * @since GDAL 2.3
1611 : */
1612 : ConstIterator begin() const;
1613 : /** Return end of point iterator. */
1614 : ConstIterator end() const;
1615 :
1616 : // IWks Interface.
1617 : virtual size_t WkbSize() const override;
1618 : virtual OGRErr importFromWkb(const unsigned char *, size_t, OGRwkbVariant,
1619 : size_t &nBytesConsumedOut) override;
1620 : virtual OGRErr
1621 : exportToWkb(unsigned char *,
1622 : const OGRwkbExportOptions * = nullptr) const override;
1623 :
1624 : #ifndef DOXYGEN_XML
1625 : using OGRGeometry::importFromWkt; /** deprecated */
1626 : #endif
1627 :
1628 : OGRErr importFromWkt(const char **) override;
1629 :
1630 : #ifndef DOXYGEN_XML
1631 : using OGRGeometry::exportToWkt;
1632 : #endif
1633 :
1634 : /// Export a simple curve to WKT
1635 : /// \param opts Output options.
1636 : /// \param err Pointer to error code, if desired.
1637 : /// \return WKT string representing this simple curve.
1638 : virtual std::string exportToWkt(const OGRWktOptions &opts = OGRWktOptions(),
1639 : OGRErr *err = nullptr) const override;
1640 :
1641 : // IGeometry interface.
1642 : virtual void empty() override;
1643 : virtual void getEnvelope(OGREnvelope *psEnvelope) const override;
1644 : virtual void getEnvelope(OGREnvelope3D *psEnvelope) const override;
1645 : virtual OGRBoolean IsEmpty() const override;
1646 : virtual OGRSimpleCurve *clone() const override = 0;
1647 :
1648 : // ICurve methods.
1649 : virtual double get_Length() const override;
1650 : virtual void StartPoint(OGRPoint *) const override;
1651 : virtual void EndPoint(OGRPoint *) const override;
1652 : virtual void Value(double, OGRPoint *) const override;
1653 : virtual double Project(const OGRPoint *) const;
1654 : virtual OGRLineString *getSubLine(double, double, int) const;
1655 :
1656 : // ILineString methods.
1657 10295109 : virtual int getNumPoints() const override
1658 : {
1659 10295109 : return nPointCount;
1660 : }
1661 :
1662 : void getPoint(int, OGRPoint *) const;
1663 :
1664 4583585 : double getX(int i) const
1665 : {
1666 4583585 : return paoPoints[i].x;
1667 : }
1668 :
1669 4317139 : double getY(int i) const
1670 : {
1671 4317139 : return paoPoints[i].y;
1672 : }
1673 :
1674 : double getZ(int i) const;
1675 : double getM(int i) const;
1676 :
1677 : // ISpatialRelation
1678 : virtual OGRBoolean Equals(const OGRGeometry *) const override;
1679 :
1680 : // non standard.
1681 : virtual bool setCoordinateDimension(int nDimension) override;
1682 : virtual bool set3D(OGRBoolean bIs3D) override;
1683 : virtual bool setMeasured(OGRBoolean bIsMeasured) override;
1684 : bool setNumPoints(int nNewPointCount, int bZeroizeNewContent = TRUE);
1685 : bool setPoint(int, OGRPoint *);
1686 : bool setPoint(int, double, double);
1687 : bool setZ(int, double);
1688 : bool setM(int, double);
1689 : bool setPoint(int, double, double, double);
1690 : bool setPointM(int, double, double, double);
1691 : bool setPoint(int, double, double, double, double);
1692 : bool setPoints(int, const OGRRawPoint *, const double * = nullptr);
1693 : bool setPointsM(int, const OGRRawPoint *, const double *);
1694 : bool setPoints(int, const OGRRawPoint *, const double *, const double *);
1695 : bool setPoints(int, const double *padfX, const double *padfY,
1696 : const double *padfZIn = nullptr);
1697 : bool setPointsM(int, const double *padfX, const double *padfY,
1698 : const double *padfMIn = nullptr);
1699 : bool setPoints(int, const double *padfX, const double *padfY,
1700 : const double *padfZIn, const double *padfMIn);
1701 : bool addPoint(const OGRPoint *);
1702 : bool addPoint(double, double);
1703 : bool addPoint(double, double, double);
1704 : bool addPointM(double, double, double);
1705 : bool addPoint(double, double, double, double);
1706 :
1707 : bool removePoint(int);
1708 :
1709 : void getPoints(OGRRawPoint *, double * = nullptr) const;
1710 : void getPoints(void *pabyX, int nXStride, void *pabyY, int nYStride,
1711 : void *pabyZ = nullptr, int nZStride = 0,
1712 : void *pabyM = nullptr, int nMStride = 0) const;
1713 :
1714 : void addSubLineString(const OGRLineString *, int nStartVertex = 0,
1715 : int nEndVertex = -1);
1716 : void reversePoints() override;
1717 : virtual OGRPointIterator *getPointIterator() const override;
1718 :
1719 : // non-standard from OGRGeometry
1720 : virtual OGRErr transform(OGRCoordinateTransformation *poCT) override;
1721 : virtual void flattenTo2D() override;
1722 : virtual bool segmentize(double dfMaxLength) override;
1723 :
1724 : virtual void swapXY() override;
1725 :
1726 3 : OGR_ALLOW_UPCAST_TO(Curve)
1727 : OGR_ALLOW_CAST_TO_THIS(SimpleCurve)
1728 : };
1729 :
1730 : //! @cond Doxygen_Suppress
1731 : /** @see OGRSimpleCurve::begin() */
1732 5 : inline OGRSimpleCurve::Iterator begin(OGRSimpleCurve *poCurve)
1733 : {
1734 5 : return poCurve->begin();
1735 : }
1736 :
1737 : /** @see OGRSimpleCurve::end() */
1738 5 : inline OGRSimpleCurve::Iterator end(OGRSimpleCurve *poCurve)
1739 : {
1740 5 : return poCurve->end();
1741 : }
1742 :
1743 : /** @see OGRSimpleCurve::begin() const */
1744 5 : inline OGRSimpleCurve::ConstIterator begin(const OGRSimpleCurve *poCurve)
1745 : {
1746 5 : return poCurve->begin();
1747 : }
1748 :
1749 : /** @see OGRSimpleCurve::end() const */
1750 5 : inline OGRSimpleCurve::ConstIterator end(const OGRSimpleCurve *poCurve)
1751 : {
1752 5 : return poCurve->end();
1753 : }
1754 :
1755 : //! @endcond
1756 :
1757 : /************************************************************************/
1758 : /* OGRLineString */
1759 : /************************************************************************/
1760 :
1761 : /**
1762 : * Concrete representation of a multi-vertex line.
1763 : *
1764 : * Note: for implementation convenience, we make it inherit from OGRSimpleCurve
1765 : * whereas SFSQL and SQL/MM only make it inherits from OGRCurve.
1766 : */
1767 :
1768 300879 : class CPL_DLL OGRLineString : public OGRSimpleCurve
1769 : {
1770 : // cppcheck-suppress unusedPrivateFunction
1771 : static OGRLinearRing *CasterToLinearRing(OGRCurve *poCurve);
1772 :
1773 : protected:
1774 : //! @cond Doxygen_Suppress
1775 : static OGRLineString *TransferMembersAndDestroy(OGRLineString *poSrc,
1776 : OGRLineString *poDst);
1777 :
1778 : virtual OGRCurveCasterToLineString GetCasterToLineString() const override;
1779 : virtual OGRCurveCasterToLinearRing GetCasterToLinearRing() const override;
1780 :
1781 : virtual double get_AreaOfCurveSegments() const override;
1782 : //! @endcond
1783 :
1784 : static OGRLinearRing *CastToLinearRing(OGRLineString *poLS);
1785 :
1786 : public:
1787 : /** Create an empty line string. */
1788 3464220 : OGRLineString() = default;
1789 : OGRLineString(const OGRLineString &other);
1790 : OGRLineString(OGRLineString &&other);
1791 :
1792 : OGRLineString &operator=(const OGRLineString &other);
1793 : OGRLineString &operator=(OGRLineString &&other);
1794 :
1795 : virtual OGRLineString *clone() const override;
1796 : virtual OGRLineString *
1797 : CurveToLine(double dfMaxAngleStepSizeDegrees = 0,
1798 : const char *const *papszOptions = nullptr) const override;
1799 : virtual OGRGeometry *
1800 : getCurveGeometry(const char *const *papszOptions = nullptr) const override;
1801 : virtual double get_Area() const override;
1802 : virtual double get_GeodesicArea(
1803 : const OGRSpatialReference *poSRSOverride = nullptr) const override;
1804 : virtual double get_GeodesicLength(
1805 : const OGRSpatialReference *poSRSOverride = nullptr) const override;
1806 :
1807 : // Non-standard from OGRGeometry.
1808 : virtual OGRwkbGeometryType getGeometryType() const override;
1809 : virtual const char *getGeometryName() const override;
1810 : virtual int isClockwise() const override;
1811 :
1812 : /** Return pointer of this in upper class */
1813 : inline OGRSimpleCurve *toUpperClass()
1814 : {
1815 : return this;
1816 : }
1817 :
1818 : /** Return pointer of this in upper class */
1819 : inline const OGRSimpleCurve *toUpperClass() const
1820 : {
1821 : return this;
1822 : }
1823 :
1824 24 : virtual void accept(IOGRGeometryVisitor *visitor) override
1825 : {
1826 24 : visitor->visit(this);
1827 24 : }
1828 :
1829 5 : virtual void accept(IOGRConstGeometryVisitor *visitor) const override
1830 : {
1831 5 : visitor->visit(this);
1832 5 : }
1833 :
1834 2 : OGR_ALLOW_UPCAST_TO(SimpleCurve)
1835 : OGR_ALLOW_CAST_TO_THIS(LineString)
1836 : };
1837 :
1838 : /************************************************************************/
1839 : /* OGRLinearRing */
1840 : /************************************************************************/
1841 :
1842 : /**
1843 : * Concrete representation of a closed ring.
1844 : *
1845 : * This class is functionally equivalent to an OGRLineString, but has a
1846 : * separate identity to maintain alignment with the OpenGIS simple feature
1847 : * data model. It exists to serve as a component of an OGRPolygon.
1848 : *
1849 : * The OGRLinearRing has no corresponding free standing well known binary
1850 : * representation, so importFromWkb() and exportToWkb() will not actually
1851 : * work. There is a non-standard GDAL WKT representation though.
1852 : *
1853 : * Because OGRLinearRing is not a "proper" free standing simple features
1854 : * object, it cannot be directly used on a feature via SetGeometry(), and
1855 : * cannot generally be used with GEOS for operations like Intersects().
1856 : * Instead the polygon should be used, or the OGRLinearRing should be
1857 : * converted to an OGRLineString for such operations.
1858 : *
1859 : * Note: this class exists in SFSQL 1.2, but not in ISO SQL/MM Part 3.
1860 : */
1861 :
1862 6 : class CPL_DLL OGRLinearRing : public OGRLineString
1863 : {
1864 : static OGRLineString *CasterToLineString(OGRCurve *poCurve);
1865 :
1866 : // IWks Interface - Note this isn't really a first class object
1867 : // for the purposes of WKB form. These methods always fail since this
1868 : // object can't be serialized on its own.
1869 : virtual size_t WkbSize() const override;
1870 : virtual OGRErr importFromWkb(const unsigned char *, size_t, OGRwkbVariant,
1871 : size_t &nBytesConsumedOut) override;
1872 : OGRErr exportToWkb(unsigned char *,
1873 : const OGRwkbExportOptions * = nullptr) const override;
1874 :
1875 : protected:
1876 : //! @cond Doxygen_Suppress
1877 : friend class OGRPolygon;
1878 : friend class OGRTriangle;
1879 :
1880 : // These are not IWks compatible ... just a convenience for OGRPolygon.
1881 : virtual size_t _WkbSize(int _flags) const;
1882 : virtual OGRErr _importFromWkb(OGRwkbByteOrder, int _flags,
1883 : const unsigned char *, size_t,
1884 : size_t &nBytesConsumedOut);
1885 : virtual OGRErr _exportToWkb(int _flags, unsigned char *,
1886 : const OGRwkbExportOptions *) const;
1887 :
1888 : virtual OGRCurveCasterToLineString GetCasterToLineString() const override;
1889 : virtual OGRCurveCasterToLinearRing GetCasterToLinearRing() const override;
1890 : //! @endcond
1891 :
1892 : static OGRLineString *CastToLineString(OGRLinearRing *poLR);
1893 :
1894 : public:
1895 : /** Constructor */
1896 3113514 : OGRLinearRing() = default;
1897 : OGRLinearRing(const OGRLinearRing &other);
1898 : /** Move constructor*/
1899 1 : OGRLinearRing(OGRLinearRing &&other) = default;
1900 : explicit OGRLinearRing(const OGRLinearRing *);
1901 :
1902 : OGRLinearRing &operator=(const OGRLinearRing &other);
1903 : /** Move assignment operator */
1904 : OGRLinearRing &operator=(OGRLinearRing &&other) = default;
1905 :
1906 : // Non standard.
1907 : virtual const char *getGeometryName() const override;
1908 : virtual OGRLinearRing *clone() const override;
1909 :
1910 : //! @cond Doxygen_Suppress
1911 : void reverseWindingOrder()
1912 : CPL_WARN_DEPRECATED("Use reversePoints() instead");
1913 : //! @endcond
1914 :
1915 : virtual void closeRings() override;
1916 : OGRBoolean isPointInRing(const OGRPoint *pt,
1917 : int bTestEnvelope = TRUE) const;
1918 : OGRBoolean isPointOnRingBoundary(const OGRPoint *pt,
1919 : int bTestEnvelope = TRUE) const;
1920 : virtual OGRErr transform(OGRCoordinateTransformation *poCT) override;
1921 :
1922 : /** Return pointer of this in upper class */
1923 80 : inline OGRLineString *toUpperClass()
1924 : {
1925 80 : return this;
1926 : }
1927 :
1928 : /** Return pointer of this in upper class */
1929 8 : inline const OGRLineString *toUpperClass() const
1930 : {
1931 8 : return this;
1932 : }
1933 :
1934 80 : virtual void accept(IOGRGeometryVisitor *visitor) override
1935 : {
1936 80 : visitor->visit(this);
1937 80 : }
1938 :
1939 8 : virtual void accept(IOGRConstGeometryVisitor *visitor) const override
1940 : {
1941 8 : visitor->visit(this);
1942 8 : }
1943 :
1944 : OGR_ALLOW_UPCAST_TO(LineString)
1945 : OGR_ALLOW_CAST_TO_THIS(LinearRing)
1946 : };
1947 :
1948 : /************************************************************************/
1949 : /* OGRCircularString */
1950 : /************************************************************************/
1951 :
1952 : /**
1953 : * Concrete representation of a circular string, that is to say a curve made
1954 : * of one or several arc circles.
1955 : *
1956 : * Note: for implementation convenience, we make it inherit from OGRSimpleCurve
1957 : * whereas SQL/MM only makes it inherits from OGRCurve.
1958 : *
1959 : * Compatibility: ISO SQL/MM Part 3.
1960 : *
1961 : * @since GDAL 2.0
1962 : */
1963 :
1964 411 : class CPL_DLL OGRCircularString : public OGRSimpleCurve
1965 : {
1966 : private:
1967 : void ExtendEnvelopeWithCircular(OGREnvelope *psEnvelope) const;
1968 : OGRBoolean IsValidFast() const;
1969 : int IsFullCircle(double &cx, double &cy, double &square_R) const;
1970 :
1971 : protected:
1972 : //! @cond Doxygen_Suppress
1973 : virtual OGRCurveCasterToLineString GetCasterToLineString() const override;
1974 : virtual OGRCurveCasterToLinearRing GetCasterToLinearRing() const override;
1975 : virtual int IntersectsPoint(const OGRPoint *p) const override;
1976 : virtual int ContainsPoint(const OGRPoint *p) const override;
1977 : virtual double get_AreaOfCurveSegments() const override;
1978 : //! @endcond
1979 :
1980 : public:
1981 : /** Create an empty circular string. */
1982 7133 : OGRCircularString() = default;
1983 :
1984 : OGRCircularString(const OGRCircularString &other);
1985 : /** Move constructor */
1986 1 : OGRCircularString(OGRCircularString &&other) = default;
1987 :
1988 : OGRCircularString &operator=(const OGRCircularString &other);
1989 : /** Move assignment operator */
1990 : OGRCircularString &operator=(OGRCircularString &&other) = default;
1991 :
1992 : // IWks Interface.
1993 : virtual OGRErr importFromWkb(const unsigned char *, size_t, OGRwkbVariant,
1994 : size_t &nBytesConsumedOut) override;
1995 : OGRErr exportToWkb(unsigned char *,
1996 : const OGRwkbExportOptions * = nullptr) const override;
1997 :
1998 : #ifndef DOXYGEN_XML
1999 : using OGRGeometry::importFromWkt; /** deprecated */
2000 : #endif
2001 :
2002 : OGRErr importFromWkt(const char **) override;
2003 :
2004 : #ifndef DOXYGEN_XML
2005 : using OGRGeometry::exportToWkt;
2006 : #endif
2007 :
2008 : /// Export a circular string to WKT
2009 : /// \param opts Output options.
2010 : /// \param err Pointer to error code, if desired.
2011 : /// \return WKT string representing this circular string.
2012 : virtual std::string exportToWkt(const OGRWktOptions &opts = OGRWktOptions(),
2013 : OGRErr *err = nullptr) const override;
2014 :
2015 : // IGeometry interface.
2016 : virtual OGRBoolean IsValid() const override;
2017 : virtual void getEnvelope(OGREnvelope *psEnvelope) const override;
2018 : virtual void getEnvelope(OGREnvelope3D *psEnvelope) const override;
2019 : virtual OGRCircularString *clone() const override;
2020 :
2021 : // ICurve methods.
2022 : virtual double get_Length() const override;
2023 : virtual OGRLineString *
2024 : CurveToLine(double dfMaxAngleStepSizeDegrees = 0,
2025 : const char *const *papszOptions = nullptr) const override;
2026 : virtual void Value(double, OGRPoint *) const override;
2027 : virtual double get_Area() const override;
2028 : virtual double get_GeodesicArea(
2029 : const OGRSpatialReference *poSRSOverride = nullptr) const override;
2030 : virtual double get_GeodesicLength(
2031 : const OGRSpatialReference *poSRSOverride = nullptr) const override;
2032 :
2033 : // Non-standard from OGRGeometry.
2034 : virtual OGRwkbGeometryType getGeometryType() const override;
2035 : virtual const char *getGeometryName() const override;
2036 : virtual bool segmentize(double dfMaxLength) override;
2037 : virtual OGRBoolean
2038 : hasCurveGeometry(int bLookForNonLinear = FALSE) const override;
2039 : virtual OGRGeometry *
2040 : getLinearGeometry(double dfMaxAngleStepSizeDegrees = 0,
2041 : const char *const *papszOptions = nullptr) const override;
2042 :
2043 : /** Return pointer of this in upper class */
2044 : inline OGRSimpleCurve *toUpperClass()
2045 : {
2046 : return this;
2047 : }
2048 :
2049 : /** Return pointer of this in upper class */
2050 : inline const OGRSimpleCurve *toUpperClass() const
2051 : {
2052 : return this;
2053 : }
2054 :
2055 1 : virtual void accept(IOGRGeometryVisitor *visitor) override
2056 : {
2057 1 : visitor->visit(this);
2058 1 : }
2059 :
2060 1 : virtual void accept(IOGRConstGeometryVisitor *visitor) const override
2061 : {
2062 1 : visitor->visit(this);
2063 1 : }
2064 :
2065 1 : OGR_ALLOW_UPCAST_TO(SimpleCurve)
2066 : OGR_ALLOW_CAST_TO_THIS(CircularString)
2067 : };
2068 :
2069 : /************************************************************************/
2070 : /* OGRCurveCollection */
2071 : /************************************************************************/
2072 :
2073 : /**
2074 : * Utility class to store a collection of curves. Used as a member of
2075 : * OGRCompoundCurve and OGRCurvePolygon.
2076 : *
2077 : * This class is only exported because of linking issues. It should never
2078 : * be directly used.
2079 : *
2080 : * @since GDAL 2.0
2081 : */
2082 :
2083 : //! @cond Doxygen_Suppress
2084 : class CPL_DLL OGRCurveCollection
2085 : {
2086 : protected:
2087 : friend class OGRCompoundCurve;
2088 : friend class OGRCurvePolygon;
2089 : friend class OGRPolygon;
2090 : friend class OGRTriangle;
2091 :
2092 : int nCurveCount = 0;
2093 : OGRCurve **papoCurves = nullptr;
2094 :
2095 : public:
2096 1510254 : OGRCurveCollection() = default;
2097 : OGRCurveCollection(const OGRCurveCollection &other);
2098 : OGRCurveCollection(OGRCurveCollection &&other);
2099 : ~OGRCurveCollection();
2100 :
2101 : OGRCurveCollection &operator=(const OGRCurveCollection &other);
2102 : OGRCurveCollection &operator=(OGRCurveCollection &&other);
2103 :
2104 : /** Type of child elements. */
2105 : typedef OGRCurve ChildType;
2106 :
2107 : /** Return begin of curve iterator.
2108 : * @since GDAL 2.3
2109 : */
2110 6249279 : OGRCurve **begin()
2111 : {
2112 6249279 : return papoCurves;
2113 : }
2114 :
2115 : /** Return end of curve iterator. */
2116 6249279 : OGRCurve **end()
2117 : {
2118 6249279 : return papoCurves + nCurveCount;
2119 : }
2120 :
2121 : /** Return begin of curve iterator.
2122 : * @since GDAL 2.3
2123 : */
2124 1794998 : const OGRCurve *const *begin() const
2125 : {
2126 1794998 : return papoCurves;
2127 : }
2128 :
2129 : /** Return end of curve iterator. */
2130 1795008 : const OGRCurve *const *end() const
2131 : {
2132 1795008 : return papoCurves + nCurveCount;
2133 : }
2134 :
2135 : void empty(OGRGeometry *poGeom);
2136 : OGRBoolean IsEmpty() const;
2137 : void getEnvelope(OGREnvelope *psEnvelope) const;
2138 : void getEnvelope(OGREnvelope3D *psEnvelope) const;
2139 :
2140 : OGRErr addCurveDirectly(OGRGeometry *poGeom, OGRCurve *poCurve,
2141 : int bNeedRealloc);
2142 : size_t WkbSize() const;
2143 : OGRErr importPreambleFromWkb(OGRGeometry *poGeom,
2144 : const unsigned char *pabyData, size_t &nSize,
2145 : size_t &nDataOffset,
2146 : OGRwkbByteOrder &eByteOrder,
2147 : size_t nMinSubGeomSize,
2148 : OGRwkbVariant eWkbVariant);
2149 : OGRErr
2150 : importBodyFromWkb(OGRGeometry *poGeom, const unsigned char *pabyData,
2151 : size_t nSize, bool bAcceptCompoundCurve,
2152 : OGRErr (*pfnAddCurveDirectlyFromWkb)(OGRGeometry *poGeom,
2153 : OGRCurve *poCurve),
2154 : OGRwkbVariant eWkbVariant, size_t &nBytesConsumedOut);
2155 : std::string exportToWkt(const OGRGeometry *geom, const OGRWktOptions &opts,
2156 : OGRErr *err) const;
2157 : OGRErr exportToWkb(const OGRGeometry *poGeom, unsigned char *,
2158 : const OGRwkbExportOptions * = nullptr) const;
2159 : OGRBoolean Equals(const OGRCurveCollection *poOCC) const;
2160 : bool setCoordinateDimension(OGRGeometry *poGeom, int nNewDimension);
2161 : bool set3D(OGRGeometry *poGeom, OGRBoolean bIs3D);
2162 : bool setMeasured(OGRGeometry *poGeom, OGRBoolean bIsMeasured);
2163 : void assignSpatialReference(OGRGeometry *poGeom,
2164 : const OGRSpatialReference *poSR);
2165 : int getNumCurves() const;
2166 : OGRCurve *getCurve(int);
2167 : const OGRCurve *getCurve(int) const;
2168 : OGRCurve *stealCurve(int);
2169 :
2170 : OGRErr removeCurve(int iIndex, bool bDelete = true);
2171 :
2172 : bool hasEmptyParts() const;
2173 : void removeEmptyParts();
2174 :
2175 : void reversePoints();
2176 :
2177 : OGRErr transform(OGRGeometry *poGeom, OGRCoordinateTransformation *poCT);
2178 : void flattenTo2D(OGRGeometry *poGeom);
2179 : bool segmentize(double dfMaxLength);
2180 : void swapXY();
2181 : OGRBoolean hasCurveGeometry(int bLookForNonLinear) const;
2182 : };
2183 :
2184 : //! @endcond
2185 :
2186 : /************************************************************************/
2187 : /* OGRCompoundCurve */
2188 : /************************************************************************/
2189 :
2190 : /**
2191 : * Concrete representation of a compound curve, made of curves: OGRLineString
2192 : * and OGRCircularString. Each curve is connected by its first point to
2193 : * the last point of the previous curve.
2194 : *
2195 : * Compatibility: ISO SQL/MM Part 3.
2196 : *
2197 : * @since GDAL 2.0
2198 : */
2199 :
2200 266 : class CPL_DLL OGRCompoundCurve : public OGRCurve
2201 : {
2202 : private:
2203 : OGRCurveCollection oCC{};
2204 :
2205 : OGRErr addCurveDirectlyInternal(OGRCurve *poCurve, double dfToleranceEps,
2206 : int bNeedRealloc);
2207 : static OGRErr addCurveDirectlyFromWkt(OGRGeometry *poSelf,
2208 : OGRCurve *poCurve);
2209 : static OGRErr addCurveDirectlyFromWkb(OGRGeometry *poSelf,
2210 : OGRCurve *poCurve);
2211 : OGRLineString *CurveToLineInternal(double dfMaxAngleStepSizeDegrees,
2212 : const char *const *papszOptions,
2213 : int bIsLinearRing) const;
2214 : // cppcheck-suppress unusedPrivateFunction
2215 : static OGRLineString *CasterToLineString(OGRCurve *poCurve);
2216 : // cppcheck-suppress unusedPrivateFunction
2217 : static OGRLinearRing *CasterToLinearRing(OGRCurve *poCurve);
2218 :
2219 : protected:
2220 : //! @cond Doxygen_Suppress
2221 : static OGRLineString *CastToLineString(OGRCompoundCurve *poCC);
2222 : static OGRLinearRing *CastToLinearRing(OGRCompoundCurve *poCC);
2223 :
2224 : virtual OGRCurveCasterToLineString GetCasterToLineString() const override;
2225 : virtual OGRCurveCasterToLinearRing GetCasterToLinearRing() const override;
2226 : //! @endcond
2227 :
2228 : public:
2229 : /** Create an empty compound curve. */
2230 2754 : OGRCompoundCurve() = default;
2231 :
2232 : OGRCompoundCurve(const OGRCompoundCurve &other);
2233 : /** Move constructor */
2234 1 : OGRCompoundCurve(OGRCompoundCurve &&other) = default;
2235 :
2236 : OGRCompoundCurve &operator=(const OGRCompoundCurve &other);
2237 : /** Move assignment operator */
2238 : OGRCompoundCurve &operator=(OGRCompoundCurve &&other) = default;
2239 :
2240 : /** Type of child elements. */
2241 : typedef OGRCurve ChildType;
2242 :
2243 : /** Return begin of curve iterator.
2244 : * @since GDAL 2.3
2245 : */
2246 15 : ChildType **begin()
2247 : {
2248 15 : return oCC.begin();
2249 : }
2250 :
2251 : /** Return end of curve iterator. */
2252 15 : ChildType **end()
2253 : {
2254 15 : return oCC.end();
2255 : }
2256 :
2257 : /** Return begin of curve iterator.
2258 : * @since GDAL 2.3
2259 : */
2260 18 : const ChildType *const *begin() const
2261 : {
2262 18 : return oCC.begin();
2263 : }
2264 :
2265 : /** Return end of curve iterator. */
2266 18 : const ChildType *const *end() const
2267 : {
2268 18 : return oCC.end();
2269 : }
2270 :
2271 : // IWks Interface
2272 : virtual size_t WkbSize() const override;
2273 : virtual OGRErr importFromWkb(const unsigned char *, size_t, OGRwkbVariant,
2274 : size_t &nBytesConsumedOut) override;
2275 : OGRErr exportToWkb(unsigned char *,
2276 : const OGRwkbExportOptions * = nullptr) const override;
2277 :
2278 : #ifndef DOXYGEN_XML
2279 : using OGRGeometry::importFromWkt; /** deprecated */
2280 : #endif
2281 :
2282 : OGRErr importFromWkt(const char **) override;
2283 :
2284 : #ifndef DOXYGEN_XML
2285 : using OGRGeometry::exportToWkt;
2286 : #endif
2287 :
2288 : /// Export a compound curve to WKT
2289 : /// \param opts Output options.
2290 : /// \param err Pointer to error code, if desired.
2291 : /// \return WKT representation of the compound curve.
2292 : virtual std::string exportToWkt(const OGRWktOptions &opts = OGRWktOptions(),
2293 : OGRErr *err = nullptr) const override;
2294 :
2295 : // IGeometry interface.
2296 : virtual OGRCompoundCurve *clone() const override;
2297 : virtual void empty() override;
2298 : virtual void getEnvelope(OGREnvelope *psEnvelope) const override;
2299 : virtual void getEnvelope(OGREnvelope3D *psEnvelope) const override;
2300 : virtual OGRBoolean IsEmpty() const override;
2301 :
2302 : // ICurve methods.
2303 : virtual double get_Length() const override;
2304 : virtual void StartPoint(OGRPoint *) const override;
2305 : virtual void EndPoint(OGRPoint *) const override;
2306 : virtual void Value(double, OGRPoint *) const override;
2307 : virtual OGRLineString *
2308 : CurveToLine(double dfMaxAngleStepSizeDegrees = 0,
2309 : const char *const *papszOptions = nullptr) const override;
2310 :
2311 : virtual int getNumPoints() const override;
2312 : virtual double get_AreaOfCurveSegments() const override;
2313 : virtual double get_Area() const override;
2314 : virtual double get_GeodesicArea(
2315 : const OGRSpatialReference *poSRSOverride = nullptr) const override;
2316 : virtual double get_GeodesicLength(
2317 : const OGRSpatialReference *poSRSOverride = nullptr) const override;
2318 :
2319 : // ISpatialRelation.
2320 : virtual OGRBoolean Equals(const OGRGeometry *) const override;
2321 :
2322 : // ICompoundCurve method.
2323 : int getNumCurves() const;
2324 : OGRCurve *getCurve(int);
2325 : const OGRCurve *getCurve(int) const;
2326 :
2327 : // Non-standard.
2328 : virtual bool setCoordinateDimension(int nDimension) override;
2329 : virtual bool set3D(OGRBoolean bIs3D) override;
2330 : virtual bool setMeasured(OGRBoolean bIsMeasured) override;
2331 :
2332 : virtual void
2333 : assignSpatialReference(const OGRSpatialReference *poSR) override;
2334 :
2335 : /** Default relative tolerance to assume that the end of the previous curve
2336 : * is equal to the start of the next one.
2337 : */
2338 : static constexpr double DEFAULT_TOLERANCE_EPSILON = 1e-14;
2339 :
2340 : OGRErr addCurve(const OGRCurve *,
2341 : double dfToleranceEps = DEFAULT_TOLERANCE_EPSILON);
2342 : OGRErr addCurveDirectly(OGRCurve *,
2343 : double dfToleranceEps = DEFAULT_TOLERANCE_EPSILON);
2344 : OGRErr addCurve(std::unique_ptr<OGRCurve>,
2345 : double dfToleranceEps = DEFAULT_TOLERANCE_EPSILON);
2346 : OGRCurve *stealCurve(int);
2347 : virtual OGRPointIterator *getPointIterator() const override;
2348 : void reversePoints() override;
2349 :
2350 : // Non-standard from OGRGeometry.
2351 : virtual OGRwkbGeometryType getGeometryType() const override;
2352 : virtual const char *getGeometryName() const override;
2353 : virtual OGRErr transform(OGRCoordinateTransformation *poCT) override;
2354 : virtual void flattenTo2D() override;
2355 : virtual bool segmentize(double dfMaxLength) override;
2356 : virtual OGRBoolean
2357 : hasCurveGeometry(int bLookForNonLinear = FALSE) const override;
2358 : virtual OGRGeometry *
2359 : getLinearGeometry(double dfMaxAngleStepSizeDegrees = 0,
2360 : const char *const *papszOptions = nullptr) const override;
2361 :
2362 1 : virtual void accept(IOGRGeometryVisitor *visitor) override
2363 : {
2364 1 : visitor->visit(this);
2365 1 : }
2366 :
2367 1 : virtual void accept(IOGRConstGeometryVisitor *visitor) const override
2368 : {
2369 1 : visitor->visit(this);
2370 1 : }
2371 :
2372 : virtual void swapXY() override;
2373 :
2374 : bool hasEmptyParts() const override;
2375 : void removeEmptyParts() override;
2376 :
2377 1 : OGR_ALLOW_UPCAST_TO(Curve)
2378 : OGR_ALLOW_CAST_TO_THIS(CompoundCurve)
2379 : };
2380 :
2381 : //! @cond Doxygen_Suppress
2382 : /** @see OGRCompoundCurve::begin() const */
2383 : inline const OGRCompoundCurve::ChildType *const *
2384 3 : begin(const OGRCompoundCurve *poCurve)
2385 : {
2386 3 : return poCurve->begin();
2387 : }
2388 :
2389 : /** @see OGRCompoundCurve::end() const */
2390 : inline const OGRCompoundCurve::ChildType *const *
2391 3 : end(const OGRCompoundCurve *poCurve)
2392 : {
2393 3 : return poCurve->end();
2394 : }
2395 :
2396 : /** @see OGRCompoundCurve::begin() */
2397 14 : inline OGRCompoundCurve::ChildType **begin(OGRCompoundCurve *poCurve)
2398 : {
2399 14 : return poCurve->begin();
2400 : }
2401 :
2402 : /** @see OGRCompoundCurve::end() */
2403 14 : inline OGRCompoundCurve::ChildType **end(OGRCompoundCurve *poCurve)
2404 : {
2405 14 : return poCurve->end();
2406 : }
2407 :
2408 : //! @endcond
2409 :
2410 : /************************************************************************/
2411 : /* OGRSurface */
2412 : /************************************************************************/
2413 :
2414 : /**
2415 : * Abstract base class for 2 dimensional objects like polygons or curve
2416 : * polygons.
2417 : */
2418 :
2419 : class CPL_DLL OGRSurface : public OGRGeometry
2420 : {
2421 : protected:
2422 : //! @cond Doxygen_Suppress
2423 : virtual OGRSurfaceCasterToPolygon GetCasterToPolygon() const = 0;
2424 : virtual OGRSurfaceCasterToCurvePolygon GetCasterToCurvePolygon() const = 0;
2425 : //! @endcond
2426 :
2427 : public:
2428 : virtual double get_Area() const = 0;
2429 : virtual double get_GeodesicArea(
2430 : const OGRSpatialReference *poSRSOverride = nullptr) const = 0;
2431 : virtual double get_Length() const = 0;
2432 : virtual double get_GeodesicLength(
2433 : const OGRSpatialReference *poSRSOverride = nullptr) const = 0;
2434 :
2435 0 : virtual OGRErr PointOnSurface(OGRPoint *poPoint) const
2436 : {
2437 0 : return PointOnSurfaceInternal(poPoint);
2438 : }
2439 :
2440 : virtual OGRSurface *clone() const override = 0;
2441 :
2442 : //! @cond Doxygen_Suppress
2443 : static OGRPolygon *CastToPolygon(OGRSurface *poSurface);
2444 : static OGRCurvePolygon *CastToCurvePolygon(OGRSurface *poSurface);
2445 : //! @endcond
2446 :
2447 : OGR_FORBID_DOWNCAST_TO_POINT
2448 : OGR_FORBID_DOWNCAST_TO_ALL_CURVES
2449 : OGR_ALLOW_CAST_TO_THIS(Surface)
2450 : OGR_FORBID_DOWNCAST_TO_ALL_MULTI
2451 : };
2452 :
2453 : /************************************************************************/
2454 : /* OGRCurvePolygon */
2455 : /************************************************************************/
2456 :
2457 : /**
2458 : * Concrete class representing curve polygons.
2459 : *
2460 : * Note that curve polygons consist of one outer (curve) ring, and zero or
2461 : * more inner rings. A curve polygon cannot represent disconnected
2462 : * regions (such as multiple islands in a political body). The
2463 : * OGRMultiSurface must be used for this.
2464 : *
2465 : * Compatibility: ISO SQL/MM Part 3.
2466 : *
2467 : * @since GDAL 2.0
2468 : */
2469 :
2470 1548486 : class CPL_DLL OGRCurvePolygon : public OGRSurface
2471 : {
2472 : static OGRPolygon *CasterToPolygon(OGRSurface *poSurface);
2473 :
2474 : private:
2475 : OGRBoolean IntersectsPoint(const OGRPoint *p) const;
2476 : OGRBoolean ContainsPoint(const OGRPoint *p) const;
2477 :
2478 : virtual bool isRingCorrectType(const OGRCurve *poRing) const;
2479 :
2480 : virtual bool checkRing(const OGRCurve *poNewRing) const;
2481 : OGRErr addRingDirectlyInternal(OGRCurve *poCurve, int bNeedRealloc);
2482 : static OGRErr addCurveDirectlyFromWkt(OGRGeometry *poSelf,
2483 : OGRCurve *poCurve);
2484 : static OGRErr addCurveDirectlyFromWkb(OGRGeometry *poSelf,
2485 : OGRCurve *poCurve);
2486 :
2487 : protected:
2488 : //! @cond Doxygen_Suppress
2489 : friend class OGRPolygon;
2490 : friend class OGRTriangle;
2491 : OGRCurveCollection oCC{};
2492 :
2493 : virtual OGRSurfaceCasterToPolygon GetCasterToPolygon() const override;
2494 : virtual OGRSurfaceCasterToCurvePolygon
2495 : GetCasterToCurvePolygon() const override;
2496 :
2497 : //! @endcond
2498 :
2499 : static OGRPolygon *CastToPolygon(OGRCurvePolygon *poCP);
2500 :
2501 : public:
2502 : /** Create an empty curve polygon. */
2503 1507503 : OGRCurvePolygon() = default;
2504 :
2505 : OGRCurvePolygon(const OGRCurvePolygon &);
2506 : /** Move constructor */
2507 3 : OGRCurvePolygon(OGRCurvePolygon &&) = default;
2508 :
2509 : OGRCurvePolygon &operator=(const OGRCurvePolygon &other);
2510 : /** Move assignment operator */
2511 : OGRCurvePolygon &operator=(OGRCurvePolygon &&other) = default;
2512 :
2513 : /** Type of child elements. */
2514 : typedef OGRCurve ChildType;
2515 :
2516 : /** Return begin of curve iterator.
2517 : * @since GDAL 2.3
2518 : */
2519 100 : ChildType **begin()
2520 : {
2521 100 : return oCC.begin();
2522 : }
2523 :
2524 : /** Return end of curve iterator. */
2525 100 : ChildType **end()
2526 : {
2527 100 : return oCC.end();
2528 : }
2529 :
2530 : /** Return begin of curve iterator.
2531 : * @since GDAL 2.3
2532 : */
2533 53 : const ChildType *const *begin() const
2534 : {
2535 53 : return oCC.begin();
2536 : }
2537 :
2538 : /** Return end of curve iterator. */
2539 53 : const ChildType *const *end() const
2540 : {
2541 53 : return oCC.end();
2542 : }
2543 :
2544 : // Non standard (OGRGeometry).
2545 : virtual const char *getGeometryName() const override;
2546 : virtual OGRwkbGeometryType getGeometryType() const override;
2547 : virtual OGRCurvePolygon *clone() const override;
2548 : virtual void empty() override;
2549 : virtual OGRErr transform(OGRCoordinateTransformation *poCT) override;
2550 : virtual void flattenTo2D() override;
2551 : virtual OGRBoolean IsEmpty() const override;
2552 : virtual bool segmentize(double dfMaxLength) override;
2553 : virtual OGRBoolean
2554 : hasCurveGeometry(int bLookForNonLinear = FALSE) const override;
2555 : virtual OGRGeometry *
2556 : getLinearGeometry(double dfMaxAngleStepSizeDegrees = 0,
2557 : const char *const *papszOptions = nullptr) const override;
2558 : virtual double get_GeodesicArea(
2559 : const OGRSpatialReference *poSRSOverride = nullptr) const override;
2560 : virtual double get_GeodesicLength(
2561 : const OGRSpatialReference *poSRSOverride = nullptr) const override;
2562 :
2563 : // ISurface Interface
2564 : virtual double get_Area() const override;
2565 :
2566 : virtual double get_Length() const override;
2567 :
2568 : // IWks Interface
2569 : virtual size_t WkbSize() const override;
2570 : virtual OGRErr importFromWkb(const unsigned char *, size_t, OGRwkbVariant,
2571 : size_t &nBytesConsumedOut) override;
2572 : OGRErr exportToWkb(unsigned char *,
2573 : const OGRwkbExportOptions * = nullptr) const override;
2574 :
2575 : #ifndef DOXYGEN_XML
2576 : using OGRGeometry::importFromWkt; /** deprecated */
2577 : #endif
2578 :
2579 : OGRErr importFromWkt(const char **) override;
2580 :
2581 : #ifndef DOXYGEN_XML
2582 : using OGRGeometry::exportToWkt;
2583 : #endif
2584 :
2585 : /// Export a curve polygon to WKT
2586 : /// \param opts Output options.
2587 : /// \param err Pointer to error code, if desired.
2588 : /// \return WKT representation of the curve polygon.
2589 : virtual std::string exportToWkt(const OGRWktOptions &opts = OGRWktOptions(),
2590 : OGRErr *err = nullptr) const override;
2591 :
2592 : // IGeometry
2593 : virtual int getDimension() const override;
2594 : virtual void getEnvelope(OGREnvelope *psEnvelope) const override;
2595 : virtual void getEnvelope(OGREnvelope3D *psEnvelope) const override;
2596 :
2597 : // ICurvePolygon
2598 : virtual OGRPolygon *
2599 : CurvePolyToPoly(double dfMaxAngleStepSizeDegrees = 0,
2600 : const char *const *papszOptions = nullptr) const;
2601 :
2602 : // ISpatialRelation
2603 : virtual OGRBoolean Equals(const OGRGeometry *) const override;
2604 : virtual OGRBoolean Intersects(const OGRGeometry *) const override;
2605 : virtual OGRBoolean Contains(const OGRGeometry *) const override;
2606 :
2607 : // Non standard
2608 : virtual bool setCoordinateDimension(int nDimension) override;
2609 : virtual bool set3D(OGRBoolean bIs3D) override;
2610 : virtual bool setMeasured(OGRBoolean bIsMeasured) override;
2611 :
2612 : virtual void
2613 : assignSpatialReference(const OGRSpatialReference *poSR) override;
2614 :
2615 : virtual OGRErr addRing(const OGRCurve *);
2616 : virtual OGRErr addRingDirectly(OGRCurve *);
2617 : OGRErr addRing(std::unique_ptr<OGRCurve>);
2618 :
2619 : OGRCurve *getExteriorRingCurve();
2620 : const OGRCurve *getExteriorRingCurve() const;
2621 : int getNumInteriorRings() const;
2622 : OGRCurve *getInteriorRingCurve(int);
2623 : const OGRCurve *getInteriorRingCurve(int) const;
2624 :
2625 : OGRCurve *stealExteriorRingCurve();
2626 :
2627 : OGRErr removeRing(int iIndex, bool bDelete = true);
2628 :
2629 1 : virtual void accept(IOGRGeometryVisitor *visitor) override
2630 : {
2631 1 : visitor->visit(this);
2632 1 : }
2633 :
2634 1 : virtual void accept(IOGRConstGeometryVisitor *visitor) const override
2635 : {
2636 1 : visitor->visit(this);
2637 1 : }
2638 :
2639 : virtual void swapXY() override;
2640 :
2641 : bool hasEmptyParts() const override;
2642 : void removeEmptyParts() override;
2643 :
2644 8 : OGR_ALLOW_UPCAST_TO(Surface)
2645 : OGR_ALLOW_CAST_TO_THIS(CurvePolygon)
2646 : };
2647 :
2648 : //! @cond Doxygen_Suppress
2649 : /** @see OGRCurvePolygon::begin() const */
2650 : inline const OGRCurvePolygon::ChildType *const *
2651 2 : begin(const OGRCurvePolygon *poGeom)
2652 : {
2653 2 : return poGeom->begin();
2654 : }
2655 :
2656 : /** @see OGRCurvePolygon::end() const */
2657 : inline const OGRCurvePolygon::ChildType *const *
2658 2 : end(const OGRCurvePolygon *poGeom)
2659 : {
2660 2 : return poGeom->end();
2661 : }
2662 :
2663 : /** @see OGRCurvePolygon::begin() */
2664 2 : inline OGRCurvePolygon::ChildType **begin(OGRCurvePolygon *poGeom)
2665 : {
2666 2 : return poGeom->begin();
2667 : }
2668 :
2669 : /** @see OGRCurvePolygon::end() */
2670 2 : inline OGRCurvePolygon::ChildType **end(OGRCurvePolygon *poGeom)
2671 : {
2672 2 : return poGeom->end();
2673 : }
2674 :
2675 : //! @endcond
2676 :
2677 : /************************************************************************/
2678 : /* OGRPolygon */
2679 : /************************************************************************/
2680 :
2681 : /**
2682 : * Concrete class representing polygons.
2683 : *
2684 : * Note that the OpenGIS simple features polygons consist of one outer ring
2685 : * (linearring), and zero or more inner rings. A polygon cannot represent
2686 : * disconnected regions (such as multiple islands in a political body). The
2687 : * OGRMultiPolygon must be used for this.
2688 : */
2689 :
2690 1548224 : class CPL_DLL OGRPolygon : public OGRCurvePolygon
2691 : {
2692 : static OGRCurvePolygon *CasterToCurvePolygon(OGRSurface *poSurface);
2693 :
2694 : protected:
2695 : //! @cond Doxygen_Suppress
2696 : friend class OGRMultiSurface;
2697 : friend class OGRPolyhedralSurface;
2698 : friend class OGRTriangulatedSurface;
2699 :
2700 : virtual bool isRingCorrectType(const OGRCurve *poRing) const override;
2701 :
2702 : virtual bool checkRing(const OGRCurve *poNewRing) const override;
2703 : virtual OGRErr importFromWKTListOnly(const char **ppszInput, int bHasZ,
2704 : int bHasM, OGRRawPoint *&paoPoints,
2705 : int &nMaxPoints, double *&padfZ);
2706 :
2707 : static OGRCurvePolygon *CastToCurvePolygon(OGRPolygon *poPoly);
2708 :
2709 : virtual OGRSurfaceCasterToPolygon GetCasterToPolygon() const override;
2710 : virtual OGRSurfaceCasterToCurvePolygon
2711 : GetCasterToCurvePolygon() const override;
2712 : //! @endcond
2713 :
2714 : public:
2715 : /** Create an empty polygon. */
2716 1506874 : OGRPolygon() = default;
2717 :
2718 : OGRPolygon(const OGRPolygon &other);
2719 : /** Move constructor */
2720 2 : OGRPolygon(OGRPolygon &&other) = default;
2721 :
2722 : OGRPolygon &operator=(const OGRPolygon &other);
2723 : /** Move assignment operator */
2724 : OGRPolygon &operator=(OGRPolygon &&other) = default;
2725 :
2726 : /** Type of child elements. */
2727 : typedef OGRLinearRing ChildType;
2728 :
2729 : /** Return begin of iterator.
2730 : * @since GDAL 2.3
2731 : */
2732 1774 : ChildType **begin()
2733 : {
2734 1774 : return reinterpret_cast<ChildType **>(oCC.begin());
2735 : }
2736 :
2737 : /** Return end of iterator */
2738 1774 : ChildType **end()
2739 : {
2740 1774 : return reinterpret_cast<ChildType **>(oCC.end());
2741 : }
2742 :
2743 : /** Return begin of iterator.
2744 : * @since GDAL 2.3
2745 : */
2746 1229715 : const ChildType *const *begin() const
2747 : {
2748 1229715 : return reinterpret_cast<const ChildType *const *>(oCC.begin());
2749 : }
2750 :
2751 : /** Return end of iterator */
2752 1229675 : const ChildType *const *end() const
2753 : {
2754 1229675 : return reinterpret_cast<const ChildType *const *>(oCC.end());
2755 : }
2756 :
2757 : // Non-standard (OGRGeometry).
2758 : virtual const char *getGeometryName() const override;
2759 : virtual OGRwkbGeometryType getGeometryType() const override;
2760 : virtual OGRPolygon *clone() const override;
2761 : virtual OGRBoolean
2762 : hasCurveGeometry(int bLookForNonLinear = FALSE) const override;
2763 : virtual OGRGeometry *
2764 : getCurveGeometry(const char *const *papszOptions = nullptr) const override;
2765 : virtual OGRGeometry *
2766 : getLinearGeometry(double dfMaxAngleStepSizeDegrees = 0,
2767 : const char *const *papszOptions = nullptr) const override;
2768 :
2769 : // IWks Interface.
2770 : virtual size_t WkbSize() const override;
2771 : virtual OGRErr importFromWkb(const unsigned char *, size_t, OGRwkbVariant,
2772 : size_t &nBytesConsumedOut) override;
2773 : OGRErr exportToWkb(unsigned char *,
2774 : const OGRwkbExportOptions * = nullptr) const override;
2775 :
2776 : #ifndef DOXYGEN_XML
2777 : using OGRGeometry::importFromWkt; /** deprecated */
2778 : #endif
2779 :
2780 : OGRErr importFromWkt(const char **) override;
2781 :
2782 : #ifndef DOXYGEN_XML
2783 : using OGRGeometry::exportToWkt;
2784 : #endif
2785 :
2786 : /// Export a polygon to WKT
2787 : /// \param opts Output options.
2788 : /// \param err Pointer to error code, if desired.
2789 : /// \return WKT representation of the polygon.
2790 : virtual std::string exportToWkt(const OGRWktOptions &opts = OGRWktOptions(),
2791 : OGRErr *err = nullptr) const override;
2792 :
2793 : // ICurvePolygon.
2794 : virtual OGRPolygon *
2795 : CurvePolyToPoly(double dfMaxAngleStepSizeDegrees = 0,
2796 : const char *const *papszOptions = nullptr) const override;
2797 :
2798 : OGRLinearRing *getExteriorRing();
2799 : const OGRLinearRing *getExteriorRing() const;
2800 : virtual OGRLinearRing *getInteriorRing(int);
2801 : virtual const OGRLinearRing *getInteriorRing(int) const;
2802 :
2803 : OGRLinearRing *stealExteriorRing();
2804 : virtual OGRLinearRing *stealInteriorRing(int);
2805 :
2806 : OGRBoolean IsPointOnSurface(const OGRPoint *) const;
2807 :
2808 : /** Return pointer of this in upper class */
2809 77 : inline OGRCurvePolygon *toUpperClass()
2810 : {
2811 77 : return this;
2812 : }
2813 :
2814 : /** Return pointer of this in upper class */
2815 7 : inline const OGRCurvePolygon *toUpperClass() const
2816 : {
2817 7 : return this;
2818 : }
2819 :
2820 75 : virtual void accept(IOGRGeometryVisitor *visitor) override
2821 : {
2822 75 : visitor->visit(this);
2823 75 : }
2824 :
2825 5 : virtual void accept(IOGRConstGeometryVisitor *visitor) const override
2826 : {
2827 5 : visitor->visit(this);
2828 5 : }
2829 :
2830 : virtual void closeRings() override;
2831 :
2832 2 : OGR_ALLOW_UPCAST_TO(CurvePolygon)
2833 : OGR_ALLOW_CAST_TO_THIS(Polygon)
2834 : };
2835 :
2836 : //! @cond Doxygen_Suppress
2837 : /** @see OGRPolygon::begin() const */
2838 13659 : inline const OGRPolygon::ChildType *const *begin(const OGRPolygon *poGeom)
2839 : {
2840 13659 : return poGeom->begin();
2841 : }
2842 :
2843 : /** @see OGRPolygon::end() const */
2844 13659 : inline const OGRPolygon::ChildType *const *end(const OGRPolygon *poGeom)
2845 : {
2846 13659 : return poGeom->end();
2847 : }
2848 :
2849 : /** @see OGRPolygon::begin() */
2850 68 : inline OGRPolygon::ChildType **begin(OGRPolygon *poGeom)
2851 : {
2852 68 : return poGeom->begin();
2853 : }
2854 :
2855 : /** @see OGRPolygon::end() */
2856 68 : inline OGRPolygon::ChildType **end(OGRPolygon *poGeom)
2857 : {
2858 68 : return poGeom->end();
2859 : }
2860 :
2861 : //! @endcond
2862 :
2863 : /************************************************************************/
2864 : /* OGRTriangle */
2865 : /************************************************************************/
2866 :
2867 : /**
2868 : * Triangle class.
2869 : *
2870 : * @since GDAL 2.2
2871 : */
2872 :
2873 1296182 : class CPL_DLL OGRTriangle : public OGRPolygon
2874 : {
2875 : private:
2876 : // cppcheck-suppress unusedPrivateFunction
2877 : static OGRPolygon *CasterToPolygon(OGRSurface *poSurface);
2878 : bool quickValidityCheck() const;
2879 :
2880 : protected:
2881 : //! @cond Doxygen_Suppress
2882 : virtual OGRSurfaceCasterToPolygon GetCasterToPolygon() const override;
2883 : virtual OGRErr importFromWKTListOnly(const char **ppszInput, int bHasZ,
2884 : int bHasM, OGRRawPoint *&paoPoints,
2885 : int &nMaxPoints,
2886 : double *&padfZ) override;
2887 : //! @endcond
2888 :
2889 : public:
2890 : /** Constructor. */
2891 14726 : OGRTriangle() = default;
2892 : OGRTriangle(const OGRPoint &p, const OGRPoint &q, const OGRPoint &r);
2893 : OGRTriangle(const OGRTriangle &other);
2894 : /** Move constructor */
2895 1 : OGRTriangle(OGRTriangle &&other) = default;
2896 : OGRTriangle(const OGRPolygon &other, OGRErr &eErr);
2897 : OGRTriangle &operator=(const OGRTriangle &other);
2898 : /** Move assignment operator */
2899 : OGRTriangle &operator=(OGRTriangle &&other) = default;
2900 :
2901 : virtual const char *getGeometryName() const override;
2902 : virtual OGRwkbGeometryType getGeometryType() const override;
2903 : virtual OGRTriangle *clone() const override;
2904 :
2905 : // IWks Interface.
2906 : virtual OGRErr importFromWkb(const unsigned char *, size_t, OGRwkbVariant,
2907 : size_t &nBytesConsumedOut) override;
2908 :
2909 : // New methods rewritten from OGRPolygon/OGRCurvePolygon/OGRGeometry.
2910 : virtual OGRErr addRingDirectly(OGRCurve *poNewRing) override;
2911 :
2912 : /** Return pointer of this in upper class */
2913 2 : inline OGRPolygon *toUpperClass()
2914 : {
2915 2 : return this;
2916 : }
2917 :
2918 : /** Return pointer of this in upper class */
2919 2 : inline const OGRPolygon *toUpperClass() const
2920 : {
2921 2 : return this;
2922 : }
2923 :
2924 2 : virtual void accept(IOGRGeometryVisitor *visitor) override
2925 : {
2926 2 : visitor->visit(this);
2927 2 : }
2928 :
2929 2 : virtual void accept(IOGRConstGeometryVisitor *visitor) const override
2930 : {
2931 2 : visitor->visit(this);
2932 2 : }
2933 :
2934 : //! @cond Doxygen_Suppress
2935 : static OGRGeometry *CastToPolygon(OGRGeometry *poGeom);
2936 : //! @endcond
2937 :
2938 1 : OGR_ALLOW_UPCAST_TO(Polygon)
2939 : OGR_ALLOW_CAST_TO_THIS(Triangle)
2940 : };
2941 :
2942 : /************************************************************************/
2943 : /* OGRGeometryCollection */
2944 : /************************************************************************/
2945 :
2946 : /**
2947 : * A collection of 1 or more geometry objects.
2948 : *
2949 : * All geometries must share a common spatial reference system, and
2950 : * Subclasses may impose additional restrictions on the contents.
2951 : */
2952 :
2953 : class CPL_DLL OGRGeometryCollection : public OGRGeometry
2954 : {
2955 : OGRErr importFromWktInternal(const char **ppszInput, int nRecLevel);
2956 :
2957 : protected:
2958 : //! @cond Doxygen_Suppress
2959 : int nGeomCount = 0;
2960 : OGRGeometry **papoGeoms = nullptr;
2961 :
2962 : std::string
2963 : exportToWktInternal(const OGRWktOptions &opts, OGRErr *err,
2964 : const std::string &exclude = std::string()) const;
2965 : static OGRGeometryCollection *
2966 : TransferMembersAndDestroy(OGRGeometryCollection *poSrc,
2967 : OGRGeometryCollection *poDst);
2968 :
2969 : OGRErr importFromWkbInternal(const unsigned char *pabyData, size_t nSize,
2970 : int nRecLevel, OGRwkbVariant,
2971 : size_t &nBytesConsumedOut);
2972 : //! @endcond
2973 : virtual OGRBoolean isCompatibleSubType(OGRwkbGeometryType) const;
2974 :
2975 : public:
2976 : /** Create an empty geometry collection. */
2977 117402 : OGRGeometryCollection() = default;
2978 :
2979 : OGRGeometryCollection(const OGRGeometryCollection &other);
2980 : OGRGeometryCollection(OGRGeometryCollection &&other);
2981 : ~OGRGeometryCollection() override;
2982 :
2983 : OGRGeometryCollection &operator=(const OGRGeometryCollection &other);
2984 : OGRGeometryCollection &operator=(OGRGeometryCollection &&other);
2985 :
2986 : /** Type of child elements. */
2987 : typedef OGRGeometry ChildType;
2988 :
2989 : /** Return begin of sub-geometry iterator.
2990 : * @since GDAL 2.3
2991 : */
2992 391228 : ChildType **begin()
2993 : {
2994 391228 : return papoGeoms;
2995 : }
2996 :
2997 : /** Return end of sub-geometry iterator. */
2998 391223 : ChildType **end()
2999 : {
3000 391223 : return papoGeoms + nGeomCount;
3001 : }
3002 :
3003 : /** Return begin of sub-geometry iterator.
3004 : * @since GDAL 2.3
3005 : */
3006 146722 : const ChildType *const *begin() const
3007 : {
3008 146722 : return papoGeoms;
3009 : }
3010 :
3011 : /** Return end of sub-geometry iterator. */
3012 146722 : const ChildType *const *end() const
3013 : {
3014 146722 : return papoGeoms + nGeomCount;
3015 : }
3016 :
3017 : // Non standard (OGRGeometry).
3018 : virtual const char *getGeometryName() const override;
3019 : virtual OGRwkbGeometryType getGeometryType() const override;
3020 : virtual OGRGeometryCollection *clone() const override;
3021 : virtual void empty() override;
3022 : virtual OGRErr transform(OGRCoordinateTransformation *poCT) override;
3023 : virtual void flattenTo2D() override;
3024 : virtual OGRBoolean IsEmpty() const override;
3025 : virtual bool segmentize(double dfMaxLength) override;
3026 : virtual OGRBoolean
3027 : hasCurveGeometry(int bLookForNonLinear = FALSE) const override;
3028 : virtual OGRGeometry *
3029 : getCurveGeometry(const char *const *papszOptions = nullptr) const override;
3030 : virtual OGRGeometry *
3031 : getLinearGeometry(double dfMaxAngleStepSizeDegrees = 0,
3032 : const char *const *papszOptions = nullptr) const override;
3033 : virtual double
3034 : get_GeodesicArea(const OGRSpatialReference *poSRSOverride = nullptr) const;
3035 : virtual double get_GeodesicLength(
3036 : const OGRSpatialReference *poSRSOverride = nullptr) const;
3037 :
3038 : // IWks Interface
3039 : virtual size_t WkbSize() const override;
3040 : virtual OGRErr importFromWkb(const unsigned char *, size_t, OGRwkbVariant,
3041 : size_t &nBytesConsumedOut) override;
3042 : OGRErr exportToWkb(unsigned char *,
3043 : const OGRwkbExportOptions * = nullptr) const override;
3044 :
3045 : #ifndef DOXYGEN_XML
3046 : using OGRGeometry::importFromWkt; /** deprecated */
3047 : #endif
3048 :
3049 : OGRErr importFromWkt(const char **) override;
3050 :
3051 : #ifndef DOXYGEN_XML
3052 : using OGRGeometry::exportToWkt;
3053 : #endif
3054 :
3055 : /// Export a geometry collection to WKT
3056 : /// \param opts Output options.
3057 : /// \param err Pointer to error code, if desired.
3058 : /// \return WKT representation of the geometry collection.
3059 : virtual std::string exportToWkt(const OGRWktOptions &opts = OGRWktOptions(),
3060 : OGRErr *err = nullptr) const override;
3061 :
3062 : virtual double get_Length() const;
3063 : virtual double get_Area() const;
3064 :
3065 : // IGeometry methods
3066 : virtual int getDimension() const override;
3067 : virtual void getEnvelope(OGREnvelope *psEnvelope) const override;
3068 : virtual void getEnvelope(OGREnvelope3D *psEnvelope) const override;
3069 :
3070 : // IGeometryCollection
3071 : int getNumGeometries() const;
3072 : OGRGeometry *getGeometryRef(int);
3073 : const OGRGeometry *getGeometryRef(int) const;
3074 :
3075 : // ISpatialRelation
3076 : virtual OGRBoolean Equals(const OGRGeometry *) const override;
3077 :
3078 : // Non standard
3079 : virtual bool setCoordinateDimension(int nDimension) override;
3080 : virtual bool set3D(OGRBoolean bIs3D) override;
3081 : virtual bool setMeasured(OGRBoolean bIsMeasured) override;
3082 : virtual OGRErr addGeometry(const OGRGeometry *);
3083 : virtual OGRErr addGeometryDirectly(OGRGeometry *);
3084 : OGRErr addGeometry(std::unique_ptr<OGRGeometry> geom);
3085 : virtual OGRErr removeGeometry(int iIndex, int bDelete = TRUE);
3086 : std::unique_ptr<OGRGeometry> stealGeometry(int iIndex);
3087 :
3088 : bool hasEmptyParts() const override;
3089 : void removeEmptyParts() override;
3090 :
3091 : virtual void
3092 : assignSpatialReference(const OGRSpatialReference *poSR) override;
3093 :
3094 : void closeRings() override;
3095 :
3096 : virtual void swapXY() override;
3097 :
3098 1 : virtual void accept(IOGRGeometryVisitor *visitor) override
3099 : {
3100 1 : visitor->visit(this);
3101 1 : }
3102 :
3103 1 : virtual void accept(IOGRConstGeometryVisitor *visitor) const override
3104 : {
3105 1 : visitor->visit(this);
3106 1 : }
3107 :
3108 : static OGRGeometryCollection *
3109 : CastToGeometryCollection(OGRGeometryCollection *poSrc);
3110 :
3111 : OGR_FORBID_DOWNCAST_TO_POINT
3112 : OGR_FORBID_DOWNCAST_TO_ALL_CURVES
3113 : OGR_FORBID_DOWNCAST_TO_ALL_SURFACES
3114 : OGR_ALLOW_CAST_TO_THIS(GeometryCollection)
3115 : };
3116 :
3117 : //! @cond Doxygen_Suppress
3118 : /** @see OGRGeometryCollection::begin() const */
3119 : inline const OGRGeometryCollection::ChildType *const *
3120 1353 : begin(const OGRGeometryCollection *poGeom)
3121 : {
3122 1353 : return poGeom->begin();
3123 : }
3124 :
3125 : /** @see OGRGeometryCollection::end() const */
3126 : inline const OGRGeometryCollection::ChildType *const *
3127 1334 : end(const OGRGeometryCollection *poGeom)
3128 : {
3129 1334 : return poGeom->end();
3130 : }
3131 :
3132 : /** @see OGRGeometryCollection::begin() */
3133 568 : inline OGRGeometryCollection::ChildType **begin(OGRGeometryCollection *poGeom)
3134 : {
3135 568 : return poGeom->begin();
3136 : }
3137 :
3138 : /** @see OGRGeometryCollection::end() */
3139 568 : inline OGRGeometryCollection::ChildType **end(OGRGeometryCollection *poGeom)
3140 : {
3141 568 : return poGeom->end();
3142 : }
3143 :
3144 : //! @endcond
3145 :
3146 : /************************************************************************/
3147 : /* OGRMultiSurface */
3148 : /************************************************************************/
3149 :
3150 : /**
3151 : * A collection of non-overlapping OGRSurface.
3152 : *
3153 : * @since GDAL 2.0
3154 : */
3155 :
3156 17279 : class CPL_DLL OGRMultiSurface : public OGRGeometryCollection
3157 : {
3158 : protected:
3159 : virtual OGRBoolean isCompatibleSubType(OGRwkbGeometryType) const override;
3160 :
3161 : public:
3162 : /** Create an empty multi surface collection. */
3163 78570 : OGRMultiSurface() = default;
3164 :
3165 : OGRMultiSurface(const OGRMultiSurface &other);
3166 : /** Move constructor */
3167 4 : OGRMultiSurface(OGRMultiSurface &&other) = default;
3168 :
3169 : OGRMultiSurface &operator=(const OGRMultiSurface &other);
3170 : /** Move assignment operator */
3171 : OGRMultiSurface &operator=(OGRMultiSurface &&other) = default;
3172 :
3173 : /** Type of child elements. */
3174 : typedef OGRSurface ChildType;
3175 :
3176 : /** Return begin of iterator.
3177 : * @since GDAL 2.3
3178 : */
3179 64 : ChildType **begin()
3180 : {
3181 64 : return reinterpret_cast<ChildType **>(papoGeoms);
3182 : }
3183 :
3184 : /** Return end of iterator */
3185 64 : ChildType **end()
3186 : {
3187 64 : return reinterpret_cast<ChildType **>(papoGeoms + nGeomCount);
3188 : }
3189 :
3190 : /** Return begin of iterator.
3191 : * @since GDAL 2.3
3192 : */
3193 24 : const ChildType *const *begin() const
3194 : {
3195 24 : return reinterpret_cast<const ChildType *const *>(papoGeoms);
3196 : }
3197 :
3198 : /** Return end of iterator */
3199 24 : const ChildType *const *end() const
3200 : {
3201 24 : return reinterpret_cast<const ChildType *const *>(papoGeoms +
3202 24 : nGeomCount);
3203 : }
3204 :
3205 : // Non standard (OGRGeometry).
3206 : virtual const char *getGeometryName() const override;
3207 : virtual OGRwkbGeometryType getGeometryType() const override;
3208 : virtual OGRMultiSurface *clone() const override;
3209 :
3210 : #ifndef DOXYGEN_XML
3211 : using OGRGeometry::importFromWkt; /** deprecated */
3212 : #endif
3213 :
3214 : OGRErr importFromWkt(const char **) override;
3215 :
3216 : #ifndef DOXYGEN_XML
3217 : using OGRGeometry::exportToWkt;
3218 : #endif
3219 :
3220 : /// Export a geometry collection to WKT
3221 : /// \param opts Output options.
3222 : /// \param err Pointer to error code, if desired.
3223 : /// \return WKT representation of the geometry collection.
3224 : virtual std::string exportToWkt(const OGRWktOptions &opts = OGRWktOptions(),
3225 : OGRErr *err = nullptr) const override;
3226 :
3227 : // IMultiSurface methods
3228 : virtual OGRErr PointOnSurface(OGRPoint *poPoint) const;
3229 :
3230 : // IGeometry methods
3231 : virtual int getDimension() const override;
3232 :
3233 : // IGeometryCollection
3234 : /** See OGRGeometryCollection::getGeometryRef() */
3235 8 : OGRSurface *getGeometryRef(int i)
3236 : {
3237 8 : return OGRGeometryCollection::getGeometryRef(i)->toSurface();
3238 : }
3239 :
3240 : /** See OGRGeometryCollection::getGeometryRef() */
3241 : const OGRSurface *getGeometryRef(int i) const
3242 : {
3243 : return OGRGeometryCollection::getGeometryRef(i)->toSurface();
3244 : }
3245 :
3246 : // Non standard
3247 : virtual OGRBoolean
3248 : hasCurveGeometry(int bLookForNonLinear = FALSE) const override;
3249 :
3250 : /** Return pointer of this in upper class */
3251 1 : inline OGRGeometryCollection *toUpperClass()
3252 : {
3253 1 : return this;
3254 : }
3255 :
3256 : /** Return pointer of this in upper class */
3257 1 : inline const OGRGeometryCollection *toUpperClass() const
3258 : {
3259 1 : return this;
3260 : }
3261 :
3262 1 : virtual void accept(IOGRGeometryVisitor *visitor) override
3263 : {
3264 1 : visitor->visit(this);
3265 1 : }
3266 :
3267 1 : virtual void accept(IOGRConstGeometryVisitor *visitor) const override
3268 : {
3269 1 : visitor->visit(this);
3270 1 : }
3271 :
3272 : static OGRMultiPolygon *CastToMultiPolygon(OGRMultiSurface *poMS);
3273 :
3274 : OGR_ALLOW_CAST_TO_THIS(MultiSurface)
3275 2 : OGR_ALLOW_UPCAST_TO(GeometryCollection)
3276 : OGR_FORBID_DOWNCAST_TO_MULTIPOINT
3277 : OGR_FORBID_DOWNCAST_TO_MULTILINESTRING
3278 : OGR_FORBID_DOWNCAST_TO_MULTICURVE
3279 : };
3280 :
3281 : //! @cond Doxygen_Suppress
3282 : /** @see OGRMultiSurface::begin() const */
3283 : inline const OGRMultiSurface::ChildType *const *
3284 2 : begin(const OGRMultiSurface *poGeom)
3285 : {
3286 2 : return poGeom->begin();
3287 : }
3288 :
3289 : /** @see OGRMultiSurface::end() const */
3290 : inline const OGRMultiSurface::ChildType *const *
3291 2 : end(const OGRMultiSurface *poGeom)
3292 : {
3293 2 : return poGeom->end();
3294 : }
3295 :
3296 : /** @see OGRMultiSurface::begin() */
3297 2 : inline OGRMultiSurface::ChildType **begin(OGRMultiSurface *poGeom)
3298 : {
3299 2 : return poGeom->begin();
3300 : }
3301 :
3302 : /** @see OGRMultiSurface::end() */
3303 2 : inline OGRMultiSurface::ChildType **end(OGRMultiSurface *poGeom)
3304 : {
3305 2 : return poGeom->end();
3306 : }
3307 :
3308 : //! @endcond
3309 :
3310 : /************************************************************************/
3311 : /* OGRMultiPolygon */
3312 : /************************************************************************/
3313 :
3314 : /**
3315 : * A collection of non-overlapping OGRPolygon.
3316 : */
3317 :
3318 17148 : class CPL_DLL OGRMultiPolygon : public OGRMultiSurface
3319 : {
3320 : protected:
3321 : virtual OGRBoolean isCompatibleSubType(OGRwkbGeometryType) const override;
3322 : friend class OGRPolyhedralSurface;
3323 : friend class OGRTriangulatedSurface;
3324 :
3325 : private:
3326 : //! @cond Doxygen_Suppress
3327 : OGRErr _addGeometryWithExpectedSubGeometryType(
3328 : const OGRGeometry *poNewGeom, OGRwkbGeometryType eSubGeometryType);
3329 : OGRErr _addGeometryDirectlyWithExpectedSubGeometryType(
3330 : OGRGeometry *poNewGeom, OGRwkbGeometryType eSubGeometryType);
3331 : //! @endcond
3332 :
3333 : public:
3334 : /** Create an empty multi polygon collection. */
3335 77075 : OGRMultiPolygon() = default;
3336 :
3337 : OGRMultiPolygon(const OGRMultiPolygon &other);
3338 : /** Move constructor */
3339 3 : OGRMultiPolygon(OGRMultiPolygon &&other) = default;
3340 :
3341 : OGRMultiPolygon &operator=(const OGRMultiPolygon &other);
3342 : /** Move assignment operator */
3343 : OGRMultiPolygon &operator=(OGRMultiPolygon &&other) = default;
3344 :
3345 : /** Type of child elements. */
3346 : typedef OGRPolygon ChildType;
3347 :
3348 : /** Return begin of iterator.
3349 : * @since GDAL 2.3
3350 : */
3351 1427 : ChildType **begin()
3352 : {
3353 1427 : return reinterpret_cast<ChildType **>(papoGeoms);
3354 : }
3355 :
3356 : /** Return end of iterator */
3357 1427 : ChildType **end()
3358 : {
3359 1427 : return reinterpret_cast<ChildType **>(papoGeoms + nGeomCount);
3360 : }
3361 :
3362 : /** Return begin of iterator.
3363 : * @since GDAL 2.3
3364 : */
3365 20776 : const ChildType *const *begin() const
3366 : {
3367 20776 : return reinterpret_cast<const ChildType *const *>(papoGeoms);
3368 : }
3369 :
3370 : /** Return end of iterator */
3371 20776 : const ChildType *const *end() const
3372 : {
3373 20776 : return reinterpret_cast<const ChildType *const *>(papoGeoms +
3374 20776 : nGeomCount);
3375 : }
3376 :
3377 : // IGeometryCollection
3378 : /** See OGRGeometryCollection::getGeometryRef() */
3379 546 : OGRPolygon *getGeometryRef(int i)
3380 : {
3381 546 : return OGRGeometryCollection::getGeometryRef(i)->toPolygon();
3382 : }
3383 :
3384 : /** See OGRGeometryCollection::getGeometryRef() */
3385 165160 : const OGRPolygon *getGeometryRef(int i) const
3386 : {
3387 165160 : return OGRGeometryCollection::getGeometryRef(i)->toPolygon();
3388 : }
3389 :
3390 : // Non-standard (OGRGeometry).
3391 : virtual const char *getGeometryName() const override;
3392 : virtual OGRwkbGeometryType getGeometryType() const override;
3393 : virtual OGRMultiPolygon *clone() const override;
3394 :
3395 : #ifndef DOXYGEN_XML
3396 : using OGRGeometry::exportToWkt;
3397 : #endif
3398 :
3399 : virtual OGRErr importFromWkb(const unsigned char *, size_t, OGRwkbVariant,
3400 : size_t &nBytesConsumedOut) override;
3401 :
3402 : /// Export a multipolygon to WKT
3403 : /// \param opts Output options.
3404 : /// \param err Pointer to error code, if desired.
3405 : /// \return WKT representation of the multipolygon.
3406 : virtual std::string exportToWkt(const OGRWktOptions &opts = OGRWktOptions(),
3407 : OGRErr *err = nullptr) const override;
3408 :
3409 : // Non standard
3410 : virtual OGRBoolean
3411 : hasCurveGeometry(int bLookForNonLinear = FALSE) const override;
3412 :
3413 : /** Return pointer of this in upper class */
3414 14 : inline OGRGeometryCollection *toUpperClass()
3415 : {
3416 14 : return this;
3417 : }
3418 :
3419 : /** Return pointer of this in upper class */
3420 1 : inline const OGRGeometryCollection *toUpperClass() const
3421 : {
3422 1 : return this;
3423 : }
3424 :
3425 14 : virtual void accept(IOGRGeometryVisitor *visitor) override
3426 : {
3427 14 : visitor->visit(this);
3428 14 : }
3429 :
3430 1 : virtual void accept(IOGRConstGeometryVisitor *visitor) const override
3431 : {
3432 1 : visitor->visit(this);
3433 1 : }
3434 :
3435 : static OGRMultiSurface *CastToMultiSurface(OGRMultiPolygon *poMP);
3436 :
3437 : OGR_ALLOW_CAST_TO_THIS(MultiPolygon)
3438 1 : OGR_ALLOW_UPCAST_TO(MultiSurface)
3439 : };
3440 :
3441 : //! @cond Doxygen_Suppress
3442 : /** @see OGRMultiPolygon::begin() const */
3443 : inline const OGRMultiPolygon::ChildType *const *
3444 150 : begin(const OGRMultiPolygon *poGeom)
3445 : {
3446 150 : return poGeom->begin();
3447 : }
3448 :
3449 : /** @see OGRMultiPolygon::end() const */
3450 : inline const OGRMultiPolygon::ChildType *const *
3451 150 : end(const OGRMultiPolygon *poGeom)
3452 : {
3453 150 : return poGeom->end();
3454 : }
3455 :
3456 : /** @see OGRMultiPolygon::begin() */
3457 11 : inline OGRMultiPolygon::ChildType **begin(OGRMultiPolygon *poGeom)
3458 : {
3459 11 : return poGeom->begin();
3460 : }
3461 :
3462 : /** @see OGRMultiPolygon::end() */
3463 11 : inline OGRMultiPolygon::ChildType **end(OGRMultiPolygon *poGeom)
3464 : {
3465 11 : return poGeom->end();
3466 : }
3467 :
3468 : //! @endcond
3469 :
3470 : /************************************************************************/
3471 : /* OGRPolyhedralSurface */
3472 : /************************************************************************/
3473 :
3474 : /**
3475 : * PolyhedralSurface class.
3476 : *
3477 : * @since GDAL 2.2
3478 : */
3479 :
3480 47 : class CPL_DLL OGRPolyhedralSurface : public OGRSurface
3481 : {
3482 : protected:
3483 : //! @cond Doxygen_Suppress
3484 : friend class OGRTriangulatedSurface;
3485 : OGRMultiPolygon oMP{};
3486 : virtual OGRSurfaceCasterToPolygon GetCasterToPolygon() const override;
3487 : virtual OGRSurfaceCasterToCurvePolygon
3488 : GetCasterToCurvePolygon() const override;
3489 : virtual OGRBoolean isCompatibleSubType(OGRwkbGeometryType) const;
3490 : virtual const char *getSubGeometryName() const;
3491 : virtual OGRwkbGeometryType getSubGeometryType() const;
3492 : std::string exportToWktInternal(const OGRWktOptions &opts,
3493 : OGRErr *err) const;
3494 :
3495 : virtual OGRPolyhedralSurfaceCastToMultiPolygon
3496 : GetCasterToMultiPolygon() const;
3497 : static OGRMultiPolygon *CastToMultiPolygonImpl(OGRPolyhedralSurface *poPS);
3498 : //! @endcond
3499 :
3500 : public:
3501 : /** Create an empty PolyhedralSurface */
3502 50381 : OGRPolyhedralSurface() = default;
3503 :
3504 : OGRPolyhedralSurface(const OGRPolyhedralSurface &other);
3505 : /** Move constructor */
3506 2 : OGRPolyhedralSurface(OGRPolyhedralSurface &&other) = default;
3507 :
3508 : OGRPolyhedralSurface &operator=(const OGRPolyhedralSurface &other);
3509 : /** Move assignment operator */
3510 : OGRPolyhedralSurface &operator=(OGRPolyhedralSurface &&other) = default;
3511 :
3512 : /** Type of child elements. */
3513 : typedef OGRPolygon ChildType;
3514 :
3515 : /** Return begin of iterator.
3516 : * @since GDAL 2.3
3517 : */
3518 1066 : ChildType **begin()
3519 : {
3520 1066 : return oMP.begin();
3521 : }
3522 :
3523 : /** Return end of iterator */
3524 1066 : ChildType **end()
3525 : {
3526 1066 : return oMP.end();
3527 : }
3528 :
3529 : /** Return begin of iterator.
3530 : * @since GDAL 2.3
3531 : */
3532 18640 : const ChildType *const *begin() const
3533 : {
3534 18640 : return oMP.begin();
3535 : }
3536 :
3537 : /** Return end of iterator */
3538 18640 : const ChildType *const *end() const
3539 : {
3540 18640 : return oMP.end();
3541 : }
3542 :
3543 : // IWks Interface.
3544 : virtual size_t WkbSize() const override;
3545 : virtual const char *getGeometryName() const override;
3546 : virtual OGRwkbGeometryType getGeometryType() const override;
3547 : virtual OGRErr importFromWkb(const unsigned char *, size_t, OGRwkbVariant,
3548 : size_t &nBytesConsumedOut) override;
3549 : OGRErr exportToWkb(unsigned char *,
3550 : const OGRwkbExportOptions * = nullptr) const override;
3551 :
3552 : #ifndef DOXYGEN_XML
3553 : using OGRGeometry::importFromWkt; /** deprecated */
3554 : #endif
3555 :
3556 : OGRErr importFromWkt(const char **) override;
3557 :
3558 : #ifndef DOXYGEN_XML
3559 : using OGRGeometry::exportToWkt;
3560 : #endif
3561 :
3562 : /// Export a polyhedral surface to WKT
3563 : /// \param opts Output options.
3564 : /// \param err Pointer to error code, if desired.
3565 : /// \return WKT representation of the polyhedral surface.
3566 : virtual std::string exportToWkt(const OGRWktOptions &opts = OGRWktOptions(),
3567 : OGRErr *err = nullptr) const override;
3568 :
3569 : // IGeometry methods.
3570 : virtual int getDimension() const override;
3571 :
3572 : virtual void empty() override;
3573 :
3574 : virtual OGRPolyhedralSurface *clone() const override;
3575 : virtual void getEnvelope(OGREnvelope *psEnvelope) const override;
3576 : virtual void getEnvelope(OGREnvelope3D *psEnvelope) const override;
3577 :
3578 : virtual void flattenTo2D() override;
3579 : virtual OGRErr transform(OGRCoordinateTransformation *) override;
3580 : virtual OGRBoolean Equals(const OGRGeometry *) const override;
3581 : virtual double get_Area() const override;
3582 : virtual double get_GeodesicArea(
3583 : const OGRSpatialReference *poSRSOverride = nullptr) const override;
3584 : virtual double get_Length() const override;
3585 : virtual double get_GeodesicLength(
3586 : const OGRSpatialReference *poSRSOverride = nullptr) const override;
3587 :
3588 : virtual OGRErr PointOnSurface(OGRPoint *) const override;
3589 :
3590 : static OGRMultiPolygon *CastToMultiPolygon(OGRPolyhedralSurface *poPS);
3591 : virtual OGRBoolean
3592 : hasCurveGeometry(int bLookForNonLinear = FALSE) const override;
3593 : virtual OGRErr addGeometry(const OGRGeometry *);
3594 : OGRErr addGeometryDirectly(OGRGeometry *poNewGeom);
3595 : OGRErr addGeometry(std::unique_ptr<OGRGeometry> poNewGeom);
3596 :
3597 : int getNumGeometries() const;
3598 : OGRPolygon *getGeometryRef(int i);
3599 : const OGRPolygon *getGeometryRef(int i) const;
3600 :
3601 : virtual OGRBoolean IsEmpty() const override;
3602 : virtual bool setCoordinateDimension(int nDimension) override;
3603 : virtual bool set3D(OGRBoolean bIs3D) override;
3604 : virtual bool setMeasured(OGRBoolean bIsMeasured) override;
3605 : virtual void swapXY() override;
3606 : OGRErr removeGeometry(int iIndex, int bDelete = TRUE);
3607 :
3608 : bool hasEmptyParts() const override;
3609 : void removeEmptyParts() override;
3610 :
3611 1 : virtual void accept(IOGRGeometryVisitor *visitor) override
3612 : {
3613 1 : visitor->visit(this);
3614 1 : }
3615 :
3616 1 : virtual void accept(IOGRConstGeometryVisitor *visitor) const override
3617 : {
3618 1 : visitor->visit(this);
3619 1 : }
3620 :
3621 : virtual void
3622 : assignSpatialReference(const OGRSpatialReference *poSR) override;
3623 :
3624 : OGR_ALLOW_CAST_TO_THIS(PolyhedralSurface)
3625 2 : OGR_ALLOW_UPCAST_TO(Surface)
3626 : };
3627 :
3628 : //! @cond Doxygen_Suppress
3629 : /** @see OGRPolyhedralSurface::begin() const */
3630 : inline const OGRPolyhedralSurface::ChildType *const *
3631 2 : begin(const OGRPolyhedralSurface *poGeom)
3632 : {
3633 2 : return poGeom->begin();
3634 : }
3635 :
3636 : /** @see OGRPolyhedralSurface::end() const */
3637 : inline const OGRPolyhedralSurface::ChildType *const *
3638 2 : end(const OGRPolyhedralSurface *poGeom)
3639 : {
3640 2 : return poGeom->end();
3641 : }
3642 :
3643 : /** @see OGRPolyhedralSurface::begin() */
3644 2 : inline OGRPolyhedralSurface::ChildType **begin(OGRPolyhedralSurface *poGeom)
3645 : {
3646 2 : return poGeom->begin();
3647 : }
3648 :
3649 : /** @see OGRPolyhedralSurface::end() */
3650 2 : inline OGRPolyhedralSurface::ChildType **end(OGRPolyhedralSurface *poGeom)
3651 : {
3652 2 : return poGeom->end();
3653 : }
3654 :
3655 : //! @endcond
3656 :
3657 : /************************************************************************/
3658 : /* OGRTriangulatedSurface */
3659 : /************************************************************************/
3660 :
3661 : /**
3662 : * TriangulatedSurface class.
3663 : *
3664 : * @since GDAL 2.2
3665 : */
3666 :
3667 2 : class CPL_DLL OGRTriangulatedSurface : public OGRPolyhedralSurface
3668 : {
3669 : protected:
3670 : //! @cond Doxygen_Suppress
3671 : virtual OGRBoolean isCompatibleSubType(OGRwkbGeometryType) const override;
3672 : virtual const char *getSubGeometryName() const override;
3673 : virtual OGRwkbGeometryType getSubGeometryType() const override;
3674 :
3675 : virtual OGRPolyhedralSurfaceCastToMultiPolygon
3676 : GetCasterToMultiPolygon() const override;
3677 : static OGRMultiPolygon *CastToMultiPolygonImpl(OGRPolyhedralSurface *poPS);
3678 : //! @endcond
3679 :
3680 : public:
3681 : /** Constructor */
3682 41361 : OGRTriangulatedSurface() = default;
3683 :
3684 : OGRTriangulatedSurface(const OGRTriangulatedSurface &other);
3685 : /** Move constructor */
3686 1 : OGRTriangulatedSurface(OGRTriangulatedSurface &&other) = default;
3687 :
3688 : OGRTriangulatedSurface &operator=(const OGRTriangulatedSurface &other);
3689 : /** Move assignment operator */
3690 : OGRTriangulatedSurface &operator=(OGRTriangulatedSurface &&other) = default;
3691 :
3692 : /** Type of child elements. */
3693 : typedef OGRTriangle ChildType;
3694 :
3695 : /** Return begin of iterator.
3696 : * @since GDAL 2.3
3697 : */
3698 3 : ChildType **begin()
3699 : {
3700 3 : return reinterpret_cast<ChildType **>(oMP.begin());
3701 : }
3702 :
3703 : /** Return end of iterator */
3704 3 : ChildType **end()
3705 : {
3706 3 : return reinterpret_cast<ChildType **>(oMP.end());
3707 : }
3708 :
3709 : /** Return begin of iterator.
3710 : * @since GDAL 2.3
3711 : */
3712 3 : const ChildType *const *begin() const
3713 : {
3714 3 : return reinterpret_cast<const ChildType *const *>(oMP.begin());
3715 : }
3716 :
3717 : /** Return end of iterator */
3718 3 : const ChildType *const *end() const
3719 : {
3720 3 : return reinterpret_cast<const ChildType *const *>(oMP.end());
3721 : }
3722 :
3723 : virtual const char *getGeometryName() const override;
3724 : virtual OGRwkbGeometryType getGeometryType() const override;
3725 : virtual OGRTriangulatedSurface *clone() const override;
3726 :
3727 : /** See OGRPolyhedralSurface::getGeometryRef() */
3728 : OGRTriangle *getGeometryRef(int i)
3729 : {
3730 : return OGRPolyhedralSurface::getGeometryRef(i)->toTriangle();
3731 : }
3732 :
3733 : /** See OGRPolyhedralSurface::getGeometryRef() */
3734 1 : const OGRTriangle *getGeometryRef(int i) const
3735 : {
3736 1 : return OGRPolyhedralSurface::getGeometryRef(i)->toTriangle();
3737 : }
3738 :
3739 : // IWks Interface.
3740 : virtual OGRErr addGeometry(const OGRGeometry *) override;
3741 :
3742 : #ifndef DOXYGEN_XML
3743 : using OGRPolyhedralSurface::addGeometry;
3744 : #endif
3745 :
3746 : /** Return pointer of this in upper class */
3747 1 : inline OGRPolyhedralSurface *toUpperClass()
3748 : {
3749 1 : return this;
3750 : }
3751 :
3752 : /** Return pointer of this in upper class */
3753 1 : inline const OGRPolyhedralSurface *toUpperClass() const
3754 : {
3755 1 : return this;
3756 : }
3757 :
3758 1 : virtual void accept(IOGRGeometryVisitor *visitor) override
3759 : {
3760 1 : visitor->visit(this);
3761 1 : }
3762 :
3763 1 : virtual void accept(IOGRConstGeometryVisitor *visitor) const override
3764 : {
3765 1 : visitor->visit(this);
3766 1 : }
3767 :
3768 : static OGRPolyhedralSurface *
3769 : CastToPolyhedralSurface(OGRTriangulatedSurface *poTS);
3770 :
3771 : OGR_ALLOW_CAST_TO_THIS(TriangulatedSurface)
3772 1 : OGR_ALLOW_UPCAST_TO(PolyhedralSurface)
3773 : };
3774 :
3775 : //! @cond Doxygen_Suppress
3776 : /** @see OGRTriangulatedSurface::begin() const */
3777 : inline const OGRTriangulatedSurface::ChildType *const *
3778 2 : begin(const OGRTriangulatedSurface *poGeom)
3779 : {
3780 2 : return poGeom->begin();
3781 : }
3782 :
3783 : /** @see OGRTriangulatedSurface::end() const */
3784 : inline const OGRTriangulatedSurface::ChildType *const *
3785 2 : end(const OGRTriangulatedSurface *poGeom)
3786 : {
3787 2 : return poGeom->end();
3788 : }
3789 :
3790 : /** @see OGRTriangulatedSurface::begin() */
3791 2 : inline OGRTriangulatedSurface::ChildType **begin(OGRTriangulatedSurface *poGeom)
3792 : {
3793 2 : return poGeom->begin();
3794 : }
3795 :
3796 : /** @see OGRTriangulatedSurface::end() */
3797 2 : inline OGRTriangulatedSurface::ChildType **end(OGRTriangulatedSurface *poGeom)
3798 : {
3799 2 : return poGeom->end();
3800 : }
3801 :
3802 : //! @endcond
3803 :
3804 : /************************************************************************/
3805 : /* OGRMultiPoint */
3806 : /************************************************************************/
3807 :
3808 : /**
3809 : * A collection of OGRPoint.
3810 : */
3811 :
3812 740 : class CPL_DLL OGRMultiPoint : public OGRGeometryCollection
3813 : {
3814 : private:
3815 : OGRErr importFromWkt_Bracketed(const char **, int bHasM, int bHasZ);
3816 :
3817 : protected:
3818 : virtual OGRBoolean isCompatibleSubType(OGRwkbGeometryType) const override;
3819 :
3820 : public:
3821 : /** Create an empty multi point collection. */
3822 4272 : OGRMultiPoint() = default;
3823 :
3824 : OGRMultiPoint(const OGRMultiPoint &other);
3825 : /** Move constructor */
3826 1 : OGRMultiPoint(OGRMultiPoint &&other) = default;
3827 :
3828 : OGRMultiPoint &operator=(const OGRMultiPoint &other);
3829 : /** Move assignment operator */
3830 : OGRMultiPoint &operator=(OGRMultiPoint &&other) = default;
3831 :
3832 : /** Type of child elements. */
3833 : typedef OGRPoint ChildType;
3834 :
3835 : /** Return begin of iterator.
3836 : * @since GDAL 2.3
3837 : */
3838 120 : ChildType **begin()
3839 : {
3840 120 : return reinterpret_cast<ChildType **>(papoGeoms);
3841 : }
3842 :
3843 : /** Return end of iterator */
3844 120 : ChildType **end()
3845 : {
3846 120 : return reinterpret_cast<ChildType **>(papoGeoms + nGeomCount);
3847 : }
3848 :
3849 : /** Return begin of iterator.
3850 : * @since GDAL 2.3
3851 : */
3852 388 : const ChildType *const *begin() const
3853 : {
3854 388 : return reinterpret_cast<const ChildType *const *>(papoGeoms);
3855 : }
3856 :
3857 : /** Return end of iterator */
3858 388 : const ChildType *const *end() const
3859 : {
3860 388 : return reinterpret_cast<const ChildType *const *>(papoGeoms +
3861 388 : nGeomCount);
3862 : }
3863 :
3864 : // IGeometryCollection
3865 : /** See OGRGeometryCollection::getGeometryRef() */
3866 962 : OGRPoint *getGeometryRef(int i)
3867 : {
3868 962 : return OGRGeometryCollection::getGeometryRef(i)->toPoint();
3869 : }
3870 :
3871 : /** See OGRGeometryCollection::getGeometryRef() */
3872 251 : const OGRPoint *getGeometryRef(int i) const
3873 : {
3874 251 : return OGRGeometryCollection::getGeometryRef(i)->toPoint();
3875 : }
3876 :
3877 : // Non-standard (OGRGeometry).
3878 : virtual const char *getGeometryName() const override;
3879 : virtual OGRwkbGeometryType getGeometryType() const override;
3880 : virtual OGRMultiPoint *clone() const override;
3881 :
3882 : #ifndef DOXYGEN_XML
3883 : using OGRGeometry::importFromWkt; /** deprecated */
3884 : #endif
3885 :
3886 : OGRErr importFromWkt(const char **) override;
3887 :
3888 : #ifndef DOXYGEN_XML
3889 : using OGRGeometry::exportToWkt;
3890 : #endif
3891 :
3892 : /// Export a multipoint to WKT
3893 : /// \param opts Output options.
3894 : /// \param err Pointer to error code, if desired.
3895 : /// \return WKT representation of the multipoint.
3896 : virtual std::string exportToWkt(const OGRWktOptions &opts = OGRWktOptions(),
3897 : OGRErr *err = nullptr) const override;
3898 :
3899 : // IGeometry methods.
3900 : virtual int getDimension() const override;
3901 :
3902 : /** Return pointer of this in upper class */
3903 1 : inline OGRGeometryCollection *toUpperClass()
3904 : {
3905 1 : return this;
3906 : }
3907 :
3908 : /** Return pointer of this in upper class */
3909 40 : inline const OGRGeometryCollection *toUpperClass() const
3910 : {
3911 40 : return this;
3912 : }
3913 :
3914 1 : virtual void accept(IOGRGeometryVisitor *visitor) override
3915 : {
3916 1 : visitor->visit(this);
3917 1 : }
3918 :
3919 40 : virtual void accept(IOGRConstGeometryVisitor *visitor) const override
3920 : {
3921 40 : visitor->visit(this);
3922 40 : }
3923 :
3924 : // Non-standard.
3925 : virtual OGRBoolean
3926 : hasCurveGeometry(int bLookForNonLinear = FALSE) const override;
3927 :
3928 : OGR_ALLOW_CAST_TO_THIS(MultiPoint)
3929 1 : OGR_ALLOW_UPCAST_TO(GeometryCollection)
3930 : OGR_FORBID_DOWNCAST_TO_MULTILINESTRING
3931 : OGR_FORBID_DOWNCAST_TO_MULTICURVE
3932 : OGR_FORBID_DOWNCAST_TO_MULTISURFACE
3933 : OGR_FORBID_DOWNCAST_TO_MULTIPOLYGON
3934 : };
3935 :
3936 : //! @cond Doxygen_Suppress
3937 : /** @see OGRMultiPoint::begin() const */
3938 271 : inline const OGRMultiPoint::ChildType *const *begin(const OGRMultiPoint *poGeom)
3939 : {
3940 271 : return poGeom->begin();
3941 : }
3942 :
3943 : /** @see OGRMultiPoint::end() const */
3944 271 : inline const OGRMultiPoint::ChildType *const *end(const OGRMultiPoint *poGeom)
3945 : {
3946 271 : return poGeom->end();
3947 : }
3948 :
3949 : /** @see OGRMultiPoint::begin() */
3950 2 : inline OGRMultiPoint::ChildType **begin(OGRMultiPoint *poGeom)
3951 : {
3952 2 : return poGeom->begin();
3953 : }
3954 :
3955 : /** @see OGRMultiPoint::end() */
3956 2 : inline OGRMultiPoint::ChildType **end(OGRMultiPoint *poGeom)
3957 : {
3958 2 : return poGeom->end();
3959 : }
3960 :
3961 : //! @endcond
3962 :
3963 : /************************************************************************/
3964 : /* OGRMultiCurve */
3965 : /************************************************************************/
3966 :
3967 : /**
3968 : * A collection of OGRCurve.
3969 : *
3970 : * @since GDAL 2.0
3971 : */
3972 :
3973 16519 : class CPL_DLL OGRMultiCurve : public OGRGeometryCollection
3974 : {
3975 : protected:
3976 : //! @cond Doxygen_Suppress
3977 : static OGRErr addCurveDirectlyFromWkt(OGRGeometry *poSelf,
3978 : OGRCurve *poCurve);
3979 : //! @endcond
3980 : virtual OGRBoolean isCompatibleSubType(OGRwkbGeometryType) const override;
3981 :
3982 : public:
3983 : /** Create an empty multi curve collection. */
3984 29352 : OGRMultiCurve() = default;
3985 :
3986 : OGRMultiCurve(const OGRMultiCurve &other);
3987 : /** Move constructor */
3988 2 : OGRMultiCurve(OGRMultiCurve &&other) = default;
3989 :
3990 : OGRMultiCurve &operator=(const OGRMultiCurve &other);
3991 : /** Move assignment operator */
3992 : OGRMultiCurve &operator=(OGRMultiCurve &&other) = default;
3993 :
3994 : /** Type of child elements. */
3995 : typedef OGRCurve ChildType;
3996 :
3997 : /** Return begin of iterator.
3998 : * @since GDAL 2.3
3999 : */
4000 64 : ChildType **begin()
4001 : {
4002 64 : return reinterpret_cast<ChildType **>(papoGeoms);
4003 : }
4004 :
4005 : /** Return end of iterator */
4006 64 : ChildType **end()
4007 : {
4008 64 : return reinterpret_cast<ChildType **>(papoGeoms + nGeomCount);
4009 : }
4010 :
4011 : /** Return begin of iterator.
4012 : * @since GDAL 2.3
4013 : */
4014 17 : const ChildType *const *begin() const
4015 : {
4016 17 : return reinterpret_cast<const ChildType *const *>(papoGeoms);
4017 : }
4018 :
4019 : /** Return end of iterator */
4020 17 : const ChildType *const *end() const
4021 : {
4022 17 : return reinterpret_cast<const ChildType *const *>(papoGeoms +
4023 17 : nGeomCount);
4024 : }
4025 :
4026 : // IGeometryCollection
4027 : /** See OGRGeometryCollection::getGeometryRef() */
4028 : OGRCurve *getGeometryRef(int i)
4029 : {
4030 : return OGRGeometryCollection::getGeometryRef(i)->toCurve();
4031 : }
4032 :
4033 : /** See OGRGeometryCollection::getGeometryRef() */
4034 : const OGRCurve *getGeometryRef(int i) const
4035 : {
4036 : return OGRGeometryCollection::getGeometryRef(i)->toCurve();
4037 : }
4038 :
4039 : // Non standard (OGRGeometry).
4040 : virtual const char *getGeometryName() const override;
4041 : virtual OGRwkbGeometryType getGeometryType() const override;
4042 : virtual OGRMultiCurve *clone() const override;
4043 :
4044 : #ifndef DOXYGEN_XML
4045 : using OGRGeometry::importFromWkt; /** deprecated */
4046 : #endif
4047 :
4048 : OGRErr importFromWkt(const char **) override;
4049 :
4050 : #ifndef DOXYGEN_XML
4051 : using OGRGeometry::exportToWkt;
4052 : #endif
4053 :
4054 : /// Export a multicurve to WKT
4055 : /// \param opts Output options.
4056 : /// \param err Pointer to error code, if desired.
4057 : /// \return WKT representation of the multicurve.
4058 : virtual std::string exportToWkt(const OGRWktOptions &opts = OGRWktOptions(),
4059 : OGRErr *err = nullptr) const override;
4060 :
4061 : // IGeometry methods.
4062 : virtual int getDimension() const override;
4063 :
4064 : // Non-standard.
4065 : virtual OGRBoolean
4066 : hasCurveGeometry(int bLookForNonLinear = FALSE) const override;
4067 :
4068 : /** Return pointer of this in upper class */
4069 1 : inline OGRGeometryCollection *toUpperClass()
4070 : {
4071 1 : return this;
4072 : }
4073 :
4074 : /** Return pointer of this in upper class */
4075 1 : inline const OGRGeometryCollection *toUpperClass() const
4076 : {
4077 1 : return this;
4078 : }
4079 :
4080 1 : virtual void accept(IOGRGeometryVisitor *visitor) override
4081 : {
4082 1 : visitor->visit(this);
4083 1 : }
4084 :
4085 1 : virtual void accept(IOGRConstGeometryVisitor *visitor) const override
4086 : {
4087 1 : visitor->visit(this);
4088 1 : }
4089 :
4090 : static OGRMultiLineString *CastToMultiLineString(OGRMultiCurve *poMC);
4091 :
4092 : OGR_ALLOW_CAST_TO_THIS(MultiCurve)
4093 2 : OGR_ALLOW_UPCAST_TO(GeometryCollection)
4094 : OGR_FORBID_DOWNCAST_TO_MULTIPOINT
4095 : OGR_FORBID_DOWNCAST_TO_MULTISURFACE
4096 : OGR_FORBID_DOWNCAST_TO_MULTIPOLYGON
4097 : };
4098 :
4099 : //! @cond Doxygen_Suppress
4100 : /** @see OGRMultiCurve::begin() const */
4101 2 : inline const OGRMultiCurve::ChildType *const *begin(const OGRMultiCurve *poGeom)
4102 : {
4103 2 : return poGeom->begin();
4104 : }
4105 :
4106 : /** @see OGRMultiCurve::end() const */
4107 2 : inline const OGRMultiCurve::ChildType *const *end(const OGRMultiCurve *poGeom)
4108 : {
4109 2 : return poGeom->end();
4110 : }
4111 :
4112 : /** @see OGRMultiCurve::begin() */
4113 21 : inline OGRMultiCurve::ChildType **begin(OGRMultiCurve *poGeom)
4114 : {
4115 21 : return poGeom->begin();
4116 : }
4117 :
4118 : /** @see OGRMultiCurve::end() */
4119 21 : inline OGRMultiCurve::ChildType **end(OGRMultiCurve *poGeom)
4120 : {
4121 21 : return poGeom->end();
4122 : }
4123 :
4124 : //! @endcond
4125 :
4126 : /************************************************************************/
4127 : /* OGRMultiLineString */
4128 : /************************************************************************/
4129 :
4130 : /**
4131 : * A collection of OGRLineString.
4132 : */
4133 :
4134 16359 : class CPL_DLL OGRMultiLineString : public OGRMultiCurve
4135 : {
4136 : protected:
4137 : virtual OGRBoolean isCompatibleSubType(OGRwkbGeometryType) const override;
4138 :
4139 : public:
4140 : /** Create an empty multi line string collection. */
4141 27917 : OGRMultiLineString() = default;
4142 :
4143 : OGRMultiLineString(const OGRMultiLineString &other);
4144 : /** Move constructor */
4145 1 : OGRMultiLineString(OGRMultiLineString &&other) = default;
4146 :
4147 : OGRMultiLineString &operator=(const OGRMultiLineString &other);
4148 : /** Move assignment operator */
4149 : OGRMultiLineString &operator=(OGRMultiLineString &&other) = default;
4150 :
4151 : /** Type of child elements. */
4152 : typedef OGRLineString ChildType;
4153 :
4154 : /** Return begin of iterator.
4155 : * @since GDAL 2.3
4156 : */
4157 114 : ChildType **begin()
4158 : {
4159 114 : return reinterpret_cast<ChildType **>(papoGeoms);
4160 : }
4161 :
4162 : /** Return end of iterator */
4163 114 : ChildType **end()
4164 : {
4165 114 : return reinterpret_cast<ChildType **>(papoGeoms + nGeomCount);
4166 : }
4167 :
4168 : /** Return begin of iterator.
4169 : * @since GDAL 2.3
4170 : */
4171 8893 : const ChildType *const *begin() const
4172 : {
4173 8893 : return reinterpret_cast<const ChildType *const *>(papoGeoms);
4174 : }
4175 :
4176 : /** Return end of iterator */
4177 8893 : const ChildType *const *end() const
4178 : {
4179 8893 : return reinterpret_cast<const ChildType *const *>(papoGeoms +
4180 8893 : nGeomCount);
4181 : }
4182 :
4183 : // IGeometryCollection
4184 : /** See OGRGeometryCollection::getGeometryRef() */
4185 26936 : OGRLineString *getGeometryRef(int i)
4186 : {
4187 26936 : return OGRGeometryCollection::getGeometryRef(i)->toLineString();
4188 : }
4189 :
4190 : /** See OGRGeometryCollection::getGeometryRef() */
4191 67 : const OGRLineString *getGeometryRef(int i) const
4192 : {
4193 67 : return OGRGeometryCollection::getGeometryRef(i)->toLineString();
4194 : }
4195 :
4196 : // Non standard (OGRGeometry).
4197 : virtual const char *getGeometryName() const override;
4198 : virtual OGRwkbGeometryType getGeometryType() const override;
4199 : virtual OGRMultiLineString *clone() const override;
4200 :
4201 : #ifndef DOXYGEN_XML
4202 : using OGRGeometry::exportToWkt;
4203 : #endif
4204 :
4205 : virtual OGRErr importFromWkb(const unsigned char *, size_t, OGRwkbVariant,
4206 : size_t &nBytesConsumedOut) override;
4207 :
4208 : /// Export a multilinestring to WKT
4209 : /// \param opts Output options.
4210 : /// \param err Pointer to error code, if desired.
4211 : /// \return WKT representation of the multilinestring.
4212 : virtual std::string exportToWkt(const OGRWktOptions &opts = OGRWktOptions(),
4213 : OGRErr *err = nullptr) const override;
4214 :
4215 : // Non standard
4216 : virtual OGRBoolean
4217 : hasCurveGeometry(int bLookForNonLinear = FALSE) const override;
4218 :
4219 : /** Return pointer of this in upper class */
4220 8 : inline OGRGeometryCollection *toUpperClass()
4221 : {
4222 8 : return this;
4223 : }
4224 :
4225 : /** Return pointer of this in upper class */
4226 1 : inline const OGRGeometryCollection *toUpperClass() const
4227 : {
4228 1 : return this;
4229 : }
4230 :
4231 8 : virtual void accept(IOGRGeometryVisitor *visitor) override
4232 : {
4233 8 : visitor->visit(this);
4234 8 : }
4235 :
4236 1 : virtual void accept(IOGRConstGeometryVisitor *visitor) const override
4237 : {
4238 1 : visitor->visit(this);
4239 1 : }
4240 :
4241 : static OGRMultiCurve *CastToMultiCurve(OGRMultiLineString *poMLS);
4242 :
4243 : OGR_ALLOW_CAST_TO_THIS(MultiLineString)
4244 1 : OGR_ALLOW_UPCAST_TO(MultiCurve)
4245 : OGR_FORBID_DOWNCAST_TO_MULTIPOINT
4246 : OGR_FORBID_DOWNCAST_TO_MULTISURFACE
4247 : OGR_FORBID_DOWNCAST_TO_MULTIPOLYGON
4248 : };
4249 :
4250 : //! @cond Doxygen_Suppress
4251 : /** @see OGRMultiLineString::begin() const */
4252 : inline const OGRMultiLineString::ChildType *const *
4253 8803 : begin(const OGRMultiLineString *poGeom)
4254 : {
4255 8803 : return poGeom->begin();
4256 : }
4257 :
4258 : /** @see OGRMultiLineString::end() const */
4259 : inline const OGRMultiLineString::ChildType *const *
4260 8803 : end(const OGRMultiLineString *poGeom)
4261 : {
4262 8803 : return poGeom->end();
4263 : }
4264 :
4265 : /** @see OGRMultiLineString::begin() */
4266 2 : inline OGRMultiLineString::ChildType **begin(OGRMultiLineString *poGeom)
4267 : {
4268 2 : return poGeom->begin();
4269 : }
4270 :
4271 : /** @see OGRMultiLineString::end() */
4272 2 : inline OGRMultiLineString::ChildType **end(OGRMultiLineString *poGeom)
4273 : {
4274 2 : return poGeom->end();
4275 : }
4276 :
4277 : //! @endcond
4278 :
4279 : /************************************************************************/
4280 : /* OGRGeometryFactory */
4281 : /************************************************************************/
4282 :
4283 : /**
4284 : * Create geometry objects from well known text/binary.
4285 : */
4286 :
4287 : class CPL_DLL OGRGeometryFactory
4288 : {
4289 : static OGRErr createFromFgfInternal(const unsigned char *pabyData,
4290 : OGRSpatialReference *poSR,
4291 : OGRGeometry **ppoReturn, int nBytes,
4292 : int *pnBytesConsumed, int nRecLevel);
4293 :
4294 : public:
4295 : static OGRErr createFromWkb(const void *, const OGRSpatialReference *,
4296 : OGRGeometry **,
4297 : size_t = static_cast<size_t>(-1),
4298 : OGRwkbVariant = wkbVariantOldOgc);
4299 : static OGRErr createFromWkb(const void *pabyData,
4300 : const OGRSpatialReference *, OGRGeometry **,
4301 : size_t nSize, OGRwkbVariant eVariant,
4302 : size_t &nBytesConsumedOut);
4303 : static OGRErr createFromWkt(const char *, const OGRSpatialReference *,
4304 : OGRGeometry **);
4305 : static OGRErr createFromWkt(const char **, const OGRSpatialReference *,
4306 : OGRGeometry **);
4307 : static std::pair<std::unique_ptr<OGRGeometry>, OGRErr>
4308 : createFromWkt(const char *, const OGRSpatialReference * = nullptr);
4309 :
4310 : /** Deprecated.
4311 : * @deprecated in GDAL 2.3
4312 : */
4313 : static OGRErr createFromWkt(char **ppszInput,
4314 : const OGRSpatialReference *poSRS,
4315 : OGRGeometry **ppoGeom)
4316 : CPL_WARN_DEPRECATED("Use createFromWkt(const char**, ...) instead")
4317 : {
4318 : return createFromWkt(const_cast<const char **>(ppszInput), poSRS,
4319 : ppoGeom);
4320 : }
4321 :
4322 : static OGRErr createFromFgf(const void *, OGRSpatialReference *,
4323 : OGRGeometry **, int = -1, int * = nullptr);
4324 : static OGRGeometry *createFromGML(const char *);
4325 : static OGRGeometry *createFromGEOS(GEOSContextHandle_t hGEOSCtxt, GEOSGeom);
4326 : static OGRGeometry *createFromGeoJson(const char *, int = -1);
4327 : static OGRGeometry *createFromGeoJson(const CPLJSONObject &oJSONObject);
4328 :
4329 : static void destroyGeometry(OGRGeometry *);
4330 : static OGRGeometry *createGeometry(OGRwkbGeometryType);
4331 :
4332 : static OGRGeometry *forceToPolygon(OGRGeometry *);
4333 : static OGRGeometry *forceToLineString(OGRGeometry *,
4334 : bool bOnlyInOrder = true);
4335 : static OGRGeometry *forceToMultiPolygon(OGRGeometry *);
4336 : static OGRGeometry *forceToMultiPoint(OGRGeometry *);
4337 : static OGRGeometry *forceToMultiLineString(OGRGeometry *);
4338 :
4339 : static OGRGeometry *forceTo(OGRGeometry *poGeom,
4340 : OGRwkbGeometryType eTargetType,
4341 : const char *const *papszOptions = nullptr);
4342 :
4343 : static OGRGeometry *removeLowerDimensionSubGeoms(const OGRGeometry *poGeom);
4344 :
4345 : static OGRGeometry *organizePolygons(OGRGeometry **papoPolygons,
4346 : int nPolygonCount,
4347 : int *pbResultValidGeometry,
4348 : const char **papszOptions = nullptr);
4349 : static bool haveGEOS();
4350 :
4351 : /** Opaque class used as argument to transformWithOptions() */
4352 : class CPL_DLL TransformWithOptionsCache
4353 : {
4354 : friend class OGRGeometryFactory;
4355 : struct Private;
4356 : std::unique_ptr<Private> d;
4357 :
4358 : public:
4359 : TransformWithOptionsCache();
4360 : ~TransformWithOptionsCache();
4361 : };
4362 :
4363 : //! @cond Doxygen_Suppress
4364 : static bool isTransformWithOptionsRegularTransform(
4365 : const OGRSpatialReference *poSourceCRS,
4366 : const OGRSpatialReference *poTargetCRS, CSLConstList papszOptions);
4367 : //! @endcond
4368 :
4369 : static OGRGeometry *transformWithOptions(
4370 : const OGRGeometry *poSrcGeom, OGRCoordinateTransformation *poCT,
4371 : char **papszOptions,
4372 : const TransformWithOptionsCache &cache = TransformWithOptionsCache());
4373 :
4374 : static double GetDefaultArcStepSize();
4375 :
4376 : static OGRGeometry *
4377 : approximateArcAngles(double dfX, double dfY, double dfZ,
4378 : double dfPrimaryRadius, double dfSecondaryAxis,
4379 : double dfRotation, double dfStartAngle,
4380 : double dfEndAngle, double dfMaxAngleStepSizeDegrees,
4381 : const bool bUseMaxGap = false);
4382 :
4383 : static int GetCurveParameters(double x0, double y0, double x1, double y1,
4384 : double x2, double y2, double &R, double &cx,
4385 : double &cy, double &alpha0, double &alpha1,
4386 : double &alpha2);
4387 : static OGRLineString *
4388 : curveToLineString(double x0, double y0, double z0, double x1, double y1,
4389 : double z1, double x2, double y2, double z2, int bHasZ,
4390 : double dfMaxAngleStepSizeDegrees,
4391 : const char *const *papszOptions = nullptr);
4392 : static OGRCurve *
4393 : curveFromLineString(const OGRLineString *poLS,
4394 : const char *const *papszOptions = nullptr);
4395 : };
4396 :
4397 : OGRwkbGeometryType CPL_DLL OGRFromOGCGeomType(const char *pszGeomType);
4398 : const char CPL_DLL *OGRToOGCGeomType(OGRwkbGeometryType eGeomType,
4399 : bool bCamelCase = false,
4400 : bool bAddZM = false,
4401 : bool bSpaceBeforeZM = false);
4402 :
4403 : //! @cond Doxygen_Suppress
4404 : typedef struct _OGRPreparedGeometry OGRPreparedGeometry;
4405 :
4406 : struct CPL_DLL OGRPreparedGeometryUniquePtrDeleter
4407 : {
4408 : void operator()(OGRPreparedGeometry *) const;
4409 : };
4410 :
4411 : //! @endcond
4412 :
4413 : /** Unique pointer type for OGRPreparedGeometry.
4414 : * @since GDAL 2.3
4415 : */
4416 : typedef std::unique_ptr<OGRPreparedGeometry,
4417 : OGRPreparedGeometryUniquePtrDeleter>
4418 : OGRPreparedGeometryUniquePtr;
4419 :
4420 : #endif /* ndef OGR_GEOMETRY_H_INCLUDED */
|