diff options
| author | F. Jason Park | 2023-12-23 12:46:33 -0800 |
|---|---|---|
| committer | F. Jason Park | 2023-12-27 21:32:25 -0800 |
| commit | 65735efdca017f2ec0aa1022b7e82f68fbe0084d (patch) | |
| tree | 9e00293e01aff32fe594e43ba484a702429a0a26 /lisp/erc | |
| parent | 8f571769e155a214ae2f9f760dd179b687d9982e (diff) | |
| download | emacs-65735efdca017f2ec0aa1022b7e82f68fbe0084d.tar.gz emacs-65735efdca017f2ec0aa1022b7e82f68fbe0084d.zip | |
Improve multi-window erc-keep-place-indicator-mode
* lisp/erc/erc-goodies.el (erc-keep-place-indicator-follow): Describe
condition causing an indicator update.
(erc--keep-place-indicator-on-window-configuration-change,
erc--keep-place-indicator-on-window-buffer-change): Rename former to
latter, add required WINDOW parameter, and don't move indicator if
buffer appears in multiple windows. Also, don't bother checking
whether either buffer is a mini because the manual says window change
functions don't run for minibuffer replacements.
(erc--keep-place-indicator-setup): Hook on
`window-buffer-change-functions' instead of
`window-configuration-change-hook'.
(erc-keep-place-mode, erc-keep-place-disable): Remove member from
`window-buffer-change-functions' instead of
`window-configuration-change-hook'.
(erc-keep-place): Use `visible' FRAME arg of `get-buffer-window'.
Don't twiddle `window-prev-buffers' when
`erc-keep-place-indicator-mode' is non-nil. This feature was
originally introduced by bug#59943.
* test/lisp/erc/erc-goodies-tests.el
(erc-goodies-tests--assert-kp-indicator-on,
erc-goodies-tests--assert-kp-indicator-off): Update hook name.
* test/lisp/erc/erc-scenarios-keep-place-indicator.el: New file.
* test/lisp/erc/resources/keep-place/follow.eld: New file.
Diffstat (limited to 'lisp/erc')
| -rw-r--r-- | lisp/erc/erc-goodies.el | 54 |
1 files changed, 35 insertions, 19 deletions
diff --git a/lisp/erc/erc-goodies.el b/lisp/erc/erc-goodies.el index e10f047b187..9d385b628dc 100644 --- a/lisp/erc/erc-goodies.el +++ b/lisp/erc/erc-goodies.el | |||
| @@ -300,7 +300,10 @@ A value of t means \"all\" ERC buffers." | |||
| 300 | 300 | ||
| 301 | (defcustom erc-keep-place-indicator-follow nil | 301 | (defcustom erc-keep-place-indicator-follow nil |
| 302 | "Whether to sync visual kept place to window's top when reading. | 302 | "Whether to sync visual kept place to window's top when reading. |
| 303 | For use with `erc-keep-place-indicator-mode'." | 303 | For use with `erc-keep-place-indicator-mode'. When enabled, the |
| 304 | indicator updates when the last window displaying the same buffer | ||
| 305 | switches away, but only if the indicator resides earlier in the | ||
| 306 | buffer than the window's start." | ||
| 304 | :group 'erc | 307 | :group 'erc |
| 305 | :package-version '(ERC . "5.6") | 308 | :package-version '(ERC . "5.6") |
| 306 | :type 'boolean) | 309 | :type 'boolean) |
| @@ -328,17 +331,26 @@ For use with `erc-keep-place-indicator-mode'." | |||
| 328 | (defvar-local erc--keep-place-indicator-overlay nil | 331 | (defvar-local erc--keep-place-indicator-overlay nil |
| 329 | "Overlay for `erc-keep-place-indicator-mode'.") | 332 | "Overlay for `erc-keep-place-indicator-mode'.") |
| 330 | 333 | ||
| 331 | (defun erc--keep-place-indicator-on-window-configuration-change () | 334 | (defun erc--keep-place-indicator-on-window-buffer-change (window) |
| 332 | "Maybe sync `erc--keep-place-indicator-overlay'. | 335 | "Maybe sync `erc--keep-place-indicator-overlay'. |
| 333 | Specifically, do so unless switching to or from another window in | 336 | Do so only when switching to a new buffer in the same window if |
| 334 | the active frame." | 337 | the replaced buffer is no longer visible in another window and |
| 335 | (when erc-keep-place-indicator-follow | 338 | its `window-start' at the time of switching is strictly greater |
| 336 | (unless (or (minibuffer-window-active-p (minibuffer-window)) | 339 | than the indicator's position." |
| 337 | (eq (window-old-buffer) (current-buffer))) | 340 | (when-let ((erc-keep-place-indicator-follow) |
| 338 | (when (< (overlay-end erc--keep-place-indicator-overlay) | 341 | ((eq window (selected-window))) |
| 339 | (window-start) | 342 | (old-buffer (window-old-buffer window)) |
| 340 | erc-insert-marker) | 343 | ((buffer-live-p old-buffer)) |
| 341 | (erc-keep-place-move (window-start)))))) | 344 | ((not (eq old-buffer (current-buffer)))) |
| 345 | (ov (buffer-local-value 'erc--keep-place-indicator-overlay | ||
| 346 | old-buffer)) | ||
| 347 | ((not (get-buffer-window old-buffer 'visible))) | ||
| 348 | (prev (assq old-buffer (window-prev-buffers window))) | ||
| 349 | (old-start (nth 1 prev)) | ||
| 350 | (old-inmkr (buffer-local-value 'erc-insert-marker old-buffer)) | ||
| 351 | ((< (overlay-end ov) old-start old-inmkr))) | ||
| 352 | (with-current-buffer old-buffer | ||
| 353 | (erc-keep-place-move old-start)))) | ||
| 342 | 354 | ||
| 343 | (defun erc--keep-place-indicator-setup () | 355 | (defun erc--keep-place-indicator-setup () |
| 344 | "Initialize buffer for maintaining `erc--keep-place-indicator-overlay'." | 356 | "Initialize buffer for maintaining `erc--keep-place-indicator-overlay'." |
| @@ -347,8 +359,8 @@ the active frame." | |||
| 347 | erc--keep-place-indicator-overlay (make-overlay 0 0)) | 359 | erc--keep-place-indicator-overlay (make-overlay 0 0)) |
| 348 | (add-hook 'erc-keep-place-mode-hook | 360 | (add-hook 'erc-keep-place-mode-hook |
| 349 | #'erc--keep-place-indicator-on-global-module nil t) | 361 | #'erc--keep-place-indicator-on-global-module nil t) |
| 350 | (add-hook 'window-configuration-change-hook | 362 | (add-hook 'window-buffer-change-functions |
| 351 | #'erc--keep-place-indicator-on-window-configuration-change nil t) | 363 | #'erc--keep-place-indicator-on-window-buffer-change 40 t) |
| 352 | (when-let* (((memq erc-keep-place-indicator-style '(t arrow))) | 364 | (when-let* (((memq erc-keep-place-indicator-style '(t arrow))) |
| 353 | (ov-property (if (zerop (fringe-columns 'left)) | 365 | (ov-property (if (zerop (fringe-columns 'left)) |
| 354 | 'after-string | 366 | 'after-string |
| @@ -368,7 +380,11 @@ the active frame." | |||
| 368 | "Buffer-local `keep-place' with fringe arrow and/or highlighted face. | 380 | "Buffer-local `keep-place' with fringe arrow and/or highlighted face. |
| 369 | Play nice with global module `keep-place' but don't depend on it. | 381 | Play nice with global module `keep-place' but don't depend on it. |
| 370 | Expect that users may want different combinations of `keep-place' | 382 | Expect that users may want different combinations of `keep-place' |
| 371 | and `keep-place-indicator' in different buffers." | 383 | and `keep-place-indicator' in different buffers. Unlike global |
| 384 | `keep-place', when `switch-to-buffer-preserve-window-point' is | ||
| 385 | enabled, don't forcibly sync point in all windows where buffer | ||
| 386 | has previously been shown because that defeats the purpose of | ||
| 387 | having a placeholder." | ||
| 372 | ((cond (erc-keep-place-mode) | 388 | ((cond (erc-keep-place-mode) |
| 373 | ((memq 'keep-place erc-modules) | 389 | ((memq 'keep-place erc-modules) |
| 374 | (erc-keep-place-mode +1)) | 390 | (erc-keep-place-mode +1)) |
| @@ -382,8 +398,8 @@ and `keep-place-indicator' in different buffers." | |||
| 382 | (erc-keep-place-indicator-mode -1))) | 398 | (erc-keep-place-indicator-mode -1))) |
| 383 | ((when erc--keep-place-indicator-overlay | 399 | ((when erc--keep-place-indicator-overlay |
| 384 | (delete-overlay erc--keep-place-indicator-overlay)) | 400 | (delete-overlay erc--keep-place-indicator-overlay)) |
| 385 | (remove-hook 'window-configuration-change-hook | 401 | (remove-hook 'window-buffer-change-functions |
| 386 | #'erc--keep-place-indicator-on-window-configuration-change t) | 402 | #'erc--keep-place-indicator-on-window-buffer-change t) |
| 387 | (remove-hook 'erc-keep-place-mode-hook | 403 | (remove-hook 'erc-keep-place-mode-hook |
| 388 | #'erc--keep-place-indicator-on-global-module t) | 404 | #'erc--keep-place-indicator-on-global-module t) |
| 389 | (remove-hook 'erc-insert-pre-hook #'erc-keep-place t) | 405 | (remove-hook 'erc-insert-pre-hook #'erc-keep-place t) |
| @@ -450,13 +466,13 @@ For use with `keep-place-indicator' module." | |||
| 450 | (forward-line -1) | 466 | (forward-line -1) |
| 451 | (when erc-keep-place-indicator-mode | 467 | (when erc-keep-place-indicator-mode |
| 452 | (unless (or (minibuffer-window-active-p (selected-window)) | 468 | (unless (or (minibuffer-window-active-p (selected-window)) |
| 453 | (and (frame-visible-p (selected-frame)) | 469 | (get-buffer-window nil 'visible)) |
| 454 | (get-buffer-window (current-buffer) (selected-frame)))) | ||
| 455 | (erc-keep-place-move nil))) | 470 | (erc-keep-place-move nil))) |
| 456 | ;; if `switch-to-buffer-preserve-window-point' is set, | 471 | ;; if `switch-to-buffer-preserve-window-point' is set, |
| 457 | ;; we cannot rely on point being saved, and must commit | 472 | ;; we cannot rely on point being saved, and must commit |
| 458 | ;; it to window-prev-buffers. | 473 | ;; it to window-prev-buffers. |
| 459 | (when switch-to-buffer-preserve-window-point | 474 | (when (and switch-to-buffer-preserve-window-point |
| 475 | (not erc-keep-place-indicator-mode)) | ||
| 460 | (dolist (frame (frame-list)) | 476 | (dolist (frame (frame-list)) |
| 461 | (walk-window-tree | 477 | (walk-window-tree |
| 462 | (lambda (window) | 478 | (lambda (window) |