diff options
Diffstat (limited to 'lisp/window.el')
| -rw-r--r-- | lisp/window.el | 396 |
1 files changed, 240 insertions, 156 deletions
diff --git a/lisp/window.el b/lisp/window.el index 87817fb8773..811b1781b4c 100644 --- a/lisp/window.el +++ b/lisp/window.el | |||
| @@ -84,7 +84,7 @@ This hook is run by `with-temp-buffer-window' with the buffer | |||
| 84 | displayed and current and its window selected.") | 84 | displayed and current and its window selected.") |
| 85 | 85 | ||
| 86 | (defun temp-buffer-window-setup (buffer-or-name) | 86 | (defun temp-buffer-window-setup (buffer-or-name) |
| 87 | "Set up temporary buffer specified by BUFFER-OR-NAME | 87 | "Set up temporary buffer specified by BUFFER-OR-NAME. |
| 88 | Return the buffer." | 88 | Return the buffer." |
| 89 | (let ((old-dir default-directory) | 89 | (let ((old-dir default-directory) |
| 90 | (buffer (get-buffer-create buffer-or-name))) | 90 | (buffer (get-buffer-create buffer-or-name))) |
| @@ -508,7 +508,7 @@ failed." | |||
| 508 | (window-make-atom (window-parent window)) | 508 | (window-make-atom (window-parent window)) |
| 509 | ;; Display BUFFER in NEW and return NEW. | 509 | ;; Display BUFFER in NEW and return NEW. |
| 510 | (window--display-buffer | 510 | (window--display-buffer |
| 511 | buffer new 'window display-buffer-mark-dedicated)))) | 511 | buffer new 'window alist display-buffer-mark-dedicated)))) |
| 512 | 512 | ||
| 513 | (defun window--atom-check-1 (window) | 513 | (defun window--atom-check-1 (window) |
| 514 | "Subroutine of `window--atom-check'." | 514 | "Subroutine of `window--atom-check'." |
| @@ -677,12 +677,6 @@ The new window automatically becomes the \"major\" side window on | |||
| 677 | SIDE. Return the new window, nil if its creation window failed." | 677 | SIDE. Return the new window, nil if its creation window failed." |
| 678 | (let* ((root (frame-root-window)) | 678 | (let* ((root (frame-root-window)) |
| 679 | (left-or-right (memq side '(left right))) | 679 | (left-or-right (memq side '(left right))) |
| 680 | (size (or (assq 'size alist) | ||
| 681 | (/ (window-total-size (frame-root-window) left-or-right) | ||
| 682 | ;; By default use a fourth of the size of the | ||
| 683 | ;; frame's root window. This has to be made | ||
| 684 | ;; customizable via ALIST. | ||
| 685 | 4))) | ||
| 686 | (major (window--major-side-window side)) | 680 | (major (window--major-side-window side)) |
| 687 | (selected-window (selected-window)) | 681 | (selected-window (selected-window)) |
| 688 | (on-side (cond | 682 | (on-side (cond |
| @@ -694,7 +688,7 @@ SIDE. Return the new window, nil if its creation window failed." | |||
| 694 | ;; parent window unless needed. | 688 | ;; parent window unless needed. |
| 695 | (window-combination-resize 'side) | 689 | (window-combination-resize 'side) |
| 696 | (window-combination-limit nil) | 690 | (window-combination-limit nil) |
| 697 | (new (split-window major (- size) on-side)) | 691 | (new (split-window major nil on-side)) |
| 698 | fun) | 692 | fun) |
| 699 | (when new | 693 | (when new |
| 700 | ;; Initialize `window-side' parameter of new window to SIDE. | 694 | ;; Initialize `window-side' parameter of new window to SIDE. |
| @@ -705,8 +699,22 @@ SIDE. Return the new window, nil if its creation window failed." | |||
| 705 | ;; the new window is deleted, a side window on the opposite side | 699 | ;; the new window is deleted, a side window on the opposite side |
| 706 | ;; does not get resized. | 700 | ;; does not get resized. |
| 707 | (set-window-parameter new 'delete-window 'delete-side-window) | 701 | (set-window-parameter new 'delete-window 'delete-side-window) |
| 702 | ;; Auto-adjust height/width of new window unless a size has been | ||
| 703 | ;; explicitly requested. | ||
| 704 | (unless (if left-or-right | ||
| 705 | (cdr (assq 'window-width alist)) | ||
| 706 | (cdr (assq 'window-height alist))) | ||
| 707 | (setq alist | ||
| 708 | (cons | ||
| 709 | (cons | ||
| 710 | (if left-or-right 'window-width 'window-height) | ||
| 711 | (/ (window-total-size (frame-root-window) left-or-right) | ||
| 712 | ;; By default use a fourth of the size of the | ||
| 713 | ;; frame's root window. | ||
| 714 | 4)) | ||
| 715 | alist))) | ||
| 708 | ;; Install BUFFER in new window and return NEW. | 716 | ;; Install BUFFER in new window and return NEW. |
| 709 | (window--display-buffer buffer new 'window 'side)))) | 717 | (window--display-buffer buffer new 'window alist 'side)))) |
| 710 | 718 | ||
| 711 | (defun delete-side-window (window) | 719 | (defun delete-side-window (window) |
| 712 | "Delete side window WINDOW." | 720 | "Delete side window WINDOW." |
| @@ -814,7 +822,7 @@ following symbols can be used: | |||
| 814 | ;; ALIST (or, better, avoided in the "other" functions). | 822 | ;; ALIST (or, better, avoided in the "other" functions). |
| 815 | (or (and this-window | 823 | (or (and this-window |
| 816 | ;; Reuse `this-window'. | 824 | ;; Reuse `this-window'. |
| 817 | (window--display-buffer buffer this-window 'reuse 'side)) | 825 | (window--display-buffer buffer this-window 'reuse alist 'side)) |
| 818 | (and (or (not max-slots) (< slots max-slots)) | 826 | (and (or (not max-slots) (< slots max-slots)) |
| 819 | (or (and next-window | 827 | (or (and next-window |
| 820 | ;; Make new window before `next-window'. | 828 | ;; Make new window before `next-window'. |
| @@ -839,13 +847,14 @@ following symbols can be used: | |||
| 839 | window 'delete-window 'delete-side-window) | 847 | window 'delete-window 'delete-side-window) |
| 840 | window))) | 848 | window))) |
| 841 | (set-window-parameter window 'window-slot slot) | 849 | (set-window-parameter window 'window-slot slot) |
| 842 | (window--display-buffer buffer window 'window 'side)) | 850 | (window--display-buffer buffer window 'window alist 'side)) |
| 843 | (and best-window | 851 | (and best-window |
| 844 | ;; Reuse `best-window'. | 852 | ;; Reuse `best-window'. |
| 845 | (progn | 853 | (progn |
| 846 | ;; Give best-window the new slot value. | 854 | ;; Give best-window the new slot value. |
| 847 | (set-window-parameter best-window 'window-slot slot) | 855 | (set-window-parameter best-window 'window-slot slot) |
| 848 | (window--display-buffer buffer best-window 'reuse 'side))))))))) | 856 | (window--display-buffer |
| 857 | buffer best-window 'reuse alist 'side))))))))) | ||
| 849 | 858 | ||
| 850 | (defun window--side-check (&optional frame) | 859 | (defun window--side-check (&optional frame) |
| 851 | "Check the side window configuration of FRAME. | 860 | "Check the side window configuration of FRAME. |
| @@ -903,7 +912,7 @@ of all windows on FRAME to nil." | |||
| 903 | (if right (throw 'reset t) (setq right t))) | 912 | (if right (throw 'reset t) (setq right t))) |
| 904 | ((eq side 'bottom) | 913 | ((eq side 'bottom) |
| 905 | (if bottom (throw 'reset t) (setq bottom t))) | 914 | (if bottom (throw 'reset t) (setq bottom t))) |
| 906 | (t | 915 | (t |
| 907 | (throw 'reset t)))) | 916 | (throw 'reset t)))) |
| 908 | frame t)) | 917 | frame t)) |
| 909 | ;; If there's a side window, there must be at least one | 918 | ;; If there's a side window, there must be at least one |
| @@ -2079,9 +2088,9 @@ preferably only resize windows adjacent to EDGE. | |||
| 2079 | Return the symbol `normalized' if new normal sizes have been | 2088 | Return the symbol `normalized' if new normal sizes have been |
| 2080 | already set by this routine." | 2089 | already set by this routine." |
| 2081 | (let* ((first (window-child parent)) | 2090 | (let* ((first (window-child parent)) |
| 2082 | (sub first) | 2091 | (last (window-last-child parent)) |
| 2083 | (parent-total (+ (window-total-size parent horizontal) delta)) | 2092 | (parent-total (+ (window-total-size parent horizontal) delta)) |
| 2084 | best-window best-value) | 2093 | sub best-window best-value) |
| 2085 | 2094 | ||
| 2086 | (if (and edge (memq trail '(before after)) | 2095 | (if (and edge (memq trail '(before after)) |
| 2087 | (progn | 2096 | (progn |
| @@ -2125,7 +2134,7 @@ already set by this routine." | |||
| 2125 | ;; normal sizes have been already set. | 2134 | ;; normal sizes have been already set. |
| 2126 | 'normalized) | 2135 | 'normalized) |
| 2127 | ;; Resize all windows proportionally. | 2136 | ;; Resize all windows proportionally. |
| 2128 | (setq sub first) | 2137 | (setq sub last) |
| 2129 | (while sub | 2138 | (while sub |
| 2130 | (cond | 2139 | (cond |
| 2131 | ((or (window--resize-child-windows-skip-p sub) | 2140 | ((or (window--resize-child-windows-skip-p sub) |
| @@ -2154,14 +2163,14 @@ already set by this routine." | |||
| 2154 | parent-total) | 2163 | parent-total) |
| 2155 | (window-normal-size sub horizontal))))) | 2164 | (window-normal-size sub horizontal))))) |
| 2156 | 2165 | ||
| 2157 | (setq sub (window-right sub))) | 2166 | (setq sub (window-left sub))) |
| 2158 | 2167 | ||
| 2159 | (cond | 2168 | (cond |
| 2160 | ((< delta 0) | 2169 | ((< delta 0) |
| 2161 | ;; Shrink windows by delta. | 2170 | ;; Shrink windows by delta. |
| 2162 | (setq best-window t) | 2171 | (setq best-window t) |
| 2163 | (while (and best-window (not (zerop delta))) | 2172 | (while (and best-window (not (zerop delta))) |
| 2164 | (setq sub first) | 2173 | (setq sub last) |
| 2165 | (setq best-window nil) | 2174 | (setq best-window nil) |
| 2166 | (setq best-value most-negative-fixnum) | 2175 | (setq best-value most-negative-fixnum) |
| 2167 | (while sub | 2176 | (while sub |
| @@ -2171,7 +2180,7 @@ already set by this routine." | |||
| 2171 | (setq best-window sub) | 2180 | (setq best-window sub) |
| 2172 | (setq best-value (cdr (window-new-normal sub)))) | 2181 | (setq best-value (cdr (window-new-normal sub)))) |
| 2173 | 2182 | ||
| 2174 | (setq sub (window-right sub))) | 2183 | (setq sub (window-left sub))) |
| 2175 | 2184 | ||
| 2176 | (when best-window | 2185 | (when best-window |
| 2177 | (setq delta (1+ delta))) | 2186 | (setq delta (1+ delta))) |
| @@ -2188,7 +2197,7 @@ already set by this routine." | |||
| 2188 | ;; Enlarge windows by delta. | 2197 | ;; Enlarge windows by delta. |
| 2189 | (setq best-window t) | 2198 | (setq best-window t) |
| 2190 | (while (and best-window (not (zerop delta))) | 2199 | (while (and best-window (not (zerop delta))) |
| 2191 | (setq sub first) | 2200 | (setq sub last) |
| 2192 | (setq best-window nil) | 2201 | (setq best-window nil) |
| 2193 | (setq best-value most-positive-fixnum) | 2202 | (setq best-value most-positive-fixnum) |
| 2194 | (while sub | 2203 | (while sub |
| @@ -2197,7 +2206,7 @@ already set by this routine." | |||
| 2197 | (setq best-window sub) | 2206 | (setq best-window sub) |
| 2198 | (setq best-value (window-new-normal sub))) | 2207 | (setq best-value (window-new-normal sub))) |
| 2199 | 2208 | ||
| 2200 | (setq sub (window-right sub))) | 2209 | (setq sub (window-left sub))) |
| 2201 | 2210 | ||
| 2202 | (when best-window | 2211 | (when best-window |
| 2203 | (setq delta (1- delta))) | 2212 | (setq delta (1- delta))) |
| @@ -2209,7 +2218,7 @@ already set by this routine." | |||
| 2209 | (window-normal-size best-window horizontal)))))) | 2218 | (window-normal-size best-window horizontal)))))) |
| 2210 | 2219 | ||
| 2211 | (when best-window | 2220 | (when best-window |
| 2212 | (setq sub first) | 2221 | (setq sub last) |
| 2213 | (while sub | 2222 | (while sub |
| 2214 | (when (or (consp (window-new-normal sub)) | 2223 | (when (or (consp (window-new-normal sub)) |
| 2215 | (numberp (window-new-normal sub))) | 2224 | (numberp (window-new-normal sub))) |
| @@ -2227,7 +2236,7 @@ already set by this routine." | |||
| 2227 | ;; recursively even if it's size does not change. | 2236 | ;; recursively even if it's size does not change. |
| 2228 | (window--resize-this-window | 2237 | (window--resize-this-window |
| 2229 | sub delta horizontal ignore nil trail edge)))) | 2238 | sub delta horizontal ignore nil trail edge)))) |
| 2230 | (setq sub (window-right sub))))))) | 2239 | (setq sub (window-left sub))))))) |
| 2231 | 2240 | ||
| 2232 | (defun window--resize-siblings (window delta &optional horizontal ignore trail edge) | 2241 | (defun window--resize-siblings (window delta &optional horizontal ignore trail edge) |
| 2233 | "Resize other windows when WINDOW is resized vertically by DELTA lines. | 2242 | "Resize other windows when WINDOW is resized vertically by DELTA lines. |
| @@ -2406,27 +2415,33 @@ Return the number of lines that were recovered. | |||
| 2406 | This function is only called by the minibuffer window resizing | 2415 | This function is only called by the minibuffer window resizing |
| 2407 | routines. It resizes windows proportionally and never deletes | 2416 | routines. It resizes windows proportionally and never deletes |
| 2408 | any windows." | 2417 | any windows." |
| 2409 | (when (numberp delta) | 2418 | (let ((frame (window-frame window)) |
| 2410 | (let (ignore) | 2419 | ignore) |
| 2411 | (cond | 2420 | (cond |
| 2412 | ((< delta 0) | 2421 | ((not (numberp delta)) |
| 2413 | (setq delta (window-sizable window delta))) | 2422 | (setq delta 0)) |
| 2414 | ((> delta 0) | 2423 | ((zerop delta)) |
| 2415 | (unless (window-sizable window delta) | 2424 | ((< delta 0) |
| 2416 | (setq ignore t)))) | 2425 | (setq delta (window-sizable window delta)) |
| 2417 | 2426 | (window--resize-reset frame) | |
| 2418 | (window--resize-reset (window-frame window)) | 2427 | ;; When shrinking the root window, emulate an edge drag in order |
| 2419 | ;; Ideally, we would resize just the last window in a combination | 2428 | ;; to not resize other windows if we can avoid it (Bug#12419). |
| 2420 | ;; but that's not feasible for the following reason: If we grow | 2429 | (window--resize-this-window |
| 2421 | ;; the minibuffer window and the last window cannot be shrunk any | 2430 | window delta nil ignore t 'before |
| 2422 | ;; more, we shrink another window instead. But if we then shrink | 2431 | (+ (window-top-line window) (window-total-size window))) |
| 2423 | ;; the minibuffer window again, the last window might get enlarged | 2432 | ;; Don't record new normal sizes to make sure that shrinking back |
| 2424 | ;; and the state after shrinking is not the state before growing. | 2433 | ;; proportionally works as intended. |
| 2425 | ;; So, in practice, we'd need a history variable to record how to | 2434 | (walk-window-tree |
| 2426 | ;; proceed. But I'm not sure how such a variable could work with | 2435 | (lambda (window) (set-window-new-normal window 'ignore)) frame t)) |
| 2427 | ;; repeated minibuffer window growing steps. | 2436 | ((> delta 0) |
| 2428 | (window--resize-this-window window delta nil ignore t) | 2437 | (window--resize-reset frame) |
| 2429 | delta))) | 2438 | (unless (window-sizable window delta) |
| 2439 | (setq ignore t)) | ||
| 2440 | ;; When growing the root window, resize proportionally. This | ||
| 2441 | ;; should give windows back their original sizes (hopefully). | ||
| 2442 | (window--resize-this-window window delta nil ignore t))) | ||
| 2443 | ;; Return the possibly adjusted DELTA. | ||
| 2444 | delta)) | ||
| 2430 | 2445 | ||
| 2431 | (defun adjust-window-trailing-edge (window delta &optional horizontal) | 2446 | (defun adjust-window-trailing-edge (window delta &optional horizontal) |
| 2432 | "Move WINDOW's bottom edge by DELTA lines. | 2447 | "Move WINDOW's bottom edge by DELTA lines. |
| @@ -5071,7 +5086,7 @@ split." | |||
| 5071 | (with-selected-window window | 5086 | (with-selected-window window |
| 5072 | (split-window-below)))))))) | 5087 | (split-window-below)))))))) |
| 5073 | 5088 | ||
| 5074 | (defun window--try-to-split-window (window) | 5089 | (defun window--try-to-split-window (window &optional alist) |
| 5075 | "Try to split WINDOW. | 5090 | "Try to split WINDOW. |
| 5076 | Return value returned by `split-window-preferred-function' if it | 5091 | Return value returned by `split-window-preferred-function' if it |
| 5077 | represents a live window, nil otherwise." | 5092 | represents a live window, nil otherwise." |
| @@ -5079,9 +5094,14 @@ represents a live window, nil otherwise." | |||
| 5079 | (not (frame-parameter (window-frame window) 'unsplittable)) | 5094 | (not (frame-parameter (window-frame window) 'unsplittable)) |
| 5080 | (let* ((window-combination-limit | 5095 | (let* ((window-combination-limit |
| 5081 | ;; When `window-combination-limit' equals | 5096 | ;; When `window-combination-limit' equals |
| 5082 | ;; `display-buffer' bind it to t so resizing steals | 5097 | ;; `display-buffer' or equals `resize-window' and a |
| 5083 | ;; space preferably from the window that was split. | 5098 | ;; `window-height' or `window-width' alist entry are |
| 5084 | (if (eq window-combination-limit 'display-buffer) | 5099 | ;; present, bind it to t so resizing steals space |
| 5100 | ;; preferably from the window that was split. | ||
| 5101 | (if (or (eq window-combination-limit 'display-buffer) | ||
| 5102 | (and (eq window-combination-limit 'window-size) | ||
| 5103 | (or (cdr (assq 'window-height alist)) | ||
| 5104 | (cdr (assq 'window-width alist))))) | ||
| 5085 | t | 5105 | t |
| 5086 | window-combination-limit)) | 5106 | window-combination-limit)) |
| 5087 | (new-window | 5107 | (new-window |
| @@ -5138,7 +5158,7 @@ is higher than WINDOW." | |||
| 5138 | (/ (- (window-total-height window) (window-total-height)) 2)) | 5158 | (/ (- (window-total-height window) (window-total-height)) 2)) |
| 5139 | (error nil)))) | 5159 | (error nil)))) |
| 5140 | 5160 | ||
| 5141 | (defun window--display-buffer (buffer window type &optional dedicated) | 5161 | (defun window--display-buffer (buffer window type &optional alist dedicated) |
| 5142 | "Display BUFFER in WINDOW and make its frame visible. | 5162 | "Display BUFFER in WINDOW and make its frame visible. |
| 5143 | TYPE must be one of the symbols `reuse', `window' or `frame' and | 5163 | TYPE must be one of the symbols `reuse', `window' or `frame' and |
| 5144 | is passed unaltered to `display-buffer-record-window'. Set | 5164 | is passed unaltered to `display-buffer-record-window'. Set |
| @@ -5153,6 +5173,58 @@ BUFFER and WINDOW are live." | |||
| 5153 | (set-window-dedicated-p window dedicated)) | 5173 | (set-window-dedicated-p window dedicated)) |
| 5154 | (when (memq type '(window frame)) | 5174 | (when (memq type '(window frame)) |
| 5155 | (set-window-prev-buffers window nil))) | 5175 | (set-window-prev-buffers window nil))) |
| 5176 | (let ((parameter (window-parameter window 'quit-restore)) | ||
| 5177 | (height (cdr (assq 'window-height alist))) | ||
| 5178 | (width (cdr (assq 'window-width alist)))) | ||
| 5179 | (when (or (memq type '(window frame)) | ||
| 5180 | (and (eq (car parameter) 'same) | ||
| 5181 | (memq (nth 1 parameter) '(window frame)))) | ||
| 5182 | ;; Adjust height of new window or frame. | ||
| 5183 | (cond | ||
| 5184 | ((not height)) | ||
| 5185 | ((numberp height) | ||
| 5186 | (let* ((new-height | ||
| 5187 | (if (integerp height) | ||
| 5188 | height | ||
| 5189 | (round | ||
| 5190 | (* (window-total-size (frame-root-window window)) | ||
| 5191 | height)))) | ||
| 5192 | (delta (- new-height (window-total-size window)))) | ||
| 5193 | (cond | ||
| 5194 | ((and (window--resizable-p window delta nil 'safe) | ||
| 5195 | (window-combined-p window)) | ||
| 5196 | (window-resize window delta nil 'safe)) | ||
| 5197 | ((or (eq type 'frame) | ||
| 5198 | (and (eq (car parameter) 'same) | ||
| 5199 | (eq (nth 1 parameter) 'frame))) | ||
| 5200 | (set-frame-height | ||
| 5201 | (window-frame window) | ||
| 5202 | (+ (frame-height (window-frame window)) delta)))))) | ||
| 5203 | ((functionp height) | ||
| 5204 | (ignore-errors (funcall height window)))) | ||
| 5205 | ;; Adjust width of a window or frame. | ||
| 5206 | (cond | ||
| 5207 | ((not width)) | ||
| 5208 | ((numberp width) | ||
| 5209 | (let* ((new-width | ||
| 5210 | (if (integerp width) | ||
| 5211 | width | ||
| 5212 | (round | ||
| 5213 | (* (window-total-size (frame-root-window window) t) | ||
| 5214 | width)))) | ||
| 5215 | (delta (- new-width (window-total-size window t)))) | ||
| 5216 | (cond | ||
| 5217 | ((and (window--resizable-p window delta t 'safe) | ||
| 5218 | (window-combined-p window t)) | ||
| 5219 | (window-resize window delta t 'safe)) | ||
| 5220 | ((or (eq type 'frame) | ||
| 5221 | (and (eq (car parameter) 'same) | ||
| 5222 | (eq (nth 1 parameter) 'frame))) | ||
| 5223 | (set-frame-width | ||
| 5224 | (window-frame window) | ||
| 5225 | (+ (frame-width (window-frame window)) delta)))))) | ||
| 5226 | ((functionp width) | ||
| 5227 | (ignore-errors (funcall width window)))))) | ||
| 5156 | window)) | 5228 | window)) |
| 5157 | 5229 | ||
| 5158 | (defun window--maybe-raise-frame (frame) | 5230 | (defun window--maybe-raise-frame (frame) |
| @@ -5394,7 +5466,7 @@ selected window." | |||
| 5394 | (unless (or (cdr (assq 'inhibit-same-window alist)) | 5466 | (unless (or (cdr (assq 'inhibit-same-window alist)) |
| 5395 | (window-minibuffer-p) | 5467 | (window-minibuffer-p) |
| 5396 | (window-dedicated-p)) | 5468 | (window-dedicated-p)) |
| 5397 | (window--display-buffer buffer (selected-window) 'reuse))) | 5469 | (window--display-buffer buffer (selected-window) 'reuse alist))) |
| 5398 | 5470 | ||
| 5399 | (defun display-buffer--maybe-same-window (buffer alist) | 5471 | (defun display-buffer--maybe-same-window (buffer alist) |
| 5400 | "Conditionally display BUFFER in the selected window. | 5472 | "Conditionally display BUFFER in the selected window. |
| @@ -5442,7 +5514,7 @@ that frame." | |||
| 5442 | (get-buffer-window-list buffer 'nomini | 5514 | (get-buffer-window-list buffer 'nomini |
| 5443 | frames)))))) | 5515 | frames)))))) |
| 5444 | (when (window-live-p window) | 5516 | (when (window-live-p window) |
| 5445 | (prog1 (window--display-buffer buffer window 'reuse) | 5517 | (prog1 (window--display-buffer buffer window 'reuse alist) |
| 5446 | (unless (cdr (assq 'inhibit-switch-frame alist)) | 5518 | (unless (cdr (assq 'inhibit-switch-frame alist)) |
| 5447 | (window--maybe-raise-frame (window-frame window))))))) | 5519 | (window--maybe-raise-frame (window-frame window))))))) |
| 5448 | 5520 | ||
| @@ -5479,8 +5551,8 @@ new frame." | |||
| 5479 | (when (and fun | 5551 | (when (and fun |
| 5480 | (setq frame (funcall fun)) | 5552 | (setq frame (funcall fun)) |
| 5481 | (setq window (frame-selected-window frame))) | 5553 | (setq window (frame-selected-window frame))) |
| 5482 | (prog1 (window--display-buffer buffer window | 5554 | (prog1 (window--display-buffer |
| 5483 | 'frame display-buffer-mark-dedicated) | 5555 | buffer window 'frame alist display-buffer-mark-dedicated) |
| 5484 | (unless (cdr (assq 'inhibit-switch-frame alist)) | 5556 | (unless (cdr (assq 'inhibit-switch-frame alist)) |
| 5485 | (window--maybe-raise-frame frame)))))) | 5557 | (window--maybe-raise-frame frame)))))) |
| 5486 | 5558 | ||
| @@ -5505,11 +5577,11 @@ raising the frame." | |||
| 5505 | (not (frame-parameter frame 'unsplittable)))) | 5577 | (not (frame-parameter frame 'unsplittable)))) |
| 5506 | ;; Attempt to split largest or least recently used window. | 5578 | ;; Attempt to split largest or least recently used window. |
| 5507 | (setq window (or (window--try-to-split-window | 5579 | (setq window (or (window--try-to-split-window |
| 5508 | (get-largest-window frame t)) | 5580 | (get-largest-window frame t) alist) |
| 5509 | (window--try-to-split-window | 5581 | (window--try-to-split-window |
| 5510 | (get-lru-window frame t))))) | 5582 | (get-lru-window frame t) alist)))) |
| 5511 | (prog1 (window--display-buffer buffer window | 5583 | (prog1 (window--display-buffer |
| 5512 | 'window display-buffer-mark-dedicated) | 5584 | buffer window 'window alist display-buffer-mark-dedicated) |
| 5513 | (unless (cdr (assq 'inhibit-switch-frame alist)) | 5585 | (unless (cdr (assq 'inhibit-switch-frame alist)) |
| 5514 | (window--maybe-raise-frame (window-frame window))))))) | 5586 | (window--maybe-raise-frame (window-frame window))))))) |
| 5515 | 5587 | ||
| @@ -5528,21 +5600,21 @@ again with `display-buffer-pop-up-window'." | |||
| 5528 | (and pop-up-windows | 5600 | (and pop-up-windows |
| 5529 | (display-buffer-pop-up-window buffer alist)))) | 5601 | (display-buffer-pop-up-window buffer alist)))) |
| 5530 | 5602 | ||
| 5531 | (defun display-buffer-below-selected (buffer _alist) | 5603 | (defun display-buffer-below-selected (buffer alist) |
| 5532 | "Try displaying BUFFER in a window below the selected window. | 5604 | "Try displaying BUFFER in a window below the selected window. |
| 5533 | This either splits the selected window or reuses the window below | 5605 | This either splits the selected window or reuses the window below |
| 5534 | the selected one." | 5606 | the selected one." |
| 5535 | (let (window) | 5607 | (let (window) |
| 5536 | (or (and (not (frame-parameter nil 'unsplittable)) | 5608 | (or (and (not (frame-parameter nil 'unsplittable)) |
| 5537 | (setq window (window--try-to-split-window (selected-window))) | 5609 | (setq window (window--try-to-split-window (selected-window) alist)) |
| 5538 | (window--display-buffer | 5610 | (window--display-buffer |
| 5539 | buffer window 'window display-buffer-mark-dedicated)) | 5611 | buffer window 'window alist display-buffer-mark-dedicated)) |
| 5540 | (and (setq window (window-in-direction 'below)) | 5612 | (and (setq window (window-in-direction 'below)) |
| 5541 | (not (window-dedicated-p window)) | 5613 | (not (window-dedicated-p window)) |
| 5542 | (window--display-buffer | 5614 | (window--display-buffer |
| 5543 | buffer window 'reuse display-buffer-mark-dedicated))))) | 5615 | buffer window 'reuse alist display-buffer-mark-dedicated))))) |
| 5544 | 5616 | ||
| 5545 | (defun display-buffer-at-bottom (buffer _alist) | 5617 | (defun display-buffer-at-bottom (buffer alist) |
| 5546 | "Try displaying BUFFER in a window at the botom of the selected frame. | 5618 | "Try displaying BUFFER in a window at the botom of the selected frame. |
| 5547 | This either splits the window at the bottom of the frame or the | 5619 | This either splits the window at the bottom of the frame or the |
| 5548 | frame's root window, or reuses an existing window at the bottom | 5620 | frame's root window, or reuses an existing window at the bottom |
| @@ -5550,20 +5622,20 @@ of the selected frame." | |||
| 5550 | (let (bottom-window window) | 5622 | (let (bottom-window window) |
| 5551 | (walk-window-tree (lambda (window) (setq bottom-window window))) | 5623 | (walk-window-tree (lambda (window) (setq bottom-window window))) |
| 5552 | (or (and (not (frame-parameter nil 'unsplittable)) | 5624 | (or (and (not (frame-parameter nil 'unsplittable)) |
| 5553 | (setq window (window--try-to-split-window bottom-window)) | 5625 | (setq window (window--try-to-split-window bottom-window alist)) |
| 5554 | (window--display-buffer | 5626 | (window--display-buffer |
| 5555 | buffer window 'window display-buffer-mark-dedicated)) | 5627 | buffer window 'window alist display-buffer-mark-dedicated)) |
| 5556 | (and (not (frame-parameter nil 'unsplittable)) | 5628 | (and (not (frame-parameter nil 'unsplittable)) |
| 5557 | (setq window | 5629 | (setq window |
| 5558 | (condition-case nil | 5630 | (condition-case nil |
| 5559 | (split-window (frame-root-window)) | 5631 | (split-window (frame-root-window)) |
| 5560 | (error nil))) | 5632 | (error nil))) |
| 5561 | (window--display-buffer | 5633 | (window--display-buffer |
| 5562 | buffer window 'window display-buffer-mark-dedicated)) | 5634 | buffer window 'window alist display-buffer-mark-dedicated)) |
| 5563 | (and (setq window bottom-window) | 5635 | (and (setq window bottom-window) |
| 5564 | (not (window-dedicated-p window)) | 5636 | (not (window-dedicated-p window)) |
| 5565 | (window--display-buffer | 5637 | (window--display-buffer |
| 5566 | buffer window 'reuse display-buffer-mark-dedicated))))) | 5638 | buffer window 'reuse alist display-buffer-mark-dedicated))))) |
| 5567 | 5639 | ||
| 5568 | (defun display-buffer-in-previous-window (buffer alist) | 5640 | (defun display-buffer-in-previous-window (buffer alist) |
| 5569 | "Display BUFFER in a window previously showing it. | 5641 | "Display BUFFER in a window previously showing it. |
| @@ -5619,7 +5691,7 @@ above, even if that window never showed BUFFER before." | |||
| 5619 | (setq best-window window))) | 5691 | (setq best-window window))) |
| 5620 | ;; Return best or second best window found. | 5692 | ;; Return best or second best window found. |
| 5621 | (when (setq window (or best-window second-best-window)) | 5693 | (when (setq window (or best-window second-best-window)) |
| 5622 | (window--display-buffer buffer window 'reuse)))) | 5694 | (window--display-buffer buffer window 'reuse alist)))) |
| 5623 | 5695 | ||
| 5624 | (defun display-buffer-use-some-window (buffer alist) | 5696 | (defun display-buffer-use-some-window (buffer alist) |
| 5625 | "Display BUFFER in an existing window. | 5697 | "Display BUFFER in an existing window. |
| @@ -5647,7 +5719,7 @@ that frame." | |||
| 5647 | (get-largest-window 0 not-this-window)))) | 5719 | (get-largest-window 0 not-this-window)))) |
| 5648 | (when (window-live-p window) | 5720 | (when (window-live-p window) |
| 5649 | (prog1 | 5721 | (prog1 |
| 5650 | (window--display-buffer buffer window 'reuse) | 5722 | (window--display-buffer buffer window 'reuse alist) |
| 5651 | (window--even-window-heights window) | 5723 | (window--even-window-heights window) |
| 5652 | (unless (cdr (assq 'inhibit-switch-frame alist)) | 5724 | (unless (cdr (assq 'inhibit-switch-frame alist)) |
| 5653 | (window--maybe-raise-frame (window-frame window))))))) | 5725 | (window--maybe-raise-frame (window-frame window))))))) |
| @@ -5917,6 +5989,97 @@ WINDOW must be a live window and defaults to the selected one." | |||
| 5917 | window)))) | 5989 | window)))) |
| 5918 | 5990 | ||
| 5919 | ;;; Resizing buffers to fit their contents exactly. | 5991 | ;;; Resizing buffers to fit their contents exactly. |
| 5992 | (defcustom fit-frame-to-buffer nil | ||
| 5993 | "Non-nil means `fit-window-to-buffer' can resize frames. | ||
| 5994 | A frame can be resized if and only if its root window is a live | ||
| 5995 | window. The height of the root window is subject to the values | ||
| 5996 | of `fit-frame-to-buffer-max-height' and `window-min-height'." | ||
| 5997 | :type 'boolean | ||
| 5998 | :version "24.2" | ||
| 5999 | :group 'help) | ||
| 6000 | |||
| 6001 | (defcustom fit-frame-to-buffer-bottom-margin 4 | ||
| 6002 | "Bottom margin for `fit-frame-to-buffer'. | ||
| 6003 | This is the number of lines `fit-frame-to-buffer' leaves free at the | ||
| 6004 | bottom of the display in order to not obscure the system task bar." | ||
| 6005 | :type 'integer | ||
| 6006 | :version "24.2" | ||
| 6007 | :group 'windows) | ||
| 6008 | |||
| 6009 | (defun fit-frame-to-buffer (&optional frame max-height min-height) | ||
| 6010 | "Adjust height of FRAME to display its buffer's contents exactly. | ||
| 6011 | FRAME can be any live frame and defaults to the selected one. | ||
| 6012 | |||
| 6013 | Optional argument MAX-HEIGHT specifies the maximum height of | ||
| 6014 | FRAME and defaults to the height of the display below the current | ||
| 6015 | top line of FRAME minus FIT-FRAME-TO-BUFFER-BOTTOM-MARGIN. | ||
| 6016 | Optional argument MIN-HEIGHT specifies the minimum height of | ||
| 6017 | FRAME." | ||
| 6018 | (interactive) | ||
| 6019 | (setq frame (window-normalize-frame frame)) | ||
| 6020 | (let* ((root (frame-root-window frame)) | ||
| 6021 | (frame-min-height | ||
| 6022 | (+ (- (frame-height frame) (window-total-size root)) | ||
| 6023 | window-min-height)) | ||
| 6024 | (frame-top (frame-parameter frame 'top)) | ||
| 6025 | (top (if (consp frame-top) | ||
| 6026 | (funcall (car frame-top) (cadr frame-top)) | ||
| 6027 | frame-top)) | ||
| 6028 | (frame-max-height | ||
| 6029 | (- (/ (- (x-display-pixel-height frame) top) | ||
| 6030 | (frame-char-height frame)) | ||
| 6031 | fit-frame-to-buffer-bottom-margin)) | ||
| 6032 | (compensate 0) | ||
| 6033 | delta) | ||
| 6034 | (when (and (window-live-p root) (not (window-size-fixed-p root))) | ||
| 6035 | (with-selected-window root | ||
| 6036 | (cond | ||
| 6037 | ((not max-height) | ||
| 6038 | (setq max-height frame-max-height)) | ||
| 6039 | ((numberp max-height) | ||
| 6040 | (setq max-height (min max-height frame-max-height))) | ||
| 6041 | (t | ||
| 6042 | (error "%s is an invalid maximum height" max-height))) | ||
| 6043 | (cond | ||
| 6044 | ((not min-height) | ||
| 6045 | (setq min-height frame-min-height)) | ||
| 6046 | ((numberp min-height) | ||
| 6047 | (setq min-height (min min-height frame-min-height))) | ||
| 6048 | (t | ||
| 6049 | (error "%s is an invalid minimum height" min-height))) | ||
| 6050 | ;; When tool-bar-mode is enabled and we have just created a new | ||
| 6051 | ;; frame, reserve lines for toolbar resizing. This is needed | ||
| 6052 | ;; because for reasons unknown to me Emacs (1) reserves one line | ||
| 6053 | ;; for the toolbar when making the initial frame and toolbars | ||
| 6054 | ;; are enabled, and (2) later adds the remaining lines needed. | ||
| 6055 | ;; Our code runs IN BETWEEN (1) and (2). YMMV when you're on a | ||
| 6056 | ;; system that behaves differently. | ||
| 6057 | (let ((quit-restore (window-parameter root 'quit-restore)) | ||
| 6058 | (lines (tool-bar-lines-needed frame))) | ||
| 6059 | (when (and quit-restore (eq (car quit-restore) 'frame) | ||
| 6060 | (not (zerop lines))) | ||
| 6061 | (setq compensate (1- lines)))) | ||
| 6062 | (message "%s" compensate) | ||
| 6063 | (setq delta | ||
| 6064 | ;; Always count a final newline - we don't do any | ||
| 6065 | ;; post-processing, so let's play safe. | ||
| 6066 | (+ (count-screen-lines nil nil t) | ||
| 6067 | (- (window-body-size)) | ||
| 6068 | compensate))) | ||
| 6069 | ;; Move away from final newline. | ||
| 6070 | (when (and (eobp) (bolp) (not (bobp))) | ||
| 6071 | (set-window-point root (line-beginning-position 0))) | ||
| 6072 | (set-window-start root (point-min)) | ||
| 6073 | (set-window-vscroll root 0) | ||
| 6074 | (condition-case nil | ||
| 6075 | (set-frame-height | ||
| 6076 | frame | ||
| 6077 | (min (max (+ (frame-height frame) delta) | ||
| 6078 | min-height) | ||
| 6079 | max-height)) | ||
| 6080 | (error (setq delta nil)))) | ||
| 6081 | delta)) | ||
| 6082 | |||
| 5920 | (defun fit-window-to-buffer (&optional window max-height min-height) | 6083 | (defun fit-window-to-buffer (&optional window max-height min-height) |
| 5921 | "Adjust height of WINDOW to display its buffer's contents exactly. | 6084 | "Adjust height of WINDOW to display its buffer's contents exactly. |
| 5922 | WINDOW must be a live window and defaults to the selected one. | 6085 | WINDOW must be a live window and defaults to the selected one. |
| @@ -5937,9 +6100,12 @@ _all_ lines of its buffer you might not see the first lines when | |||
| 5937 | WINDOW was scrolled." | 6100 | WINDOW was scrolled." |
| 5938 | (interactive) | 6101 | (interactive) |
| 5939 | (setq window (window-normalize-window window t)) | 6102 | (setq window (window-normalize-window window t)) |
| 5940 | ;; Can't resize a full height or fixed-size window. | 6103 | (cond |
| 5941 | (unless (or (window-size-fixed-p window) | 6104 | ((window-size-fixed-p window)) |
| 5942 | (window-full-height-p window)) | 6105 | ((window-full-height-p window) |
| 6106 | (when fit-frame-to-buffer | ||
| 6107 | (fit-frame-to-buffer (window-frame window)))) | ||
| 6108 | (t | ||
| 5943 | (with-selected-window window | 6109 | (with-selected-window window |
| 5944 | (let* ((height (window-total-size)) | 6110 | (let* ((height (window-total-size)) |
| 5945 | (min-height | 6111 | (min-height |
| @@ -5955,7 +6121,7 @@ WINDOW was scrolled." | |||
| 5955 | ;; Can't get larger than height of frame. | 6121 | ;; Can't get larger than height of frame. |
| 5956 | (min max-height | 6122 | (min max-height |
| 5957 | (window-total-size (frame-root-window window))) | 6123 | (window-total-size (frame-root-window window))) |
| 5958 | ;, Don't delete other windows. | 6124 | ;; Don't delete other windows. |
| 5959 | (+ height (window-max-delta nil nil window)))) | 6125 | (+ height (window-max-delta nil nil window)))) |
| 5960 | ;; Make `desired-height' the height necessary to show | 6126 | ;; Make `desired-height' the height necessary to show |
| 5961 | ;; all of WINDOW's buffer, constrained by MIN-HEIGHT | 6127 | ;; all of WINDOW's buffer, constrained by MIN-HEIGHT |
| @@ -6018,89 +6184,7 @@ WINDOW was scrolled." | |||
| 6018 | (window-resize window 1 nil window) | 6184 | (window-resize window 1 nil window) |
| 6019 | (setq desired-height (1+ desired-height))))) | 6185 | (setq desired-height (1+ desired-height))))) |
| 6020 | (error (setq delta nil))) | 6186 | (error (setq delta nil))) |
| 6021 | delta)))) | 6187 | delta))))) |
| 6022 | |||
| 6023 | (defcustom fit-frame-to-buffer-bottom-margin 4 | ||
| 6024 | "Bottom margin for `fit-frame-to-buffer'. | ||
| 6025 | This is the number of lines `fit-frame-to-buffer' leaves free at the | ||
| 6026 | bottom of the display in order to not obscure the system task bar." | ||
| 6027 | :type 'integer | ||
| 6028 | :version "24.2" | ||
| 6029 | :group 'windows) | ||
| 6030 | |||
| 6031 | (defun fit-frame-to-buffer (&optional frame max-height min-height) | ||
| 6032 | "Adjust height of FRAME to display its buffer's contents exactly. | ||
| 6033 | FRAME can be any live frame and defaults to the selected one. | ||
| 6034 | |||
| 6035 | Optional argument MAX-HEIGHT specifies the maximum height of | ||
| 6036 | FRAME and defaults to the height of the display below the current | ||
| 6037 | top line of FRAME minus FIT-FRAME-TO-BUFFER-BOTTOM-MARGIN. | ||
| 6038 | Optional argument MIN-HEIGHT specifies the minimum height of | ||
| 6039 | FRAME." | ||
| 6040 | (interactive) | ||
| 6041 | (setq frame (window-normalize-frame frame)) | ||
| 6042 | (let* ((root (frame-root-window frame)) | ||
| 6043 | (frame-min-height | ||
| 6044 | (+ (- (frame-height frame) (window-total-size root)) | ||
| 6045 | window-min-height)) | ||
| 6046 | (frame-top (frame-parameter frame 'top)) | ||
| 6047 | (top (if (consp frame-top) | ||
| 6048 | (funcall (car frame-top) (cadr frame-top)) | ||
| 6049 | frame-top)) | ||
| 6050 | (frame-max-height | ||
| 6051 | (- (/ (- (x-display-pixel-height frame) top) | ||
| 6052 | (frame-char-height frame)) | ||
| 6053 | fit-frame-to-buffer-bottom-margin)) | ||
| 6054 | (compensate 0) | ||
| 6055 | delta) | ||
| 6056 | (when (and (window-live-p root) (not (window-size-fixed-p root))) | ||
| 6057 | (with-selected-window root | ||
| 6058 | (cond | ||
| 6059 | ((not max-height) | ||
| 6060 | (setq max-height frame-max-height)) | ||
| 6061 | ((numberp max-height) | ||
| 6062 | (setq max-height (min max-height frame-max-height))) | ||
| 6063 | (t | ||
| 6064 | (error "%s is an invalid maximum height" max-height))) | ||
| 6065 | (cond | ||
| 6066 | ((not min-height) | ||
| 6067 | (setq min-height frame-min-height)) | ||
| 6068 | ((numberp min-height) | ||
| 6069 | (setq min-height (min min-height frame-min-height))) | ||
| 6070 | (t | ||
| 6071 | (error "%s is an invalid minimum height" min-height))) | ||
| 6072 | ;; When tool-bar-mode is enabled and we have just created a new | ||
| 6073 | ;; frame, reserve lines for toolbar resizing. This is needed | ||
| 6074 | ;; because for reasons unknown to me Emacs (1) reserves one line | ||
| 6075 | ;; for the toolbar when making the initial frame and toolbars | ||
| 6076 | ;; are enabled, and (2) later adds the remaining lines needed. | ||
| 6077 | ;; Our code runs IN BETWEEN (1) and (2). YMMV when you're on a | ||
| 6078 | ;; system that behaves differently. | ||
| 6079 | (let ((quit-restore (window-parameter root 'quit-restore)) | ||
| 6080 | (lines (tool-bar-lines-needed frame))) | ||
| 6081 | (when (and quit-restore (eq (car quit-restore) 'frame) | ||
| 6082 | (not (zerop lines))) | ||
| 6083 | (setq compensate (1- lines)))) | ||
| 6084 | (message "%s" compensate) | ||
| 6085 | (setq delta | ||
| 6086 | ;; Always count a final newline - we don't do any | ||
| 6087 | ;; post-processing, so let's play safe. | ||
| 6088 | (+ (count-screen-lines nil nil t) | ||
| 6089 | (- (window-body-size)) | ||
| 6090 | compensate))) | ||
| 6091 | ;; Move away from final newline. | ||
| 6092 | (when (and (eobp) (bolp) (not (bobp))) | ||
| 6093 | (set-window-point root (line-beginning-position 0))) | ||
| 6094 | (set-window-start root (point-min)) | ||
| 6095 | (set-window-vscroll root 0) | ||
| 6096 | (condition-case nil | ||
| 6097 | (set-frame-height | ||
| 6098 | frame | ||
| 6099 | (min (max (+ (frame-height frame) delta) | ||
| 6100 | min-height) | ||
| 6101 | max-height)) | ||
| 6102 | (error (setq delta nil)))) | ||
| 6103 | delta)) | ||
| 6104 | 6188 | ||
| 6105 | (defun window-safely-shrinkable-p (&optional window) | 6189 | (defun window-safely-shrinkable-p (&optional window) |
| 6106 | "Return t if WINDOW can be shrunk without shrinking other windows. | 6190 | "Return t if WINDOW can be shrunk without shrinking other windows. |