Home | History | Annotate | Download | only in gm
      1 /*
      2  * Copyright 2013 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.h"
      9 #include "SkCanvas.h"
     10 #include "SkPaint.h"
     11 #include "SkPath.h"
     12 #include "SkRect.h"
     13 
     14 namespace skiagm {
     15 
     16 /*
     17  * This GM exercises the flags to SkCanvas::save(). The canvas' save() and
     18  * restore actions can be limited to only a portion of the canvas' state through
     19  * the use of flags when calling save.
     20  */
     21 class CanvasStateGM : public GM {
     22     SkSize  fSize;
     23     enum {
     24         WIDTH = 150,
     25         HEIGHT = 150,
     26     };
     27 
     28     SkPaint fFillPaint;
     29     SkPaint fStrokePaint;
     30 
     31     SkPath fPath;
     32 
     33     SkRect fOutlineRect;
     34     SkRect fFillRect;
     35 
     36 
     37 public:
     38     CanvasStateGM() {
     39         fSize.set(SkIntToScalar(WIDTH), SkIntToScalar(HEIGHT));
     40 
     41         fFillPaint.setColor(SK_ColorRED);
     42         fFillPaint.setStyle(SkPaint::kFill_Style);
     43 
     44         fStrokePaint.setColor(SK_ColorBLUE);
     45         fStrokePaint.setStyle(SkPaint::kStroke_Style);
     46         fStrokePaint.setStrokeWidth(1);
     47 
     48         fPath.moveTo(25, 25);
     49         fPath.lineTo(125, 25);
     50         fPath.lineTo(75, 125);
     51         fPath.close();
     52 
     53         fOutlineRect = SkRect::MakeXYWH(1, 1, WIDTH-2, HEIGHT-2);
     54         fFillRect = SkRect::MakeXYWH(10, 10, WIDTH-20, HEIGHT-20);
     55     }
     56 
     57 protected:
     58     virtual SkString onShortName() SK_OVERRIDE {
     59         return SkString("canvas-state");
     60     }
     61 
     62     virtual SkISize onISize() SK_OVERRIDE {
     63         return SkISize::Make(WIDTH*3, HEIGHT*4);
     64     }
     65 
     66     virtual void onDraw(SkCanvas* canvas) SK_OVERRIDE {
     67 
     68         SkCanvas::SaveFlags flags[] = { SkCanvas::kMatrix_SaveFlag,
     69                                         SkCanvas::kClip_SaveFlag,
     70                                         SkCanvas::kMatrixClip_SaveFlag };
     71 
     72         // columns -- flags
     73         // rows -- permutations of setting the clip and matrix
     74         for (int i = 0; i < static_cast<int>(SK_ARRAY_COUNT(flags)); ++i) {
     75             for (int j = 0; j < 2; ++j) {
     76                 for (int k = 0; k < 2; ++k) {
     77                     this->drawTestPattern(i, (2*j)+k, canvas, flags[i],
     78                                           SkToBool(j), SkToBool(k));
     79                 }
     80             }
     81         }
     82     }
     83 
     84 
     85     virtual uint32_t onGetFlags() const SK_OVERRIDE { return kSkipPicture_Flag; }
     86 
     87 private:
     88     void drawTestPattern(int x, int y, SkCanvas* canvas,
     89                          SkCanvas::SaveFlags flags, bool doClip, bool doScale) {
     90         canvas->save();
     91         canvas->translate(SkIntToScalar(x*WIDTH), SkIntToScalar(y*HEIGHT));
     92 
     93         canvas->drawRect(fOutlineRect, fStrokePaint);
     94         canvas->save(flags);
     95         if(doClip) {
     96             canvas->clipPath(fPath);
     97         }
     98         if (doScale) {
     99             canvas->scale(SkDoubleToScalar(0.5), SkDoubleToScalar(0.5));
    100         }
    101         canvas->restore();
    102         canvas->drawRect(fFillRect, fFillPaint);
    103 
    104         canvas->restore();
    105     }
    106 
    107     typedef GM INHERITED;
    108 };
    109 
    110 //////////////////////////////////////////////////////////////////////////////
    111 
    112 class CanvasLayerStateGM : public GM {
    113 public:
    114     CanvasLayerStateGM() {
    115         fBluePaint.setColor(SK_ColorBLUE);
    116         fBluePaint.setStyle(SkPaint::kFill_Style);
    117 
    118         fRect = SkRect::MakeXYWH(SPACER, SPACER, WIDTH-(2*SPACER), (HEIGHT-(2*SPACER)) / 7);
    119     }
    120 
    121 protected:
    122     virtual SkString onShortName() SK_OVERRIDE {
    123         return SkString("canvas-layer-state");
    124     }
    125 
    126     virtual SkISize onISize() SK_OVERRIDE {
    127         return SkISize::Make(WIDTH, HEIGHT);
    128     }
    129 
    130     virtual void onDraw(SkCanvas* canvas) SK_OVERRIDE {
    131 
    132         // clear the canvas to red
    133         canvas->drawColor(SK_ColorRED);
    134 
    135 #ifdef SK_SUPPORT_LEGACY_CLIPTOLAYERFLAG
    136         // both rects should appear
    137         drawTestPattern(canvas, 255, SkCanvas::kARGB_NoClipLayer_SaveFlag);
    138 
    139         canvas->translate(0, 2*(fRect.height() + 10));
    140 
    141         // only the top rect should appear
    142         drawTestPattern(canvas, 255, SkCanvas::kARGB_ClipLayer_SaveFlag);
    143 
    144         canvas->translate(0, 2*(fRect.height() + 10));
    145 
    146         // only the bottom rect should appear
    147         drawTestPattern(canvas, 0, SkCanvas::kARGB_NoClipLayer_SaveFlag);
    148 #endif
    149     }
    150 
    151     virtual uint32_t onGetFlags() const SK_OVERRIDE { return kSkipGPU_Flag; }
    152 
    153 private:
    154     // draw a rect within the layer's bounds and again outside the layer's bounds
    155     void drawTestPattern(SkCanvas* canvas, U8CPU layerAlpha, SkCanvas::SaveFlags flags) {
    156         canvas->saveLayerAlpha(&fRect, layerAlpha, flags);
    157         canvas->drawRect(fRect, fBluePaint);
    158         canvas->translate(0, fRect.height() + 10);
    159         canvas->drawRect(fRect, fBluePaint);
    160         canvas->restore();
    161     }
    162 
    163     enum {
    164         WIDTH = 400,
    165         HEIGHT = 400,
    166         SPACER = 10,
    167     };
    168 
    169     SkPaint fBluePaint;
    170     SkRect fRect;
    171 
    172     typedef GM INHERITED;
    173 };
    174 
    175 //////////////////////////////////////////////////////////////////////////////
    176 
    177 DEF_GM( return SkNEW(CanvasStateGM); )
    178 DEF_GM( return SkNEW(CanvasLayerStateGM); )
    179 
    180 } // end namespace
    181