OLD | NEW |
1 /* | 1 /* |
2 * Copyright 2012 Google Inc. | 2 * Copyright 2012 Google Inc. |
3 * | 3 * |
4 * Use of this source code is governed by a BSD-style license that can be | 4 * Use of this source code is governed by a BSD-style license that can be |
5 * found in the LICENSE file. | 5 * found in the LICENSE file. |
6 */ | 6 */ |
7 | 7 |
8 #include "SkDebugCanvas.h" | 8 #include "SkDebugCanvas.h" |
9 #include "SkDevice.h" | 9 #include "SkDevice.h" |
10 #include "SkGraphics.h" | 10 #include "SkGraphics.h" |
(...skipping 22 matching lines...) Expand all Loading... |
33 return NULL == p.getPathEffect() && | 33 return NULL == p.getPathEffect() && |
34 NULL == p.getShader() && | 34 NULL == p.getShader() && |
35 NULL == p.getXfermode() && | 35 NULL == p.getXfermode() && |
36 NULL == p.getMaskFilter() && | 36 NULL == p.getMaskFilter() && |
37 NULL == p.getColorFilter() && | 37 NULL == p.getColorFilter() && |
38 NULL == p.getRasterizer() && | 38 NULL == p.getRasterizer() && |
39 NULL == p.getLooper() && | 39 NULL == p.getLooper() && |
40 NULL == p.getImageFilter(); | 40 NULL == p.getImageFilter(); |
41 } | 41 } |
42 | 42 |
| 43 |
43 // Check for: | 44 // Check for: |
44 // SAVE_LAYER | 45 // SAVE_LAYER |
45 // DRAW_BITMAP_RECT_TO_RECT | 46 // DRAW_BITMAP_RECT_TO_RECT |
46 // RESTORE | 47 // RESTORE |
47 // where the saveLayer's color can be moved into the drawBitmapRect | 48 // where the saveLayer's color can be moved into the drawBitmapRect |
48 static bool check_0(const SkTDArray<SkDrawCommand*>& commands, int curCommand) { | 49 static bool check_0(SkDebugCanvas* canvas, int curCommand) { |
49 if (SAVE_LAYER != commands[curCommand]->getType() || | 50 if (SAVE_LAYER != canvas->getDrawCommandAt(curCommand)->getType() || |
50 commands.count() <= curCommand+2 || | 51 canvas->getSize() <= curCommand+2 || |
51 DRAW_BITMAP_RECT_TO_RECT != commands[curCommand+1]->getType() || | 52 DRAW_BITMAP_RECT_TO_RECT != canvas->getDrawCommandAt(curCommand+1)->getT
ype() || |
52 RESTORE != commands[curCommand+2]->getType()) | 53 RESTORE != canvas->getDrawCommandAt(curCommand+2)->getType()) { |
53 return false; | 54 return false; |
| 55 } |
54 | 56 |
55 SaveLayer* saveLayer = (SaveLayer*) commands[curCommand]; | 57 SaveLayer* saveLayer = (SaveLayer*) canvas->getDrawCommandAt(curCommand); |
56 DrawBitmapRect* dbmr = (DrawBitmapRect*) commands[curCommand+1]; | 58 DrawBitmapRect* dbmr = (DrawBitmapRect*) canvas->getDrawCommandAt(curCommand
+1); |
57 | 59 |
58 const SkPaint* saveLayerPaint = saveLayer->paint(); | 60 const SkPaint* saveLayerPaint = saveLayer->paint(); |
59 SkPaint* dbmrPaint = dbmr->paint(); | 61 SkPaint* dbmrPaint = dbmr->paint(); |
60 | 62 |
61 // For this optimization we only fold the saveLayer and drawBitmapRect | 63 // For this optimization we only fold the saveLayer and drawBitmapRect |
62 // together if the saveLayer's draw is simple (i.e., no fancy effects) and | 64 // together if the saveLayer's draw is simple (i.e., no fancy effects) and |
63 // and the only difference in the colors is that the saveLayer's can have | 65 // and the only difference in the colors is that the saveLayer's can have |
64 // an alpha while the drawBitmapRect's is opaque. | 66 // an alpha while the drawBitmapRect's is opaque. |
65 // TODO: it should be possible to fold them together even if they both | 67 // TODO: it should be possible to fold them together even if they both |
66 // have different non-255 alphas but this is low priority since we have | 68 // have different non-255 alphas but this is low priority since we have |
67 // never seen that case | 69 // never seen that case |
68 // If either operation lacks a paint then the collapse is trivial | 70 // If either operation lacks a paint then the collapse is trivial |
69 SkColor layerColor = saveLayerPaint->getColor() | 0xFF000000; // force opaqu
e | 71 SkColor layerColor = saveLayerPaint->getColor() | 0xFF000000; // force opaqu
e |
70 | 72 |
71 return NULL == saveLayerPaint || | 73 return NULL == saveLayerPaint || |
72 NULL == dbmrPaint || | 74 NULL == dbmrPaint || |
73 (is_simple(*saveLayerPaint) && dbmrPaint->getColor() == layerColor); | 75 (is_simple(*saveLayerPaint) && dbmrPaint->getColor() == layerColor); |
74 } | 76 } |
75 | 77 |
76 // Fold the saveLayer's alpha into the drawBitmapRect and remove the saveLayer | 78 // Fold the saveLayer's alpha into the drawBitmapRect and remove the saveLayer |
77 // and restore | 79 // and restore |
78 static void apply_0(SkTDArray<SkDrawCommand*>& commands, int curCommand) { | 80 static void apply_0(SkDebugCanvas* canvas, int curCommand) { |
79 SaveLayer* saveLayer = (SaveLayer*) commands[curCommand]; | 81 SaveLayer* saveLayer = (SaveLayer*) canvas->getDrawCommandAt(curCommand); |
80 DrawBitmapRect* dbmr = (DrawBitmapRect*) commands[curCommand+1]; | 82 const SkPaint* saveLayerPaint = saveLayer->paint(); |
81 Restore* restore = (Restore*) commands[curCommand+2]; | |
82 | 83 |
83 const SkPaint* saveLayerPaint = saveLayer->paint(); | 84 // if (NULL == saveLayerPaint) the dbmr's paint doesn't need to be changed |
84 SkPaint* dbmrPaint = dbmr->paint(); | 85 if (NULL != saveLayerPaint) { |
| 86 DrawBitmapRect* dbmr = (DrawBitmapRect*) canvas->getDrawCommandAt(curCom
mand+1); |
| 87 SkPaint* dbmrPaint = dbmr->paint(); |
85 | 88 |
86 if (NULL == saveLayerPaint) { | 89 if (NULL == dbmrPaint) { |
87 saveLayer->setVisible(false); | 90 // if the DBMR doesn't have a paint just use the saveLayer's |
88 restore->setVisible(false); | 91 dbmr->setPaint(*saveLayerPaint); |
89 } else if (NULL == dbmrPaint) { | 92 } else if (NULL != saveLayerPaint) { |
90 saveLayer->setVisible(false); | 93 SkColor newColor = SkColorSetA(dbmrPaint->getColor(), |
91 dbmr->setPaint(*saveLayerPaint); | 94 SkColorGetA(saveLayerPaint->getColor(
))); |
92 restore->setVisible(false); | 95 dbmrPaint->setColor(newColor); |
93 } else { | 96 } |
94 saveLayer->setVisible(false); | |
95 SkColor newColor = SkColorSetA(dbmrPaint->getColor(), | |
96 SkColorGetA(saveLayerPaint->getColor())); | |
97 dbmrPaint->setColor(newColor); | |
98 restore->setVisible(false); | |
99 } | 97 } |
| 98 |
| 99 canvas->deleteDrawCommandAt(curCommand+2); // restore |
| 100 canvas->deleteDrawCommandAt(curCommand); // saveLayer |
100 } | 101 } |
101 | 102 |
102 // Check for: | 103 // Check for: |
103 // SAVE_LAYER | 104 // SAVE_LAYER |
104 // SAVE | 105 // SAVE |
105 // CLIP_RECT | 106 // CLIP_RECT |
106 // DRAW_BITMAP_RECT_TO_RECT | 107 // DRAW_BITMAP_RECT_TO_RECT |
107 // RESTORE | 108 // RESTORE |
108 // RESTORE | 109 // RESTORE |
109 // where the saveLayer's color can be moved into the drawBitmapRect | 110 // where the saveLayer's color can be moved into the drawBitmapRect |
110 static bool check_1(const SkTDArray<SkDrawCommand*>& commands, int curCommand) { | 111 static bool check_1(SkDebugCanvas* canvas, int curCommand) { |
111 if (SAVE_LAYER != commands[curCommand]->getType() || | 112 if (SAVE_LAYER != canvas->getDrawCommandAt(curCommand)->getType() || |
112 commands.count() <= curCommand+5 || | 113 canvas->getSize() <= curCommand+5 || |
113 SAVE != commands[curCommand+1]->getType() || | 114 SAVE != canvas->getDrawCommandAt(curCommand+1)->getType() || |
114 CLIP_RECT != commands[curCommand+2]->getType() || | 115 CLIP_RECT != canvas->getDrawCommandAt(curCommand+2)->getType() || |
115 DRAW_BITMAP_RECT_TO_RECT != commands[curCommand+3]->getType() || | 116 DRAW_BITMAP_RECT_TO_RECT != canvas->getDrawCommandAt(curCommand+3)->getT
ype() || |
116 RESTORE != commands[curCommand+4]->getType() || | 117 RESTORE != canvas->getDrawCommandAt(curCommand+4)->getType() || |
117 RESTORE != commands[curCommand+5]->getType()) | 118 RESTORE != canvas->getDrawCommandAt(curCommand+5)->getType()) { |
118 return false; | 119 return false; |
| 120 } |
119 | 121 |
120 SaveLayer* saveLayer = (SaveLayer*) commands[curCommand]; | 122 SaveLayer* saveLayer = (SaveLayer*) canvas->getDrawCommandAt(curCommand); |
121 DrawBitmapRect* dbmr = (DrawBitmapRect*) commands[curCommand+3]; | 123 DrawBitmapRect* dbmr = (DrawBitmapRect*) canvas->getDrawCommandAt(curCommand
+3); |
122 | 124 |
123 const SkPaint* saveLayerPaint = saveLayer->paint(); | 125 const SkPaint* saveLayerPaint = saveLayer->paint(); |
124 SkPaint* dbmrPaint = dbmr->paint(); | 126 SkPaint* dbmrPaint = dbmr->paint(); |
125 | 127 |
126 // For this optimization we only fold the saveLayer and drawBitmapRect | 128 // For this optimization we only fold the saveLayer and drawBitmapRect |
127 // together if the saveLayer's draw is simple (i.e., no fancy effects) and | 129 // together if the saveLayer's draw is simple (i.e., no fancy effects) and |
128 // and the only difference in the colors is that the saveLayer's can have | 130 // and the only difference in the colors is that the saveLayer's can have |
129 // an alpha while the drawBitmapRect's is opaque. | 131 // an alpha while the drawBitmapRect's is opaque. |
130 // TODO: it should be possible to fold them together even if they both | 132 // TODO: it should be possible to fold them together even if they both |
131 // have different non-255 alphas but this is low priority since we have | 133 // have different non-255 alphas but this is low priority since we have |
132 // never seen that case | 134 // never seen that case |
133 // If either operation lacks a paint then the collapse is trivial | 135 // If either operation lacks a paint then the collapse is trivial |
134 SkColor layerColor = saveLayerPaint->getColor() | 0xFF000000; // force opaqu
e | 136 SkColor layerColor = saveLayerPaint->getColor() | 0xFF000000; // force opaqu
e |
135 | 137 |
136 return NULL == saveLayerPaint || | 138 return NULL == saveLayerPaint || |
137 NULL == dbmrPaint || | 139 NULL == dbmrPaint || |
138 (is_simple(*saveLayerPaint) && dbmrPaint->getColor() == layerColor); | 140 (is_simple(*saveLayerPaint) && dbmrPaint->getColor() == layerColor); |
139 } | 141 } |
140 | 142 |
141 // Fold the saveLayer's alpha into the drawBitmapRect and remove the saveLayer | 143 // Fold the saveLayer's alpha into the drawBitmapRect and remove the saveLayer |
142 // and restore | 144 // and restore |
143 static void apply_1(SkTDArray<SkDrawCommand*>& commands, int curCommand) { | 145 static void apply_1(SkDebugCanvas* canvas, int curCommand) { |
144 SaveLayer* saveLayer = (SaveLayer*) commands[curCommand]; | 146 SaveLayer* saveLayer = (SaveLayer*) canvas->getDrawCommandAt(curCommand); |
145 DrawBitmapRect* dbmr = (DrawBitmapRect*) commands[curCommand+3]; | 147 const SkPaint* saveLayerPaint = saveLayer->paint(); |
146 Restore* restore = (Restore*) commands[curCommand+5]; | |
147 | 148 |
148 const SkPaint* saveLayerPaint = saveLayer->paint(); | 149 // if (NULL == saveLayerPaint) the dbmr's paint doesn't need to be changed |
149 SkPaint* dbmrPaint = dbmr->paint(); | 150 if (NULL != saveLayerPaint) { |
| 151 DrawBitmapRect* dbmr = (DrawBitmapRect*) canvas->getDrawCommandAt(curCom
mand+3); |
| 152 SkPaint* dbmrPaint = dbmr->paint(); |
150 | 153 |
151 if (NULL == saveLayerPaint) { | 154 if (NULL == dbmrPaint) { |
152 saveLayer->setVisible(false); | 155 dbmr->setPaint(*saveLayerPaint); |
153 restore->setVisible(false); | 156 } else { |
154 } else if (NULL == dbmrPaint) { | 157 SkColor newColor = SkColorSetA(dbmrPaint->getColor(), |
155 saveLayer->setVisible(false); | 158 SkColorGetA(saveLayerPaint->getColor(
))); |
156 dbmr->setPaint(*saveLayerPaint); | 159 dbmrPaint->setColor(newColor); |
157 restore->setVisible(false); | 160 } |
158 } else { | |
159 saveLayer->setVisible(false); | |
160 SkColor newColor = SkColorSetA(dbmrPaint->getColor(), | |
161 SkColorGetA(saveLayerPaint->getColor())); | |
162 dbmrPaint->setColor(newColor); | |
163 restore->setVisible(false); | |
164 } | 161 } |
| 162 |
| 163 canvas->deleteDrawCommandAt(curCommand+5); // restore |
| 164 canvas->deleteDrawCommandAt(curCommand); // saveLayer |
165 } | 165 } |
166 | 166 |
167 // Check for: | 167 // Check for: |
168 // SAVE | 168 // SAVE |
169 // CLIP_RECT | 169 // CLIP_RECT |
170 // DRAW_RECT | 170 // DRAW_RECT |
171 // RESTORE | 171 // RESTORE |
172 // where the rect is entirely within the clip and the clip is an intersect | 172 // where the rect is entirely within the clip and the clip is an intersect |
173 static bool check_2(const SkTDArray<SkDrawCommand*>& commands, int curCommand) { | 173 static bool check_2(SkDebugCanvas* canvas, int curCommand) { |
174 if (SAVE != commands[curCommand]->getType() || | 174 if (SAVE != canvas->getDrawCommandAt(curCommand)->getType() || |
175 commands.count() <= curCommand+4 || | 175 canvas->getSize() <= curCommand+4 || |
176 CLIP_RECT != commands[curCommand+1]->getType() || | 176 CLIP_RECT != canvas->getDrawCommandAt(curCommand+1)->getType() || |
177 DRAW_RECT != commands[curCommand+2]->getType() || | 177 DRAW_RECT != canvas->getDrawCommandAt(curCommand+2)->getType() || |
178 RESTORE != commands[curCommand+3]->getType()) | 178 RESTORE != canvas->getDrawCommandAt(curCommand+3)->getType()) { |
179 return false; | 179 return false; |
| 180 } |
180 | 181 |
181 ClipRect* cr = (ClipRect*) commands[curCommand+1]; | 182 ClipRect* cr = (ClipRect*) canvas->getDrawCommandAt(curCommand+1); |
182 DrawRectC* dr = (DrawRectC*) commands[curCommand+2]; | 183 DrawRectC* dr = (DrawRectC*) canvas->getDrawCommandAt(curCommand+2); |
183 | 184 |
184 if (SkRegion::kIntersect_Op != cr->op()) { | 185 if (SkRegion::kIntersect_Op != cr->op()) { |
185 return false; | 186 return false; |
186 } | 187 } |
187 | 188 |
188 return cr->rect().contains(dr->rect()); | 189 return cr->rect().contains(dr->rect()); |
189 } | 190 } |
190 | 191 |
191 // Remove everything but the drawRect | 192 // Remove everything but the drawRect |
192 static void apply_2(SkTDArray<SkDrawCommand*>& commands, int curCommand) { | 193 static void apply_2(SkDebugCanvas* canvas, int curCommand) { |
193 Save* save = (Save*) commands[curCommand]; | 194 canvas->deleteDrawCommandAt(curCommand+3); // restore |
194 ClipRect* cr = (ClipRect*) commands[curCommand+1]; | 195 // drawRect |
195 Restore* restore = (Restore*) commands[curCommand+3]; | 196 canvas->deleteDrawCommandAt(curCommand+1); // clipRect |
196 | 197 canvas->deleteDrawCommandAt(curCommand); // save |
197 save->setVisible(false); | |
198 cr->setVisible(false); | |
199 // leave the drawRect alone | |
200 restore->setVisible(false); | |
201 } | 198 } |
202 | 199 |
203 // Check for: | 200 // Check for: |
204 // SAVE | 201 // SAVE |
205 // CLIP_RRECT | 202 // CLIP_RRECT |
206 // DRAW_RECT | 203 // DRAW_RECT |
207 // RESTORE | 204 // RESTORE |
208 // where the rect entirely encloses the clip | 205 // where the rect entirely encloses the clip |
209 static bool check_3(const SkTDArray<SkDrawCommand*>& commands, int curCommand) { | 206 static bool check_3(SkDebugCanvas* canvas, int curCommand) { |
210 if (SAVE != commands[curCommand]->getType() || | 207 if (SAVE != canvas->getDrawCommandAt(curCommand)->getType() || |
211 commands.count() <= curCommand+4 || | 208 canvas->getSize() <= curCommand+4 || |
212 CLIP_RRECT != commands[curCommand+1]->getType() || | 209 CLIP_RRECT != canvas->getDrawCommandAt(curCommand+1)->getType() || |
213 DRAW_RECT != commands[curCommand+2]->getType() || | 210 DRAW_RECT != canvas->getDrawCommandAt(curCommand+2)->getType() || |
214 RESTORE != commands[curCommand+3]->getType()) | 211 RESTORE != canvas->getDrawCommandAt(curCommand+3)->getType()) { |
215 return false; | 212 return false; |
| 213 } |
216 | 214 |
217 ClipRRect* crr = (ClipRRect*) commands[curCommand+1]; | 215 ClipRRect* crr = (ClipRRect*) canvas->getDrawCommandAt(curCommand+1); |
218 DrawRectC* dr = (DrawRectC*) commands[curCommand+2]; | 216 DrawRectC* dr = (DrawRectC*) canvas->getDrawCommandAt(curCommand+2); |
219 | 217 |
220 if (SkRegion::kIntersect_Op != crr->op()) { | 218 if (SkRegion::kIntersect_Op != crr->op()) { |
221 return false; | 219 return false; |
222 } | 220 } |
223 | 221 |
224 return dr->rect().contains(crr->rrect().rect()); | 222 return dr->rect().contains(crr->rrect().rect()); |
225 } | 223 } |
226 | 224 |
227 // Replace everything with a drawRRect with the paint from the drawRect | 225 // Replace everything with a drawRRect with the paint from the drawRect |
228 // and the AA settings from the clipRRect | 226 // and the AA settings from the clipRRect |
229 static void apply_3(SkTDArray<SkDrawCommand*>& commands, int curCommand) { | 227 static void apply_3(SkDebugCanvas* canvas, int curCommand) { |
230 Save* save = (Save*) commands[curCommand]; | |
231 ClipRRect* crr = (ClipRRect*) commands[curCommand+1]; | |
232 DrawRectC* dr = (DrawRectC*) commands[curCommand+2]; | |
233 Restore* restore = (Restore*) commands[curCommand+3]; | |
234 | 228 |
235 save->setVisible(false); | 229 canvas->deleteDrawCommandAt(curCommand+3); // restore |
236 crr->setVisible(false); | 230 |
237 dr->setVisible(false); | 231 ClipRRect* crr = (ClipRRect*) canvas->getDrawCommandAt(curCommand+1); |
238 restore->setVisible(false); | 232 DrawRectC* dr = (DrawRectC*) canvas->getDrawCommandAt(curCommand+2); |
239 | 233 |
240 // TODO: could skip paint re-creation if the AA settings already match | 234 // TODO: could skip paint re-creation if the AA settings already match |
241 SkPaint newPaint = dr->paint(); | 235 SkPaint newPaint = dr->paint(); |
242 newPaint.setAntiAlias(crr->doAA()); | 236 newPaint.setAntiAlias(crr->doAA()); |
243 DrawRRect* drr = new DrawRRect(crr->rrect(), newPaint); | 237 DrawRRect* drr = new DrawRRect(crr->rrect(), newPaint); |
244 commands[curCommand+2] = drr; | 238 canvas->setDrawCommandAt(curCommand+2, drr); |
| 239 |
| 240 canvas->deleteDrawCommandAt(curCommand+1); // clipRRect |
| 241 canvas->deleteDrawCommandAt(curCommand); // save |
245 } | 242 } |
246 | 243 |
247 // Check for: | 244 // Check for: |
248 // SAVE | 245 // SAVE |
249 // CLIP_RECT | 246 // CLIP_RECT |
250 // DRAW_BITMAP_RECT_TO_RECT | 247 // DRAW_BITMAP_RECT_TO_RECT |
251 // RESTORE | 248 // RESTORE |
252 // where the rect and drawBitmapRect dst exactly match | 249 // where the rect and drawBitmapRect dst exactly match |
253 static bool check_4(const SkTDArray<SkDrawCommand*>& commands, int curCommand) { | 250 static bool check_4(SkDebugCanvas* canvas, int curCommand) { |
254 if (SAVE != commands[curCommand]->getType() || | 251 if (SAVE != canvas->getDrawCommandAt(curCommand)->getType() || |
255 commands.count() <= curCommand+4 || | 252 canvas->getSize() <= curCommand+4 || |
256 CLIP_RECT != commands[curCommand+1]->getType() || | 253 CLIP_RECT != canvas->getDrawCommandAt(curCommand+1)->getType() || |
257 DRAW_BITMAP_RECT_TO_RECT != commands[curCommand+2]->getType() || | 254 DRAW_BITMAP_RECT_TO_RECT != canvas->getDrawCommandAt(curCommand+2)->getT
ype() || |
258 RESTORE != commands[curCommand+3]->getType()) | 255 RESTORE != canvas->getDrawCommandAt(curCommand+3)->getType()) { |
259 return false; | 256 return false; |
| 257 } |
260 | 258 |
261 ClipRect* cr = (ClipRect*) commands[curCommand+1]; | 259 ClipRect* cr = (ClipRect*) canvas->getDrawCommandAt(curCommand+1); |
262 DrawBitmapRect* dbmr = (DrawBitmapRect*) commands[curCommand+2]; | 260 DrawBitmapRect* dbmr = (DrawBitmapRect*) canvas->getDrawCommandAt(curComman
d+2); |
263 | 261 |
264 if (SkRegion::kIntersect_Op != cr->op()) { | 262 if (SkRegion::kIntersect_Op != cr->op()) { |
265 return false; | 263 return false; |
266 } | 264 } |
267 | 265 |
268 return dbmr->dstRect() == cr->rect(); | 266 return dbmr->dstRect() == cr->rect(); |
269 } | 267 } |
270 | 268 |
271 // Remove everything but the drawBitmapRect | 269 // Remove everything but the drawBitmapRect |
272 static void apply_4(SkTDArray<SkDrawCommand*>& commands, int curCommand) { | 270 static void apply_4(SkDebugCanvas* canvas, int curCommand) { |
273 Save* save = (Save*) commands[curCommand]; | 271 canvas->deleteDrawCommandAt(curCommand+3); // restore |
274 ClipRect* cr = (ClipRect*) commands[curCommand+1]; | 272 // drawBitmapRectToRect |
275 Restore* restore = (Restore*) commands[curCommand+3]; | 273 canvas->deleteDrawCommandAt(curCommand+1); // clipRect |
276 | 274 canvas->deleteDrawCommandAt(curCommand); // save |
277 save->setVisible(false); | |
278 cr->setVisible(false); | |
279 // leave drawBitmapRect alone | |
280 restore->setVisible(false); | |
281 } | 275 } |
282 | 276 |
283 // Check for: | 277 // Check for: |
284 // TRANSLATE | 278 // TRANSLATE |
285 // where the translate is zero | 279 // where the translate is zero |
286 static bool check_5(const SkTDArray<SkDrawCommand*>& commands, int curCommand) { | 280 static bool check_5(SkDebugCanvas* canvas, int curCommand) { |
287 if (TRANSLATE != commands[curCommand]->getType()) { | 281 if (TRANSLATE != canvas->getDrawCommandAt(curCommand)->getType()) { |
288 return false; | 282 return false; |
289 } | 283 } |
290 | 284 |
291 Translate* t = (Translate*) commands[curCommand]; | 285 Translate* t = (Translate*) canvas->getDrawCommandAt(curCommand); |
292 | 286 |
293 return 0 == t->x() && 0 == t->y(); | 287 return 0 == t->x() && 0 == t->y(); |
294 } | 288 } |
295 | 289 |
296 // Just remove the translate | 290 // Just remove the translate |
297 static void apply_5(SkTDArray<SkDrawCommand*>& commands, int curCommand) { | 291 static void apply_5(SkDebugCanvas* canvas, int curCommand) { |
298 Translate* t = (Translate*) commands[curCommand]; | 292 canvas->deleteDrawCommandAt(curCommand); // translate |
299 | |
300 t->setVisible(false); | |
301 } | 293 } |
302 | 294 |
303 // Check for: | 295 // Check for: |
304 // SCALE | 296 // SCALE |
305 // where the scale is 1,1 | 297 // where the scale is 1,1 |
306 static bool check_6(const SkTDArray<SkDrawCommand*>& commands, int curCommand) { | 298 static bool check_6(SkDebugCanvas* canvas, int curCommand) { |
307 if (SCALE != commands[curCommand]->getType()) { | 299 if (SCALE != canvas->getDrawCommandAt(curCommand)->getType()) { |
308 return false; | 300 return false; |
309 } | 301 } |
310 | 302 |
311 Scale* s = (Scale*) commands[curCommand]; | 303 Scale* s = (Scale*) canvas->getDrawCommandAt(curCommand); |
312 | 304 |
313 return SK_Scalar1 == s->x() && SK_Scalar1 == s->y(); | 305 return SK_Scalar1 == s->x() && SK_Scalar1 == s->y(); |
314 } | 306 } |
315 | 307 |
316 // Just remove the scale | 308 // Just remove the scale |
317 static void apply_6(SkTDArray<SkDrawCommand*>& commands, int curCommand) { | 309 static void apply_6(SkDebugCanvas* canvas, int curCommand) { |
318 Scale* s = (Scale*) commands[curCommand]; | 310 canvas->deleteDrawCommandAt(curCommand); // scale |
319 | |
320 s->setVisible(false); | |
321 } | 311 } |
322 | 312 |
323 // Check for: | 313 // Check for: |
324 // SAVE | 314 // SAVE |
325 // CLIP_RECT | 315 // CLIP_RECT |
326 // SAVE_LAYER | 316 // SAVE_LAYER |
327 // SAVE | 317 // SAVE |
328 // CLIP_RECT | 318 // CLIP_RECT |
329 // SAVE_LAYER | 319 // SAVE_LAYER |
330 // SAVE | 320 // SAVE |
331 // CLIP_RECT | 321 // CLIP_RECT |
332 // DRAWBITMAPRECTTORECT | 322 // DRAWBITMAPRECTTORECT |
333 // RESTORE | 323 // RESTORE |
334 // RESTORE | 324 // RESTORE |
335 // RESTORE | 325 // RESTORE |
336 // RESTORE | 326 // RESTORE |
337 // RESTORE | 327 // RESTORE |
338 // where: | 328 // where: |
339 // all the clipRect's are BW, nested, intersections | 329 // all the clipRect's are BW, nested, intersections |
340 // the drawBitmapRectToRect is a 1-1 copy from src to dest | 330 // the drawBitmapRectToRect is a 1-1 copy from src to dest |
341 // the last (smallest) clip rect is a subset of the drawBitmapRectToRect's
dest rect | 331 // the last (smallest) clip rect is a subset of the drawBitmapRectToRect's
dest rect |
342 // all the saveLayer's paints can be rolled into the drawBitmapRectToRect's
paint | 332 // all the saveLayer's paints can be rolled into the drawBitmapRectToRect's
paint |
343 // This pattern is used by Google spreadsheet when drawing the toolbar buttons | 333 // This pattern is used by Google spreadsheet when drawing the toolbar buttons |
344 static bool check_7(const SkTDArray<SkDrawCommand*>& commands, int curCommand) { | 334 static bool check_7(SkDebugCanvas* canvas, int curCommand) { |
345 if (SAVE != commands[curCommand]->getType() || | 335 if (SAVE != canvas->getDrawCommandAt(curCommand)->getType() || |
346 commands.count() <= curCommand+13 || | 336 canvas->getSize() <= curCommand+13 || |
347 CLIP_RECT != commands[curCommand+1]->getType() || | 337 CLIP_RECT != canvas->getDrawCommandAt(curCommand+1)->getType() || |
348 SAVE_LAYER != commands[curCommand+2]->getType() || | 338 SAVE_LAYER != canvas->getDrawCommandAt(curCommand+2)->getType() || |
349 SAVE != commands[curCommand+3]->getType() || | 339 SAVE != canvas->getDrawCommandAt(curCommand+3)->getType() || |
350 CLIP_RECT != commands[curCommand+4]->getType() || | 340 CLIP_RECT != canvas->getDrawCommandAt(curCommand+4)->getType() || |
351 SAVE_LAYER != commands[curCommand+5]->getType() || | 341 SAVE_LAYER != canvas->getDrawCommandAt(curCommand+5)->getType() || |
352 SAVE != commands[curCommand+6]->getType() || | 342 SAVE != canvas->getDrawCommandAt(curCommand+6)->getType() || |
353 CLIP_RECT != commands[curCommand+7]->getType() || | 343 CLIP_RECT != canvas->getDrawCommandAt(curCommand+7)->getType() || |
354 DRAW_BITMAP_RECT_TO_RECT != commands[curCommand+8]->getType() || | 344 DRAW_BITMAP_RECT_TO_RECT != canvas->getDrawCommandAt(curCommand+8)->getT
ype() || |
355 RESTORE != commands[curCommand+9]->getType() || | 345 RESTORE != canvas->getDrawCommandAt(curCommand+9)->getType() || |
356 RESTORE != commands[curCommand+10]->getType() || | 346 RESTORE != canvas->getDrawCommandAt(curCommand+10)->getType() || |
357 RESTORE != commands[curCommand+11]->getType() || | 347 RESTORE != canvas->getDrawCommandAt(curCommand+11)->getType() || |
358 RESTORE != commands[curCommand+12]->getType() || | 348 RESTORE != canvas->getDrawCommandAt(curCommand+12)->getType() || |
359 RESTORE != commands[curCommand+13]->getType()) | 349 RESTORE != canvas->getDrawCommandAt(curCommand+13)->getType()) { |
360 return false; | 350 return false; |
| 351 } |
361 | 352 |
362 ClipRect* clip0 = (ClipRect*) commands[curCommand+1]; | 353 ClipRect* clip0 = (ClipRect*) canvas->getDrawCommandAt(curCommand+1); |
363 SaveLayer* saveLayer0 = (SaveLayer*) commands[curCommand+2]; | 354 SaveLayer* saveLayer0 = (SaveLayer*) canvas->getDrawCommandAt(curCommand+2); |
364 ClipRect* clip1 = (ClipRect*) commands[curCommand+4]; | 355 ClipRect* clip1 = (ClipRect*) canvas->getDrawCommandAt(curCommand+4); |
365 SaveLayer* saveLayer1 = (SaveLayer*) commands[curCommand+5]; | 356 SaveLayer* saveLayer1 = (SaveLayer*) canvas->getDrawCommandAt(curCommand+5); |
366 ClipRect* clip2 = (ClipRect*) commands[curCommand+7]; | 357 ClipRect* clip2 = (ClipRect*) canvas->getDrawCommandAt(curCommand+7); |
367 DrawBitmapRect* dbmr = (DrawBitmapRect*) commands[curCommand+8]; | 358 DrawBitmapRect* dbmr = (DrawBitmapRect*) canvas->getDrawCommandAt(curCommand
+8); |
368 | 359 |
369 if (clip0->doAA() || clip1->doAA() || clip2->doAA()) { | 360 if (clip0->doAA() || clip1->doAA() || clip2->doAA()) { |
370 return false; | 361 return false; |
371 } | 362 } |
372 | 363 |
373 if (SkRegion::kIntersect_Op != clip0->op() || | 364 if (SkRegion::kIntersect_Op != clip0->op() || |
374 SkRegion::kIntersect_Op != clip1->op() || | 365 SkRegion::kIntersect_Op != clip1->op() || |
375 SkRegion::kIntersect_Op != clip2->op()) { | 366 SkRegion::kIntersect_Op != clip2->op()) { |
376 return false; | 367 return false; |
377 } | 368 } |
(...skipping 47 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
425 return false; | 416 return false; |
426 } | 417 } |
427 } | 418 } |
428 | 419 |
429 return true; | 420 return true; |
430 } | 421 } |
431 | 422 |
432 // Reduce to a single drawBitmapRectToRect call by folding the clipRect's into | 423 // Reduce to a single drawBitmapRectToRect call by folding the clipRect's into |
433 // the src and dst Rects and the saveLayer paints into the drawBitmapRectToRect'
s | 424 // the src and dst Rects and the saveLayer paints into the drawBitmapRectToRect'
s |
434 // paint. | 425 // paint. |
435 static void apply_7(SkTDArray<SkDrawCommand*>& commands, int curCommand) { | 426 static void apply_7(SkDebugCanvas* canvas, int curCommand) { |
436 Save* save0 = (Save*) commands[curCommand]; | 427 SaveLayer* saveLayer0 = (SaveLayer*) canvas->getDrawCommandAt(curCommand+2); |
437 ClipRect* clip0 = (ClipRect*) commands[curCommand+1]; | 428 SaveLayer* saveLayer1 = (SaveLayer*) canvas->getDrawCommandAt(curCommand+5); |
438 SaveLayer* saveLayer0 = (SaveLayer*) commands[curCommand+2]; | 429 ClipRect* clip2 = (ClipRect*) canvas->getDrawCommandAt(curCommand+7); |
439 Save* save1 = (Save*) commands[curCommand+3]; | 430 DrawBitmapRect* dbmr = (DrawBitmapRect*) canvas->getDrawCommandAt(curCommand
+8); |
440 ClipRect* clip1 = (ClipRect*) commands[curCommand+4]; | |
441 SaveLayer* saveLayer1 = (SaveLayer*) commands[curCommand+5]; | |
442 Save* save2 = (Save*) commands[curCommand+6]; | |
443 ClipRect* clip2 = (ClipRect*) commands[curCommand+7]; | |
444 DrawBitmapRect* dbmr = (DrawBitmapRect*) commands[curCommand+8]; | |
445 Restore* restore0 = (Restore*) commands[curCommand+9]; | |
446 Restore* restore1 = (Restore*) commands[curCommand+10]; | |
447 Restore* restore2 = (Restore*) commands[curCommand+11]; | |
448 Restore* restore3 = (Restore*) commands[curCommand+12]; | |
449 Restore* restore4 = (Restore*) commands[curCommand+13]; | |
450 | 431 |
451 SkScalar newSrcLeft = dbmr->srcRect()->fLeft + clip2->rect().fLeft - dbmr->d
stRect().fLeft; | 432 SkScalar newSrcLeft = dbmr->srcRect()->fLeft + clip2->rect().fLeft - dbmr->d
stRect().fLeft; |
452 SkScalar newSrcTop = dbmr->srcRect()->fTop + clip2->rect().fTop - dbmr->dstR
ect().fTop; | 433 SkScalar newSrcTop = dbmr->srcRect()->fTop + clip2->rect().fTop - dbmr->dstR
ect().fTop; |
453 | 434 |
454 SkRect newSrc = SkRect::MakeXYWH(newSrcLeft, newSrcTop, | 435 SkRect newSrc = SkRect::MakeXYWH(newSrcLeft, newSrcTop, |
455 clip2->rect().width(), clip2->rect().height
()); | 436 clip2->rect().width(), clip2->rect().height
()); |
456 | 437 |
457 dbmr->setSrcRect(newSrc); | 438 dbmr->setSrcRect(newSrc); |
458 dbmr->setDstRect(clip2->rect()); | 439 dbmr->setDstRect(clip2->rect()); |
459 | 440 |
(...skipping 26 matching lines...) Expand all Loading... |
486 dbmrPaint->setColor(newColor); | 467 dbmrPaint->setColor(newColor); |
487 } else { | 468 } else { |
488 SkColor newColor = SkColorSetA(color, newA); | 469 SkColor newColor = SkColorSetA(color, newA); |
489 | 470 |
490 SkPaint newPaint; | 471 SkPaint newPaint; |
491 newPaint.setColor(newColor); | 472 newPaint.setColor(newColor); |
492 dbmr->setPaint(newPaint); | 473 dbmr->setPaint(newPaint); |
493 } | 474 } |
494 | 475 |
495 // remove everything except the drawbitmaprect | 476 // remove everything except the drawbitmaprect |
496 save0->setVisible(false); | 477 canvas->deleteDrawCommandAt(curCommand+13); // restore |
497 clip0->setVisible(false); | 478 canvas->deleteDrawCommandAt(curCommand+12); // restore |
498 saveLayer0->setVisible(false); | 479 canvas->deleteDrawCommandAt(curCommand+11); // restore |
499 save1->setVisible(false); | 480 canvas->deleteDrawCommandAt(curCommand+10); // restore |
500 clip1->setVisible(false); | 481 canvas->deleteDrawCommandAt(curCommand+9); // restore |
501 saveLayer1->setVisible(false); | 482 canvas->deleteDrawCommandAt(curCommand+7); // clipRect |
502 save2->setVisible(false); | 483 canvas->deleteDrawCommandAt(curCommand+6); // save |
503 clip2->setVisible(false); | 484 canvas->deleteDrawCommandAt(curCommand+5); // saveLayer |
504 restore0->setVisible(false); | 485 canvas->deleteDrawCommandAt(curCommand+4); // clipRect |
505 restore1->setVisible(false); | 486 canvas->deleteDrawCommandAt(curCommand+3); // save |
506 restore2->setVisible(false); | 487 canvas->deleteDrawCommandAt(curCommand+2); // saveLayer |
507 restore3->setVisible(false); | 488 canvas->deleteDrawCommandAt(curCommand+1); // clipRect |
508 restore4->setVisible(false); | 489 canvas->deleteDrawCommandAt(curCommand); // save |
509 } | 490 } |
510 | 491 |
511 typedef bool (*PFCheck)(const SkTDArray<SkDrawCommand*>& commands, int curComman
d); | 492 typedef bool (*PFCheck)(SkDebugCanvas* canvas, int curCommand); |
512 typedef void (*PFApply)(SkTDArray<SkDrawCommand*>& commands, int curCommand); | 493 typedef void (*PFApply)(SkDebugCanvas* canvas, int curCommand); |
513 | 494 |
514 struct OptTableEntry { | 495 struct OptTableEntry { |
515 PFCheck fCheck; | 496 PFCheck fCheck; |
516 PFApply fApply; | 497 PFApply fApply; |
517 int fNumTimesApplied; | 498 int fNumTimesApplied; |
518 } gOptTable[] = { | 499 } gOptTable[] = { |
519 { check_0, apply_0, 0 }, | 500 { check_0, apply_0, 0 }, |
520 { check_1, apply_1, 0 }, | 501 { check_1, apply_1, 0 }, |
521 { check_2, apply_2, 0 }, | 502 { check_2, apply_2, 0 }, |
522 { check_3, apply_3, 0 }, | 503 { check_3, apply_3, 0 }, |
523 { check_4, apply_4, 0 }, | 504 { check_4, apply_4, 0 }, |
524 { check_5, apply_5, 0 }, | 505 { check_5, apply_5, 0 }, |
525 { check_6, apply_6, 0 }, | 506 { check_6, apply_6, 0 }, |
526 { check_7, apply_7, 0 }, | 507 { check_7, apply_7, 0 }, |
527 }; | 508 }; |
528 | 509 |
| 510 |
529 static int filter_picture(const SkString& inFile, const SkString& outFile) { | 511 static int filter_picture(const SkString& inFile, const SkString& outFile) { |
530 SkPicture* inPicture = NULL; | 512 SkPicture* inPicture = NULL; |
531 | 513 |
532 SkFILEStream inStream(inFile.c_str()); | 514 SkFILEStream inStream(inFile.c_str()); |
533 if (inStream.isValid()) { | 515 if (inStream.isValid()) { |
534 inPicture = SkNEW_ARGS(SkPicture, (&inStream, NULL, &SkImageDecoder::Dec
odeMemory)); | 516 inPicture = SkNEW_ARGS(SkPicture, (&inStream, NULL, &SkImageDecoder::Dec
odeMemory)); |
535 } | 517 } |
536 | 518 |
537 if (NULL == inPicture) { | 519 if (NULL == inPicture) { |
538 SkDebugf("Could not read file %s\n", inFile.c_str()); | 520 SkDebugf("Could not read file %s\n", inFile.c_str()); |
539 return -1; | 521 return -1; |
540 } | 522 } |
541 | 523 |
542 int localCount[SK_ARRAY_COUNT(gOptTable)]; | 524 int localCount[SK_ARRAY_COUNT(gOptTable)]; |
543 | 525 |
544 memset(localCount, 0, sizeof(localCount)); | 526 memset(localCount, 0, sizeof(localCount)); |
545 | 527 |
546 SkDebugCanvas debugCanvas(inPicture->width(), inPicture->height()); | 528 SkDebugCanvas debugCanvas(inPicture->width(), inPicture->height()); |
547 debugCanvas.setBounds(inPicture->width(), inPicture->height()); | 529 debugCanvas.setBounds(inPicture->width(), inPicture->height()); |
548 inPicture->draw(&debugCanvas); | 530 inPicture->draw(&debugCanvas); |
549 | 531 |
550 SkTDArray<SkDrawCommand*>& commands = debugCanvas.getDrawCommands(); | 532 // delete the initial save and restore since replaying the commands will |
551 | |
552 // hide the initial save and restore since replaying the commands will | |
553 // re-add them | 533 // re-add them |
554 if (commands.count() > 0) { | 534 if (debugCanvas.getSize() > 1) { |
555 commands[0]->setVisible(false); | 535 debugCanvas.deleteDrawCommandAt(0); |
556 commands[commands.count()-1]->setVisible(false); | 536 debugCanvas.deleteDrawCommandAt(debugCanvas.getSize()-1); |
557 } | 537 } |
558 | 538 |
559 for (int i = 0; i < commands.count(); ++i) { | 539 for (int i = 0; i < debugCanvas.getSize(); ++i) { |
560 for (size_t opt = 0; opt < SK_ARRAY_COUNT(gOptTable); ++opt) { | 540 for (size_t opt = 0; opt < SK_ARRAY_COUNT(gOptTable); ++opt) { |
561 if ((*gOptTable[opt].fCheck)(commands, i)) { | 541 if ((*gOptTable[opt].fCheck)(&debugCanvas, i)) { |
562 (*gOptTable[opt].fApply)(commands, i); | 542 (*gOptTable[opt].fApply)(&debugCanvas, i); |
563 ++gOptTable[opt].fNumTimesApplied; | 543 ++gOptTable[opt].fNumTimesApplied; |
564 ++localCount[opt]; | 544 ++localCount[opt]; |
565 } | 545 } |
566 } | 546 } |
567 } | 547 } |
568 | 548 |
569 if (!outFile.isEmpty()) { | 549 if (!outFile.isEmpty()) { |
570 SkPicture outPicture; | 550 SkPicture outPicture; |
571 | 551 |
572 SkCanvas* canvas = outPicture.beginRecording(inPicture->width(), inPictu
re->height()); | 552 SkCanvas* canvas = outPicture.beginRecording(inPicture->width(), inPictu
re->height()); |
(...skipping 111 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
684 | 664 |
685 SkGraphics::Term(); | 665 SkGraphics::Term(); |
686 return 0; | 666 return 0; |
687 } | 667 } |
688 | 668 |
689 #if !defined SK_BUILD_FOR_IOS | 669 #if !defined SK_BUILD_FOR_IOS |
690 int main(int argc, char * const argv[]) { | 670 int main(int argc, char * const argv[]) { |
691 return tool_main(argc, (char**) argv); | 671 return tool_main(argc, (char**) argv); |
692 } | 672 } |
693 #endif | 673 #endif |
OLD | NEW |