将元素附加到d3选择

时间:2014-08-19 03:15:56

标签: javascript svg d3.js

在d3程序中,我有许多circle元素,并且数据绑定到它们。在对事件的回调中,我想过滤掉大部分事件,并在剩下的那些上面放置一个更大的红色圆圈。它看起来像这样:

svg.selectAll("circle")
  .filter(/* filter function not important */)
  .append("circle")
  .attr("class", "extra")
  .attr("cx", function(){return d3.select(this).attr("cx")})
  .attr("cy", function(){return d3.select(this).attr("cy")})
  .attr("r", 5);

结果就是这样(第一行是原始圆圈):

<circle cx="55.41208075590415" cy="279.3650793650794" r="1">
  <circle class="extra" r="5"></circle>
</circle>

所以我有两个问题。一,它是作为旧元素的孩子插入,而不是兄弟姐妹。理想情况下,它将作为svg的最后一个子项插入。其次,cxcy不会被复制。我需要说些什么才能使这项工作成功?


如果您可以覆盖现有元素,请参阅下面的答案。要创建新的,这是如何。

svg.selectAll("circle")
  .filter(/* filter function not important */)
  .each(function(d){
      svg.append("circle")
         .attr("class", "extra")
         .attr("cx", function() { return x(d.fop) })
         .attr("cy", function() { return y(d.bar) })
         .attr("r", 5);
   })

注意两件事。一,内部函数不带参数,因为没有数据绑定到额外的圆。请改用现有圈子中的d。第二,我无法弄清楚如何访问现有圈子的cxcy,所以我不得不重新计算它们,这意味着比例x和{{1}必须保持不变。如果有人能改进,我会改变接受的答案。

1 个答案:

答案 0 :(得分:0)

您应该只使用过滤器功能来修改其数据具有通过过滤器功能的标准的圆圈,而不是对您的选择进行.append。您可以修改这些圈子,而不是附加新元素。所以你的代码看起来像这样。

svg.selectAll('circle')
    .filter(/** what you want**/)
    .attr('r', newRadiusSize)
    .attr('fill', 'red')

你甚至可以添加一个漂亮的过渡来使圆圈变为红色,而不是仅仅捕捉到更大的圆圈。