1694b519ac647fe998fd396fe0784cc8e179aadc4Romain Guy/*
2694b519ac647fe998fd396fe0784cc8e179aadc4Romain Guy * Copyright (C) 2010 The Android Open Source Project
3694b519ac647fe998fd396fe0784cc8e179aadc4Romain Guy *
4694b519ac647fe998fd396fe0784cc8e179aadc4Romain Guy * Licensed under the Apache License, Version 2.0 (the "License");
5694b519ac647fe998fd396fe0784cc8e179aadc4Romain Guy * you may not use this file except in compliance with the License.
6694b519ac647fe998fd396fe0784cc8e179aadc4Romain Guy * You may obtain a copy of the License at
7694b519ac647fe998fd396fe0784cc8e179aadc4Romain Guy *
8694b519ac647fe998fd396fe0784cc8e179aadc4Romain Guy *      http://www.apache.org/licenses/LICENSE-2.0
9694b519ac647fe998fd396fe0784cc8e179aadc4Romain Guy *
10694b519ac647fe998fd396fe0784cc8e179aadc4Romain Guy * Unless required by applicable law or agreed to in writing, software
11694b519ac647fe998fd396fe0784cc8e179aadc4Romain Guy * distributed under the License is distributed on an "AS IS" BASIS,
12694b519ac647fe998fd396fe0784cc8e179aadc4Romain Guy * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13694b519ac647fe998fd396fe0784cc8e179aadc4Romain Guy * See the License for the specific language governing permissions and
14694b519ac647fe998fd396fe0784cc8e179aadc4Romain Guy * limitations under the License.
15694b519ac647fe998fd396fe0784cc8e179aadc4Romain Guy */
16694b519ac647fe998fd396fe0784cc8e179aadc4Romain Guy
175e00c7ce063116c11315639f0035aca8ad73e8ccChris Craik#pragma once
18694b519ac647fe998fd396fe0784cc8e179aadc4Romain Guy
1996a5c4c7bab6718524de7253da8309143ab48befChris Craik#include "font/CacheTexture.h"
2096a5c4c7bab6718524de7253da8309143ab48befChris Craik#include "font/CachedGlyphInfo.h"
2196a5c4c7bab6718524de7253da8309143ab48befChris Craik#include "font/Font.h"
221bcacfdcab0eaa0cee92bd7f5a1b5e271dd68e52John Reck#include "font/FontUtil.h"
23af102bee518191f1e6ad843f06dcd7a64611462dsergeyv#ifdef BUGREPORT_FONT_CACHE_USAGE
24af102bee518191f1e6ad843f06dcd7a64611462dsergeyv#include "font/FontCacheHistoryTracker.h"
25af102bee518191f1e6ad843f06dcd7a64611462dsergeyv#endif
2696a5c4c7bab6718524de7253da8309143ab48befChris Craik
27e3a9b24b5e3f9b2058486814a6d27729e51ad466Romain Guy#include <utils/LruCache.h>
28baf29e7cf433624687c9d6b3bac180d33add8e0fsergeyv#include <utils/String8.h>
291f5762e646bed2290934280464832782766ee68eMathias Agopian#include <utils/StrongPointer.h>
30694b519ac647fe998fd396fe0784cc8e179aadc4Romain Guy
31694b519ac647fe998fd396fe0784cc8e179aadc4Romain Guy#include <SkPaint.h>
32694b519ac647fe998fd396fe0784cc8e179aadc4Romain Guy
33694b519ac647fe998fd396fe0784cc8e179aadc4Romain Guy#include <GLES2/gl2.h>
34694b519ac647fe998fd396fe0784cc8e179aadc4Romain Guy
35272a685f17cc4828257e521a6f62b7b17870f75eJohn Reck#include <vector>
36272a685f17cc4828257e521a6f62b7b17870f75eJohn Reck
37250b1cfc831fd2a271c09cab547efcc5e3d5f828Tim Murray#include "RenderScript.h"
38f2d8ccc15d7272b3416f73605c1f31d1d346bd40Chris Craiknamespace RSC {
391bcacfdcab0eaa0cee92bd7f5a1b5e271dd68e52John Reckclass Element;
401bcacfdcab0eaa0cee92bd7f5a1b5e271dd68e52John Reckclass RS;
411bcacfdcab0eaa0cee92bd7f5a1b5e271dd68e52John Reckclass ScriptIntrinsicBlur;
421bcacfdcab0eaa0cee92bd7f5a1b5e271dd68e52John Reckclass sp;
43f2d8ccc15d7272b3416f73605c1f31d1d346bd40Chris Craik}
44f2d8ccc15d7272b3416f73605c1f31d1d346bd40Chris Craik
45694b519ac647fe998fd396fe0784cc8e179aadc4Romain Guynamespace android {
46694b519ac647fe998fd396fe0784cc8e179aadc4Romain Guynamespace uirenderer {
47694b519ac647fe998fd396fe0784cc8e179aadc4Romain Guy
48a1717271caac5e8ea3808c331d4141ac01a42134Chris Craikclass BakedOpState;
49a1717271caac5e8ea3808c331d4141ac01a42134Chris Craikclass BakedOpRenderer;
50e4db79de127cfe961195f52907af8451026eaa20Chris Craikstruct ClipBase;
511e546815bbb736c50679a8aefc25f48561026fc5Victoria Lease
52828407356dd5c34a3e441604aaf895cbec7c7e66Chris Craikclass TextDrawFunctor {
531e546815bbb736c50679a8aefc25f48561026fc5Victoria Leasepublic:
541bcacfdcab0eaa0cee92bd7f5a1b5e271dd68e52John Reck    TextDrawFunctor(BakedOpRenderer* renderer, const BakedOpState* bakedState, const ClipBase* clip,
551bcacfdcab0eaa0cee92bd7f5a1b5e271dd68e52John Reck                    float x, float y, bool pureTranslate, int alpha, SkBlendMode mode,
561bcacfdcab0eaa0cee92bd7f5a1b5e271dd68e52John Reck                    const SkPaint* paint)
571bcacfdcab0eaa0cee92bd7f5a1b5e271dd68e52John Reck            : renderer(renderer)
581bcacfdcab0eaa0cee92bd7f5a1b5e271dd68e52John Reck            , bakedState(bakedState)
591bcacfdcab0eaa0cee92bd7f5a1b5e271dd68e52John Reck            , clip(clip)
601bcacfdcab0eaa0cee92bd7f5a1b5e271dd68e52John Reck            , x(x)
611bcacfdcab0eaa0cee92bd7f5a1b5e271dd68e52John Reck            , y(y)
621bcacfdcab0eaa0cee92bd7f5a1b5e271dd68e52John Reck            , pureTranslate(pureTranslate)
631bcacfdcab0eaa0cee92bd7f5a1b5e271dd68e52John Reck            , alpha(alpha)
641bcacfdcab0eaa0cee92bd7f5a1b5e271dd68e52John Reck            , mode(mode)
651bcacfdcab0eaa0cee92bd7f5a1b5e271dd68e52John Reck            , paint(paint) {}
661e546815bbb736c50679a8aefc25f48561026fc5Victoria Lease
67e2bb380bc26749782c873e5488cfdf4e42b27346Chris Craik    void draw(CacheTexture& texture, bool linearFiltering);
681e546815bbb736c50679a8aefc25f48561026fc5Victoria Lease
69a1717271caac5e8ea3808c331d4141ac01a42134Chris Craik    BakedOpRenderer* renderer;
70a1717271caac5e8ea3808c331d4141ac01a42134Chris Craik    const BakedOpState* bakedState;
71e4db79de127cfe961195f52907af8451026eaa20Chris Craik    const ClipBase* clip;
721e546815bbb736c50679a8aefc25f48561026fc5Victoria Lease    float x;
731e546815bbb736c50679a8aefc25f48561026fc5Victoria Lease    float y;
741e546815bbb736c50679a8aefc25f48561026fc5Victoria Lease    bool pureTranslate;
751e546815bbb736c50679a8aefc25f48561026fc5Victoria Lease    int alpha;
76260ab726486317496bc12a57d599ea96dcde3284Mike Reed    SkBlendMode mode;
77d218a92c0afb8c0d98135b20b52ac87236e1c935Chris Craik    const SkPaint* paint;
781e546815bbb736c50679a8aefc25f48561026fc5Victoria Lease};
791e546815bbb736c50679a8aefc25f48561026fc5Victoria Lease
80694b519ac647fe998fd396fe0784cc8e179aadc4Romain Guyclass FontRenderer {
81694b519ac647fe998fd396fe0784cc8e179aadc4Romain Guypublic:
82a619ec70cf765d9166f0862e74653711b87307b3Chih-Hung Hsieh    explicit FontRenderer(const uint8_t* gammaTable);
83694b519ac647fe998fd396fe0784cc8e179aadc4Romain Guy    ~FontRenderer();
84694b519ac647fe998fd396fe0784cc8e179aadc4Romain Guy
85272a685f17cc4828257e521a6f62b7b17870f75eJohn Reck    void flushLargeCaches(std::vector<CacheTexture*>& cacheTextures);
869a8245629d69d81e0b62e52970feaf9c02580e75Chet Haase    void flushLargeCaches();
87694b519ac647fe998fd396fe0784cc8e179aadc4Romain Guy
8859744b79ec302000802cd56d30a1bf70f0183c80Chris Craik    void setFont(const SkPaint* paint, const SkMatrix& matrix);
89e816baea651476aca4407200d4a5e629b9ab8dfaChet Haase
901bcacfdcab0eaa0cee92bd7f5a1b5e271dd68e52John Reck    void precache(const SkPaint* paint, const glyph_t* glyphs, int numGlyphs,
911bcacfdcab0eaa0cee92bd7f5a1b5e271dd68e52John Reck                  const SkMatrix& matrix);
92cf51a4199835e9604aa4c8b3854306f8fbabbf33Romain Guy    void endPrecaching();
93e816baea651476aca4407200d4a5e629b9ab8dfaChet Haase
941bcacfdcab0eaa0cee92bd7f5a1b5e271dd68e52John Reck    bool renderPosText(const SkPaint* paint, const Rect* clip, const glyph_t* glyphs, int numGlyphs,
951bcacfdcab0eaa0cee92bd7f5a1b5e271dd68e52John Reck                       int x, int y, const float* positions, Rect* outBounds,
961bcacfdcab0eaa0cee92bd7f5a1b5e271dd68e52John Reck                       TextDrawFunctor* functor, bool forceFinish = true);
97527a3aace1dd72432c2e0472a570e030ad04bf16Chris Craik
98e8c3c813b0e3ac98304b17a751ce6e436e252bd9Chris Craik    bool renderTextOnPath(const SkPaint* paint, const Rect* clip, const glyph_t* glyphs,
991bcacfdcab0eaa0cee92bd7f5a1b5e271dd68e52John Reck                          int numGlyphs, const SkPath* path, float hOffset, float vOffset,
1001bcacfdcab0eaa0cee92bd7f5a1b5e271dd68e52John Reck                          Rect* outBounds, TextDrawFunctor* functor);
101694b519ac647fe998fd396fe0784cc8e179aadc4Romain Guy
102f18136cb3c881a9d16c1a4f0f341732c276936bfAlex Sakhartchouk    struct DropShadow {
103f18136cb3c881a9d16c1a4f0f341732c276936bfAlex Sakhartchouk        uint32_t width;
104f18136cb3c881a9d16c1a4f0f341732c276936bfAlex Sakhartchouk        uint32_t height;
105f18136cb3c881a9d16c1a4f0f341732c276936bfAlex Sakhartchouk        uint8_t* image;
106f18136cb3c881a9d16c1a4f0f341732c276936bfAlex Sakhartchouk        int32_t penX;
107f18136cb3c881a9d16c1a4f0f341732c276936bfAlex Sakhartchouk        int32_t penY;
108f18136cb3c881a9d16c1a4f0f341732c276936bfAlex Sakhartchouk    };
109f18136cb3c881a9d16c1a4f0f341732c276936bfAlex Sakhartchouk
110f18136cb3c881a9d16c1a4f0f341732c276936bfAlex Sakhartchouk    // After renderDropShadow returns, the called owns the memory in DropShadow.image
111f18136cb3c881a9d16c1a4f0f341732c276936bfAlex Sakhartchouk    // and is responsible for releasing it when it's done with it
1121bcacfdcab0eaa0cee92bd7f5a1b5e271dd68e52John Reck    DropShadow renderDropShadow(const SkPaint* paint, const glyph_t* glyphs, int numGlyphs,
1131bcacfdcab0eaa0cee92bd7f5a1b5e271dd68e52John Reck                                float radius, const float* positions);
114f18136cb3c881a9d16c1a4f0f341732c276936bfAlex Sakhartchouk
1151bcacfdcab0eaa0cee92bd7f5a1b5e271dd68e52John Reck    void setTextureFiltering(bool linearFiltering) { mLinearFiltering = linearFiltering; }
116c15008e72ec00ca20a271c3006dac649fd07533bRomain Guy
117baf29e7cf433624687c9d6b3bac180d33add8e0fsergeyv    uint32_t getSize() const;
118baf29e7cf433624687c9d6b3bac180d33add8e0fsergeyv    void dumpMemoryUsage(String8& log) const;
119c15008e72ec00ca20a271c3006dac649fd07533bRomain Guy
120af102bee518191f1e6ad843f06dcd7a64611462dsergeyv#ifdef BUGREPORT_FONT_CACHE_USAGE
121af102bee518191f1e6ad843f06dcd7a64611462dsergeyv    FontCacheHistoryTracker& historyTracker() { return mHistoryTracker; }
122af102bee518191f1e6ad843f06dcd7a64611462dsergeyv#endif
123c15008e72ec00ca20a271c3006dac649fd07533bRomain Guy
1249b1204baf4740b4d443e72157dea98571cf84e1fRomain Guyprivate:
125694b519ac647fe998fd396fe0784cc8e179aadc4Romain Guy    friend class Font;
126694b519ac647fe998fd396fe0784cc8e179aadc4Romain Guy
127b45c0c9774bd19a9dbe77d149abae4e124b08bf6Romain Guy    const uint8_t* mGammaTable;
128b45c0c9774bd19a9dbe77d149abae4e124b08bf6Romain Guy
1292a47c14e2a6f152496b43104bc785c488583fd59Chet Haase    void allocateTextureMemory(CacheTexture* cacheTexture);
1309a8245629d69d81e0b62e52970feaf9c02580e75Chet Haase    void deallocateTextureMemory(CacheTexture* cacheTexture);
1317de0cb12d0e5fd64811da0b5d1ae0c0d58b86f86Chet Haase    void initTextTexture();
1321e546815bbb736c50679a8aefc25f48561026fc5Victoria Lease    CacheTexture* createCacheTexture(int width, int height, GLenum format, bool allocate);
1331bcacfdcab0eaa0cee92bd7f5a1b5e271dd68e52John Reck    void cacheBitmap(const SkGlyph& glyph, CachedGlyphInfo* cachedGlyph, uint32_t* retOriginX,
1341bcacfdcab0eaa0cee92bd7f5a1b5e271dd68e52John Reck                     uint32_t* retOriginY, bool precaching);
1351bcacfdcab0eaa0cee92bd7f5a1b5e271dd68e52John Reck    CacheTexture* cacheBitmapInTexture(std::vector<CacheTexture*>& cacheTextures,
1361bcacfdcab0eaa0cee92bd7f5a1b5e271dd68e52John Reck                                       const SkGlyph& glyph, uint32_t* startX, uint32_t* startY);
137694b519ac647fe998fd396fe0784cc8e179aadc4Romain Guy
138694b519ac647fe998fd396fe0784cc8e179aadc4Romain Guy    void flushAllAndInvalidate();
139694b519ac647fe998fd396fe0784cc8e179aadc4Romain Guy
140694b519ac647fe998fd396fe0784cc8e179aadc4Romain Guy    void checkInit();
141828407356dd5c34a3e441604aaf895cbec7c7e66Chris Craik    void initRender(const Rect* clip, Rect* bounds, TextDrawFunctor* functor);
142671d6cf460531825a321edb200523d0faa7792c9Romain Guy    void finishRender();
143694b519ac647fe998fd396fe0784cc8e179aadc4Romain Guy
144272a685f17cc4828257e521a6f62b7b17870f75eJohn Reck    void issueDrawCommand(std::vector<CacheTexture*>& cacheTextures);
145694b519ac647fe998fd396fe0784cc8e179aadc4Romain Guy    void issueDrawCommand();
1461bcacfdcab0eaa0cee92bd7f5a1b5e271dd68e52John Reck    void appendMeshQuadNoClip(float x1, float y1, float u1, float v1, float x2, float y2, float u2,
1471bcacfdcab0eaa0cee92bd7f5a1b5e271dd68e52John Reck                              float v2, float x3, float y3, float u3, float v3, float x4, float y4,
1481bcacfdcab0eaa0cee92bd7f5a1b5e271dd68e52John Reck                              float u4, float v4, CacheTexture* texture);
1491bcacfdcab0eaa0cee92bd7f5a1b5e271dd68e52John Reck    void appendMeshQuad(float x1, float y1, float u1, float v1, float x2, float y2, float u2,
1501bcacfdcab0eaa0cee92bd7f5a1b5e271dd68e52John Reck                        float v2, float x3, float y3, float u3, float v3, float x4, float y4,
1511bcacfdcab0eaa0cee92bd7f5a1b5e271dd68e52John Reck                        float u4, float v4, CacheTexture* texture);
1521bcacfdcab0eaa0cee92bd7f5a1b5e271dd68e52John Reck    void appendRotatedMeshQuad(float x1, float y1, float u1, float v1, float x2, float y2, float u2,
1531bcacfdcab0eaa0cee92bd7f5a1b5e271dd68e52John Reck                               float v2, float x3, float y3, float u3, float v3, float x4, float y4,
1541bcacfdcab0eaa0cee92bd7f5a1b5e271dd68e52John Reck                               float u4, float v4, CacheTexture* texture);
155694b519ac647fe998fd396fe0784cc8e179aadc4Romain Guy
1569b1204baf4740b4d443e72157dea98571cf84e1fRomain Guy    void checkTextureUpdate();
1579b1204baf4740b4d443e72157dea98571cf84e1fRomain Guy
1581bcacfdcab0eaa0cee92bd7f5a1b5e271dd68e52John Reck    void setTextureDirty() { mUploadTexture = true; }
1599b1204baf4740b4d443e72157dea98571cf84e1fRomain Guy
160baf29e7cf433624687c9d6b3bac180d33add8e0fsergeyv    const std::vector<CacheTexture*>& cacheTexturesForFormat(GLenum format) const;
161baf29e7cf433624687c9d6b3bac180d33add8e0fsergeyv    uint32_t getCacheSize(GLenum format) const;
162baf29e7cf433624687c9d6b3bac180d33add8e0fsergeyv    uint32_t getFreeCacheSize(GLenum format) const;
163baf29e7cf433624687c9d6b3bac180d33add8e0fsergeyv
1647de0cb12d0e5fd64811da0b5d1ae0c0d58b86f86Chet Haase    uint32_t mSmallCacheWidth;
1657de0cb12d0e5fd64811da0b5d1ae0c0d58b86f86Chet Haase    uint32_t mSmallCacheHeight;
166eb32a499194119b3783b86c925172df02e5d2685Chet Haase    uint32_t mLargeCacheWidth;
167eb32a499194119b3783b86c925172df02e5d2685Chet Haase    uint32_t mLargeCacheHeight;
168694b519ac647fe998fd396fe0784cc8e179aadc4Romain Guy
169272a685f17cc4828257e521a6f62b7b17870f75eJohn Reck    std::vector<CacheTexture*> mACacheTextures;
170272a685f17cc4828257e521a6f62b7b17870f75eJohn Reck    std::vector<CacheTexture*> mRGBACacheTextures;
171694b519ac647fe998fd396fe0784cc8e179aadc4Romain Guy
17209147fbdc8206a0cac78bfe9083e7e15b3c5689cRomain Guy    Font* mCurrentFont;
173e3a9b24b5e3f9b2058486814a6d27729e51ad466Romain Guy    LruCache<Font::FontDescription, Font*> mActiveFonts;
174694b519ac647fe998fd396fe0784cc8e179aadc4Romain Guy
1757de0cb12d0e5fd64811da0b5d1ae0c0d58b86f86Chet Haase    CacheTexture* mCurrentCacheTexture;
1767de0cb12d0e5fd64811da0b5d1ae0c0d58b86f86Chet Haase
177694b519ac647fe998fd396fe0784cc8e179aadc4Romain Guy    bool mUploadTexture;
178694b519ac647fe998fd396fe0784cc8e179aadc4Romain Guy
179828407356dd5c34a3e441604aaf895cbec7c7e66Chris Craik    TextDrawFunctor* mFunctor;
18009147fbdc8206a0cac78bfe9083e7e15b3c5689cRomain Guy    const Rect* mClip;
1815b3b35296e8b2c8d3f07d32bb645d5414db41a1dRomain Guy    Rect* mBounds;
1825b3b35296e8b2c8d3f07d32bb645d5414db41a1dRomain Guy    bool mDrawn;
18309147fbdc8206a0cac78bfe9083e7e15b3c5689cRomain Guy
184694b519ac647fe998fd396fe0784cc8e179aadc4Romain Guy    bool mInitialized;
18589a524ac2d4a36739e51b01b336c0bade77e2ee0Alex Sakhartchouk
186e8cb9c14309b0f01c0159efdf9a7198f44a62642Romain Guy    bool mLinearFiltering;
187e8cb9c14309b0f01c0159efdf9a7198f44a62642Romain Guy
188af102bee518191f1e6ad843f06dcd7a64611462dsergeyv#ifdef BUGREPORT_FONT_CACHE_USAGE
189af102bee518191f1e6ad843f06dcd7a64611462dsergeyv    FontCacheHistoryTracker mHistoryTracker;
190af102bee518191f1e6ad843f06dcd7a64611462dsergeyv#endif
191af102bee518191f1e6ad843f06dcd7a64611462dsergeyv
192f2d8ccc15d7272b3416f73605c1f31d1d346bd40Chris Craik    // RS constructs
193250b1cfc831fd2a271c09cab547efcc5e3d5f828Tim Murray    RSC::sp<RSC::RS> mRs;
194250b1cfc831fd2a271c09cab547efcc5e3d5f828Tim Murray    RSC::sp<const RSC::Element> mRsElement;
195250b1cfc831fd2a271c09cab547efcc5e3d5f828Tim Murray    RSC::sp<RSC::ScriptIntrinsicBlur> mRsScript;
196f2d8ccc15d7272b3416f73605c1f31d1d346bd40Chris Craik
1979b1204baf4740b4d443e72157dea98571cf84e1fRomain Guy    static void computeGaussianWeights(float* weights, int32_t radius);
1981bcacfdcab0eaa0cee92bd7f5a1b5e271dd68e52John Reck    static void horizontalBlur(float* weights, int32_t radius, const uint8_t* source, uint8_t* dest,
1991bcacfdcab0eaa0cee92bd7f5a1b5e271dd68e52John Reck                               int32_t width, int32_t height);
2001bcacfdcab0eaa0cee92bd7f5a1b5e271dd68e52John Reck    static void verticalBlur(float* weights, int32_t radius, const uint8_t* source, uint8_t* dest,
2011bcacfdcab0eaa0cee92bd7f5a1b5e271dd68e52John Reck                             int32_t width, int32_t height);
202f2d8ccc15d7272b3416f73605c1f31d1d346bd40Chris Craik
203f2d8ccc15d7272b3416f73605c1f31d1d346bd40Chris Craik    // the input image handle may have its pointer replaced (to avoid copies)
204e392c81f6b8f9ace0c0a48c9d4df117fda31fd13Derek Sollenberger    void blurImage(uint8_t** image, int32_t width, int32_t height, float radius);
205694b519ac647fe998fd396fe0784cc8e179aadc4Romain Guy};
206694b519ac647fe998fd396fe0784cc8e179aadc4Romain Guy
2071bcacfdcab0eaa0cee92bd7f5a1b5e271dd68e52John Reck};  // namespace uirenderer
2081bcacfdcab0eaa0cee92bd7f5a1b5e271dd68e52John Reck};  // namespace android
209