Skip to content

Commit

Permalink
using modified HeatLayer.js and simpleheat from npm due to this bug - L…
Browse files Browse the repository at this point in the history
  • Loading branch information
sghaskell committed Jun 6, 2018
1 parent ac87c03 commit d96c0e6
Show file tree
Hide file tree
Showing 5 changed files with 374 additions and 34 deletions.
200 changes: 200 additions & 0 deletions appserver/static/visualizations/maps-plus/contrib/HeatLayer.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,200 @@
'use strict';

L.HeatLayer = (L.Layer ? L.Layer : L.Class).extend({

// options: {
// minOpacity: 0.05,
// maxZoom: 18,
// radius: 25,
// blur: 15,
// max: 1.0
// },

initialize: function (latlngs, options) {
this._latlngs = latlngs;
L.setOptions(this, options);
},

setLatLngs: function (latlngs) {
this._latlngs = latlngs;
return this.redraw();
},

addLatLng: function (latlng) {
this._latlngs.push(latlng);
return this.redraw();
},

setOptions: function (options) {
L.setOptions(this, options);
if (this._heat) {
this._updateOptions();
}
return this.redraw();
},

redraw: function () {
if (this._heat && !this._frame && !this._map._animating) {
this._frame = L.Util.requestAnimFrame(this._redraw, this);
}
return this;
},

onAdd: function (map) {
this._map = map;

if (!this._canvas) {
this._initCanvas();
}

map._panes.overlayPane.appendChild(this._canvas);

map.on('moveend', this._reset, this);

if (map.options.zoomAnimation && L.Browser.any3d) {
map.on('zoomanim', this._animateZoom, this);
}

this._reset();
},

onRemove: function (map) {
map.getPanes().overlayPane.removeChild(this._canvas);

map.off('moveend', this._reset, this);

if (map.options.zoomAnimation) {
map.off('zoomanim', this._animateZoom, this);
}
},

addTo: function (map) {
map.addLayer(this);
return this;
},

_initCanvas: function () {
var canvas = this._canvas = L.DomUtil.create('canvas', 'leaflet-heatmap-layer leaflet-layer');

var originProp = L.DomUtil.testProp(['transformOrigin', 'WebkitTransformOrigin', 'msTransformOrigin']);
canvas.style[originProp] = '50% 50%';

var size = this._map.getSize();
canvas.width = size.x;
canvas.height = size.y;

var animated = this._map.options.zoomAnimation && L.Browser.any3d;
L.DomUtil.addClass(canvas, 'leaflet-zoom-' + (animated ? 'animated' : 'hide'));

this._heat = simpleheat(canvas);
this._updateOptions();
},

_updateOptions: function () {
this._heat.radius(this.options.radius || this._heat.defaultRadius, this.options.blur);

if (this.options.gradient) {
this._heat.gradient(this.options.gradient);
}
this._max = 1;
},

_reset: function () {
var topLeft = this._map.containerPointToLayerPoint([0, 0]);
L.DomUtil.setPosition(this._canvas, topLeft);

var size = this._map.getSize();

if (this._heat._width !== size.x) {
this._canvas.width = this._heat._width = size.x;
}
if (this._heat._height !== size.y) {
this._canvas.height = this._heat._height = size.y;
}

this._redraw();
},

_redraw: function () {
var data = [],
r = this._heat._r,
size = this._map.getSize(),
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;

// 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;

grid[y] = grid[y] || [];
cell = grid[y][x];

if (!cell) {
grid[y][x] = [p.x, p.y, k];

} 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
}
}
}

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) {
data.push([
Math.round(cell[0]),
Math.round(cell[1]),
Math.min(cell[2], max)
]);
}
}
}
}
// console.timeEnd('process');

// console.time('draw ' + data.length);
this._heat.data(data).draw(this.options.minOpacity);
// console.timeEnd('draw ' + data.length);

this._frame = null;
},

_animateZoom: function (e) {
var scale = this._map.getZoomScale(e.zoom),
offset = this._map._getCenterOffset(e.center)._multiplyBy(-scale).subtract(this._map._getMapPanePos());

if (L.DomUtil.setTransform) {
L.DomUtil.setTransform(this._canvas, offset, scale);

} else {
this._canvas.style[L.DomUtil.TRANSFORM] = L.DomUtil.getTranslateString(offset) + ' scale(' + scale + ')';
}
}
});

L.heatLayer = function (latlngs, options) {
return new L.HeatLayer(latlngs, options);
};
2 changes: 1 addition & 1 deletion appserver/static/visualizations/maps-plus/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -28,7 +28,7 @@
"leaflet-contextmenu": "^1.2.1",
"leaflet-dialog": "^1.0.1",
"leaflet-google-places-autocomplete": "^0.0.8",
"leaflet.heat":"^0.2.0",
"simpleheat": "^0.4.0",
"load-google-maps-api": "^1.0.0",
"leaflet-bing-layer": "^3.3.0",
"leaflet.markercluster": "^1.3.0",
Expand Down
2 changes: 1 addition & 1 deletion appserver/static/visualizations/maps-plus/src/maps-plus.js
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,7 @@ define([
'leaflet-dialog',
'leaflet-google-places-autocomplete',
'leaflet.markercluster',
'leaflet.heat',
'simpleheat',
'../contrib/leaflet.spin',
'../contrib/leaflet.featuregroup.subgroup-src',
'../contrib/leaflet-measure',
Expand Down
Loading

0 comments on commit d96c0e6

Please sign in to comment.