【问题标题】:Grouping Nodes with Radio Button使用单选按钮对节点进行分组
【发布时间】:2013-08-14 17:03:56
【问题描述】:

我一直试图拼凑出这个问题的答案,但我被官方难住了。我正在研究 D3 中的强制布局可视化,与http://vallandingham.me/vis/gates/ 非常相似。当我单击单选按钮时,我遇到的问题是让我的节点进行分组和取消分组。节点会短暂地转移到它们的新位置,但几乎会立即恢复到原来的形式。任何有关此事的帮助将不胜感激!我确实花了几个小时搜索 Jim 的博客/代码,以及其他来自 Bostock 的示例,但无济于事。下面是我的代码。再次感谢任何建议...

谢谢

<body>
 <form>
    <input type="radio" name="radio" value="P1",  checked="checked"> Group
    <input type="radio" name="radio" value="P2",  unchecked> Category Group
</form>
<script src="d3.v3.js"></script>
<script>

  var width = 960,
      height = 700;

  var svg = d3.select("body").append("svg")
       .attr("width", width)
       .attr("height", height) 

//Load Data
  d3.csv("data/ski5.csv", function(error, data) {

  var rScale = d3.scale.linear()
      .domain([0,d3.max(data, function (d) {return d.acres; })])
      .range([0, 12]);          

  var force = d3.layout.force()
      .nodes(data)
      .size([width, height])
      .on("tick", tick)
      .charge(charge);
    force.alpha()
    force.gravity(.45)
    force.start()

   var node = svg.selectAll("circle")
       .data(force.nodes()) 
       .enter()
       .append("circle")
       .attr("class", "node")
       .attr("r",  function(d) {return (rScale(d.acres));})
       .attr("stroke", "white")
       .attr("stroke-width", .5)
       .attr("fill", function(d) {return d.color;})
       .call(force.drag);
    svg.style("opacity", 1e-6)
       .transition()
       .duration(1300)
       .style("opacity", 1);

 function charge(d) {
     return ((rScale(d.acres)) * (rScale(d.acres)) * (-.65));
 } 


 function tick(e) {
    node.attr("cx", function(d) { return d.x; })
        .attr("cy", function(d) { return d.y; });
  }


//Radio Button for Category Group
  d3.selectAll("input[value=P2]")
      .on("change", groupCategory);  

 function groupCategory() {
    data.forEach(function(d, i) {   
       d.x = d.x + (d.line*10 - d.x) * (.01 + 0.02);
       d.y = d.y + (300 - d.y) * (.01 + 0.02);
       });
   force.start();
 }

;}) 

</script>

【问题讨论】:

    标签: d3.js force-layout


    【解决方案1】:

    我认为您需要将节点的属性实际设置为新位置。现在您正在移动位置而不更改任何属性,这可能解释了您正在观察的行为。在引用的示例中,会发生以下情况:

    .attr("cx", (d) -> d.x)
    .attr("cy", (d) -> d.y)
    

    通过“move_towards_year”方法设置新的“cx”和“cy”。所以你应该创建一个相应的方法来放置你已经编写的逻辑:

    d.x = d.x + (d.line*10 - d.x) * (.01 + 0.02);
    d.y = d.y + (300 - d.y) * (.01 + 0.02);
    

    然后以类似于“display_by_year”方法的方式调用此方法:

    display_by_whatever: () =>
      @force.gravity(@layout_gravity)
        .charge(this.charge)
        .friction(0.9)
        .on "tick", (e) =>
          @circles.each(this.your_move_method(e.alpha))
            .attr("cx", (d) -> d.x)
            .attr("cy", (d) -> d.y)
      @force.start()
    

    要处理单选按钮事件(根据您的评论),请执行以下操作:

    d3.select('radio button id/class').on('change', display_by_whatever)
    

    【讨论】:

    • 感谢您的回复@rysloan。
    • 作为后续;在您的示例中,您会将广播事件放在哪里?我很难在...中添加该功能。谢谢!
    猜你喜欢
    • 2023-01-24
    • 2013-01-25
    • 2013-06-02
    • 1970-01-01
    • 1970-01-01
    • 2011-01-11
    • 1970-01-01
    • 1970-01-01
    • 2021-03-14
    相关资源
    最近更新 更多