Reland of Implement canComputeFastBounds() for image filters. (patchset #1 id:1 of https://codereview.chromium.org/1300403003/ )

Reason for revert:
The Mac compile issue was fixed here: https://chromium.googlesource.com/chromium/src/+/fdd331a42ae0b9a6909a121020735161ab61c6e5

Original issue's description:
> Revert of Implement canComputeFastBounds() for image filters. (patchset #8 id:130001 of https://codereview.chromium.org/1296943002/ )
>
> Reason for revert:
> This causes a syntax error.
>
> http://build.chromium.org/p/tryserver.chromium.mac/builders/mac_chromium_compile_dbg_ng/builds/87819/steps/compile%20%28with%20patch%29/logs/stdio
>
> Original issue's description:
> > Implement canComputeFastBounds() for image filters.
> >
> > Image filters have never implemented this check, which means that
> > filters which affect transparent black falsely claim they can compute
> > their bounds.
> >
> > Implemented an affectsTransparentBlack() virtual for image
> > filters, and a similar helper function for color filters.
> >
> > This will affect the following GMs: imagefiltersscaled
> > (lighting, perlin noise now filter to clip),
> > colorfilterimagefilter (new test case), imagefiltersclipped
> > (perlin noise now filters to clip).
> >
> > Note: I de-inlined SkPaint::canComputeFastBounds() to avoid adding
> > a dependency from SkPaint.h to SkImageFilter.h.h. Skia benches show
> > no impact from this change, but will watch the perf bots carefully.
> >
> > BUG=4212
> >
> > Committed: https://skia.googlesource.com/skia/+/915881fe743f9a789037695f543bc6ea189cd0cb
>
> TBR=reed@google.com,senorblanco@chromium.org
> NOPRESUBMIT=true
> NOTREECHECKS=true
> NOTRY=true
> BUG=4212
>
> Committed: https://skia.googlesource.com/skia/+/12d8472d31ea5edb636d7d5214db253570115c40

TBR=reed@google.com,herb@google.com
NOPRESUBMIT=true
NOTREECHECKS=true
NOTRY=true
BUG=4212

Review URL: https://codereview.chromium.org/1301823005
diff --git a/tests/ImageFilterTest.cpp b/tests/ImageFilterTest.cpp
index d822212..c15d719 100644
--- a/tests/ImageFilterTest.cpp
+++ b/tests/ImageFilterTest.cpp
@@ -30,6 +30,7 @@
 #include "SkReadBuffer.h"
 #include "SkRect.h"
 #include "SkRectShaderImageFilter.h"
+#include "SkTableColorFilter.h"
 #include "SkTileImageFilter.h"
 #include "SkXfermodeImageFilter.h"
 #include "Test.h"
@@ -1159,6 +1160,58 @@
     REPORTER_ASSERT(reporter, result.height() == 30);
 }
 
+DEF_TEST(ImageFilterCanComputeFastBounds, reporter) {
+
+    SkPoint3 location = SkPoint3::Make(0, 0, SK_Scalar1);
+    SkAutoTUnref<SkImageFilter> lighting(SkLightingImageFilter::CreatePointLitDiffuse(
+          location, SK_ColorGREEN, 0, 0));
+    REPORTER_ASSERT(reporter, !lighting->canComputeFastBounds());
+
+    SkAutoTUnref<SkImageFilter> gray(make_grayscale(nullptr, nullptr));
+    REPORTER_ASSERT(reporter, gray->canComputeFastBounds());
+    {
+        SkColorFilter* grayCF;
+        REPORTER_ASSERT(reporter, gray->asAColorFilter(&grayCF));
+        REPORTER_ASSERT(reporter, !grayCF->affectsTransparentBlack());
+        grayCF->unref();
+    }
+    REPORTER_ASSERT(reporter, gray->canComputeFastBounds());
+
+    SkAutoTUnref<SkImageFilter> grayBlur(SkBlurImageFilter::Create(SK_Scalar1, SK_Scalar1, gray.get()));
+    REPORTER_ASSERT(reporter, grayBlur->canComputeFastBounds());
+
+    SkScalar greenMatrix[20] = { 0, 0, 0, 0, 0,
+                                 0, 0, 0, 0, 1,
+                                 0, 0, 0, 0, 0,
+                                 0, 0, 0, 0, 1 };
+    SkAutoTUnref<SkColorFilter> greenCF(SkColorMatrixFilter::Create(greenMatrix));
+    SkAutoTUnref<SkImageFilter> green(SkColorFilterImageFilter::Create(greenCF));
+
+    REPORTER_ASSERT(reporter, greenCF->affectsTransparentBlack());
+    REPORTER_ASSERT(reporter, !green->canComputeFastBounds());
+
+    SkAutoTUnref<SkImageFilter> greenBlur(SkBlurImageFilter::Create(SK_Scalar1, SK_Scalar1, green.get()));
+    REPORTER_ASSERT(reporter, !greenBlur->canComputeFastBounds());
+
+    uint8_t allOne[256], identity[256];
+    for (int i = 0; i < 256; ++i) {
+        identity[i] = i;
+        allOne[i] = 255;
+    }
+
+    SkAutoTUnref<SkColorFilter> identityCF(
+        SkTableColorFilter::CreateARGB(identity, identity, identity, allOne));
+    SkAutoTUnref<SkImageFilter> identityFilter(SkColorFilterImageFilter::Create(identityCF.get()));
+    REPORTER_ASSERT(reporter, !identityCF->affectsTransparentBlack());
+    REPORTER_ASSERT(reporter, identityFilter->canComputeFastBounds());
+
+    SkAutoTUnref<SkColorFilter> forceOpaqueCF(
+        SkTableColorFilter::CreateARGB(allOne, identity, identity, identity));
+    SkAutoTUnref<SkImageFilter> forceOpaque(SkColorFilterImageFilter::Create(forceOpaqueCF.get()));
+    REPORTER_ASSERT(reporter, forceOpaqueCF->affectsTransparentBlack());
+    REPORTER_ASSERT(reporter, !forceOpaque->canComputeFastBounds());
+}
+
 #if SK_SUPPORT_GPU
 
 DEF_GPUTEST(ImageFilterCropRectGPU, reporter, factory) {