Coverage Report

Created: 2025-06-09 07:43

/src/gdal/ogr/ogrmulticurve.cpp
Line
Count
Source (jump to first uncovered line)
1
/******************************************************************************
2
 *
3
 * Project:  OpenGIS Simple Features Reference Implementation
4
 * Purpose:  The OGRMultiCurve class.
5
 * Author:   Even Rouault <even dot rouault at spatialys dot com>
6
 *
7
 ******************************************************************************
8
 * Copyright (c) 2014, Even Rouault <even dot rouault at spatialys dot com>
9
 *
10
 * SPDX-License-Identifier: MIT
11
 ****************************************************************************/
12
13
#include "cpl_port.h"
14
#include "ogr_geometry.h"
15
16
#include <cstddef>
17
18
#include "cpl_error.h"
19
#include "ogr_api.h"
20
#include "ogr_core.h"
21
#include "ogr_p.h"
22
23
/************************************************************************/
24
/*                OGRMultiCurve( const OGRMultiCurve& )                 */
25
/************************************************************************/
26
27
/**
28
 * \brief Copy constructor.
29
 *
30
 * Note: before GDAL 2.1, only the default implementation of the constructor
31
 * existed, which could be unsafe to use.
32
 *
33
 * @since GDAL 2.1
34
 */
35
36
0
OGRMultiCurve::OGRMultiCurve(const OGRMultiCurve &) = default;
37
38
/************************************************************************/
39
/*                  operator=( const OGRMultiCurve&)                    */
40
/************************************************************************/
41
42
/**
43
 * \brief Assignment operator.
44
 *
45
 * Note: before GDAL 2.1, only the default implementation of the operator
46
 * existed, which could be unsafe to use.
47
 *
48
 * @since GDAL 2.1
49
 */
50
51
OGRMultiCurve &OGRMultiCurve::operator=(const OGRMultiCurve &other)
52
0
{
53
0
    if (this != &other)
54
0
    {
55
0
        OGRGeometryCollection::operator=(other);
56
0
    }
57
0
    return *this;
58
0
}
59
60
/************************************************************************/
61
/*                               clone()                                */
62
/************************************************************************/
63
64
OGRMultiCurve *OGRMultiCurve::clone() const
65
66
0
{
67
0
    auto ret = new (std::nothrow) OGRMultiCurve(*this);
68
0
    if (ret)
69
0
    {
70
0
        if (ret->WkbSize() != WkbSize())
71
0
        {
72
0
            delete ret;
73
0
            ret = nullptr;
74
0
        }
75
0
    }
76
0
    return ret;
77
0
}
78
79
/************************************************************************/
80
/*                          getGeometryType()                           */
81
/************************************************************************/
82
83
OGRwkbGeometryType OGRMultiCurve::getGeometryType() const
84
85
0
{
86
0
    if ((flags & OGR_G_3D) && (flags & OGR_G_MEASURED))
87
0
        return wkbMultiCurveZM;
88
0
    else if (flags & OGR_G_MEASURED)
89
0
        return wkbMultiCurveM;
90
0
    else if (flags & OGR_G_3D)
91
0
        return wkbMultiCurveZ;
92
0
    else
93
0
        return wkbMultiCurve;
94
0
}
95
96
/************************************************************************/
97
/*                            getDimension()                            */
98
/************************************************************************/
99
100
int OGRMultiCurve::getDimension() const
101
102
0
{
103
0
    return 1;
104
0
}
105
106
/************************************************************************/
107
/*                          getGeometryName()                           */
108
/************************************************************************/
109
110
const char *OGRMultiCurve::getGeometryName() const
111
112
0
{
113
0
    return "MULTICURVE";
114
0
}
115
116
/************************************************************************/
117
/*                          isCompatibleSubType()                       */
118
/************************************************************************/
119
120
OGRBoolean
121
OGRMultiCurve::isCompatibleSubType(OGRwkbGeometryType eGeomType) const
122
0
{
123
0
    return OGR_GT_IsCurve(eGeomType);
124
0
}
125
126
/*! @cond Doxygen_Suppress */
127
/************************************************************************/
128
/*                       addCurveDirectlyFromWkt()                      */
129
/************************************************************************/
130
131
OGRErr OGRMultiCurve::addCurveDirectlyFromWkt(OGRGeometry *poSelf,
132
                                              OGRCurve *poCurve)
133
0
{
134
0
    return poSelf->toMultiCurve()->addGeometryDirectly(poCurve);
135
0
}
136
137
/*! @endcond */
138
139
/************************************************************************/
140
/*                           importFromWkt()                            */
141
/*                                                                      */
142
/*      Instantiate from well known text format.                        */
143
/************************************************************************/
144
145
OGRErr OGRMultiCurve::importFromWkt(const char **ppszInput)
146
147
0
{
148
0
    const bool bIsMultiCurve = wkbFlatten(getGeometryType()) == wkbMultiCurve;
149
0
    return importCurveCollectionFromWkt(ppszInput,
150
0
                                        TRUE,           // bAllowEmptyComponent.
151
0
                                        bIsMultiCurve,  // bAllowLineString.
152
0
                                        bIsMultiCurve,  // bAllowCurve.
153
0
                                        bIsMultiCurve,  // bAllowCompoundCurve.
154
0
                                        addCurveDirectlyFromWkt);
155
0
}
156
157
/************************************************************************/
158
/*                            exportToWkt()                             */
159
/************************************************************************/
160
161
std::string OGRMultiCurve::exportToWkt(const OGRWktOptions &opts,
162
                                       OGRErr *err) const
163
0
{
164
0
    OGRWktOptions optsModified(opts);
165
0
    optsModified.variant = wkbVariantIso;
166
0
    return exportToWktInternal(optsModified, err, "LINESTRING");
167
0
}
168
169
/************************************************************************/
170
/*                         hasCurveGeometry()                           */
171
/************************************************************************/
172
173
OGRBoolean OGRMultiCurve::hasCurveGeometry(int bLookForNonLinear) const
174
0
{
175
0
    if (bLookForNonLinear)
176
0
        return OGRGeometryCollection::hasCurveGeometry(TRUE);
177
0
    return true;
178
0
}
179
180
/************************************************************************/
181
/*                          CastToMultiLineString()                     */
182
/************************************************************************/
183
184
/**
185
 * \brief Cast to multi line string.
186
 *
187
 * This method should only be called if the multicurve actually only contains
188
 * instances of OGRLineString. This can be verified if hasCurveGeometry(TRUE)
189
 * returns FALSE. It is not intended to approximate circular curves. For that
190
 * use getLinearGeometry().
191
 *
192
 * The passed in geometry is consumed and a new one returned (or NULL in case
193
 * of failure).
194
 *
195
 * @param poMC the input geometry - ownership is passed to the method.
196
 * @return new geometry.
197
 */
198
199
OGRMultiLineString *OGRMultiCurve::CastToMultiLineString(OGRMultiCurve *poMC)
200
0
{
201
0
    for (auto &&poSubGeom : *poMC)
202
0
    {
203
0
        poSubGeom = OGRCurve::CastToLineString(poSubGeom);
204
0
        if (poSubGeom == nullptr)
205
0
        {
206
0
            delete poMC;
207
0
            return nullptr;
208
0
        }
209
0
    }
210
0
    OGRMultiLineString *poMLS = new OGRMultiLineString();
211
0
    TransferMembersAndDestroy(poMC, poMLS);
212
0
    return poMLS;
213
0
}