Remove GrShaderCaps accessor functions.
This CL also removes a few from SkSLUtil but the majority of these will be cleaned up in a followup. (Some of these are currently in active use in SkSL.) Change-Id: I7a018d3f6d8d21d69805f91d81a49c09636e4661 Bug: skia:12559 Reviewed-on: https://skia-review.googlesource.com/c/skia/+/547818 Commit-Queue: Jim Van Verth <jvanverth@google.com> Commit-Queue: John Stiles <johnstiles@google.com> Reviewed-by: Jim Van Verth <jvanverth@google.com> Auto-Submit: John Stiles <johnstiles@google.com>
This commit is contained in:
parent
acfa138998
commit
4d77ec3280
@ -137,7 +137,7 @@ DEF_PATH_TESS_BENCH(GrPathCurveTessellator, make_cubic_path(8), SkMatrix::I()) {
|
||||
GrPipeline noVaryingsPipeline(GrScissorTest::kDisabled, SkBlendMode::kSrcOver,
|
||||
skgpu::Swizzle::RGBA());
|
||||
auto tess = PathCurveTessellator::Make(&arena,
|
||||
fTarget->caps().shaderCaps()->infinitySupport());
|
||||
fTarget->caps().shaderCaps()->fInfinitySupport);
|
||||
tess->prepare(fTarget.get(),
|
||||
fMatrix,
|
||||
{gAlmostIdentity, fPath, SK_PMColor4fTRANSPARENT},
|
||||
@ -149,7 +149,7 @@ DEF_PATH_TESS_BENCH(GrPathWedgeTessellator, make_cubic_path(8), SkMatrix::I()) {
|
||||
GrPipeline noVaryingsPipeline(GrScissorTest::kDisabled, SkBlendMode::kSrcOver,
|
||||
skgpu::Swizzle::RGBA());
|
||||
auto tess = PathWedgeTessellator::Make(&arena,
|
||||
fTarget->caps().shaderCaps()->infinitySupport());
|
||||
fTarget->caps().shaderCaps()->fInfinitySupport);
|
||||
tess->prepare(fTarget.get(),
|
||||
fMatrix,
|
||||
{gAlmostIdentity, fPath, SK_PMColor4fTRANSPARENT},
|
||||
|
@ -271,7 +271,7 @@ private:
|
||||
namespace skiagm {
|
||||
|
||||
DEF_SIMPLE_GPU_GM_CAN_FAIL(fwidth_squircle, rContext, canvas, errorMsg, 200, 200) {
|
||||
if (!rContext->priv().caps()->shaderCaps()->shaderDerivativeSupport()) {
|
||||
if (!rContext->priv().caps()->shaderCaps()->fShaderDerivativeSupport) {
|
||||
*errorMsg = "Shader derivatives not supported.";
|
||||
return DrawResult::kSkip;
|
||||
}
|
||||
|
@ -218,7 +218,7 @@ DEF_SIMPLE_GPU_GM_CAN_FAIL(runtime_intrinsics_trig_es3,
|
||||
plot_es3(canvas, "tanh(x)", -2.0f, 2.0f, -1.0f, 1.0f);
|
||||
next_row(canvas);
|
||||
|
||||
if (ctx->priv().caps()->shaderCaps()->inverseHyperbolicSupport()) {
|
||||
if (ctx->priv().caps()->shaderCaps()->fInverseHyperbolicSupport) {
|
||||
plot_es3(canvas, "asinh(x)", -2.0f, 2.0f, -2.0f, 2.0f);
|
||||
plot_es3(canvas, "acosh(x)", 0.0f, 5.0f, 0.0f, 3.0f);
|
||||
plot_es3(canvas, "atanh(x)", -1.0f, 1.0f, -4.0f, 4.0f);
|
||||
|
@ -95,13 +95,13 @@ private:
|
||||
}
|
||||
}
|
||||
|
||||
auto* tess = PathCurveTessellator::Make(alloc, shaderCaps.infinitySupport());
|
||||
auto* tess = PathCurveTessellator::Make(alloc, shaderCaps.fInfinitySupport);
|
||||
tess->prepareWithTriangles(flushState, shaderMatrix, &triangles, pathList,
|
||||
fPath.countVerbs());
|
||||
fTessellator = tess;
|
||||
} else {
|
||||
// This emulates what PathStencilCoverOp does when using wedges.
|
||||
fTessellator = PathWedgeTessellator::Make(alloc, shaderCaps.infinitySupport());
|
||||
fTessellator = PathWedgeTessellator::Make(alloc, shaderCaps.fInfinitySupport);
|
||||
fTessellator->prepare(flushState, shaderMatrix, pathList, fPath.countVerbs());
|
||||
}
|
||||
|
||||
|
@ -944,7 +944,7 @@ static std::unique_ptr<GrFragmentProcessor> make_rect_blur(GrRecordingContext* c
|
||||
srcRect.bottom() * scale.height()};
|
||||
}
|
||||
|
||||
if (!caps.floatIs32Bits()) {
|
||||
if (!caps.fFloatIs32Bits) {
|
||||
// We promote the math that gets us into the Gaussian space to full float when the rect
|
||||
// coords are large. If we don't have full float then fail. We could probably clip the rect
|
||||
// to an outset device bounds instead.
|
||||
|
@ -184,7 +184,7 @@ static std::unique_ptr<skgpu::v1::SurfaceDrawContext> convolve_gaussian(
|
||||
bool canSplit = mode == SkTileMode::kDecal || mode == SkTileMode::kClamp;
|
||||
// ...but it's not worth doing the splitting if we'll get HW tiling instead of shader tiling.
|
||||
bool canHWTile =
|
||||
srcBounds.contains(srcBackingBounds) &&
|
||||
srcBounds.contains(srcBackingBounds) &&
|
||||
!rContext->priv().caps()->reducedShaderMode() && // this mode always uses shader tiling
|
||||
!(mode == SkTileMode::kDecal && !rContext->priv().caps()->clampToBorderSupport());
|
||||
if (!canSplit || canHWTile) {
|
||||
|
@ -166,8 +166,8 @@ public:
|
||||
return fMustSyncGpuDuringAbandon;
|
||||
}
|
||||
|
||||
// Shortcut for shaderCaps()->reducedShaderMode().
|
||||
bool reducedShaderMode() const { return this->shaderCaps()->reducedShaderMode(); }
|
||||
// Shortcut for shaderCaps()->fReducedShaderMode.
|
||||
bool reducedShaderMode() const { return this->shaderCaps()->fReducedShaderMode; }
|
||||
|
||||
/**
|
||||
* Indicates whether GPU->CPU memory mapping for GPU resources such as vertex buffers and
|
||||
|
@ -256,7 +256,7 @@ bool GrDirectContext::init() {
|
||||
GrDrawOpAtlas::AllowMultitexturing allowMultitexturing;
|
||||
if (GrContextOptions::Enable::kNo == this->options().fAllowMultipleGlyphCacheTextures ||
|
||||
// multitexturing supported only if range can represent the index + texcoords fully
|
||||
!(this->caps()->shaderCaps()->floatIs32Bits() ||
|
||||
!(this->caps()->shaderCaps()->fFloatIs32Bits ||
|
||||
this->caps()->shaderCaps()->integerSupport())) {
|
||||
allowMultitexturing = GrDrawOpAtlas::AllowMultitexturing::kNo;
|
||||
} else {
|
||||
|
@ -698,7 +698,7 @@ GrFPResult GrFragmentProcessor::Ellipse(std::unique_ptr<GrFragmentProcessor> inp
|
||||
SkPoint center,
|
||||
SkPoint radii,
|
||||
const GrShaderCaps& caps) {
|
||||
const bool medPrecision = !caps.floatIs32Bits();
|
||||
const bool medPrecision = !caps.fFloatIs32Bits;
|
||||
|
||||
// Small radii produce bad results on devices without full float.
|
||||
if (medPrecision && (radii.fX < 0.5f || radii.fY < 0.5f)) {
|
||||
@ -940,7 +940,7 @@ SkString ProgramImpl::invokeChildWithMatrix(int childIndex,
|
||||
// Any parent perspective will have already been applied when evaluated in the FS.
|
||||
if (childProc->sampleUsage().hasPerspective()) {
|
||||
invocation.appendf(", proj((%s) * %s.xy1)", matrixName.c_str(), args.fSampleCoord);
|
||||
} else if (args.fShaderCaps->nonsquareMatrixSupport()) {
|
||||
} else if (args.fShaderCaps->fNonsquareMatrixSupport) {
|
||||
invocation.appendf(", float3x2(%s) * %s.xy1", matrixName.c_str(), args.fSampleCoord);
|
||||
} else {
|
||||
invocation.appendf(", ((%s) * %s.xy1).xy", matrixName.c_str(), args.fSampleCoord);
|
||||
|
@ -297,7 +297,7 @@ void ProgramImpl::emitTransformCode(GrGLSLVertexBuilder* vb, GrGLSLUniformHandle
|
||||
|
||||
vb->codeAppend("{\n");
|
||||
if (info.varying.type() == SkSLType::kFloat2) {
|
||||
if (vb->getProgramBuilder()->shaderCaps()->nonsquareMatrixSupport()) {
|
||||
if (vb->getProgramBuilder()->shaderCaps()->fNonsquareMatrixSupport) {
|
||||
vb->codeAppendf("%s = float3x2(%s) * %s",
|
||||
info.varying.vsOut(),
|
||||
transformExpression.c_str(),
|
||||
@ -334,7 +334,7 @@ void ProgramImpl::setupUniformColor(GrGLSLFPFragmentBuilder* fragBuilder,
|
||||
"Color",
|
||||
&stagedLocalVarName);
|
||||
fragBuilder->codeAppendf("%s = %s;", outputName, stagedLocalVarName);
|
||||
if (fragBuilder->getProgramBuilder()->shaderCaps()->mustObfuscateUniformColor()) {
|
||||
if (fragBuilder->getProgramBuilder()->shaderCaps()->fMustObfuscateUniformColor) {
|
||||
fragBuilder->codeAppendf("%s = max(%s, half4(0));", outputName, outputName);
|
||||
}
|
||||
}
|
||||
@ -351,7 +351,7 @@ void ProgramImpl::SetTransform(const GrGLSLProgramDataManager& pdman,
|
||||
if (state) {
|
||||
*state = matrix;
|
||||
}
|
||||
if (matrix.isScaleTranslate() && !shaderCaps.reducedShaderMode()) {
|
||||
if (matrix.isScaleTranslate() && !shaderCaps.fReducedShaderMode) {
|
||||
// ComputeMatrixKey and writeX() assume the uniform is a float4 (can't assert since nothing
|
||||
// is exposed on a handle, but should be caught lower down).
|
||||
float values[4] = {matrix.getScaleX(), matrix.getTranslateX(),
|
||||
@ -385,13 +385,13 @@ static void write_vertex_position(GrGLSLVertexBuilder* vertBuilder,
|
||||
SkASSERT(inPos.getType() == SkSLType::kFloat3 || inPos.getType() == SkSLType::kFloat2);
|
||||
SkString outName = vertBuilder->newTmpVarName(inPos.getName().c_str());
|
||||
|
||||
if (matrix.isIdentity() && !shaderCaps.reducedShaderMode()) {
|
||||
if (matrix.isIdentity() && !shaderCaps.fReducedShaderMode) {
|
||||
write_passthrough_vertex_position(vertBuilder, inPos, outPos);
|
||||
return;
|
||||
}
|
||||
SkASSERT(matrixUniform);
|
||||
|
||||
bool useCompactTransform = matrix.isScaleTranslate() && !shaderCaps.reducedShaderMode();
|
||||
bool useCompactTransform = matrix.isScaleTranslate() && !shaderCaps.fReducedShaderMode;
|
||||
const char* mangledMatrixName;
|
||||
*matrixUniform = uniformHandler->addUniform(nullptr,
|
||||
kVertex_GrShaderFlag,
|
||||
@ -433,7 +433,7 @@ static void write_vertex_position(GrGLSLVertexBuilder* vertBuilder,
|
||||
mangledMatrixName,
|
||||
inPos.getName().c_str(),
|
||||
mangledMatrixName);
|
||||
} else if (shaderCaps.nonsquareMatrixSupport()) {
|
||||
} else if (shaderCaps.fNonsquareMatrixSupport) {
|
||||
vertBuilder->codeAppendf("float2 %s = float3x2(%s) * %s.xy1;\n",
|
||||
outName.c_str(),
|
||||
mangledMatrixName,
|
||||
|
@ -342,7 +342,7 @@ public:
|
||||
// GPs that use writeOutputPosition and/or writeLocalCoord must incorporate the matrix type
|
||||
// into their key, and should use this function or one of the other related helpers.
|
||||
static uint32_t ComputeMatrixKey(const GrShaderCaps& caps, const SkMatrix& mat) {
|
||||
if (!caps.reducedShaderMode()) {
|
||||
if (!caps.fReducedShaderMode) {
|
||||
if (mat.isIdentity()) {
|
||||
return 0b00;
|
||||
}
|
||||
|
@ -50,5 +50,5 @@ GrColorFragmentProcessorAnalysis::GrColorFragmentProcessorAnalysis(
|
||||
}
|
||||
|
||||
bool GrColorFragmentProcessorAnalysis::requiresDstTexture(const GrCaps& caps) const {
|
||||
return this->willReadDstColor() && !caps.shaderCaps()->dstReadInShaderSupport();
|
||||
return this->willReadDstColor() && !caps.shaderCaps()->fDstReadInShaderSupport;
|
||||
}
|
||||
|
@ -18,64 +18,10 @@ class SkJSONWriter;
|
||||
struct GrShaderCaps : SkSL::ShaderCaps {
|
||||
GrShaderCaps() {}
|
||||
|
||||
//
|
||||
// TODO: Remove these unnecessary accessors
|
||||
//
|
||||
void dumpJSON(SkJSONWriter*) const;
|
||||
|
||||
bool supportsDistanceFieldText() const { return fShaderDerivativeSupport; }
|
||||
|
||||
bool dstReadInShaderSupport() const { return fDstReadInShaderSupport; }
|
||||
bool dualSourceBlendingSupport() const { return fDualSourceBlendingSupport; }
|
||||
|
||||
const char* fbFetchExtensionString() const { return fFBFetchExtensionString; }
|
||||
|
||||
bool preferFlatInterpolation() const { return fPreferFlatInterpolation; }
|
||||
|
||||
bool vertexIDSupport() const { return fVertexIDSupport; }
|
||||
|
||||
// isinf() is defined, and floating point infinities are handled according to IEEE standards.
|
||||
bool infinitySupport() const { return fInfinitySupport; }
|
||||
|
||||
// Returns true if `expr` in `myArray[expr]` can be any integer expression. If false, `expr`
|
||||
// must be a constant-index-expression as defined in the OpenGL ES2 specification, Appendix A.5.
|
||||
bool nonconstantArrayIndexSupport() const {
|
||||
return fNonconstantArrayIndexSupport;
|
||||
}
|
||||
|
||||
// frexp(), ldexp(), findMSB(), findLSB().
|
||||
bool bitManipulationSupport() const { return fBitManipulationSupport; }
|
||||
|
||||
bool halfIs32Bits() const { return fHalfIs32Bits; }
|
||||
|
||||
bool hasLowFragmentPrecision() const { return fHasLowFragmentPrecision; }
|
||||
|
||||
// Use a reduced set of rendering algorithms or less optimal effects in order to
|
||||
// reduce the number of unique shaders generated.
|
||||
bool reducedShaderMode() const { return fReducedShaderMode; }
|
||||
|
||||
// SkSL only.
|
||||
bool colorSpaceMathNeedsFloat() const { return fColorSpaceMathNeedsFloat; }
|
||||
|
||||
bool requiresLocalOutputColorForFBFetch() const { return fRequiresLocalOutputColorForFBFetch; }
|
||||
|
||||
bool mustObfuscateUniformColor() const { return fMustObfuscateUniformColor; }
|
||||
|
||||
// On Nexus 6, the GL context can get lost if a shader does not write a value to gl_FragColor.
|
||||
// https://bugs.chromium.org/p/chromium/issues/detail?id=445377
|
||||
bool mustWriteToFragColor() const { return fMustWriteToFragColor; }
|
||||
|
||||
// When we have the option of using either dFdx or dfDy in a shader, this returns whether we
|
||||
// should avoid using dFdx. We have found some drivers have bugs or lower precision when using
|
||||
// dFdx.
|
||||
bool avoidDfDxForGradientsWhenPossible() const { return fAvoidDfDxForGradientsWhenPossible; }
|
||||
|
||||
// This returns the name of an extension that must be enabled in the shader, if such a thing is
|
||||
// required in order to use a secondary output in the shader. This returns a nullptr if no such
|
||||
// extension is required. However, the return value of this function does not say whether dual
|
||||
// source blending is supported.
|
||||
const char* secondaryOutputExtensionString() const { return fSecondaryOutputExtensionString; }
|
||||
|
||||
const char* noperspectiveInterpolationExtensionString() const {
|
||||
SkASSERT(this->noperspectiveInterpolationSupport());
|
||||
return fNoPerspectiveInterpolationExtensionString;
|
||||
@ -86,29 +32,44 @@ struct GrShaderCaps : SkSL::ShaderCaps {
|
||||
return fSampleVariablesExtensionString;
|
||||
}
|
||||
|
||||
int maxFragmentSamplers() const { return fMaxFragmentSamplers; }
|
||||
|
||||
void applyOptionsOverrides(const GrContextOptions& options);
|
||||
|
||||
bool fDstReadInShaderSupport = false;
|
||||
bool fDualSourceBlendingSupport = false;
|
||||
bool fPreferFlatInterpolation = false;
|
||||
bool fVertexIDSupport = false;
|
||||
// isinf() is defined, and floating point infinities are handled according to IEEE standards.
|
||||
bool fInfinitySupport = false;
|
||||
// Returns true if `expr` in `myArray[expr]` can be any integer expression. If false, `expr`
|
||||
// must be a constant-index-expression as defined in the OpenGL ES2 specification, Appendix A.5.
|
||||
bool fNonconstantArrayIndexSupport = false;
|
||||
// frexp(), ldexp(), findMSB(), findLSB().
|
||||
bool fBitManipulationSupport = false;
|
||||
bool fHalfIs32Bits = false;
|
||||
bool fHasLowFragmentPrecision = false;
|
||||
// Use a reduced set of rendering algorithms or less optimal effects in order to reduce the
|
||||
// number of unique shaders generated.
|
||||
bool fReducedShaderMode = false;
|
||||
|
||||
// Used for specific driver bug workarounds
|
||||
bool fRequiresLocalOutputColorForFBFetch = false;
|
||||
// Workaround for Mali GPU opacity bug with uniform colors.
|
||||
bool fMustObfuscateUniformColor = false;
|
||||
// On Nexus 6, the GL context can get lost if a shader does not write a value to gl_FragColor.
|
||||
// https://bugs.chromium.org/p/chromium/issues/detail?id=445377
|
||||
bool fMustWriteToFragColor = false;
|
||||
bool fColorSpaceMathNeedsFloat = false;
|
||||
// When we have the option of using either dFdx or dfDy in a shader, this returns whether we
|
||||
// should avoid using dFdx. We have found some drivers have bugs or lower precision when using
|
||||
// dFdx.
|
||||
bool fAvoidDfDxForGradientsWhenPossible = false;
|
||||
|
||||
// This contains the name of an extension that must be enabled in the shader, if such a thing is
|
||||
// required in order to use a secondary output in the shader. This returns a nullptr if no such
|
||||
// extension is required. However, the return value of this function does not say whether dual
|
||||
// source blending is supported.
|
||||
const char* fSecondaryOutputExtensionString = nullptr;
|
||||
|
||||
const char* fNoPerspectiveInterpolationExtensionString = nullptr;
|
||||
const char* fSampleVariablesExtensionString = nullptr;
|
||||
|
||||
|
@ -169,7 +169,7 @@ GrXPFactory::AnalysisProperties GrXPFactory::GetAnalysisProperties(
|
||||
}
|
||||
SkASSERT(!(result & AnalysisProperties::kRequiresDstTexture));
|
||||
if ((result & AnalysisProperties::kReadsDstInShader) &&
|
||||
!caps.shaderCaps()->dstReadInShaderSupport()) {
|
||||
!caps.shaderCaps()->fDstReadInShaderSupport) {
|
||||
result |= AnalysisProperties::kRequiresDstTexture |
|
||||
AnalysisProperties::kRequiresNonOverlappingDraws;
|
||||
}
|
||||
@ -235,7 +235,7 @@ void ProgramImpl::emitCode(const EmitArgs& args) {
|
||||
args.fInputCoverage);
|
||||
}
|
||||
} else {
|
||||
needsLocalOutColor = args.fShaderCaps->requiresLocalOutputColorForFBFetch();
|
||||
needsLocalOutColor = args.fShaderCaps->fRequiresLocalOutputColorForFBFetch;
|
||||
}
|
||||
|
||||
const char* outColor = "_localColorOut";
|
||||
|
@ -65,7 +65,7 @@ public:
|
||||
const SkMatrix& localMatrix,
|
||||
bool usesLocalCoords,
|
||||
uint8_t coverage = 0xff) {
|
||||
if (!caps.shaderCaps()->shaderDerivativeSupport()) {
|
||||
if (!caps.shaderCaps()->fShaderDerivativeSupport) {
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
@ -127,7 +127,7 @@ public:
|
||||
const SkMatrix& localMatrix,
|
||||
bool usesLocalCoords,
|
||||
uint8_t coverage = 0xff) {
|
||||
if (!caps.shaderCaps()->shaderDerivativeSupport()) {
|
||||
if (!caps.shaderCaps()->fShaderDerivativeSupport) {
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
|
@ -38,7 +38,7 @@ std::unique_ptr<GrXferProcessor::ProgramImpl> DisableColorXP::makeProgramImpl()
|
||||
class Impl : public ProgramImpl {
|
||||
private:
|
||||
void emitOutputsForBlendState(const EmitArgs& args) override {
|
||||
if (args.fShaderCaps->mustWriteToFragColor()) {
|
||||
if (args.fShaderCaps->fMustWriteToFragColor) {
|
||||
// This emit code should be empty. However, on the nexus 6 there is a driver bug
|
||||
// where if you do not give gl_FragColor a value, the gl context is lost and we end
|
||||
// up drawing nothing. So this fix just sets the gl_FragColor arbitrarily to 0.
|
||||
|
@ -127,7 +127,7 @@ private:
|
||||
// We use st coordinates to ensure we're mapping 1:1 from texel space to pixel space.
|
||||
|
||||
// this gives us a smooth step across approximately one fragment
|
||||
if (args.fShaderCaps->avoidDfDxForGradientsWhenPossible()) {
|
||||
if (args.fShaderCaps->fAvoidDfDxForGradientsWhenPossible) {
|
||||
fragBuilder->codeAppendf(
|
||||
"afwidth = abs(" SK_DistanceFieldAAFactor "*half(dFdy(%s.y)));", st.fsIn());
|
||||
} else {
|
||||
@ -141,7 +141,7 @@ private:
|
||||
// We use the y gradient because there is a bug in the Mali 400 in the x direction.
|
||||
|
||||
// this gives us a smooth step across approximately one fragment
|
||||
if (args.fShaderCaps->avoidDfDxForGradientsWhenPossible()) {
|
||||
if (args.fShaderCaps->fAvoidDfDxForGradientsWhenPossible) {
|
||||
fragBuilder->codeAppendf("half st_grad_len = length(half2(dFdy(%s)));", st.fsIn());
|
||||
} else {
|
||||
fragBuilder->codeAppendf("half st_grad_len = length(half2(dFdx(%s)));", st.fsIn());
|
||||
@ -412,7 +412,7 @@ private:
|
||||
// We use st coordinates to ensure we're mapping 1:1 from texel space to pixel space.
|
||||
|
||||
// this gives us a smooth step across approximately one fragment
|
||||
if (args.fShaderCaps->avoidDfDxForGradientsWhenPossible()) {
|
||||
if (args.fShaderCaps->fAvoidDfDxForGradientsWhenPossible) {
|
||||
fragBuilder->codeAppendf(
|
||||
"afwidth = abs(" SK_DistanceFieldAAFactor "*half(dFdy(%s.y)));", st.fsIn());
|
||||
} else {
|
||||
@ -425,7 +425,7 @@ private:
|
||||
// to ensure we're mapping 1:1 from texel space to pixel space.
|
||||
|
||||
// this gives us a smooth step across approximately one fragment
|
||||
if (args.fShaderCaps->avoidDfDxForGradientsWhenPossible()) {
|
||||
if (args.fShaderCaps->fAvoidDfDxForGradientsWhenPossible) {
|
||||
fragBuilder->codeAppendf("half st_grad_len = half(length(dFdy(%s)));", st.fsIn());
|
||||
} else {
|
||||
fragBuilder->codeAppendf("half st_grad_len = half(length(dFdx(%s)));", st.fsIn());
|
||||
@ -668,7 +668,7 @@ private:
|
||||
fragBuilder->codeAppendf("float2 uv = %s;\n", uv.fsIn());
|
||||
|
||||
if (isUniformScale) {
|
||||
if (args.fShaderCaps->avoidDfDxForGradientsWhenPossible()) {
|
||||
if (args.fShaderCaps->fAvoidDfDxForGradientsWhenPossible) {
|
||||
fragBuilder->codeAppendf("half st_grad_len = half(abs(dFdy(%s.y)));", st.fsIn());
|
||||
} else {
|
||||
fragBuilder->codeAppendf("half st_grad_len = half(abs(dFdx(%s.x)));", st.fsIn());
|
||||
@ -678,7 +678,7 @@ private:
|
||||
} else if (isSimilarity) {
|
||||
// For a similarity matrix with rotation, the gradient will not be aligned
|
||||
// with the texel coordinate axes, so we need to calculate it.
|
||||
if (args.fShaderCaps->avoidDfDxForGradientsWhenPossible()) {
|
||||
if (args.fShaderCaps->fAvoidDfDxForGradientsWhenPossible) {
|
||||
// We use dFdy instead and rotate -90 degrees to get the gradient in the x
|
||||
// direction.
|
||||
fragBuilder->codeAppendf("half2 st_grad = half2(dFdy(%s));", st.fsIn());
|
||||
|
@ -35,7 +35,7 @@ private:
|
||||
static bool should_use_variable_length_loop(const GrShaderCaps& caps) {
|
||||
// If we're in reduced-shader mode, and we can use variable length loops, then use a uniform to
|
||||
// limit the number of iterations, so we don't need a code variation for each width.
|
||||
return (caps.generation() >= SkSL::GLSLGeneration::k300es && caps.reducedShaderMode());
|
||||
return (caps.generation() >= SkSL::GLSLGeneration::k300es && caps.fReducedShaderMode);
|
||||
}
|
||||
|
||||
void GrGaussianConvolutionFragmentProcessor::Impl::emitCode(EmitArgs& args) {
|
||||
|
@ -731,8 +731,8 @@ sk_sp<const GrXferProcessor> GrPorterDuffXPFactory::makeXferProcessor(
|
||||
// See comment in MakeSrcOverXferProcessor about color.isOpaque here
|
||||
if (isLCD &&
|
||||
SkBlendMode::kSrcOver == fBlendMode && color.isConstant() && /*color.isOpaque() &&*/
|
||||
!caps.shaderCaps()->dualSourceBlendingSupport() &&
|
||||
!caps.shaderCaps()->dstReadInShaderSupport()) {
|
||||
!caps.shaderCaps()->fDualSourceBlendingSupport &&
|
||||
!caps.shaderCaps()->fDstReadInShaderSupport) {
|
||||
// If we don't have dual source blending or in shader dst reads, we fall back to this
|
||||
// trick for rendering SrcOver LCD text instead of doing a dst copy.
|
||||
return PDLCDXferProcessor::Make(fBlendMode, color);
|
||||
@ -753,7 +753,7 @@ sk_sp<const GrXferProcessor> GrPorterDuffXPFactory::makeXferProcessor(
|
||||
|
||||
// Skia always saturates after the kPlus blend mode, so it requires shader-based blending when
|
||||
// pixels aren't guaranteed to automatically be normalized (i.e. any floating point config).
|
||||
if ((blendFormula.hasSecondaryOutput() && !caps.shaderCaps()->dualSourceBlendingSupport()) ||
|
||||
if ((blendFormula.hasSecondaryOutput() && !caps.shaderCaps()->fDualSourceBlendingSupport) ||
|
||||
(isLCD && (SkBlendMode::kSrcOver != fBlendMode /*|| !color.isOpaque()*/)) ||
|
||||
(GrClampType::kAuto != clampType && SkBlendMode::kPlus == fBlendMode)) {
|
||||
return sk_sp<const GrXferProcessor>(new ShaderPDXferProcessor(fBlendMode, coverage));
|
||||
@ -782,8 +782,8 @@ static inline GrXPFactory::AnalysisProperties analysis_properties(
|
||||
if (isLCD) {
|
||||
// See comment in MakeSrcOverXferProcessor about color.isOpaque here
|
||||
if (SkBlendMode::kSrcOver == mode && color.isConstant() && /*color.isOpaque() &&*/
|
||||
!caps.shaderCaps()->dualSourceBlendingSupport() &&
|
||||
!caps.shaderCaps()->dstReadInShaderSupport()) {
|
||||
!caps.shaderCaps()->fDualSourceBlendingSupport &&
|
||||
!caps.shaderCaps()->fDstReadInShaderSupport) {
|
||||
props |= AnalysisProperties::kIgnoresInputColor;
|
||||
} else {
|
||||
// For LCD blending, if the color is not opaque we must read the dst in shader even if
|
||||
@ -793,13 +793,13 @@ static inline GrXPFactory::AnalysisProperties analysis_properties(
|
||||
// do not have dual source blending.
|
||||
if (SkBlendMode::kSrcOver != mode ||
|
||||
/*!color.isOpaque() ||*/ // See comment in MakeSrcOverXferProcessor about isOpaque.
|
||||
(formula.hasSecondaryOutput() && !caps.shaderCaps()->dualSourceBlendingSupport())) {
|
||||
(formula.hasSecondaryOutput() && !caps.shaderCaps()->fDualSourceBlendingSupport)) {
|
||||
props |= AnalysisProperties::kReadsDstInShader;
|
||||
}
|
||||
}
|
||||
} else {
|
||||
// With dual-source blending we never need the destination color in the shader.
|
||||
if (!caps.shaderCaps()->dualSourceBlendingSupport()) {
|
||||
if (!caps.shaderCaps()->fDualSourceBlendingSupport) {
|
||||
if (formula.hasSecondaryOutput()) {
|
||||
props |= AnalysisProperties::kReadsDstInShader;
|
||||
}
|
||||
@ -890,8 +890,8 @@ sk_sp<const GrXferProcessor> GrPorterDuffXPFactory::MakeSrcOverXferProcessor(
|
||||
// This also fixes a chrome bug on macs where we are getting random fuzziness when doing
|
||||
// blending in the shader for non opaque sources.
|
||||
if (color.isConstant() && /*color.isOpaque() &&*/
|
||||
!caps.shaderCaps()->dualSourceBlendingSupport() &&
|
||||
!caps.shaderCaps()->dstReadInShaderSupport()) {
|
||||
!caps.shaderCaps()->fDualSourceBlendingSupport &&
|
||||
!caps.shaderCaps()->fDstReadInShaderSupport) {
|
||||
// If we don't have dual source blending or in shader dst reads, we fall
|
||||
// back to this trick for rendering SrcOver LCD text instead of doing a
|
||||
// dst copy.
|
||||
@ -901,7 +901,7 @@ sk_sp<const GrXferProcessor> GrPorterDuffXPFactory::MakeSrcOverXferProcessor(
|
||||
BlendFormula blendFormula = get_lcd_blend_formula(SkBlendMode::kSrcOver);
|
||||
// See comment above regarding why the opaque check is commented out here.
|
||||
if (/*!color.isOpaque() ||*/
|
||||
(blendFormula.hasSecondaryOutput() && !caps.shaderCaps()->dualSourceBlendingSupport())) {
|
||||
(blendFormula.hasSecondaryOutput() && !caps.shaderCaps()->fDualSourceBlendingSupport)) {
|
||||
return sk_sp<GrXferProcessor>(new ShaderPDXferProcessor(SkBlendMode::kSrcOver, coverage));
|
||||
}
|
||||
return sk_sp<GrXferProcessor>(new PorterDuffXferProcessor(blendFormula, coverage));
|
||||
|
@ -171,7 +171,7 @@ void CircularRRectEffect::Impl::emitCode(EmitArgs& args) {
|
||||
|
||||
// If we're on a device where float != fp32 then the length calculation could overflow.
|
||||
SkString clampedCircleDistance;
|
||||
if (!args.fShaderCaps->floatIs32Bits()) {
|
||||
if (!args.fShaderCaps->fFloatIs32Bits) {
|
||||
clampedCircleDistance.printf("saturate(%s.x * (1.0 - length(dxy * %s.y)))",
|
||||
radiusPlusHalfName, radiusPlusHalfName);
|
||||
} else {
|
||||
@ -499,7 +499,7 @@ static bool elliptical_effect_uses_scale(const GrShaderCaps& caps, const SkRRect
|
||||
// If we're on a device where float != fp32 then we'll do the distance computation in a space
|
||||
// that is normalized by the largest radius. The scale uniform will be scale, 1/scale. The
|
||||
// radii uniform values are already in this normalized space.
|
||||
if (!caps.floatIs32Bits()) {
|
||||
if (!caps.fFloatIs32Bits) {
|
||||
return true;
|
||||
}
|
||||
// Additionally, even if we have fp32, large radii can underflow 1/radii^2 terms leading to
|
||||
|
@ -226,7 +226,7 @@ static inline GrGLenum wrap_mode_to_gl_wrap(GrSamplerState::WrapMode wrapMode,
|
||||
class GrGLGpu::SamplerObjectCache {
|
||||
public:
|
||||
SamplerObjectCache(GrGLGpu* gpu) : fGpu(gpu) {
|
||||
fNumTextureUnits = fGpu->glCaps().shaderCaps()->maxFragmentSamplers();
|
||||
fNumTextureUnits = fGpu->glCaps().shaderCaps()->fMaxFragmentSamplers;
|
||||
fTextureUnitStates = std::make_unique<UnitState[]>(fNumTextureUnits);
|
||||
}
|
||||
|
||||
|
@ -436,7 +436,7 @@ private:
|
||||
void flushWindowRectangles(const GrWindowRectsState&, const GrGLRenderTarget*, GrSurfaceOrigin);
|
||||
void disableWindowRectangles();
|
||||
|
||||
int numTextureUnits() const { return this->caps()->shaderCaps()->maxFragmentSamplers(); }
|
||||
int numTextureUnits() const { return this->caps()->shaderCaps()->fMaxFragmentSamplers; }
|
||||
|
||||
// Binds a texture to a target on the "scratch" texture unit to use for texture operations
|
||||
// other than usual draw flow (i.e. a GrGLProgram derived from a GrPipeline used to draw). It
|
||||
|
@ -21,7 +21,7 @@ const char* GrGLSLFragmentShaderBuilder::dstColor() {
|
||||
const GrShaderCaps* shaderCaps = fProgramBuilder->shaderCaps();
|
||||
if (shaderCaps->fbFetchSupport()) {
|
||||
this->addFeature(1 << kFramebufferFetch_GLSLPrivateFeature,
|
||||
shaderCaps->fbFetchExtensionString());
|
||||
shaderCaps->fFBFetchExtensionString);
|
||||
|
||||
// Some versions of this extension string require declaring custom color output on ES 3.0+
|
||||
const char* fbFetchColorName = "sk_LastFragColor";
|
||||
@ -61,7 +61,7 @@ void GrGLSLFragmentShaderBuilder::enableSecondaryOutput() {
|
||||
SkASSERT(!fHasSecondaryOutput);
|
||||
fHasSecondaryOutput = true;
|
||||
const GrShaderCaps& caps = *fProgramBuilder->shaderCaps();
|
||||
if (const char* extension = caps.secondaryOutputExtensionString()) {
|
||||
if (const char* extension = caps.fSecondaryOutputExtensionString) {
|
||||
this->addFeature(1 << kBlendFuncExtended_GLSLPrivateFeature, extension);
|
||||
}
|
||||
|
||||
|
@ -418,7 +418,7 @@ GrGLSLProgramBuilder::SamplerHandle GrGLSLProgramBuilder::emitInputSampler(
|
||||
|
||||
bool GrGLSLProgramBuilder::checkSamplerCounts() {
|
||||
const GrShaderCaps& shaderCaps = *this->shaderCaps();
|
||||
if (fNumFragmentSamplers > shaderCaps.maxFragmentSamplers()) {
|
||||
if (fNumFragmentSamplers > shaderCaps.fMaxFragmentSamplers) {
|
||||
GrCapsDebugf(this->caps(), "Program would use too many fragment samplers\n");
|
||||
return false;
|
||||
}
|
||||
|
@ -228,7 +228,7 @@ void GrGLSLShaderBuilder::appendColorGamutXform(SkString* out,
|
||||
// Most GPUs work just fine with half float. Strangely, the GPUs that have this bug
|
||||
// (Mali G series) only require us to promote the type of a few temporaries here --
|
||||
// the helper functions above can always be written to use half.
|
||||
bool useFloat = fProgramBuilder->shaderCaps()->colorSpaceMathNeedsFloat();
|
||||
bool useFloat = fProgramBuilder->shaderCaps()->fColorSpaceMathNeedsFloat;
|
||||
|
||||
const GrShaderVar gColorXformArgs[] = {
|
||||
GrShaderVar("color", useFloat ? SkSLType::kFloat4 : SkSLType::kHalf4)};
|
||||
|
@ -26,11 +26,10 @@ static bool use_flat_interpolation(GrGLSLVaryingHandler::Interpolation interpola
|
||||
case Interpolation::kInterpolated:
|
||||
return false;
|
||||
case Interpolation::kCanBeFlat:
|
||||
SkASSERT(!shaderCaps.preferFlatInterpolation() ||
|
||||
shaderCaps.flatInterpolationSupport());
|
||||
return shaderCaps.preferFlatInterpolation();
|
||||
SkASSERT(!shaderCaps.fPreferFlatInterpolation || shaderCaps.fFlatInterpolationSupport);
|
||||
return shaderCaps.fPreferFlatInterpolation;
|
||||
case Interpolation::kMustBeFlat:
|
||||
SkASSERT(shaderCaps.flatInterpolationSupport());
|
||||
SkASSERT(shaderCaps.fFlatInterpolationSupport);
|
||||
return true;
|
||||
}
|
||||
SK_ABORT("Invalid interpolation");
|
||||
|
@ -467,7 +467,7 @@ static std::unique_ptr<GrFragmentProcessor> make_colorizer(const SkPMColor4f* co
|
||||
// isn't 32-bit, output can be incorrect if the thresholds are too close together. However,
|
||||
// the analytic shaders are higher quality, so they can be used with lower precision
|
||||
// hardware when the thresholds are not ill-conditioned.
|
||||
if (!caps->floatIs32Bits()) {
|
||||
if (!caps->fFloatIs32Bits) {
|
||||
// Could run into problems. Check if thresholds are close together (with a limit of .01,
|
||||
// so that scales will be less than 100, which leaves 4 decimals of precision on
|
||||
// 16-bit).
|
||||
@ -501,8 +501,8 @@ static std::unique_ptr<GrFragmentProcessor> make_colorizer(const SkPMColor4f* co
|
||||
return nullptr;
|
||||
};
|
||||
|
||||
int binaryColorizerLimit = caps->nonconstantArrayIndexSupport() ? kMaxLoopingColorCount
|
||||
: kMaxUnrolledColorCount;
|
||||
int binaryColorizerLimit = caps->fNonconstantArrayIndexSupport ? kMaxLoopingColorCount
|
||||
: kMaxUnrolledColorCount;
|
||||
if ((count <= binaryColorizerLimit) && !intervalsExceedPrecisionLimit()) {
|
||||
// The dual-interval colorizer uses the same principles as the binary-search colorizer, but
|
||||
// is limited to exactly 2 intervals.
|
||||
@ -511,7 +511,7 @@ static std::unique_ptr<GrFragmentProcessor> make_colorizer(const SkPMColor4f* co
|
||||
return colorizer;
|
||||
}
|
||||
// Attempt to create an analytic colorizer that uses a binary-search loop.
|
||||
colorizer = caps->nonconstantArrayIndexSupport()
|
||||
colorizer = caps->fNonconstantArrayIndexSupport
|
||||
? make_looping_binary_colorizer(colors, positions, count)
|
||||
: make_unrolled_binary_colorizer(colors, positions, count);
|
||||
if (colorizer) {
|
||||
|
@ -678,7 +678,7 @@ GrGeometryProcessor* QuadEdgeEffect::TestCreate(GrProcessorTestData* d) {
|
||||
bool usesLocalCoords = d->fRandom->nextBool();
|
||||
bool wideColor = d->fRandom->nextBool();
|
||||
// Doesn't work without derivative instructions.
|
||||
return d->caps()->shaderCaps()->shaderDerivativeSupport()
|
||||
return d->caps()->shaderCaps()->fShaderDerivativeSupport
|
||||
? QuadEdgeEffect::Make(d->allocator(), localMatrix, usesLocalCoords, wideColor)
|
||||
: nullptr;
|
||||
}
|
||||
@ -906,7 +906,7 @@ private:
|
||||
PathRenderer::CanDrawPath AAConvexPathRenderer::onCanDrawPath(const CanDrawPathArgs& args) const {
|
||||
// This check requires convexity and known direction, since the direction is used to build
|
||||
// the geometry segments. Degenerate convex paths will fall through to some other path renderer.
|
||||
if (args.fCaps->shaderCaps()->shaderDerivativeSupport() &&
|
||||
if (args.fCaps->shaderCaps()->fShaderDerivativeSupport &&
|
||||
(GrAAType::kCoverage == args.fAAType) && args.fShape->style().isSimpleFill() &&
|
||||
!args.fShape->inverseFilled() && args.fShape->knownToBeConvex() &&
|
||||
args.fShape->knownDirection()) {
|
||||
|
@ -1050,7 +1050,7 @@ void AAHairlineOp::makeConicProgramInfo(const GrCaps& caps, SkArenaAlloc* arena,
|
||||
}
|
||||
|
||||
AAHairlineOp::Program AAHairlineOp::predictPrograms(const GrCaps* caps) const {
|
||||
bool convertConicsToQuads = !caps->shaderCaps()->floatIs32Bits();
|
||||
bool convertConicsToQuads = !caps->shaderCaps()->fFloatIs32Bits;
|
||||
|
||||
// When predicting the programs we always include the lineProgram bc it is used as a fallback
|
||||
// for quads and conics. In non-DDL mode there are cases where it sometimes isn't needed for a
|
||||
@ -1172,7 +1172,7 @@ void AAHairlineOp::onPrepareDraws(GrMeshDrawTarget* target) {
|
||||
int quadCount = 0;
|
||||
|
||||
int instanceCount = fPaths.count();
|
||||
bool convertConicsToQuads = !target->caps().shaderCaps()->floatIs32Bits();
|
||||
bool convertConicsToQuads = !target->caps().shaderCaps()->fFloatIs32Bits;
|
||||
for (int i = 0; i < instanceCount; i++) {
|
||||
const PathData& args = fPaths[i];
|
||||
quadCount += gather_lines_and_quads(args.fPath, args.fViewMatrix, args.fDevClipBounds,
|
||||
@ -1323,7 +1323,7 @@ PathRenderer::CanDrawPath AAHairLinePathRenderer::onCanDrawPath(const CanDrawPat
|
||||
}
|
||||
|
||||
if (SkPath::kLine_SegmentMask == args.fShape->segmentMask() ||
|
||||
args.fCaps->shaderCaps()->shaderDerivativeSupport()) {
|
||||
args.fCaps->shaderCaps()->fShaderDerivativeSupport) {
|
||||
return CanDrawPath::kYes;
|
||||
}
|
||||
|
||||
|
@ -31,7 +31,7 @@ public:
|
||||
, fAtlasAccess(GrSamplerState::Filter::kNearest,
|
||||
fAtlasHelper->proxy()->backendFormat(),
|
||||
fAtlasHelper->atlasSwizzle()) {
|
||||
if (!shaderCaps.vertexIDSupport()) {
|
||||
if (!shaderCaps.fVertexIDSupport) {
|
||||
constexpr static Attribute kUnitCoordAttrib(
|
||||
"unitCoord", kFloat2_GrVertexAttribType, SkSLType::kFloat2);
|
||||
this->setVertexAttributesWithImplicitOffsets(&kUnitCoordAttrib, 1);
|
||||
@ -82,7 +82,7 @@ private:
|
||||
const auto& shader = args.fGeomProc.cast<DrawAtlasPathShader>();
|
||||
args.fVaryingHandler->emitAttributes(shader);
|
||||
|
||||
if (args.fShaderCaps->vertexIDSupport()) {
|
||||
if (args.fShaderCaps->fVertexIDSupport) {
|
||||
// If we don't have sk_VertexID support then "unitCoord" already came in as a vertex
|
||||
// attrib.
|
||||
args.fVertBuilder->codeAppendf(R"(
|
||||
@ -204,7 +204,7 @@ void DrawAtlasPathOp::onPrepare(GrOpFlushState* flushState) {
|
||||
}
|
||||
}
|
||||
|
||||
if (!flushState->caps().shaderCaps()->vertexIDSupport()) {
|
||||
if (!flushState->caps().shaderCaps()->fVertexIDSupport) {
|
||||
constexpr static SkPoint kUnitQuad[4] = {{0,0}, {0,1}, {1,0}, {1,1}};
|
||||
|
||||
SKGPU_DEFINE_STATIC_UNIQUE_KEY(gUnitQuadBufferKey);
|
||||
|
@ -860,7 +860,7 @@ bool can_use_hw_derivatives_with_coverage(const skvx::float2& devScale,
|
||||
bool can_use_hw_derivatives_with_coverage(const GrShaderCaps& shaderCaps,
|
||||
const SkMatrix& viewMatrix,
|
||||
const SkRRect& rrect) {
|
||||
if (!shaderCaps.shaderDerivativeSupport()) {
|
||||
if (!shaderCaps.fShaderDerivativeSupport) {
|
||||
return false;
|
||||
}
|
||||
|
||||
|
@ -636,7 +636,7 @@ private:
|
||||
fragBuilder->codeAppend("float grad_dot = dot(grad, grad);");
|
||||
|
||||
// avoid calling inversesqrt on zero.
|
||||
if (args.fShaderCaps->floatIs32Bits()) {
|
||||
if (args.fShaderCaps->fFloatIs32Bits) {
|
||||
fragBuilder->codeAppend("grad_dot = max(grad_dot, 1.1755e-38);");
|
||||
} else {
|
||||
fragBuilder->codeAppend("grad_dot = max(grad_dot, 6.1036e-5);");
|
||||
@ -661,7 +661,7 @@ private:
|
||||
fragBuilder->codeAppendf("grad = 2.0*offset*%s.zw;", ellipseRadii.fsIn());
|
||||
}
|
||||
fragBuilder->codeAppend("grad_dot = dot(grad, grad);");
|
||||
if (!args.fShaderCaps->floatIs32Bits()) {
|
||||
if (!args.fShaderCaps->fFloatIs32Bits) {
|
||||
fragBuilder->codeAppend("grad_dot = max(grad_dot, 6.1036e-5);");
|
||||
}
|
||||
if (egp.fUseScale) {
|
||||
@ -824,7 +824,7 @@ private:
|
||||
|
||||
fragBuilder->codeAppend("float grad_dot = 4.0*dot(grad, grad);");
|
||||
// avoid calling inversesqrt on zero.
|
||||
if (args.fShaderCaps->floatIs32Bits()) {
|
||||
if (args.fShaderCaps->fFloatIs32Bits) {
|
||||
fragBuilder->codeAppend("grad_dot = max(grad_dot, 1.1755e-38);");
|
||||
} else {
|
||||
fragBuilder->codeAppend("grad_dot = max(grad_dot, 6.1036e-5);");
|
||||
@ -855,7 +855,7 @@ private:
|
||||
fragBuilder->codeAppendf("grad *= %s.z;", offsets0.fsIn());
|
||||
}
|
||||
fragBuilder->codeAppend("grad_dot = 4.0*dot(grad, grad);");
|
||||
if (!args.fShaderCaps->floatIs32Bits()) {
|
||||
if (!args.fShaderCaps->fFloatIs32Bits) {
|
||||
fragBuilder->codeAppend("grad_dot = max(grad_dot, 6.1036e-5);");
|
||||
}
|
||||
fragBuilder->codeAppend("invlen = inversesqrt(grad_dot);");
|
||||
@ -1894,7 +1894,7 @@ public:
|
||||
// minimum value to avoid divides by zero. With large ovals and low precision this
|
||||
// leads to blurring at the edge of the oval.
|
||||
const SkScalar kMaxOvalRadius = 16384;
|
||||
if (!context->priv().caps()->shaderCaps()->floatIs32Bits() &&
|
||||
if (!context->priv().caps()->shaderCaps()->fFloatIs32Bits &&
|
||||
(params.fXRadius >= kMaxOvalRadius || params.fYRadius >= kMaxOvalRadius)) {
|
||||
return nullptr;
|
||||
}
|
||||
@ -1938,8 +1938,8 @@ public:
|
||||
|
||||
GrProcessorSet::Analysis finalize(const GrCaps& caps, const GrAppliedClip* clip,
|
||||
GrClampType clampType) override {
|
||||
fUseScale = !caps.shaderCaps()->floatIs32Bits() &&
|
||||
!caps.shaderCaps()->hasLowFragmentPrecision();
|
||||
fUseScale = !caps.shaderCaps()->fFloatIs32Bits &&
|
||||
!caps.shaderCaps()->fHasLowFragmentPrecision;
|
||||
SkPMColor4f* color = &fEllipses.front().fColor;
|
||||
return fHelper.finalizeProcessors(caps, clip, clampType,
|
||||
GrProcessorAnalysisCoverage::kSingleChannel, color,
|
||||
@ -2179,7 +2179,7 @@ public:
|
||||
// minimum value to avoid divides by zero. With large ovals and low precision this
|
||||
// leads to blurring at the edge of the oval.
|
||||
const SkScalar kMaxOvalRadius = 16384;
|
||||
if (!context->priv().caps()->shaderCaps()->floatIs32Bits() &&
|
||||
if (!context->priv().caps()->shaderCaps()->fFloatIs32Bits &&
|
||||
(params.fXRadius >= kMaxOvalRadius || params.fYRadius >= kMaxOvalRadius)) {
|
||||
return nullptr;
|
||||
}
|
||||
@ -2227,8 +2227,8 @@ public:
|
||||
|
||||
GrProcessorSet::Analysis finalize(const GrCaps& caps, const GrAppliedClip* clip,
|
||||
GrClampType clampType) override {
|
||||
fUseScale = !caps.shaderCaps()->floatIs32Bits() &&
|
||||
!caps.shaderCaps()->hasLowFragmentPrecision();
|
||||
fUseScale = !caps.shaderCaps()->fFloatIs32Bits &&
|
||||
!caps.shaderCaps()->fHasLowFragmentPrecision;
|
||||
SkPMColor4f* color = &fEllipses.front().fColor;
|
||||
return fHelper.finalizeProcessors(caps, clip, clampType,
|
||||
GrProcessorAnalysisCoverage::kSingleChannel, color,
|
||||
@ -2960,7 +2960,7 @@ public:
|
||||
|
||||
GrProcessorSet::Analysis finalize(const GrCaps& caps, const GrAppliedClip* clip,
|
||||
GrClampType clampType) override {
|
||||
fUseScale = !caps.shaderCaps()->floatIs32Bits();
|
||||
fUseScale = !caps.shaderCaps()->fFloatIs32Bits;
|
||||
SkPMColor4f* color = &fRRects.front().fColor;
|
||||
return fHelper.finalizeProcessors(caps, clip, clampType,
|
||||
GrProcessorAnalysisCoverage::kSingleChannel, color,
|
||||
@ -3361,7 +3361,7 @@ GrOp::Owner GrOvalOpFactory::MakeOvalOp(GrRecordingContext* context,
|
||||
}
|
||||
|
||||
// Otherwise, if we have shader derivative support, render as device-independent
|
||||
if (shaderCaps->shaderDerivativeSupport()) {
|
||||
if (shaderCaps->fShaderDerivativeSupport) {
|
||||
SkScalar a = viewMatrix[SkMatrix::kMScaleX];
|
||||
SkScalar b = viewMatrix[SkMatrix::kMSkewX];
|
||||
SkScalar c = viewMatrix[SkMatrix::kMSkewY];
|
||||
|
@ -32,7 +32,7 @@ public:
|
||||
PatchAttribs::kNone) {
|
||||
fInstanceAttribs.emplace_back("p01", kFloat4_GrVertexAttribType, SkSLType::kFloat4);
|
||||
fInstanceAttribs.emplace_back("p23", kFloat4_GrVertexAttribType, SkSLType::kFloat4);
|
||||
if (!shaderCaps.infinitySupport()) {
|
||||
if (!shaderCaps.fInfinitySupport) {
|
||||
// A conic curve is written out with p3=[w,Infinity], but GPUs that don't support
|
||||
// infinity can't detect this. On these platforms we also write out an extra float with
|
||||
// each patch that explicitly tells the shader what type of curve it is.
|
||||
@ -42,7 +42,7 @@ public:
|
||||
fInstanceAttribs.count());
|
||||
SkASSERT(fInstanceAttribs.count() <= kMaxInstanceAttribCount);
|
||||
|
||||
if (!shaderCaps.vertexIDSupport()) {
|
||||
if (!shaderCaps.fVertexIDSupport) {
|
||||
constexpr static Attribute kVertexIdxAttrib("vertexidx", kFloat_GrVertexAttribType,
|
||||
SkSLType::kFloat);
|
||||
this->setVertexAttributesWithImplicitOffsets(&kVertexIdxAttrib, 1);
|
||||
@ -66,7 +66,7 @@ std::unique_ptr<GrGeometryProcessor::ProgramImpl> HullShader::makeProgramImpl(
|
||||
GrGLSLVertexBuilder* v,
|
||||
GrGLSLVaryingHandler*,
|
||||
GrGPArgs* gpArgs) override {
|
||||
if (shaderCaps.infinitySupport()) {
|
||||
if (shaderCaps.fInfinitySupport) {
|
||||
v->insertFunction(R"(
|
||||
bool is_conic_curve() { return isinf(p23.w); }
|
||||
bool is_non_triangular_conic_curve() {
|
||||
@ -119,7 +119,7 @@ std::unique_ptr<GrGeometryProcessor::ProgramImpl> HullShader::makeProgramImpl(
|
||||
}
|
||||
})");
|
||||
|
||||
if (shaderCaps.vertexIDSupport()) {
|
||||
if (shaderCaps.fVertexIDSupport) {
|
||||
// If we don't have sk_VertexID support then "vertexidx" already came in as a
|
||||
// vertex attrib.
|
||||
v->codeAppend(R"(
|
||||
@ -253,7 +253,7 @@ void PathInnerTriangulateOp::prePreparePrograms(const GrTessellationShader::Prog
|
||||
// Pass 1: Tessellate the outer curves into the stencil buffer.
|
||||
if (!isLinear) {
|
||||
fTessellator = PathCurveTessellator::Make(args.fArena,
|
||||
args.fCaps->shaderCaps()->infinitySupport());
|
||||
args.fCaps->shaderCaps()->fInfinitySupport);
|
||||
auto* tessShader = GrPathTessellationShader::Make(*args.fCaps->shaderCaps(),
|
||||
args.fArena,
|
||||
fViewMatrix,
|
||||
@ -426,7 +426,7 @@ void PathInnerTriangulateOp::onPrepare(GrOpFlushState* flushState) {
|
||||
fPath.countVerbs());
|
||||
}
|
||||
|
||||
if (!caps.shaderCaps()->vertexIDSupport()) {
|
||||
if (!caps.shaderCaps()->fVertexIDSupport) {
|
||||
constexpr static float kStripOrderIDs[4] = {0, 1, 3, 2};
|
||||
|
||||
SKGPU_DEFINE_STATIC_UNIQUE_KEY(gHullVertexBufferKey);
|
||||
|
@ -32,7 +32,7 @@ public:
|
||||
BoundingBoxShader(SkPMColor4f color, const GrShaderCaps& shaderCaps)
|
||||
: GrGeometryProcessor(kTessellate_BoundingBoxShader_ClassID)
|
||||
, fColor(color) {
|
||||
if (!shaderCaps.vertexIDSupport()) {
|
||||
if (!shaderCaps.fVertexIDSupport) {
|
||||
constexpr static Attribute kUnitCoordAttrib("unitCoord", kFloat2_GrVertexAttribType,
|
||||
SkSLType::kFloat2);
|
||||
this->setVertexAttributesWithImplicitOffsets(&kUnitCoordAttrib, 1);
|
||||
@ -70,7 +70,7 @@ std::unique_ptr<GrGeometryProcessor::ProgramImpl> BoundingBoxShader::makeProgram
|
||||
args.fVaryingHandler->emitAttributes(args.fGeomProc);
|
||||
|
||||
// Vertex shader.
|
||||
if (args.fShaderCaps->vertexIDSupport()) {
|
||||
if (args.fShaderCaps->fVertexIDSupport) {
|
||||
// If we don't have sk_VertexID support then "unitCoord" already came in as a vertex
|
||||
// attrib.
|
||||
args.fVertBuilder->codeAppend(R"(
|
||||
@ -158,10 +158,10 @@ void PathStencilCoverOp::prePreparePrograms(const GrTessellationShader::ProgramA
|
||||
stencilPipeline,
|
||||
stencilSettings);
|
||||
fTessellator = PathCurveTessellator::Make(args.fArena,
|
||||
args.fCaps->shaderCaps()->infinitySupport());
|
||||
args.fCaps->shaderCaps()->fInfinitySupport);
|
||||
} else {
|
||||
fTessellator = PathWedgeTessellator::Make(args.fArena,
|
||||
args.fCaps->shaderCaps()->infinitySupport());
|
||||
args.fCaps->shaderCaps()->fInfinitySupport);
|
||||
}
|
||||
auto* tessShader = GrPathTessellationShader::Make(*args.fCaps->shaderCaps(),
|
||||
args.fArena,
|
||||
@ -304,7 +304,7 @@ void PathStencilCoverOp::onPrepare(GrOpFlushState* flushState) {
|
||||
SkASSERT(pathCount == fPathCount);
|
||||
}
|
||||
|
||||
if (!flushState->caps().shaderCaps()->vertexIDSupport()) {
|
||||
if (!flushState->caps().shaderCaps()->fVertexIDSupport) {
|
||||
constexpr static SkPoint kUnitQuad[4] = {{0,0}, {0,1}, {1,0}, {1,1}};
|
||||
|
||||
SKGPU_DEFINE_STATIC_UNIQUE_KEY(gUnitQuadBufferKey);
|
||||
|
@ -72,7 +72,7 @@ void PathTessellateOp::prepareTessellator(const GrTessellationShader::ProgramArg
|
||||
auto* pipeline = GrTessellationShader::MakePipeline(args, fAAType, std::move(appliedClip),
|
||||
std::move(fProcessors));
|
||||
fTessellator = PathWedgeTessellator::Make(args.fArena,
|
||||
args.fCaps->shaderCaps()->infinitySupport(),
|
||||
args.fCaps->shaderCaps()->fInfinitySupport,
|
||||
fPatchAttribs);
|
||||
auto* tessShader = GrPathTessellationShader::Make(*args.fCaps->shaderCaps(),
|
||||
args.fArena,
|
||||
|
@ -662,7 +662,7 @@ private:
|
||||
///////////////////////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
PathRenderer::CanDrawPath SmallPathRenderer::onCanDrawPath(const CanDrawPathArgs& args) const {
|
||||
if (!args.fCaps->shaderCaps()->shaderDerivativeSupport()) {
|
||||
if (!args.fCaps->shaderCaps()->fShaderDerivativeSupport) {
|
||||
return CanDrawPath::kNo;
|
||||
}
|
||||
// If the shape has no key then we won't get any reuse.
|
||||
|
@ -59,7 +59,7 @@ GrProcessorSet::Analysis StrokeTessellateOp::finalize(const GrCaps& caps,
|
||||
GrClampType clampType) {
|
||||
// Make sure the finalize happens before combining. We might change fNeedsStencil here.
|
||||
SkASSERT(fPathStrokeList.fNext == nullptr);
|
||||
if (!caps.shaderCaps()->infinitySupport()) {
|
||||
if (!caps.shaderCaps()->fInfinitySupport) {
|
||||
// The GPU can't infer curve type based in infinity, so we need to send in an attrib
|
||||
// explicitly stating the curve type.
|
||||
fPatchAttribs |= PatchAttribs::kExplicitCurveType;
|
||||
|
@ -149,12 +149,12 @@ std::unique_ptr<GrGeometryProcessor::ProgramImpl> MiddleOutShader::makeProgramIm
|
||||
return curveType == %g;
|
||||
})", skgpu::tess::kTriangularConicCurveType).c_str());
|
||||
} else {
|
||||
SkASSERT(shaderCaps.infinitySupport());
|
||||
SkASSERT(shaderCaps.fInfinitySupport);
|
||||
v->insertFunction(R"(
|
||||
bool is_conic_curve() { return isinf(p23.w); }
|
||||
bool is_triangular_conic_curve() { return isinf(p23.z); })");
|
||||
}
|
||||
if (shaderCaps.bitManipulationSupport()) {
|
||||
if (shaderCaps.fBitManipulationSupport) {
|
||||
v->insertFunction(R"(
|
||||
float ldexp_portable(float x, float p) {
|
||||
return ldexp(x, int(p));
|
||||
@ -258,7 +258,7 @@ GrPathTessellationShader* GrPathTessellationShader::Make(const GrShaderCaps& sha
|
||||
PatchAttribs attribs) {
|
||||
// We should use explicit curve type when, and only when, there isn't infinity support.
|
||||
// Otherwise the GPU can infer curve type based on infinity.
|
||||
SkASSERT(shaderCaps.infinitySupport() != (attribs & PatchAttribs::kExplicitCurveType));
|
||||
SkASSERT(shaderCaps.fInfinitySupport != (attribs & PatchAttribs::kExplicitCurveType));
|
||||
return arena->make<MiddleOutShader>(shaderCaps, viewMatrix, color, attribs);
|
||||
}
|
||||
|
||||
|
@ -93,7 +93,7 @@ GrStrokeTessellationShader::GrStrokeTessellationShader(const GrShaderCaps& shade
|
||||
, fStroke(stroke) {
|
||||
// We should use explicit curve type when, and only when, there isn't infinity support.
|
||||
// Otherwise the GPU can infer curve type based on infinity.
|
||||
SkASSERT(shaderCaps.infinitySupport() != (attribs & PatchAttribs::kExplicitCurveType));
|
||||
SkASSERT(shaderCaps.fInfinitySupport != (attribs & PatchAttribs::kExplicitCurveType));
|
||||
// pts 0..3 define the stroke as a cubic bezier. If p3.y is infinity, then it's a conic
|
||||
// with w=p3.x.
|
||||
//
|
||||
@ -125,7 +125,7 @@ GrStrokeTessellationShader::GrStrokeTessellationShader(const GrShaderCaps& shade
|
||||
|
||||
this->setInstanceAttributesWithImplicitOffsets(fAttribs.data(), fAttribs.count());
|
||||
SkASSERT(this->instanceStride() == sizeof(SkPoint) * 4 + PatchAttribsStride(fPatchAttribs));
|
||||
if (!shaderCaps.vertexIDSupport()) {
|
||||
if (!shaderCaps.fVertexIDSupport) {
|
||||
constexpr static Attribute kVertexAttrib("edgeID", kFloat_GrVertexAttribType,
|
||||
SkSLType::kFloat);
|
||||
this->setVertexAttributesWithImplicitOffsets(&kVertexAttrib, 1);
|
||||
@ -190,8 +190,8 @@ void GrStrokeTessellationShader::Impl::onEmitCode(EmitArgs& args, GrGPArgs* gpAr
|
||||
// the number of radial segments per radian, Wang's formula, and join type). When there is
|
||||
// vertex ID support, the limit is what can be represented in a uint16; otherwise the limit is
|
||||
// the size of the fallback vertex buffer.
|
||||
float maxEdges = args.fShaderCaps->vertexIDSupport() ? FixedCountStrokes::kMaxEdges
|
||||
: FixedCountStrokes::kMaxEdgesNoVertexIDs;
|
||||
float maxEdges = args.fShaderCaps->fVertexIDSupport ? FixedCountStrokes::kMaxEdges
|
||||
: FixedCountStrokes::kMaxEdgesNoVertexIDs;
|
||||
args.fVertBuilder->defineConstant("NUM_TOTAL_EDGES", maxEdges);
|
||||
|
||||
// Helper functions.
|
||||
@ -312,7 +312,7 @@ void GrStrokeTessellationShader::Impl::onEmitCode(EmitArgs& args, GrGPArgs* gpAr
|
||||
tan1 = float2(-1,0);
|
||||
})");
|
||||
|
||||
if (args.fShaderCaps->vertexIDSupport()) {
|
||||
if (args.fShaderCaps->fVertexIDSupport) {
|
||||
// If we don't have sk_VertexID support then "edgeID" already came in as a vertex attrib.
|
||||
args.fVertBuilder->codeAppend(R"(
|
||||
float edgeID = float(sk_VertexID >> 1);
|
||||
|
@ -158,7 +158,7 @@ void StrokeTessellator::prepare(GrMeshDrawTarget* target,
|
||||
write_fixed_count_patches(std::move(patchWriter), shaderMatrix, pathStrokeList);
|
||||
fVertexCount = FixedCountStrokes::VertexCount(worstCase);
|
||||
|
||||
if (!target->caps().shaderCaps()->vertexIDSupport()) {
|
||||
if (!target->caps().shaderCaps()->fVertexIDSupport) {
|
||||
// Our shader won't be able to use sk_VertexID. Bind a fallback vertex buffer with the IDs
|
||||
// in it instead.
|
||||
fVertexCount = std::min(fVertexCount, 2 * FixedCountStrokes::kMaxEdgesNoVertexIDs);
|
||||
@ -177,7 +177,7 @@ void StrokeTessellator::draw(GrOpFlushState* flushState) const {
|
||||
if (fVertexChunkArray.empty() || fVertexCount <= 0) {
|
||||
return;
|
||||
}
|
||||
if (!flushState->caps().shaderCaps()->vertexIDSupport() &&
|
||||
if (!flushState->caps().shaderCaps()->fVertexIDSupport &&
|
||||
!fVertexBufferIfNoIDSupport) {
|
||||
return;
|
||||
}
|
||||
|
@ -41,15 +41,10 @@ struct ShaderCaps {
|
||||
//
|
||||
// TODO: Remove these accessors
|
||||
//
|
||||
bool shaderDerivativeSupport() const { return fShaderDerivativeSupport; }
|
||||
bool nonsquareMatrixSupport() const { return fNonsquareMatrixSupport; }
|
||||
|
||||
/** Indicates true 32-bit integer support, with unsigned types and bitwise operations */
|
||||
bool integerSupport() const { return fIntegerSupport; }
|
||||
|
||||
/** asinh(), acosh(), atanh() */
|
||||
bool inverseHyperbolicSupport() const { return fInverseHyperbolicSupport; }
|
||||
|
||||
/**
|
||||
* Some helper functions for encapsulating various extensions to read FB Buffer on openglES
|
||||
*
|
||||
@ -63,8 +58,6 @@ struct ShaderCaps {
|
||||
|
||||
const char* fbFetchColorName() const { return fFBFetchColorName; }
|
||||
|
||||
bool flatInterpolationSupport() const { return fFlatInterpolationSupport; }
|
||||
|
||||
bool noperspectiveInterpolationSupport() const { return fNoPerspectiveInterpolationSupport; }
|
||||
|
||||
bool sampleMaskSupport() const { return fSampleMaskSupport; }
|
||||
@ -160,7 +153,7 @@ struct ShaderCaps {
|
||||
// derivatives. If nullptr is returned then no extension needs to be enabled. Before calling
|
||||
// this function, the caller should check that shaderDerivativeSupport exists.
|
||||
const char* shaderDerivativeExtensionString() const {
|
||||
SkASSERT(this->shaderDerivativeSupport());
|
||||
SkASSERT(this->fShaderDerivativeSupport);
|
||||
return fShaderDerivativeExtensionString;
|
||||
}
|
||||
|
||||
@ -196,6 +189,7 @@ struct ShaderCaps {
|
||||
bool fShaderDerivativeSupport = false;
|
||||
bool fIntegerSupport = false;
|
||||
bool fNonsquareMatrixSupport = false;
|
||||
/** asinh(), acosh(), atanh() */
|
||||
bool fInverseHyperbolicSupport = false;
|
||||
bool fFBFetchSupport = false;
|
||||
bool fFBFetchNeedsCustomOutput = false;
|
||||
|
@ -114,7 +114,7 @@ DEF_GPUTEST_FOR_RENDERING_CONTEXTS(ApplyGamma, reporter, ctxInfo) {
|
||||
SkAutoTMalloc<uint32_t> read(kBaseSize.area());
|
||||
|
||||
// We allow more error on GPUs with lower precision shader variables.
|
||||
float error = context->priv().caps()->shaderCaps()->halfIs32Bits() ? 0.5f : 1.2f;
|
||||
float error = context->priv().caps()->shaderCaps()->fHalfIs32Bits ? 0.5f : 1.2f;
|
||||
|
||||
for (auto toSRGB : { false, true }) {
|
||||
sk_sp<SkSurface> dst(SkSurface::MakeRenderTarget(context, SkBudgeted::kNo, ii));
|
||||
|
@ -268,7 +268,7 @@ DEF_GPUTEST_FOR_RENDERING_CONTEXTS(GrMeshTest, reporter, ctxInfo) {
|
||||
int baseVertex = 0;
|
||||
switch (y % 3) {
|
||||
case 0:
|
||||
if (dContext->priv().caps()->shaderCaps()->vertexIDSupport()) {
|
||||
if (dContext->priv().caps()->shaderCaps()->fVertexIDSupport) {
|
||||
break;
|
||||
}
|
||||
[[fallthrough]];
|
||||
|
@ -33,7 +33,7 @@ DEF_GPUTEST(GrPorterDuff, reporter, /*ctxInfo*/) {
|
||||
sk_sp<GrDirectContext> context = GrDirectContext::MakeMock(&mockOptions, GrContextOptions());
|
||||
const GrCaps& caps = *context->priv().getGpu()->caps();
|
||||
|
||||
if (!caps.shaderCaps()->dualSourceBlendingSupport()) {
|
||||
if (!caps.shaderCaps()->fDualSourceBlendingSupport) {
|
||||
SK_ABORT("Null context does not support dual source blending.");
|
||||
}
|
||||
|
||||
@ -91,7 +91,7 @@ public:
|
||||
GrClampType::kAuto));
|
||||
TEST_ASSERT(!analysis.requiresDstTexture() ||
|
||||
(isLCD &&
|
||||
!caps.shaderCaps()->dstReadInShaderSupport() &&
|
||||
!caps.shaderCaps()->fDstReadInShaderSupport &&
|
||||
(SkBlendMode::kSrcOver != xfermode ||
|
||||
!inputColor.isOpaque())));
|
||||
// Porter Duff modes currently only use fixed-function or shader blending, and Ganesh
|
||||
@ -1069,7 +1069,7 @@ DEF_GPUTEST(PorterDuffNoDualSourceBlending, reporter, options) {
|
||||
|
||||
GrProxyProvider* proxyProvider = ctx->priv().proxyProvider();
|
||||
const GrCaps& caps = *ctx->priv().caps();
|
||||
if (caps.shaderCaps()->dualSourceBlendingSupport()) {
|
||||
if (caps.shaderCaps()->fDualSourceBlendingSupport) {
|
||||
SK_ABORT("Mock context failed to honor request for no ARB_blend_func_extended.");
|
||||
}
|
||||
|
||||
|
@ -243,11 +243,11 @@ DEF_GPUTEST_FOR_RENDERING_CONTEXTS(SRGBReadWritePixels, reporter, ctxInfo) {
|
||||
return;
|
||||
}
|
||||
// We allow more error on GPUs with lower precision shader variables.
|
||||
float error = context->priv().caps()->shaderCaps()->halfIs32Bits() ? 0.5f : 1.2f;
|
||||
float error = context->priv().caps()->shaderCaps()->fHalfIs32Bits ? 0.5f : 1.2f;
|
||||
// For the all-sRGB case, we allow a small error only for devices that have
|
||||
// precision variation because the sRGB data gets converted to linear and back in
|
||||
// the shader.
|
||||
float smallError = context->priv().caps()->shaderCaps()->halfIs32Bits() ? 0.0f : 1.f;
|
||||
float smallError = context->priv().caps()->shaderCaps()->fHalfIs32Bits ? 0.0f : 1.f;
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////////////////////
|
||||
// Write sRGB data to a sRGB context - no conversion on the write.
|
||||
|
Loading…
Reference in New Issue
Block a user