Skip to content Skip to sidebar Skip to footer

D3 Grouped Bar Chart Update Pattern Not Working

It's been few days already while I'm trying to grasp this. I was also looking into similar questions with no progress so far. I have a simple grouped bar chart. I am able to draw i

Solution 1:

Inside your draw function, instead of:

var groupsUpdate = groupsSelection.data(data);

It should be:

var groupsUpdate = chart.selectAll('.group').data(data);

Or, alternatively, move the variable assignment...

var groupsSelection = chart.selectAll('.group');

... to inside draw.

The reason for this is that groupsSelection was defined before any group being appended, and it is an empty selection.

Here is your code with that change only:

// .chart -> .group -> .bar
// each group has 2 bars: one for data 'in' and another for 'out'
var data = [{
  "in": 0,
  "out": 40
}, {
  "in": 10,
  "out": 39
}, {
  "in": 20,
  "out": 40
}];

var chart = d3.select('.chart');
var groupsSelection = chart.selectAll('.group');
var xScale = d3.scaleLinear().range([0, 666]);

function draw(data) {
  // make data flat array of numbers to find max value for xScale domain
  var dataValues = data.reduce(
    (result, currentVal) => result.concat([currentVal.in, currentVal.out]), []
  );
  // set x axis domain
  xScale.domain([0, d3.max(dataValues)]);

  var groupsUpdate = chart.selectAll('.group').data(data);

  // groups
  var groups = groupsUpdate.enter()
    .append('div')
    .attr('class', 'group')
    .merge(groupsUpdate);

  // derive data from parent group
  var barsUpdate = groups.selectAll('.bar')
    .data(d => [d.in, d.out]);

  var bars = barsUpdate.enter()
    .append('div')
    .attr('class', 'bar')
    .merge(barsUpdate)
    .text(d => d)
    .style('background', 'pink')
    .style('width', d => xScale(d) + 'px');

  barsUpdate.exit().remove();

  // groups exit
  groupsUpdate.exit().remove();
}

// 1st time draw
draw(data)

// delayed data update (2nd draw)
setTimeout(() => {
  var newData = [{
    "in": 0,
    "out": 40
  }, {
    "in": 20,
    "out": 40
  }];
  draw(newData);
}, 1000);
.chart {
  background: #fff;
  width: 686px;
  padding: 20px;
}

.group {
  background: grey;
  padding: 10px;
  border: solid 1px #000;
  margin: 10px 0;
}

.bar {
  background: white;
  margin: 5px 0;
  height: 20px;
  border: solid 1px yellow;
  font-size: 16px;
  line-height: 20px;
  text-indent: 10px;
  color: white;
  font-weight: bold;
  text-shadow: 0 1px 1px #000;
}
<script src="https://d3js.org/d3.v4.min.js"></script>
<div class="chart"></div>

Post a Comment for "D3 Grouped Bar Chart Update Pattern Not Working"