branch: elpa/annotate commit 475cc56ec6ab12b6b3a0a6ef4c5b4cb09fca8566 Author: cage <cage-invalid@invalid> Commit: cage <cage-invalid@invalid>
- added checksum for files to check if annotations could be updated; - added a cutomizable variable that holds the major modes that should not load annotate-mode; - added more docstrings; - minor cosmetic changes. --- annotate.el | 115 ++++++++++++++++++++++++++++++++++++++++++++++++------------ 1 file changed, 93 insertions(+), 22 deletions(-) diff --git a/annotate.el b/annotate.el index 80563206d7..6d277ec1fa 100644 --- a/annotate.el +++ b/annotate.el @@ -62,12 +62,12 @@ :lighter " Ann" :keymap (make-sparse-keymap) :group 'annotate - :after-hook (if annotate-mode - (annotate-initialize) - (annotate-shutdown))) + :after-hook (annotate-after-hook)) (define-key annotate-mode-map (kbd "C-c C-a") 'annotate-annotate) + (define-key annotate-mode-map (kbd "C-c ]") 'annotate-next-annotation) + (define-key annotate-mode-map (kbd "C-c [") 'annotate-previous-annotation) (defcustom annotate-file (locate-user-emacs-file "annotations" ".annotations") @@ -115,6 +115,43 @@ :type 'string :group 'annotate) +(defcustom annotate-maximum-size-checksum 5000000 + "Calculate checksum of the current buffer only if the size is +less than this size (in characters)" + :type 'integer + :group 'annotate) + +(defconst annotate-warn-file-changed-control-string + (concat "The file '%s' has changed on disk " + "from the last time the annotations was saved. " + "Chances are that they will not be displayed correctly") + "The message to warn user that file has been modified and + annototatnions position could be outdated") + +(defcustom annotate-blacklist-major-mode '(org-mode) + "Prevent loading of annotated-mode When the visited file's +major mode is a member of this list (space separated entries)." + :type '(repeat symbol) + :group 'annotate) + +(defun annotate-after-hook () + (let ((annotate-allowed-p (with-current-buffer (current-buffer) + (not (cl-member major-mode annotate-blacklist-major-mode))))) + (cond + ((not annotate-allowed-p) + (annotate-shutdown) + (setq annotate-mode nil)) + (annotate-mode + (annotate-initialize)) + (t + (annotate-shutdown))))) + +(cl-defun annotate-buffer-checksum (&optional (object (current-buffer))) + (if (< (buffer-size) + annotate-maximum-size-checksum) + (md5 object) + nil)) + (defun annotate-initialize () "Load annotations and set up save and display hooks." (annotate-load-annotations) @@ -133,6 +170,11 @@ nil '((annotate--font-lock-matcher (2 (annotate--annotation-builder)) (1 (annotate--change-guard)))))) +(defun annotate-overlay-filled-p (overlay) + (and overlay + (overlayp overlay) + (overlay-get overlay 'annotation))) + (defun annotate-annotate () "Create, modify, or delete annotation." (interactive) @@ -191,12 +233,15 @@ (interactive) (let ((file-annotations (annotate-describe-annotations)) (all-annotations (annotate-load-annotation-data)) - (filename (substring-no-properties (or (buffer-file-name) "")))) + (filename (substring-no-properties (or (buffer-file-name) "")))) (if (assoc-string filename all-annotations) (setcdr (assoc-string filename all-annotations) - file-annotations) + (list file-annotations + (annotate-buffer-checksum))) (setq all-annotations - (push (cons filename file-annotations) + (push (list filename + file-annotations + (annotate-buffer-checksum)) all-annotations))) ;; remove duplicate entries (a user reported seeing them) (dolist (entry all-annotations) @@ -210,18 +255,26 @@ (message "Annotations saved.")))) (defun annotate-actual-comment-start () + "String for comment start related to current buffer's major +mode." (or comment-start annotate-fallback-comment)) (defun annotate-actual-comment-end () + "String for comment ends, if any, related to current buffer's +major mode." (or comment-end "")) (defun annotate-comments-length () + "Total length of the comment markers (start and end) strings." (+ (string-width (annotate-actual-comment-start)) (string-width (annotate-actual-comment-end)))) (defun annotate-wrap-in-comment (&rest strings) + "Put comment markers at the start and (if does makes sense) +ends of a string. See: annotate-actual-comment-start and +annotate-actual-comment-end" (apply #'concat (append (list (annotate-actual-comment-start)) strings (list (annotate-actual-comment-end))))) @@ -251,9 +304,9 @@ An example might look like this:" (- ov-start bol (annotate-comments-length))) - ? ) - (make-string (max 0 (- eol ov-start)) - annotate-integrate-higlight)))) + ? ) + (make-string (max 0 (- eol ov-start)) + annotate-integrate-higlight)))) ;; fully underline second to second-to-last line (while (< (progn (forward-line) (end-of-line) @@ -265,11 +318,11 @@ An example might look like this:" (point)))) (end-of-line) (insert "\n" - (annotate-wrap-in-comment (make-string (max 0 - (- eol - bol - (annotate-comments-length))) - annotate-integrate-higlight))))) + (annotate-wrap-in-comment (make-string (max 0 + (- eol + bol + (annotate-comments-length))) + annotate-integrate-higlight))))) ;; partially underline last line (let ((bol (progn (beginning-of-line) (point))) @@ -656,15 +709,31 @@ an overlay and it's annotation." (1+ (- (line-number-at-pos end) (line-number-at-pos start)))))) (format "-%i,%i +%i,%i" start-line diff-size start-line diff-size))) +(defun annotate-checksum-from-dump (record) + (nth 2 record)) + +(defun annotate-annotations-from-dump (record) + (nth 1 record)) + (defun annotate-load-annotations () "Load all annotations from disk." (interactive) - (let ((annotations (cdr (assoc-string - (substring-no-properties (or (buffer-file-name) "")) - (annotate-load-annotation-data)))) - (modified-p (buffer-modified-p))) + (let* ((filename (substring-no-properties (or (buffer-file-name) ""))) + (all-annotations-data (annotate-load-annotation-data)) + (annotation-dump (assoc-string filename all-annotations-data)) + (annotations (annotate-annotations-from-dump annotation-dump)) + (old-checksum (annotate-checksum-from-dump annotation-dump)) + (new-checksum (annotate-buffer-checksum)) + (modified-p (buffer-modified-p))) + (when (and old-checksum + new-checksum + (not (string= old-checksum new-checksum))) + (lwarn "annotate-mode" + :warning + annotate-warn-file-changed-control-string + filename)) ;; remove empty annotations created by earlier bug: - (setq annotations (cl-remove-if (lambda (ann) (eq (nth 2 ann) nil)) + (setq annotations (cl-remove-if (lambda (ann) (null (nth 2 ann))) annotations)) (when (and (eq nil annotations) annotate-use-messages) (message "No annotations found.")) @@ -774,9 +843,11 @@ an overlay and it's annotation." (when (file-exists-p annotate-file) (insert-file-contents annotate-file)) (goto-char (point-max)) - (cond ((= (point) 1) nil) - (t (goto-char (point-min)) - (read (current-buffer)))))) + (cond ((= (point) 1) + nil) + (t + (goto-char (point-min)) + (read (current-buffer)))))) (defun annotate-dump-annotation-data (data) "Save `data` into annotation file."