commit 50549cefcd5e2837cf73aa4524f9c87faeba2cec (HEAD, refs/remotes/origin/master) Author: Paul Eggert Date: Wed Jun 21 00:06:44 2023 -0700 * configure.ac: Update GCC bug number in comment. diff --git a/configure.ac b/configure.ac index d6592ded8ea..dffdef48c10 100644 --- a/configure.ac +++ b/configure.ac @@ -1081,7 +1081,7 @@ AC_DEFUN nw="$nw -Wcast-align=strict" # Emacs is tricky with pointers. nw="$nw -Wduplicated-branches" # Too many false alarms - nw="$nw -Wformat-overflow=2" # False alarms due to GCC bug 80776 + nw="$nw -Wformat-overflow=2" # False alarms due to GCC bug 110333 nw="$nw -Wsystem-headers" # Don't let system headers trigger warnings nw="$nw -Woverlength-strings" # Not a problem these days nw="$nw -Wvla" # Emacs uses . commit 0273cb5e6dbd6c5111f3352b7777b4efc769ba14 Author: Po Lu Date: Wed Jun 21 11:32:41 2023 +0800 ; * src/pgtkfns.c (frame_geometry): Fix typo in last change. diff --git a/src/pgtkfns.c b/src/pgtkfns.c index 9cec7243515..c154d37f47f 100644 --- a/src/pgtkfns.c +++ b/src/pgtkfns.c @@ -3451,7 +3451,6 @@ frame_geometry (Lisp_Object frame, Lisp_Object attribute) tab_bar_height = FRAME_TAB_BAR_HEIGHT (f); tab_bar_width = (tab_bar_height ? native_width - 2 * internal_border_width : 0); - inner_top += tab_bar_height; /* Construct list. */ if (EQ (attribute, Qouter_edges)) @@ -3464,10 +3463,12 @@ frame_geometry (Lisp_Object frame, Lisp_Object attribute) else if (EQ (attribute, Qinner_edges)) return list4 (make_fixnum (native_left + internal_border_width), make_fixnum (native_top - + tool_bar_height + + tab_bar_height + + FRAME_TOOL_BAR_TOP_HEIGHT (f) + internal_border_width), make_fixnum (native_right - internal_border_width), - make_fixnum (native_bottom - internal_border_width)); + make_fixnum (native_bottom - internal_border_width + - FRAME_TOOL_BAR_BOTTOM_HEIGHT (f))); else return list (Fcons (Qouter_position, commit db6de49f231f863b21547173ce3ac9ab8e5e0d86 Author: Po Lu Date: Wed Jun 21 10:04:31 2023 +0800 Allow displaying tool bar on the bottom of the frame * src/xterm.c (x_clear_under_internal_border): Subtract bottom margins before clearing bottom border. (XTflash): Subtract bottom margins before flashing mini window. * src/xfns.c (x_set_tool_bar_position): Allow setting different values outside of GTK+. (frame_geometry): Adjust inner width and height for tool bars placed on the bottom. * src/xdisp.c (init_xdisp): Calculate using top margins only. * src/window.c (resize_frame_windows): Fix commentary. * src/w32fns.c (Fw32_frame_geometry): Report tool bar position correctly. (w32_clear_under_internal_border): Subtract bottom margins prior to clearing bottom border. (w32_set_tool_bar_position): New function. (Fw32_frame_edges): Subtract bottom tool bar from inner width and height. (w32_frame_parm_handlers): Add `set_tool_bar_position' parameter handler. * src/pgtkterm.c (pgtk_flash): Subtract bottom margins before clearing bottom border. (XTflash): Subtract bottom margins before flashing mini window. * src/pgtkfns.c (frame_geometry): Set `inner_top' correctly. (Fpgtk_set_mouse_absolute_pixel_position): (Fpgtk_mouse_absolute_pixel_position): (Fpgtk_page_setup_dialog): (Fpgtk_get_page_setup): Wrap lines which cause C Mode to hang. * src/nsterm.m (ns_clear_under_internal_border): Subtract bottom margins before clearing bottom border. * src/nsfns.m (ns_set_tool_bar_position): New function. Error if arg is not top. (ns_frame_parm_handlers): Add that as the handler for `tool-bar-position', to prevent it from being set to an invalid value. * src/haikuterm.c (haiku_flash): Subtract bottom margins before flashing mini window. (haiku_clear_under_internal_border): Subtract bottom margins before clearing bottom border. * src/haikufns.c (haiku_set_tool_bar_position): Allow setting values other than `top'. (frame_geometry): Take bottom margin into account when calculating inner dimensions. * src/frame.h (struct frame): Always define `tool_bar_position'. (fset_tool_bar_position): Define function everywhere. (FRAME_TOOL_BAR_POSITION): Define correctly on all toolkits. (FRAME_TOOL_BAR_TOP_HEIGHT): (FRAME_TOOL_BAR_TOP_LINES): (FRAME_TOOL_BAR_BOTTOM_HEIGHT): (FRAME_TOOL_BAR_BOTTOM_LINES): New macros. Each pair returns the tool bar dimensions only if the tool bar position is set appropriately. (FRAME_TOP_MARGIN, FRAME_TOP_MARGIN_HEIGHT): Only add tool bar height if it is placed at the top of the frame. (FRAME_BOTTOM_MARGIN, FRAME_BOTTOM_MARGIN_HEIGHT): Add ``bottom margins''. (FRAME_MARGINS, FRAME_MARGIN_HEIGHT): Move original margin macro here. (FRAME_PIXEL_HEIGHT_TO_TEXT_LINES): (FRAME_TEXT_TO_PIXEL_HEIGHT): (FRAME_PIXEL_TO_TEXT_HEIGHT): (FRAME_INNER_HEIGHT): Subtract both vertical margins. * src/frame.c (adjust_frame_size): Subtract both top and bottom margins to determine the inner height. (make_frame): Initialize `f->tool_bar_position' unconditionally. * src/dispnew.c (adjust_frame_glyphs_for_window_redisplay): Place internal tool bar on bottom if requested. * doc/lispref/frames.texi (Frame Layout): Describe the possibility of the tool bar being placed below the inner area of the frame. (Layout Parameters): Describe that `tool-bar-position' is now supported almost everywhere. diff --git a/doc/lispref/frames.texi b/doc/lispref/frames.texi index a8ac9a214f6..67def9b1fda 100644 --- a/doc/lispref/frames.texi +++ b/doc/lispref/frames.texi @@ -523,7 +523,8 @@ Frame Layout | | | |<--+--- Inner Frame Width ------->| | | | | | | | | | | | | | | | |___v______________________________| | | | - | | |___________ Internal Border __________| | v + | | |___________ Internal Border __________| | | + | | (4)__________ Bottom Tool Bar __________| | v v |___________ External/Outer Border __________| <-------- Native Frame Width --------> @@ -707,6 +708,10 @@ Frame Layout those of the menu bar and the tool bar (non-toolkit and text terminal frames). +If the native position would otherwise be (2), but the tool bar is +placed at the bottom of the frame as depicted in (4), the native +position of the frame becomes that of the tab bar. + The native position of a frame is the reference position for functions that set or return the current position of the mouse (@pxref{Mouse Position}) and for functions dealing with the position of windows like @@ -844,8 +849,11 @@ Frame Layout @item tool-bar-position This tells on which side the tool bar on @var{frame} is and can be one -of @code{left}, @code{top}, @code{right} or @code{bottom}. The only -toolkit that currently supports a value other than @code{top} is GTK+. +of @code{left}, @code{top}, @code{right} or @code{bottom}. + +The values @code{left} and @code{bottom} are only supported on builds +using the GTK+ toolkit; @code{bottom} is supported on all builds other +than NS, and @code{top} is supported everywhere. @item tool-bar-size A cons of the width and height of the tool bar of @var{frame}. @@ -1905,9 +1913,11 @@ Layout Parameters @vindex tool-bar-position@r{, a frame parameter} @item tool-bar-position -The position of the tool bar when Emacs was built with GTK+. Its value -can be one of @code{top}, @code{bottom} @code{left}, @code{right}. The -default is @code{top}. +The position of the tool bar. Its value can be one of @code{top}, +@code{bottom} @code{left}, @code{right}. The default is @code{top}. + +It can be set to @code{bottom} on Emacs built with any toolkit other +than Nextstep, and @code{left} or @code{right} on builds using GTK+. @vindex tab-bar-lines@r{, a frame parameter} @item tab-bar-lines diff --git a/etc/NEWS b/etc/NEWS index 2170323e74a..77ca749ccc3 100644 --- a/etc/NEWS +++ b/etc/NEWS @@ -82,6 +82,11 @@ This is used for displaying the time and date components of Several symbolic icons are added to "etc/images/symbols", including plus, minus, check-mark, start, etc. ++++ +** Tool bars can now be placed on the bottom on more systems. +The 'tool-bar-position' frame parameter can be set to 'bottom' on all +window systems other than Nextstep. + * Editing Changes in Emacs 30.1 diff --git a/src/dispnew.c b/src/dispnew.c index 9133d515ca3..82524d8cb8d 100644 --- a/src/dispnew.c +++ b/src/dispnew.c @@ -2218,10 +2218,10 @@ adjust_frame_glyphs_for_window_redisplay (struct frame *f) w->pixel_top = (FRAME_MENU_BAR_HEIGHT (f) + (!NILP (Vtab_bar_position) - ? FRAME_TOOL_BAR_HEIGHT (f) : 0)); + ? FRAME_TOOL_BAR_TOP_HEIGHT (f) : 0)); w->top_line = (FRAME_MENU_BAR_LINES (f) + (!NILP (Vtab_bar_position) - ? FRAME_TOOL_BAR_LINES (f) : 0)); + ? FRAME_TOOL_BAR_TOP_LINES (f) : 0)); w->total_cols = FRAME_TOTAL_COLS (f); w->pixel_width = (FRAME_PIXEL_WIDTH (f) - 2 * FRAME_INTERNAL_BORDER_WIDTH (f)); @@ -2250,10 +2250,29 @@ adjust_frame_glyphs_for_window_redisplay (struct frame *f) w->pixel_left = 0; w->left_col = 0; - w->pixel_top = FRAME_MENU_BAR_HEIGHT (f) - + (NILP (Vtab_bar_position) ? FRAME_TAB_BAR_HEIGHT (f) : 0); - w->top_line = FRAME_MENU_BAR_LINES (f) - + (NILP (Vtab_bar_position) ? FRAME_TAB_BAR_LINES (f) : 0); + + /* If the tool bar should be placed at the bottom of the frame, + place it there instead, outside the internal border. */ + + if (EQ (FRAME_TOOL_BAR_POSITION (f), Qbottom)) + { + w->pixel_top = (FRAME_PIXEL_HEIGHT (f) + - FRAME_TOOL_BAR_HEIGHT (f)); + w->top_line = (FRAME_LINES (f) + - FRAME_TOOL_BAR_LINES (f)); + } + else + { + /* Otherwise, place the window at the top of the frame. */ + + w->pixel_top = (FRAME_MENU_BAR_HEIGHT (f) + + (NILP (Vtab_bar_position) + ? FRAME_TAB_BAR_HEIGHT (f) : 0)); + w->top_line = (FRAME_MENU_BAR_LINES (f) + + (NILP (Vtab_bar_position) + ? FRAME_TAB_BAR_LINES (f) : 0)); + } + w->total_cols = FRAME_TOTAL_COLS (f); w->pixel_width = (FRAME_PIXEL_WIDTH (f) - 2 * FRAME_INTERNAL_BORDER_WIDTH (f)); diff --git a/src/frame.c b/src/frame.c index 037914ac9dc..3d140fcfc12 100644 --- a/src/frame.c +++ b/src/frame.c @@ -710,10 +710,10 @@ adjust_frame_size (struct frame *f, int new_text_width, int new_text_height, ? old_native_height : max (FRAME_TEXT_TO_PIXEL_HEIGHT (f, new_text_height), min_inner_height - + FRAME_TOP_MARGIN_HEIGHT (f) + + FRAME_MARGIN_HEIGHT (f) + 2 * FRAME_INTERNAL_BORDER_WIDTH (f))); new_inner_height = (new_native_height - - FRAME_TOP_MARGIN_HEIGHT (f) + - FRAME_MARGIN_HEIGHT (f) - 2 * FRAME_INTERNAL_BORDER_WIDTH (f)); new_text_height = FRAME_PIXEL_TO_TEXT_HEIGHT (f, new_native_height); new_text_lines = new_text_height / unit_height; @@ -940,11 +940,9 @@ make_frame (bool mini_p) f = allocate_frame (); XSETFRAME (frame, f); -#ifdef USE_GTK /* Initialize Lisp data. Note that allocate_frame initializes all Lisp data to nil, so do it only for slots which should not be nil. */ fset_tool_bar_position (f, Qtop); -#endif /* Initialize non-Lisp data. Note that allocate_frame zeroes out all non-Lisp data, so do it only for slots which should not be zero. diff --git a/src/frame.h b/src/frame.h index b95b94c7685..44eefa357fc 100644 --- a/src/frame.h +++ b/src/frame.h @@ -205,11 +205,9 @@ #define EMACS_FRAME_H Lisp_Object current_tool_bar_string; #endif -#ifdef USE_GTK /* Where tool bar is, can be left, right, top or bottom. Except with GTK, the only supported position is `top'. */ Lisp_Object tool_bar_position; -#endif #if defined (HAVE_XFT) || defined (HAVE_FREETYPE) /* List of data specific to font-driver and frame, but common to faces. */ @@ -782,14 +780,9 @@ fset_tool_bar_items (struct frame *f, Lisp_Object val) { f->tool_bar_items = val; } -#ifdef USE_GTK -INLINE void -fset_tool_bar_position (struct frame *f, Lisp_Object val) -{ - f->tool_bar_position = val; -} -#endif /* USE_GTK */ + #if defined (HAVE_WINDOW_SYSTEM) && ! defined (HAVE_EXT_TOOL_BAR) + INLINE void fset_tool_bar_window (struct frame *f, Lisp_Object val) { @@ -805,7 +798,14 @@ fset_desired_tool_bar_string (struct frame *f, Lisp_Object val) { f->desired_tool_bar_string = val; } -#endif /* HAVE_WINDOW_SYSTEM && !USE_GTK && !HAVE_NS */ + +#endif /* HAVE_WINDOW_SYSTEM && !HAVE_EXT_TOOL_BAR */ + +INLINE void +fset_tool_bar_position (struct frame *f, Lisp_Object val) +{ + f->tool_bar_position = val; +} INLINE double NUMVAL (Lisp_Object x) @@ -984,25 +984,68 @@ #define FRAME_EXTERNAL_TOOL_BAR(f) (f)->external_tool_bar #define FRAME_EXTERNAL_TOOL_BAR(f) false #endif -/* This is really supported only with GTK. */ -#ifdef USE_GTK +/* Position of F's tool bar; one of Qtop, Qleft, Qright, or + Qbottom. + + Qleft and Qright are not supported outside GTK+. */ #define FRAME_TOOL_BAR_POSITION(f) (f)->tool_bar_position -#else -#define FRAME_TOOL_BAR_POSITION(f) ((void) (f), Qtop) -#endif /* Size of frame F's internal tool bar in frame lines and pixels. */ #define FRAME_TOOL_BAR_LINES(f) (f)->tool_bar_lines #define FRAME_TOOL_BAR_HEIGHT(f) (f)->tool_bar_height +/* Size of F's tool bar if it is placed at the top of the + frame, else 0. */ + +#define FRAME_TOOL_BAR_TOP_HEIGHT(f) \ + ((BASE_EQ ((f)->tool_bar_position, Qtop)) \ + ? (f)->tool_bar_height : 0) + +#define FRAME_TOOL_BAR_TOP_LINES(f) \ + ((BASE_EQ ((f)->tool_bar_position, Qtop)) \ + ? (f)->tool_bar_height : 0) + +/* Size of F's tool bar if it is placed at the bottom of the + frame. */ +#define FRAME_TOOL_BAR_BOTTOM_HEIGHT(f) \ + ((BASE_EQ ((f)->tool_bar_position, Qbottom)) \ + ? (f)->tool_bar_height : 0) + +#define FRAME_TOOL_BAR_BOTTOM_LINES(f) \ + ((BASE_EQ ((f)->tool_bar_position, Qbottom)) \ + ? (f)->tool_bar_lines : 0) + /* Height of frame F's top margin in frame lines. */ #define FRAME_TOP_MARGIN(F) \ (FRAME_MENU_BAR_LINES (F) \ + FRAME_TAB_BAR_LINES (F) \ - + FRAME_TOOL_BAR_LINES (F)) + + FRAME_TOOL_BAR_TOP_LINES (F)) /* Pixel height of frame F's top margin. */ + #define FRAME_TOP_MARGIN_HEIGHT(F) \ + (FRAME_MENU_BAR_HEIGHT (F) \ + + FRAME_TAB_BAR_HEIGHT (F) \ + + FRAME_TOOL_BAR_TOP_HEIGHT (F)) + +/* Height of F's bottom margin in frame lines. */ + +#define FRAME_BOTTOM_MARGIN(f) \ + (FRAME_TOOL_BAR_BOTTOM_LINES (f)) + +/* Pixel height of frame F's bottom margin. */ + +#define FRAME_BOTTOM_MARGIN_HEIGHT(f) \ + (FRAME_TOOL_BAR_BOTTOM_HEIGHT (f)) + +/* Size of both vertical margins combined. */ + +#define FRAME_MARGINS(F) \ + (FRAME_MENU_BAR_LINES (F) \ + + FRAME_TAB_BAR_LINES (F) \ + + FRAME_TOOL_BAR_LINES (F)) + +#define FRAME_MARGIN_HEIGHT(F) \ (FRAME_MENU_BAR_HEIGHT (F) \ + FRAME_TAB_BAR_HEIGHT (F) \ + FRAME_TOOL_BAR_HEIGHT (F)) @@ -1625,7 +1668,7 @@ #define FRAME_PIXEL_WIDTH_TO_TEXT_COLS(f, width) \ #define FRAME_PIXEL_HEIGHT_TO_TEXT_LINES(f, height) \ (((height) \ - - FRAME_TOP_MARGIN_HEIGHT (f) \ + - FRAME_MARGIN_HEIGHT (f) \ - FRAME_SCROLL_BAR_AREA_HEIGHT (f) \ - 2 * FRAME_INTERNAL_BORDER_WIDTH (f)) \ / FRAME_LINE_HEIGHT (f)) @@ -1640,7 +1683,7 @@ #define FRAME_TEXT_TO_PIXEL_WIDTH(f, width) \ #define FRAME_TEXT_TO_PIXEL_HEIGHT(f, height) \ ((height) \ - + FRAME_TOP_MARGIN_HEIGHT (f) \ + + FRAME_MARGIN_HEIGHT (f) \ + FRAME_SCROLL_BAR_AREA_HEIGHT (f) \ + 2 * FRAME_INTERNAL_BORDER_WIDTH (f)) @@ -1654,7 +1697,7 @@ #define FRAME_PIXEL_TO_TEXT_WIDTH(f, width) \ #define FRAME_PIXEL_TO_TEXT_HEIGHT(f, height) \ ((height) \ - - FRAME_TOP_MARGIN_HEIGHT (f) \ + - FRAME_MARGIN_HEIGHT (f) \ - FRAME_SCROLL_BAR_AREA_HEIGHT (f) \ - 2 * FRAME_INTERNAL_BORDER_WIDTH (f)) @@ -1664,7 +1707,7 @@ #define FRAME_INNER_WIDTH(f) \ #define FRAME_INNER_HEIGHT(f) \ (FRAME_PIXEL_HEIGHT (f) \ - - FRAME_TOP_MARGIN_HEIGHT (f) \ + - FRAME_MARGIN_HEIGHT (f) \ - 2 * FRAME_INTERNAL_BORDER_WIDTH (f)) /* Value is the smallest width of any character in any font on frame F. */ diff --git a/src/haikufns.c b/src/haikufns.c index b4e68495a35..8028a73abd1 100644 --- a/src/haikufns.c +++ b/src/haikufns.c @@ -263,15 +263,26 @@ haiku_set_tool_bar_position (struct frame *f, Lisp_Object new_value, Lisp_Object old_value) { - Lisp_Object choice = list4 (Qleft, Qright, Qtop, Qbottom); + if (!EQ (new_value, Qtop) && !EQ (new_value, Qbottom)) + error ("Tool bar position must be either `top' or `bottom'"); - if (!NILP (Fmemq (new_value, choice))) - { - if (!EQ (new_value, Qtop)) - error ("The only supported tool bar position is top"); - } - else - wrong_choice (choice, new_value); + if (EQ (new_value, old_value)) + return; + + /* Set the tool bar position. */ + fset_tool_bar_position (f, new_value); + + /* Now reconfigure frame glyphs to place the tool bar at the bottom. + While the inner height has not changed, call + `resize_frame_windows' to place each of the windows at its new + position. */ + + adjust_frame_size (f, -1, -1, 3, false, Qtool_bar_position); + adjust_frame_glyphs (f); + SET_FRAME_GARBAGED (f); + + if (FRAME_HAIKU_WINDOW (f)) + haiku_clear_under_internal_border (f); } static void @@ -1436,10 +1447,11 @@ haiku_set_menu_bar_lines (struct frame *f, Lisp_Object value, Lisp_Object oldval } /* Return geometric attributes of FRAME. According to the value of - ATTRIBUTES return the outer edges of FRAME (Qouter_edges), the inner - edges of FRAME, the root window edges of frame (Qroot_edges). Any - other value means to return the geometry as returned by + ATTRIBUTES return the outer edges of FRAME (Qouter_edges), the + inner edges of FRAME, the root window edges of frame (Qroot_edges). + Any other value means to return the geometry as returned by Fx_frame_geometry. */ + static Lisp_Object frame_geometry (Lisp_Object frame, Lisp_Object attribute) { @@ -1448,6 +1460,9 @@ frame_geometry (Lisp_Object frame, Lisp_Object attribute) int outer_x, outer_y, outer_width, outer_height; int right_off, bottom_off, top_off; int native_x, native_y; + int inner_left, inner_top, inner_right, inner_bottom; + int internal_border_width, tab_bar_height; + int tool_bar_height, tab_bar_width; f = decode_window_system_frame (frame); parent = FRAME_PARENT_FRAME (f); @@ -1473,6 +1488,31 @@ frame_geometry (Lisp_Object frame, Lisp_Object attribute) native_y -= FRAME_OUTPUT_DATA (parent)->frame_y; } + internal_border_width = FRAME_INTERNAL_BORDER_WIDTH (f); + inner_left = native_x + internal_border_width; + inner_top = native_y + internal_border_width; + inner_right = (native_x + FRAME_PIXEL_WIDTH (f) + - internal_border_width); + inner_bottom = (native_y + FRAME_PIXEL_HEIGHT (f) + - internal_border_width); + + tab_bar_height = FRAME_TAB_BAR_HEIGHT (f); + tab_bar_width = (tab_bar_height + ? (FRAME_PIXEL_WIDTH (f) - 2 + * internal_border_width) + : 0); + inner_top += tab_bar_height; + + tool_bar_height = FRAME_TOOL_BAR_HEIGHT (f); + + /* Subtract or add to the inner dimensions based on the tool bar + position. */ + + if (EQ (FRAME_TOOL_BAR_POSITION (f), Qtop)) + inner_top += tool_bar_height; + else + inner_bottom -= tool_bar_height; + if (EQ (attribute, Qouter_edges)) return list4i (outer_x, outer_y, outer_x + outer_width, @@ -1482,14 +1522,7 @@ frame_geometry (Lisp_Object frame, Lisp_Object attribute) native_x + FRAME_PIXEL_WIDTH (f), native_y + FRAME_PIXEL_HEIGHT (f)); else if (EQ (attribute, Qinner_edges)) - return list4i (native_x + FRAME_INTERNAL_BORDER_WIDTH (f), - native_y + FRAME_INTERNAL_BORDER_WIDTH (f) - + FRAME_MENU_BAR_HEIGHT (f) + FRAME_TOOL_BAR_HEIGHT (f), - native_x - FRAME_INTERNAL_BORDER_WIDTH (f) - + FRAME_PIXEL_WIDTH (f), - native_y + FRAME_PIXEL_HEIGHT (f) - - FRAME_INTERNAL_BORDER_WIDTH (f)); - + return list4i (inner_left, inner_top, inner_right, inner_bottom); else return list (Fcons (Qouter_position, Fcons (make_fixnum (outer_x), @@ -1506,13 +1539,18 @@ frame_geometry (Lisp_Object frame, Lisp_Object attribute) Fcons (Qmenu_bar_external, Qnil), Fcons (Qmenu_bar_size, Fcons (make_fixnum (FRAME_PIXEL_WIDTH (f) - - (FRAME_INTERNAL_BORDER_WIDTH (f) * 2)), + - (FRAME_INTERNAL_BORDER_WIDTH (f) + * 2)), make_fixnum (FRAME_MENU_BAR_HEIGHT (f)))), + Fcons (Qtab_bar_size, + Fcons (make_fixnum (tab_bar_width), + make_fixnum (tab_bar_height))), Fcons (Qtool_bar_external, Qnil), - Fcons (Qtool_bar_position, Qtop), + Fcons (Qtool_bar_position, FRAME_TOOL_BAR_POSITION (f)), Fcons (Qtool_bar_size, Fcons (make_fixnum (FRAME_PIXEL_WIDTH (f) - - (FRAME_INTERNAL_BORDER_WIDTH (f) * 2)), + - (FRAME_INTERNAL_BORDER_WIDTH (f) + * 2)), make_fixnum (FRAME_TOOL_BAR_HEIGHT (f)))), Fcons (Qinternal_border_width, make_fixnum (FRAME_INTERNAL_BORDER_WIDTH (f)))); diff --git a/src/haikuterm.c b/src/haikuterm.c index 212870064e8..ed28a806ff2 100644 --- a/src/haikuterm.c +++ b/src/haikuterm.c @@ -4165,7 +4165,8 @@ haiku_flash (struct frame *f) BView_InvertRect (view, flash_left, (height - flash_height - - FRAME_INTERNAL_BORDER_WIDTH (f)), + - FRAME_INTERNAL_BORDER_WIDTH (f) + - FRAME_BOTTOM_MARGIN_HEIGHT (f)), width, flash_height); } else @@ -4210,7 +4211,8 @@ haiku_flash (struct frame *f) BView_InvertRect (view, flash_left, (height - flash_height - - FRAME_INTERNAL_BORDER_WIDTH (f)), + - FRAME_INTERNAL_BORDER_WIDTH (f) + - FRAME_BOTTOM_MARGIN_HEIGHT (f)), width, flash_height); } else @@ -4465,14 +4467,16 @@ haiku_clear_under_internal_border (struct frame *f) int width = FRAME_PIXEL_WIDTH (f); int height = FRAME_PIXEL_HEIGHT (f); int margin = FRAME_TOP_MARGIN_HEIGHT (f); - int face_id = - (FRAME_PARENT_FRAME (f) - ? (!NILP (Vface_remapping_alist) - ? lookup_basic_face (NULL, f, CHILD_FRAME_BORDER_FACE_ID) - : CHILD_FRAME_BORDER_FACE_ID) - : (!NILP (Vface_remapping_alist) - ? lookup_basic_face (NULL, f, INTERNAL_BORDER_FACE_ID) - : INTERNAL_BORDER_FACE_ID)); + int bottom_margin = FRAME_BOTTOM_MARGIN_HEIGHT (f); + int face_id = (FRAME_PARENT_FRAME (f) + ? (!NILP (Vface_remapping_alist) + ? lookup_basic_face (NULL, f, + CHILD_FRAME_BORDER_FACE_ID) + : CHILD_FRAME_BORDER_FACE_ID) + : (!NILP (Vface_remapping_alist) + ? lookup_basic_face (NULL, f, + INTERNAL_BORDER_FACE_ID) + : INTERNAL_BORDER_FACE_ID)); struct face *face = FACE_FROM_ID_OR_NULL (f, face_id); void *view = FRAME_HAIKU_DRAWABLE (f); @@ -4492,7 +4496,8 @@ haiku_clear_under_internal_border (struct frame *f) BView_FillRectangle (view, 0, 0, border, height); BView_FillRectangle (view, 0, margin, width, border); BView_FillRectangle (view, width - border, 0, border, height); - BView_FillRectangle (view, 0, height - border, width, border); + BView_FillRectangle (view, 0, height - bottom_margin - border, + width, border); BView_EndClip (view); BView_draw_unlock (view); unblock_input (); diff --git a/src/nsfns.m b/src/nsfns.m index 8804a7df7cf..90159533128 100644 --- a/src/nsfns.m +++ b/src/nsfns.m @@ -706,8 +706,10 @@ Turn the input menu (an NSMenu) into a lisp list for tracking on lisp side. ns_change_tab_bar_height (f, nlines * FRAME_LINE_HEIGHT (f)); } + + +/* Tool bar support. */ -/* toolbar support */ static void ns_set_tool_bar_lines (struct frame *f, Lisp_Object value, Lisp_Object oldval) { @@ -760,7 +762,16 @@ Turn the input menu (an NSMenu) into a lisp list for tracking on lisp side. } static void -ns_set_child_frame_border_width (struct frame *f, Lisp_Object arg, Lisp_Object oldval) +ns_set_tool_bar_position (struct frame *f, Lisp_Object arg, + Lisp_Object oldval) +{ + if (!EQ (arg, Qtop)) + error ("Tool bar position must be `top'"); +} + +static void +ns_set_child_frame_border_width (struct frame *f, Lisp_Object arg, + Lisp_Object oldval) { int border; @@ -1055,7 +1066,7 @@ Turn the input menu (an NSMenu) into a lisp list for tracking on lisp side. gui_set_font_backend, /* generic OK */ gui_set_alpha, 0, /* x_set_sticky */ - 0, /* x_set_tool_bar_position */ + ns_set_tool_bar_position, 0, /* x_set_inhibit_double_buffering */ ns_set_undecorated, ns_set_parent_frame, diff --git a/src/nsterm.m b/src/nsterm.m index 3e089cc1ff1..8c72bb25df1 100644 --- a/src/nsterm.m +++ b/src/nsterm.m @@ -2728,6 +2728,7 @@ Hide the window (X11 semantics) int width = FRAME_PIXEL_WIDTH (f); int height = FRAME_PIXEL_HEIGHT (f); int margin = FRAME_TOP_MARGIN_HEIGHT (f); + int bottom_margin = FRAME_BOTTOM_MARGIN_HEIGHT (f); int face_id = (FRAME_PARENT_FRAME (f) ? (!NILP (Vface_remapping_alist) @@ -2753,7 +2754,8 @@ Hide the window (X11 semantics) NSRectFill (NSMakeRect (0, 0, border, height)); NSRectFill (NSMakeRect (0, margin, width, border)); NSRectFill (NSMakeRect (width - border, 0, border, height)); - NSRectFill (NSMakeRect (0, height - border, width, border)); + NSRectFill (NSMakeRect (0, height - bottom_margin - border, + width, border)); ns_unfocus (f); } } diff --git a/src/pgtkfns.c b/src/pgtkfns.c index 801f97d26d2..9cec7243515 100644 --- a/src/pgtkfns.c +++ b/src/pgtkfns.c @@ -3451,7 +3451,7 @@ frame_geometry (Lisp_Object frame, Lisp_Object attribute) tab_bar_height = FRAME_TAB_BAR_HEIGHT (f); tab_bar_width = (tab_bar_height ? native_width - 2 * internal_border_width : 0); - /* inner_top += tab_bar_height; */ + inner_top += tab_bar_height; /* Construct list. */ if (EQ (attribute, Qouter_edges)) @@ -3564,7 +3564,9 @@ manager (like the title bar or external borders) as well as any external ? type : Qnative_edges)); } -DEFUN ("pgtk-set-mouse-absolute-pixel-position", Fpgtk_set_mouse_absolute_pixel_position, Spgtk_set_mouse_absolute_pixel_position, 2, 2, 0, +DEFUN ("pgtk-set-mouse-absolute-pixel-position", + Fpgtk_set_mouse_absolute_pixel_position, + Spgtk_set_mouse_absolute_pixel_position, 2, 2, 0, doc: /* Move mouse pointer to absolute pixel position (X, Y). The coordinates X and Y are interpreted in pixels relative to a position \(0, 0) of the selected frame's display. */) @@ -3583,7 +3585,9 @@ DEFUN ("pgtk-set-mouse-absolute-pixel-position", Fpgtk_set_mouse_absolute_pixel_ return Qnil; } -DEFUN ("pgtk-mouse-absolute-pixel-position", Fpgtk_mouse_absolute_pixel_position, Spgtk_mouse_absolute_pixel_position, 0, 0, 0, +DEFUN ("pgtk-mouse-absolute-pixel-position", + Fpgtk_mouse_absolute_pixel_position, + Spgtk_mouse_absolute_pixel_position, 0, 0, 0, doc: /* Return absolute position of mouse cursor in pixels. The position is returned as a cons cell (X . Y) of the coordinates of the mouse cursor position in pixels relative to a @@ -3605,7 +3609,8 @@ position (0, 0) of the selected frame's terminal. */) } -DEFUN ("pgtk-page-setup-dialog", Fpgtk_page_setup_dialog, Spgtk_page_setup_dialog, 0, 0, 0, +DEFUN ("pgtk-page-setup-dialog", Fpgtk_page_setup_dialog, + Spgtk_page_setup_dialog, 0, 0, 0, doc: /* Pop up a page setup dialog. The current page setup can be obtained using `x-get-page-setup'. */) (void) @@ -3617,7 +3622,8 @@ DEFUN ("pgtk-page-setup-dialog", Fpgtk_page_setup_dialog, Spgtk_page_setup_dialo return Qnil; } -DEFUN ("pgtk-get-page-setup", Fpgtk_get_page_setup, Spgtk_get_page_setup, 0, 0, 0, +DEFUN ("pgtk-get-page-setup", Fpgtk_get_page_setup, + Spgtk_get_page_setup, 0, 0, 0, doc: /* Return the value of the current page setup. The return value is an alist containing the following keys: diff --git a/src/pgtkterm.c b/src/pgtkterm.c index 91e4d828f51..dc2d6477bb5 100644 --- a/src/pgtkterm.c +++ b/src/pgtkterm.c @@ -3766,7 +3766,8 @@ pgtk_flash (struct frame *f) cairo_rectangle (cr, flash_left, (height - flash_height - - FRAME_INTERNAL_BORDER_WIDTH (f)), + - FRAME_INTERNAL_BORDER_WIDTH (f) + - FRAME_BOTTOM_MARGIN_HEIGHT (f)), width, flash_height); cairo_fill (cr); } @@ -4947,14 +4948,16 @@ pgtk_clear_under_internal_border (struct frame *f) int width = FRAME_PIXEL_WIDTH (f); int height = FRAME_PIXEL_HEIGHT (f); int margin = FRAME_TOP_MARGIN_HEIGHT (f); - int face_id = - (FRAME_PARENT_FRAME (f) - ? (!NILP (Vface_remapping_alist) - ? lookup_basic_face (NULL, f, CHILD_FRAME_BORDER_FACE_ID) - : CHILD_FRAME_BORDER_FACE_ID) - : (!NILP (Vface_remapping_alist) - ? lookup_basic_face (NULL, f, INTERNAL_BORDER_FACE_ID) - : INTERNAL_BORDER_FACE_ID)); + int bottom_margin = FRAME_BOTTOM_MARGIN_HEIGHT (f); + int face_id = (FRAME_PARENT_FRAME (f) + ? (!NILP (Vface_remapping_alist) + ? lookup_basic_face (NULL, f, + CHILD_FRAME_BORDER_FACE_ID) + : CHILD_FRAME_BORDER_FACE_ID) + : (!NILP (Vface_remapping_alist) + ? lookup_basic_face (NULL, f, + INTERNAL_BORDER_FACE_ID) + : INTERNAL_BORDER_FACE_ID)); struct face *face = FACE_FROM_ID_OR_NULL (f, face_id); block_input (); @@ -4965,15 +4968,18 @@ pgtk_clear_under_internal_border (struct frame *f) fill_background_by_face (f, face, 0, 0, border, height); fill_background_by_face (f, face, width - border, 0, border, height); - fill_background_by_face (f, face, 0, height - border, width, - border); + fill_background_by_face (f, face, 0, (height + - bottom_margin + - border), + width, border); } else { pgtk_clear_area (f, 0, 0, border, height); pgtk_clear_area (f, 0, margin, width, border); pgtk_clear_area (f, width - border, 0, border, height); - pgtk_clear_area (f, 0, height - border, width, border); + pgtk_clear_area (f, 0, height - bottom_margin - border, + width, border); } unblock_input (); diff --git a/src/w32fns.c b/src/w32fns.c index 745f561e6b1..dcf9a212bdd 100644 --- a/src/w32fns.c +++ b/src/w32fns.c @@ -1537,14 +1537,16 @@ w32_clear_under_internal_border (struct frame *f) { int width = FRAME_PIXEL_WIDTH (f); int height = FRAME_PIXEL_HEIGHT (f); - int face_id = - (FRAME_PARENT_FRAME (f) - ? (!NILP (Vface_remapping_alist) - ? lookup_basic_face (NULL, f, CHILD_FRAME_BORDER_FACE_ID) - : CHILD_FRAME_BORDER_FACE_ID) - : (!NILP (Vface_remapping_alist) - ? lookup_basic_face (NULL, f, INTERNAL_BORDER_FACE_ID) - : INTERNAL_BORDER_FACE_ID)); + int bottom_margin = FRAME_BOTTOM_MARGIN_HEIGHT (f); + int face_id = (FRAME_PARENT_FRAME (f) + ? (!NILP (Vface_remapping_alist) + ? lookup_basic_face (NULL, f, + CHILD_FRAME_BORDER_FACE_ID) + : CHILD_FRAME_BORDER_FACE_ID) + : (!NILP (Vface_remapping_alist) + ? lookup_basic_face (NULL, f, + INTERNAL_BORDER_FACE_ID) + : INTERNAL_BORDER_FACE_ID)); struct face *face = FACE_FROM_ID_OR_NULL (f, face_id); block_input (); @@ -1554,17 +1556,21 @@ w32_clear_under_internal_border (struct frame *f) /* Fill border with internal border face. */ unsigned long color = face->background; - w32_fill_area (f, hdc, color, 0, FRAME_TOP_MARGIN_HEIGHT (f), width, border); + w32_fill_area (f, hdc, color, 0, FRAME_TOP_MARGIN_HEIGHT (f), + width, border); w32_fill_area (f, hdc, color, 0, 0, border, height); w32_fill_area (f, hdc, color, width - border, 0, border, height); - w32_fill_area (f, hdc, color, 0, height - border, width, border); + w32_fill_area (f, hdc, color, 0, height - bottom_margin - border, + width, border); } else { - w32_clear_area (f, hdc, 0, FRAME_TOP_MARGIN_HEIGHT (f), width, border); + w32_clear_area (f, hdc, 0, FRAME_TOP_MARGIN_HEIGHT (f), + width, border); w32_clear_area (f, hdc, 0, 0, border, height); w32_clear_area (f, hdc, width - border, 0, border, height); - w32_clear_area (f, hdc, 0, height - border, width, border); + w32_clear_area (f, hdc, 0, height - bottom_margin - border, + width, border); } release_frame_dc (f, hdc); unblock_input (); @@ -1806,6 +1812,33 @@ w32_set_tool_bar_lines (struct frame *f, Lisp_Object value, Lisp_Object oldval) w32_change_tool_bar_height (f, nlines * FRAME_LINE_HEIGHT (f)); } +static void +w32_set_tool_bar_position (struct frame *f, + Lisp_Object new_value, + Lisp_Object old_value) +{ + if (!EQ (new_value, Qtop) && !EQ (new_value, Qbottom)) + error ("Tool bar position must be either `top' or `bottom'"); + + if (EQ (new_value, old_value)) + return; + + /* Set the tool bar position. */ + fset_tool_bar_position (f, new_value); + + /* Now reconfigure frame glyphs to place the tool bar at the + bottom. While the inner height has not changed, call + `resize_frame_windows' to place each of the windows at its + new position. */ + + adjust_frame_size (f, -1, -1, 3, false, Qtool_bar_position); + adjust_frame_glyphs (f); + SET_FRAME_GARBAGED (f); + + if (FRAME_W32_WINDOW (f)) + w32_clear_under_internal_border (f); +} + /* Enable or disable double buffering on frame F. When double buffering is enabled, all drawing happens on a back @@ -8993,7 +9026,9 @@ DEFUN ("w32-frame-geometry", Fw32_frame_geometry, Sw32_frame_geometry, 0, 1, 0, : 0), make_fixnum (tab_bar_height))), Fcons (Qtool_bar_external, Qnil), - Fcons (Qtool_bar_position, tool_bar_height ? Qtop : Qnil), + Fcons (Qtool_bar_position, (tool_bar_height + ? FRAME_TOOL_BAR_POSITION (f) + : Qnil)), Fcons (Qtool_bar_size, Fcons (make_fixnum (tool_bar_height @@ -9084,10 +9119,11 @@ manager (like the title bar or external borders) as well as any external return list4 (make_fixnum (left + internal_border_width), make_fixnum (top + FRAME_TAB_BAR_HEIGHT (f) - + FRAME_TOOL_BAR_HEIGHT (f) + + FRAME_TOOL_BAR_TOP_HEIGHT (f) + internal_border_width), make_fixnum (right - internal_border_width), - make_fixnum (bottom - internal_border_width)); + make_fixnum (bottom - internal_border_width + - FRAME_TOOL_BAR_BOTTOM_HEIGHT (f))); } else return list4 (make_fixnum (left), make_fixnum (top), @@ -10556,7 +10592,7 @@ DEFUN ("w32-set-wallpaper", Fw32_set_wallpaper, Sw32_set_wallpaper, 1, 1, 0, gui_set_font_backend, gui_set_alpha, 0, /* x_set_sticky */ - 0, /* x_set_tool_bar_position */ + w32_set_tool_bar_position, w32_set_inhibit_double_buffering, w32_set_undecorated, w32_set_parent_frame, diff --git a/src/window.c b/src/window.c index e22fea0bb7a..fa024b6d2d8 100644 --- a/src/window.c +++ b/src/window.c @@ -4828,10 +4828,9 @@ DEFUN ("window-resize-apply-total", Fwindow_resize_apply_total, Swindow_resize_a return Qt; } +/* Resize frame F's windows when F's inner height (inner width if + HORFLAG is true) has been set to SIZE pixels. */ -/** -Resize frame F's windows when F's inner height (inner width if HORFLAG -is true) has been set to SIZE pixels. */ void resize_frame_windows (struct frame *f, int size, bool horflag) { diff --git a/src/xdisp.c b/src/xdisp.c index 8bcf2acfe04..4a48b93b29e 100644 --- a/src/xdisp.c +++ b/src/xdisp.c @@ -37494,7 +37494,7 @@ init_xdisp (void) r->pixel_top = r->top_line * FRAME_LINE_HEIGHT (f); r->total_cols = FRAME_COLS (f); r->pixel_width = r->total_cols * FRAME_COLUMN_WIDTH (f); - r->total_lines = FRAME_TOTAL_LINES (f) - 1 - FRAME_TOP_MARGIN (f); + r->total_lines = FRAME_TOTAL_LINES (f) - 1 - FRAME_MARGINS (f); r->pixel_height = r->total_lines * FRAME_LINE_HEIGHT (f); m->top_line = FRAME_TOTAL_LINES (f) - 1; diff --git a/src/xfns.c b/src/xfns.c index 234a48c908f..a58e854811b 100644 --- a/src/xfns.c +++ b/src/xfns.c @@ -807,23 +807,45 @@ x_set_tool_bar_position (struct frame *f, Lisp_Object new_value, Lisp_Object old_value) { - Lisp_Object choice = list4 (Qleft, Qright, Qtop, Qbottom); +#ifdef USE_GTK + Lisp_Object choice; + + choice = list4 (Qleft, Qright, Qtop, Qbottom); if (!NILP (Fmemq (new_value, choice))) { -#ifdef USE_GTK if (!EQ (new_value, old_value)) { xg_change_toolbar_position (f, new_value); fset_tool_bar_position (f, new_value); } -#else - if (!EQ (new_value, Qtop)) - error ("The only supported tool bar position is top"); -#endif +#else /* !USE_GTK */ + if (!EQ (new_value, Qtop) && !EQ (new_value, Qbottom)) + error ("Tool bar position must be either `top' or `bottom'"); + + if (EQ (new_value, old_value)) + return; + + /* Set the tool bar position. */ + fset_tool_bar_position (f, new_value); + + /* Now reconfigure frame glyphs to place the tool bar at the + bottom. While the inner height has not changed, call + `resize_frame_windows' to place each of the windows at its + new position. */ + + adjust_frame_size (f, -1, -1, 3, false, Qtool_bar_position); + adjust_frame_glyphs (f); + SET_FRAME_GARBAGED (f); + + if (FRAME_X_WINDOW (f)) + x_clear_under_internal_border (f); +#endif /* USE_GTK */ +#ifdef USE_GTK } else wrong_choice (choice, new_value); +#endif /* USE_GTK */ } #ifdef HAVE_XDBE @@ -6673,10 +6695,11 @@ DEFUN ("x-display-monitor-attributes-list", Fx_display_monitor_attributes_list, } /* Return geometric attributes of FRAME. According to the value of - ATTRIBUTES return the outer edges of FRAME (Qouter_edges), the native - edges of FRAME (Qnative_edges), or the inner edges of frame + ATTRIBUTES return the outer edges of FRAME (Qouter_edges), the + native edges of FRAME (Qnative_edges), or the inner edges of frame (Qinner_edges). Any other value means to return the geometry as returned by Fx_frame_geometry. */ + static Lisp_Object frame_geometry (Lisp_Object frame, Lisp_Object attribute) { @@ -6765,8 +6788,8 @@ frame_geometry (Lisp_Object frame, Lisp_Object attribute) tab_bar_height = FRAME_TAB_BAR_HEIGHT (f); tab_bar_width = (tab_bar_height - ? native_width - 2 * internal_border_width - : 0); + ? native_width - 2 * internal_border_width + : 0); inner_top += tab_bar_height; #ifdef HAVE_EXT_TOOL_BAR @@ -6806,7 +6829,14 @@ frame_geometry (Lisp_Object frame, Lisp_Object attribute) tool_bar_width = (tool_bar_height ? native_width - 2 * internal_border_width : 0); - inner_top += tool_bar_height; + + /* Subtract or add to the inner dimensions based on the tool bar + position. */ + + if (EQ (FRAME_TOOL_BAR_POSITION (f), Qtop)) + inner_top += tool_bar_height; + else + inner_bottom -= tool_bar_height; #endif /* Construct list. */ diff --git a/src/xterm.c b/src/xterm.c index 0450230efe6..7fb6283c088 100644 --- a/src/xterm.c +++ b/src/xterm.c @@ -7574,14 +7574,16 @@ x_clear_under_internal_border (struct frame *f) int width = FRAME_PIXEL_WIDTH (f); int height = FRAME_PIXEL_HEIGHT (f); int margin = FRAME_TOP_MARGIN_HEIGHT (f); - int face_id = - (FRAME_PARENT_FRAME (f) - ? (!NILP (Vface_remapping_alist) - ? lookup_basic_face (NULL, f, CHILD_FRAME_BORDER_FACE_ID) - : CHILD_FRAME_BORDER_FACE_ID) - : (!NILP (Vface_remapping_alist) - ? lookup_basic_face (NULL, f, INTERNAL_BORDER_FACE_ID) - : INTERNAL_BORDER_FACE_ID)); + int bottom_margin = FRAME_BOTTOM_MARGIN_HEIGHT (f); + int face_id = (FRAME_PARENT_FRAME (f) + ? (!NILP (Vface_remapping_alist) + ? lookup_basic_face (NULL, f, + CHILD_FRAME_BORDER_FACE_ID) + : CHILD_FRAME_BORDER_FACE_ID) + : (!NILP (Vface_remapping_alist) + ? lookup_basic_face (NULL, f, + INTERNAL_BORDER_FACE_ID) + : INTERNAL_BORDER_FACE_ID)); struct face *face = FACE_FROM_ID_OR_NULL (f, face_id); if (face) @@ -7594,7 +7596,8 @@ x_clear_under_internal_border (struct frame *f) x_fill_rectangle (f, gc, 0, margin, width, border, false); x_fill_rectangle (f, gc, 0, 0, border, height, false); x_fill_rectangle (f, gc, width - border, 0, border, height, false); - x_fill_rectangle (f, gc, 0, height - border, width, border, false); + x_fill_rectangle (f, gc, 0, height - bottom_margin - border, + width, border, false); XSetForeground (display, gc, FRAME_FOREGROUND_PIXEL (f)); } else @@ -7602,7 +7605,8 @@ x_clear_under_internal_border (struct frame *f) x_clear_area (f, 0, 0, border, height); x_clear_area (f, 0, margin, width, border); x_clear_area (f, width - border, 0, border, height); - x_clear_area (f, 0, height - border, width, border); + x_clear_area (f, 0, height - bottom_margin - border, + width, border); } } } @@ -11318,7 +11322,8 @@ XTflash (struct frame *f) XFillRectangle (FRAME_X_DISPLAY (f), FRAME_X_WINDOW (f), gc, flash_left, (height - flash_height - - FRAME_INTERNAL_BORDER_WIDTH (f)), + - FRAME_INTERNAL_BORDER_WIDTH (f) + - FRAME_BOTTOM_MARGIN_HEIGHT (f)), width, flash_height); } @@ -11372,7 +11377,8 @@ XTflash (struct frame *f) XFillRectangle (FRAME_X_DISPLAY (f), FRAME_X_WINDOW (f), gc, flash_left, (height - flash_height - - FRAME_INTERNAL_BORDER_WIDTH (f)), + - FRAME_INTERNAL_BORDER_WIDTH (f) + - FRAME_BOTTOM_MARGIN_HEIGHT (f)), width, flash_height); } else commit bc6068fe9451f62157c25c9568923ef6c49ed967 Author: Harald Jörg Date: Tue Jun 20 22:51:29 2023 +0200 ; cperl-mode.el: Eliminate cperl-font-lock-multiline This undocumented variable was always set to t. There was no function to change the variable. * lisp/progmodes/cperl-mode.el: Eliminate top-level variables cperl-font-lock-multiline and cperl-font-lock-multiline-start. (cperl-mode): Don't set cperl-font-lock-multiline. (cperl-windowed-init): Don't set cperl-font-lock-multiline. (cperl-init-faces): Eliminate (if cperl-font-lock-multiline) conditionals. diff --git a/lisp/progmodes/cperl-mode.el b/lisp/progmodes/cperl-mode.el index 6548ba3bd36..66f01109e3f 100644 --- a/lisp/progmodes/cperl-mode.el +++ b/lisp/progmodes/cperl-mode.el @@ -1476,8 +1476,6 @@ cperl-faces-init ;; Fix for msb.el (defvar cperl-msb-fixed nil) (defvar cperl-use-major-mode 'cperl-mode) -(defvar cperl-font-lock-multiline-start nil) -(defvar cperl-font-lock-multiline nil) (defvar cperl-font-locking nil) (defvar cperl-compilation-error-regexp-list @@ -1686,7 +1684,6 @@ cperl-mode (when (< emacs-major-version 27) (setq-local open-paren-in-column-0-is-defun-start nil)) ;; Until Emacs is multi-threaded, we do not actually need it local: - (make-local-variable 'cperl-font-lock-multiline-start) (make-local-variable 'cperl-font-locking) (setq-local outline-regexp cperl-outline-regexp) (setq-local outline-level 'cperl-outline-level) @@ -1759,7 +1756,6 @@ cperl-mode ;; to re-apply them. (setq cperl-syntax-done-to start) (cperl-fontify-syntactically end)))) - (setq cperl-font-lock-multiline t) ; Not localized... (setq-local font-lock-multiline t) (setq-local font-lock-fontify-region-function #'cperl-font-lock-fontify-region-function) @@ -3609,7 +3605,7 @@ cperl-process-here-doc delim-begin delim-end) "Process a here-document's delimiters and body. The parameters MIN, MAX, END, OVERSHOOT, STOP-POINT, ERR-L are -used for recursive calls to `cperl-find-pods-here' to handle the +used for recursive calls to `cperl-find-pods-heres' to handle the rest of the line which contains the delimiter. MATCHED-POS and TODO-POS are initial values for this function's result. END-OF-HERE-DOC is the end of a previous here-doc in the same @@ -5623,7 +5619,6 @@ cperl-windowed-init (cond ((featurep 'ps-print) (or cperl-faces-init (progn - (setq cperl-font-lock-multiline t) (cperl-init-faces)))) ((not cperl-faces-init) (add-hook 'font-lock-mode-hook @@ -5768,20 +5763,9 @@ cperl-init-faces "([^()]*)\\)?" ; prototype cperl-maybe-white-and-comment-rex ; whitespace/comments? "[{;]") - 2 (if cperl-font-lock-multiline - '(if (eq (char-after (cperl-1- (match-end 0))) ?\{ ) + 2 '(if (eq (char-after (cperl-1- (match-end 0))) ?\{ ) 'font-lock-function-name-face - 'font-lock-variable-name-face) - ;; need to manually set 'multiline' for older font-locks - '(progn - (if (< 1 (count-lines (match-beginning 0) - (match-end 0))) - (put-text-property - (+ 3 (match-beginning 0)) (match-end 0) - 'syntax-type 'multiline)) - (if (eq (char-after (cperl-1- (match-end 0))) ?\{ ) - 'font-lock-function-name-face - 'font-lock-variable-name-face)))) + 'font-lock-variable-name-face)) `(,(rx (sequence symbol-start (or "package" "require" "use" "import" "no" "bootstrap") @@ -5856,12 +5840,7 @@ cperl-init-faces ;; "\\((" ;; cperl-maybe-white-and-comment-rex ;; "\\)?\\([$@%*]\\([a-zA-Z0-9_:]+\\|[^a-zA-Z0-9_]\\)\\)") - ;; (5 ,(if cperl-font-lock-multiline - (1 ,(if cperl-font-lock-multiline - 'font-lock-variable-name-face - '(progn (setq cperl-font-lock-multiline-start - (match-beginning 0)) - 'font-lock-variable-name-face))) + (1 font-lock-variable-name-face) (,(rx (sequence point (eval cperl--ws*-rx) "," @@ -5882,35 +5861,18 @@ cperl-init-faces ;; Bug in font-lock: limit is used not only to limit ;; searches, but to set the "extend window for ;; facification" property. Thus we need to minimize. - ,(if cperl-font-lock-multiline - '(if (match-beginning 1) - (save-excursion - (goto-char (match-beginning 1)) - (condition-case nil - (forward-sexp 1) - (error - (condition-case nil - (forward-char 200) - (error nil)))) ; typeahead - (1- (point))) ; report limit - (forward-char -2)) ; disable continued expr - '(if (match-beginning 1) - (point-max) ; No limit for continuation - (forward-char -2))) ; disable continued expr - ,(if cperl-font-lock-multiline - nil - '(progn ; Do at end - ;; "my" may be already fontified (POD), - ;; so cperl-font-lock-multiline-start is nil - (if (or (not cperl-font-lock-multiline-start) - (> 2 (count-lines - cperl-font-lock-multiline-start - (point)))) - nil - (put-text-property - (1+ cperl-font-lock-multiline-start) (point) - 'syntax-type 'multiline)) - (setq cperl-font-lock-multiline-start nil))) + '(if (match-beginning 1) + (save-excursion + (goto-char (match-beginning 1)) + (condition-case nil + (forward-sexp 1) + (error + (condition-case nil + (forward-char 200) + (error nil)))) ; typeahead + (1- (point))) ; report limit + (forward-char -2)) ; disable continued expr + nil (1 font-lock-variable-name-face))) ;; foreach my $foo ( `(,(rx symbol-start "for" (opt "each") commit ada8822c45baa61fcfc06d11643969dd24bf5393 Author: Filipp Gunbin Date: Tue Jun 20 20:43:32 2023 +0300 Fix ldap-search when WITHDN is non-nil (bug#64089) * lisp/net/ldap.el (ldap-search): Apply ldap-decode-attribute only to attribute pairs. (ldap-search-internal): Parse dn with the same regexp as other attrs; use its value instead of the whole line. Include entry into result only if valid dn is present, to avoid treating process sentinel messages like an entry. Fix accidental match data clobbering. Document return value format. diff --git a/lisp/net/ldap.el b/lisp/net/ldap.el index 78405414a28..5c3766a76b3 100644 --- a/lisp/net/ldap.el +++ b/lisp/net/ldap.el @@ -472,7 +472,8 @@ ldap-search If WITHDN is non-nil, each entry in the result will be prepended with its distinguished name WITHDN. Additional search parameters can be specified through -`ldap-host-parameters-alist', which see." +`ldap-host-parameters-alist', which see. +See `ldap-search-internal' for the description of return value." (interactive "sFilter:") (or host (setq host ldap-default-host) @@ -487,7 +488,9 @@ ldap-search (if ldap-ignore-attribute-codings result (mapcar (lambda (record) - (mapcar #'ldap-decode-attribute record)) + (append (and withdn (list (car record))) + (mapcar #'ldap-decode-attribute + (if withdn (cdr record) record)))) result)))) (defun ldap-password-read (host) @@ -570,8 +573,13 @@ ldap-search-internal `sizelimit' is the maximum number of matches to return. `withdn' if non-nil each entry in the result will be prepended with its distinguished name DN. -The function returns a list of matching entries. Each entry is itself -an alist of attribute/value pairs." + +The function returns a list of matching entries. Each entry is +itself a list ATTRS of (ATTR VALUE) pairs; `dn' attribute is not +included. +When `withdn' is non-nil the result is instead an alist with +elements (DN . ATTRS), where DN is a string value and ATTRS is +same as above." (let* ((buf (get-buffer-create " *ldap-search*")) (bufval (get-buffer-create " *ldap-value*")) (host (or (plist-get search-plist 'host) @@ -703,35 +711,42 @@ ldap-search-internal (while (progn (skip-chars-forward " \t\n") (not (eobp))) - (setq dn (buffer-substring (point) (line-end-position))) - (forward-line 1) (while (looking-at "^\\([A-Za-z][-A-Za-z0-9]*\ \\|[0-9]+\\(?:\\.[0-9]+\\)*\\)\\(;[-A-Za-z0-9]+\\)*[=:\t ]+\ \\(<[\t ]*file://\\)?\\(.*\\)$") (setq name (match-string 1) value (match-string 4)) - ;; Need to handle file:///D:/... as generated by OpenLDAP - ;; on DOS/Windows as local files. - (if (and (memq system-type '(windows-nt ms-dos)) - (eq (string-match "/\\(.:.*\\)$" value) 0)) - (setq value (match-string 1 value))) - ;; Do not try to open non-existent files - (if (match-string 3) - (with-current-buffer bufval - (erase-buffer) - (set-buffer-multibyte nil) - (insert-file-contents-literally value) - (delete-file value) - (setq value (buffer-string))) - (setq value " ")) - (setq record (cons (list name value) - record)) + (when (memq system-type '(windows-nt ms-dos)) + ;; Need to handle file:///D:/... as generated by + ;; OpenLDAP on DOS/Windows as local files. + (save-match-data + (when (eq (string-match "/\\(.:.*\\)$" value) 0) + (setq value (match-string 1 value))))) + (cond ((match-string 3) ;normal value written to a file + (with-current-buffer bufval + (erase-buffer) + (set-buffer-multibyte nil) + (insert-file-contents-literally value) + (delete-file value) + (setq value (buffer-string)))) + (;; dn is output inline + (string-equal-ignore-case name "dn") + (setq dn value + name nil + value nil)) + (t (setq value " "))) + (and name value + (setq record (cons (list name value) + record))) (forward-line 1)) - (cond (withdn - (push (cons dn (nreverse record)) result)) - (record - (push (nreverse record) result))) - (setq record nil) + (when dn + (cond (withdn + (push (cons dn (nreverse record)) + result)) + (record + (push (nreverse record) result)))) + (setq record nil + dn nil) (message "Parsing results... %d" numres) (setq numres (1+ numres))) (message "Parsing results... done")