PostGIS  2.2.7dev-r@@SVN_REVISION@@
double lwgeom_area_spheroid ( const LWGEOM lwgeom,
const SPHEROID spheroid 
)

Calculate the geodetic area of a lwgeom on the spheroid.

The result will have the squared units of the spheroid axes.

Calculate the geodetic area of a lwgeom on the spheroid.

Anything except POLYGON, MULTIPOLYGON and GEOMETRYCOLLECTION return zero immediately. Multi's recurse, polygons calculate external ring area and subtract internal ring area. A GBOX is required to check relationship to equator an outside point. WARNING: Does NOT WORK for polygons over equator or pole.

Definition at line 628 of file lwspheroid.c.

References area(), COLLECTIONTYPE, LWCOLLECTION::geoms, lwgeom_is_empty(), MULTIPOLYGONTYPE, LWCOLLECTION::ngeoms, LWPOLY::nrings, POLYGONTYPE, ptarray_area_spheroid(), LWPOLY::rings, and LWGEOM::type.

Referenced by geography_area(), and test_spheroid_area().

629 {
630  int type;
631 
632  assert(lwgeom);
633 
634  /* No area in nothing */
635  if ( lwgeom_is_empty(lwgeom) )
636  return 0.0;
637 
638  /* Read the geometry type number */
639  type = lwgeom->type;
640 
641  /* Anything but polygons and collections returns zero */
642  if ( ! ( type == POLYGONTYPE || type == MULTIPOLYGONTYPE || type == COLLECTIONTYPE ) )
643  return 0.0;
644 
645  /* Actually calculate area */
646  if ( type == POLYGONTYPE )
647  {
648  LWPOLY *poly = (LWPOLY*)lwgeom;
649  int i;
650  double area = 0.0;
651 
652  /* Just in case there's no rings */
653  if ( poly->nrings < 1 )
654  return 0.0;
655 
656  /* First, the area of the outer ring */
657  area += ptarray_area_spheroid(poly->rings[0], spheroid);
658 
659  /* Subtract areas of inner rings */
660  for ( i = 1; i < poly->nrings; i++ )
661  {
662  area -= ptarray_area_spheroid(poly->rings[i], spheroid);
663  }
664  return area;
665  }
666 
667  /* Recurse into sub-geometries to get area */
668  if ( type == MULTIPOLYGONTYPE || type == COLLECTIONTYPE )
669  {
670  LWCOLLECTION *col = (LWCOLLECTION*)lwgeom;
671  int i;
672  double area = 0.0;
673 
674  for ( i = 0; i < col->ngeoms; i++ )
675  {
676  area += lwgeom_area_spheroid(col->geoms[i], spheroid);
677  }
678  return area;
679  }
680 
681  /* Shouldn't get here. */
682  return 0.0;
683 }
#define POLYGONTYPE
Definition: liblwgeom.h:72
Datum area(PG_FUNCTION_ARGS)
LWGEOM ** geoms
Definition: liblwgeom.h:493
POINTARRAY ** rings
Definition: liblwgeom.h:441
double lwgeom_area_spheroid(const LWGEOM *lwgeom, const SPHEROID *spheroid)
Calculate the area of an LWGEOM.
Definition: lwspheroid.c:628
int nrings
Definition: liblwgeom.h:439
static double ptarray_area_spheroid(const POINTARRAY *pa, const SPHEROID *spheroid)
Definition: lwspheroid.c:480
#define MULTIPOLYGONTYPE
Definition: liblwgeom.h:75
uint8_t type
Definition: liblwgeom.h:380
int lwgeom_is_empty(const LWGEOM *geom)
Return true or false depending on whether a geometry is an "empty" geometry (no vertices members) ...
Definition: lwgeom.c:1297
#define COLLECTIONTYPE
Definition: liblwgeom.h:76

Here is the call graph for this function:

Here is the caller graph for this function: