aboutsummaryrefslogtreecommitdiffhomepage
path: root/src/gpu
diff options
context:
space:
mode:
Diffstat (limited to 'src/gpu')
-rw-r--r--src/gpu/GrPaint.cpp13
-rw-r--r--src/gpu/GrPipeline.cpp12
-rw-r--r--src/gpu/GrPrimitiveProcessor.h14
-rw-r--r--src/gpu/GrXferProcessor.cpp26
-rw-r--r--src/gpu/effects/GrCoverageSetOpXP.cpp6
-rw-r--r--src/gpu/effects/GrCustomXfermode.cpp22
-rw-r--r--src/gpu/effects/GrDisableColorXP.h17
-rw-r--r--src/gpu/effects/GrPorterDuffXferProcessor.cpp65
-rw-r--r--src/gpu/ops/GrDrawPathOp.cpp5
-rw-r--r--src/gpu/ops/GrDrawPathOp.h6
10 files changed, 83 insertions, 103 deletions
diff --git a/src/gpu/GrPaint.cpp b/src/gpu/GrPaint.cpp
index 19bfef3360..26dbf3d2df 100644
--- a/src/gpu/GrPaint.cpp
+++ b/src/gpu/GrPaint.cpp
@@ -81,16 +81,5 @@ bool GrPaint::internalIsConstantBlendedColor(GrColor paintColor, GrColor* color)
sk_sp_address_as_pointer_address(fColorFragmentProcessors.begin()),
this->numColorFragmentProcessors());
- GrXPFactory::InvariantBlendedColor blendedColor;
- if (fXPFactory) {
- fXPFactory->getInvariantBlendedColor(colorProcInfo, &blendedColor);
- } else {
- GrPorterDuffXPFactory::SrcOverInvariantBlendedColor(colorProcInfo, &blendedColor);
- }
-
- if (kRGBA_GrColorComponentFlags == blendedColor.fKnownColorFlags) {
- *color = blendedColor.fKnownColor;
- return true;
- }
- return false;
+ return GrXPFactory::IsPreCoverageBlendedColorConstant(fXPFactory, colorProcInfo, color);
}
diff --git a/src/gpu/GrPipeline.cpp b/src/gpu/GrPipeline.cpp
index 94f11e93ac..e2b76f8ab4 100644
--- a/src/gpu/GrPipeline.cpp
+++ b/src/gpu/GrPipeline.cpp
@@ -144,15 +144,9 @@ GrPipeline* GrPipeline::CreateAt(void* memory, const CreateArgs& args,
optimizations->fFlags |= GrPipelineOptimizations::kCanTweakAlphaForCoverage_Flag;
}
- GrXPFactory::InvariantBlendedColor blendedColor;
- if (xpFactory) {
- xpFactory->getInvariantBlendedColor(args.fAnalysis.fColorPOI, &blendedColor);
- } else {
- GrPorterDuffXPFactory::SrcOverInvariantBlendedColor(args.fAnalysis.fColorPOI,
- &blendedColor);
- }
- if (blendedColor.fWillBlendWithDst) {
- optimizations->fFlags |= GrPipelineOptimizations::kWillColorBlendWithDst_Flag;
+ if (GrXPFactory::WillReadDst(xpFactory, args.fAnalysis.fColorPOI,
+ args.fAnalysis.fCoveragePOI)) {
+ optimizations->fFlags |= GrPipelineOptimizations::kXPReadsDst_Flag;
}
return pipeline;
diff --git a/src/gpu/GrPrimitiveProcessor.h b/src/gpu/GrPrimitiveProcessor.h
index 9f726d242b..47564d9862 100644
--- a/src/gpu/GrPrimitiveProcessor.h
+++ b/src/gpu/GrPrimitiveProcessor.h
@@ -80,17 +80,9 @@ public:
}
/**
- * Returns true if the pipeline's color output will be affected by the existing render target
- * destination pixel values (meaning we need to be careful with overlapping draws). Note that we
- * can conflate coverage and color, so the destination color may still bleed into pixels that
- * have partial coverage, even if this function returns false.
- *
- * The above comment seems incorrect for the use case. This function is used to turn two
- * overlapping draws into a single draw (really to stencil multiple paths and do a single
- * cover). It seems that what really matters is whether the dst is read for color OR for
- * coverage.
+ * Returns true if the color written to the output pixel depends on the pixels previous value.
*/
- bool willColorBlendWithDst() const { return SkToBool(kWillColorBlendWithDst_Flag & fFlags); }
+ bool xpReadsDst() const { return SkToBool(kXPReadsDst_Flag & fFlags); }
private:
enum {
@@ -105,7 +97,7 @@ private:
// output color. If not set fOverrideColor is to be ignored.
kUseOverrideColor_Flag = 0x4,
- kWillColorBlendWithDst_Flag = 0x8,
+ kXPReadsDst_Flag = 0x8,
};
uint32_t fFlags;
diff --git a/src/gpu/GrXferProcessor.cpp b/src/gpu/GrXferProcessor.cpp
index bc90f99ec7..e6a1817aba 100644
--- a/src/gpu/GrXferProcessor.cpp
+++ b/src/gpu/GrXferProcessor.cpp
@@ -203,13 +203,31 @@ CoverageType analysis_coverage_type(const GrPipelineAnalysis& analysis) {
return CoverageType::kSingleChannel;
}
-bool GrXPFactory::willReadDstColor(const GrCaps& caps, const GrPipelineAnalysis& analysis) const {
+bool GrXPFactory::WillReadDst(const GrXPFactory* factory, const GrProcOptInfo& colorInput,
+ const GrProcOptInfo& coverageInput) {
+ if (factory) {
+ return factory->willReadsDst(colorInput, coverageInput);
+ }
+ return GrPorterDuffXPFactory::WillSrcOverReadDst(colorInput, coverageInput);
+}
+
+bool GrXPFactory::IsPreCoverageBlendedColorConstant(const GrXPFactory* factory,
+ const GrProcOptInfo& colorInput,
+ GrColor* color) {
+ if (factory) {
+ return factory->isPreCoverageBlendedColorConstant(colorInput, color);
+ }
+ return GrPorterDuffXPFactory::IsSrcOverPreCoverageBlendedColorConstant(colorInput, color);
+}
+
+bool GrXPFactory::willReadDstInShader(const GrCaps& caps,
+ const GrPipelineAnalysis& analysis) const {
if (analysis.fUsesPLSDstRead) {
return true;
}
ColorType colorType = analysis_color_type(analysis);
CoverageType coverageType = analysis_coverage_type(analysis);
- return this->willReadDstColor(caps, colorType, coverageType);
+ return this->willReadDstInShader(caps, colorType, coverageType);
}
GrXferProcessor* GrXPFactory::createXferProcessor(const GrPipelineAnalysis& analysis,
@@ -217,7 +235,7 @@ GrXferProcessor* GrXPFactory::createXferProcessor(const GrPipelineAnalysis& anal
const DstTexture* dstTexture,
const GrCaps& caps) const {
#ifdef SK_DEBUG
- if (this->willReadDstColor(caps, analysis)) {
+ if (this->willReadDstInShader(caps, analysis)) {
if (!caps.shaderCaps()->dstReadInShaderSupport()) {
SkASSERT(dstTexture && dstTexture->texture());
} else {
@@ -233,5 +251,5 @@ GrXferProcessor* GrXPFactory::createXferProcessor(const GrPipelineAnalysis& anal
bool GrXPFactory::willNeedDstTexture(const GrCaps& caps, const GrPipelineAnalysis& analysis) const {
return !analysis.fUsesPLSDstRead && !caps.shaderCaps()->dstReadInShaderSupport() &&
- this->willReadDstColor(caps, analysis);
+ this->willReadDstInShader(caps, analysis);
}
diff --git a/src/gpu/effects/GrCoverageSetOpXP.cpp b/src/gpu/effects/GrCoverageSetOpXP.cpp
index b8902de58c..9cf994f07a 100644
--- a/src/gpu/effects/GrCoverageSetOpXP.cpp
+++ b/src/gpu/effects/GrCoverageSetOpXP.cpp
@@ -339,12 +339,6 @@ GrXferProcessor* GrCoverageSetOpXPFactory::onCreateXferProcessor(const GrCaps& c
return CoverageSetOpXP::Create(fRegionOp, fInvertCoverage);
}
-void GrCoverageSetOpXPFactory::getInvariantBlendedColor(const GrProcOptInfo& colorPOI,
- InvariantBlendedColor* blendedColor) const {
- blendedColor->fWillBlendWithDst = SkRegion::kReplace_Op != fRegionOp;
- blendedColor->fKnownColorFlags = kNone_GrColorComponentFlags;
-}
-
GR_DEFINE_XP_FACTORY_TEST(GrCoverageSetOpXPFactory);
#if GR_TEST_UTILS
diff --git a/src/gpu/effects/GrCustomXfermode.cpp b/src/gpu/effects/GrCustomXfermode.cpp
index 4a4cb60b4e..bc11d7e533 100644
--- a/src/gpu/effects/GrCustomXfermode.cpp
+++ b/src/gpu/effects/GrCustomXfermode.cpp
@@ -331,16 +331,20 @@ public:
constexpr CustomXPFactory(SkBlendMode mode)
: fMode(mode), fHWBlendEquation(hw_blend_equation(mode)) {}
- void getInvariantBlendedColor(const GrProcOptInfo& colorPOI,
- GrXPFactory::InvariantBlendedColor*) const override;
-
private:
GrXferProcessor* onCreateXferProcessor(const GrCaps& caps,
const GrPipelineAnalysis&,
bool hasMixedSamples,
const DstTexture*) const override;
- bool willReadDstColor(const GrCaps&, ColorType, CoverageType) const override;
+ bool isPreCoverageBlendedColorConstant(const GrProcOptInfo& colorInput,
+ GrColor* color) const override {
+ return false;
+ }
+
+ bool willReadsDst(const GrProcOptInfo&, const GrProcOptInfo&) const override { return true; }
+
+ bool willReadDstInShader(const GrCaps&, ColorType, CoverageType) const override;
GR_DECLARE_XP_FACTORY_TEST;
@@ -366,20 +370,14 @@ GrXferProcessor* CustomXPFactory::onCreateXferProcessor(const GrCaps& caps,
return new CustomXP(dstTexture, hasMixedSamples, fMode);
}
-bool CustomXPFactory::willReadDstColor(const GrCaps& caps, ColorType colorType,
- CoverageType coverageType) const {
+bool CustomXPFactory::willReadDstInShader(const GrCaps& caps, ColorType colorType,
+ CoverageType coverageType) const {
// This should not be called if we're using PLS dst read.
static constexpr bool kUsesPLSRead = false;
return !can_use_hw_blend_equation(fHWBlendEquation, kUsesPLSRead,
CoverageType::kLCD == coverageType, caps);
}
-void CustomXPFactory::getInvariantBlendedColor(const GrProcOptInfo& colorPOI,
- InvariantBlendedColor* blendedColor) const {
- blendedColor->fWillBlendWithDst = true;
- blendedColor->fKnownColorFlags = kNone_GrColorComponentFlags;
-}
-
GR_DEFINE_XP_FACTORY_TEST(CustomXPFactory);
#if GR_TEST_UTILS
const GrXPFactory* CustomXPFactory::TestGet(GrProcessorTestData* d) {
diff --git a/src/gpu/effects/GrDisableColorXP.h b/src/gpu/effects/GrDisableColorXP.h
index f027e3c3bb..e98e71e069 100644
--- a/src/gpu/effects/GrDisableColorXP.h
+++ b/src/gpu/effects/GrDisableColorXP.h
@@ -23,16 +23,21 @@ class GrDisableColorXPFactory : public GrXPFactory {
public:
static const GrXPFactory* Get();
- void getInvariantBlendedColor(const GrProcOptInfo& colorPOI,
- GrXPFactory::InvariantBlendedColor* blendedColor) const override {
- blendedColor->fKnownColorFlags = kNone_GrColorComponentFlags;
- blendedColor->fWillBlendWithDst = false;
+private:
+ bool isPreCoverageBlendedColorConstant(const GrProcOptInfo&, GrColor*) const override {
+ return false;
+ }
+
+ bool willReadsDst(const GrProcOptInfo& colorInput,
+ const GrProcOptInfo& coverageInput) const override {
+ return false;
}
-private:
constexpr GrDisableColorXPFactory() {}
- bool willReadDstColor(const GrCaps&, ColorType, CoverageType) const override { return false; }
+ bool willReadDstInShader(const GrCaps&, ColorType, CoverageType) const override {
+ return false;
+ }
GrXferProcessor* onCreateXferProcessor(const GrCaps& caps,
const GrPipelineAnalysis&,
diff --git a/src/gpu/effects/GrPorterDuffXferProcessor.cpp b/src/gpu/effects/GrPorterDuffXferProcessor.cpp
index 5f44c7a108..a04bb5b512 100644
--- a/src/gpu/effects/GrPorterDuffXferProcessor.cpp
+++ b/src/gpu/effects/GrPorterDuffXferProcessor.cpp
@@ -764,40 +764,33 @@ GrXferProcessor* GrPorterDuffXPFactory::onCreateXferProcessor(const GrCaps& caps
SkASSERT(!dstTexture || !dstTexture->texture());
return new PorterDuffXferProcessor(blendFormula);
}
-
-void GrPorterDuffXPFactory::getInvariantBlendedColor(const GrProcOptInfo& colorPOI,
- InvariantBlendedColor* blendedColor) const {
- // Find the blended color info based on the formula that does not have coverage.
- BlendFormula colorFormula = gBlendTable[colorPOI.isOpaque()][0][(int)fBlendMode];
+bool GrPorterDuffXPFactory::isPreCoverageBlendedColorConstant(const GrProcOptInfo& colorInput,
+ GrColor* color) const {
+ BlendFormula colorFormula = gBlendTable[colorInput.isOpaque()][0][(int)fBlendMode];
+ SkASSERT(kAdd_GrBlendEquation == colorFormula.fBlendEquation);
if (colorFormula.usesDstColor()) {
- blendedColor->fWillBlendWithDst = true;
- blendedColor->fKnownColorFlags = kNone_GrColorComponentFlags;
- return;
+ return false;
}
-
- blendedColor->fWillBlendWithDst = false;
-
- SkASSERT(kAdd_GrBlendEquation == colorFormula.fBlendEquation);
-
switch (colorFormula.fSrcCoeff) {
case kZero_GrBlendCoeff:
- blendedColor->fKnownColor = 0;
- blendedColor->fKnownColorFlags = kRGBA_GrColorComponentFlags;
- return;
+ *color = GrColor_TRANSPARENT_BLACK;
+ return true;
case kOne_GrBlendCoeff:
- blendedColor->fKnownColorFlags =
- colorPOI.hasKnownOutputColor(&blendedColor->fKnownColor)
- ? kRGBA_GrColorComponentFlags
- : kNone_GrColorComponentFlags;
- return;
+ return colorInput.hasKnownOutputColor(color);
default:
- blendedColor->fKnownColorFlags = kNone_GrColorComponentFlags;
- return;
+ return false;
}
}
-bool GrPorterDuffXPFactory::willReadDstColor(const GrCaps& caps, ColorType colorType,
- CoverageType coverageType) const {
+bool GrPorterDuffXPFactory::willReadsDst(const GrProcOptInfo& colorInput,
+ const GrProcOptInfo& coverageInput) const {
+ BlendFormula colorFormula = gBlendTable[colorInput.isOpaque()][0][(int)fBlendMode];
+ SkASSERT(kAdd_GrBlendEquation == colorFormula.fBlendEquation);
+ return (colorFormula.usesDstColor() || !coverageInput.isSolidWhite());
+}
+
+bool GrPorterDuffXPFactory::willReadDstInShader(const GrCaps& caps, ColorType colorType,
+ CoverageType coverageType) const {
if (caps.shaderCaps()->dualSourceBlendingSupport()) {
return false;
}
@@ -900,19 +893,17 @@ sk_sp<GrXferProcessor> GrPorterDuffXPFactory::CreateNoCoverageXP(SkBlendMode ble
return sk_make_sp<PorterDuffXferProcessor>(formula);
}
-void GrPorterDuffXPFactory::SrcOverInvariantBlendedColor(
- const GrProcOptInfo& colorPOI, GrXPFactory::InvariantBlendedColor* blendedColor) {
- if (!colorPOI.isOpaque()) {
- blendedColor->fWillBlendWithDst = true;
- blendedColor->fKnownColorFlags = kNone_GrColorComponentFlags;
- return;
- }
- blendedColor->fWillBlendWithDst = false;
- if (colorPOI.hasKnownOutputColor(&blendedColor->fKnownColor)) {
- blendedColor->fKnownColorFlags = kRGBA_GrColorComponentFlags;
- } else {
- blendedColor->fKnownColorFlags = kNone_GrColorComponentFlags;
+bool GrPorterDuffXPFactory::WillSrcOverReadDst(const GrProcOptInfo& colorInput,
+ const GrProcOptInfo& coverageInput) {
+ return !coverageInput.isSolidWhite() || !colorInput.isOpaque();
+}
+
+bool GrPorterDuffXPFactory::IsSrcOverPreCoverageBlendedColorConstant(
+ const GrProcOptInfo& colorInput, GrColor* color) {
+ if (!colorInput.isOpaque()) {
+ return false;
}
+ return colorInput.hasKnownOutputColor(color);
}
bool GrPorterDuffXPFactory::SrcOverWillNeedDstTexture(const GrCaps& caps,
diff --git a/src/gpu/ops/GrDrawPathOp.cpp b/src/gpu/ops/GrDrawPathOp.cpp
index a32d7080e0..c2b4fdb4bc 100644
--- a/src/gpu/ops/GrDrawPathOp.cpp
+++ b/src/gpu/ops/GrDrawPathOp.cpp
@@ -99,11 +99,10 @@ bool GrDrawPathRangeOp::onCombineIfPossible(GrOp* t, const GrCaps& caps) {
// numbers, and we only partially account for this by not allowing even/odd paths to be
// combined. (Glyphs in the same font tend to wind the same direction so it works out OK.)
if (GrPathRendering::kWinding_FillType != this->fillType() ||
- GrPathRendering::kWinding_FillType != that->fillType() ||
- this->blendsWithDst()) {
+ GrPathRendering::kWinding_FillType != that->fillType() || this->xpReadsDst()) {
return false;
}
- SkASSERT(!that->blendsWithDst());
+ SkASSERT(!that->xpReadsDst());
fTotalPathCount += that->fTotalPathCount;
while (Draw* head = that->fDraws.head()) {
Draw* draw = fDraws.addToTail();
diff --git a/src/gpu/ops/GrDrawPathOp.h b/src/gpu/ops/GrDrawPathOp.h
index a18a351162..e82ff22845 100644
--- a/src/gpu/ops/GrDrawPathOp.h
+++ b/src/gpu/ops/GrDrawPathOp.h
@@ -33,7 +33,7 @@ protected:
const SkMatrix& viewMatrix() const { return fViewMatrix; }
GrColor color() const { return fColor; }
GrPathRendering::FillType fillType() const { return fFillType; }
- bool blendsWithDst() const { return fBlendsWithDst; }
+ bool xpReadsDst() const { return fXPReadsDst; }
private:
void getPipelineAnalysisInput(GrPipelineAnalysisDrawOpInput* input) const override {
@@ -43,7 +43,7 @@ private:
void applyPipelineOptimizations(const GrPipelineOptimizations& optimizations) override {
optimizations.getOverrideColorIfSet(&fColor);
- fBlendsWithDst = optimizations.willColorBlendWithDst();
+ fXPReadsDst = optimizations.xpReadsDst();
}
void onPrepare(GrOpFlushState*) override; // Initializes fStencilPassSettings.
@@ -52,7 +52,7 @@ private:
GrColor fColor;
GrPathRendering::FillType fFillType;
GrStencilSettings fStencilPassSettings;
- bool fBlendsWithDst;
+ bool fXPReadsDst;
typedef GrDrawOp INHERITED;
};