LCOV - code coverage report
Current view: top level - ogr - ogresrijsongeometry.cpp (source / functions) Hit Total Coverage
Test: gdal_filtered.info Lines: 240 300 80.0 %
Date: 2026-02-01 11:59:10 Functions: 12 12 100.0 %

          Line data    Source code
       1             : // SPDX-License-Identifier: MIT
       2             : // Copyright 2024, Even Rouault <even.rouault at spatialys.com>
       3             : 
       4             : /*! @cond Doxygen_Suppress */
       5             : 
       6             : #include "ogresrijsongeometry.h"
       7             : 
       8             : #include "ogrlibjsonutils.h"
       9             : 
      10             : #include "ogr_geometry.h"
      11             : #include "ogr_spatialref.h"
      12             : 
      13             : static OGRPoint *OGRESRIJSONReadPoint(json_object *poObj);
      14             : static OGRGeometry *OGRESRIJSONReadLineString(json_object *poObj);
      15             : static OGRGeometry *OGRESRIJSONReadPolygon(json_object *poObj);
      16             : static OGRMultiPoint *OGRESRIJSONReadMultiPoint(json_object *poObj);
      17             : 
      18             : /************************************************************************/
      19             : /*                      OGRESRIJSONReadGeometry()                       */
      20             : /************************************************************************/
      21             : 
      22          19 : OGRGeometry *OGRESRIJSONReadGeometry(json_object *poObj)
      23             : {
      24          19 :     OGRGeometry *poGeometry = nullptr;
      25             : 
      26          19 :     if (OGRGeoJSONFindMemberByName(poObj, "x"))
      27           6 :         poGeometry = OGRESRIJSONReadPoint(poObj);
      28          13 :     else if (OGRGeoJSONFindMemberByName(poObj, "paths"))
      29           3 :         poGeometry = OGRESRIJSONReadLineString(poObj);
      30          10 :     else if (OGRGeoJSONFindMemberByName(poObj, "rings"))
      31           5 :         poGeometry = OGRESRIJSONReadPolygon(poObj);
      32           5 :     else if (OGRGeoJSONFindMemberByName(poObj, "points"))
      33           5 :         poGeometry = OGRESRIJSONReadMultiPoint(poObj);
      34             : 
      35          19 :     return poGeometry;
      36             : }
      37             : 
      38             : /************************************************************************/
      39             : /*                  OGR_G_CreateGeometryFromEsriJson()                  */
      40             : /************************************************************************/
      41             : 
      42             : /** Create a OGR geometry from a ESRIJson geometry object */
      43           2 : OGRGeometryH OGR_G_CreateGeometryFromEsriJson(const char *pszJson)
      44             : {
      45           2 :     if (nullptr == pszJson)
      46             :     {
      47             :         // Translation failed.
      48           0 :         return nullptr;
      49             :     }
      50             : 
      51           2 :     json_object *poObj = nullptr;
      52           2 :     if (!OGRJSonParse(pszJson, &poObj))
      53           1 :         return nullptr;
      54             : 
      55           1 :     OGRGeometry *poGeometry = OGRESRIJSONReadGeometry(poObj);
      56             : 
      57             :     // Release JSON tree.
      58           1 :     json_object_put(poObj);
      59             : 
      60           1 :     return OGRGeometry::ToHandle(poGeometry);
      61             : }
      62             : 
      63             : /************************************************************************/
      64             : /*                         OGRESRIJSONGetType()                         */
      65             : /************************************************************************/
      66             : 
      67          21 : OGRwkbGeometryType OGRESRIJSONGetGeometryType(json_object *poObj)
      68             : {
      69          21 :     if (nullptr == poObj)
      70           0 :         return wkbUnknown;
      71             : 
      72          21 :     json_object *poObjType = OGRGeoJSONFindMemberByName(poObj, "geometryType");
      73          21 :     if (nullptr == poObjType)
      74             :     {
      75           1 :         return wkbNone;
      76             :     }
      77             : 
      78          20 :     const char *name = json_object_get_string(poObjType);
      79          20 :     if (EQUAL(name, "esriGeometryPoint"))
      80           8 :         return wkbPoint;
      81          12 :     else if (EQUAL(name, "esriGeometryPolyline"))
      82           3 :         return wkbLineString;
      83           9 :     else if (EQUAL(name, "esriGeometryPolygon"))
      84           4 :         return wkbPolygon;
      85           5 :     else if (EQUAL(name, "esriGeometryMultiPoint"))
      86           5 :         return wkbMultiPoint;
      87             :     else
      88           0 :         return wkbUnknown;
      89             : }
      90             : 
      91             : /************************************************************************/
      92             : /*                  OGRESRIJSONGetCoordinateToDouble()                  */
      93             : /************************************************************************/
      94             : 
      95         175 : static double OGRESRIJSONGetCoordinateToDouble(json_object *poObjCoord,
      96             :                                                const char *pszCoordName,
      97             :                                                bool &bValid)
      98             : {
      99         175 :     const int iType = json_object_get_type(poObjCoord);
     100         175 :     if (json_type_double != iType && json_type_int != iType)
     101             :     {
     102           0 :         CPLError(CE_Failure, CPLE_AppDefined,
     103             :                  "Invalid '%s' coordinate. "
     104             :                  "Type is not double or integer for \'%s\'.",
     105             :                  pszCoordName, json_object_to_json_string(poObjCoord));
     106           0 :         bValid = false;
     107           0 :         return 0.0;
     108             :     }
     109             : 
     110         175 :     return json_object_get_double(poObjCoord);
     111             : }
     112             : 
     113             : /************************************************************************/
     114             : /*                      OGRESRIJSONGetCoordinate()                      */
     115             : /************************************************************************/
     116             : 
     117          12 : static double OGRESRIJSONGetCoordinate(json_object *poObj,
     118             :                                        const char *pszCoordName, bool &bValid)
     119             : {
     120          12 :     json_object *poObjCoord = OGRGeoJSONFindMemberByName(poObj, pszCoordName);
     121          12 :     if (nullptr == poObjCoord)
     122             :     {
     123           0 :         CPLError(CE_Failure, CPLE_AppDefined,
     124             :                  "Invalid Point object. "
     125             :                  "Missing '%s' member.",
     126             :                  pszCoordName);
     127           0 :         bValid = false;
     128           0 :         return 0.0;
     129             :     }
     130             : 
     131          12 :     return OGRESRIJSONGetCoordinateToDouble(poObjCoord, pszCoordName, bValid);
     132             : }
     133             : 
     134             : /************************************************************************/
     135             : /*                        OGRESRIJSONReadPoint()                        */
     136             : /************************************************************************/
     137             : 
     138           6 : OGRPoint *OGRESRIJSONReadPoint(json_object *poObj)
     139             : {
     140           6 :     CPLAssert(nullptr != poObj);
     141             : 
     142           6 :     bool bValid = true;
     143           6 :     const double dfX = OGRESRIJSONGetCoordinate(poObj, "x", bValid);
     144           6 :     const double dfY = OGRESRIJSONGetCoordinate(poObj, "y", bValid);
     145           6 :     if (!bValid)
     146           0 :         return nullptr;
     147             : 
     148           6 :     json_object *poObjZ = OGRGeoJSONFindMemberByName(poObj, "z");
     149           6 :     if (nullptr == poObjZ)
     150           3 :         return new OGRPoint(dfX, dfY);
     151             : 
     152           3 :     const double dfZ = OGRESRIJSONGetCoordinateToDouble(poObjZ, "z", bValid);
     153           3 :     if (!bValid)
     154           0 :         return nullptr;
     155           3 :     return new OGRPoint(dfX, dfY, dfZ);
     156             : }
     157             : 
     158             : /************************************************************************/
     159             : /*                      OGRESRIJSONReaderParseZM()                      */
     160             : /************************************************************************/
     161             : 
     162          13 : static void OGRESRIJSONReaderParseZM(json_object *poObj, bool *bHasZ,
     163             :                                      bool *bHasM)
     164             : {
     165          13 :     CPLAssert(nullptr != poObj);
     166             :     // The ESRI geojson spec states that geometries other than point can
     167             :     // have the attributes hasZ and hasM.  A geometry that has a z value
     168             :     // implies the 3rd number in the tuple is z.  if hasM is true, but hasZ
     169             :     // is not, it is the M value.
     170          13 :     bool bZ = false;
     171          13 :     json_object *poObjHasZ = OGRGeoJSONFindMemberByName(poObj, "hasZ");
     172          13 :     if (poObjHasZ != nullptr)
     173             :     {
     174           2 :         if (json_object_get_type(poObjHasZ) == json_type_boolean)
     175             :         {
     176           2 :             bZ = CPL_TO_BOOL(json_object_get_boolean(poObjHasZ));
     177             :         }
     178             :     }
     179             : 
     180          13 :     bool bM = false;
     181          13 :     json_object *poObjHasM = OGRGeoJSONFindMemberByName(poObj, "hasM");
     182          13 :     if (poObjHasM != nullptr)
     183             :     {
     184           2 :         if (json_object_get_type(poObjHasM) == json_type_boolean)
     185             :         {
     186           2 :             bM = CPL_TO_BOOL(json_object_get_boolean(poObjHasM));
     187             :         }
     188             :     }
     189          13 :     if (bHasZ != nullptr)
     190          13 :         *bHasZ = bZ;
     191          13 :     if (bHasM != nullptr)
     192          13 :         *bHasM = bM;
     193          13 : }
     194             : 
     195             : /************************************************************************/
     196             : /*                  OGRESRIJSONReaderParseXYZMArray()                   */
     197             : /************************************************************************/
     198             : 
     199          70 : static bool OGRESRIJSONReaderParseXYZMArray(json_object *poObjCoords,
     200             :                                             bool /*bHasZ*/, bool bHasM,
     201             :                                             double *pdfX, double *pdfY,
     202             :                                             double *pdfZ, double *pdfM,
     203             :                                             int *pnNumCoords)
     204             : {
     205          70 :     if (poObjCoords == nullptr)
     206             :     {
     207           0 :         CPLDebug("ESRIJSON",
     208             :                  "OGRESRIJSONReaderParseXYZMArray: got null object.");
     209           0 :         return false;
     210             :     }
     211             : 
     212          70 :     if (json_type_array != json_object_get_type(poObjCoords))
     213             :     {
     214           0 :         CPLDebug("ESRIJSON",
     215             :                  "OGRESRIJSONReaderParseXYZMArray: got non-array object.");
     216           0 :         return false;
     217             :     }
     218             : 
     219          70 :     const auto coordDimension = json_object_array_length(poObjCoords);
     220             : 
     221             :     // Allow 4 coordinates if M is present, but it is eventually ignored.
     222          70 :     if (coordDimension < 2 || coordDimension > 4)
     223             :     {
     224           0 :         CPLDebug("ESRIJSON",
     225             :                  "OGRESRIJSONReaderParseXYZMArray: got an unexpected "
     226             :                  "array object.");
     227           0 :         return false;
     228             :     }
     229             : 
     230             :     // Read X coordinate.
     231          70 :     json_object *poObjCoord = json_object_array_get_idx(poObjCoords, 0);
     232          70 :     if (poObjCoord == nullptr)
     233             :     {
     234           0 :         CPLDebug("ESRIJSON",
     235             :                  "OGRESRIJSONReaderParseXYZMArray: got null object.");
     236           0 :         return false;
     237             :     }
     238             : 
     239          70 :     bool bValid = true;
     240             :     const double dfX =
     241          70 :         OGRESRIJSONGetCoordinateToDouble(poObjCoord, "x", bValid);
     242             : 
     243             :     // Read Y coordinate.
     244          70 :     poObjCoord = json_object_array_get_idx(poObjCoords, 1);
     245          70 :     if (poObjCoord == nullptr)
     246             :     {
     247           0 :         CPLDebug("ESRIJSON",
     248             :                  "OGRESRIJSONReaderParseXYZMArray: got null object.");
     249           0 :         return false;
     250             :     }
     251             : 
     252             :     const double dfY =
     253          70 :         OGRESRIJSONGetCoordinateToDouble(poObjCoord, "y", bValid);
     254          70 :     if (!bValid)
     255           0 :         return false;
     256             : 
     257             :     // Read Z or M or Z and M coordinates.
     258          70 :     if (coordDimension > 2)
     259             :     {
     260          18 :         poObjCoord = json_object_array_get_idx(poObjCoords, 2);
     261          18 :         if (poObjCoord == nullptr)
     262             :         {
     263           0 :             CPLDebug("ESRIJSON",
     264             :                      "OGRESRIJSONReaderParseXYZMArray: got null object.");
     265           0 :             return false;
     266             :         }
     267             : 
     268          34 :         const double dfZorM = OGRESRIJSONGetCoordinateToDouble(
     269          16 :             poObjCoord, (coordDimension > 3 || !bHasM) ? "z" : "m", bValid);
     270          18 :         if (!bValid)
     271           0 :             return false;
     272          18 :         if (pdfZ != nullptr)
     273             :         {
     274          18 :             if (coordDimension > 3 || !bHasM)
     275          16 :                 *pdfZ = dfZorM;
     276             :             else
     277           2 :                 *pdfZ = 0.0;
     278             :         }
     279          18 :         if (pdfM != nullptr && coordDimension == 3)
     280             :         {
     281          16 :             if (bHasM)
     282           2 :                 *pdfM = dfZorM;
     283             :             else
     284          14 :                 *pdfM = 0.0;
     285             :         }
     286          18 :         if (coordDimension == 4)
     287             :         {
     288           2 :             poObjCoord = json_object_array_get_idx(poObjCoords, 3);
     289           2 :             if (poObjCoord == nullptr)
     290             :             {
     291           0 :                 CPLDebug("ESRIJSON",
     292             :                          "OGRESRIJSONReaderParseXYZMArray: got null object.");
     293           0 :                 return false;
     294             :             }
     295             : 
     296             :             const double dfM =
     297           2 :                 OGRESRIJSONGetCoordinateToDouble(poObjCoord, "m", bValid);
     298           2 :             if (!bValid)
     299           0 :                 return false;
     300           2 :             if (pdfM != nullptr)
     301           2 :                 *pdfM = dfM;
     302             :         }
     303             :     }
     304             :     else
     305             :     {
     306          52 :         if (pdfZ != nullptr)
     307          52 :             *pdfZ = 0.0;
     308          52 :         if (pdfM != nullptr)
     309          52 :             *pdfM = 0.0;
     310             :     }
     311             : 
     312          70 :     if (pnNumCoords != nullptr)
     313          70 :         *pnNumCoords = static_cast<int>(coordDimension);
     314          70 :     if (pdfX != nullptr)
     315          70 :         *pdfX = dfX;
     316          70 :     if (pdfY != nullptr)
     317          70 :         *pdfY = dfY;
     318             : 
     319          70 :     return true;
     320             : }
     321             : 
     322             : /************************************************************************/
     323             : /*                     OGRESRIJSONReadLineString()                      */
     324             : /************************************************************************/
     325             : 
     326           3 : OGRGeometry *OGRESRIJSONReadLineString(json_object *poObj)
     327             : {
     328           3 :     CPLAssert(nullptr != poObj);
     329             : 
     330           3 :     bool bHasZ = false;
     331           3 :     bool bHasM = false;
     332             : 
     333           3 :     OGRESRIJSONReaderParseZM(poObj, &bHasZ, &bHasM);
     334             : 
     335           3 :     json_object *poObjPaths = OGRGeoJSONFindMemberByName(poObj, "paths");
     336           3 :     if (nullptr == poObjPaths)
     337             :     {
     338           0 :         CPLError(CE_Failure, CPLE_AppDefined,
     339             :                  "Invalid LineString object. "
     340             :                  "Missing \'paths\' member.");
     341           0 :         return nullptr;
     342             :     }
     343             : 
     344           3 :     if (json_type_array != json_object_get_type(poObjPaths))
     345             :     {
     346           0 :         CPLError(CE_Failure, CPLE_AppDefined,
     347             :                  "Invalid LineString object. "
     348             :                  "Invalid \'paths\' member.");
     349           0 :         return nullptr;
     350             :     }
     351             : 
     352           3 :     OGRMultiLineString *poMLS = nullptr;
     353           3 :     OGRGeometry *poRet = nullptr;
     354           3 :     const auto nPaths = json_object_array_length(poObjPaths);
     355           7 :     for (auto iPath = decltype(nPaths){0}; iPath < nPaths; iPath++)
     356             :     {
     357           4 :         json_object *poObjPath = json_object_array_get_idx(poObjPaths, iPath);
     358           8 :         if (poObjPath == nullptr ||
     359           4 :             json_type_array != json_object_get_type(poObjPath))
     360             :         {
     361           0 :             delete poRet;
     362           0 :             CPLDebug("ESRIJSON", "LineString: got non-array object.");
     363           0 :             return nullptr;
     364             :         }
     365             : 
     366           4 :         OGRLineString *poLine = new OGRLineString();
     367           4 :         if (nPaths > 1)
     368             :         {
     369           2 :             if (iPath == 0)
     370             :             {
     371           1 :                 poMLS = new OGRMultiLineString();
     372           1 :                 poRet = poMLS;
     373             :             }
     374           2 :             poMLS->addGeometryDirectly(poLine);
     375             :         }
     376             :         else
     377             :         {
     378           2 :             poRet = poLine;
     379             :         }
     380           4 :         const auto nPoints = json_object_array_length(poObjPath);
     381          12 :         for (auto i = decltype(nPoints){0}; i < nPoints; i++)
     382             :         {
     383           8 :             int nNumCoords = 2;
     384           8 :             json_object *poObjCoords = json_object_array_get_idx(poObjPath, i);
     385           8 :             double dfX = 0.0;
     386           8 :             double dfY = 0.0;
     387           8 :             double dfZ = 0.0;
     388           8 :             double dfM = 0.0;
     389           8 :             if (!OGRESRIJSONReaderParseXYZMArray(poObjCoords, bHasZ, bHasM,
     390             :                                                  &dfX, &dfY, &dfZ, &dfM,
     391             :                                                  &nNumCoords))
     392             :             {
     393           0 :                 delete poRet;
     394           0 :                 return nullptr;
     395             :             }
     396             : 
     397           8 :             if (nNumCoords == 3 && !bHasM)
     398             :             {
     399           2 :                 poLine->addPoint(dfX, dfY, dfZ);
     400             :             }
     401           6 :             else if (nNumCoords == 3)
     402             :             {
     403           0 :                 poLine->addPointM(dfX, dfY, dfM);
     404             :             }
     405           6 :             else if (nNumCoords == 4)
     406             :             {
     407           0 :                 poLine->addPoint(dfX, dfY, dfZ, dfM);
     408             :             }
     409             :             else
     410             :             {
     411           6 :                 poLine->addPoint(dfX, dfY);
     412             :             }
     413             :         }
     414             :     }
     415             : 
     416           3 :     if (poRet == nullptr)
     417           0 :         poRet = new OGRLineString();
     418             : 
     419           3 :     return poRet;
     420             : }
     421             : 
     422             : /************************************************************************/
     423             : /*                       OGRESRIJSONReadPolygon()                       */
     424             : /************************************************************************/
     425             : 
     426           5 : OGRGeometry *OGRESRIJSONReadPolygon(json_object *poObj)
     427             : {
     428           5 :     CPLAssert(nullptr != poObj);
     429             : 
     430           5 :     bool bHasZ = false;
     431           5 :     bool bHasM = false;
     432             : 
     433           5 :     OGRESRIJSONReaderParseZM(poObj, &bHasZ, &bHasM);
     434             : 
     435           5 :     json_object *poObjRings = OGRGeoJSONFindMemberByName(poObj, "rings");
     436           5 :     if (nullptr == poObjRings)
     437             :     {
     438           0 :         CPLError(CE_Failure, CPLE_AppDefined,
     439             :                  "Invalid Polygon object. "
     440             :                  "Missing \'rings\' member.");
     441           0 :         return nullptr;
     442             :     }
     443             : 
     444           5 :     if (json_type_array != json_object_get_type(poObjRings))
     445             :     {
     446           0 :         CPLError(CE_Failure, CPLE_AppDefined,
     447             :                  "Invalid Polygon object. "
     448             :                  "Invalid \'rings\' member.");
     449           0 :         return nullptr;
     450             :     }
     451             : 
     452           5 :     const auto nRings = json_object_array_length(poObjRings);
     453          10 :     std::vector<std::unique_ptr<OGRGeometry>> apoGeoms;
     454           5 :     apoGeoms.reserve(nRings);
     455          11 :     for (auto iRing = decltype(nRings){0}; iRing < nRings; iRing++)
     456             :     {
     457           6 :         json_object *poObjRing = json_object_array_get_idx(poObjRings, iRing);
     458          12 :         if (poObjRing == nullptr ||
     459           6 :             json_type_array != json_object_get_type(poObjRing))
     460             :         {
     461           0 :             CPLDebug("ESRIJSON", "Polygon: got non-array object.");
     462           0 :             return nullptr;
     463             :         }
     464             : 
     465           6 :         auto poLine = std::make_unique<OGRLinearRing>();
     466             : 
     467           6 :         const auto nPoints = json_object_array_length(poObjRing);
     468          58 :         for (auto i = decltype(nPoints){0}; i < nPoints; i++)
     469             :         {
     470          52 :             int nNumCoords = 2;
     471          52 :             json_object *poObjCoords = json_object_array_get_idx(poObjRing, i);
     472          52 :             double dfX = 0.0;
     473          52 :             double dfY = 0.0;
     474          52 :             double dfZ = 0.0;
     475          52 :             double dfM = 0.0;
     476          52 :             if (!OGRESRIJSONReaderParseXYZMArray(poObjCoords, bHasZ, bHasM,
     477             :                                                  &dfX, &dfY, &dfZ, &dfM,
     478             :                                                  &nNumCoords))
     479             :             {
     480           0 :                 return nullptr;
     481             :             }
     482             : 
     483          52 :             if (nNumCoords == 3 && !bHasM)
     484             :             {
     485          10 :                 poLine->addPoint(dfX, dfY, dfZ);
     486             :             }
     487          42 :             else if (nNumCoords == 3)
     488             :             {
     489           0 :                 poLine->addPointM(dfX, dfY, dfM);
     490             :             }
     491          42 :             else if (nNumCoords == 4)
     492             :             {
     493           0 :                 poLine->addPoint(dfX, dfY, dfZ, dfM);
     494             :             }
     495             :             else
     496             :             {
     497          42 :                 poLine->addPoint(dfX, dfY);
     498             :             }
     499             :         }
     500             : 
     501           6 :         auto poPoly = std::make_unique<OGRPolygon>();
     502           6 :         poPoly->addRing(std::move(poLine));
     503           6 :         apoGeoms.push_back(std::move(poPoly));
     504             :     }
     505             : 
     506           5 :     return OGRGeometryFactory::organizePolygons(apoGeoms).release();
     507             : }
     508             : 
     509             : /************************************************************************/
     510             : /*                     OGRESRIJSONReadMultiPoint()                      */
     511             : /************************************************************************/
     512             : 
     513           5 : OGRMultiPoint *OGRESRIJSONReadMultiPoint(json_object *poObj)
     514             : {
     515           5 :     CPLAssert(nullptr != poObj);
     516             : 
     517           5 :     bool bHasZ = false;
     518           5 :     bool bHasM = false;
     519             : 
     520           5 :     OGRESRIJSONReaderParseZM(poObj, &bHasZ, &bHasM);
     521             : 
     522           5 :     json_object *poObjPoints = OGRGeoJSONFindMemberByName(poObj, "points");
     523           5 :     if (nullptr == poObjPoints)
     524             :     {
     525           0 :         CPLError(CE_Failure, CPLE_AppDefined,
     526             :                  "Invalid MultiPoint object. "
     527             :                  "Missing \'points\' member.");
     528           0 :         return nullptr;
     529             :     }
     530             : 
     531           5 :     if (json_type_array != json_object_get_type(poObjPoints))
     532             :     {
     533           0 :         CPLError(CE_Failure, CPLE_AppDefined,
     534             :                  "Invalid MultiPoint object. "
     535             :                  "Invalid \'points\' member.");
     536           0 :         return nullptr;
     537             :     }
     538             : 
     539           5 :     OGRMultiPoint *poMulti = new OGRMultiPoint();
     540             : 
     541           5 :     const auto nPoints = json_object_array_length(poObjPoints);
     542          15 :     for (auto i = decltype(nPoints){0}; i < nPoints; i++)
     543             :     {
     544          10 :         int nNumCoords = 2;
     545          10 :         json_object *poObjCoords = json_object_array_get_idx(poObjPoints, i);
     546          10 :         double dfX = 0.0;
     547          10 :         double dfY = 0.0;
     548          10 :         double dfZ = 0.0;
     549          10 :         double dfM = 0.0;
     550          10 :         if (!OGRESRIJSONReaderParseXYZMArray(poObjCoords, bHasZ, bHasM, &dfX,
     551             :                                              &dfY, &dfZ, &dfM, &nNumCoords))
     552             :         {
     553           0 :             delete poMulti;
     554           0 :             return nullptr;
     555             :         }
     556             : 
     557          10 :         if (nNumCoords == 3 && !bHasM)
     558             :         {
     559           2 :             poMulti->addGeometryDirectly(new OGRPoint(dfX, dfY, dfZ));
     560             :         }
     561           8 :         else if (nNumCoords == 3)
     562             :         {
     563           2 :             OGRPoint *poPoint = new OGRPoint(dfX, dfY);
     564           2 :             poPoint->setM(dfM);
     565           2 :             poMulti->addGeometryDirectly(poPoint);
     566             :         }
     567           6 :         else if (nNumCoords == 4)
     568             :         {
     569           2 :             poMulti->addGeometryDirectly(new OGRPoint(dfX, dfY, dfZ, dfM));
     570             :         }
     571             :         else
     572             :         {
     573           4 :             poMulti->addGeometryDirectly(new OGRPoint(dfX, dfY));
     574             :         }
     575             :     }
     576             : 
     577           5 :     return poMulti;
     578             : }
     579             : 
     580             : /************************************************************************/
     581             : /*                  OGRESRIJSONReadSpatialReference()                   */
     582             : /************************************************************************/
     583             : 
     584          22 : OGRSpatialReference *OGRESRIJSONReadSpatialReference(json_object *poObj)
     585             : {
     586             :     /* -------------------------------------------------------------------- */
     587             :     /*      Read spatial reference definition.                              */
     588             :     /* -------------------------------------------------------------------- */
     589          22 :     OGRSpatialReference *poSRS = nullptr;
     590             : 
     591             :     json_object *poObjSrs =
     592          22 :         OGRGeoJSONFindMemberByName(poObj, "spatialReference");
     593          22 :     if (nullptr != poObjSrs)
     594             :     {
     595             :         json_object *poObjWkid =
     596          10 :             OGRGeoJSONFindMemberByName(poObjSrs, "latestWkid");
     597          10 :         if (poObjWkid == nullptr)
     598           9 :             poObjWkid = OGRGeoJSONFindMemberByName(poObjSrs, "wkid");
     599          10 :         if (poObjWkid == nullptr)
     600             :         {
     601           1 :             json_object *poObjWkt = OGRGeoJSONFindMemberByName(poObjSrs, "wkt");
     602           1 :             if (poObjWkt == nullptr)
     603           0 :                 return nullptr;
     604             : 
     605           1 :             const char *pszWKT = json_object_get_string(poObjWkt);
     606           1 :             poSRS = new OGRSpatialReference();
     607           1 :             poSRS->SetAxisMappingStrategy(OAMS_TRADITIONAL_GIS_ORDER);
     608           1 :             if (OGRERR_NONE != poSRS->importFromWkt(pszWKT))
     609             :             {
     610           0 :                 delete poSRS;
     611           0 :                 poSRS = nullptr;
     612             :             }
     613             :             else
     614             :             {
     615           1 :                 auto poSRSMatch = poSRS->FindBestMatch(70);
     616           1 :                 if (poSRSMatch)
     617             :                 {
     618           1 :                     poSRS->Release();
     619           1 :                     poSRS = poSRSMatch;
     620           1 :                     poSRS->SetAxisMappingStrategy(OAMS_TRADITIONAL_GIS_ORDER);
     621             :                 }
     622             :             }
     623             : 
     624           1 :             return poSRS;
     625             :         }
     626             : 
     627           9 :         const int nEPSG = json_object_get_int(poObjWkid);
     628             : 
     629           9 :         poSRS = new OGRSpatialReference();
     630           9 :         poSRS->SetAxisMappingStrategy(OAMS_TRADITIONAL_GIS_ORDER);
     631           9 :         if (OGRERR_NONE != poSRS->importFromEPSG(nEPSG))
     632             :         {
     633           0 :             delete poSRS;
     634           0 :             poSRS = nullptr;
     635             :         }
     636             :     }
     637             : 
     638          21 :     return poSRS;
     639             : }
     640             : 
     641             : /*! @endcond */

Generated by: LCOV version 1.14