/* STRING argument of last `x-show-tip' call. */
Lisp_Object tip_last_string;
-/* FRAME argument of last `x-show-tip' call. */
+/* Normalized FRAME argument of last `x-show-tip' call. */
Lisp_Object tip_last_frame;
/* PARMS argument of last `x-show-tip' call. */
specbind (Qinhibit_redisplay, Qt);
CHECK_STRING (string);
+
+ if (NILP (frame))
+ frame = selected_frame;
decode_window_system_frame (frame);
+
if (NILP (timeout))
timeout = make_number (5);
else
parms = Fcons (Fcons (Qbackground_color, build_string ("lightyellow")),
parms);
- /* Create a frame for the tooltip, and record it in the global
+ /* Create a frame for the tooltip and record it in the global
variable tip_frame. */
struct frame *f; /* The value is unused. */
if (NILP (tip_frame = x_create_tip_frame (FRAME_DISPLAY_INFO (f), parms)))
/* An alist with parameters. */
Lisp_Object window_parameters;
+ /* The help echo text for this window. Qnil if there's none. */
+ Lisp_Object mode_line_help_echo;
+
/* No Lisp data may follow below this point without changing
mark_object in alloc.c. The member current_matrix must be the
first non-Lisp member. */
w->redisplay_end_trigger = val;
}
+INLINE void
+wset_mode_line_help_echo (struct window *w, Lisp_Object val)
+{
+ w->mode_line_help_echo = val;
+}
+
INLINE void
wset_new_pixel (struct window *w, Lisp_Object val)
{
Lisp_Object old_frame_selected_window = XFRAME (new_frame)->selected_window;
int n = 0;
+ if (window_wants_mode_line (w))
+ {
+ Lisp_Object window;
+ Lisp_Object default_help
+ = buffer_local_value (Qmode_line_default_help_echo, w->contents);
+
+ /* Set up mode line help echo. Do this before selecting w so it
+ can reasonably tell whether a mouse click will select w. */
+ XSETWINDOW (window, w);
+ if (FUNCTIONP (default_help))
+ wset_mode_line_help_echo (w, safe_call1 (default_help, window));
+ else if (STRINGP (default_help))
+ wset_mode_line_help_echo (w, default_help);
+ else
+ wset_mode_line_help_echo (w, Qnil);
+ }
+
selected_frame = new_frame;
/* FIXME: If we were to allow the mode-line's computation changing the buffer
or window's point, then we'd need select_window_1 here as well. */
{
Lisp_Object window_mode_line_format
= window_parameter (w, Qmode_line_format);
-
struct window *sel_w = XWINDOW (old_selected_window);
/* Select mode line face based on the real selected window. */
struct window *w = XWINDOW (window);
struct frame *f = XFRAME (w->frame);
Mouse_HLInfo *hlinfo = MOUSE_HL_INFO (f);
-#ifdef HAVE_WINDOW_SYSTEM
- Display_Info *dpyinfo;
-#endif
Cursor cursor = No_Cursor;
Lisp_Object pointer = Qnil;
int dx, dy, width, height;
/* Set the help text and mouse pointer. If the mouse is on a part
of the mode line without any text (e.g. past the right edge of
- the mode line text), use the default help text and pointer. */
+ the mode line text), use that windows's mode line help echo if it
+ has been set. */
if (STRINGP (string) || area == ON_MODE_LINE)
{
/* Arrange to display the help by setting the global variables
help_echo_object = string;
help_echo_pos = charpos;
}
- else if (area == ON_MODE_LINE)
+ else if (area == ON_MODE_LINE
+ && !NILP (w->mode_line_help_echo))
{
- Lisp_Object default_help
- = buffer_local_value (Qmode_line_default_help_echo,
- w->contents);
-
- if (FUNCTIONP (default_help) || STRINGP (default_help))
- {
- help_echo_string = (FUNCTIONP (default_help)
- ? safe_call1 (default_help, window)
- : default_help);
- XSETWINDOW (help_echo_window, w);
- help_echo_object = Qnil;
- help_echo_pos = -1;
- }
+ help_echo_string = w->mode_line_help_echo;
+ XSETWINDOW (help_echo_window, w);
+ help_echo_object = Qnil;
+ help_echo_pos = -1;
}
}
|| minibuf_level
|| NILP (Vresize_mini_windows));
- dpyinfo = FRAME_DISPLAY_INFO (f);
if (STRINGP (string))
{
cursor = FRAME_X_OUTPUT (f)->nontext_cursor;
/* Change the mouse pointer according to what is under X/Y. */
if (NILP (pointer)
- && ((area == ON_MODE_LINE) || (area == ON_HEADER_LINE)))
+ && (area == ON_MODE_LINE || area == ON_HEADER_LINE))
{
Lisp_Object map;
+
map = Fget_text_property (pos, Qlocal_map, string);
if (!KEYMAPP (map))
map = Fget_text_property (pos, Qkeymap, string);
- if (!KEYMAPP (map) && draggable)
- cursor = dpyinfo->vertical_scroll_bar_cursor;
+ if (!KEYMAPP (map) && draggable && area == ON_MODE_LINE)
+ cursor = FRAME_X_OUTPUT (f)->vertical_drag_cursor;
}
}
- else if (draggable)
- /* Default mode-line pointer. */
- cursor = FRAME_DISPLAY_INFO (f)->vertical_scroll_bar_cursor;
+ else if (draggable && area == ON_MODE_LINE)
+ cursor = FRAME_X_OUTPUT (f)->vertical_drag_cursor;
+ else
+ cursor = FRAME_X_OUTPUT (f)->nontext_cursor;
}
#endif
}
/* Change the mouse face according to what is under X/Y. */
bool mouse_face_shown = false;
+
if (STRINGP (string))
{
mouse_face = Fget_text_property (pos, Qmouse_face, string);
/* STRING argument of last `x-show-tip' call. */
static Lisp_Object tip_last_string;
-/* FRAME argument of last `x-show-tip' call. */
+/* Normalized FRAME argument of last `x-show-tip' call. */
static Lisp_Object tip_last_frame;
/* PARMS argument of last `x-show-tip' call. */
}
#ifdef USE_GTK
- /* The GTK+ system tooltip window can be found via the x_output
- structure of tip_last_frame, if it still exists. */
- if (x_gtk_use_system_tooltips && NILP (tip_last_frame))
- return Qnil;
- else if (!x_gtk_use_system_tooltips
- && (NILP (tip_frame)
- || (!delete
- && FRAMEP (tip_frame)
- && FRAME_LIVE_P (XFRAME (tip_frame))
- && !FRAME_VISIBLE_P (XFRAME (tip_frame)))))
+ /* Any GTK+ system tooltip can be found via the x_output structure of
+ tip_last_frame, provided that frame is still live. Any Emacs
+ tooltip is found via the tip_frame variable. Note that the current
+ value of x_gtk_use_system_tooltips might not be the same as used
+ for the tooltip we have to hide, see Bug#30399. */
+ if ((NILP (tip_last_frame) && NILP (tip_frame))
+ || (!x_gtk_use_system_tooltips
+ && !delete
+ && FRAMEP (tip_frame)
+ && FRAME_LIVE_P (XFRAME (tip_frame))
+ && !FRAME_VISIBLE_P (XFRAME (tip_frame))))
+ /* Either there's no tooltip to hide or it's an already invisible
+ Emacs tooltip and we don't want to change its type. Return
+ quickly. */
return Qnil;
else
{
specbind (Qinhibit_redisplay, Qt);
specbind (Qinhibit_quit, Qt);
- if (x_gtk_use_system_tooltips)
+ /* Try to hide the GTK+ system tip first. */
+ if (FRAMEP (tip_last_frame))
{
- /* The GTK+ system tooltip window is stored in the x_output
- structure of tip_last_frame. */
struct frame *f = XFRAME (tip_last_frame);
if (FRAME_LIVE_P (f))
if (xg_hide_tooltip (f))
was_open = Qt;
}
- else
- tip_last_frame = Qnil;
}
- else
+
+ /* Reset tip_last_frame, it will be reassigned when showing the
+ next GTK+ system tooltip. */
+ tip_last_frame = Qnil;
+
+ /* Now look whether there's an Emacs tip around. */
+ if (FRAMEP (tip_frame))
{
- if (FRAMEP (tip_frame))
- {
- struct frame *f = XFRAME (tip_frame);
+ struct frame *f = XFRAME (tip_frame);
- if (FRAME_LIVE_P (f))
+ if (FRAME_LIVE_P (f))
+ {
+ if (delete || x_gtk_use_system_tooltips)
{
- if (delete)
- {
- delete_frame (tip_frame, Qnil);
- tip_frame = Qnil;
- }
- else
- x_make_frame_invisible (f);
-
- was_open = Qt;
+ /* Delete the Emacs tooltip frame when DELETE is true
+ or we change the tooltip type from an Emacs one to
+ a GTK+ system one. */
+ delete_frame (tip_frame, Qnil);
+ tip_frame = Qnil;
}
else
- tip_frame = Qnil;
+ x_make_frame_invisible (f);
+
+ was_open = Qt;
}
else
tip_frame = Qnil;
}
+ else
+ tip_frame = Qnil;
return unbind_to (count, was_open);
}
if (SCHARS (string) == 0)
string = make_unibyte_string (" ", 1);
+ if (NILP (frame))
+ frame = selected_frame;
f = decode_window_system_frame (frame);
+
if (NILP (timeout))
timeout = make_number (5);
else