block by devgru 8623153

Car accidents

Full Screen

index.html

<!DOCTYPE html>
<html lang='en'>
<head>
    <meta charset='utf-8'>
    <title>Accidents on the Road - Choropleth</title>
    <script src='//d3js.org/d3.v4.js'></script>
    <script src='//d3js.org/topojson.v1.js'></script>
    <script src='//d3js.org/colorbrewer.v1.js'></script>
</head>
<body>
<script type='text/javascript'>
var width = 960
var height = 500
var colorDomain = d3.range(300, 1501, 300)

var color = d3.scaleThreshold()
  .range(colorbrewer['RdYlGn'][6].reverse())
  .domain(colorDomain)

d3.queue()
  .defer(d3.json, '//d3.devg.ru/data/russia.json')
  .defer(d3.csv, '//d3.devg.ru/data/accidents.csv')
  .defer(d3.tsv, '//d3.devg.ru/data/cities.tsv')
  .await(ready)

function drawMap(svg, map, cities, rateById, projection) {
  var path = d3.geoPath()
    .projection(projection)
  
  var mapData = topojson.feature(map, map.objects.russia).features
  
  svg.append('g')
    .attr('class', 'region')
    .selectAll('path')
    .data(mapData)
    .enter()
    .append('path')
    .attr('stroke', 'white')
    .attr('stroke-width', 1)
    .attr('d', path)
    .attr('fill', function (d) {
      return color(rateById[d.properties.region])
    })

  var city = svg.selectAll('g')
    .data(cities)
    .enter()
    .append('g')
    .attr('transform', function (d) {
      return 'translate(' + projection([d.lon, d.lat]) + ')'
    })

  city.append('circle')
    .attr('r', 1.5)
    .style('fill', 'white')

  city.append('text')
    .attr('font-family', 'sans-serif')
    .attr('font-size', '11px')
    .attr('text-anchor', 'middle')
    .attr('stroke', 'white')
    .attr('fill', 'white')
    .attr('stroke-width', 3)
    .style('text-shadow', '0 0 2px white')
  
  city.append('text')
    .attr('font-family', 'sans-serif')
    .attr('font-size', '11px')
    .attr('text-anchor', 'middle')
  
  city.selectAll('text')
    .attr('y', function (d) {
      if (d.City == 'Красноярск') return 13
      return -7
    })
    .text(function (d) { return d.City })
}
  
function drawLegend(svg) {
  
  var legendSize = 20
  var legendLabels = [
    '< 300', '300-600', '600-900', '900-1200', '1200-1500', '> 1500'
  ]
  var legendDomain = d3.range(0, 1501, 300)

  var legend = svg.selectAll('g.legend')
    .data(legendDomain)
    .enter().append('g')
    .attr('class', 'legend')

  legend.append('rect')
    .attr('x', 200)
    .attr('y', function (d, i) {
      return i * legendSize
    })
    .attr('width', legendSize)
    .attr('height', legendSize)
    .attr('fill', function (d, i) { return color(d) })
    .attr('opacity', 0.8)
    .attr('stroke', 'black')
    .attr('stroke-width', 0.3)

  legend.append('text')
    .attr('x', 230)
    .attr('dy','-4')
    .attr('font-family', 'sans-serif')
    .attr('font-size', '12px')
    .attr('y', function (d, i) {
      return (i + 1) * legendSize
    })
    .text(function (d, i) {
      return legendLabels[i]
    })

}
  
function ready(error, map, data, cities) {
  var svg = d3.select('body')
    .append('svg')
    .attr('width', width * 0.39)
    .attr('height', height)
  
  var projection = d3.geoAlbers()
    .rotate([-105, 0])
    .center([-10, 65])
    .parallels([52, 64])
    .scale(1000)
    .translate([width * 0.675, height * 0.7])

  var svg2 = d3.select('body')
    .append('svg')
    .attr('width', width * 0.5)
    .attr('height', height)
    .style('border-left', '1px solid #000')
    .style('margin', '10px auto')

  var projection2 = d3.geoAlbers()
    .rotate([-105, 0])
    .center([-10, 65])
    .parallels([52, 64])
    .scale(500)
    .translate([width * 0.1425, height * 0.65])

  var rateById = {}
  data.forEach(function (d) { rateById[d.RegionCode] = +d.Deaths })

  drawMap(svg, map, cities, rateById, projection)
  drawMap(svg2, map, cities.filter(function (a) {
    return a.lon > 70
  }), rateById, projection2)

  drawLegend(svg2)
  svg.append('text')
    .attr('font-family', 'sans-serif')
    .text('× 2')
    .attr('x', width * 0.36)
    .attr('opacity', 0.5)
    .attr('y', 20)
}
</script>
</body>
</html>