Mark when effects and programs have vertex code
Adds a 'hasVertexCode' method to GrEffect and a 'fHasVertexCode' field to GrGLProgramDesc::KeyHeader. Also adds a GrVertexEffect class that effects have to inherit from in order to set the 'hasVertexCode' flag and be able to emit vertex code, and updates the existing effects to use it as needed. R=bsalomon@google.com Author: cdalton@nvidia.com Review URL: https://codereview.chromium.org/23653059 git-svn-id: http://skia.googlecode.com/svn/trunk@11537 2bbb7eff-a529-9590-31e7-b0007b416f81
This commit is contained in:
parent
3400f4b00a
commit
234d4fba75
@ -17,6 +17,7 @@
|
||||
class GrBackendEffectFactory;
|
||||
class GrContext;
|
||||
class GrEffect;
|
||||
class GrVertexEffect;
|
||||
class SkString;
|
||||
|
||||
/**
|
||||
@ -152,7 +153,14 @@ public:
|
||||
/** Will this effect read the fragment position? */
|
||||
bool willReadFragmentPosition() const { return fWillReadFragmentPosition; }
|
||||
|
||||
int numVertexAttribs() const { return fVertexAttribTypes.count(); }
|
||||
/** Will this effect emit custom vertex shader code?
|
||||
(To set this value the effect must inherit from GrVertexEffect.) */
|
||||
bool hasVertexCode() const { return fHasVertexCode; }
|
||||
|
||||
int numVertexAttribs() const {
|
||||
SkASSERT(0 == fVertexAttribTypes.count() || fHasVertexCode);
|
||||
return fVertexAttribTypes.count();
|
||||
}
|
||||
|
||||
GrSLType vertexAttribType(int index) const { return fVertexAttribTypes[index]; }
|
||||
|
||||
@ -204,14 +212,11 @@ protected:
|
||||
*/
|
||||
void addTextureAccess(const GrTextureAccess* textureAccess);
|
||||
|
||||
/**
|
||||
* 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);
|
||||
|
||||
GrEffect() : fWillReadDstColor(false), fWillReadFragmentPosition(false), fEffectRef(NULL) {}
|
||||
GrEffect()
|
||||
: fWillReadDstColor(false)
|
||||
, fWillReadFragmentPosition(false)
|
||||
, fHasVertexCode(false)
|
||||
, fEffectRef(NULL) {}
|
||||
|
||||
/** This should be called by GrEffect subclass factories. See the comment on AutoEffectUnref for
|
||||
an example factory function. */
|
||||
@ -304,11 +309,13 @@ private:
|
||||
friend class GrEffectStage; // to rewrap GrEffect in GrEffectRef when restoring an effect-stage
|
||||
// from deferred state, to call isEqual on naked GrEffects, and
|
||||
// to inc/dec deferred ref counts.
|
||||
friend class GrVertexEffect; // to set fHasVertexCode and build fVertexAttribTypes.
|
||||
|
||||
SkSTArray<4, const GrTextureAccess*, true> fTextureAccesses;
|
||||
SkSTArray<kMaxVertexAttribs, GrSLType, true> fVertexAttribTypes;
|
||||
bool fWillReadDstColor;
|
||||
bool fWillReadFragmentPosition;
|
||||
bool fHasVertexCode;
|
||||
GrEffectRef* fEffectRef;
|
||||
|
||||
typedef SkRefCnt INHERITED;
|
||||
|
@ -21,6 +21,8 @@
|
||||
#include "gl/GrGLEffect.h"
|
||||
#include "gl/GrGLSL.h"
|
||||
|
||||
#include "effects/GrVertexEffect.h"
|
||||
|
||||
GrAAConvexPathRenderer::GrAAConvexPathRenderer() {
|
||||
}
|
||||
|
||||
@ -497,7 +499,7 @@ static void create_vertices(const SegmentArray& segments,
|
||||
* Requires shader derivative instruction support.
|
||||
*/
|
||||
|
||||
class QuadEdgeEffect : public GrEffect {
|
||||
class QuadEdgeEffect : public GrVertexEffect {
|
||||
public:
|
||||
|
||||
static GrEffectRef* Create() {
|
||||
@ -586,7 +588,7 @@ private:
|
||||
|
||||
GR_DECLARE_EFFECT_TEST;
|
||||
|
||||
typedef GrEffect INHERITED;
|
||||
typedef GrVertexEffect INHERITED;
|
||||
};
|
||||
|
||||
GR_DEFINE_EFFECT_TEST(QuadEdgeEffect);
|
||||
|
@ -10,6 +10,7 @@
|
||||
#include "gl/GrGLEffect.h"
|
||||
#include "GrTBackendEffectFactory.h"
|
||||
#include "SkColorPriv.h"
|
||||
#include "effects/GrVertexEffect.h"
|
||||
|
||||
SK_DEFINE_INST_COUNT(GrAARectRenderer)
|
||||
|
||||
@ -17,7 +18,7 @@ SK_DEFINE_INST_COUNT(GrAARectRenderer)
|
||||
class GrGLAlignedRectEffect;
|
||||
|
||||
// Axis Aligned special case
|
||||
class GrAlignedRectEffect : public GrEffect {
|
||||
class GrAlignedRectEffect : public GrVertexEffect {
|
||||
public:
|
||||
static GrEffectRef* Create() {
|
||||
GR_CREATE_STATIC_EFFECT(gAlignedRectEffect, GrAlignedRectEffect, ());
|
||||
@ -101,7 +102,7 @@ public:
|
||||
|
||||
|
||||
private:
|
||||
GrAlignedRectEffect() : GrEffect() {
|
||||
GrAlignedRectEffect() : GrVertexEffect() {
|
||||
this->addVertexAttrib(kVec4f_GrSLType);
|
||||
}
|
||||
|
||||
@ -109,7 +110,7 @@ private:
|
||||
|
||||
GR_DECLARE_EFFECT_TEST;
|
||||
|
||||
typedef GrEffect INHERITED;
|
||||
typedef GrVertexEffect INHERITED;
|
||||
};
|
||||
|
||||
|
||||
@ -137,7 +138,7 @@ 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 GrEffect {
|
||||
class GrRectEffect : public GrVertexEffect {
|
||||
public:
|
||||
static GrEffectRef* Create() {
|
||||
GR_CREATE_STATIC_EFFECT(gRectEffect, GrRectEffect, ());
|
||||
@ -236,7 +237,7 @@ public:
|
||||
|
||||
|
||||
private:
|
||||
GrRectEffect() : GrEffect() {
|
||||
GrRectEffect() : GrVertexEffect() {
|
||||
this->addVertexAttrib(kVec4f_GrSLType);
|
||||
this->addVertexAttrib(kVec2f_GrSLType);
|
||||
this->setWillReadFragmentPosition();
|
||||
@ -246,7 +247,7 @@ private:
|
||||
|
||||
GR_DECLARE_EFFECT_TEST;
|
||||
|
||||
typedef GrEffect INHERITED;
|
||||
typedef GrVertexEffect INHERITED;
|
||||
};
|
||||
|
||||
|
||||
|
@ -90,11 +90,6 @@ void GrEffect::addTextureAccess(const GrTextureAccess* access) {
|
||||
fTextureAccesses.push_back(access);
|
||||
}
|
||||
|
||||
void GrEffect::addVertexAttrib(GrSLType type) {
|
||||
SkASSERT(fVertexAttribTypes.count() < kMaxVertexAttribs);
|
||||
fVertexAttribTypes.push_back(type);
|
||||
}
|
||||
|
||||
void* GrEffect::operator new(size_t size) {
|
||||
return GrEffect_Globals::GetTLS()->allocate(size);
|
||||
}
|
||||
|
@ -19,6 +19,8 @@
|
||||
#include "SkRRect.h"
|
||||
#include "SkStrokeRec.h"
|
||||
|
||||
#include "effects/GrVertexEffect.h"
|
||||
|
||||
SK_DEFINE_INST_COUNT(GrOvalRenderer)
|
||||
|
||||
namespace {
|
||||
@ -56,7 +58,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 GrEffect {
|
||||
class CircleEdgeEffect : public GrVertexEffect {
|
||||
public:
|
||||
static GrEffectRef* Create(bool stroke) {
|
||||
GR_CREATE_STATIC_EFFECT(gCircleStrokeEdge, CircleEdgeEffect, (true));
|
||||
@ -134,7 +136,7 @@ public:
|
||||
|
||||
|
||||
private:
|
||||
CircleEdgeEffect(bool stroke) : GrEffect() {
|
||||
CircleEdgeEffect(bool stroke) : GrVertexEffect() {
|
||||
this->addVertexAttrib(kVec4f_GrSLType);
|
||||
fStroke = stroke;
|
||||
}
|
||||
@ -148,7 +150,7 @@ private:
|
||||
|
||||
GR_DECLARE_EFFECT_TEST;
|
||||
|
||||
typedef GrEffect INHERITED;
|
||||
typedef GrVertexEffect INHERITED;
|
||||
};
|
||||
|
||||
GR_DEFINE_EFFECT_TEST(CircleEdgeEffect);
|
||||
@ -170,7 +172,7 @@ GrEffectRef* CircleEdgeEffect::TestCreate(SkRandom* random,
|
||||
* We are using an implicit function of x^2/a^2 + y^2/b^2 - 1 = 0.
|
||||
*/
|
||||
|
||||
class EllipseEdgeEffect : public GrEffect {
|
||||
class EllipseEdgeEffect : public GrVertexEffect {
|
||||
public:
|
||||
static GrEffectRef* Create(bool stroke) {
|
||||
GR_CREATE_STATIC_EFFECT(gEllipseStrokeEdge, EllipseEdgeEffect, (true));
|
||||
@ -269,7 +271,7 @@ public:
|
||||
};
|
||||
|
||||
private:
|
||||
EllipseEdgeEffect(bool stroke) : GrEffect() {
|
||||
EllipseEdgeEffect(bool stroke) : GrVertexEffect() {
|
||||
this->addVertexAttrib(kVec2f_GrSLType);
|
||||
this->addVertexAttrib(kVec4f_GrSLType);
|
||||
fStroke = stroke;
|
||||
@ -284,7 +286,7 @@ private:
|
||||
|
||||
GR_DECLARE_EFFECT_TEST;
|
||||
|
||||
typedef GrEffect INHERITED;
|
||||
typedef GrVertexEffect INHERITED;
|
||||
};
|
||||
|
||||
GR_DEFINE_EFFECT_TEST(EllipseEdgeEffect);
|
||||
@ -307,7 +309,7 @@ GrEffectRef* EllipseEdgeEffect::TestCreate(SkRandom* random,
|
||||
* The result is device-independent and can be used with any affine matrix.
|
||||
*/
|
||||
|
||||
class DIEllipseEdgeEffect : public GrEffect {
|
||||
class DIEllipseEdgeEffect : public GrVertexEffect {
|
||||
public:
|
||||
enum Mode { kStroke = 0, kHairline, kFill };
|
||||
|
||||
@ -430,7 +432,7 @@ public:
|
||||
};
|
||||
|
||||
private:
|
||||
DIEllipseEdgeEffect(Mode mode) : GrEffect() {
|
||||
DIEllipseEdgeEffect(Mode mode) : GrVertexEffect() {
|
||||
this->addVertexAttrib(kVec2f_GrSLType);
|
||||
this->addVertexAttrib(kVec2f_GrSLType);
|
||||
fMode = mode;
|
||||
@ -445,7 +447,7 @@ private:
|
||||
|
||||
GR_DECLARE_EFFECT_TEST;
|
||||
|
||||
typedef GrEffect INHERITED;
|
||||
typedef GrVertexEffect INHERITED;
|
||||
};
|
||||
|
||||
GR_DEFINE_EFFECT_TEST(DIEllipseEdgeEffect);
|
||||
|
@ -128,7 +128,7 @@ const GrBackendEffectFactory& GrConicEffect::getFactory() const {
|
||||
return GrTBackendEffectFactory<GrConicEffect>::getInstance();
|
||||
}
|
||||
|
||||
GrConicEffect::GrConicEffect(GrBezierEdgeType edgeType) : GrEffect() {
|
||||
GrConicEffect::GrConicEffect(GrBezierEdgeType edgeType) : GrVertexEffect() {
|
||||
this->addVertexAttrib(kVec4f_GrSLType);
|
||||
fEdgeType = edgeType;
|
||||
}
|
||||
@ -260,7 +260,7 @@ const GrBackendEffectFactory& GrQuadEffect::getFactory() const {
|
||||
return GrTBackendEffectFactory<GrQuadEffect>::getInstance();
|
||||
}
|
||||
|
||||
GrQuadEffect::GrQuadEffect(GrBezierEdgeType edgeType) : GrEffect() {
|
||||
GrQuadEffect::GrQuadEffect(GrBezierEdgeType edgeType) : GrVertexEffect() {
|
||||
this->addVertexAttrib(kVec4f_GrSLType);
|
||||
fEdgeType = edgeType;
|
||||
}
|
||||
@ -403,7 +403,7 @@ const GrBackendEffectFactory& GrCubicEffect::getFactory() const {
|
||||
return GrTBackendEffectFactory<GrCubicEffect>::getInstance();
|
||||
}
|
||||
|
||||
GrCubicEffect::GrCubicEffect(GrBezierEdgeType edgeType) : GrEffect() {
|
||||
GrCubicEffect::GrCubicEffect(GrBezierEdgeType edgeType) : GrVertexEffect() {
|
||||
this->addVertexAttrib(kVec4f_GrSLType);
|
||||
fEdgeType = edgeType;
|
||||
}
|
||||
|
@ -8,8 +8,9 @@
|
||||
#ifndef GrBezierEffect_DEFINED
|
||||
#define GrBezierEffect_DEFINED
|
||||
|
||||
#include "GrEffect.h"
|
||||
#include "GrDrawTargetCaps.h"
|
||||
#include "GrEffect.h"
|
||||
#include "GrVertexEffect.h"
|
||||
|
||||
enum GrBezierEdgeType {
|
||||
kFillAA_GrBezierEdgeType,
|
||||
@ -67,7 +68,7 @@ static inline bool GrBezierEdgeTypeIsAA(const GrBezierEdgeType edgeType) {
|
||||
*/
|
||||
class GrGLConicEffect;
|
||||
|
||||
class GrConicEffect : public GrEffect {
|
||||
class GrConicEffect : public GrVertexEffect {
|
||||
public:
|
||||
static GrEffectRef* Create(const GrBezierEdgeType edgeType, const GrDrawTargetCaps& caps) {
|
||||
GR_CREATE_STATIC_EFFECT(gConicFillAA, GrConicEffect, (kFillAA_GrBezierEdgeType));
|
||||
@ -117,7 +118,7 @@ private:
|
||||
|
||||
GR_DECLARE_EFFECT_TEST;
|
||||
|
||||
typedef GrEffect INHERITED;
|
||||
typedef GrVertexEffect INHERITED;
|
||||
};
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
@ -131,7 +132,7 @@ private:
|
||||
*/
|
||||
class GrGLQuadEffect;
|
||||
|
||||
class GrQuadEffect : public GrEffect {
|
||||
class GrQuadEffect : public GrVertexEffect {
|
||||
public:
|
||||
static GrEffectRef* Create(const GrBezierEdgeType edgeType, const GrDrawTargetCaps& caps) {
|
||||
GR_CREATE_STATIC_EFFECT(gQuadFillAA, GrQuadEffect, (kFillAA_GrBezierEdgeType));
|
||||
@ -181,7 +182,7 @@ private:
|
||||
|
||||
GR_DECLARE_EFFECT_TEST;
|
||||
|
||||
typedef GrEffect INHERITED;
|
||||
typedef GrVertexEffect INHERITED;
|
||||
};
|
||||
|
||||
//////////////////////////////////////////////////////////////////////////////
|
||||
@ -197,7 +198,7 @@ private:
|
||||
*/
|
||||
class GrGLCubicEffect;
|
||||
|
||||
class GrCubicEffect : public GrEffect {
|
||||
class GrCubicEffect : public GrVertexEffect {
|
||||
public:
|
||||
static GrEffectRef* Create(const GrBezierEdgeType edgeType, const GrDrawTargetCaps& caps) {
|
||||
GR_CREATE_STATIC_EFFECT(gCubicFillAA, GrCubicEffect, (kFillAA_GrBezierEdgeType));
|
||||
@ -247,7 +248,7 @@ private:
|
||||
|
||||
GR_DECLARE_EFFECT_TEST;
|
||||
|
||||
typedef GrEffect INHERITED;
|
||||
typedef GrVertexEffect INHERITED;
|
||||
};
|
||||
|
||||
#endif
|
||||
|
@ -9,6 +9,7 @@
|
||||
#define GrCustomCoordsTextureEffect_DEFINED
|
||||
|
||||
#include "GrEffect.h"
|
||||
#include "GrVertexEffect.h"
|
||||
|
||||
class GrGLCustomCoordsTextureEffect;
|
||||
|
||||
@ -17,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 GrEffect {
|
||||
class GrCustomCoordsTextureEffect : public GrVertexEffect {
|
||||
public:
|
||||
static GrEffectRef* Create(GrTexture* tex, const GrTextureParams& p) {
|
||||
AutoEffectUnref effect(SkNEW_ARGS(GrCustomCoordsTextureEffect, (tex, p)));
|
||||
@ -43,7 +44,7 @@ private:
|
||||
|
||||
GR_DECLARE_EFFECT_TEST;
|
||||
|
||||
typedef GrEffect INHERITED;
|
||||
typedef GrVertexEffect INHERITED;
|
||||
};
|
||||
|
||||
#endif
|
||||
|
37
src/gpu/effects/GrVertexEffect.h
Normal file
37
src/gpu/effects/GrVertexEffect.h
Normal file
@ -0,0 +1,37 @@
|
||||
/*
|
||||
* 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() { fHasVertexCode = 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
|
@ -19,7 +19,8 @@ inline GrGLEffect::EffectKey get_key_and_update_stats(const GrEffectStage& stage
|
||||
const GrGLCaps& caps,
|
||||
bool useExplicitLocalCoords,
|
||||
bool* setTrueIfReadsDst,
|
||||
bool* setTrueIfReadsPos) {
|
||||
bool* setTrueIfReadsPos,
|
||||
bool* setTrueIfHasVertexCode) {
|
||||
const GrEffectRef& effect = *stage.getEffect();
|
||||
const GrBackendEffectFactory& factory = effect->getFactory();
|
||||
GrDrawEffect drawEffect(stage, useExplicitLocalCoords);
|
||||
@ -29,6 +30,9 @@ inline GrGLEffect::EffectKey get_key_and_update_stats(const GrEffectStage& stage
|
||||
if (effect->willReadFragmentPosition()) {
|
||||
*setTrueIfReadsPos = true;
|
||||
}
|
||||
if (effect->hasVertexCode()) {
|
||||
*setTrueIfHasVertexCode = true;
|
||||
}
|
||||
return factory.glEffectKey(drawEffect, caps);
|
||||
}
|
||||
}
|
||||
@ -87,21 +91,25 @@ void GrGLProgramDesc::Build(const GrDrawState& drawState,
|
||||
int currEffectKey = 0;
|
||||
bool readsDst = false;
|
||||
bool readFragPosition = false;
|
||||
bool hasVertexCode = false;
|
||||
if (!skipColor) {
|
||||
for (int s = 0; s < drawState.numColorStages(); ++s) {
|
||||
effectKeys[currEffectKey++] =
|
||||
get_key_and_update_stats(drawState.getColorStage(s), gpu->glCaps(),
|
||||
requiresLocalCoordAttrib, &readsDst, &readFragPosition);
|
||||
requiresLocalCoordAttrib, &readsDst, &readFragPosition,
|
||||
&hasVertexCode);
|
||||
}
|
||||
}
|
||||
if (!skipCoverage) {
|
||||
for (int s = 0; s < drawState.numCoverageStages(); ++s) {
|
||||
effectKeys[currEffectKey++] =
|
||||
get_key_and_update_stats(drawState.getCoverageStage(s), gpu->glCaps(),
|
||||
requiresLocalCoordAttrib, &readsDst, &readFragPosition);
|
||||
requiresLocalCoordAttrib, &readsDst, &readFragPosition,
|
||||
&hasVertexCode);
|
||||
}
|
||||
}
|
||||
|
||||
header->fHasVertexCode = hasVertexCode || requiresLocalCoordAttrib;
|
||||
header->fEmitsPointSize = isPoints;
|
||||
header->fColorFilterXfermode = skipColor ? SkXfermode::kDst_Mode : drawState.getColorFilterMode();
|
||||
|
||||
@ -122,6 +130,7 @@ void GrGLProgramDesc::Build(const GrDrawState& drawState,
|
||||
header->fColorInput = kUniform_ColorInput;
|
||||
} else {
|
||||
header->fColorInput = kAttribute_ColorInput;
|
||||
header->fHasVertexCode = true;
|
||||
}
|
||||
|
||||
bool covIsSolidWhite = !requiresCoverageAttrib && 0xffffffff == drawState.getCoverage();
|
||||
@ -134,6 +143,7 @@ void GrGLProgramDesc::Build(const GrDrawState& drawState,
|
||||
header->fCoverageInput = kUniform_ColorInput;
|
||||
} else {
|
||||
header->fCoverageInput = kAttribute_ColorInput;
|
||||
header->fHasVertexCode = true;
|
||||
}
|
||||
|
||||
if (readsDst) {
|
||||
|
@ -158,6 +158,7 @@ private:
|
||||
uint8_t fCoverageInput; // casts to enum ColorInput
|
||||
uint8_t fCoverageOutput; // casts to enum CoverageOutput
|
||||
|
||||
SkBool8 fHasVertexCode;
|
||||
SkBool8 fEmitsPointSize;
|
||||
uint8_t fColorFilterXfermode; // casts to enum SkXfermode::Mode
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user