Bug 1406183 - Add a boolean aIsInactiveLayerManager to FrameLayerBuilder so that IsBuildingRetainedLayers can return false for inactive layer managers even if there is no containing PaintedLayerData. r=mattwoodrow
authorMarkus Stange <mstange@themasta.com>
Fri, 06 Oct 2017 18:32:30 -0400
changeset 428124 62d565a1c99a793688060b75ab6d13f41e5ed78c
parent 428123 8ad5d399ad84ce019270a2174cfb6016ab2d6c45
child 428125 0db7e0090021692f2f7f5f23c6f30ae877700d26
push id97
push userfmarier@mozilla.com
push dateSat, 14 Oct 2017 01:12:59 +0000
reviewersmattwoodrow
bugs1406183
milestone58.0a1
Bug 1406183 - Add a boolean aIsInactiveLayerManager to FrameLayerBuilder so that IsBuildingRetainedLayers can return false for inactive layer managers even if there is no containing PaintedLayerData. r=mattwoodrow MozReview-Commit-ID: KkrEXLD85iP
gfx/layers/wr/WebRenderCommandBuilder.cpp
layout/painting/FrameLayerBuilder.cpp
layout/painting/FrameLayerBuilder.h
layout/reftests/bugs/1406183-1-ref.html
layout/reftests/bugs/1406183-1.html
layout/reftests/bugs/reftest.list
--- a/gfx/layers/wr/WebRenderCommandBuilder.cpp
+++ b/gfx/layers/wr/WebRenderCommandBuilder.cpp
@@ -349,17 +349,17 @@ PaintItemByDrawTarget(nsDisplayItem* aIt
     break;
   case DisplayItemType::TYPE_FILTER:
     {
       if (aManager == nullptr) {
         aManager = new BasicLayerManager(BasicLayerManager::BLM_INACTIVE);
       }
 
       FrameLayerBuilder* layerBuilder = new FrameLayerBuilder();
-      layerBuilder->Init(aDisplayListBuilder, aManager);
+      layerBuilder->Init(aDisplayListBuilder, aManager, nullptr, true);
       layerBuilder->DidBeginRetainedLayerTransaction(aManager);
 
       aManager->BeginTransactionWithTarget(context);
 
       ContainerLayerParameters param;
       RefPtr<Layer> layer =
         static_cast<nsDisplayFilter*>(aItem)->BuildLayer(aDisplayListBuilder,
                                                          aManager, param);
--- a/layout/painting/FrameLayerBuilder.cpp
+++ b/layout/painting/FrameLayerBuilder.cpp
@@ -118,16 +118,17 @@ static inline MaskLayerImageCache* GetMa
 
 FrameLayerBuilder::FrameLayerBuilder()
   : mRetainingManager(nullptr)
   , mContainingPaintedLayer(nullptr)
   , mInactiveLayerClip(nullptr)
   , mDetectedDOMModification(false)
   , mInvalidateAllLayers(false)
   , mInLayerTreeCompressionMode(false)
+  , mIsInactiveLayerManager(false)
   , mContainerLayerGeneration(0)
   , mMaxContainerLayerGeneration(0)
 {
   MOZ_COUNT_CTOR(FrameLayerBuilder);
 }
 
 FrameLayerBuilder::~FrameLayerBuilder()
 {
@@ -1792,24 +1793,26 @@ FrameLayerBuilder::Shutdown()
     delete gMaskLayerImageCache;
     gMaskLayerImageCache = nullptr;
   }
 }
 
 void
 FrameLayerBuilder::Init(nsDisplayListBuilder* aBuilder, LayerManager* aManager,
                         PaintedLayerData* aLayerData,
+                        bool aIsInactiveLayerManager,
                         const DisplayItemClip* aInactiveLayerClip)
 {
   mDisplayListBuilder = aBuilder;
   mRootPresContext = aBuilder->RootReferenceFrame()->PresContext()->GetRootPresContext();
   if (mRootPresContext) {
     mInitialDOMGeneration = mRootPresContext->GetDOMGeneration();
   }
   mContainingPaintedLayer = aLayerData;
+  mIsInactiveLayerManager = aIsInactiveLayerManager;
   mInactiveLayerClip = aInactiveLayerClip;
   aManager->SetUserData(&gLayerManagerLayerBuilder, this);
 }
 
 void
 FrameLayerBuilder::FlashPaint(gfxContext *aContext)
 {
   float r = float(rand()) / RAND_MAX;
@@ -4705,17 +4708,18 @@ FrameLayerBuilder::AddPaintedDisplayItem
   if (entry) {
     entry->mContainerLayerFrame = aContainerState.GetContainerFrame();
     if (entry->mContainerLayerGeneration == 0) {
       entry->mContainerLayerGeneration = mContainerLayerGeneration;
     }
     if (tempManager) {
       FLB_LOG_PAINTED_LAYER_DECISION(aLayerData, "Creating nested FLB for item %p\n", aItem);
       FrameLayerBuilder* layerBuilder = new FrameLayerBuilder();
-      layerBuilder->Init(mDisplayListBuilder, tempManager, aLayerData, &aClip);
+      layerBuilder->Init(mDisplayListBuilder, tempManager, aLayerData, true,
+                         &aClip);
 
       tempManager->BeginTransaction();
       if (mRetainingManager) {
         layerBuilder->DidBeginRetainedLayerTransaction(tempManager);
       }
 
       UniquePtr<LayerProperties> props(LayerProperties::CloneFrom(tempManager->GetRoot()));
       RefPtr<Layer> tmpLayer =
--- a/layout/painting/FrameLayerBuilder.h
+++ b/layout/painting/FrameLayerBuilder.h
@@ -335,16 +335,17 @@ public:
 
   FrameLayerBuilder();
   ~FrameLayerBuilder();
 
   static void Shutdown();
 
   void Init(nsDisplayListBuilder* aBuilder, LayerManager* aManager,
             PaintedLayerData* aLayerData = nullptr,
+            bool aIsInactiveLayerManager = false,
             const DisplayItemClip* aInactiveLayerClip = nullptr);
 
   /**
    * Call this to notify that we have just started a transaction on the
    * retained layer manager aManager.
    */
   void DidBeginRetainedLayerTransaction(LayerManager* aManager);
 
@@ -725,17 +726,17 @@ public:
 
   const DisplayItemClip* GetInactiveLayerClip() const
   {
     return mInactiveLayerClip;
   }
 
   bool IsBuildingRetainedLayers()
   {
-    return !mContainingPaintedLayer && mRetainingManager;
+    return !mIsInactiveLayerManager && mRetainingManager;
   }
 
   /**
    * Attempt to build the most compressed layer tree possible, even if it means
    * throwing away existing retained buffers.
    */
   void SetLayerTreeCompressionMode() { mInLayerTreeCompressionMode = true; }
   bool CheckInLayerTreeCompressionMode();
@@ -794,15 +795,17 @@ protected:
   /**
    * Indicates that the entire layer tree should be rerendered
    * during this paint.
    */
   bool                                mInvalidateAllLayers;
 
   bool                                mInLayerTreeCompressionMode;
 
+  bool                                mIsInactiveLayerManager;
+
   uint32_t                            mContainerLayerGeneration;
   uint32_t                            mMaxContainerLayerGeneration;
 };
 
 } // namespace mozilla
 
 #endif /* FRAMELAYERBUILDER_H_ */
new file mode 100644
--- /dev/null
+++ b/layout/reftests/bugs/1406183-1-ref.html
@@ -0,0 +1,23 @@
+<!DOCTYPE html>
+<meta charset="utf-8">
+
+<title>Reference for bug 1406183: ImageLayer inside inactive BasicLayerManager for fallback nsDisplayFilter is drawn at the wrong position</title>
+
+<style>
+
+body {
+  margin: 0;
+}
+
+.outer {
+  margin-left: 100px;
+  margin-top: 50px;
+  width: 200px;
+  height: 200px;
+}
+
+</style>
+
+<div class="outer">
+  <img src="data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAAYAAAAGCAIAAABvrngfAAAAFklEQVQImWMwjWhCQwxECoW3oCHihAB0LyYv5/oAHwAAAABJRU5ErkJggg==">
+</div>
new file mode 100644
--- /dev/null
+++ b/layout/reftests/bugs/1406183-1.html
@@ -0,0 +1,30 @@
+<!DOCTYPE html>
+<meta charset="utf-8">
+
+<title>Testcase for bug 1406183: ImageLayer inside inactive BasicLayerManager for fallback nsDisplayFilter is drawn at the wrong position</title>
+
+<style>
+
+body {
+  margin: 0;
+}
+
+.outer {
+  margin-left: 100px;
+  margin-top: 50px;
+  width: 200px;
+  height: 200px;
+}
+
+.filter {
+  height: 200px;
+  filter: hue-rotate(0deg);
+}
+
+</style>
+
+<div class="outer">
+  <div class="filter">
+    <img src="data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAAYAAAAGCAIAAABvrngfAAAAFklEQVQImWMwjWhCQwxECoW3oCHihAB0LyYv5/oAHwAAAABJRU5ErkJggg==">
+  </div>
+</div>
--- a/layout/reftests/bugs/reftest.list
+++ b/layout/reftests/bugs/reftest.list
@@ -2040,8 +2040,9 @@ needs-focus != 1377447-1.html 1377447-2.
 == 1381821.html 1381821-ref.html
 == 1395650-1.html 1395650-1-ref.html
 == 1398500-1.html 1398500-1-ref.html
 == 1401317.html 1401317-ref.html
 == 1401992.html 1401992-ref.html
 == 1405878-1.xml 1405878-1-ref.xml
 == 1404057.html 1404057-ref.html
 != 1404057.html 1404057-noref.html
+== 1406183-1.html 1406183-1-ref.html