编程语言
首页 > 编程语言> > javascript – D3更新circle-pack数据新节点重叠现有节点

javascript – D3更新circle-pack数据新节点重叠现有节点

作者:互联网

我正在关注General Update Pattern,但是关于分层问题.

使用circle-pack布局,我打包新数据,更新,进入和退出圆元素.但是,当新元素进入时,它们会与更新的圆圈重叠.

数据键功能基于元素名称:

.data(nodes, function(d, i) { return d.name; });

所以我的圆圈包有更新圆圈的位置(正确的位置和大小),但它隐藏在新输入的父圆圈后面.

有没有办法将这些更新的节点发送到前面或在输入的圆圈上重绘它们?

–UPDATE–
正如关闭此问题的人所建议的那样,我尝试使用moveToFront实现链接到解决方案.

我在更新部分添加了以下代码(没有更改任何内容),然后尝试在输入和退出代码之后添加它,这也没有任何区别.

.each("end", function(d){ d3.select(this).moveToFront(); });


d3.selection.prototype.moveToFront = function() {
  return this.each(function(){
    this.parentNode.appendChild(this);
  });
};

为清楚起见,这就是选择和更新的样子:

// Load data into svg, join new data with old elements, if any.
var nodes = pack.nodes(postData);
node = root = postData;

groupNodes = svg.selectAll("g")
  .data(nodes, function(d, i) { return d.name; });

// Update and transition existing elements
groupNodes.select("circle")
  .transition()
  .duration(duration)
  .attr('transform', function(d) { return 'translate(' + d.x + ',' + d.y + ')'; })
  .attr('r', function(d) { return d.r; })
  .each("end", function(d){ d3.select(this).moveToFront(); });

此moveToFront代码对我的输出没有影响,更新的圆圈仍然在输入的选择圈后面.

总结一下:这个问题似乎是由层次结构布局(circle-packing)引起的,它希望按照数据层次结构的顺序绘制圆. d3更新模式(使用输入,更新和退出选择)会在重新绘制层次结构时使选定的更新元素保留在svg中,并在其上绘制新图层.这些节点的父节点已经正确设置,因此在这种情况下,parentNode.appendChild不会执行任何操作,因为它不是问题的原因.

Here is a fiddle来证明我的问题.我已经尝试将moveToFront代码放在不同的地方,没有明显的区别.
当您点击“更改数据”按钮时,它会重绘圆圈,但是在两个数据集之间名称重叠的任何圆圈都没有在圆包中正确嵌套. “A组”的孩子隐藏在其中一个父圈之后.您可以通过Inspect Element验证节点是否在那里.

来自更新小提琴的另一张照片:
hidden nodes

解决方法:

D3提供了一种基于与.sort() function绑定的数据重新排序元素的方法.在您的情况下,要检查的条件是元素的.depth属性 – “更深”元素应该出现在前面:

svg.selectAll("g")
  .sort(function (a, b) {
    if (a.depth < b.depth) return -1;
    else return 1;
  });

完整演示here.

标签:javascript,svg,d3-js,circle-pack
来源: https://codeday.me/bug/20190702/1359182.html