Move the per-node attributes from coordinates to a parallel array

This commit is contained in:
Eric Fischer 2018-08-30 15:18:54 -07:00
parent cf902bf3ab
commit 09f76cdf2a
5 changed files with 69 additions and 30 deletions

View File

@ -65,6 +65,11 @@ int serialize_geojson_feature(struct serialization_state *sst, json_object *geom
return 0;
}
json_object *attributes = json_hash_get(geometry, "attributes");
if (attributes != NULL && attributes->type != JSON_ARRAY) {
attributes = NULL;
}
int t;
for (t = 0; t < GEOM_TYPES; t++) {
if (strcmp(geometry_type->string, geometry_names[t]) == 0) {
@ -175,7 +180,26 @@ int serialize_geojson_feature(struct serialization_state *sst, json_object *geom
}
drawvec dv;
parse_geometry(t, coordinates, dv, VT_MOVETO, sst->fname, sst->line, feature);
parse_geometry(t, coordinates, dv, VT_MOVETO, sst->fname, sst->line, feature, false);
if (attributes != NULL) {
drawvec dv2;
parse_geometry(t, attributes, dv2, VT_MOVETO, sst->fname, sst->line, feature, true);
if (dv2.size() != dv.size()) {
fprintf(stderr, "Geometry attributes don't match coordinates\n");
exit(EXIT_FAILURE);
}
for (size_t i = 0; i < dv2.size(); i++) {
if (dv[i].op != dv2[i].op) {
fprintf(stderr, "Geometry attributes don't match coordinates\n");
exit(EXIT_FAILURE);
}
dv[i].attributes = dv2[i].attributes;
}
}
serial_feature sf;
sf.layer = layer;

View File

@ -186,7 +186,8 @@ std::vector<mvt_layer> parse_layers(int fd, int z, unsigned x, unsigned y, std::
auto l = ret.find(layername);
drawvec dv;
parse_geometry(t, coordinates, dv, VT_MOVETO, "Filter output", jp->line, j);
parse_geometry(t, coordinates, dv, VT_MOVETO, "Filter output", jp->line, j, false);
// XXX do node attributes
if (mb_geometry[t] == VT_POLYGON) {
dv = fix_polygon(dv);
}
@ -376,7 +377,8 @@ serial_feature parse_feature(json_pull *jp, int z, unsigned x, unsigned y, std::
}
drawvec dv;
parse_geometry(t, coordinates, dv, VT_MOVETO, "Filter output", jp->line, j);
parse_geometry(t, coordinates, dv, VT_MOVETO, "Filter output", jp->line, j, false);
// XXX do node attributes
if (mb_geometry[t] == VT_POLYGON) {
dv = fix_polygon(dv);
}

View File

@ -41,15 +41,15 @@ void json_context(json_object *j) {
free(s); // stringify
}
void parse_geometry(int t, json_object *j, drawvec &out, int op, const char *fname, int line, json_object *feature) {
if (j == NULL || j->type != JSON_ARRAY) {
fprintf(stderr, "%s:%d: expected array for type %d\n", fname, line, t);
json_context(feature);
return;
}
void parse_geometry(int t, json_object *j, drawvec &out, int op, const char *fname, int line, json_object *feature, bool doing_attributes) {
int within = geometry_within[t];
if (within >= 0) {
if (j == NULL || j->type != JSON_ARRAY) {
fprintf(stderr, "%s:%d: expected array for coordinate container %d\n", fname, line, t);
json_context(feature);
return;
}
size_t i;
for (i = 0; i < j->length; i++) {
if (within == GEOM_POINT) {
@ -60,10 +60,30 @@ void parse_geometry(int t, json_object *j, drawvec &out, int op, const char *fna
}
}
parse_geometry(within, j->array[i], out, op, fname, line, feature);
parse_geometry(within, j->array[i], out, op, fname, line, feature, doing_attributes);
}
} else {
if (j->length >= 2 && j->array[0]->type == JSON_NUMBER && j->array[1]->type == JSON_NUMBER) {
if (doing_attributes) {
draw d(op, 0, 0);
if (j != NULL && j->type == JSON_HASH) {
char *s = json_stringify(j);
d.attributes = std::string(s);
free(s); // stringify
} else {
fprintf(stderr, "%s:%d: malformed point attribute\n", fname, line);
json_context(j);
json_context(feature);
}
out.push_back(d);
} else if (j->length >= 2 && j->array[0]->type == JSON_NUMBER && j->array[1]->type == JSON_NUMBER) {
if (j == NULL || j->type != JSON_ARRAY) {
fprintf(stderr, "%s:%d: expected array for coordinate pair %d\n", fname, line, t);
json_context(feature);
return;
}
long long x, y;
double lon = j->array[0]->number;
double lat = j->array[1]->number;
@ -86,13 +106,6 @@ void parse_geometry(int t, json_object *j, drawvec &out, int op, const char *fna
if (j->array[i]->type == JSON_NUMBER) {
d.elevations.push_back(j->array[i]->number);
}
// XXX Reconcile with GeoJSON
if (j->array[i]->type == JSON_HASH) {
char *s = json_stringify(j->array[i]);
d.attributes = std::string(s);
free(s); // stringify
}
}
out.push_back(d);

View File

@ -11,6 +11,6 @@ extern int geometry_within[GEOM_TYPES];
extern int mb_geometry[GEOM_TYPES];
void json_context(json_object *j);
void parse_geometry(int t, json_object *j, drawvec &out, int op, const char *fname, int line, json_object *feature);
void parse_geometry(int t, json_object *j, drawvec &out, int op, const char *fname, int line, json_object *feature, bool doing_attributes);
void stringify_value(json_object *value, int &type, std::string &stringified, const char *reading, int line, json_object *feature);

File diff suppressed because one or more lines are too long