Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(644)

Side by Side Diff: src/gpu/effects/GrCustomXfermode.cpp

Issue 1166513002: Re-enable advanced blend with a blacklist (Closed) Base URL: https://skia.googlesource.com/skia.git@master
Patch Set: rebase Created 5 years, 6 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
1 /* 1 /*
2 * Copyright 2015 Google Inc. 2 * Copyright 2015 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/GrCustomXfermode.h" 8 #include "effects/GrCustomXfermode.h"
9 #include "effects/GrCustomXfermodePriv.h" 9 #include "effects/GrCustomXfermodePriv.h"
10 10
(...skipping 33 matching lines...) Expand 10 before | Expand all | Expand 10 after
44 GR_STATIC_ASSERT(kDifference_GrBlendEquation == SkXfermode::kDifference_Mode + kOffset); 44 GR_STATIC_ASSERT(kDifference_GrBlendEquation == SkXfermode::kDifference_Mode + kOffset);
45 GR_STATIC_ASSERT(kExclusion_GrBlendEquation == SkXfermode::kExclusion_Mode + kOffset); 45 GR_STATIC_ASSERT(kExclusion_GrBlendEquation == SkXfermode::kExclusion_Mode + kOffset);
46 GR_STATIC_ASSERT(kMultiply_GrBlendEquation == SkXfermode::kMultiply_Mode + k Offset); 46 GR_STATIC_ASSERT(kMultiply_GrBlendEquation == SkXfermode::kMultiply_Mode + k Offset);
47 GR_STATIC_ASSERT(kHSLHue_GrBlendEquation == SkXfermode::kHue_Mode + kOffset) ; 47 GR_STATIC_ASSERT(kHSLHue_GrBlendEquation == SkXfermode::kHue_Mode + kOffset) ;
48 GR_STATIC_ASSERT(kHSLSaturation_GrBlendEquation == SkXfermode::kSaturation_M ode + kOffset); 48 GR_STATIC_ASSERT(kHSLSaturation_GrBlendEquation == SkXfermode::kSaturation_M ode + kOffset);
49 GR_STATIC_ASSERT(kHSLColor_GrBlendEquation == SkXfermode::kColor_Mode + kOff set); 49 GR_STATIC_ASSERT(kHSLColor_GrBlendEquation == SkXfermode::kColor_Mode + kOff set);
50 GR_STATIC_ASSERT(kHSLLuminosity_GrBlendEquation == SkXfermode::kLuminosity_M ode + kOffset); 50 GR_STATIC_ASSERT(kHSLLuminosity_GrBlendEquation == SkXfermode::kLuminosity_M ode + kOffset);
51 GR_STATIC_ASSERT(kGrBlendEquationCnt == SkXfermode::kLastMode + 1 + kOffset) ; 51 GR_STATIC_ASSERT(kGrBlendEquationCnt == SkXfermode::kLastMode + 1 + kOffset) ;
52 } 52 }
53 53
54 static bool can_use_hw_blend_equation(GrBlendEquation equation,
55 const GrProcOptInfo& coveragePOI,
56 const GrCaps& caps) {
57 if (!caps.advancedBlendEquationSupport()) {
58 return false;
59 }
60 if (coveragePOI.isFourChannelOutput()) {
61 return false; // LCD coverage must be applied after the blend equation.
62 }
63 if (caps.advancedBlendEquationIsBlacklist(equation)) {
64 return false;
65 }
66 return true;
67 }
68
54 static void hard_light(GrGLFragmentBuilder* fsBuilder, 69 static void hard_light(GrGLFragmentBuilder* fsBuilder,
55 const char* final, 70 const char* final,
56 const char* src, 71 const char* src,
57 const char* dst) { 72 const char* dst) {
58 static const char kComponents[] = {'r', 'g', 'b'}; 73 static const char kComponents[] = {'r', 'g', 'b'};
59 for (size_t i = 0; i < SK_ARRAY_COUNT(kComponents); ++i) { 74 for (size_t i = 0; i < SK_ARRAY_COUNT(kComponents); ++i) {
60 char component = kComponents[i]; 75 char component = kComponents[i];
61 fsBuilder->codeAppendf("if (2.0 * %s.%c <= %s.a) {", src, component, src ); 76 fsBuilder->codeAppendf("if (2.0 * %s.%c <= %s.a) {", src, component, src );
62 fsBuilder->codeAppendf("%s.%c = 2.0 * %s.%c * %s.%c;", 77 fsBuilder->codeAppendf("%s.%c = 2.0 * %s.%c * %s.%c;",
63 final, component, src, component, dst, component) ; 78 final, component, src, component, dst, component) ;
(...skipping 437 matching lines...) Expand 10 before | Expand all | Expand 10 after
501 516
502 return SkNEW_ARGS(GrCustomXferFP, (static_cast<SkXfermode::Mode>(mode), text ures[0])); 517 return SkNEW_ARGS(GrCustomXferFP, (static_cast<SkXfermode::Mode>(mode), text ures[0]));
503 } 518 }
504 519
505 /////////////////////////////////////////////////////////////////////////////// 520 ///////////////////////////////////////////////////////////////////////////////
506 // Xfer Processor 521 // Xfer Processor
507 /////////////////////////////////////////////////////////////////////////////// 522 ///////////////////////////////////////////////////////////////////////////////
508 523
509 class CustomXP : public GrXferProcessor { 524 class CustomXP : public GrXferProcessor {
510 public: 525 public:
511 static GrXferProcessor* Create(SkXfermode::Mode mode, const DstTexture* dstT exture, 526 CustomXP(SkXfermode::Mode mode, GrBlendEquation hwBlendEquation)
512 bool willReadDstColor) { 527 : fMode(mode),
513 if (!GrCustomXfermode::IsSupportedMode(mode)) { 528 fHWBlendEquation(hwBlendEquation) {
514 return NULL; 529 this->initClassID<CustomXP>();
515 } else {
516 return SkNEW_ARGS(CustomXP, (mode, dstTexture, willReadDstColor));
517 }
518 } 530 }
519 531
520 ~CustomXP() override {}; 532 CustomXP(SkXfermode::Mode mode, const DstTexture* dstTexture)
533 : INHERITED(dstTexture, true),
534 fMode(mode),
535 fHWBlendEquation(static_cast<GrBlendEquation>(-1)) {
536 this->initClassID<CustomXP>();
537 }
521 538
522 const char* name() const override { return "Custom Xfermode"; } 539 const char* name() const override { return "Custom Xfermode"; }
523 540
524 GrGLXferProcessor* createGLInstance() const override; 541 GrGLXferProcessor* createGLInstance() const override;
525 542
526 bool hasSecondaryOutput() const override { return false; } 543 bool hasSecondaryOutput() const override { return false; }
527 544
528 SkXfermode::Mode mode() const { return fMode; } 545 SkXfermode::Mode mode() const { return fMode; }
529 bool hasHWBlendEquation() const { return -1 != static_cast<int>(fHWBlendEqua tion); } 546 bool hasHWBlendEquation() const { return -1 != static_cast<int>(fHWBlendEqua tion); }
530 547
531 GrBlendEquation hwBlendEquation() const { 548 GrBlendEquation hwBlendEquation() const {
532 SkASSERT(this->hasHWBlendEquation()); 549 SkASSERT(this->hasHWBlendEquation());
533 return fHWBlendEquation; 550 return fHWBlendEquation;
534 } 551 }
535 552
536 private: 553 private:
537 CustomXP(SkXfermode::Mode mode, const DstTexture*, bool willReadDstColor);
538
539 GrXferProcessor::OptFlags onGetOptimizations(const GrProcOptInfo& colorPOI, 554 GrXferProcessor::OptFlags onGetOptimizations(const GrProcOptInfo& colorPOI,
540 const GrProcOptInfo& coveragePO I, 555 const GrProcOptInfo& coveragePO I,
541 bool doesStencilWrite, 556 bool doesStencilWrite,
542 GrColor* overrideColor, 557 GrColor* overrideColor,
543 const GrCaps& caps) override; 558 const GrCaps& caps) override;
544 559
545 void onGetGLProcessorKey(const GrGLSLCaps& caps, GrProcessorKeyBuilder* b) c onst override; 560 void onGetGLProcessorKey(const GrGLSLCaps& caps, GrProcessorKeyBuilder* b) c onst override;
546 561
547 bool onWillNeedXferBarrier(const GrRenderTarget* rt, 562 bool onWillNeedXferBarrier(const GrRenderTarget* rt,
548 const GrCaps& caps, 563 const GrCaps& caps,
549 GrXferBarrierType* outBarrierType) const override ; 564 GrXferBarrierType* outBarrierType) const override ;
550 565
551 void onGetBlendInfo(BlendInfo*) const override; 566 void onGetBlendInfo(BlendInfo*) const override;
552 567
553 bool onIsEqual(const GrXferProcessor& xpBase) const override; 568 bool onIsEqual(const GrXferProcessor& xpBase) const override;
554 569
555 SkXfermode::Mode fMode; 570 const SkXfermode::Mode fMode;
556 GrBlendEquation fHWBlendEquation; 571 const GrBlendEquation fHWBlendEquation;
557 572
558 typedef GrXferProcessor INHERITED; 573 typedef GrXferProcessor INHERITED;
559 }; 574 };
560 575
561 /////////////////////////////////////////////////////////////////////////////// 576 ///////////////////////////////////////////////////////////////////////////////
562 577
563 GrXPFactory* GrCustomXfermode::CreateXPFactory(SkXfermode::Mode mode) { 578 GrXPFactory* GrCustomXfermode::CreateXPFactory(SkXfermode::Mode mode) {
564 if (!GrCustomXfermode::IsSupportedMode(mode)) { 579 if (!GrCustomXfermode::IsSupportedMode(mode)) {
565 return NULL; 580 return NULL;
566 } else { 581 } else {
(...skipping 52 matching lines...) Expand 10 before | Expand all | Expand 10 after
619 } 634 }
620 } 635 }
621 636
622 void onSetData(const GrGLProgramDataManager&, const GrXferProcessor&) overri de {} 637 void onSetData(const GrGLProgramDataManager&, const GrXferProcessor&) overri de {}
623 638
624 typedef GrGLFragmentProcessor INHERITED; 639 typedef GrGLFragmentProcessor INHERITED;
625 }; 640 };
626 641
627 /////////////////////////////////////////////////////////////////////////////// 642 ///////////////////////////////////////////////////////////////////////////////
628 643
629 CustomXP::CustomXP(SkXfermode::Mode mode, const DstTexture* dstTexture, bool wil lReadDstColor)
630 : INHERITED(dstTexture, willReadDstColor),
631 fMode(mode),
632 fHWBlendEquation(static_cast<GrBlendEquation>(-1)) {
633 this->initClassID<CustomXP>();
634 }
635
636 void CustomXP::onGetGLProcessorKey(const GrGLSLCaps& caps, GrProcessorKeyBuilder * b) const { 644 void CustomXP::onGetGLProcessorKey(const GrGLSLCaps& caps, GrProcessorKeyBuilder * b) const {
637 GLCustomXP::GenKey(*this, caps, b); 645 GLCustomXP::GenKey(*this, caps, b);
638 } 646 }
639 647
640 GrGLXferProcessor* CustomXP::createGLInstance() const { 648 GrGLXferProcessor* CustomXP::createGLInstance() const {
641 SkASSERT(this->willReadDstColor() != this->hasHWBlendEquation()); 649 SkASSERT(this->willReadDstColor() != this->hasHWBlendEquation());
642 return SkNEW_ARGS(GLCustomXP, (*this)); 650 return SkNEW_ARGS(GLCustomXP, (*this));
643 } 651 }
644 652
645 bool CustomXP::onIsEqual(const GrXferProcessor& other) const { 653 bool CustomXP::onIsEqual(const GrXferProcessor& other) const {
(...skipping 102 matching lines...) Expand 10 before | Expand all | Expand 10 after
748 = blend(f*Sa, Da) 756 = blend(f*Sa, Da)
749 */ 757 */
750 758
751 OptFlags flags = kNone_Opt; 759 OptFlags flags = kNone_Opt;
752 if (colorPOI.allStagesMultiplyInput()) { 760 if (colorPOI.allStagesMultiplyInput()) {
753 flags |= kCanTweakAlphaForCoverage_OptFlag; 761 flags |= kCanTweakAlphaForCoverage_OptFlag;
754 } 762 }
755 if (coveragePOI.isSolidWhite()) { 763 if (coveragePOI.isSolidWhite()) {
756 flags |= kIgnoreCoverage_OptFlag; 764 flags |= kIgnoreCoverage_OptFlag;
757 } 765 }
758 if (caps.advancedBlendEquationSupport() && !coveragePOI.isFourChannelOutput( )) {
759 // This blend mode can be implemented in hardware.
760 fHWBlendEquation = hw_blend_equation(fMode);
761 }
762 return flags; 766 return flags;
763 } 767 }
764 768
765 bool CustomXP::onWillNeedXferBarrier(const GrRenderTarget* rt, 769 bool CustomXP::onWillNeedXferBarrier(const GrRenderTarget* rt,
766 const GrCaps& caps, 770 const GrCaps& caps,
767 GrXferBarrierType* outBarrierType) const { 771 GrXferBarrierType* outBarrierType) const {
768 if (this->hasHWBlendEquation() && !caps.advancedCoherentBlendEquationSupport ()) { 772 if (this->hasHWBlendEquation() && !caps.advancedCoherentBlendEquationSupport ()) {
769 *outBarrierType = kBlend_GrXferBarrierType; 773 *outBarrierType = kBlend_GrXferBarrierType;
770 return true; 774 return true;
771 } 775 }
772 return false; 776 return false;
773 } 777 }
774 778
775 void CustomXP::onGetBlendInfo(BlendInfo* blendInfo) const { 779 void CustomXP::onGetBlendInfo(BlendInfo* blendInfo) const {
776 if (this->hasHWBlendEquation()) { 780 if (this->hasHWBlendEquation()) {
777 blendInfo->fEquation = this->hwBlendEquation(); 781 blendInfo->fEquation = this->hwBlendEquation();
778 } 782 }
779 } 783 }
780 784
781 /////////////////////////////////////////////////////////////////////////////// 785 ///////////////////////////////////////////////////////////////////////////////
782 786
783 GrCustomXPFactory::GrCustomXPFactory(SkXfermode::Mode mode) 787 GrCustomXPFactory::GrCustomXPFactory(SkXfermode::Mode mode)
784 : fMode(mode) { 788 : fMode(mode),
789 fHWBlendEquation(hw_blend_equation(mode)) {
790 SkASSERT(GrCustomXfermode::IsSupportedMode(fMode));
785 this->initClassID<GrCustomXPFactory>(); 791 this->initClassID<GrCustomXPFactory>();
786 } 792 }
787 793
788 GrXferProcessor* 794 GrXferProcessor*
789 GrCustomXPFactory::onCreateXferProcessor(const GrCaps& caps, 795 GrCustomXPFactory::onCreateXferProcessor(const GrCaps& caps,
790 const GrProcOptInfo& colorPOI, 796 const GrProcOptInfo& colorPOI,
791 const GrProcOptInfo& coveragePOI, 797 const GrProcOptInfo& coveragePOI,
792 const DstTexture* dstTexture) const { 798 const DstTexture* dstTexture) const {
793 return CustomXP::Create(fMode, dstTexture, this->willReadDstColor(caps, colo rPOI, coveragePOI)); 799 if (can_use_hw_blend_equation(fHWBlendEquation, coveragePOI, caps)) {
800 SkASSERT(!dstTexture || !dstTexture->texture());
801 return SkNEW_ARGS(CustomXP, (fMode, fHWBlendEquation));
802 }
803 return SkNEW_ARGS(CustomXP, (fMode, dstTexture));
794 } 804 }
795 805
796 bool GrCustomXPFactory::willReadDstColor(const GrCaps& caps, 806 bool GrCustomXPFactory::willReadDstColor(const GrCaps& caps,
797 const GrProcOptInfo& colorPOI, 807 const GrProcOptInfo& colorPOI,
798 const GrProcOptInfo& coveragePOI) const { 808 const GrProcOptInfo& coveragePOI) const {
799 if (!caps.advancedBlendEquationSupport()) { 809 return !can_use_hw_blend_equation(fHWBlendEquation, coveragePOI, caps);
800 // No hardware support for advanced blend equations; we will need to do it in the shader.
801 return true;
802 }
803 if (coveragePOI.isFourChannelOutput()) {
804 // Advanced blend equations can't tweak alpha for RGB coverage.
805 return true;
806 }
807 return false;
808 } 810 }
809 811
810 void GrCustomXPFactory::getInvariantBlendedColor(const GrProcOptInfo& colorPOI, 812 void GrCustomXPFactory::getInvariantBlendedColor(const GrProcOptInfo& colorPOI,
811 InvariantBlendedColor* blendedC olor) const { 813 InvariantBlendedColor* blendedC olor) const {
812 blendedColor->fWillBlendWithDst = true; 814 blendedColor->fWillBlendWithDst = true;
813 blendedColor->fKnownColorFlags = kNone_GrColorComponentFlags; 815 blendedColor->fKnownColorFlags = kNone_GrColorComponentFlags;
814 } 816 }
815 817
816 GR_DEFINE_XP_FACTORY_TEST(GrCustomXPFactory); 818 GR_DEFINE_XP_FACTORY_TEST(GrCustomXPFactory);
817 GrXPFactory* GrCustomXPFactory::TestCreate(SkRandom* rand, 819 GrXPFactory* GrCustomXPFactory::TestCreate(SkRandom* rand,
818 GrContext*, 820 GrContext*,
819 const GrCaps&, 821 const GrCaps&,
820 GrTexture*[]) { 822 GrTexture*[]) {
821 int mode = rand->nextRangeU(SkXfermode::kLastCoeffMode + 1, SkXfermode::kLas tSeparableMode); 823 int mode = rand->nextRangeU(SkXfermode::kLastCoeffMode + 1, SkXfermode::kLas tSeparableMode);
822 824
823 return SkNEW_ARGS(GrCustomXPFactory, (static_cast<SkXfermode::Mode>(mode))); 825 return SkNEW_ARGS(GrCustomXPFactory, (static_cast<SkXfermode::Mode>(mode)));
824 } 826 }
825 827
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698