• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 // Copyright 2019 Google LLC.
2 #ifndef ParagraphStyle_DEFINED
3 #define ParagraphStyle_DEFINED
4 
5 #include "include/core/SkFontStyle.h"
6 #include "include/core/SkScalar.h"
7 #include "include/core/SkString.h"
8 #include "modules/skparagraph/include/DartTypes.h"
9 #include "modules/skparagraph/include/TextStyle.h"
10 #ifdef ENABLE_TEXT_ENHANCE
11 #include "drawing.h"
12 #endif
13 
14 #include <stddef.h>
15 #include <algorithm>
16 #include <limits>
17 #include <string>
18 #include <utility>
19 #include <vector>
20 
21 namespace skia {
22 namespace textlayout {
23 
24 #ifdef ENABLE_TEXT_ENHANCE
25 struct TextTabs {
26     TextAlign alignment;
27     SkScalar location;
28     bool operator==(const TextTabs& other) const {
29         return (alignment == other.alignment) && nearlyEqual(location, other.location);
30     }
31 };
32 
33 struct TextBlobRecordInfo {
34     std::shared_ptr<RSTextBlob> fBlob{nullptr};
35     SkPoint fOffset{0.0f, 0.0f};
36     ParagraphPainter::SkPaintOrID fPaint;
37 };
38 
39 enum class TextVerticalAlign {
40     BASELINE,
41     BOTTOM,
42     CENTER,
43     TOP,
44 };
45 
46 enum class WordBreakType {
47     NORMAL,     // to be done.
48     BREAK_ALL,  // break occur after any characters.
49     BREAK_WORD, // break only occur after word.
50     BREAK_HYPHEN,
51 };
52 
53 enum class LineBreakStrategy {
54     GREEDY,        // faster and linear.
55     HIGH_QUALITY,  // breaking tries to split the lines as efficiently as possible
56     BALANCED,      // breaking tries to make the line lengths even
57 };
58 #endif
59 struct StrutStyle {
60     StrutStyle();
61 
getFontFamiliesStrutStyle62     const std::vector<SkString>& getFontFamilies() const { return fFontFamilies; }
setFontFamiliesStrutStyle63     void setFontFamilies(std::vector<SkString> families) { fFontFamilies = std::move(families); }
64 
65 #ifdef ENABLE_TEXT_ENHANCE
getFontStyleStrutStyle66     RSFontStyle getFontStyle() const { return fFontStyle; }
setFontStyleStrutStyle67     void setFontStyle(RSFontStyle fontStyle) { fFontStyle = fontStyle; }
68 #else
getFontStyleStrutStyle69     SkFontStyle getFontStyle() const { return fFontStyle; }
setFontStyleStrutStyle70     void setFontStyle(SkFontStyle fontStyle) { fFontStyle = fontStyle; }
71 #endif
72 
getFontSizeStrutStyle73     SkScalar getFontSize() const { return fFontSize; }
setFontSizeStrutStyle74     void setFontSize(SkScalar size) { fFontSize = size; }
75 
setHeightStrutStyle76     void setHeight(SkScalar height) { fHeight = height; }
getHeightStrutStyle77     SkScalar getHeight() const { return fHeight; }
78 
setLeadingStrutStyle79     void setLeading(SkScalar Leading) { fLeading = Leading; }
getLeadingStrutStyle80     SkScalar getLeading() const { return fLeading; }
81 
getStrutEnabledStrutStyle82     bool getStrutEnabled() const { return fEnabled; }
setStrutEnabledStrutStyle83     void setStrutEnabled(bool v) { fEnabled = v; }
84 
getForceStrutHeightStrutStyle85     bool getForceStrutHeight() const { return fForceHeight; }
setForceStrutHeightStrutStyle86     void setForceStrutHeight(bool v) { fForceHeight = v; }
87 
getHeightOverrideStrutStyle88     bool getHeightOverride() const { return fHeightOverride; }
setHeightOverrideStrutStyle89     void setHeightOverride(bool v) { fHeightOverride = v; }
90 
setHalfLeadingStrutStyle91     void setHalfLeading(bool halfLeading) { fHalfLeading = halfLeading; }
getHalfLeadingStrutStyle92     bool getHalfLeading() const { return fHalfLeading; }
93 
94 #ifdef ENABLE_TEXT_ENHANCE
setWordBreakTypeStrutStyle95     void setWordBreakType(const WordBreakType& wordBreakType) { fWordBreakType = wordBreakType; }
getWordBreakTypeStrutStyle96     WordBreakType getWordBreakType() const { return fWordBreakType; }
97 
setLineBreakStrategyStrutStyle98     void setLineBreakStrategy(const LineBreakStrategy& lineBreakStrategy) { fLineBreakStrategy = lineBreakStrategy; }
getLineBreakStrategyStrutStyle99     LineBreakStrategy getLineBreakStrategy() const { return fLineBreakStrategy; }
100 #endif
101 
102     bool operator==(const StrutStyle& rhs) const {
103 #ifdef ENABLE_TEXT_ENHANCE
104         return this->fEnabled == rhs.fEnabled &&
105                this->fHeightOverride == rhs.fHeightOverride &&
106                this->fForceHeight == rhs.fForceHeight &&
107                this->fHalfLeading == rhs.fHalfLeading &&
108                nearlyEqual(this->fLeading, rhs.fLeading) &&
109                nearlyEqual(this->fHeight, rhs.fHeight) &&
110                nearlyEqual(this->fFontSize, rhs.fFontSize) &&
111                this->fFontStyle == rhs.fFontStyle &&
112                this->fFontFamilies == rhs.fFontFamilies &&
113                this->fWordBreakType == rhs.fWordBreakType &&
114                this->fLineBreakStrategy == rhs.fLineBreakStrategy;
115 #else
116         return this->fEnabled == rhs.fEnabled &&
117                this->fHeightOverride == rhs.fHeightOverride &&
118                this->fForceHeight == rhs.fForceHeight &&
119                this->fHalfLeading == rhs.fHalfLeading &&
120                nearlyEqual(this->fLeading, rhs.fLeading) &&
121                nearlyEqual(this->fHeight, rhs.fHeight) &&
122                nearlyEqual(this->fFontSize, rhs.fFontSize) &&
123                this->fFontStyle == rhs.fFontStyle &&
124                this->fFontFamilies == rhs.fFontFamilies;
125 #endif
126     }
127 
128 private:
129 
130     std::vector<SkString> fFontFamilies;
131 #ifdef ENABLE_TEXT_ENHANCE
132     RSFontStyle fFontStyle;
133 #else
134     SkFontStyle fFontStyle;
135 #endif
136     SkScalar fFontSize;
137     SkScalar fHeight;
138     SkScalar fLeading;
139     bool fForceHeight;
140     bool fEnabled;
141     bool fHeightOverride;
142     // true: half leading.
143     // false: scale ascent/descent with fHeight.
144     bool fHalfLeading;
145 #ifdef ENABLE_TEXT_ENHANCE
146     WordBreakType fWordBreakType;
147     LineBreakStrategy fLineBreakStrategy { LineBreakStrategy::GREEDY };
148 #endif
149 };
150 
151 struct ParagraphStyle {
152     ParagraphStyle();
153 
154     bool operator==(const ParagraphStyle& rhs) const {
155 #ifdef ENABLE_TEXT_ENHANCE
156         return this->fHeight == rhs.fHeight && this->fEllipsis == rhs.fEllipsis &&
157                this->fEllipsisUtf16 == rhs.fEllipsisUtf16 &&
158                this->fTextDirection == rhs.fTextDirection && this->fTextAlign == rhs.fTextAlign &&
159                this->fDefaultTextStyle == rhs.fDefaultTextStyle &&
160                this->fEllipsisModal == rhs.fEllipsisModal &&
161                this->fTextOverflower == rhs.fTextOverflower &&
162                this->fReplaceTabCharacters == rhs.fReplaceTabCharacters &&
163                this->fTextTab == rhs.fTextTab && this->fParagraphSpacing == rhs.fParagraphSpacing &&
164                this->fIsEndAddParagraphSpacing == rhs.fIsEndAddParagraphSpacing &&
165                this->fIsTrailingSpaceOptimized == rhs.fIsTrailingSpaceOptimized &&
166                this->fEnableAutoSpace == rhs.fEnableAutoSpace &&
167                this->fVerticalAlignment == rhs.fVerticalAlignment &&
168                nearlyEqual(this->fTextSplitRatio, rhs.fTextSplitRatio);
169 #else
170         return this->fHeight == rhs.fHeight &&
171                this->fEllipsis == rhs.fEllipsis &&
172                this->fEllipsisUtf16 == rhs.fEllipsisUtf16 &&
173                this->fTextDirection == rhs.fTextDirection && this->fTextAlign == rhs.fTextAlign &&
174                this->fDefaultTextStyle == rhs.fDefaultTextStyle &&
175                this->fReplaceTabCharacters == rhs.fReplaceTabCharacters;
176 #endif
177     }
178 
getStrutStyleParagraphStyle179     const StrutStyle& getStrutStyle() const { return fStrutStyle; }
setStrutStyleParagraphStyle180     void setStrutStyle(StrutStyle strutStyle) { fStrutStyle = std::move(strutStyle); }
181 
getTextStyleParagraphStyle182     const TextStyle& getTextStyle() const { return fDefaultTextStyle; }
setTextStyleParagraphStyle183     void setTextStyle(const TextStyle& textStyle) { fDefaultTextStyle = textStyle; }
184 
getTextDirectionParagraphStyle185     TextDirection getTextDirection() const { return fTextDirection; }
setTextDirectionParagraphStyle186     void setTextDirection(TextDirection direction) { fTextDirection = direction; }
187 
getTextAlignParagraphStyle188     TextAlign getTextAlign() const { return fTextAlign; }
setTextAlignParagraphStyle189     void setTextAlign(TextAlign align) { fTextAlign = align; }
190 
getMaxLinesParagraphStyle191     size_t getMaxLines() const { return fLinesLimit; }
setMaxLinesParagraphStyle192     void setMaxLines(size_t maxLines) { fLinesLimit = maxLines; }
193 
getEllipsisParagraphStyle194     SkString getEllipsis() const { return fEllipsis; }
getEllipsisUtf16ParagraphStyle195     std::u16string getEllipsisUtf16() const { return fEllipsisUtf16; }
setEllipsisParagraphStyle196     void setEllipsis(const std::u16string& ellipsis) {  fEllipsisUtf16 = ellipsis; }
setEllipsisParagraphStyle197     void setEllipsis(const SkString& ellipsis) { fEllipsis = ellipsis; }
198 
getHeightParagraphStyle199     SkScalar getHeight() const { return fHeight; }
setHeightParagraphStyle200     void setHeight(SkScalar height) { fHeight = height; }
201 
getTextHeightBehaviorParagraphStyle202     TextHeightBehavior getTextHeightBehavior() const { return fTextHeightBehavior; }
setTextHeightBehaviorParagraphStyle203     void setTextHeightBehavior(TextHeightBehavior v) { fTextHeightBehavior = v; }
204 
unlimited_linesParagraphStyle205     bool unlimited_lines() const {
206         return fLinesLimit == std::numeric_limits<size_t>::max();
207     }
ellipsizedParagraphStyle208     bool ellipsized() const { return !fEllipsis.isEmpty() || !fEllipsisUtf16.empty(); }
209     TextAlign effective_align() const;
hintingIsOnParagraphStyle210     bool hintingIsOn() const { return fHintingIsOn; }
turnHintingOffParagraphStyle211     void turnHintingOff() { fHintingIsOn = false; }
212 
getReplaceTabCharactersParagraphStyle213     bool getReplaceTabCharacters() const { return fReplaceTabCharacters; }
setReplaceTabCharactersParagraphStyle214     void setReplaceTabCharacters(bool value) { fReplaceTabCharacters = value; }
215 
216 #ifdef ENABLE_TEXT_ENHANCE
setVerticalAlignmentParagraphStyle217     void setVerticalAlignment(TextVerticalAlign verticalAlignment) { fVerticalAlignment = verticalAlignment; }
getVerticalAlignmentParagraphStyle218     TextVerticalAlign getVerticalAlignment() const { return fVerticalAlignment; }
exportStrutStyleParagraphStyle219     StrutStyle& exportStrutStyle() { return fStrutStyle; }
exportTextStyleParagraphStyle220     TextStyle& exportTextStyle() { return fDefaultTextStyle; }
221 
getEllipsisModParagraphStyle222     skia::textlayout::EllipsisModal getEllipsisMod() const { return fEllipsisModal; }
setEllipsisModParagraphStyle223     void setEllipsisMod(skia::textlayout::EllipsisModal ellipsisModel) { fEllipsisModal = ellipsisModel; }
getTextSplitRatioParagraphStyle224     SkScalar getTextSplitRatio() const { return fTextSplitRatio; }
setTextSplitRatioParagraphStyle225     void setTextSplitRatio(SkScalar textSplitRatio) { fTextSplitRatio = textSplitRatio; }
226 
getTextOverflowerParagraphStyle227     bool getTextOverflower() const { return fTextOverflower; }
setTextOverflowerParagraphStyle228     void setTextOverflower(bool textOverflowerFlag) { fTextOverflower = textOverflowerFlag; }
getTextTabParagraphStyle229     const TextTabs& getTextTab() const { return fTextTab; }
setTextTabParagraphStyle230     void setTextTab(const TextTabs& textTab) { fTextTab = textTab; }
getParagraphSpacingParagraphStyle231     SkScalar getParagraphSpacing() const { return fParagraphSpacing; }
setParagraphSpacingParagraphStyle232     void setParagraphSpacing(SkScalar paragraphSpacing)
233     {
234         fParagraphSpacing = paragraphSpacing;
235     }
getIsEndAddParagraphSpacingParagraphStyle236     bool getIsEndAddParagraphSpacing() const { return fIsEndAddParagraphSpacing; }
setIsEndAddParagraphSpacingParagraphStyle237     void setIsEndAddParagraphSpacing(bool isEndAddParagraphSpacing)
238     {
239         fIsEndAddParagraphSpacing = isEndAddParagraphSpacing;
240     }
getTrailingSpaceOptimizedParagraphStyle241     bool getTrailingSpaceOptimized() const { return fIsTrailingSpaceOptimized; }
setTrailingSpaceOptimizedParagraphStyle242     void setTrailingSpaceOptimized(bool isTrailingSpaceOptimized)
243     {
244         fIsTrailingSpaceOptimized = isTrailingSpaceOptimized;
245     }
246 
getEnableAutoSpaceParagraphStyle247     bool getEnableAutoSpace() const { return fEnableAutoSpace; }
setEnableAutoSpaceParagraphStyle248     void setEnableAutoSpace(bool enableAutoSpace)
249     {
250         fEnableAutoSpace = enableAutoSpace;
251     }
252 #endif
getApplyRoundingHackParagraphStyle253     bool getApplyRoundingHack() const { return fApplyRoundingHack; }
setApplyRoundingHackParagraphStyle254     void setApplyRoundingHack(bool value) { fApplyRoundingHack = value; }
255 
256 private:
257     StrutStyle fStrutStyle;
258     TextStyle fDefaultTextStyle;
259     TextAlign fTextAlign;
260     TextDirection fTextDirection;
261     size_t fLinesLimit;
262     std::u16string fEllipsisUtf16;
263     SkString fEllipsis;
264     SkScalar fHeight;
265     TextHeightBehavior fTextHeightBehavior;
266     bool fHintingIsOn;
267     bool fReplaceTabCharacters;
268     bool fApplyRoundingHack = true;
269 #ifdef ENABLE_TEXT_ENHANCE
270     bool fTextOverflower;
271     skia::textlayout::EllipsisModal fEllipsisModal;
272     SkScalar fTextSplitRatio{0.5f};
273     TextTabs fTextTab;
274     SkScalar fParagraphSpacing{0.0f};
275     bool fIsEndAddParagraphSpacing{false};
276     bool fIsTrailingSpaceOptimized{false};
277     bool fEnableAutoSpace{false};
278     TextVerticalAlign fVerticalAlignment{TextVerticalAlign::BASELINE};
279 #endif
280 };
281 }  // namespace textlayout
282 }  // namespace skia
283 
284 #endif  // ParagraphStyle_DEFINED
285