本文介绍了为什么我们需要force.on('tick'..在d3中的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在通过编写基础的力导向图来学习d3。我的代码如下。我不明白的目的是 force.on('tick' ...

I am learning d3 by coding a force directed graph from basics. My code is below.What I don’t understand is the purpose of force.on('tick'...

当然,如果我们正在使用内置类进行布局我认为它足以给d3.layout.force()你的节点和链接,它应该能够以平衡的布局绘制图形。

Surely if we are using a in-built class for the layout I would have thought that it is enough to give d3.layout.force() your nodes and links and it should be able to draw the graph in a balanced layout.

如果我注释掉 force.on('tick' ...部分,那么我的所有圆圈和线条都会在左上角结束。是否有内部发生的事情与svg容器中发生的事情之间存在差异,因此我们需要 force.on('tick'重新绘制布局以匹配每次的当前内部值集合?

If I comment out the section force.on('tick'... then all my circles and lines end up in the top left hand corner. Is there are difference between what is happening internally and what is happening in the svg container hence we need the force.on('tick' to redraw the layout to match the current set of internal values each time?

var nodes = [
      {},
      {},
      {}
];

var links = [
      {'source': 0, 'target': 1}
];

// append svg element to container
var mychart = d3.select('#chart')
      .append('svg')
      .attr('width', w)
      .attr('height', h);

// create force layout in memory
var force = d3.layout.force()
      .nodes(nodes)
      .links(links)
      .size([w, h]);

// append a group for each data element
var node = mychart.selectAll('circle')
      .data(nodes).enter()
      .append('g')
      .call(force.drag);

// append circle onto each 'g' node
node.append('circle')
      .attr('fill', palette.green)
      .attr('r', circleWidth);


/*force.on('tick', function(e) {
      node.attr('transform', function(d, i) {
            return 'translate('+ d.x +', '+ d.y +')';
      })

      link
            .attr('x1', function(d) { return d.source.x })
            .attr('y1', function(d) { return d.source.y })
            .attr('x2', function(d) { return d.target.x })
            .attr('y2', function(d) { return d.target.y })
});*/


var link = mychart.selectAll('line')
      .data(links).enter()
      .append('line')
      .attr('stroke', palette.gray)

force.start();


推荐答案

强制布局以异步方式运行。也就是说,当你调用 force.start()时,它会开始执行计算,以确定后台并行节点的位置。这些计算不是一个步骤,而是长时间(几秒钟)运行的模拟。

The force layout runs asynchronously. That is, when you call force.start() it starts doing its computations that determine the position of the nodes in parallel in the background. These computations are not a single step, but a simulation running over a long time (several seconds).

tick handler是一个函数,它使您能够在更改时获得布局的状态(模拟已经提前计算)并对其进行操作 - 特别是,重绘当前在模拟中的节点和链接。

The tick handler is the function that enables you to get the state of the layout when it has changed (the simulation has advanced by a tick) and act on it -- in particular, redraw the nodes and links where they currently are in the simulation.

你不必处理 tick 事件,你只需运行一定数量的布局步骤然后绘制而不处理 tick 事件,如。在 tick 处理函数中动态执行此操作具有以下优势:您可以看到布局如何进展。但是,从技术上讲,如果您只对结果感兴趣,则不需要它。

You don't have to handle the tick event though, you could simply run the layout for a certain number of steps and then draw without handling the tick event at all, as in this example. Doing it dynamically in the tick handler function has the advantage that you can see how the layout progresses. However, technically it is not needed if you're just interested in the result.

这篇关于为什么我们需要force.on('tick'..在d3中的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!

10-14 15:43