visualization of the police reports in Boston via d3 hexbins onto leaflet, data from boston
xxxxxxxxxx
<meta charset="utf-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge,chrome=1">
<meta name="viewport" content="width=1024, user-scalable=no">
<style>
html { height: 100% }
body { height: 100%; margin: 0; padding: 0;}
#map{ height: 100% }
</style>
<link rel="stylesheet" href="https://cdn.leafletjs.com/leaflet-0.5.1/leaflet.css" />
<title>Hex Bins + leaflet</title>
<div id="map"></div>
<script src="https://d3js.org/d3.v3.min.js"></script>
<script src="colorbrewer.js"></script>
<script src="hexbin.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/leaflet/0.5.1/leaflet.min.js"></script>
<script>
var m = L.map("map").setView([42.35321607653588, -71.06369018554688],11);
var buckets = 11;
//make the map
var _p;
L.layerGroup([
L.tileLayer("https://{s}.tile.stamen.com/terrain-background/{z}/{x}/{y}.jpg",{minZoom:4,maxZoom:18}),
L.tileLayer("https://{s}.tile.stamen.com/terrain-lines/{z}/{x}/{y}.png",{minZoom:4,maxZoom:18,attribution:'Map tiles by <a href="https://stamen.com">Stamen Design</a>, <a href="https://creativecommons.org/licenses/by/3.0">CC BY 3.0</a> — Map data © <a href="https://openstreetmap.org">OpenStreetMap</a> contributors, <a href="https://creativecommons.org/licenses/by-sa/2.0/">CC-BY-SA</a>'})
]).addTo(m);
//add a tileset
//boston police bloter
d3.json("points.json",function(err,points){
_p = points;
//generate 60k random points
var radius = 0.0035;
var hexbin = d3.hexbin()
.size([
d3.max(points,function(v){return v[0]})-d3.min(points,function(v){return v[0]}),
d3.max(points,function(v){return v[1]})-d3.min(points,function(v){return v[1]})])
.radius(radius);
//create a hexbin
var hex = hexbin(points);
//populate it
var q = d3.scale.quantile().domain(hex.map(function(h){return h.length;}).reduce(function(a,b){if(a.indexOf(b)===-1){a.push(b)};return a;},[]).sort(function(a,b){return a-b})).range(d3.range(buckets))
//make a scale
function hexagon(radius) {
var x0 = 0, y0 = 0;
return d3.range(0, 2 * Math.PI, Math.PI / 3).map(function(angle) {
var x1 = Math.sin(angle) * radius,
y1 = -Math.cos(angle) * radius,
dx = x1 - x0,
dy = y1 - y0;
x0 = x1, y0 = y1;
return [dx, dy];
});
};
//from the hexbin file, we need this to create points
var transform = hexagon(radius);
//use it to create a transform function
transform.shift();
//remove the first value as it's a duplicate
L.layerGroup(hex.map(function(h){//create a layergroup
return L.polygon(transform.map(function(t){//filled with polygons
return [h.x+t[0],h.y+t[1]];//that are the hexagons we need
}),{//styled like so
stroke:false,
color:colorbrewer.Spectral[buckets][(buckets-1)-q(h.length)],//including color brewer colors
fillOpacity:0.7
}).bindPopup("number: "+h.length);//with the number of points in the popup
})).addTo(m);
});
</script>
Modified http://d3js.org/d3.v3.min.js to a secure url
Modified http://cdn.leafletjs.com/leaflet-0.5.1/leaflet.js to a secure url
https://d3js.org/d3.v3.min.js
https://cdn.leafletjs.com/leaflet-0.5.1/leaflet.js