From dceb4c2e48e2c94f52141d777015435fe7b2587e Mon Sep 17 00:00:00 2001 From: Victor Berchet Date: Mon, 26 Jun 2023 05:04:23 -0700 Subject: [PATCH] fix(grid): max zoom (#677) --- src/algorithms/core.ts | 2 ++ src/algorithms/grid.test.ts | 21 +++++++++++++++------ src/algorithms/grid.ts | 7 +++---- src/algorithms/supercluster.ts | 4 +--- 4 files changed, 21 insertions(+), 13 deletions(-) diff --git a/src/algorithms/core.ts b/src/algorithms/core.ts index 8c43169b..2dc1971c 100644 --- a/src/algorithms/core.ts +++ b/src/algorithms/core.ts @@ -57,8 +57,10 @@ export interface Algorithm { } export interface AlgorithmOptions { + // Markers are not clustered at maxZoom and above. maxZoom?: number; } + /** * @hidden */ diff --git a/src/algorithms/grid.test.ts b/src/algorithms/grid.test.ts index 6013a82e..37c29e4f 100644 --- a/src/algorithms/grid.test.ts +++ b/src/algorithms/grid.test.ts @@ -16,7 +16,6 @@ import { GridAlgorithm } from "./grid"; import { initialize, MapCanvasProjection } from "@googlemaps/jest-mocks"; -import { Marker } from "../marker-utils"; initialize(); const markers = [ @@ -35,7 +34,7 @@ describe.each(markers)( test("calculate should return changed: true for first call when zoom > max zoom", () => { const mapCanvasProjection = new MapCanvasProjection(); - const markers: Marker[] = [marker]; + const markers = [marker]; const grid = new GridAlgorithm({ maxZoom: 16 }); grid["noop"] = jest.fn(); @@ -60,10 +59,10 @@ describe.each(markers)( expect(changed).toBe(true); }); - test("calculate should return changed: false for next calls above max zoom", () => { + test("calculate should return changed: false when zoom doesn't change", () => { const mapCanvasProjection = jest.fn() as unknown as google.maps.MapCanvasProjection; - const markers: Marker[] = [marker]; + const markers = [marker]; const grid = new GridAlgorithm({ maxZoom: 16 }); grid["noop"] = jest.fn(); @@ -87,10 +86,10 @@ describe.each(markers)( expect(result.changed).toBe(false); }); - test("calculate should return changed: false for next calls above max zoom, even if zoom changed", () => { + test("calculate should return changed: false for next calls at or above max zoom, even if zoom changed", () => { const mapCanvasProjection = jest.fn() as unknown as google.maps.MapCanvasProjection; - const markers: Marker[] = [marker]; + const markers = [marker]; const grid = new GridAlgorithm({ maxZoom: 16 }); grid["noop"] = jest.fn(); @@ -114,6 +113,16 @@ describe.each(markers)( }); expect(result.changed).toBe(false); + + map.getZoom = jest.fn().mockReturnValue(16); + + result = grid.calculate({ + markers, + map, + mapCanvasProjection, + }); + + expect(result.changed).toBe(false); }); } ); diff --git a/src/algorithms/grid.ts b/src/algorithms/grid.ts index 2d196fde..6757f55f 100644 --- a/src/algorithms/grid.ts +++ b/src/algorithms/grid.ts @@ -50,14 +50,13 @@ export class GridAlgorithm extends AbstractViewportAlgorithm { protected gridSize: number; protected maxDistance: number; protected clusters: Cluster[] = []; - protected state: { zoom: number }; + protected state = { zoom: -1 }; constructor({ maxDistance = 40000, gridSize = 40, ...options }: GridOptions) { super(options); this.maxDistance = maxDistance; this.gridSize = gridSize; - this.state = { zoom: null }; } public calculate({ @@ -67,8 +66,8 @@ export class GridAlgorithm extends AbstractViewportAlgorithm { }: AlgorithmInput): AlgorithmOutput { const state = { zoom: map.getZoom() }; let changed = false; - if (this.state.zoom > this.maxZoom && state.zoom > this.maxZoom) { - // still beyond maxZoom, no change + if (this.state.zoom >= this.maxZoom && state.zoom >= this.maxZoom) { + // still at or beyond maxZoom, no change } else { changed = !equal(this.state, state); } diff --git a/src/algorithms/supercluster.ts b/src/algorithms/supercluster.ts index 488b117f..75336882 100644 --- a/src/algorithms/supercluster.ts +++ b/src/algorithms/supercluster.ts @@ -36,7 +36,7 @@ export class SuperClusterAlgorithm extends AbstractAlgorithm { protected superCluster: SuperCluster; protected markers: Marker[]; protected clusters: Cluster[]; - protected state: { zoom: number | null }; + protected state = { zoom: -1 }; constructor({ maxZoom, radius = 60, ...options }: SuperClusterOptions) { super({ maxZoom }); @@ -46,8 +46,6 @@ export class SuperClusterAlgorithm extends AbstractAlgorithm { radius, ...options, }); - - this.state = { zoom: null }; } public calculate(input: AlgorithmInput): AlgorithmOutput {