RectoriBench.cpp revision 0431b87a98f2f3721d8e5dba04bf81a2fd8b5d1c
11d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com/* 21d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com * Copyright 2013 Google Inc. 31d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com * 41d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com * Use of this source code is governed by a BSD-style license that can be 51d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com * found in the LICENSE file. 61d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com */ 71d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com 81d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com#include "SkBenchmark.h" 91d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com#include "SkCanvas.h" 101d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com#include "SkPaint.h" 111d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com#include "SkRandom.h" 121d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com#include "SkBlurMaskFilter.h" 131d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com#include "SkLayerDrawLooper.h" 141d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com 151d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com// This bench replicates a problematic use case of a draw looper used 161d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com// to create an inner blurred rect 171d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.comclass RectoriBench : public SkBenchmark { 181d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.compublic: 191d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com RectoriBench(void* param) : INHERITED(param) {} 201d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com 211d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.comprotected: 221d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com 231d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com virtual const char* onGetName() { 241d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com return "rectori"; 251d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com } 261d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com 271d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com virtual void onDraw(SkCanvas* canvas) SK_OVERRIDE { 281d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com SkMWCRandom Random; 291d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com 301d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com for (int i = 0; i < N; i++) { 311d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com SkScalar blurRad = Random.nextRangeScalar(1.5f, 25.0f); 321d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com SkScalar size = Random.nextRangeScalar(20*blurRad, 50*blurRad); 331d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com 341d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com SkScalar x = Random.nextRangeScalar(0.0f, W - size); 351d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com SkScalar y = Random.nextRangeScalar(0.0f, H - size); 361d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com 371d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com SkRect inner = { x, y, x + size, y + size }; 381d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com 391d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com SkRect outer(inner); 401d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com // outer is always outset either 2x or 4x the blur radius (we go with 2x) 4163a3f6f5d98711f1d83967ed10e5e972b586ae6erobertphillips@google.com outer.outset(2*blurRad, 2*blurRad); 421d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com 431d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com SkPath p; 441d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com 451d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com p.addRect(outer); 461d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com p.addRect(inner); 471d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com p.setFillType(SkPath::kEvenOdd_FillType); 481d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com 491d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com // This will be used to translate the normal draw outside the 501d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com // clip rect and translate the blurred version back inside 511d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com SkScalar translate = 2.0f * size; 521d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com 531d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com SkPaint paint; 541d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com paint.setLooper(this->createLooper(-translate, blurRad))->unref(); 551d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com paint.setColor(0xff000000 | Random.nextU()); 561d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com paint.setAntiAlias(true); 571d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com 581d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com canvas->save(); 591d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com // clip always equals inner rect so we get the inside blur 601d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com canvas->clipRect(inner); 611d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com canvas->translate(translate, 0); 621d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com canvas->drawPath(p, paint); 631d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com canvas->restore(); 641d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com } 651d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com } 661d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com 671d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.comprivate: 681d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com enum { 691d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com W = 640, 701d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com H = 480, 711d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com }; 721d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com 731d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com enum { N = SkBENCHLOOP(100) }; 741d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com 751d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com SkLayerDrawLooper* createLooper(SkScalar xOff, SkScalar radius) { 761d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com SkLayerDrawLooper* looper = new SkLayerDrawLooper; 771d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com 781d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com //----------------------------------------------- 791d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com SkLayerDrawLooper::LayerInfo info; 801d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com 811d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com info.fFlagsMask = 0; 821d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com // TODO: add a color filter to better match what is seen in the wild 830431b87a98f2f3721d8e5dba04bf81a2fd8b5d1cskia.committer@gmail.com info.fPaintBits = /* SkLayerDrawLooper::kColorFilter_Bit |*/ 841d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com SkLayerDrawLooper::kMaskFilter_Bit; 851d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com info.fColorMode = SkXfermode::kDst_Mode; 861d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com info.fOffset.set(xOff, 0); 871d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com info.fPostTranslate = false; 881d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com 891d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com SkPaint* paint = looper->addLayer(info); 901d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com 9163a3f6f5d98711f1d83967ed10e5e972b586ae6erobertphillips@google.com SkMaskFilter* mf = SkBlurMaskFilter::Create(radius, 921d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com SkBlurMaskFilter::kNormal_BlurStyle, 931d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com SkBlurMaskFilter::kHighQuality_BlurFlag); 941d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com paint->setMaskFilter(mf)->unref(); 951d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com 961d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com //----------------------------------------------- 971d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com info.fPaintBits = 0; 981d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com info.fOffset.set(0, 0); 991d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com 1001d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com paint = looper->addLayer(info); 1011d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com return looper; 1021d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com } 1031d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com 1041d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com typedef SkBenchmark INHERITED; 1051d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com}; 1061d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com 1071d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.com 1081d2f63159416ceec0544f803aef80f6e0c09e85crobertphillips@google.comDEF_BENCH( return SkNEW_ARGS(RectoriBench, (p)); ) 109