d3 js - 将气泡聚集到线段 [英] d3 js - clustering bubbles to segments

查看:933
本文介绍了d3 js - 将气泡聚集到线段的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

****最新版本 -








  • 最新的小提琴。
    http://jsfiddle.net/NYEaX/1505/



    http://jsfiddle.net/NYEaX/1506/) - refactored

      1.  - 如何为弧线设置动画
    2. - 气泡
    3. - 添加回随机化按钮以测试2个虚拟数据集。






    这是旧派动画,效果非常好

      / * ------- ANIMATE PIE SLICES ------- * / 
    var slice = doughpie.select(。slices)。selectAll(path.slice)
    .data(pie(data),key);

    slice.enter()
    .insert(path)
    .style(fill,function(d){
    return color(d.data .label);
    })
    .style(transform,function(d,i){
    // returntranslate(0,0);
    }
    .attr(class,slice);

    slice
    .transition()。duration(1000)
    .attrTween(d,function(d){
    this._current = this._current | | d;
    var interpolate = d3.interpolate(this._current,d);
    this._current = interpolate(0);
    return function(t){
    return arc (interpolate(t));
    };
    })

    slice.exit()
    .remove
    / * ------- ANIMATE PIE SLICES ------- * /


    $ b b

    //这是当前的饼圆 - 但是当我尝试以相同的方式对饼进行动画时,它会失败。

      var g = svg.selectAll(。arc)
    .data(pie(data))
    .enter()。append(g)
    .attr类,弧);

    g.append(path)
    .attr(d,arc)
    .style(fill,function(d){
    return color(d.data.label);
    });

    arc
    .outerRadius(radius - 10)
    .innerRadius(0);


    **** LATEST FIDDLE --- https://jsfiddle.net/tk5xog0g/8/

    -- 2nd fiddle with a custom chart -- randomly placing the bubbles closer to region zones but can not account for overlapping or falling off the central chart zone. http://jsfiddle.net/NYEaX/1484/

    I want to combine a doughtnut pie and a bubble chart to produce an exact result like this

    The closest I have got to - is here.

    https://jsfiddle.net/tk5xog0g/10/

    /* ------- ANIMATE BUBBLES -------*/
    
    
    // generate data with calculated layout values
    
    var data = bubbledata(data);
    
    var nodes = bubble.nodes(data)
      .filter(function(d) {
        return !d.children;
      }); // filter out the outer bubble
    
    
    var bubbles = bubs.selectAll('circle')
      .data(nodes);
    
    
    
    bubbles.enter()
      .insert("circle")
      .attr('transform', function(d) {
        return 'translate(' + d.x + ',' + d.y + ')';
      })
      .attr('r', function(d) {
        return d.r;
      })
      .style("fill", function(d) {
        return color(d.group);
      });
    
    
    bubbles = bubbles.transition()
      .transition()
      .duration(250)
      .attr('transform', function(d) {
        return 'translate(' + d.x + ',' + d.y + ')';
      })
      .attr('r', function(d) {
        //console.log("dr", d.r)
        return d.r;
      })
      .ease('sine');
    
    /* ------- ANIMATE BUBBLES -------*/
    

    I have also looked at trying to cluster the bubble chart to at least always group the colours together -- but this still won't match the required chart -- with the need for the colour bubbles to be close to the matching pie segments.

    -- this is a clustered variant but the orange bubbles may sit sandwiched in the middle and once I try and merge it with the pie - won't correspond. I have considered trying to add a charge/gravity to try and get the bubbles to repel. https://jsfiddle.net/tk5xog0g/20/

    https://bl.ocks.org/mbostock/7881887

    var width = 960,
        height = 500,
        radius = Math.min(width, height) / 2;
    
    var color = d3.scale.ordinal()
        .range(["#98abc5", "#8a89a6", "#7b6888", "#6b486b", "#a05d56", "#d0743c", "#ff8c00"]);
    
    var arc = d3.svg.arc()
        .outerRadius(radius - 60)
        .innerRadius(radius - 70);
    
    var pie = d3.layout.pie()
        .sort(null)
        .value(function(d) { return d.value; });
    
    var svg = d3.select("body").append("svg")
        .attr("width", width)
        .attr("height", height)
      .append("g")
        .attr("transform", "translate(" + width / 2 + "," + height / 2 + ")");
    
    
      var data = [
        {
          "group": "<5",
          "value": 1000,
          "children": [
            {
              "group": "<5",     
              "label": "Mel",
              "value": 1000,
              "totalGroupValue": 1000
            }
          ]
        },
        {
          "group": "5-13",
          "value": 1000,
          "children": [
            {
              "group": "5-13",        
              "label": "Erica",
              "value": 1000,
              "totalGroupValue": 1000
            }
          ]
        },
        {
          "group": "14-17",
          "value": 2000,
          "children": [
            {
              "group": "14-17",
              "label": "Jessica",
              "value": 1500,
              "totalGroupValue": 2000  
            },
            {
              "group": "14-17",
              "label": "Jill",
              "value": 500,
              "totalGroupValue": 2000  
            }
          ]
        },
        {
          "group": "18-24",
          "value": 1300,
          "children": [
            {
              "group": "18-24",
              "label": "Jerry",
              "value": 500,          
              "totalGroupValue": 1300 
            },
            {
              "group": "18-24",
              "label": "Ben",
              "value": 500,
              "totalGroupValue": 1300  
            },
            {
              "group": "18-24",
              "label": "Billy",
              "value": 300,
              "totalGroupValue": 1300  
            }
          ]
        },
        {
          "group": "25-44",
          "value": 1000,
          "children": [
            {
              "group": "25-44",
              "label": "Kelly",
              "value": 1000,
              "totalGroupValue": 1000
            }
          ]
        }
      ];  
    
    
      var g = svg.selectAll(".arc")
          .data(pie(data))
        .enter().append("g")
          .attr("class", "arc");
    
      g.append("path")
          .attr("d", arc)
          .style("fill", function(d) {
            return color(d.data.group); 
          });
    
      arc
        .outerRadius(radius - 10)
        .innerRadius(0);
    	  
    
    //create zone regions
    var zones = [];
    g.append("circle")
      .attr("transform", function(d) {
    
        zones[d.data.group] = arc.centroid(d);
        //zones.push(obj);
    
        return "translate(" + arc.centroid(d) + ")"; 
      })
      .attr("r", "1px")
      .style("fill", function(d) { 
        return "black"//color(d.data.group); 
      });
    //create zone regions
    
    
    //custom bubble chart
    function makeBubbles(transform, group, radius){
        g.append("circle")
        .attr("transform", function(d) {
          return "translate("+transform+")"; 
        })
        .attr("r", radius)
        .style("stroke", function(d) { 
          return "black";//color(group); 
        })
        .style("fill", function(d) { 
          return color(group); 
        });
    }
    
    //loop through data and for EACH children array paint dots.
    $.each(data, function( index, value ) {
    
      $.each(value.children, function( i, v ) {
          var randomX = Math.floor(Math.random() * 101) - 50;
          var randomY = Math.floor(Math.random() * 101) - 50;      
    
          var zoneregion = zones[v.group];
          var transform = (zoneregion[0] - randomX)+","+(zoneregion[1]+randomY);
          var group = v.group;
          var radius = ((v.value/v.totalGroupValue)*100) *0.5;
          makeBubbles(transform, group, radius);
    
      });    
    });    
    //custom bubble chart    
       
    
    function type(d) {
      d.value = +d.value;
      return d;
    }

    .arc text {
      font: 10px sans-serif;
      text-anchor: middle;
    }
    
    .arc path {
      stroke: #fff;
    }

    <script src="https://ajax.googleapis.com/ajax/libs/jquery/3.1.0/jquery.min.js"></script><script src="https://cdnjs.cloudflare.com/ajax/libs/d3/3.4.11/d3.min.js"></script>
    <body>

    解决方案

    Latest fiddle. http://jsfiddle.net/NYEaX/1505/

    ( http://jsfiddle.net/NYEaX/1506/ )- refactored

     1. -- how to animate the arcs
     2. -- how to animate the bubbles
     3. -- adding back the randomise button to test with 2 dummy data sets.
    


    this is the old pie animations and worked very well

                    /* ------- ANIMATE PIE SLICES -------*/
                    var slice = doughpie.select(".slices").selectAll("path.slice")
                      .data(pie(data), key);
    
                    slice.enter()
                      .insert("path")
                      .style("fill", function(d) {
                        return color(d.data.label);
                      })
                      .style("transform", function(d, i){
                        //return "translate(0, 0)";
                      })
                      .attr("class", "slice");
    
                    slice
                      .transition().duration(1000)
                      .attrTween("d", function(d) {
                        this._current = this._current || d;
                        var interpolate = d3.interpolate(this._current, d);
                        this._current = interpolate(0);
                        return function(t) {
                          return arc(interpolate(t));
                        };
                      })
    
                    slice.exit()
                      .remove();
                    /* ------- ANIMATE PIE SLICES -------*/
    

    //this is the current pie arcs - but when I try and animate the pie in the same manner - it fails.

    var g = svg.selectAll(".arc")
      .data(pie(data))
      .enter().append("g")
      .attr("class", "arc");
    
    g.append("path")
      .attr("d", arc)
      .style("fill", function(d) {
        return color(d.data.label);
      });
    
    arc
      .outerRadius(radius - 10)
      .innerRadius(0);
    

    这篇关于d3 js - 将气泡聚集到线段的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