summaryrefslogtreecommitdiff
path: root/src/menu.c
diff options
context:
space:
mode:
Diffstat (limited to 'src/menu.c')
-rw-r--r--src/menu.c55
1 files changed, 41 insertions, 14 deletions
diff --git a/src/menu.c b/src/menu.c
index 7b6fdf812c5..398bf9329ff 100644
--- a/src/menu.c
+++ b/src/menu.c
@@ -50,7 +50,8 @@ extern AppendMenuW_Proc unicode_append_menu;
static bool
have_boxes (void)
{
-#if defined (USE_X_TOOLKIT) || defined (USE_GTK) || defined (HAVE_NTGUI) || defined(HAVE_NS)
+#if defined (USE_X_TOOLKIT) || defined (USE_GTK) || defined (HAVE_NTGUI) || defined (HAVE_NS) \
+ || defined (HAVE_HAIKU)
if (FRAME_WINDOW_P (XFRAME (Vmenu_updating_frame)))
return 1;
#endif
@@ -422,7 +423,8 @@ single_menu_item (Lisp_Object key, Lisp_Object item, Lisp_Object dummy, void *sk
AREF (item_properties, ITEM_PROPERTY_SELECTED),
AREF (item_properties, ITEM_PROPERTY_HELP));
-#if defined (USE_X_TOOLKIT) || defined (USE_GTK) || defined (HAVE_NS) || defined (HAVE_NTGUI)
+#if defined (USE_X_TOOLKIT) || defined (USE_GTK) || defined (HAVE_NS) \
+ || defined (HAVE_NTGUI) || defined (HAVE_HAIKU) || defined (HAVE_PGTK)
/* Display a submenu using the toolkit. */
if (FRAME_WINDOW_P (XFRAME (Vmenu_updating_frame))
&& ! (NILP (map) || NILP (enabled)))
@@ -872,6 +874,10 @@ update_submenu_strings (widget_value *first_wv)
}
}
+#endif /* USE_X_TOOLKIT || USE_GTK || HAVE_NS || HAVE_NTGUI */
+#if defined (USE_X_TOOLKIT) || defined (USE_GTK) || defined (HAVE_NS) \
+ || defined (HAVE_NTGUI) || defined (HAVE_HAIKU)
+
/* Find the menu selection and store it in the keyboard buffer.
F is the frame the menu is on.
MENU_BAR_ITEMS_USED is the length of VECTOR.
@@ -959,7 +965,7 @@ find_and_call_menu_selection (struct frame *f, int menu_bar_items_used,
SAFE_FREE ();
}
-#endif /* USE_X_TOOLKIT || USE_GTK || HAVE_NS || HAVE_NTGUI */
+#endif /* USE_X_TOOLKIT || USE_GTK || HAVE_NS || HAVE_NTGUI || HAVE_HAIKU */
#ifdef HAVE_NS
/* As above, but return the menu selection instead of storing in kb buffer.
@@ -1107,7 +1113,7 @@ into menu items. */)
Lisp_Object
x_popup_menu_1 (Lisp_Object position, Lisp_Object menu)
{
- Lisp_Object keymap, tem, tem2;
+ Lisp_Object keymap, tem, tem2 = Qnil;
int xpos = 0, ypos = 0;
Lisp_Object title;
const char *error_name = NULL;
@@ -1115,7 +1121,7 @@ x_popup_menu_1 (Lisp_Object position, Lisp_Object menu)
struct frame *f = NULL;
Lisp_Object x, y, window;
int menuflags = 0;
- ptrdiff_t specpdl_count = SPECPDL_INDEX ();
+ specpdl_ref specpdl_count = SPECPDL_INDEX ();
if (NILP (position))
/* This is an obsolete call, which wants us to precompute the
@@ -1246,8 +1252,21 @@ x_popup_menu_1 (Lisp_Object position, Lisp_Object menu)
CHECK_LIVE_WINDOW (window);
f = XFRAME (WINDOW_FRAME (win));
- xpos = WINDOW_LEFT_EDGE_X (win);
- ypos = WINDOW_TOP_EDGE_Y (win);
+ if (FIXNUMP (tem2))
+ {
+ /* Clicks in the text area, where TEM2 is a buffer
+ position, are relative to the top-left edge of the text
+ area, see keyboard.c:make_lispy_position. */
+ xpos = window_box_left (win, TEXT_AREA);
+ ypos = (WINDOW_TOP_EDGE_Y (win)
+ + WINDOW_TAB_LINE_HEIGHT (win)
+ + WINDOW_HEADER_LINE_HEIGHT (win));
+ }
+ else
+ {
+ xpos = WINDOW_LEFT_EDGE_X (win);
+ ypos = WINDOW_TOP_EDGE_Y (win);
+ }
}
else
/* ??? Not really clean; should be CHECK_WINDOW_OR_FRAME,
@@ -1372,9 +1391,9 @@ x_popup_menu_1 (Lisp_Object position, Lisp_Object menu)
}
#endif
-#ifdef HAVE_NS /* FIXME: ns-specific, why? --Stef */
record_unwind_protect_void (discard_menu_items);
-#endif
+
+ run_hook (Qx_pre_popup_menu_hook);
/* Display them in a menu, but not if F is the initial frame that
doesn't have its hooks set (e.g., in a batch session), because
@@ -1383,13 +1402,13 @@ x_popup_menu_1 (Lisp_Object position, Lisp_Object menu)
selection = FRAME_TERMINAL (f)->menu_show_hook (f, xpos, ypos, menuflags,
title, &error_name);
-#ifdef HAVE_NS
unbind_to (specpdl_count, Qnil);
-#else
- discard_menu_items ();
-#endif
-#ifdef HAVE_NTGUI /* FIXME: Is it really w32-specific? --Stef */
+#ifdef HAVE_NTGUI /* W32 specific because other terminals clear
+ the grab inside their `menu_show_hook's if
+ it's actually required (i.e. there isn't a
+ way to query the buttons currently held down
+ after XMenuActivate). */
if (FRAME_W32_P (f))
FRAME_DISPLAY_INFO (f)->grabbed = 0;
#endif
@@ -1583,6 +1602,14 @@ syms_of_menu (void)
staticpro (&menu_items);
DEFSYM (Qhide, "hide");
+ DEFSYM (Qx_pre_popup_menu_hook, "x-pre-popup-menu-hook");
+
+ DEFVAR_LISP ("x-pre-popup-menu-hook", Vx_pre_popup_menu_hook,
+ doc: /* Hook run before `x-popup-menu' displays a popup menu.
+It is only run before the menu is really going to be displayed. It
+won't be run if `x-popup-menu' fails or returns for some other reason
+(such as the keymap is invalid). */);
+ Vx_pre_popup_menu_hook = Qnil;
defsubr (&Sx_popup_menu);
defsubr (&Sx_popup_dialog);