From 547c8590a553efef7bcfb4c04e52072eb1271bea Mon Sep 17 00:00:00 2001 From: Mike Reed Date: Mon, 5 Feb 2018 15:59:23 -0500 Subject: gpu impl for compose and combine maskfilters remove "warning" in GrProcessorSet about coverage-as-alpha (we think the current behavior is correct) update gpudevice::drawImage to check for maskfilter before trying to create its mask Bug: skia: Change-Id: I9ecb6cd25dd003bc19fa1e33edf6614a5ba4acb7 Reviewed-on: https://skia-review.googlesource.com/103761 Commit-Queue: Mike Reed Reviewed-by: Brian Salomon --- gm/shadermaskfilter.cpp | 52 +++++++++++++++++++++++++++++++++---------------- 1 file changed, 35 insertions(+), 17 deletions(-) (limited to 'gm') diff --git a/gm/shadermaskfilter.cpp b/gm/shadermaskfilter.cpp index 73a9cda65f..c3efdc832c 100644 --- a/gm/shadermaskfilter.cpp +++ b/gm/shadermaskfilter.cpp @@ -7,13 +7,14 @@ #include "gm.h" #include "sk_tool_utils.h" +#include "SkBlendModePriv.h" #include "SkBlurMaskFilter.h" #include "SkCanvas.h" #include "SkImage.h" #include "SkShaderMaskFilter.h" static void draw_masked_image(SkCanvas* canvas, const SkImage* image, SkScalar x, SkScalar y, - const SkImage* mask, sk_sp outer = nullptr) { + const SkImage* mask, sk_sp outer, SkBlendMode mode) { SkMatrix matrix = SkMatrix::MakeScale(SkIntToScalar(image->width()) / mask->width(), SkIntToScalar(image->height() / mask->height())); SkPaint paint; @@ -23,6 +24,7 @@ static void draw_masked_image(SkCanvas* canvas, const SkImage* image, SkScalar x } paint.setMaskFilter(mf); paint.setAntiAlias(true); + paint.setBlendMode(mode); canvas->drawImage(image, x, y, &paint); } @@ -51,19 +53,25 @@ DEF_SIMPLE_GM(shadermaskfilter_gradient, canvas, 512, 512) { } #include "Resources.h" -DEF_SIMPLE_GM(shadermaskfilter_image, canvas, 512, 512) { +DEF_SIMPLE_GM(shadermaskfilter_image, canvas, 560, 370) { canvas->scale(1.25f, 1.25f); auto image = GetResourceAsImage("images/mandrill_128.png"); auto mask = GetResourceAsImage("images/color_wheel.png"); auto blurmf = SkBlurMaskFilter::Make(kNormal_SkBlurStyle, 5); + auto gradmf = SkShaderMaskFilter::Make(make_shader(SkRect::MakeIWH(mask->width(), + mask->height()))); - canvas->drawImage(image, 10, 10, nullptr); - canvas->drawImage(mask, 10 + image->width() + 10.f, 10, nullptr); - - draw_masked_image(canvas, image.get(), 10, 10 + image->height() + 10.f, mask.get()); - draw_masked_image(canvas, image.get(), 10 + image->width() + 10.f, 10 + image->height() + 10.f, - mask.get(), blurmf); + const sk_sp array[] = { nullptr , blurmf, gradmf }; + for (SkBlendMode mode : {SkBlendMode::kSrcOver, SkBlendMode::kSrcIn}) { + canvas->save(); + for (sk_sp mf : array) { + draw_masked_image(canvas, image.get(), 10, 10, mask.get(), mf, mode); + canvas->translate(image->width() + 20.f, 0); + } + canvas->restore(); + canvas->translate(0, image->height() + 20.f); + } } /////////////////////////////////////////////////////////////////////////////////////////////////// @@ -90,7 +98,7 @@ const char* gCoverageName[] = { "union", "sect", "diff", "rev-diff", "xor" }; -DEF_SIMPLE_GM(combinemaskfilter, canvas, 565, 250) { +DEF_SIMPLE_GM(combinemaskfilter, canvas, 560, 510) { const SkRect r = { 0, 0, 100, 100 }; SkPaint paint; @@ -102,8 +110,8 @@ DEF_SIMPLE_GM(combinemaskfilter, canvas, 565, 250) { labelP.setTextAlign(SkPaint::kCenter_Align); const SkRect r2 = r.makeOutset(1.5f, 1.5f); - SkPaint paint2; - paint2.setStyle(SkPaint::kStroke_Style); + SkPaint strokePaint; + strokePaint.setStyle(SkPaint::kStroke_Style); auto proc0 = [](const SkRect& r, SkPath* pathA, SkPath* pathB) { pathA->moveTo(r.fLeft, r.fBottom); @@ -132,13 +140,23 @@ DEF_SIMPLE_GM(combinemaskfilter, canvas, 565, 250) { for (int i = 0; i < 5; ++i) { canvas->drawText(gCoverageName[i], strlen(gCoverageName[i]), r.width()*0.5f, -10, labelP); - SkCoverageMode mode = static_cast(i); + SkCoverageMode cmode = static_cast(i); canvas->save(); - for (int j = 0; j < 2; ++j) { - paint.setMaskFilter(SkMaskFilter::MakeCombine(mfA[j], mfB[j], mode)); - canvas->drawRect(r2, paint2); - canvas->drawRect(r, paint); - canvas->translate(0, r.height() + 10); + // esp. on gpu side, its valuable to exercise modes that do and do-not convolve coverage + // with alpha. SrcOver and SrcIn have these properties, but also happen to "look" the same + // for this test. + const SkBlendMode bmodes[] = { SkBlendMode::kSrcOver, SkBlendMode::kSrcIn }; + SkASSERT( SkBlendMode_SupportsCoverageAsAlpha(bmodes[0])); // test as-alpha + SkASSERT(!SkBlendMode_SupportsCoverageAsAlpha(bmodes[1])); // test not-as-alpha + for (auto bmode : bmodes) { + paint.setBlendMode(bmode); + for (int j = 0; j < 2; ++j) { + paint.setMaskFilter(SkMaskFilter::MakeCombine(mfA[j], mfB[j], cmode)); + canvas->drawRect(r2, strokePaint); + canvas->drawRect(r, paint); + canvas->translate(0, r.height() + 10); + } + canvas->translate(0, 40); } canvas->restore(); canvas->translate(r.width() + 10, 0); -- cgit v1.2.3