Hi,

This small series keeps the original narrowing visible while reading a new
heading title.

`org-edit-headline' widens the buffer in order to find and update the
current heading.  However, the interactive prompt does not need to run in
the widened buffer.  The first patch temporarily restores the original
narrowing while reading the new heading text.

The second patch handles the column view ITEM path separately.  Column view
calls `org-edit-headline' through `org-with-point-at', which widens the
buffer before the command runs.  Therefore, the ITEM value has to be read
before moving to the heading marker.

Best,
-- 
Slawomir Grochowski
>From d4e5d2ee3990157cd623efe4d7c332c6d634a534 Mon Sep 17 00:00:00 2001
From: Slawomir Grochowski <[email protected]>
Date: Tue, 23 Jun 2026 09:49:54 +0200
Subject: [PATCH 1/2] ; org: Preserve narrowing while editing heading

* lisp/org.el (org-edit-headline): Temporarily restore narrowing
while reading new heading text.
* testing/lisp/test-org.el (test-org/edit-headline): Test it.
---
 lisp/org.el              | 33 ++++++++++++++++++++-------------
 testing/lisp/test-org.el | 18 +++++++++++++++++-
 2 files changed, 37 insertions(+), 14 deletions(-)

diff --git a/lisp/org.el b/lisp/org.el
index 04eed3088..da8ae6588 100644
--- a/lisp/org.el
+++ b/lisp/org.el
@@ -6852,19 +6852,26 @@ This is a list with the following elements:
   "Edit the current headline.
 Set it to HEADING when provided."
   (interactive nil org-mode)
-  (org-with-wide-buffer
-   (org-back-to-heading t)
-   (let ((case-fold-search nil))
-     (when (looking-at org-complex-heading-regexp)
-       (let* ((old (match-string-no-properties 4))
-	      (new (save-match-data
-		     (org-trim (or heading (read-string "Edit: " old))))))
-	 (unless (equal old new)
-	   (if old (replace-match new t t nil 4)
-	     (goto-char (or (match-end 3) (match-end 2) (match-end 1)))
-	     (insert " " new))
-	   (when org-auto-align-tags (org-align-tags))
-	   (when (looking-at "[ \t]*$") (replace-match ""))))))))
+  (let ((beg (point-min))
+	(end (point-max)))
+    (org-with-wide-buffer
+     (org-back-to-heading t)
+     (let ((case-fold-search nil))
+       (when (looking-at org-complex-heading-regexp)
+	 (let* ((old (match-string-no-properties 4))
+		(new (save-match-data
+		       (org-trim
+			(or heading
+			    (save-excursion
+			      (save-restriction
+				(narrow-to-region beg end)
+				(read-string "Edit: " old))))))))
+	   (unless (equal old new)
+	     (if old (replace-match new t t nil 4)
+	       (goto-char (or (match-end 3) (match-end 2) (match-end 1)))
+	       (insert " " new))
+	     (when org-auto-align-tags (org-align-tags))
+	     (when (looking-at "[ \t]*$") (replace-match "")))))))))
 
 (defun org-insert-heading-after-current ()
   "Insert a new heading with same level as current, after current subtree."
diff --git a/testing/lisp/test-org.el b/testing/lisp/test-org.el
index aabf18bfa..1b0bcbf3d 100644
--- a/testing/lisp/test-org.el
+++ b/testing/lisp/test-org.el
@@ -3283,7 +3283,23 @@ More text
    (equal "* B :tag:"
 	  (org-test-with-temp-text "* A :tag:"
 	    (let ((org-tags-column 4)) (org-edit-headline "B"))
-	    (buffer-string)))))
+	    (buffer-string))))
+  ;; Preserve narrowing while reading a new heading.
+  (should
+   (equal "B"
+	  (org-test-with-temp-text "* Top
+** <point>A
+*** Child
+* Other"
+	    (org-narrow-to-subtree)
+	    (let ((min (point-min)))
+	      (cl-letf (((symbol-function 'read-string)
+			 (lambda (&rest _)
+			   (should (buffer-narrowed-p))
+			   (should (= (point-min) min))
+			   "B")))
+		(org-edit-headline))
+	      (org-get-heading t t t t))))))
 
 
 
-- 
2.39.5

>From ebd1b0717a7bd8b123f2d619de0ed0cd09e760b1 Mon Sep 17 00:00:00 2001
From: Slawomir Grochowski <[email protected]>
Date: Tue, 23 Jun 2026 09:59:52 +0200
Subject: [PATCH 2/2] ; org-colview: Preserve narrowing editing ITEM

* lisp/org-colview.el (org-columns-edit-value): Read a new ITEM
value before moving to the heading marker.
* testing/lisp/test-org-colview.el
(test-org-colview/columns-edit-value): Test editing ITEM through
column view.
---
 lisp/org-colview.el              |  8 +++++++-
 testing/lisp/test-org-colview.el | 19 +++++++++++++++++++
 2 files changed, 26 insertions(+), 1 deletion(-)

diff --git a/lisp/org-colview.el b/lisp/org-colview.el
index 37cfbe937..97e874274 100644
--- a/lisp/org-colview.el
+++ b/lisp/org-colview.el
@@ -835,7 +835,13 @@ Where possible, use the standard interface for changing this line."
 	      ("BEAMER_ENV" (command-action #'org-beamer-select-environment))
 	      ("CLOCKSUM" (user-error "This special column cannot be edited"))
 	      ("DEADLINE" (command-action #'org-deadline))
-	      ("ITEM" (command-action #'org-edit-headline))
+	      ("ITEM"
+	       (let* ((value (org-with-point-at pom
+			 (or (nth 4 (org-heading-components)) "")))
+		      (nval (org-trim (read-string "Edit: " value))))
+		 (and (not (equal nval value))
+		      (lambda ()
+			(org-with-point-at pom (org-edit-headline nval))))))
 	      ("PRIORITY" (command-action #'org-priority))
 	      ("SCHEDULED" (command-action #'org-schedule))
 	      ("TAGS"
diff --git a/testing/lisp/test-org-colview.el b/testing/lisp/test-org-colview.el
index 6a1f9d21b..8d7dc7692 100644
--- a/testing/lisp/test-org-colview.el
+++ b/testing/lisp/test-org-colview.el
@@ -1706,6 +1706,25 @@ https://list.orgmode.org/[email protected]/T/#u.";
 		       (lambda (&rest _) "new")))
 	      (org-columns-edit-value))
 	    (org-entry-get (point) "A"))))
+  ;; Edit ITEM while preserving narrowing at the prompt.
+  (should
+   (equal "B"
+	  (org-test-with-temp-text "* Top
+** <point>A
+*** Child
+* Other"
+	    (org-narrow-to-subtree)
+	    (let ((min (point-min))
+		  (org-columns-default-format "%ITEM"))
+	      (org-columns)
+	      (cl-letf (((symbol-function 'read-string)
+			 (lambda (_prompt initial &rest _)
+			   (should (equal initial "A"))
+			   (should (buffer-narrowed-p))
+			   (should (= (point-min) min))
+			   "B")))
+		(org-columns-edit-value "ITEM"))
+	      (org-get-heading t t t t)))))
   ;; When the new value matches the current one, the property is
   ;; left untouched.
   (should
-- 
2.39.5

Reply via email to