1 /* 2 * Copyright 2016 Google Inc. 3 * 4 * Use of this source code is governed by a BSD-style license that can be 5 * found in the LICENSE file. 6 */ 7 8 #include "gm/gm.h" 9 #include "include/core/SkCanvas.h" 10 #include "include/core/SkColor.h" 11 #include "include/core/SkPaint.h" 12 #include "include/core/SkPath.h" 13 #include "include/core/SkRRect.h" 14 #include "include/core/SkRect.h" 15 #include "include/core/SkScalar.h" 16 #include "include/core/SkSize.h" 17 #include "include/core/SkString.h" 18 #include "src/core/SkCanvasPriv.h" 19 20 namespace skiagm { 21 22 // This test exercise SkCanvas::androidFramework_replaceClip behavior 23 class ComplexClip4GM : public GM { 24 public: ComplexClip4GM(bool aaclip)25 ComplexClip4GM(bool aaclip) 26 : fDoAAClip(aaclip) { 27 this->setBGColor(0xFFDEDFDE); 28 } 29 30 protected: onShortName()31 SkString onShortName() override { 32 SkString str; 33 str.printf("complexclip4_%s", 34 fDoAAClip ? "aa" : "bw"); 35 return str; 36 } 37 onISize()38 SkISize onISize() override { return SkISize::Make(970, 780); } 39 40 // Android Framework will still support the legacy kReplace SkClipOp on older devices, so 41 // this represents how to do so while also respecting the device restriction using the newer 42 // androidFramework_resetClip() API. emulateDeviceRestriction(SkCanvas * canvas,const SkIRect & deviceRestriction)43 void emulateDeviceRestriction(SkCanvas* canvas, const SkIRect& deviceRestriction) { 44 // TODO(michaelludwig): It may make more sense for device clip restriction to move on to 45 // the SkSurface (which would let this GM draw correctly in viewer). 46 canvas->androidFramework_setDeviceClipRestriction(deviceRestriction); 47 } 48 emulateClipRectReplace(SkCanvas * canvas,const SkRect & clipRect,bool aa)49 void emulateClipRectReplace(SkCanvas* canvas, 50 const SkRect& clipRect, 51 bool aa) { 52 SkCanvasPriv::ResetClip(canvas); 53 canvas->clipRect(clipRect, SkClipOp::kIntersect, aa); 54 } 55 emulateClipRRectReplace(SkCanvas * canvas,const SkRRect & clipRRect,bool aa)56 void emulateClipRRectReplace(SkCanvas* canvas, 57 const SkRRect& clipRRect, 58 bool aa) { 59 SkCanvasPriv::ResetClip(canvas); 60 canvas->clipRRect(clipRRect, SkClipOp::kIntersect, aa); 61 } 62 emulateClipPathReplace(SkCanvas * canvas,const SkPath & path,bool aa)63 void emulateClipPathReplace(SkCanvas* canvas, 64 const SkPath& path, 65 bool aa) { 66 SkCanvasPriv::ResetClip(canvas); 67 canvas->clipPath(path, SkClipOp::kIntersect, aa); 68 } 69 onDraw(SkCanvas * canvas)70 void onDraw(SkCanvas* canvas) override { 71 SkPaint p; 72 p.setAntiAlias(fDoAAClip); 73 p.setColor(SK_ColorYELLOW); 74 75 canvas->save(); 76 // draw a yellow rect through a rect clip 77 canvas->save(); 78 emulateDeviceRestriction(canvas, SkIRect::MakeLTRB(100, 100, 300, 300)); 79 canvas->drawColor(SK_ColorGREEN); 80 emulateClipRectReplace(canvas, SkRect::MakeLTRB(100, 200, 400, 500), fDoAAClip); 81 canvas->drawRect(SkRect::MakeLTRB(100, 200, 400, 500), p); 82 canvas->restore(); 83 84 // draw a yellow rect through a diamond clip 85 canvas->save(); 86 emulateDeviceRestriction(canvas, SkIRect::MakeLTRB(500, 100, 800, 300)); 87 canvas->drawColor(SK_ColorGREEN); 88 89 SkPath pathClip = SkPath::Polygon({ 90 {650, 200}, 91 {900, 300}, 92 {650, 400}, 93 {650, 300}, 94 }, true); 95 emulateClipPathReplace(canvas, pathClip, fDoAAClip); 96 canvas->drawRect(SkRect::MakeLTRB(500, 200, 900, 500), p); 97 canvas->restore(); 98 99 // draw a yellow rect through a round rect clip 100 canvas->save(); 101 emulateDeviceRestriction(canvas, SkIRect::MakeLTRB(500, 500, 800, 700)); 102 canvas->drawColor(SK_ColorGREEN); 103 104 emulateClipRRectReplace( 105 canvas, SkRRect::MakeOval(SkRect::MakeLTRB(500, 600, 900, 750)), fDoAAClip); 106 canvas->drawRect(SkRect::MakeLTRB(500, 600, 900, 750), p); 107 canvas->restore(); 108 109 // fill the clip with yellow color showing that androidFramework_replaceClip is 110 // in device space 111 canvas->save(); 112 canvas->clipRect(SkRect::MakeLTRB(100, 400, 300, 750), 113 SkClipOp::kIntersect, fDoAAClip); 114 canvas->drawColor(SK_ColorGREEN); 115 // should not affect the device-space clip 116 canvas->rotate(20.f); 117 canvas->translate(50.f, 50.f); 118 emulateDeviceRestriction(canvas, SkIRect::MakeLTRB(150, 450, 250, 700)); 119 canvas->drawColor(SK_ColorYELLOW); 120 canvas->restore(); 121 122 canvas->restore(); 123 } 124 private: 125 bool fDoAAClip; 126 127 using INHERITED = GM; 128 }; 129 130 ////////////////////////////////////////////////////////////////////////////// 131 132 DEF_GM(return new ComplexClip4GM(false);) 133 DEF_GM(return new ComplexClip4GM(true);) 134 } // namespace skiagm 135