Bug 1300338: Do not attempt to preserve layer content when we're going to override it in a blend operation anyway. r=jrmuizel draft
authorBas Schouten <bschouten@mozilla.com>
Mon, 12 Sep 2016 18:41:10 +0200
changeset 412679 0201b307ccc25f7d9ec40dd426effdaca586bb3b
parent 412678 7f3a9e2318555b99f355f0bd84a0e62c0459ed91
child 531045 736198ced4e3425e38430dccbaaacc94fe17ee90
push id29234
push userbschouten@mozilla.com
push dateMon, 12 Sep 2016 16:42:10 +0000
reviewersjrmuizel
bugs1300338
milestone51.0a1
Bug 1300338: Do not attempt to preserve layer content when we're going to override it in a blend operation anyway. r=jrmuizel MozReview-Commit-ID: DIEyrK89jtd
gfx/2d/DrawTargetD2D1.cpp
gfx/2d/DrawTargetD2D1.h
--- a/gfx/2d/DrawTargetD2D1.cpp
+++ b/gfx/2d/DrawTargetD2D1.cpp
@@ -1313,17 +1313,19 @@ DrawTargetD2D1::FinalizeDrawing(Composit
     RefPtr<ID2D1Effect> blendEffect;
     HRESULT hr = mDC->CreateEffect(CLSID_D2D1Blend, getter_AddRefs(blendEffect));
 
     if (FAILED(hr) || !blendEffect) {
       gfxWarning() << "Failed to create blend effect!";
       return;
     }
 
-    RefPtr<ID2D1Image> tmpImage = GetImageForLayerContent();
+    // We don't need to preserve the current content of this layer as the output
+    // of the blend effect should completely replace it.
+    RefPtr<ID2D1Image> tmpImage = GetImageForLayerContent(false);
 
     blendEffect->SetInput(0, tmpImage);
     blendEffect->SetInput(1, source);
     blendEffect->SetValue(D2D1_BLEND_PROP_MODE, D2DBlendMode(aOp));
 
     mDC->DrawImage(blendEffect, D2D1_INTERPOLATION_MODE_NEAREST_NEIGHBOR, D2D1_COMPOSITE_MODE_BOUNDED_SOURCE_COPY);
 
     // This may seem a little counter intuitive. If this is false, we go through the regular
@@ -1402,17 +1404,17 @@ DrawTargetD2D1::GetDeviceSpaceClipRect(D
     if (!iter->mIsPixelAligned) {
       aIsPixelAligned = false;
     }
   }
   return true;
 }
 
 already_AddRefed<ID2D1Image>
-DrawTargetD2D1::GetImageForLayerContent()
+DrawTargetD2D1::GetImageForLayerContent(bool aShouldPreserveContent)
 {
   if (!CurrentLayer().mCurrentList) {
     RefPtr<ID2D1Bitmap> tmpBitmap;
     HRESULT hr = mDC->CreateBitmap(D2DIntSize(mSize), D2D1::BitmapProperties(D2DPixelFormat(mFormat)), getter_AddRefs(tmpBitmap));
     if (FAILED(hr)) {
       gfxCriticalError(CriticalLog::DefaultOptions(Factory::ReasonableSurfaceSize(mSize))) << "[D2D1.1] 6CreateBitmap failure " << mSize << " Code: " << hexa(hr) << " format " << (int)mFormat;
       // For now, crash in this scenario; this should happen because tmpBitmap is
       // null and CopyFromBitmap call below dereferences it.
@@ -1439,17 +1441,20 @@ DrawTargetD2D1::GetImageForLayerContent(
       mDC->CreateBitmap(mBitmap->GetPixelSize(), nullptr, 0, &props, getter_AddRefs(tmpBitmap));
       mDC->SetTransform(D2D1::IdentityMatrix());
       mDC->SetTarget(tmpBitmap);
       mDC->DrawImage(list, D2D1_INTERPOLATION_MODE_NEAREST_NEIGHBOR, D2D1_COMPOSITE_MODE_BOUNDED_SOURCE_COPY);
       mDC->SetTarget(CurrentTarget());
     }
 
     DCCommandSink sink(mDC);
-    list->Stream(&sink);
+
+    if (aShouldPreserveContent) {
+      list->Stream(&sink);
+    }
 
     PushAllClips();
 
     if (mDidComplexBlendWithListInList) {
       return tmpBitmap.forget();
     }
 
     return list.forget();
--- a/gfx/2d/DrawTargetD2D1.h
+++ b/gfx/2d/DrawTargetD2D1.h
@@ -179,17 +179,17 @@ private:
     if (mTransformDirty) {
       mDC->SetTransform(D2DMatrix(mTransform));
       mTransformDirty = false;
     }
   }
   void AddDependencyOnSource(SourceSurfaceD2D1* aSource);
 
   // Must be called with all clips popped and an identity matrix set.
-  already_AddRefed<ID2D1Image> GetImageForLayerContent();
+  already_AddRefed<ID2D1Image> GetImageForLayerContent(bool aShouldPreserveContent = true);
 
   ID2D1Image* CurrentTarget()
   {
     if (CurrentLayer().mCurrentList) {
       return CurrentLayer().mCurrentList;
     }
     return mBitmap;
   }