| Index: gm/blurcircles2.cpp
|
| diff --git a/gm/blurcircles2.cpp b/gm/blurcircles2.cpp
|
| new file mode 100644
|
| index 0000000000000000000000000000000000000000..284c1ab24e1a4399b3cb5852d45bc8f8cae716c7
|
| --- /dev/null
|
| +++ b/gm/blurcircles2.cpp
|
| @@ -0,0 +1,141 @@
|
| +/*
|
| +* Copyright 2016 Google Inc.
|
| +*
|
| +* Use of this source code is governed by a BSD-style license that can be
|
| +* found in the LICENSE file.
|
| +*/
|
| +
|
| +#include "gm.h"
|
| +#include "SkAnimTimer.h"
|
| +#include "SkBlurMask.h"
|
| +#include "SkBlurMaskFilter.h"
|
| +#include "SkCanvas.h"
|
| +#include "SkPaint.h"
|
| +#include "SkPath.h"
|
| +#include "SkString.h"
|
| +
|
| +/**
|
| + * In GM mode this draws an array of circles with different radii and different blur radii. Below
|
| + * each circle an almost-circle path is drawn with the same blur filter for comparison.
|
| + *
|
| + * In Sample mode this draws a single circle and almost-circle with animating radius and blur
|
| + * radius.
|
| + */
|
| +class BlurCircles2GM : public skiagm::GM {
|
| +public:
|
| + BlurCircles2GM() {
|
| + fAnimRadius = SkAnimTimer::PingPong(0, kRadiusPingPoingPeriod, kRadiusPingPoingShift,
|
| + kMinRadius, kMaxRadius);
|
| + fAnimBlurRadius = SkAnimTimer::PingPong(0, kBlurRadiusPingPoingPeriod,
|
| + kBlurRadiusPingPoingShift, kMinBlurRadius,
|
| + kMaxBlurRadius);
|
| + }
|
| +
|
| +protected:
|
| + SkString onShortName() override { return SkString("blurcircles2"); }
|
| +
|
| + SkISize onISize() override {
|
| + return SkISize::Make(730, 1350);
|
| + }
|
| +
|
| + void onDraw(SkCanvas* canvas) override {
|
| + static constexpr SkScalar kMaxR = kMaxRadius + kMaxBlurRadius;
|
| +
|
| + auto almostCircleMaker = [] (SkScalar radius, SkPath* dst) {
|
| + dst->reset();
|
| + dst->addArc(SkRect::MakeXYWH(-radius, -radius, 2 * radius, 2 * radius), 0, 355);
|
| + dst->setIsVolatile(true);
|
| + dst->close();
|
| + };
|
| +
|
| + auto blurMaker = [] (SkScalar radius) ->sk_sp<SkMaskFilter> {
|
| + return SkBlurMaskFilter::Make(kNormal_SkBlurStyle,
|
| + SkBlurMask::ConvertRadiusToSigma(radius),
|
| + SkBlurMaskFilter::kHighQuality_BlurFlag);
|
| + };
|
| +
|
| + SkPaint paint;
|
| + paint.setColor(SK_ColorBLACK);
|
| +
|
| + if (this->getMode() == kSample_Mode) {
|
| + paint.setMaskFilter(blurMaker(fAnimBlurRadius));
|
| + SkISize size = canvas->getBaseLayerSize();
|
| + SkPath almostCircle;
|
| + almostCircleMaker(fAnimRadius, &almostCircle);
|
| + canvas->save();
|
| + canvas->translate(size.fWidth / 2.f, size.fHeight / 4.f);
|
| + canvas->drawCircle(0, 0, fAnimRadius, paint);
|
| + canvas->translate(0, 2 * kMaxR);
|
| + canvas->drawPath(almostCircle, paint);
|
| + canvas->restore();
|
| + } else {
|
| + canvas->save();
|
| + static constexpr SkScalar kPad = 5;
|
| + static constexpr SkScalar kRadiusSteps = 5;
|
| + static constexpr SkScalar kBlurRadiusSteps = 5;
|
| + canvas->translate(kPad + kMinRadius + kMaxBlurRadius,
|
| + kPad + kMinRadius + kMaxBlurRadius);
|
| + SkScalar lineWidth = 0;
|
| + for (int r = 0; r < kRadiusSteps - 1; ++r) {
|
| + const SkScalar radius = r * (kMaxRadius - kMinRadius) / kBlurRadiusSteps +
|
| + kMinRadius;
|
| + lineWidth += 2 * (radius + kMaxBlurRadius) + kPad;
|
| + }
|
| + for (int br = 0; br < kBlurRadiusSteps; ++br) {
|
| + const SkScalar blurRadius = br * (kMaxBlurRadius - kMinBlurRadius) /
|
| + kBlurRadiusSteps + kMinBlurRadius;
|
| + const SkScalar maxRowR = blurRadius + kMaxRadius;
|
| + paint.setMaskFilter(blurMaker(blurRadius));
|
| + canvas->save();
|
| + for (int r = 0; r < kRadiusSteps; ++r) {
|
| + const SkScalar radius = r * (kMaxRadius - kMinRadius) / kBlurRadiusSteps +
|
| + kMinRadius;
|
| + SkPath almostCircle;
|
| + almostCircleMaker(radius, &almostCircle);
|
| + canvas->save();
|
| + canvas->drawCircle(0, 0, radius, paint);
|
| + canvas->translate(0, 2 * maxRowR + kPad);
|
| + canvas->drawPath(almostCircle, paint);
|
| + canvas->restore();
|
| + const SkScalar maxColR = radius + kMaxBlurRadius;
|
| + canvas->translate(maxColR * 2 + kPad, 0);
|
| + }
|
| + canvas->restore();
|
| + SkPaint blackPaint;
|
| + blackPaint.setColor(SK_ColorBLACK);
|
| + const SkScalar lineY = 3 * maxRowR + 1.5f * kPad;
|
| + if (br != kBlurRadiusSteps - 1) {
|
| + canvas->drawLine(0, lineY, lineWidth, lineY, blackPaint);
|
| + }
|
| + canvas->translate(0, maxRowR * 4 + 2 * kPad);
|
| + }
|
| + canvas->restore();
|
| + }
|
| + }
|
| +
|
| + bool onAnimate(const SkAnimTimer& timer) override {
|
| + fAnimRadius = timer.pingPong(kRadiusPingPoingPeriod, kRadiusPingPoingShift, kMinRadius,
|
| + kMaxRadius);
|
| + fAnimBlurRadius = timer.pingPong(kBlurRadiusPingPoingPeriod, kBlurRadiusPingPoingShift,
|
| + kMinBlurRadius, kMaxBlurRadius);
|
| + return true;
|
| + }
|
| +
|
| +private:
|
| + static constexpr SkScalar kMinRadius = 15;
|
| + static constexpr SkScalar kMaxRadius = 45;
|
| + static constexpr SkScalar kRadiusPingPoingPeriod = 8;
|
| + static constexpr SkScalar kRadiusPingPoingShift = 3;
|
| +
|
| + static constexpr SkScalar kMinBlurRadius = 5;
|
| + static constexpr SkScalar kMaxBlurRadius = 45;
|
| + static constexpr SkScalar kBlurRadiusPingPoingPeriod = 3;
|
| + static constexpr SkScalar kBlurRadiusPingPoingShift = 1.5;
|
| +
|
| + SkScalar fAnimRadius;
|
| + SkScalar fAnimBlurRadius;
|
| +
|
| + typedef skiagm::GM INHERITED;
|
| +};
|
| +
|
| +DEF_GM(return new BlurCircles2GM();)
|
|
|