| OLD | NEW | 
|    1  |    1  | 
|    2 /* |    2 /* | 
|    3  * Copyright 2012 Google Inc. |    3  * Copyright 2012 Google Inc. | 
|    4  * |    4  * | 
|    5  * Use of this source code is governed by a BSD-style license that can be |    5  * Use of this source code is governed by a BSD-style license that can be | 
|    6  * found in the LICENSE file. |    6  * found in the LICENSE file. | 
|    7  */ |    7  */ | 
|    8  |    8  | 
|    9 #include "GrAAConvexPathRenderer.h" |    9 #include "GrAAConvexPathRenderer.h" | 
|   10  |   10  | 
|   11 #include "GrContext.h" |   11 #include "GrContext.h" | 
|   12 #include "GrDrawState.h" |   12 #include "GrDrawState.h" | 
|   13 #include "GrDrawTargetCaps.h" |   13 #include "GrDrawTargetCaps.h" | 
 |   14 #include "GrEffect.h" | 
|   14 #include "GrPathUtils.h" |   15 #include "GrPathUtils.h" | 
 |   16 #include "GrTBackendEffectFactory.h" | 
|   15 #include "SkString.h" |   17 #include "SkString.h" | 
|   16 #include "SkStrokeRec.h" |   18 #include "SkStrokeRec.h" | 
|   17 #include "SkTrace.h" |   19 #include "SkTrace.h" | 
|   18  |   20  | 
|   19 #include "effects/GrEdgeEffect.h" |   21 #include "gl/GrGLEffect.h" | 
 |   22 #include "gl/GrGLSL.h" | 
