diff options
| author | Tino Calancha | 2017-01-21 11:54:38 +0900 |
|---|---|---|
| committer | Tino Calancha | 2017-01-21 11:54:38 +0900 |
| commit | 1508b538fd8f8c2e00aadcea42ac36013fad02e3 (patch) | |
| tree | 5d151c617b299ced19824626bd26b7c21a25ce70 /lisp | |
| parent | 82a5e4dc889ecbfa35374616fe9c5edfa23f4504 (diff) | |
| download | emacs-1508b538fd8f8c2e00aadcea42ac36013fad02e3.tar.gz emacs-1508b538fd8f8c2e00aadcea42ac36013fad02e3.zip | |
; Revert "Improve diff-mode navigation/manipulation"
This reverts commit 2c8a7e50d24daf19ea7d86f1cfeaa98a41c56085.
This change causes regressions:
https://lists.gnu.org/archive/html/emacs-devel/2016-11/msg00738.html
The following related commits are reverted as well:
61c6a10e3110490dadac4577cc540053341ff25c
a283d655db88cdcc8cb53d8e2578e1cdf751c84b
6b6abe0dba6a9a2e5f78aac3814421886e7a184f
e5ef59b87da5c2ddfa22f7342efe29b3eea6ed97
73349822cbd6e50526eda9c75453584d73dfca83
Fixes: debbugs:25105, 25400.
Diffstat (limited to 'lisp')
| -rw-r--r-- | lisp/vc/diff-mode.el | 174 |
1 files changed, 34 insertions, 140 deletions
diff --git a/lisp/vc/diff-mode.el b/lisp/vc/diff-mode.el index b50b4a254f4..4e878c404cd 100644 --- a/lisp/vc/diff-mode.el +++ b/lisp/vc/diff-mode.el | |||
| @@ -551,124 +551,26 @@ next hunk if TRY-HARDER is non-nil; otherwise signal an error." | |||
| 551 | 551 | ||
| 552 | ;; Define diff-{hunk,file}-{prev,next} | 552 | ;; Define diff-{hunk,file}-{prev,next} |
| 553 | (easy-mmode-define-navigation | 553 | (easy-mmode-define-navigation |
| 554 | diff--internal-hunk diff-hunk-header-re "hunk" diff-end-of-hunk diff-restrict-view) | 554 | diff-hunk diff-hunk-header-re "hunk" diff-end-of-hunk diff-restrict-view |
| 555 | (when diff-auto-refine-mode | ||
| 556 | (unless (prog1 diff--auto-refine-data | ||
| 557 | (setq diff--auto-refine-data | ||
| 558 | (cons (current-buffer) (point-marker)))) | ||
| 559 | (run-at-time 0.0 nil | ||
| 560 | (lambda () | ||
| 561 | (when diff--auto-refine-data | ||
| 562 | (let ((buffer (car diff--auto-refine-data)) | ||
| 563 | (point (cdr diff--auto-refine-data))) | ||
| 564 | (setq diff--auto-refine-data nil) | ||
| 565 | (with-local-quit | ||
| 566 | (when (buffer-live-p buffer) | ||
| 567 | (with-current-buffer buffer | ||
| 568 | (save-excursion | ||
| 569 | (goto-char point) | ||
| 570 | (diff-refine-hunk)))))))))))) | ||
| 555 | 571 | ||
| 556 | (easy-mmode-define-navigation | 572 | (easy-mmode-define-navigation |
| 557 | diff--internal-file diff-file-header-re "file" diff-end-of-file) | 573 | diff-file diff-file-header-re "file" diff-end-of-file) |
| 558 | |||
| 559 | (defun diff--wrap-navigation (skip-hunk-start | ||
| 560 | what orig | ||
| 561 | header-re goto-start-func count) | ||
| 562 | "Wrap diff-{hunk,file}-{next,prev} for more intuitive behavior. | ||
| 563 | Override the default diff-{hunk,file}-{next,prev} implementation | ||
| 564 | by skipping any lines that are associated with this hunk/file but | ||
| 565 | precede the hunk-start marker. For instance, a diff file could | ||
| 566 | contain | ||
| 567 | |||
| 568 | diff --git a/lisp/vc/diff-mode.el b/lisp/vc/diff-mode.el | ||
| 569 | index 923de9a..6b1c24f 100644 | ||
| 570 | --- a/lisp/vc/diff-mode.el | ||
| 571 | +++ b/lisp/vc/diff-mode.el | ||
| 572 | @@ -590,6 +590,22 @@ | ||
| 573 | ....... | ||
| 574 | |||
| 575 | If a point is on 'index', then the point is considered to be in | ||
| 576 | this first hunk. Move the point to the @@... marker before | ||
| 577 | executing the default diff-hunk-next/prev implementation to move | ||
| 578 | to the NEXT marker." | ||
| 579 | (if (not skip-hunk-start) | ||
| 580 | (funcall orig count) | ||
| 581 | |||
| 582 | (let ((start (point))) | ||
| 583 | (funcall goto-start-func) | ||
| 584 | |||
| 585 | ;; Trap the error. | ||
| 586 | (condition-case nil | ||
| 587 | (funcall orig count) | ||
| 588 | (error nil)) | ||
| 589 | |||
| 590 | (when (not (looking-at header-re)) | ||
| 591 | (goto-char start) | ||
| 592 | (user-error (format "No %s" what))) | ||
| 593 | |||
| 594 | ;; We successfully moved to the next/prev hunk/file. Apply the | ||
| 595 | ;; auto-refinement if needed | ||
| 596 | (when diff-auto-refine-mode | ||
| 597 | (unless (prog1 diff--auto-refine-data | ||
| 598 | (setq diff--auto-refine-data | ||
| 599 | (cons (current-buffer) (point-marker)))) | ||
| 600 | (run-at-time 0.0 nil | ||
| 601 | (lambda () | ||
| 602 | (when diff--auto-refine-data | ||
| 603 | (let ((buffer (car diff--auto-refine-data)) | ||
| 604 | (point (cdr diff--auto-refine-data))) | ||
| 605 | (setq diff--auto-refine-data nil) | ||
| 606 | (with-local-quit | ||
| 607 | (when (buffer-live-p buffer) | ||
| 608 | (with-current-buffer buffer | ||
| 609 | (save-excursion | ||
| 610 | (goto-char point) | ||
| 611 | (diff-refine-hunk)))))))))))))) | ||
| 612 | |||
| 613 | ;; These functions all take a skip-hunk-start argument which controls | ||
| 614 | ;; whether we skip pre-hunk-start text or not. In interactive uses we | ||
| 615 | ;; always want to do this, but the simple behavior is still necessary | ||
| 616 | ;; to, for example, avoid an infinite loop: | ||
| 617 | ;; | ||
| 618 | ;; diff-hunk-next calls | ||
| 619 | ;; diff--wrap-navigation calls | ||
| 620 | ;; diff-bounds-of-hunk calls | ||
| 621 | ;; diff-beginning-of-hunk calls | ||
| 622 | ;; diff-hunk-next | ||
| 623 | ;; | ||
| 624 | ;; Here the outer diff-hunk-next has skip-hunk-start set to t, but the | ||
| 625 | ;; inner one does not, which breaks the loop. | ||
| 626 | (defun diff-hunk-prev (&optional count skip-hunk-start) | ||
| 627 | "Go to the previous COUNT'th hunk." | ||
| 628 | (interactive (list (prefix-numeric-value current-prefix-arg) t)) | ||
| 629 | (diff--wrap-navigation | ||
| 630 | skip-hunk-start | ||
| 631 | "prev hunk" | ||
| 632 | 'diff--internal-hunk-prev | ||
| 633 | diff-hunk-header-re | ||
| 634 | (lambda () (goto-char (car (diff-bounds-of-hunk)))) | ||
| 635 | count)) | ||
| 636 | |||
| 637 | (defun diff-hunk-next (&optional count skip-hunk-start) | ||
| 638 | "Go to the next COUNT'th hunk." | ||
| 639 | (interactive (list (prefix-numeric-value current-prefix-arg) t)) | ||
| 640 | (diff--wrap-navigation | ||
| 641 | skip-hunk-start | ||
| 642 | "next hunk" | ||
| 643 | 'diff--internal-hunk-next | ||
| 644 | diff-hunk-header-re | ||
| 645 | (lambda () (goto-char (car (diff-bounds-of-hunk)))) | ||
| 646 | count)) | ||
| 647 | |||
| 648 | (defun diff-file-prev (&optional count skip-hunk-start) | ||
| 649 | "Go to the previous COUNT'th file." | ||
| 650 | (interactive (list (prefix-numeric-value current-prefix-arg) t)) | ||
| 651 | (diff--wrap-navigation | ||
| 652 | skip-hunk-start | ||
| 653 | "prev file" | ||
| 654 | 'diff--internal-file-prev | ||
| 655 | diff-file-header-re | ||
| 656 | (lambda () (goto-char (car (diff-bounds-of-file))) (diff--internal-hunk-next)) | ||
| 657 | count)) | ||
| 658 | |||
| 659 | (defun diff-file-next (&optional count skip-hunk-start) | ||
| 660 | "Go to the next COUNT'th file." | ||
| 661 | (interactive (list (prefix-numeric-value current-prefix-arg) t)) | ||
| 662 | (diff--wrap-navigation | ||
| 663 | skip-hunk-start | ||
| 664 | "next file" | ||
| 665 | 'diff--internal-file-next | ||
| 666 | diff-file-header-re | ||
| 667 | (lambda () (goto-char (car (diff-bounds-of-file))) (diff--internal-hunk-next)) | ||
| 668 | count)) | ||
| 669 | |||
| 670 | |||
| 671 | |||
| 672 | 574 | ||
| 673 | (defun diff-bounds-of-hunk () | 575 | (defun diff-bounds-of-hunk () |
| 674 | "Return the bounds of the diff hunk at point. | 576 | "Return the bounds of the diff hunk at point. |
| @@ -679,13 +581,12 @@ point is in a file header, return the bounds of the next hunk." | |||
| 679 | (let ((pos (point)) | 581 | (let ((pos (point)) |
| 680 | (beg (diff-beginning-of-hunk t)) | 582 | (beg (diff-beginning-of-hunk t)) |
| 681 | (end (diff-end-of-hunk))) | 583 | (end (diff-end-of-hunk))) |
| 682 | (cond ((> end pos) | 584 | (cond ((>= end pos) |
| 683 | (list beg end)) | 585 | (list beg end)) |
| 684 | ;; If this hunk ends above POS, consider the next hunk. | 586 | ;; If this hunk ends above POS, consider the next hunk. |
| 685 | ((re-search-forward diff-hunk-header-re nil t) | 587 | ((re-search-forward diff-hunk-header-re nil t) |
| 686 | (list (match-beginning 0) (diff-end-of-hunk))) | 588 | (list (match-beginning 0) (diff-end-of-hunk))) |
| 687 | ;; There's no next hunk, so just take the one we have. | 589 | (t (error "No hunk found")))))) |
| 688 | (t (list beg end)))))) | ||
| 689 | 590 | ||
| 690 | (defun diff-bounds-of-file () | 591 | (defun diff-bounds-of-file () |
| 691 | "Return the bounds of the file segment at point. | 592 | "Return the bounds of the file segment at point. |
| @@ -771,7 +672,7 @@ data such as \"Index: ...\" and such." | |||
| 771 | (setq prevfile nextfile)) | 672 | (setq prevfile nextfile)) |
| 772 | (if (and previndex (numberp prevfile) (< previndex prevfile)) | 673 | (if (and previndex (numberp prevfile) (< previndex prevfile)) |
| 773 | (setq prevfile previndex)) | 674 | (setq prevfile previndex)) |
| 774 | (if (numberp prevfile) | 675 | (if (and (numberp prevfile) (<= prevfile start)) |
| 775 | (progn | 676 | (progn |
| 776 | (goto-char prevfile) | 677 | (goto-char prevfile) |
| 777 | ;; Now skip backward over the leading junk we may have before the | 678 | ;; Now skip backward over the leading junk we may have before the |
| @@ -1764,9 +1665,8 @@ SRC and DST are the two variants of text as returned by `diff-hunk-text'. | |||
| 1764 | SWITCHED is non-nil if the patch is already applied. | 1665 | SWITCHED is non-nil if the patch is already applied. |
| 1765 | NOPROMPT, if non-nil, means not to prompt the user." | 1666 | NOPROMPT, if non-nil, means not to prompt the user." |
| 1766 | (save-excursion | 1667 | (save-excursion |
| 1767 | (let* ((hunk-bounds (diff-bounds-of-hunk)) | 1668 | (let* ((other (diff-xor other-file diff-jump-to-old-file)) |
| 1768 | (other (diff-xor other-file diff-jump-to-old-file)) | 1669 | (char-offset (- (point) (diff-beginning-of-hunk t))) |
| 1769 | (char-offset (- (point) (goto-char (car hunk-bounds)))) | ||
| 1770 | ;; Check that the hunk is well-formed. Otherwise diff-mode and | 1670 | ;; Check that the hunk is well-formed. Otherwise diff-mode and |
| 1771 | ;; the user may disagree on what constitutes the hunk | 1671 | ;; the user may disagree on what constitutes the hunk |
| 1772 | ;; (e.g. because an empty line truncates the hunk mid-course), | 1672 | ;; (e.g. because an empty line truncates the hunk mid-course), |
| @@ -1775,7 +1675,7 @@ NOPROMPT, if non-nil, means not to prompt the user." | |||
| 1775 | ;; Suppress check when NOPROMPT is non-nil (Bug#3033). | 1675 | ;; Suppress check when NOPROMPT is non-nil (Bug#3033). |
| 1776 | (_ (unless noprompt (diff-sanity-check-hunk))) | 1676 | (_ (unless noprompt (diff-sanity-check-hunk))) |
| 1777 | (hunk (buffer-substring | 1677 | (hunk (buffer-substring |
| 1778 | (point) (cadr hunk-bounds))) | 1678 | (point) (save-excursion (diff-end-of-hunk) (point)))) |
| 1779 | (old (diff-hunk-text hunk reverse char-offset)) | 1679 | (old (diff-hunk-text hunk reverse char-offset)) |
| 1780 | (new (diff-hunk-text hunk (not reverse) char-offset)) | 1680 | (new (diff-hunk-text hunk (not reverse) char-offset)) |
| 1781 | ;; Find the location specification. | 1681 | ;; Find the location specification. |
| @@ -1883,15 +1783,8 @@ With a prefix argument, REVERSE the hunk." | |||
| 1883 | ;; Display BUF in a window | 1783 | ;; Display BUF in a window |
| 1884 | (set-window-point (display-buffer buf) (+ (car pos) (cdr new))) | 1784 | (set-window-point (display-buffer buf) (+ (car pos) (cdr new))) |
| 1885 | (diff-hunk-status-msg line-offset (diff-xor switched reverse) nil) | 1785 | (diff-hunk-status-msg line-offset (diff-xor switched reverse) nil) |
| 1886 | |||
| 1887 | ;; Advance to the next hunk with skip-hunk-start set to t | ||
| 1888 | ;; because we want the behavior of moving to the next logical | ||
| 1889 | ;; hunk, not the original behavior where were would sometimes | ||
| 1890 | ;; stay on the current hunk. This is the behavior we get when | ||
| 1891 | ;; navigating through hunks interactively, and we want it when | ||
| 1892 | ;; applying hunks too (see http://debbugs.gnu.org/17544). | ||
| 1893 | (when diff-advance-after-apply-hunk | 1786 | (when diff-advance-after-apply-hunk |
| 1894 | (diff-hunk-next nil t)))))) | 1787 | (diff-hunk-next)))))) |
| 1895 | 1788 | ||
| 1896 | 1789 | ||
| 1897 | (defun diff-test-hunk (&optional reverse) | 1790 | (defun diff-test-hunk (&optional reverse) |
| @@ -1972,15 +1865,14 @@ For use in `add-log-current-defun-function'." | |||
| 1972 | (defun diff-ignore-whitespace-hunk () | 1865 | (defun diff-ignore-whitespace-hunk () |
| 1973 | "Re-diff the current hunk, ignoring whitespace differences." | 1866 | "Re-diff the current hunk, ignoring whitespace differences." |
| 1974 | (interactive) | 1867 | (interactive) |
| 1975 | (let* ((hunk-bounds (diff-bounds-of-hunk)) | 1868 | (let* ((char-offset (- (point) (diff-beginning-of-hunk t))) |
| 1976 | (char-offset (- (point) (goto-char (car hunk-bounds)))) | ||
| 1977 | (opts (pcase (char-after) (?@ "-bu") (?* "-bc") (_ "-b"))) | 1869 | (opts (pcase (char-after) (?@ "-bu") (?* "-bc") (_ "-b"))) |
| 1978 | (line-nb (and (or (looking-at "[^0-9]+\\([0-9]+\\)") | 1870 | (line-nb (and (or (looking-at "[^0-9]+\\([0-9]+\\)") |
| 1979 | (error "Can't find line number")) | 1871 | (error "Can't find line number")) |
| 1980 | (string-to-number (match-string 1)))) | 1872 | (string-to-number (match-string 1)))) |
| 1981 | (inhibit-read-only t) | 1873 | (inhibit-read-only t) |
| 1982 | (hunk (delete-and-extract-region | 1874 | (hunk (delete-and-extract-region |
| 1983 | (point) (cadr hunk-bounds))) | 1875 | (point) (save-excursion (diff-end-of-hunk) (point)))) |
| 1984 | (lead (make-string (1- line-nb) ?\n)) ;Line nums start at 1. | 1876 | (lead (make-string (1- line-nb) ?\n)) ;Line nums start at 1. |
| 1985 | (file1 (make-temp-file "diff1")) | 1877 | (file1 (make-temp-file "diff1")) |
| 1986 | (file2 (make-temp-file "diff2")) | 1878 | (file2 (make-temp-file "diff2")) |
| @@ -2076,14 +1968,16 @@ Return new point, if it was moved." | |||
| 2076 | (interactive) | 1968 | (interactive) |
| 2077 | (require 'smerge-mode) | 1969 | (require 'smerge-mode) |
| 2078 | (save-excursion | 1970 | (save-excursion |
| 2079 | (let* ((hunk-bounds (diff-bounds-of-hunk)) | 1971 | (diff-beginning-of-hunk t) |
| 2080 | (style (progn (goto-char (car hunk-bounds)) | 1972 | (let* ((start (point)) |
| 2081 | (diff-hunk-style))) ;Skips the hunk header as well. | 1973 | (style (diff-hunk-style)) ;Skips the hunk header as well. |
| 2082 | (beg (point)) | 1974 | (beg (point)) |
| 2083 | (end (cadr hunk-bounds)) | ||
| 2084 | (props-c '((diff-mode . fine) (face diff-refine-changed))) | 1975 | (props-c '((diff-mode . fine) (face diff-refine-changed))) |
| 2085 | (props-r '((diff-mode . fine) (face diff-refine-removed))) | 1976 | (props-r '((diff-mode . fine) (face diff-refine-removed))) |
| 2086 | (props-a '((diff-mode . fine) (face diff-refine-added)))) | 1977 | (props-a '((diff-mode . fine) (face diff-refine-added))) |
| 1978 | ;; Be careful to go back to `start' so diff-end-of-hunk gets | ||
| 1979 | ;; to read the hunk header's line info. | ||
| 1980 | (end (progn (goto-char start) (diff-end-of-hunk) (point)))) | ||
| 2087 | 1981 | ||
| 2088 | (remove-overlays beg end 'diff-mode 'fine) | 1982 | (remove-overlays beg end 'diff-mode 'fine) |
| 2089 | 1983 | ||