1/*
2 * Copyright (C) 2012 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_HWUI_FONT_H
18#define ANDROID_HWUI_FONT_H
19
20#include <vector>
21
22#include <utils/KeyedVector.h>
23
24#include <SkScalar.h>
25#include <SkDeviceProperties.h>
26#include <SkGlyphCache.h>
27#include <SkScalerContext.h>
28#include <SkPaint.h>
29#include <SkPathMeasure.h>
30
31#include "CachedGlyphInfo.h"
32#include "../Rect.h"
33#include "../Matrix.h"
34
35namespace android {
36namespace uirenderer {
37
38///////////////////////////////////////////////////////////////////////////////
39// Font
40///////////////////////////////////////////////////////////////////////////////
41
42class FontRenderer;
43
44/**
45 * Represents a font, defined by a Skia font id and a font size. A font is used
46 * to generate glyphs and cache them in the FontState.
47 */
48class Font {
49public:
50    enum Style {
51        kFakeBold = 1
52    };
53
54    struct FontDescription {
55        FontDescription(const SkPaint* paint, const SkMatrix& matrix);
56
57        static int compare(const FontDescription& lhs, const FontDescription& rhs);
58
59        hash_t hash() const;
60
61        bool operator==(const FontDescription& other) const {
62            return compare(*this, other) == 0;
63        }
64
65        bool operator!=(const FontDescription& other) const {
66            return compare(*this, other) != 0;
67        }
68
69        SkFontID mFontId;
70        float mFontSize;
71        int mFlags;
72        float mItalicStyle;
73        float mScaleX;
74        uint8_t mStyle;
75        float mStrokeWidth;
76        bool mAntiAliasing;
77        uint8_t mHinting;
78        SkMatrix mLookupTransform;
79        SkMatrix mInverseLookupTransform;
80    };
81
82    ~Font();
83
84    void render(const SkPaint* paint, const char* text, uint32_t start, uint32_t len,
85            int numGlyphs, int x, int y, const float* positions);
86
87    void render(const SkPaint* paint, const char* text, uint32_t start, uint32_t len,
88            int numGlyphs, const SkPath* path, float hOffset, float vOffset);
89
90    const Font::FontDescription& getDescription() const {
91        return mDescription;
92    }
93
94    /**
95     * Creates a new font associated with the specified font state.
96     */
97    static Font* create(FontRenderer* state, const SkPaint* paint, const SkMatrix& matrix);
98
99private:
100    friend class FontRenderer;
101
102    Font(FontRenderer* state, const Font::FontDescription& desc);
103
104    typedef void (Font::*RenderGlyph)(CachedGlyphInfo*, int, int, uint8_t*,
105            uint32_t, uint32_t, Rect*, const float*);
106
107    enum RenderMode {
108        FRAMEBUFFER,
109        BITMAP,
110        MEASURE,
111    };
112
113    void precache(const SkPaint* paint, const char* text, int numGlyphs);
114
115    void render(const SkPaint* paint, const char *text, uint32_t start, uint32_t len,
116            int numGlyphs, int x, int y, RenderMode mode, uint8_t *bitmap,
117            uint32_t bitmapW, uint32_t bitmapH, Rect *bounds, const float* positions);
118
119    void measure(const SkPaint* paint, const char* text, uint32_t start, uint32_t len,
120            int numGlyphs, Rect *bounds, const float* positions);
121
122    void invalidateTextureCache(CacheTexture* cacheTexture = NULL);
123
124    CachedGlyphInfo* cacheGlyph(const SkPaint* paint, glyph_t glyph, bool precaching);
125    void updateGlyphCache(const SkPaint* paint, const SkGlyph& skiaGlyph,
126            SkGlyphCache* skiaGlyphCache, CachedGlyphInfo* glyph, bool precaching);
127
128    void measureCachedGlyph(CachedGlyphInfo* glyph, int x, int y,
129            uint8_t *bitmap, uint32_t bitmapW, uint32_t bitmapH,
130            Rect* bounds, const float* pos);
131    void drawCachedGlyph(CachedGlyphInfo* glyph, int x, int y,
132            uint8_t *bitmap, uint32_t bitmapW, uint32_t bitmapH,
133            Rect* bounds, const float* pos);
134    void drawCachedGlyphTransformed(CachedGlyphInfo* glyph, int x, int y,
135            uint8_t *bitmap, uint32_t bitmapW, uint32_t bitmapH,
136            Rect* bounds, const float* pos);
137    void drawCachedGlyphBitmap(CachedGlyphInfo* glyph, int x, int y,
138            uint8_t *bitmap, uint32_t bitmapW, uint32_t bitmapH,
139            Rect* bounds, const float* pos);
140    void drawCachedGlyph(CachedGlyphInfo* glyph, float x, float hOffset, float vOffset,
141            SkPathMeasure& measure, SkPoint* position, SkVector* tangent);
142
143    CachedGlyphInfo* getCachedGlyph(const SkPaint* paint, glyph_t textUnit,
144            bool precaching = false);
145
146    FontRenderer* mState;
147    FontDescription mDescription;
148
149    // Cache of glyphs
150    DefaultKeyedVector<glyph_t, CachedGlyphInfo*> mCachedGlyphs;
151
152    bool mIdentityTransform;
153    SkDeviceProperties mDeviceProperties;
154};
155
156inline int strictly_order_type(const Font::FontDescription& lhs,
157        const Font::FontDescription& rhs) {
158    return Font::FontDescription::compare(lhs, rhs) < 0;
159}
160
161inline int compare_type(const Font::FontDescription& lhs, const Font::FontDescription& rhs) {
162    return Font::FontDescription::compare(lhs, rhs);
163}
164
165inline hash_t hash_type(const Font::FontDescription& entry) {
166    return entry.hash();
167}
168
169}; // namespace uirenderer
170}; // namespace android
171
172#endif // ANDROID_HWUI_FONT_H
173