text_word_parser.h 3.2 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126
  1. // This file is part of Desktop App Toolkit,
  2. // a set of libraries for developing nice desktop applications.
  3. //
  4. // For license and copyright information please follow this link:
  5. // https://github.com/desktop-app/legal/blob/master/LEGAL
  6. //
  7. #pragma once
  8. #include "ui/text/text.h"
  9. #include "ui/text/text_block.h"
  10. #include "ui/text/text_stack_engine.h"
  11. #include "ui/text/text_word.h"
  12. struct QGlyphLayout;
  13. struct QScriptItem;
  14. namespace Ui::Text {
  15. class WordParser {
  16. public:
  17. explicit WordParser(not_null<String*> string);
  18. private:
  19. struct ScriptLine {
  20. int length = 0;
  21. QFixed textWidth;
  22. };
  23. struct LineBreakHelper {
  24. ScriptLine tmpData;
  25. ScriptLine spaceData;
  26. QGlyphLayout glyphs;
  27. int glyphCount = 0;
  28. int maxGlyphs = INT_MAX;
  29. int currentPosition = 0;
  30. glyph_t previousGlyph = 0;
  31. QExplicitlySharedDataPointer<QFontEngine> previousGlyphFontEngine;
  32. QFixed rightBearing;
  33. QExplicitlySharedDataPointer<QFontEngine> fontEngine;
  34. const unsigned short *logClusters = nullptr;
  35. bool whiteSpaceOrObject = true;
  36. glyph_t currentGlyph() const;
  37. void saveCurrentGlyph();
  38. void calculateRightBearing(QFontEngine *engine, glyph_t glyph);
  39. void calculateRightBearing();
  40. void calculateRightBearingForPreviousGlyph();
  41. // We always calculate the right bearing right before it is needed.
  42. // So we don't need caching / optimizations referred to
  43. // delayed right bearing calculations.
  44. //static const QFixed RightBearingNotCalculated;
  45. //inline void resetRightBearing()
  46. //{
  47. // rightBearing = RightBearingNotCalculated;
  48. //}
  49. // We express the negative right bearing as an absolute number
  50. // so that it can be applied to the width using addition.
  51. QFixed negativeRightBearing() const;
  52. };
  53. struct BidiInitedAnalysis {
  54. explicit BidiInitedAnalysis(not_null<String*> text);
  55. QVarLengthArray<QScriptAnalysis, 4096> list;
  56. };
  57. void parse();
  58. const QCharAttributes *moveToNewItemGetAttributes();
  59. void pushAccumulatedWord();
  60. void processSingleGlyphItem(QFixed added = 0);
  61. void wordProcessed(int nextWordStart, bool spaces = false);
  62. void wordContinued(int nextPartStart, bool spaces = false);
  63. void accumulateWhitespaces();
  64. void ensureWordForRightPadding();
  65. void maybeStartUnfinishedWord();
  66. void pushFinishedWord(uint16 position, QFixed width, QFixed rbearing);
  67. void pushUnfinishedWord(uint16 position, QFixed width, QFixed rbearing);
  68. void pushNewline(uint16 position, int newlineBlockIndex);
  69. void addNextCluster(
  70. int &pos,
  71. int end,
  72. ScriptLine &line,
  73. int &glyphCount,
  74. const QScriptItem &current,
  75. const unsigned short *logClusters,
  76. const QGlyphLayout &glyphs);
  77. [[nodiscard]] bool isLineBreak(
  78. const QCharAttributes *attributes,
  79. int index) const;
  80. [[nodiscard]] bool isSpaceBreak(
  81. const QCharAttributes *attributes,
  82. int index) const;
  83. const not_null<String*> _t;
  84. QString &_tText;
  85. std::vector<Block> &_tBlocks;
  86. std::vector<Word> &_tWords;
  87. BidiInitedAnalysis _analysis;
  88. StackEngine _engine;
  89. QTextEngine &_e;
  90. LineBreakHelper _lbh;
  91. const QCharAttributes *_attributes = nullptr;
  92. int _wordStart = 0;
  93. bool _addingEachGrapheme = false;
  94. int _lastGraphemeBoundaryPosition = -1;
  95. ScriptLine _lastGraphemeBoundaryLine;
  96. int _item = -1;
  97. int _newItem = -1;
  98. int _itemEnd = 0;
  99. };
  100. } // namespace Ui::Text