1ce0537b80087a6225273040a987414b1dd081aa0Romain Guy/*
2ce0537b80087a6225273040a987414b1dd081aa0Romain Guy * Copyright (C) 2010 The Android Open Source Project
3ce0537b80087a6225273040a987414b1dd081aa0Romain Guy *
4ce0537b80087a6225273040a987414b1dd081aa0Romain Guy * Licensed under the Apache License, Version 2.0 (the "License");
5ce0537b80087a6225273040a987414b1dd081aa0Romain Guy * you may not use this file except in compliance with the License.
6ce0537b80087a6225273040a987414b1dd081aa0Romain Guy * You may obtain a copy of the License at
7ce0537b80087a6225273040a987414b1dd081aa0Romain Guy *
8ce0537b80087a6225273040a987414b1dd081aa0Romain Guy *      http://www.apache.org/licenses/LICENSE-2.0
9ce0537b80087a6225273040a987414b1dd081aa0Romain Guy *
10ce0537b80087a6225273040a987414b1dd081aa0Romain Guy * Unless required by applicable law or agreed to in writing, software
11ce0537b80087a6225273040a987414b1dd081aa0Romain Guy * distributed under the License is distributed on an "AS IS" BASIS,
12ce0537b80087a6225273040a987414b1dd081aa0Romain Guy * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13ce0537b80087a6225273040a987414b1dd081aa0Romain Guy * See the License for the specific language governing permissions and
14ce0537b80087a6225273040a987414b1dd081aa0Romain Guy * limitations under the License.
15ce0537b80087a6225273040a987414b1dd081aa0Romain Guy */
16ce0537b80087a6225273040a987414b1dd081aa0Romain Guy
175b3b35296e8b2c8d3f07d32bb645d5414db41a1dRomain Guy#ifndef ANDROID_HWUI_TEXTURE_CACHE_H
185b3b35296e8b2c8d3f07d32bb645d5414db41a1dRomain Guy#define ANDROID_HWUI_TEXTURE_CACHE_H
19ce0537b80087a6225273040a987414b1dd081aa0Romain Guy
20ce0537b80087a6225273040a987414b1dd081aa0Romain Guy#include <SkBitmap.h>
21ce0537b80087a6225273040a987414b1dd081aa0Romain Guy
22059e12ccd20f5c249724a8362d6bac325334ea76Romain Guy#include <utils/LruCache.h>
23029f64303b8fe506ef34c12777da86b830d3bf7aDerek Sollenberger#include <utils/Mutex.h>
24fe48f65922d4a3cc4aefe058cee5acec51504a20Romain Guy#include <utils/Vector.h>
25fe48f65922d4a3cc4aefe058cee5acec51504a20Romain Guy
26c15008e72ec00ca20a271c3006dac649fd07533bRomain Guy#include "Debug.h"
27ce0537b80087a6225273040a987414b1dd081aa0Romain Guy#include "Texture.h"
28ce0537b80087a6225273040a987414b1dd081aa0Romain Guy
29ce0537b80087a6225273040a987414b1dd081aa0Romain Guynamespace android {
30ce0537b80087a6225273040a987414b1dd081aa0Romain Guynamespace uirenderer {
31ce0537b80087a6225273040a987414b1dd081aa0Romain Guy
32d98aa2de9ab18e09c2be1997f41212740f51f6e6Chet Haase///////////////////////////////////////////////////////////////////////////////
33d98aa2de9ab18e09c2be1997f41212740f51f6e6Chet Haase// Defines
34d98aa2de9ab18e09c2be1997f41212740f51f6e6Chet Haase///////////////////////////////////////////////////////////////////////////////
35d98aa2de9ab18e09c2be1997f41212740f51f6e6Chet Haase
36d98aa2de9ab18e09c2be1997f41212740f51f6e6Chet Haase// Debug
37d98aa2de9ab18e09c2be1997f41212740f51f6e6Chet Haase#if DEBUG_TEXTURES
385baa3a62a97544669fba6d65a11c07f252e654ddSteve Block    #define TEXTURE_LOGD(...) ALOGD(__VA_ARGS__)
39d98aa2de9ab18e09c2be1997f41212740f51f6e6Chet Haase#else
40d98aa2de9ab18e09c2be1997f41212740f51f6e6Chet Haase    #define TEXTURE_LOGD(...)
41d98aa2de9ab18e09c2be1997f41212740f51f6e6Chet Haase#endif
42d98aa2de9ab18e09c2be1997f41212740f51f6e6Chet Haase
439e10841c27d973b930e1b49a099c69d866659505Romain Guy///////////////////////////////////////////////////////////////////////////////
449e10841c27d973b930e1b49a099c69d866659505Romain Guy// Classes
459e10841c27d973b930e1b49a099c69d866659505Romain Guy///////////////////////////////////////////////////////////////////////////////
469e10841c27d973b930e1b49a099c69d866659505Romain Guy
47121e2242565d5f09ad83a2d33ecd2225838802c5Romain Guy/**
48121e2242565d5f09ad83a2d33ecd2225838802c5Romain Guy * A simple LRU texture cache. The cache has a maximum size expressed in bytes.
49121e2242565d5f09ad83a2d33ecd2225838802c5Romain Guy * Any texture added to the cache causing the cache to grow beyond the maximum
50121e2242565d5f09ad83a2d33ecd2225838802c5Romain Guy * allowed size will also cause the oldest texture to be kicked out.
51121e2242565d5f09ad83a2d33ecd2225838802c5Romain Guy */
52d1ad5e62fda248c6d185cde3cb6d9f01a223066cLeon Scroggins IIIclass TextureCache: public OnEntryRemoved<const SkPixelRef*, Texture*> {
53ce0537b80087a6225273040a987414b1dd081aa0Romain Guypublic:
54fb8b763f762ae21923c58d64caa729b012f40e05Romain Guy    TextureCache();
557d139ba2c331f11e9b485753cc727a0ff202f2a4Romain Guy    TextureCache(uint32_t maxByteSize);
56ce0537b80087a6225273040a987414b1dd081aa0Romain Guy    ~TextureCache();
57ce0537b80087a6225273040a987414b1dd081aa0Romain Guy
58121e2242565d5f09ad83a2d33ecd2225838802c5Romain Guy    /**
59121e2242565d5f09ad83a2d33ecd2225838802c5Romain Guy     * Used as a callback when an entry is removed from the cache.
60121e2242565d5f09ad83a2d33ecd2225838802c5Romain Guy     * Do not invoke directly.
61121e2242565d5f09ad83a2d33ecd2225838802c5Romain Guy     */
62d1ad5e62fda248c6d185cde3cb6d9f01a223066cLeon Scroggins III    void operator()(const SkPixelRef*& pixelRef, Texture*& texture);
63ce0537b80087a6225273040a987414b1dd081aa0Romain Guy
64121e2242565d5f09ad83a2d33ecd2225838802c5Romain Guy    /**
65860d155f866cc15a725e7ce03763280987f24901John Reck     * Resets all Textures to not be marked as in use
66860d155f866cc15a725e7ce03763280987f24901John Reck     */
67860d155f866cc15a725e7ce03763280987f24901John Reck    void resetMarkInUse();
68860d155f866cc15a725e7ce03763280987f24901John Reck
69860d155f866cc15a725e7ce03763280987f24901John Reck    /**
70860d155f866cc15a725e7ce03763280987f24901John Reck     * Attempts to precache the SkBitmap. Returns true if a Texture was successfully
71860d155f866cc15a725e7ce03763280987f24901John Reck     * acquired for the bitmap, false otherwise. If a Texture was acquired it is
72860d155f866cc15a725e7ce03763280987f24901John Reck     * marked as in use.
73860d155f866cc15a725e7ce03763280987f24901John Reck     */
74860d155f866cc15a725e7ce03763280987f24901John Reck    bool prefetchAndMarkInUse(const SkBitmap* bitmap);
75860d155f866cc15a725e7ce03763280987f24901John Reck
76860d155f866cc15a725e7ce03763280987f24901John Reck    /**
77121e2242565d5f09ad83a2d33ecd2225838802c5Romain Guy     * Returns the texture associated with the specified bitmap. If the texture
78121e2242565d5f09ad83a2d33ecd2225838802c5Romain Guy     * cannot be found in the cache, a new texture is generated.
79121e2242565d5f09ad83a2d33ecd2225838802c5Romain Guy     */
80d218a92c0afb8c0d98135b20b52ac87236e1c935Chris Craik    Texture* get(const SkBitmap* bitmap);
81121e2242565d5f09ad83a2d33ecd2225838802c5Romain Guy    /**
82e651cc6239616a202f6e96ebc2ed93b4b8b3627cRomain Guy     * Returns the texture associated with the specified bitmap. The generated
83e651cc6239616a202f6e96ebc2ed93b4b8b3627cRomain Guy     * texture is not kept in the cache. The caller must destroy the texture.
84e651cc6239616a202f6e96ebc2ed93b4b8b3627cRomain Guy     */
85d218a92c0afb8c0d98135b20b52ac87236e1c935Chris Craik    Texture* getTransient(const SkBitmap* bitmap);
86e651cc6239616a202f6e96ebc2ed93b4b8b3627cRomain Guy    /**
87fe48f65922d4a3cc4aefe058cee5acec51504a20Romain Guy     * Removes the texture associated with the specified bitmap.
88fe48f65922d4a3cc4aefe058cee5acec51504a20Romain Guy     * Upon remove the texture is freed.
89121e2242565d5f09ad83a2d33ecd2225838802c5Romain Guy     */
90d218a92c0afb8c0d98135b20b52ac87236e1c935Chris Craik    void remove(const SkBitmap* bitmap);
91121e2242565d5f09ad83a2d33ecd2225838802c5Romain Guy    /**
92fe48f65922d4a3cc4aefe058cee5acec51504a20Romain Guy     * Removes the texture associated with the specified bitmap. This is meant
93fe48f65922d4a3cc4aefe058cee5acec51504a20Romain Guy     * to be called from threads that are not the EGL context thread.
94fe48f65922d4a3cc4aefe058cee5acec51504a20Romain Guy     */
95d218a92c0afb8c0d98135b20b52ac87236e1c935Chris Craik    void removeDeferred(const SkBitmap* bitmap);
96fe48f65922d4a3cc4aefe058cee5acec51504a20Romain Guy    /**
97fe48f65922d4a3cc4aefe058cee5acec51504a20Romain Guy     * Process deferred removals.
98fe48f65922d4a3cc4aefe058cee5acec51504a20Romain Guy     */
99fe48f65922d4a3cc4aefe058cee5acec51504a20Romain Guy    void clearGarbage();
100fe48f65922d4a3cc4aefe058cee5acec51504a20Romain Guy
101fe48f65922d4a3cc4aefe058cee5acec51504a20Romain Guy    /**
102121e2242565d5f09ad83a2d33ecd2225838802c5Romain Guy     * Clears the cache. This causes all textures to be deleted.
103121e2242565d5f09ad83a2d33ecd2225838802c5Romain Guy     */
104ce0537b80087a6225273040a987414b1dd081aa0Romain Guy    void clear();
105ce0537b80087a6225273040a987414b1dd081aa0Romain Guy
106121e2242565d5f09ad83a2d33ecd2225838802c5Romain Guy    /**
107121e2242565d5f09ad83a2d33ecd2225838802c5Romain Guy     * Sets the maximum size of the cache in bytes.
108121e2242565d5f09ad83a2d33ecd2225838802c5Romain Guy     */
1097d139ba2c331f11e9b485753cc727a0ff202f2a4Romain Guy    void setMaxSize(uint32_t maxSize);
110121e2242565d5f09ad83a2d33ecd2225838802c5Romain Guy    /**
111121e2242565d5f09ad83a2d33ecd2225838802c5Romain Guy     * Returns the maximum size of the cache in bytes.
112121e2242565d5f09ad83a2d33ecd2225838802c5Romain Guy     */
1137d139ba2c331f11e9b485753cc727a0ff202f2a4Romain Guy    uint32_t getMaxSize();
114121e2242565d5f09ad83a2d33ecd2225838802c5Romain Guy    /**
115121e2242565d5f09ad83a2d33ecd2225838802c5Romain Guy     * Returns the current size of the cache in bytes.
116121e2242565d5f09ad83a2d33ecd2225838802c5Romain Guy     */
1177d139ba2c331f11e9b485753cc727a0ff202f2a4Romain Guy    uint32_t getSize();
118121e2242565d5f09ad83a2d33ecd2225838802c5Romain Guy
119eca0ca2424afc1e98912405906edfc32f7733e16Romain Guy    /**
120eca0ca2424afc1e98912405906edfc32f7733e16Romain Guy     * Partially flushes the cache. The amount of memory freed by a flush
121eca0ca2424afc1e98912405906edfc32f7733e16Romain Guy     * is defined by the flush rate.
122eca0ca2424afc1e98912405906edfc32f7733e16Romain Guy     */
123eca0ca2424afc1e98912405906edfc32f7733e16Romain Guy    void flush();
124eca0ca2424afc1e98912405906edfc32f7733e16Romain Guy    /**
125eca0ca2424afc1e98912405906edfc32f7733e16Romain Guy     * Indicates the percentage of the cache to retain when a
126eca0ca2424afc1e98912405906edfc32f7733e16Romain Guy     * memory trim is requested (see Caches::flush).
127eca0ca2424afc1e98912405906edfc32f7733e16Romain Guy     */
128eca0ca2424afc1e98912405906edfc32f7733e16Romain Guy    void setFlushRate(float flushRate);
129eca0ca2424afc1e98912405906edfc32f7733e16Romain Guy
130ce0537b80087a6225273040a987414b1dd081aa0Romain Guyprivate:
131860d155f866cc15a725e7ce03763280987f24901John Reck
132860d155f866cc15a725e7ce03763280987f24901John Reck    bool canMakeTextureFromBitmap(const SkBitmap* bitmap);
133860d155f866cc15a725e7ce03763280987f24901John Reck
134860d155f866cc15a725e7ce03763280987f24901John Reck    Texture* getCachedTexture(const SkBitmap* bitmap);
135860d155f866cc15a725e7ce03763280987f24901John Reck
136121e2242565d5f09ad83a2d33ecd2225838802c5Romain Guy    /**
137121e2242565d5f09ad83a2d33ecd2225838802c5Romain Guy     * Generates the texture from a bitmap into the specified texture structure.
138121e2242565d5f09ad83a2d33ecd2225838802c5Romain Guy     *
139121e2242565d5f09ad83a2d33ecd2225838802c5Romain Guy     * @param regenerate If true, the bitmap data is reuploaded into the texture, but
140121e2242565d5f09ad83a2d33ecd2225838802c5Romain Guy     *        no new texture is generated.
141121e2242565d5f09ad83a2d33ecd2225838802c5Romain Guy     */
142d218a92c0afb8c0d98135b20b52ac87236e1c935Chris Craik    void generateTexture(const SkBitmap* bitmap, Texture* texture, bool regenerate = false);
143ce0537b80087a6225273040a987414b1dd081aa0Romain Guy
144d218a92c0afb8c0d98135b20b52ac87236e1c935Chris Craik    void uploadLoFiTexture(bool resize, const SkBitmap* bitmap, uint32_t width, uint32_t height);
145c5e0a295418a1fd8c17608041962d70296af6794Lu, Shenghua    void uploadToTexture(bool resize, GLenum format, GLsizei stride, GLsizei bpp,
146318ae7bb92869d99a05388c598ad105e7aa4cdbdRomain Guy            GLsizei width, GLsizei height, GLenum type, const GLvoid * data);
1478c749f87d29e1a363ddf9027c3a51753c612d510Romain Guy
148fb8b763f762ae21923c58d64caa729b012f40e05Romain Guy    void init();
149fb8b763f762ae21923c58d64caa729b012f40e05Romain Guy
150d1ad5e62fda248c6d185cde3cb6d9f01a223066cLeon Scroggins III    LruCache<const SkPixelRef*, Texture*> mCache;
151121e2242565d5f09ad83a2d33ecd2225838802c5Romain Guy
1527d139ba2c331f11e9b485753cc727a0ff202f2a4Romain Guy    uint32_t mSize;
1537d139ba2c331f11e9b485753cc727a0ff202f2a4Romain Guy    uint32_t mMaxSize;
154163935113919a184122b8b3bd672ef08c8df65dcRomain Guy    GLint mMaxTextureSize;
1559aaa8269a3e7291aab84d01c3fc9c744d8f2d2f4Romain Guy
156eca0ca2424afc1e98912405906edfc32f7733e16Romain Guy    float mFlushRate;
157eca0ca2424afc1e98912405906edfc32f7733e16Romain Guy
158e190aa69756aecfaffabdd4c6d32cb6b3220d842Romain Guy    bool mDebugEnabled;
159e190aa69756aecfaffabdd4c6d32cb6b3220d842Romain Guy
160d218a92c0afb8c0d98135b20b52ac87236e1c935Chris Craik    Vector<const SkBitmap*> mGarbage;
1619aaa8269a3e7291aab84d01c3fc9c744d8f2d2f4Romain Guy    mutable Mutex mLock;
162ce0537b80087a6225273040a987414b1dd081aa0Romain Guy}; // class TextureCache
163ce0537b80087a6225273040a987414b1dd081aa0Romain Guy
164ce0537b80087a6225273040a987414b1dd081aa0Romain Guy}; // namespace uirenderer
165ce0537b80087a6225273040a987414b1dd081aa0Romain Guy}; // namespace android
166ce0537b80087a6225273040a987414b1dd081aa0Romain Guy
1675b3b35296e8b2c8d3f07d32bb645d5414db41a1dRomain Guy#endif // ANDROID_HWUI_TEXTURE_CACHE_H
168