LCOV - code coverage report
Current view: directory - ogr - ogr_api.cpp (source / functions) Found Hit Coverage
Test: gdal_filtered.info Lines: 204 151 74.0 %
Date: 2012-12-26 Functions: 18 17 94.4 %

       1                 : /******************************************************************************
       2                 :  * $Id: ogr_api.cpp 22416 2011-05-22 20:19:45Z rouault $
       3                 :  *
       4                 :  * Project:  OpenGIS Simple Features Reference Implementation
       5                 :  * Purpose:  C API Functions that don't correspond one-to-one with C++ 
       6                 :  *           methods, such as the "simplified" geometry access functions.
       7                 :  * Author:   Frank Warmerdam, warmerdam@pobox.com
       8                 :  *
       9                 :  ******************************************************************************
      10                 :  * Copyright (c) 2002, Frank Warmerdam
      11                 :  *
      12                 :  * Permission is hereby granted, free of charge, to any person obtaining a
      13                 :  * copy of this software and associated documentation files (the "Software"),
      14                 :  * to deal in the Software without restriction, including without limitation
      15                 :  * the rights to use, copy, modify, merge, publish, distribute, sublicense,
      16                 :  * and/or sell copies of the Software, and to permit persons to whom the
      17                 :  * Software is furnished to do so, subject to the following conditions:
      18                 :  *
      19                 :  * The above copyright notice and this permission notice shall be included
      20                 :  * in all copies or substantial portions of the Software.
      21                 :  *
      22                 :  * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
      23                 :  * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
      24                 :  * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
      25                 :  * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
      26                 :  * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
      27                 :  * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
      28                 :  * DEALINGS IN THE SOFTWARE.
      29                 :  ****************************************************************************/
      30                 : 
      31                 : #include "ogr_geometry.h"
      32                 : #include "ogr_api.h"
      33                 : #include "cpl_error.h"
      34                 : 
      35                 : /************************************************************************/
      36                 : /*                        OGR_G_GetPointCount()                         */
      37                 : /************************************************************************/
      38                 : /**
      39                 :  * \brief Fetch number of points from a geometry.
      40                 :  *
      41                 :  * Only wkbPoint[25D] or wkbLineString[25D] may return a valid value.
      42                 :  * Other geometry types will silently return 0.
      43                 :  *
      44                 :  * @param hGeom handle to the geometry from which to get the number of points.
      45                 :  * @return the number of points.
      46                 :  */
      47                 : 
      48            3927 : int OGR_G_GetPointCount( OGRGeometryH hGeom )
      49                 : 
      50                 : {
      51            3927 :     VALIDATE_POINTER1( hGeom, "OGR_G_GetPointCount", 0 );
      52                 : 
      53            3927 :     switch( wkbFlatten(((OGRGeometry *) hGeom)->getGeometryType()) )
      54                 :     {
      55                 :       case wkbPoint:
      56             844 :         return 1;
      57                 : 
      58                 :       case wkbLineString:
      59                 :       {
      60            2069 :           OGRLineString *poLine = (OGRLineString *) hGeom;
      61            2069 :           return poLine->getNumPoints();
      62                 :       }
      63                 : 
      64                 :       default:
      65                 :         // autotest/pymod/ogrtest.py calls this method on any geometry. So keep silent
      66                 :         //CPLError(CE_Failure, CPLE_NotSupported, "Incompatible geometry for operation");
      67            1014 :         return 0;
      68                 :     }
      69                 : }
      70                 : 
      71                 : /************************************************************************/
      72                 : /*                             OGR_G_GetX()                             */
      73                 : /************************************************************************/
      74                 : /**
      75                 :  * \brief Fetch the x coordinate of a point from a geometry.
      76                 :  *
      77                 :  * @param hGeom handle to the geometry from which to get the x coordinate.
      78                 :  * @param i point to get the x coordinate.
      79                 :  * @return the X coordinate of this point. 
      80                 :  */
      81                 : 
      82           17958 : double OGR_G_GetX( OGRGeometryH hGeom, int i )
      83                 : 
      84                 : {
      85           17958 :     VALIDATE_POINTER1( hGeom, "OGR_G_GetX", 0 );
      86                 : 
      87           17958 :     switch( wkbFlatten(((OGRGeometry *) hGeom)->getGeometryType()) )
      88                 :     {
      89                 :       case wkbPoint:
      90                 :       {
      91             597 :           if( i == 0 )
      92             597 :               return ((OGRPoint *) hGeom)->getX();
      93                 :           else
      94                 :           {
      95               0 :               CPLError(CE_Failure, CPLE_NotSupported, "Only i == 0 is supported");
      96               0 :               return 0.0;
      97                 :           }
      98                 :       }
      99                 : 
     100                 :       case wkbLineString:
     101                 :       {
     102           17361 :           OGRLineString* poLS = (OGRLineString *) hGeom;
     103           17361 :           if (i < 0 || i >= poLS->getNumPoints())
     104                 :           {
     105               0 :               CPLError(CE_Failure, CPLE_NotSupported, "Index out of bounds");
     106               0 :               return 0.0;
     107                 :           }
     108           17361 :           return poLS->getX( i );
     109                 :       }
     110                 : 
     111                 :       default:
     112               0 :         CPLError(CE_Failure, CPLE_NotSupported, "Incompatible geometry for operation");
     113               0 :         return 0.0;
     114                 :     }
     115                 : }
     116                 : 
     117                 : /************************************************************************/
     118                 : /*                             OGR_G_GetY()                             */
     119                 : /************************************************************************/
     120                 : /**
     121                 :  * \brief Fetch the x coordinate of a point from a geometry.
     122                 :  *
     123                 :  * @param hGeom handle to the geometry from which to get the y coordinate.
     124                 :  * @param i point to get the Y coordinate.
     125                 :  * @return the Y coordinate of this point. 
     126                 :  */
     127                 : 
     128           17958 : double OGR_G_GetY( OGRGeometryH hGeom, int i )
     129                 : 
     130                 : {
     131           17958 :     VALIDATE_POINTER1( hGeom, "OGR_G_GetY", 0 );
     132                 : 
     133           17958 :     switch( wkbFlatten(((OGRGeometry *) hGeom)->getGeometryType()) )
     134                 :     {
     135                 :       case wkbPoint:
     136                 :       {
     137             597 :           if( i == 0 )
     138             597 :               return ((OGRPoint *) hGeom)->getY();
     139                 :           else
     140                 :           {
     141               0 :               CPLError(CE_Failure, CPLE_NotSupported, "Only i == 0 is supported");
     142               0 :               return 0.0;
     143                 :           }
     144                 :       }
     145                 : 
     146                 :       case wkbLineString:
     147                 :       {
     148           17361 :           OGRLineString* poLS = (OGRLineString *) hGeom;
     149           17361 :           if (i < 0 || i >= poLS->getNumPoints())
     150                 :           {
     151               0 :               CPLError(CE_Failure, CPLE_NotSupported, "Index out of bounds");
     152               0 :               return 0.0;
     153                 :           }
     154           17361 :           return poLS->getY( i );
     155                 :       }
     156                 : 
     157                 :       default:
     158               0 :         CPLError(CE_Failure, CPLE_NotSupported, "Incompatible geometry for operation");
     159               0 :         return 0.0;
     160                 :     }
     161                 : }
     162                 : 
     163                 : /************************************************************************/
     164                 : /*                             OGR_G_GetZ()                             */
     165                 : /************************************************************************/
     166                 : /**
     167                 :  * \brief Fetch the z coordinate of a point from a geometry.
     168                 :  *
     169                 :  * @param hGeom handle to the geometry from which to get the Z coordinate.
     170                 :  * @param i point to get the Z coordinate.
     171                 :  * @return the Z coordinate of this point. 
     172                 :  */
     173                 : 
     174           17618 : double OGR_G_GetZ( OGRGeometryH hGeom, int i )
     175                 : 
     176                 : {
     177           17618 :     VALIDATE_POINTER1( hGeom, "OGR_G_GetZ", 0 );
     178                 : 
     179           17618 :     switch( wkbFlatten(((OGRGeometry *) hGeom)->getGeometryType()) )
     180                 :     {
     181                 :       case wkbPoint:
     182                 :       {
     183             562 :           if( i == 0 )
     184             562 :               return ((OGRPoint *) hGeom)->getZ();
     185                 :           else
     186                 :           {
     187               0 :               CPLError(CE_Failure, CPLE_NotSupported, "Only i == 0 is supported");
     188               0 :               return 0.0;
     189                 :           }
     190                 :       }
     191                 : 
     192                 :       case wkbLineString:
     193                 :       {
     194           17056 :           OGRLineString* poLS = (OGRLineString *) hGeom;
     195           17056 :           if (i < 0 || i >= poLS->getNumPoints())
     196                 :           {
     197               0 :               CPLError(CE_Failure, CPLE_NotSupported, "Index out of bounds");
     198               0 :               return 0.0;
     199                 :           }
     200           17056 :           return poLS->getZ( i );
     201                 :       }
     202                 : 
     203                 :       default:
     204               0 :           CPLError(CE_Failure, CPLE_NotSupported, "Incompatible geometry for operation");
     205               0 :           return 0.0;
     206                 :     }
     207                 : }
     208                 : 
     209                 : /************************************************************************/
     210                 : /*                          OGR_G_GetPoints()                           */
     211                 : /************************************************************************/
     212                 : 
     213                 : /**
     214                 :  * \brief Returns all points of line string.
     215                 :  *
     216                 :  * This method copies all points into user arrays. The user provides the
     217                 :  * stride between 2 consecutives elements of the array.
     218                 :  *
     219                 :  * On some CPU architectures, care must be taken so that the arrays are properly aligned.
     220                 :  *
     221                 :  * @param hGeom handle to the geometry from which to get the coordinates.
     222                 :  * @param pabyX a buffer of at least (sizeof(double) * nXStride * nPointCount) bytes, may be NULL.
     223                 :  * @param nXStride the number of bytes between 2 elements of pabyX.
     224                 :  * @param pabyY a buffer of at least (sizeof(double) * nYStride * nPointCount) bytes, may be NULL.
     225                 :  * @param nYStride the number of bytes between 2 elements of pabyY.
     226                 :  * @param pabyZ a buffer of at last size (sizeof(double) * nZStride * nPointCount) bytes, may be NULL.
     227                 :  * @param nZStride the number of bytes between 2 elements of pabyZ.
     228                 :  *
     229                 :  * @return the number of points
     230                 :  *
     231                 :  * @since OGR 1.9.0
     232                 :  */
     233                 : 
     234              13 : int OGR_G_GetPoints( OGRGeometryH hGeom,
     235                 :                      void* pabyX, int nXStride,
     236                 :                      void* pabyY, int nYStride,
     237                 :                      void* pabyZ, int nZStride)
     238                 : {
     239              13 :     VALIDATE_POINTER1( hGeom, "OGR_G_GetPoints", 0 );
     240                 : 
     241              13 :     switch( wkbFlatten(((OGRGeometry *) hGeom)->getGeometryType()) )
     242                 :     {
     243                 :       case wkbPoint:
     244                 :       {
     245               4 :         if (pabyX) *((double*)pabyX) = ((OGRPoint *)hGeom)->getX();
     246               4 :         if (pabyY) *((double*)pabyY) = ((OGRPoint *)hGeom)->getY();
     247               4 :         if (pabyZ) *((double*)pabyZ) = ((OGRPoint *)hGeom)->getZ();
     248               4 :         return 1;
     249                 :       }
     250                 :       break;
     251                 : 
     252                 :       case wkbLineString:
     253                 :       {
     254               9 :           OGRLineString* poLS = (OGRLineString *) hGeom;
     255               9 :           poLS->getPoints(pabyX, nXStride, pabyY, nYStride, pabyZ, nZStride);
     256               9 :           return poLS->getNumPoints();
     257                 :       }
     258                 :       break;
     259                 : 
     260                 :       default:
     261               0 :         CPLError(CE_Failure, CPLE_NotSupported, "Incompatible geometry for operation");
     262               0 :         return 0;
     263                 :         break;
     264                 :     }
     265                 : }
     266                 : 
     267                 : 
     268                 : /************************************************************************/
     269                 : /*                           OGR_G_GetPoint()                           */
     270                 : /************************************************************************/
     271                 : 
     272                 : /**
     273                 :  * \brief Fetch a point in line string or a point geometry.
     274                 :  *
     275                 :  * @param hGeom handle to the geometry from which to get the coordinates.
     276                 :  * @param i the vertex to fetch, from 0 to getNumPoints()-1, zero for a point.
     277                 :  * @param pdfX value of x coordinate.
     278                 :  * @param pdfY value of y coordinate.
     279                 :  * @param pdfZ value of z coordinate.
     280                 :  */
     281                 : 
     282               6 : void OGR_G_GetPoint( OGRGeometryH hGeom, int i, 
     283                 :                      double *pdfX, double *pdfY, double *pdfZ )
     284                 : 
     285                 : {
     286               6 :     VALIDATE_POINTER0( hGeom, "OGR_G_GetPoint" );
     287                 : 
     288               6 :     switch( wkbFlatten(((OGRGeometry *) hGeom)->getGeometryType()) )
     289                 :     {
     290                 :       case wkbPoint:
     291                 :       {
     292               2 :           if( i == 0 )
     293                 :           {
     294               2 :               *pdfX = ((OGRPoint *)hGeom)->getX();
     295               2 :               *pdfY = ((OGRPoint *)hGeom)->getY();
     296               2 :               if( pdfZ != NULL )
     297               2 :                   *pdfZ = ((OGRPoint *)hGeom)->getZ();
     298                 :           }
     299                 :           else
     300                 :           {
     301               0 :               CPLError(CE_Failure, CPLE_NotSupported, "Only i == 0 is supported");
     302                 :           }
     303                 :       }
     304               2 :       break;
     305                 : 
     306                 :       case wkbLineString:
     307                 :       {
     308               4 :           OGRLineString* poLS = (OGRLineString *) hGeom;
     309               4 :           if (i < 0 || i >= poLS->getNumPoints())
     310                 :           {
     311               4 :               CPLError(CE_Failure, CPLE_NotSupported, "Index out of bounds");
     312               4 :               *pdfX = *pdfY = 0;
     313               4 :               if( pdfZ != NULL )
     314               2 :                   *pdfZ = 0;
     315                 :           }
     316                 :           else
     317                 :           {
     318               0 :             *pdfX = poLS->getX( i );
     319               0 :             *pdfY = poLS->getY( i );
     320               0 :             if( pdfZ != NULL )
     321               0 :                 *pdfZ =  poLS->getZ( i );
     322                 :           }
     323                 :       }
     324               4 :       break;
     325                 : 
     326                 :       default:
     327               0 :         CPLError(CE_Failure, CPLE_NotSupported, "Incompatible geometry for operation");
     328                 :         break;
     329                 :     }
     330                 : }
     331                 : 
     332                 : /************************************************************************/
     333                 : /*                           OGR_G_SetPoint()                           */
     334                 : /************************************************************************/
     335                 : /**
     336                 :  * \brief Set the location of a vertex in a point or linestring geometry.
     337                 :  *
     338                 :  * If iPoint is larger than the number of existing
     339                 :  * points in the linestring, the point count will be increased to
     340                 :  * accomodate the request.
     341                 :  *
     342                 :  * @param hGeom handle to the geometry to add a vertex to.
     343                 :  * @param i the index of the vertex to assign (zero based) or
     344                 :  *  zero for a point.
     345                 :  * @param dfX input X coordinate to assign.
     346                 :  * @param dfY input Y coordinate to assign.
     347                 :  * @param dfZ input Z coordinate to assign (defaults to zero).
     348                 :  */
     349                 : 
     350           21765 : void OGR_G_SetPoint( OGRGeometryH hGeom, int i, 
     351                 :                      double dfX, double dfY, double dfZ )
     352                 : 
     353                 : {
     354           21765 :     VALIDATE_POINTER0( hGeom, "OGR_G_SetPoint" );
     355                 : 
     356           21765 :     switch( wkbFlatten(((OGRGeometry *) hGeom)->getGeometryType()) )
     357                 :     {
     358                 :       case wkbPoint:
     359                 :       {
     360               4 :           if( i == 0 )
     361                 :           {
     362               4 :               ((OGRPoint *) hGeom)->setX( dfX );
     363               4 :               ((OGRPoint *) hGeom)->setY( dfY );
     364               4 :               ((OGRPoint *) hGeom)->setZ( dfZ );
     365                 :           }
     366                 :           else
     367                 :           {
     368               0 :               CPLError(CE_Failure, CPLE_NotSupported, "Only i == 0 is supported");
     369                 :           }
     370                 :       }
     371               4 :       break;
     372                 : 
     373                 :       case wkbLineString:
     374                 :       {
     375           21761 :           if (i < 0)
     376                 :           {
     377               1 :               CPLError(CE_Failure, CPLE_NotSupported, "Index out of bounds");
     378               1 :               return;
     379                 :           }
     380           21760 :           ((OGRLineString *) hGeom)->setPoint( i, dfX, dfY, dfZ );
     381           21760 :           break;
     382                 :       }
     383                 : 
     384                 :       default:
     385               0 :         CPLError(CE_Failure, CPLE_NotSupported, "Incompatible geometry for operation");
     386                 :         break;
     387                 :     }
     388                 : }
     389                 : 
     390                 : /************************************************************************/
     391                 : /*                         OGR_G_SetPoint_2D()                          */
     392                 : /************************************************************************/
     393                 : /**
     394                 :  * \brief Set the location of a vertex in a point or linestring geometry.
     395                 :  *
     396                 :  * If iPoint is larger than the number of existing
     397                 :  * points in the linestring, the point count will be increased to
     398                 :  * accomodate the request.
     399                 :  *
     400                 :  * @param hGeom handle to the geometry to add a vertex to.
     401                 :  * @param i the index of the vertex to assign (zero based) or
     402                 :  *  zero for a point.
     403                 :  * @param dfX input X coordinate to assign.
     404                 :  * @param dfY input Y coordinate to assign.
     405                 :  */
     406                 : 
     407            1262 : void OGR_G_SetPoint_2D( OGRGeometryH hGeom, int i, 
     408                 :                         double dfX, double dfY )
     409                 :     
     410                 : {
     411            1262 :     VALIDATE_POINTER0( hGeom, "OGR_G_SetPoint_2D" );
     412                 : 
     413            1262 :     switch( wkbFlatten(((OGRGeometry *) hGeom)->getGeometryType()) )
     414                 :     {
     415                 :       case wkbPoint:
     416                 :       {
     417               0 :           if( i == 0 )
     418                 :           {
     419               0 :               ((OGRPoint *) hGeom)->setX( dfX );
     420               0 :               ((OGRPoint *) hGeom)->setY( dfY );
     421                 :           }
     422                 :           else
     423                 :           {
     424               0 :               CPLError(CE_Failure, CPLE_NotSupported, "Only i == 0 is supported");
     425                 :           }
     426                 :       }
     427               0 :       break;
     428                 : 
     429                 :       case wkbLineString:
     430                 :       {
     431            1262 :           if (i < 0)
     432                 :           {
     433               1 :               CPLError(CE_Failure, CPLE_NotSupported, "Index out of bounds");
     434               1 :               return;
     435                 :           }
     436            1261 :           ((OGRLineString *) hGeom)->setPoint( i, dfX, dfY );
     437            1261 :           break;
     438                 :       }
     439                 : 
     440                 :       default:
     441               0 :         CPLError(CE_Failure, CPLE_NotSupported, "Incompatible geometry for operation");
     442                 :         break;
     443                 :     }
     444                 : }
     445                 : 
     446                 : /************************************************************************/
     447                 : /*                           OGR_G_AddPoint()                           */
     448                 : /************************************************************************/
     449                 : /**
     450                 :  * \brief Add a point to a geometry (line string or point).
     451                 :  *
     452                 :  * The vertex count of the line string is increased by one, and assigned from
     453                 :  * the passed location value.
     454                 :  *
     455                 :  * @param hGeom handle to the geometry to add a point to.
     456                 :  * @param dfX x coordinate of point to add.
     457                 :  * @param dfY y coordinate of point to add.
     458                 :  * @param dfZ z coordinate of point to add.
     459                 :  */
     460                 : 
     461              10 : void OGR_G_AddPoint( OGRGeometryH hGeom, 
     462                 :                      double dfX, double dfY, double dfZ )
     463                 : 
     464                 : {
     465              10 :     VALIDATE_POINTER0( hGeom, "OGR_G_AddPoint" );
     466                 : 
     467              10 :     switch( wkbFlatten(((OGRGeometry *) hGeom)->getGeometryType()) )
     468                 :     {
     469                 :       case wkbPoint:
     470                 :       {
     471               0 :           ((OGRPoint *) hGeom)->setX( dfX );
     472               0 :           ((OGRPoint *) hGeom)->setY( dfY );
     473               0 :           ((OGRPoint *) hGeom)->setZ( dfZ );
     474                 :       }
     475               0 :       break;
     476                 : 
     477                 :       case wkbLineString:
     478              10 :         ((OGRLineString *) hGeom)->addPoint( dfX, dfY, dfZ );
     479              10 :         break;
     480                 : 
     481                 :       default:
     482               0 :         CPLError(CE_Failure, CPLE_NotSupported, "Incompatible geometry for operation");
     483                 :         break;
     484                 :     }
     485                 : }
     486                 : 
     487                 : /************************************************************************/
     488                 : /*                           OGR_G_AddPoint()                           */
     489                 : /************************************************************************/
     490                 : /**
     491                 :  * \brief Add a point to a geometry (line string or point).
     492                 :  *
     493                 :  * The vertex count of the line string is increased by one, and assigned from
     494                 :  * the passed location value.
     495                 :  *
     496                 :  * @param hGeom handle to the geometry to add a point to.
     497                 :  * @param dfX x coordinate of point to add.
     498                 :  * @param dfY y coordinate of point to add.
     499                 :  */
     500                 : 
     501             245 : void OGR_G_AddPoint_2D( OGRGeometryH hGeom, 
     502                 :                         double dfX, double dfY )
     503                 : 
     504                 : {
     505             245 :     VALIDATE_POINTER0( hGeom, "OGR_G_AddPoint_2D" );
     506                 : 
     507             245 :     switch( wkbFlatten(((OGRGeometry *) hGeom)->getGeometryType()) )
     508                 :     {
     509                 :       case wkbPoint:
     510                 :       {
     511              10 :           ((OGRPoint *) hGeom)->setX( dfX );
     512              10 :           ((OGRPoint *) hGeom)->setY( dfY );
     513                 :       }
     514              10 :       break;
     515                 : 
     516                 :       case wkbLineString:
     517             235 :         ((OGRLineString *) hGeom)->addPoint( dfX, dfY );
     518             235 :         break;
     519                 : 
     520                 :       default:
     521               0 :         CPLError(CE_Failure, CPLE_NotSupported, "Incompatible geometry for operation");
     522                 :         break;
     523                 :     }
     524                 : }
     525                 : 
     526                 : /************************************************************************/
     527                 : /*                       OGR_G_GetGeometryCount()                       */
     528                 : /************************************************************************/
     529                 : /**
     530                 :  * \brief Fetch the number of elements in a geometry or number of geometries in container.
     531                 :  *
     532                 :  * Only geometries of type wkbPolygon[25D], wkbMultiPoint[25D], wkbMultiLineString[25D],
     533                 :  * wkbMultiPolygon[25D] or wkbGeometryCollection[25D] may return a valid value.
     534                 :  * Other geometry types will silently return 0.
     535                 :  *
     536                 :  * For a polygon, the returned number is the number of rings (exterior ring + interior rings).
     537                 :  *
     538                 :  * @param hGeom single geometry or geometry container from which to get
     539                 :  * the number of elements.
     540                 :  * @return the number of elements.
     541                 :  */
     542                 : 
     543            4939 : int OGR_G_GetGeometryCount( OGRGeometryH hGeom )
     544                 : 
     545                 : {
     546            4939 :     VALIDATE_POINTER1( hGeom, "OGR_G_GetGeometryCount", 0 );
     547                 : 
     548            4939 :     switch( wkbFlatten(((OGRGeometry *) hGeom)->getGeometryType()) )
     549                 :     {
     550                 :       case wkbPolygon:
     551            1486 :         if( ((OGRPolygon *)hGeom)->getExteriorRing() == NULL )
     552               6 :             return 0;
     553                 :         else
     554            1480 :             return ((OGRPolygon *)hGeom)->getNumInteriorRings() + 1;
     555                 : 
     556                 :       case wkbMultiPoint:
     557                 :       case wkbMultiLineString:
     558                 :       case wkbMultiPolygon:
     559                 :       case wkbGeometryCollection:
     560             597 :         return ((OGRGeometryCollection *)hGeom)->getNumGeometries();
     561                 : 
     562                 :       default:
     563                 :         // autotest/pymod/ogrtest.py calls this method on any geometry. So keep silent
     564                 :         //CPLError(CE_Failure, CPLE_NotSupported, "Incompatible geometry for operation");
     565            2856 :         return 0;
     566                 :     }
     567                 : }
     568                 : 
     569                 : /************************************************************************/
     570                 : /*                        OGR_G_GetGeometryRef()                        */
     571                 : /************************************************************************/
     572                 : 
     573                 : /**
     574                 :  * \brief Fetch geometry from a geometry container.
     575                 :  *
     576                 :  * This function returns an handle to a geometry within the container.
     577                 :  * The returned geometry remains owned by the container, and should not be
     578                 :  * modified.  The handle is only valid untill the next change to the
     579                 :  * geometry container.  Use OGR_G_Clone() to make a copy.
     580                 :  *
     581                 :  * This function relates to the SFCOM 
     582                 :  * IGeometryCollection::get_Geometry() method.
     583                 :  *
     584                 :  * This function is the same as the CPP method 
     585                 :  * OGRGeometryCollection::getGeometryRef().
     586                 :  *
     587                 :  * For a polygon, OGR_G_GetGeometryRef(iSubGeom) returns the exterior ring
     588                 :  * if iSubGeom == 0, and the interior rings for iSubGeom > 0.
     589                 :  *
     590                 :  * @param hGeom handle to the geometry container from which to get a 
     591                 :  * geometry from.
     592                 :  * @param iSubGeom the index of the geometry to fetch, between 0 and
     593                 :  *          getNumGeometries() - 1.
     594                 :  * @return handle to the requested geometry.
     595                 :  */
     596                 : 
     597            1592 : OGRGeometryH OGR_G_GetGeometryRef( OGRGeometryH hGeom, int iSubGeom )
     598                 : 
     599                 : {
     600            1592 :     VALIDATE_POINTER1( hGeom, "OGR_G_GetGeometryRef", NULL );
     601                 : 
     602            1592 :     switch( wkbFlatten(((OGRGeometry *) hGeom)->getGeometryType()) )
     603                 :     {
     604                 :       case wkbPolygon:
     605             888 :         if( iSubGeom == 0 )
     606                 :             return (OGRGeometryH) 
     607             752 :                 ((OGRPolygon *)hGeom)->getExteriorRing();
     608                 :         else
     609                 :             return (OGRGeometryH) 
     610             136 :                 ((OGRPolygon *)hGeom)->getInteriorRing(iSubGeom-1);
     611                 : 
     612                 :       case wkbMultiPoint:
     613                 :       case wkbMultiLineString:
     614                 :       case wkbMultiPolygon:
     615                 :       case wkbGeometryCollection:
     616                 :         return (OGRGeometryH) 
     617             704 :             ((OGRGeometryCollection *)hGeom)->getGeometryRef( iSubGeom );
     618                 : 
     619                 :       default:
     620               0 :         CPLError(CE_Failure, CPLE_NotSupported, "Incompatible geometry for operation");
     621               0 :         return 0;
     622                 :     }
     623                 : }
     624                 : 
     625                 : /************************************************************************/
     626                 : /*                         OGR_G_AddGeometry()                          */
     627                 : /************************************************************************/
     628                 : 
     629                 : /**
     630                 :  * \brief Add a geometry to a geometry container.
     631                 :  *
     632                 :  * Some subclasses of OGRGeometryCollection restrict the types of geometry
     633                 :  * that can be added, and may return an error.  The passed geometry is cloned
     634                 :  * to make an internal copy.
     635                 :  *
     636                 :  * There is no SFCOM analog to this method.
     637                 :  *
     638                 :  * This function is the same as the CPP method 
     639                 :  * OGRGeometryCollection::addGeometry.
     640                 :  *
     641                 :  * For a polygon, hNewSubGeom must be a linearring. If the polygon is empty,
     642                 :  * the first added subgeometry will be the exterior ring. The next ones will be
     643                 :  * the interior rings.
     644                 :  *
     645                 :  * @param hGeom existing geometry container.
     646                 :  * @param hNewSubGeom geometry to add to the container.
     647                 :  *
     648                 :  * @return OGRERR_NONE if successful, or OGRERR_UNSUPPORTED_GEOMETRY_TYPE if
     649                 :  * the geometry type is illegal for the type of existing geometry.
     650                 :  */
     651                 : 
     652              52 : OGRErr OGR_G_AddGeometry( OGRGeometryH hGeom, OGRGeometryH hNewSubGeom )
     653                 : 
     654                 : {
     655              52 :     VALIDATE_POINTER1( hGeom, "OGR_G_AddGeometry", OGRERR_UNSUPPORTED_OPERATION );
     656              52 :     VALIDATE_POINTER1( hNewSubGeom, "OGR_G_AddGeometry", OGRERR_UNSUPPORTED_OPERATION );
     657                 : 
     658              52 :     switch( wkbFlatten(((OGRGeometry *) hGeom)->getGeometryType()) )
     659                 :     {
     660                 :       case wkbPolygon:
     661                 :       {
     662              12 :           if( !EQUAL( ((OGRGeometry*) hNewSubGeom)->getGeometryName(), "LINEARRING" ) )
     663                 :           {
     664               0 :               return OGRERR_UNSUPPORTED_GEOMETRY_TYPE;
     665                 :           }
     666                 :           else
     667                 :           {
     668              12 :               ((OGRPolygon *)hGeom)->addRing( (OGRLinearRing *) hNewSubGeom );
     669              12 :               return OGRERR_NONE;
     670                 :           }
     671                 :       }
     672                 : 
     673                 :       case wkbMultiPoint:
     674                 :       case wkbMultiLineString:
     675                 :       case wkbMultiPolygon:
     676                 :       case wkbGeometryCollection:
     677                 :         return ((OGRGeometryCollection *)hGeom)->addGeometry( 
     678              40 :             (OGRGeometry *) hNewSubGeom );
     679                 : 
     680                 :       default:
     681               0 :         return OGRERR_UNSUPPORTED_OPERATION;
     682                 :     }
     683                 : }
     684                 : 
     685                 : /************************************************************************/
     686                 : /*                     OGR_G_AddGeometryDirectly()                      */
     687                 : /************************************************************************/
     688                 : /**
     689                 :  * \brief Add a geometry directly to an existing geometry container.
     690                 :  *
     691                 :  * Some subclasses of OGRGeometryCollection restrict the types of geometry
     692                 :  * that can be added, and may return an error.  Ownership of the passed
     693                 :  * geometry is taken by the container rather than cloning as addGeometry()
     694                 :  * does.
     695                 :  *
     696                 :  * This function is the same as the CPP method 
     697                 :  * OGRGeometryCollection::addGeometryDirectly.
     698                 :  *
     699                 :  * There is no SFCOM analog to this method.
     700                 :  *
     701                 :  * For a polygon, hNewSubGeom must be a linearring. If the polygon is empty,
     702                 :  * the first added subgeometry will be the exterior ring. The next ones will be
     703                 :  * the interior rings.
     704                 :  *
     705                 :  * @param hGeom existing geometry.
     706                 :  * @param hNewSubGeom geometry to add to the existing geometry.
     707                 :  *
     708                 :  * @return OGRERR_NONE if successful, or OGRERR_UNSUPPORTED_GEOMETRY_TYPE if
     709                 :  * the geometry type is illegal for the type of geometry container.
     710                 :  */
     711                 : 
     712             276 : OGRErr OGR_G_AddGeometryDirectly( OGRGeometryH hGeom, 
     713                 :                                   OGRGeometryH hNewSubGeom )
     714                 : 
     715                 : {
     716             276 :     VALIDATE_POINTER1( hGeom, "OGR_G_AddGeometryDirectly", OGRERR_UNSUPPORTED_OPERATION );
     717             276 :     VALIDATE_POINTER1( hNewSubGeom, "OGR_G_AddGeometryDirectly", OGRERR_UNSUPPORTED_OPERATION );
     718                 : 
     719             276 :     switch( wkbFlatten(((OGRGeometry *) hGeom)->getGeometryType()) )
     720                 :     {
     721                 :       case wkbPolygon:
     722                 :       {
     723             259 :           if( !EQUAL( ((OGRGeometry*) hNewSubGeom)->getGeometryName(), "LINEARRING" ) )
     724                 :           {
     725               0 :               return OGRERR_UNSUPPORTED_GEOMETRY_TYPE;
     726                 :           }
     727                 :           else
     728                 :           {
     729             259 :               ((OGRPolygon *)hGeom)->addRingDirectly( (OGRLinearRing *) hNewSubGeom );
     730             259 :               return OGRERR_NONE;
     731                 :           }
     732                 :       }
     733                 : 
     734                 :       case wkbMultiPoint:
     735                 :       case wkbMultiLineString:
     736                 :       case wkbMultiPolygon:
     737                 :       case wkbGeometryCollection:
     738                 :         return ((OGRGeometryCollection *)hGeom)->addGeometryDirectly( 
     739              17 :             (OGRGeometry *) hNewSubGeom );
     740                 : 
     741                 :       default:
     742               0 :         return OGRERR_UNSUPPORTED_OPERATION;
     743                 :     }
     744                 : }
     745                 : 
     746                 : /************************************************************************/
     747                 : /*                        OGR_G_RemoveGeometry()                        */
     748                 : /************************************************************************/
     749                 : 
     750                 : /**
     751                 :  * \brief Remove a geometry from an exiting geometry container.
     752                 :  *
     753                 :  * Removing a geometry will cause the geometry count to drop by one, and all
     754                 :  * "higher" geometries will shuffle down one in index.
     755                 :  *
     756                 :  * There is no SFCOM analog to this method.
     757                 :  *
     758                 :  * This function is the same as the CPP method 
     759                 :  * OGRGeometryCollection::removeGeometry().
     760                 :  *
     761                 :  * @param hGeom the existing geometry to delete from.
     762                 :  * @param iGeom the index of the geometry to delete.  A value of -1 is a
     763                 :  * special flag meaning that all geometries should be removed.
     764                 :  *
     765                 :  * @param bDelete if TRUE the geometry will be destroyed, otherwise it will
     766                 :  * not.  The default is TRUE as the existing geometry is considered to own the
     767                 :  * geometries in it. 
     768                 :  *
     769                 :  * @return OGRERR_NONE if successful, or OGRERR_FAILURE if the index is
     770                 :  * out of range.
     771                 :  */
     772                 : 
     773                 : 
     774                 : 
     775               0 : OGRErr OGR_G_RemoveGeometry( OGRGeometryH hGeom, int iGeom, int bDelete )
     776                 : 
     777                 : {
     778               0 :     VALIDATE_POINTER1( hGeom, "OGR_G_RemoveGeometry", 0 );
     779                 : 
     780               0 :     switch( wkbFlatten(((OGRGeometry *) hGeom)->getGeometryType()) )
     781                 :     {
     782                 :       case wkbPolygon:
     783                 :       {
     784                 :           CPLError( CE_Failure, CPLE_AppDefined, 
     785               0 :                     "OGR_G_RemoveGeometry() not supported on polygons yet." );
     786               0 :           return OGRERR_UNSUPPORTED_OPERATION;
     787                 :       }
     788                 : 
     789                 :       case wkbMultiPoint:
     790                 :       case wkbMultiLineString:
     791                 :       case wkbMultiPolygon:
     792                 :       case wkbGeometryCollection:
     793               0 :         return ((OGRGeometryCollection *)hGeom)->removeGeometry( iGeom,bDelete);
     794                 : 
     795                 :       default:
     796               0 :         return OGRERR_UNSUPPORTED_OPERATION;
     797                 :     }
     798                 : }
     799                 : 
     800                 : /************************************************************************/
     801                 : /*                           OGR_G_Length()                             */
     802                 : /************************************************************************/
     803                 : 
     804                 : /**
     805                 :  * \brief Compute length of a geometry.
     806                 :  *
     807                 :  * Computes the area for OGRCurve or MultiCurve objects.
     808                 :  * Undefined for all other geometry types (returns zero). 
     809                 :  *
     810                 :  * This function utilizes the C++ get_Length() method.
     811                 :  *
     812                 :  * @param hGeom the geometry to operate on.
     813                 :  * @return the lenght or 0.0 for unsupported geometry types.
     814                 :  *
     815                 :  * @since OGR 1.8.0
     816                 :  */
     817                 : 
     818              12 : double OGR_G_Length( OGRGeometryH hGeom )
     819                 : 
     820                 : {
     821              12 :     VALIDATE_POINTER1( hGeom, "OGR_G_GetLength", 0 );
     822                 : 
     823              12 :     double fLength = 0.0;
     824                 : 
     825              12 :     switch( wkbFlatten(((OGRGeometry *) hGeom)->getGeometryType()) )
     826                 :     {
     827                 :       case wkbLinearRing:
     828                 :       case wkbLineString:
     829               6 :         fLength = ((OGRCurve *) hGeom)->get_Length();
     830               6 :         break;
     831                 : 
     832                 :       case wkbMultiLineString:
     833                 :       case wkbGeometryCollection:
     834               5 :         fLength = ((OGRGeometryCollection *) hGeom)->get_Length();
     835               5 :         break;
     836                 : 
     837                 :       default:
     838                 :         CPLError( CE_Warning, CPLE_AppDefined,
     839               1 :                   "OGR_G_Length() called against a non-curve geometry type." );
     840                 : 
     841               1 :         fLength = 0.0;
     842                 :     }
     843                 : 
     844              12 :     return fLength;
     845                 : }
     846                 : 
     847                 : /************************************************************************/
     848                 : /*                           OGR_G_Area()                               */
     849                 : /************************************************************************/
     850                 : 
     851                 : /**
     852                 :  * \brief Compute geometry area.
     853                 :  *
     854                 :  * Computes the area for an OGRLinearRing, OGRPolygon or OGRMultiPolygon.
     855                 :  * Undefined for all other geometry types (returns zero). 
     856                 :  *
     857                 :  * This function utilizes the C++ get_Area() methods such as
     858                 :  * OGRPolygon::get_Area(). 
     859                 :  *
     860                 :  * @param hGeom the geometry to operate on. 
     861                 :  * @return the area or 0.0 for unsupported geometry types.
     862                 :  *
     863                 :  * @since OGR 1.8.0
     864                 :  */
     865                 : 
     866              34 : double OGR_G_Area( OGRGeometryH hGeom )
     867                 : 
     868                 : {
     869              34 :     VALIDATE_POINTER1( hGeom, "OGR_G_Area", 0 );
     870                 : 
     871              34 :     double fArea = 0.0;
     872                 : 
     873              34 :     switch( wkbFlatten(((OGRGeometry *) hGeom)->getGeometryType()) )
     874                 :     {
     875                 :       case wkbPolygon:
     876              27 :         fArea = ((OGRPolygon *) hGeom)->get_Area();
     877              27 :         break;
     878                 : 
     879                 :       case wkbMultiPolygon:
     880               2 :         fArea = ((OGRMultiPolygon *) hGeom)->get_Area();
     881               2 :         break;
     882                 : 
     883                 :       case wkbLinearRing:
     884                 :       case wkbLineString:
     885                 :         /* This test below is required to filter out wkbLineString geometries
     886                 :          * not being of type of wkbLinearRing.
     887                 :          */
     888               3 :         if( EQUAL( ((OGRGeometry*) hGeom)->getGeometryName(), "LINEARRING" ) )
     889                 :         {
     890               3 :             fArea = ((OGRLinearRing *) hGeom)->get_Area();
     891                 :         }
     892               3 :         break;
     893                 : 
     894                 :       case wkbGeometryCollection:
     895               1 :         fArea = ((OGRGeometryCollection *) hGeom)->get_Area();
     896               1 :         break;
     897                 : 
     898                 :       default:
     899                 :         CPLError( CE_Warning, CPLE_AppDefined,
     900               1 :                   "OGR_G_Area() called against non-surface geometry type." );
     901                 : 
     902               1 :         fArea = 0.0;
     903                 :     }
     904                 : 
     905              34 :     return fArea;
     906                 : }
     907                 : 
     908                 : /**
     909                 :  * \brief Compute geometry area (deprecated)
     910                 :  *
     911                 :  * @deprecated
     912                 :  * @see OGR_G_Area()
     913                 :  */
     914              27 : double OGR_G_GetArea( OGRGeometryH hGeom )
     915                 : 
     916                 : {
     917              27 :     return OGR_G_Area( hGeom );
     918                 : }

Generated by: LCOV version 1.7