The key prefix 'C-x t t' displays next command buffer in a new tab (bug#41691)
* lisp/tab-bar.el (other-tab-prefix): New command. (tab-prefix-map): Bind key 'C-x t t' to other-tab-prefix. * lisp/windmove.el (windmove-display-in-direction): Use display-buffer-override-next-command. * lisp/window.el (display-buffer-override-next-command): New function refactored from windmove-display-in-direction.
This commit is contained in:
parent
7ac79872ae
commit
788cd6d8b9
4 changed files with 97 additions and 54 deletions
4
etc/NEWS
4
etc/NEWS
|
@ -109,6 +109,10 @@ setting the variable 'auto-save-visited-mode' buffer-locally to nil.
|
|||
|
||||
* Changes in Specialized Modes and Packages in Emacs 28.1
|
||||
|
||||
** Tab Bars
|
||||
|
||||
*** The key prefix 'C-x t t' displays next command buffer in a new tab.
|
||||
|
||||
** New bindings in occur-mode, 'next-error-no-select' bound to 'n' and
|
||||
'previous-error-no-select' bound to 'p'.
|
||||
|
||||
|
|
|
@ -1575,6 +1575,25 @@ Like \\[find-file-other-frame] (which see), but creates a new tab."
|
|||
value)
|
||||
(switch-to-buffer-other-tab value))))
|
||||
|
||||
(defun other-tab-prefix ()
|
||||
"Display the buffer of the next command in a new tab.
|
||||
The next buffer is the buffer displayed by the next command invoked
|
||||
immediately after this command (ignoring reading from the minibuffer).
|
||||
Creates a new tab before displaying the buffer, or switches to the tab
|
||||
that already contains that buffer.
|
||||
When `switch-to-buffer-obey-display-actions' is non-nil,
|
||||
`switch-to-buffer' commands are also supported."
|
||||
(interactive)
|
||||
(display-buffer-override-next-command
|
||||
(lambda (buffer alist)
|
||||
(cons (progn
|
||||
(display-buffer-in-tab
|
||||
buffer (append alist '((inhibit-same-window . nil)
|
||||
(reusable-frames . t))))
|
||||
(selected-window))
|
||||
'tab)))
|
||||
(message "Display next command buffer in a new tab..."))
|
||||
|
||||
(define-key tab-prefix-map "2" 'tab-new)
|
||||
(define-key tab-prefix-map "1" 'tab-close-other)
|
||||
(define-key tab-prefix-map "0" 'tab-close)
|
||||
|
@ -1585,6 +1604,7 @@ Like \\[find-file-other-frame] (which see), but creates a new tab."
|
|||
(define-key tab-prefix-map "b" 'switch-to-buffer-other-tab)
|
||||
(define-key tab-prefix-map "f" 'find-file-other-tab)
|
||||
(define-key tab-prefix-map "\C-f" 'find-file-other-tab)
|
||||
(define-key tab-prefix-map "t" 'other-tab-prefix)
|
||||
|
||||
|
||||
(provide 'tab-bar)
|
||||
|
|
|
@ -461,60 +461,38 @@ select the window with a displayed buffer, and the meaning of
|
|||
the prefix argument is reversed.
|
||||
When `switch-to-buffer-obey-display-actions' is non-nil,
|
||||
`switch-to-buffer' commands are also supported."
|
||||
(let* ((no-select (xor (consp arg) windmove-display-no-select))
|
||||
(old-window (or (minibuffer-selected-window) (selected-window)))
|
||||
(new-window)
|
||||
(minibuffer-depth (minibuffer-depth))
|
||||
(action (lambda (buffer alist)
|
||||
(unless (> (minibuffer-depth) minibuffer-depth)
|
||||
(let* ((type 'reuse)
|
||||
(window (cond
|
||||
((eq dir 'new-tab)
|
||||
(let ((tab-bar-new-tab-choice t))
|
||||
(tab-bar-new-tab))
|
||||
(setq type 'tab)
|
||||
(selected-window))
|
||||
((eq dir 'new-frame)
|
||||
(let* ((params (cdr (assq 'pop-up-frame-parameters alist)))
|
||||
(pop-up-frame-alist (append params pop-up-frame-alist))
|
||||
(frame (make-frame-on-current-monitor
|
||||
pop-up-frame-alist)))
|
||||
(unless (cdr (assq 'inhibit-switch-frame alist))
|
||||
(window--maybe-raise-frame frame))
|
||||
(setq type 'frame)
|
||||
(frame-selected-window frame)))
|
||||
((eq dir 'same-window)
|
||||
(selected-window))
|
||||
(t (window-in-direction
|
||||
dir nil nil
|
||||
(and arg (prefix-numeric-value arg))
|
||||
windmove-wrap-around)))))
|
||||
(unless window
|
||||
(setq window (split-window nil nil dir) type 'window))
|
||||
(setq new-window (window--display-buffer buffer window
|
||||
type alist))))))
|
||||
(command this-command)
|
||||
(clearfun (make-symbol "clear-display-buffer-overriding-action"))
|
||||
(exitfun
|
||||
(lambda ()
|
||||
(setq display-buffer-overriding-action
|
||||
(delq action display-buffer-overriding-action))
|
||||
(when (window-live-p (if no-select old-window new-window))
|
||||
(select-window (if no-select old-window new-window)))
|
||||
(remove-hook 'post-command-hook clearfun))))
|
||||
(fset clearfun
|
||||
(lambda ()
|
||||
(unless (or
|
||||
;; Remove the hook immediately
|
||||
;; after exiting the minibuffer.
|
||||
(> (minibuffer-depth) minibuffer-depth)
|
||||
;; But don't remove immediately after
|
||||
;; adding the hook by the same command below.
|
||||
(eq this-command command))
|
||||
(funcall exitfun))))
|
||||
(add-hook 'post-command-hook clearfun)
|
||||
(push action display-buffer-overriding-action)
|
||||
(message "[display-%s]" dir)))
|
||||
(let ((no-select (xor (consp arg) windmove-display-no-select)))
|
||||
(display-buffer-override-next-command
|
||||
(lambda (_buffer alist)
|
||||
(let* ((type 'reuse)
|
||||
(window (cond
|
||||
((eq dir 'new-tab)
|
||||
(let ((tab-bar-new-tab-choice t))
|
||||
(tab-bar-new-tab))
|
||||
(setq type 'tab)
|
||||
(selected-window))
|
||||
((eq dir 'new-frame)
|
||||
(let* ((params (cdr (assq 'pop-up-frame-parameters alist)))
|
||||
(pop-up-frame-alist (append params pop-up-frame-alist))
|
||||
(frame (make-frame-on-current-monitor
|
||||
pop-up-frame-alist)))
|
||||
(unless (cdr (assq 'inhibit-switch-frame alist))
|
||||
(window--maybe-raise-frame frame))
|
||||
(setq type 'frame)
|
||||
(frame-selected-window frame)))
|
||||
((eq dir 'same-window)
|
||||
(selected-window))
|
||||
(t (window-in-direction
|
||||
dir nil nil
|
||||
(and arg (prefix-numeric-value arg))
|
||||
windmove-wrap-around)))))
|
||||
(unless window
|
||||
(setq window (split-window nil nil dir) type 'window))
|
||||
(cons window type)))
|
||||
(lambda (old-window new-window)
|
||||
(when (window-live-p (if no-select old-window new-window))
|
||||
(select-window (if no-select old-window new-window))))))
|
||||
(message "[display-%s]" dir))
|
||||
|
||||
;;;###autoload
|
||||
(defun windmove-display-left (&optional arg)
|
||||
|
|
|
@ -8578,6 +8578,47 @@ documentation for additional customization information."
|
|||
(interactive
|
||||
(list (read-buffer-to-switch "Switch to buffer in other frame: ")))
|
||||
(pop-to-buffer buffer-or-name display-buffer--other-frame-action norecord))
|
||||
|
||||
(defun display-buffer-override-next-command (pre-function &optional post-function)
|
||||
"Set `display-buffer-overriding-action' for the next command.
|
||||
`pre-function' is called to prepare the window where the buffer should be
|
||||
displayed. This function takes two arguments `buffer' and `alist', and
|
||||
should return a cons with the displayed window and its type. See the
|
||||
meaning of these values in `window--display-buffer'.
|
||||
Optional `post-function' is called after the buffer is displayed in the
|
||||
window; the function takes two arguments: an old and new window."
|
||||
(let* ((old-window (or (minibuffer-selected-window) (selected-window)))
|
||||
(new-window nil)
|
||||
(minibuffer-depth (minibuffer-depth))
|
||||
(action (lambda (buffer alist)
|
||||
(unless (> (minibuffer-depth) minibuffer-depth)
|
||||
(let* ((ret (funcall pre-function buffer alist))
|
||||
(window (car ret))
|
||||
(type (cdr ret)))
|
||||
(setq new-window (window--display-buffer buffer window
|
||||
type alist))))))
|
||||
(command this-command)
|
||||
(clearfun (make-symbol "clear-display-buffer-overriding-action"))
|
||||
(exitfun
|
||||
(lambda ()
|
||||
(setq display-buffer-overriding-action
|
||||
(delq action display-buffer-overriding-action))
|
||||
(remove-hook 'post-command-hook clearfun)
|
||||
(when (functionp post-function)
|
||||
(funcall post-function old-window new-window)))))
|
||||
(fset clearfun
|
||||
(lambda ()
|
||||
(unless (or
|
||||
;; Remove the hook immediately
|
||||
;; after exiting the minibuffer.
|
||||
(> (minibuffer-depth) minibuffer-depth)
|
||||
;; But don't remove immediately after
|
||||
;; adding the hook by the same command below.
|
||||
(eq this-command command))
|
||||
(funcall exitfun))))
|
||||
(add-hook 'post-command-hook clearfun)
|
||||
(push action display-buffer-overriding-action)))
|
||||
|
||||
|
||||
(defun set-window-text-height (window height)
|
||||
"Set the height in lines of the text display area of WINDOW to HEIGHT.
|
||||
|
|
Loading…
Add table
Reference in a new issue