[gtk/wip/matthiasc/can-focus: 3/17] root: Reorganize focus handling



commit 8ae3c2ae11ee40002d61cf3242360519a64fa80d
Author: Matthias Clasen <mclasen redhat com>
Date:   Sun Mar 29 15:19:23 2020 -0400

    root: Reorganize focus handling
    
    Make :focus-widget a GtkWindow property and add vfuncs
    to the GtkRoot interface instead of the property.

 gtk/gtkdragicon.c    |  8 -----
 gtk/gtkroot.c        | 40 ++++++++++--------------
 gtk/gtkrootprivate.h | 13 +++-----
 gtk/gtkwindow.c      | 88 +++++++++++++++++++++++++++++++++++-----------------
 4 files changed, 80 insertions(+), 69 deletions(-)
---
diff --git a/gtk/gtkdragicon.c b/gtk/gtkdragicon.c
index dc52dbcf54..bc13f75a93 100644
--- a/gtk/gtkdragicon.c
+++ b/gtk/gtkdragicon.c
@@ -317,10 +317,6 @@ gtk_drag_icon_get_property (GObject     *object,
       g_value_set_object (value, self->child);
       break;
 
-    case LAST_ARG + GTK_ROOT_PROP_FOCUS_WIDGET:
-      g_value_set_object (value, NULL);
-      break;
-
     default:
       G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
       break;
@@ -341,9 +337,6 @@ gtk_drag_icon_set_property (GObject      *object,
       gtk_drag_icon_set_child (self, g_value_get_object (value));
       break;
 
-    case LAST_ARG + GTK_ROOT_PROP_FOCUS_WIDGET:
-      // do nothing
-      break;
     default:
       G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
       break;
@@ -382,7 +375,6 @@ gtk_drag_icon_class_init (GtkDragIconClass *klass)
                          G_PARAM_READWRITE | G_PARAM_EXPLICIT_NOTIFY | G_PARAM_STATIC_STRINGS);
 
   g_object_class_install_properties (object_class, LAST_ARG, properties);
-  gtk_root_install_properties (object_class, LAST_ARG);
 
   gtk_widget_class_set_css_name (widget_class, "dnd");
 }
diff --git a/gtk/gtkroot.c b/gtk/gtkroot.c
index 3e6a7b78b6..0252b85856 100644
--- a/gtk/gtkroot.c
+++ b/gtk/gtkroot.c
@@ -59,18 +59,25 @@ gtk_root_default_get_constraint_solver (GtkRoot *self)
   return NULL;
 }
 
+static GtkWidget *
+gtk_root_default_get_focus (GtkRoot *self)
+{
+  return NULL;
+}
+
+static void
+gtk_root_default_set_focus (GtkRoot   *self,
+                            GtkWidget *focus)
+{
+}
+
 static void
 gtk_root_default_init (GtkRootInterface *iface)
 {
   iface->get_display = gtk_root_default_get_display;
   iface->get_constraint_solver = gtk_root_default_get_constraint_solver;
-
-  g_object_interface_install_property (iface,
-      g_param_spec_object ("focus-widget",
-                           P_("Focus widget"),
-                           P_("The focus widget"),
-                           GTK_TYPE_WIDGET,
-                           GTK_PARAM_READWRITE|G_PARAM_EXPLICIT_NOTIFY));
+  iface->get_focus = gtk_root_default_get_focus;
+  iface->set_focus = gtk_root_default_set_focus;
 }
 
 /**
@@ -123,7 +130,7 @@ gtk_root_set_focus (GtkRoot   *self,
   g_return_if_fail (GTK_IS_ROOT (self));
   g_return_if_fail (focus == NULL || GTK_IS_WIDGET (focus));
 
-  g_object_set (self, "focus-widget", focus, NULL);
+  GTK_ROOT_GET_IFACE (self)->set_focus (self, focus);
 }
 
 /**
@@ -143,22 +150,7 @@ gtk_root_set_focus (GtkRoot   *self,
 GtkWidget *
 gtk_root_get_focus (GtkRoot *self)
 {
-  GtkWidget *focus;
-
   g_return_val_if_fail (GTK_IS_ROOT (self), NULL);
 
-  g_object_get (self, "focus-widget", &focus, NULL);
-
-  if (focus)
-    g_object_unref (focus);
-
-  return focus;
-}
-
-guint
-gtk_root_install_properties (GObjectClass *object_class,
-                             guint         first_prop)
-{
-  g_object_class_override_property (object_class, first_prop + GTK_ROOT_PROP_FOCUS_WIDGET, "focus-widget");
-  return GTK_ROOT_NUM_PROPERTIES;
+  return GTK_ROOT_GET_IFACE (self)->get_focus (self);
 }
diff --git a/gtk/gtkrootprivate.h b/gtk/gtkrootprivate.h
index 41f1360673..57246127a5 100644
--- a/gtk/gtkrootprivate.h
+++ b/gtk/gtkrootprivate.h
@@ -21,17 +21,14 @@ struct _GtkRootInterface
   GdkDisplay * (* get_display)  (GtkRoot *self);
 
   GtkConstraintSolver * (* get_constraint_solver) (GtkRoot *self);
-};
 
-GtkConstraintSolver *   gtk_root_get_constraint_solver  (GtkRoot *self);
+  GtkWidget *  (* get_focus)    (GtkRoot   *self);
+  void         (* set_focus)    (GtkRoot   *self,
+                                 GtkWidget *focus);
 
-typedef enum {
-  GTK_ROOT_PROP_FOCUS_WIDGET,
-  GTK_ROOT_NUM_PROPERTIES
-} GtkRootProperties;
+};
 
-guint gtk_root_install_properties (GObjectClass *object_class,
-                                   guint         first_prop);
+GtkConstraintSolver *   gtk_root_get_constraint_solver  (GtkRoot *self);
 
 G_END_DECLS
 
diff --git a/gtk/gtkwindow.c b/gtk/gtkwindow.c
index 42135b8bb9..745946c8b2 100644
--- a/gtk/gtkwindow.c
+++ b/gtk/gtkwindow.c
@@ -288,6 +288,7 @@ enum {
   PROP_TRANSIENT_FOR,
   PROP_APPLICATION,
   PROP_DEFAULT_WIDGET,
+  PROP_FOCUS_WIDGET,
 
   /* Readonly properties */
   PROP_IS_ACTIVE,
