MultiLineText.js 2.6 KB

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