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
--- 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;
}