diff options
author | joshualitt <joshualitt@chromium.org> | 2015-02-12 14:20:52 -0800 |
---|---|---|
committer | Commit bot <commit-bot@chromium.org> | 2015-02-12 14:20:52 -0800 |
commit | 8072caa80384292858d31ae34b7e19768875866b (patch) | |
tree | 540934943305cb0aa1e73bfa836e260cab8b45b0 /src/gpu/gl | |
parent | b0fb935bd544b0c6f68c692c7e1ee40876184a1a (diff) |
A simple change to move a bunch of stuff out of Gr*Geometry.h
BUG=skia:
Review URL: https://codereview.chromium.org/920863002
Diffstat (limited to 'src/gpu/gl')
-rw-r--r-- | src/gpu/gl/GrGLGeometryProcessor.cpp | 129 | ||||
-rw-r--r-- | src/gpu/gl/GrGLGeometryProcessor.h | 156 | ||||
-rw-r--r-- | src/gpu/gl/GrGLPathProcessor.cpp | 183 | ||||
-rw-r--r-- | src/gpu/gl/GrGLPathProcessor.h | 113 | ||||
-rw-r--r-- | src/gpu/gl/GrGLPrimitiveProcessor.cpp | 75 | ||||
-rw-r--r-- | src/gpu/gl/GrGLPrimitiveProcessor.h | 130 | ||||
-rw-r--r-- | src/gpu/gl/GrGLProgram.cpp | 4 | ||||
-rw-r--r-- | src/gpu/gl/builders/GrGLProgramBuilder.cpp | 7 | ||||
-rw-r--r-- | src/gpu/gl/builders/GrGLProgramBuilder.h | 2 |
9 files changed, 640 insertions, 159 deletions
diff --git a/src/gpu/gl/GrGLGeometryProcessor.cpp b/src/gpu/gl/GrGLGeometryProcessor.cpp new file mode 100644 index 0000000000..a8d020a166 --- /dev/null +++ b/src/gpu/gl/GrGLGeometryProcessor.cpp @@ -0,0 +1,129 @@ +/* + * Copyright 2014 Google Inc. + * + * Use of this source code is governed by a BSD-style license that can be + * found in the LICENSE file. + */ + +#include "GrGLGeometryProcessor.h" + +#include "builders/GrGLProgramBuilder.h" + +void GrGLGeometryProcessor::emitCode(EmitArgs& args) { + GrGLVertexBuilder* vsBuilder = args.fPB->getVertexShaderBuilder(); + GrGPArgs gpArgs; + this->onEmitCode(args, &gpArgs); + vsBuilder->transformToNormalizedDeviceSpace(gpArgs.fPositionVar); +} + +void GrGLGeometryProcessor::emitTransforms(GrGLGPBuilder* pb, + const GrShaderVar& posVar, + const char* localCoords, + const SkMatrix& localMatrix, + const TransformsIn& tin, + TransformsOut* tout) { + GrGLVertexBuilder* vb = pb->getVertexShaderBuilder(); + tout->push_back_n(tin.count()); + fInstalledTransforms.push_back_n(tin.count()); + for (int i = 0; i < tin.count(); i++) { + const ProcCoords& coordTransforms = tin[i]; + fInstalledTransforms[i].push_back_n(coordTransforms.count()); + for (int t = 0; t < coordTransforms.count(); t++) { + SkString strUniName("StageMatrix"); + strUniName.appendf("_%i_%i", i, t); + GrSLType varyingType; + + GrCoordSet coordType = coordTransforms[t]->sourceCoords(); + uint32_t type = coordTransforms[t]->getMatrix().getType(); + if (kLocal_GrCoordSet == coordType) { + type |= localMatrix.getType(); + } + varyingType = SkToBool(SkMatrix::kPerspective_Mask & type) ? kVec3f_GrSLType : + kVec2f_GrSLType; + GrSLPrecision precision = coordTransforms[t]->precision(); + + const char* uniName; + fInstalledTransforms[i][t].fHandle = + pb->addUniform(GrGLProgramBuilder::kVertex_Visibility, + kMat33f_GrSLType, precision, + strUniName.c_str(), + &uniName).toShaderBuilderIndex(); + + SkString strVaryingName("MatrixCoord"); + strVaryingName.appendf("_%i_%i", i, t); + + GrGLVertToFrag v(varyingType); + pb->addVarying(strVaryingName.c_str(), &v, precision); + + SkASSERT(kVec2f_GrSLType == varyingType || kVec3f_GrSLType == varyingType); + SkNEW_APPEND_TO_TARRAY(&(*tout)[i], GrGLProcessor::TransformedCoords, + (SkString(v.fsIn()), varyingType)); + + // varying = matrix * coords (logically) + if (kDevice_GrCoordSet == coordType) { + if (kVec2f_GrSLType == varyingType) { + if (kVec2f_GrSLType == posVar.getType()) { + vb->codeAppendf("%s = (%s * vec3(%s, 1)).xy;", + v.vsOut(), uniName, posVar.c_str()); + } else { + // The brackets here are just to scope the temp variable + vb->codeAppendf("{ vec3 temp = %s * %s;", uniName, posVar.c_str()); + vb->codeAppendf("%s = vec2(temp.x/temp.z, temp.y/temp.z); }", v.vsOut()); + } + } else { + if (kVec2f_GrSLType == posVar.getType()) { + vb->codeAppendf("%s = %s * vec3(%s, 1);", + v.vsOut(), uniName, posVar.c_str()); + } else { + vb->codeAppendf("%s = %s * %s;", v.vsOut(), uniName, posVar.c_str()); + } + } + } else { + if (kVec2f_GrSLType == varyingType) { + vb->codeAppendf("%s = (%s * vec3(%s, 1)).xy;", v.vsOut(), uniName, localCoords); + } else { + vb->codeAppendf("%s = %s * vec3(%s, 1);", v.vsOut(), uniName, localCoords); + } + } + } + } +} + +void +GrGLGeometryProcessor::setTransformData(const GrPrimitiveProcessor& primProc, + const GrGLProgramDataManager& pdman, + int index, + const SkTArray<const GrCoordTransform*, true>& transforms) { + SkSTArray<2, Transform, true>& procTransforms = fInstalledTransforms[index]; + int numTransforms = transforms.count(); + for (int t = 0; t < numTransforms; ++t) { + SkASSERT(procTransforms[t].fHandle.isValid()); + const SkMatrix& transform = GetTransformMatrix(primProc.localMatrix(), *transforms[t]); + if (!procTransforms[t].fCurrentValue.cheapEqualTo(transform)) { + pdman.setSkMatrix(procTransforms[t].fHandle.convertToUniformHandle(), transform); + procTransforms[t].fCurrentValue = transform; + } + } +} + +void GrGLGeometryProcessor::SetupPosition(GrGLVertexBuilder* vsBuilder, + GrGPArgs* gpArgs, + const char* posName, + const SkMatrix& mat, + const char* matName) { + if (mat.isIdentity()) { + gpArgs->fPositionVar.set(kVec2f_GrSLType, "pos2"); + + vsBuilder->codeAppendf("vec2 %s = %s;", gpArgs->fPositionVar.c_str(), posName); + } else if (!mat.hasPerspective()) { + gpArgs->fPositionVar.set(kVec2f_GrSLType, "pos2"); + + vsBuilder->codeAppendf("vec2 %s = vec2(%s * vec3(%s, 1));", + gpArgs->fPositionVar.c_str(), matName, posName); + } else { + gpArgs->fPositionVar.set(kVec3f_GrSLType, "pos3"); + + vsBuilder->codeAppendf("vec3 %s = %s * vec3(%s, 1);", + gpArgs->fPositionVar.c_str(), matName, posName); + } +} diff --git a/src/gpu/gl/GrGLGeometryProcessor.h b/src/gpu/gl/GrGLGeometryProcessor.h index da6c347314..e8b16afe33 100644 --- a/src/gpu/gl/GrGLGeometryProcessor.h +++ b/src/gpu/gl/GrGLGeometryProcessor.h @@ -8,126 +8,10 @@ #ifndef GrGLGeometryProcessor_DEFINED #define GrGLGeometryProcessor_DEFINED -#include "GrGLProcessor.h" +#include "GrGLPrimitiveProcessor.h" -class GrBatchTracker; -class GrFragmentProcessor; -class GrGLGPBuilder; - -class GrGLPrimitiveProcessor { -public: - GrGLPrimitiveProcessor() : fViewMatrixName(NULL) { fViewMatrix = SkMatrix::InvalidMatrix(); } - virtual ~GrGLPrimitiveProcessor() {} - - typedef GrGLProgramDataManager::UniformHandle UniformHandle; - typedef GrGLProcessor::TextureSamplerArray TextureSamplerArray; - - typedef SkSTArray<2, const GrCoordTransform*, true> ProcCoords; - typedef SkSTArray<8, ProcCoords> TransformsIn; - typedef SkSTArray<8, GrGLProcessor::TransformedCoordsArray> TransformsOut; - - struct EmitArgs { - EmitArgs(GrGLGPBuilder* pb, - const GrPrimitiveProcessor& gp, - const GrBatchTracker& bt, - const char* outputColor, - const char* outputCoverage, - const TextureSamplerArray& samplers, - const TransformsIn& transformsIn, - TransformsOut* transformsOut) - : fPB(pb) - , fGP(gp) - , fBT(bt) - , fOutputColor(outputColor) - , fOutputCoverage(outputCoverage) - , fSamplers(samplers) - , fTransformsIn(transformsIn) - , fTransformsOut(transformsOut) {} - GrGLGPBuilder* fPB; - const GrPrimitiveProcessor& fGP; - const GrBatchTracker& fBT; - const char* fOutputColor; - const char* fOutputCoverage; - const TextureSamplerArray& fSamplers; - const TransformsIn& fTransformsIn; - TransformsOut* fTransformsOut; - }; - - /** - * This is similar to emitCode() in the base class, except it takes a full shader builder. - * This allows the effect subclass to emit vertex code. - */ - virtual void emitCode(EmitArgs&) = 0; - - - /** A GrGLPrimitiveProcessor instance can be reused with any GrGLPrimitiveProcessor that - produces the same stage key; this function reads data from a GrGLPrimitiveProcessor and - uploads any uniform variables required by the shaders created in emitCode(). The - GrPrimitiveProcessor parameter is guaranteed to be of the same type that created this - GrGLPrimitiveProcessor and to have an identical processor key as the one that created this - GrGLPrimitiveProcessor. */ - virtual void setData(const GrGLProgramDataManager&, - const GrPrimitiveProcessor&, - const GrBatchTracker&) = 0; - - static SkMatrix GetTransformMatrix(const SkMatrix& localMatrix, const GrCoordTransform&); - -protected: - /** a helper which can setup vertex, constant, or uniform color depending on inputType. - * This function will only do the minimum required to emit the correct shader code. If - * inputType == attribute, then colorAttr must not be NULL. Likewise, if inputType == Uniform - * then colorUniform must not be NULL. - */ - void setupColorPassThrough(GrGLGPBuilder* pb, - GrGPInput inputType, - const char* inputName, - const GrGeometryProcessor::Attribute* colorAttr, - UniformHandle* colorUniform); - - const char* uViewM() const { return fViewMatrixName; } - - /** a helper function to setup the uniform handle for the uniform view matrix */ - void addUniformViewMatrix(GrGLGPBuilder*); - - - /** a helper function to upload a uniform viewmatrix. - * TODO we can remove this function when we have deferred geometry in place - */ - void setUniformViewMatrix(const GrGLProgramDataManager&, - const SkMatrix& viewMatrix); - - class ShaderVarHandle { - public: - bool isValid() const { return fHandle > -1; } - ShaderVarHandle() : fHandle(-1) {} - ShaderVarHandle(int value) : fHandle(value) { SkASSERT(this->isValid()); } - int handle() const { SkASSERT(this->isValid()); return fHandle; } - UniformHandle convertToUniformHandle() { - SkASSERT(this->isValid()); - return GrGLProgramDataManager::UniformHandle::CreateFromUniformIndex(fHandle); - } - - private: - int fHandle; - }; - - struct Transform { - Transform() : fType(kVoid_GrSLType) { fCurrentValue = SkMatrix::InvalidMatrix(); } - ShaderVarHandle fHandle; - SkMatrix fCurrentValue; - GrSLType fType; - }; - - SkSTArray<8, SkSTArray<2, Transform, true> > fInstalledTransforms; - -private: - UniformHandle fViewMatrixUniform; - SkMatrix fViewMatrix; - const char* fViewMatrixName; -}; - -class GrGLPathRendering; class GrGLVertexBuilder; + /** * If a GL effect needs a GrGLFullShaderBuilder* object to emit vertex code, then it must inherit * from this class. Since paths don't have vertices, this class is only meant to be used internally @@ -189,40 +73,4 @@ private: typedef GrGLPrimitiveProcessor INHERITED; }; -class GrGLGpu; - -class GrGLPathProcessor : public GrGLPrimitiveProcessor { -public: - GrGLPathProcessor(const GrPathProcessor&, const GrBatchTracker&); - - static void GenKey(const GrPathProcessor&, - const GrBatchTracker& bt, - const GrGLCaps&, - GrProcessorKeyBuilder* b); - - void emitCode(EmitArgs&) SK_OVERRIDE; - - virtual void emitTransforms(GrGLGPBuilder*, const TransformsIn&, TransformsOut*) = 0; - - virtual void resolveSeparableVaryings(GrGLGpu* gpu, GrGLuint programId) {} - - void setData(const GrGLProgramDataManager&, - const GrPrimitiveProcessor&, - const GrBatchTracker&) SK_OVERRIDE; - - virtual void setTransformData(const GrPrimitiveProcessor&, - int index, - const SkTArray<const GrCoordTransform*, true>& transforms, - GrGLPathRendering*, - GrGLuint programID) = 0; - - virtual void didSetData(GrGLPathRendering*) {} - -private: - UniformHandle fColorUniform; - GrColor fColor; - - typedef GrGLPrimitiveProcessor INHERITED; -}; - #endif diff --git a/src/gpu/gl/GrGLPathProcessor.cpp b/src/gpu/gl/GrGLPathProcessor.cpp new file mode 100644 index 0000000000..3f3e5d9be7 --- /dev/null +++ b/src/gpu/gl/GrGLPathProcessor.cpp @@ -0,0 +1,183 @@ +/* + * Copyright 2013 Google Inc. + * + * Use of this source code is governed by a BSD-style license that can be + * found in the LICENSE file. + */ + +#include "GrGLPathProcessor.h" + +#include "GrPathProcessor.h" +#include "GrGLGpu.h" +#include "GrGLPathRendering.h" + +GrGLPathProcessor::GrGLPathProcessor(const GrPathProcessor&, const GrBatchTracker&) + : fColor(GrColor_ILLEGAL) {} + +void GrGLPathProcessor::emitCode(EmitArgs& args) { + GrGLGPBuilder* pb = args.fPB; + GrGLGPFragmentBuilder* fs = args.fPB->getFragmentShaderBuilder(); + const PathBatchTracker& local = args.fBT.cast<PathBatchTracker>(); + + // emit transforms + this->emitTransforms(args.fPB, args.fTransformsIn, args.fTransformsOut); + + // Setup uniform color + if (kUniform_GrGPInput == local.fInputColorType) { + const char* stagedLocalVarName; + fColorUniform = pb->addUniform(GrGLProgramBuilder::kFragment_Visibility, + kVec4f_GrSLType, + kDefault_GrSLPrecision, + "Color", + &stagedLocalVarName); + fs->codeAppendf("%s = %s;", args.fOutputColor, stagedLocalVarName); + } + + // setup constant solid coverage + if (kAllOnes_GrGPInput == local.fInputCoverageType) { + fs->codeAppendf("%s = vec4(1);", args.fOutputCoverage); + } +} + +void GrGLPathProcessor::GenKey(const GrPathProcessor&, + const GrBatchTracker& bt, + const GrGLCaps&, + GrProcessorKeyBuilder* b) { + const PathBatchTracker& local = bt.cast<PathBatchTracker>(); + b->add32(local.fInputColorType | local.fInputCoverageType << 16); +} + +void GrGLPathProcessor::setData(const GrGLProgramDataManager& pdman, + const GrPrimitiveProcessor& primProc, + const GrBatchTracker& bt) { + const PathBatchTracker& local = bt.cast<PathBatchTracker>(); + if (kUniform_GrGPInput == local.fInputColorType && local.fColor != fColor) { + GrGLfloat c[4]; + GrColorToRGBAFloat(local.fColor, c); + pdman.set4fv(fColorUniform, 1, c); + fColor = local.fColor; + } +} + +/////////////////////////////////////////////////////////////////////////////////////////////////// + +void GrGLLegacyPathProcessor::emitTransforms(GrGLGPBuilder*, const TransformsIn& tin, + TransformsOut* tout) { + tout->push_back_n(tin.count()); + fInstalledTransforms.push_back_n(tin.count()); + for (int i = 0; i < tin.count(); i++) { + const ProcCoords& coordTransforms = tin[i]; + int texCoordIndex = this->addTexCoordSets(coordTransforms.count()); + + // Use the first uniform location as the texcoord index. + fInstalledTransforms[i].push_back_n(1); + fInstalledTransforms[i][0].fHandle = ShaderVarHandle(texCoordIndex); + + SkString name; + for (int t = 0; t < coordTransforms.count(); ++t) { + GrSLType type = coordTransforms[t]->getMatrix().hasPerspective() ? kVec3f_GrSLType : + kVec2f_GrSLType; + + name.printf("%s(gl_TexCoord[%i])", GrGLSLTypeString(type), texCoordIndex++); + SkNEW_APPEND_TO_TARRAY(&(*tout)[i], GrGLProcessor::TransformedCoords, (name, type)); + } + } +} + +void GrGLLegacyPathProcessor::setTransformData( + const GrPrimitiveProcessor& primProc, + int index, + const SkTArray<const GrCoordTransform*, true>& transforms, + GrGLPathRendering* glpr, + GrGLuint) { + // We've hidden the texcoord index in the first entry of the transforms array for each + // effect + int texCoordIndex = fInstalledTransforms[index][0].fHandle.handle(); + for (int t = 0; t < transforms.count(); ++t) { + const SkMatrix& transform = GetTransformMatrix(primProc.localMatrix(), *transforms[t]); + GrGLPathRendering::PathTexGenComponents components = + GrGLPathRendering::kST_PathTexGenComponents; + if (transform.hasPerspective()) { + components = GrGLPathRendering::kSTR_PathTexGenComponents; + } + glpr->enablePathTexGen(texCoordIndex++, components, transform); + } +} + +void GrGLLegacyPathProcessor::didSetData(GrGLPathRendering* glpr) { + glpr->flushPathTexGenSettings(fTexCoordSetCnt); +} + +/////////////////////////////////////////////////////////////////////////////////////////////////// + +void GrGLNormalPathProcessor::emitTransforms(GrGLGPBuilder* pb, const TransformsIn& tin, + TransformsOut* tout) { + tout->push_back_n(tin.count()); + fInstalledTransforms.push_back_n(tin.count()); + for (int i = 0; i < tin.count(); i++) { + const ProcCoords& coordTransforms = tin[i]; + fInstalledTransforms[i].push_back_n(coordTransforms.count()); + for (int t = 0; t < coordTransforms.count(); t++) { + GrSLType varyingType = + coordTransforms[t]->getMatrix().hasPerspective() ? kVec3f_GrSLType : + kVec2f_GrSLType; + + + SkString strVaryingName("MatrixCoord"); + strVaryingName.appendf("_%i_%i", i, t); + GrGLVertToFrag v(varyingType); + pb->addVarying(strVaryingName.c_str(), &v); + SeparableVaryingInfo& varyingInfo = fSeparableVaryingInfos.push_back(); + varyingInfo.fVariable = pb->getFragmentShaderBuilder()->fInputs.back(); + varyingInfo.fLocation = fSeparableVaryingInfos.count() - 1; + varyingInfo.fType = varyingType; + fInstalledTransforms[i][t].fHandle = ShaderVarHandle(varyingInfo.fLocation); + fInstalledTransforms[i][t].fType = varyingType; + + SkNEW_APPEND_TO_TARRAY(&(*tout)[i], GrGLProcessor::TransformedCoords, + (SkString(v.fsIn()), varyingType)); + } + } +} + +void GrGLNormalPathProcessor::resolveSeparableVaryings(GrGLGpu* gpu, GrGLuint programId) { + int count = fSeparableVaryingInfos.count(); + for (int i = 0; i < count; ++i) { + GrGLint location; + GR_GL_CALL_RET(gpu->glInterface(), + location, + GetProgramResourceLocation(programId, + GR_GL_FRAGMENT_INPUT, + fSeparableVaryingInfos[i].fVariable.c_str())); + fSeparableVaryingInfos[i].fLocation = location; + } +} + +void GrGLNormalPathProcessor::setTransformData( + const GrPrimitiveProcessor& primProc, + int index, + const SkTArray<const GrCoordTransform*, true>& coordTransforms, + GrGLPathRendering* glpr, + GrGLuint programID) { + SkSTArray<2, Transform, true>& transforms = fInstalledTransforms[index]; + int numTransforms = transforms.count(); + for (int t = 0; t < numTransforms; ++t) { + SkASSERT(transforms[t].fHandle.isValid()); + const SkMatrix& transform = GetTransformMatrix(primProc.localMatrix(), + *coordTransforms[t]); + if (transforms[t].fCurrentValue.cheapEqualTo(transform)) { + continue; + } + transforms[t].fCurrentValue = transform; + const SeparableVaryingInfo& fragmentInput = + fSeparableVaryingInfos[transforms[t].fHandle.handle()]; + SkASSERT(transforms[t].fType == kVec2f_GrSLType || + transforms[t].fType == kVec3f_GrSLType); + unsigned components = transforms[t].fType == kVec2f_GrSLType ? 2 : 3; + glpr->setProgramPathFragmentInputTransform(programID, + fragmentInput.fLocation, + GR_GL_OBJECT_LINEAR, + components, + transform); + } +} diff --git a/src/gpu/gl/GrGLPathProcessor.h b/src/gpu/gl/GrGLPathProcessor.h new file mode 100644 index 0000000000..368f1f9fcd --- /dev/null +++ b/src/gpu/gl/GrGLPathProcessor.h @@ -0,0 +1,113 @@ +/* + * Copyright 2013 Google Inc. + * + * Use of this source code is governed by a BSD-style license that can be + * found in the LICENSE file. + */ + +#ifndef GrGLPathProcessor_DEFINED +#define GrGLPathProcessor_DEFINED + +#include "GrGLPrimitiveProcessor.h" + +class GrPathProcessor; +class GrGLPathRendering; +class GrGLGpu; + +class GrGLPathProcessor : public GrGLPrimitiveProcessor { +public: + GrGLPathProcessor(const GrPathProcessor&, const GrBatchTracker&); + + static void GenKey(const GrPathProcessor&, + const GrBatchTracker& bt, + const GrGLCaps&, + GrProcessorKeyBuilder* b); + + void emitCode(EmitArgs&) SK_OVERRIDE; + + virtual void emitTransforms(GrGLGPBuilder*, const TransformsIn&, TransformsOut*) = 0; + + virtual void resolveSeparableVaryings(GrGLGpu* gpu, GrGLuint programId) {} + + void setData(const GrGLProgramDataManager&, + const GrPrimitiveProcessor&, + const GrBatchTracker&) SK_OVERRIDE; + + virtual void setTransformData(const GrPrimitiveProcessor&, + int index, + const SkTArray<const GrCoordTransform*, true>& transforms, + GrGLPathRendering*, + GrGLuint programID) = 0; + + virtual void didSetData(GrGLPathRendering*) {} + +private: + UniformHandle fColorUniform; + GrColor fColor; + + typedef GrGLPrimitiveProcessor INHERITED; +}; + +class GrGLLegacyPathProcessor : public GrGLPathProcessor { +public: + GrGLLegacyPathProcessor(const GrPathProcessor& pathProc, const GrBatchTracker& bt, + int maxTexCoords) + : INHERITED(pathProc, bt) + , fTexCoordSetCnt(0) { + SkDEBUGCODE(fMaxTexCoords = maxTexCoords;) + } + + int addTexCoordSets(int count) { + int firstFreeCoordSet = fTexCoordSetCnt; + fTexCoordSetCnt += count; + SkASSERT(fMaxTexCoords >= fTexCoordSetCnt); + return firstFreeCoordSet; + } + + void emitTransforms(GrGLGPBuilder*, const TransformsIn& tin, TransformsOut* tout) SK_OVERRIDE; + + void setTransformData(const GrPrimitiveProcessor& primProc, + int index, + const SkTArray<const GrCoordTransform*, true>& transforms, + GrGLPathRendering* glpr, + GrGLuint) SK_OVERRIDE; + + void didSetData(GrGLPathRendering* glpr) SK_OVERRIDE; + +private: + SkDEBUGCODE(int fMaxTexCoords;) + int fTexCoordSetCnt; + + typedef GrGLPathProcessor INHERITED; +}; + +class GrGLNormalPathProcessor : public GrGLPathProcessor { +public: + GrGLNormalPathProcessor(const GrPathProcessor& pathProc, const GrBatchTracker& bt) + : INHERITED(pathProc, bt) {} + + void emitTransforms(GrGLGPBuilder* pb, const TransformsIn& tin,TransformsOut* tout) SK_OVERRIDE; + + void resolveSeparableVaryings(GrGLGpu* gpu, GrGLuint programId); + + void setTransformData(const GrPrimitiveProcessor& primProc, + int index, + const SkTArray<const GrCoordTransform*, true>& coordTransforms, + GrGLPathRendering* glpr, + GrGLuint programID) SK_OVERRIDE; + +private: + struct SeparableVaryingInfo { + GrSLType fType; + GrGLShaderVar fVariable; + GrGLint fLocation; + }; + + typedef SkSTArray<8, SeparableVaryingInfo, true> SeparableVaryingInfoArray; + + SeparableVaryingInfoArray fSeparableVaryingInfos; + + typedef GrGLPathProcessor INHERITED; +}; + +#endif diff --git a/src/gpu/gl/GrGLPrimitiveProcessor.cpp b/src/gpu/gl/GrGLPrimitiveProcessor.cpp new file mode 100644 index 0000000000..335dc4fe5f --- /dev/null +++ b/src/gpu/gl/GrGLPrimitiveProcessor.cpp @@ -0,0 +1,75 @@ +/* + * Copyright 2014 Google Inc. + * + * Use of this source code is governed by a BSD-style license that can be + * found in the LICENSE file. + */ + +#include "GrGLPrimitiveProcessor.h" + +#include "builders/GrGLProgramBuilder.h" + +SkMatrix GrGLPrimitiveProcessor::GetTransformMatrix(const SkMatrix& localMatrix, + const GrCoordTransform& coordTransform) { + SkMatrix combined; + // We only apply the localmatrix to localcoords + if (kLocal_GrCoordSet == coordTransform.sourceCoords()) { + combined.setConcat(coordTransform.getMatrix(), localMatrix); + } else { + combined = coordTransform.getMatrix(); + } + if (coordTransform.reverseY()) { + // combined.postScale(1,-1); + // combined.postTranslate(0,1); + combined.set(SkMatrix::kMSkewY, + combined[SkMatrix::kMPersp0] - combined[SkMatrix::kMSkewY]); + combined.set(SkMatrix::kMScaleY, + combined[SkMatrix::kMPersp1] - combined[SkMatrix::kMScaleY]); + combined.set(SkMatrix::kMTransY, + combined[SkMatrix::kMPersp2] - combined[SkMatrix::kMTransY]); + } + return combined; +} + +void +GrGLPrimitiveProcessor::setupColorPassThrough(GrGLGPBuilder* pb, + GrGPInput inputType, + const char* outputName, + const GrGeometryProcessor::Attribute* colorAttr, + UniformHandle* colorUniform) { + GrGLGPFragmentBuilder* fs = pb->getFragmentShaderBuilder(); + if (kUniform_GrGPInput == inputType) { + SkASSERT(colorUniform); + const char* stagedLocalVarName; + *colorUniform = pb->addUniform(GrGLProgramBuilder::kFragment_Visibility, + kVec4f_GrSLType, + kDefault_GrSLPrecision, + "Color", + &stagedLocalVarName); + fs->codeAppendf("%s = %s;", outputName, stagedLocalVarName); + } else if (kAttribute_GrGPInput == inputType) { + SkASSERT(colorAttr); + pb->addPassThroughAttribute(colorAttr, outputName); + } else if (kAllOnes_GrGPInput == inputType) { + fs->codeAppendf("%s = vec4(1);", outputName); + } +} + +void GrGLPrimitiveProcessor::addUniformViewMatrix(GrGLGPBuilder* pb) { + fViewMatrixUniform = pb->addUniform(GrGLProgramBuilder::kVertex_Visibility, + kMat33f_GrSLType, kDefault_GrSLPrecision, + "uViewM", + &fViewMatrixName); +} + +void GrGLPrimitiveProcessor::setUniformViewMatrix(const GrGLProgramDataManager& pdman, + const SkMatrix& viewMatrix) { + if (!fViewMatrix.cheapEqualTo(viewMatrix)) { + SkASSERT(fViewMatrixUniform.isValid()); + fViewMatrix = viewMatrix; + + GrGLfloat viewMatrix[3 * 3]; + GrGLGetMatrix<3>(viewMatrix, fViewMatrix); + pdman.setMatrix3f(fViewMatrixUniform, viewMatrix); + } +} diff --git a/src/gpu/gl/GrGLPrimitiveProcessor.h b/src/gpu/gl/GrGLPrimitiveProcessor.h new file mode 100644 index 0000000000..30b1c178cd --- /dev/null +++ b/src/gpu/gl/GrGLPrimitiveProcessor.h @@ -0,0 +1,130 @@ +/* + * Copyright 2013 Google Inc. + * + * Use of this source code is governed by a BSD-style license that can be + * found in the LICENSE file. + */ + +#ifndef GrGLPrimitiveProcessor_DEFINED +#define GrGLPrimitiveProcessor_DEFINED + +#include "GrPrimitiveProcessor.h" +#include "GrGLProcessor.h" + +class GrBatchTracker; +class GrPrimitiveProcessor; +class GrGLGPBuilder; + +class GrGLPrimitiveProcessor { +public: + GrGLPrimitiveProcessor() : fViewMatrixName(NULL) { fViewMatrix = SkMatrix::InvalidMatrix(); } + virtual ~GrGLPrimitiveProcessor() {} + + typedef GrGLProgramDataManager::UniformHandle UniformHandle; + typedef GrGLProcessor::TextureSamplerArray TextureSamplerArray; + + typedef SkSTArray<2, const GrCoordTransform*, true> ProcCoords; + typedef SkSTArray<8, ProcCoords> TransformsIn; + typedef SkSTArray<8, GrGLProcessor::TransformedCoordsArray> TransformsOut; + + struct EmitArgs { + EmitArgs(GrGLGPBuilder* pb, + const GrPrimitiveProcessor& gp, + const GrBatchTracker& bt, + const char* outputColor, + const char* outputCoverage, + const TextureSamplerArray& samplers, + const TransformsIn& transformsIn, + TransformsOut* transformsOut) + : fPB(pb) + , fGP(gp) + , fBT(bt) + , fOutputColor(outputColor) + , fOutputCoverage(outputCoverage) + , fSamplers(samplers) + , fTransformsIn(transformsIn) + , fTransformsOut(transformsOut) {} + GrGLGPBuilder* fPB; + const GrPrimitiveProcessor& fGP; + const GrBatchTracker& fBT; + const char* fOutputColor; + const char* fOutputCoverage; + const TextureSamplerArray& fSamplers; + const TransformsIn& fTransformsIn; + TransformsOut* fTransformsOut; + }; + + /** + * This is similar to emitCode() in the base class, except it takes a full shader builder. + * This allows the effect subclass to emit vertex code. + */ + virtual void emitCode(EmitArgs&) = 0; + + + /** A GrGLPrimitiveProcessor instance can be reused with any GrGLPrimitiveProcessor that + produces the same stage key; this function reads data from a GrGLPrimitiveProcessor and + uploads any uniform variables required by the shaders created in emitCode(). The + GrPrimitiveProcessor parameter is guaranteed to be of the same type that created this + GrGLPrimitiveProcessor and to have an identical processor key as the one that created this + GrGLPrimitiveProcessor. */ + virtual void setData(const GrGLProgramDataManager&, + const GrPrimitiveProcessor&, + const GrBatchTracker&) = 0; + + static SkMatrix GetTransformMatrix(const SkMatrix& localMatrix, const GrCoordTransform&); + +protected: + /** a helper which can setup vertex, constant, or uniform color depending on inputType. + * This function will only do the minimum required to emit the correct shader code. If + * inputType == attribute, then colorAttr must not be NULL. Likewise, if inputType == Uniform + * then colorUniform must not be NULL. + */ + void setupColorPassThrough(GrGLGPBuilder* pb, + GrGPInput inputType, + const char* inputName, + const GrPrimitiveProcessor::Attribute* colorAttr, + UniformHandle* colorUniform); + + const char* uViewM() const { return fViewMatrixName; } + + /** a helper function to setup the uniform handle for the uniform view matrix */ + void addUniformViewMatrix(GrGLGPBuilder*); + + + /** a helper function to upload a uniform viewmatrix. + * TODO we can remove this function when we have deferred geometry in place + */ + void setUniformViewMatrix(const GrGLProgramDataManager&, + const SkMatrix& viewMatrix); + + class ShaderVarHandle { + public: + bool isValid() const { return fHandle > -1; } + ShaderVarHandle() : fHandle(-1) {} + ShaderVarHandle(int value) : fHandle(value) { SkASSERT(this->isValid()); } + int handle() const { SkASSERT(this->isValid()); return fHandle; } + UniformHandle convertToUniformHandle() { + SkASSERT(this->isValid()); + return GrGLProgramDataManager::UniformHandle::CreateFromUniformIndex(fHandle); + } + + private: + int fHandle; + }; + + struct Transform { + Transform() : fType(kVoid_GrSLType) { fCurrentValue = SkMatrix::InvalidMatrix(); } + ShaderVarHandle fHandle; + SkMatrix fCurrentValue; + GrSLType fType; + }; + + SkSTArray<8, SkSTArray<2, Transform, true> > fInstalledTransforms; + +private: + UniformHandle fViewMatrixUniform; + SkMatrix fViewMatrix; + const char* fViewMatrixName; +}; + +#endif diff --git a/src/gpu/gl/GrGLProgram.cpp b/src/gpu/gl/GrGLProgram.cpp index eebcf6b2f3..2f6b784b40 100644 --- a/src/gpu/gl/GrGLProgram.cpp +++ b/src/gpu/gl/GrGLProgram.cpp @@ -11,12 +11,12 @@ #include "GrProcessor.h" #include "GrCoordTransform.h" #include "GrGLGeometryProcessor.h" -#include "GrGLProcessor.h" -#include "GrGLXferProcessor.h" #include "GrGLGpu.h" +#include "GrGLPathProcessor.h" #include "GrGLPathRendering.h" #include "GrGLShaderVar.h" #include "GrGLSL.h" +#include "GrGLXferProcessor.h" #include "GrPipeline.h" #include "GrXferProcessor.h" #include "SkXfermode.h" diff --git a/src/gpu/gl/builders/GrGLProgramBuilder.cpp b/src/gpu/gl/builders/GrGLProgramBuilder.cpp index bb278be395..5a623033fb 100644 --- a/src/gpu/gl/builders/GrGLProgramBuilder.cpp +++ b/src/gpu/gl/builders/GrGLProgramBuilder.cpp @@ -6,11 +6,14 @@ */ #include "GrGLProgramBuilder.h" + +#include "gl/GrGLGeometryProcessor.h" +#include "gl/GrGLGpu.h" +#include "gl/GrGLPathProcessor.h" #include "gl/GrGLProgram.h" #include "gl/GrGLSLPrettyPrint.h" #include "gl/GrGLUniformHandle.h" -#include "../GrGLXferProcessor.h" -#include "../GrGLGpu.h" +#include "gl/GrGLXferProcessor.h" #include "GrCoordTransform.h" #include "GrGLProgramBuilder.h" #include "GrTexture.h" diff --git a/src/gpu/gl/builders/GrGLProgramBuilder.h b/src/gpu/gl/builders/GrGLProgramBuilder.h index a9288cc9b0..37908f9971 100644 --- a/src/gpu/gl/builders/GrGLProgramBuilder.h +++ b/src/gpu/gl/builders/GrGLProgramBuilder.h @@ -13,7 +13,7 @@ #include "GrGLVertexShaderBuilder.h" #include "../GrGLProgramDataManager.h" #include "../GrGLUniformHandle.h" -#include "../GrGLGeometryProcessor.h" +#include "../GrGLPrimitiveProcessor.h" #include "../GrGLXferProcessor.h" #include "../../GrPendingFragmentStage.h" #include "../../GrPipeline.h" |