script: Properly root nodes with animating images (#37689)

This change fixes an issue and makes a few more minor improvements to
the `ImageAnimationState`:

1. Image rooting and unrooted now happens in one step from
   `Window::update_animations_post_reflow`.
2. The `node_to_animating_image_map` is now stored as a shared `RwLock`
   so that it doesn't need to be taken and then replaced in the
`ImageAnimationState` during reflow. This should prevent a hypothetical
issue
   where image animations are restarted during empty reflows.
3. General naming and idiomatic Rust usage improvements.

Testing: This doesn't really have any obvious behavioral changes,
because all
reflows currently trigger a restyle. It becomes a serious problem with
#37677
and this change fixes the failing test there.

Signed-off-by: Martin Robinson <mrobinson@igalia.com>
This commit is contained in:
Martin Robinson 2025-06-25 15:52:11 +02:00 committed by GitHub
parent b89a44c539
commit a66a257b38
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
10 changed files with 107 additions and 118 deletions

View file

@ -4189,7 +4189,7 @@ impl Document {
DomRefCell::new(AnimationTimeline::new())
},
animations: DomRefCell::new(Animations::new()),
image_animation_manager: DomRefCell::new(ImageAnimationManager::new()),
image_animation_manager: DomRefCell::new(ImageAnimationManager::default()),
dirty_root: Default::default(),
declarative_refresh: Default::default(),
pending_input_events: Default::default(),
@ -4960,6 +4960,7 @@ impl Document {
self.animations
.borrow()
.do_post_reflow_update(&self.window, self.current_animation_timeline_value());
self.image_animation_manager().update_rooted_dom_nodes();
}
pub(crate) fn cancel_animations_for_node(&self, node: &Node) {
@ -4998,12 +4999,9 @@ impl Document {
pub(crate) fn image_animation_manager(&self) -> Ref<ImageAnimationManager> {
self.image_animation_manager.borrow()
}
pub(crate) fn image_animation_manager_mut(&self) -> RefMut<ImageAnimationManager> {
self.image_animation_manager.borrow_mut()
}
pub(crate) fn update_animating_images(&self) {
let mut image_animation_manager = self.image_animation_manager.borrow_mut();
let image_animation_manager = self.image_animation_manager.borrow();
if !image_animation_manager.image_animations_present() {
return;
}
@ -5011,8 +5009,8 @@ impl Document {
.update_active_frames(&self.window, self.current_animation_timeline_value());
if !self.animations().animations_present() {
let next_scheduled_time =
image_animation_manager.next_schedule_time(self.current_animation_timeline_value());
let next_scheduled_time = image_animation_manager
.next_scheduled_time(self.current_animation_timeline_value());
// TODO: Once we have refresh signal from the compositor,
// we should get rid of timer for animated image update.
if let Some(next_scheduled_time) = next_scheduled_time {