d3js饼图渐变

时间:2016-02-25 22:03:47

标签: d3.js gradient pie-chart

一直试图建立一个平滑渐变的饼图/圆环图,但发现它很难制作。已经花了很多时间,仍然没有运气如何解决这个问题。我正在使用d3js库

我有类似的东西

enter image description here

想要用渐变填充它,就像这样

enter image description here

任何建议如何使它更接近它。也许你们中的某个人已经面对过这个问题,并对此有所了解。

对于任何答案和建议都会感激不尽。

1 个答案:

答案 0 :(得分:2)

正如@meetamit在他的评论中所说的那样,我没有内置的SVG方式可以像你展示的那样产生圆形渐变。但是,如果我们建立在这个优秀的answer之上,我们可以很好地复制你的图表。

诀窍是制作一个360度的圆环(每个度数一个)来自己创建渐变。然后我们可以使用pie计算来不包括我们的切片填充应该是的弧:

<!DOCTYPE html>
<html>

  <head>
    <script data-require="d3@3.5.3" data-semver="3.5.3" src="//cdnjs.cloudflare.com/ajax/libs/d3/3.5.3/d3.js"></script>
  </head>

  <body>
    <script>
    
      // sample data
      var data = [10,20,30,40,50];
    
      var height = 500,
          width = 500,
          radius = 200,
          padding = 0.04;
      
      var svg = d3.select('body')
        .append('svg')
        .attr('width', width)
        .attr('height', height)
        .append('g')
        .attr('transform', 'translate(' + width/2 + ',' + width/2 + ')');
        
      var arc = d3.svg.arc()
        .innerRadius(radius - 100)
        .outerRadius(radius);
      
      // pie the data
      var pie = d3.layout.pie()
        .sort(null)
        .value(function(d) { return d; });
      data = pie(data);

      // create our gradient
      var colors = [],
          slice = 0,
          inPad = false;
      // 360 degrees
      d3.range(360).forEach(function(d, i) {
        // convert to radians
        var start = i * (Math.PI / 180),
            end = (i + 1) * (Math.PI / 180);
        // if we are in a padding area
        if ( Math.abs(data[slice].startAngle - start) < padding || 
            Math.abs(data[slice].endAngle - start) < padding ) {
          inPad = true;
        } else {
          // when to move to next slice
          if (inPad){
            // move to next slice
            slice++;
            // "stick" on last slice
            if (slice >= data.length) slice = 4;
          }
          inPad = false;
        }
        // only push if not in padding
        if (!inPad){
          colors.push({
            startAngle: start,
            endAngle: end,
            fill: d3.hsl(i, 1, .5).toString()
          });
        }
      });
      // add arcs
      svg.selectAll('.arc')
        .data(colors)
        .enter()
        .append('path')
        .attr('class', 'arc')
        .attr('d', arc)
        .style('fill', function(d){
          return d.fill;
        })
        .style('stroke',function(d){
          return d.fill;
        });
    </script>
  </body>

</html>