Bug 1309804 - Part 2. Split invalid region computation into nsDisplayMask & nsDisplayFilter. draft
authorcku <cku@mozilla.com>
Thu, 13 Oct 2016 15:36:48 +0800
changeset 425109 a36e17774524fad0b5fd0ed8519d6d228dd6388b
parent 425108 ea7976d5ebe5d8b329b127b68ccd261bbad050b2
child 425110 0dd50b50c3d7e68eb65b5625d376254c0f31dbac
push id32345
push userbmo:cku@mozilla.com
push dateFri, 14 Oct 2016 07:44:21 +0000
bugs1309804
milestone52.0a1
Bug 1309804 - Part 2. Split invalid region computation into nsDisplayMask & nsDisplayFilter. MozReview-Commit-ID: IOL7S2Y6Hhm
layout/base/nsDisplayList.cpp
layout/base/nsDisplayList.h
layout/base/nsDisplayListInvalidation.cpp
layout/base/nsDisplayListInvalidation.h
--- a/layout/base/nsDisplayList.cpp
+++ b/layout/base/nsDisplayList.cpp
@@ -6797,21 +6797,16 @@ nsDisplaySVGEffects::ComputeInvalidation
     // Filter and mask output can depend on the location of the frame's user
     // space and on the frame's BBox. We need to invalidate if either of these
     // change relative to the reference frame.
     // Invalidations from our inactive layer manager are not enough to catch
     // some of these cases because filters can produce output even if there's
     // nothing in the filter input.
     aInvalidRegion->Or(bounds, geometry->mBounds);
   }
