From 4cb56a6b11ee0d0769b1672943e60ea98a613827 Mon Sep 17 00:00:00 2001 From: Eric Fischer Date: Mon, 27 Oct 2014 12:56:51 -0700 Subject: [PATCH] The indexing side of buffering features at the edges of tiles --- geojson.c | 42 ++++++++++++++++++++++++++++++++---------- tile.cc | 4 ++++ tile.h | 1 + 3 files changed, 37 insertions(+), 10 deletions(-) diff --git a/geojson.c b/geojson.c index a2f63dd9..3fd22e7e 100644 --- a/geojson.c +++ b/geojson.c @@ -342,6 +342,7 @@ void read_json(FILE *f, char *fname, char *layername, int maxzoom, int minzoom, } int z = maxzoom; + int buffer = 10; unsigned cx = bbox[0] / 2 + bbox[2] / 2; unsigned cy = bbox[1] / 2 + bbox[3] / 2; @@ -353,18 +354,39 @@ void read_json(FILE *f, char *fname, char *layername, int maxzoom, int minzoom, ix.fpos = start; fwrite_check(&ix, sizeof(struct index), 1, indexfile, fname, jp); } else { - unsigned x, y; - for (x = bbox[0] >> (32 - z); x <= bbox[2] >> (32 - z); x++) { - for (y = bbox[1] >> (32 - z); y <= bbox[3] >> (32 - z); y++) { - struct index ix; + for (z = maxzoom; z >= 1; z--) { + unsigned x, y; + for (x = (bbox[0] - (buffer << (32 - z - 8))) >> (32 - z); x <= (bbox[2] + (buffer << (32 - z - 8))) >> (32 - z); x++) { + for (y = (bbox[1] - (buffer << (32 - z - 8))) >> (32 - z); y <= (bbox[3] + (buffer << (32 - z - 8))) >> (32 - z); y++) { + if (z != maxzoom) { + // There must be a clearer way to write this, but the intent is + // not to add an additional index for a low-zoom tile + // if one of its children was already part of the + // buffered bounding box for the child's zoom. - if (x == cx >> (32 - z) && y == cy >> (32 - z)) { - ix.index = encode(cx, cy); - } else { - ix.index = encode(x << (32 - z), y << (32 - z)); + // So we are comparing this tile's x and y to the edges of the + // bounding box at the next zoom down, but divided by two + // to get it back into this zoom's tile coordinate scheme + + if ((x >= ((bbox[0] - (buffer << (32 - (z + 1) - 8))) >> (32 - (z + 1)) >> 1)) && + (x <= ((bbox[2] + (buffer << (32 - (z + 1) - 8))) >> (32 - (z + 1)) >> 1)) && + (y >= ((bbox[1] - (buffer << (32 - (z + 1) - 8))) >> (32 - (z + 1)) >> 1)) && + (y <= ((bbox[3] + (buffer << (32 - (z + 1) - 8))) >> (32 - (z + 1)) >> 1))) { + continue; + } + } + + struct index ix; + + if (x == cx >> (32 - z) && y == cy >> (32 - z)) { + ix.index = encode(cx, cy); + } else { + ix.index = encode(x << (32 - z), y << (32 - z)); + } + ix.fpos = start; + ix.maxzoom = z; + fwrite_check(&ix, sizeof(struct index), 1, indexfile, fname, jp); } - ix.fpos = start; - fwrite_check(&ix, sizeof(struct index), 1, indexfile, fname, jp); } } } diff --git a/tile.cc b/tile.cc index 41dff855..ae4023ea 100644 --- a/tile.cc +++ b/tile.cc @@ -366,6 +366,10 @@ long long write_tile(struct index *start, struct index *end, char *metabase, uns struct index *i; for (i = start; i < end; i++) { + if (z > i->maxzoom) { + continue; + } + struct pool_val *pv = pool_long_long(&dup, &i->fpos, 0); if (pv->n == 0) { continue; diff --git a/tile.h b/tile.h index cb4a5be6..f1d7d736 100644 --- a/tile.h +++ b/tile.h @@ -20,6 +20,7 @@ struct pool_val *deserialize_string(char **f, struct pool *p, int type); struct index { unsigned long long index; long long fpos; + int maxzoom; }; long long write_tile(struct index *start, struct index *end, char *metabase, unsigned *file_bbox, int z, unsigned x, unsigned y, int detail, int basezoom, struct pool *file_keys, char *layername, sqlite3 *outdb, double droprate);