OLD | NEW |
1 /* | 1 /* |
2 * Copyright 2014 Google Inc. | 2 * Copyright 2014 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 "effects/GrPorterDuffXferProcessor.h" | 8 #include "effects/GrPorterDuffXferProcessor.h" |
9 | 9 |
10 #include "GrBlend.h" | 10 #include "GrBlend.h" |
(...skipping 501 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
512 this->initClassID<ShaderPDXferProcessor>(); | 512 this->initClassID<ShaderPDXferProcessor>(); |
513 } | 513 } |
514 | 514 |
515 const char* name() const override { return "Porter Duff Shader"; } | 515 const char* name() const override { return "Porter Duff Shader"; } |
516 | 516 |
517 GrGLSLXferProcessor* createGLSLInstance() const override; | 517 GrGLSLXferProcessor* createGLSLInstance() const override; |
518 | 518 |
519 SkXfermode::Mode getXfermode() const { return fXfermode; } | 519 SkXfermode::Mode getXfermode() const { return fXfermode; } |
520 | 520 |
521 private: | 521 private: |
522 GrXferProcessor::OptFlags onGetOptimizations(const GrPipelineOptimizations&,
bool, GrColor*, | 522 GrXferProcessor::OptFlags onGetOptimizations(const GrPipelineOptimizations&,
bool, GrColor*, |
523 const GrCaps&) const override { | 523 const GrCaps&) const override { |
524 return kNone_OptFlags; | 524 return kNone_OptFlags; |
525 } | 525 } |
526 | 526 |
527 void onGetGLSLProcessorKey(const GrGLSLCaps& caps, GrProcessorKeyBuilder* b)
const override; | 527 void onGetGLSLProcessorKey(const GrGLSLCaps& caps, GrProcessorKeyBuilder* b)
const override; |
528 | 528 |
529 bool onIsEqual(const GrXferProcessor& xpBase) const override { | 529 bool onIsEqual(const GrXferProcessor& xpBase) const override { |
530 const ShaderPDXferProcessor& xp = xpBase.cast<ShaderPDXferProcessor>(); | 530 const ShaderPDXferProcessor& xp = xpBase.cast<ShaderPDXferProcessor>(); |
531 return fXfermode == xp.fXfermode; | 531 return fXfermode == xp.fXfermode; |
532 } | 532 } |
(...skipping 215 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
748 kRGBA_GrColorComponentFlags == optimizations.fColorPOI.validFlags()
&& | 748 kRGBA_GrColorComponentFlags == optimizations.fColorPOI.validFlags()
&& |
749 !caps.shaderCaps()->dualSourceBlendingSupport() && | 749 !caps.shaderCaps()->dualSourceBlendingSupport() && |
750 !caps.shaderCaps()->dstReadInShaderSupport()) { | 750 !caps.shaderCaps()->dstReadInShaderSupport()) { |
751 // If we don't have dual source blending or in shader dst reads, we
fall back to this | 751 // If we don't have dual source blending or in shader dst reads, we
fall back to this |
752 // trick for rendering SrcOver LCD text instead of doing a dst copy. | 752 // trick for rendering SrcOver LCD text instead of doing a dst copy. |
753 SkASSERT(!dstTexture || !dstTexture->texture()); | 753 SkASSERT(!dstTexture || !dstTexture->texture()); |
754 return PDLCDXferProcessor::Create(fXfermode, optimizations.fColorPOI
); | 754 return PDLCDXferProcessor::Create(fXfermode, optimizations.fColorPOI
); |
755 } | 755 } |
756 blendFormula = get_lcd_blend_formula(optimizations.fCoveragePOI, fXfermo
de); | 756 blendFormula = get_lcd_blend_formula(optimizations.fCoveragePOI, fXfermo
de); |
757 } else { | 757 } else { |
758 blendFormula = get_blend_formula(optimizations.fColorPOI, optimizations.
fCoveragePOI, | 758 blendFormula = get_blend_formula(optimizations.fColorPOI, optimizations.
fCoveragePOI, |
759 hasMixedSamples, fXfermode); | 759 hasMixedSamples, fXfermode); |
760 } | 760 } |
761 | 761 |
762 if (blendFormula.hasSecondaryOutput() && !caps.shaderCaps()->dualSourceBlend
ingSupport()) { | 762 if (blendFormula.hasSecondaryOutput() && !caps.shaderCaps()->dualSourceBlend
ingSupport()) { |
763 return new ShaderPDXferProcessor(dstTexture, hasMixedSamples, fXfermode)
; | 763 return new ShaderPDXferProcessor(dstTexture, hasMixedSamples, fXfermode)
; |
764 } | 764 } |
765 | 765 |
766 SkASSERT(!dstTexture || !dstTexture->texture()); | 766 SkASSERT(!dstTexture || !dstTexture->texture()); |
767 return new PorterDuffXferProcessor(blendFormula); | 767 return new PorterDuffXferProcessor(blendFormula); |
768 } | 768 } |
(...skipping 28 matching lines...) Expand all Loading... |
797 return; | 797 return; |
798 } | 798 } |
799 } | 799 } |
800 | 800 |
801 bool GrPorterDuffXPFactory::onWillReadDstColor(const GrCaps& caps, | 801 bool GrPorterDuffXPFactory::onWillReadDstColor(const GrCaps& caps, |
802 const GrPipelineOptimizations& op
timizations, | 802 const GrPipelineOptimizations& op
timizations, |
803 bool hasMixedSamples) const { | 803 bool hasMixedSamples) const { |
804 if (caps.shaderCaps()->dualSourceBlendingSupport()) { | 804 if (caps.shaderCaps()->dualSourceBlendingSupport()) { |
805 return false; | 805 return false; |
806 } | 806 } |
807 | 807 |
808 // When we have four channel coverage we always need to read the dst in orde
r to correctly | 808 // When we have four channel coverage we always need to read the dst in orde
r to correctly |
809 // blend. The one exception is when we are using srcover mode and we know th
e input color into | 809 // blend. The one exception is when we are using srcover mode and we know th
e input color into |
810 // the XP. | 810 // the XP. |
811 if (optimizations.fCoveragePOI.isFourChannelOutput()) { | 811 if (optimizations.fCoveragePOI.isFourChannelOutput()) { |
812 if (SkXfermode::kSrcOver_Mode == fXfermode && | 812 if (SkXfermode::kSrcOver_Mode == fXfermode && |
813 kRGBA_GrColorComponentFlags == optimizations.fColorPOI.validFlags()
&& | 813 kRGBA_GrColorComponentFlags == optimizations.fColorPOI.validFlags()
&& |
814 !caps.shaderCaps()->dstReadInShaderSupport()) { | 814 !caps.shaderCaps()->dstReadInShaderSupport()) { |
815 return false; | 815 return false; |
816 } | 816 } |
817 return get_lcd_blend_formula(optimizations.fCoveragePOI, fXfermode).hasS
econdaryOutput(); | 817 return get_lcd_blend_formula(optimizations.fCoveragePOI, fXfermode).hasS
econdaryOutput(); |
818 } | 818 } |
819 // We fallback on the shader XP when the blend formula would use dual source
blending but we | 819 // We fallback on the shader XP when the blend formula would use dual source
blending but we |
820 // don't have support for it. | 820 // don't have support for it. |
821 return get_blend_formula(optimizations.fColorPOI, optimizations.fCoveragePOI
, hasMixedSamples, | 821 return get_blend_formula(optimizations.fColorPOI, optimizations.fCoveragePOI
, hasMixedSamples, |
822 fXfermode).hasSecondaryOutput(); | 822 fXfermode).hasSecondaryOutput(); |
823 } | 823 } |
824 | 824 |
825 GR_DEFINE_XP_FACTORY_TEST(GrPorterDuffXPFactory); | 825 GR_DEFINE_XP_FACTORY_TEST(GrPorterDuffXPFactory); |
826 | 826 |
827 const GrXPFactory* GrPorterDuffXPFactory::TestCreate(GrProcessorTestData* d) { | 827 const GrXPFactory* GrPorterDuffXPFactory::TestCreate(GrProcessorTestData* d) { |
828 SkXfermode::Mode mode = SkXfermode::Mode(d->fRandom->nextULessThan(SkXfermod
e::kLastCoeffMode)); | 828 SkXfermode::Mode mode = SkXfermode::Mode(d->fRandom->nextULessThan(SkXfermod
e::kLastCoeffMode)); |
829 return GrPorterDuffXPFactory::Create(mode); | 829 return GrPorterDuffXPFactory::Create(mode); |
830 } | 830 } |
831 | 831 |
(...skipping 45 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
877 !caps.shaderCaps()->dualSourceBlendingSupport() && | 877 !caps.shaderCaps()->dualSourceBlendingSupport() && |
878 !caps.shaderCaps()->dstReadInShaderSupport()) { | 878 !caps.shaderCaps()->dstReadInShaderSupport()) { |
879 // If we don't have dual source blending or in shader dst reads, we
fall | 879 // If we don't have dual source blending or in shader dst reads, we
fall |
880 // back to this trick for rendering SrcOver LCD text instead of doin
g a | 880 // back to this trick for rendering SrcOver LCD text instead of doin
g a |
881 // dst copy. | 881 // dst copy. |
882 SkASSERT(!dstTexture || !dstTexture->texture()); | 882 SkASSERT(!dstTexture || !dstTexture->texture()); |
883 return PDLCDXferProcessor::Create(SkXfermode::kSrcOver_Mode, optimiz
ations.fColorPOI); | 883 return PDLCDXferProcessor::Create(SkXfermode::kSrcOver_Mode, optimiz
ations.fColorPOI); |
884 } | 884 } |
885 blendFormula = get_lcd_blend_formula(optimizations.fCoveragePOI, SkXferm
ode::kSrcOver_Mode); | 885 blendFormula = get_lcd_blend_formula(optimizations.fCoveragePOI, SkXferm
ode::kSrcOver_Mode); |
886 } else { | 886 } else { |
887 blendFormula = get_blend_formula(optimizations.fColorPOI, optimizations.
fCoveragePOI, | 887 blendFormula = get_blend_formula(optimizations.fColorPOI, optimizations.
fCoveragePOI, |
888 hasMixedSamples, SkXfermode::kSrcOver_M
ode); | 888 hasMixedSamples, SkXfermode::kSrcOver_M
ode); |
889 } | 889 } |
890 | 890 |
891 if (blendFormula.hasSecondaryOutput() && !caps.shaderCaps()->dualSourceBlend
ingSupport()) { | 891 if (blendFormula.hasSecondaryOutput() && !caps.shaderCaps()->dualSourceBlend
ingSupport()) { |
892 return new ShaderPDXferProcessor(dstTexture, hasMixedSamples, SkXfermode
::kSrcOver_Mode); | 892 return new ShaderPDXferProcessor(dstTexture, hasMixedSamples, SkXfermode
::kSrcOver_Mode); |
893 } | 893 } |
894 | 894 |
895 SkASSERT(!dstTexture || !dstTexture->texture()); | 895 SkASSERT(!dstTexture || !dstTexture->texture()); |
896 return new PorterDuffXferProcessor(blendFormula); | 896 return new PorterDuffXferProcessor(blendFormula); |
897 } | 897 } |
898 | 898 |
899 bool GrPorterDuffXPFactory::SrcOverWillNeedDstTexture(const GrCaps& caps, | 899 bool GrPorterDuffXPFactory::SrcOverWillNeedDstTexture(const GrCaps& caps, |
900 const GrPipelineOptimizati
ons& optimizations, | 900 const GrPipelineOptimizati
ons& optimizations, |
901 bool hasMixedSamples) { | 901 bool hasMixedSamples) { |
902 if (caps.shaderCaps()->dstReadInShaderSupport() || | 902 if (caps.shaderCaps()->dstReadInShaderSupport() || |
903 caps.shaderCaps()->dualSourceBlendingSupport()) { | 903 caps.shaderCaps()->dualSourceBlendingSupport()) { |
904 return false; | 904 return false; |
905 } | 905 } |
906 | 906 |
907 // When we have four channel coverage we always need to read the dst in orde
r to correctly | 907 // When we have four channel coverage we always need to read the dst in orde
r to correctly |
908 // blend. The one exception is when we are using srcover mode and we know th
e input color | 908 // blend. The one exception is when we are using srcover mode and we know th
e input color |
909 // into the XP. | 909 // into the XP. |
910 if (optimizations.fCoveragePOI.isFourChannelOutput()) { | 910 if (optimizations.fCoveragePOI.isFourChannelOutput()) { |
911 if (kRGBA_GrColorComponentFlags == optimizations.fColorPOI.validFlags()
&& | 911 if (kRGBA_GrColorComponentFlags == optimizations.fColorPOI.validFlags()
&& |
912 !caps.shaderCaps()->dstReadInShaderSupport()) { | 912 !caps.shaderCaps()->dstReadInShaderSupport()) { |
913 return false; | 913 return false; |
914 } | 914 } |
915 return get_lcd_blend_formula(optimizations.fCoveragePOI, | 915 return get_lcd_blend_formula(optimizations.fCoveragePOI, |
916 SkXfermode::kSrcOver_Mode).hasSecondaryOutp
ut(); | 916 SkXfermode::kSrcOver_Mode).hasSecondaryOutp
ut(); |
917 } | 917 } |
918 // We fallback on the shader XP when the blend formula would use dual source
blending but we | 918 // We fallback on the shader XP when the blend formula would use dual source
blending but we |
919 // don't have support for it. | 919 // don't have support for it. |
920 return get_blend_formula(optimizations.fColorPOI, optimizations.fCoveragePOI
, | 920 return get_blend_formula(optimizations.fColorPOI, optimizations.fCoveragePOI
, |
921 hasMixedSamples, SkXfermode::kSrcOver_Mode).hasSeco
ndaryOutput(); | 921 hasMixedSamples, SkXfermode::kSrcOver_Mode).hasSeco
ndaryOutput(); |
922 } | 922 } |
923 | |
OLD | NEW |