问题描述
我想在D3中实现条形图,但是我在dx轴上的值是Date类型,D3库应该接受的数据类型,但似乎给了我这样的错误:属性宽度:预期长度,"NaN".这是我的代码:
I want to implement a bar chart in D3, but my values on the dx axis are of type Date, data type which the D3 library should accept, but it seems to give me an error like this: attribute width: Expected length, "NaN".This is my code:
<html>
<head>
<meta charset="utf-8">
<title>a bar graph</title>
</head>
<style>
.axis path,
.axis line{
fill: none;
stroke: black;
shape-rendering: crispEdges;
}
.axis text {
font-family: sans-serif;
font-size: 11px;
}
.MyRect {
fill: steelblue;
}
.MyText {
fill: white;
text-anchor: middle;
}
</style>
<body>
<script src="http://d3js.org/d3.v4.min.js" charset="utf-8"></script>
<script>
var width=400;
var height=400;
var svg=d3.select("body")
.append("svg")
.attr("width",width)
.attr("height",height);
var padding = {left:30, right:30, top:20, bottom:20};
var dataset=[10,20,30,40,33,24,12,5];
var xScale = d3.scaleBand()
.domain(d3.range(dataset.length))
.range([0, width-padding.left-padding.right]);
var yScale = d3.scaleLinear()
.domain([0,d3.max(dataset)])
.range([height-padding.top-padding.bottom,0]);
var xAxis = d3.axisBottom()
.scale(xScale)
var yAxis = d3.axisLeft()
.scale(yScale)
var rectPadding=4;
var rects = svg.selectAll(".Myrect")
.data(dataset)
.enter()
.append("rect")
.attr("class","Myrect")
.attr("transform","translate(" + padding.left + "," + padding.top + ")")
.attr("x",function(d,i){
return xScale(i) + rectPadding/2;
})
.attr("y",function(d){
return yScale(d);
})
.attr("width",xScale.range()- rectPadding)
.attr("height",function(d){
return height - padding.top - padding.bottom - yScale(d);
});
var texts = svg.selectAll(".MyText")
.data(dataset)
.enter()
.append("text")
.attr("class","MyText")
.attr("transform","translate(" + padding.left + "," + padding.top + ")")
.attr("x", function(d,i){
return xScale(i) + rectPadding/2;
})
.attr("y",function(d){
return yScale(d);
})
.attr("dx",function(){
return (xScale.range() - rectPadding)/2;
})
.attr("dy",function(d){
return 20;
})
.text(function(d){
return d;
});
svg.append("g")
.attr("class","axis")
.attr("transform","translate(" + padding.left + "," + (height - padding.bottom) + ")")
.call(xAxis);
svg.append("g")
.attr("class","axis")
.attr("transform","translate(" + padding.left + "," + padding.top + ")")
.call(yAxis);
</script>
</body>
</html>
另一个错误:属性dx:预期长度"NaN".我认为这是由乐队的规模引起的,但是在使用了官方的介绍之后,它仍然无法正常工作.官方介绍:
And the another error: attribute dx: Expected length, "NaN". I think it arises from band scales, but after using the introduction of the official, it still can't work.The introduction of the official:
var x = d3.scaleBand()
.domain(["a", "b", "c"])
.range([0, width]);
因此,当我想调用代码时,我认为应该在粘贴的代码中这样使用它:
So when I want to call the code, I think it should be used like this in my pasted code:
var texts = svg.selectAll(".MyText")
.data(dataset)
.enter()
.append("text")
.attr("class","MyText")
.attr("transform","translate(" + padding.left + "," + padding.top + ")")
.attr("x", function(d,i){
return xScale(i) + rectPadding/2;
})
.attr("y",function(d){
return yScale(d);
})
.attr("dx",function(){
return (xScale.range() - rectPadding)/2;
})
.attr("dy",function(d){
return 20;
})
.text(function(d){
return d;
});
但这似乎给了我两个错误.我是初学者.非常感谢你!
But it seems to give me two errors. I'm a beginner. Thank you very much!
推荐答案
现在,对于矩形的宽度和文本的dx
,您正在使用:
Right now, for the width of the rectangles and the dx
of the texts, you're using:
xScale.range() - rectPadding
但是xScale.range()
返回一个数组,而array - number
将给您一个NaN
.而且您无法使用NaN
...
But xScale.range()
returns an array, and array - number
will give you a NaN
. And you're not getting anywhere with a NaN
...
您应该使用:
xScale.bandwidth();
不仅返回正确的数字,而且这也是您要查找的内容.
Which not only returns a proper number, but it's also what you're looking for.
这是您所做的更改的代码:
Here is your code with that change:
<style>
.axis path,
.axis line {
fill: none;
stroke: black;
shape-rendering: crispEdges;
}
.axis text {
font-family: sans-serif;
font-size: 11px;
}
.MyRect {
fill: steelblue;
}
.MyText {
fill: white;
text-anchor: middle;
}
</style>
<body>
<script src="https://d3js.org/d3.v4.min.js" charset="utf-8"></script>
<script>
var width = 400;
var height = 400;
var svg = d3.select("body")
.append("svg")
.attr("width", width)
.attr("height", height);
var padding = {
left: 30,
right: 30,
top: 20,
bottom: 20
};
var dataset = [10, 20, 30, 40, 33, 24, 12, 5];
var xScale = d3.scaleBand()
.domain(d3.range(dataset.length))
.range([0, width - padding.left - padding.right]);
var yScale = d3.scaleLinear()
.domain([0, d3.max(dataset)])
.range([height - padding.top - padding.bottom, 0]);
var xAxis = d3.axisBottom()
.scale(xScale)
var yAxis = d3.axisLeft()
.scale(yScale)
var rectPadding = 4;
var rects = svg.selectAll(".Myrect")
.data(dataset)
.enter()
.append("rect")
.attr("class", "Myrect")
.attr("transform", "translate(" + padding.left + "," + padding.top + ")")
.attr("x", function(d, i) {
return xScale(i) + rectPadding / 2;
})
.attr("y", function(d) {
return yScale(d);
})
.attr("width", xScale.bandwidth() - rectPadding)
.attr("height", function(d) {
return height - padding.top - padding.bottom - yScale(d);
});
var texts = svg.selectAll(".MyText")
.data(dataset)
.enter()
.append("text")
.attr("class", "MyText")
.attr("transform", "translate(" + padding.left + "," + padding.top + ")")
.attr("x", function(d, i) {
return xScale(i) + rectPadding / 2;
})
.attr("y", function(d) {
return yScale(d);
})
.attr("dx", function() {
return (xScale.bandwidth() - rectPadding) / 2;
})
.attr("dy", function(d) {
return 20;
})
.text(function(d) {
return d;
});
svg.append("g")
.attr("class", "axis")
.attr("transform", "translate(" + padding.left + "," + (height - padding.bottom) + ")")
.call(xAxis);
svg.append("g")
.attr("class", "axis")
.attr("transform", "translate(" + padding.left + "," + padding.top + ")")
.call(yAxis);
</script>
</body>
PS::您不需要rectPadding
.只需在band标度中设置填充即可:
PS: You don't need rectPadding
. Just set the padding in the band scale:
var xScale = d3.scaleBand()
.domain(d3.range(dataset.length))
.range([0, width-padding.left-padding.right])
.padding(0.2);//some value here
这篇关于错误:< rect>属性宽度:期望的长度"NaN".和< text>属性dx:预期长度,"NaN".的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!