ERL_NIF_TERM geom_to_eterm_polygon_coords(ErlNifEnv *env, const GEOSGeometry *geom) { unsigned int inner_num, i; const GEOSGeometry *outer, *inner; const GEOSCoordSequence *coords_seq; ERL_NIF_TERM coords; ERL_NIF_TERM *rings; inner_num = GEOSGetNumInteriorRings(geom); // all rings, outer + inner rings = malloc(sizeof(ERL_NIF_TERM)*inner_num+1); outer = GEOSGetExteriorRing(geom); coords_seq = GEOSGeom_getCoordSeq(outer); rings[0] = GEOSCoordSequence_to_eterm_list(env, coords_seq, GEOSGetNumCoordinates(outer)); for (i=0; i<inner_num; i++) { inner = GEOSGetInteriorRingN(geom, i); coords_seq = GEOSGeom_getCoordSeq(inner); rings[i+1] = GEOSCoordSequence_to_eterm_list(env, coords_seq, GEOSGetNumCoordinates(inner)); } coords = enif_make_list_from_array(env, rings, inner_num+1); free(rings); return coords; }
static shapeObj *msGEOSGeometry2Shape_polygon(GEOSGeom g) { shapeObj *shape=NULL; lineObj line; int numPoints, numRings; int i, j; GEOSCoordSeq coords; GEOSGeom ring; if(!g) return NULL; shape = (shapeObj *) malloc(sizeof(shapeObj)); msInitShape(shape); shape->type = MS_SHAPE_POLYGON; shape->geometry = (GEOSGeom) g; /* exterior ring */ ring = (GEOSGeom) GEOSGetExteriorRing(g); numPoints = GEOSGetNumCoordinates(ring); coords = (GEOSCoordSeq) GEOSGeom_getCoordSeq(ring); line.point = (pointObj *) malloc(sizeof(pointObj)*numPoints); line.numpoints = numPoints; for(i=0; i<numPoints; i++) { GEOSCoordSeq_getX(coords, i, &(line.point[i].x)); GEOSCoordSeq_getY(coords, i, &(line.point[i].y)); /* GEOSCoordSeq_getZ(coords, i, &(line.point[i].z)); */ } msAddLineDirectly(shape, &line); /* interior rings */ numRings = GEOSGetNumInteriorRings(g); for(j=0; j<numRings; j++) { ring = (GEOSGeom) GEOSGetInteriorRingN(g, j); if(GEOSisRing(ring) != 1) continue; /* skip it */ numPoints = GEOSGetNumCoordinates(ring); coords = (GEOSCoordSeq) GEOSGeom_getCoordSeq(ring); line.point = (pointObj *) malloc(sizeof(pointObj)*numPoints); line.numpoints = numPoints; for(i=0; i<numPoints; i++) { GEOSCoordSeq_getX(coords, i, &(line.point[i].x)); GEOSCoordSeq_getY(coords, i, &(line.point[i].y)); /* GEOSCoordSeq_getZ(coords, i, &(line.point[i].z)); */ } msAddLineDirectly(shape, &line); } msComputeBounds(shape); return shape; }
static shapeObj *msGEOSGeometry2Shape_line(GEOSGeom g) { shapeObj *shape=NULL; int i; int numPoints; GEOSCoordSeq coords; if(!g) return NULL; numPoints = GEOSGetNumCoordinates(g); coords = (GEOSCoordSeq) GEOSGeom_getCoordSeq(g); shape = (shapeObj *) malloc(sizeof(shapeObj)); msInitShape(shape); shape->type = MS_SHAPE_LINE; shape->line = (lineObj *) malloc(sizeof(lineObj)); shape->numlines = 1; shape->line[0].point = (pointObj *) malloc(sizeof(pointObj)*numPoints); shape->line[0].numpoints = numPoints; shape->geometry = (GEOSGeom) g; for(i=0; i<numPoints; i++) { GEOSCoordSeq_getX(coords, i, &(shape->line[0].point[i].x)); GEOSCoordSeq_getY(coords, i, &(shape->line[0].point[i].y)); /* GEOSCoordSeq_getZ(coords, i, &(shape->line[0].point[i].z)); */ } msComputeBounds(shape); return shape; }
static int ring2pts(const GEOSGeometry *geom, struct line_pnts *Points) { int i, ncoords; double x, y, z; const GEOSCoordSequence *seq = NULL; G_debug(3, "ring2pts()"); Vect_reset_line(Points); if (!geom) { G_warning(_("Invalid GEOS geometry!")); return 0; } z = 0.0; ncoords = GEOSGetNumCoordinates(geom); if (!ncoords) { G_warning(_("No coordinates in GEOS geometry (can be ok for negative distance)!")); return 0; } seq = GEOSGeom_getCoordSeq(geom); for (i = 0; i < ncoords; i++) { GEOSCoordSeq_getX(seq, i, &x); GEOSCoordSeq_getY(seq, i, &y); if (x != x || x > DBL_MAX || x < -DBL_MAX) G_fatal_error(_("Invalid x coordinate %f"), x); if (y != y || y > DBL_MAX || y < -DBL_MAX) G_fatal_error(_("Invalid y coordinate %f"), y); Vect_append_point(Points, x, y, z); } return 1; }
ERL_NIF_TERM geom_to_eterm_linestring_coords(ErlNifEnv *env, const GEOSGeometry *geom) { const GEOSCoordSequence *coords_seq; coords_seq = GEOSGeom_getCoordSeq(geom); return GEOSCoordSequence_to_eterm_list(env, coords_seq, GEOSGetNumCoordinates(geom)); }
void geo_points(sqlite3_context *context,int argc,sqlite3_value **argv) { if(argc == 1 && sqlite3_value_type(argv[0]) == SQLITE_BLOB) { GEOSGeometry* geometry; const void* data = sqlite3_value_blob(argv[0]); size_t data_size = sqlite3_value_bytes(argv[0]); _init_geos(); geometry = _geo_from_wkb((const unsigned char*)data,data_size); if(geometry != 0) { int num_points = GEOSGetNumCoordinates(geometry); sqlite3_result_int(context,num_points); } GEOSGeom_destroy(geometry); finishGEOS(); } }
static shapeObj *msGEOSGeometry2Shape_multiline(GEOSGeom g) { int i, j; int numPoints, numLines; GEOSCoordSeq coords; GEOSGeom lineString; shapeObj *shape=NULL; lineObj line; if(!g) return NULL; numLines = GEOSGetNumGeometries(g); shape = (shapeObj *) malloc(sizeof(shapeObj)); msInitShape(shape); shape->type = MS_SHAPE_LINE; shape->geometry = (GEOSGeom) g; for(j=0; j<numLines; j++) { lineString = (GEOSGeom) GEOSGetGeometryN(g, j); numPoints = GEOSGetNumCoordinates(lineString); coords = (GEOSCoordSeq) GEOSGeom_getCoordSeq(lineString); line.point = (pointObj *) malloc(sizeof(pointObj)*numPoints); line.numpoints = numPoints; for(i=0; i<numPoints; i++) { GEOSCoordSeq_getX(coords, i, &(line.point[i].x)); GEOSCoordSeq_getY(coords, i, &(line.point[i].y)); /* GEOSCoordSeq_getZ(coords, i, &(line.point[i].z)); */ } msAddLineDirectly(shape, &line); } msComputeBounds(shape); return shape; }