Hello, everyone! I noticed that sometimes (sentence-at-point) doesn't
return a string in Org Mode, like when you call it from "Is this" in the
first item in this list, because the previous sentence ended with a :
instead of a sentence-ending mark.

----------------------------------------------------------------
This sentence is before the list.  There's one here.  This is a test:

- Is this the first sentence?  There is another.
- This is the third sentence.
- Some
- are
- over several lines!
----------------------------------------------------------------

I've attached a patch that should fix it, including a test. My copyright
papers should be on file with the FSF. Hope this helps!
>From 0dfb6da2d721e155c1fb36b4f85f8f3ad839d1a4 Mon Sep 17 00:00:00 2001
From: Sacha Chua <[email protected]>
Date: Wed, 11 Mar 2026 14:32:20 -0400
Subject: [PATCH] org.el: Handle sentence boundaries for thing-at-point

* lisp/org.el (org-mode): Handle sentence boundaries.
(org--bounds-of-sentence-at-point): Handle sentence boundaries.
* testing/lisp/test-org.el (test-org/thing-at-point/sentence): New test.
---
 lisp/org.el              | 25 +++++++++++++++++++++++--
 testing/lisp/test-org.el | 36 ++++++++++++++++++++++++++++++++++--
 2 files changed, 57 insertions(+), 4 deletions(-)

diff --git a/lisp/org.el b/lisp/org.el
index fc51d4ba3..769e93bfb 100644
--- a/lisp/org.el
+++ b/lisp/org.el
@@ -5273,8 +5273,10 @@ define-derived-mode org-mode
                       forward-thing-provider-alist)))
   (when (boundp 'bounds-of-thing-at-point-provider-alist)
     (setq-local bounds-of-thing-at-point-provider-alist
-                (cons '(url . org--bounds-of-link-at-point)
-                      bounds-of-thing-at-point-provider-alist)))
+                (append
+                 '((url . org--bounds-of-link-at-point)
+                   (sentence . org--bounds-of-sentence-at-point))
+                 bounds-of-thing-at-point-provider-alist)))
 
   ;; If empty file that did not turn on Org mode automatically, make
   ;; it to.
@@ -9031,6 +9033,25 @@ defun org--bounds-of-link-at-point
       (cons (org-element-begin context)
             (org-element-end context)))))
 
+(defun org--bounds-of-sentence-at-point ()
+  "`bounds-of-thing-at-point' provider function for sentences."
+  (save-excursion
+    (let* ((orig (point))
+           (sentence-end-double-space t)
+           (end (org-forward-sentence 1))
+           (beg (org-backward-sentence 1)))
+      (if (and (< beg end)
+               (<= orig end)
+               (<= beg orig))
+          (cons beg end)
+        (goto-char orig)
+        (setq beg (org-backward-sentence 1))
+        (setq end (org-forward-sentence 1))
+        (when (and (< beg end)
+                   (<= orig end)
+                   (<= beg orig))
+          (cons beg end))))))
+
 ;;; File search
 
 (defun org-do-occur (regexp &optional cleanup)
diff --git a/testing/lisp/test-org.el b/testing/lisp/test-org.el
index 51265d255..d903403a6 100644
--- a/testing/lisp/test-org.el
+++ b/testing/lisp/test-org.el
@@ -3749,14 +3749,46 @@ defmacro org-test-without-dow
       (should (equal (bounds-of-thing-at-point 'url)
                      '(1 . 51))))))
 
+(ert-deftest test-org/thing-at-point/sentence ()
+  "Test that `thing-at-point' returns the sentence at point."
+  (org-test-with-temp-text
+   "This sentence is before the list.  There's one here.  This is a test:
+
+- Is this the first sentence?  There is another.
+- This is the third sentence.
+- Some
+- are
+- over several lines!
+
+The end."
+   (when (boundp 'bounds-of-thing-at-point-provider-alist)
+     (goto-char (point-min))
+     (should (string= (thing-at-point 'sentence)
+                      "This sentence is before the list."))
+     (re-search-forward "one here\\.")
+     (should (string= (thing-at-point 'sentence)
+                      "There's one here."))
+     (re-search-forward "test")
+     (should (string= (thing-at-point 'sentence)
+                      "This is a test:"))
+     (re-search-forward "first")
+     (should (string= (thing-at-point 'sentence)
+                      "Is this the first sentence?"))
+     (re-search-forward "another")
+     (should (string= (thing-at-point 'sentence)
+                      "There is another."))
+     (re-search-forward "Some")
+     (should (string= (thing-at-point 'sentence)
+                      "Some\n- are\n- over several lines!")))))
+
 
 ;;; Node Properties
 
 (ert-deftest test-org/accumulated-properties-in-drawers ()
   "Ensure properties accumulate in subtree drawers."
   (org-test-at-id "75282ba2-f77a-4309-a970-e87c149fe125"
-    (org-babel-next-src-block)
-    (should (equal '(2 1) (org-babel-execute-src-block)))))
+                  (org-babel-next-src-block)
+                  (should (equal '(2 1) (org-babel-execute-src-block)))))
 
 (ert-deftest test-org/custom-properties ()
   "Test custom properties specifications."
-- 
2.43.0

Best regards,

Sacha

Reply via email to