Reland "Remove GrDeviceSpaceTextureDecalFragmentProcessor."
This is a reland of af5f9f008de060a91d8069c876a765f11c3d36f6
This was reverted due to Metal GMs failing. That is a bug in Metal where
pipeline creation fails with "internal error". Reporting to Apple, filing
Skia bug, and moving on.
Original change's description:
> Remove GrDeviceSpaceTextureDecalFragmentProcessor.
>
> It was used to sample clip masks using device coords.
>
> Replace with a more generic GrDeviceSpaceEffect that simply calls a
> child FP with sk_FragCoord.
>
> Also fix issue in GrQuadPerEdgeAA GP. It wouldn't setup coord transforms
> at all if they are all applied in the FS (explicit coords). Moreover,
> the GrGLSLGeometryProcessor::emitTransforms() helper required a valid VS
> var for local coords even when all FPs use explicit coords and wouldn't
> use a local coords var.
>
> Make CPP SkSL code gen for clone copy the explicit coord status of
> children.
>
> Change-Id: Ib8bb36028354405c8012f6e91e9eb46db75d16a6
> Reviewed-on: https://skia-review.googlesource.com/c/skia/+/271658
> Commit-Queue: Brian Salomon <bsalomon@google.com>
> Reviewed-by: Brian Osman <brianosman@google.com>
Change-Id: Ia4530e6799019cd92863fe983a2d3c71df6f0620
Reviewed-on: https://skia-review.googlesource.com/c/skia/+/273511
Commit-Queue: Brian Salomon <bsalomon@google.com>
Reviewed-by: Brian Salomon <bsalomon@google.com>
diff --git a/src/gpu/GrClipStackClip.cpp b/src/gpu/GrClipStackClip.cpp
index 2c5a941..66f2de8 100644
--- a/src/gpu/GrClipStackClip.cpp
+++ b/src/gpu/GrClipStackClip.cpp
@@ -5,12 +5,13 @@
* found in the LICENSE file.
*/
+#include "src/gpu/GrClipStackClip.h"
+
#include "include/private/SkTo.h"
#include "src/core/SkClipOpPriv.h"
#include "src/core/SkTaskGroup.h"
#include "src/core/SkTraceEvent.h"
#include "src/gpu/GrAppliedClip.h"
-#include "src/gpu/GrClipStackClip.h"
#include "src/gpu/GrContextPriv.h"
#include "src/gpu/GrDeferredProxyUploader.h"
#include "src/gpu/GrDrawingManager.h"
@@ -26,6 +27,7 @@
#include "src/gpu/effects/GrConvexPolyEffect.h"
#include "src/gpu/effects/GrRRectEffect.h"
#include "src/gpu/effects/GrTextureDomain.h"
+#include "src/gpu/effects/generated/GrDeviceSpaceEffect.h"
#include "src/gpu/geometry/GrShape.h"
typedef SkClipStack::Element Element;
@@ -78,11 +80,18 @@
////////////////////////////////////////////////////////////////////////////////
// set up the draw state to enable the aa clipping mask.
static std::unique_ptr<GrFragmentProcessor> create_fp_for_mask(GrSurfaceProxyView mask,
- const SkIRect& devBound) {
- SkASSERT(mask.asTextureProxy());
- SkIRect domainTexels = SkIRect::MakeWH(devBound.width(), devBound.height());
- return GrDeviceSpaceTextureDecalFragmentProcessor::Make(std::move(mask), domainTexels,
- {devBound.fLeft, devBound.fTop});
+ const SkIRect& devBound,
+ const GrCaps& caps) {
+ GrSamplerState samplerState(GrSamplerState::WrapMode::kClampToBorder,
+ GrSamplerState::Filter::kNearest);
+ auto m = SkMatrix::MakeTrans(-devBound.fLeft, -devBound.fTop);
+ auto subset = SkRect::Make(devBound.size());
+ // We scissor to devBounds. The mask's texel centers are aligned to device space
+ // pixel centers. Hence this domain of texture coordinates.
+ auto domain = subset.makeInset(0.5, 0.5);
+ auto fp = GrTextureEffect::MakeSubset(std::move(mask), kPremul_SkAlphaType, m, samplerState,
+ subset, domain, caps);
+ return GrDeviceSpaceEffect::Make(std::move(fp));
}
// Does the path in 'element' require SW rendering? If so, return true (and,
@@ -283,7 +292,8 @@
if (result) {
// The mask's top left coord should be pinned to the rounded-out top left corner of
// the clip's device space bounds.
- out->addCoverageFP(create_fp_for_mask(std::move(result), reducedClip.scissor()));
+ out->addCoverageFP(create_fp_for_mask(std::move(result), reducedClip.scissor(),
+ *context->priv().caps()));
return true;
}
diff --git a/src/gpu/GrProcessor.h b/src/gpu/GrProcessor.h
index 3274a14..4069344 100644
--- a/src/gpu/GrProcessor.h
+++ b/src/gpu/GrProcessor.h
@@ -101,7 +101,7 @@
kGrConicEffect_ClassID,
kGrConstColorProcessor_ClassID,
kGrConvexPolyEffect_ClassID,
- kGrDeviceSpaceTextureDecalFragmentProcessor_ClassID,
+ kGrDeviceSpaceEffect_ClassID,
kGrDiffuseLightingEffect_ClassID,
kGrDisplacementMapEffect_ClassID,
kGrDistanceFieldA8TextGeoProc_ClassID,
diff --git a/src/gpu/effects/GrDeviceSpaceEffect.fp b/src/gpu/effects/GrDeviceSpaceEffect.fp
new file mode 100644
index 0000000..d817ec2
--- /dev/null
+++ b/src/gpu/effects/GrDeviceSpaceEffect.fp
@@ -0,0 +1,22 @@
+/*
+* Copyright 2020 Google LLC
+*
+* Use of this source code is governed by a BSD-style license that can be
+* found in the LICENSE file.
+*/
+
+in fragmentProcessor fp;
+
+void main() {
+ sk_OutColor = sample(fp, sk_InColor, sk_FragCoord.xy);
+}
+
+@test(d) {
+ std::unique_ptr<GrFragmentProcessor> fp;
+ // We have a restriction that explicit coords only work for FPs with exactly one
+ // coord transform.
+ do {
+ fp = GrProcessorUnitTest::MakeChildFP(d);
+ } while (fp->numCoordTransforms() != 1);
+ return GrDeviceSpaceEffect::Make(std::move(fp));
+}
diff --git a/src/gpu/effects/GrTextureDomain.cpp b/src/gpu/effects/GrTextureDomain.cpp
index 59c3dfa..9d8202c 100644
--- a/src/gpu/effects/GrTextureDomain.cpp
+++ b/src/gpu/effects/GrTextureDomain.cpp
@@ -314,123 +314,3 @@
std::copy_n(decalFilterWeights, 3, fPrevDeclFilterWeights);
}
}
-
-///////////////////////////////////////////////////////////////////////////////
-
-std::unique_ptr<GrFragmentProcessor> GrDeviceSpaceTextureDecalFragmentProcessor::Make(
- GrSurfaceProxyView view, const SkIRect& subset, const SkIPoint& deviceSpaceOffset) {
- return std::unique_ptr<GrFragmentProcessor>(new GrDeviceSpaceTextureDecalFragmentProcessor(
- std::move(view), subset, deviceSpaceOffset));
-}
-
-GrDeviceSpaceTextureDecalFragmentProcessor::GrDeviceSpaceTextureDecalFragmentProcessor(
- GrSurfaceProxyView view, const SkIRect& subset, const SkIPoint& deviceSpaceOffset)
- : INHERITED(kGrDeviceSpaceTextureDecalFragmentProcessor_ClassID,
- kCompatibleWithCoverageAsAlpha_OptimizationFlag)
- , fTextureDomain(view.proxy(),
- GrTextureDomain::MakeTexelDomain(subset, GrTextureDomain::kDecal_Mode),
- GrTextureDomain::kDecal_Mode, GrTextureDomain::kDecal_Mode)
- , fTextureSampler(std::move(view), GrSamplerState::Filter::kNearest) {
- this->setTextureSamplerCnt(1);
- fDeviceSpaceOffset.fX = deviceSpaceOffset.fX - subset.fLeft;
- fDeviceSpaceOffset.fY = deviceSpaceOffset.fY - subset.fTop;
-}
-
-GrDeviceSpaceTextureDecalFragmentProcessor::GrDeviceSpaceTextureDecalFragmentProcessor(
- const GrDeviceSpaceTextureDecalFragmentProcessor& that)
- : INHERITED(kGrDeviceSpaceTextureDecalFragmentProcessor_ClassID,
- kCompatibleWithCoverageAsAlpha_OptimizationFlag)
- , fTextureDomain(that.fTextureDomain)
- , fTextureSampler(that.fTextureSampler)
- , fDeviceSpaceOffset(that.fDeviceSpaceOffset) {
- this->setTextureSamplerCnt(1);
-}
-
-std::unique_ptr<GrFragmentProcessor> GrDeviceSpaceTextureDecalFragmentProcessor::clone() const {
- return std::unique_ptr<GrFragmentProcessor>(
- new GrDeviceSpaceTextureDecalFragmentProcessor(*this));
-}
-
-GrGLSLFragmentProcessor* GrDeviceSpaceTextureDecalFragmentProcessor::onCreateGLSLInstance() const {
- class GLSLProcessor : public GrGLSLFragmentProcessor {
- public:
- void emitCode(EmitArgs& args) override {
- const GrDeviceSpaceTextureDecalFragmentProcessor& dstdfp =
- args.fFp.cast<GrDeviceSpaceTextureDecalFragmentProcessor>();
- const char* scaleAndTranslateName;
- fScaleAndTranslateUni = args.fUniformHandler->addUniform(kFragment_GrShaderFlag,
- kHalf4_GrSLType,
- "scaleAndTranslate",
- &scaleAndTranslateName);
- args.fFragBuilder->codeAppendf("half2 coords = half2(sk_FragCoord.xy * %s.xy + %s.zw);",
- scaleAndTranslateName, scaleAndTranslateName);
- fGLDomain.sampleTexture(args.fFragBuilder,
- args.fUniformHandler,
- args.fShaderCaps,
- dstdfp.fTextureDomain,
- args.fOutputColor,
- SkString("coords"),
- args.fTexSamplers[0],
- args.fInputColor);
- }
-
- protected:
- void onSetData(const GrGLSLProgramDataManager& pdman,
- const GrFragmentProcessor& fp) override {
- const GrDeviceSpaceTextureDecalFragmentProcessor& dstdfp =
- fp.cast<GrDeviceSpaceTextureDecalFragmentProcessor>();
- const auto& view = dstdfp.textureSampler(0).view();
- SkISize textureDims = view.proxy()->backingStoreDimensions();
-
- fGLDomain.setData(pdman, dstdfp.fTextureDomain, view,
- dstdfp.textureSampler(0).samplerState());
- float iw = 1.f / textureDims.width();
- float ih = 1.f / textureDims.height();
- float scaleAndTransData[4] = {
- iw, ih,
- -dstdfp.fDeviceSpaceOffset.fX * iw, -dstdfp.fDeviceSpaceOffset.fY * ih
- };
- if (view.origin() == kBottomLeft_GrSurfaceOrigin) {
- scaleAndTransData[1] = -scaleAndTransData[1];
- scaleAndTransData[3] = 1 - scaleAndTransData[3];
- }
- pdman.set4fv(fScaleAndTranslateUni, 1, scaleAndTransData);
- }
-
- private:
- GrTextureDomain::GLDomain fGLDomain;
- UniformHandle fScaleAndTranslateUni;
- };
-
- return new GLSLProcessor;
-}
-
-bool GrDeviceSpaceTextureDecalFragmentProcessor::onIsEqual(const GrFragmentProcessor& fp) const {
- const GrDeviceSpaceTextureDecalFragmentProcessor& dstdfp =
- fp.cast<GrDeviceSpaceTextureDecalFragmentProcessor>();
- return dstdfp.fTextureSampler.view().proxy()->underlyingUniqueID() ==
- fTextureSampler.view().proxy()->underlyingUniqueID() &&
- dstdfp.fDeviceSpaceOffset == fDeviceSpaceOffset &&
- dstdfp.fTextureDomain == fTextureDomain;
-}
-
-///////////////////////////////////////////////////////////////////////////////
-
-GR_DEFINE_FRAGMENT_PROCESSOR_TEST(GrDeviceSpaceTextureDecalFragmentProcessor);
-
-#if GR_TEST_UTILS
-std::unique_ptr<GrFragmentProcessor> GrDeviceSpaceTextureDecalFragmentProcessor::TestCreate(
- GrProcessorTestData* d) {
- auto [view, at, ct] = d->randomView();
- SkIRect subset;
- subset.fLeft = d->fRandom->nextULessThan(view.width() - 1);
- subset.fRight = d->fRandom->nextRangeU(subset.fLeft, view.width());
- subset.fTop = d->fRandom->nextULessThan(view.height() - 1);
- subset.fBottom = d->fRandom->nextRangeU(subset.fTop, view.height());
- SkIPoint pt;
- pt.fX = d->fRandom->nextULessThan(2048);
- pt.fY = d->fRandom->nextULessThan(2048);
-
- return GrDeviceSpaceTextureDecalFragmentProcessor::Make(std::move(view), subset, pt);
-}
-#endif
diff --git a/src/gpu/effects/GrTextureDomain.h b/src/gpu/effects/GrTextureDomain.h
index c9a563a..e88c4c2 100644
--- a/src/gpu/effects/GrTextureDomain.h
+++ b/src/gpu/effects/GrTextureDomain.h
@@ -231,47 +231,4 @@
int fIndex;
};
-class GrDeviceSpaceTextureDecalFragmentProcessor : public GrFragmentProcessor {
-public:
- static std::unique_ptr<GrFragmentProcessor> Make(GrSurfaceProxyView,
- const SkIRect& subset,
- const SkIPoint& deviceSpaceOffset);
-
- const char* name() const override { return "GrDeviceSpaceTextureDecalFragmentProcessor"; }
-
-#ifdef SK_DEBUG
- SkString dumpInfo() const override {
- SkString str;
- str.appendf("Domain: [L: %.2f, T: %.2f, R: %.2f, B: %.2f] Offset: [%d %d]",
- fTextureDomain.domain().fLeft, fTextureDomain.domain().fTop,
- fTextureDomain.domain().fRight, fTextureDomain.domain().fBottom,
- fDeviceSpaceOffset.fX, fDeviceSpaceOffset.fY);
- str.append(INHERITED::dumpInfo());
- return str;
- }
-#endif
-
- std::unique_ptr<GrFragmentProcessor> clone() const override;
-
-private:
- GrTextureDomain fTextureDomain;
- TextureSampler fTextureSampler;
- SkIPoint fDeviceSpaceOffset;
-
- GrDeviceSpaceTextureDecalFragmentProcessor(GrSurfaceProxyView, const SkIRect&, const SkIPoint&);
- GrDeviceSpaceTextureDecalFragmentProcessor(const GrDeviceSpaceTextureDecalFragmentProcessor&);
-
- GrGLSLFragmentProcessor* onCreateGLSLInstance() const override;
-
- // Since we always use decal mode, there is no need for key data.
- void onGetGLSLProcessorKey(const GrShaderCaps&, GrProcessorKeyBuilder*) const override {}
-
- bool onIsEqual(const GrFragmentProcessor& fp) const override;
-
- const TextureSampler& onTextureSampler(int) const override { return fTextureSampler; }
-
- GR_DECLARE_FRAGMENT_PROCESSOR_TEST
-
- typedef GrFragmentProcessor INHERITED;
-};
#endif
diff --git a/src/gpu/effects/generated/GrDeviceSpaceEffect.cpp b/src/gpu/effects/generated/GrDeviceSpaceEffect.cpp
new file mode 100644
index 0000000..8df3a1b
--- /dev/null
+++ b/src/gpu/effects/generated/GrDeviceSpaceEffect.cpp
@@ -0,0 +1,71 @@
+/*
+ * Copyright 2020 Google LLC
+ *
+ * Use of this source code is governed by a BSD-style license that can be
+ * found in the LICENSE file.
+ */
+
+/**************************************************************************************************
+ *** This file was autogenerated from GrDeviceSpaceEffect.fp; do not modify.
+ **************************************************************************************************/
+#include "GrDeviceSpaceEffect.h"
+
+#include "include/gpu/GrTexture.h"
+#include "src/gpu/glsl/GrGLSLFragmentProcessor.h"
+#include "src/gpu/glsl/GrGLSLFragmentShaderBuilder.h"
+#include "src/gpu/glsl/GrGLSLProgramBuilder.h"
+#include "src/sksl/SkSLCPP.h"
+#include "src/sksl/SkSLUtil.h"
+class GrGLSLDeviceSpaceEffect : public GrGLSLFragmentProcessor {
+public:
+ GrGLSLDeviceSpaceEffect() {}
+ void emitCode(EmitArgs& args) override {
+ GrGLSLFPFragmentBuilder* fragBuilder = args.fFragBuilder;
+ const GrDeviceSpaceEffect& _outer = args.fFp.cast<GrDeviceSpaceEffect>();
+ (void)_outer;
+ SkString _input204 = SkStringPrintf("%s", args.fInputColor);
+ SkString _sample204;
+ SkString _coords204("sk_FragCoord.xy");
+ _sample204 =
+ this->invokeChild(_outer.fp_index, _input204.c_str(), args, _coords204.c_str());
+ fragBuilder->codeAppendf("%s = %s;\n", args.fOutputColor, _sample204.c_str());
+ }
+
+private:
+ void onSetData(const GrGLSLProgramDataManager& pdman,
+ const GrFragmentProcessor& _proc) override {}
+};
+GrGLSLFragmentProcessor* GrDeviceSpaceEffect::onCreateGLSLInstance() const {
+ return new GrGLSLDeviceSpaceEffect();
+}
+void GrDeviceSpaceEffect::onGetGLSLProcessorKey(const GrShaderCaps& caps,
+ GrProcessorKeyBuilder* b) const {}
+bool GrDeviceSpaceEffect::onIsEqual(const GrFragmentProcessor& other) const {
+ const GrDeviceSpaceEffect& that = other.cast<GrDeviceSpaceEffect>();
+ (void)that;
+ return true;
+}
+GrDeviceSpaceEffect::GrDeviceSpaceEffect(const GrDeviceSpaceEffect& src)
+ : INHERITED(kGrDeviceSpaceEffect_ClassID, src.optimizationFlags()), fp_index(src.fp_index) {
+ {
+ auto clone = src.childProcessor(fp_index).clone();
+ clone->setSampledWithExplicitCoords(
+ src.childProcessor(fp_index).isSampledWithExplicitCoords());
+ this->registerChildProcessor(std::move(clone));
+ }
+}
+std::unique_ptr<GrFragmentProcessor> GrDeviceSpaceEffect::clone() const {
+ return std::unique_ptr<GrFragmentProcessor>(new GrDeviceSpaceEffect(*this));
+}
+GR_DEFINE_FRAGMENT_PROCESSOR_TEST(GrDeviceSpaceEffect);
+#if GR_TEST_UTILS
+std::unique_ptr<GrFragmentProcessor> GrDeviceSpaceEffect::TestCreate(GrProcessorTestData* d) {
+ std::unique_ptr<GrFragmentProcessor> fp;
+ // We have a restriction that explicit coords only work for FPs with exactly one
+ // coord transform.
+ do {
+ fp = GrProcessorUnitTest::MakeChildFP(d);
+ } while (fp->numCoordTransforms() != 1);
+ return GrDeviceSpaceEffect::Make(std::move(fp));
+}
+#endif
diff --git a/src/gpu/effects/generated/GrDeviceSpaceEffect.h b/src/gpu/effects/generated/GrDeviceSpaceEffect.h
new file mode 100644
index 0000000..d0e9253
--- /dev/null
+++ b/src/gpu/effects/generated/GrDeviceSpaceEffect.h
@@ -0,0 +1,42 @@
+/*
+ * Copyright 2020 Google LLC
+ *
+ * Use of this source code is governed by a BSD-style license that can be
+ * found in the LICENSE file.
+ */
+
+/**************************************************************************************************
+ *** This file was autogenerated from GrDeviceSpaceEffect.fp; do not modify.
+ **************************************************************************************************/
+#ifndef GrDeviceSpaceEffect_DEFINED
+#define GrDeviceSpaceEffect_DEFINED
+#include "include/core/SkTypes.h"
+#include "include/core/SkM44.h"
+
+#include "src/gpu/GrCoordTransform.h"
+#include "src/gpu/GrFragmentProcessor.h"
+class GrDeviceSpaceEffect : public GrFragmentProcessor {
+public:
+ static std::unique_ptr<GrFragmentProcessor> Make(std::unique_ptr<GrFragmentProcessor> fp) {
+ return std::unique_ptr<GrFragmentProcessor>(new GrDeviceSpaceEffect(std::move(fp)));
+ }
+ GrDeviceSpaceEffect(const GrDeviceSpaceEffect& src);
+ std::unique_ptr<GrFragmentProcessor> clone() const override;
+ const char* name() const override { return "DeviceSpaceEffect"; }
+ int fp_index = -1;
+
+private:
+ GrDeviceSpaceEffect(std::unique_ptr<GrFragmentProcessor> fp)
+ : INHERITED(kGrDeviceSpaceEffect_ClassID, kNone_OptimizationFlags) {
+ SkASSERT(fp);
+ fp_index = this->numChildProcessors();
+ fp->setSampledWithExplicitCoords(true);
+ this->registerChildProcessor(std::move(fp));
+ }
+ GrGLSLFragmentProcessor* onCreateGLSLInstance() const override;
+ void onGetGLSLProcessorKey(const GrShaderCaps&, GrProcessorKeyBuilder*) const override;
+ bool onIsEqual(const GrFragmentProcessor&) const override;
+ GR_DECLARE_FRAGMENT_PROCESSOR_TEST
+ typedef GrFragmentProcessor INHERITED;
+};
+#endif