From b7e5990aa906d076110712bee824a7ad5e5f86d4 Mon Sep 17 00:00:00 2001 From: Joost Date: Tue, 12 Oct 2021 09:10:49 +0200 Subject: [PATCH 1/8] Changed "quest" to "theme" Because nowhere else do we call themes quests --- langs/en.json | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/langs/en.json b/langs/en.json index 9282ad4465..5a4854db70 100644 --- a/langs/en.json +++ b/langs/en.json @@ -120,7 +120,7 @@ }, "morescreen": { "intro": "

More thematic maps?

Do you enjoy collecting geodata?
There are more themes available.", - "requestATheme": "If you want a custom-built quest, request it in the issue tracker", + "requestATheme": "If you want a custom-built theme, request it in the issue tracker", "streetcomplete": "Another, similar application is StreetComplete.", "createYourOwnTheme": "Create your own MapComplete theme from scratch" }, @@ -247,4 +247,4 @@ "attribution": "Reviews are powered by Mangrove Reviews and are available under CC-BY 4.0.", "plz_login": "Login to leave a review" } -} \ No newline at end of file +} From e530eba55ab9c278d35a7f283d099cd556fc6efc Mon Sep 17 00:00:00 2001 From: pietervdvn Date: Tue, 12 Oct 2021 16:39:36 +0200 Subject: [PATCH 2/8] Quickfix: disable optimazation which blocks loading dynamic tiles --- .../TiledFeatureSource/DynamicGeoJsonTileSource.ts | 3 ++- assets/themes/natuurpunt/natuurpunt.json | 2 +- index.ts | 3 +++ 3 files changed, 6 insertions(+), 2 deletions(-) diff --git a/Logic/FeatureSource/TiledFeatureSource/DynamicGeoJsonTileSource.ts b/Logic/FeatureSource/TiledFeatureSource/DynamicGeoJsonTileSource.ts index fcfdbea5a4..c2ccf518d8 100644 --- a/Logic/FeatureSource/TiledFeatureSource/DynamicGeoJsonTileSource.ts +++ b/Logic/FeatureSource/TiledFeatureSource/DynamicGeoJsonTileSource.ts @@ -46,7 +46,8 @@ export default class DynamicGeoJsonTileSource extends DynamicTileSource { if(whitelist !== undefined){ const isWhiteListed = whitelist.get(zxy[1])?.has(zxy[2]) if(!isWhiteListed){ - return undefined; + console.log("Not whitelisted:",zxy, isWhiteListed, whitelist) + // return undefined; } } diff --git a/assets/themes/natuurpunt/natuurpunt.json b/assets/themes/natuurpunt/natuurpunt.json index 4b49e7465f..fb45742cae 100644 --- a/assets/themes/natuurpunt/natuurpunt.json +++ b/assets/themes/natuurpunt/natuurpunt.json @@ -34,7 +34,7 @@ "hideFromOverview": true, "clustering": { "#": "Disable clustering for this theme", - "maxZoom": 0 + "maxZoom": 1 }, "layers": [ { diff --git a/index.ts b/index.ts index e5e58a6f0a..dc738eaf4f 100644 --- a/index.ts +++ b/index.ts @@ -63,6 +63,9 @@ if (path !== "index.html" && path !== "") { defaultLayout = QueryParameters.GetQueryParameter("layout", defaultLayout, "The layout to load into MapComplete").data; let layoutToUse: LayoutConfig = AllKnownLayouts.allKnownLayouts.get(defaultLayout.toLowerCase()); +if(layoutToUse.id === "natuurpunt"){ + localStorage.clear() +} const userLayoutParam = QueryParameters.GetQueryParameter("userlayout", "false", "If not 'false', a custom (non-official) theme is loaded. This custom layout can be done in multiple ways: \n\n- The hash of the URL contains a base64-encoded .json-file containing the theme definition\n- The hash of the URL contains a lz-compressed .json-file, as generated by the custom theme generator\n- The parameter itself is an URL, in which case that URL will be downloaded. It should point to a .json of a theme"); From e5a24ff499e04e874edd32b8da07359ac5f81294 Mon Sep 17 00:00:00 2001 From: pietervdvn Date: Tue, 12 Oct 2021 19:11:48 +0200 Subject: [PATCH 3/8] Fix build --- index.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/index.ts b/index.ts index dc738eaf4f..3bfa4f28b9 100644 --- a/index.ts +++ b/index.ts @@ -63,7 +63,7 @@ if (path !== "index.html" && path !== "") { defaultLayout = QueryParameters.GetQueryParameter("layout", defaultLayout, "The layout to load into MapComplete").data; let layoutToUse: LayoutConfig = AllKnownLayouts.allKnownLayouts.get(defaultLayout.toLowerCase()); -if(layoutToUse.id === "natuurpunt"){ +if(layoutToUse?.id === "natuurpunt"){ localStorage.clear() } From 2bcc573f2a148952b9c997ec7683956682da371f Mon Sep 17 00:00:00 2001 From: pietervdvn Date: Tue, 12 Oct 2021 19:11:59 +0200 Subject: [PATCH 4/8] Fix build --- index.ts | 4 ---- 1 file changed, 4 deletions(-) diff --git a/index.ts b/index.ts index 3bfa4f28b9..7126a0a7cc 100644 --- a/index.ts +++ b/index.ts @@ -63,10 +63,6 @@ if (path !== "index.html" && path !== "") { defaultLayout = QueryParameters.GetQueryParameter("layout", defaultLayout, "The layout to load into MapComplete").data; let layoutToUse: LayoutConfig = AllKnownLayouts.allKnownLayouts.get(defaultLayout.toLowerCase()); -if(layoutToUse?.id === "natuurpunt"){ - localStorage.clear() -} - const userLayoutParam = QueryParameters.GetQueryParameter("userlayout", "false", "If not 'false', a custom (non-official) theme is loaded. This custom layout can be done in multiple ways: \n\n- The hash of the URL contains a base64-encoded .json-file containing the theme definition\n- The hash of the URL contains a lz-compressed .json-file, as generated by the custom theme generator\n- The parameter itself is an URL, in which case that URL will be downloaded. It should point to a .json of a theme"); // Workaround/legacy to keep the old paramters working as I renamed some of them From 8bdabe5d73447a2e32208230e90917f588762af9 Mon Sep 17 00:00:00 2001 From: pietervdvn Date: Wed, 13 Oct 2021 00:08:41 +0200 Subject: [PATCH 5/8] Fixes to caching --- .../DynamicGeoJsonTileSource.ts | 4 +- scripts/generateCache.ts | 40 +++++++++++++------ 2 files changed, 31 insertions(+), 13 deletions(-) diff --git a/Logic/FeatureSource/TiledFeatureSource/DynamicGeoJsonTileSource.ts b/Logic/FeatureSource/TiledFeatureSource/DynamicGeoJsonTileSource.ts index c2ccf518d8..fc110e1c2c 100644 --- a/Logic/FeatureSource/TiledFeatureSource/DynamicGeoJsonTileSource.ts +++ b/Logic/FeatureSource/TiledFeatureSource/DynamicGeoJsonTileSource.ts @@ -21,7 +21,9 @@ export default class DynamicGeoJsonTileSource extends DynamicTileSource { throw "Invalid layer: geojsonSource expected" } - const whitelistUrl = source.geojsonSource.replace("{z}_{x}_{y}.geojson", "overview.json") + const whitelistUrl = source.geojsonSource + .replace("{z}", ""+source.geojsonZoomLevel) + .replace("{x}_{y}.geojson", "overview.json") .replace("{layer}",layer.layerDef.id) let whitelist = undefined diff --git a/scripts/generateCache.ts b/scripts/generateCache.ts index 1377b3153e..d92fc86288 100644 --- a/scripts/generateCache.ts +++ b/scripts/generateCache.ts @@ -20,6 +20,7 @@ import FeatureSource, {FeatureSourceForLayer} from "../Logic/FeatureSource/Featu import StaticFeatureSource from "../Logic/FeatureSource/Sources/StaticFeatureSource"; import TiledFeatureSource from "../Logic/FeatureSource/TiledFeatureSource/TiledFeatureSource"; import Constants from "../Models/Constants"; +import {GeoOperations} from "../Logic/GeoOperations"; ScriptUtils.fixUtils() @@ -170,11 +171,11 @@ function loadAllTiles(targetdir: string, r: TileRange, theme: LayoutConfig, extr /** * Load all the tiles into memory from disk */ -function postProcess(allFeatures: FeatureSource, theme: LayoutConfig, relationsTracker: RelationsTracker, targetdir: string) { - - +function sliceToTiles(allFeatures: FeatureSource, theme: LayoutConfig, relationsTracker: RelationsTracker, targetdir: string, pointsOnlyLayers: string[]) { function handleLayer(source: FeatureSourceForLayer) { const layer = source.layer.layerDef; + const targetZoomLevel = layer.source.geojsonZoomLevel ?? 0 + const layerId = layer.id if (layer.source.isOsmCacheLayer !== true) { return; @@ -200,13 +201,10 @@ function postProcess(allFeatures: FeatureSource, theme: LayoutConfig, relationsT // At this point, we have all the features of the entire area. // However, we want to export them per tile of a fixed size, so we use a dynamicTileSOurce to split it up TiledFeatureSource.createHierarchy(source, { - minZoomLevel: 14, - maxZoomLevel: 14, + minZoomLevel: targetZoomLevel, + maxZoomLevel: targetZoomLevel, maxFeatureCount: undefined, registerTile: tile => { - if (tile.z < 12) { - return; - } if (tile.features.data.length === 0) { return } @@ -229,7 +227,7 @@ function postProcess(allFeatures: FeatureSource, theme: LayoutConfig, relationsT // All the tiles are written at this point // Only thing left to do is to create the index - const path = targetdir + "_" + layerId + "_overview.json" + const path = targetdir + "_" + layerId + "_" + targetZoomLevel + "_overview.json" const perX = {} createdTiles.map(i => Tiles.tile_from_index(i)).forEach(([z, x, y]) => { const key = "" + x @@ -240,7 +238,18 @@ function postProcess(allFeatures: FeatureSource, theme: LayoutConfig, relationsT }) writeFileSync(path, JSON.stringify(perX)) - + // And, if needed, to create a points-only layer + if(pointsOnlyLayers.indexOf(layer.id) >= 0){ + const features = source.features.data.map(f => f.feature) + const points = features.map(feature => GeoOperations.centerpoint(feature)) + console.log("Writing points overview for ", layerId) + const targetPath = targetdir+"_"+layerId+"_points.geojson" + // This is the geojson file containing all features for this tile + writeFileSync(targetPath, JSON.stringify({ + type: "FeatureCollection", + features: points + }, null, " ")) + } } new PerLayerFeatureSourceSplitter( @@ -255,10 +264,11 @@ function postProcess(allFeatures: FeatureSource, theme: LayoutConfig, relationsT } + async function main(args: string[]) { if (args.length == 0) { - console.error("Expected arguments are: theme zoomlevel targetdirectory lat0 lon0 lat1 lon1 [--generate-point-overview layer-name]") + console.error("Expected arguments are: theme zoomlevel targetdirectory lat0 lon0 lat1 lon1 [--generate-point-overview layer-name,layer-name,...]") return; } const themeName = args[0] @@ -268,6 +278,12 @@ async function main(args: string[]) { const lon0 = Number(args[4]) const lat1 = Number(args[5]) const lon1 = Number(args[6]) + + let generatePointLayersFor = [] + if(args[7] == "--generate-point-overview"){ + generatePointLayersFor = args[8].split(",") + } + const tileRange = Tiles.TileRangeBetween(zoomlevel, lat0, lon0, lat1, lon1) @@ -293,7 +309,7 @@ async function main(args: string[]) { const extraFeatures = await downloadExtraData(theme); const allFeaturesSource = loadAllTiles(targetdir, tileRange, theme, extraFeatures) - postProcess(allFeaturesSource, theme, relationTracker, targetdir) + sliceToTiles(allFeaturesSource, theme, relationTracker, targetdir, generatePointLayersFor) } From 9e7dec010163d11c17ba4370ec8da119b34e21b8 Mon Sep 17 00:00:00 2001 From: pietervdvn Date: Wed, 13 Oct 2021 00:43:19 +0200 Subject: [PATCH 6/8] Add toggle to disable squares on low zoom levels, fix maxzoom property --- InitUiElements.ts | 32 ++++++++++++--------- Models/ThemeConfig/Json/LayoutConfigJson.ts | 8 +++++- Models/ThemeConfig/LayoutConfig.ts | 11 ++++--- UI/ShowDataLayer/TileHierarchyAggregator.ts | 11 +++++-- assets/themes/natuurpunt/natuurpunt.json | 5 ++-- 5 files changed, 43 insertions(+), 24 deletions(-) diff --git a/InitUiElements.ts b/InitUiElements.ts index e7113e2d68..59f56b849f 100644 --- a/InitUiElements.ts +++ b/InitUiElements.ts @@ -423,13 +423,13 @@ export class InitUiElements { flayers.push(flayer); } state.filteredLayers = new UIEventSource(flayers); - - + + const clustering = State.state.layoutToUse.clustering const clusterCounter = TileHierarchyAggregator.createHierarchy() new ShowDataLayer({ - features: clusterCounter.getCountsForZoom(State.state.locationControl, State.state.layoutToUse.clustering.minNeededElements), + features: clusterCounter.getCountsForZoom(clustering, State.state.locationControl, State.state.layoutToUse.clustering.minNeededElements), leafletMap: State.state.leafletMap, layerToShow: ShowTileInfo.styling, enablePopups: false @@ -440,7 +440,7 @@ export class InitUiElements { clusterCounter.addTile(source) - const clustering = State.state.layoutToUse.clustering + // Do show features indicates if the 'showDataLayer' should be shown const doShowFeatures = source.features.map( f => { const z = State.state.locationControl.data.zoom @@ -449,6 +449,18 @@ export class InitUiElements { return false; } + const bounds = State.state.currentBounds.data + if(bounds === undefined){ + // Map is not yet displayed + return false; + } + + if (!source.bbox.overlapsWith(bounds)) { + // Not within range -> features are hidden + return false + } + + if (z < source.layer.layerDef.minzoom) { // Layer is always hidden for this zoom level return false; @@ -473,21 +485,13 @@ export class InitUiElements { } if (clusterCounter.getTile(Tiles.tile_index(tileZ, tileX, tileY))?.totalValue > clustering.minNeededElements) { + // To much elements return false } } - const bounds = State.state.currentBounds.data - if(bounds === undefined){ - // Map is not yet displayed - return false; - } - if (!source.bbox.overlapsWith(bounds)) { - // Not within range - return false - } - + return true }, [State.state.currentBounds, source.layer.isDisplayed] ) diff --git a/Models/ThemeConfig/Json/LayoutConfigJson.ts b/Models/ThemeConfig/Json/LayoutConfigJson.ts index 89439f529b..64d6be83e2 100644 --- a/Models/ThemeConfig/Json/LayoutConfigJson.ts +++ b/Models/ThemeConfig/Json/LayoutConfigJson.ts @@ -237,6 +237,12 @@ export interface LayoutConfigJson { * If clustering is defined, defaults to 25 */ minNeededElements?: number + /** + * By default, a box is shown indicating the number of features even if the map is zoomed out beyond the minzoom of the layer. + * This flag switches this behaviour to not show these boxes. + */ + hideClustersAboveMinZoom?: boolean; + }, /** @@ -253,7 +259,7 @@ export interface LayoutConfigJson { * If set to [[lat0, lon0], [lat1, lon1]], the map will not scroll outside of those bounds. * Off by default, which will enable panning to the entire world */ - lockLocation?: boolean | [[number, number], [number, number]]; + lockLocation?: boolean | [[number, number], [number, number]] | number[][]; enableUserBadge?: boolean; enableShareScreen?: boolean; diff --git a/Models/ThemeConfig/LayoutConfig.ts b/Models/ThemeConfig/LayoutConfig.ts index 9add1c7f92..fbfc924f7c 100644 --- a/Models/ThemeConfig/LayoutConfig.ts +++ b/Models/ThemeConfig/LayoutConfig.ts @@ -30,7 +30,8 @@ export default class LayoutConfig { public layers: LayerConfig[]; public readonly clustering?: { maxZoom: number, - minNeededElements: number + minNeededElements: number, + hideClustersAboveMinzoom: boolean }; public readonly hideFromOverview: boolean; public lockLocation: boolean | [[number, number], [number, number]]; @@ -139,12 +140,14 @@ export default class LayoutConfig { this.clustering = { maxZoom: 16, - minNeededElements: 25 + minNeededElements: 25, + hideClustersAboveMinzoom: false }; if (json.clustering) { this.clustering = { maxZoom: json.clustering.maxZoom ?? 18, - minNeededElements: json.clustering.minNeededElements ?? 25 + minNeededElements: json.clustering.minNeededElements ?? 25, + hideClustersAboveMinzoom: json.clustering.hideClustersAboveMinZoom ?? false } } @@ -153,7 +156,7 @@ export default class LayoutConfig { if (json.hideInOverview) { throw "The json for " + this.id + " contains a 'hideInOverview'. Did you mean hideFromOverview instead?" } - this.lockLocation = json.lockLocation ?? undefined; + this.lockLocation = <[[number, number], [number, number]]> json.lockLocation ?? undefined; this.enableUserBadge = json.enableUserBadge ?? true; this.enableShareScreen = json.enableShareScreen ?? true; this.enableMoreQuests = json.enableMoreQuests ?? true; diff --git a/UI/ShowDataLayer/TileHierarchyAggregator.ts b/UI/ShowDataLayer/TileHierarchyAggregator.ts index 4b1685981d..e1d934a95e 100644 --- a/UI/ShowDataLayer/TileHierarchyAggregator.ts +++ b/UI/ShowDataLayer/TileHierarchyAggregator.ts @@ -153,13 +153,18 @@ export class TileHierarchyAggregator implements FeatureSource { } } - getCountsForZoom(locationControl: UIEventSource<{ zoom : number }>, cutoff: number = 0) : FeatureSource{ + getCountsForZoom(clusteringConfig: {maxZoom: number}, locationControl: UIEventSource<{ zoom : number }>, cutoff: number = 0) : FeatureSource{ const self = this - + const empty = [] return new StaticFeatureSource( locationControl.map(loc => { - const features = [] const targetZoom = loc.zoom + + if(targetZoom > clusteringConfig.maxZoom){ + return empty + } + + const features = [] self.visitSubTiles(aggr => { if(aggr.totalValue < cutoff) { return false diff --git a/assets/themes/natuurpunt/natuurpunt.json b/assets/themes/natuurpunt/natuurpunt.json index fb45742cae..0090eb2373 100644 --- a/assets/themes/natuurpunt/natuurpunt.json +++ b/assets/themes/natuurpunt/natuurpunt.json @@ -34,7 +34,8 @@ "hideFromOverview": true, "clustering": { "#": "Disable clustering for this theme", - "maxZoom": 1 + "maxZoom": 1, + "hideBoxesAboveMinZoom": true }, "layers": [ { @@ -109,7 +110,7 @@ ] }, "geoJson": "https://pietervdvn.github.io/natuurpunt_cache/natuurpunt_{layer}_{z}_{x}_{y}.geojson", - "geoJsonZoomLevel": 12, + "geoJsonZoomLevel": 10, "isOsmCache": true }, "minzoom": "13", From 8f674b7976fca2b8db70040c93b2ec09d9a7255d Mon Sep 17 00:00:00 2001 From: pietervdvn Date: Wed, 13 Oct 2021 01:28:20 +0200 Subject: [PATCH 7/8] Improvents to caching script --- scripts/generateCache.ts | 9 +++++++-- 1 file changed, 7 insertions(+), 2 deletions(-) diff --git a/scripts/generateCache.ts b/scripts/generateCache.ts index d92fc86288..c7fc2f04be 100644 --- a/scripts/generateCache.ts +++ b/scripts/generateCache.ts @@ -74,6 +74,7 @@ async function downloadRaw(targetdir: string, r: TileRange, theme: LayoutConfig, let downloaded = 0 let failed = 0 let skipped = 0 + const startTime = new Date().getTime() for (let x = r.xstart; x <= r.xend; x++) { for (let y = r.ystart; y <= r.yend; y++) { downloaded++; @@ -83,7 +84,11 @@ async function downloadRaw(targetdir: string, r: TileRange, theme: LayoutConfig, skipped++ continue; } - console.log("x:", (x - r.xstart), "/", (r.xend - r.xstart), "; y:", (y - r.ystart), "/", (r.yend - r.ystart), "; total: ", downloaded, "/", r.total, "failed: ", failed, "skipped: ", skipped) + const runningSeconds = (new Date().getTime() - startTime) / 1000 + const resting = failed + (r.total - downloaded) + const perTile= (runningSeconds / (downloaded - skipped)) + const estimated =Math.floor(resting * perTile) + console.log("total: ", downloaded, "/", r.total, "failed: ", failed, "skipped: ", skipped, "running time: ",Utils.toHumanTime(runningSeconds)+"s", "estimated left: ", Utils.toHumanTime(estimated), "("+Math.floor(perTile)+"s/tile)") const boundsArr = Tiles.tile_bounds(r.zoomlevel, x, y) const bounds = { @@ -92,7 +97,7 @@ async function downloadRaw(targetdir: string, r: TileRange, theme: LayoutConfig, east: Math.max(boundsArr[0][1], boundsArr[1][1]), west: Math.min(boundsArr[0][1], boundsArr[1][1]) } - const overpass = createOverpassObject(theme, relationTracker, Constants.defaultOverpassUrls[(downloaded + failed) % Constants.defaultOverpassUrls.length]) + const overpass = createOverpassObject(theme, relationTracker, Constants.defaultOverpassUrls[(failed) % Constants.defaultOverpassUrls.length]) const url = overpass.buildQuery("[bbox:" + bounds.south + "," + bounds.west + "," + bounds.north + "," + bounds.east + "]") try { From adb36c2ffe2509784e484ab1d08a573595ed4d76 Mon Sep 17 00:00:00 2001 From: pietervdvn Date: Wed, 13 Oct 2021 01:28:46 +0200 Subject: [PATCH 8/8] Cluster styling tweaks, tweaks to NP --- Models/ThemeConfig/Json/LayoutConfigJson.ts | 7 ----- Models/ThemeConfig/LayoutConfig.ts | 10 ++++--- UI/ShowDataLayer/TileHierarchyAggregator.ts | 6 +++-- Utils.ts | 26 ++++++++++--------- .../layers/cluster_style/cluster_style.json | 4 +-- assets/themes/natuurpunt/natuurpunt.json | 9 +++---- 6 files changed, 30 insertions(+), 32 deletions(-) diff --git a/Models/ThemeConfig/Json/LayoutConfigJson.ts b/Models/ThemeConfig/Json/LayoutConfigJson.ts index 64d6be83e2..408bc10098 100644 --- a/Models/ThemeConfig/Json/LayoutConfigJson.ts +++ b/Models/ThemeConfig/Json/LayoutConfigJson.ts @@ -1,6 +1,5 @@ import {TagRenderingConfigJson} from "./TagRenderingConfigJson"; import {LayerConfigJson} from "./LayerConfigJson"; -import UnitConfigJson from "./UnitConfigJson"; /** * Defines the entire theme. @@ -237,12 +236,6 @@ export interface LayoutConfigJson { * If clustering is defined, defaults to 25 */ minNeededElements?: number - /** - * By default, a box is shown indicating the number of features even if the map is zoomed out beyond the minzoom of the layer. - * This flag switches this behaviour to not show these boxes. - */ - hideClustersAboveMinZoom?: boolean; - }, /** diff --git a/Models/ThemeConfig/LayoutConfig.ts b/Models/ThemeConfig/LayoutConfig.ts index fbfc924f7c..a06e329523 100644 --- a/Models/ThemeConfig/LayoutConfig.ts +++ b/Models/ThemeConfig/LayoutConfig.ts @@ -31,7 +31,6 @@ export default class LayoutConfig { public readonly clustering?: { maxZoom: number, minNeededElements: number, - hideClustersAboveMinzoom: boolean }; public readonly hideFromOverview: boolean; public lockLocation: boolean | [[number, number], [number, number]]; @@ -141,13 +140,16 @@ export default class LayoutConfig { this.clustering = { maxZoom: 16, minNeededElements: 25, - hideClustersAboveMinzoom: false }; - if (json.clustering) { + if(json.clustering === false){ + this.clustering = { + maxZoom: 0, + minNeededElements: 100000, + }; + }else if (json.clustering) { this.clustering = { maxZoom: json.clustering.maxZoom ?? 18, minNeededElements: json.clustering.minNeededElements ?? 25, - hideClustersAboveMinzoom: json.clustering.hideClustersAboveMinZoom ?? false } } diff --git a/UI/ShowDataLayer/TileHierarchyAggregator.ts b/UI/ShowDataLayer/TileHierarchyAggregator.ts index e1d934a95e..cdaa5e4206 100644 --- a/UI/ShowDataLayer/TileHierarchyAggregator.ts +++ b/UI/ShowDataLayer/TileHierarchyAggregator.ts @@ -22,7 +22,7 @@ export class TileHierarchyAggregator implements FeatureSource { public readonly name; private readonly featuresStatic = [] - private readonly featureProperties: { count: string, tileId: string, id: string }; + private readonly featureProperties: { count: string, kilocount: string, tileId: string, id: string }; private constructor(parent: TileHierarchyAggregator, z: number, x: number, y: number) { this._parent = parent; @@ -36,7 +36,8 @@ export class TileHierarchyAggregator implements FeatureSource { const totals = { id: ""+this._tileIndex, tileId: ""+this._tileIndex, - count: ""+0 + count: `0`, + kilocount: "0" } this.featureProperties = totals @@ -108,6 +109,7 @@ export class TileHierarchyAggregator implements FeatureSource { this.features.setData(TileHierarchyAggregator.empty) } else { this.featureProperties.count = "" + total; + this.featureProperties.kilocount = "" +Math.floor(total/1000); this.features.data = this.featuresStatic this.features.ping() } diff --git a/Utils.ts b/Utils.ts index 5c04c95472..0d88048c46 100644 --- a/Utils.ts +++ b/Utils.ts @@ -78,18 +78,6 @@ export class Utils { return res; } - static DoEvery(millis: number, f: (() => void)) { - if (Utils.runningFromConsole) { - return; - } - window.setTimeout( - function () { - f(); - Utils.DoEvery(millis, f); - } - , millis) - } - public static NoNull(array: T[]): T[] { const ls: T[] = []; for (const t of array) { @@ -440,5 +428,19 @@ export class Utils { window.setTimeout(resolve, timeMillis); }) } + + public static toHumanTime(seconds): string{ + seconds = Math.floor(seconds) + let minutes = Math.floor(seconds / 60) + seconds = seconds % 60 + let hours = Math.floor(minutes / 60) + minutes = minutes % 60 + let days = Math.floor(hours / 24) + hours = hours % 24 + if(days > 0){ + return days+"days"+" "+hours+"h" + } + return hours+":"+Utils.TwoDigits(minutes)+":"+Utils.TwoDigits(seconds) + } } diff --git a/assets/layers/cluster_style/cluster_style.json b/assets/layers/cluster_style/cluster_style.json index d6b68d1133..982baa79bb 100644 --- a/assets/layers/cluster_style/cluster_style.json +++ b/assets/layers/cluster_style/cluster_style.json @@ -28,8 +28,8 @@ "render": "
{count}
", "mappings": [ { - "if": "count>99", - "then": "
>99
" + "if": "count>1000", + "then": "
{kilocount}K
" } ] } diff --git a/assets/themes/natuurpunt/natuurpunt.json b/assets/themes/natuurpunt/natuurpunt.json index 0090eb2373..54effec905 100644 --- a/assets/themes/natuurpunt/natuurpunt.json +++ b/assets/themes/natuurpunt/natuurpunt.json @@ -32,10 +32,9 @@ "enablePdfDownload": true, "enableDownload": true, "hideFromOverview": true, - "clustering": { "#": "Disable clustering for this theme", - "maxZoom": 1, - "hideBoxesAboveMinZoom": true + "clustering": { + "maxZoom": 0 }, "layers": [ { @@ -110,10 +109,10 @@ ] }, "geoJson": "https://pietervdvn.github.io/natuurpunt_cache/natuurpunt_{layer}_{z}_{x}_{y}.geojson", - "geoJsonZoomLevel": 10, + "geoJsonZoomLevel": 12, "isOsmCache": true }, - "minzoom": "13", + "minzoom": 10, "icon": { "render": "circle:#FE6F32;./assets/themes/natuurpunt/trail.svg", "mappings": [