gl: Rewrite update area tracking code

Make it more generic. That way we could dynamically change the number of
buffers we track.

We don't do that yet though.
This commit is contained in:
Benjamin Otte 2023-05-24 21:40:20 +02:00
parent cd9c277820
commit 7573a9d2a7
3 changed files with 39 additions and 43 deletions

View File

@ -466,29 +466,26 @@ gdk_gl_context_real_get_damage (GdkGLContext *context)
eglQuerySurface (gdk_display_get_egl_display (display), egl_surface,
EGL_BUFFER_AGE_EXT, &buffer_age);
switch (buffer_age)
if (buffer_age > 0 && buffer_age <= GDK_GL_MAX_TRACKED_BUFFERS)
{
case 1:
return cairo_region_create ();
break;
cairo_region_t *damage = cairo_region_create ();
int i;
case 2:
if (context->old_updated_area[0])
return cairo_region_copy (context->old_updated_area[0]);
break;
for (i = 0; i < buffer_age - 1; i++)
{
if (context->old_updated_area[i] == NULL)
{
cairo_region_create_rectangle (&(GdkRectangle) {
0, 0,
gdk_surface_get_width (surface),
gdk_surface_get_height (surface)
});
break;
}
cairo_region_union (damage, context->old_updated_area[i]);
}
case 3:
if (context->old_updated_area[0] &&
context->old_updated_area[1])
{
cairo_region_t *damage = cairo_region_copy (context->old_updated_area[0]);
cairo_region_union (damage, context->old_updated_area[1]);
return damage;
}
break;
default:
;
return damage;
}
}
#endif
@ -597,6 +594,7 @@ gdk_gl_context_real_begin_frame (GdkDrawContext *draw_context,
cairo_region_t *damage;
double scale;
int ww, wh;
int i;
surface = gdk_draw_context_get_surface (draw_context);
scale = gdk_gl_context_get_scale (context);
@ -608,9 +606,11 @@ gdk_gl_context_real_begin_frame (GdkDrawContext *draw_context,
damage = GDK_GL_CONTEXT_GET_CLASS (context)->get_damage (context);
if (context->old_updated_area[1])
cairo_region_destroy (context->old_updated_area[1]);
context->old_updated_area[1] = context->old_updated_area[0];
g_clear_pointer (&context->old_updated_area[GDK_GL_MAX_TRACKED_BUFFERS - 1], cairo_region_destroy);
for (i = GDK_GL_MAX_TRACKED_BUFFERS - 1; i > 0; i--)
{
context->old_updated_area[i] = context->old_updated_area[i - 1];
}
context->old_updated_area[0] = cairo_region_copy (region);
cairo_region_union (region, damage);

View File

@ -34,6 +34,11 @@ typedef enum {
GDK_GL_CGL
} GdkGLBackend;
/* The maximum amount of buffers we track update regions for.
* Note that this is equal to the max buffer age value we
* can provide a damage region for */
#define GDK_GL_MAX_TRACKED_BUFFERS 2
#define GDK_GL_CONTEXT_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST ((klass), GDK_TYPE_GL_CONTEXT, GdkGLContextClass))
#define GDK_IS_GL_CONTEXT_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE ((klass), GDK_TYPE_GL_CONTEXT))
#define GDK_GL_CONTEXT_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS ((obj), GDK_TYPE_GL_CONTEXT, GdkGLContextClass))
@ -45,7 +50,7 @@ struct _GdkGLContext
GdkDrawContext parent_instance;
/* We store the old drawn areas to support buffer-age optimizations */
cairo_region_t *old_updated_area[2];
cairo_region_t *old_updated_area[GDK_GL_MAX_TRACKED_BUFFERS];
};
struct _GdkGLContextClass

View File

@ -287,29 +287,20 @@ gdk_x11_gl_context_glx_get_damage (GdkGLContext *context)
glXQueryDrawable (dpy, gdk_x11_gl_context_glx_get_drawable (self),
GLX_BACK_BUFFER_AGE_EXT, &buffer_age);
switch (buffer_age)
if (buffer_age > 0 && buffer_age <= GDK_GL_MAX_TRACKED_BUFFERS)
{
case 1:
return cairo_region_create ();
break;
cairo_region_t *damage = cairo_region_create ();
int i;
case 2:
if (context->old_updated_area[0])
return cairo_region_copy (context->old_updated_area[0]);
break;
for (i = 0; i < buffer_age - 1; i++)
{
if (context->old_updated_area[i] == NULL)
return GDK_GL_CONTEXT_CLASS (gdk_x11_gl_context_glx_parent_class)->get_damage (context);
case 3:
if (context->old_updated_area[0] &&
context->old_updated_area[1])
{
cairo_region_t *damage = cairo_region_copy (context->old_updated_area[0]);
cairo_region_union (damage, context->old_updated_area[1]);
return damage;
}
break;
cairo_region_union (damage, context->old_updated_area[i]);
}
default:
;
return damage;
}
}