* initial implementation of the header/view split viewmode (WIP)

This commit is contained in:
djcb
2012-04-08 12:43:37 +03:00
parent 1b451b754a
commit bf36858c9d
3 changed files with 89 additions and 36 deletions

View File

@ -30,6 +30,7 @@
(eval-when-compile (require 'cl)) (eval-when-compile (require 'cl))
(require 'hl-line)
(require 'mu4e-proc) (require 'mu4e-proc)
;;;; internal variables/constants ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;;;; internal variables/constants ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
@ -351,14 +352,19 @@ after the end of the search results."
(make-local-variable 'mu4e-hdrs-proc) (make-local-variable 'mu4e-hdrs-proc)
(make-local-variable 'mu4e-marks-map) (make-local-variable 'mu4e-marks-map)
(make-local-variable 'mu4e-thread-info-map) (make-local-variable 'mu4e-thread-info-map)
(make-local-variable 'global-mode-string) (make-local-variable 'global-mode-string)
(make-local-variable 'hl-line-face)
(setq (setq
mu4e-marks-map (make-hash-table :size 16 :rehash-size 2) mu4e-marks-map (make-hash-table :size 16 :rehash-size 2)
mu4e-thread-info-map (make-hash-table :size 512 :rehash-size 2) mu4e-thread-info-map (make-hash-table :size 512 :rehash-size 2)
truncate-lines t truncate-lines t
buffer-undo-list t ;; don't record undo information buffer-undo-list t ;; don't record undo information
overwrite-mode 'overwrite-mode-binary) overwrite-mode 'overwrite-mode-binary
hl-line-face 'mu4e-header-highlight-face)
(hl-line-mode 1)
(setq header-line-format (setq header-line-format
(cons (cons
@ -707,29 +713,51 @@ do a new search."
(defun mu4e-view-message () (defun mu4e-view-message ()
"View the message at point." "View the message at point."
(interactive) (interactive)
(mu4e-hdrs-view)) (let ((viewwin (when (buffer-live-p mu4e-view-buffer)
(get-buffer-window mu4e-view-buffer))))
(unless (window-live-p viewwin)
;; no view window yet; create one, based on the split settings etc.
(setq viewwin
(cond ;; is there are live window for the message view?
;; split horizontally
((eq mu4e-split-mode 'horizontal)
(split-window nil mu4e-headers-visible-lines 'below))
;; split vertically
((eq mu4e-split-mode 'vertical)
(split-window nil mu4e-headers-visible-columns 'right))
;; no splitting; just use the currently selected one
(t
(selected-window)))))
;; okay, now we have viewwin
(select-window viewwin)
(mu4e-hdrs-view)))
(defun mu4e--hdrs-move (lines)
"Move point LINES lines forward (if LINES is positive) or
backward (if LINES is negative). If this succeeds, return the new
docid. Otherwise, return nil."
(with-current-buffer mu4e-hdrs-buffer
(hl-line-unhighlight)
(let ((succeeded (= 0 (forward-line lines)))
(docid (mu4e--docid-at-point)))
;; trick to move point, even if this function is called when this window
;; is not visible
(set-window-point (get-buffer-window mu4e-hdrs-buffer) (point))
(hl-line-highlight)
;; return the docid only if the move succeeded
(when succeeded docid))))
(defun mu4e-next-header () (defun mu4e-next-header ()
"Move point to the next message header. If this succeeds, return "Move point to the next message header. If this succeeds, return
the new docid. Otherwise, return nil." the new docid. Otherwise, return nil."
(interactive) (interactive)
(with-current-buffer mu4e-hdrs-buffer (mu4e--hdrs-move 1))
(when (= 0 (forward-line 1))
(or (mu4e--docid-at-point) (mu4e-next-header)) ;; skip non-headers
;; trick to move point, even if this function is called when this window
;; is not visible
(set-window-point (get-buffer-window mu4e-hdrs-buffer) (point)))))
(defun mu4e-prev-header () (defun mu4e-prev-header ()
"Move point to the previous message header. If this succeeds, "Move point to the previous message header. If this succeeds,
return the new docid. Otherwise, return nil." return the new docid. Otherwise, return nil."
(interactive) (interactive)
(with-current-buffer mu4e-hdrs-buffer (mu4e--hdrs-move -1))
(when (= 0 (forward-line -1))
(or (mu4e--docid-at-point) (mu4e-prev-header)) ;; skip non-headers
;; trick to move point, even if this function is called when this window
;; is not visible
(set-window-point (get-buffer-window mu4e-hdrs-buffer) (point)))))
(defun mu4e-jump-to-maildir () (defun mu4e-jump-to-maildir ()

View File

@ -35,8 +35,7 @@
(defconst mu4e-view-buffer-name "*mu4e-view*" (defconst mu4e-view-buffer-name "*mu4e-view*"
"*internal* Name for the message view buffer") "*internal* Name for the message view buffer")
(defconst mu4e-raw-view-buffer-name "*mu4e-raw-view*" (defvar mu4e-view-buffer nil "*internal* The view buffer.")
"*internal* Name for the raw message view buffer")
;; some buffer-local variables ;; some buffer-local variables
(defvar mu4e-hdrs-buffer nil (defvar mu4e-hdrs-buffer nil
@ -50,7 +49,6 @@
wanting to show specific messages - for example, `mu4e-org'." wanting to show specific messages - for example, `mu4e-org'."
(mu4e-proc-view-msg msgid)) (mu4e-proc-view-msg msgid))
(defun mu4e-view (msg hdrsbuf &optional update) (defun mu4e-view (msg hdrsbuf &optional update)
"Display the message MSG in a new buffer, and keep in sync with HDRSBUF. "Display the message MSG in a new buffer, and keep in sync with HDRSBUF.
'In sync' here means that moving to the next/previous message in 'In sync' here means that moving to the next/previous message in
@ -64,6 +62,7 @@ marking if it still had that."
(let ((buf (get-buffer-create mu4e-view-buffer-name)) (let ((buf (get-buffer-create mu4e-view-buffer-name))
(inhibit-read-only t)) (inhibit-read-only t))
(with-current-buffer buf (with-current-buffer buf
(setq mu4e-view-buffer buf)
(erase-buffer) (erase-buffer)
(insert (insert
(mapconcat (mapconcat
@ -456,8 +455,10 @@ number them so they can be opened using `mu4e-view-go-to-url'."
;; raw mode ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;; raw mode ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
;; some buffer-local variables ;; some buffer-local variables
(defvar mu4e-view-buffer nil (defconst mu4e-raw-view-buffer-name "*mu4e-raw-view*"
"*internal* View buffer connected to this raw view.") "*internal* Name for the raw message view buffer")
(defvar mu4e-raw-view-buffer nil "*internal* The raw view buffer.")
(defvar mu4e-raw-view-mode-map nil (defvar mu4e-raw-view-mode-map nil
"Keymap for \"*mu4e-raw-view*\" buffers.") "Keymap for \"*mu4e-raw-view*\" buffers.")
@ -501,7 +502,7 @@ number them so they can be opened using `mu4e-view-go-to-url'."
(insert-file file) (insert-file file)
;; initialize view-mode ;; initialize view-mode
(mu4e-raw-view-mode) (mu4e-raw-view-mode)
(setq mu4e-view-buffer view-buffer) (setq mu4e-raw-view-buffer view-buffer)
(switch-to-buffer buf) (switch-to-buffer buf)
(goto-char (point-min))))) (goto-char (point-min)))))
@ -517,7 +518,7 @@ number them so they can be opened using `mu4e-view-go-to-url'."
(erase-buffer) (erase-buffer)
(process-file-shell-command cmd file buf) (process-file-shell-command cmd file buf)
(mu4e-raw-view-mode) (mu4e-raw-view-mode)
(setq mu4e-view-buffer view-buffer) (setq mu4e-raw-view-buffer view-buffer)
(switch-to-buffer buf) (switch-to-buffer buf)
(goto-char (point-min))))) (goto-char (point-min)))))
@ -525,9 +526,7 @@ number them so they can be opened using `mu4e-view-go-to-url'."
(defun mu4e-raw-view-quit-buffer () (defun mu4e-raw-view-quit-buffer ()
"Quit the raw view and return to the message." "Quit the raw view and return to the message."
(interactive) (interactive)
(if (buffer-live-p mu4e-view-buffer) (kill-buffer))
(switch-to-buffer mu4e-view-buffer)
(kill-buffer)))
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
;; functions for org-contacts ;; functions for org-contacts
@ -610,9 +609,9 @@ citations."
(defun mu4e-view-quit-buffer () (defun mu4e-view-quit-buffer ()
"Quit the message view and return to the headers." "Quit the message view and return to the headers."
(interactive) (interactive)
(if (buffer-live-p mu4e-hdrs-buffer) (kill-buffer-and-window)
(switch-to-buffer mu4e-hdrs-buffer) (when (buffer-live-p mu4e-hdrs-buffer)
(kill-buffer))) (switch-to-buffer mu4e-hdrs-buffer)))
(defun mu4e-view-next-header () (defun mu4e-view-next-header ()
"View the next header." "View the next header."

View File

@ -116,6 +116,12 @@ form (QUERY DESCRIPTION KEY), where QUERY is a string with a mu
query, DESCRIPTION is a short description of the query (this will query, DESCRIPTION is a short description of the query (this will
show up in the UI), and KEY is a shortcut key for the query.") show up in the UI), and KEY is a shortcut key for the query.")
(defvar mu4e-split-mode nil
"How to show messages / headers; as symbol which is either:
nil: don't split (show either headers or messages, not both)
horizontal: split horizontally (headers on top)
vertical: split vertically (headers on the left).
Also see `mu4e-headers-visible-lines'.")
;; Sending ;; Sending
(defgroup mu4e-sending nil (defgroup mu4e-sending nil
@ -208,6 +214,20 @@ designated shortcut character for the maildir.")
:type 'symbol :type 'symbol
:group 'mu4e-headers) :group 'mu4e-headers)
(defcustom mu4e-headers-visible-lines 8
"Number of header lines to display for the header view when using
the horizontal split-view."
:type 'integer
:group 'mu4e-headers)
(defcustom mu4e-headers-visible-columns 30
"Number of columns to display for the header view when using the
vertical split-view."
:type 'integer
:group 'mu4e-headers)
;; the message view ;; the message view
(defgroup mu4e-view nil (defgroup mu4e-view nil
"Settings for the message view." "Settings for the message view."
@ -312,6 +332,7 @@ sent folder."
:group 'mu4e :group 'mu4e
:group 'faces) :group 'faces)
(defface mu4e-unread-face (defface mu4e-unread-face
'((t :inherit font-lock-keyword-face :bold t)) '((t :inherit font-lock-keyword-face :bold t))
"Face for an unread message header." "Face for an unread message header."
@ -351,6 +372,11 @@ flag set)."
view." view."
:group 'mu4e-faces) :group 'mu4e-faces)
(defface mu4e-header-highlight-face
'((t :inherit default :weight bold :underline t))
"Face for the header at point."
:group 'mu4e-faces)
(defface mu4e-view-header-value-face (defface mu4e-view-header-value-face
'((t :inherit font-lock-doc-face)) '((t :inherit font-lock-doc-face))
"Face for a header value (such as \"Re: Hello!\") in the message "Face for a header value (such as \"Re: Hello!\") in the message