• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (c) 2021-2022 Huawei Device Co., Ltd.
3  * Licensed under the Apache License, Version 2.0 (the "License");
4  * you may not use this file except in compliance with the License.
5  * You may obtain a copy of the License at
6  *
7  *     http://www.apache.org/licenses/LICENSE-2.0
8  *
9  * Unless required by applicable law or agreed to in writing, software
10  * distributed under the License is distributed on an "AS IS" BASIS,
11  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12  * See the License for the specific language governing permissions and
13  * limitations under the License.
14  */
15 
16 #include "pipeline/rs_paint_filter_canvas.h"
17 
18 #include <algorithm>
19 
20 #ifndef USE_ROSEN_DRAWING
21 #include "include/core/SkColorFilter.h"
22 #else
23 #include "draw/canvas.h"
24 #endif
25 
26 namespace OHOS {
27 namespace Rosen {
28 
29 #ifdef USE_ROSEN_DRAWING
30 using namespace Drawing;
31 
RSPaintFilterCanvasBase(Drawing::Canvas * canvas)32 RSPaintFilterCanvasBase::RSPaintFilterCanvasBase(Drawing::Canvas* canvas)
33     : Canvas(canvas->GetWidth(), canvas->GetHeight()), canvas_(canvas)
34 {
35 #ifdef ENABLE_RECORDING_DCL
36     this->AddCanvas(canvas);
37 #endif
38 }
39 
GetTotalMatrix() const40 Drawing::Matrix RSPaintFilterCanvasBase::GetTotalMatrix() const
41 {
42     return canvas_->GetTotalMatrix();
43 }
44 
GetLocalClipBounds() const45 Drawing::Rect RSPaintFilterCanvasBase::GetLocalClipBounds() const
46 {
47     return canvas_->GetLocalClipBounds();
48 }
49 
GetDeviceClipBounds() const50 Drawing::RectI RSPaintFilterCanvasBase::GetDeviceClipBounds() const
51 {
52     return canvas_->GetDeviceClipBounds();
53 }
54 
GetSaveCount() const55 uint32_t RSPaintFilterCanvasBase::GetSaveCount() const
56 {
57     return canvas_->GetSaveCount();
58 }
59 
60 #ifdef ACE_ENABLE_GPU
GetGPUContext()61 std::shared_ptr<Drawing::GPUContext> RSPaintFilterCanvasBase::GetGPUContext()
62 {
63     return canvas_ != nullptr ? canvas_->GetGPUContext() : nullptr;
64 }
65 #endif
66 
DrawPoint(const Point & point)67 void RSPaintFilterCanvasBase::DrawPoint(const Point& point)
68 {
69 #ifdef ENABLE_RECORDING_DCL
70     for (auto iter = pCanvasList_.begin(); iter != pCanvasList_.end(); ++iter) {
71         if ((*iter) != nullptr && OnFilter()) {
72             (*iter)->DrawPoint(point);
73         }
74     }
75 #else
76     if (canvas_ != nullptr && OnFilter()) {
77         canvas_->DrawPoint(point);
78     }
79 #endif
80 }
81 
DrawPoints(PointMode mode,size_t count,const Point pts[])82 void RSPaintFilterCanvasBase::DrawPoints(PointMode mode, size_t count, const Point pts[])
83 {
84 #ifdef ENABLE_RECORDING_DCL
85     for (auto iter = pCanvasList_.begin(); iter != pCanvasList_.end(); ++iter) {
86         if ((*iter) != nullptr && OnFilter()) {
87             (*iter)->DrawPoints(mode, count, pts);
88         }
89     }
90 #else
91     if (canvas_ != nullptr && OnFilter()) {
92         canvas_->DrawPoints(mode, count, pts);
93     }
94 #endif
95 }
96 
DrawLine(const Point & startPt,const Point & endPt)97 void RSPaintFilterCanvasBase::DrawLine(const Point& startPt, const Point& endPt)
98 {
99 #ifdef ENABLE_RECORDING_DCL
100     for (auto iter = pCanvasList_.begin(); iter != pCanvasList_.end(); ++iter) {
101         if ((*iter) != nullptr && OnFilter()) {
102             (*iter)->DrawLine(startPt, endPt);
103         }
104     }
105 #else
106     if (canvas_ != nullptr && OnFilter()) {
107         canvas_->DrawLine(startPt, endPt);
108     }
109 #endif
110 }
111 
DrawRect(const Rect & rect)112 void RSPaintFilterCanvasBase::DrawRect(const Rect& rect)
113 {
114 #ifdef ENABLE_RECORDING_DCL
115     for (auto iter = pCanvasList_.begin(); iter != pCanvasList_.end(); ++iter) {
116         if ((*iter) != nullptr && OnFilter()) {
117             (*iter)->DrawRect(rect);
118         }
119     }
120 #else
121     if (canvas_ != nullptr && OnFilter()) {
122         canvas_->DrawRect(rect);
123     }
124 #endif
125 }
126 
DrawRoundRect(const RoundRect & roundRect)127 void RSPaintFilterCanvasBase::DrawRoundRect(const RoundRect& roundRect)
128 {
129 #ifdef ENABLE_RECORDING_DCL
130     for (auto iter = pCanvasList_.begin(); iter != pCanvasList_.end(); ++iter) {
131         if ((*iter) != nullptr && OnFilter()) {
132             (*iter)->DrawRoundRect(roundRect);
133         }
134     }
135 #else
136     if (canvas_ != nullptr && OnFilter()) {
137         canvas_->DrawRoundRect(roundRect);
138     }
139 #endif
140 }
141 
DrawNestedRoundRect(const RoundRect & outer,const RoundRect & inner)142 void RSPaintFilterCanvasBase::DrawNestedRoundRect(const RoundRect& outer, const RoundRect& inner)
143 {
144 #ifdef ENABLE_RECORDING_DCL
145     for (auto iter = pCanvasList_.begin(); iter != pCanvasList_.end(); ++iter) {
146         if ((*iter) != nullptr && OnFilter()) {
147             (*iter)->DrawNestedRoundRect(outer, inner);
148         }
149     }
150 #else
151     if (canvas_ != nullptr && OnFilter()) {
152         canvas_->DrawNestedRoundRect(outer, inner);
153     }
154 #endif
155 }
156 
DrawArc(const Rect & oval,scalar startAngle,scalar sweepAngle)157 void RSPaintFilterCanvasBase::DrawArc(const Rect& oval, scalar startAngle, scalar sweepAngle)
158 {
159 #ifdef ENABLE_RECORDING_DCL
160     for (auto iter = pCanvasList_.begin(); iter != pCanvasList_.end(); ++iter) {
161         if ((*iter) != nullptr && OnFilter()) {
162             (*iter)->DrawArc(oval, startAngle, sweepAngle);
163         }
164     }
165 #else
166     if (canvas_ != nullptr && OnFilter()) {
167         canvas_->DrawArc(oval, startAngle, sweepAngle);
168     }
169 #endif
170 }
171 
DrawPie(const Rect & oval,scalar startAngle,scalar sweepAngle)172 void RSPaintFilterCanvasBase::DrawPie(const Rect& oval, scalar startAngle, scalar sweepAngle)
173 {
174 #ifdef ENABLE_RECORDING_DCL
175     for (auto iter = pCanvasList_.begin(); iter != pCanvasList_.end(); ++iter) {
176         if ((*iter) != nullptr && OnFilter()) {
177             (*iter)->DrawPie(oval, startAngle, sweepAngle);
178         }
179     }
180 #else
181     if (canvas_ != nullptr && OnFilter()) {
182         canvas_->DrawPie(oval, startAngle, sweepAngle);
183     }
184 #endif
185 }
186 
DrawOval(const Rect & oval)187 void RSPaintFilterCanvasBase::DrawOval(const Rect& oval)
188 {
189 #ifdef ENABLE_RECORDING_DCL
190     for (auto iter = pCanvasList_.begin(); iter != pCanvasList_.end(); ++iter) {
191         if ((*iter) != nullptr && OnFilter()) {
192             (*iter)->DrawOval(oval);
193         }
194     }
195 #else
196     if (canvas_ != nullptr && OnFilter()) {
197         canvas_->DrawOval(oval);
198     }
199 #endif
200 }
201 
DrawCircle(const Point & centerPt,scalar radius)202 void RSPaintFilterCanvasBase::DrawCircle(const Point& centerPt, scalar radius)
203 {
204 #ifdef ENABLE_RECORDING_DCL
205     for (auto iter = pCanvasList_.begin(); iter != pCanvasList_.end(); ++iter) {
206         if ((*iter) != nullptr && OnFilter()) {
207             (*iter)->DrawCircle(centerPt, radius);
208         }
209     }
210 #else
211     if (canvas_ != nullptr && OnFilter()) {
212         canvas_->DrawCircle(centerPt, radius);
213     }
214 #endif
215 }
216 
DrawPath(const Path & path)217 void RSPaintFilterCanvasBase::DrawPath(const Path& path)
218 {
219 #ifdef ENABLE_RECORDING_DCL
220     for (auto iter = pCanvasList_.begin(); iter != pCanvasList_.end(); ++iter) {
221         if ((*iter) != nullptr && OnFilter()) {
222             (*iter)->DrawPath(path);
223         }
224     }
225 #else
226     if (canvas_ != nullptr && OnFilter()) {
227         canvas_->DrawPath(path);
228     }
229 #endif
230 }
231 
DrawBackground(const Brush & brush)232 void RSPaintFilterCanvasBase::DrawBackground(const Brush& brush)
233 {
234     Brush b(brush);
235 #ifdef ENABLE_RECORDING_DCL
236     for (auto iter = pCanvasList_.begin(); iter != pCanvasList_.end(); ++iter) {
237         if ((*iter) != nullptr && OnFilterWithBrush(b)) {
238             (*iter)->DrawBackground(b);
239         }
240     }
241 #else
242     if (canvas_ != nullptr && OnFilterWithBrush(b)) {
243         canvas_->DrawBackground(b);
244     }
245 #endif
246 }
247 
DrawShadow(const Path & path,const Point3 & planeParams,const Point3 & devLightPos,scalar lightRadius,Color ambientColor,Color spotColor,ShadowFlags flag)248 void RSPaintFilterCanvasBase::DrawShadow(const Path& path, const Point3& planeParams, const Point3& devLightPos,
249     scalar lightRadius, Color ambientColor, Color spotColor, ShadowFlags flag)
250 {
251 #ifdef ENABLE_RECORDING_DCL
252     for (auto iter = pCanvasList_.begin(); iter != pCanvasList_.end(); ++iter) {
253         if ((*iter) != nullptr && OnFilter()) {
254             (*iter)->DrawShadow(path, planeParams, devLightPos, lightRadius, ambientColor, spotColor, flag);
255         }
256     }
257 #else
258     if (canvas_ != nullptr && OnFilter()) {
259         canvas_->DrawShadow(path, planeParams, devLightPos, lightRadius, ambientColor, spotColor, flag);
260     }
261 #endif
262 }
263 
DrawColor(Drawing::ColorQuad color,Drawing::BlendMode mode)264 void RSPaintFilterCanvasBase::DrawColor(Drawing::ColorQuad color, Drawing::BlendMode mode)
265 {
266 #ifdef ENABLE_RECORDING_DCL
267     for (auto iter = pCanvasList_.begin(); iter != pCanvasList_.end(); ++iter) {
268         if ((*iter) != nullptr && OnFilter()) {
269             (*iter)->DrawColor(color, mode);
270         }
271     }
272 #else
273     if (canvas_ != nullptr && OnFilter()) {
274         canvas_->DrawColor(color, mode);
275     }
276 #endif
277 }
278 
DrawRegion(const Drawing::Region & region)279 void RSPaintFilterCanvasBase::DrawRegion(const Drawing::Region& region)
280 {
281 #ifdef ENABLE_RECORDING_DCL
282     for (auto iter = pCanvasList_.begin(); iter != pCanvasList_.end(); ++iter) {
283         if ((*iter) != nullptr && OnFilter()) {
284             (*iter)->DrawRegion(region);
285         }
286     }
287 #else
288     if (canvas_ != nullptr && OnFilter()) {
289         canvas_->DrawRegion(region);
290     }
291 #endif
292 }
293 
DrawPatch(const Drawing::Point cubics[12],const Drawing::ColorQuad colors[4],const Drawing::Point texCoords[4],Drawing::BlendMode mode)294 void RSPaintFilterCanvasBase::DrawPatch(const Drawing::Point cubics[12], const Drawing::ColorQuad colors[4],
295     const Drawing::Point texCoords[4], Drawing::BlendMode mode)
296 {
297 #ifdef ENABLE_RECORDING_DCL
298     for (auto iter = pCanvasList_.begin(); iter != pCanvasList_.end(); ++iter) {
299         if ((*iter) != nullptr && OnFilter()) {
300             (*iter)->DrawPatch(cubics, colors, texCoords, mode);
301         }
302     }
303 #else
304     if (canvas_ != nullptr && OnFilter()) {
305         canvas_->DrawPatch(cubics, colors, texCoords, mode);
306     }
307 #endif
308 }
309 
DrawVertices(const Drawing::Vertices & vertices,Drawing::BlendMode mode)310 void RSPaintFilterCanvasBase::DrawVertices(const Drawing::Vertices& vertices, Drawing::BlendMode mode)
311 {
312 #ifdef ENABLE_RECORDING_DCL
313     for (auto iter = pCanvasList_.begin(); iter != pCanvasList_.end(); ++iter) {
314         if ((*iter) != nullptr && OnFilter()) {
315             (*iter)->DrawVertices(vertices, mode);
316         }
317     }
318 #else
319     if (canvas_ != nullptr && OnFilter()) {
320         canvas_->DrawVertices(vertices, mode);
321     }
322 #endif
323 }
324 
DrawBitmap(const Bitmap & bitmap,const scalar px,const scalar py)325 void RSPaintFilterCanvasBase::DrawBitmap(const Bitmap& bitmap, const scalar px, const scalar py)
326 {
327 #ifdef ENABLE_RECORDING_DCL
328     for (auto iter = pCanvasList_.begin(); iter != pCanvasList_.end(); ++iter) {
329         if ((*iter) != nullptr && OnFilter()) {
330             (*iter)->DrawBitmap(bitmap, px, py);
331         }
332     }
333 #else
334     if (canvas_ != nullptr && OnFilter()) {
335         canvas_->DrawBitmap(bitmap, px, py);
336     }
337 #endif
338 }
339 
DrawImageNine(const Drawing::Image * image,const Drawing::RectI & center,const Drawing::Rect & dst,Drawing::FilterMode filter,const Drawing::Brush * brush)340 void RSPaintFilterCanvasBase::DrawImageNine(const Drawing::Image* image, const Drawing::RectI& center,
341     const Drawing::Rect& dst, Drawing::FilterMode filter, const Drawing::Brush* brush)
342 {
343 #ifdef ENABLE_RECORDING_DCL
344     for (auto iter = pCanvasList_.begin(); iter != pCanvasList_.end(); ++iter) {
345         if ((*iter) != nullptr && OnFilter()) {
346             (*iter)->DrawImageNine(image, center, dst, filter, brush);
347         }
348     }
349 #else
350     if (canvas_ != nullptr && OnFilter()) {
351         canvas_->DrawImageNine(image, center, dst, filter, brush);
352     }
353 #endif
354 }
355 
DrawImageLattice(const Drawing::Image * image,const Drawing::Lattice & lattice,const Drawing::Rect & dst,Drawing::FilterMode filter,const Drawing::Brush * brush)356 void RSPaintFilterCanvasBase::DrawImageLattice(const Drawing::Image* image, const Drawing::Lattice& lattice,
357     const Drawing::Rect& dst, Drawing::FilterMode filter, const Drawing::Brush* brush)
358 {
359 #ifdef ENABLE_RECORDING_DCL
360     for (auto iter = pCanvasList_.begin(); iter != pCanvasList_.end(); ++iter) {
361         if ((*iter) != nullptr && OnFilter()) {
362             (*iter)->DrawImageLattice(image, lattice, dst, filter, brush);
363         }
364     }
365 #else
366     if (canvas_ != nullptr && OnFilter()) {
367         canvas_->DrawImageLattice(image, lattice, dst, filter, brush);
368     }
369 #endif
370 }
371 
DrawBitmap(Media::PixelMap & pixelMap,const scalar px,const scalar py)372 void RSPaintFilterCanvasBase::DrawBitmap(Media::PixelMap& pixelMap, const scalar px, const scalar py)
373 {
374 #ifdef ENABLE_RECORDING_DCL
375     for (auto iter = pCanvasList_.begin(); iter != pCanvasList_.end(); ++iter) {
376         if ((*iter) != nullptr && OnFilter()) {
377             (*iter)->DrawBitmap(pixelMap, px, py);
378         }
379     }
380 #else
381     if (canvas_ != nullptr && OnFilter()) {
382         canvas_->DrawBitmap(pixelMap, px, py);
383     }
384 #endif
385 }
386 
DrawImage(const Image & image,const scalar px,const scalar py,const SamplingOptions & sampling)387 void RSPaintFilterCanvasBase::DrawImage(
388     const Image& image, const scalar px, const scalar py, const SamplingOptions& sampling)
389 {
390 #ifdef ENABLE_RECORDING_DCL
391     for (auto iter = pCanvasList_.begin(); iter != pCanvasList_.end(); ++iter) {
392         if ((*iter) != nullptr && OnFilter()) {
393             (*iter)->DrawImage(image, px, py, sampling);
394         }
395     }
396 #else
397     if (canvas_ != nullptr && OnFilter()) {
398         canvas_->DrawImage(image, px, py, sampling);
399     }
400 #endif
401 }
402 
DrawImageRect(const Image & image,const Rect & src,const Rect & dst,const SamplingOptions & sampling,SrcRectConstraint constraint)403 void RSPaintFilterCanvasBase::DrawImageRect(const Image& image, const Rect& src, const Rect& dst,
404     const SamplingOptions& sampling, SrcRectConstraint constraint)
405 {
406 #ifdef ENABLE_RECORDING_DCL
407     for (auto iter = pCanvasList_.begin(); iter != pCanvasList_.end(); ++iter) {
408         if ((*iter) != nullptr && OnFilter()) {
409             (*iter)->DrawImageRect(image, src, dst, sampling, constraint);
410         }
411     }
412 #else
413     if (canvas_ != nullptr && OnFilter()) {
414         canvas_->DrawImageRect(image, src, dst, sampling, constraint);
415     }
416 #endif
417 }
418 
DrawImageRect(const Image & image,const Rect & dst,const SamplingOptions & sampling)419 void RSPaintFilterCanvasBase::DrawImageRect(const Image& image, const Rect& dst, const SamplingOptions& sampling)
420 {
421 #ifdef ENABLE_RECORDING_DCL
422     for (auto iter = pCanvasList_.begin(); iter != pCanvasList_.end(); ++iter) {
423         if ((*iter) != nullptr && OnFilter()) {
424             (*iter)->DrawImageRect(image, dst, sampling);
425         }
426     }
427 #else
428     if (canvas_ != nullptr && OnFilter()) {
429         canvas_->DrawImageRect(image, dst, sampling);
430     }
431 #endif
432 }
433 
DrawPicture(const Picture & picture)434 void RSPaintFilterCanvasBase::DrawPicture(const Picture& picture)
435 {
436 #ifdef ENABLE_RECORDING_DCL
437     for (auto iter = pCanvasList_.begin(); iter != pCanvasList_.end(); ++iter) {
438         if ((*iter) != nullptr && OnFilter()) {
439             (*iter)->DrawPicture(picture);
440         }
441     }
442 #else
443     if (canvas_ != nullptr && OnFilter()) {
444         canvas_->DrawPicture(picture);
445     }
446 #endif
447 }
448 
DrawTextBlob(const Drawing::TextBlob * blob,const Drawing::scalar x,const Drawing::scalar y)449 void RSPaintFilterCanvasBase::DrawTextBlob(
450     const Drawing::TextBlob* blob, const Drawing::scalar x, const Drawing::scalar y)
451 {
452 #ifdef ENABLE_RECORDING_DCL
453     for (auto iter = pCanvasList_.begin(); iter != pCanvasList_.end(); ++iter) {
454         if ((*iter) != nullptr && OnFilter()) {
455             (*iter)->DrawTextBlob(blob, x, y);
456         }
457     }
458 #else
459     if (canvas_ != nullptr && OnFilter()) {
460         canvas_->DrawTextBlob(blob, x, y);
461     }
462 #endif
463 }
464 
ClipRect(const Drawing::Rect & rect,Drawing::ClipOp op,bool doAntiAlias)465 void RSPaintFilterCanvasBase::ClipRect(const Drawing::Rect& rect, Drawing::ClipOp op, bool doAntiAlias)
466 {
467 #ifdef ENABLE_RECORDING_DCL
468     for (auto iter = pCanvasList_.begin(); iter != pCanvasList_.end(); ++iter) {
469         if ((*iter) != nullptr) {
470             (*iter)->ClipRect(rect, op, doAntiAlias);
471         }
472     }
473 #else
474     if (canvas_ != nullptr) {
475         canvas_->ClipRect(rect, op, doAntiAlias);
476     }
477 #endif
478 }
479 
ClipIRect(const Drawing::RectI & rect,Drawing::ClipOp op)480 void RSPaintFilterCanvasBase::ClipIRect(const Drawing::RectI& rect, Drawing::ClipOp op)
481 {
482 #ifdef ENABLE_RECORDING_DCL
483     for (auto iter = pCanvasList_.begin(); iter != pCanvasList_.end(); ++iter) {
484         if ((*iter) != nullptr) {
485             (*iter)->ClipIRect(rect, op);
486         }
487     }
488 #else
489     if (canvas_ != nullptr) {
490         canvas_->ClipIRect(rect, op);
491     }
492 #endif
493 }
494 
ClipRoundRect(const RoundRect & roundRect,ClipOp op,bool doAntiAlias)495 void RSPaintFilterCanvasBase::ClipRoundRect(const RoundRect& roundRect, ClipOp op, bool doAntiAlias)
496 {
497 #ifdef ENABLE_RECORDING_DCL
498     for (auto iter = pCanvasList_.begin(); iter != pCanvasList_.end(); ++iter) {
499         if ((*iter) != nullptr) {
500             (*iter)->ClipRoundRect(roundRect, op, doAntiAlias);
501         }
502     }
503 #else
504     if (canvas_ != nullptr) {
505         canvas_->ClipRoundRect(roundRect, op, doAntiAlias);
506     }
507 #endif
508 }
509 
ClipRoundRect(const Drawing::Rect & rect,std::vector<Drawing::Point> & pts,bool doAntiAlias)510 void RSPaintFilterCanvasBase::ClipRoundRect(const Drawing::Rect& rect,
511     std::vector<Drawing::Point>& pts, bool doAntiAlias)
512 {
513 #ifdef ENABLE_RECORDING_DCL
514     for (auto iter = pCanvasList_.begin(); iter != pCanvasList_.end(); ++iter) {
515         if ((*iter) != nullptr) {
516             (*iter)->ClipRoundRect(rect, pts, doAntiAlias);
517         }
518     }
519 #else
520     if (canvas_ != nullptr) {
521         canvas_->ClipRoundRect(rect, pts, doAntiAlias);
522     }
523 #endif
524 }
525 
ClipPath(const Path & path,ClipOp op,bool doAntiAlias)526 void RSPaintFilterCanvasBase::ClipPath(const Path& path, ClipOp op, bool doAntiAlias)
527 {
528 #ifdef ENABLE_RECORDING_DCL
529     for (auto iter = pCanvasList_.begin(); iter != pCanvasList_.end(); ++iter) {
530         if ((*iter) != nullptr) {
531             (*iter)->ClipPath(path, op, doAntiAlias);
532         }
533     }
534 #else
535     if (canvas_ != nullptr) {
536         canvas_->ClipPath(path, op, doAntiAlias);
537     }
538 #endif
539 }
540 
ClipRegion(const Region & region,ClipOp op)541 void RSPaintFilterCanvasBase::ClipRegion(const Region& region, ClipOp op)
542 {
543 #ifdef ENABLE_RECORDING_DCL
544     for (auto iter = pCanvasList_.begin(); iter != pCanvasList_.end(); ++iter) {
545         if ((*iter) != nullptr) {
546             (*iter)->ClipRegion(region, op);
547         }
548     }
549 #else
550     if (canvas_ != nullptr) {
551         canvas_->ClipRegion(region, op);
552     }
553 #endif
554 }
555 
SetMatrix(const Matrix & matrix)556 void RSPaintFilterCanvasBase::SetMatrix(const Matrix& matrix)
557 {
558 #ifdef ENABLE_RECORDING_DCL
559     for (auto iter = pCanvasList_.begin(); iter != pCanvasList_.end(); ++iter) {
560         if ((*iter) != nullptr) {
561             (*iter)->SetMatrix(matrix);
562         }
563     }
564 #else
565     if (canvas_ != nullptr) {
566         canvas_->SetMatrix(matrix);
567     }
568 #endif
569 }
570 
ResetMatrix()571 void RSPaintFilterCanvasBase::ResetMatrix()
572 {
573 #ifdef ENABLE_RECORDING_DCL
574     for (auto iter = pCanvasList_.begin(); iter != pCanvasList_.end(); ++iter) {
575         if ((*iter) != nullptr) {
576             (*iter)->ResetMatrix();
577         }
578     }
579 #else
580     if (canvas_ != nullptr) {
581         canvas_->ResetMatrix();
582     }
583 #endif
584 }
585 
ConcatMatrix(const Matrix & matrix)586 void RSPaintFilterCanvasBase::ConcatMatrix(const Matrix& matrix)
587 {
588 #ifdef ENABLE_RECORDING_DCL
589     for (auto iter = pCanvasList_.begin(); iter != pCanvasList_.end(); ++iter) {
590         if ((*iter) != nullptr) {
591             (*iter)->ConcatMatrix(matrix);
592         }
593     }
594 #else
595     if (canvas_ != nullptr) {
596         canvas_->ConcatMatrix(matrix);
597     }
598 #endif
599 }
600 
Translate(scalar dx,scalar dy)601 void RSPaintFilterCanvasBase::Translate(scalar dx, scalar dy)
602 {
603 #ifdef ENABLE_RECORDING_DCL
604     for (auto iter = pCanvasList_.begin(); iter != pCanvasList_.end(); ++iter) {
605         if ((*iter) != nullptr) {
606             (*iter)->Translate(dx, dy);
607         }
608     }
609 #else
610     if (canvas_ != nullptr) {
611         canvas_->Translate(dx, dy);
612     }
613 #endif
614 }
615 
Scale(scalar sx,scalar sy)616 void RSPaintFilterCanvasBase::Scale(scalar sx, scalar sy)
617 {
618 #ifdef ENABLE_RECORDING_DCL
619     for (auto iter = pCanvasList_.begin(); iter != pCanvasList_.end(); ++iter) {
620         if ((*iter) != nullptr) {
621             (*iter)->Scale(sx, sy);
622         }
623     }
624 #else
625     if (canvas_ != nullptr) {
626         canvas_->Scale(sx, sy);
627     }
628 #endif
629 }
630 
Rotate(scalar deg,scalar sx,scalar sy)631 void RSPaintFilterCanvasBase::Rotate(scalar deg, scalar sx, scalar sy)
632 {
633 #ifdef ENABLE_RECORDING_DCL
634     for (auto iter = pCanvasList_.begin(); iter != pCanvasList_.end(); ++iter) {
635         if ((*iter) != nullptr) {
636             (*iter)->Rotate(deg, sx, sy);
637         }
638     }
639 #else
640     if (canvas_ != nullptr) {
641         canvas_->Rotate(deg, sx, sy);
642     }
643 #endif
644 }
645 
Shear(scalar sx,scalar sy)646 void RSPaintFilterCanvasBase::Shear(scalar sx, scalar sy)
647 {
648 #ifdef ENABLE_RECORDING_DCL
649     for (auto iter = pCanvasList_.begin(); iter != pCanvasList_.end(); ++iter) {
650         if ((*iter) != nullptr) {
651             (*iter)->Shear(sx, sy);
652         }
653     }
654 #else
655     if (canvas_ != nullptr) {
656         canvas_->Shear(sx, sy);
657     }
658 #endif
659 }
660 
Flush()661 void RSPaintFilterCanvasBase::Flush()
662 {
663 #ifdef ENABLE_RECORDING_DCL
664     for (auto iter = pCanvasList_.begin(); iter != pCanvasList_.end(); ++iter) {
665         if ((*iter) != nullptr) {
666             (*iter)->Flush();
667         }
668     }
669 #else
670     if (canvas_ != nullptr) {
671         canvas_->Flush();
672     }
673 #endif
674 }
675 
Clear(ColorQuad color)676 void RSPaintFilterCanvasBase::Clear(ColorQuad color)
677 {
678 #ifdef ENABLE_RECORDING_DCL
679     for (auto iter = pCanvasList_.begin(); iter != pCanvasList_.end(); ++iter) {
680         if ((*iter) != nullptr) {
681             (*iter)->Clear(color);
682         }
683     }
684 #else
685     if (canvas_ != nullptr) {
686         canvas_->Clear(color);
687     }
688 #endif
689 }
690 
Save()691 uint32_t RSPaintFilterCanvasBase::Save()
692 {
693 #ifdef ENABLE_RECORDING_DCL
694     uint32_t count = 0U;
695     for (auto iter = pCanvasList_.begin(); iter != pCanvasList_.end(); ++iter) {
696         if ((*iter) != nullptr) {
697             auto c = (*iter)->Save();
698             if ((*iter) == canvas_) {
699                 count = c;
700             }
701         }
702     }
703     return count;
704 #else
705     if (canvas_ != nullptr) {
706         return canvas_->Save();
707     }
708     return 0;
709 #endif
710 }
711 
SaveLayer(const SaveLayerOps & saveLayerRec)712 void RSPaintFilterCanvasBase::SaveLayer(const SaveLayerOps& saveLayerRec)
713 {
714     if (canvas_ == nullptr) {
715         return;
716     }
717     Brush brush;
718     if (saveLayerRec.GetBrush() != nullptr) {
719         brush = *saveLayerRec.GetBrush();
720         OnFilterWithBrush(brush);
721     }
722     SaveLayerOps slo(saveLayerRec.GetBounds(), &brush, saveLayerRec.GetSaveLayerFlags());
723 #ifdef ENABLE_RECORDING_DCL
724     for (auto iter = pCanvasList_.begin(); iter != pCanvasList_.end(); ++iter) {
725         if ((*iter) != nullptr) {
726             (*iter)->SaveLayer(slo);
727         }
728     }
729 #else
730     canvas_->SaveLayer(slo);
731 #endif
732 }
733 
Restore()734 void RSPaintFilterCanvasBase::Restore()
735 {
736 #ifdef ENABLE_RECORDING_DCL
737     for (auto iter = pCanvasList_.begin(); iter != pCanvasList_.end(); ++iter) {
738         if ((*iter) != nullptr) {
739             (*iter)->Restore();
740         }
741     }
742 #else
743     if (canvas_ != nullptr) {
744         canvas_->Restore();
745     }
746 #endif
747 }
748 
Discard()749 void RSPaintFilterCanvasBase::Discard()
750 {
751 #ifdef ENABLE_RECORDING_DCL
752     for (auto iter = pCanvasList_.begin(); iter != pCanvasList_.end(); ++iter) {
753         if ((*iter) != nullptr) {
754             (*iter)->Discard();
755         }
756     }
757 #else
758     if (canvas_ != nullptr) {
759         canvas_->Discard();
760     }
761 #endif
762 }
763 
AttachPen(const Pen & pen)764 CoreCanvas& RSPaintFilterCanvasBase::AttachPen(const Pen& pen)
765 {
766 #ifdef ENABLE_RECORDING_DCL
767     for (auto iter = pCanvasList_.begin(); iter != pCanvasList_.end(); ++iter) {
768         if ((*iter) != nullptr) {
769             (*iter)->AttachPen(pen);
770         }
771     }
772 #else
773     if (canvas_ != nullptr) {
774         canvas_->AttachPen(pen);
775     }
776 #endif
777     return *this;
778 }
779 
AttachBrush(const Brush & brush)780 CoreCanvas& RSPaintFilterCanvasBase::AttachBrush(const Brush& brush)
781 {
782 #ifdef ENABLE_RECORDING_DCL
783     for (auto iter = pCanvasList_.begin(); iter != pCanvasList_.end(); ++iter) {
784         if ((*iter) != nullptr) {
785             (*iter)->AttachBrush(brush);
786         }
787     }
788 #else
789     if (canvas_ != nullptr) {
790         canvas_->AttachBrush(brush);
791     }
792 #endif
793     return *this;
794 }
795 
AttachPaint(const Drawing::Paint & paint)796 CoreCanvas& RSPaintFilterCanvasBase::AttachPaint(const Drawing::Paint& paint)
797 {
798 #ifdef ENABLE_RECORDING_DCL
799     for (auto iter = pCanvasList_.begin(); iter != pCanvasList_.end(); ++iter) {
800         if ((*iter) != nullptr) {
801             (*iter)->AttachPaint(paint);
802         }
803     }
804 #else
805     if (canvas_ != nullptr) {
806         canvas_->AttachPaint(paint);
807     }
808 #endif
809     return *this;
810 }
811 
DetachPen()812 CoreCanvas& RSPaintFilterCanvasBase::DetachPen()
813 {
814 #ifdef ENABLE_RECORDING_DCL
815     for (auto iter = pCanvasList_.begin(); iter != pCanvasList_.end(); ++iter) {
816         if ((*iter) != nullptr) {
817             (*iter)->DetachPen();
818         }
819     }
820 #else
821     if (canvas_ != nullptr) {
822         canvas_->DetachPen();
823     }
824 #endif
825     return *this;
826 }
827 
DetachBrush()828 CoreCanvas& RSPaintFilterCanvasBase::DetachBrush()
829 {
830 #ifdef ENABLE_RECORDING_DCL
831     for (auto iter = pCanvasList_.begin(); iter != pCanvasList_.end(); ++iter) {
832         if ((*iter) != nullptr) {
833             (*iter)->DetachBrush();
834         }
835     }
836 #else
837     if (canvas_ != nullptr) {
838         canvas_->DetachBrush();
839     }
840 #endif
841     return *this;
842 }
843 
DetachPaint()844 CoreCanvas& RSPaintFilterCanvasBase::DetachPaint()
845 {
846 #ifdef ENABLE_RECORDING_DCL
847     for (auto iter = pCanvasList_.begin(); iter != pCanvasList_.end(); ++iter) {
848         if ((*iter) != nullptr) {
849             (*iter)->DetachPaint();
850         }
851     }
852 #else
853     if (canvas_ != nullptr) {
854         canvas_->DetachPaint();
855     }
856 #endif
857     return *this;
858 }
859 #endif
860 
861 #ifndef USE_ROSEN_DRAWING
RSPaintFilterCanvas(SkCanvas * canvas,float alpha)862 RSPaintFilterCanvas::RSPaintFilterCanvas(SkCanvas* canvas, float alpha)
863     : SkPaintFilterCanvas(canvas),
864       alphaStack_({ std::clamp(alpha, 0.f, 1.f) }), // construct stack with given alpha
865       // Temporary fix, this default color should be 0x000000FF, fix this after foreground color refactor
866       envStack_({ Env({ Color(0xFF000000) }) }), // construct stack with default foreground color
867       blendModeStack_({std::nullopt})
868 {}
869 
RSPaintFilterCanvas(SkSurface * skSurface,float alpha)870 RSPaintFilterCanvas::RSPaintFilterCanvas(SkSurface* skSurface, float alpha)
871     : SkPaintFilterCanvas(skSurface ? skSurface->getCanvas() : nullptr), skSurface_(skSurface),
872       alphaStack_({ std::clamp(alpha, 0.f, 1.f) }), // construct stack with given alpha
873       // Temporary fix, this default color should be 0x000000FF, fix this after foreground color refactor
874       envStack_({ Env({ Color(0xFF000000) }) }), // construct stack with default foreground color
875       blendModeStack_({std::nullopt})
876 {}
877 
GetSurface() const878 SkSurface* RSPaintFilterCanvas::GetSurface() const
879 {
880     return skSurface_;
881 }
882 
onFilter(SkPaint & paint) const883 bool RSPaintFilterCanvas::onFilter(SkPaint& paint) const
884 {
885     if (paint.getColor() == 0x00000001) { // foreground color and foreground color strategy identification
886         paint.setColor(envStack_.top().envForegroundColor_.AsArgbInt());
887     }
888 
889     if (alphaStack_.top() >= 1.f) {
890         return true;
891     } else if (alphaStack_.top() <= 0.f) {
892         return false;
893     }
894 
895     // use blendModeStack_.top() to set blend mode
896     if (auto& blendMode = blendModeStack_.top()) {
897         paint.SetBlendMode(static_cast<Drawing::BlendMode>(*blendMode));
898     }
899 
900     // use alphaStack_.top() to multiply alpha
901     paint.setAlphaf(paint.getAlphaf() * alphaStack_.top());
902     return true;
903 }
904 
onDrawPicture(const SkPicture * picture,const SkMatrix * matrix,const SkPaint * paint)905 void RSPaintFilterCanvas::onDrawPicture(const SkPicture* picture, const SkMatrix* matrix, const SkPaint* paint)
906 {
907     SkPaint filteredPaint(paint ? *paint : SkPaint());
908     if (this->onFilter(filteredPaint)) {
909         this->SkCanvas::onDrawPicture(picture, matrix, &filteredPaint);
910     }
911 }
912 
GetRecordingCanvas() const913 SkCanvas* RSPaintFilterCanvas::GetRecordingCanvas() const
914 {
915     return recordingState_? fList[0] : nullptr;
916 }
917 
918 #else
RSPaintFilterCanvas(Drawing::Canvas * canvas,float alpha)919 RSPaintFilterCanvas::RSPaintFilterCanvas(Drawing::Canvas* canvas, float alpha)
920     : RSPaintFilterCanvasBase(canvas), alphaStack_({ std::clamp(alpha, 0.f, 1.f) }), // construct stack with given alpha
921       // Temporary fix, this default color should be 0x000000FF, fix this after foreground color refactor
922       envStack_({ Env({ RSColor(0xFF000000) }) }), // construct stack with default foreground color
923       blendModeStack_({std::nullopt})
924 {}
925 
RSPaintFilterCanvas(Drawing::Surface * surface,float alpha)926 RSPaintFilterCanvas::RSPaintFilterCanvas(Drawing::Surface* surface, float alpha)
927     : RSPaintFilterCanvasBase(surface ? surface->GetCanvas().get() : nullptr), surface_(surface),
928       alphaStack_({ std::clamp(alpha, 0.f, 1.f) }), // construct stack with given alpha
929       // Temporary fix, this default color should be 0x000000FF, fix this after foreground color refactor
930       envStack_({ Env({ RSColor(0xFF000000) }) }), // construct stack with default foreground color
931       blendModeStack_({std::nullopt})
932 {}
933 
GetSurface() const934 Drawing::Surface* RSPaintFilterCanvas::GetSurface() const
935 {
936     return surface_;
937 }
938 
AttachPen(const Pen & pen)939 CoreCanvas& RSPaintFilterCanvas::AttachPen(const Pen& pen)
940 {
941     if (canvas_ == nullptr) {
942         return *this;
943     }
944 
945     Pen p(pen);
946     if (p.GetColor() == 0x00000001) { // foreground color and foreground color strategy identification
947         p.SetColor(envStack_.top().envForegroundColor_.AsArgbInt());
948     }
949 
950     // use alphaStack_.top() to multiply alpha
951     if (alphaStack_.top() < 1 && alphaStack_.top() > 0) {
952         p.SetAlpha(p.GetAlpha() * alphaStack_.top());
953     }
954 
955     // use blendModeStack_.top() to set blend mode
956     if (auto& blendMode = blendModeStack_.top()) {
957         p.SetBlendMode(static_cast<Drawing::BlendMode>(*blendMode));
958     }
959 
960 #ifdef ENABLE_RECORDING_DCL
961     for (auto iter = pCanvasList_.begin(); iter != pCanvasList_.end(); ++iter) {
962         if ((*iter) != nullptr) {
963             (*iter)->AttachPen(p);
964         }
965     }
966 #else
967     canvas_->AttachPen(p);
968 #endif
969     return *this;
970 }
971 
AttachBrush(const Brush & brush)972 CoreCanvas& RSPaintFilterCanvas::AttachBrush(const Brush& brush)
973 {
974     if (canvas_ == nullptr) {
975         return *this;
976     }
977 
978     Brush b(brush);
979     if (b.GetColor() == 0x00000001) { // foreground color and foreground color strategy identification
980         b.SetColor(envStack_.top().envForegroundColor_.AsArgbInt());
981     }
982 
983     // use alphaStack_.top() to multiply alpha
984     if (alphaStack_.top() < 1 && alphaStack_.top() > 0) {
985         b.SetAlpha(b.GetAlpha() * alphaStack_.top());
986     }
987 
988     // use blendModeStack_.top() to set blend mode
989     if (auto& blendMode = blendModeStack_.top()) {
990         b.SetBlendMode(static_cast<Drawing::BlendMode>(*blendMode));
991     }
992 #ifdef ENABLE_RECORDING_DCL
993     for (auto iter = pCanvasList_.begin(); iter != pCanvasList_.end(); ++iter) {
994         if ((*iter) != nullptr) {
995             (*iter)->AttachBrush(b);
996         }
997     }
998 #else
999     canvas_->AttachBrush(b);
1000 #endif
1001     return *this;
1002 }
1003 
AttachPaint(const Drawing::Paint & paint)1004 CoreCanvas& RSPaintFilterCanvas::AttachPaint(const Drawing::Paint& paint)
1005 {
1006     if (canvas_ == nullptr) {
1007         return *this;
1008     }
1009 
1010     Paint p(paint);
1011     if (p.GetColor() == 0x00000001) { // foreground color and foreground color strategy identification
1012         p.SetColor(envStack_.top().envForegroundColor_.AsArgbInt());
1013     }
1014 
1015     // use alphaStack_.top() to multiply alpha
1016     if (alphaStack_.top() < 1 && alphaStack_.top() > 0) {
1017         p.SetAlpha(p.GetAlpha() * alphaStack_.top());
1018     }
1019 
1020     // use blendModeStack_.top() to set blend mode
1021     if (auto& blendMode = blendModeStack_.top()) {
1022         p.SetBlendMode(static_cast<Drawing::BlendMode>(*blendMode));
1023     }
1024 
1025 #ifdef ENABLE_RECORDING_DCL
1026     for (auto iter = pCanvasList_.begin(); iter != pCanvasList_.end(); ++iter) {
1027         if ((*iter) != nullptr) {
1028             (*iter)->AttachPaint(p);
1029         }
1030     }
1031 #else
1032     canvas_->AttachPaint(p);
1033 #endif
1034     return *this;
1035 }
1036 
OnFilter() const1037 bool RSPaintFilterCanvas::OnFilter() const
1038 {
1039     return alphaStack_.top() > 0.f;
1040 }
1041 
GetRecordingCanvas() const1042 Drawing::Canvas* RSPaintFilterCanvas::GetRecordingCanvas() const
1043 {
1044     return recordingState_ ? canvas_ : nullptr;
1045 }
1046 
1047 #endif // USE_ROSEN_DRAWING
1048 
GetRecordingState() const1049 bool RSPaintFilterCanvas::GetRecordingState() const
1050 {
1051     return recordingState_;
1052 }
1053 
SetRecordingState(bool flag)1054 void RSPaintFilterCanvas::SetRecordingState(bool flag)
1055 {
1056     recordingState_ = flag;
1057 }
1058 
MultiplyAlpha(float alpha)1059 void RSPaintFilterCanvas::MultiplyAlpha(float alpha)
1060 {
1061     // multiply alpha to top of stack
1062     alphaStack_.top() *= std::clamp(alpha, 0.f, 1.f);
1063 }
1064 
SetAlpha(float alpha)1065 void RSPaintFilterCanvas::SetAlpha(float alpha)
1066 {
1067     alphaStack_.top() = std::clamp(alpha, 0.f, 1.f);
1068 }
1069 
SaveAlpha()1070 int RSPaintFilterCanvas::SaveAlpha()
1071 {
1072     // make a copy of top of stack
1073     alphaStack_.push(alphaStack_.top());
1074     // return prev stack height
1075     return alphaStack_.size() - 1;
1076 }
1077 
GetAlpha() const1078 float RSPaintFilterCanvas::GetAlpha() const
1079 {
1080     // return top of stack
1081     return alphaStack_.top();
1082 }
1083 
RestoreAlpha()1084 void RSPaintFilterCanvas::RestoreAlpha()
1085 {
1086     // sanity check, stack should not be empty
1087     if (alphaStack_.size() <= 1u) {
1088         return;
1089     }
1090     alphaStack_.pop();
1091 }
1092 
GetAlphaSaveCount() const1093 int RSPaintFilterCanvas::GetAlphaSaveCount() const
1094 {
1095     return alphaStack_.size();
1096 }
1097 
RestoreAlphaToCount(int count)1098 void RSPaintFilterCanvas::RestoreAlphaToCount(int count)
1099 {
1100     // sanity check, stack should not be empty
1101     if (count < 1) {
1102         count = 1;
1103     }
1104     // poo stack until stack height equals count
1105     int n = static_cast<int>(alphaStack_.size()) - count;
1106     for (int i = 0; i < n; ++i) {
1107         alphaStack_.pop();
1108     }
1109 }
1110 
SetBlendMode(std::optional<int> blendMode)1111 void RSPaintFilterCanvas::SetBlendMode(std::optional<int> blendMode)
1112 {
1113     blendModeStack_.top() = blendMode;
1114 }
1115 
SaveBlendMode()1116 int RSPaintFilterCanvas::SaveBlendMode()
1117 {
1118     // make a copy of top of stack
1119     blendModeStack_.push(blendModeStack_.top());
1120     // return prev stack height
1121     return blendModeStack_.size() - 1;
1122 }
1123 
RestoreBlendMode()1124 void RSPaintFilterCanvas::RestoreBlendMode()
1125 {
1126     blendModeStack_.pop();
1127 }
1128 
SaveEnv()1129 int RSPaintFilterCanvas::SaveEnv()
1130 {
1131     // make a copy of top of stack
1132     envStack_.push(envStack_.top());
1133     // return prev stack height
1134     return envStack_.size() - 1;
1135 }
1136 
RestoreEnv()1137 void RSPaintFilterCanvas::RestoreEnv()
1138 {
1139     // sanity check, stack should not be empty
1140     if (envStack_.size() <= 1) {
1141         return;
1142     }
1143     envStack_.pop();
1144 }
1145 
RestoreEnvToCount(int count)1146 void RSPaintFilterCanvas::RestoreEnvToCount(int count)
1147 {
1148     // sanity check, stack should not be empty
1149     if (count < 1) {
1150         count = 1;
1151     }
1152     // poo stack until stack height equals count
1153     int n = static_cast<int>(envStack_.size()) - count;
1154     for (int i = 0; i < n; ++i) {
1155         envStack_.pop();
1156     }
1157 }
1158 
GetEnvSaveCount() const1159 int RSPaintFilterCanvas::GetEnvSaveCount() const
1160 {
1161     return envStack_.size();
1162 }
1163 
1164 #ifndef USE_ROSEN_DRAWING
SetEnvForegroundColor(Color color)1165 void RSPaintFilterCanvas::SetEnvForegroundColor(Color color)
1166 #else
1167 void RSPaintFilterCanvas::SetEnvForegroundColor(Rosen::RSColor color)
1168 #endif
1169 {
1170     // sanity check, stack should not be empty
1171     if (envStack_.empty()) {
1172         return;
1173     }
1174     envStack_.top().envForegroundColor_ = color;
1175 }
1176 
1177 #ifndef USE_ROSEN_DRAWING
GetEnvForegroundColor() const1178 Color RSPaintFilterCanvas::GetEnvForegroundColor() const
1179 {
1180     // sanity check, stack should not be empty
1181     if (envStack_.empty()) {
1182         return Color { 0xFF000000 }; // 0xFF000000 is default value -- black
1183     }
1184     return envStack_.top().envForegroundColor_;
1185 }
1186 #else
GetEnvForegroundColor() const1187 Drawing::ColorQuad RSPaintFilterCanvas::GetEnvForegroundColor() const
1188 {
1189     // sanity check, stack should not be empty
1190     if (envStack_.empty()) {
1191         return Drawing::Color::COLOR_BLACK; // 0xFF000000 is default value -- black
1192     }
1193     return envStack_.top().envForegroundColor_.AsArgbInt();
1194 }
1195 #endif
1196 
1197 #ifndef USE_ROSEN_DRAWING
Save(SaveType type)1198 RSPaintFilterCanvas::SaveStatus RSPaintFilterCanvas::Save(SaveType type)
1199 {
1200     // save and return status on demand
1201     return { (RSPaintFilterCanvas::kCanvas & type) ? save() : getSaveCount(),
1202         (RSPaintFilterCanvas::kAlpha & type) ? SaveAlpha() : GetAlphaSaveCount(),
1203         (RSPaintFilterCanvas::kEnv & type) ? SaveEnv() : GetEnvSaveCount() };
1204 }
1205 #else
SaveAllStatus(SaveType type)1206 RSPaintFilterCanvas::SaveStatus RSPaintFilterCanvas::SaveAllStatus(SaveType type)
1207 {
1208     // save and return status on demand
1209     return { (RSPaintFilterCanvas::kCanvas & type) ? Save() : GetSaveCount(),
1210         (RSPaintFilterCanvas::kAlpha & type) ? SaveAlpha() : GetAlphaSaveCount(),
1211         (RSPaintFilterCanvas::kEnv & type) ? SaveEnv() : GetEnvSaveCount() };
1212 }
1213 #endif
1214 
GetSaveStatus() const1215 RSPaintFilterCanvas::SaveStatus RSPaintFilterCanvas::GetSaveStatus() const
1216 {
1217 #ifndef USE_ROSEN_DRAWING
1218     return { getSaveCount(), GetAlphaSaveCount(), GetEnvSaveCount() };
1219 #else
1220     return { GetSaveCount(), GetAlphaSaveCount(), GetEnvSaveCount() };
1221 #endif
1222 }
1223 
RestoreStatus(const SaveStatus & status)1224 void RSPaintFilterCanvas::RestoreStatus(const SaveStatus& status)
1225 {
1226     // simultaneously restore canvas and alpha
1227 #ifndef USE_ROSEN_DRAWING
1228     restoreToCount(status.canvasSaveCount);
1229 #else
1230     RestoreToCount(status.canvasSaveCount);
1231 #endif
1232     RestoreAlphaToCount(status.alphaSaveCount);
1233     RestoreEnvToCount(status.envSaveCount);
1234 }
1235 
CopyConfiguration(const RSPaintFilterCanvas & other)1236 void RSPaintFilterCanvas::CopyConfiguration(const RSPaintFilterCanvas& other)
1237 {
1238     // Note:
1239     // 1. we don't need to copy alpha status, alpha will be applied when drawing cache.
1240     // copy high contrast flag
1241     isHighContrastEnabled_.store(other.isHighContrastEnabled_.load());
1242     // copy env
1243     envStack_.top() = other.envStack_.top();
1244     // cache related
1245     if (other.isHighContrastEnabled()) {
1246         // explicit disable cache for high contrast mode
1247         SetCacheType(RSPaintFilterCanvas::CacheType::DISABLED);
1248     } else {
1249         // planning: maybe we should copy source cache status
1250         SetCacheType(other.GetCacheType());
1251     }
1252     isParallelCanvas_ = other.isParallelCanvas_;
1253 }
1254 
SetHighContrast(bool enabled)1255 void RSPaintFilterCanvas::SetHighContrast(bool enabled)
1256 {
1257     isHighContrastEnabled_ = enabled;
1258 }
isHighContrastEnabled() const1259 bool RSPaintFilterCanvas::isHighContrastEnabled() const
1260 {
1261     return isHighContrastEnabled_;
1262 }
1263 
SetCacheType(CacheType type)1264 void RSPaintFilterCanvas::SetCacheType(CacheType type)
1265 {
1266     cacheType_ = type;
1267 }
1268 #ifndef USE_ROSEN_DRAWING
GetCacheType() const1269 RSPaintFilterCanvas::CacheType RSPaintFilterCanvas::GetCacheType() const
1270 #else
1271 Drawing::CacheType RSPaintFilterCanvas::GetCacheType() const
1272 #endif
1273 {
1274     return cacheType_;
1275 }
1276 
1277 #ifndef USE_ROSEN_DRAWING
SetVisibleRect(SkRect visibleRect)1278 void RSPaintFilterCanvas::SetVisibleRect(SkRect visibleRect)
1279 {
1280     visibleRect_ = visibleRect;
1281 }
1282 
GetVisibleRect() const1283 SkRect RSPaintFilterCanvas::GetVisibleRect() const
1284 {
1285     return visibleRect_;
1286 }
1287 #else
SetVisibleRect(Drawing::Rect visibleRect)1288 void RSPaintFilterCanvas::SetVisibleRect(Drawing::Rect visibleRect)
1289 {
1290     visibleRect_ = visibleRect;
1291 }
1292 
GetVisibleRect() const1293 Drawing::Rect RSPaintFilterCanvas::GetVisibleRect() const
1294 {
1295     return visibleRect_;
1296 }
1297 #endif
1298 
1299 #ifndef USE_ROSEN_DRAWING
GetLocalClipBounds(const SkCanvas & canvas,const SkIRect * clipRect)1300 std::optional<SkRect> RSPaintFilterCanvas::GetLocalClipBounds(const SkCanvas& canvas, const SkIRect* clipRect)
1301 {
1302     // if clipRect is explicitly specified, use it as the device clip bounds
1303     SkRect bounds = SkRect::Make((clipRect != nullptr) ? *clipRect : canvas.getDeviceClipBounds());
1304     if (bounds.isEmpty()) {
1305         return std::nullopt;
1306     }
1307     SkMatrix inverse;
1308     // if we can't invert the CTM, we can't return local clip bounds
1309     if (!(canvas.getTotalMatrix().invert(&inverse))) {
1310         return std::nullopt;
1311     }
1312     // return the inverse of the CTM applied to the device clip bounds as local clip bounds
1313     return inverse.mapRect(bounds);
1314 }
1315 #else
GetLocalClipBounds(const Drawing::Canvas & canvas,const Drawing::RectI * clipRect)1316 std::optional<Drawing::Rect> RSPaintFilterCanvas::GetLocalClipBounds(const Drawing::Canvas& canvas,
1317     const Drawing::RectI* clipRect)
1318 {
1319     // if clipRect is explicitly specified, use it as the device clip bounds
1320     Drawing::Rect bounds = Rect((clipRect != nullptr) ? *clipRect : canvas.GetDeviceClipBounds());
1321 
1322     if (!bounds.IsValid()) {
1323         return std::nullopt;
1324     }
1325 
1326     Drawing::Matrix inverse;
1327     // if we can't invert the CTM, we can't return local clip bounds
1328     if (!(canvas.GetTotalMatrix().Invert(inverse))) {
1329         return std::nullopt;
1330     }
1331     // return the inverse of the CTM applied to the device clip bounds as local clip bounds
1332     Drawing::Rect dst;
1333     inverse.MapRect(dst, bounds);
1334     return dst;
1335 }
1336 #endif
1337 
1338 #ifndef USE_ROSEN_DRAWING
getSaveLayerStrategy(const SaveLayerRec & rec)1339 SkCanvas::SaveLayerStrategy RSPaintFilterCanvas::getSaveLayerStrategy(const SaveLayerRec& rec)
1340 {
1341     SkPaint p = rec.fPaint ? *rec.fPaint : SkPaint();
1342     SaveLayerRec tmpRec = rec;
1343     if (onFilter(p)) {
1344         tmpRec.fPaint = &p;
1345     }
1346     return SkPaintFilterCanvas::getSaveLayerStrategy(tmpRec);
1347 }
1348 #endif
1349 
SetEffectData(const std::shared_ptr<RSPaintFilterCanvas::CachedEffectData> & effectData)1350 void RSPaintFilterCanvas::SetEffectData(const std::shared_ptr<RSPaintFilterCanvas::CachedEffectData>& effectData)
1351 {
1352     envStack_.top().effectData_ = effectData;
1353 }
1354 
GetEffectData() const1355 const std::shared_ptr<RSPaintFilterCanvas::CachedEffectData>& RSPaintFilterCanvas::GetEffectData() const
1356 {
1357     return envStack_.top().effectData_;
1358 }
1359 
1360 #ifndef USE_ROSEN_DRAWING
SetCanvasStatus(const CanvasStatus & status)1361 void RSPaintFilterCanvas::SetCanvasStatus(const CanvasStatus& status)
1362 {
1363     SetAlpha(status.alpha_);
1364     setMatrix(status.matrix_);
1365     SetEffectData(status.effectData_);
1366 }
1367 
GetCanvasStatus() const1368 RSPaintFilterCanvas::CanvasStatus RSPaintFilterCanvas::GetCanvasStatus() const
1369 {
1370     return { GetAlpha(), getTotalMatrix(), GetEffectData() };
1371 }
1372 
CachedEffectData(sk_sp<SkImage> && image,const SkIRect & rect)1373 RSPaintFilterCanvas::CachedEffectData::CachedEffectData(sk_sp<SkImage>&& image, const SkIRect& rect)
1374     : cachedImage_(image), cachedRect_(rect)
1375 {}
1376 #else
SetCanvasStatus(const CanvasStatus & status)1377 void RSPaintFilterCanvas::SetCanvasStatus(const CanvasStatus& status)
1378 {
1379     SetAlpha(status.alpha_);
1380     SetMatrix(status.matrix_);
1381     SetEffectData(status.effectData_);
1382 }
1383 
GetCanvasStatus() const1384 RSPaintFilterCanvas::CanvasStatus RSPaintFilterCanvas::GetCanvasStatus() const
1385 {
1386     return { GetAlpha(), GetTotalMatrix(), GetEffectData() };
1387 }
1388 
CachedEffectData(std::shared_ptr<Drawing::Image> && image,const Drawing::RectI & rect)1389 RSPaintFilterCanvas::CachedEffectData::CachedEffectData(std::shared_ptr<Drawing::Image>&& image,
1390     const Drawing::RectI& rect)
1391     : cachedImage_(image), cachedRect_(rect)
1392 {}
1393 #endif
1394 
SetIsParallelCanvas(bool isParallel)1395 void RSPaintFilterCanvas::SetIsParallelCanvas(bool isParallel)
1396 {
1397     isParallelCanvas_ = isParallel;
1398 }
1399 
GetIsParallelCanvas() const1400 bool RSPaintFilterCanvas::GetIsParallelCanvas() const
1401 {
1402     return isParallelCanvas_;
1403 }
1404 
SetDisableFilterCache(bool disable)1405 void RSPaintFilterCanvas::SetDisableFilterCache(bool disable)
1406 {
1407     disableFilterCache_ = disable;
1408 }
1409 
GetDisableFilterCache() const1410 bool RSPaintFilterCanvas::GetDisableFilterCache() const
1411 {
1412     return disableFilterCache_;
1413 }
1414 
SetRecordDrawable(bool enable)1415 void RSPaintFilterCanvas::SetRecordDrawable(bool enable)
1416 {
1417     recordDrawable_ = enable;
1418 }
1419 
GetRecordDrawable() const1420 bool RSPaintFilterCanvas::GetRecordDrawable() const
1421 {
1422     return recordDrawable_;
1423 }
1424 } // namespace Rosen
1425 } // namespace OHOS
1426