Bug 1150807 part 4 - Don't play/pause an idle animation when animation-play-state changes; r=jwatt

This isn't spec'ed anywhere (since the whole Web Animations API <-> CSS
interaction isn't spec'ed yet) but it seems that changing animation-play-state
should not restart an idle animation.

If an author calls Cancel() on an animation then that animation should continue
to be idle until they call Play()/Pause() from the API. Cancelling an animation
and hanging on to it is a purely API-only feature and hence it's reasonable that
restoring it from this state is also an API-only feature.

One can imagine use-cases such as polyfilling where script wants to remove any
CSS Animations/Transitions run by the browser and replace them with something
else entirely. In that case, the script can call Cancel() on the animation and
be sure that the animation is going to stay out of the way even if something
else tweaks the animation-play-state.
This commit is contained in:
Brian Birtles 2015-04-27 08:53:19 +09:00
parent 97f87ec0a6
commit d40f32d326

View File

@ -25,6 +25,7 @@
using namespace mozilla;
using namespace mozilla::css;
using mozilla::dom::Animation;
using mozilla::dom::AnimationPlayState;
using mozilla::dom::KeyframeEffectReadonly;
using mozilla::CSSAnimation;
@ -49,7 +50,7 @@ CSSAnimation::Pause()
Animation::Pause();
}
mozilla::dom::AnimationPlayState
AnimationPlayState
CSSAnimation::PlayStateFromJS() const
{
// Flush style to ensure that any properties controlling animation state
@ -363,21 +364,24 @@ nsAnimationManager::CheckAnimationRule(nsStyleContext* aStyleContext,
// Reset compositor state so animation will be re-synchronized.
oldAnim->ClearIsRunningOnCompositor();
// Handle changes in play state.
// CSSAnimation takes care of override behavior so that,
// for example, if the author has called pause(), that will
// override the animation-play-state.
// (We should check newAnim->IsStylePaused() but that requires
// downcasting to CSSAnimation and we happen to know that
// newAnim will only ever be paused by calling PauseFromStyle
// making IsPausedOrPausing synonymous in this case.)
if (!oldAnim->IsStylePaused() && newAnim->IsPausedOrPausing()) {
oldAnim->PauseFromStyle();
animationChanged = true;
} else if (oldAnim->IsStylePaused() &&
!newAnim->IsPausedOrPausing()) {
oldAnim->PlayFromStyle();
animationChanged = true;
// Handle changes in play state. If the animation is idle, however,
// changes to animation-play-state should *not* restart it.
if (oldAnim->PlayState() != AnimationPlayState::Idle) {
// CSSAnimation takes care of override behavior so that,
// for example, if the author has called pause(), that will
// override the animation-play-state.
// (We should check newAnim->IsStylePaused() but that requires
// downcasting to CSSAnimation and we happen to know that
// newAnim will only ever be paused by calling PauseFromStyle
// making IsPausedOrPausing synonymous in this case.)
if (!oldAnim->IsStylePaused() && newAnim->IsPausedOrPausing()) {
oldAnim->PauseFromStyle();
animationChanged = true;
} else if (oldAnim->IsStylePaused() &&
!newAnim->IsPausedOrPausing()) {
oldAnim->PlayFromStyle();
animationChanged = true;
}
}
if (animationChanged) {