[Top][All Lists]

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

Re: Type Ahead Find

From: Juri Linkov
Subject: Re: Type Ahead Find
Date: Sun, 20 Mar 2005 22:19:48 +0200
User-agent: Gnus/5.110002 (No Gnus v0.2) Emacs/22.0.50 (gnu/linux)

Richard Stallman <address@hidden> writes:
>       But it allows to narrow the search only
>     to specific text part (such as e.g. in Firefox typing a ' before the
>     search string searches only links) which is currently not easily
>     implementable in Emacs.
> Making such a feature useful, and not intolerable, in the context
> of Emacs is not a simple matter.  I think I'd rather turn off any
> feature that makes some printing characters special in isearch.

The change I proposed has nothing to do with making some characters
special in isearch.

> Please let's not think about this now.  If you'd like to work
> on new features for after the release, how about implementing
> some of the features listed in etc/TODO?

This is not a new feature.  This is the change very closely related
to other recent fixes in isearch.el.  I want to finish all fixes
related to isearch.el before the next release.

Essentially, my proposed change is to make configurable the
currently hard-coded constraint imposed by `isearch-range-invisible'
in `isearch-search'.  The new variable `isearch-success-function'
will allow to override it with a user-defined function.

Also in the course of preparing this change I noticed some problems
in isearch.el related to searching of invisible text:

The lazy highlighting feature creates overlays even for matches inside
invisible texts.  A solution is to create a loop similar to the while-loop
in `isearch-search', but instead of `isearch-range-invisible' (which also
opens invisible overlays) to use the following condition in

    (text-property-any (match-beginning 0) (match-end 0)
                       'invisible nil)

This condition seems to be more correct even if it lazy-highlights
partly hidden matches.  An alternative condition

    (not (text-property-not-all (match-beginning 0) (match-end 0)
                                'invisible nil))

that lazy-highlights a match only if it is fully visible, doesn't
follow the logic of `isearch-range-invisible' used in `isearch-search'
which matches partly invisible text.

The current version of a patch is below:

Index: lisp/isearch.el
RCS file: /cvsroot/emacs/emacs/lisp/isearch.el,v
retrieving revision 1.261
diff -u -w -b -r1.261 isearch.el
--- lisp/isearch.el     18 Mar 2005 09:59:31 -0000      1.261
+++ lisp/isearch.el     20 Mar 2005 20:03:07 -0000
@@ -165,6 +165,11 @@
   "Function to save a function restoring the mode-specific isearch state
 to the search status stack.")
+(defvar isearch-success-function nil
+  "Function to report whether the new search match is considered successful.
+The function has two arguments: the positions of start and end of text
+matched by search.")
 ;; Search ring.
 (defvar search-ring nil
@@ -2039,7 +2046,8 @@
       (setq isearch-case-fold-search
            (isearch-no-upper-case-p isearch-string isearch-regexp)))
   (condition-case lossage
-      (let ((inhibit-point-motion-hooks search-invisible)
+      (let ((inhibit-point-motion-hooks
+            (and (not isearch-success-function) search-invisible))
            (inhibit-quit nil)
            (case-fold-search isearch-case-fold-search)
            (search-spaces-regexp search-whitespace-regexp)
@@ -2052,12 +2060,15 @@
                 isearch-string nil t))
          ;; Clear RETRY unless we matched some invisible text
          ;; and we aren't supposed to do that.
-         (if (or (eq search-invisible t)
-                 (not isearch-success)
+         (if (or (not isearch-success)
                  (bobp) (eobp)
                  (= (match-beginning 0) (match-end 0))
+                 (if isearch-success-function
+                     (funcall isearch-success-function
+                              (match-beginning 0) (match-end 0))
+                   (or (eq search-invisible t)
                  (not (isearch-range-invisible
-                       (match-beginning 0) (match-end 0))))
+                             (match-beginning 0) (match-end 0))))))
              (setq retry nil)))
        (setq isearch-just-started nil)
        (if isearch-success
@@ -2369,7 +2381,6 @@
     ;; something important did indeed change
     (lazy-highlight-cleanup t) ;kill old loop & remove overlays
-    (when (not isearch-error)
       (setq isearch-lazy-highlight-start-limit beg
            isearch-lazy-highlight-end-limit end)
       (setq isearch-lazy-highlight-window       (selected-window)
@@ -2384,7 +2395,7 @@
       (unless (equal isearch-string "")
        (setq isearch-lazy-highlight-timer
              (run-with-idle-timer lazy-highlight-initial-delay nil
-                                  'isearch-lazy-highlight-update))))))
+                                'isearch-lazy-highlight-update)))))
 (defun isearch-lazy-highlight-search ()
   "Search ahead for the next or previous match, for lazy highlighting.
@@ -2393,9 +2404,9 @@
        (isearch-regexp isearch-lazy-highlight-regexp)
        (search-spaces-regexp search-whitespace-regexp))
     (condition-case nil
-       (funcall (isearch-search-fun)
-                isearch-lazy-highlight-last-string
-                (if isearch-forward
+       (let ((retry t)
+             (success nil)
+             (bound (if isearch-forward
                     (min (or isearch-lazy-highlight-end-limit (point-max))
                          (if isearch-lazy-highlight-wrapped
@@ -2403,8 +2414,22 @@
                   (max (or isearch-lazy-highlight-start-limit (point-min))
                        (if isearch-lazy-highlight-wrapped
-                         (window-start))))
-                t)
+                             (window-start))))))
+         (while retry
+           (setq success
+                 (funcall (isearch-search-fun)
+                          isearch-lazy-highlight-last-string
+                          bound t))
+           (if (or (not success)
+                   (eq (point) bound)
+                   (if isearch-success-function
+                       (funcall isearch-success-function
+                                (match-beginning 0) (match-end 0))
+                     (text-property-any
+                      (match-beginning 0) (match-end 0)
+                      'invisible nil)))
+               (setq retry nil)))
+         success)
       (error nil))))
 (defun isearch-lazy-highlight-update ()

Juri Linkov

reply via email to

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