[graphite] Update GMs to have graphite-backed gpu SkImages

This makes part of of our testing infrastructure (i.e., the GMs)
compatible with Graphite's more stringent requirements.

Bug: skia:12701
Change-Id: I5d2bf44a1f044797971a1cf6874cf1819d715ca6
Reviewed-on: https://skia-review.googlesource.com/c/skia/+/530539
Reviewed-by: Jim Van Verth <jvanverth@google.com>
Commit-Queue: Robert Phillips <robertphillips@google.com>
This commit is contained in:
Robert Phillips 2022-04-19 10:49:11 -04:00 committed by SkCQ
parent ffba7ace41
commit 932801c29e
19 changed files with 203 additions and 124 deletions

View File

@ -1357,6 +1357,7 @@ generated_cc_atom(
"//include/core:SkTileMode_hdr", "//include/core:SkTileMode_hdr",
"//include/core:SkTypes_hdr", "//include/core:SkTypes_hdr",
"//include/effects:SkGradientShader_hdr", "//include/effects:SkGradientShader_hdr",
"//tools:ToolUtils_hdr",
], ],
) )
@ -3149,6 +3150,7 @@ generated_cc_atom(
"//include/effects:SkImageFilters_hdr", "//include/effects:SkImageFilters_hdr",
"//src/effects/imagefilters:SkCropImageFilter_hdr", "//src/effects/imagefilters:SkCropImageFilter_hdr",
"//tools:Resources_hdr", "//tools:Resources_hdr",
"//tools:ToolUtils_hdr",
], ],
) )
@ -3170,6 +3172,7 @@ generated_cc_atom(
"//include/core:SkSize_hdr", "//include/core:SkSize_hdr",
"//include/core:SkString_hdr", "//include/core:SkString_hdr",
"//include/core:SkSurface_hdr", "//include/core:SkSurface_hdr",
"//tools:ToolUtils_hdr",
], ],
) )
@ -3503,6 +3506,7 @@ generated_cc_atom(
"//include/core:SkMatrix_hdr", "//include/core:SkMatrix_hdr",
"//include/core:SkRect_hdr", "//include/core:SkRect_hdr",
"//tools:Resources_hdr", "//tools:Resources_hdr",
"//tools:ToolUtils_hdr",
], ],
) )
@ -3709,6 +3713,7 @@ generated_cc_atom(
"//include/effects:SkGradientShader_hdr", "//include/effects:SkGradientShader_hdr",
"//include/utils:SkRandom_hdr", "//include/utils:SkRandom_hdr",
"//src/core:SkMathPriv_hdr", "//src/core:SkMathPriv_hdr",
"//tools:ToolUtils_hdr",
], ],
) )
@ -6904,6 +6909,7 @@ generated_cc_atom(
"//include/private:SkTArray_hdr", "//include/private:SkTArray_hdr",
"//include/private:SkTDArray_hdr", "//include/private:SkTDArray_hdr",
"//tools:Resources_hdr", "//tools:Resources_hdr",
"//tools:ToolUtils_hdr",
], ],
) )
@ -8641,6 +8647,7 @@ generated_cc_atom(
"//include/core:SkTypes_hdr", "//include/core:SkTypes_hdr",
"//include/private:SkTo_hdr", "//include/private:SkTo_hdr",
"//include/utils:SkRandom_hdr", "//include/utils:SkRandom_hdr",
"//tools:ToolUtils_hdr",
], ],
) )
@ -9360,6 +9367,7 @@ generated_cc_atom(
"//include/core:SkSurface_hdr", "//include/core:SkSurface_hdr",
"//include/core:SkTileMode_hdr", "//include/core:SkTileMode_hdr",
"//include/effects:SkGradientShader_hdr", "//include/effects:SkGradientShader_hdr",
"//tools:ToolUtils_hdr",
], ],
) )

View File

