饼图阴影或3D d3.js

时间:2017-03-17 01:59:56

标签: javascript d3.js pie-chart dropshadow

我是D3.js的新手,我开始学习饼图。我正在尝试创建阴影或添加3d形状。我可以让阴影出现,但现在馅饼的每个切片都有自己的阴影。是否有可能让馅饼作为一个整体使用阴影而不是每个单独的切片?我希望它能够在没有模糊和一种颜色的情况下使其锋利。

首先,我一直在使用其他帖子中包含的example。如果可以使用阴影或者有另一种方法来获得这种3D形状,请告诉我。谢谢。

片段

var width = 500,
    height = 500,
    radius = Math.min(width, height) / 2.5;

var color = d3.scale.ordinal()
    .range(["#ED5545","#ED933A","#337382","#EDD55D","#64B5CE","#AA2731","#F7B166","#7DD886"])

var arc = d3.svg.arc()
    .outerRadius(radius - 40)
    .innerRadius(0);

var pie = d3.layout.pie()
    .sort(null)
    .value(function(d) { return d.amount; });

var svg = d3.select("body").append("svg")
    .attr("width", width)
    .attr("height", height)
    .append("g")
    .attr("transform", "translate(" + width / 2 + "," + height / 2 + ")");


//Drop Shadow    
var defs = svg.append("defs");

var filter = defs.append("filter")
      .attr("id", "dropshadow")

  filter.append("feGaussianBlur")
      .attr("in", "SourceAlpha")
      .attr("stdDeviation", 0)
      .attr("result", "blur");
  filter.append("feOffset")
      .attr("in", "blur")
      .attr("dx", 0)
      .attr("dy", 15)
      .attr("result", "offsetBlur");
   filter.append("feFlood")
        .attr("in", "offsetBlur")
        .attr("flood-color", "#93864d")
        .attr("flood-opacity", "1")
        .attr("result", "offsetColor");
    filter.append("feComposite")
        .attr("in", "offsetColor")
        .attr("in2", "offsetBlur")
        .attr("operator", "in")
        .attr("result", "offsetBlur");

  var feMerge = filter.append("feMerge");

  feMerge.append("feMergeNode")
      .attr("in", "offsetBlur")
  feMerge.append("feMergeNode")
      .attr("in", "SourceGraphic");

//CSV
d3.csv("foodData.csv", function(error, data) {

  data.forEach(function(d) {
    d.amount = +d.amount;
  });

  var g = svg.selectAll(".arc")
      .data(pie(data))
      .enter().append("g")
      .attr("filter", "url(#dropshadow)")
      .attr("class", "arc");

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

});



.arc path {
  stroke: #93864d;
  stroke-width: 3;
}


 food,amount
 Pizza,30
 Burgers,20
 Seafood,2
 Junk,17
 bbq,7
 Other,4
 Mexican,10
 Vegetables,3`

1 个答案:

答案 0 :(得分:0)

主要问题是你要将阴影附加到馅饼的每个楔形物上。正如您所注意到的,这会导致它被附加到每个切片。相反,你可以做的是在饼图后面创建一个圆圈,其大小与图表本身相同。然后你要做的就是将模糊/阴影/等附加到该特征:



var width = 400;
var height = 400;
var radius = 175;

var svg = d3.select('body').append('svg')
  .attr('width',width)
  .attr('height',height);
  
// you can use to groups to order elements, they appear in the order they are appended:
var g1 = svg.append('g').attr('transform','translate('+width/2+','+height/2+')');
var g2 = svg.append('g').attr('transform','translate('+width/2+','+height/2+')');


// shadow stuff:
var defs = svg.append("defs");

var filter = defs.append("filter")
      .attr("id", "dropshadow")

  filter.append("feGaussianBlur")
      .attr("in", "SourceAlpha")
      .attr("stdDeviation", 0)
      .attr("result", "blur");
  filter.append("feOffset")
      .attr("in", "blur")
      .attr("dx", 0)
      .attr("dy", 15)
      .attr("result", "offsetBlur");
   filter.append("feFlood")
        .attr("in", "offsetBlur")
        .attr("flood-color", "#93864d")
        .attr("flood-opacity", "1")
        .attr("result", "offsetColor");
    filter.append("feComposite")
        .attr("in", "offsetColor")
        .attr("in2", "offsetBlur")
        .attr("operator", "in")
        .attr("result", "offsetBlur");

  var feMerge = filter.append("feMerge");

  feMerge.append("feMergeNode")
      .attr("in", "offsetBlur")
  feMerge.append("feMergeNode")
      .attr("in", "SourceGraphic");

// Now back to the pie chart:
var data = [10,50,15,30,40,35];
var color = d3.schemeCategory10;

var pie = d3.pie();

var path = d3.arc()
  .outerRadius(radius)
  .innerRadius(0);
  
var arc = g2.selectAll(".arc")
  .data(pie(data))
  .enter()
  .append('path')
  .attr('d',path)
  .attr('fill',function(d,i) { return color[i]; });
  
var shadow = g1.append('circle')
  .attr('r',radius)
  .attr("filter", "url(#dropshadow)");

<script src="https://cdnjs.cloudflare.com/ajax/libs/d3/4.5.0/d3.min.js"></script>
&#13;
&#13;
&#13;