PieChart.js 3.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162
  1. import {Object2D} from "../../Object2D.js";
  2. /**
  3. * Pie chart represents a set of data in a pie like chart graph.
  4. *
  5. * The values are drawn in porportion relative to their sum.
  6. *
  7. * @class
  8. * @extends {Object2D}
  9. */
  10. function PieChart(data)
  11. {
  12. Object2D.call(this);
  13. /**
  14. * Data to be displayed on the pie chart. Each element should store a value and a stroke/fill styles.
  15. *
  16. * Each element should use the following structure {value: 0.0, fillStyle: ..., strokestyle: ...}.
  17. *
  18. * @type {Array<{value: number, fillStyle: ColorStyle, strokeStyle: ColorStyle}>}
  19. */
  20. this.data = data !== undefined ? data : [];
  21. /**
  22. * Variable pie slice size based on their value compared to the biggest value.
  23. *
  24. * @type {boolean}
  25. */
  26. this.sliceSize = false;
  27. /**
  28. * Radius of the pie chart object.
  29. *
  30. * @type {number}
  31. */
  32. this.radius = 50;
  33. /**
  34. * The line width of each pie chart section.
  35. *
  36. * @type {number}
  37. */
  38. this.lineWidth = 1.0;
  39. /**
  40. * Start angle of the pie chart.
  41. *
  42. * @type {number}
  43. */
  44. this.startAngle = 0;
  45. /**
  46. * End angle of the pie chart.
  47. *
  48. * @type {number}
  49. */
  50. this.endAngle = 2 * Math.PI;
  51. }
  52. PieChart.prototype = Object.create(Object2D.prototype);
  53. PieChart.prototype.constructor = PieChart;
  54. PieChart.prototype.type = "PieChart";
  55. Object2D.register(PieChart, "PieChart");
  56. PieChart.prototype.isInside = function(point)
  57. {
  58. return point.length() <= this.radius;
  59. };
  60. PieChart.prototype.draw = function(context)
  61. {
  62. if(this.data.length === 0)
  63. {
  64. return;
  65. }
  66. var sum = 0;
  67. var max = this.data[0].value;
  68. for(var i = 0; i < this.data.length; i++)
  69. {
  70. sum += this.data[i].value;
  71. if(this.data[i].value > max)
  72. {
  73. max = this.data[i].value;
  74. }
  75. }
  76. context.lineWidth = this.lineWidth;
  77. var angleRange = this.endAngle - this.startAngle;
  78. var angle = this.startAngle;
  79. // Fill
  80. for(var i = 0; i < this.data.length; i++)
  81. {
  82. var section = angleRange * (this.data[i].value / sum);
  83. if(this.data[i].fillStyle)
  84. {
  85. context.beginPath();
  86. context.moveTo(0, 0);
  87. var radius = this.sliceSize ? ((this.data[i].value / max) * this.radius) : this.radius;
  88. context.arc(0, 0, radius, angle, angle + section);
  89. context.moveTo(0, 0);
  90. context.fillStyle = this.data[i].fillStyle.get(context);
  91. context.fill();
  92. }
  93. angle += section;
  94. }
  95. // Stroke
  96. for(var i = 0; i < this.data.length; i++)
  97. {
  98. var section = angleRange * (this.data[i].value / sum);
  99. if(this.data[i].strokeStyle)
  100. {
  101. context.beginPath();
  102. context.moveTo(0, 0);
  103. var radius = this.sliceSize ? ((this.data[i].value / max) * this.radius) : this.radius;
  104. context.arc(0, 0, radius, angle, angle + section);
  105. context.moveTo(0, 0);
  106. context.strokeStyle = this.data[i].strokeStyle.get(context);
  107. context.stroke();
  108. }
  109. angle += section;
  110. }
  111. };
  112. PieChart.prototype.serialize = function(recursive)
  113. {
  114. var data = Object2D.prototype.serialize.call(this, recursive);
  115. data.radius = this.radius;
  116. data.lineWidth = this.lineWidth;
  117. data.startAngle = this.startAngle;
  118. data.endAngle = this.endAngle;
  119. data.sliceSize = this.sliceSize;
  120. return data;
  121. };
  122. PieChart.prototype.parse = function(data, root)
  123. {
  124. Object2D.prototype.parse.call(this, data, root);
  125. this.radius = data.radius;
  126. this.lineWidth = data.lineWidth;
  127. this.startAngle = data.startAngle;
  128. this.endAngle = data.endAngle;
  129. this.sliceSize = data.sliceSize;
  130. };
  131. export {PieChart};