Files @ 454aa3e3d784
Branch filter:

Location: workgroups2/src/workgroups-restore.el - annotation

Sergey Pashinin
restoring speedbar-mode
02ed61787ebd
088605c05794
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
088605c05794
088605c05794
088605c05794
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
643551b0cac0
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
443938b472d4
443938b472d4
088605c05794
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
031a33ecd5cb
031a33ecd5cb
031a33ecd5cb
031a33ecd5cb
031a33ecd5cb
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
0cd9bea1f5fe
02ed61787ebd
02ed61787ebd
0cd9bea1f5fe
0cd9bea1f5fe
0cd9bea1f5fe
0cd9bea1f5fe
0cd9bea1f5fe
0cd9bea1f5fe
0cd9bea1f5fe
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
443938b472d4
443938b472d4
02ed61787ebd
02ed61787ebd
02ed61787ebd
443938b472d4
02ed61787ebd
02ed61787ebd
02ed61787ebd
443938b472d4
02ed61787ebd
443938b472d4
443938b472d4
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
02ed61787ebd
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
443938b472d4
02ed61787ebd
02ed61787ebd
;;; workgroups-restore --- Functions to restore buffers and frames
;;; Commentary:
;;
;; TIPS
;;---------
;; Each Emacs frame ("window") can contain several workgroups.
;; WCONFIG is settings for each workgroup (buffers, parameters,...)
;;
;; So restoring WCONFIG using `wg-restore-wconfig' is restoring buffers
;; for current workgroup. Generally speaking each Workgroup can have
;; several WCONFIGs.
;;
;;; Code:

(require 'workgroups-variables)

(defun wg-restore-default-buffer ()
  "Switch to `wg-default-buffer'."
  (switch-to-buffer wg-default-buffer t))

(defun wg-restore-existing-buffer (buf)
  "Switch to and return BUF's referrent (some live buffer) if it exists."
  (wg-awhen (wg-find-buf-in-buffer-list buf (buffer-list))
    (switch-to-buffer it t)
    (wg-set-buffer-uid-or-error (wg-buf-uid buf))
    it))

(defun wg-restore-file-buffer (buf)
  "Restore BUF by finding its file.  Return the created buffer.
If BUF's file doesn't exist, call `wg-restore-default-buffer'"
  (wg-when-let ((file-name (wg-buf-file-name buf)))
    (when (or wg-restore-remote-buffers
              (not (file-remote-p file-name)))
      (cond ((file-exists-p file-name)
             (find-file file-name)
             (rename-buffer (wg-buf-name buf) t)
             (wg-set-buffer-uid-or-error (wg-buf-uid buf))
             (when wg-restore-mark
               (set-mark (wg-buf-mark buf))
               (deactivate-mark))
             (wg-deserialize-buffer-local-variables buf)
             (current-buffer))
            (t
             ;; try directory
             (if (not (file-remote-p file-name))
                 (if (file-directory-p (file-name-directory file-name))
                     (progn
                       (dired (file-name-directory file-name))
                       (current-buffer))
                   (progn
                     (message "Attempt to restore nonexistent file: %S" file-name)
                     nil))
               nil)
             )))))

(defun wg-restore-special-buffer (buf)
  "Restore a buffer BUF with DESERIALIZER-FN."
  (wg-when-let
      ((special-data (wg-buf-special-data buf))
       (buffer (save-window-excursion
                 (condition-case err
                     (funcall (car special-data) buf)
                   (error (message "Error deserializing %S: %S"
                                   (wg-buf-name buf) err)
                          nil)))))
    (switch-to-buffer buffer t)
    (wg-set-buffer-uid-or-error (wg-buf-uid buf))
    buffer))

(defun wg-restore-buffer (buf)
  "Restore BUF and return it."
  (let (wg-buffer-auto-association-on)
    (or (wg-restore-existing-buffer buf)
        (wg-restore-special-buffer buf)
        (wg-restore-file-buffer buf)
        (progn (wg-restore-default-buffer) nil))))

(defun wg-restore-window-positions (win &optional window)
  "Restore various positions in WINDOW from their values in WIN."
  (let ((window (or window (selected-window))))
    (wg-with-slots win
        ((win-point wg-win-point)
         (win-start wg-win-start)
         (win-hscroll wg-win-hscroll))
      (set-window-start window win-start t)
      (set-window-hscroll window win-hscroll)
      (set-window-point
       window
       (cond ((not wg-restore-point) win-start)
             ((eq win-point :max) (point-max))
             (t win-point)))
      (when (>= win-start (point-max)) (recenter)))))

(defun wg-restore-window (win)
  "Restore WIN in `selected-window'."
  (let ((selwin (selected-window))
        (buf (wg-find-buf-by-uid (wg-win-buf-uid win))))
    (if (not buf) (wg-restore-default-buffer)
      (when (wg-restore-buffer buf)
        (wg-restore-window-positions win selwin)
        (when wg-restore-window-dedicated-p
          (set-window-dedicated-p selwin (wg-win-dedicated win)))))))

(defun wg-reset-window-tree ()
  "Delete all but one window in `selected-frame', and reset
various parameters of that window in preparation for restoring
a wtree."
  (delete-other-windows)
  (set-window-dedicated-p nil nil))

