Home | History | Annotate | Download | only in hwui
      1 /*
      2  * Copyright (C) 2010 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_PATCH_CACHE_H
     18 #define ANDROID_HWUI_PATCH_CACHE_H
     19 
     20 #include <GLES2/gl2.h>
     21 
     22 #include <utils/LruCache.h>
     23 
     24 #include <androidfw/ResourceTypes.h>
     25 
     26 #include "AssetAtlas.h"
     27 #include "Debug.h"
     28 #include "utils/Pair.h"
     29 
     30 namespace android {
     31 namespace uirenderer {
     32 
     33 class Patch;
     34 
     35 ///////////////////////////////////////////////////////////////////////////////
     36 // Defines
     37 ///////////////////////////////////////////////////////////////////////////////
     38 
     39 // Debug
     40 #if DEBUG_PATCHES
     41     #define PATCH_LOGD(...) ALOGD(__VA_ARGS__)
     42 #else
     43     #define PATCH_LOGD(...)
     44 #endif
     45 
     46 ///////////////////////////////////////////////////////////////////////////////
     47 // Cache
     48 ///////////////////////////////////////////////////////////////////////////////
     49 
     50 class Caches;
     51 
     52 class PatchCache {
     53 public:
     54     PatchCache(RenderState& renderState);
     55     ~PatchCache();
     56     void init();
     57 
     58     const Patch* get(const AssetAtlas::Entry* entry,
     59             const uint32_t bitmapWidth, const uint32_t bitmapHeight,
     60             const float pixelWidth, const float pixelHeight, const Res_png_9patch* patch);
     61     void clear();
     62 
     63     uint32_t getSize() const {
     64         return mSize;
     65     }
     66 
     67     uint32_t getMaxSize() const {
     68         return mMaxSize;
     69     }
     70 
     71     GLuint getMeshBuffer() const {
     72         return mMeshBuffer;
     73     }
     74 
     75     uint32_t getGenerationId() const {
     76         return mGenerationId;
     77     }
     78 
     79     /**
     80      * Removes the entries associated with the specified 9-patch. This is meant
     81      * to be called from threads that are not the EGL context thread (GC thread
     82      * on the VM side for instance.)
     83      */
     84     void removeDeferred(Res_png_9patch* patch);
     85 
     86     /**
     87      * Process deferred removals.
     88      */
     89     void clearGarbage();
     90 
     91 
     92 private:
     93     struct PatchDescription {
     94         PatchDescription(): mPatch(nullptr), mBitmapWidth(0), mBitmapHeight(0),
     95                 mPixelWidth(0), mPixelHeight(0) {
     96         }
     97 
     98         PatchDescription(const uint32_t bitmapWidth, const uint32_t bitmapHeight,
     99                 const float pixelWidth, const float pixelHeight, const Res_png_9patch* patch):
    100                 mPatch(patch), mBitmapWidth(bitmapWidth), mBitmapHeight(bitmapHeight),
    101                 mPixelWidth(pixelWidth), mPixelHeight(pixelHeight) {
    102         }
    103 
    104         hash_t hash() const;
    105 
    106         const Res_png_9patch* getPatch() const { return mPatch; }
    107 
    108         static int compare(const PatchDescription& lhs, const PatchDescription& rhs);
    109 
    110         bool operator==(const PatchDescription& other) const {
    111             return compare(*this, other) == 0;
    112         }
    113 
    114         bool operator!=(const PatchDescription& other) const {
    115             return compare(*this, other) != 0;
    116         }
    117 
    118         friend inline int strictly_order_type(const PatchDescription& lhs,
    119                 const PatchDescription& rhs) {
    120             return PatchDescription::compare(lhs, rhs) < 0;
    121         }
    122 
    123         friend inline int compare_type(const PatchDescription& lhs,
    124                 const PatchDescription& rhs) {
    125             return PatchDescription::compare(lhs, rhs);
    126         }
    127 
    128         friend inline hash_t hash_type(const PatchDescription& entry) {
    129             return entry.hash();
    130         }
    131 
    132     private:
    133         const Res_png_9patch* mPatch;
    134         uint32_t mBitmapWidth;
    135         uint32_t mBitmapHeight;
    136         float mPixelWidth;
    137         float mPixelHeight;
    138 
    139     }; // struct PatchDescription
    140 
    141     /**
    142      * A buffer block represents an empty range in the mesh buffer
    143      * that can be used to store vertices.
    144      *
    145      * The patch cache maintains a linked-list of buffer blocks
    146      * to track available regions of memory in the VBO.
    147      */
    148     struct BufferBlock {
    149         BufferBlock(uint32_t offset, uint32_t size): offset(offset), size(size), next(nullptr) {
    150         }
    151 
    152         uint32_t offset;
    153         uint32_t size;
    154 
    155         BufferBlock* next;
    156     }; // struct BufferBlock
    157 
    158     typedef Pair<const PatchDescription*, Patch*> patch_pair_t;
    159 
    160     void clearCache();
    161     void createVertexBuffer();
    162 
    163     void setupMesh(Patch* newMesh);
    164 
    165     void remove(Vector<patch_pair_t>& patchesToRemove, Res_png_9patch* patch);
    166 
    167 #if DEBUG_PATCHES
    168     void dumpFreeBlocks(const char* prefix);
    169 #endif
    170 
    171     RenderState& mRenderState;
    172     const uint32_t mMaxSize;
    173     uint32_t mSize;
    174 
    175     LruCache<PatchDescription, Patch*> mCache;
    176 
    177     GLuint mMeshBuffer;
    178     // First available free block inside the mesh buffer
    179     BufferBlock* mFreeBlocks;
    180 
    181     uint32_t mGenerationId;
    182 
    183     // Garbage tracking, required to handle GC events on the VM side
    184     Vector<Res_png_9patch*> mGarbage;
    185     mutable Mutex mLock;
    186 }; // class PatchCache
    187 
    188 }; // namespace uirenderer
    189 }; // namespace android
    190 
    191 #endif // ANDROID_HWUI_PATCH_CACHE_H
    192