joshualitt 2014-09-15 11:41:13 -07:00 committed by Commit bot
parent c90e0149ec
commit 249af15fb8
37 changed files with 728 additions and 527 deletions

View File

@ -170,7 +170,7 @@ protected:
GrDrawState* drawState = tt.target()->drawState();
drawState->setVertexAttribs<kAttribs>(2, sizeof(Vertex));
drawState->setGeometryProcessor(effect, 1);
drawState->setGeometryProcessor(effect);
drawState->setRenderTarget(rt);
drawState->setColor(0xff000000);
@ -325,7 +325,7 @@ protected:
GrDrawState* drawState = tt.target()->drawState();
drawState->setVertexAttribs<kAttribs>(2, sizeof(Vertex));
drawState->setGeometryProcessor(effect, 1);
drawState->setGeometryProcessor(effect);
drawState->setRenderTarget(rt);
drawState->setColor(0xff000000);
@ -509,7 +509,7 @@ protected:
GrDrawState* drawState = tt.target()->drawState();
drawState->setVertexAttribs<kAttribs>(2, sizeof(Vertex));
drawState->setGeometryProcessor(effect, 1);
drawState->setGeometryProcessor(effect);
drawState->setRenderTarget(rt);
drawState->setColor(0xff000000);

View File

@ -127,7 +127,6 @@ protected:
return;
}
GrDrawState* drawState = tt.target()->drawState();
drawState->setVertexAttribs<kAttribs>(SK_ARRAY_COUNT(kAttribs), sizeof(SkPoint));
SkMatrix m;
SkPath p;
@ -139,7 +138,7 @@ protected:
if (!effect) {
continue;
}
drawState->addCoverageEffect(effect, 1);
drawState->addCoverageEffect(effect);
drawState->setIdentityViewMatrix();
drawState->setRenderTarget(rt);
drawState->setColor(0xff000000);
@ -193,8 +192,7 @@ protected:
}
GrDrawState* drawState = tt.target()->drawState();
drawState->setVertexAttribs<kAttribs>(SK_ARRAY_COUNT(kAttribs), sizeof(SkPoint));
drawState->addCoverageEffect(effect, 1);
drawState->addCoverageEffect(effect);
drawState->setIdentityViewMatrix();
drawState->setRenderTarget(rt);
drawState->setColor(0xff000000);

View File

@ -136,7 +136,7 @@ protected:
drawState->reset(viewMatrix);
drawState->setRenderTarget(rt);
drawState->setColor(0xffffffff);
drawState->addColorEffect(effect, 1);
drawState->addColorEffect(effect);
tt.target()->drawSimpleRect(renderRect);
x += renderRect.width() + kTestPad;

View File

@ -118,7 +118,7 @@ protected:
drawState->reset(viewMatrix);
drawState->setRenderTarget(rt);
drawState->setColor(0xffffffff);
drawState->addColorEffect(effect, 1);
drawState->addColorEffect(effect);
tt.target()->drawSimpleRect(renderRect);
}
x += renderRect.width() + kTestPad;

View File

@ -31,6 +31,7 @@
'<(skia_include_path)/gpu/GrRenderTarget.h',
'<(skia_include_path)/gpu/GrResourceKey.h',
'<(skia_include_path)/gpu/GrSurface.h',
'<(skia_include_path)/gpu/GrShaderVar.h',
'<(skia_include_path)/gpu/GrTBackendEffectFactory.h',
'<(skia_include_path)/gpu/GrTexture.h',
'<(skia_include_path)/gpu/GrTextureAccess.h',
@ -207,7 +208,7 @@
'<(skia_src_path)/gpu/gl/GrGLDefaultInterface_none.cpp',
'<(skia_src_path)/gpu/gl/GrGLDefines.h',
'<(skia_src_path)/gpu/gl/GrGLEffect.h',
'<(skia_src_path)/gpu/gl/GrGLVertexEffect.h',
'<(skia_src_path)/gpu/gl/GrGLGeometryProcessor.h',
'<(skia_src_path)/gpu/gl/GrGLExtensions.cpp',
'<(skia_src_path)/gpu/gl/GrGLIndexBuffer.cpp',
'<(skia_src_path)/gpu/gl/GrGLIndexBuffer.h',

View File

@ -39,9 +39,6 @@ public:
bool programHasExplicitLocalCoords() const { return fExplicitLocalCoords; }
const int* getVertexAttribIndices() const { return fEffectStage->getVertexAttribIndices(); }
int getVertexAttribIndexCount() const { return fEffectStage->getVertexAttribIndexCount(); }
private:
const GrEffectStage* fEffectStage;
bool fExplicitLocalCoords;

View File

@ -11,14 +11,15 @@
#include "GrColor.h"
#include "GrEffectUnitTest.h"
#include "GrProgramElement.h"
#include "GrShaderVar.h"
#include "GrTextureAccess.h"
#include "GrTypesPriv.h"
#include "SkString.h"
class GrBackendEffectFactory;
class GrContext;
class GrCoordTransform;
/** Provides custom vertex shader, fragment shader, uniform data for a particular stage of the
Ganesh shading pipeline.
Subclasses must have a function that produces a human-readable name:
@ -114,14 +115,10 @@ public:
(To set this value the effect must inherit from GrEffect.) */
bool requiresVertexShader() const { return fRequiresVertexShader; }
int numVertexAttribs() const {
SkASSERT(0 == fVertexAttribTypes.count() || fRequiresVertexShader);
return fVertexAttribTypes.count();
}
GrSLType vertexAttribType(int index) const { return fVertexAttribTypes[index]; }
static const int kMaxVertexAttribs = 2;
typedef SkSTArray<kMaxVertexAttribs, GrShaderVar, true> VertexAttribArray;
const VertexAttribArray& getVertexAttribs() const { return fVertexAttribs; }
void* operator new(size_t size);
void operator delete(void* target);
@ -193,11 +190,11 @@ private:
getFactory()).*/
virtual bool onIsEqual(const GrEffect& other) const = 0;
friend class GrVertexEffect; // to set fRequiresVertexShader and build fVertexAttribTypes.
friend class GrGeometryProcessor; // to set fRequiresVertexShader and build fVertexAttribTypes.
SkSTArray<4, const GrCoordTransform*, true> fCoordTransforms;
SkSTArray<4, const GrTextureAccess*, true> fTextureAccesses;
SkSTArray<kMaxVertexAttribs, GrSLType, true> fVertexAttribTypes;
VertexAttribArray fVertexAttribs;
bool fWillReadDstColor;
bool fWillReadFragmentPosition;
bool fWillUseInputColor;

View File

@ -24,11 +24,9 @@
// when draws are enqueued in the GrInOrderDrawBuffer.
class GrEffectStage {
public:
explicit GrEffectStage(const GrEffect* effect, int attrIndex0 = -1, int attrIndex1 = -1)
explicit GrEffectStage(const GrEffect* effect)
: fEffect(SkRef(effect)) {
fCoordChangeMatrixSet = false;
fVertexAttribIndices[0] = attrIndex0;
fVertexAttribIndices[1] = attrIndex1;
}
GrEffectStage(const GrEffectStage& other) {
@ -37,7 +35,6 @@ public:
fCoordChangeMatrix = other.fCoordChangeMatrix;
}
fEffect.initAndRef(other.fEffect);
memcpy(fVertexAttribIndices, other.fVertexAttribIndices, sizeof(fVertexAttribIndices));
}
static bool AreCompatible(const GrEffectStage& a, const GrEffectStage& b,
@ -133,16 +130,12 @@ public:
const GrEffect* getEffect() const { return fEffect.get(); }
const int* getVertexAttribIndices() const { return fVertexAttribIndices; }
int getVertexAttribIndexCount() const { return fEffect->numVertexAttribs(); }
void convertToPendingExec() { fEffect.convertToPendingExec(); }
private:
bool fCoordChangeMatrixSet;
SkMatrix fCoordChangeMatrix;
GrProgramElementRef<const GrEffect> fEffect;
int fVertexAttribIndices[2];
};
#endif

View File

