Bug 1234485 - Part 5. Implement MaskImageData::CreateImageAndImageContainer. r=mstange
authorcku <cku@mozilla.com>
Wed, 26 Oct 2016 22:17:24 +0800
changeset 351727 bf9e4704d56944b640b454eb8b2a6a6316e95e73
parent 351726 42ed9b2fcf5b81ec50587ef10b0b10a5426afc9e
child 351728 6e607ef327c8fbb3a5ae7d5896c3bde01e7c2c8a
push id6795
push userjlund@mozilla.com
push dateMon, 23 Jan 2017 14:19:46 +0000
treeherdermozilla-esr52@76101b503191 [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
reviewersmstange
bugs1234485
milestone52.0a1
Bug 1234485 - Part 5. Implement MaskImageData::CreateImageAndImageContainer. r=mstange Simply move some code from ContainerState::CreateMaskLayer into MaskImageData, so that we can reuse it later. MozReview-Commit-ID: H2zktYL9PIh
layout/base/FrameLayerBuilder.cpp
--- a/layout/base/FrameLayerBuilder.cpp
+++ b/layout/base/FrameLayerBuilder.cpp
@@ -1522,39 +1522,45 @@ struct MaskLayerUserData : public LayerU
   nsTArray<DisplayItemClip::RoundedRect> mRoundedClipRects;
   // scale from the masked layer which is applied to the mask
   float mScaleX, mScaleY;
   // The ContainerLayerParameters offset which is applied to the mask's transform.
   nsIntPoint mOffset;
   int32_t mAppUnitsPerDevPixel;
 };
 
+/*
+ * A helper object to create a draw target for painting mask and create a
+ * image container to hold the drawing result. The caller can then bind this
+ * image container with a image mask layer via ImageLayer::SetContainer.
+ */
 class MaskImageData
 {
 public:
   MaskImageData(const gfx::IntSize& aSize, LayerManager* aLayerManager)
     : mTextureClientLocked(false)
     , mSize(aSize)
     , mLayerManager(aLayerManager)
   {
+    MOZ_ASSERT(!mSize.IsEmpty());
+    MOZ_ASSERT(mLayerManager);
   }
 
   ~MaskImageData()
   {
     if (mTextureClientLocked) {
       MOZ_ASSERT(mTextureClient);
       // Clear DrawTarget before Unlock.
       mDrawTarget = nullptr;
       mTextureClient->Unlock();
     }
   }
 
   gfx::DrawTarget* CreateDrawTarget()
   {
-    MOZ_ASSERT(mLayerManager);
     if (mDrawTarget) {
       return mDrawTarget;
     }
 
     if (mLayerManager->GetBackendType() == LayersBackend::LAYERS_BASIC) {
       mDrawTarget = mLayerManager->CreateOptimalMaskDrawTarget(mSize);
       return mDrawTarget;
     }
@@ -1580,16 +1586,30 @@ public:
     if (!mTextureClientLocked) {
       return nullptr;
     }
 
     mDrawTarget = mTextureClient->BorrowDrawTarget();
     return mDrawTarget;
   }
 
+  already_AddRefed<ImageContainer> CreateImageAndImageContainer()
+  {
+    RefPtr<ImageContainer> container = mLayerManager->CreateImageContainer();
+    RefPtr<Image> image = CreateImage();
+
+    if (!image) {
+      return nullptr;
+    }
+    container->SetCurrentImageInTransaction(image);
+
+    return container.forget();
+  }
+
+private:
   already_AddRefed<Image> CreateImage()
   {
     if (mLayerManager->GetBackendType() == LayersBackend::LAYERS_BASIC &&
         mDrawTarget) {
       RefPtr<SourceSurface> surface = mDrawTarget->Snapshot();
       RefPtr<SourceSurfaceImage> image = new SourceSurfaceImage(mSize, surface);
       // Disallow BIGIMAGE (splitting into multiple textures) for mask
       // layer images
@@ -1599,20 +1619,20 @@ public:
 
     if (mLayerManager->GetBackendType() == LayersBackend::LAYERS_CLIENT &&
         mTextureClient &&
         mDrawTarget) {
       RefPtr<TextureWrapperImage> image =
           new TextureWrapperImage(mTextureClient, gfx::IntRect(gfx::IntPoint(0, 0), mSize));
       return image.forget();
     }
+
     return nullptr;
   }
 
-private:
   bool mTextureClientLocked;
   gfx::IntSize mSize;
   LayerManager* mLayerManager;
   RefPtr<gfx::DrawTarget> mDrawTarget;
   RefPtr<TextureClient> mTextureClient;
 };
 
 /**
@@ -6109,24 +6129,23 @@ ContainerState::CreateMaskLayer(Layer *a
     // paint the clipping rects with alpha to create the mask
     aClip.FillIntersectionOfRoundedRectClips(context,
                                              Color(1.f, 1.f, 1.f, 1.f),
                                              newData.mAppUnitsPerDevPixel,
                                              0,
                                              aRoundedRectClipCount);
 
     // build the image and container
-    container = aLayer->Manager()->CreateImageContainer();
+    MOZ_ASSERT(aLayer->Manager() == mManager);
+    container = imageData.CreateImageAndImageContainer();
     NS_ASSERTION(container, "Could not create image container for mask layer.");
 
-    RefPtr<Image> image = imageData.CreateImage();
-    if (!image) {
+    if (!container) {
       return nullptr;
     }
-    container->SetCurrentImageInTransaction(image);
 
     GetMaskLayerImageCache()->PutImage(newKey.forget(), container);
   }
 
   maskLayer->SetContainer(container);
 
   maskTransform.Invert();
   Matrix4x4 matrix = Matrix4x4::From2D(maskTransform);