|   20  |   23  | 
|   21 GrAAConvexPathRenderer::GrAAConvexPathRenderer() { |   24 GrAAConvexPathRenderer::GrAAConvexPathRenderer() { | 
|   22 } |   25 } | 
|   23  |   26  | 
|   24 namespace { |   27 namespace { | 
|   25  |   28  | 
|   26 struct Segment { |   29 struct Segment { | 
|   27     enum { |   30     enum { | 
|   28         // These enum values are assumed in member functions below. |   31         // These enum values are assumed in member functions below. | 
|   29         kLine = 0, |   32         kLine = 0, | 
| (...skipping 394 matching lines...) Expand 10 before | Expand all | Expand 10 after  Loading... | 
|  424             idxs[i + 11] = v + 1; |  427             idxs[i + 11] = v + 1; | 
|  425  |  428  | 
|  426             v += 6; |  429             v += 6; | 
|  427             i += 12; |  430             i += 12; | 
|  428         } |  431         } | 
|  429     } |  432     } | 
|  430 } |  433 } | 
|  431  |  434  | 
|  432 } |  435 } | 
|  433  |  436  | 
 |  437 /////////////////////////////////////////////////////////////////////////////// | 
 |  438  | 
 |  439 /* | 
 |  440  * Quadratic specified by 0=u^2-v canonical coords. u and v are the first | 
 |  441  * two components of the vertex attribute. Coverage is based on signed | 
 |  442  * distance with negative being inside, positive outside. The edge is specified 
     in | 
 |  443  * window space (y-down). If either the third or fourth component of the interpo
     lated | 
 |  444  * vertex coord is > 0 then the pixel is considered outside the edge. This is us
     ed to | 
 |  445  * attempt to trim to a portion of the infinite quad.  | 
 |  446  * Requires shader derivative instruction support.  | 
 |  447  */ | 
 |  448  | 
 |  449 class QuadEdgeEffect : public GrEffect { | 
 |  450 public: | 
 |  451  | 
 |  452     static GrEffectRef* Create() { | 
 |  453         // we go through this so we only have one copy of each effect | 
 |  454         static GrEffectRef* gQuadEdgeEffectRef =  | 
 |  455             CreateEffectRef(AutoEffectUnref(SkNEW(QuadEdgeEffect))); | 
 |  456         static SkAutoTUnref<GrEffectRef> gUnref(gQuadEdgeEffectRef); | 
 |  457  | 
 |  458         gQuadEdgeEffectRef->ref(); | 
 |  459         return gQuadEdgeEffectRef; | 
 |  460     } | 
 |  461  | 
 |  462     virtual ~QuadEdgeEffect() {} | 
 |  463  | 
 |  464     static const char* Name() { return "QuadEdge"; } | 
 |  465  | 
 |  466     virtual void getConstantColorComponents(GrColor* color,  | 
 |  467                                             uint32_t* validFlags) const SK_OVERR
     IDE { | 
 |  468         *validFlags = 0; | 
 |  469     } | 
 |  470  | 
 |  471     virtual const GrBackendEffectFactory& getFactory() const SK_OVERRIDE { | 
 |  472         return GrTBackendEffectFactory<QuadEdgeEffect>::getInstance(); | 
 |  473     } | 
 |  474  | 
 |  475     class GLEffect : public GrGLEffect { | 
 |  476     public: | 
 |  477         GLEffect(const GrBackendEffectFactory& factory, const GrDrawEffect&) | 
 |  478             : INHERITED (factory) {} | 
 |  479  | 
 |  480         virtual void emitCode(GrGLShaderBuilder* builder, | 
 |  481                               const GrDrawEffect& drawEffect, | 
 |  482                               EffectKey key, | 
 |  483                               const char* outputColor, | 
 |  484                               const char* inputColor, | 
 |  485                               const TextureSamplerArray& samplers) SK_OVERRIDE { | 
 |  486             const char *vsName, *fsName; | 
 |  487             const SkString* attrName = | 
 |  488                 builder->getEffectAttributeName(drawEffect.getVertexAttribIndice
     s()[0]); | 
 |  489             builder->fsCodeAppendf("\t\tfloat edgeAlpha;\n"); | 
 |  490  | 
 |  491             SkAssertResult(builder->enableFeature( | 
 |  492                                               GrGLShaderBuilder::kStandardDeriva
     tives_GLSLFeature)); | 
 |  493             builder->addVarying(kVec4f_GrSLType, "QuadEdge", &vsName, &fsName); | 
 |  494  | 
 |  495             // keep the derivative instructions outside the conditional | 
 |  496             builder->fsCodeAppendf("\t\tvec2 duvdx = dFdx(%s.xy);\n", fsName); | 
 |  497             builder->fsCodeAppendf("\t\tvec2 duvdy = dFdy(%s.xy);\n", fsName); | 
 |  498             builder->fsCodeAppendf("\t\tif (%s.z > 0.0 && %s.w > 0.0) {\n", fsNa
     me, fsName); | 
 |  499             // today we know z and w are in device space. We could use derivativ
     es | 
 |  500             builder->fsCodeAppendf("\t\t\tedgeAlpha = min(min(%s.z, %s.w) + 0.5,
      1.0);\n", fsName, | 
 |  501                                     fsName); | 
 |  502             builder->fsCodeAppendf ("\t\t} else {\n"); | 
 |  503             builder->fsCodeAppendf("\t\t\tvec2 gF = vec2(2.0*%s.x*duvdx.x - duvd
     x.y,\n" | 
 |  504                                    "\t\t\t               2.0*%s.x*duvdy.x - duvd
     y.y);\n", | 
 |  505                                    fsName, fsName); | 
 |  506             builder->fsCodeAppendf("\t\t\tedgeAlpha = (%s.x*%s.x - %s.y);\n", fs
     Name, fsName, | 
 |  507                                     fsName); | 
 |  508             builder->fsCodeAppendf("\t\t\tedgeAlpha = " | 
 |  509                                    "clamp(0.5 - edgeAlpha / length(gF), 0.0, 1.0
     );\n\t\t}\n"); | 
 |  510  | 
 |  511             SkString modulate; | 
 |  512             GrGLSLModulate4f(&modulate, inputColor, "edgeAlpha"); | 
 |  513             builder->fsCodeAppendf("\t%s = %s;\n", outputColor, modulate.c_str()
     ); | 
 |  514  | 
 |  515             builder->vsCodeAppendf("\t%s = %s;\n", vsName, attrName->c_str()); | 
 |  516         } | 
 |  517  | 
 |  518         static inline EffectKey GenKey(const GrDrawEffect& drawEffect, const GrG
     LCaps&) { | 
 |  519             return 0x0; | 
 |  520         } | 
 |  521  | 
 |  522         virtual void setData(const GrGLUniformManager&, const GrDrawEffect&) SK_
     OVERRIDE {} | 
 |  523  | 
 |  524     private: | 
 |  525         typedef GrGLEffect INHERITED; | 
 |  526     }; | 
 |  527  | 
 |  528 private: | 
 |  529     QuadEdgeEffect() {  | 
 |  530         this->addVertexAttrib(kVec4f_GrSLType);  | 
 |  531     } | 
 |  532  | 
 |  533     virtual bool onIsEqual(const GrEffect& other) const SK_OVERRIDE { | 
 |  534         return true; | 
 |  535     } | 
 |  536  | 
 |  537     GR_DECLARE_EFFECT_TEST; | 
 |  538  | 
 |  539     typedef GrEffect INHERITED; | 
 |  540 }; | 
 |  541  | 
 |  542 GR_DEFINE_EFFECT_TEST(QuadEdgeEffect); | 
 |  543  | 
 |  544 GrEffectRef* QuadEdgeEffect::TestCreate(SkMWCRandom* random, | 
 |  545                                         GrContext*, | 
 |  546                                         const GrDrawTargetCaps& caps, | 
 |  547                                         GrTexture*[]) { | 
 |  548     // Doesn't work without derivative instructions. | 
 |  549     return caps.shaderDerivativeSupport() ? QuadEdgeEffect::Create() : NULL; | 
 |  550 } | 
 |  551  | 
 |  552 /////////////////////////////////////////////////////////////////////////////// | 
 |  553  | 