@ -87,24 +87,26 @@ public:
/**
* Appends an additional color effect to the color computation.
*/
const GrEffect* addColorEffect(const GrEffect* effect, int attr0 = -1, int attr1 = -1) {
const GrEffect* addColorEffect(const GrEffect* effect) {
SkASSERT(effect);
SkASSERT(!effect->requiresVertexShader());
if (!effect->willUseInputColor()) {
fColorStages.reset();
}
SkNEW_APPEND_TO_TARRAY(&fColorStages, GrEffectStage, (effect, attr0, attr1));
SkNEW_APPEND_TO_TARRAY(&fColorStages, GrEffectStage, (effect));
return effect;
}
/**
* Appends an additional coverage effect to the coverage computation.
*/
const GrEffect* addCoverageEffect(const GrEffect* effect, int attr0 = -1, int attr1 = -1) {
const GrEffect* addCoverageEffect(const GrEffect* effect) {
SkASSERT(effect);
SkASSERT(!effect->requiresVertexShader());
if (!effect->willUseInputColor()) {
fCoverageStages.reset();
}
SkNEW_APPEND_TO_TARRAY(&fCoverageStages, GrEffectStage, (effect, attr0, attr1));
SkNEW_APPEND_TO_TARRAY(&fCoverageStages, GrEffectStage, (effect));
return effect;
}

223
include/gpu/GrShaderVar.h Normal file
View File

@ -0,0 +1,223 @@
/*
* Copyright 2014 Google Inc.
*
* Use of this source code is governed by a BSD-style license that can be
* found in the LICENSE file.
*/
#ifndef GrShaderVar_DEFINED
#define GrShaderVar_DEFINED
#include "GrTypesPriv.h"
#include "SkString.h"
class GrShaderVar {
public:
/**
* Early versions of GLSL have Varying and Attribute; those are later
* deprecated, but we still need to know whether a Varying variable
* should be treated as In or Out.
*
* TODO This really shouldn't live here, but until we have c++11, there is really no good way
* to write extensible enums. In reality, only none, out, in, inout, and uniform really
* make sense on this base class
*/
enum TypeModifier {
kNone_TypeModifier,
kOut_TypeModifier,
kIn_TypeModifier,
kInOut_TypeModifier,
kUniform_TypeModifier,
// GL Specific types below
kAttribute_TypeModifier,
kVaryingIn_TypeModifier,
kVaryingOut_TypeModifier
};
enum Precision {
kLow_Precision, // lowp
kMedium_Precision, // mediump
kHigh_Precision, // highp
kDefault_Precision, // Default for the current context. We make
// fragment shaders default to mediump on ES2
// because highp support is not guaranteed (and
// we haven't been motivated to test for it).
// Otherwise, highp.
};
/**
* Defaults to a float with no precision specifier
*/
GrShaderVar()
: fType(kFloat_GrSLType)
, fTypeModifier(kNone_TypeModifier)
, fCount(kNonArray)
, fPrecision(kDefault_Precision) {
}
GrShaderVar(const char* name, GrSLType type, int arrayCount = kNonArray,
Precision precision = kDefault_Precision)
: fType(type)
, fTypeModifier(kNone_TypeModifier)
, fName(name)
, fCount(arrayCount)
, fPrecision(precision) {
SkASSERT(kVoid_GrSLType != type);
}
GrShaderVar(const char* name, GrSLType type, TypeModifier typeModifier,
int arrayCount = kNonArray, Precision precision = kDefault_Precision)
: fType(type)
, fTypeModifier(typeModifier)
, fName(name)
, fCount(arrayCount)
, fPrecision(precision) {
SkASSERT(kVoid_GrSLType != type);
}
/**
* Values for array count that have special meaning. We allow 1-sized arrays.
*/
enum {
kNonArray = 0, // not an array
kUnsizedArray = -1, // an unsized array (declared with [])
};
/**
* Sets as a non-array.
*/
void set(GrSLType type,
TypeModifier typeModifier,
const SkString& name,
Precision precision = kDefault_Precision) {
SkASSERT(kVoid_GrSLType != type);
fType = type;
fTypeModifier = typeModifier;
fName = name;
fCount = kNonArray;
fPrecision = precision;
}
/**
* Sets as a non-array.
*/
void set(GrSLType type,
TypeModifier typeModifier,
const char* name,
Precision precision = kDefault_Precision) {
SkASSERT(kVoid_GrSLType != type);
fType = type;
fTypeModifier = typeModifier;
fName = name;
fCount = kNonArray;
fPrecision = precision;
}
/**
* Set all var options
*/
void set(GrSLType type,
TypeModifier typeModifier,
const SkString& name,
int count,
Precision precision = kDefault_Precision) {
SkASSERT(kVoid_GrSLType != type);
fType = type;
fTypeModifier = typeModifier;
fName = name;
fCount = count;
fPrecision = precision;
}
/**
* Set all var options
*/
void set(GrSLType type,
TypeModifier typeModifier,
const char* name,
int count,
Precision precision = kDefault_Precision) {
SkASSERT(kVoid_GrSLType != type);
fType = type;
fTypeModifier = typeModifier;
fName = name;
fCount = count;
fPrecision = precision;
}
/**
* Is the var an array.
*/
bool isArray() const { return kNonArray != fCount; }
/**
* Is this an unsized array, (i.e. declared with []).
*/
bool isUnsizedArray() const { return kUnsizedArray == fCount; }
/**
* Get the array length of the var.
*/
int getArrayCount() const { return fCount; }
/**
* Set the array length of the var
*/
void setArrayCount(int count) { fCount = count; }
/**
* Set to be a non-array.
*/
void setNonArray() { fCount = kNonArray; }
/**
* Set to be an unsized array.
*/
void setUnsizedArray() { fCount = kUnsizedArray; }
/**
* Access the var name as a writable string
*/
SkString* accessName() { return &fName; }
/**
* Set the var name
*/
void setName(const SkString& n) { fName = n; }
void setName(const char* n) { fName = n; }
/**
* Get the var name.
*/
const SkString& getName() const { return fName; }
/**
* Shortcut for this->getName().c_str();
*/
const char* c_str() const { return this->getName().c_str(); }
/**
* Get the type of the var
*/
GrSLType getType() const { return fType; }
/**
* Set the type of the var
*/
void setType(GrSLType type) { fType = type; }
TypeModifier getTypeModifier() const { return fTypeModifier; }
void setTypeModifier(TypeModifier type) { fTypeModifier = type; }
/**
* Get the precision of the var
*/
Precision getPrecision() const { return fPrecision; }
/**
* Set the precision of the var
*/
void setPrecision(Precision p) { fPrecision = p; }
protected:
GrSLType fType;
TypeModifier fTypeModifier;
SkString fName;
int fCount;
Precision fPrecision;
};
#endif

View File

@ -21,9 +21,9 @@
#include "gl/GrGLEffect.h"
#include "gl/GrGLSL.h"
#include "gl/GrGLVertexEffect.h"
#include "gl/GrGLGeometryProcessor.h"
#include "effects/GrVertexEffect.h"
#include "effects/GrGeometryProcessor.h"
GrAAConvexPathRenderer::GrAAConvexPathRenderer() {
}
@ -504,7 +504,7 @@ static void create_vertices(const SegmentArray& segments,
* Requires shader derivative instruction support.
*/
class QuadEdgeEffect : public GrVertexEffect {
class QuadEdgeEffect : public GrGeometryProcessor {
public:
static GrEffect* Create() {
@ -522,11 +522,13 @@ public:
*validFlags = 0;
}
const GrShaderVar& inQuadEdge() const { return fInQuadEdge; }
virtual const GrBackendEffectFactory& getFactory() const SK_OVERRIDE {
return GrTBackendEffectFactory<QuadEdgeEffect>::getInstance();
}
class GLEffect : public GrGLVertexEffect {
class GLEffect : public GrGLGeometryProcessor {
public:
GLEffect(const GrBackendEffectFactory& factory, const GrDrawEffect&)
: INHERITED (factory) {}
@ -567,10 +569,9 @@ public:
fsBuilder->codeAppendf("\t%s = %s;\n", outputColor,
(GrGLSLExpr4(inputColor) * GrGLSLExpr1("edgeAlpha")).c_str());
const GrShaderVar& inQuadEdge = drawEffect.castEffect<QuadEdgeEffect>().inQuadEdge();
GrGLVertexShaderBuilder* vsBuilder = builder->getVertexShaderBuilder();
const SkString* attr0Name =
vsBuilder->getEffectAttributeName(drawEffect.getVertexAttribIndices()[0]);
vsBuilder->codeAppendf("\t%s = %s;\n", vsName, attr0Name->c_str());
vsBuilder->codeAppendf("\t%s = %s;\n", vsName, inQuadEdge.c_str());
}
static inline void GenKey(const GrDrawEffect&, const GrGLCaps&, GrEffectKeyBuilder*) {}
@ -578,18 +579,22 @@ public:
virtual void setData(const GrGLProgramDataManager&, const GrDrawEffect&) SK_OVERRIDE {}
private:
typedef GrGLVertexEffect INHERITED;
typedef GrGLGeometryProcessor INHERITED;
};
private:
QuadEdgeEffect() {
this->addVertexAttrib(kVec4f_GrSLType);
QuadEdgeEffect()
: fInQuadEdge(this->addVertexAttrib(GrShaderVar("inQuadEdge",
kVec4f_GrSLType,
GrShaderVar::kAttribute_TypeModifier))) {
}
virtual bool onIsEqual(const GrEffect& other) const SK_OVERRIDE {
return true;
}
const GrShaderVar& fInQuadEdge;
GR_DECLARE_EFFECT_TEST;
typedef GrEffect INHERITED;
@ -676,9 +681,8 @@ bool GrAAConvexPathRenderer::onDrawPath(const SkPath& origPath,
drawState->setVertexAttribs<gPathAttribs>(SK_ARRAY_COUNT(gPathAttribs), sizeof(QuadVertex));
static const int kEdgeAttrIndex = 1;
GrEffect* quadEffect = QuadEdgeEffect::Create();
drawState->setGeometryProcessor(quadEffect, kEdgeAttrIndex)->unref();
drawState->setGeometryProcessor(quadEffect)->unref();
GrDrawTarget::AutoReleaseGeometry arg(target, vCount, iCount);
if (!arg.succeeded()) {

View File

@ -990,8 +990,6 @@ bool GrAAHairLinePathRenderer::onDrawPath(const SkPath& path,
}
GrDrawState* drawState = target->drawState();
static const int kEdgeAttrIndex = 1;
// Check devBounds
SkASSERT(check_bounds<BezierVertex>(drawState, devBounds, arg.vertices(),
kVertsPerQuad * quadCnt + kVertsPerQuad * conicCnt));
@ -1002,7 +1000,7 @@ bool GrAAHairLinePathRenderer::onDrawPath(const SkPath& path,
SkASSERT(hairQuadEffect);
GrDrawState::AutoRestoreEffects are(drawState);
target->setIndexSourceToBuffer(fQuadsIndexBuffer);
drawState->setGeometryProcessor(hairQuadEffect, kEdgeAttrIndex)->unref();
drawState->setGeometryProcessor(hairQuadEffect)->unref();
int quads = 0;
while (quads < quadCnt) {
int n = SkTMin(quadCnt - quads, kNumQuadsInIdxBuffer);
@ -1021,7 +1019,7 @@ bool GrAAHairLinePathRenderer::onDrawPath(const SkPath& path,
GrEffect* hairConicEffect = GrConicEffect::Create(kHairlineAA_GrEffectEdgeType,
*target->caps());
SkASSERT(hairConicEffect);
drawState->setGeometryProcessor(hairConicEffect, 1, 2)->unref();
drawState->setGeometryProcessor(hairConicEffect)->unref();
int conics = 0;
while (conics < conicCnt) {
int n = SkTMin(conicCnt - conics, kNumQuadsInIdxBuffer);

View File

@ -9,16 +9,16 @@
#include "GrAARectRenderer.h"
#include "GrGpu.h"
#include "gl/GrGLEffect.h"
#include "gl/GrGLVertexEffect.h"
#include "gl/GrGLGeometryProcessor.h"
#include "GrTBackendEffectFactory.h"
#include "SkColorPriv.h"
#include "effects/GrVertexEffect.h"
#include "effects/GrGeometryProcessor.h"
///////////////////////////////////////////////////////////////////////////////
class GrGLAlignedRectEffect;
// Axis Aligned special case
class GrAlignedRectEffect : public GrVertexEffect {
class GrAlignedRectEffect : public GrGeometryProcessor {
public:
static GrEffect* Create() {
GR_CREATE_STATIC_EFFECT(gAlignedRectEffect, GrAlignedRectEffect, ());
@ -35,11 +35,13 @@ public:
*validFlags = 0;
}
const GrShaderVar& inRect() const { return fInRect; }
virtual const GrBackendEffectFactory& getFactory() const SK_OVERRIDE {
return GrTBackendEffectFactory<GrAlignedRectEffect>::getInstance();
}
class GLEffect : public GrGLVertexEffect {
class GLEffect : public GrGLGeometryProcessor {
public:
GLEffect(const GrBackendEffectFactory& factory, const GrDrawEffect&)
: INHERITED (factory) {}
@ -57,10 +59,9 @@ public:
const char *vsRectName, *fsRectName;
builder->addVarying(kVec4f_GrSLType, "Rect", &vsRectName, &fsRectName);
const GrShaderVar& inRect = drawEffect.castEffect<GrAlignedRectEffect>().inRect();
GrGLVertexShaderBuilder* vsBuilder = builder->getVertexShaderBuilder();
const SkString* attr0Name =
vsBuilder->getEffectAttributeName(drawEffect.getVertexAttribIndices()[0]);
vsBuilder->codeAppendf("\t%s = %s;\n", vsRectName, attr0Name->c_str());
vsBuilder->codeAppendf("\t%s = %s;\n", vsRectName, inRect.c_str());
GrGLFragmentShaderBuilder* fsBuilder = builder->getFragmentShaderBuilder();
// TODO: compute all these offsets, spans, and scales in the VS
@ -96,20 +97,24 @@ public:
virtual void setData(const GrGLProgramDataManager& pdman, const GrDrawEffect&) SK_OVERRIDE {}
private:
typedef GrGLVertexEffect INHERITED;
typedef GrGLGeometryProcessor INHERITED;
};
private:
GrAlignedRectEffect() : GrVertexEffect() {
this->addVertexAttrib(kVec4f_GrSLType);
GrAlignedRectEffect()
: fInRect(this->addVertexAttrib(GrShaderVar("inRect",
kVec4f_GrSLType,
GrShaderVar::kAttribute_TypeModifier))) {
}
const GrShaderVar& fInRect;
virtual bool onIsEqual(const GrEffect&) const SK_OVERRIDE { return true; }
GR_DECLARE_EFFECT_TEST;
typedef GrVertexEffect INHERITED;
typedef GrGeometryProcessor INHERITED;
};
@ -137,7 +142,8 @@ class GrGLRectEffect;
* The munged width and height are stored in a vec2 varying ("WidthHeight")
* with the width in x and the height in y.
*/
class GrRectEffect : public GrVertexEffect {
class GrRectEffect : public GrGeometryProcessor {
public:
static GrEffect* Create() {
GR_CREATE_STATIC_EFFECT(gRectEffect, GrRectEffect, ());
@ -154,11 +160,14 @@ public:
*validFlags = 0;
}
const GrShaderVar& inRectEdge() const { return fInRectEdge; }
const GrShaderVar& inWidthHeight() const { return fInWidthHeight; }
virtual const GrBackendEffectFactory& getFactory() const SK_OVERRIDE {
return GrTBackendEffectFactory<GrRectEffect>::getInstance();
}
class GLEffect : public GrGLVertexEffect {
class GLEffect : public GrGLGeometryProcessor {
public:
GLEffect(const GrBackendEffectFactory& factory, const GrDrawEffect&)
: INHERITED (factory) {}
@ -176,18 +185,17 @@ public:
builder->addVarying(kVec4f_GrSLType, "RectEdge",
&vsRectEdgeName, &fsRectEdgeName);
const GrRectEffect& rectEffect = drawEffect.castEffect<GrRectEffect>();
GrGLVertexShaderBuilder* vsBuilder = builder->getVertexShaderBuilder();
const SkString* attr0Name =
vsBuilder->getEffectAttributeName(drawEffect.getVertexAttribIndices()[0]);
vsBuilder->codeAppendf("\t%s = %s;\n", vsRectEdgeName, attr0Name->c_str());
vsBuilder->codeAppendf("%s = %s;", vsRectEdgeName, rectEffect.inRectEdge().c_str());
// setup the varying for width/2+.5 and height/2+.5
const char *vsWidthHeightName, *fsWidthHeightName;
builder->addVarying(kVec2f_GrSLType, "WidthHeight",
&vsWidthHeightName, &fsWidthHeightName);
const SkString* attr1Name =
vsBuilder->getEffectAttributeName(drawEffect.getVertexAttribIndices()[1]);
vsBuilder->codeAppendf("\t%s = %s;\n", vsWidthHeightName, attr1Name->c_str());
vsBuilder->codeAppendf("%s = %s;",
vsWidthHeightName,
rectEffect.inWidthHeight().c_str());
GrGLFragmentShaderBuilder* fsBuilder = builder->getFragmentShaderBuilder();
// TODO: compute all these offsets, spans, and scales in the VS
@ -230,22 +238,31 @@ public:
virtual void setData(const GrGLProgramDataManager& pdman, const GrDrawEffect&) SK_OVERRIDE {}
private:
typedef GrGLVertexEffect INHERITED;
typedef GrGLGeometryProcessor INHERITED;
};
private:
GrRectEffect() : GrVertexEffect() {
this->addVertexAttrib(kVec4f_GrSLType);
this->addVertexAttrib(kVec2f_GrSLType);
GrRectEffect()
: fInRectEdge(this->addVertexAttrib(GrShaderVar("inRectEdge",
kVec4f_GrSLType,
GrShaderVar::kAttribute_TypeModifier)))
, fInWidthHeight(this->addVertexAttrib(
GrShaderVar("inWidthHeight",
kVec2f_GrSLType,
GrShaderVar::kAttribute_TypeModifier))) {
this->setWillReadFragmentPosition();
}
virtual bool onIsEqual(const GrEffect&) const SK_OVERRIDE { return true; }
const GrShaderVar& fInRectEdge;
const GrShaderVar& fInWidthHeight;
GR_DECLARE_EFFECT_TEST;
typedef GrVertexEffect INHERITED;
typedef GrGeometryProcessor INHERITED;
};
@ -646,9 +663,7 @@ void GrAARectRenderer::shaderFillAARect(GrGpu* gpu,
RectVertex* verts = reinterpret_cast<RectVertex*>(geo.vertices());
GrEffect* effect = GrRectEffect::Create();
static const int kRectAttrIndex = 1;
static const int kWidthIndex = 2;
drawState->setGeometryProcessor(effect, kRectAttrIndex, kWidthIndex)->unref();
drawState->setGeometryProcessor(effect)->unref();
for (int i = 0; i < 4; ++i) {
verts[i].fCenter = center;
@ -696,8 +711,7 @@ void GrAARectRenderer::shaderFillAlignedAARect(GrGpu* gpu,
AARectVertex* verts = reinterpret_cast<AARectVertex*>(geo.vertices());
GrEffect* effect = GrAlignedRectEffect::Create();
static const int kOffsetIndex = 1;
drawState->setGeometryProcessor(effect, kOffsetIndex)->unref();
drawState->setGeometryProcessor(effect)->unref();
SkRect devRect;
combinedMatrix.mapRect(&devRect, rect);

View File

@ -30,9 +30,6 @@
SK_CONF_DECLARE(bool, c_DumpFontCache, "gpu.dumpFontCache", false,
"Dump the contents of the font cache before every purge.");
static const int kGlyphCoordsNoColorAttributeIndex = 1;
static const int kGlyphCoordsWithColorAttributeIndex = 2;
namespace {
// position + texture coord
extern const GrVertexAttrib gTextVertexAttribs[] = {
@ -106,9 +103,7 @@ void GrBitmapTextContext::flushGlyphs() {
}
// This effect could be stored with one of the cache objects (atlas?)
int coordsIdx = drawState->hasColorVertexAttribute() ? kGlyphCoordsWithColorAttributeIndex :
kGlyphCoordsNoColorAttributeIndex;
drawState->setGeometryProcessor(fCachedEffect.get(), coordsIdx);
drawState->setGeometryProcessor(fCachedEffect.get());
SkASSERT(fStrike);
switch (fStrike->getMaskFormat()) {
// Color bitmap text

View File

@ -28,9 +28,6 @@
SK_CONF_DECLARE(bool, c_DumpFontCache, "gpu.dumpFontCache", false,
"Dump the contents of the font cache before every purge.");
static const int kGlyphCoordsNoColorAttributeIndex = 1;
static const int kGlyphCoordsWithColorAttributeIndex = 2;
static const int kSmallDFFontSize = 32;
static const int kSmallDFFontLimit = 32;
static const int kMediumDFFontSize = 64;
@ -196,9 +193,7 @@ void GrDistanceFieldTextContext::flushGlyphs() {
this->setupCoverageEffect(filteredColor);
// Effects could be stored with one of the cache objects (atlas?)
int coordsIdx = drawState->hasColorVertexAttribute() ? kGlyphCoordsWithColorAttributeIndex :
kGlyphCoordsNoColorAttributeIndex;
drawState->addCoverageEffect(fCachedEffect.get(), coordsIdx);
drawState->setGeometryProcessor(fCachedEffect.get());
// Set draw state
if (fUseLCDText) {

View File

@ -180,10 +180,11 @@ public:
* but is never put in the color processing pipeline.
*/
const GrEffect* setGeometryProcessor(const GrEffect* effect, int attr0 = -1, int attr1 = -1) {
const GrEffect* setGeometryProcessor(const GrEffect* effect) {
SkASSERT(effect);
SkASSERT(effect->requiresVertexShader());
SkASSERT(!this->hasGeometryProcessor());
fGeometryProcessor.reset(new GrEffectStage(effect, attr0, attr1));
fGeometryProcessor.reset(new GrEffectStage(effect));
this->invalidateOptState();
return effect;
}
@ -208,16 +209,18 @@ public:
/// the color / coverage distinction.
////
const GrEffect* addColorEffect(const GrEffect* effect, int attr0 = -1, int attr1 = -1) {
const GrEffect* addColorEffect(const GrEffect* effect) {
SkASSERT(effect);
SkNEW_APPEND_TO_TARRAY(&fColorStages, GrEffectStage, (effect, attr0, attr1));
SkASSERT(!effect->requiresVertexShader());
SkNEW_APPEND_TO_TARRAY(&fColorStages, GrEffectStage, (effect));
this->invalidateOptState();
return effect;
}
const GrEffect* addCoverageEffect(const GrEffect* effect, int attr0 = -1, int attr1 = -1) {
const GrEffect* addCoverageEffect(const GrEffect* effect) {
SkASSERT(effect);
SkNEW_APPEND_TO_TARRAY(&fCoverageStages, GrEffectStage, (effect, attr0, attr1));
SkASSERT(!effect->requiresVertexShader());
SkNEW_APPEND_TO_TARRAY(&fCoverageStages, GrEffectStage, (effect));
this->invalidateOptState();
return effect;
}

View File

@ -11,7 +11,7 @@
#include "GrEffect.h"
#include "gl/GrGLEffect.h"
#include "gl/GrGLSL.h"
#include "gl/GrGLVertexEffect.h"
#include "gl/GrGLGeometryProcessor.h"
#include "GrTBackendEffectFactory.h"
#include "GrDrawState.h"
@ -22,7 +22,7 @@
#include "SkStrokeRec.h"
#include "SkTLazy.h"
#include "effects/GrVertexEffect.h"
#include "effects/GrGeometryProcessor.h"
#include "effects/GrRRectEffect.h"
namespace {
@ -60,7 +60,7 @@ inline bool circle_stays_circle(const SkMatrix& m) {
* specified as offset_x, offset_y (both from center point), outer radius and inner radius.
*/
class CircleEdgeEffect : public GrVertexEffect {
class CircleEdgeEffect : public GrGeometryProcessor {
public:
static GrEffect* Create(bool stroke) {
GR_CREATE_STATIC_EFFECT(gCircleStrokeEdge, CircleEdgeEffect, (true));
@ -80,6 +80,8 @@ public:
*validFlags = 0;
}
const GrShaderVar& inCircleEdge() const { return fInCircleEdge; }
virtual const GrBackendEffectFactory& getFactory() const SK_OVERRIDE {
return GrTBackendEffectFactory<CircleEdgeEffect>::getInstance();
}
@ -90,7 +92,7 @@ public:
inline bool isStroked() const { return fStroke; }
class GLEffect : public GrGLVertexEffect {
class GLEffect : public GrGLGeometryProcessor {
public:
GLEffect(const GrBackendEffectFactory& factory, const GrDrawEffect&)
: INHERITED (factory) {}
@ -106,10 +108,8 @@ public:
const char *vsName, *fsName;
builder->addVarying(kVec4f_GrSLType, "CircleEdge", &vsName, &fsName);
GrGLVertexShaderBuilder* vsBuilder = builder->getVertexShaderBuilder();
const SkString* attr0Name =
vsBuilder->getEffectAttributeName(drawEffect.getVertexAttribIndices()[0]);
vsBuilder->codeAppendf("\t%s = %s;\n", vsName, attr0Name->c_str());
GrGLVertexShaderBuilder* vsBuilder = builder->getVertexShaderBuilder();;
vsBuilder->codeAppendf("\t%s = %s;\n", vsName, circleEffect.inCircleEdge().c_str());
GrGLFragmentShaderBuilder* fsBuilder = builder->getFragmentShaderBuilder();
fsBuilder->codeAppendf("\tfloat d = length(%s.xy);\n", fsName);
@ -132,13 +132,16 @@ public:
virtual void setData(const GrGLProgramDataManager&, const GrDrawEffect&) SK_OVERRIDE {}
private:
typedef GrGLVertexEffect INHERITED;
typedef GrGLGeometryProcessor INHERITED;
};
private:
CircleEdgeEffect(bool stroke) : GrVertexEffect() {
this->addVertexAttrib(kVec4f_GrSLType);
CircleEdgeEffect(bool stroke)
: fInCircleEdge(this->addVertexAttrib(
GrShaderVar("inCircleEdge",
kVec4f_GrSLType,
GrShaderVar::kAttribute_TypeModifier))) {
fStroke = stroke;
}
@ -147,11 +150,12 @@ private:
return cee.fStroke == fStroke;
}
const GrShaderVar& fInCircleEdge;
bool fStroke;
GR_DECLARE_EFFECT_TEST;
typedef GrVertexEffect INHERITED;
typedef GrGeometryProcessor INHERITED;
};
GR_DEFINE_EFFECT_TEST(CircleEdgeEffect);
@ -173,7 +177,7 @@ GrEffect* CircleEdgeEffect::TestCreate(SkRandom* random,
* We are using an implicit function of x^2/a^2 + y^2/b^2 - 1 = 0.
*/
class EllipseEdgeEffect : public GrVertexEffect {
class EllipseEdgeEffect : public GrGeometryProcessor {
public:
static GrEffect* Create(bool stroke) {
GR_CREATE_STATIC_EFFECT(gEllipseStrokeEdge, EllipseEdgeEffect, (true));
@ -201,9 +205,12 @@ public:
static const char* Name() { return "EllipseEdge"; }
const GrShaderVar& inEllipseOffset() const { return fInEllipseOffset; }
const GrShaderVar& inEllipseRadii() const { return fInEllipseRadii; }
inline bool isStroked() const { return fStroke; }
class GLEffect : public GrGLVertexEffect {
class GLEffect : public GrGLGeometryProcessor {
public:
GLEffect(const GrBackendEffectFactory& factory, const GrDrawEffect&)
: INHERITED (factory) {}
@ -223,14 +230,11 @@ public:
builder->addVarying(kVec2f_GrSLType, "EllipseOffsets", &vsOffsetName, &fsOffsetName);
GrGLVertexShaderBuilder* vsBuilder = builder->getVertexShaderBuilder();
const SkString* attr0Name =
vsBuilder->getEffectAttributeName(drawEffect.getVertexAttribIndices()[0]);
vsBuilder->codeAppendf("\t%s = %s;\n", vsOffsetName, attr0Name->c_str());
vsBuilder->codeAppendf("%s = %s;", vsOffsetName,
ellipseEffect.inEllipseOffset().c_str());
builder->addVarying(kVec4f_GrSLType, "EllipseRadii", &vsRadiiName, &fsRadiiName);
const SkString* attr1Name =
vsBuilder->getEffectAttributeName(drawEffect.getVertexAttribIndices()[1]);
vsBuilder->codeAppendf("\t%s = %s;\n", vsRadiiName, attr1Name->c_str());
vsBuilder->codeAppendf("%s = %s;", vsRadiiName, ellipseEffect.inEllipseRadii().c_str());
// for outer curve
GrGLFragmentShaderBuilder* fsBuilder = builder->getFragmentShaderBuilder();
@ -266,13 +270,19 @@ public:
}
private:
typedef GrGLVertexEffect INHERITED;
typedef GrGLGeometryProcessor INHERITED;
};
private:
EllipseEdgeEffect(bool stroke) : GrVertexEffect() {
this->addVertexAttrib(kVec2f_GrSLType);
this->addVertexAttrib(kVec4f_GrSLType);
EllipseEdgeEffect(bool stroke)
: fInEllipseOffset(this->addVertexAttrib(
GrShaderVar("inEllipseOffset",
kVec2f_GrSLType,
GrShaderVar::kAttribute_TypeModifier)))
, fInEllipseRadii(this->addVertexAttrib(
GrShaderVar("inEllipseRadii",
kVec4f_GrSLType,
GrShaderVar::kAttribute_TypeModifier))) {
fStroke = stroke;
}
@ -281,11 +291,13 @@ private:
return eee.fStroke == fStroke;
}
const GrShaderVar& fInEllipseOffset;
const GrShaderVar& fInEllipseRadii;
bool fStroke;
GR_DECLARE_EFFECT_TEST;
typedef GrVertexEffect INHERITED;
typedef GrGeometryProcessor INHERITED;
};
GR_DEFINE_EFFECT_TEST(EllipseEdgeEffect);
@ -308,7 +320,7 @@ GrEffect* EllipseEdgeEffect::TestCreate(SkRandom* random,
* The result is device-independent and can be used with any affine matrix.
*/
class DIEllipseEdgeEffect : public GrVertexEffect {
class DIEllipseEdgeEffect : public GrGeometryProcessor {
public:
enum Mode { kStroke = 0, kHairline, kFill };
@ -342,9 +354,12 @@ public:
static const char* Name() { return "DIEllipseEdge"; }
const GrShaderVar& inEllipseOffsets0() const { return fInEllipseOffsets0; }
const GrShaderVar& inEllipseOffsets1() const { return fInEllipseOffsets1; }
inline Mode getMode() const { return fMode; }
class GLEffect : public GrGLVertexEffect {
class GLEffect : public GrGLGeometryProcessor {
public:
GLEffect(const GrBackendEffectFactory& factory, const GrDrawEffect&)
: INHERITED (factory) {}
@ -363,15 +378,13 @@ public:
&vsOffsetName0, &fsOffsetName0);
GrGLVertexShaderBuilder* vsBuilder = builder->getVertexShaderBuilder();
const SkString* attr0Name =
vsBuilder->getEffectAttributeName(drawEffect.getVertexAttribIndices()[0]);
vsBuilder->codeAppendf("\t%s = %s;\n", vsOffsetName0, attr0Name->c_str());
vsBuilder->codeAppendf("%s = %s;", vsOffsetName0,
ellipseEffect.inEllipseOffsets0().c_str());
const char *vsOffsetName1, *fsOffsetName1;
builder->addVarying(kVec2f_GrSLType, "EllipseOffsets1",
&vsOffsetName1, &fsOffsetName1);
const SkString* attr1Name =
vsBuilder->getEffectAttributeName(drawEffect.getVertexAttribIndices()[1]);
vsBuilder->codeAppendf("\t%s = %s;\n", vsOffsetName1, attr1Name->c_str());
vsBuilder->codeAppendf("\t%s = %s;\n", vsOffsetName1,
ellipseEffect.inEllipseOffsets1().c_str());
GrGLFragmentShaderBuilder* fsBuilder = builder->getFragmentShaderBuilder();
SkAssertResult(fsBuilder->enableFeature(
@ -426,13 +439,19 @@ public:
}
private:
typedef GrGLVertexEffect INHERITED;
typedef GrGLGeometryProcessor INHERITED;
};
private:
DIEllipseEdgeEffect(Mode mode) : GrVertexEffect() {
this->addVertexAttrib(kVec2f_GrSLType);
this->addVertexAttrib(kVec2f_GrSLType);
DIEllipseEdgeEffect(Mode mode)
: fInEllipseOffsets0(this->addVertexAttrib(
GrShaderVar("inEllipseOffsets0",
kVec2f_GrSLType,
GrShaderVar::kAttribute_TypeModifier)))
, fInEllipseOffsets1(this->addVertexAttrib(
GrShaderVar("inEllipseOffsets1",
kVec2f_GrSLType,
GrShaderVar::kAttribute_TypeModifier))) {
fMode = mode;
}
@ -441,11 +460,13 @@ private:
return eee.fMode == fMode;
}
const GrShaderVar& fInEllipseOffsets0;
const GrShaderVar& fInEllipseOffsets1;
Mode fMode;
GR_DECLARE_EFFECT_TEST;
typedef GrVertexEffect INHERITED;
typedef GrGeometryProcessor INHERITED;
};
GR_DEFINE_EFFECT_TEST(DIEllipseEdgeEffect);
@ -552,8 +573,7 @@ void GrOvalRenderer::drawCircle(GrDrawTarget* target,
}
GrEffect* effect = CircleEdgeEffect::Create(isStrokeOnly && innerRadius > 0);
static const int kCircleEdgeAttrIndex = 1;
drawState->setGeometryProcessor(effect, kCircleEdgeAttrIndex)->unref();
drawState->setGeometryProcessor(effect)->unref();
// The radii are outset for two reasons. First, it allows the shader to simply perform
// clamp(distance-to-center - radius, 0, 1). Second, the outer radius is used to compute the
@ -694,9 +714,7 @@ bool GrOvalRenderer::drawEllipse(GrDrawTarget* target,
GrEffect* effect = EllipseEdgeEffect::Create(isStrokeOnly &&
innerXRadius > 0 && innerYRadius > 0);
static const int kEllipseCenterAttrIndex = 1;
static const int kEllipseEdgeAttrIndex = 2;
drawState->setGeometryProcessor(effect, kEllipseCenterAttrIndex, kEllipseEdgeAttrIndex)->unref();
drawState->setGeometryProcessor(effect)->unref();
// Compute the reciprocals of the radii here to save time in the shader
SkScalar xRadRecip = SkScalarInvert(xRadius);
@ -812,10 +830,7 @@ bool GrOvalRenderer::drawDIEllipse(GrDrawTarget* target,
GrEffect* effect = DIEllipseEdgeEffect::Create(mode);
static const int kEllipseOuterOffsetAttrIndex = 1;
static const int kEllipseInnerOffsetAttrIndex = 2;
drawState->setGeometryProcessor(effect, kEllipseOuterOffsetAttrIndex,
kEllipseInnerOffsetAttrIndex)->unref();
drawState->setGeometryProcessor(effect)->unref();
// This expands the outer rect so that after CTM we end up with a half-pixel border
SkScalar a = vm[SkMatrix::kMScaleX];
@ -1062,8 +1077,7 @@ bool GrOvalRenderer::drawRRect(GrDrawTarget* target, GrContext* context, bool us
isStrokeOnly = (isStrokeOnly && innerRadius >= 0);
GrEffect* effect = CircleEdgeEffect::Create(isStrokeOnly);
static const int kCircleEdgeAttrIndex = 1;
drawState->setGeometryProcessor(effect, kCircleEdgeAttrIndex)->unref();
drawState->setGeometryProcessor(effect)->unref();
// The radii are outset for two reasons. First, it allows the shader to simply perform
// clamp(distance-to-center - radius, 0, 1). Second, the outer radius is used to compute the
@ -1166,11 +1180,7 @@ bool GrOvalRenderer::drawRRect(GrDrawTarget* target, GrContext* context, bool us
EllipseVertex* verts = reinterpret_cast<EllipseVertex*>(geo.vertices());
GrEffect* effect = EllipseEdgeEffect::Create(isStrokeOnly);
static const int kEllipseOffsetAttrIndex = 1;
static const int kEllipseRadiiAttrIndex = 2;
drawState->setGeometryProcessor(effect,
kEllipseOffsetAttrIndex,
kEllipseRadiiAttrIndex)->unref();
drawState->setGeometryProcessor(effect)->unref();
// Compute the reciprocals of the radii here to save time in the shader
SkScalar xRadRecip = SkScalarInvert(xRadius);

View File

@ -93,26 +93,28 @@ bool GrRODrawState::validateVertexAttribs() const {
// make sure that any attribute indices have the correct binding type, that the attrib
// type and effect's shader lang type are compatible, and that attributes shared by
// multiple effects use the same shader lang type.
const int* attributeIndices = stage.getVertexAttribIndices();
int numAttributes = stage.getVertexAttribIndexCount();
for (int i = 0; i < numAttributes; ++i) {
int attribIndex = attributeIndices[i];
if (attribIndex >= fVACount ||
kEffect_GrVertexAttribBinding != fVAPtr[attribIndex].fBinding) {
return false;
}
const GrEffect::VertexAttribArray& s = effect->getVertexAttribs();
GrSLType effectSLType = effect->vertexAttribType(i);
GrVertexAttribType attribType = fVAPtr[attribIndex].fType;
int effectIndex = 0;
for (int index = 0; index < fVACount; index++) {
if (kEffect_GrVertexAttribBinding != fVAPtr[index].fBinding) {
// we only care about effect bindings
continue;
}
SkASSERT(effectIndex < s.count());
GrSLType effectSLType = s[effectIndex].getType();
GrVertexAttribType attribType = fVAPtr[index].fType;
int slVecCount = GrSLTypeVectorCount(effectSLType);
int attribVecCount = GrVertexAttribTypeVectorCount(attribType);
if (slVecCount != attribVecCount ||
(static_cast<GrSLType>(-1) != slTypes[attribIndex] &&
slTypes[attribIndex] != effectSLType)) {
(static_cast<GrSLType>(-1) != slTypes[index] && slTypes[index] != effectSLType)) {
return false;
}
slTypes[attribIndex] = effectSLType;
slTypes[index] = effectSLType;
effectIndex++;
}
// Make sure all attributes are consumed and we were able to find everything
SkASSERT(s.count() == effectIndex);
}
return true;

View File

@ -10,10 +10,10 @@
#include "gl/GrGLEffect.h"
#include "gl/GrGLSL.h"
#include "gl/GrGLVertexEffect.h"
#include "gl/GrGLGeometryProcessor.h"
#include "GrTBackendEffectFactory.h"
class GrGLConicEffect : public GrGLVertexEffect {
class GrGLConicEffect : public GrGLGeometryProcessor {
public:
GrGLConicEffect(const GrBackendEffectFactory&, const GrDrawEffect&);
@ -32,7 +32,7 @@ public:
private:
GrEffectEdgeType fEdgeType;
typedef GrGLVertexEffect INHERITED;
typedef GrGLGeometryProcessor INHERITED;
};
GrGLConicEffect::GrGLConicEffect(const GrBackendEffectFactory& factory,
@ -54,10 +54,9 @@ void GrGLConicEffect::emitCode(GrGLFullProgramBuilder* builder,
builder->addVarying(kVec4f_GrSLType, "ConicCoeffs",
&vsName, &fsName);
const GrShaderVar& inConicCoeffs = drawEffect.castEffect<GrConicEffect>().inConicCoeffs();
GrGLVertexShaderBuilder* vsBuilder = builder->getVertexShaderBuilder();
const SkString* attr0Name =
vsBuilder->getEffectAttributeName(drawEffect.getVertexAttribIndices()[0]);
vsBuilder->codeAppendf("%s = %s;", vsName, attr0Name->c_str());
vsBuilder->codeAppendf("%s = %s;", vsName, inConicCoeffs.c_str());
GrGLFragmentShaderBuilder* fsBuilder = builder->getFragmentShaderBuilder();
fsBuilder->codeAppend("float edgeAlpha;");
@ -135,9 +134,11 @@ const GrBackendEffectFactory& GrConicEffect::getFactory() const {
return GrTBackendEffectFactory<GrConicEffect>::getInstance();
}
GrConicEffect::GrConicEffect(GrEffectEdgeType edgeType) : GrVertexEffect() {
this->addVertexAttrib(kVec4f_GrSLType);
fEdgeType = edgeType;
GrConicEffect::GrConicEffect(GrEffectEdgeType edgeType)
: fEdgeType(edgeType)
, fInConicCoeffs(this->addVertexAttrib(GrShaderVar("inConicCoeffs",
kVec4f_GrSLType,
GrShaderVar::kAttribute_TypeModifier))) {
}
bool GrConicEffect::onIsEqual(const GrEffect& other) const {
@ -166,7 +167,7 @@ GrEffect* GrConicEffect::TestCreate(SkRandom* random,
// Quad
//////////////////////////////////////////////////////////////////////////////
class GrGLQuadEffect : public GrGLVertexEffect {
class GrGLQuadEffect : public GrGLGeometryProcessor {
public:
GrGLQuadEffect(const GrBackendEffectFactory&, const GrDrawEffect&);
@ -185,7 +186,7 @@ public:
private:
GrEffectEdgeType fEdgeType;
typedef GrGLVertexEffect INHERITED;
typedef GrGLGeometryProcessor INHERITED;
};
GrGLQuadEffect::GrGLQuadEffect(const GrBackendEffectFactory& factory,
@ -206,9 +207,8 @@ void GrGLQuadEffect::emitCode(GrGLFullProgramBuilder* builder,
builder->addVarying(kVec4f_GrSLType, "HairQuadEdge", &vsName, &fsName);
GrGLVertexShaderBuilder* vsBuilder = builder->getVertexShaderBuilder();
const SkString* attrName =
vsBuilder->getEffectAttributeName(drawEffect.getVertexAttribIndices()[0]);
vsBuilder->codeAppendf("%s = %s;", vsName, attrName->c_str());
const GrShaderVar& inHairQuadEdge = drawEffect.castEffect<GrQuadEffect>().inHairQuadEdge();
vsBuilder->codeAppendf("%s = %s;", vsName, inHairQuadEdge.c_str());
GrGLFragmentShaderBuilder* fsBuilder = builder->getFragmentShaderBuilder();
fsBuilder->codeAppendf("float edgeAlpha;");
@ -272,9 +272,11 @@ const GrBackendEffectFactory& GrQuadEffect::getFactory() const {
return GrTBackendEffectFactory<GrQuadEffect>::getInstance();
}
GrQuadEffect::GrQuadEffect(GrEffectEdgeType edgeType) : GrVertexEffect() {
this->addVertexAttrib(kVec4f_GrSLType);
fEdgeType = edgeType;
GrQuadEffect::GrQuadEffect(GrEffectEdgeType edgeType)
: fEdgeType(edgeType)
, fInHairQuadEdge(this->addVertexAttrib(GrShaderVar("inCubicCoeffs",
kVec4f_GrSLType,
GrShaderVar::kAttribute_TypeModifier))) {
}
bool GrQuadEffect::onIsEqual(const GrEffect& other) const {
@ -303,7 +305,7 @@ GrEffect* GrQuadEffect::TestCreate(SkRandom* random,
// Cubic
//////////////////////////////////////////////////////////////////////////////
class GrGLCubicEffect : public GrGLVertexEffect {
class GrGLCubicEffect : public GrGLGeometryProcessor {
public:
GrGLCubicEffect(const GrBackendEffectFactory&, const GrDrawEffect&);
@ -322,7 +324,7 @@ public:
private:
GrEffectEdgeType fEdgeType;
typedef GrGLVertexEffect INHERITED;
typedef GrGLGeometryProcessor INHERITED;
};
GrGLCubicEffect::GrGLCubicEffect(const GrBackendEffectFactory& factory,
@ -345,9 +347,8 @@ void GrGLCubicEffect::emitCode(GrGLFullProgramBuilder* builder,
&vsName, &fsName, GrGLShaderVar::kHigh_Precision);
GrGLVertexShaderBuilder* vsBuilder = builder->getVertexShaderBuilder();
const SkString* attr0Name =
vsBuilder->getEffectAttributeName(drawEffect.getVertexAttribIndices()[0]);
vsBuilder->codeAppendf("%s = %s;", vsName, attr0Name->c_str());
const GrShaderVar& inCubicCoeffs = drawEffect.castEffect<GrCubicEffect>().inCubicCoeffs();
vsBuilder->codeAppendf("%s = %s;", vsName, inCubicCoeffs.c_str());
GrGLFragmentShaderBuilder* fsBuilder = builder->getFragmentShaderBuilder();
@ -451,9 +452,11 @@ const GrBackendEffectFactory& GrCubicEffect::getFactory() const {
return GrTBackendEffectFactory<GrCubicEffect>::getInstance();
}
GrCubicEffect::GrCubicEffect(GrEffectEdgeType edgeType) : GrVertexEffect() {
this->addVertexAttrib(kVec4f_GrSLType);
fEdgeType = edgeType;
GrCubicEffect::GrCubicEffect(GrEffectEdgeType edgeType)
: fEdgeType(edgeType)
, fInCubicCoeffs(this->addVertexAttrib(GrShaderVar("inCubicCoeffs",
kVec4f_GrSLType,
GrShaderVar::kAttribute_TypeModifier))) {
}
bool GrCubicEffect::onIsEqual(const GrEffect& other) const {

View File

@ -10,7 +10,7 @@
#include "GrDrawTargetCaps.h"
#include "GrEffect.h"
#include "GrVertexEffect.h"
#include "GrGeometryProcessor.h"
#include "GrTypesPriv.h"
/**
@ -55,7 +55,7 @@
*/
class GrGLConicEffect;
class GrConicEffect : public GrVertexEffect {
class GrConicEffect : public GrGeometryProcessor {
public:
static GrEffect* Create(const GrEffectEdgeType edgeType, const GrDrawTargetCaps& caps) {
GR_CREATE_STATIC_EFFECT(gConicFillAA, GrConicEffect, (kFillAA_GrEffectEdgeType));
@ -86,6 +86,7 @@ public:
static const char* Name() { return "Conic"; }
inline const GrShaderVar& inConicCoeffs() const { return fInConicCoeffs; }
inline bool isAntiAliased() const { return GrEffectEdgeTypeIsAA(fEdgeType); }
inline bool isFilled() const { return GrEffectEdgeTypeIsFill(fEdgeType); }
inline GrEffectEdgeType getEdgeType() const { return fEdgeType; }
@ -104,11 +105,12 @@ private:
virtual bool onIsEqual(const GrEffect& other) const SK_OVERRIDE;
GrEffectEdgeType fEdgeType;
GrEffectEdgeType fEdgeType;
const GrShaderVar& fInConicCoeffs;
GR_DECLARE_EFFECT_TEST;
typedef GrVertexEffect INHERITED;
typedef GrGeometryProcessor INHERITED;
};
///////////////////////////////////////////////////////////////////////////////
@ -122,7 +124,7 @@ private:
*/
class GrGLQuadEffect;
class GrQuadEffect : public GrVertexEffect {
class GrQuadEffect : public GrGeometryProcessor {
public:
static GrEffect* Create(const GrEffectEdgeType edgeType, const GrDrawTargetCaps& caps) {
GR_CREATE_STATIC_EFFECT(gQuadFillAA, GrQuadEffect, (kFillAA_GrEffectEdgeType));
@ -153,6 +155,7 @@ public:
static const char* Name() { return "Quad"; }
inline const GrShaderVar& inHairQuadEdge() const { return fInHairQuadEdge; }
inline bool isAntiAliased() const { return GrEffectEdgeTypeIsAA(fEdgeType); }
inline bool isFilled() const { return GrEffectEdgeTypeIsFill(fEdgeType); }
inline GrEffectEdgeType getEdgeType() const { return fEdgeType; }
@ -171,11 +174,12 @@ private:
virtual bool onIsEqual(const GrEffect& other) const SK_OVERRIDE;
GrEffectEdgeType fEdgeType;
GrEffectEdgeType fEdgeType;
const GrShaderVar& fInHairQuadEdge;
GR_DECLARE_EFFECT_TEST;
typedef GrVertexEffect INHERITED;
typedef GrGeometryProcessor INHERITED;
};
//////////////////////////////////////////////////////////////////////////////
@ -191,7 +195,7 @@ private:
*/
class GrGLCubicEffect;
class GrCubicEffect : public GrVertexEffect {
class GrCubicEffect : public GrGeometryProcessor {
public:
static GrEffect* Create(const GrEffectEdgeType edgeType, const GrDrawTargetCaps& caps) {
GR_CREATE_STATIC_EFFECT(gCubicFillAA, GrCubicEffect, (kFillAA_GrEffectEdgeType));
@ -222,6 +226,7 @@ public:
static const char* Name() { return "Cubic"; }
inline const GrShaderVar& inCubicCoeffs() const { return fInCubicCoeffs; }
inline bool isAntiAliased() const { return GrEffectEdgeTypeIsAA(fEdgeType); }
inline bool isFilled() const { return GrEffectEdgeTypeIsFill(fEdgeType); }
inline GrEffectEdgeType getEdgeType() const { return fEdgeType; }
@ -240,11 +245,12 @@ private:
virtual bool onIsEqual(const GrEffect& other) const SK_OVERRIDE;
GrEffectEdgeType fEdgeType;
GrEffectEdgeType fEdgeType;
const GrShaderVar& fInCubicCoeffs;
GR_DECLARE_EFFECT_TEST;
typedef GrVertexEffect INHERITED;
typedef GrGeometryProcessor INHERITED;
};
#endif

View File

@ -10,11 +10,11 @@
#include "gl/GrGLEffect.h"
#include "gl/GrGLSL.h"
#include "gl/GrGLTexture.h"
#include "gl/GrGLVertexEffect.h"
#include "gl/GrGLGeometryProcessor.h"
#include "GrTBackendEffectFactory.h"
#include "GrTexture.h"
class GrGLCustomCoordsTextureEffect : public GrGLVertexEffect {
class GrGLCustomCoordsTextureEffect : public GrGLGeometryProcessor {
public:
GrGLCustomCoordsTextureEffect(const GrBackendEffectFactory& factory, const GrDrawEffect& drawEffect)
: INHERITED (factory) {}
@ -26,7 +26,9 @@ public:
const char* inputColor,
const TransformedCoordsArray&,
const TextureSamplerArray& samplers) SK_OVERRIDE {
SkASSERT(1 == drawEffect.castEffect<GrCustomCoordsTextureEffect>().numVertexAttribs());
const GrCustomCoordsTextureEffect& customCoordsTextureEffect =
drawEffect.castEffect<GrCustomCoordsTextureEffect>();
SkASSERT(1 == customCoordsTextureEffect.getVertexAttribs().count());
SkString fsCoordName;
const char* vsVaryingName;
@ -35,9 +37,8 @@ public:
fsCoordName = fsVaryingNamePtr;
GrGLVertexShaderBuilder* vsBuilder = builder->getVertexShaderBuilder();
const SkString* attr0Name =
vsBuilder->getEffectAttributeName(drawEffect.getVertexAttribIndices()[0]);
vsBuilder->codeAppendf("\t%s = %s;\n", vsVaryingName, attr0Name->c_str());
const GrShaderVar& inTextureCoords = customCoordsTextureEffect.inTextureCoords();
vsBuilder->codeAppendf("\t%s = %s;\n", vsVaryingName, inTextureCoords.c_str());
GrGLFragmentShaderBuilder* fsBuilder = builder->getFragmentShaderBuilder();
fsBuilder->codeAppendf("\t%s = ", outputColor);
@ -52,16 +53,18 @@ public:
const GrDrawEffect& drawEffect) SK_OVERRIDE {}
private:
typedef GrGLVertexEffect INHERITED;
typedef GrGLGeometryProcessor INHERITED;
};
///////////////////////////////////////////////////////////////////////////////
GrCustomCoordsTextureEffect::GrCustomCoordsTextureEffect(GrTexture* texture,
const GrTextureParams& params)
: fTextureAccess(texture, params) {
: fTextureAccess(texture, params)
, fInTextureCoords(this->addVertexAttrib(GrShaderVar("inTextureCoords",
kVec2f_GrSLType,
GrShaderVar::kAttribute_TypeModifier))) {
this->addTextureAccess(&fTextureAccess);
this->addVertexAttrib(kVec2f_GrSLType);
}
bool GrCustomCoordsTextureEffect::onIsEqual(const GrEffect& other) const {

View File

@ -9,7 +9,7 @@
#define GrCustomCoordsTextureEffect_DEFINED
#include "GrEffect.h"
#include "GrVertexEffect.h"
#include "GrGeometryProcessor.h"
class GrGLCustomCoordsTextureEffect;
@ -18,7 +18,7 @@ class GrGLCustomCoordsTextureEffect;
* It allows explicit specification of the filtering and wrap modes (GrTextureParams). The input
* coords are a custom attribute.
*/
class GrCustomCoordsTextureEffect : public GrVertexEffect {
class GrCustomCoordsTextureEffect : public GrGeometryProcessor {
public:
static GrEffect* Create(GrTexture* tex, const GrTextureParams& p) {
return SkNEW_ARGS(GrCustomCoordsTextureEffect, (tex, p));
@ -30,6 +30,8 @@ public:
virtual void getConstantColorComponents(GrColor* color, uint32_t* validFlags) const SK_OVERRIDE;
const GrShaderVar& inTextureCoords() const { return fInTextureCoords; }
typedef GrGLCustomCoordsTextureEffect GLEffect;
virtual const GrBackendEffectFactory& getFactory() const SK_OVERRIDE;
@ -39,11 +41,12 @@ private:
virtual bool onIsEqual(const GrEffect& other) const SK_OVERRIDE;
GrTextureAccess fTextureAccess;
GrTextureAccess fTextureAccess;
const GrShaderVar& fInTextureCoords;
GR_DECLARE_EFFECT_TEST;
typedef GrVertexEffect INHERITED;
typedef GrGeometryProcessor INHERITED;
};
#endif

View File

@ -10,9 +10,9 @@
#include "../GrAARectRenderer.h"
#include "effects/GrVertexEffect.h"
#include "effects/GrGeometryProcessor.h"
#include "gl/GrGLEffect.h"
#include "gl/GrGLVertexEffect.h"
#include "gl/GrGLGeometryProcessor.h"
#include "gl/GrGLSL.h"
#include "GrContext.h"
#include "GrCoordTransform.h"
@ -69,6 +69,10 @@ struct DashLineVertex {
SkPoint fDashPos;
};
extern const GrVertexAttrib gDashLineNoAAVertexAttribs[] = {
{ kVec2f_GrVertexAttribType, 0, kPosition_GrVertexAttribBinding }
};
extern const GrVertexAttrib gDashLineVertexAttribs[] = {
{ kVec2f_GrVertexAttribType, 0, kPosition_GrVertexAttribBinding },
{ kVec2f_GrVertexAttribType, sizeof(SkPoint), kEffect_GrVertexAttribBinding },
@ -346,12 +350,16 @@ bool GrDashingEffect::DrawDashLine(const SkPoint pts[2], const GrPaint& paint,
GrDashingEffect::DashCap capType = isRoundCap ? GrDashingEffect::kRound_DashCap :
GrDashingEffect::kNonRound_DashCap;
drawState->setGeometryProcessor(
GrDashingEffect::Create(edgeType, devInfo, strokeWidth, capType), 1)->unref();
}
GrDashingEffect::Create(edgeType, devInfo, strokeWidth, capType))->unref();
// Set up the vertex data for the line and start/end dashes
drawState->setVertexAttribs<gDashLineVertexAttribs>(SK_ARRAY_COUNT(gDashLineVertexAttribs),
sizeof(DashLineVertex));
// Set up the vertex data for the line and start/end dashes
drawState->setVertexAttribs<gDashLineVertexAttribs>(SK_ARRAY_COUNT(gDashLineVertexAttribs),
sizeof(DashLineVertex));
} else {
// Set up the vertex data for the line and start/end dashes
drawState->setVertexAttribs<gDashLineNoAAVertexAttribs>(
SK_ARRAY_COUNT(gDashLineNoAAVertexAttribs), sizeof(DashLineVertex));
}
int totalRectCnt = 0;
@ -424,7 +432,7 @@ class GLDashingCircleEffect;
* transform the line to be horizontal, with the start of line at the origin then shifted to the
* right by half the off interval. The line then goes in the positive x direction.
*/
class DashingCircleEffect : public GrVertexEffect {
class DashingCircleEffect : public GrGeometryProcessor {
public:
typedef SkPathEffect::DashInfo DashInfo;
@ -434,6 +442,8 @@ public:
static const char* Name() { return "DashingCircleEffect"; }
const GrShaderVar& inCoord() const { return fInCoord; }
GrEffectEdgeType getEdgeType() const { return fEdgeType; }
SkScalar getRadius() const { return fRadius; }
@ -454,18 +464,19 @@ private:
virtual bool onIsEqual(const GrEffect& other) const SK_OVERRIDE;
GrEffectEdgeType fEdgeType;
const GrShaderVar& fInCoord;
SkScalar fIntervalLength;
SkScalar fRadius;
SkScalar fCenterX;
GR_DECLARE_EFFECT_TEST;
typedef GrVertexEffect INHERITED;
typedef GrGeometryProcessor INHERITED;
};
//////////////////////////////////////////////////////////////////////////////
class GLDashingCircleEffect : public GrGLVertexEffect {
class GLDashingCircleEffect : public GrGLGeometryProcessor {
public:
GLDashingCircleEffect(const GrBackendEffectFactory&, const GrDrawEffect&);
@ -486,7 +497,7 @@ private:
SkScalar fPrevRadius;
SkScalar fPrevCenterX;
SkScalar fPrevIntervalLength;
typedef GrGLVertexEffect INHERITED;
typedef GrGLGeometryProcessor INHERITED;
};
GLDashingCircleEffect::GLDashingCircleEffect(const GrBackendEffectFactory& factory,
@ -517,9 +528,7 @@ void GLDashingCircleEffect::emitCode(GrGLFullProgramBuilder* builder,
builder->addVarying(kVec2f_GrSLType, "Coord", &vsCoordName, &fsCoordName);
GrGLVertexShaderBuilder* vsBuilder = builder->getVertexShaderBuilder();
const SkString* attr0Name =
vsBuilder->getEffectAttributeName(drawEffect.getVertexAttribIndices()[0]);
vsBuilder->codeAppendf("\t%s = %s;\n", vsCoordName, attr0Name->c_str());
vsBuilder->codeAppendf("\t%s = %s;\n", vsCoordName, dce.inCoord().c_str());
// transforms all points so that we can compare them to our test circle
GrGLFragmentShaderBuilder* fsBuilder = builder->getFragmentShaderBuilder();
@ -582,14 +591,15 @@ const GrBackendEffectFactory& DashingCircleEffect::getFactory() const {
DashingCircleEffect::DashingCircleEffect(GrEffectEdgeType edgeType, const DashInfo& info,
SkScalar radius)
: fEdgeType(edgeType) {
: fEdgeType(edgeType)
, fInCoord(this->addVertexAttrib(GrShaderVar("inCoord",
kVec2f_GrSLType,
GrShaderVar::kAttribute_TypeModifier))) {
SkScalar onLen = info.fIntervals[0];
SkScalar offLen = info.fIntervals[1];
fIntervalLength = onLen + offLen;
fRadius = radius;
fCenterX = SkScalarHalf(offLen);
this->addVertexAttrib(kVec2f_GrSLType);
}
bool DashingCircleEffect::onIsEqual(const GrEffect& other) const {
@ -635,7 +645,7 @@ class GLDashingLineEffect;
* line at the origin then shifted to the right by half the off interval. The line then goes in the
* positive x direction.
*/
class DashingLineEffect : public GrVertexEffect {
class DashingLineEffect : public GrGeometryProcessor {
public:
typedef SkPathEffect::DashInfo DashInfo;
@ -645,6 +655,8 @@ public:
static const char* Name() { return "DashingEffect"; }
const GrShaderVar& inCoord() const { return fInCoord; }
GrEffectEdgeType getEdgeType() const { return fEdgeType; }
const SkRect& getRect() const { return fRect; }
@ -663,17 +675,18 @@ private:
virtual bool onIsEqual(const GrEffect& other) const SK_OVERRIDE;
GrEffectEdgeType fEdgeType;
const GrShaderVar& fInCoord;
SkRect fRect;
SkScalar fIntervalLength;
GR_DECLARE_EFFECT_TEST;
typedef GrVertexEffect INHERITED;
typedef GrGeometryProcessor INHERITED;
};
//////////////////////////////////////////////////////////////////////////////
class GLDashingLineEffect : public GrGLVertexEffect {
class GLDashingLineEffect : public GrGLGeometryProcessor {
public:
GLDashingLineEffect(const GrBackendEffectFactory&, const GrDrawEffect&);
@ -694,7 +707,7 @@ private:
GrGLProgramDataManager::UniformHandle fIntervalUniform;
SkRect fPrevRect;
SkScalar fPrevIntervalLength;
typedef GrGLVertexEffect INHERITED;
typedef GrGLGeometryProcessor INHERITED;
};
GLDashingLineEffect::GLDashingLineEffect(const GrBackendEffectFactory& factory,
@ -729,9 +742,7 @@ void GLDashingLineEffect::emitCode(GrGLFullProgramBuilder* builder,
const char *vsCoordName, *fsCoordName;
builder->addVarying(kVec2f_GrSLType, "Coord", &vsCoordName, &fsCoordName);
GrGLVertexShaderBuilder* vsBuilder = builder->getVertexShaderBuilder();
const SkString* attr0Name =
vsBuilder->getEffectAttributeName(drawEffect.getVertexAttribIndices()[0]);
vsBuilder->codeAppendf("\t%s = %s;\n", vsCoordName, attr0Name->c_str());
vsBuilder->codeAppendf("\t%s = %s;\n", vsCoordName, de.inCoord().c_str());
// transforms all points so that we can compare them to our test rect
GrGLFragmentShaderBuilder* fsBuilder = builder->getFragmentShaderBuilder();
@ -801,15 +812,16 @@ const GrBackendEffectFactory& DashingLineEffect::getFactory() const {
DashingLineEffect::DashingLineEffect(GrEffectEdgeType edgeType, const DashInfo& info,
SkScalar strokeWidth)
: fEdgeType(edgeType) {
: fEdgeType(edgeType)
, fInCoord(this->addVertexAttrib(GrShaderVar("inCoord",
kVec2f_GrSLType,
GrShaderVar::kAttribute_TypeModifier))) {
SkScalar onLen = info.fIntervals[0];
SkScalar offLen = info.fIntervals[1];
SkScalar halfOffLen = SkScalarHalf(offLen);
SkScalar halfStroke = SkScalarHalf(strokeWidth);
fIntervalLength = onLen + offLen;
fRect.set(halfOffLen, -halfStroke, halfOffLen + onLen, halfStroke);
this->addVertexAttrib(kVec2f_GrSLType);
}
bool DashingLineEffect::onIsEqual(const GrEffect& other) const {

View File

@ -10,7 +10,7 @@
#include "gl/GrGLEffect.h"
#include "gl/GrGLSL.h"
#include "gl/GrGLTexture.h"
#include "gl/GrGLVertexEffect.h"
#include "gl/GrGLGeometryProcessor.h"
#include "GrTBackendEffectFactory.h"
#include "GrTexture.h"
@ -29,7 +29,7 @@
// Assuming a radius of the diagonal of the fragment, hence a factor of sqrt(2)/2
#define SK_DistanceFieldAAFactor "0.7071"
class GrGLDistanceFieldTextureEffect : public GrGLVertexEffect {
class GrGLDistanceFieldTextureEffect : public GrGLGeometryProcessor {
public:
GrGLDistanceFieldTextureEffect(const GrBackendEffectFactory& factory,
const GrDrawEffect& drawEffect)
@ -43,13 +43,13 @@ public:
const char* inputColor,
const TransformedCoordsArray&,
const TextureSamplerArray& samplers) SK_OVERRIDE {
SkASSERT(1 == drawEffect.castEffect<GrDistanceFieldTextureEffect>().numVertexAttribs());
const GrDistanceFieldTextureEffect& dfTexEffect =
drawEffect.castEffect<GrDistanceFieldTextureEffect>();
SkASSERT(1 == dfTexEffect.getVertexAttribs().count());
GrGLFragmentShaderBuilder* fsBuilder = builder->getFragmentShaderBuilder();
SkAssertResult(fsBuilder->enableFeature(
GrGLFragmentShaderBuilder::kStandardDerivatives_GLSLFeature));
const GrDistanceFieldTextureEffect& dfTexEffect =
drawEffect.castEffect<GrDistanceFieldTextureEffect>();
SkString fsCoordName;
const char* vsCoordName;
@ -58,9 +58,7 @@ public:
fsCoordName = fsCoordNamePtr;
GrGLVertexShaderBuilder* vsBuilder = builder->getVertexShaderBuilder();
const SkString* attr0Name =
vsBuilder->getEffectAttributeName(drawEffect.getVertexAttribIndices()[0]);
vsBuilder->codeAppendf("\t%s = %s;\n", vsCoordName, attr0Name->c_str());
vsBuilder->codeAppendf("\t%s = %s;\n", vsCoordName, dfTexEffect.inTextureCoords().c_str());
const char* textureSizeUniName = NULL;
fTextureSizeUni = builder->addUniform(GrGLProgramBuilder::kFragment_Visibility,
@ -165,7 +163,7 @@ private:
GrGLProgramDataManager::UniformHandle fLuminanceUni;
float fLuminance;
typedef GrGLVertexEffect INHERITED;
typedef GrGLGeometryProcessor INHERITED;
};
///////////////////////////////////////////////////////////////////////////////
@ -183,13 +181,15 @@ GrDistanceFieldTextureEffect::GrDistanceFieldTextureEffect(GrTexture* texture,
, fGammaTextureAccess(gamma, gammaParams)
, fLuminance(luminance)
#endif
, fFlags(flags & kNonLCD_DistanceFieldEffectMask) {
, fFlags(flags & kNonLCD_DistanceFieldEffectMask)
, fInTextureCoords(this->addVertexAttrib(GrShaderVar("inTextureCoords",
kVec2f_GrSLType,
GrShaderVar::kAttribute_TypeModifier))) {
SkASSERT(!(flags & ~kNonLCD_DistanceFieldEffectMask));
this->addTextureAccess(&fTextureAccess);
#ifdef SK_GAMMA_APPLY_TO_A8
this->addTextureAccess(&fGammaTextureAccess);
#endif
this->addVertexAttrib(kVec2f_GrSLType);
}
bool GrDistanceFieldTextureEffect::onIsEqual(const GrEffect& other) const {
@ -257,7 +257,7 @@ GrEffect* GrDistanceFieldTextureEffect::TestCreate(SkRandom* random,
///////////////////////////////////////////////////////////////////////////////
class GrGLDistanceFieldLCDTextureEffect : public GrGLVertexEffect {
class GrGLDistanceFieldLCDTextureEffect : public GrGLGeometryProcessor {
public:
GrGLDistanceFieldLCDTextureEffect(const GrBackendEffectFactory& factory,
const GrDrawEffect& drawEffect)
@ -271,10 +271,9 @@ public:
const char* inputColor,
const TransformedCoordsArray&,
const TextureSamplerArray& samplers) SK_OVERRIDE {
SkASSERT(1 == drawEffect.castEffect<GrDistanceFieldLCDTextureEffect>().numVertexAttribs());
const GrDistanceFieldLCDTextureEffect& dfTexEffect =
drawEffect.castEffect<GrDistanceFieldLCDTextureEffect>();
SkASSERT(1 == dfTexEffect.getVertexAttribs().count());
SkString fsCoordName;
const char* vsCoordName;
@ -283,9 +282,7 @@ public:
fsCoordName = fsCoordNamePtr;
GrGLVertexShaderBuilder* vsBuilder = builder->getVertexShaderBuilder();
const SkString* attr0Name =
vsBuilder->getEffectAttributeName(drawEffect.getVertexAttribIndices()[0]);
vsBuilder->codeAppendf("\t%s = %s;\n", vsCoordName, attr0Name->c_str());
vsBuilder->codeAppendf("\t%s = %s;\n", vsCoordName, dfTexEffect.inTextureCoords().c_str());
const char* textureSizeUniName = NULL;
// width, height, 1/(3*width)
@ -443,7 +440,7 @@ private:
GrGLProgramDataManager::UniformHandle fTextColorUni;
SkColor fTextColor;
typedef GrGLVertexEffect INHERITED;
typedef GrGLGeometryProcessor INHERITED;
};
///////////////////////////////////////////////////////////////////////////////
@ -456,12 +453,14 @@ GrDistanceFieldLCDTextureEffect::GrDistanceFieldLCDTextureEffect(
: fTextureAccess(texture, params)
, fGammaTextureAccess(gamma, gParams)
, fTextColor(textColor)
, fFlags(flags & kLCD_DistanceFieldEffectMask) {
, fFlags(flags & kLCD_DistanceFieldEffectMask)
, fInTextureCoords(this->addVertexAttrib(GrShaderVar("inTextureCoords",
kVec2f_GrSLType,
GrShaderVar::kAttribute_TypeModifier))) {
SkASSERT(!(flags & ~kLCD_DistanceFieldEffectMask) && (flags & kUseLCD_DistanceFieldEffectFlag));
this->addTextureAccess(&fTextureAccess);
this->addTextureAccess(&fGammaTextureAccess);
this->addVertexAttrib(kVec2f_GrSLType);
}
bool GrDistanceFieldLCDTextureEffect::onIsEqual(const GrEffect& other) const {

View File

@ -9,7 +9,7 @@
#define GrDistanceFieldTextureEffect_DEFINED
#include "GrEffect.h"
#include "GrVertexEffect.h"
#include "GrGeometryProcessor.h"
class GrGLDistanceFieldTextureEffect;
class GrGLDistanceFieldLCDTextureEffect;
@ -38,7 +38,7 @@ enum GrDistanceFieldEffectFlags {
* It allows explicit specification of the filtering and wrap modes (GrTextureParams). The input
* coords are a custom attribute. Gamma correction is handled via a texture LUT.
*/
class GrDistanceFieldTextureEffect : public GrVertexEffect {
class GrDistanceFieldTextureEffect : public GrGeometryProcessor {
public:
#ifdef SK_GAMMA_APPLY_TO_A8
static GrEffect* Create(GrTexture* tex, const GrTextureParams& params,
@ -59,6 +59,8 @@ public:
static const char* Name() { return "DistanceFieldTexture"; }
virtual void getConstantColorComponents(GrColor* color, uint32_t* validFlags) const SK_OVERRIDE;
const GrShaderVar& inTextureCoords() const { return fInTextureCoords; }
#ifdef SK_GAMMA_APPLY_TO_A8
float getLuminance() const { return fLuminance; }
#endif
@ -77,12 +79,13 @@ private:
virtual bool onIsEqual(const GrEffect& other) const SK_OVERRIDE;
GrTextureAccess fTextureAccess;
GrTextureAccess fTextureAccess;
#ifdef SK_GAMMA_APPLY_TO_A8
GrTextureAccess fGammaTextureAccess;
float fLuminance;
GrTextureAccess fGammaTextureAccess;
float fLuminance;
#endif
uint32_t fFlags;
uint32_t fFlags;
const GrShaderVar& fInTextureCoords;
GR_DECLARE_EFFECT_TEST;
@ -95,7 +98,7 @@ private:
* It allows explicit specification of the filtering and wrap modes (GrTextureParams). The input
* coords are a custom attribute. Gamma correction is handled via a texture LUT.
*/
class GrDistanceFieldLCDTextureEffect : public GrVertexEffect {
class GrDistanceFieldLCDTextureEffect : public GrGeometryProcessor {
public:
static GrEffect* Create(GrTexture* tex, const GrTextureParams& params,
GrTexture* gamma, const GrTextureParams& gammaParams,
@ -108,6 +111,7 @@ public:
static const char* Name() { return "DistanceFieldLCDTexture"; }
const GrShaderVar& inTextureCoords() const { return fInTextureCoords; }
virtual void getConstantColorComponents(GrColor* color, uint32_t* validFlags) const SK_OVERRIDE;
GrColor getTextColor() const { return fTextColor; }
uint32_t getFlags() const { return fFlags; }
@ -124,10 +128,11 @@ private:
virtual bool onIsEqual(const GrEffect& other) const SK_OVERRIDE;
GrTextureAccess fTextureAccess;
GrTextureAccess fGammaTextureAccess;
GrColor fTextColor;
uint32_t fFlags;
GrTextureAccess fTextureAccess;
GrTextureAccess fGammaTextureAccess;
GrColor fTextColor;
uint32_t fFlags;
const GrShaderVar& fInTextureCoords;
GR_DECLARE_EFFECT_TEST;

View File

@ -0,0 +1,41 @@
/*
* 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 GrGeometryProcessor_DEFINED
#define GrGeometryProcessor_DEFINED
#include "GrEffect.h"
/**
* If an effect needs specialized vertex shader code, then it must inherit from this class.
* Otherwise it won't be able to add vertex attribs, and it will be given a vertexless shader
* program in emitCode.
*/
class GrGeometryProcessor : public GrEffect {
public:
GrGeometryProcessor() { fRequiresVertexShader = true; }
protected:
/**
* Subclasses call this from their constructor to register vertex attributes (at most
* kMaxVertexAttribs). This must only be called from the constructor because GrEffects are
* immutable.
*
* We return a reference to the added var so that derived classes can name it nicely and use it
* in shader code.
*/
const GrShaderVar& addVertexAttrib(const GrShaderVar& var) {
SkASSERT(GrShaderVar::kAttribute_TypeModifier == var.getTypeModifier());
SkASSERT(fVertexAttribs.count() < kMaxVertexAttribs);
return fVertexAttribs.push_back(var);
}
private:
typedef GrEffect INHERITED;
};
#endif

View File

@ -1,37 +0,0 @@
/*
* 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 GrVertexEffect_DEFINED
#define GrVertexEffect_DEFINED
#include "GrEffect.h"
/**
* If an effect needs specialized vertex shader code, then it must inherit from this class.
* Otherwise it won't be able to add vertex attribs, and it might be given a vertexless shader
* program in emitCode.
*/
class GrVertexEffect : public GrEffect {
public:
GrVertexEffect() { fRequiresVertexShader = true; }
protected:
/**
* Subclasses call this from their constructor to register vertex attributes (at most
* kMaxVertexAttribs). This must only be called from the constructor because GrEffects are
* immutable.
*/
void addVertexAttrib(GrSLType type) {
SkASSERT(fVertexAttribTypes.count() < kMaxVertexAttribs);
fVertexAttribTypes.push_back(type);
}
private:
typedef GrEffect INHERITED;
};
#endif

View File

@ -34,7 +34,7 @@ class GrGLShaderBuilder;
class GrDrawEffect;
class GrGLTexture;
class GrGLVertexEffect;
class GrGLGeometryProcessor;
class GrGLEffect {
@ -90,14 +90,14 @@ public:
static void GenKey(const GrDrawEffect&, const GrGLCaps&, GrEffectKeyBuilder*) {}
/** Used by the system when generating shader code, to see if this effect can be downcasted to
the internal GrGLVertexEffect type */
the internal GrGLGeometryProcessor type */
bool isVertexEffect() const { return fIsVertexEffect; }
protected:
const GrBackendEffectFactory& fFactory;
private:
friend class GrGLVertexEffect; // to set fIsVertexEffect
friend class GrGLGeometryProcessor; // to set fIsVertexEffect
bool fIsVertexEffect;
};

View File

@ -5,8 +5,8 @@
* found in the LICENSE file.
*/
#ifndef GrGLVertexEffect_DEFINED
#define GrGLVertexEffect_DEFINED
#ifndef GrGLGeometryProcessor_DEFINED
#define GrGLGeometryProcessor_DEFINED
#include "GrGLEffect.h"
@ -15,9 +15,9 @@
* from this class. Since paths don't have vertices, this class is only meant to be used internally
* by skia, for special cases.
*/
class GrGLVertexEffect : public GrGLEffect {
class GrGLGeometryProcessor : public GrGLEffect {
public:
GrGLVertexEffect(const GrBackendEffectFactory& factory)
GrGLGeometryProcessor(const GrBackendEffectFactory& factory)
: INHERITED(factory) { fIsVertexEffect = true; }
/**
@ -41,7 +41,7 @@ public:
const char* inputColor,
const TransformedCoordsArray& coords,
const TextureSamplerArray& samplers) SK_OVERRIDE {
SkFAIL("GrGLVertexEffect requires GrGLFullProgramBuilder* overload for emitCode().");
SkFAIL("GrGLGeometryProcessor requires GrGLFullProgramBuilder* overload for emitCode().");
}

View File

@ -11,7 +11,7 @@
#include "gl/GrGLEffect.h"
#include "gl/GrGLPathRendering.h"
#include "gl/builders/GrGLProgramBuilder.h"
#include "gl/GrGLVertexEffect.h"
#include "gl/GrGLGeometryProcessor.h"
#include "gl/GrGpuGL.h"
typedef GrGLProgramEffects::TransformedCoords TransformedCoords;
@ -123,7 +123,7 @@ bool GrGLProgramEffects::GenEffectMetaKey(const GrDrawEffect& drawEffect, const
uint32_t textureKey = GrGLProgramEffects::GenTextureKey(drawEffect, caps);
uint32_t transformKey = GrGLProgramEffects::GenTransformKey(drawEffect);
uint32_t attribKey = GrGLProgramEffects::GenAttribKey(drawEffect);
uint32_t attribKey = GrGLProgramEffects::GenAttribKey(drawEffect.castEffect<GrEffect>());
uint32_t classID = drawEffect.effect()->getFactory().effectClassID();
// Currently we allow 16 bits for each of the above portions of the meta-key. Fail if they
@ -139,14 +139,14 @@ bool GrGLProgramEffects::GenEffectMetaKey(const GrDrawEffect& drawEffect, const
return true;
}
uint32_t GrGLProgramEffects::GenAttribKey(const GrDrawEffect& drawEffect) {
uint32_t GrGLProgramEffects::GenAttribKey(const GrEffect& effect) {
uint32_t key = 0;
int numAttributes = drawEffect.getVertexAttribIndexCount();
const GrEffect::VertexAttribArray& vars = effect.getVertexAttribs();
int numAttributes = vars.count();
SkASSERT(numAttributes <= 2);
const int* attributeIndices = drawEffect.getVertexAttribIndices();
for (int a = 0; a < numAttributes; ++a) {
uint32_t value = attributeIndices[a] << 3 * a;
SkASSERT(0 == (value & key)); // keys for each attribute ought not to overlap
uint32_t value = 1 << a;
key |= value;
}
return key;
@ -279,7 +279,7 @@ void GrGLVertexProgramEffects::emitEffect(GrGLFullProgramBuilder* builder,
vsBuilder->codeAppend(openBrace.c_str());
if (glEffect->isVertexEffect()) {
GrGLVertexEffect* vertexEffect = static_cast<GrGLVertexEffect*>(glEffect);
GrGLGeometryProcessor* vertexEffect = static_cast<GrGLGeometryProcessor*>(glEffect);
vertexEffect->emitCode(builder, drawEffect, key, outColor, inColor, coords, samplers);
} else {
glEffect->emitCode(builder, drawEffect, key, outColor, inColor, coords, samplers);
@ -478,7 +478,7 @@ void GrGLPathTexGenProgramEffects::emitEffect(GrGLFragmentOnlyProgramBuilder* bu
SkSTArray<2, TransformedCoords> coords(effect->numTransforms());
SkSTArray<4, TextureSampler> samplers(effect->numTextures());
SkASSERT(0 == stage.getVertexAttribIndexCount());
SkASSERT(0 == effect->getVertexAttribs().count());
this->setupPathTexGen(builder, drawEffect, &coords);
this->emitSamplers(builder, effect, &samplers);

View File

@ -114,7 +114,7 @@ protected:
/**
* Helpers for GenEffectMetaKey.
*/
static uint32_t GenAttribKey(const GrDrawEffect&);
static uint32_t GenAttribKey(const GrEffect&);
static uint32_t GenTransformKey(const GrDrawEffect&);
static uint32_t GenTextureKey(const GrDrawEffect&, const GrGLCaps&);

View File

@ -10,43 +10,15 @@
#include "GrGLContext.h"
#include "GrGLSL.h"
#include "SkString.h"
#include "GrShaderVar.h"
#define USE_UNIFORM_FLOAT_ARRAYS true
/**
* Represents a variable in a shader
*/
class GrGLShaderVar {
class GrGLShaderVar : public GrShaderVar {
public:
/**
* Early versions of GLSL have Varying and Attribute; those are later
* deprecated, but we still need to know whether a Varying variable
* should be treated as In or Out.
*/
enum TypeModifier {
kNone_TypeModifier,
kOut_TypeModifier,
kIn_TypeModifier,
kInOut_TypeModifier,
kUniform_TypeModifier,
kAttribute_TypeModifier,
kVaryingIn_TypeModifier,
kVaryingOut_TypeModifier
};
enum Precision {
kLow_Precision, // lowp
kMedium_Precision, // mediump
kHigh_Precision, // highp
kDefault_Precision, // Default for the current context. We make
// fragment shaders default to mediump on ES2
// because highp support is not guaranteed (and
// we haven't been motivated to test for it).
// Otherwise, highp.
};
/**
* See GL_ARB_fragment_coord_conventions.
*/
@ -58,36 +30,43 @@ public:
/**
* Defaults to a float with no precision specifier
*/
GrGLShaderVar() {
fType = kFloat_GrSLType;
fTypeModifier = kNone_TypeModifier;
fCount = kNonArray;
fPrecision = kDefault_Precision;
fOrigin = kDefault_Origin;
fUseUniformFloatArrays = USE_UNIFORM_FLOAT_ARRAYS;
GrGLShaderVar()
: GrShaderVar()
, fOrigin(kDefault_Origin)
, fUseUniformFloatArrays(USE_UNIFORM_FLOAT_ARRAYS) {
}
GrGLShaderVar(const char* name, GrSLType type, int arrayCount = kNonArray,
Precision precision = kDefault_Precision) {
Precision precision = kDefault_Precision)
: GrShaderVar(name, type, arrayCount, precision)
, fOrigin(kDefault_Origin)
, fUseUniformFloatArrays(USE_UNIFORM_FLOAT_ARRAYS) {
SkASSERT(kVoid_GrSLType != type);
fType = type;
fTypeModifier = kNone_TypeModifier;
fCount = arrayCount;
fPrecision = precision;
fOrigin = kDefault_Origin;
fUseUniformFloatArrays = USE_UNIFORM_FLOAT_ARRAYS;
fName = name;
}
GrGLShaderVar(const char* name, GrSLType type, TypeModifier typeModifier,
int arrayCount = kNonArray, Precision precision = kDefault_Precision)
: GrShaderVar(name, type, typeModifier, arrayCount, precision)
, fOrigin(kDefault_Origin)
, fUseUniformFloatArrays(USE_UNIFORM_FLOAT_ARRAYS) {
SkASSERT(kVoid_GrSLType != type);
}
GrGLShaderVar(const GrShaderVar& var)
: GrShaderVar(var)
, fOrigin(kDefault_Origin)
, fUseUniformFloatArrays(USE_UNIFORM_FLOAT_ARRAYS) {
SkASSERT(kVoid_GrSLType != var.getType());
}
GrGLShaderVar(const GrGLShaderVar& var)
: fType(var.fType)
, fTypeModifier(var.fTypeModifier)
, fName(var.fName)
, fCount(var.fCount)
, fPrecision(var.fPrecision)
: GrShaderVar(var.c_str(), var.getType(), var.getTypeModifier(),
var.getArrayCount(), var.getPrecision())
, fOrigin(var.fOrigin)
, fUseUniformFloatArrays(var.fUseUniformFloatArrays) {
SkASSERT(kVoid_GrSLType != var.fType);
SkASSERT(kVoid_GrSLType != var.getType());
}
/**
@ -108,11 +87,7 @@ public:
Origin origin = kDefault_Origin,
bool useUniformFloatArrays = USE_UNIFORM_FLOAT_ARRAYS) {
SkASSERT(kVoid_GrSLType != type);
fType = type;
fTypeModifier = typeModifier;
fName = name;
fCount = kNonArray;
fPrecision = precision;
INHERITED::set(type, typeModifier, name, precision);
fOrigin = origin;
fUseUniformFloatArrays = useUniformFloatArrays;
}
@ -127,11 +102,7 @@ public:
Origin origin = kDefault_Origin,
bool useUniformFloatArrays = USE_UNIFORM_FLOAT_ARRAYS) {
SkASSERT(kVoid_GrSLType != type);
fType = type;
fTypeModifier = typeModifier;
fName = name;
fCount = kNonArray;
fPrecision = precision;
INHERITED::set(type, typeModifier, name, precision);
fOrigin = origin;
fUseUniformFloatArrays = useUniformFloatArrays;
}
@ -147,11 +118,7 @@ public:
Origin origin = kDefault_Origin,
bool useUniformFloatArrays = USE_UNIFORM_FLOAT_ARRAYS) {
SkASSERT(kVoid_GrSLType != type);
fType = type;
fTypeModifier = typeModifier;
fName = name;
fCount = count;
fPrecision = precision;
INHERITED::set(type, typeModifier, name, count, precision);
fOrigin = origin;
fUseUniformFloatArrays = useUniformFloatArrays;
}
@ -167,82 +134,11 @@ public:
Origin origin = kDefault_Origin,
bool useUniformFloatArrays = USE_UNIFORM_FLOAT_ARRAYS) {
SkASSERT(kVoid_GrSLType != type);
fType = type;
fTypeModifier = typeModifier;
fName = name;
fCount = count;
fPrecision = precision;
INHERITED::set(type, typeModifier, name, count, precision);
fOrigin = origin;
fUseUniformFloatArrays = useUniformFloatArrays;
}
/**
* Is the var an array.
*/
bool isArray() const { return kNonArray != fCount; }
/**
* Is this an unsized array, (i.e. declared with []).
*/
bool isUnsizedArray() const { return kUnsizedArray == fCount; }
/**
* Get the array length of the var.
*/
int getArrayCount() const { return fCount; }
/**
* Set the array length of the var
*/
void setArrayCount(int count) { fCount = count; }
/**
* Set to be a non-array.
*/
void setNonArray() { fCount = kNonArray; }
/**
* Set to be an unsized array.
*/
void setUnsizedArray() { fCount = kUnsizedArray; }
/**
* Access the var name as a writable string
*/
SkString* accessName() { return &fName; }
/**
* Set the var name
*/
void setName(const SkString& n) { fName = n; }
void setName(const char* n) { fName = n; }
/**
* Get the var name.
*/
const SkString& getName() const { return fName; }
/**
* Shortcut for this->getName().c_str();
*/
const char* c_str() const { return this->getName().c_str(); }
/**
* Get the type of the var
*/
GrSLType getType() const { return fType; }
/**
* Set the type of the var
*/
void setType(GrSLType type) { fType = type; }
TypeModifier getTypeModifier() const { return fTypeModifier; }
void setTypeModifier(TypeModifier type) { fTypeModifier = type; }
/**
* Get the precision of the var
*/
Precision getPrecision() const { return fPrecision; }
/**
* Set the precision of the var
*/
void setPrecision(Precision p) { fPrecision = p; }
/**
* Get the origin of the var
*/
@ -346,15 +242,12 @@ private:
}
}
GrSLType fType;
TypeModifier fTypeModifier;
SkString fName;
int fCount;
Precision fPrecision;
Origin fOrigin;
/// Work around driver bugs on some hardware that don't correctly
/// support uniform float []
bool fUseUniformFloatArrays;
typedef GrShaderVar INHERITED;
};
#endif

View File

@ -228,6 +228,7 @@ protected:
int fCurrentIndex;
const GrEffectStage* fEffectStage;
} fCodeStage;
private:
/**

View File

@ -12,7 +12,6 @@
#include "gl/GrGLProgramEffects.h"
#include "gl/GrGLSL.h"
#include "gl/GrGLProgramDataManager.h"
#include "GrAllocator.h"
#include "GrBackendEffectFactory.h"
#include "GrColor.h"
#include "GrEffect.h"

View File

@ -14,8 +14,8 @@
#define GL_CALL_RET(R, X) GR_GL_CALL_RET(gpu->glInterface(), R, X)
namespace {
inline const char* color_attribute_name() { return "aColor"; }
inline const char* coverage_attribute_name() { return "aCoverage"; }
inline const char* color_attribute_name() { return "inColor"; }
inline const char* coverage_attribute_name() { return "inCoverage"; }
}
GrGLVertexShaderBuilder::GrGLVertexShaderBuilder(GrGLFullProgramBuilder* program)
@ -23,53 +23,29 @@ GrGLVertexShaderBuilder::GrGLVertexShaderBuilder(GrGLFullProgramBuilder* program
, fPositionVar(NULL)
, fLocalCoordsVar(NULL) {
}
bool GrGLVertexShaderBuilder::addAttribute(GrSLType type, const char* name) {
bool GrGLVertexShaderBuilder::addAttribute(const GrShaderVar& var) {
SkASSERT(GrShaderVar::kAttribute_TypeModifier == var.getTypeModifier());
for (int i = 0; i < fInputs.count(); ++i) {
const GrGLShaderVar& attr = fInputs[i];
// if attribute already added, don't add it again
if (attr.getName().equals(name)) {
if (attr.getName().equals(var.getName())) {
return false;
}
}
fInputs.push_back().set(type, GrGLShaderVar::kAttribute_TypeModifier, name);
return true;
}
bool GrGLVertexShaderBuilder::addEffectAttribute(int attributeIndex,
GrSLType type,
const SkString& name) {
if (!this->addAttribute(type, name.c_str())) {
return false;
}
fEffectAttributes.push_back().set(attributeIndex, name);
fInputs.push_back(var);
return true;
}
void GrGLVertexShaderBuilder::emitAttributes(const GrEffectStage& stage) {
int numAttributes = stage.getVertexAttribIndexCount();
const int* attributeIndices = stage.getVertexAttribIndices();
const GrEffect& effect = *stage.getEffect();
const GrEffect::VertexAttribArray& vars =
effect.getVertexAttribs();
int numAttributes = vars.count();
for (int a = 0; a < numAttributes; ++a) {
// TODO: Make addAttribute mangle the name.
SkString attributeName("aAttr");
attributeName.appendS32(attributeIndices[a]);
this->addEffectAttribute(attributeIndices[a],
stage.getEffect()->vertexAttribType(a),
attributeName);
this->addAttribute(vars[a]);
}
}
const SkString* GrGLVertexShaderBuilder::getEffectAttributeName(int attributeIndex) const {
const AttributePair* attribEnd = fEffectAttributes.end();
for (const AttributePair* attrib = fEffectAttributes.begin(); attrib != attribEnd; ++attrib) {
if (attrib->fIndex == attributeIndex) {
return &attrib->fName;
}
}
return NULL;
}
void GrGLVertexShaderBuilder::addVarying(GrSLType type, const char* name, const char** vsOutName) {
fOutputs.push_back();
fOutputs.back().setType(type);
@ -107,10 +83,27 @@ void GrGLVertexShaderBuilder::bindProgramLocations(GrGLuint programId) {
coverage_attribute_name()));
}
const AttributePair* attribEnd = fEffectAttributes.end();
for (const AttributePair* attrib = fEffectAttributes.begin(); attrib != attribEnd; ++attrib) {
GL_CALL(BindAttribLocation(programId, attrib->fIndex, attrib->fName.c_str()));
// We pull the current state of attributes off of drawstate and bind them in order
const GrRODrawState* ds = fProgramBuilder->gpu()->drawState();
const GrVertexAttrib* vaPtr = ds->getVertexAttribs();
const int vaCount = ds->getVertexAttribCount();
int i = fEffectAttribOffset;
for (int index = 0; index < vaCount; index++) {
if (kEffect_GrVertexAttribBinding != vaPtr[index].fBinding) {
continue;
}
SkASSERT(index != header.fPositionAttributeIndex &&
index != header.fLocalCoordAttributeIndex &&
index != header.fColorAttributeIndex &&
index != header.fCoverageAttributeIndex);
// We should never find another effect attribute if we have bound everything
SkASSERT(i < fInputs.count());
GL_CALL(BindAttribLocation(programId, index, fInputs[i].c_str()));
i++;
}
// Make sure we bound everything
SkASSERT(fInputs.count() == i);
}
bool GrGLVertexShaderBuilder::compileAndAttachShaders(GrGLuint programId,
@ -183,7 +176,9 @@ void GrGLVertexShaderBuilder::emitCodeBeforeEffects(GrGLSLExpr4* color, GrGLSLEx
}
if (GrGLProgramDesc::kAttribute_ColorInput == header.fColorInput) {
this->addAttribute(kVec4f_GrSLType, color_attribute_name());
this->addAttribute(GrShaderVar(color_attribute_name(),
kVec4f_GrSLType,
GrShaderVar::kAttribute_TypeModifier));
const char *vsName, *fsName;
fFullProgramBuilder->addVarying(kVec4f_GrSLType, "Color", &vsName, &fsName);
this->codeAppendf("\t%s = %s;\n", vsName, color_attribute_name());
@ -191,10 +186,13 @@ void GrGLVertexShaderBuilder::emitCodeBeforeEffects(GrGLSLExpr4* color, GrGLSLEx
}
if (GrGLProgramDesc::kAttribute_ColorInput == header.fCoverageInput) {
this->addAttribute(kVec4f_GrSLType, coverage_attribute_name());
this->addAttribute(GrShaderVar(coverage_attribute_name(),
kVec4f_GrSLType,
GrShaderVar::kAttribute_TypeModifier));
const char *vsName, *fsName;
fFullProgramBuilder->addVarying(kVec4f_GrSLType, "Coverage", &vsName, &fsName);
this->codeAppendf("\t%s = %s;\n", vsName, coverage_attribute_name());
*coverage = fsName;
}
fEffectAttribOffset = fInputs.count();
}

View File

@ -15,14 +15,6 @@ class GrGLVertexShaderBuilder : public GrGLFullShaderBuilder {
public:
GrGLVertexShaderBuilder(GrGLFullProgramBuilder* program);
/*
* Add attribute will push a new attribute onto the end. It will also assert if there is
* a duplicate attribute
*/
bool addAttribute(GrSLType type, const char* name);
bool addEffectAttribute(int attributeIndex, GrSLType type, const SkString& name);
/*
* this call is only for GrGLProgramEffects' internal use
*/
@ -46,6 +38,12 @@ public:
const GrGLShaderVar& positionAttribute() const { return *fPositionVar; }
private:
/*
* Add attribute will push a new attribute onto the end. It will also assert if there is
* a duplicate attribute
*/
bool addAttribute(const GrShaderVar& var);
/*
* Internal call for GrGLFullProgramBuilder.addVarying
*/
@ -69,9 +67,9 @@ private:
SkString fName;
};
SkSTArray<10, AttributePair, true> fEffectAttributes;
GrGLShaderVar* fPositionVar;
GrGLShaderVar* fLocalCoordsVar;
int fEffectAttribOffset;
friend class GrGLFullProgramBuilder;

View File

@ -162,6 +162,37 @@ bool GrGLProgramDesc::setRandom(SkRandom* random,
return true;
}
// TODO clean this up, we have to do this to test geometry processors but there has got to be
// a better way. In the mean time, we actually fill out these generic vertex attribs below with
// the correct vertex attribs from the GP. We have to ensure, however, we don't try to add more
// than two attributes.
GrVertexAttrib genericVertexAttribs[] = {
{ kVec2f_GrVertexAttribType, 0, kPosition_GrVertexAttribBinding },
{ kVec2f_GrVertexAttribType, 0, kEffect_GrVertexAttribBinding },
{ kVec2f_GrVertexAttribType, 0, kEffect_GrVertexAttribBinding }
};
/*
* convert sl type to vertexattrib type, not a complete implementation, only use for debugging
*/
GrVertexAttribType convert_sltype_to_attribtype(GrSLType type) {
switch (type) {
case kFloat_GrSLType:
return kFloat_GrVertexAttribType;
case kVec2f_GrSLType:
return kVec2f_GrVertexAttribType;
case kVec3f_GrSLType:
return kVec3f_GrVertexAttribType;
case kVec4f_GrSLType:
return kVec4f_GrVertexAttribType;
default:
SkFAIL("Type isn't convertible");
return kFloat_GrVertexAttribType;
}
}
// TODO end test hack
bool GrGpuGL::programUnitTest(int maxStages) {
GrTextureDesc dummyDesc;
@ -197,7 +228,6 @@ bool GrGpuGL::programUnitTest(int maxStages) {
int currAttribIndex = 1; // we need to always leave room for position
int currTextureCoordSet = 0;
int attribIndices[2] = { 0, 0 };
GrTexture* dummyTextures[] = {dummyTexture1.get(), dummyTexture2.get()};
int numStages = random.nextULessThan(maxStages + 1);
@ -220,19 +250,32 @@ bool GrGpuGL::programUnitTest(int maxStages) {
*this->caps(),
dummyTextures));
SkASSERT(effect);
// Only geometryProcessor can use vertex shader
if (!effect->requiresVertexShader()) {
continue;
}
int numAttribs = effect->numVertexAttribs();
for (int i = 0; i < numAttribs; ++i) {
attribIndices[i] = currAttribIndex++;
}
GrEffectStage* stage = SkNEW_ARGS(GrEffectStage,
(effect.get(), attribIndices[0], attribIndices[1]));
GrEffectStage* stage = SkNEW_ARGS(GrEffectStage, (effect.get()));
geometryProcessor.reset(stage);
// we have to set dummy vertex attribs
const GrEffect::VertexAttribArray& v = effect->getVertexAttribs();
int numVertexAttribs = v.count();
SkASSERT(GrEffect::kMaxVertexAttribs == 2 &&
GrEffect::kMaxVertexAttribs >= numVertexAttribs);
size_t runningStride = GrVertexAttribTypeSize(genericVertexAttribs[0].fType);
for (int i = 0; i < numVertexAttribs; i++) {
genericVertexAttribs[i + 1].fOffset = runningStride;
genericVertexAttribs[i + 1].fType =
convert_sltype_to_attribtype(v[i].getType());
runningStride += GrVertexAttribTypeSize(genericVertexAttribs[i + 1].fType);
}
// update the vertex attributes with the ds
GrDrawState* ds = this->drawState();
ds->setVertexAttribs<genericVertexAttribs>(numVertexAttribs + 1, runningStride);
currAttribIndex = numVertexAttribs + 1;
break;
}
}
@ -258,8 +301,7 @@ bool GrGpuGL::programUnitTest(int maxStages) {
}
currTextureCoordSet += numTransforms;
}
GrEffectStage* stage = SkNEW_ARGS(GrEffectStage,
(effect.get(), attribIndices[0], attribIndices[1]));
GrEffectStage* stage = SkNEW_ARGS(GrEffectStage, (effect.get()));
stages[s] = stage;
++s;
@ -288,6 +330,9 @@ bool GrGpuGL::programUnitTest(int maxStages) {
if (NULL == program.get()) {
return false;
}
// We have to reset the drawstate because we might have added a gp
this->drawState()->reset();
}
return true;
}