Bug 1656419 - Check whether the given animation and the animation stored in mPartialPrerenderedAnimations are in the same EffectSet instead of just comparing the animation instances. r=boris

Differential Revision: https://phabricator.services.mozilla.com/D85535
This commit is contained in:
Hiroyuki Ikezoe
2020-07-31 21:06:42 +00:00
parent 00530bed53
commit 2f624f98b8
6 changed files with 52 additions and 3 deletions

View File

@@ -124,6 +124,16 @@ EffectSet* EffectSet::GetEffectSetForStyleFrame(const nsIFrame* aStyleFrame) {
return GetEffectSet(target->mElement, target->mPseudoType); return GetEffectSet(target->mElement, target->mPseudoType);
} }
/* static */
EffectSet* EffectSet::GetEffectSetForEffect(const KeyframeEffect* aEffect) {
NonOwningAnimationTarget target = aEffect->GetAnimationTarget();
if (!target) {
return nullptr;
}
return EffectSet::GetEffectSet(target.mElement, target.mPseudoType);
}
/* static */ /* static */
void EffectSet::DestroyEffectSet(dom::Element* aElement, void EffectSet::DestroyEffectSet(dom::Element* aElement,
PseudoStyleType aPseudoType) { PseudoStyleType aPseudoType) {

View File

@@ -89,6 +89,8 @@ class EffectSet {
// to use this. // to use this.
static EffectSet* GetEffectSetForStyleFrame(const nsIFrame* aStyleFrame); static EffectSet* GetEffectSetForStyleFrame(const nsIFrame* aStyleFrame);
static EffectSet* GetEffectSetForEffect(const dom::KeyframeEffect* aEffect);
static void DestroyEffectSet(dom::Element* aElement, static void DestroyEffectSet(dom::Element* aElement,
PseudoStyleType aPseudoType); PseudoStyleType aPseudoType);

View File

@@ -904,8 +904,12 @@ void KeyframeEffect::UpdateTarget(Element* aElement,
} }
if (mTarget) { if (mTarget) {
UnregisterTarget(); // Call ResetIsRunningOnCompositor() prior to UnregisterTarget() since
// ResetIsRunningOnCompositor() might try to get the EffectSet associated
// with this keyframe effect to remove partial pre-render animation from
// the layer manager.
ResetIsRunningOnCompositor(); ResetIsRunningOnCompositor();
UnregisterTarget();
RequestRestyle(EffectCompositor::RestyleType::Layer); RequestRestyle(EffectCompositor::RestyleType::Layer);

View File

@@ -0,0 +1,23 @@
<!DOCTYPE html>
<html class="reftest-wait">
<style>
#target {
width: 200vw;
height: 200vh;
}
</style>
<div id="target"></div>
<script>
const animA = target.animate(
{ transform: 'translateX(100px)' },
{ duration: 50 }
);
const animB = target.animate(
{ transform: 'translateX(100px)', composite: 'add' },
{ duration: 100 }
);
animB.finished.then(() => {
document.documentElement.classList.remove("reftest-wait");
});
</script>
</html>

View File

@@ -53,3 +53,4 @@ pref(dom.animations-api.core.enabled,true) load 1612891-2.html
pref(dom.animations-api.core.enabled,true) load 1612891-3.html pref(dom.animations-api.core.enabled,true) load 1612891-3.html
pref(dom.animations-api.core.enabled,true) pref(dom.animations-api.getAnimations.enabled,true) load 1633442.html pref(dom.animations-api.core.enabled,true) pref(dom.animations-api.getAnimations.enabled,true) load 1633442.html
pref(dom.animations-api.core.enabled,true) pref(dom.animations-api.implicit-keyframes.enabled,true) load 1633486.html pref(dom.animations-api.core.enabled,true) pref(dom.animations-api.implicit-keyframes.enabled,true) load 1633486.html
pref(layout.animation.prerender.partial,true) load 1656419.html

View File

@@ -25,6 +25,8 @@
#include "mozilla/Telemetry.h" // for Accumulate #include "mozilla/Telemetry.h" // for Accumulate
#include "mozilla/ToString.h" #include "mozilla/ToString.h"
#include "mozilla/dom/Animation.h" // for dom::Animation #include "mozilla/dom/Animation.h" // for dom::Animation
#include "mozilla/dom/KeyframeEffect.h" // for dom::Animation
#include "mozilla/EffectSet.h" // for dom::Animation
#include "mozilla/gfx/2D.h" // for DrawTarget #include "mozilla/gfx/2D.h" // for DrawTarget
#include "mozilla/gfx/BaseSize.h" // for BaseSize #include "mozilla/gfx/BaseSize.h" // for BaseSize
#include "mozilla/gfx/Matrix.h" // for Matrix4x4 #include "mozilla/gfx/Matrix.h" // for Matrix4x4
@@ -180,8 +182,15 @@ void LayerManager::RemovePartialPrerenderedAnimation(
#ifdef DEBUG #ifdef DEBUG
RefPtr<dom::Animation> animation; RefPtr<dom::Animation> animation;
if (mPartialPrerenderedAnimations.Remove(aCompositorAnimationId, if (mPartialPrerenderedAnimations.Remove(aCompositorAnimationId,
getter_AddRefs(animation))) { getter_AddRefs(animation)) &&
MOZ_ASSERT(aAnimation == animation.get()); // It may be possible that either animation's effect has already been
// nulled out via Animation::SetEffect() so ignore such cases.
aAnimation->GetEffect() && aAnimation->GetEffect()->AsKeyframeEffect() &&
animation->GetEffect() && animation->GetEffect()->AsKeyframeEffect()) {
MOZ_ASSERT(EffectSet::GetEffectSetForEffect(
aAnimation->GetEffect()->AsKeyframeEffect()) ==
EffectSet::GetEffectSetForEffect(
animation->GetEffect()->AsKeyframeEffect()));
} }
#else #else
mPartialPrerenderedAnimations.Remove(aCompositorAnimationId); mPartialPrerenderedAnimations.Remove(aCompositorAnimationId);