[gtk+/wip/window-scales2: 17/40] x11: Support the Gdk/WindowScalingFactor xsetting
- From: Alexander Larsson <alexl src gnome org>
- To: commits-list gnome org
- Cc:
- Subject: [gtk+/wip/window-scales2: 17/40] x11: Support the Gdk/WindowScalingFactor xsetting
- Date: Wed, 3 Jul 2013 12:43:23 +0000 (UTC)
commit d89a98e31e6105a2194e41524d80c577cb014067
Author: Alexander Larsson <alexl redhat com>
Date: Thu Jun 27 22:45:40 2013 +0200
x11: Support the Gdk/WindowScalingFactor xsetting
This xsetting can be used to tell Gtk to use a specific window
scaling for the screen.
gdk/x11/gdkscreen-x11.c | 21 ++++++++++++
gdk/x11/gdkscreen-x11.h | 2 +
gdk/x11/gdksettings.c | 6 +++-
gdk/x11/gdkwindow-x11.c | 79 ++++++++++++++++++++++++++++++++++++++++++--
gdk/x11/gdkwindow-x11.h | 7 +++-
gdk/x11/xsettings-client.c | 10 +++++
6 files changed, 120 insertions(+), 5 deletions(-)
---
diff --git a/gdk/x11/gdkscreen-x11.c b/gdk/x11/gdkscreen-x11.c
index cddb3de..c615098 100644
--- a/gdk/x11/gdkscreen-x11.c
+++ b/gdk/x11/gdkscreen-x11.c
@@ -1090,6 +1090,27 @@ _gdk_x11_screen_new (GdkDisplay *display,
return screen;
}
+void
+_gdk_x11_screen_set_window_scale (GdkX11Screen *x11_screen,
+ int scale)
+{
+ GList *toplevels, *l;
+
+ if (x11_screen->window_scale == scale)
+ return;
+
+ x11_screen->window_scale = scale;
+
+ toplevels = gdk_screen_get_toplevel_windows (GDK_SCREEN (x11_screen));
+
+ for (l = toplevels; l != NULL; l = l->next)
+ {
+ GdkWindow *window = l->data;
+
+ _gdk_x11_window_set_window_scale (window, scale);
+ }
+}
+
/*
* It is important that we first request the selection
* notification, and then setup the initial state of
diff --git a/gdk/x11/gdkscreen-x11.h b/gdk/x11/gdkscreen-x11.h
index 7b27657..f37b61a 100644
--- a/gdk/x11/gdkscreen-x11.h
+++ b/gdk/x11/gdkscreen-x11.h
@@ -121,6 +121,8 @@ void _gdk_x11_screen_get_edge_monitors (GdkScreen *screen,
gint *bottom,
gint *left,
gint *right);
+void _gdk_x11_screen_set_window_scale (GdkX11Screen *x11_screen,
+ int scale);
G_END_DECLS
diff --git a/gdk/x11/gdksettings.c b/gdk/x11/gdksettings.c
index 5f4119f..b86a17e 100644
--- a/gdk/x11/gdksettings.c
+++ b/gdk/x11/gdksettings.c
@@ -59,7 +59,11 @@ static const struct {
{"Gtk/ShellShowsMenubar", "gtk-shell-shows-menubar"},
{"Gtk/EnablePrimaryPaste", "gtk-enable-primary-paste"},
{"Gtk/RecentFilesMaxAge", "gtk-recent-files-max-age"},
- {"Gtk/RecentFilesEnabled", "gtk-recent-files-enabled"}
+ {"Gtk/RecentFilesEnabled", "gtk-recent-files-enabled"},
+
+ /* These are here in order to be recognized, but are not sent to
+ gtk as they are handled internally by gdk: */
+ {"Gdk/WindowScalingFactor", "gdk-window-scaling-factor"}
};
static const char *
diff --git a/gdk/x11/gdkwindow-x11.c b/gdk/x11/gdkwindow-x11.c
index 4141d33..6f8527d 100644
--- a/gdk/x11/gdkwindow-x11.c
+++ b/gdk/x11/gdkwindow-x11.c
@@ -1821,8 +1821,6 @@ window_x11_resize (GdkWindow *window,
window->resize_count += 1;
}
}
-
- _gdk_x11_window_update_size (GDK_WINDOW_IMPL_X11 (window->impl));
}
static inline void
@@ -1891,6 +1889,73 @@ gdk_window_x11_move_resize (GdkWindow *window,
}
}
+static void
+set_scale_recursive (GdkWindow *window, int scale)
+{
+ GdkWindow *child;
+ GList *l;
+
+ for (l = window->children; l; l = l->next)
+ {
+ child = l->data;
+
+ if (child->impl != window->impl)
+ _gdk_x11_window_set_window_scale (child, scale);
+ else
+ set_scale_recursive (child, scale);
+ }
+}
+
+void
+_gdk_x11_window_set_window_scale (GdkWindow *window,
+ int scale)
+{
+ GdkWindowImplX11 *impl;
+ GdkToplevelX11 *toplevel;
+ GdkWindowHints geom_mask;
+
+ if (window->window_type == GDK_WINDOW_OFFSCREEN)
+ return;
+
+ impl = GDK_WINDOW_IMPL_X11 (window->impl);
+
+ impl->window_scale = scale;
+
+ toplevel = _gdk_x11_window_get_toplevel (window);
+ if (toplevel && window->window_type != GDK_WINDOW_FOREIGN)
+ {
+ /* These are affected by window scale: */
+ geom_mask = toplevel->last_geometry_hints_mask &
+ (GDK_HINT_MIN_SIZE | GDK_HINT_MAX_SIZE | GDK_HINT_BASE_SIZE | GDK_HINT_RESIZE_INC);
+ if (geom_mask)
+ gdk_window_set_geometry_hints (window,
+ &toplevel->last_geometry_hints,
+ geom_mask);
+ }
+
+ if (window->window_type == GDK_WINDOW_FOREIGN)
+ XMoveWindow (GDK_WINDOW_XDISPLAY (window),
+ GDK_WINDOW_XID (window),
+ (window->x + window->parent->abs_x) * impl->window_scale,
+ (window->y + window->parent->abs_y) * impl->window_scale);
+ else if (WINDOW_IS_TOPLEVEL(window))
+ XResizeWindow (GDK_WINDOW_XDISPLAY (window),
+ GDK_WINDOW_XID (window),
+ window->width * impl->window_scale,
+ window->height * impl->window_scale);
+ else
+ XMoveResizeWindow (GDK_WINDOW_XDISPLAY (window),
+ GDK_WINDOW_XID (window),
+ (window->x + window->parent->abs_x) * impl->window_scale,
+ (window->y + window->parent->abs_y) * impl->window_scale,
+ window->width * impl->window_scale,
+ window->height * impl->window_scale);
+
+ gdk_window_invalidate_rect (window, NULL, TRUE);
+
+ set_scale_recursive (window, scale);
+}
+
static gboolean
gdk_window_x11_reparent (GdkWindow *window,
GdkWindow *new_parent,
@@ -2401,10 +2466,18 @@ gdk_x11_window_set_geometry_hints (GdkWindow *window,
{
GdkWindowImplX11 *impl = GDK_WINDOW_IMPL_X11 (window->impl);
XSizeHints size_hints;
-
+ GdkToplevelX11 *toplevel;
+
if (GDK_WINDOW_DESTROYED (window) ||
!WINDOW_IS_TOPLEVEL_OR_FOREIGN (window))
return;
+
+ toplevel = _gdk_x11_window_get_toplevel (window);
+ if (toplevel)
+ {
+ toplevel->last_geometry_hints = *geometry;
+ toplevel->last_geometry_hints_mask = geom_mask;
+ }
size_hints.flags = 0;
diff --git a/gdk/x11/gdkwindow-x11.h b/gdk/x11/gdkwindow-x11.h
index 5a9b31d..1c50cf4 100644
--- a/gdk/x11/gdkwindow-x11.h
+++ b/gdk/x11/gdkwindow-x11.h
@@ -152,7 +152,10 @@ struct _GdkToplevelX11
* that might not even be part of this app
*/
Window focus_window;
-
+
+ GdkWindowHints last_geometry_hints_mask;
+ GdkGeometry last_geometry_hints;
+
#ifdef HAVE_XSYNC
XID update_counter;
XID extended_update_counter;
@@ -185,6 +188,8 @@ void _gdk_x11_window_tmp_reset_parent_bg (GdkWindow *window);
GdkCursor *_gdk_x11_window_get_cursor (GdkWindow *window);
void _gdk_x11_window_update_size (GdkWindowImplX11 *impl);
+void _gdk_x11_window_set_window_scale (GdkWindow *window,
+ int scale);
G_END_DECLS
diff --git a/gdk/x11/xsettings-client.c b/gdk/x11/xsettings-client.c
index 41bfaeb..4cafb93 100644
--- a/gdk/x11/xsettings-client.c
+++ b/gdk/x11/xsettings-client.c
@@ -68,6 +68,9 @@ gdk_xsettings_notify (GdkX11Screen *x11_screen,
{
GdkEvent new_event;
+ if (!g_str_has_prefix (name, "gtk-"))
+ return;
+
new_event.type = GDK_SETTING;
new_event.setting.window = gdk_screen_get_root_window (GDK_SCREEN (x11_screen));
new_event.setting.send_event = FALSE;
@@ -406,6 +409,7 @@ read_settings (GdkX11Screen *x11_screen,
int result;
GHashTable *old_list = x11_screen->xsettings;
+ GValue value = G_VALUE_INIT;
x11_screen->xsettings = NULL;
@@ -443,6 +447,12 @@ read_settings (GdkX11Screen *x11_screen,
notify_changes (x11_screen, old_list);
if (old_list)
g_hash_table_unref (old_list);
+
+ g_value_init (&value, G_TYPE_INT);
+ if (gdk_screen_get_setting (GDK_SCREEN (x11_screen),
+ "gdk-window-scaling-factor", &value))
+ _gdk_x11_screen_set_window_scale (x11_screen,
+ g_value_get_int (&value));
}
static Atom
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]