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 #ifndef SkRecordDraw_DEFINED | 8 #ifndef SkRecordDraw_DEFINED |
9 #define SkRecordDraw_DEFINED | 9 #define SkRecordDraw_DEFINED |
10 | 10 |
(...skipping 53 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
64 p.setColor(c.color); | 64 p.setColor(c.color); |
65 DrawRect drawRect(p, fClearRect); | 65 DrawRect drawRect(p, fClearRect); |
66 this->INHERITED::operator()(drawRect); | 66 this->INHERITED::operator()(drawRect); |
67 } | 67 } |
68 | 68 |
69 private: | 69 private: |
70 const SkRect fClearRect; | 70 const SkRect fClearRect; |
71 typedef Draw INHERITED; | 71 typedef Draw INHERITED; |
72 }; | 72 }; |
73 | 73 |
74 // This is an SkRecord visitor that fills an SkBBoxHierarchy. | |
75 // | |
76 // The interesting part here is how to calculate bounds for ops which don't | |
77 // have intrinsic bounds. What is the bounds of a Save or a Translate? | |
78 // | |
79 // We answer this by thinking about a particular definition of bounds: if I | |
80 // don't execute this op, pixels in this rectangle might draw incorrectly. So | |
81 // the bounds of a Save, a Translate, a Restore, etc. are the union of the | |
82 // bounds of Draw* ops that they might have an effect on. For any given | |
83 // Save/Restore block, the bounds of the Save, the Restore, and any other | |
84 // non-drawing ("control") ops inside are exactly the union of the bounds of | |
85 // the drawing ops inside that block. | |
86 // | |
87 // To implement this, we keep a stack of active Save blocks. As we consume ops | |
88 // inside the Save/Restore block, drawing ops are unioned with the bounds of | |
89 // the block, and control ops are stashed away for later. When we finish the | |
90 // block with a Restore, our bounds are complete, and we go back and fill them | |
91 // in for all the control ops we stashed away. | |
92 class FillBounds : SkNoncopyable { | |
93 public: | |
94 FillBounds(const SkRecord& record, SkBBoxHierarchy* bbh); | |
95 | |
96 template <typename T> void operator()(const T& op) { | |
97 this->updateCTM(op); | |
98 this->updateClipBounds(op); | |
99 this->trackBounds(op); | |
100 } | |
101 | |
102 protected: | |
103 // In FillBounds, SkRect are in local coordinates, Bounds are translated bac k to identity space. | |
104 typedef SkRect Bounds; | |
105 | |
106 unsigned currentOp() const { return fCurrentOp; } | |
107 const SkMatrix& ctm() const { return *fCTM; } | |
108 const Bounds& currentClipBounds() const { return fCurrentClipBounds; } | |
109 | |
110 Bounds adjustAndMap(SkRect rect, const SkPaint* paint) const; | |
robertphillips
2014/11/03 15:38:57
getBound is only called when processing a Restore
mtklein
2014/11/03 15:56:46
Let's call it getBounds() for consistency with all
robertphillips
2014/11/03 16:49:18
Done.
| |
111 const Bounds& getBound(unsigned index) const { return fBounds[index]; } | |
112 | |
113 private: | |
114 struct SaveBounds { | |
115 int controlOps; // Number of control ops in this Save block, incl uding the Save. | |
116 Bounds bounds; // Bounds of everything in the block. | |
117 const SkPaint* paint; // Unowned. If set, adjusts the bounds of all op s in this block. | |
118 }; | |
119 | |
120 template <typename T> void updateCTM(const T&); | |
121 template <typename T> void updateClipBounds(const T&); | |
122 template <typename T> void trackBounds(const T&); | |
123 template <typename T> Bounds bounds(const T&) const; | |
124 | |
125 void updateClipBoundsForClipOp(const SkIRect& devBounds); | |
126 | |
127 void pushSaveBlock(const SkPaint* paint); | |
128 static bool PaintMayAffectTransparentBlack(const SkPaint* paint); | |
mtklein
2014/11/03 15:56:46
Let's make this guy a static function in the .cpp?
robertphillips
2014/11/03 16:49:18
Done.
| |
129 Bounds popSaveBlock(); | |
130 void pushControl(); | |
131 void popControl(const Bounds& bounds); | |
132 void updateSaveBounds(const Bounds& bounds); | |
133 | |
134 static void AdjustTextForFontMetrics(SkRect* rect, const SkPaint& paint); | |
mtklein
2014/11/03 15:56:46
These two too?
robertphillips
2014/11/03 16:49:18
Done.
| |
135 static bool AdjustForPaint(const SkPaint* paint, SkRect* rect); | |
136 bool adjustForSaveLayerPaints(SkRect* rect, int savesToIgnore = 0) const; | |
137 | |
138 // Conservative identity-space bounds for each op in the SkRecord. | |
139 SkAutoTMalloc<Bounds> fBounds; | |
140 | |
141 // We walk fCurrentOp through the SkRecord, as we go using updateCTM() | |
142 // and updateClipBounds() to maintain the exact CTM (fCTM) and conservative | |
143 // identity-space bounds of the current clip (fCurrentClipBounds). | |
144 unsigned fCurrentOp; | |
145 const SkMatrix* fCTM; | |
146 Bounds fCurrentClipBounds; | |
147 | |
148 // Used to track the bounds of Save/Restore blocks and the control ops insid e them. | |
149 SkTDArray<SaveBounds> fSaveStack; | |
150 SkTDArray<unsigned> fControlIndices; | |
151 }; | |
152 | |
153 | |
74 } // namespace SkRecords | 154 } // namespace SkRecords |
75 | 155 |
76 #endif//SkRecordDraw_DEFINED | 156 #endif//SkRecordDraw_DEFINED |
OLD | NEW |