block by mbostock 1313857

Point-Along-Path Interpolation

Full Screen

Demonstrates how to use the getTotalLength and getPointAtLength methods on SVG path elements to interpolate a point along an existing path. Built with D3.

index.html

<!DOCTYPE html>
<meta charset="utf-8">
<style>

path {
  cursor: pointer;
  fill: #eee;
  stroke: #666;
  stroke-width: 1.5px;
}

circle {
  fill: steelblue;
  stroke: white;
  stroke-width: 1.5px;
}

</style>
<body>
<script src="//d3js.org/d3.v3.min.js"></script>
<script>

var width = 960,
    height = 500;

var svg = d3.select("body").append("svg")
    .attr("width", width)
    .attr("height", height)
  .append("g")
    .attr("transform", "translate(" + width / 2 + "," + height / 2 + ")");

var path = svg.append("path")
    .attr("d", d3.svg.arc()
        .innerRadius(height / 4)
        .outerRadius(height / 3)
        .startAngle(0)
        .endAngle(Math.PI));

var circle = svg.append("circle")
    .attr("r", 6.5)
    .attr("transform", "translate(0," + -height / 3 + ")");

function transition() {
  circle.transition()
      .duration(5000)
      .attrTween("transform", translateAlong(path.node()))
      .each("end", transition);
}

transition();

// Returns an attrTween for translating along the specified path element.
function translateAlong(path) {
  var l = path.getTotalLength();
  return function(d, i, a) {
    return function(t) {
      var p = path.getPointAtLength(t * l);
      return "translate(" + p.x + "," + p.y + ")";
    };
  };
}

</script>