-
-  if (aBuilder->ShouldSyncDecodeImages() &&
-      geometry->ShouldInvalidateToSyncDecodeImages()) {
-    aInvalidRegion->Or(*aInvalidRegion, bounds);
-  }
 }
 
 bool nsDisplaySVGEffects::ValidateSVGFrame()
 {
   const nsIContent* content = mFrame->GetContent();
   bool hasSVGLayout = (mFrame->GetStateBits() & NS_FRAME_SVG_LAYOUT);
   if (hasSVGLayout) {
     nsISVGChildFrame *svgChildFrame = do_QueryFrame(mFrame);
@@ -7044,16 +7039,34 @@ bool nsDisplayMask::ComputeVisibility(ns
   // not allow them to subtract area from aVisibleRegion.
   nsRegion childrenVisible(mVisibleRect);
   nsRect r = mVisibleRect.Intersect(mList.GetBounds(aBuilder));
   mList.ComputeVisibilityForSublist(aBuilder, &childrenVisible, r);
   return true;
 }
 
 void
+nsDisplayMask::ComputeInvalidationRegion(nsDisplayListBuilder* aBuilder,
+                                               const nsDisplayItemGeometry* aGeometry,
+                                               nsRegion* aInvalidRegion)
+{
+  nsDisplaySVGEffects::ComputeInvalidationRegion(aBuilder, aGeometry,
+                                                 aInvalidRegion);
+
+  const nsDisplayMaskGeometry* geometry =
+    static_cast<const nsDisplayMaskGeometry*>(aGeometry);
+  bool snap;
+  nsRect bounds = GetBounds(aBuilder, &snap);
+  if (aBuilder->ShouldSyncDecodeImages() &&
+      geometry->ShouldInvalidateToSyncDecodeImages()) {
+    aInvalidRegion->Or(*aInvalidRegion, bounds);
+  }
+}
+
+void
 nsDisplayMask::PaintAsLayer(nsDisplayListBuilder* aBuilder,
                             nsRenderingContext* aCtx,
                             LayerManager* aManager)
 {
   nsRect borderArea = nsRect(ToReferenceFrame(), mFrame->GetSize());
   nsSVGIntegrationUtils::PaintFramesParams params(*aCtx->ThebesContext(),
                                                   mFrame,  mVisibleRect,
                                                   borderArea, aBuilder,
@@ -7223,20 +7236,18 @@ nsDisplayFilter::PaintAsLayer(nsDisplayL
 {
   nsRect borderArea = nsRect(ToReferenceFrame(), mFrame->GetSize());
   nsSVGIntegrationUtils::PaintFramesParams params(*aCtx->ThebesContext(),
                                                   mFrame,  mVisibleRect,
                                                   borderArea, aBuilder,
                                                   aManager,
                                                   mHandleOpacity);
 
-  image::DrawResult result =
-    nsSVGIntegrationUtils::PaintFilter(params);
-
-  nsDisplayMaskGeometry::UpdateDrawResult(this, result);
+  image::DrawResult result = nsSVGIntegrationUtils::PaintFilter(params);
+  nsDisplayFilterGeometry::UpdateDrawResult(this, result);
 }
 
 #ifdef MOZ_DUMP_PAINTING
 void
 nsDisplayFilter::PrintEffects(nsACString& aTo)
 {
   nsIFrame* firstFrame =
     nsLayoutUtils::FirstContinuationOrIBSplitSibling(mFrame);
--- a/layout/base/nsDisplayList.h
+++ b/layout/base/nsDisplayList.h
@@ -3856,20 +3856,16 @@ public:
 
   virtual bool ShouldFlattenAway(nsDisplayListBuilder* aBuilder) override {
     return false;
   }
 
   gfxRect BBoxInUserSpace() const;
   gfxPoint UserSpaceOffset() const;
 
-  virtual nsDisplayItemGeometry* AllocateGeometry(nsDisplayListBuilder* aBuilder) override
-  {
-    return new nsDisplayMaskGeometry(this, aBuilder);
-  }
   virtual void ComputeInvalidationRegion(nsDisplayListBuilder* aBuilder,
                                          const nsDisplayItemGeometry* aGeometry,
                                          nsRegion* aInvalidRegion) override;
 protected:
   bool ValidateSVGFrame();
 
   // relative to mFrame
   nsRect mEffectsBounds;
@@ -3897,16 +3893,24 @@ public:
                                              LayerManager* aManager,
                                              const ContainerLayerParameters& aContainerParameters) override;
   virtual LayerState GetLayerState(nsDisplayListBuilder* aBuilder,
                                    LayerManager* aManager,
                                    const ContainerLayerParameters& aParameters) override;
 
   virtual bool ComputeVisibility(nsDisplayListBuilder* aBuilder,
                                  nsRegion* aVisibleRegion) override;
+
+  virtual nsDisplayItemGeometry* AllocateGeometry(nsDisplayListBuilder* aBuilder) override
+  {
+    return new nsDisplayMaskGeometry(this, aBuilder);
+  }
+  virtual void ComputeInvalidationRegion(nsDisplayListBuilder* aBuilder,
+                                         const nsDisplayItemGeometry* aGeometry,
+                                         nsRegion* aInvalidRegion) override;
 #ifdef MOZ_DUMP_PAINTING
   void PrintEffects(nsACString& aTo);
 #endif
 
   void PaintAsLayer(nsDisplayListBuilder* aBuilder,
                     nsRenderingContext* aCtx,
                     LayerManager* aManager);
 };
@@ -3934,16 +3938,21 @@ public:
                                    const ContainerLayerParameters& aParameters) override;
   virtual nsRect GetBounds(nsDisplayListBuilder* aBuilder,
                            bool* aSnap) override {
     *aSnap = false;
     return mEffectsBounds + ToReferenceFrame();
   }
   virtual bool ComputeVisibility(nsDisplayListBuilder* aBuilder,
                                  nsRegion* aVisibleRegion) override;
+  virtual nsDisplayItemGeometry* AllocateGeometry(nsDisplayListBuilder* aBuilder) override
+  {
+    return new nsDisplayFilterGeometry(this, aBuilder);
+  }
+
 #ifdef MOZ_DUMP_PAINTING
   void PrintEffects(nsACString& aTo);
 #endif
 
   void PaintAsLayer(nsDisplayListBuilder* aBuilder,
                     nsRenderingContext* aCtx,
                     LayerManager* aManager);
 };
--- a/layout/base/nsDisplayListInvalidation.cpp
+++ b/layout/base/nsDisplayListInvalidation.cpp
@@ -108,31 +108,46 @@ nsDisplayBoxShadowOuterGeometry::nsDispl
 
 void
 nsDisplaySolidColorRegionGeometry::MoveBy(const nsPoint& aOffset)
 {
   nsDisplayItemGeometry::MoveBy(aOffset);
   mRegion.MoveBy(aOffset);
 }
 
-nsDisplayMaskGeometry::nsDisplayMaskGeometry(nsDisplaySVGEffects* aItem, nsDisplayListBuilder* aBuilder)
+nsDisplayMaskGeometry::nsDisplayMaskGeometry(nsDisplayMask* aItem, nsDisplayListBuilder* aBuilder)
   : nsDisplayItemGeometry(aItem, aBuilder)
   , nsImageGeometryMixin(aItem, aBuilder)
   , mBBox(aItem->BBoxInUserSpace())
   , mUserSpaceOffset(aItem->UserSpaceOffset())
   , mFrameOffsetToReferenceFrame(aItem->ToReferenceFrame())
 {}
 
 void
 nsDisplayMaskGeometry::MoveBy(const nsPoint& aOffset)
 {
   mBounds.MoveBy(aOffset);
   mFrameOffsetToReferenceFrame += aOffset;
 }
 
+nsDisplayFilterGeometry::nsDisplayFilterGeometry(nsDisplayFilter* aItem, nsDisplayListBuilder* aBuilder)
+  : nsDisplayItemGeometry(aItem, aBuilder)
+  , nsImageGeometryMixin(aItem, aBuilder)
+  , mBBox(aItem->BBoxInUserSpace())
+  , mUserSpaceOffset(aItem->UserSpaceOffset())
+  , mFrameOffsetToReferenceFrame(aItem->ToReferenceFrame())
+{}
+
+void
+nsDisplayFilterGeometry::MoveBy(const nsPoint& aOffset)
+{
+  mBounds.MoveBy(aOffset);
+  mFrameOffsetToReferenceFrame += aOffset;
+}
+
 nsCharClipGeometry::nsCharClipGeometry(nsCharClipDisplayItem* aItem, nsDisplayListBuilder* aBuilder)
   : nsDisplayItemGenericGeometry(aItem, aBuilder)
   , mVisIStartEdge(aItem->mVisIStartEdge)
   , mVisIEndEdge(aItem->mVisIEndEdge)
 {}
 
 nsDisplayTableItemGeometry::nsDisplayTableItemGeometry(nsDisplayTableItem* aItem,
                                                        nsDisplayListBuilder* aBuilder,
--- a/layout/base/nsDisplayListInvalidation.h
+++ b/layout/base/nsDisplayListInvalidation.h
@@ -12,19 +12,20 @@
 #include "nsRect.h"
 #include "nsColor.h"
 #include "gfxRect.h"
 
 class nsDisplayBackgroundImage;
 class nsCharClipDisplayItem;
 class nsDisplayItem;
 class nsDisplayListBuilder;
-class nsDisplaySVGEffects;
 class nsDisplayTableItem;
 class nsDisplayThemedBackground;
+class nsDisplayMask;
+class nsDisplayFilter;
 
 namespace mozilla {
 namespace gfx {
 struct Color;
 }
 }
 
 /**
@@ -264,17 +265,31 @@ public:
   nsRegion mRegion;
   mozilla::gfx::Color mColor;
 };
 
 class nsDisplayMaskGeometry : public nsDisplayItemGeometry
   , public nsImageGeometryMixin<nsDisplayMaskGeometry>
 {
 public:
-  nsDisplayMaskGeometry(nsDisplaySVGEffects* aItem, nsDisplayListBuilder* aBuilder);
+  nsDisplayMaskGeometry(nsDisplayMask* aItem, nsDisplayListBuilder* aBuilder);
+
+  virtual void MoveBy(const nsPoint& aOffset) override;
+
+  gfxRect mBBox;
+  gfxPoint mUserSpaceOffset;
+  nsPoint mFrameOffsetToReferenceFrame;
+};
+
+class nsDisplayFilterGeometry : public nsDisplayItemGeometry
+  , public nsImageGeometryMixin<nsDisplayMaskGeometry>
+{
+public:
+  nsDisplayFilterGeometry(nsDisplayFilter* aItem,
+                          nsDisplayListBuilder* aBuilder);
 
   virtual void MoveBy(const nsPoint& aOffset) override;
 
   gfxRect mBBox;
   gfxPoint mUserSpaceOffset;
   nsPoint mFrameOffsetToReferenceFrame;
 };