| OLD | NEW |
| 1 /* | 1 /* |
| 2 * Copyright 2006 The Android Open Source Project | 2 * Copyright 2006 The Android Open Source Project |
| 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 "SkBlurMaskFilter.h" | 8 #include "SkBlurMaskFilter.h" |
| 9 #include "SkBlurMask.h" | 9 #include "SkBlurMask.h" |
| 10 #include "SkGpuBlurUtils.h" | 10 #include "SkGpuBlurUtils.h" |
| (...skipping 589 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 600 #if SK_SUPPORT_GPU | 600 #if SK_SUPPORT_GPU |
| 601 | 601 |
| 602 class GrGLRectBlurEffect; | 602 class GrGLRectBlurEffect; |
| 603 | 603 |
| 604 class GrRectBlurEffect : public GrFragmentProcessor { | 604 class GrRectBlurEffect : public GrFragmentProcessor { |
| 605 public: | 605 public: |
| 606 ~GrRectBlurEffect() override { } | 606 ~GrRectBlurEffect() override { } |
| 607 | 607 |
| 608 const char* name() const override { return "RectBlur"; } | 608 const char* name() const override { return "RectBlur"; } |
| 609 | 609 |
| 610 static GrFragmentProcessor* Create(GrTextureProvider *textureProvider, | 610 static sk_sp<GrFragmentProcessor> Make(GrTextureProvider *textureProvider, |
| 611 const SkRect& rect, float sigma) { | 611 const SkRect& rect, float sigma) { |
| 612 int doubleProfileSize = SkScalarCeilToInt(12*sigma); | 612 int doubleProfileSize = SkScalarCeilToInt(12*sigma); |
| 613 | 613 |
| 614 if (doubleProfileSize >= rect.width() || doubleProfileSize >= rect.heigh
t()) { | 614 if (doubleProfileSize >= rect.width() || doubleProfileSize >= rect.heigh
t()) { |
| 615 // if the blur sigma is too large so the gaussian overlaps the whole | 615 // if the blur sigma is too large so the gaussian overlaps the whole |
| 616 // rect in either direction, fall back to CPU path for now. | 616 // rect in either direction, fall back to CPU path for now. |
| 617 return nullptr; | 617 return nullptr; |
| 618 } | 618 } |
| 619 | 619 |
| 620 SkAutoTUnref<GrTexture> blurProfile(CreateBlurProfileTexture(textureProv
ider, sigma)); | 620 SkAutoTUnref<GrTexture> blurProfile(CreateBlurProfileTexture(textureProv
ider, sigma)); |
| 621 if (!blurProfile) { | 621 if (!blurProfile) { |
| 622 return nullptr; | 622 return nullptr; |
| 623 } | 623 } |
| 624 // in OpenGL ES, mediump floats have a minimum range of 2^14. If we have
coordinates bigger | 624 // in OpenGL ES, mediump floats have a minimum range of 2^14. If we have
coordinates bigger |
| 625 // than that, the shader math will end up with infinities and result in
the blur effect not | 625 // than that, the shader math will end up with infinities and result in
the blur effect not |
| 626 // working correctly. To avoid this, we switch into highp when the coord
inates are too big. | 626 // working correctly. To avoid this, we switch into highp when the coord
inates are too big. |
| 627 // As 2^14 is the minimum range but the actual range can be bigger, we m
ight end up | 627 // As 2^14 is the minimum range but the actual range can be bigger, we m
ight end up |
| 628 // switching to highp sooner than strictly necessary, but most devices t
hat have a bigger | 628 // switching to highp sooner than strictly necessary, but most devices t
hat have a bigger |
| 629 // range for mediump also have mediump being exactly the same as highp (
e.g. all non-OpenGL | 629 // range for mediump also have mediump being exactly the same as highp (
e.g. all non-OpenGL |
| 630 // ES devices), and thus incur no additional penalty for the switch. | 630 // ES devices), and thus incur no additional penalty for the switch. |
| 631 static const SkScalar kMAX_BLUR_COORD = SkIntToScalar(16000); | 631 static const SkScalar kMAX_BLUR_COORD = SkIntToScalar(16000); |
| 632 GrSLPrecision precision; | 632 GrSLPrecision precision; |
| 633 if (SkScalarAbs(rect.top()) > kMAX_BLUR_COORD || | 633 if (SkScalarAbs(rect.top()) > kMAX_BLUR_COORD || |
| 634 SkScalarAbs(rect.left()) > kMAX_BLUR_COORD || | 634 SkScalarAbs(rect.left()) > kMAX_BLUR_COORD || |
| 635 SkScalarAbs(rect.bottom()) > kMAX_BLUR_COORD || | 635 SkScalarAbs(rect.bottom()) > kMAX_BLUR_COORD || |
| 636 SkScalarAbs(rect.right()) > kMAX_BLUR_COORD || | 636 SkScalarAbs(rect.right()) > kMAX_BLUR_COORD || |
| 637 SkScalarAbs(rect.width()) > kMAX_BLUR_COORD || | 637 SkScalarAbs(rect.width()) > kMAX_BLUR_COORD || |
| 638 SkScalarAbs(rect.height()) > kMAX_BLUR_COORD) { | 638 SkScalarAbs(rect.height()) > kMAX_BLUR_COORD) { |
| 639 precision = kHigh_GrSLPrecision; | 639 precision = kHigh_GrSLPrecision; |
| 640 } | 640 } else { |
| 641 else { | |
| 642 precision = kDefault_GrSLPrecision; | 641 precision = kDefault_GrSLPrecision; |
| 643 } | 642 } |
| 644 return new GrRectBlurEffect(rect, sigma, blurProfile, precision); | 643 return sk_sp<GrFragmentProcessor>( |
| 644 new GrRectBlurEffect(rect, sigma, blurProfile, precision)); |
| 645 } | 645 } |
| 646 | 646 |
| 647 const SkRect& getRect() const { return fRect; } | 647 const SkRect& getRect() const { return fRect; } |
| 648 float getSigma() const { return fSigma; } | 648 float getSigma() const { return fSigma; } |
| 649 GrSLPrecision precision() const { return fPrecision; } | 649 GrSLPrecision precision() const { return fPrecision; } |
| 650 | 650 |
| 651 private: | 651 private: |
| 652 GrRectBlurEffect(const SkRect& rect, float sigma, GrTexture *blurProfile, | 652 GrRectBlurEffect(const SkRect& rect, float sigma, GrTexture *blurProfile, |
| 653 GrSLPrecision fPrecision); | 653 GrSLPrecision fPrecision); |
| 654 | 654 |
| (...skipping 179 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 834 const GrRectBlurEffect& s = sBase.cast<GrRectBlurEffect>(); | 834 const GrRectBlurEffect& s = sBase.cast<GrRectBlurEffect>(); |
| 835 return this->getSigma() == s.getSigma() && this->getRect() == s.getRect(); | 835 return this->getSigma() == s.getSigma() && this->getRect() == s.getRect(); |
| 836 } | 836 } |
| 837 | 837 |
| 838 void GrRectBlurEffect::onComputeInvariantOutput(GrInvariantOutput* inout) const
{ | 838 void GrRectBlurEffect::onComputeInvariantOutput(GrInvariantOutput* inout) const
{ |
| 839 inout->mulByUnknownSingleComponent(); | 839 inout->mulByUnknownSingleComponent(); |
| 840 } | 840 } |
| 841 | 841 |
| 842 GR_DEFINE_FRAGMENT_PROCESSOR_TEST(GrRectBlurEffect); | 842 GR_DEFINE_FRAGMENT_PROCESSOR_TEST(GrRectBlurEffect); |
| 843 | 843 |
| 844 const GrFragmentProcessor* GrRectBlurEffect::TestCreate(GrProcessorTestData* d)
{ | 844 sk_sp<GrFragmentProcessor> GrRectBlurEffect::TestCreate(GrProcessorTestData* d)
{ |
| 845 float sigma = d->fRandom->nextRangeF(3,8); | 845 float sigma = d->fRandom->nextRangeF(3,8); |
| 846 float width = d->fRandom->nextRangeF(200,300); | 846 float width = d->fRandom->nextRangeF(200,300); |
| 847 float height = d->fRandom->nextRangeF(200,300); | 847 float height = d->fRandom->nextRangeF(200,300); |
| 848 return GrRectBlurEffect::Create(d->fContext->textureProvider(), SkRect::Make
WH(width, height), | 848 return GrRectBlurEffect::Make(d->fContext->textureProvider(), SkRect::MakeWH
(width, height), |
| 849 sigma); | 849 sigma); |
| 850 } | 850 } |
| 851 | 851 |
| 852 | 852 |
| 853 bool SkBlurMaskFilterImpl::directFilterMaskGPU(GrTextureProvider* texProvider, | 853 bool SkBlurMaskFilterImpl::directFilterMaskGPU(GrTextureProvider* texProvider, |
| 854 GrDrawContext* drawContext, | 854 GrDrawContext* drawContext, |
| 855 GrPaint* grp, | 855 GrPaint* grp, |
| 856 const GrClip& clip, | 856 const GrClip& clip, |
| 857 const SkMatrix& viewMatrix, | 857 const SkMatrix& viewMatrix, |
| 858 const SkStrokeRec& strokeRec, | 858 const SkStrokeRec& strokeRec, |
| 859 const SkPath& path) const { | 859 const SkPath& path) const { |
| 860 SkASSERT(drawContext); | 860 SkASSERT(drawContext); |
| 861 | 861 |
| 862 if (fBlurStyle != kNormal_SkBlurStyle) { | 862 if (fBlurStyle != kNormal_SkBlurStyle) { |
| 863 return false; | 863 return false; |
| 864 } | 864 } |
| 865 | 865 |
| 866 // TODO: we could handle blurred stroked circles | 866 // TODO: we could handle blurred stroked circles |
| 867 if (!strokeRec.isFillStyle()) { | 867 if (!strokeRec.isFillStyle()) { |
| 868 return false; | 868 return false; |
| 869 } | 869 } |
| 870 | 870 |
| 871 SkScalar xformedSigma = this->computeXformedSigma(viewMatrix); | 871 SkScalar xformedSigma = this->computeXformedSigma(viewMatrix); |
| 872 | 872 |
| 873 SkAutoTUnref<const GrFragmentProcessor> fp; | 873 sk_sp<GrFragmentProcessor> fp; |
| 874 | 874 |
| 875 SkRect rect; | 875 SkRect rect; |
| 876 if (path.isRect(&rect)) { | 876 if (path.isRect(&rect)) { |
| 877 int pad = SkScalarCeilToInt(6*xformedSigma)/2; | 877 int pad = SkScalarCeilToInt(6*xformedSigma)/2; |
| 878 rect.outset(SkIntToScalar(pad), SkIntToScalar(pad)); | 878 rect.outset(SkIntToScalar(pad), SkIntToScalar(pad)); |
| 879 | 879 |
| 880 fp.reset(GrRectBlurEffect::Create(texProvider, rect, xformedSigma)); | 880 fp = GrRectBlurEffect::Make(texProvider, rect, xformedSigma); |
| 881 } else if (path.isOval(&rect) && SkScalarNearlyEqual(rect.width(), rect.heig
ht())) { | 881 } else if (path.isOval(&rect) && SkScalarNearlyEqual(rect.width(), rect.heig
ht())) { |
| 882 fp.reset(GrCircleBlurFragmentProcessor::Create(texProvider, rect, xforme
dSigma)); | 882 fp = GrCircleBlurFragmentProcessor::Make(texProvider, rect, xformedSigma
); |
| 883 | 883 |
| 884 // expand the rect for the coverage geometry | 884 // expand the rect for the coverage geometry |
| 885 int pad = SkScalarCeilToInt(6*xformedSigma)/2; | 885 int pad = SkScalarCeilToInt(6*xformedSigma)/2; |
| 886 rect.outset(SkIntToScalar(pad), SkIntToScalar(pad)); | 886 rect.outset(SkIntToScalar(pad), SkIntToScalar(pad)); |
| 887 } else { | 887 } else { |
| 888 return false; | 888 return false; |
| 889 } | 889 } |
| 890 | 890 |
| 891 if (!fp) { | 891 if (!fp) { |
| 892 return false; | 892 return false; |
| 893 } | 893 } |
| 894 | 894 |
| 895 grp->addCoverageFragmentProcessor(fp); | 895 grp->addCoverageFragmentProcessor(std::move(fp)); |
| 896 | 896 |
| 897 SkMatrix inverse; | 897 SkMatrix inverse; |
| 898 if (!viewMatrix.invert(&inverse)) { | 898 if (!viewMatrix.invert(&inverse)) { |
| 899 return false; | 899 return false; |
| 900 } | 900 } |
| 901 | 901 |
| 902 drawContext->fillRectWithLocalMatrix(clip, *grp, SkMatrix::I(), rect, invers
e); | 902 drawContext->fillRectWithLocalMatrix(clip, *grp, SkMatrix::I(), rect, invers
e); |
| 903 return true; | 903 return true; |
| 904 } | 904 } |
| 905 | 905 |
| 906 ////////////////////////////////////////////////////////////////////////////// | 906 ////////////////////////////////////////////////////////////////////////////// |
| 907 | 907 |
| 908 class GrRRectBlurEffect : public GrFragmentProcessor { | 908 class GrRRectBlurEffect : public GrFragmentProcessor { |
| 909 public: | 909 public: |
| 910 | 910 |
| 911 static const GrFragmentProcessor* Create(GrTextureProvider*, float sigma, co
nst SkRRect&); | 911 static sk_sp<GrFragmentProcessor> Make(GrTextureProvider*, float sigma, cons
t SkRRect&); |
| 912 | 912 |
| 913 virtual ~GrRRectBlurEffect() {}; | 913 virtual ~GrRRectBlurEffect() {}; |
| 914 const char* name() const override { return "GrRRectBlur"; } | 914 const char* name() const override { return "GrRRectBlur"; } |
| 915 | 915 |
| 916 const SkRRect& getRRect() const { return fRRect; } | 916 const SkRRect& getRRect() const { return fRRect; } |
| 917 float getSigma() const { return fSigma; } | 917 float getSigma() const { return fSigma; } |
| 918 | 918 |
| 919 private: | 919 private: |
| 920 GrGLSLFragmentProcessor* onCreateGLSLInstance() const override; | 920 GrGLSLFragmentProcessor* onCreateGLSLInstance() const override; |
| 921 | 921 |
| 922 GrRRectBlurEffect(float sigma, const SkRRect&, GrTexture* profileTexture); | 922 GrRRectBlurEffect(float sigma, const SkRRect&, GrTexture* profileTexture); |
| 923 | 923 |
| 924 virtual void onGetGLSLProcessorKey(const GrGLSLCaps& caps, | 924 virtual void onGetGLSLProcessorKey(const GrGLSLCaps& caps, |
| 925 GrProcessorKeyBuilder* b) const override; | 925 GrProcessorKeyBuilder* b) const override; |
| 926 | 926 |
| 927 bool onIsEqual(const GrFragmentProcessor& other) const override; | 927 bool onIsEqual(const GrFragmentProcessor& other) const override; |
| 928 | 928 |
| 929 void onComputeInvariantOutput(GrInvariantOutput* inout) const override; | 929 void onComputeInvariantOutput(GrInvariantOutput* inout) const override; |
| 930 | 930 |
| 931 SkRRect fRRect; | 931 SkRRect fRRect; |
| 932 float fSigma; | 932 float fSigma; |
| 933 GrTextureAccess fNinePatchAccess; | 933 GrTextureAccess fNinePatchAccess; |
| 934 | 934 |
| 935 GR_DECLARE_FRAGMENT_PROCESSOR_TEST; | 935 GR_DECLARE_FRAGMENT_PROCESSOR_TEST; |
| 936 | 936 |
| 937 typedef GrFragmentProcessor INHERITED; | 937 typedef GrFragmentProcessor INHERITED; |
| 938 }; | 938 }; |
| 939 | 939 |
| 940 | 940 |
| 941 const GrFragmentProcessor* GrRRectBlurEffect::Create(GrTextureProvider* texProvi
der, float sigma, | 941 sk_sp<GrFragmentProcessor> GrRRectBlurEffect::Make(GrTextureProvider* texProvide
r, float sigma, |
| 942 const SkRRect& rrect) { | 942 const SkRRect& rrect) { |
| 943 if (rrect.isCircle()) { | 943 if (rrect.isCircle()) { |
| 944 return GrCircleBlurFragmentProcessor::Create(texProvider, rrect.rect(),
sigma); | 944 return GrCircleBlurFragmentProcessor::Make(texProvider, rrect.rect(), si
gma); |
| 945 } | 945 } |
| 946 | 946 |
| 947 if (!rrect.isSimpleCircular()) { | 947 if (!rrect.isSimpleCircular()) { |
| 948 return nullptr; | 948 return nullptr; |
| 949 } | 949 } |
| 950 | 950 |
| 951 // Make sure we can successfully ninepatch this rrect -- the blur sigma has
to be | 951 // Make sure we can successfully ninepatch this rrect -- the blur sigma has
to be |
| 952 // sufficiently small relative to both the size of the corner radius and the | 952 // sufficiently small relative to both the size of the corner radius and the |
| 953 // width (and height) of the rrect. | 953 // width (and height) of the rrect. |
| 954 | 954 |
| (...skipping 52 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1007 texDesc.fIsMipMapped = false; | 1007 texDesc.fIsMipMapped = false; |
| 1008 | 1008 |
| 1009 blurNinePatchTexture.reset( | 1009 blurNinePatchTexture.reset( |
| 1010 texProvider->createTexture(texDesc, SkBudgeted::kYes , blurredMask.f
Image, 0)); | 1010 texProvider->createTexture(texDesc, SkBudgeted::kYes , blurredMask.f
Image, 0)); |
| 1011 SkMask::FreeImage(blurredMask.fImage); | 1011 SkMask::FreeImage(blurredMask.fImage); |
| 1012 if (!blurNinePatchTexture) { | 1012 if (!blurNinePatchTexture) { |
| 1013 return nullptr; | 1013 return nullptr; |
| 1014 } | 1014 } |
| 1015 texProvider->assignUniqueKeyToTexture(key, blurNinePatchTexture); | 1015 texProvider->assignUniqueKeyToTexture(key, blurNinePatchTexture); |
| 1016 } | 1016 } |
| 1017 return new GrRRectBlurEffect(sigma, rrect, blurNinePatchTexture); | 1017 return sk_sp<GrFragmentProcessor>(new GrRRectBlurEffect(sigma, rrect, blurNi
nePatchTexture)); |
| 1018 } | 1018 } |
| 1019 | 1019 |
| 1020 void GrRRectBlurEffect::onComputeInvariantOutput(GrInvariantOutput* inout) const
{ | 1020 void GrRRectBlurEffect::onComputeInvariantOutput(GrInvariantOutput* inout) const
{ |
| 1021 inout->mulByUnknownSingleComponent(); | 1021 inout->mulByUnknownSingleComponent(); |
| 1022 } | 1022 } |
| 1023 | 1023 |
| 1024 GrRRectBlurEffect::GrRRectBlurEffect(float sigma, const SkRRect& rrect, GrTextur
e *ninePatchTexture) | 1024 GrRRectBlurEffect::GrRRectBlurEffect(float sigma, const SkRRect& rrect, GrTextur
e *ninePatchTexture) |
| 1025 : fRRect(rrect), | 1025 : fRRect(rrect), |
| 1026 fSigma(sigma), | 1026 fSigma(sigma), |
| 1027 fNinePatchAccess(ninePatchTexture) { | 1027 fNinePatchAccess(ninePatchTexture) { |
| 1028 this->initClassID<GrRRectBlurEffect>(); | 1028 this->initClassID<GrRRectBlurEffect>(); |
| 1029 this->addTextureAccess(&fNinePatchAccess); | 1029 this->addTextureAccess(&fNinePatchAccess); |
| 1030 this->setWillReadFragmentPosition(); | 1030 this->setWillReadFragmentPosition(); |
| 1031 } | 1031 } |
| 1032 | 1032 |
| 1033 bool GrRRectBlurEffect::onIsEqual(const GrFragmentProcessor& other) const { | 1033 bool GrRRectBlurEffect::onIsEqual(const GrFragmentProcessor& other) const { |
| 1034 const GrRRectBlurEffect& rrbe = other.cast<GrRRectBlurEffect>(); | 1034 const GrRRectBlurEffect& rrbe = other.cast<GrRRectBlurEffect>(); |
| 1035 return fRRect.getSimpleRadii().fX == rrbe.fRRect.getSimpleRadii().fX && | 1035 return fRRect.getSimpleRadii().fX == rrbe.fRRect.getSimpleRadii().fX && |
| 1036 fSigma == rrbe.fSigma && | 1036 fSigma == rrbe.fSigma && |
| 1037 fRRect.rect() == rrbe.fRRect.rect(); | 1037 fRRect.rect() == rrbe.fRRect.rect(); |
| 1038 } | 1038 } |
| 1039 | 1039 |
| 1040 ////////////////////////////////////////////////////////////////////////////// | 1040 ////////////////////////////////////////////////////////////////////////////// |
| 1041 | 1041 |
| 1042 GR_DEFINE_FRAGMENT_PROCESSOR_TEST(GrRRectBlurEffect); | 1042 GR_DEFINE_FRAGMENT_PROCESSOR_TEST(GrRRectBlurEffect); |
| 1043 | 1043 |
| 1044 const GrFragmentProcessor* GrRRectBlurEffect::TestCreate(GrProcessorTestData* d)
{ | 1044 sk_sp<GrFragmentProcessor> GrRRectBlurEffect::TestCreate(GrProcessorTestData* d)
{ |
| 1045 SkScalar w = d->fRandom->nextRangeScalar(100.f, 1000.f); | 1045 SkScalar w = d->fRandom->nextRangeScalar(100.f, 1000.f); |
| 1046 SkScalar h = d->fRandom->nextRangeScalar(100.f, 1000.f); | 1046 SkScalar h = d->fRandom->nextRangeScalar(100.f, 1000.f); |
| 1047 SkScalar r = d->fRandom->nextRangeF(1.f, 9.f); | 1047 SkScalar r = d->fRandom->nextRangeF(1.f, 9.f); |
| 1048 SkScalar sigma = d->fRandom->nextRangeF(1.f,10.f); | 1048 SkScalar sigma = d->fRandom->nextRangeF(1.f,10.f); |
| 1049 SkRRect rrect; | 1049 SkRRect rrect; |
| 1050 rrect.setRectXY(SkRect::MakeWH(w, h), r, r); | 1050 rrect.setRectXY(SkRect::MakeWH(w, h), r, r); |
| 1051 return GrRRectBlurEffect::Create(d->fContext->textureProvider(), sigma, rrec
t); | 1051 return GrRRectBlurEffect::Make(d->fContext->textureProvider(), sigma, rrect)
; |
| 1052 } | 1052 } |
| 1053 | 1053 |
| 1054 ////////////////////////////////////////////////////////////////////////////// | 1054 ////////////////////////////////////////////////////////////////////////////// |
| 1055 | 1055 |
| 1056 class GrGLRRectBlurEffect : public GrGLSLFragmentProcessor { | 1056 class GrGLRRectBlurEffect : public GrGLSLFragmentProcessor { |
| 1057 public: | 1057 public: |
| 1058 void emitCode(EmitArgs&) override; | 1058 void emitCode(EmitArgs&) override; |
| 1059 | 1059 |
| 1060 protected: | 1060 protected: |
| 1061 void onSetData(const GrGLSLProgramDataManager&, const GrProcessor&) override
; | 1061 void onSetData(const GrGLSLProgramDataManager&, const GrProcessor&) override
; |
| (...skipping 105 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1167 if (!strokeRec.isFillStyle()) { | 1167 if (!strokeRec.isFillStyle()) { |
| 1168 return false; | 1168 return false; |
| 1169 } | 1169 } |
| 1170 | 1170 |
| 1171 SkScalar xformedSigma = this->computeXformedSigma(viewMatrix); | 1171 SkScalar xformedSigma = this->computeXformedSigma(viewMatrix); |
| 1172 float extra=3.f*SkScalarCeilToScalar(xformedSigma-1/6.0f); | 1172 float extra=3.f*SkScalarCeilToScalar(xformedSigma-1/6.0f); |
| 1173 | 1173 |
| 1174 SkRect proxyRect = rrect.rect(); | 1174 SkRect proxyRect = rrect.rect(); |
| 1175 proxyRect.outset(extra, extra); | 1175 proxyRect.outset(extra, extra); |
| 1176 | 1176 |
| 1177 SkAutoTUnref<const GrFragmentProcessor> fp(GrRRectBlurEffect::Create(texProv
ider, | 1177 sk_sp<GrFragmentProcessor> fp(GrRRectBlurEffect::Make(texProvider, xformedSi
gma, rrect)); |
| 1178 xformed
Sigma, rrect)); | |
| 1179 if (!fp) { | 1178 if (!fp) { |
| 1180 return false; | 1179 return false; |
| 1181 } | 1180 } |
| 1182 | 1181 |
| 1183 grp->addCoverageFragmentProcessor(fp); | 1182 grp->addCoverageFragmentProcessor(std::move(fp)); |
| 1184 | 1183 |
| 1185 SkMatrix inverse; | 1184 SkMatrix inverse; |
| 1186 if (!viewMatrix.invert(&inverse)) { | 1185 if (!viewMatrix.invert(&inverse)) { |
| 1187 return false; | 1186 return false; |
| 1188 } | 1187 } |
| 1189 | 1188 |
| 1190 drawContext->fillRectWithLocalMatrix(clip, *grp, SkMatrix::I(), proxyRect, i
nverse); | 1189 drawContext->fillRectWithLocalMatrix(clip, *grp, SkMatrix::I(), proxyRect, i
nverse); |
| 1191 return true; | 1190 return true; |
| 1192 } | 1191 } |
| 1193 | 1192 |
| (...skipping 61 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1255 xformedSigma,
xformedSigma)); | 1254 xformedSigma,
xformedSigma)); |
| 1256 if (!drawContext) { | 1255 if (!drawContext) { |
| 1257 return false; | 1256 return false; |
| 1258 } | 1257 } |
| 1259 | 1258 |
| 1260 if (!isNormalBlur) { | 1259 if (!isNormalBlur) { |
| 1261 GrPaint paint; | 1260 GrPaint paint; |
| 1262 SkMatrix matrix; | 1261 SkMatrix matrix; |
| 1263 matrix.setIDiv(src->width(), src->height()); | 1262 matrix.setIDiv(src->width(), src->height()); |
| 1264 // Blend pathTexture over blurTexture. | 1263 // Blend pathTexture over blurTexture. |
| 1265 paint.addCoverageFragmentProcessor(GrSimpleTextureEffect::Create(src, ma
trix))->unref(); | 1264 paint.addCoverageFragmentProcessor(GrSimpleTextureEffect::Make(src, matr
ix)); |
| 1266 if (kInner_SkBlurStyle == fBlurStyle) { | 1265 if (kInner_SkBlurStyle == fBlurStyle) { |
| 1267 // inner: dst = dst * src | 1266 // inner: dst = dst * src |
| 1268 paint.setCoverageSetOpXPFactory(SkRegion::kIntersect_Op); | 1267 paint.setCoverageSetOpXPFactory(SkRegion::kIntersect_Op); |
| 1269 } else if (kSolid_SkBlurStyle == fBlurStyle) { | 1268 } else if (kSolid_SkBlurStyle == fBlurStyle) { |
| 1270 // solid: dst = src + dst - src * dst | 1269 // solid: dst = src + dst - src * dst |
| 1271 // = src + (1 - src) * dst | 1270 // = src + (1 - src) * dst |
| 1272 paint.setCoverageSetOpXPFactory(SkRegion::kUnion_Op); | 1271 paint.setCoverageSetOpXPFactory(SkRegion::kUnion_Op); |
| 1273 } else if (kOuter_SkBlurStyle == fBlurStyle) { | 1272 } else if (kOuter_SkBlurStyle == fBlurStyle) { |
| 1274 // outer: dst = dst * (1 - src) | 1273 // outer: dst = dst * (1 - src) |
| 1275 // = 0 * src + (1 - src) * dst | 1274 // = 0 * src + (1 - src) * dst |
| (...skipping 37 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1313 } else { | 1312 } else { |
| 1314 str->append("None"); | 1313 str->append("None"); |
| 1315 } | 1314 } |
| 1316 str->append("))"); | 1315 str->append("))"); |
| 1317 } | 1316 } |
| 1318 #endif | 1317 #endif |
| 1319 | 1318 |
| 1320 SK_DEFINE_FLATTENABLE_REGISTRAR_GROUP_START(SkBlurMaskFilter) | 1319 SK_DEFINE_FLATTENABLE_REGISTRAR_GROUP_START(SkBlurMaskFilter) |
| 1321 SK_DEFINE_FLATTENABLE_REGISTRAR_ENTRY(SkBlurMaskFilterImpl) | 1320 SK_DEFINE_FLATTENABLE_REGISTRAR_ENTRY(SkBlurMaskFilterImpl) |
| 1322 SK_DEFINE_FLATTENABLE_REGISTRAR_GROUP_END | 1321 SK_DEFINE_FLATTENABLE_REGISTRAR_GROUP_END |
| OLD | NEW |