aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorJuri Linkov2022-06-12 19:45:15 +0300
committerJuri Linkov2022-06-12 19:45:15 +0300
commite42d4d2ddf4f193c2e3b9391fd6b4cb4ea3ba4b3 (patch)
tree6aeb2c0912b0e3e065de0ef96602df8d650ede05
parent1dd92bb7b8817038577626a13d7464a09e4d8a27 (diff)
downloademacs-e42d4d2ddf4f193c2e3b9391fd6b4cb4ea3ba4b3.tar.gz
emacs-e42d4d2ddf4f193c2e3b9391fd6b4cb4ea3ba4b3.zip
* lisp/isearch.el (isearch-search-fun-in-text-property): Handle ^/$ specially.
When the regexp contains ^ or $ then use a temporary buffer to find matches at the beginning/end of the region with the given text property (bug#14013).
-rw-r--r--etc/NEWS6
-rw-r--r--lisp/isearch.el68
2 files changed, 62 insertions, 12 deletions
diff --git a/etc/NEWS b/etc/NEWS
index 424d1250c33..6f00a51a708 100644
--- a/etc/NEWS
+++ b/etc/NEWS
@@ -1575,6 +1575,12 @@ If non-nil (which is the default), hitting 'RET' or 'mouse-1' on
1575the directory components at the directory displayed at the start of 1575the directory components at the directory displayed at the start of
1576the buffer will take you to that directory. 1576the buffer will take you to that directory.
1577 1577
1578---
1579*** Search and replace in Dired/Wdired supports more regexps.
1580For example, the regexp ".*" will match only characters that are part
1581of the file name. Also "^.*$" can be used to match at the beginning
1582of the file name and at the end of the file name.
1583
1578** Exif 1584** Exif
1579 1585
1580--- 1586---
diff --git a/lisp/isearch.el b/lisp/isearch.el
index 5fbfb724a3c..fb52bfe30cb 100644
--- a/lisp/isearch.el
+++ b/lisp/isearch.el
@@ -4456,12 +4456,12 @@ LAX-WHITESPACE: The value of `isearch-lax-whitespace' and
4456 4456
4457 4457
4458(defun isearch-search-fun-in-text-property (property &optional search-fun) 4458(defun isearch-search-fun-in-text-property (property &optional search-fun)
4459 "Return the function that searches inside fields. 4459 "Return the function that searches inside text properties.
4460The arg PROPERTY defines the name of the text property that 4460The arg PROPERTY defines the name of the text property, and the search
4461delimits fields in the current buffer. Then the search will be 4461will be narrowed to match only inside such text properties in the current
4462narrowed to match only on such text properties. The optional arg 4462buffer. The optional arg SEARCH-FUN can provide the default search
4463SEARCH-FUN can provide the default search function which is 4463function which is by default is the same as returned by
4464by default is the same as returned by `isearch-search-fun-default'." 4464`isearch-search-fun-default'."
4465 (lambda (string &optional bound noerror count) 4465 (lambda (string &optional bound noerror count)
4466 (let* ((old (point)) 4466 (let* ((old (point))
4467 ;; Check if point is already on the property. 4467 ;; Check if point is already on the property.
@@ -4469,7 +4469,16 @@ by default is the same as returned by `isearch-search-fun-default'."
4469 (if isearch-forward old (max (1- old) (point-min))) 4469 (if isearch-forward old (max (1- old) (point-min)))
4470 property) 4470 property)
4471 old)) 4471 old))
4472 end found) 4472 end found (i 0)
4473 (subregexp
4474 (and isearch-regexp
4475 (save-match-data
4476 (catch 'subregexp
4477 (while (string-match "\\^\\|\\$" string i)
4478 (setq i (match-end 0))
4479 (when (subregexp-context-p string (match-beginning 0))
4480 ;; The ^/$ is not inside a char-range or escaped.
4481 (throw 'subregexp t))))))))
4473 ;; Otherwise, try to search for the next property. 4482 ;; Otherwise, try to search for the next property.
4474 (unless beg 4483 (unless beg
4475 (setq beg (if isearch-forward 4484 (setq beg (if isearch-forward
@@ -4482,12 +4491,47 @@ by default is the same as returned by `isearch-search-fun-default'."
4482 (setq end (if isearch-forward 4491 (setq end (if isearch-forward
4483 (next-single-property-change beg property) 4492 (next-single-property-change beg property)
4484 (previous-single-property-change beg property))) 4493 (previous-single-property-change beg property)))
4485 (setq found (funcall (or search-fun (isearch-search-fun-default)) 4494 ;; Handle ^/$ specially by matching in a temporary buffer.
4486 string (if bound (if isearch-forward 4495 (if subregexp
4487 (min bound end) 4496 (let* ((prop-beg
4488 (max bound end)) 4497 (if (or (if isearch-forward (bobp) (eobp))
4489 end) 4498 (null (get-text-property
4499 (+ (point) (if isearch-forward -1 0))
4500 property)))
4501 ;; Already at the beginning of the field.
4502 beg
4503 ;; Get the real beginning of the field when
4504 ;; the search was started in the middle.
4505 (if isearch-forward
4506 (previous-single-property-change beg property)
4507 (next-single-property-change beg property))))
4508 (substring (buffer-substring prop-beg end))
4509 (offset (if isearch-forward prop-beg end))
4510 match-data)
4511 (with-temp-buffer
4512 (insert substring)
4513 (goto-char (- beg offset -1))
4514 ;; Apply ^/$ regexp on the whole extracted substring.
4515 (setq found (funcall
4516 (or search-fun (isearch-search-fun-default))
4517 string (and bound (max (point-min)
4518 (min (point-max)
4519 (- bound offset -1))))
4490 noerror count)) 4520 noerror count))
4521 ;; Adjust match data as if it's matched in original buffer.
4522 (when found
4523 (setq found (+ found offset -1)
4524 match-data (mapcar (lambda (m) (+ m offset -1))
4525 (match-data)))))
4526 (when match-data (set-match-data match-data)))
4527 (setq found (funcall
4528 (or search-fun (isearch-search-fun-default))
4529 string (if bound (if isearch-forward
4530 (min bound end)
4531 (max bound end))
4532 end)
4533 noerror count)))
4534 ;; Get the next text property.
4491 (unless found 4535 (unless found
4492 (setq beg (if isearch-forward 4536 (setq beg (if isearch-forward
4493 (next-single-property-change end property) 4537 (next-single-property-change end property)