[mutter/wip/carlosg/queue-redraw-fix: 2/2] clutter: Keep actors dirty if a redraw was queued up during paint()
- From: Carlos Garnacho <carlosg src gnome org>
- To: commits-list gnome org
- Cc:
- Subject: [mutter/wip/carlosg/queue-redraw-fix: 2/2] clutter: Keep actors dirty if a redraw was queued up during paint()
- Date: Wed, 30 Mar 2022 19:38:01 +0000 (UTC)
commit 6eb903fd8eda1cb41ba553937a4481a78cd46ebd
Author: Carlos Garnacho <carlosg gnome org>
Date: Wed Mar 30 21:02:18 2022 +0200
clutter: Keep actors dirty if a redraw was queued up during paint()
In the right combination of circumstances, and given 2 actors (parent
actor P with an offscreen effect and child actor C), we may have the
following situation happening:
- A redraw is queued on the actor C, actors C and P are marked as
priv->is_dirty and priv->propagated_one_redraw.
- During paint() handling we paint actor P, priv->propagated_one_redraw
is turned off.
- We recurse into child actor C, priv->propagated_one_redraw is turned
off.
- A new redraw is queued on actor C, actors C and P are marked as
priv->is_dirty and priv->propagated_one_redraw.
- The paint() method recurses back, actors C and P get priv->is_dirty
disabled, priv->propagated_one_redraw remains set.
- At this point queueing up more redraws on actor C will not propagate
up, because actor C has priv->propagated_one_redraw set, but the
parent actor P has priv->is_dirty unset, so the offscreen effect will
not get CLUTTER_EFFECT_PAINT_ACTOR_DIRTY and will avoid repainting
actor C.
The end result is that actor C does not redraw again, despite requesting
redraws. This situation eventually resolves itself through e.g. relayouts
on actor P, but may take some time to happen.
In order to fix this, consider actors that did get a further redraw
request still dirty after paint().
Fixes: https://gitlab.gnome.org/GNOME/mutter/-/issues/2188
clutter/clutter/clutter-actor.c | 6 ++++--
1 file changed, 4 insertions(+), 2 deletions(-)
---
diff --git a/clutter/clutter/clutter-actor.c b/clutter/clutter/clutter-actor.c
index 2e4b30effc..23ef03dc1f 100644
--- a/clutter/clutter/clutter-actor.c
+++ b/clutter/clutter/clutter-actor.c
@@ -3840,8 +3840,10 @@ clutter_actor_paint (ClutterActor *self,
clutter_paint_node_paint (root_node, paint_context);
/* If we make it here then the actor has run through a complete
- paint run including all the effects so it's no longer dirty */
- priv->is_dirty = FALSE;
+ * paint run including all the effects so it's no longer dirty,
+ * unless a new redraw was queued up.
+ */
+ priv->is_dirty = priv->propagated_one_redraw;
}
/**
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]