bug-gnu-emacs
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

bug#33567: Syntactic fontification of diff hunks


From: Juri Linkov
Subject: bug#33567: Syntactic fontification of diff hunks
Date: Tue, 18 Dec 2018 02:14:48 +0200
User-agent: Gnus/5.13 (Gnus v5.13) Emacs/27.0.50 (x86_64-pc-linux-gnu)

>> Thanks, this LGTM.
>
> Pushed to master and closed.

Here's an additional patch to support diffs with files that contain
just one line as documented in (info "(diffutils) Detailed Unified")
and also without the final newline.  Such diffs have the text:

\ No newline at end of file

diff --git a/lisp/vc/diff-mode.el b/lisp/vc/diff-mode.el
index ed953deb21..8c18f69e8c 100644
--- a/lisp/vc/diff-mode.el
+++ b/lisp/vc/diff-mode.el
@@ -1697,10 +1697,11 @@ diff-hunk-text
              (delete-region divider-pos (point-max)))
            (delete-region (point-min) keep))
          ;; Remove line-prefix characters, and unneeded lines (unified diffs).
-         (let ((kill-char (if destp ?- ?+)))
+          ;; Also skip lines like "\ No newline at end of file"
+         (let ((kill-chars (list (if destp ?- ?+) ?\\)))
            (goto-char (point-min))
            (while (not (eobp))
-             (if (eq (char-after) kill-char)
+             (if (memq (char-after) kill-chars)
                  (delete-region (point) (progn (forward-line 1) (point)))
                (delete-char num-pfx-chars)
                (forward-line 1)))))
@@ -2394,19 +2395,23 @@ diff-syntax-fontify
 
 (defvar diff-syntax-fontify-revisions (make-hash-table :test 'equal))
 
+(eval-when-compile (require 'subr-x)) ; for string-trim-right
+
 (defun diff-syntax-fontify-hunk (beg end old)
   "Highlight source language syntax in diff hunk between BEG and END.
 When OLD is non-nil, highlight the hunk from the old source."
   (remove-overlays beg end 'diff-mode 'syntax)
   (goto-char beg)
   (let* ((hunk (buffer-substring-no-properties beg end))
-         (text (or (ignore-errors (diff-hunk-text hunk (not old) nil)) ""))
+         (text (string-trim-right (or (ignore-errors (diff-hunk-text hunk (not 
old) nil)) "")))
         (line (if (looking-at "\\(?:\\*\\{15\\}.*\n\\)?[-@* 
]*\\([0-9,]+\\)\\([ acd+]+\\([0-9,]+\\)\\)?")
                   (if old (match-string 1)
                     (if (match-end 3) (match-string 3) (match-string 1)))))
-         (line-nb (and line (string-match "\\([0-9]+\\),\\([0-9]+\\)" line)
+         (line-nb (when line
+                    (if (string-match "\\([0-9]+\\),\\([0-9]+\\)" line)
                         (list (string-to-number (match-string 1 line))
-                             (string-to-number (match-string 2 line)))))
+                             (string-to-number (match-string 2 line)))
+                      (list (string-to-number line) 1)))) ; One-line diffs
          props)
     (cond
      ((and diff-vc-backend (not (eq diff-font-lock-syntax 'hunk-only)))
@@ -2470,6 +2475,7 @@ diff-syntax-fontify-hunk
       (while (< (progn (forward-line 1) (point)) end)
         (when (or (and (not old) (not (looking-at-p "[-<]")))
                   (and      old  (not (looking-at-p "[+>]"))))
+          (unless (looking-at-p "\\\\") ; skip "\ No newline at end of file"
             (if (and old (not (looking-at-p "[-<]")))
                 ;; Fontify context lines only from new source,
                 ;; don't refontify context lines from old source.
@@ -2481,7 +2487,7 @@ diff-syntax-fontify-hunk
                                           (+ bol (nth 1 prop))
                                           nil 'front-advance nil)))
                     (overlay-put ol 'evaporate t)
-                  (overlay-put ol 'face (nth 2 prop)))))))))))
+                    (overlay-put ol 'face (nth 2 prop))))))))))))
 
 (defun diff-syntax-fontify-props (file text line-nb &optional no-init 
hunk-only)
   "Get font-lock properties from the source code.

reply via email to

[Prev in Thread] Current Thread [Next in Thread]