| OLD | NEW |
| 1 | 1 |
| 2 /* | 2 /* |
| 3 * Copyright 2006 The Android Open Source Project | 3 * Copyright 2006 The Android Open Source Project |
| 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 "SkBlurMaskFilter.h" | 9 #include "SkBlurMaskFilter.h" |
| 10 #include "SkBlurMask.h" | 10 #include "SkBlurMask.h" |
| (...skipping 599 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 610 const char* name() const override { return "RectBlur"; } | 610 const char* name() const override { return "RectBlur"; } |
| 611 | 611 |
| 612 virtual void getGLProcessorKey(const GrGLSLCaps& caps, | 612 virtual void getGLProcessorKey(const GrGLSLCaps& caps, |
| 613 GrProcessorKeyBuilder* b) const override; | 613 GrProcessorKeyBuilder* b) const override; |
| 614 | 614 |
| 615 GrGLFragmentProcessor* createGLInstance() const override; | 615 GrGLFragmentProcessor* createGLInstance() const override; |
| 616 | 616 |
| 617 /** | 617 /** |
| 618 * Create a simple filter effect with custom bicubic coefficients. | 618 * Create a simple filter effect with custom bicubic coefficients. |
| 619 */ | 619 */ |
| 620 static GrFragmentProcessor* Create(GrContext *context, const SkRect& rect, f
loat sigma) { | 620 static GrFragmentProcessor* Create(GrTextureProvider *textureProvider, const
SkRect& rect, |
| 621 float sigma) { |
| 621 GrTexture *blurProfileTexture = NULL; | 622 GrTexture *blurProfileTexture = NULL; |
| 622 int doubleProfileSize = SkScalarCeilToInt(12*sigma); | 623 int doubleProfileSize = SkScalarCeilToInt(12*sigma); |
| 623 | 624 |
| 624 if (doubleProfileSize >= rect.width() || doubleProfileSize >= rect.heigh
t()) { | 625 if (doubleProfileSize >= rect.width() || doubleProfileSize >= rect.heigh
t()) { |
| 625 // if the blur sigma is too large so the gaussian overlaps the whole | 626 // if the blur sigma is too large so the gaussian overlaps the whole |
| 626 // rect in either direction, fall back to CPU path for now. | 627 // rect in either direction, fall back to CPU path for now. |
| 627 | 628 |
| 628 return NULL; | 629 return NULL; |
| 629 } | 630 } |
| 630 | 631 |
| 631 bool createdBlurProfileTexture = CreateBlurProfileTexture(context, sigma
, &blurProfileTexture); | 632 bool createdBlurProfileTexture = CreateBlurProfileTexture( |
| 633 textureProvider, sigma, &blurProfileTexture); |
| 632 SkAutoTUnref<GrTexture> hunref(blurProfileTexture); | 634 SkAutoTUnref<GrTexture> hunref(blurProfileTexture); |
| 633 if (!createdBlurProfileTexture) { | 635 if (!createdBlurProfileTexture) { |
| 634 return NULL; | 636 return NULL; |
| 635 } | 637 } |
| 636 return SkNEW_ARGS(GrRectBlurEffect, (rect, sigma, blurProfileTexture)); | 638 return SkNEW_ARGS(GrRectBlurEffect, (rect, sigma, blurProfileTexture)); |
| 637 } | 639 } |
| 638 | 640 |
| 639 const SkRect& getRect() const { return fRect; } | 641 const SkRect& getRect() const { return fRect; } |
| 640 float getSigma() const { return fSigma; } | 642 float getSigma() const { return fSigma; } |
| 641 | 643 |
| 642 private: | 644 private: |
| 643 GrRectBlurEffect(const SkRect& rect, float sigma, GrTexture *blur_profile); | 645 GrRectBlurEffect(const SkRect& rect, float sigma, GrTexture *blur_profile); |
| 644 bool onIsEqual(const GrFragmentProcessor&) const override; | 646 bool onIsEqual(const GrFragmentProcessor&) const override; |
| 645 | 647 |
| 646 void onComputeInvariantOutput(GrInvariantOutput* inout) const override; | 648 void onComputeInvariantOutput(GrInvariantOutput* inout) const override; |
| 647 | 649 |
| 648 static bool CreateBlurProfileTexture(GrContext *context, float sigma, | 650 static bool CreateBlurProfileTexture(GrTextureProvider*, float sigma, |
| 649 GrTexture **blurProfileTexture); | 651 GrTexture **blurProfileTexture); |
| 650 | 652 |
| 651 SkRect fRect; | 653 SkRect fRect; |
| 652 float fSigma; | 654 float fSigma; |
| 653 GrTextureAccess fBlurProfileAccess; | 655 GrTextureAccess fBlurProfileAccess; |
| 654 | 656 |
| 655 GR_DECLARE_FRAGMENT_PROCESSOR_TEST; | 657 GR_DECLARE_FRAGMENT_PROCESSOR_TEST; |
| 656 | 658 |
| 657 typedef GrFragmentProcessor INHERITED; | 659 typedef GrFragmentProcessor INHERITED; |
| 658 }; | 660 }; |
| (...skipping 82 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 741 | 743 |
| 742 void GrGLRectBlurEffect::setData(const GrGLProgramDataManager& pdman, | 744 void GrGLRectBlurEffect::setData(const GrGLProgramDataManager& pdman, |
| 743 const GrProcessor& proc) { | 745 const GrProcessor& proc) { |
| 744 const GrRectBlurEffect& rbe = proc.cast<GrRectBlurEffect>(); | 746 const GrRectBlurEffect& rbe = proc.cast<GrRectBlurEffect>(); |
| 745 SkRect rect = rbe.getRect(); | 747 SkRect rect = rbe.getRect(); |
| 746 | 748 |
| 747 pdman.set4f(fProxyRectUniform, rect.fLeft, rect.fTop, rect.fRight, rect.fBot
tom); | 749 pdman.set4f(fProxyRectUniform, rect.fLeft, rect.fTop, rect.fRight, rect.fBot
tom); |
| 748 pdman.set1f(fProfileSizeUniform, SkScalarCeilToScalar(6*rbe.getSigma())); | 750 pdman.set1f(fProfileSizeUniform, SkScalarCeilToScalar(6*rbe.getSigma())); |
| 749 } | 751 } |
| 750 | 752 |
| 751 bool GrRectBlurEffect::CreateBlurProfileTexture(GrContext *context, float sigma, | 753 bool GrRectBlurEffect::CreateBlurProfileTexture(GrTextureProvider* textureProvid
er, float sigma, |
| 752 GrTexture **blurProfileTexture)
{ | 754 GrTexture **blurProfileTexture)
{ |
| 753 GrSurfaceDesc texDesc; | 755 GrSurfaceDesc texDesc; |
| 754 | 756 |
| 755 unsigned int profileSize = SkScalarCeilToInt(6*sigma); | 757 unsigned int profileSize = SkScalarCeilToInt(6*sigma); |
| 756 | 758 |
| 757 texDesc.fWidth = profileSize; | 759 texDesc.fWidth = profileSize; |
| 758 texDesc.fHeight = 1; | 760 texDesc.fHeight = 1; |
| 759 texDesc.fConfig = kAlpha_8_GrPixelConfig; | 761 texDesc.fConfig = kAlpha_8_GrPixelConfig; |
| 760 | 762 |
| 761 static const GrUniqueKey::Domain kDomain = GrUniqueKey::GenerateDomain(); | 763 static const GrUniqueKey::Domain kDomain = GrUniqueKey::GenerateDomain(); |
| 762 GrUniqueKey key; | 764 GrUniqueKey key; |
| 763 GrUniqueKey::Builder builder(&key, kDomain, 1); | 765 GrUniqueKey::Builder builder(&key, kDomain, 1); |
| 764 builder[0] = profileSize; | 766 builder[0] = profileSize; |
| 765 builder.finish(); | 767 builder.finish(); |
| 766 | 768 |
| 767 uint8_t *profile = NULL; | 769 uint8_t *profile = NULL; |
| 768 SkAutoTDeleteArray<uint8_t> ada(NULL); | 770 SkAutoTDeleteArray<uint8_t> ada(NULL); |
| 769 | 771 |
| 770 *blurProfileTexture = context->findAndRefCachedTexture(key); | 772 *blurProfileTexture = textureProvider->findAndRefTextureByUniqueKey(key); |
| 771 | 773 |
| 772 if (NULL == *blurProfileTexture) { | 774 if (NULL == *blurProfileTexture) { |
| 773 | 775 |
| 774 SkBlurMask::ComputeBlurProfile(sigma, &profile); | 776 SkBlurMask::ComputeBlurProfile(sigma, &profile); |
| 775 ada.reset(profile); | 777 ada.reset(profile); |
| 776 | 778 |
| 777 *blurProfileTexture = context->createTexture(texDesc, true, profile, 0); | 779 *blurProfileTexture = textureProvider->createTexture(texDesc, true, prof
ile, 0); |
| 778 | 780 |
| 779 if (NULL == *blurProfileTexture) { | 781 if (NULL == *blurProfileTexture) { |
| 780 return false; | 782 return false; |
| 781 } | 783 } |
| 782 context->addResourceToCache(key, *blurProfileTexture); | 784 textureProvider->assignUniqueKeyToTexture(key, *blurProfileTexture); |
| 783 } | 785 } |
| 784 | 786 |
| 785 return true; | 787 return true; |
| 786 } | 788 } |
| 787 | 789 |
| 788 GrRectBlurEffect::GrRectBlurEffect(const SkRect& rect, float sigma, | 790 GrRectBlurEffect::GrRectBlurEffect(const SkRect& rect, float sigma, |
| 789 GrTexture *blur_profile) | 791 GrTexture *blur_profile) |
| 790 : fRect(rect), | 792 : fRect(rect), |
| 791 fSigma(sigma), | 793 fSigma(sigma), |
| 792 fBlurProfileAccess(blur_profile) { | 794 fBlurProfileAccess(blur_profile) { |
| (...skipping 25 matching lines...) Expand all Loading... |
| 818 | 820 |
| 819 GR_DEFINE_FRAGMENT_PROCESSOR_TEST(GrRectBlurEffect); | 821 GR_DEFINE_FRAGMENT_PROCESSOR_TEST(GrRectBlurEffect); |
| 820 | 822 |
| 821 GrFragmentProcessor* GrRectBlurEffect::TestCreate(SkRandom* random, | 823 GrFragmentProcessor* GrRectBlurEffect::TestCreate(SkRandom* random, |
| 822 GrContext* context, | 824 GrContext* context, |
| 823 const GrDrawTargetCaps&, | 825 const GrDrawTargetCaps&, |
| 824 GrTexture**) { | 826 GrTexture**) { |
| 825 float sigma = random->nextRangeF(3,8); | 827 float sigma = random->nextRangeF(3,8); |
| 826 float width = random->nextRangeF(200,300); | 828 float width = random->nextRangeF(200,300); |
| 827 float height = random->nextRangeF(200,300); | 829 float height = random->nextRangeF(200,300); |
| 828 return GrRectBlurEffect::Create(context, SkRect::MakeWH(width, height), sigm
a); | 830 return GrRectBlurEffect::Create(context->textureProvider(), SkRect::MakeWH(w
idth, height), |
| 831 sigma); |
| 829 } | 832 } |
| 830 | 833 |
| 831 | 834 |
| 832 bool SkBlurMaskFilterImpl::directFilterMaskGPU(GrContext* context, | 835 bool SkBlurMaskFilterImpl::directFilterMaskGPU(GrContext* context, |
| 833 GrRenderTarget* rt, | 836 GrRenderTarget* rt, |
| 834 GrPaint* grp, | 837 GrPaint* grp, |
| 835 const GrClip& clip, | 838 const GrClip& clip, |
| 836 const SkMatrix& viewMatrix, | 839 const SkMatrix& viewMatrix, |
| 837 const SkStrokeRec& strokeRec, | 840 const SkStrokeRec& strokeRec, |
| 838 const SkPath& path) const { | 841 const SkPath& path) const { |
| 839 if (fBlurStyle != kNormal_SkBlurStyle) { | 842 if (fBlurStyle != kNormal_SkBlurStyle) { |
| 840 return false; | 843 return false; |
| 841 } | 844 } |
| 842 | 845 |
| 843 SkRect rect; | 846 SkRect rect; |
| 844 if (!path.isRect(&rect)) { | 847 if (!path.isRect(&rect)) { |
| 845 return false; | 848 return false; |
| 846 } | 849 } |
| 847 | 850 |
| 848 if (!strokeRec.isFillStyle()) { | 851 if (!strokeRec.isFillStyle()) { |
| 849 return false; | 852 return false; |
| 850 } | 853 } |
| 851 | 854 |
| 852 SkMatrix ctm = viewMatrix; | 855 SkMatrix ctm = viewMatrix; |
| 853 SkScalar xformedSigma = this->computeXformedSigma(ctm); | 856 SkScalar xformedSigma = this->computeXformedSigma(ctm); |
| 854 | 857 |
| 855 int pad=SkScalarCeilToInt(6*xformedSigma)/2; | 858 int pad=SkScalarCeilToInt(6*xformedSigma)/2; |
| 856 rect.outset(SkIntToScalar(pad), SkIntToScalar(pad)); | 859 rect.outset(SkIntToScalar(pad), SkIntToScalar(pad)); |
| 857 | 860 |
| 858 SkAutoTUnref<GrFragmentProcessor> fp(GrRectBlurEffect::Create(context, rect,
xformedSigma)); | 861 SkAutoTUnref<GrFragmentProcessor> fp(GrRectBlurEffect::Create( |
| 862 context->textureProvider(), rect, xformedSigma)); |
| 859 if (!fp) { | 863 if (!fp) { |
| 860 return false; | 864 return false; |
| 861 } | 865 } |
| 862 | 866 |
| 863 grp->addCoverageProcessor(fp); | 867 grp->addCoverageProcessor(fp); |
| 864 | 868 |
| 865 SkMatrix inverse; | 869 SkMatrix inverse; |
| 866 if (!viewMatrix.invert(&inverse)) { | 870 if (!viewMatrix.invert(&inverse)) { |
| 867 return false; | 871 return false; |
| 868 } | 872 } |
| (...skipping 51 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 920 return NULL; | 924 return NULL; |
| 921 } | 925 } |
| 922 | 926 |
| 923 static const GrUniqueKey::Domain kDomain = GrUniqueKey::GenerateDomain(); | 927 static const GrUniqueKey::Domain kDomain = GrUniqueKey::GenerateDomain(); |
| 924 GrUniqueKey key; | 928 GrUniqueKey key; |
| 925 GrUniqueKey::Builder builder(&key, kDomain, 2); | 929 GrUniqueKey::Builder builder(&key, kDomain, 2); |
| 926 builder[0] = blurRadius; | 930 builder[0] = blurRadius; |
| 927 builder[1] = cornerRadius; | 931 builder[1] = cornerRadius; |
| 928 builder.finish(); | 932 builder.finish(); |
| 929 | 933 |
| 930 SkAutoTUnref<GrTexture> blurNinePatchTexture(context->findAndRefCachedTextur
e(key)); | 934 SkAutoTUnref<GrTexture> blurNinePatchTexture( |
| 935 context->textureProvider()->findAndRefTextureByUniqueKey(key)); |
| 931 | 936 |
| 932 if (!blurNinePatchTexture) { | 937 if (!blurNinePatchTexture) { |
| 933 SkMask mask; | 938 SkMask mask; |
| 934 | 939 |
| 935 unsigned int smallRectSide = 2*(blurRadius + cornerRadius) + 1; | 940 unsigned int smallRectSide = 2*(blurRadius + cornerRadius) + 1; |
| 936 | 941 |
| 937 mask.fBounds = SkIRect::MakeWH(smallRectSide, smallRectSide); | 942 mask.fBounds = SkIRect::MakeWH(smallRectSide, smallRectSide); |
| 938 mask.fFormat = SkMask::kA8_Format; | 943 mask.fFormat = SkMask::kA8_Format; |
| 939 mask.fRowBytes = mask.fBounds.width(); | 944 mask.fRowBytes = mask.fBounds.width(); |
| 940 mask.fImage = SkMask::AllocImage(mask.computeTotalImageSize()); | 945 mask.fImage = SkMask::AllocImage(mask.computeTotalImageSize()); |
| (...skipping 16 matching lines...) Expand all Loading... |
| 957 SkMask blurredMask; | 962 SkMask blurredMask; |
| 958 SkBlurMask::BoxBlur(&blurredMask, mask, sigma, kNormal_SkBlurStyle, kHig
h_SkBlurQuality, | 963 SkBlurMask::BoxBlur(&blurredMask, mask, sigma, kNormal_SkBlurStyle, kHig
h_SkBlurQuality, |
| 959 NULL, true ); | 964 NULL, true ); |
| 960 | 965 |
| 961 unsigned int texSide = smallRectSide + 2*blurRadius; | 966 unsigned int texSide = smallRectSide + 2*blurRadius; |
| 962 GrSurfaceDesc texDesc; | 967 GrSurfaceDesc texDesc; |
| 963 texDesc.fWidth = texSide; | 968 texDesc.fWidth = texSide; |
| 964 texDesc.fHeight = texSide; | 969 texDesc.fHeight = texSide; |
| 965 texDesc.fConfig = kAlpha_8_GrPixelConfig; | 970 texDesc.fConfig = kAlpha_8_GrPixelConfig; |
| 966 | 971 |
| 967 blurNinePatchTexture.reset(context->createTexture(texDesc, true, blurred
Mask.fImage, 0)); | 972 blurNinePatchTexture.reset( |
| 973 context->textureProvider()->createTexture(texDesc, true, blurredMask
.fImage, 0)); |
| 968 SkMask::FreeImage(blurredMask.fImage); | 974 SkMask::FreeImage(blurredMask.fImage); |
| 969 if (!blurNinePatchTexture) { | 975 if (!blurNinePatchTexture) { |
| 970 return NULL; | 976 return NULL; |
| 971 } | 977 } |
| 972 context->addResourceToCache(key, blurNinePatchTexture); | 978 context->textureProvider()->assignUniqueKeyToTexture(key, blurNinePatchT
exture); |
| 973 } | 979 } |
| 974 return SkNEW_ARGS(GrRRectBlurEffect, (sigma, rrect, blurNinePatchTexture)); | 980 return SkNEW_ARGS(GrRRectBlurEffect, (sigma, rrect, blurNinePatchTexture)); |
| 975 } | 981 } |
| 976 | 982 |
| 977 void GrRRectBlurEffect::onComputeInvariantOutput(GrInvariantOutput* inout) const
{ | 983 void GrRRectBlurEffect::onComputeInvariantOutput(GrInvariantOutput* inout) const
{ |
| 978 inout->mulByUnknownSingleComponent(); | 984 inout->mulByUnknownSingleComponent(); |
| 979 } | 985 } |
| 980 | 986 |
| 981 GrRRectBlurEffect::GrRRectBlurEffect(float sigma, const SkRRect& rrect, GrTextur
e *ninePatchTexture) | 987 GrRRectBlurEffect::GrRRectBlurEffect(float sigma, const SkRRect& rrect, GrTextur
e *ninePatchTexture) |
| 982 : fRRect(rrect), | 988 : fRRect(rrect), |
| (...skipping 282 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1265 } else { | 1271 } else { |
| 1266 str->append("None"); | 1272 str->append("None"); |
| 1267 } | 1273 } |
| 1268 str->append("))"); | 1274 str->append("))"); |
| 1269 } | 1275 } |
| 1270 #endif | 1276 #endif |
| 1271 | 1277 |
| 1272 SK_DEFINE_FLATTENABLE_REGISTRAR_GROUP_START(SkBlurMaskFilter) | 1278 SK_DEFINE_FLATTENABLE_REGISTRAR_GROUP_START(SkBlurMaskFilter) |
| 1273 SK_DEFINE_FLATTENABLE_REGISTRAR_ENTRY(SkBlurMaskFilterImpl) | 1279 SK_DEFINE_FLATTENABLE_REGISTRAR_ENTRY(SkBlurMaskFilterImpl) |
| 1274 SK_DEFINE_FLATTENABLE_REGISTRAR_GROUP_END | 1280 SK_DEFINE_FLATTENABLE_REGISTRAR_GROUP_END |
| OLD | NEW |