block by syntagmatic c256fda4965d38e7c59b

Hexbin Heightmap Transitions

Full Screen

Hexbin Heightmap with cell colors cycling between minimum and maximum elevation. Transitions use data-space interpolation to tween colors.

index.html

<!DOCTYPE html>
<meta charset="utf-8">
<style>
html, body {
  background: #222;
}
svg, canvas {
  position: absolute;
  top: 0;
  left: 0;
}
canvas {
  display: none;
}
</style>
<body>
<script src="//d3js.org/d3.v3.min.js"></script>
<script src="//d3js.org/d3.hexbin.v0.min.js"></script>
<script>

var width = 960,
    height = 500;

var hexbin = d3.hexbin()
    .size([width, height])
    .radius(5.5);

var color = d3.scale.linear()
   .domain([0, 14, 15, 35, 132])
   .range(["#050505", "#222", "#d7191c", "#ffffbf", "#2c7bb6"])
   .interpolate(d3.interpolateHcl);

var canvas = d3.select("body").append("canvas")
    .attr("width", width)
    .attr("height", height);

var context = canvas.node().getContext("2d");
var points = [];
var hexagons = [];

getImage("readme.png", function(image) {
  context.drawImage(image, 0, 0, width, height);
  image = context.getImageData(0, 0, width, height);

  // Rescale the colors.
  for (var c, i = 0, n = width * height * 4, d = image.data; i < n; i += 4) {
    points.push([i/4%width, Math.floor(i/4/width), d[i]]);
  }

  hexagons = hexbin(points);
  hexagons.forEach(function(d) {
    d.min = d3.min(d, function(p) { return p[2]; });
    d.max = d3.max(d, function(p) { return p[2]; });
    d.mean = d3.mean(d, function(p) { return p[2]; });
  });

  var svg = d3.select("body").append("svg")
      .attr("width", width)
      .attr("height", height);

  var hexagon = svg.append("g")
      .attr("class", "hexagons")
    .selectAll("path")
    .data(hexagons.filter(function(d) {
      return !(d.max < 16 && d.min > 12);
    }))
    .enter().append("path")
      .attr("d", hexbin.hexagon(6))
      .attr("transform", function(d) { return "translate(" + d.x + "," + d.y + ")"; })
      .style("fill", function(d) { return color(d.min); });

  var flip = true;

  function toggle() {
    flip = !flip;
    hexagon
      .transition()
      .duration(function(d) { return d3.min([360*Math.sqrt(d.max - d.min),4200]); })
      .style("fill", function(d) { return color(flip ? d.min : d.max); })
      .styleTween("fill", function(d,i,a) {
        var interpolate = d3.interpolate(flip ? d.min : d.max, flip ? d.max : d.min);
        return function(t) {
          return color(interpolate(t));
        };
      });

  };

  loop(toggle, 4200);

  function loop(f,t) {
    f();
    setTimeout(function() {
      loop(f,t);
    },t)
  };
});


function getImage(path, callback) {
  var image = new Image;
  image.onload = function() { callback(image); };
  image.src = path;
}

</script>