blob: c3444e60784f8758dc4bbeb14ecb2b2e1370d974 [file] [log] [blame]
Romain Guy4aa90572010-09-26 18:40:37 -07001/*
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#define LOG_TAG "OpenGLRenderer"
18
Romain Guyd5a85fb2012-03-13 11:18:20 -070019#include <SkCamera.h>
Chet Haase9c1e23b2011-03-24 10:51:31 -070020
Romain Guy65549432012-03-26 16:45:05 -070021#include <private/hwui/DrawGlInfo.h>
22
Chet Haase9c1e23b2011-03-24 10:51:31 -070023#include "DisplayListLogBuffer.h"
Romain Guy4aa90572010-09-26 18:40:37 -070024#include "DisplayListRenderer.h"
Chet Haase9c1e23b2011-03-24 10:51:31 -070025#include "Caches.h"
Romain Guy13631f32012-01-30 17:41:55 -080026
Romain Guy4aa90572010-09-26 18:40:37 -070027namespace android {
28namespace uirenderer {
29
30///////////////////////////////////////////////////////////////////////////////
Romain Guyb051e892010-09-28 19:09:36 -070031// Display list
32///////////////////////////////////////////////////////////////////////////////
33
Romain Guyffac7fc2011-01-13 17:21:49 -080034const char* DisplayList::OP_NAMES[] = {
Romain Guyffac7fc2011-01-13 17:21:49 -080035 "Save",
36 "Restore",
37 "RestoreToCount",
38 "SaveLayer",
39 "SaveLayerAlpha",
40 "Translate",
41 "Rotate",
42 "Scale",
Romain Guy4cf6e2f2011-01-23 11:35:13 -080043 "Skew",
Romain Guyffac7fc2011-01-13 17:21:49 -080044 "SetMatrix",
45 "ConcatMatrix",
46 "ClipRect",
47 "DrawDisplayList",
48 "DrawLayer",
49 "DrawBitmap",
50 "DrawBitmapMatrix",
51 "DrawBitmapRect",
Romain Guye651cc62012-05-14 19:44:40 -070052 "DrawBitmapData",
Romain Guy5a7b4662011-01-20 19:09:30 -080053 "DrawBitmapMesh",
Romain Guyffac7fc2011-01-13 17:21:49 -080054 "DrawPatch",
55 "DrawColor",
56 "DrawRect",
Romain Guy01d58e42011-01-19 21:54:02 -080057 "DrawRoundRect",
58 "DrawCircle",
Romain Guyc1cd9ba32011-01-23 14:18:41 -080059 "DrawOval",
Romain Guy8b2f5262011-01-23 16:15:02 -080060 "DrawArc",
Romain Guyffac7fc2011-01-13 17:21:49 -080061 "DrawPath",
62 "DrawLines",
Romain Guyed6fcb02011-03-21 13:11:28 -070063 "DrawPoints",
Romain Guy325740f2012-02-24 16:48:34 -080064 "DrawTextOnPath",
Romain Guyeb9a5362012-01-17 17:39:26 -080065 "DrawPosText",
Romain Guyc2525952012-07-27 16:41:22 -070066 "DrawText",
Romain Guyffac7fc2011-01-13 17:21:49 -080067 "ResetShader",
68 "SetupShader",
69 "ResetColorFilter",
70 "SetupColorFilter",
71 "ResetShadow",
Chet Haasedaf98e92011-01-10 14:10:36 -080072 "SetupShadow",
Romain Guy5ff9df62012-01-23 17:09:05 -080073 "ResetPaintFilter",
74 "SetupPaintFilter",
Chet Haasedaf98e92011-01-10 14:10:36 -080075 "DrawGLFunction"
Romain Guyffac7fc2011-01-13 17:21:49 -080076};
77
Chet Haase9c1e23b2011-03-24 10:51:31 -070078void DisplayList::outputLogBuffer(int fd) {
79 DisplayListLogBuffer& logBuffer = DisplayListLogBuffer::getInstance();
80 if (logBuffer.isEmpty()) {
81 return;
82 }
Romain Guy65b345f2011-07-27 18:51:50 -070083
Chet Haase9c1e23b2011-03-24 10:51:31 -070084 FILE *file = fdopen(fd, "a");
Romain Guy65b345f2011-07-27 18:51:50 -070085
Chet Haase9c1e23b2011-03-24 10:51:31 -070086 fprintf(file, "\nRecent DisplayList operations\n");
87 logBuffer.outputCommands(file, OP_NAMES);
Romain Guy65b345f2011-07-27 18:51:50 -070088
89 String8 cachesLog;
90 Caches::getInstance().dumpMemoryUsage(cachesLog);
91 fprintf(file, "\nCaches:\n%s", cachesLog.string());
92 fprintf(file, "\n");
93
Chet Haase9c1e23b2011-03-24 10:51:31 -070094 fflush(file);
95}
96
Chet Haase491189f2012-03-13 11:42:34 -070097DisplayList::DisplayList(const DisplayListRenderer& recorder) :
Chet Haase9420abd2012-03-29 16:28:32 -070098 mTransformMatrix(NULL), mTransformCamera(NULL), mTransformMatrix3D(NULL),
99 mStaticMatrix(NULL), mAnimationMatrix(NULL) {
Chet Haase491189f2012-03-13 11:42:34 -0700100
Chet Haase5977baa2011-01-05 18:01:22 -0800101 initFromDisplayListRenderer(recorder);
102}
103
104DisplayList::~DisplayList() {
Chet Haased63cbd12011-02-03 16:32:46 -0800105 clearResources();
106}
107
Chet Haasea1cff502012-02-21 13:43:44 -0800108void DisplayList::initProperties() {
109 mLeft = 0;
110 mTop = 0;
Chet Haaseb85967b2012-03-26 14:37:51 -0700111 mRight = 0;
Chet Haasea1cff502012-02-21 13:43:44 -0800112 mBottom = 0;
Chet Haasea1cff502012-02-21 13:43:44 -0800113 mClipChildren = true;
114 mAlpha = 1;
115 mMultipliedAlpha = 255;
Chet Haasedb8c9a62012-03-21 18:54:18 -0700116 mHasOverlappingRendering = true;
Chet Haasea1cff502012-02-21 13:43:44 -0800117 mTranslationX = 0;
118 mTranslationY = 0;
119 mRotation = 0;
120 mRotationX = 0;
121 mRotationY= 0;
122 mScaleX = 1;
123 mScaleY = 1;
124 mPivotX = 0;
125 mPivotY = 0;
Chet Haaseb85967b2012-03-26 14:37:51 -0700126 mCameraDistance = 0;
Chet Haasea1cff502012-02-21 13:43:44 -0800127 mMatrixDirty = false;
128 mMatrixFlags = 0;
129 mPrevWidth = -1;
130 mPrevHeight = -1;
131 mWidth = 0;
132 mHeight = 0;
133 mPivotExplicitlySet = false;
Chet Haasea1cff502012-02-21 13:43:44 -0800134 mCaching = false;
135}
136
Romain Guybb0acdf2012-03-05 13:44:35 -0800137void DisplayList::destroyDisplayListDeferred(DisplayList* displayList) {
138 if (displayList) {
139 DISPLAY_LIST_LOGD("Deferring display list destruction");
140 Caches::getInstance().deleteDisplayListDeferred(displayList);
141 }
142}
143
Chet Haased63cbd12011-02-03 16:32:46 -0800144void DisplayList::clearResources() {
Chet Haase5977baa2011-01-05 18:01:22 -0800145 sk_free((void*) mReader.base());
146
Chet Haase1271e2c2012-04-20 09:54:27 -0700147 delete mTransformMatrix;
148 delete mTransformCamera;
149 delete mTransformMatrix3D;
150 delete mStaticMatrix;
151 delete mAnimationMatrix;
Romain Guy58ecc202012-09-07 11:58:36 -0700152
Chet Haase1271e2c2012-04-20 09:54:27 -0700153 mTransformMatrix = NULL;
154 mTransformCamera = NULL;
155 mTransformMatrix3D = NULL;
156 mStaticMatrix = NULL;
157 mAnimationMatrix = NULL;
Chet Haasea1cff502012-02-21 13:43:44 -0800158
Chet Haase5977baa2011-01-05 18:01:22 -0800159 Caches& caches = Caches::getInstance();
Romain Guy58ecc202012-09-07 11:58:36 -0700160 caches.resourceCache.lock();
Chet Haase5977baa2011-01-05 18:01:22 -0800161
162 for (size_t i = 0; i < mBitmapResources.size(); i++) {
Romain Guy58ecc202012-09-07 11:58:36 -0700163 caches.resourceCache.decrementRefcountLocked(mBitmapResources.itemAt(i));
Chet Haase5977baa2011-01-05 18:01:22 -0800164 }
Chet Haase5977baa2011-01-05 18:01:22 -0800165
Romain Guy49c5fc02012-05-15 11:10:01 -0700166 for (size_t i = 0; i < mOwnedBitmapResources.size(); i++) {
167 SkBitmap* bitmap = mOwnedBitmapResources.itemAt(i);
Romain Guy58ecc202012-09-07 11:58:36 -0700168 caches.resourceCache.decrementRefcountLocked(bitmap);
169 caches.resourceCache.destructorLocked(bitmap);
Romain Guy49c5fc02012-05-15 11:10:01 -0700170 }
Romain Guy49c5fc02012-05-15 11:10:01 -0700171
Romain Guyd586ad92011-06-22 16:14:36 -0700172 for (size_t i = 0; i < mFilterResources.size(); i++) {
Romain Guy58ecc202012-09-07 11:58:36 -0700173 caches.resourceCache.decrementRefcountLocked(mFilterResources.itemAt(i));
Romain Guyd586ad92011-06-22 16:14:36 -0700174 }
Romain Guyd586ad92011-06-22 16:14:36 -0700175
Romain Guy24c00212011-01-14 15:31:00 -0800176 for (size_t i = 0; i < mShaders.size(); i++) {
Romain Guy58ecc202012-09-07 11:58:36 -0700177 caches.resourceCache.decrementRefcountLocked(mShaders.itemAt(i));
178 caches.resourceCache.destructorLocked(mShaders.itemAt(i));
Chet Haase5977baa2011-01-05 18:01:22 -0800179 }
Romain Guy58ecc202012-09-07 11:58:36 -0700180
181 for (size_t i = 0; i < mSourcePaths.size(); i++) {
182 caches.resourceCache.decrementRefcountLocked(mSourcePaths.itemAt(i));
183 }
184
185 caches.resourceCache.unlock();
Chet Haase5977baa2011-01-05 18:01:22 -0800186
187 for (size_t i = 0; i < mPaints.size(); i++) {
188 delete mPaints.itemAt(i);
189 }
Chet Haase5977baa2011-01-05 18:01:22 -0800190
Romain Guy2fc941e2011-02-03 15:06:05 -0800191 for (size_t i = 0; i < mPaths.size(); i++) {
Romain Guy1af23a32011-03-24 16:03:55 -0700192 SkPath* path = mPaths.itemAt(i);
193 caches.pathCache.remove(path);
194 delete path;
Romain Guy2fc941e2011-02-03 15:06:05 -0800195 }
Chet Haased34dd712012-05-02 18:50:34 -0700196
Chet Haase5977baa2011-01-05 18:01:22 -0800197 for (size_t i = 0; i < mMatrices.size(); i++) {
198 delete mMatrices.itemAt(i);
199 }
Romain Guy58ecc202012-09-07 11:58:36 -0700200
201 mBitmapResources.clear();
202 mOwnedBitmapResources.clear();
203 mFilterResources.clear();
204 mShaders.clear();
205 mSourcePaths.clear();
206 mPaints.clear();
207 mPaths.clear();
Chet Haase5977baa2011-01-05 18:01:22 -0800208 mMatrices.clear();
Chet Haase5977baa2011-01-05 18:01:22 -0800209}
210
Chet Haased63cbd12011-02-03 16:32:46 -0800211void DisplayList::initFromDisplayListRenderer(const DisplayListRenderer& recorder, bool reusing) {
Romain Guyb051e892010-09-28 19:09:36 -0700212 const SkWriter32& writer = recorder.writeStream();
213 init();
214
215 if (writer.size() == 0) {
216 return;
217 }
218
Chet Haased63cbd12011-02-03 16:32:46 -0800219 if (reusing) {
220 // re-using display list - clear out previous allocations
221 clearResources();
222 }
Chet Haasea1cff502012-02-21 13:43:44 -0800223 initProperties();
Chet Haased63cbd12011-02-03 16:32:46 -0800224
Romain Guy65b345f2011-07-27 18:51:50 -0700225 mSize = writer.size();
226 void* buffer = sk_malloc_throw(mSize);
Romain Guyb051e892010-09-28 19:09:36 -0700227 writer.flatten(buffer);
Romain Guy65b345f2011-07-27 18:51:50 -0700228 mReader.setMemory(buffer, mSize);
Romain Guyb051e892010-09-28 19:09:36 -0700229
Chet Haase5c13d892010-10-08 08:37:55 -0700230 Caches& caches = Caches::getInstance();
Romain Guy58ecc202012-09-07 11:58:36 -0700231 caches.resourceCache.lock();
Romain Guyb051e892010-09-28 19:09:36 -0700232
Romain Guy49c5fc02012-05-15 11:10:01 -0700233 const Vector<SkBitmap*>& bitmapResources = recorder.getBitmapResources();
Chet Haase5c13d892010-10-08 08:37:55 -0700234 for (size_t i = 0; i < bitmapResources.size(); i++) {
235 SkBitmap* resource = bitmapResources.itemAt(i);
236 mBitmapResources.add(resource);
Romain Guy58ecc202012-09-07 11:58:36 -0700237 caches.resourceCache.incrementRefcountLocked(resource);
Romain Guyb051e892010-09-28 19:09:36 -0700238 }
Chet Haased98aa2d2010-10-25 15:47:32 -0700239
Romain Guy49c5fc02012-05-15 11:10:01 -0700240 const Vector<SkBitmap*> &ownedBitmapResources = recorder.getOwnedBitmapResources();
241 for (size_t i = 0; i < ownedBitmapResources.size(); i++) {
242 SkBitmap* resource = ownedBitmapResources.itemAt(i);
243 mOwnedBitmapResources.add(resource);
Romain Guy58ecc202012-09-07 11:58:36 -0700244 caches.resourceCache.incrementRefcountLocked(resource);
Romain Guy49c5fc02012-05-15 11:10:01 -0700245 }
246
247 const Vector<SkiaColorFilter*>& filterResources = recorder.getFilterResources();
Romain Guyd586ad92011-06-22 16:14:36 -0700248 for (size_t i = 0; i < filterResources.size(); i++) {
249 SkiaColorFilter* resource = filterResources.itemAt(i);
250 mFilterResources.add(resource);
Romain Guy58ecc202012-09-07 11:58:36 -0700251 caches.resourceCache.incrementRefcountLocked(resource);
Romain Guyd586ad92011-06-22 16:14:36 -0700252 }
253
Romain Guy49c5fc02012-05-15 11:10:01 -0700254 const Vector<SkiaShader*>& shaders = recorder.getShaders();
Romain Guy24c00212011-01-14 15:31:00 -0800255 for (size_t i = 0; i < shaders.size(); i++) {
Romain Guyd586ad92011-06-22 16:14:36 -0700256 SkiaShader* resource = shaders.itemAt(i);
257 mShaders.add(resource);
Romain Guy58ecc202012-09-07 11:58:36 -0700258 caches.resourceCache.incrementRefcountLocked(resource);
Romain Guyb051e892010-09-28 19:09:36 -0700259 }
260
Romain Guy58ecc202012-09-07 11:58:36 -0700261 const SortedVector<SkPath*>& sourcePaths = recorder.getSourcePaths();
262 for (size_t i = 0; i < sourcePaths.size(); i++) {
263 mSourcePaths.add(sourcePaths.itemAt(i));
264 caches.resourceCache.incrementRefcountLocked(sourcePaths.itemAt(i));
265 }
266
267 caches.resourceCache.unlock();
268
Romain Guy49c5fc02012-05-15 11:10:01 -0700269 const Vector<SkPaint*>& paints = recorder.getPaints();
Chet Haased98aa2d2010-10-25 15:47:32 -0700270 for (size_t i = 0; i < paints.size(); i++) {
271 mPaints.add(paints.itemAt(i));
272 }
273
Romain Guy49c5fc02012-05-15 11:10:01 -0700274 const Vector<SkPath*>& paths = recorder.getPaths();
Romain Guy2fc941e2011-02-03 15:06:05 -0800275 for (size_t i = 0; i < paths.size(); i++) {
276 mPaths.add(paths.itemAt(i));
277 }
278
Romain Guy49c5fc02012-05-15 11:10:01 -0700279 const Vector<SkMatrix*>& matrices = recorder.getMatrices();
Chet Haased98aa2d2010-10-25 15:47:32 -0700280 for (size_t i = 0; i < matrices.size(); i++) {
281 mMatrices.add(matrices.itemAt(i));
282 }
Romain Guyb051e892010-09-28 19:09:36 -0700283}
284
Romain Guyb051e892010-09-28 19:09:36 -0700285void DisplayList::init() {
Romain Guy65b345f2011-07-27 18:51:50 -0700286 mSize = 0;
Romain Guy04c9d8c2011-08-25 14:01:48 -0700287 mIsRenderable = true;
Romain Guy65b345f2011-07-27 18:51:50 -0700288}
289
290size_t DisplayList::getSize() {
291 return mSize;
Romain Guyb051e892010-09-28 19:09:36 -0700292}
293
Chet Haaseed30fd82011-04-22 16:18:45 -0700294/**
295 * This function is a simplified version of replay(), where we simply retrieve and log the
296 * display list. This function should remain in sync with the replay() function.
297 */
298void DisplayList::output(OpenGLRenderer& renderer, uint32_t level) {
299 TextContainer text;
300
301 uint32_t count = (level + 1) * 2;
302 char indent[count + 1];
303 for (uint32_t i = 0; i < count; i++) {
304 indent[i] = ' ';
305 }
306 indent[count] = '\0';
Romain Guyddf74372012-05-22 14:07:07 -0700307 ALOGD("%sStart display list (%p, %s, render=%d)", (char*) indent + 2, this,
308 mName.string(), isRenderable());
Chet Haaseed30fd82011-04-22 16:18:45 -0700309
Chet Haase1271e2c2012-04-20 09:54:27 -0700310 ALOGD("%s%s %d", indent, "Save", SkCanvas::kMatrix_SaveFlag | SkCanvas::kClip_SaveFlag);
Chet Haaseed30fd82011-04-22 16:18:45 -0700311 int saveCount = renderer.getSaveCount() - 1;
312
Chet Haasea1cff502012-02-21 13:43:44 -0800313 outputViewProperties(renderer, (char*) indent);
Chet Haaseed30fd82011-04-22 16:18:45 -0700314 mReader.rewind();
315
316 while (!mReader.eof()) {
317 int op = mReader.readInt();
Romain Guy33f6beb2012-02-16 19:24:51 -0800318 if (op & OP_MAY_BE_SKIPPED_MASK) {
319 int skip = mReader.readInt();
320 ALOGD("%sSkip %d", (char*) indent, skip);
321 op &= ~OP_MAY_BE_SKIPPED_MASK;
Chet Haasea1cff502012-02-21 13:43:44 -0800322 }
Chet Haaseed30fd82011-04-22 16:18:45 -0700323
324 switch (op) {
325 case DrawGLFunction: {
326 Functor *functor = (Functor *) getInt();
Steve Block5baa3a62011-12-20 16:23:08 +0000327 ALOGD("%s%s %p", (char*) indent, OP_NAMES[op], functor);
Chet Haaseed30fd82011-04-22 16:18:45 -0700328 }
329 break;
330 case Save: {
331 int rendererNum = getInt();
Steve Block5baa3a62011-12-20 16:23:08 +0000332 ALOGD("%s%s %d", (char*) indent, OP_NAMES[op], rendererNum);
Chet Haaseed30fd82011-04-22 16:18:45 -0700333 }
334 break;
335 case Restore: {
Steve Block5baa3a62011-12-20 16:23:08 +0000336 ALOGD("%s%s", (char*) indent, OP_NAMES[op]);
Chet Haaseed30fd82011-04-22 16:18:45 -0700337 }
338 break;
339 case RestoreToCount: {
340 int restoreCount = saveCount + getInt();
Steve Block5baa3a62011-12-20 16:23:08 +0000341 ALOGD("%s%s %d", (char*) indent, OP_NAMES[op], restoreCount);
Chet Haaseed30fd82011-04-22 16:18:45 -0700342 }
343 break;
344 case SaveLayer: {
345 float f1 = getFloat();
346 float f2 = getFloat();
347 float f3 = getFloat();
348 float f4 = getFloat();
Romain Guy5ff9df62012-01-23 17:09:05 -0800349 SkPaint* paint = getPaint(renderer);
Chet Haaseed30fd82011-04-22 16:18:45 -0700350 int flags = getInt();
Steve Block5baa3a62011-12-20 16:23:08 +0000351 ALOGD("%s%s %.2f, %.2f, %.2f, %.2f, %p, 0x%x", (char*) indent,
Chet Haasea1cff502012-02-21 13:43:44 -0800352 OP_NAMES[op], f1, f2, f3, f4, paint, flags);
Chet Haaseed30fd82011-04-22 16:18:45 -0700353 }
354 break;
355 case SaveLayerAlpha: {
356 float f1 = getFloat();
357 float f2 = getFloat();
358 float f3 = getFloat();
359 float f4 = getFloat();
360 int alpha = getInt();
361 int flags = getInt();
Steve Block5baa3a62011-12-20 16:23:08 +0000362 ALOGD("%s%s %.2f, %.2f, %.2f, %.2f, %d, 0x%x", (char*) indent,
Chet Haasea1cff502012-02-21 13:43:44 -0800363 OP_NAMES[op], f1, f2, f3, f4, alpha, flags);
Chet Haaseed30fd82011-04-22 16:18:45 -0700364 }
365 break;
366 case Translate: {
367 float f1 = getFloat();
368 float f2 = getFloat();
Steve Block5baa3a62011-12-20 16:23:08 +0000369 ALOGD("%s%s %.2f, %.2f", (char*) indent, OP_NAMES[op], f1, f2);
Chet Haaseed30fd82011-04-22 16:18:45 -0700370 }
371 break;
372 case Rotate: {
373 float rotation = getFloat();
Steve Block5baa3a62011-12-20 16:23:08 +0000374 ALOGD("%s%s %.2f", (char*) indent, OP_NAMES[op], rotation);
Chet Haaseed30fd82011-04-22 16:18:45 -0700375 }
376 break;
377 case Scale: {
378 float sx = getFloat();
379 float sy = getFloat();
Steve Block5baa3a62011-12-20 16:23:08 +0000380 ALOGD("%s%s %.2f, %.2f", (char*) indent, OP_NAMES[op], sx, sy);
Chet Haaseed30fd82011-04-22 16:18:45 -0700381 }
382 break;
383 case Skew: {
384 float sx = getFloat();
385 float sy = getFloat();
Steve Block5baa3a62011-12-20 16:23:08 +0000386 ALOGD("%s%s %.2f, %.2f", (char*) indent, OP_NAMES[op], sx, sy);
Chet Haaseed30fd82011-04-22 16:18:45 -0700387 }
388 break;
389 case SetMatrix: {
390 SkMatrix* matrix = getMatrix();
Steve Block5baa3a62011-12-20 16:23:08 +0000391 ALOGD("%s%s %p", (char*) indent, OP_NAMES[op], matrix);
Chet Haaseed30fd82011-04-22 16:18:45 -0700392 }
393 break;
394 case ConcatMatrix: {
395 SkMatrix* matrix = getMatrix();
Chet Haasea1cff502012-02-21 13:43:44 -0800396 ALOGD("%s%s new concat %p: [%f, %f, %f] [%f, %f, %f] [%f, %f, %f]",
397 (char*) indent, OP_NAMES[op], matrix, matrix->get(0), matrix->get(1),
398 matrix->get(2), matrix->get(3), matrix->get(4), matrix->get(5),
399 matrix->get(6), matrix->get(7), matrix->get(8));
Chet Haaseed30fd82011-04-22 16:18:45 -0700400 }
401 break;
402 case ClipRect: {
403 float f1 = getFloat();
404 float f2 = getFloat();
405 float f3 = getFloat();
406 float f4 = getFloat();
407 int regionOp = getInt();
Steve Block5baa3a62011-12-20 16:23:08 +0000408 ALOGD("%s%s %.2f, %.2f, %.2f, %.2f, %d", (char*) indent, OP_NAMES[op],
Chet Haasea1cff502012-02-21 13:43:44 -0800409 f1, f2, f3, f4, regionOp);
Chet Haaseed30fd82011-04-22 16:18:45 -0700410 }
411 break;
412 case DrawDisplayList: {
413 DisplayList* displayList = getDisplayList();
Romain Guy33f6beb2012-02-16 19:24:51 -0800414 int32_t flags = getInt();
415 ALOGD("%s%s %p, %dx%d, 0x%x %d", (char*) indent, OP_NAMES[op],
Chet Haase1271e2c2012-04-20 09:54:27 -0700416 displayList, mWidth, mHeight, flags, level + 1);
Chet Haaseed30fd82011-04-22 16:18:45 -0700417 renderer.outputDisplayList(displayList, level + 1);
418 }
419 break;
420 case DrawLayer: {
421 Layer* layer = (Layer*) getInt();
422 float x = getFloat();
423 float y = getFloat();
Romain Guy5ff9df62012-01-23 17:09:05 -0800424 SkPaint* paint = getPaint(renderer);
Steve Block5baa3a62011-12-20 16:23:08 +0000425 ALOGD("%s%s %p, %.2f, %.2f, %p", (char*) indent, OP_NAMES[op],
Chet Haasea1cff502012-02-21 13:43:44 -0800426 layer, x, y, paint);
Chet Haaseed30fd82011-04-22 16:18:45 -0700427 }
428 break;
429 case DrawBitmap: {
430 SkBitmap* bitmap = getBitmap();
431 float x = getFloat();
432 float y = getFloat();
Romain Guy5ff9df62012-01-23 17:09:05 -0800433 SkPaint* paint = getPaint(renderer);
Steve Block5baa3a62011-12-20 16:23:08 +0000434 ALOGD("%s%s %p, %.2f, %.2f, %p", (char*) indent, OP_NAMES[op],
Chet Haasea1cff502012-02-21 13:43:44 -0800435 bitmap, x, y, paint);
Chet Haaseed30fd82011-04-22 16:18:45 -0700436 }
437 break;
438 case DrawBitmapMatrix: {
439 SkBitmap* bitmap = getBitmap();
440 SkMatrix* matrix = getMatrix();
Romain Guy5ff9df62012-01-23 17:09:05 -0800441 SkPaint* paint = getPaint(renderer);
Steve Block5baa3a62011-12-20 16:23:08 +0000442 ALOGD("%s%s %p, %p, %p", (char*) indent, OP_NAMES[op],
Chet Haasea1cff502012-02-21 13:43:44 -0800443 bitmap, matrix, paint);
Chet Haaseed30fd82011-04-22 16:18:45 -0700444 }
445 break;
446 case DrawBitmapRect: {
447 SkBitmap* bitmap = getBitmap();
448 float f1 = getFloat();
449 float f2 = getFloat();
450 float f3 = getFloat();
451 float f4 = getFloat();
452 float f5 = getFloat();
453 float f6 = getFloat();
454 float f7 = getFloat();
455 float f8 = getFloat();
Romain Guy5ff9df62012-01-23 17:09:05 -0800456 SkPaint* paint = getPaint(renderer);
Steve Block5baa3a62011-12-20 16:23:08 +0000457 ALOGD("%s%s %p, %.2f, %.2f, %.2f, %.2f, %.2f, %.2f, %.2f, %.2f, %p",
Chet Haasea1cff502012-02-21 13:43:44 -0800458 (char*) indent, OP_NAMES[op], bitmap, f1, f2, f3, f4, f5, f6, f7, f8, paint);
Chet Haaseed30fd82011-04-22 16:18:45 -0700459 }
460 break;
Romain Guye651cc62012-05-14 19:44:40 -0700461 case DrawBitmapData: {
462 SkBitmap* bitmap = getBitmapData();
463 float x = getFloat();
464 float y = getFloat();
465 SkPaint* paint = getPaint(renderer);
466 ALOGD("%s%s %.2f, %.2f, %p", (char*) indent, OP_NAMES[op], x, y, paint);
467 }
468 break;
Chet Haaseed30fd82011-04-22 16:18:45 -0700469 case DrawBitmapMesh: {
470 int verticesCount = 0;
471 uint32_t colorsCount = 0;
472 SkBitmap* bitmap = getBitmap();
473 uint32_t meshWidth = getInt();
474 uint32_t meshHeight = getInt();
475 float* vertices = getFloats(verticesCount);
476 bool hasColors = getInt();
477 int* colors = hasColors ? getInts(colorsCount) : NULL;
Romain Guy5ff9df62012-01-23 17:09:05 -0800478 SkPaint* paint = getPaint(renderer);
Steve Block5baa3a62011-12-20 16:23:08 +0000479 ALOGD("%s%s", (char*) indent, OP_NAMES[op]);
Chet Haaseed30fd82011-04-22 16:18:45 -0700480 }
481 break;
482 case DrawPatch: {
483 int32_t* xDivs = NULL;
484 int32_t* yDivs = NULL;
485 uint32_t* colors = NULL;
486 uint32_t xDivsCount = 0;
487 uint32_t yDivsCount = 0;
488 int8_t numColors = 0;
489 SkBitmap* bitmap = getBitmap();
490 xDivs = getInts(xDivsCount);
491 yDivs = getInts(yDivsCount);
492 colors = getUInts(numColors);
Romain Guya62f1722011-10-19 17:06:19 -0700493 float left = getFloat();
494 float top = getFloat();
495 float right = getFloat();
496 float bottom = getFloat();
Romain Guybe6f9dc2012-07-16 12:41:17 -0700497 int alpha = getInt();
498 SkXfermode::Mode mode = (SkXfermode::Mode) getInt();
Steve Block5baa3a62011-12-20 16:23:08 +0000499 ALOGD("%s%s %.2f, %.2f, %.2f, %.2f", (char*) indent, OP_NAMES[op],
Romain Guya62f1722011-10-19 17:06:19 -0700500 left, top, right, bottom);
Chet Haaseed30fd82011-04-22 16:18:45 -0700501 }
502 break;
503 case DrawColor: {
504 int color = getInt();
505 int xferMode = getInt();
Steve Block5baa3a62011-12-20 16:23:08 +0000506 ALOGD("%s%s 0x%x %d", (char*) indent, OP_NAMES[op], color, xferMode);
Chet Haaseed30fd82011-04-22 16:18:45 -0700507 }
508 break;
509 case DrawRect: {
510 float f1 = getFloat();
511 float f2 = getFloat();
512 float f3 = getFloat();
513 float f4 = getFloat();
Romain Guy5ff9df62012-01-23 17:09:05 -0800514 SkPaint* paint = getPaint(renderer);
Steve Block5baa3a62011-12-20 16:23:08 +0000515 ALOGD("%s%s %.2f, %.2f, %.2f, %.2f, %p", (char*) indent, OP_NAMES[op],
Chet Haasea1cff502012-02-21 13:43:44 -0800516 f1, f2, f3, f4, paint);
Chet Haaseed30fd82011-04-22 16:18:45 -0700517 }
518 break;
519 case DrawRoundRect: {
520 float f1 = getFloat();
521 float f2 = getFloat();
522 float f3 = getFloat();
523 float f4 = getFloat();
524 float f5 = getFloat();
525 float f6 = getFloat();
Romain Guy5ff9df62012-01-23 17:09:05 -0800526 SkPaint* paint = getPaint(renderer);
Steve Block5baa3a62011-12-20 16:23:08 +0000527 ALOGD("%s%s %.2f, %.2f, %.2f, %.2f, %.2f, %.2f, %p",
Chet Haasea1cff502012-02-21 13:43:44 -0800528 (char*) indent, OP_NAMES[op], f1, f2, f3, f4, f5, f6, paint);
Chet Haaseed30fd82011-04-22 16:18:45 -0700529 }
530 break;
531 case DrawCircle: {
532 float f1 = getFloat();
533 float f2 = getFloat();
534 float f3 = getFloat();
Romain Guy5ff9df62012-01-23 17:09:05 -0800535 SkPaint* paint = getPaint(renderer);
Steve Block5baa3a62011-12-20 16:23:08 +0000536 ALOGD("%s%s %.2f, %.2f, %.2f, %p",
Chet Haasea1cff502012-02-21 13:43:44 -0800537 (char*) indent, OP_NAMES[op], f1, f2, f3, paint);
Chet Haaseed30fd82011-04-22 16:18:45 -0700538 }
539 break;
540 case DrawOval: {
541 float f1 = getFloat();
542 float f2 = getFloat();
543 float f3 = getFloat();
544 float f4 = getFloat();
Romain Guy5ff9df62012-01-23 17:09:05 -0800545 SkPaint* paint = getPaint(renderer);
Steve Block5baa3a62011-12-20 16:23:08 +0000546 ALOGD("%s%s %.2f, %.2f, %.2f, %.2f, %p",
Chet Haasea1cff502012-02-21 13:43:44 -0800547 (char*) indent, OP_NAMES[op], f1, f2, f3, f4, paint);
Chet Haaseed30fd82011-04-22 16:18:45 -0700548 }
549 break;
550 case DrawArc: {
551 float f1 = getFloat();
552 float f2 = getFloat();
553 float f3 = getFloat();
554 float f4 = getFloat();
555 float f5 = getFloat();
556 float f6 = getFloat();
557 int i1 = getInt();
Romain Guy5ff9df62012-01-23 17:09:05 -0800558 SkPaint* paint = getPaint(renderer);
Steve Block5baa3a62011-12-20 16:23:08 +0000559 ALOGD("%s%s %.2f, %.2f, %.2f, %.2f, %.2f, %.2f, %d, %p",
Chet Haasea1cff502012-02-21 13:43:44 -0800560 (char*) indent, OP_NAMES[op], f1, f2, f3, f4, f5, f6, i1, paint);
Chet Haaseed30fd82011-04-22 16:18:45 -0700561 }
562 break;
563 case DrawPath: {
564 SkPath* path = getPath();
Romain Guy5ff9df62012-01-23 17:09:05 -0800565 SkPaint* paint = getPaint(renderer);
Steve Block5baa3a62011-12-20 16:23:08 +0000566 ALOGD("%s%s %p, %p", (char*) indent, OP_NAMES[op], path, paint);
Chet Haaseed30fd82011-04-22 16:18:45 -0700567 }
568 break;
569 case DrawLines: {
570 int count = 0;
571 float* points = getFloats(count);
Romain Guy5ff9df62012-01-23 17:09:05 -0800572 SkPaint* paint = getPaint(renderer);
Steve Block5baa3a62011-12-20 16:23:08 +0000573 ALOGD("%s%s", (char*) indent, OP_NAMES[op]);
Chet Haaseed30fd82011-04-22 16:18:45 -0700574 }
575 break;
576 case DrawPoints: {
577 int count = 0;
578 float* points = getFloats(count);
Romain Guy5ff9df62012-01-23 17:09:05 -0800579 SkPaint* paint = getPaint(renderer);
Steve Block5baa3a62011-12-20 16:23:08 +0000580 ALOGD("%s%s", (char*) indent, OP_NAMES[op]);
Chet Haaseed30fd82011-04-22 16:18:45 -0700581 }
582 break;
Romain Guy325740f2012-02-24 16:48:34 -0800583 case DrawTextOnPath: {
584 getText(&text);
585 int32_t count = getInt();
586 SkPath* path = getPath();
587 float hOffset = getFloat();
588 float vOffset = getFloat();
589 SkPaint* paint = getPaint(renderer);
590 ALOGD("%s%s %s, %d, %d, %p", (char*) indent, OP_NAMES[op],
591 text.text(), text.length(), count, paint);
592 }
593 break;
Romain Guyeb9a5362012-01-17 17:39:26 -0800594 case DrawPosText: {
595 getText(&text);
596 int count = getInt();
597 int positionsCount = 0;
598 float* positions = getFloats(positionsCount);
Romain Guy5ff9df62012-01-23 17:09:05 -0800599 SkPaint* paint = getPaint(renderer);
Romain Guyeb9a5362012-01-17 17:39:26 -0800600 ALOGD("%s%s %s, %d, %d, %p", (char*) indent, OP_NAMES[op],
Chet Haasea1cff502012-02-21 13:43:44 -0800601 text.text(), text.length(), count, paint);
Romain Guyeb9a5362012-01-17 17:39:26 -0800602 }
Raph Levien996e57c2012-07-23 15:22:52 -0700603 break;
Romain Guyc2525952012-07-27 16:41:22 -0700604 case DrawText: {
Raph Levien996e57c2012-07-23 15:22:52 -0700605 getText(&text);
Romain Guy18edb812012-08-03 16:06:55 -0700606 int32_t count = getInt();
607 float x = getFloat();
608 float y = getFloat();
609 int32_t positionsCount = 0;
Raph Levien996e57c2012-07-23 15:22:52 -0700610 float* positions = getFloats(positionsCount);
611 SkPaint* paint = getPaint(renderer);
Romain Guy18edb812012-08-03 16:06:55 -0700612 float length = getFloat();
Raph Levien996e57c2012-07-23 15:22:52 -0700613 ALOGD("%s%s %s, %d, %d, %p", (char*) indent, OP_NAMES[op],
614 text.text(), text.length(), count, paint);
615 }
616 break;
Chet Haaseed30fd82011-04-22 16:18:45 -0700617 case ResetShader: {
Steve Block5baa3a62011-12-20 16:23:08 +0000618 ALOGD("%s%s", (char*) indent, OP_NAMES[op]);
Chet Haaseed30fd82011-04-22 16:18:45 -0700619 }
620 break;
621 case SetupShader: {
622 SkiaShader* shader = getShader();
Steve Block5baa3a62011-12-20 16:23:08 +0000623 ALOGD("%s%s %p", (char*) indent, OP_NAMES[op], shader);
Chet Haaseed30fd82011-04-22 16:18:45 -0700624 }
625 break;
626 case ResetColorFilter: {
Steve Block5baa3a62011-12-20 16:23:08 +0000627 ALOGD("%s%s", (char*) indent, OP_NAMES[op]);
Chet Haaseed30fd82011-04-22 16:18:45 -0700628 }
629 break;
630 case SetupColorFilter: {
631 SkiaColorFilter *colorFilter = getColorFilter();
Steve Block5baa3a62011-12-20 16:23:08 +0000632 ALOGD("%s%s %p", (char*) indent, OP_NAMES[op], colorFilter);
Chet Haaseed30fd82011-04-22 16:18:45 -0700633 }
634 break;
635 case ResetShadow: {
Steve Block5baa3a62011-12-20 16:23:08 +0000636 ALOGD("%s%s", (char*) indent, OP_NAMES[op]);
Chet Haaseed30fd82011-04-22 16:18:45 -0700637 }
638 break;
639 case SetupShadow: {
640 float radius = getFloat();
641 float dx = getFloat();
642 float dy = getFloat();
643 int color = getInt();
Steve Block5baa3a62011-12-20 16:23:08 +0000644 ALOGD("%s%s %.2f, %.2f, %.2f, 0x%x", (char*) indent, OP_NAMES[op],
Chet Haasea1cff502012-02-21 13:43:44 -0800645 radius, dx, dy, color);
Chet Haaseed30fd82011-04-22 16:18:45 -0700646 }
647 break;
Romain Guy5ff9df62012-01-23 17:09:05 -0800648 case ResetPaintFilter: {
649 ALOGD("%s%s", (char*) indent, OP_NAMES[op]);
650 }
651 break;
652 case SetupPaintFilter: {
653 int clearBits = getInt();
654 int setBits = getInt();
655 ALOGD("%s%s 0x%x, 0x%x", (char*) indent, OP_NAMES[op], clearBits, setBits);
656 }
657 break;
Chet Haaseed30fd82011-04-22 16:18:45 -0700658 default:
Steve Block5baa3a62011-12-20 16:23:08 +0000659 ALOGD("Display List error: op not handled: %s%s",
Chet Haasea1cff502012-02-21 13:43:44 -0800660 (char*) indent, OP_NAMES[op]);
Chet Haaseed30fd82011-04-22 16:18:45 -0700661 break;
662 }
663 }
Chet Haasea1cff502012-02-21 13:43:44 -0800664 ALOGD("%sDone (%p, %s)", (char*) indent + 2, this, mName.string());
Chet Haaseed30fd82011-04-22 16:18:45 -0700665}
666
Chet Haasea1cff502012-02-21 13:43:44 -0800667void DisplayList::updateMatrix() {
668 if (mMatrixDirty) {
669 if (!mTransformMatrix) {
670 mTransformMatrix = new SkMatrix();
671 }
672 if (mMatrixFlags == 0 || mMatrixFlags == TRANSLATION) {
673 mTransformMatrix->reset();
674 } else {
675 if (!mPivotExplicitlySet) {
676 if (mWidth != mPrevWidth || mHeight != mPrevHeight) {
677 mPrevWidth = mWidth;
678 mPrevHeight = mHeight;
679 mPivotX = mPrevWidth / 2;
680 mPivotY = mPrevHeight / 2;
681 }
682 }
683 if ((mMatrixFlags & ROTATION_3D) == 0) {
684 mTransformMatrix->setTranslate(mTranslationX, mTranslationY);
685 mTransformMatrix->preRotate(mRotation, mPivotX, mPivotY);
686 mTransformMatrix->preScale(mScaleX, mScaleY, mPivotX, mPivotY);
687 } else {
688 if (!mTransformCamera) {
689 mTransformCamera = new Sk3DView();
690 mTransformMatrix3D = new SkMatrix();
691 }
692 mTransformMatrix->reset();
693 mTransformCamera->save();
694 mTransformMatrix->preScale(mScaleX, mScaleY, mPivotX, mPivotY);
695 mTransformCamera->rotateX(mRotationX);
696 mTransformCamera->rotateY(mRotationY);
697 mTransformCamera->rotateZ(-mRotation);
698 mTransformCamera->getMatrix(mTransformMatrix3D);
699 mTransformMatrix3D->preTranslate(-mPivotX, -mPivotY);
700 mTransformMatrix3D->postTranslate(mPivotX + mTranslationX,
701 mPivotY + mTranslationY);
702 mTransformMatrix->postConcat(*mTransformMatrix3D);
703 mTransformCamera->restore();
704 }
705 }
706 mMatrixDirty = false;
707 }
708}
709
710void DisplayList::outputViewProperties(OpenGLRenderer& renderer, char* indent) {
Chet Haase1271e2c2012-04-20 09:54:27 -0700711 updateMatrix();
712 if (mLeft != 0 || mTop != 0) {
713 ALOGD("%s%s %d, %d", indent, "Translate (left, top)", mLeft, mTop);
714 }
715 if (mStaticMatrix) {
716 ALOGD("%s%s %p: [%.2f, %.2f, %.2f] [%.2f, %.2f, %.2f] [%.2f, %.2f, %.2f]",
717 indent, "ConcatMatrix (static)", mStaticMatrix,
718 mStaticMatrix->get(0), mStaticMatrix->get(1),
719 mStaticMatrix->get(2), mStaticMatrix->get(3),
720 mStaticMatrix->get(4), mStaticMatrix->get(5),
721 mStaticMatrix->get(6), mStaticMatrix->get(7),
722 mStaticMatrix->get(8));
723 }
724 if (mAnimationMatrix) {
725 ALOGD("%s%s %p: [%.2f, %.2f, %.2f] [%.2f, %.2f, %.2f] [%.2f, %.2f, %.2f]",
726 indent, "ConcatMatrix (animation)", mAnimationMatrix,
727 mAnimationMatrix->get(0), mAnimationMatrix->get(1),
728 mAnimationMatrix->get(2), mAnimationMatrix->get(3),
729 mAnimationMatrix->get(4), mAnimationMatrix->get(5),
730 mAnimationMatrix->get(6), mAnimationMatrix->get(7),
731 mAnimationMatrix->get(8));
732 }
733 if (mMatrixFlags != 0) {
734 if (mMatrixFlags == TRANSLATION) {
735 ALOGD("%s%s %f, %f", indent, "Translate", mTranslationX, mTranslationY);
736 } else {
Chet Haase9420abd2012-03-29 16:28:32 -0700737 ALOGD("%s%s %p: [%.2f, %.2f, %.2f] [%.2f, %.2f, %.2f] [%.2f, %.2f, %.2f]",
Chet Haase1271e2c2012-04-20 09:54:27 -0700738 indent, "ConcatMatrix", mTransformMatrix,
739 mTransformMatrix->get(0), mTransformMatrix->get(1),
740 mTransformMatrix->get(2), mTransformMatrix->get(3),
741 mTransformMatrix->get(4), mTransformMatrix->get(5),
742 mTransformMatrix->get(6), mTransformMatrix->get(7),
743 mTransformMatrix->get(8));
Chet Haase9420abd2012-03-29 16:28:32 -0700744 }
Chet Haase1271e2c2012-04-20 09:54:27 -0700745 }
746 if (mAlpha < 1 && !mCaching) {
747 // TODO: should be able to store the size of a DL at record time and not
748 // have to pass it into this call. In fact, this information might be in the
749 // location/size info that we store with the new native transform data.
750 int flags = SkCanvas::kHasAlphaLayer_SaveFlag;
Chet Haasea1cff502012-02-21 13:43:44 -0800751 if (mClipChildren) {
Chet Haase1271e2c2012-04-20 09:54:27 -0700752 flags |= SkCanvas::kClipToLayer_SaveFlag;
Chet Haasea1cff502012-02-21 13:43:44 -0800753 }
Chet Haase1271e2c2012-04-20 09:54:27 -0700754 ALOGD("%s%s %.2f, %.2f, %.2f, %.2f, %d, 0x%x", indent, "SaveLayerAlpha",
755 (float) 0, (float) 0, (float) mRight - mLeft, (float) mBottom - mTop,
756 mMultipliedAlpha, flags);
757 }
758 if (mClipChildren) {
759 ALOGD("%s%s %.2f, %.2f, %.2f, %.2f", indent, "ClipRect", 0.0f, 0.0f,
760 (float) mRight - mLeft, (float) mBottom - mTop);
Chet Haasea1cff502012-02-21 13:43:44 -0800761 }
762}
763
Chet Haase1271e2c2012-04-20 09:54:27 -0700764void DisplayList::setViewProperties(OpenGLRenderer& renderer, uint32_t level) {
Chet Haasea1cff502012-02-21 13:43:44 -0800765#if DEBUG_DISPLAY_LIST
766 uint32_t count = (level + 1) * 2;
767 char indent[count + 1];
768 for (uint32_t i = 0; i < count; i++) {
769 indent[i] = ' ';
770 }
771 indent[count] = '\0';
772#endif
Chet Haase1271e2c2012-04-20 09:54:27 -0700773 updateMatrix();
774 if (mLeft != 0 || mTop != 0) {
775 DISPLAY_LIST_LOGD("%s%s %d, %d", indent, "Translate (left, top)", mLeft, mTop);
776 renderer.translate(mLeft, mTop);
777 }
778 if (mStaticMatrix) {
779 DISPLAY_LIST_LOGD(
780 "%s%s %p: [%.2f, %.2f, %.2f] [%.2f, %.2f, %.2f] [%.2f, %.2f, %.2f]",
781 indent, "ConcatMatrix (static)", mStaticMatrix,
782 mStaticMatrix->get(0), mStaticMatrix->get(1),
783 mStaticMatrix->get(2), mStaticMatrix->get(3),
784 mStaticMatrix->get(4), mStaticMatrix->get(5),
785 mStaticMatrix->get(6), mStaticMatrix->get(7),
786 mStaticMatrix->get(8));
787 renderer.concatMatrix(mStaticMatrix);
788 } else if (mAnimationMatrix) {
789 DISPLAY_LIST_LOGD(
790 "%s%s %p: [%.2f, %.2f, %.2f] [%.2f, %.2f, %.2f] [%.2f, %.2f, %.2f]",
791 indent, "ConcatMatrix (animation)", mAnimationMatrix,
792 mAnimationMatrix->get(0), mAnimationMatrix->get(1),
793 mAnimationMatrix->get(2), mAnimationMatrix->get(3),
794 mAnimationMatrix->get(4), mAnimationMatrix->get(5),
795 mAnimationMatrix->get(6), mAnimationMatrix->get(7),
796 mAnimationMatrix->get(8));
797 renderer.concatMatrix(mAnimationMatrix);
798 }
799 if (mMatrixFlags != 0) {
800 if (mMatrixFlags == TRANSLATION) {
801 DISPLAY_LIST_LOGD("%s%s %f, %f", indent, "Translate", mTranslationX, mTranslationY);
802 renderer.translate(mTranslationX, mTranslationY);
803 } else {
Chet Haase9420abd2012-03-29 16:28:32 -0700804 DISPLAY_LIST_LOGD(
805 "%s%s %p: [%.2f, %.2f, %.2f] [%.2f, %.2f, %.2f] [%.2f, %.2f, %.2f]",
Chet Haase1271e2c2012-04-20 09:54:27 -0700806 indent, "ConcatMatrix", mTransformMatrix,
807 mTransformMatrix->get(0), mTransformMatrix->get(1),
808 mTransformMatrix->get(2), mTransformMatrix->get(3),
809 mTransformMatrix->get(4), mTransformMatrix->get(5),
810 mTransformMatrix->get(6), mTransformMatrix->get(7),
811 mTransformMatrix->get(8));
812 renderer.concatMatrix(mTransformMatrix);
Chet Haasea1cff502012-02-21 13:43:44 -0800813 }
Chet Haase1271e2c2012-04-20 09:54:27 -0700814 }
815 if (mAlpha < 1 && !mCaching) {
816 if (!mHasOverlappingRendering) {
817 DISPLAY_LIST_LOGD("%s%s %.2f", indent, "SetAlpha", mAlpha);
818 renderer.setAlpha(mAlpha);
819 } else {
820 // TODO: should be able to store the size of a DL at record time and not
821 // have to pass it into this call. In fact, this information might be in the
822 // location/size info that we store with the new native transform data.
823 int flags = SkCanvas::kHasAlphaLayer_SaveFlag;
824 if (mClipChildren) {
825 flags |= SkCanvas::kClipToLayer_SaveFlag;
Chet Haasea1cff502012-02-21 13:43:44 -0800826 }
Chet Haase1271e2c2012-04-20 09:54:27 -0700827 DISPLAY_LIST_LOGD("%s%s %.2f, %.2f, %.2f, %.2f, %d, 0x%x", indent, "SaveLayerAlpha",
828 (float) 0, (float) 0, (float) mRight - mLeft, (float) mBottom - mTop,
829 mMultipliedAlpha, flags);
830 renderer.saveLayerAlpha(0, 0, mRight - mLeft, mBottom - mTop,
831 mMultipliedAlpha, flags);
Chet Haasea1cff502012-02-21 13:43:44 -0800832 }
Chet Haase1271e2c2012-04-20 09:54:27 -0700833 }
834 if (mClipChildren) {
835 DISPLAY_LIST_LOGD("%s%s %.2f, %.2f, %.2f, %.2f", indent, "ClipRect", 0.0f, 0.0f,
836 (float) mRight - mLeft, (float) mBottom - mTop);
837 renderer.clipRect(0, 0, mRight - mLeft, mBottom - mTop,
838 SkRegion::kIntersect_Op);
Chet Haasea1cff502012-02-21 13:43:44 -0800839 }
840}
841
Chet Haaseed30fd82011-04-22 16:18:45 -0700842/**
843 * Changes to replay(), specifically those involving opcode or parameter changes, should be mimicked
844 * in the output() function, since that function processes the same list of opcodes for the
845 * purposes of logging display list info for a given view.
846 */
Chet Haase1271e2c2012-04-20 09:54:27 -0700847status_t DisplayList::replay(OpenGLRenderer& renderer, Rect& dirty, int32_t flags, uint32_t level) {
Chet Haase48659092012-05-31 15:21:51 -0700848 status_t drawGlStatus = DrawGlInfo::kStatusDone;
Romain Guyb051e892010-09-28 19:09:36 -0700849 TextContainer text;
850 mReader.rewind();
851
Romain Guyffac7fc2011-01-13 17:21:49 -0800852#if DEBUG_DISPLAY_LIST
853 uint32_t count = (level + 1) * 2;
854 char indent[count + 1];
855 for (uint32_t i = 0; i < count; i++) {
856 indent[i] = ' ';
857 }
858 indent[count] = '\0';
Chet Haasea23eed82012-04-12 15:19:04 -0700859 Rect* clipRect = renderer.getClipRect();
860 DISPLAY_LIST_LOGD("%sStart display list (%p, %s), clipRect: %.0f, %.f, %.0f, %.0f",
861 (char*) indent + 2, this, mName.string(), clipRect->left, clipRect->top,
862 clipRect->right, clipRect->bottom);
Romain Guyffac7fc2011-01-13 17:21:49 -0800863#endif
Romain Guyb051e892010-09-28 19:09:36 -0700864
Romain Guy13631f32012-01-30 17:41:55 -0800865 renderer.startMark(mName.string());
Romain Guy8a4ac612012-07-17 17:32:48 -0700866
Chet Haase1271e2c2012-04-20 09:54:27 -0700867 int restoreTo = renderer.save(SkCanvas::kMatrix_SaveFlag | SkCanvas::kClip_SaveFlag);
868 DISPLAY_LIST_LOGD("%s%s %d %d", indent, "Save",
869 SkCanvas::kMatrix_SaveFlag | SkCanvas::kClip_SaveFlag, restoreTo);
870 setViewProperties(renderer, level);
Romain Guy8a4ac612012-07-17 17:32:48 -0700871
872 if (renderer.quickRejectNoScissor(0, 0, mWidth, mHeight)) {
Chet Haaseb85967b2012-03-26 14:37:51 -0700873 DISPLAY_LIST_LOGD("%s%s %d", (char*) indent, "RestoreToCount", restoreTo);
874 renderer.restoreToCount(restoreTo);
875 renderer.endMark();
Chet Haase48659092012-05-31 15:21:51 -0700876 return drawGlStatus;
Chet Haaseb85967b2012-03-26 14:37:51 -0700877 }
Romain Guy13631f32012-01-30 17:41:55 -0800878
Chet Haase9c1e23b2011-03-24 10:51:31 -0700879 DisplayListLogBuffer& logBuffer = DisplayListLogBuffer::getInstance();
Romain Guyffac7fc2011-01-13 17:21:49 -0800880 int saveCount = renderer.getSaveCount() - 1;
Romain Guy8a4ac612012-07-17 17:32:48 -0700881
Romain Guyb051e892010-09-28 19:09:36 -0700882 while (!mReader.eof()) {
Romain Guy5b3b3522010-10-27 18:57:51 -0700883 int op = mReader.readInt();
Romain Guy33f6beb2012-02-16 19:24:51 -0800884 if (op & OP_MAY_BE_SKIPPED_MASK) {
Romain Guy390f8822012-03-13 18:00:10 -0700885 int32_t skip = mReader.readInt();
Romain Guy33f6beb2012-02-16 19:24:51 -0800886 if (CC_LIKELY(flags & kReplayFlag_ClipChildren)) {
887 mReader.skip(skip);
888 DISPLAY_LIST_LOGD("%s%s skipping %d bytes", (char*) indent,
889 OP_NAMES[op & ~OP_MAY_BE_SKIPPED_MASK], skip);
890 continue;
891 } else {
892 op &= ~OP_MAY_BE_SKIPPED_MASK;
Romain Guy33f6beb2012-02-16 19:24:51 -0800893 }
894 }
Chet Haase9c1e23b2011-03-24 10:51:31 -0700895 logBuffer.writeCommand(level, op);
Romain Guyffac7fc2011-01-13 17:21:49 -0800896
Romain Guy8a4ac612012-07-17 17:32:48 -0700897#if DEBUG_DISPLAY_LIST_OPS_AS_EVENTS
898 Caches::getInstance().eventMark(strlen(OP_NAMES[op]), OP_NAMES[op]);
899#endif
900
Romain Guy5b3b3522010-10-27 18:57:51 -0700901 switch (op) {
Chet Haasedaf98e92011-01-10 14:10:36 -0800902 case DrawGLFunction: {
903 Functor *functor = (Functor *) getInt();
904 DISPLAY_LIST_LOGD("%s%s %p", (char*) indent, OP_NAMES[op], functor);
Romain Guy13631f32012-01-30 17:41:55 -0800905 renderer.startMark("GL functor");
Romain Guy65549432012-03-26 16:45:05 -0700906 drawGlStatus |= renderer.callDrawGLFunction(functor, dirty);
Romain Guy13631f32012-01-30 17:41:55 -0800907 renderer.endMark();
Chet Haasedaf98e92011-01-10 14:10:36 -0800908 }
909 break;
Romain Guyb051e892010-09-28 19:09:36 -0700910 case Save: {
Romain Guy33f6beb2012-02-16 19:24:51 -0800911 int32_t rendererNum = getInt();
Chet Haasedaf98e92011-01-10 14:10:36 -0800912 DISPLAY_LIST_LOGD("%s%s %d", (char*) indent, OP_NAMES[op], rendererNum);
913 renderer.save(rendererNum);
Romain Guyb051e892010-09-28 19:09:36 -0700914 }
915 break;
916 case Restore: {
Chet Haasedaf98e92011-01-10 14:10:36 -0800917 DISPLAY_LIST_LOGD("%s%s", (char*) indent, OP_NAMES[op]);
Romain Guyb051e892010-09-28 19:09:36 -0700918 renderer.restore();
919 }
920 break;
921 case RestoreToCount: {
Romain Guy33f6beb2012-02-16 19:24:51 -0800922 int32_t restoreCount = saveCount + getInt();
Chet Haasedaf98e92011-01-10 14:10:36 -0800923 DISPLAY_LIST_LOGD("%s%s %d", (char*) indent, OP_NAMES[op], restoreCount);
924 renderer.restoreToCount(restoreCount);
Romain Guyb051e892010-09-28 19:09:36 -0700925 }
926 break;
927 case SaveLayer: {
Chet Haasedaf98e92011-01-10 14:10:36 -0800928 float f1 = getFloat();
929 float f2 = getFloat();
930 float f3 = getFloat();
931 float f4 = getFloat();
Romain Guy5ff9df62012-01-23 17:09:05 -0800932 SkPaint* paint = getPaint(renderer);
Romain Guy33f6beb2012-02-16 19:24:51 -0800933 int32_t flags = getInt();
Chet Haasedaf98e92011-01-10 14:10:36 -0800934 DISPLAY_LIST_LOGD("%s%s %.2f, %.2f, %.2f, %.2f, %p, 0x%x", (char*) indent,
Chet Haasea1cff502012-02-21 13:43:44 -0800935 OP_NAMES[op], f1, f2, f3, f4, paint, flags);
Chet Haasedaf98e92011-01-10 14:10:36 -0800936 renderer.saveLayer(f1, f2, f3, f4, paint, flags);
Romain Guyb051e892010-09-28 19:09:36 -0700937 }
938 break;
Romain Guy5b3b3522010-10-27 18:57:51 -0700939 case SaveLayerAlpha: {
Chet Haasedaf98e92011-01-10 14:10:36 -0800940 float f1 = getFloat();
941 float f2 = getFloat();
942 float f3 = getFloat();
943 float f4 = getFloat();
Romain Guy33f6beb2012-02-16 19:24:51 -0800944 int32_t alpha = getInt();
945 int32_t flags = getInt();
Chet Haasedaf98e92011-01-10 14:10:36 -0800946 DISPLAY_LIST_LOGD("%s%s %.2f, %.2f, %.2f, %.2f, %d, 0x%x", (char*) indent,
Chet Haasea1cff502012-02-21 13:43:44 -0800947 OP_NAMES[op], f1, f2, f3, f4, alpha, flags);
Chet Haasedaf98e92011-01-10 14:10:36 -0800948 renderer.saveLayerAlpha(f1, f2, f3, f4, alpha, flags);
Romain Guy5b3b3522010-10-27 18:57:51 -0700949 }
950 break;
Romain Guyb051e892010-09-28 19:09:36 -0700951 case Translate: {
Chet Haasedaf98e92011-01-10 14:10:36 -0800952 float f1 = getFloat();
953 float f2 = getFloat();
954 DISPLAY_LIST_LOGD("%s%s %.2f, %.2f", (char*) indent, OP_NAMES[op], f1, f2);
955 renderer.translate(f1, f2);
Romain Guyb051e892010-09-28 19:09:36 -0700956 }
957 break;
958 case Rotate: {
Chet Haasedaf98e92011-01-10 14:10:36 -0800959 float rotation = getFloat();
960 DISPLAY_LIST_LOGD("%s%s %.2f", (char*) indent, OP_NAMES[op], rotation);
961 renderer.rotate(rotation);
Romain Guyb051e892010-09-28 19:09:36 -0700962 }
963 break;
964 case Scale: {
Chet Haasedaf98e92011-01-10 14:10:36 -0800965 float sx = getFloat();
966 float sy = getFloat();
967 DISPLAY_LIST_LOGD("%s%s %.2f, %.2f", (char*) indent, OP_NAMES[op], sx, sy);
968 renderer.scale(sx, sy);
Romain Guyb051e892010-09-28 19:09:36 -0700969 }
970 break;
Romain Guy807daf72011-01-18 11:19:19 -0800971 case Skew: {
Chet Haasedaf98e92011-01-10 14:10:36 -0800972 float sx = getFloat();
973 float sy = getFloat();
974 DISPLAY_LIST_LOGD("%s%s %.2f, %.2f", (char*) indent, OP_NAMES[op], sx, sy);
975 renderer.skew(sx, sy);
Romain Guy807daf72011-01-18 11:19:19 -0800976 }
977 break;
Romain Guyb051e892010-09-28 19:09:36 -0700978 case SetMatrix: {
Chet Haasedaf98e92011-01-10 14:10:36 -0800979 SkMatrix* matrix = getMatrix();
980 DISPLAY_LIST_LOGD("%s%s %p", (char*) indent, OP_NAMES[op], matrix);
981 renderer.setMatrix(matrix);
Romain Guyb051e892010-09-28 19:09:36 -0700982 }
983 break;
984 case ConcatMatrix: {
Chet Haasedaf98e92011-01-10 14:10:36 -0800985 SkMatrix* matrix = getMatrix();
Chet Haasea1cff502012-02-21 13:43:44 -0800986 DISPLAY_LIST_LOGD(
987 "%s%s %p: [%.2f, %.2f, %.2f] [%.2f, %.2f, %.2f] [%.2f, %.2f, %.2f]",
988 (char*) indent, OP_NAMES[op], matrix,
989 matrix->get(0), matrix->get(1), matrix->get(2),
990 matrix->get(3), matrix->get(4), matrix->get(5),
991 matrix->get(6), matrix->get(7), matrix->get(8));
Chet Haasedaf98e92011-01-10 14:10:36 -0800992 renderer.concatMatrix(matrix);
Romain Guyb051e892010-09-28 19:09:36 -0700993 }
994 break;
995 case ClipRect: {
Chet Haasedaf98e92011-01-10 14:10:36 -0800996 float f1 = getFloat();
997 float f2 = getFloat();
998 float f3 = getFloat();
999 float f4 = getFloat();
Romain Guy33f6beb2012-02-16 19:24:51 -08001000 int32_t regionOp = getInt();
Chet Haasedaf98e92011-01-10 14:10:36 -08001001 DISPLAY_LIST_LOGD("%s%s %.2f, %.2f, %.2f, %.2f, %d", (char*) indent, OP_NAMES[op],
Chet Haasea1cff502012-02-21 13:43:44 -08001002 f1, f2, f3, f4, regionOp);
Chet Haasedaf98e92011-01-10 14:10:36 -08001003 renderer.clipRect(f1, f2, f3, f4, (SkRegion::Op) regionOp);
Romain Guyb051e892010-09-28 19:09:36 -07001004 }
1005 break;
Romain Guy0fe478e2010-11-08 12:08:41 -08001006 case DrawDisplayList: {
Chet Haasedaf98e92011-01-10 14:10:36 -08001007 DisplayList* displayList = getDisplayList();
Romain Guy33f6beb2012-02-16 19:24:51 -08001008 int32_t flags = getInt();
1009 DISPLAY_LIST_LOGD("%s%s %p, %dx%d, 0x%x %d", (char*) indent, OP_NAMES[op],
Chet Haase1271e2c2012-04-20 09:54:27 -07001010 displayList, mWidth, mHeight, flags, level + 1);
1011 drawGlStatus |= renderer.drawDisplayList(displayList, dirty, flags, level + 1);
Romain Guy0fe478e2010-11-08 12:08:41 -08001012 }
1013 break;
Romain Guy6c319ca2011-01-11 14:29:25 -08001014 case DrawLayer: {
Chet Haased15ebf22012-09-05 11:40:29 -07001015 int oldAlpha = -1;
Chet Haasedaf98e92011-01-10 14:10:36 -08001016 Layer* layer = (Layer*) getInt();
1017 float x = getFloat();
1018 float y = getFloat();
Romain Guy5ff9df62012-01-23 17:09:05 -08001019 SkPaint* paint = getPaint(renderer);
Chet Haased15ebf22012-09-05 11:40:29 -07001020 if (mCaching && mMultipliedAlpha < 255) {
1021 oldAlpha = layer->getAlpha();
1022 layer->setAlpha(mMultipliedAlpha);
Chet Haasea1cff502012-02-21 13:43:44 -08001023 }
Chet Haasedaf98e92011-01-10 14:10:36 -08001024 DISPLAY_LIST_LOGD("%s%s %p, %.2f, %.2f, %p", (char*) indent, OP_NAMES[op],
Chet Haasea1cff502012-02-21 13:43:44 -08001025 layer, x, y, paint);
Chet Haase48659092012-05-31 15:21:51 -07001026 drawGlStatus |= renderer.drawLayer(layer, x, y, paint);
Chet Haased15ebf22012-09-05 11:40:29 -07001027 if (oldAlpha >= 0) {
1028 layer->setAlpha(oldAlpha);
1029 }
Romain Guy6c319ca2011-01-11 14:29:25 -08001030 }
1031 break;
Romain Guyb051e892010-09-28 19:09:36 -07001032 case DrawBitmap: {
Chet Haased15ebf22012-09-05 11:40:29 -07001033 int oldAlpha = -1;
Chet Haasedaf98e92011-01-10 14:10:36 -08001034 SkBitmap* bitmap = getBitmap();
1035 float x = getFloat();
1036 float y = getFloat();
Romain Guy5ff9df62012-01-23 17:09:05 -08001037 SkPaint* paint = getPaint(renderer);
Chet Haased15ebf22012-09-05 11:40:29 -07001038 if (mCaching && mMultipliedAlpha < 255) {
1039 oldAlpha = paint->getAlpha();
Chet Haaseb85967b2012-03-26 14:37:51 -07001040 paint->setAlpha(mMultipliedAlpha);
1041 }
Chet Haasedaf98e92011-01-10 14:10:36 -08001042 DISPLAY_LIST_LOGD("%s%s %p, %.2f, %.2f, %p", (char*) indent, OP_NAMES[op],
Chet Haasea1cff502012-02-21 13:43:44 -08001043 bitmap, x, y, paint);
Chet Haase48659092012-05-31 15:21:51 -07001044 drawGlStatus |= renderer.drawBitmap(bitmap, x, y, paint);
Chet Haased15ebf22012-09-05 11:40:29 -07001045 if (oldAlpha >= 0) {
1046 paint->setAlpha(oldAlpha);
1047 }
Romain Guyb051e892010-09-28 19:09:36 -07001048 }
1049 break;
1050 case DrawBitmapMatrix: {
Chet Haasedaf98e92011-01-10 14:10:36 -08001051 SkBitmap* bitmap = getBitmap();
1052 SkMatrix* matrix = getMatrix();
Romain Guy5ff9df62012-01-23 17:09:05 -08001053 SkPaint* paint = getPaint(renderer);
Chet Haasedaf98e92011-01-10 14:10:36 -08001054 DISPLAY_LIST_LOGD("%s%s %p, %p, %p", (char*) indent, OP_NAMES[op],
Chet Haasea1cff502012-02-21 13:43:44 -08001055 bitmap, matrix, paint);
Chet Haase48659092012-05-31 15:21:51 -07001056 drawGlStatus |= renderer.drawBitmap(bitmap, matrix, paint);
Romain Guyb051e892010-09-28 19:09:36 -07001057 }
1058 break;
1059 case DrawBitmapRect: {
Chet Haasedaf98e92011-01-10 14:10:36 -08001060 SkBitmap* bitmap = getBitmap();
1061 float f1 = getFloat();
1062 float f2 = getFloat();
1063 float f3 = getFloat();
1064 float f4 = getFloat();
1065 float f5 = getFloat();
1066 float f6 = getFloat();
1067 float f7 = getFloat();
1068 float f8 = getFloat();
Romain Guy5ff9df62012-01-23 17:09:05 -08001069 SkPaint* paint = getPaint(renderer);
Chet Haasedaf98e92011-01-10 14:10:36 -08001070 DISPLAY_LIST_LOGD("%s%s %p, %.2f, %.2f, %.2f, %.2f, %.2f, %.2f, %.2f, %.2f, %p",
Chet Haasea1cff502012-02-21 13:43:44 -08001071 (char*) indent, OP_NAMES[op], bitmap,
1072 f1, f2, f3, f4, f5, f6, f7, f8,paint);
Chet Haase48659092012-05-31 15:21:51 -07001073 drawGlStatus |= renderer.drawBitmap(bitmap, f1, f2, f3, f4, f5, f6, f7, f8, paint);
Romain Guyb051e892010-09-28 19:09:36 -07001074 }
1075 break;
Romain Guye651cc62012-05-14 19:44:40 -07001076 case DrawBitmapData: {
1077 SkBitmap* bitmap = getBitmapData();
1078 float x = getFloat();
1079 float y = getFloat();
1080 SkPaint* paint = getPaint(renderer);
1081 DISPLAY_LIST_LOGD("%s%s %p, %.2f, %.2f, %p", (char*) indent, OP_NAMES[op],
1082 bitmap, x, y, paint);
Chet Haase48659092012-05-31 15:21:51 -07001083 drawGlStatus |= renderer.drawBitmap(bitmap, x, y, paint);
Romain Guye651cc62012-05-14 19:44:40 -07001084 }
1085 break;
Romain Guy5a7b4662011-01-20 19:09:30 -08001086 case DrawBitmapMesh: {
Romain Guy33f6beb2012-02-16 19:24:51 -08001087 int32_t verticesCount = 0;
Romain Guy5a7b4662011-01-20 19:09:30 -08001088 uint32_t colorsCount = 0;
1089
1090 SkBitmap* bitmap = getBitmap();
1091 uint32_t meshWidth = getInt();
1092 uint32_t meshHeight = getInt();
1093 float* vertices = getFloats(verticesCount);
1094 bool hasColors = getInt();
Romain Guy33f6beb2012-02-16 19:24:51 -08001095 int32_t* colors = hasColors ? getInts(colorsCount) : NULL;
Romain Guy5ff9df62012-01-23 17:09:05 -08001096 SkPaint* paint = getPaint(renderer);
Romain Guy5a7b4662011-01-20 19:09:30 -08001097
Chet Haasedaf98e92011-01-10 14:10:36 -08001098 DISPLAY_LIST_LOGD("%s%s", (char*) indent, OP_NAMES[op]);
Chet Haase48659092012-05-31 15:21:51 -07001099 drawGlStatus |= renderer.drawBitmapMesh(bitmap, meshWidth, meshHeight, vertices,
1100 colors, paint);
Romain Guy5a7b4662011-01-20 19:09:30 -08001101 }
Romain Guya566b7c2011-01-23 16:36:11 -08001102 break;
Romain Guyb051e892010-09-28 19:09:36 -07001103 case DrawPatch: {
1104 int32_t* xDivs = NULL;
1105 int32_t* yDivs = NULL;
Romain Guy4bb94202010-10-12 15:59:26 -07001106 uint32_t* colors = NULL;
Romain Guyb051e892010-09-28 19:09:36 -07001107 uint32_t xDivsCount = 0;
1108 uint32_t yDivsCount = 0;
Romain Guy4bb94202010-10-12 15:59:26 -07001109 int8_t numColors = 0;
Romain Guyb051e892010-09-28 19:09:36 -07001110
1111 SkBitmap* bitmap = getBitmap();
1112
1113 xDivs = getInts(xDivsCount);
1114 yDivs = getInts(yDivsCount);
Romain Guy4bb94202010-10-12 15:59:26 -07001115 colors = getUInts(numColors);
Romain Guyb051e892010-09-28 19:09:36 -07001116
Romain Guy9ff3cb52011-06-28 14:02:11 -07001117 float left = getFloat();
1118 float top = getFloat();
1119 float right = getFloat();
1120 float bottom = getFloat();
Romain Guybe6f9dc2012-07-16 12:41:17 -07001121
1122 int alpha = getInt();
1123 SkXfermode::Mode mode = (SkXfermode::Mode) getInt();
Romain Guy9ff3cb52011-06-28 14:02:11 -07001124
Chet Haasedaf98e92011-01-10 14:10:36 -08001125 DISPLAY_LIST_LOGD("%s%s", (char*) indent, OP_NAMES[op]);
Chet Haase48659092012-05-31 15:21:51 -07001126 drawGlStatus |= renderer.drawPatch(bitmap, xDivs, yDivs, colors,
Romain Guybe6f9dc2012-07-16 12:41:17 -07001127 xDivsCount, yDivsCount, numColors, left, top, right, bottom,
1128 alpha, mode);
Romain Guyb051e892010-09-28 19:09:36 -07001129 }
1130 break;
1131 case DrawColor: {
Romain Guy33f6beb2012-02-16 19:24:51 -08001132 int32_t color = getInt();
1133 int32_t xferMode = getInt();
Chet Haasedaf98e92011-01-10 14:10:36 -08001134 DISPLAY_LIST_LOGD("%s%s 0x%x %d", (char*) indent, OP_NAMES[op], color, xferMode);
Chet Haase48659092012-05-31 15:21:51 -07001135 drawGlStatus |= renderer.drawColor(color, (SkXfermode::Mode) xferMode);
Romain Guyb051e892010-09-28 19:09:36 -07001136 }
1137 break;
1138 case DrawRect: {
Chet Haasedaf98e92011-01-10 14:10:36 -08001139 float f1 = getFloat();
1140 float f2 = getFloat();
1141 float f3 = getFloat();
1142 float f4 = getFloat();
Romain Guy5ff9df62012-01-23 17:09:05 -08001143 SkPaint* paint = getPaint(renderer);
Chet Haasedaf98e92011-01-10 14:10:36 -08001144 DISPLAY_LIST_LOGD("%s%s %.2f, %.2f, %.2f, %.2f, %p", (char*) indent, OP_NAMES[op],
Chet Haasea1cff502012-02-21 13:43:44 -08001145 f1, f2, f3, f4, paint);
Chet Haase48659092012-05-31 15:21:51 -07001146 drawGlStatus |= renderer.drawRect(f1, f2, f3, f4, paint);
Romain Guyb051e892010-09-28 19:09:36 -07001147 }
1148 break;
Romain Guy01d58e42011-01-19 21:54:02 -08001149 case DrawRoundRect: {
Chet Haasedaf98e92011-01-10 14:10:36 -08001150 float f1 = getFloat();
1151 float f2 = getFloat();
1152 float f3 = getFloat();
1153 float f4 = getFloat();
1154 float f5 = getFloat();
1155 float f6 = getFloat();
Romain Guy5ff9df62012-01-23 17:09:05 -08001156 SkPaint* paint = getPaint(renderer);
Chet Haasedaf98e92011-01-10 14:10:36 -08001157 DISPLAY_LIST_LOGD("%s%s %.2f, %.2f, %.2f, %.2f, %.2f, %.2f, %p",
Chet Haasea1cff502012-02-21 13:43:44 -08001158 (char*) indent, OP_NAMES[op], f1, f2, f3, f4, f5, f6, paint);
Chet Haase48659092012-05-31 15:21:51 -07001159 drawGlStatus |= renderer.drawRoundRect(f1, f2, f3, f4, f5, f6, paint);
Romain Guy01d58e42011-01-19 21:54:02 -08001160 }
1161 break;
1162 case DrawCircle: {
Chet Haasedaf98e92011-01-10 14:10:36 -08001163 float f1 = getFloat();
1164 float f2 = getFloat();
1165 float f3 = getFloat();
Romain Guy5ff9df62012-01-23 17:09:05 -08001166 SkPaint* paint = getPaint(renderer);
Chet Haasedaf98e92011-01-10 14:10:36 -08001167 DISPLAY_LIST_LOGD("%s%s %.2f, %.2f, %.2f, %p",
Chet Haasea1cff502012-02-21 13:43:44 -08001168 (char*) indent, OP_NAMES[op], f1, f2, f3, paint);
Chet Haase48659092012-05-31 15:21:51 -07001169 drawGlStatus |= renderer.drawCircle(f1, f2, f3, paint);
Romain Guy01d58e42011-01-19 21:54:02 -08001170 }
1171 break;
Romain Guyc1cd9ba32011-01-23 14:18:41 -08001172 case DrawOval: {
Chet Haasedaf98e92011-01-10 14:10:36 -08001173 float f1 = getFloat();
1174 float f2 = getFloat();
1175 float f3 = getFloat();
1176 float f4 = getFloat();
Romain Guy5ff9df62012-01-23 17:09:05 -08001177 SkPaint* paint = getPaint(renderer);
Chet Haasedaf98e92011-01-10 14:10:36 -08001178 DISPLAY_LIST_LOGD("%s%s %.2f, %.2f, %.2f, %.2f, %p",
Chet Haasea1cff502012-02-21 13:43:44 -08001179 (char*) indent, OP_NAMES[op], f1, f2, f3, f4, paint);
Chet Haase48659092012-05-31 15:21:51 -07001180 drawGlStatus |= renderer.drawOval(f1, f2, f3, f4, paint);
Romain Guyc1cd9ba32011-01-23 14:18:41 -08001181 }
1182 break;
Romain Guy8b2f5262011-01-23 16:15:02 -08001183 case DrawArc: {
Chet Haasedaf98e92011-01-10 14:10:36 -08001184 float f1 = getFloat();
1185 float f2 = getFloat();
1186 float f3 = getFloat();
1187 float f4 = getFloat();
1188 float f5 = getFloat();
1189 float f6 = getFloat();
Romain Guy33f6beb2012-02-16 19:24:51 -08001190 int32_t i1 = getInt();
Romain Guy5ff9df62012-01-23 17:09:05 -08001191 SkPaint* paint = getPaint(renderer);
Chet Haasedaf98e92011-01-10 14:10:36 -08001192 DISPLAY_LIST_LOGD("%s%s %.2f, %.2f, %.2f, %.2f, %.2f, %.2f, %d, %p",
Chet Haasea1cff502012-02-21 13:43:44 -08001193 (char*) indent, OP_NAMES[op], f1, f2, f3, f4, f5, f6, i1, paint);
Chet Haase48659092012-05-31 15:21:51 -07001194 drawGlStatus |= renderer.drawArc(f1, f2, f3, f4, f5, f6, i1 == 1, paint);
Romain Guy8b2f5262011-01-23 16:15:02 -08001195 }
1196 break;
Romain Guyb051e892010-09-28 19:09:36 -07001197 case DrawPath: {
Chet Haasedaf98e92011-01-10 14:10:36 -08001198 SkPath* path = getPath();
Romain Guy5ff9df62012-01-23 17:09:05 -08001199 SkPaint* paint = getPaint(renderer);
Chet Haasedaf98e92011-01-10 14:10:36 -08001200 DISPLAY_LIST_LOGD("%s%s %p, %p", (char*) indent, OP_NAMES[op], path, paint);
Chet Haase48659092012-05-31 15:21:51 -07001201 drawGlStatus |= renderer.drawPath(path, paint);
Romain Guyb051e892010-09-28 19:09:36 -07001202 }
1203 break;
1204 case DrawLines: {
Romain Guy33f6beb2012-02-16 19:24:51 -08001205 int32_t count = 0;
Romain Guyb051e892010-09-28 19:09:36 -07001206 float* points = getFloats(count);
Romain Guy5ff9df62012-01-23 17:09:05 -08001207 SkPaint* paint = getPaint(renderer);
Chet Haasedaf98e92011-01-10 14:10:36 -08001208 DISPLAY_LIST_LOGD("%s%s", (char*) indent, OP_NAMES[op]);
Chet Haase48659092012-05-31 15:21:51 -07001209 drawGlStatus |= renderer.drawLines(points, count, paint);
Romain Guyb051e892010-09-28 19:09:36 -07001210 }
1211 break;
Romain Guyed6fcb02011-03-21 13:11:28 -07001212 case DrawPoints: {
Romain Guy33f6beb2012-02-16 19:24:51 -08001213 int32_t count = 0;
Romain Guyed6fcb02011-03-21 13:11:28 -07001214 float* points = getFloats(count);
Romain Guy5ff9df62012-01-23 17:09:05 -08001215 SkPaint* paint = getPaint(renderer);
Romain Guyed6fcb02011-03-21 13:11:28 -07001216 DISPLAY_LIST_LOGD("%s%s", (char*) indent, OP_NAMES[op]);
Chet Haase48659092012-05-31 15:21:51 -07001217 drawGlStatus |= renderer.drawPoints(points, count, paint);
Romain Guyed6fcb02011-03-21 13:11:28 -07001218 }
1219 break;
Romain Guy325740f2012-02-24 16:48:34 -08001220 case DrawTextOnPath: {
1221 getText(&text);
1222 int32_t count = getInt();
1223 SkPath* path = getPath();
1224 float hOffset = getFloat();
1225 float vOffset = getFloat();
1226 SkPaint* paint = getPaint(renderer);
1227 DISPLAY_LIST_LOGD("%s%s %s, %d, %d, %p", (char*) indent, OP_NAMES[op],
1228 text.text(), text.length(), count, paint);
Chet Haase48659092012-05-31 15:21:51 -07001229 drawGlStatus |= renderer.drawTextOnPath(text.text(), text.length(), count, path,
Romain Guy325740f2012-02-24 16:48:34 -08001230 hOffset, vOffset, paint);
1231 }
1232 break;
Romain Guyeb9a5362012-01-17 17:39:26 -08001233 case DrawPosText: {
1234 getText(&text);
Romain Guy33f6beb2012-02-16 19:24:51 -08001235 int32_t count = getInt();
1236 int32_t positionsCount = 0;
Romain Guyeb9a5362012-01-17 17:39:26 -08001237 float* positions = getFloats(positionsCount);
Romain Guy5ff9df62012-01-23 17:09:05 -08001238 SkPaint* paint = getPaint(renderer);
Romain Guyeb9a5362012-01-17 17:39:26 -08001239 DISPLAY_LIST_LOGD("%s%s %s, %d, %d, %p", (char*) indent,
1240 OP_NAMES[op], text.text(), text.length(), count, paint);
Chet Haase48659092012-05-31 15:21:51 -07001241 drawGlStatus |= renderer.drawPosText(text.text(), text.length(), count,
1242 positions, paint);
Romain Guyeb9a5362012-01-17 17:39:26 -08001243 }
1244 break;
Romain Guyc2525952012-07-27 16:41:22 -07001245 case DrawText: {
Raph Levien996e57c2012-07-23 15:22:52 -07001246 getText(&text);
1247 int32_t count = getInt();
1248 float x = getFloat();
1249 float y = getFloat();
1250 int32_t positionsCount = 0;
1251 float* positions = getFloats(positionsCount);
1252 SkPaint* paint = getPaint(renderer);
1253 float length = getFloat();
1254 DISPLAY_LIST_LOGD("%s%s %s, %d, %d, %.2f, %.2f, %p, %.2f", (char*) indent,
1255 OP_NAMES[op], text.text(), text.length(), count, x, y, paint, length);
Romain Guyc2525952012-07-27 16:41:22 -07001256 drawGlStatus |= renderer.drawText(text.text(), text.length(), count,
Raph Levien996e57c2012-07-23 15:22:52 -07001257 x, y, positions, paint, length);
1258 }
1259 break;
Romain Guyb051e892010-09-28 19:09:36 -07001260 case ResetShader: {
Chet Haasedaf98e92011-01-10 14:10:36 -08001261 DISPLAY_LIST_LOGD("%s%s", (char*) indent, OP_NAMES[op]);
Romain Guyb051e892010-09-28 19:09:36 -07001262 renderer.resetShader();
1263 }
1264 break;
1265 case SetupShader: {
Chet Haasedaf98e92011-01-10 14:10:36 -08001266 SkiaShader* shader = getShader();
1267 DISPLAY_LIST_LOGD("%s%s %p", (char*) indent, OP_NAMES[op], shader);
1268 renderer.setupShader(shader);
Romain Guyb051e892010-09-28 19:09:36 -07001269 }
1270 break;
1271 case ResetColorFilter: {
Chet Haasedaf98e92011-01-10 14:10:36 -08001272 DISPLAY_LIST_LOGD("%s%s", (char*) indent, OP_NAMES[op]);
Romain Guyb051e892010-09-28 19:09:36 -07001273 renderer.resetColorFilter();
1274 }
1275 break;
1276 case SetupColorFilter: {
Chet Haasedaf98e92011-01-10 14:10:36 -08001277 SkiaColorFilter *colorFilter = getColorFilter();
1278 DISPLAY_LIST_LOGD("%s%s %p", (char*) indent, OP_NAMES[op], colorFilter);
1279 renderer.setupColorFilter(colorFilter);
Romain Guyb051e892010-09-28 19:09:36 -07001280 }
1281 break;
1282 case ResetShadow: {
Chet Haasedaf98e92011-01-10 14:10:36 -08001283 DISPLAY_LIST_LOGD("%s%s", (char*) indent, OP_NAMES[op]);
Romain Guyb051e892010-09-28 19:09:36 -07001284 renderer.resetShadow();
1285 }
1286 break;
1287 case SetupShadow: {
Chet Haasedaf98e92011-01-10 14:10:36 -08001288 float radius = getFloat();
1289 float dx = getFloat();
1290 float dy = getFloat();
Romain Guy33f6beb2012-02-16 19:24:51 -08001291 int32_t color = getInt();
Chet Haasedaf98e92011-01-10 14:10:36 -08001292 DISPLAY_LIST_LOGD("%s%s %.2f, %.2f, %.2f, 0x%x", (char*) indent, OP_NAMES[op],
Chet Haasea1cff502012-02-21 13:43:44 -08001293 radius, dx, dy, color);
Chet Haasedaf98e92011-01-10 14:10:36 -08001294 renderer.setupShadow(radius, dx, dy, color);
Romain Guyb051e892010-09-28 19:09:36 -07001295 }
1296 break;
Romain Guy5ff9df62012-01-23 17:09:05 -08001297 case ResetPaintFilter: {
1298 DISPLAY_LIST_LOGD("%s%s", (char*) indent, OP_NAMES[op]);
1299 renderer.resetPaintFilter();
1300 }
1301 break;
1302 case SetupPaintFilter: {
Romain Guy33f6beb2012-02-16 19:24:51 -08001303 int32_t clearBits = getInt();
1304 int32_t setBits = getInt();
Romain Guy5ff9df62012-01-23 17:09:05 -08001305 DISPLAY_LIST_LOGD("%s%s 0x%x, 0x%x", (char*) indent, OP_NAMES[op],
1306 clearBits, setBits);
1307 renderer.setupPaintFilter(clearBits, setBits);
1308 }
1309 break;
Chet Haasedaf98e92011-01-10 14:10:36 -08001310 default:
1311 DISPLAY_LIST_LOGD("Display List error: op not handled: %s%s",
Chet Haasea1cff502012-02-21 13:43:44 -08001312 (char*) indent, OP_NAMES[op]);
Chet Haasedaf98e92011-01-10 14:10:36 -08001313 break;
Romain Guyb051e892010-09-28 19:09:36 -07001314 }
1315 }
Romain Guyffac7fc2011-01-13 17:21:49 -08001316
Chet Haase1271e2c2012-04-20 09:54:27 -07001317 DISPLAY_LIST_LOGD("%s%s %d", (char*) indent, "RestoreToCount", restoreTo);
1318 renderer.restoreToCount(restoreTo);
Romain Guy13631f32012-01-30 17:41:55 -08001319 renderer.endMark();
1320
Chet Haasea1cff502012-02-21 13:43:44 -08001321 DISPLAY_LIST_LOGD("%sDone (%p, %s), returning %d", (char*) indent + 2, this, mName.string(),
Romain Guy65549432012-03-26 16:45:05 -07001322 drawGlStatus);
1323 return drawGlStatus;
Romain Guyb051e892010-09-28 19:09:36 -07001324}
1325
1326///////////////////////////////////////////////////////////////////////////////
Romain Guy4aa90572010-09-26 18:40:37 -07001327// Base structure
1328///////////////////////////////////////////////////////////////////////////////
1329
Romain Guy58ecc202012-09-07 11:58:36 -07001330DisplayListRenderer::DisplayListRenderer():
1331 mCaches(Caches::getInstance()), mWriter(MIN_WRITER_SIZE),
Romain Guy33f6beb2012-02-16 19:24:51 -08001332 mTranslateX(0.0f), mTranslateY(0.0f), mHasTranslate(false), mHasDrawOps(false) {
Romain Guy4aa90572010-09-26 18:40:37 -07001333}
1334
1335DisplayListRenderer::~DisplayListRenderer() {
1336 reset();
1337}
1338
1339void DisplayListRenderer::reset() {
Romain Guy4aa90572010-09-26 18:40:37 -07001340 mWriter.reset();
Chet Haase5c13d892010-10-08 08:37:55 -07001341
Romain Guy58ecc202012-09-07 11:58:36 -07001342 mCaches.resourceCache.lock();
1343
Chet Haase5c13d892010-10-08 08:37:55 -07001344 for (size_t i = 0; i < mBitmapResources.size(); i++) {
Romain Guy58ecc202012-09-07 11:58:36 -07001345 mCaches.resourceCache.decrementRefcountLocked(mBitmapResources.itemAt(i));
Chet Haase5c13d892010-10-08 08:37:55 -07001346 }
Chet Haased98aa2d2010-10-25 15:47:32 -07001347
Romain Guy49c5fc02012-05-15 11:10:01 -07001348 for (size_t i = 0; i < mOwnedBitmapResources.size(); i++) {
Romain Guy58ecc202012-09-07 11:58:36 -07001349 mCaches.resourceCache.decrementRefcountLocked(mOwnedBitmapResources.itemAt(i));
Romain Guy49c5fc02012-05-15 11:10:01 -07001350 }
Romain Guy49c5fc02012-05-15 11:10:01 -07001351
Romain Guyd586ad92011-06-22 16:14:36 -07001352 for (size_t i = 0; i < mFilterResources.size(); i++) {
Romain Guy58ecc202012-09-07 11:58:36 -07001353 mCaches.resourceCache.decrementRefcountLocked(mFilterResources.itemAt(i));
Romain Guyd586ad92011-06-22 16:14:36 -07001354 }
Romain Guyd586ad92011-06-22 16:14:36 -07001355
Romain Guy43ccf462011-01-14 18:51:01 -08001356 for (size_t i = 0; i < mShaders.size(); i++) {
Romain Guy58ecc202012-09-07 11:58:36 -07001357 mCaches.resourceCache.decrementRefcountLocked(mShaders.itemAt(i));
Romain Guy43ccf462011-01-14 18:51:01 -08001358 }
Romain Guy43ccf462011-01-14 18:51:01 -08001359
Chet Haased34dd712012-05-02 18:50:34 -07001360 for (size_t i = 0; i < mSourcePaths.size(); i++) {
Romain Guy58ecc202012-09-07 11:58:36 -07001361 mCaches.resourceCache.decrementRefcountLocked(mSourcePaths.itemAt(i));
Chet Haased34dd712012-05-02 18:50:34 -07001362 }
Romain Guy58ecc202012-09-07 11:58:36 -07001363
1364 mCaches.resourceCache.unlock();
1365
1366 mBitmapResources.clear();
1367 mOwnedBitmapResources.clear();
1368 mFilterResources.clear();
Chet Haased34dd712012-05-02 18:50:34 -07001369 mSourcePaths.clear();
1370
Romain Guy58ecc202012-09-07 11:58:36 -07001371 mShaders.clear();
1372 mShaderMap.clear();
1373
Romain Guy43ccf462011-01-14 18:51:01 -08001374 mPaints.clear();
1375 mPaintMap.clear();
Romain Guyd586ad92011-06-22 16:14:36 -07001376
Romain Guy2fc941e2011-02-03 15:06:05 -08001377 mPaths.clear();
1378 mPathMap.clear();
Romain Guyd586ad92011-06-22 16:14:36 -07001379
Chet Haased98aa2d2010-10-25 15:47:32 -07001380 mMatrices.clear();
Romain Guy04c9d8c2011-08-25 14:01:48 -07001381
1382 mHasDrawOps = false;
Romain Guy4aa90572010-09-26 18:40:37 -07001383}
1384
1385///////////////////////////////////////////////////////////////////////////////
1386// Operations
1387///////////////////////////////////////////////////////////////////////////////
1388
Jeff Brown162a0212011-07-21 17:02:54 -07001389DisplayList* DisplayListRenderer::getDisplayList(DisplayList* displayList) {
1390 if (!displayList) {
1391 displayList = new DisplayList(*this);
Chet Haase5977baa2011-01-05 18:01:22 -08001392 } else {
Jeff Brown162a0212011-07-21 17:02:54 -07001393 displayList->initFromDisplayListRenderer(*this, true);
Chet Haase5977baa2011-01-05 18:01:22 -08001394 }
Romain Guy04c9d8c2011-08-25 14:01:48 -07001395 displayList->setRenderable(mHasDrawOps);
Jeff Brown162a0212011-07-21 17:02:54 -07001396 return displayList;
Chet Haase5977baa2011-01-05 18:01:22 -08001397}
1398
Romain Guy49c5fc02012-05-15 11:10:01 -07001399bool DisplayListRenderer::isDeferred() {
1400 return true;
1401}
1402
Romain Guyb051e892010-09-28 19:09:36 -07001403void DisplayListRenderer::setViewport(int width, int height) {
1404 mOrthoMatrix.loadOrtho(0, width, height, 0, -1, 1);
1405
1406 mWidth = width;
1407 mHeight = height;
1408}
1409
Chet Haase44b2fe32012-06-06 19:03:58 -07001410int DisplayListRenderer::prepareDirty(float left, float top,
Romain Guy7d7b5492011-01-24 16:33:45 -08001411 float right, float bottom, bool opaque) {
Romain Guyb051e892010-09-28 19:09:36 -07001412 mSnapshot = new Snapshot(mFirstSnapshot,
1413 SkCanvas::kMatrix_SaveFlag | SkCanvas::kClip_SaveFlag);
1414 mSaveCount = 1;
Romain Guy45e4c3d2012-09-11 17:17:07 -07001415
Romain Guyb051e892010-09-28 19:09:36 -07001416 mSnapshot->setClip(0.0f, 0.0f, mWidth, mHeight);
Romain Guy45e4c3d2012-09-11 17:17:07 -07001417 mDirtyClip = opaque;
1418
Romain Guy27454a42011-01-23 12:01:41 -08001419 mRestoreSaveCount = -1;
Romain Guy45e4c3d2012-09-11 17:17:07 -07001420
Chet Haase44b2fe32012-06-06 19:03:58 -07001421 return DrawGlInfo::kStatusDone; // No invalidate needed at record-time
Romain Guy27454a42011-01-23 12:01:41 -08001422}
1423
1424void DisplayListRenderer::finish() {
1425 insertRestoreToCount();
Romain Guy33f6beb2012-02-16 19:24:51 -08001426 insertTranlate();
Romain Guyb051e892010-09-28 19:09:36 -07001427}
1428
Chet Haasedaf98e92011-01-10 14:10:36 -08001429void DisplayListRenderer::interrupt() {
Chet Haasedaf98e92011-01-10 14:10:36 -08001430}
Romain Guy2b1847e2011-01-26 13:43:01 -08001431
Chet Haasedaf98e92011-01-10 14:10:36 -08001432void DisplayListRenderer::resume() {
Romain Guy4aa90572010-09-26 18:40:37 -07001433}
1434
Romain Guy65549432012-03-26 16:45:05 -07001435status_t DisplayListRenderer::callDrawGLFunction(Functor *functor, Rect& dirty) {
Romain Guycabfcc12011-03-07 18:06:46 -08001436 // Ignore dirty during recording, it matters only when we replay
Chet Haasedaf98e92011-01-10 14:10:36 -08001437 addOp(DisplayList::DrawGLFunction);
1438 addInt((int) functor);
Romain Guy65549432012-03-26 16:45:05 -07001439 return DrawGlInfo::kStatusDone; // No invalidate needed at record-time
Chet Haasedaf98e92011-01-10 14:10:36 -08001440}
1441
Romain Guy4aa90572010-09-26 18:40:37 -07001442int DisplayListRenderer::save(int flags) {
Romain Guyb051e892010-09-28 19:09:36 -07001443 addOp(DisplayList::Save);
Romain Guy4aa90572010-09-26 18:40:37 -07001444 addInt(flags);
1445 return OpenGLRenderer::save(flags);
1446}
1447
1448void DisplayListRenderer::restore() {
Romain Guy04c9d8c2011-08-25 14:01:48 -07001449 if (mRestoreSaveCount < 0) {
Romain Guy33f6beb2012-02-16 19:24:51 -08001450 restoreToCount(getSaveCount() - 1);
1451 return;
Romain Guy04c9d8c2011-08-25 14:01:48 -07001452 }
Romain Guy33f6beb2012-02-16 19:24:51 -08001453
1454 mRestoreSaveCount--;
1455 insertTranlate();
Romain Guy4aa90572010-09-26 18:40:37 -07001456 OpenGLRenderer::restore();
1457}
1458
1459void DisplayListRenderer::restoreToCount(int saveCount) {
Romain Guy27454a42011-01-23 12:01:41 -08001460 mRestoreSaveCount = saveCount;
Romain Guy33f6beb2012-02-16 19:24:51 -08001461 insertTranlate();
Romain Guy4aa90572010-09-26 18:40:37 -07001462 OpenGLRenderer::restoreToCount(saveCount);
1463}
1464
1465int DisplayListRenderer::saveLayer(float left, float top, float right, float bottom,
Chet Haase5c13d892010-10-08 08:37:55 -07001466 SkPaint* p, int flags) {
Romain Guyb051e892010-09-28 19:09:36 -07001467 addOp(DisplayList::SaveLayer);
Romain Guy4aa90572010-09-26 18:40:37 -07001468 addBounds(left, top, right, bottom);
1469 addPaint(p);
1470 addInt(flags);
Romain Guyb051e892010-09-28 19:09:36 -07001471 return OpenGLRenderer::save(flags);
Romain Guy4aa90572010-09-26 18:40:37 -07001472}
1473
Romain Guy5b3b3522010-10-27 18:57:51 -07001474int DisplayListRenderer::saveLayerAlpha(float left, float top, float right, float bottom,
1475 int alpha, int flags) {
1476 addOp(DisplayList::SaveLayerAlpha);
1477 addBounds(left, top, right, bottom);
1478 addInt(alpha);
1479 addInt(flags);
1480 return OpenGLRenderer::save(flags);
1481}
1482
Romain Guy4aa90572010-09-26 18:40:37 -07001483void DisplayListRenderer::translate(float dx, float dy) {
Romain Guy33f6beb2012-02-16 19:24:51 -08001484 mHasTranslate = true;
1485 mTranslateX += dx;
1486 mTranslateY += dy;
1487 insertRestoreToCount();
Romain Guy4aa90572010-09-26 18:40:37 -07001488 OpenGLRenderer::translate(dx, dy);
1489}
1490
1491void DisplayListRenderer::rotate(float degrees) {
Romain Guyb051e892010-09-28 19:09:36 -07001492 addOp(DisplayList::Rotate);
Romain Guy4aa90572010-09-26 18:40:37 -07001493 addFloat(degrees);
1494 OpenGLRenderer::rotate(degrees);
1495}
1496
1497void DisplayListRenderer::scale(float sx, float sy) {
Romain Guyb051e892010-09-28 19:09:36 -07001498 addOp(DisplayList::Scale);
Romain Guy4aa90572010-09-26 18:40:37 -07001499 addPoint(sx, sy);
1500 OpenGLRenderer::scale(sx, sy);
1501}
1502
Romain Guy807daf72011-01-18 11:19:19 -08001503void DisplayListRenderer::skew(float sx, float sy) {
1504 addOp(DisplayList::Skew);
1505 addPoint(sx, sy);
1506 OpenGLRenderer::skew(sx, sy);
1507}
1508
Romain Guy4aa90572010-09-26 18:40:37 -07001509void DisplayListRenderer::setMatrix(SkMatrix* matrix) {
Romain Guyb051e892010-09-28 19:09:36 -07001510 addOp(DisplayList::SetMatrix);
Romain Guy4aa90572010-09-26 18:40:37 -07001511 addMatrix(matrix);
1512 OpenGLRenderer::setMatrix(matrix);
1513}
1514
1515void DisplayListRenderer::concatMatrix(SkMatrix* matrix) {
Romain Guyb051e892010-09-28 19:09:36 -07001516 addOp(DisplayList::ConcatMatrix);
Romain Guy4aa90572010-09-26 18:40:37 -07001517 addMatrix(matrix);
1518 OpenGLRenderer::concatMatrix(matrix);
1519}
1520
1521bool DisplayListRenderer::clipRect(float left, float top, float right, float bottom,
1522 SkRegion::Op op) {
Romain Guyb051e892010-09-28 19:09:36 -07001523 addOp(DisplayList::ClipRect);
Romain Guy4aa90572010-09-26 18:40:37 -07001524 addBounds(left, top, right, bottom);
1525 addInt(op);
1526 return OpenGLRenderer::clipRect(left, top, right, bottom, op);
1527}
1528
Romain Guy65549432012-03-26 16:45:05 -07001529status_t DisplayListRenderer::drawDisplayList(DisplayList* displayList,
Chet Haase1271e2c2012-04-20 09:54:27 -07001530 Rect& dirty, int32_t flags, uint32_t level) {
Romain Guycabfcc12011-03-07 18:06:46 -08001531 // dirty is an out parameter and should not be recorded,
1532 // it matters only when replaying the display list
Chet Haaseb85967b2012-03-26 14:37:51 -07001533
1534 addOp(DisplayList::DrawDisplayList);
Romain Guy0fe478e2010-11-08 12:08:41 -08001535 addDisplayList(displayList);
Romain Guy33f6beb2012-02-16 19:24:51 -08001536 addInt(flags);
Romain Guy65549432012-03-26 16:45:05 -07001537 return DrawGlInfo::kStatusDone;
Romain Guy0fe478e2010-11-08 12:08:41 -08001538}
1539
Chet Haase48659092012-05-31 15:21:51 -07001540status_t DisplayListRenderer::drawLayer(Layer* layer, float x, float y, SkPaint* paint) {
Romain Guy6c319ca2011-01-11 14:29:25 -08001541 addOp(DisplayList::DrawLayer);
Romain Guyada830f2011-01-13 12:13:20 -08001542 addInt((int) layer);
1543 addPoint(x, y);
Romain Guy6c319ca2011-01-11 14:29:25 -08001544 addPaint(paint);
Chet Haase48659092012-05-31 15:21:51 -07001545 return DrawGlInfo::kStatusDone;
Romain Guy6c319ca2011-01-11 14:29:25 -08001546}
1547
Chet Haase48659092012-05-31 15:21:51 -07001548status_t DisplayListRenderer::drawBitmap(SkBitmap* bitmap, float left, float top, SkPaint* paint) {
Romain Guy33f6beb2012-02-16 19:24:51 -08001549 const bool reject = quickReject(left, top, left + bitmap->width(), top + bitmap->height());
1550 uint32_t* location = addOp(DisplayList::DrawBitmap, reject);
Romain Guy4aa90572010-09-26 18:40:37 -07001551 addBitmap(bitmap);
1552 addPoint(left, top);
1553 addPaint(paint);
Romain Guy33f6beb2012-02-16 19:24:51 -08001554 addSkip(location);
Chet Haase48659092012-05-31 15:21:51 -07001555 return DrawGlInfo::kStatusDone;
Romain Guy4aa90572010-09-26 18:40:37 -07001556}
1557
Chet Haase48659092012-05-31 15:21:51 -07001558status_t DisplayListRenderer::drawBitmap(SkBitmap* bitmap, SkMatrix* matrix, SkPaint* paint) {
Romain Guy33f6beb2012-02-16 19:24:51 -08001559 Rect r(0.0f, 0.0f, bitmap->width(), bitmap->height());
1560 const mat4 transform(*matrix);
1561 transform.mapRect(r);
1562
1563 const bool reject = quickReject(r.left, r.top, r.right, r.bottom);
1564 uint32_t* location = addOp(DisplayList::DrawBitmapMatrix, reject);
Romain Guy4aa90572010-09-26 18:40:37 -07001565 addBitmap(bitmap);
1566 addMatrix(matrix);
1567 addPaint(paint);
Romain Guy33f6beb2012-02-16 19:24:51 -08001568 addSkip(location);
Chet Haase48659092012-05-31 15:21:51 -07001569 return DrawGlInfo::kStatusDone;
Romain Guy4aa90572010-09-26 18:40:37 -07001570}
1571
Chet Haase48659092012-05-31 15:21:51 -07001572status_t DisplayListRenderer::drawBitmap(SkBitmap* bitmap, float srcLeft, float srcTop,
Romain Guy4aa90572010-09-26 18:40:37 -07001573 float srcRight, float srcBottom, float dstLeft, float dstTop,
Chet Haase5c13d892010-10-08 08:37:55 -07001574 float dstRight, float dstBottom, SkPaint* paint) {
Romain Guy33f6beb2012-02-16 19:24:51 -08001575 const bool reject = quickReject(dstLeft, dstTop, dstRight, dstBottom);
1576 uint32_t* location = addOp(DisplayList::DrawBitmapRect, reject);
Romain Guy4aa90572010-09-26 18:40:37 -07001577 addBitmap(bitmap);
1578 addBounds(srcLeft, srcTop, srcRight, srcBottom);
1579 addBounds(dstLeft, dstTop, dstRight, dstBottom);
1580 addPaint(paint);
Romain Guy33f6beb2012-02-16 19:24:51 -08001581 addSkip(location);
Chet Haase48659092012-05-31 15:21:51 -07001582 return DrawGlInfo::kStatusDone;
Romain Guy4aa90572010-09-26 18:40:37 -07001583}
1584
Chet Haase48659092012-05-31 15:21:51 -07001585status_t DisplayListRenderer::drawBitmapData(SkBitmap* bitmap, float left, float top,
1586 SkPaint* paint) {
Romain Guy95c21d02012-07-17 17:46:03 -07001587 const bool reject = quickReject(left, top, left + bitmap->width(), top + bitmap->height());
Romain Guye651cc62012-05-14 19:44:40 -07001588 uint32_t* location = addOp(DisplayList::DrawBitmapData, reject);
1589 addBitmapData(bitmap);
1590 addPoint(left, top);
1591 addPaint(paint);
1592 addSkip(location);
Chet Haase48659092012-05-31 15:21:51 -07001593 return DrawGlInfo::kStatusDone;
Romain Guye651cc62012-05-14 19:44:40 -07001594}
1595
Chet Haase48659092012-05-31 15:21:51 -07001596status_t DisplayListRenderer::drawBitmapMesh(SkBitmap* bitmap, int meshWidth, int meshHeight,
Romain Guy5a7b4662011-01-20 19:09:30 -08001597 float* vertices, int* colors, SkPaint* paint) {
1598 addOp(DisplayList::DrawBitmapMesh);
1599 addBitmap(bitmap);
1600 addInt(meshWidth);
1601 addInt(meshHeight);
1602 addFloats(vertices, (meshWidth + 1) * (meshHeight + 1) * 2);
1603 if (colors) {
1604 addInt(1);
1605 addInts(colors, (meshWidth + 1) * (meshHeight + 1));
1606 } else {
1607 addInt(0);
1608 }
1609 addPaint(paint);
Chet Haase48659092012-05-31 15:21:51 -07001610 return DrawGlInfo::kStatusDone;
Romain Guy5a7b4662011-01-20 19:09:30 -08001611}
1612
Chet Haase48659092012-05-31 15:21:51 -07001613status_t DisplayListRenderer::drawPatch(SkBitmap* bitmap, const int32_t* xDivs,
1614 const int32_t* yDivs, const uint32_t* colors, uint32_t width, uint32_t height,
1615 int8_t numColors, float left, float top, float right, float bottom, SkPaint* paint) {
Romain Guybe6f9dc2012-07-16 12:41:17 -07001616 int alpha;
1617 SkXfermode::Mode mode;
1618 OpenGLRenderer::getAlphaAndModeDirect(paint, &alpha, &mode);
1619
Romain Guy33f6beb2012-02-16 19:24:51 -08001620 const bool reject = quickReject(left, top, right, bottom);
1621 uint32_t* location = addOp(DisplayList::DrawPatch, reject);
Romain Guy4aa90572010-09-26 18:40:37 -07001622 addBitmap(bitmap);
1623 addInts(xDivs, width);
1624 addInts(yDivs, height);
Romain Guy4bb94202010-10-12 15:59:26 -07001625 addUInts(colors, numColors);
Romain Guy4aa90572010-09-26 18:40:37 -07001626 addBounds(left, top, right, bottom);
Romain Guybe6f9dc2012-07-16 12:41:17 -07001627 addInt(alpha);
1628 addInt(mode);
Romain Guy33f6beb2012-02-16 19:24:51 -08001629 addSkip(location);
Chet Haase48659092012-05-31 15:21:51 -07001630 return DrawGlInfo::kStatusDone;
Romain Guy4aa90572010-09-26 18:40:37 -07001631}
1632
Chet Haase48659092012-05-31 15:21:51 -07001633status_t DisplayListRenderer::drawColor(int color, SkXfermode::Mode mode) {
Romain Guyb051e892010-09-28 19:09:36 -07001634 addOp(DisplayList::DrawColor);
Romain Guy4aa90572010-09-26 18:40:37 -07001635 addInt(color);
1636 addInt(mode);
Chet Haase48659092012-05-31 15:21:51 -07001637 return DrawGlInfo::kStatusDone;
Romain Guy4aa90572010-09-26 18:40:37 -07001638}
1639
Chet Haase48659092012-05-31 15:21:51 -07001640status_t DisplayListRenderer::drawRect(float left, float top, float right, float bottom,
Chet Haase5c13d892010-10-08 08:37:55 -07001641 SkPaint* paint) {
Romain Guy33f6beb2012-02-16 19:24:51 -08001642 const bool reject = paint->getStyle() == SkPaint::kFill_Style &&
1643 quickReject(left, top, right, bottom);
1644 uint32_t* location = addOp(DisplayList::DrawRect, reject);
Romain Guy4aa90572010-09-26 18:40:37 -07001645 addBounds(left, top, right, bottom);
1646 addPaint(paint);
Romain Guy33f6beb2012-02-16 19:24:51 -08001647 addSkip(location);
Chet Haase48659092012-05-31 15:21:51 -07001648 return DrawGlInfo::kStatusDone;
Romain Guy4aa90572010-09-26 18:40:37 -07001649}
1650
Chet Haase48659092012-05-31 15:21:51 -07001651status_t DisplayListRenderer::drawRoundRect(float left, float top, float right, float bottom,
Chet Haasea1cff502012-02-21 13:43:44 -08001652 float rx, float ry, SkPaint* paint) {
Romain Guy33f6beb2012-02-16 19:24:51 -08001653 const bool reject = paint->getStyle() == SkPaint::kFill_Style &&
1654 quickReject(left, top, right, bottom);
1655 uint32_t* location = addOp(DisplayList::DrawRoundRect, reject);
Romain Guy01d58e42011-01-19 21:54:02 -08001656 addBounds(left, top, right, bottom);
1657 addPoint(rx, ry);
1658 addPaint(paint);
Romain Guy33f6beb2012-02-16 19:24:51 -08001659 addSkip(location);
Chet Haase48659092012-05-31 15:21:51 -07001660 return DrawGlInfo::kStatusDone;
Romain Guy01d58e42011-01-19 21:54:02 -08001661}
1662
Chet Haase48659092012-05-31 15:21:51 -07001663status_t DisplayListRenderer::drawCircle(float x, float y, float radius, SkPaint* paint) {
Romain Guy01d58e42011-01-19 21:54:02 -08001664 addOp(DisplayList::DrawCircle);
1665 addPoint(x, y);
1666 addFloat(radius);
1667 addPaint(paint);
Chet Haase48659092012-05-31 15:21:51 -07001668 return DrawGlInfo::kStatusDone;
Romain Guy01d58e42011-01-19 21:54:02 -08001669}
1670
Chet Haase48659092012-05-31 15:21:51 -07001671status_t DisplayListRenderer::drawOval(float left, float top, float right, float bottom,
Romain Guyc1cd9ba32011-01-23 14:18:41 -08001672 SkPaint* paint) {
1673 addOp(DisplayList::DrawOval);
1674 addBounds(left, top, right, bottom);
1675 addPaint(paint);
Chet Haase48659092012-05-31 15:21:51 -07001676 return DrawGlInfo::kStatusDone;
Romain Guyc1cd9ba32011-01-23 14:18:41 -08001677}
1678
Chet Haase48659092012-05-31 15:21:51 -07001679status_t DisplayListRenderer::drawArc(float left, float top, float right, float bottom,
Romain Guy8b2f5262011-01-23 16:15:02 -08001680 float startAngle, float sweepAngle, bool useCenter, SkPaint* paint) {
Romain Guy82d41a52011-01-24 21:53:42 -08001681 addOp(DisplayList::DrawArc);
Romain Guy8b2f5262011-01-23 16:15:02 -08001682 addBounds(left, top, right, bottom);
1683 addPoint(startAngle, sweepAngle);
1684 addInt(useCenter ? 1 : 0);
1685 addPaint(paint);
Chet Haase48659092012-05-31 15:21:51 -07001686 return DrawGlInfo::kStatusDone;
Romain Guy8b2f5262011-01-23 16:15:02 -08001687}
1688
Chet Haase48659092012-05-31 15:21:51 -07001689status_t DisplayListRenderer::drawPath(SkPath* path, SkPaint* paint) {
Romain Guy33f6beb2012-02-16 19:24:51 -08001690 float left, top, offset;
1691 uint32_t width, height;
1692 computePathBounds(path, paint, left, top, offset, width, height);
1693
Romain Guy95c21d02012-07-17 17:46:03 -07001694 left -= offset;
1695 top -= offset;
1696
1697 const bool reject = quickReject(left, top, left + width, top + height);
Romain Guy33f6beb2012-02-16 19:24:51 -08001698 uint32_t* location = addOp(DisplayList::DrawPath, reject);
Romain Guy4aa90572010-09-26 18:40:37 -07001699 addPath(path);
1700 addPaint(paint);
Romain Guy33f6beb2012-02-16 19:24:51 -08001701 addSkip(location);
Chet Haase48659092012-05-31 15:21:51 -07001702 return DrawGlInfo::kStatusDone;
Romain Guy4aa90572010-09-26 18:40:37 -07001703}
1704
Chet Haase48659092012-05-31 15:21:51 -07001705status_t DisplayListRenderer::drawLines(float* points, int count, SkPaint* paint) {
Romain Guyb051e892010-09-28 19:09:36 -07001706 addOp(DisplayList::DrawLines);
Romain Guy4aa90572010-09-26 18:40:37 -07001707 addFloats(points, count);
1708 addPaint(paint);
Chet Haase48659092012-05-31 15:21:51 -07001709 return DrawGlInfo::kStatusDone;
Romain Guy4aa90572010-09-26 18:40:37 -07001710}
1711
Chet Haase48659092012-05-31 15:21:51 -07001712status_t DisplayListRenderer::drawPoints(float* points, int count, SkPaint* paint) {
Romain Guyed6fcb02011-03-21 13:11:28 -07001713 addOp(DisplayList::DrawPoints);
1714 addFloats(points, count);
1715 addPaint(paint);
Chet Haase48659092012-05-31 15:21:51 -07001716 return DrawGlInfo::kStatusDone;
Romain Guyed6fcb02011-03-21 13:11:28 -07001717}
1718
Chet Haase48659092012-05-31 15:21:51 -07001719status_t DisplayListRenderer::drawTextOnPath(const char* text, int bytesCount, int count,
Romain Guy325740f2012-02-24 16:48:34 -08001720 SkPath* path, float hOffset, float vOffset, SkPaint* paint) {
Chet Haase48659092012-05-31 15:21:51 -07001721 if (!text || count <= 0) return DrawGlInfo::kStatusDone;
Romain Guy325740f2012-02-24 16:48:34 -08001722 addOp(DisplayList::DrawTextOnPath);
1723 addText(text, bytesCount);
1724 addInt(count);
1725 addPath(path);
1726 addFloat(hOffset);
1727 addFloat(vOffset);
1728 paint->setAntiAlias(true);
Chet Haasee816bae2012-08-09 13:39:02 -07001729 SkPaint* addedPaint = addPaint(paint);
1730 FontRenderer& fontRenderer = mCaches.fontRenderer->getFontRenderer(addedPaint);
1731 fontRenderer.precache(addedPaint, text, count);
Chet Haase48659092012-05-31 15:21:51 -07001732 return DrawGlInfo::kStatusDone;
Romain Guy325740f2012-02-24 16:48:34 -08001733}
1734
Chet Haase48659092012-05-31 15:21:51 -07001735status_t DisplayListRenderer::drawPosText(const char* text, int bytesCount, int count,
Romain Guyeb9a5362012-01-17 17:39:26 -08001736 const float* positions, SkPaint* paint) {
Chet Haase48659092012-05-31 15:21:51 -07001737 if (!text || count <= 0) return DrawGlInfo::kStatusDone;
Romain Guyeb9a5362012-01-17 17:39:26 -08001738 addOp(DisplayList::DrawPosText);
1739 addText(text, bytesCount);
1740 addInt(count);
1741 addFloats(positions, count * 2);
1742 paint->setAntiAlias(true);
Chet Haasee816bae2012-08-09 13:39:02 -07001743 SkPaint* addedPaint = addPaint(paint);
1744 FontRenderer& fontRenderer = mCaches.fontRenderer->getFontRenderer(addedPaint);
1745 fontRenderer.precache(addedPaint, text, count);
Chet Haase48659092012-05-31 15:21:51 -07001746 return DrawGlInfo::kStatusDone;
Romain Guyeb9a5362012-01-17 17:39:26 -08001747}
1748
Romain Guyc2525952012-07-27 16:41:22 -07001749status_t DisplayListRenderer::drawText(const char* text, int bytesCount, int count,
Raph Levien996e57c2012-07-23 15:22:52 -07001750 float x, float y, const float* positions, SkPaint* paint, float length) {
1751 if (!text || count <= 0) return DrawGlInfo::kStatusDone;
1752
1753 // TODO: We should probably make a copy of the paint instead of modifying
1754 // it; modifying the paint will change its generationID the first
1755 // time, which might impact caches. More investigation needed to
1756 // see if it matters.
1757 // If we make a copy, then drawTextDecorations() should *not* make
1758 // its own copy as it does right now.
1759 // Beware: this needs Glyph encoding (already done on the Paint constructor)
1760 paint->setAntiAlias(true);
1761 if (length < 0.0f) length = paint->measureText(text, bytesCount);
1762
1763 bool reject = false;
1764 if (CC_LIKELY(paint->getTextAlign() == SkPaint::kLeft_Align)) {
1765 SkPaint::FontMetrics metrics;
1766 paint->getFontMetrics(&metrics, 0.0f);
1767 reject = quickReject(x, y + metrics.fTop, x + length, y + metrics.fBottom);
1768 }
1769
Romain Guyc2525952012-07-27 16:41:22 -07001770 uint32_t* location = addOp(DisplayList::DrawText, reject);
Raph Levien996e57c2012-07-23 15:22:52 -07001771 addText(text, bytesCount);
1772 addInt(count);
1773 addFloat(x);
1774 addFloat(y);
1775 addFloats(positions, count * 2);
Chet Haasee816bae2012-08-09 13:39:02 -07001776 SkPaint* addedPaint = addPaint(paint);
1777 if (!reject) {
1778 FontRenderer& fontRenderer = mCaches.fontRenderer->getFontRenderer(addedPaint);
1779 fontRenderer.precache(addedPaint, text, count);
1780 }
Raph Levien996e57c2012-07-23 15:22:52 -07001781 addFloat(length);
1782 addSkip(location);
1783 return DrawGlInfo::kStatusDone;
1784}
1785
Romain Guy4aa90572010-09-26 18:40:37 -07001786void DisplayListRenderer::resetShader() {
Romain Guyb051e892010-09-28 19:09:36 -07001787 addOp(DisplayList::ResetShader);
Romain Guy4aa90572010-09-26 18:40:37 -07001788}
1789
1790void DisplayListRenderer::setupShader(SkiaShader* shader) {
Chet Haase5c13d892010-10-08 08:37:55 -07001791 addOp(DisplayList::SetupShader);
1792 addShader(shader);
Romain Guy4aa90572010-09-26 18:40:37 -07001793}
1794
1795void DisplayListRenderer::resetColorFilter() {
Romain Guyb051e892010-09-28 19:09:36 -07001796 addOp(DisplayList::ResetColorFilter);
Romain Guy4aa90572010-09-26 18:40:37 -07001797}
1798
1799void DisplayListRenderer::setupColorFilter(SkiaColorFilter* filter) {
Chet Haasead93c2b2010-10-22 16:17:12 -07001800 addOp(DisplayList::SetupColorFilter);
1801 addColorFilter(filter);
Romain Guy4aa90572010-09-26 18:40:37 -07001802}
1803
1804void DisplayListRenderer::resetShadow() {
Romain Guyb051e892010-09-28 19:09:36 -07001805 addOp(DisplayList::ResetShadow);
Romain Guy4aa90572010-09-26 18:40:37 -07001806}
1807
1808void DisplayListRenderer::setupShadow(float radius, float dx, float dy, int color) {
Romain Guyb051e892010-09-28 19:09:36 -07001809 addOp(DisplayList::SetupShadow);
Romain Guy4aa90572010-09-26 18:40:37 -07001810 addFloat(radius);
1811 addPoint(dx, dy);
1812 addInt(color);
Romain Guy4aa90572010-09-26 18:40:37 -07001813}
1814
Romain Guy5ff9df62012-01-23 17:09:05 -08001815void DisplayListRenderer::resetPaintFilter() {
1816 addOp(DisplayList::ResetPaintFilter);
1817}
1818
1819void DisplayListRenderer::setupPaintFilter(int clearBits, int setBits) {
1820 addOp(DisplayList::SetupPaintFilter);
1821 addInt(clearBits);
1822 addInt(setBits);
1823}
1824
Romain Guy4aa90572010-09-26 18:40:37 -07001825}; // namespace uirenderer
1826}; // namespace android