Add GM to verify removal of 32767 limit in SkBlurMaskFilter::filterRectsToNine is...
authorrobertphillips@google.com <robertphillips@google.com@2bbb7eff-a529-9590-31e7-b0007b416f81>
Thu, 7 Nov 2013 22:25:21 +0000 (22:25 +0000)
committerrobertphillips@google.com <robertphillips@google.com@2bbb7eff-a529-9590-31e7-b0007b416f81>
Thu, 7 Nov 2013 22:25:21 +0000 (22:25 +0000)
https://codereview.chromium.org/60513013/

git-svn-id: http://skia.googlecode.com/svn/trunk@12181 2bbb7eff-a529-9590-31e7-b0007b416f81

gm/bigblurs.cpp [new file with mode: 0644]
gyp/gmslides.gypi
src/effects/SkBlurMaskFilter.cpp

diff --git a/gm/bigblurs.cpp b/gm/bigblurs.cpp
new file mode 100644 (file)
index 0000000..195d085
--- /dev/null
@@ -0,0 +1,117 @@
+
+/*
+ * Copyright 2013 Google Inc.
+ *
+ * Use of this source code is governed by a BSD-style license that can be
+ * found in the LICENSE file.
+ */
+
+#include "gm.h"
+#include "SkBlurMask.h"
+#include "SkBlurMaskFilter.h"
+
+namespace skiagm {
+
+// This GM exercises the blurred rect nine-patching special cases when the
+// blurred rect is very large and/or very far from the origin.
+// It creates a large blurred rect/rectori then renders the 4 corners and the 
+// middle.
+class BigBlursGM : public GM {
+public:
+    BigBlursGM() {
+        this->setBGColor(0xFFDDDDDD);
+    }
+
+protected:
+    virtual SkString onShortName() SK_OVERRIDE {
+        return SkString("bigblurs");
+    }
+
+    virtual SkISize onISize() SK_OVERRIDE {
+        return make_isize(kWidth, kHeight);
+    }
+
+    virtual void onDraw(SkCanvas* canvas) SK_OVERRIDE {
+        static const int kBig = 65536;
+        static const SkScalar kSigma = SkBlurMask::ConvertRadiusToSigma(SkIntToScalar(4));
+
+        const SkRect bigRect = SkRect::MakeWH(SkIntToScalar(kBig), SkIntToScalar(kBig));
+        SkRect insetRect = bigRect;
+        insetRect.inset(20, 20);
+
+        SkPath rectori;
+
+        rectori.addRect(bigRect);
+        rectori.addRect(insetRect, SkPath::kCCW_Direction);
+
+        // The blur extends 3*kSigma out from the big rect.
+        // Offset the close-up windows so we get the entire blur
+        static const SkScalar kLeftTopPad  = 3*kSigma;   // use on left & up of big rect
+        static const SkScalar kRightBotPad = kCloseUpSize-3*kSigma; // use on right and bot sides
+
+        // UL hand corners of the rendered closeups
+        const SkPoint origins[] = {
+            { -kLeftTopPad,          -kLeftTopPad           }, // UL
+            {  kBig-kRightBotPad,    -kLeftTopPad           }, // UR
+            {  kBig-kRightBotPad,     kBig-kRightBotPad     }, // LR
+            { -kLeftTopPad,           kBig-kRightBotPad     }, // LL
+            {  kBig/2-kCloseUpSize/2, kBig/2-kCloseUpSize/2 }, // center
+        };
+
+        SkPaint outlinePaint;
+        outlinePaint.setColor(SK_ColorRED);
+        outlinePaint.setStyle(SkPaint::kStroke_Style);
+
+        SkPaint blurPaint;
+        blurPaint.setAntiAlias(true);
+        blurPaint.setColor(SK_ColorBLACK);
+
+        int desiredX = 0, desiredY = 0;
+
+        for (int i = 0; i < 2; ++i) {
+            for (int j = 0; j < SkBlurMaskFilter::kBlurStyleCount; ++j) {
+                SkMaskFilter* mf = SkBlurMaskFilter::Create((SkBlurMaskFilter::BlurStyle)j, 
+                                                            kSigma);
+                blurPaint.setMaskFilter(mf)->unref();
+
+                for (int k = 0; k < (int)SK_ARRAY_COUNT(origins); ++k) {
+                    canvas->save();
+
+                    SkRect clipRect = SkRect::MakeXYWH(SkIntToScalar(desiredX), 
+                                                       SkIntToScalar(desiredY),
+                                                       SkIntToScalar(kCloseUpSize), 
+                                                       SkIntToScalar(kCloseUpSize));
+
+                    canvas->clipRect(clipRect, SkRegion::kReplace_Op, false);
+
+                    canvas->translate(desiredX-origins[k].fX, 
+                                      desiredY-origins[k].fY);
+
+                    if (0 == i) {
+                        canvas->drawRect(bigRect, blurPaint);
+                    } else {
+                        canvas->drawPath(rectori, blurPaint);
+                    }
+                    canvas->restore();
+                    canvas->drawRect(clipRect, outlinePaint);
+
+                    desiredX += kCloseUpSize;
+                }
+
+                desiredX = 0;
+                desiredY += kCloseUpSize;
+            }
+        }
+    }
+
+private:
+    static const int kCloseUpSize = 64;
+    static const int kWidth = 5 * kCloseUpSize;
+    static const int kHeight = 2 * SkBlurMaskFilter::kBlurStyleCount * kCloseUpSize;
+
+    typedef GM INHERITED;
+};
+
+DEF_GM( return SkNEW(BigBlursGM); )
+
+}
\ No newline at end of file
index dd2c374..a18ad54 100644 (file)
@@ -9,6 +9,7 @@
     '../gm/arithmode.cpp',
     '../gm/beziereffects.cpp',
     '../gm/bicubicfilter.cpp',
+    '../gm/bigblurs.cpp',
     '../gm/bigmatrix.cpp',
     '../gm/bigtext.cpp',
     '../gm/bitmapalphathreshold.cpp',
index 5b72a6c..a2e8065 100644 (file)
@@ -214,7 +214,8 @@ SkBlurMaskFilterImpl::filterRectsToNine(const SkRect rects[], int count,
 
     // TODO: report correct metrics for innerstyle, where we do not grow the
     // total bounds, but we do need an inset the size of our blur-radius
-    if (SkBlurMaskFilter::kInner_BlurStyle == fBlurStyle) {
+    if (SkBlurMaskFilter::kInner_BlurStyle == fBlurStyle ||
+        SkBlurMaskFilter::kOuter_BlurStyle == fBlurStyle) {
         return kUnimplemented_FilterReturn;
     }