Bug 1141468 - Don't attempt to modify prerender state (for will-change) in nsDisplayTransform since it's already too late. r=BenWa,mstange

--HG--
extra : rebase_source : 62e38ec1e4fbfa4f92a008e16a85a7db5691b7ed
This commit is contained in:
Matt Woodrow 2016-05-18 15:12:14 +12:00
Родитель 37f3397832
Коммит 4258a918f0
3 изменённых файлов: 19 добавлений и 60 удалений

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

@ -3903,7 +3903,7 @@ ContainerState::ProcessDisplayItems(nsDisplayList* aList)
}
nsIntRect itemDrawRect = ScaleToOutsidePixels(itemContent, snap);
bool prerenderedTransform = itemType == nsDisplayItem::TYPE_TRANSFORM &&
static_cast<nsDisplayTransform*>(item)->ShouldPrerender(mBuilder);
static_cast<nsDisplayTransform*>(item)->ShouldPrerender();
ParentLayerIntRect clipRect;
const DisplayItemClip& itemClip = item->GetClip();
if (itemClip.HasClip()) {

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

@ -4305,7 +4305,7 @@ nsDisplayOpacity::BuildLayer(nsDisplayListBuilder* aBuilder,
static bool
IsItemTooSmallForActiveLayer(nsDisplayItem* aItem)
{
nsIntRect visibleDevPixels = aItem->GetVisibleRect().ToOutsidePixels(
nsIntRect visibleDevPixels = aItem->Frame()->GetVisualOverflowRectRelativeToSelf().ToOutsidePixels(
aItem->Frame()->PresContext()->AppUnitsPerDevPixel());
static const int MIN_ACTIVE_LAYER_SIZE_DEV_PIXELS = 16;
return visibleDevPixels.Size() <
@ -4318,7 +4318,7 @@ SetAnimationPerformanceWarningForTooSmallItem(nsDisplayItem* aItem,
{
// We use ToNearestPixels() here since ToOutsidePixels causes some sort of
// errors. See https://bugzilla.mozilla.org/show_bug.cgi?id=1258904#c19
nsIntRect visibleDevPixels = aItem->GetVisibleRect().ToNearestPixels(
nsIntRect visibleDevPixels = aItem->Frame()->GetVisualOverflowRectRelativeToSelf().ToNearestPixels(
aItem->Frame()->PresContext()->AppUnitsPerDevPixel());
// Set performance warning only if the visible dev pixels is not empty
@ -5318,18 +5318,10 @@ nsDisplayTransform::Init(nsDisplayListBuilder* aBuilder)
mHasBounds = false;
mStoredList.SetClip(aBuilder, DisplayItemClip::NoClip());
mStoredList.SetVisibleRect(mChildrenVisibleRect);
mMaybePrerender = ShouldPrerenderTransformedContent(aBuilder, mFrame);
const nsStyleDisplay* disp = mFrame->StyleDisplay();
if ((disp->mWillChangeBitField & NS_STYLE_WILL_CHANGE_TRANSFORM)) {
// We will only pre-render if this will-change is on budget.
mMaybePrerender = true;
}
if (mMaybePrerender) {
bool snap;
mVisibleRect = GetBounds(aBuilder, &snap);
}
// If this is true, then BuildDisplayListForStacking context should have already
// set the correct visible region and made sure we built all the necessary
// descendant display items.
mPrerender = ShouldPrerenderTransformedContent(aBuilder, mFrame);
}
nsDisplayTransform::nsDisplayTransform(nsDisplayListBuilder* aBuilder,
@ -5792,35 +5784,14 @@ nsDisplayOpacity::CanUseAsyncAnimations(nsDisplayListBuilder* aBuilder)
}
bool
nsDisplayTransform::ShouldPrerender(nsDisplayListBuilder* aBuilder) {
if (!mMaybePrerender) {
return false;
}
if (ShouldPrerenderTransformedContent(aBuilder, mFrame)) {
return true;
}
const nsStyleDisplay* disp = mFrame->StyleDisplay();
if ((disp->mWillChangeBitField & NS_STYLE_WILL_CHANGE_TRANSFORM) &&
aBuilder->IsInWillChangeBudget(mFrame, mFrame->GetSize())) {
return true;
}
return false;
nsDisplayTransform::ShouldPrerender() {
return mPrerender;
}
bool
nsDisplayTransform::CanUseAsyncAnimations(nsDisplayListBuilder* aBuilder)
{
if (mMaybePrerender) {
// TODO We need to make sure that if we use async animation we actually
// pre-render even if we're out of will change budget.
return true;
}
DebugOnly<bool> prerender = ShouldPrerenderTransformedContent(aBuilder, mFrame);
NS_ASSERTION(!prerender, "Something changed under us!");
return false;
return mPrerender;
}
/* static */ bool
@ -5964,7 +5935,7 @@ nsDisplayTransform::ShouldBuildLayerEvenIfInvisible(nsDisplayListBuilder* aBuild
// The visible rect of a Preserves-3D frame is just an intermediate
// result. It should always build a layer to make sure it is
// rendering correctly.
return ShouldPrerender(aBuilder) || mFrame->Combines3DTransformWithAncestors();
return ShouldPrerender() || mFrame->Combines3DTransformWithAncestors();
}
already_AddRefed<Layer> nsDisplayTransform::BuildLayer(nsDisplayListBuilder *aBuilder,
@ -5977,7 +5948,7 @@ already_AddRefed<Layer> nsDisplayTransform::BuildLayer(nsDisplayListBuilder *aBu
*/
const Matrix4x4& newTransformMatrix = GetTransformForRendering();
uint32_t flags = ShouldPrerender(aBuilder) ?
uint32_t flags = ShouldPrerender() ?
FrameLayerBuilder::CONTAINER_NOT_CLIPPED_BY_ANCESTORS : 0;
flags |= FrameLayerBuilder::CONTAINER_ALLOW_PULL_BACKGROUND_COLOR;
RefPtr<ContainerLayer> container = aManager->GetLayerBuilder()->
@ -5999,7 +5970,7 @@ already_AddRefed<Layer> nsDisplayTransform::BuildLayer(nsDisplayListBuilder *aBu
nsDisplayListBuilder::AddAnimationsAndTransitionsToLayer(container, aBuilder,
this, mFrame,
eCSSProperty_transform);
if (ShouldPrerender(aBuilder)) {
if (ShouldPrerender()) {
if (MayBeAnimated(aBuilder)) {
// Only allow async updates to the transform if we're an animated layer, since that's what
// triggers us to set the correct AGR in the constructor and makes sure FrameLayerBuilder
@ -6051,11 +6022,6 @@ nsDisplayTransform::GetLayerState(nsDisplayListBuilder* aBuilder,
return LAYER_ACTIVE_FORCE;
}
const nsStyleDisplay* disp = mFrame->StyleDisplay();
if ((disp->mWillChangeBitField & NS_STYLE_WILL_CHANGE_TRANSFORM)) {
return LAYER_ACTIVE;
}
// Expect the child display items to have this frame as their animated
// geometry root (since it will be their reference frame). If they have a
// different animated geometry root, we'll make this an active layer so the
@ -6072,7 +6038,7 @@ bool nsDisplayTransform::ComputeVisibility(nsDisplayListBuilder *aBuilder,
* think that it's painting in its original rectangular coordinate space.
* If we can't untransform, take the entire overflow rect */
nsRect untransformedVisibleRect;
if (ShouldPrerender(aBuilder) ||
if (ShouldPrerender() ||
!UntransformVisibleRect(aBuilder, &untransformedVisibleRect))
{
untransformedVisibleRect = mFrame->GetVisualOverflowRectRelativeToSelf();
@ -6218,7 +6184,7 @@ nsDisplayTransform::GetBounds(nsDisplayListBuilder* aBuilder, bool* aSnap)
return nsRect();
}
nsRect untransformedBounds = MaybePrerender() ?
nsRect untransformedBounds = ShouldPrerender() ?
mFrame->GetVisualOverflowRectRelativeToSelf() :
mStoredList.GetBounds(aBuilder, aSnap);
// GetTransform always operates in dev pixels.
@ -6257,7 +6223,7 @@ nsDisplayTransform::ComputeBounds(nsDisplayListBuilder* aBuilder)
* nsDisplayListBuilder.
*/
bool snap;
nsRect untransformedBounds = MaybePrerender() ?
nsRect untransformedBounds = ShouldPrerender() ?
mFrame->GetVisualOverflowRectRelativeToSelf() :
mStoredList.GetBounds(aBuilder, &snap);
// GetTransform always operates in dev pixels.
@ -6297,7 +6263,7 @@ nsRegion nsDisplayTransform::GetOpaqueRegion(nsDisplayListBuilder *aBuilder,
// covers the entire window, but it allows our transform to be
// updated extremely cheaply, without invalidating any other
// content.
if (MaybePrerender() ||
if (ShouldPrerender() ||
!UntransformVisibleRect(aBuilder, &untransformedVisible)) {
return nsRegion();
}

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

@ -4116,16 +4116,11 @@ public:
bool MayBeAnimated(nsDisplayListBuilder* aBuilder);
/**
* This will return if it's possible for this element to be prerendered.
* This should never return false if we're going to prerender.
*/
bool MaybePrerender() const { return mMaybePrerender; }
/**
* Check if this element will be prerendered. This must be done after the
* display list has been fully built.
*/
bool ShouldPrerender(nsDisplayListBuilder* aBuilder);
bool ShouldPrerender();
virtual void WriteDebugInfo(std::stringstream& aStream) override;
@ -4211,9 +4206,7 @@ private:
nsRect mBounds;
// True for mBounds is valid.
bool mHasBounds;
// We wont know if we pre-render until the layer building phase where we can
// check layers will-change budget.
bool mMaybePrerender;
bool mPrerender;
// Be forced not to extend 3D context. Since we don't create a
// transform item, a container layer, for every frames in a
// preserves3d context, the transform items of a child preserves3d