@ -20,20 +20,21 @@
#include "include/core/SkTileMode.h" #include "include/core/SkTileMode.h"
#include "include/core/SkTypes.h" #include "include/core/SkTypes.h"
#include "include/effects/SkGradientShader.h" #include "include/effects/SkGradientShader.h"
#include "tools/ToolUtils.h"
static sk_sp<SkImage> make_image() { static sk_sp<SkImage> make_image(SkCanvas* destCanvas) {
auto surf = SkSurface::MakeRasterN32Premul(64, 64); auto surf = SkSurface::MakeRasterN32Premul(64, 64);
auto canvas = surf->getCanvas(); auto tmpCanvas = surf->getCanvas();
canvas->drawColor(SK_ColorRED); tmpCanvas->drawColor(SK_ColorRED);
SkPaint paint; SkPaint paint;
paint.setAntiAlias(true); paint.setAntiAlias(true);
const SkPoint pts[] = { { 0, 0 }, { 64, 64 } }; const SkPoint pts[] = { { 0, 0 }, { 64, 64 } };
const SkColor colors[] = { SK_ColorWHITE, SK_ColorBLUE }; const SkColor colors[] = { SK_ColorWHITE, SK_ColorBLUE };
paint.setShader(SkGradientShader::MakeLinear(pts, colors, nullptr, 2, SkTileMode::kClamp)); paint.setShader(SkGradientShader::MakeLinear(pts, colors, nullptr, 2, SkTileMode::kClamp));
canvas->drawCircle(32, 32, 32, paint); tmpCanvas->drawCircle(32, 32, 32, paint);
return surf->makeImageSnapshot(); return ToolUtils::MakeTextureImage(destCanvas, surf->makeImageSnapshot());
} }
class DrawBitmapRect2 : public skiagm::GM { class DrawBitmapRect2 : public skiagm::GM {
@ -67,7 +68,7 @@ protected:
paint.setStyle(SkPaint::kStroke_Style); paint.setStyle(SkPaint::kStroke_Style);
auto sampling = SkSamplingOptions(); auto sampling = SkSamplingOptions();
auto image = make_image(); auto image = make_image(canvas);
SkRect dstR = { 0, 200, 128, 380 }; SkRect dstR = { 0, 200, 128, 380 };
@ -152,7 +153,8 @@ protected:
SkRect srcR = { 0.5f, 0.5f, 2.5f, 2.5f }; SkRect srcR = { 0.5f, 0.5f, 2.5f, 2.5f };
SkRect dstR = { 100, 100, 300, 200 }; SkRect dstR = { 100, 100, 300, 200 };
canvas->drawImageRect(bitmap.asImage(), srcR, dstR, SkSamplingOptions(), canvas->drawImageRect(ToolUtils::MakeTextureImage(canvas, bitmap.asImage()),
srcR, dstR, SkSamplingOptions(),
nullptr, SkCanvas::kStrict_SrcRectConstraint); nullptr, SkCanvas::kStrict_SrcRectConstraint);
} }
@ -161,7 +163,7 @@ private:
}; };
////////////////////////////////////////////////////////////////////////////// //////////////////////////////////////////////////////////////////////////////
static sk_sp<SkImage> make_big_bitmap() { static sk_sp<SkImage> make_big_bitmap(SkCanvas* canvas) {
constexpr int gXSize = 4096; constexpr int gXSize = 4096;
constexpr int gYSize = 4096; constexpr int gYSize = 4096;
@ -180,7 +182,7 @@ static sk_sp<SkImage> make_big_bitmap() {
} }
} }
bitmap.setImmutable(); bitmap.setImmutable();
return bitmap.asImage(); return ToolUtils::MakeTextureImage(canvas, bitmap.asImage());
} }
// This GM attempts to reveal any issues we may have when the GPU has to // This GM attempts to reveal any issues we may have when the GPU has to
@ -207,11 +209,11 @@ protected:
return SkISize::Make(640, 480); return SkISize::Make(640, 480);
} }
void onOnceBeforeDraw() override {
fBigImage = make_big_bitmap();
}
void onDraw(SkCanvas* canvas) override { void onDraw(SkCanvas* canvas) override {
if (!fBigImage) {
fBigImage = make_big_bitmap(canvas);
}
SkPaint paint; SkPaint paint;
paint.setAlpha(128); paint.setAlpha(128);
paint.setBlendMode(SkBlendMode::kXor); paint.setBlendMode(SkBlendMode::kXor);

View File

@ -33,7 +33,7 @@
/** Creates an image with two one-pixel wide borders around a checkerboard. The checkerboard is 2x2 /** Creates an image with two one-pixel wide borders around a checkerboard. The checkerboard is 2x2
checks where each check has as many pixels as is necessary to fill the interior. It returns checks where each check has as many pixels as is necessary to fill the interior. It returns
the image and a src rect that bounds the checkerboard portion. */ the image and a src rect that bounds the checkerboard portion. */
std::tuple<sk_sp<SkImage>, SkRect> make_ringed_image(int width, int height) { std::tuple<sk_sp<SkImage>, SkRect> make_ringed_image(SkCanvas* canvas, int width, int height) {
// These are kRGBA_8888_SkColorType values. // These are kRGBA_8888_SkColorType values.
static constexpr uint32_t kOuterRingColor = 0xFFFF0000, static constexpr uint32_t kOuterRingColor = 0xFFFF0000,
@ -101,7 +101,8 @@ std::tuple<sk_sp<SkImage>, SkRect> make_ringed_image(int width, int height) {
scanline[x] = kOuterRingColor; scanline[x] = kOuterRingColor;
} }
bitmap.setImmutable(); bitmap.setImmutable();
return {bitmap.asImage(), SkRect::Make({2, 2, width - 2, height - 2})}; return { ToolUtils::MakeTextureImage(canvas, bitmap.asImage()),
SkRect::Make({2, 2, width - 2, height - 2})};
} }
/** /**
@ -127,6 +128,10 @@ protected:
void drawImage(SkCanvas* canvas, sk_sp<SkImage> image, SkRect srcRect, SkRect dstRect, void drawImage(SkCanvas* canvas, sk_sp<SkImage> image, SkRect srcRect, SkRect dstRect,
const SkSamplingOptions& sampling, SkPaint* paint) { const SkSamplingOptions& sampling, SkPaint* paint) {
if (fBatch) { if (fBatch) {
if (!image) {
return;
}
SkCanvas::ImageSetEntry imageSetEntry[1]; SkCanvas::ImageSetEntry imageSetEntry[1];
imageSetEntry[0].fImage = image; imageSetEntry[0].fImage = image;
imageSetEntry[0].fSrcRect = srcRect; imageSetEntry[0].fSrcRect = srcRect;
@ -152,7 +157,7 @@ protected:
paint.setColor(SK_ColorBLUE); paint.setColor(SK_ColorBLUE);
paint.setAntiAlias(aa); paint.setAntiAlias(aa);
drawImage(canvas, fSmallImage, fSmallSrcRect, dst, sampling, &paint); this->drawImage(canvas, fSmallImage, fSmallSrcRect, dst, sampling, &paint);
} }
// Draw the area of interest of the large image // Draw the area of interest of the large image
@ -165,7 +170,7 @@ protected:
paint.setColor(SK_ColorBLUE); paint.setColor(SK_ColorBLUE);
paint.setAntiAlias(aa); paint.setAntiAlias(aa);
drawImage(canvas, fBigImage, fBigSrcRect, dst, sampling, &paint); this->drawImage(canvas, fBigImage, fBigSrcRect, dst, sampling, &paint);
} }
// Draw upper-left 1/4 of the area of interest of the large image // Draw upper-left 1/4 of the area of interest of the large image
@ -182,7 +187,7 @@ protected:
paint.setColor(SK_ColorBLUE); paint.setColor(SK_ColorBLUE);
paint.setAntiAlias(aa); paint.setAntiAlias(aa);
drawImage(canvas, fBigImage, src, dst, sampling, &paint); this->drawImage(canvas, fBigImage, src, dst, sampling, &paint);
} }
// Draw the area of interest of the small image with a normal blur // Draw the area of interest of the small image with a normal blur
@ -197,7 +202,7 @@ protected:
paint.setColor(SK_ColorBLUE); paint.setColor(SK_ColorBLUE);
paint.setAntiAlias(aa); paint.setAntiAlias(aa);
drawImage(canvas, fSmallImage, fSmallSrcRect, dst, sampling, &paint); this->drawImage(canvas, fSmallImage, fSmallSrcRect, dst, sampling, &paint);
} }
// Draw the area of interest of the small image with a outer blur // Draw the area of interest of the small image with a outer blur
@ -212,15 +217,18 @@ protected:
paint.setColor(SK_ColorBLUE); paint.setColor(SK_ColorBLUE);
paint.setAntiAlias(aa); paint.setAntiAlias(aa);
drawImage(canvas, fSmallImage, fSmallSrcRect, dst, sampling, &paint); this->drawImage(canvas, fSmallImage, fSmallSrcRect, dst, sampling, &paint);
}
void onOnceBeforeDraw() override {
std::tie(fBigImage, fBigSrcRect) = make_ringed_image(2*kMaxTextureSize, 2*kMaxTextureSize);
std::tie(fSmallImage, fSmallSrcRect) = make_ringed_image(kSmallSize, kSmallSize);
} }
void onDraw(SkCanvas* canvas) override { void onDraw(SkCanvas* canvas) override {
if (!fSmallImage) {
std::tie(fBigImage, fBigSrcRect) = make_ringed_image(canvas,
2*kMaxTextureSize,
2*kMaxTextureSize);
std::tie(fSmallImage, fSmallSrcRect) = make_ringed_image(canvas,
kSmallSize, kSmallSize);
}
canvas->clear(SK_ColorGRAY); canvas->clear(SK_ColorGRAY);
std::vector<SkMatrix> matrices; std::vector<SkMatrix> matrices;
// Draw with identity // Draw with identity
@ -393,5 +401,3 @@ DEF_SIMPLE_GM(bleed_downscale, canvas, 360, 240) {
canvas->translate(0, 120); canvas->translate(0, 120);
} }
} }

View File

@ -68,8 +68,12 @@ DEF_SIMPLE_GM(colorwheel_alphatypes, canvas, 256, 128) {
sk_sp<SkData> imgData = GetResourceAsData("images/color_wheel.png"); sk_sp<SkData> imgData = GetResourceAsData("images/color_wheel.png");
auto pmImg = SkImage::MakeFromEncoded(imgData, kPremul_SkAlphaType); auto pmImg = ToolUtils::MakeTextureImage(canvas,
auto upmImg = SkImage::MakeFromEncoded(imgData, kUnpremul_SkAlphaType); SkImage::MakeFromEncoded(imgData,
kPremul_SkAlphaType));
auto upmImg = ToolUtils::MakeTextureImage(canvas,
SkImage::MakeFromEncoded(imgData,
kUnpremul_SkAlphaType));
SkSamplingOptions linear{SkFilterMode::kLinear}; SkSamplingOptions linear{SkFilterMode::kLinear};

View File

@ -19,6 +19,7 @@
#include "include/effects/SkImageFilters.h" #include "include/effects/SkImageFilters.h"
#include "tools/Resources.h" #include "tools/Resources.h"
#include "tools/ToolUtils.h"
// TODO(michaelludwig) - This will be made public within SkImageFilters.h at some point // TODO(michaelludwig) - This will be made public within SkImageFilters.h at some point
#include "src/effects/imagefilters/SkCropImageFilter.h" #include "src/effects/imagefilters/SkCropImageFilter.h"
@ -179,16 +180,19 @@ void draw_example(
{ {
SkRect clippedContentBounds; SkRect clippedContentBounds;
if (clippedContentBounds.intersect(contentBounds, kExampleBounds)) { if (clippedContentBounds.intersect(contentBounds, kExampleBounds)) {
auto contentImage = image->makeSubset(clippedContentBounds.roundOut()); auto contentImage = ToolUtils::MakeTextureImage(
SkPaint tiledPaint; canvas, image->makeSubset(clippedContentBounds.roundOut()));
tiledPaint.setShader(contentImage->makeShader( if (contentImage) {
inputMode, inputMode, SkSamplingOptions(SkFilterMode::kLinear))); SkPaint tiledPaint;
tiledPaint.setAlphaf(0.15f); tiledPaint.setShader(contentImage->makeShader(
inputMode, inputMode, SkSamplingOptions(SkFilterMode::kLinear)));
tiledPaint.setAlphaf(0.15f);
canvas->save(); canvas->save();
canvas->translate(clippedContentBounds.fLeft, clippedContentBounds.fTop); canvas->translate(clippedContentBounds.fLeft, clippedContentBounds.fTop);
canvas->drawPaint(tiledPaint); canvas->drawPaint(tiledPaint);
canvas->restore(); canvas->restore();
}
} }
} }
@ -204,7 +208,8 @@ void draw_example(
canvas->clipRect(outputBounds); canvas->clipRect(outputBounds);
canvas->saveLayer(hintContent ? &contentBounds : nullptr, &layerPaint); canvas->saveLayer(hintContent ? &contentBounds : nullptr, &layerPaint);
canvas->drawImageRect(image.get(), contentBounds, contentBounds, auto tmp = ToolUtils::MakeTextureImage(canvas, image);
canvas->drawImageRect(tmp, contentBounds, contentBounds,
SkSamplingOptions(SkFilterMode::kLinear), nullptr, SkSamplingOptions(SkFilterMode::kLinear), nullptr,
SkCanvas::kFast_SrcRectConstraint); SkCanvas::kFast_SrcRectConstraint);
canvas->restore(); canvas->restore();

View File

@ -18,11 +18,32 @@
#include "include/core/SkSize.h" #include "include/core/SkSize.h"
#include "include/core/SkString.h" #include "include/core/SkString.h"
#include "include/core/SkSurface.h" #include "include/core/SkSurface.h"
#include "tools/ToolUtils.h"
namespace skiagm { namespace skiagm {
constexpr SkRect kSrcImageClip{75, 75, 275, 275}; constexpr SkRect kSrcImageClip{75, 75, 275, 275};
static sk_sp<SkImage> create_image(SkCanvas* destCanvas) {
sk_sp<SkSurface> srcSurface = SkSurface::MakeRasterN32Premul(500, 500);
SkCanvas* srcCanvas = srcSurface->getCanvas();
srcCanvas->clear(SK_ColorRED);
SkPaint paint;
paint.setColor(0xff00ff00);
srcCanvas->drawRect(kSrcImageClip, paint);
constexpr SkScalar kStrokeWidth = 10;
SkPaint stroke;
stroke.setStyle(SkPaint::kStroke_Style);
stroke.setStrokeWidth(kStrokeWidth);
stroke.setColor(0xff008800);
srcCanvas->drawRect(kSrcImageClip.makeInset(kStrokeWidth / 2, kStrokeWidth / 2), stroke);
return ToolUtils::MakeTextureImage(destCanvas, srcSurface->makeImageSnapshot());
}
/* /*
* The purpose of this test is to exercise all three codepaths in skgpu::v1::SurfaceDrawContext * The purpose of this test is to exercise all three codepaths in skgpu::v1::SurfaceDrawContext
* (drawFilledRect, fillRectToRect, fillRectWithLocalMatrix) that pre-crop filled rects based on the * (drawFilledRect, fillRectToRect, fillRectWithLocalMatrix) that pre-crop filled rects based on the
@ -37,28 +58,12 @@ private:
SkString onShortName() final { return SkString("croppedrects"); } SkString onShortName() final { return SkString("croppedrects"); }
SkISize onISize() override { return SkISize::Make(500, 500); } SkISize onISize() override { return SkISize::Make(500, 500); }
void onOnceBeforeDraw() override {
sk_sp<SkSurface> srcSurface = SkSurface::MakeRasterN32Premul(500, 500);
SkCanvas* srcCanvas = srcSurface->getCanvas();
srcCanvas->clear(SK_ColorRED);
SkPaint paint;
paint.setColor(0xff00ff00);
srcCanvas->drawRect(kSrcImageClip, paint);
constexpr SkScalar kStrokeWidth = 10;
SkPaint stroke;
stroke.setStyle(SkPaint::kStroke_Style);
stroke.setStrokeWidth(kStrokeWidth);
stroke.setColor(0xff008800);
srcCanvas->drawRect(kSrcImageClip.makeInset(kStrokeWidth / 2, kStrokeWidth / 2), stroke);
fSrcImage = srcSurface->makeImageSnapshot();
fSrcImageShader = fSrcImage->makeShader(SkSamplingOptions());
}
void onDraw(SkCanvas* canvas) override { void onDraw(SkCanvas* canvas) override {
if (!fSrcImage) {
fSrcImage = create_image(canvas);
fSrcImageShader = fSrcImage->makeShader(SkSamplingOptions());
}
canvas->clear(SK_ColorWHITE); canvas->clear(SK_ColorWHITE);
{ {

View File

@ -11,10 +11,12 @@
#include "include/core/SkMatrix.h" #include "include/core/SkMatrix.h"
#include "include/core/SkRect.h" #include "include/core/SkRect.h"
#include "tools/Resources.h" #include "tools/Resources.h"
#include "tools/ToolUtils.h"
// https://bug.skia.org/4374 // https://bug.skia.org/4374
DEF_SIMPLE_GM(draw_bitmap_rect_skbug4734, canvas, 64, 64) { DEF_SIMPLE_GM(draw_bitmap_rect_skbug4734, canvas, 64, 64) {
if (auto img = GetResourceAsImage("images/randPixels.png")) { auto img = ToolUtils::MakeTextureImage(canvas, GetResourceAsImage("images/randPixels.png"));
if (img) {
SkRect rect = SkRect::Make(img->bounds()); SkRect rect = SkRect::Make(img->bounds());
rect.inset(0.5, 1.5); rect.inset(0.5, 1.5);
SkRect dst; SkRect dst;

View File

@ -104,14 +104,16 @@ static sk_sp<SkImage> makebm(SkCanvas* origCanvas, SkBitmap* resultBM, int w, in
return image; return image;
} }
static void bitmapproc(SkCanvas* canvas, SkImage*, const SkBitmap& bm, const SkIRect& srcR, static void bitmapproc(SkCanvas* canvas, sk_sp<SkImage>, const SkBitmap& bm, const SkIRect& srcR,
const SkRect& dstR, const SkSamplingOptions& sampling, const SkRect& dstR, const SkSamplingOptions& sampling,
const SkPaint* paint) { const SkPaint* paint) {
canvas->drawImageRect(bm.asImage(), SkRect::Make(srcR), dstR, sampling, paint, sk_sp<SkImage> img = ToolUtils::MakeTextureImage(canvas, bm.asImage());
canvas->drawImageRect(img, SkRect::Make(srcR), dstR, sampling, paint,
SkCanvas::kStrict_SrcRectConstraint); SkCanvas::kStrict_SrcRectConstraint);
} }
static void bitmapsubsetproc(SkCanvas* canvas, SkImage*, const SkBitmap& bm, const SkIRect& srcR, static void bitmapsubsetproc(SkCanvas* canvas, sk_sp<SkImage>,
const SkBitmap& bm, const SkIRect& srcR,
const SkRect& dstR, const SkSamplingOptions& sampling, const SkRect& dstR, const SkSamplingOptions& sampling,
const SkPaint* paint) { const SkPaint* paint) {
if (!bm.bounds().contains(srcR)) { if (!bm.bounds().contains(srcR)) {
@ -121,21 +123,23 @@ static void bitmapsubsetproc(SkCanvas* canvas, SkImage*, const SkBitmap& bm, con
SkBitmap subset; SkBitmap subset;
if (bm.extractSubset(&subset, srcR)) { if (bm.extractSubset(&subset, srcR)) {
canvas->drawImageRect(subset.asImage(), dstR, sampling, paint); sk_sp<SkImage> subsetImg = ToolUtils::MakeTextureImage(canvas, subset.asImage());
canvas->drawImageRect(subsetImg, dstR, sampling, paint);
} }
} }
static void imageproc(SkCanvas* canvas, SkImage* image, const SkBitmap&, const SkIRect& srcR, static void imageproc(SkCanvas* canvas, sk_sp<SkImage> image, const SkBitmap&, const SkIRect& srcR,
const SkRect& dstR, const SkSamplingOptions& sampling, const SkPaint* paint) { const SkRect& dstR, const SkSamplingOptions& sampling, const SkPaint* paint) {
canvas->drawImageRect(image, SkRect::Make(srcR), dstR, sampling, paint, sk_sp<SkImage> tmp = ToolUtils::MakeTextureImage(canvas, std::move(image));
canvas->drawImageRect(tmp, SkRect::Make(srcR), dstR, sampling, paint,
SkCanvas::kStrict_SrcRectConstraint); SkCanvas::kStrict_SrcRectConstraint);
} }
static void imagesubsetproc(SkCanvas* canvas, SkImage* image, const SkBitmap& bm, static void imagesubsetproc(SkCanvas* canvas, sk_sp<SkImage> image, const SkBitmap& bm,
const SkIRect& srcR, const SkRect& dstR, const SkIRect& srcR, const SkRect& dstR,
const SkSamplingOptions& sampling, const SkPaint* paint) { const SkSamplingOptions& sampling, const SkPaint* paint) {
if (!image->bounds().contains(srcR)) { if (!image->bounds().contains(srcR)) {
imageproc(canvas, image, bm, srcR, dstR, sampling, paint); imageproc(canvas, std::move(image), bm, srcR, dstR, sampling, paint);
return; return;
} }
@ -145,7 +149,8 @@ static void imagesubsetproc(SkCanvas* canvas, SkImage* image, const SkBitmap& bm
} }
} }
typedef void DrawRectRectProc(SkCanvas*, SkImage*, const SkBitmap&, const SkIRect&, const SkRect&, typedef void DrawRectRectProc(SkCanvas*, sk_sp<SkImage>, const SkBitmap&,
const SkIRect& srcR, const SkRect& dstR,
const SkSamplingOptions&, const SkPaint*); const SkSamplingOptions&, const SkPaint*);
constexpr int gSize = 1024; constexpr int gSize = 1024;
@ -171,7 +176,8 @@ protected:
SkISize onISize() override { return SkISize::Make(gSize, gSize); } SkISize onISize() override { return SkISize::Make(gSize, gSize); }
void setupImage(SkCanvas* canvas) { void setupImage(SkCanvas* canvas) {
fImage = makebm(canvas, &fLargeBitmap, gBmpSize, gBmpSize); fImage = ToolUtils::MakeTextureImage(canvas,
makebm(canvas, &fLargeBitmap, gBmpSize, gBmpSize));
} }
void onDraw(SkCanvas* canvas) override { void onDraw(SkCanvas* canvas) override {
@ -208,7 +214,7 @@ protected:
for (int h = 1; h <= kMaxSrcRectSize; h *= 4) { for (int h = 1; h <= kMaxSrcRectSize; h *= 4) {
SkIRect srcRect = SkIRect::MakeXYWH((gBmpSize - w) / 2, (gBmpSize - h) / 2, w, h); SkIRect srcRect = SkIRect::MakeXYWH((gBmpSize - w) / 2, (gBmpSize - h) / 2, w, h);
fProc(canvas, fImage.get(), fLargeBitmap, srcRect, dstRect, SkSamplingOptions(), fProc(canvas, fImage, fLargeBitmap, srcRect, dstRect, SkSamplingOptions(),
nullptr); nullptr);
SkString label; SkString label;
@ -246,7 +252,7 @@ protected:
kNormal_SkBlurStyle, kNormal_SkBlurStyle,
SkBlurMask::ConvertRadiusToSigma(SkIntToScalar(5)))); SkBlurMask::ConvertRadiusToSigma(SkIntToScalar(5))));
fProc(canvas, bm.asImage().get(), bm, srcRect, dstRect, fProc(canvas, bm.asImage(), bm, srcRect, dstRect,
SkSamplingOptions(SkFilterMode::kLinear), &maskPaint); SkSamplingOptions(SkFilterMode::kLinear), &maskPaint);
} }
} }

View File

@ -338,7 +338,9 @@ private:
int i = y * kM + x; int i = y * kM + x;
SkPaint entryPaint = paint; SkPaint entryPaint = paint;
entryPaint.setAlphaf(fSet[i].fAlpha * paint.getAlphaf()); entryPaint.setAlphaf(fSet[i].fAlpha * paint.getAlphaf());
canvas->drawImageRect(fSet[i].fImage.get(), fSet[i].fSrcRect, fSet[i].fDstRect, sk_sp<SkImage> orig = sk_ref_sp(const_cast<SkImage*>(fSet[i].fImage.get()));
canvas->drawImageRect(ToolUtils::MakeTextureImage(canvas, std::move(orig)),
fSet[i].fSrcRect, fSet[i].fDstRect,
SkSamplingOptions(), &entryPaint, SkSamplingOptions(), &entryPaint,
SkCanvas::kFast_SrcRectConstraint); SkCanvas::kFast_SrcRectConstraint);
} }

View File

@ -25,6 +25,7 @@
#include "include/effects/SkGradientShader.h" #include "include/effects/SkGradientShader.h"
#include "include/utils/SkRandom.h" #include "include/utils/SkRandom.h"
#include "src/core/SkMathPriv.h" #include "src/core/SkMathPriv.h"
#include "tools/ToolUtils.h"
static sk_sp<SkImage> makebm(int w, int h) { static sk_sp<SkImage> makebm(int w, int h) {
SkImageInfo info = SkImageInfo::MakeN32Premul(w, h); SkImageInfo info = SkImageInfo::MakeN32Premul(w, h);
@ -90,7 +91,7 @@ protected:
void onDraw(SkCanvas* canvas) override { void onDraw(SkCanvas* canvas) override {
if (nullptr == fImage) { if (nullptr == fImage) {
fImage = makebm(gSurfaceSize, gSurfaceSize); fImage = ToolUtils::MakeTextureImage(canvas, makebm(gSurfaceSize, gSurfaceSize));
} }
const SkRect dstRect = { 0, 0, SkIntToScalar(64), SkIntToScalar(64)}; const SkRect dstRect = { 0, 0, SkIntToScalar(64), SkIntToScalar(64)};

View File

@ -46,7 +46,7 @@ const SkSamplingOptions gSamplings[] = {
SkSamplingOptions(SkCubicResampler::Mitchell()), SkSamplingOptions(SkCubicResampler::Mitchell()),
}; };
static void drawContents(SkSurface* surface, SkColor fillC) { static void draw_contents(SkSurface* surface, SkColor fillC) {
SkSize size = SkSize::Make(SkIntToScalar(surface->width()), SkSize size = SkSize::Make(SkIntToScalar(surface->width()),
SkIntToScalar(surface->height())); SkIntToScalar(surface->height()));
SkCanvas* canvas = surface->getCanvas(); SkCanvas* canvas = surface->getCanvas();
@ -67,7 +67,7 @@ static void drawContents(SkSurface* surface, SkColor fillC) {
} }
static void test_surface(SkCanvas* canvas, SkSurface* surf, bool usePaint) { static void test_surface(SkCanvas* canvas, SkSurface* surf, bool usePaint) {
drawContents(surf, SK_ColorRED); draw_contents(surf, SK_ColorRED);
sk_sp<SkImage> imgR = surf->makeImageSnapshot(); sk_sp<SkImage> imgR = surf->makeImageSnapshot();
if (true) { if (true) {
@ -75,13 +75,14 @@ static void test_surface(SkCanvas* canvas, SkSurface* surf, bool usePaint) {
SkASSERT(imgR == imgR2); SkASSERT(imgR == imgR2);
} }
drawContents(surf, SK_ColorGREEN); imgR = ToolUtils::MakeTextureImage(canvas, std::move(imgR));
sk_sp<SkImage> imgG = surf->makeImageSnapshot(); draw_contents(surf, SK_ColorGREEN);
sk_sp<SkImage> imgG = ToolUtils::MakeTextureImage(canvas, surf->makeImageSnapshot());
// since we've drawn after we snapped imgR, imgG will be a different obj // since we've drawn after we snapped imgR, imgG will be a different obj
SkASSERT(imgR != imgG); SkASSERT(imgR != imgG);
drawContents(surf, SK_ColorBLUE); draw_contents(surf, SK_ColorBLUE);
SkSamplingOptions sampling; SkSamplingOptions sampling;
SkPaint paint; SkPaint paint;

View File

@ -268,28 +268,16 @@ protected:
{ 30, 30, 75, 75 } { 30, 30, 75, 75 }
}; };
auto rContext = canvas->recordingContext();
if (rContext && rContext->abandoned()) {
*errorMsg = "Direct context abandoned.";
return DrawResult::kSkip;
}
// These need to be GPU-backed when on the GPU to ensure that the image filters use the GPU // These need to be GPU-backed when on the GPU to ensure that the image filters use the GPU
// code paths (otherwise they may choose to do CPU filtering then upload) // code paths (otherwise they may choose to do CPU filtering then upload)
sk_sp<SkImage> mainImage, auxImage; sk_sp<SkImage> mainImage = ToolUtils::MakeTextureImage(canvas, fMainImage);
sk_sp<SkImage> auxImage = ToolUtils::MakeTextureImage(canvas, fAuxImage);
auto rContext = canvas->recordingContext();
// In a DDL context, we can't use the GPU code paths and we will drop the work skip.
auto dContext = GrAsDirectContext(rContext);
if (rContext) {
if (!dContext) {
*errorMsg = "Requires a direct context.";
return DrawResult::kSkip;
}
if (dContext->abandoned()) {
*errorMsg = "Direct context abandoned.";
return DrawResult::kSkip;
}
mainImage = fMainImage->makeTextureImage(dContext);
auxImage = fAuxImage->makeTextureImage(dContext);
} else {
mainImage = fMainImage;
auxImage = fAuxImage;
}
if (!mainImage || !auxImage) { if (!mainImage || !auxImage) {
return DrawResult::kFail; return DrawResult::kFail;
} }
@ -382,8 +370,10 @@ private:
auto rContext = canvas->recordingContext(); auto rContext = canvas->recordingContext();
result = mainImage->makeWithFilter(rContext, filter.get(), subset, clip, result = mainImage->makeWithFilter(rContext, filter.get(), subset, clip,
&outSubset, &offset); &outSubset, &offset);
if (!result) {
return;
}
SkASSERT(result);
SkASSERT(mainImage->isTextureBacked() == result->isTextureBacked()); SkASSERT(mainImage->isTextureBacked() == result->isTextureBacked());
*dstRect = SkIRect::MakeXYWH(offset.x(), offset.y(), *dstRect = SkIRect::MakeXYWH(offset.x(), offset.y(),

View File

@ -80,7 +80,7 @@ DEF_SIMPLE_GM(imagemasksubset, canvas, 480, 480) {
const SkImageInfo info = SkImageInfo::MakeA8(kSize.width(), kSize.height()); const SkImageInfo info = SkImageInfo::MakeA8(kSize.width(), kSize.height());
for (size_t i = 0; i < SK_ARRAY_COUNT(makers); ++i) { for (size_t i = 0; i < SK_ARRAY_COUNT(makers); ++i) {
sk_sp<SkImage> image = makers[i](canvas, info); sk_sp<SkImage> image = ToolUtils::MakeTextureImage(canvas, makers[i](canvas, info));
if (image) { if (image) {
canvas->drawImageRect(image, SkRect::Make(kSubset), kDest, SkSamplingOptions(), canvas->drawImageRect(image, SkRect::Make(kSubset), kDest, SkSamplingOptions(),
&paint, SkCanvas::kStrict_SrcRectConstraint); &paint, SkCanvas::kStrict_SrcRectConstraint);

View File

@ -17,6 +17,7 @@
#include "include/private/SkTArray.h" #include "include/private/SkTArray.h"
#include "include/private/SkTDArray.h" #include "include/private/SkTDArray.h"
#include "tools/Resources.h" #include "tools/Resources.h"
#include "tools/ToolUtils.h"
#include <initializer_list> #include <initializer_list>
@ -82,27 +83,30 @@ protected:
SkSamplingOptions(SkFilterMode::kLinear), SkSamplingOptions(SkFilterMode::kLinear),
SkSamplingOptions(SkFilterMode::kLinear, SkMipmapMode::kLinear), SkSamplingOptions(SkFilterMode::kLinear, SkMipmapMode::kLinear),
SkSamplingOptions(SkCubicResampler::Mitchell())}) { SkSamplingOptions(SkCubicResampler::Mitchell())}) {
for (const auto& img : fImages) { for (const auto& origImage : fImages) {
canvas->save(); sk_sp<SkImage> img = ToolUtils::MakeTextureImage(canvas, origImage);
canvas->concat(m); if (img) {
SkRect src = {img->width() / 4.f, img->height() / 4.f, canvas->save();
3.f * img->width() / 4.f, 3.f * img->height() / 4}; canvas->concat(m);
SkRect dst = {0, 0, SkRect src = { img->width() / 4.f, img->height() / 4.f,
3.f / 4.f * img->width(), 3.f / 4.f * img->height()}; 3.f * img->width() / 4.f, 3.f * img->height() / 4 };
switch (type) { SkRect dst = { 0, 0,
case DrawType::kDrawImage: 3.f / 4.f * img->width(), 3.f / 4.f * img->height()};
canvas->drawImage(img, 0, 0, sampling, &paint); switch (type) {
break; case DrawType::kDrawImage:
case DrawType::kDrawImageRectStrict: canvas->drawImage(img, 0, 0, sampling, &paint);
canvas->drawImageRect(img, src, dst, sampling, &paint, break;
SkCanvas::kStrict_SrcRectConstraint); case DrawType::kDrawImageRectStrict:
break; canvas->drawImageRect(img, src, dst, sampling, &paint,
case DrawType::kDrawImageRectFast: SkCanvas::kStrict_SrcRectConstraint);
canvas->drawImageRect(img, src, dst, sampling, &paint, break;
SkCanvas::kFast_SrcRectConstraint); case DrawType::kDrawImageRectFast:
break; canvas->drawImageRect(img, src, dst, sampling, &paint,
SkCanvas::kFast_SrcRectConstraint);
break;
}
canvas->restore();
} }
canvas->restore();
++n; ++n;
if (n < 8) { if (n < 8) {
canvas->translate(bounds.width() + 10.f, 0); canvas->translate(bounds.width() + 10.f, 0);

View File

@ -17,6 +17,7 @@
#include "include/core/SkTypes.h" #include "include/core/SkTypes.h"
#include "include/private/SkTo.h" #include "include/private/SkTo.h"
#include "include/utils/SkRandom.h" #include "include/utils/SkRandom.h"
#include "tools/ToolUtils.h"
int make_bm(SkBitmap* bm, int height) { int make_bm(SkBitmap* bm, int height) {
constexpr int kRadius = 22; constexpr int kRadius = 22;
@ -93,7 +94,8 @@ protected:
SkIRect subRect = SkIRect::MakeLTRB(0, startItem * itemHeight, SkIRect subRect = SkIRect::MakeLTRB(0, startItem * itemHeight,
bmp.width(), bmp.height()); bmp.width(), bmp.height());
SkRect dstRect = SkRect::MakeWH(SkIntToScalar(bmp.width()), 10.f * itemHeight); SkRect dstRect = SkRect::MakeWH(SkIntToScalar(bmp.width()), 10.f * itemHeight);
canvas->drawImageRect(bmp.asImage(), SkRect::Make(subRect), dstRect, canvas->drawImageRect(ToolUtils::MakeTextureImage(canvas, bmp.asImage()),
SkRect::Make(subRect), dstRect,
SkSamplingOptions(SkFilterMode::kLinear), nullptr, SkSamplingOptions(SkFilterMode::kLinear), nullptr,
SkCanvas::kStrict_SrcRectConstraint); SkCanvas::kStrict_SrcRectConstraint);
canvas->translate(SkIntToScalar(bmp.width() + 10), 0); canvas->translate(SkIntToScalar(bmp.width() + 10), 0);

View File

@ -24,6 +24,7 @@
#include "include/core/SkSurface.h" #include "include/core/SkSurface.h"
#include "include/core/SkTileMode.h" #include "include/core/SkTileMode.h"
#include "include/effects/SkGradientShader.h" #include "include/effects/SkGradientShader.h"
#include "tools/ToolUtils.h"
static void draw(SkCanvas* canvas, int width, int height, SkColor colors[2]) { static void draw(SkCanvas* canvas, int width, int height, SkColor colors[2]) {
const SkPoint center = { SkIntToScalar(width)/2, SkIntToScalar(height)/2 }; const SkPoint center = { SkIntToScalar(width)/2, SkIntToScalar(height)/2 };
@ -54,7 +55,10 @@ typedef sk_sp<SkImage> (*ImageMakerProc)(int width, int height, SkColor colors[2
static void show_image(SkCanvas* canvas, int width, int height, SkColor colors[2], static void show_image(SkCanvas* canvas, int width, int height, SkColor colors[2],
ImageMakerProc proc) { ImageMakerProc proc) {
sk_sp<SkImage> image(proc(width, height, colors)); sk_sp<SkImage> image = ToolUtils::MakeTextureImage(canvas, proc(width, height, colors));
if (!image) {
return;
}
SkPaint borderPaint; SkPaint borderPaint;

View File

@ -395,12 +395,16 @@ generated_cc_atom(
"//include/core:SkShader_hdr", "//include/core:SkShader_hdr",
"//include/core:SkSurface_hdr", "//include/core:SkSurface_hdr",
"//include/core:SkTextBlob_hdr", "//include/core:SkTextBlob_hdr",
"//include/gpu:GrDirectContext_hdr",
"//include/gpu:GrRecordingContext_hdr",
"//include/ports:SkTypeface_win_hdr", "//include/ports:SkTypeface_win_hdr",
"//include/private:SkColorData_hdr", "//include/private:SkColorData_hdr",
"//include/private:SkFloatingPoint_hdr", "//include/private:SkFloatingPoint_hdr",
"//modules/svg/include:SkSVGDOM_hdr", "//modules/svg/include:SkSVGDOM_hdr",
"//modules/svg/include:SkSVGNode_hdr", "//modules/svg/include:SkSVGNode_hdr",
"//src/core:SkFontPriv_hdr", "//src/core:SkFontPriv_hdr",
"//src/gpu/ganesh:GrCaps_hdr",
"//src/gpu/ganesh:GrDirectContextPriv_hdr",
"//src/xml:SkDOM_hdr", "//src/xml:SkDOM_hdr",
], ],
) )

View File

@ -21,10 +21,14 @@
#include "include/core/SkShader.h" #include "include/core/SkShader.h"
#include "include/core/SkSurface.h" #include "include/core/SkSurface.h"
#include "include/core/SkTextBlob.h" #include "include/core/SkTextBlob.h"
#include "include/gpu/GrDirectContext.h"
#include "include/gpu/GrRecordingContext.h"
#include "include/ports/SkTypeface_win.h" #include "include/ports/SkTypeface_win.h"
#include "include/private/SkColorData.h" #include "include/private/SkColorData.h"
#include "include/private/SkFloatingPoint.h" #include "include/private/SkFloatingPoint.h"
#include "src/core/SkFontPriv.h" #include "src/core/SkFontPriv.h"
#include "src/gpu/ganesh/GrCaps.h"
#include "src/gpu/ganesh/GrDirectContextPriv.h"
#include "tools/ToolUtils.h" #include "tools/ToolUtils.h"
#include <cmath> #include <cmath>
@ -517,4 +521,31 @@ void sniff_paths(const char filepath[], std::function<PathSniffCallback> callbac
} }
} }
sk_sp<SkImage> MakeTextureImage(SkCanvas* canvas, sk_sp<SkImage> orig) {
if (!orig) {
return nullptr;
}
if (canvas->recordingContext() && canvas->recordingContext()->asDirectContext()) {
GrDirectContext* dContext = canvas->recordingContext()->asDirectContext();
const GrCaps* caps = dContext->priv().caps();
if (orig->width() >= caps->maxTextureSize() || orig->height() >= caps->maxTextureSize()) {
// Ganesh is able to tile large SkImage draws. Always forcing SkImages to be uploaded
// prevents this feature from being tested by our tools. For now, leave excessively
// large SkImages as bitmaps.
return orig;
}
return orig->makeTextureImage(dContext);
}
#if SK_GRAPHITE_ENABLED
else if (canvas->recorder()) {
return orig->makeTextureImage(canvas->recorder());
}
#endif
return orig;
}
} // namespace ToolUtils } // namespace ToolUtils

View File

@ -300,6 +300,8 @@ using PathSniffCallback = void(const SkMatrix&, const SkPath&, const SkPaint&);
// Supported file formats are .svg and .skp. // Supported file formats are .svg and .skp.
void sniff_paths(const char filepath[], std::function<PathSniffCallback>); void sniff_paths(const char filepath[], std::function<PathSniffCallback>);
sk_sp<SkImage> MakeTextureImage(SkCanvas* canvas, sk_sp<SkImage> orig);
} // namespace ToolUtils } // namespace ToolUtils
#endif // ToolUtils_DEFINED #endif // ToolUtils_DEFINED