From 8e6fac38fa73ec4c8a67835a1128e6b1a9889302 Mon Sep 17 00:00:00 2001 From: "Owen W. Taylor" <otaylor@fishsoup.net> Date: Sat, 13 Nov 2010 11:29:49 -0500 Subject: [PATCH] Don't update or use last_paint_box when painting inside a clone The last_paint_box for an actor represents its "normal" position - we shouldn't update it or use it to cull drawing if we are painting a clone of the actor. Tracking whether we are painting a clone is done by adding _clutter_actor_push/pop_clone_paint() and a global "clone paint level". http://bugzilla.clutter-project.org/show_bug.cgi?id=2396 --- clutter/clutter-actor-private.h | 3 +++ clutter/clutter-actor.c | 42 +++++++++++++++++++++++++++------ clutter/clutter-clone.c | 2 ++ 3 files changed, 40 insertions(+), 7 deletions(-) diff --git a/clutter/clutter-actor-private.h b/clutter/clutter-actor-private.h index 2c1cc3342..716234682 100644 --- a/clutter/clutter-actor-private.h +++ b/clutter/clutter-actor-private.h @@ -115,6 +115,9 @@ gboolean _clutter_actor_set_default_paint_volume (ClutterActor *self, G_CONST_RETURN gchar *_clutter_actor_get_debug_name (ClutterActor *self); +void _clutter_actor_push_clone_paint (void); +void _clutter_actor_pop_clone_paint (void); + G_END_DECLS #endif /* __CLUTTER_ACTOR_PRIVATE_H__ */ diff --git a/clutter/clutter-actor.c b/clutter/clutter-actor.c index 553b112c5..4bf713bca 100644 --- a/clutter/clutter-actor.c +++ b/clutter/clutter-actor.c @@ -2465,6 +2465,26 @@ _clutter_actor_draw_paint_volume (ClutterActor *self) clutter_paint_volume_free (&fake_pv); } +static int clone_paint_level = 0; + +void +_clutter_actor_push_clone_paint (void) +{ + clone_paint_level++; +} + +void +_clutter_actor_pop_clone_paint (void) +{ + clone_paint_level--; +} + +static gboolean +in_clone_paint (void) +{ + return clone_paint_level > 0; +} + /* Returns TRUE if the actor can be ignored */ static gboolean cull_actor (ClutterActor *self) @@ -2619,6 +2639,11 @@ clutter_actor_paint (ClutterActor *self) * We also fetch the current paint box to perform culling so we * can avoid painting actors outside the current clip region. * + * If we are painting inside a clone, we should neither update + * the paint box or use it to cull painting, since the paint + * box represents the location of the source actor on the + * screen. + * * XXX: We are starting to do a lot of vertex transforms on * the CPU in a typical paint, so at some point we should * audit these and consider caching some things. @@ -2636,14 +2661,17 @@ clutter_actor_paint (ClutterActor *self) * or we'd need to be able to invalidate paint-volumes on * projection changes. */ - if (G_LIKELY (need_paint_box) && - clutter_actor_get_paint_box (self, &priv->last_paint_box)) - priv->last_paint_box_valid = TRUE; - else - priv->last_paint_box_valid = FALSE; + if (!in_clone_paint ()) + { + if (G_LIKELY (need_paint_box) && + clutter_actor_get_paint_box (self, &priv->last_paint_box)) + priv->last_paint_box_valid = TRUE; + else + priv->last_paint_box_valid = FALSE; - if (cull_actor (self)) - goto done; + if (cull_actor (self)) + goto done; + } if (priv->effects != NULL) effect_painted = _clutter_actor_effects_pre_paint (self); diff --git a/clutter/clutter-clone.c b/clutter/clutter-clone.c index cb5027328..ed3348908 100644 --- a/clutter/clutter-clone.c +++ b/clutter/clutter-clone.c @@ -184,7 +184,9 @@ clutter_clone_paint (ClutterActor *self) was_unmapped = TRUE; } + _clutter_actor_push_clone_paint (); clutter_actor_paint (priv->clone_source); + _clutter_actor_pop_clone_paint (); if (was_unmapped) _clutter_actor_set_enable_paint_unmapped (priv->clone_source, FALSE);