From 6a7c0b7e9c075e34dd89f0b789b88ef205a445c8 Mon Sep 17 00:00:00 2001 From: Boris Chiou Date: Mon, 4 May 2020 19:15:43 +0000 Subject: [PATCH] style: Add ::marker when checking may_have_animations() during traversal. When unhidding a ::marker element, we construct its generated item, and then call StyleNewSubtree() on this generated item. During traversal, we may update any animation related values in Gecko_UpdateAnimations(), which may update the base styles for animation properties. The test case is an animation segment from "null" to "inital" value. We replace the "null" value with the base style value for the specific animation property, so we can do interpolation properly. (e.g. opacity: "null => initial" becomes "1.0 => initial") If we don't update the animation related values in Gecko_UpdateAnimations after generating ::marker, we may do interpolation from "null" to "initial", which causes a panic. Differential Revision: https://phabricator.services.mozilla.com/D73408 --- components/style/gecko/pseudo_element.rs | 6 ++++++ components/style/gecko/wrapper.rs | 2 +- 2 files changed, 7 insertions(+), 1 deletion(-) diff --git a/components/style/gecko/pseudo_element.rs b/components/style/gecko/pseudo_element.rs index d989380c02ea..3ca06eea37ef 100644 --- a/components/style/gecko/pseudo_element.rs +++ b/components/style/gecko/pseudo_element.rs @@ -92,6 +92,12 @@ impl PseudoElement { EAGER_PSEUDOS[i].clone() } + /// Whether the current pseudo element is animatable. + #[inline] + pub fn is_animatable(&self) -> bool { + matches!(*self, Self::Before | Self::After | Self::Marker) + } + /// Whether the current pseudo element is ::before or ::after. #[inline] pub fn is_before_or_after(&self) -> bool { diff --git a/components/style/gecko/wrapper.rs b/components/style/gecko/wrapper.rs index a5472fadd668..af3173f92d11 100644 --- a/components/style/gecko/wrapper.rs +++ b/components/style/gecko/wrapper.rs @@ -1446,7 +1446,7 @@ impl<'le> TElement for GeckoElement<'le> { #[inline] fn may_have_animations(&self) -> bool { if let Some(pseudo) = self.implemented_pseudo_element() { - if !pseudo.is_before_or_after() { + if !pseudo.is_animatable() { return false; } // FIXME(emilio): When would the parent of a ::before / ::after