function Step(context, t) { this._context = context; this._t = t; } Step.prototype = { areaStart: function() { this._line = 0; }, areaEnd: function() { this._line = NaN; }, lineStart: function() { this._x = this._y = NaN; this._point = 0; }, lineEnd: function() { if (0 < this._t && this._t < 1 && this._point === 2) this._context.lineTo(this._x, this._y); if (this._line || (this._line !== 0 && this._point === 1)) this._context.closePath(); if (this._line >= 0) this._t = 1 - this._t, this._line = 1 - this._line; }, point: function(x, y) { x = +x, y = +y; switch (this._point) { case 0: case 0: this._point = 1; this._line ? this._context.lineTo(x, y) : this._context.moveTo(x, y); break; case 1: this._point = 2;
<!DOCTYPE html> <html> <head> <script data-require=" d3@4.0.0 " data-semver="4.0.0" src="https://d3js.org/d3.v4.min.js"></script> </head> <body> <script> document.addEventListener("DOMContentLoaded", function(event) { var width = 500, height = 500, N = 10; var svg = d3.select('body') .append('svg') .attr('width', width) .attr('height', height); var points = []; for (var i = 0; i < N; i++) { points.push({ x: (width / N) * i + (width / N / 2), y: Math.random() * height }); } var line1 = d3.line() .x(function(d) { return dx; }) .y(function(d) { return dy; }) .curve(stepRound); var line2 = d3.line() .x(function(d) { return dx; }) .y(function(d) { return dy; }) .curve(d3.curveStep); svg.append('path') .datum(points) .attr('d', line1) .attr('fill', 'none') .attr('stroke', 'orange') .attr('stroke-width', '3px'); svg.append('path') .datum(points) .attr('d', line2) .attr('fill', 'none') .attr('stroke', 'steelblue') .attr('stroke-width', '1px'); }); </script> </body> </html>