From dcf67f1aef555e0c214c2b6f904cf09a28d1c012 Mon Sep 17 00:00:00 2001 From: Tom Harvey Date: Thu, 24 Nov 2016 00:50:44 +0000 Subject: [PATCH] #43 Patch to fix intensity/altitude issue (auto max) This patch works by automatically setting the max as it changes on each zoom level as points get combined/separated. You no longer need to manually set options.max When calculating the max value it considers all points (even if they are off the screen). This way you always get the same results at a particular zoom level. Thanks to @spacemansteve for pointing me in the right direction ca1f43026545f7e413c653e376b1fa8bf3a2b6a6 --- src/HeatLayer.js | 57 ++++++++++++++++++++++++------------------------ 1 file changed, 28 insertions(+), 29 deletions(-) diff --git a/src/HeatLayer.js b/src/HeatLayer.js index 9c020da..93ea22a 100644 --- a/src/HeatLayer.js +++ b/src/HeatLayer.js @@ -104,9 +104,6 @@ L.HeatLayer = (L.Layer ? L.Layer : L.Class).extend({ if (this.options.gradient) { this._heat.gradient(this.options.gradient); } - if (this.options.max) { - this._heat.max(this.options.max); - } }, _reset: function () { @@ -135,52 +132,54 @@ L.HeatLayer = (L.Layer ? L.Layer : L.Class).extend({ bounds = new L.Bounds( L.point([-r, -r]), size.add([r, r])), - - max = this.options.max === undefined ? 1 : this.options.max, - maxZoom = this.options.maxZoom === undefined ? this._map.getMaxZoom() : this.options.maxZoom, - v = 1 / Math.pow(2, Math.max(0, Math.min(maxZoom - this._map.getZoom(), 12))), cellSize = r / 2, grid = [], panePos = this._map._getMapPanePos(), offsetX = panePos.x % cellSize, offsetY = panePos.y % cellSize, - i, len, p, cell, x, y, j, len2, k; + i, len, p, cell, x, y, j, len2; + + this._max = 1; // console.time('process'); for (i = 0, len = this._latlngs.length; i < len; i++) { p = this._map.latLngToContainerPoint(this._latlngs[i]); - if (bounds.contains(p)) { - x = Math.floor((p.x - offsetX) / cellSize) + 2; - y = Math.floor((p.y - offsetY) / cellSize) + 2; - - var alt = - this._latlngs[i].alt !== undefined ? this._latlngs[i].alt : - this._latlngs[i][2] !== undefined ? +this._latlngs[i][2] : 1; - k = alt * v; - - grid[y] = grid[y] || []; - cell = grid[y][x]; - - if (!cell) { - grid[y][x] = [p.x, p.y, k]; + x = Math.floor((p.x - offsetX) / cellSize) + 2; + y = Math.floor((p.y - offsetY) / cellSize) + 2; + + var alt = + this._latlngs[i].alt !== undefined ? this._latlngs[i].alt : + this._latlngs[i][2] !== undefined ? +this._latlngs[i][2] : 1; + + grid[y] = grid[y] || []; + cell = grid[y][x]; + + if (!cell) { + cell = grid[y][x] = [p.x, p.y, alt]; + cell.p = p; + } else { + cell[0] = (cell[0] * cell[2] + p.x * alt) / (cell[2] + alt); // x + cell[1] = (cell[1] * cell[2] + p.y * alt) / (cell[2] + alt); // y + cell[2] += alt; // cumulated intensity value + } - } else { - cell[0] = (cell[0] * cell[2] + p.x * k) / (cell[2] + k); // x - cell[1] = (cell[1] * cell[2] + p.y * k) / (cell[2] + k); // y - cell[2] += k; // cumulated intensity value - } + // Set the max for the current zoom level + if (cell[2] > this._max) { + this._max = cell[2]; } } + this._heat.max(this._max); + for (i = 0, len = grid.length; i < len; i++) { if (grid[i]) { for (j = 0, len2 = grid[i].length; j < len2; j++) { cell = grid[i][j]; - if (cell) { + if (cell && bounds.contains(cell.p)) { data.push([ Math.round(cell[0]), Math.round(cell[1]), - Math.min(cell[2], max) + Math.min(cell[2], this._max) ]); } }