From 943fcc7c1a5e9b7ca7cf815c9adbd35de6ab14b2 Mon Sep 17 00:00:00 2001 From: Robert Mader Date: Mon, 20 Feb 2023 02:41:42 +0100 Subject: [PATCH] stage-impl: Transform damage region before queuing In order to queue the right values for transformed `MetaRendererView`s. While on it ensure we query the framebuffers width/height only once, saving some cpu cycles. Closes https://gitlab.gnome.org/GNOME/mutter/-/issues/2557 Part-of: --- cogl/cogl/cogl-onscreen.h | 3 +++ src/backends/meta-stage-impl.c | 14 ++++++++++++-- 2 files changed, 15 insertions(+), 2 deletions(-) diff --git a/cogl/cogl/cogl-onscreen.h b/cogl/cogl/cogl-onscreen.h index 44ba12dc1..eea38292c 100644 --- a/cogl/cogl/cogl-onscreen.h +++ b/cogl/cogl/cogl-onscreen.h @@ -230,6 +230,9 @@ cogl_onscreen_get_buffer_age (CoglOnscreen *onscreen); * This immediately queues state to OpenGL that will be used for the * next swap. * This needs to be called every frame. + * + * The expected values are independent of any viewport transforms applied to + * the framebuffer. */ COGL_EXPORT void cogl_onscreen_queue_damage_region (CoglOnscreen *onscreen, diff --git a/src/backends/meta-stage-impl.c b/src/backends/meta-stage-impl.c index 7774393e1..31e07d965 100644 --- a/src/backends/meta-stage-impl.c +++ b/src/backends/meta-stage-impl.c @@ -214,6 +214,8 @@ queue_damage_region (ClutterStageWindow *stage_window, g_autofree int *freeme = NULL; CoglFramebuffer *framebuffer; CoglOnscreen *onscreen; + int fb_width; + int fb_height; if (cairo_region_is_empty (damage_region)) return; @@ -223,6 +225,8 @@ queue_damage_region (ClutterStageWindow *stage_window, return; onscreen = COGL_ONSCREEN (framebuffer); + fb_width = cogl_framebuffer_get_width (framebuffer); + fb_height = cogl_framebuffer_get_height (framebuffer); n_rects = cairo_region_num_rectangles (damage_region); @@ -234,12 +238,18 @@ queue_damage_region (ClutterStageWindow *stage_window, for (i = 0; i < n_rects; i++) { cairo_rectangle_int_t rect; - int height = cogl_framebuffer_get_height (framebuffer); cairo_region_get_rectangle (damage_region, i, &rect); + + clutter_stage_view_transform_rect_to_onscreen (stage_view, + &rect, + fb_width, + fb_height, + &rect); + damage[i * 4] = rect.x; /* y coordinate needs to be flipped for OpenGL */ - damage[i * 4 + 1] = height - rect.y - rect.height; + damage[i * 4 + 1] = fb_height - rect.y - rect.height; damage[i * 4 + 2] = rect.width; damage[i * 4 + 3] = rect.height; }