clients: add support for surface compression in simple-egl
When option "-c <bpc>" is specified, the application uses EGL_EXT_surface_compression extension to compress the window surface to the given bitrate (bits per component). Signed-off-by: Louis-Francis Ratté-Boulianne <lfrb@collabora.com>
This commit is contained in:
parent
3908e3e345
commit
1703d76822
|
@ -85,6 +85,7 @@ struct display {
|
||||||
struct wl_list output_list; /* struct output::link */
|
struct wl_list output_list; /* struct output::link */
|
||||||
|
|
||||||
PFNEGLSWAPBUFFERSWITHDAMAGEEXTPROC swap_buffers_with_damage;
|
PFNEGLSWAPBUFFERSWITHDAMAGEEXTPROC swap_buffers_with_damage;
|
||||||
|
PFNEGLQUERYSUPPORTEDCOMPRESSIONRATESEXTPROC query_compression_rates;
|
||||||
};
|
};
|
||||||
|
|
||||||
struct geometry {
|
struct geometry {
|
||||||
|
@ -116,7 +117,7 @@ struct window {
|
||||||
struct xdg_toplevel *xdg_toplevel;
|
struct xdg_toplevel *xdg_toplevel;
|
||||||
EGLSurface egl_surface;
|
EGLSurface egl_surface;
|
||||||
int fullscreen, maximized, opaque, buffer_bpp, interval, delay;
|
int fullscreen, maximized, opaque, buffer_bpp, interval, delay;
|
||||||
int present_opaque;
|
int compression_rate, present_opaque;
|
||||||
struct wp_tearing_control_v1 *tear_control;
|
struct wp_tearing_control_v1 *tear_control;
|
||||||
struct wp_viewport *viewport;
|
struct wp_viewport *viewport;
|
||||||
struct wp_fractional_scale_v1 *fractional_scale_obj;
|
struct wp_fractional_scale_v1 *fractional_scale_obj;
|
||||||
|
@ -161,6 +162,27 @@ static const char *frag_shader_text =
|
||||||
|
|
||||||
static int running = 1;
|
static int running = 1;
|
||||||
|
|
||||||
|
|
||||||
|
static int
|
||||||
|
enum_to_compression_rate(EGLint value)
|
||||||
|
{
|
||||||
|
switch (value) {
|
||||||
|
case EGL_SURFACE_COMPRESSION_FIXED_RATE_1BPC_EXT: return 1;
|
||||||
|
case EGL_SURFACE_COMPRESSION_FIXED_RATE_2BPC_EXT: return 2;
|
||||||
|
case EGL_SURFACE_COMPRESSION_FIXED_RATE_3BPC_EXT: return 3;
|
||||||
|
case EGL_SURFACE_COMPRESSION_FIXED_RATE_4BPC_EXT: return 4;
|
||||||
|
case EGL_SURFACE_COMPRESSION_FIXED_RATE_5BPC_EXT: return 5;
|
||||||
|
case EGL_SURFACE_COMPRESSION_FIXED_RATE_6BPC_EXT: return 6;
|
||||||
|
case EGL_SURFACE_COMPRESSION_FIXED_RATE_7BPC_EXT: return 7;
|
||||||
|
case EGL_SURFACE_COMPRESSION_FIXED_RATE_8BPC_EXT: return 8;
|
||||||
|
case EGL_SURFACE_COMPRESSION_FIXED_RATE_9BPC_EXT: return 9;
|
||||||
|
case EGL_SURFACE_COMPRESSION_FIXED_RATE_10BPC_EXT: return 10;
|
||||||
|
case EGL_SURFACE_COMPRESSION_FIXED_RATE_11BPC_EXT: return 11;
|
||||||
|
case EGL_SURFACE_COMPRESSION_FIXED_RATE_12BPC_EXT: return 12;
|
||||||
|
default: return 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
static void
|
static void
|
||||||
init_egl(struct display *display, struct window *window)
|
init_egl(struct display *display, struct window *window)
|
||||||
{
|
{
|
||||||
|
@ -281,6 +303,13 @@ init_egl(struct display *display, struct window *window)
|
||||||
if (display->swap_buffers_with_damage)
|
if (display->swap_buffers_with_damage)
|
||||||
printf("has EGL_EXT_buffer_age and %s\n", swap_damage_ext_to_entrypoint[i].extension);
|
printf("has EGL_EXT_buffer_age and %s\n", swap_damage_ext_to_entrypoint[i].extension);
|
||||||
|
|
||||||
|
if (extensions &&
|
||||||
|
weston_check_egl_extension(extensions, "EGL_EXT_surface_compression")) {
|
||||||
|
display->query_compression_rates =
|
||||||
|
(PFNEGLQUERYSUPPORTEDCOMPRESSIONRATESEXTPROC)
|
||||||
|
eglGetProcAddress("eglQuerySupportedCompressionRatesEXT");
|
||||||
|
printf("has EGL_EXT_surface_compression\n");
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
static void
|
static void
|
||||||
|
@ -446,20 +475,58 @@ init_gl(struct window *window)
|
||||||
GLuint program;
|
GLuint program;
|
||||||
GLint status;
|
GLint status;
|
||||||
EGLBoolean ret;
|
EGLBoolean ret;
|
||||||
EGLint attribs[] = { EGL_PRESENT_OPAQUE_EXT, EGL_TRUE, EGL_NONE };
|
EGLint attribs[5] = { EGL_NONE };
|
||||||
|
uint32_t num_attribs = 0;
|
||||||
|
|
||||||
if (window->needs_buffer_geometry_update)
|
if (window->needs_buffer_geometry_update)
|
||||||
update_buffer_geometry(window);
|
update_buffer_geometry(window);
|
||||||
|
|
||||||
|
if (window->present_opaque) {
|
||||||
|
attribs[num_attribs++] = EGL_PRESENT_OPAQUE_EXT;
|
||||||
|
attribs[num_attribs++] = EGL_TRUE;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (window->compression_rate != 0) {
|
||||||
|
EGLint rates[16], num_rates;
|
||||||
|
|
||||||
|
if (!window->display->query_compression_rates) {
|
||||||
|
fprintf(stderr, "Fixed-rate compression is not supported\n");
|
||||||
|
exit(1);
|
||||||
|
}
|
||||||
|
|
||||||
|
attribs[num_attribs++] = EGL_SURFACE_COMPRESSION_EXT;
|
||||||
|
|
||||||
|
if (window->compression_rate < 0) {
|
||||||
|
/* Use default compression rate if user specified -1 */
|
||||||
|
attribs[num_attribs++] = EGL_SURFACE_COMPRESSION_FIXED_RATE_DEFAULT_EXT;
|
||||||
|
} else if (window->compression_rate > 0) {
|
||||||
|
bool supported = false;
|
||||||
|
|
||||||
|
window->display->query_compression_rates(window->display->egl.dpy,
|
||||||
|
window->display->egl.conf,
|
||||||
|
NULL, rates, 16, &num_rates);
|
||||||
|
for (int i = 0; i < num_rates; ++i) {
|
||||||
|
if (enum_to_compression_rate(rates[i]) == window->compression_rate) {
|
||||||
|
attribs[num_attribs++] = rates[i];
|
||||||
|
supported = true;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!supported) {
|
||||||
|
printf("Compression rate (%i bpc) is not supported\n", window->compression_rate);
|
||||||
|
exit(1);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
window->native = wl_egl_window_create(window->surface,
|
window->native = wl_egl_window_create(window->surface,
|
||||||
window->buffer_size.width,
|
window->buffer_size.width,
|
||||||
window->buffer_size.height);
|
window->buffer_size.height);
|
||||||
window->egl_surface =
|
window->egl_surface =
|
||||||
weston_platform_create_egl_surface(window->display->egl.dpy,
|
weston_platform_create_egl_surface(window->display->egl.dpy,
|
||||||
window->display->egl.conf,
|
window->display->egl.conf,
|
||||||
window->native,
|
window->native, attribs);
|
||||||
window->present_opaque ?
|
|
||||||
attribs : NULL);
|
|
||||||
|
|
||||||
if (!window->egl_surface) {
|
if (!window->egl_surface) {
|
||||||
fprintf(stderr, "Failed to create EGLSurface, error 0x%x\n",
|
fprintf(stderr, "Failed to create EGLSurface, error 0x%x\n",
|
||||||
|
@ -1324,6 +1391,8 @@ usage(int error_code)
|
||||||
" -v\tDraw a moving vertical bar instead of a triangle\n"
|
" -v\tDraw a moving vertical bar instead of a triangle\n"
|
||||||
" -i <interval> \tSet eglSwapInterval to interval\n"
|
" -i <interval> \tSet eglSwapInterval to interval\n"
|
||||||
" -p\tPresent surface opaquely, regardless of alpha\n"
|
" -p\tPresent surface opaquely, regardless of alpha\n"
|
||||||
|
" -c <bpc>\tCompress the texture to given bitrate;\n"
|
||||||
|
" \tDefault fixed-rate value is used if -1 is specified.\n"
|
||||||
" -h\tThis help text\n\n");
|
" -h\tThis help text\n\n");
|
||||||
|
|
||||||
exit(error_code);
|
exit(error_code);
|
||||||
|
@ -1379,6 +1448,8 @@ main(int argc, char **argv)
|
||||||
window.interval = atoi(argv[++i]);
|
window.interval = atoi(argv[++i]);
|
||||||
else if (strcmp("-p", argv[i]) == 0)
|
else if (strcmp("-p", argv[i]) == 0)
|
||||||
window.present_opaque = 1;
|
window.present_opaque = 1;
|
||||||
|
else if (strcmp("-c", argv[i]) == 0 && i+1 < argc)
|
||||||
|
window.compression_rate = atoi(argv[++i]);
|
||||||
else if (strcmp("-h", argv[i]) == 0)
|
else if (strcmp("-h", argv[i]) == 0)
|
||||||
usage(EXIT_SUCCESS);
|
usage(EXIT_SUCCESS);
|
||||||
else
|
else
|
||||||
|
|
Loading…
Reference in New Issue