From afdbedb73c005dc9d88ab4167167866d7302c253 Mon Sep 17 00:00:00 2001 From: reed Date: Wed, 14 Jan 2015 13:16:26 -0800 Subject: add sample for filter quality BUG=skia: TBR= Review URL: https://codereview.chromium.org/788163007 --- samplecode/SampleFilterQuality.cpp | 184 +++++++++++++++++++++++++++++++++++++ 1 file changed, 184 insertions(+) create mode 100644 samplecode/SampleFilterQuality.cpp (limited to 'samplecode/SampleFilterQuality.cpp') diff --git a/samplecode/SampleFilterQuality.cpp b/samplecode/SampleFilterQuality.cpp new file mode 100644 index 0000000000..4c778e35e4 --- /dev/null +++ b/samplecode/SampleFilterQuality.cpp @@ -0,0 +1,184 @@ +/* + * Copyright 2015 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 "Resources.h" +#include "SampleCode.h" +#include "SkCanvas.h" +#include "SkInterpolator.h" +#include "SkSurface.h" +#include "SkRandom.h" +#include "SkTime.h" + +#define N 128 + +static SkImage* make_image() { + SkImageInfo info = SkImageInfo::MakeN32Premul(N, N); + SkAutoTUnref surface(SkSurface::NewRaster(info)); + SkCanvas* canvas = surface->getCanvas(); + + SkPath path; + path.setFillType(SkPath::kEvenOdd_FillType); + + path.addRect(SkRect::MakeWH(N/2, N)); + path.addRect(SkRect::MakeWH(N, N/2)); + path.moveTo(0, 0); path.lineTo(N, 0); path.lineTo(0, N); path.close(); + + canvas->drawPath(path, SkPaint()); + return surface->newImageSnapshot(); +} + +struct AnimValue { + SkScalar fValue; + SkScalar fMin; + SkScalar fMax; + SkScalar fMod; + + operator SkScalar() const { return fValue; } + + void set(SkScalar value, SkScalar min, SkScalar max) { + fValue = value; + fMin = min; + fMax = max; + fMod = 0; + } + + void setMod(SkScalar value, SkScalar mod) { + fValue = value; + fMin = 0; + fMax = 0; + fMod = mod; + } + + SkScalar inc(SkScalar delta) { + fValue += delta; + return this->fixUp(); + } + + SkScalar fixUp() { + if (fMod) { + fValue = SkScalarMod(fValue, fMod); + } else { + if (fValue > fMax) { + fValue = fMax; + } else if (fValue < fMin) { + fValue = fMin; + } + } + return fValue; + } +}; + +#define ANGLE_DELTA 3 +#define SCALE_DELTA (SK_Scalar1 / 32) + +class FilterQualityView : public SampleView { + SkAutoTUnref fImage; + AnimValue fScale, fAngle; + + SkInterpolator fTrans; + +public: + FilterQualityView() : fImage(make_image()), fTrans(2, 2) { + fScale.set(1, SK_Scalar1 / 8, 1); + fAngle.setMod(0, 360); + + SkScalar values[2]; + fTrans.setMirror(true); + fTrans.setReset(true); + + fTrans.setRepeatCount(999); + values[0] = values[1] = 0; + fTrans.setKeyFrame(0, SkTime::GetMSecs(), values); + values[0] = values[1] = 1; + fTrans.setKeyFrame(1, SkTime::GetMSecs() + 2000, values); + } + +protected: + + // overrides from SkEventSink + bool onQuery(SkEvent* evt) SK_OVERRIDE { + if (SampleCode::TitleQ(*evt)) { + SampleCode::TitleR(evt, "FilterQuality"); + return true; + } + SkUnichar uni; + if (SampleCode::CharQ(*evt, &uni)) { + switch (uni) { + case '1': fAngle.inc(-ANGLE_DELTA); this->inval(NULL); return true; + case '2': fAngle.inc( ANGLE_DELTA); this->inval(NULL); return true; + case '3': fScale.inc(-SCALE_DELTA); this->inval(NULL); return true; + case '4': fScale.inc( SCALE_DELTA); this->inval(NULL); return true; + default: break; + } + } + return this->INHERITED::onQuery(evt); + } + + void drawHere(SkCanvas* canvas, SkScalar x, SkScalar y, SkPaint::FilterLevel filter) { + SkAutoCanvasRestore acr(canvas, true); + SkPaint paint; + paint.setAntiAlias(true); + paint.setFilterLevel(filter); + + canvas->translate(x, y); + canvas->scale(fScale, fScale); + canvas->rotate(fAngle); + canvas->drawImage(fImage, -SkScalarHalf(fImage->width()), -SkScalarHalf(fImage->height()), + &paint); + } + + void onDrawContent(SkCanvas* canvas) SK_OVERRIDE { + SkScalar trans[2]; + fTrans.timeToValues(SkTime::GetMSecs(), trans); + canvas->translate(trans[0], trans[1]); + this->inval(NULL); + + const struct { + SkScalar fX; + SkScalar fY; + SkPaint::FilterLevel fFilter; + } rec[] = { + { 100, 100, SkPaint::kNone_FilterLevel }, + { 300, 100, SkPaint::kLow_FilterLevel }, + { 100, 300, SkPaint::kMedium_FilterLevel }, + { 300, 300, SkPaint::kHigh_FilterLevel }, + }; + + for (size_t i = 0; i < SK_ARRAY_COUNT(rec); ++i) { + this->drawHere(canvas, rec[i].fX, rec[i].fY, rec[i].fFilter); + } + + SkPaint paint; + paint.setAntiAlias(true); + paint.setTextSize(40); + SkString str; + str.appendScalar(fScale); + canvas->drawText(str.c_str(), str.size(), 450, 100, paint); + str.reset(); str.appendScalar(fAngle); + canvas->drawText(str.c_str(), str.size(), 450, 150, paint); + + str.reset(); str.appendScalar(trans[0]); + canvas->drawText(str.c_str(), str.size(), 450, 200, paint); + str.reset(); str.appendScalar(trans[1]); + canvas->drawText(str.c_str(), str.size(), 450, 250, paint); +} + + virtual bool handleKey(SkKey key) { + this->inval(NULL); + return true; + } + +private: + typedef SampleView INHERITED; +}; + +////////////////////////////////////////////////////////////////////////////// + +static SkView* MyFactory() { return new FilterQualityView; } +static SkViewRegister reg(MyFactory); -- cgit v1.2.3