OLD | NEW |
1 /* | 1 /* |
2 * Copyright 2014 Google Inc. | 2 * Copyright 2014 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 "SkRecordDraw.h" | 8 #include "SkRecordDraw.h" |
9 #include "SkTSort.h" | 9 #include "SkTSort.h" |
10 | 10 |
(...skipping 186 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
197 this->updateSaveBounds(fBounds[fCurrentOp]); | 197 this->updateSaveBounds(fBounds[fCurrentOp]); |
198 } | 198 } |
199 | 199 |
200 void pushSaveBlock(const SkPaint* paint) { | 200 void pushSaveBlock(const SkPaint* paint) { |
201 // Starting a new Save block. Push a new entry to represent that. | 201 // Starting a new Save block. Push a new entry to represent that. |
202 SaveBounds sb = { 0, SkIRect::MakeEmpty(), paint }; | 202 SaveBounds sb = { 0, SkIRect::MakeEmpty(), paint }; |
203 fSaveStack.push(sb); | 203 fSaveStack.push(sb); |
204 this->pushControl(); | 204 this->pushControl(); |
205 } | 205 } |
206 | 206 |
| 207 static bool PaintMayAffectTransparentBlack(const SkPaint* paint) { |
| 208 // FIXME: this is very conservative |
| 209 return paint && (paint->getImageFilter() || paint->getColorFilter()); |
| 210 } |
| 211 |
207 SkIRect popSaveBlock() { | 212 SkIRect popSaveBlock() { |
208 // We're done the Save block. Apply the block's bounds to all control o
ps inside it. | 213 // We're done the Save block. Apply the block's bounds to all control o
ps inside it. |
209 SaveBounds sb; | 214 SaveBounds sb; |
210 fSaveStack.pop(&sb); | 215 fSaveStack.pop(&sb); |
| 216 |
| 217 // If the paint affects transparent black, we can't trust any of our cal
culated bounds. |
| 218 const SkIRect& bounds = |
| 219 PaintMayAffectTransparentBlack(sb.paint) ? fCurrentClipBounds : sb.b
ounds; |
| 220 |
211 while (sb.controlOps --> 0) { | 221 while (sb.controlOps --> 0) { |
212 this->popControl(sb.bounds); | 222 this->popControl(bounds); |
213 } | 223 } |
214 | 224 |
215 // This whole Save block may be part another Save block. | 225 // This whole Save block may be part another Save block. |
216 this->updateSaveBounds(sb.bounds); | 226 this->updateSaveBounds(bounds); |
217 | 227 |
218 // If called from a real Restore (not a phony one for balance), it'll ne
ed the bounds. | 228 // If called from a real Restore (not a phony one for balance), it'll ne
ed the bounds. |
219 return sb.bounds; | 229 return bounds; |
220 } | 230 } |
221 | 231 |
222 void pushControl() { | 232 void pushControl() { |
223 fControlIndices.push(fCurrentOp); | 233 fControlIndices.push(fCurrentOp); |
224 if (!fSaveStack.isEmpty()) { | 234 if (!fSaveStack.isEmpty()) { |
225 fSaveStack.top().controlOps++; | 235 fSaveStack.top().controlOps++; |
226 } | 236 } |
227 } | 237 } |
228 | 238 |
229 void popControl(const SkIRect& bounds) { | 239 void popControl(const SkIRect& bounds) { |
(...skipping 160 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
390 // Used to track the bounds of Save/Restore blocks and the control ops insid
e them. | 400 // Used to track the bounds of Save/Restore blocks and the control ops insid
e them. |
391 SkTDArray<SaveBounds> fSaveStack; | 401 SkTDArray<SaveBounds> fSaveStack; |
392 SkTDArray<unsigned> fControlIndices; | 402 SkTDArray<unsigned> fControlIndices; |
393 }; | 403 }; |
394 | 404 |
395 } // namespace SkRecords | 405 } // namespace SkRecords |
396 | 406 |
397 void SkRecordFillBounds(const SkRecord& record, SkBBoxHierarchy* bbh) { | 407 void SkRecordFillBounds(const SkRecord& record, SkBBoxHierarchy* bbh) { |
398 SkRecords::FillBounds(record, bbh); | 408 SkRecords::FillBounds(record, bbh); |
399 } | 409 } |
OLD | NEW |