mirror of
https://gitlab.gnome.org/GNOME/gtk.git
synced 2024-12-26 13:41:07 +00:00
wayland: Implement gdk_screen_get_monitor_scale()
We bind to the newer version of the wl_output which supports the new done and scale events, and if we use this to get the scale for each monitor (defaulting to 1 if not supported).
This commit is contained in:
parent
8524e0c150
commit
ce68a2f870
@ -168,8 +168,8 @@ gdk_registry_handle_global(void *data, struct wl_registry *registry, uint32_t id
|
||||
wl_registry_bind(display_wayland->wl_registry, id, &wl_shell_interface, 1);
|
||||
} else if (strcmp(interface, "wl_output") == 0) {
|
||||
output =
|
||||
wl_registry_bind(display_wayland->wl_registry, id, &wl_output_interface, 1);
|
||||
_gdk_wayland_screen_add_output(display_wayland->screen, id, output);
|
||||
wl_registry_bind(display_wayland->wl_registry, id, &wl_output_interface, 2);
|
||||
_gdk_wayland_screen_add_output(display_wayland->screen, id, output, version);
|
||||
/* We need another roundtrip to receive the modes and geometry
|
||||
* events for the output, which gives us the physical properties
|
||||
* and available modes on the output. */
|
||||
|
@ -161,11 +161,14 @@ GdkWindow *_gdk_wayland_screen_create_root_window (GdkScreen *screen,
|
||||
GdkScreen *_gdk_wayland_screen_new (GdkDisplay *display);
|
||||
void _gdk_wayland_screen_add_output (GdkScreen *screen,
|
||||
guint32 id,
|
||||
struct wl_output *output);
|
||||
struct wl_output *output,
|
||||
guint32 version);
|
||||
void _gdk_wayland_screen_remove_output (GdkScreen *screen,
|
||||
guint32 id);
|
||||
int _gdk_wayland_screen_get_output_refresh_rate (GdkScreen *screen,
|
||||
struct wl_output *output);
|
||||
guint32 _gdk_wayland_screen_get_output_scale (GdkScreen *screen,
|
||||
struct wl_output *output);
|
||||
|
||||
void _gdk_wayland_window_set_device_grabbed (GdkWindow *window,
|
||||
GdkDevice *device,
|
||||
|
@ -77,10 +77,13 @@ struct _GdkWaylandScreenClass
|
||||
void (* window_manager_changed) (GdkWaylandScreen *screen_wayland);
|
||||
};
|
||||
|
||||
#define OUTPUT_VERSION_WITH_DONE 2
|
||||
|
||||
struct _GdkWaylandMonitor
|
||||
{
|
||||
GdkWaylandScreen *screen;
|
||||
guint32 id;
|
||||
guint32 version;
|
||||
struct wl_output *output;
|
||||
GdkRectangle geometry;
|
||||
int width_mm;
|
||||
@ -88,6 +91,7 @@ struct _GdkWaylandMonitor
|
||||
char * output_name;
|
||||
char * manufacturer;
|
||||
int refresh_rate;
|
||||
gint scale;
|
||||
};
|
||||
|
||||
G_DEFINE_TYPE (GdkWaylandScreen, _gdk_wayland_screen, GDK_TYPE_SCREEN)
|
||||
@ -249,6 +253,21 @@ gdk_wayland_screen_get_monitor_geometry (GdkScreen *screen,
|
||||
*dest = monitor->geometry;
|
||||
}
|
||||
|
||||
static gint
|
||||
gdk_wayland_screen_get_monitor_scale_factor (GdkScreen *screen,
|
||||
gint monitor_num)
|
||||
{
|
||||
GdkWaylandScreen *screen_wayland = GDK_WAYLAND_SCREEN (screen);
|
||||
GdkWaylandMonitor *monitor;
|
||||
|
||||
if (monitor_num >= screen_wayland->monitors->len)
|
||||
return 1;
|
||||
|
||||
monitor = g_ptr_array_index(screen_wayland->monitors, monitor_num);
|
||||
|
||||
return monitor->scale;
|
||||
}
|
||||
|
||||
static GdkVisual *
|
||||
gdk_wayland_screen_get_system_visual (GdkScreen * screen)
|
||||
{
|
||||
@ -822,6 +841,7 @@ _gdk_wayland_screen_class_init (GdkWaylandScreenClass *klass)
|
||||
screen_class->get_monitor_plug_name = gdk_wayland_screen_get_monitor_plug_name;
|
||||
screen_class->get_monitor_geometry = gdk_wayland_screen_get_monitor_geometry;
|
||||
screen_class->get_monitor_workarea = gdk_wayland_screen_get_monitor_geometry;
|
||||
screen_class->get_monitor_scale_factor = gdk_wayland_screen_get_monitor_scale_factor;
|
||||
screen_class->get_system_visual = gdk_wayland_screen_get_system_visual;
|
||||
screen_class->get_rgba_visual = gdk_wayland_screen_get_rgba_visual;
|
||||
screen_class->is_composited = gdk_wayland_screen_is_composited;
|
||||
@ -888,13 +908,33 @@ output_handle_geometry(void *data,
|
||||
monitor->manufacturer = g_strdup (make);
|
||||
monitor->output_name = g_strdup (model);
|
||||
|
||||
if (monitor->geometry.width != 0)
|
||||
if (monitor->geometry.width != 0 && monitor->version < OUTPUT_VERSION_WITH_DONE)
|
||||
{
|
||||
g_signal_emit_by_name (monitor->screen, "monitors-changed");
|
||||
update_screen_size (monitor->screen);
|
||||
}
|
||||
}
|
||||
|
||||
static void
|
||||
output_handle_done(void *data,
|
||||
struct wl_output *wl_output)
|
||||
{
|
||||
GdkWaylandMonitor *monitor = (GdkWaylandMonitor *)data;
|
||||
|
||||
g_signal_emit_by_name (monitor->screen, "monitors-changed");
|
||||
update_screen_size (monitor->screen);
|
||||
}
|
||||
|
||||
static void
|
||||
output_handle_scale(void *data,
|
||||
struct wl_output *wl_output,
|
||||
uint32_t factor)
|
||||
{
|
||||
GdkWaylandMonitor *monitor = (GdkWaylandMonitor *)data;
|
||||
|
||||
monitor->scale = factor;
|
||||
}
|
||||
|
||||
static void
|
||||
output_handle_mode(void *data,
|
||||
struct wl_output *wl_output,
|
||||
@ -912,27 +952,35 @@ output_handle_mode(void *data,
|
||||
monitor->geometry.height = height;
|
||||
monitor->refresh_rate = refresh;
|
||||
|
||||
g_signal_emit_by_name (monitor->screen, "monitors-changed");
|
||||
update_screen_size (monitor->screen);
|
||||
if (monitor->geometry.width != 0 && monitor->version < OUTPUT_VERSION_WITH_DONE)
|
||||
{
|
||||
g_signal_emit_by_name (monitor->screen, "monitors-changed");
|
||||
update_screen_size (monitor->screen);
|
||||
}
|
||||
}
|
||||
|
||||
static const struct wl_output_listener output_listener =
|
||||
{
|
||||
output_handle_geometry,
|
||||
output_handle_mode
|
||||
output_handle_mode,
|
||||
output_handle_done,
|
||||
output_handle_scale,
|
||||
};
|
||||
|
||||
void
|
||||
_gdk_wayland_screen_add_output (GdkScreen *screen,
|
||||
guint32 id,
|
||||
struct wl_output *output)
|
||||
struct wl_output *output,
|
||||
guint32 version)
|
||||
{
|
||||
GdkWaylandScreen *screen_wayland = GDK_WAYLAND_SCREEN (screen);
|
||||
GdkWaylandMonitor *monitor = g_new0(GdkWaylandMonitor, 1);
|
||||
|
||||
monitor->id = id;
|
||||
monitor->output = output;
|
||||
monitor->version = version;
|
||||
monitor->screen = screen_wayland;
|
||||
monitor->scale = 1;
|
||||
g_ptr_array_add(screen_wayland->monitors, monitor);
|
||||
|
||||
wl_output_add_listener(output, &output_listener, monitor);
|
||||
@ -977,3 +1025,21 @@ _gdk_wayland_screen_get_output_refresh_rate (GdkScreen *screen,
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
guint32
|
||||
_gdk_wayland_screen_get_output_scale (GdkScreen *screen,
|
||||
struct wl_output *output)
|
||||
{
|
||||
GdkWaylandScreen *screen_wayland = GDK_WAYLAND_SCREEN (screen);
|
||||
int i;
|
||||
|
||||
for (i = 0; i < screen_wayland->monitors->len; i++)
|
||||
{
|
||||
GdkWaylandMonitor *monitor = screen_wayland->monitors->pdata[i];
|
||||
|
||||
if (monitor->output == output)
|
||||
return monitor->scale;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user