1*c8dee2aaSAndroid Build Coastguard Worker /* 2*c8dee2aaSAndroid Build Coastguard Worker * Copyright 2021 Google Inc. 3*c8dee2aaSAndroid Build Coastguard Worker * 4*c8dee2aaSAndroid Build Coastguard Worker * Use of this source code is governed by a BSD-style license that can be 5*c8dee2aaSAndroid Build Coastguard Worker * found in the LICENSE file. 6*c8dee2aaSAndroid Build Coastguard Worker */ 7*c8dee2aaSAndroid Build Coastguard Worker 8*c8dee2aaSAndroid Build Coastguard Worker // This test only works with the GPU backend. 9*c8dee2aaSAndroid Build Coastguard Worker 10*c8dee2aaSAndroid Build Coastguard Worker #include "gm/gm.h" 11*c8dee2aaSAndroid Build Coastguard Worker #include "include/core/SkBlendMode.h" 12*c8dee2aaSAndroid Build Coastguard Worker #include "include/core/SkCanvas.h" 13*c8dee2aaSAndroid Build Coastguard Worker #include "include/core/SkMatrix.h" 14*c8dee2aaSAndroid Build Coastguard Worker #include "include/core/SkPaint.h" 15*c8dee2aaSAndroid Build Coastguard Worker #include "include/core/SkRect.h" 16*c8dee2aaSAndroid Build Coastguard Worker #include "include/core/SkScalar.h" 17*c8dee2aaSAndroid Build Coastguard Worker #include "include/core/SkSize.h" 18*c8dee2aaSAndroid Build Coastguard Worker #include "include/core/SkString.h" 19*c8dee2aaSAndroid Build Coastguard Worker #include "include/private/gpu/ganesh/GrTypesPriv.h" 20*c8dee2aaSAndroid Build Coastguard Worker #include "src/core/SkCanvasPriv.h" 21*c8dee2aaSAndroid Build Coastguard Worker #include "src/gpu/ganesh/GrCanvas.h" 22*c8dee2aaSAndroid Build Coastguard Worker #include "src/gpu/ganesh/GrFragmentProcessor.h" 23*c8dee2aaSAndroid Build Coastguard Worker #include "src/gpu/ganesh/GrPaint.h" 24*c8dee2aaSAndroid Build Coastguard Worker #include "src/gpu/ganesh/SurfaceDrawContext.h" 25*c8dee2aaSAndroid Build Coastguard Worker #include "src/gpu/ganesh/effects/GrPorterDuffXferProcessor.h" 26*c8dee2aaSAndroid Build Coastguard Worker #include "tools/gpu/TestOps.h" 27*c8dee2aaSAndroid Build Coastguard Worker 28*c8dee2aaSAndroid Build Coastguard Worker #include <memory> 29*c8dee2aaSAndroid Build Coastguard Worker #include <utility> 30*c8dee2aaSAndroid Build Coastguard Worker 31*c8dee2aaSAndroid Build Coastguard Worker class GrAppliedClip; 32*c8dee2aaSAndroid Build Coastguard Worker 33*c8dee2aaSAndroid Build Coastguard Worker namespace skiagm { 34*c8dee2aaSAndroid Build Coastguard Worker 35*c8dee2aaSAndroid Build Coastguard Worker /** 36*c8dee2aaSAndroid Build Coastguard Worker * This GM directly exercises a GrProcessor that clips against rects. 37*c8dee2aaSAndroid Build Coastguard Worker */ 38*c8dee2aaSAndroid Build Coastguard Worker class AARectEffect : public GpuGM { 39*c8dee2aaSAndroid Build Coastguard Worker public: AARectEffect()40*c8dee2aaSAndroid Build Coastguard Worker AARectEffect() { this->setBGColor(0xFFFFFFFF); } 41*c8dee2aaSAndroid Build Coastguard Worker 42*c8dee2aaSAndroid Build Coastguard Worker protected: getName() const43*c8dee2aaSAndroid Build Coastguard Worker SkString getName() const override { return SkString("aa_rect_effect"); } 44*c8dee2aaSAndroid Build Coastguard Worker getISize()45*c8dee2aaSAndroid Build Coastguard Worker SkISize getISize() override { return SkISize::Make(210, 250); } 46*c8dee2aaSAndroid Build Coastguard Worker onOnceBeforeDraw()47*c8dee2aaSAndroid Build Coastguard Worker void onOnceBeforeDraw() override {} 48*c8dee2aaSAndroid Build Coastguard Worker onDraw(GrRecordingContext * rContext,SkCanvas * canvas,SkString * errorMsg)49*c8dee2aaSAndroid Build Coastguard Worker DrawResult onDraw(GrRecordingContext* rContext, SkCanvas* canvas, SkString* errorMsg) override { 50*c8dee2aaSAndroid Build Coastguard Worker auto sdc = skgpu::ganesh::TopDeviceSurfaceDrawContext(canvas); 51*c8dee2aaSAndroid Build Coastguard Worker if (!sdc) { 52*c8dee2aaSAndroid Build Coastguard Worker *errorMsg = kErrorMsg_DrawSkippedGpuOnly; 53*c8dee2aaSAndroid Build Coastguard Worker return DrawResult::kSkip; 54*c8dee2aaSAndroid Build Coastguard Worker } 55*c8dee2aaSAndroid Build Coastguard Worker 56*c8dee2aaSAndroid Build Coastguard Worker SkScalar y = 12.f; 57*c8dee2aaSAndroid Build Coastguard Worker static constexpr SkScalar kDX = 12.f; 58*c8dee2aaSAndroid Build Coastguard Worker static constexpr SkScalar kOutset = 5.f; 59*c8dee2aaSAndroid Build Coastguard Worker 60*c8dee2aaSAndroid Build Coastguard Worker static constexpr SkRect kRects[] = { 61*c8dee2aaSAndroid Build Coastguard Worker // integer edges 62*c8dee2aaSAndroid Build Coastguard Worker SkRect::MakeLTRB(5.f, 1.f, 30.f, 25.f), 63*c8dee2aaSAndroid Build Coastguard Worker // half-integer edges 64*c8dee2aaSAndroid Build Coastguard Worker SkRect::MakeLTRB(5.5f, 0.5f, 29.5f, 24.5f), 65*c8dee2aaSAndroid Build Coastguard Worker // vertically/horizontally thin rects that cover pixel centers 66*c8dee2aaSAndroid Build Coastguard Worker SkRect::MakeLTRB(5.25f, 0.5f, 5.75f, 24.5f), 67*c8dee2aaSAndroid Build Coastguard Worker SkRect::MakeLTRB(5.5f, 0.5f, 29.5f, 0.75f), 68*c8dee2aaSAndroid Build Coastguard Worker // vertically/horizontally thin rects that don't cover pixel centers 69*c8dee2aaSAndroid Build Coastguard Worker SkRect::MakeLTRB(5.55f, 0.5f, 5.75f, 24.5f), 70*c8dee2aaSAndroid Build Coastguard Worker SkRect::MakeLTRB(5.5f, .05f, 29.5f, .25f), 71*c8dee2aaSAndroid Build Coastguard Worker // small in x and y 72*c8dee2aaSAndroid Build Coastguard Worker SkRect::MakeLTRB(5.05f, .55f, 5.45f, .85f), 73*c8dee2aaSAndroid Build Coastguard Worker }; 74*c8dee2aaSAndroid Build Coastguard Worker 75*c8dee2aaSAndroid Build Coastguard Worker for (auto r : kRects) { 76*c8dee2aaSAndroid Build Coastguard Worker SkScalar x = kDX; 77*c8dee2aaSAndroid Build Coastguard Worker 78*c8dee2aaSAndroid Build Coastguard Worker for (int et = 0; et < kGrClipEdgeTypeCnt; ++et) { 79*c8dee2aaSAndroid Build Coastguard Worker SkRect rect = r.makeOffset(x, y); 80*c8dee2aaSAndroid Build Coastguard Worker GrClipEdgeType edgeType = static_cast<GrClipEdgeType>(et); 81*c8dee2aaSAndroid Build Coastguard Worker auto fp = GrFragmentProcessor::Rect(/*inputFP=*/nullptr, edgeType, rect); 82*c8dee2aaSAndroid Build Coastguard Worker SkASSERT(fp); 83*c8dee2aaSAndroid Build Coastguard Worker 84*c8dee2aaSAndroid Build Coastguard Worker GrPaint grPaint; 85*c8dee2aaSAndroid Build Coastguard Worker grPaint.setColor4f({ 0, 0, 0, 1.f }); 86*c8dee2aaSAndroid Build Coastguard Worker grPaint.setXPFactory(GrPorterDuffXPFactory::Get(SkBlendMode::kSrc)); 87*c8dee2aaSAndroid Build Coastguard Worker grPaint.setCoverageFragmentProcessor(std::move(fp)); 88*c8dee2aaSAndroid Build Coastguard Worker auto drawRect = rect.makeOutset(kOutset, kOutset); 89*c8dee2aaSAndroid Build Coastguard Worker auto op = sk_gpu_test::test_ops::MakeRect(rContext, std::move(grPaint), drawRect); 90*c8dee2aaSAndroid Build Coastguard Worker sdc->addDrawOp(std::move(op)); 91*c8dee2aaSAndroid Build Coastguard Worker 92*c8dee2aaSAndroid Build Coastguard Worker x += SkScalarCeilToScalar(rect.width() + kDX); 93*c8dee2aaSAndroid Build Coastguard Worker } 94*c8dee2aaSAndroid Build Coastguard Worker 95*c8dee2aaSAndroid Build Coastguard Worker // Draw rect without and with AA using normal API for reference 96*c8dee2aaSAndroid Build Coastguard Worker canvas->save(); 97*c8dee2aaSAndroid Build Coastguard Worker canvas->translate(x, y); 98*c8dee2aaSAndroid Build Coastguard Worker SkPaint paint; 99*c8dee2aaSAndroid Build Coastguard Worker canvas->drawRect(r, paint); 100*c8dee2aaSAndroid Build Coastguard Worker x += SkScalarCeilToScalar(r.width() + kDX); 101*c8dee2aaSAndroid Build Coastguard Worker paint.setAntiAlias(true); 102*c8dee2aaSAndroid Build Coastguard Worker canvas->drawRect(r, paint); 103*c8dee2aaSAndroid Build Coastguard Worker canvas->restore(); 104*c8dee2aaSAndroid Build Coastguard Worker 105*c8dee2aaSAndroid Build Coastguard Worker y += SkScalarCeilToScalar(r.height() + 20.f); 106*c8dee2aaSAndroid Build Coastguard Worker } 107*c8dee2aaSAndroid Build Coastguard Worker 108*c8dee2aaSAndroid Build Coastguard Worker return DrawResult::kOk; 109*c8dee2aaSAndroid Build Coastguard Worker } 110*c8dee2aaSAndroid Build Coastguard Worker 111*c8dee2aaSAndroid Build Coastguard Worker private: 112*c8dee2aaSAndroid Build Coastguard Worker using INHERITED = GM; 113*c8dee2aaSAndroid Build Coastguard Worker }; 114*c8dee2aaSAndroid Build Coastguard Worker 115*c8dee2aaSAndroid Build Coastguard Worker DEF_GM(return new AARectEffect;) 116*c8dee2aaSAndroid Build Coastguard Worker } // namespace skiagm 117