概要 实例 介绍 源码

和弦图

源文件:index.html

  1. <!DOCTYPE html>
  2. <meta charset="utf-8">
  3. <style>
  4. body {
  5. font: 10px sans-serif;
  6. }
  7. .group-tick line {
  8. stroke: #000;
  9. }
  10. .ribbons {
  11. fill-opacity: 0.67;
  12. }
  13. </style>
  14. <svg width="960" height="960"></svg>
  15. <script src="https://d3js.org/d3.v4.min.js"></script>
  16. <script>
  17. var matrix = [
  18. [11975, 5871, 8916, 2868],
  19. [ 1951, 10048, 2060, 6171],
  20. [ 8010, 16145, 8090, 8045],
  21. [ 1013, 990, 940, 6907]
  22. ];
  23. var svg = d3.select("svg"),
  24. width = +svg.attr("width"),
  25. height = +svg.attr("height"),
  26. outerRadius = Math.min(width, height) * 0.5 - 40,
  27. innerRadius = outerRadius - 30;
  28. var formatValue = d3.formatPrefix(",.0", 1e3);
  29. var chord = d3.chord()
  30. .padAngle(0.05)
  31. .sortSubgroups(d3.descending);
  32. var arc = d3.arc()
  33. .innerRadius(innerRadius)
  34. .outerRadius(outerRadius);
  35. var ribbon = d3.ribbon()
  36. .radius(innerRadius);
  37. var color = d3.scaleOrdinal()
  38. .domain(d3.range(4))
  39. .range(["#000000", "#FFDD89", "#957244", "#F26223"]);
  40. var g = svg.append("g")
  41. .attr("transform", "translate(" + width / 2 + "," + height / 2 + ")")
  42. .datum(chord(matrix));
  43. var group = g.append("g")
  44. .attr("class", "groups")
  45. .selectAll("g")
  46. .data(function(chords) { return chords.groups; })
  47. .enter().append("g");
  48. group.append("path")
  49. .style("fill", function(d) { return color(d.index); })
  50. .style("stroke", function(d) { return d3.rgb(color(d.index)).darker(); })
  51. .attr("d", arc);
  52. var groupTick = group.selectAll(".group-tick")
  53. .data(function(d) { return groupTicks(d, 1e3); })
  54. .enter().append("g")
  55. .attr("class", "group-tick")
  56. .attr("transform", function(d) { return "rotate(" + (d.angle * 180 / Math.PI - 90) + ") translate(" + outerRadius + ",0)"; });
  57. groupTick.append("line")
  58. .attr("x2", 6);
  59. groupTick
  60. .filter(function(d) { return d.value % 5e3 === 0; })
  61. .append("text")
  62. .attr("x", 8)
  63. .attr("dy", ".35em")
  64. .attr("transform", function(d) { return d.angle > Math.PI ? "rotate(180) translate(-16)" : null; })
  65. .style("text-anchor", function(d) { return d.angle > Math.PI ? "end" : null; })
  66. .text(function(d) { return formatValue(d.value); });
  67. g.append("g")
  68. .attr("class", "ribbons")
  69. .selectAll("path")
  70. .data(function(chords) { return chords; })
  71. .enter().append("path")
  72. .attr("d", ribbon)
  73. .style("fill", function(d) { return color(d.target.index); })
  74. .style("stroke", function(d) { return d3.rgb(color(d.target.index)).darker(); });
  75. // Returns an array of tick angles and values for a given group and step.
  76. function groupTicks(d, step) {
  77. var k = (d.endAngle - d.startAngle) / d.value;
  78. return d3.range(0, d.value, step).map(function(value) {
  79. return {value: value, angle: value * k + d.startAngle};
  80. });
  81. }
  82. </script>