/ diff-hl-flydiff.el
diff-hl-flydiff.el
1 ;; Copyright (C) 2015-2025 Free Software Foundation, Inc. -*- lexical-binding: t -*- 2 3 ;; Author: Jonathan Hayase <PythonNut@gmail.com> 4 ;; URL: https://github.com/dgutov/diff-hl 5 6 ;; This file is part of GNU Emacs. 7 8 ;; GNU Emacs is free software: you can redistribute it and/or modify 9 ;; it under the terms of the GNU General Public License as published by 10 ;; the Free Software Foundation, either version 3 of the License, or 11 ;; (at your option) any later version. 12 13 ;; GNU Emacs is distributed in the hope that it will be useful, 14 ;; but WITHOUT ANY WARRANTY; without even the implied warranty of 15 ;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 16 ;; GNU General Public License for more details. 17 18 ;; You should have received a copy of the GNU General Public License 19 ;; along with GNU Emacs. If not, see <https://www.gnu.org/licenses/>. 20 21 ;;; Commentary: 22 23 ;; This mode enables diffing on-the-fly (i.e. without saving the buffer first) 24 ;; Toggle in all buffers with M-x diff-hl-flydiff-mode 25 26 ;;; Code: 27 28 (require 'diff-hl) 29 (require 'diff) 30 31 (defgroup diff-hl-flydiff nil 32 "Highlight changes on the fly" 33 :group 'diff-hl) 34 35 (defcustom diff-hl-flydiff-delay 0.3 36 "The idle delay in seconds before highlighting is updated." 37 :type 'number) 38 39 (defvar diff-hl-flydiff-modified-tick nil) 40 (defvar diff-hl-flydiff-timer nil) 41 (make-variable-buffer-local 'diff-hl-flydiff-modified-tick) 42 43 (defun diff-hl-flydiff-changes-buffer (file backend &optional new-rev buffer) 44 (setq buffer (or buffer " *diff-hl-diff*")) 45 (setq diff-hl-flydiff-modified-tick (buffer-chars-modified-tick)) 46 (if new-rev 47 (diff-hl-with-diff-switches 48 (diff-hl-diff-against-reference file backend buffer new-rev)) 49 (diff-hl-diff-buffer-with-reference file buffer backend))) 50 51 (defun diff-hl-flydiff-update () 52 (unless (or 53 (not diff-hl-mode) 54 (eq diff-hl-flydiff-modified-tick (buffer-chars-modified-tick)) 55 (not buffer-file-name) 56 (file-remote-p default-directory) 57 (not (file-exists-p buffer-file-name))) 58 (diff-hl-update))) 59 60 (defun diff-hl-flydiff/modified-p (_state) 61 (buffer-modified-p)) 62 63 ;;;###autoload 64 (define-minor-mode diff-hl-flydiff-mode 65 "Perform highlighting on-the-fly. 66 This is a global minor mode. It alters how `diff-hl-mode' works." 67 :lighter "" :global t 68 (and diff-hl-flydiff-timer 69 (cancel-timer diff-hl-flydiff-timer)) 70 71 (if diff-hl-flydiff-mode 72 (progn 73 (advice-add 'diff-hl-overlay-modified :override #'ignore) 74 75 (advice-add 'diff-hl-modified-p :before-until 76 #'diff-hl-flydiff/modified-p) 77 (advice-add 'diff-hl-changes-buffer :override 78 #'diff-hl-flydiff-changes-buffer) 79 (setq diff-hl-flydiff-timer 80 (run-with-idle-timer diff-hl-flydiff-delay t #'diff-hl-flydiff-update))) 81 82 (advice-remove 'diff-hl-overlay-modified #'ignore) 83 84 (advice-remove 'diff-hl-modified-p #'diff-hl-flydiff/modified-p) 85 (advice-remove 'diff-hl-changes-buffer #'diff-hl-flydiff-changes-buffer))) 86 87 (provide 'diff-hl-flydiff)