Bug 1565904. Move the blob metadata from image space to an absolute space. r=nical

This is a follow up to bug 1564655. It removes the offset from ToDeviceSpace
and thus moves item rects into absolute space which is now the same coordinate
space as the recordings are in.

We also adjust item bounds for fallback blobs.

Some additional changes that need happen to:

1. In Moz2DImageRenderer we can reunify the origin because the recording and
the recording metadata return to using the same coordinate space.

2. The calls to PushLayer can return to using the item bounds
which are now in the same coordinate space.

3. This dirty rect which remains in images space is adjusted during merging.

Differential Revision: https://phabricator.services.mozilla.com/D38015

--HG--
extra : moz-landing-system : lando
This commit is contained in:
Jeff Muizelaar 2019-07-15 15:24:54 +00:00
Родитель fb2fb2496b
Коммит 81db073a18
3 изменённых файлов: 60 добавлений и 67 удалений

Просмотреть файл

@ -305,8 +305,7 @@ struct DIGroup {
ScrollableLayerGuid::ViewID mScrollId; ScrollableLayerGuid::ViewID mScrollId;
LayerPoint mResidualOffset; LayerPoint mResidualOffset;
LayerIntRect mLayerBounds; LayerIntRect mLayerBounds;
// The current bounds of the blob image, relative to // The current bounds of the blob image
// the top-left of the mLayerBounds.
IntRect mImageBounds; IntRect mImageBounds;
// mImageBounds clipped to the container/parent of the // mImageBounds clipped to the container/parent of the
// current item being processed. // current item being processed.
@ -348,16 +347,14 @@ struct DIGroup {
} }
static IntRect ToDeviceSpace(nsRect aBounds, Matrix& aMatrix, static IntRect ToDeviceSpace(nsRect aBounds, Matrix& aMatrix,
int32_t aAppUnitsPerDevPixel, int32_t aAppUnitsPerDevPixel) {
LayerIntPoint aOffset) {
// RoundedOut can convert empty rectangles to non-empty ones // RoundedOut can convert empty rectangles to non-empty ones
// so special case them here // so special case them here
if (aBounds.IsEmpty()) { if (aBounds.IsEmpty()) {
return IntRect(); return IntRect();
} }
return RoundedOut(aMatrix.TransformBounds(ToRect( return RoundedOut(aMatrix.TransformBounds(
nsLayoutUtils::RectToGfxRect(aBounds, aAppUnitsPerDevPixel)))) - ToRect(nsLayoutUtils::RectToGfxRect(aBounds, aAppUnitsPerDevPixel))));
aOffset.ToUnknownPoint();
} }
void ComputeGeometryChange(nsDisplayItem* aItem, BlobItemData* aData, void ComputeGeometryChange(nsDisplayItem* aItem, BlobItemData* aData,
@ -372,14 +369,12 @@ struct DIGroup {
int32_t appUnitsPerDevPixel = int32_t appUnitsPerDevPixel =
aItem->Frame()->PresContext()->AppUnitsPerDevPixel(); aItem->Frame()->PresContext()->AppUnitsPerDevPixel();
MOZ_RELEASE_ASSERT(mAppUnitsPerDevPixel == appUnitsPerDevPixel); MOZ_RELEASE_ASSERT(mAppUnitsPerDevPixel == appUnitsPerDevPixel);
LayoutDeviceRect bounds =
LayoutDeviceRect::FromAppUnits(mGroupBounds, appUnitsPerDevPixel);
LayoutDeviceIntPoint offset = RoundedToInt(bounds.TopLeft());
GP("\n"); GP("\n");
GP("CGC offset %d %d\n", offset.x, offset.y);
GP("clippedImageRect %d %d %d %d\n", mClippedImageBounds.x, GP("clippedImageRect %d %d %d %d\n", mClippedImageBounds.x,
mClippedImageBounds.y, mClippedImageBounds.width, mClippedImageBounds.y, mClippedImageBounds.width,
mClippedImageBounds.height); mClippedImageBounds.height);
LayerIntSize size = mLayerBounds.Size();
GP("imageSize: %d %d\n", size.width, size.height);
/*if (aItem->IsReused() && aData->mGeometry) { /*if (aItem->IsReused() && aData->mGeometry) {
return; return;
}*/ }*/
@ -397,12 +392,12 @@ struct DIGroup {
geometry->ComputeInvalidationRegion()); geometry->ComputeInvalidationRegion());
aData->mGeometry = std::move(geometry); aData->mGeometry = std::move(geometry);
IntRect transformedRect = ToDeviceSpace( IntRect transformedRect =
clippedBounds, aMatrix, appUnitsPerDevPixel, mLayerBounds.TopLeft()); ToDeviceSpace(clippedBounds, aMatrix, appUnitsPerDevPixel);
aData->mRect = transformedRect.Intersect(mClippedImageBounds); aData->mRect = transformedRect.Intersect(mClippedImageBounds);
GP("CGC %s %d %d %d %d\n", aItem->Name(), clippedBounds.x, GP("CGC %s %d %d %d %d\n", aItem->Name(), clippedBounds.x,
clippedBounds.y, clippedBounds.width, clippedBounds.height); clippedBounds.y, clippedBounds.width, clippedBounds.height);
GP("%d %d, %f %f\n", mLayerBounds.TopLeft().x, mLayerBounds.TopLeft().y, GP("%d %d, %f %f\n", mPaintRect.TopLeft().x, mPaintRect.TopLeft().y,
aMatrix._11, aMatrix._22); aMatrix._11, aMatrix._22);
GP("mRect %d %d %d %d\n", aData->mRect.x, aData->mRect.y, GP("mRect %d %d %d %d\n", aData->mRect.x, aData->mRect.y,
aData->mRect.width, aData->mRect.height); aData->mRect.width, aData->mRect.height);
@ -411,7 +406,6 @@ struct DIGroup {
} else if (aData->mInvalid || } else if (aData->mInvalid ||
/* XXX: handle image load invalidation */ ( /* XXX: handle image load invalidation */ (
aItem->IsInvalid(invalid) && invalid.IsEmpty())) { aItem->IsInvalid(invalid) && invalid.IsEmpty())) {
MOZ_RELEASE_ASSERT(mLayerBounds.TopLeft() == aData->mGroupOffset);
UniquePtr<nsDisplayItemGeometry> geometry( UniquePtr<nsDisplayItemGeometry> geometry(
aItem->AllocateGeometry(aBuilder)); aItem->AllocateGeometry(aBuilder));
nsRect clippedBounds = clip.ApplyNonRoundedIntersection( nsRect clippedBounds = clip.ApplyNonRoundedIntersection(
@ -427,15 +421,14 @@ struct DIGroup {
// matrix? // matrix?
// XXX: TransformBounds is expensive. We should avoid doing it if we have // XXX: TransformBounds is expensive. We should avoid doing it if we have
// no transform // no transform
IntRect transformedRect = ToDeviceSpace( IntRect transformedRect =
clippedBounds, aMatrix, appUnitsPerDevPixel, mLayerBounds.TopLeft()); ToDeviceSpace(clippedBounds, aMatrix, appUnitsPerDevPixel);
aData->mRect = transformedRect.Intersect(mClippedImageBounds); aData->mRect = transformedRect.Intersect(mClippedImageBounds);
InvalidateRect(aData->mRect); InvalidateRect(aData->mRect);
GP("new rect: %d %d %d %d\n", aData->mRect.x, aData->mRect.y, GP("new rect: %d %d %d %d\n", aData->mRect.x, aData->mRect.y,
aData->mRect.width, aData->mRect.height); aData->mRect.width, aData->mRect.height);
aData->mInvalid = true; aData->mInvalid = true;
} else { } else {
MOZ_RELEASE_ASSERT(mLayerBounds.TopLeft() == aData->mGroupOffset);
GP("else invalidate: %s\n", aItem->Name()); GP("else invalidate: %s\n", aItem->Name());
nsRegion combined; nsRegion combined;
// this includes situations like reflow changing the position // this includes situations like reflow changing the position
@ -456,8 +449,7 @@ struct DIGroup {
nsRect clippedBounds = clip.ApplyNonRoundedIntersection( nsRect clippedBounds = clip.ApplyNonRoundedIntersection(
aData->mGeometry->ComputeInvalidationRegion()); aData->mGeometry->ComputeInvalidationRegion());
IntRect transformedRect = IntRect transformedRect =
ToDeviceSpace(clippedBounds, aMatrix, appUnitsPerDevPixel, ToDeviceSpace(clippedBounds, aMatrix, appUnitsPerDevPixel);
mLayerBounds.TopLeft());
aData->mRect = transformedRect.Intersect(mClippedImageBounds); aData->mRect = transformedRect.Intersect(mClippedImageBounds);
InvalidateRect(aData->mRect); InvalidateRect(aData->mRect);
@ -487,8 +479,7 @@ struct DIGroup {
nsRect clippedBounds = clip.ApplyNonRoundedIntersection( nsRect clippedBounds = clip.ApplyNonRoundedIntersection(
aData->mGeometry->ComputeInvalidationRegion()); aData->mGeometry->ComputeInvalidationRegion());
IntRect transformedRect = IntRect transformedRect =
ToDeviceSpace(clippedBounds, aMatrix, appUnitsPerDevPixel, ToDeviceSpace(clippedBounds, aMatrix, appUnitsPerDevPixel);
mLayerBounds.TopLeft());
InvalidateRect(aData->mRect.Intersect(mImageBounds)); InvalidateRect(aData->mRect.Intersect(mImageBounds));
aData->mRect = transformedRect.Intersect(mClippedImageBounds); aData->mRect = transformedRect.Intersect(mClippedImageBounds);
InvalidateRect(aData->mRect); InvalidateRect(aData->mRect);
@ -517,8 +508,7 @@ struct DIGroup {
nsRect clippedBounds = clip.ApplyNonRoundedIntersection( nsRect clippedBounds = clip.ApplyNonRoundedIntersection(
aData->mGeometry->ComputeInvalidationRegion()); aData->mGeometry->ComputeInvalidationRegion());
IntRect transformedRect = IntRect transformedRect =
ToDeviceSpace(clippedBounds, aMatrix, appUnitsPerDevPixel, ToDeviceSpace(clippedBounds, aMatrix, appUnitsPerDevPixel);
mLayerBounds.TopLeft());
InvalidateRect(aData->mRect.Intersect(mImageBounds)); InvalidateRect(aData->mRect.Intersect(mImageBounds));
aData->mRect = transformedRect.Intersect(mClippedImageBounds); aData->mRect = transformedRect.Intersect(mClippedImageBounds);
InvalidateRect(aData->mRect); InvalidateRect(aData->mRect);
@ -536,8 +526,7 @@ struct DIGroup {
geometry->ComputeInvalidationRegion()); geometry->ComputeInvalidationRegion());
aData->mGeometry = std::move(geometry); aData->mGeometry = std::move(geometry);
IntRect transformedRect = IntRect transformedRect =
ToDeviceSpace(clippedBounds, aMatrix, appUnitsPerDevPixel, ToDeviceSpace(clippedBounds, aMatrix, appUnitsPerDevPixel);
mLayerBounds.TopLeft());
InvalidateRect(aData->mRect.Intersect(mImageBounds)); InvalidateRect(aData->mRect.Intersect(mImageBounds));
aData->mRect = transformedRect.Intersect(mClippedImageBounds); aData->mRect = transformedRect.Intersect(mClippedImageBounds);
InvalidateRect(aData->mRect); InvalidateRect(aData->mRect);
@ -547,8 +536,7 @@ struct DIGroup {
nsRect clippedBounds = clip.ApplyNonRoundedIntersection( nsRect clippedBounds = clip.ApplyNonRoundedIntersection(
geometry->ComputeInvalidationRegion()); geometry->ComputeInvalidationRegion());
IntRect transformedRect = IntRect transformedRect =
ToDeviceSpace(clippedBounds, aMatrix, appUnitsPerDevPixel, ToDeviceSpace(clippedBounds, aMatrix, appUnitsPerDevPixel);
mLayerBounds.TopLeft());
// The invalid rect should contain the old rect and the new rect // The invalid rect should contain the old rect and the new rect
// but may not because the parent may have been removed. // but may not because the parent may have been removed.
InvalidateRect(aData->mRect); InvalidateRect(aData->mRect);
@ -560,8 +548,7 @@ struct DIGroup {
nsRect clippedBounds = clip.ApplyNonRoundedIntersection( nsRect clippedBounds = clip.ApplyNonRoundedIntersection(
geometry->ComputeInvalidationRegion()); geometry->ComputeInvalidationRegion());
IntRect transformedRect = IntRect transformedRect =
ToDeviceSpace(clippedBounds, aMatrix, appUnitsPerDevPixel, ToDeviceSpace(clippedBounds, aMatrix, appUnitsPerDevPixel);
mLayerBounds.TopLeft());
auto rect = transformedRect.Intersect(mClippedImageBounds); auto rect = transformedRect.Intersect(mClippedImageBounds);
GP("Layer NoChange: %s %d %d %d %d\n", aItem->Name(), GP("Layer NoChange: %s %d %d %d %d\n", aItem->Name(),
aData->mRect.x, aData->mRect.y, aData->mRect.XMost(), aData->mRect.x, aData->mRect.y, aData->mRect.XMost(),
@ -575,8 +562,7 @@ struct DIGroup {
nsRect clippedBounds = clip.ApplyNonRoundedIntersection( nsRect clippedBounds = clip.ApplyNonRoundedIntersection(
geometry->ComputeInvalidationRegion()); geometry->ComputeInvalidationRegion());
IntRect transformedRect = IntRect transformedRect =
ToDeviceSpace(clippedBounds, aMatrix, appUnitsPerDevPixel, ToDeviceSpace(clippedBounds, aMatrix, appUnitsPerDevPixel);
mLayerBounds.TopLeft());
// The invalid rect should contain the old rect and the new rect // The invalid rect should contain the old rect and the new rect
// but may not because the parent may have been removed. // but may not because the parent may have been removed.
InvalidateRect(aData->mRect); InvalidateRect(aData->mRect);
@ -590,18 +576,17 @@ struct DIGroup {
nsRect clippedBounds = clip.ApplyNonRoundedIntersection( nsRect clippedBounds = clip.ApplyNonRoundedIntersection(
geometry->ComputeInvalidationRegion()); geometry->ComputeInvalidationRegion());
IntRect transformedRect = IntRect transformedRect =
ToDeviceSpace(clippedBounds, aMatrix, appUnitsPerDevPixel, ToDeviceSpace(clippedBounds, aMatrix, appUnitsPerDevPixel);
mLayerBounds.TopLeft());
auto rect = transformedRect.Intersect(mClippedImageBounds); auto rect = transformedRect.Intersect(mClippedImageBounds);
GP("NoChange: %s %d %d %d %d\n", aItem->Name(), aData->mRect.x, GP("NoChange: %s %d %d %d %d vs %d %d %d %d\n", aItem->Name(), rect.x,
aData->mRect.y, aData->mRect.XMost(), aData->mRect.YMost()); rect.y, rect.XMost(), rect.YMost(), aData->mRect.x, aData->mRect.y,
aData->mRect.XMost(), aData->mRect.YMost());
MOZ_RELEASE_ASSERT(rect.IsEqualEdges(aData->mRect)); MOZ_RELEASE_ASSERT(rect.IsEqualEdges(aData->mRect));
} }
} }
} }
aData->mClip = clip; aData->mClip = clip;
aData->mMatrix = aMatrix; aData->mMatrix = aMatrix;
aData->mGroupOffset = mLayerBounds.TopLeft();
aData->mImageRect = mClippedImageBounds; aData->mImageRect = mClippedImageBounds;
GP("post mInvalidRect: %d %d %d %d\n", mInvalidRect.x, mInvalidRect.y, GP("post mInvalidRect: %d %d %d %d\n", mInvalidRect.x, mInvalidRect.y,
mInvalidRect.width, mInvalidRect.height); mInvalidRect.width, mInvalidRect.height);
@ -630,22 +615,25 @@ struct DIGroup {
} }
} }
IntSize dtSize = mLayerBounds.Size().ToUnknownSize();
// The actual display item's size shouldn't have the scale factored in
// Round the bounds out to leave space for unsnapped content // Round the bounds out to leave space for unsnapped content
LayoutDeviceToLayerScale2D scale(mScale.width, mScale.height); LayoutDeviceToLayerScale2D scale(mScale.width, mScale.height);
LayerIntRect layerBounds = mLayerBounds; LayoutDeviceRect itemBounds =
IntSize dtSize = layerBounds.Size().ToUnknownSize(); (LayerRect(mLayerBounds) - mResidualOffset) / scale;
LayoutDeviceRect bounds =
(LayerRect(layerBounds) - mResidualOffset) / scale;
if (mInvalidRect.IsEmpty()) { if (mInvalidRect.IsEmpty()) {
GP("Not repainting group because it's empty\n"); GP("Not repainting group because it's empty\n");
GP("End EndGroup\n"); GP("End EndGroup\n");
if (mKey) { if (mKey) {
// Although the contents haven't changed, the visible area *may* have,
// so request it be updated unconditionally (wr should be able to easily
// detect if this is a no-op on its side, if that matters)
aResources.SetBlobImageVisibleArea( aResources.SetBlobImageVisibleArea(
mKey.value().second(), mKey.value().second(),
ViewAs<ImagePixel>(mPaintRect, ViewAs<ImagePixel>(mPaintRect,
PixelCastJustification::LayerIsImage)); PixelCastJustification::LayerIsImage));
PushImage(aBuilder, bounds); PushImage(aBuilder, itemBounds);
} }
return; return;
} }
@ -681,7 +669,9 @@ struct DIGroup {
recorder, dummyDt, mLayerBounds.ToUnknownRect()); recorder, dummyDt, mLayerBounds.ToUnknownRect());
// Setup the gfxContext // Setup the gfxContext
RefPtr<gfxContext> context = gfxContext::CreateOrNull(dt); RefPtr<gfxContext> context = gfxContext::CreateOrNull(dt);
context->SetMatrix(Matrix::Scaling(mScale.width, mScale.height).PostTranslate(mResidualOffset.x, mResidualOffset.y)); context->SetMatrix(
Matrix::Scaling(mScale.width, mScale.height)
.PostTranslate(mResidualOffset.x, mResidualOffset.y));
GP("mInvalidRect: %d %d %d %d\n", mInvalidRect.x, mInvalidRect.y, GP("mInvalidRect: %d %d %d %d\n", mInvalidRect.x, mInvalidRect.y,
mInvalidRect.width, mInvalidRect.height); mInvalidRect.width, mInvalidRect.height);
@ -728,7 +718,13 @@ struct DIGroup {
mKey = Some(MakePair(aBuilder.GetRenderRoot(), key)); mKey = Some(MakePair(aBuilder.GetRenderRoot(), key));
} else { } else {
wr::ImageDescriptor descriptor(dtSize, 0, dt->GetFormat(), opacity); wr::ImageDescriptor descriptor(dtSize, 0, dt->GetFormat(), opacity);
auto bottomRight = mInvalidRect.BottomRight();
// Convert mInvalidRect to image space by subtracting the corner of the
// image bounds
auto dirtyRect = ViewAs<ImagePixel>(
mInvalidRect - mLayerBounds.ToUnknownRect().TopLeft());
auto bottomRight = dirtyRect.BottomRight();
GP("check invalid %d %d - %d %d\n", bottomRight.x, bottomRight.y, GP("check invalid %d %d - %d %d\n", bottomRight.x, bottomRight.y,
dtSize.width, dtSize.height); dtSize.width, dtSize.height);
MOZ_RELEASE_ASSERT(bottomRight.x <= dtSize.width && MOZ_RELEASE_ASSERT(bottomRight.x <= dtSize.width &&
@ -739,7 +735,7 @@ struct DIGroup {
mKey.value().second(), descriptor, bytes, mKey.value().second(), descriptor, bytes,
ViewAs<ImagePixel>(mPaintRect, ViewAs<ImagePixel>(mPaintRect,
PixelCastJustification::LayerIsImage), PixelCastJustification::LayerIsImage),
ViewAs<ImagePixel>(mInvalidRect))) { dirtyRect)) {
return; return;
} }
} }
@ -748,7 +744,7 @@ struct DIGroup {
aResources.SetBlobImageVisibleArea( aResources.SetBlobImageVisibleArea(
mKey.value().second(), mKey.value().second(),
ViewAs<ImagePixel>(mPaintRect, PixelCastJustification::LayerIsImage)); ViewAs<ImagePixel>(mPaintRect, PixelCastJustification::LayerIsImage));
PushImage(aBuilder, bounds); PushImage(aBuilder, itemBounds);
GP("End EndGroup\n\n"); GP("End EndGroup\n\n");
} }
@ -965,7 +961,7 @@ void Grouper::PaintContainerItem(DIGroup* aGroup, nsDisplayItem* aItem,
aContext->GetDrawTarget()->PushLayer(false, opacityItem->GetOpacity(), aContext->GetDrawTarget()->PushLayer(false, opacityItem->GetOpacity(),
nullptr, mozilla::gfx::Matrix(), nullptr, mozilla::gfx::Matrix(),
aItemBounds + aGroup->mLayerBounds.ToUnknownRect().TopLeft()); aItemBounds);
GP("beginGroup %s %p-%d\n", aItem->Name(), aItem->Frame(), GP("beginGroup %s %p-%d\n", aItem->Name(), aItem->Frame(),
aItem->GetPerFrameKey()); aItem->GetPerFrameKey());
aContext->GetDrawTarget()->FlushItem(aItemBounds); aContext->GetDrawTarget()->FlushItem(aItemBounds);
@ -981,7 +977,7 @@ void Grouper::PaintContainerItem(DIGroup* aGroup, nsDisplayItem* aItem,
auto blendItem = static_cast<nsDisplayBlendMode*>(aItem); auto blendItem = static_cast<nsDisplayBlendMode*>(aItem);
auto blendMode = blendItem->BlendMode(); auto blendMode = blendItem->BlendMode();
aContext->GetDrawTarget()->PushLayerWithBlend( aContext->GetDrawTarget()->PushLayerWithBlend(
false, 1.0, nullptr, mozilla::gfx::Matrix(), aItemBounds + aGroup->mLayerBounds.ToUnknownRect().TopLeft(), false, false, 1.0, nullptr, mozilla::gfx::Matrix(), aItemBounds, false,
blendMode); blendMode);
GP("beginGroup %s %p-%d\n", aItem->Name(), aItem->Frame(), GP("beginGroup %s %p-%d\n", aItem->Name(), aItem->Frame(),
aItem->GetPerFrameKey()); aItem->GetPerFrameKey());
@ -996,7 +992,7 @@ void Grouper::PaintContainerItem(DIGroup* aGroup, nsDisplayItem* aItem,
} }
case DisplayItemType::TYPE_BLEND_CONTAINER: { case DisplayItemType::TYPE_BLEND_CONTAINER: {
aContext->GetDrawTarget()->PushLayer(false, 1.0, nullptr, aContext->GetDrawTarget()->PushLayer(false, 1.0, nullptr,
mozilla::gfx::Matrix(), aItemBounds + aGroup->mLayerBounds.ToUnknownRect().TopLeft()); mozilla::gfx::Matrix(), aItemBounds);
GP("beginGroup %s %p-%d\n", aItem->Name(), aItem->Frame(), GP("beginGroup %s %p-%d\n", aItem->Name(), aItem->Frame(),
aItem->GetPerFrameKey()); aItem->GetPerFrameKey());
aContext->GetDrawTarget()->FlushItem(aItemBounds); aContext->GetDrawTarget()->FlushItem(aItemBounds);
@ -1518,8 +1514,7 @@ void WebRenderCommandBuilder::DoGroupingForDisplayList(
group.mLayerBounds = LayerIntRect::FromUnknownRect( group.mLayerBounds = LayerIntRect::FromUnknownRect(
ScaleToOutsidePixelsOffset(group.mGroupBounds, scale.width, scale.height, ScaleToOutsidePixelsOffset(group.mGroupBounds, scale.width, scale.height,
group.mAppUnitsPerDevPixel, residualOffset)); group.mAppUnitsPerDevPixel, residualOffset));
group.mImageBounds = group.mImageBounds = group.mLayerBounds.ToUnknownRect();
IntRect(0, 0, group.mLayerBounds.width, group.mLayerBounds.height);
group.mClippedImageBounds = group.mImageBounds; group.mClippedImageBounds = group.mImageBounds;
const nsRect& untransformedPaintRect = const nsRect& untransformedPaintRect =
@ -1530,10 +1525,7 @@ void WebRenderCommandBuilder::DoGroupingForDisplayList(
untransformedPaintRect, scale.width, scale.height, untransformedPaintRect, scale.width, scale.height,
group.mAppUnitsPerDevPixel, residualOffset)) group.mAppUnitsPerDevPixel, residualOffset))
.Intersect(group.mLayerBounds); .Intersect(group.mLayerBounds);
// XXX: Make the paint rect relative to the layer bounds. After we include
// mLayerBounds.TopLeft() in the blob image we want to stop doing this
// adjustment.
group.mPaintRect = group.mPaintRect - group.mLayerBounds.TopLeft();
g.mTransform = Matrix::Scaling(scale.width, scale.height) g.mTransform = Matrix::Scaling(scale.width, scale.height)
.PostTranslate(residualOffset.x, residualOffset.y); .PostTranslate(residualOffset.x, residualOffset.y);
group.mScale = scale; group.mScale = scale;
@ -2292,7 +2284,7 @@ WebRenderCommandBuilder::GenerateFallbackData(
isInvalidated = true; isInvalidated = true;
} }
} }
recorder->FlushItem(IntRect({0, 0}, dtSize.ToUnknownSize())); recorder->FlushItem(dtRect.ToUnknownRect());
recorder->Finish(); recorder->Finish();
if (!validFonts) { if (!validFonts) {

Просмотреть файл

@ -369,10 +369,9 @@ static bool Moz2DRenderCallback(const Range<const uint8_t> aBlob,
// them because of CompositorHitTestInfo and merging. // them because of CompositorHitTestInfo and merging.
size_t footerSize = sizeof(size_t) + sizeof(IntPoint); size_t footerSize = sizeof(size_t) + sizeof(IntPoint);
MOZ_RELEASE_ASSERT(aBlob.length() >= footerSize); MOZ_RELEASE_ASSERT(aBlob.length() >= footerSize);
size_t indexOffset = size_t indexOffset = ConvertFromBytes<size_t>(aBlob.end().get() - footerSize);
ConvertFromBytes<size_t>(aBlob.end().get() - footerSize); IntPoint origin = ConvertFromBytes<IntPoint>(aBlob.end().get() - footerSize +
IntPoint recordingOrigin = sizeof(size_t));
ConvertFromBytes<IntPoint>(aBlob.end().get() - footerSize + sizeof(size_t));
// Apply the visibleRect's offset to make (0, 0) in the DT correspond to (0, // Apply the visibleRect's offset to make (0, 0) in the DT correspond to (0,
// 0) in the texture // 0) in the texture
@ -380,20 +379,17 @@ static bool Moz2DRenderCallback(const Range<const uint8_t> aBlob,
Reader reader(aBlob.begin().get() + indexOffset, Reader reader(aBlob.begin().get() + indexOffset,
aBlob.length() - footerSize - indexOffset); aBlob.length() - footerSize - indexOffset);
IntPoint origin;
if (aTileOffset) { if (aTileOffset) {
origin += origin +=
gfx::IntPoint(aTileOffset->x * *aTileSize, aTileOffset->y * *aTileSize); gfx::IntPoint(aTileOffset->x * *aTileSize, aTileOffset->y * *aTileSize);
} }
dt = gfx::Factory::CreateOffsetDrawTarget(dt, recordingOrigin + origin); dt = gfx::Factory::CreateOffsetDrawTarget(dt, origin);
auto bounds = gfx::IntRect(origin, aSize); auto bounds = gfx::IntRect(origin, aSize);
if (aDirtyRect) { if (aDirtyRect) {
Rect dirty(aDirtyRect->origin.x + recordingOrigin.x, Rect dirty(aDirtyRect->origin.x, aDirtyRect->origin.y,
aDirtyRect->origin.y + recordingOrigin.y, aDirtyRect->size.width, aDirtyRect->size.height);
aDirtyRect->size.width,
aDirtyRect->size.height);
dt->PushClipRect(dirty); dt->PushClipRect(dirty);
bounds = bounds.Intersect( bounds = bounds.Intersect(
IntRect(aDirtyRect->origin.x, aDirtyRect->origin.y, IntRect(aDirtyRect->origin.x, aDirtyRect->origin.y,

Просмотреть файл

@ -380,7 +380,7 @@ impl<'a> CachedReader<'a> {
/// the first not-yet-copied item with those bounds in the old list and copy that. /// the first not-yet-copied item with those bounds in the old list and copy that.
/// Any items found in the old list but not the new one can be safely assumed to /// Any items found in the old list but not the new one can be safely assumed to
/// have been deleted. /// have been deleted.
fn merge_blob_images(old_buf: &[u8], new_buf: &[u8], dirty_rect: Box2d) -> Vec<u8> { fn merge_blob_images(old_buf: &[u8], new_buf: &[u8], mut dirty_rect: Box2d) -> Vec<u8> {
let mut result = BlobWriter::new(); let mut result = BlobWriter::new();
dlog!("dirty rect: {:?}", dirty_rect); dlog!("dirty rect: {:?}", dirty_rect);
@ -395,6 +395,11 @@ fn merge_blob_images(old_buf: &[u8], new_buf: &[u8], dirty_rect: Box2d) -> Vec<u
// we currently only support merging blobs that have the same origin // we currently only support merging blobs that have the same origin
assert_eq!(old_reader.reader.origin, new_reader.origin); assert_eq!(old_reader.reader.origin, new_reader.origin);
dirty_rect.x1 += new_reader.origin.x;
dirty_rect.y1 += new_reader.origin.y;
dirty_rect.x2 += new_reader.origin.x;
dirty_rect.y2 += new_reader.origin.y;
// Loop over both new and old entries merging them. // Loop over both new and old entries merging them.
// Both new and old must have the same number of entries that // Both new and old must have the same number of entries that
// overlap but are not contained by the dirty rect, and they // overlap but are not contained by the dirty rect, and they