(defun wg-restore-window-tree-helper (w)
  "Recursion helper for `wg-restore-window-tree'."
  (if (wg-wtree-p w)
      (loop with dir = (wg-wtree-dir w)
            for (win . rest) on (wg-wtree-wlist w)
            do (when rest (split-window nil (wg-w-size win dir) (not dir)))
            do (wg-restore-window-tree-helper win))
    (wg-restore-window w)
    (when (wg-win-selected w)
      (setq wg-window-tree-selected-window (selected-window)))
    (when (wg-win-minibuffer-scroll w)
      (setq minibuffer-scroll-window (selected-window)))
    (other-window 1)))

(defun wg-restore-window-tree (wtree)
  "Restore WTREE in `selected-frame'."
  (let ((window-min-width wg-window-min-width)
        (window-min-height wg-window-min-height)
        (wg-window-tree-selected-window nil))
    (wg-reset-window-tree)
    (wg-restore-window-tree-helper wtree)
    (wg-awhen wg-window-tree-selected-window (select-window it))))

(defun wg-wconfig-restore-frame-position (wconfig)
  "Restore `selected-frame's position from WCONFIG."
  (wg-when-let ((left (wg-wconfig-left wconfig))
                (top (wg-wconfig-top wconfig)))
    ;; Check that arguments are integers
    ;; Problem: https://github.com/pashinin/workgroups2/issues/15
    (if (and (integerp left)
             (integerp top))
        (set-frame-position (selected-frame) left top))))

(defun wg-wconfig-restore-scroll-bars (wconfig)
  "Restore `selected-frame's scroll-bar settings from WCONFIG."
  (set-frame-parameter
   nil 'vertical-scroll-bars (wg-wconfig-vertical-scroll-bars wconfig))
  (set-frame-parameter
   nil 'scroll-bar-width (wg-wconfig-scroll-bar-width wconfig)))

;;(defun wg-wconfig-restore-fullscreen (wconfig)
;;  "Restore `selected-frame's fullscreen settings from WCONFIG."
;;  (set-frame-parameter
;;   nil 'fullscreen (wg-wconfig-parameters wconfig))
;;  )

(defun wg-scale-wconfig-to-frame (wconfig)
  "Scale WCONFIG buffers to fit current frame size.
Return a scaled copy of WCONFIG."
  (interactive)
  (wg-scale-wconfigs-wtree wconfig
                           (frame-parameter nil 'width)
                           (frame-parameter nil 'height)))

(defun wg-frame-resize-and-position (wconfig)
  "Resize and position a frame based on WCONFIG of current workgroup."
  (interactive)
  (let* ((params (wg-wconfig-parameters wconfig))
         fullscreen)
    (set-frame-parameter nil 'fullscreen (if (assoc 'fullscreen params)
                                             (cdr (assoc 'fullscreen params))
                                           nil))
    (when (and wg-restore-frame-position
               (not (frame-parameter nil 'fullscreen)))
      (wg-wconfig-restore-frame-position wconfig))
    ))

(defun wg-restore-frame-size-position (wconfig)
  "Smart-restore of frame size and position.

Depending on `wg-remember-frame-for-each-wg' frame parameters may
be restored for each workgroup.

If `wg-remember-frame-for-each-wg' is nil (by default) then
current frame parameters are saved/restored to/from first
workgroup. And frame parameters for all other workgroups are just
ignored.
"
  (interactive)
  (let* ((params (wg-wconfig-parameters wconfig))
         fullscreen)
    ;; Frame maximized / fullscreen / none
    (unless wg-remember-frame-for-each-wg
      (setq params (wg-wconfig-parameters (wg-workgroup-working-wconfig (wg-first-workgroup)))))
    (setq fullscreen (if (assoc 'fullscreen params)
                         (cdr (assoc 'fullscreen params))
                       nil))
    (when (and fullscreen
             (or wg-remember-frame-for-each-wg
                 (null (wg-current-workgroup t))))
      (set-frame-parameter nil 'fullscreen fullscreen)
      ;; I had bugs restoring maximized frame:
      ;; Frame could be maximized but buffers are not scaled to fit it.
      ;;
      ;; Maybe because of `set-frame-parameter' takes some time to finish and is async.
      ;; So I tried this and it helped
      (sleep-for 0 100))

    ;; Position
    (when (and wg-restore-frame-position
               wg-remember-frame-for-each-wg
               (not (frame-parameter nil 'fullscreen)))
      (wg-wconfig-restore-frame-position wconfig))
    ))

;; FIXME: throw a specific error if the restoration was unsuccessful
(defun wg-restore-wconfig (wconfig)
  "Restore a workgroup configuration WCONFIG in `selected-frame'.

Runs each time you're switching workgroups."
  (let ((wg-record-incorrectly-restored-bufs t)
        (wg-incorrectly-restored-bufs nil)
        (params (wg-wconfig-parameters wconfig))
        fullscreen wtree)
    (wg-barf-on-active-minibuffer)
    (wg-restore-frame-size-position wconfig)
    (when wg-restore-scroll-bars
      (wg-wconfig-restore-scroll-bars wconfig))
    (setq wtree (wg-scale-wconfig-to-frame wconfig))  ; scale wtree to frame size

    ;; Restore buffers
    (wg-restore-window-tree
     (if (not (wg-morph-p)) wtree (wg-morph wtree)))

    ;; Restore frame position
    (when (and wg-restore-frame-position
               (not (frame-parameter nil 'fullscreen))
               (null (wg-current-workgroup t)))
      (wg-wconfig-restore-frame-position wconfig))

    (when wg-incorrectly-restored-bufs
      (message "Unable to restore these buffers: %S\
If you want, restore them manually and try again."
               (mapcar 'wg-buf-name wg-incorrectly-restored-bufs)))))



(provide 'workgroups-restore)
;;; workgroups-restore.el ends here