skia2/gm/texturedomaineffect.cpp
Robert Phillips e98234f231 Start making texture coordinates be absolute
The idea here is that we will pass GrTextureProxys in (where we're currently passing GrTextures) and defer the normalization until the texture is actually instantiated (and possibly move it to the GPU entirely)

This CL does (intentionally) change the texturedomaineffect GM but I believe the new behavior is more correct.

Change-Id: I4e0510b3dfb65ff0d0ee5921f9a6f94151e602d3
Reviewed-on: https://skia-review.googlesource.com/6807
Commit-Queue: Robert Phillips <robertphillips@google.com>
Reviewed-by: Brian Salomon <bsalomon@google.com>
2017-01-10 16:15:02 +00:00

154 lines
5.6 KiB
C++

/*
* Copyright 2014 Google Inc.
*
* Use of this source code is governed by a BSD-style license that can be
* found in the LICENSE file.
*/
// This test only works with the GPU backend.
#include "gm.h"
#if SK_SUPPORT_GPU
#include "GrContext.h"
#include "GrRenderTargetContextPriv.h"
#include "SkBitmap.h"
#include "SkGr.h"
#include "SkGradientShader.h"
#include "effects/GrTextureDomain.h"
#include "ops/GrDrawOp.h"
#include "ops/GrRectOpFactory.h"
namespace skiagm {
/**
* This GM directly exercises GrTextureDomainEffect.
*/
class TextureDomainEffect : public GM {
public:
TextureDomainEffect() {
this->setBGColor(0xFFFFFFFF);
}
protected:
SkString onShortName() override {
return SkString("texture_domain_effect");
}
SkISize onISize() override {
const SkScalar canvasWidth = kDrawPad +
(kTargetWidth + 2 * kDrawPad) * GrTextureDomain::kModeCount +
kTestPad * GrTextureDomain::kModeCount;
return SkISize::Make(SkScalarCeilToInt(canvasWidth), 800);
}
void onOnceBeforeDraw() override {
fBmp.allocN32Pixels(kTargetWidth, kTargetHeight);
SkCanvas canvas(fBmp);
canvas.clear(0x00000000);
SkPaint paint;
SkColor colors1[] = { SK_ColorCYAN, SK_ColorLTGRAY, SK_ColorGRAY };
paint.setShader(SkGradientShader::MakeSweep(65.f, 75.f, colors1, nullptr,
SK_ARRAY_COUNT(colors1)));
canvas.drawOval(SkRect::MakeXYWH(-5.f, -5.f, fBmp.width() + 10.f, fBmp.height() + 10.f),
paint);
SkColor colors2[] = { SK_ColorMAGENTA, SK_ColorLTGRAY, SK_ColorYELLOW };
paint.setShader(SkGradientShader::MakeSweep(45.f, 55.f, colors2, nullptr,
SK_ARRAY_COUNT(colors2)));
paint.setBlendMode(SkBlendMode::kDarken);
canvas.drawOval(SkRect::MakeXYWH(-5.f, -5.f, fBmp.width() + 10.f, fBmp.height() + 10.f),
paint);
SkColor colors3[] = { SK_ColorBLUE, SK_ColorLTGRAY, SK_ColorGREEN };
paint.setShader(SkGradientShader::MakeSweep(25.f, 35.f, colors3, nullptr,
SK_ARRAY_COUNT(colors3)));
paint.setBlendMode(SkBlendMode::kLighten);
canvas.drawOval(SkRect::MakeXYWH(-5.f, -5.f, fBmp.width() + 10.f, fBmp.height() + 10.f),
paint);
}
void onDraw(SkCanvas* canvas) override {
GrRenderTargetContext* renderTargetContext =
canvas->internal_private_accessTopLayerRenderTargetContext();
if (!renderTargetContext) {
skiagm::GM::DrawGpuOnlyMessage(canvas);
return;
}
GrContext* context = canvas->getGrContext();
if (!context) {
return;
}
sk_sp<GrTexture> texture(
GrRefCachedBitmapTexture(context, fBmp, GrSamplerParams::ClampNoFilter()));
if (!texture) {
return;
}
SkTArray<SkMatrix> textureMatrices;
textureMatrices.push_back().setIDiv(texture->width(), texture->height());
textureMatrices.push_back() = textureMatrices[0];
textureMatrices.back().postScale(1.5f, 0.85f);
textureMatrices.push_back() = textureMatrices[0];
textureMatrices.back().preRotate(45.f, texture->width() / 2.f, texture->height() / 2.f);
const SkIRect texelDomains[] = {
fBmp.bounds(),
SkIRect::MakeXYWH(fBmp.width() / 4,
fBmp.height() / 4,
fBmp.width() / 2,
fBmp.height() / 2),
};
SkRect renderRect = SkRect::Make(fBmp.bounds());
renderRect.outset(kDrawPad, kDrawPad);
SkScalar y = kDrawPad + kTestPad;
for (int tm = 0; tm < textureMatrices.count(); ++tm) {
for (size_t d = 0; d < SK_ARRAY_COUNT(texelDomains); ++d) {
SkScalar x = kDrawPad + kTestPad;
for (int m = 0; m < GrTextureDomain::kModeCount; ++m) {
GrTextureDomain::Mode mode = (GrTextureDomain::Mode) m;
GrPaint grPaint;
grPaint.setXPFactory(GrPorterDuffXPFactory::Get(SkBlendMode::kSrc));
sk_sp<GrFragmentProcessor> fp(
GrTextureDomainEffect::Make(
texture.get(), nullptr, textureMatrices[tm],
GrTextureDomain::MakeTexelDomainForMode(texelDomains[d], mode),
mode, GrSamplerParams::kNone_FilterMode));
if (!fp) {
continue;
}
const SkMatrix viewMatrix = SkMatrix::MakeTrans(x, y);
grPaint.addColorFragmentProcessor(std::move(fp));
std::unique_ptr<GrDrawOp> op(GrRectOpFactory::MakeNonAAFill(
GrColor_WHITE, viewMatrix, renderRect, nullptr, nullptr));
renderTargetContext->priv().testingOnly_addDrawOp(grPaint, GrAAType::kNone,
std::move(op));
x += renderRect.width() + kTestPad;
}
y += renderRect.height() + kTestPad;
}
}
}
private:
static constexpr SkScalar kDrawPad = 10.f;
static constexpr SkScalar kTestPad = 10.f;;
static constexpr int kTargetWidth = 100;
static constexpr int kTargetHeight = 100;
SkBitmap fBmp;
typedef GM INHERITED;
};
DEF_GM(return new TextureDomainEffect;)
}
#endif