1*c8dee2aaSAndroid Build Coastguard Worker /* 2*c8dee2aaSAndroid Build Coastguard Worker * Copyright 2013 Google Inc. 3*c8dee2aaSAndroid Build Coastguard Worker * 4*c8dee2aaSAndroid Build Coastguard Worker * Use of this source code is governed by a BSD-style license that can be 5*c8dee2aaSAndroid Build Coastguard Worker * found in the LICENSE file. 6*c8dee2aaSAndroid Build Coastguard Worker */ 7*c8dee2aaSAndroid Build Coastguard Worker 8*c8dee2aaSAndroid Build Coastguard Worker #include "bench/Benchmark.h" 9*c8dee2aaSAndroid Build Coastguard Worker #include "include/core/SkCanvas.h" 10*c8dee2aaSAndroid Build Coastguard Worker #include "include/core/SkFont.h" 11*c8dee2aaSAndroid Build Coastguard Worker #include "include/core/SkPaint.h" 12*c8dee2aaSAndroid Build Coastguard Worker #include "include/core/SkString.h" 13*c8dee2aaSAndroid Build Coastguard Worker #include "include/core/SkTextBlob.h" 14*c8dee2aaSAndroid Build Coastguard Worker #include "src/base/SkRandom.h" 15*c8dee2aaSAndroid Build Coastguard Worker #include "src/core/SkBlendModePriv.h" 16*c8dee2aaSAndroid Build Coastguard Worker #include "tools/DecodeUtils.h" 17*c8dee2aaSAndroid Build Coastguard Worker #include "tools/Resources.h" 18*c8dee2aaSAndroid Build Coastguard Worker #include "tools/fonts/FontToolUtils.h" 19*c8dee2aaSAndroid Build Coastguard Worker 20*c8dee2aaSAndroid Build Coastguard Worker namespace { 21*c8dee2aaSAndroid Build Coastguard Worker enum Type { 22*c8dee2aaSAndroid Build Coastguard Worker kText, 23*c8dee2aaSAndroid Build Coastguard Worker kRect, 24*c8dee2aaSAndroid Build Coastguard Worker kSprite, 25*c8dee2aaSAndroid Build Coastguard Worker }; 26*c8dee2aaSAndroid Build Coastguard Worker } 27*c8dee2aaSAndroid Build Coastguard Worker 28*c8dee2aaSAndroid Build Coastguard Worker const char* gTypeNames[] = { 29*c8dee2aaSAndroid Build Coastguard Worker "mask", "rect", "sprite", 30*c8dee2aaSAndroid Build Coastguard Worker }; 31*c8dee2aaSAndroid Build Coastguard Worker 32*c8dee2aaSAndroid Build Coastguard Worker // Benchmark that draws non-AA rects or AA text with an SkBlendMode. 33*c8dee2aaSAndroid Build Coastguard Worker class XfermodeBench : public Benchmark { 34*c8dee2aaSAndroid Build Coastguard Worker public: XfermodeBench(SkBlendMode mode,Type t)35*c8dee2aaSAndroid Build Coastguard Worker XfermodeBench(SkBlendMode mode, Type t) : fBlendMode(mode) { 36*c8dee2aaSAndroid Build Coastguard Worker fType = t; 37*c8dee2aaSAndroid Build Coastguard Worker fName.printf("blendmicro_%s_%s", gTypeNames[t], SkBlendMode_Name(mode)); 38*c8dee2aaSAndroid Build Coastguard Worker } 39*c8dee2aaSAndroid Build Coastguard Worker 40*c8dee2aaSAndroid Build Coastguard Worker protected: onGetName()41*c8dee2aaSAndroid Build Coastguard Worker const char* onGetName() override { return fName.c_str(); } 42*c8dee2aaSAndroid Build Coastguard Worker onDelayedSetup()43*c8dee2aaSAndroid Build Coastguard Worker void onDelayedSetup() override { 44*c8dee2aaSAndroid Build Coastguard Worker if (fType == kSprite) { 45*c8dee2aaSAndroid Build Coastguard Worker fImage = ToolUtils::GetResourceAsImage("images/color_wheel.png"); 46*c8dee2aaSAndroid Build Coastguard Worker } 47*c8dee2aaSAndroid Build Coastguard Worker } 48*c8dee2aaSAndroid Build Coastguard Worker onDraw(int loops,SkCanvas * canvas)49*c8dee2aaSAndroid Build Coastguard Worker void onDraw(int loops, SkCanvas* canvas) override { 50*c8dee2aaSAndroid Build Coastguard Worker const char* text = "Hamburgefons"; 51*c8dee2aaSAndroid Build Coastguard Worker size_t len = strlen(text); 52*c8dee2aaSAndroid Build Coastguard Worker SkISize size = canvas->getBaseLayerSize(); 53*c8dee2aaSAndroid Build Coastguard Worker SkRandom random; 54*c8dee2aaSAndroid Build Coastguard Worker while (loops > 0) { 55*c8dee2aaSAndroid Build Coastguard Worker SkPaint paint; 56*c8dee2aaSAndroid Build Coastguard Worker paint.setBlendMode(fBlendMode); 57*c8dee2aaSAndroid Build Coastguard Worker paint.setColor(random.nextU()); 58*c8dee2aaSAndroid Build Coastguard Worker switch (fType) { 59*c8dee2aaSAndroid Build Coastguard Worker case kText: { 60*c8dee2aaSAndroid Build Coastguard Worker // Draw text to exercise AA code paths. 61*c8dee2aaSAndroid Build Coastguard Worker SkFont font = ToolUtils::DefaultFont(); 62*c8dee2aaSAndroid Build Coastguard Worker font.setSize(random.nextRangeScalar(12, 96)); 63*c8dee2aaSAndroid Build Coastguard Worker SkScalar x = random.nextRangeScalar(0, (SkScalar)size.fWidth), 64*c8dee2aaSAndroid Build Coastguard Worker y = random.nextRangeScalar(0, (SkScalar)size.fHeight); 65*c8dee2aaSAndroid Build Coastguard Worker auto blob = SkTextBlob::MakeFromText(text, len, font, SkTextEncoding::kUTF8); 66*c8dee2aaSAndroid Build Coastguard Worker int iterations = std::min(1000, loops); 67*c8dee2aaSAndroid Build Coastguard Worker for (int j = 0; j < iterations; ++j) { 68*c8dee2aaSAndroid Build Coastguard Worker canvas->drawTextBlob(blob, x, y, paint); 69*c8dee2aaSAndroid Build Coastguard Worker } 70*c8dee2aaSAndroid Build Coastguard Worker loops -= iterations; 71*c8dee2aaSAndroid Build Coastguard Worker } break; 72*c8dee2aaSAndroid Build Coastguard Worker case kRect: { 73*c8dee2aaSAndroid Build Coastguard Worker // Draw rects to exercise non-AA code paths. 74*c8dee2aaSAndroid Build Coastguard Worker SkScalar w = random.nextRangeScalar(50, 100); 75*c8dee2aaSAndroid Build Coastguard Worker SkScalar h = random.nextRangeScalar(50, 100); 76*c8dee2aaSAndroid Build Coastguard Worker SkRect rect = SkRect::MakeXYWH( 77*c8dee2aaSAndroid Build Coastguard Worker random.nextUScalar1() * (size.fWidth - w), 78*c8dee2aaSAndroid Build Coastguard Worker random.nextUScalar1() * (size.fHeight - h), 79*c8dee2aaSAndroid Build Coastguard Worker w, 80*c8dee2aaSAndroid Build Coastguard Worker h 81*c8dee2aaSAndroid Build Coastguard Worker ); 82*c8dee2aaSAndroid Build Coastguard Worker int iterations = std::min(1000, loops); 83*c8dee2aaSAndroid Build Coastguard Worker for (int j = 0; j < iterations; ++j) { 84*c8dee2aaSAndroid Build Coastguard Worker canvas->drawRect(rect, paint); 85*c8dee2aaSAndroid Build Coastguard Worker } 86*c8dee2aaSAndroid Build Coastguard Worker loops -= iterations; 87*c8dee2aaSAndroid Build Coastguard Worker } break; 88*c8dee2aaSAndroid Build Coastguard Worker case kSprite: 89*c8dee2aaSAndroid Build Coastguard Worker paint.setAlphaf(1.0f); 90*c8dee2aaSAndroid Build Coastguard Worker for (int i = 0; i < 10; ++i) { 91*c8dee2aaSAndroid Build Coastguard Worker canvas->drawImage(fImage, 0, 0, SkSamplingOptions(), &paint); 92*c8dee2aaSAndroid Build Coastguard Worker } 93*c8dee2aaSAndroid Build Coastguard Worker loops -= 1; 94*c8dee2aaSAndroid Build Coastguard Worker break; 95*c8dee2aaSAndroid Build Coastguard Worker } 96*c8dee2aaSAndroid Build Coastguard Worker } 97*c8dee2aaSAndroid Build Coastguard Worker } 98*c8dee2aaSAndroid Build Coastguard Worker 99*c8dee2aaSAndroid Build Coastguard Worker private: 100*c8dee2aaSAndroid Build Coastguard Worker SkBlendMode fBlendMode; 101*c8dee2aaSAndroid Build Coastguard Worker SkString fName; 102*c8dee2aaSAndroid Build Coastguard Worker sk_sp<SkImage> fImage; 103*c8dee2aaSAndroid Build Coastguard Worker Type fType; 104*c8dee2aaSAndroid Build Coastguard Worker 105*c8dee2aaSAndroid Build Coastguard Worker using INHERITED = Benchmark; 106*c8dee2aaSAndroid Build Coastguard Worker }; 107*c8dee2aaSAndroid Build Coastguard Worker 108*c8dee2aaSAndroid Build Coastguard Worker ////////////////////////////////////////////////////////////////////////////// 109*c8dee2aaSAndroid Build Coastguard Worker 110*c8dee2aaSAndroid Build Coastguard Worker #define BENCH(mode) \ 111*c8dee2aaSAndroid Build Coastguard Worker DEF_BENCH( return new XfermodeBench(mode, kText); ) \ 112*c8dee2aaSAndroid Build Coastguard Worker DEF_BENCH( return new XfermodeBench(mode, kRect); ) \ 113*c8dee2aaSAndroid Build Coastguard Worker DEF_BENCH( return new XfermodeBench(mode, kSprite); ) 114*c8dee2aaSAndroid Build Coastguard Worker 115*c8dee2aaSAndroid Build Coastguard Worker BENCH(SkBlendMode::kClear) 116*c8dee2aaSAndroid Build Coastguard Worker BENCH(SkBlendMode::kSrc) 117*c8dee2aaSAndroid Build Coastguard Worker BENCH(SkBlendMode::kDst) 118*c8dee2aaSAndroid Build Coastguard Worker BENCH(SkBlendMode::kSrcOver) 119*c8dee2aaSAndroid Build Coastguard Worker BENCH(SkBlendMode::kDstOver) 120*c8dee2aaSAndroid Build Coastguard Worker BENCH(SkBlendMode::kSrcIn) 121*c8dee2aaSAndroid Build Coastguard Worker BENCH(SkBlendMode::kDstIn) 122*c8dee2aaSAndroid Build Coastguard Worker BENCH(SkBlendMode::kSrcOut) 123*c8dee2aaSAndroid Build Coastguard Worker BENCH(SkBlendMode::kDstOut) 124*c8dee2aaSAndroid Build Coastguard Worker BENCH(SkBlendMode::kSrcATop) 125*c8dee2aaSAndroid Build Coastguard Worker BENCH(SkBlendMode::kDstATop) 126*c8dee2aaSAndroid Build Coastguard Worker BENCH(SkBlendMode::kXor) 127*c8dee2aaSAndroid Build Coastguard Worker 128*c8dee2aaSAndroid Build Coastguard Worker BENCH(SkBlendMode::kPlus) 129*c8dee2aaSAndroid Build Coastguard Worker BENCH(SkBlendMode::kModulate) 130*c8dee2aaSAndroid Build Coastguard Worker BENCH(SkBlendMode::kScreen) 131*c8dee2aaSAndroid Build Coastguard Worker 132*c8dee2aaSAndroid Build Coastguard Worker BENCH(SkBlendMode::kOverlay) 133*c8dee2aaSAndroid Build Coastguard Worker BENCH(SkBlendMode::kDarken) 134*c8dee2aaSAndroid Build Coastguard Worker BENCH(SkBlendMode::kLighten) 135*c8dee2aaSAndroid Build Coastguard Worker BENCH(SkBlendMode::kColorDodge) 136*c8dee2aaSAndroid Build Coastguard Worker BENCH(SkBlendMode::kColorBurn) 137*c8dee2aaSAndroid Build Coastguard Worker BENCH(SkBlendMode::kHardLight) 138*c8dee2aaSAndroid Build Coastguard Worker BENCH(SkBlendMode::kSoftLight) 139*c8dee2aaSAndroid Build Coastguard Worker BENCH(SkBlendMode::kDifference) 140*c8dee2aaSAndroid Build Coastguard Worker BENCH(SkBlendMode::kExclusion) 141*c8dee2aaSAndroid Build Coastguard Worker BENCH(SkBlendMode::kMultiply) 142*c8dee2aaSAndroid Build Coastguard Worker 143*c8dee2aaSAndroid Build Coastguard Worker BENCH(SkBlendMode::kHue) 144*c8dee2aaSAndroid Build Coastguard Worker BENCH(SkBlendMode::kSaturation) 145*c8dee2aaSAndroid Build Coastguard Worker BENCH(SkBlendMode::kColor) 146*c8dee2aaSAndroid Build Coastguard Worker BENCH(SkBlendMode::kLuminosity) 147