Skip to content

clutter/actor: Always update last_paint_volumes during painting

It's currently possible that some last_paint_volumes don't get updated during a paint cycle, this can happen when a ClutterOffscreenEffect is used: The offscreen effect might skip painting the content and the children of an actor because it uses its own offscreened texture instead. This means the offscreen effect doesn't call clutter_actor_continue_paint(), and thus the the last_paint_volumes of the children won't be updated.

Now one might think that isn't a problem, because as soon as a child changes it's size or position, the offscreened texture would get invalidated and clutter_actor_continue_paint() would get called. It's not that easy though: Because the last_paint_volume includes all the transformation matrices up to eye-coordinates, it has to be updated on any changes to matrices, which includes position/transformation changes to any actor up the hierarchy.

Now that's where get into problems with the offscreen effect: In case of transformation changes to the offscreened actor or an actor up the hierarchy, the offscreened texture won't get invalidated (that makes sense, we can simply paint it transformed) and the last_paint_volumes won't get updated even though they should.

This leaves us around with outdated last_paint_volumes where last_paint_volume_valid is still set to TRUE. It can cause issues with culling and clipped redraws.

So fix that by ensuring that all children that would get painted by Clutter get their last_paint_volumes updated in case a ClutterEffect decided not to call clutter_actor_continue_paint().

This ignores the case where a paint() vfunc override does the same and doesn't call clutter_actor_paint() on children. Let's ignore this case for now, there shouldn't be any implementation which does that and ideally in a world that's painted solely by ClutterContent, we can get rid of that vfunc in the future.

Merge request reports