示例#1
0
GAIAGEO_DECLARE void
gaiaScaleCoords (gaiaGeomCollPtr geom, double scale_x, double scale_y)
{
/* returns a geometry that is the old geometry with required scaling applied to coordinates */
    int ib;
    int iv;
    double x;
    double y;
    double z;
    double m;
    gaiaPointPtr point;
    gaiaPolygonPtr polyg;
    gaiaLinestringPtr line;
    gaiaRingPtr ring;
    if (!geom)
	return;
    point = geom->FirstPoint;
    while (point)
      {
	  /* scaling POINTs */
	  point->X *= scale_x;
	  point->Y *= scale_y;
	  point = point->Next;
      }
    line = geom->FirstLinestring;
    while (line)
      {
	  /* scaling LINESTRINGs */
	  for (iv = 0; iv < line->Points; iv++)
	    {
		if (line->DimensionModel == GAIA_XY_Z)
		  {
		      gaiaGetPointXYZ (line->Coords, iv, &x, &y, &z);
		  }
		else if (line->DimensionModel == GAIA_XY_M)
		  {
		      gaiaGetPointXYM (line->Coords, iv, &x, &y, &m);
		  }
		else if (line->DimensionModel == GAIA_XY_Z_M)
		  {
		      gaiaGetPointXYZM (line->Coords, iv, &x, &y, &z, &m);
		  }
		else
		  {
		      gaiaGetPoint (line->Coords, iv, &x, &y);
		  }
		x *= scale_x;
		y *= scale_y;
		if (line->DimensionModel == GAIA_XY_Z)
		  {
		      gaiaSetPointXYZ (line->Coords, iv, x, y, z);
		  }
		else if (line->DimensionModel == GAIA_XY_M)
		  {
		      gaiaSetPointXYM (line->Coords, iv, x, y, m);
		  }
		else if (line->DimensionModel == GAIA_XY_Z_M)
		  {
		      gaiaSetPointXYZM (line->Coords, iv, x, y, z, m);
		  }
		else
		  {
		      gaiaSetPoint (line->Coords, iv, x, y);
		  }
	    }
	  line = line->Next;
      }
    polyg = geom->FirstPolygon;
    while (polyg)
      {
	  /* scaling POLYGONs */
	  ring = polyg->Exterior;
	  for (iv = 0; iv < ring->Points; iv++)
	    {
		/* scaling the EXTERIOR RING */
		if (ring->DimensionModel == GAIA_XY_Z)
		  {
		      gaiaGetPointXYZ (ring->Coords, iv, &x, &y, &z);
		  }
		else if (ring->DimensionModel == GAIA_XY_M)
		  {
		      gaiaGetPointXYM (ring->Coords, iv, &x, &y, &m);
		  }
		else if (ring->DimensionModel == GAIA_XY_Z_M)
		  {
		      gaiaGetPointXYZM (ring->Coords, iv, &x, &y, &z, &m);
		  }
		else
		  {
		      gaiaGetPoint (ring->Coords, iv, &x, &y);
		  }
		x *= scale_x;
		y *= scale_y;
		if (ring->DimensionModel == GAIA_XY_Z)
		  {
		      gaiaSetPointXYZ (ring->Coords, iv, x, y, z);
		  }
		else if (ring->DimensionModel == GAIA_XY_M)
		  {
		      gaiaSetPointXYM (ring->Coords, iv, x, y, m);
		  }
		else if (ring->DimensionModel == GAIA_XY_Z_M)
		  {
		      gaiaSetPointXYZM (ring->Coords, iv, x, y, z, m);
		  }
		else
		  {
		      gaiaSetPoint (ring->Coords, iv, x, y);
		  }
	    }
	  for (ib = 0; ib < polyg->NumInteriors; ib++)
	    {
		/* scaling the INTERIOR RINGs */
		ring = polyg->Interiors + ib;
		for (iv = 0; iv < ring->Points; iv++)
		  {
		      if (ring->DimensionModel == GAIA_XY_Z)
			{
			    gaiaGetPointXYZ (ring->Coords, iv, &x, &y, &z);
			}
		      else if (ring->DimensionModel == GAIA_XY_M)
			{
			    gaiaGetPointXYM (ring->Coords, iv, &x, &y, &m);
			}
		      else if (ring->DimensionModel == GAIA_XY_Z_M)
			{
			    gaiaGetPointXYZM (ring->Coords, iv, &x, &y, &z, &m);
			}
		      else
			{
			    gaiaGetPoint (ring->Coords, iv, &x, &y);
			}
		      x *= scale_x;
		      y *= scale_y;
		      if (ring->DimensionModel == GAIA_XY_Z)
			{
			    gaiaSetPointXYZ (ring->Coords, iv, x, y, z);
			}
		      else if (ring->DimensionModel == GAIA_XY_M)
			{
			    gaiaSetPointXYM (ring->Coords, iv, x, y, m);
			}
		      else if (ring->DimensionModel == GAIA_XY_Z_M)
			{
			    gaiaSetPointXYZM (ring->Coords, iv, x, y, z, m);
			}
		      else
			{
			    gaiaSetPoint (ring->Coords, iv, x, y);
			}
		  }
	    }
	  polyg = polyg->Next;
      }
    gaiaMbrGeometry (geom);
}
示例#2
0
GAIAGEO_DECLARE void
gaiaShiftLongitude (gaiaGeomCollPtr geom)
{
/* returns a geometry that is the old geometry with negative longitudes shift by 360 */
    int ib;
    int iv;
    double x;
    double y;
    double z;
    double m;
    gaiaPointPtr point;
    gaiaPolygonPtr polyg;
    gaiaLinestringPtr line;
    gaiaRingPtr ring;
    if (!geom)
	return;
    point = geom->FirstPoint;
    while (point)
      {
	  /* shifting POINTs */
	  if (point->X < 0)
	    {
		point->X += 360.0;
	    }
	  point = point->Next;
      }
    line = geom->FirstLinestring;
    while (line)
      {
	  /* shifting LINESTRINGs */
	  for (iv = 0; iv < line->Points; iv++)
	    {
		if (line->DimensionModel == GAIA_XY_Z)
		  {
		      gaiaGetPointXYZ (line->Coords, iv, &x, &y, &z);
		  }
		else if (line->DimensionModel == GAIA_XY_M)
		  {
		      gaiaGetPointXYM (line->Coords, iv, &x, &y, &m);
		  }
		else if (line->DimensionModel == GAIA_XY_Z_M)
		  {
		      gaiaGetPointXYZM (line->Coords, iv, &x, &y, &z, &m);
		  }
		else
		  {
		      gaiaGetPoint (line->Coords, iv, &x, &y);
		  }
		if (x < 0)
		  {
		      x += 360.0;
		  }
		if (line->DimensionModel == GAIA_XY_Z)
		  {
		      gaiaSetPointXYZ (line->Coords, iv, x, y, z);
		  }
		else if (line->DimensionModel == GAIA_XY_M)
		  {
		      gaiaSetPointXYM (line->Coords, iv, x, y, m);
		  }
		else if (line->DimensionModel == GAIA_XY_Z_M)
		  {
		      gaiaSetPointXYZM (line->Coords, iv, x, y, z, m);
		  }
		else
		  {
		      gaiaSetPoint (line->Coords, iv, x, y);
		  }
	    }
	  line = line->Next;
      }
    polyg = geom->FirstPolygon;
    while (polyg)
      {
	  /* shifting POLYGONs */
	  ring = polyg->Exterior;
	  for (iv = 0; iv < ring->Points; iv++)
	    {
		/* shifting the EXTERIOR RING */
		if (ring->DimensionModel == GAIA_XY_Z)
		  {
		      gaiaGetPointXYZ (ring->Coords, iv, &x, &y, &z);
		  }
		else if (ring->DimensionModel == GAIA_XY_M)
		  {
		      gaiaGetPointXYM (ring->Coords, iv, &x, &y, &m);
		  }
		else if (ring->DimensionModel == GAIA_XY_Z_M)
		  {
		      gaiaGetPointXYZM (ring->Coords, iv, &x, &y, &z, &m);
		  }
		else
		  {
		      gaiaGetPoint (ring->Coords, iv, &x, &y);
		  }
		if (x < 0)
		  {
		      x += 360.0;
		  }
		if (ring->DimensionModel == GAIA_XY_Z)
		  {
		      gaiaSetPointXYZ (ring->Coords, iv, x, y, z);
		  }
		else if (ring->DimensionModel == GAIA_XY_M)
		  {
		      gaiaSetPointXYM (ring->Coords, iv, x, y, m);
		  }
		else if (ring->DimensionModel == GAIA_XY_Z_M)
		  {
		      gaiaSetPointXYZM (ring->Coords, iv, x, y, z, m);
		  }
		else
		  {
		      gaiaSetPoint (ring->Coords, iv, x, y);
		  }
	    }
	  for (ib = 0; ib < polyg->NumInteriors; ib++)
	    {
		/* shifting the INTERIOR RINGs */
		ring = polyg->Interiors + ib;
		for (iv = 0; iv < ring->Points; iv++)
		  {
		      if (ring->DimensionModel == GAIA_XY_Z)
			{
			    gaiaGetPointXYZ (ring->Coords, iv, &x, &y, &z);
			}
		      else if (ring->DimensionModel == GAIA_XY_M)
			{
			    gaiaGetPointXYM (ring->Coords, iv, &x, &y, &m);
			}
		      else if (ring->DimensionModel == GAIA_XY_Z_M)
			{
			    gaiaGetPointXYZM (ring->Coords, iv, &x, &y, &z, &m);
			}
		      else
			{
			    gaiaGetPoint (ring->Coords, iv, &x, &y);
			}
		      if (x < 0)
			{
			    x += 360.0;
			}
		      if (ring->DimensionModel == GAIA_XY_Z)
			{
			    gaiaSetPointXYZ (ring->Coords, iv, x, y, z);
			}
		      else if (ring->DimensionModel == GAIA_XY_M)
			{
			    gaiaSetPointXYM (ring->Coords, iv, x, y, m);
			}
		      else if (ring->DimensionModel == GAIA_XY_Z_M)
			{
			    gaiaSetPointXYZM (ring->Coords, iv, x, y, z, m);
			}
		      else
			{
			    gaiaSetPoint (ring->Coords, iv, x, y);
			}
		  }
	    }
	  polyg = polyg->Next;
      }
    gaiaMbrGeometry (geom);
}
示例#3
0
GAIAGEO_DECLARE void
gaiaNormalizeLonLat (gaiaGeomCollPtr geom)
{
/* returns a geometry that is the old geometry with all latitudes shifted
 into the range -90 to 90, and all longitudes shifted into the range -180 to
 180.
*/
    int ib;
    int iv;
    double x;
    double y;
    double z;
    double m;
    gaiaPointPtr point;
    gaiaPolygonPtr polyg;
    gaiaLinestringPtr line;
    gaiaRingPtr ring;
    if (!geom)
	return;
    point = geom->FirstPoint;
    while (point)
      {
	  normalizePoint (&(point->X), &(point->Y));
	  point = point->Next;
      }
    line = geom->FirstLinestring;
    while (line)
      {
	  /* shifting LINESTRINGs */
	  for (iv = 0; iv < line->Points; iv++)
	    {
		if (line->DimensionModel == GAIA_XY_Z)
		  {
		      gaiaGetPointXYZ (line->Coords, iv, &x, &y, &z);
		  }
		else if (line->DimensionModel == GAIA_XY_M)
		  {
		      gaiaGetPointXYM (line->Coords, iv, &x, &y, &m);
		  }
		else if (line->DimensionModel == GAIA_XY_Z_M)
		  {
		      gaiaGetPointXYZM (line->Coords, iv, &x, &y, &z, &m);
		  }
		else
		  {
		      gaiaGetPoint (line->Coords, iv, &x, &y);
		  }
		normalizePoint (&x, &y);
		if (line->DimensionModel == GAIA_XY_Z)
		  {
		      gaiaSetPointXYZ (line->Coords, iv, x, y, z);
		  }
		else if (line->DimensionModel == GAIA_XY_M)
		  {
		      gaiaSetPointXYM (line->Coords, iv, x, y, m);
		  }
		else if (line->DimensionModel == GAIA_XY_Z_M)
		  {
		      gaiaSetPointXYZM (line->Coords, iv, x, y, z, m);
		  }
		else
		  {
		      gaiaSetPoint (line->Coords, iv, x, y);
		  }
	    }
	  line = line->Next;
      }
    polyg = geom->FirstPolygon;
    while (polyg)
      {
	  /* shifting POLYGONs */
	  ring = polyg->Exterior;
	  for (iv = 0; iv < ring->Points; iv++)
	    {
		/* shifting the EXTERIOR RING */
		if (ring->DimensionModel == GAIA_XY_Z)
		  {
		      gaiaGetPointXYZ (ring->Coords, iv, &x, &y, &z);
		  }
		else if (ring->DimensionModel == GAIA_XY_M)
		  {
		      gaiaGetPointXYM (ring->Coords, iv, &x, &y, &m);
		  }
		else if (ring->DimensionModel == GAIA_XY_Z_M)
		  {
		      gaiaGetPointXYZM (ring->Coords, iv, &x, &y, &z, &m);
		  }
		else
		  {
		      gaiaGetPoint (ring->Coords, iv, &x, &y);
		  }
		normalizePoint (&x, &y);
		if (ring->DimensionModel == GAIA_XY_Z)
		  {
		      gaiaSetPointXYZ (ring->Coords, iv, x, y, z);
		  }
		else if (ring->DimensionModel == GAIA_XY_M)
		  {
		      gaiaSetPointXYM (ring->Coords, iv, x, y, m);
		  }
		else if (ring->DimensionModel == GAIA_XY_Z_M)
		  {
		      gaiaSetPointXYZM (ring->Coords, iv, x, y, z, m);
		  }
		else
		  {
		      gaiaSetPoint (ring->Coords, iv, x, y);
		  }
	    }
	  for (ib = 0; ib < polyg->NumInteriors; ib++)
	    {
		/* shifting the INTERIOR RINGs */
		ring = polyg->Interiors + ib;
		for (iv = 0; iv < ring->Points; iv++)
		  {
		      if (ring->DimensionModel == GAIA_XY_Z)
			{
			    gaiaGetPointXYZ (ring->Coords, iv, &x, &y, &z);
			}
		      else if (ring->DimensionModel == GAIA_XY_M)
			{
			    gaiaGetPointXYM (ring->Coords, iv, &x, &y, &m);
			}
		      else if (ring->DimensionModel == GAIA_XY_Z_M)
			{
			    gaiaGetPointXYZM (ring->Coords, iv, &x, &y, &z, &m);
			}
		      else
			{
			    gaiaGetPoint (ring->Coords, iv, &x, &y);
			}
		      normalizePoint (&x, &y);
		      if (ring->DimensionModel == GAIA_XY_Z)
			{
			    gaiaSetPointXYZ (ring->Coords, iv, x, y, z);
			}
		      else if (ring->DimensionModel == GAIA_XY_M)
			{
			    gaiaSetPointXYM (ring->Coords, iv, x, y, m);
			}
		      else if (ring->DimensionModel == GAIA_XY_Z_M)
			{
			    gaiaSetPointXYZM (ring->Coords, iv, x, y, z, m);
			}
		      else
			{
			    gaiaSetPoint (ring->Coords, iv, x, y);
			}
		  }
	    }
	  polyg = polyg->Next;
      }
    gaiaMbrGeometry (geom);
}
示例#4
0
GAIAGEO_DECLARE void
gaiaSwapCoords (gaiaGeomCollPtr geom)
{
/* returns a geometry that is the old geometry with swapped x- and y-coordinates */
    int ib;
    int iv;
    double x;
    double y;
    double z;
    double m;
    double sv;
    gaiaPointPtr point;
    gaiaPolygonPtr polyg;
    gaiaLinestringPtr line;
    gaiaRingPtr ring;
    if (!geom)
	return;
    point = geom->FirstPoint;
    while (point)
      {
	  /* swapping POINTs */
	  sv = point->X;
	  point->X = point->Y;
	  point->Y = sv;
	  point = point->Next;
      }
    line = geom->FirstLinestring;
    while (line)
      {
	  /* swapping LINESTRINGs */
	  for (iv = 0; iv < line->Points; iv++)
	    {
		if (line->DimensionModel == GAIA_XY_Z)
		  {
		      gaiaGetPointXYZ (line->Coords, iv, &x, &y, &z);
		  }
		else if (line->DimensionModel == GAIA_XY_M)
		  {
		      gaiaGetPointXYM (line->Coords, iv, &x, &y, &m);
		  }
		else if (line->DimensionModel == GAIA_XY_Z_M)
		  {
		      gaiaGetPointXYZM (line->Coords, iv, &x, &y, &z, &m);
		  }
		else
		  {
		      gaiaGetPoint (line->Coords, iv, &x, &y);
		  }
		sv = x;
		x = y;
		y = sv;
		if (line->DimensionModel == GAIA_XY_Z)
		  {
		      gaiaSetPointXYZ (line->Coords, iv, x, y, z);
		  }
		else if (line->DimensionModel == GAIA_XY_M)
		  {
		      gaiaSetPointXYM (line->Coords, iv, x, y, m);
		  }
		else if (line->DimensionModel == GAIA_XY_Z_M)
		  {
		      gaiaSetPointXYZM (line->Coords, iv, x, y, z, m);
		  }
		else
		  {
		      gaiaSetPoint (line->Coords, iv, x, y);
		  }
	    }
	  line = line->Next;
      }
    polyg = geom->FirstPolygon;
    while (polyg)
      {
	  /* swapping POLYGONs */
	  ring = polyg->Exterior;
	  for (iv = 0; iv < ring->Points; iv++)
	    {
		/* shifting the EXTERIOR RING */
		if (ring->DimensionModel == GAIA_XY_Z)
		  {
		      gaiaGetPointXYZ (ring->Coords, iv, &x, &y, &z);
		  }
		else if (ring->DimensionModel == GAIA_XY_M)
		  {
		      gaiaGetPointXYM (ring->Coords, iv, &x, &y, &m);
		  }
		else if (ring->DimensionModel == GAIA_XY_Z_M)
		  {
		      gaiaGetPointXYZM (ring->Coords, iv, &x, &y, &z, &m);
		  }
		else
		  {
		      gaiaGetPoint (ring->Coords, iv, &x, &y);
		  }
		sv = x;
		x = y;
		y = sv;
		if (ring->DimensionModel == GAIA_XY_Z)
		  {
		      gaiaSetPointXYZ (ring->Coords, iv, x, y, z);
		  }
		else if (ring->DimensionModel == GAIA_XY_M)
		  {
		      gaiaSetPointXYM (ring->Coords, iv, x, y, m);
		  }
		else if (ring->DimensionModel == GAIA_XY_Z_M)
		  {
		      gaiaSetPointXYZM (ring->Coords, iv, x, y, z, m);
		  }
		else
		  {
		      gaiaSetPoint (ring->Coords, iv, x, y);
		  }
	    }
	  for (ib = 0; ib < polyg->NumInteriors; ib++)
	    {
		/* swapping the INTERIOR RINGs */
		ring = polyg->Interiors + ib;
		for (iv = 0; iv < ring->Points; iv++)
		  {
		      if (ring->DimensionModel == GAIA_XY_Z)
			{
			    gaiaGetPointXYZ (ring->Coords, iv, &x, &y, &z);
			}
		      else if (ring->DimensionModel == GAIA_XY_M)
			{
			    gaiaGetPointXYM (ring->Coords, iv, &x, &y, &m);
			}
		      else if (ring->DimensionModel == GAIA_XY_Z_M)
			{
			    gaiaGetPointXYZM (ring->Coords, iv, &x, &y, &z, &m);
			}
		      else
			{
			    gaiaGetPoint (ring->Coords, iv, &x, &y);
			}
		      sv = x;
		      x = y;
		      y = sv;
		      if (ring->DimensionModel == GAIA_XY_Z)
			{
			    gaiaSetPointXYZ (ring->Coords, iv, x, y, z);
			}
		      else if (ring->DimensionModel == GAIA_XY_M)
			{
			    gaiaSetPointXYM (ring->Coords, iv, x, y, m);
			}
		      else if (ring->DimensionModel == GAIA_XY_Z_M)
			{
			    gaiaSetPointXYZM (ring->Coords, iv, x, y, z, m);
			}
		      else
			{
			    gaiaSetPoint (ring->Coords, iv, x, y);
			}
		  }
	    }
	  polyg = polyg->Next;
      }
    gaiaMbrGeometry (geom);
}
示例#5
0
static gaiaGeomCollPtr
gaiaTransformCommon (projCtx handle, gaiaGeomCollPtr org, char *proj_from,
		     char *proj_to)
{
/* creates a new GEOMETRY reprojecting coordinates from the original one */
    int ib;
    int cnt;
    int i;
    double *xx;
    double *yy;
    double *zz;
    double *mm = NULL;
    double x;
    double y;
    double z = 0.0;
    double m = 0.0;
    int error = 0;
    int from_angle;
    int to_angle;
    gaiaPointPtr pt;
    gaiaLinestringPtr ln;
    gaiaLinestringPtr dst_ln;
    gaiaPolygonPtr pg;
    gaiaPolygonPtr dst_pg;
    gaiaRingPtr rng;
    gaiaRingPtr dst_rng;
    projPJ from_cs;
    projPJ to_cs;
    gaiaGeomCollPtr dst;
    if (handle != NULL)
      {
	  from_cs = pj_init_plus_ctx (handle, proj_from);
	  to_cs = pj_init_plus_ctx (handle, proj_to);
      }
    else
      {
	  from_cs = pj_init_plus (proj_from);
	  to_cs = pj_init_plus (proj_to);
      }
    if (!from_cs)
      {
	  if (to_cs)
	      pj_free (to_cs);
	  return NULL;
      }
    if (!to_cs)
      {
	  pj_free (from_cs);
	  return NULL;
      }
    if (org->DimensionModel == GAIA_XY_Z)
	dst = gaiaAllocGeomCollXYZ ();
    else if (org->DimensionModel == GAIA_XY_M)
	dst = gaiaAllocGeomCollXYM ();
    else if (org->DimensionModel == GAIA_XY_Z_M)
	dst = gaiaAllocGeomCollXYZM ();
    else
	dst = gaiaAllocGeomColl ();
/* setting up projection parameters */
    from_angle = gaiaIsLongLat (proj_from);
    to_angle = gaiaIsLongLat (proj_to);
    cnt = 0;
    pt = org->FirstPoint;
    while (pt)
      {
	  /* counting POINTs */
	  cnt++;
	  pt = pt->Next;
      }
    if (cnt)
      {
	  /* reprojecting POINTs */
	  xx = malloc (sizeof (double) * cnt);
	  yy = malloc (sizeof (double) * cnt);
	  zz = malloc (sizeof (double) * cnt);
	  if (org->DimensionModel == GAIA_XY_M
	      || org->DimensionModel == GAIA_XY_Z_M)
	      mm = malloc (sizeof (double) * cnt);
	  i = 0;
	  pt = org->FirstPoint;
	  while (pt)
	    {
		/* inserting points to be converted in temporary arrays */
		if (from_angle)
		  {
		      xx[i] = gaiaDegsToRads (pt->X);
		      yy[i] = gaiaDegsToRads (pt->Y);
		  }
		else
		  {
		      xx[i] = pt->X;
		      yy[i] = pt->Y;
		  }
		if (org->DimensionModel == GAIA_XY_Z
		    || org->DimensionModel == GAIA_XY_Z_M)
		    zz[i] = pt->Z;
		else
		    zz[i] = 0.0;
		if (org->DimensionModel == GAIA_XY_M
		    || org->DimensionModel == GAIA_XY_Z_M)
		    mm[i] = pt->M;
		i++;
		pt = pt->Next;
	    }
	  /* applying reprojection        */
	  if (pj_transform (from_cs, to_cs, cnt, 0, xx, yy, zz) == 0)
	    {
		/* inserting the reprojected POINTs in the new GEOMETRY */
		for (i = 0; i < cnt; i++)
		  {
		      if (to_angle)
			{
			    x = gaiaRadsToDegs (xx[i]);
			    y = gaiaRadsToDegs (yy[i]);
			}
		      else
			{
			    x = xx[i];
			    y = yy[i];
			}
		      if (org->DimensionModel == GAIA_XY_Z
			  || org->DimensionModel == GAIA_XY_Z_M)
			  z = zz[i];
		      else
			  z = 0.0;
		      if (org->DimensionModel == GAIA_XY_M
			  || org->DimensionModel == GAIA_XY_Z_M)
			  m = mm[i];
		      else
			  m = 0.0;
		      if (dst->DimensionModel == GAIA_XY_Z)
			  gaiaAddPointToGeomCollXYZ (dst, x, y, z);
		      else if (dst->DimensionModel == GAIA_XY_M)
			  gaiaAddPointToGeomCollXYM (dst, x, y, m);
		      else if (dst->DimensionModel == GAIA_XY_Z_M)
			  gaiaAddPointToGeomCollXYZM (dst, x, y, z, m);
		      else
			  gaiaAddPointToGeomColl (dst, x, y);
		  }
	    }
	  else
	      error = 1;
	  free (xx);
	  free (yy);
	  free (zz);
	  if (org->DimensionModel == GAIA_XY_M
	      || org->DimensionModel == GAIA_XY_Z_M)
	      free (mm);
      }
    if (error)
	goto stop;
    ln = org->FirstLinestring;
    while (ln)
      {
	  /* reprojecting LINESTRINGs */
	  cnt = ln->Points;
	  xx = malloc (sizeof (double) * cnt);
	  yy = malloc (sizeof (double) * cnt);
	  zz = malloc (sizeof (double) * cnt);
	  if (ln->DimensionModel == GAIA_XY_M
	      || ln->DimensionModel == GAIA_XY_Z_M)
	      mm = malloc (sizeof (double) * cnt);
	  for (i = 0; i < cnt; i++)
	    {
		/* inserting points to be converted in temporary arrays */
		if (ln->DimensionModel == GAIA_XY_Z)
		  {
		      gaiaGetPointXYZ (ln->Coords, i, &x, &y, &z);
		  }
		else if (ln->DimensionModel == GAIA_XY_M)
		  {
		      gaiaGetPointXYM (ln->Coords, i, &x, &y, &m);
		  }
		else if (ln->DimensionModel == GAIA_XY_Z_M)
		  {
		      gaiaGetPointXYZM (ln->Coords, i, &x, &y, &z, &m);
		  }
		else
		  {
		      gaiaGetPoint (ln->Coords, i, &x, &y);
		  }
		if (from_angle)
		  {
		      xx[i] = gaiaDegsToRads (x);
		      yy[i] = gaiaDegsToRads (y);
		  }
		else
		  {
		      xx[i] = x;
		      yy[i] = y;
		  }
		if (ln->DimensionModel == GAIA_XY_Z
		    || ln->DimensionModel == GAIA_XY_Z_M)
		    zz[i] = z;
		else
		    zz[i] = 0.0;
		if (ln->DimensionModel == GAIA_XY_M
		    || ln->DimensionModel == GAIA_XY_Z_M)
		    mm[i] = m;
	    }
	  /* applying reprojection        */
	  if (pj_transform (from_cs, to_cs, cnt, 0, xx, yy, zz) == 0)
	    {
		/* inserting the reprojected LINESTRING in the new GEOMETRY */
		dst_ln = gaiaAddLinestringToGeomColl (dst, cnt);
		for (i = 0; i < cnt; i++)
		  {
		      /* setting LINESTRING points */
		      if (to_angle)
			{
			    x = gaiaRadsToDegs (xx[i]);
			    y = gaiaRadsToDegs (yy[i]);
			}
		      else
			{
			    x = xx[i];
			    y = yy[i];
			}
		      if (ln->DimensionModel == GAIA_XY_Z
			  || ln->DimensionModel == GAIA_XY_Z_M)
			  z = zz[i];
		      else
			  z = 0.0;
		      if (ln->DimensionModel == GAIA_XY_M
			  || ln->DimensionModel == GAIA_XY_Z_M)
			  m = mm[i];
		      else
			  m = 0.0;
		      if (dst_ln->DimensionModel == GAIA_XY_Z)
			{
			    gaiaSetPointXYZ (dst_ln->Coords, i, x, y, z);
			}
		      else if (dst_ln->DimensionModel == GAIA_XY_M)
			{
			    gaiaSetPointXYM (dst_ln->Coords, i, x, y, m);
			}
		      else if (dst_ln->DimensionModel == GAIA_XY_Z_M)
			{
			    gaiaSetPointXYZM (dst_ln->Coords, i, x, y, z, m);
			}
		      else
			{
			    gaiaSetPoint (dst_ln->Coords, i, x, y);
			}
		  }
	    }
	  else
	      error = 1;
	  free (xx);
	  free (yy);
	  free (zz);
	  if (ln->DimensionModel == GAIA_XY_M
	      || ln->DimensionModel == GAIA_XY_Z_M)
	      free (mm);
	  if (error)
	      goto stop;
	  ln = ln->Next;
      }
    pg = org->FirstPolygon;
    while (pg)
      {
	  /* reprojecting POLYGONs */
	  rng = pg->Exterior;
	  cnt = rng->Points;
	  dst_pg = gaiaAddPolygonToGeomColl (dst, cnt, pg->NumInteriors);
	  xx = malloc (sizeof (double) * cnt);
	  yy = malloc (sizeof (double) * cnt);
	  zz = malloc (sizeof (double) * cnt);
	  if (rng->DimensionModel == GAIA_XY_M
	      || rng->DimensionModel == GAIA_XY_Z_M)
	      mm = malloc (sizeof (double) * cnt);
	  for (i = 0; i < cnt; i++)
	    {
		/* inserting points to be converted in temporary arrays [EXTERIOR RING] */
		if (rng->DimensionModel == GAIA_XY_Z)
		  {
		      gaiaGetPointXYZ (rng->Coords, i, &x, &y, &z);
		  }
		else if (rng->DimensionModel == GAIA_XY_M)
		  {
		      gaiaGetPointXYM (rng->Coords, i, &x, &y, &m);
		  }
		else if (rng->DimensionModel == GAIA_XY_Z_M)
		  {
		      gaiaGetPointXYZM (rng->Coords, i, &x, &y, &z, &m);
		  }
		else
		  {
		      gaiaGetPoint (rng->Coords, i, &x, &y);
		  }
		if (from_angle)
		  {
		      xx[i] = gaiaDegsToRads (x);
		      yy[i] = gaiaDegsToRads (y);
		  }
		else
		  {
		      xx[i] = x;
		      yy[i] = y;
		  }
		if (rng->DimensionModel == GAIA_XY_Z
		    || rng->DimensionModel == GAIA_XY_Z_M)
		    zz[i] = z;
		else
		    zz[i] = 0.0;
		if (rng->DimensionModel == GAIA_XY_M
		    || rng->DimensionModel == GAIA_XY_Z_M)
		    mm[i] = m;
	    }
	  /* applying reprojection        */
	  if (pj_transform (from_cs, to_cs, cnt, 0, xx, yy, zz) == 0)
	    {
		/* inserting the reprojected POLYGON in the new GEOMETRY */
		dst_rng = dst_pg->Exterior;
		for (i = 0; i < cnt; i++)
		  {
		      /* setting EXTERIOR RING points */
		      if (to_angle)
			{
			    x = gaiaRadsToDegs (xx[i]);
			    y = gaiaRadsToDegs (yy[i]);
			}
		      else
			{
			    x = xx[i];
			    y = yy[i];
			}
		      if (rng->DimensionModel == GAIA_XY_Z
			  || rng->DimensionModel == GAIA_XY_Z_M)
			  z = zz[i];
		      else
			  z = 0.0;
		      if (rng->DimensionModel == GAIA_XY_M
			  || rng->DimensionModel == GAIA_XY_Z_M)
			  m = mm[i];
		      else
			  m = 0.0;
		      if (dst_rng->DimensionModel == GAIA_XY_Z)
			{
			    gaiaSetPointXYZ (dst_rng->Coords, i, x, y, z);
			}
		      else if (dst_rng->DimensionModel == GAIA_XY_M)
			{
			    gaiaSetPointXYM (dst_rng->Coords, i, x, y, m);
			}
		      else if (dst_rng->DimensionModel == GAIA_XY_Z_M)
			{
			    gaiaSetPointXYZM (dst_rng->Coords, i, x, y, z, m);
			}
		      else
			{
			    gaiaSetPoint (dst_rng->Coords, i, x, y);
			}
		  }
	    }
	  else
	      error = 1;
	  free (xx);
	  free (yy);
	  free (zz);
	  if (rng->DimensionModel == GAIA_XY_M
	      || rng->DimensionModel == GAIA_XY_Z_M)
	      free (mm);
	  if (error)
	      goto stop;
	  for (ib = 0; ib < pg->NumInteriors; ib++)
	    {
		/* processing INTERIOR RINGS */
		rng = pg->Interiors + ib;
		cnt = rng->Points;
		xx = malloc (sizeof (double) * cnt);
		yy = malloc (sizeof (double) * cnt);
		zz = malloc (sizeof (double) * cnt);
		if (rng->DimensionModel == GAIA_XY_M
		    || rng->DimensionModel == GAIA_XY_Z_M)
		    mm = malloc (sizeof (double) * cnt);
		for (i = 0; i < cnt; i++)
		  {
		      /* inserting points to be converted in temporary arrays [INTERIOR RING] */
		      if (rng->DimensionModel == GAIA_XY_Z)
			{
			    gaiaGetPointXYZ (rng->Coords, i, &x, &y, &z);
			}
		      else if (rng->DimensionModel == GAIA_XY_M)
			{
			    gaiaGetPointXYM (rng->Coords, i, &x, &y, &m);
			}
		      else if (rng->DimensionModel == GAIA_XY_Z_M)
			{
			    gaiaGetPointXYZM (rng->Coords, i, &x, &y, &z, &m);
			}
		      else
			{
			    gaiaGetPoint (rng->Coords, i, &x, &y);
			}
		      if (from_angle)
			{
			    xx[i] = gaiaDegsToRads (x);
			    yy[i] = gaiaDegsToRads (y);
			}
		      else
			{
			    xx[i] = x;
			    yy[i] = y;
			}
		      if (rng->DimensionModel == GAIA_XY_Z
			  || rng->DimensionModel == GAIA_XY_Z_M)
			  zz[i] = z;
		      else
			  zz[i] = 0.0;
		      if (rng->DimensionModel == GAIA_XY_M
			  || rng->DimensionModel == GAIA_XY_Z_M)
			  mm[i] = m;
		  }
		/* applying reprojection        */
		if (pj_transform (from_cs, to_cs, cnt, 0, xx, yy, zz) == 0)
		  {
		      /* inserting the reprojected POLYGON in the new GEOMETRY */
		      dst_rng = gaiaAddInteriorRing (dst_pg, ib, cnt);
		      for (i = 0; i < cnt; i++)
			{
			    /* setting INTERIOR RING points */
			    if (to_angle)
			      {
				  x = gaiaRadsToDegs (xx[i]);
				  y = gaiaRadsToDegs (yy[i]);
			      }
			    else
			      {
				  x = xx[i];
				  y = yy[i];
			      }
			    if (rng->DimensionModel == GAIA_XY_Z
				|| rng->DimensionModel == GAIA_XY_Z_M)
				z = zz[i];
			    else
				z = 0.0;
			    if (rng->DimensionModel == GAIA_XY_M
				|| rng->DimensionModel == GAIA_XY_Z_M)
				m = mm[i];
			    else
				m = 0.0;
			    if (dst_rng->DimensionModel == GAIA_XY_Z)
			      {
				  gaiaSetPointXYZ (dst_rng->Coords, i, x, y, z);
			      }
			    else if (dst_rng->DimensionModel == GAIA_XY_M)
			      {
				  gaiaSetPointXYM (dst_rng->Coords, i, x, y, m);
			      }
			    else if (dst_rng->DimensionModel == GAIA_XY_Z_M)
			      {
				  gaiaSetPointXYZM (dst_rng->Coords, i, x, y, z,
						    m);
			      }
			    else
			      {
				  gaiaSetPoint (dst_rng->Coords, i, x, y);
			      }
			}
		  }
		else
		    error = 1;
		free (xx);
		free (yy);
		free (zz);
		if (rng->DimensionModel == GAIA_XY_M
		    || rng->DimensionModel == GAIA_XY_Z_M)
		    free (mm);
		if (error)
		    goto stop;
	    }
	  pg = pg->Next;
      }
/* destroying the PROJ4 params */
  stop:
    pj_free (from_cs);
    pj_free (to_cs);
    if (error)
      {
	  /* some error occurred */
	  gaiaPointPtr pP;
	  gaiaPointPtr pPn;
	  gaiaLinestringPtr pL;
	  gaiaLinestringPtr pLn;
	  gaiaPolygonPtr pA;
	  gaiaPolygonPtr pAn;
	  pP = dst->FirstPoint;
	  while (pP != NULL)
	    {
		pPn = pP->Next;
		gaiaFreePoint (pP);
		pP = pPn;
	    }
	  pL = dst->FirstLinestring;
	  while (pL != NULL)
	    {
		pLn = pL->Next;
		gaiaFreeLinestring (pL);
		pL = pLn;
	    }
	  pA = dst->FirstPolygon;
	  while (pA != NULL)
	    {
		pAn = pA->Next;
		gaiaFreePolygon (pA);
		pA = pAn;
	    }
	  dst->FirstPoint = NULL;
	  dst->LastPoint = NULL;
	  dst->FirstLinestring = NULL;
	  dst->LastLinestring = NULL;
	  dst->FirstPolygon = NULL;
	  dst->LastPolygon = NULL;
      }
    if (dst)
      {
	  gaiaMbrGeometry (dst);
	  dst->DeclaredType = org->DeclaredType;
      }
    return dst;
}
示例#6
0
GAIAGEO_DECLARE gaiaGeomCollPtr
gaiaSanitize (gaiaGeomCollPtr geom)
{
/* 
/ sanitizes a GEOMETRYCOLLECTION:
/ - repeated vertices are omitted
/ - ring closure is enforced anyway  
*/
    int iv;
    int ib;
    double x = 0.0;
    double y = 0.0;
    double z = 0.0;
    double m = 0.0;
    double last_x = 0.0;
    double last_y = 0.0;
    double last_z = 0.0;
    int points;
    gaiaPointPtr point;
    gaiaLinestringPtr line;
    gaiaLinestringPtr new_line;
    gaiaPolygonPtr polyg;
    gaiaPolygonPtr new_polyg;
    gaiaGeomCollPtr new_geom;
    gaiaRingPtr i_ring;
    gaiaRingPtr o_ring;
    if (!geom)
	return NULL;
    if (geom->DimensionModel == GAIA_XY_Z)
	new_geom = gaiaAllocGeomCollXYZ ();
    else if (geom->DimensionModel == GAIA_XY_M)
	new_geom = gaiaAllocGeomCollXYM ();
    else if (geom->DimensionModel == GAIA_XY_Z_M)
	new_geom = gaiaAllocGeomCollXYZM ();
    else
	new_geom = gaiaAllocGeomColl ();
    new_geom->Srid = geom->Srid;
    new_geom->DeclaredType = geom->DeclaredType;
    point = geom->FirstPoint;
    while (point)
      {
	  /* copying POINTs */
	  gaiaAddPointToGeomCollXYZM (new_geom, point->X, point->Y, point->Z,
				      point->M);
	  point = point->Next;
      }
    line = geom->FirstLinestring;
    while (line)
      {
	  /* sanitizing LINESTRINGs */
	  points = 0;
	  for (iv = 0; iv < line->Points; iv++)
	    {
		/* PASS I - checking points */
		z = 0.0;
		m = 0.0;
		if (line->DimensionModel == GAIA_XY_Z)
		  {
		      gaiaGetPointXYZ (line->Coords, iv, &x, &y, &z);
		  }
		else if (line->DimensionModel == GAIA_XY_M)
		  {
		      gaiaGetPointXYM (line->Coords, iv, &x, &y, &m);
		  }
		else if (line->DimensionModel == GAIA_XY_Z_M)
		  {
		      gaiaGetPointXYZM (line->Coords, iv, &x, &y, &z, &m);
		  }
		else
		  {
		      gaiaGetPoint (line->Coords, iv, &x, &y);
		  }
		if (iv > 0)
		  {
		      if (last_x == x && last_y == y && last_z == z)
			  ;
		      else
			  points++;
		  }
		else
		    points++;
		last_x = x;
		last_y = y;
		last_z = z;
	    }
	  if (points < 2)
	    {
		/* illegal LINESTRING - copying the original one */
		new_line = gaiaAddLinestringToGeomColl (new_geom, line->Points);
		gaiaCopyLinestringCoords (new_line, line);
	    }
	  else
	    {
		/* valid LINESTRING - sanitizing */
		new_line = gaiaAddLinestringToGeomColl (new_geom, points);
		points = 0;
		for (iv = 0; iv < line->Points; iv++)
		  {
		      /* PASS II - inserting points */
		      z = 0.0;
		      m = 0.0;
		      if (line->DimensionModel == GAIA_XY_Z)
			{
			    gaiaGetPointXYZ (line->Coords, iv, &x, &y, &z);
			}
		      else if (line->DimensionModel == GAIA_XY_M)
			{
			    gaiaGetPointXYM (line->Coords, iv, &x, &y, &m);
			}
		      else if (line->DimensionModel == GAIA_XY_Z_M)
			{
			    gaiaGetPointXYZM (line->Coords, iv, &x, &y, &z, &m);
			}
		      else
			{
			    gaiaGetPoint (line->Coords, iv, &x, &y);
			}
		      if (iv > 0)
			{
			    if (last_x == x && last_y == y && last_z == z)
				;
			    else
			      {
				  if (new_line->DimensionModel == GAIA_XY_Z)
				    {
					gaiaSetPointXYZ (new_line->Coords,
							 points, x, y, z);
				    }
				  else if (new_line->DimensionModel ==
					   GAIA_XY_M)
				    {
					gaiaSetPointXYM (new_line->Coords,
							 points, x, y, m);
				    }
				  else if (new_line->DimensionModel ==
					   GAIA_XY_Z_M)
				    {
					gaiaSetPointXYZM (new_line->Coords,
							  points, x, y, z, m);
				    }
				  else
				    {
					gaiaSetPoint (new_line->Coords, points,
						      x, y);
				    }
				  points++;
			      }
			}
		      else
			{
			    if (new_line->DimensionModel == GAIA_XY_Z)
			      {
				  gaiaSetPointXYZ (new_line->Coords, points, x,
						   y, z);
			      }
			    else if (new_line->DimensionModel == GAIA_XY_M)
			      {
				  gaiaSetPointXYM (new_line->Coords, points, x,
						   y, m);
			      }
			    else if (new_line->DimensionModel == GAIA_XY_Z_M)
			      {
				  gaiaSetPointXYZM (new_line->Coords, points, x,
						    y, z, m);
			      }
			    else
			      {
				  gaiaSetPoint (new_line->Coords, points, x, y);
			      }
			    points++;
			}
		      last_x = x;
		      last_y = y;
		      last_z = z;
		  }
	    }
	  line = line->Next;
      }
    polyg = geom->FirstPolygon;
    while (polyg)
      {
	  /* copying POLYGONs */
	  i_ring = polyg->Exterior;
	  /* sanitizing EXTERIOR RING */
	  points = 0;
	  for (iv = 0; iv < i_ring->Points; iv++)
	    {
		/* PASS I - checking points */
		z = 0.0;
		m = 0.0;
		if (i_ring->DimensionModel == GAIA_XY_Z)
		  {
		      gaiaGetPointXYZ (i_ring->Coords, iv, &x, &y, &z);
		  }
		else if (i_ring->DimensionModel == GAIA_XY_M)
		  {
		      gaiaGetPointXYM (i_ring->Coords, iv, &x, &y, &m);
		  }
		else if (i_ring->DimensionModel == GAIA_XY_Z_M)
		  {
		      gaiaGetPointXYZM (i_ring->Coords, iv, &x, &y, &z, &m);
		  }
		else
		  {
		      gaiaGetPoint (i_ring->Coords, iv, &x, &y);
		  }
		if (iv > 0)
		  {
		      if (last_x == x && last_y == y && last_z == z)
			  ;
		      else
			  points++;
		  }
		else
		    points++;
		last_x = x;
		last_y = y;
		last_z = z;
	    }
	  if (last_x == x && last_y == y && last_z == z)
	      ;
	  else
	    {
		/* forcing RING closure */
		points++;
	    }
	  if (points < 4)
	    {
		/* illegal RING - copying the original one */
		new_polyg =
		    gaiaAddPolygonToGeomColl (new_geom, i_ring->Points,
					      polyg->NumInteriors);
		o_ring = new_polyg->Exterior;
		gaiaCopyRingCoords (o_ring, i_ring);
	    }
	  else
	    {
		/* valid RING - sanitizing */
		new_polyg =
		    gaiaAddPolygonToGeomColl (new_geom, points,
					      polyg->NumInteriors);
		o_ring = new_polyg->Exterior;
		points = 0;
		for (iv = 0; iv < i_ring->Points; iv++)
		  {
		      /* PASS II - inserting points */
		      z = 0.0;
		      m = 0.0;
		      if (i_ring->DimensionModel == GAIA_XY_Z)
			{
			    gaiaGetPointXYZ (i_ring->Coords, iv, &x, &y, &z);
			}
		      else if (i_ring->DimensionModel == GAIA_XY_M)
			{
			    gaiaGetPointXYM (i_ring->Coords, iv, &x, &y, &m);
			}
		      else if (i_ring->DimensionModel == GAIA_XY_Z_M)
			{
			    gaiaGetPointXYZM (i_ring->Coords, iv, &x, &y, &z,
					      &m);
			}
		      else
			{
			    gaiaGetPoint (i_ring->Coords, iv, &x, &y);
			}
		      if (iv > 0)
			{
			    if (last_x == x && last_y == y && last_z == z)
				;
			    else
			      {
				  if (o_ring->DimensionModel == GAIA_XY_Z)
				    {
					gaiaSetPointXYZ (o_ring->Coords, points,
							 x, y, z);
				    }
				  else if (o_ring->DimensionModel == GAIA_XY_M)
				    {
					gaiaSetPointXYM (o_ring->Coords, points,
							 x, y, m);
				    }
				  else if (o_ring->DimensionModel ==
					   GAIA_XY_Z_M)
				    {
					gaiaSetPointXYZM (o_ring->Coords,
							  points, x, y, z, m);
				    }
				  else
				    {
					gaiaSetPoint (o_ring->Coords, points, x,
						      y);
				    }
				  points++;
			      }
			}
		      else
			{
			    if (o_ring->DimensionModel == GAIA_XY_Z)
			      {
				  gaiaSetPointXYZ (o_ring->Coords, points, x,
						   y, z);
			      }
			    else if (o_ring->DimensionModel == GAIA_XY_M)
			      {
				  gaiaSetPointXYM (o_ring->Coords, points, x,
						   y, m);
			      }
			    else if (o_ring->DimensionModel == GAIA_XY_Z_M)
			      {
				  gaiaSetPointXYZM (o_ring->Coords, points, x,
						    y, z, m);
			      }
			    else
			      {
				  gaiaSetPoint (o_ring->Coords, points, x, y);
			      }
			    points++;
			}
		      last_x = x;
		      last_y = y;
		      last_z = z;
		  }
	    }
	  /* PASS III - forcing RING closure */
	  z = 0.0;
	  m = 0.0;
	  if (i_ring->DimensionModel == GAIA_XY_Z)
	    {
		gaiaGetPointXYZ (i_ring->Coords, 0, &x, &y, &z);
	    }
	  else if (i_ring->DimensionModel == GAIA_XY_M)
	    {
		gaiaGetPointXYM (i_ring->Coords, 0, &x, &y, &m);
	    }
	  else if (i_ring->DimensionModel == GAIA_XY_Z_M)
	    {
		gaiaGetPointXYZM (i_ring->Coords, 0, &x, &y, &z, &m);
	    }
	  else
	    {
		gaiaGetPoint (i_ring->Coords, 0, &x, &y);
	    }
	  points = o_ring->Points - 1;
	  if (o_ring->DimensionModel == GAIA_XY_Z)
	    {
		gaiaSetPointXYZ (o_ring->Coords, points, x, y, z);
	    }
	  else if (o_ring->DimensionModel == GAIA_XY_M)
	    {
		gaiaSetPointXYM (o_ring->Coords, points, x, y, m);
	    }
	  else if (o_ring->DimensionModel == GAIA_XY_Z_M)
	    {
		gaiaSetPointXYZM (o_ring->Coords, points, x, y, z, m);
	    }
	  else
	    {
		gaiaSetPoint (o_ring->Coords, points, x, y);
	    }
	  for (ib = 0; ib < new_polyg->NumInteriors; ib++)
	    {
		/* copying each INTERIOR RING [if any] */
		i_ring = polyg->Interiors + ib;
		/* sanitizing an INTERIOR RING */
		points = 0;
		for (iv = 0; iv < i_ring->Points; iv++)
		  {
		      /* PASS I - checking points */
		      z = 0.0;
		      m = 0.0;
		      if (i_ring->DimensionModel == GAIA_XY_Z)
			{
			    gaiaGetPointXYZ (i_ring->Coords, iv, &x, &y, &z);
			}
		      else if (i_ring->DimensionModel == GAIA_XY_M)
			{
			    gaiaGetPointXYM (i_ring->Coords, iv, &x, &y, &m);
			}
		      else if (i_ring->DimensionModel == GAIA_XY_Z_M)
			{
			    gaiaGetPointXYZM (i_ring->Coords, iv, &x, &y, &z,
					      &m);
			}
		      else
			{
			    gaiaGetPoint (i_ring->Coords, iv, &x, &y);
			}
		      if (iv > 0)
			{
			    if (last_x == x && last_y == y && last_z == z)
				;
			    else
				points++;
			}
		      else
			  points++;
		      last_x = x;
		      last_y = y;
		      last_z = z;
		  }
		if (last_x == x && last_y == y && last_z == z)
		    ;
		else
		  {
		      /* forcing RING closure */
		      points++;
		  }
		if (points < 4)
		  {
		      /* illegal RING - copying the original one */
		      o_ring =
			  gaiaAddInteriorRing (new_polyg, ib, i_ring->Points);
		      gaiaCopyRingCoords (o_ring, i_ring);
		  }
		else
		  {
		      /* valid RING - sanitizing */
		      o_ring = gaiaAddInteriorRing (new_polyg, ib, points);
		      points = 0;
		      for (iv = 0; iv < i_ring->Points; iv++)
			{
			    /* PASS II - inserting points */
			    z = 0.0;
			    m = 0.0;
			    if (i_ring->DimensionModel == GAIA_XY_Z)
			      {
				  gaiaGetPointXYZ (i_ring->Coords, iv, &x, &y,
						   &z);
			      }
			    else if (i_ring->DimensionModel == GAIA_XY_M)
			      {
				  gaiaGetPointXYM (i_ring->Coords, iv, &x, &y,
						   &m);
			      }
			    else if (i_ring->DimensionModel == GAIA_XY_Z_M)
			      {
				  gaiaGetPointXYZM (i_ring->Coords, iv, &x, &y,
						    &z, &m);
			      }
			    else
			      {
				  gaiaGetPoint (i_ring->Coords, iv, &x, &y);
			      }
			    if (iv > 0)
			      {
				  if (last_x == x && last_y == y && last_z == z)
				      ;
				  else
				    {
					if (o_ring->DimensionModel == GAIA_XY_Z)
					  {
					      gaiaSetPointXYZ (o_ring->Coords,
							       points, x, y, z);
					  }
					else if (o_ring->DimensionModel ==
						 GAIA_XY_M)
					  {
					      gaiaSetPointXYM (o_ring->Coords,
							       points, x, y, m);
					  }
					else if (o_ring->DimensionModel ==
						 GAIA_XY_Z_M)
					  {
					      gaiaSetPointXYZM (o_ring->Coords,
								points, x, y, z,
								m);
					  }
					else
					  {
					      gaiaSetPoint (o_ring->Coords,
							    points, x, y);
					  }
					points++;
				    }
			      }
			    else
			      {
				  if (o_ring->DimensionModel == GAIA_XY_Z)
				    {
					gaiaSetPointXYZ (o_ring->Coords, points,
							 x, y, z);
				    }
				  else if (o_ring->DimensionModel == GAIA_XY_M)
				    {
					gaiaSetPointXYM (o_ring->Coords, points,
							 x, y, m);
				    }
				  else if (o_ring->DimensionModel ==
					   GAIA_XY_Z_M)
				    {
					gaiaSetPointXYZM (o_ring->Coords,
							  points, x, y, z, m);
				    }
				  else
				    {
					gaiaSetPoint (o_ring->Coords, points, x,
						      y);
				    }
				  points++;
			      }
			    last_x = x;
			    last_y = y;
			    last_z = z;
			}
		      /* PASS III - forcing RING closure */
		      z = 0.0;
		      m = 0.0;
		      if (i_ring->DimensionModel == GAIA_XY_Z)
			{
			    gaiaGetPointXYZ (i_ring->Coords, 0, &x, &y, &z);
			}
		      else if (i_ring->DimensionModel == GAIA_XY_M)
			{
			    gaiaGetPointXYM (i_ring->Coords, 0, &x, &y, &m);
			}
		      else if (i_ring->DimensionModel == GAIA_XY_Z_M)
			{
			    gaiaGetPointXYZM (i_ring->Coords, 0, &x, &y, &z,
					      &m);
			}
		      else
			{
			    gaiaGetPoint (i_ring->Coords, 0, &x, &y);
			}
		      points = o_ring->Points - 1;
		      if (o_ring->DimensionModel == GAIA_XY_Z)
			{
			    gaiaSetPointXYZ (o_ring->Coords, points, x, y, z);
			}
		      else if (o_ring->DimensionModel == GAIA_XY_M)
			{
			    gaiaSetPointXYM (o_ring->Coords, points, x, y, m);
			}
		      else if (o_ring->DimensionModel == GAIA_XY_Z_M)
			{
			    gaiaSetPointXYZM (o_ring->Coords, points, x, y, z,
					      m);
			}
		      else
			{
			    gaiaSetPoint (o_ring->Coords, points, x, y);
			}
		  }
	    }
	  polyg = polyg->Next;
      }
    return new_geom;
}
示例#7
0
GAIAGEO_DECLARE void
gaiaRotateCoords (gaiaGeomCollPtr geom, double angle)
{
/* returns a geometry that is the old geometry with required rotation applied to coordinates */
    int ib;
    int iv;
    double x;
    double y;
    double z;
    double m;
    double nx;
    double ny;
    double rad = angle * 0.0174532925199432958;
    double cosine = cos (rad);
    double sine = sin (rad);
    gaiaPointPtr point;
    gaiaPolygonPtr polyg;
    gaiaLinestringPtr line;
    gaiaRingPtr ring;
    if (!geom)
	return;
    point = geom->FirstPoint;
    while (point)
      {
	  /* shifting POINTs */
	  x = point->X;
	  y = point->Y;
	  point->X = (x * cosine) + (y * sine);
	  point->Y = (y * cosine) - (x * sine);
	  point = point->Next;
      }
    line = geom->FirstLinestring;
    while (line)
      {
	  /* rotating LINESTRINGs */
	  for (iv = 0; iv < line->Points; iv++)
	    {
		if (line->DimensionModel == GAIA_XY_Z)
		  {
		      gaiaGetPointXYZ (line->Coords, iv, &x, &y, &z);
		  }
		else if (line->DimensionModel == GAIA_XY_M)
		  {
		      gaiaGetPointXYM (line->Coords, iv, &x, &y, &m);
		  }
		else if (line->DimensionModel == GAIA_XY_Z_M)
		  {
		      gaiaGetPointXYZM (line->Coords, iv, &x, &y, &z, &m);
		  }
		else
		  {
		      gaiaGetPoint (line->Coords, iv, &x, &y);
		  }
		nx = (x * cosine) + (y * sine);
		ny = (y * cosine) - (x * sine);
		if (line->DimensionModel == GAIA_XY_Z)
		  {
		      gaiaSetPointXYZ (line->Coords, iv, nx, ny, z);
		  }
		else if (line->DimensionModel == GAIA_XY_M)
		  {
		      gaiaSetPointXYM (line->Coords, iv, nx, ny, m);
		  }
		else if (line->DimensionModel == GAIA_XY_Z_M)
		  {
		      gaiaSetPointXYZM (line->Coords, iv, nx, ny, z, m);
		  }
		else
		  {
		      gaiaSetPoint (line->Coords, iv, nx, ny);
		  }
	    }
	  line = line->Next;
      }
    polyg = geom->FirstPolygon;
    while (polyg)
      {
	  /* rotating POLYGONs */
	  ring = polyg->Exterior;
	  for (iv = 0; iv < ring->Points; iv++)
	    {
		/* rotating the EXTERIOR RING */
		if (ring->DimensionModel == GAIA_XY_Z)
		  {
		      gaiaGetPointXYZ (ring->Coords, iv, &x, &y, &z);
		  }
		else if (ring->DimensionModel == GAIA_XY_M)
		  {
		      gaiaGetPointXYM (ring->Coords, iv, &x, &y, &m);
		  }
		else if (ring->DimensionModel == GAIA_XY_Z_M)
		  {
		      gaiaGetPointXYZM (ring->Coords, iv, &x, &y, &z, &m);
		  }
		else
		  {
		      gaiaGetPoint (ring->Coords, iv, &x, &y);
		  }
		nx = (x * cosine) + (y * sine);
		ny = (y * cosine) - (x * sine);
		if (ring->DimensionModel == GAIA_XY_Z)
		  {
		      gaiaSetPointXYZ (ring->Coords, iv, nx, ny, z);
		  }
		else if (ring->DimensionModel == GAIA_XY_M)
		  {
		      gaiaSetPointXYM (ring->Coords, iv, nx, ny, m);
		  }
		else if (ring->DimensionModel == GAIA_XY_Z_M)
		  {
		      gaiaSetPointXYZM (ring->Coords, iv, nx, ny, z, m);
		  }
		else
		  {
		      gaiaSetPoint (ring->Coords, iv, nx, ny);
		  }
	    }
	  for (ib = 0; ib < polyg->NumInteriors; ib++)
	    {
		/* rotating the INTERIOR RINGs */
		ring = polyg->Interiors + ib;
		for (iv = 0; iv < ring->Points; iv++)
		  {
		      if (ring->DimensionModel == GAIA_XY_Z)
			{
			    gaiaGetPointXYZ (ring->Coords, iv, &x, &y, &z);
			}
		      else if (ring->DimensionModel == GAIA_XY_M)
			{
			    gaiaGetPointXYM (ring->Coords, iv, &x, &y, &m);
			}
		      else if (ring->DimensionModel == GAIA_XY_Z_M)
			{
			    gaiaGetPointXYZM (ring->Coords, iv, &x, &y, &z, &m);
			}
		      else
			{
			    gaiaGetPoint (ring->Coords, iv, &x, &y);
			}
		      nx = (x * cosine) + (y * sine);
		      ny = (y * cosine) - (x * sine);
		      if (ring->DimensionModel == GAIA_XY_Z)
			{
			    gaiaSetPointXYZ (ring->Coords, iv, nx, ny, z);
			}
		      else if (ring->DimensionModel == GAIA_XY_M)
			{
			    gaiaSetPointXYM (ring->Coords, iv, nx, ny, m);
			}
		      else if (ring->DimensionModel == GAIA_XY_Z_M)
			{
			    gaiaSetPointXYZM (ring->Coords, iv, nx, ny, z, m);
			}
		      else
			{
			    gaiaSetPoint (ring->Coords, iv, nx, ny);
			}
		  }
	    }
	  polyg = polyg->Next;
      }
    gaiaMbrGeometry (geom);
}
示例#8
0
GAIAGEO_DECLARE gaiaGeomCollPtr
gaiaExtractLinestringsFromGeomColl (gaiaGeomCollPtr geom)
{
/* extracts any LINESTRING from a GeometryCollection */
    gaiaGeomCollPtr result;
    gaiaLinestringPtr ln;
    gaiaLinestringPtr new_ln;
    int lns = 0;
    int iv;
    double x;
    double y;
    double z;
    double m;
    if (!geom)
	return NULL;

    ln = geom->FirstLinestring;
    while (ln)
      {
	  lns++;
	  ln = ln->Next;
      }
    if (!lns)
	return NULL;

    if (geom->DimensionModel == GAIA_XY_Z_M)
	result = gaiaAllocGeomCollXYZM ();
    else if (geom->DimensionModel == GAIA_XY_Z)
	result = gaiaAllocGeomCollXYZ ();
    else if (geom->DimensionModel == GAIA_XY_M)
	result = gaiaAllocGeomCollXYM ();
    else
	result = gaiaAllocGeomColl ();
    ln = geom->FirstLinestring;
    while (ln)
      {
	  new_ln = gaiaAddLinestringToGeomColl (result, ln->Points);
	  for (iv = 0; iv < ln->Points; iv++)
	    {
		if (ln->DimensionModel == GAIA_XY_Z_M)
		  {
		      gaiaGetPointXYZM (ln->Coords, iv, &x, &y, &z, &m);
		      gaiaSetPointXYZM (new_ln->Coords, iv, x, y, z, m);
		  }
		else if (ln->DimensionModel == GAIA_XY_Z)
		  {
		      gaiaGetPointXYZ (ln->Coords, iv, &x, &y, &z);
		      gaiaSetPointXYZ (new_ln->Coords, iv, x, y, z);
		  }
		else if (ln->DimensionModel == GAIA_XY_M)
		  {
		      gaiaGetPointXYM (ln->Coords, iv, &x, &y, &m);
		      gaiaSetPointXYM (new_ln->Coords, iv, x, y, m);
		  }
		else
		  {
		      gaiaGetPoint (ln->Coords, iv, &x, &y);
		      gaiaSetPoint (new_ln->Coords, iv, x, y);
		  }
	    }
	  ln = ln->Next;
      }
    result->Srid = geom->Srid;
    result->DeclaredType = GAIA_MULTILINESTRING;
    return result;
}
示例#9
0
GAIAGEO_DECLARE gaiaGeomCollPtr
gaiaExtractPolygonsFromGeomColl (gaiaGeomCollPtr geom)
{
/* extracts any POLYGON from a GeometryCollection */
    gaiaGeomCollPtr result;
    gaiaPolygonPtr pg;
    gaiaPolygonPtr new_pg;
    gaiaRingPtr rng;
    gaiaRingPtr new_rng;
    int pgs = 0;
    int iv;
    int ib;
    double x;
    double y;
    double z;
    double m;
    if (!geom)
	return NULL;

    pg = geom->FirstPolygon;
    while (pg)
      {
	  pgs++;
	  pg = pg->Next;
      }
    if (!pgs)
	return NULL;

    if (geom->DimensionModel == GAIA_XY_Z_M)
	result = gaiaAllocGeomCollXYZM ();
    else if (geom->DimensionModel == GAIA_XY_Z)
	result = gaiaAllocGeomCollXYZ ();
    else if (geom->DimensionModel == GAIA_XY_M)
	result = gaiaAllocGeomCollXYM ();
    else
	result = gaiaAllocGeomColl ();
    pg = geom->FirstPolygon;
    while (pg)
      {
	  rng = pg->Exterior;
	  new_pg =
	      gaiaAddPolygonToGeomColl (result, rng->Points, pg->NumInteriors);
	  new_rng = new_pg->Exterior;
	  for (iv = 0; iv < rng->Points; iv++)
	    {
		if (rng->DimensionModel == GAIA_XY_Z_M)
		  {
		      gaiaGetPointXYZM (rng->Coords, iv, &x, &y, &z, &m);
		      gaiaSetPointXYZM (new_rng->Coords, iv, x, y, z, m);
		  }
		else if (rng->DimensionModel == GAIA_XY_Z)
		  {
		      gaiaGetPointXYZ (rng->Coords, iv, &x, &y, &z);
		      gaiaSetPointXYZ (new_rng->Coords, iv, x, y, z);
		  }
		else if (rng->DimensionModel == GAIA_XY_M)
		  {
		      gaiaGetPointXYM (rng->Coords, iv, &x, &y, &m);
		      gaiaSetPointXYM (new_rng->Coords, iv, x, y, m);
		  }
		else
		  {
		      gaiaGetPoint (rng->Coords, iv, &x, &y);
		      gaiaSetPoint (new_rng->Coords, iv, x, y);
		  }
	    }
	  for (ib = 0; ib < pg->NumInteriors; ib++)
	    {
		rng = pg->Interiors + ib;
		new_rng = gaiaAddInteriorRing (new_pg, ib, rng->Points);
		for (iv = 0; iv < rng->Points; iv++)
		  {
		      if (rng->DimensionModel == GAIA_XY_Z_M)
			{
			    gaiaGetPointXYZM (rng->Coords, iv, &x, &y, &z, &m);
			    gaiaSetPointXYZM (new_rng->Coords, iv, x, y, z, m);
			}
		      else if (rng->DimensionModel == GAIA_XY_Z)
			{
			    gaiaGetPointXYZ (rng->Coords, iv, &x, &y, &z);
			    gaiaSetPointXYZ (new_rng->Coords, iv, x, y, z);
			}
		      else if (rng->DimensionModel == GAIA_XY_M)
			{
			    gaiaGetPointXYM (rng->Coords, iv, &x, &y, &m);
			    gaiaSetPointXYM (new_rng->Coords, iv, x, y, m);
			}
		      else
			{
			    gaiaGetPoint (rng->Coords, iv, &x, &y);
			    gaiaSetPoint (new_rng->Coords, iv, x, y);
			}
		  }
	    }
	  pg = pg->Next;
      }
    result->Srid = geom->Srid;
    result->DeclaredType = GAIA_MULTIPOLYGON;
    return result;
}
示例#10
0
GAIAGEO_DECLARE gaiaGeomCollPtr
gaiaDissolveSegments (gaiaGeomCollPtr geom)
{
/* attempts to dissolve a Geometry into segments */
    gaiaGeomCollPtr result;
    gaiaPointPtr pt;
    gaiaLinestringPtr ln;
    gaiaLinestringPtr segment;
    gaiaPolygonPtr pg;
    gaiaRingPtr rng;
    int iv;
    int ib;
    double x;
    double y;
    double z;
    double m;
    double x0;
    double y0;
    double z0;
    double m0;
    if (!geom)
	return NULL;

    if (geom->DimensionModel == GAIA_XY_Z_M)
	result = gaiaAllocGeomCollXYZM ();
    else if (geom->DimensionModel == GAIA_XY_Z)
	result = gaiaAllocGeomCollXYZ ();
    else if (geom->DimensionModel == GAIA_XY_M)
	result = gaiaAllocGeomCollXYM ();
    else
	result = gaiaAllocGeomColl ();
    pt = geom->FirstPoint;
    while (pt)
      {
	  if (geom->DimensionModel == GAIA_XY_Z_M)
	      gaiaAddPointToGeomCollXYZM (result, pt->X, pt->Y, pt->Z, pt->M);
	  else if (geom->DimensionModel == GAIA_XY_Z)
	      gaiaAddPointToGeomCollXYZ (result, pt->X, pt->Y, pt->Z);
	  else if (geom->DimensionModel == GAIA_XY_M)
	      gaiaAddPointToGeomCollXYM (result, pt->X, pt->Y, pt->M);
	  else
	      gaiaAddPointToGeomColl (result, pt->X, pt->Y);
	  pt = pt->Next;
      }
    ln = geom->FirstLinestring;
    while (ln)
      {
	  for (iv = 0; iv < ln->Points; iv++)
	    {
		if (ln->DimensionModel == GAIA_XY_Z_M)
		  {
		      gaiaGetPointXYZM (ln->Coords, iv, &x, &y, &z, &m);
		  }
		else if (ln->DimensionModel == GAIA_XY_Z)
		  {
		      gaiaGetPointXYZ (ln->Coords, iv, &x, &y, &z);
		  }
		else if (ln->DimensionModel == GAIA_XY_M)
		  {
		      gaiaGetPointXYM (ln->Coords, iv, &x, &y, &m);
		  }
		else
		  {
		      gaiaGetPoint (ln->Coords, iv, &x, &y);
		  }
		if (iv > 0)
		  {
		      if (geom->DimensionModel == GAIA_XY_Z_M)
			{
			    if (x != x0 || y != y0 || z != z0 || m != m0)
			      {
				  segment =
				      gaiaAddLinestringToGeomColl (result, 2);
				  gaiaSetPointXYZM (segment->Coords, 0, x0, y0,
						    z0, m0);
				  gaiaSetPointXYZM (segment->Coords, 1, x, y, z,
						    m);
			      }
			}
		      else if (geom->DimensionModel == GAIA_XY_Z)
			{
			    if (x != x0 || y != y0 || z != z0)
			      {
				  segment =
				      gaiaAddLinestringToGeomColl (result, 2);
				  gaiaSetPointXYZ (segment->Coords, 0, x0, y0,
						   z0);
				  gaiaSetPointXYZ (segment->Coords, 1, x, y, z);
			      }
			}
		      else if (geom->DimensionModel == GAIA_XY_M)
			{
			    if (x != x0 || y != y0 || m != m0)
			      {
				  segment =
				      gaiaAddLinestringToGeomColl (result, 2);
				  gaiaSetPointXYM (segment->Coords, 0, x0, y0,
						   m0);
				  gaiaSetPointXYM (segment->Coords, 1, x, y, m);
			      }
			}
		      else
			{
			    if (x != x0 || y != y0)
			      {
				  segment =
				      gaiaAddLinestringToGeomColl (result, 2);
				  gaiaSetPoint (segment->Coords, 0, x0, y0);
				  gaiaSetPoint (segment->Coords, 1, x, y);
			      }
			}
		  }
		x0 = x;
		y0 = y;
		z0 = z;
		m0 = m;
	    }
	  ln = ln->Next;
      }
    pg = geom->FirstPolygon;
    while (pg)
      {
	  rng = pg->Exterior;
	  for (iv = 0; iv < rng->Points; iv++)
	    {
		/* exterior Ring */
		if (rng->DimensionModel == GAIA_XY_Z_M)
		  {
		      gaiaGetPointXYZM (rng->Coords, iv, &x, &y, &z, &m);
		  }
		else if (rng->DimensionModel == GAIA_XY_Z)
		  {
		      gaiaGetPointXYZ (rng->Coords, iv, &x, &y, &z);
		  }
		else if (rng->DimensionModel == GAIA_XY_M)
		  {
		      gaiaGetPointXYM (rng->Coords, iv, &x, &y, &m);
		  }
		else
		  {
		      gaiaGetPoint (rng->Coords, iv, &x, &y);
		  }
		if (iv > 0)
		  {
		      if (geom->DimensionModel == GAIA_XY_Z_M)
			{
			    if (x != x0 || y != y0 || z != z0 || m != m0)
			      {
				  segment =
				      gaiaAddLinestringToGeomColl (result, 2);
				  gaiaSetPointXYZM (segment->Coords, 0, x0, y0,
						    z0, m0);
				  gaiaSetPointXYZM (segment->Coords, 1, x, y, z,
						    m);
			      }
			}
		      else if (geom->DimensionModel == GAIA_XY_Z)
			{
			    if (x != x0 || y != y0 || z != z0)
			      {
				  segment =
				      gaiaAddLinestringToGeomColl (result, 2);
				  gaiaSetPointXYZ (segment->Coords, 0, x0, y0,
						   z0);
				  gaiaSetPointXYZ (segment->Coords, 1, x, y, z);
			      }
			}
		      else if (geom->DimensionModel == GAIA_XY_M)
			{
			    if (x != x0 || y != y0 || m != m0)
			      {
				  segment =
				      gaiaAddLinestringToGeomColl (result, 2);
				  gaiaSetPointXYM (segment->Coords, 0, x0, y0,
						   m0);
				  gaiaSetPointXYM (segment->Coords, 1, x, y, m);
			      }
			}
		      else
			{
			    if (x != x0 || y != y0)
			      {
				  segment =
				      gaiaAddLinestringToGeomColl (result, 2);
				  gaiaSetPoint (segment->Coords, 0, x0, y0);
				  gaiaSetPoint (segment->Coords, 1, x, y);
			      }
			}
		  }
		x0 = x;
		y0 = y;
		z0 = z;
		m0 = m;
	    }
	  for (ib = 0; ib < pg->NumInteriors; ib++)
	    {
		rng = pg->Interiors + ib;
		for (iv = 0; iv < rng->Points; iv++)
		  {
		      /* interior Ring */
		      if (rng->DimensionModel == GAIA_XY_Z_M)
			{
			    gaiaGetPointXYZM (rng->Coords, iv, &x, &y, &z, &m);
			}
		      else if (rng->DimensionModel == GAIA_XY_Z)
			{
			    gaiaGetPointXYZ (rng->Coords, iv, &x, &y, &z);
			}
		      else if (rng->DimensionModel == GAIA_XY_M)
			{
			    gaiaGetPointXYM (rng->Coords, iv, &x, &y, &m);
			}
		      else
			{
			    gaiaGetPoint (rng->Coords, iv, &x, &y);
			}
		      if (iv > 0)
			{
			    if (geom->DimensionModel == GAIA_XY_Z_M)
			      {
				  if (x != x0 || y != y0 || z != z0 || m != m0)
				    {
					segment =
					    gaiaAddLinestringToGeomColl (result,
									 2);
					gaiaSetPointXYZM (segment->Coords, 0,
							  x0, y0, z0, m0);
					gaiaSetPointXYZM (segment->Coords, 1, x,
							  y, z, m);
				    }
			      }
			    else if (geom->DimensionModel == GAIA_XY_Z)
			      {
				  if (x != x0 || y != y0 || z != z0)
				    {
					segment =
					    gaiaAddLinestringToGeomColl (result,
									 2);
					gaiaSetPointXYZ (segment->Coords, 0, x0,
							 y0, z0);
					gaiaSetPointXYZ (segment->Coords, 1, x,
							 y, z);
				    }
			      }
			    else if (geom->DimensionModel == GAIA_XY_M)
			      {
				  if (x != x0 || y != y0 || m != m0)
				    {
					segment =
					    gaiaAddLinestringToGeomColl (result,
									 2);
					gaiaSetPointXYM (segment->Coords, 0, x0,
							 y0, m0);
					gaiaSetPointXYM (segment->Coords, 1, x,
							 y, m);
				    }
			      }
			    else
			      {
				  if (x != x0 || y != y0)
				    {
					segment =
					    gaiaAddLinestringToGeomColl (result,
									 2);
					gaiaSetPoint (segment->Coords, 0, x0,
						      y0);
					gaiaSetPoint (segment->Coords, 1, x, y);
				    }
			      }
			}
		      x0 = x;
		      y0 = y;
		      z0 = z;
		      m0 = m;
		  }
	    }
	  pg = pg->Next;
      }
    result->Srid = geom->Srid;
    return result;
}
示例#11
0
GAIAGEO_DECLARE gaiaGeomCollPtr
gaiaLinearize (gaiaGeomCollPtr geom, int force_multi)
{
/* attempts to rearrange a generic Geometry into a (multi)linestring */
    int pts = 0;
    int lns = 0;
    gaiaGeomCollPtr result;
    gaiaPointPtr pt;
    gaiaLinestringPtr ln;
    gaiaLinestringPtr new_ln;
    gaiaPolygonPtr pg;
    gaiaRingPtr rng;
    int iv;
    int ib;
    double x;
    double y;
    double m;
    double z;
    if (!geom)
	return NULL;
    pt = geom->FirstPoint;
    while (pt)
      {
	  pts++;
	  pt = pt->Next;
      }
    ln = geom->FirstLinestring;
    while (ln)
      {
	  lns++;
	  ln = ln->Next;
      }
    if (pts || lns)
	return NULL;

    if (geom->DimensionModel == GAIA_XY_Z_M)
	result = gaiaAllocGeomCollXYZM ();
    else if (geom->DimensionModel == GAIA_XY_Z)
	result = gaiaAllocGeomCollXYZ ();
    else if (geom->DimensionModel == GAIA_XY_M)
	result = gaiaAllocGeomCollXYM ();
    else
	result = gaiaAllocGeomColl ();
    result->Srid = geom->Srid;
    if (force_multi)
	result->DeclaredType = GAIA_MULTILINESTRING;

    pg = geom->FirstPolygon;
    while (pg)
      {
	  /* dissolving any POLYGON as simple LINESTRINGs (rings) */
	  rng = pg->Exterior;
	  new_ln = gaiaAddLinestringToGeomColl (result, rng->Points);
	  for (iv = 0; iv < rng->Points; iv++)
	    {
		/* copying the EXTERIOR RING as LINESTRING */
		if (geom->DimensionModel == GAIA_XY_Z_M)
		  {
		      gaiaGetPointXYZM (rng->Coords, iv, &x, &y, &z, &m);
		      gaiaSetPointXYZM (new_ln->Coords, iv, x, y, z, m);
		  }
		else if (geom->DimensionModel == GAIA_XY_Z)
		  {
		      gaiaGetPointXYZ (rng->Coords, iv, &x, &y, &z);
		      gaiaSetPointXYZ (new_ln->Coords, iv, x, y, z);
		  }
		else if (geom->DimensionModel == GAIA_XY_M)
		  {
		      gaiaGetPointXYM (rng->Coords, iv, &x, &y, &m);
		      gaiaSetPointXYM (new_ln->Coords, iv, x, y, m);
		  }
		else
		  {
		      gaiaGetPoint (rng->Coords, iv, &x, &y);
		      gaiaSetPoint (new_ln->Coords, iv, x, y);
		  }
	    }
	  for (ib = 0; ib < pg->NumInteriors; ib++)
	    {
		rng = pg->Interiors + ib;
		new_ln = gaiaAddLinestringToGeomColl (result, rng->Points);
		for (iv = 0; iv < rng->Points; iv++)
		  {
		      /* copying an INTERIOR RING as LINESTRING */
		      if (geom->DimensionModel == GAIA_XY_Z_M)
			{
			    gaiaGetPointXYZM (rng->Coords, iv, &x, &y, &z, &m);
			    gaiaSetPointXYZM (new_ln->Coords, iv, x, y, z, m);
			}
		      else if (geom->DimensionModel == GAIA_XY_Z)
			{
			    gaiaGetPointXYZ (rng->Coords, iv, &x, &y, &z);
			    gaiaSetPointXYZ (new_ln->Coords, iv, x, y, z);
			}
		      else if (geom->DimensionModel == GAIA_XY_M)
			{
			    gaiaGetPointXYM (rng->Coords, iv, &x, &y, &m);
			    gaiaSetPointXYM (new_ln->Coords, iv, x, y, m);
			}
		      else
			{
			    gaiaGetPoint (rng->Coords, iv, &x, &y);
			    gaiaSetPoint (new_ln->Coords, iv, x, y);
			}
		  }
	    }
	  pg = pg->Next;
      }
    if (result->FirstLinestring == NULL)
      {
	  gaiaFreeGeomColl (result);
	  return NULL;
      }
    return result;
}
示例#12
0
static void
auxGridSnapPolygon (gaiaPolygonPtr pg, gaiaGeomCollPtr result, double origin_x,
		    double origin_y, double origin_z, double origin_m,
		    double size_x, double size_y, double size_z, double size_m)
{
/* snapping a Polygon to a regular Grid */
    int ib;
    int holes = 0;
    int count;
    int next_hole = 0;
    int iv;
    gaiaRingPtr rng;
    gaiaPolygonPtr pgx;
    gaiaPointPtr pt;
    gaiaDynamicLinePtr rng_ext;
    gaiaDynamicLinePtr dyn;
    gaiaDynamicLinePtr *rng_ints = NULL;

    if (pg == NULL || result == NULL)
	return;
/* snapping the Exterior Ring */
    rng = pg->Exterior;
    rng_ext =
	auxGridSnapRing (rng, origin_x, origin_y, origin_z, origin_m, size_x,
			 size_y, size_z, size_m);
    if (rng_ext == NULL)	/* skipping any collaped Polygon */
	return;

    if (pg->NumInteriors)
      {
	  /* snapping any Interior Ring */
	  rng_ints = malloc (sizeof (gaiaRingPtr *) * pg->NumInteriors);
	  for (ib = 0; ib < pg->NumInteriors; ib++)
	    {
		rng = pg->Interiors + ib;
		*(rng_ints + ib) =
		    auxGridSnapRing (rng, origin_x, origin_y, origin_z,
				     origin_m, size_x, size_y, size_z, size_m);
		if (*(rng_ints + ib) != NULL)
		    holes++;
	    }
      }

/* inserting into the result Geometry */
    pt = rng_ext->First;
    count = 0;
    while (pt)
      {
	  /* counting how many points are in the Exterior Ring */
	  count++;
	  pt = pt->Next;
      }
    pgx = gaiaAddPolygonToGeomColl (result, count, holes);
    rng = pgx->Exterior;
    iv = 0;
    pt = rng_ext->First;
    while (pt)
      {
	  /* copying Exterior Ring points */
	  if (rng->DimensionModel == GAIA_XY_Z)
	    {
		gaiaSetPointXYZ (rng->Coords, iv, pt->X, pt->Y, pt->Z);
	    }
	  else if (rng->DimensionModel == GAIA_XY_M)
	    {
		gaiaSetPointXYM (rng->Coords, iv, pt->X, pt->Y, pt->M);
	    }
	  else if (rng->DimensionModel == GAIA_XY_Z_M)
	    {
		gaiaSetPointXYZM (rng->Coords, iv, pt->X, pt->Y, pt->Z, pt->M);
	    }
	  else
	    {
		gaiaSetPoint (rng->Coords, iv, pt->X, pt->Y);
	    }
	  iv++;
	  pt = pt->Next;
      }
    if (holes > 0)
      {
	  /* setting up any not-collapsed Hole */
	  for (ib = 0; ib < pg->NumInteriors; ib++)
	    {
		if (*(rng_ints + ib) == NULL)
		    continue;
		dyn = *(rng_ints + ib);
		pt = dyn->First;
		count = 0;
		while (pt)
		  {
		      /* counting how many points are in the Exterior Ring */
		      count++;
		      pt = pt->Next;
		  }
		rng = gaiaAddInteriorRing (pgx, next_hole++, count);
		iv = 0;
		pt = dyn->First;
		while (pt)
		  {
		      /* copying Interior Ring points */
		      if (rng->DimensionModel == GAIA_XY_Z)
			{
			    gaiaSetPointXYZ (rng->Coords, iv, pt->X, pt->Y,
					     pt->Z);
			}
		      else if (rng->DimensionModel == GAIA_XY_M)
			{
			    gaiaSetPointXYM (rng->Coords, iv, pt->X, pt->Y,
					     pt->M);
			}
		      else if (rng->DimensionModel == GAIA_XY_Z_M)
			{
			    gaiaSetPointXYZM (rng->Coords, iv, pt->X, pt->Y,
					      pt->Z, pt->M);
			}
		      else
			{
			    gaiaSetPoint (rng->Coords, iv, pt->X, pt->Y);
			}
		      iv++;
		      pt = pt->Next;
		  }
	    }
      }

/* memory clean-up */
    gaiaFreeDynamicLine (rng_ext);
    if (rng_ints)
      {
	  for (ib = 0; ib < pg->NumInteriors; ib++)
	    {
		dyn = *(rng_ints + ib);
		if (dyn)
		    gaiaFreeDynamicLine (dyn);
	    }
	  free (rng_ints);
      }
}
示例#13
0
static void
auxGridSnapLinestring (gaiaLinestringPtr ln, gaiaGeomCollPtr result,
		       double origin_x, double origin_y, double origin_z,
		       double origin_m, double size_x, double size_y,
		       double size_z, double size_m)
{
/* snapping a Linestring to a regular Grid */
    double x;
    double y;
    double z;
    double m;
    int has_z = 0;
    int has_m = 0;
    int iv;
    gaiaDynamicLinePtr dyn;
    gaiaPointPtr pt;
    gaiaLinestringPtr lnx;
    int count = 0;

    if (ln == NULL || result == NULL)
	return;
    if (ln->DimensionModel == GAIA_XY_Z || ln->DimensionModel == GAIA_XY_Z_M)
	has_z = 1;
    if (ln->DimensionModel == GAIA_XY_M || ln->DimensionModel == GAIA_XY_Z_M)
	has_m = 1;
    dyn = gaiaAllocDynamicLine ();

    for (iv = 0; iv < ln->Points; iv++)
      {
	  /* snapping each Vertex to the given grid */
	  int to_be_inserted = 0;
	  z = 0.0;
	  m = 0.0;
	  if (has_z && has_m)
	    {
		gaiaGetPointXYZM (ln->Coords, iv, &x, &y, &z, &m);
	    }
	  else if (has_z)
	    {
		gaiaGetPointXYZ (ln->Coords, iv, &x, &y, &z);
	    }
	  else if (has_m)
	    {
		gaiaGetPointXYM (ln->Coords, iv, &x, &y, &m);
	    }
	  else
	    {
		gaiaGetPoint (ln->Coords, iv, &x, &y);
	    }
	  /* snapping coords to the given grid */
	  if (size_x > 0.0)
	      x = rint ((x - origin_x) / size_x) * size_x + origin_x;
	  if (size_y > 0.0)
	      y = rint ((y - origin_y) / size_y) * size_y + origin_y;
	  if (has_z && size_z > 0.0)
	      z = rint ((z - origin_z) / size_z) * size_z + origin_z;
	  if (has_m && size_m > 0.0)
	      m = rint ((m - origin_m) / size_m) * size_m + origin_m;

	  if (dyn->Last == NULL)
	      to_be_inserted = 1;
	  else
	    {
		/* skipping repeated points */
		pt = dyn->Last;
		if (has_z && has_m)
		  {
		      if (pt->X == x && pt->Y == y && pt->Z == z && pt->M == m)
			  ;
		      else
			  to_be_inserted = 1;
		  }
		else if (has_z)
		  {
		      if (pt->X == x && pt->Y == y && pt->Z == z)
			  ;
		      else
			  to_be_inserted = 1;
		  }
		else if (has_m)
		  {
		      if (pt->X == x && pt->Y == y && pt->M == m)
			  ;
		      else
			  to_be_inserted = 1;
		  }
		else
		  {
		      if (pt->X == x && pt->Y == y)
			  ;
		      else
			  to_be_inserted = 1;
		  }
	    }
	  if (to_be_inserted)
	    {
		if (has_z && has_m)
		    gaiaAppendPointZMToDynamicLine (dyn, x, y, z, m);
		else if (has_z)
		    gaiaAppendPointZToDynamicLine (dyn, x, y, z);
		else if (has_m)
		    gaiaAppendPointMToDynamicLine (dyn, x, y, m);
		else
		    gaiaAppendPointToDynamicLine (dyn, x, y);
	    }
      }

/* checking for validity */
    pt = dyn->First;
    while (pt)
      {
	  /* counting how many points are there */
	  count++;
	  pt = pt->Next;
      }
    if (count < 2)
      {
	  /* skipping any collapsed line */
	  gaiaFreeDynamicLine (dyn);
	  return;
      }

/* inserting into the result Geometry */
    lnx = gaiaAddLinestringToGeomColl (result, count);
    iv = 0;
    pt = dyn->First;
    while (pt)
      {
	  /* copying points */
	  if (lnx->DimensionModel == GAIA_XY_Z)
	    {
		gaiaSetPointXYZ (lnx->Coords, iv, pt->X, pt->Y, pt->Z);
	    }
	  else if (lnx->DimensionModel == GAIA_XY_M)
	    {
		gaiaSetPointXYM (lnx->Coords, iv, pt->X, pt->Y, pt->M);
	    }
	  else if (lnx->DimensionModel == GAIA_XY_Z_M)
	    {
		gaiaSetPointXYZM (lnx->Coords, iv, pt->X, pt->Y, pt->Z, pt->M);
	    }
	  else
	    {
		gaiaSetPoint (lnx->Coords, iv, pt->X, pt->Y);
	    }
	  iv++;
	  pt = pt->Next;
      }
    gaiaFreeDynamicLine (dyn);
}
示例#14
0
static gaiaGeomCollPtr
fromGeosGeometry (const GEOSGeometry * geos, const int dimension_model)
{
/* converting a GEOS Geometry into a GAIA Geometry */
    int type;
    int itemType;
    unsigned int dims;
    int iv;
    int ib;
    int it;
    int sub_it;
    int nItems;
    int nSubItems;
    int holes;
    unsigned int points;
    double x;
    double y;
    double z;
    const GEOSCoordSequence *cs;
    const GEOSGeometry *geos_ring;
    const GEOSGeometry *geos_item;
    const GEOSGeometry *geos_sub_item;
    gaiaGeomCollPtr gaia = NULL;
    gaiaLinestringPtr ln;
    gaiaPolygonPtr pg;
    gaiaRingPtr rng;
    if (!geos)
	return NULL;
    type = GEOSGeomTypeId (geos);
    switch (type)
      {
      case GEOS_POINT:
	  if (dimension_model == GAIA_XY_Z)
	      gaia = gaiaAllocGeomCollXYZ ();
	  else if (dimension_model == GAIA_XY_M)
	      gaia = gaiaAllocGeomCollXYM ();
	  else if (dimension_model == GAIA_XY_Z_M)
	      gaia = gaiaAllocGeomCollXYZM ();
	  else
	      gaia = gaiaAllocGeomColl ();
	  gaia->DeclaredType = GAIA_POINT;
	  gaia->Srid = GEOSGetSRID (geos);
	  cs = GEOSGeom_getCoordSeq (geos);
	  GEOSCoordSeq_getDimensions (cs, &dims);
	  if (dims == 3)
	    {
		GEOSCoordSeq_getX (cs, 0, &x);
		GEOSCoordSeq_getY (cs, 0, &y);
		GEOSCoordSeq_getZ (cs, 0, &z);
	    }
	  else
	    {
		GEOSCoordSeq_getX (cs, 0, &x);
		GEOSCoordSeq_getY (cs, 0, &y);
		z = 0.0;
	    }
	  if (dimension_model == GAIA_XY_Z)
	      gaiaAddPointToGeomCollXYZ (gaia, x, y, z);
	  else if (dimension_model == GAIA_XY_M)
	      gaiaAddPointToGeomCollXYM (gaia, x, y, 0.0);
	  else if (dimension_model == GAIA_XY_Z_M)
	      gaiaAddPointToGeomCollXYZM (gaia, x, y, z, 0.0);
	  else
	      gaiaAddPointToGeomColl (gaia, x, y);
	  break;
      case GEOS_LINESTRING:
	  if (dimension_model == GAIA_XY_Z)
	      gaia = gaiaAllocGeomCollXYZ ();
	  else if (dimension_model == GAIA_XY_M)
	      gaia = gaiaAllocGeomCollXYM ();
	  else if (dimension_model == GAIA_XY_Z_M)
	      gaia = gaiaAllocGeomCollXYZM ();
	  else
	      gaia = gaiaAllocGeomColl ();
	  gaia->DeclaredType = GAIA_LINESTRING;
	  gaia->Srid = GEOSGetSRID (geos);
	  cs = GEOSGeom_getCoordSeq (geos);
	  GEOSCoordSeq_getDimensions (cs, &dims);
	  GEOSCoordSeq_getSize (cs, &points);
	  ln = gaiaAddLinestringToGeomColl (gaia, points);
	  for (iv = 0; iv < (int) points; iv++)
	    {
		if (dims == 3)
		  {
		      GEOSCoordSeq_getX (cs, iv, &x);
		      GEOSCoordSeq_getY (cs, iv, &y);
		      GEOSCoordSeq_getZ (cs, iv, &z);
		  }
		else
		  {
		      GEOSCoordSeq_getX (cs, iv, &x);
		      GEOSCoordSeq_getY (cs, iv, &y);
		      z = 0.0;
		  }
		if (dimension_model == GAIA_XY_Z)
		  {
		      gaiaSetPointXYZ (ln->Coords, iv, x, y, z);
		  }
		else if (dimension_model == GAIA_XY_M)
		  {
		      gaiaSetPointXYM (ln->Coords, iv, x, y, 0.0);
		  }
		else if (dimension_model == GAIA_XY_Z_M)
		  {
		      gaiaSetPointXYZM (ln->Coords, iv, x, y, z, 0.0);
		  }
		else
		  {
		      gaiaSetPoint (ln->Coords, iv, x, y);
		  }
	    }
	  break;
      case GEOS_POLYGON:
	  if (dimension_model == GAIA_XY_Z)
	      gaia = gaiaAllocGeomCollXYZ ();
	  else if (dimension_model == GAIA_XY_M)
	      gaia = gaiaAllocGeomCollXYM ();
	  else if (dimension_model == GAIA_XY_Z_M)
	      gaia = gaiaAllocGeomCollXYZM ();
	  else
	      gaia = gaiaAllocGeomColl ();
	  gaia->DeclaredType = GAIA_POLYGON;
	  gaia->Srid = GEOSGetSRID (geos);
	  /* exterior ring */
	  holes = GEOSGetNumInteriorRings (geos);
	  geos_ring = GEOSGetExteriorRing (geos);
	  cs = GEOSGeom_getCoordSeq (geos_ring);
	  GEOSCoordSeq_getDimensions (cs, &dims);
	  GEOSCoordSeq_getSize (cs, &points);
	  pg = gaiaAddPolygonToGeomColl (gaia, points, holes);
	  rng = pg->Exterior;
	  for (iv = 0; iv < (int) points; iv++)
	    {
		if (dims == 3)
		  {
		      GEOSCoordSeq_getX (cs, iv, &x);
		      GEOSCoordSeq_getY (cs, iv, &y);
		      GEOSCoordSeq_getZ (cs, iv, &z);
		  }
		else
		  {
		      GEOSCoordSeq_getX (cs, iv, &x);
		      GEOSCoordSeq_getY (cs, iv, &y);
		      z = 0.0;
		  }
		if (dimension_model == GAIA_XY_Z)
		  {
		      gaiaSetPointXYZ (rng->Coords, iv, x, y, z);
		  }
		else if (dimension_model == GAIA_XY_M)
		  {
		      gaiaSetPointXYM (rng->Coords, iv, x, y, 0.0);
		  }
		else if (dimension_model == GAIA_XY_Z_M)
		  {
		      gaiaSetPointXYZM (rng->Coords, iv, x, y, z, 0.0);
		  }
		else
		  {
		      gaiaSetPoint (rng->Coords, iv, x, y);
		  }
	    }
	  for (ib = 0; ib < holes; ib++)
	    {
		/* interior rings */
		geos_ring = GEOSGetInteriorRingN (geos, ib);
		cs = GEOSGeom_getCoordSeq (geos_ring);
		GEOSCoordSeq_getDimensions (cs, &dims);
		GEOSCoordSeq_getSize (cs, &points);
		rng = gaiaAddInteriorRing (pg, ib, points);
		for (iv = 0; iv < (int) points; iv++)
		  {
		      if (dims == 3)
			{
			    GEOSCoordSeq_getX (cs, iv, &x);
			    GEOSCoordSeq_getY (cs, iv, &y);
			    GEOSCoordSeq_getZ (cs, iv, &z);
			}
		      else
			{
			    GEOSCoordSeq_getX (cs, iv, &x);
			    GEOSCoordSeq_getY (cs, iv, &y);
			    z = 0.0;
			}
		      if (dimension_model == GAIA_XY_Z)
			{
			    gaiaSetPointXYZ (rng->Coords, iv, x, y, z);
			}
		      else if (dimension_model == GAIA_XY_M)
			{
			    gaiaSetPointXYM (rng->Coords, iv, x, y, 0.0);
			}
		      else if (dimension_model == GAIA_XY_Z_M)
			{
			    gaiaSetPointXYZM (rng->Coords, iv, x, y, z, 0.0);
			}
		      else
			{
			    gaiaSetPoint (rng->Coords, iv, x, y);
			}
		  }
	    }
	  break;
      case GEOS_MULTIPOINT:
      case GEOS_MULTILINESTRING:
      case GEOS_MULTIPOLYGON:
      case GEOS_GEOMETRYCOLLECTION:
	  if (dimension_model == GAIA_XY_Z)
	      gaia = gaiaAllocGeomCollXYZ ();
	  else if (dimension_model == GAIA_XY_M)
	      gaia = gaiaAllocGeomCollXYM ();
	  else if (dimension_model == GAIA_XY_Z_M)
	      gaia = gaiaAllocGeomCollXYZM ();
	  else
	      gaia = gaiaAllocGeomColl ();
	  if (type == GEOS_MULTIPOINT)
	      gaia->DeclaredType = GAIA_MULTIPOINT;
	  else if (type == GEOS_MULTILINESTRING)
	      gaia->DeclaredType = GAIA_MULTILINESTRING;
	  else if (type == GEOS_MULTIPOLYGON)
	      gaia->DeclaredType = GAIA_MULTIPOLYGON;
	  else
	      gaia->DeclaredType = GAIA_GEOMETRYCOLLECTION;
	  gaia->Srid = GEOSGetSRID (geos);
	  nItems = GEOSGetNumGeometries (geos);
	  for (it = 0; it < nItems; it++)
	    {
		/* looping on elementaty geometries */
		geos_item = GEOSGetGeometryN (geos, it);
		itemType = GEOSGeomTypeId (geos_item);
		switch (itemType)
		  {
		  case GEOS_POINT:
		      cs = GEOSGeom_getCoordSeq (geos_item);
		      GEOSCoordSeq_getDimensions (cs, &dims);
		      if (dims == 3)
			{
			    GEOSCoordSeq_getX (cs, 0, &x);
			    GEOSCoordSeq_getY (cs, 0, &y);
			    GEOSCoordSeq_getZ (cs, 0, &z);
			}
		      else
			{
			    GEOSCoordSeq_getX (cs, 0, &x);
			    GEOSCoordSeq_getY (cs, 0, &y);
			    z = 0.0;
			}
		      if (dimension_model == GAIA_XY_Z)
			  gaiaAddPointToGeomCollXYZ (gaia, x, y, z);
		      else if (dimension_model == GAIA_XY_M)
			  gaiaAddPointToGeomCollXYM (gaia, x, y, 0.0);
		      else if (dimension_model == GAIA_XY_Z_M)
			  gaiaAddPointToGeomCollXYZM (gaia, x, y, z, 0.0);
		      else
			  gaiaAddPointToGeomColl (gaia, x, y);
		      break;
		  case GEOS_LINESTRING:
		      cs = GEOSGeom_getCoordSeq (geos_item);
		      GEOSCoordSeq_getDimensions (cs, &dims);
		      GEOSCoordSeq_getSize (cs, &points);
		      ln = gaiaAddLinestringToGeomColl (gaia, points);
		      for (iv = 0; iv < (int) points; iv++)
			{
			    if (dims == 3)
			      {
				  GEOSCoordSeq_getX (cs, iv, &x);
				  GEOSCoordSeq_getY (cs, iv, &y);
				  GEOSCoordSeq_getZ (cs, iv, &z);
			      }
			    else
			      {
				  GEOSCoordSeq_getX (cs, iv, &x);
				  GEOSCoordSeq_getY (cs, iv, &y);
				  z = 0.0;
			      }
			    if (dimension_model == GAIA_XY_Z)
			      {
				  gaiaSetPointXYZ (ln->Coords, iv, x, y, z);
			      }
			    else if (dimension_model == GAIA_XY_M)
			      {
				  gaiaSetPointXYM (ln->Coords, iv, x, y, 0.0);
			      }
			    else if (dimension_model == GAIA_XY_Z_M)
			      {
				  gaiaSetPointXYZM (ln->Coords, iv, x, y, z,
						    0.0);
			      }
			    else
			      {
				  gaiaSetPoint (ln->Coords, iv, x, y);
			      }
			}
		      break;
		  case GEOS_MULTILINESTRING:
		      nSubItems = GEOSGetNumGeometries (geos_item);
		      for (sub_it = 0; sub_it < nSubItems; sub_it++)
			{
			    /* looping on elementaty geometries */
			    geos_sub_item =
				GEOSGetGeometryN (geos_item, sub_it);
			    cs = GEOSGeom_getCoordSeq (geos_sub_item);
			    GEOSCoordSeq_getDimensions (cs, &dims);
			    GEOSCoordSeq_getSize (cs, &points);
			    ln = gaiaAddLinestringToGeomColl (gaia, points);
			    for (iv = 0; iv < (int) points; iv++)
			      {
				  if (dims == 3)
				    {
					GEOSCoordSeq_getX (cs, iv, &x);
					GEOSCoordSeq_getY (cs, iv, &y);
					GEOSCoordSeq_getZ (cs, iv, &z);
				    }
				  else
				    {
					GEOSCoordSeq_getX (cs, iv, &x);
					GEOSCoordSeq_getY (cs, iv, &y);
					z = 0.0;
				    }
				  if (dimension_model == GAIA_XY_Z)
				    {
					gaiaSetPointXYZ (ln->Coords, iv, x, y,
							 z);
				    }
				  else if (dimension_model == GAIA_XY_M)
				    {
					gaiaSetPointXYM (ln->Coords, iv, x, y,
							 0.0);
				    }
				  else if (dimension_model == GAIA_XY_Z_M)
				    {
					gaiaSetPointXYZM (ln->Coords, iv, x, y,
							  z, 0.0);
				    }
				  else
				    {
					gaiaSetPoint (ln->Coords, iv, x, y);
				    }
			      }
			}
		      break;
		  case GEOS_POLYGON:
		      /* exterior ring */
		      holes = GEOSGetNumInteriorRings (geos_item);
		      geos_ring = GEOSGetExteriorRing (geos_item);
		      cs = GEOSGeom_getCoordSeq (geos_ring);
		      GEOSCoordSeq_getDimensions (cs, &dims);
		      GEOSCoordSeq_getSize (cs, &points);
		      pg = gaiaAddPolygonToGeomColl (gaia, points, holes);
		      rng = pg->Exterior;
		      for (iv = 0; iv < (int) points; iv++)
			{
			    if (dims == 3)
			      {
				  GEOSCoordSeq_getX (cs, iv, &x);
				  GEOSCoordSeq_getY (cs, iv, &y);
				  GEOSCoordSeq_getZ (cs, iv, &z);
			      }
			    else
			      {
				  GEOSCoordSeq_getX (cs, iv, &x);
				  GEOSCoordSeq_getY (cs, iv, &y);
				  z = 0.0;
			      }
			    if (dimension_model == GAIA_XY_Z)
			      {
				  gaiaSetPointXYZ (rng->Coords, iv, x, y, z);
			      }
			    else if (dimension_model == GAIA_XY_M)
			      {
				  gaiaSetPointXYM (rng->Coords, iv, x, y, 0.0);
			      }
			    else if (dimension_model == GAIA_XY_Z_M)
			      {
				  gaiaSetPointXYZM (rng->Coords, iv, x, y, z,
						    0.0);
			      }
			    else
			      {
				  gaiaSetPoint (rng->Coords, iv, x, y);
			      }
			}
		      for (ib = 0; ib < holes; ib++)
			{
			    /* interior rings */
			    geos_ring = GEOSGetInteriorRingN (geos_item, ib);
			    cs = GEOSGeom_getCoordSeq (geos_ring);
			    GEOSCoordSeq_getDimensions (cs, &dims);
			    GEOSCoordSeq_getSize (cs, &points);
			    rng = gaiaAddInteriorRing (pg, ib, points);
			    for (iv = 0; iv < (int) points; iv++)
			      {
				  if (dims == 3)
				    {
					GEOSCoordSeq_getX (cs, iv, &x);
					GEOSCoordSeq_getY (cs, iv, &y);
					GEOSCoordSeq_getZ (cs, iv, &z);
				    }
				  else
				    {
					GEOSCoordSeq_getX (cs, iv, &x);
					GEOSCoordSeq_getY (cs, iv, &y);
					z = 0.0;
				    }
				  if (dimension_model == GAIA_XY_Z)
				    {
					gaiaSetPointXYZ (rng->Coords, iv, x, y,
							 z);
				    }
				  else if (dimension_model == GAIA_XY_M)
				    {
					gaiaSetPointXYM (rng->Coords, iv, x, y,
							 0.0);
				    }
				  else if (dimension_model == GAIA_XY_Z_M)
				    {
					gaiaSetPointXYZM (rng->Coords, iv, x, y,
							  z, 0.0);
				    }
				  else
				    {
					gaiaSetPoint (rng->Coords, iv, x, y);
				    }
			      }
			}
		      break;
		  };
	    }
	  break;
      };
    return gaia;
}