@@ -941,8 +942,14 @@ gtk_window_class_init (GtkWindowClass *klass)
                            GTK_TYPE_WIDGET,
                            GTK_PARAM_READWRITE|G_PARAM_STATIC_STRINGS|G_PARAM_EXPLICIT_NOTIFY);
 
+  window_props[PROP_FOCUS_WIDGET] =
+      g_param_spec_object ("focus-widget",
+                           P_("Focus widget"),
+                           P_("The focus widget"),
+                           GTK_TYPE_WIDGET,
+                           GTK_PARAM_READWRITE|G_PARAM_STATIC_STRINGS|G_PARAM_EXPLICIT_NOTIFY);
+
   g_object_class_install_properties (gobject_class, LAST_ARG, window_props);
-  gtk_root_install_properties (gobject_class, LAST_ARG);
 
   /**
    * GtkWindow::activate-focus:
@@ -1858,7 +1865,7 @@ gtk_window_set_property (GObject      *object,
     case PROP_FOCUS_VISIBLE:
       gtk_window_set_focus_visible (window, g_value_get_boolean (value));
       break;
-    case LAST_ARG + GTK_ROOT_PROP_FOCUS_WIDGET:
+    case PROP_FOCUS_WIDGET:
       gtk_window_set_focus (window, g_value_get_object (value));
       break;
     default:
@@ -1941,7 +1948,7 @@ gtk_window_get_property (GObject      *object,
     case PROP_IS_MAXIMIZED:
       g_value_set_boolean (value, gtk_window_is_maximized (window));
       break;
-    case LAST_ARG + GTK_ROOT_PROP_FOCUS_WIDGET:
+    case PROP_FOCUS_WIDGET:
       g_value_set_object (value, gtk_window_get_focus (window));
       break;
     default:
@@ -2028,6 +2035,52 @@ gtk_window_root_get_constraint_solver (GtkRoot *root)
   return priv->constraint_solver;
 }
 
+static GtkWidget *
+gtk_window_root_get_focus (GtkRoot *root)
+{
+  GtkWindow *self = GTK_WINDOW (root);
+  GtkWindowPrivate *priv = gtk_window_get_instance_private (self);
+
+  return priv->focus_widget;
+}
+
+static void synthesize_focus_change_events (GtkWindow *window,
+                                            GtkWidget *old_focus,
+                                            GtkWidget *new_focus);
+
+static void
+gtk_window_root_set_focus (GtkRoot   *root,
+                           GtkWidget *focus)
+{
+  GtkWindow *self = GTK_WINDOW (root);
+  GtkWindowPrivate *priv = gtk_window_get_instance_private (self);
+  GtkWidget *old_focus = NULL;
+
+  if (focus && !gtk_widget_is_sensitive (focus))
+    return;
+
+  if (focus == priv->focus_widget)
+    return;
+
+  if (priv->focus_widget)
+    old_focus = g_object_ref (priv->focus_widget);
+  g_set_object (&priv->focus_widget, NULL);
+
+  if (old_focus)
+    gtk_widget_set_has_focus (old_focus, FALSE);
+
+  synthesize_focus_change_events (self, old_focus, focus);
+
+  if (focus)
+    gtk_widget_set_has_focus (focus, TRUE);
+
+  g_set_object (&priv->focus_widget, focus);
+
+  g_clear_object (&old_focus);
+
+  g_object_notify (G_OBJECT (self), "focus-widget");
+}
+
 static void
 gtk_window_native_get_surface_transform (GtkNative *native,
                                          int       *x,
@@ -2054,6 +2107,8 @@ gtk_window_root_interface_init (GtkRootInterface *iface)
 {
   iface->get_display = gtk_window_root_get_display;
   iface->get_constraint_solver = gtk_window_root_get_constraint_solver;
+  iface->get_focus = gtk_window_root_get_focus;
+  iface->set_focus = gtk_window_root_set_focus;
 }
 
 static void
@@ -5610,34 +5665,9 @@ void
 gtk_window_set_focus (GtkWindow *window,
                       GtkWidget *focus)
 {
-  GtkWindowPrivate *priv = gtk_window_get_instance_private (window);
-  GtkWidget *old_focus = NULL;
-
   g_return_if_fail (GTK_IS_WINDOW (window));
 
-  if (focus && !gtk_widget_is_sensitive (focus))
-    return;
-
-  if (focus == priv->focus_widget)
-    return;
-
-  if (priv->focus_widget)
-    old_focus = g_object_ref (priv->focus_widget);
-  g_set_object (&priv->focus_widget, NULL);
-
-  if (old_focus)
-    gtk_widget_set_has_focus (old_focus, FALSE);
-
-  synthesize_focus_change_events (window, old_focus, focus);
-
-  if (focus)
-    gtk_widget_set_has_focus (focus, TRUE);
-
-  g_set_object (&priv->focus_widget, focus);
-
-  g_clear_object (&old_focus);
-
-  g_object_notify (G_OBJECT (window), "focus-widget");
+  gtk_root_set_focus (GTK_ROOT (window), focus);
 }
 
 static void


[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]