OLD | NEW |
1 /* | 1 /* |
2 * Copyright 2013 Google Inc. | 2 * Copyright 2013 Google Inc. |
3 * | 3 * |
4 * Use of this source code is governed by a BSD-style license that can be | 4 * Use of this source code is governed by a BSD-style license that can be |
5 * found in the LICENSE file. | 5 * found in the LICENSE file. |
6 */ | 6 */ |
7 | 7 |
8 #include "GrDistanceFieldTextureEffect.h" | 8 #include "GrDistanceFieldTextureEffect.h" |
9 #include "GrInvariantOutput.h" | 9 #include "GrInvariantOutput.h" |
10 #include "GrTexture.h" | 10 #include "GrTexture.h" |
11 #include "SkDistanceFieldGen.h" | 11 #include "SkDistanceFieldGen.h" |
12 #include "gl/GrGLProcessor.h" | 12 #include "gl/GrGLProcessor.h" |
13 #include "gl/GrGLSL.h" | 13 #include "gl/GrGLSL.h" |
14 #include "gl/GrGLTexture.h" | 14 #include "gl/GrGLTexture.h" |
15 #include "gl/GrGLGeometryProcessor.h" | 15 #include "gl/GrGLGeometryProcessor.h" |
16 #include "gl/builders/GrGLProgramBuilder.h" | 16 #include "gl/builders/GrGLProgramBuilder.h" |
17 | 17 |
18 // Assuming a radius of the diagonal of the fragment, hence a factor of sqrt(2)/
2 | 18 // Assuming a radius of the diagonal of the fragment, hence a factor of sqrt(2)/
2 |
19 #define SK_DistanceFieldAAFactor "0.7071" | 19 #define SK_DistanceFieldAAFactor "0.7071" |
20 | 20 |
| 21 struct DistanceFieldBatchTracker { |
| 22 GrGPInput fInputColorType; |
| 23 GrColor fColor; |
| 24 }; |
| 25 |
21 class GrGLDistanceFieldTextureEffect : public GrGLGeometryProcessor { | 26 class GrGLDistanceFieldTextureEffect : public GrGLGeometryProcessor { |
22 public: | 27 public: |
23 GrGLDistanceFieldTextureEffect(const GrGeometryProcessor&, | 28 GrGLDistanceFieldTextureEffect(const GrGeometryProcessor&, |
24 const GrBatchTracker&) | 29 const GrBatchTracker&) |
25 : fTextureSize(SkISize::Make(-1,-1)) | 30 : fColor(GrColor_ILLEGAL) |
| 31 , fTextureSize(SkISize::Make(-1,-1)) |
26 #ifdef SK_GAMMA_APPLY_TO_A8 | 32 #ifdef SK_GAMMA_APPLY_TO_A8 |
27 , fLuminance(-1.0f) | 33 , fLuminance(-1.0f) |
28 #endif | 34 #endif |
29 {} | 35 {} |
30 | 36 |
31 virtual void emitCode(const EmitArgs& args) SK_OVERRIDE { | 37 virtual void emitCode(const EmitArgs& args) SK_OVERRIDE { |
32 const GrDistanceFieldTextureEffect& dfTexEffect = | 38 const GrDistanceFieldTextureEffect& dfTexEffect = |
33 args.fGP.cast<GrDistanceFieldTextureEffect>(); | 39 args.fGP.cast<GrDistanceFieldTextureEffect>(); |
34 | 40 const DistanceFieldBatchTracker& local = args.fBT.cast<DistanceFieldBatc
hTracker>(); |
| 41 GrGLGPBuilder* pb = args.fPB; |
35 GrGLGPFragmentBuilder* fsBuilder = args.fPB->getFragmentShaderBuilder(); | 42 GrGLGPFragmentBuilder* fsBuilder = args.fPB->getFragmentShaderBuilder(); |
36 SkAssertResult(fsBuilder->enableFeature( | 43 SkAssertResult(fsBuilder->enableFeature( |
37 GrGLFragmentShaderBuilder::kStandardDerivatives_GLSLFeature)); | 44 GrGLFragmentShaderBuilder::kStandardDerivatives_GLSLFeature)); |
38 | 45 |
39 GrGLVertexBuilder* vsBuilder = args.fPB->getVertexShaderBuilder(); | 46 GrGLVertexBuilder* vsBuilder = args.fPB->getVertexShaderBuilder(); |
40 GrGLVertToFrag v(kVec2f_GrSLType); | 47 GrGLVertToFrag v(kVec2f_GrSLType); |
41 args.fPB->addVarying("TextureCoords", &v); | 48 args.fPB->addVarying("TextureCoords", &v); |
42 vsBuilder->codeAppendf("%s = %s;", v.vsOut(), dfTexEffect.inTextureCoord
s()->fName); | 49 vsBuilder->codeAppendf("%s = %s;", v.vsOut(), dfTexEffect.inTextureCoord
s()->fName); |
43 | 50 |
44 // setup color attribute | 51 // Setup pass through color |
45 if(dfTexEffect.inColor()) { | 52 this->setupColorPassThrough(pb, local.fInputColorType, args.fOutputColor
, |
46 args.fPB->addPassThroughAttribute(dfTexEffect.inColor(), args.fOutpu
tColor); | 53 dfTexEffect.inColor(), &fColorUniform); |
47 } | |
48 | 54 |
49 // setup position varying | 55 // setup position varying |
50 vsBuilder->codeAppendf("%s = %s * vec3(%s, 1);", vsBuilder->glPosition()
, | 56 vsBuilder->codeAppendf("%s = %s * vec3(%s, 1);", vsBuilder->glPosition()
, |
51 vsBuilder->uViewM(), dfTexEffect.inPosition()->fN
ame); | 57 vsBuilder->uViewM(), dfTexEffect.inPosition()->fN
ame); |
52 | 58 |
53 // setup output coords | 59 // setup output coords |
54 vsBuilder->codeAppendf("%s = %s;", vsBuilder->positionCoords(), | 60 vsBuilder->codeAppendf("%s = %s;", vsBuilder->positionCoords(), |
55 dfTexEffect.inPosition()->fName); | 61 dfTexEffect.inPosition()->fName); |
56 vsBuilder->codeAppendf("%s = %s;", vsBuilder->localCoords(), | 62 vsBuilder->codeAppendf("%s = %s;", vsBuilder->localCoords(), |
57 dfTexEffect.inPosition()->fName); | 63 dfTexEffect.inPosition()->fName); |
(...skipping 56 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
114 fsBuilder->codeAppend("\tvec4 gammaColor = "); | 120 fsBuilder->codeAppend("\tvec4 gammaColor = "); |
115 fsBuilder->appendTextureLookup(args.fSamplers[1], "uv", kVec2f_GrSLType)
; | 121 fsBuilder->appendTextureLookup(args.fSamplers[1], "uv", kVec2f_GrSLType)
; |
116 fsBuilder->codeAppend(";\n"); | 122 fsBuilder->codeAppend(";\n"); |
117 fsBuilder->codeAppend("\tval = gammaColor.r;\n"); | 123 fsBuilder->codeAppend("\tval = gammaColor.r;\n"); |
118 #endif | 124 #endif |
119 | 125 |
120 fsBuilder->codeAppendf("%s = vec4(val);", args.fOutputCoverage); | 126 fsBuilder->codeAppendf("%s = vec4(val);", args.fOutputCoverage); |
121 } | 127 } |
122 | 128 |
123 virtual void setData(const GrGLProgramDataManager& pdman, | 129 virtual void setData(const GrGLProgramDataManager& pdman, |
124 const GrGeometryProcessor& proc, | 130 const GrPrimitiveProcessor& proc, |
125 const GrBatchTracker&) SK_OVERRIDE { | 131 const GrBatchTracker& bt) SK_OVERRIDE { |
126 SkASSERT(fTextureSizeUni.isValid()); | 132 SkASSERT(fTextureSizeUni.isValid()); |
127 | 133 |
128 GrTexture* texture = proc.texture(0); | 134 GrTexture* texture = proc.texture(0); |
129 if (texture->width() != fTextureSize.width() || | 135 if (texture->width() != fTextureSize.width() || |
130 texture->height() != fTextureSize.height()) { | 136 texture->height() != fTextureSize.height()) { |
131 fTextureSize = SkISize::Make(texture->width(), texture->height()); | 137 fTextureSize = SkISize::Make(texture->width(), texture->height()); |
132 pdman.set2f(fTextureSizeUni, | 138 pdman.set2f(fTextureSizeUni, |
133 SkIntToScalar(fTextureSize.width()), | 139 SkIntToScalar(fTextureSize.width()), |
134 SkIntToScalar(fTextureSize.height())); | 140 SkIntToScalar(fTextureSize.height())); |
135 } | 141 } |
136 #ifdef SK_GAMMA_APPLY_TO_A8 | 142 #ifdef SK_GAMMA_APPLY_TO_A8 |
137 const GrDistanceFieldTextureEffect& dfTexEffect = | 143 const GrDistanceFieldTextureEffect& dfTexEffect = |
138 proc.cast<GrDistanceFieldTextureEffect>(); | 144 proc.cast<GrDistanceFieldTextureEffect>(); |
139 float luminance = dfTexEffect.getLuminance(); | 145 float luminance = dfTexEffect.getLuminance(); |
140 if (luminance != fLuminance) { | 146 if (luminance != fLuminance) { |
141 pdman.set1f(fLuminanceUni, luminance); | 147 pdman.set1f(fLuminanceUni, luminance); |
142 fLuminance = luminance; | 148 fLuminance = luminance; |
143 } | 149 } |
144 #endif | 150 #endif |
| 151 |
| 152 const DistanceFieldBatchTracker& local = bt.cast<DistanceFieldBatchTrack
er>(); |
| 153 if (kUniform_GrGPInput == local.fInputColorType && local.fColor != fColo
r) { |
| 154 GrGLfloat c[4]; |
| 155 GrColorToRGBAFloat(local.fColor, c); |
| 156 pdman.set4fv(fColorUniform, 1, c); |
| 157 fColor = local.fColor; |
| 158 } |
145 } | 159 } |
146 | 160 |
147 static inline void GenKey(const GrGeometryProcessor& processor, | 161 static inline void GenKey(const GrGeometryProcessor& processor, |
148 const GrBatchTracker&, | 162 const GrBatchTracker& bt, |
149 const GrGLCaps&, | 163 const GrGLCaps&, |
150 GrProcessorKeyBuilder* b) { | 164 GrProcessorKeyBuilder* b) { |
151 const GrDistanceFieldTextureEffect& dfTexEffect = | 165 const GrDistanceFieldTextureEffect& dfTexEffect = |
152 processor.cast<GrDistanceFieldTextureEffect>(); | 166 processor.cast<GrDistanceFieldTextureEffect>(); |
153 | 167 const DistanceFieldBatchTracker& local = bt.cast<DistanceFieldBatchTrack
er>(); |
154 b->add32(dfTexEffect.getFlags()); | 168 b->add32(dfTexEffect.getFlags()); |
| 169 b->add32(local.fInputColorType); |
155 } | 170 } |
156 | 171 |
157 private: | 172 private: |
158 GrGLProgramDataManager::UniformHandle fTextureSizeUni; | 173 GrColor fColor; |
159 SkISize fTextureSize; | 174 UniformHandle fColorUniform; |
160 GrGLProgramDataManager::UniformHandle fLuminanceUni; | 175 UniformHandle fTextureSizeUni; |
161 float fLuminance; | 176 SkISize fTextureSize; |
| 177 UniformHandle fLuminanceUni; |
| 178 float fLuminance; |
162 | 179 |
163 typedef GrGLGeometryProcessor INHERITED; | 180 typedef GrGLGeometryProcessor INHERITED; |
164 }; | 181 }; |
165 | 182 |
166 /////////////////////////////////////////////////////////////////////////////// | 183 /////////////////////////////////////////////////////////////////////////////// |
167 | 184 |
168 GrDistanceFieldTextureEffect::GrDistanceFieldTextureEffect(GrColor color, | 185 GrDistanceFieldTextureEffect::GrDistanceFieldTextureEffect(GrColor color, |
169 GrTexture* texture, | 186 GrTexture* texture, |
170 const GrTextureParams
& params, | 187 const GrTextureParams
& params, |
171 #ifdef SK_GAMMA_APPLY_TO_A8 | 188 #ifdef SK_GAMMA_APPLY_TO_A8 |
(...skipping 42 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
214 const GrGLCaps& caps, | 231 const GrGLCaps& caps, |
215 GrProcessorKeyBuilder* b) c
onst { | 232 GrProcessorKeyBuilder* b) c
onst { |
216 GrGLDistanceFieldTextureEffect::GenKey(*this, bt, caps, b); | 233 GrGLDistanceFieldTextureEffect::GenKey(*this, bt, caps, b); |
217 } | 234 } |
218 | 235 |
219 GrGLGeometryProcessor* | 236 GrGLGeometryProcessor* |
220 GrDistanceFieldTextureEffect::createGLInstance(const GrBatchTracker& bt) const { | 237 GrDistanceFieldTextureEffect::createGLInstance(const GrBatchTracker& bt) const { |
221 return SkNEW_ARGS(GrGLDistanceFieldTextureEffect, (*this, bt)); | 238 return SkNEW_ARGS(GrGLDistanceFieldTextureEffect, (*this, bt)); |
222 } | 239 } |
223 | 240 |
| 241 void GrDistanceFieldTextureEffect::initBatchTracker(GrBatchTracker* bt, const In
itBT& init) const { |
| 242 DistanceFieldBatchTracker* local = bt->cast<DistanceFieldBatchTracker>(); |
| 243 local->fInputColorType = GetColorInputType(&local->fColor, this->color(), in
it, |
| 244 SkToBool(fInColor)); |
| 245 } |
| 246 |
| 247 bool GrDistanceFieldTextureEffect::onCanMakeEqual(const GrBatchTracker& m, |
| 248 const GrBatchTracker& t) const
{ |
| 249 const DistanceFieldBatchTracker& mine = m.cast<DistanceFieldBatchTracker>(); |
| 250 const DistanceFieldBatchTracker& theirs = t.cast<DistanceFieldBatchTracker>(
); |
| 251 return CanCombineOutput(mine.fInputColorType, mine.fColor, |
| 252 theirs.fInputColorType, theirs.fColor); |
| 253 } |
| 254 |
224 /////////////////////////////////////////////////////////////////////////////// | 255 /////////////////////////////////////////////////////////////////////////////// |
225 | 256 |
226 GR_DEFINE_GEOMETRY_PROCESSOR_TEST(GrDistanceFieldTextureEffect); | 257 GR_DEFINE_GEOMETRY_PROCESSOR_TEST(GrDistanceFieldTextureEffect); |
227 | 258 |
228 GrGeometryProcessor* GrDistanceFieldTextureEffect::TestCreate(SkRandom* random, | 259 GrGeometryProcessor* GrDistanceFieldTextureEffect::TestCreate(SkRandom* random, |
229 GrContext*, | 260 GrContext*, |
230 const GrDrawTarget
Caps&, | 261 const GrDrawTarget
Caps&, |
231 GrTexture* texture
s[]) { | 262 GrTexture* texture
s[]) { |
232 int texIdx = random->nextBool() ? GrProcessorUnitTest::kSkiaPMTextureIdx : | 263 int texIdx = random->nextBool() ? GrProcessorUnitTest::kSkiaPMTextureIdx : |
233 GrProcessorUnitTest::kAlphaTextureIdx; | 264 GrProcessorUnitTest::kAlphaTextureIdx; |
(...skipping 22 matching lines...) Expand all Loading... |
256 textures[texIdx2], params2, | 287 textures[texIdx2], params2, |
257 random->nextF(), | 288 random->nextF(), |
258 #endif | 289 #endif |
259 random->nextBool() ? | 290 random->nextBool() ? |
260 kSimilarity_DistanceFieldEff
ectFlag : 0, | 291 kSimilarity_DistanceFieldEff
ectFlag : 0, |
261 random->nextBool()); | 292 random->nextBool()); |
262 } | 293 } |
263 | 294 |
264 /////////////////////////////////////////////////////////////////////////////// | 295 /////////////////////////////////////////////////////////////////////////////// |
265 | 296 |
| 297 struct DistanceFieldNoGammaBatchTracker { |
| 298 GrGPInput fInputColorType; |
| 299 GrColor fColor; |
| 300 }; |
| 301 |
266 class GrGLDistanceFieldNoGammaTextureEffect : public GrGLGeometryProcessor { | 302 class GrGLDistanceFieldNoGammaTextureEffect : public GrGLGeometryProcessor { |
267 public: | 303 public: |
268 GrGLDistanceFieldNoGammaTextureEffect(const GrGeometryProcessor&, | 304 GrGLDistanceFieldNoGammaTextureEffect(const GrGeometryProcessor&, |
269 const GrBatchTracker&) | 305 const GrBatchTracker&) |
270 : fTextureSize(SkISize::Make(-1, -1)) {} | 306 : fColor(GrColor_ILLEGAL), fTextureSize(SkISize::Make(-1, -1)) {} |
271 | 307 |
272 virtual void emitCode(const EmitArgs& args) SK_OVERRIDE { | 308 virtual void emitCode(const EmitArgs& args) SK_OVERRIDE { |
273 const GrDistanceFieldNoGammaTextureEffect& dfTexEffect = | 309 const GrDistanceFieldNoGammaTextureEffect& dfTexEffect = |
274 args.fGP.cast<GrDistanceFieldNoGammaTextureEffect>(); | 310 args.fGP.cast<GrDistanceFieldNoGammaTextureEffect>(); |
275 | 311 |
| 312 const DistanceFieldNoGammaBatchTracker& local = |
| 313 args.fBT.cast<DistanceFieldNoGammaBatchTracker>(); |
| 314 GrGLGPBuilder* pb = args.fPB; |
276 GrGLGPFragmentBuilder* fsBuilder = args.fPB->getFragmentShaderBuilder(); | 315 GrGLGPFragmentBuilder* fsBuilder = args.fPB->getFragmentShaderBuilder(); |
277 SkAssertResult(fsBuilder->enableFeature( | 316 SkAssertResult(fsBuilder->enableFeature( |
278 GrGLFragmentShaderBuilder::kStandardDerivat
ives_GLSLFeature)); | 317 GrGLFragmentShaderBuilder::kStandardDerivat
ives_GLSLFeature)); |
279 | 318 |
280 GrGLVertexBuilder* vsBuilder = args.fPB->getVertexShaderBuilder(); | 319 GrGLVertexBuilder* vsBuilder = args.fPB->getVertexShaderBuilder(); |
281 GrGLVertToFrag v(kVec2f_GrSLType); | 320 GrGLVertToFrag v(kVec2f_GrSLType); |
282 args.fPB->addVarying("TextureCoords", &v); | 321 args.fPB->addVarying("TextureCoords", &v); |
283 | 322 |
284 // setup color attribute | 323 // setup pass through color |
285 if(dfTexEffect.inColor()) { | 324 this->setupColorPassThrough(pb, local.fInputColorType, args.fOutputColor
, |
286 args.fPB->addPassThroughAttribute(dfTexEffect.inColor(), args.fOutpu
tColor); | 325 dfTexEffect.inColor(), &fColorUniform); |
287 } | |
288 | 326 |
289 vsBuilder->codeAppendf("%s = %s;", v.vsOut(), dfTexEffect.inTextureCoord
s()->fName); | 327 vsBuilder->codeAppendf("%s = %s;", v.vsOut(), dfTexEffect.inTextureCoord
s()->fName); |
290 | 328 |
291 // setup coord outputs | 329 // setup coord outputs |
292 vsBuilder->codeAppendf("%s = %s;", vsBuilder->positionCoords(), | 330 vsBuilder->codeAppendf("%s = %s;", vsBuilder->positionCoords(), |
293 dfTexEffect.inPosition()->fName); | 331 dfTexEffect.inPosition()->fName); |
294 vsBuilder->codeAppendf("%s = %s;", vsBuilder->localCoords(), | 332 vsBuilder->codeAppendf("%s = %s;", vsBuilder->localCoords(), |
295 dfTexEffect.inPosition()->fName); | 333 dfTexEffect.inPosition()->fName); |
296 | 334 |
297 // setup position varying | 335 // setup position varying |
(...skipping 43 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
341 | 379 |
342 // this gives us a smooth step across approximately one fragment | 380 // this gives us a smooth step across approximately one fragment |
343 fsBuilder->codeAppend("afwidth = " SK_DistanceFieldAAFactor "*length
(grad);"); | 381 fsBuilder->codeAppend("afwidth = " SK_DistanceFieldAAFactor "*length
(grad);"); |
344 } | 382 } |
345 fsBuilder->codeAppend("float val = smoothstep(-afwidth, afwidth, distanc
e);"); | 383 fsBuilder->codeAppend("float val = smoothstep(-afwidth, afwidth, distanc
e);"); |
346 | 384 |
347 fsBuilder->codeAppendf("%s = vec4(val);", args.fOutputCoverage); | 385 fsBuilder->codeAppendf("%s = vec4(val);", args.fOutputCoverage); |
348 } | 386 } |
349 | 387 |
350 virtual void setData(const GrGLProgramDataManager& pdman, | 388 virtual void setData(const GrGLProgramDataManager& pdman, |
351 const GrGeometryProcessor& proc, | 389 const GrPrimitiveProcessor& proc, |
352 const GrBatchTracker&) SK_OVERRIDE { | 390 const GrBatchTracker& bt) SK_OVERRIDE { |
353 SkASSERT(fTextureSizeUni.isValid()); | 391 SkASSERT(fTextureSizeUni.isValid()); |
354 | 392 |
355 GrTexture* texture = proc.texture(0); | 393 GrTexture* texture = proc.texture(0); |
356 if (texture->width() != fTextureSize.width() || | 394 if (texture->width() != fTextureSize.width() || |
357 texture->height() != fTextureSize.height()) { | 395 texture->height() != fTextureSize.height()) { |
358 fTextureSize = SkISize::Make(texture->width(), texture->height()); | 396 fTextureSize = SkISize::Make(texture->width(), texture->height()); |
359 pdman.set2f(fTextureSizeUni, | 397 pdman.set2f(fTextureSizeUni, |
360 SkIntToScalar(fTextureSize.width()), | 398 SkIntToScalar(fTextureSize.width()), |
361 SkIntToScalar(fTextureSize.height())); | 399 SkIntToScalar(fTextureSize.height())); |
362 } | 400 } |
| 401 |
| 402 const DistanceFieldNoGammaBatchTracker& local = bt.cast<DistanceFieldNoG
ammaBatchTracker>(); |
| 403 if (kUniform_GrGPInput == local.fInputColorType && local.fColor != fColo
r) { |
| 404 GrGLfloat c[4]; |
| 405 GrColorToRGBAFloat(local.fColor, c); |
| 406 pdman.set4fv(fColorUniform, 1, c); |
| 407 fColor = local.fColor; |
| 408 } |
363 } | 409 } |
364 | 410 |
365 static inline void GenKey(const GrGeometryProcessor& proc, | 411 static inline void GenKey(const GrGeometryProcessor& proc, |
366 const GrBatchTracker&, | 412 const GrBatchTracker& bt, |
367 const GrGLCaps&, | 413 const GrGLCaps&, |
368 GrProcessorKeyBuilder* b) { | 414 GrProcessorKeyBuilder* b) { |
369 const GrDistanceFieldNoGammaTextureEffect& dfTexEffect = | 415 const GrDistanceFieldNoGammaTextureEffect& dfTexEffect = |
370 proc.cast<GrDistanceFieldNoGammaTextureEffect>(); | 416 proc.cast<GrDistanceFieldNoGammaTextureEffect>(); |
371 | 417 |
| 418 const DistanceFieldNoGammaBatchTracker& local = bt.cast<DistanceFieldNoG
ammaBatchTracker>(); |
372 b->add32(dfTexEffect.getFlags()); | 419 b->add32(dfTexEffect.getFlags()); |
| 420 b->add32(local.fInputColorType); |
373 } | 421 } |
374 | 422 |
375 private: | 423 private: |
376 GrGLProgramDataManager::UniformHandle fTextureSizeUni; | 424 UniformHandle fColorUniform; |
377 SkISize fTextureSize; | 425 UniformHandle fTextureSizeUni; |
| 426 GrColor fColor; |
| 427 SkISize fTextureSize; |
378 | 428 |
379 typedef GrGLGeometryProcessor INHERITED; | 429 typedef GrGLGeometryProcessor INHERITED; |
380 }; | 430 }; |
381 | 431 |
382 /////////////////////////////////////////////////////////////////////////////// | 432 /////////////////////////////////////////////////////////////////////////////// |
383 | 433 |
384 GrDistanceFieldNoGammaTextureEffect::GrDistanceFieldNoGammaTextureEffect( | 434 GrDistanceFieldNoGammaTextureEffect::GrDistanceFieldNoGammaTextureEffect( |
385 GrColor color, | 435 GrColor color, |
386 GrTexture* texture, | 436 GrTexture* texture, |
387 const GrTextureParams& params, | 437 const GrTextureParams& params, |
(...skipping 29 matching lines...) Expand all Loading... |
417 const GrGLCaps& caps
, | 467 const GrGLCaps& caps
, |
418 GrProcessorKeyBuilde
r* b) const { | 468 GrProcessorKeyBuilde
r* b) const { |
419 GrGLDistanceFieldNoGammaTextureEffect::GenKey(*this, bt, caps, b); | 469 GrGLDistanceFieldNoGammaTextureEffect::GenKey(*this, bt, caps, b); |
420 } | 470 } |
421 | 471 |
422 GrGLGeometryProcessor* | 472 GrGLGeometryProcessor* |
423 GrDistanceFieldNoGammaTextureEffect::createGLInstance(const GrBatchTracker& bt)
const { | 473 GrDistanceFieldNoGammaTextureEffect::createGLInstance(const GrBatchTracker& bt)
const { |
424 return SkNEW_ARGS(GrGLDistanceFieldNoGammaTextureEffect, (*this, bt)); | 474 return SkNEW_ARGS(GrGLDistanceFieldNoGammaTextureEffect, (*this, bt)); |
425 } | 475 } |
426 | 476 |
| 477 void GrDistanceFieldNoGammaTextureEffect::initBatchTracker(GrBatchTracker* bt, |
| 478 const InitBT& init) c
onst { |
| 479 DistanceFieldNoGammaBatchTracker* local = bt->cast<DistanceFieldNoGammaBatch
Tracker>(); |
| 480 local->fInputColorType = GetColorInputType(&local->fColor, this->color(), in
it, |
| 481 SkToBool(fInColor)); |
| 482 } |
| 483 |
| 484 bool GrDistanceFieldNoGammaTextureEffect::onCanMakeEqual(const GrBatchTracker& m
, |
| 485 const GrBatchTracker& t
) const { |
| 486 const DistanceFieldNoGammaBatchTracker& mine = m.cast<DistanceFieldNoGammaBa
tchTracker>(); |
| 487 const DistanceFieldNoGammaBatchTracker& theirs = t.cast<DistanceFieldNoGamma
BatchTracker>(); |
| 488 return CanCombineOutput(mine.fInputColorType, mine.fColor, |
| 489 theirs.fInputColorType, theirs.fColor); |
| 490 } |
| 491 |
427 /////////////////////////////////////////////////////////////////////////////// | 492 /////////////////////////////////////////////////////////////////////////////// |
428 | 493 |
429 GR_DEFINE_GEOMETRY_PROCESSOR_TEST(GrDistanceFieldNoGammaTextureEffect); | 494 GR_DEFINE_GEOMETRY_PROCESSOR_TEST(GrDistanceFieldNoGammaTextureEffect); |
430 | 495 |
431 GrGeometryProcessor* GrDistanceFieldNoGammaTextureEffect::TestCreate(SkRandom* r
andom, | 496 GrGeometryProcessor* GrDistanceFieldNoGammaTextureEffect::TestCreate(SkRandom* r
andom, |
432 GrContext*, | 497 GrContext*, |
433 const GrDra
wTargetCaps&, | 498 const GrDra
wTargetCaps&, |
434 GrTexture*
textures[]) { | 499 GrTexture*
textures[]) { |
435 int texIdx = random->nextBool() ? GrProcessorUnitTest::kSkiaPMTextureIdx | 500 int texIdx = random->nextBool() ? GrProcessorUnitTest::kSkiaPMTextureIdx |
436 : GrProcessorUnitTest::kAlphaTextureIdx; | 501 : GrProcessorUnitTest::kAlphaTextureIdx; |
437 static const SkShader::TileMode kTileModes[] = { | 502 static const SkShader::TileMode kTileModes[] = { |
438 SkShader::kClamp_TileMode, | 503 SkShader::kClamp_TileMode, |
439 SkShader::kRepeat_TileMode, | 504 SkShader::kRepeat_TileMode, |
440 SkShader::kMirror_TileMode, | 505 SkShader::kMirror_TileMode, |
441 }; | 506 }; |
442 SkShader::TileMode tileModes[] = { | 507 SkShader::TileMode tileModes[] = { |
443 kTileModes[random->nextULessThan(SK_ARRAY_COUNT(kTileModes))], | 508 kTileModes[random->nextULessThan(SK_ARRAY_COUNT(kTileModes))], |
444 kTileModes[random->nextULessThan(SK_ARRAY_COUNT(kTileModes))], | 509 kTileModes[random->nextULessThan(SK_ARRAY_COUNT(kTileModes))], |
445 }; | 510 }; |
446 GrTextureParams params(tileModes, random->nextBool() ? GrTextureParams::kBil
erp_FilterMode | 511 GrTextureParams params(tileModes, random->nextBool() ? GrTextureParams::kBil
erp_FilterMode |
447 : GrTextureParams::kNon
e_FilterMode); | 512 : GrTextureParams::kNon
e_FilterMode); |
448 | 513 |
449 return GrDistanceFieldNoGammaTextureEffect::Create(GrRandomColor(random), te
xtures[texIdx], | 514 return GrDistanceFieldNoGammaTextureEffect::Create(GrRandomColor(random), te
xtures[texIdx], |
450 params, | 515 params, |
451 random->nextBool() ? kSimilarity_DistanceFieldEffectFlag : 0, random->ne
xtBool()); | 516 random->nextBool() ? kSimilarity_DistanceFieldEffectFlag : 0, random->ne
xtBool()); |
452 } | 517 } |
453 | 518 |
454 /////////////////////////////////////////////////////////////////////////////// | 519 /////////////////////////////////////////////////////////////////////////////// |
455 | 520 |
| 521 struct DistanceFieldLCDBatchTracker { |
| 522 GrGPInput fInputColorType; |
| 523 GrColor fColor; |
| 524 }; |
| 525 |
456 class GrGLDistanceFieldLCDTextureEffect : public GrGLGeometryProcessor { | 526 class GrGLDistanceFieldLCDTextureEffect : public GrGLGeometryProcessor { |
457 public: | 527 public: |
458 GrGLDistanceFieldLCDTextureEffect(const GrGeometryProcessor&, | 528 GrGLDistanceFieldLCDTextureEffect(const GrGeometryProcessor&, |
459 const GrBatchTracker&) | 529 const GrBatchTracker&) |
460 : fTextureSize(SkISize::Make(-1,-1)) | 530 : fColor(GrColor_ILLEGAL) |
| 531 , fTextureSize(SkISize::Make(-1,-1)) |
461 , fTextColor(GrColor_ILLEGAL) {} | 532 , fTextColor(GrColor_ILLEGAL) {} |
462 | 533 |
463 virtual void emitCode(const EmitArgs& args) SK_OVERRIDE { | 534 virtual void emitCode(const EmitArgs& args) SK_OVERRIDE { |
464 const GrDistanceFieldLCDTextureEffect& dfTexEffect = | 535 const GrDistanceFieldLCDTextureEffect& dfTexEffect = |
465 args.fGP.cast<GrDistanceFieldLCDTextureEffect>(); | 536 args.fGP.cast<GrDistanceFieldLCDTextureEffect>(); |
| 537 const DistanceFieldLCDBatchTracker& local = args.fBT.cast<DistanceFieldL
CDBatchTracker>(); |
| 538 GrGLGPBuilder* pb = args.fPB; |
466 | 539 |
467 GrGLVertexBuilder* vsBuilder = args.fPB->getVertexShaderBuilder(); | 540 GrGLVertexBuilder* vsBuilder = args.fPB->getVertexShaderBuilder(); |
468 GrGLVertToFrag v(kVec2f_GrSLType); | 541 GrGLVertToFrag v(kVec2f_GrSLType); |
469 args.fPB->addVarying("TextureCoords", &v); | 542 args.fPB->addVarying("TextureCoords", &v); |
470 vsBuilder->codeAppendf("%s = %s;", v.vsOut(), dfTexEffect.inTextureCoord
s()->fName); | 543 vsBuilder->codeAppendf("%s = %s;", v.vsOut(), dfTexEffect.inTextureCoord
s()->fName); |
471 | 544 |
| 545 // setup pass through color |
| 546 this->setupColorPassThrough(pb, local.fInputColorType, args.fOutputColor
, NULL, |
| 547 &fColorUniform); |
| 548 |
472 // setup coord outputs | 549 // setup coord outputs |
473 vsBuilder->codeAppendf("%s = %s;", vsBuilder->positionCoords(), | 550 vsBuilder->codeAppendf("%s = %s;", vsBuilder->positionCoords(), |
474 dfTexEffect.inPosition()->fName); | 551 dfTexEffect.inPosition()->fName); |
475 vsBuilder->codeAppendf("%s = %s;", vsBuilder->localCoords(), | 552 vsBuilder->codeAppendf("%s = %s;", vsBuilder->localCoords(), |
476 dfTexEffect.inPosition()->fName); | 553 dfTexEffect.inPosition()->fName); |
477 | 554 |
478 // setup position varying | 555 // setup position varying |
479 vsBuilder->codeAppendf("%s = %s * vec3(%s, 1);", vsBuilder->glPosition()
, | 556 vsBuilder->codeAppendf("%s = %s * vec3(%s, 1);", vsBuilder->glPosition()
, |
480 vsBuilder->uViewM(), dfTexEffect.inPosition()->fN
ame); | 557 vsBuilder->uViewM(), dfTexEffect.inPosition()->fN
ame); |
481 | 558 |
(...skipping 99 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
581 fsBuilder->codeAppendf("\tuv = vec2(val.z, %s.z);\n", textColorUniName); | 658 fsBuilder->codeAppendf("\tuv = vec2(val.z, %s.z);\n", textColorUniName); |
582 fsBuilder->codeAppend("\tgammaColor = "); | 659 fsBuilder->codeAppend("\tgammaColor = "); |
583 fsBuilder->appendTextureLookup(args.fSamplers[1], "uv", kVec2f_GrSLType)
; | 660 fsBuilder->appendTextureLookup(args.fSamplers[1], "uv", kVec2f_GrSLType)
; |
584 fsBuilder->codeAppend(";\n"); | 661 fsBuilder->codeAppend(";\n"); |
585 fsBuilder->codeAppend("\tval.z = gammaColor.r;\n"); | 662 fsBuilder->codeAppend("\tval.z = gammaColor.r;\n"); |
586 | 663 |
587 fsBuilder->codeAppendf("%s = vec4(val);", args.fOutputCoverage); | 664 fsBuilder->codeAppendf("%s = vec4(val);", args.fOutputCoverage); |
588 } | 665 } |
589 | 666 |
590 virtual void setData(const GrGLProgramDataManager& pdman, | 667 virtual void setData(const GrGLProgramDataManager& pdman, |
591 const GrGeometryProcessor& processor, | 668 const GrPrimitiveProcessor& processor, |
592 const GrBatchTracker&) SK_OVERRIDE { | 669 const GrBatchTracker& bt) SK_OVERRIDE { |
593 SkASSERT(fTextureSizeUni.isValid()); | 670 SkASSERT(fTextureSizeUni.isValid()); |
594 SkASSERT(fTextColorUni.isValid()); | 671 SkASSERT(fTextColorUni.isValid()); |
595 | 672 |
596 const GrDistanceFieldLCDTextureEffect& dfTexEffect = | 673 const GrDistanceFieldLCDTextureEffect& dfTexEffect = |
597 processor.cast<GrDistanceFieldLCDTextureEffect>(); | 674 processor.cast<GrDistanceFieldLCDTextureEffect>(); |
598 GrTexture* texture = processor.texture(0); | 675 GrTexture* texture = processor.texture(0); |
599 if (texture->width() != fTextureSize.width() || | 676 if (texture->width() != fTextureSize.width() || |
600 texture->height() != fTextureSize.height()) { | 677 texture->height() != fTextureSize.height()) { |
601 fTextureSize = SkISize::Make(texture->width(), texture->height()); | 678 fTextureSize = SkISize::Make(texture->width(), texture->height()); |
602 float delta = 1.0f/(3.0f*texture->width()); | 679 float delta = 1.0f/(3.0f*texture->width()); |
603 if (dfTexEffect.getFlags() & kBGR_DistanceFieldEffectFlag) { | 680 if (dfTexEffect.getFlags() & kBGR_DistanceFieldEffectFlag) { |
604 delta = -delta; | 681 delta = -delta; |
605 } | 682 } |
606 pdman.set3f(fTextureSizeUni, | 683 pdman.set3f(fTextureSizeUni, |
607 SkIntToScalar(fTextureSize.width()), | 684 SkIntToScalar(fTextureSize.width()), |
608 SkIntToScalar(fTextureSize.height()), | 685 SkIntToScalar(fTextureSize.height()), |
609 delta); | 686 delta); |
610 } | 687 } |
611 | 688 |
612 GrColor textColor = dfTexEffect.getTextColor(); | 689 GrColor textColor = dfTexEffect.getTextColor(); |
613 if (textColor != fTextColor) { | 690 if (textColor != fTextColor) { |
614 static const float ONE_OVER_255 = 1.f / 255.f; | 691 static const float ONE_OVER_255 = 1.f / 255.f; |
615 pdman.set3f(fTextColorUni, | 692 pdman.set3f(fTextColorUni, |
616 GrColorUnpackR(textColor) * ONE_OVER_255, | 693 GrColorUnpackR(textColor) * ONE_OVER_255, |
617 GrColorUnpackG(textColor) * ONE_OVER_255, | 694 GrColorUnpackG(textColor) * ONE_OVER_255, |
618 GrColorUnpackB(textColor) * ONE_OVER_255); | 695 GrColorUnpackB(textColor) * ONE_OVER_255); |
619 fTextColor = textColor; | 696 fTextColor = textColor; |
620 } | 697 } |
| 698 |
| 699 const DistanceFieldLCDBatchTracker& local = bt.cast<DistanceFieldLCDBatc
hTracker>(); |
| 700 if (kUniform_GrGPInput == local.fInputColorType && local.fColor != fColo
r) { |
| 701 GrGLfloat c[4]; |
| 702 GrColorToRGBAFloat(local.fColor, c); |
| 703 pdman.set4fv(fColorUniform, 1, c); |
| 704 fColor = local.fColor; |
| 705 } |
621 } | 706 } |
622 | 707 |
623 static inline void GenKey(const GrGeometryProcessor& processor, | 708 static inline void GenKey(const GrGeometryProcessor& processor, |
624 const GrBatchTracker&, | 709 const GrBatchTracker& bt, |
625 const GrGLCaps&, | 710 const GrGLCaps&, |
626 GrProcessorKeyBuilder* b) { | 711 GrProcessorKeyBuilder* b) { |
627 const GrDistanceFieldLCDTextureEffect& dfTexEffect = | 712 const GrDistanceFieldLCDTextureEffect& dfTexEffect = |
628 processor.cast<GrDistanceFieldLCDTextureEffect>(); | 713 processor.cast<GrDistanceFieldLCDTextureEffect>(); |
629 | 714 |
| 715 const DistanceFieldLCDBatchTracker& local = bt.cast<DistanceFieldLCDBatc
hTracker>(); |
630 b->add32(dfTexEffect.getFlags()); | 716 b->add32(dfTexEffect.getFlags()); |
| 717 b->add32(local.fInputColorType); |
631 } | 718 } |
632 | 719 |
633 private: | 720 private: |
634 GrGLProgramDataManager::UniformHandle fTextureSizeUni; | 721 GrColor fColor; |
635 SkISize fTextureSize; | 722 UniformHandle fColorUniform; |
636 GrGLProgramDataManager::UniformHandle fTextColorUni; | 723 UniformHandle fTextureSizeUni; |
637 SkColor fTextColor; | 724 SkISize fTextureSize; |
| 725 UniformHandle fTextColorUni; |
| 726 SkColor fTextColor; |
638 | 727 |
639 typedef GrGLGeometryProcessor INHERITED; | 728 typedef GrGLGeometryProcessor INHERITED; |
640 }; | 729 }; |
641 | 730 |
642 /////////////////////////////////////////////////////////////////////////////// | 731 /////////////////////////////////////////////////////////////////////////////// |
643 | 732 |
644 GrDistanceFieldLCDTextureEffect::GrDistanceFieldLCDTextureEffect( | 733 GrDistanceFieldLCDTextureEffect::GrDistanceFieldLCDTextureEffect( |
645 GrColor color, | 734 GrColor color, |
646 GrTexture* texture, const GrTe
xtureParams& params, | 735 GrTexture* texture, const GrTe
xtureParams& params, |
647 GrTexture* gamma, const GrText
ureParams& gParams, | 736 GrTexture* gamma, const GrText
ureParams& gParams, |
(...skipping 28 matching lines...) Expand all Loading... |
676 const GrGLCaps& caps, | 765 const GrGLCaps& caps, |
677 GrProcessorKeyBuilder* b
) const { | 766 GrProcessorKeyBuilder* b
) const { |
678 GrGLDistanceFieldLCDTextureEffect::GenKey(*this, bt, caps, b); | 767 GrGLDistanceFieldLCDTextureEffect::GenKey(*this, bt, caps, b); |
679 } | 768 } |
680 | 769 |
681 GrGLGeometryProcessor* | 770 GrGLGeometryProcessor* |
682 GrDistanceFieldLCDTextureEffect::createGLInstance(const GrBatchTracker& bt) cons
t { | 771 GrDistanceFieldLCDTextureEffect::createGLInstance(const GrBatchTracker& bt) cons
t { |
683 return SkNEW_ARGS(GrGLDistanceFieldLCDTextureEffect, (*this, bt)); | 772 return SkNEW_ARGS(GrGLDistanceFieldLCDTextureEffect, (*this, bt)); |
684 } | 773 } |
685 | 774 |
| 775 void GrDistanceFieldLCDTextureEffect::initBatchTracker(GrBatchTracker* bt, |
| 776 const InitBT& init) const
{ |
| 777 DistanceFieldLCDBatchTracker* local = bt->cast<DistanceFieldLCDBatchTracker>
(); |
| 778 local->fInputColorType = GetColorInputType(&local->fColor, this->color(), in
it, false); |
| 779 } |
| 780 |
| 781 bool GrDistanceFieldLCDTextureEffect::onCanMakeEqual(const GrBatchTracker& m, |
| 782 const GrBatchTracker& t) co
nst { |
| 783 const DistanceFieldLCDBatchTracker& mine = m.cast<DistanceFieldLCDBatchTrack
er>(); |
| 784 const DistanceFieldLCDBatchTracker& theirs = t.cast<DistanceFieldLCDBatchTra
cker>(); |
| 785 return CanCombineOutput(mine.fInputColorType, mine.fColor, |
| 786 theirs.fInputColorType, theirs.fColor); |
| 787 } |
| 788 |
686 /////////////////////////////////////////////////////////////////////////////// | 789 /////////////////////////////////////////////////////////////////////////////// |
687 | 790 |
688 GR_DEFINE_GEOMETRY_PROCESSOR_TEST(GrDistanceFieldLCDTextureEffect); | 791 GR_DEFINE_GEOMETRY_PROCESSOR_TEST(GrDistanceFieldLCDTextureEffect); |
689 | 792 |
690 GrGeometryProcessor* GrDistanceFieldLCDTextureEffect::TestCreate(SkRandom* rando
m, | 793 GrGeometryProcessor* GrDistanceFieldLCDTextureEffect::TestCreate(SkRandom* rando
m, |
691 GrContext*, | 794 GrContext*, |
692 const GrDrawTar
getCaps&, | 795 const GrDrawTar
getCaps&, |
693 GrTexture* text
ures[]) { | 796 GrTexture* text
ures[]) { |
694 int texIdx = random->nextBool() ? GrProcessorUnitTest::kSkiaPMTextureIdx : | 797 int texIdx = random->nextBool() ? GrProcessorUnitTest::kSkiaPMTextureIdx : |
695 GrProcessorUnitTest::kAlphaTextureIdx; | 798 GrProcessorUnitTest::kAlphaTextureIdx; |
(...skipping 17 matching lines...) Expand all Loading... |
713 random->nextULessThan(256), | 816 random->nextULessThan(256), |
714 random->nextULessThan(256)); | 817 random->nextULessThan(256)); |
715 uint32_t flags = kUseLCD_DistanceFieldEffectFlag; | 818 uint32_t flags = kUseLCD_DistanceFieldEffectFlag; |
716 flags |= random->nextBool() ? kUniformScale_DistanceFieldEffectMask : 0; | 819 flags |= random->nextBool() ? kUniformScale_DistanceFieldEffectMask : 0; |
717 flags |= random->nextBool() ? kBGR_DistanceFieldEffectFlag : 0; | 820 flags |= random->nextBool() ? kBGR_DistanceFieldEffectFlag : 0; |
718 return GrDistanceFieldLCDTextureEffect::Create(GrRandomColor(random), textur
es[texIdx], params, | 821 return GrDistanceFieldLCDTextureEffect::Create(GrRandomColor(random), textur
es[texIdx], params, |
719 textures[texIdx2], params2, | 822 textures[texIdx2], params2, |
720 textColor, | 823 textColor, |
721 flags); | 824 flags); |
722 } | 825 } |
OLD | NEW |