score:0

Accepted answer

Use a custom center force with a strength parameter.

.force("center", myCenterForce(this.props.width / 2, this.props.height / 2))

In drag functions call

simulation.force("center").strength(0);

simulation.force("center").strength(1.0);

Or you can animate/interpolate the strength in the tick function.

var dragNode = null;

  drag = simulation => {
    const dragStarted = function (d) {
      if (!d3.event.active) {
        simulation.alphaTarget(0.7).restart()
      }
      dragNode = null;
      d.fx = d.x
      d.fy = d.y
    }

    const dragged = function (d) {
      d.fx = d3.event.x
      d.fy = d3.event.y
    }

    const dragEnded = function (d) {
      if (!d3.event.active) simulation.alphaTarget(0);
      dragNode = this;
      d3.select(this).attr("data-strength", 0)
          .transition().duration(2000)
          .attr("data-strength", 1.0)
          .on("end", function () { dragNode = null; } );
      d.fx = null
      d.fy = null
    }

    return d3
      .drag()
      .on("start", dragStarted)
      .on("drag", dragged)
      .on("end", dragEnded)
  }

function tick() {
    if (dragNode)
        simulation.force("center")
            .strength(d3.select(dragNode).attr("data-strength"));

    // update nodes
}

Custom force

function myCenterForce(x, y) {
  var nodes;
  var strength = 1.0;

  if (x == null) x = 0;
  if (y == null) y = 0;

  function force() {
    var i,
        n = nodes.length,
        node,
        sx = 0,
        sy = 0;

    for (i = 0; i < n; ++i) {
      node = nodes[i], sx += node.x, sy += node.y;
    }

    for (sx = sx / n - x, sy = sy / n - y, i = 0; i < n; ++i) {
      node = nodes[i], node.x -= strength * sx, node.y -= strength * sy;
    }
  }

  force.initialize = function(_) {
    nodes = _;
  };

  force.x = function(_) {
    return arguments.length ? (x = +_, force) : x;
  };

  force.y = function(_) {
    return arguments.length ? (y = +_, force) : y;
  };

  force.strength = function(_) {
    return arguments.length ? (strength = +_, force) : strength;
  };

  return force;
}

Related Query

More Query from same tag