@mytec: iter10.3.1 ready for testing

This commit is contained in:
2026-01-30 18:24:45 +02:00
parent 12b5c89355
commit 176df9ddaf
3 changed files with 24 additions and 5 deletions

View File

@@ -380,6 +380,7 @@ export default function App() {
visible={heatmapVisible}
opacity={settings.heatmapOpacity}
radiusMeters={settings.heatmapRadius}
rsrpThreshold={settings.rsrpThreshold}
/>
<CoverageBoundary
points={coverageResult.points}

View File

@@ -24,6 +24,7 @@ interface GeographicHeatmapProps {
visible: boolean;
opacity?: number;
radiusMeters?: number;
rsrpThreshold?: number;
}
export default function GeographicHeatmap({
@@ -31,6 +32,7 @@ export default function GeographicHeatmap({
visible,
opacity = 0.7,
radiusMeters = 400,
rsrpThreshold = -100,
}: GeographicHeatmapProps) {
const map = useMap();
const layerRef = useRef<L.GridLayer | null>(null);
@@ -53,7 +55,12 @@ export default function GeographicHeatmap({
rendererRef.current.setRadiusMeters(radiusMeters);
}, [radiusMeters]);
// Invalidate cache when points change (use length + first/last coords as fingerprint)
// Update renderer threshold when prop changes
useEffect(() => {
rendererRef.current.setRsrpThreshold(rsrpThreshold);
}, [rsrpThreshold]);
// Invalidate cache when points or threshold change
useEffect(() => {
if (points.length === 0) {
rendererRef.current.setPointsHash('empty');
@@ -61,9 +68,9 @@ export default function GeographicHeatmap({
}
const first = points[0];
const last = points[points.length - 1];
const hash = `${points.length}:${first.lat.toFixed(4)},${first.lon.toFixed(4)}:${last.rsrp}`;
const hash = `${points.length}:${first.lat.toFixed(4)},${first.lon.toFixed(4)}:${last.rsrp}:t${rsrpThreshold}`;
rendererRef.current.setPointsHash(hash);
}, [points]);
}, [points, rsrpThreshold]);
// Create / destroy GridLayer
const createLayer = useCallback(() => {

View File

@@ -34,6 +34,7 @@ export interface HeatmapPoint {
export class HeatmapTileRenderer {
private tileSize = 256;
private radiusMeters: number;
private rsrpThreshold: number;
// LRU cache: key → canvas
private cache = new Map<string, ImageData>();
@@ -42,9 +43,10 @@ export class HeatmapTileRenderer {
// Points fingerprint for cache invalidation
private pointsHash = '';
constructor(radiusMeters = 400, maxCacheSize = 150) {
constructor(radiusMeters = 400, maxCacheSize = 150, rsrpThreshold = -100) {
this.radiusMeters = radiusMeters;
this.maxCacheSize = maxCacheSize;
this.rsrpThreshold = rsrpThreshold;
}
/** Update the geographic radius of each coverage point. */
@@ -55,6 +57,14 @@ export class HeatmapTileRenderer {
}
}
/** Update the RSRP threshold — points below this are not rendered. */
setRsrpThreshold(threshold: number): void {
if (threshold !== this.rsrpThreshold) {
this.rsrpThreshold = threshold;
this.clearCache();
}
}
/** Call when points change to invalidate cache. */
setPointsHash(hash: string): void {
if (hash !== this.pointsHash) {
@@ -105,9 +115,10 @@ export class HeatmapTileRenderer {
// still contribute their gaussian tail inside the tile
const bufferDeg = (this.radiusMeters / 111_000) * 2;
// Filter relevant points
// Filter relevant points — geographic bounds AND RSRP threshold
const relevant = points.filter(
(p) =>
p.rsrp >= this.rsrpThreshold &&
p.lat >= latMin - bufferDeg &&
p.lat <= latMax + bufferDeg &&
p.lon >= lonMin - bufferDeg &&