commit deb74de4f2e6a16b81663cbd95f97bfc9e24e467 (HEAD, refs/remotes/origin/master) Author: F. Jason Park Date: Sun Jul 23 23:09:42 2023 -0700 Simplify multi-frame behavior in erc-bufbar-mode * lisp/erc/erc-status-sidebar.el (erc-status-sidebar-singular, erc-status-sidebar--singular-p): Replace option new in ERC 5.6 with the latter, an internal flag. (erc-status-sidebar-get-window): Use new name for option turned ordinary variable `erc-status-sidebar--singular-p'. (erc-status-sidebar-close): Add comment. (erc-status-sidebar--open): New function containing the old body of `erc-status-sidebar-open'. (erc-bufbar-mode, erc-bufbar-enable, erc-bufbar-disable): Update variable names. Close sidebar window on all frames when disabling, and don't set mode variable to nil when enabling. These may have made some practical sense but were illogical. For example, it's confusing to leave `erc-status-sidebar--open' in `erc--setup-buffer-hook' while reporting the mode as being disabled. (erc-status-sidebar-open): Move to slightly later in same file, after defining `erc-bufbar-mode'. When `erc-bufbar-mode' is active, always create a sidebar if needed, even when another frame is already displaying one. (erc-status-toggle-sidebar): When `erc-bufbar-mode' is disabled, revert to pre-5.6 behavior. When the module is enabled, adopt new behavior of ensuring the current frame shows a sidebar, even if another frame already has one. (erc-status-sidebar-refresh): Save and restore `window-start' in all windows showing a sidebar buffer after refreshing. Update option and variable names. (erc-status-sidebar-refresh-triggers): Add doc string, noting that the variable is set locally when the option `erc-status-sidebar-highlight-active-buffer' is non-nil. (erc-status-sidebar--highlight-refresh-triggers): New variable containing additional triggers enabled when the option `erc-status-highlight-active-buffer' is non-nil. (erc-status-sidebar--refresh-unless-input): New function to run `erc-status-sidebar-refresh' unless input is pending or the selected window's buffer is a minibuffer. (erc-status-sidebar--post-refresh): Call `erc-status-sidebar-refresh' wrapper `erc-status-sidebar--refresh-unless-input' instead. (erc-status-sidebar-set-window-preserve-size): Update var name to `erc-status-sidebar--singular-p'. (erc-status-sidebar-mode): Run `erc-status-sidebar--post-refresh' on `window-selection-change-functions' globally when highlighting active buffers. (bug#63595) diff --git a/lisp/erc/erc-status-sidebar.el b/lisp/erc/erc-status-sidebar.el index b8bd7b0065e..cf3d20aeffa 100644 --- a/lisp/erc/erc-status-sidebar.el +++ b/lisp/erc/erc-status-sidebar.el @@ -45,8 +45,8 @@ ;; Use M-x erc-status-sidebar-kill RET to kill the sidebar buffer and ;; close the sidebar on all frames. -;; In addition to the commands above, you can also try the all-in-one, -;; "DWIM" command, `erc-bufbar-mode'. See its doc string for usage. +;; In addition to the commands above, you can also try the all-in-one +;; entry point `erc-bufbar-mode'. See its doc string for usage. ;; If you want the status sidebar enabled whenever you use ERC, add ;; `bufbar' to `erc-modules'. Note that this library also has a major @@ -130,8 +130,11 @@ erc-status-sidebar-style `erc-status-sidebar-pad-hierarchy' for the above-mentioned purposes. ERC also accepts a list of -functions to preform these roles a la carte. See doc strings for -a description of their expected arguments and return values." +functions to preform these roles a la carte. Since the members +of the above sets aren't really interoperable, we don't offer +them here as customization choices, but you can still specify +them manually. See doc strings for a description of their +expected arguments and return values." :package-version '(ERC . "5.6") ; FIXME sync on release :type '(choice (const channels-only) (const all-mixed) @@ -158,10 +161,12 @@ erc-status-sidebar-click-display-action :key-type symbol :value-type (sexp :tag "Value"))))) -(defcustom erc-status-sidebar-singular t - "Whether to show the sidebar on all frames or just one (default)." - :package-version '(ERC . "5.6") ; FIXME sync on release - :type 'boolean) +(defvar erc-status-sidebar--singular-p t + "Whether to restrict the sidebar to a single frame. +This variable only affects `erc-bufbar-mode'. Disabling it does +not arrange for automatically showing the sidebar in all frames. +Rather, disabling it allows for displaying the sidebar in the +selected frame even if it's already showing in some other frame.") (defvar hl-line-mode) (declare-function hl-line-highlight "hl-line" nil) @@ -178,7 +183,7 @@ erc-status-sidebar-get-window If NO-CREATION is non-nil, the window is not created." (let ((sidebar-window (get-buffer-window erc-status-sidebar-buffer-name - erc-status-sidebar-singular))) + erc-status-sidebar--singular-p))) (unless (or sidebar-window no-creation) (with-current-buffer (erc-status-sidebar-get-buffer) (setq-local vertical-scroll-bar nil)) @@ -214,7 +219,7 @@ erc-status-sidebar-close containing it on the current frame is closed. See `erc-status-sidebar-kill'." (interactive "P") - (mapcar #'delete-window + (mapcar #'delete-window ; FIXME use `mapc'. (get-buffer-window-list (erc-status-sidebar-get-buffer) nil (if all-frames t)))) @@ -223,10 +228,8 @@ erc-status-sidebar-writable `(let ((buffer-read-only nil)) ,@body)) -;;;###autoload -(defun erc-status-sidebar-open () - "Open or create a sidebar." - (interactive) +(defun erc-status-sidebar--open () + "Maybe open the sidebar, respecting `erc-status-sidebar--singular-p'." (save-excursion (if (erc-status-sidebar-buffer-exists-p) (erc-status-sidebar-get-window) @@ -237,11 +240,15 @@ erc-status-sidebar-open ;;;###autoload(autoload 'erc-bufbar-mode "erc-status-sidebar" nil t) (define-erc-module bufbar nil "Show `erc-track'-like activity in a side window. -When enabling, show the sidebar immediately if called from a -connected ERC buffer. Otherwise, arrange for doing so on connect -or whenever next displaying a new ERC buffer. When disabling, -hide the status window if it's showing. With a negative prefix -arg, also shutdown the session." +When enabling, show the sidebar immediately in the current frame +if called from a connected ERC buffer. Otherwise, arrange for +doing so on connect or whenever next displaying a new ERC buffer. +When disabling, hide the status window in all frames. With a +negative prefix arg, also shutdown the session. Normally, this +module only allows one sidebar window in an Emacs session. To +override this, use `erc-status-sidebar-open' to force creation +and `erc-status-sidebar-close' to hide a single instance on the +current frame only." ((unless erc-track-mode (unless (memq 'track erc-modules) (erc--warn-once-before-connect 'erc-bufbar-mode @@ -249,30 +256,38 @@ bufbar " This will affect \C-]all\C-] ERC sessions." " Add `track' to `erc-modules' to silence this message.")) (erc-track-mode +1)) - (add-hook 'erc--setup-buffer-hook #'erc-status-sidebar-open) + (add-hook 'erc--setup-buffer-hook #'erc-status-sidebar--open) (unless erc--updating-modules-p (if (erc-with-server-buffer erc-server-connected) - (erc-status-sidebar-open) - (setq erc-bufbar-mode nil) + (erc-status-sidebar--open) (when (derived-mode-p 'erc-mode) (erc-error "Not initializing `erc-bufbar-mode' in %s" (current-buffer)))))) - ((remove-hook 'erc--setup-buffer-hook #'erc-status-sidebar-open) - (erc-status-sidebar-close erc-status-sidebar-singular) + ((remove-hook 'erc--setup-buffer-hook #'erc-status-sidebar--open) + (erc-status-sidebar-close 'all-frames) (when-let ((arg erc--module-toggle-prefix-arg) ((numberp arg)) ((< arg 0))) (erc-status-sidebar-kill)))) +;;;###autoload +(defun erc-status-sidebar-open () + "Open or create a sidebar window in the current frame. +When `erc-bufbar-mode' is active, do this even if one already +exists in another frame." + (interactive) + (let ((erc-status-sidebar--singular-p (not erc-bufbar-mode))) + (erc-status-sidebar--open))) + ;;;###autoload (defun erc-status-sidebar-toggle () "Toggle the sidebar open/closed on the current frame. -Do this regardless of `erc-status-sidebar-singular'." +When opening, and `erc-bufbar-mode' is active, create a sidebar +even if one already exists in another frame." (interactive) (if (get-buffer-window erc-status-sidebar-buffer-name nil) (erc-status-sidebar-close) - (let (erc-status-sidebar-singular) - (erc-status-sidebar-open)))) + (erc-status-sidebar-open))) (defun erc-status-sidebar-get-channame (buffer) "Return name of BUFFER with all leading \"#\" characters removed." @@ -413,11 +428,10 @@ erc-status-sidebar-refresh erc-status-sidebar-pad-hierarchy)) (v v))) (chanlist (apply sort-fn (funcall list-fn nil) nil)) - (window nil) - (winstart nil)) + (windows nil)) (with-current-buffer (erc-status-sidebar-get-buffer) - (setq window (get-buffer-window nil erc-status-sidebar-singular) - winstart (and window (window-start window))) + (dolist (window (get-buffer-window-list nil nil t)) + (push (cons window (window-start window)) windows)) (erc-status-sidebar-writable (delete-region (point-min) (point-max)) (goto-char (point-min)) @@ -443,9 +457,8 @@ erc-status-sidebar-refresh 0 cnlen 'help-echo "mouse-1: switch to buffer in other window" channame) (funcall insert-fn channame chanbuf chanlist))) - (when winstart - (set-window-point window winstart) - (with-selected-window window (recenter 0))) + (when windows + (map-apply #'set-window-start windows)) (when (and erc-status-sidebar-highlight-active-buffer (marker-buffer erc-status-sidebar--active-marker)) (goto-char erc-status-sidebar--active-marker) @@ -519,14 +532,28 @@ erc-status-sidebar-refresh-triggers erc-kill-server-hook erc-kick-hook erc-disconnected-hook - erc-quit-hook)) + erc-quit-hook) + "Hooks to refresh the sidebar on. +This may be set locally in the status-sidebar buffer under +various conditions, like when the option +`erc-status-sidebar-highlight-active-buffer' is non-nil.") + +(defvar erc-status-sidebar--highlight-refresh-triggers + '(window-selection-change-functions) + "Triggers enabled with `erc-status-sidebar-highlight-active-buffer'.") + +(defun erc-status-sidebar--refresh-unless-input () + "Run `erc-status-sidebar-refresh' unless there are unread commands. +Also abstain when the user is interacting with the minibuffer." + (unless (or (input-pending-p) (minibuffer-window-active-p (selected-window))) + (erc-status-sidebar-refresh))) (defun erc-status-sidebar--post-refresh (&rest _ignore) "Schedule sidebar refresh for execution after command stack is cleared. Ignore arguments in IGNORE, allowing this function to be added to hooks that invoke it with arguments." - (run-at-time 0 nil #'erc-status-sidebar-refresh)) + (run-at-time 0 nil #'erc-status-sidebar--refresh-unless-input)) (defun erc-status-sidebar-mode--unhook () "Remove hooks installed by `erc-status-sidebar-mode'." @@ -541,7 +568,7 @@ erc-status-sidebar-set-window-preserve-size Note that preserve status needs to be reset when the window is manually resized, so `erc-status-sidebar-mode' adds this function to the `window-configuration-change-hook'." - (when (and (eq (selected-window) (let (erc-status-sidebar-singular) + (when (and (eq (selected-window) (let (erc-status-sidebar--singular-p) (erc-status-sidebar-get-window))) (fboundp 'window-preserve-size)) (unless (eq (window-total-width) (window-min-size nil t)) @@ -563,6 +590,10 @@ erc-status-sidebar-mode (add-hook 'window-configuration-change-hook #'erc-status-sidebar-set-window-preserve-size nil t) + (when erc-status-sidebar-highlight-active-buffer + (setq-local erc-status-sidebar-refresh-triggers + `(,@erc-status-sidebar--highlight-refresh-triggers + ,@erc-status-sidebar-refresh-triggers))) (dolist (hk erc-status-sidebar-refresh-triggers) (add-hook hk #'erc-status-sidebar--post-refresh)) commit fb57b6ccb9f033106b0c00539590f22614604f22 Author: F. Jason Park Date: Sun Jul 23 05:05:13 2023 -0700 ; Add example buffer-display option to ERC's manual * doc/misc/erc.texi: Add customization for `erc-interactive-display' to Sample Configuration section. * etc/ERC-NEWS: Improve various entries, like those for `keep-place-indicator', `fill-wrap', `bufbar', etc. diff --git a/doc/misc/erc.texi b/doc/misc/erc.texi index 2e216629a1d..6d7785a9b54 100644 --- a/doc/misc/erc.texi +++ b/doc/misc/erc.texi @@ -1268,6 +1268,9 @@ Sample Configuration (erc-server-reconnect-function #'erc-server-delayed-check-reconnect) (erc-server-reconnect-timeout 30) + ;; Show new buffers in the current window instead of a split. + (erc-interactive-display 'buffer) + ;; Insert a newline when I hit at the prompt, and prefer ;; something more deliberate for actually sending messages. :bind (:map erc-mode-map @@ -1391,6 +1394,16 @@ Sample Configuration customize-group @key{RET} erc-server @key{RET}} from almost anywhere in Emacs. +To make sure you've got this, try quickly customizing the option +@code{erc-interactive-display}, which lives in the @samp{Erc Buffers} +group (@kbd{M-x customize-group @key{RET} erc-buffers @key{RET}}). As +its doc string explains, the option controls where new buffers show up +when you do @kbd{M-x erc-tls @key{RET}} or issue certain ``slash'' +commands, like @kbd{/JOIN #emacs-beginners @key{RET}}, at ERC's +prompt. Change its value to the symbol @code{buffer} by choosing +@samp{Use current window} (item @kbd{5}) from the option's +@samp{[Value Menu]}. Don't forget to save. + Now it's time to set some key bindings for @code{erc-mode-map}, a major-mode keymap active in all ERC buffers. In general, it's best to do this part either entirely or in conjunction with some lisp code in diff --git a/etc/ERC-NEWS b/etc/ERC-NEWS index a3a8cb086e0..94452514e6d 100644 --- a/etc/ERC-NEWS +++ b/etc/ERC-NEWS @@ -14,29 +14,29 @@ GNU Emacs since Emacs version 22.1. * Changes in ERC 5.6 -** Module 'keep-place' has gained a more flamboyant cousin. -Remember your place in ERC buffers more easily while retaining the -freedom to look around, all with the help of a configurable, visible -indicator. Optionally sync the indicator to any progress made when -you haven't yet caught up to the live stream. See options -'erc-keep-place-indicator-style' and friends, and try M-x +** Module 'keep-place' has a more decorative cousin. +Remember your place in ERC buffers a bit more easily with the help of +a configurable, visible indicator. Optionally sync the indicator to +any progress made while you haven't yet caught up to the live stream. +See options 'erc-keep-place-indicator-style' and friends, and try M-x keep-place-indicator-mode to see it in action. -** Module 'fill' offers a style based on 'visual-line-mode'. -This fill style mimics the "hanging indent" look of 'erc-fill-static' -and provides some movement and editing commands to optionally tame the +** Module 'fill' offers an adaptive style based on 'visual-line-mode'. +This style dynamically wraps messages to a window's width while +mimicking the "hanging indent" look of 'erc-fill-static'. It also +provides some movement and editing commands to optionally tame the less familiar aspects of 'visual-line' behavior. An interactive -helper called 'erc-fill-wrap-nudge' allows for dynamic "refilling" of -buffers on the fly. Set 'erc-fill-function' to 'erc-fill-wrap' to get -started. +helper called 'erc-fill-wrap-nudge' makes easy work of adjusting the +overhang on the fly. Set 'erc-fill-function' to 'erc-fill-wrap' to +get started. ** A module for nickname highlighting has joined ERC. Automatic nickname coloring has come to ERC core. Users familiar with 'erc-hl-nicks', from which this module directly descends, will already be familiar with its suite of handy options. By default, each nickname in an ERC session receives a unique face with a unique (or -evenly dealt) foreground color. Add 'nicks' to 'erc-modules' to get -started. +uniformly dealt) foreground color. Add 'nicks' to 'erc-modules' to +get started. ** A unified interactive entry point. New users are often dismayed to discover that M-x ERC doesn't connect @@ -88,9 +88,9 @@ users to edit the 'erc-modules' widget instead. Users can now add 'bufbar' to 'erc-modules' to achieve the same effect as toggling 'erc-status-sidebar-open' manually at the start of an IRC session. The module has also been outfitted to show channels and -queries under their respective servers by default. To avoid -confusion, the major mode used for the sidebar buffer itself, -'erc-status-sidebar-mode', is no longer available interactively. +queries under their servers by default. To avoid confusion, the major +mode for the actual sidebar buffer itself, 'erc-status-sidebar-mode', +is no longer available interactively. ** A new spin on a classic integration in erc-speedbar. Add 'nickbar' to 'erc-modules' to spawn a dynamically updating side @@ -252,20 +252,19 @@ versions. For starters, the 'cursor-sensor-functions' property no longer contains unique closures and thus no longer proves effective for traversing messages. To compensate, a new property, 'erc-timestamp', -now spans message bodies but not the newlines delimiting them. -Somewhat relatedly, the function 'erc-insert-aligned' has been -deprecated and removed from the primary client code path. -Additionally, the 'stamp' module now merges its 'invisible' property -with existing ones, when present, and it includes all white space -around stamps when doing so. - -Moreover, such "propertizing" of surrounding white space now extends -to all 'stamp'-applied properties, like 'field', in all intervening -space between message text and timestamps. This constitutes a +now spans message bodies but not the newlines delimiting them. Also +affecting the `stamp' module is the deprecation of the function +'erc-insert-aligned' and its removal from client code. Additionally, +the module now merges its 'invisible' property with existing ones and +includes all white space around stamps when doing so. + +This "propertizing" of surrounding white space also extends to all +'stamp'-applied properties, like 'field', in all intervening space +between message text and timestamps. Technically, this constitutes a breaking change from the perspective of detecting a timestamp's -bounds. For example, ERC has always propertized leading space before +bounds. However, ERC has always propertized leading space before right-sided stamps on the same line as message text but not those -folded onto the next line. This inconsistency made stamp detection +folded onto the next line. Such inconsistency made stamp detection overly complex and produced uneven results when toggling stamp visibility. @@ -317,11 +316,11 @@ third-party code, the key takeaway is that more 'font-lock-face' properties encountered in the wild may be combinations of faces rather than lone ones. -*** Prompt input split before 'erc-pre-send-functions' gets a say. -Hook members are now treated to input whose lines have already been -adjusted to fall within the allowed length limit. For convenience, -third-party code can request that the final input be "re-filled" prior -to being sent. See doc string for details. +*** 'erc-pre-send-functions' visits prompt input post-split. +ERC now adjusts input lines to fall within allowed length limits +before showing hook members the result. For compatibility, +third-party code can request that the final input be adjusted again +prior to being sent. See doc string for details. *** ERC's prompt survives the insertion of user input and messages. Previously, ERC's prompt and its input marker disappeared while @@ -329,18 +328,20 @@ running hooks during message insertion, and the position of its "insert marker" (ERC's per-buffer process mark) was inconsistent during these spells. To make insertion handling more predictable in preparation for incorporating various protocol extensions, the prompt -and its bounding markers have become perennial fixtures. To effect -this change, small behavioral differences in message insertion have -been adopted. Crucially, 'erc-insert-marker' now has an "insertion -type" of t, and 'erc-display-line-1' now calls 'insert' instead of -'insert-before-prompt'. This allows user code to leave its own -markers via 'erc-insert-modify-hook' and 'erc-insert-post-hook' -instead of having to resort to workarounds. Message insertion for -outgoing messages, in 'erc-display-msg', remains as before. In rare -cases, these changes may mean third-party code needs tweaking, for -example, requiring the use of 'insert-before-markers' instead of -'insert'. As always, users feeling unduly inconvenienced by these -changes are encouraged to voice their concerns on the bug list. +and its bounding markers have become perennial fixtures. + +To effect this change, small behavioral differences in message +insertion have been adopted. Crucially, 'erc-insert-marker' now has +an "insertion type" of t, and 'erc-display-line-1' now calls 'insert' +instead of 'insert-before-markers. This allows user code running on +'erc-insert-modify-hook' and 'erc-insert-post-hook' to leave its own +markers at the actual insertion point instead of resorting to +workarounds. Message insertion for outgoing messages, in +'erc-display-msg', remains as before. In rare cases, these changes +may mean third-party code needs tweaking, for example, requiring the +use of 'insert-before-markers' instead of 'insert'. As always, users +feeling unduly inconvenienced by these changes are encouraged to voice +their concerns on the bug list. *** Miscellaneous changes Two helper macros from GNU ELPA's Compat library are now available to commit 8623159b4aec870085a897d321dd9599831ef191 Author: F. Jason Park Date: Sat Jul 22 14:07:38 2023 -0700 Fix CTCP ACTION regression in erc-fill-wrap * lisp/erc/erc-fill.el (erc-fill--wrap-continued-message-p): Return nil when current message is a CTCP ACTION. This fixes a regression introduced by 63d8b2a59a4 "Make erc-fill-wrap work with left-sided stamps". * test/lisp/erc/erc-fill-tests.el: (erc-fill-wrap--merge-action): New test. * test/lisp/erc/resources/fill/snapshots/merge-wrap-01.eld: New test data file. (Bug#60936) diff --git a/lisp/erc/erc-fill.el b/lisp/erc/erc-fill.el index 17eb0002f08..e2a82582a3f 100644 --- a/lisp/erc/erc-fill.el +++ b/lisp/erc/erc-fill.el @@ -443,12 +443,13 @@ erc-fill--wrap-continued-message-p (cons (get-text-property m 'erc-timestamp) (get-text-property spr 'erc-speaker))))) (ts (pop props)) + (props) ((not (time-less-p (erc-stamp--current-time) ts))) ((time-less-p (time-subtract (erc-stamp--current-time) ts) erc-fill--wrap-max-lull)) (speaker (next-single-property-change (point-min) 'erc-speaker)) + ((not (eq (get-text-property speaker 'erc-ctcp) 'ACTION))) (nick (get-text-property speaker 'erc-speaker)) - (props) ((erc-nick-equal-p props nick)))) (set-marker erc-fill--wrap-last-msg (point-min)))) diff --git a/test/lisp/erc/erc-fill-tests.el b/test/lisp/erc/erc-fill-tests.el index 67622da9f3d..b81d0c15558 100644 --- a/test/lisp/erc/erc-fill-tests.el +++ b/test/lisp/erc/erc-fill-tests.el @@ -241,6 +241,46 @@ erc-fill-wrap--merge " " " " " " " " " " " " " ") (erc-fill-tests--compare "merge-02-right"))))) +(ert-deftest erc-fill-wrap--merge-action () + :tags '(:unstable) + (unless (>= emacs-major-version 29) + (ert-skip "Emacs version too low, missing `buffer-text-pixel-size'")) + + (erc-fill-tests--wrap-populate + + (lambda () + ;; Set this here so that the first few messages are from 1970 + (let ((erc-fill-tests--time-vals (lambda () 1680332400))) + (erc-fill-tests--insert-privmsg "bob" "zero.") + + (erc-process-ctcp-query + erc-server-process + (make-erc-response + :unparsed ":bob!~u@fake PRIVMSG #chan :\1ACTION one\1" + :sender "bob!~u@fake" :command "PRIVMSG" + :command-args '("#chan" "\1ACTION one\1") :contents "\1ACTION one\1") + "bob" "~u" "fake") + + (erc-fill-tests--insert-privmsg "bob" "two.") + + ;; Compat switch to opt out of overhanging speaker. + (let (erc-fill--wrap-action-dedent-p) + (erc-process-ctcp-query + erc-server-process + (make-erc-response + :unparsed ":bob!~u@fake PRIVMSG #chan :\1ACTION three\1" + :sender "bob!~u@fake" :command "PRIVMSG" + :command-args '("#chan" "\1ACTION three\1") + :contents "\1ACTION three\1") + "bob" "~u" "fake")) + + (erc-fill-tests--insert-privmsg "bob" "four.")) + + (should (= erc-fill--wrap-value 27)) + (erc-fill-tests--wrap-check-prefixes + "*** " " " " " " " "* bob " " " "* " " ") + (erc-fill-tests--compare "merge-wrap-01")))) + (ert-deftest erc-fill-line-spacing () :tags '(:unstable) (unless (>= emacs-major-version 29) diff --git a/test/lisp/erc/resources/fill/snapshots/merge-wrap-01.eld b/test/lisp/erc/resources/fill/snapshots/merge-wrap-01.eld new file mode 100644 index 00000000000..a3d533c87b5 --- /dev/null +++ b/test/lisp/erc/resources/fill/snapshots/merge-wrap-01.eld @@ -0,0 +1 @@ +#("\n\n\n[Thu Jan 1 1970]\n*** This server is in debug mode and is logging all user I/O. If you do not wish for everything you send to be readable by the server owner(s), please disconnect.[00:00]\n bob: come, you are a tedious fool: to the purpose. What was done to Elbow's wife, that he hath cause to complain of? Come me to what was done to her.\n alice: Either your unparagoned mistress is dead, or she's outprized by a trifle.\n\n[Sat Apr 1 2023]\n zero.[07:00]\n* bob one\n two.\n* bob three\n four.\n" 2 20 (erc-timestamp 0 line-prefix (space :width (- 27 (18))) field erc-timestamp) 20 21 (erc-timestamp 0 field erc-timestamp) 21 183 (erc-timestamp 0 wrap-prefix #2=(space :width 27) line-prefix #3=(space :width (- 27 (4)))) 183 190 (erc-timestamp 0 field erc-timestamp wrap-prefix #2# line-prefix #3# display #1=(#7=(margin right-margin) #("[00:00]" 0 7 (display #1# invisible timestamp font-lock-face erc-timestamp-face)))) 191 192 (erc-timestamp 0 wrap-prefix #2# line-prefix #4=(space :width (- 27 (8))) erc-command PRIVMSG) 192 197 (erc-timestamp 0 wrap-prefix #2# line-prefix #4# erc-command PRIVMSG) 197 199 (erc-timestamp 0 wrap-prefix #2# line-prefix #4# erc-command PRIVMSG) 199 202 (erc-timestamp 0 wrap-prefix #2# line-prefix #4# erc-command PRIVMSG) 202 315 (erc-timestamp 0 wrap-prefix #2# line-prefix #4# erc-command PRIVMSG) 315 316 (erc-timestamp 0 erc-command PRIVMSG) 316 348 (erc-timestamp 0 wrap-prefix #2# line-prefix #4# erc-command PRIVMSG) 349 350 (erc-timestamp 0 wrap-prefix #2# line-prefix #5=(space :width (- 27 (6))) erc-command PRIVMSG) 350 353 (erc-timestamp 0 wrap-prefix #2# line-prefix #5# erc-command PRIVMSG) 353 355 (erc-timestamp 0 wrap-prefix #2# line-prefix #5# erc-command PRIVMSG) 355 360 (erc-timestamp 0 wrap-prefix #2# line-prefix #5# erc-command PRIVMSG) 360 435 (erc-timestamp 0 wrap-prefix #2# line-prefix #5# erc-command PRIVMSG) 436 454 (erc-timestamp 1680332400 line-prefix (space :width (- 27 (18))) field erc-timestamp) 454 455 (erc-timestamp 1680332400 field erc-timestamp) 455 456 (erc-timestamp 1680332400 wrap-prefix #2# line-prefix #6=(space :width (- 27 (6))) erc-command PRIVMSG) 456 459 (erc-timestamp 1680332400 wrap-prefix #2# line-prefix #6# erc-command PRIVMSG) 459 466 (erc-timestamp 1680332400 wrap-prefix #2# line-prefix #6# erc-command PRIVMSG) 466 473 (erc-timestamp 1680332400 field erc-timestamp wrap-prefix #2# line-prefix #6# display #8=(#7# #("[07:00]" 0 7 (display #8# invisible timestamp font-lock-face erc-timestamp-face)))) 474 476 (erc-timestamp 1680332400 wrap-prefix #2# line-prefix #9=(space :width (- 27 (6))) erc-ctcp ACTION erc-command PRIVMSG) 476 479 (erc-timestamp 1680332400 wrap-prefix #2# line-prefix #9# erc-ctcp ACTION erc-command PRIVMSG) 479 483 (erc-timestamp 1680332400 wrap-prefix #2# line-prefix #9# erc-ctcp ACTION erc-command PRIVMSG) 484 485 (erc-timestamp 1680332400 wrap-prefix #2# line-prefix #10=(space :width (- 27 (6))) erc-command PRIVMSG) 485 488 (erc-timestamp 1680332400 wrap-prefix #2# line-prefix #10# erc-command PRIVMSG) 488 494 (erc-timestamp 1680332400 wrap-prefix #2# line-prefix #10# erc-command PRIVMSG) 495 497 (erc-timestamp 1680332400 wrap-prefix #2# line-prefix #11=(space :width (- 27 (2))) erc-ctcp ACTION erc-command PRIVMSG) 497 500 (erc-timestamp 1680332400 wrap-prefix #2# line-prefix #11# erc-ctcp ACTION erc-command PRIVMSG) 500 506 (erc-timestamp 1680332400 wrap-prefix #2# line-prefix #11# erc-ctcp ACTION erc-command PRIVMSG) 507 508 (erc-timestamp 1680332400 wrap-prefix #2# line-prefix #12=(space :width (- 27 (6))) erc-command PRIVMSG) 508 511 (erc-timestamp 1680332400 wrap-prefix #2# line-prefix #12# erc-command PRIVMSG) 511 518 (erc-timestamp 1680332400 wrap-prefix #2# line-prefix #12# erc-command PRIVMSG)) \ No newline at end of file commit 6479e8758d9b20736afce35c5e2b2b334c47593b Author: Basil L. Contovounesios Date: Fri Jul 28 18:35:20 2023 +0200 ; Avoid recent tar-mode.el constant mutation * lisp/tar-mode.el (tar-attr-vector): Initialize with fresh vector to avoid constant vector mutation (bug#64686). (tar-parse-pax-extended-header): Use fillarray. diff --git a/lisp/tar-mode.el b/lisp/tar-mode.el index e4ea95343e0..2b6329fecc3 100644 --- a/lisp/tar-mode.el +++ b/lisp/tar-mode.el @@ -255,15 +255,14 @@ pax-decode-string (decode-coding-string str coding) str)) -(defvar tar-attr-vector '[nil nil nil nil nil nil nil nil]) +(defvar tar-attr-vector (make-vector 8 nil)) (defun tar-parse-pax-extended-header (pos) "Parse a pax external header of a Posix-format tar file." (let ((end (+ pos 512)) (result tar-attr-vector) (coding 'utf-8-unix) attr value record-len value-len) - (dotimes (i 8) - (aset result i nil)) + (fillarray result nil) (goto-char pos) (while (and (< pos end) (re-search-forward pax-extended-attribute-record-regexp commit 8c3338f6ba354218aee12c223d778be4180f892b Author: Ulrich Müller Date: Fri Jul 28 12:21:42 2023 +0200 Avoid spurious whitespace in the modeline of emacsclient frames * lisp/bindings.el (mode-line-client): Compute 'help-echotext property in advance. (Bug#58183) diff --git a/lisp/bindings.el b/lisp/bindings.el index 0a0fef1b564..22f05939235 100644 --- a/lisp/bindings.el +++ b/lisp/bindings.el @@ -226,9 +226,9 @@ mode-line-mule-info (put 'mode-line-mule-info 'risky-local-variable t) (defvar mode-line-client - `("" - (:propertize ("" (:eval (if (frame-parameter nil 'client) "@" ""))) - help-echo ,(purecopy "emacsclient frame"))) + `(:eval + (if (frame-parameter nil 'client) + ,(propertize "@" 'help-echo (purecopy "emacsclient frame")))) "Mode line construct for identifying emacsclient frames.") ;; Autoload if this file no longer dumped. ;;;###autoload commit 53948b6bffb3d8d7170ffad2628c9ae7f9ac2ac1 Author: Tassilo Horn Date: Fri Jul 28 12:26:49 2023 +0200 Make shell command status code checks more robust * lisp/doc-view.el (doc-view-ghostscript-program) (doc-view--revert-buffer, doc-view--pdf-outline): Compare 'shell-command' / 'call-process' return values with 'eql' instead of '=' to cater for the situation where the process received a signal. diff --git a/lisp/doc-view.el b/lisp/doc-view.el index 2f3c453471d..002b74e8898 100644 --- a/lisp/doc-view.el +++ b/lisp/doc-view.el @@ -176,7 +176,7 @@ doc-view-ghostscript-program ;; non-MikTeX apps. Was available under: ;; http://blog.miktex.org/post/2005/04/07/Starting-mgsexe-at-the-DOS-Prompt.aspx ((and (executable-find "mgs") - (= 0 (shell-command "mgs -q -dNODISPLAY -c quit"))) + (eql 0 (shell-command "mgs -q -dNODISPLAY -c quit"))) "mgs"))) (t "gs")) "Program to convert PS and PDF files to PNG." @@ -577,8 +577,8 @@ doc-view--revert-buffer ;; file. (TODO: We'd like to have something like that also ;; for other types, at least PS, but I don't know a good way ;; to test if a PS file is complete.) - (if (= 0 (call-process "pdfinfo" nil nil nil - doc-view--buffer-file-name)) + (if (eql 0 (call-process "pdfinfo" nil nil nil + doc-view--buffer-file-name)) (revert) (when (called-interactively-p 'interactive) (message "Can't revert right now because the file is corrupted."))) @@ -1914,7 +1914,7 @@ doc-view--pdf-outline (let ((outline nil) (fn (expand-file-name fn))) (with-temp-buffer - (unless (= 0 (call-process "mutool" nil (current-buffer) nil "show" fn "outline")) + (unless (eql 0 (call-process "mutool" nil (current-buffer) nil "show" fn "outline")) (imenu-unavailable-error "Unable to create imenu index using `mutool'")) (goto-char (point-min)) (while (re-search-forward doc-view--outline-rx nil t) commit aa360dfc3ed699f3e06a99a339d6a18080c2e9c5 Author: Mattias Engdegård Date: Fri Jul 28 11:14:01 2023 +0200 Clarify docs about regexp syntax-dependent character classes * doc/lispref/searching.texi (Char Classes, Rx Constructs) (Regexp Problems): Note that character classes don't take syntax properties into account. diff --git a/doc/lispref/searching.texi b/doc/lispref/searching.texi index a0289d1f3cd..66b33316faa 100644 --- a/doc/lispref/searching.texi +++ b/doc/lispref/searching.texi @@ -669,6 +669,10 @@ Char Classes through @samp{f} and @samp{A} through @samp{F}. @end table +The classes @samp{[:space:]}, @samp{[:word:]} and @samp{[:punct:]} use +the syntax-table of the current buffer but not any overriding syntax +text properties (@pxref{Syntax Properties}). + @node Regexp Backslash @subsubsection Backslash Constructs in Regular Expressions @cindex backslash in regular expressions @@ -1341,6 +1345,9 @@ Rx Constructs Match any non-@acronym{ASCII} character (but not raw bytes). @end table +The classes @code{space}, @code{word} and @code{punct} use the +syntax-table of the current buffer but not any overriding syntax text +properties (@pxref{Syntax Properties}).@* Corresponding string regexp: @samp{[[:@var{class}:]]} @item @code{(syntax @var{syntax})} @@ -1920,7 +1927,8 @@ Regexp Problems @item Avoid or-patterns in favor of bracket expressions: write @samp{[ab]} instead of @samp{a\|b}. Recall that @samp{\s-} and @samp{\sw} -are equivalent to @samp{[[:space:]]} and @samp{[[:word:]]}, respectively. +are equivalent to @samp{[[:space:]]} and @samp{[[:word:]]}, respectively, +most of the time. @item Since the last branch of an or-pattern does not add a backtrack point commit 0ecf2549a2443a9211b59d33dab83e00a51e8bfd Author: Mattias Engdegård Date: Fri Jul 28 11:12:09 2023 +0200 Make uniquify-tests work with out-of-tree builds and clean up * test/lisp/uniquify-tests.el (uniquify-project-transform): Set an explicit default-directory. * test/lisp/uniquify-tests.el (uniquify-dirs): Remove temporary directory after test. diff --git a/test/lisp/uniquify-tests.el b/test/lisp/uniquify-tests.el index e533c4b644c..224991cb048 100644 --- a/test/lisp/uniquify-tests.el +++ b/test/lisp/uniquify-tests.el @@ -22,6 +22,7 @@ ;;; Code: (require 'ert) +(require 'ert-x) (ert-deftest uniquify-basic () (let (bufs old-names) @@ -58,35 +59,35 @@ uniquify-basic (ert-deftest uniquify-dirs () "Check strip-common-suffix and trailing-separator-p work together; bug#47132" - (let* ((root (make-temp-file "emacs-uniquify-tests" 'dir)) - (a-path (file-name-concat root "a/x/y/dir")) - (b-path (file-name-concat root "b/x/y/dir"))) - (make-directory a-path 'parents) - (make-directory b-path 'parents) - (let ((uniquify-buffer-name-style 'forward) - (uniquify-strip-common-suffix t) - (uniquify-trailing-separator-p nil)) - (let ((bufs (list (find-file-noselect a-path) - (find-file-noselect b-path)))) - (should (equal (mapcar #'buffer-name bufs) - '("a/dir" "b/dir"))) - (mapc #'kill-buffer bufs))) - (let ((uniquify-buffer-name-style 'forward) - (uniquify-strip-common-suffix nil) - (uniquify-trailing-separator-p t)) - (let ((bufs (list (find-file-noselect a-path) - (find-file-noselect b-path)))) - (should (equal (mapcar #'buffer-name bufs) - '("a/x/y/dir/" "b/x/y/dir/"))) - (mapc #'kill-buffer bufs))) - (let ((uniquify-buffer-name-style 'forward) - (uniquify-strip-common-suffix t) - (uniquify-trailing-separator-p t)) - (let ((bufs (list (find-file-noselect a-path) - (find-file-noselect b-path)))) - (should (equal (mapcar #'buffer-name bufs) - '("a/dir/" "b/dir/"))) - (mapc #'kill-buffer bufs))))) + (ert-with-temp-directory root + (let ((a-path (file-name-concat root "a/x/y/dir")) + (b-path (file-name-concat root "b/x/y/dir"))) + (make-directory a-path 'parents) + (make-directory b-path 'parents) + (let ((uniquify-buffer-name-style 'forward) + (uniquify-strip-common-suffix t) + (uniquify-trailing-separator-p nil)) + (let ((bufs (list (find-file-noselect a-path) + (find-file-noselect b-path)))) + (should (equal (mapcar #'buffer-name bufs) + '("a/dir" "b/dir"))) + (mapc #'kill-buffer bufs))) + (let ((uniquify-buffer-name-style 'forward) + (uniquify-strip-common-suffix nil) + (uniquify-trailing-separator-p t)) + (let ((bufs (list (find-file-noselect a-path) + (find-file-noselect b-path)))) + (should (equal (mapcar #'buffer-name bufs) + '("a/x/y/dir/" "b/x/y/dir/"))) + (mapc #'kill-buffer bufs))) + (let ((uniquify-buffer-name-style 'forward) + (uniquify-strip-common-suffix t) + (uniquify-trailing-separator-p t)) + (let ((bufs (list (find-file-noselect a-path) + (find-file-noselect b-path)))) + (should (equal (mapcar #'buffer-name bufs) + '("a/dir/" "b/dir/"))) + (mapc #'kill-buffer bufs)))))) (ert-deftest uniquify-home () "uniquify works, albeit confusingly, in the presence of directories named \"~\"" @@ -147,16 +148,18 @@ uniquify-project-transform (project-vc-name "foo1/bar") bufs) (save-excursion - (should (file-exists-p "../README")) - (push (find-file-noselect "../README") bufs) - (push (find-file-noselect "other/README") bufs) - (should (equal (mapcar #'buffer-name bufs) - '("README" "README"))) - (push (find-file-noselect "foo2/bar/README") bufs) - (should (equal (mapcar #'buffer-name bufs) - '("README" "README" "README"))) - (while bufs - (kill-buffer (pop bufs)))))) + (let ((default-directory (expand-file-name "test/" source-directory))) + (should (file-exists-p "../README")) + (push (find-file-noselect "../README") bufs) + (push (find-file-noselect "other/README") bufs) + (should (equal (mapcar #'buffer-name bufs) + '("README" "README"))) + (push (find-file-noselect "foo2/bar/README") bufs) + (should (equal (mapcar #'buffer-name bufs) + '("README" "README" + "README"))) + (while bufs + (kill-buffer (pop bufs))))))) (provide 'uniquify-tests) ;;; uniquify-tests.el ends here