|  434 bool GrAAConvexPathRenderer::canDrawPath(const SkPath& path, |  554 bool GrAAConvexPathRenderer::canDrawPath(const SkPath& path, | 
|  435                                          const SkStrokeRec& stroke, |  555                                          const SkStrokeRec& stroke, | 
|  436                                          const GrDrawTarget* target, |  556                                          const GrDrawTarget* target, | 
|  437                                          bool antiAlias) const { |  557                                          bool antiAlias) const { | 
|  438     return (target->caps()->shaderDerivativeSupport() && antiAlias && |  558     return (target->caps()->shaderDerivativeSupport() && antiAlias && | 
|  439             stroke.isFillStyle() && !path.isInverseFillType() && path.isConvex()
     ); |  559             stroke.isFillStyle() && !path.isInverseFillType() && path.isConvex()
     ); | 
|  440 } |  560 } | 
|  441  |  561  | 
|  442 bool GrAAConvexPathRenderer::onDrawPath(const SkPath& origPath, |  562 bool GrAAConvexPathRenderer::onDrawPath(const SkPath& origPath, | 
|  443                                         const SkStrokeRec&, |  563                                         const SkStrokeRec&, | 
| (...skipping 46 matching lines...) Expand 10 before | Expand all | Expand 10 after  Loading... | 
|  490     }; |  610     }; | 
|  491     drawState->setVertexAttribs(kAttribs, SK_ARRAY_COUNT(kAttribs)); |  611     drawState->setVertexAttribs(kAttribs, SK_ARRAY_COUNT(kAttribs)); | 
|  492  |  612  | 
|  493     enum { |  613     enum { | 
|  494         // the edge effects share this stage with glyph rendering |  614         // the edge effects share this stage with glyph rendering | 
|  495         // (kGlyphMaskStage in GrTextContext) && SW path rendering |  615         // (kGlyphMaskStage in GrTextContext) && SW path rendering | 
|  496         // (kPathMaskStage in GrSWMaskHelper) |  616         // (kPathMaskStage in GrSWMaskHelper) | 
|  497         kEdgeEffectStage = GrPaint::kTotalStages, |  617         kEdgeEffectStage = GrPaint::kTotalStages, | 
|  498     }; |  618     }; | 
|  499     static const int kEdgeAttrIndex = 1; |  619     static const int kEdgeAttrIndex = 1; | 
|  500     GrEffectRef* quadEffect = GrEdgeEffect::Create(GrEdgeEffect::kQuad_EdgeType)
     ; |  620     GrEffectRef* quadEffect = QuadEdgeEffect::Create(); | 
|  501     drawState->setEffect(kEdgeEffectStage, quadEffect, kEdgeAttrIndex)->unref(); |  621     drawState->setEffect(kEdgeEffectStage, quadEffect, kEdgeAttrIndex)->unref(); | 
|  502  |  622  | 
|  503     GrDrawTarget::AutoReleaseGeometry arg(target, vCount, iCount); |  623     GrDrawTarget::AutoReleaseGeometry arg(target, vCount, iCount); | 
|  504     if (!arg.succeeded()) { |  624     if (!arg.succeeded()) { | 
|  505         return false; |  625         return false; | 
|  506     } |  626     } | 
|  507     GrAssert(sizeof(QuadVertex) == drawState->getVertexSize()); |  627     GrAssert(sizeof(QuadVertex) == drawState->getVertexSize()); | 
|  508     verts = reinterpret_cast<QuadVertex*>(arg.vertices()); |  628     verts = reinterpret_cast<QuadVertex*>(arg.vertices()); | 
|  509     idxs = reinterpret_cast<uint16_t*>(arg.indices()); |  629     idxs = reinterpret_cast<uint16_t*>(arg.indices()); | 
|  510  |  630  | 
|  511     create_vertices(segments, fanPt, verts, idxs); |  631     create_vertices(segments, fanPt, verts, idxs); | 
|  512  |  632  | 
|  513     target->drawIndexed(kTriangles_GrPrimitiveType, |  633     target->drawIndexed(kTriangles_GrPrimitiveType, | 
|  514                         0,        // start vertex |  634                         0,        // start vertex | 
|  515                         0,        // start index |  635                         0,        // start index | 
|  516                         vCount, |  636                         vCount, | 
|  517                         iCount); |  637                         iCount); | 
|  518  |  638  | 
|  519     return true; |  639     return true; | 
|  520 } |  640 } | 
| OLD | NEW |