Подсказки для нескольких линейных графиков в D3
Я новичок в D3, и мое требование-получить несколько линейных графиков и предоставить подсказки для них.
Я мог бы получить несколько линейных графиков, чтобы появиться, но я иду неправильно в получении нескольких точек подсказки.
Я также новичок в javascript. Так что любая помощь будет очень признательна.
Вот мой код.
<script>
function showData(obj, d) {
var coord = d3.mouse(obj);
var infobox = d3.select(".infobox");
// now we just position the infobox roughly where our mouse is
infobox.style("left", (coord[0] + 200) + "px" );
infobox.style("top", (coord[1] - 130) + "px");
$(".infobox").html(d);
$(".infobox").show();
}
function hideData() {
$(".infobox").hide();
}
var xx,yy;
function xx(e) {
return x(e.date); };
function yy(e) {
return y(e.returns); };
var draw = function() {
var margin = {top:100,left:200,right:200,bottom:100},
width = 1150 - margin.left - margin.right,
height = 500 - margin.top - margin.bottom;
var parseDate = d3.time.format("%Y-%m-%d").parse;
x = d3.time.scale().range([0,width]);
y = d3.scale.linear().range([height,0]);
//values of the axis is plotted here
var xAxis = d3.svg.axis().scale(x).orient("bottom");
var yAxis = d3.svg.axis().scale(y).orient("left");
var svg = d3.select("#chart").append("svg")
.attr("width" , width + margin.left + margin.right)
.attr("height" , height + margin.top + margin.bottom)
.attr("pointer-events" , "all")
.append("g")
//this is the line that positions the graph
.attr("transform" , "translate(" + margin.left + "," + margin.top +") ");
var activeReturns = new Array();
var passiveReturns = new Array();
var D3Obj = new Array();
var line = d3.svg.line()
.interpolate("basis")
.x(function(d) { return x(d.date); })
.y(function(d) { return y(d.returns);});
d3.json("d3.v3/sample1.json",function(error,result) {
result.data.forEach(function(d){
var arObj = new Object();
arObj.date = parseDate(d.date);
arObj.returns = +d.returns;
var prObj = new Object();
prObj.date = parseDate(d.date);
prObj.returns = +d.ticker_performance;
activeReturns.push(arObj);
passiveReturns.push(prObj);
});
D3Obj.push(activeReturns);
D3Obj.push(passiveReturns);
// this is where i tell that the line graph to be done
x.domain(d3.extent(D3Obj[0], function(d) {return d.date ;} ));
y.domain(d3.extent(D3Obj[0], function(d) {return d.returns ;} ));
svg.append("g")
.attr("class" , "x axis")
.call(xAxis)
.attr("transform","translate(0 ,"+ height + ")")
svg.append("g")
.attr("class" , "y axis")
//this is where yaxis line is added
.call(yAxis)
.append("text")
.attr("transform", "rotate(-90)")
.attr("y", 6)
.attr("dy", ".71em")
.style("text-anchor", "end")
.text("Price ($)");
svg.selectAll(".line")
.data(D3Obj)
.enter().append("path")
.attr("class","line")
.attr("d",line)
//this is where i am adding the tooltips
//tooltip for 1st line
svg.selectAll("circle")
.data(D3Obj[0])
.enter().append("circle")
.attr("fill", "red")
.attr("r", 2)
.attr("cx", xx)
.attr("cy", yy)
.on("mouseover", function(d) { showData(this, d.returns);})
.on("mouseout", function(){ hideData();});
//tooltip for 2nd line - this is where i think i am going wrong.
svg.selectAll("circle")
.data(D3Obj[1])
.enter().append("circle")
.attr("fill", "steelblue")
.attr("r", 2)
.attr("cx", xx)
.attr("cy", yy)
.on("mouseover", function(d) { showData(this, d.returns);})
.on("mouseout", function(){ hideData();});
});
$("#chart").append("<div class='infobox' style='display:none;'>Test</div>");
};
</script>
1 ответ:
Когда вы создаете вторую точку, на самом деле ничего не происходит. Функция
.data()
попытается сопоставить элементы данных, которые вы передаете, с тем, что вы выбрали (в данном случае один круг), и преуспеет в этом. Это означает, что ваш выбор enter пуст и ничего не происходит.Способ d3 состоит в том, чтобы передать в все данные, которые вы хотите использовать для создания элементов сразу и соответственно обрабатывать в функциях для установки атрибутов и т. д. То есть ваш код должен выглядеть как-то иначе как
Это создаст два круга и присоединит к ним соответствующих слушателей.svg.selectAll("circle") .data(D3Obj) .enter().append("circle") .attr("fill", function(d, i) { if(i == 0) { return "red"; } else { return "steelblue"; } }) .attr("r", 2) .attr("cx", xx) .attr("cy", yy) .on("mouseover", function(d) { showData(this, d.returns);}) .on("mouseout", function(){ hideData();});