[gnome-builder] gui: show omnibar popover on release



commit 62827e987740e8a3e3dffa82f444b3bdaf4c40be
Author: Christian Hergert <chergert redhat com>
Date:   Wed Jan 23 16:35:32 2019 -0800

    gui: show omnibar popover on release
    
    If we wait until button release, we can allow dragging the window by
    grabbing that area. This also helps with touch support.
    
    Fixes #781

 src/libide/gui/ide-omni-bar.c | 66 +++++++++++++++++++++++++++++++++++++++++--
 1 file changed, 64 insertions(+), 2 deletions(-)
---
diff --git a/src/libide/gui/ide-omni-bar.c b/src/libide/gui/ide-omni-bar.c
index fbf8c6399..0fc897447 100644
--- a/src/libide/gui/ide-omni-bar.c
+++ b/src/libide/gui/ide-omni-bar.c
@@ -50,6 +50,8 @@ struct _IdeOmniBar
   GtkProgressBar       *progress;
   GtkWidget            *placeholder;
   DzlPriorityBox       *sections_box;
+
+  guint                 in_button : 1;
 };
 
 static void ide_omni_bar_move_next     (IdeOmniBar        *self,
@@ -101,7 +103,11 @@ multipress_pressed_cb (IdeOmniBar           *self,
   g_assert (IDE_IS_OMNI_BAR (self));
   g_assert (GTK_IS_GESTURE_MULTI_PRESS (gesture));
 
-  gtk_popover_popup (self->popover);
+  if (gtk_widget_get_focus_on_click (GTK_WIDGET (self)) &&
+      !gtk_widget_has_focus (GTK_WIDGET (self)))
+    gtk_widget_grab_focus (GTK_WIDGET (self));
+
+  self->in_button = TRUE;
 
   style_context = gtk_widget_get_style_context (GTK_WIDGET (self));
   state_flags = gtk_style_context_get_state (style_context);
@@ -110,6 +116,52 @@ multipress_pressed_cb (IdeOmniBar           *self,
   gtk_gesture_set_state (GTK_GESTURE (gesture), GTK_EVENT_SEQUENCE_CLAIMED);
 }
 
+static void
+multipress_released_cb (IdeOmniBar           *self,
+                        guint                 n_press,
+                        gdouble               x,
+                        gdouble               y,
+                        GtkGestureMultiPress *gesture)
+{
+  GtkStyleContext *style_context;
+  GtkStateFlags state_flags;
+  gboolean show;
+
+  g_assert (IDE_IS_OMNI_BAR (self));
+  g_assert (GTK_IS_GESTURE_MULTI_PRESS (gesture));
+
+  show = self->in_button;
+  self->in_button = FALSE;
+
+  if (show)
+    {
+      gtk_popover_popup (self->popover);
+      return;
+    }
+
+  style_context = gtk_widget_get_style_context (GTK_WIDGET (self));
+  state_flags = gtk_style_context_get_state (style_context);
+  gtk_style_context_set_state (style_context, state_flags & ~GTK_STATE_FLAG_ACTIVE);
+}
+
+static void
+multipress_cancel_cb (IdeOmniBar           *self,
+                      GdkEventSequence     *sequence,
+                      GtkGestureMultiPress *gesture)
+{
+  GtkStyleContext *style_context;
+  GtkStateFlags state_flags;
+
+  g_assert (IDE_IS_OMNI_BAR (self));
+  g_assert (GTK_IS_GESTURE_MULTI_PRESS (gesture));
+
+  self->in_button = FALSE;
+
+  style_context = gtk_widget_get_style_context (GTK_WIDGET (self));
+  state_flags = gtk_style_context_get_state (style_context);
+  gtk_style_context_set_state (style_context, state_flags & ~GTK_STATE_FLAG_ACTIVE);
+}
+
 static void
 ide_omni_bar_notification_stack_changed_cb (IdeOmniBar           *self,
                                             IdeNotificationStack *stack)
@@ -439,11 +491,21 @@ ide_omni_bar_init (IdeOmniBar *self)
                             self);
 
   self->gesture = gtk_gesture_multi_press_new (GTK_WIDGET (self));
-
+  gtk_gesture_single_set_touch_only (GTK_GESTURE_SINGLE (self->gesture), FALSE);
+  gtk_gesture_single_set_exclusive (GTK_GESTURE_SINGLE (self->gesture), TRUE);
+  gtk_gesture_single_set_button (GTK_GESTURE_SINGLE (self->gesture), GDK_BUTTON_PRIMARY);
   g_signal_connect_swapped (self->gesture,
                             "pressed",
                             G_CALLBACK (multipress_pressed_cb),
                             self);
+  g_signal_connect_swapped (self->gesture,
+                            "released",
+                            G_CALLBACK (multipress_released_cb),
+                            self);
+  g_signal_connect_swapped (self->gesture,
+                            "cancel",
+                            G_CALLBACK (multipress_cancel_cb),
+                            self);
 
   g_signal_connect_object (self->notification_stack,
                            "changed",


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