score:1

Accepted answer

It's because you haven't actually created any objects to change the attributes of, you tried to create the paths off of the force links at the top of your file, before any links had actually been created. You needed to create the paths based on the links in your 'restart' function and then update their attributes in the 'tick' function. Here's a codepen: https://codepen.io/anon/pen/RBazVp?editors=0010

Here's the relevant changes:

function restart() {
       ...
       ...
  link = link.data(links);
  link.enter()
      .append('path')
      .attr('class', 'link');
  link.exit().remove();

  force.start();
       ...
       ...
}

function tick() {
  link.attr("d", function(d) {
    var dx = d.target.x - d.source.x,
        dy = d.target.y - d.source.y,
        dr = Math.sqrt(dx * dx + dy * dy);
    return (
      "M" +
      d.source.x +
      "," +
      d.source.y +
      "A" +
      dr +
      "," +
      dr +
      " 0 0,1 " +
      d.target.x +
      "," +
      d.target.y
    );
  });
       ...
       ...
}

To add arrows to the links:

var arrows = svg.append("defs")
            .selectAll("marker")
              .data(["arrow"])
              .enter()
              .append("marker")
                .attr("id", String)
                .attr("viewBox", "0 -5 10 10")
                .attr("refX", 15)
                .attr("refY", -1.5)
                .attr("markerWidth", 6)
                .attr("markerHeight", 6)
                .attr("orient", "auto")
                .append("path")
                  .attr("d", "M0,-5L10,0L0,5");

function restart() {
       ...
       ...
  link = link.data(links);
  link.enter()
      .append('path')
      .attr('class', 'link')
      .attr('marker-end', 'url(#arrow)');  
  link.exit().remove();

  force.start();
       ...
       ...
}

Interestingly, you only need to define and create the arrow once, and changing the 'marker-end' attribute will automatically generate another copy of the arrow. Pretty neat!


Related Query