Home | History | Annotate | Download | only in samplecode
      1 
      2 /*
      3  * Copyright 2011 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 "SampleCode.h"
      9 #include "SkView.h"
     10 #include "SkCanvas.h"
     11 #include "SkGradientShader.h"
     12 
     13 static SkShader* setgrad(const SkRect& r, SkColor c0, SkColor c1) {
     14     SkColor colors[] = { c0, c1 };
     15     SkPoint pts[] = { { r.fLeft, r.fTop }, { r.fRight, r.fTop } };
     16     return SkGradientShader::CreateLinear(pts, colors, NULL, 2, SkShader::kClamp_TileMode);
     17 }
     18 
     19 static void test_alphagradients(SkCanvas* canvas) {
     20     SkRect r;
     21     r.set(SkIntToScalar(10), SkIntToScalar(10),
     22           SkIntToScalar(410), SkIntToScalar(30));
     23     SkPaint p, p2;
     24     p2.setStyle(SkPaint::kStroke_Style);
     25 
     26     p.setShader(setgrad(r, 0xFF00FF00, 0x0000FF00))->unref();
     27     canvas->drawRect(r, p);
     28     canvas->drawRect(r, p2);
     29 
     30     r.offset(0, r.height() + SkIntToScalar(4));
     31     p.setShader(setgrad(r, 0xFF00FF00, 0x00000000))->unref();
     32     canvas->drawRect(r, p);
     33     canvas->drawRect(r, p2);
     34 
     35     r.offset(0, r.height() + SkIntToScalar(4));
     36     p.setShader(setgrad(r, 0xFF00FF00, 0x00FF0000))->unref();
     37     canvas->drawRect(r, p);
     38     canvas->drawRect(r, p2);
     39 }
     40 
     41 ///////////////////////////////////////////////////////////////////////////////
     42 
     43 struct GradData {
     44     int             fCount;
     45     const SkColor*  fColors;
     46     const SkScalar* fPos;
     47 };
     48 
     49 static const SkColor gColors[] = {
     50     SK_ColorRED, SK_ColorGREEN, SK_ColorBLUE, SK_ColorWHITE, SK_ColorBLACK
     51 };
     52 static const SkScalar gPos0[] = { 0, SK_Scalar1 };
     53 static const SkScalar gPos1[] = { SK_Scalar1/4, SK_Scalar1*3/4 };
     54 static const SkScalar gPos2[] = {
     55     0, SK_Scalar1/8, SK_Scalar1/2, SK_Scalar1*7/8, SK_Scalar1
     56 };
     57 
     58 static const GradData gGradData[] = {
     59     { 2, gColors, NULL },
     60     { 2, gColors, gPos0 },
     61     { 2, gColors, gPos1 },
     62     { 5, gColors, NULL },
     63     { 5, gColors, gPos2 }
     64 };
     65 
     66 static SkShader* MakeLinear(const SkPoint pts[2], const GradData& data, SkShader::TileMode tm) {
     67     return SkGradientShader::CreateLinear(pts, data.fColors, data.fPos, data.fCount, tm);
     68 }
     69 
     70 static SkShader* MakeRadial(const SkPoint pts[2], const GradData& data, SkShader::TileMode tm) {
     71     SkPoint center;
     72     center.set(SkScalarAve(pts[0].fX, pts[1].fX),
     73                SkScalarAve(pts[0].fY, pts[1].fY));
     74     return SkGradientShader::CreateRadial(center, center.fX, data.fColors,
     75                                           data.fPos, data.fCount, tm);
     76 }
     77 
     78 static SkShader* MakeSweep(const SkPoint pts[2], const GradData& data, SkShader::TileMode tm) {
     79     SkPoint center;
     80     center.set(SkScalarAve(pts[0].fX, pts[1].fX),
     81                SkScalarAve(pts[0].fY, pts[1].fY));
     82     return SkGradientShader::CreateSweep(center.fX, center.fY, data.fColors, data.fPos, data.fCount);
     83 }
     84 
     85 static SkShader* Make2Radial(const SkPoint pts[2], const GradData& data, SkShader::TileMode tm) {
     86     SkPoint center0, center1;
     87     center0.set(SkScalarAve(pts[0].fX, pts[1].fX),
     88                 SkScalarAve(pts[0].fY, pts[1].fY));
     89     center1.set(SkScalarInterp(pts[0].fX, pts[1].fX, SkIntToScalar(3)/5),
     90                 SkScalarInterp(pts[0].fY, pts[1].fY, SkIntToScalar(1)/4));
     91     return SkGradientShader::CreateTwoPointRadial(
     92                             center1, (pts[1].fX - pts[0].fX) / 7,
     93                             center0, (pts[1].fX - pts[0].fX) / 2,
     94                             data.fColors, data.fPos, data.fCount, tm);
     95 }
     96 
     97 static SkShader* Make2RadialConcentric(const SkPoint pts[2], const GradData& data,
     98                                        SkShader::TileMode tm) {
     99     SkPoint center;
    100     center.set(SkScalarAve(pts[0].fX, pts[1].fX),
    101                SkScalarAve(pts[0].fY, pts[1].fY));
    102     return SkGradientShader::CreateTwoPointRadial(
    103                             center, (pts[1].fX - pts[0].fX) / 7,
    104                             center, (pts[1].fX - pts[0].fX) / 2,
    105                             data.fColors, data.fPos, data.fCount, tm);
    106 }
    107 
    108 typedef SkShader* (*GradMaker)(const SkPoint pts[2], const GradData& data, SkShader::TileMode tm);
    109 
    110 static const GradMaker gGradMakers[] = {
    111     MakeLinear, MakeRadial, MakeSweep, Make2Radial, Make2RadialConcentric
    112 };
    113 
    114 ///////////////////////////////////////////////////////////////////////////////
    115 
    116 class GradientsView : public SampleView {
    117 public:
    118     GradientsView() {
    119         this->setBGColor(0xFFDDDDDD);
    120     }
    121 
    122 protected:
    123     // overrides from SkEventSink
    124     virtual bool onQuery(SkEvent* evt) {
    125         if (SampleCode::TitleQ(*evt)) {
    126             SampleCode::TitleR(evt, "Gradients");
    127             return true;
    128         }
    129         return this->INHERITED::onQuery(evt);
    130     }
    131 
    132     virtual void onDrawContent(SkCanvas* canvas) {
    133         SkPoint pts[2] = {
    134             { 0, 0 },
    135             { SkIntToScalar(100), SkIntToScalar(100) }
    136         };
    137         SkRect r = { 0, 0, SkIntToScalar(100), SkIntToScalar(100) };
    138         SkPaint paint;
    139         paint.setDither(true);
    140 
    141         canvas->save();
    142         canvas->translate(SkIntToScalar(20), SkIntToScalar(10));
    143 
    144         for (int tm = 0; tm < SkShader::kTileModeCount; ++tm) {
    145             canvas->save();
    146             for (size_t i = 0; i < SK_ARRAY_COUNT(gGradData); i++) {
    147                 canvas->save();
    148                 for (size_t j = 0; j < SK_ARRAY_COUNT(gGradMakers); j++) {
    149                     SkShader* shader;
    150                     shader = gGradMakers[j](pts, gGradData[i], (SkShader::TileMode)tm);
    151                     paint.setShader(shader)->unref();
    152                     canvas->drawRect(r, paint);
    153                     canvas->translate(0, SkIntToScalar(120));
    154                 }
    155                 canvas->restore();
    156                 canvas->translate(SkIntToScalar(120), 0);
    157             }
    158             canvas->restore();
    159             canvas->translate(SK_ARRAY_COUNT(gGradData)*SkIntToScalar(120), 0);
    160         }
    161         canvas->restore();
    162 
    163         canvas->translate(0, SkIntToScalar(370));
    164         if (false) { // avoid bit rot, suppress warning
    165             test_alphagradients(canvas);
    166         }
    167         this->inval(NULL);
    168     }
    169 
    170 private:
    171     typedef SampleView INHERITED;
    172 };
    173 
    174 ///////////////////////////////////////////////////////////////////////////////
    175 
    176 static SkView* MyFactory() { return new GradientsView; }
    177 static SkViewRegister reg(MyFactory);
    178