blob: 5bd5640eea9ab5dfa99e4c6371967110063267d3 [file] [log] [blame]
epoger@google.comec3ed6a2011-07-28 14:26:00 +00001
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 */
tfarinaf168b862014-06-19 12:32:29 -07008#include "Benchmark.h"
reed@android.combd700c32009-01-05 03:34:50 +00009#include "SkCanvas.h"
mtklein@google.comc2897432013-09-10 19:23:38 +000010#include "SkCommandLineFlags.h"
reed@android.combd700c32009-01-05 03:34:50 +000011#include "SkPaint.h"
12#include "SkRandom.h"
reed@google.com981d4792011-03-09 12:55:47 +000013#include "SkShader.h"
mtklein@google.comc2897432013-09-10 19:23:38 +000014#include "SkString.h"
15
16DEFINE_double(strokeWidth, -1.0, "If set, use this stroke width in RectBench.");
reed@android.combd700c32009-01-05 03:34:50 +000017
tfarinaf168b862014-06-19 12:32:29 -070018class RectBench : public Benchmark {
reed@android.combd700c32009-01-05 03:34:50 +000019public:
mike@reedtribe.org2ecead52011-04-02 13:37:23 +000020 int fShift, fStroke;
reed@android.combd700c32009-01-05 03:34:50 +000021 enum {
22 W = 640,
23 H = 480,
mtklein@google.comc2897432013-09-10 19:23:38 +000024 N = 300,
reed@android.combd700c32009-01-05 03:34:50 +000025 };
26 SkRect fRects[N];
27 SkColor fColors[N];
28
mtklein@google.com410e6e82013-09-13 19:52:27 +000029 RectBench(int shift, int stroke = 0)
30 : fShift(shift)
commit-bot@chromium.org000d7322013-12-05 12:07:44 +000031 , fStroke(stroke) {}
reed@google.com1fcd51e2011-01-05 15:50:27 +000032
reed@android.comd2c37442009-01-08 03:00:57 +000033 SkString fName;
34 const char* computeName(const char root[]) {
mike@reedtribe.org2ecead52011-04-02 13:37:23 +000035 fName.printf("%s_%d", root, fShift);
36 if (fStroke > 0) {
37 fName.appendf("_stroke_%d", fStroke);
38 }
reed@android.comd2c37442009-01-08 03:00:57 +000039 return fName.c_str();
40 }
reed@google.com1fcd51e2011-01-05 15:50:27 +000041
joshualitt7d4b4582015-09-24 08:08:23 -070042 bool isVisual() override { return true; }
43
reed@android.combd700c32009-01-05 03:34:50 +000044protected:
45 virtual void drawThisRect(SkCanvas* c, const SkRect& r, const SkPaint& p) {
46 c->drawRect(r, p);
47 }
48
reed57b76712015-09-25 04:49:43 -070049 const char* onGetName() override { return computeName("rects"); }
commit-bot@chromium.org000d7322013-12-05 12:07:44 +000050
joshualitt8a6697a2015-09-30 12:11:07 -070051 void onDelayedSetup() override {
commit-bot@chromium.org000d7322013-12-05 12:07:44 +000052 SkRandom rand;
53 const SkScalar offset = SK_Scalar1/3;
54 for (int i = 0; i < N; i++) {
55 int x = rand.nextU() % W;
56 int y = rand.nextU() % H;
57 int w = rand.nextU() % W;
58 int h = rand.nextU() % H;
59 w >>= fShift;
60 h >>= fShift;
61 x -= w/2;
62 y -= h/2;
63 fRects[i].set(SkIntToScalar(x), SkIntToScalar(y),
64 SkIntToScalar(x+w), SkIntToScalar(y+h));
65 fRects[i].offset(offset, offset);
66 fColors[i] = rand.nextU() | 0xFF808080;
67 }
68 }
69
mtkleina1ebeb22015-10-01 09:43:39 -070070 void onDraw(int loops, SkCanvas* canvas) override {
reed@android.combd700c32009-01-05 03:34:50 +000071 SkPaint paint;
mike@reedtribe.org2ecead52011-04-02 13:37:23 +000072 if (fStroke > 0) {
73 paint.setStyle(SkPaint::kStroke_Style);
74 paint.setStrokeWidth(SkIntToScalar(fStroke));
75 }
commit-bot@chromium.org33614712013-12-03 18:17:16 +000076 for (int i = 0; i < loops; i++) {
mtklein@google.comc2897432013-09-10 19:23:38 +000077 paint.setColor(fColors[i % N]);
reed@android.com4bc19832009-01-19 20:08:35 +000078 this->setupPaint(&paint);
mtklein@google.comc2897432013-09-10 19:23:38 +000079 this->drawThisRect(canvas, fRects[i % N], paint);
reed@android.combd700c32009-01-05 03:34:50 +000080 }
81 }
reed@android.come9d00602009-09-02 21:12:42 +000082private:
tfarinaf168b862014-06-19 12:32:29 -070083 typedef Benchmark INHERITED;
reed@android.combd700c32009-01-05 03:34:50 +000084};
85
reed@google.com2d078b62012-11-15 19:52:07 +000086class SrcModeRectBench : public RectBench {
87public:
mtklein@google.com410e6e82013-09-13 19:52:27 +000088 SrcModeRectBench() : INHERITED(1, 0) {
reed@google.com2d078b62012-11-15 19:52:07 +000089 fMode = SkXfermode::Create(SkXfermode::kSrc_Mode);
90 }
skia.committer@gmail.com884e60b2012-11-16 02:01:17 +000091
reed@google.com2d078b62012-11-15 19:52:07 +000092 virtual ~SrcModeRectBench() {
93 SkSafeUnref(fMode);
94 }
95
96protected:
mtklein36352bf2015-03-25 18:17:31 -070097 void setupPaint(SkPaint* paint) override {
reed@google.com2d078b62012-11-15 19:52:07 +000098 this->INHERITED::setupPaint(paint);
99 // srcmode is most interesting when we're not opaque
100 paint->setAlpha(0x80);
101 paint->setXfermode(fMode);
102 }
103
mtklein36352bf2015-03-25 18:17:31 -0700104 const char* onGetName() override {
reed@google.com2d078b62012-11-15 19:52:07 +0000105 fName.set(this->INHERITED::onGetName());
106 fName.prepend("srcmode_");
107 return fName.c_str();
108 }
109
110private:
111 SkString fName;
112 SkXfermode* fMode;
113
114 typedef RectBench INHERITED;
115};
116
joshualitt8db65a62015-09-24 12:42:02 -0700117class TransparentRectBench : public RectBench {
118public:
119 TransparentRectBench() : INHERITED(1, 0) {}
120
121protected:
122 void setupPaint(SkPaint* paint) override {
123 this->INHERITED::setupPaint(paint);
124 // draw non opaque rect
125 paint->setAlpha(0x80);
126 }
127
128 const char* onGetName() override {
129 fName.set(this->INHERITED::onGetName());
130 fName.prepend("transparent_");
131 return fName.c_str();
132 }
133
134private:
135 SkString fName;
136
137 typedef RectBench INHERITED;
138};
139
140
reed@android.combd700c32009-01-05 03:34:50 +0000141class OvalBench : public RectBench {
reed@android.comd2c37442009-01-08 03:00:57 +0000142public:
mtklein@google.com410e6e82013-09-13 19:52:27 +0000143 OvalBench(int shift, int stroke = 0) : RectBench(shift, stroke) {}
reed@android.combd700c32009-01-05 03:34:50 +0000144protected:
reed57b76712015-09-25 04:49:43 -0700145 void drawThisRect(SkCanvas* c, const SkRect& r, const SkPaint& p) override {
reed@android.combd700c32009-01-05 03:34:50 +0000146 c->drawOval(r, p);
147 }
reed57b76712015-09-25 04:49:43 -0700148 const char* onGetName() override { return computeName("ovals"); }
reed@android.combd700c32009-01-05 03:34:50 +0000149};
150
151class RRectBench : public RectBench {
reed@android.comd2c37442009-01-08 03:00:57 +0000152public:
mtklein@google.com410e6e82013-09-13 19:52:27 +0000153 RRectBench(int shift, int stroke = 0) : RectBench(shift, stroke) {}
reed@android.combd700c32009-01-05 03:34:50 +0000154protected:
reed57b76712015-09-25 04:49:43 -0700155 void drawThisRect(SkCanvas* c, const SkRect& r, const SkPaint& p) override {
reed@android.combd700c32009-01-05 03:34:50 +0000156 c->drawRoundRect(r, r.width() / 4, r.height() / 4, p);
157 }
reed57b76712015-09-25 04:49:43 -0700158 const char* onGetName() override { return computeName("rrects"); }
reed@android.combd700c32009-01-05 03:34:50 +0000159};
160
161class PointsBench : public RectBench {
162public:
163 SkCanvas::PointMode fMode;
164 const char* fName;
165
mtklein@google.com410e6e82013-09-13 19:52:27 +0000166 PointsBench(SkCanvas::PointMode mode, const char* name)
167 : RectBench(2)
168 , fMode(mode) {
reed@android.combd700c32009-01-05 03:34:50 +0000169 fName = name;
170 }
171
172protected:
mtkleina1ebeb22015-10-01 09:43:39 -0700173 void onDraw(int loops, SkCanvas* canvas) override {
agl@chromium.org652807b2010-04-27 15:47:34 +0000174 SkScalar gSizes[] = {
reed@android.combd700c32009-01-05 03:34:50 +0000175 SkIntToScalar(7), 0
176 };
agl@chromium.org652807b2010-04-27 15:47:34 +0000177 size_t sizes = SK_ARRAY_COUNT(gSizes);
178
mtklein@google.comc2897432013-09-10 19:23:38 +0000179 if (FLAGS_strokeWidth >= 0) {
mtklein@google.comb87bf832013-09-10 19:51:10 +0000180 gSizes[0] = (SkScalar)FLAGS_strokeWidth;
agl@chromium.org652807b2010-04-27 15:47:34 +0000181 sizes = 1;
182 }
reed@android.combd700c32009-01-05 03:34:50 +0000183
184 SkPaint paint;
reed@android.combd700c32009-01-05 03:34:50 +0000185 paint.setStrokeCap(SkPaint::kRound_Cap);
agl@chromium.org652807b2010-04-27 15:47:34 +0000186
commit-bot@chromium.org33614712013-12-03 18:17:16 +0000187 for (int loop = 0; loop < loops; loop++) {
mtklein@google.comc2897432013-09-10 19:23:38 +0000188 for (size_t i = 0; i < sizes; i++) {
189 paint.setStrokeWidth(gSizes[i]);
190 this->setupPaint(&paint);
191 canvas->drawPoints(fMode, N * 2, SkTCast<SkPoint*>(fRects), paint);
192 paint.setColor(fColors[i % N]);
193 }
reed@android.combd700c32009-01-05 03:34:50 +0000194 }
195 }
reed57b76712015-09-25 04:49:43 -0700196 const char* onGetName() override { return fName; }
reed@android.combd700c32009-01-05 03:34:50 +0000197};
198
reed@google.com981d4792011-03-09 12:55:47 +0000199/*******************************************************************************
200 * to bench BlitMask [Opaque, Black, color, shader]
201 *******************************************************************************/
202
203class BlitMaskBench : public RectBench {
204public:
205 enum kMaskType {
206 kMaskOpaque = 0,
207 kMaskBlack,
208 kMaskColor,
209 KMaskShader
210 };
211 SkCanvas::PointMode fMode;
212 const char* fName;
213
mtklein@google.com410e6e82013-09-13 19:52:27 +0000214 BlitMaskBench(SkCanvas::PointMode mode,
reed@google.com981d4792011-03-09 12:55:47 +0000215 BlitMaskBench::kMaskType type, const char* name) :
mtklein@google.com410e6e82013-09-13 19:52:27 +0000216 RectBench(2), fMode(mode), _type(type) {
reed@google.com981d4792011-03-09 12:55:47 +0000217 fName = name;
218 }
219
220protected:
mtkleina1ebeb22015-10-01 09:43:39 -0700221 void onDraw(int loops, SkCanvas* canvas) override {
reed@google.com981d4792011-03-09 12:55:47 +0000222 SkScalar gSizes[] = {
223 SkIntToScalar(13), SkIntToScalar(24)
224 };
225 size_t sizes = SK_ARRAY_COUNT(gSizes);
226
mtklein@google.comc2897432013-09-10 19:23:38 +0000227 if (FLAGS_strokeWidth >= 0) {
mtklein@google.comb87bf832013-09-10 19:51:10 +0000228 gSizes[0] = (SkScalar)FLAGS_strokeWidth;
reed@google.com981d4792011-03-09 12:55:47 +0000229 sizes = 1;
230 }
commit-bot@chromium.orge0e7cfe2013-09-09 20:09:12 +0000231 SkRandom rand;
reed@google.com981d4792011-03-09 12:55:47 +0000232 SkColor color = 0xFF000000;
233 U8CPU alpha = 0xFF;
234 SkPaint paint;
235 paint.setStrokeCap(SkPaint::kRound_Cap);
236 if (_type == KMaskShader) {
237 SkBitmap srcBM;
reed6c225732014-06-09 19:52:07 -0700238 srcBM.allocN32Pixels(10, 1);
reed@google.com981d4792011-03-09 12:55:47 +0000239 srcBM.eraseColor(0xFF00FF00);
240
reedc6f28f72016-03-14 12:22:10 -0700241 paint.setShader(SkShader::MakeBitmapShader(srcBM, SkShader::kClamp_TileMode,
242 SkShader::kClamp_TileMode));
reed@google.com981d4792011-03-09 12:55:47 +0000243 }
commit-bot@chromium.org33614712013-12-03 18:17:16 +0000244 for (int loop = 0; loop < loops; loop++) {
mtklein@google.comc2897432013-09-10 19:23:38 +0000245 for (size_t i = 0; i < sizes; i++) {
246 switch (_type) {
247 case kMaskOpaque:
248 color = fColors[i];
249 alpha = 0xFF;
250 break;
251 case kMaskBlack:
252 alpha = 0xFF;
253 color = 0xFF000000;
254 break;
255 case kMaskColor:
256 color = fColors[i];
257 alpha = rand.nextU() & 255;
258 break;
259 case KMaskShader:
260 break;
261 }
262 paint.setStrokeWidth(gSizes[i]);
263 this->setupPaint(&paint);
264 paint.setColor(color);
265 paint.setAlpha(alpha);
266 canvas->drawPoints(fMode, N * 2, SkTCast<SkPoint*>(fRects), paint);
267 }
268 }
reed@google.com981d4792011-03-09 12:55:47 +0000269 }
reed57b76712015-09-25 04:49:43 -0700270 const char* onGetName() override { return fName; }
reed@google.com981d4792011-03-09 12:55:47 +0000271private:
rmistry@google.comfbfcd562012-08-23 18:09:54 +0000272 typedef RectBench INHERITED;
273 kMaskType _type;
reed@google.com981d4792011-03-09 12:55:47 +0000274};
275
halcanary385fe4d2015-08-26 13:07:48 -0700276DEF_BENCH(return new RectBench(1);)
277DEF_BENCH(return new RectBench(1, 4);)
278DEF_BENCH(return new RectBench(3);)
279DEF_BENCH(return new RectBench(3, 4);)
280DEF_BENCH(return new OvalBench(1);)
281DEF_BENCH(return new OvalBench(3);)
282DEF_BENCH(return new OvalBench(1, 4);)
283DEF_BENCH(return new OvalBench(3, 4);)
284DEF_BENCH(return new RRectBench(1);)
285DEF_BENCH(return new RRectBench(1, 4);)
286DEF_BENCH(return new RRectBench(3);)
287DEF_BENCH(return new RRectBench(3, 4);)
288DEF_BENCH(return new PointsBench(SkCanvas::kPoints_PointMode, "points");)
289DEF_BENCH(return new PointsBench(SkCanvas::kLines_PointMode, "lines");)
290DEF_BENCH(return new PointsBench(SkCanvas::kPolygon_PointMode, "polygon");)
reed@google.com981d4792011-03-09 12:55:47 +0000291
halcanary385fe4d2015-08-26 13:07:48 -0700292DEF_BENCH(return new SrcModeRectBench();)
robertphillips@google.com370d8352013-05-02 13:57:52 +0000293
joshualitt8db65a62015-09-24 12:42:02 -0700294DEF_BENCH(return new TransparentRectBench();)
295
reed@google.com981d4792011-03-09 12:55:47 +0000296/* init the blitmask bench
297 */
halcanary385fe4d2015-08-26 13:07:48 -0700298DEF_BENCH(return new BlitMaskBench(SkCanvas::kPoints_PointMode,
299 BlitMaskBench::kMaskOpaque,
300 "maskopaque");)
301DEF_BENCH(return new BlitMaskBench(SkCanvas::kPoints_PointMode,
302 BlitMaskBench::kMaskBlack,
303 "maskblack");)
304DEF_BENCH(return new BlitMaskBench(SkCanvas::kPoints_PointMode,
305 BlitMaskBench::kMaskColor,
306 "maskcolor");)
307DEF_BENCH(return new BlitMaskBench(SkCanvas::kPoints_PointMode,
308 BlitMaskBench::KMaskShader,
309 "maskshader");)