blob: 375560e15df659345c5098b23d0851087a145bc1 [file] [log] [blame]
dandovb3c9d1c2014-08-12 08:34:29 -07001/*
2 * Copyright 2014 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 "Benchmark.h"
dandovb3c9d1c2014-08-12 08:34:29 -07008#include "SkCanvas.h"
dandovb3c9d1c2014-08-12 08:34:29 -07009#include "SkGradientShader.h"
10#include "SkPaint.h"
11#include "SkPatchUtils.h"
dandovb3c9d1c2014-08-12 08:34:29 -070012#include "SkString.h"
dandov7e5598a2014-08-15 13:30:47 -070013
14/**
halcanary9d524f22016-03-29 09:03:52 -070015 * This bench measures the rendering time of the call SkCanvas::drawPatch with different types of
16 * input patches (regular case, with loops, a square, with a big difference between "parallel"
17 * sides). This bench also tests the different combination of optional parameters for the function
dandov7e5598a2014-08-15 13:30:47 -070018 * (passing texture coordinates and colors, only textures coordinates, only colors or none).
halcanary9d524f22016-03-29 09:03:52 -070019 * Finally, it applies a scale to test if the size affects the rendering time.
dandov7e5598a2014-08-15 13:30:47 -070020 */
dandovb3c9d1c2014-08-12 08:34:29 -070021
22class PatchBench : public Benchmark {
mtkleine556be72014-08-13 10:41:16 -070023
dandovb3c9d1c2014-08-12 08:34:29 -070024public:
mtkleine556be72014-08-13 10:41:16 -070025
dandovb3c9d1c2014-08-12 08:34:29 -070026 enum VertexMode {
27 kNone_VertexMode,
28 kColors_VertexMode,
29 kTexCoords_VertexMode,
30 kBoth_VertexMode
31 };
mtkleine556be72014-08-13 10:41:16 -070032
dandovb3c9d1c2014-08-12 08:34:29 -070033 PatchBench(SkPoint scale, VertexMode vertexMode)
34 : fScale(scale)
35 , fVertexMode(vertexMode) { }
36
37 // to add name of specific class override this method
38 virtual void appendName(SkString* name) {
39 name->append("normal");
40 }
mtkleine556be72014-08-13 10:41:16 -070041
dandovb3c9d1c2014-08-12 08:34:29 -070042 // to make other type of patches override this method
43 virtual void setCubics() {
44 const SkPoint points[SkPatchUtils::kNumCtrlPts] = {
45 //top points
46 {100,100},{150,50},{250,150}, {300,100},
47 //right points
48 {350, 150},{250,200},
49 //bottom points
50 {300,300},{250,250},{150,350},{100,300},
51 //left points
52 {50,250},{150,50}
53 };
54 memcpy(fCubics, points, SkPatchUtils::kNumCtrlPts * sizeof(SkPoint));
55 }
mtkleine556be72014-08-13 10:41:16 -070056
dandovb3c9d1c2014-08-12 08:34:29 -070057 virtual void setColors() {
58 const SkColor colors[SkPatchUtils::kNumCorners] = {
59 SK_ColorRED, SK_ColorGREEN, SK_ColorBLUE, SK_ColorCYAN
60 };
61 memcpy(fColors, colors, SkPatchUtils::kNumCorners * sizeof(SkColor));
62 }
mtkleine556be72014-08-13 10:41:16 -070063
dandovb3c9d1c2014-08-12 08:34:29 -070064 virtual void setTexCoords() {
65 const SkPoint texCoords[SkPatchUtils::kNumCorners] = {
66 {0.0f, 0.0f}, {1.0f, 0.0f}, {1.0f,1.0f}, {0.0f, 1.0f}
67 };
68 memcpy(fTexCoords, texCoords, SkPatchUtils::kNumCorners * sizeof(SkPoint));
69 }
mtkleine556be72014-08-13 10:41:16 -070070
dandovb3c9d1c2014-08-12 08:34:29 -070071 // override this method to change the shader
reedc6f28f72016-03-14 12:22:10 -070072 virtual sk_sp<SkShader> createShader() {
dandovb3c9d1c2014-08-12 08:34:29 -070073 const SkColor colors[] = {
74 SK_ColorRED, SK_ColorCYAN, SK_ColorGREEN, SK_ColorWHITE,
75 SK_ColorMAGENTA, SK_ColorBLUE, SK_ColorYELLOW,
76 };
77 const SkPoint pts[] = { { 200.f / 4.f, 0.f }, { 3.f * 200.f / 4, 200.f } };
mtkleine556be72014-08-13 10:41:16 -070078
reedc6f28f72016-03-14 12:22:10 -070079 return SkGradientShader::MakeLinear(pts, colors, nullptr, SK_ARRAY_COUNT(colors),
80 SkShader::kMirror_TileMode);
dandovb3c9d1c2014-08-12 08:34:29 -070081 }
82
83protected:
mtklein36352bf2015-03-25 18:17:31 -070084 const char* onGetName() override {
dandovb3c9d1c2014-08-12 08:34:29 -070085 SkString vertexMode;
86 switch (fVertexMode) {
87 case kNone_VertexMode:
88 vertexMode.set("meshlines");
89 break;
90 case kColors_VertexMode:
91 vertexMode.set("colors");
92 break;
93 case kTexCoords_VertexMode:
94 vertexMode.set("texs");
95 break;
96 case kBoth_VertexMode:
dandov7e5598a2014-08-15 13:30:47 -070097 vertexMode.set("colors_texs");
dandovb3c9d1c2014-08-12 08:34:29 -070098 break;
99 default:
100 break;
101 }
102 SkString type;
103 this->appendName(&type);
jcgregorio1703bd12016-08-29 13:33:04 -0700104 fName.printf("patch_%s_%s_%fx%f", type.c_str(), vertexMode.c_str(),
dandovb3c9d1c2014-08-12 08:34:29 -0700105 fScale.x(), fScale.y());
106 return fName.c_str();
107 }
mtkleine556be72014-08-13 10:41:16 -0700108
joshualitt8a6697a2015-09-30 12:11:07 -0700109 void onDelayedSetup() override {
dandovb3c9d1c2014-08-12 08:34:29 -0700110 this->setCubics();
111 this->setColors();
112 this->setTexCoords();
113 this->setupPaint(&fPaint);
114 switch (fVertexMode) {
115 case kTexCoords_VertexMode:
116 case kBoth_VertexMode:
reedc6f28f72016-03-14 12:22:10 -0700117 fPaint.setShader(this->createShader());
dandovb3c9d1c2014-08-12 08:34:29 -0700118 break;
119 default:
halcanary96fcdcc2015-08-27 07:41:13 -0700120 fPaint.setShader(nullptr);
dandovb3c9d1c2014-08-12 08:34:29 -0700121 break;
122 }
dandov7e5598a2014-08-15 13:30:47 -0700123 }
mtkleine556be72014-08-13 10:41:16 -0700124
mtkleina1ebeb22015-10-01 09:43:39 -0700125 void onDraw(int loops, SkCanvas* canvas) override {
dandovb3c9d1c2014-08-12 08:34:29 -0700126 canvas->scale(fScale.x(), fScale.y());
127 for (int i = 0; i < loops; i++) {
128 switch (fVertexMode) {
129 case kNone_VertexMode:
Mike Reed7d954ad2016-10-28 15:42:34 -0400130 canvas->drawPatch(fCubics, nullptr, nullptr, fPaint);
dandovb3c9d1c2014-08-12 08:34:29 -0700131 break;
132 case kColors_VertexMode:
Mike Reed7d954ad2016-10-28 15:42:34 -0400133 canvas->drawPatch(fCubics, fColors, nullptr, fPaint);
dandovb3c9d1c2014-08-12 08:34:29 -0700134 break;
135 case kTexCoords_VertexMode:
Mike Reed7d954ad2016-10-28 15:42:34 -0400136 canvas->drawPatch(fCubics, nullptr, fTexCoords, fPaint);
dandovb3c9d1c2014-08-12 08:34:29 -0700137 break;
138 case kBoth_VertexMode:
Mike Reed7d954ad2016-10-28 15:42:34 -0400139 canvas->drawPatch(fCubics, fColors, fTexCoords, fPaint);
dandovb3c9d1c2014-08-12 08:34:29 -0700140 break;
141 default:
142 break;
143 }
144 }
145 }
146
147 SkPaint fPaint;
148 SkString fName;
149 SkVector fScale;
150 SkPoint fCubics[12];
151 SkPoint fTexCoords[4];
152 SkColor fColors[4];
153 VertexMode fVertexMode;
mtkleine556be72014-08-13 10:41:16 -0700154
dandovb3c9d1c2014-08-12 08:34:29 -0700155 typedef Benchmark INHERITED;
156};
157
158class SquarePatchBench : public PatchBench {
159public:
160 SquarePatchBench(SkPoint scale, VertexMode vertexMode)
161 : INHERITED(scale, vertexMode) { }
162
mtklein36352bf2015-03-25 18:17:31 -0700163 void appendName(SkString* name) override {
dandovb3c9d1c2014-08-12 08:34:29 -0700164 name->append("square");
165 }
mtkleine556be72014-08-13 10:41:16 -0700166
mtklein36352bf2015-03-25 18:17:31 -0700167 void setCubics() override {
dandovb3c9d1c2014-08-12 08:34:29 -0700168 const SkPoint points[SkPatchUtils::kNumCtrlPts] = {
169 //top points
170 {100,100},{150,100},{250,100}, {300,100},
171 //right points
172 {300, 150},{300,250},
173 //bottom points
174 {300,300},{250,300},{150,300},{100,300},
175 //left points
176 {100,250},{100,150}
177 };
178 memcpy(fCubics, points, SkPatchUtils::kNumCtrlPts * sizeof(SkPoint));
179 }
180private:
181 typedef PatchBench INHERITED;
182};
183
184class LODDiffPatchBench : public PatchBench {
185public:
186 LODDiffPatchBench(SkPoint scale, VertexMode vertexMode)
187 : INHERITED(scale, vertexMode) { }
mtkleine556be72014-08-13 10:41:16 -0700188
mtklein36352bf2015-03-25 18:17:31 -0700189 void appendName(SkString* name) override {
dandovb3c9d1c2014-08-12 08:34:29 -0700190 name->append("LOD_Diff");
191 }
mtkleine556be72014-08-13 10:41:16 -0700192
mtklein36352bf2015-03-25 18:17:31 -0700193 void setCubics() override {
dandovb3c9d1c2014-08-12 08:34:29 -0700194 const SkPoint points[SkPatchUtils::kNumCtrlPts] = {
195 //top points
196 {100,175},{150,100},{250,100}, {300,0},
197 //right points
198 {300, 150},{300,250},
199 //bottom points
200 {300,400},{250,300},{150,300},{100,225},
201 //left points
202 {100,215},{100,185}
203 };
204 memcpy(fCubics, points, SkPatchUtils::kNumCtrlPts * sizeof(SkPoint));
205 }
206private:
207 typedef PatchBench INHERITED;
208};
209
210class LoopPatchBench : public PatchBench {
211public:
212 LoopPatchBench(SkPoint scale, VertexMode vertexMode)
213 : INHERITED(scale, vertexMode) { }
mtkleine556be72014-08-13 10:41:16 -0700214
mtklein36352bf2015-03-25 18:17:31 -0700215 void appendName(SkString* name) override {
dandovb3c9d1c2014-08-12 08:34:29 -0700216 name->append("loop");
217 }
mtkleine556be72014-08-13 10:41:16 -0700218
mtklein36352bf2015-03-25 18:17:31 -0700219 void setCubics() override {
dandovb3c9d1c2014-08-12 08:34:29 -0700220 const SkPoint points[SkPatchUtils::kNumCtrlPts] = {
221 //top points
222 {100,100},{300,200},{100,200}, {300,100},
223 //right points
224 {380, 400},{380,0},
225 //bottom points
226 {300,300},{250,250},{30,200},{100,300},
227 //left points
228 {140,325},{150,150}
229 };
230 memcpy(fCubics, points, SkPatchUtils::kNumCtrlPts * sizeof(SkPoint));
231 }
232private:
233 typedef PatchBench INHERITED;
234};
235
236///////////////////////////////////////////////////////////////////////////////
237
238DEF_BENCH( return new PatchBench(SkVector::Make(0.1f, 0.1f), PatchBench::kNone_VertexMode); )
239DEF_BENCH( return new PatchBench(SkVector::Make(0.1f, 0.1f), PatchBench::kColors_VertexMode); )
240DEF_BENCH( return new PatchBench(SkVector::Make(0.1f, 0.1f), PatchBench::kTexCoords_VertexMode); )
241DEF_BENCH( return new PatchBench(SkVector::Make(0.1f, 0.1f), PatchBench::kBoth_VertexMode); )
242DEF_BENCH( return new PatchBench(SkVector::Make(1.f, 1.0f), PatchBench::kNone_VertexMode); )
243DEF_BENCH( return new PatchBench(SkVector::Make(1.0f, 1.0f), PatchBench::kColors_VertexMode); )
244DEF_BENCH( return new PatchBench(SkVector::Make(1.0f, 1.0f), PatchBench::kTexCoords_VertexMode); )
245DEF_BENCH( return new PatchBench(SkVector::Make(1.0f, 1.0f), PatchBench::kBoth_VertexMode); )
246DEF_BENCH( return new PatchBench(SkVector::Make(3.0f, 3.0f), PatchBench::kNone_VertexMode); )
247DEF_BENCH( return new PatchBench(SkVector::Make(3.0f, 3.0f), PatchBench::kColors_VertexMode); )
248DEF_BENCH( return new PatchBench(SkVector::Make(3.0f, 3.0f), PatchBench::kTexCoords_VertexMode); )
249DEF_BENCH( return new PatchBench(SkVector::Make(3.0f, 3.0f), PatchBench::kBoth_VertexMode); )
250
251DEF_BENCH( return new SquarePatchBench(SkVector::Make(0.1f, 0.1f),
252 PatchBench::kNone_VertexMode); )
253DEF_BENCH( return new SquarePatchBench(SkVector::Make(0.1f, 0.1f),
254 PatchBench::kColors_VertexMode); )
255DEF_BENCH( return new SquarePatchBench(SkVector::Make(0.1f, 0.1f),
256 PatchBench::kTexCoords_VertexMode); )
257DEF_BENCH( return new SquarePatchBench(SkVector::Make(0.1f, 0.1f),
258 PatchBench::kBoth_VertexMode); )
259DEF_BENCH( return new SquarePatchBench(SkVector::Make(1.f, 1.0f),
260 PatchBench::kNone_VertexMode); )
261DEF_BENCH( return new SquarePatchBench(SkVector::Make(1.0f, 1.0f),
262 PatchBench::kColors_VertexMode); )
263DEF_BENCH( return new SquarePatchBench(SkVector::Make(1.0f, 1.0f),
264 PatchBench::kTexCoords_VertexMode); )
265DEF_BENCH( return new SquarePatchBench(SkVector::Make(1.0f, 1.0f),
266 PatchBench::kBoth_VertexMode); )
267DEF_BENCH( return new SquarePatchBench(SkVector::Make(3.0f, 3.0f),
268 PatchBench::kNone_VertexMode); )
269DEF_BENCH( return new SquarePatchBench(SkVector::Make(3.0f, 3.0f),
270 PatchBench::kColors_VertexMode); )
271DEF_BENCH( return new SquarePatchBench(SkVector::Make(3.0f, 3.0f),
272 PatchBench::kTexCoords_VertexMode); )
273DEF_BENCH( return new SquarePatchBench(SkVector::Make(3.0f, 3.0f),
274 PatchBench::kBoth_VertexMode); )
275
276DEF_BENCH( return new LODDiffPatchBench(SkVector::Make(0.1f, 0.1f),
277 PatchBench::kNone_VertexMode); )
278DEF_BENCH( return new LODDiffPatchBench(SkVector::Make(0.1f, 0.1f),
279 PatchBench::kColors_VertexMode); )
280DEF_BENCH( return new LODDiffPatchBench(SkVector::Make(0.1f, 0.1f),
281 PatchBench::kTexCoords_VertexMode); )
282DEF_BENCH( return new LODDiffPatchBench(SkVector::Make(0.1f, 0.1f),
283 PatchBench::kBoth_VertexMode); )
284DEF_BENCH( return new LODDiffPatchBench(SkVector::Make(1.f, 1.0f),
285 PatchBench::kNone_VertexMode); )
286DEF_BENCH( return new LODDiffPatchBench(SkVector::Make(1.0f, 1.0f),
287 PatchBench::kColors_VertexMode); )
288DEF_BENCH( return new LODDiffPatchBench(SkVector::Make(1.0f, 1.0f),
289 PatchBench::kTexCoords_VertexMode); )
290DEF_BENCH( return new LODDiffPatchBench(SkVector::Make(1.0f, 1.0f),
291 PatchBench::kBoth_VertexMode); )
292DEF_BENCH( return new LODDiffPatchBench(SkVector::Make(3.0f, 3.0f),
293 PatchBench::kNone_VertexMode); )
294DEF_BENCH( return new LODDiffPatchBench(SkVector::Make(3.0f, 3.0f),
295 PatchBench::kColors_VertexMode); )
296DEF_BENCH( return new LODDiffPatchBench(SkVector::Make(3.0f, 3.0f),
297 PatchBench::kTexCoords_VertexMode); )
298DEF_BENCH( return new LODDiffPatchBench(SkVector::Make(3.0f, 3.0f),
299 PatchBench::kBoth_VertexMode); )
300
301DEF_BENCH( return new LoopPatchBench(SkVector::Make(0.1f, 0.1f),
302 PatchBench::kNone_VertexMode); )
303DEF_BENCH( return new LoopPatchBench(SkVector::Make(0.1f, 0.1f),
304 PatchBench::kColors_VertexMode); )
305DEF_BENCH( return new LoopPatchBench(SkVector::Make(0.1f, 0.1f),
306 PatchBench::kTexCoords_VertexMode); )
307DEF_BENCH( return new LoopPatchBench(SkVector::Make(0.1f, 0.1f),
308 PatchBench::kBoth_VertexMode); )
309DEF_BENCH( return new LoopPatchBench(SkVector::Make(1.f, 1.0f),
310 PatchBench::kNone_VertexMode); )
311DEF_BENCH( return new LoopPatchBench(SkVector::Make(1.0f, 1.0f),
312 PatchBench::kColors_VertexMode); )
313DEF_BENCH( return new LoopPatchBench(SkVector::Make(1.0f, 1.0f),
314 PatchBench::kTexCoords_VertexMode); )
315DEF_BENCH( return new LoopPatchBench(SkVector::Make(1.0f, 1.0f),
316 PatchBench::kBoth_VertexMode); )
317DEF_BENCH( return new LoopPatchBench(SkVector::Make(3.0f, 3.0f),
318 PatchBench::kNone_VertexMode); )
319DEF_BENCH( return new LoopPatchBench(SkVector::Make(3.0f, 3.0f),
320 PatchBench::kColors_VertexMode); )
321DEF_BENCH( return new LoopPatchBench(SkVector::Make(3.0f, 3.0f),
322 PatchBench::kTexCoords_VertexMode); )
323DEF_BENCH( return new LoopPatchBench(SkVector::Make(3.0f, 3.0f),
324 PatchBench::kBoth_VertexMode); )
Mike Reedeee76212017-05-22 22:45:05 -0400325
326//////////////////////////////////////////////
327#include "SkPatchUtils.h"
328
329class PatchUtilsBench : public Benchmark {
Mike Reed435071e2017-05-23 11:22:56 -0400330 SkString fName;
331 const bool fLinearInterp;
Mike Reedeee76212017-05-22 22:45:05 -0400332public:
Mike Reed435071e2017-05-23 11:22:56 -0400333 PatchUtilsBench(bool linearInterp) : fLinearInterp(linearInterp) {
334 fName.printf("patchutils_%s", linearInterp ? "linear" : "legacy");
Mike Reedeee76212017-05-22 22:45:05 -0400335 }
336
Mike Reed435071e2017-05-23 11:22:56 -0400337 const char* onGetName() override { return fName.c_str(); }
338
Mike Reedeee76212017-05-22 22:45:05 -0400339 bool isSuitableFor(Backend backend) override {
340 return backend == kNonRendering_Backend;
341 }
342
Mike Reed435071e2017-05-23 11:22:56 -0400343 void onDraw(int loops, SkCanvas*) override {
Mike Reedeee76212017-05-22 22:45:05 -0400344 const SkColor colors[] = { 0xFF000000, 0xFF00FF00, 0xFF0000FF, 0xFFFF0000 };
345 const SkPoint pts[] = {
346 { 0, 0 }, { 10, 0 }, { 20, 0 }, { 30, 0 },
347 { 30,10}, { 30,20 }, { 30,30 }, { 20,30 },
348 { 10,30}, { 0, 30 }, { 0, 20 }, { 0, 10 },
349 };
350 const SkPoint tex[] = {
351 { 0, 0 }, { 10, 0 }, { 10, 10 }, { 0, 10 },
352 };
353
Brian Osmane0a99622018-07-09 16:12:27 -0400354 auto cs = fLinearInterp ? SkColorSpace::MakeSRGBLinear() : nullptr;
Mike Reed435071e2017-05-23 11:22:56 -0400355 for (int i = 0; i < 100*loops; ++i) {
Brian Osmane0a99622018-07-09 16:12:27 -0400356 SkPatchUtils::MakeVertices(pts, colors, tex, 20, 20, cs.get());
Mike Reedeee76212017-05-22 22:45:05 -0400357 }
358 }
359};
Mike Reed435071e2017-05-23 11:22:56 -0400360DEF_BENCH( return new PatchUtilsBench(false); )
361DEF_BENCH( return new PatchUtilsBench(true); )