• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (C) 2013 The Android Open Source Project
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *      http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 
17 #ifndef ANDROID_GRAPHICS_PAINT_H_
18 #define ANDROID_GRAPHICS_PAINT_H_
19 
20 #include "Typeface.h"
21 
22 #include <cutils/compiler.h>
23 
24 #include <SkFont.h>
25 #include <SkPaint.h>
26 #include <SkSamplingOptions.h>
27 #include <string>
28 
29 #include <minikin/FontFamily.h>
30 #include <minikin/FamilyVariant.h>
31 #include <minikin/Hyphenator.h>
32 
33 namespace android {
34 
35 class BlurDrawLooper;
36 
37 class Paint : public SkPaint {
38 public:
39     // Default values for underlined and strikethrough text,
40     // as defined by Skia in SkTextFormatParams.h.
41     constexpr static float kStdStrikeThru_Offset = (-6.0f / 21.0f);
42     constexpr static float kStdUnderline_Offset = (1.0f / 9.0f);
43     constexpr static float kStdUnderline_Thickness = (1.0f / 18.0f);
44 
45     constexpr static float kStdUnderline_Top =
46             kStdUnderline_Offset - 0.5f * kStdUnderline_Thickness;
47 
48     constexpr static float kStdStrikeThru_Thickness = kStdUnderline_Thickness;
49     constexpr static float kStdStrikeThru_Top =
50             kStdStrikeThru_Offset - 0.5f * kStdStrikeThru_Thickness;
51 
52     Paint();
53     Paint(const Paint& paint);
54     ~Paint();
55 
56     Paint& operator=(const Paint& other);
57 
58     friend bool operator==(const Paint& a, const Paint& b);
59     friend bool operator!=(const Paint& a, const Paint& b) { return !(a == b); }
60 
getSkFont()61     SkFont& getSkFont() { return mFont; }
getSkFont()62     const SkFont& getSkFont() const { return mFont; }
63 
getLooper()64     BlurDrawLooper* getLooper() const { return mLooper.get(); }
65     void setLooper(sk_sp<BlurDrawLooper> looper);
66 
67     // These shadow the methods on SkPaint, but we need to so we can keep related
68     // attributes in-sync.
69 
70     void reset();
71     void setAntiAlias(bool);
72 
nothingToDraw()73     bool nothingToDraw() const { return !mLooper && SkPaint::nothingToDraw(); }
74 
75     // End method shadowing
76 
setLetterSpacing(float letterSpacing)77     void setLetterSpacing(float letterSpacing) { mLetterSpacing = letterSpacing; }
78 
getLetterSpacing()79     float getLetterSpacing() const { return mLetterSpacing; }
80 
setWordSpacing(float wordSpacing)81     void setWordSpacing(float wordSpacing) { mWordSpacing = wordSpacing; }
82 
getWordSpacing()83     float getWordSpacing() const { return mWordSpacing; }
84 
setFontFeatureSettings(const std::string & fontFeatureSettings)85     void setFontFeatureSettings(const std::string& fontFeatureSettings) {
86         mFontFeatureSettings = fontFeatureSettings;
87     }
88 
getFontFeatureSettings()89     std::string getFontFeatureSettings() const { return mFontFeatureSettings; }
90 
setMinikinLocaleListId(uint32_t minikinLocaleListId)91     void setMinikinLocaleListId(uint32_t minikinLocaleListId) {
92         mMinikinLocaleListId = minikinLocaleListId;
93     }
94 
getMinikinLocaleListId()95     uint32_t getMinikinLocaleListId() const { return mMinikinLocaleListId; }
96 
setFamilyVariant(minikin::FamilyVariant variant)97     void setFamilyVariant(minikin::FamilyVariant variant) { mFamilyVariant = variant; }
98 
getFamilyVariant()99     minikin::FamilyVariant getFamilyVariant() const { return mFamilyVariant; }
100 
setStartHyphenEdit(uint32_t startHyphen)101     void setStartHyphenEdit(uint32_t startHyphen) {
102         mHyphenEdit = minikin::packHyphenEdit(
103             static_cast<minikin::StartHyphenEdit>(startHyphen),
104             minikin::endHyphenEdit(mHyphenEdit));
105     }
106 
setEndHyphenEdit(uint32_t endHyphen)107     void setEndHyphenEdit(uint32_t endHyphen) {
108         mHyphenEdit = minikin::packHyphenEdit(
109             minikin::startHyphenEdit(mHyphenEdit),
110             static_cast<minikin::EndHyphenEdit>(endHyphen));
111     }
112 
getStartHyphenEdit()113     minikin::StartHyphenEdit getStartHyphenEdit() const {
114         return minikin::startHyphenEdit(mHyphenEdit);
115     }
116 
getEndHyphenEdit()117     minikin::EndHyphenEdit getEndHyphenEdit() const {
118         return minikin::endHyphenEdit(mHyphenEdit);
119     }
120 
setAndroidTypeface(Typeface * typeface)121     void setAndroidTypeface(Typeface* typeface) { mTypeface = typeface; }
122 
getAndroidTypeface()123     const Typeface* getAndroidTypeface() const { return mTypeface; }
124 
125     enum Align {
126         kLeft_Align,
127         kCenter_Align,
128         kRight_Align,
129     };
getTextAlign()130     Align getTextAlign() const { return mAlign; }
setTextAlign(Align align)131     void setTextAlign(Align align) { mAlign = align; }
132 
isStrikeThru()133     bool isStrikeThru() const { return mStrikeThru; }
setStrikeThru(bool st)134     void setStrikeThru(bool st) { mStrikeThru = st; }
135 
isUnderline()136     bool isUnderline() const { return mUnderline; }
setUnderline(bool u)137     void setUnderline(bool u) { mUnderline = u; }
138 
isDevKern()139     bool isDevKern() const { return mDevKern; }
setDevKern(bool d)140     void setDevKern(bool d) { mDevKern = d; }
141 
142     // Deprecated -- bitmapshaders will be taking this flag explicitly
isFilterBitmap()143     bool isFilterBitmap() const { return mFilterBitmap; }
setFilterBitmap(bool filter)144     void setFilterBitmap(bool filter) { mFilterBitmap = filter; }
145 
filterMode()146     SkFilterMode filterMode() const {
147         return mFilterBitmap ? SkFilterMode::kLinear : SkFilterMode::kNearest;
148     }
sampling()149     SkSamplingOptions sampling() const {
150         return SkSamplingOptions(this->filterMode());
151     }
152 
153     // The Java flags (Paint.java) no longer fit into the native apis directly.
154     // These methods handle converting to and from them and the native representations
155     // in android::Paint.
156 
157     uint32_t getJavaFlags() const;
158     void setJavaFlags(uint32_t);
159 
160     // Helpers that return or apply legacy java flags to SkPaint, ignoring all flags
161     // that are meant for SkFont or Paint (e.g. underline, strikethru)
162     // The only respected flags are : [ antialias, dither, filterBitmap ]
163     static uint32_t GetSkPaintJavaFlags(const SkPaint&);
164     static void SetSkPaintJavaFlags(SkPaint*, uint32_t flags);
165 
166 private:
167     SkFont mFont;
168     sk_sp<BlurDrawLooper> mLooper;
169 
170     float mLetterSpacing = 0;
171     float mWordSpacing = 0;
172     std::string mFontFeatureSettings;
173     uint32_t mMinikinLocaleListId;
174     minikin::FamilyVariant mFamilyVariant;
175     uint32_t mHyphenEdit = 0;
176     // The native Typeface object has the same lifetime of the Java Typeface
177     // object. The Java Paint object holds a strong reference to the Java Typeface
178     // object. Thus, following pointer can never be a dangling pointer. Note that
179     // nullptr is valid: it means the default typeface.
180     const Typeface* mTypeface = nullptr;
181     Align mAlign = kLeft_Align;
182     bool mFilterBitmap = false;
183     bool mStrikeThru = false;
184     bool mUnderline = false;
185     bool mDevKern = false;
186 };
187 
188 }  // namespace android
189 
190 #endif  // ANDROID_GRAPHICS_PAINT_H_
191