[英]D3 x scale positioning
大家好,我是 d3.js 的新手,我需要一些關於 x 軸比例定位的幫助。
我需要將 x 軸比例放置在靠近 y 軸比例的位置。 簡單來說,我想向上移動 x 刻度以觸摸其底部尖端的 y 刻度。 請查看所附圖片以獲得清晰的圖片。
但是,我可以通過更改 y 比例范圍的值來向下移動 y 比例,但我不希望這樣做,因為我試圖避免圖像上看到的 x 軸標簽被切斷,因此我需要將它們向上移動。
這是我的整個代碼:
d3.json("month.json", function(error, jdata) {
var margin = {top: 20, right: 160, bottom: 35, left: 30};
var width = 960 - margin.left - margin.right,
height = 500 - margin.top - margin.bottom;
var svg = d3.select("#chart").append("svg")
.attr("width", 1200)
.attr("height", height + margin.top + margin.bottom)
.append("g")
.attr("transform", "translate(" + margin.left + "," + margin.top + ")");
var data = jdata.MonthsData;
var dataset = d3.layout.stack()(["Value", "Value3", "Value1", "Value2"].map(function (c) {
return data.map(function (d) {
if(d.Total == 0){
return { x: d.Location + " - Volume: "+ d.Max +")", y: +d[c]};
}else{
return { x: d.Location + " - Volume: "+ d.Max +" - Total: "+d.Total, y: +d[c]};
}
});
}));
var x = d3.scale.ordinal()
.domain(dataset[0].map(function (d){return d.x;}))
.rangeRoundBands([0, width-10], .25, .100);
var y = d3.scale.linear()
.domain([0, 380]).nice()
.range([height - 30, 0]);
var colors = ["#002672", "#B8CFFF","#70A0FF","#2970FF"];
var xAxis = d3.svg.axis().scale(x).orient("bottom");
var yAxis = d3.svg.axis().scale(y).orient("left").ticks(10).tickSize(-width, 0, 0).tickFormat( function(d) { return d } );
svg.append("g")
.attr("class", "y axis")
.call(yAxis);
svg.append("g")
.attr("class", "x axis")
.attr("transform", "translate(0," + height + ")")
.call(xAxis)
.selectAll(".tick text")
.call(wrap, x.rangeBand());
var groups = svg.selectAll("g.cost")
.data(dataset)
.enter()
.append("g")
.attr("class", "cost")
.style("fill", function (d, i) {return colors[i];});
var rect = groups.selectAll("rect")
.data(function (d) {return d;})
.enter().append("rect")
.attr("x", function (d) {return x(d.x);})
.attr("y", function (d) {return y(d.y + d.y0);})
.attr("height", function (d) {return y(d.y0) - y(d.y + d.y0);})
.attr("width", x.rangeBand())
.on("mouseover", function() { tooltip.style("display", null); })
.on("mouseout", function() { tooltip.style("display", "none"); })
.on("mousemove", function(d) {
var xPosition = d3.mouse(this)[0] - 15;
var yPosition = d3.mouse(this)[1] - 25;
tooltip.attr("transform", "translate(" + xPosition + "," + yPosition + ")");
tooltip.select("text").text(d.y);
})
.append("text")
.attr("class", "label")
.attr("x", function (d,i) {
return i * ( width / dataset.length);
})
.attr("y", function (d) {
var e = d.y;
return (height - e);
})
.attr("font-size", "16px")
.attr("fill", "red")
.text(function (d){
return d.y;
});
// Draw legend
var legend = svg.selectAll(".legend")
.data(colors)
.enter().append("g")
.attr("class", "legend")
.attr("transform", function(d, i) { return "translate(30," + i * 19 + ")"; });
legend.append("rect")
.attr("x", width - 18)
.attr("width", 18)
.attr("height", 18)
.style("fill", function(d, i) {return colors.slice().reverse()[i];});
legend.append("text")
.data(dataset)
.attr("x", width + 5)
.attr("y", 9)
.attr("dy", ".35em")
.style("text-anchor", "start")
.text(function(d, i) {
switch (i) {
case i: return d[i].x;
}
});
// Prep the tooltip bits, initial display is hidden
var tooltip = svg.append("g")
.attr("class", "tooltip")
.style("display", "none");
tooltip.append("rect")
.attr("width", 30)
.attr("height", 20)
.attr("fill", "white")
.style("opacity", 0.5);
tooltip.append("text")
.attr("x", 15)
.attr("dy", "1.2em")
.style("text-anchor", "middle")
.attr("font-size", "12px")
.attr("font-weight", "bold");
//Text Wrap funtion on x-axis labels
function wrap(text, width) {
text.each(function() {
var text = d3.select(this),
words = text.text().split(/\s+/).reverse(),
word,
line = [],
lineNumber = 0,
lineHeight = 1.1, // ems
y = text.attr("y"),
dy = parseFloat(text.attr("dy")),
tspan = text.text(null).append("tspan").attr("x", 0).attr("y", y).attr("dy", dy + "em");
while (word = words.pop()) {
line.push(word);
tspan.text(line.join(" "));
if (tspan.node().getComputedTextLength() > width) {
line.pop();
tspan.text(line.join(" "));
line = [word];
tspan = text.append("tspan").attr("x", 0).attr("y", y).attr("dy", ++lineNumber * lineHeight + dy + "em").text(word);
}
}
});
}
function type(d) {
d.value = +d.value;
return d;
}
});
通常,您定位軸的方式是取高度,然后減去任何填充。 這是從 Mike's Margin Convention Block截取的屏幕截圖
因此,您確定所需的邊距大小(在本例中為底部 x 軸),然后當您添加 x 軸時,您只需執行以下操作:
var margin = { top: 20, right: 10, bottom: 20, left: 10 };
svg.append("g")
.attr("class", "x axis")
.attr("transform", "translate(0," + height - margin.bottom + ")")
.call(xAxis)
.selectAll(".tick text")
.call(wrap, x.rangeBand());
然后應該考慮到您設置的任何邊距來定位您的軸。 請注意,這是D3
約定,因此最好進行此實踐。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.