blob: 75811ee8ba729708a601406eeb67dce4743d693f [file] [log] [blame]
Robert Phillipsaea785b2018-08-03 11:15:24 -04001/*
2 * Copyright 2018 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 "sk_tool_utils.h"
10#include "SkBitmap.h"
11
12namespace skiagm {
13
14// This GM recreates the blend mode images from the Android documentation
15class AndroidBlendModesGM : public GM {
16public:
17 AndroidBlendModesGM() {
18 this->setBGColor(SK_ColorBLACK);
19 }
20
21protected:
22 SkString onShortName() override {
23 return SkString("androidblendmodes");
24 }
25
26 SkISize onISize() override {
27 return SkISize::Make(kNumCols * kBitmapSize, kNumRows * kBitmapSize);
28 }
29
30 void onOnceBeforeDraw() override {
31 SkImageInfo ii = SkImageInfo::MakeN32Premul(kBitmapSize, kBitmapSize);
32 {
33 fCompositeSrc.allocPixels(ii);
34 SkCanvas tmp(fCompositeSrc);
35 tmp.clear(SK_ColorTRANSPARENT);
36 SkPaint p;
37 p.setAntiAlias(true);
38 p.setColor(sk_tool_utils::color_to_565(kBlue));
39 tmp.drawRect(SkRect::MakeLTRB(16, 96, 160, 240), p);
40 }
41
42 {
43 fCompositeDst.allocPixels(ii);
44 SkCanvas tmp(fCompositeDst);
45 tmp.clear(SK_ColorTRANSPARENT);
46 SkPaint p;
47 p.setAntiAlias(true);
48 p.setColor(sk_tool_utils::color_to_565(kRed));
49 tmp.drawCircle(160, 95, 80, p);
50 }
51 }
52
53 void drawTile(SkCanvas* canvas, int xOffset, int yOffset, SkBlendMode mode) {
54 canvas->translate(xOffset, yOffset);
55
56 canvas->clipRect(SkRect::MakeXYWH(0, 0, 256, 256));
57
58 canvas->saveLayer(nullptr, nullptr);
59
60 SkPaint p;
61 canvas->drawBitmap(fCompositeDst, 0, 0, &p);
62 p.setBlendMode(mode);
63 canvas->drawBitmap(fCompositeSrc, 0, 0, &p);
64 }
65
66 void onDraw(SkCanvas* canvas) override {
67 SkPaint textPaint;
68 textPaint.setAntiAlias(true);
69 sk_tool_utils::set_portable_typeface(&textPaint);
70 textPaint.setTextAlign(SkPaint::kCenter_Align);
71
72 sk_tool_utils::draw_checkerboard(canvas,
Mike Kleind46dce32018-08-16 10:17:03 -040073 kWhite,
74 kGrey,
Robert Phillipsaea785b2018-08-03 11:15:24 -040075 32);
76
77 int xOffset = 0, yOffset = 0;
78
79 // Android doesn't expose all the blend modes
80 // Note that the Android documentation calls:
81 // Skia's kPlus, add
82 // Skia's kModulate, multiply
83 for (SkBlendMode mode : { SkBlendMode::kPlus /* add */, SkBlendMode::kClear,
84 SkBlendMode::kDarken, SkBlendMode::kDst,
85 SkBlendMode::kDstATop, SkBlendMode::kDstIn,
86 SkBlendMode::kDstOut, SkBlendMode::kDstOver,
87 SkBlendMode::kLighten, SkBlendMode::kModulate /* multiply */,
88 SkBlendMode::kOverlay, SkBlendMode::kScreen,
89 SkBlendMode::kSrc, SkBlendMode::kSrcATop,
90 SkBlendMode::kSrcIn, SkBlendMode::kSrcOut,
91 SkBlendMode::kSrcOver, SkBlendMode::kXor } ) {
92
93 int saveCount = canvas->save();
94 this->drawTile(canvas, xOffset, yOffset, mode);
95 canvas->restoreToCount(saveCount);
96
97 canvas->drawString(SkBlendMode_Name(mode),
98 xOffset + kBitmapSize/2.0f,
99 yOffset + kBitmapSize,
100 textPaint);
101
102 xOffset += 256;
103 if (xOffset >= 1024) {
104 xOffset = 0;
105 yOffset += 256;
106 }
107 }
108 }
109
110private:
111 static const int kBitmapSize = 256;
112 static const int kNumRows = 5;
113 static const int kNumCols = 4;
114
115 static const SkColor kBlue = SkColorSetARGB(255, 22, 150, 243);
116 static const SkColor kRed = SkColorSetARGB(255, 233, 30, 99);
117 static const SkColor kWhite = SkColorSetARGB(255, 243, 243, 243);
118 static const SkColor kGrey = SkColorSetARGB(255, 222, 222, 222);
119
120 SkBitmap fCompositeSrc;
121 SkBitmap fCompositeDst;
122
123 typedef GM INHERITED;
124};
125
126//////////////////////////////////////////////////////////////////////////////
127
128DEF_GM(return new AndroidBlendModesGM;)
129}