1dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com/* 2dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com * Copyright 2012 Google Inc. 3dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com * 4dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com * Use of this source code is governed by a BSD-style license that can be 5dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com * found in the LICENSE file. 6dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com */ 7f168b86d7fafc5c20c87bebc6fd393cb17e120catfarina#include "Benchmark.h" 8dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com#include "SkCanvas.h" 9dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com#include "SkColor.h" 10dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com#include "SkPaint.h" 11dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com#include "SkPicture.h" 12770963f23f4fc313db0fa3bac18b1b8aafb55f17robertphillips@google.com#include "SkPictureRecorder.h" 13dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com#include "SkPoint.h" 147fe6409ecbff281edd6251c128eff38a7c206524reed@google.com#include "SkRandom.h" 15dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com#include "SkRect.h" 16dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com#include "SkString.h" 17dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com 18f168b86d7fafc5c20c87bebc6fd393cb17e120catfarinaclass PictureRecordBench : public Benchmark { 19dde718c558b118e2a918d14046770a8c37d75040djsollen@google.compublic: 20410e6e80f00a6c660675c80904807a041c7b7d2amtklein@google.com PictureRecordBench(const char name[]) { 21dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com fName.printf("picture_record_%s", name); 22644629c1c7913a43ced172b98d56e0f471bc348bcommit-bot@chromium.org } 23644629c1c7913a43ced172b98d56e0f471bc348bcommit-bot@chromium.org 24644629c1c7913a43ced172b98d56e0f471bc348bcommit-bot@chromium.org virtual bool isSuitableFor(Backend backend) SK_OVERRIDE { 25644629c1c7913a43ced172b98d56e0f471bc348bcommit-bot@chromium.org return backend == kNonRendering_Backend; 26dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com } 27dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com 28dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com enum { 29dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com PICTURE_WIDTH = 1000, 30dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com PICTURE_HEIGHT = 4000, 31dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com }; 32dde718c558b118e2a918d14046770a8c37d75040djsollen@google.comprotected: 3393d2f559b88b7eb59929451000a0e307f17c996fmtklein@google.com virtual const char* onGetName() SK_OVERRIDE { 34dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com return fName.c_str(); 35dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com } 36dde718c558b118e2a918d14046770a8c37d75040djsollen@google.comprivate: 3793d2f559b88b7eb59929451000a0e307f17c996fmtklein@google.com SkString fName; 38f168b86d7fafc5c20c87bebc6fd393cb17e120catfarina typedef Benchmark INHERITED; 39dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com}; 40dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com 4193d2f559b88b7eb59929451000a0e307f17c996fmtklein@google.com 4293d2f559b88b7eb59929451000a0e307f17c996fmtklein@google.comstatic const int kMaxLoopsPerCanvas = 10000; 4393d2f559b88b7eb59929451000a0e307f17c996fmtklein@google.com 44dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com/* 45dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com * An SkPicture has internal dictionaries to store bitmaps, matrices, paints, 46dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com * and regions. This bench populates those dictionaries to test the speed of 47dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com * reading and writing to those particular dictionary data structures. 48dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com */ 49dde718c558b118e2a918d14046770a8c37d75040djsollen@google.comclass DictionaryRecordBench : public PictureRecordBench { 50dde718c558b118e2a918d14046770a8c37d75040djsollen@google.compublic: 5193d2f559b88b7eb59929451000a0e307f17c996fmtklein@google.com DictionaryRecordBench() : INHERITED("dictionaries") {} 52dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com 53dde718c558b118e2a918d14046770a8c37d75040djsollen@google.comprotected: 543361471a3504ecd0351ff70f4c42d8d6fee963d4commit-bot@chromium.org virtual void onDraw(const int loops, SkCanvas*) SK_OVERRIDE { 5584b18c7e3e042bf206e1ace3d1b6ea5bb929fe51robertphillips@google.com SkPictureRecorder recorder; 5693d2f559b88b7eb59929451000a0e307f17c996fmtklein@google.com SkCanvas* canvas = NULL; 57dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com 583361471a3504ecd0351ff70f4c42d8d6fee963d4commit-bot@chromium.org const SkPoint translateDelta = getTranslateDelta(loops); 59dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com 603361471a3504ecd0351ff70f4c42d8d6fee963d4commit-bot@chromium.org for (int i = 0; i < loops; i++) { 6193d2f559b88b7eb59929451000a0e307f17c996fmtklein@google.com if (0 == i % kMaxLoopsPerCanvas) { 6284b18c7e3e042bf206e1ace3d1b6ea5bb929fe51robertphillips@google.com SkAutoTUnref<SkPicture> picture(recorder.endRecording()); 635fb2ce38b3dcb8e60e9e112df23c9d42456d7069commit-bot@chromium.org canvas = recorder.beginRecording(PICTURE_WIDTH, PICTURE_HEIGHT, NULL, 0); 6493d2f559b88b7eb59929451000a0e307f17c996fmtklein@google.com } 65dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com 66dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com SkColor color = SK_ColorYELLOW + (i % 255); 67c289743864e2ab926a95e617a5cd1d29b26d1825mtklein@google.com SkIRect rect = SkIRect::MakeWH(i % PICTURE_WIDTH, i % PICTURE_HEIGHT); 68dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com 69dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com canvas->save(); 70dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com 71dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com // set the clip to the given region 72dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com SkRegion region; 73dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com region.setRect(rect); 74dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com canvas->clipRegion(region); 75dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com 76dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com // fill the clip with a color 77dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com SkPaint paint; 78dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com paint.setColor(color); 79dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com canvas->drawPaint(paint); 80dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com 81dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com // set a matrix on the canvas 82dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com SkMatrix matrix; 83dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com matrix.setRotate(SkIntToScalar(i % 360)); 84dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com canvas->setMatrix(matrix); 85dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com 86dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com // create a simple bitmap 87dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com SkBitmap bitmap; 886c22573edb234ad14df947278cfed010669a39a7reed bitmap.allocPixels(SkImageInfo::Make(10, 10, 896c22573edb234ad14df947278cfed010669a39a7reed kRGB_565_SkColorType, kOpaque_SkAlphaType)); 90dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com 91dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com // draw a single color into the bitmap 92dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com SkCanvas bitmapCanvas(bitmap); 93dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com bitmapCanvas.drawColor(SkColorSetA(color, i % 255)); 94dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com 95dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com // draw the bitmap onto the canvas 96dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com canvas->drawBitmapMatrix(bitmap, matrix); 97dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com 98dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com canvas->restore(); 99dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com canvas->translate(translateDelta.fX, translateDelta.fY); 100dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com } 101dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com } 102dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com 103c289743864e2ab926a95e617a5cd1d29b26d1825mtklein@google.com SkPoint getTranslateDelta(int M) { 104dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com SkIPoint canvasSize = onGetSize(); 105dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com return SkPoint::Make(SkIntToScalar((PICTURE_WIDTH - canvasSize.fX)/M), 106dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com SkIntToScalar((PICTURE_HEIGHT- canvasSize.fY)/M)); 107dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com } 108dde718c558b118e2a918d14046770a8c37d75040djsollen@google.comprivate: 109dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com typedef PictureRecordBench INHERITED; 110dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com}; 111dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com 112ef76060cbf36032a5bef9cd8d18138704349c3aejunov@chromium.org/* 113ef76060cbf36032a5bef9cd8d18138704349c3aejunov@chromium.org * Populates the SkPaint dictionary with a large number of unique paint 114ef76060cbf36032a5bef9cd8d18138704349c3aejunov@chromium.org * objects that differ only by color 115ef76060cbf36032a5bef9cd8d18138704349c3aejunov@chromium.org */ 116ef76060cbf36032a5bef9cd8d18138704349c3aejunov@chromium.orgclass UniquePaintDictionaryRecordBench : public PictureRecordBench { 117ef76060cbf36032a5bef9cd8d18138704349c3aejunov@chromium.orgpublic: 11893d2f559b88b7eb59929451000a0e307f17c996fmtklein@google.com UniquePaintDictionaryRecordBench() : INHERITED("unique_paint_dictionary") { } 119ef76060cbf36032a5bef9cd8d18138704349c3aejunov@chromium.org 120ef76060cbf36032a5bef9cd8d18138704349c3aejunov@chromium.orgprotected: 1213361471a3504ecd0351ff70f4c42d8d6fee963d4commit-bot@chromium.org virtual void onDraw(const int loops, SkCanvas*) SK_OVERRIDE { 122e0e7cfe44bb9d66d76120a79e5275c294bacaa22commit-bot@chromium.org SkRandom rand; 1235e5239ed35dcac2a42c4780baa7846b751111895mtklein@google.com SkPaint paint; 12484b18c7e3e042bf206e1ace3d1b6ea5bb929fe51robertphillips@google.com SkPictureRecorder recorder; 1255e5239ed35dcac2a42c4780baa7846b751111895mtklein@google.com SkCanvas* canvas = NULL; 1263361471a3504ecd0351ff70f4c42d8d6fee963d4commit-bot@chromium.org for (int i = 0; i < loops; i++) { 12793d2f559b88b7eb59929451000a0e307f17c996fmtklein@google.com if (0 == i % kMaxLoopsPerCanvas) { 12884b18c7e3e042bf206e1ace3d1b6ea5bb929fe51robertphillips@google.com SkAutoTUnref<SkPicture> picture(recorder.endRecording()); 1295fb2ce38b3dcb8e60e9e112df23c9d42456d7069commit-bot@chromium.org canvas = recorder.beginRecording(PICTURE_WIDTH, PICTURE_HEIGHT, NULL, 0); 1305e5239ed35dcac2a42c4780baa7846b751111895mtklein@google.com } 1317fe6409ecbff281edd6251c128eff38a7c206524reed@google.com paint.setColor(rand.nextU()); 132ef76060cbf36032a5bef9cd8d18138704349c3aejunov@chromium.org canvas->drawPaint(paint); 133ef76060cbf36032a5bef9cd8d18138704349c3aejunov@chromium.org } 134ef76060cbf36032a5bef9cd8d18138704349c3aejunov@chromium.org } 135ef76060cbf36032a5bef9cd8d18138704349c3aejunov@chromium.org 136ef76060cbf36032a5bef9cd8d18138704349c3aejunov@chromium.orgprivate: 137ef76060cbf36032a5bef9cd8d18138704349c3aejunov@chromium.org typedef PictureRecordBench INHERITED; 138ef76060cbf36032a5bef9cd8d18138704349c3aejunov@chromium.org}; 139ef76060cbf36032a5bef9cd8d18138704349c3aejunov@chromium.org 140ef76060cbf36032a5bef9cd8d18138704349c3aejunov@chromium.org/* 141ef76060cbf36032a5bef9cd8d18138704349c3aejunov@chromium.org * Populates the SkPaint dictionary with a number of unique paint 1420c4e21da9598a2eb5324e90ac8648048a1a34636commit-bot@chromium.org * objects that get reused repeatedly. 1430c4e21da9598a2eb5324e90ac8648048a1a34636commit-bot@chromium.org * 1440c4e21da9598a2eb5324e90ac8648048a1a34636commit-bot@chromium.org * Re-creating the paint objects in the inner loop slows the benchmark down 10%. 1450c4e21da9598a2eb5324e90ac8648048a1a34636commit-bot@chromium.org * Using setColor(i % objCount) instead of a random color creates a very high rate 1460c4e21da9598a2eb5324e90ac8648048a1a34636commit-bot@chromium.org * of hash conflicts, slowing us down 12%. 147ef76060cbf36032a5bef9cd8d18138704349c3aejunov@chromium.org */ 148ef76060cbf36032a5bef9cd8d18138704349c3aejunov@chromium.orgclass RecurringPaintDictionaryRecordBench : public PictureRecordBench { 149ef76060cbf36032a5bef9cd8d18138704349c3aejunov@chromium.orgpublic: 15093d2f559b88b7eb59929451000a0e307f17c996fmtklein@google.com RecurringPaintDictionaryRecordBench() : INHERITED("recurring_paint_dictionary") { 151e0e7cfe44bb9d66d76120a79e5275c294bacaa22commit-bot@chromium.org SkRandom rand; 1520c4e21da9598a2eb5324e90ac8648048a1a34636commit-bot@chromium.org for (int i = 0; i < ObjCount; i++) { 1530c4e21da9598a2eb5324e90ac8648048a1a34636commit-bot@chromium.org fPaint[i].setColor(rand.nextU()); 1540c4e21da9598a2eb5324e90ac8648048a1a34636commit-bot@chromium.org } 1550c4e21da9598a2eb5324e90ac8648048a1a34636commit-bot@chromium.org } 156ef76060cbf36032a5bef9cd8d18138704349c3aejunov@chromium.org 157ef76060cbf36032a5bef9cd8d18138704349c3aejunov@chromium.org enum { 158c289743864e2ab926a95e617a5cd1d29b26d1825mtklein@google.com ObjCount = 100, // number of unique paint objects 159ef76060cbf36032a5bef9cd8d18138704349c3aejunov@chromium.org }; 160ef76060cbf36032a5bef9cd8d18138704349c3aejunov@chromium.orgprotected: 1613361471a3504ecd0351ff70f4c42d8d6fee963d4commit-bot@chromium.org virtual void onDraw(const int loops, SkCanvas*) SK_OVERRIDE { 16284b18c7e3e042bf206e1ace3d1b6ea5bb929fe51robertphillips@google.com SkPictureRecorder recorder; 1635fb2ce38b3dcb8e60e9e112df23c9d42456d7069commit-bot@chromium.org SkCanvas* canvas = recorder.beginRecording(PICTURE_WIDTH, PICTURE_HEIGHT, NULL, 0); 1643361471a3504ecd0351ff70f4c42d8d6fee963d4commit-bot@chromium.org for (int i = 0; i < loops; i++) { 1650c4e21da9598a2eb5324e90ac8648048a1a34636commit-bot@chromium.org canvas->drawPaint(fPaint[i % ObjCount]); 166ef76060cbf36032a5bef9cd8d18138704349c3aejunov@chromium.org } 167ef76060cbf36032a5bef9cd8d18138704349c3aejunov@chromium.org } 168ef76060cbf36032a5bef9cd8d18138704349c3aejunov@chromium.org 169ef76060cbf36032a5bef9cd8d18138704349c3aejunov@chromium.orgprivate: 1700c4e21da9598a2eb5324e90ac8648048a1a34636commit-bot@chromium.org SkPaint fPaint [ObjCount]; 171ef76060cbf36032a5bef9cd8d18138704349c3aejunov@chromium.org typedef PictureRecordBench INHERITED; 172ef76060cbf36032a5bef9cd8d18138704349c3aejunov@chromium.org}; 173ef76060cbf36032a5bef9cd8d18138704349c3aejunov@chromium.org 174dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com/////////////////////////////////////////////////////////////////////////////// 175dde718c558b118e2a918d14046770a8c37d75040djsollen@google.com 176410e6e80f00a6c660675c80904807a041c7b7d2amtklein@google.comDEF_BENCH( return new DictionaryRecordBench(); ) 177410e6e80f00a6c660675c80904807a041c7b7d2amtklein@google.comDEF_BENCH( return new UniquePaintDictionaryRecordBench(); ) 178410e6e80f00a6c660675c80904807a041c7b7d2amtklein@google.comDEF_BENCH( return new RecurringPaintDictionaryRecordBench(); ) 179