Javascript 在给定示例d3js中,如何填充条之间的区域
我正试图创造这样的东西 我把它看作是一个有扭曲的水平堆叠条形图。我需要一些关于如何转换的指南 或者至少看起来像那样。Javascript 在给定示例d3js中,如何填充条之间的区域,javascript,d3.js,bar-chart,data-visualization,Javascript,D3.js,Bar Chart,Data Visualization,我正试图创造这样的东西 我把它看作是一个有扭曲的水平堆叠条形图。我需要一些关于如何转换的指南 或者至少看起来像那样。 我面临的第一个问题是将堆叠条形图居中对齐。意味着如果移除yaxis并使所有钢筋居中对齐。如何使所有堆叠居中 您当前的实现 答复 通过图形中心将其旋转90度,如代码中所示 var svg = d3.select("body").append("svg") .attr("id", "mySVG") .attr("width", width + margin.left
我面临的第一个问题是将堆叠条形图居中对齐。意味着如果移除yaxis并使所有钢筋居中对齐。如何使所有堆叠居中 您当前的实现 答复 通过图形中心将其旋转90度,如代码中所示
var svg = d3.select("body").append("svg")
.attr("id", "mySVG")
.attr("width", width + margin.left + margin.right)
.attr("height", height + margin.top + margin.bottom)
.append("g")
.attr("transform", "translate(" + margin.left + "," + margin.top + ")rotate(90," + width / 2 + "," + height / 2 + ")");
var legend = d3.select("svg").append("g");
这将旋转图形,它看起来像
接下来介绍如何用图形显示图例
//this will get the last g(group) element as we want to attach the legend to it
var lastG = d3.select(d3.selectAll(".state")[0].pop());
//this will get all the rectangles in the last group
var lastRect = d3.select(d3.selectAll(".state")[0].pop()).selectAll("rect");
//to get the bbox's y (since its rotated by 90 so x will become y)
var lastx = lastG.node().getBBox().y;
var lineFunction = d3.svg.line()
.x(function (d) {
return d.x;
})
.y(function (d) {
return d.y;
})
.interpolate("step-before");
//to each rectangle in the last group
lastRect[0].forEach(function (d, i) {
//make an svg point
var point = document.getElementById("mySVG").createSVGPoint();
point.x = (d3.select(d).attr("x") + +parseFloat(d3.select(d).attr("width")));
point.y = (parseFloat(d3.select(d).attr("y")) + parseFloat(d3.select(d).attr("height")));
//the point after rotation moves to the new position.
var newPoint = point.matrixTransform(d.getScreenCTM());
//making a circle and appending to the legend group
legend.append("circle").attr("r", 2).attr("cx", newPoint.x).attr("cy", newPoint.y).style("fill", "red").attr("class", "entry");
var x1 = lastx;
var y1 = newPoint.y + 50 + (10 * i);
legend.append("circle").attr("r", 2).attr("cx", x1).attr("cy", y1).style("fill", "red").attr("class", "entry");
//making the line with start point and end point
var lineData = [{
x: newPoint.x,
y: newPoint.y
}, {
x: x1,
y: y1
}];
//make the line and append it to legend
legend.append("path")
.attr("d", lineFunction(lineData))
.attr("stroke", "blue")
.attr("stroke-width", 2)
.attr("fill", "none");
//adding the text with label
legend.append("text").attr("x", x1+20).attr("y", y1).text(d3.select(d).data()[0].name)
});
完整的工作代码
我添加了注释以帮助您理解代码 你能在下一步中画一个小草图吗?我不知道你的意思是什么,如果删除yaxis并使所有钢筋中心对齐。嗨,你知道如何填充每个钢筋之间的区域。钢筋的连接角。使它看起来像上传的图像。;是的,但我觉得那会很漂亮,不是吗;
//this will get the last g(group) element as we want to attach the legend to it
var lastG = d3.select(d3.selectAll(".state")[0].pop());
//this will get all the rectangles in the last group
var lastRect = d3.select(d3.selectAll(".state")[0].pop()).selectAll("rect");
//to get the bbox's y (since its rotated by 90 so x will become y)
var lastx = lastG.node().getBBox().y;
var lineFunction = d3.svg.line()
.x(function (d) {
return d.x;
})
.y(function (d) {
return d.y;
})
.interpolate("step-before");
//to each rectangle in the last group
lastRect[0].forEach(function (d, i) {
//make an svg point
var point = document.getElementById("mySVG").createSVGPoint();
point.x = (d3.select(d).attr("x") + +parseFloat(d3.select(d).attr("width")));
point.y = (parseFloat(d3.select(d).attr("y")) + parseFloat(d3.select(d).attr("height")));
//the point after rotation moves to the new position.
var newPoint = point.matrixTransform(d.getScreenCTM());
//making a circle and appending to the legend group
legend.append("circle").attr("r", 2).attr("cx", newPoint.x).attr("cy", newPoint.y).style("fill", "red").attr("class", "entry");
var x1 = lastx;
var y1 = newPoint.y + 50 + (10 * i);
legend.append("circle").attr("r", 2).attr("cx", x1).attr("cy", y1).style("fill", "red").attr("class", "entry");
//making the line with start point and end point
var lineData = [{
x: newPoint.x,
y: newPoint.y
}, {
x: x1,
y: y1
}];
//make the line and append it to legend
legend.append("path")
.attr("d", lineFunction(lineData))
.attr("stroke", "blue")
.attr("stroke-width", 2)
.attr("fill", "none");
//adding the text with label
legend.append("text").attr("x", x1+20).attr("y", y1).text(d3.select(d).data()[0].name)
});