MultiLineText.js 2.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118
  1. import {Text} from "./Text.js";
  2. /**
  3. * Multiple line text drawing directly into the canvas.
  4. *
  5. * Has support for basic text indent and alignment.
  6. *
  7. * @class
  8. * @extends {Text}
  9. */
  10. function MultiLineText()
  11. {
  12. Text.call(this);
  13. /**
  14. * Maximum width of the text content. After text reaches the max width a line break is placed.
  15. *
  16. * Can be set to null to be ignored.
  17. *
  18. * @type {number}
  19. */
  20. this.maxWidth = null;
  21. /**
  22. * Height of each line of text, can be smaller or larger than the actual font size.
  23. *
  24. * Can be set to null to be ignored.
  25. *
  26. * @type {number}
  27. */
  28. this.lineHeight = null;
  29. }
  30. MultiLineText.prototype = Object.create(Text.prototype);
  31. MultiLineText.prototype.constructor = MultiLineText;
  32. MultiLineText.prototype.type = "MultiLineText";
  33. Object2D.register(MultiLineText, "MultiLineText");
  34. MultiLineText.prototype.draw = function(context, viewport, canvas)
  35. {
  36. context.font = this.font;
  37. context.textAlign = this.textAlign;
  38. context.textBaseline = this.textBaseline;
  39. var lineHeight = this.lineHeight || Number.parseFloat(this.font);
  40. var lines = this.text.split("\n");
  41. var offsetY = 0;
  42. // Iterate trough all lines (breakpoints)
  43. for(var i = 0; i < lines.length; i++)
  44. {
  45. var line = lines[i];
  46. var size = context.measureText(line);
  47. var sublines = [];
  48. // Split into multiple sub-lines
  49. if(this.maxWidth !== null && size.width > this.maxWidth)
  50. {
  51. while(line.length > 0)
  52. {
  53. var subline = "";
  54. var subsize = context.measureText(subline + line[0]);
  55. while(subsize.width < this.maxWidth && line.length > 0)
  56. {
  57. subline += line[0];
  58. line = line.substr(1);
  59. subsize = context.measureText(subline + line[0]);
  60. }
  61. sublines.push(subline);
  62. }
  63. }
  64. // Fits into a single line
  65. else
  66. {
  67. sublines = [line];
  68. }
  69. for(var j = 0; j < sublines.length; j++)
  70. {
  71. if(this.fillStyle !== null)
  72. {
  73. context.fillStyle = this.fillStyle;
  74. context.fillText(sublines[j], this.position.x, this.position.y + offsetY);
  75. }
  76. if(this.strokeStyle !== null)
  77. {
  78. context.strokeStyle = this.strokeStyle;
  79. context.strokeText(sublines[j], this.position.x, this.position.y + offsetY);
  80. }
  81. offsetY += lineHeight;
  82. }
  83. }
  84. };
  85. MultiLineText.prototype.serialize = function(recursive)
  86. {
  87. var data = Text.prototype.serialize.call(this, recursive);
  88. data.maxWidth = this.maxWidth;
  89. data.lineHeight = this.lineHeight;
  90. return data;
  91. };
  92. MultiLineText.prototype.parse = function(data)
  93. {
  94. Text.prototype.parse.call(this, data);
  95. this.maxWidth = data.maxWidth;
  96. this.lineHeight = data.lineHeight;
  97. };
  98. export {MultiLineText};