return menu_shell_type;
}
-static guint
-binding_signal_new (const gchar *signal_name,
- GType itype,
- GSignalFlags signal_flags,
- GCallback handler,
- GSignalAccumulator accumulator,
- gpointer accu_data,
- GSignalCMarshaller c_marshaller,
- GType return_type,
- guint n_params,
- ...)
-{
- va_list args;
- guint signal_id;
-
- g_return_val_if_fail (signal_name != NULL, 0);
-
- va_start (args, n_params);
-
- signal_id = g_signal_new_valist (signal_name, itype, signal_flags,
- g_cclosure_new (handler, NULL, NULL),
- accumulator, accu_data, c_marshaller,
- return_type, n_params, args);
-
- va_end (args);
-
- return signal_id;
-}
-
static void
gtk_menu_shell_class_init (GtkMenuShellClass *klass)
{
_gtk_marshal_VOID__VOID,
G_TYPE_NONE, 0);
menu_shell_signals[CYCLE_FOCUS] =
- binding_signal_new ("cycle_focus",
- G_OBJECT_CLASS_TYPE (object_class),
- G_SIGNAL_RUN_LAST | G_SIGNAL_ACTION,
- G_CALLBACK (gtk_real_menu_shell_cycle_focus),
- NULL, NULL,
- _gtk_marshal_VOID__ENUM,
- G_TYPE_NONE, 1,
- GTK_TYPE_DIRECTION_TYPE);
+ _gtk_binding_signal_new ("cycle_focus",
+ G_OBJECT_CLASS_TYPE (object_class),
+ G_SIGNAL_RUN_LAST | G_SIGNAL_ACTION,
+ G_CALLBACK (gtk_real_menu_shell_cycle_focus),
+ NULL, NULL,
+ _gtk_marshal_VOID__ENUM,
+ G_TYPE_NONE, 1,
+ GTK_TYPE_DIRECTION_TYPE);
binding_set = gtk_binding_set_by_class (klass);
menu_shell->active = FALSE;
menu_shell->have_grab = FALSE;
menu_shell->have_xgrab = FALSE;
- menu_shell->ignore_leave = FALSE;
menu_shell->button = 0;
menu_shell->menu_flag = 0;
menu_shell->activate_time = 0;
gtk_widget_event (menu_shell->parent_menu_shell, (GdkEvent*) event);
return TRUE;
}
+
+ /* If we ended up on an item with a submenu, leave the menu up.
+ */
+ if (menu_item && (menu_shell->active_menu_item == menu_item))
+ deactivate = FALSE;
}
- else
+ else /* a very fast press-release */
{
/* We only ever want to prevent deactivation on the first
* press/release. Setting the time to zero is a bit of a
deactivate = FALSE;
}
- /* If the button click was very fast, or we ended up on a submenu,
- * leave the menu up
- */
- if (!deactivate ||
- (menu_item && (menu_shell->active_menu_item == menu_item)))
- {
- deactivate = FALSE;
- menu_shell->ignore_leave = TRUE;
- }
- else
- deactivate = TRUE;
-
if (deactivate)
{
gtk_menu_shell_deactivate (menu_shell);
menu_item = GTK_MENU_ITEM (event_widget);
- if (menu_shell->ignore_leave)
- {
- menu_shell->ignore_leave = FALSE;
- return TRUE;
- }
-
if (!_gtk_menu_item_is_selectable (event_widget))
return TRUE;
class = GTK_MENU_SHELL_GET_CLASS (menu_shell);
- if (class->select_item)
+ if (class->select_item &&
+ !(menu_shell->active &&
+ menu_shell->active_menu_item == menu_item))
class->select_item (menu_shell, menu_item);
}
* Select the first visible or selectable child of the menu shell;
* don't select tearoff items unless the only item is a tearoff
* item.
+ *
+ * Since: 2.2
**/
void
gtk_menu_shell_select_first (GtkMenuShell *menu_shell,
gtk_menu_shell_select_item (menu_shell, to_select);
}
-static void
-gtk_menu_shell_select_last (GtkMenuShell *menu_shell,
- gboolean search_sensitive)
+void
+_gtk_menu_shell_select_last (GtkMenuShell *menu_shell,
+ gboolean search_sensitive)
{
GtkWidget *to_select = NULL;
GList *tmp_list;
gtk_menu_shell_select_submenu_first (parent_menu_shell);
}
}
+ /* If there is no parent and the submenu is in the opposite direction
+ * to the menu, then make the PARENT direction wrap around to
+ * the bottom of the submenu.
+ */
+ else if (menu_shell->active_menu_item &&
+ _gtk_menu_item_is_selectable (menu_shell->active_menu_item) &&
+ GTK_MENU_ITEM (menu_shell->active_menu_item)->submenu)
+ {
+ GtkMenuShell *submenu = GTK_MENU_SHELL (GTK_MENU_ITEM (menu_shell->active_menu_item)->submenu);
+
+ if (GTK_MENU_SHELL_GET_CLASS (menu_shell)->submenu_placement !=
+ GTK_MENU_SHELL_GET_CLASS (submenu)->submenu_placement)
+ _gtk_menu_shell_select_last (submenu, TRUE);
+ }
break;
case GTK_MENU_DIR_CHILD:
if (!had_selection &&
!menu_shell->active_menu_item &&
menu_shell->children)
- gtk_menu_shell_select_last (menu_shell, TRUE);
+ _gtk_menu_shell_select_last (menu_shell, TRUE);
break;
case GTK_MENU_DIR_NEXT:
gtk_menu_shell_move_selected (menu_shell, 1);
gint popup_delay;
GtkWidget *widget = GTK_WIDGET (menu_shell);
- g_object_get (G_OBJECT (gtk_widget_get_settings (widget)),
+ g_object_get (gtk_widget_get_settings (widget),
"gtk-menu-popup-delay", &popup_delay,
NULL);