Add blacklist of ids to geojson source in order to avoid duplicate features to be loaded multiple times
This commit is contained in:
parent
fdcda66e5c
commit
36d62f9923
2 changed files with 28 additions and 2 deletions
|
@ -21,14 +21,26 @@ export default class GeoJsonSource implements FeatureSourceForLayer, Tiled {
|
||||||
public readonly tileIndex
|
public readonly tileIndex
|
||||||
public readonly bbox;
|
public readonly bbox;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Only used if the actual source is a tiled geojson.
|
||||||
|
* A big feature might be contained in multiple tiles.
|
||||||
|
* However, we only want to load them once. The blacklist thus contains all ids of all features previously seen
|
||||||
|
* @private
|
||||||
|
*/
|
||||||
|
private readonly featureIdBlacklist?: UIEventSource<Set<string>>
|
||||||
|
|
||||||
public constructor(flayer: FilteredLayer,
|
public constructor(flayer: FilteredLayer,
|
||||||
zxy?: [number, number, number]) {
|
zxy?: [number, number, number],
|
||||||
|
options?: {
|
||||||
|
featureIdBlacklist?: UIEventSource<Set<string>>
|
||||||
|
}) {
|
||||||
|
|
||||||
if (flayer.layerDef.source.geojsonZoomLevel !== undefined && zxy === undefined) {
|
if (flayer.layerDef.source.geojsonZoomLevel !== undefined && zxy === undefined) {
|
||||||
throw "Dynamic layers are not supported. Use 'DynamicGeoJsonTileSource instead"
|
throw "Dynamic layers are not supported. Use 'DynamicGeoJsonTileSource instead"
|
||||||
}
|
}
|
||||||
|
|
||||||
this.layer = flayer;
|
this.layer = flayer;
|
||||||
|
this.featureIdBlacklist = options?.featureIdBlacklist
|
||||||
let url = flayer.layerDef.source.geojsonSource.replace("{layer}", flayer.layerDef.id);
|
let url = flayer.layerDef.source.geojsonSource.replace("{layer}", flayer.layerDef.id);
|
||||||
if (zxy !== undefined) {
|
if (zxy !== undefined) {
|
||||||
const [z, x, y] = zxy;
|
const [z, x, y] = zxy;
|
||||||
|
@ -68,6 +80,7 @@ export default class GeoJsonSource implements FeatureSourceForLayer, Tiled {
|
||||||
const props = feature.properties
|
const props = feature.properties
|
||||||
for (const key in props) {
|
for (const key in props) {
|
||||||
if (typeof props[key] !== "string") {
|
if (typeof props[key] !== "string") {
|
||||||
|
// Make sure all the values are string, it crashes stuff otherwise
|
||||||
props[key] = "" + props[key]
|
props[key] = "" + props[key]
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -82,6 +95,10 @@ export default class GeoJsonSource implements FeatureSourceForLayer, Tiled {
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
self.seenids.add(props.id)
|
self.seenids.add(props.id)
|
||||||
|
|
||||||
|
if(self.featureIdBlacklist?.data?.has(props.id)){
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
let freshness: Date = time;
|
let freshness: Date = time;
|
||||||
if (feature.properties["_last_edit:timestamp"] !== undefined) {
|
if (feature.properties["_last_edit:timestamp"] !== undefined) {
|
||||||
|
|
|
@ -37,6 +37,8 @@ export default class DynamicGeoJsonTileSource extends DynamicTileSource {
|
||||||
console.warn("No whitelist found for ", layer.layerDef.id, err)
|
console.warn("No whitelist found for ", layer.layerDef.id, err)
|
||||||
})
|
})
|
||||||
|
|
||||||
|
const seenIds = new Set<string>();
|
||||||
|
const blackList = new UIEventSource(seenIds)
|
||||||
super(
|
super(
|
||||||
layer,
|
layer,
|
||||||
source.geojsonZoomLevel,
|
source.geojsonZoomLevel,
|
||||||
|
@ -50,8 +52,15 @@ export default class DynamicGeoJsonTileSource extends DynamicTileSource {
|
||||||
|
|
||||||
const src = new GeoJsonSource(
|
const src = new GeoJsonSource(
|
||||||
layer,
|
layer,
|
||||||
zxy
|
zxy,
|
||||||
|
{
|
||||||
|
featureIdBlacklist: blackList
|
||||||
|
}
|
||||||
)
|
)
|
||||||
|
src.features.addCallbackAndRunD(feats => {
|
||||||
|
feats.forEach(feat => seenIds.add(feat.feature.properties.id))
|
||||||
|
blackList.ping();
|
||||||
|
})
|
||||||
registerLayer(src)
|
registerLayer(src)
|
||||||
return src
|
return src
|
||||||
},
|
},
|
||||||
|
|
Loading…
Reference in a new issue