blob: ae07d8e27463cf7fe5de1ec0c40a02389da850c6 [file] [log] [blame]
egdanieldf795032014-12-17 11:22:37 -08001
2/*
3 * Copyright 2014 Google Inc.
4 *
5 * Use of this source code is governed by a BSD-style license that can be
6 * found in the LICENSE file.
7 */
8#include "gm.h"
9#include "SkCanvas.h"
10#include "SkPath.h"
11
12namespace skiagm {
13
14static const SkColor gPathColor = SK_ColorYELLOW;
15
16class ComplexClip3GM : public GM {
17public:
18 ComplexClip3GM(bool doSimpleClipFirst)
19 : fDoSimpleClipFirst(doSimpleClipFirst) {
caryclark65cdba62015-06-15 06:51:08 -070020 this->setBGColor(sk_tool_utils::color_to_565(0xFFDDDDDD));
egdanieldf795032014-12-17 11:22:37 -080021 }
22
23protected:
egdanieldf795032014-12-17 11:22:37 -080024
25 SkString onShortName() {
26 SkString str;
27 str.printf("complexclip3_%s", fDoSimpleClipFirst ? "simple" : "complex");
28 return str;
29 }
30
31 SkISize onISize() { return SkISize::Make(1000, 950); }
32
33 virtual void onDraw(SkCanvas* canvas) {
34 SkPath clipSimple;
35 clipSimple.addCircle(SkIntToScalar(70), SkIntToScalar(50), SkIntToScalar(20));
36
37 SkRect r1 = { 10, 20, 70, 80 };
38 SkPath clipComplex;
39 clipComplex.moveTo(SkIntToScalar(40), SkIntToScalar(50));
40 clipComplex.arcTo(r1, SkIntToScalar(30), SkIntToScalar(300), false);
41 clipComplex.close();
42
43 SkPath* firstClip = &clipSimple;
44 SkPath* secondClip = &clipComplex;
45
46 if (!fDoSimpleClipFirst) {
47 SkTSwap<SkPath*>(firstClip, secondClip);
48 }
49
50 SkPaint paint;
51 paint.setAntiAlias(true);
caryclark1818acb2015-07-24 12:09:25 -070052 sk_tool_utils::set_portable_typeface(&paint);
egdanieldf795032014-12-17 11:22:37 -080053 paint.setTextSize(SkIntToScalar(20));
54
55 static const struct {
56 SkRegion::Op fOp;
57 const char* fName;
58 } gOps[] = {
59 {SkRegion::kIntersect_Op, "I"},
60 {SkRegion::kDifference_Op, "D" },
61 {SkRegion::kUnion_Op, "U"},
62 {SkRegion::kXOR_Op, "X" },
63 {SkRegion::kReverseDifference_Op, "R"}
64 };
65
66 canvas->translate(SkIntToScalar(20), SkIntToScalar(20));
67 canvas->scale(3 * SK_Scalar1 / 4, 3 * SK_Scalar1 / 4);
68
69 SkPaint pathPaint;
70 pathPaint.setAntiAlias(true);
71 pathPaint.setColor(gPathColor);
72
73 for (int invA = 0; invA < 2; ++invA) {
74 for (int aaBits = 0; aaBits < 4; ++aaBits) {
75 canvas->save();
76 for (size_t op = 0; op < SK_ARRAY_COUNT(gOps); ++op) {
77 for (int invB = 0; invB < 2; ++invB) {
78 bool doAAA = SkToBool(aaBits & 1);
79 bool doAAB = SkToBool(aaBits & 2);
80 bool doInvA = SkToBool(invA);
81 bool doInvB = SkToBool(invB);
82 canvas->save();
83 // set clip
84 firstClip->setFillType(doInvA ? SkPath::kInverseEvenOdd_FillType :
85 SkPath::kEvenOdd_FillType);
86 secondClip->setFillType(doInvB ? SkPath::kInverseEvenOdd_FillType :
87 SkPath::kEvenOdd_FillType);
88 canvas->clipPath(*firstClip, SkRegion::kIntersect_Op, doAAA);
89 canvas->clipPath(*secondClip, gOps[op].fOp, doAAB);
90
91 // draw rect clipped
92 SkRect r = { 0, 0, 100, 100 };
93 canvas->drawRect(r, pathPaint);
94 canvas->restore();
95
96
97 SkScalar txtX = SkIntToScalar(10);
98 paint.setColor(SK_ColorBLACK);
99 SkString str;
100 str.printf("%s%s %s %s%s", doAAA ? "A" : "B",
101 doInvA ? "I" : "N",
102 gOps[op].fName,
103 doAAB ? "A" : "B",
104 doInvB ? "I" : "N");
105
106 canvas->drawText(str.c_str(), strlen(str.c_str()), txtX, SkIntToScalar(130),
107 paint);
108 if (doInvB) {
109 canvas->translate(SkIntToScalar(150),0);
110 } else {
111 canvas->translate(SkIntToScalar(120),0);
112 }
113 }
114 }
115 canvas->restore();
116 canvas->translate(0, SkIntToScalar(150));
117 }
118 }
119 }
120
121private:
122 bool fDoSimpleClipFirst;
123
124 typedef GM INHERITED;
125};
126
127//////////////////////////////////////////////////////////////////////////////
128
129// Simple clip first
130DEF_GM( return new ComplexClip3GM(true); )
131// Complex clip first
132DEF_GM( return new ComplexClip3GM(false); )
133}