[GRASS-SVN] r48960 - grass/trunk/lib/vector/Vlib
svn_grass at osgeo.org
svn_grass at osgeo.org
Thu Oct 27 07:16:52 EDT 2011
Author: martinl
Date: 2011-10-27 04:16:51 -0700 (Thu, 27 Oct 2011)
New Revision: 48960
Modified:
grass/trunk/lib/vector/Vlib/build_ogr.c
Log:
vlib: Vect_build_ogr() support other build levels
Modified: grass/trunk/lib/vector/Vlib/build_ogr.c
===================================================================
--- grass/trunk/lib/vector/Vlib/build_ogr.c 2011-10-27 11:16:02 UTC (rev 48959)
+++ grass/trunk/lib/vector/Vlib/build_ogr.c 2011-10-27 11:16:51 UTC (rev 48960)
@@ -161,7 +161,7 @@
/*!
\brief Recursively add geometry to topology
*/
-static int add_geometry(struct Map_info *Map, OGRGeometryH hGeom, int FID,
+static int add_geometry(struct Map_info *Map, OGRGeometryH hGeom, int FID, int build,
GEOM_PARTS * parts)
{
struct Plus_head *plus;
@@ -244,11 +244,14 @@
line = add_line(Map, GV_BOUNDARY, Points[iPart], FID, parts);
del_part(parts);
+ if (build < GV_BUILD_AREAS)
+ continue;
+
/* add area (each inner ring is also area) */
dig_line_box(Points[iPart], &box);
dig_find_area_poly(Points[iPart], &area_size);
- if (area_size > 0) /* clockwise */
+ if (area_size > 0) /* area clockwise */
lines[0] = line;
else
lines[0] = -line;
@@ -260,6 +263,9 @@
isle = dig_add_isle(plus, 1, lines, &box);
+ if (build < GV_BUILD_ATTACH_ISLES)
+ continue;
+
if (iPart == 0) { /* outer ring */
outer_area = area;
}
@@ -272,32 +278,34 @@
dig_area_add_isle(plus, outer_area, isle);
}
}
-
- /* create virtual centroid */
- ret = Vect_get_point_in_poly_isl((const struct line_pnts *) Points[0],
- (const struct line_pnts **) Points + 1,
- nRings - 1, &x, &y);
- if (ret < -1) {
- G_warning(_("Unable to calculate centroid for area %d"),
- outer_area);
+
+ if (build >= GV_BUILD_CENTROIDS) {
+ /* create virtual centroid */
+ ret = Vect_get_point_in_poly_isl((const struct line_pnts *) Points[0],
+ (const struct line_pnts **) Points + 1,
+ nRings - 1, &x, &y);
+ if (ret < -1) {
+ G_warning(_("Unable to calculate centroid for area %d"),
+ outer_area);
+ }
+ else {
+ struct P_area *Area;
+ struct P_topo_c *topo;
+
+ G_debug(4, " Centroid: %f, %f", x, y);
+ Vect_reset_line(Points[0]);
+ Vect_append_point(Points[0], x, y, 0.0);
+ line = add_line(Map, GV_CENTROID, Points[0], FID, parts);
+
+ Line = plus->Line[line];
+ topo = (struct P_topo_c *)Line->topo;
+ topo->area = outer_area;
+
+ /* register centroid to area */
+ Area = plus->Area[outer_area];
+ Area->centroid = line;
+ }
}
- else {
- struct P_area *Area;
- struct P_topo_c *topo;
-
- G_debug(4, " Centroid: %f, %f", x, y);
- Vect_reset_line(Points[0]);
- Vect_append_point(Points[0], x, y, 0.0);
- line = add_line(Map, GV_CENTROID, Points[0], FID, parts);
-
- Line = plus->Line[line];
- topo = (struct P_topo_c *)Line->topo;
- topo->area = outer_area;
-
- /* register centroid to area */
- Area = plus->Area[outer_area];
- Area->centroid = line;
- }
break;
case wkbMultiPoint:
@@ -309,7 +317,7 @@
for (i = 0; i < nParts; i++) {
add_part(parts, i);
hGeom2 = OGR_G_GetGeometryRef(hGeom, i);
- add_geometry(Map, hGeom2, FID, parts);
+ add_geometry(Map, hGeom2, FID, build, parts);
del_part(parts);
}
break;
@@ -325,16 +333,24 @@
/*!
\brief Build pseudo-topology for OGR layer
+ Build levels:
+ - GV_BUILD_NONE
+ - GV_BUILD_BASE
+ - GV_BUILD_ATTACH_ISLES
+ - GV_BUILD_CENTROIDS
+ - GV_BUILD_ALL
+
\param Map pointer to Map_info structure
- \param build build level (GV_BUILD_NONE and GV_BUILD_ALL currently supported)
+ \param build build level
\return 1 on success
\return 0 on error
*/
int Vect_build_ogr(struct Map_info *Map, int build)
{
- int iFeature, count, FID;
+ int iFeature, FID, line;
struct Plus_head *plus;
+ struct P_line *Line;
GEOM_PARTS parts;
OGRFeatureH hFeature;
@@ -343,21 +359,17 @@
G_debug(1, "Vect_build_ogr(): dsn=%s layer=%s, build=%d",
Map->fInfo.ogr.dsn, Map->fInfo.ogr.layer_name, build);
- if (build != GV_BUILD_ALL && build != GV_BUILD_NONE) {
- G_warning(_("Partial build for OGR is not supported"));
- return 0;
- }
-
plus = &(Map->plus);
if (build == plus->built)
return 1; /* do nothing */
/* TODO move this init to better place (Vect_open_ ?), because in theory build may be reused on level2 */
- G_free((void *) Map->fInfo.ogr.offset);
- Map->fInfo.ogr.offset = NULL;
- Map->fInfo.ogr.offset_num = 0;
- Map->fInfo.ogr.offset_alloc = 0;
-
+ if (build >= plus->built && build > GV_BUILD_BASE) {
+ G_free((void *) Map->fInfo.ogr.offset);
+ Map->fInfo.ogr.offset = NULL;
+ Map->fInfo.ogr.offset_num = 0;
+ Map->fInfo.ogr.offset_alloc = 0;
+ }
if (!Map->fInfo.ogr.layer) {
G_warning(_("Empty OGR layer, nothing to build"));
return 0;
@@ -382,52 +394,87 @@
/* Check if upgrade or downgrade */
if (build < plus->built) { /* lower level request, currently only GV_BUILD_NONE */
- dig_free_plus_areas(plus);
- dig_spidx_free_areas(plus);
- dig_free_plus_isles(plus);
- dig_spidx_free_isles(plus);
+ if (plus->built >= GV_BUILD_CENTROIDS && build < GV_BUILD_CENTROIDS) {
+ /* reset info about areas stored for centroids */
+ int nlines = Vect_get_num_lines(Map);
+
+ for (line = 1; line <= nlines; line++) {
+ Line = plus->Line[line];
+ if (Line && Line->type == GV_CENTROID) {
+ struct P_topo_c *topo = (struct P_topo_c *)Line->topo;
+ topo->area = 0;
+ }
+ }
+ dig_free_plus_areas(plus);
+ dig_spidx_free_areas(plus);
+ dig_free_plus_isles(plus);
+ dig_spidx_free_isles(plus);
+ }
- dig_free_plus_nodes(plus);
- dig_spidx_free_nodes(plus);
- dig_free_plus_lines(plus);
- dig_spidx_free_lines(plus);
+ if (plus->built >= GV_BUILD_AREAS && build < GV_BUILD_AREAS) {
+ /* reset info about areas stored for lines */
+ int nlines = Vect_get_num_lines(Map);
+
+ for (line = 1; line <= nlines; line++) {
+ Line = plus->Line[line];
+ if (Line && Line->type == GV_BOUNDARY) {
+ struct P_topo_b *topo = (struct P_topo_b *)Line->topo;
+ topo->left = 0;
+ topo->right = 0;
+ }
+ }
+ dig_free_plus_areas(plus);
+ dig_spidx_free_areas(plus);
+ dig_free_plus_isles(plus);
+ dig_spidx_free_isles(plus);
+ }
+
+ if (plus->built >= GV_BUILD_BASE && build < GV_BUILD_BASE) {
+ dig_free_plus_nodes(plus);
+ dig_spidx_free_nodes(plus);
+ dig_free_plus_lines(plus);
+ dig_spidx_free_lines(plus);
+ }
}
else {
- /* Note: Do not use OGR_L_GetFeatureCount (it may scan all features) */
- OGR_L_ResetReading(Map->fInfo.ogr.layer);
- count = iFeature = 0;
- while ((hFeature = OGR_L_GetNextFeature(Map->fInfo.ogr.layer)) != NULL) {
- iFeature++;
- count++;
-
- G_debug(3, " Feature %d", iFeature);
-
- hGeom = OGR_F_GetGeometryRef(hFeature);
- if (hGeom == NULL) {
- G_warning(_("Feature %d without geometry ignored"), iFeature);
+ if (plus->built < GV_BUILD_BASE) {
+ /* Note: Do not use OGR_L_GetFeatureCount (it may scan all features) */
+ OGR_L_ResetReading(Map->fInfo.ogr.layer);
+ iFeature = 0;
+ while ((hFeature = OGR_L_GetNextFeature(Map->fInfo.ogr.layer)) != NULL) {
+ iFeature++;
+
+ G_debug(3, " Feature %d", iFeature);
+
+ hGeom = OGR_F_GetGeometryRef(hFeature);
+ if (hGeom == NULL) {
+ G_warning(_("Feature %d without geometry ignored"), iFeature);
+ OGR_F_Destroy(hFeature);
+ continue;
+ }
+
+ FID = (int)OGR_F_GetFID(hFeature);
+ if (FID == OGRNullFID) {
+ G_warning(_("OGR feature %d without ID ignored"), iFeature);
+ OGR_F_Destroy(hFeature);
+ continue;
+ }
+ G_debug(4, " FID = %d", FID);
+
+ reset_parts(&parts);
+ add_part(&parts, FID);
+ add_geometry(Map, hGeom, FID, build, &parts);
+
OGR_F_Destroy(hFeature);
- continue;
- }
+ } /* while */
- FID = (int)OGR_F_GetFID(hFeature);
- if (FID == OGRNullFID) {
- G_warning(_("OGR feature %d without ID ignored"), iFeature);
- OGR_F_Destroy(hFeature);
- continue;
- }
- G_debug(4, " FID = %d", FID);
-
- reset_parts(&parts);
- add_part(&parts, FID);
- add_geometry(Map, hGeom, FID, &parts);
-
- OGR_F_Destroy(hFeature);
- } /* while */
+ plus->built = GV_BUILD_BASE;
+ }
}
free_parts(&parts);
- Map->plus.built = build;
+ plus->built = build;
return 1;
}
More information about the grass-commit
mailing list