diff options
author | Søren Sandmann <sandmann@redhat.com> | 2004-12-22 16:52:23 +0000 |
---|---|---|
committer | Søren Sandmann Pedersen <ssp@src.gnome.org> | 2004-12-22 16:52:23 +0000 |
commit | 03413577a1ee364109a181c5c7711c2b118a703b (patch) | |
tree | cf415c25d5ff14092b159f726a621f0ffa08f1ff /gtk/gtkmenu.c | |
parent | 5ec1648473815ab4d09ab1151f22c55d59c1cc8c (diff) | |
download | gdk-pixbuf-03413577a1ee364109a181c5c7711c2b118a703b.tar.gz |
Bug #147497, make menu items activate immediately when you release the
Wed Dec 22 11:35:41 2004 Søren Sandmann <sandmann@redhat.com>
Bug #147497, make menu items activate immediately when you release
the button.
* gtk/gtkmenu.c (gtk_menu_enter_notify, menu_motion_notify): Make
items activate immediately.
* gtk/gtkmenu.c (definitely_within_item): New function
* gtk/gtkmenu.c (check_threshold): New function
Diffstat (limited to 'gtk/gtkmenu.c')
-rw-r--r-- | gtk/gtkmenu.c | 76 |
1 files changed, 76 insertions, 0 deletions
diff --git a/gtk/gtkmenu.c b/gtk/gtkmenu.c index 71048e84a..7266bb756 100644 --- a/gtk/gtkmenu.c +++ b/gtk/gtkmenu.c @@ -76,6 +76,8 @@ struct _GtkMenuAttachData struct _GtkMenuPrivate { + gboolean seen_item_enter; + gboolean have_position; gint x; gint y; @@ -1278,6 +1280,7 @@ gtk_menu_popup (GtkMenu *menu, GtkWidget *parent; GdkEvent *current_event; GtkMenuShell *menu_shell; + GtkMenuPrivate *priv = gtk_menu_get_private (menu); g_return_if_fail (GTK_IS_MENU (menu)); @@ -1285,6 +1288,8 @@ gtk_menu_popup (GtkMenu *menu, menu_shell = GTK_MENU_SHELL (menu); menu_shell->parent_menu_shell = parent_menu_shell; + + priv->seen_item_enter = FALSE; /* Find the last viewable ancestor, and make an X grab on it */ @@ -2718,12 +2723,42 @@ gtk_menu_key_press (GtkWidget *widget, } static gboolean +check_threshold (GtkWidget *widget, + int start_x, int start_y, + int x, int y) +{ +#define THRESHOLD 8 + + return + ABS (start_x - x) > THRESHOLD || + ABS (start_y - y) > THRESHOLD; +} + +static gboolean +definitely_within_item (GtkWidget *widget, + int x, + int y) +{ + GdkWindow *window = GTK_MENU_ITEM (widget)->event_window; + int w, h; + + gdk_drawable_get_size (window, &w, &h); + + return + check_threshold (widget, 0, 0, x, y) && + check_threshold (widget, w - 1, 0, x, y) && + check_threshold (widget, w - 1, h - 1, x, y) && + check_threshold (widget, 0, h - 1, x, y); +} + +static gboolean gtk_menu_motion_notify (GtkWidget *widget, GdkEventMotion *event) { GtkWidget *menu_item; GtkMenu *menu; GtkMenuShell *menu_shell; + GtkMenuPrivate *priv; gboolean need_enter; @@ -2746,6 +2781,11 @@ gtk_menu_motion_notify (GtkWidget *widget, menu_shell = GTK_MENU_SHELL (menu_item->parent); menu = GTK_MENU (menu_shell); + + priv = gtk_menu_get_private (GTK_MENU (widget)); + + if (definitely_within_item (menu_item, event->x, event->y)) + menu_shell->activate_time = 0; need_enter = (menu->navigation_region != NULL || menu_shell->ignore_enter); @@ -2993,6 +3033,42 @@ gtk_menu_enter_notify (GtkWidget *widget, if (!menu_shell->ignore_enter) gtk_menu_handle_scrolling (GTK_MENU (widget), TRUE); } + + if (menu_item && GTK_IS_MENU_ITEM (menu_item)) + { + GtkWidget *menu = menu_item->parent; + + if (menu && GTK_IS_MENU (menu)) + { + GtkMenuPrivate *priv = gtk_menu_get_private (GTK_MENU (menu)); + GtkMenuShell *menu_shell = GTK_MENU_SHELL (menu); + + if (priv->seen_item_enter) + { + /* This is the second enter we see for an item + * on this menu. This means a release should always + * mean activate. + */ + menu_shell->activate_time = 0; + } + else if ((event->detail != GDK_NOTIFY_NONLINEAR && + event->detail != GDK_NOTIFY_NONLINEAR_VIRTUAL)) + { + if (definitely_within_item (menu_item, event->x, event->y)) + { + /* This is an actual user-enter (ie. not a pop-under) + * In this case, the user must either have entered + * sufficiently far enough into the item, or he must move + * far enough away from the enter point. (see + * gtk_menu_motion_notify()) + */ + menu_shell->activate_time = 0; + } + } + + priv->seen_item_enter = TRUE; + } + } /* If this is a faked enter (see gtk_menu_motion_notify), 'widget' * will not correspond to the event widget's parent. Check to see |