blob: 06e567e114e2c53e6c352c488be3ddb45093246f [file] [log] [blame]
Chris Craik05f3d6e2014-06-02 16:27:04 -07001/*
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_HWUI_TESSELLATION_CACHE_H
18#define ANDROID_HWUI_TESSELLATION_CACHE_H
19
Chris Craik05f3d6e2014-06-02 16:27:04 -070020#include "Debug.h"
John Reck82f5e0c2015-10-22 17:07:45 -070021#include "Matrix.h"
22#include "Rect.h"
23#include "Vector.h"
24#include "thread/TaskProcessor.h"
Chris Craik05f3d6e2014-06-02 16:27:04 -070025#include "utils/Macros.h"
26#include "utils/Pair.h"
Chris Craik05f3d6e2014-06-02 16:27:04 -070027
John Reck82f5e0c2015-10-22 17:07:45 -070028#include <SkPaint.h>
29
30#include <utils/LruCache.h>
31#include <utils/Mutex.h>
32#include <utils/StrongPointer.h>
33
Chris Craik05f3d6e2014-06-02 16:27:04 -070034class SkBitmap;
35class SkCanvas;
Chris Craik05f3d6e2014-06-02 16:27:04 -070036class SkPath;
37struct SkRect;
38
39namespace android {
40namespace uirenderer {
41
42class Caches;
Tom Hudson2dc236b2014-10-15 15:46:42 -040043class VertexBuffer;
Chris Craik05f3d6e2014-06-02 16:27:04 -070044
45///////////////////////////////////////////////////////////////////////////////
46// Classes
47///////////////////////////////////////////////////////////////////////////////
48
49class TessellationCache {
50public:
51 typedef Pair<VertexBuffer*, VertexBuffer*> vertexBuffer_pair_t;
52
53 struct Description {
54 DESCRIPTION_TYPE(Description);
55 enum Type {
56 kNone,
57 kRoundRect,
Chris Craik05f3d6e2014-06-02 16:27:04 -070058 };
59
60 Type type;
Chris Craik6ac174b2014-06-17 13:47:05 -070061 float scaleX;
62 float scaleY;
Chris Craiked4ef0b2014-06-12 13:27:30 -070063 bool aa;
Chris Craik05f3d6e2014-06-02 16:27:04 -070064 SkPaint::Cap cap;
65 SkPaint::Style style;
66 float strokeWidth;
67 union Shape {
68 struct RoundRect {
Chris Craik6ac174b2014-06-17 13:47:05 -070069 float width;
70 float height;
71 float rx;
72 float ry;
Chris Craik05f3d6e2014-06-02 16:27:04 -070073 } roundRect;
74 } shape;
75
76 Description();
Chris Craik6ac174b2014-06-17 13:47:05 -070077 Description(Type type, const Matrix4& transform, const SkPaint& paint);
Chris Craik05f3d6e2014-06-02 16:27:04 -070078 hash_t hash() const;
Chris Craik6ac174b2014-06-17 13:47:05 -070079 void setupMatrixAndPaint(Matrix4* matrix, SkPaint* paint) const;
Chris Craik05f3d6e2014-06-02 16:27:04 -070080 };
81
82 struct ShadowDescription {
83 DESCRIPTION_TYPE(ShadowDescription);
84 const void* nodeKey;
85 float matrixData[16];
86
87 ShadowDescription();
88 ShadowDescription(const void* nodeKey, const Matrix4* drawTransform);
89 hash_t hash() const;
90 };
91
92 TessellationCache();
93 ~TessellationCache();
94
95 /**
96 * Clears the cache. This causes all TessellationBuffers to be deleted.
97 */
98 void clear();
99
100 /**
101 * Sets the maximum size of the cache in bytes.
102 */
103 void setMaxSize(uint32_t maxSize);
104 /**
105 * Returns the maximum size of the cache in bytes.
106 */
107 uint32_t getMaxSize();
108 /**
109 * Returns the current size of the cache in bytes.
110 */
111 uint32_t getSize();
112
113 /**
114 * Trims the contents of the cache, removing items until it's under its
115 * specified limit.
116 *
117 * Trimming is used for caches that support pre-caching from a worker
118 * thread. During pre-caching the maximum limit of the cache can be
119 * exceeded for the duration of the frame. It is therefore required to
120 * trim the cache at the end of the frame to keep the total amount of
121 * memory used under control.
122 *
123 * Also removes transient Shadow VertexBuffers, which aren't cached between frames.
124 */
125 void trim();
126
127 // TODO: precache/get for Oval, Lines, Points, etc.
128
Chris Craik6ac174b2014-06-17 13:47:05 -0700129 void precacheRoundRect(const Matrix4& transform, const SkPaint& paint,
130 float width, float height, float rx, float ry) {
131 getRoundRectBuffer(transform, paint, width, height, rx, ry);
Chris Craik05f3d6e2014-06-02 16:27:04 -0700132 }
Chris Craik6ac174b2014-06-17 13:47:05 -0700133 const VertexBuffer* getRoundRect(const Matrix4& transform, const SkPaint& paint,
134 float width, float height, float rx, float ry);
Chris Craik05f3d6e2014-06-02 16:27:04 -0700135
136 void precacheShadows(const Matrix4* drawTransform, const Rect& localClip,
137 bool opaque, const SkPath* casterPerimeter,
138 const Matrix4* transformXY, const Matrix4* transformZ,
139 const Vector3& lightCenter, float lightRadius);
140
141 void getShadowBuffers(const Matrix4* drawTransform, const Rect& localClip,
142 bool opaque, const SkPath* casterPerimeter,
143 const Matrix4* transformXY, const Matrix4* transformZ,
144 const Vector3& lightCenter, float lightRadius,
145 vertexBuffer_pair_t& outBuffers);
146
147private:
148 class Buffer;
149 class TessellationTask;
150 class TessellationProcessor;
151
Chris Craik6ac174b2014-06-17 13:47:05 -0700152 typedef VertexBuffer* (*Tessellator)(const Description&);
Chris Craik05f3d6e2014-06-02 16:27:04 -0700153
Chris Craik6ac174b2014-06-17 13:47:05 -0700154 Buffer* getRectBuffer(const Matrix4& transform, const SkPaint& paint,
155 float width, float height);
156 Buffer* getRoundRectBuffer(const Matrix4& transform, const SkPaint& paint,
157 float width, float height, float rx, float ry);
Chris Craik05f3d6e2014-06-02 16:27:04 -0700158
Chris Craik6ac174b2014-06-17 13:47:05 -0700159 Buffer* getOrCreateBuffer(const Description& entry, Tessellator tessellator);
Chris Craik05f3d6e2014-06-02 16:27:04 -0700160
161 uint32_t mSize;
162 uint32_t mMaxSize;
163
164 bool mDebugEnabled;
165
166 mutable Mutex mLock;
167
168 ///////////////////////////////////////////////////////////////////////////////
169 // General tessellation caching
170 ///////////////////////////////////////////////////////////////////////////////
171 sp<TaskProcessor<VertexBuffer*> > mProcessor;
172 LruCache<Description, Buffer*> mCache;
173 class BufferRemovedListener : public OnEntryRemoved<Description, Buffer*> {
Chris Craike84a2082014-12-22 14:28:49 -0800174 void operator()(Description& description, Buffer*& buffer) override;
Chris Craik05f3d6e2014-06-02 16:27:04 -0700175 };
176 BufferRemovedListener mBufferRemovedListener;
177
178 ///////////////////////////////////////////////////////////////////////////////
179 // Shadow tessellation caching
180 ///////////////////////////////////////////////////////////////////////////////
181 sp<TaskProcessor<vertexBuffer_pair_t*> > mShadowProcessor;
182
183 // holds a pointer, and implicit strong ref to each shadow task of the frame
184 LruCache<ShadowDescription, Task<vertexBuffer_pair_t*>*> mShadowCache;
185 class BufferPairRemovedListener : public OnEntryRemoved<ShadowDescription, Task<vertexBuffer_pair_t*>*> {
Chris Craike84a2082014-12-22 14:28:49 -0800186 void operator()(ShadowDescription& description, Task<vertexBuffer_pair_t*>*& bufferPairTask) override {
187 bufferPairTask->decStrong(nullptr);
Chris Craik05f3d6e2014-06-02 16:27:04 -0700188 }
189 };
190 BufferPairRemovedListener mBufferPairRemovedListener;
191
192}; // class TessellationCache
193
John Reck82f5e0c2015-10-22 17:07:45 -0700194void tessellateShadows(
195 const Matrix4* drawTransform, const Rect* localClip,
196 bool isCasterOpaque, const SkPath* casterPerimeter,
197 const Matrix4* casterTransformXY, const Matrix4* casterTransformZ,
198 const Vector3& lightCenter, float lightRadius,
199 VertexBuffer& ambientBuffer, VertexBuffer& spotBuffer);
200
Chris Craik05f3d6e2014-06-02 16:27:04 -0700201}; // namespace uirenderer
202}; // namespace android
203
204#endif // ANDROID_HWUI_PATH_CACHE_H