#javascript #d3.js
#javascript #d3.js
Вопрос:
Я пытаюсь сгенерировать график на основе некоторых данных из файла CSV.
Мой код:
<script>
var svg = d3.select("body").append("svg")
.attr("width", 1000)
.attr("height", 1000);
function render(data){
var circles = svg.selectAll("circle").data(data);
circles.enter().append("circle")
.attr("r", 1);
circles
.attr("cx", function (d){return d[' Monthly Term']})
.attr("cy", function (d){ return d[' Principal Balance']/1000});
circles.exit().remove();
}
d3.csv("{% static "data/Total.csv" %}" , type, function(myArray){
render(myArray);
myArray.forEach(function(d){
console.log(d[' Principal Payment'] ", " d[' Interest Payment'] ", " d[' Principal Balance'] ", " d[' Monthly Term']);
});
});
function type(d){
d.value = d.value;
return d;
}
</script>
Все «работает», но ось Y кажется перевернутой.
Не уверен, что вы, ребята, видите окно проверки, но значение Y должно уменьшаться по мере увеличения значения x.
Есть идеи?
Ответ №1:
В выводе на консоль значение Y уменьшается по мере увеличения значения X. В SVG расположение 0,0 находится вверху слева. Таким образом, меньшее значение Y ближе к верхней части экрана. Попробуйте инвертировать значение Y:
.attr("cy", function (d){ return height - d[' Principal Balance']/1000});
Ответ №2:
Как указывает @genestd в своем ответе, координаты SVG y начинаются сверху и увеличиваются в значении, двигаясь вниз. Как правило, вы должны использовать масштаб d3 для сопоставления значений пользовательского пространства со значениями координат svg. Глядя на классический пример столбчатой диаграммы, вы видите эти строки:
var x = d3.scaleBand().rangeRound([0, width]).padding(0.1),
y = d3.scaleLinear().rangeRound([height, 0]);
Здесь масштаб x изменяется от 0 до ширины, а y — от высоты до 0. Они меняются местами друг от друга из-за того, что вы видите, x увеличивается слева направо, а y увеличивается сверху вниз. Этот .range
вызов отображает координаты SVG.
Позже вы увидите эту строку:
y.domain([0, d3.max(data, function(d) { return d.frequency; })]);
Теперь эта часть сопоставила координаты пространства пользователя, указав, что они выполняются от 0 до максимума наших данных.
Затем вы можете использовать шкалы как функции при построении своей точки.
В вашем коде это может выглядеть так:
var svg = d3.select("body").append("svg")
.attr("width", 1000)
.attr("height", 1000);
var x = d3.scaleLinear().range([0, 1000]),
y = d3.scaleLinear().range([1000, 0]);
function render(data){
x.domain([0, d3.max(data, function(d){
return d[' Monthly Term'];
});
y.domain([0, d3.max(data, function(d){
return d[' Principal Balance']/1000;
});
var circles = svg.selectAll("circle").data(data);
circles.enter().append("circle")
.attr("r", 1);
circles
.attr("cx", function (d){return x(d[' Monthly Term']); })
.attr("cy", function (d){ return y(d[' Principal Balance']/1000); });
...