Package: emacs;
Reported by: Tino Calancha <tino.calancha <at> gmail.com>
Date: Sun, 29 Jan 2017 11:38:02 UTC
Severity: normal
Tags: patch
Found in version 24.5
Done: Tino Calancha <tino.calancha <at> gmail.com>
Bug is archived. No further changes may be made.
View this message in rfc822 format
From: help-debbugs <at> gnu.org (GNU bug Tracking System) To: Tino Calancha <tino.calancha <at> gmail.com> Subject: bug#25571: closed (Re: bug#25571: 24.5; Check if there are hunks before kill or refine a hunk) Date: Thu, 02 Feb 2017 13:35:02 +0000
[Message part 1 (text/plain, inline)]
Your bug report #25571: 24.5; Check if there are hunks before kill or refine a hunk which was filed against the emacs package, has been closed. The explanation is attached below, along with your original report. If you require more details, please reply to 25571 <at> debbugs.gnu.org. -- 25571: http://debbugs.gnu.org/cgi/bugreport.cgi?bug=25571 GNU Bug Tracking System Contact help-debbugs <at> gnu.org with problems
[Message part 2 (message/rfc822, inline)]
From: Tino Calancha <tino.calancha <at> gmail.com> To: 25571-done <at> debbugs.gnu.org Subject: Re: bug#25571: 24.5; Check if there are hunks before kill or refine a hunk Date: Thu, 02 Feb 2017 22:34:30 +0900Tino Calancha <tino.calancha <at> gmail.com> writes: > Tino Calancha <tino.calancha <at> gmail.com> writes: > >> emacs -Q: >> ; Put following content in a buffer in diff-mode: >> ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; START >> diff --git a/a b/a >> index 184cbf6..d2d9a24 100644 >> --- a/a >> +++ b/a >> @@ -1,2 +1,2 @@ >> -I have a foo in my bar. >> +I have a qux in my bar. >> Me too. >> ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; END > < ; Go to beginning of buffer > M-n M-k > M-n ; Shows: 'No next hunk'. > M-k ; Shows: "Can't find the beginning of the file". > ;; It would be more clear a message like: 'No more hunks'. Push fix to master branch as commit a362b56b51f49963dbb63cd318967bca9b9fef74
[Message part 3 (message/rfc822, inline)]
From: Tino Calancha <tino.calancha <at> gmail.com> To: bug-gnu-emacs <at> gnu.org Subject: 24.5; Check if there are hunks before kill or refine a hunk Date: Sun, 29 Jan 2017 20:37:37 +0900 (JST)emacs -Q: ; Put following content in a buffer in diff-mode: ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; START diff --git a/a b/a index 184cbf6..d2d9a24 100644 --- a/a +++ b/a @@ -1,2 +1,2 @@ -I have a foo in my bar. +I have a qux in my bar. Me too. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; END From ed6a10f980bd1eec73982582db7599f936fa5315 Mon Sep 17 00:00:00 2001 From: Tino Calancha <tino.calancha <at> gmail.com> Date: Sun, 29 Jan 2017 20:29:47 +0900 Subject: [PATCH] Check if there are hunks before kill or refine a hunk * lisp/vc/diff-mode.el (diff--some-hunks-p): New predicate. (diff-hunk-kill, diff-file-kill, diff-refine-hunk): Use it (Bug#25571). --- lisp/vc/diff-mode.el | 156 +++++++++++++++++++++++++++------------------------ 1 file changed, 83 insertions(+), 73 deletions(-) diff --git a/lisp/vc/diff-mode.el b/lisp/vc/diff-mode.el index e609ca9f94..4ad03be7f0 100644 --- a/lisp/vc/diff-mode.el +++ b/lisp/vc/diff-mode.el @@ -647,28 +647,35 @@ diff-restrict-view (if arg (diff-bounds-of-file) (diff-bounds-of-hunk))) (set (make-local-variable 'diff-narrowed-to) (if arg 'file 'hunk))) +(defun diff--some-hunks-p () + (save-excursion + (goto-char (point-min)) + (re-search-forward diff-hunk-header-re nil t))) + (defun diff-hunk-kill () "Kill the hunk at point." (interactive) - (let* ((hunk-bounds (diff-bounds-of-hunk)) - (file-bounds (ignore-errors (diff-bounds-of-file))) - ;; If the current hunk is the only one for its file, kill the - ;; file header too. - (bounds (if (and file-bounds - (progn (goto-char (car file-bounds)) - (= (progn (diff-hunk-next) (point)) - (car hunk-bounds))) - (progn (goto-char (cadr hunk-bounds)) - ;; bzr puts a newline after the last hunk. - (while (looking-at "^\n") - (forward-char 1)) - (= (point) (cadr file-bounds)))) - file-bounds - hunk-bounds)) - (inhibit-read-only t)) - (apply 'kill-region bounds) - (goto-char (car bounds)) - (diff-beginning-of-hunk t))) + (if (not (diff--some-hunks-p)) + (error "No more hunks") + (let* ((hunk-bounds (diff-bounds-of-hunk)) + (file-bounds (ignore-errors (diff-bounds-of-file))) + ;; If the current hunk is the only one for its file, kill the + ;; file header too. + (bounds (if (and file-bounds + (progn (goto-char (car file-bounds)) + (= (progn (diff-hunk-next) (point)) + (car hunk-bounds))) + (progn (goto-char (cadr hunk-bounds)) + ;; bzr puts a newline after the last hunk. + (while (looking-at "^\n") + (forward-char 1)) + (= (point) (cadr file-bounds)))) + file-bounds + hunk-bounds)) + (inhibit-read-only t)) + (apply 'kill-region bounds) + (goto-char (car bounds)) + (diff-beginning-of-hunk t)))) (defun diff-beginning-of-file-and-junk () "Go to the beginning of file-related diff-info. @@ -720,9 +727,11 @@ diff-beginning-of-file-and-junk (defun diff-file-kill () "Kill current file's hunks." (interactive) - (let ((inhibit-read-only t)) - (apply 'kill-region (diff-bounds-of-file))) - (diff-beginning-of-hunk t)) + (if (not (diff--some-hunks-p)) + (error "No more hunks") + (let ((inhibit-read-only t)) + (apply 'kill-region (diff-bounds-of-file))) + (diff-beginning-of-hunk t))) (defun diff-kill-junk () "Kill spurious empty diffs." @@ -2000,57 +2009,58 @@ diff-refine-hunk "Highlight changes of hunk at point at a finer granularity." (interactive) (require 'smerge-mode) - (save-excursion - (diff-beginning-of-hunk t) - (let* ((start (point)) - (style (diff-hunk-style)) ;Skips the hunk header as well. - (beg (point)) - (props-c '((diff-mode . fine) (face diff-refine-changed))) - (props-r '((diff-mode . fine) (face diff-refine-removed))) - (props-a '((diff-mode . fine) (face diff-refine-added))) - ;; Be careful to go back to `start' so diff-end-of-hunk gets - ;; to read the hunk header's line info. - (end (progn (goto-char start) (diff-end-of-hunk) (point)))) - - (remove-overlays beg end 'diff-mode 'fine) - - (goto-char beg) - (pcase style - (`unified - (while (re-search-forward "^-" end t) - (let ((beg-del (progn (beginning-of-line) (point))) - beg-add end-add) - (when (and (diff--forward-while-leading-char ?- end) - ;; Allow for "\ No newline at end of file". - (progn (diff--forward-while-leading-char ?\\ end) - (setq beg-add (point))) - (diff--forward-while-leading-char ?+ end) - (progn (diff--forward-while-leading-char ?\\ end) - (setq end-add (point)))) - (smerge-refine-subst beg-del beg-add beg-add end-add - nil 'diff-refine-preproc props-r props-a))))) - (`context - (let* ((middle (save-excursion (re-search-forward "^---"))) - (other middle)) - (while (re-search-forward "^\\(?:!.*\n\\)+" middle t) - (smerge-refine-subst (match-beginning 0) (match-end 0) - (save-excursion - (goto-char other) - (re-search-forward "^\\(?:!.*\n\\)+" end) - (setq other (match-end 0)) - (match-beginning 0)) - other - (if diff-use-changed-face props-c) - 'diff-refine-preproc - (unless diff-use-changed-face props-r) - (unless diff-use-changed-face props-a))))) - (_ ;; Normal diffs. - (let ((beg1 (1+ (point)))) - (when (re-search-forward "^---.*\n" end t) - ;; It's a combined add&remove, so there's something to do. - (smerge-refine-subst beg1 (match-beginning 0) - (match-end 0) end - nil 'diff-refine-preproc props-r props-a)))))))) + (when (diff--some-hunks-p) + (save-excursion + (diff-beginning-of-hunk t) + (let* ((start (point)) + (style (diff-hunk-style)) ;Skips the hunk header as well. + (beg (point)) + (props-c '((diff-mode . fine) (face diff-refine-changed))) + (props-r '((diff-mode . fine) (face diff-refine-removed))) + (props-a '((diff-mode . fine) (face diff-refine-added))) + ;; Be careful to go back to `start' so diff-end-of-hunk gets + ;; to read the hunk header's line info. + (end (progn (goto-char start) (diff-end-of-hunk) (point)))) + + (remove-overlays beg end 'diff-mode 'fine) + + (goto-char beg) + (pcase style + (`unified + (while (re-search-forward "^-" end t) + (let ((beg-del (progn (beginning-of-line) (point))) + beg-add end-add) + (when (and (diff--forward-while-leading-char ?- end) + ;; Allow for "\ No newline at end of file". + (progn (diff--forward-while-leading-char ?\\ end) + (setq beg-add (point))) + (diff--forward-while-leading-char ?+ end) + (progn (diff--forward-while-leading-char ?\\ end) + (setq end-add (point)))) + (smerge-refine-subst beg-del beg-add beg-add end-add + nil 'diff-refine-preproc props-r props-a))))) + (`context + (let* ((middle (save-excursion (re-search-forward "^---"))) + (other middle)) + (while (re-search-forward "^\\(?:!.*\n\\)+" middle t) + (smerge-refine-subst (match-beginning 0) (match-end 0) + (save-excursion + (goto-char other) + (re-search-forward "^\\(?:!.*\n\\)+" end) + (setq other (match-end 0)) + (match-beginning 0)) + other + (if diff-use-changed-face props-c) + 'diff-refine-preproc + (unless diff-use-changed-face props-r) + (unless diff-use-changed-face props-a))))) + (_ ;; Normal diffs. + (let ((beg1 (1+ (point)))) + (when (re-search-forward "^---.*\n" end t) + ;; It's a combined add&remove, so there's something to do. + (smerge-refine-subst beg1 (match-beginning 0) + (match-end 0) end + nil 'diff-refine-preproc props-r props-a))))))))) (defun diff-undo (&optional arg) "Perform `undo', ignoring the buffer's read-only status." -- 2.11.0 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; In GNU Emacs 26.0.50.1 (x86_64-pc-linux-gnu, GTK+ Version 3.22.6) of 2017-01-29 Repository revision: 0073223c23749ffd6bd3f882bc30a82cc37efd2a
GNU bug tracking system
Copyright (C) 1999 Darren O. Benham,
1997,2003 nCipher Corporation Ltd,
1994-97 Ian Jackson.