使用d3.js

时间:2015-12-22 06:30:16

标签: javascript d3.js charts

我正在尝试创建堆积条形图,这样当您点击它们时,它会为您提供有关该堆栈的更详细信息。

考虑每个条形代表一个主题,条形图中的每个部分代表掌握学生在六个不同级别学习该主题:比如1级到6级; 1级学生的表现非常糟糕,6级表明学生已经掌握了这门课程

让我们说最初堆叠的条看起来像这样:

enter image description here

如果选择主题,请说实心几何。

然后我点击其中一个栏:

enter image description here

如上图所示,可以看到有4名学生在这门课程中挣扎,而4名学生需要练习这门课程......等等...

然后,堆叠的条形图将以这种方式展开,为我提供有关enter image description here

的更多信息

我们怎样才能在D3中做到这一点?

任何帮助表示感谢。

1 个答案:

答案 0 :(得分:2)

我没有看到任何研究或尝试学习或使用D3。虽然D3最初可能令人生畏,但文档使其相当平易近人,如果您的问题稍微具体一点,您可能会在这里获得更多的牵引力。

那说,看看下面的例子。您将看到D3是将数据映射到元素和编排DOM操作的帮助器。另请注意,普通的旧CSS可以完成大部分交互要求。最后,要明白你可以通过许多不同的方式完成这些任务这只是一个快速入侵。

var student_data = [{
  category: 'Struggling',
  students: [
    'Ben',
    'Elizabeth'
  ]
}, {
  category: 'Level One',
  students: [
    'Jessica',
    'Matt'
  ]
}, {
  category: 'Mastered',
  students: [
    'John',
    'Katie'
  ]
}];

// the quantile scale maps an input domain of
// values to an output range of values by 'spreading'
// the domain across the range.
var colors = d3.scale.quantile()
  .domain([0, student_data.length])
  .range(['red', 'grey', 'lightblue', 'darkblue']);

// the base element
var root = d3.select('.panel');

// selectAll ~= querySelectorAll
// says, find all elements with class 'category'
// if none exist, prepare a selection of
// student_data.length elements
var display = root.selectAll('.category')
  .data(student_data);

// take the prepared selection and
// for each
display.enter()
  // create an element
  .append('div')
  // assign the 'category' class to the element
  .attr('class', 'category')
  // set the background color
  .style('background-color', function(d, i) {
    // d is the current array element of student_data
    // i is the index of the current array element of student_data
    // so, pass i to the colors scale/map to get back a color
    return colors(i);
  })
  // add a mouse enter handler to set the text of a
  // yet to be added label.
  .on('mouseenter', function(d) {
    // this is the current element
    d3.select(this)
      // so, select the first element
      // with class label
      .select('.label')
      // and set it's text to the category property
      // of current array element of student_data
      .text(d.category);
  })
  // add a mouse leave handler to reset the text of the still
  // yet to be added label.
  .on('mouseleave', function(d) {
    d3.select(this).select('.label').text(d.students.length);
  })
  // for each created element
  .each(function(d) {
    // select the current element
    var selection = d3.select(this);
    // create the label referenced above
    var label = selection.append('div')
      // assign it a class of 'label'
      .attr('class', 'label')
      // and set it's text to count of
      // the students property
      .text(function(d) {
        // d = student_data[i]
        return d.students.length;
      });
    // also, prepare a new selection of
    // elements for each of the student names
    var names = selection
      .selectAll('.student')
      .data(d.students);
    // take the prepared selection and
    // for each
    names.enter()
      // create an element
      .append('div')
      // assign the 'student' class
      .attr('class', 'student')
      // and set the text to that
      // of the current element
      .text(function(dd) {
        // dd = student_data[i].students[j]
        return dd;
      });
  });
div {
  -webkit-box-sizing: border-box;
  -moz-box-sizing: border-box;
  box-sizing: border-box;
  font-family: arial;
}
.panel {
  display: -webkit-box;
  display: -moz-box;
  display: -ms-flexbox;
  display: -webkit-flex;
  display: flex;
  -webkit-box-align: start;
  -webkit-align-items: flex-start;
  -ms-flex-align: start;
  align-items: flex-start;
  width: 100%;
  font-size: 0.8rem;
}
.category {
  display: inline-block;
  padding: 0.5rem;
  min-width: 2rem;
  min-height: 2rem;
  color: white;
  background-color: black;
  transition: all 250ms ease;
}
.category:hover {
  min-width: 10rem;
  width: auto;
  height: auto;
  transition: all 250ms ease;
}
.label {
  transition: all 250ms ease;
}
.student {
  display: none;
  padding: 0.25rem;
  width: 100%;
  color: black;
  background-color: white;
  cursor: pointer;
  transition: all 250ms ease;
}
.student:hover {
  background-color: lightblue;
}
.category:hover .label {
  padding-bottom: 0.5rem;
}
.category:hover .student {
  display: inline-block;
}
<div class='panel'></div>
<script src="https://cdnjs.cloudflare.com/ajax/libs/d3/3.4.11/d3.min.js"></script>