更新有关 d3.js 中数据变化的图表

Updating a graph on change of data in d3.js

您好,我正在使用以下代码通过使用来自服务调用的数据来创建条形图。这样做的问题是,随着来自服务调用的数据发生变化,它不会反映在条形图中,而是保持其原始状态。 Appname 和 Appcount 是我从服务调用中得到的两件事

jQuery(function($) 
{
Appnames = []//array will be populated from service call,
  Appcount = []//array will be populated from serv`enter code here`ice call,
  chart,
  width = 700,
  bar_height = 40,
  gap = 2,
  height = bar_height * Appnames.length;
  var margin = {top: 20, right: 120, bottom: 20, left: 120};

  /* step 1 - create the background*/
  chart = d3.select($("#step-1")[0])
.append('svg')
.attr('class', 'chart')
.attr('width', width)
.attr('height', height);

  /* step 2 - create the bars*/
  var x, y;

 chart = d3.select($("#step-2")[0])
.append('svg')
.attr('class', 'chart')
.attr('width', width + margin.right + margin.left)
.attr('height', height);

 x = d3.scale.linear()
 .domain([0, d3.max(Appcount)])
 .range([0, width]);

 y = function(i) { return bar_height * i; }

 chart.selectAll("rect")
 .data(Appcount)
 .enter().append("rect")
 .attr("x", 0)
 .attr("y", function(d, i) { return y(i);})
 .attr("width", x)
 .attr("height", bar_height);

  /* step 3 - add counts to the bars*/
chart = d3.select($("#step-3")[0])
.append('svg')
.attr('class', 'chart')
.attr('width', width)
.attr('height', height);

 chart.selectAll("rect")
.data(Appcount)
.enter().append("rect")
.attr("x", 0)
.attr("y", function(d, i) { return y(i);})
.attr("width", x)
.attr("height", bar_height);

 chart.selectAll("text")
.data(Appcount)
.enter().append("text")
.attr("x", x)
.attr("y", function(d, i){ return y(i) + bar_height/2; } )
.attr("dx", -5)
.attr("dy", ".36em")
.attr("text-anchor", "end")
.text(String);

 /* step 4 - add Appnames to bars*/
 var left_width = 100;

chart = d3.select($("#step-4")[0])
.append('svg')
.attr('class', 'chart')
.attr('width', left_width + width)
.attr('height', height);

chart.selectAll("rect")
.data(Appcount)
.enter().append("rect")
.attr("x", left_width)
.attr("y", function(d, i) { return y(i);})
.attr("width", x)
.attr("height", bar_height);

chart.selectAll("text.score")
.data(Appcount)
.enter().append("text")
.attr("x", function(d) { return x(d) + left_width; })
.attr("y", function(d, i) { return y(i) + bar_height / 2;})
.attr("dx", -5)
.attr("dy", ".36em")
.attr("text-anchor", "end")
.attr('class', 'score')
.text(String);

 chart.selectAll("text.name")
.data(Appnames)
.enter().append("text")
.attr("x", left_width / 2)
.attr("y", function(d, i){ return y(i) +bar_height/2; } )
.attr("dy", ".36em")
.attr("text-anchor", "middle")
.attr('class', 'name')
.text(String);

 /* step 5 - add a ruler line to the bars*/
 var gap = 2, yRangeBand;
// redefine y for adjusting the gap
yRangeBand = bar_height + 2 * gap;
y = function(i) { return yRangeBand * i; };

chart = d3.select($("#step-5")[0])
.append('svg')
.attr('class', 'chart')
.attr('width', left_width + width + 40)
.attr('height', (bar_height + gap * 2) * Appnames.length + 30)
.append("g")
.attr("transform", "translate(10, 20)");

chart.selectAll("line")
.data(x.ticks(d3.max(Appcount)))
.enter().append("line")
.attr("x1", function(d) { return x(d) + left_width; })
.attr("x2", function(d) { return x(d) + left_width; })
.attr("y1", 0)
.attr("y2", (bar_height + gap * 2) * Appnames.length);

chart.selectAll(".rule")
.data(x.ticks(d3.max(Appcount)))
.enter().append("text")
.attr("class", "rule")
.attr("x", function(d) { return x(d) + left_width; })
.attr("y", 0)
.attr("dy", -6)
.attr("text-anchor", "middle")
.attr("font-size", 10)
.text(String);

 chart.selectAll("rect")
.data(Appcount)
.enter().append("rect")
.attr("x", left_width)
.attr("y", function(d, i) { return y(i) + gap; })
.attr("width", x)
.attr("height", bar_height);

 chart.selectAll("text.score")
.data(Appcount)
.enter().append("text")
.attr("x", function(d) { return x(d) + left_width; })
.attr("y", function(d, i) { return y(i) + yRangeBand/2;})
.attr("dx", -5)
.attr("dy", ".36em")
.attr("text-anchor", "end")
.attr('class', 'score')
.text(String);

 chart.selectAll("text.name")
.data(Appnames)
.enter().append("text")
.attr("x", left_width / 2)
.attr("y", function(d, i){ return y(i) + yRangeBand/2; } )
.attr("dy", ".36em")
.attr("text-anchor", "middle")
.attr('class', 'name')
.text(String); }(jQuery));

d3 使用 enter, update and exit pattern。您的代码仅处理 enter 状态。拆分它以处理所有 3 个状态:

var rects = chart.selectAll("rect")
  .data(Appcount); //<-- create your data join

rects.enter().append("rect"); //<-- ENTER - when data enters the join append a rect element to dom

rects.exit().remove(); //<-- EXIT - when data leaves the join, remove the rect

rects.attr("x", 0) //<-- UPDATE - update the rects based on data
  .attr("y", function(d, i) { return y(i);})
  .attr("width", x)
  .attr("height", bar_height);