2013-08-20 4 views
2

У меня есть диаграмма с пузырем/разбросом, работающая в d3.js, но по какой-то причине, когда я пытаюсь добавить обработчик события клика по кругам, я получаю неопределенная ошибка.d3.js: событие click в диаграмме пузырьков/рассеяния

Я пробовал перемещать обработчики кликов в порядке, я пробовал простые предупреждения, но получаю ту же ошибку.

TypeError: 'undefined' is not a function (near '....on("click", function(d...') 

В чем проблема?

function click(d) { 
    svg.selectAll(".active").classed("active", false); 
    d3.select(this).classed("active", active = d); 
} 

function reset() { 
    svg.selectAll(".active").classed("active", active = false); 
} 

function renderBubbleGraph(data){ 

// define some variables for the bubble chart 
    var w = parseInt(mainWidth(), 10), 
     h = 500, 
     margin = {top: 48, right: 48, bottom: 48, left: 72}; 

    var svg = d3.select("#chart") 
      .append("svg") 
      .attr("width", w) 
      .attr("height", h); 

    var x = d3.scale.linear().domain([0, 50]).range([margin.left, w-margin.right]), 
     y = d3.scale.linear().domain([0, 80000]).range([h-margin.bottom, margin.top]); 

    var xAxis = d3.svg.axis() 
         .scale(x) 
         .orient("bottom") 
         .ticks(5), 

     yAxis = d3.svg.axis() 
         .scale(y) 
         .orient("left") 
         .ticks(10) 
         .tickFormat(function(d) {return abbreviate(d,0,false,'K'); }); 
    //bubble radius range and scale 
    var max_r = d3.max(data.map(
          function (d) { return d.Size; })), 
      r = d3.scale.linear() 
       .domain([0, d3.max(data, function (d) { return d.Size; })]) 
       .range([0, 80]); 

    //start drawing the chart 
    svg.append("g") 
     .attr("class", "axis x-axis") 
     .attr("transform", "translate(0, "+(h-margin.bottom)+")") 
     .call(xAxis); 

    svg.append("g") 
     .attr("class", "axis y-axis") 
     .attr("transform", "translate("+(margin.left)+", 0)") 
     .call(yAxis);  

    svg.append("text") 
     .attr("class", "loading") 
     .text("Loading ...") 
     .attr("x", function() { return w/2; }) 
     .attr("y", function() { return h/2-5; }); 

    svg.selectAll(".loading").remove(); 

    svg.selectAll("circle") 
     .data(data) 
     .enter() 
     .append("circle") 
     .attr("class", "bubble") 
     .attr("cx", function (d) { return x(d.Number);}) 
     .attr("cy", function (d) { return y(d.Avg);}) 
     .transition() 
     .duration(800) 
     .attr("r", function (d) { return r(d.Size); }) 
     .on("click", function(d){click(d)}); 

} 
$(document).ready(function() { 

    $.getJSON('/data/mydata.json', function(data) { 
     renderBubbleGraph(data); 
    }); 

}); 

Спасибо!

+0

Вы пытались подключить слушателя до инициализации перехода? –

+0

Я думаю, что сработало, потому что теперь я получаю другие ошибки ... так что спасибо Ларсу. – rolfsf

ответ

3

Переходы в D3 не поддерживают функцию «on» They only exist on selections. Таким образом, вам нужно будет переместить прослушиватель событий выше вашего перехода и после вашего добавления. Как это:

svg.selectAll("circle") 
    .data(data) 
    .enter() 
    .append("circle") 
    .on("click", function(d){click(d)}) 
    .attr("class", "bubble") 
    .attr("cx", function (d) { return x(d.Number);}) 
    .attr("cy", function (d) { return y(d.Avg);}) 
    .transition() 
    .duration(800) 
    .attr("r", function (d) { return r(d.Size); }); 

Это должно быть поведение, которое вы хотите в любом случае, как вы не хотели бы, чтобы добавить прослушиватель событий нажмите каждый раз, когда вы повторно сделать ваши круги, если бы вы назвать renderBubbleGraph в более позднее время с различными параметры рисования.

+1

Спасибо за разъяснение @ nross83. Это определенно вызывает прослушиватель событий щелчка, хотя функция моего обработчика - нет. Я также замечаю, что переход тоже не работает. Вернуться к API! – rolfsf

Смежные вопросы