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#include "gm.h" 8#include "sk_tool_utils.h" 9#include "SkBitmap.h" 10#include "SkShader.h" 11#include "SkBlendModePriv.h" 12#include "SkColorPriv.h" 13 14namespace skiagm { 15 16class Xfermodes2GM : public GM { 17public: 18 Xfermodes2GM() {} 19 20protected: 21 SkString onShortName() override { 22 return SkString("xfermodes2"); 23 } 24 25 SkISize onISize() override { 26 return SkISize::Make(455, 475); 27 } 28 29 void onDraw(SkCanvas* canvas) override { 30 canvas->translate(SkIntToScalar(10), SkIntToScalar(20)); 31 32 const SkScalar w = SkIntToScalar(kSize); 33 const SkScalar h = SkIntToScalar(kSize); 34 35 SkPaint labelP; 36 labelP.setAntiAlias(true); 37 sk_tool_utils::set_portable_typeface(&labelP); 38 labelP.setTextAlign(SkPaint::kCenter_Align); 39 40 const int W = 6; 41 42 SkScalar x = 0, y = 0; 43 for (size_t m = 0; m <= (size_t)SkBlendMode::kLastMode; m++) { 44 SkBlendMode mode = static_cast<SkBlendMode>(m); 45 46 canvas->save(); 47 48 canvas->translate(x, y); 49 SkPaint p; 50 p.setAntiAlias(false); 51 p.setStyle(SkPaint::kFill_Style); 52 p.setShader(fBG); 53 SkRect r = SkRect::MakeWH(w, h); 54 canvas->drawRect(r, p); 55 56 canvas->saveLayer(&r, nullptr); 57 58 p.setShader(fDst); 59 canvas->drawRect(r, p); 60 p.setShader(fSrc); 61 p.setBlendMode(mode); 62 canvas->drawRect(r, p); 63 64 canvas->restore(); 65 66 r.inset(-SK_ScalarHalf, -SK_ScalarHalf); 67 p.setStyle(SkPaint::kStroke_Style); 68 p.setShader(nullptr); 69 p.setBlendMode(SkBlendMode::kSrcOver); 70 canvas->drawRect(r, p); 71 72 canvas->restore(); 73 74#if 1 75 canvas->drawString(SkBlendMode_Name(mode), 76 x + w/2, y - labelP.getTextSize()/2, labelP); 77#endif 78 x += w + SkIntToScalar(10); 79 if ((m % W) == W - 1) { 80 x = 0; 81 y += h + SkIntToScalar(30); 82 } 83 } 84 } 85 86private: 87 void onOnceBeforeDraw() override { 88 const uint32_t kCheckData[] = { 89 SkPackARGB32(0xFF, 0x42, 0x41, 0x42), 90 SkPackARGB32(0xFF, 0xD6, 0xD3, 0xD6), 91 SkPackARGB32(0xFF, 0xD6, 0xD3, 0xD6), 92 SkPackARGB32(0xFF, 0x42, 0x41, 0x42) 93 }; 94 SkBitmap bg; 95 bg.allocN32Pixels(2, 2, true); 96 memcpy(bg.getPixels(), kCheckData, sizeof(kCheckData)); 97 98 SkMatrix lm; 99 lm.setScale(SkIntToScalar(16), SkIntToScalar(16)); 100 fBG = SkShader::MakeBitmapShader(bg, SkShader::kRepeat_TileMode, SkShader::kRepeat_TileMode, 101 &lm); 102 103 SkBitmap srcBmp; 104 srcBmp.allocN32Pixels(kSize, kSize); 105 SkPMColor* pixels = reinterpret_cast<SkPMColor*>(srcBmp.getPixels()); 106 107 for (int y = 0; y < kSize; ++y) { 108 int c = y * (1 << kShift); 109 SkPMColor rowColor = SkPackARGB32(c, c, 0, c/2); 110 for (int x = 0; x < kSize; ++x) { 111 pixels[kSize * y + x] = rowColor; 112 } 113 } 114 fSrc = SkShader::MakeBitmapShader(srcBmp, SkShader::kClamp_TileMode, 115 SkShader::kClamp_TileMode); 116 SkBitmap dstBmp; 117 dstBmp.allocN32Pixels(kSize, kSize); 118 pixels = reinterpret_cast<SkPMColor*>(dstBmp.getPixels()); 119 120 for (int x = 0; x < kSize; ++x) { 121 int c = x * (1 << kShift); 122 SkPMColor colColor = SkPackARGB32(c, 0, c, c/2); 123 for (int y = 0; y < kSize; ++y) { 124 pixels[kSize * y + x] = colColor; 125 } 126 } 127 fDst = SkShader::MakeBitmapShader(dstBmp, SkShader::kClamp_TileMode, 128 SkShader::kClamp_TileMode); 129 } 130 131 enum { 132 kShift = 2, 133 kSize = 256 >> kShift, 134 }; 135 136 sk_sp<SkShader> fBG; 137 sk_sp<SkShader> fSrc; 138 sk_sp<SkShader> fDst; 139 140 typedef GM INHERITED; 141}; 142 143////////////////////////////////////////////////////////////////////////////// 144 145static GM* MyFactory(void*) { return new Xfermodes2GM; } 146static GMRegistry reg(MyFactory); 147 148} 149