1 // Copyright 2019 Google LLC. 2 #ifndef Paragraph_DEFINED 3 #define Paragraph_DEFINED 4 5 #include "modules/skparagraph/include/FontCollection.h" 6 #include "modules/skparagraph/include/Metrics.h" 7 #include "modules/skparagraph/include/ParagraphStyle.h" 8 #include "modules/skparagraph/include/TextStyle.h" 9 10 class SkCanvas; 11 12 namespace skia { 13 namespace textlayout { 14 15 class Paragraph { 16 17 public: 18 Paragraph(ParagraphStyle style, sk_sp<FontCollection> fonts); 19 20 virtual ~Paragraph() = default; 21 getMaxWidth()22 SkScalar getMaxWidth() { return fWidth; } 23 getHeight()24 SkScalar getHeight() { return fHeight; } 25 getMinIntrinsicWidth()26 SkScalar getMinIntrinsicWidth() { return fMinIntrinsicWidth; } 27 getMaxIntrinsicWidth()28 SkScalar getMaxIntrinsicWidth() { return fMaxIntrinsicWidth; } 29 getAlphabeticBaseline()30 SkScalar getAlphabeticBaseline() { return fAlphabeticBaseline; } 31 getIdeographicBaseline()32 SkScalar getIdeographicBaseline() { return fIdeographicBaseline; } 33 getLongestLine()34 SkScalar getLongestLine() { return fLongestLine; } 35 didExceedMaxLines()36 bool didExceedMaxLines() { return fExceededMaxLines; } 37 38 virtual void layout(SkScalar width) = 0; 39 40 virtual void paint(SkCanvas* canvas, SkScalar x, SkScalar y) = 0; 41 42 // Returns a vector of bounding boxes that enclose all text between 43 // start and end glyph indexes, including start and excluding end 44 virtual std::vector<TextBox> getRectsForRange(unsigned start, 45 unsigned end, 46 RectHeightStyle rectHeightStyle, 47 RectWidthStyle rectWidthStyle) = 0; 48 49 virtual std::vector<TextBox> getRectsForPlaceholders() = 0; 50 51 // Returns the index of the glyph that corresponds to the provided coordinate, 52 // with the top left corner as the origin, and +y direction as down 53 virtual PositionWithAffinity getGlyphPositionAtCoordinate(SkScalar dx, SkScalar dy) = 0; 54 55 // Finds the first and last glyphs that define a word containing 56 // the glyph at index offset 57 virtual SkRange<size_t> getWordBoundary(unsigned offset) = 0; 58 59 virtual void getLineMetrics(std::vector<LineMetrics>&) = 0; 60 61 virtual size_t lineNumber() = 0; 62 63 virtual void markDirty() = 0; 64 65 // This function will return the number of unresolved glyphs or 66 // -1 if not applicable (has not been shaped yet - valid case) 67 virtual int32_t unresolvedGlyphs() = 0; 68 69 // Experimental API that allows fast way to update "immutable" paragraph 70 virtual void updateTextAlign(TextAlign textAlign) = 0; 71 virtual void updateText(size_t from, SkString text) = 0; 72 virtual void updateFontSize(size_t from, size_t to, SkScalar fontSize) = 0; 73 virtual void updateForegroundPaint(size_t from, size_t to, SkPaint paint) = 0; 74 virtual void updateBackgroundPaint(size_t from, size_t to, SkPaint paint) = 0; 75 76 enum VisitorFlags { 77 kWhiteSpace_VisitorFlag = 1 << 0, 78 }; 79 struct VisitorInfo { 80 const SkFont& font; 81 SkPoint origin; 82 SkScalar advanceX; 83 int count; 84 const uint16_t* glyphs; // count values 85 const SkPoint* positions; // count values 86 const uint32_t* utf8Starts; // count+1 values 87 unsigned flags; 88 }; 89 90 // lineNumber begins at 0. If info is null, this signals the end of that line. 91 using Visitor = std::function<void(int lineNumber, const VisitorInfo*)>; 92 virtual void visit(const Visitor&) = 0; 93 94 protected: 95 sk_sp<FontCollection> fFontCollection; 96 ParagraphStyle fParagraphStyle; 97 98 // Things for Flutter 99 SkScalar fAlphabeticBaseline; 100 SkScalar fIdeographicBaseline; 101 SkScalar fHeight; 102 SkScalar fWidth; 103 SkScalar fMaxIntrinsicWidth; 104 SkScalar fMinIntrinsicWidth; 105 SkScalar fLongestLine; 106 bool fExceededMaxLines; 107 }; 108 } // namespace textlayout 109 } // namespace skia 110 111 #endif // Paragraph_DEFINED 112