Prior to this patch, CSSAnimation defined a method for converting an
nsCSSPseudoElements::Type to a nsString (but only for the set of
pseudo-elements that can have animations). We would like to re-use this
when setting up transition events so this patch moves it to
AnimationCollection. Re-using this method more widely means we can make
a few further simplifications to the code.
This patch extracts a utility class for queueing up a series of EventInfo
objects (of templated type) and then dispatching them. This covers the event
queuing behavior in nsAnimationManager so that we can reuse it in
nsTransitionManager.
The long-term plan is to drop the mozilla::css namespace altogether. Before we
go to much further with refactoring code in AnimationCommon, we should drop
usage of the mozilla::css namespace. Specifically, this patch moves the
CommonAnimationManager and AnimValuesStyleRule classes to the mozilla namespace.
This patch prepares the way for script-generated events by making
event dispatch a separate process that happens after sampling animations.
This will allow us to sample animations from their associated timeline
(removing the need for a further manager to tracker script-generated
animations).
Furthermore, once we sample animations from timelines the order in which they
are sampled is likely to be more or less random so by making event dispatch at
separate step, we have an opportunity to sort the events and dispatch in
a consistent and sensible order. It also ensures that event callbacks will
not be run until all animations (including transitions) have been updated
ensuring they see a consistent view of timing properties.
This patch only affects event handling for CSS animations. Transitions will
be dealt with in a subsequent patch.
There was a bug introduced in to animation_utils.js in
https://hg.mozilla.org/mozilla-central/rev/496e867cd2cd (bug 1070745). This
patch fixes this bug so we can be sure testing events correctly before messing
with them.
The goal of ComputeCollapsedBStartMargin is to collapse all of the
margins that collapse with a block's top margin. It does this by
scanning forward through the child list until it finds something that
blocks collapsing; it descends into children through recursion. When we
find a non-empty block or line, we stop collapsing and report to the
parent that the child is non-empty so that it stops collapsing as well.
This patch changes our behavior when we have clearance to do the same
thing that we do for non-empty lines or blocks (which makes both
occurrences of |goto done| be preceded by the same code). Without the
patch we would fail to report being non-empty to the parent (and instead
report emptiness based on the IsEmpty() method). This meant that,
without the patch, if a block has a child with clearance but also has
IsEmpty() true, we would stop scanning margins in that block after the
clearance, but start searching again for margins in the block's parent,
starting with the block's bottom margin. This patch sets *aBlockIsEmpty
to true in that case so that we do not pick up again in the block's
parent (or, potentially, grandparent, etc.).
This was introduced in bug 209694 (gecko-dev 13a65028) but became unused
through bug 292295 (gecko-dev 4593df2a57) and bug 300030 (gecko-dev
31f18988).
After this change, we have ShallowSizeOf{In,Ex}cludingThis(), which don't do
anything to measure children. (They can be combined with iteration to measure
children.)
After this change, we have ShallowSizeOf{In,Ex}cludingThis(), which don't do
anything to measure children. (They can be combined with iteration to measure
children.)
And we still have the existing single-arg SizeOf{In,Ex}cluding() functions,
which work if the entry type itself defines SizeOfExcludingThis().
This is because patch 4 now uses AddAndRemoveTransform hints for changes
that are other than adding and removing a transform. There's still a
little bit of transform-related stuff there too (which I did make
conditional in patch 2).
As expected, without the patch in patch 4, the filter and perspective
tests fail, but the added transform test passes. All the tests pass
locally with patch 4.
Note that this now uses AddAndRemoveTransform hints for changes that are
other than adding and removing a transform. Since there's still a
little bit of transform-related stuff there too (which I did make
conditional), I figure it's probably best to leave the name as-is,
although I'd be open to renaming it as well.
As expected, without the patch, the filter and perspective tests fail,
but the added transform test passes. All the tests pass locally with
the patch.
This adds an additional retry loop in block reflow that we can only
trigger when reflowing a block formatting context (replacedBlock
non-null). It can retry in two different ways, either with a narrower
width but at the same vertical position (when
ReplacedBlockFitsInAvailSpace is still true) or at a new vertical
position (which is treated as a form of clearance).
Fortunately we don't have to worry about margins collapsing *through*
such a boundary since we're dealing with a new block formatting context.
Note that Chromium passes all of the new bfc-displace-* tests, although
it moves the block formating context down unnecessarily in
bfc-shrink-1.html (which we do neither before nor after the patch),
though agrees with the width we have after the patch (but not before the
patch).
This is a temporary preference to allow for testing-in-the-wild by a larger
audience, for nightly builds. When 1177263 is fixed this can be removed.
---
layout/style/nsCSSParser.cpp | 14 ++++++++++++++
modules/libpref/init/all.js | 6 ++++++
2 files changed, 20 insertions(+)
After this change, we have PLDHashTable::ShallowSizeOf{In,Ex}cludingThis(),
which don't do anything to measure children. (They can be combined with
iteration to measure children.)
This patch also removes the PL_DHashTableSizeOf{In,Ex}cludingThis() functions.
They're not necessary because the methods can be used instead.
Finally, the patch deliberately converts some SizeOfExcludingThis() calls to
SizeOfIncludingThis(). These are all done on heap pointers so this change is
valid.
Bug 960465 (specifically part 6, changeset 7d16f2fd8329) changed the way we
process animation-only style changes. This caused us to update SMIL animations
more often than is needed.
This patch adjusts this behavior to update the style from SMIL animations less
frequently by tracking when animated values have been composited without adding
the corresponding changes to a restyle tracker.
Bug 1176077 introduced the parameter aDirtyRegion to
DrawPaintedLayerCallback, which allows the callback to recompute the
visibility of all items to be painted in that transaction in a single
go. However, this parameter can not always be determined correctly
when using RotatedBuffer, and using an incorrect value was causing
graphical glitches.
Make the parameter optional, and on null values do not perform the
optimisation. Pass null from ClientPaintedLayer, which uses
RotatedBuffer and was causing problems, but continue to pass the
correct value from other Layer implementations. This optimisation was
most important for tiled layers using progressive paint, so this is
okay.
When the refresh driver ticks it clears the RAF callbacks (content asks for another RAF if it desires) but it wasn't checking if it should exit high precision mode at this point.
The previous code seemed like it was using the wrong model that a RAF is persistent until it is revoked. But that is not the case.
This makes it clearer that, unlike how SizeOf*() functions usually work, this
doesn't measure any children hanging off the array.
And do likewise for nsTObserverArray.
AppendScrollPartsTo finds or creates a scroll id for the current scroll frame if IsMaybeScrollingActive() is true (otherwise it uses the null scrollid). IsMaybeScrollingActive() looks at mShouldBuildScrollableLayer, which we compute after the first call to AppendScrollPartsTo in ScrollFrameHelper::BuildDisplayList.
This means that on the first paint with a displayport set (or even if we create a displayport is ScrollFrameHelper::BuildDisplayList) we wouldn't layerize the scroll thumb in nsSliderFrame::BuildDisplayListForChildren because it looks for the current scroll id set on the display list builder. On subsequent paints this would be corrected so it caused reftest failures.
This patch causes transition events to be dispatched as a separate step after
sampling the transitions. Eventually this will allow us to sample transitions
from their timeline (independently of where they came from and in potentially
any order) by separating the concepts of sampling and event dispatch.
This patch moves the logic for queueing events out of the logic for flushing
transitions making it a separate step. It still doesn't delay the dispatch of
those events into a separate step, however. That is done in a subsequent patch.
This patch also makes sure to clear any queued events when the nsPresShell that
owns the transition manager is destroyed. We don't expect CSSTransition::Tick to
be called anywhere except nsTransitionManger::FlushTransitions so there
shouldn't be any orphaned events but for completeness it seems best to add this
now. (Later, when we tick transitions from their timeline we will need this.)
This patch introduces a separate flag to CSSTransition for tracking if a
transition is newly-finished so we can correctly dispatch the transitionend
event. Although, this may seem to be redundant with the "IsFinishedTransition"
we also track, that state will soon be removed in bug 1181392 and hence this
flag will be needed then.
Note that Animation already has flags mIsPreviousStateFinished and
mFinishedAtLastComposeStyle which would appear to be similar however,
- mIsPreviousStateFinished will be removed in bug 1178665 and is updated more
often than we queue events so it is not useful here.
- mFinishedAtLastComposeStyle is used to determine if we can throttle a style
update and is also updated more frequently than we queue events and hence
can't be used here.
Once we guarantee one call to Tick() per frame we may be able to simplify this
by tracking "state on last tick" but for now we need this additional flag on
CSSTransition. CSSAnimation has a similar flag for this
(mPreviousPhaseOrIteration) which we may be able to unify at the same point.
This simply uses the DelayedEventDispatcher in place of the previous array of
TransitionEventInfo objects. Doing the actual delayed dispatch is performed in
a separate patch.
Prior to this patch, CSSAnimation defined a method for converting an
nsCSSPseudoElements::Type to a nsString (but only for the set of
pseudo-elements that can have animations). We would like to re-use this
when setting up transition events so this patch moves it to
AnimationCollection. Re-using this method more widely means we can make
a few further simplifications to the code.
This patch extracts a utility class for queueing up a series of EventInfo
objects (of templated type) and then dispatching them. This covers the event
queuing behavior in nsAnimationManager so that we can reuse it in
nsTransitionManager.
The long-term plan is to drop the mozilla::css namespace altogether. Before we
go to much further with refactoring code in AnimationCommon, we should drop
usage of the mozilla::css namespace. Specifically, this patch moves the
CommonAnimationManager and AnimValuesStyleRule classes to the mozilla namespace.
This patch prepares the way for script-generated events by making
event dispatch a separate process that happens after sampling animations.
This will allow us to sample animations from their associated timeline
(removing the need for a further manager to tracker script-generated
animations).
Furthermore, once we sample animations from timelines the order in which they
are sampled is likely to be more or less random so by making event dispatch at
separate step, we have an opportunity to sort the events and dispatch in
a consistent and sensible order. It also ensures that event callbacks will
not be run until all animations (including transitions) have been updated
ensuring they see a consistent view of timing properties.
This patch only affects event handling for CSS animations. Transitions will
be dealt with in a subsequent patch.
There was a bug introduced in to animation_utils.js in
https://hg.mozilla.org/mozilla-central/rev/496e867cd2cd (bug 1070745). This
patch fixes this bug so we can be sure testing events correctly before messing
with them.
Without this change, nsBlockFrame::ReflowBlockFrame will fail to have
mayNeedRetry true, which means that it won't set
blockHTMLRS.mDiscoveredClearance, which means that on a descendant
replaced block we will fail to fall into any of the cases that call
ClearFloats. This change will cause us to hit the first ClearFloats
call and discover the need for clearance.
I tested locally that the new reftest fails without the patch and passes
with the patch.
We were returning a nullptr from AllocPRenderFrameParent in TabParent, which causes
a killhard abort in the child. We suspect this is occurring because the TabParent
is attempting to kick off drawing in a tab that's already closed (so there is no
frame loader, which means we can't create a PRenderFrameParent). So now, we return
a PRenderFrameParent* even if constructing it was unsuccessful, and the child
destroys it once it confirms that there is an invalid layer ID associated with
the RenderFrame.
We don't currently have a mechanism for rerendering when the front/back
flips, so we should disable running such animations on the compositor
thread for now until we do.
Bug 1186204 covers reenabling.
The reftest fails without the patch (showing a blue almost-square
rectangle), and passes with the patch.
The use of reftest-no-flush (added in patch 1) is needed to achieve the
failure without the patch, because the flushWindow() function in
reftest-content.js calls getBoundingClientRect() to flush rendering,
which has the side-effect of flushing style updates that have been
suppressed on the main thread while we're running an animation off the
main thread, which in turn covers up the bug.
FrameLayerManager::RecomputeItemsVisibility() was being called on every
call to FrameLayerBuilder::DrawPaintedLayer(), each time for the region
to be painted by that paint call. This is inefficient when progressive
paint is enabled. Change it so that we compute the visibility of all the
layer's items within the total region to be painted, but only on the
first paint after the display list has been modified.
I confirmed that the patch fixes the original testcase (attachment
8634600). I also confirmed that with the whole patch,
layout/style/test/test_descriptor_syntax_errors.html passes, but with
the new tests but not the code change, it reports 12 failures.
The MobileViewportManager ("MVM") is responsible for setting the CSS viewport on
any of the following events:
- a page is painted for the first time (on the before-first-paint event)
- a meta-viewport tag is added (on the DOMMetaAdded event)
- the full-zoom is changed (on the FullZoomChanged event)
- if the window is resized (ResizeReflow gets called as part of normal layout
processing, and this will pick up a new CSS viewport from MVM)
If the CSS viewport changes or if it is the initial paint, the MVM additionally
calls SetResolutionAndScaleTo on the presShell to update the displayed zoom.
The APZ code in AsyncPanZoomController::NotifyLayersUpdated already has
corresponding code to accept this updated zoom when the CSS viewport changes.