From 89890c8acb2e5c88eae84195cc382b68511feb6c Mon Sep 17 00:00:00 2001 From: Dominik Moritz Date: Wed, 12 Sep 2012 01:52:58 +0100 Subject: [PATCH] automatically enable clustering if there is a large number of markers --- README.md | 2 ++ src/view.map.js | 31 +++++++++++++++++++------------ test/view.map.test.js | 7 ++----- 3 files changed, 23 insertions(+), 17 deletions(-) diff --git a/README.md b/README.md index 90967c07..284a5b67 100755 --- a/README.md +++ b/README.md @@ -42,6 +42,8 @@ For larger changes: Possible breaking changes +* Updated Leaflet to latest version 0.4.4 #220 +* Added marker clustering in map view to handle a large number of markers * Dataset.restore method removed (not used internally except from Multiview.restore) * Views no longer call render in initialize but must be called client code diff --git a/src/view.map.js b/src/view.map.js index 97a25fea..9f3e90d3 100644 --- a/src/view.map.js +++ b/src/view.map.js @@ -54,7 +54,7 @@ my.Map = Backbone.View.extend({ lonField: null, latField: null, autoZoom: true, - cluster: true + cluster: false }, options.state ); @@ -156,6 +156,13 @@ my.Map = Backbone.View.extend({ } if (this._geomReady() && this.mapReady){ + // removing ad re-adding the layer enables faster bulk loading + this.map.removeLayer(this.features); + this.map.removeLayer(this.markers); + + var countBefore = 0; + this.features.eachLayer(function(){countBefore++;}); + if (action == 'refresh' || action == 'reset') { this.features.clearLayers(); // recreate cluster group because of issues with clearLayer @@ -167,6 +174,16 @@ my.Map = Backbone.View.extend({ } else if (action == 'remove' && doc){ this._remove(doc); } + + // enable clustering if there is a large number of markers + var countAfter = 0; + this.features.eachLayer(function(){countAfter++;}); + var sizeIncreased = countAfter - countBefore > 0; + if (!this.state.get('cluster') && countAfter > 100 && sizeIncreased) { + this.state.set({cluster: true}); + return; + } + if (this.state.get('autoZoom')){ if (this.visible){ this._zoomToFeatures(); @@ -174,8 +191,6 @@ my.Map = Backbone.View.extend({ this._zoomPending = true; } } - this.map.removeLayer(this.features); - this.map.removeLayer(this.markers); if (this.state.get('cluster')) { this.map.addLayer(this.markers); } else { @@ -218,9 +233,6 @@ my.Map = Backbone.View.extend({ if (!(docs instanceof Array)) docs = [docs]; - // removing ad re-adding the layer enables faster bulk loading - self.map.removeLayer(self.markers); - var count = 0; var wrongSoFar = 0; _.every(docs, function(doc){ @@ -259,8 +271,6 @@ my.Map = Backbone.View.extend({ } return true; }); - - self.map.addLayer(self.markers); }, // Private: Remove one or n features from the map @@ -394,9 +404,6 @@ my.Map = Backbone.View.extend({ this.markers = new L.MarkerClusterGroup(this._clusterOptions); - m = this.map; - l = this.markers; - this.features = new L.GeoJSON(null,{ pointToLayer: function (feature, latlng) { var marker = new L.marker(latlng); @@ -479,7 +486,7 @@ my.MapMenu = Backbone.View.extend({ \ Auto zoom to features \ \ \ \ diff --git a/test/view.map.test.js b/test/view.map.test.js index 23c9ea1d..f1865a56 100644 --- a/test/view.map.test.js +++ b/test/view.map.test.js @@ -54,7 +54,7 @@ test('_setupGeometryField', function () { lonField: 'lon', latField: 'lat', autoZoom: true, - cluster: true + cluster: false }; deepEqual(view.state.toJSON(), exp); deepEqual(view.menu.state.toJSON(), exp); @@ -165,10 +165,7 @@ test('Popup', function () { test('Popup - Custom', function () { var dataset = GeoJSONFixture.getDataset(); var view = new recline.View.Map({ - model: dataset, - state: { - cluster: false - } + model: dataset }); $('.fixtures').append(view.el); view.infobox = function(record) {