Home | History | Annotate | Download | only in gm
      1 /*
      2  * Copyright 2011 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 
      9 #include "gm.h"
     10 #include "SkCanvas.h"
     11 #include "SkPath.h"
     12 #include "SkRandom.h"
     13 #include "SkRect.h"
     14 #include "SkRRect.h"
     15 
     16 namespace skiagm {
     17 
     18 class ComplexClip2GM : public GM {
     19 public:
     20     enum Clip {
     21         kRect_Clip,
     22         kRRect_Clip,
     23         kPath_Clip
     24     };
     25 
     26     ComplexClip2GM(Clip clip, bool antiAlias)
     27     : fClip(clip)
     28     , fAntiAlias(antiAlias) {
     29         SkScalar xA = 0.65f;
     30         SkScalar xF = 50.65f;
     31 
     32         SkScalar yA = 0.65f;
     33         SkScalar yF = 50.65f;
     34 
     35         fWidth = xF - xA;
     36         fHeight = yF - yA;
     37 
     38         fTotalWidth = kCols * fWidth + SK_Scalar1 * (kCols + 1) * kPadX;
     39         fTotalHeight = kRows * fHeight + SK_Scalar1 * (kRows + 1) * kPadY;
     40     }
     41 
     42 protected:
     43     void onOnceBeforeDraw() override {
     44         this->setBGColor(SkColorSetRGB(0xDD,0xA0,0xDD));
     45 
     46         // offset the rects a bit so we get antialiasing even in the rect case
     47         SkScalar xA = 0.65f;
     48         SkScalar xB = 10.65f;
     49         SkScalar xC = 20.65f;
     50         SkScalar xD = 30.65f;
     51         SkScalar xE = 40.65f;
     52         SkScalar xF = 50.65f;
     53 
     54         SkScalar yA = 0.65f;
     55         SkScalar yB = 10.65f;
     56         SkScalar yC = 20.65f;
     57         SkScalar yD = 30.65f;
     58         SkScalar yE = 40.65f;
     59         SkScalar yF = 50.65f;
     60 
     61         fRects[0].set(xB, yB, xE, yE);
     62         fRRects[0].setRectXY(fRects[0], 7, 7);
     63         fPaths[0].addRoundRect(fRects[0], 5, 5);
     64         fRectColors[0] = SK_ColorRED;
     65 
     66         fRects[1].set(xA, yA, xD, yD);
     67         fRRects[1].setRectXY(fRects[1], 7, 7);
     68         fPaths[1].addRoundRect(fRects[1], 5, 5);
     69         fRectColors[1] = SK_ColorGREEN;
     70 
     71         fRects[2].set(xC, yA, xF, yD);
     72         fRRects[2].setRectXY(fRects[2], 7, 7);
     73         fPaths[2].addRoundRect(fRects[2], 5, 5);
     74         fRectColors[2] = SK_ColorBLUE;
     75 
     76         fRects[3].set(xA, yC, xD, yF);
     77         fRRects[3].setRectXY(fRects[3], 7, 7);
     78         fPaths[3].addRoundRect(fRects[3], 5, 5);
     79         fRectColors[3] = SK_ColorYELLOW;
     80 
     81         fRects[4].set(xC, yC, xF, yF);
     82         fRRects[4].setRectXY(fRects[4], 7, 7);
     83         fPaths[4].addRoundRect(fRects[4], 5, 5);
     84         fRectColors[4] = SK_ColorCYAN;
     85 
     86         const SkClipOp ops[] = {
     87             kDifference_SkClipOp,
     88             kIntersect_SkClipOp,
     89             kUnion_SkClipOp,
     90             kXOR_SkClipOp,
     91             kReverseDifference_SkClipOp,
     92             kReplace_SkClipOp,
     93         };
     94 
     95         SkRandom r;
     96         for (int i = 0; i < kRows; ++i) {
     97             for (int j = 0; j < kCols; ++j) {
     98                 for (int k = 0; k < 5; ++k) {
     99                     fOps[j*kRows+i][k] = ops[r.nextU() % SK_ARRAY_COUNT(ops)];
    100                 }
    101             }
    102         }
    103     }
    104 
    105     static constexpr int kRows = 5;
    106     static constexpr int kCols = 5;
    107     static constexpr int kPadX = 20;
    108     static constexpr int kPadY = 20;
    109 
    110     static const char* ClipStr(Clip clip) {
    111         switch (clip) {
    112         case kRect_Clip:
    113             return "rect";
    114         case kRRect_Clip:
    115             return "rrect";
    116         case kPath_Clip:
    117             return "path";
    118         }
    119         SkDEBUGFAIL("Unknown clip type.");
    120         return "";
    121     }
    122 
    123     SkString onShortName() override {
    124         if (kRect_Clip == fClip && !fAntiAlias) {
    125             return SkString("complexclip2");
    126         }
    127 
    128         SkString str;
    129         str.printf("complexclip2_%s_%s",
    130                     ClipStr(fClip),
    131                     fAntiAlias ? "aa" : "bw");
    132         return str;
    133     }
    134 
    135     SkISize onISize() override {
    136         return SkISize::Make(SkScalarRoundToInt(fTotalWidth),
    137                              SkScalarRoundToInt(fTotalHeight));
    138     }
    139 
    140     void onDraw(SkCanvas* canvas) override {
    141         SkPaint rectPaint;
    142         rectPaint.setStyle(SkPaint::kStroke_Style);
    143         rectPaint.setStrokeWidth(-1);
    144 
    145         SkPaint fillPaint;
    146         fillPaint.setColor(SkColorSetRGB(0xA0,0xDD,0xA0));
    147 
    148         for (int i = 0; i < kRows; ++i) {
    149             for (int j = 0; j < kCols; ++j) {
    150                 canvas->save();
    151 
    152                 canvas->translate(kPadX * SK_Scalar1 + (fWidth + kPadX * SK_Scalar1)*j,
    153                                   kPadY * SK_Scalar1 + (fHeight + kPadY * SK_Scalar1)*i);
    154 
    155                 // draw the original shapes first so we can see the
    156                 // antialiasing on the clipped draw
    157                 for (int k = 0; k < 5; ++k) {
    158                     rectPaint.setColor(fRectColors[k]);
    159                     switch (fClip) {
    160                         case kRect_Clip:
    161                             canvas->drawRect(fRects[k], rectPaint);
    162                             break;
    163                         case kRRect_Clip:
    164                             canvas->drawRRect(fRRects[k], rectPaint);
    165                             break;
    166                         case kPath_Clip:
    167                             canvas->drawPath(fPaths[k], rectPaint);
    168                             break;
    169                     }
    170                 }
    171 
    172                 for (int k = 0; k < 5; ++k) {
    173                     switch (fClip) {
    174                         case kRect_Clip:
    175                             canvas->clipRect(fRects[k],
    176                                              fOps[j*kRows+i][k],
    177                                              fAntiAlias);
    178                             break;
    179                         case kRRect_Clip:
    180                             canvas->clipRRect(fRRects[k],
    181                                               fOps[j*kRows+i][k],
    182                                               fAntiAlias);
    183                             break;
    184                         case kPath_Clip:
    185                             canvas->clipPath(fPaths[k],
    186                                              fOps[j*kRows+i][k],
    187                                              fAntiAlias);
    188                             break;
    189                     }
    190                 }
    191                 canvas->drawRect(SkRect::MakeWH(fWidth, fHeight), fillPaint);
    192                 canvas->restore();
    193             }
    194         }
    195     }
    196 private:
    197     Clip fClip;
    198     bool fAntiAlias;
    199     SkRect fRects[5];
    200     SkRRect fRRects[5];
    201     SkPath fPaths[5];
    202     SkColor fRectColors[5];
    203     SkClipOp fOps[kRows * kCols][5];
    204     SkScalar fWidth;
    205     SkScalar fHeight;
    206     SkScalar fTotalWidth;
    207     SkScalar fTotalHeight;
    208 
    209     typedef GM INHERITED;
    210 };
    211 
    212 //////////////////////////////////////////////////////////////////////////////
    213 
    214 // bw
    215 DEF_GM( return new ComplexClip2GM(ComplexClip2GM::kRect_Clip, false); )
    216 DEF_GM( return new ComplexClip2GM(ComplexClip2GM::kRRect_Clip, false); )
    217 DEF_GM( return new ComplexClip2GM(ComplexClip2GM::kPath_Clip, false); )
    218 
    219 // aa
    220 DEF_GM( return new ComplexClip2GM(ComplexClip2GM::kRect_Clip, true); )
    221 DEF_GM( return new ComplexClip2GM(ComplexClip2GM::kRRect_Clip, true); )
    222 DEF_GM( return new ComplexClip2GM(ComplexClip2GM::kPath_Clip, true); )
    223 
    224 }
    225