emacs-elpa-diffs
[Top][All Lists]
Advanced

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

[elpa] master 4f1bbc1 151/399: swiper.el (swiper-isearch-function): Full


From: Oleh Krehel
Subject: [elpa] master 4f1bbc1 151/399: swiper.el (swiper-isearch-function): Full point history for DEL
Date: Sat, 20 Jul 2019 14:57:13 -0400 (EDT)

branch: master
commit 4f1bbc177a871eaab2edc4d701ef8f63d2715cb4
Author: Oleh Krehel <address@hidden>
Commit: Oleh Krehel <address@hidden>

    swiper.el (swiper-isearch-function): Full point history for DEL
    
    * swiper.el (swiper--isearch-point-history): Store point positions for
      all previous states of the input. This way, if the input is restored
      to an older state with "DEL", the point will also be restored.
    
    * ivy-test.el (swiper-isearch): Add test, making sure the behavior is
      the same as that of `isearch-forward-regexp'.
---
 ivy-test.el | 50 ++++++++++++++++++++++++++++++++++++++++++++++++++
 swiper.el   | 30 ++++++++++++++++++++----------
 2 files changed, 70 insertions(+), 10 deletions(-)

diff --git a/ivy-test.el b/ivy-test.el
index 4579894..4a24366 100644
--- a/ivy-test.el
+++ b/ivy-test.el
@@ -1003,6 +1003,56 @@ a buffer visiting a file."
       (counsel--grep-regex "ivy"))
     "(i)[^v\n]*(v)[^y\n]*(y)")))
 
+(defmacro ivy-with-text (text &rest body)
+  (let ((old-bindings
+         (delq nil (mapcar
+                    (lambda (x)
+                      (when (and (listp x)
+                                 (eq (car x) 'global-set-key))
+                        (let ((key (eval (cadr x))))
+                          (list key (lookup-key global-map key)))))
+                    body))))
+    `(let ((temp-buffer (generate-new-buffer " *temp*")))
+       (save-window-excursion
+         (unwind-protect
+              (progn
+                (switch-to-buffer temp-buffer)
+                (insert ,text)
+                (search-backward "|")
+                (delete-char 1)
+                (setq current-prefix-arg nil)
+                ,@(mapcar (lambda (x)
+                            (if (and (listp x)
+                                     (stringp (car x)))
+                                `(execute-kbd-macro
+                                  (vconcat ,@(mapcar #'kbd x)))
+                              x))
+                          body)
+                (insert "|")
+                (buffer-substring-no-properties
+                 (point-min)
+                 (point-max)))
+           (dolist (old-binding ',old-bindings)
+             (apply #'global-set-key old-binding))
+           (and (buffer-name temp-buffer)
+                (kill-buffer temp-buffer)))))))
+
+(ert-deftest swiper-isearch ()
+  (should
+   (string=
+    (ivy-with-text
+     "abc\na|sdf123 def\ndem"
+     (global-set-key (kbd "C-s") #'isearch-forward-regexp)
+     ("C-s" "de" "" "RET"))
+    "abc\nasd|f123 def\ndem"))
+  (should
+   (string=
+    (ivy-with-text
+     "abc\na|sdf123 def\ndem"
+     (global-set-key (kbd "C-s") #'swiper-isearch)
+     ("C-s" "de" "" "RET"))
+    "abc\nasd|f123 def\ndem")))
+
 (provide 'ivy-test)
 
 ;;; ivy-test.el ends here
diff --git a/swiper.el b/swiper.el
index 960010d..60a8d37 100644
--- a/swiper.el
+++ b/swiper.el
@@ -1132,24 +1132,32 @@ See `ivy-format-function' for further information."
     res))
 
 ;;* `swiper-isearch'
-(defvar swiper--isearch-last-point nil)
+(defvar swiper--isearch-point-history nil
+  "Store the current input and point history for a single search.
+Each element is a cons cell of an input and a point position that
+corresponds to it.
+
+This ensures that if the user enters \"ab\", the point will
+come back to the same place as when \"a\" was initially entered.")
 
 (defun swiper-isearch-function (str)
   "Collect STR matches in the current buffer for `swiper-isearch'."
   (unless (string= str "")
-    (let ((re-full (funcall ivy--regex-function str))
-          re
-          cands
-          idx-found
-          (idx 0))
-      (setq re (ivy-re-to-str re-full))
+    (let* ((re-full (funcall ivy--regex-function str))
+           (re (ivy-re-to-str re-full))
+           (pt-hist (cdr (assoc str swiper--isearch-point-history)))
+           cands
+           idx-found
+           (idx 0))
       (with-ivy-window
         (save-excursion
           (goto-char (point-min))
           (while (re-search-forward re nil t)
             (unless idx-found
-              (when (>= (match-beginning 0) swiper--isearch-last-point)
-                (setq swiper--isearch-last-point (match-beginning 0))
+              (when (or
+                     (eq (match-beginning 0) pt-hist)
+                     (>= (match-beginning 0) (cdar 
swiper--isearch-point-history)))
+                (push (cons str (match-beginning 0)) 
swiper--isearch-point-history)
                 (setq idx-found idx)))
             (cl-incf idx)
             (let ((line (buffer-substring
@@ -1186,7 +1194,9 @@ See `ivy-format-function' for further information."
   "A `swiper' that's not line-based."
   (interactive)
   (swiper--init)
-  (setq swiper--isearch-last-point (line-beginning-position))
+  (setq swiper--isearch-point-history
+        (list
+         (cons "" (line-beginning-position))))
   (let ((ivy-fixed-height-minibuffer t)
         (cursor-in-non-selected-windows nil)
         (swiper-min-highlight 1)



reply via email to

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