Revert of Added varying struct (patchset #9 id:160001 of https://codereview.chromium.org/671023002/)

Reason for revert:
may have caused gm change on arm

Original issue's description:
> Added varying struct
>
> TBR=
> BUG=skia:
>
> Committed: https://skia.googlesource.com/skia/+/852ae80b9c3c6fd53f993ac35133d80863993cbe

TBR=bsalomon@google.com,joshualitt@chromium.org
NOTREECHECKS=true
NOTRY=true
BUG=skia:

Review URL: https://codereview.chromium.org/675193002
This commit is contained in:
joshualitt 2014-10-24 08:24:08 -07:00 committed by Commit bot
parent 20b7960798
commit c6f3e2c17b
17 changed files with 264 additions and 308 deletions

View File

@ -23,8 +23,7 @@
*/
class GrGeometryProcessor : public GrProcessor {
public:
GrGeometryProcessor()
: fWillUseGeoShader(false) {}
GrGeometryProcessor() {}
virtual const GrBackendGeometryProcessorFactory& getFactory() const = 0;
@ -38,8 +37,6 @@ public:
const VertexAttribArray& getVertexAttribs() const { return fVertexAttribs; }
bool willUseGeoShader() const { return fWillUseGeoShader; }
/** Returns true if this and other processor conservatively draw identically. It can only return
true when the two prcoessors are of the same subclass (i.e. they return the same object from
from getFactory()).
@ -64,13 +61,10 @@ protected:
return fVertexAttribs.push_back(var);
}
void setWillUseGeoShader() { fWillUseGeoShader = true; }
private:
virtual bool onIsEqual(const GrGeometryProcessor&) const = 0;
SkSTArray<kMaxVertexAttribs, GrShaderVar, true> fVertexAttribs;
bool fWillUseGeoShader;
typedef GrProcessor INHERITED;
};

View File

@ -529,38 +529,38 @@ public:
: INHERITED (factory) {}
virtual void emitCode(const EmitArgs& args) SK_OVERRIDE {
GrGLVertToFrag v(kVec4f_GrSLType);
args.fPB->addVarying("QuadEdge", &v);
const char *vsName, *fsName;
args.fPB->addVarying(kVec4f_GrSLType, "QuadEdge", &vsName, &fsName);
GrGLGPFragmentBuilder* fsBuilder = args.fPB->getFragmentShaderBuilder();
SkAssertResult(fsBuilder->enableFeature(
GrGLFragmentShaderBuilder::kStandardDerivatives_GLSLFeature));
fsBuilder->codeAppendf("float edgeAlpha;");
fsBuilder->codeAppendf("\t\tfloat edgeAlpha;\n");
// keep the derivative instructions outside the conditional
fsBuilder->codeAppendf("vec2 duvdx = dFdx(%s.xy);", v.fsIn());
fsBuilder->codeAppendf("vec2 duvdy = dFdy(%s.xy);", v.fsIn());
fsBuilder->codeAppendf("if (%s.z > 0.0 && %s.w > 0.0) {", v.fsIn(), v.fsIn());
fsBuilder->codeAppendf("\t\tvec2 duvdx = dFdx(%s.xy);\n", fsName);
fsBuilder->codeAppendf("\t\tvec2 duvdy = dFdy(%s.xy);\n", fsName);
fsBuilder->codeAppendf("\t\tif (%s.z > 0.0 && %s.w > 0.0) {\n", fsName, fsName);
// today we know z and w are in device space. We could use derivatives
fsBuilder->codeAppendf("edgeAlpha = min(min(%s.z, %s.w) + 0.5, 1.0);", v.fsIn(),
v.fsIn());
fsBuilder->codeAppendf ("} else {");
fsBuilder->codeAppendf("vec2 gF = vec2(2.0*%s.x*duvdx.x - duvdx.y,"
" 2.0*%s.x*duvdy.x - duvdy.y);",
v.fsIn(), v.fsIn());
fsBuilder->codeAppendf("edgeAlpha = (%s.x*%s.x - %s.y);", v.fsIn(), v.fsIn(),
v.fsIn());
fsBuilder->codeAppendf("edgeAlpha = "
"clamp(0.5 - edgeAlpha / length(gF), 0.0, 1.0);}");
fsBuilder->codeAppendf("\t\t\tedgeAlpha = min(min(%s.z, %s.w) + 0.5, 1.0);\n", fsName,
fsName);
fsBuilder->codeAppendf ("\t\t} else {\n");
fsBuilder->codeAppendf("\t\t\tvec2 gF = vec2(2.0*%s.x*duvdx.x - duvdx.y,\n"
"\t\t\t 2.0*%s.x*duvdy.x - duvdy.y);\n",
fsName, fsName);
fsBuilder->codeAppendf("\t\t\tedgeAlpha = (%s.x*%s.x - %s.y);\n", fsName, fsName,
fsName);
fsBuilder->codeAppendf("\t\t\tedgeAlpha = "
"clamp(0.5 - edgeAlpha / length(gF), 0.0, 1.0);\n\t\t}\n");
fsBuilder->codeAppendf("%s = %s;", args.fOutput,
fsBuilder->codeAppendf("\t%s = %s;\n", args.fOutput,
(GrGLSLExpr4(args.fInput) * GrGLSLExpr1("edgeAlpha")).c_str());
const GrShaderVar& inQuadEdge = args.fGP.cast<QuadEdgeEffect>().inQuadEdge();
GrGLVertexBuilder* vsBuilder = args.fPB->getVertexShaderBuilder();
vsBuilder->codeAppendf("\t%s = %s;\n", v.vsOut(), inQuadEdge.c_str());
vsBuilder->codeAppendf("\t%s = %s;\n", vsName, inQuadEdge.c_str());
}
static inline void GenKey(const GrProcessor&, const GrGLCaps&, GrProcessorKeyBuilder*) {}

View File

@ -45,17 +45,17 @@ public:
// setup the varying for the Axis aligned rect effect
// xy -> interpolated offset
// zw -> w/2+0.5, h/2+0.5
GrGLVertToFrag v(kVec4f_GrSLType);
args.fPB->addVarying("Rect", &v);
const char *vsRectName, *fsRectName;
args.fPB->addVarying(kVec4f_GrSLType, "Rect", &vsRectName, &fsRectName);
const GrShaderVar& inRect = args.fGP.cast<GrAlignedRectEffect>().inRect();
GrGLVertexBuilder* vsBuilder = args.fPB->getVertexShaderBuilder();
vsBuilder->codeAppendf("\t%s = %s;\n", v.fsIn(), inRect.c_str());
vsBuilder->codeAppendf("\t%s = %s;\n", vsRectName, inRect.c_str());
GrGLGPFragmentBuilder* fsBuilder = args.fPB->getFragmentShaderBuilder();
// TODO: compute all these offsets, spans, and scales in the VS
fsBuilder->codeAppendf("\tfloat insetW = min(1.0, %s.z) - 0.5;\n", v.fsIn());
fsBuilder->codeAppendf("\tfloat insetH = min(1.0, %s.w) - 0.5;\n", v.fsIn());
fsBuilder->codeAppendf("\tfloat insetW = min(1.0, %s.z) - 0.5;\n", fsRectName);
fsBuilder->codeAppendf("\tfloat insetH = min(1.0, %s.w) - 0.5;\n", fsRectName);
fsBuilder->codeAppend("\tfloat outset = 0.5;\n");
// For rects > 1 pixel wide and tall the span's are noops (i.e., 1.0). For rects
// < 1 pixel wide or tall they serve to normalize the < 1 ramp to a 0 .. 1 range.
@ -69,12 +69,12 @@ public:
// Compute the coverage for the rect's width
fsBuilder->codeAppendf(
"\tfloat coverage = scaleW*clamp((%s.z-abs(%s.x))/spanW, 0.0, 1.0);\n", v.fsIn(),
v.fsIn());
"\tfloat coverage = scaleW*clamp((%s.z-abs(%s.x))/spanW, 0.0, 1.0);\n", fsRectName,
fsRectName);
// Compute the coverage for the rect's height and merge with the width
fsBuilder->codeAppendf(
"\tcoverage = coverage*scaleH*clamp((%s.w-abs(%s.y))/spanH, 0.0, 1.0);\n",
v.fsIn(), v.fsIn());
fsRectName, fsRectName);
fsBuilder->codeAppendf("\t%s = %s;\n", args.fOutput,
@ -163,24 +163,26 @@ public:
virtual void emitCode(const EmitArgs& args) SK_OVERRIDE {
// setup the varying for the center point and the unit vector
// that points down the height of the rect
GrGLVertToFrag rectEdge(kVec4f_GrSLType);
args.fPB->addVarying("RectEdge", &rectEdge);
const char *vsRectEdgeName, *fsRectEdgeName;
args.fPB->addVarying(kVec4f_GrSLType, "RectEdge",
&vsRectEdgeName, &fsRectEdgeName);
const GrRectEffect& rectEffect = args.fGP.cast<GrRectEffect>();
GrGLVertexBuilder* vsBuilder = args.fPB->getVertexShaderBuilder();
vsBuilder->codeAppendf("%s = %s;", rectEdge.vsOut(), rectEffect.inRectEdge().c_str());
vsBuilder->codeAppendf("%s = %s;", vsRectEdgeName, rectEffect.inRectEdge().c_str());
// setup the varying for width/2+.5 and height/2+.5
GrGLVertToFrag widthHeight(kVec2f_GrSLType);
args.fPB->addVarying("WidthHeight", &widthHeight);
const char *vsWidthHeightName, *fsWidthHeightName;
args.fPB->addVarying(kVec2f_GrSLType, "WidthHeight",
&vsWidthHeightName, &fsWidthHeightName);
vsBuilder->codeAppendf("%s = %s;",
widthHeight.vsOut(),
vsWidthHeightName,
rectEffect.inWidthHeight().c_str());
GrGLGPFragmentBuilder* fsBuilder = args.fPB->getFragmentShaderBuilder();
// TODO: compute all these offsets, spans, and scales in the VS
fsBuilder->codeAppendf("\tfloat insetW = min(1.0, %s.x) - 0.5;\n", widthHeight.fsIn());
fsBuilder->codeAppendf("\tfloat insetH = min(1.0, %s.y) - 0.5;\n", widthHeight.fsIn());
fsBuilder->codeAppendf("\tfloat insetW = min(1.0, %s.x) - 0.5;\n", fsWidthHeightName);
fsBuilder->codeAppendf("\tfloat insetH = min(1.0, %s.y) - 0.5;\n", fsWidthHeightName);
fsBuilder->codeAppend("\tfloat outset = 0.5;\n");
// For rects > 1 pixel wide and tall the span's are noops (i.e., 1.0). For rects
// < 1 pixel wide or tall they serve to normalize the < 1 ramp to a 0 .. 1 range.
@ -194,19 +196,19 @@ public:
// Compute the coverage for the rect's width
fsBuilder->codeAppendf("\tvec2 offset = %s.xy - %s.xy;\n",
fsBuilder->fragmentPosition(), rectEdge.fsIn());
fsBuilder->fragmentPosition(), fsRectEdgeName);
fsBuilder->codeAppendf("\tfloat perpDot = abs(offset.x * %s.w - offset.y * %s.z);\n",
rectEdge.fsIn(), rectEdge.fsIn());
fsRectEdgeName, fsRectEdgeName);
fsBuilder->codeAppendf(
"\tfloat coverage = scaleW*clamp((%s.x-perpDot)/spanW, 0.0, 1.0);\n",
widthHeight.fsIn());
fsWidthHeightName);
// Compute the coverage for the rect's height and merge with the width
fsBuilder->codeAppendf("\tperpDot = abs(dot(offset, %s.zw));\n",
rectEdge.fsIn());
fsRectEdgeName);
fsBuilder->codeAppendf(
"\tcoverage = coverage*scaleH*clamp((%s.y-perpDot)/spanH, 0.0, 1.0);\n",
widthHeight.fsIn());
fsWidthHeightName);
fsBuilder->codeAppendf("\t%s = %s;\n", args.fOutput,

View File

@ -94,22 +94,21 @@ public:
virtual void emitCode(const EmitArgs& args) SK_OVERRIDE {
const CircleEdgeEffect& circleEffect = args.fGP.cast<CircleEdgeEffect>();
GrGLVertToFrag v(kVec4f_GrSLType);
args.fPB->addVarying("CircleEdge", &v);
const char *vsName, *fsName;
args.fPB->addVarying(kVec4f_GrSLType, "CircleEdge", &vsName, &fsName);
GrGLVertexBuilder* vsBuilder = args.fPB->getVertexShaderBuilder();;
vsBuilder->codeAppendf("%s = %s;", v.vsOut(), circleEffect.inCircleEdge().c_str());
vsBuilder->codeAppendf("\t%s = %s;\n", vsName, circleEffect.inCircleEdge().c_str());
GrGLGPFragmentBuilder* fsBuilder = args.fPB->getFragmentShaderBuilder();
fsBuilder->codeAppendf("float d = length(%s.xy);", v.fsIn());
fsBuilder->codeAppendf("float edgeAlpha = clamp(%s.z - d, 0.0, 1.0);", v.fsIn());
fsBuilder->codeAppendf("\tfloat d = length(%s.xy);\n", fsName);
fsBuilder->codeAppendf("\tfloat edgeAlpha = clamp(%s.z - d, 0.0, 1.0);\n", fsName);
if (circleEffect.isStroked()) {
fsBuilder->codeAppendf("float innerAlpha = clamp(d - %s.w, 0.0, 1.0);",
v.fsIn());
fsBuilder->codeAppend("edgeAlpha *= innerAlpha;");
fsBuilder->codeAppendf("\tfloat innerAlpha = clamp(d - %s.w, 0.0, 1.0);\n", fsName);
fsBuilder->codeAppend("\tedgeAlpha *= innerAlpha;\n");
}
fsBuilder->codeAppendf("%s = %s;\n", args.fOutput,
fsBuilder->codeAppendf("\t%s = %s;\n", args.fOutput,
(GrGLSLExpr4(args.fInput) * GrGLSLExpr1("edgeAlpha")).c_str());
}
@ -207,43 +206,39 @@ public:
virtual void emitCode(const EmitArgs& args) SK_OVERRIDE {
const EllipseEdgeEffect& ellipseEffect = args.fGP.cast<EllipseEdgeEffect>();
GrGLVertToFrag ellipseOffsets(kVec2f_GrSLType);
args.fPB->addVarying("EllipseOffsets", &ellipseOffsets);
const char *vsOffsetName, *fsOffsetName;
const char *vsRadiiName, *fsRadiiName;
args.fPB->addVarying(kVec2f_GrSLType, "EllipseOffsets", &vsOffsetName, &fsOffsetName);
GrGLVertexBuilder* vsBuilder = args.fPB->getVertexShaderBuilder();
vsBuilder->codeAppendf("%s = %s;", ellipseOffsets.vsOut(),
vsBuilder->codeAppendf("%s = %s;", vsOffsetName,
ellipseEffect.inEllipseOffset().c_str());
GrGLVertToFrag ellipseRadii(kVec4f_GrSLType);
args.fPB->addVarying("EllipseRadii", &ellipseRadii);
vsBuilder->codeAppendf("%s = %s;", ellipseRadii.vsOut(),
ellipseEffect.inEllipseRadii().c_str());
args.fPB->addVarying(kVec4f_GrSLType, "EllipseRadii", &vsRadiiName, &fsRadiiName);
vsBuilder->codeAppendf("%s = %s;", vsRadiiName, ellipseEffect.inEllipseRadii().c_str());
// for outer curve
GrGLGPFragmentBuilder* fsBuilder = args.fPB->getFragmentShaderBuilder();
fsBuilder->codeAppendf("vec2 scaledOffset = %s*%s.xy;", ellipseOffsets.fsIn(),
ellipseRadii.fsIn());
fsBuilder->codeAppend("float test = dot(scaledOffset, scaledOffset) - 1.0;");
fsBuilder->codeAppendf("vec2 grad = 2.0*scaledOffset*%s.xy;", ellipseRadii.fsIn());
fsBuilder->codeAppend("float grad_dot = dot(grad, grad);");
fsBuilder->codeAppendf("\tvec2 scaledOffset = %s*%s.xy;\n", fsOffsetName, fsRadiiName);
fsBuilder->codeAppend("\tfloat test = dot(scaledOffset, scaledOffset) - 1.0;\n");
fsBuilder->codeAppendf("\tvec2 grad = 2.0*scaledOffset*%s.xy;\n", fsRadiiName);
fsBuilder->codeAppend("\tfloat grad_dot = dot(grad, grad);\n");
// avoid calling inversesqrt on zero.
fsBuilder->codeAppend("grad_dot = max(grad_dot, 1.0e-4);");
fsBuilder->codeAppend("float invlen = inversesqrt(grad_dot);");
fsBuilder->codeAppend("float edgeAlpha = clamp(0.5-test*invlen, 0.0, 1.0);");
fsBuilder->codeAppend("\tgrad_dot = max(grad_dot, 1.0e-4);\n");
fsBuilder->codeAppend("\tfloat invlen = inversesqrt(grad_dot);\n");
fsBuilder->codeAppend("\tfloat edgeAlpha = clamp(0.5-test*invlen, 0.0, 1.0);\n");
// for inner curve
if (ellipseEffect.isStroked()) {
fsBuilder->codeAppendf("scaledOffset = %s*%s.zw;",
ellipseOffsets.fsIn(), ellipseRadii.fsIn());
fsBuilder->codeAppend("test = dot(scaledOffset, scaledOffset) - 1.0;");
fsBuilder->codeAppendf("grad = 2.0*scaledOffset*%s.zw;",
ellipseRadii.fsIn());
fsBuilder->codeAppend("invlen = inversesqrt(dot(grad, grad));");
fsBuilder->codeAppend("edgeAlpha *= clamp(0.5+test*invlen, 0.0, 1.0);");
fsBuilder->codeAppendf("\tscaledOffset = %s*%s.zw;\n", fsOffsetName, fsRadiiName);
fsBuilder->codeAppend("\ttest = dot(scaledOffset, scaledOffset) - 1.0;\n");
fsBuilder->codeAppendf("\tgrad = 2.0*scaledOffset*%s.zw;\n", fsRadiiName);
fsBuilder->codeAppend("\tinvlen = inversesqrt(dot(grad, grad));\n");
fsBuilder->codeAppend("\tedgeAlpha *= clamp(0.5+test*invlen, 0.0, 1.0);\n");
}
fsBuilder->codeAppendf("%s = %s;", args.fOutput,
fsBuilder->codeAppendf("\t%s = %s;\n", args.fOutput,
(GrGLSLExpr4(args.fInput) * GrGLSLExpr1("edgeAlpha")).c_str());
}
@ -353,57 +348,57 @@ public:
virtual void emitCode(const EmitArgs& args) SK_OVERRIDE {
const DIEllipseEdgeEffect& ellipseEffect = args.fGP.cast<DIEllipseEdgeEffect>();
GrGLVertToFrag offsets0(kVec2f_GrSLType);
args.fPB->addVarying("EllipseOffsets0", &offsets0);
const char *vsOffsetName0, *fsOffsetName0;
args.fPB->addVarying(kVec2f_GrSLType, "EllipseOffsets0",
&vsOffsetName0, &fsOffsetName0);
GrGLVertexBuilder* vsBuilder = args.fPB->getVertexShaderBuilder();
vsBuilder->codeAppendf("%s = %s;", offsets0.vsOut(),
vsBuilder->codeAppendf("%s = %s;", vsOffsetName0,
ellipseEffect.inEllipseOffsets0().c_str());
GrGLVertToFrag offsets1(kVec2f_GrSLType);
args.fPB->addVarying("EllipseOffsets1", &offsets1);
vsBuilder->codeAppendf("%s = %s;", offsets1.vsOut(),
const char *vsOffsetName1, *fsOffsetName1;
args.fPB->addVarying(kVec2f_GrSLType, "EllipseOffsets1",
&vsOffsetName1, &fsOffsetName1);
vsBuilder->codeAppendf("\t%s = %s;\n", vsOffsetName1,
ellipseEffect.inEllipseOffsets1().c_str());
GrGLGPFragmentBuilder* fsBuilder = args.fPB->getFragmentShaderBuilder();
SkAssertResult(fsBuilder->enableFeature(
GrGLFragmentShaderBuilder::kStandardDerivatives_GLSLFeature));
// for outer curve
fsBuilder->codeAppendf("vec2 scaledOffset = %s.xy;", offsets0.fsIn());
fsBuilder->codeAppend("float test = dot(scaledOffset, scaledOffset) - 1.0;");
fsBuilder->codeAppendf("vec2 duvdx = dFdx(%s);", offsets0.fsIn());
fsBuilder->codeAppendf("vec2 duvdy = dFdy(%s);", offsets0.fsIn());
fsBuilder->codeAppendf("vec2 grad = vec2(2.0*%s.x*duvdx.x + 2.0*%s.y*duvdx.y,"
" 2.0*%s.x*duvdy.x + 2.0*%s.y*duvdy.y);",
offsets0.fsIn(), offsets0.fsIn(), offsets0.fsIn(), offsets0.fsIn());
fsBuilder->codeAppendf("\tvec2 scaledOffset = %s.xy;\n", fsOffsetName0);
fsBuilder->codeAppend("\tfloat test = dot(scaledOffset, scaledOffset) - 1.0;\n");
fsBuilder->codeAppendf("\tvec2 duvdx = dFdx(%s);\n", fsOffsetName0);
fsBuilder->codeAppendf("\tvec2 duvdy = dFdy(%s);\n", fsOffsetName0);
fsBuilder->codeAppendf("\tvec2 grad = vec2(2.0*%s.x*duvdx.x + 2.0*%s.y*duvdx.y,\n"
"\t 2.0*%s.x*duvdy.x + 2.0*%s.y*duvdy.y);\n",
fsOffsetName0, fsOffsetName0, fsOffsetName0, fsOffsetName0);
fsBuilder->codeAppend("float grad_dot = dot(grad, grad);");
fsBuilder->codeAppend("\tfloat grad_dot = dot(grad, grad);\n");
// avoid calling inversesqrt on zero.
fsBuilder->codeAppend("grad_dot = max(grad_dot, 1.0e-4);");
fsBuilder->codeAppend("float invlen = inversesqrt(grad_dot);");
fsBuilder->codeAppend("\tgrad_dot = max(grad_dot, 1.0e-4);\n");
fsBuilder->codeAppend("\tfloat invlen = inversesqrt(grad_dot);\n");
if (kHairline == ellipseEffect.getMode()) {
// can probably do this with one step
fsBuilder->codeAppend("float edgeAlpha = clamp(1.0-test*invlen, 0.0, 1.0);");
fsBuilder->codeAppend("edgeAlpha *= clamp(1.0+test*invlen, 0.0, 1.0);");
fsBuilder->codeAppend("\tfloat edgeAlpha = clamp(1.0-test*invlen, 0.0, 1.0);\n");
fsBuilder->codeAppend("\tedgeAlpha *= clamp(1.0+test*invlen, 0.0, 1.0);\n");
} else {
fsBuilder->codeAppend("float edgeAlpha = clamp(0.5-test*invlen, 0.0, 1.0);");
fsBuilder->codeAppend("\tfloat edgeAlpha = clamp(0.5-test*invlen, 0.0, 1.0);\n");
}
// for inner curve
if (kStroke == ellipseEffect.getMode()) {
fsBuilder->codeAppendf("scaledOffset = %s.xy;", offsets1.fsIn());
fsBuilder->codeAppend("test = dot(scaledOffset, scaledOffset) - 1.0;");
fsBuilder->codeAppendf("duvdx = dFdx(%s);", offsets1.fsIn());
fsBuilder->codeAppendf("duvdy = dFdy(%s);", offsets1.fsIn());
fsBuilder->codeAppendf("grad = vec2(2.0*%s.x*duvdx.x + 2.0*%s.y*duvdx.y,"
" 2.0*%s.x*duvdy.x + 2.0*%s.y*duvdy.y);",
offsets1.fsIn(), offsets1.fsIn(), offsets1.fsIn(),
offsets1.fsIn());
fsBuilder->codeAppend("invlen = inversesqrt(dot(grad, grad));");
fsBuilder->codeAppend("edgeAlpha *= clamp(0.5+test*invlen, 0.0, 1.0);");
fsBuilder->codeAppendf("\tscaledOffset = %s.xy;\n", fsOffsetName1);
fsBuilder->codeAppend("\ttest = dot(scaledOffset, scaledOffset) - 1.0;\n");
fsBuilder->codeAppendf("\tduvdx = dFdx(%s);\n", fsOffsetName1);
fsBuilder->codeAppendf("\tduvdy = dFdy(%s);\n", fsOffsetName1);
fsBuilder->codeAppendf("\tgrad = vec2(2.0*%s.x*duvdx.x + 2.0*%s.y*duvdx.y,\n"
"\t 2.0*%s.x*duvdy.x + 2.0*%s.y*duvdy.y);\n",
fsOffsetName1, fsOffsetName1, fsOffsetName1, fsOffsetName1);
fsBuilder->codeAppend("\tinvlen = inversesqrt(dot(grad, grad));\n");
fsBuilder->codeAppend("\tedgeAlpha *= clamp(0.5+test*invlen, 0.0, 1.0);\n");
}
fsBuilder->codeAppendf("%s = %s;", args.fOutput,
fsBuilder->codeAppendf("\t%s = %s;\n", args.fOutput,
(GrGLSLExpr4(args.fInput) * GrGLSLExpr1("edgeAlpha")).c_str());
}

View File

@ -37,12 +37,13 @@ GrGLConicEffect::GrGLConicEffect(const GrBackendProcessorFactory& factory,
}
void GrGLConicEffect::emitCode(const EmitArgs& args) {
GrGLVertToFrag v(kVec4f_GrSLType);
args.fPB->addVarying("ConicCoeffs", &v);
const char *vsName, *fsName;
args.fPB->addVarying(kVec4f_GrSLType, "ConicCoeffs", &vsName, &fsName);
const GrShaderVar& inConicCoeffs = args.fGP.cast<GrConicEffect>().inConicCoeffs();
GrGLVertexBuilder* vsBuilder = args.fPB->getVertexShaderBuilder();
vsBuilder->codeAppendf("%s = %s;", v.vsOut(), inConicCoeffs.c_str());
vsBuilder->codeAppendf("%s = %s;", vsName, inConicCoeffs.c_str());
GrGLGPFragmentBuilder* fsBuilder = args.fPB->getFragmentShaderBuilder();
fsBuilder->codeAppend("float edgeAlpha;");
@ -51,18 +52,18 @@ void GrGLConicEffect::emitCode(const EmitArgs& args) {
case kHairlineAA_GrProcessorEdgeType: {
SkAssertResult(fsBuilder->enableFeature(
GrGLFragmentShaderBuilder::kStandardDerivatives_GLSLFeature));
fsBuilder->codeAppendf("vec3 dklmdx = dFdx(%s.xyz);", v.fsIn());
fsBuilder->codeAppendf("vec3 dklmdy = dFdy(%s.xyz);", v.fsIn());
fsBuilder->codeAppendf("vec3 dklmdx = dFdx(%s.xyz);", fsName);
fsBuilder->codeAppendf("vec3 dklmdy = dFdy(%s.xyz);", fsName);
fsBuilder->codeAppendf("float dfdx ="
"2.0 * %s.x * dklmdx.x - %s.y * dklmdx.z - %s.z * dklmdx.y;",
v.fsIn(), v.fsIn(), v.fsIn());
fsName, fsName, fsName);
fsBuilder->codeAppendf("float dfdy ="
"2.0 * %s.x * dklmdy.x - %s.y * dklmdy.z - %s.z * dklmdy.y;",
v.fsIn(), v.fsIn(), v.fsIn());
fsName, fsName, fsName);
fsBuilder->codeAppend("vec2 gF = vec2(dfdx, dfdy);");
fsBuilder->codeAppend("float gFM = sqrt(dot(gF, gF));");
fsBuilder->codeAppendf("float func = %s.x*%s.x - %s.y*%s.z;", v.fsIn(), v.fsIn(),
v.fsIn(), v.fsIn());
fsBuilder->codeAppendf("float func = %s.x*%s.x - %s.y*%s.z;", fsName, fsName,
fsName, fsName);
fsBuilder->codeAppend("func = abs(func);");
fsBuilder->codeAppend("edgeAlpha = func / gFM;");
fsBuilder->codeAppend("edgeAlpha = max(1.0 - edgeAlpha, 0.0);");
@ -73,18 +74,18 @@ void GrGLConicEffect::emitCode(const EmitArgs& args) {
case kFillAA_GrProcessorEdgeType: {
SkAssertResult(fsBuilder->enableFeature(
GrGLFragmentShaderBuilder::kStandardDerivatives_GLSLFeature));
fsBuilder->codeAppendf("vec3 dklmdx = dFdx(%s.xyz);", v.fsIn());
fsBuilder->codeAppendf("vec3 dklmdy = dFdy(%s.xyz);", v.fsIn());
fsBuilder->codeAppendf("vec3 dklmdx = dFdx(%s.xyz);", fsName);
fsBuilder->codeAppendf("vec3 dklmdy = dFdy(%s.xyz);", fsName);
fsBuilder->codeAppendf("float dfdx ="
"2.0 * %s.x * dklmdx.x - %s.y * dklmdx.z - %s.z * dklmdx.y;",
v.fsIn(), v.fsIn(), v.fsIn());
fsName, fsName, fsName);
fsBuilder->codeAppendf("float dfdy ="
"2.0 * %s.x * dklmdy.x - %s.y * dklmdy.z - %s.z * dklmdy.y;",
v.fsIn(), v.fsIn(), v.fsIn());
fsName, fsName, fsName);
fsBuilder->codeAppend("vec2 gF = vec2(dfdx, dfdy);");
fsBuilder->codeAppend("float gFM = sqrt(dot(gF, gF));");
fsBuilder->codeAppendf("float func = %s.x * %s.x - %s.y * %s.z;", v.fsIn(), v.fsIn(),
v.fsIn(), v.fsIn());
fsBuilder->codeAppendf("float func = %s.x * %s.x - %s.y * %s.z;", fsName, fsName,
fsName, fsName);
fsBuilder->codeAppend("edgeAlpha = func / gFM;");
fsBuilder->codeAppend("edgeAlpha = clamp(1.0 - edgeAlpha, 0.0, 1.0);");
// Add line below for smooth cubic ramp
@ -92,8 +93,8 @@ void GrGLConicEffect::emitCode(const EmitArgs& args) {
break;
}
case kFillBW_GrProcessorEdgeType: {
fsBuilder->codeAppendf("edgeAlpha = %s.x * %s.x - %s.y * %s.z;", v.fsIn(), v.fsIn(),
v.fsIn(), v.fsIn());
fsBuilder->codeAppendf("edgeAlpha = %s.x * %s.x - %s.y * %s.z;", fsName, fsName,
fsName, fsName);
fsBuilder->codeAppend("edgeAlpha = float(edgeAlpha < 0.0);");
break;
}
@ -177,12 +178,12 @@ GrGLQuadEffect::GrGLQuadEffect(const GrBackendProcessorFactory& factory,
}
void GrGLQuadEffect::emitCode(const EmitArgs& args) {
GrGLVertToFrag v(kVec4f_GrSLType);
args.fPB->addVarying("HairQuadEdge", &v);
const char *vsName, *fsName;
args.fPB->addVarying(kVec4f_GrSLType, "HairQuadEdge", &vsName, &fsName);
GrGLVertexBuilder* vsBuilder = args.fPB->getVertexShaderBuilder();
const GrShaderVar& inHairQuadEdge = args.fGP.cast<GrQuadEffect>().inHairQuadEdge();
vsBuilder->codeAppendf("%s = %s;", v.vsOut(), inHairQuadEdge.c_str());
vsBuilder->codeAppendf("%s = %s;", vsName, inHairQuadEdge.c_str());
GrGLGPFragmentBuilder* fsBuilder = args.fPB->getFragmentShaderBuilder();
fsBuilder->codeAppendf("float edgeAlpha;");
@ -191,12 +192,12 @@ void GrGLQuadEffect::emitCode(const EmitArgs& args) {
case kHairlineAA_GrProcessorEdgeType: {
SkAssertResult(fsBuilder->enableFeature(
GrGLFragmentShaderBuilder::kStandardDerivatives_GLSLFeature));
fsBuilder->codeAppendf("vec2 duvdx = dFdx(%s.xy);", v.fsIn());
fsBuilder->codeAppendf("vec2 duvdy = dFdy(%s.xy);", v.fsIn());
fsBuilder->codeAppendf("vec2 duvdx = dFdx(%s.xy);", fsName);
fsBuilder->codeAppendf("vec2 duvdy = dFdy(%s.xy);", fsName);
fsBuilder->codeAppendf("vec2 gF = vec2(2.0 * %s.x * duvdx.x - duvdx.y,"
" 2.0 * %s.x * duvdy.x - duvdy.y);",
v.fsIn(), v.fsIn());
fsBuilder->codeAppendf("edgeAlpha = (%s.x * %s.x - %s.y);", v.fsIn(), v.fsIn(), v.fsIn());
fsName, fsName);
fsBuilder->codeAppendf("edgeAlpha = (%s.x * %s.x - %s.y);", fsName, fsName, fsName);
fsBuilder->codeAppend("edgeAlpha = sqrt(edgeAlpha * edgeAlpha / dot(gF, gF));");
fsBuilder->codeAppend("edgeAlpha = max(1.0 - edgeAlpha, 0.0);");
// Add line below for smooth cubic ramp
@ -206,12 +207,12 @@ void GrGLQuadEffect::emitCode(const EmitArgs& args) {
case kFillAA_GrProcessorEdgeType: {
SkAssertResult(fsBuilder->enableFeature(
GrGLFragmentShaderBuilder::kStandardDerivatives_GLSLFeature));
fsBuilder->codeAppendf("vec2 duvdx = dFdx(%s.xy);", v.fsIn());
fsBuilder->codeAppendf("vec2 duvdy = dFdy(%s.xy);", v.fsIn());
fsBuilder->codeAppendf("vec2 duvdx = dFdx(%s.xy);", fsName);
fsBuilder->codeAppendf("vec2 duvdy = dFdy(%s.xy);", fsName);
fsBuilder->codeAppendf("vec2 gF = vec2(2.0 * %s.x * duvdx.x - duvdx.y,"
" 2.0 * %s.x * duvdy.x - duvdy.y);",
v.fsIn(), v.fsIn());
fsBuilder->codeAppendf("edgeAlpha = (%s.x * %s.x - %s.y);", v.fsIn(), v.fsIn(), v.fsIn());
fsName, fsName);
fsBuilder->codeAppendf("edgeAlpha = (%s.x * %s.x - %s.y);", fsName, fsName, fsName);
fsBuilder->codeAppend("edgeAlpha = edgeAlpha / sqrt(dot(gF, gF));");
fsBuilder->codeAppend("edgeAlpha = clamp(1.0 - edgeAlpha, 0.0, 1.0);");
// Add line below for smooth cubic ramp
@ -219,7 +220,7 @@ void GrGLQuadEffect::emitCode(const EmitArgs& args) {
break;
}
case kFillBW_GrProcessorEdgeType: {
fsBuilder->codeAppendf("edgeAlpha = (%s.x * %s.x - %s.y);", v.fsIn(), v.fsIn(), v.fsIn());
fsBuilder->codeAppendf("edgeAlpha = (%s.x * %s.x - %s.y);", fsName, fsName, fsName);
fsBuilder->codeAppend("edgeAlpha = float(edgeAlpha < 0.0);");
break;
}
@ -303,12 +304,14 @@ GrGLCubicEffect::GrGLCubicEffect(const GrBackendProcessorFactory& factory,
}
void GrGLCubicEffect::emitCode(const EmitArgs& args) {
GrGLVertToFrag v(kVec4f_GrSLType);
args.fPB->addVarying("CubicCoeffs", &v, GrGLShaderVar::kHigh_Precision);
const char *vsName, *fsName;
args.fPB->addVarying(kVec4f_GrSLType, "CubicCoeffs",
&vsName, &fsName, GrGLShaderVar::kHigh_Precision);
GrGLVertexBuilder* vsBuilder = args.fPB->getVertexShaderBuilder();
const GrShaderVar& inCubicCoeffs = args.fGP.cast<GrCubicEffect>().inCubicCoeffs();
vsBuilder->codeAppendf("%s = %s;", v.vsOut(), inCubicCoeffs.c_str());
vsBuilder->codeAppendf("%s = %s;", vsName, inCubicCoeffs.c_str());
GrGLGPFragmentBuilder* fsBuilder = args.fPB->getFragmentShaderBuilder();
@ -334,18 +337,18 @@ void GrGLCubicEffect::emitCode(const EmitArgs& args) {
case kHairlineAA_GrProcessorEdgeType: {
SkAssertResult(fsBuilder->enableFeature(
GrGLFragmentShaderBuilder::kStandardDerivatives_GLSLFeature));
fsBuilder->codeAppendf("%s = dFdx(%s.xyz);", dklmdx.c_str(), v.fsIn());
fsBuilder->codeAppendf("%s = dFdy(%s.xyz);", dklmdy.c_str(), v.fsIn());
fsBuilder->codeAppendf("%s = dFdx(%s.xyz);", dklmdx.c_str(), fsName);
fsBuilder->codeAppendf("%s = dFdy(%s.xyz);", dklmdy.c_str(), fsName);
fsBuilder->codeAppendf("%s = 3.0 * %s.x * %s.x * %s.x - %s.y * %s.z - %s.z * %s.y;",
dfdx.c_str(), v.fsIn(), v.fsIn(), dklmdx.c_str(), v.fsIn(),
dklmdx.c_str(), v.fsIn(), dklmdx.c_str());
dfdx.c_str(), fsName, fsName, dklmdx.c_str(), fsName,
dklmdx.c_str(), fsName, dklmdx.c_str());
fsBuilder->codeAppendf("%s = 3.0 * %s.x * %s.x * %s.x - %s.y * %s.z - %s.z * %s.y;",
dfdy.c_str(), v.fsIn(), v.fsIn(), dklmdy.c_str(), v.fsIn(),
dklmdy.c_str(), v.fsIn(), dklmdy.c_str());
dfdy.c_str(), fsName, fsName, dklmdy.c_str(), fsName,
dklmdy.c_str(), fsName, dklmdy.c_str());
fsBuilder->codeAppendf("%s = vec2(%s, %s);", gF.c_str(), dfdx.c_str(), dfdy.c_str());
fsBuilder->codeAppendf("%s = sqrt(dot(%s, %s));", gFM.c_str(), gF.c_str(), gF.c_str());
fsBuilder->codeAppendf("%s = %s.x * %s.x * %s.x - %s.y * %s.z;",
func.c_str(), v.fsIn(), v.fsIn(), v.fsIn(), v.fsIn(), v.fsIn());
func.c_str(), fsName, fsName, fsName, fsName, fsName);
fsBuilder->codeAppendf("%s = abs(%s);", func.c_str(), func.c_str());
fsBuilder->codeAppendf("%s = %s / %s;",
edgeAlpha.c_str(), func.c_str(), gFM.c_str());
@ -360,19 +363,19 @@ void GrGLCubicEffect::emitCode(const EmitArgs& args) {
case kFillAA_GrProcessorEdgeType: {
SkAssertResult(fsBuilder->enableFeature(
GrGLFragmentShaderBuilder::kStandardDerivatives_GLSLFeature));
fsBuilder->codeAppendf("%s = dFdx(%s.xyz);", dklmdx.c_str(), v.fsIn());
fsBuilder->codeAppendf("%s = dFdy(%s.xyz);", dklmdy.c_str(), v.fsIn());
fsBuilder->codeAppendf("%s = dFdx(%s.xyz);", dklmdx.c_str(), fsName);
fsBuilder->codeAppendf("%s = dFdy(%s.xyz);", dklmdy.c_str(), fsName);
fsBuilder->codeAppendf("%s ="
"3.0 * %s.x * %s.x * %s.x - %s.y * %s.z - %s.z * %s.y;",
dfdx.c_str(), v.fsIn(), v.fsIn(), dklmdx.c_str(), v.fsIn(),
dklmdx.c_str(), v.fsIn(), dklmdx.c_str());
dfdx.c_str(), fsName, fsName, dklmdx.c_str(), fsName,
dklmdx.c_str(), fsName, dklmdx.c_str());
fsBuilder->codeAppendf("%s = 3.0 * %s.x * %s.x * %s.x - %s.y * %s.z - %s.z * %s.y;",
dfdy.c_str(), v.fsIn(), v.fsIn(), dklmdy.c_str(), v.fsIn(),
dklmdy.c_str(), v.fsIn(), dklmdy.c_str());
dfdy.c_str(), fsName, fsName, dklmdy.c_str(), fsName,
dklmdy.c_str(), fsName, dklmdy.c_str());
fsBuilder->codeAppendf("%s = vec2(%s, %s);", gF.c_str(), dfdx.c_str(), dfdy.c_str());
fsBuilder->codeAppendf("%s = sqrt(dot(%s, %s));", gFM.c_str(), gF.c_str(), gF.c_str());
fsBuilder->codeAppendf("%s = %s.x * %s.x * %s.x - %s.y * %s.z;",
func.c_str(), v.fsIn(), v.fsIn(), v.fsIn(), v.fsIn(), v.fsIn());
func.c_str(), fsName, fsName, fsName, fsName, fsName);
fsBuilder->codeAppendf("%s = %s / %s;",
edgeAlpha.c_str(), func.c_str(), gFM.c_str());
fsBuilder->codeAppendf("%s = clamp(1.0 - %s, 0.0, 1.0);",
@ -385,7 +388,7 @@ void GrGLCubicEffect::emitCode(const EmitArgs& args) {
}
case kFillBW_GrProcessorEdgeType: {
fsBuilder->codeAppendf("%s = %s.x * %s.x * %s.x - %s.y * %s.z;",
edgeAlpha.c_str(), v.fsIn(), v.fsIn(), v.fsIn(), v.fsIn(), v.fsIn());
edgeAlpha.c_str(), fsName, fsName, fsName, fsName, fsName);
fsBuilder->codeAppendf("%s = float(%s < 0.0);", edgeAlpha.c_str(), edgeAlpha.c_str());
break;
}

View File

@ -24,20 +24,23 @@ public:
args.fGP.cast<GrCustomCoordsTextureEffect>();
SkASSERT(1 == customCoordsTextureEffect.getVertexAttribs().count());
GrGLVertToFrag v(kVec2f_GrSLType);
args.fPB->addVarying("TextureCoords", &v);
SkString fsCoordName;
const char* vsVaryingName;
const char* fsVaryingNamePtr;
args.fPB->addVarying(kVec2f_GrSLType, "textureCoords", &vsVaryingName, &fsVaryingNamePtr);
fsCoordName = fsVaryingNamePtr;
GrGLVertexBuilder* vsBuilder = args.fPB->getVertexShaderBuilder();
const GrShaderVar& inTextureCoords = customCoordsTextureEffect.inTextureCoords();
vsBuilder->codeAppendf("%s = %s;", v.vsOut(), inTextureCoords.c_str());
vsBuilder->codeAppendf("\t%s = %s;\n", vsVaryingName, inTextureCoords.c_str());
GrGLGPFragmentBuilder* fsBuilder = args.fPB->getFragmentShaderBuilder();
fsBuilder->codeAppendf("%s = ", args.fOutput);
fsBuilder->codeAppendf("\t%s = ", args.fOutput);
fsBuilder->appendTextureLookupAndModulate(args.fInput,
args.fSamplers[0],
v.fsIn(),
fsCoordName.c_str(),
kVec2f_GrSLType);
fsBuilder->codeAppend(";");
fsBuilder->codeAppend(";\n");
}
virtual void setData(const GrGLProgramDataManager&,

View File

@ -514,17 +514,17 @@ void GLDashingCircleEffect::emitCode(const EmitArgs& args) {
"params",
&paramName);
GrGLVertToFrag v(kVec2f_GrSLType);
args.fPB->addVarying("Coord", &v);
const char *vsCoordName, *fsCoordName;
args.fPB->addVarying(kVec2f_GrSLType, "Coord", &vsCoordName, &fsCoordName);
GrGLVertexBuilder* vsBuilder = args.fPB->getVertexShaderBuilder();
vsBuilder->codeAppendf("\t%s = %s;\n", v.vsOut(), dce.inCoord().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
GrGLGPFragmentBuilder* fsBuilder = args.fPB->getFragmentShaderBuilder();
fsBuilder->codeAppendf("\t\tfloat xShifted = %s.x - floor(%s.x / %s.z) * %s.z;\n",
v.fsIn(), v.fsIn(), paramName, paramName);
fsBuilder->codeAppendf("\t\tvec2 fragPosShifted = vec2(xShifted, %s.y);\n", v.fsIn());
fsCoordName, fsCoordName, paramName, paramName);
fsBuilder->codeAppendf("\t\tvec2 fragPosShifted = vec2(xShifted, %s.y);\n", fsCoordName);
fsBuilder->codeAppendf("\t\tvec2 center = vec2(%s.y, 0.0);\n", paramName);
fsBuilder->codeAppend("\t\tfloat dist = length(center - fragPosShifted);\n");
if (GrProcessorEdgeTypeIsAA(dce.getEdgeType())) {
@ -718,16 +718,16 @@ void GLDashingLineEffect::emitCode(const EmitArgs& args) {
"interval",
&intervalName);
GrGLVertToFrag v(kVec2f_GrSLType);
args.fPB->addVarying("Coord", &v);
const char *vsCoordName, *fsCoordName;
args.fPB->addVarying(kVec2f_GrSLType, "Coord", &vsCoordName, &fsCoordName);
GrGLVertexBuilder* vsBuilder = args.fPB->getVertexShaderBuilder();
vsBuilder->codeAppendf("\t%s = %s;\n", v.vsOut(), de.inCoord().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
GrGLGPFragmentBuilder* fsBuilder = args.fPB->getFragmentShaderBuilder();
fsBuilder->codeAppendf("\t\tfloat xShifted = %s.x - floor(%s.x / %s) * %s;\n",
v.fsIn(), v.fsIn(), intervalName, intervalName);
fsBuilder->codeAppendf("\t\tvec2 fragPosShifted = vec2(xShifted, %s.y);\n", v.fsIn());
fsCoordName, fsCoordName, intervalName, intervalName);
fsBuilder->codeAppendf("\t\tvec2 fragPosShifted = vec2(xShifted, %s.y);\n", fsCoordName);
if (GrProcessorEdgeTypeIsAA(de.getEdgeType())) {
// The amount of coverage removed in x and y by the edges is computed as a pair of negative
// numbers, xSub and ySub.

View File

@ -49,11 +49,14 @@ public:
SkAssertResult(fsBuilder->enableFeature(
GrGLFragmentShaderBuilder::kStandardDerivatives_GLSLFeature));
GrGLVertToFrag v(kVec2f_GrSLType);
args.fPB->addVarying("TextureCoords", &v);
SkString fsCoordName;
const char* vsCoordName;
const char* fsCoordNamePtr;
args.fPB->addVarying(kVec2f_GrSLType, "textureCoords", &vsCoordName, &fsCoordNamePtr);
fsCoordName = fsCoordNamePtr;
GrGLVertexBuilder* vsBuilder = args.fPB->getVertexShaderBuilder();
vsBuilder->codeAppendf("\t%s = %s;\n", v.vsOut(), dfTexEffect.inTextureCoords().c_str());
vsBuilder->codeAppendf("\t%s = %s;\n", vsCoordName, dfTexEffect.inTextureCoords().c_str());
const char* textureSizeUniName = NULL;
fTextureSizeUni = args.fPB->addUniform(GrGLProgramBuilder::kFragment_Visibility,
@ -62,7 +65,7 @@ public:
fsBuilder->codeAppend("\tvec4 texColor = ");
fsBuilder->appendTextureLookup(args.fSamplers[0],
v.fsIn(),
fsCoordName.c_str(),
kVec2f_GrSLType);
fsBuilder->codeAppend(";\n");
fsBuilder->codeAppend("\tfloat distance = "
@ -72,7 +75,7 @@ public:
// we adjust for the effect of the transformation on the distance by using
// the length of the gradient of the texture coordinates. We use st coordinates
// to ensure we're mapping 1:1 from texel space to pixel space.
fsBuilder->codeAppendf("\tvec2 uv = %s;\n", v.fsIn());
fsBuilder->codeAppendf("\tvec2 uv = %s;\n", fsCoordName.c_str());
fsBuilder->codeAppendf("\tvec2 st = uv*%s;\n", textureSizeUniName);
fsBuilder->codeAppend("\tfloat afwidth;\n");
if (dfTexEffect.getFlags() & kSimilarity_DistanceFieldEffectFlag) {
@ -261,11 +264,14 @@ public:
SkAssertResult(fsBuilder->enableFeature(
GrGLFragmentShaderBuilder::kStandardDerivatives_GLSLFeature));
GrGLVertToFrag v(kVec2f_GrSLType);
args.fPB->addVarying("TextureCoords", &v);
SkString fsCoordName;
const char* vsCoordName;
const char* fsCoordNamePtr;
args.fPB->addVarying(kVec2f_GrSLType, "textureCoords", &vsCoordName, &fsCoordNamePtr);
fsCoordName = fsCoordNamePtr;
GrGLVertexBuilder* vsBuilder = args.fPB->getVertexShaderBuilder();
vsBuilder->codeAppendf("%s = %s;", v.vsOut(), dfTexEffect.inTextureCoords().c_str());
vsBuilder->codeAppendf("%s = %s;", vsCoordName, dfTexEffect.inTextureCoords().c_str());
const char* textureSizeUniName = NULL;
fTextureSizeUni = args.fPB->addUniform(GrGLProgramBuilder::kFragment_Visibility,
@ -274,7 +280,7 @@ public:
fsBuilder->codeAppend("vec4 texColor = ");
fsBuilder->appendTextureLookup(args.fSamplers[0],
v.fsIn(),
fsCoordName.c_str(),
kVec2f_GrSLType);
fsBuilder->codeAppend(";");
fsBuilder->codeAppend("float distance = "
@ -283,7 +289,7 @@ public:
// we adjust for the effect of the transformation on the distance by using
// the length of the gradient of the texture coordinates. We use st coordinates
// to ensure we're mapping 1:1 from texel space to pixel space.
fsBuilder->codeAppendf("vec2 uv = %s;", v.fsIn());
fsBuilder->codeAppendf("vec2 uv = %s;", fsCoordName.c_str());
fsBuilder->codeAppendf("vec2 st = uv*%s;", textureSizeUniName);
fsBuilder->codeAppend("float afwidth;");
if (dfTexEffect.getFlags() & kSimilarity_DistanceFieldEffectFlag) {
@ -415,11 +421,14 @@ public:
args.fGP.cast<GrDistanceFieldLCDTextureEffect>();
SkASSERT(1 == dfTexEffect.getVertexAttribs().count());
GrGLVertToFrag v(kVec2f_GrSLType);
args.fPB->addVarying("TextureCoords", &v);
SkString fsCoordName;
const char* vsCoordName;
const char* fsCoordNamePtr;
args.fPB->addVarying(kVec2f_GrSLType, "textureCoords", &vsCoordName, &fsCoordNamePtr);
fsCoordName = fsCoordNamePtr;
GrGLVertexBuilder* vsBuilder = args.fPB->getVertexShaderBuilder();
vsBuilder->codeAppendf("\t%s = %s;\n", v.vsOut(), dfTexEffect.inTextureCoords().c_str());
vsBuilder->codeAppendf("\t%s = %s;\n", vsCoordName, dfTexEffect.inTextureCoords().c_str());
const char* textureSizeUniName = NULL;
// width, height, 1/(3*width)
@ -433,7 +442,7 @@ public:
GrGLFragmentShaderBuilder::kStandardDerivatives_GLSLFeature));
// create LCD offset adjusted by inverse of transform
fsBuilder->codeAppendf("\tvec2 uv = %s;\n", v.fsIn());
fsBuilder->codeAppendf("\tvec2 uv = %s;\n", fsCoordName.c_str());
fsBuilder->codeAppendf("\tvec2 st = uv*%s.xy;\n", textureSizeUniName);
bool isUniformScale = !!(dfTexEffect.getFlags() & kUniformScale_DistanceFieldEffectMask);
if (isUniformScale) {

View File

@ -346,10 +346,12 @@ void GrGLFragmentShaderBuilder::bindFragmentShaderLocations(GrGLuint programID)
}
}
void GrGLFragmentShaderBuilder::addVarying(GrGLVarying* v, GrGLShaderVar::Precision fsPrec) {
v->fFsIn = v->fVsOut;
if (v->fGsOut) {
v->fFsIn = v->fGsOut;
void GrGLFragmentShaderBuilder::addVarying(GrSLType type,
const char* name,
const char** fsInName,
GrGLShaderVar::Precision fsPrecision) {
fInputs.push_back().set(type, GrGLShaderVar::kVaryingIn_TypeModifier, name, fsPrecision);
if (fsInName) {
*fsInName = name;
}
fInputs.push_back().set(v->fType, GrGLShaderVar::kVaryingIn_TypeModifier, v->fFsIn, fsPrec);
}

View File

@ -10,8 +10,6 @@
#include "GrGLShaderBuilder.h"
class GrGLVarying;
/*
* This base class encapsulates the functionality which the GP uses to build fragment shaders
*/
@ -93,7 +91,6 @@ public:
virtual const char* fragmentPosition() SK_OVERRIDE;
virtual const char* dstColor() SK_OVERRIDE;
private:
// Private public interface, used by GrGLProgramBuilder to build a fragment shader
void emitCodeToReadDstTexture();
void enableCustomOutput();
@ -105,6 +102,14 @@ private:
bool compileAndAttachShaders(GrGLuint programId, SkTDArray<GrGLuint>* shaderIds) const;
void bindFragmentShaderLocations(GrGLuint programID);
/*
* An internal call for GrGLProgramBuilder to use to add varyings to the vertex shader
*/
void addVarying(GrSLType type,
const char* name,
const char** fsInName,
GrGLShaderVar::Precision fsPrecision = GrGLShaderVar::kDefault_Precision);
// As GLProcessors emit code, there are some conditions we need to verify. We use the below
// state to track this. The reset call is called per processor emitted.
bool hasReadDstColor() const { return fHasReadDstColor; }
@ -114,12 +119,7 @@ private:
fHasReadFragmentPosition = false;
}
/*
* An internal call for GrGLProgramBuilder to use to add varyings to the vertex shader
*/
void addVarying(GrGLVarying* v,
GrGLShaderVar::Precision fsPrec = GrGLShaderVar::kDefault_Precision);
private:
/**
* Features that should only be enabled by GrGLFragmentShaderBuilder itself.
*/

View File

@ -15,27 +15,26 @@ GrGLGeometryBuilder::GrGLGeometryBuilder(GrGLProgramBuilder* program)
}
void GrGLGeometryBuilder::addVarying(const char* name, GrGLVarying* v) {
void GrGLGeometryBuilder::addVarying(GrSLType type,
const char* name,
const char** gsOutName) {
// if we have a GS take each varying in as an array
// and output as non-array.
if (v->vsVarying()) {
fInputs.push_back();
fInputs.back().setType(v->fType);
fInputs.back().setTypeModifier(GrGLShaderVar::kVaryingIn_TypeModifier);
fInputs.back().setUnsizedArray();
*fInputs.back().accessName() = v->fVsOut;
v->fGsIn = v->fVsOut;
}
if (v->fsVarying()) {
fOutputs.push_back();
fOutputs.back().setType(v->fType);
fOutputs.back().setTypeModifier(GrGLShaderVar::kVaryingOut_TypeModifier);
fProgramBuilder->nameVariable(fOutputs.back().accessName(), 'g', name);
v->fGsOut = fOutputs.back().getName().c_str();
fInputs.push_back();
fInputs.back().setType(type);
fInputs.back().setTypeModifier(GrGLShaderVar::kVaryingIn_TypeModifier);
fInputs.back().setUnsizedArray();
*fInputs.back().accessName() = name;
fOutputs.push_back();
fOutputs.back().setType(type);
fOutputs.back().setTypeModifier(GrGLShaderVar::kVaryingOut_TypeModifier);
fProgramBuilder->nameVariable(fOutputs.back().accessName(), 'g', name);
if (gsOutName) {
*gsOutName = fOutputs.back().getName().c_str();
}
}
bool GrGLGeometryBuilder::compileAndAttachShaders(GrGLuint programId,
SkTDArray<GrGLuint>* shaderIds) const {
const GrGLContext& glCtx = fProgramBuilder->gpu()->glContext();

View File

@ -10,22 +10,18 @@
#include "GrGLShaderBuilder.h"
class GrGLVarying;
class GrGLGeometryBuilder : public GrGLShaderBuilder {
public:
GrGLGeometryBuilder(GrGLProgramBuilder* program);
private:
/*
* an internal call for GrGLFullProgramBuilder to add varyings
*/
void addVarying(const char* name, GrGLVarying*);
void addVarying(GrSLType type,
const char* name,
const char** gsOutName);
bool compileAndAttachShaders(GrGLuint programId, SkTDArray<GrGLuint>* shaderIds) const;
friend class GrGLProgramBuilder;
typedef GrGLShaderBuilder INHERITED;
};

View File

@ -55,6 +55,7 @@ GrGLNvprProgramBuilder::addSeparableVarying(GrSLType type,
const char* name,
const char** vsOutName,
const char** fsInName) {
addVarying(type, name, vsOutName, fsInName);
SeparableVaryingInfo& varying = fSeparableVaryingInfos.push_back();
varying.fVariable = fFS.fInputs.back();
return GrGLInstalledFragProc::ShaderVarHandle(fSeparableVaryingInfos.count() - 1);

View File

@ -126,19 +126,13 @@ GrGLProgramBuilder::GrGLProgramBuilder(GrGpuGL* gpu,
, fUniforms(kVarsPerBlock) {
}
void GrGLProgramBuilder::addVarying(const char* name,
GrGLVarying* varying,
void GrGLProgramBuilder::addVarying(GrSLType type,
const char* name,
const char** vsOutName,
const char** fsInName,
GrGLShaderVar::Precision fsPrecision) {
SkASSERT(varying);
if (varying->vsVarying()) {
fVS.addVarying(name, varying);
}
if (fOptState.hasGeometryProcessor() && fOptState.getGeometryProcessor()->willUseGeoShader()) {
fGS.addVarying(name, varying);
}
if (varying->fsVarying()) {
fFS.addVarying(varying);
}
SkString* fsInputName = fVS.addVarying(type, name, vsOutName);
fFS.addVarying(type, fsInputName->c_str(), fsInName, fsPrecision);
}
void GrGLProgramBuilder::nameVariable(SkString* out, char prefix, const char* name) {
@ -368,8 +362,9 @@ void GrGLProgramBuilder::emitTransforms(const GrFragmentStage& effectStage,
suffixedVaryingName.appendf("_%i", t);
varyingName = suffixedVaryingName.c_str();
}
GrGLVertToFrag v(varyingType);
this->addVarying(varyingName, &v);
const char* vsVaryingName;
const char* fsVaryingName;
this->addVarying(varyingType, varyingName, &vsVaryingName, &fsVaryingName);
const GrGLShaderVar& coords =
kPosition_GrCoordSet == effect->coordTransform(t).sourceCoords() ?
@ -380,13 +375,13 @@ void GrGLProgramBuilder::emitTransforms(const GrFragmentStage& effectStage,
SkASSERT(kVec2f_GrSLType == varyingType || kVec3f_GrSLType == varyingType);
if (kVec2f_GrSLType == varyingType) {
fVS.codeAppendf("%s = (%s * vec3(%s, 1)).xy;",
v.vsOut(), uniName, coords.c_str());
vsVaryingName, uniName, coords.c_str());
} else {
fVS.codeAppendf("%s = %s * vec3(%s, 1);",
v.vsOut(), uniName, coords.c_str());
vsVaryingName, uniName, coords.c_str());
}
SkNEW_APPEND_TO_TARRAY(outCoords, GrGLProcessor::TransformedCoords,
(SkString(v.fsIn()), varyingType));
(SkString(fsVaryingName), varyingType));
}
}

View File

@ -69,63 +69,13 @@ public:
*/
};
// TODO move this into GrGLGPBuilder and move them both out of this file
class GrGLVarying {
public:
bool vsVarying() const { return kVertToFrag_Varying == fVarying ||
kVertToGeo_Varying == fVarying; }
bool fsVarying() const { return kVertToFrag_Varying == fVarying ||
kGeoToFrag_Varying == fVarying; }
const char* vsOut() const { return fVsOut; }
const char* gsIn() const { return fGsIn; }
const char* gsOut() const { return fGsOut; }
const char* fsIn() const { return fFsIn; }
protected:
enum Varying {
kVertToFrag_Varying,
kVertToGeo_Varying,
kGeoToFrag_Varying,
};
GrGLVarying(GrSLType type, Varying varying)
: fVarying(varying), fType(type), fVsOut(NULL), fGsIn(NULL), fGsOut(NULL),
fFsIn(NULL) {}
Varying fVarying;
private:
GrSLType fType;
const char* fVsOut;
const char* fGsIn;
const char* fGsOut;
const char* fFsIn;
friend class GrGLVertexBuilder;
friend class GrGLGeometryBuilder;
friend class GrGLFragmentShaderBuilder;
};
struct GrGLVertToFrag : public GrGLVarying {
GrGLVertToFrag(GrSLType type)
: GrGLVarying(type, kVertToFrag_Varying) {}
};
struct GrGLVertToGeo : public GrGLVarying {
GrGLVertToGeo(GrSLType type)
: GrGLVarying(type, kVertToGeo_Varying) {}
};
struct GrGLGeoToFrag : public GrGLVarying {
GrGLGeoToFrag(GrSLType type)
: GrGLVarying(type, kGeoToFrag_Varying) {}
};
/* a specialization of the above for GPs. Lets the user add uniforms, varyings, and VS / FS code */
class GrGLGPBuilder : public virtual GrGLUniformBuilder {
public:
virtual void addVarying(const char* name,
GrGLVarying*,
virtual void addVarying(GrSLType type,
const char* name,
const char** vsOutName = NULL,
const char** fsInName = NULL,
GrGLShaderVar::Precision fsPrecision=GrGLShaderVar::kDefault_Precision) = 0;
// TODO rename getFragmentBuilder
@ -202,8 +152,10 @@ public:
virtual GrGLVertexBuilder* getVertexShaderBuilder() SK_OVERRIDE { return &fVS; }
virtual void addVarying(
GrSLType type,
const char* name,
GrGLVarying*,
const char** vsOutName = NULL,
const char** fsInName = NULL,
GrGLShaderVar::Precision fsPrecision=GrGLShaderVar::kDefault_Precision) SK_OVERRIDE;
// Handles for program uniforms (other than per-effect uniforms)

View File

@ -23,12 +23,17 @@ GrGLVertexBuilder::GrGLVertexBuilder(GrGLProgramBuilder* program)
, fEffectAttribOffset(0) {
}
void GrGLVertexBuilder::addVarying(const char* name, GrGLVarying* v) {
SkString* GrGLVertexBuilder::addVarying(GrSLType type, const char* name,
const char** vsOutName) {
fOutputs.push_back();
fOutputs.back().setType(v->fType);
fOutputs.back().setType(type);
fOutputs.back().setTypeModifier(GrGLShaderVar::kVaryingOut_TypeModifier);
fProgramBuilder->nameVariable(fOutputs.back().accessName(), 'v', name);
v->fVsOut = fOutputs.back().getName().c_str();
if (vsOutName) {
*vsOutName = fOutputs.back().getName().c_str();
}
return fOutputs.back().accessName();
}
void GrGLVertexBuilder::setupLocalCoords() {
@ -58,15 +63,15 @@ void GrGLVertexBuilder::transformGLToSkiaCoords() {
}
void GrGLVertexBuilder::setupBuiltinVertexAttribute(const char* inName, GrGLSLExpr4* out) {
GrGLVertToFrag v(kVec4f_GrSLType);
fProgramBuilder->addVarying(inName, &v);
SkString name(inName);
const char *vsName, *fsName;
fProgramBuilder->addVarying(kVec4f_GrSLType, name.c_str(), &vsName, &fsName);
name.prepend("in");
this->addAttribute(GrShaderVar(name.c_str(),
kVec4f_GrSLType,
GrShaderVar::kAttribute_TypeModifier));
this->codeAppendf("%s = %s;", v.vsOut(), name.c_str());
*out = v.fsIn();
this->codeAppendf("%s = %s;", vsName, name.c_str());
*out = fsName;
fEffectAttribOffset++;
}

View File

@ -10,8 +10,10 @@
#include "GrGLShaderBuilder.h"
class GrGLVarying;
class GrGLProgramBuilder;
// TODO we only actually ever need to return a GrGLShaderBuilder for this guy, none of the below
// functions need to be part of VertexShaderBuilder's public interface
class GrGLVertexBuilder : public GrGLShaderBuilder {
public:
GrGLVertexBuilder(GrGLProgramBuilder* program);
@ -31,11 +33,10 @@ public:
*/
const GrGLShaderVar& positionAttribute() const { return *fPositionVar; }
private:
/*
* Internal call for GrGLProgramBuilder.addVarying
*/
void addVarying(const char* name, GrGLVarying*);
SkString* addVarying(GrSLType type, const char* name, const char** vsOutName);
/*
* private helpers for compilation by GrGLProgramBuilder
@ -48,6 +49,7 @@ private:
void bindVertexAttributes(GrGLuint programID);
bool compileAndAttachShaders(GrGLuint programId, SkTDArray<GrGLuint>* shaderIds) const;
private:
// an internal call which checks for uniquness of a var before adding it to the list of inputs
bool addAttribute(const GrShaderVar& var);
struct AttributePair {
@ -62,8 +64,6 @@ private:
GrGLShaderVar* fLocalCoordsVar;
int fEffectAttribOffset;
friend class GrGLProgramBuilder;
typedef GrGLShaderBuilder INHERITED;
};