D3甜甜圈图表功能仅在第一次被称为

时间:2018-05-24 20:04:01

标签: javascript function d3.js charts

我创建了一个用D3制作圆环图的功能,它在第一次调用时效果很好。但是,随后它被称为SVG元素,它附加的是空的,路径被附加到第一个图表。我是D3的新手,所以我很有可能在我的功能上做坏事。控制台中没有错误消息。如果你看到奇怪的东西,请告诉我。谢谢!!

这是功能:

function donutChart (id, data, color) {

var donut = (function(one){ 
    console.log("Hello");
    var width = 400;
    var height = 400;
    var radius = 200;
    var greyColor = '#e8e8e8';
    var dataColor = '#1dafd3';
    var red
    var colors = d3.scaleOrdinal([color, greyColor]);
    var piedata = [{
            name: "one", value: data
        }, {
            name: "two", value: (1 - data)
        }];

    var arc = d3.arc().innerRadius(radius - 50).outerRadius(radius);

    var donutChart = d3.select(id).append('svg')
      .attr('width', width)
      .attr('height', height)
      .append('g')
      .attr('transform', 'translate(' + (width - radius) + ',' + (height - radius) + ')');

    var pie = d3.pie()
      .sort(null)
      .value(function(piedata) { return piedata.value; });

    var arc_g = d3.select('svg g').selectAll('arc').data(pie(piedata)).enter()
        .append('g')
        .attr('class', 'slice');
    console.log()

    arc_g.append('path').attr("d",arc)
    .attr('fill', function(d, range) {
       return colors(range);
  })
  })();
};  

这是函数调用,它第一次运行很好但不是第二次。

donutChart (songData.audio_features[0].danceability, "#1dafd3"); 
donutChart (songData.audio_features[0].acousticness, "#1dafd3");

1 个答案:

答案 0 :(得分:0)

问题在于每次调用函数时,都会在此行附加一个新的SVG元素:

var donutChart = d3.select(id).append('svg')

因为它选择了它使用ID找到的第一个元素,并且无论如何都附加一个新的SVG元素。

当您尝试使用此行附加弧时会出现第二个问题

var arc_g = d3.select('svg g').selectAll('arc')

同样,“select”只会找到DOM中的第一个匹配项,这是您原来的SVG> G元素,并选择它可以在那里找到的弧

第三,.selectAll('arc')将找不到任何内容,因为现有元素要么是'path'要么是'slice',所以你需要selectAll来匹配其中任何一个。

纠正问题:

//append the SVG on the first call, with a dummy data, and each subsequent call will use the existing element in the DOM
var donutChart = d3.select(id).selectAll('svg')
      .data([null])

donutChart = donutChart.enter().append('svg')
      .merge(donutChart)
      .attr('width', width)
      .attr('height', height)

var g = donutChart.append('g')
      .attr('transform', 'translate(' + (width - radius) + ',' + (height - radius) + ')');

    var pie = d3.pie()
      .sort(null)
      .value(function(piedata) { return piedata.value; });

//selectAll on class '.slice'
    var arc_g = g.selectAll('.slice')
        .data(pie(piedata))

//create new g and path elements on enter (ie if new), and then update d and color after a merge()
    arc_g = arc_g.enter()
        .append('g')
        .attr('class', 'slice')
        .append('path')
        .merge(arc_g)
        .attr("d",arc)
        .attr('fill', function(d, range) {
           return colors(range);
        })

有关合并的更多信息,请参阅:https://github.com/d3/d3-selection#selection_merge