Refactor rotate-windows, add utility swap-windows

Changes to rotate-windows:
- rename to spacemacs/rotate-windows-forward
- direction of rotation matches window numbers
- COUNT argument now rotates all windows by COUNT steps
- all window parameters are saved, not only buffer and window-start

swap-windows is not used for now, but could be helpful in the future.
This commit is contained in:
bmag 2016-08-23 18:58:23 +03:00 committed by bmag
parent 6e4442e0db
commit aa3f1816af
2 changed files with 33 additions and 26 deletions

View File

@ -148,41 +148,48 @@ automatically applied to."
"Determines if a buffer is useless."
(not (spacemacs/useful-buffer-p buffer)))
;; from magnars modified by ffevotte for dedicated windows support
(defun spacemacs/rotate-windows (count)
(defun spacemacs/swap-windows (window1 window2)
"Swap two windows.
WINDOW1 and WINDOW2 must be valid windows. They may contain child
windows."
(let ((state1 (window-state-get window1))
(state2 (window-state-get window2)))
;; to put state into dedicated windows, we must undedicate them first (not
;; needed with Emacs 25.1)
(dolist (win (list window1 window2))
(if (window-live-p win)
(set-window-dedicated-p win nil)
;; win has sub-windows, undedicate all of them
(walk-window-subtree (lambda (leaf-window)
(set-window-dedicated-p leaf-window nil))
win)))
(window-state-put state1 window2)
(window-state-put state2 window1)))
;; originally from magnars and modified by ffevotte for dedicated windows
;; support, it has quite diverged by now
(defun spacemacs/rotate-windows-forward (count)
"Rotate each window forwards.
A negative prefix argument rotates each window backwards.
Dedicated (locked) windows are left untouched."
(interactive "p")
(let* ((non-dedicated-windows (remove-if 'window-dedicated-p (window-list)))
(let* ((non-dedicated-windows (cl-remove-if 'window-dedicated-p (window-list)))
(states (mapcar #'window-state-get non-dedicated-windows))
(num-windows (length non-dedicated-windows))
(i 0)
(step (+ num-windows count)))
(cond ((not (> num-windows 1))
(message "You can't rotate a single window!"))
(t
(dotimes (counter (- num-windows 1))
(let* ((next-i (% (+ step i) num-windows))
(w1 (elt non-dedicated-windows i))
(w2 (elt non-dedicated-windows next-i))
(b1 (window-buffer w1))
(b2 (window-buffer w2))
(s1 (window-start w1))
(s2 (window-start w2)))
(set-window-buffer w1 b2)
(set-window-buffer w2 b1)
(set-window-start w1 s2)
(set-window-start w2 s1)
(setq i next-i)))))))
(if (< num-windows 2)
(error "You can't rotate a single window!")
(dotimes (i num-windows)
(window-state-put
(elt states i)
(elt non-dedicated-windows (% (+ step i) num-windows)))))))
(defun spacemacs/rotate-windows-backward (count)
"Rotate each window backwards.
Dedicated (locked) windows are left untouched."
(interactive "p")
(spacemacs/rotate-windows (* -1 count)))
(spacemacs/rotate-windows-forward (* -1 count)))
;; Note that this duplicates code from select-window-by-number, ideally should
;; upstream this function into windows.el

View File

@ -392,7 +392,7 @@
"wc" 'spacemacs/toggle-centered-buffer-mode
"wC" 'spacemacs/centered-buffer-mode-full-width
"wo" 'other-frame
"wr" 'spacemacs/rotate-windows
"wr" 'spacemacs/rotate-windows-forward
"wR" 'spacemacs/rotate-windows-backward
"ws" 'split-window-below
"wS" 'split-window-below-and-focus
@ -541,7 +541,7 @@
("L" evil-window-move-far-right)
("<S-right>" evil-window-move-far-right)
("o" other-frame)
("r" spacemacs/rotate-windows)
("r" spacemacs/rotate-windows-forward)
("R" spacemacs/rotate-windows-backward)
("s" split-window-below)
("S" split-window-below-and-focus)