Chromium Code Reviews| Index: src/core/SkRecordOpts.cpp |
| diff --git a/src/core/SkRecordOpts.cpp b/src/core/SkRecordOpts.cpp |
| index 8faa45ce562201ac0c3029d06d2abf8f0f2acffe..2eef11f6e390d9bbdb4cd851583d1e78eb1e6881 100644 |
| --- a/src/core/SkRecordOpts.cpp |
| +++ b/src/core/SkRecordOpts.cpp |
| @@ -13,17 +13,6 @@ |
| using namespace SkRecords; |
| -void SkRecordOptimize(SkRecord* record) { |
| - // This might be useful as a first pass in the future if we want to weed |
| - // out junk for other optimization passes. Right now, nothing needs it, |
| - // and the bounding box hierarchy will do the work of skipping no-op |
| - // Save-NoDraw-Restore sequences better than we can here. |
| - //SkRecordNoopSaveRestores(record); |
| - |
| - SkRecordNoopSaveLayerDrawRestores(record); |
| - SkRecordMergeSvgOpacityAndFilterLayers(record); |
| -} |
| - |
| // Most of the optimizations in this file are pattern-based. These are all defined as structs with: |
| // - a Pattern typedef |
| // - a bool onMatch(SkRceord*, Pattern*, int begin, int end) method, |
| @@ -44,6 +33,61 @@ static bool apply(Pass* pass, SkRecord* record) { |
| return changed; |
| } |
| +/////////////////////////////////////////////////////////////////////////////////////////////////// |
| + |
| +struct MultipleSetMatrixNooper { |
| + typedef Pattern2<Is<SetMatrix>, |
| + // TODO: tried Star<Or<Is<Noop>, Is<SetMatrix>>>, but it seemed to not match |
|
mtklein
2015/11/19 16:26:56
After refamiliarizing myself with how these patter
reed1
2015/11/19 17:29:44
Done.
Does this mean I should loop myself, or is
|
| + Is<SetMatrix> > |
| + Pattern; |
| + |
| + bool onMatch(SkRecord* record, Pattern* pattern, int begin, int end) { |
| + SkASSERT(begin + 2 == end); |
| + record->replace<NoOp>(begin); // SetMatrix |
| + return true; |
| + } |
| +}; |
| +static void multiple_set_matrices(SkRecord* record) { |
|
mtklein
2015/11/19 16:26:56
I've found it butt-saving to have each pass unit t
|
| + MultipleSetMatrixNooper pass; |
|
mtklein
2015/11/19 16:26:56
Might want to move the struct in here too like wit
reed1
2015/11/19 17:29:44
Done.
|
| + |
| + // No need to loop, as we never "open up" opportunities for more of this type of optimization. |
| + apply(&pass, record); |
| +} |
| + |
| +/////////////////////////////////////////////////////////////////////////////////////////////////// |
| + |
| +#if 0 // experimental, but needs knowledge of previous matrix to operate correctly |
| +static void apply_matrix_to_draw_params(SkRecord* record) { |
| + struct { |
| + typedef Pattern3<Is<SetMatrix>, |
| + Is<DrawBitmapRect>, |
| + Is<Restore> > |
| + Pattern; |
| + |
| + bool onMatch(SkRecord* record, Pattern* pattern, int begin, int end) { |
| + const SkMatrix& m = pattern->first<SetMatrix>()->matrix; |
| + if (m.getType() > (SkMatrix::kScale_Mask | SkMatrix::kTranslate_Mask)) { |
| + SkDebugf("too complex\n"); |
| + return false; // can't handle rotation or perspective |
| + } |
| + if (m.getScaleX() < 0 || m.getScaleY() < 0) { |
| + SkDebugf("negative\n"); |
| + return false; // can't represent a flip in a rect |
| + } |
| + DrawBitmapRect* dbr = pattern->second<DrawBitmapRect>(); |
| + m.dump(); |
| + // wack the rect, and eliminate the matrix |
| + m.mapRect(&dbr->dst); |
| + record->replace<NoOp>(begin); |
| + return true; |
| + } |
| + } pass; |
| + apply(&pass, record); |
| +} |
| +#endif |
| + |
| +/////////////////////////////////////////////////////////////////////////////////////////////////// |
| + |
| // Turns the logical NoOp Save and Restore in Save-Draw*-Restore patterns into actual NoOps. |
| struct SaveOnlyDrawsRestoreNooper { |
| typedef Pattern3<Is<Save>, |
| @@ -230,3 +274,26 @@ void SkRecordMergeSvgOpacityAndFilterLayers(SkRecord* record) { |
| SvgOpacityAndFilterLayerMergePass pass; |
| apply(&pass, record); |
| } |
| + |
| +/////////////////////////////////////////////////////////////////////////////////////////////////// |
| + |
| +void SkRecordOptimize(SkRecord* record) { |
| + // This might be useful as a first pass in the future if we want to weed |
| + // out junk for other optimization passes. Right now, nothing needs it, |
| + // and the bounding box hierarchy will do the work of skipping no-op |
| + // Save-NoDraw-Restore sequences better than we can here. |
| + //SkRecordNoopSaveRestores(record); |
| + |
| + SkRecordNoopSaveLayerDrawRestores(record); |
| + SkRecordMergeSvgOpacityAndFilterLayers(record); |
| +} |
| + |
| +void SkRecordOptimize2(SkRecord* record) { |
| + multiple_set_matrices(record); |
| + |
| + SkRecordNoopSaveRestores(record); |
| + |
| + SkRecordNoopSaveLayerDrawRestores(record); |
| + SkRecordMergeSvgOpacityAndFilterLayers(record); |
| +} |
| + |