| OLD | NEW |
| 1 /* | 1 /* |
| 2 * Copyright 2015 Google Inc. | 2 * Copyright 2015 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 // Some shared code used by both SkBigPicture and SkMiniPicture. | 8 // Some shared code used by both SkBigPicture and SkMiniPicture. |
| 9 // SkTextHunter -- SkRecord visitor that returns true when the op draws text
. | 9 // SkTextHunter -- SkRecord visitor that returns true when the op draws text
. |
| 10 // SkBitmapHunter -- SkRecord visitor that returns true when the op draws a bi
tmap or image. | 10 // SkBitmapHunter -- SkRecord visitor that returns true when the op draws a bi
tmap or image. |
| 11 // SkPathCounter -- SkRecord visitor that counts paths that draw slowly on th
e GPU. | 11 // SkPathCounter -- SkRecord visitor that counts paths that draw slowly on th
e GPU. |
| 12 | 12 |
| 13 #include "SkPathEffect.h" | 13 #include "SkPathEffect.h" |
| 14 #include "SkRecords.h" | 14 #include "SkRecords.h" |
| 15 #include "SkTLogic.h" | 15 #include "SkTLogic.h" |
| 16 | 16 |
| 17 struct SkTextHunter { | 17 struct SkTextHunter { |
| 18 // Most ops never have text. Some always do. Subpictures know themeselves. | 18 // Most ops never have text. Some always do. Subpictures know themeselves. |
| 19 template <typename T> bool operator()(const T&) { return false; } | |
| 20 bool operator()(const SkRecords::DrawPosText&) { return true; } | |
| 21 bool operator()(const SkRecords::DrawPosTextH&) { return true; } | |
| 22 bool operator()(const SkRecords::DrawText&) { return true; } | |
| 23 bool operator()(const SkRecords::DrawTextBlob&) { return true; } | |
| 24 bool operator()(const SkRecords::DrawTextOnPath&) { return true; } | |
| 25 bool operator()(const SkRecords::DrawPicture& op) { return op.picture->hasTe
xt(); } | 19 bool operator()(const SkRecords::DrawPicture& op) { return op.picture->hasTe
xt(); } |
| 20 bool operator()(const SkRecords::DrawDrawable&) { /*TODO*/ return false; } |
| 21 |
| 22 template <typename T> |
| 23 SK_WHEN(T::kTags & SkRecords::kHasText_Tag, bool) operator()(const T&) { ret
urn true; } |
| 24 template <typename T> |
| 25 SK_WHEN(!(T::kTags & SkRecords::kHasText_Tag), bool) operator()(const T&) {
return false; } |
| 26 }; | 26 }; |
| 27 | 27 |
| 28 | 28 |
| 29 // N.B. This name is slightly historical: hunting season is now open for SkImage
s too. | 29 // N.B. This name is slightly historical: hunting season is now open for SkImage
s too. |
| 30 struct SkBitmapHunter { | 30 struct SkBitmapHunter { |
| 31 // Helpers. These let us detect the presence of struct members with particu
lar names. | |
| 32 SK_CREATE_MEMBER_DETECTOR(bitmap); | |
| 33 SK_CREATE_MEMBER_DETECTOR(image); | |
| 34 SK_CREATE_MEMBER_DETECTOR(paint); | |
| 35 | |
| 36 template <typename T> | |
| 37 struct HasMember_bitmap_or_image { | |
| 38 static const bool value = HasMember_bitmap<T>::value || HasMember_image<
T>::value; | |
| 39 }; | |
| 40 | |
| 41 // Some ops have a paint, some have an optional paint. Either way, get back
a pointer. | 31 // Some ops have a paint, some have an optional paint. Either way, get back
a pointer. |
| 42 static const SkPaint* AsPtr(const SkPaint& p) { return &p; } | 32 static const SkPaint* AsPtr(const SkPaint& p) { return &p; } |
| 43 static const SkPaint* AsPtr(const SkRecords::Optional<SkPaint>& p) { return
p; } | 33 static const SkPaint* AsPtr(const SkRecords::Optional<SkPaint>& p) { return
p; } |
| 44 | 34 |
| 45 // Main entry for visitor: | 35 // Main entry for visitor: |
| 46 // If the op is a DrawPicture, recurse. | 36 // If the op is a DrawPicture, recurse. |
| 47 // If the op has a bitmap or image directly, return true. | 37 // If the op has a bitmap or image directly, return true. |
| 48 // If the op has a paint and the paint has a bitmap, return true. | 38 // If the op has a paint and the paint has a bitmap, return true. |
| 49 // Otherwise, return false. | 39 // Otherwise, return false. |
| 50 bool operator()(const SkRecords::DrawPicture& op) { return op.picture->willP
layBackBitmaps(); } | 40 bool operator()(const SkRecords::DrawPicture& op) { return op.picture->willP
layBackBitmaps(); } |
| 41 bool operator()(const SkRecords::DrawDrawable&) { /*TODO*/ return false; } |
| 51 | 42 |
| 52 template <typename T> | 43 template <typename T> |
| 53 bool operator()(const T& r) { return CheckBitmap(r); } | 44 bool operator()(const T& op) { return CheckBitmap(op); } |
| 54 | 45 |
| 55 // If the op has a bitmap, of course we're going to play back bitmaps. | 46 // If the op is tagged as having an image, return true. |
| 56 template <typename T> | 47 template <typename T> |
| 57 static SK_WHEN(HasMember_bitmap_or_image<T>, bool) CheckBitmap(const T&) { | 48 static SK_WHEN(T::kTags & SkRecords::kHasImage_Tag, bool) CheckBitmap(const
T&) { |
| 58 return true; | 49 return true; |
| 59 } | 50 } |
| 60 | 51 |
| 61 // If not, look for one in its paint (if it has a paint). | 52 // If not, look for one in its paint (if it has a paint). |
| 62 template <typename T> | 53 template <typename T> |
| 63 static SK_WHEN(!HasMember_bitmap_or_image<T>, bool) CheckBitmap(const T& r)
{ | 54 static SK_WHEN(!(T::kTags & SkRecords::kHasImage_Tag), bool) CheckBitmap(con
st T& op) { |
| 64 return CheckPaint(r); | 55 return CheckPaint(op); |
| 65 } | 56 } |
| 66 | 57 |
| 67 // If we have a paint, dig down into the effects looking for a bitmap. | 58 // Most draws-type ops have paints. |
| 68 template <typename T> | 59 template <typename T> |
| 69 static SK_WHEN(HasMember_paint<T>, bool) CheckPaint(const T& r) { | 60 static SK_WHEN(T::kTags & SkRecords::kDraw_Tag, bool) CheckPaint(const T& op
) { |
| 70 const SkPaint* paint = AsPtr(r.paint); | 61 return PaintHasBitmap(AsPtr(op.paint)); |
| 62 } |
| 63 |
| 64 // SaveLayers also have a paint to check. |
| 65 static bool CheckPaint(const SkRecords::SaveLayer& op) { |
| 66 return PaintHasBitmap(AsPtr(op.paint)); |
| 67 } |
| 68 |
| 69 // Shouldn't be any non-Draw non-SaveLayer ops with paints. |
| 70 template <typename T> |
| 71 static SK_WHEN(!(T::kTags & SkRecords::kDraw_Tag), bool) CheckPaint(const T&
) { |
| 72 return false; |
| 73 } |
| 74 |
| 75 private: |
| 76 static bool PaintHasBitmap(const SkPaint* paint) { |
| 71 if (paint) { | 77 if (paint) { |
| 72 const SkShader* shader = paint->getShader(); | 78 const SkShader* shader = paint->getShader(); |
| 73 if (shader && shader->isABitmap()) { | 79 if (shader && shader->isABitmap()) { |
| 74 return true; | 80 return true; |
| 75 } | 81 } |
| 76 } | 82 } |
| 77 return false; | 83 return false; |
| 78 } | 84 } |
| 79 | |
| 80 // If we don't have a paint, that non-paint has no bitmap. | |
| 81 template <typename T> | |
| 82 static SK_WHEN(!HasMember_paint<T>, bool) CheckPaint(const T&) { return fals
e; } | |
| 83 }; | 85 }; |
| 84 | 86 |
| 85 // TODO: might be nicer to have operator() return an int (the number of slow pat
hs) ? | 87 // TODO: might be nicer to have operator() return an int (the number of slow pat
hs) ? |
| 86 struct SkPathCounter { | 88 struct SkPathCounter { |
| 87 SK_CREATE_MEMBER_DETECTOR(paint); | |
| 88 | |
| 89 // Some ops have a paint, some have an optional paint. Either way, get back
a pointer. | 89 // Some ops have a paint, some have an optional paint. Either way, get back
a pointer. |
| 90 static const SkPaint* AsPtr(const SkPaint& p) { return &p; } | 90 static const SkPaint* AsPtr(const SkPaint& p) { return &p; } |
| 91 static const SkPaint* AsPtr(const SkRecords::Optional<SkPaint>& p) { return
p; } | 91 static const SkPaint* AsPtr(const SkRecords::Optional<SkPaint>& p) { return
p; } |
| 92 | 92 |
| 93 SkPathCounter() : fNumSlowPathsAndDashEffects(0) {} | 93 SkPathCounter() : fNumSlowPathsAndDashEffects(0) {} |
| 94 | 94 |
| 95 // Recurse into nested pictures. | 95 // Recurse into nested pictures. |
| 96 void operator()(const SkRecords::DrawPicture& op) { | 96 void operator()(const SkRecords::DrawPicture& op) { |
| 97 fNumSlowPathsAndDashEffects += op.picture->numSlowPaths(); | 97 fNumSlowPathsAndDashEffects += op.picture->numSlowPaths(); |
| 98 } | 98 } |
| 99 void operator()(const SkRecords::DrawDrawable&) { /* TODO */ } |
| 99 | 100 |
| 100 void checkPaint(const SkPaint* paint) { | 101 void checkPaint(const SkPaint* paint) { |
| 101 if (paint && paint->getPathEffect()) { | 102 if (paint && paint->getPathEffect()) { |
| 102 // Initially assume it's slow. | 103 // Initially assume it's slow. |
| 103 fNumSlowPathsAndDashEffects++; | 104 fNumSlowPathsAndDashEffects++; |
| 104 } | 105 } |
| 105 } | 106 } |
| 106 | 107 |
| 107 void operator()(const SkRecords::DrawPoints& op) { | 108 void operator()(const SkRecords::DrawPoints& op) { |
| 108 this->checkPaint(&op.paint); | 109 this->checkPaint(&op.paint); |
| (...skipping 18 matching lines...) Expand all Loading... |
| 127 // AA hairline concave path is not slow. | 128 // AA hairline concave path is not slow. |
| 128 } else if (SkPaint::kFill_Style == paintStyle && pathBounds.width()
< 64.f && | 129 } else if (SkPaint::kFill_Style == paintStyle && pathBounds.width()
< 64.f && |
| 129 pathBounds.height() < 64.f && !op.path.isVolatile()) { | 130 pathBounds.height() < 64.f && !op.path.isVolatile()) { |
| 130 // AADF eligible concave path is not slow. | 131 // AADF eligible concave path is not slow. |
| 131 } else { | 132 } else { |
| 132 fNumSlowPathsAndDashEffects++; | 133 fNumSlowPathsAndDashEffects++; |
| 133 } | 134 } |
| 134 } | 135 } |
| 135 } | 136 } |
| 136 | 137 |
| 137 template <typename T> | 138 void operator()(const SkRecords::SaveLayer& op) { |
| 138 SK_WHEN(HasMember_paint<T>, void) operator()(const T& op) { | |
| 139 this->checkPaint(AsPtr(op.paint)); | 139 this->checkPaint(AsPtr(op.paint)); |
| 140 } | 140 } |
| 141 | 141 |
| 142 template <typename T> | 142 template <typename T> |
| 143 SK_WHEN(!HasMember_paint<T>, void) operator()(const T& op) { /* do nothing *
/ } | 143 SK_WHEN(T::kTags & SkRecords::kDraw_Tag, void) operator()(const T& op) { |
| 144 this->checkPaint(AsPtr(op.paint)); |
| 145 } |
| 146 |
| 147 template <typename T> |
| 148 SK_WHEN(!(T::kTags & SkRecords::kDraw_Tag), void) operator()(const T& op) {
/* do nothing */ } |
| 144 | 149 |
| 145 int fNumSlowPathsAndDashEffects; | 150 int fNumSlowPathsAndDashEffects; |
| 146 }; | 151 }; |
| OLD | NEW |