📄 gtkmenuitem.c
字号:
allocation->x, allocation->y, allocation->width, allocation->height); if (menu_item->submenu) gtk_menu_reposition (GTK_MENU (menu_item->submenu));}static voidgtk_menu_item_paint (GtkWidget *widget, GdkRectangle *area){ GtkMenuItem *menu_item; GtkStateType state_type; GtkShadowType shadow_type; gint width, height; gint x, y; g_return_if_fail (widget != NULL); g_return_if_fail (GTK_IS_MENU_ITEM (widget)); if (GTK_WIDGET_DRAWABLE (widget)) { menu_item = GTK_MENU_ITEM (widget); state_type = widget->state; x = GTK_CONTAINER (menu_item)->border_width; y = GTK_CONTAINER (menu_item)->border_width; width = widget->allocation.width - x * 2; height = widget->allocation.height - y * 2; if ((state_type == GTK_STATE_PRELIGHT) && (GTK_BIN (menu_item)->child)) gtk_paint_box (widget->style, widget->window, GTK_STATE_PRELIGHT, GTK_SHADOW_OUT, area, widget, "menuitem", x, y, width, height); else { gdk_window_set_back_pixmap (widget->window, NULL, TRUE); gdk_window_clear_area (widget->window, area->x, area->y, area->width, area->height); } if (menu_item->submenu && menu_item->show_submenu_indicator) { shadow_type = GTK_SHADOW_OUT; if (state_type == GTK_STATE_PRELIGHT) shadow_type = GTK_SHADOW_IN; gtk_paint_arrow (widget->style, widget->window, state_type, shadow_type, area, widget, "menuitem", GTK_ARROW_RIGHT, TRUE, x + width - 15, y + height / 2 - 5, 10, 10); } else if (!GTK_BIN (menu_item)->child) { gtk_paint_hline (widget->style, widget->window, GTK_STATE_NORMAL, area, widget, "menuitem", 0, widget->allocation.width, 0); } }}static voidgtk_menu_item_draw (GtkWidget *widget, GdkRectangle *area){ GtkBin *bin; GdkRectangle child_area; g_return_if_fail (widget != NULL); g_return_if_fail (GTK_IS_MENU_ITEM (widget)); g_return_if_fail (area != NULL); if (GTK_WIDGET_DRAWABLE (widget)) { gtk_menu_item_paint (widget, area); bin = GTK_BIN (widget); if (bin->child) { if (gtk_widget_intersect (bin->child, area, &child_area)) gtk_widget_draw (bin->child, &child_area); } }}static gintgtk_menu_item_expose (GtkWidget *widget, GdkEventExpose *event){ GtkBin *bin; GdkEventExpose child_event; g_return_val_if_fail (widget != NULL, FALSE); g_return_val_if_fail (GTK_IS_MENU_ITEM (widget), FALSE); g_return_val_if_fail (event != NULL, FALSE); if (GTK_WIDGET_DRAWABLE (widget)) { gtk_menu_item_paint (widget, &event->area); bin = GTK_BIN (widget); if (bin->child) { child_event = *event; if (GTK_WIDGET_NO_WINDOW (bin->child) && gtk_widget_intersect (bin->child, &event->area, &child_event.area)) gtk_widget_event (bin->child, (GdkEvent*) &child_event); } } return FALSE;}static voidgtk_real_menu_item_select (GtkItem *item){ GtkMenuItem *menu_item; g_return_if_fail (item != NULL); g_return_if_fail (GTK_IS_MENU_ITEM (item)); menu_item = GTK_MENU_ITEM (item); /* if (menu_item->submenu && !GTK_WIDGET_VISIBLE (menu_item->submenu))*/ if (menu_item->submenu) { guint32 etime; GdkEvent *event = gtk_get_current_event (); etime = event ? gdk_event_get_time (event) : GDK_CURRENT_TIME; if (etime >= last_submenu_deselect_time && last_submenu_deselect_time + SELECT_TIMEOUT > etime) menu_item->timer = gtk_timeout_add (SELECT_TIMEOUT - (etime - last_submenu_deselect_time), gtk_menu_item_select_timeout, menu_item); else gtk_menu_item_select_timeout_unlocked (menu_item); if(event) gdk_event_free(event); } gtk_widget_set_state (GTK_WIDGET (menu_item), GTK_STATE_PRELIGHT); gtk_widget_draw (GTK_WIDGET (menu_item), NULL);}static voidgtk_real_menu_item_deselect (GtkItem *item){ GtkMenuItem *menu_item; g_return_if_fail (item != NULL); g_return_if_fail (GTK_IS_MENU_ITEM (item)); menu_item = GTK_MENU_ITEM (item); if (menu_item->submenu) { guint32 etime; GdkEvent *event = gtk_get_current_event (); if (menu_item->timer) { gtk_timeout_remove (menu_item->timer); menu_item->timer = 0; } else gtk_menu_popdown (GTK_MENU (menu_item->submenu)); etime = event ? gdk_event_get_time (event) : GDK_CURRENT_TIME; if (etime > last_submenu_deselect_time) last_submenu_deselect_time = etime; if(event) gdk_event_free(event); } gtk_widget_set_state (GTK_WIDGET (menu_item), GTK_STATE_NORMAL); gtk_widget_draw (GTK_WIDGET (menu_item), NULL);}static voidgtk_real_menu_item_activate_item (GtkMenuItem *menu_item){ GtkWidget *widget; g_return_if_fail (menu_item != NULL); g_return_if_fail (GTK_IS_MENU_ITEM (menu_item)); widget = GTK_WIDGET (menu_item); if (widget->parent && GTK_IS_MENU_SHELL (widget->parent)) { if (menu_item->submenu == NULL) gtk_menu_shell_activate_item (GTK_MENU_SHELL (widget->parent), widget, TRUE); else { GtkMenuShell *menu_shell = GTK_MENU_SHELL (widget->parent); if (!menu_shell->active) { gtk_grab_add (GTK_WIDGET (menu_shell)); menu_shell->have_grab = TRUE; menu_shell->active = TRUE; } gtk_menu_shell_select_item (GTK_MENU_SHELL (widget->parent), widget); } }}static gintgtk_menu_item_select_timeout (gpointer data){ GDK_THREADS_ENTER (); gtk_menu_item_select_timeout_unlocked (data); GDK_THREADS_LEAVE (); return FALSE; }static voidgtk_menu_item_select_timeout_unlocked (gpointer data){ GtkMenuItem *menu_item; menu_item = GTK_MENU_ITEM (data); menu_item->timer = 0; if (GTK_WIDGET_IS_SENSITIVE (menu_item->submenu)) { gtk_menu_popup (GTK_MENU (menu_item->submenu), GTK_WIDGET (menu_item)->parent, GTK_WIDGET (menu_item), gtk_menu_item_position_menu, menu_item, GTK_MENU_SHELL (GTK_WIDGET (menu_item)->parent)->button, 0); /* This is a bit of a hack - we want to select the first item * of menus hanging of a menu bar, but not for cascading submenus */ if (GTK_IS_MENU_BAR (GTK_WIDGET (menu_item)->parent)) { GtkMenuShell *submenu = GTK_MENU_SHELL (menu_item->submenu); if (submenu->children) gtk_menu_shell_select_item (submenu, submenu->children->data); } }}static voidgtk_menu_item_position_menu (GtkMenu *menu, gint *x, gint *y, gpointer user_data){ GtkMenuItem *menu_item; GtkWidget *parent_menu_item; gint screen_width; gint screen_height; gint twidth, theight; gint tx, ty; g_return_if_fail (menu != NULL); g_return_if_fail (x != NULL); g_return_if_fail (y != NULL); menu_item = GTK_MENU_ITEM (user_data); twidth = GTK_WIDGET (menu)->requisition.width; theight = GTK_WIDGET (menu)->requisition.height; screen_width = gdk_screen_width (); screen_height = gdk_screen_height (); if (!gdk_window_get_origin (GTK_WIDGET (menu_item)->window, &tx, &ty)) { g_warning ("Menu not on screen"); return; } switch (menu_item->submenu_placement) { case GTK_TOP_BOTTOM: if ((ty + GTK_WIDGET (menu_item)->allocation.height + theight) <= screen_height) ty += GTK_WIDGET (menu_item)->allocation.height; else if ((ty - theight) >= 0) ty -= theight; else ty += GTK_WIDGET (menu_item)->allocation.height; break; case GTK_LEFT_RIGHT: menu_item->submenu_direction = GTK_DIRECTION_RIGHT; parent_menu_item = GTK_MENU (GTK_WIDGET (menu_item)->parent)->parent_menu_item; if (parent_menu_item) menu_item->submenu_direction = GTK_MENU_ITEM (parent_menu_item)->submenu_direction; switch (menu_item->submenu_direction) { case GTK_DIRECTION_LEFT: if ((tx - twidth) >= 0) tx -= twidth; else { menu_item->submenu_direction = GTK_DIRECTION_RIGHT; tx += GTK_WIDGET (menu_item)->allocation.width - 5; } break; case GTK_DIRECTION_RIGHT: if ((tx + GTK_WIDGET (menu_item)->allocation.width + twidth - 5) <= screen_width) tx += GTK_WIDGET (menu_item)->allocation.width - 5; else { menu_item->submenu_direction = GTK_DIRECTION_LEFT; tx -= twidth; } break; } ty += GTK_WIDGET (menu_item)->allocation.height / 4; break; } /* If we have negative, tx, ty here it is because we can't get * the menu all the way on screen. Favor the upper-left portion. */ *x = CLAMP (tx, 0, MAX (0, screen_width - twidth)); *y = CLAMP (ty, 0, MAX (0, screen_height - theight));}voidgtk_menu_item_right_justify(GtkMenuItem *menuitem){ g_return_if_fail (menuitem != NULL); g_return_if_fail (GTK_IS_MENU_ITEM (menuitem)); menuitem->right_justify = 1;}static voidgtk_menu_item_show_all (GtkWidget *widget){ GtkMenuItem *menu_item; g_return_if_fail (widget != NULL); g_return_if_fail (GTK_IS_MENU_ITEM (widget)); menu_item = GTK_MENU_ITEM (widget); /* show children including submenu */ if (menu_item->submenu) gtk_widget_show_all (menu_item->submenu); gtk_container_foreach (GTK_CONTAINER (widget), (GtkCallback) gtk_widget_show_all, NULL); gtk_widget_show (widget);}static voidgtk_menu_item_hide_all (GtkWidget *widget){ GtkMenuItem *menu_item; g_return_if_fail (widget != NULL); g_return_if_fail (GTK_IS_MENU_ITEM (widget)); gtk_widget_hide (widget); menu_item = GTK_MENU_ITEM (widget); /* hide children including submenu */ gtk_container_foreach (GTK_CONTAINER (widget), (GtkCallback) gtk_widget_hide_all, NULL); if (menu_item->submenu) gtk_widget_hide_all (menu_item->submenu);}static voidgtk_menu_item_forall (GtkContainer *container, gboolean include_internals, GtkCallback callback, gpointer callback_data){ GtkBin *bin; GtkMenuItem *menu_item; g_return_if_fail (container != NULL); g_return_if_fail (GTK_IS_MENU_ITEM (container)); g_return_if_fail (callback != NULL); bin = GTK_BIN (container); menu_item = GTK_MENU_ITEM (container); if (bin->child) (* callback) (bin->child, callback_data); if (include_internals && menu_item->submenu) (* callback) (menu_item->submenu, callback_data);}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -