Add an option to specify the clustering distance directly

This commit is contained in:
Eric Fischer 2017-12-20 17:31:11 -08:00
parent fc32a0e897
commit aaf08a6c55
7 changed files with 7705 additions and 3 deletions

View File

@ -204,6 +204,7 @@ tippecanoe -z5 -o filtered.mbtiles -j '{ "ne_10m_admin_0_countries": [ "all", [
compensate for the larger marker, or `-Bf`*number* to allow at most *number* features in the densest tile.
* `-al` or `--drop-lines`: Let "dot" dropping at lower zooms apply to lines too
* `-ap` or `--drop-polygons`: Let "dot" dropping at lower zooms apply to polygons too
* `-K` _distance_ or `--cluster-distance=`_distance_: Cluster points (as with `--cluster-densest-as-needed`, but without the experimental discovery process) that are approximately within _distance_ of each other. The units are tile coordinates within a nominally 256-pixel tile, so the maximum value of 255 allows only one feature per tile. Values around 20 are probably appropriate for typical marker sizes.
### Dropping a fraction of features to keep under tile size limits

View File

@ -69,6 +69,7 @@ int geometry_scale = 0;
double simplification = 1;
size_t max_tile_size = 500000;
size_t max_tile_features = 200000;
int cluster_distance = 0;
int prevent[256];
int additional[256];
@ -2271,6 +2272,7 @@ int main(int argc, char **argv) {
{"base-zoom", required_argument, 0, 'B'},
{"drop-lines", no_argument, &additional[A_LINE_DROP], 1},
{"drop-polygons", no_argument, &additional[A_POLYGON_DROP], 1},
{"cluster-distance", required_argument, 0, 'K'},
{"Dropping a fraction of features to keep under tile size limits", 0, 0, 0},
{"drop-densest-as-needed", no_argument, &additional[A_DROP_DENSEST_AS_NEEDED], 1},
@ -2449,6 +2451,14 @@ int main(int argc, char **argv) {
}
break;
case 'K':
cluster_distance = atoi(optarg);
if (cluster_distance > 255) {
fprintf(stderr, "%s: --cluster-distance %d is too big; limit is 255\n", argv[0], cluster_distance);
exit(EXIT_FAILURE);
}
break;
case 'd':
full_detail = atoi(optarg);
break;

View File

@ -28,6 +28,7 @@ extern size_t TEMP_FILES;
extern size_t max_tile_size;
extern size_t max_tile_features;
extern int cluster_distance;
int mkstemp_cloexec(char *name);
FILE *fopen_oflag(const char *name, const char *mode, int oflag);

View File

@ -233,6 +233,8 @@ compensate for the larger marker, or \fB\fC\-Bf\fR\fInumber\fP to allow at most
\fB\fC\-al\fR or \fB\fC\-\-drop\-lines\fR: Let "dot" dropping at lower zooms apply to lines too
.IP \(bu 2
\fB\fC\-ap\fR or \fB\fC\-\-drop\-polygons\fR: Let "dot" dropping at lower zooms apply to polygons too
.IP \(bu 2
\fB\fC\-K\fR \fIdistance\fP or \fB\fC\-\-cluster\-distance=\fR\fIdistance\fP: Cluster points (as with \fB\fC\-\-cluster\-densest\-as\-needed\fR, but without the experimental discovery process) that are approximately within \fIdistance\fP of each other. The units are tile coordinates within a nominally 256\-pixel tile, so the maximum value of 255 allows only one feature per tile. Values around 20 are probably appropriate for typical marker sizes.
.RE
.SS Dropping a fraction of features to keep under tile size limits
.RS

View File

@ -487,7 +487,7 @@ int serialize_feature(struct serialization_state *sst, serial_feature &sf) {
long long midy = (sf.bbox[1] / 2 + sf.bbox[3] / 2) & ((1LL << 32) - 1);
bbox_index = encode(midx, midy);
if (additional[A_DROP_DENSEST_AS_NEEDED] || additional[A_CLUSTER_DENSEST_AS_NEEDED] || additional[A_CALCULATE_FEATURE_DENSITY] || additional[A_INCREASE_GAMMA_AS_NEEDED] || sst->uses_gamma) {
if (additional[A_DROP_DENSEST_AS_NEEDED] || additional[A_CLUSTER_DENSEST_AS_NEEDED] || additional[A_CALCULATE_FEATURE_DENSITY] || additional[A_INCREASE_GAMMA_AS_NEEDED] || sst->uses_gamma || cluster_distance != 0) {
sf.index = bbox_index;
} else {
sf.index = 0;

7688
tests/muni/out/-r1_-K20.json Normal file

File diff suppressed because it is too large Load Diff

View File

@ -1569,7 +1569,7 @@ long long write_tile(FILE *geoms, long long *geompos_in, char *metabase, char *s
}
}
if (additional[A_CLUSTER_DENSEST_AS_NEEDED]) {
if (additional[A_CLUSTER_DENSEST_AS_NEEDED] || cluster_distance != 0) {
indices.push_back(sf.index);
if (sf.index - merge_previndex < mingap) {
clustered++;
@ -2420,7 +2420,7 @@ int traverse_zooms(int *geomfd, off_t *geom_size, char *metabase, char *stringpo
}
double zoom_gamma = gamma;
unsigned long long zoom_mingap = 0;
unsigned long long zoom_mingap = ((1LL << (32 - i)) / 256 * cluster_distance) * ((1LL << (32 - i)) / 256 * cluster_distance);
long long zoom_minextent = 0;
double zoom_fraction = 1;