wayland: Add support for preferred_buffer_scale/transform

Which got introduced in wl_compositor version 6.

Note that if the surface is visible on multiple monitors with different
transforms, we pick the transform of the monitor which we choose for the
scale as well. This doesn't really matter at the moment, as the
transform is only really relevant for direct-scanout - which we
currently only support for fullscreen clients.

Once we support direct-scanout for partially visible clients we'll
likely want to introduce a more sophisticated algorithm.

Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3580>
This commit is contained in:
Robert Mader 2024-02-11 22:13:02 +01:00 committed by Marge Bot
parent 037077bb56
commit f21762ea6e
4 changed files with 45 additions and 2 deletions

View File

@ -45,7 +45,7 @@ udev_req = '>= 228'
gudev_req = '>= 232'
# wayland version requirements
wayland_server_req = '>= 1.21'
wayland_server_req = '>= 1.22'
wayland_protocols_req = '>= 1.33'
# native backend version requirements

View File

@ -162,6 +162,9 @@ struct _MetaWaylandSurface
GHashTable *outputs;
MetaMonitorTransform buffer_transform;
int preferred_scale;
MetaMonitorTransform preferred_transform;
/* Buffer reference state. */
MetaWaylandBuffer *buffer;

View File

@ -1437,6 +1437,25 @@ out:
return scale;
}
static MetaMonitorTransform
meta_wayland_surface_get_output_transform (MetaWaylandSurface *surface)
{
MetaMonitorTransform transform = META_MONITOR_TRANSFORM_NORMAL;
MetaWindow *window;
MetaLogicalMonitor *logical_monitor;
window = meta_wayland_surface_get_window (surface);
if (!window)
return transform;
logical_monitor = meta_window_get_highest_scale_monitor (window);
if (!logical_monitor)
return transform;
transform = meta_logical_monitor_get_transform (logical_monitor);
return transform;
}
static void
update_surface_output_state (gpointer key, gpointer value, gpointer user_data)
{
@ -2404,6 +2423,27 @@ committed_state_handle_highest_scale_monitor (MetaWaylandSurface *surface)
meta_wayland_fractional_scale_maybe_send_preferred_scale (surface, scale);
if (wl_resource_get_version (surface->resource) >=
WL_SURFACE_PREFERRED_BUFFER_SCALE_SINCE_VERSION)
{
int ceiled_scale;
MetaMonitorTransform transform;
ceiled_scale = ceil (scale);
if (ceiled_scale > 0 && ceiled_scale != surface->preferred_scale)
{
wl_surface_send_preferred_buffer_scale (surface->resource, ceiled_scale);
surface->preferred_scale = ceiled_scale;
}
transform = meta_wayland_surface_get_output_transform (surface);
if (transform != surface->preferred_transform)
{
wl_surface_send_preferred_buffer_transform (surface->resource, ceiled_scale);
surface->preferred_transform = transform;
}
}
META_WAYLAND_SURFACE_FOREACH_SUBSURFACE (&surface->committed_state,
subsurface_surface)
committed_state_handle_highest_scale_monitor (subsurface_surface);

View File

@ -32,7 +32,7 @@
/* #define META_WL_BUFFER_VERSION 1 */
/* Global/master objects (version exported by wl_registry and negotiated through bind) */
#define META_WL_COMPOSITOR_VERSION 5
#define META_WL_COMPOSITOR_VERSION 6
#define META_WL_DATA_DEVICE_MANAGER_VERSION 3
#define META_XDG_WM_BASE_VERSION 6
#define META_WL_SEAT_VERSION 8