如何更新饼图?

时间:2016-12-30 15:11:06

标签: javascript d3.js

我正在尝试制作一个饼图,当我按下“2016”按钮时会更新,但我不是更新我创建一个新的饼图,如何更改饼图的值?提前致谢。我试图搜索一个问题,但所有问题都是如此具体。

var dataset = [{
  key: "Alumnos",
  value: 15
}, {
  key: "AlumnosFCT",
  value: 12
}];
var w = 300;
var h = 300;
var outerRadius = w / 2;
var innerRadius = 0;

var arc = d3.svg.arc()
  .innerRadius(innerRadius)
  .outerRadius(outerRadius);


var color = d3.scale.ordinal()
  .domain([15, 12])
  .range(["#FF4081", "#3F51B5"]);

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

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

var arcs = svg.selectAll("g.arc")
  .data(pie(dataset))
  .enter()
  .append("g")
  .attr("class", "arc")
  .attr("transform", "translate(" + outerRadius + ", " + outerRadius + ")");

arcs.append("path")
  .attr("fill", function(d, i) {
    return color(i);
  })
  .attr("d", arc);

arcs.append("text")
  .attr("transform", function(d) {
    return "translate(" + arc.centroid(d) + ")";
  })
  .attr("text-anchor", "middle")
  .attr("font-family", "sans-serif")
  .text(function(d) {
    return d.value;
  });

d3.selectAll("button").on("click", function() {
  var paragraphID = d3.select(this).attr("id");
  if (paragraphID == "2016") {
    dataset.push({
      key: "Alumnos",
      value: 20
    }, {
      key: "AlumnosFCT",
      value: 18
    });
    dataset.shift();
    dataset.shift();
  }

  var arc = d3.svg.arc()
    .innerRadius(innerRadius)
    .outerRadius(outerRadius);


  var color = d3.scale.ordinal()
    .domain([15, 12])
    .range(["#FF4081", "#3F51B5"]);

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

  var pie = d3.layout.pie()
    .sort(null)
    .value(function(d) {
      return d.value;
    });
  var arcs = svg.selectAll("g.arc")
    .data(pie(dataset))
    .enter()
    .append("g")
    .attr("class", "arc")
    .attr("transform", "translate(" + outerRadius + ", " + outerRadius + ")");

  arcs.append("path")
    .attr("fill", function(d, i) {
      return color(i);
    })
    .attr("d", arc);
  arcs.append("text")
    .attr("transform", function(d) {
      return "translate(" + arc.centroid(d) + ")";
    })
    .attr("text-anchor", "middle")
    .attr("font-family", "sans-serif")
    .text(function(d) {
      return d.value;
    });
});
<script src="https://cdnjs.cloudflare.com/ajax/libs/d3/3.4.11/d3.min.js"></script>

<button id="2016">2016</button>

1 个答案:

答案 0 :(得分:2)

一般来说,只要你在他们的API中工作,d3就可以很好地管理DOM元素。通过这种方式,您可以编写一个可以为新数据创建新元素的函数,或者使用与这些元素相关的新数据更新现有元素。

请参阅以下更新版本的代码段,特别是将依赖于数据的DOM操作转移到名为update的函数中:

&#13;
&#13;
/*** 
* Original Code
***/

var dataset = [{
  key: "Alumnos",
  value: 15
}, {
  key: "AlumnosFCT",
  value: 12
}];
var w = 300;
var h = 300;
var outerRadius = w / 2;
var innerRadius = 0;

var arc = d3.svg.arc()
  .innerRadius(innerRadius)
  .outerRadius(outerRadius);


var color = d3.scale.ordinal()
  .domain([15, 12])
  .range(["#FF4081", "#3F51B5"]);

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

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

/*** 
* update function for data dependent manipulations
***/
function update(data) {
  var arcs = svg.selectAll("g.arc").data(pie(data));
  arcs.exit().remove();
  arcs.enter().append("g")
    .attr("class", "arc")
    .attr("transform", "translate(" + outerRadius + ", " + outerRadius + ")");

  var paths = arcs.selectAll('path').data(function (d, i) {
    d.idx = i;
    return [d];
  })
  paths.enter().append('path');
  paths
  	.attr("fill", function(d) {
      return color(d.idx);
    })
    .attr("d", arc);
  
  var texts = arcs.selectAll('text').data(function (d) {
    return [d];
  })
  texts.enter().append('text');
  texts.attr("transform", function(d) {
      return "translate(" + arc.centroid(d) + ")";
    })
    .attr("text-anchor", "middle")
    .attr("font-family", "sans-serif")
    .text(function(d) {
      return d.value;
    });
}

update(dataset);

/*** 
* Handler to set new data based on button clicked
***/
d3.select('button').on('click', function() {
  var newData;
  if (this.id === '2016') {
    newData = [{
      key: "Alumnos",
      value: 20
    }, {
      key: "AlumnosFCT",
      value: 18
    }];
    
    update(newData);
  }
});
&#13;
<script src="https://cdnjs.cloudflare.com/ajax/libs/d3/3.4.11/d3.min.js"></script>

<button id="2016">2016</button>
&#13;
&#13;
&#13;

(根据您的浏览器,您可能需要滚动视图才能看到&#34; 2016&#34;按钮)

请注意以下优点:

  • 仅在调用update时更新其数据需要更改的元素。
  • 如果您在更新时添加新数据点,则会添加一个新元素,而不会触及应保持不变的元素(通过enter
  • 如果您在更新时删除数据点,则该元素将被删除(通过exit

d3版本: 3.4.11