饼图阴影或 3D d3.js
Pie chart drop-shadow or 3D d3.js
我是 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`
主要问题是您将阴影附加到饼图的每个楔形上。正如您所注意到的,这会导致它被附加到每个切片。相反,您可以做的是在饼图后面创建一个与图表本身大小相等的圆圈。然后你所要做的就是将 blur/shadow/etc 附加到该特征:
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>
我是 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`
主要问题是您将阴影附加到饼图的每个楔形上。正如您所注意到的,这会导致它被附加到每个切片。相反,您可以做的是在饼图后面创建一个与图表本身大小相等的圆圈。然后你所要做的就是将 blur/shadow/etc 附加到该特征:
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>