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